Flattened the usrp2 impl properties guts.

Created init methods for various sub-parts.
Added the ddc control (still needs update transaction).
This commit is contained in:
Josh Blum 2010-02-18 15:30:34 -08:00
parent f439fe8218
commit b4e5df4080
11 changed files with 464 additions and 268 deletions

View file

@ -16,7 +16,7 @@
#
ADD_LIBRARY(uhd SHARED
SET(libuhd_sources
device.cpp
device_addr.cpp
gain_handler.cpp
@ -32,11 +32,15 @@ ADD_LIBRARY(uhd SHARED
usrp/dboard/manager.cpp
usrp/mboard/base.cpp
usrp/mboard/usrp2.cpp
usrp/mboard/usrp2/impl_base.cpp
usrp/mboard/usrp2/dboard_impl.cpp
usrp/mboard/usrp2/dboard_interface.cpp
usrp/mboard/usrp2/dsp_impl.cpp
usrp/mboard/usrp2/mboard_impl.cpp
usrp/mboard/usrp2/usrp2_impl.cpp
)
ADD_LIBRARY(uhd SHARED ${libuhd_sources})
TARGET_LINK_LIBRARIES(uhd ${Boost_LIBRARIES})
INSTALL(TARGETS uhd LIBRARY DESTINATION ${LIBRARY_DIR})

View file

@ -22,7 +22,7 @@
#include <boost/format.hpp>
#include <boost/thread.hpp>
#include <netinet/in.h>
#include "usrp2/impl_base.hpp"
#include "usrp2/usrp2_impl.hpp"
using namespace uhd::usrp::mboard;
@ -92,8 +92,8 @@ usrp2::usrp2(const device_addr_t &device_addr){
);
//create the usrp2 implementation guts
_impl = impl_base::sptr(
new impl_base(ctrl_transport, data_transport)
_impl = usrp2_impl::sptr(
new usrp2_impl(ctrl_transport, data_transport)
);
}
@ -105,12 +105,12 @@ usrp2::~usrp2(void){
* Get Properties
**********************************************************************/
void usrp2::get(const wax::obj &key, wax::obj &val){
return wax::cast<impl_base::sptr>(_impl)->get(key, val);
return wax::cast<usrp2_impl::sptr>(_impl)->get(key, val);
}
/***********************************************************************
* Set Properties
**********************************************************************/
void usrp2::set(const wax::obj &key, const wax::obj &val){
return wax::cast<impl_base::sptr>(_impl)->set(key, val);
return wax::cast<usrp2_impl::sptr>(_impl)->set(key, val);
}

View file

@ -15,62 +15,110 @@
// along with this program. If not, see <http://www.gnu.org/licenses/>.
//
#include <boost/format.hpp>
#include <uhd/utils.hpp>
#include <uhd/props.hpp>
#include <iostream>
#include "dboard_impl.hpp"
#include "usrp2_impl.hpp"
#include "dboard_interface.hpp"
using namespace uhd;
using namespace uhd::usrp;
dboard_impl::dboard_impl(uhd::usrp::dboard::manager::sptr mgr, type_t type){
_mgr = mgr;
_type = type;
/***********************************************************************
* Helper Methods
**********************************************************************/
void usrp2_impl::dboard_init(void){
//grab the dboard ids over the control line
usrp2_ctrl_data_t out_data;
out_data.id = htonl(USRP2_CTRL_ID_GIVE_ME_YOUR_DBOARD_IDS_BRO);
usrp2_ctrl_data_t in_data = ctrl_send_and_recv(out_data);
ASSERT_THROW(htonl(in_data.id) == USRP2_CTRL_ID_THESE_ARE_MY_DBOARD_IDS_DUDE);
std::cout << boost::format("rx id 0x%.2x, tx id 0x%.2x")
% ntohs(in_data.data.dboard_ids.rx_id)
% ntohs(in_data.data.dboard_ids.tx_id) << std::endl;
//extract the dboard ids an convert them to enums
dboard::dboard_id_t rx_dboard_id = static_cast<dboard::dboard_id_t>(
ntohs(in_data.data.dboard_ids.rx_id)
);
dboard::dboard_id_t tx_dboard_id = static_cast<dboard::dboard_id_t>(
ntohs(in_data.data.dboard_ids.tx_id)
);
//create a new dboard interface and manager
dboard::interface::sptr _dboard_interface(
new dboard_interface(this)
);
dboard::manager::sptr _dboard_manager(
new dboard::manager(rx_dboard_id, tx_dboard_id, _dboard_interface)
);
//load dboards
_rx_dboards[""] = wax_obj_proxy(
boost::bind(&usrp2_impl::rx_dboard_get, this, _1, _2),
boost::bind(&usrp2_impl::rx_dboard_set, this, _1, _2)
);
_tx_dboards[""] = wax_obj_proxy(
boost::bind(&usrp2_impl::tx_dboard_get, this, _1, _2),
boost::bind(&usrp2_impl::tx_dboard_set, this, _1, _2)
);
}
dboard_impl::~dboard_impl(void){
/* NOP */
}
void dboard_impl::get(const wax::obj &key_, wax::obj &val){
/***********************************************************************
* RX DBoard Properties
**********************************************************************/
void usrp2_impl::rx_dboard_get(const wax::obj &key_, wax::obj &val){
wax::obj key; std::string name;
boost::tie(key, name) = extract_named_prop(key_);
//handle the get request conditioned on the key
switch(wax::cast<dboard_prop_t>(key)){
case DBOARD_PROP_NAME:
val = std::string("usrp2 dboard");
val = std::string("usrp2 dboard (rx unit)");
return;
case DBOARD_PROP_SUBDEV:
switch(_type){
case TYPE_RX:
val = _mgr->get_rx_subdev(name);
return;
case TYPE_TX:
val = _mgr->get_tx_subdev(name);
return;
}
val = _dboard_manager->get_rx_subdev(name);
return;
case DBOARD_PROP_SUBDEV_NAMES:
switch(_type){
case TYPE_RX:
val = _mgr->get_rx_subdev_names();
return;
case TYPE_TX:
val = _mgr->get_tx_subdev_names();
return;
}
val = _dboard_manager->get_rx_subdev_names();
return;
case DBOARD_PROP_CODEC:
throw std::runtime_error("unhandled prop in usrp2 dboard");
}
}
void dboard_impl::set(const wax::obj &, const wax::obj &){
void usrp2_impl::rx_dboard_set(const wax::obj &, const wax::obj &){
throw std::runtime_error("Cannot set on usrp2 dboard");
}
/***********************************************************************
* TX DBoard Properties
**********************************************************************/
void usrp2_impl::tx_dboard_get(const wax::obj &key_, wax::obj &val){
wax::obj key; std::string name;
boost::tie(key, name) = extract_named_prop(key_);
//handle the get request conditioned on the key
switch(wax::cast<dboard_prop_t>(key)){
case DBOARD_PROP_NAME:
val = std::string("usrp2 dboard (tx unit)");
return;
case DBOARD_PROP_SUBDEV:
val = _dboard_manager->get_tx_subdev(name);
return;
case DBOARD_PROP_SUBDEV_NAMES:
val = _dboard_manager->get_tx_subdev_names();
return;
case DBOARD_PROP_CODEC:
throw std::runtime_error("unhandled prop in usrp2 dboard");
}
}
void usrp2_impl::tx_dboard_set(const wax::obj &, const wax::obj &){
throw std::runtime_error("Cannot set on usrp2 dboard");
}

View file

@ -1,50 +0,0 @@
//
// Copyright 2010 Ettus Research LLC
//
// 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/>.
//
#include <uhd/usrp/dboard/manager.hpp>
#include <boost/utility.hpp>
#include <boost/shared_ptr.hpp>
#include "fw_common.h"
#ifndef INCLUDED_DBOARD_IMPL_HPP
#define INCLUDED_DBOARD_IMPL_HPP
/*!
* The usrp2 dboard implementation:
* Provide the properties access for a dboard.
* Internally, hold a dboard manager and the direction.
* The usrp2 mboard base implementation will create
* two of these classes (one for rx and one for tx).
*/
class dboard_impl : boost::noncopyable, public wax::obj{
public:
typedef boost::shared_ptr<dboard_impl> sptr;
enum type_t {TYPE_RX, TYPE_TX};
dboard_impl(uhd::usrp::dboard::manager::sptr manager, type_t type);
~dboard_impl(void);
void get(const wax::obj &, wax::obj &);
void set(const wax::obj &, const wax::obj &);
private:
uhd::usrp::dboard::manager::sptr _mgr;
type_t _type;
};
#endif /* INCLUDED_DBOARD_IMPL_HPP */

View file

@ -17,14 +17,14 @@
#include <uhd/utils.hpp>
#include "dboard_interface.hpp"
#include "fw_common.h"
#include "usrp2_impl.hpp"
using namespace uhd::usrp::dboard;
/***********************************************************************
* Structors
**********************************************************************/
dboard_interface::dboard_interface(impl_base *impl){
dboard_interface::dboard_interface(usrp2_impl *impl){
_impl = impl;
}

View file

@ -16,14 +16,15 @@
//
#include <uhd/usrp/dboard/interface.hpp>
#include "impl_base.hpp"
#ifndef INCLUDED_DBOARD_INTERFACE_HPP
#define INCLUDED_DBOARD_INTERFACE_HPP
class usrp2_impl; //dummy class declaration
class dboard_interface : public uhd::usrp::dboard::interface{
public:
dboard_interface(impl_base *impl);
dboard_interface(usrp2_impl *impl);
~dboard_interface(void);
@ -56,7 +57,7 @@ private:
bool readback
);
impl_base *_impl;
usrp2_impl *_impl;
};
#endif /* INCLUDED_DBOARD_INTERFACE_HPP */

View file

@ -0,0 +1,111 @@
//
// Copyright 2010 Ettus Research LLC
//
// 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/>.
//
#include <uhd/utils.hpp>
#include <uhd/props.hpp>
#include <boost/assign/list_of.hpp>
#include "usrp2_impl.hpp"
using namespace uhd;
/***********************************************************************
* Helper Methods
**********************************************************************/
void usrp2_impl::ddc_init(size_t which){
//create the ddc in the rx dsp dict
_rx_dsps[str(boost::format("ddc%d") % which)] = wax_obj_proxy(
boost::bind(&usrp2_impl::ddc_get, this, _1, _2, which),
boost::bind(&usrp2_impl::ddc_set, this, _1, _2, which)
);
//initial config and update
_ddc_decim[which] = 16;
_ddc_freq[which] = 0;
update_ddc_config(which);
}
void usrp2_impl::update_ddc_config(size_t){
//TODO
}
/***********************************************************************
* DDC Properties
**********************************************************************/
void usrp2_impl::ddc_get(const wax::obj &key, wax::obj &val, size_t which){
//handle the case where the key is an expected dsp property
if (key.type() == typeid(dsp_prop_t)){
switch(wax::cast<dsp_prop_t>(key)){
case DSP_PROP_NAME:
val = str(boost::format("usrp2 ddc%d") % which);
return;
case DSP_PROP_OTHERS:{
prop_names_t others = boost::assign::list_of
("rate")
("decim")
("freq")
;
val = others;
}
return;
}
}
//handle string-based properties specific to this dsp
std::string key_name = wax::cast<std::string>(key);
if (key_name == "rate"){
val = get_master_clock_freq();
return;
}
if (key_name == "decim"){
val = _ddc_decim[which];
return;
}
if (key_name == "freq"){
val = _ddc_freq[which];
return;
}
throw std::invalid_argument(str(
boost::format("error getting: unknown key with name %s") % key_name
));
}
void usrp2_impl::ddc_set(const wax::obj &key, const wax::obj &val, size_t which){
//handle string-based properties specific to this dsp
std::string key_name = wax::cast<std::string>(key);
if (key_name == "decim"){
size_t new_decim = wax::cast<size_t>(val);
_ddc_decim[which] = new_decim; //shadow
update_ddc_config(which);
return;
}
if (key_name == "freq"){
freq_t new_freq = wax::cast<freq_t>(val);
_ddc_freq[which] = new_freq; //shadow
update_ddc_config(which);
return;
}
throw std::invalid_argument(str(
boost::format("error setting: unknown key with name %s") % key_name
));
}
/***********************************************************************
* DUC Properties
**********************************************************************/

View file

@ -1,78 +0,0 @@
//
// Copyright 2010 Ettus Research LLC
//
// 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/>.
//
#include <boost/utility.hpp>
#include <boost/thread.hpp>
#include <boost/shared_ptr.hpp>
#include <uhd/transport/udp.hpp>
#include <uhd/dict.hpp>
#include "dboard_impl.hpp"
#include "fw_common.h"
#ifndef INCLUDED_IMPL_BASE_HPP
#define INCLUDED_IMPL_BASE_HPP
class impl_base : boost::noncopyable, public wax::obj{
public:
typedef boost::shared_ptr<impl_base> sptr;
/*!
* Create a new usrp2 impl base.
* \param ctrl_transport the udp transport for control
* \param data_transport the udp transport for data
*/
impl_base(
uhd::transport::udp::sptr ctrl_transport,
uhd::transport::udp::sptr data_transport
);
~impl_base(void);
//performs a control transaction
usrp2_ctrl_data_t ctrl_send_and_recv(const usrp2_ctrl_data_t &);
//properties access methods
void get(const wax::obj &, wax::obj &);
void set(const wax::obj &, const wax::obj &);
//misc access methods
double get_master_clock_freq(void);
void update_clock_config(void);
private:
//udp transports for control and data
uhd::transport::udp::sptr _ctrl_transport;
uhd::transport::udp::sptr _data_transport;
//private vars for dealing with send/recv control
uint32_t _ctrl_seq_num;
boost::mutex _ctrl_mutex;
//containers for the dboard objects
uhd::dict<std::string, dboard_impl::sptr> _rx_dboards;
uhd::dict<std::string, dboard_impl::sptr> _tx_dboards;
//shadows for various settings
std::string _pps_source, _pps_polarity, _ref_source;
//mappings from clock config strings to over the wire enums
uhd::dict<std::string, usrp2_pps_source_t> _pps_source_dict;
uhd::dict<std::string, usrp2_pps_polarity_t> _pps_polarity_dict;
uhd::dict<std::string, usrp2_ref_source_t> _ref_source_dict;
};
#endif /* INCLUDED_IMPL_BASE_HPP */

View file

@ -15,57 +15,16 @@
// along with this program. If not, see <http://www.gnu.org/licenses/>.
//
#include <boost/format.hpp>
#include <uhd/utils.hpp>
#include <uhd/props.hpp>
#include <iostream>
#include "impl_base.hpp"
#include "dboard_interface.hpp"
#include "usrp2_impl.hpp"
using namespace uhd;
using namespace uhd::usrp;
/***********************************************************************
* Structors
* Helper Methods
**********************************************************************/
impl_base::impl_base(
uhd::transport::udp::sptr ctrl_transport,
uhd::transport::udp::sptr data_transport
){
_ctrl_transport = ctrl_transport;
_data_transport = data_transport;
//grab the dboard ids over the control line
usrp2_ctrl_data_t out_data;
out_data.id = htonl(USRP2_CTRL_ID_GIVE_ME_YOUR_DBOARD_IDS_BRO);
usrp2_ctrl_data_t in_data = ctrl_send_and_recv(out_data);
ASSERT_THROW(htonl(in_data.id) == USRP2_CTRL_ID_THESE_ARE_MY_DBOARD_IDS_DUDE);
std::cout << boost::format("rx id 0x%.2x, tx id 0x%.2x")
% ntohs(in_data.data.dboard_ids.rx_id)
% ntohs(in_data.data.dboard_ids.tx_id) << std::endl;
//extract the dboard ids an convert them to enums
dboard::dboard_id_t rx_dboard_id = static_cast<dboard::dboard_id_t>(
ntohs(in_data.data.dboard_ids.rx_id)
);
dboard::dboard_id_t tx_dboard_id = static_cast<dboard::dboard_id_t>(
ntohs(in_data.data.dboard_ids.tx_id)
);
//create a new dboard interface and manager
dboard::interface::sptr _dboard_interface(
new dboard_interface(this)
);
dboard::manager::sptr dboard_manager(
new dboard::manager(rx_dboard_id, tx_dboard_id, _dboard_interface)
);
//load dboards
_rx_dboards[""] = dboard_impl::sptr(new dboard_impl(dboard_manager, dboard_impl::TYPE_RX));
_tx_dboards[""] = dboard_impl::sptr(new dboard_impl(dboard_manager, dboard_impl::TYPE_TX));
//TOD load dsps
void usrp2_impl::init_clock_config(void){
//init the pps source clock config
_pps_source_dict["sma"] = USRP2_PPS_SOURCE_SMA;
_pps_source_dict["mimo"] = USRP2_PPS_SOURCE_MIMO;
@ -86,18 +45,7 @@ impl_base::impl_base(
update_clock_config();
}
impl_base::~impl_base(void){
/* NOP */
}
/***********************************************************************
* Misc Access Methods
**********************************************************************/
double impl_base::get_master_clock_freq(void){
return 100e6;
}
void impl_base::update_clock_config(void){
void usrp2_impl::update_clock_config(void){
//setup the out data
usrp2_ctrl_data_t out_data;
out_data.id = htonl(USRP2_CTRL_ID_HERES_A_NEW_CLOCK_CONFIG_BRO);
@ -111,40 +59,9 @@ void impl_base::update_clock_config(void){
}
/***********************************************************************
* Control Send/Recv
* MBoard Get Properties
**********************************************************************/
usrp2_ctrl_data_t impl_base::ctrl_send_and_recv(const usrp2_ctrl_data_t &out_data){
boost::mutex::scoped_lock lock(_ctrl_mutex);
//fill in the seq number and send
usrp2_ctrl_data_t out_copy = out_data;
out_copy.seq = htonl(++_ctrl_seq_num);
_ctrl_transport->send(boost::asio::buffer(&out_copy, sizeof(usrp2_ctrl_data_t)));
//loop and recieve until the time is up
size_t num_timeouts = 0;
while(true){
uhd::shared_iovec iov = _ctrl_transport->recv();
if (iov.len < sizeof(usrp2_ctrl_data_t)){
//sleep a little so we dont burn cpu
if (num_timeouts++ > 50) break;
boost::this_thread::sleep(boost::posix_time::milliseconds(1));
}else{
//handle the received data
usrp2_ctrl_data_t in_data = *reinterpret_cast<const usrp2_ctrl_data_t *>(iov.base);
if (ntohl(in_data.seq) == _ctrl_seq_num){
return in_data;
}
//didnt get seq, continue on...
}
}
throw std::runtime_error("usrp2 no control response");
}
/***********************************************************************
* Get Properties
**********************************************************************/
void impl_base::get(const wax::obj &key_, wax::obj &val){
void usrp2_impl::get(const wax::obj &key_, wax::obj &val){
wax::obj key; std::string name;
boost::tie(key, name) = extract_named_prop(key_);
@ -159,7 +76,7 @@ void impl_base::get(const wax::obj &key_, wax::obj &val){
return;
case MBOARD_PROP_RX_DBOARD:
val = _rx_dboards[name]->get_link();
val = _rx_dboards[name].get_link();
return;
case MBOARD_PROP_RX_DBOARD_NAMES:
@ -167,7 +84,7 @@ void impl_base::get(const wax::obj &key_, wax::obj &val){
return;
case MBOARD_PROP_TX_DBOARD:
val = _tx_dboards[name]->get_link();
val = _tx_dboards[name].get_link();
return;
case MBOARD_PROP_TX_DBOARD_NAMES:
@ -185,16 +102,20 @@ void impl_base::get(const wax::obj &key_, wax::obj &val){
return;
case MBOARD_PROP_RX_DSP:
throw std::runtime_error("unhandled prop in usrp2 mboard");
val = _rx_dsps[name].get_link();
return;
case MBOARD_PROP_RX_DSP_NAMES:
throw std::runtime_error("unhandled prop in usrp2 mboard");
val = prop_names_t(_rx_dsps.get_keys());
return;
case MBOARD_PROP_TX_DSP:
throw std::runtime_error("unhandled prop in usrp2 mboard");
val = _tx_dsps[name].get_link();
return;
case MBOARD_PROP_TX_DSP_NAMES:
throw std::runtime_error("unhandled prop in usrp2 mboard");
val = prop_names_t(_tx_dsps.get_keys());
return;
case MBOARD_PROP_PPS_SOURCE:
val = _pps_source;
@ -224,9 +145,9 @@ void impl_base::get(const wax::obj &key_, wax::obj &val){
}
/***********************************************************************
* Set Properties
* MBoard Set Properties
**********************************************************************/
void impl_base::set(const wax::obj &key, const wax::obj &val){
void usrp2_impl::set(const wax::obj &key, const wax::obj &val){
//handle the get request conditioned on the key
switch(wax::cast<mboard_prop_t>(key)){

View file

@ -0,0 +1,90 @@
//
// Copyright 2010 Ettus Research LLC
//
// 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/>.
//
#include <uhd/usrp/dboard/manager.hpp>
#include <boost/format.hpp>
#include <boost/bind.hpp>
#include <uhd/utils.hpp>
#include <uhd/props.hpp>
#include <iostream>
#include "usrp2_impl.hpp"
using namespace uhd;
/***********************************************************************
* Structors
**********************************************************************/
usrp2_impl::usrp2_impl(
uhd::transport::udp::sptr ctrl_transport,
uhd::transport::udp::sptr data_transport
){
_ctrl_transport = ctrl_transport;
_data_transport = data_transport;
//init the tx and rx dboards
dboard_init();
//init the ddcs (however many we have)
for (size_t i = 0; i < _num_ddc; i++){
ddc_init(i);
}
//initialize the clock configuration
init_clock_config();
}
usrp2_impl::~usrp2_impl(void){
/* NOP */
}
/***********************************************************************
* Misc Access Methods
**********************************************************************/
double usrp2_impl::get_master_clock_freq(void){
return 100e6;
}
/***********************************************************************
* Control Send/Recv
**********************************************************************/
usrp2_ctrl_data_t usrp2_impl::ctrl_send_and_recv(const usrp2_ctrl_data_t &out_data){
boost::mutex::scoped_lock lock(_ctrl_mutex);
//fill in the seq number and send
usrp2_ctrl_data_t out_copy = out_data;
out_copy.seq = htonl(++_ctrl_seq_num);
_ctrl_transport->send(boost::asio::buffer(&out_copy, sizeof(usrp2_ctrl_data_t)));
//loop and recieve until the time is up
size_t num_timeouts = 0;
while(true){
uhd::shared_iovec iov = _ctrl_transport->recv();
if (iov.len < sizeof(usrp2_ctrl_data_t)){
//sleep a little so we dont burn cpu
if (num_timeouts++ > 50) break;
boost::this_thread::sleep(boost::posix_time::milliseconds(1));
}else{
//handle the received data
usrp2_ctrl_data_t in_data = *reinterpret_cast<const usrp2_ctrl_data_t *>(iov.base);
if (ntohl(in_data.seq) == _ctrl_seq_num){
return in_data;
}
//didnt get seq, continue on...
}
}
throw std::runtime_error("usrp2 no control response");
}

View file

@ -0,0 +1,149 @@
//
// Copyright 2010 Ettus Research LLC
//
// 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/>.
//
#include <uhd/dict.hpp>
#include <boost/thread.hpp>
#include <boost/shared_ptr.hpp>
#include <boost/function.hpp>
#include <uhd/transport/udp.hpp>
#include <uhd/usrp/dboard/manager.hpp>
#include "fw_common.h"
#ifndef INCLUDED_USRP2_IMPL_HPP
#define INCLUDED_USRP2_IMPL_HPP
/*!
* Simple wax obj proxy class:
* Provides a wax obj interface for a set and a get function.
* This allows us to create nested properties structures
* while maintaining flattened code within the implementation.
*/
class wax_obj_proxy : public wax::obj{
public:
typedef boost::function<void(const wax::obj &, wax::obj &)> get_t;
typedef boost::function<void(const wax::obj &, const wax::obj &)> set_t;
wax_obj_proxy(void){
/* NOP */
}
wax_obj_proxy(const get_t &get, const set_t &set){
_get = get;
_set = set;
};
~wax_obj_proxy(void){
/* NOP */
}
void get(const wax::obj &key, wax::obj &val){
return _get(key, val);
}
void set(const wax::obj &key, const wax::obj &val){
return _set(key, val);
}
private:
get_t _get;
set_t _set;
};
/*!
* USRP2 implementation guts:
* The implementation details are encapsulated here.
* Handles properties on the mboard, dboard, dsps...
*/
class usrp2_impl : boost::noncopyable, public wax::obj{
public:
typedef boost::shared_ptr<usrp2_impl> sptr;
/*!
* Create a new usrp2 impl base.
* \param ctrl_transport the udp transport for control
* \param data_transport the udp transport for data
*/
usrp2_impl(
uhd::transport::udp::sptr ctrl_transport,
uhd::transport::udp::sptr data_transport
);
~usrp2_impl(void);
//properties interface
void get(const wax::obj &, wax::obj &);
void set(const wax::obj &, const wax::obj &);
//performs a control transaction
usrp2_ctrl_data_t ctrl_send_and_recv(const usrp2_ctrl_data_t &);
//misc access methods
double get_master_clock_freq(void);
private:
//udp transports for control and data
uhd::transport::udp::sptr _ctrl_transport;
uhd::transport::udp::sptr _data_transport;
//private vars for dealing with send/recv control
uint32_t _ctrl_seq_num;
boost::mutex _ctrl_mutex;
//methods and shadows for clock configuration
std::string _pps_source, _pps_polarity, _ref_source;
void init_clock_config(void);
void update_clock_config(void);
//mappings from clock config strings to over the wire enums
uhd::dict<std::string, usrp2_pps_source_t> _pps_source_dict;
uhd::dict<std::string, usrp2_pps_polarity_t> _pps_polarity_dict;
uhd::dict<std::string, usrp2_ref_source_t> _ref_source_dict;
//rx and tx dboard methods and objects
uhd::usrp::dboard::manager::sptr _dboard_manager;
void dboard_init(void);
//properties interface for rx dboard
void rx_dboard_get(const wax::obj &, wax::obj &);
void rx_dboard_set(const wax::obj &, const wax::obj &);
uhd::dict<std::string, wax_obj_proxy> _rx_dboards;
//properties interface for tx dboard
void tx_dboard_get(const wax::obj &, wax::obj &);
void tx_dboard_set(const wax::obj &, const wax::obj &);
uhd::dict<std::string, wax_obj_proxy> _tx_dboards;
//methods and shadows for the ddc dsp
static const size_t _num_ddc = 1;
size_t _ddc_decim[_num_ddc];
double _ddc_freq[_num_ddc];
void ddc_init(size_t which);
void update_ddc_config(size_t which_ddc);
//properties interface for ddc
void ddc_get(const wax::obj &, wax::obj &, size_t which);
void ddc_set(const wax::obj &, const wax::obj &, size_t which);
uhd::dict<std::string, wax_obj_proxy> _rx_dsps;
//properties interface for duc
void duc_get(const wax::obj &, wax::obj &);
void duc_set(const wax::obj &, const wax::obj &);
uhd::dict<std::string, wax_obj_proxy> _tx_dsps;
};
#endif /* INCLUDED_USRP2_IMPL_HPP */