[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Commit-gnuradio] [gnuradio] 14/148: Created transport abstraction. Impl
From: |
git |
Subject: |
[Commit-gnuradio] [gnuradio] 14/148: Created transport abstraction. Implemented ethernet transport for control. Control transport works in usrp impl. Needs a lot of cleanup. |
Date: |
Mon, 15 Aug 2016 00:47:20 +0000 (UTC) |
This is an automated email from the git hooks/post-receive script.
nwest pushed a commit to annotated tag old_usrp_devel_udp
in repository gnuradio.
commit c49d96df6a38a31df98b67b2d20d65b4a448869f
Author: Josh Blum <address@hidden>
Date: Tue Nov 3 19:49:57 2009 -0800
Created transport abstraction.
Implemented ethernet transport for control.
Control transport works in usrp impl.
Needs a lot of cleanup.
---
usrp2/host/lib/Makefile.am | 4 +-
usrp2/host/lib/transport.cc | 82 +++++++++++++++++++++++++++++++++++++++++
usrp2/host/lib/transport.h | 79 +++++++++++++++++++++++++++++++++++++++
usrp2/host/lib/usrp2.cc | 88 +++++++++++++++++++++++++++++++++++++++++++-
usrp2/host/lib/usrp2_impl.cc | 33 +++++++++--------
usrp2/host/lib/usrp2_impl.h | 11 ++++--
6 files changed, 275 insertions(+), 22 deletions(-)
diff --git a/usrp2/host/lib/Makefile.am b/usrp2/host/lib/Makefile.am
index 0c3e180..1371ab0 100644
--- a/usrp2/host/lib/Makefile.am
+++ b/usrp2/host/lib/Makefile.am
@@ -1,5 +1,5 @@
#
-# Copyright 2007,2008 Free Software Foundation, Inc.
+# Copyright 2007,2008,2009 Free Software Foundation, Inc.
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
@@ -41,6 +41,7 @@ libusrp2_la_SOURCES = \
open_usrp2_socket.cc \
pktfilter.cc \
ring.cc \
+ transport.cc \
rx_nop_handler.cc \
rx_sample_handler.cc \
strtod_si.c \
@@ -60,5 +61,6 @@ noinst_HEADERS = \
open_usrp2_socket.h \
pktfilter.h \
ring.h \
+ transport.h \
usrp2_bytesex.h \
usrp2_impl.h
diff --git a/usrp2/host/lib/transport.cc b/usrp2/host/lib/transport.cc
new file mode 100644
index 0000000..325e829
--- /dev/null
+++ b/usrp2/host/lib/transport.cc
@@ -0,0 +1,82 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2009 Free Software Foundation, Inc.
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#include "transport.h"
+#include <stdexcept>
+
+static void nop_cb(void *buff, size_t len){
+ //NOP
+}
+
+usrp2::transport::transport(const std::string &type_str){
+ d_cb = nop_cb;
+ d_type_str = type_str;
+ d_running = false;
+}
+
+usrp2::transport::~transport(){
+ if (d_running) stop();
+}
+
+void usrp2::transport::init(){
+ //NOP
+}
+
+void usrp2::transport::start(){
+ if (d_running){
+ throw std::runtime_error("usrp2::transport for" + d_type_str + "
already started\n");
+ }
+ d_thread = new boost::thread(boost::bind(&usrp2::transport::run, this));
+}
+
+void usrp2::transport::stop(){
+ if (not d_running){
+ throw std::runtime_error("usrp2::transport for" + d_type_str + "
already stopped\n");
+ }
+ d_running = false;
+ d_thread->join();
+}
+
+void usrp2::transport::run(){
+ init();
+ d_running = true;
+ void *buff;
+ while (d_running){
+ try{
+ // call recv to get a pointer into memory
+ // pass the buffer into the callback
+ int len = recv(&buff);
+ if (len > 0) d_cb(buff, len);
+ //catch thread interrupts from join, sleep, etc
+ //the running condition will be re-checked
+ }catch(boost::thread_interrupted const &){}
+ }
+}
+
+int usrp2::transport::send(const void *buff, int len){
+ return -1; //NOP
+}
+
+int usrp2::transport::recv(void **buff){
+ *buff = NULL;
+ return -1; //NOP
+}
diff --git a/usrp2/host/lib/transport.h b/usrp2/host/lib/transport.h
new file mode 100644
index 0000000..c6a42f8
--- /dev/null
+++ b/usrp2/host/lib/transport.h
@@ -0,0 +1,79 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2009 Free Software Foundation, Inc.
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef INCLUDED_TRANSPORT_H
+#define INCLUDED_TRANSPORT_H
+
+#include <boost/thread.hpp>
+#include <cstring>
+
+namespace usrp2 {
+
+ class transport {
+ public:
+ typedef boost::function<void(void*, size_t)> callback_t;
+ private:
+ std::string d_type_str;
+ volatile bool d_running;
+ boost::thread *d_thread;
+ callback_t d_cb;
+ void run();
+ public:
+ /*!
+ * \brief create a new transport
+ * The callback takes a void * pointer and a length in bytes.
+ * \param type_str a descriptive string
+ */
+ transport(const std::string &type_str);
+ ~transport();
+ /*!
+ * \brief Set the callback
+ * \param cb the callback created by boost::bind
+ */
+ void set_callback(callback_t cb){d_cb=cb;}
+ /*!
+ * \brief create a new thread for receiving
+ */
+ void start();
+ /*!
+ * \brief stop and join the current thread
+ */
+ void stop();
+ /*!
+ * \brief called from thread on init (override in a subclass)
+ * Purpose: to have a thread initialization hook.
+ */
+ virtual void init();
+ /*!
+ * \brief send the contents of the buffer (override in a subclass)
+ * \param buff a pointer into memory
+ * \param len the length of the buffer in bytes
+ * \return the number of bytes sent, -1 for error
+ */
+ virtual int send(const void *buff, int len);
+ /*!
+ * \brief receive data into the buffer (override in a subclass)
+ * \param buff a pointer to a pointer into memory
+ * \return the number of bytes received, -1 for error
+ */
+ virtual int recv(void **buff);
+ };
+
+} // namespace usrp2
+
+#endif /* INCLUDED_TRANSPORT_H */
diff --git a/usrp2/host/lib/usrp2.cc b/usrp2/host/lib/usrp2.cc
index a2a9ecc..0ed854a 100644
--- a/usrp2/host/lib/usrp2.cc
+++ b/usrp2/host/lib/usrp2.cc
@@ -29,6 +29,91 @@
#include <stdexcept>
#include <cstdio>
+ //FIXME this is the third instance of this function, find it a home
+ static bool
+ parse_mac_addr(const std::string &s, u2_mac_addr_t *p)
+ {
+ p->addr[0] = 0x00; // Matt's IAB
+ p->addr[1] = 0x50;
+ p->addr[2] = 0xC2;
+ p->addr[3] = 0x85;
+ p->addr[4] = 0x30;
+ p->addr[5] = 0x00;
+
+ int len = s.size();
+
+ switch (len){
+
+ case 5:
+ return sscanf(s.c_str(), "%hhx:%hhx", &p->addr[4], &p->addr[5]) == 2;
+
+ case 17:
+ return sscanf(s.c_str(), "%hhx:%hhx:%hhx:%hhx:%hhx:%hhx",
+ &p->addr[0], &p->addr[1], &p->addr[2],
+ &p->addr[3], &p->addr[4], &p->addr[5]) == 6;
+ default:
+ return false;
+ }
+ }
+
+// ----------------------------------------------------------------
+// Ethernet transport classes for data and control
+// ----------------------------------------------------------------
+#include "transport.h"
+#include "ethernet.h"
+#include "pktfilter.h"
+class eth_ctrl_transport: public usrp2::transport{
+ private:
+ uint8_t d_buff[1500]; //FIXME use MTU
+ usrp2::ethernet *d_eth_ctrl; // unbuffered control frames
+ usrp2::pktfilter *d_pf_ctrl;
+
+ public:
+ eth_ctrl_transport(const std::string &ifc, usrp2::props *p) :
usrp2::transport("ethernet control"){
+
+ //create raw ethernet device
+ d_eth_ctrl = new usrp2::ethernet();
+ if (!d_eth_ctrl->open(ifc, htons(U2_CTRL_ETHERTYPE)))
+ throw std::runtime_error("Unable to open/register USRP2 control
protocol");
+
+ //extract mac addr
+ u2_mac_addr_t usrp_mac;
+ parse_mac_addr(p->addr, &usrp_mac);
+
+ //create and attach packet filter
+ d_pf_ctrl =
usrp2::pktfilter::make_ethertype_inbound_target(U2_CTRL_ETHERTYPE, (const
unsigned char*)&(usrp_mac.addr));
+ if (!d_pf_ctrl || !d_eth_ctrl->attach_pktfilter(d_pf_ctrl))
+ throw std::runtime_error("Unable to attach packet filter for control
packets.");
+
+ start(); //start thread now
+ }
+
+ ~eth_ctrl_transport(){
+ delete d_pf_ctrl;
+ d_eth_ctrl->close();
+ delete d_eth_ctrl;
+ }
+
+ int send(const void *buff, int len){
+ return d_eth_ctrl->write_packet(buff, len);
+ }
+
+ int recv(void **buff){
+ int recv_len = d_eth_ctrl->read_packet_dont_block(d_buff, sizeof(d_buff));
+ if (recv_len > 0){
+ *buff = d_buff;
+ return recv_len;
+ }
+ boost::this_thread::sleep(gruel::get_new_timeout(0.05)); //50ms timeout
+ return 0; //nothing yet
+ }
+
+};
+
+
+// ----------------------------------------------------------------
+// The USRP2 class wrapper for impl
+// ----------------------------------------------------------------
namespace usrp2 {
// --- Table of weak pointers to usrps we know about ---
@@ -144,9 +229,8 @@ namespace usrp2 {
// Private constructor. Sole function is to create an impl.
usrp2::usrp2(const std::string &ifc, props *p, size_t rx_bufsize)
- : d_impl(new usrp2::impl(ifc, p, rx_bufsize))
{
- // NOP
+ d_impl = std::auto_ptr<impl>(new usrp2::impl(ifc, p, rx_bufsize, new
eth_ctrl_transport(ifc, p)));
}
// Public class destructor. d_impl will auto-delete.
diff --git a/usrp2/host/lib/usrp2_impl.cc b/usrp2/host/lib/usrp2_impl.cc
index 1caa071..e9bb4b8 100644
--- a/usrp2/host/lib/usrp2_impl.cc
+++ b/usrp2/host/lib/usrp2_impl.cc
@@ -129,7 +129,7 @@ namespace usrp2 {
}
- usrp2::impl::impl(const std::string &ifc, props *p, size_t rx_bufsize)
+ usrp2::impl::impl(const std::string &ifc, props *p, size_t rx_bufsize,
transport *ctrl_transport)
: d_eth_data(new eth_buffer(rx_bufsize)),
d_eth_ctrl(new ethernet()),
d_pf_data(0),
@@ -150,12 +150,15 @@ namespace usrp2 {
d_rx_decim(0),
d_dont_enqueue(true),
d_ctrl_running(false),
- d_data_running(false)
+ d_data_running(false),
+ d_ctrl_transport(ctrl_transport)
{
+
d_ctrl_transport->set_callback(boost::bind(&usrp2::impl::handle_control_packet,
this, _1, _2));
+
if (!d_eth_data->open(ifc, htons(U2_DATA_ETHERTYPE)))
throw std::runtime_error("Unable to open/register USRP2 data protocol");
- if (!d_eth_ctrl->open(ifc, htons(U2_CTRL_ETHERTYPE)))
- throw std::runtime_error("Unable to open/register USRP2 control
protocol");
+ //if (!d_eth_ctrl->open(ifc, htons(U2_CTRL_ETHERTYPE)))
+ // throw std::runtime_error("Unable to open/register USRP2 control
protocol");
d_addr = p->addr;
@@ -165,9 +168,9 @@ namespace usrp2 {
d_pf_data = pktfilter::make_ethertype_inbound_target(U2_DATA_ETHERTYPE,
(const unsigned char*)&(usrp_mac.addr));
if (!d_pf_data || !d_eth_data->attach_pktfilter(d_pf_data))
throw std::runtime_error("Unable to attach packet filter for data
packets.");
- d_pf_ctrl = pktfilter::make_ethertype_inbound_target(U2_CTRL_ETHERTYPE,
(const unsigned char*)&(usrp_mac.addr));
- if (!d_pf_ctrl || !d_eth_ctrl->attach_pktfilter(d_pf_ctrl))
- throw std::runtime_error("Unable to attach packet filter for control
packets.");
+ //d_pf_ctrl = pktfilter::make_ethertype_inbound_target(U2_CTRL_ETHERTYPE,
(const unsigned char*)&(usrp_mac.addr));
+ //if (!d_pf_ctrl || !d_eth_ctrl->attach_pktfilter(d_pf_ctrl))
+ // throw std::runtime_error("Unable to attach packet filter for control
packets.");
if (USRP2_IMPL_DEBUG)
std::cerr << "usrp2 constructor: using USRP2 at " << d_addr << std::endl;
@@ -175,7 +178,7 @@ namespace usrp2 {
memset(d_pending_replies, 0, sizeof(d_pending_replies));
start_data_thread();
- start_ctrl_thread();
+ //start_ctrl_thread();
// In case the USRP2 was left streaming RX
// FIXME: only one channel right now
@@ -231,14 +234,14 @@ namespace usrp2 {
{
//thread cleanup
stop_data_thread();
- stop_ctrl_thread();
+ //stop_ctrl_thread();
//socket cleanup
delete d_pf_data;
- delete d_pf_ctrl;
+ //delete d_pf_ctrl;
d_eth_data->close();
delete d_eth_data;
- d_eth_ctrl->close();
- delete d_eth_ctrl;
+ //d_eth_ctrl->close();
+ //delete d_eth_ctrl;
if (USRP2_IMPL_DEBUG) {
std::cerr << std::endl
@@ -341,7 +344,7 @@ namespace usrp2 {
len = sizeof(tmp);
}
- return d_eth_ctrl->write_packet(cmd, len) >= 0;
+ return d_ctrl_transport->send(cmd, len) >= 0;
}
bool
@@ -363,7 +366,7 @@ namespace usrp2 {
// Background loop for handling control packets
// ----------------------------------------------------------------
- void
+ /*void
usrp2::impl::start_ctrl_thread()
{
d_ctrl_thread = new
boost::thread(boost::bind(&usrp2::impl::run_ctrl_thread, this));
@@ -387,7 +390,7 @@ namespace usrp2 {
if (ctrl_recv_len > 0) handle_control_packet(buff, ctrl_recv_len);
else boost::this_thread::sleep(gruel::get_new_timeout(0.05)); //50ms
timeout
}
- }
+ }*/
// ----------------------------------------------------------------
// Background loop for handling data packets
diff --git a/usrp2/host/lib/usrp2_impl.h b/usrp2/host/lib/usrp2_impl.h
index 594a4bf..50cb78a 100644
--- a/usrp2/host/lib/usrp2_impl.h
+++ b/usrp2/host/lib/usrp2_impl.h
@@ -27,6 +27,7 @@
#include <boost/thread.hpp>
#include "control.h"
#include "ring.h"
+#include "transport.h"
#include <string>
#define MAX_SUBPKT_LEN 252
@@ -120,9 +121,9 @@ namespace usrp2 {
//control thread stuff
volatile bool d_ctrl_running;
boost::thread *d_ctrl_thread;
- void start_ctrl_thread();
- void stop_ctrl_thread();
- void run_ctrl_thread();
+ //void start_ctrl_thread();
+ //void stop_ctrl_thread();
+ //void run_ctrl_thread();
//data thread stuff
volatile bool d_data_running; // TODO: multistate if needed
@@ -131,8 +132,10 @@ namespace usrp2 {
void stop_data_thread();
void run_data_thread();
+ transport *d_ctrl_transport;
+
public:
- impl(const std::string &ifc, props *p, size_t rx_bufsize);
+ impl(const std::string &ifc, props *p, size_t rx_bufsize, transport
*ctrl_transport);
~impl();
std::string mac_addr() const { return d_addr; } // FIXME: convert from
u2_mac_addr_t
- [Commit-gnuradio] [gnuradio] 03/148: Created a new thread for handling incoming control packets. TX/RX app is working with separate data and control ethernet types., (continued)
- [Commit-gnuradio] [gnuradio] 03/148: Created a new thread for handling incoming control packets. TX/RX app is working with separate data and control ethernet types., git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 10/148: Fix incorrect comparison, git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 13/148: usrp2: remove install data hook for usrp2_socket_opener, git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 04/148: Hosekeeping after control/data separation., git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 05/148: Removed references to U2_ETHERTYPE and CONTROL_CHAN. Moved non-txrx-related apps in firmware broken by this., git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 06/148: Common naming convention for control and data thread stuff., git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 02/148: working a separate ctrl ethernet device into the code, git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 07/148: using boost threads for control and data, git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 09/148: Refactored timeout handling, git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 17/148: Began work on eth data transport class. Switched send in transport to use iovecs. Pass mac addr into eth transports rather than re-parsing., git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 14/148: Created transport abstraction. Implemented ethernet transport for control. Control transport works in usrp impl. Needs a lot of cleanup.,
git <=
- [Commit-gnuradio] [gnuradio] 08/148: Removed omnithreads dependency from libusrp2, still debugging, git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 18/148: Added a callback into the channel ring enqueue and dequeue. This will allow the deqeue caller to make an arbitrary call when its done with the data. Currently, the enqueue caller makes this callback a release_frames., git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 15/148: virtual destructor and shared ptr for transport, git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 28/148: Cleaned up the parse ethernet stuff. Made an official max_buffs method for the transport., git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 20/148: Created sbuff class to house chunks of memory, their length, and possible callback for freeing/cleanup. Switched ring and transport to make use of the sbuff on receive., git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 37/148: Fixes usrp2 firmware configure with mb-gcc on ubuntu 9.10/autoconf 2.64. Disables the regression test for fopen since stdio is non-functional., git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 22/148: usrp2 impl working with data transport. not up to full potential yet, but working. needs major cleanup., git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 23/148: Changed the transport to return a vector of sbuffs. This way the ethernet can pass up as many buffs as ready., git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 11/148: some house keeping while trying to fix thread exception, git, 2016/08/14
- [Commit-gnuradio] [gnuradio] 12/148: Disable interruption in those functions that use interruption points such as sleep, wait, and timed_wait., git, 2016/08/14