Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
L
linux
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Kirill Smelkov
linux
Commits
8c0b740d
Commit
8c0b740d
authored
Jun 11, 2002
by
James Bottomley
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
[SCSI mid-layer]
Add support for generic blk layer TCQ (needs blk_queue_find_tag function)
parent
838ede57
Changes
4
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
84 additions
and
23 deletions
+84
-23
drivers/scsi/hosts.h
drivers/scsi/hosts.h
+20
-0
drivers/scsi/scsi.c
drivers/scsi/scsi.c
+11
-2
drivers/scsi/scsi.h
drivers/scsi/scsi.h
+43
-17
drivers/scsi/scsi_lib.c
drivers/scsi/scsi_lib.c
+10
-4
No files found.
drivers/scsi/hosts.h
View file @
8c0b740d
...
...
@@ -562,6 +562,26 @@ extern int scsi_unregister_host(Scsi_Host_Template *);
#define SD_EXTRA_DEVS CONFIG_SD_EXTRA_DEVS
#define SR_EXTRA_DEVS CONFIG_SR_EXTRA_DEVS
/**
* scsi_find_device - find a device given the host
* @channel: SCSI channel (zero if only one channel)
* @pun: SCSI target number (physical unit number)
* @lun: SCSI Logical Unit Number
**/
static
inline
Scsi_Device
*
scsi_find_device
(
struct
Scsi_Host
*
host
,
int
channel
,
int
pun
,
int
lun
)
{
Scsi_Device
*
SDpnt
;
for
(
SDpnt
=
host
->
host_queue
;
SDpnt
!=
NULL
;
SDpnt
=
SDpnt
->
next
)
if
(
SDpnt
->
channel
==
channel
&&
SDpnt
->
id
==
pun
&&
SDpnt
->
lun
==
lun
)
break
;
return
SDpnt
;
}
#endif
/*
* Overrides for Emacs so that we follow Linus's tabbing style.
...
...
drivers/scsi/scsi.c
View file @
8c0b740d
...
...
@@ -254,11 +254,20 @@ __setup("scsi_logging=", scsi_logging_setup);
static
void
scsi_wait_done
(
Scsi_Cmnd
*
SCpnt
)
{
struct
request
*
req
;
struct
request
*
req
=
SCpnt
->
request
;
struct
request_queue
*
q
=
&
SCpnt
->
device
->
request_queue
;
unsigned
long
flags
;
req
=
SCpnt
->
request
;
ASSERT_LOCK
(
q
->
queue_lock
,
0
)
;
req
->
rq_status
=
RQ_SCSI_DONE
;
/* Busy, but indicate request done */
spin_lock_irqsave
(
q
->
queue_lock
,
flags
);
if
(
blk_rq_tagged
(
req
))
blk_queue_end_tag
(
q
,
req
);
spin_unlock_irqrestore
(
q
->
queue_lock
,
flags
);
if
(
req
->
waiting
)
complete
(
req
->
waiting
);
}
...
...
drivers/scsi/scsi.h
View file @
8c0b740d
...
...
@@ -560,6 +560,7 @@ struct scsi_device {
atomic_t
device_active
;
/* commands checked out for device */
volatile
unsigned
short
device_busy
;
/* commands actually active on low-level */
Scsi_Cmnd
*
device_queue
;
/* queue of SCSI Command structures */
Scsi_Cmnd
*
current_cmnd
;
/* currently active command */
unsigned
int
id
,
lun
,
channel
;
...
...
@@ -861,12 +862,12 @@ extern int scsi_reset_provider(Scsi_Device *, int);
* would be adjustable from 0 to depth.
**/
static
inline
void
scsi_activate_tcq
(
Scsi_Device
*
SDpnt
,
int
depth
)
{
request_queue_t
*
q
=
&
SDpnt
->
request_queue
;
request_queue_t
*
q
=
&
SDpnt
->
request_queue
;
if
(
SDpnt
->
tagged_supported
&&
!
blk_queue_tagged
(
q
))
{
blk_queue_init_tags
(
q
,
depth
);
SDpnt
->
tagged_queue
=
1
;
}
if
(
SDpnt
->
tagged_supported
&&
!
blk_queue_tagged
(
q
))
{
blk_queue_init_tags
(
q
,
depth
);
SDpnt
->
tagged_queue
=
1
;
}
}
/**
...
...
@@ -874,13 +875,15 @@ static inline void scsi_activate_tcq(Scsi_Device *SDpnt, int depth) {
* @SDpnt: device to turn off TCQ for
**/
static
inline
void
scsi_deactivate_tcq
(
Scsi_Device
*
SDpnt
)
{
blk_queue_free_tags
(
&
SDpnt
->
request_queue
);
SDpnt
->
tagged_queue
=
0
;
blk_queue_free_tags
(
&
SDpnt
->
request_queue
);
SDpnt
->
tagged_queue
=
0
;
}
#define MSG_SIMPLE_TAG 0x20
#define MSG_HEAD_TAG 0x21
#define MSG_ORDERED_TAG 0x22
#define SCSI_NO_TAG (-1)
/* identify no tag in use */
/**
* scsi_populate_tag_msg - place a tag message in a buffer
* @SCpnt: pointer to the Scsi_Cmnd for the tag
...
...
@@ -892,21 +895,44 @@ static inline void scsi_deactivate_tcq(Scsi_Device *SDpnt) {
* May return 0 if TCQ is disabled for this device.
**/
static
inline
int
scsi_populate_tag_msg
(
Scsi_Cmnd
*
SCpnt
,
char
*
msg
)
{
struct
request
*
req
=
SCpnt
->
request
;
struct
request
*
req
=
SCpnt
->
request
;
if
(
!
blk_rq_tagged
(
req
))
return
0
;
if
(
!
blk_rq_tagged
(
req
))
return
0
;
if
(
req
->
flags
&
REQ_BARRIER
)
*
msg
++
=
MSG_ORDERED_TAG
;
else
*
msg
++
=
MSG_SIMPLE_TAG
;
if
(
req
->
flags
&
REQ_BARRIER
)
*
msg
++
=
MSG_ORDERED_TAG
;
else
*
msg
++
=
MSG_SIMPLE_TAG
;
*
msg
++
=
SCpnt
->
request
->
tag
;
*
msg
++
=
SCpnt
->
request
->
tag
;
return
2
;
return
2
;
}
/**
* scsi_find_tag - find a tagged command by device
* @SDpnt: pointer to the ScSI device
* @tag: the tag number
*
* Notes:
* Only works with tags allocated by the generic blk layer.
**/
static
inline
Scsi_Cmnd
*
scsi_find_tag
(
Scsi_Device
*
SDpnt
,
int
tag
)
{
struct
request
*
req
;
if
(
tag
==
SCSI_NO_TAG
)
/* single command, look in space */
return
SDpnt
->
current_cmnd
;
req
=
blk_queue_find_tag
(
&
SDpnt
->
request_queue
,
tag
);
if
(
req
==
NULL
)
return
NULL
;
return
(
Scsi_Cmnd
*
)
req
->
special
;
}
#endif
...
...
drivers/scsi/scsi_lib.c
View file @
8c0b740d
...
...
@@ -76,7 +76,8 @@ static void __scsi_insert_special(request_queue_t *q, struct request *rq,
* must not attempt merges on this) and that it acts as a soft
* barrier
*/
rq
->
flags
=
REQ_SPECIAL
|
REQ_BARRIER
;
rq
->
flags
&=
REQ_QUEUED
;
rq
->
flags
|=
REQ_SPECIAL
|
REQ_BARRIER
;
rq
->
special
=
data
;
...
...
@@ -87,6 +88,9 @@ static void __scsi_insert_special(request_queue_t *q, struct request *rq,
* device, or a host that is unable to accept a particular command.
*/
spin_lock_irqsave
(
q
->
queue_lock
,
flags
);
/* If command is tagged, release the tag */
if
(
blk_rq_tagged
(
rq
))
blk_queue_end_tag
(
q
,
rq
);
_elv_add_request
(
q
,
rq
,
!
at_head
,
0
);
q
->
request_fn
(
q
);
spin_unlock_irqrestore
(
q
->
queue_lock
,
flags
);
...
...
@@ -927,11 +931,13 @@ void scsi_request_fn(request_queue_t * q)
* reason to search the list, because all of the commands
* in this queue are for the same device.
*/
if
(
blk_queue_tagged
(
q
))
blk_queue_start_tag
(
q
,
req
);
else
if
(
!
(
blk_queue_tagged
(
q
)
&&
(
blk_queue_start_tag
(
q
,
req
)
==
0
)))
blkdev_dequeue_request
(
req
);
/* note the overloading of req->special. When the tag
* is active it always means SCpnt. If the tag goes
* back for re-queueing, it may be reset */
req
->
special
=
SCpnt
;
SCpnt
->
request
=
req
;
/*
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment