summaryrefslogtreecommitdiff
path: root/usb/device/massstorage/SBC.h
blob: 7c648443b3828e115dbd0ebebf34cd89ca7b1b02 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
/* ----------------------------------------------------------------------------
 *         ATMEL Microcontroller Software Support 
 * ----------------------------------------------------------------------------
 * Copyright (c) 2008, Atmel Corporation
 *
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are met:
 *
 * - Redistributions of source code must retain the above copyright notice,
 * this list of conditions and the disclaimer below.
 *
 * Atmel's name may not be used to endorse or promote products derived from
 * this software without specific prior written permission.
 *
 * DISCLAIMER: THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR
 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE
 * DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR ANY DIRECT, INDIRECT,
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
 * OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
 * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 * ----------------------------------------------------------------------------
 */

//------------------------------------------------------------------------------
/// \unit
/// !Purpose
/// 
/// SCSI definitions.
/// 
/// !Usage
/// 
/// -# After command block received, Access and decode the SCSI command block
///    with SBCCommand structure.
//------------------------------------------------------------------------------

#ifndef SBC_H
#define SBC_H

//------------------------------------------------------------------------------
//      Definitions
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \page "SBC Operation Codes"
/// This page lists operation codes of commands described in the SBC-3
/// standard.
///
/// \note That most commands are actually defined in other standards,
///       like SPC-4. Optional commands are not included here.
///
/// \see    sbc3r07.pdf - Section 5.1 - Table 12
/// \see    spc4r06.pdf
/// \see    SBCCommand
///
/// !Codes
/// - SBC_INQUIRY
/// - SBC_READ_10
/// - SBC_READ_CAPACITY_10
/// - SBC_REQUEST_SENSE
/// - SBC_TEST_UNIT_READY
/// - SBC_WRITE_10
///
/// !Optional Codes but required by Windows
/// - SBC_PREVENT_ALLOW_MEDIUM_REMOVAL
/// - SBC_MODE_SENSE_6
/// - SBC_VERIFY_10
/// - SBC_READ_FORMAT_CAPACITIES

/// Request information regarding parameters of the target and Logical Unit.
#define SBC_INQUIRY                                     0x12
/// Request the transfer data to the host.
#define SBC_READ_10                                     0x28
/// Request capacities of the currently installed medium.
#define SBC_READ_CAPACITY_10                            0x25
/// Request that the device server transfer sense data.
#define SBC_REQUEST_SENSE                               0x03
/// Check if the LUN is ready
#define SBC_TEST_UNIT_READY                             0x00
/// Request that the device write the data transferred by the host.
#define SBC_WRITE_10                                    0x2A

/// Request that the target enable or disable the removal of the medium in
/// the Logical Unit.
#define SBC_PREVENT_ALLOW_MEDIUM_REMOVAL                0x1E
/// Report parameters.
#define SBC_MODE_SENSE_6                                0x1A
/// Request that the %device verify the data on the medium.
#define SBC_VERIFY_10                                   0x2F
/// Request a list of the possible capacities that can be formatted on medium
#define SBC_READ_FORMAT_CAPACITIES                      0x23
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \page "SBC Periph. Qualifiers"
/// This page lists the peripheral qualifier values specified in the INQUIRY
/// data
/// \see    spc4r06.pdf - Section 6.4.2 - Table 83
/// \see    SBCInquiryData
///
/// !Qualifiers
/// - SBC_PERIPHERAL_DEVICE_CONNECTED
/// - SBC_PERIPHERAL_DEVICE_NOT_CONNECTED
/// - SBC_PERIPHERAL_DEVICE_NOT_SUPPORTED

