From b66a74ff1f629af714e26040b410d472c08be522 Mon Sep 17 00:00:00 2001 From: Josh Blum Date: Wed, 7 Apr 2010 00:46:42 -0700 Subject: Reworked the spi part of the dboard interface. It turns out to be more complicated. The integer type is better for holding the bits. The edges can be different, so the spi config hold 2 edge setting for mosi and miso. --- host/lib/usrp/usrp2/dboard_interface.cpp | 95 +++++++++++++++++++------------- host/lib/usrp/usrp2/fw_common.h | 7 ++- 2 files changed, 61 insertions(+), 41 deletions(-) (limited to 'host/lib/usrp/usrp2') diff --git a/host/lib/usrp/usrp2/dboard_interface.cpp b/host/lib/usrp/usrp2/dboard_interface.cpp index 6dd756420..eee7c087a 100644 --- a/host/lib/usrp/usrp2/dboard_interface.cpp +++ b/host/lib/usrp/usrp2/dboard_interface.cpp @@ -42,9 +42,35 @@ public: double get_rx_clock_rate(void); double get_tx_clock_rate(void); + void write_spi( + unit_type_t unit, + const spi_config_t &config, + boost::uint32_t data, + size_t num_bits + ){ + transact_spi(unit, config, data, num_bits, false /*no rb*/); + } + + boost::uint32_t read_spi( + unit_type_t unit, + const spi_config_t &config, + size_t num_bits + ){ + return transact_spi(unit, config, 0, num_bits, true /*rb*/); + } + + boost::uint32_t read_write_spi( + unit_type_t unit, + const spi_config_t &config, + boost::uint32_t data, + size_t num_bits + ){ + return transact_spi(unit, config, data, num_bits, true /*rb*/); + } + private: - byte_vector_t transact_spi( - spi_dev_t, spi_edge_t, const byte_vector_t &, bool + boost::uint32_t transact_spi( + unit_type_t, const spi_config_t &, boost::uint32_t, size_t, bool ); usrp2_impl *_impl; @@ -136,17 +162,17 @@ void usrp2_dboard_interface::set_atr_reg(gpio_bank_t bank, atr_reg_t atr, boost: * SPI **********************************************************************/ /*! - * Static function to convert a spi dev enum - * to an over-the-wire value for the usrp2 control. - * \param dev the dboard interface spi dev enum + * Static function to convert a unit type enum + * to an over-the-wire value for the spi device. + * \param unit the dboard interface unit type enum * \return an over the wire representation */ -static boost::uint8_t spi_dev_to_otw(dboard_interface::spi_dev_t dev){ - switch(dev){ - case uhd::usrp::dboard_interface::SPI_DEV_TX: return SPI_SS_TX_DB; - case uhd::usrp::dboard_interface::SPI_DEV_RX: return SPI_SS_RX_DB; +static boost::uint8_t unit_to_otw_dev(dboard_interface::unit_type_t unit){ + switch(unit){ + case dboard_interface::UNIT_TYPE_TX: return SPI_SS_TX_DB; + case dboard_interface::UNIT_TYPE_RX: return SPI_SS_RX_DB; } - throw std::invalid_argument("unknown spi device type"); + throw std::invalid_argument("unknown unit type type"); } /*! @@ -155,43 +181,36 @@ static boost::uint8_t spi_dev_to_otw(dboard_interface::spi_dev_t dev){ * \param edge the dboard interface spi edge enum * \return an over the wire representation */ -static boost::uint8_t spi_edge_to_otw(dboard_interface::spi_edge_t edge){ +static boost::uint8_t spi_edge_to_otw(dboard_interface::spi_config_t::edge_t edge){ switch(edge){ - case uhd::usrp::dboard_interface::SPI_EDGE_RISE: return USRP2_CLK_EDGE_RISE; - case uhd::usrp::dboard_interface::SPI_EDGE_FALL: return USRP2_CLK_EDGE_FALL; + case dboard_interface::spi_config_t::EDGE_RISE: return USRP2_CLK_EDGE_RISE; + case dboard_interface::spi_config_t::EDGE_FALL: return USRP2_CLK_EDGE_FALL; } throw std::invalid_argument("unknown spi edge type"); } -dboard_interface::byte_vector_t usrp2_dboard_interface::transact_spi( - spi_dev_t dev, - spi_edge_t edge, - const byte_vector_t &buf, +boost::uint32_t usrp2_dboard_interface::transact_spi( + unit_type_t unit, + const spi_config_t &config, + boost::uint32_t data, + size_t num_bits, bool readback ){ //setup the out data usrp2_ctrl_data_t out_data; out_data.id = htonl(USRP2_CTRL_ID_TRANSACT_ME_SOME_SPI_BRO); - out_data.data.spi_args.dev = spi_dev_to_otw(dev); - out_data.data.spi_args.edge = spi_edge_to_otw(edge); + out_data.data.spi_args.dev = unit_to_otw_dev(unit); + out_data.data.spi_args.miso_edge = spi_edge_to_otw(config.miso_edge); + out_data.data.spi_args.mosi_edge = spi_edge_to_otw(config.mosi_edge); out_data.data.spi_args.readback = (readback)? 1 : 0; - out_data.data.spi_args.bytes = buf.size(); - - //limitation of spi transaction size - ASSERT_THROW(buf.size() <= sizeof(out_data.data.spi_args.data)); - - //copy in the data - std::copy(buf.begin(), buf.end(), out_data.data.spi_args.data); + out_data.data.spi_args.num_bits = num_bits; + out_data.data.spi_args.data = htonl(data); //send and recv usrp2_ctrl_data_t in_data = _impl->ctrl_send_and_recv(out_data); ASSERT_THROW(htonl(in_data.id) == USRP2_CTRL_ID_OMG_TRANSACTED_SPI_DUDE); - ASSERT_THROW(in_data.data.spi_args.bytes == buf.size()); - //copy out the data - byte_vector_t result(buf.size()); - std::copy(in_data.data.spi_args.data, in_data.data.spi_args.data + buf.size(), result.begin()); - return result; + return ntohl(out_data.data.spi_args.data); } /*********************************************************************** @@ -245,19 +264,19 @@ dboard_interface::byte_vector_t usrp2_dboard_interface::read_i2c(int i2c_addr, s * \param unit the dboard interface unit type enum * \return an over the wire representation */ -static boost::uint8_t spi_dev_to_otw(dboard_interface::unit_type_t unit){ +static boost::uint8_t unit_to_otw(dboard_interface::unit_type_t unit){ switch(unit){ - case uhd::usrp::dboard_interface::UNIT_TYPE_TX: return USRP2_DIR_TX; - case uhd::usrp::dboard_interface::UNIT_TYPE_RX: return USRP2_DIR_RX; + case dboard_interface::UNIT_TYPE_TX: return USRP2_DIR_TX; + case dboard_interface::UNIT_TYPE_RX: return USRP2_DIR_RX; } throw std::invalid_argument("unknown unit type type"); } -void usrp2_dboard_interface::write_aux_dac(dboard_interface::unit_type_t unit, int which, int value){ +void usrp2_dboard_interface::write_aux_dac(unit_type_t unit, int which, int value){ //setup the out data usrp2_ctrl_data_t out_data; out_data.id = htonl(USRP2_CTRL_ID_WRITE_THIS_TO_THE_AUX_DAC_BRO); - out_data.data.aux_args.dir = spi_dev_to_otw(unit); + out_data.data.aux_args.dir = unit_to_otw(unit); out_data.data.aux_args.which = which; out_data.data.aux_args.value = htonl(value); @@ -266,11 +285,11 @@ void usrp2_dboard_interface::write_aux_dac(dboard_interface::unit_type_t unit, i ASSERT_THROW(htonl(in_data.id) == USRP2_CTRL_ID_DONE_WITH_THAT_AUX_DAC_DUDE); } -int usrp2_dboard_interface::read_aux_adc(dboard_interface::unit_type_t unit, int which){ +int usrp2_dboard_interface::read_aux_adc(unit_type_t unit, int which){ //setup the out data usrp2_ctrl_data_t out_data; out_data.id = htonl(USRP2_CTRL_ID_READ_FROM_THIS_AUX_ADC_BRO); - out_data.data.aux_args.dir = spi_dev_to_otw(unit); + out_data.data.aux_args.dir = unit_to_otw(unit); out_data.data.aux_args.which = which; //send and recv diff --git a/host/lib/usrp/usrp2/fw_common.h b/host/lib/usrp/usrp2/fw_common.h index 019f3b931..b600a2a70 100644 --- a/host/lib/usrp/usrp2/fw_common.h +++ b/host/lib/usrp/usrp2/fw_common.h @@ -110,10 +110,11 @@ typedef struct{ } dboard_ids; struct { _SINS_ uint8_t dev; - _SINS_ uint8_t edge; + _SINS_ uint8_t miso_edge; + _SINS_ uint8_t mosi_edge; _SINS_ uint8_t readback; - _SINS_ uint8_t bytes; - _SINS_ uint8_t data[sizeof(_SINS_ uint32_t)]; + _SINS_ uint32_t data; + _SINS_ uint8_t num_bits; } spi_args; struct { _SINS_ uint8_t addr; -- cgit v1.2.3 From d743784919b362d93e6408f05bdef6e543e3fc7e Mon Sep 17 00:00:00 2001 From: Josh Blum Date: Thu, 8 Apr 2010 10:57:16 -0700 Subject: converted timespec to use nanoseconds for fractional part --- host/CMakeLists.txt | 1 + host/examples/rx_timed_samples.cpp | 4 +- host/include/uhd/transport/vrt.hpp | 8 +++- host/include/uhd/types/metadata.hpp | 1 + host/include/uhd/types/time_spec.hpp | 36 +++++++++++------- host/lib/transport/gen_vrt.py | 10 +++-- host/lib/transport/vrt.cpp | 72 ++++++++++++++++++------------------ host/lib/types.cpp | 27 ++++++-------- host/lib/usrp/usrp2/dboard_impl.cpp | 1 + host/lib/usrp/usrp2/io_impl.cpp | 11 ++++-- host/lib/usrp/usrp2/mboard_impl.cpp | 8 +--- host/test/vrt_test.cpp | 12 +++--- 12 files changed, 105 insertions(+), 86 deletions(-) (limited to 'host/lib/usrp/usrp2') diff --git a/host/CMakeLists.txt b/host/CMakeLists.txt index d2889fe58..baae90861 100644 --- a/host/CMakeLists.txt +++ b/host/CMakeLists.txt @@ -145,6 +145,7 @@ ENDIF(DOXYGEN_FOUND) INSTALL(FILES ${CMAKE_SOURCE_DIR}/README ${CMAKE_SOURCE_DIR}/LICENSE + ${CMAKE_SOURCE_DIR}/AUTHORS DESTINATION ${PKG_DOC_DIR} ) diff --git a/host/examples/rx_timed_samples.cpp b/host/examples/rx_timed_samples.cpp index e971e9f6a..d49f7d182 100644 --- a/host/examples/rx_timed_samples.cpp +++ b/host/examples/rx_timed_samples.cpp @@ -86,8 +86,8 @@ int UHD_SAFE_MAIN(int argc, char *argv[]){ ); if (num_rx_samps == 0) continue; //wait for packets with contents - std::cout << boost::format("Got packet: %u samples, %u secs, %u ticks") - % num_rx_samps % md.time_spec.secs % md.time_spec.ticks << std::endl; + std::cout << boost::format("Got packet: %u samples, %u secs, %u nsecs") + % num_rx_samps % md.time_spec.secs % md.time_spec.nsecs << std::endl; num_acc_samps += num_rx_samps; } diff --git a/host/include/uhd/transport/vrt.hpp b/host/include/uhd/transport/vrt.hpp index 04945b347..137698e57 100644 --- a/host/include/uhd/transport/vrt.hpp +++ b/host/include/uhd/transport/vrt.hpp @@ -36,6 +36,7 @@ namespace vrt{ * \param num_payload_words32 the length of the payload * \param num_packet_words32 the length of the packet * \param packet_count the packet count sequence number + * \param tick_rate ticks per second used in time conversion */ UHD_API void pack( const tx_metadata_t &metadata, //input @@ -43,7 +44,8 @@ namespace vrt{ size_t &num_header_words32, //output size_t num_payload_words32, //input size_t &num_packet_words32, //output - size_t packet_count //input + size_t packet_count, //input + double tick_rate //input ); /*! @@ -54,6 +56,7 @@ namespace vrt{ * \param num_payload_words32 the length of the payload * \param num_packet_words32 the length of the packet * \param packet_count the packet count sequence number + * \param tick_rate ticks per second used in time conversion */ UHD_API void unpack( rx_metadata_t &metadata, //output @@ -61,7 +64,8 @@ namespace vrt{ size_t &num_header_words32, //output size_t &num_payload_words32, //output size_t num_packet_words32, //input - size_t &packet_count //output + size_t &packet_count, //output + double tick_rate //input ); } //namespace vrt diff --git a/host/include/uhd/types/metadata.hpp b/host/include/uhd/types/metadata.hpp index 20f483bed..d93b38b50 100644 --- a/host/include/uhd/types/metadata.hpp +++ b/host/include/uhd/types/metadata.hpp @@ -19,6 +19,7 @@ #define INCLUDED_UHD_TYPES_METADATA_HPP #include +#include #include namespace uhd{ diff --git a/host/include/uhd/types/time_spec.hpp b/host/include/uhd/types/time_spec.hpp index 8c8f2bc25..f06d27118 100644 --- a/host/include/uhd/types/time_spec.hpp +++ b/host/include/uhd/types/time_spec.hpp @@ -20,33 +20,43 @@ #include #include -#include namespace uhd{ /*! - * A time_spec_t holds a seconds and ticks time value. - * The temporal width of a tick depends on the device's clock rate. - * The time_spec_t can be used when setting the time on devices + * A time_spec_t holds a seconds and fractional seconds time value. + * The time_spec_t can be used when setting the time on devices, + * and for dealing with time stamped samples though the metadata. * and for controlling the start of streaming for applicable dsps. */ struct UHD_API time_spec_t{ + + //! whole seconds count boost::uint32_t secs; - boost::uint32_t ticks; + + //! fractional seconds count in nano-seconds + double nsecs; /*! - * Create a time_spec_t from seconds and ticks. - * \param new_secs the new seconds (default = 0) - * \param new_ticks the new ticks (default = 0) + * Convert the fractional nsecs to clock ticks. + * \param tick_rate the number of ticks per second + * \return the number of ticks in this time spec */ - time_spec_t(boost::uint32_t new_secs = 0, boost::uint32_t new_ticks = 0); + boost::uint32_t get_ticks(double tick_rate) const; /*! - * Create a time_spec_t from boost posix time. - * \param time fine-grained boost posix time - * \param tick_rate the rate of ticks per second + * Set the fractional nsecs from clock ticks. + * \param ticks the fractional seconds tick count + * \param tick_rate the number of ticks per second + */ + void set_ticks(boost::uint32_t ticks, double tick_rate); + + /*! + * Create a time_spec_t from seconds and ticks. + * \param new_secs the new seconds (default = 0) + * \param new_nsecs the new nano-seconds (default = 0) */ - time_spec_t(boost::posix_time::ptime time, double tick_rate); + time_spec_t(boost::uint32_t new_secs = 0, double new_nsecs = 0); }; diff --git a/host/lib/transport/gen_vrt.py b/host/lib/transport/gen_vrt.py index 918de3ad7..bc6635d78 100755 --- a/host/lib/transport/gen_vrt.py +++ b/host/lib/transport/gen_vrt.py @@ -54,7 +54,8 @@ void vrt::pack( size_t &num_header_words32, //output size_t num_payload_words32, //input size_t &num_packet_words32, //output - size_t packet_count //input + size_t packet_count, //input + double tick_rate //input ){ boost::uint32_t vrt_hdr_flags; @@ -91,7 +92,7 @@ void vrt::pack( #if $pred & $tsf_p header_buff[$num_header_words] = htonl(0); #set $num_header_words += 1 - header_buff[$num_header_words] = htonl(metadata.time_spec.ticks); + header_buff[$num_header_words] = htonl(metadata.time_spec.get_ticks(tick_rate)); #set $num_header_words += 1 #set $flags |= (0x1 << 20); #end if @@ -127,7 +128,8 @@ void vrt::unpack( size_t &num_header_words32, //output size_t &num_payload_words32, //output size_t num_packet_words32, //input - size_t &packet_count //output + size_t &packet_count, //output + double tick_rate //input ){ //clear the metadata metadata = rx_metadata_t(); @@ -180,7 +182,7 @@ void vrt::unpack( #set $set_has_time_spec = True #end if #set $num_header_words += 1 - metadata.time_spec.ticks = ntohl(header_buff[$num_header_words]); + metadata.time_spec.set_ticks(ntohl(header_buff[$num_header_words]), tick_rate); #set $num_header_words += 1 #end if ########## Trailer ########## diff --git a/host/lib/transport/vrt.cpp b/host/lib/transport/vrt.cpp index bebca5db9..78c3cf2cb 100644 --- a/host/lib/transport/vrt.cpp +++ b/host/lib/transport/vrt.cpp @@ -2,7 +2,7 @@ /*********************************************************************** - * This file was generated by ./gen_vrt.py on Fri Mar 26 15:33:00 2010 + * This file was generated by gen_vrt.py on 04/08/10 10:55:26 **********************************************************************/ #include @@ -18,7 +18,8 @@ void vrt::pack( size_t &num_header_words32, //output size_t num_payload_words32, //input size_t &num_packet_words32, //output - size_t packet_count //input + size_t packet_count, //input + double tick_rate //input ){ boost::uint32_t vrt_hdr_flags; @@ -85,7 +86,7 @@ void vrt::pack( break; case 8: header_buff[1] = htonl(0); - header_buff[2] = htonl(metadata.time_spec.ticks); + header_buff[2] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 3; num_packet_words32 = 3 + num_payload_words32; vrt_hdr_flags = 0x100000; @@ -93,7 +94,7 @@ void vrt::pack( case 9: header_buff[1] = htonl(metadata.stream_id); header_buff[2] = htonl(0); - header_buff[3] = htonl(metadata.time_spec.ticks); + header_buff[3] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 4; num_packet_words32 = 4 + num_payload_words32; vrt_hdr_flags = 0x10100000; @@ -102,7 +103,7 @@ void vrt::pack( header_buff[1] = htonl(0); header_buff[2] = htonl(0); header_buff[3] = htonl(0); - header_buff[4] = htonl(metadata.time_spec.ticks); + header_buff[4] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 5; num_packet_words32 = 5 + num_payload_words32; vrt_hdr_flags = 0x8100000; @@ -112,7 +113,7 @@ void vrt::pack( header_buff[2] = htonl(0); header_buff[3] = htonl(0); header_buff[4] = htonl(0); - header_buff[5] = htonl(metadata.time_spec.ticks); + header_buff[5] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 6; num_packet_words32 = 6 + num_payload_words32; vrt_hdr_flags = 0x18100000; @@ -120,7 +121,7 @@ void vrt::pack( case 12: header_buff[1] = htonl(metadata.time_spec.secs); header_buff[2] = htonl(0); - header_buff[3] = htonl(metadata.time_spec.ticks); + header_buff[3] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 4; num_packet_words32 = 4 + num_payload_words32; vrt_hdr_flags = 0xd00000; @@ -129,7 +130,7 @@ void vrt::pack( header_buff[1] = htonl(metadata.stream_id); header_buff[2] = htonl(metadata.time_spec.secs); header_buff[3] = htonl(0); - header_buff[4] = htonl(metadata.time_spec.ticks); + header_buff[4] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 5; num_packet_words32 = 5 + num_payload_words32; vrt_hdr_flags = 0x10d00000; @@ -139,7 +140,7 @@ void vrt::pack( header_buff[2] = htonl(0); header_buff[3] = htonl(metadata.time_spec.secs); header_buff[4] = htonl(0); - header_buff[5] = htonl(metadata.time_spec.ticks); + header_buff[5] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 6; num_packet_words32 = 6 + num_payload_words32; vrt_hdr_flags = 0x8d00000; @@ -150,7 +151,7 @@ void vrt::pack( header_buff[3] = htonl(0); header_buff[4] = htonl(metadata.time_spec.secs); header_buff[5] = htonl(0); - header_buff[6] = htonl(metadata.time_spec.ticks); + header_buff[6] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 7; num_packet_words32 = 7 + num_payload_words32; vrt_hdr_flags = 0x18d00000; @@ -213,7 +214,7 @@ void vrt::pack( break; case 24: header_buff[1] = htonl(0); - header_buff[2] = htonl(metadata.time_spec.ticks); + header_buff[2] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 3; num_packet_words32 = 4 + num_payload_words32; vrt_hdr_flags = 0x4100000; @@ -221,7 +222,7 @@ void vrt::pack( case 25: header_buff[1] = htonl(metadata.stream_id); header_buff[2] = htonl(0); - header_buff[3] = htonl(metadata.time_spec.ticks); + header_buff[3] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 4; num_packet_words32 = 5 + num_payload_words32; vrt_hdr_flags = 0x14100000; @@ -230,7 +231,7 @@ void vrt::pack( header_buff[1] = htonl(0); header_buff[2] = htonl(0); header_buff[3] = htonl(0); - header_buff[4] = htonl(metadata.time_spec.ticks); + header_buff[4] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 5; num_packet_words32 = 6 + num_payload_words32; vrt_hdr_flags = 0xc100000; @@ -240,7 +241,7 @@ void vrt::pack( header_buff[2] = htonl(0); header_buff[3] = htonl(0); header_buff[4] = htonl(0); - header_buff[5] = htonl(metadata.time_spec.ticks); + header_buff[5] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 6; num_packet_words32 = 7 + num_payload_words32; vrt_hdr_flags = 0x1c100000; @@ -248,7 +249,7 @@ void vrt::pack( case 28: header_buff[1] = htonl(metadata.time_spec.secs); header_buff[2] = htonl(0); - header_buff[3] = htonl(metadata.time_spec.ticks); + header_buff[3] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 4; num_packet_words32 = 5 + num_payload_words32; vrt_hdr_flags = 0x4d00000; @@ -257,7 +258,7 @@ void vrt::pack( header_buff[1] = htonl(metadata.stream_id); header_buff[2] = htonl(metadata.time_spec.secs); header_buff[3] = htonl(0); - header_buff[4] = htonl(metadata.time_spec.ticks); + header_buff[4] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 5; num_packet_words32 = 6 + num_payload_words32; vrt_hdr_flags = 0x14d00000; @@ -267,7 +268,7 @@ void vrt::pack( header_buff[2] = htonl(0); header_buff[3] = htonl(metadata.time_spec.secs); header_buff[4] = htonl(0); - header_buff[5] = htonl(metadata.time_spec.ticks); + header_buff[5] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 6; num_packet_words32 = 7 + num_payload_words32; vrt_hdr_flags = 0xcd00000; @@ -278,7 +279,7 @@ void vrt::pack( header_buff[3] = htonl(0); header_buff[4] = htonl(metadata.time_spec.secs); header_buff[5] = htonl(0); - header_buff[6] = htonl(metadata.time_spec.ticks); + header_buff[6] = htonl(metadata.time_spec.get_ticks(tick_rate)); num_header_words32 = 7; num_packet_words32 = 8 + num_payload_words32; vrt_hdr_flags = 0x1cd00000; @@ -302,7 +303,8 @@ void vrt::unpack( size_t &num_header_words32, //output size_t &num_payload_words32, //output size_t num_packet_words32, //input - size_t &packet_count //output + size_t &packet_count, //output + double tick_rate //input ){ //clear the metadata metadata = rx_metadata_t(); @@ -376,7 +378,7 @@ void vrt::unpack( break; case 8: metadata.has_time_spec = true; - metadata.time_spec.ticks = ntohl(header_buff[2]); + metadata.time_spec.set_ticks(ntohl(header_buff[2]), tick_rate); num_header_words32 = 3; num_payload_words32 = packet_words32 - 3; break; @@ -384,13 +386,13 @@ void vrt::unpack( metadata.has_stream_id = true; metadata.stream_id = ntohl(header_buff[1]); metadata.has_time_spec = true; - metadata.time_spec.ticks = ntohl(header_buff[3]); + metadata.time_spec.set_ticks(ntohl(header_buff[3]), tick_rate); num_header_words32 = 4; num_payload_words32 = packet_words32 - 4; break; case 10: metadata.has_time_spec = true; - metadata.time_spec.ticks = ntohl(header_buff[4]); + metadata.time_spec.set_ticks(ntohl(header_buff[4]), tick_rate); num_header_words32 = 5; num_payload_words32 = packet_words32 - 5; break; @@ -398,14 +400,14 @@ void vrt::unpack( metadata.has_stream_id = true; metadata.stream_id = ntohl(header_buff[1]); metadata.has_time_spec = true; - metadata.time_spec.ticks = ntohl(header_buff[5]); + metadata.time_spec.set_ticks(ntohl(header_buff[5]), tick_rate); num_header_words32 = 6; num_payload_words32 = packet_words32 - 6; break; case 12: metadata.has_time_spec = true; metadata.time_spec.secs = ntohl(header_buff[1]); - metadata.time_spec.ticks = ntohl(header_buff[3]); + metadata.time_spec.set_ticks(ntohl(header_buff[3]), tick_rate); num_header_words32 = 4; num_payload_words32 = packet_words32 - 4; break; @@ -414,14 +416,14 @@ void vrt::unpack( metadata.stream_id = ntohl(header_buff[1]); metadata.has_time_spec = true; metadata.time_spec.secs = ntohl(header_buff[2]); - metadata.time_spec.ticks = ntohl(header_buff[4]); + metadata.time_spec.set_ticks(ntohl(header_buff[4]), tick_rate); num_header_words32 = 5; num_payload_words32 = packet_words32 - 5; break; case 14: metadata.has_time_spec = true; metadata.time_spec.secs = ntohl(header_buff[3]); - metadata.time_spec.ticks = ntohl(header_buff[5]); + metadata.time_spec.set_ticks(ntohl(header_buff[5]), tick_rate); num_header_words32 = 6; num_payload_words32 = packet_words32 - 6; break; @@ -430,7 +432,7 @@ void vrt::unpack( metadata.stream_id = ntohl(header_buff[1]); metadata.has_time_spec = true; metadata.time_spec.secs = ntohl(header_buff[4]); - metadata.time_spec.ticks = ntohl(header_buff[6]); + metadata.time_spec.set_ticks(ntohl(header_buff[6]), tick_rate); num_header_words32 = 7; num_payload_words32 = packet_words32 - 7; break; @@ -484,7 +486,7 @@ void vrt::unpack( break; case 24: metadata.has_time_spec = true; - metadata.time_spec.ticks = ntohl(header_buff[2]); + metadata.time_spec.set_ticks(ntohl(header_buff[2]), tick_rate); num_header_words32 = 3; num_payload_words32 = packet_words32 - 4; break; @@ -492,13 +494,13 @@ void vrt::unpack( metadata.has_stream_id = true; metadata.stream_id = ntohl(header_buff[1]); metadata.has_time_spec = true; - metadata.time_spec.ticks = ntohl(header_buff[3]); + metadata.time_spec.set_ticks(ntohl(header_buff[3]), tick_rate); num_header_words32 = 4; num_payload_words32 = packet_words32 - 5; break; case 26: metadata.has_time_spec = true; - metadata.time_spec.ticks = ntohl(header_buff[4]); + metadata.time_spec.set_ticks(ntohl(header_buff[4]), tick_rate); num_header_words32 = 5; num_payload_words32 = packet_words32 - 6; break; @@ -506,14 +508,14 @@ void vrt::unpack( metadata.has_stream_id = true; metadata.stream_id = ntohl(header_buff[1]); metadata.has_time_spec = true; - metadata.time_spec.ticks = ntohl(header_buff[5]); + metadata.time_spec.set_ticks(ntohl(header_buff[5]), tick_rate); num_header_words32 = 6; num_payload_words32 = packet_words32 - 7; break; case 28: metadata.has_time_spec = true; metadata.time_spec.secs = ntohl(header_buff[1]); - metadata.time_spec.ticks = ntohl(header_buff[3]); + metadata.time_spec.set_ticks(ntohl(header_buff[3]), tick_rate); num_header_words32 = 4; num_payload_words32 = packet_words32 - 5; break; @@ -522,14 +524,14 @@ void vrt::unpack( metadata.stream_id = ntohl(header_buff[1]); metadata.has_time_spec = true; metadata.time_spec.secs = ntohl(header_buff[2]); - metadata.time_spec.ticks = ntohl(header_buff[4]); + metadata.time_spec.set_ticks(ntohl(header_buff[4]), tick_rate); num_header_words32 = 5; num_payload_words32 = packet_words32 - 6; break; case 30: metadata.has_time_spec = true; metadata.time_spec.secs = ntohl(header_buff[3]); - metadata.time_spec.ticks = ntohl(header_buff[5]); + metadata.time_spec.set_ticks(ntohl(header_buff[5]), tick_rate); num_header_words32 = 6; num_payload_words32 = packet_words32 - 7; break; @@ -538,7 +540,7 @@ void vrt::unpack( metadata.stream_id = ntohl(header_buff[1]); metadata.has_time_spec = true; metadata.time_spec.secs = ntohl(header_buff[4]); - metadata.time_spec.ticks = ntohl(header_buff[6]); + metadata.time_spec.set_ticks(ntohl(header_buff[6]), tick_rate); num_header_words32 = 7; num_payload_words32 = packet_words32 - 8; break; diff --git a/host/lib/types.cpp b/host/lib/types.cpp index 61a63b710..cd688e73d 100644 --- a/host/lib/types.cpp +++ b/host/lib/types.cpp @@ -26,6 +26,7 @@ #include #include #include +#include #include #include #include @@ -101,29 +102,26 @@ tx_metadata_t::tx_metadata_t(void){ /*********************************************************************** * time spec **********************************************************************/ -time_spec_t::time_spec_t(boost::uint32_t new_secs, boost::uint32_t new_ticks){ +time_spec_t::time_spec_t(boost::uint32_t new_secs, double new_nsecs){ secs = new_secs; - ticks = new_ticks; + nsecs = new_nsecs; } -static const boost::posix_time::ptime epoch(boost::gregorian::date(1970,1,1)); -static double time_tick_rate = double(boost::posix_time::time_duration::ticks_per_second()); +boost::uint32_t time_spec_t::get_ticks(double tick_rate) const{ + return boost::math::iround(nsecs*tick_rate*1e-9); +} -time_spec_t::time_spec_t(boost::posix_time::ptime time, double tick_rate){ - boost::posix_time::time_duration td = time - epoch; - secs = boost::uint32_t(td.total_seconds()); - double time_ticks_per_device_ticks = time_tick_rate/tick_rate; - ticks = boost::uint32_t(td.fractional_seconds()/time_ticks_per_device_ticks); +void time_spec_t::set_ticks(boost::uint32_t ticks, double tick_rate){ + nsecs = double(ticks)*1e9/tick_rate; } /*********************************************************************** * device addr **********************************************************************/ std::string device_addr_t::to_string(void) const{ - const device_addr_t &device_addr = *this; std::stringstream ss; - BOOST_FOREACH(std::string key, device_addr.keys()){ - ss << boost::format("%s: %s") % key % device_addr[key] << std::endl; + BOOST_FOREACH(std::string key, this->keys()){ + ss << boost::format("%s: %s") % key % (*this)[key] << std::endl; } return ss.str(); } @@ -137,9 +135,8 @@ static std::string trim(const std::string &in){ std::string device_addr_t::to_args_str(void) const{ std::string args_str; - const device_addr_t &device_addr = *this; - BOOST_FOREACH(const std::string &key, device_addr.keys()){ - args_str += key + pair_delim + device_addr[key] + arg_delim; + BOOST_FOREACH(const std::string &key, this->keys()){ + args_str += key + pair_delim + (*this)[key] + arg_delim; } return args_str; } diff --git a/host/lib/usrp/usrp2/dboard_impl.cpp b/host/lib/usrp/usrp2/dboard_impl.cpp index d1515f2d5..3ac805421 100644 --- a/host/lib/usrp/usrp2/dboard_impl.cpp +++ b/host/lib/usrp/usrp2/dboard_impl.cpp @@ -22,6 +22,7 @@ #include #include #include +#include using namespace uhd; using namespace uhd::usrp; diff --git a/host/lib/usrp/usrp2/io_impl.cpp b/host/lib/usrp/usrp2/io_impl.cpp index a58e32619..eb6b5f7b9 100644 --- a/host/lib/usrp/usrp2/io_impl.cpp +++ b/host/lib/usrp/usrp2/io_impl.cpp @@ -15,9 +15,10 @@ // along with this program. If not, see . // -#include -#include #include "usrp2_impl.hpp" +#include +#include +#include using namespace uhd; using namespace uhd::usrp; @@ -144,7 +145,8 @@ void usrp2_impl::recv_raw(rx_metadata_t &metadata){ num_header_words32_out, //output num_payload_words32_out, //output num_packet_words32, //input - packet_count_out //output + packet_count_out, //output + get_master_clock_freq() ); }catch(const std::exception &e){ std::cerr << "bad vrt header: " << e.what() << std::endl; @@ -196,7 +198,8 @@ size_t usrp2_impl::send( num_header_words32, //output num_samps, //input num_packet_words32, //output - packet_count //input + packet_count, //input + get_master_clock_freq() ); boost::uint32_t *items = tx_mem + num_header_words32; //offset for data diff --git a/host/lib/usrp/usrp2/mboard_impl.cpp b/host/lib/usrp/usrp2/mboard_impl.cpp index 94ab88a6b..2fa2e5211 100644 --- a/host/lib/usrp/usrp2/mboard_impl.cpp +++ b/host/lib/usrp/usrp2/mboard_impl.cpp @@ -33,10 +33,6 @@ void usrp2_impl::mboard_init(void){ boost::bind(&usrp2_impl::mboard_get, this, _1, _2), boost::bind(&usrp2_impl::mboard_set, this, _1, _2) ); - - //set the time on the usrp2 as close as possible to the system utc time - boost::posix_time::ptime now(boost::posix_time::microsec_clock::universal_time()); - set_time_spec(time_spec_t(now, get_master_clock_freq()), true); } void usrp2_impl::init_clock_config(void){ @@ -75,7 +71,7 @@ void usrp2_impl::update_clock_config(void){ void usrp2_impl::set_time_spec(const time_spec_t &time_spec, bool now){ //set ticks and seconds this->poke32(FR_TIME64_SECS, time_spec.secs); - this->poke32(FR_TIME64_TICKS, time_spec.ticks); + this->poke32(FR_TIME64_TICKS, time_spec.get_ticks(get_master_clock_freq())); //set the register to latch it all in boost::uint32_t imm_flags = (now)? FRF_TIME64_LATCH_NOW : FRF_TIME64_LATCH_NEXT_PPS; @@ -88,7 +84,7 @@ void usrp2_impl::issue_ddc_stream_cmd(const stream_cmd_t &stream_cmd){ out_data.id = htonl(USRP2_CTRL_ID_SEND_STREAM_COMMAND_FOR_ME_BRO); out_data.data.stream_cmd.now = (stream_cmd.stream_now)? 1 : 0; out_data.data.stream_cmd.secs = htonl(stream_cmd.time_spec.secs); - out_data.data.stream_cmd.ticks = htonl(stream_cmd.time_spec.ticks); + out_data.data.stream_cmd.ticks = htonl(stream_cmd.time_spec.get_ticks(get_master_clock_freq())); //set these to defaults, then change in the switch statement out_data.data.stream_cmd.continuous = 0; diff --git a/host/test/vrt_test.cpp b/host/test/vrt_test.cpp index 40116e110..939a61eb4 100644 --- a/host/test/vrt_test.cpp +++ b/host/test/vrt_test.cpp @@ -36,7 +36,8 @@ static void pack_and_unpack( num_header_words32, //output num_payload_words32, //input num_packet_words32, //output - packet_count //input + packet_count, //input + 100e6 ); uhd::rx_metadata_t metadata_out; @@ -51,7 +52,8 @@ static void pack_and_unpack( num_header_words32_out, //output num_payload_words32_out, //output num_packet_words32, //input - packet_count_out //output + packet_count_out, //output + 100e6 ); //check the the unpacked metadata is the same @@ -65,7 +67,7 @@ static void pack_and_unpack( BOOST_CHECK_EQUAL(metadata.has_time_spec, metadata_out.has_time_spec); if (metadata.has_time_spec and metadata_out.has_time_spec){ BOOST_CHECK_EQUAL(metadata.time_spec.secs, metadata_out.time_spec.secs); - BOOST_CHECK_EQUAL(metadata.time_spec.ticks, metadata_out.time_spec.ticks); + BOOST_CHECK_EQUAL(metadata.time_spec.nsecs, metadata_out.time_spec.nsecs); } } @@ -85,7 +87,7 @@ BOOST_AUTO_TEST_CASE(test_with_time_spec){ uhd::tx_metadata_t metadata; metadata.has_time_spec = true; metadata.time_spec.secs = 7; - metadata.time_spec.ticks = 2000; + metadata.time_spec.nsecs = 2000; pack_and_unpack(metadata, 500, 3); } @@ -95,6 +97,6 @@ BOOST_AUTO_TEST_CASE(test_with_sid_and_time_spec){ metadata.stream_id = 2; metadata.has_time_spec = true; metadata.time_spec.secs = 5; - metadata.time_spec.ticks = 1000; + metadata.time_spec.nsecs = 1000; pack_and_unpack(metadata, 600, 4); } -- cgit v1.2.3