Discussion:
Linux scsi / usb-mass-storage and HP printer cardreader bug + fix
Hans de Goede
2008-01-09 21:44:49 UTC
Permalink
Hi All,

First of all sorry for the somewhat massive cross-posting, I've spend a
significant amount of time hunting down this bug, and so far the response has
been less the overwhelming.

The problem is with the HP PSC 1350 (my printer and confirmed by 2 others) and
atleast also the HP PSC 1610 (confirmed by Guillaume Bedot, in the CC).

The cardreader of the multi function printers will "crash" and from that moment
on no longer communicate in any sane way, if you try to read the last sector of
an sdcard* in a read that is more then 1 sector, so trying to read 8 sectors
starting at sector capicity-8 will crash it, as will reading 2 sectors starting
at sector capicity-2, however reading the last sector in a one 1 sector read
will succeed! (* xdcards seem to be fine).

I haven't tried if it will crash on larger then 1 sector writes which include
the last sector too, I immediately added code to not do that in both the read
and write paths. I have tested reading and writing the end of the disk with
this kludge in and it works.

I currently have a somewhat ugly proof of concept patch for this, which adds
another type of usb-massstorage quirk. When this quirk flag is set, the
usb-massstorage driver modifies READ_10 and WRITE_10 commands of more then 1
sector which includes the last sector to become one sector less. I've been told
by scsi subsystem developers that doing a shorter read / write then requested
is not a problem, the scsi subsystem is designed to handle getting less then it
asked for and will send a seperate request for the last sector.

I and 3 others (2 on a PSC 1350 too, one on a PSC1610) have tested this patch
with success. I'm not asking for this patch to be included to the kernel as is,
I'm asking for the now known workaround for this to be added to the kernel in
someway!

Perhaps its an idea to add the posibility to have a scsi command filter
function / callback to the scsi or usb-massstorage subsystem, and then add a
mechanism to set this filter depending on usb id's and if added to the scsi
layer, a mechanism to set it based on scsi device and manufacturer
identification strings. Such a mechanism might be usefull in the future to work
around other broken hardware too, and has the added advantage of not having
todo much changes to the normal code path, keep that readable.

I'm willing to come up with a patch for such a filter mechanism, provided I get
some pointers where this is best added.

Thanks & Regards,

Hans


p.s.

I've also included the fedora-kernel list in the addressee's because I was
hoping that maybe someone can take one of these printers to the kernel hackfest
in the weekend's fudcon and take a look at this.
Matthew Dharm
2008-01-09 22:10:46 UTC
Permalink
Post by Hans de Goede
First of all sorry for the somewhat massive cross-posting, I've spend a
significant amount of time hunting down this bug, and so far the response
has been less the overwhelming.
The cardreader of the multi function printers will "crash" and from that
moment on no longer communicate in any sane way, if you try to read the
last sector of an sdcard* in a read that is more then 1 sector, so trying
to read 8 sectors starting at sector capicity-8 will crash it, as will
reading 2 sectors starting at sector capicity-2, however reading the last
sector in a one 1 sector read will succeed! (* xdcards seem to be fine).
To continue the history on this.... we over in usb-storage land looked at
this and think it belongs in the SCSI layer. We don't like changing
commands in-flight; it has, historically, caused us all sorts of issues in
the past.

Furthermore, this seems like the likely sort of off-by-one bug that can
affect many types of devices, not just USB.

I'd really like to see this in sd_mod -- I have no objection to requiring
an HCD to set a flag to indicate that it should be used, if really desired.
But, it seems to me to be a much easier change to make where the command
originated rather than in mid-flight.

Matt
--
Matthew Dharm Home: mdharm-***@one-eyed-alien.net
Maintainer, Linux USB Mass Storage Driver

