aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJosh Blum <josh@joshknows.com>2011-10-11 10:29:33 -0700
committerJosh Blum <josh@joshknows.com>2011-11-03 20:37:12 -0700
commitfce49fd66f577b92482af6ad516944befa31b861 (patch)
tree2c58e9f23facd1b43945981f759ed1b15a5e084d
parent0946176f513dd58407869e3b019207ff3eef24f5 (diff)
downloaduhd-fce49fd66f577b92482af6ad516944befa31b861.tar.gz
uhd-fce49fd66f577b92482af6ad516944befa31b861.tar.bz2
uhd-fce49fd66f577b92482af6ad516944befa31b861.zip
uhd: added one packet mode to rx streamer
-rw-r--r--host/include/uhd/stream.hpp10
-rw-r--r--host/lib/transport/super_recv_packet_handler.hpp14
-rw-r--r--host/lib/transport/super_send_packet_handler.hpp6
-rw-r--r--host/lib/usrp/usrp1/io_impl.cpp18
-rw-r--r--host/tests/sph_recv_test.cpp33
5 files changed, 47 insertions, 34 deletions
diff --git a/host/include/uhd/stream.hpp b/host/include/uhd/stream.hpp
index 7a3151276..c86463184 100644
--- a/host/include/uhd/stream.hpp
+++ b/host/include/uhd/stream.hpp
@@ -123,17 +123,23 @@ public:
* Under a timeout condition, the number of samples returned
* may be less than the number of samples specified.
*
+ * The one_packet option allows the user to guarantee that
+ * the call will return after a single packet has been processed.
+ * This may be useful to maintain packet boundaries in some cases.
+ *
* \param buffs a vector of writable memory to fill with samples
* \param nsamps_per_buff the size of each buffer in number of samples
* \param metadata data to fill describing the buffer
* \param timeout the timeout in seconds to wait for a packet
+ * \param one_packet return after the first packet is received
* \return the number of samples received or 0 on error
*/
virtual size_t recv(
const buffs_type &buffs,
const size_t nsamps_per_buff,
rx_metadata_t &metadata,
- double timeout = 0.1
+ const double timeout = 0.1,
+ const bool one_packet = false
) = 0;
};
@@ -180,7 +186,7 @@ public:
const buffs_type &buffs,
const size_t nsamps_per_buff,
const tx_metadata_t &metadata,
- double timeout = 0.1
+ const double timeout = 0.1
) = 0;
};
diff --git a/host/lib/transport/super_recv_packet_handler.hpp b/host/lib/transport/super_recv_packet_handler.hpp
index 83c8988e8..6762a8a00 100644
--- a/host/lib/transport/super_recv_packet_handler.hpp
+++ b/host/lib/transport/super_recv_packet_handler.hpp
@@ -148,7 +148,8 @@ public:
const uhd::rx_streamer::buffs_type &buffs,
const size_t nsamps_per_buff,
uhd::rx_metadata_t &metadata,
- double timeout
+ const double timeout,
+ const bool one_packet
){
//handle metadata queued from a previous receive
if (_queue_error_for_next_call){
@@ -163,9 +164,7 @@ public:
buffs, nsamps_per_buff, metadata, timeout
);
- #ifdef SRPH_TEST_MODE_ONE_PACKET
- return accum_num_samps;
- #endif
+ if (one_packet) return accum_num_samps;
//first recv had an error code set, return immediately
if (metadata.error_code != rx_metadata_t::ERROR_CODE_NONE) return accum_num_samps;
@@ -493,7 +492,7 @@ private:
const uhd::rx_streamer::buffs_type &buffs,
const size_t nsamps_per_buff,
uhd::rx_metadata_t &metadata,
- double timeout,
+ const double timeout,
const size_t buffer_offset_bytes = 0
){
//get the next buffer if the current one has expired
@@ -571,9 +570,10 @@ public:
const rx_streamer::buffs_type &buffs,
const size_t nsamps_per_buff,
uhd::rx_metadata_t &metadata,
- double timeout
+ const double timeout,
+ const bool one_packet
){
- return recv_packet_handler::recv(buffs, nsamps_per_buff, metadata, timeout);
+ return recv_packet_handler::recv(buffs, nsamps_per_buff, metadata, timeout, one_packet);
}
private:
diff --git a/host/lib/transport/super_send_packet_handler.hpp b/host/lib/transport/super_send_packet_handler.hpp
index 1ac178ad2..5b5ee2981 100644
--- a/host/lib/transport/super_send_packet_handler.hpp
+++ b/host/lib/transport/super_send_packet_handler.hpp
@@ -128,7 +128,7 @@ public:
const uhd::tx_streamer::buffs_type &buffs,
const size_t nsamps_per_buff,
const uhd::tx_metadata_t &metadata,
- double timeout
+ const double timeout
){
//translate the metadata to vrt if packet info
vrt::if_packet_info_t if_packet_info;
@@ -215,7 +215,7 @@ private:
const uhd::tx_streamer::buffs_type &buffs,
const size_t nsamps_per_buff,
vrt::if_packet_info_t &if_packet_info,
- double timeout,
+ const double timeout,
const size_t buffer_offset_bytes = 0
){
//load the rest of the if_packet_info in here
@@ -269,7 +269,7 @@ public:
const tx_streamer::buffs_type &buffs,
const size_t nsamps_per_buff,
const uhd::tx_metadata_t &metadata,
- double timeout
+ const double timeout
){
return send_packet_handler::send(buffs, nsamps_per_buff, metadata, timeout);
}
diff --git a/host/lib/usrp/usrp1/io_impl.cpp b/host/lib/usrp/usrp1/io_impl.cpp
index c199e4178..a0fdfc6bf 100644
--- a/host/lib/usrp/usrp1/io_impl.cpp
+++ b/host/lib/usrp/usrp1/io_impl.cpp
@@ -325,13 +325,14 @@ public:
const rx_streamer::buffs_type &buffs,
const size_t nsamps_per_buff,
uhd::rx_metadata_t &metadata,
- double timeout
+ const double timeout,
+ const bool one_packet
){
//interleave a "soft" inline message into the receive stream:
if (_stc->get_inline_queue().pop_with_haste(metadata)) return 0;
size_t num_samps_recvd = sph::recv_packet_handler::recv(
- buffs, nsamps_per_buff, metadata, timeout
+ buffs, nsamps_per_buff, metadata, timeout, one_packet
);
return _stc->recv_post(metadata, num_samps_recvd);
@@ -366,8 +367,9 @@ public:
const tx_streamer::buffs_type &buffs,
const size_t nsamps_per_buff,
const uhd::tx_metadata_t &metadata,
- double timeout
+ const double timeout_
){
+ double timeout = timeout_; //rw copy
_stc->send_pre(metadata, timeout);
_tx_enb_fcn(true); //always enable (it will do the right thing)
@@ -545,7 +547,10 @@ rx_streamer::sptr usrp1_impl::get_rx_stream(const uhd::stream_args_t &args_){
//setup defaults for unspecified values
args.otw_format = args.otw_format.empty()? "sc16" : args.otw_format;
- args.channels = args.channels.empty()? std::vector<size_t>(1, 0) : args.channels;
+ args.channels.clear(); //NOTE: we have no choice about the channel mapping
+ for (size_t ch = 0; ch < _rx_subdev_spec.size(); ch++){
+ args.channels.push_back(ch);
+ }
if (args.otw_format == "sc16"){
_iface->poke32(FR_RX_FORMAT, 0
@@ -610,7 +615,10 @@ tx_streamer::sptr usrp1_impl::get_tx_stream(const uhd::stream_args_t &args_){
//setup defaults for unspecified values
args.otw_format = args.otw_format.empty()? "sc16" : args.otw_format;
- args.channels = args.channels.empty()? std::vector<size_t>(1, 0) : args.channels;
+ args.channels.clear(); //NOTE: we have no choice about the channel mapping
+ for (size_t ch = 0; ch < _tx_subdev_spec.size(); ch++){
+ args.channels.push_back(ch);
+ }
if (args.otw_format != "sc16"){
throw uhd::value_error("USRP1 TX cannot handle requested wire format: " + args.otw_format);
diff --git a/host/tests/sph_recv_test.cpp b/host/tests/sph_recv_test.cpp
index 3ca123ef2..6fab2ad5f 100644
--- a/host/tests/sph_recv_test.cpp
+++ b/host/tests/sph_recv_test.cpp
@@ -16,7 +16,6 @@
//
#include <boost/test/unit_test.hpp>
-#define SRPH_TEST_MODE_ONE_PACKET
#include "../lib/transport/super_recv_packet_handler.hpp"
#include <boost/shared_array.hpp>
#include <boost/bind.hpp>
@@ -155,7 +154,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_one_channel_normal){
for (size_t i = 0; i < NUM_PKTS_TO_TEST; i++){
std::cout << "data check " << i << std::endl;
size_t num_samps_ret = handler.recv(
- &buff.front(), buff.size(), metadata, 1.0
+ &buff.front(), buff.size(), metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_NONE);
BOOST_CHECK(not metadata.more_fragments);
@@ -169,7 +168,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_one_channel_normal){
for (size_t i = 0; i < 3; i++){
std::cout << "timeout check " << i << std::endl;
handler.recv(
- &buff.front(), buff.size(), metadata, 1.0
+ &buff.front(), buff.size(), metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_TIMEOUT);
}
@@ -228,7 +227,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_one_channel_sequence_error){
for (size_t i = 0; i < NUM_PKTS_TO_TEST; i++){
std::cout << "data check " << i << std::endl;
size_t num_samps_ret = handler.recv(
- &buff.front(), buff.size(), metadata, 1.0
+ &buff.front(), buff.size(), metadata, 1.0, true
);
if (i == NUM_PKTS_TO_TEST/2){
//must get the soft overflow here
@@ -250,7 +249,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_one_channel_sequence_error){
for (size_t i = 0; i < 3; i++){
std::cout << "timeout check " << i << std::endl;
handler.recv(
- &buff.front(), buff.size(), metadata, 1.0
+ &buff.front(), buff.size(), metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_TIMEOUT);
}
@@ -319,7 +318,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_one_channel_inline_message){
for (size_t i = 0; i < NUM_PKTS_TO_TEST; i++){
std::cout << "data check " << i << std::endl;
size_t num_samps_ret = handler.recv(
- &buff.front(), buff.size(), metadata, 1.0
+ &buff.front(), buff.size(), metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_NONE);
BOOST_CHECK(not metadata.more_fragments);
@@ -329,7 +328,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_one_channel_inline_message){
num_accum_samps += num_samps_ret;
if (i == NUM_PKTS_TO_TEST/2){
handler.recv(
- &buff.front(), buff.size(), metadata, 1.0
+ &buff.front(), buff.size(), metadata, 1.0, true
);
std::cout << "metadata.error_code " << metadata.error_code << std::endl;
BOOST_REQUIRE(metadata.error_code == uhd::rx_metadata_t::ERROR_CODE_OVERFLOW);
@@ -342,7 +341,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_one_channel_inline_message){
for (size_t i = 0; i < 3; i++){
std::cout << "timeout check " << i << std::endl;
handler.recv(
- &buff.front(), buff.size(), metadata, 1.0
+ &buff.front(), buff.size(), metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_TIMEOUT);
}
@@ -410,7 +409,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_multi_channel_normal){
for (size_t i = 0; i < NUM_PKTS_TO_TEST; i++){
std::cout << "data check " << i << std::endl;
size_t num_samps_ret = handler.recv(
- buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0
+ buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_NONE);
BOOST_CHECK(not metadata.more_fragments);
@@ -424,7 +423,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_multi_channel_normal){
for (size_t i = 0; i < 3; i++){
std::cout << "timeout check " << i << std::endl;
handler.recv(
- buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0
+ buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_TIMEOUT);
}
@@ -496,7 +495,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_multi_channel_sequence_error){
for (size_t i = 0; i < NUM_PKTS_TO_TEST; i++){
std::cout << "data check " << i << std::endl;
size_t num_samps_ret = handler.recv(
- buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0
+ buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0, true
);
if (i == NUM_PKTS_TO_TEST/2){
//must get the soft overflow here
@@ -518,7 +517,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_multi_channel_sequence_error){
for (size_t i = 0; i < 3; i++){
std::cout << "timeout check " << i << std::endl;
handler.recv(
- buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0
+ buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_TIMEOUT);
}
@@ -589,7 +588,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_multi_channel_time_error){
for (size_t i = 0; i < NUM_PKTS_TO_TEST; i++){
std::cout << "data check " << i << std::endl;
size_t num_samps_ret = handler.recv(
- buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0
+ buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_NONE);
BOOST_CHECK(not metadata.more_fragments);
@@ -606,7 +605,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_multi_channel_time_error){
for (size_t i = 0; i < 3; i++){
std::cout << "timeout check " << i << std::endl;
handler.recv(
- buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0
+ buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_TIMEOUT);
}
@@ -674,7 +673,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_multi_channel_fragment){
for (size_t i = 0; i < NUM_PKTS_TO_TEST; i++){
std::cout << "data check " << i << std::endl;
size_t num_samps_ret = handler.recv(
- buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0
+ buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_NONE);
BOOST_CHECK(metadata.has_time_spec);
@@ -685,7 +684,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_multi_channel_fragment){
if (not metadata.more_fragments) continue;
num_samps_ret = handler.recv(
- buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0
+ buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_NONE);
BOOST_CHECK(not metadata.more_fragments);
@@ -700,7 +699,7 @@ BOOST_AUTO_TEST_CASE(test_sph_recv_multi_channel_fragment){
for (size_t i = 0; i < 3; i++){
std::cout << "timeout check " << i << std::endl;
handler.recv(
- buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0
+ buffs, NUM_SAMPS_PER_BUFF, metadata, 1.0, true
);
BOOST_CHECK_EQUAL(metadata.error_code, uhd::rx_metadata_t::ERROR_CODE_TIMEOUT);
}