Skip to content

Commit 3682e0c

Browse files
hreineckegregkh
authored andcommitted
scsi: sg: use standard lists for sg_requests
commit 109bade9c625c89bb5ea753aaa1a0a97e6fbb548 upstream. 'Sg_request' is using a private list implementation; convert it to standard lists. Signed-off-by: Hannes Reinecke <hare@suse.com> Reviewed-by: Johannes Thumshirn <jthumshirn@suse.de> Tested-by: Johannes Thumshirn <jthumshirn@suse.de> Reviewed-by: Christoph Hellwig <hch@lst.de> Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
1 parent 6b498ad commit 3682e0c

1 file changed

Lines changed: 61 additions & 86 deletions

File tree

drivers/scsi/sg.c

Lines changed: 61 additions & 86 deletions
Original file line numberDiff line numberDiff line change
@@ -133,7 +133,7 @@ struct sg_device; /* forward declarations */
133133
struct sg_fd;
134134

135135
typedef struct sg_request { /* SG_MAX_QUEUE requests outstanding per file */
136-
struct sg_request *nextrp; /* NULL -> tail request (slist) */
136+
struct list_head entry; /* list entry */
137137
struct sg_fd *parentfp; /* NULL -> not in use */
138138
Sg_scatter_hold data; /* hold buffer, perhaps scatter list */
139139
sg_io_hdr_t header; /* scsi command+info, see <scsi/sg.h> */
@@ -157,7 +157,7 @@ typedef struct sg_fd { /* holds the state of a file descriptor */
157157
int timeout; /* defaults to SG_DEFAULT_TIMEOUT */
158158
int timeout_user; /* defaults to SG_DEFAULT_TIMEOUT_USER */
159159
Sg_scatter_hold reserve; /* buffer held for this file descriptor */
160-
Sg_request *headrp; /* head of request slist, NULL->empty */
160+
struct list_head rq_list; /* head of request list */
161161
struct fasync_struct *async_qp; /* used by asynchronous notification */
162162
Sg_request req_arr[SG_MAX_QUEUE]; /* used as singly-linked list */
163163
char low_dma; /* as in parent but possibly overridden to 1 */
@@ -950,7 +950,7 @@ sg_ioctl(struct file *filp, unsigned int cmd_in, unsigned long arg)
950950
if (!access_ok(VERIFY_WRITE, ip, sizeof (int)))
951951
return -EFAULT;
952952
read_lock_irqsave(&sfp->rq_list_lock, iflags);
953-
for (srp = sfp->headrp; srp; srp = srp->nextrp) {
953+
list_for_each_entry(srp, &sfp->rq_list, entry) {
954954
if ((1 == srp->done) && (!srp->sg_io_owned)) {
955955
read_unlock_irqrestore(&sfp->rq_list_lock,
956956
iflags);
@@ -963,7 +963,8 @@ sg_ioctl(struct file *filp, unsigned int cmd_in, unsigned long arg)
963963
return 0;
964964
case SG_GET_NUM_WAITING:
965965
read_lock_irqsave(&sfp->rq_list_lock, iflags);
966-
for (val = 0, srp = sfp->headrp; srp; srp = srp->nextrp) {
966+
val = 0;
967+
list_for_each_entry(srp, &sfp->rq_list, entry) {
967968
if ((1 == srp->done) && (!srp->sg_io_owned))
968969
++val;
969970
}
@@ -1038,35 +1039,33 @@ sg_ioctl(struct file *filp, unsigned int cmd_in, unsigned long arg)
10381039
if (!rinfo)
10391040
return -ENOMEM;
10401041
read_lock_irqsave(&sfp->rq_list_lock, iflags);
1041-
for (srp = sfp->headrp, val = 0; val < SG_MAX_QUEUE;
1042-
++val, srp = srp ? srp->nextrp : srp) {
1042+
val = 0;
1043+
list_for_each_entry(srp, &sfp->rq_list, entry) {
1044+
if (val > SG_MAX_QUEUE)
1045+
break;
10431046
memset(&rinfo[val], 0, SZ_SG_REQ_INFO);
1044-
if (srp) {
1045-
rinfo[val].req_state = srp->done + 1;
1046-
rinfo[val].problem =
1047-
srp->header.masked_status &
1048-
srp->header.host_status &
1049-
srp->header.driver_status;
1050-
if (srp->done)
1051-
rinfo[val].duration =
1052-
srp->header.duration;
1053-
else {
1054-
ms = jiffies_to_msecs(jiffies);
1055-
rinfo[val].duration =
1056-
(ms > srp->header.duration) ?
1057-
(ms - srp->header.duration) : 0;
1058-
}
1059-
rinfo[val].orphan = srp->orphan;
1060-
rinfo[val].sg_io_owned =
1061-
srp->sg_io_owned;
1062-
rinfo[val].pack_id =
1063-
srp->header.pack_id;
1064-
rinfo[val].usr_ptr =
1065-
srp->header.usr_ptr;
1047+
rinfo[val].req_state = srp->done + 1;
1048+
rinfo[val].problem =
1049+
srp->header.masked_status &
1050+
srp->header.host_status &
1051+
srp->header.driver_status;
1052+
if (srp->done)
1053+
rinfo[val].duration =
1054+
srp->header.duration;
1055+
else {
1056+
ms = jiffies_to_msecs(jiffies);
1057+
rinfo[val].duration =
1058+
(ms > srp->header.duration) ?
1059+
(ms - srp->header.duration) : 0;
10661060
}
1061+
rinfo[val].orphan = srp->orphan;
1062+
rinfo[val].sg_io_owned = srp->sg_io_owned;
1063+
rinfo[val].pack_id = srp->header.pack_id;
1064+
rinfo[val].usr_ptr = srp->header.usr_ptr;
1065+
val++;
10671066
}
10681067
read_unlock_irqrestore(&sfp->rq_list_lock, iflags);
1069-
result = __copy_to_user(p, rinfo,
1068+
result = __copy_to_user(p, rinfo,
10701069
SZ_SG_REQ_INFO * SG_MAX_QUEUE);
10711070
result = result ? -EFAULT : 0;
10721071
kfree(rinfo);
@@ -1172,7 +1171,7 @@ sg_poll(struct file *filp, poll_table * wait)
11721171
return POLLERR;
11731172
poll_wait(filp, &sfp->read_wait, wait);
11741173
read_lock_irqsave(&sfp->rq_list_lock, iflags);
1175-
for (srp = sfp->headrp; srp; srp = srp->nextrp) {
1174+
list_for_each_entry(srp, &sfp->rq_list, entry) {
11761175
/* if any read waiting, flag it */
11771176
if ((0 == res) && (1 == srp->done) && (!srp->sg_io_owned))
11781177
res = POLLIN | POLLRDNORM;
@@ -2070,7 +2069,7 @@ sg_get_rq_mark(Sg_fd * sfp, int pack_id)
20702069
unsigned long iflags;
20712070

20722071
write_lock_irqsave(&sfp->rq_list_lock, iflags);
2073-
for (resp = sfp->headrp; resp; resp = resp->nextrp) {
2072+
list_for_each_entry(resp, &sfp->rq_list, entry) {
20742073
/* look for requests that are ready + not SG_IO owned */
20752074
if ((1 == resp->done) && (!resp->sg_io_owned) &&
20762075
((-1 == pack_id) || (resp->header.pack_id == pack_id))) {
@@ -2088,70 +2087,45 @@ sg_add_request(Sg_fd * sfp)
20882087
{
20892088
int k;
20902089
unsigned long iflags;
2091-
Sg_request *resp;
20922090
Sg_request *rp = sfp->req_arr;
20932091

20942092
write_lock_irqsave(&sfp->rq_list_lock, iflags);
2095-
resp = sfp->headrp;
2096-
if (!resp) {
2097-
memset(rp, 0, sizeof (Sg_request));
2098-
rp->parentfp = sfp;
2099-
resp = rp;
2100-
sfp->headrp = resp;
2101-
} else {
2102-
if (0 == sfp->cmd_q)
2103-
resp = NULL; /* command queuing disallowed */
2104-
else {
2105-
for (k = 0; k < SG_MAX_QUEUE; ++k, ++rp) {
2106-
if (!rp->parentfp)
2107-
break;
2108-
}
2109-
if (k < SG_MAX_QUEUE) {
2110-
memset(rp, 0, sizeof (Sg_request));
2111-
rp->parentfp = sfp;
2112-
while (resp->nextrp)
2113-
resp = resp->nextrp;
2114-
resp->nextrp = rp;
2115-
resp = rp;
2116-
} else
2117-
resp = NULL;
2093+
if (!list_empty(&sfp->rq_list)) {
2094+
if (!sfp->cmd_q)
2095+
goto out_unlock;
2096+
2097+
for (k = 0; k < SG_MAX_QUEUE; ++k, ++rp) {
2098+
if (!rp->parentfp)
2099+
break;
21182100
}
2101+
if (k >= SG_MAX_QUEUE)
2102+
goto out_unlock;
21192103
}
2120-
if (resp) {
2121-
resp->nextrp = NULL;
2122-
resp->header.duration = jiffies_to_msecs(jiffies);
2123-
}
2104+
memset(rp, 0, sizeof (Sg_request));
2105+
rp->parentfp = sfp;
2106+
rp->header.duration = jiffies_to_msecs(jiffies);
2107+
list_add_tail(&rp->entry, &sfp->rq_list);
21242108
write_unlock_irqrestore(&sfp->rq_list_lock, iflags);
2125-
return resp;
2109+
return rp;
2110+
out_unlock:
2111+
write_unlock_irqrestore(&sfp->rq_list_lock, iflags);
2112+
return NULL;
21262113
}
21272114

21282115
/* Return of 1 for found; 0 for not found */
21292116
static int
21302117
sg_remove_request(Sg_fd * sfp, Sg_request * srp)
21312118
{
2132-
Sg_request *prev_rp;
2133-
Sg_request *rp;
21342119
unsigned long iflags;
21352120
int res = 0;
21362121

2137-
if ((!sfp) || (!srp) || (!sfp->headrp))
2122+
if (!sfp || !srp || list_empty(&sfp->rq_list))
21382123
return res;
21392124
write_lock_irqsave(&sfp->rq_list_lock, iflags);
2140-
prev_rp = sfp->headrp;
2141-
if (srp == prev_rp) {
2142-
sfp->headrp = prev_rp->nextrp;
2143-
prev_rp->parentfp = NULL;
2125+
if (!list_empty(&srp->entry)) {
2126+
list_del(&srp->entry);
2127+
srp->parentfp = NULL;
21442128
res = 1;
2145-
} else {
2146-
while ((rp = prev_rp->nextrp)) {
2147-
if (srp == rp) {
2148-
prev_rp->nextrp = rp->nextrp;
2149-
rp->parentfp = NULL;
2150-
res = 1;
2151-
break;
2152-
}
2153-
prev_rp = rp;
2154-
}
21552129
}
21562130
write_unlock_irqrestore(&sfp->rq_list_lock, iflags);
21572131
return res;
@@ -2170,7 +2144,7 @@ sg_add_sfp(Sg_device * sdp)
21702144

21712145
init_waitqueue_head(&sfp->read_wait);
21722146
rwlock_init(&sfp->rq_list_lock);
2173-
2147+
INIT_LIST_HEAD(&sfp->rq_list);
21742148
kref_init(&sfp->f_ref);
21752149
mutex_init(&sfp->f_mutex);
21762150
sfp->timeout = SG_DEFAULT_TIMEOUT;
@@ -2211,10 +2185,13 @@ sg_remove_sfp_usercontext(struct work_struct *work)
22112185
{
22122186
struct sg_fd *sfp = container_of(work, struct sg_fd, ew.work);
22132187
struct sg_device *sdp = sfp->parentdp;
2188+
Sg_request *srp;
22142189

22152190
/* Cleanup any responses which were never read(). */
2216-
while (sfp->headrp)
2217-
sg_finish_rem_req(sfp->headrp);
2191+
while (!list_empty(&sfp->rq_list)) {
2192+
srp = list_first_entry(&sfp->rq_list, Sg_request, entry);
2193+
sg_finish_rem_req(srp);
2194+
}
22182195

22192196
if (sfp->reserve.bufflen > 0) {
22202197
SCSI_LOG_TIMEOUT(6, sg_printk(KERN_INFO, sdp,
@@ -2617,7 +2594,7 @@ static int sg_proc_seq_show_devstrs(struct seq_file *s, void *v)
26172594
/* must be called while holding sg_index_lock */
26182595
static void sg_proc_debug_helper(struct seq_file *s, Sg_device * sdp)
26192596
{
2620-
int k, m, new_interface, blen, usg;
2597+
int k, new_interface, blen, usg;
26212598
Sg_request *srp;
26222599
Sg_fd *fp;
26232600
const sg_io_hdr_t *hp;
@@ -2637,13 +2614,11 @@ static void sg_proc_debug_helper(struct seq_file *s, Sg_device * sdp)
26372614
seq_printf(s, " cmd_q=%d f_packid=%d k_orphan=%d closed=0\n",
26382615
(int) fp->cmd_q, (int) fp->force_packid,
26392616
(int) fp->keep_orphan);
2640-
for (m = 0, srp = fp->headrp;
2641-
srp != NULL;
2642-
++m, srp = srp->nextrp) {
2617+
list_for_each_entry(srp, &fp->rq_list, entry) {
26432618
hp = &srp->header;
26442619
new_interface = (hp->interface_id == '\0') ? 0 : 1;
26452620
if (srp->res_used) {
2646-
if (new_interface &&
2621+
if (new_interface &&
26472622
(SG_FLAG_MMAP_IO & hp->flags))
26482623
cp = " mmap>> ";
26492624
else
@@ -2674,7 +2649,7 @@ static void sg_proc_debug_helper(struct seq_file *s, Sg_device * sdp)
26742649
seq_printf(s, "ms sgat=%d op=0x%02x\n", usg,
26752650
(int) srp->data.cmd_opcode);
26762651
}
2677-
if (0 == m)
2652+
if (list_empty(&fp->rq_list))
26782653
seq_puts(s, " No requests active\n");
26792654
read_unlock(&fp->rq_list_lock);
26802655
}

0 commit comments

Comments
 (0)