#define SBC_PERIPHERAL_DEVICE_CONNECTED                 0x00
#define SBC_PERIPHERAL_DEVICE_NOT_CONNECTED             0x01
#define SBC_PERIPHERAL_DEVICE_NOT_SUPPORTED             0x03
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \page "SBC Periph. Types"
/// This page lists peripheral device types specified in the INQUIRY data
/// \see    spc4r06.pdf - Section 6.4.2 - Table 84
/// \see    SBCInquiryData
///
/// !Types
/// - SBC_DIRECT_ACCESS_BLOCK_DEVICE
/// - SBC_SEQUENTIAL_ACCESS_DEVICE
/// - SBC_PRINTER_DEVICE
/// - SBC_PROCESSOR_DEVICE
/// - SBC_WRITE_ONCE_DEVICE
/// - SBC_CD_DVD_DEVICE
/// - SBC_SCANNER_DEVICE
/// - SBC_OPTICAL_MEMORY_DEVICE
/// - SBC_MEDIA_CHANGER_DEVICE
/// - SBC_COMMUNICATION_DEVICE
/// - SBC_STORAGE_ARRAY_CONTROLLER_DEVICE
/// - SBC_ENCLOSURE_SERVICES_DEVICE
/// - SBC_SIMPLIFIED_DIRECT_ACCESS_DEVICE
/// - SBC_OPTICAL_CARD_READER_WRITER_DEVICE
/// - SBC_BRIDGE_CONTROLLER_COMMANDS
/// - SBC_OBJECT_BASED_STORAGE_DEVICE

#define SBC_DIRECT_ACCESS_BLOCK_DEVICE              0x00
#define SBC_SEQUENTIAL_ACCESS_DEVICE                0x01
#define SBC_PRINTER_DEVICE                          0x02
#define SBC_PROCESSOR_DEVICE                        0x03
#define SBC_WRITE_ONCE_DEVICE                       0x04
#define SBC_CD_DVD_DEVICE                           0x05
#define SBC_SCANNER_DEVICE                          0x06
#define SBC_OPTICAL_MEMORY_DEVICE                   0x07
#define SBC_MEDIA_CHANGER_DEVICE                    0x08
#define SBC_COMMUNICATION_DEVICE                    0x09
#define SBC_STORAGE_ARRAY_CONTROLLER_DEVICE         0x0C
#define SBC_ENCLOSURE_SERVICES_DEVICE               0x0D
#define SBC_SIMPLIFIED_DIRECT_ACCESS_DEVICE         0x0E
#define SBC_OPTICAL_CARD_READER_WRITER_DEVICE       0x0F
#define SBC_BRIDGE_CONTROLLER_COMMANDS              0x10
#define SBC_OBJECT_BASED_STORAGE_DEVICE             0x11
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \brief  Version value for the SBC-3 specification
/// \see    spc4r06.pdf - Section 6.4.2 - Table 85
#define SBC_SPC_VERSION_4                           0x06
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \brief  Values for the TPGS field returned in INQUIRY data
/// \see    spc4r06.pdf - Section 6.4.2 - Table 86
#define SBC_TPGS_NONE                               0x0
#define SBC_TPGS_ASYMMETRIC                         0x1
#define SBC_TPGS_SYMMETRIC                          0x2
#define SBC_TPGS_BOTH                               0x3
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \brief  Version descriptor value for the SBC-3 specification
/// \see    spc4r06.pdf - Section 6.4.2 - Table 87
#define SBC_VERSION_DESCRIPTOR_SBC_3                0x04C0
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \page "SBC Sense Response Codes"
/// This page lists sense data response codes returned in REQUEST SENSE data
/// \see    spc4r06.pdf - Section 4.5.1 - Table 12
///
/// !Codes
/// - SBC_SENSE_DATA_FIXED_CURRENT
/// - SBC_SENSE_DATA_FIXED_DEFERRED
/// - SBC_SENSE_DATA_DESCRIPTOR_CURRENT
/// - SBC_SENSE_DATA_DESCRIPTOR_DEFERRED

#define SBC_SENSE_DATA_FIXED_CURRENT                0x70
#define SBC_SENSE_DATA_FIXED_DEFERRED               0x71
#define SBC_SENSE_DATA_DESCRIPTOR_CURRENT           0x72
#define SBC_SENSE_DATA_DESCRIPTOR_DEFERRED          0x73
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \page "SBC Sense Keys"
/// This page lists sense key values returned in the REQUEST SENSE data
/// \see    spc4r06.pdf - Section 4.5.6 - Table 27
///
/// !Keys
/// - SBC_SENSE_KEY_NO_SENSE
/// - SBC_SENSE_KEY_RECOVERED_ERROR
/// - SBC_SENSE_KEY_NOT_READY
/// - SBC_SENSE_KEY_MEDIUM_ERROR
/// - SBC_SENSE_KEY_HARDWARE_ERROR
/// - SBC_SENSE_KEY_ILLEGAL_REQUEST
/// - SBC_SENSE_KEY_UNIT_ATTENTION
/// - SBC_SENSE_KEY_DATA_PROTECT
/// - SBC_SENSE_KEY_BLANK_CHECK
/// - SBC_SENSE_KEY_VENDOR_SPECIFIC
/// - SBC_SENSE_KEY_COPY_ABORTED
/// - SBC_SENSE_KEY_ABORTED_COMMAND
/// - SBC_SENSE_KEY_VOLUME_OVERFLOW
/// - SBC_SENSE_KEY_MISCOMPARE

