Sorry, here is the attached snippet.

Emanuele Tolomei

----- Messaggio originale -----
Da: "Emanuele Tolomei" <[email protected]>
A: "usrp-users" <[email protected]>
Cc: "Luigi Venuso" <[email protected]>, "gianluca.bafanelli" 
<[email protected]>
Inviato: Lunedì, 22 novembre 2021 9:21:45
Oggetto: Trouble with TwinRX frequency tuning

Hello,

I have an X300 with two TwinRX daughterboards, and I'm using UHD 3.13.1. I need 
channels synchronization for DOA calculation, so the channels share the same LO 
provided by channel 0.
The code for the LO sharing is the following:

m_MultiUsrp->set_time_unknown_pps(uhd::time_spec_t());
std::this_thread::sleep_for(std::chrono::seconds(1)); // wait for pps sync pulse
// Set channel specific settings
m_MultiUsrp->set_rx_lo_export_enabled(true, m_MultiUsrp->ALL_LOS, 0);
m_MultiUsrp->set_rx_lo_source("internal", m_MultiUsrp->ALL_LOS, 0);
m_MultiUsrp->set_rx_dc_offset(true, 0);
m_MultiUsrp->set_rx_lo_source("companion", m_MultiUsrp->ALL_LOS, 1);
m_MultiUsrp->set_rx_dc_offset(true, 1);
m_MultiUsrp->set_rx_lo_source("external", m_MultiUsrp->ALL_LOS, 2);
m_MultiUsrp->set_rx_dc_offset(true, 2);
m_MultiUsrp->set_rx_lo_source("external", m_MultiUsrp->ALL_LOS, 3);
m_MultiUsrp->set_rx_dc_offset(true, 3);

I am able to correctly tune the channels for the first time. However I'm having 
problems with changing the center frequency at runtime. When using the command 
set_rx_frequency() both in channel tuning and in channel synchronization, after 
a few loops the application crashes producing the error:

what():  EnvironmentError: IOError: Block ctrl (CE_01_Port_40) no response 
packet - AssertionError: bool(buff)
  in uint64_t ctrl_iface_impl<_endianness>::wait_for_ack(bool, double) [with 
uhd::endianness_t _endianness = (uhd::endianness_t)0u; uint64_t = long unsigned 
int]
  at /home/emanuele/uhd/host/lib/rfnoc/ctrl_iface.cpp:154

In particular, in the attached code of the ReceiveSamplesBurst function, if I 
comment between lines tagged with "INDICTED CODE LINES", the application runs 
without problems but the channels are not phase-synchronized.
How can I avoid this error while keeping the synchronization between all the 
four channels?

Thank you in advance.

Emanuele Tolomei

