On Thu, Apr 12 2001, Brian J King wrote:
> I am currently writing a low-level SCSI device driver which has the
> requirement that the largest op that can be issued to it is 256k. It
> appears as if there is not an architected way for the low level to
> communicate this to the upper levels. I am currently limiting the number of
> scatter/gather elements to 64 and relying that an element can not be larger
> than 4k (this adapter is not going to run on hardware with anything other
> than a 4k page size). There are comments in the scsi merging code that
> there is a desire for this requirement to go away in the future and when it
> does, scatter/gather elements could be > 4K. It appears to me that it would
> be reasonable for the max op size (MAX_SECTORS) to be a parameter on the
> host structure just like num_sg is today. I know I am not the first to
This was solved some time ago, the scsi-max-sectors patch is included
in the current -ac series kernels. I've attached a copy for you, it does
exactly what you suggest -- making it a paramter in the host structure.
> encounter this issue (The IBM ServeRAID card, I believe, recently added
> some code in their device driver to split up ops, which seems like a very
> distateful solution to me). Has this been discussed before?
Exactly why scsi-max-sectors was written, having low level drivers split
requests is dead ugly.
--
Jens Axboe
diff -u --new-file --recursive --exclude-from /usr/src/exclude
linux.vanilla/drivers/scsi/hosts.c linux.ac/drivers/scsi/hosts.c
--- linux.vanilla/drivers/scsi/hosts.c Mon Oct 30 22:44:29 2000
+++ linux.ac/drivers/scsi/hosts.c Fri Mar 2 15:56:02 2001
@@ -232,6 +232,7 @@
retval->use_clustering = tpnt->use_clustering;
retval->select_queue_depths = tpnt->select_queue_depths;
+ retval->max_sectors = tpnt->max_sectors;
if(!scsi_hostlist)
scsi_hostlist = retval;
diff -u --new-file --recursive --exclude-from /usr/src/exclude
linux.vanilla/drivers/scsi/hosts.h linux.ac/drivers/scsi/hosts.h
--- linux.vanilla/drivers/scsi/hosts.h Thu Jan 4 22:52:08 2001
+++ linux.ac/drivers/scsi/hosts.h Fri Mar 2 15:35:33 2001
@@ -242,6 +242,11 @@
short unsigned int sg_tablesize;
/*
+ * if the host adapter has limitations beside segment count
+ */
+ short unsigned int max_sectors;
+
+ /*
* True if this host adapter can make good use of linked commands.
* This will allow more than one command to be queued to a given
* unit on a given host. Set this to the maximum number of command
@@ -379,6 +384,7 @@
int can_queue;
short cmd_per_lun;
short unsigned int sg_tablesize;
+ short unsigned int max_sectors;
unsigned in_recovery:1;
unsigned unchecked_is
diff -u --new-file --recursive --exclude-from /usr/src/exclude
linux.vanilla/drivers/scsi/scsi_merge.c linux.ac/drivers/scsi/scsi_merge.c
--- linux.vanilla/drivers/scsi/scsi_merge.c Thu Feb 22 09:06:05 2001
+++ linux.ac/drivers/scsi/scsi_merge.c Fri Mar 2 15:35:33 2001
@@ -417,6 +417,9 @@
max_segments = 64;
#endif
+ if ((req->nr_sectors + (bh->b_size >> 9)) > SHpnt->max_sectors)
+ return 0;
+
if (use_clustering) {
/*
* See if we can do this without creating another
@@ -473,6 +476,9 @@
max_segments = 64;
#endif
+ if ((req->nr_sectors + (bh->b_size >> 9)) > SHpnt->max_sectors)
+ return 0;
+
if (use_clustering) {
/*
* See if we can do this without creating another
@@ -624,6 +630,10 @@
return 0;
}
#endif
+
+ if ((req->nr_sectors + next->nr_sectors) > SHpnt->max_sectors)
+ return 0;
+
/*
* The main question is whether the two segments at the boundaries
* would be considered one or two.