/// No specific sense key. Successful command.
#define SBC_SENSE_KEY_NO_SENSE                        0x00
/// Command completed succesfully with some recovery action by the %device.
#define SBC_SENSE_KEY_RECOVERED_ERROR                 0x01
/// The device can not be accessed.
#define SBC_SENSE_KEY_NOT_READY                       0x02
/// Command terminated with a error condition that was probably caused by a
/// flaw in the medium or an error in the recorded data.
#define SBC_SENSE_KEY_MEDIUM_ERROR                    0x03
/// Hardware failure while performing the command or during a self test.
#define SBC_SENSE_KEY_HARDWARE_ERROR                  0x04
/// Illegal parameter found in the command or additional parameters.
#define SBC_SENSE_KEY_ILLEGAL_REQUEST                 0x05
/// Removable medium may have been changed or the %device has been reset.
#define SBC_SENSE_KEY_UNIT_ATTENTION                  0x06
/// Write on a block that is protected.
#define SBC_SENSE_KEY_DATA_PROTECT                    0x07
/// Indicates that a write-once device or a sequential-access device
/// encountered blank medium or format-defined end-of-data indication while
/// reading or a write-once device encountered a non-blank medium while writing.
#define SBC_SENSE_KEY_BLANK_CHECK                     0x08
/// Reporting vendor specific conditions.
#define SBC_SENSE_KEY_VENDOR_SPECIFIC                 0x09
/// EXTENDED COPY command was aborted.
#define SBC_SENSE_KEY_COPY_ABORTED                    0x0A
/// Device aborted the command.
#define SBC_SENSE_KEY_ABORTED_COMMAND                 0x0B
/// A buffered peripheral device is overflow.
#define SBC_SENSE_KEY_VOLUME_OVERFLOW                 0x0D
/// The source data did not match the data read from the medium.
#define SBC_SENSE_KEY_MISCOMPARE                      0x0E
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \page "SBC Sense Additionals"
/// This page lists additional sense code values returned in REQUEST SENSE data
/// \see    spc4r06.pdf - Section 4.5.6 - Table 28
///
/// !Additional Codes
/// - SBC_ASC_LOGICAL_UNIT_NOT_READY
/// - SBC_ASC_LOGICAL_BLOCK_ADDRESS_OUT_OF_RANGE
/// - SBC_ASC_INVALID_FIELD_IN_CDB
/// - SBC_ASC_WRITE_PROTECTED
/// - SBC_ASC_FORMAT_CORRUPTED
/// - SBC_ASC_INVALID_COMMAND_OPERATION_CODE
/// - SBC_ASC_TOO_MUCH_WRITE_DATA
/// - SBC_ASC_NOT_READY_TO_READY_CHANGE
/// - SBC_ASC_MEDIUM_NOT_PRESENT

