[PATCH net] 6lowpan: fix off-by-one in multicast context address compression

Yizhou Zhao posted 1 patch 1 week, 5 days ago
[PATCH net] 6lowpan: fix off-by-one in multicast context address compression
Posted by Yizhou Zhao 1 week, 5 days ago
The second memcpy in lowpan_iphc_mcast_ctx_addr_compress() uses
&data[1] as destination and &ipaddr->s6_addr[11] as source, but
both should be offset by one: &data[2] and &ipaddr->s6_addr[12]
respectively.

This off-by-one has two consequences:
1. data[1] is overwritten with s6_addr[11], corrupting the RIID
   field in the compressed multicast address
2. data[5] is never written, so uninitialized kernel stack memory
   is transmitted over the network via lowpan_push_hc_data(),
   leaking kernel stack contents

The correct inline data layout must match what the decompression
function lowpan_uncompress_multicast_ctx_daddr() expects:
  data[0..1] = s6_addr[1..2]  (flags/scope + RIID)
  data[2..5] = s6_addr[12..15] (group ID)

Also zero-initialize the data array as a defensive measure against
similar bugs in the future.

Fixes: 5609c185f24d ("6lowpan: iphc: add support for stateful compression")
Reported-by: Yizhou Zhao <zhaoyz24@mails.tsinghua.edu.cn>
Reported-by: Yuxiang Yang <yangyx22@mails.tsinghua.edu.cn>
Reported-by: Ao Wang <wangao@seu.edu.cn>
Reported-by: Xuewei Feng <fengxw06@126.com>
Reported-by: Qi Li <qli01@tsinghua.edu.cn>
Reported-by: Ke Xu <xuke@tsinghua.edu.cn>
Assisted-by: GLM:GLM-5.1
Signed-off-by: Yizhou Zhao <zhaoyz24@mails.tsinghua.edu.cn>
---
diff --git a/net/6lowpan/iphc.c b/net/6lowpan/iphc.c
index e116d30..37eaff3 100644
--- a/net/6lowpan/iphc.c
+++ b/net/6lowpan/iphc.c
@@ -1086,12 +1086,12 @@ static u8 lowpan_iphc_mcast_ctx_addr_compress(u8 **hc_ptr,
 					      const struct lowpan_iphc_ctx *ctx,
 					      const struct in6_addr *ipaddr)
 {
-	u8 data[6];
+	u8 data[6] = {};
 
 	/* flags/scope, reserved (RIID) */
 	memcpy(data, &ipaddr->s6_addr[1], 2);
 	/* group ID */
-	memcpy(&data[1], &ipaddr->s6_addr[11], 4);
+	memcpy(&data[2], &ipaddr->s6_addr[12], 4);
 	lowpan_push_hc_data(hc_ptr, data, 6);
 
 	return LOWPAN_IPHC_DAM_00;


--
2.43.0
Re: [PATCH net] 6lowpan: fix off-by-one in multicast context address compression
Posted by Alexander Aring 1 week ago
Hi,

On Wed, May 27, 2026 at 4:19 AM Yizhou Zhao
<zhaoyz24@mails.tsinghua.edu.cn> wrote:
>
> The second memcpy in lowpan_iphc_mcast_ctx_addr_compress() uses
> &data[1] as destination and &ipaddr->s6_addr[11] as source, but
> both should be offset by one: &data[2] and &ipaddr->s6_addr[12]
> respectively.
>
> This off-by-one has two consequences:
> 1. data[1] is overwritten with s6_addr[11], corrupting the RIID
>    field in the compressed multicast address
> 2. data[5] is never written, so uninitialized kernel stack memory
>    is transmitted over the network via lowpan_push_hc_data(),
>    leaking kernel stack contents
>
> The correct inline data layout must match what the decompression
> function lowpan_uncompress_multicast_ctx_daddr() expects:
>   data[0..1] = s6_addr[1..2]  (flags/scope + RIID)
>   data[2..5] = s6_addr[12..15] (group ID)
>
> Also zero-initialize the data array as a defensive measure against
> similar bugs in the future.
>
> Fixes: 5609c185f24d ("6lowpan: iphc: add support for stateful compression")
> Reported-by: Yizhou Zhao <zhaoyz24@mails.tsinghua.edu.cn>
> Reported-by: Yuxiang Yang <yangyx22@mails.tsinghua.edu.cn>
> Reported-by: Ao Wang <wangao@seu.edu.cn>
> Reported-by: Xuewei Feng <fengxw06@126.com>
> Reported-by: Qi Li <qli01@tsinghua.edu.cn>
> Reported-by: Ke Xu <xuke@tsinghua.edu.cn>
> Assisted-by: GLM:GLM-5.1
> Signed-off-by: Yizhou Zhao <zhaoyz24@mails.tsinghua.edu.cn>
> ---
> diff --git a/net/6lowpan/iphc.c b/net/6lowpan/iphc.c
> index e116d30..37eaff3 100644
> --- a/net/6lowpan/iphc.c
> +++ b/net/6lowpan/iphc.c
> @@ -1086,12 +1086,12 @@ static u8 lowpan_iphc_mcast_ctx_addr_compress(u8 **hc_ptr,
>                                               const struct lowpan_iphc_ctx *ctx,
>                                               const struct in6_addr *ipaddr)
>  {
> -       u8 data[6];
> +       u8 data[6] = {};
>
>         /* flags/scope, reserved (RIID) */
>         memcpy(data, &ipaddr->s6_addr[1], 2);
>         /* group ID */
> -       memcpy(&data[1], &ipaddr->s6_addr[11], 4);
> +       memcpy(&data[2], &ipaddr->s6_addr[12], 4);
>         lowpan_push_hc_data(hc_ptr, data, 6);
>
>         return LOWPAN_IPHC_DAM_00;

Looks good to me.

Acked-by: Alexander Aring <aahringo@redhat.com>

Thanks.

- Alex