Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Using the convolutional decoder in streaming mode? (Continuous decoder) #39

Open
Aang23 opened this issue Mar 1, 2021 · 5 comments
Open

Comments

@Aang23
Copy link

Aang23 commented Mar 1, 2021

Is there any way to utilize libcorrect as a continuous, streaming decoder simlar to the GNU Radio implementation?

In my current usecase, I am basically locking onto the right QPSK state of a signal based on BER calculations, decoding the stream data, and after the fact performing other operations such as deframing. I was looking into switching over to libcorrect for the decoder implementation, but from what I could see, there is no directly supported way of making it operate that way.

How would I go about doing so? I did take a look at the code, but I am not quite sure...

Thanks!

@SignalWhisperer
Copy link

SignalWhisperer commented Jun 16, 2021

Normally, the FEC is performed on the frame data, not on a continuous stream. When streaming, you usually end up cutting up your data into chunks. It's not impossible though, just unlikely that it was designed this way. Looking at the current implementation of libcorrect, it is mostly stateless, always expecting to go back to the initial state after every block of data. This means it will provide you with the flush bits (careful, there's a bug in libcorrect where it uses R*(K+1) instead of R*(K-1) to calculate the number of flush bits), and if you simply discard those bits, you can keep on processing. You will lose some "protection" at the boundaries though, since you won't have the previous data, but you can always add an overlap to the input and then discard it afterwards in the output.

@brian-armstrong
Copy link
Member

You caught my attention with the description of this bug ;) I tried to mimic libfec's behavior on this particular issue as I wanted to make sure the shim would work, and I did some testing of BER and various tail lengths until I got one that matched libfec's. It's been a bit tricky for me to find the "right" number of bits for this in literature. If you have sources that suggest it should change I'd be happy to change it though I wonder why this is libfec's behavior or if perhaps I did not actually match it correctly.

@SignalWhisperer
Copy link

With a constraint length of K, your convolutional encoder has K-1 memory states, so you need K-1 known bits to flush it out (we use zeros by convention). This is by design of the convolutional encoder. You can use more bits, but to be guaranteed to return to the zero state from any arbitrary state, you need a minimum of K-1 zeros inserted into the encoder. Every other zero bit after this would simply give you more zeros, and thus are not necessary.

I know MATLAB documentation mentions it: https://www.mathworks.com/help/comm/ref/vitdec.html
Search for "flush", you'll find it.

As for academic papers mentioning it, most of them are behind a paywall and I lost my access when I graduated. But if you take the typical example with a constraint length of K=3, and run through it by hand, you only need to add K-1 zeros to return to your initial zero state, or 2 in this case. The same holds true for any value of K.

@SignalWhisperer
Copy link

The more I think about it, the continuous FEC solution I gave is wrong. The internal state will most likely be wrong, even if you go back by a few bits. Because of the flushing to zero, I don't think it's doable with this library.

@brian-armstrong
Copy link
Member

It's not going to work with how things are currently implemented no, you would have the elide the flush. I wouldn't say it's incompatible though, there would just need to be a new API that doesn't flush.

It's not clear how one would get deterministic group delay from this though. Viterbi has a relatively cheap "add new bit" step and then a much more expensive step of scanning backward through time to pull out a message. The latter should be done relatively infrequently both to increase the probability of decoding the correct message and for performance concerns. Probably a new API could be added to control this.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants