commit-gnuradio
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Commit-gnuradio] r8436 - gnuradio/branches/developers/gnychis/inband/us


From: gnychis
Subject: [Commit-gnuradio] r8436 - gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband
Date: Sat, 17 May 2008 12:01:18 -0600 (MDT)

Author: gnychis
Date: 2008-05-17 12:01:17 -0600 (Sat, 17 May 2008)
New Revision: 8436

Modified:
   
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/qa_inband_usrp_server.cc
   
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/qa_inband_usrp_server.h
   
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_inband_usb_packet.h
   
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_rx_stub.cc
   
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_rx_stub.h
   
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_server.cc
   
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_server.h
   
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_tx_stub.cc
Log:
adding in TX success feedback support through the tag and drop flag... also 
adding in QA code

Modified: 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/qa_inband_usrp_server.cc
===================================================================
--- 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/qa_inband_usrp_server.cc
   2008-05-17 13:39:23 UTC (rev 8435)
+++ 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/qa_inband_usrp_server.cc
   2008-05-17 18:01:17 UTC (rev 8436)
@@ -1237,6 +1237,142 @@
 
 // 
----------------------------------------------------------------------------------------------
 
+class qa_tags_top : public mb_mblock
+{
+  mb_port_sptr d_tx;
+  mb_port_sptr d_rx;
+  mb_port_sptr d_cs;
+
+  long d_next_tag;
+  long d_tags_to_check;
+  bool d_running_check_wrap;
+
+ public:
+  qa_tags_top(mb_runtime *runtime, const std::string &instance_name, pmt_t 
user_arg);
+  ~qa_tags_top();
+  void initial_transition();
+  void handle_message(mb_message_sptr msg);
+ 
+ protected:
+  void check_message(mb_message_sptr msg);
+  void run_tests();
+  void tx_tags();
+
+};
+
+qa_tags_top::qa_tags_top(mb_runtime *runtime, const std::string 
&instance_name, pmt_t user_arg)
+  : mb_mblock(runtime, instance_name, user_arg),
+  d_next_tag(0),
+  d_tags_to_check(usrp_server::D_MAX_TAG),
+  d_running_check_wrap(false)
+{ 
+  
+  d_rx = define_port("rx0", "usrp-rx", false, mb_port::INTERNAL);
+  d_tx = define_port("tx0", "usrp-tx", false, mb_port::INTERNAL);
+  d_cs = define_port("cs", "usrp-server-cs", false, mb_port::INTERNAL);
+ 
+  // Use the stub with the usrp_server
+  pmt_t usrp_server_dict = pmt_make_dict();
+  pmt_dict_set(usrp_server_dict, pmt_intern("fake-usrp"),PMT_T);
+
+  // Test the TX side
+  define_component("server", "usrp_server", usrp_server_dict);
+  connect("self", "tx0", "server", "tx0");
+  connect("self", "rx0", "server", "rx0");
+  connect("self", "cs", "server", "cs");
+
+}
+
+qa_tags_top::~qa_tags_top() {}
+
+void
+qa_tags_top::initial_transition()
+{
+  run_tests();
+}
+
+void
+qa_tags_top::run_tests()
+{
+  // Retrieve information about the USRP, then run tests
+  d_cs->send(s_cmd_open, 
+             pmt_list2(pmt_list2(s_response_open, PMT_T), 
+             pmt_from_long(0)));
+
+  // should be able to allocate 1 byte
+  d_tx->send(s_cmd_allocate_channel, 
+             pmt_list2(pmt_list2(s_response_allocate_channel, PMT_T), 
+                       pmt_from_long(1)));
+  
+  d_rx->send(s_cmd_allocate_channel, 
+             pmt_list2(pmt_list2(s_response_allocate_channel, PMT_T), 
+                       pmt_from_long(1)));
+  
+  // Need to start receiving to read from the USRP to get tag responses
+  d_rx->send(s_cmd_start_recv_raw_samples, 
+             pmt_list2(PMT_NIL, 
+                       pmt_from_long(0)));
+  tx_tags();
+}
+
+void
+qa_tags_top::tx_tags()
+{
+  // Transmit a bunch of frames
+  for(int i=0; i < d_tags_to_check; i++)
+    d_tx->send(s_cmd_xmit_raw_frame, 
+               pmt_list4(pmt_list2(s_response_xmit_raw_frame, 
pmt_from_long(i)), 
+                         pmt_from_long(0), 
+                         pmt_make_u32vector(transport_pkt::max_payload()/4, 
0), 
+                         pmt_from_long(0)));
+}
+
+void
+qa_tags_top::handle_message(mb_message_sptr msg)
+{
+  if (pmt_eq(msg->port_id(), d_tx->port_symbol())
+      && pmt_eq(msg->signal(), s_response_xmit_raw_frame))
+    check_message(msg);
+}
+
+void
+qa_tags_top::check_message(mb_message_sptr msg)
+{
+  pmt_t data = msg->data();
+  pmt_t event = msg->signal();
+
+  pmt_t expected = pmt_nth(0, data);
+  pmt_t status = pmt_nth(1, data);
+
+  pmt_t e_event = pmt_nth(0, expected);
+  long e_tag = pmt_to_long(pmt_nth(1, expected));
+  
+  if(e_tag!=d_next_tag) {
+    std::cerr << "[QA_TAGS_TOP] Improper tag"
+              << "\n  expected: " << e_tag
+              << "\n  got: " << d_next_tag
+              << std::endl;
+    shutdown_all(PMT_F);
+  }
+
+  d_next_tag = (d_next_tag+1) % usrp_server::D_MAX_TAG;
+  d_tags_to_check--;
+  
+  if(d_tags_to_check==0 && d_running_check_wrap)
+    shutdown_all(PMT_T);
+
+  if(d_tags_to_check==0 && !d_running_check_wrap) {
+    d_tags_to_check = usrp_server::D_MAX_TAG;
+    d_running_check_wrap = true;
+    tx_tags();
+  }
+}
+
+
+REGISTER_MBLOCK_CLASS(qa_tags_top);
+
+// 
----------------------------------------------------------------------------------------------
+
 class qa_cs_top : public mb_mblock
 {
   mb_port_sptr d_tx;
@@ -1567,3 +1703,14 @@
   
   CPPUNIT_ASSERT(pmt_equal(PMT_T, result));
 }