#define SBC_ASC_LOGICAL_UNIT_NOT_READY                0x04
#define SBC_ASC_LOGICAL_BLOCK_ADDRESS_OUT_OF_RANGE    0x21
#define SBC_ASC_INVALID_FIELD_IN_CDB                  0x24
#define SBC_ASC_WRITE_PROTECTED                       0x27
#define SBC_ASC_FORMAT_CORRUPTED                      0x31
#define SBC_ASC_INVALID_COMMAND_OPERATION_CODE        0x20
#define SBC_ASC_TOO_MUCH_WRITE_DATA                   0x26
#define SBC_ASC_NOT_READY_TO_READY_CHANGE             0x28
#define SBC_ASC_MEDIUM_NOT_PRESENT                    0x3A
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \brief  MEDIUM TYPE field value for direct-access block devices
/// \see    sbc3r06.pdf - Section 6.3.1
#define SBC_MEDIUM_TYPE_DIRECT_ACCESS_BLOCK_DEVICE    0x00
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \brief  MRIE field values
/// \see    sbc3r06.pdf - Section 7.4.11 - Table 286
#define SBC_MRIE_NO_REPORTING                         0x00
#define SBC_MRIE_ASYNCHRONOUS                         0x01
#define SBC_MRIE_GENERATE_UNIT_ATTENTION              0x02
#define SBC_MRIE_COND_GENERATE_RECOVERED_ERROR        0x03
#define SBC_MRIE_UNCOND_GENERATE_RECOVERED_ERROR      0x04
#define SBC_MRIE_GENERATE_NO_SENSE                    0x05
#define SBC_MRIE_ON_REQUEST                           0x06
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \brief  Supported mode pages
/// \see    sbc3r06.pdf - Section 6.3.1 - Table 115
#define SBC_PAGE_READ_WRITE_ERROR_RECOVERY            0x01
#define SBC_PAGE_INFORMATIONAL_EXCEPTIONS_CONTROL     0x1C
#define SBC_PAGE_RETURN_ALL                           0x3F
#define SBC_PAGE_VENDOR_SPECIFIC                      0x00
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
/// \page "MSD Endian Macros"
/// This page lists the macros for endianness conversion.
///
/// !Macros
/// - WORDB
/// - DWORDB
/// - STORE_DWORDB
/// - STORE_WORDB
/// \brief  Converts a byte array to a word value using the big endian format
#define WORDB(bytes)            ((unsigned short) ((bytes[0] << 8) | bytes[1]))

/// \brief  Converts a byte array to a dword value using the big endian format
#define DWORDB(bytes)   ((unsigned int) ((bytes[0] << 24) | (bytes[1] << 16) \
                                         | (bytes[2] << 8) | bytes[3]))

/// \brief  Stores a dword value in a byte array, in big endian format
#define STORE_DWORDB(dword, bytes) \
    bytes[0] = (unsigned char) (((dword) >> 24) & 0xFF); \
    bytes[1] = (unsigned char) (((dword) >> 16) & 0xFF); \
    bytes[2] = (unsigned char) (((dword) >> 8) & 0xFF); \
    bytes[3] = (unsigned char) ((dword) & 0xFF);

/// \brief  Stores a word value in a byte array, in big endian format
#define STORE_WORDB(word, bytes) \
    bytes[0] = (unsigned char) (((word) >> 8) & 0xFF); \
    bytes[1] = (unsigned char) ((word) & 0xFF);
//------------------------------------------------------------------------------

//------------------------------------------------------------------------------
//      Structures
//------------------------------------------------------------------------------

#ifdef __ICCARM__          // IAR
#pragma pack(1)            // IAR
#define __attribute__(...) // IAR
#endif                     // IAR

//------------------------------------------------------------------------------
/// \brief  Structure for the INQUIRY command
/// \see    spc4r06.pdf - Section 6.4.1 - Table 81
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bOperationCode;       //!< 0x12 : SBC_INQUIRY
    unsigned char isEVPD:1,             //!< Type of requested data
                  bReserved1:7;         //!< Reserved bits
    unsigned char bPageCode;            //!< Specifies the VPD to return
    unsigned char pAllocationLength[2]; //!< Size of host buffer
    unsigned char bControl;             //!< 0x00

} __attribute__ ((packed)) SBCInquiry; // GCC

