⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 usrp_basic.cc

📁 这是用python语言写的一个数字广播的信号处理工具包。利用它
💻 CC
📖 第 1 页 / 共 3 页
字号:
/* -*- c++ -*- *//* * Copyright 2003,2004 Free Software Foundation, Inc. *  * This file is part of GNU Radio *  * GNU Radio 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, or (at your option) * any later version. *  * GNU Radio 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 GNU Radio; see the file COPYING.  If not, write to * the Free Software Foundation, Inc., 51 Franklin Street, * Boston, MA 02110-1301, USA. */#ifdef HAVE_CONFIG_H#include "config.h"#endif#include "usrp_basic.h"#include "usrp_prims.h"#include "usrp_interfaces.h"#include "fpga_regs_common.h"#include "fusb.h"#include <usb.h>#include <stdexcept>#include <assert.h>#include <math.h>#include <ad9862.h>#include <string.h>using namespace ad9862;#define NELEM(x) (sizeof (x) / sizeof (x[0]))// These set the buffer size used for each end point using the fast// usb interface.  The kernel ends up locking down this much memory.static const int FUSB_BUFFER_SIZE = fusb_sysconfig::default_buffer_size();static const int FUSB_BLOCK_SIZE = fusb_sysconfig::max_block_size();static const int FUSB_NBLOCKS    = FUSB_BUFFER_SIZE / FUSB_BLOCK_SIZE;static const double POLLING_INTERVAL = 0.1;	// seconds////////////////////////////////////////////////////////////////static struct usb_dev_handle *open_rx_interface (struct usb_device *dev){  struct usb_dev_handle *udh = usrp_open_rx_interface (dev);  if (udh == 0){    fprintf (stderr, "usrp_basic_rx: can't open rx interface\n");    usb_strerror ();  }  return udh;}static struct usb_dev_handle *open_tx_interface (struct usb_device *dev){  struct usb_dev_handle *udh = usrp_open_tx_interface (dev);  if (udh == 0){    fprintf (stderr, "usrp_basic_tx: can't open tx interface\n");    usb_strerror ();  }  return udh;}//////////////////////////////////////////////////////////////////////			usrp_basic//////////////////////////////////////////////////////////////////// Given://   CLKIN = 64 MHz//   CLKSEL pin = high //// These settings give us://   CLKOUT1 = CLKIN = 64 MHz//   CLKOUT2 = CLKIN = 64 MHz//   ADC is clocked at  64 MHz//   DAC is clocked at 128 MHzstatic unsigned char common_regs[] = {  REG_GENERAL,		0,  REG_DLL,		(DLL_DISABLE_INTERNAL_XTAL_OSC			 | DLL_MULT_2X			 | DLL_FAST),  REG_CLKOUT,		CLKOUT2_EQ_DLL_OVER_2,  REG_AUX_ADC_CLK,	AUX_ADC_CLK_CLK_OVER_4};usrp_basic::usrp_basic (int which_board, 			struct usb_dev_handle *			open_interface (struct usb_device *dev),			const std::string fpga_filename,			const std::string firmware_filename)  : d_udh (0),    d_usb_data_rate (16000000),	// SWAG, see below    d_bytes_per_poll ((int) (POLLING_INTERVAL * d_usb_data_rate)),    d_verbose (false){  /*   * SWAG: Scientific Wild Ass Guess.   *   * d_usb_data_rate is used only to determine how often to poll for over- and under-runs.   * We defualt it to 1/2  of our best case.  Classes derived from usrp_basic (e.g.,    * usrp_standard_tx and usrp_standard_rx) call set_usb_data_rate() to tell us the   * actual rate.  This doesn't change our throughput, that's determined by the signal   * processing code in the FPGA (which we know nothing about), and the system limits   * determined by libusb, fusb_*, and the underlying drivers.   */  memset (d_fpga_shadows, 0, sizeof (d_fpga_shadows));  usrp_one_time_init ();  if (!usrp_load_standard_bits (which_board, false, fpga_filename, firmware_filename))    throw std::runtime_error ("usrp_basic/usrp_load_standard_bits");  struct usb_device *dev = usrp_find_device (which_board);  if (dev == 0){    fprintf (stderr, "usrp_basic: can't find usrp[%d]\n", which_board);    throw std::runtime_error ("usrp_basic/usrp_find_device");  }  if (!(usrp_usrp_p(dev) && usrp_hw_rev(dev) >= 1)){    fprintf (stderr, "usrp_basic: sorry, this code only works with USRP revs >= 1\n");    throw std::runtime_error ("usrp_basic/bad_rev");  }  if ((d_udh = open_interface (dev)) == 0)    throw std::runtime_error ("usrp_basic/open_interface");  // initialize registers that are common to rx and tx  if (!usrp_9862_write_many_all (d_udh, common_regs, sizeof (common_regs))){    fprintf (stderr, "usrp_basic: failed to init common AD9862 regs\n");    throw std::runtime_error ("usrp_basic/init_9862");  }  _write_fpga_reg (FR_MODE, 0);		// ensure we're in normal mode  _write_fpga_reg (FR_DEBUG_EN, 0);	// disable debug outputs}usrp_basic::~usrp_basic (){  if (d_udh)    usb_close (d_udh);}boolusrp_basic::start (){  return true;		// nop}boolusrp_basic::stop (){  return true;		// nop}voidusrp_basic::set_usb_data_rate (int usb_data_rate){  d_usb_data_rate = usb_data_rate;  d_bytes_per_poll = (int) (usb_data_rate * POLLING_INTERVAL);}boolusrp_basic::write_aux_dac (int slot, int which_dac, int value){  return usrp_write_aux_dac (d_udh, slot, which_dac, value);}boolusrp_basic::read_aux_adc (int slot, int which_adc, int *value){  return usrp_read_aux_adc (d_udh, slot, which_adc, value);}intusrp_basic::read_aux_adc (int slot, int which_adc){  int	value;  if (!read_aux_adc (slot, which_adc, &value))    return READ_FAILED;  return value;}boolusrp_basic::write_eeprom (int i2c_addr, int eeprom_offset, const std::string buf){  return usrp_eeprom_write (d_udh, i2c_addr, eeprom_offset, buf.data (), buf.size ());}std::stringusrp_basic::read_eeprom (int i2c_addr, int eeprom_offset, int len){  if (len <= 0)    return "";  char buf[len];  if (!usrp_eeprom_read (d_udh, i2c_addr, eeprom_offset, buf, len))    return "";  return std::string (buf, len);}boolusrp_basic::write_i2c (int i2c_addr, const std::string buf){  return usrp_i2c_write (d_udh, i2c_addr, buf.data (), buf.size ());}std::stringusrp_basic::read_i2c (int i2c_addr, int len){  if (len <= 0)    return "";  char buf[len];  if (!usrp_i2c_read (d_udh, i2c_addr, buf, len))    return "";  return std::string (buf, len);}std::stringusrp_basic::serial_number(){  return usrp_serial_number(d_udh);}// ----------------------------------------------------------------boolusrp_basic::set_adc_offset (int which, int offset){  if (which < 0 || which > 3)    return false;  return _write_fpga_reg (FR_ADC_OFFSET_0 + which, offset);}boolusrp_basic::set_dac_offset (int which, int offset, int offset_pin){  if (which < 0 || which > 3)    return false;  int which_codec = which >> 1;  int tx_a = (which & 0x1) == 0;  int lo = ((offset & 0x3) << 6) | (offset_pin & 0x1);  int hi = (offset >> 2);  bool ok;  if (tx_a){    ok =  _write_9862 (which_codec, REG_TX_A_OFFSET_LO, lo);    ok &= _write_9862 (which_codec, REG_TX_A_OFFSET_HI, hi);  }  else {    ok =  _write_9862 (which_codec, REG_TX_B_OFFSET_LO, lo);    ok &= _write_9862 (which_codec, REG_TX_B_OFFSET_HI, hi);  }  return ok;}boolusrp_basic::set_adc_buffer_bypass (int which, bool bypass){  if (which < 0 || which > 3)    return false;  int codec = which >> 1;  int reg = (which & 1) == 0 ? REG_RX_A : REG_RX_B;  unsigned char cur_rx;  unsigned char cur_pwr_dn;  // If the input buffer is bypassed, we need to power it down too.  bool ok = _read_9862 (codec, reg, &cur_rx);  ok &= _read_9862 (codec, REG_RX_PWR_DN, &cur_pwr_dn);  if (!ok)    return false;  if (bypass){    cur_rx |= RX_X_BYPASS_INPUT_BUFFER;    cur_pwr_dn |= ((which & 1) == 0) ? RX_PWR_DN_BUF_A : RX_PWR_DN_BUF_B;  }  else {    cur_rx &= ~RX_X_BYPASS_INPUT_BUFFER;    cur_pwr_dn &= ~(((which & 1) == 0) ? RX_PWR_DN_BUF_A : RX_PWR_DN_BUF_B);  }  ok &= _write_9862 (codec, reg, cur_rx);  ok &= _write_9862 (codec, REG_RX_PWR_DN, cur_pwr_dn);  return ok;}// ----------------------------------------------------------------boolusrp_basic::_write_fpga_reg (int regno, int value){  if (d_verbose){    fprintf (stdout, "_write_fpga_reg(%3d, 0x%08x)\n", regno, value);    fflush (stdout);  }  if (regno >= 0 && regno < MAX_REGS)    d_fpga_shadows[regno] = value;  return usrp_write_fpga_reg (d_udh, regno, value);}boolusrp_basic::_write_fpga_reg_masked (int regno, int value, int mask){  //Only use this for registers who actually use a mask in the verilog firmware, like FR_RX_MASTER_SLAVE  //value is a 16 bits value and mask is a 16 bits mask  if (d_verbose){    fprintf (stdout, "_write_fpga_reg_masked(%3d, 0x%04x,0x%04x)\n", regno, value, mask);    fflush (stdout);  }  if (regno >= 0 && regno < MAX_REGS)    d_fpga_shadows[regno] = value;  return usrp_write_fpga_reg (d_udh, regno, (value & 0xffff) | ((mask & 0xffff)<<16));}boolusrp_basic::_read_fpga_reg (int regno, int *value){  return usrp_read_fpga_reg (d_udh, regno, value);}intusrp_basic::_read_fpga_reg (int regno){  int value;  if (!_read_fpga_reg (regno, &value))    return READ_FAILED;  return value;}boolusrp_basic::_write_9862 (int which_codec, int regno, unsigned char value){  if (0 && d_verbose){    // FIXME really want to enable logging in usrp_prims:usrp_9862_write    fprintf(stdout, "_write_9862(codec = %d, regno = %2d, val = 0x%02x)\n", which_codec, regno, value);    fflush(stdout);  }  return usrp_9862_write (d_udh, which_codec, regno, value);}boolusrp_basic::_read_9862 (int which_codec, int regno, unsigned char *value) const{  return usrp_9862_read (d_udh, which_codec, regno, value);}intusrp_basic::_read_9862 (int which_codec, int regno) const{  unsigned char value;  if (!_read_9862 (which_codec, regno, &value))    return READ_FAILED;  return value;}boolusrp_basic::_write_spi (int optional_header, int enables, int format, std::string buf){  return usrp_spi_write (d_udh, optional_header, enables, format,			 buf.data(), buf.size());}std::stringusrp_basic::_read_spi (int optional_header, int enables, int format, int len){  if (len <= 0)    return "";    char buf[len];  if (!usrp_spi_read (d_udh, optional_header, enables, format, buf, len))    return "";  return std::string (buf, len);}bool

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -