2 * Generic SCSI Device support
4 * Copyright (c) 2007 Bull S.A.S.
5 * Based on code by Paul Brook
6 * Based on code by Fabrice Bellard
8 * Written by Laurent Vivier <Laurent.Vivier@bull.net>
10 * This code is licenced under the LGPL.
14 #include "qemu-common.h"
16 #include "scsi-disk.h"
20 SCSIDevice
*scsi_generic_init(BlockDriverState
*bdrv
, int tcq
,
21 scsi_completionfn completion
, void *opaque
)
31 #define DPRINTF(fmt, args...) \
32 do { printf("scsi-generic: " fmt , ##args); } while (0)
34 #define DPRINTF(fmt, args...) do {} while(0)
37 #define BADF(fmt, args...) \
38 do { fprintf(stderr, "scsi-generic: " fmt , ##args); } while (0)
41 #include <sys/types.h>
45 #include <scsi/scsi.h>
48 #define REPORT_DENSITY_SUPPORT 0x44
49 #define LOAD_UNLOAD 0xa6
50 #define SET_CD_SPEED 0xbb
53 #define SCSI_CMD_BUF_SIZE 16
54 #define SCSI_SENSE_BUF_SIZE 96
56 #define SG_ERR_DRIVER_TIMEOUT 0x06
57 #define SG_ERR_DRIVER_SENSE 0x08
60 #define MAX_UINT ((unsigned int)-1)
63 typedef struct SCSIRequest
{
64 BlockDriverAIOCB
*aiocb
;
65 struct SCSIRequest
*next
;
68 uint8_t cmd
[SCSI_CMD_BUF_SIZE
];
73 sg_io_hdr_t io_header
;
76 struct SCSIDeviceState
78 SCSIRequest
*requests
;
79 BlockDriverState
*bdrv
;
83 scsi_completionfn completion
;
86 uint8_t sensebuf
[SCSI_SENSE_BUF_SIZE
];
90 /* Global pool of SCSIRequest structures. */
91 static SCSIRequest
*free_requests
= NULL
;
93 static SCSIRequest
*scsi_new_request(SCSIDeviceState
*s
, uint32_t tag
)
99 free_requests
= r
->next
;
101 r
= qemu_malloc(sizeof(SCSIRequest
));
107 memset(r
->cmd
, 0, sizeof(r
->cmd
));
108 memset(&r
->io_header
, 0, sizeof(r
->io_header
));
115 r
->next
= s
->requests
;
120 static void scsi_remove_request(SCSIRequest
*r
)
123 SCSIDeviceState
*s
= r
->dev
;
125 if (s
->requests
== r
) {
126 s
->requests
= r
->next
;
129 while (last
&& last
->next
!= r
)
132 last
->next
= r
->next
;
134 BADF("Orphaned request\n");
137 r
->next
= free_requests
;
141 static SCSIRequest
*scsi_find_request(SCSIDeviceState
*s
, uint32_t tag
)
146 while (r
&& r
->tag
!= tag
)
152 /* Helper function for command completion. */
153 static void scsi_command_complete(void *opaque
, int ret
)
155 SCSIRequest
*r
= (SCSIRequest
*)opaque
;
156 SCSIDeviceState
*s
= r
->dev
;
160 s
->driver_status
= r
->io_header
.driver_status
;
161 if (s
->driver_status
& SG_ERR_DRIVER_SENSE
)
162 s
->senselen
= r
->io_header
.sb_len_wr
;
167 if (s
->driver_status
& SG_ERR_DRIVER_TIMEOUT
) {
169 BADF("Driver Timeout\n");
170 } else if (r
->io_header
.status
)
171 status
= r
->io_header
.status
;
172 else if (s
->driver_status
& SG_ERR_DRIVER_SENSE
)
173 status
= CHECK_CONDITION
<< 1;
177 DPRINTF("Command complete 0x%p tag=0x%x status=%d\n",
180 scsi_remove_request(r
);
181 s
->completion(s
->opaque
, SCSI_REASON_DONE
, tag
, status
);
184 /* Cancel a pending data transfer. */
185 static void scsi_cancel_io(SCSIDevice
*d
, uint32_t tag
)
187 DPRINTF("scsi_cancel_io 0x%x\n", tag
);
188 SCSIDeviceState
*s
= d
->state
;
190 DPRINTF("Cancel tag=0x%x\n", tag
);
191 r
= scsi_find_request(s
, tag
);
194 bdrv_aio_cancel(r
->aiocb
);
196 scsi_remove_request(r
);
200 static int execute_command(BlockDriverState
*bdrv
,
201 SCSIRequest
*r
, int direction
,
202 BlockDriverCompletionFunc
*complete
)
206 r
->io_header
.interface_id
= 'S';
207 r
->io_header
.dxfer_direction
= direction
;
208 r
->io_header
.dxferp
= r
->buf
;
209 r
->io_header
.dxfer_len
= r
->buflen
;
210 r
->io_header
.cmdp
= r
->cmd
;
211 r
->io_header
.cmd_len
= r
->cmdlen
;
212 r
->io_header
.mx_sb_len
= sizeof(r
->dev
->sensebuf
);
213 r
->io_header
.sbp
= r
->dev
->sensebuf
;
214 r
->io_header
.timeout
= MAX_UINT
;
215 r
->io_header
.usr_ptr
= r
;
216 r
->io_header
.flags
|= SG_FLAG_DIRECT_IO
;
218 ret
= bdrv_sg_send_command(bdrv
, &r
->io_header
, sizeof(r
->io_header
));
220 BADF("execute_command: write failed ! (%d)\n", errno
);
223 if (complete
== NULL
) {
226 while ((ret
= bdrv_sg_recv_response(bdrv
, &r
->io_header
,
227 sizeof(r
->io_header
))) < 0 &&
231 BADF("execute_command: read failed !\n");
237 r
->aiocb
= bdrv_sg_aio_read(bdrv
, (uint8_t*)&r
->io_header
,
238 sizeof(r
->io_header
), complete
, r
);
239 if (r
->aiocb
== NULL
) {
240 BADF("execute_command: read failed !\n");
247 static void scsi_read_complete(void * opaque
, int ret
)
249 SCSIRequest
*r
= (SCSIRequest
*)opaque
;
250 SCSIDeviceState
*s
= r
->dev
;
254 DPRINTF("IO error\n");
255 scsi_command_complete(r
, ret
);
258 len
= r
->io_header
.dxfer_len
- r
->io_header
.resid
;
259 DPRINTF("Data ready tag=0x%x len=%d\n", r
->tag
, len
);
262 s
->completion(s
->opaque
, SCSI_REASON_DATA
, r
->tag
, len
);
264 scsi_command_complete(r
, 0);
267 /* Read more data from scsi device into buffer. */
268 static void scsi_read_data(SCSIDevice
*d
, uint32_t tag
)
270 SCSIDeviceState
*s
= d
->state
;
274 DPRINTF("scsi_read_data 0x%x\n", tag
);
275 r
= scsi_find_request(s
, tag
);
277 BADF("Bad read tag 0x%x\n", tag
);
278 /* ??? This is the wrong error. */
279 scsi_command_complete(r
, -EINVAL
);
284 scsi_command_complete(r
, 0);
288 if (r
->cmd
[0] == REQUEST_SENSE
&& s
->driver_status
& SG_ERR_DRIVER_SENSE
)
290 s
->senselen
= MIN(r
->len
, s
->senselen
);
291 memcpy(r
->buf
, s
->sensebuf
, s
->senselen
);
292 r
->io_header
.driver_status
= 0;
293 r
->io_header
.status
= 0;
294 r
->io_header
.dxfer_len
= s
->senselen
;
296 DPRINTF("Data ready tag=0x%x len=%d\n", r
->tag
, s
->senselen
);
297 DPRINTF("Sense: %d %d %d %d %d %d %d %d\n",
298 r
->buf
[0], r
->buf
[1], r
->buf
[2], r
->buf
[3],
299 r
->buf
[4], r
->buf
[5], r
->buf
[6], r
->buf
[7]);
300 s
->completion(s
->opaque
, SCSI_REASON_DATA
, r
->tag
, s
->senselen
);
304 ret
= execute_command(s
->bdrv
, r
, SG_DXFER_FROM_DEV
, scsi_read_complete
);
306 scsi_command_complete(r
, -EINVAL
);
311 static void scsi_write_complete(void * opaque
, int ret
)
313 SCSIRequest
*r
= (SCSIRequest
*)opaque
;
315 DPRINTF("scsi_write_complete() ret = %d\n", ret
);
317 DPRINTF("IO error\n");
318 scsi_command_complete(r
, ret
);
322 if (r
->cmd
[0] == MODE_SELECT
&& r
->cmd
[4] == 12 &&
323 r
->dev
->type
== TYPE_TAPE
) {
324 r
->dev
->blocksize
= (r
->buf
[9] << 16) | (r
->buf
[10] << 8) | r
->buf
[11];
325 DPRINTF("block size %d\n", r
->dev
->blocksize
);
328 scsi_command_complete(r
, ret
);
331 /* Write data to a scsi device. Returns nonzero on failure.
332 The transfer may complete asynchronously. */
333 static int scsi_write_data(SCSIDevice
*d
, uint32_t tag
)
335 SCSIDeviceState
*s
= d
->state
;
339 DPRINTF("scsi_write_data 0x%x\n", tag
);
340 r
= scsi_find_request(s
, tag
);
342 BADF("Bad write tag 0x%x\n", tag
);
343 /* ??? This is the wrong error. */
344 scsi_command_complete(r
, -EINVAL
);
350 s
->completion(s
->opaque
, SCSI_REASON_DATA
, r
->tag
, r
->len
);
354 ret
= execute_command(s
->bdrv
, r
, SG_DXFER_TO_DEV
, scsi_write_complete
);
356 scsi_command_complete(r
, -EINVAL
);
363 /* Return a pointer to the data buffer. */
364 static uint8_t *scsi_get_buf(SCSIDevice
*d
, uint32_t tag
)
366 SCSIDeviceState
*s
= d
->state
;
368 r
= scsi_find_request(s
, tag
);
370 BADF("Bad buffer tag 0x%x\n", tag
);
376 static int scsi_length(uint8_t *cmd
, int blocksize
, int *cmdlen
, uint32_t *len
)
378 switch (cmd
[0] >> 5) {
382 /* length 0 means 256 blocks */
388 *len
= cmd
[8] | (cmd
[7] << 8);
392 *len
= cmd
[13] | (cmd
[12] << 8) | (cmd
[11] << 16) | (cmd
[10] << 24);
396 *len
= cmd
[9] | (cmd
[8] << 8) | (cmd
[7] << 16) | (cmd
[6] << 24);
404 case TEST_UNIT_READY
:
408 case WRITE_FILEMARKS
:
411 case ALLOW_MEDIUM_REMOVAL
:
414 case SYNCHRONIZE_CACHE
:
415 case LOCK_UNLOCK_CACHE
:
432 case READ_BLOCK_LIMITS
:
438 case SEND_VOLUME_TAG
:
445 cmd
[1] &= ~0x08; /* disable FUA */
449 case WRITE_VERIFY_12
:
453 cmd
[1] &= ~0x08; /* disable FUA */
456 case RECOVER_BUFFERED_DATA
:
461 *len
= cmd
[4] | (cmd
[3] << 8);
467 static int scsi_stream_length(uint8_t *cmd
, int blocksize
, int *cmdlen
, uint32_t *len
)
470 /* stream commands */
473 case RECOVER_BUFFERED_DATA
:
476 *len
= cmd
[4] | (cmd
[3] << 8) | (cmd
[2] << 16);
477 if (cmd
[1] & 0x01) /* fixed */
484 cmd
[1] = 0x01; /* force IMMED, otherwise qemu waits end of command */
486 /* generic commands */
488 return scsi_length(cmd
, blocksize
, cmdlen
, len
);
493 static int is_write(int command
)
499 case CHANGE_DEFINITION
:
503 case SEND_DIAGNOSTIC
:
506 case REASSIGN_BLOCKS
:
518 case SEARCH_EQUAL_12
:
521 case WRITE_VERIFY_12
:
524 case SEND_VOLUME_TAG
:
531 /* Execute a scsi command. Returns the length of the data expected by the
532 command. This will be Positive for data transfers from the device
533 (eg. disk reads), negative for transfers to the device (eg. disk writes),
534 and zero if the command does not transfer any data. */
536 static int32_t scsi_send_command(SCSIDevice
*d
, uint32_t tag
,
537 uint8_t *cmd
, int lun
)
539 SCSIDeviceState
*s
= d
->state
;
545 if (s
->type
== TYPE_TAPE
) {
546 if (scsi_stream_length(cmd
, s
->blocksize
, &cmdlen
, &len
) == -1) {
547 BADF("Unsupported command length, command %x\n", cmd
[0]);
551 if (scsi_length(cmd
, s
->blocksize
, &cmdlen
, &len
) == -1) {
552 BADF("Unsupported command length, command %x\n", cmd
[0]);
557 DPRINTF("Command: lun=%d tag=0x%x data=0x%02x len %d\n", lun
, tag
,
560 if (cmd
[0] != REQUEST_SENSE
&&
561 (lun
!= s
->lun
|| (cmd
[1] >> 5) != s
->lun
)) {
562 DPRINTF("Unimplemented LUN %d\n", lun
? lun
: cmd
[1] >> 5);
564 s
->sensebuf
[0] = 0x70;
565 s
->sensebuf
[1] = 0x00;
566 s
->sensebuf
[2] = ILLEGAL_REQUEST
;
567 s
->sensebuf
[3] = 0x00;
568 s
->sensebuf
[4] = 0x00;
569 s
->sensebuf
[5] = 0x00;
570 s
->sensebuf
[6] = 0x00;
572 s
->driver_status
= SG_ERR_DRIVER_SENSE
;
573 s
->completion(s
->opaque
, SCSI_REASON_DONE
, tag
, CHECK_CONDITION
<< 1);
577 r
= scsi_find_request(s
, tag
);
579 BADF("Tag 0x%x already in use %p\n", tag
, r
);
580 scsi_cancel_io(d
, tag
);
582 r
= scsi_new_request(s
, tag
);
584 memcpy(r
->cmd
, cmd
, cmdlen
);
592 ret
= execute_command(s
->bdrv
, r
, SG_DXFER_NONE
, scsi_command_complete
);
594 scsi_command_complete(r
, -EINVAL
);
600 if (r
->buflen
!= len
) {
603 r
->buf
= qemu_malloc(len
);
607 memset(r
->buf
, 0, r
->buflen
);
609 if (is_write(cmd
[0])) {
617 static int get_blocksize(BlockDriverState
*bdrv
)
622 sg_io_hdr_t io_header
;
625 memset(cmd
, 0, sizeof(cmd
));
626 memset(buf
, 0, sizeof(buf
));
627 cmd
[0] = READ_CAPACITY
;
629 memset(&io_header
, 0, sizeof(io_header
));
630 io_header
.interface_id
= 'S';
631 io_header
.dxfer_direction
= SG_DXFER_FROM_DEV
;
632 io_header
.dxfer_len
= sizeof(buf
);
633 io_header
.dxferp
= buf
;
634 io_header
.cmdp
= cmd
;
635 io_header
.cmd_len
= sizeof(cmd
);
636 io_header
.mx_sb_len
= sizeof(sensebuf
);
637 io_header
.sbp
= sensebuf
;
638 io_header
.timeout
= 6000; /* XXX */
640 ret
= bdrv_sg_send_command(bdrv
, &io_header
, sizeof(io_header
));
644 while ((ret
= bdrv_sg_recv_response(bdrv
, &io_header
, sizeof(io_header
))) < 0 &&
651 return (buf
[4] << 24) | (buf
[5] << 16) | (buf
[6] << 8) | buf
[7];
654 static int get_stream_blocksize(BlockDriverState
*bdrv
)
659 sg_io_hdr_t io_header
;
662 memset(cmd
, 0, sizeof(cmd
));
663 memset(buf
, 0, sizeof(buf
));
665 cmd
[4] = sizeof(buf
);
667 memset(&io_header
, 0, sizeof(io_header
));
668 io_header
.interface_id
= 'S';
669 io_header
.dxfer_direction
= SG_DXFER_FROM_DEV
;
670 io_header
.dxfer_len
= sizeof(buf
);
671 io_header
.dxferp
= buf
;
672 io_header
.cmdp
= cmd
;
673 io_header
.cmd_len
= sizeof(cmd
);
674 io_header
.mx_sb_len
= sizeof(sensebuf
);
675 io_header
.sbp
= sensebuf
;
676 io_header
.timeout
= 6000; /* XXX */
678 ret
= bdrv_sg_send_command(bdrv
, &io_header
, sizeof(io_header
));
682 while ((ret
= bdrv_sg_recv_response(bdrv
, &io_header
, sizeof(io_header
))) < 0 &&
689 return (buf
[9] << 16) | (buf
[10] << 8) | buf
[11];
692 static void scsi_destroy(SCSIDevice
*d
)
696 r
= d
->state
->requests
;
714 SCSIDevice
*scsi_generic_init(BlockDriverState
*bdrv
, int tcq
,
715 scsi_completionfn completion
, void *opaque
)
720 struct sg_scsi_id scsiid
;
722 /* check we are really using a /dev/sg* file */
724 if (!bdrv_is_sg(bdrv
))
727 /* check we are using a driver managing SG_IO (version 3 and after */
729 if (bdrv_ioctl(bdrv
, SG_GET_VERSION_NUM
, &sg_version
) < 0 ||
733 /* get LUN of the /dev/sg? */
735 if (bdrv_ioctl(bdrv
, SG_GET_SCSI_ID
, &scsiid
))
738 /* define device state */
740 s
= (SCSIDeviceState
*)qemu_mallocz(sizeof(SCSIDeviceState
));
743 s
->completion
= completion
;
746 DPRINTF("LUN %d\n", s
->lun
);
747 s
->type
= scsiid
.scsi_type
;
748 DPRINTF("device type %d\n", s
->type
);
749 if (s
->type
== TYPE_TAPE
) {
750 s
->blocksize
= get_stream_blocksize(s
->bdrv
);
751 if (s
->blocksize
== -1)
754 s
->blocksize
= get_blocksize(s
->bdrv
);
755 /* removable media returns 0 if not present */
756 if (s
->blocksize
<= 0) {
757 if (s
->type
== TYPE_ROM
|| s
->type
== TYPE_WORM
)
763 DPRINTF("block size %d\n", s
->blocksize
);
764 s
->driver_status
= 0;
765 memset(s
->sensebuf
, 0, sizeof(s
->sensebuf
));
767 /* define function to manage device */
769 d
= (SCSIDevice
*)qemu_mallocz(sizeof(SCSIDevice
));
771 d
->destroy
= scsi_destroy
;
772 d
->send_command
= scsi_send_command
;
773 d
->read_data
= scsi_read_data
;
774 d
->write_data
= scsi_write_data
;
775 d
->cancel_io
= scsi_cancel_io
;
776 d
->get_buf
= scsi_get_buf
;
780 #endif /* __linux__ */