l2tp: copy 4 more bytes to linear part if necessary [Linux 5.0]

l2tp: copy 4 more bytes to linear part if necessary [Linux 5.0]

This Linux kernel change "l2tp: copy 4 more bytes to linear part if necessary" is included in the Linux 5.0 release. This change is authored by Jacob Wen <jian.w.wen [at] oracle.com> on Thu Jan 31 15:18:56 2019 +0800. The commit for this change in Linux stable tree is 91c5247 (patch).

l2tp: copy 4 more bytes to linear part if necessary

The size of L2TPv2 header with all optional fields is 14 bytes.
l2tp_udp_recv_core only moves 10 bytes to the linear part of a
skb. This may lead to l2tp_recv_common read data outside of a skb.

This patch make sure that there is at least 14 bytes in the linear
part of a skb to meet the maximum need of l2tp_udp_recv_core and
l2tp_recv_common. The minimum size of both PPP HDLC-like frame and
Ethernet frame is larger than 14 bytes, so we are safe to do so.

Also remove L2TP_HDR_SIZE_NOSEQ, it is unused now.

Fixes: fd558d186df2 ("l2tp: Split pppol2tp patch into separate l2tp and ppp parts")
Suggested-by: Guillaume Nault <[email protected]>
Signed-off-by: Jacob Wen <[email protected]>
Acked-by: Guillaume Nault <[email protected]>
Signed-off-by: David S. Miller <[email protected]>

There are 5 lines of Linux source code added/deleted in this change. Code changes to Linux kernel are as follows.

 net/l2tp/l2tp_core.c | 5 ++---
 1 file changed, 2 insertions(+), 3 deletions(-)

diff --git a/net/l2tp/l2tp_core.c b/net/l2tp/l2tp_core.c
index dd5ba0c..fed6bec 100644
--- a/net/l2tp/l2tp_core.c
+++ b/net/l2tp/l2tp_core.c
@@ -83,8 +83,7 @@
 #define L2TP_SLFLAG_S     0x40000000
 #define L2TP_SL_SEQ_MASK   0x00ffffff

-#define L2TP_HDR_SIZE_SEQ      10
-#define L2TP_HDR_SIZE_NOSEQ        6
+#define L2TP_HDR_SIZE_MAX      14

 /* Default trace flags */
 #define L2TP_DEFAULT_DEBUG_FLAGS   0
@@ -808,7 +807,7 @@ static int l2tp_udp_recv_core(struct l2tp_tunnel *tunnel, struct sk_buff *skb)
    __skb_pull(skb, sizeof(struct udphdr));

    /* Short packet? */
-   if (!pskb_may_pull(skb, L2TP_HDR_SIZE_SEQ)) {
+   if (!pskb_may_pull(skb, L2TP_HDR_SIZE_MAX)) {
        l2tp_info(tunnel, L2TP_MSG_DATA,
              "%s: recv short packet (len=%d)\n",
              tunnel->name, skb->len);

Leave a Reply

Your email address will not be published. Required fields are marked *