ide_timer_expiry() - shouldn't 'wait' be int?
vi drivers/ide/ide-io.c +906 and note:
void ide_timer_expiry (unsigned long data)
{
ide_expiry_t *expiry = hwif->expiry;
...
unsigned long wait = -1;
...
if (expiry) {
...
wait = expiry(drive);
if (wait > 0) { /* continue */also note that in include/linux/ide.h:883:
typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?
Roel
Quoted 7 lines · Roel Kluin
vi
drivers/ide/ide-io.c+906 and note:void
ide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1;
Hm, haven't nothiced that this is *unsigned*.
Quoted 6 lines
...
if (expiry) {
...
wait = expiry(drive);
if (wait > 0) { /* continue */Quoted 6 lines
also note that in
include/linux/ide.h:883:typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?
It rather means that ide_expiry_t() should return unsigned. However, you're right as ide_dma_timeout_retry() takes *int* as a 2nd
argument.
Quoted 1 line
Roel
MBR, Sergei
Quoted 13 lines · Roel Kluin
vi
drivers/ide/ide-io.c+906 and note:void
ide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1; ... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */
Quoted 6 lines
also note that in
include/linux/ide.h:883:typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?
It does... and it seems like it could cause insanely long timeouts for:
* ATA_DMA_ERR error in dma_timer_expiry()
* commands without ->expiry in tc86c001_timer_expiry() (TC86C001 IDE controller only)
This is 2.6.29 material, care to make a patch?
Thanks,
Bart
Quoted 18 lines · Sergei Shtylyov
Quoted 7 lines · Roel Kluin
vi
drivers/ide/ide-io.c+906 and note:void
ide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1;Hm, haven't nothiced that this is *unsigned*.
Quoted 5 lines
... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */
Quoted 8 lines
Quoted 6 lines
also note that in
include/linux/ide.h:883:typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?
It rather means that
ide_expiry_t()should return unsigned.
Seconded. Roel, could you also handle it?
[ However since this is 2.6.30 stuff and there has been much work in
this area recently please base in top of linux-next or pata-2.6 tree. ]
Quoted 2 lines
However, you're right as
ide_dma_timeout_retry()takes *int* as a 2nd
argument.
Though it works fine (by a luck :) we should also fix it while we're at it.
Thanks,
Bart
Quoted 27 lines · Bartlomiej Zolnierkiewicz
Quoted 19 lines · Sergei Shtylyov
Quoted 6 lines · Roel Kluin
vi
drivers/ide/ide-io.c+906 and note:
voidide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1;Hm, haven't nothiced that this is *unsigned*.
Quoted 9 lines
... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */also note that in
include/linux/ide.h:883:
typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?Quoted 1 line
It rather means that
ide_expiry_t()should return unsigned.Seconded. Roel, could you also handle it?
[ However since this is 2.6.30 stuff and there has been much work in
this area recently please base in top of linux-next or pata-2.6 tree. ]
Quoted 7 lines
Quoted 2 lines
However, you're right as
ide_dma_timeout_retry()takes *int* as a 2nd
argument.Though it works fine (by a luck :) we should also fix it while we're at it.
Thanks,
Bart
I'm a little confused, do you want wait to be int, as my patch does below, or do you want the typedef to be:
typedef unsigned long (ide_expiry_t)(ide_drive_t *);
If the latter, I think the functions that expiry points to have to be adapted as well, right?
this is against tip-latest, feel free to modify the changelog. ------------------------------>8-------------8<--------------------------------- expiry() returns int, negative expiry() return values won't be noticed.
---
drivers/ide/ide-io.c +1 -1
@@ -1190,7 +1190,7 @@ void ide_timer_expiry (unsigned long data)ide_handler_t *handler;ide_expiry_t *expiry;unsigned long flags; -unsigned long wait =-1 ; +int wait =-1 ;spin_lock_irqsave (&ide_lock, flags);
Quoted 33 lines · Roel Kluin
Quoted 32 lines · Bartlomiej Zolnierkiewicz
Quoted 19 lines · Sergei Shtylyov
Quoted 6 lines · Roel Kluin
vi
drivers/ide/ide-io.c+906 and note:
voidide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1;Hm, haven't nothiced that this is *unsigned*.
Quoted 9 lines
... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */also note that in
include/linux/ide.h:883:
typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?Quoted 1 line
It rather means that
ide_expiry_t()should return unsigned.Seconded. Roel, could you also handle it?
[ However since this is 2.6.30 stuff and there has been much work in
this area recently please base in top of linux-next or pata-2.6 tree. ]Quoted 2 lines
However, you're right as
ide_dma_timeout_retry()takes *int* as a 2nd
argument.Though it works fine (by a luck :) we should also fix it while we're at it.
Quoted 7 lines
Quoted 2 lines
Thanks,
BartI'm a little confused, do you want wait to be int, as my patch does below, or do you want the typedef to be:
typedef unsigned long (ide_expiry_t)(ide_drive_t *);
Both. ;)
Quoted 4 lines
If the latter, I think the functions that expiry points to have to be adapted as well, right?
this is against tip-latest, feel free to modify the changelog.
Thanks! This is exactly what I meant for 2.6.29 (one-line bugfix), for 2.6.30 we should also do s/int/unsigned long/ cleanup (on top of the current linux-next/pata-2.6 tree).
Quoted 17 lines
------------------------------>8-------------8<---------------------------------
expiry()returns int, negativeexpiry()return values won't be noticed.Signed-off-by Roel Kluin <[email protected]>---
drivers/ide/ide-io.c +1
-1@@ -1190,7 +1190,7 @@ void ide_timer_expiry (unsigned long data)ide_handler_t *handler;ide_expiry_t *expiry;unsigned long flags; -unsigned long wait =-1 ; +int wait =-1 ;spin_lock_irqsave (&ide_lock, flags);
Hello.
Quoted 18 lines · Bartlomiej Zolnierkiewicz
Quoted 17 lines
Quoted 7 lines
vi
drivers/ide/ide-io.c+906 and note:void
ide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1;Hm, haven't nothiced that this is *unsigned*.
Quoted 7 lines
... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */also note that in
include/linux/ide.h:883:
Quoted 8 lines
Quoted 6 lines
Quoted 4 lines
typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?
It rather means that
ide_expiry_t()should return unsigned.Seconded. Roel, could you also handle it?
Not worth it, IMO...
Quoted 7 lines
[ However since this is 2.6.30 stuff and there has been much work in
this area recently please base in top of linux-next or pata-2.6 tree. ]Quoted 2 lines
However, you're right as
ide_dma_timeout_retry()takes *int* as a 2nd
argument.Though it works fine (by a luck :) we should also fix it while we're at it.
Fix what?
Quoted 2 lines
Thanks,
Bart
MBR, Sergei
Quoted 20 lines · Bartlomiej Zolnierkiewicz
Quoted 13 lines
vi
drivers/ide/ide-io.c+906 and note:void
ide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1; ... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */Quoted 6 lines
also note that in
include/linux/ide.h:883:typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?
Quoted 8 lines
It does... and it seems like it could cause insanely long timeouts for:
*
ATA_DMA_ERRerror indma_timer_expiry()* commands without ->expiry in
tc86c001_timer_expiry()(TC86C001 IDE controller only)This is 2.6.29 material, care to make a patch?
Er, it's not that bad as it gets cast back to *int* when callingide_dma_timer_expiry().
Quoted 2 lines
Thanks,
Bart
MBR, Sergei
Quoted 16 lines · Hello, I wrote:
Quoted 7 lines
vi
drivers/ide/ide-io.c+906 and note:void
ide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1;Hm, haven't nothiced that this is *unsigned*.
Quoted 5 lines
... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */
Quoted 8 lines
Quoted 6 lines
also note that in
include/linux/ide.h:883:typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?
It rather means that
ide_expiry_t()should return unsigned.
Er, not really, as it can return -1 too.
Quoted 1 line
Quoted 1 line
Roel
MBR, Sergei
Quoted 20 lines · Sergei Shtylyov
Quoted 17 lines · Hello, I wrote:
Quoted 7 lines
vi
drivers/ide/ide-io.c+906 and note:void
ide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1;Hm, haven't nothiced that this is *unsigned*.
Quoted 7 lines
... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */also note that in
include/linux/ide.h:883:
Quoted 8 lines
Quoted 6 lines
Quoted 4 lines
typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?
It rather means that
ide_expiry_t()should return unsigned.Er, not really, as it can return -1 too.
It can just return 0 instead.
Quoted 26 lines · Sergei Shtylyov
Quoted 23 lines · Bartlomiej Zolnierkiewicz
Quoted 13 lines
vi
drivers/ide/ide-io.c+906 and note:void
ide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1; ... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */Quoted 6 lines
also note that in
include/linux/ide.h:883:typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?
It does... and it seems like it could cause insanely long timeouts for:
*
ATA_DMA_ERRerror indma_timer_expiry()
Quoted 7 lines
Quoted 4 lines
* commands without ->expiry in
tc86c001_timer_expiry()(TC86C001 IDE controller only)This is 2.6.29 material, care to make a patch?
Er, it's not that bad as it gets cast back to *int* when calling
ide_dma_timer_expiry().
This case yes, however look at "wait > 0" one:
On -1 returned from ->expiry code sets "rather" long timeouts (4294967295/HZ on 32-bit...).
Quoted 36 lines · Sergei Shtylyov
Hello.
Quoted 18 lines · Bartlomiej Zolnierkiewicz
Quoted 17 lines
Quoted 7 lines
vi
drivers/ide/ide-io.c+906 and note:void
ide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1;Hm, haven't nothiced that this is *unsigned*.
Quoted 7 lines
... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */also note that in
include/linux/ide.h:883:Quoted 8 lines
Quoted 6 lines
Quoted 4 lines
typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?
It rather means that
ide_expiry_t()should return unsigned.Seconded. Roel, could you also handle it?
Not worth it, IMO...
Quoted 2 lines
[ However since this is 2.6.30 stuff and there has been much work in
this area recently please base in top of linux-next or pata-2.6 tree. ]
Quoted 6 lines
Quoted 4 lines
Quoted 2 lines
However, you're right as
ide_dma_timeout_retry()takes *int* as a 2nd
argument.Though it works fine (by a luck :) we should also fix it while we're at it.
Fix what?
ide_dma_timeout_retry's argument -- it is not the error value that we want to pass but the timeout value.
Quoted 35 lines · Bartlomiej Zolnierkiewicz
Quoted 34 lines
Quoted 34 lines · Sergei Shtylyov
Quoted 22 lines
Quoted 6 lines · Roel Kluin
vi
drivers/ide/ide-io.c+906 and note:
voidide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1;Hm, haven't nothiced that this is *unsigned*.
Quoted 9 lines
... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */also note that in
include/linux/ide.h:883:
typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?Quoted 1 line
It rather means that
ide_expiry_t()should return unsigned.Seconded. Roel, could you also handle it?
[ However since this is 2.6.30 stuff and there has been much work in
this area recently please base in top of linux-next or pata-2.6 tree. ]Quoted 2 lines
However, you're right as
ide_dma_timeout_retry()takes *int* as a 2nd
argument.Though it works fine (by a luck :) we should also fix it while we're at it.
Quoted 7 lines
Quoted 4 lines
I'm a little confused, do you want wait to be int, as my patch does below, or do you want the typedef to be:
typedef unsigned long (ide_expiry_t)(ide_drive_t *);
Both. ;)
No, not both really. Sorry for getting everyone confused.
Quoted 8 lines
Quoted 4 lines
If the latter, I think the functions that expiry points to have to be adapted as well, right?
this is against tip-latest, feel free to modify the changelog.
Thanks! This is exactly what I meant for 2.6.29 (one-line bugfix), for 2.6.30 we should also do s/int/unsigned long/ cleanup (on top of the current linux-next/pata-2.6 tree).
Er, what cleanup?
Quoted 2 lines
Quoted 2 lines
------------------------------>8-------------8<---------------------------------
expiry()returns int, negativeexpiry()return values won't be noticed.
In fact, -1 will still get noticed by its only user,ide_dma_timeout_retry() because 'wait' will be cast back to int.
MBR, Sergei
Quoted 29 lines · Bartlomiej Zolnierkiewicz
Quoted 28 lines
Quoted 28 lines
Quoted 13 lines
vi
drivers/ide/ide-io.c+906 and note:void
ide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1; ... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */Quoted 6 lines
also note that in
include/linux/ide.h:883:typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?
It does... and it seems like it could cause insanely long timeouts for:
*
ATA_DMA_ERRerror indma_timer_expiry()* commands without ->expiry in
tc86c001_timer_expiry()(TC86C001 IDE controller only)This is 2.6.29 material, care to make a patch?
Quoted 7 lines
Quoted 2 lines
Er, it's not that bad as it gets cast back to *int* when calling
ide_dma_timer_expiry().This case yes, however look at "wait > 0" one:
On -1 returned from ->expiry code sets "rather" long timeouts (4294967295/HZ on 32-bit...).
Ah... ignore me then. :-<
MBR, Sergei
Quoted 23 lines · Bartlomiej Zolnierkiewicz
Quoted 22 lines · Sergei Shtylyov
Quoted 19 lines · Hello, I wrote:
Quoted 7 lines
vi
drivers/ide/ide-io.c+906 and note:void
ide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1;Hm, haven't nothiced that this is *unsigned*.
Quoted 9 lines
... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */also note that in
include/linux/ide.h:883:typedef int (ide_expiry_t)(ide_drive_t *);
Quoted 8 lines
Quoted 6 lines
Quoted 4 lines
Quoted 2 lines
doesn't this mean that expiry returns int, and wait therefore should be int as well?
It rather means that
ide_expiry_t()should return unsigned.Er, not really, as it can return -1 too.
It can just return 0 instead.
This time I got confused. ide_dma_timeout_retry() takes different actions depending on error == -1 and error == 0.
[ BTW I worked on unifying those cases so ->dma_test_irq call can be moved
out from ide_dma_timeout_retry() to ide_timer_expiry() (=> it can be later merged with ->expiry tests)... ]
Thanks,
Bart
Quoted 69 lines · Bartlomiej Zolnierkiewicz
Quoted 33 lines · Roel Kluin
Quoted 32 lines · Bartlomiej Zolnierkiewicz
Quoted 19 lines · Sergei Shtylyov
Quoted 6 lines · Roel Kluin
vi
drivers/ide/ide-io.c+906 and note:
voidide_timer_expiry(unsigned long data){ ide_expiry_t *expiry = hwif->expiry; ... unsigned long wait = -1;Hm, haven't nothiced that this is *unsigned*.
Quoted 9 lines
... if (expiry) { ... wait = expiry(drive); if (wait > 0) { /* continue */also note that in
include/linux/ide.h:883:
typedef int (ide_expiry_t)(ide_drive_t *);
doesn't this mean that expiry returns int, and wait therefore should be int as well?Quoted 1 line
It rather means that
ide_expiry_t()should return unsigned.Seconded. Roel, could you also handle it?
[ However since this is 2.6.30 stuff and there has been much work in
this area recently please base in top of linux-next or pata-2.6 tree. ]Quoted 2 lines
However, you're right as
ide_dma_timeout_retry()takes *int* as a 2nd
argument.Though it works fine (by a luck :) we should also fix it while we're at it.
Quoted 7 lines
Quoted 2 lines
Thanks,
BartI'm a little confused, do you want wait to be int, as my patch does below, or do you want the typedef to be:
typedef unsigned long (ide_expiry_t)(ide_drive_t *);
Both. ;)
Quoted 4 lines
If the latter, I think the functions that expiry points to have to be adapted as well, right?
this is against tip-latest, feel free to modify the changelog.
Thanks! This is exactly what I meant for 2.6.29 (one-line bugfix), for 2.6.30 we should also do s/int/unsigned long/ cleanup (on top of the current linux-next/pata-2.6 tree).
Quoted 16 lines
------------------------------>8-------------8<---------------------------------
expiry()returns int, negativeexpiry()return values won't be noticed.Signed-off-by Roel Kluin <[email protected]>---
drivers/ide/ide-io.c +1
-1@@ -1190,7 +1190,7 @@ void ide_timer_expiry (unsigned long data)ide_handler_t *handler;ide_expiry_t *expiry;unsigned long flags; -unsigned long wait =-1 ; +int wait =-1 ;
Quoted 1 line
drivers/ide/ide-io.c void ide_timer_expiry (unsigned long data) · line 1195
Quoted 1 line
drivers/ide/ide-io.c +0
-0spin_lock_irqsave (&ide_lock, flags);
I failed to notice it before but the patch was against some old kernel (we don't have ide_lock anymore) so it won't apply to Linus' tree...
Anyway I ended up with the following version:
From: Roel Kluin <[email protected]>
Subject: ide: expiry() returns int, negative expiry() return values won't be noticed
bart:
It seems like the bug could cause insanely long timeouts for:
- ATA_DMA_ERR error in dma_timer_expiry()
- commands without ->expiry in tc86c001_timer_expiry() (TC86C001 IDE controller only)
--- drivers/ide/ide-io.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/ide/ide-io.c +1 -1
@@ -908,7 +908,7 @@ void ide_timer_expiry (unsigned long datide_drive_t *uninitialized_var (drive );ide_handler_t *handler;unsigned long flags; -unsigned long wait =-1 ; +int wait =-1 ;int plug_device =0 ;spin_lock_irqsave (&hwif->lock, flags);