P: Nine more messages in admin.policy.
M: I know, I'm typing as fast as I can!
-- Pitr and Mike
User Friendly, 11/27/97
Boaz Harrosh
2008-01-10 10:43:25 UTC
Permalink
----- Original Message -----
*From:* Hans de Goede <***@hhs.nl>
*To:* USB Storage list <usb-***@lists.one-eyed-alien.net>
*CC:* fedora-kernel-***@redhat.com, USB development list
<linux-usb-***@lists.sourceforge.net>, David Brown
<usb-***@davidb.org>, Guillaume Bedot <***@zarb.org>,
linux-***@vger.kernel.org, linux-***@vger.kernel.org
*Sent:* Wed, Jan 09 2008 at 23:44 +0200
*Subject:* Linux scsi / usb-mass-storage and HP printer cardreader bug + fix
Post by Hans de Goede
Hi All,
First of all sorry for the somewhat massive cross-posting, I've spend a
significant amount of time hunting down this bug, and so far the response has
been less the overwhelming.
The problem is with the HP PSC 1350 (my printer and confirmed by 2 others) and
atleast also the HP PSC 1610 (confirmed by Guillaume Bedot, in the CC).
The cardreader of the multi function printers will "crash" and from that moment
on no longer communicate in any sane way, if you try to read the last sector of
an sdcard* in a read that is more then 1 sector, so trying to read 8 sectors
starting at sector capicity-8 will crash it, as will reading 2 sectors starting
at sector capicity-2, however reading the last sector in a one 1 sector read
will succeed! (* xdcards seem to be fine).
I haven't tried if it will crash on larger then 1 sector writes which include
the last sector too, I immediately added code to not do that in both the read
and write paths. I have tested reading and writing the end of the disk with
this kludge in and it works.
I currently have a somewhat ugly proof of concept patch for this, which adds
another type of usb-massstorage quirk. When this quirk flag is set, the
usb-massstorage driver modifies READ_10 and WRITE_10 commands of more then 1
sector which includes the last sector to become one sector less. I've been told
by scsi subsystem developers that doing a shorter read / write then requested
is not a problem, the scsi subsystem is designed to handle getting less then it
asked for and will send a seperate request for the last sector.
I and 3 others (2 on a PSC 1350 too, one on a PSC1610) have tested this patch
with success. I'm not asking for this patch to be included to the kernel as is,
I'm asking for the now known workaround for this to be added to the kernel in
someway!
Perhaps its an idea to add the posibility to have a scsi command filter
function / callback to the scsi or usb-massstorage subsystem, and then add a
mechanism to set this filter depending on usb id's and if added to the scsi
layer, a mechanism to set it based on scsi device and manufacturer
identification strings. Such a mechanism might be usefull in the future to work
around other broken hardware too, and has the added advantage of not having
todo much changes to the normal code path, keep that readable.
I'm willing to come up with a patch for such a filter mechanism, provided I get
some pointers where this is best added.
Thanks & Regards,
Hans
p.s.
I've also included the fedora-kernel list in the addressee's because I was
hoping that maybe someone can take one of these printers to the kernel hackfest
in the weekend's fudcon and take a look at this.
+ if ((offset + num) == sdkp->capacity && num > 1) {
+ if (srb->cmnd[8] == 0)
+ srb->cmnd[7]--;
+ srb->cmnd[8]--;
+ srb->request_bufflen -= 512;
+ srb->underflow -= 512;
+ }
This will no longer compile on top of latest scsi-misc, and
LLDs are not suppose to modify request_bufflen anymore.

I'm not sure what the proper solution should be?

Boaz


-------------------------------------------------------------------------
Check out the new SourceForge.net Marketplace.
It's the best place to buy or sell services for
just about anything Open Source.
http://ad.doubleclick.net/clk;164216239;13503038;w?http://sf.net/marketplace
_______________________________________________
linux-usb-***@lists.sourceforge.net
To unsubscribe, use the last form field at:
https://lists.sourceforge.net/lists/listinfo/linux-usb-devel
Hans de Goede
2008-01-10 10:52:56 UTC
Permalink
Post by Boaz Harrosh
----- Original Message -----
*Sent:* Wed, Jan 09 2008 at 23:44 +0200
*Subject:* Linux scsi / usb-mass-storage and HP printer cardreader bug + fix
Post by Hans de Goede
Hi All,
First of all sorry for the somewhat massive cross-posting, I've spend a
significant amount of time hunting down this bug, and so far the response has
been less the overwhelming.
The problem is with the HP PSC 1350 (my printer and confirmed by 2 others) and
atleast also the HP PSC 1610 (confirmed by Guillaume Bedot, in the CC).
The cardreader of the multi function printers will "crash" and from that moment
on no longer communicate in any sane way, if you try to read the last sector of
an sdcard* in a read that is more then 1 sector, so trying to read 8 sectors
starting at sector capicity-8 will crash it, as will reading 2 sectors starting
at sector capicity-2, however reading the last sector in a one 1 sector read
will succeed! (* xdcards seem to be fine).
I haven't tried if it will crash on larger then 1 sector writes which include
the last sector too, I immediately added code to not do that in both the read
and write paths. I have tested reading and writing the end of the disk with
this kludge in and it works.
I currently have a somewhat ugly proof of concept patch for this, which adds
another type of usb-massstorage quirk. When this quirk flag is set, the
usb-massstorage driver modifies READ_10 and WRITE_10 commands of more then 1
sector which includes the last sector to become one sector less. I've been told
by scsi subsystem developers that doing a shorter read / write then requested
is not a problem, the scsi subsystem is designed to handle getting less then it
asked for and will send a seperate request for the last sector.
I and 3 others (2 on a PSC 1350 too, one on a PSC1610) have tested this patch
with success. I'm not asking for this patch to be included to the kernel as is,
I'm asking for the now known workaround for this to be added to the kernel in
someway!
Perhaps its an idea to add the posibility to have a scsi command filter
function / callback to the scsi or usb-massstorage subsystem, and then add a
mechanism to set this filter depending on usb id's and if added to the scsi
layer, a mechanism to set it based on scsi device and manufacturer
identification strings. Such a mechanism might be usefull in the future to work
around other broken hardware too, and has the added advantage of not having
todo much changes to the normal code path, keep that readable.
I'm willing to come up with a patch for such a filter mechanism, provided I get
some pointers where this is best added.
Thanks & Regards,
Hans
p.s.
I've also included the fedora-kernel list in the addressee's because I was
hoping that maybe someone can take one of these printers to the kernel hackfest
in the weekend's fudcon and take a look at this.
+ if ((offset + num) == sdkp->capacity && num > 1) {
+ if (srb->cmnd[8] == 0)
+ srb->cmnd[7]--;
+ srb->cmnd[8]--;
+ srb->request_bufflen -= 512;
+ srb->underflow -= 512;
+ }
This will no longer compile on top of latest scsi-misc, and
LLDs are not suppose to modify request_bufflen anymore.
I'm not sure what the proper solution should be?
I guess the proper solution would be to add a special case to the scsi layer
where the read10 / write10 command is issued, and split the request in 2 there
when it involves the last sector.

