[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Commit-gnuradio] r10172 - in gnuradio/trunk: gr-usrp2/src usrp2/firmwar
From: |
jcorgan |
Subject: |
[Commit-gnuradio] r10172 - in gnuradio/trunk: gr-usrp2/src usrp2/firmware/apps usrp2/firmware/include usrp2/host/include/usrp2 usrp2/host/lib |
Date: |
Sat, 27 Dec 2008 14:09:27 -0700 (MST) |
Author: jcorgan
Date: 2008-12-27 14:09:26 -0700 (Sat, 27 Dec 2008)
New Revision: 10172
Modified:
gnuradio/trunk/gr-usrp2/src/usrp2.i
gnuradio/trunk/gr-usrp2/src/usrp2_base.cc
gnuradio/trunk/gr-usrp2/src/usrp2_base.h
gnuradio/trunk/usrp2/firmware/apps/app_common_v2.c
gnuradio/trunk/usrp2/firmware/include/usrp2_eth_packet.h
gnuradio/trunk/usrp2/host/include/usrp2/usrp2.h
gnuradio/trunk/usrp2/host/lib/control.h
gnuradio/trunk/usrp2/host/lib/usrp2.cc
gnuradio/trunk/usrp2/host/lib/usrp2_impl.cc
gnuradio/trunk/usrp2/host/lib/usrp2_impl.h
Log:
Implements USRP2 peek() command, allowing arbitrary reads from the internal
Wishbone bus. Minor fix for USRP2 sync_to_pps() (uses correct packet type.)
Example:
>>> from gnuradio import usrp2
>>> u = usrp2.source_32fc()
>>> u.peek(0x1234, 4) # Read four bytes at offset 0x1234 (code)
(185, 244, 253, 164)
>>>
The return value will be zero length upon error.
The read address must be 32-bit aligned, and only the lower 16 bits are
significant. The length must be an integral multiple of 4 bytes. There is
currently a read limit of 176 bytes per read; to change requires some
additional
firmware changes to allocate a larger reply packet.
WARNING: Trying to read from memory locations not serviced by RAM or by a
Wishbone peripheral may result in a hang requiring a USRP2 power cycle. The
USRP2 internal memory map is documented in usrp2/firmware/lib/memory_map.h.
Modified: gnuradio/trunk/gr-usrp2/src/usrp2.i
===================================================================
--- gnuradio/trunk/gr-usrp2/src/usrp2.i 2008-12-27 00:56:08 UTC (rev 10171)
+++ gnuradio/trunk/gr-usrp2/src/usrp2.i 2008-12-27 21:09:26 UTC (rev 10172)
@@ -24,6 +24,7 @@
%include "exception.i"
%import "gnuradio.i" // the common stuff
+%import <stdint.i>
%{
#include <gnuradio_swig_bug_workaround.h>
@@ -35,6 +36,8 @@
%include <usrp2/tune_result.h>
+%template(uint8_t_vector) std::vector<uint8_t>;
+
// ----------------------------------------------------------------
class usrp2_base : public gr_sync_block
@@ -49,6 +52,7 @@
%rename(_real_fpga_master_clock_freq) fpga_master_clock_freq;
bool fpga_master_clock_freq(long *freq);
bool sync_to_pps();
+ std::vector<uint8_t> peek(uint32_t addr, uint32_t len);
};
// ----------------------------------------------------------------
Modified: gnuradio/trunk/gr-usrp2/src/usrp2_base.cc
===================================================================
--- gnuradio/trunk/gr-usrp2/src/usrp2_base.cc 2008-12-27 00:56:08 UTC (rev
10171)
+++ gnuradio/trunk/gr-usrp2/src/usrp2_base.cc 2008-12-27 21:09:26 UTC (rev
10172)
@@ -67,6 +67,12 @@
return d_u2->sync_to_pps();
}
+std::vector<uint8_t>
+usrp2_base::peek(uint32_t addr, uint32_t len)
+{
+ return d_u2->peek(addr, len);
+}
+
bool
usrp2_base::start()
{
Modified: gnuradio/trunk/gr-usrp2/src/usrp2_base.h
===================================================================
--- gnuradio/trunk/gr-usrp2/src/usrp2_base.h 2008-12-27 00:56:08 UTC (rev
10171)
+++ gnuradio/trunk/gr-usrp2/src/usrp2_base.h 2008-12-27 21:09:26 UTC (rev
10172)
@@ -63,7 +63,13 @@
*/
bool sync_to_pps();
+
/*!
+ * \brief Read memory from Wishbone bus
+ */
+ std::vector<uint8_t> peek(uint32_t addr, uint32_t len);
+
+ /*!
* \brief Called by scheduler when starting flowgraph
*/
virtual bool start();
Modified: gnuradio/trunk/usrp2/firmware/apps/app_common_v2.c
===================================================================
--- gnuradio/trunk/usrp2/firmware/apps/app_common_v2.c 2008-12-27 00:56:08 UTC
(rev 10171)
+++ gnuradio/trunk/usrp2/firmware/apps/app_common_v2.c 2008-12-27 21:09:26 UTC
(rev 10172)
@@ -332,6 +332,30 @@
}
static size_t
+peek_cmd(const op_peek_t *p,
+ void *reply_payload, size_t reply_payload_space)
+{
+ op_generic_t *r = (op_generic_t *) reply_payload;
+
+ putstr("peek: addr="); puthex32(p->addr);
+ printf(" bytes=%u\n", p->bytes);
+
+ if (reply_payload_space < (sizeof(*r) + p->bytes)) {
+ putstr("peek: insufficient reply packet space\n");
+ return 0; // FIXME do partial read?
+ }
+
+ r->opcode = OP_PEEK_REPLY;
+ r->len = sizeof(*r)+p->bytes;
+ r->rid = p->rid;
+ r->ok = true;
+
+ memcpy_wa(reply_payload+sizeof(*r), p->addr, p->bytes);
+
+ return r->len;
+}
+
+static size_t
generic_reply(const op_generic_t *p,
void *reply_payload, size_t reply_payload_space,
bool ok)
@@ -435,6 +459,10 @@
sync_to_pps((op_generic_t *) payload));
break;
+ case OP_PEEK:
+ subpktlen = peek_cmd((op_peek_t *)payload, reply_payload,
reply_payload_space);
+ break;
+
default:
printf("app_common_v2: unhandled opcode = %d\n", gp->opcode);
break;
Modified: gnuradio/trunk/usrp2/firmware/include/usrp2_eth_packet.h
===================================================================
--- gnuradio/trunk/usrp2/firmware/include/usrp2_eth_packet.h 2008-12-27
00:56:08 UTC (rev 10171)
+++ gnuradio/trunk/usrp2/firmware/include/usrp2_eth_packet.h 2008-12-27
21:09:26 UTC (rev 10172)
@@ -185,13 +185,9 @@
#define OP_DBOARD_INFO_REPLY (OP_DBOARD_INFO | OP_REPLY_BIT)
#define OP_SYNC_TO_PPS 10
#define OP_SYNC_TO_PPS_REPLY (OP_SYNC_TO_PPS | OP_REPLY_BIT)
+#define OP_PEEK 11
+#define OP_PEEK_REPLY (OP_PEEK | OP_REPLY_BIT)
-
-//#define OP_WRITE_REG xx // not implemented
-//#define OP_WRITE_REG_MASKED xx
-//#define OP_READ_REG xx
-//#define OP_READ_REG_REPLY xx
-
/*
* All subpackets are a multiple of 4 bytes long.
* All subpackets start with an 8-bit opcode, an 8-bit len and an 8-bit rid.
@@ -203,7 +199,7 @@
*
* Used by:
* OP_EOP, OP_BURN_MAC_ADDR_REPLY, OP_START_RX_STREAMING_REPLY,
- * OP_STOP_RX_REPLY, OP_DBOARD_INFO
+ * OP_STOP_RX_REPLY, OP_DBOARD_INFO, OP_SYNC_TO_PPS
*/
typedef struct {
uint8_t opcode;
@@ -380,8 +376,18 @@
u2_db_info_t rx_db_info;
} _AL4 op_dboard_info_reply_t;
+/*!
+ * \brief Read from Wishbone memory
+ */
+typedef struct {
+ uint8_t opcode;
+ uint8_t len;
+ uint8_t rid;
+ uint8_t mbz;
+ uint32_t addr;
+ uint32_t bytes;
+} _AL4 op_peek_t;
-
/*
* ================================================================
* union of all of subpacket types
@@ -399,6 +405,7 @@
op_config_tx_v2_t op_config_tx_v2;
op_config_tx_reply_v2_t op_config_tx_reply_v2;
op_config_mimo_t op_config_mimo;
+ op_peek_t op_peek;
} u2_subpkt_t;
Modified: gnuradio/trunk/usrp2/host/include/usrp2/usrp2.h
===================================================================
--- gnuradio/trunk/usrp2/host/include/usrp2/usrp2.h 2008-12-27 00:56:08 UTC
(rev 10171)
+++ gnuradio/trunk/usrp2/host/include/usrp2/usrp2.h 2008-12-27 21:09:26 UTC
(rev 10172)
@@ -361,6 +361,21 @@
*/
bool sync_to_pps();
+ /*!
+ * Read memory from Wishbone bus
+ *
+ * \param addr 32-bit aligned address. Only the lower 16-bits are
significant.
+ * \param len Number of bytes to read, must be positive and multiple
of 4.
+ *
+ * \returns Vector of 8-bit read values
+ *
+ * WARNING: Attempts to read memory from addresses that do not correspond
to RAM or
+ * memory-mapped peripherals may cause the USRP2 to hang, requiring a
power cycle.
+ *
+ */
+ std::vector<uint8_t> peek(uint32_t addr, uint32_t len);
+
+
#if 0 // not yet implemented
/*!
* \brief Write EEPROM on motherboard or any daughterboard.
Modified: gnuradio/trunk/usrp2/host/lib/control.h
===================================================================
--- gnuradio/trunk/usrp2/host/lib/control.h 2008-12-27 00:56:08 UTC (rev
10171)
+++ gnuradio/trunk/usrp2/host/lib/control.h 2008-12-27 21:09:26 UTC (rev
10172)
@@ -23,6 +23,13 @@
#include <usrp2_eth_packet.h>
namespace usrp2 {
+
+ struct op_generic_cmd {
+ u2_eth_packet_t h;
+ op_generic_t op;
+ op_generic_t eop;
+ };
+
/*!
* OP_CONFIG_RX_V2 command packet
*/
@@ -73,6 +80,11 @@
op_generic_t eop;
};
+ struct op_peek_cmd {
+ u2_eth_packet_t h;
+ op_peek_t op;
+ op_generic_t eop;
+ };
/*!
* Control mechanism to allow API calls to block waiting for reply packets
Modified: gnuradio/trunk/usrp2/host/lib/usrp2.cc
===================================================================
--- gnuradio/trunk/usrp2/host/lib/usrp2.cc 2008-12-27 00:56:08 UTC (rev
10171)
+++ gnuradio/trunk/usrp2/host/lib/usrp2.cc 2008-12-27 21:09:26 UTC (rev
10172)
@@ -395,6 +395,12 @@
return d_impl->sync_to_pps();
}
+ std::vector<uint8_t>
+ usrp2::peek(uint32_t addr, uint32_t len)
+ {
+ return d_impl->peek(addr, len);
+ }
+
} // namespace usrp2
Modified: gnuradio/trunk/usrp2/host/lib/usrp2_impl.cc
===================================================================
--- gnuradio/trunk/usrp2/host/lib/usrp2_impl.cc 2008-12-27 00:56:08 UTC (rev
10171)
+++ gnuradio/trunk/usrp2/host/lib/usrp2_impl.cc 2008-12-27 21:09:26 UTC (rev
10172)
@@ -72,12 +72,9 @@
case OP_DBOARD_INFO: return "OP_DBOARD_INFO";
case OP_DBOARD_INFO_REPLY: return "OP_DBOARD_INFO_REPLY";
case OP_SYNC_TO_PPS: return "OP_SYNC_TO_PPS";
-#if 0
- case OP_WRITE_REG: return "OP_WRITE_REG";
- case OP_WRITE_REG_MASKED: return "OP_WRITE_REG_MASKED";
- case OP_READ_REG: return "OP_READ_REG";
- case OP_READ_REG_REPLY: return "OP_READ_REG_REPLY";
-#endif
+ case OP_PEEK: return "OP_PEEK";
+ case OP_PEEK_REPLY: return "OP_PEEK_REPLY";
+
default:
char buf[64];
snprintf(buf, sizeof(buf), "<unknown opcode: %d>", opcode);
@@ -1024,8 +1021,8 @@
bool
usrp2::impl::sync_to_pps()
{
- op_config_mimo_cmd cmd;
- op_generic_t reply;
+ op_generic_cmd cmd;
+ op_generic_t reply;
memset(&cmd, 0, sizeof(cmd));
init_etf_hdrs(&cmd.h, d_addr, 0, CONTROL_CHAN, -1);
@@ -1042,4 +1039,47 @@
return ntohx(reply.ok) == 1;
}
+ std::vector<uint8_t>
+ usrp2::impl::peek(uint32_t addr, uint32_t len)
+ {
+ std::vector<uint8_t> result; // zero sized on error return
+ // fprintf(stderr, "usrp2::peek: addr=%08X len=%u\n", addr, len);
+
+ if (addr % 4 != 0) {
+ fprintf(stderr, "usrp2::peek: addr (=%08X) must be 32-bit word
aligned\n", addr);
+ return result;
+ }
+
+ if (len < 4 || len % 4 != 0) {
+ fprintf(stderr, "usrp2::peek: len (=%u) must be an integral multiple of
4\n", len);
+ return result;
+ }
+
+ op_peek_cmd cmd;
+ op_generic_t *reply;
+
+ memset(&cmd, 0, sizeof(cmd));
+ init_etf_hdrs(&cmd.h, d_addr, 0, CONTROL_CHAN, -1);
+ cmd.op.opcode = OP_PEEK;
+ cmd.op.len = sizeof(cmd.op);
+ cmd.op.rid = d_next_rid++;
+ cmd.eop.opcode = OP_EOP;
+ cmd.eop.len = sizeof(cmd.eop);
+
+ cmd.op.addr = htonl(addr);
+ cmd.op.bytes = htonl(len);
+
+ reply = (op_generic_t *)malloc(sizeof(*reply)+len);
+ pending_reply p(cmd.op.rid, reply, sizeof(*reply)+len);
+ if (transmit_cmd(&cmd, sizeof(cmd), &p, DEF_CMD_TIMEOUT)) {
+ uint32_t bytes = reply->len-sizeof(*reply);
+ uint8_t *data = (uint8_t *)(reply)+sizeof(*reply);
+ for (unsigned int i = 0; i < bytes; i++)
+ result.push_back(data[i]);
+ }
+
+ free(reply);
+ return result;
+ }
+
} // namespace usrp2
Modified: gnuradio/trunk/usrp2/host/lib/usrp2_impl.h
===================================================================
--- gnuradio/trunk/usrp2/host/lib/usrp2_impl.h 2008-12-27 00:56:08 UTC (rev
10171)
+++ gnuradio/trunk/usrp2/host/lib/usrp2_impl.h 2008-12-27 21:09:26 UTC (rev
10172)
@@ -174,6 +174,7 @@
bool burn_mac_addr(const std::string &new_addr);
bool sync_to_pps();
+ std::vector<uint8_t> peek(uint32_t addr, uint32_t len);
};
} // namespace usrp2
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [Commit-gnuradio] r10172 - in gnuradio/trunk: gr-usrp2/src usrp2/firmware/apps usrp2/firmware/include usrp2/host/include/usrp2 usrp2/host/lib,
jcorgan <=