Thread (3 messages) 3 messages, 2 authors, 2017-01-26

Re: IPv6-UDP 0x0000 checksum

From: Eric Dumazet <hidden>
Date: 2017-01-26 13:45:01
Also in: linux-wireless
Subsystem: networking [general], the rest · Maintainers: "David S. Miller", Eric Dumazet, Jakub Kicinski, Paolo Abeni, Linus Torvalds

On Thu, 2017-01-26 at 14:27 +0100, Johannes Berg wrote:
Hi,

It looks like right now we may have a hardware bug and accept 0x0000 as
valid, when the outcome of the calculation is 0xffff.

What do you think we should do about this?

We could ignore the issue entirely, since 0 wasn't ever supposed to be
sent anyway - but then we don't drop frames that we should drop. I
didn't manage to find the code in the IPv6/UDP stack that even does
that, but I assume it's there somewhere.

Alternatively, we could parse the packet to find the checksum inside,
and if it's 0 then don't report CHECKSUM_UNNECESSARY, but that seems
rather expensive/difficult due to the IPv6 variable header and all
that. If we wanted to go this route, are there any helper functions for
this?

Unfortunately, in the current devices, we neither have a complete
indication that the packet was even UDP-IPv6, nor do we have the raw
csum or anything like that. I think they're adding that to the next
hardware spin, but we probably need to address this issue now.

johannes
Hi Johannes

I am afraid information is missing.

Is this a xmit or rcv problem ?

I recently fixed an issue, could this be this ?

commit 4f2e4ad56a65f3b7d64c258e373cb71e8d2499f4
Author: Eric Dumazet [off-list ref]
Date:   Sat Oct 29 11:02:36 2016 -0700

    net: mangle zero checksum in skb_checksum_help()
    
    Sending zero checksum is ok for TCP, but not for UDP.
    
    UDPv6 receiver should by default drop a frame with a 0 checksum,
    and UDPv4 would not verify the checksum and might accept a corrupted
    packet.
    
    Simply replace such checksum by 0xffff, regardless of transport.
    
    This error was caught on SIT tunnels, but seems generic.
    
    Signed-off-by: Eric Dumazet [off-list ref]
    Cc: Maciej Żenczykowski [off-list ref]
    Cc: Willem de Bruijn [off-list ref]
    Acked-by: Maciej Żenczykowski [off-list ref]
    Signed-off-by: David S. Miller [off-list ref]
diff --git a/net/core/dev.c b/net/core/dev.c
index 820bac239738eb021354ac95ca5bbdff1840cb8e..eaad4c28069ff523ac784bf2dffd0acff82341a0 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -2484,7 +2484,7 @@ int skb_checksum_help(struct sk_buff *skb)
                        goto out;
        }
 
-       *(__sum16 *)(skb->data + offset) = csum_fold(csum);
+       *(__sum16 *)(skb->data + offset) = csum_fold(csum) ?: CSUM_MANGLED_0;
 out_set_summed:
        skb->ip_summed = CHECKSUM_NONE;
 out:
Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help