//------------------------------------------------------------------------------
/// \brief  Standard INQUIRY data format returned by the device
/// \see    spc4r06.pdf - Section 6.4.2 - Table 82
//------------------------------------------------------------------------------
typedef struct {

    unsigned char  bPeripheralDeviceType:5, //!< Peripheral device type
                   bPeripheralQualifier :3; //!< Peripheral qualifier
    unsigned char  bReserved1:7,            //!< Reserved bits
                   isRMB     :1;            //!< Is media removable ?
    unsigned char  bVersion;                //!< SPC version used
    unsigned char  bResponseDataFormat:4,   //!< Must be 0x2
                   isHIGHSUP          :1,   //!< Hierarchical addressing used ?
                   isNORMACA          :1,   //!< ACA attribute supported ?
                   bObsolete1         :2;   //!< Obsolete bits
    unsigned char  bAdditionalLength;       //!< Length of remaining INQUIRY data
    unsigned char  isSCCS    :1,            //!< Embedded SCC ?
                   isACC     :1,            //!< Access control coordinator ?
                   bTPGS     :2,            //!< Target port support group
                   is3PC     :1,            //!< Third-party copy supported ?
                   bReserved2:2,            //!< Reserved bits
                   isProtect :1;            //!< Protection info supported ?
    unsigned char  bObsolete2:1,            //!< Obsolete bit
                   isEncServ :1,            //!< Embedded enclosure service comp?
                   isVS      :1,            //!< ???
                   isMultiP  :1,            //!< Multi-port device ?
                   bObsolete3:3,            //!< Obsolete bits
                   bUnused1  :1;            //!< Unused feature
    unsigned char  bUnused2:6,              //!< Unused features
                   isCmdQue:1,              //!< Task management model supported ?
                   isVS2   :1;              //!< ???
    unsigned char  pVendorID[8];            //!< T10 vendor identification
    unsigned char  pProductID[16];          //!< Vendor-defined product ID
    unsigned char  pProductRevisionLevel[4];//!< Vendor-defined product revision
    unsigned char  pVendorSpecific[20];     //!< Vendor-specific data
    unsigned char  bUnused3;                //!< Unused features
    unsigned char  bReserved3;              //!< Reserved bits
    unsigned short pVersionDescriptors[8];  //!< Standards the device complies to
    unsigned char  pReserved4[22];          //!< Reserved bytes

} __attribute__ ((packed)) SBCInquiryData; // GCC

//------------------------------------------------------------------------------
/// \brief  Data structure for the READ (10) command
/// \see    sbc3r07.pdf - Section 5.7 - Table 34
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bOperationCode;          //!< 0x28 : SBC_READ_10
    unsigned char bObsolete1:1,            //!< Obsolete bit
                  isFUA_NV:1,              //!< Cache control bit
                  bReserved1:1,            //!< Reserved bit
                  isFUA:1,                 //!< Cache control bit
                  isDPO:1,                 //!< Cache control bit
                  bRdProtect:3;            //!< Protection information to send
    unsigned char pLogicalBlockAddress[4]; //!< Index of first block to read
    unsigned char bGroupNumber:5,          //!< Information grouping
                  bReserved2:3;            //!< Reserved bits
    unsigned char pTransferLength[2];      //!< Number of blocks to transmit
    unsigned char bControl;                //!< 0x00

} __attribute__ ((packed)) SBCRead10; // GCC

//------------------------------------------------------------------------------
/// \brief  Structure for the READ CAPACITY (10) command
/// \see    sbc3r07.pdf - Section 5.11.1 - Table 40
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bOperationCode;          //!< 0x25 : RBC_READ_CAPACITY
    unsigned char bObsolete1:1,            //!< Obsolete bit
                  bReserved1:7;            //!< Reserved bits
    unsigned char pLogicalBlockAddress[4]; //!< Block to evaluate if PMI is set
    unsigned char pReserved2[2];           //!< Reserved bytes
    unsigned char isPMI:1,                 //!< Partial medium indicator bit
                  bReserved3:7;            //!< Reserved bits
    unsigned char bControl;                //!< 0x00

} SBCReadCapacity10;

//------------------------------------------------------------------------------
/// \brief  Data returned by the device after a READ CAPACITY (10) command
/// \see    sbc3r07.pdf - Section 5.11.2 - Table 41
//------------------------------------------------------------------------------
typedef struct {

    unsigned char pLogicalBlockAddress[4]; //!< Address of last logical block
    unsigned char pLogicalBlockLength[4];  //!< Length of each logical block

} SBCReadCapacity10Data;

//------------------------------------------------------------------------------
/// \brief  Structure for the REQUEST SENSE command
/// \see    spc4r06.pdf - Section 6.26 - Table 170
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bOperationCode;    //!< 0x03 : SBC_REQUEST_SENSE
    unsigned char isDesc    :1,      //!< Type of information expected
                  bReserved1:7;      //!< Reserved bits
    unsigned char pReserved2[2];     //!< Reserved bytes
    unsigned char bAllocationLength; //!< Size of host buffer
    unsigned char bControl;          //!< 0x00

} SBCRequestSense;