+
+void
+qa_inband_usrp_server::test_tags()
+{
+  mb_runtime_sptr rt = mb_make_runtime();
+  pmt_t result = PMT_T;
+
+  rt->run("top", "qa_tags_top", PMT_F, &result);
+
+  CPPUNIT_ASSERT(pmt_equal(PMT_T, result));
+}

Modified: 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/qa_inband_usrp_server.h
===================================================================
--- 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/qa_inband_usrp_server.h
    2008-05-17 13:39:23 UTC (rev 8435)
+++ 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/qa_inband_usrp_server.h
    2008-05-17 18:01:17 UTC (rev 8436)
@@ -35,6 +35,7 @@
   CPPUNIT_TEST(test_rx);
   CPPUNIT_TEST(test_cs);
   CPPUNIT_TEST(test_rid);
+  CPPUNIT_TEST(test_tags);
   CPPUNIT_TEST_SUITE_END();
 
  private:
@@ -45,6 +46,7 @@
   void test_rx();
   void test_cs();
   void test_rid();
+  void test_tags();
 };
 
 #endif /* INCLUDED_QA_INBAND_USRP_SERVER_H */

Modified: 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_inband_usb_packet.h
===================================================================
--- 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_inband_usb_packet.h
   2008-05-17 13:39:23 UTC (rev 8435)
+++ 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_inband_usb_packet.h
   2008-05-17 18:01:17 UTC (rev 8436)
