]> git.proxmox.com Git - mirror_qemu.git/blame - hw/scsi-disk.c
scsi-disk: support emulated TO_DEV requests
[mirror_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
87ecb68b 31#include "qemu-common.h"
2f792016 32#include "qemu-error.h"
43b443b6 33#include "scsi.h"
0d65e1f8 34#include "scsi-defs.h"
666daa68 35#include "sysemu.h"
2446333c 36#include "blockdev.h"
9db1c0f7 37#include "hw/block-common.h"
5d0d2467 38#include "dma.h"
22864256 39
336a6915
PB
40#ifdef __linux
41#include <scsi/sg.h>
42#endif
43
f0f72ffe 44#define SCSI_DMA_BUF_SIZE 131072
57575058 45#define SCSI_MAX_INQUIRY_LEN 256
a917d384 46
d52affa7
GH
47typedef struct SCSIDiskState SCSIDiskState;
48
4c41d2ef
GH
49typedef struct SCSIDiskReq {
50 SCSIRequest req;
a917d384 51 /* Both sector and sector_count are in terms of qemu 512 byte blocks. */
e035b43d
AL
52 uint64_t sector;
53 uint32_t sector_count;
7285477a 54 uint32_t buflen;
a0e66a69 55 bool started;
c87c0672
AL
56 struct iovec iov;
57 QEMUIOVector qiov;
a597e79c 58 BlockAcctCookie acct;
4c41d2ef 59} SCSIDiskReq;
a917d384 60
bfe3d7ac 61#define SCSI_DISK_F_REMOVABLE 0
da8365db 62#define SCSI_DISK_F_DPOFUA 1
bfe3d7ac 63
d52affa7 64struct SCSIDiskState
a917d384 65{
d52affa7 66 SCSIDevice qdev;
bfe3d7ac 67 uint32_t features;
8a9c16f6 68 bool media_changed;
3c2f7c12 69 bool media_event;
4480de19 70 bool eject_request;
27395add 71 uint64_t wwn;
213189ab 72 QEMUBH *bh;
383b4d9b 73 char *version;
a0fef654 74 char *serial;
353815aa
DF
75 char *vendor;
76 char *product;
ece0d5e9 77 bool tray_open;
81b1008d 78 bool tray_locked;
2e5d83bb
PB
79};
80
71544d30 81static int scsi_handle_rw_error(SCSIDiskReq *r, int error);
5dba48a8 82
ad2d30f7 83static void scsi_free_request(SCSIRequest *req)
4d611c9a 84{
ad2d30f7
PB
85 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
86
7285477a
PB
87 if (r->iov.iov_base) {
88 qemu_vfree(r->iov.iov_base);
89 }
4d611c9a
PB
90}
91
b45ef674
PB
92/* Helper function for command completion with sense. */
93static void scsi_check_condition(SCSIDiskReq *r, SCSISense sense)
ed3a34a3 94{
02fa69b6
BS
95 DPRINTF("Command complete tag=0x%x sense=%d/%d/%d\n",
96 r->req.tag, sense.key, sense.asc, sense.ascq);
b45ef674
PB
97 scsi_req_build_sense(&r->req, sense);
98 scsi_req_complete(&r->req, CHECK_CONDITION);
4d611c9a
PB
99}
100
101/* Cancel a pending data transfer. */
5c6c0e51 102static void scsi_cancel_io(SCSIRequest *req)
4d611c9a 103{
5c6c0e51
HR
104 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
105
106 DPRINTF("Cancel tag=0x%x\n", req->tag);
107 if (r->req.aiocb) {
108 bdrv_aio_cancel(r->req.aiocb);
c7bae6a7
PB
109
110 /* This reference was left in by scsi_*_data. We take ownership of
111 * it the moment scsi_req_cancel is called, independent of whether
112 * bdrv_aio_cancel completes the request or not. */
113 scsi_req_unref(&r->req);
a917d384 114 }
5c6c0e51 115 r->req.aiocb = NULL;
a917d384
PB
116}
117
43b978b9 118static uint32_t scsi_init_iovec(SCSIDiskReq *r, size_t size)
103b40f5 119{
7285477a
PB
120 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
121
122 if (!r->iov.iov_base) {
43b978b9 123 r->buflen = size;
44740c38 124 r->iov.iov_base = qemu_blockalign(s->qdev.conf.bs, r->buflen);
7285477a
PB
125 }
126 r->iov.iov_len = MIN(r->sector_count * 512, r->buflen);
103b40f5
PB
127 qemu_iovec_init_external(&r->qiov, &r->iov, 1);
128 return r->qiov.size / 512;
129}
130
43b978b9
PB
131static void scsi_disk_save_request(QEMUFile *f, SCSIRequest *req)
132{
133 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
134
135 qemu_put_be64s(f, &r->sector);
136 qemu_put_be32s(f, &r->sector_count);
137 qemu_put_be32s(f, &r->buflen);
18eef3bc
GH
138 if (r->buflen) {
139 if (r->req.cmd.mode == SCSI_XFER_TO_DEV) {
140 qemu_put_buffer(f, r->iov.iov_base, r->iov.iov_len);
141 } else if (!req->retry) {
142 uint32_t len = r->iov.iov_len;
143 qemu_put_be32s(f, &len);
144 qemu_put_buffer(f, r->iov.iov_base, r->iov.iov_len);
145 }
43b978b9
PB
146 }
147}
148
149static void scsi_disk_load_request(QEMUFile *f, SCSIRequest *req)
150{
151 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
152
153 qemu_get_be64s(f, &r->sector);
154 qemu_get_be32s(f, &r->sector_count);
155 qemu_get_be32s(f, &r->buflen);
156 if (r->buflen) {
157 scsi_init_iovec(r, r->buflen);
158 if (r->req.cmd.mode == SCSI_XFER_TO_DEV) {
159 qemu_get_buffer(f, r->iov.iov_base, r->iov.iov_len);
18eef3bc
GH
160 } else if (!r->req.retry) {
161 uint32_t len;
162 qemu_get_be32s(f, &len);
163 r->iov.iov_len = len;
164 assert(r->iov.iov_len <= r->buflen);
165 qemu_get_buffer(f, r->iov.iov_base, r->iov.iov_len);
43b978b9
PB
166 }
167 }
168
169 qemu_iovec_init_external(&r->qiov, &r->iov, 1);
170}
171
c1b35247 172static void scsi_aio_complete(void *opaque, int ret)
5d0d2467
PB
173{
174 SCSIDiskReq *r = (SCSIDiskReq *)opaque;
175 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
176
177 bdrv_acct_done(s->qdev.conf.bs, &r->acct);
178
80624c93 179 if (ret < 0) {
5d0d2467
PB
180 if (scsi_handle_rw_error(r, -ret)) {
181 goto done;
182 }
183 }
184
5d0d2467
PB
185 scsi_req_complete(&r->req, GOOD);
186
187done:
b8aba8d7
PB
188 if (!r->req.io_canceled) {
189 scsi_req_unref(&r->req);
190 }
5d0d2467
PB
191}
192
7e8c49c5
PB
193static bool scsi_is_cmd_fua(SCSICommand *cmd)
194{
195 switch (cmd->buf[0]) {
196 case READ_10:
197 case READ_12:
198 case READ_16:
199 case WRITE_10:
200 case WRITE_12:
201 case WRITE_16:
202 return (cmd->buf[1] & 8) != 0;
203
7f64f8e2
PB
204 case VERIFY_10:
205 case VERIFY_12:
206 case VERIFY_16:
7e8c49c5
PB
207 case WRITE_VERIFY_10:
208 case WRITE_VERIFY_12:
209 case WRITE_VERIFY_16:
210 return true;
211
212 case READ_6:
213 case WRITE_6:
214 default:
215 return false;
216 }
217}
218
219static void scsi_write_do_fua(SCSIDiskReq *r)
220{
221 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
222
223 if (scsi_is_cmd_fua(&r->req.cmd)) {
224 bdrv_acct_start(s->qdev.conf.bs, &r->acct, 0, BDRV_ACCT_FLUSH);
c1b35247 225 r->req.aiocb = bdrv_aio_flush(s->qdev.conf.bs, scsi_aio_complete, r);
7e8c49c5
PB
226 return;
227 }
228
229 scsi_req_complete(&r->req, GOOD);
230 if (!r->req.io_canceled) {
231 scsi_req_unref(&r->req);
232 }
233}
234
b77912a7 235static void scsi_dma_complete(void *opaque, int ret)
a917d384 236{
4c41d2ef 237 SCSIDiskReq *r = (SCSIDiskReq *)opaque;
a597e79c 238 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
a917d384 239
7f64f8e2
PB
240 if (r->req.aiocb != NULL) {
241 r->req.aiocb = NULL;
242 bdrv_acct_done(s->qdev.conf.bs, &r->acct);
243 }
a597e79c 244
80624c93 245 if (ret < 0) {
71544d30 246 if (scsi_handle_rw_error(r, -ret)) {
c7bae6a7 247 goto done;
5dba48a8 248 }
4d611c9a 249 }
5dba48a8 250
b77912a7
PB
251 r->sector += r->sector_count;
252 r->sector_count = 0;
7e8c49c5
PB
253 if (r->req.cmd.mode == SCSI_XFER_TO_DEV) {
254 scsi_write_do_fua(r);
255 return;
256 } else {
257 scsi_req_complete(&r->req, GOOD);
258 }
c7bae6a7
PB
259
260done:
261 if (!r->req.io_canceled) {
262 scsi_req_unref(&r->req);
263 }
4d611c9a
PB
264}
265
b77912a7 266static void scsi_read_complete(void * opaque, int ret)
0a4ac106
PB
267{
268 SCSIDiskReq *r = (SCSIDiskReq *)opaque;
269 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
b77912a7 270 int n;
0a4ac106 271
b77912a7
PB
272 if (r->req.aiocb != NULL) {
273 r->req.aiocb = NULL;
274 bdrv_acct_done(s->qdev.conf.bs, &r->acct);
275 }
0a4ac106
PB
276
277 if (ret < 0) {
71544d30 278 if (scsi_handle_rw_error(r, -ret)) {
c7bae6a7 279 goto done;
0a4ac106
PB
280 }
281 }
282
b77912a7
PB
283 DPRINTF("Data ready tag=0x%x len=%zd\n", r->req.tag, r->qiov.size);
284
285 n = r->qiov.size / 512;
286 r->sector += n;
287 r->sector_count -= n;
288 scsi_req_data(&r->req, r->qiov.size);
c7bae6a7
PB
289
290done:
291 if (!r->req.io_canceled) {
292 scsi_req_unref(&r->req);
293 }
0a4ac106 294}
5dba48a8 295
ac668426
PB
296/* Actually issue a read to the block device. */
297static void scsi_do_read(void *opaque, int ret)
298{
299 SCSIDiskReq *r = opaque;
300 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
301 uint32_t n;
302
303 if (r->req.aiocb != NULL) {
304 r->req.aiocb = NULL;
305 bdrv_acct_done(s->qdev.conf.bs, &r->acct);
306 }
307
308 if (ret < 0) {
309 if (scsi_handle_rw_error(r, -ret)) {
310 goto done;
311 }
312 }
313
31e8fd86
PB
314 if (r->req.io_canceled) {
315 return;
316 }
317
318 /* The request is used as the AIO opaque value, so add a ref. */
319 scsi_req_ref(&r->req);
320
ac668426
PB
321 if (r->req.sg) {
322 dma_acct_start(s->qdev.conf.bs, &r->acct, r->req.sg, BDRV_ACCT_READ);
323 r->req.resid -= r->req.sg->size;
324 r->req.aiocb = dma_bdrv_read(s->qdev.conf.bs, r->req.sg, r->sector,
325 scsi_dma_complete, r);
326 } else {
327 n = scsi_init_iovec(r, SCSI_DMA_BUF_SIZE);
328 bdrv_acct_start(s->qdev.conf.bs, &r->acct, n * BDRV_SECTOR_SIZE, BDRV_ACCT_READ);
329 r->req.aiocb = bdrv_aio_readv(s->qdev.conf.bs, r->sector, &r->qiov, n,
330 scsi_read_complete, r);
331 }
332
333done:
334 if (!r->req.io_canceled) {
335 scsi_req_unref(&r->req);
336 }
337}
338
5c6c0e51
HR
339/* Read more data from scsi device into buffer. */
340static void scsi_read_data(SCSIRequest *req)
2e5d83bb 341{
5c6c0e51 342 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
5dba48a8 343 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
ac668426 344 bool first;
2e5d83bb 345
a917d384
PB
346 DPRINTF("Read sector_count=%d\n", r->sector_count);
347 if (r->sector_count == 0) {
b45ef674
PB
348 /* This also clears the sense buffer for REQUEST SENSE. */
349 scsi_req_complete(&r->req, GOOD);
a917d384 350 return;
2e5d83bb
PB
351 }
352
6fa2c95f
SH
353 /* No data transfer may already be in progress */
354 assert(r->req.aiocb == NULL);
355
c7bae6a7
PB
356 /* The request is used as the AIO opaque value, so add a ref. */
357 scsi_req_ref(&r->req);
efb9ee02
HR
358 if (r->req.cmd.mode == SCSI_XFER_TO_DEV) {
359 DPRINTF("Data transfer direction invalid\n");
360 scsi_read_complete(r, -EINVAL);
361 return;
362 }
363
a1aff5bf
MA
364 if (s->tray_open) {
365 scsi_read_complete(r, -ENOMEDIUM);
c7bae6a7 366 return;
a1aff5bf 367 }
c7bae6a7 368
ac668426 369 first = !r->started;
a0e66a69 370 r->started = true;
ac668426
PB
371 if (first && scsi_is_cmd_fua(&r->req.cmd)) {
372 bdrv_acct_start(s->qdev.conf.bs, &r->acct, 0, BDRV_ACCT_FLUSH);
373 r->req.aiocb = bdrv_aio_flush(s->qdev.conf.bs, scsi_do_read, r);
5d0d2467 374 } else {
ac668426 375 scsi_do_read(r, 0);
5d0d2467 376 }
2e5d83bb
PB
377}
378
c7bae6a7
PB
379/*
380 * scsi_handle_rw_error has two return values. 0 means that the error
381 * must be ignored, 1 means that the error has been processed and the
382 * caller should not do anything else for this request. Note that
383 * scsi_handle_rw_error always manages its reference counts, independent
384 * of the return value.
385 */
71544d30 386static int scsi_handle_rw_error(SCSIDiskReq *r, int error)
5dba48a8 387{
71544d30 388 int is_read = (r->req.cmd.xfer == SCSI_XFER_FROM_DEV);
4c41d2ef 389 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
44740c38 390 BlockErrorAction action = bdrv_get_on_error(s->qdev.conf.bs, is_read);
ea8a5d7f 391
380f640f 392 if (action == BLOCK_ERR_IGNORE) {
329c0a48 393 bdrv_emit_qmp_error_event(s->qdev.conf.bs, BDRV_ACTION_IGNORE, is_read);
ea8a5d7f 394 return 0;
380f640f 395 }
ea8a5d7f
AL
396
397 if ((error == ENOSPC && action == BLOCK_ERR_STOP_ENOSPC)
398 || action == BLOCK_ERR_STOP_ANY) {
5dba48a8 399
329c0a48 400 bdrv_emit_qmp_error_event(s->qdev.conf.bs, BDRV_ACTION_STOP, is_read);
0461d5a6 401 vm_stop(RUN_STATE_IO_ERROR);
44740c38 402 bdrv_iostatus_set_err(s->qdev.conf.bs, error);
71544d30 403 scsi_req_retry(&r->req);
ea8a5d7f 404 } else {
efb9ee02 405 switch (error) {
7e218df5
PB
406 case ENOMEDIUM:
407 scsi_check_condition(r, SENSE_CODE(NO_MEDIUM));
408 break;
efb9ee02 409 case ENOMEM:
b45ef674 410 scsi_check_condition(r, SENSE_CODE(TARGET_FAILURE));
efb9ee02
HR
411 break;
412 case EINVAL:
b45ef674 413 scsi_check_condition(r, SENSE_CODE(INVALID_FIELD));
efb9ee02
HR
414 break;
415 default:
b45ef674 416 scsi_check_condition(r, SENSE_CODE(IO_ERROR));
efb9ee02 417 break;
a1f0cce2 418 }
329c0a48 419 bdrv_emit_qmp_error_event(s->qdev.conf.bs, BDRV_ACTION_REPORT, is_read);
ea8a5d7f 420 }
ea8a5d7f
AL
421 return 1;
422}
423
4d611c9a
PB
424static void scsi_write_complete(void * opaque, int ret)
425{
4c41d2ef 426 SCSIDiskReq *r = (SCSIDiskReq *)opaque;
a597e79c 427 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
ea8a5d7f
AL
428 uint32_t n;
429
8e321cc6
PB
430 if (r->req.aiocb != NULL) {
431 r->req.aiocb = NULL;
44740c38 432 bdrv_acct_done(s->qdev.conf.bs, &r->acct);
8e321cc6 433 }
a597e79c 434
80624c93 435 if (ret < 0) {
71544d30 436 if (scsi_handle_rw_error(r, -ret)) {
c7bae6a7 437 goto done;
5dba48a8 438 }
4d611c9a
PB
439 }
440
103b40f5 441 n = r->qiov.size / 512;
ea8a5d7f
AL
442 r->sector += n;
443 r->sector_count -= n;
a917d384 444 if (r->sector_count == 0) {
7e8c49c5
PB
445 scsi_write_do_fua(r);
446 return;
a917d384 447 } else {
43b978b9 448 scsi_init_iovec(r, SCSI_DMA_BUF_SIZE);
103b40f5
PB
449 DPRINTF("Write complete tag=0x%x more=%d\n", r->req.tag, r->qiov.size);
450 scsi_req_data(&r->req, r->qiov.size);
4d611c9a 451 }
c7bae6a7
PB
452
453done:
454 if (!r->req.io_canceled) {
455 scsi_req_unref(&r->req);
456 }
4d611c9a
PB
457}
458
42741212 459static void scsi_write_data(SCSIRequest *req)
ea8a5d7f 460{
5c6c0e51 461 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
4c41d2ef 462 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
ea8a5d7f
AL
463 uint32_t n;
464
6fa2c95f
SH
465 /* No data transfer may already be in progress */
466 assert(r->req.aiocb == NULL);
467
c7bae6a7
PB
468 /* The request is used as the AIO opaque value, so add a ref. */
469 scsi_req_ref(&r->req);
efb9ee02
HR
470 if (r->req.cmd.mode != SCSI_XFER_TO_DEV) {
471 DPRINTF("Data transfer direction invalid\n");
472 scsi_write_complete(r, -EINVAL);
42741212 473 return;
efb9ee02
HR
474 }
475
5d0d2467
PB
476 if (!r->req.sg && !r->qiov.size) {
477 /* Called for the first time. Ask the driver to send us more data. */
a0e66a69 478 r->started = true;
5d0d2467
PB
479 scsi_write_complete(r, 0);
480 return;
481 }
482 if (s->tray_open) {
483 scsi_write_complete(r, -ENOMEDIUM);
484 return;
485 }
486
7f64f8e2
PB
487 if (r->req.cmd.buf[0] == VERIFY_10 || r->req.cmd.buf[0] == VERIFY_12 ||
488 r->req.cmd.buf[0] == VERIFY_16) {
489 if (r->req.sg) {
490 scsi_dma_complete(r, 0);
491 } else {
492 scsi_write_complete(r, 0);
493 }
494 return;
495 }
496
5d0d2467
PB
497 if (r->req.sg) {
498 dma_acct_start(s->qdev.conf.bs, &r->acct, r->req.sg, BDRV_ACCT_WRITE);
499 r->req.resid -= r->req.sg->size;
500 r->req.aiocb = dma_bdrv_write(s->qdev.conf.bs, r->req.sg, r->sector,
501 scsi_dma_complete, r);
502 } else {
503 n = r->qiov.size / 512;
44740c38
PB
504 bdrv_acct_start(s->qdev.conf.bs, &r->acct, n * BDRV_SECTOR_SIZE, BDRV_ACCT_WRITE);
505 r->req.aiocb = bdrv_aio_writev(s->qdev.conf.bs, r->sector, &r->qiov, n,
103b40f5 506 scsi_write_complete, r);
ea8a5d7f 507 }
a917d384 508}
2e5d83bb 509
a917d384 510/* Return a pointer to the data buffer. */
5c6c0e51 511static uint8_t *scsi_get_buf(SCSIRequest *req)
a917d384 512{
5c6c0e51 513 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
2e5d83bb 514
3f4cb3d3 515 return (uint8_t *)r->iov.iov_base;
2e5d83bb
PB
516}
517
0b06c059
GH
518static int scsi_disk_emulate_inquiry(SCSIRequest *req, uint8_t *outbuf)
519{
383b4d9b 520 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
0b06c059 521 int buflen = 0;
82579390 522 int start;
0b06c059 523
0b06c059
GH
524 if (req->cmd.buf[1] & 0x1) {
525 /* Vital product data */
526 uint8_t page_code = req->cmd.buf[2];
0b06c059 527
e39be482 528 outbuf[buflen++] = s->qdev.type & 0x1f;
0b06c059
GH
529 outbuf[buflen++] = page_code ; // this page
530 outbuf[buflen++] = 0x00;
82579390
PB
531 outbuf[buflen++] = 0x00;
532 start = buflen;
0b06c059
GH
533
534 switch (page_code) {
535 case 0x00: /* Supported page codes, mandatory */
39d98982 536 {
0b06c059
GH
537 DPRINTF("Inquiry EVPD[Supported pages] "
538 "buffer size %zd\n", req->cmd.xfer);
0b06c059 539 outbuf[buflen++] = 0x00; // list of supported pages (this page)
f01b5931 540 if (s->serial) {
3e1c0c9a 541 outbuf[buflen++] = 0x80; // unit serial number
f01b5931 542 }
0b06c059 543 outbuf[buflen++] = 0x83; // device identification
f37bd73b 544 if (s->qdev.type == TYPE_DISK) {
ea3bd56f
CH
545 outbuf[buflen++] = 0xb0; // block limits
546 outbuf[buflen++] = 0xb2; // thin provisioning
39d98982 547 }
0b06c059 548 break;
39d98982 549 }
0b06c059
GH
550 case 0x80: /* Device serial number, optional */
551 {
3e1c0c9a 552 int l;
0b06c059 553
3e1c0c9a
HR
554 if (!s->serial) {
555 DPRINTF("Inquiry (EVPD[Serial number] not supported\n");
556 return -1;
557 }
558
559 l = strlen(s->serial);
f01b5931 560 if (l > 20) {
0b06c059 561 l = 20;
f01b5931 562 }
0b06c059
GH
563
564 DPRINTF("Inquiry EVPD[Serial number] "
565 "buffer size %zd\n", req->cmd.xfer);
a0fef654 566 memcpy(outbuf+buflen, s->serial, l);
0b06c059
GH
567 buflen += l;
568 break;
569 }
570
571 case 0x83: /* Device identification page, mandatory */
572 {
fd930791
PB
573 const char *str = s->serial ?: bdrv_get_device_name(s->qdev.conf.bs);
574 int max_len = s->serial ? 20 : 255 - 8;
575 int id_len = strlen(str);
0b06c059 576
f01b5931 577 if (id_len > max_len) {
0b06c059 578 id_len = max_len;
f01b5931 579 }
0b06c059
GH
580 DPRINTF("Inquiry EVPD[Device identification] "
581 "buffer size %zd\n", req->cmd.xfer);
582
0b06c059
GH
583 outbuf[buflen++] = 0x2; // ASCII
584 outbuf[buflen++] = 0; // not officially assigned
585 outbuf[buflen++] = 0; // reserved
586 outbuf[buflen++] = id_len; // length of data following
fd930791 587 memcpy(outbuf+buflen, str, id_len);
0b06c059 588 buflen += id_len;
27395add
PB
589
590 if (s->wwn) {
591 outbuf[buflen++] = 0x1; // Binary
592 outbuf[buflen++] = 0x3; // NAA
593 outbuf[buflen++] = 0; // reserved
594 outbuf[buflen++] = 8;
595 stq_be_p(&outbuf[buflen], s->wwn);
596 buflen += 8;
597 }
0b06c059
GH
598 break;
599 }
ea3bd56f 600 case 0xb0: /* block limits */
ee3659e3 601 {
ea3bd56f
CH
602 unsigned int unmap_sectors =
603 s->qdev.conf.discard_granularity / s->qdev.blocksize;
8cfacf07
CH
604 unsigned int min_io_size =
605 s->qdev.conf.min_io_size / s->qdev.blocksize;
606 unsigned int opt_io_size =
607 s->qdev.conf.opt_io_size / s->qdev.blocksize;
ee3659e3 608
f37bd73b 609 if (s->qdev.type == TYPE_ROM) {
39d98982
HR
610 DPRINTF("Inquiry (EVPD[%02X] not supported for CDROM\n",
611 page_code);
612 return -1;
613 }
ee3659e3 614 /* required VPD size with unmap support */
82579390 615 buflen = 0x40;
ee3659e3
CH
616 memset(outbuf + 4, 0, buflen - 4);
617
618 /* optimal transfer length granularity */
619 outbuf[6] = (min_io_size >> 8) & 0xff;
620 outbuf[7] = min_io_size & 0xff;
621
622 /* optimal transfer length */
623 outbuf[12] = (opt_io_size >> 24) & 0xff;
624 outbuf[13] = (opt_io_size >> 16) & 0xff;
625 outbuf[14] = (opt_io_size >> 8) & 0xff;
626 outbuf[15] = opt_io_size & 0xff;
ea3bd56f
CH
627
628 /* optimal unmap granularity */
629 outbuf[28] = (unmap_sectors >> 24) & 0xff;
630 outbuf[29] = (unmap_sectors >> 16) & 0xff;
631 outbuf[30] = (unmap_sectors >> 8) & 0xff;
632 outbuf[31] = unmap_sectors & 0xff;
633 break;
634 }
635 case 0xb2: /* thin provisioning */
636 {
82579390 637 buflen = 8;
ea3bd56f 638 outbuf[4] = 0;
c9e4d828 639 outbuf[5] = 0x60; /* write_same 10/16 supported */
f644a290 640 outbuf[6] = s->qdev.conf.discard_granularity ? 2 : 1;
ea3bd56f 641 outbuf[7] = 0;
ee3659e3
CH
642 break;
643 }
0b06c059 644 default:
0b06c059
GH
645 return -1;
646 }
647 /* done with EVPD */
82579390
PB
648 assert(buflen - start <= 255);
649 outbuf[start - 1] = buflen - start;
0b06c059
GH
650 return buflen;
651 }
652
653 /* Standard INQUIRY data */
654 if (req->cmd.buf[2] != 0) {
0b06c059
GH
655 return -1;
656 }
657
658 /* PAGE CODE == 0 */
0b06c059 659 buflen = req->cmd.xfer;
f01b5931 660 if (buflen > SCSI_MAX_INQUIRY_LEN) {
0b06c059 661 buflen = SCSI_MAX_INQUIRY_LEN;
f01b5931 662 }
0b06c059
GH
663 memset(outbuf, 0, buflen);
664
f37bd73b 665 outbuf[0] = s->qdev.type & 0x1f;
bfe3d7ac 666 outbuf[1] = (s->features & (1 << SCSI_DISK_F_REMOVABLE)) ? 0x80 : 0;
353815aa
DF
667
668 strpadcpy((char *) &outbuf[16], 16, s->product, ' ');
669 strpadcpy((char *) &outbuf[8], 8, s->vendor, ' ');
670
314b1811 671 memset(&outbuf[32], 0, 4);
552fee93 672 memcpy(&outbuf[32], s->version, MIN(4, strlen(s->version)));
99aba0c4
CH
673 /*
674 * We claim conformance to SPC-3, which is required for guests
675 * to ask for modern features like READ CAPACITY(16) or the
676 * block characteristics VPD page by default. Not all of SPC-3
677 * is actually implemented, but we're good enough.
678 */
ee3659e3 679 outbuf[2] = 5;
0b06c059 680 outbuf[3] = 2; /* Format 2 */
ad3cea42
AT
681
682 if (buflen > 36) {
683 outbuf[4] = buflen - 5; /* Additional Length = (Len - 1) - 4 */
684 } else {
685 /* If the allocation length of CDB is too small,
686 the additional length is not adjusted */
687 outbuf[4] = 36 - 5;
688 }
689
0b06c059 690 /* Sync data transfer and TCQ. */
afd4030c 691 outbuf[7] = 0x10 | (req->bus->info->tcq ? 0x02 : 0);
0b06c059
GH
692 return buflen;
693}
694
430ee2f2
PB
695static inline bool media_is_dvd(SCSIDiskState *s)
696{
697 uint64_t nb_sectors;
698 if (s->qdev.type != TYPE_ROM) {
699 return false;
700 }
44740c38 701 if (!bdrv_is_inserted(s->qdev.conf.bs)) {
430ee2f2
PB
702 return false;
703 }
44740c38 704 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
430ee2f2
PB
705 return nb_sectors > CD_MAX_SECTORS;
706}
707
ceb792ef
PB
708static inline bool media_is_cd(SCSIDiskState *s)
709{
710 uint64_t nb_sectors;
711 if (s->qdev.type != TYPE_ROM) {
712 return false;
713 }
44740c38 714 if (!bdrv_is_inserted(s->qdev.conf.bs)) {
ceb792ef
PB
715 return false;
716 }
44740c38 717 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
ceb792ef
PB
718 return nb_sectors <= CD_MAX_SECTORS;
719}
720
1a4f0c3a
PB
721static int scsi_read_disc_information(SCSIDiskState *s, SCSIDiskReq *r,
722 uint8_t *outbuf)
723{
724 uint8_t type = r->req.cmd.buf[1] & 7;
725
726 if (s->qdev.type != TYPE_ROM) {
727 return -1;
728 }
729
730 /* Types 1/2 are only defined for Blu-Ray. */
731 if (type != 0) {
732 scsi_check_condition(r, SENSE_CODE(INVALID_FIELD));
733 return -1;
734 }
735
736 memset(outbuf, 0, 34);
737 outbuf[1] = 32;
738 outbuf[2] = 0xe; /* last session complete, disc finalized */
739 outbuf[3] = 1; /* first track on disc */
740 outbuf[4] = 1; /* # of sessions */
741 outbuf[5] = 1; /* first track of last session */
742 outbuf[6] = 1; /* last track of last session */
743 outbuf[7] = 0x20; /* unrestricted use */
744 outbuf[8] = 0x00; /* CD-ROM or DVD-ROM */
745 /* 9-10-11: most significant byte corresponding bytes 4-5-6 */
746 /* 12-23: not meaningful for CD-ROM or DVD-ROM */
747 /* 24-31: disc bar code */
748 /* 32: disc application code */
749 /* 33: number of OPC tables */
750
751 return 34;
752}
753
b6c251ab
PB
754static int scsi_read_dvd_structure(SCSIDiskState *s, SCSIDiskReq *r,
755 uint8_t *outbuf)
756{
ceb792ef
PB
757 static const int rds_caps_size[5] = {
758 [0] = 2048 + 4,
759 [1] = 4 + 4,
760 [3] = 188 + 4,
761 [4] = 2048 + 4,
762 };
763
764 uint8_t media = r->req.cmd.buf[1];
765 uint8_t layer = r->req.cmd.buf[6];
766 uint8_t format = r->req.cmd.buf[7];
767 int size = -1;
768
769 if (s->qdev.type != TYPE_ROM) {
770 return -1;
771 }
772 if (media != 0) {
773 scsi_check_condition(r, SENSE_CODE(INVALID_FIELD));
774 return -1;
775 }
776
777 if (format != 0xff) {
44740c38 778 if (s->tray_open || !bdrv_is_inserted(s->qdev.conf.bs)) {
ceb792ef
PB
779 scsi_check_condition(r, SENSE_CODE(NO_MEDIUM));
780 return -1;
781 }
782 if (media_is_cd(s)) {
783 scsi_check_condition(r, SENSE_CODE(INCOMPATIBLE_FORMAT));
784 return -1;
785 }
786 if (format >= ARRAY_SIZE(rds_caps_size)) {
787 return -1;
788 }
789 size = rds_caps_size[format];
790 memset(outbuf, 0, size);
791 }
792
793 switch (format) {
794 case 0x00: {
795 /* Physical format information */
796 uint64_t nb_sectors;
797 if (layer != 0) {
798 goto fail;
799 }
44740c38 800 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
ceb792ef
PB
801
802 outbuf[4] = 1; /* DVD-ROM, part version 1 */
803 outbuf[5] = 0xf; /* 120mm disc, minimum rate unspecified */
804 outbuf[6] = 1; /* one layer, read-only (per MMC-2 spec) */
805 outbuf[7] = 0; /* default densities */
806
807 stl_be_p(&outbuf[12], (nb_sectors >> 2) - 1); /* end sector */
808 stl_be_p(&outbuf[16], (nb_sectors >> 2) - 1); /* l0 end sector */
809 break;
810 }
811
812 case 0x01: /* DVD copyright information, all zeros */
813 break;
814
815 case 0x03: /* BCA information - invalid field for no BCA info */
816 return -1;
817
818 case 0x04: /* DVD disc manufacturing information, all zeros */
819 break;
820
821 case 0xff: { /* List capabilities */
822 int i;
823 size = 4;
824 for (i = 0; i < ARRAY_SIZE(rds_caps_size); i++) {
825 if (!rds_caps_size[i]) {
826 continue;
827 }
828 outbuf[size] = i;
829 outbuf[size + 1] = 0x40; /* Not writable, readable */
830 stw_be_p(&outbuf[size + 2], rds_caps_size[i]);
831 size += 4;
832 }
833 break;
834 }
835
836 default:
837 return -1;
838 }
839
840 /* Size of buffer, not including 2 byte size field */
841 stw_be_p(outbuf, size - 2);
842 return size;
843
844fail:
b6c251ab
PB
845 return -1;
846}
847
3c2f7c12 848static int scsi_event_status_media(SCSIDiskState *s, uint8_t *outbuf)
b6c251ab 849{
3c2f7c12
PB
850 uint8_t event_code, media_status;
851
852 media_status = 0;
853 if (s->tray_open) {
854 media_status = MS_TRAY_OPEN;
44740c38 855 } else if (bdrv_is_inserted(s->qdev.conf.bs)) {
3c2f7c12
PB
856 media_status = MS_MEDIA_PRESENT;
857 }
858
859 /* Event notification descriptor */
860 event_code = MEC_NO_CHANGE;
4480de19
PB
861 if (media_status != MS_TRAY_OPEN) {
862 if (s->media_event) {
863 event_code = MEC_NEW_MEDIA;
864 s->media_event = false;
865 } else if (s->eject_request) {
866 event_code = MEC_EJECT_REQUESTED;
867 s->eject_request = false;
868 }
3c2f7c12
PB
869 }
870
871 outbuf[0] = event_code;
872 outbuf[1] = media_status;
873
874 /* These fields are reserved, just clear them. */
875 outbuf[2] = 0;
876 outbuf[3] = 0;
877 return 4;
878}
879
880static int scsi_get_event_status_notification(SCSIDiskState *s, SCSIDiskReq *r,
881 uint8_t *outbuf)
882{
883 int size;
884 uint8_t *buf = r->req.cmd.buf;
885 uint8_t notification_class_request = buf[4];
886 if (s->qdev.type != TYPE_ROM) {
887 return -1;
888 }
889 if ((buf[1] & 1) == 0) {
890 /* asynchronous */
891 return -1;
892 }
893
894 size = 4;
895 outbuf[0] = outbuf[1] = 0;
896 outbuf[3] = 1 << GESN_MEDIA; /* supported events */
897 if (notification_class_request & (1 << GESN_MEDIA)) {
898 outbuf[2] = GESN_MEDIA;
899 size += scsi_event_status_media(s, &outbuf[size]);
900 } else {
901 outbuf[2] = 0x80;
902 }
903 stw_be_p(outbuf, size - 4);
904 return size;
b6c251ab
PB
905}
906
430ee2f2 907static int scsi_get_configuration(SCSIDiskState *s, uint8_t *outbuf)
b6c251ab 908{
430ee2f2
PB
909 int current;
910
b6c251ab
PB
911 if (s->qdev.type != TYPE_ROM) {
912 return -1;
913 }
430ee2f2
PB
914 current = media_is_dvd(s) ? MMC_PROFILE_DVD_ROM : MMC_PROFILE_CD_ROM;
915 memset(outbuf, 0, 40);
916 stl_be_p(&outbuf[0], 36); /* Bytes after the data length field */
917 stw_be_p(&outbuf[6], current);
918 /* outbuf[8] - outbuf[19]: Feature 0 - Profile list */
919 outbuf[10] = 0x03; /* persistent, current */
920 outbuf[11] = 8; /* two profiles */
921 stw_be_p(&outbuf[12], MMC_PROFILE_DVD_ROM);
922 outbuf[14] = (current == MMC_PROFILE_DVD_ROM);
923 stw_be_p(&outbuf[16], MMC_PROFILE_CD_ROM);
924 outbuf[18] = (current == MMC_PROFILE_CD_ROM);
925 /* outbuf[20] - outbuf[31]: Feature 1 - Core feature */
926 stw_be_p(&outbuf[20], 1);
927 outbuf[22] = 0x08 | 0x03; /* version 2, persistent, current */
928 outbuf[23] = 8;
929 stl_be_p(&outbuf[24], 1); /* SCSI */
930 outbuf[28] = 1; /* DBE = 1, mandatory */
931 /* outbuf[32] - outbuf[39]: Feature 3 - Removable media feature */
932 stw_be_p(&outbuf[32], 3);
933 outbuf[34] = 0x08 | 0x03; /* version 2, persistent, current */
934 outbuf[35] = 4;
935 outbuf[36] = 0x39; /* tray, load=1, eject=1, unlocked at powerup, lock=1 */
936 /* TODO: Random readable, CD read, DVD read, drive serial number,
937 power management */
938 return 40;
b6c251ab
PB
939}
940
941static int scsi_emulate_mechanism_status(SCSIDiskState *s, uint8_t *outbuf)
942{
943 if (s->qdev.type != TYPE_ROM) {
944 return -1;
945 }
946 memset(outbuf, 0, 8);
947 outbuf[5] = 1; /* CD-ROM */
948 return 8;
949}
950
cfc606da 951static int mode_sense_page(SCSIDiskState *s, int page, uint8_t **p_outbuf,
282ab04e 952 int page_control)
ebddfcbe 953{
a8f4bbe2
PB
954 static const int mode_sense_valid[0x3f] = {
955 [MODE_PAGE_HD_GEOMETRY] = (1 << TYPE_DISK),
956 [MODE_PAGE_FLEXIBLE_DISK_GEOMETRY] = (1 << TYPE_DISK),
957 [MODE_PAGE_CACHING] = (1 << TYPE_DISK) | (1 << TYPE_ROM),
a07c7dcd
PB
958 [MODE_PAGE_R_W_ERROR] = (1 << TYPE_DISK) | (1 << TYPE_ROM),
959 [MODE_PAGE_AUDIO_CTL] = (1 << TYPE_ROM),
a8f4bbe2
PB
960 [MODE_PAGE_CAPABILITIES] = (1 << TYPE_ROM),
961 };
cfc606da 962 uint8_t *p = *p_outbuf;
ebddfcbe 963
a8f4bbe2
PB
964 if ((mode_sense_valid[page] & (1 << s->qdev.type)) == 0) {
965 return -1;
966 }
967
968 p[0] = page;
969
282ab04e
BK
970 /*
971 * If Changeable Values are requested, a mask denoting those mode parameters
972 * that are changeable shall be returned. As we currently don't support
973 * parameter changes via MODE_SELECT all bits are returned set to zero.
974 * The buffer was already menset to zero by the caller of this function.
975 */
ebddfcbe 976 switch (page) {
67cc61e4 977 case MODE_PAGE_HD_GEOMETRY:
ebddfcbe 978 p[1] = 0x16;
282ab04e 979 if (page_control == 1) { /* Changeable Values */
cfc606da 980 break;
282ab04e 981 }
ebddfcbe 982 /* if a geometry hint is available, use it */
d252df48
MA
983 p[2] = (s->qdev.conf.cyls >> 16) & 0xff;
984 p[3] = (s->qdev.conf.cyls >> 8) & 0xff;
985 p[4] = s->qdev.conf.cyls & 0xff;
986 p[5] = s->qdev.conf.heads & 0xff;
ebddfcbe 987 /* Write precomp start cylinder, disabled */
d252df48
MA
988 p[6] = (s->qdev.conf.cyls >> 16) & 0xff;
989 p[7] = (s->qdev.conf.cyls >> 8) & 0xff;
990 p[8] = s->qdev.conf.cyls & 0xff;
ebddfcbe 991 /* Reduced current start cylinder, disabled */
d252df48
MA
992 p[9] = (s->qdev.conf.cyls >> 16) & 0xff;
993 p[10] = (s->qdev.conf.cyls >> 8) & 0xff;
994 p[11] = s->qdev.conf.cyls & 0xff;
ebddfcbe
GH
995 /* Device step rate [ns], 200ns */
996 p[12] = 0;
997 p[13] = 200;
998 /* Landing zone cylinder */
999 p[14] = 0xff;
1000 p[15] = 0xff;
1001 p[16] = 0xff;
1002 /* Medium rotation rate [rpm], 5400 rpm */
1003 p[20] = (5400 >> 8) & 0xff;
1004 p[21] = 5400 & 0xff;
cfc606da 1005 break;
ebddfcbe 1006
67cc61e4 1007 case MODE_PAGE_FLEXIBLE_DISK_GEOMETRY:
ebddfcbe 1008 p[1] = 0x1e;
282ab04e 1009 if (page_control == 1) { /* Changeable Values */
cfc606da 1010 break;
282ab04e 1011 }
ebddfcbe
GH
1012 /* Transfer rate [kbit/s], 5Mbit/s */
1013 p[2] = 5000 >> 8;
1014 p[3] = 5000 & 0xff;
1015 /* if a geometry hint is available, use it */
d252df48
MA
1016 p[4] = s->qdev.conf.heads & 0xff;
1017 p[5] = s->qdev.conf.secs & 0xff;
69377307 1018 p[6] = s->qdev.blocksize >> 8;
d252df48
MA
1019 p[8] = (s->qdev.conf.cyls >> 8) & 0xff;
1020 p[9] = s->qdev.conf.cyls & 0xff;
ebddfcbe 1021 /* Write precomp start cylinder, disabled */
d252df48
MA
1022 p[10] = (s->qdev.conf.cyls >> 8) & 0xff;
1023 p[11] = s->qdev.conf.cyls & 0xff;
ebddfcbe 1024 /* Reduced current start cylinder, disabled */
d252df48
MA
1025 p[12] = (s->qdev.conf.cyls >> 8) & 0xff;
1026 p[13] = s->qdev.conf.cyls & 0xff;
ebddfcbe
GH
1027 /* Device step rate [100us], 100us */
1028 p[14] = 0;
1029 p[15] = 1;
1030 /* Device step pulse width [us], 1us */
1031 p[16] = 1;
1032 /* Device head settle delay [100us], 100us */
1033 p[17] = 0;
1034 p[18] = 1;
1035 /* Motor on delay [0.1s], 0.1s */
1036 p[19] = 1;
1037 /* Motor off delay [0.1s], 0.1s */
1038 p[20] = 1;
1039 /* Medium rotation rate [rpm], 5400 rpm */
1040 p[28] = (5400 >> 8) & 0xff;
1041 p[29] = 5400 & 0xff;
cfc606da 1042 break;
ebddfcbe 1043
67cc61e4 1044 case MODE_PAGE_CACHING:
ebddfcbe
GH
1045 p[0] = 8;
1046 p[1] = 0x12;
282ab04e 1047 if (page_control == 1) { /* Changeable Values */
cfc606da 1048 break;
282ab04e 1049 }
44740c38 1050 if (bdrv_enable_write_cache(s->qdev.conf.bs)) {
ebddfcbe
GH
1051 p[2] = 4; /* WCE */
1052 }
cfc606da 1053 break;
ebddfcbe 1054
a07c7dcd
PB
1055 case MODE_PAGE_R_W_ERROR:
1056 p[1] = 10;
1057 p[2] = 0x80; /* Automatic Write Reallocation Enabled */
1058 if (s->qdev.type == TYPE_ROM) {
1059 p[3] = 0x20; /* Read Retry Count */
1060 }
1061 break;
1062
1063 case MODE_PAGE_AUDIO_CTL:
1064 p[1] = 14;
1065 break;
1066
67cc61e4 1067 case MODE_PAGE_CAPABILITIES:
ebddfcbe 1068 p[1] = 0x14;
282ab04e 1069 if (page_control == 1) { /* Changeable Values */
cfc606da 1070 break;
282ab04e 1071 }
a07c7dcd
PB
1072
1073 p[2] = 0x3b; /* CD-R & CD-RW read */
1074 p[3] = 0; /* Writing not supported */
ebddfcbe
GH
1075 p[4] = 0x7f; /* Audio, composite, digital out,
1076 mode 2 form 1&2, multi session */
1077 p[5] = 0xff; /* CD DA, DA accurate, RW supported,
1078 RW corrected, C2 errors, ISRC,
1079 UPC, Bar code */
81b1008d 1080 p[6] = 0x2d | (s->tray_locked ? 2 : 0);
ebddfcbe
GH
1081 /* Locking supported, jumper present, eject, tray */
1082 p[7] = 0; /* no volume & mute control, no
1083 changer */
a07c7dcd 1084 p[8] = (50 * 176) >> 8; /* 50x read speed */
ebddfcbe 1085 p[9] = (50 * 176) & 0xff;
a07c7dcd
PB
1086 p[10] = 2 >> 8; /* Two volume levels */
1087 p[11] = 2 & 0xff;
1088 p[12] = 2048 >> 8; /* 2M buffer */
ebddfcbe 1089 p[13] = 2048 & 0xff;
a07c7dcd 1090 p[14] = (16 * 176) >> 8; /* 16x read speed current */
ebddfcbe 1091 p[15] = (16 * 176) & 0xff;
a07c7dcd 1092 p[18] = (16 * 176) >> 8; /* 16x write speed */
ebddfcbe 1093 p[19] = (16 * 176) & 0xff;
a07c7dcd 1094 p[20] = (16 * 176) >> 8; /* 16x write speed current */
ebddfcbe 1095 p[21] = (16 * 176) & 0xff;
cfc606da 1096 break;
ebddfcbe
GH
1097
1098 default:
cfc606da 1099 return -1;
ebddfcbe 1100 }
cfc606da
PB
1101
1102 *p_outbuf += p[1] + 2;
1103 return p[1] + 2;
ebddfcbe
GH
1104}
1105
cfc606da 1106static int scsi_disk_emulate_mode_sense(SCSIDiskReq *r, uint8_t *outbuf)
ebddfcbe 1107{
cfc606da 1108 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
ebddfcbe 1109 uint64_t nb_sectors;
e590ecbe
PB
1110 bool dbd;
1111 int page, buflen, ret, page_control;
ebddfcbe 1112 uint8_t *p;
ce512ee1 1113 uint8_t dev_specific_param;
ebddfcbe 1114
e590ecbe 1115 dbd = (r->req.cmd.buf[1] & 0x8) != 0;
cfc606da
PB
1116 page = r->req.cmd.buf[2] & 0x3f;
1117 page_control = (r->req.cmd.buf[2] & 0xc0) >> 6;
aa2b1e89 1118 DPRINTF("Mode Sense(%d) (page %d, xfer %zd, page_control %d)\n",
cfc606da
PB
1119 (r->req.cmd.buf[0] == MODE_SENSE) ? 6 : 10, page, r->req.cmd.xfer, page_control);
1120 memset(outbuf, 0, r->req.cmd.xfer);
ebddfcbe
GH
1121 p = outbuf;
1122
e590ecbe 1123 if (s->qdev.type == TYPE_DISK) {
da8365db 1124 dev_specific_param = s->features & (1 << SCSI_DISK_F_DPOFUA) ? 0x10 : 0;
e590ecbe
PB
1125 if (bdrv_is_read_only(s->qdev.conf.bs)) {
1126 dev_specific_param |= 0x80; /* Readonly. */
1127 }
ce512ee1 1128 } else {
e590ecbe
PB
1129 /* MMC prescribes that CD/DVD drives have no block descriptors,
1130 * and defines no device-specific parameter. */
6a2de0f2 1131 dev_specific_param = 0x00;
e590ecbe 1132 dbd = true;
ce512ee1
BK
1133 }
1134
cfc606da 1135 if (r->req.cmd.buf[0] == MODE_SENSE) {
ce512ee1
BK
1136 p[1] = 0; /* Default media type. */
1137 p[2] = dev_specific_param;
1138 p[3] = 0; /* Block descriptor length. */
1139 p += 4;
1140 } else { /* MODE_SENSE_10 */
1141 p[2] = 0; /* Default media type. */
1142 p[3] = dev_specific_param;
1143 p[6] = p[7] = 0; /* Block descriptor length. */
1144 p += 8;
ebddfcbe 1145 }
ebddfcbe 1146
44740c38 1147 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
e590ecbe 1148 if (!dbd && nb_sectors) {
cfc606da 1149 if (r->req.cmd.buf[0] == MODE_SENSE) {
ce512ee1
BK
1150 outbuf[3] = 8; /* Block descriptor length */
1151 } else { /* MODE_SENSE_10 */
1152 outbuf[7] = 8; /* Block descriptor length */
1153 }
69377307 1154 nb_sectors /= (s->qdev.blocksize / 512);
f01b5931 1155 if (nb_sectors > 0xffffff) {
2488b740 1156 nb_sectors = 0;
f01b5931 1157 }
ebddfcbe
GH
1158 p[0] = 0; /* media density code */
1159 p[1] = (nb_sectors >> 16) & 0xff;
1160 p[2] = (nb_sectors >> 8) & 0xff;
1161 p[3] = nb_sectors & 0xff;
1162 p[4] = 0; /* reserved */
1163 p[5] = 0; /* bytes 5-7 are the sector size in bytes */
69377307 1164 p[6] = s->qdev.blocksize >> 8;
ebddfcbe
GH
1165 p[7] = 0;
1166 p += 8;
1167 }
1168
cfc606da
PB
1169 if (page_control == 3) {
1170 /* Saved Values */
1171 scsi_check_condition(r, SENSE_CODE(SAVING_PARAMS_NOT_SUPPORTED));
1172 return -1;
282ab04e
BK
1173 }
1174
cfc606da
PB
1175 if (page == 0x3f) {
1176 for (page = 0; page <= 0x3e; page++) {
1177 mode_sense_page(s, page, &p, page_control);
1178 }
1179 } else {
1180 ret = mode_sense_page(s, page, &p, page_control);
1181 if (ret == -1) {
1182 return -1;
1183 }
ebddfcbe
GH
1184 }
1185
1186 buflen = p - outbuf;
ce512ee1
BK
1187 /*
1188 * The mode data length field specifies the length in bytes of the
1189 * following data that is available to be transferred. The mode data
1190 * length does not include itself.
1191 */
cfc606da 1192 if (r->req.cmd.buf[0] == MODE_SENSE) {
ce512ee1
BK
1193 outbuf[0] = buflen - 1;
1194 } else { /* MODE_SENSE_10 */
1195 outbuf[0] = ((buflen - 2) >> 8) & 0xff;
1196 outbuf[1] = (buflen - 2) & 0xff;
1197 }
ebddfcbe
GH
1198 return buflen;
1199}
1200
02880f43
GH
1201static int scsi_disk_emulate_read_toc(SCSIRequest *req, uint8_t *outbuf)
1202{
1203 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
02880f43
GH
1204 int start_track, format, msf, toclen;
1205 uint64_t nb_sectors;
1206
1207 msf = req->cmd.buf[1] & 2;
1208 format = req->cmd.buf[2] & 0xf;
1209 start_track = req->cmd.buf[6];
44740c38 1210 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
02880f43 1211 DPRINTF("Read TOC (track %d format %d msf %d)\n", start_track, format, msf >> 1);
69377307 1212 nb_sectors /= s->qdev.blocksize / 512;
02880f43
GH
1213 switch (format) {
1214 case 0:
1215 toclen = cdrom_read_toc(nb_sectors, outbuf, msf, start_track);
1216 break;
1217 case 1:
1218 /* multi session : only a single session defined */
1219 toclen = 12;
1220 memset(outbuf, 0, 12);
1221 outbuf[1] = 0x0a;
1222 outbuf[2] = 0x01;
1223 outbuf[3] = 0x01;
1224 break;
1225 case 2:
1226 toclen = cdrom_read_toc_raw(nb_sectors, outbuf, msf, start_track);
1227 break;
1228 default:
1229 return -1;
1230 }
02880f43
GH
1231 return toclen;
1232}
1233
68bb01f3 1234static int scsi_disk_emulate_start_stop(SCSIDiskReq *r)
bfd52647
MA
1235{
1236 SCSIRequest *req = &r->req;
1237 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
1238 bool start = req->cmd.buf[4] & 1;
1239 bool loej = req->cmd.buf[4] & 2; /* load on start, eject on !start */
1240
1241 if (s->qdev.type == TYPE_ROM && loej) {
68bb01f3
MA
1242 if (!start && !s->tray_open && s->tray_locked) {
1243 scsi_check_condition(r,
44740c38 1244 bdrv_is_inserted(s->qdev.conf.bs)
68bb01f3
MA
1245 ? SENSE_CODE(ILLEGAL_REQ_REMOVAL_PREVENTED)
1246 : SENSE_CODE(NOT_READY_REMOVAL_PREVENTED));
1247 return -1;
fdec4404 1248 }
d88b1819
LC
1249
1250 if (s->tray_open != !start) {
1251 bdrv_eject(s->qdev.conf.bs, !start);
1252 s->tray_open = !start;
1253 }
bfd52647 1254 }
68bb01f3 1255 return 0;
bfd52647
MA
1256}
1257
314a3299
PB
1258static void scsi_disk_emulate_read_data(SCSIRequest *req)
1259{
1260 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
1261 int buflen = r->iov.iov_len;
1262
1263 if (buflen) {
1264 DPRINTF("Read buf_len=%zd\n", buflen);
1265 r->iov.iov_len = 0;
1266 r->started = true;
1267 scsi_req_data(&r->req, buflen);
1268 return;
1269 }
1270
1271 /* This also clears the sense buffer for REQUEST SENSE. */
1272 scsi_req_complete(&r->req, GOOD);
1273}
1274
1275static void scsi_disk_emulate_write_data(SCSIRequest *req)
1276{
af6d510d
PB
1277 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
1278
1279 if (r->iov.iov_len) {
1280 int buflen = r->iov.iov_len;
1281 DPRINTF("Write buf_len=%zd\n", buflen);
1282 r->iov.iov_len = 0;
1283 scsi_req_data(&r->req, buflen);
1284 return;
1285 }
1286
1287 switch (req->cmd.buf[0]) {
1288 case MODE_SELECT:
1289 case MODE_SELECT_10:
1290 /* This also clears the sense buffer for REQUEST SENSE. */
1291 scsi_req_complete(&r->req, GOOD);
1292 break;
1293
1294 default:
1295 abort();
1296 }
314a3299
PB
1297}
1298
b08d0ea0 1299static int32_t scsi_disk_emulate_command(SCSIRequest *req, uint8_t *buf)
aa5dbdc1 1300{
b08d0ea0 1301 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
e7e25e32 1302 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
e7e25e32 1303 uint64_t nb_sectors;
7285477a 1304 uint8_t *outbuf;
af6d510d 1305 int buflen;
aa5dbdc1 1306
b08d0ea0
PB
1307 switch (req->cmd.buf[0]) {
1308 case INQUIRY:
1309 case MODE_SENSE:
1310 case MODE_SENSE_10:
1311 case RESERVE:
1312 case RESERVE_10:
1313 case RELEASE:
1314 case RELEASE_10:
1315 case START_STOP:
1316 case ALLOW_MEDIUM_REMOVAL:
1317 case GET_CONFIGURATION:
1318 case GET_EVENT_STATUS_NOTIFICATION:
1319 case MECHANISM_STATUS:
1320 case REQUEST_SENSE:
1321 break;
1322
1323 default:
1324 if (s->tray_open || !bdrv_is_inserted(s->qdev.conf.bs)) {
1325 scsi_check_condition(r, SENSE_CODE(NO_MEDIUM));
1326 return 0;
1327 }
1328 break;
1329 }
1330
7285477a
PB
1331 if (!r->iov.iov_base) {
1332 /*
1333 * FIXME: we shouldn't return anything bigger than 4k, but the code
1334 * requires the buffer to be as big as req->cmd.xfer in several
1335 * places. So, do not allow CDBs with a very large ALLOCATION
1336 * LENGTH. The real fix would be to modify scsi_read_data and
1337 * dma_buf_read, so that they return data beyond the buflen
1338 * as all zeros.
1339 */
1340 if (req->cmd.xfer > 65536) {
1341 goto illegal_request;
1342 }
1343 r->buflen = MAX(4096, req->cmd.xfer);
44740c38 1344 r->iov.iov_base = qemu_blockalign(s->qdev.conf.bs, r->buflen);
7285477a
PB
1345 }
1346
af6d510d 1347 buflen = req->cmd.xfer;
7285477a 1348 outbuf = r->iov.iov_base;
aa5dbdc1
GH
1349 switch (req->cmd.buf[0]) {
1350 case TEST_UNIT_READY:
9bcaf4fe 1351 assert(!s->tray_open && bdrv_is_inserted(s->qdev.conf.bs));
5f71d32f 1352 break;
0b06c059
GH
1353 case INQUIRY:
1354 buflen = scsi_disk_emulate_inquiry(req, outbuf);
f01b5931 1355 if (buflen < 0) {
0b06c059 1356 goto illegal_request;
f01b5931 1357 }
5f71d32f 1358 break;
ebddfcbe
GH
1359 case MODE_SENSE:
1360 case MODE_SENSE_10:
cfc606da 1361 buflen = scsi_disk_emulate_mode_sense(r, outbuf);
f01b5931 1362 if (buflen < 0) {
ebddfcbe 1363 goto illegal_request;
f01b5931 1364 }
ebddfcbe 1365 break;
02880f43
GH
1366 case READ_TOC:
1367 buflen = scsi_disk_emulate_read_toc(req, outbuf);
f01b5931 1368 if (buflen < 0) {
02880f43 1369 goto illegal_request;
f01b5931 1370 }
02880f43 1371 break;
3d53ba18 1372 case RESERVE:
f01b5931 1373 if (req->cmd.buf[1] & 1) {
3d53ba18 1374 goto illegal_request;
f01b5931 1375 }
3d53ba18
GH
1376 break;
1377 case RESERVE_10:
f01b5931 1378 if (req->cmd.buf[1] & 3) {
3d53ba18 1379 goto illegal_request;
f01b5931 1380 }
3d53ba18
GH
1381 break;
1382 case RELEASE:
f01b5931 1383 if (req->cmd.buf[1] & 1) {
3d53ba18 1384 goto illegal_request;
f01b5931 1385 }
3d53ba18
GH
1386 break;
1387 case RELEASE_10:
f01b5931 1388 if (req->cmd.buf[1] & 3) {
3d53ba18 1389 goto illegal_request;
f01b5931 1390 }
3d53ba18 1391 break;
8d3628ff 1392 case START_STOP:
68bb01f3 1393 if (scsi_disk_emulate_start_stop(r) < 0) {
b08d0ea0 1394 return 0;
68bb01f3 1395 }
5f71d32f 1396 break;
c68b9f34 1397 case ALLOW_MEDIUM_REMOVAL:
81b1008d 1398 s->tray_locked = req->cmd.buf[4] & 1;
44740c38 1399 bdrv_lock_medium(s->qdev.conf.bs, req->cmd.buf[4] & 1);
5f71d32f 1400 break;
5e30a07d 1401 case READ_CAPACITY_10:
e7e25e32 1402 /* The normal LEN field for this command is zero. */
5f71d32f 1403 memset(outbuf, 0, 8);
44740c38 1404 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
f01b5931 1405 if (!nb_sectors) {
9bcaf4fe
PB
1406 scsi_check_condition(r, SENSE_CODE(LUN_NOT_READY));
1407 return -1;
f01b5931 1408 }
7cec78b6
PB
1409 if ((req->cmd.buf[8] & 1) == 0 && req->cmd.lba) {
1410 goto illegal_request;
1411 }
69377307 1412 nb_sectors /= s->qdev.blocksize / 512;
e7e25e32
GH
1413 /* Returned value is the address of the last sector. */
1414 nb_sectors--;
1415 /* Remember the new size for read/write sanity checking. */
7877903a 1416 s->qdev.max_lba = nb_sectors;
e7e25e32 1417 /* Clip to 2TB, instead of returning capacity modulo 2TB. */
f01b5931 1418 if (nb_sectors > UINT32_MAX) {
e7e25e32 1419 nb_sectors = UINT32_MAX;
f01b5931 1420 }
e7e25e32
GH
1421 outbuf[0] = (nb_sectors >> 24) & 0xff;
1422 outbuf[1] = (nb_sectors >> 16) & 0xff;
1423 outbuf[2] = (nb_sectors >> 8) & 0xff;
1424 outbuf[3] = nb_sectors & 0xff;
1425 outbuf[4] = 0;
1426 outbuf[5] = 0;
69377307 1427 outbuf[6] = s->qdev.blocksize >> 8;
e7e25e32
GH
1428 outbuf[7] = 0;
1429 buflen = 8;
5f71d32f 1430 break;
f3b338ef
PB
1431 case REQUEST_SENSE:
1432 /* Just return "NO SENSE". */
1433 buflen = scsi_build_sense(NULL, 0, outbuf, r->buflen,
1434 (req->cmd.buf[1] & 1) == 0);
1435 break;
b6c251ab
PB
1436 case MECHANISM_STATUS:
1437 buflen = scsi_emulate_mechanism_status(s, outbuf);
1438 if (buflen < 0) {
1439 goto illegal_request;
1440 }
1441 break;
38215553 1442 case GET_CONFIGURATION:
430ee2f2 1443 buflen = scsi_get_configuration(s, outbuf);
b6c251ab
PB
1444 if (buflen < 0) {
1445 goto illegal_request;
1446 }
1447 break;
1448 case GET_EVENT_STATUS_NOTIFICATION:
1449 buflen = scsi_get_event_status_notification(s, r, outbuf);
1450 if (buflen < 0) {
1451 goto illegal_request;
1452 }
1453 break;
1a4f0c3a
PB
1454 case READ_DISC_INFORMATION:
1455 buflen = scsi_read_disc_information(s, r, outbuf);
1456 if (buflen < 0) {
1457 goto illegal_request;
1458 }
1459 break;
b6c251ab
PB
1460 case READ_DVD_STRUCTURE:
1461 buflen = scsi_read_dvd_structure(s, r, outbuf);
1462 if (buflen < 0) {
1463 goto illegal_request;
1464 }
38215553 1465 break;
f6515262 1466 case SERVICE_ACTION_IN_16:
5dd90e2a 1467 /* Service Action In subcommands. */
f6515262 1468 if ((req->cmd.buf[1] & 31) == SAI_READ_CAPACITY_16) {
5dd90e2a
GH
1469 DPRINTF("SAI READ CAPACITY(16)\n");
1470 memset(outbuf, 0, req->cmd.xfer);
44740c38 1471 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
f01b5931 1472 if (!nb_sectors) {
9bcaf4fe
PB
1473 scsi_check_condition(r, SENSE_CODE(LUN_NOT_READY));
1474 return -1;
f01b5931 1475 }
7cec78b6
PB
1476 if ((req->cmd.buf[14] & 1) == 0 && req->cmd.lba) {
1477 goto illegal_request;
1478 }
69377307 1479 nb_sectors /= s->qdev.blocksize / 512;
5dd90e2a
GH
1480 /* Returned value is the address of the last sector. */
1481 nb_sectors--;
1482 /* Remember the new size for read/write sanity checking. */
7877903a 1483 s->qdev.max_lba = nb_sectors;
5dd90e2a
GH
1484 outbuf[0] = (nb_sectors >> 56) & 0xff;
1485 outbuf[1] = (nb_sectors >> 48) & 0xff;
1486 outbuf[2] = (nb_sectors >> 40) & 0xff;
1487 outbuf[3] = (nb_sectors >> 32) & 0xff;
1488 outbuf[4] = (nb_sectors >> 24) & 0xff;
1489 outbuf[5] = (nb_sectors >> 16) & 0xff;
1490 outbuf[6] = (nb_sectors >> 8) & 0xff;
1491 outbuf[7] = nb_sectors & 0xff;
1492 outbuf[8] = 0;
1493 outbuf[9] = 0;
69377307 1494 outbuf[10] = s->qdev.blocksize >> 8;
5dd90e2a 1495 outbuf[11] = 0;
ee3659e3
CH
1496 outbuf[12] = 0;
1497 outbuf[13] = get_physical_block_exp(&s->qdev.conf);
ea3bd56f
CH
1498
1499 /* set TPE bit if the format supports discard */
1500 if (s->qdev.conf.discard_granularity) {
1501 outbuf[14] = 0x80;
1502 }
1503
5dd90e2a
GH
1504 /* Protection, exponent and lowest lba field left blank. */
1505 buflen = req->cmd.xfer;
1506 break;
1507 }
1508 DPRINTF("Unsupported Service Action In\n");
1509 goto illegal_request;
101aa85f
PB
1510 case SYNCHRONIZE_CACHE:
1511 /* The request is used as the AIO opaque value, so add a ref. */
1512 scsi_req_ref(&r->req);
1513 bdrv_acct_start(s->qdev.conf.bs, &r->acct, 0, BDRV_ACCT_FLUSH);
1514 r->req.aiocb = bdrv_aio_flush(s->qdev.conf.bs, scsi_aio_complete, r);
1515 return 0;
1516 case SEEK_10:
1517 DPRINTF("Seek(10) (sector %" PRId64 ")\n", r->req.cmd.lba);
1518 if (r->req.cmd.lba > s->qdev.max_lba) {
1519 goto illegal_lba;
1520 }
1521 break;
101aa85f
PB
1522 case MODE_SELECT:
1523 DPRINTF("Mode Select(6) (len %lu)\n", (long)r->req.cmd.xfer);
1524 /* We don't support mode parameter changes.
1525 Allow the mode parameter header + block descriptors only. */
1526 if (r->req.cmd.xfer > 12) {
1527 goto illegal_request;
1528 }
1529 break;
1530 case MODE_SELECT_10:
1531 DPRINTF("Mode Select(10) (len %lu)\n", (long)r->req.cmd.xfer);
1532 /* We don't support mode parameter changes.
1533 Allow the mode parameter header + block descriptors only. */
1534 if (r->req.cmd.xfer > 16) {
1535 goto illegal_request;
1536 }
1537 break;
101aa85f
PB
1538 case WRITE_SAME_10:
1539 nb_sectors = lduw_be_p(&req->cmd.buf[7]);
1540 goto write_same;
1541 case WRITE_SAME_16:
1542 nb_sectors = ldl_be_p(&req->cmd.buf[10]) & 0xffffffffULL;
1543 write_same:
1544 if (r->req.cmd.lba > s->qdev.max_lba) {
1545 goto illegal_lba;
1546 }
1547
1548 /*
1549 * We only support WRITE SAME with the unmap bit set for now.
1550 */
1551 if (!(req->cmd.buf[1] & 0x8)) {
1552 goto illegal_request;
1553 }
1554
1555 /* The request is used as the AIO opaque value, so add a ref. */
1556 scsi_req_ref(&r->req);
1557 r->req.aiocb = bdrv_aio_discard(s->qdev.conf.bs,
1558 r->req.cmd.lba * (s->qdev.blocksize / 512),
1559 nb_sectors * (s->qdev.blocksize / 512),
1560 scsi_aio_complete, r);
1561 return 0;
aa5dbdc1 1562 default:
b08d0ea0 1563 DPRINTF("Unknown SCSI command (%2.2x)\n", buf[0]);
b45ef674 1564 scsi_check_condition(r, SENSE_CODE(INVALID_OPCODE));
b08d0ea0 1565 return 0;
aa5dbdc1 1566 }
314a3299 1567 assert(!r->req.aiocb);
b08d0ea0 1568 r->iov.iov_len = MIN(buflen, req->cmd.xfer);
b08d0ea0
PB
1569 if (r->iov.iov_len == 0) {
1570 scsi_req_complete(&r->req, GOOD);
1571 }
af6d510d
PB
1572 if (r->req.cmd.mode == SCSI_XFER_TO_DEV) {
1573 assert(r->iov.iov_len == req->cmd.xfer);
1574 return -r->iov.iov_len;
1575 } else {
1576 return r->iov.iov_len;
1577 }
aa5dbdc1 1578
aa5dbdc1 1579illegal_request:
cfc606da
PB
1580 if (r->req.status == -1) {
1581 scsi_check_condition(r, SENSE_CODE(INVALID_FIELD));
1582 }
b08d0ea0 1583 return 0;
101aa85f
PB
1584
1585illegal_lba:
1586 scsi_check_condition(r, SENSE_CODE(LBA_OUT_OF_RANGE));
1587 return 0;
aa5dbdc1
GH
1588}
1589
2e5d83bb
PB
1590/* Execute a scsi command. Returns the length of the data expected by the
1591 command. This will be Positive for data transfers from the device
1592 (eg. disk reads), negative for transfers to the device (eg. disk writes),
1593 and zero if the command does not transfer any data. */
1594
b08d0ea0 1595static int32_t scsi_disk_dma_command(SCSIRequest *req, uint8_t *buf)
2e5d83bb 1596{
5c6c0e51
HR
1597 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
1598 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
ad2d30f7 1599 int32_t len;
a917d384 1600 uint8_t command;
a917d384
PB
1601
1602 command = buf[0];
aa5dbdc1 1603
b08d0ea0
PB
1604 if (s->tray_open || !bdrv_is_inserted(s->qdev.conf.bs)) {
1605 scsi_check_condition(r, SENSE_CODE(NO_MEDIUM));
1606 return 0;
9bcaf4fe
PB
1607 }
1608
a917d384 1609 switch (command) {
ebf46023
GH
1610 case READ_6:
1611 case READ_10:
bd536cf3
GH
1612 case READ_12:
1613 case READ_16:
5c6c0e51 1614 len = r->req.cmd.xfer / s->qdev.blocksize;
2dd791b6 1615 DPRINTF("Read (sector %" PRId64 ", count %d)\n", r->req.cmd.lba, len);
7877903a 1616 if (r->req.cmd.lba > s->qdev.max_lba) {
274fb0e1 1617 goto illegal_lba;
f01b5931 1618 }
69377307
PB
1619 r->sector = r->req.cmd.lba * (s->qdev.blocksize / 512);
1620 r->sector_count = len * (s->qdev.blocksize / 512);
2e5d83bb 1621 break;
7f64f8e2
PB
1622 case VERIFY_10:
1623 case VERIFY_12:
1624 case VERIFY_16:
ebf46023
GH
1625 case WRITE_6:
1626 case WRITE_10:
bd536cf3
GH
1627 case WRITE_12:
1628 case WRITE_16:
5e30a07d 1629 case WRITE_VERIFY_10:
ebef0bbb
BK
1630 case WRITE_VERIFY_12:
1631 case WRITE_VERIFY_16:
5c6c0e51 1632 len = r->req.cmd.xfer / s->qdev.blocksize;
ebef0bbb 1633 DPRINTF("Write %s(sector %" PRId64 ", count %d)\n",
2dd791b6
HR
1634 (command & 0xe) == 0xe ? "And Verify " : "",
1635 r->req.cmd.lba, len);
7877903a 1636 if (r->req.cmd.lba > s->qdev.max_lba) {
274fb0e1 1637 goto illegal_lba;
f01b5931 1638 }
69377307
PB
1639 r->sector = r->req.cmd.lba * (s->qdev.blocksize / 512);
1640 r->sector_count = len * (s->qdev.blocksize / 512);
2e5d83bb 1641 break;
101aa85f 1642 default:
b08d0ea0 1643 abort();
274fb0e1 1644 illegal_lba:
b45ef674 1645 scsi_check_condition(r, SENSE_CODE(LBA_OUT_OF_RANGE));
274fb0e1 1646 return 0;
2e5d83bb 1647 }
b08d0ea0 1648 if (r->sector_count == 0) {
b45ef674 1649 scsi_req_complete(&r->req, GOOD);
a917d384 1650 }
b08d0ea0 1651 assert(r->iov.iov_len == 0);
efb9ee02 1652 if (r->req.cmd.mode == SCSI_XFER_TO_DEV) {
b08d0ea0 1653 return -r->sector_count * 512;
a917d384 1654 } else {
b08d0ea0 1655 return r->sector_count * 512;
2e5d83bb 1656 }
2e5d83bb
PB
1657}
1658
e9447f35
JK
1659static void scsi_disk_reset(DeviceState *dev)
1660{
1661 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev.qdev, dev);
1662 uint64_t nb_sectors;
1663
c7b48872 1664 scsi_device_purge_requests(&s->qdev, SENSE_CODE(RESET));
e9447f35 1665
44740c38 1666 bdrv_get_geometry(s->qdev.conf.bs, &nb_sectors);
69377307 1667 nb_sectors /= s->qdev.blocksize / 512;
e9447f35
JK
1668 if (nb_sectors) {
1669 nb_sectors--;
1670 }
7877903a 1671 s->qdev.max_lba = nb_sectors;
e9447f35
JK
1672}
1673
1674static void scsi_destroy(SCSIDevice *dev)
1675{
1676 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, dev);
1677
c7b48872 1678 scsi_device_purge_requests(&s->qdev, SENSE_CODE(NO_SENSE));
f8b6cc00 1679 blockdev_mark_auto_del(s->qdev.conf.bs);
56a14938
GH
1680}
1681
7d4b4ba5 1682static void scsi_cd_change_media_cb(void *opaque, bool load)
2c6942fa 1683{
8a9c16f6
PB
1684 SCSIDiskState *s = opaque;
1685
1686 /*
1687 * When a CD gets changed, we have to report an ejected state and
1688 * then a loaded state to guests so that they detect tray
1689 * open/close and media change events. Guests that do not use
1690 * GET_EVENT_STATUS_NOTIFICATION to detect such tray open/close
1691 * states rely on this behavior.
1692 *
1693 * media_changed governs the state machine used for unit attention
1694 * report. media_event is used by GET EVENT STATUS NOTIFICATION.
1695 */
1696 s->media_changed = load;
1697 s->tray_open = !load;
1698 s->qdev.unit_attention = SENSE_CODE(UNIT_ATTENTION_NO_MEDIUM);
3c2f7c12 1699 s->media_event = true;
4480de19
PB
1700 s->eject_request = false;
1701}
1702
1703static void scsi_cd_eject_request_cb(void *opaque, bool force)
1704{
1705 SCSIDiskState *s = opaque;
1706
1707 s->eject_request = true;
1708 if (force) {
1709 s->tray_locked = false;
1710 }
2c6942fa
MA
1711}
1712
e4def80b
MA
1713static bool scsi_cd_is_tray_open(void *opaque)
1714{
1715 return ((SCSIDiskState *)opaque)->tray_open;
1716}
1717
f107639a
MA
1718static bool scsi_cd_is_medium_locked(void *opaque)
1719{
1720 return ((SCSIDiskState *)opaque)->tray_locked;
1721}
1722
1723static const BlockDevOps scsi_cd_block_ops = {
2c6942fa 1724 .change_media_cb = scsi_cd_change_media_cb,
4480de19 1725 .eject_request_cb = scsi_cd_eject_request_cb,
e4def80b 1726 .is_tray_open = scsi_cd_is_tray_open,
f107639a
MA
1727 .is_medium_locked = scsi_cd_is_medium_locked,
1728};
1729
8a9c16f6
PB
1730static void scsi_disk_unit_attention_reported(SCSIDevice *dev)
1731{
1732 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, dev);
1733 if (s->media_changed) {
1734 s->media_changed = false;
1735 s->qdev.unit_attention = SENSE_CODE(MEDIUM_CHANGED);
1736 }
1737}
1738
e39be482 1739static int scsi_initfn(SCSIDevice *dev)
2e5d83bb 1740{
d52affa7 1741 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, dev);
2e5d83bb 1742
f8b6cc00 1743 if (!s->qdev.conf.bs) {
6a84cb1f 1744 error_report("drive property not set");
d52affa7
GH
1745 return -1;
1746 }
1747
bfe3d7ac
PB
1748 if (!(s->features & (1 << SCSI_DISK_F_REMOVABLE)) &&
1749 !bdrv_is_inserted(s->qdev.conf.bs)) {
98f28ad7
MA
1750 error_report("Device needs media, but drive is empty");
1751 return -1;
1752 }
1753
911525db 1754 blkconf_serial(&s->qdev.conf, &s->serial);
b7eb0c9f
MA
1755 if (blkconf_geometry(&dev->conf, NULL, 65535, 255, 255) < 0) {
1756 return -1;
1757 }
a0fef654 1758
552fee93 1759 if (!s->version) {
93bfef4c 1760 s->version = g_strdup(qemu_get_version());
552fee93 1761 }
353815aa
DF
1762 if (!s->vendor) {
1763 s->vendor = g_strdup("QEMU");
1764 }
552fee93 1765
44740c38 1766 if (bdrv_is_sg(s->qdev.conf.bs)) {
6a84cb1f 1767 error_report("unwanted /dev/sg*");
32bb404a
MA
1768 return -1;
1769 }
1770
bfe3d7ac 1771 if (s->features & (1 << SCSI_DISK_F_REMOVABLE)) {
44740c38 1772 bdrv_set_dev_ops(s->qdev.conf.bs, &scsi_cd_block_ops, s);
2e5d83bb 1773 }
44740c38 1774 bdrv_set_buffer_alignment(s->qdev.conf.bs, s->qdev.blocksize);
8cfacf07 1775
44740c38 1776 bdrv_iostatus_enable(s->qdev.conf.bs);
7082826e 1777 add_boot_device_path(s->qdev.conf.bootindex, &dev->qdev, NULL);
d52affa7
GH
1778 return 0;
1779}
1780
b443ae67
MA
1781static int scsi_hd_initfn(SCSIDevice *dev)
1782{
e39be482
PB
1783 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, dev);
1784 s->qdev.blocksize = s->qdev.conf.logical_block_size;
1785 s->qdev.type = TYPE_DISK;
353815aa
DF
1786 if (!s->product) {
1787 s->product = g_strdup("QEMU HARDDISK");
1788 }
e39be482 1789 return scsi_initfn(&s->qdev);
b443ae67
MA
1790}
1791
1792static int scsi_cd_initfn(SCSIDevice *dev)
1793{
e39be482
PB
1794 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, dev);
1795 s->qdev.blocksize = 2048;
1796 s->qdev.type = TYPE_ROM;
bfe3d7ac 1797 s->features |= 1 << SCSI_DISK_F_REMOVABLE;
353815aa
DF
1798 if (!s->product) {
1799 s->product = g_strdup("QEMU CD-ROM");
1800 }
e39be482 1801 return scsi_initfn(&s->qdev);
b443ae67
MA
1802}
1803
1804static int scsi_disk_initfn(SCSIDevice *dev)
1805{
95b5edcd 1806 DriveInfo *dinfo;
b443ae67
MA
1807
1808 if (!dev->conf.bs) {
e39be482 1809 return scsi_initfn(dev); /* ... and die there */
b443ae67
MA
1810 }
1811
e39be482
PB
1812 dinfo = drive_get_by_blockdev(dev->conf.bs);
1813 if (dinfo->media_cd) {
1814 return scsi_cd_initfn(dev);
1815 } else {
1816 return scsi_hd_initfn(dev);
1817 }
b443ae67
MA
1818}
1819
b08d0ea0 1820static const SCSIReqOps scsi_disk_emulate_reqops = {
8dbd4574 1821 .size = sizeof(SCSIDiskReq),
12010e7b 1822 .free_req = scsi_free_request,
b08d0ea0 1823 .send_command = scsi_disk_emulate_command,
314a3299
PB
1824 .read_data = scsi_disk_emulate_read_data,
1825 .write_data = scsi_disk_emulate_write_data,
b08d0ea0
PB
1826 .get_buf = scsi_get_buf,
1827};
1828
1829static const SCSIReqOps scsi_disk_dma_reqops = {
1830 .size = sizeof(SCSIDiskReq),
1831 .free_req = scsi_free_request,
1832 .send_command = scsi_disk_dma_command,
12010e7b
PB
1833 .read_data = scsi_read_data,
1834 .write_data = scsi_write_data,
1835 .cancel_io = scsi_cancel_io,
1836 .get_buf = scsi_get_buf,
43b978b9
PB
1837 .load_request = scsi_disk_load_request,
1838 .save_request = scsi_disk_save_request,
8dbd4574
PB
1839};
1840
b08d0ea0
PB
1841static const SCSIReqOps *const scsi_disk_reqops_dispatch[256] = {
1842 [TEST_UNIT_READY] = &scsi_disk_emulate_reqops,
1843 [INQUIRY] = &scsi_disk_emulate_reqops,
1844 [MODE_SENSE] = &scsi_disk_emulate_reqops,
1845 [MODE_SENSE_10] = &scsi_disk_emulate_reqops,
1846 [START_STOP] = &scsi_disk_emulate_reqops,
1847 [ALLOW_MEDIUM_REMOVAL] = &scsi_disk_emulate_reqops,
1848 [READ_CAPACITY_10] = &scsi_disk_emulate_reqops,
1849 [READ_TOC] = &scsi_disk_emulate_reqops,
1850 [READ_DVD_STRUCTURE] = &scsi_disk_emulate_reqops,
1851 [READ_DISC_INFORMATION] = &scsi_disk_emulate_reqops,
1852 [GET_CONFIGURATION] = &scsi_disk_emulate_reqops,
1853 [GET_EVENT_STATUS_NOTIFICATION] = &scsi_disk_emulate_reqops,
1854 [MECHANISM_STATUS] = &scsi_disk_emulate_reqops,
1855 [SERVICE_ACTION_IN_16] = &scsi_disk_emulate_reqops,
1856 [REQUEST_SENSE] = &scsi_disk_emulate_reqops,
1857 [SYNCHRONIZE_CACHE] = &scsi_disk_emulate_reqops,
1858 [SEEK_10] = &scsi_disk_emulate_reqops,
b08d0ea0
PB
1859 [MODE_SELECT] = &scsi_disk_emulate_reqops,
1860 [MODE_SELECT_10] = &scsi_disk_emulate_reqops,
b08d0ea0
PB
1861 [WRITE_SAME_10] = &scsi_disk_emulate_reqops,
1862 [WRITE_SAME_16] = &scsi_disk_emulate_reqops,
1863
1864 [READ_6] = &scsi_disk_dma_reqops,
1865 [READ_10] = &scsi_disk_dma_reqops,
1866 [READ_12] = &scsi_disk_dma_reqops,
1867 [READ_16] = &scsi_disk_dma_reqops,
1868 [VERIFY_10] = &scsi_disk_dma_reqops,
1869 [VERIFY_12] = &scsi_disk_dma_reqops,
1870 [VERIFY_16] = &scsi_disk_dma_reqops,
1871 [WRITE_6] = &scsi_disk_dma_reqops,
1872 [WRITE_10] = &scsi_disk_dma_reqops,
1873 [WRITE_12] = &scsi_disk_dma_reqops,
1874 [WRITE_16] = &scsi_disk_dma_reqops,
1875 [WRITE_VERIFY_10] = &scsi_disk_dma_reqops,
1876 [WRITE_VERIFY_12] = &scsi_disk_dma_reqops,
1877 [WRITE_VERIFY_16] = &scsi_disk_dma_reqops,
1878};
1879
63db0f0e
PB
1880static SCSIRequest *scsi_new_request(SCSIDevice *d, uint32_t tag, uint32_t lun,
1881 uint8_t *buf, void *hba_private)
8dbd4574
PB
1882{
1883 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, d);
1884 SCSIRequest *req;
b08d0ea0
PB
1885 const SCSIReqOps *ops;
1886 uint8_t command;
8dbd4574 1887
b08d0ea0
PB
1888#ifdef DEBUG_SCSI
1889 DPRINTF("Command: lun=%d tag=0x%x data=0x%02x", lun, buf[0]);
1890 {
1891 int i;
1892 for (i = 1; i < r->req.cmd.len; i++) {
1893 printf(" 0x%02x", buf[i]);
1894 }
1895 printf("\n");
1896 }
1897#endif
1898
1899 command = buf[0];
1900 ops = scsi_disk_reqops_dispatch[command];
1901 if (!ops) {
1902 ops = &scsi_disk_emulate_reqops;
1903 }
1904 req = scsi_req_alloc(ops, &s->qdev, tag, lun, hba_private);
8dbd4574
PB
1905 return req;
1906}
1907
336a6915
PB
1908#ifdef __linux__
1909static int get_device_type(SCSIDiskState *s)
1910{
1911 BlockDriverState *bdrv = s->qdev.conf.bs;
1912 uint8_t cmd[16];
1913 uint8_t buf[36];
1914 uint8_t sensebuf[8];
1915 sg_io_hdr_t io_header;
1916 int ret;
1917
1918 memset(cmd, 0, sizeof(cmd));
1919 memset(buf, 0, sizeof(buf));
1920 cmd[0] = INQUIRY;
1921 cmd[4] = sizeof(buf);
1922
1923 memset(&io_header, 0, sizeof(io_header));
1924 io_header.interface_id = 'S';
1925 io_header.dxfer_direction = SG_DXFER_FROM_DEV;
1926 io_header.dxfer_len = sizeof(buf);
1927 io_header.dxferp = buf;
1928 io_header.cmdp = cmd;
1929 io_header.cmd_len = sizeof(cmd);
1930 io_header.mx_sb_len = sizeof(sensebuf);
1931 io_header.sbp = sensebuf;
1932 io_header.timeout = 6000; /* XXX */
1933
1934 ret = bdrv_ioctl(bdrv, SG_IO, &io_header);
1935 if (ret < 0 || io_header.driver_status || io_header.host_status) {
1936 return -1;
1937 }
1938 s->qdev.type = buf[0];
bfe3d7ac
PB
1939 if (buf[1] & 0x80) {
1940 s->features |= 1 << SCSI_DISK_F_REMOVABLE;
1941 }
336a6915
PB
1942 return 0;
1943}
1944
1945static int scsi_block_initfn(SCSIDevice *dev)
1946{
1947 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, dev);
1948 int sg_version;
1949 int rc;
1950
1951 if (!s->qdev.conf.bs) {
1952 error_report("scsi-block: drive property not set");
1953 return -1;
1954 }
1955
1956 /* check we are using a driver managing SG_IO (version 3 and after) */
1957 if (bdrv_ioctl(s->qdev.conf.bs, SG_GET_VERSION_NUM, &sg_version) < 0 ||
1958 sg_version < 30000) {
1959 error_report("scsi-block: scsi generic interface too old");
1960 return -1;
1961 }
1962
1963 /* get device type from INQUIRY data */
1964 rc = get_device_type(s);
1965 if (rc < 0) {
1966 error_report("scsi-block: INQUIRY failed");
1967 return -1;
1968 }
1969
1970 /* Make a guess for the block size, we'll fix it when the guest sends.
1971 * READ CAPACITY. If they don't, they likely would assume these sizes
1972 * anyway. (TODO: check in /sys).
1973 */
1974 if (s->qdev.type == TYPE_ROM || s->qdev.type == TYPE_WORM) {
1975 s->qdev.blocksize = 2048;
1976 } else {
1977 s->qdev.blocksize = 512;
1978 }
1979 return scsi_initfn(&s->qdev);
1980}
1981
1982static SCSIRequest *scsi_block_new_request(SCSIDevice *d, uint32_t tag,
1983 uint32_t lun, uint8_t *buf,
1984 void *hba_private)
1985{
1986 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, d);
1987
1988 switch (buf[0]) {
1989 case READ_6:
1990 case READ_10:
1991 case READ_12:
1992 case READ_16:
7f64f8e2
PB
1993 case VERIFY_10:
1994 case VERIFY_12:
1995 case VERIFY_16:
336a6915
PB
1996 case WRITE_6:
1997 case WRITE_10:
1998 case WRITE_12:
1999 case WRITE_16:
2000 case WRITE_VERIFY_10:
2001 case WRITE_VERIFY_12:
2002 case WRITE_VERIFY_16:
eaccf49e
PB
2003 /* If we are not using O_DIRECT, we might read stale data from the
2004 * host cache if writes were made using other commands than these
2005 * ones (such as WRITE SAME or EXTENDED COPY, etc.). So, without
2006 * O_DIRECT everything must go through SG_IO.
2007 */
137745c5 2008 if (bdrv_get_flags(s->qdev.conf.bs) & BDRV_O_NOCACHE) {
eaccf49e
PB
2009 break;
2010 }
2011
33ebad12
PB
2012 /* MMC writing cannot be done via pread/pwrite, because it sometimes
2013 * involves writing beyond the maximum LBA or to negative LBA (lead-in).
2014 * And once you do these writes, reading from the block device is
2015 * unreliable, too. It is even possible that reads deliver random data
2016 * from the host page cache (this is probably a Linux bug).
2017 *
b08d0ea0 2018 * We might use scsi_disk_dma_reqops as long as no writing commands are
33ebad12
PB
2019 * seen, but performance usually isn't paramount on optical media. So,
2020 * just make scsi-block operate the same as scsi-generic for them.
2021 */
b08d0ea0
PB
2022 if (s->qdev.type != TYPE_ROM) {
2023 return scsi_req_alloc(&scsi_disk_dma_reqops, &s->qdev, tag, lun,
2024 hba_private);
2025 }
336a6915
PB
2026 }
2027
2028 return scsi_req_alloc(&scsi_generic_req_ops, &s->qdev, tag, lun,
2029 hba_private);
2030}
2031#endif
2032
353815aa
DF
2033#define DEFINE_SCSI_DISK_PROPERTIES() \
2034 DEFINE_BLOCK_PROPERTIES(SCSIDiskState, qdev.conf), \
2035 DEFINE_PROP_STRING("ver", SCSIDiskState, version), \
2036 DEFINE_PROP_STRING("serial", SCSIDiskState, serial), \
2037 DEFINE_PROP_STRING("vendor", SCSIDiskState, vendor), \
2038 DEFINE_PROP_STRING("product", SCSIDiskState, product)
b443ae67 2039
39bffca2
AL
2040static Property scsi_hd_properties[] = {
2041 DEFINE_SCSI_DISK_PROPERTIES(),
bfe3d7ac
PB
2042 DEFINE_PROP_BIT("removable", SCSIDiskState, features,
2043 SCSI_DISK_F_REMOVABLE, false),
da8365db
PB
2044 DEFINE_PROP_BIT("dpofua", SCSIDiskState, features,
2045 SCSI_DISK_F_DPOFUA, false),
27395add 2046 DEFINE_PROP_HEX64("wwn", SCSIDiskState, wwn, 0),
d252df48 2047 DEFINE_BLOCK_CHS_PROPERTIES(SCSIDiskState, qdev.conf),
39bffca2
AL
2048 DEFINE_PROP_END_OF_LIST(),
2049};
2050
43b978b9
PB
2051static const VMStateDescription vmstate_scsi_disk_state = {
2052 .name = "scsi-disk",
2053 .version_id = 1,
2054 .minimum_version_id = 1,
2055 .minimum_version_id_old = 1,
2056 .fields = (VMStateField[]) {
2057 VMSTATE_SCSI_DEVICE(qdev, SCSIDiskState),
2058 VMSTATE_BOOL(media_changed, SCSIDiskState),
2059 VMSTATE_BOOL(media_event, SCSIDiskState),
2060 VMSTATE_BOOL(eject_request, SCSIDiskState),
2061 VMSTATE_BOOL(tray_open, SCSIDiskState),
2062 VMSTATE_BOOL(tray_locked, SCSIDiskState),
2063 VMSTATE_END_OF_LIST()
2064 }
2065};
2066
b9eea3e6
AL
2067static void scsi_hd_class_initfn(ObjectClass *klass, void *data)
2068{
39bffca2 2069 DeviceClass *dc = DEVICE_CLASS(klass);
b9eea3e6
AL
2070 SCSIDeviceClass *sc = SCSI_DEVICE_CLASS(klass);
2071
2072 sc->init = scsi_hd_initfn;
2073 sc->destroy = scsi_destroy;
2074 sc->alloc_req = scsi_new_request;
2075 sc->unit_attention_reported = scsi_disk_unit_attention_reported;
39bffca2
AL
2076 dc->fw_name = "disk";
2077 dc->desc = "virtual SCSI disk";
2078 dc->reset = scsi_disk_reset;
2079 dc->props = scsi_hd_properties;
43b978b9 2080 dc->vmsd = &vmstate_scsi_disk_state;
b9eea3e6
AL
2081}
2082
39bffca2
AL
2083static TypeInfo scsi_hd_info = {
2084 .name = "scsi-hd",
2085 .parent = TYPE_SCSI_DEVICE,
2086 .instance_size = sizeof(SCSIDiskState),
2087 .class_init = scsi_hd_class_initfn,
2088};
2089
2090static Property scsi_cd_properties[] = {
2091 DEFINE_SCSI_DISK_PROPERTIES(),
27395add 2092 DEFINE_PROP_HEX64("wwn", SCSIDiskState, wwn, 0),
39bffca2 2093 DEFINE_PROP_END_OF_LIST(),
b9eea3e6
AL
2094};
2095
2096static void scsi_cd_class_initfn(ObjectClass *klass, void *data)
2097{
39bffca2 2098 DeviceClass *dc = DEVICE_CLASS(klass);
b9eea3e6
AL
2099 SCSIDeviceClass *sc = SCSI_DEVICE_CLASS(klass);
2100
2101 sc->init = scsi_cd_initfn;
2102 sc->destroy = scsi_destroy;
2103 sc->alloc_req = scsi_new_request;
2104 sc->unit_attention_reported = scsi_disk_unit_attention_reported;
39bffca2
AL
2105 dc->fw_name = "disk";
2106 dc->desc = "virtual SCSI CD-ROM";
2107 dc->reset = scsi_disk_reset;
2108 dc->props = scsi_cd_properties;
43b978b9 2109 dc->vmsd = &vmstate_scsi_disk_state;
b9eea3e6
AL
2110}
2111
39bffca2
AL
2112static TypeInfo scsi_cd_info = {
2113 .name = "scsi-cd",
2114 .parent = TYPE_SCSI_DEVICE,
2115 .instance_size = sizeof(SCSIDiskState),
2116 .class_init = scsi_cd_class_initfn,
b9eea3e6
AL
2117};
2118
336a6915 2119#ifdef __linux__
39bffca2 2120static Property scsi_block_properties[] = {
03847837 2121 DEFINE_PROP_DRIVE("drive", SCSIDiskState, qdev.conf.bs),
39bffca2
AL
2122 DEFINE_PROP_END_OF_LIST(),
2123};
2124
b9eea3e6
AL
2125static void scsi_block_class_initfn(ObjectClass *klass, void *data)
2126{
39bffca2 2127 DeviceClass *dc = DEVICE_CLASS(klass);
b9eea3e6
AL
2128 SCSIDeviceClass *sc = SCSI_DEVICE_CLASS(klass);
2129
2130 sc->init = scsi_block_initfn;
2131 sc->destroy = scsi_destroy;
2132 sc->alloc_req = scsi_block_new_request;
39bffca2
AL
2133 dc->fw_name = "disk";
2134 dc->desc = "SCSI block device passthrough";
2135 dc->reset = scsi_disk_reset;
2136 dc->props = scsi_block_properties;
43b978b9 2137 dc->vmsd = &vmstate_scsi_disk_state;
b9eea3e6
AL
2138}
2139
39bffca2
AL
2140static TypeInfo scsi_block_info = {
2141 .name = "scsi-block",
2142 .parent = TYPE_SCSI_DEVICE,
2143 .instance_size = sizeof(SCSIDiskState),
2144 .class_init = scsi_block_class_initfn,
b9eea3e6 2145};
336a6915 2146#endif
b9eea3e6 2147
39bffca2
AL
2148static Property scsi_disk_properties[] = {
2149 DEFINE_SCSI_DISK_PROPERTIES(),
bfe3d7ac
PB
2150 DEFINE_PROP_BIT("removable", SCSIDiskState, features,
2151 SCSI_DISK_F_REMOVABLE, false),
da8365db
PB
2152 DEFINE_PROP_BIT("dpofua", SCSIDiskState, features,
2153 SCSI_DISK_F_DPOFUA, false),
27395add 2154 DEFINE_PROP_HEX64("wwn", SCSIDiskState, wwn, 0),
39bffca2
AL
2155 DEFINE_PROP_END_OF_LIST(),
2156};
2157
b9eea3e6
AL
2158static void scsi_disk_class_initfn(ObjectClass *klass, void *data)
2159{
39bffca2 2160 DeviceClass *dc = DEVICE_CLASS(klass);
b9eea3e6
AL
2161 SCSIDeviceClass *sc = SCSI_DEVICE_CLASS(klass);
2162
2163 sc->init = scsi_disk_initfn;
2164 sc->destroy = scsi_destroy;
2165 sc->alloc_req = scsi_new_request;
2166 sc->unit_attention_reported = scsi_disk_unit_attention_reported;
39bffca2
AL
2167 dc->fw_name = "disk";
2168 dc->desc = "virtual SCSI disk or CD-ROM (legacy)";
2169 dc->reset = scsi_disk_reset;
2170 dc->props = scsi_disk_properties;
43b978b9 2171 dc->vmsd = &vmstate_scsi_disk_state;
b9eea3e6
AL
2172}
2173
39bffca2
AL
2174static TypeInfo scsi_disk_info = {
2175 .name = "scsi-disk",
2176 .parent = TYPE_SCSI_DEVICE,
2177 .instance_size = sizeof(SCSIDiskState),
2178 .class_init = scsi_disk_class_initfn,
d52affa7
GH
2179};
2180
83f7d43a 2181static void scsi_disk_register_types(void)
d52affa7 2182{
39bffca2
AL
2183 type_register_static(&scsi_hd_info);
2184 type_register_static(&scsi_cd_info);
b9eea3e6 2185#ifdef __linux__
39bffca2 2186 type_register_static(&scsi_block_info);
b9eea3e6 2187#endif
39bffca2 2188 type_register_static(&scsi_disk_info);
8ccc2ace 2189}
83f7d43a
AF
2190
2191type_init(scsi_disk_register_types)