//------------------------------------------------------------------------------
/// \brief  Fixed format sense data returned after a REQUEST SENSE command has
///         been received with a DESC bit cleared.
/// \see    spc4r06.pdf - Section 4.5.3 - Table 26
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bResponseCode:7,                //!< Sense data format
                  isValid      :1;                //!< Information field is standard
    unsigned char bObsolete1;                     //!< Obsolete byte
    unsigned char bSenseKey :4,                   //!< Generic error information
                  bReserved1:1,                   //!< Reserved bit
                  isILI     :1,                   //!< SSC
                  isEOM     :1,                   //!< SSC
                  isFilemark:1;                   //!< SSC
    unsigned char pInformation[4];                //!< Command-specific
    unsigned char bAdditionalSenseLength;         //!< sizeof(SBCRequestSense_data)-8
    unsigned char pCommandSpecificInformation[4]; //!< Command-specific
    unsigned char bAdditionalSenseCode;           //!< Additional error information
    unsigned char bAdditionalSenseCodeQualifier;  //!< Further error information
    unsigned char bFieldReplaceableUnitCode;      //!< Specific component code
    unsigned char bSenseKeySpecific:7,            //!< Additional exception info
                  isSKSV           :1;            //!< Is sense key specific valid?
    unsigned char pSenseKeySpecific[2];           //!< Additional exception info

} SBCRequestSenseData;

//------------------------------------------------------------------------------
/// \brief  Data structure for the TEST UNIT READY command
/// \see    spc4r06.pdf - Section 6.34 - Table 192
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bOperationCode; //!< 0x00 : SBC_TEST_UNIT_READY
    unsigned char pReserved1[4];  //!< Reserved bits
    unsigned char bControl;       //!< 0x00

} __attribute__ ((packed)) SBCTestUnitReady; // GCC

//------------------------------------------------------------------------------
/// \brief  Structure for the WRITE (10) command
/// \see    sbc3r07.pdf - Section 5.26 - Table 70
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bOperationCode;          //!< 0x2A : SBC_WRITE_10
    unsigned char bObsolete1:1,            //!< Obsolete bit
                  isFUA_NV:1,              //!< Cache control bit
                  bReserved1:1,            //!< Reserved bit
                  isFUA:1,                 //!< Cache control bit
                  isDPO:1,                 //!< Cache control bit
                  bWrProtect:3;            //!< Protection information to send
    unsigned char pLogicalBlockAddress[4]; //!< First block to write
    unsigned char bGroupNumber:5,          //!< Information grouping
                  bReserved2:3;            //!< Reserved bits
    unsigned char pTransferLength[2];      //!< Number of blocks to write
    unsigned char bControl;                //!< 0x00

} SBCWrite10;

//------------------------------------------------------------------------------
/// \brief  Structure for the PREVENT/ALLOW MEDIUM REMOVAL command
/// \see    sbc3r07.pdf - Section 5.5 - Table 30
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bOperationCode; //!< 0x1E : SBC_PREVENT_ALLOW_MEDIUM_REMOVAL
    unsigned char pReserved1[3];  //!< Reserved bytes
    unsigned char bPrevent:2,     //!< Accept/prohibit removal
                  bReserved2:6;   //!< Reserved bits
    unsigned char bControl;       //!< 0x00

} __attribute__ ((packed)) SBCMediumRemoval; // GCC

//------------------------------------------------------------------------------
/// \brief  Structure for the MODE SENSE (6) command
/// \see    spc4r06 - Section 6.9.1 - Table 98
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bOperationCode;    //!< 0x1A : SBC_MODE_SENSE_6
    unsigned char bReserved1:3,      //!< Reserved bits
                  isDBD:1,           //!< Disable block descriptors bit
                  bReserved2:4;      //!< Reserved bits
    unsigned char bPageCode:6,       //!< Mode page to return
                  bPC:2;             //!< Type of parameter values to return
    unsigned char bSubpageCode;      //!< Mode subpage to return
    unsigned char bAllocationLength; //!< Host buffer allocated size
    unsigned char bControl;          //!< 0x00

} __attribute__ ((packed)) SBCModeSense6; // GCC

//------------------------------------------------------------------------------
/// \brief  Header for the data returned after a MODE SENSE (6) command
/// \see    spc4r06.pdf - Section 7.4.3 - Table 268
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bModeDataLength;          //!< Length of mode data to follow
    unsigned char bMediumType;              //!< Type of medium (SBC_MEDIUM_TYPE_DIRECT_ACCESS_BLOCK_DEVICE)
    unsigned char bReserved1:4,             //!< Reserved bits
                  isDPOFUA:1,               //!< DPO/FUA bits supported ?
                  bReserved2:2,             //!< Reserved bits
                  isWP:1;                   //!< Is medium write-protected ?
    unsigned char bBlockDescriptorLength;   //!< Length of all block descriptors

} __attribute__ ((packed)) SBCModeParameterHeader6; // GCC