@@ -32,6 +32,7 @@
 static const int USB_PKT_SIZE = 512;   // bytes
 static const int MAX_PAYLOAD = USB_PKT_SIZE-2*sizeof(uint32_t);
 static const int CONTROL_CHAN = 0x1f;
+static const int TAG_INVALID = 0xf;
 
 class usrp_inband_usb_packet {
   //

Modified: 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_rx_stub.cc
===================================================================
--- 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_rx_stub.cc
    2008-05-17 13:39:23 UTC (rev 8435)
+++ 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_rx_stub.cc
    2008-05-17 18:01:17 UTC (rev 8436)
@@ -48,6 +48,7 @@
 // Used for the fake control packet response code to send the responses back up
 // the RX.  The TX stub dumps responses in to this queue.
 std::queue<pmt_t> d_cs_queue;
+std::queue<long> d_tags;
 
 usrp_rx_stub::usrp_rx_stub(mb_runtime *rt, const std::string &instance_name, 
pmt_t user_arg)
   : mb_mblock(rt, instance_name, user_arg),
@@ -194,9 +195,16 @@
   transport_pkt *pkt =
     (transport_pkt *) pmt_u8vector_writeable_elements(v_pkt, ignore);
 
-  pkt->set_header(0, channel, 0, n_bytes);
+  long tag = TAG_INVALID;
+  if(!d_tags.empty()) {
+    tag = d_tags.front();
+    d_tags.pop();
+  }
+
+  pkt->set_header(0, channel, tag, n_bytes);
   pkt->set_timestamp(0xffffffff);
   memcpy(pkt->payload(), samples, n_bytes);
+
   
   d_cs->send(s_response_usrp_rx_read, pmt_list3(PMT_NIL, PMT_T, v_pkt));
 

Modified: 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_rx_stub.h
===================================================================
--- 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_rx_stub.h 
    2008-05-17 13:39:23 UTC (rev 8435)
+++ 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_rx_stub.h 
    2008-05-17 18:01:17 UTC (rev 8436)
@@ -33,6 +33,7 @@
 
 extern bool usrp_rx_stop_stub;   // used to communicate a 'stop' to the RX stub
 extern std::queue<pmt_t> d_cs_queue;
+extern std::queue<long> d_tags;
 
 static pmt_t s_timeout = pmt_intern("%timeout");
 static pmt_t s_done = pmt_intern("done");

Modified: 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_server.cc
===================================================================
--- 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_server.cc 
    2008-05-17 13:39:23 UTC (rev 8435)
+++ 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_server.cc 
    2008-05-17 18:01:17 UTC (rev 8436)
@@ -138,8 +138,9 @@
 
   for(int i=0; i < D_MAX_TAG; i++)
     d_tags.push_back(tag_info());
-  d_curr_tag=0;
 
+  d_next_tag=0;
+
   //d_fake_rx=true;
 }
 
@@ -259,10 +260,10 @@
       if(channel == CONTROL_CHAN)
         return;
 
-      // Find the port through the owner of the channel
-      if((port = tx_port_index(d_chaninfo_tx[channel].owner)) !=-1 )
-        d_tx[port]->send(s_response_xmit_raw_frame, 
-                         pmt_list2(invocation_handle, status));
+      // Do not report of success until we get a tag response from the USRP
+//      if((port = tx_port_index(d_chaninfo_tx[channel].owner)) !=-1 )
+//        d_tx[port]->send(s_response_xmit_raw_frame, 
+//                         pmt_list2(invocation_handle, status));
       return;
     }
     //--------------- USRP READ ---------------//