There was another reply in this thread stating that problems reading the last
sector with sd / mmc cards happen quite often, and that this is most likely not
an isolated case.

Regards,

Hans


-------------------------------------------------------------------------
Check out the new SourceForge.net Marketplace.
It's the best place to buy or sell services for
just about anything Open Source.
http://ad.doubleclick.net/clk;164216239;13503038;w?http://sf.net/marketplace
_______________________________________________
linux-usb-***@lists.sourceforge.net
To unsubscribe, use the last form field at:
https://lists.sourceforge.net/lists/listinfo/linux-usb-devel
Boaz Harrosh
2008-01-10 11:27:02 UTC
Permalink
Post by Hans de Goede
Post by Boaz Harrosh
----- Original Message -----
*Sent:* Wed, Jan 09 2008 at 23:44 +0200
*Subject:* Linux scsi / usb-mass-storage and HP printer cardreader bug + fix
Post by Hans de Goede
Hi All,
First of all sorry for the somewhat massive cross-posting, I've spend a
significant amount of time hunting down this bug, and so far the response has
been less the overwhelming.
The problem is with the HP PSC 1350 (my printer and confirmed by 2 others) and
atleast also the HP PSC 1610 (confirmed by Guillaume Bedot, in the CC).
The cardreader of the multi function printers will "crash" and from that moment
on no longer communicate in any sane way, if you try to read the last sector of
an sdcard* in a read that is more then 1 sector, so trying to read 8 sectors
starting at sector capicity-8 will crash it, as will reading 2 sectors starting
at sector capicity-2, however reading the last sector in a one 1 sector read
will succeed! (* xdcards seem to be fine).
I haven't tried if it will crash on larger then 1 sector writes which include
the last sector too, I immediately added code to not do that in both the read
and write paths. I have tested reading and writing the end of the disk with
this kludge in and it works.
I currently have a somewhat ugly proof of concept patch for this, which adds
another type of usb-massstorage quirk. When this quirk flag is set, the
usb-massstorage driver modifies READ_10 and WRITE_10 commands of more then 1
sector which includes the last sector to become one sector less. I've been told
by scsi subsystem developers that doing a shorter read / write then requested
is not a problem, the scsi subsystem is designed to handle getting less then it
asked for and will send a seperate request for the last sector.
I and 3 others (2 on a PSC 1350 too, one on a PSC1610) have tested this patch
with success. I'm not asking for this patch to be included to the kernel as is,
I'm asking for the now known workaround for this to be added to the kernel in
someway!
Perhaps its an idea to add the posibility to have a scsi command filter
function / callback to the scsi or usb-massstorage subsystem, and then add a
mechanism to set this filter depending on usb id's and if added to the scsi
layer, a mechanism to set it based on scsi device and manufacturer
identification strings. Such a mechanism might be usefull in the future to work
around other broken hardware too, and has the added advantage of not having
todo much changes to the normal code path, keep that readable.
I'm willing to come up with a patch for such a filter mechanism, provided I get
some pointers where this is best added.
Thanks & Regards,
Hans
p.s.
I've also included the fedora-kernel list in the addressee's because I was
hoping that maybe someone can take one of these printers to the kernel hackfest
in the weekend's fudcon and take a look at this.
+ if ((offset + num) == sdkp->capacity && num > 1) {
+ if (srb->cmnd[8] == 0)
+ srb->cmnd[7]--;
+ srb->cmnd[8]--;
+ srb->request_bufflen -= 512;
+ srb->underflow -= 512;
+ }
This will no longer compile on top of latest scsi-misc, and
LLDs are not suppose to modify request_bufflen anymore.
I'm not sure what the proper solution should be?
I guess the proper solution would be to add a special case to the scsi layer
where the read10 / write10 command is issued, and split the request in 2 there
when it involves the last sector.
There was another reply in this thread stating that problems reading the last
sector with sd / mmc cards happen quite often, and that this is most likely not
an isolated case.
Regards,
Hans
Yes, you're right. in ULDs it is a much proper way to do this.

