[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Commit-gnuradio] r8496 - in usrp2/trunk/host: apps gr-usrp2 lib
From: |
jcorgan |
Subject: |
[Commit-gnuradio] r8496 - in usrp2/trunk/host: apps gr-usrp2 lib |
Date: |
Sun, 25 May 2008 19:36:47 -0600 (MDT) |
Author: jcorgan
Date: 2008-05-25 19:36:46 -0600 (Sun, 25 May 2008)
New Revision: 8496
Added:
usrp2/trunk/host/gr-usrp2/usrp2_source_raw.cc
usrp2/trunk/host/gr-usrp2/usrp2_source_raw.h
usrp2/trunk/host/lib/ring_buffer.h
usrp2/trunk/host/lib/sample_buffer.cc
usrp2/trunk/host/lib/sample_buffer.h
usrp2/trunk/host/lib/usrp2_basic_thread.cc
usrp2/trunk/host/lib/usrp2_basic_thread.h
usrp2/trunk/host/lib/usrp2_tune_result.h
Modified:
usrp2/trunk/host/apps/rx_streaming_samples.cc
usrp2/trunk/host/gr-usrp2/Makefile.am
usrp2/trunk/host/gr-usrp2/usrp2.i
usrp2/trunk/host/gr-usrp2/usrp2_source_base.cc
usrp2/trunk/host/gr-usrp2/usrp2_source_base.h
usrp2/trunk/host/gr-usrp2/usrp2_source_c.cc
usrp2/trunk/host/gr-usrp2/usrp2_source_c.h
usrp2/trunk/host/lib/Makefile.am
usrp2/trunk/host/lib/usrp2_basic.cc
usrp2/trunk/host/lib/usrp2_basic.h
Log:
Merged r8422:8478 from jcorgan/u2 into usrp2 trunk.
Modified: usrp2/trunk/host/apps/rx_streaming_samples.cc
===================================================================
--- usrp2/trunk/host/apps/rx_streaming_samples.cc 2008-05-26 01:22:16 UTC
(rev 8495)
+++ usrp2/trunk/host/apps/rx_streaming_samples.cc 2008-05-26 01:36:46 UTC
(rev 8496)
@@ -334,7 +334,7 @@
class file_writer *writer = new file_writer(ofd, rb);
writer->start_undetached();
- usrp2_tune_result tune_result;
+ usrp2_tune_result_sptr tune_result;
if (gain != GAIN_NOT_SET){
if (!u2->set_rx_gain(gain)){
@@ -343,9 +343,9 @@
}
}
- if (!u2->set_rx_freq(freq, &tune_result)){
+ if (!(tune_result = u2->set_rx_freq(freq))){
std::cerr << "set_rx_freq failed\n";
- return 1;
+ //return 1;
}
if (!u2->set_rx_decim(decim)){
Modified: usrp2/trunk/host/gr-usrp2/Makefile.am
===================================================================
--- usrp2/trunk/host/gr-usrp2/Makefile.am 2008-05-26 01:22:16 UTC (rev
8495)
+++ usrp2/trunk/host/gr-usrp2/Makefile.am 2008-05-26 01:36:46 UTC (rev
8496)
@@ -27,6 +27,7 @@
usrp2_sink_c.cc \
usrp2_source_base.cc \
usrp2_source_c.cc \
+ usrp2_source_raw.cc \
usrp2_table.cc
libgr_usrp2_la_LIBADD = \
@@ -36,7 +37,8 @@
usrp2_sink_base.h \
usrp2_sink_c.h \
usrp2_source_base.h \
- usrp2_source_c.h
+ usrp2_source_c.h \
+ usrp2_source_raw.h
noinst_HEADERS = \
usrp2_table.h
Modified: usrp2/trunk/host/gr-usrp2/usrp2.i
===================================================================
--- usrp2/trunk/host/gr-usrp2/usrp2.i 2008-05-26 01:22:16 UTC (rev 8495)
+++ usrp2/trunk/host/gr-usrp2/usrp2.i 2008-05-26 01:36:46 UTC (rev 8496)
@@ -29,8 +29,12 @@
#include "gnuradio_swig_bug_workaround.h" // mandatory bug fix
#include "usrp2_sink_c.h"
#include "usrp2_source_c.h"
+#include "usrp2_source_raw.h"
%}
+%include "../lib/usrp2_tune_result.h"
+%template(usrp2_tune_result_sptr) boost::shared_ptr<usrp2_tune_result>;
+
// ----------------------------------------------------------------
class usrp2_source_base : public gr_sync_block {
@@ -42,6 +46,13 @@
public:
~usrp2_source_base();
+ bool set_gain(double gain);
+ usrp2_tune_result_sptr set_freq(double frequency);
+ bool set_decim(int decimation_factor);
+ bool set_scale_iq(int scale_i, int scale_q);
+
+ float adc_rate() const;
+ int decim_rate() const;
};
// ----------------------------------------------------------------
@@ -64,6 +75,24 @@
// ----------------------------------------------------------------
+GR_SWIG_BLOCK_MAGIC(usrp2,source_raw)
+
+usrp2_source_raw_sptr
+usrp2_make_source_raw(const std::string &ifc="eth0", const std::string
&mac="")
+ throw (std::runtime_error);
+
+class usrp2_source_raw : public usrp2_source_base {
+
+protected:
+ usrp2_source_raw(const std::string &ifc, const std::string &mac);
+
+public:
+ ~usrp2_source_raw();
+
+};
+
+// ----------------------------------------------------------------
+
class usrp2_sink_base : public gr_sync_block {
protected:
Modified: usrp2/trunk/host/gr-usrp2/usrp2_source_base.cc
===================================================================
--- usrp2/trunk/host/gr-usrp2/usrp2_source_base.cc 2008-05-26 01:22:16 UTC
(rev 8495)
+++ usrp2/trunk/host/gr-usrp2/usrp2_source_base.cc 2008-05-26 01:36:46 UTC
(rev 8496)
@@ -31,6 +31,8 @@
#define USRP2_SOURCE_BASE_DEBUG 1
+#define SAMPLES_PER_PACKET 250
+
usrp2_source_base::usrp2_source_base(const std::string &name,
gr_io_signature_sptr output_signature,
const std::string &ifc,
@@ -66,12 +68,48 @@
}
bool
+usrp2_source_base::set_gain(double gain)
+{
+ return d_u2->set_rx_gain(gain);
+}
+
+usrp2_tune_result_sptr
+usrp2_source_base::set_freq(double frequency)
+{
+ return d_u2->set_rx_freq(frequency);
+}
+
+bool
+usrp2_source_base::set_decim(int decimation_factor)
+{
+ return d_u2->set_rx_decim(decimation_factor);
+}
+
+bool
+usrp2_source_base::set_scale_iq(int scale_i, int scale_q)
+{
+ return d_u2->set_rx_scale_iq(scale_i, scale_q);
+}
+
+float
+usrp2_source_base::adc_rate() const
+{
+ return d_u2->adc_rate();
+}
+
+int
+usrp2_source_base::decim_rate() const
+{
+ return d_u2->rx_decim_rate();
+}
+
+bool
usrp2_source_base::start()
{
if (USRP2_SOURCE_BASE_DEBUG)
std::cout << "usrp2_source_base: start" << std::endl;
- return true;
+ return d_u2->start_rx_streaming(SAMPLES_PER_PACKET);
}
bool
@@ -80,7 +118,7 @@
if (USRP2_SOURCE_BASE_DEBUG)
std::cout << "usrp2_source_base: stop" << std::endl;
- return true;
+ return d_u2->stop_rx();
}
usrp2_source_base::~usrp2_source_base ()
@@ -92,5 +130,14 @@
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)
{
- return noutput_items;
+ if (USRP2_SOURCE_BASE_DEBUG)
+ ::write(1, "w", 1);
+
+ uint32_t buffer[SAMPLES_PER_PACKET];
+ uint32_t flags = 0; // In the streaming mode that gr-usrp2 uses, these are
ignored
+
+ int n = d_u2->rx_samples(std::min(noutput_items, SAMPLES_PER_PACKET),
buffer, &flags);
+ copy_from_usrp2_buffer(buffer, output_items[0], n);
+
+ return n;
}
Modified: usrp2/trunk/host/gr-usrp2/usrp2_source_base.h
===================================================================
--- usrp2/trunk/host/gr-usrp2/usrp2_source_base.h 2008-05-26 01:22:16 UTC
(rev 8495)
+++ usrp2/trunk/host/gr-usrp2/usrp2_source_base.h 2008-05-26 01:36:46 UTC
(rev 8496)
@@ -37,16 +37,26 @@
throw (std::runtime_error);
usrp2_basic_sptr d_u2;
-
+
public:
~usrp2_source_base();
virtual bool start();
virtual bool stop();
+ bool set_gain(double gain);
+ usrp2_tune_result_sptr set_freq(double frequency);
+ bool set_decim(int decimation_factor);
+ bool set_scale_iq(int scale_i, int scale_q);
+
+ float adc_rate() const;
+ int decim_rate() const;
+
int work(int noutput_items,
gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items);
+
+ virtual void copy_from_usrp2_buffer(uint32_t *src, void *dst, int nsamples)
= 0;
};
#endif /* INCLUDED_USRP2_SOURCE_BASE_H */
Modified: usrp2/trunk/host/gr-usrp2/usrp2_source_c.cc
===================================================================
--- usrp2/trunk/host/gr-usrp2/usrp2_source_c.cc 2008-05-26 01:22:16 UTC (rev
8495)
+++ usrp2/trunk/host/gr-usrp2/usrp2_source_c.cc 2008-05-26 01:36:46 UTC (rev
8496)
@@ -26,7 +26,10 @@
#include <usrp2_source_c.h>
#include <gr_io_signature.h>
+#include <iostream>
+#define USRP2_SOURCE_C_DEBUG 1
+
usrp2_source_c_sptr
usrp2_make_source_c(const std::string &ifc,
const std::string &mac)
@@ -47,3 +50,14 @@
usrp2_source_c::~usrp2_source_c()
{
}
+
+void
+usrp2_source_c::copy_from_usrp2_buffer(uint32_t *src, void *dst, int nsamples)
+{
+ gr_complex *out = (gr_complex *)dst;
+ for (int i = 0; i < nsamples; i++) {
+ float re = (int16_t)(src[i] >> 16);
+ float im = (int16_t)(src[i] & 0xFFFF);
+ *out++ = gr_complex(re, im);
+ }
+}
Modified: usrp2/trunk/host/gr-usrp2/usrp2_source_c.h
===================================================================
--- usrp2/trunk/host/gr-usrp2/usrp2_source_c.h 2008-05-26 01:22:16 UTC (rev
8495)
+++ usrp2/trunk/host/gr-usrp2/usrp2_source_c.h 2008-05-26 01:36:46 UTC (rev
8496)
@@ -46,6 +46,8 @@
public:
~usrp2_source_c();
+
+ virtual void copy_from_usrp2_buffer(uint32_t *src, void *dst, int nsamples);
};
#endif /* INCLUDED_USRP2_SOURCE_C_H */
Copied: usrp2/trunk/host/gr-usrp2/usrp2_source_raw.cc (from rev 8478,
usrp2/branches/developers/jcorgan/u2/host/gr-usrp2/usrp2_source_raw.cc)
===================================================================
--- usrp2/trunk/host/gr-usrp2/usrp2_source_raw.cc
(rev 0)
+++ usrp2/trunk/host/gr-usrp2/usrp2_source_raw.cc 2008-05-26 01:36:46 UTC
(rev 8496)
@@ -0,0 +1,59 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2008 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 <usrp2_source_raw.h>
+#include <gr_io_signature.h>
+#include <iostream>
+
+usrp2_source_raw_sptr
+usrp2_make_source_raw(const std::string &ifc,
+ const std::string &mac)
+ throw (std::runtime_error)
+{
+ return usrp2_source_raw_sptr(new usrp2_source_raw(ifc, mac));
+}
+
+usrp2_source_raw::usrp2_source_raw(const std::string &ifc,
+ const std::string &mac)
+ throw (std::runtime_error)
+ : usrp2_source_base("usrp2_source_raw",
+ gr_make_io_signature(1, 1, sizeof(uint32_t)),
+ ifc, mac)
+{
+}
+
+usrp2_source_raw::~usrp2_source_raw()
+{
+}
+
+void
+usrp2_source_raw::copy_from_usrp2_buffer(uint32_t *src, void *dst, int
nsamples)
+{
+ uint32_t *out = (uint32_t *)dst;
+
+ for (int i = 0; i < nsamples; i++)
+ *out++ = src[i];
+}
Copied: usrp2/trunk/host/gr-usrp2/usrp2_source_raw.h (from rev 8478,
usrp2/branches/developers/jcorgan/u2/host/gr-usrp2/usrp2_source_raw.h)
===================================================================
--- usrp2/trunk/host/gr-usrp2/usrp2_source_raw.h
(rev 0)
+++ usrp2/trunk/host/gr-usrp2/usrp2_source_raw.h 2008-05-26 01:36:46 UTC
(rev 8496)
@@ -0,0 +1,53 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2008 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.
+ */
+
+#ifndef INCLUDED_USRP2_SOURCE_RAW_H
+#define INCLUDED_USRP2_SOURCE_RAW_H
+
+#include <usrp2_source_base.h>
+
+class usrp2_source_raw;
+typedef boost::shared_ptr<usrp2_source_raw> usrp2_source_raw_sptr;
+
+usrp2_source_raw_sptr
+usrp2_make_source_raw(const std::string &ifc="eth0",
+ const std::string &mac="")
+ throw (std::runtime_error);
+
+class usrp2_source_raw : public usrp2_source_base {
+
+private:
+ friend usrp2_source_raw_sptr
+ usrp2_make_source_raw(const std::string &ifc,
+ const std::string &mac) throw (std::runtime_error);
+
+protected:
+ usrp2_source_raw(const std::string &ifc="eth0",
+ const std::string &mac="") throw (std::runtime_error);
+
+public:
+ ~usrp2_source_raw();
+
+ virtual void copy_from_usrp2_buffer(uint32_t *src, void *dst, int nsamples);
+};
+
+#endif /* INCLUDED_USRP2_SOURCE_RAW_H */
Modified: usrp2/trunk/host/lib/Makefile.am
===================================================================
--- usrp2/trunk/host/lib/Makefile.am 2008-05-26 01:22:16 UTC (rev 8495)
+++ usrp2/trunk/host/lib/Makefile.am 2008-05-26 01:36:46 UTC (rev 8496)
@@ -31,8 +31,10 @@
gri_ethernet_pfring.cc \
gri_if_stats.cc \
gri_pktfilter.cc \
+ sample_buffer.cc \
strtod_si.c \
- usrp2_basic.cc
+ usrp2_basic.cc \
+ usrp2_basic_thread.cc
libpfring_la_SOURCES = \
pfring.c
@@ -46,6 +48,11 @@
gri_ethernet_pfring.h \
gri_if_stats.h \
gri_pktfilter.h \
+ ring_buffer.h \
+ sample_buffer.h \
strtod_si.h \
- usrp2_basic.h
+ usrp2_tune_result.h \
+ usrp2_basic.h \
+ usrp2_basic_thread.h
+MOSTLYCLEANFILES = *~ *.loT
Copied: usrp2/trunk/host/lib/ring_buffer.h (from rev 8478,
usrp2/branches/developers/jcorgan/u2/host/lib/ring_buffer.h)
===================================================================
--- usrp2/trunk/host/lib/ring_buffer.h (rev 0)
+++ usrp2/trunk/host/lib/ring_buffer.h 2008-05-26 01:36:46 UTC (rev 8496)
@@ -0,0 +1,89 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2008 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.
+ */
+
+#ifndef INCLUDED_RING_BUFFER_H
+#define INCLUDED_RING_BUFFER_H
+
+#include <vector>
+#include <cmath>
+
+template <class T>
+class ring_buffer
+{
+public:
+ ring_buffer(size_t nitems);
+
+ size_t space_available() const;
+ size_t items_available() const;
+ size_t size() const { return d_size; }
+
+ void write(size_t nitems, const T *items);
+ void read(size_t nitems, T *items);
+
+private:
+ size_t d_size;
+ size_t d_read_index;
+ size_t d_write_index;
+
+ std::vector<T> d_items;
+};
+
+template<class T>
+ring_buffer<T>::ring_buffer(size_t nitems)
+ : d_size(pow(2, ceil(log2(nitems+1)))),
+ d_read_index(0),
+ d_write_index(0),
+ d_items(d_size)
+{
+}
+
+template<class T>
+size_t ring_buffer<T>::items_available() const
+{
+ return (d_write_index-d_read_index) & (d_size-1);
+}
+
+template<class T>
+size_t ring_buffer<T>::space_available() const
+{
+ return d_size-items_available()-1;
+}
+
+template<class T>
+void ring_buffer<T>::read(size_t nitems, T *items)
+{
+ for (size_t i=0; i < nitems; i++) {
+ items[i] = d_items[d_read_index];
+ d_read_index = (d_read_index + 1) & (d_size-1);
+ }
+}
+
+template<class T>
+void ring_buffer<T>::write(size_t nitems, const T *items)
+{
+ for (size_t i=0; i < nitems; i++) {
+ d_items[d_write_index] = items[i];
+ d_write_index = (d_write_index+1) & (d_size-1);
+ }
+}
+
+#endif /* INCLUDED_RING_BUFFER_H */
Copied: usrp2/trunk/host/lib/sample_buffer.cc (from rev 8478,
usrp2/branches/developers/jcorgan/u2/host/lib/sample_buffer.cc)
===================================================================
--- usrp2/trunk/host/lib/sample_buffer.cc (rev 0)
+++ usrp2/trunk/host/lib/sample_buffer.cc 2008-05-26 01:36:46 UTC (rev
8496)
@@ -0,0 +1,94 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2008 Free Software Foundation, Inc.
+ *
+ * This program 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 of the License, or
+ * (at your option) any later version.
+ *
+ * This program 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 this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include "sample_buffer.h"
+#include <usrp2_eth_packet.h>
+#include <cstdio>
+#include <cassert>
+
+#define SAMPLE_BUFFER_DEBUG 0
+
+sample_buffer::sample_buffer(size_t nsamples, size_t ndescs)
+ : d_samples(nsamples),
+ d_descs(ndescs),
+ d_rx_remainder(0),
+ d_not_empty(&d_mutex),
+ d_not_full(&d_mutex)
+{
+}
+
+void
+sample_buffer::write(size_t nsamples, const uint32_t *samples, uint32_t flags)
+{
+ omni_mutex_lock l(d_mutex);
+
+ while (is_full_p())
+ d_not_full.wait();
+
+ sample_desc_t desc;
+ desc.nsamples = nsamples;
+ desc.flags = flags;
+ d_descs.write(1, &desc);
+ d_samples.write(nsamples, samples);
+
+ ::write(1, "e", 1); // enqueued
+ d_not_empty.signal();
+}
+
+size_t
+sample_buffer::read(size_t nmax, uint32_t *samples, uint32_t *flags)
+{
+ size_t count = 0, n = 0;
+
+ while (count < nmax) {
+ omni_mutex_lock l(d_mutex);
+ while (is_empty_p())
+ d_not_empty.wait();
+
+ // Try to read from leftover from last descriptor
+ if (d_rx_remainder > 0) {
+ n = std::min(d_rx_remainder, nmax-count);
+ d_rx_remainder -= n;
+ ::write(1, "p", 1); // partial read
+ }
+ else {
+ // Grab a descriptor out of the queue
+ sample_desc_t desc;
+ d_descs.read(1, &desc);
+ n = std::min(nmax-count, desc.nsamples);
+ d_rx_remainder = desc.nsamples-n;
+ if (flags)
+ *flags |= desc.flags;
+ ::write(1, "d", 1); // dequeue
+ }
+
+ d_samples.read(n, &samples[count]);
+ count += n;
+
+ d_not_full.signal();
+
+ if (flags && (*flags & U2P_TX_END_OF_BURST))
+ return count;
+ }
+
+ return count;
+}
Copied: usrp2/trunk/host/lib/sample_buffer.h (from rev 8478,
usrp2/branches/developers/jcorgan/u2/host/lib/sample_buffer.h)
===================================================================
--- usrp2/trunk/host/lib/sample_buffer.h (rev 0)
+++ usrp2/trunk/host/lib/sample_buffer.h 2008-05-26 01:36:46 UTC (rev
8496)
@@ -0,0 +1,87 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2008 Free Software Foundation, Inc.
+ *
+ * This program 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 of the License, or
+ * (at your option) any later version.
+ *
+ * This program 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 this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef INCLUDED_SAMPLE_BUFFER_H
+#define INCLUDED_SAMPLE_BUFFER_H
+
+#include "ring_buffer.h"
+#include <omnithread.h>
+
+typedef struct sample_desc
+{
+ size_t nsamples;
+ uint32_t flags;
+}
+sample_desc_t;
+
+typedef class sample_buffer
+{
+private:
+ ring_buffer<uint32_t> d_samples;
+ ring_buffer<sample_desc_t> d_descs;
+ size_t d_rx_remainder;
+
+ omni_mutex d_mutex;
+ omni_condition d_not_empty;
+ omni_condition d_not_full;
+
+public:
+ /*!
+ * Create a sample buffer that can hold at least nsamples of data and
+ * ndescs of descriptors.
+ */
+ sample_buffer(size_t nsamples, size_t ndescs);
+
+ /*!
+ * Write nsamples of data into buffer and associate flags with this range.
+ * If space is not available, calling thread will block until it is.
+ */
+ void write(size_t nsamples, const uint32_t *samples, uint32_t flags);
+
+ /*!
+ * Read no more than nsamples of data from buffer. If samples are available,
+ * read as many as possible until either a) nsamples is reached, or b) the
+ * associated flags for the range has U2P_TX_END_OF_BURST set. If no
samples at
+ * all are available, the calling thread will block until they are.
+ *
+ * Returns number of samples read and places the OR of the associated flags
+ * into the 'flags' parameter, if not NULL.
+ */
+ size_t read(size_t nmax, uint32_t *samples, uint32_t *flags);
+
+ /*!
+ * Returns true if there are no samples available for reading.
+ */
+ bool is_empty_p() const { return d_rx_remainder == 0 &&
+ d_descs.items_available() == 0; }
+
+ /*!
+ * Returns true if there is either no space available for samples OR there
+ * is no space available for enqueuing descriptors.
+ */
+ bool is_full_p() const { return d_descs.space_available() == 0 |
+ d_samples.space_available() == 0; }
+
+ /*!
+ * Returns sample space available if not full.
+ */
+ size_t space_available() const { return is_full_p() ? 0 :
d_samples.space_available(); }
+}
+sample_buffer_t;
+
+#endif /* INCLUDED_SAMPLE_BUFFER_H */
Modified: usrp2/trunk/host/lib/usrp2_basic.cc
===================================================================
--- usrp2/trunk/host/lib/usrp2_basic.cc 2008-05-26 01:22:16 UTC (rev 8495)
+++ usrp2/trunk/host/lib/usrp2_basic.cc 2008-05-26 01:36:46 UTC (rev 8496)
@@ -1,6 +1,6 @@
/* -*- c++ -*- */
/*
- * Copyright 2007 Free Software Foundation, Inc.
+ * Copyright 2007,2008 Free Software Foundation, Inc.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -20,14 +20,17 @@
#include "config.h"
#endif
#include "usrp2_basic.h"
+#include "usrp2_basic_thread.h"
#include "gri_ethernet.h"
#include "gri_ethernet_pfring.h" // FIXME
#include "gri_pktfilter.h"
#include <usrp2_types.h>
+#include <usrp2_eth_packet.h>
#include <iostream>
#include <stdexcept>
#include <math.h>
-#include <time.h> // debug
+#include <time.h>
+#include <errno.h>
#ifdef HAVE_SYS_SELECT_H
#include <sys/select.h>
@@ -54,6 +57,10 @@
#define MAX_PKTLEN 1512 // biggest thing USRP2 can swallow
// (14-byte ethernet hdr + 1500 byte payload)
+usrp2_tune_result::~usrp2_tune_result()
+{
+}
+
usrp2_basic_sptr
usrp2_make_basic(const std::string &ifc, const u2_mac_addr_t &addr)
{
@@ -61,7 +68,9 @@
}
usrp2_basic::usrp2_basic(const std::string &ifc, const u2_mac_addr_t &addr)
- : d_ethernet(new GRI_ETHERNET()), d_pf(0), d_seqno(0), d_next_rid(0)
+ : d_ethernet(new GRI_ETHERNET()), d_pf(0), d_seqno(0), d_next_rid(0),
+ d_rx_started(false), d_tx_started(false), d_thread(0),
+ d_rx_samples(65535, 255), d_tx_samples(65535, 255)
{
if (USRP2_BASIC_DEBUG)
std::cerr << "usrp2_basic: constructor" << std::endl;
@@ -262,9 +271,10 @@
return true;
}
-bool
-usrp2_basic::set_rx_freq(double freq, usrp2_tune_result *result)
+usrp2_tune_result_sptr
+usrp2_basic::set_rx_freq(double freq)
{
+ usrp2_tune_result_sptr result(new usrp2_tune_result());
uint8_t pktbuf[MAX_PKTLEN];
memset(pktbuf, 0, sizeof(pktbuf));
@@ -290,15 +300,11 @@
c->eop.len = sizeof(op_eop_t);
int len = std::max((size_t) MIN_PKTLEN, sizeof(command));
- if (d_ethernet->write_packet(c, len) != len)
- return false;
+ if (d_ethernet->write_packet(c, len) == len) {
+ // FIXME: wait for corresponding reply, set tune result members
+ }
- // FIXME wait for corresponding reply, etc.
-
- if (result)
- memset(result, 0, sizeof(*result));
-
- return true;
+ return result;
}
bool
@@ -332,6 +338,7 @@
// FIXME wait for corresponding reply, etc.
+ d_rx_decim = decimation_factor;
return true;
}
@@ -398,6 +405,9 @@
if (d_ethernet->write_packet(c, len) != len)
return false;
+ d_rx_started = true;
+ d_thread = new usrp2_basic_thread(this);
+ d_thread->start();
return true;
}
@@ -421,6 +431,10 @@
if (d_ethernet->write_packet(c, len) != len)
return false;
+ d_thread->stop();
+ d_rx_started = false;
+
+ d_thread = 0; // pthread derived objects delete themselves
return true;
}
@@ -582,31 +596,33 @@
}
int
-usrp2_basic::read_raw_samples(u2_eth_samples_t *pkt)
+usrp2_basic::read_raw_samples(u2_eth_samples_t *pkt, int nmax)
{
- int len = d_ethernet->read_packet(pkt, sizeof(*pkt));
- // printf("read_packet = %d\n", len);
+ int nmaxbytes = (nmax == -1) ? sizeof(*pkt) : nmax*sizeof(uint32_t) +
sizeof(u2_eth_packet_t);
+ int readsize = std::min(int(sizeof(*pkt)), nmaxbytes);
+ int len = d_ethernet->read_packet(pkt, readsize);
if (len <= 0)
return len;
// FIXME check channel
-
- // shouldn't happen
- if ((size_t) len < sizeof(u2_eth_packet_t))
+ if ((size_t) len < sizeof(u2_eth_packet_t)) {
+ printf("usrp2_basic::read_raw_samples: short read, len=%d\n", len);
return 0;
+ }
- // convert to samples
int r = (len - sizeof(u2_eth_packet_t)) / sizeof(uint32_t);
- // printf("read_raw_samples = %d\n", r);
+ if (USRP2_BASIC_DEBUG)
+ printf("usrp2_basic::read_raw_samples: nmax=%d nmaxbytes=%d readsize=%d
len=%d r=%d\n",
+ nmax, nmaxbytes, readsize, len, r);
return r;
}
int
-usrp2_basic::read_samples(u2_eth_samples_t *pkt)
+usrp2_basic::read_samples(u2_eth_samples_t *pkt, int nmax)
{
- int r = read_raw_samples(pkt);
+ int r = read_raw_samples(pkt, nmax);
#ifndef WORDS_BIGENDIAN
for (int i = 0; i < r; i++)
@@ -819,3 +835,93 @@
return memcmp(&a, &b, sizeof(u2_mac_addr_t)) == 0;
}
+void usrp2_basic::loop()
+{
+ fd_set read_fds, write_fds;
+ FD_ZERO(&read_fds);
+ FD_ZERO(&write_fds);
+
+ if (d_rx_started)
+ FD_SET(d_ethernet->fd(), &read_fds);
+ if (d_tx_started)
+ FD_SET(d_ethernet->fd(), &write_fds);
+
+ struct timeval timeout;
+ timeout.tv_sec = 0;
+ timeout.tv_usec = 100 * 1000; // 100 ms
+
+ ::write(1, "S", 1); // select
+ int r = select(d_ethernet->fd()+1, &read_fds, &write_fds, 0, &timeout);
+ if (r > 0) { // Socket available for read or for write
+ if (FD_ISSET(d_ethernet->fd(), &read_fds)) {
+ ::write(1, "r", 1); // data to read()
+ rx_frames();
+ }
+
+ if (FD_ISSET(d_ethernet->fd(), &write_fds)) {
+ ::write(1, "r", 1); // data to write()
+ tx_frames();
+ }
+ }
+ else if (r == 0) {
+ ::write(1, "T", 1); // socket timeout
+ return;
+ }
+ else {
+ if (errno == EINTR)
+ ::write(1, "I", 1); // interrupted system call
+ else
+ ::write(1, "!", 1); // error on socket
+ return;
+ }
+}
+
+void
+usrp2_basic::rx_frames()
+{
+ uint8_t pktbuf[MAX_PKTLEN];
+ memset(pktbuf, 0, sizeof(pktbuf));
+
+ int len;
+ while (1) {
+ len = d_ethernet->read_packet_dont_block(pktbuf, sizeof(pktbuf));
+ if (len < 0) {
+ ::write(1, "!", 1); // error
+ return;
+ }
+ else if (len == 0) {
+ ::write(1, "|", 1); // no more frames
+ return;
+ }
+ else if ((size_t)len < sizeof(u2_eth_packet_t)) {
+ ::write(1, "<", 1); // short frame
+ }
+ else
+ ::write(1, "R", 1); // rx ok
+
+ u2_eth_packet_t *p = (u2_eth_packet_t *)pktbuf;
+ if (u2p_chan(&p->fixed) == CONTROL_CHAN) {
+ ::write(1, "-", 1); // ignore (FIXME: multiple channels, control channel)
+ continue;
+ }
+
+ u2_eth_samples_t *s = (u2_eth_samples_t *)pktbuf;
+ size_t plen = (len-sizeof(s->hdrs))/sizeof(uint32_t);
+ if (d_rx_samples.space_available() < plen) {
+ ::write(1, "uO", 2); // overrun
+ return;
+ }
+
+ d_rx_samples.write(plen, (uint32_t *)(&s->samples[0]), 0);
+ }
+}
+
+void
+usrp2_basic::tx_frames()
+{
+}
+
+size_t usrp2_basic::rx_samples(size_t nmax, uint32_t *samples, uint32_t *flags)
+{
+ return d_rx_samples.read(nmax, samples, flags);
+}
Modified: usrp2/trunk/host/lib/usrp2_basic.h
===================================================================
--- usrp2/trunk/host/lib/usrp2_basic.h 2008-05-26 01:22:16 UTC (rev 8495)
+++ usrp2/trunk/host/lib/usrp2_basic.h 2008-05-26 01:36:46 UTC (rev 8496)
@@ -23,6 +23,8 @@
#include <boost/shared_ptr.hpp>
#include <vector>
#include "usrp2_eth_packet.h"
+#include "usrp2_tune_result.h"
+#include "sample_buffer.h"
class gri_ethernet;
class gri_ethernet_pfring;
@@ -30,35 +32,18 @@
#define GRI_ETHERNET gri_ethernet
-//! Provides detailed result of tuning request
-
-struct usrp2_tune_result
-{
- // RF frequency that corresponds to DC in the IF
- double baseband_freq;
-
- // frequency programmed into the DDC/DUC
- double dxc_freq;
-
- // residual frequency (typically < 0.01 Hz)
- double residual_freq;
-
- // is the spectrum inverted?
- bool spectrum_inverted;
-
- usrp2_tune_result()
- : baseband_freq(0), dxc_freq(0), residual_freq(0),
spectrum_inverted(false) {}
-};
-
class usrp2_basic;
typedef boost::shared_ptr<usrp2_basic> usrp2_basic_sptr;
+class usrp2_basic_thread;
+
usrp2_basic_sptr usrp2_make_basic(const std::string &ifc, const u2_mac_addr_t
&addr);
class usrp2_basic : public boost::noncopyable
{
private:
friend usrp2_basic_sptr usrp2_make_basic(const std::string &ifc, const
u2_mac_addr_t &addr);
+ friend class usrp2_basic_thread;
usrp2_basic(const std::string &ifc, const u2_mac_addr_t &addr);
GRI_ETHERNET *d_ethernet;
@@ -66,13 +51,24 @@
int d_seqno;
int d_next_rid;
u2_mac_addr_t d_addr;
+ int d_rx_decim;
+ bool d_rx_started;
+ bool d_tx_started;
+ usrp2_basic_thread *d_thread;
+ sample_buffer_t d_rx_samples;
+ sample_buffer_t d_tx_samples;
+
void init_et_hdrs(u2_eth_packet_t *p, const u2_mac_addr_t &dst);
void init_etf_hdrs(u2_eth_packet_t *p,
const u2_mac_addr_t &dst,
int word0_flags, int chan, uint32_t timestamp);
+ void loop();
+ void rx_frames();
+ void tx_frames();
+
public:
// ---- Static methods ----
@@ -130,7 +126,7 @@
* Rx configuration and control
*/
bool set_rx_gain(double gain);
- bool set_rx_freq(double frequency, usrp2_tune_result *result);
+ usrp2_tune_result_sptr set_rx_freq(double frequency);
bool set_rx_decim(int decimation_factor);
bool set_rx_scale_iq(int scale_i, int scale_q);
@@ -140,6 +136,7 @@
//! stop streaming Rx samples
bool stop_rx();
+ int rx_decim_rate() const { return d_rx_decim; }
/*
* Tx configuration and control
@@ -155,7 +152,7 @@
* \param pkt contains the raw (non-endian corrected) samples
* \returns number of valid samples in pkt.
*/
- int read_raw_samples(u2_eth_samples_t *pkt);
+ int read_raw_samples(u2_eth_samples_t *pkt, int nmax = -1);
/*!
* \brief Read native-endian samples from USRP2.
@@ -163,7 +160,7 @@
* \param pkt contains native-endian samples.
* \returns number of valid samples in pkt.
*/
- int read_samples(u2_eth_samples_t *pkt);
+ int read_samples(u2_eth_samples_t *pkt, int nmax = -1);
/*!
* \brief Write raw samples to USRP2.
@@ -193,6 +190,14 @@
/*!
+ * Receive at most nmax samples. Returns number of samples actually read,
+ * and places the OR of the sample ranges into the flags variable.
+ *
+ * FIXME: multiple channels
+ */
+ size_t rx_samples(size_t nmax, uint32_t *samples, uint32_t *flags);
+
+ /*!
* \brief Read FPGA's idea of time
*
* N.B., this interface will probably change.
@@ -205,14 +210,13 @@
//! Return frequency of master oscillator on USRP2.
- long fpga_master_clock_freq () const { return 100000000; } // 100e6
+ long fpga_master_clock_freq () const { return 100000000; } // 100e6
//! Return A/D sample rate
long adc_rate() const { return fpga_master_clock_freq(); }
//! Return D/A sample rate
long dac_rate() const { return fpga_master_clock_freq(); }
-
};
std::ostream& operator<<(std::ostream &os, const op_id_reply_t &x);
Copied: usrp2/trunk/host/lib/usrp2_basic_thread.cc (from rev 8478,
usrp2/branches/developers/jcorgan/u2/host/lib/usrp2_basic_thread.cc)
===================================================================
--- usrp2/trunk/host/lib/usrp2_basic_thread.cc (rev 0)
+++ usrp2/trunk/host/lib/usrp2_basic_thread.cc 2008-05-26 01:36:46 UTC (rev
8496)
@@ -0,0 +1,80 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2008 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 <usrp2_basic_thread.h>
+
+#define USRP2_BASIC_THREAD_DEBUG 1
+
+usrp2_basic_thread::usrp2_basic_thread(usrp2_basic *u2) :
+ omni_thread(NULL, PRIORITY_NORMAL),
+ d_u2(u2), d_keep_running(false)
+{
+ if (USRP2_BASIC_THREAD_DEBUG)
+ std::cout << "usrp2_basic_thread: constructor" << std::endl;
+}
+
+usrp2_basic_thread::~usrp2_basic_thread()
+{
+ if (USRP2_BASIC_THREAD_DEBUG)
+ std::cout << "usrp2_basic_thread: destructor" << std::endl;
+
+ if (d_keep_running)
+ stop();
+
+ // we don't own this, so don't delete
+ d_u2 = 0;
+}
+
+void usrp2_basic_thread::start()
+{
+ if (USRP2_BASIC_THREAD_DEBUG)
+ std::cout << "usrp2_basic_thread::start() "
+ << this << std::endl;
+ d_keep_running = true;
+ start_undetached();
+}
+
+void *
+usrp2_basic_thread::run_undetached(void *arg)
+{
+ // This is the first code to run in the new thread context.
+ while(d_keep_running)
+ d_u2->loop();
+
+ return 0;
+}
+
+void
+usrp2_basic_thread::stop()
+{
+ if (USRP2_BASIC_THREAD_DEBUG)
+ std::cout << "usrp2_basic_thread::stop() "
+ << this << std::endl;
+ d_keep_running = false;
+
+ void *dummy_status;
+ join(&dummy_status);
+}
Copied: usrp2/trunk/host/lib/usrp2_basic_thread.h (from rev 8478,
usrp2/branches/developers/jcorgan/u2/host/lib/usrp2_basic_thread.h)
===================================================================
--- usrp2/trunk/host/lib/usrp2_basic_thread.h (rev 0)
+++ usrp2/trunk/host/lib/usrp2_basic_thread.h 2008-05-26 01:36:46 UTC (rev
8496)
@@ -0,0 +1,46 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2008 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.
+ */
+
+#ifndef INCLUDED_USRP2_BASIC_THREAD_H
+#define INCLUDED_USRP2_BASIC_THREAD_H
+
+#include <omnithread.h>
+#include <usrp2_basic.h>
+#include <iostream>
+
+class usrp2_basic_thread : public omni_thread
+{
+private:
+ usrp2_basic *d_u2;
+ bool d_keep_running;
+
+public:
+ usrp2_basic_thread(usrp2_basic *u2);
+ ~usrp2_basic_thread();
+
+ void start();
+ void stop();
+
+ virtual void *run_undetached(void *arg);
+};
+
+#endif /* INCLUDED_USRP2_BASIC_THREAD_H */
Copied: usrp2/trunk/host/lib/usrp2_tune_result.h (from rev 8478,
usrp2/branches/developers/jcorgan/u2/host/lib/usrp2_tune_result.h)
===================================================================
--- usrp2/trunk/host/lib/usrp2_tune_result.h (rev 0)
+++ usrp2/trunk/host/lib/usrp2_tune_result.h 2008-05-26 01:36:46 UTC (rev
8496)
@@ -0,0 +1,46 @@
+/* -*- c++ -*- */
+/*
+ * Copyright 2008 Free Software Foundation, Inc.
+ *
+ * This program 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 of the License, or
+ * (at your option) any later version.
+ *
+ * This program 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 this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef INCLUDED_USRP2_TUNE_RESULT_H
+#define INCLUDED_USRP2_TUNE_RESULT_H
+
+#include <boost/shared_ptr.hpp>
+
+class usrp2_tune_result
+{
+public:
+ // RF frequency that corresponds to DC in the IF
+ double baseband_freq;
+
+ // frequency programmed into the DDC/DUC
+ double dxc_freq;
+
+ // residual frequency (typically < 0.01 Hz)
+ double residual_freq;
+
+ // is the spectrum inverted?
+ bool spectrum_inverted;
+
+ usrp2_tune_result()
+ : baseband_freq(0), dxc_freq(0), residual_freq(0),
spectrum_inverted(false) {}
+ ~usrp2_tune_result();
+};
+
+typedef boost::shared_ptr<usrp2_tune_result> usrp2_tune_result_sptr;
+
+#endif /* INCLUDED_USRP2_TUNE_RESULT_H */
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [Commit-gnuradio] r8496 - in usrp2/trunk/host: apps gr-usrp2 lib,
jcorgan <=