diff options
| author | Chengfeng Ye <nicoyip.dev@gmail.com> | 2026-10-13 17:05:00 +0800 |
|---|---|---|
| committer | Paolo Abeni <pabeni@redhat.com> | 2026-10-20 11:30:20 +0200 |
| commit | d06ae66516e1aaf023808912af6292aef09d46c3 (patch) | |
| tree | c0cfcf1cfc801647ab85041478530136234a47ec /include/linux | |
| parent | b6ef0d965fe8ce0ee4b4dcb58b3511f83003e42d (diff) | |
| download | linux-d06ae66516e1aaf023808912af6292aef09d46c3.tar.gz linux-d06ae66516e1aaf023808912af6292aef09d46c3.zip | |
l2tp: snapshot sequencing state when building transmit headers
Updates to send_seq from netlink, PPP setsockopt and receive-side
negotiation race with packet transmission. The header length is updated
separately, while transmit reads both fields repeatedly without
synchronization.
For example, transmit can push a ten-byte L2TPv2 header, then a concurrent
writer clears send_seq before the header builder reads it. The builder
writes only six bytes, leaving four bytes of uninitialized skb headroom
in the outgoing packet. The reverse mismatch overwrites the beginning of
the payload. A later hdr_len read can also make the UDP length disagree
with the skb length.
KCSAN reported:
BUG: KCSAN: data-race in l2tp_session_set_header_len / l2tp_xmit_skb
write to 0xffff888100d0944a of 2 bytes by task 116 on cpu 1:
l2tp_session_set_header_len+0x81/0xc0
l2tp_nl_cmd_session_modify+0x122/0x2c0
genl_family_rcv_msg_doit+0x170/0x1d0
read to 0xffff888100d0944a of 2 bytes by task 115 on cpu 0:
l2tp_xmit_skb+0x9c/0xc80
pppol2tp_sendmsg+0x21c/0x2a0
__sys_sendto+0x28c/0x2a0
The bug can lead to leak kernel base address for KASLR bypass, the
corresponding reproducer can be provided per request.
Initialize hdr_len to the maximum header size and leave it unchanged
when sequencing is toggled. Snapshot send_seq once per packet and use
that snapshot for the actual header length and header construction,
including the sequence flag. Use the same length for headroom, the header
push and the UDP length. PPP callers can safely reserve the maximum size;
L2TPv3 header sizes do not depend on sequencing.
Make send_seq a separate bool so READ_ONCE() and WRITE_ONCE() can be used
without sharing a bitfield storage unit with other configuration flags.
Preserve the netlink attribute's existing low-bit truncation.
Fixes: 3557baabf280 ("[L2TP]: PPP over L2TP driver core")
Cc: stable@vger.kernel.org
Assisted-by: GPT-6 Astra
Signed-off-by: Chengfeng Ye <nicoyip.dev@gmail.com>
Link: https://patch.msgid.link/20261013090500.1180376-1-nicoyip.dev@gmail.com
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
Diffstat (limited to 'include/linux')
0 files changed, 0 insertions, 0 deletions
