aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDimitri Stolnikov <horiz0n@gmx.net>2014-05-06 22:37:10 +0200
committerDimitri Stolnikov <horiz0n@gmx.net>2014-05-07 14:59:18 +0200
commitd94645c17c1d3a5ea0915d64d603b291d99f4874 (patch)
tree1fb0b45e851f82dd9126cd3c65c701361284ee19
parent16c32a9fe0cae142877166d23e43e607ad4969f3 (diff)
wip: dynamic signatureswip-signat
-rw-r--r--grc/gen_osmosdr_blocks.py26
-rw-r--r--lib/sink_impl.cc33
-rw-r--r--lib/source_impl.cc71
3 files changed, 110 insertions, 20 deletions
diff --git a/grc/gen_osmosdr_blocks.py b/grc/gen_osmosdr_blocks.py
index a10c871..c93ace6 100644
--- a/grc/gen_osmosdr_blocks.py
+++ b/grc/gen_osmosdr_blocks.py
@@ -26,7 +26,7 @@ MAIN_TMPL = """\
<category>$($sourk.title())s</category>
<throttle>1</throttle>
<import>import osmosdr</import>
- <make>osmosdr.$(sourk)( args="numchan=" + str(\$nchan) + " " + \$args )
+ <make>osmosdr.$(sourk)( args=\$args )
self.\$(id).set_sample_rate(\$sample_rate)
#for $n in range($max_nchan)
\#if \$nchan() > $n
@@ -69,6 +69,21 @@ self.\$(id).set_bandwidth(\$bw$(n), $n)
<key>fc32</key>
<opt>type:fc32</opt>
</option>
+ <option>
+ <name>Complex int16</name>
+ <key>sc16</key>
+ <opt>type:sc16</opt>
+ </option>
+ <option>
+ <name>Complex int8</name>
+ <key>sc8</key>
+ <opt>type:sc8</opt>
+ </option>
+ <option>
+ <name>Octet stream</name>
+ <key>s8</key>
+ <opt>type:s8</opt>
+ </option>
</param>
<param>
<name>Device Arguments</name>
@@ -132,8 +147,11 @@ While primarily being developed for the OsmoSDR hardware, this block as well sup
By using the osmocom $sourk block you can take advantage of a common software api in your application(s) independent of the underlying radio hardware.
-Output Type:
-This parameter controls the data type of the stream in gnuradio. Only complex float32 samples are supported at the moment.
+$(dir.title())put Type:
+This parameter controls the data type of the stream in gnuradio.
+Complex float32, Complex int16 and Complex int8 are available for UHD devices.
+Complex float32 and Octet stream are available for bladeRF sink.
+Complex float32 must be used for everything else.
Device Arguments:
The device argument is a comma delimited string used to locate devices on your system. Device arguments for multiple devices may be given by separating them with a space.
@@ -167,7 +185,7 @@ Num Channels:
Selects the total number of channels in this multi-device configuration. Required when specifying multiple device arguments.
Sample Rate:
-The sample rate is the number of samples per second output by this block on each channel.
+The sample rate is the number of samples per second on each channel.
Frequency:
The center frequency is the frequency the RF chain is tuned to.
diff --git a/lib/sink_impl.cc b/lib/sink_impl.cc
index 3f4db4b..9d3cdbe 100644
--- a/lib/sink_impl.cc
+++ b/lib/sink_impl.cc
@@ -64,7 +64,7 @@ osmosdr::sink::make( const std::string &args )
*/
sink_impl::sink_impl( const std::string &args )
: gr::hier_block2 ("sink_impl",
- args_to_io_signature(args),
+ gr::io_signature::make(1, 1, sizeof(gr_complex)),
gr::io_signature::make(0, 0, 0)),
_sample_rate(NAN)
{
@@ -129,6 +129,10 @@ sink_impl::sink_impl( const std::string &args )
throw std::runtime_error("No supported devices found to pick from.");
}
+ int min_streams = 0, max_streams = 0;
+ std::vector<int> stream_items;
+ std::vector< gr::basic_block_sptr > blocks;
+
BOOST_FOREACH(std::string arg, arg_list) {
dict_t dict = params_to_dict(arg);
@@ -161,15 +165,36 @@ sink_impl::sink_impl( const std::string &args )
if ( iface != NULL && long(block.get()) != 0 ) {
_devs.push_back( iface );
+ blocks.push_back( block );
- for (size_t i = 0; i < iface->get_num_channels(); i++) {
- connect(self(), channel++, block, i);
- }
+ min_streams += block->input_signature()->min_streams();
+ max_streams += block->input_signature()->max_streams();
+
+ if ( stream_items.empty() )
+ stream_items.push_back( block->input_signature()->sizeof_stream_item(0) );
+
+// BOOST_FOREACH(int size, block->input_signature()->sizeof_stream_items())
+// {
+// stream_items.push_back( size );
+// }
} else if ( (iface != NULL) || (long(block.get()) != 0) )
throw std::runtime_error("Eitner iface or block are NULL.");
}
+ set_input_signature( gr::io_signature::makev( min_streams,
+ max_streams,
+ stream_items ) );
+
+ for (size_t k = 0; k < _devs.size(); k++)
+ {
+ gr::basic_block_sptr block = blocks[k];
+
+ for (size_t i = 0; i < _devs[k]->get_num_channels(); i++) {
+ connect(self(), channel++, block, i);
+ }
+ }
+
if (!_devs.size())
throw std::runtime_error("No devices specified via device arguments.");
#ifdef WORKAROUND_GR_HIER_BLOCK2_BUG
diff --git a/lib/source_impl.cc b/lib/source_impl.cc
index 1e9af47..2e5f876 100644
--- a/lib/source_impl.cc
+++ b/lib/source_impl.cc
@@ -99,7 +99,7 @@ osmosdr::source::make( const std::string &args )
source_impl::source_impl( const std::string &args )
: gr::hier_block2 ("source_impl",
gr::io_signature::make(0, 0, 0),
- args_to_io_signature(args)),
+ gr::io_signature::make(1, 1, sizeof(gr_complex))),
_sample_rate(NAN)
{
size_t channel = 0;
@@ -217,6 +217,10 @@ source_impl::source_impl( const std::string &args )
throw std::runtime_error("No supported devices found to pick from.");
}
+ int min_streams = 0, max_streams = 0;
+ std::vector<int> stream_items;
+ std::vector< gr::basic_block_sptr > blocks;
+
BOOST_FOREACH(std::string arg, arg_list) {
dict_t dict = params_to_dict(arg);
@@ -310,29 +314,72 @@ source_impl::source_impl( const std::string &args )
if ( iface != NULL && long(block.get()) != 0 ) {
_devs.push_back( iface );
+ blocks.push_back( block );
+
+ min_streams += block->output_signature()->min_streams();
+ max_streams += block->output_signature()->max_streams();
+
+ BOOST_FOREACH(int size, block->output_signature()->sizeof_stream_items())
+ {
+ stream_items.push_back( size );
+ }
+ } else if ( (iface != NULL) || (long(block.get()) != 0) )
+ throw std::runtime_error("Eitner iface or block are NULL.");
- for (size_t i = 0; i < iface->get_num_channels(); i++) {
+ }
+
+ std::cerr << min_streams << " " << max_streams << " { ";
+ for ( size_t i = 0; i < stream_items.size(); ++i )
+ std::cerr << stream_items[i] << " ";
+ std::cerr << "}" << std::endl;
+
+ set_output_signature( gr::io_signature::makev( min_streams,
+ max_streams,
+ stream_items ) );
+
+ for (size_t k = 0; k < _devs.size(); k++)
+ {
+ gr::basic_block_sptr block = blocks[k];
+
+ for (int i = 0; i < block->output_signature()->max_streams(); i++) {
#ifdef HAVE_IQBALANCE
+#if 0
gr::iqbalance::optimize_c::sptr iq_opt = gr::iqbalance::optimize_c::make( 0 );
gr::iqbalance::fix_cc::sptr iq_fix = gr::iqbalance::fix_cc::make();
- connect(block, i, iq_fix, 0);
- connect(iq_fix, 0, self(), channel++);
+ std::cerr << block->output_signature()->sizeof_stream_item(i) << " "
+ << iq_fix->input_signature()->sizeof_stream_item(0) << " ";
- connect(block, i, iq_opt, 0);
- msg_connect(iq_opt, "iqbal_corr", iq_fix, "iqbal_corr");
+ if ( block->output_signature()->sizeof_stream_item(i) ==
+ iq_fix->input_signature()->sizeof_stream_item(0) )
+ {
+ connect(block, i, iq_fix, 0);
+ connect(iq_fix, 0, self(), channel++);
- _iq_opt.push_back( iq_opt.get() );
- _iq_fix.push_back( iq_fix.get() );
+ connect(block, i, iq_opt, 0);
+ msg_connect(iq_opt, "iqbal_corr", iq_fix, "iqbal_corr");
+
+ _iq_opt.push_back( iq_opt.get() );
+ _iq_fix.push_back( iq_fix.get() );
+ }
+ else
+#endif
+ {
+// std::cerr << "Signatures don't match, bypassing gr::iqbalance on channel "
+// << channel << std::endl;
+
+ std::cerr << "connect" << k << ": out" << i << " to in" << channel << std::endl;
+
+ connect(block, i, self(), channel++);
+ }
#else
connect(block, i, self(), channel++);
#endif
- }
- } else if ( (iface != NULL) || (long(block.get()) != 0) )
- throw std::runtime_error("Eitner iface or block are NULL.");
-
+ }
}
+ std::cerr << "connect passed" << std::endl;
+
if (!_devs.size())
throw std::runtime_error("No devices specified via device arguments.");
#ifdef WORKAROUND_GR_HIER_BLOCK2_BUG