]> git.proxmox.com Git - mirror_smartmontools-debian.git/blob - scsiata.cpp
Merge commit 'upstream/5.38+svn2993'
[mirror_smartmontools-debian.git] / scsiata.cpp
1 /*
2 * scsiata.cpp
3 *
4 * Home page of code is: http://smartmontools.sourceforge.net
5 *
6 * Copyright (C) 2006-9 Douglas Gilbert <dougg@torque.net>
7 * Copyright (C) 2009 Christian Franke <smartmontools-support@lists.sourceforge.net>
8 *
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2, or (at your option)
12 * any later version.
13 *
14 * You should have received a copy of the GNU General Public License
15 * (for example COPYING); if not, write to the Free
16 * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17 *
18 * The code in this file is based on the SCSI to ATA Translation (SAT)
19 * draft found at http://www.t10.org . The original draft used for this
20 * code is sat-r08.pdf which is not too far away from becoming a
21 * standard. The SAT commands of interest to smartmontools are the
22 * ATA PASS THROUGH SCSI (16) and ATA PASS THROUGH SCSI (12) defined in
23 * section 12 of that document.
24 *
25 * sat-r09.pdf is the most recent, easily accessible draft prior to the
26 * original SAT standard (ANSI INCITS 431-2007). By mid-2009 the second
27 * version of the SAT standard (SAT-2) is nearing standardization. In
28 * their wisdom an incompatible change has been introduced in draft
29 * sat2r08a.pdf in the area of the ATA RETURN DESCRIPTOR. A new "fixed
30 * format" ATA RETURN buffer has been defined (sat2r08b.pdf section
31 * 12.2.7) for the case when DSENSE=0 in the Control mode page.
32 * Unfortunately this is the normal case. If the change stands our
33 * code will need to be extended for this case.
34 *
35 * With more transports "hiding" SATA disks (and other S-ATAPI devices)
36 * behind a SCSI command set, accessing special features like SMART
37 * information becomes a challenge. The SAT standard offers ATA PASS
38 * THROUGH commands for special usages. Note that the SAT layer may
39 * be inside a generic OS layer (e.g. libata in linux), in a host
40 * adapter (HA or HBA) firmware, or somewhere on the interconnect
41 * between the host computer and the SATA devices (e.g. a RAID made
42 * of SATA disks and the RAID talks "SCSI" to the host computer).
43 * Note that in the latter case, this code does not solve the
44 * addressing issue (i.e. which SATA disk to address behind the logical
45 * SCSI (RAID) interface).
46 *
47 */
48
49 #include <stdio.h>
50 #include <string.h>
51 #include <stdlib.h>
52 #include <ctype.h>
53
54 #include "config.h"
55 #include "int64.h"
56 #include "extern.h"
57 #include "scsicmds.h"
58 #include "atacmds.h" // ataReadHDIdentity()
59 #include "utility.h"
60 #include "dev_interface.h"
61 #include "dev_ata_cmd_set.h" // ata_device_with_command_set
62 #include "dev_tunnelled.h" // tunnelled_device<>
63
64 const char * scsiata_cpp_cvsid = "$Id: scsiata.cpp 2988 2009-11-29 16:21:07Z samm2 $";
65
66 /* for passing global control variables */
67 extern smartmonctrl *con;
68
69 /* This is a slightly stretched SCSI sense "descriptor" format header.
70 The addition is to allow the 0x70 and 0x71 response codes. The idea
71 is to place the salient data of both "fixed" and "descriptor" sense
72 format into one structure to ease application processing.
73 The original sense buffer should be kept around for those cases
74 in which more information is required (e.g. the LBA of a MEDIUM ERROR). */
75 /// Abridged SCSI sense data
76 struct sg_scsi_sense_hdr {
77 unsigned char response_code; /* permit: 0x0, 0x70, 0x71, 0x72, 0x73 */
78 unsigned char sense_key;
79 unsigned char asc;
80 unsigned char ascq;
81 unsigned char byte4;
82 unsigned char byte5;
83 unsigned char byte6;
84 unsigned char additional_length;
85 };
86
87 /* Maps the salient data from a sense buffer which is in either fixed or
88 descriptor format into a structure mimicking a descriptor format
89 header (i.e. the first 8 bytes of sense descriptor format).
90 If zero response code returns 0. Otherwise returns 1 and if 'sshp' is
91 non-NULL then zero all fields and then set the appropriate fields in
92 that structure. sshp::additional_length is always 0 for response
93 codes 0x70 and 0x71 (fixed format). */
94 static int sg_scsi_normalize_sense(const unsigned char * sensep, int sb_len,
95 struct sg_scsi_sense_hdr * sshp);
96
97 /* Attempt to find the first SCSI sense data descriptor that matches the
98 given 'desc_type'. If found return pointer to start of sense data
99 descriptor; otherwise (including fixed format sense data) returns NULL. */
100 static const unsigned char * sg_scsi_sense_desc_find(const unsigned char * sensep,
101 int sense_len, int desc_type);
102
103 #define SAT_ATA_PASSTHROUGH_12LEN 12
104 #define SAT_ATA_PASSTHROUGH_16LEN 16
105
106 #define DEF_SAT_ATA_PASSTHRU_SIZE 16
107 #define ATA_RETURN_DESCRIPTOR 9
108
109
110 namespace sat { // no need to publish anything, name provided for Doxygen
111
112 /// SAT support.
113 /// Implements ATA by tunnelling through SCSI.
114
115 class sat_device
116 : public tunnelled_device<
117 /*implements*/ ata_device
118 /*by tunnelling through a*/, scsi_device
119 >
120 {
121 public:
122 sat_device(smart_interface * intf, scsi_device * scsidev,
123 const char * req_type, int passthrulen = 0);
124
125 virtual ~sat_device() throw();
126
127 virtual bool ata_pass_through(const ata_cmd_in & in, ata_cmd_out & out);
128
129 private:
130 int m_passthrulen;
131 };
132
133
134 sat_device::sat_device(smart_interface * intf, scsi_device * scsidev,
135 const char * req_type, int passthrulen /*= 0*/)
136 : smart_device(intf, scsidev->get_dev_name(), "sat", req_type),
137 tunnelled_device<ata_device, scsi_device>(scsidev),
138 m_passthrulen(passthrulen)
139 {
140 set_info().info_name = strprintf("%s [SAT]", scsidev->get_info_name());
141 }
142
143 sat_device::~sat_device() throw()
144 {
145 }
146
147
148 // cdb[0]: ATA PASS THROUGH (16) SCSI command opcode byte (0x85)
149 // cdb[1]: multiple_count, protocol + extend
150 // cdb[2]: offline, ck_cond, t_dir, byte_block + t_length
151 // cdb[3]: features (15:8)
152 // cdb[4]: features (7:0)
153 // cdb[5]: sector_count (15:8)
154 // cdb[6]: sector_count (7:0)
155 // cdb[7]: lba_low (15:8)
156 // cdb[8]: lba_low (7:0)
157 // cdb[9]: lba_mid (15:8)
158 // cdb[10]: lba_mid (7:0)
159 // cdb[11]: lba_high (15:8)
160 // cdb[12]: lba_high (7:0)
161 // cdb[13]: device
162 // cdb[14]: (ata) command
163 // cdb[15]: control (SCSI, leave as zero)
164 //
165 // 24 bit lba (from MSB): cdb[12] cdb[10] cdb[8]
166 // 48 bit lba (from MSB): cdb[11] cdb[9] cdb[7] cdb[12] cdb[10] cdb[8]
167 //
168 //
169 // cdb[0]: ATA PASS THROUGH (12) SCSI command opcode byte (0xa1)
170 // cdb[1]: multiple_count, protocol + extend
171 // cdb[2]: offline, ck_cond, t_dir, byte_block + t_length
172 // cdb[3]: features (7:0)
173 // cdb[4]: sector_count (7:0)
174 // cdb[5]: lba_low (7:0)
175 // cdb[6]: lba_mid (7:0)
176 // cdb[7]: lba_high (7:0)
177 // cdb[8]: device
178 // cdb[9]: (ata) command
179 // cdb[10]: reserved
180 // cdb[11]: control (SCSI, leave as zero)
181 //
182 //
183 // ATA Return Descriptor (component of descriptor sense data)
184 // des[0]: descriptor code (0x9)
185 // des[1]: additional descriptor length (0xc)
186 // des[2]: extend (bit 0)
187 // des[3]: error
188 // des[4]: sector_count (15:8)
189 // des[5]: sector_count (7:0)
190 // des[6]: lba_low (15:8)
191 // des[7]: lba_low (7:0)
192 // des[8]: lba_mid (15:8)
193 // des[9]: lba_mid (7:0)
194 // des[10]: lba_high (15:8)
195 // des[11]: lba_high (7:0)
196 // des[12]: device
197 // des[13]: status
198
199
200
201 // PURPOSE
202 // This interface routine takes ATA SMART commands and packages
203 // them in the SAT-defined ATA PASS THROUGH SCSI commands. There are
204 // two available SCSI commands: a 12 byte and 16 byte variant; the
205 // one used is chosen via this->m_passthrulen .
206 // DETAILED DESCRIPTION OF ARGUMENTS
207 // device: is the file descriptor provided by (a SCSI dvice type) open()
208 // command: defines the different ATA operations.
209 // select: additional input data if needed (which log, which type of
210 // self-test).
211 // data: location to write output data, if needed (512 bytes).
212 // Note: not all commands use all arguments.
213 // RETURN VALUES
214 // -1 if the command failed
215 // 0 if the command succeeded,
216 // STATUS_CHECK routine:
217 // -1 if the command failed
218 // 0 if the command succeeded and disk SMART status is "OK"
219 // 1 if the command succeeded and disk SMART status is "FAILING"
220
221 bool sat_device::ata_pass_through(const ata_cmd_in & in, ata_cmd_out & out)
222 {
223 if (!ata_cmd_is_ok(in,
224 true, // data_out_support
225 true, // multi_sector_support
226 true) // ata_48bit_support
227 )
228 return false;
229
230 struct scsi_cmnd_io io_hdr;
231 struct scsi_sense_disect sinfo;
232 struct sg_scsi_sense_hdr ssh;
233 unsigned char cdb[SAT_ATA_PASSTHROUGH_16LEN];
234 unsigned char sense[32];
235 const unsigned char * ardp;
236 int status, ard_len, have_sense;
237 int extend = 0;
238 int ck_cond = 0; /* set to 1 to read register(s) back */
239 int protocol = 3; /* non-data */
240 int t_dir = 1; /* 0 -> to device, 1 -> from device */
241 int byte_block = 1; /* 0 -> bytes, 1 -> 512 byte blocks */
242 int t_length = 0; /* 0 -> no data transferred */
243 int passthru_size = DEF_SAT_ATA_PASSTHRU_SIZE;
244
245 memset(cdb, 0, sizeof(cdb));
246 memset(sense, 0, sizeof(sense));
247
248 // Set data direction
249 // TODO: This works only for commands where sector_count holds count!
250 switch (in.direction) {
251 case ata_cmd_in::no_data:
252 break;
253 case ata_cmd_in::data_in:
254 protocol = 4; // PIO data-in
255 t_length = 2; // sector_count holds count
256 break;
257 case ata_cmd_in::data_out:
258 protocol = 5; // PIO data-out
259 t_length = 2; // sector_count holds count
260 t_dir = 0; // to device
261 break;
262 default:
263 return set_err(EINVAL, "sat_device::ata_pass_through: invalid direction=%d",
264 (int)in.direction);
265 }
266
267 // Check condition if any output register needed
268 if (in.out_needed.is_set())
269 ck_cond = 1;
270
271 if ((SAT_ATA_PASSTHROUGH_12LEN == m_passthrulen) ||
272 (SAT_ATA_PASSTHROUGH_16LEN == m_passthrulen))
273 passthru_size = m_passthrulen;
274
275 // Set extend bit on 48-bit ATA command
276 if (in.in_regs.is_48bit_cmd()) {
277 if (passthru_size != SAT_ATA_PASSTHROUGH_16LEN)
278 return set_err(ENOSYS, "48-bit ATA commands require SAT ATA PASS-THROUGH (16)");
279 extend = 1;
280 }
281
282 cdb[0] = (SAT_ATA_PASSTHROUGH_12LEN == passthru_size) ?
283 SAT_ATA_PASSTHROUGH_12 : SAT_ATA_PASSTHROUGH_16;
284
285 cdb[1] = (protocol << 1) | extend;
286 cdb[2] = (ck_cond << 5) | (t_dir << 3) |
287 (byte_block << 2) | t_length;
288
289 if (passthru_size == SAT_ATA_PASSTHROUGH_12LEN) {
290 // ATA PASS-THROUGH (12)
291 const ata_in_regs & lo = in.in_regs;
292 cdb[3] = lo.features;
293 cdb[4] = lo.sector_count;
294 cdb[5] = lo.lba_low;
295 cdb[6] = lo.lba_mid;
296 cdb[7] = lo.lba_high;
297 cdb[8] = lo.device;
298 cdb[9] = lo.command;
299 }
300 else {
301 // ATA PASS-THROUGH (16)
302 const ata_in_regs & lo = in.in_regs;
303 const ata_in_regs & hi = in.in_regs.prev;
304 // Note: all 'in.in_regs.prev.*' are always zero for 28-bit commands
305 cdb[ 3] = hi.features;
306 cdb[ 4] = lo.features;
307 cdb[ 5] = hi.sector_count;
308 cdb[ 6] = lo.sector_count;
309 cdb[ 7] = hi.lba_low;
310 cdb[ 8] = lo.lba_low;
311 cdb[ 9] = hi.lba_mid;
312 cdb[10] = lo.lba_mid;
313 cdb[11] = hi.lba_high;
314 cdb[12] = lo.lba_high;
315 cdb[13] = lo.device;
316 cdb[14] = lo.command;
317 }
318
319 memset(&io_hdr, 0, sizeof(io_hdr));
320 if (0 == t_length) {
321 io_hdr.dxfer_dir = DXFER_NONE;
322 io_hdr.dxfer_len = 0;
323 } else if (t_dir) { /* from device */
324 io_hdr.dxfer_dir = DXFER_FROM_DEVICE;
325 io_hdr.dxfer_len = in.size;
326 io_hdr.dxferp = (unsigned char *)in.buffer;
327 memset(in.buffer, 0, in.size); // prefill with zeroes
328 } else { /* to device */
329 io_hdr.dxfer_dir = DXFER_TO_DEVICE;
330 io_hdr.dxfer_len = in.size;
331 io_hdr.dxferp = (unsigned char *)in.buffer;
332 }
333 io_hdr.cmnd = cdb;
334 io_hdr.cmnd_len = passthru_size;
335 io_hdr.sensep = sense;
336 io_hdr.max_sense_len = sizeof(sense);
337 io_hdr.timeout = SCSI_TIMEOUT_DEFAULT;
338
339 scsi_device * scsidev = get_tunnel_dev();
340 if (!scsidev->scsi_pass_through(&io_hdr)) {
341 if (con->reportscsiioctl > 0)
342 pout("sat_device::ata_pass_through: scsi_pass_through() failed, "
343 "errno=%d [%s]\n", scsidev->get_errno(), scsidev->get_errmsg());
344 return set_err(scsidev->get_err());
345 }
346 ardp = NULL;
347 ard_len = 0;
348 have_sense = sg_scsi_normalize_sense(io_hdr.sensep, io_hdr.resp_sense_len,
349 &ssh);
350 if (have_sense) {
351 /* look for SAT ATA Return Descriptor */
352 ardp = sg_scsi_sense_desc_find(io_hdr.sensep,
353 io_hdr.resp_sense_len,
354 ATA_RETURN_DESCRIPTOR);
355 if (ardp) {
356 ard_len = ardp[1] + 2;
357 if (ard_len < 12)
358 ard_len = 12;
359 else if (ard_len > 14)
360 ard_len = 14;
361 }
362 scsi_do_sense_disect(&io_hdr, &sinfo);
363 status = scsiSimpleSenseFilter(&sinfo);
364 if (0 != status) {
365 if (con->reportscsiioctl > 0) {
366 pout("sat_device::ata_pass_through: scsi error: %s\n",
367 scsiErrString(status));
368 if (ardp && (con->reportscsiioctl > 1)) {
369 pout("Values from ATA Return Descriptor are:\n");
370 dStrHex((const char *)ardp, ard_len, 1);
371 }
372 }
373 if (t_dir && (t_length > 0) && (in.direction == ata_cmd_in::data_in))
374 memset(in.buffer, 0, in.size);
375 return set_err(EIO, "scsi error %s", scsiErrString(status));
376 }
377 }
378 if (ck_cond) { /* expecting SAT specific sense data */
379 if (have_sense) {
380 if (ardp) {
381 if (con->reportscsiioctl > 1) {
382 pout("Values from ATA Return Descriptor are:\n");
383 dStrHex((const char *)ardp, ard_len, 1);
384 }
385 // Set output registers
386 ata_out_regs & lo = out.out_regs;
387 lo.error = ardp[ 3];
388 lo.sector_count = ardp[ 5];
389 lo.lba_low = ardp[ 7];
390 lo.lba_mid = ardp[ 9];
391 lo.lba_high = ardp[11];
392 lo.device = ardp[12];
393 lo.status = ardp[13];
394 if (in.in_regs.is_48bit_cmd()) {
395 ata_out_regs & hi = out.out_regs.prev;
396 hi.sector_count = ardp[ 4];
397 hi.lba_low = ardp[ 6];
398 hi.lba_mid = ardp[ 8];
399 hi.lba_high = ardp[10];
400 }
401 }
402 }
403 if (ardp == NULL)
404 ck_cond = 0; /* not the type of sense data expected */
405 }
406 if (0 == ck_cond) {
407 if (have_sense) {
408 if ((ssh.response_code >= 0x72) &&
409 ((SCSI_SK_NO_SENSE == ssh.sense_key) ||
410 (SCSI_SK_RECOVERED_ERR == ssh.sense_key)) &&
411 (0 == ssh.asc) &&
412 (SCSI_ASCQ_ATA_PASS_THROUGH == ssh.ascq)) {
413 if (ardp) {
414 if (con->reportscsiioctl > 0) {
415 pout("Values from ATA Return Descriptor are:\n");
416 dStrHex((const char *)ardp, ard_len, 1);
417 }
418 return set_err(EIO, "SAT command failed");
419 }
420 }
421 }
422 }
423 return true;
424 }
425
426 } // namespace
427
428 /////////////////////////////////////////////////////////////////////////////
429
430 /* Attempt an IDENTIFY DEVICE ATA command via SATL when packet_interface
431 is false otherwise attempt IDENTIFY PACKET DEVICE. If successful
432 return true, else false */
433
434 static bool has_sat_pass_through(ata_device * dev, bool packet_interface = false)
435 {
436 /* Note: malloc() ensures the read buffer lands on a single
437 page. This avoids some bugs seen on LSI controlers under
438 FreeBSD */
439 char *data = (char *)malloc(512);
440 ata_cmd_in in;
441 in.in_regs.command = (packet_interface ? ATA_IDENTIFY_PACKET_DEVICE : ATA_IDENTIFY_DEVICE);
442 in.set_data_in(data, 1);
443 bool ret = dev->ata_pass_through(in);
444 free(data);
445 return ret;
446 }
447
448 /////////////////////////////////////////////////////////////////////////////
449
450 /* Next two functions are borrowed from sg_lib.c in the sg3_utils
451 package. Same copyrght owner, same license as this file. */
452 static int sg_scsi_normalize_sense(const unsigned char * sensep, int sb_len,
453 struct sg_scsi_sense_hdr * sshp)
454 {
455 if (sshp)
456 memset(sshp, 0, sizeof(struct sg_scsi_sense_hdr));
457 if ((NULL == sensep) || (0 == sb_len) || (0x70 != (0x70 & sensep[0])))
458 return 0;
459 if (sshp) {
460 sshp->response_code = (0x7f & sensep[0]);
461 if (sshp->response_code >= 0x72) { /* descriptor format */
462 if (sb_len > 1)
463 sshp->sense_key = (0xf & sensep[1]);
464 if (sb_len > 2)
465 sshp->asc = sensep[2];
466 if (sb_len > 3)
467 sshp->ascq = sensep[3];
468 if (sb_len > 7)
469 sshp->additional_length = sensep[7];
470 } else { /* fixed format */
471 if (sb_len > 2)
472 sshp->sense_key = (0xf & sensep[2]);
473 if (sb_len > 7) {
474 sb_len = (sb_len < (sensep[7] + 8)) ? sb_len :
475 (sensep[7] + 8);
476 if (sb_len > 12)
477 sshp->asc = sensep[12];
478 if (sb_len > 13)
479 sshp->ascq = sensep[13];
480 }
481 }
482 }
483 return 1;
484 }
485
486
487 static const unsigned char * sg_scsi_sense_desc_find(const unsigned char * sensep,
488 int sense_len, int desc_type)
489 {
490 int add_sen_len, add_len, desc_len, k;
491 const unsigned char * descp;
492
493 if ((sense_len < 8) || (0 == (add_sen_len = sensep[7])))
494 return NULL;
495 if ((sensep[0] < 0x72) || (sensep[0] > 0x73))
496 return NULL;
497 add_sen_len = (add_sen_len < (sense_len - 8)) ?
498 add_sen_len : (sense_len - 8);
499 descp = &sensep[8];
500 for (desc_len = 0, k = 0; k < add_sen_len; k += desc_len) {
501 descp += desc_len;
502 add_len = (k < (add_sen_len - 1)) ? descp[1]: -1;
503 desc_len = add_len + 2;
504 if (descp[0] == desc_type)
505 return descp;
506 if (add_len < 0) /* short descriptor ?? */
507 break;
508 }
509 return NULL;
510 }
511
512
513 // Call scsi_pass_through and check sense.
514 // TODO: Provide as member function of class scsi_device (?)
515 static bool scsi_pass_through_and_check(scsi_device * scsidev, scsi_cmnd_io * iop,
516 const char * msg = "")
517 {
518 // Provide sense buffer
519 unsigned char sense[32] = {0, };
520 iop->sensep = sense;
521 iop->max_sense_len = sizeof(sense);
522 iop->timeout = SCSI_TIMEOUT_DEFAULT;
523
524 // Run cmd
525 if (!scsidev->scsi_pass_through(iop)) {
526 if (con->reportscsiioctl > 0)
527 pout("%sscsi_pass_through() failed, errno=%d [%s]\n",
528 msg, scsidev->get_errno(), scsidev->get_errmsg());
529 return false;
530 }
531
532 // Check sense
533 scsi_sense_disect sinfo;
534 scsi_do_sense_disect(iop, &sinfo);
535 int err = scsiSimpleSenseFilter(&sinfo);
536 if (err) {
537 if (con->reportscsiioctl > 0)
538 pout("%sscsi error: %s\n", msg, scsiErrString(err));
539 return scsidev->set_err(EIO, "scsi error %s", scsiErrString(err));
540 }
541
542 return true;
543 }
544
545
546 /////////////////////////////////////////////////////////////////////////////
547
548 namespace sat {
549
550 /// Cypress USB Brigde support.
551
552 class usbcypress_device
553 : public tunnelled_device<
554 /*implements*/ ata_device_with_command_set
555 /*by tunnelling through a*/, scsi_device
556 >
557 {
558 public:
559 usbcypress_device(smart_interface * intf, scsi_device * scsidev,
560 const char * req_type, unsigned char signature);
561
562 virtual ~usbcypress_device() throw();
563
564 protected:
565 virtual int ata_command_interface(smart_command_set command, int select, char * data);
566
567 unsigned char m_signature;
568 };
569
570
571 usbcypress_device::usbcypress_device(smart_interface * intf, scsi_device * scsidev,
572 const char * req_type, unsigned char signature)
573 : smart_device(intf, scsidev->get_dev_name(), "sat", req_type),
574 tunnelled_device<ata_device_with_command_set, scsi_device>(scsidev),
575 m_signature(signature)
576 {
577 set_info().info_name = strprintf("%s [USB Cypress]", scsidev->get_info_name());
578 }
579
580 usbcypress_device::~usbcypress_device() throw()
581 {
582 }
583
584
585 /* see cy7c68300c_8.pdf for more information */
586 #define USBCYPRESS_PASSTHROUGH_LEN 16
587 int usbcypress_device::ata_command_interface(smart_command_set command, int select, char *data)
588 {
589 struct scsi_cmnd_io io_hdr;
590 unsigned char cdb[USBCYPRESS_PASSTHROUGH_LEN];
591 unsigned char sense[32];
592 int copydata = 0;
593 int outlen = 0;
594 int ck_cond = 0; /* set to 1 to read register(s) back */
595 int protocol = 3; /* non-data */
596 int t_dir = 1; /* 0 -> to device, 1 -> from device */
597 int byte_block = 1; /* 0 -> bytes, 1 -> 512 byte blocks */
598 int t_length = 0; /* 0 -> no data transferred */
599 int feature = 0;
600 int ata_command = 0;
601 int sector_count = 0;
602 int lba_low = 0;
603 int lba_mid = 0;
604 int lba_high = 0;
605 int passthru_size = USBCYPRESS_PASSTHROUGH_LEN;
606
607 memset(cdb, 0, sizeof(cdb));
608 memset(sense, 0, sizeof(sense));
609
610 ata_command = ATA_SMART_CMD;
611 switch (command) {
612 case CHECK_POWER_MODE:
613 ata_command = ATA_CHECK_POWER_MODE;
614 ck_cond = 1;
615 copydata = 1;
616 break;
617 case READ_VALUES: /* READ DATA */
618 feature = ATA_SMART_READ_VALUES;
619 sector_count = 1; /* one (512 byte) block */
620 protocol = 4; /* PIO data-in */
621 t_length = 2; /* sector count holds count */
622 copydata = 512;
623 break;
624 case READ_THRESHOLDS: /* obsolete */
625 feature = ATA_SMART_READ_THRESHOLDS;
626 sector_count = 1; /* one (512 byte) block */
627 lba_low = 1;
628 protocol = 4; /* PIO data-in */
629 t_length = 2; /* sector count holds count */
630 copydata=512;
631 break;
632 case READ_LOG:
633 feature = ATA_SMART_READ_LOG_SECTOR;
634 sector_count = 1; /* one (512 byte) block */
635 lba_low = select;
636 protocol = 4; /* PIO data-in */
637 t_length = 2; /* sector count holds count */
638 copydata = 512;
639 break;
640 case WRITE_LOG:
641 feature = ATA_SMART_WRITE_LOG_SECTOR;
642 sector_count = 1; /* one (512 byte) block */
643 lba_low = select;
644 protocol = 5; /* PIO data-out */
645 t_length = 2; /* sector count holds count */
646 t_dir = 0; /* to device */
647 outlen = 512;
648 break;
649 case IDENTIFY:
650 ata_command = ATA_IDENTIFY_DEVICE;
651 sector_count = 1; /* one (512 byte) block */
652 protocol = 4; /* PIO data-in */
653 t_length = 2; /* sector count holds count */
654 copydata = 512;
655 break;
656 case PIDENTIFY:
657 ata_command = ATA_IDENTIFY_PACKET_DEVICE;
658 sector_count = 1; /* one (512 byte) block */
659 protocol = 4; /* PIO data-in */
660 t_length = 2; /* sector count (7:0) holds count */
661 copydata = 512;
662 break;
663 case ENABLE:
664 feature = ATA_SMART_ENABLE;
665 lba_low = 1;
666 break;
667 case DISABLE:
668 feature = ATA_SMART_DISABLE;
669 lba_low = 1;
670 break;
671 case STATUS:
672 // this command only says if SMART is working. It could be
673 // replaced with STATUS_CHECK below.
674 feature = ATA_SMART_STATUS;
675 ck_cond = 1;
676 break;
677 case AUTO_OFFLINE:
678 feature = ATA_SMART_AUTO_OFFLINE;
679 sector_count = select; // YET NOTE - THIS IS A NON-DATA COMMAND!!
680 break;
681 case AUTOSAVE:
682 feature = ATA_SMART_AUTOSAVE;
683 sector_count = select; // YET NOTE - THIS IS A NON-DATA COMMAND!!
684 break;
685 case IMMEDIATE_OFFLINE:
686 feature = ATA_SMART_IMMEDIATE_OFFLINE;
687 lba_low = select;
688 break;
689 case STATUS_CHECK:
690 // This command uses HDIO_DRIVE_TASK and has different syntax than
691 // the other commands.
692 feature = ATA_SMART_STATUS; /* SMART RETURN STATUS */
693 ck_cond = 1;
694 break;
695 default:
696 pout("Unrecognized command %d in usbcypress_device::ata_command_interface()\n"
697 "Please contact " PACKAGE_BUGREPORT "\n", command);
698 errno=ENOSYS;
699 return -1;
700 }
701 if (ATA_SMART_CMD == ata_command) {
702 lba_mid = 0x4f;
703 lba_high = 0xc2;
704 }
705
706 cdb[0] = m_signature; // bVSCBSignature : vendor-specific command
707 cdb[1] = 0x24; // bVSCBSubCommand : 0x24 for ATACB
708 cdb[2] = 0x0;
709 if (ata_command == ATA_IDENTIFY_DEVICE || ata_command == ATA_IDENTIFY_PACKET_DEVICE)
710 cdb[2] |= (1<<7); //set IdentifyPacketDevice for these cmds
711 cdb[3] = 0xff - (1<<0) - (1<<6); //features, sector count, lba low, lba med
712 // lba high, command are valid
713 cdb[4] = byte_block; //TransferBlockCount : 512
714
715
716 cdb[6] = feature;
717 cdb[7] = sector_count;
718 cdb[8] = lba_low;
719 cdb[9] = lba_mid;
720 cdb[10] = lba_high;
721 cdb[12] = ata_command;
722
723 memset(&io_hdr, 0, sizeof(io_hdr));
724 if (0 == t_length) {
725 io_hdr.dxfer_dir = DXFER_NONE;
726 io_hdr.dxfer_len = 0;
727 } else if (t_dir) { /* from device */
728 io_hdr.dxfer_dir = DXFER_FROM_DEVICE;
729 io_hdr.dxfer_len = copydata;
730 io_hdr.dxferp = (unsigned char *)data;
731 memset(data, 0, copydata); /* prefill with zeroes */
732 } else { /* to device */
733 io_hdr.dxfer_dir = DXFER_TO_DEVICE;
734 io_hdr.dxfer_len = outlen;
735 io_hdr.dxferp = (unsigned char *)data;
736 }
737 io_hdr.cmnd = cdb;
738 io_hdr.cmnd_len = passthru_size;
739 io_hdr.sensep = sense;
740 io_hdr.max_sense_len = sizeof(sense);
741 io_hdr.timeout = SCSI_TIMEOUT_DEFAULT;
742
743 scsi_device * scsidev = get_tunnel_dev();
744 if (!scsidev->scsi_pass_through(&io_hdr)) {
745 if (con->reportscsiioctl > 0)
746 pout("usbcypress_device::ata_command_interface: scsi_pass_through() failed, "
747 "errno=%d [%s]\n", scsidev->get_errno(), scsidev->get_errmsg());
748 set_err(scsidev->get_err());
749 return -1;
750 }
751
752 // if there is a sense the command failed or the
753 // device doesn't support usbcypress
754 if (io_hdr.scsi_status == SCSI_STATUS_CHECK_CONDITION &&
755 sg_scsi_normalize_sense(io_hdr.sensep, io_hdr.resp_sense_len, NULL)) {
756 return -1;
757 }
758 if (ck_cond) {
759 unsigned char ardp[8];
760 int ard_len = 8;
761 /* XXX this is racy if there other scsi command between
762 * the first usbcypress command and this one
763 */
764 //pout("If you got strange result, please retry without traffic on the disc\n");
765 /* we use the same command as before, but we set
766 * * the read taskfile bit, for not executing usbcypress command,
767 * * but reading register selected in srb->cmnd[4]
768 */
769 cdb[2] = (1<<0); /* ask read taskfile */
770 memset(sense, 0, sizeof(sense));
771
772 /* transfert 8 bytes */
773 memset(&io_hdr, 0, sizeof(io_hdr));
774 io_hdr.dxfer_dir = DXFER_FROM_DEVICE;
775 io_hdr.dxfer_len = ard_len;
776 io_hdr.dxferp = (unsigned char *)ardp;
777 memset(ardp, 0, ard_len); /* prefill with zeroes */
778
779 io_hdr.cmnd = cdb;
780 io_hdr.cmnd_len = passthru_size;
781 io_hdr.sensep = sense;
782 io_hdr.max_sense_len = sizeof(sense);
783 io_hdr.timeout = SCSI_TIMEOUT_DEFAULT;
784
785
786 if (!scsidev->scsi_pass_through(&io_hdr)) {
787 if (con->reportscsiioctl > 0)
788 pout("usbcypress_device::ata_command_interface: scsi_pass_through() failed, "
789 "errno=%d [%s]\n", scsidev->get_errno(), scsidev->get_errmsg());
790 set_err(scsidev->get_err());
791 return -1;
792 }
793 // if there is a sense the command failed or the
794 // device doesn't support usbcypress
795 if (io_hdr.scsi_status == SCSI_STATUS_CHECK_CONDITION &&
796 sg_scsi_normalize_sense(io_hdr.sensep, io_hdr.resp_sense_len, NULL)) {
797 return -1;
798 }
799
800
801 if (con->reportscsiioctl > 1) {
802 pout("Values from ATA Return Descriptor are:\n");
803 dStrHex((const char *)ardp, ard_len, 1);
804 }
805
806 if (ATA_CHECK_POWER_MODE == ata_command)
807 data[0] = ardp[2]; /* sector count (0:7) */
808 else if (STATUS_CHECK == command) {
809 if ((ardp[4] == 0x4f) && (ardp[5] == 0xc2))
810 return 0; /* GOOD smart status */
811 if ((ardp[4] == 0xf4) && (ardp[5] == 0x2c))
812 return 1; // smart predicting failure, "bad" status
813 // We haven't gotten output that makes sense so
814 // print out some debugging info
815 syserror("Error SMART Status command failed");
816 pout("This may be due to a race in usbcypress\n");
817 pout("Retry without other disc access\n");
818 pout("Please get assistance from " PACKAGE_HOMEPAGE "\n");
819 pout("Values from ATA Return Descriptor are:\n");
820 dStrHex((const char *)ardp, ard_len, 1);
821 return -1;
822 }
823 }
824 return 0;
825 }
826
827 #if 0 // Not used, see autodetect_sat_device() below.
828 static int isprint_string(const char *s)
829 {
830 while (*s) {
831 if (isprint(*s) == 0)
832 return 0;
833 s++;
834 }
835 return 1;
836 }
837
838 /* Attempt an IDENTIFY DEVICE ATA or IDENTIFY PACKET DEVICE command
839 If successful return 1, else 0 */
840 // TODO: Combine with has_sat_pass_through above
841 static int has_usbcypress_pass_through(ata_device * atadev, const char *manufacturer, const char *product)
842 {
843 struct ata_identify_device drive;
844 char model[40], serial[20], firm[8];
845
846 /* issue the command and do a checksum if possible */
847 if (ataReadHDIdentity(atadev, &drive) < 0)
848 return 0;
849
850 /* check if model string match, revision doesn't work for me */
851 format_ata_string(model, drive.model, 40);
852 if (*model == 0 || isprint_string(model) == 0)
853 return 0;
854
855 if (manufacturer && strncmp(manufacturer, model, 8))
856 pout("manufacturer doesn't match in pass_through test\n");
857 if (product &&
858 strlen(model) > 8 && strncmp(product, model+8, strlen(model)-8))
859 pout("product doesn't match in pass_through test\n");
860
861 /* check serial */
862 format_ata_string(serial, drive.serial_no, 20);
863 if (isprint_string(serial) == 0)
864 return 0;
865 format_ata_string(firm, drive.fw_rev, 8);
866 if (isprint_string(firm) == 0)
867 return 0;
868 return 1;
869 }
870 #endif
871
872 /////////////////////////////////////////////////////////////////////////////
873
874 /// JMicron USB Bridge support.
875
876 class usbjmicron_device
877 : public tunnelled_device<
878 /*implements*/ ata_device,
879 /*by tunnelling through a*/ scsi_device
880 >
881 {
882 public:
883 usbjmicron_device(smart_interface * intf, scsi_device * scsidev,
884 const char * req_type, bool ata_48bit_support, int port);
885
886 virtual ~usbjmicron_device() throw();
887
888 virtual bool open();
889
890 virtual bool ata_pass_through(const ata_cmd_in & in, ata_cmd_out & out);
891
892 private:
893 bool get_registers(unsigned short addr, unsigned char * buf, unsigned short size);
894
895 bool m_ata_48bit_support;
896 int m_port;
897 };
898
899
900 usbjmicron_device::usbjmicron_device(smart_interface * intf, scsi_device * scsidev,
901 const char * req_type, bool ata_48bit_support, int port)
902 : smart_device(intf, scsidev->get_dev_name(), "usbjmicron", req_type),
903 tunnelled_device<ata_device, scsi_device>(scsidev),
904 m_ata_48bit_support(ata_48bit_support), m_port(port)
905 {
906 set_info().info_name = strprintf("%s [USB JMicron]", scsidev->get_info_name());
907 }
908
909 usbjmicron_device::~usbjmicron_device() throw()
910 {
911 }
912
913
914 bool usbjmicron_device::open()
915 {
916 // Open USB first
917 if (!tunnelled_device<ata_device, scsi_device>::open())
918 return false;
919
920 // Detect port if not specified
921 if (m_port < 0) {
922 unsigned char regbuf[1] = {0};
923 if (!get_registers(0x720f, regbuf, sizeof(regbuf))) {
924 close();
925 return false;
926 }
927
928 switch (regbuf[0] & 0x44) {
929 case 0x04:
930 m_port = 0; break;
931 case 0x40:
932 m_port = 1; break;
933 case 0x44:
934 close();
935 return set_err(EINVAL, "Two devices connected, try '-d usbjmicron,[01]'");
936 default:
937 close();
938 return set_err(ENODEV, "No device connected");
939 }
940 }
941
942 return true;
943 }
944
945
946 bool usbjmicron_device::ata_pass_through(const ata_cmd_in & in, ata_cmd_out & out)
947 {
948 if (!ata_cmd_is_ok(in,
949 true, // data_out_support
950 false, // !multi_sector_support
951 m_ata_48bit_support) // limited, see below
952 )
953 return false;
954
955 bool is_smart_status = ( in.in_regs.command == ATA_SMART_CMD
956 && in.in_regs.features == ATA_SMART_STATUS);
957
958 // Support output registers for SMART STATUS
959 if (in.out_needed.is_set() && !is_smart_status)
960 return set_err(ENOSYS, "ATA output registers not supported");
961
962 // Support 48-bit commands with zero high bytes
963 if (in.in_regs.is_real_48bit_cmd())
964 return set_err(ENOSYS, "48-bit ATA commands not fully supported");
965
966 if (m_port < 0)
967 return set_err(EIO, "Unknown JMicron port");
968
969 scsi_cmnd_io io_hdr;
970 memset(&io_hdr, 0, sizeof(io_hdr));
971
972 bool rwbit = true;
973 unsigned char smart_status = 0;
974
975 if (is_smart_status && in.out_needed.is_set()) {
976 io_hdr.dxfer_dir = DXFER_FROM_DEVICE;
977 io_hdr.dxfer_len = 1;
978 io_hdr.dxferp = &smart_status;
979 }
980 else switch (in.direction) {
981 case ata_cmd_in::no_data:
982 io_hdr.dxfer_dir = DXFER_NONE;
983 break;
984 case ata_cmd_in::data_in:
985 io_hdr.dxfer_dir = DXFER_FROM_DEVICE;
986 io_hdr.dxfer_len = in.size;
987 io_hdr.dxferp = (unsigned char *)in.buffer;
988 memset(in.buffer, 0, in.size);
989 break;
990 case ata_cmd_in::data_out:
991 io_hdr.dxfer_dir = DXFER_TO_DEVICE;
992 io_hdr.dxfer_len = in.size;
993 io_hdr.dxferp = (unsigned char *)in.buffer;
994 rwbit = false;
995 break;
996 default:
997 return set_err(EINVAL);
998 }
999
1000 // Build pass through command
1001 unsigned char cdb[12];
1002 cdb[ 0] = 0xdf;
1003 cdb[ 1] = (rwbit ? 0x10 : 0x00);
1004 cdb[ 2] = 0x00;
1005 cdb[ 3] = (unsigned char)(io_hdr.dxfer_len >> 8);
1006 cdb[ 4] = (unsigned char)(io_hdr.dxfer_len );
1007 cdb[ 5] = in.in_regs.features;
1008 cdb[ 6] = in.in_regs.sector_count;
1009 cdb[ 7] = in.in_regs.lba_low;
1010 cdb[ 8] = in.in_regs.lba_mid;
1011 cdb[ 9] = in.in_regs.lba_high;
1012 cdb[10] = in.in_regs.device | (m_port == 0 ? 0xa0 : 0xb0);
1013 cdb[11] = in.in_regs.command;
1014
1015 io_hdr.cmnd = cdb;
1016 io_hdr.cmnd_len = sizeof(cdb);
1017
1018 scsi_device * scsidev = get_tunnel_dev();
1019 if (!scsi_pass_through_and_check(scsidev, &io_hdr,
1020 "usbjmicron_device::ata_pass_through: "))
1021 return set_err(scsidev->get_err());
1022
1023 if (in.out_needed.is_set()) {
1024 if (is_smart_status) {
1025 switch (smart_status) {
1026 case 0x01: case 0xc2:
1027 out.out_regs.lba_high = 0xc2;
1028 out.out_regs.lba_mid = 0x4f;
1029 break;
1030 case 0x00: case 0x2c:
1031 out.out_regs.lba_high = 0x2c;
1032 out.out_regs.lba_mid = 0xf4;
1033 break;
1034 }
1035 }
1036
1037 #if 0 // Not needed for SMART STATUS, see also notes below
1038 else {
1039 // Read ATA output registers
1040 // NOTE: The register addresses are not valid for some older chip revisions
1041 // NOTE: There is a small race condition here!
1042 unsigned char regbuf[16] = {0, };
1043 if (!get_registers((m_port == 0 ? 0x8000 : 0x9000), regbuf, sizeof(regbuf)))
1044 return false;
1045
1046 out.out_regs.sector_count = regbuf[ 0];
1047 out.out_regs.lba_mid = regbuf[ 4];
1048 out.out_regs.lba_low = regbuf[ 6];
1049 out.out_regs.device = regbuf[ 9];
1050 out.out_regs.lba_high = regbuf[10];
1051 out.out_regs.error = regbuf[13];
1052 out.out_regs.status = regbuf[14];
1053 }
1054 #endif
1055 }
1056
1057 return true;
1058 }
1059
1060 bool usbjmicron_device::get_registers(unsigned short addr,
1061 unsigned char * buf, unsigned short size)
1062 {
1063 unsigned char cdb[12];
1064 cdb[ 0] = 0xdf;
1065 cdb[ 1] = 0x10;
1066 cdb[ 2] = 0x00;
1067 cdb[ 3] = (unsigned char)(size >> 8);
1068 cdb[ 4] = (unsigned char)(size );
1069 cdb[ 5] = 0x00;
1070 cdb[ 6] = (unsigned char)(addr >> 8);
1071 cdb[ 7] = (unsigned char)(addr );
1072 cdb[ 8] = 0x00;
1073 cdb[ 9] = 0x00;
1074 cdb[10] = 0x00;
1075 cdb[11] = 0xfd;
1076
1077 scsi_cmnd_io io_hdr;
1078 memset(&io_hdr, 0, sizeof(io_hdr));
1079 io_hdr.dxfer_dir = DXFER_FROM_DEVICE;
1080 io_hdr.dxfer_len = size;
1081 io_hdr.dxferp = buf;
1082 io_hdr.cmnd = cdb;
1083 io_hdr.cmnd_len = sizeof(cdb);
1084
1085 scsi_device * scsidev = get_tunnel_dev();
1086 if (!scsi_pass_through_and_check(scsidev, &io_hdr,
1087 "usbjmicron_device::get_registers: "))
1088 return set_err(scsidev->get_err());
1089
1090 return true;
1091 }
1092
1093
1094 /////////////////////////////////////////////////////////////////////////////
1095
1096 /// SunplusIT USB Bridge support.
1097
1098 class usbsunplus_device
1099 : public tunnelled_device<
1100 /*implements*/ ata_device,
1101 /*by tunnelling through a*/ scsi_device
1102 >
1103 {
1104 public:
1105 usbsunplus_device(smart_interface * intf, scsi_device * scsidev,
1106 const char * req_type);
1107
1108 virtual ~usbsunplus_device() throw();
1109
1110 virtual bool ata_pass_through(const ata_cmd_in & in, ata_cmd_out & out);
1111 };
1112
1113
1114 usbsunplus_device::usbsunplus_device(smart_interface * intf, scsi_device * scsidev,
1115 const char * req_type)
1116 : smart_device(intf, scsidev->get_dev_name(), "usbsunplus", req_type),
1117 tunnelled_device<ata_device, scsi_device>(scsidev)
1118 {
1119 set_info().info_name = strprintf("%s [USB Sunplus]", scsidev->get_info_name());
1120 }
1121
1122 usbsunplus_device::~usbsunplus_device() throw()
1123 {
1124 }
1125
1126 bool usbsunplus_device::ata_pass_through(const ata_cmd_in & in, ata_cmd_out & out)
1127 {
1128 if (!ata_cmd_is_ok(in,
1129 true, // data_out_support
1130 false, // !multi_sector_support
1131 true) // ata_48bit_support
1132 )
1133 return false;
1134
1135 scsi_cmnd_io io_hdr;
1136 unsigned char cdb[12];
1137
1138 if (in.in_regs.is_48bit_cmd()) {
1139 // Set "previous" registers
1140 memset(&io_hdr, 0, sizeof(io_hdr));
1141 io_hdr.dxfer_dir = DXFER_NONE;
1142
1143 cdb[ 0] = 0xf8;
1144 cdb[ 1] = 0x00;
1145 cdb[ 2] = 0x23; // Subcommand: Pass through presetting
1146 cdb[ 3] = 0x00;
1147 cdb[ 4] = 0x00;
1148 cdb[ 5] = in.in_regs.prev.features;
1149 cdb[ 6] = in.in_regs.prev.sector_count;
1150 cdb[ 7] = in.in_regs.prev.lba_low;
1151 cdb[ 8] = in.in_regs.prev.lba_mid;
1152 cdb[ 9] = in.in_regs.prev.lba_high;
1153 cdb[10] = 0x00;
1154 cdb[11] = 0x00;
1155
1156 io_hdr.cmnd = cdb;
1157 io_hdr.cmnd_len = sizeof(cdb);
1158
1159 scsi_device * scsidev = get_tunnel_dev();
1160 if (!scsi_pass_through_and_check(scsidev, &io_hdr,
1161 "usbsunplus_device::scsi_pass_through (presetting): "))
1162 return set_err(scsidev->get_err());
1163 }
1164
1165 // Run Pass through command
1166 memset(&io_hdr, 0, sizeof(io_hdr));
1167 unsigned char protocol;
1168 switch (in.direction) {
1169 case ata_cmd_in::no_data:
1170 io_hdr.dxfer_dir = DXFER_NONE;
1171 protocol = 0x00;
1172 break;
1173 case ata_cmd_in::data_in:
1174 io_hdr.dxfer_dir = DXFER_FROM_DEVICE;
1175 io_hdr.dxfer_len = in.size;
1176 io_hdr.dxferp = (unsigned char *)in.buffer;
1177 memset(in.buffer, 0, in.size);
1178 protocol = 0x10;
1179 break;
1180 case ata_cmd_in::data_out:
1181 io_hdr.dxfer_dir = DXFER_TO_DEVICE;
1182 io_hdr.dxfer_len = in.size;
1183 io_hdr.dxferp = (unsigned char *)in.buffer;
1184 protocol = 0x11;
1185 break;
1186 default:
1187 return set_err(EINVAL);
1188 }
1189
1190 cdb[ 0] = 0xf8;
1191 cdb[ 1] = 0x00;
1192 cdb[ 2] = 0x22; // Subcommand: Pass through
1193 cdb[ 3] = protocol;
1194 cdb[ 4] = (unsigned char)(io_hdr.dxfer_len >> 9);
1195 cdb[ 5] = in.in_regs.features;
1196 cdb[ 6] = in.in_regs.sector_count;
1197 cdb[ 7] = in.in_regs.lba_low;
1198 cdb[ 8] = in.in_regs.lba_mid;
1199 cdb[ 9] = in.in_regs.lba_high;
1200 cdb[10] = in.in_regs.device | 0xa0;
1201 cdb[11] = in.in_regs.command;
1202
1203 io_hdr.cmnd = cdb;
1204 io_hdr.cmnd_len = sizeof(cdb);
1205
1206 scsi_device * scsidev = get_tunnel_dev();
1207 if (!scsi_pass_through_and_check(scsidev, &io_hdr,
1208 "usbsunplus_device::scsi_pass_through: "))
1209 // Returns sense key 0x03 (medium error) on ATA command error
1210 return set_err(scsidev->get_err());
1211
1212 if (in.out_needed.is_set()) {
1213 // Read ATA output registers
1214 unsigned char regbuf[8] = {0, };
1215 memset(&io_hdr, 0, sizeof(io_hdr));
1216 io_hdr.dxfer_dir = DXFER_FROM_DEVICE;
1217 io_hdr.dxfer_len = sizeof(regbuf);
1218 io_hdr.dxferp = regbuf;
1219
1220 cdb[ 0] = 0xf8;
1221 cdb[ 1] = 0x00;
1222 cdb[ 2] = 0x21; // Subcommand: Get status
1223 memset(cdb+3, 0, sizeof(cdb)-3);
1224 io_hdr.cmnd = cdb;
1225 io_hdr.cmnd_len = sizeof(cdb);
1226
1227 if (!scsi_pass_through_and_check(scsidev, &io_hdr,
1228 "usbsunplus_device::scsi_pass_through (get registers): "))
1229 return set_err(scsidev->get_err());
1230
1231 out.out_regs.error = regbuf[1];
1232 out.out_regs.sector_count = regbuf[2];
1233 out.out_regs.lba_low = regbuf[3];
1234 out.out_regs.lba_mid = regbuf[4];
1235 out.out_regs.lba_high = regbuf[5];
1236 out.out_regs.device = regbuf[6];
1237 out.out_regs.status = regbuf[7];
1238 }
1239
1240 return true;
1241 }
1242
1243
1244 } // namespace
1245
1246 using namespace sat;
1247
1248
1249 /////////////////////////////////////////////////////////////////////////////
1250
1251 // Return ATA->SCSI filter for SAT or USB.
1252
1253 ata_device * smart_interface::get_sat_device(const char * type, scsi_device * scsidev)
1254 {
1255 if (!strncmp(type, "sat", 3)) {
1256 int ptlen = 0, n1 = -1, n2 = -1;
1257 if (!(((sscanf(type, "sat%n,%d%n", &n1, &ptlen, &n2) == 1 && n2 == (int)strlen(type)) || n1 == (int)strlen(type))
1258 && (ptlen == 0 || ptlen == 12 || ptlen == 16))) {
1259 set_err(EINVAL, "Option '-d sat,<n>' requires <n> to be 0, 12 or 16");
1260 return 0;
1261 }
1262 return new sat_device(this, scsidev, type, ptlen);
1263 }
1264
1265 else if (!strncmp(type, "usbcypress", 10)) {
1266 unsigned signature = 0x24; int n1 = -1, n2 = -1;
1267 if (!(((sscanf(type, "usbcypress%n,0x%x%n", &n1, &signature, &n2) == 1 && n2 == (int)strlen(type)) || n1 == (int)strlen(type))
1268 && signature <= 0xff)) {
1269 set_err(EINVAL, "Option '-d usbcypress,<n>' requires <n> to be "
1270 "an hexadecimal number between 0x0 and 0xff");
1271 return 0;
1272 }
1273 return new usbcypress_device(this, scsidev, type, signature);
1274 }
1275
1276 else if (!strncmp(type, "usbjmicron", 10)) {
1277 const char * t = type + 10;
1278 bool ata_48bit_support = false;
1279 if (!strncmp(t, ",x", 2)) {
1280 t += 2;
1281 ata_48bit_support = true;
1282 }
1283 int port = -1, n = -1;
1284 if (*t && !( (sscanf(t, ",%d%n", &port, &n) == 1
1285 && n == (int)strlen(t) && 0 <= port && port <= 1))) {
1286 set_err(EINVAL, "Option '-d usbmicron[,x],<n>' requires <n> to be 0 or 1");
1287 return 0;
1288 }
1289 return new usbjmicron_device(this, scsidev, type, ata_48bit_support, port);
1290 }
1291
1292 else if (!strcmp(type, "usbsunplus")) {
1293 return new usbsunplus_device(this, scsidev, type);
1294 }
1295
1296 else {
1297 set_err(EINVAL, "Unknown USB device type '%s'", type);
1298 return 0;
1299 }
1300 }
1301
1302 // Try to detect a SAT device behind a SCSI interface.
1303
1304 ata_device * smart_interface::autodetect_sat_device(scsi_device * scsidev,
1305 const unsigned char * inqdata, unsigned inqsize)
1306 {
1307 if (!scsidev->is_open())
1308 return 0;
1309
1310 // SAT ?
1311 if (inqdata && inqsize >= 36 && !memcmp(inqdata + 8, "ATA ", 8)) { // TODO: Linux-specific?
1312 ata_device_auto_ptr atadev( new sat_device(this, scsidev, "") , scsidev);
1313 if (has_sat_pass_through(atadev.get()))
1314 return atadev.release(); // Detected SAT
1315 }
1316
1317 return 0;
1318 }
1319
1320
1321 /////////////////////////////////////////////////////////////////////////////
1322 // USB device type detection
1323
1324 struct usb_id_entry {
1325 int vendor_id, product_id, version;
1326 const char * type;
1327 };
1328
1329 const char d_sat[] = "sat";
1330 const char d_cypress[] = "usbcypress";
1331 const char d_jmicron[] = "usbjmicron";
1332 const char d_jmicron_x[] = "usbjmicron,x";
1333 const char d_sunplus[] = "usbsunplus";
1334 const char d_unsup[] = "unsupported";
1335
1336 // Map USB IDs -> '-d type' string
1337 const usb_id_entry usb_ids[] = {
1338 // Cypress
1339 { 0x04b4, 0x6830, 0x0001, d_unsup }, // Cypress CY7C68300A (AT2)
1340 { 0x04b4, 0x6830, 0x0240, d_cypress }, // Cypress CY7C68300B/C (AT2LP)
1341 //{ 0x04b4, 0x6831, -1, d_cypress }, // Cypress CY7C68310 (ISD-300LP)
1342 // Myson Century
1343 { 0x04cf, 0x8818, 0xb007, d_unsup }, // Myson Century CS8818
1344 // Sunplus
1345 { 0x04fc, 0x0c15, 0xf615, d_sunplus }, // SunPlus SPDIF215
1346 { 0x04fc, 0x0c25, 0x0103, d_sunplus }, // SunPlus SPDIF225 (USB+SATA->SATA)
1347 // Iomega
1348 { 0x059b, 0x0272, -1, d_cypress }, // Iomega LPHD080-0
1349 { 0x059b, 0x0275, 0x0001, d_unsup }, // Iomega MDHD500-U
1350 // LaCie
1351 { 0x059f, 0x0651, -1, d_unsup }, // LaCie hard disk (FA Porsche design)
1352 { 0x059f, 0x1018, -1, d_sat }, // LaCie hard disk (Neil Poulton design)
1353 // In-System Design
1354 { 0x05ab, 0x0060, 0x1101, d_cypress }, // In-System/Cypress ISD-300A1
1355 // Genesys Logic
1356 { 0x05e3, 0x0702, -1, d_unsup }, // Genesys Logic GL881E
1357 { 0x05e3, 0x0718, 0x0041, d_sat }, // Genesys Logic ? (TODO: requires '-T permissive')
1358 // Prolific
1359 { 0x067b, 0x3507, 0x0001, d_unsup }, // Prolific PL3507
1360 // Freecom
1361 { 0x07ab, 0xfc8e, 0x010f, d_sunplus }, // Freecom Hard Drive XS
1362 // Toshiba
1363 { 0x0930, 0x0b09, -1, d_sunplus }, // Toshiba PX1396E-3T01 (similar to Dura Micro 501)
1364 // Seagate
1365 { 0x0bc2, 0x2000, -1, d_sat }, // Seagate FreeAgent Go
1366 { 0x0bc2, 0x2100, -1, d_sat }, // Seagate FreeAgent Go
1367 { 0x0bc2, 0x3001, -1, d_sat }, // Seagate FreeAgent Desk
1368 // Dura Micro
1369 { 0x0c0b, 0xb159, 0x0103, d_sunplus }, // Dura Micro 509
1370 // Maxtor
1371 { 0x0d49, 0x7310, 0x0125, d_sat }, // Maxtor OneTouch 4
1372 { 0x0d49, 0x7350, 0x0125, d_sat }, // Maxtor OneTouch 4 Mini
1373 { 0x0d49, 0x7410, 0x0122, d_sat }, // Maxtor Basics Desktop
1374 { 0x0d49, 0x7450, 0x0122, d_sat }, // Maxtor Basics Portable
1375 // Western Digital
1376 { 0x1058, 0x0702, 0x0104, d_sat }, // WD My Passport Portable
1377 { 0x1058, 0x0704, 0x0175, d_sat }, // WD My Passport Essential
1378 { 0x1058, 0x0705, 0x0175, d_sat }, // WD My Passport Elite
1379 { 0x1058, 0x070a, 0x1028, d_sat }, // WD My Passport 070A
1380 { 0x1058, 0x0906, 0x0012, d_sat }, // WD My Book ES
1381 { 0x1058, 0x1001, 0x0104, d_sat }, // WD Elements Desktop
1382 { 0x1058, 0x1003, 0x0175, d_sat }, // WD Elements Desktop WDE1UBK...
1383 { 0x1058, 0x1010, 0x0105, d_sat }, // WD Elements
1384 { 0x1058, 0x1100, 0x0165, d_sat }, // WD My Book Essential
1385 { 0x1058, 0x1102, 0x1028, d_sat }, // WD My Book
1386 // Initio
1387 { 0x13fd, 0x0540, -1, d_unsup }, // Initio 316000
1388 { 0x13fd, 0x1240, 0x0104, d_sat }, // Initio ? (USB->SATA)
1389 { 0x13fd, 0x1340, 0x0208, d_sat }, // Initio ? (USB+SATA->SATA)
1390 // JMicron
1391 { 0x152d, 0x2329, 0x0100, d_jmicron }, // JMicron JM20329 (USB->SATA)
1392 { 0x152d, 0x2336, 0x0100, d_jmicron_x},// JMicron JM20336 (USB+SATA->SATA, USB->2xSATA)
1393 { 0x152d, 0x2338, 0x0100, d_jmicron }, // JMicron JM20337/8 (USB->SATA+PATA, USB+SATA->PATA)
1394 { 0x152d, 0x2339, 0x0100, d_jmicron_x},// JMicron JM20339 (USB->SATA)
1395 // Verbatim
1396 { 0x18a5, 0x0215, 0x0001, d_sat }, // Verbatim FW/USB160 - Oxford OXUF934SSA-LQAG (USB+IEE1394->SATA)
1397 // SunplusIT
1398 { 0x1bcf, 0x0c31, -1, d_sunplus }, // SunplusIT
1399 // OnSpec
1400 { 0x55aa, 0x2b00, 0x0100, d_unsup } // OnSpec ? (USB->PATA)
1401 };
1402
1403 const unsigned num_usb_ids = sizeof(usb_ids)/sizeof(usb_ids[0]);
1404
1405
1406 // Format USB ID for error messages
1407 static std::string format_usb_id(int vendor_id, int product_id, int version)
1408 {
1409 if (version >= 0)
1410 return strprintf("[0x%04x:0x%04x (0x%03x)]", vendor_id, product_id, version);
1411 else
1412 return strprintf("[0x%04x:0x%04x]", vendor_id, product_id);
1413 }
1414
1415 // Get type name for USB device with known VENDOR:PRODUCT ID.
1416 const char * smart_interface::get_usb_dev_type_by_id(int vendor_id, int product_id,
1417 int version /*= -1*/)
1418 {
1419 const usb_id_entry * entry = 0;
1420 bool state = false;
1421
1422 for (unsigned i = 0; i < num_usb_ids; i++) {
1423 const usb_id_entry & e = usb_ids[i];
1424 if (!(vendor_id == e.vendor_id && product_id == e.product_id))
1425 continue;
1426
1427 // If two entries with same vendor:product ID have different
1428 // types, use version (if provided by OS) to select entry.
1429 bool s = (version >= 0 && version == e.version);
1430 if (entry) {
1431 if (s <= state) {
1432 if (s == state && e.type != entry->type) {
1433 set_err(EINVAL, "USB bridge %s type is ambiguous: '%s' or '%s'",
1434 format_usb_id(vendor_id, product_id, version).c_str(),
1435 e.type, entry->type);
1436 return 0;
1437 }
1438 continue;
1439 }
1440 }
1441 state = s;
1442 entry = &e;
1443 }
1444
1445 if (!entry) {
1446 set_err(EINVAL, "Unknown USB bridge %s",
1447 format_usb_id(vendor_id, product_id, version).c_str());
1448 return 0;
1449 }
1450 if (entry->type == d_unsup) {
1451 set_err(ENOSYS, "Unsupported USB bridge %s",
1452 format_usb_id(vendor_id, product_id, version).c_str());
1453 return 0;
1454 }
1455 return entry->type;
1456 }