root / host / examples / test_messages.cpp @ 0368a459
History | View | Annotate | Download (11.3 KB)
| 1 | b7e3450a | Josh Blum | //
|
|---|---|---|---|
| 2 | fb7e8a09 | Josh Blum | // Copyright 2010-2011 Ettus Research LLC
|
| 3 | b7e3450a | Josh Blum | //
|
| 4 | // This program is free software: you can redistribute it and/or modify
|
||
| 5 | // it under the terms of the GNU General Public License as published by
|
||
| 6 | // the Free Software Foundation, either version 3 of the License, or
|
||
| 7 | // (at your option) any later version.
|
||
| 8 | //
|
||
| 9 | // This program is distributed in the hope that it will be useful,
|
||
| 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||
| 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||
| 12 | // GNU General Public License for more details.
|
||
| 13 | //
|
||
| 14 | // You should have received a copy of the GNU General Public License
|
||
| 15 | // along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||
| 16 | //
|
||
| 17 | |||
| 18 | #include <uhd/utils/thread_priority.hpp> |
||
| 19 | #include <uhd/utils/safe_main.hpp> |
||
| 20 | #include <uhd/utils/static.hpp> |
||
| 21 | 34265334 | Josh Blum | #include <uhd/types/stream_cmd.hpp> |
| 22 | 67bba008 | Josh Blum | #include <uhd/usrp/multi_usrp.hpp> |
| 23 | 4dfb7b8c | Josh Blum | #include <boost/assign/list_of.hpp> |
| 24 | b7e3450a | Josh Blum | #include <boost/program_options.hpp> |
| 25 | 4dfb7b8c | Josh Blum | #include <boost/foreach.hpp> |
| 26 | #include <boost/bind.hpp> |
||
| 27 | b7e3450a | Josh Blum | #include <boost/format.hpp> |
| 28 | 4dfb7b8c | Josh Blum | #include <cstdlib> |
| 29 | 11510003 | Josh Blum | #include <ctime> |
| 30 | b7e3450a | Josh Blum | #include <complex> |
| 31 | #include <iostream> |
||
| 32 | |||
| 33 | namespace po = boost::program_options;
|
||
| 34 | |||
| 35 | /*!
|
||
| 36 | 34265334 | Josh Blum | * Test the late command message:
|
| 37 | * Issue a stream command with a time that is in the past.
|
||
| 38 | * We expect to get an inline late command message.
|
||
| 39 | */
|
||
| 40 | a629bbe7 | Josh Blum | bool test_late_command_message(uhd::usrp::multi_usrp::sptr usrp, uhd::rx_streamer::sptr rx_stream, uhd::tx_streamer::sptr){
|
| 41 | 34265334 | Josh Blum | std::cout << "Test late command message... " << std::flush;
|
| 42 | |||
| 43 | usrp->set_time_now(uhd::time_spec_t(200.0)); //set time |
||
| 44 | |||
| 45 | uhd::stream_cmd_t stream_cmd(uhd::stream_cmd_t::STREAM_MODE_NUM_SAMPS_AND_DONE); |
||
| 46 | a629bbe7 | Josh Blum | stream_cmd.num_samps = rx_stream->get_max_num_samps(); |
| 47 | 34265334 | Josh Blum | stream_cmd.stream_now = false;
|
| 48 | stream_cmd.time_spec = uhd::time_spec_t(100.0); //time in the past |
||
| 49 | usrp->issue_stream_cmd(stream_cmd); |
||
| 50 | |||
| 51 | a629bbe7 | Josh Blum | std::vector<std::complex<float> > buff(rx_stream->get_max_num_samps());
|
| 52 | 34265334 | Josh Blum | uhd::rx_metadata_t md; |
| 53 | |||
| 54 | a629bbe7 | Josh Blum | const size_t nsamps = rx_stream->recv(
|
| 55 | &buff.front(), buff.size(), md |
||
| 56 | 34265334 | Josh Blum | ); |
| 57 | |||
| 58 | switch(md.error_code){
|
||
| 59 | case uhd::rx_metadata_t::ERROR_CODE_LATE_COMMAND:
|
||
| 60 | std::cout << boost::format( |
||
| 61 | "success:\n"
|
||
| 62 | " Got error code late command message.\n"
|
||
| 63 | ) << std::endl; |
||
| 64 | return true; |
||
| 65 | |||
| 66 | case uhd::rx_metadata_t::ERROR_CODE_TIMEOUT:
|
||
| 67 | std::cout << boost::format( |
||
| 68 | "failed:\n"
|
||
| 69 | " Inline message recv timed out.\n"
|
||
| 70 | ) << std::endl; |
||
| 71 | return false; |
||
| 72 | |||
| 73 | default:
|
||
| 74 | std::cout << boost::format( |
||
| 75 | "failed:\n"
|
||
| 76 | " Got unexpected error code 0x%x, nsamps %u.\n"
|
||
| 77 | ) % md.error_code % nsamps << std::endl; |
||
| 78 | return false; |
||
| 79 | } |
||
| 80 | } |
||
| 81 | |||
| 82 | /*!
|
||
| 83 | * Test the broken chain message:
|
||
| 84 | * Issue a stream command with num samps and more.
|
||
| 85 | * We expect to get an inline broken chain message.
|
||
| 86 | */
|
||
| 87 | a629bbe7 | Josh Blum | bool test_broken_chain_message(uhd::usrp::multi_usrp::sptr usrp, uhd::rx_streamer::sptr rx_stream, uhd::tx_streamer::sptr){
|
| 88 | 34265334 | Josh Blum | std::cout << "Test broken chain message... " << std::flush;
|
| 89 | |||
| 90 | uhd::stream_cmd_t stream_cmd(uhd::stream_cmd_t::STREAM_MODE_NUM_SAMPS_AND_MORE); |
||
| 91 | stream_cmd.stream_now = true;
|
||
| 92 | a629bbe7 | Josh Blum | stream_cmd.num_samps = rx_stream->get_max_num_samps(); |
| 93 | 34265334 | Josh Blum | usrp->issue_stream_cmd(stream_cmd); |
| 94 | |||
| 95 | a629bbe7 | Josh Blum | std::vector<std::complex<float> > buff(rx_stream->get_max_num_samps());
|
| 96 | 34265334 | Josh Blum | uhd::rx_metadata_t md; |
| 97 | |||
| 98 | a629bbe7 | Josh Blum | rx_stream->recv( //once for the requested samples
|
| 99 | &buff.front(), buff.size(), md |
||
| 100 | 34265334 | Josh Blum | ); |
| 101 | |||
| 102 | a629bbe7 | Josh Blum | rx_stream->recv( //again for the inline message
|
| 103 | &buff.front(), buff.size(), md |
||
| 104 | 34265334 | Josh Blum | ); |
| 105 | |||
| 106 | switch(md.error_code){
|
||
| 107 | case uhd::rx_metadata_t::ERROR_CODE_BROKEN_CHAIN:
|
||
| 108 | std::cout << boost::format( |
||
| 109 | "success:\n"
|
||
| 110 | " Got error code broken chain message.\n"
|
||
| 111 | ) << std::endl; |
||
| 112 | return true; |
||
| 113 | |||
| 114 | case uhd::rx_metadata_t::ERROR_CODE_TIMEOUT:
|
||
| 115 | std::cout << boost::format( |
||
| 116 | "failed:\n"
|
||
| 117 | " Inline message recv timed out.\n"
|
||
| 118 | ) << std::endl; |
||
| 119 | return false; |
||
| 120 | |||
| 121 | default:
|
||
| 122 | std::cout << boost::format( |
||
| 123 | "failed:\n"
|
||
| 124 | " Got unexpected error code 0x%x.\n"
|
||
| 125 | ) % md.error_code << std::endl; |
||
| 126 | return false; |
||
| 127 | } |
||
| 128 | } |
||
| 129 | |||
| 130 | /*!
|
||
| 131 | f9edd386 | Josh Blum | * Test the burst ack message:
|
| 132 | b7e3450a | Josh Blum | * Send a burst of many samples that will fragment internally.
|
| 133 | f9edd386 | Josh Blum | * We expect to get an burst ack async message.
|
| 134 | b7e3450a | Josh Blum | */
|
| 135 | a629bbe7 | Josh Blum | bool test_burst_ack_message(uhd::usrp::multi_usrp::sptr usrp, uhd::rx_streamer::sptr, uhd::tx_streamer::sptr tx_stream){
|
| 136 | f9edd386 | Josh Blum | std::cout << "Test burst ack message... " << std::flush;
|
| 137 | b7e3450a | Josh Blum | |
| 138 | uhd::tx_metadata_t md; |
||
| 139 | md.start_of_burst = true;
|
||
| 140 | md.end_of_burst = true;
|
||
| 141 | md.has_time_spec = false;
|
||
| 142 | |||
| 143 | //3 times max-sps guarantees a SOB, no burst, and EOB packet
|
||
| 144 | a629bbe7 | Josh Blum | std::vector<std::complex<float> > buff(tx_stream->get_max_num_samps()*3); |
| 145 | b7e3450a | Josh Blum | |
| 146 | a629bbe7 | Josh Blum | tx_stream->send( |
| 147 | &buff.front(), buff.size(), md |
||
| 148 | b7e3450a | Josh Blum | ); |
| 149 | |||
| 150 | uhd::async_metadata_t async_md; |
||
| 151 | 67bba008 | Josh Blum | if (not usrp->get_device()->recv_async_msg(async_md)){ |
| 152 | b7e3450a | Josh Blum | std::cout << boost::format( |
| 153 | "failed:\n"
|
||
| 154 | f9755b0a | Josh Blum | " Async message recv timed out.\n"
|
| 155 | ) << std::endl; |
||
| 156 | 4dfb7b8c | Josh Blum | return false; |
| 157 | b7e3450a | Josh Blum | } |
| 158 | f9755b0a | Josh Blum | |
| 159 | switch(async_md.event_code){
|
||
| 160 | f9edd386 | Josh Blum | case uhd::async_metadata_t::EVENT_CODE_BURST_ACK:
|
| 161 | b7e3450a | Josh Blum | std::cout << boost::format( |
| 162 | "success:\n"
|
||
| 163 | f9edd386 | Josh Blum | " Got event code burst ack message.\n"
|
| 164 | b7e3450a | Josh Blum | ) << std::endl; |
| 165 | 4dfb7b8c | Josh Blum | return true; |
| 166 | f9755b0a | Josh Blum | |
| 167 | default:
|
||
| 168 | std::cout << boost::format( |
||
| 169 | "failed:\n"
|
||
| 170 | " Got unexpected event code 0x%x.\n"
|
||
| 171 | ) % async_md.event_code << std::endl; |
||
| 172 | 4dfb7b8c | Josh Blum | return false; |
| 173 | b7e3450a | Josh Blum | } |
| 174 | } |
||
| 175 | |||
| 176 | /*!
|
||
| 177 | * Test the underflow message:
|
||
| 178 | * Send a start of burst packet with no following end of burst.
|
||
| 179 | * We expect to get an underflow(within a burst) async message.
|
||
| 180 | */
|
||
| 181 | a629bbe7 | Josh Blum | bool test_underflow_message(uhd::usrp::multi_usrp::sptr usrp, uhd::rx_streamer::sptr, uhd::tx_streamer::sptr tx_stream){
|
| 182 | b7e3450a | Josh Blum | std::cout << "Test underflow message... " << std::flush;
|
| 183 | |||
| 184 | uhd::tx_metadata_t md; |
||
| 185 | md.start_of_burst = true;
|
||
| 186 | md.end_of_burst = false;
|
||
| 187 | md.has_time_spec = false;
|
||
| 188 | |||
| 189 | a629bbe7 | Josh Blum | tx_stream->send("", 0, md); |
| 190 | b7e3450a | Josh Blum | |
| 191 | uhd::async_metadata_t async_md; |
||
| 192 | 67bba008 | Josh Blum | if (not usrp->get_device()->recv_async_msg(async_md, 1)){ |
| 193 | b7e3450a | Josh Blum | std::cout << boost::format( |
| 194 | "failed:\n"
|
||
| 195 | " Async message recv timed out.\n"
|
||
| 196 | ) << std::endl; |
||
| 197 | 4dfb7b8c | Josh Blum | return false; |
| 198 | b7e3450a | Josh Blum | } |
| 199 | |||
| 200 | switch(async_md.event_code){
|
||
| 201 | case uhd::async_metadata_t::EVENT_CODE_UNDERFLOW:
|
||
| 202 | std::cout << boost::format( |
||
| 203 | "success:\n"
|
||
| 204 | " Got event code underflow message.\n"
|
||
| 205 | ) << std::endl; |
||
| 206 | 4dfb7b8c | Josh Blum | return true; |
| 207 | b7e3450a | Josh Blum | |
| 208 | default:
|
||
| 209 | std::cout << boost::format( |
||
| 210 | "failed:\n"
|
||
| 211 | " Got unexpected event code 0x%x.\n"
|
||
| 212 | ) % async_md.event_code << std::endl; |
||
| 213 | 4dfb7b8c | Josh Blum | return false; |
| 214 | b7e3450a | Josh Blum | } |
| 215 | } |
||
| 216 | |||
| 217 | /*!
|
||
| 218 | * Test the time error message:
|
||
| 219 | * Send a burst packet that occurs at a time in the past.
|
||
| 220 | * We expect to get a time error async message.
|
||
| 221 | */
|
||
| 222 | a629bbe7 | Josh Blum | bool test_time_error_message(uhd::usrp::multi_usrp::sptr usrp, uhd::rx_streamer::sptr, uhd::tx_streamer::sptr tx_stream){
|
| 223 | b7e3450a | Josh Blum | std::cout << "Test time error message... " << std::flush;
|
| 224 | |||
| 225 | uhd::tx_metadata_t md; |
||
| 226 | md.start_of_burst = true;
|
||
| 227 | md.end_of_burst = true;
|
||
| 228 | md.has_time_spec = true;
|
||
| 229 | md.time_spec = uhd::time_spec_t(100.0); //send at 100s |
||
| 230 | |||
| 231 | 67bba008 | Josh Blum | usrp->set_time_now(uhd::time_spec_t(200.0)); //time at 200s |
| 232 | b7e3450a | Josh Blum | |
| 233 | a629bbe7 | Josh Blum | tx_stream->send("", 0, md); |
| 234 | b7e3450a | Josh Blum | |
| 235 | uhd::async_metadata_t async_md; |
||
| 236 | 67bba008 | Josh Blum | if (not usrp->get_device()->recv_async_msg(async_md)){ |
| 237 | b7e3450a | Josh Blum | std::cout << boost::format( |
| 238 | "failed:\n"
|
||
| 239 | " Async message recv timed out.\n"
|
||
| 240 | ) << std::endl; |
||
| 241 | 4dfb7b8c | Josh Blum | return false; |
| 242 | b7e3450a | Josh Blum | } |
| 243 | |||
| 244 | switch(async_md.event_code){
|
||
| 245 | case uhd::async_metadata_t::EVENT_CODE_TIME_ERROR:
|
||
| 246 | std::cout << boost::format( |
||
| 247 | "success:\n"
|
||
| 248 | " Got event code time error message.\n"
|
||
| 249 | ) << std::endl; |
||
| 250 | 4dfb7b8c | Josh Blum | return true; |
| 251 | b7e3450a | Josh Blum | |
| 252 | default:
|
||
| 253 | std::cout << boost::format( |
||
| 254 | "failed:\n"
|
||
| 255 | " Got unexpected event code 0x%x.\n"
|
||
| 256 | ) % async_md.event_code << std::endl; |
||
| 257 | 4dfb7b8c | Josh Blum | return false; |
| 258 | b7e3450a | Josh Blum | } |
| 259 | } |
||
| 260 | |||
| 261 | 34265334 | Josh Blum | void flush_async(uhd::usrp::multi_usrp::sptr usrp){
|
| 262 | 4dfb7b8c | Josh Blum | uhd::async_metadata_t async_md; |
| 263 | 34265334 | Josh Blum | while (usrp->get_device()->recv_async_msg(async_md)){}
|
| 264 | } |
||
| 265 | |||
| 266 | a629bbe7 | Josh Blum | void flush_recv(uhd::rx_streamer::sptr rx_stream){
|
| 267 | std::vector<std::complex<float> > buff(rx_stream->get_max_num_samps());
|
||
| 268 | 34265334 | Josh Blum | uhd::rx_metadata_t md; |
| 269 | |||
| 270 | do{
|
||
| 271 | a629bbe7 | Josh Blum | rx_stream->recv(&buff.front(), buff.size(), md); |
| 272 | 34265334 | Josh Blum | } while (md.error_code != uhd::rx_metadata_t::ERROR_CODE_TIMEOUT);
|
| 273 | 4dfb7b8c | Josh Blum | } |
| 274 | |||
| 275 | b7e3450a | Josh Blum | int UHD_SAFE_MAIN(int argc, char *argv[]){ |
| 276 | uhd::set_thread_priority_safe(); |
||
| 277 | |||
| 278 | //variables to be set by po
|
||
| 279 | std::string args;
|
||
| 280 | 4dfb7b8c | Josh Blum | size_t ntests; |
| 281 | b7e3450a | Josh Blum | |
| 282 | //setup the program options
|
||
| 283 | po::options_description desc("Allowed options");
|
||
| 284 | desc.add_options() |
||
| 285 | ("help", "help message") |
||
| 286 | 67bba008 | Josh Blum | ("args", po::value<std::string>(&args)->default_value(""), "multi uhd device address args") |
| 287 | 34265334 | Josh Blum | ("ntests", po::value<size_t>(&ntests)->default_value(50), "number of tests to run") |
| 288 | b7e3450a | Josh Blum | ; |
| 289 | po::variables_map vm; |
||
| 290 | po::store(po::parse_command_line(argc, argv, desc), vm); |
||
| 291 | po::notify(vm); |
||
| 292 | |||
| 293 | //print the help message
|
||
| 294 | if (vm.count("help")){ |
||
| 295 | 34265334 | Josh Blum | std::cout << boost::format("UHD Test Messages %s") % desc << std::endl;
|
| 296 | b7e3450a | Josh Blum | return ~0; |
| 297 | } |
||
| 298 | |||
| 299 | //create a usrp device
|
||
| 300 | std::cout << std::endl; |
||
| 301 | std::cout << boost::format("Creating the usrp device with: %s...") % args << std::endl;
|
||
| 302 | 67bba008 | Josh Blum | uhd::usrp::multi_usrp::sptr usrp = uhd::usrp::multi_usrp::make(args); |
| 303 | std::cout << boost::format("Using Device: %s") % usrp->get_pp_string() << std::endl;
|
||
| 304 | b7e3450a | Josh Blum | |
| 305 | a629bbe7 | Josh Blum | //create RX and TX streamers
|
| 306 | fac15db5 | Josh Blum | uhd::stream_args_t stream_args("fc32"); //complex floats |
| 307 | uhd::rx_streamer::sptr rx_stream = usrp->get_rx_stream(stream_args); |
||
| 308 | uhd::tx_streamer::sptr tx_stream = usrp->get_tx_stream(stream_args); |
||
| 309 | a629bbe7 | Josh Blum | |
| 310 | b7e3450a | Josh Blum | //------------------------------------------------------------------
|
| 311 | 34265334 | Josh Blum | // begin messages test
|
| 312 | b7e3450a | Josh Blum | //------------------------------------------------------------------
|
| 313 | a629bbe7 | Josh Blum | static const uhd::dict<std::string, boost::function<bool(uhd::usrp::multi_usrp::sptr, uhd::rx_streamer::sptr, uhd::tx_streamer::sptr)> > |
| 314 | 4dfb7b8c | Josh Blum | tests = boost::assign::map_list_of |
| 315 | f9edd386 | Josh Blum | ("Test Burst ACK ", &test_burst_ack_message)
|
| 316 | ("Test Underflow ", &test_underflow_message)
|
||
| 317 | 4dfb7b8c | Josh Blum | ("Test Time Error", &test_time_error_message)
|
| 318 | 34265334 | Josh Blum | ("Test Late Command", &test_late_command_message)
|
| 319 | ("Test Broken Chain", &test_broken_chain_message)
|
||
| 320 | 4dfb7b8c | Josh Blum | ; |
| 321 | |||
| 322 | //init result counts
|
||
| 323 | uhd::dict<std::string, size_t> failures, successes;
|
||
| 324 | BOOST_FOREACH(const std::string &key, tests.keys()){ |
||
| 325 | failures[key] = 0;
|
||
| 326 | successes[key] = 0;
|
||
| 327 | } |
||
| 328 | |||
| 329 | //run the tests, pick at random
|
||
| 330 | 11510003 | Josh Blum | std::srand((unsigned int) time(NULL)); |
| 331 | 4dfb7b8c | Josh Blum | for (size_t n = 0; n < ntests; n++){ |
| 332 | std::string key = tests.keys()[std::rand() % tests.size()];
|
||
| 333 | a629bbe7 | Josh Blum | bool pass = tests[key](usrp, rx_stream, tx_stream);
|
| 334 | 34265334 | Josh Blum | flush_async(usrp); |
| 335 | a629bbe7 | Josh Blum | flush_recv(rx_stream); |
| 336 | 4dfb7b8c | Josh Blum | |
| 337 | //store result
|
||
| 338 | if (pass) successes[key]++;
|
||
| 339 | else failures[key]++;
|
||
| 340 | } |
||
| 341 | |||
| 342 | //print the result summary
|
||
| 343 | std::cout << std::endl << "Summary:" << std::endl << std::endl;
|
||
| 344 | BOOST_FOREACH(const std::string &key, tests.keys()){ |
||
| 345 | std::cout << boost::format( |
||
| 346 | 34265334 | Josh Blum | "%s -> %3u successes, %3u failures"
|
| 347 | 4dfb7b8c | Josh Blum | ) % key % successes[key] % failures[key] << std::endl; |
| 348 | } |
||
| 349 | b7e3450a | Josh Blum | |
| 350 | //finished
|
||
| 351 | std::cout << std::endl << "Done!" << std::endl << std::endl;
|
||
| 352 | |||
| 353 | return 0; |
||
| 354 | } |