Switching flow between two paths


Discuss-gnuradio mailing list
[email protected]
https://lists.gnu.org/mailman/listinfo/discuss-gnuradio

Hi Jeon,
in principle, your flow graph does make a lot of sense.
However, there’s one problem: GNU Radio is a series of tubes, so to
speak;
as you switch the “upstream” selector, there’s still items in the in-
and output buffers of the previously selected encoder.
Thus, you’d need to switch the downstream selector just the right amount
of items later; the problem here is that you get absolutely no relation
between “wall clock time” and the amount of items that have been
processed.

Exactly for problems like that GNU Radio has stream tags, which really
are just pieces of information logically “stuck” to a single item, as it
passes through the block chain[1][2]. Now, if the selector was able to
deal with such stream tags, you could just tell each selector to switch
its ports right after a specific item has passed. Sadly, the selector
can’t do that. You could implement that in C++ or python; however, that
might be a bit challenging, because this requires usage of the general
block type, which makes it harder to implement (you’ll need to build
some kind of state machine to be able to tell GNU Radio how many input
items you need on which input to produce the wanted amount of output).
For a quick implementation, I’d go a different route:

source -±-> custom_block0 —> encoder0 —> add →
±-> custom_block1 —> encoder1 ------^

you’d need to implement custom_block in python or C++, that would either
pass through items, just like the block does that comes out of
gr_modtool add -l python -t sync
or set the output items to 0. You’d toggle that behavior exactly at the
sample that you get a tag.

Of course, this has the downside of a unnecessary copy, encoding and
adding per sample, compared to a proper stream en/disabler, but it’d be
easier to implement, I’d say.

Greetings,
Marcus
[1] You’ll find a bit of instructional information in
https://gnuradio.org/redmine/projects/gnuradio/wiki/Guided_Tutorial_Programming_Topics#52-Stream-Tags
[2] Reference http://gnuradio.org/doc/doxygen/page_stream_tags.html

Maybe the matrix multiplier can be of use here. Try the corresponding
example in gr-blocks/examples.

M

On Mar 25, 2015, at 2:15, Marcus M. [email protected] wrote:

source -±-> custom_block0 —> encoder0 —> add →
±-> custom_block1 —> encoder1 ------^

you’d need to implement custom_block in python or C++, that would either
pass through items, just like the block does that comes out of
gr_modtool add -l python -t sync
or set the output items to 0. You’d toggle that behavior exactly at the
sample that you get a tag.

Note that if you don’t actually need the switch to happen at a specific
point in the stream, but you still want the switch to be atomic
(guaranteed not to drop or repeat any items), the existing
multiply_matrix block can do the switching in this flowgraph: it would
be configured with one input and two outputs, and setting the matrix to
either [[0, 1]] or [[1, 0]].

(Of course, the disadvantage of either of these strategies is that
you’re paying the CPU cost of both encoders all of the time.)


Kevin R. http://switchb.org/kpreid/

After thinking about it for a couple of days, I’ve decided not to use
two
separated RLL blocks.
Instead, I made a block as below:

In work() function:

get_tags_in_range(tags, 0, nitems_read(0),
nitems_read(0) + ninput_items[0],
pmt::mp(“rll_coding”));
RLL_CODE rll_code = (RLL_CODE)pmt::to_long(tags[0].value);

// … omitted trivial things

switch (rll_code) {
case RLLMANCHESTER:
for(int i = 0; i < ninput_items[0]; i++) {
out[2 * i] = !!in[i];
out[2 * i + 1] = !in[i];
}
break;
case RLL4B6B:
for(int i = 0; i < ninput_items[0] / 4; i += 4) {
int rll4B = 0;
for (int j = 0; j < 4; j++) {
// make four bits into one bytes
rll4B |= (in[i + j] & 1) << j;
}
for (int j = 0; j < 6; j++) {
// put six bits corresponding to rll4B
out[6 * i + j] = !!(rll4B6B[rll4B] & (1 << j));
}
}
break;
}

// mapping definition

const char rll4B6B[16] = {
0b011100, 0b101100, 0b110010, 0b011010,
0b101010, 0b110001, 0b011001, 0b101001,
0b100110, 0b010110, 0b001110, 0b100011,
0b010011, 0b100101, 0b010101, 0b001101
};

If the code are not formatted well and hard to read, please refer:
https://gist.github.com/gsongsong/f3e34991a55f29dac5d2
There might be some syntax violation and variable definitions missing, I
apologize for that.
And please note that each in[i] is either 0b00000000 or 0b00000001.

By using a tag, RLL coding scheme are not changing during the stream.
Currently, I haven’t built it and tested yet.

What do you think of it?

I will make some notes after build and test the entire system.

Regrads,
Jeon.

2015-03-26 23:17 GMT+09:00 Kevin R. [email protected]:

Dear, Marcus

Here’s my codes

include/rll.h: https://gist.github.com/gsongsong/07e28c797bb65572982b
lib/rll_impl.h: https://gist.github.com/gsongsong/615649f628262c44c8cf
lib/rll_impl.cc: https://gist.github.com/gsongsong/14e7bdab27216bbe7a17

Please excuses some typos and syntax violation if any.

Regards,
Jeon.

2015-03-27 16:30 GMT+09:00 Marcus Müller [email protected]:

Hi Jeon,

this looks like good code; it’s an excellent design choice to use a
tagged stream block here, where you’d want GNU Radio to make sure you
get the whole “packet” that you need to encode into a single work call.

I think it should work; of course, I’m not your computer :wink: . With the
existing tagged stream block framework, it should be quite
straightforward to define a python test case for this, so I’d encourage
you to actually test it!

Best regards,
Marcus

Hi Jeon,

could you paste the whole C++ file to the gist?
Basically, what I suspect is that you’re not checking whether
get_tags_in_range() produced a tag at all, or/and might have an error in
your state machine that stores the “current” coder.

Greetings,
Marcus

Dear, Marcus

Thank you for your advice.

I will test it as soon as possible after fixing another problem in the
entire module (not related with RLL.)
And will report the result on the discuss-gnuradio.

Regards,
Jeon.

2015-03-28 21:50 GMT+09:00 Marcus Müller [email protected]: