* [PATCH 0/3] cast sizeof to int for comparison
@ 2018-07-01 17:32 Julia Lawall
2018-07-01 17:32 ` [PATCH 1/3] Input: elan_i2c_smbus - " Julia Lawall
2018-07-01 18:26 ` [PATCH 0/3] " Joe Perches
0 siblings, 2 replies; 6+ messages in thread
From: Julia Lawall @ 2018-07-01 17:32 UTC (permalink / raw)
To: linux-usb, joe, Chengguang Xu
Cc: kernel-janitors, linux-kernel, linux-input, linux-media
Comparing an int to a size, which is unsigned, causes the int to become
unsigned, giving the wrong result.
The semantic match that finds this problem is as follows:
(http://coccinelle.lip6.fr/)
// <smpl>
@safe disable not_int2@
int x;
position p;
binary operator op = {<,<=};
expression e;
@@
(
x < 0 || (x@p op e)
|
x <= 0 || (x@p op e)
|
x > 0 && (x@p op e)
|
x >= 0 && (x@p op e)
)
@@
int x;
type t;
expression e,e1;
identifier f != {strlen,resource_size};
position p != safe.p;
binary operator op = {<,<=};
@@
*x = f(...);
... when != x = e1
when != if (x < 0 || ...) { ... return ...; }
(
*x@p op sizeof(e)
|
*x@p op sizeof(t)
)
// </smpl>
---
drivers/input/mouse/elan_i2c_smbus.c | 2 +-
drivers/media/usb/gspca/kinect.c | 2 +-
drivers/usb/wusbcore/security.c | 2 +-
3 files changed, 3 insertions(+), 3 deletions(-)
^ permalink raw reply [flat|nested] 6+ messages in thread* [PATCH 1/3] Input: elan_i2c_smbus - cast sizeof to int for comparison 2018-07-01 17:32 [PATCH 0/3] cast sizeof to int for comparison Julia Lawall @ 2018-07-01 17:32 ` Julia Lawall 2018-08-01 23:03 ` Dmitry Torokhov 2018-07-01 18:26 ` [PATCH 0/3] " Joe Perches 1 sibling, 1 reply; 6+ messages in thread From: Julia Lawall @ 2018-07-01 17:32 UTC (permalink / raw) To: Dmitry Torokhov, joe, Chengguang Xu Cc: kernel-janitors, linux-input, linux-kernel Comparing an int to a size, which is unsigned, causes the int to become unsigned, giving the wrong result. i2c_smbus_read_block_data can return the result of i2c_smbus_xfer, whih can return a negative error code. A simplified version of the semantic match that finds this problem is as follows: (http://coccinelle.lip6.fr/) // <smpl> @@ int x; expression e,e1; identifier f; @@ *x = f(...); ... when != x = e1 when != if (x < 0 || ...) { ... return ...; } *x < sizeof(e) // </smpl> Signed-off-by: Julia Lawall <Julia.Lawall@lip6.fr> --- drivers/input/mouse/elan_i2c_smbus.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/input/mouse/elan_i2c_smbus.c b/drivers/input/mouse/elan_i2c_smbus.c index c060d27..88e315d 100644 --- a/drivers/input/mouse/elan_i2c_smbus.c +++ b/drivers/input/mouse/elan_i2c_smbus.c @@ -387,7 +387,7 @@ static int elan_smbus_prepare_fw_update(struct i2c_client *client) len = i2c_smbus_read_block_data(client, ETP_SMBUS_IAP_PASSWORD_READ, val); - if (len < sizeof(u16)) { + if (len < (int)sizeof(u16)) { error = len < 0 ? len : -EIO; dev_err(dev, "failed to read iap password: %d\n", error); ^ permalink raw reply related [flat|nested] 6+ messages in thread
* Re: [PATCH 1/3] Input: elan_i2c_smbus - cast sizeof to int for comparison 2018-07-01 17:32 ` [PATCH 1/3] Input: elan_i2c_smbus - " Julia Lawall @ 2018-08-01 23:03 ` Dmitry Torokhov 0 siblings, 0 replies; 6+ messages in thread From: Dmitry Torokhov @ 2018-08-01 23:03 UTC (permalink / raw) To: Julia Lawall Cc: joe, Chengguang Xu, kernel-janitors, linux-input, linux-kernel On Sun, Jul 01, 2018 at 07:32:03PM +0200, Julia Lawall wrote: > Comparing an int to a size, which is unsigned, causes the int to become > unsigned, giving the wrong result. i2c_smbus_read_block_data can return the > result of i2c_smbus_xfer, whih can return a negative error code. > > A simplified version of the semantic match that finds this problem is as > follows: (http://coccinelle.lip6.fr/) > > // <smpl> > @@ > int x; > expression e,e1; > identifier f; > @@ > > *x = f(...); > ... when != x = e1 > when != if (x < 0 || ...) { ... return ...; } > *x < sizeof(e) > // </smpl> > > Signed-off-by: Julia Lawall <Julia.Lawall@lip6.fr> > Applied, thank you. > --- > drivers/input/mouse/elan_i2c_smbus.c | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > diff --git a/drivers/input/mouse/elan_i2c_smbus.c b/drivers/input/mouse/elan_i2c_smbus.c > index c060d27..88e315d 100644 > --- a/drivers/input/mouse/elan_i2c_smbus.c > +++ b/drivers/input/mouse/elan_i2c_smbus.c > @@ -387,7 +387,7 @@ static int elan_smbus_prepare_fw_update(struct i2c_client *client) > len = i2c_smbus_read_block_data(client, > ETP_SMBUS_IAP_PASSWORD_READ, > val); > - if (len < sizeof(u16)) { > + if (len < (int)sizeof(u16)) { > error = len < 0 ? len : -EIO; > dev_err(dev, "failed to read iap password: %d\n", > error); > -- Dmitry ^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [PATCH 0/3] cast sizeof to int for comparison 2018-07-01 17:32 [PATCH 0/3] cast sizeof to int for comparison Julia Lawall 2018-07-01 17:32 ` [PATCH 1/3] Input: elan_i2c_smbus - " Julia Lawall @ 2018-07-01 18:26 ` Joe Perches 2018-07-01 18:51 ` Julia Lawall 1 sibling, 1 reply; 6+ messages in thread From: Joe Perches @ 2018-07-01 18:26 UTC (permalink / raw) To: Julia Lawall, linux-usb, Chengguang Xu Cc: kernel-janitors, linux-kernel, linux-input, linux-media On Sun, 2018-07-01 at 19:32 +0200, Julia Lawall wrote: > Comparing an int to a size, which is unsigned, causes the int to become > unsigned, giving the wrong result. > > The semantic match that finds this problem is as follows: > (http://coccinelle.lip6.fr/) Great, thanks. But what about the ones in net/smc like: > net/smc/smc_clc.c: > > len = kernel_sendmsg(smc->clcsock, &msg, &vec, 1, > sizeof(struct smc_clc_msg_decline)); > if (len < sizeof(struct smc_clc_msg_decline)) Are those detected by the semantic match and ignored? ^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [PATCH 0/3] cast sizeof to int for comparison 2018-07-01 18:26 ` [PATCH 0/3] " Joe Perches @ 2018-07-01 18:51 ` Julia Lawall 2018-07-03 13:00 ` Dan Carpenter 0 siblings, 1 reply; 6+ messages in thread From: Julia Lawall @ 2018-07-01 18:51 UTC (permalink / raw) To: Joe Perches Cc: linux-usb, Chengguang Xu, kernel-janitors, linux-kernel, linux-input, linux-media On Sun, 1 Jul 2018, Joe Perches wrote: > On Sun, 2018-07-01 at 19:32 +0200, Julia Lawall wrote: > > Comparing an int to a size, which is unsigned, causes the int to become > > unsigned, giving the wrong result. > > > > The semantic match that finds this problem is as follows: > > (http://coccinelle.lip6.fr/) > > Great, thanks. > > But what about the ones in net/smc like: > > > net/smc/smc_clc.c: > > > > len = kernel_sendmsg(smc->clcsock, &msg, &vec, 1, > > sizeof(struct smc_clc_msg_decline)); > > if (len < sizeof(struct smc_clc_msg_decline)) > > Are those detected by the semantic match and ignored? I wasn't sure how to justify that kernel_sendmsg returns a negative value. If it is the case, I can send the patch. I only found this in one file, but there were multiple occurrences. julia ^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [PATCH 0/3] cast sizeof to int for comparison 2018-07-01 18:51 ` Julia Lawall @ 2018-07-03 13:00 ` Dan Carpenter 0 siblings, 0 replies; 6+ messages in thread From: Dan Carpenter @ 2018-07-03 13:00 UTC (permalink / raw) To: Julia Lawall Cc: Joe Perches, linux-usb, Chengguang Xu, kernel-janitors, linux-kernel, linux-input, linux-media On Sun, Jul 01, 2018 at 08:51:55PM +0200, Julia Lawall wrote: > > > On Sun, 1 Jul 2018, Joe Perches wrote: > > > On Sun, 2018-07-01 at 19:32 +0200, Julia Lawall wrote: > > > Comparing an int to a size, which is unsigned, causes the int to become > > > unsigned, giving the wrong result. > > > > > > The semantic match that finds this problem is as follows: > > > (http://coccinelle.lip6.fr/) > > > > Great, thanks. > > > > But what about the ones in net/smc like: > > > > > net/smc/smc_clc.c: > > > > > > len = kernel_sendmsg(smc->clcsock, &msg, &vec, 1, > > > sizeof(struct smc_clc_msg_decline)); > > > if (len < sizeof(struct smc_clc_msg_decline)) > > > > Are those detected by the semantic match and ignored? > > I wasn't sure how to justify that kernel_sendmsg returns a negative value. > If it is the case, I can send the patch. I only found this in one file, > but there were multiple occurrences. > In theory, Smatch is supposed to know return values but kernel_sendmsg() is too complicated for Smatch. It's a tricky thing... That particular check is correct and deliberate, but there is another check which is wrong. net/smc/smc_clc.c 369 len = kernel_sendmsg(smc->clcsock, &msg, &vec, 1, 370 sizeof(struct smc_clc_msg_decline)); 371 if (len < sizeof(struct smc_clc_msg_decline)) 372 smc->sk.sk_err = EPROTO; 373 if (len < 0) 374 smc->sk.sk_err = -len; If it's invalid we set an error code, if it's already an error we preserve the error code. 375 return sock_error(&smc->sk); [ snip ] 442 /* due to the few bytes needed for clc-handshake this cannot block */ 443 len = kernel_sendmsg(smc->clcsock, &msg, vec, i, plen); 444 if (len < sizeof(pclc)) { 445 if (len >= 0) { ^^^^^^^^ This is always true. 446 reason_code = -ENETUNREACH; 447 smc->sk.sk_err = -reason_code; 448 } else { 449 smc->sk.sk_err = smc->clcsock->sk->sk_err; 450 reason_code = -smc->sk.sk_err; 451 } 452 } The other two checks are not type promoted so they also work as intended. This is an interesting sort of bug I've written a Smatch script inspired by your work here. One for the type promotion and one for the impossible condition. I'll let you know how it goes. regards, dan carpenter ^ permalink raw reply [flat|nested] 6+ messages in thread
end of thread, other threads:[~2018-08-01 23:03 UTC | newest] Thread overview: 6+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2018-07-01 17:32 [PATCH 0/3] cast sizeof to int for comparison Julia Lawall 2018-07-01 17:32 ` [PATCH 1/3] Input: elan_i2c_smbus - " Julia Lawall 2018-08-01 23:03 ` Dmitry Torokhov 2018-07-01 18:26 ` [PATCH 0/3] " Joe Perches 2018-07-01 18:51 ` Julia Lawall 2018-07-03 13:00 ` Dan Carpenter
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for NNTP newsgroup(s).