So I guess you'll have to do that special host flag or device
flag, and add a check for it in sd.c. You'll see that sd.c is
already doing bufflen truncation at sd_prep_fn(), just add one
more case.

Boaz

-------------------------------------------------------------------------
Check out the new SourceForge.net Marketplace.
It's the best place to buy or sell services for
just about anything Open Source.
http://ad.doubleclick.net/clk;164216239;13503038;w?http://sf.net/marketplace
_______________________________________________
linux-usb-***@lists.sourceforge.net
To unsubscribe, use the last form field at:
https://lists.sourceforge.net/lists/listinfo/linux-usb-devel
Hans de Goede
2008-01-11 12:48:31 UTC
Permalink
Post by Boaz Harrosh
Post by Hans de Goede
Post by Boaz Harrosh
I'm not sure what the proper solution should be?
I guess the proper solution would be to add a special case to the scsi layer
where the read10 / write10 command is issued, and split the request in 2 there
when it involves the last sector.
There was another reply in this thread stating that problems reading the last
sector with sd / mmc cards happen quite often, and that this is most likely not
an isolated case.
Regards,
Hans
Yes, you're right. in ULDs it is a much proper way to do this.
So I guess you'll have to do that special host flag or device
flag, and add a check for it in sd.c. You'll see that sd.c is
already doing bufflen truncation at sd_prep_fn(), just add one
more case.
Yes,

That will work nicely, I'll write an updated patch this evening (when I have
access to the printer to test again).

Regards,

Hans


-
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to ***@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Guillaume Bedot
2008-01-11 13:57:36 UTC
Permalink
Hello,
Post by Hans de Goede
That will work nicely, I'll write an updated patch this evening (when I have
access to the printer to test again).
Great news, i am impatient to test this new patch.

I may face an other bug with the Transcend 1GB SD card, would be
possible that the patch would be available for latests kernels ?

Thanks in advance,

Best regards,

Guillaume B.




-------------------------------------------------------------------------
Check out the new SourceForge.net Marketplace.
It's the best place to buy or sell services for
just about anything Open Source.
http://ad.doubleclick.net/clk;164216239;13503038;w?http://sf.net/marketplace
_______________________________________________
linux-usb-***@lists.sourceforge.net
To unsubscribe, use the last form field at:
https://lis
Hans de Goede
2008-01-11 20:14:00 UTC
Permalink
Post by Boaz Harrosh
Yes, you're right. in ULDs it is a much proper way to do this.
So I guess you'll have to do that special host flag or device
flag, and add a check for it in sd.c. You'll see that sd.c is
already doing bufflen truncation at sd_prep_fn(), just add one
more case.
Done, thanks for the hint. Patch implementing my fix this way attached, please
apply.

Thanks & Regards,

Hans
Matthew Dharm
2008-01-11 20:34:24 UTC
Permalink
Post by Hans de Goede
Post by Boaz Harrosh
Yes, you're right. in ULDs it is a much proper way to do this.
So I guess you'll have to do that special host flag or device
flag, and add a check for it in sd.c. You'll see that sd.c is
already doing bufflen truncation at sd_prep_fn(), just add one
more case.
Done, thanks for the hint. Patch implementing my fix this way attached,
please apply.
Well, I can't say that I'm really a big fan of matching a multi-interface
device based on the interface class code, but I don't see a better solution
that isn't a major coding project.

This approach looks pretty reasonable to me.

Matt
--
Matthew Dharm Home: mdharm-***@one-eyed-alien.net
Maintainer, Linux USB Mass Storage Driver

SP: I sell software for Microsoft. Can you set me free?
DP: Natural Selection says I shouldn't.
-- MS Salesman and Dust Puppy
User Friendly, 4/2/1998
Guillaume Bedot
2008-01-14 09:40:45 UTC
Permalink
Hello,
Post by Boaz Harrosh
Yes, you're right. in ULDs it is a much proper way to do this.
=20
So I guess you'll have to do that special host flag or device
flag, and add a check for it in sd.c. You'll see that sd.c is=20
already doing bufflen truncation at sd_prep_fn(), just add one
more case.
=20
=20
Done, thanks for the hint. Patch implementing my fix this way attache=
d, please=20
apply.
=20
Thanks & Regards,
=20
Hans
=20
I have tested this time with two PSC 1610 printers, and two SD cards,
the same bug occured without the patch.
And is fixed with your new patch. =EF=BB=BFGood work !

The bug however did not occur with a microSD card in a SD adaptator ?!

But it fixes only two models.
Do you think other devices (hp or not) can be impacted ?
There are hundreds of models with card readers only for hp :
http://hplip.sourceforge.net/supported_devices/combined.html