@@ -733,22 +734,42 @@
       std::min((long)(n_bytes-(n*max_payload_len)), (long)max_payload_len);
   
     if(n == 0) { // first packet gets start of burst flag and timestamp
+      
+      // Do not set a tag if the RX is disabled, because feedback will not be
+      // possible (tag responses are carried on RX packets)
+      long tag = TAG_INVALID;
+      if(d_rx_chan_mask==0)
+        goto tag_bail;
 
-      d_tags[d_curr_tag].owner = port->port_symbol();
-      d_tags[d_curr_tag].invocation_handle = invocation_handle;
+      tag = d_next_tag;
+      d_next_tag = (d_next_tag+1) % D_MAX_TAG;
+
+      // Check for tag wrap-around, cause exit giving helpful info
+      if(!pmt_eqv(d_tags[tag].owner, PMT_NIL)) {
+        std::cerr << "[USRP_SERVER] Error: non-throttling of TX causing tag 
wraparound\n";
+        std::cerr << "  Killing because TX responses from USRP will not be 
valid\n";
+        std::cerr << "  Throttle transmitter by starting a pipeline of 4 TX 
packets, "
+                  << "then only transmit another packet when a 
s_response_xmit_raw_frame "
+                  << "signal is generated\n";
+        shutdown_all(PMT_F);
+      }
+
+      d_tags[tag].owner = port->port_symbol();
+      d_tags[tag].invocation_handle = invocation_handle;
+
+tag_bail:
       
       if(carrier_sense)
         pkts[n].set_header(pkts[n].FL_START_OF_BURST 
                            | pkts[n].FL_CARRIER_SENSE, 
-                           channel, d_curr_tag, payload_len);
+                           channel, tag, payload_len);
       else
-        pkts[n].set_header(pkts[n].FL_START_OF_BURST, channel, d_curr_tag, 
payload_len);
+        pkts[n].set_header(pkts[n].FL_START_OF_BURST, channel, tag, 
payload_len);
 
       pkts[n].set_timestamp(timestamp);
-      d_curr_tag = (d_curr_tag+1) % D_MAX_TAG;
     
     } else {
-      pkts[n].set_header(0, channel, 0, payload_len);
+      pkts[n].set_header(0, channel, TAG_INVALID, payload_len);
       pkts[n].set_timestamp(0xffffffff);
     }
 
@@ -835,7 +856,7 @@
     transport_pkt *pkt = (transport_pkt *) 
pmt_u8vector_writeable_elements(v_packet, psize);
     payload_len = 0;
     
