All of lore.kernel.org
 help / color / mirror / Atom feed
From: Jiri Olsa <olsajiri@gmail.com>
To: Shung-Hsi Yu <shung-hsi.yu@suse.com>
Cc: bpf@vger.kernel.org, Alexei Starovoitov <ast@kernel.org>,
	Daniel Borkmann <daniel@iogearbox.net>,
	John Fastabend <john.fastabend@gmail.com>,
	Andrii Nakryiko <andrii@kernel.org>,
	Yonghong Song <yonghong.song@linux.dev>
Subject: Re: [PATCH bpf-next 2/2] bpf: verifier: use check_sub_overflow() to check for subtraction overflows
Date: Mon, 24 Jun 2024 09:15:48 +0200	[thread overview]
Message-ID: <ZnkdJCyFlENgSDS2@krava> (raw)
In-Reply-To: <20240623070324.12634-3-shung-hsi.yu@suse.com>

On Sun, Jun 23, 2024 at 03:03:20PM +0800, Shung-Hsi Yu wrote:

SNIP

> @@ -13428,15 +13409,16 @@ static void scalar_min_max_sub(struct bpf_reg_state *dst_reg,
>  	s64 smax_val = src_reg->smax_value;
>  	u64 umin_val = src_reg->umin_value;
>  	u64 umax_val = src_reg->umax_value;
> +	s64 smin_cur, smax_cur;
>  
> -	if (signed_sub_overflows(dst_reg->smin_value, smax_val) ||
> -	    signed_sub_overflows(dst_reg->smax_value, smin_val)) {
> +	if (check_sub_overflow(dst_reg->smin_value, smax_val, &smin_cur) ||
> +	    check_sub_overflow(dst_reg->smax_value, smin_val, &smax_cur)) {
>  		/* Overflow possible, we know nothing */
>  		dst_reg->smin_value = S64_MIN;
>  		dst_reg->smax_value = S64_MAX;
>  	} else {
> -		dst_reg->smin_value -= smax_val;
> -		dst_reg->smax_value -= smin_val;
> +		dst_reg->smin_value = smin_cur;
> +		dst_reg->smax_value = smax_cur;
>  	}
>  	if (dst_reg->umin_value < umax_val) {
>  		/* Overflow possible, we know nothing */
> -- 
> 2.45.2
> 
> 

could we use dst_reg->smin_* pointers directly as the sum pointer
arguments in check_add_overflow ? ditto for the check_sub_overflow
in the other change

jirka


---
diff --git a/kernel/bpf/verifier.c b/kernel/bpf/verifier.c
index 3f6be4923655..dbb99818e938 100644
--- a/kernel/bpf/verifier.c
+++ b/kernel/bpf/verifier.c
@@ -12720,26 +12720,6 @@ static int check_kfunc_call(struct bpf_verifier_env *env, struct bpf_insn *insn,
 	return 0;
 }
 
-static bool signed_add_overflows(s64 a, s64 b)
-{
-	/* Do the add in u64, where overflow is well-defined */
-	s64 res = (s64)((u64)a + (u64)b);
-
-	if (b < 0)
-		return res > a;
-	return res < a;
-}
-
-static bool signed_add32_overflows(s32 a, s32 b)
-{
-	/* Do the add in u32, where overflow is well-defined */
-	s32 res = (s32)((u32)a + (u32)b);
-
-	if (b < 0)
-		return res > a;
-	return res < a;
-}
-
 static bool signed_sub_overflows(s64 a, s64 b)
 {
 	/* Do the sub in u64, where overflow is well-defined */
@@ -13241,21 +13221,15 @@ static int adjust_ptr_min_max_vals(struct bpf_verifier_env *env,
 		 * added into the variable offset, and we copy the fixed offset
 		 * from ptr_reg.
 		 */
-		if (signed_add_overflows(smin_ptr, smin_val) ||
-		    signed_add_overflows(smax_ptr, smax_val)) {
+		if (check_add_overflow(smin_ptr, smin_val, &dst_reg->smin_value) ||
+		    check_add_overflow(smax_ptr, smax_val, &dst_reg->smax_value)) {
 			dst_reg->smin_value = S64_MIN;
 			dst_reg->smax_value = S64_MAX;
-		} else {
-			dst_reg->smin_value = smin_ptr + smin_val;
-			dst_reg->smax_value = smax_ptr + smax_val;
 		}
-		if (umin_ptr + umin_val < umin_ptr ||
-		    umax_ptr + umax_val < umax_ptr) {
+		if (check_add_overflow(umin_ptr, umin_val, &dst_reg->umin_value) ||
+		    check_add_overflow(umax_ptr, umax_val, &dst_reg->umax_value)) {
 			dst_reg->umin_value = 0;
 			dst_reg->umax_value = U64_MAX;
-		} else {
-			dst_reg->umin_value = umin_ptr + umin_val;
-			dst_reg->umax_value = umax_ptr + umax_val;
 		}
 		dst_reg->var_off = tnum_add(ptr_reg->var_off, off_reg->var_off);
 		dst_reg->off = ptr_reg->off;
@@ -13363,21 +13337,15 @@ static void scalar32_min_max_add(struct bpf_reg_state *dst_reg,
 	u32 umin_val = src_reg->u32_min_value;
 	u32 umax_val = src_reg->u32_max_value;
 
-	if (signed_add32_overflows(dst_reg->s32_min_value, smin_val) ||
-	    signed_add32_overflows(dst_reg->s32_max_value, smax_val)) {
+	if (check_add_overflow(dst_reg->s32_min_value, smin_val, &dst_reg->s32_min_value) ||
+	    check_add_overflow(dst_reg->s32_max_value, smax_val, &dst_reg->s32_max_value)) {
 		dst_reg->s32_min_value = S32_MIN;
 		dst_reg->s32_max_value = S32_MAX;
-	} else {
-		dst_reg->s32_min_value += smin_val;
-		dst_reg->s32_max_value += smax_val;
 	}
-	if (dst_reg->u32_min_value + umin_val < umin_val ||
-	    dst_reg->u32_max_value + umax_val < umax_val) {
+	if (check_add_overflow(dst_reg->u32_min_value, umin_val, &dst_reg->u32_min_value) ||
+	    check_add_overflow(dst_reg->u32_max_value, umax_val, &dst_reg->u32_max_value)) {
 		dst_reg->u32_min_value = 0;
 		dst_reg->u32_max_value = U32_MAX;
-	} else {
-		dst_reg->u32_min_value += umin_val;
-		dst_reg->u32_max_value += umax_val;
 	}
 }
 
@@ -13389,21 +13357,15 @@ static void scalar_min_max_add(struct bpf_reg_state *dst_reg,
 	u64 umin_val = src_reg->umin_value;
 	u64 umax_val = src_reg->umax_value;
 
-	if (signed_add_overflows(dst_reg->smin_value, smin_val) ||
-	    signed_add_overflows(dst_reg->smax_value, smax_val)) {
+	if (check_add_overflow(dst_reg->smin_value, smin_val, &dst_reg->smin_value) ||
+	    check_add_overflow(dst_reg->smax_value, smax_val, &dst_reg->smax_value)) {
 		dst_reg->smin_value = S64_MIN;
 		dst_reg->smax_value = S64_MAX;
-	} else {
-		dst_reg->smin_value += smin_val;
-		dst_reg->smax_value += smax_val;
 	}
-	if (dst_reg->umin_value + umin_val < umin_val ||
-	    dst_reg->umax_value + umax_val < umax_val) {
+	if (check_add_overflow(dst_reg->umin_value, umin_val, &dst_reg->umin_value) ||
+	    check_add_overflow(dst_reg->umax_value, umax_val, &dst_reg->umax_value)) {
 		dst_reg->umin_value = 0;
 		dst_reg->umax_value = U64_MAX;
-	} else {
-		dst_reg->umin_value += umin_val;
-		dst_reg->umax_value += umax_val;
 	}
 }
 

  reply	other threads:[~2024-06-24  7:15 UTC|newest]

Thread overview: 8+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2024-06-23  7:03 [PATCH bpf-next 0/2] Use overflow.h helpers to check for overflows Shung-Hsi Yu
2024-06-23  7:03 ` [PATCH bpf-next 1/2] bpf: verifier: use check_add_overflow() to check for addition overflows Shung-Hsi Yu
2024-06-24  3:38   ` Alexei Starovoitov
2024-06-24 15:26     ` Shung-Hsi Yu
2024-06-24 20:17       ` Alexei Starovoitov
2024-06-23  7:03 ` [PATCH bpf-next 2/2] bpf: verifier: use check_sub_overflow() to check for subtraction overflows Shung-Hsi Yu
2024-06-24  7:15   ` Jiri Olsa [this message]
2024-06-24 12:28     ` Shung-Hsi Yu

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=ZnkdJCyFlENgSDS2@krava \
    --to=olsajiri@gmail.com \
    --cc=andrii@kernel.org \
    --cc=ast@kernel.org \
    --cc=bpf@vger.kernel.org \
    --cc=daniel@iogearbox.net \
    --cc=john.fastabend@gmail.com \
    --cc=shung-hsi.yu@suse.com \
    --cc=yonghong.song@linux.dev \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.