Skip to content

Conversation

@RalphExp
Copy link

@RalphExp RalphExp commented Aug 4, 2025

Recently, I started using this KCP-based project, and while testing over localhost (where packets are decoded locally and re-sent to another endpoint), I occasionally observe that the number of decoded/recovered packets exceeds the number of packets actually received. In some cases, although the counts match, the contents of the recovered packets appear to be truncated. I'm only using the FEC component from KCP and not KCP itself, but it seems to me that the FEC decoder should be usable independently.

During unit testing, I noticed that the value obtained from:

sz := binary.LittleEndian.Uint16(r)
is often larger than the length of the recovered slice r itself.

for example:
recoverd: [132 0 10 0 49 95 85 120 107 65 88 79 111 122 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0]

Here, sz = 132, which is clearly larger than the length of the packet.
The original test string is only 10 characters long: "1_UxkAXOoz" (I add a uint16 to specified it's length)

another example:
[102 0 7 0 49 95 79 107 114 68 112 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0]
for string "1_OkrDp"

If I add a defensive check like
if int(sz) <= len(r)
then such packets will be dropped. However, from what I can see, the packet contents appear to be fully and correctly recovered. If I don’t include this check, all of my test cases pass successfully, and I haven’t encountered any instances of incorrect recovery.

This leads me to believe that this part of the code logic might be problematic (or too strict), and I'm wondering whether the length calculation here should be revisited.

@RalphExp RalphExp changed the title kcpInput may drop correctly decoded packets udpsession may drop correctly decoded packets Aug 4, 2025
@xtaci
Copy link
Owner

xtaci commented Aug 5, 2025

For datashard:parityshard 3:2, suppose I have 3 data packets to send, and they have different length like 100, 101, 102 bytes, The FEC module have to extend the data shars and parity shards to [102 102 102]:[102 102](the longest possible one), and the length of packet is self explaining.

@RalphExp
Copy link
Author

RalphExp commented Aug 5, 2025

Hi, I’d like to explain my situation regarding the sz > len(r) issue in sess.go.

In my usage, I’m decoding packets of varying lengths independently. Unlike the usual KCP flow where packets tend to have uniform length because KCP waits to fill segments, my packets have different lengths.

According to the logic in sess.go, packets where sz is greater than len(r) (the decoded buffer length) are discarded. However, in many cases, I observe sz > len(r) but the content appears fully intact and correctly recovered. For example, in one case, sz equals 102, but the len(r) is only around 50 bytes.

This leads me to think that the strict length check might not be suitable for scenarios where FEC is used independently without the full KCP pipeline.

I would appreciate any advice on how to properly handle this case.

@xtaci
Copy link
Owner

xtaci commented Aug 5, 2025

Cannot get your point....

@xtaci
Copy link
Owner

xtaci commented Aug 5, 2025

btw, kcp have variable length, and FEC has nothing to do with kcp, FEC is in another layer. It simply encodes data with length.

@xtaci xtaci closed this Nov 5, 2025
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

Successfully merging this pull request may close these issues.

2 participants