-    pkt->set_header(0, channel, 0, payload_len);
+    pkt->set_header(0, channel, TAG_INVALID, payload_len);
     pkt->set_timestamp(0xffffffff);
 
   while(curr_subpkt < n_subpkts) {
@@ -1265,6 +1286,8 @@
   // The channel is used to find the port to pass the samples on
   long channel = pkt->chan();
   long payload_len = pkt->payload_len();
+  long tag = pkt->tag();
+  bool success = !pkt->dropped();
   long port;
 
   // Ignore packets which seem to have incorrect size or size 0
@@ -1279,6 +1302,10 @@
 
   if((port = rx_port_index(d_chaninfo_rx[channel].owner)) == -1)
     return; // Don't know where to send the sample... possibility on abrupt 
close
+
+  // Check the tag on the RX packet and see if it carries a valid TX/RX success
+  if(channel != CONTROL_CHAN) 
+    check_tag(tag, success);
     
   pmt_t v_samples = pmt_make_u8vector(payload_len, 0);
   uint8_t *samples = pmt_u8vector_writeable_elements(v_samples, ignore);
@@ -1313,6 +1340,45 @@
 }
 
 /*!
+ * \brief Called by handle_response_usrp_read() to check the incoming packets
+ * tag, which is feedback from the USRP to the host on TX failure/success.  The
+ * tag is a wraparound transmission ID, and the drop bit specifies if the TX 
was
+ * dropped.  If dropped, success will be false.
+ */
+void
+usrp_server::check_tag(long tag, bool success)
+{
+  // Tag does not represent valid TX feedback
+  if(tag==TAG_INVALID)
+    return;
+
+  // Check that the tag, which is a valid tag ID, is truly being used by
+  // usrp_server
+  if(pmt_eqv(d_tags[tag].owner, PMT_NIL)) {
+    std::cerr << "[USRP_SERVER] Error: received tag is improper from the 
USRP\n";
+    shutdown_all(PMT_F);
+  }
+  
+  // Tag is valid, so we check the owner of the tag and send the response
+  pmt_t owner = d_tags[tag].owner;
+  pmt_t invocation_handle = d_tags[tag].invocation_handle;
+  long port;
+  if((port = tx_port_index(owner)) != -1) {
+    d_tx[port]->send(s_response_xmit_raw_frame, 
+                     pmt_list2(invocation_handle, pmt_from_bool(success)));
+  } else {
+    std::cerr << "[USRP_SERVER] Error: owner was not valid on tag response\n";
+    shutdown_all(PMT_F);
+  }
+  
+  // Blank out the tag so that we can check for wraparound causing tag
+  // collisions (using the same tag twice before the initial tag has received a
+  // response)
+  d_tags[tag].owner = PMT_NIL;
+  d_tags[tag].invocation_handle = PMT_NIL;
+}
+
+/*!
  * \brief Called by handle_response_usrp_read() when the incoming packet has a
  * channel of CONTROL_CHAN.  This means that the incoming packet contains a
  * response for a command sent to the control channel, which this method will
@@ -1824,7 +1890,7 @@
   pmt_t v_packet = pmt_make_u8vector(sizeof(transport_pkt), 0);
   transport_pkt *pkt = (transport_pkt *) 
pmt_u8vector_writeable_elements(v_packet, psize);
   
-  pkt->set_header(0, CONTROL_CHAN, 0, payload_len);
+  pkt->set_header(0, CONTROL_CHAN, TAG_INVALID, payload_len);
   pkt->set_timestamp(0xffffffff);
 
   pkt->cs_write_reg(reg, val);
@@ -1854,7 +1920,7 @@
   pmt_t v_packet = pmt_make_u8vector(sizeof(transport_pkt), 0);
   transport_pkt *pkt = (transport_pkt *) 
pmt_u8vector_writeable_elements(v_packet, psize);
   
-  pkt->set_header(0, CONTROL_CHAN, 0, payload_len);
+  pkt->set_header(0, CONTROL_CHAN, TAG_INVALID, payload_len);
   pkt->set_timestamp(0xffffffff);
 
   pkt->cs_read_reg(0, reg);

Modified: 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_server.h
===================================================================
--- 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_server.h  
    2008-05-17 13:39:23 UTC (rev 8435)
+++ 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_server.h  
    2008-05-17 18:01:17 UTC (rev 8436)
@@ -82,9 +82,9 @@
   static const long D_MAX_RID = 64;
   std::vector<rid_info> d_rids;
 
-  static const long D_MAX_TAG = 16;
+  static const long D_MAX_TAG = 15;
   std::vector<tag_info> d_tags;
-  unsigned long d_curr_tag;
+  unsigned long d_next_tag;
 
   
   struct channel_info {
@@ -135,6 +135,7 @@
   void handle_response_usrp_read(pmt_t data);
   bool check_valid(mb_port_sptr port, long channel, std::vector<struct 
channel_info> &chan_info, pmt_t signal_info);
   void parse_control_pkt(pmt_t invocation_handle, transport_pkt *pkt);
+  void check_tag(long tag, bool success);
   long next_rid();
   void initialize_registers();
   void set_register(long reg, long val);

Modified: 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_tx_stub.cc
===================================================================
--- 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_tx_stub.cc
    2008-05-17 13:39:23 UTC (rev 8435)
+++ 
gnuradio/branches/developers/gnychis/inband/usrp/host/lib/inband/usrp_tx_stub.cc
    2008-05-17 18:01:17 UTC (rev 8436)
@@ -114,6 +114,9 @@
 
     if(pkts[i].chan() == CONTROL_CHAN)
       parse_cs(invocation_handle, pkts[i]);
+    else
+      if(pkts[i].tag() != TAG_INVALID)
+        d_tags.push(pkts[i].tag());
   }
 
   d_cs->send(s_response_usrp_tx_write,





reply via email to

[Prev in Thread] Current Thread [Next in Thread]