Will this be possible to use "LAST_SECTOR_BUG" quirk for testing withou=
t
recompiling a kernel ?

Best regards,

Guillaume B.

-
To unsubscribe from this list: send the line "unsubscribe linux-scsi" i=
n
the body of a message to ***@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Hans de Goede
2008-01-14 09:46:56 UTC
Permalink
Post by Guillaume Bedot
I have tested this time with two PSC 1610 printers, and two SD cards,
the same bug occured without the patch.
And is fixed with your new patch. Good work !
Hi,

Thanks for testing!
Post by Guillaume Bedot
But it fixes only two models.
Do you think other devices (hp or not) can be impacted ?
http://hplip.sourceforge.net/supported_devices/combined.html
Will this be possible to use "LAST_SECTOR_BUG" quirk for testing without
recompiling a kernel ?
This is not possible AFAIK, I've already wrote a blog post about this asking
for people to test this, but got no responses.

I think it would be good if the people from the hplip project would take some
time to test all the printer models they have got access too.

Regards,

Hans


-------------------------------------------------------------------------
Check out the new SourceForge.net Marketplace.
It's the best place to buy or sell services for
just about anything Open Source.
http://ad.doubleclick.net/clk;164216239;13503038;w?http://sf.net/marketplace
_______________________________________________
linux-usb-***@lists.sourceforge.net
To unsubscribe, use the last form field at:
https://lists.sour
Matthew Dharm
2008-01-14 16:03:10 UTC
Permalink
Post by Hans de Goede
Post by Guillaume Bedot
But it fixes only two models.
Do you think other devices (hp or not) can be impacted ?
http://hplip.sourceforge.net/supported_devices/combined.html
Will this be possible to use "LAST_SECTOR_BUG" quirk for testing without
recompiling a kernel ?
This is not possible AFAIK, I've already wrote a blog post about this
asking for people to test this, but got no responses.
Once the patches are accepted by the SCSI people, one of the things we can
consider doing is enabling this quirk for all USB devices. It should be
pretty harmless to all properly working devices, and the performance hit
should be pretty minimal.

We may be able to convince the SCSI people to enable it for all devices,
regardless of HCD.

Matt
--
Matthew Dharm Home: mdharm-***@one-eyed-alien.net
Maintainer, Linux USB Mass Storage Driver

What the hell are you?
-- Pitr to Dust Puppy
User Friendly, 12/3/1997
James Bottomley
2008-01-14 16:33:08 UTC
Permalink
Post by Matthew Dharm
Post by Hans de Goede
Post by Guillaume Bedot
But it fixes only two models.
Do you think other devices (hp or not) can be impacted ?
http://hplip.sourceforge.net/supported_devices/combined.html
Will this be possible to use "LAST_SECTOR_BUG" quirk for testing without
recompiling a kernel ?
This is not possible AFAIK, I've already wrote a blog post about this
asking for people to test this, but got no responses.
Once the patches are accepted by the SCSI people, one of the things we can
consider doing is enabling this quirk for all USB devices. It should be
pretty harmless to all properly working devices, and the performance hit
should be pretty minimal.
The SCSI patches look OK, with the stylistic points fixed below ...
we'll need two separate patches as well (one for SCSI, one for USB).
Post by Matthew Dharm
We may be able to convince the SCSI people to enable it for all devices,
regardless of HCD.
No ... I'm not particularly keen to have enterprise vendors after my
blood ...
Post by Matthew Dharm
+ /* Some devices (some sdcards for one) don't like it if the last sector
+ gets read in a larger then 1 sector read */
The comment style in sd is