//------------------------------------------------------------------------------
/// \brief  Informational exceptions control mode page
/// \see    spc4r06.pdf - Section 7.4.11 - Table 285
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bPageCode:6,       //!< 0x1C : SBC_PAGE_INFORMATIONAL_EXCEPTIONS_CONTROL
                  isSPF:1,           //!< Page or subpage data format
                  isPS:1;            //!< Parameters saveable ?
    unsigned char bPageLength;       //!< Length of page data (0x0A)
    unsigned char isLogErr:1,        //!< Should informational exceptions be logged ?
                  isEBackErr:1,      //!< Enable background error bit
                  isTest:1,          //!< Create a device test failure ?
                  isDExcpt:1,        //!< Disable exception control bit
                  isEWasc:1,         //!< Report warnings ?
                  isEBF:1,           //!< Enable background function bit
                  bReserved1:1,      //!< Reserved bit
                  isPerf:1;          //!< Delay acceptable when treating exceptions ?
    unsigned char bMRIE:4,           //!< Method of reporting informational exceptions
                  bReserved2:4;      //!< Reserved bits
    unsigned char pIntervalTimer[4]; //!< Error reporting period
    unsigned char pReportCount[4];   //!< Maximum number of time a report can be issued

} __attribute__ ((packed)) SBCInformationalExceptionsControl; // GCC

//------------------------------------------------------------------------------
/// \brief  Read/write error recovery mode page
/// \see    sbc3r07.pdf - Section 6.3.5 - Table 122
//------------------------------------------------------------------------------
typedef struct {

    unsigned char bPageCode:6,           //!< 0x01 : SBC_PAGE_READ_WRITE_ERROR_RECOVERY
                  isSPF:1,               //!< Page or subpage data format
                  isPS:1;                //!< Parameters saveable ?
    unsigned char bPageLength;           //!< Length of page data (0x0A)
    unsigned char isDCR:1,               //!< Disable correction bit
                  isDTE:1,               //!< Data terminate on error bit
                  isPER:1,               //!< Post error bit
                  isEER:1,               //!< Enable early recovery bit
                  isRC:1,                //!< Read continuous bit
                  isTB:1,                //!< Transfer block bit
                  isARRE:1,              //!< Automatic read reallocation enabled bit
                  isAWRE:1;              //!< Automatic write reallocation enabled bit
    unsigned char bReadRetryCount;       //!< Number of retries when reading
    unsigned char pObsolete1[3];         //!< Obsolete bytes
    unsigned char bReserved1;            //!< Reserved byte
    unsigned char bWriteRetryCount;      //!< Number of retries when writing
    unsigned char bReserved2;            //!< Reserved byte
    unsigned char pRecoveryTimeLimit[2]; //!< Maximum time duration for error recovery

} __attribute__ ((packed)) SBCReadWriteErrorRecovery; // GCC

//------------------------------------------------------------------------------
/// \brief  Generic structure for holding information about SBC commands
/// \see    SBCInquiry
/// \see    SBCRead10
/// \see    SBCReadCapacity10
/// \see    SBCRequestSense
/// \see    SBCTestUnitReady
/// \see    SBCWrite10
/// \see    SBCMediumRemoval
/// \see    SBCModeSense6
//------------------------------------------------------------------------------
typedef union {

    unsigned char     bOperationCode; //!< Operation code of the command
    SBCInquiry        inquiry;        //!< INQUIRY command
    SBCRead10         read10;         //!< READ (10) command
    SBCReadCapacity10 readCapacity10; //!< READ CAPACITY (10) command
    SBCRequestSense   requestSense;   //!< REQUEST SENSE command
    SBCTestUnitReady  testUnitReady;  //!< TEST UNIT READY command
    SBCWrite10        write10;        //!< WRITE (10) command
    SBCMediumRemoval  mediumRemoval;  //!< PREVENT/ALLOW MEDIUM REMOVAL command
    SBCModeSense6     modeSense6;     //!< MODE SENSE (6) command

} SBCCommand;

#ifdef __ICCARM__          // IAR
#pragma pack()             // IAR
#endif                     // IAR

#endif //#ifndef SBC_H

personal git repositories of Harald Welte. Your mileage may vary