The value of an arithmetic expression "n * id.data" is subject
to possible overflow due to a failure to cast operands to a larger data
type before performing arithmetic. Added cast of first operand to u64
for avoiding overflow.
Found by Linux Verification Center (linuxtesting.org) with SVACE.
Fixes: 2adc6edcaec0 ("ethtool: fix error handling in ethtool_phys_id")
Signed-off-by: Maxim Korotkov <redacted>
---
net/ethtool/ioctl.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
@@ -2007,7 +2007,7 @@ static int ethtool_phys_id(struct net_device *dev, void __user *useraddr)}else{/* Driver expects to be called at twice the frequency in rc */intn=rc*2,interval=HZ/n;-u64count=n*id.data,i=0;+u64count=(u64)n*id.data,i=0;do{rtnl_lock();
From: Andrew Lunn <andrew@lunn.ch> Date: 2022-11-21 14:13:42
On Mon, Nov 21, 2022 at 10:56:18AM +0300, Maxim Korotkov wrote:
quoted hunk
The value of an arithmetic expression "n * id.data" is subject
to possible overflow due to a failure to cast operands to a larger data
type before performing arithmetic. Added cast of first operand to u64
for avoiding overflow.
Found by Linux Verification Center (linuxtesting.org) with SVACE.
Fixes: 2adc6edcaec0 ("ethtool: fix error handling in ethtool_phys_id")
Signed-off-by: Maxim Korotkov <redacted>
---
net/ethtool/ioctl.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
@@ -2007,7 +2007,7 @@ static int ethtool_phys_id(struct net_device *dev, void __user *useraddr)}else{/* Driver expects to be called at twice the frequency in rc */intn=rc*2,interval=HZ/n;-u64count=n*id.data,i=0;+u64count=(u64)n*id.data,i=0;
How about moving the code around a bit, change n to a u64 and drop the
cast? Does this look correct?
int interval = HZ / rc / 2;
u64 n = rc * 2;
u64 count = n * id.data;
i = 0;
I just don't like casts, they suggest the underlying types are wrong,
so should fix that, not add a cast.
Andrew
From: Alexander Lobakin <hidden> Date: 2022-11-21 15:11:18
From: Andrew Lunn <andrew@lunn.ch>
Date: Mon, 21 Nov 2022 15:10:18 +0100
On Mon, Nov 21, 2022 at 10:56:18AM +0300, Maxim Korotkov wrote:
quoted
The value of an arithmetic expression "n * id.data" is subject
to possible overflow due to a failure to cast operands to a larger data
type before performing arithmetic. Added cast of first operand to u64
for avoiding overflow.
Found by Linux Verification Center (linuxtesting.org) with SVACE.
Fixes: 2adc6edcaec0 ("ethtool: fix error handling in ethtool_phys_id")
Signed-off-by: Maxim Korotkov <redacted>
---
net/ethtool/ioctl.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
@@ -2007,7 +2007,7 @@ static int ethtool_phys_id(struct net_device *dev, void __user *useraddr)}else{/* Driver expects to be called at twice the frequency in rc */intn=rc*2,interval=HZ/n;-u64count=n*id.data,i=0;+u64count=(u64)n*id.data,i=0;
How about moving the code around a bit, change n to a u64 and drop the
cast? Does this look correct?
int interval = HZ / rc / 2;
u64 n = rc * 2;
u64 count = n * id.data;
i = 0;
I just don't like casts, they suggest the underlying types are wrong,
so should fix that, not add a cast.
This particular one is absolutely fine. When you want to multiply
u32 by u32, you always need a cast, otherwise the result will be
truncated. mul_u32_u32() does it the very same way[0].
From: Jakub Kicinski <kuba@kernel.org> Date: 2022-11-21 20:13:08
On Mon, 21 Nov 2022 10:56:18 +0300 Maxim Korotkov wrote:
Found by Linux Verification Center (linuxtesting.org) with SVACE.
Fixes: 2adc6edcaec0 ("ethtool: fix error handling in ethtool_phys_id")
I'm leaning towards dropping the fixes tag, and applying to -next.
Drivers returning high enough rc to cause an overflow seems theoretical,
and is pretty harmless. Please LMK if I'm missing something.
From: "Keller, Jacob E" <jacob.e.keller@intel.com> Date: 2022-11-21 21:30:25
-----Original Message-----
From: Alexander Lobakin <redacted>
Sent: Monday, November 21, 2022 7:03 AM
To: Andrew Lunn <andrew@lunn.ch>
Cc: Lobakin, Alexandr <redacted>; Maxim Korotkov
[off-list ref]; David S. Miller [off-list ref]; Eric
Dumazet [off-list ref]; Jakub Kicinski [off-list ref]; Paolo
Abeni [off-list ref]; Guangbin Huang
[off-list ref]; Tom Rix [off-list ref]; Marco Bonelli
[off-list ref]; Edward Cree [off-list ref];
netdev@vger.kernel.org; linux-kernel@vger.kernel.org; lvc-
project@linuxtesting.org
Subject: Re: [PATCH] ethtool: avoiding integer overflow in ethtool_phys_id()
From: Andrew Lunn <andrew@lunn.ch>
Date: Mon, 21 Nov 2022 15:10:18 +0100
quoted
On Mon, Nov 21, 2022 at 10:56:18AM +0300, Maxim Korotkov wrote:
quoted
The value of an arithmetic expression "n * id.data" is subject
to possible overflow due to a failure to cast operands to a larger data
type before performing arithmetic. Added cast of first operand to u64
for avoiding overflow.
Found by Linux Verification Center (linuxtesting.org) with SVACE.
Fixes: 2adc6edcaec0 ("ethtool: fix error handling in ethtool_phys_id")
Signed-off-by: Maxim Korotkov <redacted>
---
net/ethtool/ioctl.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
@@ -2007,7 +2007,7 @@ static int ethtool_phys_id(struct net_device *dev,
void __user *useraddr)
quoted
quoted
} else {
/* Driver expects to be called at twice the frequency in rc */
int n = rc * 2, interval = HZ / n;
- u64 count = n * id.data, i = 0;
+ u64 count = (u64)n * id.data, i = 0;
How about moving the code around a bit, change n to a u64 and drop the
cast? Does this look correct?
int interval = HZ / rc / 2;
u64 n = rc * 2;
u64 count = n * id.data;
i = 0;
I just don't like casts, they suggest the underlying types are wrong,
so should fix that, not add a cast.
This particular one is absolutely fine. When you want to multiply
u32 by u32, you always need a cast, otherwise the result will be
truncated. mul_u32_u32() does it the very same way[0].
Ok, I'll replace cast to macro in patch V2
On 22.11.2022 00:30, Keller, Jacob E wrote:
quoted
-----Original Message-----
From: Alexander Lobakin <redacted>
Sent: Monday, November 21, 2022 7:03 AM
To: Andrew Lunn <andrew@lunn.ch>
Cc: Lobakin, Alexandr <redacted>; Maxim Korotkov
[off-list ref]; David S. Miller [off-list ref]; Eric
Dumazet [off-list ref]; Jakub Kicinski [off-list ref]; Paolo
Abeni [off-list ref]; Guangbin Huang
[off-list ref]; Tom Rix [off-list ref]; Marco Bonelli
[off-list ref]; Edward Cree [off-list ref];
netdev@vger.kernel.org; linux-kernel@vger.kernel.org; lvc-
project@linuxtesting.org
Subject: Re: [PATCH] ethtool: avoiding integer overflow in ethtool_phys_id()
From: Andrew Lunn <andrew@lunn.ch>
Date: Mon, 21 Nov 2022 15:10:18 +0100
quoted
On Mon, Nov 21, 2022 at 10:56:18AM +0300, Maxim Korotkov wrote:
quoted
The value of an arithmetic expression "n * id.data" is subject
to possible overflow due to a failure to cast operands to a larger data
type before performing arithmetic. Added cast of first operand to u64
for avoiding overflow.
Found by Linux Verification Center (linuxtesting.org) with SVACE.
Fixes: 2adc6edcaec0 ("ethtool: fix error handling in ethtool_phys_id")
Signed-off-by: Maxim Korotkov <redacted>
---
net/ethtool/ioctl.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
@@ -2007,7 +2007,7 @@ static int ethtool_phys_id(struct net_device *dev,
void __user *useraddr)
quoted
quoted
} else {
/* Driver expects to be called at twice the frequency in rc */
int n = rc * 2, interval = HZ / n;
- u64 count = n * id.data, i = 0;
+ u64 count = (u64)n * id.data, i = 0;
How about moving the code around a bit, change n to a u64 and drop the
cast? Does this look correct?
int interval = HZ / rc / 2;
u64 n = rc * 2;
u64 count = n * id.data;
i = 0;
I just don't like casts, they suggest the underlying types are wrong,
so should fix that, not add a cast.
This particular one is absolutely fine. When you want to multiply
u32 by u32, you always need a cast, otherwise the result will be
truncated. mul_u32_u32() does it the very same way[0].