/*
* comment
*/
Post by Matthew Dharm
+ if (sdp->last_sector_bug && rq->nr_sectors > sdp->sector_size / 512 &&
An unlikely() here, please to force the compiler to optimise for the
non-buggy case. Plus what is the rq->nr_sectors > sdp->sector_size /
512 test supposed to be doing? that being true is supposed to be a
guarantee of the block layer (and if something goes wrong there's a
check for this lower down).
Post by Matthew Dharm
+ block + rq->nr_sectors == get_capacity(disk)) {
rq->nr_sectors should be this_count
Post by Matthew Dharm
+ this_count -= sdp->sector_size / 512;
If you relocate this code to after the sector_size/this_count adjustment
code (i.e. about line 442) you can just do --this_count;

James
Hans de Goede
2008-01-14 18:37:36 UTC
Permalink
Post by James Bottomley
Post by Matthew Dharm
Post by Hans de Goede
Post by Guillaume Bedot
But it fixes only two models.
Do you think other devices (hp or not) can be impacted ?
http://hplip.sourceforge.net/supported_devices/combined.html
Will this be possible to use "LAST_SECTOR_BUG" quirk for testing without
recompiling a kernel ?
This is not possible AFAIK, I've already wrote a blog post about this
asking for people to test this, but got no responses.
Once the patches are accepted by the SCSI people, one of the things we can
consider doing is enabling this quirk for all USB devices. It should be
pretty harmless to all properly working devices, and the performance hit
should be pretty minimal.
The SCSI patches look OK, with the stylistic points fixed below ...
we'll need two separate patches as well (one for SCSI, one for USB).
Okay,

Thanks for the review! I'll do a new scsi changes only patch once I get an
answer to some questions regarding your review.
Post by James Bottomley
Post by Matthew Dharm
+ /* Some devices (some sdcards for one) don't like it if the last sector
+ gets read in a larger then 1 sector read */
The comment style in sd is
/*
* comment
*/
Will fix,
Post by James Bottomley
Post by Matthew Dharm
+ if (sdp->last_sector_bug && rq->nr_sectors > sdp->sector_size / 512 &&
An unlikely() here, please to force the compiler to optimise for the
non-buggy case.
Will do.
Post by James Bottomley
Plus what is the rq->nr_sectors > sdp->sector_size /
512 test supposed to be doing? that being true is supposed to be a
guarantee of the block layer (and if something goes wrong there's a
check for this lower down).
It first is was just:
rq->nr_sectors > 1

Then I changed it to also do the right thing for 1024 and larger sector disks.
The whole purpose is to not read the last sector in a larger then one sector
read, so the amount of sectors gets reduced by one if (block + rq->nr_sectors
== get_capacity(disk)) but we do want still want to be able to read the last
sector by itself, so we must not reduce the no sectors to be read by one if it
is already one.
Post by James Bottomley
Post by Matthew Dharm
+ block + rq->nr_sectors == get_capacity(disk)) {
rq->nr_sectors should be this_count
Fine by me, but in this place in the code they are the same value, and the
check for a read beyond the end of disk a few lines above also uses
rq->nr_sectors, which one should be used when?
Post by James Bottomley
Post by Matthew Dharm
+ this_count -= sdp->sector_size / 512;
If you relocate this code to after the sector_size/this_count adjustment
code (i.e. about line 442) you can just do --this_count;
I cannot move the check down as then block has been adjusted for the sector
size, so if I move the check down it becomes:
if (block * (sdp->sector_size / 512) + rq->nr_sectors == get_capacity(disk))

I would rather not have the sdp->sector_size / 512 code in the check (slow) but
rather in the not often entered if block.

Regards,

Hans
-
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to ***@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
James Bottomley
2008-01-14 19:09:18 UTC
Permalink
Post by Hans de Goede
Post by James Bottomley
Post by Matthew Dharm
Post by Hans de Goede
Post by Guillaume Bedot
But it fixes only two models.
Do you think other devices (hp or not) can be impacted ?
http://hplip.sourceforge.net/supported_devices/combined.html
Will this be possible to use "LAST_SECTOR_BUG" quirk for testing without
recompiling a kernel ?
This is not possible AFAIK, I've already wrote a blog post about this
asking for people to test this, but got no responses.
Once the patches are accepted by the SCSI people, one of the things we can
consider doing is enabling this quirk for all USB devices. It should be
pretty harmless to all properly working devices, and the performance hit
should be pretty minimal.
The SCSI patches look OK, with the stylistic points fixed below ...
we'll need two separate patches as well (one for SCSI, one for USB).
Okay,
Thanks for the review! I'll do a new scsi changes only patch once I get an
answer to some questions regarding your review.
Post by James Bottomley
Post by Matthew Dharm
+ /* Some devices (some sdcards for one) don't like it if the last sector
+ gets read in a larger then 1 sector read */
The comment style in sd is
/*
* comment
*/
Will fix,
Post by James Bottomley
Post by Matthew Dharm
+ if (sdp->last_sector_bug && rq->nr_sectors > sdp->sector_size / 512 &&
An unlikely() here, please to force the compiler to optimise for the
non-buggy case.
Will do.
Post by James Bottomley
Plus what is the rq->nr_sectors > sdp->sector_size /
512 test supposed to be doing? that being true is supposed to be a
guarantee of the block layer (and if something goes wrong there's a
check for this lower down).
rq->nr_sectors > 1
Then I changed it to also do the right thing for 1024 and larger sector disks.
The whole purpose is to not read the last sector in a larger then one sector
read, so the amount of sectors gets reduced by one if (block + rq->nr_sectors
== get_capacity(disk)) but we do want still want to be able to read the last
sector by itself, so we must not reduce the no sectors to be read by one if it
is already one.
Yes, I know that. What I mean is the block subsystem sends reads and
writes down in increments of the sector size. Checking if the current
number of pending sectors is greater than the current block size is
checking that guarantee. The current code already has a check in it to
see if this guarantee is observed ... you don't need to check it again.
Post by Hans de Goede
Post by James Bottomley
Post by Matthew Dharm
+ block + rq->nr_sectors == get_capacity(disk)) {
rq->nr_sectors should be this_count
Fine by me, but in this place in the code they are the same value, and the
check for a read beyond the end of disk a few lines above also uses
rq->nr_sectors, which one should be used when?
this_count is the adjusted sector size. At the moment, there's no size
transformation in the code between your check and the top (where
this_count is set to rq->nr_sectors). But if there were (and someone
might add one one day) you'd be wanting to check the adjusted size (i.e.
this_count).
Post by Hans de Goede
Post by James Bottomley
Post by Matthew Dharm
+ this_count -= sdp->sector_size / 512;
If you relocate this code to after the sector_size/this_count adjustment
code (i.e. about line 442) you can just do --this_count;
I cannot move the check down as then block has been adjusted for the sector
if (block * (sdp->sector_size / 512) + rq->nr_sectors == get_capacity(disk))
I would rather not have the sdp->sector_size / 512 code in the check (slow) but
rather in the not often entered if block.
OK, point taken, it would be worse. I think today's compilers are happy
to translate x/512 to x>>9, so it shouldn't be that slow.

James



-------------------------------------------------------------------------
Check out the new SourceForge.net Marketplace.
It's the best place to buy or sell services for
just about anything Open Source.
http://ad.doubleclick.net/clk;164216239;13503038;w?http://sf.net/marketplace
_______________________________________________
linux-usb-***@lists.sourceforge.net
To unsubscribe, use the last form field at:
https://lists.sourceforge.net/lists/listinfo/linux-usb-devel
Hans de Goede
2008-01-14 19:27:17 UTC
Permalink
Post by James Bottomley
Post by Hans de Goede
Post by James Bottomley
Plus what is the rq->nr_sectors > sdp->sector_size /
512 test supposed to be doing? that being true is supposed to be a
guarantee of the block layer (and if something goes wrong there's a
check for this lower down).
rq->nr_sectors > 1
Then I changed it to also do the right thing for 1024 and larger sector disks.
The whole purpose is to not read the last sector in a larger then one sector
read, so the amount of sectors gets reduced by one if (block + rq->nr_sectors
== get_capacity(disk)) but we do want still want to be able to read the last
sector by itself, so we must not reduce the no sectors to be read by one if it
is already one.
Yes, I know that. What I mean is the block subsystem sends reads and
writes down in increments of the sector size. Checking if the current
number of pending sectors is greater than the current block size is
checking that guarantee. The current code already has a check in it to
see if this guarantee is observed ... you don't need to check it again.
I'm not checking for the guarantee, I'm checking that the read > 1
realsize_sector, before decrementing the number of _512_bytes_sectors by
realsize_sector, this check must be there, as after reading all but the last
sector, another request will be send with 1 realsize_sector size, for which
(block + rq->nr_sectors) == get_capacity(disk) will still hold true, in this
case this_count must not be lowered, otherwise this_count will become 0 in this
case and the last sector will never get read.

I hope that clarifies why that code is there, if not can you tell how you would
want the code to look by just giving the full if statement as it should be, I
think we are somehow misunderstanding each other.

Regards,

Hans
-
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to ***@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
James Bottomley
2008-01-14 20:20:46 UTC
Permalink
Post by Hans de Goede
Post by James Bottomley
Post by Hans de Goede
Post by James Bottomley
Plus what is the rq->nr_sectors > sdp->sector_size /
512 test supposed to be doing? that being true is supposed to be a
guarantee of the block layer (and if something goes wrong there's a
check for this lower down).
rq->nr_sectors > 1
Then I changed it to also do the right thing for 1024 and larger sector disks.
The whole purpose is to not read the last sector in a larger then one sector
read, so the amount of sectors gets reduced by one if (block + rq->nr_sectors
== get_capacity(disk)) but we do want still want to be able to read the last
sector by itself, so we must not reduce the no sectors to be read by one if it
is already one.
Yes, I know that. What I mean is the block subsystem sends reads and
writes down in increments of the sector size. Checking if the current
number of pending sectors is greater than the current block size is
checking that guarantee. The current code already has a check in it to
see if this guarantee is observed ... you don't need to check it again.
I'm not checking for the guarantee, I'm checking that the read > 1
realsize_sector, before decrementing the number of _512_bytes_sectors by
realsize_sector, this check must be there, as after reading all but the last
sector, another request will be send with 1 realsize_sector size, for which
(block + rq->nr_sectors) == get_capacity(disk) will still hold true, in this
case this_count must not be lowered, otherwise this_count will become 0 in this
case and the last sector will never get read.
I hope that clarifies why that code is there, if not can you tell how you would
want the code to look by just giving the full if statement as it should be, I
think we are somehow misunderstanding each other.
Oh, right; it's > rather than >= ... sorry, yes that's fine.

James


-
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to ***@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Hans de Goede
2008-01-20 10:12:16 UTC
Permalink
Post by James Bottomley
Post by Hans de Goede
Post by James Bottomley
Post by Hans de Goede
Post by James Bottomley
Plus what is the rq->nr_sectors > sdp->sector_size /
512 test supposed to be doing? that being true is supposed to be a
guarantee of the block layer (and if something goes wrong there's a
check for this lower down).
rq->nr_sectors > 1
Then I changed it to also do the right thing for 1024 and larger sector disks.
The whole purpose is to not read the last sector in a larger then one sector
read, so the amount of sectors gets reduced by one if (block + rq->nr_sectors
== get_capacity(disk)) but we do want still want to be able to read the last
sector by itself, so we must not reduce the no sectors to be read by one if it
is already one.
Yes, I know that. What I mean is the block subsystem sends reads and
writes down in increments of the sector size. Checking if the current
number of pending sectors is greater than the current block size is
checking that guarantee. The current code already has a check in it to
see if this guarantee is observed ... you don't need to check it again.
I'm not checking for the guarantee, I'm checking that the read > 1
realsize_sector, before decrementing the number of _512_bytes_sectors by
realsize_sector, this check must be there, as after reading all but the last
sector, another request will be send with 1 realsize_sector size, for which
(block + rq->nr_sectors) == get_capacity(disk) will still hold true, in this
case this_count must not be lowered, otherwise this_count will become 0 in this
case and the last sector will never get read.
I hope that clarifies why that code is there, if not can you tell how you would
want the code to look by just giving the full if statement as it should be, I
think we are somehow misunderstanding each other.
Oh, right; it's > rather than >= ... sorry, yes that's fine.
Ok,

I got swamped @work this week so it took a while, but I've made a new seperate
(scsi-sd only) patch with the cleanups as discussed.

I'm sending this (to the full recipient list) in a new top level post titled:
PATCH: scsi-sd-last-sector-bug-flag.patch

Regards,

Hans
Stefan Richter
2008-01-14 18:40:01 UTC
Permalink
Post by James Bottomley
Post by Matthew Dharm
Post by Hans de Goede
Post by Guillaume Bedot
Will this be possible to use "LAST_SECTOR_BUG" quirk for testing without
recompiling a kernel ?
This is not possible AFAIK, I've already wrote a blog post about this
asking for people to test this, but got no responses.
Once the patches are accepted by the SCSI people, one of the things we can
consider doing is enabling this quirk for all USB devices.
...
Post by James Bottomley
Post by Matthew Dharm
We may be able to convince the SCSI people to enable it for all devices,
regardless of HCD.
No ... I'm not particularly keen to have enterprise vendors after my
blood ...
Guillaume, you can tell the SCSI core driver at boot time (or module
insertion time) and/or at runtime to
- switch on default quirk flags,
- add quirk flags for selected devices per name matching.

Alas I don't know of a good documention how to do either of this, and I
am not familiar enough with the procedure to explain it here.
--
Stefan Richter
-=====-==--- ---= -===-
http://arcgraph.de/sr/
Matthew Dharm
2008-01-14 19:01:05 UTC
Permalink
Post by James Bottomley
Post by Matthew Dharm
We may be able to convince the SCSI people to enable it for all devices,
regardless of HCD.
No ... I'm not particularly keen to have enterprise vendors after my
blood ...
Fair enough. Tho, we should probably just enable this blindly for all
usb-storage devices. Otherwise, this is just going to become an
unusual_devs.h nightmare.

Matt
--
Matthew Dharm Home: mdharm-***@one-eyed-alien.net
Maintainer, Linux USB Mass Storage Driver

What, are you one of those Microsoft-bashing Linux freaks?
-- Customer to Greg
User Friendly, 2/10/1999
Hans de Goede
2008-01-14 19:10:59 UTC
Permalink
Post by Matthew Dharm
Post by James Bottomley
Post by Matthew Dharm
We may be able to convince the SCSI people to enable it for all devices,
regardless of HCD.
No ... I'm not particularly keen to have enterprise vendors after my
blood ...
Fair enough. Tho, we should probably just enable this blindly for all
usb-storage devices. Otherwise, this is just going to become an
unusual_devs.h nightmare.
Since this will make all devices with this bug "just work" (tm), I'm all for it!

As soon as I get an answer from the scsi people on my questions resulting from
there review I'll do a new patch for the scsi layer for this.

Regards,

Hans


-------------------------------------------------------------------------
Check out the new SourceForge.net Marketplace.
It's the best place to buy or sell services for
just about anything Open Source.
http://ad.doubleclick.net/clk;164216239;13503038;w?http://sf.net/marketplace
_______________________________________________
linux-usb-***@lists.sourceforge.net
To unsubscribe, use the last form field at:
https://lists.sourceforge.net/lists/listinfo/linux-usb-devel
w***@public.gmane.org
2008-04-25 05:43:07 UTC
Permalink
subscribe
--
To unsubscribe from this list: send the line "unsubscribe linux-usb" in
the body of a message to majordomo-***@public.gmane.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Loading...