Gerd Hoffmann | 1e37607 | 2009-11-26 15:33:47 +0100 | [diff] [blame] | 1 | #ifndef QEMU_HW_SCSI_H |
| 2 | #define QEMU_HW_SCSI_H |
Gerd Hoffmann | 43b443b | 2009-10-30 09:54:00 +0100 | [diff] [blame] | 3 | |
| 4 | #include "qdev.h" |
Gerd Hoffmann | 4c41d2e | 2009-11-26 15:33:48 +0100 | [diff] [blame] | 5 | #include "block.h" |
Gerd Hoffmann | 43b443b | 2009-10-30 09:54:00 +0100 | [diff] [blame] | 6 | |
Gerd Hoffmann | 29362eb | 2009-11-26 15:33:51 +0100 | [diff] [blame] | 7 | #define SCSI_CMD_BUF_SIZE 16 |
| 8 | |
Gerd Hoffmann | 43b443b | 2009-10-30 09:54:00 +0100 | [diff] [blame] | 9 | /* scsi-disk.c */ |
| 10 | enum scsi_reason { |
| 11 | SCSI_REASON_DONE, /* Command complete. */ |
| 12 | SCSI_REASON_DATA /* Transfer complete, more data required. */ |
| 13 | }; |
| 14 | |
| 15 | typedef struct SCSIBus SCSIBus; |
| 16 | typedef struct SCSIDevice SCSIDevice; |
| 17 | typedef struct SCSIDeviceInfo SCSIDeviceInfo; |
| 18 | typedef void (*scsi_completionfn)(SCSIBus *bus, int reason, uint32_t tag, |
| 19 | uint32_t arg); |
| 20 | |
Gerd Hoffmann | 97a0643 | 2009-11-26 15:33:57 +0100 | [diff] [blame] | 21 | enum SCSIXferMode { |
| 22 | SCSI_XFER_NONE, /* TEST_UNIT_READY, ... */ |
| 23 | SCSI_XFER_FROM_DEV, /* READ, INQUIRY, MODE_SENSE, ... */ |
| 24 | SCSI_XFER_TO_DEV, /* WRITE, MODE_SELECT, ... */ |
| 25 | }; |
| 26 | |
Gerd Hoffmann | 37659e5 | 2009-11-26 15:33:58 +0100 | [diff] [blame] | 27 | typedef struct SCSISense { |
| 28 | uint8_t key; |
| 29 | } SCSISense; |
| 30 | |
Gerd Hoffmann | 4c41d2e | 2009-11-26 15:33:48 +0100 | [diff] [blame] | 31 | typedef struct SCSIRequest { |
| 32 | SCSIBus *bus; |
| 33 | SCSIDevice *dev; |
| 34 | uint32_t tag; |
Gerd Hoffmann | 89b08ae | 2009-11-26 15:33:50 +0100 | [diff] [blame] | 35 | uint32_t lun; |
Gerd Hoffmann | ed3a34a | 2009-11-26 15:34:00 +0100 | [diff] [blame^] | 36 | uint32_t status; |
Gerd Hoffmann | 29362eb | 2009-11-26 15:33:51 +0100 | [diff] [blame] | 37 | struct { |
| 38 | uint8_t buf[SCSI_CMD_BUF_SIZE]; |
| 39 | int len; |
Gerd Hoffmann | 2ec749c | 2009-11-26 15:33:55 +0100 | [diff] [blame] | 40 | size_t xfer; |
| 41 | uint64_t lba; |
Gerd Hoffmann | 97a0643 | 2009-11-26 15:33:57 +0100 | [diff] [blame] | 42 | enum SCSIXferMode mode; |
Gerd Hoffmann | 29362eb | 2009-11-26 15:33:51 +0100 | [diff] [blame] | 43 | } cmd; |
Gerd Hoffmann | 4c41d2e | 2009-11-26 15:33:48 +0100 | [diff] [blame] | 44 | BlockDriverAIOCB *aiocb; |
Gerd Hoffmann | 9af99d9 | 2009-11-26 15:33:49 +0100 | [diff] [blame] | 45 | QTAILQ_ENTRY(SCSIRequest) next; |
Gerd Hoffmann | 4c41d2e | 2009-11-26 15:33:48 +0100 | [diff] [blame] | 46 | } SCSIRequest; |
| 47 | |
Gerd Hoffmann | 43b443b | 2009-10-30 09:54:00 +0100 | [diff] [blame] | 48 | struct SCSIDevice |
| 49 | { |
| 50 | DeviceState qdev; |
| 51 | uint32_t id; |
Gerd Hoffmann | 251882b | 2009-11-26 15:33:59 +0100 | [diff] [blame] | 52 | DriveInfo *dinfo; |
Gerd Hoffmann | 43b443b | 2009-10-30 09:54:00 +0100 | [diff] [blame] | 53 | SCSIDeviceInfo *info; |
Gerd Hoffmann | 9af99d9 | 2009-11-26 15:33:49 +0100 | [diff] [blame] | 54 | QTAILQ_HEAD(, SCSIRequest) requests; |
Gerd Hoffmann | b07995e | 2009-11-26 15:33:52 +0100 | [diff] [blame] | 55 | int blocksize; |
Gerd Hoffmann | 9137665 | 2009-11-26 15:33:54 +0100 | [diff] [blame] | 56 | int type; |
Gerd Hoffmann | 37659e5 | 2009-11-26 15:33:58 +0100 | [diff] [blame] | 57 | struct SCSISense sense; |
Gerd Hoffmann | 43b443b | 2009-10-30 09:54:00 +0100 | [diff] [blame] | 58 | }; |
| 59 | |
| 60 | /* cdrom.c */ |
| 61 | int cdrom_read_toc(int nb_sectors, uint8_t *buf, int msf, int start_track); |
| 62 | int cdrom_read_toc_raw(int nb_sectors, uint8_t *buf, int msf, int session_num); |
| 63 | |
| 64 | /* scsi-bus.c */ |
| 65 | typedef int (*scsi_qdev_initfn)(SCSIDevice *dev); |
| 66 | struct SCSIDeviceInfo { |
| 67 | DeviceInfo qdev; |
| 68 | scsi_qdev_initfn init; |
| 69 | void (*destroy)(SCSIDevice *s); |
| 70 | int32_t (*send_command)(SCSIDevice *s, uint32_t tag, uint8_t *buf, |
| 71 | int lun); |
| 72 | void (*read_data)(SCSIDevice *s, uint32_t tag); |
| 73 | int (*write_data)(SCSIDevice *s, uint32_t tag); |
| 74 | void (*cancel_io)(SCSIDevice *s, uint32_t tag); |
| 75 | uint8_t *(*get_buf)(SCSIDevice *s, uint32_t tag); |
| 76 | }; |
| 77 | |
| 78 | typedef void (*SCSIAttachFn)(DeviceState *host, BlockDriverState *bdrv, |
| 79 | int unit); |
| 80 | struct SCSIBus { |
| 81 | BusState qbus; |
| 82 | int busnr; |
| 83 | |
| 84 | int tcq, ndev; |
| 85 | scsi_completionfn complete; |
| 86 | |
| 87 | SCSIDevice *devs[8]; |
| 88 | }; |
| 89 | |
| 90 | void scsi_bus_new(SCSIBus *bus, DeviceState *host, int tcq, int ndev, |
| 91 | scsi_completionfn complete); |
| 92 | void scsi_qdev_register(SCSIDeviceInfo *info); |
| 93 | |
| 94 | static inline SCSIBus *scsi_bus_from_device(SCSIDevice *d) |
| 95 | { |
| 96 | return DO_UPCAST(SCSIBus, qbus, d->qdev.parent_bus); |
| 97 | } |
| 98 | |
| 99 | SCSIDevice *scsi_bus_legacy_add_drive(SCSIBus *bus, DriveInfo *dinfo, int unit); |
| 100 | void scsi_bus_legacy_handle_cmdline(SCSIBus *bus); |
| 101 | |
Gerd Hoffmann | 37659e5 | 2009-11-26 15:33:58 +0100 | [diff] [blame] | 102 | void scsi_dev_clear_sense(SCSIDevice *dev); |
| 103 | void scsi_dev_set_sense(SCSIDevice *dev, uint8_t key); |
| 104 | |
Gerd Hoffmann | 89b08ae | 2009-11-26 15:33:50 +0100 | [diff] [blame] | 105 | SCSIRequest *scsi_req_alloc(size_t size, SCSIDevice *d, uint32_t tag, uint32_t lun); |
| 106 | SCSIRequest *scsi_req_find(SCSIDevice *d, uint32_t tag); |
| 107 | void scsi_req_free(SCSIRequest *req); |
Gerd Hoffmann | 37659e5 | 2009-11-26 15:33:58 +0100 | [diff] [blame] | 108 | |
Gerd Hoffmann | 2ec749c | 2009-11-26 15:33:55 +0100 | [diff] [blame] | 109 | int scsi_req_parse(SCSIRequest *req, uint8_t *buf); |
Gerd Hoffmann | ed3a34a | 2009-11-26 15:34:00 +0100 | [diff] [blame^] | 110 | void scsi_req_complete(SCSIRequest *req); |
Gerd Hoffmann | 89b08ae | 2009-11-26 15:33:50 +0100 | [diff] [blame] | 111 | |
Gerd Hoffmann | 43b443b | 2009-10-30 09:54:00 +0100 | [diff] [blame] | 112 | #endif |