LEGAL DISCLAIMER:
The contents of this email and any transmitted files are confidential and 
intended solely for the use of the individual or entity to whom they are 
addressed. We hereby exclude any warranty and any liability as to the quality 
or accuracy of the contents of this email and any attached transmitted files. 
If you are not the intended recipient, be advised that you have received this 
email in error and that any use, dissemination, forwarding, printing or copying 
of this email is strictly prohibited. If you have received this email in error 
please contact the sender and delete the material from any computer.
int ReceiveSamplesBurst(std::vector<SamplesFrameTypeFc32> &vSampleFrame, uhd::rx_metadata_t &md, size_t nTotalNumSamps, double nGain, double nRxFrequency, double nSecondsInFuture)
{
  int nReceivedSamples, nReturnValue = DFRES_OK, idx = 0;

  // Impostazione Gain
  m_MultiUsrp->set_rx_gain(nGain,0);

  // Tune the channels to the desired frequency
  
  uhd::tune_result_t tune_resp = m_MultiUsrp->set_rx_freq(nRxFrequency,0);
  
  //set time on the master (mboard 0)
  struct timespec now;
  clock_gettime(CLOCK_REALTIME, &now);
  m_MultiUsrp->set_time_now(uhd::time_spec_t(now.tv_sec, now.tv_nsec /1e6), 0);
  uhd::time_spec_t usrp_time = m_MultiUsrp->get_time_now();

  uhd::tune_request_t tune_req;
  tune_req.rf_freq = nRxFrequency;
  tune_req.rf_freq_policy = uhd::tune_request_t::POLICY_MANUAL;
  tune_req.dsp_freq = tune_resp.actual_dsp_freq;
  tune_req.dsp_freq_policy = uhd::tune_request_t::POLICY_MANUAL;
  m_MultiUsrp->set_rx_freq(tune_req, 1);
  m_MultiUsrp->set_rx_freq(tune_req,2);
  m_MultiUsrp->set_rx_freq(tune_req,3);

  // Synchronize the tuned channels
  m_MultiUsrp->set_command_time(usrp_time + uhd::time_spec_t(0.01));

///////////////////////////////////////////////////////////////////  INDICTED CODE LINES //////////////////
  m_MultiUsrp->set_rx_freq(tune_req, 0);
  m_MultiUsrp->set_rx_freq(tune_req, 1);
  m_MultiUsrp->set_rx_freq(tune_req, 2);
  m_MultiUsrp->set_rx_freq(tune_req, 3);
///////////////////////////////////////////////////////////////////  INDICTED CODE LINES //////////////////

  m_MultiUsrp->clear_command_time();

  // Impostazione del ricevitore dello stream di campioni
  std::cout << "Begin streaming " <<  nTotalNumSamps <<  " samples, on " << nRxFrequency / 1e6 << " MHz, " << nSecondsInFuture << " seconds in the future..." << std::endl;
  uhd::stream_cmd_t stream_cmd(uhd::stream_cmd_t::STREAM_MODE_NUM_SAMPS_AND_DONE);
  stream_cmd.num_samps = nTotalNumSamps;
  stream_cmd.stream_now = false;
  if(nSecondsInFuture < 0.1) {
    std::cout << "Setting reasonable delay: " << nSecondsInFuture << std::endl;
    nSecondsInFuture = 0.5;
  }
  stream_cmd.time_spec = m_MultiUsrp->get_time_now() + uhd::time_spec_t(nSecondsInFuture);
  std::cout << "Time to stream: " << stream_cmd.time_spec.get_real_secs()/1.0e6 << "..." << std::endl; 
  m_RxStreamerFc32->issue_stream_cmd(stream_cmd); // tells all channels to stream
  
  // allocate buffers to receive with samples (one buffer per channel)
  const size_t samps_per_buff = m_RxStreamerFc32->get_max_num_samps();

  // create a vector of pointers to point to each of the channel buffers
  std::vector<std::complex<float> *> buff_ptrs(vSampleFrame.size());

  // the first call to recv() will block this many seconds before receiving
  double timeout = nSecondsInFuture + 1.0;  //timeout (delay before receive + padding)

  size_t num_acc_samps = 0; // number of accumulated samples
  while(num_acc_samps < nTotalNumSamps) {
    for (size_t i = 0; i < vSampleFrame.size(); i++) buff_ptrs[i] = &vSampleFrame[i].front()+num_acc_samps;
    
    // receive a single packet
    size_t num_rx_samps = m_RxStreamerFc32->recv(buff_ptrs, samps_per_buff, md, timeout);

    // use a small timeout for subsequent packets
    timeout = 0.1;

    if(md.error_code == uhd::rx_metadata_t::ERROR_CODE_TIMEOUT) {
      m_pCLogger->Log("ERRORE: Timeout su ricezione campioni", __FUNCTION__, LOG_LEVEL_TRACE);
      nReturnValue = DFRES_TIMEOUT;
      break;
    }
    if (md.error_code != uhd::rx_metadata_t::ERROR_CODE_NONE)
    {
      m_pCLogger->Log("ERRORE: Errore di ricezione: " + md.strerror(), __FUNCTION__, LOG_LEVEL_TRACE);
      switch (md.error_code)
      {
      case uhd::rx_metadata_t::ERROR_CODE_TIMEOUT:
        nReturnValue = DFRES_TIMEOUT;
        break;
      case uhd::rx_metadata_t::ERROR_CODE_LATE_COMMAND:
        nReturnValue = DFRES_TOO_LATE;
        break;
      case uhd::rx_metadata_t::ERROR_CODE_BROKEN_CHAIN:
      case uhd::rx_metadata_t::ERROR_CODE_OVERFLOW:
      case uhd::rx_metadata_t::ERROR_CODE_ALIGNMENT:
      case uhd::rx_metadata_t::ERROR_CODE_BAD_PACKET:
      default:
        nReturnValue = DFRES_CAPTURE_ERROR;
      };
      break;
    }

    num_acc_samps += num_rx_samps;
  }

  if (num_acc_samps < nTotalNumSamps) 
      std::cerr << "Receive timeout before all samples received..." << std::endl;
  
  return nReturnValue;
}

_______________________________________________
USRP-users mailing list -- [email protected]
To unsubscribe send an email to [email protected]

Reply via email to