]> pilppa.org Git - linux-2.6-omap-h63xx.git/blob - drivers/scsi/arm/scsi.h
Merge master.kernel.org:/pub/scm/linux/kernel/git/jejb/scsi-rc-fixes-2.6
[linux-2.6-omap-h63xx.git] / drivers / scsi / arm / scsi.h
1 /*
2  *  linux/drivers/acorn/scsi/scsi.h
3  *
4  *  Copyright (C) 2002 Russell King
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License version 2 as
8  * published by the Free Software Foundation.
9  *
10  *  Commonly used scsi driver functions.
11  */
12
13 #include <linux/scatterlist.h>
14
15 #define BELT_AND_BRACES
16
17 /*
18  * The scatter-gather list handling.  This contains all
19  * the yucky stuff that needs to be fixed properly.
20  */
21 static inline int copy_SCp_to_sg(struct scatterlist *sg, struct scsi_pointer *SCp, int max)
22 {
23         int bufs = SCp->buffers_residual;
24
25         BUG_ON(bufs + 1 > max);
26
27         sg_set_buf(sg, SCp->ptr, SCp->this_residual);
28
29         if (bufs)
30                 memcpy(sg + 1, SCp->buffer + 1,
31                        sizeof(struct scatterlist) * bufs);
32         return bufs + 1;
33 }
34
35 static inline int next_SCp(struct scsi_pointer *SCp)
36 {
37         int ret = SCp->buffers_residual;
38         if (ret) {
39                 SCp->buffer++;
40                 SCp->buffers_residual--;
41                 SCp->ptr = sg_virt(SCp->buffer);
42                 SCp->this_residual = SCp->buffer->length;
43         } else {
44                 SCp->ptr = NULL;
45                 SCp->this_residual = 0;
46         }
47         return ret;
48 }
49
50 static inline unsigned char get_next_SCp_byte(struct scsi_pointer *SCp)
51 {
52         char c = *SCp->ptr;
53
54         SCp->ptr += 1;
55         SCp->this_residual -= 1;
56
57         return c;
58 }
59
60 static inline void put_next_SCp_byte(struct scsi_pointer *SCp, unsigned char c)
61 {
62         *SCp->ptr = c;
63         SCp->ptr += 1;
64         SCp->this_residual -= 1;
65 }
66
67 static inline void init_SCp(struct scsi_cmnd *SCpnt)
68 {
69         memset(&SCpnt->SCp, 0, sizeof(struct scsi_pointer));
70
71         if (SCpnt->use_sg) {
72                 unsigned long len = 0;
73                 int buf;
74
75                 SCpnt->SCp.buffer = (struct scatterlist *) SCpnt->request_buffer;
76                 SCpnt->SCp.buffers_residual = SCpnt->use_sg - 1;
77                 SCpnt->SCp.ptr = sg_virt(SCpnt->SCp.buffer);
78                 SCpnt->SCp.this_residual = SCpnt->SCp.buffer->length;
79                 SCpnt->SCp.phase = SCpnt->request_bufflen;
80
81 #ifdef BELT_AND_BRACES
82                 /*
83                  * Calculate correct buffer length.  Some commands
84                  * come in with the wrong request_bufflen.
85                  */
86                 for (buf = 0; buf <= SCpnt->SCp.buffers_residual; buf++)
87                         len += SCpnt->SCp.buffer[buf].length;
88
89                 if (SCpnt->request_bufflen != len)
90                         printk(KERN_WARNING "scsi%d.%c: bad request buffer "
91                                "length %d, should be %ld\n", SCpnt->device->host->host_no,
92                                '0' + SCpnt->device->id, SCpnt->request_bufflen, len);
93                 SCpnt->request_bufflen = len;
94 #endif
95         } else {
96                 SCpnt->SCp.ptr = (unsigned char *)SCpnt->request_buffer;
97                 SCpnt->SCp.this_residual = SCpnt->request_bufflen;
98                 SCpnt->SCp.phase = SCpnt->request_bufflen;
99         }
100
101         /*
102          * If the upper SCSI layers pass a buffer, but zero length,
103          * we aren't interested in the buffer pointer.
104          */
105         if (SCpnt->SCp.this_residual == 0 && SCpnt->SCp.ptr) {
106 #if 0 //def BELT_AND_BRACES
107                 printk(KERN_WARNING "scsi%d.%c: zero length buffer passed for "
108                        "command ", SCpnt->host->host_no, '0' + SCpnt->target);
109                 __scsi_print_command(SCpnt->cmnd);
110 #endif
111                 SCpnt->SCp.ptr = NULL;
112         }
113 }