]> git.proxmox.com Git - qemu.git/blame - hw/scsi-disk.c
scsi-disk: remove cluster_size
[qemu.git] / hw / scsi-disk.c
CommitLineData
2e5d83bb
PB
1/*
2 * SCSI Device emulation
3 *
4 * Copyright (c) 2006 CodeSourcery.
5 * Based on code by Fabrice Bellard
6 *
7 * Written by Paul Brook
ad3cea42
AT
8 * Modifications:
9 * 2009-Dec-12 Artyom Tarasenko : implemented stamdard inquiry for the case
10 * when the allocation length of CDB is smaller
11 * than 36.
12 * 2009-Oct-13 Artyom Tarasenko : implemented the block descriptor in the
13 * MODE SENSE response.
2e5d83bb 14 *
8e31bf38 15 * This code is licensed under the LGPL.
a917d384
PB
16 *
17 * Note that this file only handles the SCSI architecture model and device
1d4db89c
AZ
18 * commands. Emulation of interface/link layer protocols is handled by
19 * the host adapter emulator.
2e5d83bb
PB
20 */
21
22//#define DEBUG_SCSI
23
24#ifdef DEBUG_SCSI
001faf32
BS
25#define DPRINTF(fmt, ...) \
26do { printf("scsi-disk: " fmt , ## __VA_ARGS__); } while (0)
2e5d83bb 27#else
001faf32 28#define DPRINTF(fmt, ...) do {} while(0)
2e5d83bb
PB
29#endif
30
001faf32
BS
31#define BADF(fmt, ...) \
32do { fprintf(stderr, "scsi-disk: " fmt , ## __VA_ARGS__); } while (0)
2e5d83bb 33
87ecb68b 34#include "qemu-common.h"
2f792016 35#include "qemu-error.h"
43b443b6 36#include "scsi.h"
0d65e1f8 37#include "scsi-defs.h"
666daa68 38#include "sysemu.h"
2446333c 39#include "blockdev.h"
d1a0739d 40#include "block_int.h"
22864256 41
f0f72ffe 42#define SCSI_DMA_BUF_SIZE 131072
57575058 43#define SCSI_MAX_INQUIRY_LEN 256
a917d384 44
5dba48a8
KW
45#define SCSI_REQ_STATUS_RETRY 0x01
46#define SCSI_REQ_STATUS_RETRY_TYPE_MASK 0x06
47#define SCSI_REQ_STATUS_RETRY_READ 0x00
48#define SCSI_REQ_STATUS_RETRY_WRITE 0x02
78ced65e 49#define SCSI_REQ_STATUS_RETRY_FLUSH 0x04
ea8a5d7f 50
d52affa7
GH
51typedef struct SCSIDiskState SCSIDiskState;
52
4c41d2ef
GH
53typedef struct SCSIDiskReq {
54 SCSIRequest req;
a917d384 55 /* Both sector and sector_count are in terms of qemu 512 byte blocks. */
e035b43d
AL
56 uint64_t sector;
57 uint32_t sector_count;
7285477a 58 uint32_t buflen;
c87c0672
AL
59 struct iovec iov;
60 QEMUIOVector qiov;
ea8a5d7f 61 uint32_t status;
a597e79c 62 BlockAcctCookie acct;
4c41d2ef 63} SCSIDiskReq;
a917d384 64
d52affa7 65struct SCSIDiskState
a917d384 66{
d52affa7 67 SCSIDevice qdev;
419e691f 68 uint32_t removable;
274fb0e1 69 uint64_t max_lba;
8a9c16f6 70 bool media_changed;
3c2f7c12 71 bool media_event;
213189ab 72 QEMUBH *bh;
383b4d9b 73 char *version;
a0fef654 74 char *serial;
ece0d5e9 75 bool tray_open;
81b1008d 76 bool tray_locked;
2e5d83bb
PB
77};
78
5dba48a8 79static int scsi_handle_rw_error(SCSIDiskReq *r, int error, int type);
628e95b6 80static int32_t scsi_send_command(SCSIRequest *req, uint8_t *buf);
5dba48a8 81
ad2d30f7 82static void scsi_free_request(SCSIRequest *req)
4d611c9a 83{
ad2d30f7
PB
84 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
85
7285477a
PB
86 if (r->iov.iov_base) {
87 qemu_vfree(r->iov.iov_base);
88 }
4d611c9a
PB
89}
90
b45ef674
PB
91/* Helper function for command completion with sense. */
92static void scsi_check_condition(SCSIDiskReq *r, SCSISense sense)
ed3a34a3 93{
02fa69b6
BS
94 DPRINTF("Command complete tag=0x%x sense=%d/%d/%d\n",
95 r->req.tag, sense.key, sense.asc, sense.ascq);
b45ef674
PB
96 scsi_req_build_sense(&r->req, sense);
97 scsi_req_complete(&r->req, CHECK_CONDITION);
4d611c9a
PB
98}
99
100/* Cancel a pending data transfer. */
5c6c0e51 101static void scsi_cancel_io(SCSIRequest *req)
4d611c9a 102{
5c6c0e51
HR
103 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
104
105 DPRINTF("Cancel tag=0x%x\n", req->tag);
106 if (r->req.aiocb) {
107 bdrv_aio_cancel(r->req.aiocb);
a917d384 108 }
5c6c0e51 109 r->req.aiocb = NULL;
a917d384
PB
110}
111
103b40f5
PB
112static uint32_t scsi_init_iovec(SCSIDiskReq *r)
113{
7285477a
PB
114 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
115
116 if (!r->iov.iov_base) {
117 r->buflen = SCSI_DMA_BUF_SIZE;
44740c38 118 r->iov.iov_base = qemu_blockalign(s->qdev.conf.bs, r->buflen);
7285477a
PB
119 }
120 r->iov.iov_len = MIN(r->sector_count * 512, r->buflen);
103b40f5
PB
121 qemu_iovec_init_external(&r->qiov, &r->iov, 1);
122 return r->qiov.size / 512;
123}
124
a917d384
PB
125static void scsi_read_complete(void * opaque, int ret)
126{
4c41d2ef 127 SCSIDiskReq *r = (SCSIDiskReq *)opaque;
a597e79c 128 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
5dba48a8 129 int n;
a917d384 130
8e321cc6
PB
131 if (r->req.aiocb != NULL) {
132 r->req.aiocb = NULL;
44740c38 133 bdrv_acct_done(s->qdev.conf.bs, &r->acct);
8e321cc6 134 }
a597e79c 135
a917d384 136 if (ret) {
5dba48a8
KW
137 if (scsi_handle_rw_error(r, -ret, SCSI_REQ_STATUS_RETRY_READ)) {
138 return;
139 }
4d611c9a 140 }
5dba48a8 141
103b40f5 142 DPRINTF("Data ready tag=0x%x len=%zd\n", r->req.tag, r->qiov.size);
a917d384 143
103b40f5 144 n = r->qiov.size / 512;
5dba48a8
KW
145 r->sector += n;
146 r->sector_count -= n;
103b40f5 147 scsi_req_data(&r->req, r->qiov.size);
4d611c9a
PB
148}
149
0a4ac106
PB
150static void scsi_flush_complete(void * opaque, int ret)
151{
152 SCSIDiskReq *r = (SCSIDiskReq *)opaque;
153 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
154
155 if (r->req.aiocb != NULL) {
156 r->req.aiocb = NULL;
44740c38 157 bdrv_acct_done(s->qdev.conf.bs, &r->acct);
0a4ac106
PB
158 }
159
160 if (ret < 0) {
161 if (scsi_handle_rw_error(r, -ret, SCSI_REQ_STATUS_RETRY_FLUSH)) {
162 return;
163 }
164 }
165
166 scsi_req_complete(&r->req, GOOD);
167}
5dba48a8 168
5c6c0e51
HR
169/* Read more data from scsi device into buffer. */
170static void scsi_read_data(SCSIRequest *req)
2e5d83bb 171{
5c6c0e51 172 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
5dba48a8 173 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
2e5d83bb
PB
174 uint32_t n;
175
a917d384 176 if (r->sector_count == (uint32_t)-1) {
aa2b1e89 177 DPRINTF("Read buf_len=%zd\n", r->iov.iov_len);
a917d384 178 r->sector_count = 0;
ab9adc88 179 scsi_req_data(&r->req, r->iov.iov_len);
a917d384 180 return;
2e5d83bb 181 }
a917d384
PB
182 DPRINTF("Read sector_count=%d\n", r->sector_count);
183 if (r->sector_count == 0) {
b45ef674
PB
184 /* This also clears the sense buffer for REQUEST SENSE. */
185 scsi_req_complete(&r->req, GOOD);
a917d384 186 return;
2e5d83bb
PB
187 }
188
6fa2c95f
SH
189 /* No data transfer may already be in progress */
190 assert(r->req.aiocb == NULL);
191
efb9ee02
HR
192 if (r->req.cmd.mode == SCSI_XFER_TO_DEV) {
193 DPRINTF("Data transfer direction invalid\n");
194 scsi_read_complete(r, -EINVAL);
195 return;
196 }
197
a1aff5bf
MA
198 if (s->tray_open) {
199 scsi_read_complete(r, -ENOMEDIUM);
200 }
103b40f5 201 n = scsi_init_iovec(r);
44740c38
PB
202 bdrv_acct_start(s->qdev.conf.bs, &r->acct, n * BDRV_SECTOR_SIZE, BDRV_ACCT_READ);
203 r->req.aiocb = bdrv_aio_readv(s->qdev.conf.bs, r->sector, &r->qiov, n,
c87c0672 204 scsi_read_complete, r);
d33ea50a
KW
205 if (r->req.aiocb == NULL) {
206 scsi_read_complete(r, -EIO);
207 }
2e5d83bb
PB
208}
209
5dba48a8
KW
210static int scsi_handle_rw_error(SCSIDiskReq *r, int error, int type)
211{
212 int is_read = (type == SCSI_REQ_STATUS_RETRY_READ);
4c41d2ef 213 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
44740c38 214 BlockErrorAction action = bdrv_get_on_error(s->qdev.conf.bs, is_read);
ea8a5d7f 215
380f640f 216 if (action == BLOCK_ERR_IGNORE) {
44740c38 217 bdrv_mon_event(s->qdev.conf.bs, BDRV_ACTION_IGNORE, is_read);
ea8a5d7f 218 return 0;
380f640f 219 }
ea8a5d7f
AL
220
221 if ((error == ENOSPC && action == BLOCK_ERR_STOP_ENOSPC)
222 || action == BLOCK_ERR_STOP_ANY) {
5dba48a8
KW
223
224 type &= SCSI_REQ_STATUS_RETRY_TYPE_MASK;
225 r->status |= SCSI_REQ_STATUS_RETRY | type;
226
44740c38 227 bdrv_mon_event(s->qdev.conf.bs, BDRV_ACTION_STOP, is_read);
0461d5a6 228 vm_stop(RUN_STATE_IO_ERROR);
44740c38 229 bdrv_iostatus_set_err(s->qdev.conf.bs, error);
ea8a5d7f 230 } else {
efb9ee02 231 switch (error) {
7e218df5
PB
232 case ENOMEDIUM:
233 scsi_check_condition(r, SENSE_CODE(NO_MEDIUM));
234 break;
efb9ee02 235 case ENOMEM:
b45ef674 236 scsi_check_condition(r, SENSE_CODE(TARGET_FAILURE));
efb9ee02
HR
237 break;
238 case EINVAL:
b45ef674 239 scsi_check_condition(r, SENSE_CODE(INVALID_FIELD));
efb9ee02
HR
240 break;
241 default:
b45ef674 242 scsi_check_condition(r, SENSE_CODE(IO_ERROR));
efb9ee02 243 break;
a1f0cce2 244 }
44740c38 245 bdrv_mon_event(s->qdev.conf.bs, BDRV_ACTION_REPORT, is_read);
ea8a5d7f 246 }
ea8a5d7f
AL
247 return 1;
248}
249
4d611c9a
PB
250static void scsi_write_complete(void * opaque, int ret)
251{
4c41d2ef 252 SCSIDiskReq *r = (SCSIDiskReq *)opaque;
a597e79c 253 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
ea8a5d7f
AL
254 uint32_t n;
255
8e321cc6
PB
256 if (r->req.aiocb != NULL) {
257 r->req.aiocb = NULL;
44740c38 258 bdrv_acct_done(s->qdev.conf.bs, &r->acct);
8e321cc6 259 }
a597e79c 260
4d611c9a 261 if (ret) {
5dba48a8 262 if (scsi_handle_rw_error(r, -ret, SCSI_REQ_STATUS_RETRY_WRITE)) {
ea8a5d7f 263 return;
5dba48a8 264 }
4d611c9a
PB
265 }
266
103b40f5 267 n = r->qiov.size / 512;
ea8a5d7f
AL
268 r->sector += n;
269 r->sector_count -= n;
a917d384 270 if (r->sector_count == 0) {
b45ef674 271 scsi_req_complete(&r->req, GOOD);
a917d384 272 } else {
103b40f5
PB
273 scsi_init_iovec(r);
274 DPRINTF("Write complete tag=0x%x more=%d\n", r->req.tag, r->qiov.size);
275 scsi_req_data(&r->req, r->qiov.size);
4d611c9a 276 }
4d611c9a
PB
277}
278
42741212 279static void scsi_write_data(SCSIRequest *req)
ea8a5d7f 280{
5c6c0e51 281 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
4c41d2ef 282 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
ea8a5d7f
AL
283 uint32_t n;
284
6fa2c95f
SH
285 /* No data transfer may already be in progress */
286 assert(r->req.aiocb == NULL);
287
efb9ee02
HR
288 if (r->req.cmd.mode != SCSI_XFER_TO_DEV) {
289 DPRINTF("Data transfer direction invalid\n");
290 scsi_write_complete(r, -EINVAL);
42741212 291 return;
efb9ee02
HR
292 }
293
103b40f5 294 n = r->qiov.size / 512;
ea8a5d7f 295 if (n) {
a1aff5bf
MA
296 if (s->tray_open) {
297 scsi_write_complete(r, -ENOMEDIUM);
298 }
44740c38
PB
299 bdrv_acct_start(s->qdev.conf.bs, &r->acct, n * BDRV_SECTOR_SIZE, BDRV_ACCT_WRITE);
300 r->req.aiocb = bdrv_aio_writev(s->qdev.conf.bs, r->sector, &r->qiov, n,
103b40f5 301 scsi_write_complete, r);
d33ea50a 302 if (r->req.aiocb == NULL) {
a1f0cce2 303 scsi_write_complete(r, -ENOMEM);
d33ea50a 304 }
ea8a5d7f 305 } else {
103b40f5 306 /* Called for the first time. Ask the driver to send us more data. */
ea8a5d7f
AL
307 scsi_write_complete(r, 0);
308 }
a917d384 309}
2e5d83bb 310
213189ab 311static void scsi_dma_restart_bh(void *opaque)
ea8a5d7f 312{
d52affa7 313 SCSIDiskState *s = opaque;
9af99d98
GH
314 SCSIRequest *req;
315 SCSIDiskReq *r;
213189ab
MA
316
317 qemu_bh_delete(s->bh);
318 s->bh = NULL;
ea8a5d7f 319
9af99d98
GH
320 QTAILQ_FOREACH(req, &s->qdev.requests, next) {
321 r = DO_UPCAST(SCSIDiskReq, req, req);
ea8a5d7f 322 if (r->status & SCSI_REQ_STATUS_RETRY) {
5dba48a8 323 int status = r->status;
78ced65e 324
5dba48a8
KW
325 r->status &=
326 ~(SCSI_REQ_STATUS_RETRY | SCSI_REQ_STATUS_RETRY_TYPE_MASK);
327
328 switch (status & SCSI_REQ_STATUS_RETRY_TYPE_MASK) {
329 case SCSI_REQ_STATUS_RETRY_READ:
5c6c0e51 330 scsi_read_data(&r->req);
5dba48a8
KW
331 break;
332 case SCSI_REQ_STATUS_RETRY_WRITE:
5c6c0e51 333 scsi_write_data(&r->req);
5dba48a8 334 break;
78ced65e 335 case SCSI_REQ_STATUS_RETRY_FLUSH:
628e95b6
PB
336 scsi_send_command(&r->req, r->req.cmd.buf);
337 break;
5dba48a8 338 }
ea8a5d7f 339 }
ea8a5d7f
AL
340 }
341}
342
1dfb4dd9 343static void scsi_dma_restart_cb(void *opaque, int running, RunState state)
213189ab 344{
d52affa7 345 SCSIDiskState *s = opaque;
213189ab 346
f01b5931 347 if (!running) {
213189ab 348 return;
f01b5931 349 }
213189ab
MA
350 if (!s->bh) {
351 s->bh = qemu_bh_new(scsi_dma_restart_bh, s);
352 qemu_bh_schedule(s->bh);
353 }
354}
355
a917d384 356/* Return a pointer to the data buffer. */
5c6c0e51 357static uint8_t *scsi_get_buf(SCSIRequest *req)
a917d384 358{
5c6c0e51 359 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
2e5d83bb 360
3f4cb3d3 361 return (uint8_t *)r->iov.iov_base;
2e5d83bb
PB
362}
363
0b06c059
GH
364static int scsi_disk_emulate_inquiry(SCSIRequest *req, uint8_t *outbuf)
365{
383b4d9b 366 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
0b06c059
GH
367 int buflen = 0;
368
369 if (req->cmd.buf[1] & 0x2) {
370 /* Command support data - optional, not implemented */
371 BADF("optional INQUIRY command support request not implemented\n");
372 return -1;
373 }
374
375 if (req->cmd.buf[1] & 0x1) {
376 /* Vital product data */
377 uint8_t page_code = req->cmd.buf[2];
378 if (req->cmd.xfer < 4) {
379 BADF("Error: Inquiry (EVPD[%02X]) buffer size %zd is "
380 "less than 4\n", page_code, req->cmd.xfer);
381 return -1;
382 }
383
f37bd73b 384 if (s->qdev.type == TYPE_ROM) {
0b06c059
GH
385 outbuf[buflen++] = 5;
386 } else {
387 outbuf[buflen++] = 0;
388 }
389 outbuf[buflen++] = page_code ; // this page
390 outbuf[buflen++] = 0x00;
391
392 switch (page_code) {
393 case 0x00: /* Supported page codes, mandatory */
39d98982
HR
394 {
395 int pages;
0b06c059
GH
396 DPRINTF("Inquiry EVPD[Supported pages] "
397 "buffer size %zd\n", req->cmd.xfer);
39d98982 398 pages = buflen++;
0b06c059 399 outbuf[buflen++] = 0x00; // list of supported pages (this page)
f01b5931 400 if (s->serial) {
3e1c0c9a 401 outbuf[buflen++] = 0x80; // unit serial number
f01b5931 402 }
0b06c059 403 outbuf[buflen++] = 0x83; // device identification
f37bd73b 404 if (s->qdev.type == TYPE_DISK) {
ea3bd56f
CH
405 outbuf[buflen++] = 0xb0; // block limits
406 outbuf[buflen++] = 0xb2; // thin provisioning
39d98982
HR
407 }
408 outbuf[pages] = buflen - pages - 1; // number of pages
0b06c059 409 break;
39d98982 410 }
0b06c059
GH
411 case 0x80: /* Device serial number, optional */
412 {
3e1c0c9a 413 int l;
0b06c059 414
3e1c0c9a
HR
415 if (!s->serial) {
416 DPRINTF("Inquiry (EVPD[Serial number] not supported\n");
417 return -1;
418 }
419
420 l = strlen(s->serial);
f01b5931 421 if (l > req->cmd.xfer) {
0b06c059 422 l = req->cmd.xfer;
f01b5931
PB
423 }
424 if (l > 20) {
0b06c059 425 l = 20;
f01b5931 426 }
0b06c059
GH
427
428 DPRINTF("Inquiry EVPD[Serial number] "
429 "buffer size %zd\n", req->cmd.xfer);
430 outbuf[buflen++] = l;
a0fef654 431 memcpy(outbuf+buflen, s->serial, l);
0b06c059
GH
432 buflen += l;
433 break;
434 }
435
436 case 0x83: /* Device identification page, mandatory */
437 {
438 int max_len = 255 - 8;
44740c38 439 int id_len = strlen(bdrv_get_device_name(s->qdev.conf.bs));
0b06c059 440
f01b5931 441 if (id_len > max_len) {
0b06c059 442 id_len = max_len;
f01b5931 443 }
0b06c059
GH
444 DPRINTF("Inquiry EVPD[Device identification] "
445 "buffer size %zd\n", req->cmd.xfer);
446
39d98982 447 outbuf[buflen++] = 4 + id_len;
0b06c059
GH
448 outbuf[buflen++] = 0x2; // ASCII
449 outbuf[buflen++] = 0; // not officially assigned
450 outbuf[buflen++] = 0; // reserved
451 outbuf[buflen++] = id_len; // length of data following
452
44740c38 453 memcpy(outbuf+buflen, bdrv_get_device_name(s->qdev.conf.bs), id_len);
0b06c059
GH
454 buflen += id_len;
455 break;
456 }
ea3bd56f 457 case 0xb0: /* block limits */
ee3659e3 458 {
ea3bd56f
CH
459 unsigned int unmap_sectors =
460 s->qdev.conf.discard_granularity / s->qdev.blocksize;
8cfacf07
CH
461 unsigned int min_io_size =
462 s->qdev.conf.min_io_size / s->qdev.blocksize;
463 unsigned int opt_io_size =
464 s->qdev.conf.opt_io_size / s->qdev.blocksize;
ee3659e3 465
f37bd73b 466 if (s->qdev.type == TYPE_ROM) {
39d98982
HR
467 DPRINTF("Inquiry (EVPD[%02X] not supported for CDROM\n",
468 page_code);
469 return -1;
470 }
ee3659e3
CH
471 /* required VPD size with unmap support */
472 outbuf[3] = buflen = 0x3c;
473
474 memset(outbuf + 4, 0, buflen - 4);
475
476 /* optimal transfer length granularity */
477 outbuf[6] = (min_io_size >> 8) & 0xff;
478 outbuf[7] = min_io_size & 0xff;
479
480 /* optimal transfer length */
481 outbuf[12] = (opt_io_size >> 24) & 0xff;
482 outbuf[13] = (opt_io_size >> 16) & 0xff;
483 outbuf[14] = (opt_io_size >> 8) & 0xff;
484 outbuf[15] = opt_io_size & 0xff;
ea3bd56f
CH
485
486 /* optimal unmap granularity */
487 outbuf[28] = (unmap_sectors >> 24) & 0xff;
488 outbuf[29] = (unmap_sectors >> 16) & 0xff;
489 outbuf[30] = (unmap_sectors >> 8) & 0xff;
490 outbuf[31] = unmap_sectors & 0xff;
491 break;
492 }
493 case 0xb2: /* thin provisioning */
494 {
495 outbuf[3] = buflen = 8;
496 outbuf[4] = 0;
497 outbuf[5] = 0x40; /* write same with unmap supported */
498 outbuf[6] = 0;
499 outbuf[7] = 0;
ee3659e3
CH
500 break;
501 }
0b06c059
GH
502 default:
503 BADF("Error: unsupported Inquiry (EVPD[%02X]) "
504 "buffer size %zd\n", page_code, req->cmd.xfer);
505 return -1;
506 }
507 /* done with EVPD */
508 return buflen;
509 }
510
511 /* Standard INQUIRY data */
512 if (req->cmd.buf[2] != 0) {
513 BADF("Error: Inquiry (STANDARD) page or code "
514 "is non-zero [%02X]\n", req->cmd.buf[2]);
515 return -1;
516 }
517
518 /* PAGE CODE == 0 */
519 if (req->cmd.xfer < 5) {
520 BADF("Error: Inquiry (STANDARD) buffer size %zd "
521 "is less than 5\n", req->cmd.xfer);
522 return -1;
523 }
524
0b06c059 525 buflen = req->cmd.xfer;
f01b5931 526 if (buflen > SCSI_MAX_INQUIRY_LEN) {
0b06c059 527 buflen = SCSI_MAX_INQUIRY_LEN;
f01b5931 528 }
0b06c059
GH
529 memset(outbuf, 0, buflen);
530
f37bd73b
HR
531 outbuf[0] = s->qdev.type & 0x1f;
532 if (s->qdev.type == TYPE_ROM) {
0b06c059 533 outbuf[1] = 0x80;
550fe6c6 534 memcpy(&outbuf[16], "QEMU CD-ROM ", 16);
0b06c059 535 } else {
419e691f 536 outbuf[1] = s->removable ? 0x80 : 0;
550fe6c6 537 memcpy(&outbuf[16], "QEMU HARDDISK ", 16);
0b06c059 538 }
550fe6c6 539 memcpy(&outbuf[8], "QEMU ", 8);
314b1811 540 memset(&outbuf[32], 0, 4);
552fee93 541 memcpy(&outbuf[32], s->version, MIN(4, strlen(s->version)));
99aba0c4
CH
542 /*
543 * We claim conformance to SPC-3, which is required for guests
544 * to ask for modern features like READ CAPACITY(16) or the
545 * block characteristics VPD page by default. Not all of SPC-3
546 * is actually implemented, but we're good enough.
547 */
ee3659e3 548 outbuf[2] = 5;
0b06c059 549 outbuf[3] = 2; /* Format 2 */
ad3cea42
AT
550
551 if (buflen > 36) {
552 outbuf[4] = buflen - 5; /* Additional Length = (Len - 1) - 4 */
553 } else {
554 /* If the allocation length of CDB is too small,
555 the additional length is not adjusted */
556 outbuf[4] = 36 - 5;
557 }
558
0b06c059 559 /* Sync data transfer and TCQ. */
afd4030c 560 outbuf[7] = 0x10 | (req->bus->info->tcq ? 0x02 : 0);
0b06c059
GH
561 return buflen;
562}
563
430ee2f2
PB
564static inline bool media_is_dvd(SCSIDiskState *s)
565{
566 uint64_t nb_sectors;
567 if (s->qdev.type != TYPE_ROM) {
568 return false;
569 }
44740c38 570 if (!bdrv_is_inserted(s->qdev.conf.bs)) {
430ee2f2
PB
571 return false;
572 }
44740c38 573 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
430ee2f2
PB
574 return nb_sectors > CD_MAX_SECTORS;
575}
576
ceb792ef
PB
577static inline bool media_is_cd(SCSIDiskState *s)
578{
579 uint64_t nb_sectors;
580 if (s->qdev.type != TYPE_ROM) {
581 return false;
582 }
44740c38 583 if (!bdrv_is_inserted(s->qdev.conf.bs)) {
ceb792ef
PB
584 return false;
585 }
44740c38 586 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
ceb792ef
PB
587 return nb_sectors <= CD_MAX_SECTORS;
588}
589
b6c251ab
PB
590static int scsi_read_dvd_structure(SCSIDiskState *s, SCSIDiskReq *r,
591 uint8_t *outbuf)
592{
ceb792ef
PB
593 static const int rds_caps_size[5] = {
594 [0] = 2048 + 4,
595 [1] = 4 + 4,
596 [3] = 188 + 4,
597 [4] = 2048 + 4,
598 };
599
600 uint8_t media = r->req.cmd.buf[1];
601 uint8_t layer = r->req.cmd.buf[6];
602 uint8_t format = r->req.cmd.buf[7];
603 int size = -1;
604
605 if (s->qdev.type != TYPE_ROM) {
606 return -1;
607 }
608 if (media != 0) {
609 scsi_check_condition(r, SENSE_CODE(INVALID_FIELD));
610 return -1;
611 }
612
613 if (format != 0xff) {
44740c38 614 if (s->tray_open || !bdrv_is_inserted(s->qdev.conf.bs)) {
ceb792ef
PB
615 scsi_check_condition(r, SENSE_CODE(NO_MEDIUM));
616 return -1;
617 }
618 if (media_is_cd(s)) {
619 scsi_check_condition(r, SENSE_CODE(INCOMPATIBLE_FORMAT));
620 return -1;
621 }
622 if (format >= ARRAY_SIZE(rds_caps_size)) {
623 return -1;
624 }
625 size = rds_caps_size[format];
626 memset(outbuf, 0, size);
627 }
628
629 switch (format) {
630 case 0x00: {
631 /* Physical format information */
632 uint64_t nb_sectors;
633 if (layer != 0) {
634 goto fail;
635 }
44740c38 636 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
ceb792ef
PB
637
638 outbuf[4] = 1; /* DVD-ROM, part version 1 */
639 outbuf[5] = 0xf; /* 120mm disc, minimum rate unspecified */
640 outbuf[6] = 1; /* one layer, read-only (per MMC-2 spec) */
641 outbuf[7] = 0; /* default densities */
642
643 stl_be_p(&outbuf[12], (nb_sectors >> 2) - 1); /* end sector */
644 stl_be_p(&outbuf[16], (nb_sectors >> 2) - 1); /* l0 end sector */
645 break;
646 }
647
648 case 0x01: /* DVD copyright information, all zeros */
649 break;
650
651 case 0x03: /* BCA information - invalid field for no BCA info */
652 return -1;
653
654 case 0x04: /* DVD disc manufacturing information, all zeros */
655 break;
656
657 case 0xff: { /* List capabilities */
658 int i;
659 size = 4;
660 for (i = 0; i < ARRAY_SIZE(rds_caps_size); i++) {
661 if (!rds_caps_size[i]) {
662 continue;
663 }
664 outbuf[size] = i;
665 outbuf[size + 1] = 0x40; /* Not writable, readable */
666 stw_be_p(&outbuf[size + 2], rds_caps_size[i]);
667 size += 4;
668 }
669 break;
670 }
671
672 default:
673 return -1;
674 }
675
676 /* Size of buffer, not including 2 byte size field */
677 stw_be_p(outbuf, size - 2);
678 return size;
679
680fail:
b6c251ab
PB
681 return -1;
682}
683
3c2f7c12 684static int scsi_event_status_media(SCSIDiskState *s, uint8_t *outbuf)
b6c251ab 685{
3c2f7c12
PB
686 uint8_t event_code, media_status;
687
688 media_status = 0;
689 if (s->tray_open) {
690 media_status = MS_TRAY_OPEN;
44740c38 691 } else if (bdrv_is_inserted(s->qdev.conf.bs)) {
3c2f7c12
PB
692 media_status = MS_MEDIA_PRESENT;
693 }
694
695 /* Event notification descriptor */
696 event_code = MEC_NO_CHANGE;
697 if (media_status != MS_TRAY_OPEN && s->media_event) {
698 event_code = MEC_NEW_MEDIA;
699 s->media_event = false;
700 }
701
702 outbuf[0] = event_code;
703 outbuf[1] = media_status;
704
705 /* These fields are reserved, just clear them. */
706 outbuf[2] = 0;
707 outbuf[3] = 0;
708 return 4;
709}
710
711static int scsi_get_event_status_notification(SCSIDiskState *s, SCSIDiskReq *r,
712 uint8_t *outbuf)
713{
714 int size;
715 uint8_t *buf = r->req.cmd.buf;
716 uint8_t notification_class_request = buf[4];
717 if (s->qdev.type != TYPE_ROM) {
718 return -1;
719 }
720 if ((buf[1] & 1) == 0) {
721 /* asynchronous */
722 return -1;
723 }
724
725 size = 4;
726 outbuf[0] = outbuf[1] = 0;
727 outbuf[3] = 1 << GESN_MEDIA; /* supported events */
728 if (notification_class_request & (1 << GESN_MEDIA)) {
729 outbuf[2] = GESN_MEDIA;
730 size += scsi_event_status_media(s, &outbuf[size]);
731 } else {
732 outbuf[2] = 0x80;
733 }
734 stw_be_p(outbuf, size - 4);
735 return size;
b6c251ab
PB
736}
737
430ee2f2 738static int scsi_get_configuration(SCSIDiskState *s, uint8_t *outbuf)
b6c251ab 739{
430ee2f2
PB
740 int current;
741
b6c251ab
PB
742 if (s->qdev.type != TYPE_ROM) {
743 return -1;
744 }
430ee2f2
PB
745 current = media_is_dvd(s) ? MMC_PROFILE_DVD_ROM : MMC_PROFILE_CD_ROM;
746 memset(outbuf, 0, 40);
747 stl_be_p(&outbuf[0], 36); /* Bytes after the data length field */
748 stw_be_p(&outbuf[6], current);
749 /* outbuf[8] - outbuf[19]: Feature 0 - Profile list */
750 outbuf[10] = 0x03; /* persistent, current */
751 outbuf[11] = 8; /* two profiles */
752 stw_be_p(&outbuf[12], MMC_PROFILE_DVD_ROM);
753 outbuf[14] = (current == MMC_PROFILE_DVD_ROM);
754 stw_be_p(&outbuf[16], MMC_PROFILE_CD_ROM);
755 outbuf[18] = (current == MMC_PROFILE_CD_ROM);
756 /* outbuf[20] - outbuf[31]: Feature 1 - Core feature */
757 stw_be_p(&outbuf[20], 1);
758 outbuf[22] = 0x08 | 0x03; /* version 2, persistent, current */
759 outbuf[23] = 8;
760 stl_be_p(&outbuf[24], 1); /* SCSI */
761 outbuf[28] = 1; /* DBE = 1, mandatory */
762 /* outbuf[32] - outbuf[39]: Feature 3 - Removable media feature */
763 stw_be_p(&outbuf[32], 3);
764 outbuf[34] = 0x08 | 0x03; /* version 2, persistent, current */
765 outbuf[35] = 4;
766 outbuf[36] = 0x39; /* tray, load=1, eject=1, unlocked at powerup, lock=1 */
767 /* TODO: Random readable, CD read, DVD read, drive serial number,
768 power management */
769 return 40;
b6c251ab
PB
770}
771
772static int scsi_emulate_mechanism_status(SCSIDiskState *s, uint8_t *outbuf)
773{
774 if (s->qdev.type != TYPE_ROM) {
775 return -1;
776 }
777 memset(outbuf, 0, 8);
778 outbuf[5] = 1; /* CD-ROM */
779 return 8;
780}
781
cfc606da 782static int mode_sense_page(SCSIDiskState *s, int page, uint8_t **p_outbuf,
282ab04e 783 int page_control)
ebddfcbe 784{
a8f4bbe2
PB
785 static const int mode_sense_valid[0x3f] = {
786 [MODE_PAGE_HD_GEOMETRY] = (1 << TYPE_DISK),
787 [MODE_PAGE_FLEXIBLE_DISK_GEOMETRY] = (1 << TYPE_DISK),
788 [MODE_PAGE_CACHING] = (1 << TYPE_DISK) | (1 << TYPE_ROM),
a07c7dcd
PB
789 [MODE_PAGE_R_W_ERROR] = (1 << TYPE_DISK) | (1 << TYPE_ROM),
790 [MODE_PAGE_AUDIO_CTL] = (1 << TYPE_ROM),
a8f4bbe2
PB
791 [MODE_PAGE_CAPABILITIES] = (1 << TYPE_ROM),
792 };
793
44740c38 794 BlockDriverState *bdrv = s->qdev.conf.bs;
ebddfcbe 795 int cylinders, heads, secs;
cfc606da 796 uint8_t *p = *p_outbuf;
ebddfcbe 797
a8f4bbe2
PB
798 if ((mode_sense_valid[page] & (1 << s->qdev.type)) == 0) {
799 return -1;
800 }
801
802 p[0] = page;
803
282ab04e
BK
804 /*
805 * If Changeable Values are requested, a mask denoting those mode parameters
806 * that are changeable shall be returned. As we currently don't support
807 * parameter changes via MODE_SELECT all bits are returned set to zero.
808 * The buffer was already menset to zero by the caller of this function.
809 */
ebddfcbe 810 switch (page) {
67cc61e4 811 case MODE_PAGE_HD_GEOMETRY:
ebddfcbe 812 p[1] = 0x16;
282ab04e 813 if (page_control == 1) { /* Changeable Values */
cfc606da 814 break;
282ab04e 815 }
ebddfcbe
GH
816 /* if a geometry hint is available, use it */
817 bdrv_get_geometry_hint(bdrv, &cylinders, &heads, &secs);
818 p[2] = (cylinders >> 16) & 0xff;
819 p[3] = (cylinders >> 8) & 0xff;
820 p[4] = cylinders & 0xff;
821 p[5] = heads & 0xff;
822 /* Write precomp start cylinder, disabled */
823 p[6] = (cylinders >> 16) & 0xff;
824 p[7] = (cylinders >> 8) & 0xff;
825 p[8] = cylinders & 0xff;
826 /* Reduced current start cylinder, disabled */
827 p[9] = (cylinders >> 16) & 0xff;
828 p[10] = (cylinders >> 8) & 0xff;
829 p[11] = cylinders & 0xff;
830 /* Device step rate [ns], 200ns */
831 p[12] = 0;
832 p[13] = 200;
833 /* Landing zone cylinder */
834 p[14] = 0xff;
835 p[15] = 0xff;
836 p[16] = 0xff;
837 /* Medium rotation rate [rpm], 5400 rpm */
838 p[20] = (5400 >> 8) & 0xff;
839 p[21] = 5400 & 0xff;
cfc606da 840 break;
ebddfcbe 841
67cc61e4 842 case MODE_PAGE_FLEXIBLE_DISK_GEOMETRY:
ebddfcbe 843 p[1] = 0x1e;
282ab04e 844 if (page_control == 1) { /* Changeable Values */
cfc606da 845 break;
282ab04e 846 }
ebddfcbe
GH
847 /* Transfer rate [kbit/s], 5Mbit/s */
848 p[2] = 5000 >> 8;
849 p[3] = 5000 & 0xff;
850 /* if a geometry hint is available, use it */
851 bdrv_get_geometry_hint(bdrv, &cylinders, &heads, &secs);
852 p[4] = heads & 0xff;
853 p[5] = secs & 0xff;
69377307 854 p[6] = s->qdev.blocksize >> 8;
ebddfcbe
GH
855 p[8] = (cylinders >> 8) & 0xff;
856 p[9] = cylinders & 0xff;
857 /* Write precomp start cylinder, disabled */
858 p[10] = (cylinders >> 8) & 0xff;
859 p[11] = cylinders & 0xff;
860 /* Reduced current start cylinder, disabled */
861 p[12] = (cylinders >> 8) & 0xff;
862 p[13] = cylinders & 0xff;
863 /* Device step rate [100us], 100us */
864 p[14] = 0;
865 p[15] = 1;
866 /* Device step pulse width [us], 1us */
867 p[16] = 1;
868 /* Device head settle delay [100us], 100us */
869 p[17] = 0;
870 p[18] = 1;
871 /* Motor on delay [0.1s], 0.1s */
872 p[19] = 1;
873 /* Motor off delay [0.1s], 0.1s */
874 p[20] = 1;
875 /* Medium rotation rate [rpm], 5400 rpm */
876 p[28] = (5400 >> 8) & 0xff;
877 p[29] = 5400 & 0xff;
cfc606da 878 break;
ebddfcbe 879
67cc61e4 880 case MODE_PAGE_CACHING:
ebddfcbe
GH
881 p[0] = 8;
882 p[1] = 0x12;
282ab04e 883 if (page_control == 1) { /* Changeable Values */
cfc606da 884 break;
282ab04e 885 }
44740c38 886 if (bdrv_enable_write_cache(s->qdev.conf.bs)) {
ebddfcbe
GH
887 p[2] = 4; /* WCE */
888 }
cfc606da 889 break;
ebddfcbe 890
a07c7dcd
PB
891 case MODE_PAGE_R_W_ERROR:
892 p[1] = 10;
893 p[2] = 0x80; /* Automatic Write Reallocation Enabled */
894 if (s->qdev.type == TYPE_ROM) {
895 p[3] = 0x20; /* Read Retry Count */
896 }
897 break;
898
899 case MODE_PAGE_AUDIO_CTL:
900 p[1] = 14;
901 break;
902
67cc61e4 903 case MODE_PAGE_CAPABILITIES:
ebddfcbe 904 p[1] = 0x14;
282ab04e 905 if (page_control == 1) { /* Changeable Values */
cfc606da 906 break;
282ab04e 907 }
a07c7dcd
PB
908
909 p[2] = 0x3b; /* CD-R & CD-RW read */
910 p[3] = 0; /* Writing not supported */
ebddfcbe
GH
911 p[4] = 0x7f; /* Audio, composite, digital out,
912 mode 2 form 1&2, multi session */
913 p[5] = 0xff; /* CD DA, DA accurate, RW supported,
914 RW corrected, C2 errors, ISRC,
915 UPC, Bar code */
81b1008d 916 p[6] = 0x2d | (s->tray_locked ? 2 : 0);
ebddfcbe
GH
917 /* Locking supported, jumper present, eject, tray */
918 p[7] = 0; /* no volume & mute control, no
919 changer */
a07c7dcd 920 p[8] = (50 * 176) >> 8; /* 50x read speed */
ebddfcbe 921 p[9] = (50 * 176) & 0xff;
a07c7dcd
PB
922 p[10] = 2 >> 8; /* Two volume levels */
923 p[11] = 2 & 0xff;
924 p[12] = 2048 >> 8; /* 2M buffer */
ebddfcbe 925 p[13] = 2048 & 0xff;
a07c7dcd 926 p[14] = (16 * 176) >> 8; /* 16x read speed current */
ebddfcbe 927 p[15] = (16 * 176) & 0xff;
a07c7dcd 928 p[18] = (16 * 176) >> 8; /* 16x write speed */
ebddfcbe 929 p[19] = (16 * 176) & 0xff;
a07c7dcd 930 p[20] = (16 * 176) >> 8; /* 16x write speed current */
ebddfcbe 931 p[21] = (16 * 176) & 0xff;
cfc606da 932 break;
ebddfcbe
GH
933
934 default:
cfc606da 935 return -1;
ebddfcbe 936 }
cfc606da
PB
937
938 *p_outbuf += p[1] + 2;
939 return p[1] + 2;
ebddfcbe
GH
940}
941
cfc606da 942static int scsi_disk_emulate_mode_sense(SCSIDiskReq *r, uint8_t *outbuf)
ebddfcbe 943{
cfc606da 944 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
ebddfcbe 945 uint64_t nb_sectors;
cfc606da 946 int page, dbd, buflen, ret, page_control;
ebddfcbe 947 uint8_t *p;
ce512ee1 948 uint8_t dev_specific_param;
ebddfcbe 949
cfc606da
PB
950 dbd = r->req.cmd.buf[1] & 0x8;
951 page = r->req.cmd.buf[2] & 0x3f;
952 page_control = (r->req.cmd.buf[2] & 0xc0) >> 6;
aa2b1e89 953 DPRINTF("Mode Sense(%d) (page %d, xfer %zd, page_control %d)\n",
cfc606da
PB
954 (r->req.cmd.buf[0] == MODE_SENSE) ? 6 : 10, page, r->req.cmd.xfer, page_control);
955 memset(outbuf, 0, r->req.cmd.xfer);
ebddfcbe
GH
956 p = outbuf;
957
44740c38 958 if (bdrv_is_read_only(s->qdev.conf.bs)) {
ce512ee1
BK
959 dev_specific_param = 0x80; /* Readonly. */
960 } else {
961 dev_specific_param = 0x00;
962 }
963
cfc606da 964 if (r->req.cmd.buf[0] == MODE_SENSE) {
ce512ee1
BK
965 p[1] = 0; /* Default media type. */
966 p[2] = dev_specific_param;
967 p[3] = 0; /* Block descriptor length. */
968 p += 4;
969 } else { /* MODE_SENSE_10 */
970 p[2] = 0; /* Default media type. */
971 p[3] = dev_specific_param;
972 p[6] = p[7] = 0; /* Block descriptor length. */
973 p += 8;
ebddfcbe 974 }
ebddfcbe 975
44740c38 976 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
333d50fe 977 if (!dbd && nb_sectors) {
cfc606da 978 if (r->req.cmd.buf[0] == MODE_SENSE) {
ce512ee1
BK
979 outbuf[3] = 8; /* Block descriptor length */
980 } else { /* MODE_SENSE_10 */
981 outbuf[7] = 8; /* Block descriptor length */
982 }
69377307 983 nb_sectors /= (s->qdev.blocksize / 512);
f01b5931 984 if (nb_sectors > 0xffffff) {
2488b740 985 nb_sectors = 0;
f01b5931 986 }
ebddfcbe
GH
987 p[0] = 0; /* media density code */
988 p[1] = (nb_sectors >> 16) & 0xff;
989 p[2] = (nb_sectors >> 8) & 0xff;
990 p[3] = nb_sectors & 0xff;
991 p[4] = 0; /* reserved */
992 p[5] = 0; /* bytes 5-7 are the sector size in bytes */
69377307 993 p[6] = s->qdev.blocksize >> 8;
ebddfcbe
GH
994 p[7] = 0;
995 p += 8;
996 }
997
cfc606da
PB
998 if (page_control == 3) {
999 /* Saved Values */
1000 scsi_check_condition(r, SENSE_CODE(SAVING_PARAMS_NOT_SUPPORTED));
1001 return -1;
282ab04e
BK
1002 }
1003
cfc606da
PB
1004 if (page == 0x3f) {
1005 for (page = 0; page <= 0x3e; page++) {
1006 mode_sense_page(s, page, &p, page_control);
1007 }
1008 } else {
1009 ret = mode_sense_page(s, page, &p, page_control);
1010 if (ret == -1) {
1011 return -1;
1012 }
ebddfcbe
GH
1013 }
1014
1015 buflen = p - outbuf;
ce512ee1
BK
1016 /*
1017 * The mode data length field specifies the length in bytes of the
1018 * following data that is available to be transferred. The mode data
1019 * length does not include itself.
1020 */
cfc606da 1021 if (r->req.cmd.buf[0] == MODE_SENSE) {
ce512ee1
BK
1022 outbuf[0] = buflen - 1;
1023 } else { /* MODE_SENSE_10 */
1024 outbuf[0] = ((buflen - 2) >> 8) & 0xff;
1025 outbuf[1] = (buflen - 2) & 0xff;
1026 }
f01b5931 1027 if (buflen > r->req.cmd.xfer) {
cfc606da 1028 buflen = r->req.cmd.xfer;
f01b5931 1029 }
ebddfcbe
GH
1030 return buflen;
1031}
1032
02880f43
GH
1033static int scsi_disk_emulate_read_toc(SCSIRequest *req, uint8_t *outbuf)
1034{
1035 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
02880f43
GH
1036 int start_track, format, msf, toclen;
1037 uint64_t nb_sectors;
1038
1039 msf = req->cmd.buf[1] & 2;
1040 format = req->cmd.buf[2] & 0xf;
1041 start_track = req->cmd.buf[6];
44740c38 1042 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
02880f43 1043 DPRINTF("Read TOC (track %d format %d msf %d)\n", start_track, format, msf >> 1);
69377307 1044 nb_sectors /= s->qdev.blocksize / 512;
02880f43
GH
1045 switch (format) {
1046 case 0:
1047 toclen = cdrom_read_toc(nb_sectors, outbuf, msf, start_track);
1048 break;
1049 case 1:
1050 /* multi session : only a single session defined */
1051 toclen = 12;
1052 memset(outbuf, 0, 12);
1053 outbuf[1] = 0x0a;
1054 outbuf[2] = 0x01;
1055 outbuf[3] = 0x01;
1056 break;
1057 case 2:
1058 toclen = cdrom_read_toc_raw(nb_sectors, outbuf, msf, start_track);
1059 break;
1060 default:
1061 return -1;
1062 }
f01b5931 1063 if (toclen > req->cmd.xfer) {
02880f43 1064 toclen = req->cmd.xfer;
f01b5931 1065 }
02880f43
GH
1066 return toclen;
1067}
1068
68bb01f3 1069static int scsi_disk_emulate_start_stop(SCSIDiskReq *r)
bfd52647
MA
1070{
1071 SCSIRequest *req = &r->req;
1072 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
1073 bool start = req->cmd.buf[4] & 1;
1074 bool loej = req->cmd.buf[4] & 2; /* load on start, eject on !start */
1075
1076 if (s->qdev.type == TYPE_ROM && loej) {
68bb01f3
MA
1077 if (!start && !s->tray_open && s->tray_locked) {
1078 scsi_check_condition(r,
44740c38 1079 bdrv_is_inserted(s->qdev.conf.bs)
68bb01f3
MA
1080 ? SENSE_CODE(ILLEGAL_REQ_REMOVAL_PREVENTED)
1081 : SENSE_CODE(NOT_READY_REMOVAL_PREVENTED));
1082 return -1;
fdec4404 1083 }
44740c38 1084 bdrv_eject(s->qdev.conf.bs, !start);
ece0d5e9 1085 s->tray_open = !start;
bfd52647 1086 }
68bb01f3 1087 return 0;
bfd52647
MA
1088}
1089
7285477a 1090static int scsi_disk_emulate_command(SCSIDiskReq *r)
aa5dbdc1 1091{
8af7a3ab 1092 SCSIRequest *req = &r->req;
e7e25e32 1093 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
e7e25e32 1094 uint64_t nb_sectors;
7285477a 1095 uint8_t *outbuf;
aa5dbdc1
GH
1096 int buflen = 0;
1097
7285477a
PB
1098 if (!r->iov.iov_base) {
1099 /*
1100 * FIXME: we shouldn't return anything bigger than 4k, but the code
1101 * requires the buffer to be as big as req->cmd.xfer in several
1102 * places. So, do not allow CDBs with a very large ALLOCATION
1103 * LENGTH. The real fix would be to modify scsi_read_data and
1104 * dma_buf_read, so that they return data beyond the buflen
1105 * as all zeros.
1106 */
1107 if (req->cmd.xfer > 65536) {
1108 goto illegal_request;
1109 }
1110 r->buflen = MAX(4096, req->cmd.xfer);
44740c38 1111 r->iov.iov_base = qemu_blockalign(s->qdev.conf.bs, r->buflen);
7285477a
PB
1112 }
1113
1114 outbuf = r->iov.iov_base;
aa5dbdc1
GH
1115 switch (req->cmd.buf[0]) {
1116 case TEST_UNIT_READY:
44740c38 1117 if (s->tray_open || !bdrv_is_inserted(s->qdev.conf.bs)) {
aa5dbdc1 1118 goto not_ready;
f01b5931 1119 }
5f71d32f 1120 break;
0b06c059
GH
1121 case INQUIRY:
1122 buflen = scsi_disk_emulate_inquiry(req, outbuf);
f01b5931 1123 if (buflen < 0) {
0b06c059 1124 goto illegal_request;
f01b5931 1125 }
5f71d32f 1126 break;
ebddfcbe
GH
1127 case MODE_SENSE:
1128 case MODE_SENSE_10:
cfc606da 1129 buflen = scsi_disk_emulate_mode_sense(r, outbuf);
f01b5931 1130 if (buflen < 0) {
ebddfcbe 1131 goto illegal_request;
f01b5931 1132 }
ebddfcbe 1133 break;
02880f43
GH
1134 case READ_TOC:
1135 buflen = scsi_disk_emulate_read_toc(req, outbuf);
f01b5931 1136 if (buflen < 0) {
02880f43 1137 goto illegal_request;
f01b5931 1138 }
02880f43 1139 break;
3d53ba18 1140 case RESERVE:
f01b5931 1141 if (req->cmd.buf[1] & 1) {
3d53ba18 1142 goto illegal_request;
f01b5931 1143 }
3d53ba18
GH
1144 break;
1145 case RESERVE_10:
f01b5931 1146 if (req->cmd.buf[1] & 3) {
3d53ba18 1147 goto illegal_request;
f01b5931 1148 }
3d53ba18
GH
1149 break;
1150 case RELEASE:
f01b5931 1151 if (req->cmd.buf[1] & 1) {
3d53ba18 1152 goto illegal_request;
f01b5931 1153 }
3d53ba18
GH
1154 break;
1155 case RELEASE_10:
f01b5931 1156 if (req->cmd.buf[1] & 3) {
3d53ba18 1157 goto illegal_request;
f01b5931 1158 }
3d53ba18 1159 break;
8d3628ff 1160 case START_STOP:
68bb01f3
MA
1161 if (scsi_disk_emulate_start_stop(r) < 0) {
1162 return -1;
1163 }
5f71d32f 1164 break;
c68b9f34 1165 case ALLOW_MEDIUM_REMOVAL:
81b1008d 1166 s->tray_locked = req->cmd.buf[4] & 1;
44740c38 1167 bdrv_lock_medium(s->qdev.conf.bs, req->cmd.buf[4] & 1);
5f71d32f 1168 break;
5e30a07d 1169 case READ_CAPACITY_10:
e7e25e32 1170 /* The normal LEN field for this command is zero. */
5f71d32f 1171 memset(outbuf, 0, 8);
44740c38 1172 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
f01b5931 1173 if (!nb_sectors) {
e7e25e32 1174 goto not_ready;
f01b5931 1175 }
7cec78b6
PB
1176 if ((req->cmd.buf[8] & 1) == 0 && req->cmd.lba) {
1177 goto illegal_request;
1178 }
69377307 1179 nb_sectors /= s->qdev.blocksize / 512;
e7e25e32
GH
1180 /* Returned value is the address of the last sector. */
1181 nb_sectors--;
1182 /* Remember the new size for read/write sanity checking. */
1183 s->max_lba = nb_sectors;
1184 /* Clip to 2TB, instead of returning capacity modulo 2TB. */
f01b5931 1185 if (nb_sectors > UINT32_MAX) {
e7e25e32 1186 nb_sectors = UINT32_MAX;
f01b5931 1187 }
e7e25e32
GH
1188 outbuf[0] = (nb_sectors >> 24) & 0xff;
1189 outbuf[1] = (nb_sectors >> 16) & 0xff;
1190 outbuf[2] = (nb_sectors >> 8) & 0xff;
1191 outbuf[3] = nb_sectors & 0xff;
1192 outbuf[4] = 0;
1193 outbuf[5] = 0;
69377307 1194 outbuf[6] = s->qdev.blocksize >> 8;
e7e25e32
GH
1195 outbuf[7] = 0;
1196 buflen = 8;
5f71d32f 1197 break;
b6c251ab
PB
1198 case MECHANISM_STATUS:
1199 buflen = scsi_emulate_mechanism_status(s, outbuf);
1200 if (buflen < 0) {
1201 goto illegal_request;
1202 }
1203 break;
38215553 1204 case GET_CONFIGURATION:
430ee2f2 1205 buflen = scsi_get_configuration(s, outbuf);
b6c251ab
PB
1206 if (buflen < 0) {
1207 goto illegal_request;
1208 }
1209 break;
1210 case GET_EVENT_STATUS_NOTIFICATION:
1211 buflen = scsi_get_event_status_notification(s, r, outbuf);
1212 if (buflen < 0) {
1213 goto illegal_request;
1214 }
1215 break;
1216 case READ_DVD_STRUCTURE:
1217 buflen = scsi_read_dvd_structure(s, r, outbuf);
1218 if (buflen < 0) {
1219 goto illegal_request;
1220 }
38215553 1221 break;
f6515262 1222 case SERVICE_ACTION_IN_16:
5dd90e2a 1223 /* Service Action In subcommands. */
f6515262 1224 if ((req->cmd.buf[1] & 31) == SAI_READ_CAPACITY_16) {
5dd90e2a
GH
1225 DPRINTF("SAI READ CAPACITY(16)\n");
1226 memset(outbuf, 0, req->cmd.xfer);
44740c38 1227 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
f01b5931 1228 if (!nb_sectors) {
5dd90e2a 1229 goto not_ready;
f01b5931 1230 }
7cec78b6
PB
1231 if ((req->cmd.buf[14] & 1) == 0 && req->cmd.lba) {
1232 goto illegal_request;
1233 }
69377307 1234 nb_sectors /= s->qdev.blocksize / 512;
5dd90e2a
GH
1235 /* Returned value is the address of the last sector. */
1236 nb_sectors--;
1237 /* Remember the new size for read/write sanity checking. */
1238 s->max_lba = nb_sectors;
1239 outbuf[0] = (nb_sectors >> 56) & 0xff;
1240 outbuf[1] = (nb_sectors >> 48) & 0xff;
1241 outbuf[2] = (nb_sectors >> 40) & 0xff;
1242 outbuf[3] = (nb_sectors >> 32) & 0xff;
1243 outbuf[4] = (nb_sectors >> 24) & 0xff;
1244 outbuf[5] = (nb_sectors >> 16) & 0xff;
1245 outbuf[6] = (nb_sectors >> 8) & 0xff;
1246 outbuf[7] = nb_sectors & 0xff;
1247 outbuf[8] = 0;
1248 outbuf[9] = 0;
69377307 1249 outbuf[10] = s->qdev.blocksize >> 8;
5dd90e2a 1250 outbuf[11] = 0;
ee3659e3
CH
1251 outbuf[12] = 0;
1252 outbuf[13] = get_physical_block_exp(&s->qdev.conf);
ea3bd56f
CH
1253
1254 /* set TPE bit if the format supports discard */
1255 if (s->qdev.conf.discard_granularity) {
1256 outbuf[14] = 0x80;
1257 }
1258
5dd90e2a
GH
1259 /* Protection, exponent and lowest lba field left blank. */
1260 buflen = req->cmd.xfer;
1261 break;
1262 }
1263 DPRINTF("Unsupported Service Action In\n");
1264 goto illegal_request;
5e30a07d 1265 case VERIFY_10:
88f8a5ed 1266 break;
aa5dbdc1 1267 default:
b45ef674 1268 scsi_check_condition(r, SENSE_CODE(INVALID_OPCODE));
a1f0cce2 1269 return -1;
aa5dbdc1 1270 }
aa5dbdc1
GH
1271 return buflen;
1272
1273not_ready:
44740c38 1274 if (s->tray_open || !bdrv_is_inserted(s->qdev.conf.bs)) {
b45ef674 1275 scsi_check_condition(r, SENSE_CODE(NO_MEDIUM));
a1f0cce2 1276 } else {
b45ef674 1277 scsi_check_condition(r, SENSE_CODE(LUN_NOT_READY));
a1f0cce2 1278 }
8af7a3ab 1279 return -1;
aa5dbdc1
GH
1280
1281illegal_request:
cfc606da
PB
1282 if (r->req.status == -1) {
1283 scsi_check_condition(r, SENSE_CODE(INVALID_FIELD));
1284 }
8af7a3ab 1285 return -1;
aa5dbdc1
GH
1286}
1287
2e5d83bb
PB
1288/* Execute a scsi command. Returns the length of the data expected by the
1289 command. This will be Positive for data transfers from the device
1290 (eg. disk reads), negative for transfers to the device (eg. disk writes),
1291 and zero if the command does not transfer any data. */
1292
5c6c0e51 1293static int32_t scsi_send_command(SCSIRequest *req, uint8_t *buf)
2e5d83bb 1294{
5c6c0e51
HR
1295 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
1296 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
ad2d30f7 1297 int32_t len;
a917d384 1298 uint8_t command;
aa5dbdc1 1299 int rc;
a917d384
PB
1300
1301 command = buf[0];
653c1c3f 1302 DPRINTF("Command: lun=%d tag=0x%x data=0x%02x", req->lun, req->tag, buf[0]);
2dd791b6 1303
2e5d83bb
PB
1304#ifdef DEBUG_SCSI
1305 {
1306 int i;
2dd791b6 1307 for (i = 1; i < r->req.cmd.len; i++) {
2e5d83bb
PB
1308 printf(" 0x%02x", buf[i]);
1309 }
1310 printf("\n");
1311 }
1312#endif
aa5dbdc1 1313
a917d384 1314 switch (command) {
ebf46023 1315 case TEST_UNIT_READY:
0b06c059 1316 case INQUIRY:
ebddfcbe
GH
1317 case MODE_SENSE:
1318 case MODE_SENSE_10:
3d53ba18
GH
1319 case RESERVE:
1320 case RESERVE_10:
1321 case RELEASE:
1322 case RELEASE_10:
8d3628ff 1323 case START_STOP:
c68b9f34 1324 case ALLOW_MEDIUM_REMOVAL:
5e30a07d 1325 case READ_CAPACITY_10:
02880f43 1326 case READ_TOC:
b6c251ab 1327 case READ_DVD_STRUCTURE:
38215553 1328 case GET_CONFIGURATION:
b6c251ab
PB
1329 case GET_EVENT_STATUS_NOTIFICATION:
1330 case MECHANISM_STATUS:
f6515262 1331 case SERVICE_ACTION_IN_16:
5e30a07d 1332 case VERIFY_10:
7285477a 1333 rc = scsi_disk_emulate_command(r);
8af7a3ab 1334 if (rc < 0) {
0b06c059 1335 return 0;
aa5dbdc1 1336 }
8af7a3ab
KW
1337
1338 r->iov.iov_len = rc;
0b06c059 1339 break;
0a4ac106 1340 case SYNCHRONIZE_CACHE:
44740c38
PB
1341 bdrv_acct_start(s->qdev.conf.bs, &r->acct, 0, BDRV_ACCT_FLUSH);
1342 r->req.aiocb = bdrv_aio_flush(s->qdev.conf.bs, scsi_flush_complete, r);
0a4ac106
PB
1343 if (r->req.aiocb == NULL) {
1344 scsi_flush_complete(r, -EIO);
1345 }
1346 return 0;
ebf46023
GH
1347 case READ_6:
1348 case READ_10:
bd536cf3
GH
1349 case READ_12:
1350 case READ_16:
5c6c0e51 1351 len = r->req.cmd.xfer / s->qdev.blocksize;
2dd791b6 1352 DPRINTF("Read (sector %" PRId64 ", count %d)\n", r->req.cmd.lba, len);
f01b5931 1353 if (r->req.cmd.lba > s->max_lba) {
274fb0e1 1354 goto illegal_lba;
f01b5931 1355 }
69377307
PB
1356 r->sector = r->req.cmd.lba * (s->qdev.blocksize / 512);
1357 r->sector_count = len * (s->qdev.blocksize / 512);
2e5d83bb 1358 break;
ebf46023
GH
1359 case WRITE_6:
1360 case WRITE_10:
bd536cf3
GH
1361 case WRITE_12:
1362 case WRITE_16:
5e30a07d 1363 case WRITE_VERIFY_10:
ebef0bbb
BK
1364 case WRITE_VERIFY_12:
1365 case WRITE_VERIFY_16:
5c6c0e51 1366 len = r->req.cmd.xfer / s->qdev.blocksize;
ebef0bbb 1367 DPRINTF("Write %s(sector %" PRId64 ", count %d)\n",
2dd791b6
HR
1368 (command & 0xe) == 0xe ? "And Verify " : "",
1369 r->req.cmd.lba, len);
f01b5931 1370 if (r->req.cmd.lba > s->max_lba) {
274fb0e1 1371 goto illegal_lba;
f01b5931 1372 }
69377307
PB
1373 r->sector = r->req.cmd.lba * (s->qdev.blocksize / 512);
1374 r->sector_count = len * (s->qdev.blocksize / 512);
2e5d83bb 1375 break;
ebef0bbb 1376 case MODE_SELECT:
2dd791b6 1377 DPRINTF("Mode Select(6) (len %lu)\n", (long)r->req.cmd.xfer);
ebef0bbb
BK
1378 /* We don't support mode parameter changes.
1379 Allow the mode parameter header + block descriptors only. */
2dd791b6 1380 if (r->req.cmd.xfer > 12) {
ebef0bbb
BK
1381 goto fail;
1382 }
1383 break;
1384 case MODE_SELECT_10:
2dd791b6 1385 DPRINTF("Mode Select(10) (len %lu)\n", (long)r->req.cmd.xfer);
ebef0bbb
BK
1386 /* We don't support mode parameter changes.
1387 Allow the mode parameter header + block descriptors only. */
2dd791b6 1388 if (r->req.cmd.xfer > 16) {
ebef0bbb
BK
1389 goto fail;
1390 }
1391 break;
1392 case SEEK_6:
1393 case SEEK_10:
2dd791b6
HR
1394 DPRINTF("Seek(%d) (sector %" PRId64 ")\n", command == SEEK_6 ? 6 : 10,
1395 r->req.cmd.lba);
1396 if (r->req.cmd.lba > s->max_lba) {
ebef0bbb
BK
1397 goto illegal_lba;
1398 }
ea3bd56f
CH
1399 break;
1400 case WRITE_SAME_16:
5c6c0e51 1401 len = r->req.cmd.xfer / s->qdev.blocksize;
ea3bd56f
CH
1402
1403 DPRINTF("WRITE SAME(16) (sector %" PRId64 ", count %d)\n",
1404 r->req.cmd.lba, len);
1405
1406 if (r->req.cmd.lba > s->max_lba) {
1407 goto illegal_lba;
1408 }
1409
1410 /*
1411 * We only support WRITE SAME with the unmap bit set for now.
1412 */
1413 if (!(buf[1] & 0x8)) {
1414 goto fail;
1415 }
1416
69377307
PB
1417 rc = bdrv_discard(s->qdev.conf.bs,
1418 r->req.cmd.lba * (s->qdev.blocksize / 512),
1419 len * (s->qdev.blocksize / 512));
ea3bd56f
CH
1420 if (rc < 0) {
1421 /* XXX: better error code ?*/
1422 goto fail;
1423 }
1424
ebef0bbb 1425 break;
739df215
PB
1426 case REQUEST_SENSE:
1427 abort();
2e5d83bb 1428 default:
2dd791b6 1429 DPRINTF("Unknown SCSI command (%2.2x)\n", buf[0]);
b45ef674 1430 scsi_check_condition(r, SENSE_CODE(INVALID_OPCODE));
a1f0cce2 1431 return 0;
2e5d83bb 1432 fail:
b45ef674 1433 scsi_check_condition(r, SENSE_CODE(INVALID_FIELD));
2dd791b6 1434 return 0;
274fb0e1 1435 illegal_lba:
b45ef674 1436 scsi_check_condition(r, SENSE_CODE(LBA_OUT_OF_RANGE));
274fb0e1 1437 return 0;
2e5d83bb 1438 }
c87c0672 1439 if (r->sector_count == 0 && r->iov.iov_len == 0) {
b45ef674 1440 scsi_req_complete(&r->req, GOOD);
a917d384 1441 }
c87c0672 1442 len = r->sector_count * 512 + r->iov.iov_len;
efb9ee02
HR
1443 if (r->req.cmd.mode == SCSI_XFER_TO_DEV) {
1444 return -len;
a917d384 1445 } else {
f01b5931 1446 if (!r->sector_count) {
a917d384 1447 r->sector_count = -1;
f01b5931 1448 }
efb9ee02 1449 return len;
2e5d83bb 1450 }
2e5d83bb
PB
1451}
1452
e9447f35
JK
1453static void scsi_disk_reset(DeviceState *dev)
1454{
1455 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev.qdev, dev);
1456 uint64_t nb_sectors;
1457
c7b48872 1458 scsi_device_purge_requests(&s->qdev, SENSE_CODE(RESET));
e9447f35 1459
44740c38 1460 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
69377307 1461 nb_sectors /= s->qdev.blocksize / 512;
e9447f35
JK
1462 if (nb_sectors) {
1463 nb_sectors--;
1464 }
1465 s->max_lba = nb_sectors;
1466}
1467
1468static void scsi_destroy(SCSIDevice *dev)
1469{
1470 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, dev);
1471
c7b48872 1472 scsi_device_purge_requests(&s->qdev, SENSE_CODE(NO_SENSE));
f8b6cc00 1473 blockdev_mark_auto_del(s->qdev.conf.bs);
56a14938
GH
1474}
1475
7d4b4ba5 1476static void scsi_cd_change_media_cb(void *opaque, bool load)
2c6942fa 1477{
8a9c16f6
PB
1478 SCSIDiskState *s = opaque;
1479
1480 /*
1481 * When a CD gets changed, we have to report an ejected state and
1482 * then a loaded state to guests so that they detect tray
1483 * open/close and media change events. Guests that do not use
1484 * GET_EVENT_STATUS_NOTIFICATION to detect such tray open/close
1485 * states rely on this behavior.
1486 *
1487 * media_changed governs the state machine used for unit attention
1488 * report. media_event is used by GET EVENT STATUS NOTIFICATION.
1489 */
1490 s->media_changed = load;
1491 s->tray_open = !load;
1492 s->qdev.unit_attention = SENSE_CODE(UNIT_ATTENTION_NO_MEDIUM);
3c2f7c12 1493 s->media_event = true;
2c6942fa
MA
1494}
1495
e4def80b
MA
1496static bool scsi_cd_is_tray_open(void *opaque)
1497{
1498 return ((SCSIDiskState *)opaque)->tray_open;
1499}
1500
f107639a
MA
1501static bool scsi_cd_is_medium_locked(void *opaque)
1502{
1503 return ((SCSIDiskState *)opaque)->tray_locked;
1504}
1505
1506static const BlockDevOps scsi_cd_block_ops = {
2c6942fa 1507 .change_media_cb = scsi_cd_change_media_cb,
e4def80b 1508 .is_tray_open = scsi_cd_is_tray_open,
f107639a
MA
1509 .is_medium_locked = scsi_cd_is_medium_locked,
1510};
1511
8a9c16f6
PB
1512static void scsi_disk_unit_attention_reported(SCSIDevice *dev)
1513{
1514 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, dev);
1515 if (s->media_changed) {
1516 s->media_changed = false;
1517 s->qdev.unit_attention = SENSE_CODE(MEDIUM_CHANGED);
1518 }
1519}
1520
f37bd73b 1521static int scsi_initfn(SCSIDevice *dev, uint8_t scsi_type)
2e5d83bb 1522{
d52affa7 1523 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, dev);
f8b6cc00 1524 DriveInfo *dinfo;
2e5d83bb 1525
f8b6cc00 1526 if (!s->qdev.conf.bs) {
1ecda02b 1527 error_report("scsi-disk: drive property not set");
d52affa7
GH
1528 return -1;
1529 }
1530
44740c38 1531 if (scsi_type == TYPE_DISK && !bdrv_is_inserted(s->qdev.conf.bs)) {
98f28ad7
MA
1532 error_report("Device needs media, but drive is empty");
1533 return -1;
1534 }
1535
a0fef654 1536 if (!s->serial) {
f8b6cc00 1537 /* try to fall back to value set with legacy -drive serial=... */
44740c38 1538 dinfo = drive_get_by_blockdev(s->qdev.conf.bs);
3e1c0c9a 1539 if (*dinfo->serial) {
7267c094 1540 s->serial = g_strdup(dinfo->serial);
3e1c0c9a 1541 }
a0fef654
MA
1542 }
1543
552fee93 1544 if (!s->version) {
7267c094 1545 s->version = g_strdup(QEMU_VERSION);
552fee93
MA
1546 }
1547
44740c38 1548 if (bdrv_is_sg(s->qdev.conf.bs)) {
1ecda02b 1549 error_report("scsi-disk: unwanted /dev/sg*");
32bb404a
MA
1550 return -1;
1551 }
1552
f37bd73b 1553 if (scsi_type == TYPE_ROM) {
44740c38 1554 bdrv_set_dev_ops(s->qdev.conf.bs, &scsi_cd_block_ops, s);
8cfacf07 1555 s->qdev.blocksize = 2048;
f37bd73b 1556 } else if (scsi_type == TYPE_DISK) {
8cfacf07 1557 s->qdev.blocksize = s->qdev.conf.logical_block_size;
f37bd73b
HR
1558 } else {
1559 error_report("scsi-disk: Unhandled SCSI type %02x", scsi_type);
1560 return -1;
2e5d83bb 1561 }
44740c38 1562 bdrv_set_buffer_alignment(s->qdev.conf.bs, s->qdev.blocksize);
8cfacf07 1563
f37bd73b 1564 s->qdev.type = scsi_type;
ea8a5d7f 1565 qemu_add_vm_change_state_handler(scsi_dma_restart_cb, s);
44740c38 1566 bdrv_iostatus_enable(s->qdev.conf.bs);
1ca4d09a 1567 add_boot_device_path(s->qdev.conf.bootindex, &dev->qdev, ",0");
d52affa7
GH
1568 return 0;
1569}
1570
b443ae67
MA
1571static int scsi_hd_initfn(SCSIDevice *dev)
1572{
f37bd73b 1573 return scsi_initfn(dev, TYPE_DISK);
b443ae67
MA
1574}
1575
1576static int scsi_cd_initfn(SCSIDevice *dev)
1577{
f37bd73b 1578 return scsi_initfn(dev, TYPE_ROM);
b443ae67
MA
1579}
1580
1581static int scsi_disk_initfn(SCSIDevice *dev)
1582{
95b5edcd 1583 DriveInfo *dinfo;
f37bd73b 1584 uint8_t scsi_type;
b443ae67
MA
1585
1586 if (!dev->conf.bs) {
f37bd73b 1587 scsi_type = TYPE_DISK; /* will die in scsi_initfn() */
b443ae67 1588 } else {
95b5edcd 1589 dinfo = drive_get_by_blockdev(dev->conf.bs);
f37bd73b 1590 scsi_type = dinfo->media_cd ? TYPE_ROM : TYPE_DISK;
b443ae67
MA
1591 }
1592
f37bd73b 1593 return scsi_initfn(dev, scsi_type);
b443ae67
MA
1594}
1595
8dbd4574
PB
1596static SCSIReqOps scsi_disk_reqops = {
1597 .size = sizeof(SCSIDiskReq),
12010e7b
PB
1598 .free_req = scsi_free_request,
1599 .send_command = scsi_send_command,
1600 .read_data = scsi_read_data,
1601 .write_data = scsi_write_data,
1602 .cancel_io = scsi_cancel_io,
1603 .get_buf = scsi_get_buf,
8dbd4574
PB
1604};
1605
1606static SCSIRequest *scsi_new_request(SCSIDevice *d, uint32_t tag,
1607 uint32_t lun, void *hba_private)
1608{
1609 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, d);
1610 SCSIRequest *req;
8dbd4574
PB
1611
1612 req = scsi_req_alloc(&scsi_disk_reqops, &s->qdev, tag, lun, hba_private);
8dbd4574
PB
1613 return req;
1614}
1615
b443ae67
MA
1616#define DEFINE_SCSI_DISK_PROPERTIES() \
1617 DEFINE_BLOCK_PROPERTIES(SCSIDiskState, qdev.conf), \
1618 DEFINE_PROP_STRING("ver", SCSIDiskState, version), \
1619 DEFINE_PROP_STRING("serial", SCSIDiskState, serial)
1620
1621static SCSIDeviceInfo scsi_disk_info[] = {
1622 {
1623 .qdev.name = "scsi-hd",
1624 .qdev.fw_name = "disk",
1625 .qdev.desc = "virtual SCSI disk",
1626 .qdev.size = sizeof(SCSIDiskState),
1627 .qdev.reset = scsi_disk_reset,
1628 .init = scsi_hd_initfn,
1629 .destroy = scsi_destroy,
5c6c0e51 1630 .alloc_req = scsi_new_request,
8a9c16f6 1631 .unit_attention_reported = scsi_disk_unit_attention_reported,
b443ae67
MA
1632 .qdev.props = (Property[]) {
1633 DEFINE_SCSI_DISK_PROPERTIES(),
1634 DEFINE_PROP_BIT("removable", SCSIDiskState, removable, 0, false),
1635 DEFINE_PROP_END_OF_LIST(),
1636 }
1637 },{
1638 .qdev.name = "scsi-cd",
1639 .qdev.fw_name = "disk",
1640 .qdev.desc = "virtual SCSI CD-ROM",
1641 .qdev.size = sizeof(SCSIDiskState),
1642 .qdev.reset = scsi_disk_reset,
1643 .init = scsi_cd_initfn,
1644 .destroy = scsi_destroy,
5c6c0e51 1645 .alloc_req = scsi_new_request,
8a9c16f6 1646 .unit_attention_reported = scsi_disk_unit_attention_reported,
b443ae67
MA
1647 .qdev.props = (Property[]) {
1648 DEFINE_SCSI_DISK_PROPERTIES(),
1649 DEFINE_PROP_END_OF_LIST(),
1650 },
1651 },{
1652 .qdev.name = "scsi-disk", /* legacy -device scsi-disk */
1653 .qdev.fw_name = "disk",
1654 .qdev.desc = "virtual SCSI disk or CD-ROM (legacy)",
1655 .qdev.size = sizeof(SCSIDiskState),
1656 .qdev.reset = scsi_disk_reset,
1657 .init = scsi_disk_initfn,
1658 .destroy = scsi_destroy,
5c6c0e51 1659 .alloc_req = scsi_new_request,
8a9c16f6 1660 .unit_attention_reported = scsi_disk_unit_attention_reported,
b443ae67
MA
1661 .qdev.props = (Property[]) {
1662 DEFINE_SCSI_DISK_PROPERTIES(),
1663 DEFINE_PROP_BIT("removable", SCSIDiskState, removable, 0, false),
1664 DEFINE_PROP_END_OF_LIST(),
1665 }
1666 }
d52affa7
GH
1667};
1668
1669static void scsi_disk_register_devices(void)
1670{
b443ae67
MA
1671 int i;
1672
1673 for (i = 0; i < ARRAY_SIZE(scsi_disk_info); i++) {
1674 scsi_qdev_register(&scsi_disk_info[i]);
1675 }
8ccc2ace 1676}
d52affa7 1677device_init(scsi_disk_register_devices)