]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - sys/cam/scsi/scsi_da.c
Merge libc++ trunk r338150, and resolve conflicts.
[FreeBSD/FreeBSD.git] / sys / cam / scsi / scsi_da.c
1 /*-
2  * Implementation of SCSI Direct Access Peripheral driver for CAM.
3  *
4  * SPDX-License-Identifier: BSD-2-Clause-FreeBSD
5  *
6  * Copyright (c) 1997 Justin T. Gibbs.
7  * All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  * 1. Redistributions of source code must retain the above copyright
13  *    notice, this list of conditions, and the following disclaimer,
14  *    without modification, immediately at the beginning of the file.
15  * 2. The name of the author may not be used to endorse or promote products
16  *    derived from this software without specific prior written permission.
17  *
18  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
19  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
21  * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
22  * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
23  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
24  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
25  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
26  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
27  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
28  * SUCH DAMAGE.
29  */
30
31 #include <sys/cdefs.h>
32 __FBSDID("$FreeBSD$");
33
34 #include <sys/param.h>
35
36 #ifdef _KERNEL
37 #include "opt_da.h"
38 #include <sys/systm.h>
39 #include <sys/kernel.h>
40 #include <sys/bio.h>
41 #include <sys/sysctl.h>
42 #include <sys/taskqueue.h>
43 #include <sys/lock.h>
44 #include <sys/mutex.h>
45 #include <sys/conf.h>
46 #include <sys/devicestat.h>
47 #include <sys/eventhandler.h>
48 #include <sys/malloc.h>
49 #include <sys/cons.h>
50 #include <sys/endian.h>
51 #include <sys/proc.h>
52 #include <sys/sbuf.h>
53 #include <geom/geom.h>
54 #include <geom/geom_disk.h>
55 #include <machine/atomic.h>
56 #endif /* _KERNEL */
57
58 #ifndef _KERNEL
59 #include <stdio.h>
60 #include <string.h>
61 #endif /* _KERNEL */
62
63 #include <cam/cam.h>
64 #include <cam/cam_ccb.h>
65 #include <cam/cam_periph.h>
66 #include <cam/cam_xpt_periph.h>
67 #include <cam/cam_sim.h>
68 #include <cam/cam_iosched.h>
69
70 #include <cam/scsi/scsi_message.h>
71 #include <cam/scsi/scsi_da.h>
72
73 #ifdef _KERNEL
74 /*
75  * Note that there are probe ordering dependencies here.  The order isn't
76  * controlled by this enumeration, but by explicit state transitions in
77  * dastart() and dadone().  Here are some of the dependencies:
78  * 
79  * 1. RC should come first, before RC16, unless there is evidence that RC16
80  *    is supported.
81  * 2. BDC needs to come before any of the ATA probes, or the ZONE probe.
82  * 3. The ATA probes should go in this order:
83  *    ATA -> LOGDIR -> IDDIR -> SUP -> ATA_ZONE
84  */
85 typedef enum {
86         DA_STATE_PROBE_WP,
87         DA_STATE_PROBE_RC,
88         DA_STATE_PROBE_RC16,
89         DA_STATE_PROBE_LBP,
90         DA_STATE_PROBE_BLK_LIMITS,
91         DA_STATE_PROBE_BDC,
92         DA_STATE_PROBE_ATA,
93         DA_STATE_PROBE_ATA_LOGDIR,
94         DA_STATE_PROBE_ATA_IDDIR,
95         DA_STATE_PROBE_ATA_SUP,
96         DA_STATE_PROBE_ATA_ZONE,
97         DA_STATE_PROBE_ZONE,
98         DA_STATE_NORMAL
99 } da_state;
100
101 typedef enum {
102         DA_FLAG_PACK_INVALID    = 0x000001,
103         DA_FLAG_NEW_PACK        = 0x000002,
104         DA_FLAG_PACK_LOCKED     = 0x000004,
105         DA_FLAG_PACK_REMOVABLE  = 0x000008,
106         DA_FLAG_NEED_OTAG       = 0x000020,
107         DA_FLAG_WAS_OTAG        = 0x000040,
108         DA_FLAG_RETRY_UA        = 0x000080,
109         DA_FLAG_OPEN            = 0x000100,
110         DA_FLAG_SCTX_INIT       = 0x000200,
111         DA_FLAG_CAN_RC16        = 0x000400,
112         DA_FLAG_PROBED          = 0x000800,
113         DA_FLAG_DIRTY           = 0x001000,
114         DA_FLAG_ANNOUNCED       = 0x002000,
115         DA_FLAG_CAN_ATA_DMA     = 0x004000,
116         DA_FLAG_CAN_ATA_LOG     = 0x008000,
117         DA_FLAG_CAN_ATA_IDLOG   = 0x010000,
118         DA_FLAG_CAN_ATA_SUPCAP  = 0x020000,
119         DA_FLAG_CAN_ATA_ZONE    = 0x040000,
120         DA_FLAG_TUR_PENDING     = 0x080000
121 } da_flags;
122
123 typedef enum {
124         DA_Q_NONE               = 0x00,
125         DA_Q_NO_SYNC_CACHE      = 0x01,
126         DA_Q_NO_6_BYTE          = 0x02,
127         DA_Q_NO_PREVENT         = 0x04,
128         DA_Q_4K                 = 0x08,
129         DA_Q_NO_RC16            = 0x10,
130         DA_Q_NO_UNMAP           = 0x20,
131         DA_Q_RETRY_BUSY         = 0x40,
132         DA_Q_SMR_DM             = 0x80,
133         DA_Q_STRICT_UNMAP       = 0x100
134 } da_quirks;
135
136 #define DA_Q_BIT_STRING         \
137         "\020"                  \
138         "\001NO_SYNC_CACHE"     \
139         "\002NO_6_BYTE"         \
140         "\003NO_PREVENT"        \
141         "\0044K"                \
142         "\005NO_RC16"           \
143         "\006NO_UNMAP"          \
144         "\007RETRY_BUSY"        \
145         "\010SMR_DM"            \
146         "\011STRICT_UNMAP"
147
148 typedef enum {
149         DA_CCB_PROBE_RC         = 0x01,
150         DA_CCB_PROBE_RC16       = 0x02,
151         DA_CCB_PROBE_LBP        = 0x03,
152         DA_CCB_PROBE_BLK_LIMITS = 0x04,
153         DA_CCB_PROBE_BDC        = 0x05,
154         DA_CCB_PROBE_ATA        = 0x06,
155         DA_CCB_BUFFER_IO        = 0x07,
156         DA_CCB_DUMP             = 0x0A,
157         DA_CCB_DELETE           = 0x0B,
158         DA_CCB_TUR              = 0x0C,
159         DA_CCB_PROBE_ZONE       = 0x0D,
160         DA_CCB_PROBE_ATA_LOGDIR = 0x0E,
161         DA_CCB_PROBE_ATA_IDDIR  = 0x0F,
162         DA_CCB_PROBE_ATA_SUP    = 0x10,
163         DA_CCB_PROBE_ATA_ZONE   = 0x11,
164         DA_CCB_PROBE_WP         = 0x12,
165         DA_CCB_TYPE_MASK        = 0x1F,
166         DA_CCB_RETRY_UA         = 0x20 
167 } da_ccb_state;
168
169 /*
170  * Order here is important for method choice
171  *
172  * We prefer ATA_TRIM as tests run against a Sandforce 2281 SSD attached to
173  * LSI 2008 (mps) controller (FW: v12, Drv: v14) resulted 20% quicker deletes
174  * using ATA_TRIM than the corresponding UNMAP results for a real world mysql
175  * import taking 5mins.
176  *
177  */
178 typedef enum {
179         DA_DELETE_NONE,
180         DA_DELETE_DISABLE,
181         DA_DELETE_ATA_TRIM,
182         DA_DELETE_UNMAP,
183         DA_DELETE_WS16,
184         DA_DELETE_WS10,
185         DA_DELETE_ZERO,
186         DA_DELETE_MIN = DA_DELETE_ATA_TRIM,
187         DA_DELETE_MAX = DA_DELETE_ZERO
188 } da_delete_methods;
189
190 /*
191  * For SCSI, host managed drives show up as a separate device type.  For
192  * ATA, host managed drives also have a different device signature.
193  * XXX KDM figure out the ATA host managed signature.
194  */
195 typedef enum {
196         DA_ZONE_NONE            = 0x00,
197         DA_ZONE_DRIVE_MANAGED   = 0x01,
198         DA_ZONE_HOST_AWARE      = 0x02,
199         DA_ZONE_HOST_MANAGED    = 0x03
200 } da_zone_mode;
201
202 /*
203  * We distinguish between these interface cases in addition to the drive type:
204  * o ATA drive behind a SCSI translation layer that knows about ZBC/ZAC
205  * o ATA drive behind a SCSI translation layer that does not know about
206  *   ZBC/ZAC, and so needs to be managed via ATA passthrough.  In this
207  *   case, we would need to share the ATA code with the ada(4) driver.
208  * o SCSI drive.
209  */
210 typedef enum {
211         DA_ZONE_IF_SCSI,
212         DA_ZONE_IF_ATA_PASS,
213         DA_ZONE_IF_ATA_SAT,
214 } da_zone_interface;
215
216 typedef enum {
217         DA_ZONE_FLAG_RZ_SUP             = 0x0001,
218         DA_ZONE_FLAG_OPEN_SUP           = 0x0002,
219         DA_ZONE_FLAG_CLOSE_SUP          = 0x0004,
220         DA_ZONE_FLAG_FINISH_SUP         = 0x0008,
221         DA_ZONE_FLAG_RWP_SUP            = 0x0010,
222         DA_ZONE_FLAG_SUP_MASK           = (DA_ZONE_FLAG_RZ_SUP |
223                                            DA_ZONE_FLAG_OPEN_SUP |
224                                            DA_ZONE_FLAG_CLOSE_SUP |
225                                            DA_ZONE_FLAG_FINISH_SUP |
226                                            DA_ZONE_FLAG_RWP_SUP),
227         DA_ZONE_FLAG_URSWRZ             = 0x0020,
228         DA_ZONE_FLAG_OPT_SEQ_SET        = 0x0040,
229         DA_ZONE_FLAG_OPT_NONSEQ_SET     = 0x0080,
230         DA_ZONE_FLAG_MAX_SEQ_SET        = 0x0100,
231         DA_ZONE_FLAG_SET_MASK           = (DA_ZONE_FLAG_OPT_SEQ_SET |
232                                            DA_ZONE_FLAG_OPT_NONSEQ_SET |
233                                            DA_ZONE_FLAG_MAX_SEQ_SET)
234 } da_zone_flags;
235
236 static struct da_zone_desc {
237         da_zone_flags value;
238         const char *desc;
239 } da_zone_desc_table[] = {
240         {DA_ZONE_FLAG_RZ_SUP, "Report Zones" },
241         {DA_ZONE_FLAG_OPEN_SUP, "Open" },
242         {DA_ZONE_FLAG_CLOSE_SUP, "Close" },
243         {DA_ZONE_FLAG_FINISH_SUP, "Finish" },
244         {DA_ZONE_FLAG_RWP_SUP, "Reset Write Pointer" },
245 };
246
247 typedef void da_delete_func_t (struct cam_periph *periph, union ccb *ccb,
248                               struct bio *bp);
249 static da_delete_func_t da_delete_trim;
250 static da_delete_func_t da_delete_unmap;
251 static da_delete_func_t da_delete_ws;
252
253 static const void * da_delete_functions[] = {
254         NULL,
255         NULL,
256         da_delete_trim,
257         da_delete_unmap,
258         da_delete_ws,
259         da_delete_ws,
260         da_delete_ws
261 };
262
263 static const char *da_delete_method_names[] =
264     { "NONE", "DISABLE", "ATA_TRIM", "UNMAP", "WS16", "WS10", "ZERO" };
265 static const char *da_delete_method_desc[] =
266     { "NONE", "DISABLED", "ATA TRIM", "UNMAP", "WRITE SAME(16) with UNMAP",
267       "WRITE SAME(10) with UNMAP", "ZERO" };
268
269 /* Offsets into our private area for storing information */
270 #define ccb_state       ppriv_field0
271 #define ccb_bp          ppriv_ptr1
272
273 struct disk_params {
274         u_int8_t  heads;
275         u_int32_t cylinders;
276         u_int8_t  secs_per_track;
277         u_int32_t secsize;      /* Number of bytes/sector */
278         u_int64_t sectors;      /* total number sectors */
279         u_int     stripesize;
280         u_int     stripeoffset;
281 };
282
283 #define UNMAP_RANGE_MAX         0xffffffff
284 #define UNMAP_HEAD_SIZE         8
285 #define UNMAP_RANGE_SIZE        16
286 #define UNMAP_MAX_RANGES        2048 /* Protocol Max is 4095 */
287 #define UNMAP_BUF_SIZE          ((UNMAP_MAX_RANGES * UNMAP_RANGE_SIZE) + \
288                                 UNMAP_HEAD_SIZE)
289
290 #define WS10_MAX_BLKS           0xffff
291 #define WS16_MAX_BLKS           0xffffffff
292 #define ATA_TRIM_MAX_RANGES     ((UNMAP_BUF_SIZE / \
293         (ATA_DSM_RANGE_SIZE * ATA_DSM_BLK_SIZE)) * ATA_DSM_BLK_SIZE)
294
295 #define DA_WORK_TUR             (1 << 16)
296
297 typedef enum {
298         DA_REF_OPEN = 1,
299         DA_REF_OPEN_HOLD,
300         DA_REF_CLOSE_HOLD,
301         DA_REF_PROBE_HOLD,
302         DA_REF_TUR,
303         DA_REF_GEOM,
304         DA_REF_SYSCTL,
305         DA_REF_REPROBE,
306         DA_REF_MAX              /* KEEP LAST */
307 } da_ref_token;
308
309 struct da_softc {
310         struct   cam_iosched_softc *cam_iosched;
311         struct   bio_queue_head delete_run_queue;
312         LIST_HEAD(, ccb_hdr) pending_ccbs;
313         int      refcount;              /* Active xpt_action() calls */
314         da_state state;
315         da_flags flags; 
316         da_quirks quirks;
317         int      minimum_cmd_size;
318         int      error_inject;
319         int      trim_max_ranges;
320         int      delete_available;      /* Delete methods possibly available */
321         da_zone_mode                    zone_mode;
322         da_zone_interface               zone_interface;
323         da_zone_flags                   zone_flags;
324         struct ata_gp_log_dir           ata_logdir;
325         int                             valid_logdir_len;
326         struct ata_identify_log_pages   ata_iddir;
327         int                             valid_iddir_len;
328         uint64_t                        optimal_seq_zones;
329         uint64_t                        optimal_nonseq_zones;
330         uint64_t                        max_seq_zones;
331         u_int                   maxio;
332         uint32_t                unmap_max_ranges;
333         uint32_t                unmap_max_lba; /* Max LBAs in UNMAP req */
334         uint32_t                unmap_gran;
335         uint32_t                unmap_gran_align;
336         uint64_t                ws_max_blks;
337         da_delete_methods       delete_method_pref;
338         da_delete_methods       delete_method;
339         da_delete_func_t        *delete_func;
340         int                     unmappedio;
341         int                     rotating;
342         struct   disk_params params;
343         struct   disk *disk;
344         union    ccb saved_ccb;
345         struct task             sysctl_task;
346         struct sysctl_ctx_list  sysctl_ctx;
347         struct sysctl_oid       *sysctl_tree;
348         struct callout          sendordered_c;
349         uint64_t wwpn;
350         uint8_t  unmap_buf[UNMAP_BUF_SIZE];
351         struct scsi_read_capacity_data_long rcaplong;
352         struct callout          mediapoll_c;
353         int                     ref_flags[DA_REF_MAX];
354 #ifdef CAM_IO_STATS
355         struct sysctl_ctx_list  sysctl_stats_ctx;
356         struct sysctl_oid       *sysctl_stats_tree;
357         u_int   errors;
358         u_int   timeouts;
359         u_int   invalidations;
360 #endif
361 #define DA_ANNOUNCETMP_SZ 160
362         char                    announce_temp[DA_ANNOUNCETMP_SZ];
363 #define DA_ANNOUNCE_SZ 400
364         char                    announcebuf[DA_ANNOUNCE_SZ];
365 };
366
367 #define dadeleteflag(softc, delete_method, enable)                      \
368         if (enable) {                                                   \
369                 softc->delete_available |= (1 << delete_method);        \
370         } else {                                                        \
371                 softc->delete_available &= ~(1 << delete_method);       \
372         }
373
374 struct da_quirk_entry {
375         struct scsi_inquiry_pattern inq_pat;
376         da_quirks quirks;
377 };
378
379 static const char quantum[] = "QUANTUM";
380 static const char microp[] = "MICROP";
381
382 static struct da_quirk_entry da_quirk_table[] =
383 {
384         /* SPI, FC devices */
385         {
386                 /*
387                  * Fujitsu M2513A MO drives.
388                  * Tested devices: M2513A2 firmware versions 1200 & 1300.
389                  * (dip switch selects whether T_DIRECT or T_OPTICAL device)
390                  * Reported by: W.Scholten <whs@xs4all.nl>
391                  */
392                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "FUJITSU", "M2513A", "*"},
393                 /*quirks*/ DA_Q_NO_SYNC_CACHE
394         },
395         {
396                 /* See above. */
397                 {T_OPTICAL, SIP_MEDIA_REMOVABLE, "FUJITSU", "M2513A", "*"},
398                 /*quirks*/ DA_Q_NO_SYNC_CACHE
399         },
400         {
401                 /*
402                  * This particular Fujitsu drive doesn't like the
403                  * synchronize cache command.
404                  * Reported by: Tom Jackson <toj@gorilla.net>
405                  */
406                 {T_DIRECT, SIP_MEDIA_FIXED, "FUJITSU", "M2954*", "*"},
407                 /*quirks*/ DA_Q_NO_SYNC_CACHE
408         },
409         {
410                 /*
411                  * This drive doesn't like the synchronize cache command
412                  * either.  Reported by: Matthew Jacob <mjacob@feral.com>
413                  * in NetBSD PR kern/6027, August 24, 1998.
414                  */
415                 {T_DIRECT, SIP_MEDIA_FIXED, microp, "2217*", "*"},
416                 /*quirks*/ DA_Q_NO_SYNC_CACHE
417         },
418         {
419                 /*
420                  * This drive doesn't like the synchronize cache command
421                  * either.  Reported by: Hellmuth Michaelis (hm@kts.org)
422                  * (PR 8882).
423                  */
424                 {T_DIRECT, SIP_MEDIA_FIXED, microp, "2112*", "*"},
425                 /*quirks*/ DA_Q_NO_SYNC_CACHE
426         },
427         {
428                 /*
429                  * Doesn't like the synchronize cache command.
430                  * Reported by: Blaz Zupan <blaz@gold.amis.net>
431                  */
432                 {T_DIRECT, SIP_MEDIA_FIXED, "NEC", "D3847*", "*"},
433                 /*quirks*/ DA_Q_NO_SYNC_CACHE
434         },
435         {
436                 /*
437                  * Doesn't like the synchronize cache command.
438                  * Reported by: Blaz Zupan <blaz@gold.amis.net>
439                  */
440                 {T_DIRECT, SIP_MEDIA_FIXED, quantum, "MAVERICK 540S", "*"},
441                 /*quirks*/ DA_Q_NO_SYNC_CACHE
442         },
443         {
444                 /*
445                  * Doesn't like the synchronize cache command.
446                  */
447                 {T_DIRECT, SIP_MEDIA_FIXED, quantum, "LPS525S", "*"},
448                 /*quirks*/ DA_Q_NO_SYNC_CACHE
449         },
450         {
451                 /*
452                  * Doesn't like the synchronize cache command.
453                  * Reported by: walter@pelissero.de
454                  */
455                 {T_DIRECT, SIP_MEDIA_FIXED, quantum, "LPS540S", "*"},
456                 /*quirks*/ DA_Q_NO_SYNC_CACHE
457         },
458         {
459                 /*
460                  * Doesn't work correctly with 6 byte reads/writes.
461                  * Returns illegal request, and points to byte 9 of the
462                  * 6-byte CDB.
463                  * Reported by:  Adam McDougall <bsdx@spawnet.com>
464                  */
465                 {T_DIRECT, SIP_MEDIA_FIXED, quantum, "VIKING 4*", "*"},
466                 /*quirks*/ DA_Q_NO_6_BYTE
467         },
468         {
469                 /* See above. */
470                 {T_DIRECT, SIP_MEDIA_FIXED, quantum, "VIKING 2*", "*"},
471                 /*quirks*/ DA_Q_NO_6_BYTE
472         },
473         {
474                 /*
475                  * Doesn't like the synchronize cache command.
476                  * Reported by: walter@pelissero.de
477                  */
478                 {T_DIRECT, SIP_MEDIA_FIXED, "CONNER", "CP3500*", "*"},
479                 /*quirks*/ DA_Q_NO_SYNC_CACHE
480         },
481         {
482                 /*
483                  * The CISS RAID controllers do not support SYNC_CACHE
484                  */
485                 {T_DIRECT, SIP_MEDIA_FIXED, "COMPAQ", "RAID*", "*"},
486                 /*quirks*/ DA_Q_NO_SYNC_CACHE
487         },
488         {
489                 /*
490                  * The STEC SSDs sometimes hang on UNMAP.
491                  */
492                 {T_DIRECT, SIP_MEDIA_FIXED, "STEC", "*", "*"},
493                 /*quirks*/ DA_Q_NO_UNMAP
494         },
495         {
496                 /*
497                  * VMware returns BUSY status when storage has transient
498                  * connectivity problems, so better wait.
499                  * Also VMware returns odd errors on misaligned UNMAPs.
500                  */
501                 {T_DIRECT, SIP_MEDIA_FIXED, "VMware*", "*", "*"},
502                 /*quirks*/ DA_Q_RETRY_BUSY | DA_Q_STRICT_UNMAP
503         },
504         /* USB mass storage devices supported by umass(4) */
505         {
506                 /*
507                  * EXATELECOM (Sigmatel) i-Bead 100/105 USB Flash MP3 Player
508                  * PR: kern/51675
509                  */
510                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "EXATEL", "i-BEAD10*", "*"},
511                 /*quirks*/ DA_Q_NO_SYNC_CACHE
512         },
513         {
514                 /*
515                  * Power Quotient Int. (PQI) USB flash key
516                  * PR: kern/53067
517                  */
518                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "Generic*", "USB Flash Disk*",
519                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
520         },
521         {
522                 /*
523                  * Creative Nomad MUVO mp3 player (USB)
524                  * PR: kern/53094
525                  */
526                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "CREATIVE", "NOMAD_MUVO", "*"},
527                 /*quirks*/ DA_Q_NO_SYNC_CACHE|DA_Q_NO_PREVENT
528         },
529         {
530                 /*
531                  * Jungsoft NEXDISK USB flash key
532                  * PR: kern/54737
533                  */
534                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "JUNGSOFT", "NEXDISK*", "*"},
535                 /*quirks*/ DA_Q_NO_SYNC_CACHE
536         },
537         {
538                 /*
539                  * FreeDik USB Mini Data Drive
540                  * PR: kern/54786
541                  */
542                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "FreeDik*", "Mini Data Drive",
543                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
544         },
545         {
546                 /*
547                  * Sigmatel USB Flash MP3 Player
548                  * PR: kern/57046
549                  */
550                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "SigmaTel", "MSCN", "*"},
551                 /*quirks*/ DA_Q_NO_SYNC_CACHE|DA_Q_NO_PREVENT
552         },
553         {
554                 /*
555                  * Neuros USB Digital Audio Computer
556                  * PR: kern/63645
557                  */
558                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "NEUROS", "dig. audio comp.",
559                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
560         },
561         {
562                 /*
563                  * SEAGRAND NP-900 MP3 Player
564                  * PR: kern/64563
565                  */
566                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "SEAGRAND", "NP-900*", "*"},
567                 /*quirks*/ DA_Q_NO_SYNC_CACHE|DA_Q_NO_PREVENT
568         },
569         {
570                 /*
571                  * iRiver iFP MP3 player (with UMS Firmware)
572                  * PR: kern/54881, i386/63941, kern/66124
573                  */
574                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "iRiver", "iFP*", "*"},
575                 /*quirks*/ DA_Q_NO_SYNC_CACHE
576         },
577         {
578                 /*
579                  * Frontier Labs NEX IA+ Digital Audio Player, rev 1.10/0.01
580                  * PR: kern/70158
581                  */
582                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "FL" , "Nex*", "*"},
583                 /*quirks*/ DA_Q_NO_SYNC_CACHE
584         },
585         {
586                 /*
587                  * ZICPlay USB MP3 Player with FM
588                  * PR: kern/75057
589                  */
590                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "ACTIONS*" , "USB DISK*", "*"},
591                 /*quirks*/ DA_Q_NO_SYNC_CACHE
592         },
593         {
594                 /*
595                  * TEAC USB floppy mechanisms
596                  */
597                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "TEAC" , "FD-05*", "*"},
598                 /*quirks*/ DA_Q_NO_SYNC_CACHE
599         },
600         {
601                 /*
602                  * Kingston DataTraveler II+ USB Pen-Drive.
603                  * Reported by: Pawel Jakub Dawidek <pjd@FreeBSD.org>
604                  */
605                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "Kingston" , "DataTraveler II+",
606                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
607         },
608         {
609                 /*
610                  * USB DISK Pro PMAP
611                  * Reported by: jhs
612                  * PR: usb/96381
613                  */
614                 {T_DIRECT, SIP_MEDIA_REMOVABLE, " ", "USB DISK Pro", "PMAP"},
615                 /*quirks*/ DA_Q_NO_SYNC_CACHE
616         },
617         {
618                 /*
619                  * Motorola E398 Mobile Phone (TransFlash memory card).
620                  * Reported by: Wojciech A. Koszek <dunstan@FreeBSD.czest.pl>
621                  * PR: usb/89889
622                  */
623                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "Motorola" , "Motorola Phone",
624                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
625         },
626         {
627                 /*
628                  * Qware BeatZkey! Pro
629                  * PR: usb/79164
630                  */
631                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "GENERIC", "USB DISK DEVICE",
632                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
633         },
634         {
635                 /*
636                  * Time DPA20B 1GB MP3 Player
637                  * PR: usb/81846
638                  */
639                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "USB2.0*", "(FS) FLASH DISK*",
640                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
641         },
642         {
643                 /*
644                  * Samsung USB key 128Mb
645                  * PR: usb/90081
646                  */
647                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "USB-DISK", "FreeDik-FlashUsb",
648                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
649         },
650         {
651                 /*
652                  * Kingston DataTraveler 2.0 USB Flash memory.
653                  * PR: usb/89196
654                  */
655                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "Kingston", "DataTraveler 2.0",
656                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
657         },
658         {
659                 /*
660                  * Creative MUVO Slim mp3 player (USB)
661                  * PR: usb/86131
662                  */
663                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "CREATIVE", "MuVo Slim",
664                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE|DA_Q_NO_PREVENT
665                 },
666         {
667                 /*
668                  * United MP5512 Portable MP3 Player (2-in-1 USB DISK/MP3)
669                  * PR: usb/80487
670                  */
671                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "Generic*", "MUSIC DISK",
672                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
673         },
674         {
675                 /*
676                  * SanDisk Micro Cruzer 128MB
677                  * PR: usb/75970
678                  */
679                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "SanDisk" , "Micro Cruzer",
680                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
681         },
682         {
683                 /*
684                  * TOSHIBA TransMemory USB sticks
685                  * PR: kern/94660
686                  */
687                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "TOSHIBA", "TransMemory",
688                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
689         },
690         {
691                 /*
692                  * PNY USB 3.0 Flash Drives
693                 */
694                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "PNY", "USB 3.0 FD*",
695                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE | DA_Q_NO_RC16
696         },
697         {
698                 /*
699                  * PNY USB Flash keys
700                  * PR: usb/75578, usb/72344, usb/65436 
701                  */
702                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "*" , "USB DISK*",
703                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
704         },
705         {
706                 /*
707                  * Genesys GL3224
708                  */
709                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "Generic*", "STORAGE DEVICE*",
710                 "120?"}, /*quirks*/ DA_Q_NO_SYNC_CACHE | DA_Q_4K | DA_Q_NO_RC16
711         },
712         {
713                 /*
714                  * Genesys 6-in-1 Card Reader
715                  * PR: usb/94647
716                  */
717                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "Generic*", "STORAGE DEVICE*",
718                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
719         },
720         {
721                 /*
722                  * Rekam Digital CAMERA
723                  * PR: usb/98713
724                  */
725                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "CAMERA*", "4MP-9J6*",
726                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
727         },
728         {
729                 /*
730                  * iRiver H10 MP3 player
731                  * PR: usb/102547
732                  */
733                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "iriver", "H10*",
734                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
735         },
736         {
737                 /*
738                  * iRiver U10 MP3 player
739                  * PR: usb/92306
740                  */
741                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "iriver", "U10*",
742                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
743         },
744         {
745                 /*
746                  * X-Micro Flash Disk
747                  * PR: usb/96901
748                  */
749                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "X-Micro", "Flash Disk",
750                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
751         },
752         {
753                 /*
754                  * EasyMP3 EM732X USB 2.0 Flash MP3 Player
755                  * PR: usb/96546
756                  */
757                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "EM732X", "MP3 Player*",
758                 "1.00"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
759         },
760         {
761                 /*
762                  * Denver MP3 player
763                  * PR: usb/107101
764                  */
765                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "DENVER", "MP3 PLAYER",
766                  "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
767         },
768         {
769                 /*
770                  * Philips USB Key Audio KEY013
771                  * PR: usb/68412
772                  */
773                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "PHILIPS", "Key*", "*"},
774                 /*quirks*/ DA_Q_NO_SYNC_CACHE | DA_Q_NO_PREVENT
775         },
776         {
777                 /*
778                  * JNC MP3 Player
779                  * PR: usb/94439
780                  */
781                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "JNC*" , "MP3 Player*",
782                  "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
783         },
784         {
785                 /*
786                  * SAMSUNG MP0402H
787                  * PR: usb/108427
788                  */
789                 {T_DIRECT, SIP_MEDIA_FIXED, "SAMSUNG", "MP0402H", "*"},
790                 /*quirks*/ DA_Q_NO_SYNC_CACHE
791         },
792         {
793                 /*
794                  * I/O Magic USB flash - Giga Bank
795                  * PR: usb/108810
796                  */
797                 {T_DIRECT, SIP_MEDIA_FIXED, "GS-Magic", "stor*", "*"},
798                 /*quirks*/ DA_Q_NO_SYNC_CACHE
799         },
800         {
801                 /*
802                  * JoyFly 128mb USB Flash Drive
803                  * PR: 96133
804                  */
805                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "USB 2.0", "Flash Disk*",
806                  "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
807         },
808         {
809                 /*
810                  * ChipsBnk usb stick
811                  * PR: 103702
812                  */
813                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "ChipsBnk", "USB*",
814                  "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
815         },
816         {
817                 /*
818                  * Storcase (Kingston) InfoStation IFS FC2/SATA-R 201A
819                  * PR: 129858
820                  */
821                 {T_DIRECT, SIP_MEDIA_FIXED, "IFS", "FC2/SATA-R*",
822                  "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
823         },
824         {
825                 /*
826                  * Samsung YP-U3 mp3-player
827                  * PR: 125398
828                  */
829                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "Samsung", "YP-U3",
830                  "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
831         },
832         {
833                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "Netac", "OnlyDisk*",
834                  "2000"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
835         },
836         {
837                 /*
838                  * Sony Cyber-Shot DSC cameras
839                  * PR: usb/137035
840                  */
841                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "Sony", "Sony DSC", "*"},
842                 /*quirks*/ DA_Q_NO_SYNC_CACHE | DA_Q_NO_PREVENT
843         },
844         {
845                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "Kingston", "DataTraveler G3",
846                  "1.00"}, /*quirks*/ DA_Q_NO_PREVENT
847         },
848         {
849                 /* At least several Transcent USB sticks lie on RC16. */
850                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "JetFlash", "Transcend*",
851                  "*"}, /*quirks*/ DA_Q_NO_RC16
852         },
853         {
854                 /*
855                  * I-O Data USB Flash Disk
856                  * PR: usb/211716
857                  */
858                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "I-O DATA", "USB Flash Disk*",
859                  "*"}, /*quirks*/ DA_Q_NO_RC16
860         },
861         /* ATA/SATA devices over SAS/USB/... */
862         {
863                 /* Hitachi Advanced Format (4k) drives */
864                 { T_DIRECT, SIP_MEDIA_FIXED, "Hitachi", "H??????????E3*", "*" },
865                 /*quirks*/DA_Q_4K
866         },
867         {
868                 /* Micron Advanced Format (4k) drives */
869                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "Micron 5100 MTFDDAK*", "*" },
870                 /*quirks*/DA_Q_4K
871         },
872         {
873                 /* Samsung Advanced Format (4k) drives */
874                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "SAMSUNG HD155UI*", "*" },
875                 /*quirks*/DA_Q_4K
876         },
877         {
878                 /* Samsung Advanced Format (4k) drives */
879                 { T_DIRECT, SIP_MEDIA_FIXED, "SAMSUNG", "HD155UI*", "*" },
880                 /*quirks*/DA_Q_4K
881         },
882         {
883                 /* Samsung Advanced Format (4k) drives */
884                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "SAMSUNG HD204UI*", "*" },
885                 /*quirks*/DA_Q_4K
886         },
887         {
888                 /* Samsung Advanced Format (4k) drives */
889                 { T_DIRECT, SIP_MEDIA_FIXED, "SAMSUNG", "HD204UI*", "*" },
890                 /*quirks*/DA_Q_4K
891         },
892         {
893                 /* Seagate Barracuda Green Advanced Format (4k) drives */
894                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST????DL*", "*" },
895                 /*quirks*/DA_Q_4K
896         },
897         {
898                 /* Seagate Barracuda Green Advanced Format (4k) drives */
899                 { T_DIRECT, SIP_MEDIA_FIXED, "ST????DL", "*", "*" },
900                 /*quirks*/DA_Q_4K
901         },
902         {
903                 /* Seagate Barracuda Green Advanced Format (4k) drives */
904                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST???DM*", "*" },
905                 /*quirks*/DA_Q_4K
906         },
907         {
908                 /* Seagate Barracuda Green Advanced Format (4k) drives */
909                 { T_DIRECT, SIP_MEDIA_FIXED, "ST???DM*", "*", "*" },
910                 /*quirks*/DA_Q_4K
911         },
912         {
913                 /* Seagate Barracuda Green Advanced Format (4k) drives */
914                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST????DM*", "*" },
915                 /*quirks*/DA_Q_4K
916         },
917         {
918                 /* Seagate Barracuda Green Advanced Format (4k) drives */
919                 { T_DIRECT, SIP_MEDIA_FIXED, "ST????DM", "*", "*" },
920                 /*quirks*/DA_Q_4K
921         },
922         {
923                 /* Seagate Momentus Advanced Format (4k) drives */
924                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST9500423AS*", "*" },
925                 /*quirks*/DA_Q_4K
926         },
927         {
928                 /* Seagate Momentus Advanced Format (4k) drives */
929                 { T_DIRECT, SIP_MEDIA_FIXED, "ST950042", "3AS*", "*" },
930                 /*quirks*/DA_Q_4K
931         },
932         {
933                 /* Seagate Momentus Advanced Format (4k) drives */
934                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST9500424AS*", "*" },
935                 /*quirks*/DA_Q_4K
936         },
937         {
938                 /* Seagate Momentus Advanced Format (4k) drives */
939                 { T_DIRECT, SIP_MEDIA_FIXED, "ST950042", "4AS*", "*" },
940                 /*quirks*/DA_Q_4K
941         },
942         {
943                 /* Seagate Momentus Advanced Format (4k) drives */
944                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST9640423AS*", "*" },
945                 /*quirks*/DA_Q_4K
946         },
947         {
948                 /* Seagate Momentus Advanced Format (4k) drives */
949                 { T_DIRECT, SIP_MEDIA_FIXED, "ST964042", "3AS*", "*" },
950                 /*quirks*/DA_Q_4K
951         },
952         {
953                 /* Seagate Momentus Advanced Format (4k) drives */
954                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST9640424AS*", "*" },
955                 /*quirks*/DA_Q_4K
956         },
957         {
958                 /* Seagate Momentus Advanced Format (4k) drives */
959                 { T_DIRECT, SIP_MEDIA_FIXED, "ST964042", "4AS*", "*" },
960                 /*quirks*/DA_Q_4K
961         },
962         {
963                 /* Seagate Momentus Advanced Format (4k) drives */
964                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST9750420AS*", "*" },
965                 /*quirks*/DA_Q_4K
966         },
967         {
968                 /* Seagate Momentus Advanced Format (4k) drives */
969                 { T_DIRECT, SIP_MEDIA_FIXED, "ST975042", "0AS*", "*" },
970                 /*quirks*/DA_Q_4K
971         },
972         {
973                 /* Seagate Momentus Advanced Format (4k) drives */
974                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST9750422AS*", "*" },
975                 /*quirks*/DA_Q_4K
976         },
977         {
978                 /* Seagate Momentus Advanced Format (4k) drives */
979                 { T_DIRECT, SIP_MEDIA_FIXED, "ST975042", "2AS*", "*" },
980                 /*quirks*/DA_Q_4K
981         },
982         {
983                 /* Seagate Momentus Advanced Format (4k) drives */
984                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST9750423AS*", "*" },
985                 /*quirks*/DA_Q_4K
986         },
987         {
988                 /* Seagate Momentus Advanced Format (4k) drives */
989                 { T_DIRECT, SIP_MEDIA_FIXED, "ST975042", "3AS*", "*" },
990                 /*quirks*/DA_Q_4K
991         },
992         {
993                 /* Seagate Momentus Thin Advanced Format (4k) drives */
994                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST???LT*", "*" },
995                 /*quirks*/DA_Q_4K
996         },
997         {
998                 /* Seagate Momentus Thin Advanced Format (4k) drives */
999                 { T_DIRECT, SIP_MEDIA_FIXED, "ST???LT*", "*", "*" },
1000                 /*quirks*/DA_Q_4K
1001         },
1002         {
1003                 /* WDC Caviar Green Advanced Format (4k) drives */
1004                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "WDC WD????RS*", "*" },
1005                 /*quirks*/DA_Q_4K
1006         },
1007         {
1008                 /* WDC Caviar Green Advanced Format (4k) drives */
1009                 { T_DIRECT, SIP_MEDIA_FIXED, "WDC WD??", "??RS*", "*" },
1010                 /*quirks*/DA_Q_4K
1011         },
1012         {
1013                 /* WDC Caviar Green Advanced Format (4k) drives */
1014                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "WDC WD????RX*", "*" },
1015                 /*quirks*/DA_Q_4K
1016         },
1017         {
1018                 /* WDC Caviar Green Advanced Format (4k) drives */
1019                 { T_DIRECT, SIP_MEDIA_FIXED, "WDC WD??", "??RX*", "*" },
1020                 /*quirks*/DA_Q_4K
1021         },
1022         {
1023                 /* WDC Caviar Green Advanced Format (4k) drives */
1024                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "WDC WD??????RS*", "*" },
1025                 /*quirks*/DA_Q_4K
1026         },
1027         {
1028                 /* WDC Caviar Green Advanced Format (4k) drives */
1029                 { T_DIRECT, SIP_MEDIA_FIXED, "WDC WD??", "????RS*", "*" },
1030                 /*quirks*/DA_Q_4K
1031         },
1032         {
1033                 /* WDC Caviar Green Advanced Format (4k) drives */
1034                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "WDC WD??????RX*", "*" },
1035                 /*quirks*/DA_Q_4K
1036         },
1037         {
1038                 /* WDC Caviar Green Advanced Format (4k) drives */
1039                 { T_DIRECT, SIP_MEDIA_FIXED, "WDC WD??", "????RX*", "*" },
1040                 /*quirks*/DA_Q_4K
1041         },
1042         {
1043                 /* WDC Scorpio Black Advanced Format (4k) drives */
1044                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "WDC WD???PKT*", "*" },
1045                 /*quirks*/DA_Q_4K
1046         },
1047         {
1048                 /* WDC Scorpio Black Advanced Format (4k) drives */
1049                 { T_DIRECT, SIP_MEDIA_FIXED, "WDC WD??", "?PKT*", "*" },
1050                 /*quirks*/DA_Q_4K
1051         },
1052         {
1053                 /* WDC Scorpio Black Advanced Format (4k) drives */
1054                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "WDC WD?????PKT*", "*" },
1055                 /*quirks*/DA_Q_4K
1056         },
1057         {
1058                 /* WDC Scorpio Black Advanced Format (4k) drives */
1059                 { T_DIRECT, SIP_MEDIA_FIXED, "WDC WD??", "???PKT*", "*" },
1060                 /*quirks*/DA_Q_4K
1061         },
1062         {
1063                 /* WDC Scorpio Blue Advanced Format (4k) drives */
1064                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "WDC WD???PVT*", "*" },
1065                 /*quirks*/DA_Q_4K
1066         },
1067         {
1068                 /* WDC Scorpio Blue Advanced Format (4k) drives */
1069                 { T_DIRECT, SIP_MEDIA_FIXED, "WDC WD??", "?PVT*", "*" },
1070                 /*quirks*/DA_Q_4K
1071         },
1072         {
1073                 /* WDC Scorpio Blue Advanced Format (4k) drives */
1074                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "WDC WD?????PVT*", "*" },
1075                 /*quirks*/DA_Q_4K
1076         },
1077         {
1078                 /* WDC Scorpio Blue Advanced Format (4k) drives */
1079                 { T_DIRECT, SIP_MEDIA_FIXED, "WDC WD??", "???PVT*", "*" },
1080                 /*quirks*/DA_Q_4K
1081         },
1082         {
1083                 /*
1084                  * Olympus FE-210 camera
1085                  */
1086                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "OLYMPUS", "FE210*",
1087                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
1088         },
1089         {
1090                 /*
1091                  * LG UP3S MP3 player
1092                  */
1093                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "LG", "UP3S",
1094                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
1095         },
1096         {
1097                 /*
1098                  * Laser MP3-2GA13 MP3 player
1099                  */
1100                 {T_DIRECT, SIP_MEDIA_REMOVABLE, "USB 2.0", "(HS) Flash Disk",
1101                 "*"}, /*quirks*/ DA_Q_NO_SYNC_CACHE
1102         },
1103         {
1104                 /*
1105                  * LaCie external 250GB Hard drive des by Porsche
1106                  * Submitted by: Ben Stuyts <ben@altesco.nl>
1107                  * PR: 121474
1108                  */
1109                 {T_DIRECT, SIP_MEDIA_FIXED, "SAMSUNG", "HM250JI", "*"},
1110                 /*quirks*/ DA_Q_NO_SYNC_CACHE
1111         },
1112         /* SATA SSDs */
1113         {
1114                 /*
1115                  * Corsair Force 2 SSDs
1116                  * 4k optimised & trim only works in 4k requests + 4k aligned
1117                  */
1118                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "Corsair CSSD-F*", "*" },
1119                 /*quirks*/DA_Q_4K
1120         },
1121         {
1122                 /*
1123                  * Corsair Force 3 SSDs
1124                  * 4k optimised & trim only works in 4k requests + 4k aligned
1125                  */
1126                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "Corsair Force 3*", "*" },
1127                 /*quirks*/DA_Q_4K
1128         },
1129         {
1130                 /*
1131                  * Corsair Neutron GTX SSDs
1132                  * 4k optimised & trim only works in 4k requests + 4k aligned
1133                  */
1134                 { T_DIRECT, SIP_MEDIA_FIXED, "*", "Corsair Neutron GTX*", "*" },
1135                 /*quirks*/DA_Q_4K
1136         },
1137         {
1138                 /*
1139                  * Corsair Force GT & GS SSDs
1140                  * 4k optimised & trim only works in 4k requests + 4k aligned
1141                  */
1142                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "Corsair Force G*", "*" },
1143                 /*quirks*/DA_Q_4K
1144         },
1145         {
1146                 /*
1147                  * Crucial M4 SSDs
1148                  * 4k optimised & trim only works in 4k requests + 4k aligned
1149                  */
1150                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "M4-CT???M4SSD2*", "*" },
1151                 /*quirks*/DA_Q_4K
1152         },
1153         {
1154                 /*
1155                  * Crucial RealSSD C300 SSDs
1156                  * 4k optimised
1157                  */
1158                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "C300-CTFDDAC???MAG*",
1159                 "*" }, /*quirks*/DA_Q_4K
1160         },
1161         {
1162                 /*
1163                  * Intel 320 Series SSDs
1164                  * 4k optimised & trim only works in 4k requests + 4k aligned
1165                  */
1166                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "INTEL SSDSA2CW*", "*" },
1167                 /*quirks*/DA_Q_4K
1168         },
1169         {
1170                 /*
1171                  * Intel 330 Series SSDs
1172                  * 4k optimised & trim only works in 4k requests + 4k aligned
1173                  */
1174                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "INTEL SSDSC2CT*", "*" },
1175                 /*quirks*/DA_Q_4K
1176         },
1177         {
1178                 /*
1179                  * Intel 510 Series SSDs
1180                  * 4k optimised & trim only works in 4k requests + 4k aligned
1181                  */
1182                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "INTEL SSDSC2MH*", "*" },
1183                 /*quirks*/DA_Q_4K
1184         },
1185         {
1186                 /*
1187                  * Intel 520 Series SSDs
1188                  * 4k optimised & trim only works in 4k requests + 4k aligned
1189                  */
1190                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "INTEL SSDSC2BW*", "*" },
1191                 /*quirks*/DA_Q_4K
1192         },
1193         {
1194                 /*
1195                  * Intel S3610 Series SSDs
1196                  * 4k optimised & trim only works in 4k requests + 4k aligned
1197                  */
1198                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "INTEL SSDSC2BX*", "*" },
1199                 /*quirks*/DA_Q_4K
1200         },
1201         {
1202                 /*
1203                  * Intel X25-M Series SSDs
1204                  * 4k optimised & trim only works in 4k requests + 4k aligned
1205                  */
1206                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "INTEL SSDSA2M*", "*" },
1207                 /*quirks*/DA_Q_4K
1208         },
1209         {
1210                 /*
1211                  * Kingston E100 Series SSDs
1212                  * 4k optimised & trim only works in 4k requests + 4k aligned
1213                  */
1214                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "KINGSTON SE100S3*", "*" },
1215                 /*quirks*/DA_Q_4K
1216         },
1217         {
1218                 /*
1219                  * Kingston HyperX 3k SSDs
1220                  * 4k optimised & trim only works in 4k requests + 4k aligned
1221                  */
1222                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "KINGSTON SH103S3*", "*" },
1223                 /*quirks*/DA_Q_4K
1224         },
1225         {
1226                 /*
1227                  * Marvell SSDs (entry taken from OpenSolaris)
1228                  * 4k optimised & trim only works in 4k requests + 4k aligned
1229                  */
1230                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "MARVELL SD88SA02*", "*" },
1231                 /*quirks*/DA_Q_4K
1232         },
1233         {
1234                 /*
1235                  * OCZ Agility 2 SSDs
1236                  * 4k optimised & trim only works in 4k requests + 4k aligned
1237                  */
1238                 { T_DIRECT, SIP_MEDIA_FIXED, "*", "OCZ-AGILITY2*", "*" },
1239                 /*quirks*/DA_Q_4K
1240         },
1241         {
1242                 /*
1243                  * OCZ Agility 3 SSDs
1244                  * 4k optimised & trim only works in 4k requests + 4k aligned
1245                  */
1246                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "OCZ-AGILITY3*", "*" },
1247                 /*quirks*/DA_Q_4K
1248         },
1249         {
1250                 /*
1251                  * OCZ Deneva R Series SSDs
1252                  * 4k optimised & trim only works in 4k requests + 4k aligned
1253                  */
1254                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "DENRSTE251M45*", "*" },
1255                 /*quirks*/DA_Q_4K
1256         },
1257         {
1258                 /*
1259                  * OCZ Vertex 2 SSDs (inc pro series)
1260                  * 4k optimised & trim only works in 4k requests + 4k aligned
1261                  */
1262                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "OCZ?VERTEX2*", "*" },
1263                 /*quirks*/DA_Q_4K
1264         },
1265         {
1266                 /*
1267                  * OCZ Vertex 3 SSDs
1268                  * 4k optimised & trim only works in 4k requests + 4k aligned
1269                  */
1270                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "OCZ-VERTEX3*", "*" },
1271                 /*quirks*/DA_Q_4K
1272         },
1273         {
1274                 /*
1275                  * OCZ Vertex 4 SSDs
1276                  * 4k optimised & trim only works in 4k requests + 4k aligned
1277                  */
1278                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "OCZ-VERTEX4*", "*" },
1279                 /*quirks*/DA_Q_4K
1280         },
1281         {
1282                 /*
1283                  * Samsung 750 Series SSDs
1284                  * 4k optimised & trim only works in 4k requests + 4k aligned
1285                  */
1286                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "Samsung SSD 750*", "*" },
1287                 /*quirks*/DA_Q_4K
1288         },
1289         {
1290                 /*
1291                  * Samsung 830 Series SSDs
1292                  * 4k optimised & trim only works in 4k requests + 4k aligned
1293                  */
1294                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "SAMSUNG SSD 830 Series*", "*" },
1295                 /*quirks*/DA_Q_4K
1296         },
1297         {
1298                 /*
1299                  * Samsung 840 SSDs
1300                  * 4k optimised & trim only works in 4k requests + 4k aligned
1301                  */
1302                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "Samsung SSD 840*", "*" },
1303                 /*quirks*/DA_Q_4K
1304         },
1305         {
1306                 /*
1307                  * Samsung 845 SSDs
1308                  * 4k optimised & trim only works in 4k requests + 4k aligned
1309                  */
1310                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "Samsung SSD 845*", "*" },
1311                 /*quirks*/DA_Q_4K
1312         },
1313         {
1314                 /*
1315                  * Samsung 850 SSDs
1316                  * 4k optimised & trim only works in 4k requests + 4k aligned
1317                  */
1318                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "Samsung SSD 850*", "*" },
1319                 /*quirks*/DA_Q_4K
1320         },
1321         {
1322                 /*
1323                  * Samsung 843T Series SSDs (MZ7WD*)
1324                  * Samsung PM851 Series SSDs (MZ7TE*)
1325                  * Samsung PM853T Series SSDs (MZ7GE*)
1326                  * Samsung SM863 Series SSDs (MZ7KM*)
1327                  * 4k optimised
1328                  */
1329                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "SAMSUNG MZ7*", "*" },
1330                 /*quirks*/DA_Q_4K
1331         },
1332         {
1333                 /*
1334                  * Same as for SAMSUNG MZ7* but enable the quirks for SSD
1335                  * starting with MZ7* too
1336                  */
1337                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "MZ7*", "*" },
1338                 /*quirks*/DA_Q_4K
1339         },
1340         {
1341                 /*
1342                  * SuperTalent TeraDrive CT SSDs
1343                  * 4k optimised & trim only works in 4k requests + 4k aligned
1344                  */
1345                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "FTM??CT25H*", "*" },
1346                 /*quirks*/DA_Q_4K
1347         },
1348         {
1349                 /*
1350                  * XceedIOPS SATA SSDs
1351                  * 4k optimised
1352                  */
1353                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "SG9XCS2D*", "*" },
1354                 /*quirks*/DA_Q_4K
1355         },
1356         {
1357                 /*
1358                  * Hama Innostor USB-Stick 
1359                  */
1360                 { T_DIRECT, SIP_MEDIA_REMOVABLE, "Innostor", "Innostor*", "*" }, 
1361                 /*quirks*/DA_Q_NO_RC16
1362         },
1363         {
1364                 /*
1365                  * Seagate Lamarr 8TB Shingled Magnetic Recording (SMR)
1366                  * Drive Managed SATA hard drive.  This drive doesn't report
1367                  * in firmware that it is a drive managed SMR drive.
1368                  */
1369                 { T_DIRECT, SIP_MEDIA_FIXED, "ATA", "ST8000AS000[23]*", "*" },
1370                 /*quirks*/DA_Q_SMR_DM
1371         },
1372         {
1373                 /*
1374                  * MX-ES USB Drive by Mach Xtreme
1375                  */
1376                 { T_DIRECT, SIP_MEDIA_REMOVABLE, "MX", "MXUB3*", "*"},
1377                 /*quirks*/DA_Q_NO_RC16
1378         },
1379 };
1380
1381 static  disk_strategy_t dastrategy;
1382 static  dumper_t        dadump;
1383 static  periph_init_t   dainit;
1384 static  void            daasync(void *callback_arg, u_int32_t code,
1385                                 struct cam_path *path, void *arg);
1386 static  void            dasysctlinit(void *context, int pending);
1387 static  int             dasysctlsofttimeout(SYSCTL_HANDLER_ARGS);
1388 static  int             dacmdsizesysctl(SYSCTL_HANDLER_ARGS);
1389 static  int             dadeletemethodsysctl(SYSCTL_HANDLER_ARGS);
1390 static  int             dazonemodesysctl(SYSCTL_HANDLER_ARGS);
1391 static  int             dazonesupsysctl(SYSCTL_HANDLER_ARGS);
1392 static  int             dadeletemaxsysctl(SYSCTL_HANDLER_ARGS);
1393 static  void            dadeletemethodset(struct da_softc *softc,
1394                                           da_delete_methods delete_method);
1395 static  off_t           dadeletemaxsize(struct da_softc *softc,
1396                                         da_delete_methods delete_method);
1397 static  void            dadeletemethodchoose(struct da_softc *softc,
1398                                              da_delete_methods default_method);
1399 static  void            daprobedone(struct cam_periph *periph, union ccb *ccb);
1400
1401 static  periph_ctor_t   daregister;
1402 static  periph_dtor_t   dacleanup;
1403 static  periph_start_t  dastart;
1404 static  periph_oninv_t  daoninvalidate;
1405 static  void            dazonedone(struct cam_periph *periph, union ccb *ccb);
1406 static  void            dadone(struct cam_periph *periph,
1407                                union ccb *done_ccb);
1408 static void             dadone_probewp(struct cam_periph *periph,
1409                                        union ccb *done_ccb);
1410 static void             dadone_proberc(struct cam_periph *periph,
1411                                        union ccb *done_ccb);
1412 static void             dadone_probelbp(struct cam_periph *periph,
1413                                         union ccb *done_ccb);
1414 static void             dadone_probeblklimits(struct cam_periph *periph,
1415                                               union ccb *done_ccb);
1416 static void             dadone_probebdc(struct cam_periph *periph,
1417                                         union ccb *done_ccb);
1418 static void             dadone_probeata(struct cam_periph *periph,
1419                                         union ccb *done_ccb);
1420 static void             dadone_probeatalogdir(struct cam_periph *periph,
1421                                               union ccb *done_ccb);
1422 static void             dadone_probeataiddir(struct cam_periph *periph,
1423                                              union ccb *done_ccb);
1424 static void             dadone_probeatasup(struct cam_periph *periph,
1425                                            union ccb *done_ccb);
1426 static void             dadone_probeatazone(struct cam_periph *periph,
1427                                             union ccb *done_ccb);
1428 static void             dadone_probezone(struct cam_periph *periph,
1429                                          union ccb *done_ccb);
1430 static void             dadone_tur(struct cam_periph *periph,
1431                                    union ccb *done_ccb);
1432 static  int             daerror(union ccb *ccb, u_int32_t cam_flags,
1433                                 u_int32_t sense_flags);
1434 static void             daprevent(struct cam_periph *periph, int action);
1435 static void             dareprobe(struct cam_periph *periph);
1436 static void             dasetgeom(struct cam_periph *periph, uint32_t block_len,
1437                                   uint64_t maxsector,
1438                                   struct scsi_read_capacity_data_long *rcaplong,
1439                                   size_t rcap_size);
1440 static timeout_t        dasendorderedtag;
1441 static void             dashutdown(void *arg, int howto);
1442 static timeout_t        damediapoll;
1443
1444 #ifndef DA_DEFAULT_POLL_PERIOD
1445 #define DA_DEFAULT_POLL_PERIOD  3
1446 #endif
1447
1448 #ifndef DA_DEFAULT_TIMEOUT
1449 #define DA_DEFAULT_TIMEOUT 60   /* Timeout in seconds */
1450 #endif
1451
1452 #ifndef DA_DEFAULT_SOFTTIMEOUT
1453 #define DA_DEFAULT_SOFTTIMEOUT  0
1454 #endif
1455
1456 #ifndef DA_DEFAULT_RETRY
1457 #define DA_DEFAULT_RETRY        4
1458 #endif
1459
1460 #ifndef DA_DEFAULT_SEND_ORDERED
1461 #define DA_DEFAULT_SEND_ORDERED 1
1462 #endif
1463
1464 static int da_poll_period = DA_DEFAULT_POLL_PERIOD;
1465 static int da_retry_count = DA_DEFAULT_RETRY;
1466 static int da_default_timeout = DA_DEFAULT_TIMEOUT;
1467 static sbintime_t da_default_softtimeout = DA_DEFAULT_SOFTTIMEOUT;
1468 static int da_send_ordered = DA_DEFAULT_SEND_ORDERED;
1469
1470 static SYSCTL_NODE(_kern_cam, OID_AUTO, da, CTLFLAG_RD, 0,
1471             "CAM Direct Access Disk driver");
1472 SYSCTL_INT(_kern_cam_da, OID_AUTO, poll_period, CTLFLAG_RWTUN,
1473            &da_poll_period, 0, "Media polling period in seconds");
1474 SYSCTL_INT(_kern_cam_da, OID_AUTO, retry_count, CTLFLAG_RWTUN,
1475            &da_retry_count, 0, "Normal I/O retry count");
1476 SYSCTL_INT(_kern_cam_da, OID_AUTO, default_timeout, CTLFLAG_RWTUN,
1477            &da_default_timeout, 0, "Normal I/O timeout (in seconds)");
1478 SYSCTL_INT(_kern_cam_da, OID_AUTO, send_ordered, CTLFLAG_RWTUN,
1479            &da_send_ordered, 0, "Send Ordered Tags");
1480
1481 SYSCTL_PROC(_kern_cam_da, OID_AUTO, default_softtimeout,
1482     CTLTYPE_UINT | CTLFLAG_RW, NULL, 0, dasysctlsofttimeout, "I",
1483     "Soft I/O timeout (ms)");
1484 TUNABLE_INT64("kern.cam.da.default_softtimeout", &da_default_softtimeout);
1485
1486 /*
1487  * DA_ORDEREDTAG_INTERVAL determines how often, relative
1488  * to the default timeout, we check to see whether an ordered
1489  * tagged transaction is appropriate to prevent simple tag
1490  * starvation.  Since we'd like to ensure that there is at least
1491  * 1/2 of the timeout length left for a starved transaction to
1492  * complete after we've sent an ordered tag, we must poll at least
1493  * four times in every timeout period.  This takes care of the worst
1494  * case where a starved transaction starts during an interval that
1495  * meets the requirement "don't send an ordered tag" test so it takes
1496  * us two intervals to determine that a tag must be sent.
1497  */
1498 #ifndef DA_ORDEREDTAG_INTERVAL
1499 #define DA_ORDEREDTAG_INTERVAL 4
1500 #endif
1501
1502 static struct periph_driver dadriver =
1503 {
1504         dainit, "da",
1505         TAILQ_HEAD_INITIALIZER(dadriver.units), /* generation */ 0
1506 };
1507
1508 PERIPHDRIVER_DECLARE(da, dadriver);
1509
1510 static MALLOC_DEFINE(M_SCSIDA, "scsi_da", "scsi_da buffers");
1511
1512 /*
1513  * This driver takes out references / holds in well defined pairs, never
1514  * recursively. These macros / inline functions enforce those rules. They
1515  * are only enabled with DA_TRACK_REFS or INVARIANTS. If DA_TRACK_REFS is
1516  * defined to be 2 or larger, the tracking also includes debug printfs.
1517  */
1518 #if defined(DA_TRACK_REFS) || defined(INVARIANTS)
1519
1520 #ifndef DA_TRACK_REFS
1521 #define DA_TRACK_REFS 1
1522 #endif
1523
1524 #if DA_TRACK_REFS > 1
1525 static const char *da_ref_text[] = {
1526         "bogus",
1527         "open",
1528         "open hold",
1529         "close hold",
1530         "reprobe hold",
1531         "Test Unit Ready",
1532         "Geom",
1533         "sysctl",
1534         "reprobe",
1535         "max -- also bogus"
1536 };
1537
1538 #define DA_PERIPH_PRINT(periph, msg, args...)           \
1539         CAM_PERIPH_PRINT(periph, msg, ##args)
1540 #else
1541 #define DA_PERIPH_PRINT(periph, msg, args...)
1542 #endif
1543
1544 static inline void
1545 token_sanity(da_ref_token token)
1546 {
1547         if ((unsigned)token >= DA_REF_MAX)
1548                 panic("Bad token value passed in %d\n", token);
1549 }
1550
1551 static inline int
1552 da_periph_hold(struct cam_periph *periph, int priority, da_ref_token token)
1553 {
1554         int err = cam_periph_hold(periph, priority);
1555
1556         token_sanity(token);
1557         DA_PERIPH_PRINT(periph, "Holding device %s (%d): %d\n",
1558             da_ref_text[token], token, err);
1559         if (err == 0) {
1560                 int cnt;
1561                 struct da_softc *softc = periph->softc;
1562
1563                 cnt = atomic_fetchadd_int(&softc->ref_flags[token], 1);
1564                 if (cnt != 0)
1565                         panic("Re-holding for reason %d, cnt = %d", token, cnt);
1566         }
1567         return (err);
1568 }
1569
1570 static inline void
1571 da_periph_unhold(struct cam_periph *periph, da_ref_token token)
1572 {
1573         int cnt;
1574         struct da_softc *softc = periph->softc;
1575
1576         token_sanity(token);
1577         DA_PERIPH_PRINT(periph, "Unholding device %s (%d)\n",
1578             da_ref_text[token], token);
1579         cnt = atomic_fetchadd_int(&softc->ref_flags[token], -1);
1580         if (cnt != 1)
1581                 panic("Unholding %d with cnt = %d", token, cnt);
1582         cam_periph_unhold(periph);
1583 }
1584
1585 static inline int
1586 da_periph_acquire(struct cam_periph *periph, da_ref_token token)
1587 {
1588         int err = cam_periph_acquire(periph);
1589
1590         token_sanity(token);
1591         DA_PERIPH_PRINT(periph, "acquiring device %s (%d): %d\n",
1592             da_ref_text[token], token, err);
1593         if (err == 0) {
1594                 int cnt;
1595                 struct da_softc *softc = periph->softc;
1596
1597                 cnt = atomic_fetchadd_int(&softc->ref_flags[token], 1);
1598                 if (cnt != 0)
1599                         panic("Re-refing for reason %d, cnt = %d", token, cnt);
1600         }
1601         return (err);
1602 }
1603
1604 static inline void
1605 da_periph_release(struct cam_periph *periph, da_ref_token token)
1606 {
1607         int cnt;
1608         struct da_softc *softc = periph->softc;
1609
1610         token_sanity(token);
1611         DA_PERIPH_PRINT(periph, "releasing device %s (%d)\n",
1612             da_ref_text[token], token);
1613         cnt = atomic_fetchadd_int(&softc->ref_flags[token], -1);
1614         if (cnt != 1)
1615                 panic("Releasing %d with cnt = %d", token, cnt);
1616         cam_periph_release(periph);
1617 }
1618
1619 static inline void
1620 da_periph_release_locked(struct cam_periph *periph, da_ref_token token)
1621 {
1622         int cnt;
1623         struct da_softc *softc = periph->softc;
1624
1625         token_sanity(token);
1626         DA_PERIPH_PRINT(periph, "releasing device (locked) %s (%d)\n",
1627             da_ref_text[token], token);
1628         cnt = atomic_fetchadd_int(&softc->ref_flags[token], -1);
1629         if (cnt != 1)
1630                 panic("Unholding %d with cnt = %d", token, cnt);
1631         cam_periph_release_locked(periph);
1632 }
1633
1634 #define cam_periph_hold POISON
1635 #define cam_periph_unhold POISON
1636 #define cam_periph_acquire POISON
1637 #define cam_periph_release POISON
1638 #define cam_periph_release_locked POISON
1639
1640 #else
1641 #define da_periph_hold(periph, prio, token)     cam_periph_hold((periph), (prio))
1642 #define da_periph_unhold(periph, token)         cam_periph_unhold((periph))
1643 #define da_periph_acquire(periph, token)        cam_periph_acquire((periph))
1644 #define da_periph_release(periph, token)        cam_periph_release((periph))
1645 #define da_periph_release_locked(periph, token) cam_periph_release_locked((periph))
1646 #endif
1647
1648 static int
1649 daopen(struct disk *dp)
1650 {
1651         struct cam_periph *periph;
1652         struct da_softc *softc;
1653         int error;
1654
1655         periph = (struct cam_periph *)dp->d_drv1;
1656         if (da_periph_acquire(periph, DA_REF_OPEN) != 0) {
1657                 return (ENXIO);
1658         }
1659
1660         cam_periph_lock(periph);
1661         if ((error = da_periph_hold(periph, PRIBIO|PCATCH, DA_REF_OPEN_HOLD)) != 0) {
1662                 cam_periph_unlock(periph);
1663                 da_periph_release(periph, DA_REF_OPEN);
1664                 return (error);
1665         }
1666
1667         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE | CAM_DEBUG_PERIPH,
1668             ("daopen\n"));
1669
1670         softc = (struct da_softc *)periph->softc;
1671         dareprobe(periph);
1672
1673         /* Wait for the disk size update.  */
1674         error = cam_periph_sleep(periph, &softc->disk->d_mediasize, PRIBIO,
1675             "dareprobe", 0);
1676         if (error != 0)
1677                 xpt_print(periph->path, "unable to retrieve capacity data\n");
1678
1679         if (periph->flags & CAM_PERIPH_INVALID)
1680                 error = ENXIO;
1681
1682         if (error == 0 && (softc->flags & DA_FLAG_PACK_REMOVABLE) != 0 &&
1683             (softc->quirks & DA_Q_NO_PREVENT) == 0)
1684                 daprevent(periph, PR_PREVENT);
1685
1686         if (error == 0) {
1687                 softc->flags &= ~DA_FLAG_PACK_INVALID;
1688                 softc->flags |= DA_FLAG_OPEN;
1689         }
1690
1691         da_periph_unhold(periph, DA_REF_OPEN_HOLD);
1692         cam_periph_unlock(periph);
1693
1694         if (error != 0)
1695                 da_periph_release(periph, DA_REF_OPEN);
1696
1697         return (error);
1698 }
1699
1700 static int
1701 daclose(struct disk *dp)
1702 {
1703         struct  cam_periph *periph;
1704         struct  da_softc *softc;
1705         union   ccb *ccb;
1706
1707         periph = (struct cam_periph *)dp->d_drv1;
1708         softc = (struct da_softc *)periph->softc;
1709         cam_periph_lock(periph);
1710         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE | CAM_DEBUG_PERIPH,
1711             ("daclose\n"));
1712
1713         if (da_periph_hold(periph, PRIBIO, DA_REF_CLOSE_HOLD) == 0) {
1714
1715                 /* Flush disk cache. */
1716                 if ((softc->flags & DA_FLAG_DIRTY) != 0 &&
1717                     (softc->quirks & DA_Q_NO_SYNC_CACHE) == 0 &&
1718                     (softc->flags & DA_FLAG_PACK_INVALID) == 0) {
1719                         ccb = cam_periph_getccb(periph, CAM_PRIORITY_NORMAL);
1720                         scsi_synchronize_cache(&ccb->csio, /*retries*/1,
1721                             /*cbfcnp*/NULL, MSG_SIMPLE_Q_TAG,
1722                             /*begin_lba*/0, /*lb_count*/0, SSD_FULL_SIZE,
1723                             5 * 60 * 1000);
1724                         cam_periph_runccb(ccb, daerror, /*cam_flags*/0,
1725                             /*sense_flags*/SF_RETRY_UA | SF_QUIET_IR,
1726                             softc->disk->d_devstat);
1727                         softc->flags &= ~DA_FLAG_DIRTY;
1728                         xpt_release_ccb(ccb);
1729                 }
1730
1731                 /* Allow medium removal. */
1732                 if ((softc->flags & DA_FLAG_PACK_REMOVABLE) != 0 &&
1733                     (softc->quirks & DA_Q_NO_PREVENT) == 0)
1734                         daprevent(periph, PR_ALLOW);
1735
1736                 da_periph_unhold(periph, DA_REF_CLOSE_HOLD);
1737         }
1738
1739         /*
1740          * If we've got removeable media, mark the blocksize as
1741          * unavailable, since it could change when new media is
1742          * inserted.
1743          */
1744         if ((softc->flags & DA_FLAG_PACK_REMOVABLE) != 0)
1745                 softc->disk->d_devstat->flags |= DEVSTAT_BS_UNAVAILABLE;
1746
1747         softc->flags &= ~DA_FLAG_OPEN;
1748         while (softc->refcount != 0)
1749                 cam_periph_sleep(periph, &softc->refcount, PRIBIO, "daclose", 1);
1750         cam_periph_unlock(periph);
1751         da_periph_release(periph, DA_REF_OPEN);
1752         return (0);
1753 }
1754
1755 static void
1756 daschedule(struct cam_periph *periph)
1757 {
1758         struct da_softc *softc = (struct da_softc *)periph->softc;
1759
1760         if (softc->state != DA_STATE_NORMAL)
1761                 return;
1762
1763         cam_iosched_schedule(softc->cam_iosched, periph);
1764 }
1765
1766 /*
1767  * Actually translate the requested transfer into one the physical driver
1768  * can understand.  The transfer is described by a buf and will include
1769  * only one physical transfer.
1770  */
1771 static void
1772 dastrategy(struct bio *bp)
1773 {
1774         struct cam_periph *periph;
1775         struct da_softc *softc;
1776         
1777         periph = (struct cam_periph *)bp->bio_disk->d_drv1;
1778         softc = (struct da_softc *)periph->softc;
1779
1780         cam_periph_lock(periph);
1781
1782         /*
1783          * If the device has been made invalid, error out
1784          */
1785         if ((softc->flags & DA_FLAG_PACK_INVALID)) {
1786                 cam_periph_unlock(periph);
1787                 biofinish(bp, NULL, ENXIO);
1788                 return;
1789         }
1790
1791         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dastrategy(%p)\n", bp));
1792
1793         /*
1794          * Zone commands must be ordered, because they can depend on the
1795          * effects of previously issued commands, and they may affect
1796          * commands after them.
1797          */
1798         if (bp->bio_cmd == BIO_ZONE)
1799                 bp->bio_flags |= BIO_ORDERED;
1800
1801         /*
1802          * Place it in the queue of disk activities for this disk
1803          */
1804         cam_iosched_queue_work(softc->cam_iosched, bp);
1805
1806         /*
1807          * Schedule ourselves for performing the work.
1808          */
1809         daschedule(periph);
1810         cam_periph_unlock(periph);
1811
1812         return;
1813 }
1814
1815 static int
1816 dadump(void *arg, void *virtual, vm_offset_t physical, off_t offset, size_t length)
1817 {
1818         struct      cam_periph *periph;
1819         struct      da_softc *softc;
1820         u_int       secsize;
1821         struct      ccb_scsiio csio;
1822         struct      disk *dp;
1823         int         error = 0;
1824
1825         dp = arg;
1826         periph = dp->d_drv1;
1827         softc = (struct da_softc *)periph->softc;
1828         secsize = softc->params.secsize;
1829         
1830         if ((softc->flags & DA_FLAG_PACK_INVALID) != 0)
1831                 return (ENXIO);
1832
1833         memset(&csio, 0, sizeof(csio));
1834         if (length > 0) {
1835                 xpt_setup_ccb(&csio.ccb_h, periph->path, CAM_PRIORITY_NORMAL);
1836                 csio.ccb_h.ccb_state = DA_CCB_DUMP;
1837                 scsi_read_write(&csio,
1838                                 /*retries*/0,
1839                                 /*cbfcnp*/NULL,
1840                                 MSG_ORDERED_Q_TAG,
1841                                 /*read*/SCSI_RW_WRITE,
1842                                 /*byte2*/0,
1843                                 /*minimum_cmd_size*/ softc->minimum_cmd_size,
1844                                 offset / secsize,
1845                                 length / secsize,
1846                                 /*data_ptr*/(u_int8_t *) virtual,
1847                                 /*dxfer_len*/length,
1848                                 /*sense_len*/SSD_FULL_SIZE,
1849                                 da_default_timeout * 1000);
1850                 error = cam_periph_runccb((union ccb *)&csio, cam_periph_error,
1851                     0, SF_NO_RECOVERY | SF_NO_RETRY, NULL);
1852                 if (error != 0)
1853                         printf("Aborting dump due to I/O error.\n");
1854                 return (error);
1855         }
1856                 
1857         /*
1858          * Sync the disk cache contents to the physical media.
1859          */
1860         if ((softc->quirks & DA_Q_NO_SYNC_CACHE) == 0) {
1861
1862                 xpt_setup_ccb(&csio.ccb_h, periph->path, CAM_PRIORITY_NORMAL);
1863                 csio.ccb_h.ccb_state = DA_CCB_DUMP;
1864                 scsi_synchronize_cache(&csio,
1865                                        /*retries*/0,
1866                                        /*cbfcnp*/NULL,
1867                                        MSG_SIMPLE_Q_TAG,
1868                                        /*begin_lba*/0,/* Cover the whole disk */
1869                                        /*lb_count*/0,
1870                                        SSD_FULL_SIZE,
1871                                        5 * 1000);
1872                 error = cam_periph_runccb((union ccb *)&csio, cam_periph_error,
1873                     0, SF_NO_RECOVERY | SF_NO_RETRY, NULL);
1874                 if (error != 0)
1875                         xpt_print(periph->path, "Synchronize cache failed\n");
1876         }
1877         return (error);
1878 }
1879
1880 static int
1881 dagetattr(struct bio *bp)
1882 {
1883         int ret;
1884         struct cam_periph *periph;
1885
1886         periph = (struct cam_periph *)bp->bio_disk->d_drv1;
1887         cam_periph_lock(periph);
1888         ret = xpt_getattr(bp->bio_data, bp->bio_length, bp->bio_attribute,
1889             periph->path);
1890         cam_periph_unlock(periph);
1891         if (ret == 0)
1892                 bp->bio_completed = bp->bio_length;
1893         return ret;
1894 }
1895
1896 static void
1897 dainit(void)
1898 {
1899         cam_status status;
1900
1901         /*
1902          * Install a global async callback.  This callback will
1903          * receive async callbacks like "new device found".
1904          */
1905         status = xpt_register_async(AC_FOUND_DEVICE, daasync, NULL, NULL);
1906
1907         if (status != CAM_REQ_CMP) {
1908                 printf("da: Failed to attach master async callback "
1909                        "due to status 0x%x!\n", status);
1910         } else if (da_send_ordered) {
1911
1912                 /* Register our shutdown event handler */
1913                 if ((EVENTHANDLER_REGISTER(shutdown_post_sync, dashutdown, 
1914                                            NULL, SHUTDOWN_PRI_DEFAULT)) == NULL)
1915                     printf("dainit: shutdown event registration failed!\n");
1916         }
1917 }
1918
1919 /*
1920  * Callback from GEOM, called when it has finished cleaning up its
1921  * resources.
1922  */
1923 static void
1924 dadiskgonecb(struct disk *dp)
1925 {
1926         struct cam_periph *periph;
1927
1928         periph = (struct cam_periph *)dp->d_drv1;
1929         da_periph_release(periph, DA_REF_GEOM);
1930 }
1931
1932 static void
1933 daoninvalidate(struct cam_periph *periph)
1934 {
1935         struct da_softc *softc;
1936
1937         cam_periph_assert(periph, MA_OWNED);
1938         softc = (struct da_softc *)periph->softc;
1939
1940         /*
1941          * De-register any async callbacks.
1942          */
1943         xpt_register_async(0, daasync, periph, periph->path);
1944
1945         softc->flags |= DA_FLAG_PACK_INVALID;
1946 #ifdef CAM_IO_STATS
1947         softc->invalidations++;
1948 #endif
1949
1950         /*
1951          * Return all queued I/O with ENXIO.
1952          * XXX Handle any transactions queued to the card
1953          *     with XPT_ABORT_CCB.
1954          */
1955         cam_iosched_flush(softc->cam_iosched, NULL, ENXIO);
1956
1957         /*
1958          * Tell GEOM that we've gone away, we'll get a callback when it is
1959          * done cleaning up its resources.
1960          */
1961         disk_gone(softc->disk);
1962 }
1963
1964 static void
1965 dacleanup(struct cam_periph *periph)
1966 {
1967         struct da_softc *softc;
1968
1969         softc = (struct da_softc *)periph->softc;
1970
1971         cam_periph_unlock(periph);
1972
1973         cam_iosched_fini(softc->cam_iosched);
1974
1975         /*
1976          * If we can't free the sysctl tree, oh well...
1977          */
1978         if ((softc->flags & DA_FLAG_SCTX_INIT) != 0) {
1979 #ifdef CAM_IO_STATS
1980                 if (sysctl_ctx_free(&softc->sysctl_stats_ctx) != 0)
1981                         xpt_print(periph->path,
1982                             "can't remove sysctl stats context\n");
1983 #endif
1984                 if (sysctl_ctx_free(&softc->sysctl_ctx) != 0)
1985                         xpt_print(periph->path,
1986                             "can't remove sysctl context\n");
1987         }
1988
1989         callout_drain(&softc->mediapoll_c);
1990         disk_destroy(softc->disk);
1991         callout_drain(&softc->sendordered_c);
1992         free(softc, M_DEVBUF);
1993         cam_periph_lock(periph);
1994 }
1995
1996 static void
1997 daasync(void *callback_arg, u_int32_t code,
1998         struct cam_path *path, void *arg)
1999 {
2000         struct cam_periph *periph;
2001         struct da_softc *softc;
2002
2003         periph = (struct cam_periph *)callback_arg;
2004         switch (code) {
2005         case AC_FOUND_DEVICE:
2006         {
2007                 struct ccb_getdev *cgd;
2008                 cam_status status;
2009  
2010                 cgd = (struct ccb_getdev *)arg;
2011                 if (cgd == NULL)
2012                         break;
2013
2014                 if (cgd->protocol != PROTO_SCSI)
2015                         break;
2016                 if (SID_QUAL(&cgd->inq_data) != SID_QUAL_LU_CONNECTED)
2017                         break;
2018                 if (SID_TYPE(&cgd->inq_data) != T_DIRECT
2019                     && SID_TYPE(&cgd->inq_data) != T_RBC
2020                     && SID_TYPE(&cgd->inq_data) != T_OPTICAL
2021                     && SID_TYPE(&cgd->inq_data) != T_ZBC_HM)
2022                         break;
2023
2024                 /*
2025                  * Allocate a peripheral instance for
2026                  * this device and start the probe
2027                  * process.
2028                  */
2029                 status = cam_periph_alloc(daregister, daoninvalidate,
2030                                           dacleanup, dastart,
2031                                           "da", CAM_PERIPH_BIO,
2032                                           path, daasync,
2033                                           AC_FOUND_DEVICE, cgd);
2034
2035                 if (status != CAM_REQ_CMP
2036                  && status != CAM_REQ_INPROG)
2037                         printf("daasync: Unable to attach to new device "
2038                                 "due to status 0x%x\n", status);
2039                 return;
2040         }
2041         case AC_ADVINFO_CHANGED:
2042         {
2043                 uintptr_t buftype;
2044
2045                 buftype = (uintptr_t)arg;
2046                 if (buftype == CDAI_TYPE_PHYS_PATH) {
2047                         struct da_softc *softc;
2048
2049                         softc = periph->softc;
2050                         disk_attr_changed(softc->disk, "GEOM::physpath",
2051                                           M_NOWAIT);
2052                 }
2053                 break;
2054         }
2055         case AC_UNIT_ATTENTION:
2056         {
2057                 union ccb *ccb;
2058                 int error_code, sense_key, asc, ascq;
2059
2060                 softc = (struct da_softc *)periph->softc;
2061                 ccb = (union ccb *)arg;
2062
2063                 /*
2064                  * Handle all UNIT ATTENTIONs except our own,
2065                  * as they will be handled by daerror().
2066                  */
2067                 if (xpt_path_periph(ccb->ccb_h.path) != periph &&
2068                     scsi_extract_sense_ccb(ccb,
2069                      &error_code, &sense_key, &asc, &ascq)) {
2070                         if (asc == 0x2A && ascq == 0x09) {
2071                                 xpt_print(ccb->ccb_h.path,
2072                                     "Capacity data has changed\n");
2073                                 cam_periph_lock(periph);
2074                                 softc->flags &= ~DA_FLAG_PROBED;
2075                                 cam_periph_unlock(periph);
2076                                 dareprobe(periph);
2077                         } else if (asc == 0x28 && ascq == 0x00) {
2078                                 cam_periph_lock(periph);
2079                                 softc->flags &= ~DA_FLAG_PROBED;
2080                                 cam_periph_unlock(periph);
2081                                 disk_media_changed(softc->disk, M_NOWAIT);
2082                         } else if (asc == 0x3F && ascq == 0x03) {
2083                                 xpt_print(ccb->ccb_h.path,
2084                                     "INQUIRY data has changed\n");
2085                                 cam_periph_lock(periph);
2086                                 softc->flags &= ~DA_FLAG_PROBED;
2087                                 cam_periph_unlock(periph);
2088                                 dareprobe(periph);
2089                         }
2090                 }
2091                 break;
2092         }
2093         case AC_SCSI_AEN:
2094                 softc = (struct da_softc *)periph->softc;
2095                 cam_periph_lock(periph);
2096                 if (!cam_iosched_has_work_flags(softc->cam_iosched, DA_WORK_TUR) &&
2097                     (softc->flags & DA_FLAG_TUR_PENDING) == 0) {
2098                         if (da_periph_acquire(periph, DA_REF_TUR) == 0) {
2099                                 cam_iosched_set_work_flags(softc->cam_iosched, DA_WORK_TUR);
2100                                 daschedule(periph);
2101                         }
2102                 }
2103                 cam_periph_unlock(periph);
2104                 /* FALLTHROUGH */
2105         case AC_SENT_BDR:
2106         case AC_BUS_RESET:
2107         {
2108                 struct ccb_hdr *ccbh;
2109
2110                 softc = (struct da_softc *)periph->softc;
2111                 /*
2112                  * Don't fail on the expected unit attention
2113                  * that will occur.
2114                  */
2115                 cam_periph_lock(periph);
2116                 softc->flags |= DA_FLAG_RETRY_UA;
2117                 LIST_FOREACH(ccbh, &softc->pending_ccbs, periph_links.le)
2118                         ccbh->ccb_state |= DA_CCB_RETRY_UA;
2119                 cam_periph_unlock(periph);
2120                 break;
2121         }
2122         case AC_INQ_CHANGED:
2123                 cam_periph_lock(periph);
2124                 softc = (struct da_softc *)periph->softc;
2125                 softc->flags &= ~DA_FLAG_PROBED;
2126                 dareprobe(periph);
2127                 cam_periph_unlock(periph);
2128                 break;
2129         default:
2130                 break;
2131         }
2132         cam_periph_async(periph, code, path, arg);
2133 }
2134
2135 static void
2136 dasysctlinit(void *context, int pending)
2137 {
2138         struct cam_periph *periph;
2139         struct da_softc *softc;
2140         char tmpstr[32], tmpstr2[16];
2141         struct ccb_trans_settings cts;
2142
2143         periph = (struct cam_periph *)context;
2144         /*
2145          * periph was held for us when this task was enqueued
2146          */
2147         if (periph->flags & CAM_PERIPH_INVALID) {
2148                 da_periph_release(periph, DA_REF_SYSCTL);
2149                 return;
2150         }
2151
2152         softc = (struct da_softc *)periph->softc;
2153         snprintf(tmpstr, sizeof(tmpstr), "CAM DA unit %d", periph->unit_number);
2154         snprintf(tmpstr2, sizeof(tmpstr2), "%d", periph->unit_number);
2155
2156         sysctl_ctx_init(&softc->sysctl_ctx);
2157         cam_periph_lock(periph);
2158         softc->flags |= DA_FLAG_SCTX_INIT;
2159         cam_periph_unlock(periph);
2160         softc->sysctl_tree = SYSCTL_ADD_NODE_WITH_LABEL(&softc->sysctl_ctx,
2161                 SYSCTL_STATIC_CHILDREN(_kern_cam_da), OID_AUTO, tmpstr2,
2162                 CTLFLAG_RD, 0, tmpstr, "device_index");
2163         if (softc->sysctl_tree == NULL) {
2164                 printf("dasysctlinit: unable to allocate sysctl tree\n");
2165                 da_periph_release(periph, DA_REF_SYSCTL);
2166                 return;
2167         }
2168
2169         /*
2170          * Now register the sysctl handler, so the user can change the value on
2171          * the fly.
2172          */
2173         SYSCTL_ADD_PROC(&softc->sysctl_ctx, SYSCTL_CHILDREN(softc->sysctl_tree),
2174                 OID_AUTO, "delete_method", CTLTYPE_STRING | CTLFLAG_RWTUN,
2175                 softc, 0, dadeletemethodsysctl, "A",
2176                 "BIO_DELETE execution method");
2177         SYSCTL_ADD_PROC(&softc->sysctl_ctx, SYSCTL_CHILDREN(softc->sysctl_tree),
2178                 OID_AUTO, "delete_max", CTLTYPE_U64 | CTLFLAG_RW,
2179                 softc, 0, dadeletemaxsysctl, "Q",
2180                 "Maximum BIO_DELETE size");
2181         SYSCTL_ADD_PROC(&softc->sysctl_ctx, SYSCTL_CHILDREN(softc->sysctl_tree),
2182                 OID_AUTO, "minimum_cmd_size", CTLTYPE_INT | CTLFLAG_RW,
2183                 &softc->minimum_cmd_size, 0, dacmdsizesysctl, "I",
2184                 "Minimum CDB size");
2185
2186         SYSCTL_ADD_PROC(&softc->sysctl_ctx, SYSCTL_CHILDREN(softc->sysctl_tree),
2187                 OID_AUTO, "zone_mode", CTLTYPE_STRING | CTLFLAG_RD,
2188                 softc, 0, dazonemodesysctl, "A",
2189                 "Zone Mode");
2190         SYSCTL_ADD_PROC(&softc->sysctl_ctx, SYSCTL_CHILDREN(softc->sysctl_tree),
2191                 OID_AUTO, "zone_support", CTLTYPE_STRING | CTLFLAG_RD,
2192                 softc, 0, dazonesupsysctl, "A",
2193                 "Zone Support");
2194         SYSCTL_ADD_UQUAD(&softc->sysctl_ctx,
2195                 SYSCTL_CHILDREN(softc->sysctl_tree), OID_AUTO,
2196                 "optimal_seq_zones", CTLFLAG_RD, &softc->optimal_seq_zones,
2197                 "Optimal Number of Open Sequential Write Preferred Zones");
2198         SYSCTL_ADD_UQUAD(&softc->sysctl_ctx,
2199                 SYSCTL_CHILDREN(softc->sysctl_tree), OID_AUTO,
2200                 "optimal_nonseq_zones", CTLFLAG_RD,
2201                 &softc->optimal_nonseq_zones,
2202                 "Optimal Number of Non-Sequentially Written Sequential Write "
2203                 "Preferred Zones");
2204         SYSCTL_ADD_UQUAD(&softc->sysctl_ctx,
2205                 SYSCTL_CHILDREN(softc->sysctl_tree), OID_AUTO,
2206                 "max_seq_zones", CTLFLAG_RD, &softc->max_seq_zones,
2207                 "Maximum Number of Open Sequential Write Required Zones");
2208
2209         SYSCTL_ADD_INT(&softc->sysctl_ctx,
2210                        SYSCTL_CHILDREN(softc->sysctl_tree),
2211                        OID_AUTO,
2212                        "error_inject",
2213                        CTLFLAG_RW,
2214                        &softc->error_inject,
2215                        0,
2216                        "error_inject leaf");
2217
2218         SYSCTL_ADD_INT(&softc->sysctl_ctx,
2219                        SYSCTL_CHILDREN(softc->sysctl_tree),
2220                        OID_AUTO,
2221                        "unmapped_io",
2222                        CTLFLAG_RD, 
2223                        &softc->unmappedio,
2224                        0,
2225                        "Unmapped I/O leaf");
2226
2227         SYSCTL_ADD_INT(&softc->sysctl_ctx,
2228                        SYSCTL_CHILDREN(softc->sysctl_tree),
2229                        OID_AUTO,
2230                        "rotating",
2231                        CTLFLAG_RD, 
2232                        &softc->rotating,
2233                        0,
2234                        "Rotating media");
2235
2236 #ifdef CAM_TEST_FAILURE
2237         SYSCTL_ADD_PROC(&softc->sysctl_ctx, SYSCTL_CHILDREN(softc->sysctl_tree),
2238                 OID_AUTO, "invalidate", CTLTYPE_U64 | CTLFLAG_RW | CTLFLAG_MPSAFE,
2239                 periph, 0, cam_periph_invalidate_sysctl, "I",
2240                 "Write 1 to invalidate the drive immediately");
2241 #endif
2242
2243         /*
2244          * Add some addressing info.
2245          */
2246         memset(&cts, 0, sizeof (cts));
2247         xpt_setup_ccb(&cts.ccb_h, periph->path, CAM_PRIORITY_NONE);
2248         cts.ccb_h.func_code = XPT_GET_TRAN_SETTINGS;
2249         cts.type = CTS_TYPE_CURRENT_SETTINGS;
2250         cam_periph_lock(periph);
2251         xpt_action((union ccb *)&cts);
2252         cam_periph_unlock(periph);
2253         if (cts.ccb_h.status != CAM_REQ_CMP) {
2254                 da_periph_release(periph, DA_REF_SYSCTL);
2255                 return;
2256         }
2257         if (cts.protocol == PROTO_SCSI && cts.transport == XPORT_FC) {
2258                 struct ccb_trans_settings_fc *fc = &cts.xport_specific.fc;
2259                 if (fc->valid & CTS_FC_VALID_WWPN) {
2260                         softc->wwpn = fc->wwpn;
2261                         SYSCTL_ADD_UQUAD(&softc->sysctl_ctx,
2262                             SYSCTL_CHILDREN(softc->sysctl_tree),
2263                             OID_AUTO, "wwpn", CTLFLAG_RD,
2264                             &softc->wwpn, "World Wide Port Name");
2265                 }
2266         }
2267
2268 #ifdef CAM_IO_STATS
2269         /*
2270          * Now add some useful stats.
2271          * XXX These should live in cam_periph and be common to all periphs
2272          */
2273         softc->sysctl_stats_tree = SYSCTL_ADD_NODE(&softc->sysctl_stats_ctx,
2274             SYSCTL_CHILDREN(softc->sysctl_tree), OID_AUTO, "stats",
2275             CTLFLAG_RD, 0, "Statistics");
2276         SYSCTL_ADD_INT(&softc->sysctl_stats_ctx,
2277                        SYSCTL_CHILDREN(softc->sysctl_stats_tree),
2278                        OID_AUTO,
2279                        "errors",
2280                        CTLFLAG_RD,
2281                        &softc->errors,
2282                        0,
2283                        "Transport errors reported by the SIM");
2284         SYSCTL_ADD_INT(&softc->sysctl_stats_ctx,
2285                        SYSCTL_CHILDREN(softc->sysctl_stats_tree),
2286                        OID_AUTO,
2287                        "timeouts",
2288                        CTLFLAG_RD,
2289                        &softc->timeouts,
2290                        0,
2291                        "Device timeouts reported by the SIM");
2292         SYSCTL_ADD_INT(&softc->sysctl_stats_ctx,
2293                        SYSCTL_CHILDREN(softc->sysctl_stats_tree),
2294                        OID_AUTO,
2295                        "pack_invalidations",
2296                        CTLFLAG_RD,
2297                        &softc->invalidations,
2298                        0,
2299                        "Device pack invalidations");
2300 #endif
2301
2302         cam_iosched_sysctl_init(softc->cam_iosched, &softc->sysctl_ctx,
2303             softc->sysctl_tree);
2304
2305         da_periph_release(periph, DA_REF_SYSCTL);
2306 }
2307
2308 static int
2309 dadeletemaxsysctl(SYSCTL_HANDLER_ARGS)
2310 {
2311         int error;
2312         uint64_t value;
2313         struct da_softc *softc;
2314
2315         softc = (struct da_softc *)arg1;
2316
2317         value = softc->disk->d_delmaxsize;
2318         error = sysctl_handle_64(oidp, &value, 0, req);
2319         if ((error != 0) || (req->newptr == NULL))
2320                 return (error);
2321
2322         /* only accept values smaller than the calculated value */
2323         if (value > dadeletemaxsize(softc, softc->delete_method)) {
2324                 return (EINVAL);
2325         }
2326         softc->disk->d_delmaxsize = value;
2327
2328         return (0);
2329 }
2330
2331 static int
2332 dacmdsizesysctl(SYSCTL_HANDLER_ARGS)
2333 {
2334         int error, value;
2335
2336         value = *(int *)arg1;
2337
2338         error = sysctl_handle_int(oidp, &value, 0, req);
2339
2340         if ((error != 0)
2341          || (req->newptr == NULL))
2342                 return (error);
2343
2344         /*
2345          * Acceptable values here are 6, 10, 12 or 16.
2346          */
2347         if (value < 6)
2348                 value = 6;
2349         else if ((value > 6)
2350               && (value <= 10))
2351                 value = 10;
2352         else if ((value > 10)
2353               && (value <= 12))
2354                 value = 12;
2355         else if (value > 12)
2356                 value = 16;
2357
2358         *(int *)arg1 = value;
2359
2360         return (0);
2361 }
2362
2363 static int
2364 dasysctlsofttimeout(SYSCTL_HANDLER_ARGS)
2365 {
2366         sbintime_t value;
2367         int error;
2368
2369         value = da_default_softtimeout / SBT_1MS;
2370
2371         error = sysctl_handle_int(oidp, (int *)&value, 0, req);
2372         if ((error != 0) || (req->newptr == NULL))
2373                 return (error);
2374
2375         /* XXX Should clip this to a reasonable level */
2376         if (value > da_default_timeout * 1000)
2377                 return (EINVAL);
2378
2379         da_default_softtimeout = value * SBT_1MS;
2380         return (0);
2381 }
2382
2383 static void
2384 dadeletemethodset(struct da_softc *softc, da_delete_methods delete_method)
2385 {
2386
2387         softc->delete_method = delete_method;
2388         softc->disk->d_delmaxsize = dadeletemaxsize(softc, delete_method);
2389         softc->delete_func = da_delete_functions[delete_method];
2390
2391         if (softc->delete_method > DA_DELETE_DISABLE)
2392                 softc->disk->d_flags |= DISKFLAG_CANDELETE;
2393         else
2394                 softc->disk->d_flags &= ~DISKFLAG_CANDELETE;
2395 }
2396
2397 static off_t
2398 dadeletemaxsize(struct da_softc *softc, da_delete_methods delete_method)
2399 {
2400         off_t sectors;
2401
2402         switch(delete_method) {
2403         case DA_DELETE_UNMAP:
2404                 sectors = (off_t)softc->unmap_max_lba;
2405                 break;
2406         case DA_DELETE_ATA_TRIM:
2407                 sectors = (off_t)ATA_DSM_RANGE_MAX * softc->trim_max_ranges;
2408                 break;
2409         case DA_DELETE_WS16:
2410                 sectors = omin(softc->ws_max_blks, WS16_MAX_BLKS);
2411                 break;
2412         case DA_DELETE_ZERO:
2413         case DA_DELETE_WS10:
2414                 sectors = omin(softc->ws_max_blks, WS10_MAX_BLKS);
2415                 break;
2416         default:
2417                 return 0;
2418         }
2419
2420         return (off_t)softc->params.secsize *
2421             omin(sectors, softc->params.sectors);
2422 }
2423
2424 static void
2425 daprobedone(struct cam_periph *periph, union ccb *ccb)
2426 {
2427         struct da_softc *softc;
2428
2429         softc = (struct da_softc *)periph->softc;
2430
2431         cam_periph_assert(periph, MA_OWNED);
2432
2433         dadeletemethodchoose(softc, DA_DELETE_NONE);
2434
2435         if (bootverbose && (softc->flags & DA_FLAG_ANNOUNCED) == 0) {
2436                 char buf[80];
2437                 int i, sep;
2438
2439                 snprintf(buf, sizeof(buf), "Delete methods: <");
2440                 sep = 0;
2441                 for (i = 0; i <= DA_DELETE_MAX; i++) {
2442                         if ((softc->delete_available & (1 << i)) == 0 &&
2443                             i != softc->delete_method)
2444                                 continue;
2445                         if (sep)
2446                                 strlcat(buf, ",", sizeof(buf));
2447                         strlcat(buf, da_delete_method_names[i],
2448                             sizeof(buf));
2449                         if (i == softc->delete_method)
2450                                 strlcat(buf, "(*)", sizeof(buf));
2451                         sep = 1;
2452                 }
2453                 strlcat(buf, ">", sizeof(buf));
2454                 printf("%s%d: %s\n", periph->periph_name,
2455                     periph->unit_number, buf);
2456         }
2457
2458         /*
2459          * Since our peripheral may be invalidated by an error
2460          * above or an external event, we must release our CCB
2461          * before releasing the probe lock on the peripheral.
2462          * The peripheral will only go away once the last lock
2463          * is removed, and we need it around for the CCB release
2464          * operation.
2465          */
2466         xpt_release_ccb(ccb);
2467         softc->state = DA_STATE_NORMAL;
2468         softc->flags |= DA_FLAG_PROBED;
2469         daschedule(periph);
2470         wakeup(&softc->disk->d_mediasize);
2471         if ((softc->flags & DA_FLAG_ANNOUNCED) == 0) {
2472                 softc->flags |= DA_FLAG_ANNOUNCED;
2473                 da_periph_unhold(periph, DA_REF_PROBE_HOLD);
2474         } else
2475                 da_periph_release_locked(periph, DA_REF_REPROBE);
2476 }
2477
2478 static void
2479 dadeletemethodchoose(struct da_softc *softc, da_delete_methods default_method)
2480 {
2481         int i, methods;
2482
2483         /* If available, prefer the method requested by user. */
2484         i = softc->delete_method_pref;
2485         methods = softc->delete_available | (1 << DA_DELETE_DISABLE);
2486         if (methods & (1 << i)) {
2487                 dadeletemethodset(softc, i);
2488                 return;
2489         }
2490
2491         /* Use the pre-defined order to choose the best performing delete. */
2492         for (i = DA_DELETE_MIN; i <= DA_DELETE_MAX; i++) {
2493                 if (i == DA_DELETE_ZERO)
2494                         continue;
2495                 if (softc->delete_available & (1 << i)) {
2496                         dadeletemethodset(softc, i);
2497                         return;
2498                 }
2499         }
2500
2501         /* Fallback to default. */
2502         dadeletemethodset(softc, default_method);
2503 }
2504
2505 static int
2506 dadeletemethodsysctl(SYSCTL_HANDLER_ARGS)
2507 {
2508         char buf[16];
2509         const char *p;
2510         struct da_softc *softc;
2511         int i, error, value;
2512
2513         softc = (struct da_softc *)arg1;
2514
2515         value = softc->delete_method;
2516         if (value < 0 || value > DA_DELETE_MAX)
2517                 p = "UNKNOWN";
2518         else
2519                 p = da_delete_method_names[value];
2520         strncpy(buf, p, sizeof(buf));
2521         error = sysctl_handle_string(oidp, buf, sizeof(buf), req);
2522         if (error != 0 || req->newptr == NULL)
2523                 return (error);
2524         for (i = 0; i <= DA_DELETE_MAX; i++) {
2525                 if (strcmp(buf, da_delete_method_names[i]) == 0)
2526                         break;
2527         }
2528         if (i > DA_DELETE_MAX)
2529                 return (EINVAL);
2530         softc->delete_method_pref = i;
2531         dadeletemethodchoose(softc, DA_DELETE_NONE);
2532         return (0);
2533 }
2534
2535 static int
2536 dazonemodesysctl(SYSCTL_HANDLER_ARGS)
2537 {
2538         char tmpbuf[40];
2539         struct da_softc *softc;
2540         int error;
2541
2542         softc = (struct da_softc *)arg1;
2543
2544         switch (softc->zone_mode) {
2545         case DA_ZONE_DRIVE_MANAGED:
2546                 snprintf(tmpbuf, sizeof(tmpbuf), "Drive Managed");
2547                 break;
2548         case DA_ZONE_HOST_AWARE:
2549                 snprintf(tmpbuf, sizeof(tmpbuf), "Host Aware");
2550                 break;
2551         case DA_ZONE_HOST_MANAGED:
2552                 snprintf(tmpbuf, sizeof(tmpbuf), "Host Managed");
2553                 break;
2554         case DA_ZONE_NONE:
2555         default:
2556                 snprintf(tmpbuf, sizeof(tmpbuf), "Not Zoned");
2557                 break;
2558         }
2559
2560         error = sysctl_handle_string(oidp, tmpbuf, sizeof(tmpbuf), req);
2561
2562         return (error);
2563 }
2564
2565 static int
2566 dazonesupsysctl(SYSCTL_HANDLER_ARGS)
2567 {
2568         char tmpbuf[180];
2569         struct da_softc *softc;
2570         struct sbuf sb;
2571         int error, first;
2572         unsigned int i;
2573
2574         softc = (struct da_softc *)arg1;
2575
2576         error = 0;
2577         first = 1;
2578         sbuf_new(&sb, tmpbuf, sizeof(tmpbuf), 0);
2579
2580         for (i = 0; i < sizeof(da_zone_desc_table) /
2581              sizeof(da_zone_desc_table[0]); i++) {
2582                 if (softc->zone_flags & da_zone_desc_table[i].value) {
2583                         if (first == 0)
2584                                 sbuf_printf(&sb, ", ");
2585                         else
2586                                 first = 0;
2587                         sbuf_cat(&sb, da_zone_desc_table[i].desc);
2588                 }
2589         }
2590
2591         if (first == 1)
2592                 sbuf_printf(&sb, "None");
2593
2594         sbuf_finish(&sb);
2595
2596         error = sysctl_handle_string(oidp, sbuf_data(&sb), sbuf_len(&sb), req);
2597
2598         return (error);
2599 }
2600
2601 static cam_status
2602 daregister(struct cam_periph *periph, void *arg)
2603 {
2604         struct da_softc *softc;
2605         struct ccb_pathinq cpi;
2606         struct ccb_getdev *cgd;
2607         char tmpstr[80];
2608         caddr_t match;
2609
2610         cgd = (struct ccb_getdev *)arg;
2611         if (cgd == NULL) {
2612                 printf("daregister: no getdev CCB, can't register device\n");
2613                 return(CAM_REQ_CMP_ERR);
2614         }
2615
2616         softc = (struct da_softc *)malloc(sizeof(*softc), M_DEVBUF,
2617             M_NOWAIT|M_ZERO);
2618
2619         if (softc == NULL) {
2620                 printf("daregister: Unable to probe new device. "
2621                        "Unable to allocate softc\n");
2622                 return(CAM_REQ_CMP_ERR);
2623         }
2624
2625         if (cam_iosched_init(&softc->cam_iosched, periph) != 0) {
2626                 printf("daregister: Unable to probe new device. "
2627                        "Unable to allocate iosched memory\n");
2628                 free(softc, M_DEVBUF);
2629                 return(CAM_REQ_CMP_ERR);
2630         }
2631         
2632         LIST_INIT(&softc->pending_ccbs);
2633         softc->state = DA_STATE_PROBE_WP;
2634         bioq_init(&softc->delete_run_queue);
2635         if (SID_IS_REMOVABLE(&cgd->inq_data))
2636                 softc->flags |= DA_FLAG_PACK_REMOVABLE;
2637         softc->unmap_max_ranges = UNMAP_MAX_RANGES;
2638         softc->unmap_max_lba = UNMAP_RANGE_MAX;
2639         softc->unmap_gran = 0;
2640         softc->unmap_gran_align = 0;
2641         softc->ws_max_blks = WS16_MAX_BLKS;
2642         softc->trim_max_ranges = ATA_TRIM_MAX_RANGES;
2643         softc->rotating = 1;
2644
2645         periph->softc = softc;
2646
2647         /*
2648          * See if this device has any quirks.
2649          */
2650         match = cam_quirkmatch((caddr_t)&cgd->inq_data,
2651                                (caddr_t)da_quirk_table,
2652                                nitems(da_quirk_table),
2653                                sizeof(*da_quirk_table), scsi_inquiry_match);
2654
2655         if (match != NULL)
2656                 softc->quirks = ((struct da_quirk_entry *)match)->quirks;
2657         else
2658                 softc->quirks = DA_Q_NONE;
2659
2660         /* Check if the SIM does not want 6 byte commands */
2661         xpt_path_inq(&cpi, periph->path);
2662         if (cpi.ccb_h.status == CAM_REQ_CMP && (cpi.hba_misc & PIM_NO_6_BYTE))
2663                 softc->quirks |= DA_Q_NO_6_BYTE;
2664
2665         if (SID_TYPE(&cgd->inq_data) == T_ZBC_HM)
2666                 softc->zone_mode = DA_ZONE_HOST_MANAGED;
2667         else if (softc->quirks & DA_Q_SMR_DM)
2668                 softc->zone_mode = DA_ZONE_DRIVE_MANAGED;
2669         else
2670                 softc->zone_mode = DA_ZONE_NONE;
2671
2672         if (softc->zone_mode != DA_ZONE_NONE) {
2673                 if (scsi_vpd_supported_page(periph, SVPD_ATA_INFORMATION)) {
2674                         if (scsi_vpd_supported_page(periph, SVPD_ZONED_BDC))
2675                                 softc->zone_interface = DA_ZONE_IF_ATA_SAT;
2676                         else
2677                                 softc->zone_interface = DA_ZONE_IF_ATA_PASS;
2678                 } else
2679                         softc->zone_interface = DA_ZONE_IF_SCSI;
2680         }
2681
2682         TASK_INIT(&softc->sysctl_task, 0, dasysctlinit, periph);
2683
2684         /*
2685          * Take an exclusive refcount on the periph while dastart is called
2686          * to finish the probe.  The reference will be dropped in dadone at
2687          * the end of probe.
2688          *
2689          * XXX if cam_periph_hold returns an error, we don't hold a refcount.
2690          */
2691         (void)da_periph_hold(periph, PRIBIO, DA_REF_PROBE_HOLD);
2692
2693         /*
2694          * Schedule a periodic event to occasionally send an
2695          * ordered tag to a device.
2696          */
2697         callout_init_mtx(&softc->sendordered_c, cam_periph_mtx(periph), 0);
2698         callout_reset(&softc->sendordered_c,
2699             (da_default_timeout * hz) / DA_ORDEREDTAG_INTERVAL,
2700             dasendorderedtag, periph);
2701
2702         cam_periph_unlock(periph);
2703         /*
2704          * RBC devices don't have to support READ(6), only READ(10).
2705          */
2706         if (softc->quirks & DA_Q_NO_6_BYTE || SID_TYPE(&cgd->inq_data) == T_RBC)
2707                 softc->minimum_cmd_size = 10;
2708         else
2709                 softc->minimum_cmd_size = 6;
2710
2711         /*
2712          * Load the user's default, if any.
2713          */
2714         snprintf(tmpstr, sizeof(tmpstr), "kern.cam.da.%d.minimum_cmd_size",
2715                  periph->unit_number);
2716         TUNABLE_INT_FETCH(tmpstr, &softc->minimum_cmd_size);
2717
2718         /*
2719          * 6, 10, 12 and 16 are the currently permissible values.
2720          */
2721         if (softc->minimum_cmd_size > 12)
2722                 softc->minimum_cmd_size = 16;
2723         else if (softc->minimum_cmd_size > 10)
2724                 softc->minimum_cmd_size = 12;
2725         else if (softc->minimum_cmd_size > 6)
2726                 softc->minimum_cmd_size = 10;
2727         else
2728                 softc->minimum_cmd_size = 6;
2729                 
2730         /* Predict whether device may support READ CAPACITY(16). */
2731         if (SID_ANSI_REV(&cgd->inq_data) >= SCSI_REV_SPC3 &&
2732             (softc->quirks & DA_Q_NO_RC16) == 0) {
2733                 softc->flags |= DA_FLAG_CAN_RC16;
2734         }
2735
2736         /*
2737          * Register this media as a disk.
2738          */
2739         softc->disk = disk_alloc();
2740         softc->disk->d_devstat = devstat_new_entry(periph->periph_name,
2741                           periph->unit_number, 0,
2742                           DEVSTAT_BS_UNAVAILABLE,
2743                           SID_TYPE(&cgd->inq_data) |
2744                           XPORT_DEVSTAT_TYPE(cpi.transport),
2745                           DEVSTAT_PRIORITY_DISK);
2746         softc->disk->d_open = daopen;
2747         softc->disk->d_close = daclose;
2748         softc->disk->d_strategy = dastrategy;
2749         softc->disk->d_dump = dadump;
2750         softc->disk->d_getattr = dagetattr;
2751         softc->disk->d_gone = dadiskgonecb;
2752         softc->disk->d_name = "da";
2753         softc->disk->d_drv1 = periph;
2754         if (cpi.maxio == 0)
2755                 softc->maxio = DFLTPHYS;        /* traditional default */
2756         else if (cpi.maxio > MAXPHYS)
2757                 softc->maxio = MAXPHYS;         /* for safety */
2758         else
2759                 softc->maxio = cpi.maxio;
2760         softc->disk->d_maxsize = softc->maxio;
2761         softc->disk->d_unit = periph->unit_number;
2762         softc->disk->d_flags = DISKFLAG_DIRECT_COMPLETION | DISKFLAG_CANZONE;
2763         if ((softc->quirks & DA_Q_NO_SYNC_CACHE) == 0)
2764                 softc->disk->d_flags |= DISKFLAG_CANFLUSHCACHE;
2765         if ((cpi.hba_misc & PIM_UNMAPPED) != 0) {
2766                 softc->unmappedio = 1;
2767                 softc->disk->d_flags |= DISKFLAG_UNMAPPED_BIO;
2768         }
2769         cam_strvis(softc->disk->d_descr, cgd->inq_data.vendor,
2770             sizeof(cgd->inq_data.vendor), sizeof(softc->disk->d_descr));
2771         strlcat(softc->disk->d_descr, " ", sizeof(softc->disk->d_descr));
2772         cam_strvis(&softc->disk->d_descr[strlen(softc->disk->d_descr)],
2773             cgd->inq_data.product, sizeof(cgd->inq_data.product),
2774             sizeof(softc->disk->d_descr) - strlen(softc->disk->d_descr));
2775         softc->disk->d_hba_vendor = cpi.hba_vendor;
2776         softc->disk->d_hba_device = cpi.hba_device;
2777         softc->disk->d_hba_subvendor = cpi.hba_subvendor;
2778         softc->disk->d_hba_subdevice = cpi.hba_subdevice;
2779
2780         /*
2781          * Acquire a reference to the periph before we register with GEOM.
2782          * We'll release this reference once GEOM calls us back (via
2783          * dadiskgonecb()) telling us that our provider has been freed.
2784          */
2785         if (da_periph_acquire(periph, DA_REF_GEOM) != 0) {
2786                 xpt_print(periph->path, "%s: lost periph during "
2787                           "registration!\n", __func__);
2788                 cam_periph_lock(periph);
2789                 return (CAM_REQ_CMP_ERR);
2790         }
2791
2792         disk_create(softc->disk, DISK_VERSION);
2793         cam_periph_lock(periph);
2794
2795         /*
2796          * Add async callbacks for events of interest.
2797          * I don't bother checking if this fails as,
2798          * in most cases, the system will function just
2799          * fine without them and the only alternative
2800          * would be to not attach the device on failure.
2801          */
2802         xpt_register_async(AC_SENT_BDR | AC_BUS_RESET | AC_LOST_DEVICE |
2803             AC_ADVINFO_CHANGED | AC_SCSI_AEN | AC_UNIT_ATTENTION |
2804             AC_INQ_CHANGED, daasync, periph, periph->path);
2805
2806         /*
2807          * Emit an attribute changed notification just in case 
2808          * physical path information arrived before our async
2809          * event handler was registered, but after anyone attaching
2810          * to our disk device polled it.
2811          */
2812         disk_attr_changed(softc->disk, "GEOM::physpath", M_NOWAIT);
2813
2814         /*
2815          * Schedule a periodic media polling events.
2816          */
2817         callout_init_mtx(&softc->mediapoll_c, cam_periph_mtx(periph), 0);
2818         if ((softc->flags & DA_FLAG_PACK_REMOVABLE) &&
2819             (cgd->inq_flags & SID_AEN) == 0 &&
2820             da_poll_period != 0)
2821                 callout_reset(&softc->mediapoll_c, da_poll_period * hz,
2822                     damediapoll, periph);
2823
2824         xpt_schedule(periph, CAM_PRIORITY_DEV);
2825
2826         return(CAM_REQ_CMP);
2827 }
2828
2829 static int
2830 da_zone_bio_to_scsi(int disk_zone_cmd)
2831 {
2832         switch (disk_zone_cmd) {
2833         case DISK_ZONE_OPEN:
2834                 return ZBC_OUT_SA_OPEN;
2835         case DISK_ZONE_CLOSE:
2836                 return ZBC_OUT_SA_CLOSE;
2837         case DISK_ZONE_FINISH:
2838                 return ZBC_OUT_SA_FINISH;
2839         case DISK_ZONE_RWP:
2840                 return ZBC_OUT_SA_RWP;
2841         }
2842
2843         return -1;
2844 }
2845
2846 static int
2847 da_zone_cmd(struct cam_periph *periph, union ccb *ccb, struct bio *bp,
2848             int *queue_ccb)
2849 {
2850         struct da_softc *softc;
2851         int error;
2852
2853         error = 0;
2854
2855         if (bp->bio_cmd != BIO_ZONE) {
2856                 error = EINVAL;
2857                 goto bailout;
2858         }
2859
2860         softc = periph->softc;
2861
2862         switch (bp->bio_zone.zone_cmd) {
2863         case DISK_ZONE_OPEN:
2864         case DISK_ZONE_CLOSE:
2865         case DISK_ZONE_FINISH:
2866         case DISK_ZONE_RWP: {
2867                 int zone_flags;
2868                 int zone_sa;
2869                 uint64_t lba;
2870
2871                 zone_sa = da_zone_bio_to_scsi(bp->bio_zone.zone_cmd);
2872                 if (zone_sa == -1) {
2873                         xpt_print(periph->path, "Cannot translate zone "
2874                             "cmd %#x to SCSI\n", bp->bio_zone.zone_cmd);
2875                         error = EINVAL;
2876                         goto bailout;
2877                 }
2878
2879                 zone_flags = 0;
2880                 lba = bp->bio_zone.zone_params.rwp.id;
2881
2882                 if (bp->bio_zone.zone_params.rwp.flags &
2883                     DISK_ZONE_RWP_FLAG_ALL)
2884                         zone_flags |= ZBC_OUT_ALL;
2885
2886                 if (softc->zone_interface != DA_ZONE_IF_ATA_PASS) {
2887                         scsi_zbc_out(&ccb->csio,
2888                                      /*retries*/ da_retry_count,
2889                                      /*cbfcnp*/ dadone,
2890                                      /*tag_action*/ MSG_SIMPLE_Q_TAG,
2891                                      /*service_action*/ zone_sa,
2892                                      /*zone_id*/ lba,
2893                                      /*zone_flags*/ zone_flags,
2894                                      /*data_ptr*/ NULL,
2895                                      /*dxfer_len*/ 0,
2896                                      /*sense_len*/ SSD_FULL_SIZE,
2897                                      /*timeout*/ da_default_timeout * 1000);
2898                 } else {
2899                         /*
2900                          * Note that in this case, even though we can
2901                          * technically use NCQ, we don't bother for several
2902                          * reasons:
2903                          * 1. It hasn't been tested on a SAT layer that
2904                          *    supports it.  This is new as of SAT-4.
2905                          * 2. Even when there is a SAT layer that supports
2906                          *    it, that SAT layer will also probably support
2907                          *    ZBC -> ZAC translation, since they are both
2908                          *    in the SAT-4 spec.
2909                          * 3. Translation will likely be preferable to ATA
2910                          *    passthrough.  LSI / Avago at least single
2911                          *    steps ATA passthrough commands in the HBA,
2912                          *    regardless of protocol, so unless that
2913                          *    changes, there is a performance penalty for
2914                          *    doing ATA passthrough no matter whether
2915                          *    you're using NCQ/FPDMA, DMA or PIO.
2916                          * 4. It requires a 32-byte CDB, which at least at
2917                          *    this point in CAM requires a CDB pointer, which
2918                          *    would require us to allocate an additional bit
2919                          *    of storage separate from the CCB.
2920                          */
2921                         error = scsi_ata_zac_mgmt_out(&ccb->csio,
2922                             /*retries*/ da_retry_count,
2923                             /*cbfcnp*/ dadone,
2924                             /*tag_action*/ MSG_SIMPLE_Q_TAG,
2925                             /*use_ncq*/ 0,
2926                             /*zm_action*/ zone_sa,
2927                             /*zone_id*/ lba,
2928                             /*zone_flags*/ zone_flags,
2929                             /*data_ptr*/ NULL,
2930                             /*dxfer_len*/ 0,
2931                             /*cdb_storage*/ NULL,
2932                             /*cdb_storage_len*/ 0,
2933                             /*sense_len*/ SSD_FULL_SIZE,
2934                             /*timeout*/ da_default_timeout * 1000);
2935                         if (error != 0) {
2936                                 error = EINVAL;
2937                                 xpt_print(periph->path,
2938                                     "scsi_ata_zac_mgmt_out() returned an "
2939                                     "error!");
2940                                 goto bailout;
2941                         }
2942                 }
2943                 *queue_ccb = 1;
2944
2945                 break;
2946         }
2947         case DISK_ZONE_REPORT_ZONES: {
2948                 uint8_t *rz_ptr;
2949                 uint32_t num_entries, alloc_size;
2950                 struct disk_zone_report *rep;
2951
2952                 rep = &bp->bio_zone.zone_params.report;
2953
2954                 num_entries = rep->entries_allocated;
2955                 if (num_entries == 0) {
2956                         xpt_print(periph->path, "No entries allocated for "
2957                             "Report Zones request\n");
2958                         error = EINVAL;
2959                         goto bailout;
2960                 }
2961                 alloc_size = sizeof(struct scsi_report_zones_hdr) +
2962                     (sizeof(struct scsi_report_zones_desc) * num_entries);
2963                 alloc_size = min(alloc_size, softc->disk->d_maxsize);
2964                 rz_ptr = malloc(alloc_size, M_SCSIDA, M_NOWAIT | M_ZERO);
2965                 if (rz_ptr == NULL) {
2966                         xpt_print(periph->path, "Unable to allocate memory "
2967                            "for Report Zones request\n");
2968                         error = ENOMEM;
2969                         goto bailout;
2970                 }
2971                 
2972                 if (softc->zone_interface != DA_ZONE_IF_ATA_PASS) {
2973                         scsi_zbc_in(&ccb->csio,
2974                                     /*retries*/ da_retry_count,
2975                                     /*cbcfnp*/ dadone,
2976                                     /*tag_action*/ MSG_SIMPLE_Q_TAG,
2977                                     /*service_action*/ ZBC_IN_SA_REPORT_ZONES,
2978                                     /*zone_start_lba*/ rep->starting_id,
2979                                     /*zone_options*/ rep->rep_options,
2980                                     /*data_ptr*/ rz_ptr,
2981                                     /*dxfer_len*/ alloc_size,
2982                                     /*sense_len*/ SSD_FULL_SIZE,
2983                                     /*timeout*/ da_default_timeout * 1000);
2984                 } else {
2985                         /*
2986                          * Note that in this case, even though we can
2987                          * technically use NCQ, we don't bother for several
2988                          * reasons:
2989                          * 1. It hasn't been tested on a SAT layer that
2990                          *    supports it.  This is new as of SAT-4.
2991                          * 2. Even when there is a SAT layer that supports
2992                          *    it, that SAT layer will also probably support
2993                          *    ZBC -> ZAC translation, since they are both
2994                          *    in the SAT-4 spec.
2995                          * 3. Translation will likely be preferable to ATA
2996                          *    passthrough.  LSI / Avago at least single
2997                          *    steps ATA passthrough commands in the HBA,
2998                          *    regardless of protocol, so unless that
2999                          *    changes, there is a performance penalty for
3000                          *    doing ATA passthrough no matter whether
3001                          *    you're using NCQ/FPDMA, DMA or PIO.
3002                          * 4. It requires a 32-byte CDB, which at least at
3003                          *    this point in CAM requires a CDB pointer, which
3004                          *    would require us to allocate an additional bit
3005                          *    of storage separate from the CCB.
3006                          */
3007                         error = scsi_ata_zac_mgmt_in(&ccb->csio,
3008                             /*retries*/ da_retry_count,
3009                             /*cbcfnp*/ dadone,
3010                             /*tag_action*/ MSG_SIMPLE_Q_TAG,
3011                             /*use_ncq*/ 0,
3012                             /*zm_action*/ ATA_ZM_REPORT_ZONES,
3013                             /*zone_id*/ rep->starting_id,
3014                             /*zone_flags*/ rep->rep_options,
3015                             /*data_ptr*/ rz_ptr,
3016                             /*dxfer_len*/ alloc_size,
3017                             /*cdb_storage*/ NULL,
3018                             /*cdb_storage_len*/ 0,
3019                             /*sense_len*/ SSD_FULL_SIZE,
3020                             /*timeout*/ da_default_timeout * 1000);
3021                         if (error != 0) {
3022                                 error = EINVAL;
3023                                 xpt_print(periph->path,
3024                                     "scsi_ata_zac_mgmt_in() returned an "
3025                                     "error!");
3026                                 goto bailout;
3027                         }
3028                 }
3029
3030                 /*
3031                  * For BIO_ZONE, this isn't normally needed.  However, it
3032                  * is used by devstat_end_transaction_bio() to determine
3033                  * how much data was transferred.
3034                  */
3035                 /*
3036                  * XXX KDM we have a problem.  But I'm not sure how to fix
3037                  * it.  devstat uses bio_bcount - bio_resid to calculate
3038                  * the amount of data transferred.   The GEOM disk code
3039                  * uses bio_length - bio_resid to calculate the amount of
3040                  * data in bio_completed.  We have different structure
3041                  * sizes above and below the ada(4) driver.  So, if we
3042                  * use the sizes above, the amount transferred won't be
3043                  * quite accurate for devstat.  If we use different sizes
3044                  * for bio_bcount and bio_length (above and below
3045                  * respectively), then the residual needs to match one or
3046                  * the other.  Everything is calculated after the bio
3047                  * leaves the driver, so changing the values around isn't
3048                  * really an option.  For now, just set the count to the
3049                  * passed in length.  This means that the calculations
3050                  * above (e.g. bio_completed) will be correct, but the
3051                  * amount of data reported to devstat will be slightly
3052                  * under or overstated.
3053                  */
3054                 bp->bio_bcount = bp->bio_length;
3055
3056                 *queue_ccb = 1;
3057
3058                 break;
3059         }
3060         case DISK_ZONE_GET_PARAMS: {
3061                 struct disk_zone_disk_params *params;
3062
3063                 params = &bp->bio_zone.zone_params.disk_params;
3064                 bzero(params, sizeof(*params));
3065
3066                 switch (softc->zone_mode) {
3067                 case DA_ZONE_DRIVE_MANAGED:
3068                         params->zone_mode = DISK_ZONE_MODE_DRIVE_MANAGED;
3069                         break;
3070                 case DA_ZONE_HOST_AWARE:
3071                         params->zone_mode = DISK_ZONE_MODE_HOST_AWARE;
3072                         break;
3073                 case DA_ZONE_HOST_MANAGED:
3074                         params->zone_mode = DISK_ZONE_MODE_HOST_MANAGED;
3075                         break;
3076                 default:
3077                 case DA_ZONE_NONE:
3078                         params->zone_mode = DISK_ZONE_MODE_NONE;
3079                         break;
3080                 }
3081
3082                 if (softc->zone_flags & DA_ZONE_FLAG_URSWRZ)
3083                         params->flags |= DISK_ZONE_DISK_URSWRZ;
3084
3085                 if (softc->zone_flags & DA_ZONE_FLAG_OPT_SEQ_SET) {
3086                         params->optimal_seq_zones = softc->optimal_seq_zones;
3087                         params->flags |= DISK_ZONE_OPT_SEQ_SET;
3088                 }
3089
3090                 if (softc->zone_flags & DA_ZONE_FLAG_OPT_NONSEQ_SET) {
3091                         params->optimal_nonseq_zones =
3092                             softc->optimal_nonseq_zones;
3093                         params->flags |= DISK_ZONE_OPT_NONSEQ_SET;
3094                 }
3095
3096                 if (softc->zone_flags & DA_ZONE_FLAG_MAX_SEQ_SET) {
3097                         params->max_seq_zones = softc->max_seq_zones;
3098                         params->flags |= DISK_ZONE_MAX_SEQ_SET;
3099                 }
3100                 if (softc->zone_flags & DA_ZONE_FLAG_RZ_SUP)
3101                         params->flags |= DISK_ZONE_RZ_SUP;
3102
3103                 if (softc->zone_flags & DA_ZONE_FLAG_OPEN_SUP)
3104                         params->flags |= DISK_ZONE_OPEN_SUP;
3105
3106                 if (softc->zone_flags & DA_ZONE_FLAG_CLOSE_SUP)
3107                         params->flags |= DISK_ZONE_CLOSE_SUP;
3108
3109                 if (softc->zone_flags & DA_ZONE_FLAG_FINISH_SUP)
3110                         params->flags |= DISK_ZONE_FINISH_SUP;
3111
3112                 if (softc->zone_flags & DA_ZONE_FLAG_RWP_SUP)
3113                         params->flags |= DISK_ZONE_RWP_SUP;
3114                 break;
3115         }
3116         default:
3117                 break;
3118         }
3119 bailout:
3120         return (error);
3121 }
3122
3123 static void
3124 dastart(struct cam_periph *periph, union ccb *start_ccb)
3125 {
3126         struct da_softc *softc;
3127
3128         cam_periph_assert(periph, MA_OWNED);
3129         softc = (struct da_softc *)periph->softc;
3130
3131         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dastart\n"));
3132
3133 skipstate:
3134         switch (softc->state) {
3135         case DA_STATE_NORMAL:
3136         {
3137                 struct bio *bp;
3138                 uint8_t tag_code;
3139
3140 more:
3141                 bp = cam_iosched_next_bio(softc->cam_iosched);
3142                 if (bp == NULL) {
3143                         if (cam_iosched_has_work_flags(softc->cam_iosched,
3144                             DA_WORK_TUR)) {
3145                                 softc->flags |= DA_FLAG_TUR_PENDING;
3146                                 cam_iosched_clr_work_flags(softc->cam_iosched,
3147                                     DA_WORK_TUR);
3148                                 scsi_test_unit_ready(&start_ccb->csio,
3149                                      /*retries*/ da_retry_count,
3150                                      dadone_tur,
3151                                      MSG_SIMPLE_Q_TAG,
3152                                      SSD_FULL_SIZE,
3153                                      da_default_timeout * 1000);
3154                                 start_ccb->ccb_h.ccb_bp = NULL;
3155                                 start_ccb->ccb_h.ccb_state = DA_CCB_TUR;
3156                                 xpt_action(start_ccb);
3157                         } else
3158                                 xpt_release_ccb(start_ccb);
3159                         break;
3160                 }
3161
3162                 if (bp->bio_cmd == BIO_DELETE) {
3163                         if (softc->delete_func != NULL) {
3164                                 softc->delete_func(periph, start_ccb, bp);
3165                                 goto out;
3166                         } else {
3167                                 /*
3168                                  * Not sure this is possible, but failsafe by
3169                                  * lying and saying "sure, done."
3170                                  */
3171                                 biofinish(bp, NULL, 0);
3172                                 goto more;
3173                         }
3174                 }
3175
3176                 if (cam_iosched_has_work_flags(softc->cam_iosched,
3177                     DA_WORK_TUR)) {
3178                         cam_iosched_clr_work_flags(softc->cam_iosched,
3179                             DA_WORK_TUR);
3180                         da_periph_release_locked(periph, DA_REF_TUR);
3181                 }
3182
3183                 if ((bp->bio_flags & BIO_ORDERED) != 0 ||
3184                     (softc->flags & DA_FLAG_NEED_OTAG) != 0) {
3185                         softc->flags &= ~DA_FLAG_NEED_OTAG;
3186                         softc->flags |= DA_FLAG_WAS_OTAG;
3187                         tag_code = MSG_ORDERED_Q_TAG;
3188                 } else {
3189                         tag_code = MSG_SIMPLE_Q_TAG;
3190                 }
3191
3192                 switch (bp->bio_cmd) {
3193                 case BIO_WRITE:
3194                 case BIO_READ:
3195                 {
3196                         void *data_ptr;
3197                         int rw_op;
3198
3199                         biotrack(bp, __func__);
3200
3201                         if (bp->bio_cmd == BIO_WRITE) {
3202                                 softc->flags |= DA_FLAG_DIRTY;
3203                                 rw_op = SCSI_RW_WRITE;
3204                         } else {
3205                                 rw_op = SCSI_RW_READ;
3206                         }
3207
3208                         data_ptr = bp->bio_data;
3209                         if ((bp->bio_flags & (BIO_UNMAPPED|BIO_VLIST)) != 0) {
3210                                 rw_op |= SCSI_RW_BIO;
3211                                 data_ptr = bp;
3212                         }
3213
3214                         scsi_read_write(&start_ccb->csio,
3215                                         /*retries*/da_retry_count,
3216                                         /*cbfcnp*/dadone,
3217                                         /*tag_action*/tag_code,
3218                                         rw_op,
3219                                         /*byte2*/0,
3220                                         softc->minimum_cmd_size,
3221                                         /*lba*/bp->bio_pblkno,
3222                                         /*block_count*/bp->bio_bcount /
3223                                         softc->params.secsize,
3224                                         data_ptr,
3225                                         /*dxfer_len*/ bp->bio_bcount,
3226                                         /*sense_len*/SSD_FULL_SIZE,
3227                                         da_default_timeout * 1000);
3228 #if defined(BUF_TRACKING) || defined(FULL_BUF_TRACKING)
3229                         start_ccb->csio.bio = bp;
3230 #endif
3231                         break;
3232                 }
3233                 case BIO_FLUSH:
3234                         /*
3235                          * If we don't support sync cache, or the disk
3236                          * isn't dirty, FLUSH is a no-op.  Use the
3237                          * allocated CCB for the next bio if one is
3238                          * available.
3239                          */
3240                         if ((softc->quirks & DA_Q_NO_SYNC_CACHE) != 0 ||
3241                             (softc->flags & DA_FLAG_DIRTY) == 0) {
3242                                 biodone(bp);
3243                                 goto skipstate;
3244                         }
3245
3246                         /*
3247                          * BIO_FLUSH doesn't currently communicate
3248                          * range data, so we synchronize the cache
3249                          * over the whole disk.  We also force
3250                          * ordered tag semantics the flush applies
3251                          * to all previously queued I/O.
3252                          */
3253                         scsi_synchronize_cache(&start_ccb->csio,
3254                                                /*retries*/1,
3255                                                /*cbfcnp*/dadone,
3256                                                MSG_ORDERED_Q_TAG,
3257                                                /*begin_lba*/0,
3258                                                /*lb_count*/0,
3259                                                SSD_FULL_SIZE,
3260                                                da_default_timeout*1000);
3261                         /*
3262                          * Clear the dirty flag before sending the command.
3263                          * Either this sync cache will be successful, or it
3264                          * will fail after a retry.  If it fails, it is
3265                          * unlikely to be successful if retried later, so
3266                          * we'll save ourselves time by just marking the
3267                          * device clean.
3268                          */
3269                         softc->flags &= ~DA_FLAG_DIRTY;
3270                         break;
3271                 case BIO_ZONE: {
3272                         int error, queue_ccb;
3273
3274                         queue_ccb = 0;
3275
3276                         error = da_zone_cmd(periph, start_ccb, bp,&queue_ccb);
3277                         if ((error != 0)
3278                          || (queue_ccb == 0)) {
3279                                 biofinish(bp, NULL, error);
3280                                 xpt_release_ccb(start_ccb);
3281                                 return;
3282                         }
3283                         break;
3284                 }
3285                 }
3286                 start_ccb->ccb_h.ccb_state = DA_CCB_BUFFER_IO;
3287                 start_ccb->ccb_h.flags |= CAM_UNLOCKED;
3288                 start_ccb->ccb_h.softtimeout = sbttotv(da_default_softtimeout);
3289
3290 out:
3291                 LIST_INSERT_HEAD(&softc->pending_ccbs,
3292                                  &start_ccb->ccb_h, periph_links.le);
3293
3294                 /* We expect a unit attention from this device */
3295                 if ((softc->flags & DA_FLAG_RETRY_UA) != 0) {
3296                         start_ccb->ccb_h.ccb_state |= DA_CCB_RETRY_UA;
3297                         softc->flags &= ~DA_FLAG_RETRY_UA;
3298                 }
3299
3300                 start_ccb->ccb_h.ccb_bp = bp;
3301                 softc->refcount++;
3302                 cam_periph_unlock(periph);
3303                 xpt_action(start_ccb);
3304                 cam_periph_lock(periph);
3305
3306                 /* May have more work to do, so ensure we stay scheduled */
3307                 daschedule(periph);
3308                 break;
3309         }
3310         case DA_STATE_PROBE_WP:
3311         {
3312                 void  *mode_buf;
3313                 int    mode_buf_len;
3314
3315                 mode_buf_len = 192;
3316                 mode_buf = malloc(mode_buf_len, M_SCSIDA, M_NOWAIT);
3317                 if (mode_buf == NULL) {
3318                         xpt_print(periph->path, "Unable to send mode sense - "
3319                             "malloc failure\n");
3320                         softc->state = DA_STATE_PROBE_RC;
3321                         goto skipstate;
3322                 }
3323                 scsi_mode_sense_len(&start_ccb->csio,
3324                                     /*retries*/ da_retry_count,
3325                                     /*cbfcnp*/ dadone_probewp,
3326                                     /*tag_action*/ MSG_SIMPLE_Q_TAG,
3327                                     /*dbd*/ FALSE,
3328                                     /*pc*/ SMS_PAGE_CTRL_CURRENT,
3329                                     /*page*/ SMS_ALL_PAGES_PAGE,
3330                                     /*param_buf*/ mode_buf,
3331                                     /*param_len*/ mode_buf_len,
3332                                     /*minimum_cmd_size*/ softc->minimum_cmd_size,
3333                                     /*sense_len*/ SSD_FULL_SIZE,
3334                                     /*timeout*/ da_default_timeout * 1000);
3335                 start_ccb->ccb_h.ccb_bp = NULL;
3336                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_WP;
3337                 xpt_action(start_ccb);
3338                 break;
3339         }
3340         case DA_STATE_PROBE_RC:
3341         {
3342                 struct scsi_read_capacity_data *rcap;
3343
3344                 rcap = (struct scsi_read_capacity_data *)
3345                     malloc(sizeof(*rcap), M_SCSIDA, M_NOWAIT|M_ZERO);
3346                 if (rcap == NULL) {
3347                         printf("dastart: Couldn't malloc read_capacity data\n");
3348                         /* da_free_periph??? */
3349                         break;
3350                 }
3351                 scsi_read_capacity(&start_ccb->csio,
3352                                    /*retries*/da_retry_count,
3353                                    dadone_proberc,
3354                                    MSG_SIMPLE_Q_TAG,
3355                                    rcap,
3356                                    SSD_FULL_SIZE,
3357                                    /*timeout*/5000);
3358                 start_ccb->ccb_h.ccb_bp = NULL;
3359                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_RC;
3360                 xpt_action(start_ccb);
3361                 break;
3362         }
3363         case DA_STATE_PROBE_RC16:
3364         {
3365                 struct scsi_read_capacity_data_long *rcaplong;
3366
3367                 rcaplong = (struct scsi_read_capacity_data_long *)
3368                         malloc(sizeof(*rcaplong), M_SCSIDA, M_NOWAIT|M_ZERO);
3369                 if (rcaplong == NULL) {
3370                         printf("dastart: Couldn't malloc read_capacity data\n");
3371                         /* da_free_periph??? */
3372                         break;
3373                 }
3374                 scsi_read_capacity_16(&start_ccb->csio,
3375                                       /*retries*/ da_retry_count,
3376                                       /*cbfcnp*/ dadone_proberc,
3377                                       /*tag_action*/ MSG_SIMPLE_Q_TAG,
3378                                       /*lba*/ 0,
3379                                       /*reladr*/ 0,
3380                                       /*pmi*/ 0,
3381                                       /*rcap_buf*/ (uint8_t *)rcaplong,
3382                                       /*rcap_buf_len*/ sizeof(*rcaplong),
3383                                       /*sense_len*/ SSD_FULL_SIZE,
3384                                       /*timeout*/ da_default_timeout * 1000);
3385                 start_ccb->ccb_h.ccb_bp = NULL;
3386                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_RC16;
3387                 xpt_action(start_ccb);
3388                 break;
3389         }
3390         case DA_STATE_PROBE_LBP:
3391         {
3392                 struct scsi_vpd_logical_block_prov *lbp;
3393
3394                 if (!scsi_vpd_supported_page(periph, SVPD_LBP)) {
3395                         /*
3396                          * If we get here we don't support any SBC-3 delete
3397                          * methods with UNMAP as the Logical Block Provisioning
3398                          * VPD page support is required for devices which
3399                          * support it according to T10/1799-D Revision 31
3400                          * however older revisions of the spec don't mandate
3401                          * this so we currently don't remove these methods
3402                          * from the available set.
3403                          */
3404                         softc->state = DA_STATE_PROBE_BLK_LIMITS;
3405                         goto skipstate;
3406                 }
3407
3408                 lbp = (struct scsi_vpd_logical_block_prov *)
3409                         malloc(sizeof(*lbp), M_SCSIDA, M_NOWAIT|M_ZERO);
3410
3411                 if (lbp == NULL) {
3412                         printf("dastart: Couldn't malloc lbp data\n");
3413                         /* da_free_periph??? */
3414                         break;
3415                 }
3416
3417                 scsi_inquiry(&start_ccb->csio,
3418                              /*retries*/da_retry_count,
3419                              /*cbfcnp*/dadone_probelbp,
3420                              /*tag_action*/MSG_SIMPLE_Q_TAG,
3421                              /*inq_buf*/(u_int8_t *)lbp,
3422                              /*inq_len*/sizeof(*lbp),
3423                              /*evpd*/TRUE,
3424                              /*page_code*/SVPD_LBP,
3425                              /*sense_len*/SSD_MIN_SIZE,
3426                              /*timeout*/da_default_timeout * 1000);
3427                 start_ccb->ccb_h.ccb_bp = NULL;
3428                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_LBP;
3429                 xpt_action(start_ccb);
3430                 break;
3431         }
3432         case DA_STATE_PROBE_BLK_LIMITS:
3433         {
3434                 struct scsi_vpd_block_limits *block_limits;
3435
3436                 if (!scsi_vpd_supported_page(periph, SVPD_BLOCK_LIMITS)) {
3437                         /* Not supported skip to next probe */
3438                         softc->state = DA_STATE_PROBE_BDC;
3439                         goto skipstate;
3440                 }
3441
3442                 block_limits = (struct scsi_vpd_block_limits *)
3443                         malloc(sizeof(*block_limits), M_SCSIDA, M_NOWAIT|M_ZERO);
3444
3445                 if (block_limits == NULL) {
3446                         printf("dastart: Couldn't malloc block_limits data\n");
3447                         /* da_free_periph??? */
3448                         break;
3449                 }
3450
3451                 scsi_inquiry(&start_ccb->csio,
3452                              /*retries*/da_retry_count,
3453                              /*cbfcnp*/dadone_probeblklimits,
3454                              /*tag_action*/MSG_SIMPLE_Q_TAG,
3455                              /*inq_buf*/(u_int8_t *)block_limits,
3456                              /*inq_len*/sizeof(*block_limits),
3457                              /*evpd*/TRUE,
3458                              /*page_code*/SVPD_BLOCK_LIMITS,
3459                              /*sense_len*/SSD_MIN_SIZE,
3460                              /*timeout*/da_default_timeout * 1000);
3461                 start_ccb->ccb_h.ccb_bp = NULL;
3462                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_BLK_LIMITS;
3463                 xpt_action(start_ccb);
3464                 break;
3465         }
3466         case DA_STATE_PROBE_BDC:
3467         {
3468                 struct scsi_vpd_block_characteristics *bdc;
3469
3470                 if (!scsi_vpd_supported_page(periph, SVPD_BDC)) {
3471                         softc->state = DA_STATE_PROBE_ATA;
3472                         goto skipstate;
3473                 }
3474
3475                 bdc = (struct scsi_vpd_block_characteristics *)
3476                         malloc(sizeof(*bdc), M_SCSIDA, M_NOWAIT|M_ZERO);
3477
3478                 if (bdc == NULL) {
3479                         printf("dastart: Couldn't malloc bdc data\n");
3480                         /* da_free_periph??? */
3481                         break;
3482                 }
3483
3484                 scsi_inquiry(&start_ccb->csio,
3485                              /*retries*/da_retry_count,
3486                              /*cbfcnp*/dadone_probebdc,
3487                              /*tag_action*/MSG_SIMPLE_Q_TAG,
3488                              /*inq_buf*/(u_int8_t *)bdc,
3489                              /*inq_len*/sizeof(*bdc),
3490                              /*evpd*/TRUE,
3491                              /*page_code*/SVPD_BDC,
3492                              /*sense_len*/SSD_MIN_SIZE,
3493                              /*timeout*/da_default_timeout * 1000);
3494                 start_ccb->ccb_h.ccb_bp = NULL;
3495                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_BDC;
3496                 xpt_action(start_ccb);
3497                 break;
3498         }
3499         case DA_STATE_PROBE_ATA:
3500         {
3501                 struct ata_params *ata_params;
3502
3503                 if (!scsi_vpd_supported_page(periph, SVPD_ATA_INFORMATION)) {
3504                         if ((softc->zone_mode == DA_ZONE_HOST_AWARE)
3505                          || (softc->zone_mode == DA_ZONE_HOST_MANAGED)) {
3506                                 /*
3507                                  * Note that if the ATA VPD page isn't
3508                                  * supported, we aren't talking to an ATA
3509                                  * device anyway.  Support for that VPD
3510                                  * page is mandatory for SCSI to ATA (SAT)
3511                                  * translation layers.
3512                                  */
3513                                 softc->state = DA_STATE_PROBE_ZONE;
3514                                 goto skipstate;
3515                         }
3516                         daprobedone(periph, start_ccb);
3517                         break;
3518                 }
3519
3520                 ata_params = (struct ata_params*)
3521                         malloc(sizeof(*ata_params), M_SCSIDA,M_NOWAIT|M_ZERO);
3522
3523                 if (ata_params == NULL) {
3524                         xpt_print(periph->path, "Couldn't malloc ata_params "
3525                             "data\n");
3526                         /* da_free_periph??? */
3527                         break;
3528                 }
3529
3530                 scsi_ata_identify(&start_ccb->csio,
3531                                   /*retries*/da_retry_count,
3532                                   /*cbfcnp*/dadone_probeata,
3533                                   /*tag_action*/MSG_SIMPLE_Q_TAG,
3534                                   /*data_ptr*/(u_int8_t *)ata_params,
3535                                   /*dxfer_len*/sizeof(*ata_params),
3536                                   /*sense_len*/SSD_FULL_SIZE,
3537                                   /*timeout*/da_default_timeout * 1000);
3538                 start_ccb->ccb_h.ccb_bp = NULL;
3539                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_ATA;
3540                 xpt_action(start_ccb);
3541                 break;
3542         }
3543         case DA_STATE_PROBE_ATA_LOGDIR:
3544         {
3545                 struct ata_gp_log_dir *log_dir;
3546                 int retval;
3547
3548                 retval = 0;
3549
3550                 if ((softc->flags & DA_FLAG_CAN_ATA_LOG) == 0) {
3551                         /*
3552                          * If we don't have log support, not much point in
3553                          * trying to probe zone support.
3554                          */
3555                         daprobedone(periph, start_ccb);
3556                         break;
3557                 }
3558
3559                 /*
3560                  * If we have an ATA device (the SCSI ATA Information VPD
3561                  * page should be present and the ATA identify should have
3562                  * succeeded) and it supports logs, ask for the log directory.
3563                  */
3564
3565                 log_dir = malloc(sizeof(*log_dir), M_SCSIDA, M_NOWAIT|M_ZERO);
3566                 if (log_dir == NULL) {
3567                         xpt_print(periph->path, "Couldn't malloc log_dir "
3568                             "data\n");
3569                         daprobedone(periph, start_ccb);
3570                         break;
3571                 }
3572
3573                 retval = scsi_ata_read_log(&start_ccb->csio,
3574                     /*retries*/ da_retry_count,
3575                     /*cbfcnp*/ dadone_probeatalogdir,
3576                     /*tag_action*/ MSG_SIMPLE_Q_TAG,
3577                     /*log_address*/ ATA_LOG_DIRECTORY,
3578                     /*page_number*/ 0,
3579                     /*block_count*/ 1,
3580                     /*protocol*/ softc->flags & DA_FLAG_CAN_ATA_DMA ?
3581                                  AP_PROTO_DMA : AP_PROTO_PIO_IN,
3582                     /*data_ptr*/ (uint8_t *)log_dir,
3583                     /*dxfer_len*/ sizeof(*log_dir),
3584                     /*sense_len*/ SSD_FULL_SIZE,
3585                     /*timeout*/ da_default_timeout * 1000);
3586
3587                 if (retval != 0) {
3588                         xpt_print(periph->path, "scsi_ata_read_log() failed!");
3589                         free(log_dir, M_SCSIDA);
3590                         daprobedone(periph, start_ccb);
3591                         break;
3592                 }
3593                 start_ccb->ccb_h.ccb_bp = NULL;
3594                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_ATA_LOGDIR;
3595                 xpt_action(start_ccb);
3596                 break;
3597         }
3598         case DA_STATE_PROBE_ATA_IDDIR:
3599         {
3600                 struct ata_identify_log_pages *id_dir;
3601                 int retval;
3602
3603                 retval = 0;
3604
3605                 /*
3606                  * Check here to see whether the Identify Device log is
3607                  * supported in the directory of logs.  If so, continue
3608                  * with requesting the log of identify device pages.
3609                  */
3610                 if ((softc->flags & DA_FLAG_CAN_ATA_IDLOG) == 0) {
3611                         daprobedone(periph, start_ccb);
3612                         break;
3613                 }
3614
3615                 id_dir = malloc(sizeof(*id_dir), M_SCSIDA, M_NOWAIT | M_ZERO);
3616                 if (id_dir == NULL) {
3617                         xpt_print(periph->path, "Couldn't malloc id_dir "
3618                             "data\n");
3619                         daprobedone(periph, start_ccb);
3620                         break;
3621                 }
3622
3623                 retval = scsi_ata_read_log(&start_ccb->csio,
3624                     /*retries*/ da_retry_count,
3625                     /*cbfcnp*/ dadone_probeataiddir,
3626                     /*tag_action*/ MSG_SIMPLE_Q_TAG,
3627                     /*log_address*/ ATA_IDENTIFY_DATA_LOG,
3628                     /*page_number*/ ATA_IDL_PAGE_LIST,
3629                     /*block_count*/ 1,
3630                     /*protocol*/ softc->flags & DA_FLAG_CAN_ATA_DMA ?
3631                                  AP_PROTO_DMA : AP_PROTO_PIO_IN,
3632                     /*data_ptr*/ (uint8_t *)id_dir,
3633                     /*dxfer_len*/ sizeof(*id_dir),
3634                     /*sense_len*/ SSD_FULL_SIZE,
3635                     /*timeout*/ da_default_timeout * 1000);
3636
3637                 if (retval != 0) {
3638                         xpt_print(periph->path, "scsi_ata_read_log() failed!");
3639                         free(id_dir, M_SCSIDA);
3640                         daprobedone(periph, start_ccb);
3641                         break;
3642                 }
3643                 start_ccb->ccb_h.ccb_bp = NULL;
3644                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_ATA_IDDIR;
3645                 xpt_action(start_ccb);
3646                 break;
3647         }
3648         case DA_STATE_PROBE_ATA_SUP:
3649         {
3650                 struct ata_identify_log_sup_cap *sup_cap;
3651                 int retval;
3652
3653                 retval = 0;
3654
3655                 /*
3656                  * Check here to see whether the Supported Capabilities log
3657                  * is in the list of Identify Device logs.
3658                  */
3659                 if ((softc->flags & DA_FLAG_CAN_ATA_SUPCAP) == 0) {
3660                         daprobedone(periph, start_ccb);
3661                         break;
3662                 }
3663
3664                 sup_cap = malloc(sizeof(*sup_cap), M_SCSIDA, M_NOWAIT|M_ZERO);
3665                 if (sup_cap == NULL) {
3666                         xpt_print(periph->path, "Couldn't malloc sup_cap "
3667                             "data\n");
3668                         daprobedone(periph, start_ccb);
3669                         break;
3670                 }
3671
3672                 retval = scsi_ata_read_log(&start_ccb->csio,
3673                     /*retries*/ da_retry_count,
3674                     /*cbfcnp*/ dadone_probeatasup,
3675                     /*tag_action*/ MSG_SIMPLE_Q_TAG,
3676                     /*log_address*/ ATA_IDENTIFY_DATA_LOG,
3677                     /*page_number*/ ATA_IDL_SUP_CAP,
3678                     /*block_count*/ 1,
3679                     /*protocol*/ softc->flags & DA_FLAG_CAN_ATA_DMA ?
3680                                  AP_PROTO_DMA : AP_PROTO_PIO_IN,
3681                     /*data_ptr*/ (uint8_t *)sup_cap,
3682                     /*dxfer_len*/ sizeof(*sup_cap),
3683                     /*sense_len*/ SSD_FULL_SIZE,
3684                     /*timeout*/ da_default_timeout * 1000);
3685
3686                 if (retval != 0) {
3687                         xpt_print(periph->path, "scsi_ata_read_log() failed!");
3688                         free(sup_cap, M_SCSIDA);
3689                         daprobedone(periph, start_ccb);
3690                         break;
3691
3692                 }
3693
3694                 start_ccb->ccb_h.ccb_bp = NULL;
3695                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_ATA_SUP;
3696                 xpt_action(start_ccb);
3697                 break;
3698         }
3699         case DA_STATE_PROBE_ATA_ZONE:
3700         {
3701                 struct ata_zoned_info_log *ata_zone;
3702                 int retval;
3703
3704                 retval = 0;
3705
3706                 /*
3707                  * Check here to see whether the zoned device information
3708                  * page is supported.  If so, continue on to request it.
3709                  * If not, skip to DA_STATE_PROBE_LOG or done.
3710                  */
3711                 if ((softc->flags & DA_FLAG_CAN_ATA_ZONE) == 0) {
3712                         daprobedone(periph, start_ccb);
3713                         break;
3714                 }
3715                 ata_zone = malloc(sizeof(*ata_zone), M_SCSIDA,
3716                                   M_NOWAIT|M_ZERO);
3717                 if (ata_zone == NULL) {
3718                         xpt_print(periph->path, "Couldn't malloc ata_zone "
3719                             "data\n");
3720                         daprobedone(periph, start_ccb);
3721                         break;
3722                 }
3723
3724                 retval = scsi_ata_read_log(&start_ccb->csio,
3725                     /*retries*/ da_retry_count,
3726                     /*cbfcnp*/ dadone_probeatazone,
3727                     /*tag_action*/ MSG_SIMPLE_Q_TAG,
3728                     /*log_address*/ ATA_IDENTIFY_DATA_LOG,
3729                     /*page_number*/ ATA_IDL_ZDI,
3730                     /*block_count*/ 1,
3731                     /*protocol*/ softc->flags & DA_FLAG_CAN_ATA_DMA ?
3732                                  AP_PROTO_DMA : AP_PROTO_PIO_IN,
3733                     /*data_ptr*/ (uint8_t *)ata_zone,
3734                     /*dxfer_len*/ sizeof(*ata_zone),
3735                     /*sense_len*/ SSD_FULL_SIZE,
3736                     /*timeout*/ da_default_timeout * 1000);
3737
3738                 if (retval != 0) {
3739                         xpt_print(periph->path, "scsi_ata_read_log() failed!");
3740                         free(ata_zone, M_SCSIDA);
3741                         daprobedone(periph, start_ccb);
3742                         break;
3743                 }
3744                 start_ccb->ccb_h.ccb_bp = NULL;
3745                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_ATA_ZONE;
3746                 xpt_action(start_ccb);
3747
3748                 break;
3749         }
3750         case DA_STATE_PROBE_ZONE:
3751         {
3752                 struct scsi_vpd_zoned_bdc *bdc;
3753
3754                 /*
3755                  * Note that this page will be supported for SCSI protocol
3756                  * devices that support ZBC (SMR devices), as well as ATA
3757                  * protocol devices that are behind a SAT (SCSI to ATA
3758                  * Translation) layer that supports converting ZBC commands
3759                  * to their ZAC equivalents.
3760                  */
3761                 if (!scsi_vpd_supported_page(periph, SVPD_ZONED_BDC)) {
3762                         daprobedone(periph, start_ccb);
3763                         break;
3764                 }
3765                 bdc = (struct scsi_vpd_zoned_bdc *)
3766                         malloc(sizeof(*bdc), M_SCSIDA, M_NOWAIT|M_ZERO);
3767
3768                 if (bdc == NULL) {
3769                         xpt_release_ccb(start_ccb);
3770                         xpt_print(periph->path, "Couldn't malloc zone VPD "
3771                             "data\n");
3772                         break;
3773                 }
3774                 scsi_inquiry(&start_ccb->csio,
3775                              /*retries*/da_retry_count,
3776                              /*cbfcnp*/dadone_probezone,
3777                              /*tag_action*/MSG_SIMPLE_Q_TAG,
3778                              /*inq_buf*/(u_int8_t *)bdc,
3779                              /*inq_len*/sizeof(*bdc),
3780                              /*evpd*/TRUE,
3781                              /*page_code*/SVPD_ZONED_BDC,
3782                              /*sense_len*/SSD_FULL_SIZE,
3783                              /*timeout*/da_default_timeout * 1000);
3784                 start_ccb->ccb_h.ccb_bp = NULL;
3785                 start_ccb->ccb_h.ccb_state = DA_CCB_PROBE_ZONE;
3786                 xpt_action(start_ccb);
3787                 break;
3788         }
3789         }
3790 }
3791
3792 /*
3793  * In each of the methods below, while its the caller's
3794  * responsibility to ensure the request will fit into a
3795  * single device request, we might have changed the delete
3796  * method due to the device incorrectly advertising either
3797  * its supported methods or limits.
3798  * 
3799  * To prevent this causing further issues we validate the
3800  * against the methods limits, and warn which would
3801  * otherwise be unnecessary.
3802  */
3803 static void
3804 da_delete_unmap(struct cam_periph *periph, union ccb *ccb, struct bio *bp)
3805 {
3806         struct da_softc *softc = (struct da_softc *)periph->softc;;
3807         struct bio *bp1;
3808         uint8_t *buf = softc->unmap_buf;
3809         struct scsi_unmap_desc *d = (void *)&buf[UNMAP_HEAD_SIZE];
3810         uint64_t lba, lastlba = (uint64_t)-1;
3811         uint64_t totalcount = 0;
3812         uint64_t count;
3813         uint32_t c, lastcount = 0, ranges = 0;
3814
3815         /*
3816          * Currently this doesn't take the UNMAP
3817          * Granularity and Granularity Alignment
3818          * fields into account.
3819          *
3820          * This could result in both unoptimal unmap
3821          * requests as as well as UNMAP calls unmapping
3822          * fewer LBA's than requested.
3823          */
3824
3825         bzero(softc->unmap_buf, sizeof(softc->unmap_buf));
3826         bp1 = bp;
3827         do {
3828                 /*
3829                  * Note: ada and da are different in how they store the
3830                  * pending bp's in a trim. ada stores all of them in the
3831                  * trim_req.bps. da stores all but the first one in the
3832                  * delete_run_queue. ada then completes all the bps in
3833                  * its adadone() loop. da completes all the bps in the
3834                  * delete_run_queue in dadone, and relies on the biodone
3835                  * after to complete. This should be reconciled since there's
3836                  * no real reason to do it differently. XXX
3837                  */
3838                 if (bp1 != bp)
3839                         bioq_insert_tail(&softc->delete_run_queue, bp1);
3840                 lba = bp1->bio_pblkno;
3841                 count = bp1->bio_bcount / softc->params.secsize;
3842
3843                 /* Try to extend the previous range. */
3844                 if (lba == lastlba) {
3845                         c = omin(count, UNMAP_RANGE_MAX - lastcount);
3846                         lastlba += c;
3847                         lastcount += c;
3848                         scsi_ulto4b(lastcount, d[ranges - 1].length);
3849                         count -= c;
3850                         lba += c;
3851                         totalcount += c;
3852                 } else if ((softc->quirks & DA_Q_STRICT_UNMAP) &&
3853                     softc->unmap_gran != 0) {
3854                         /* Align length of the previous range. */
3855                         if ((c = lastcount % softc->unmap_gran) != 0) {
3856                                 if (lastcount <= c) {
3857                                         totalcount -= lastcount;
3858                                         lastlba = (uint64_t)-1;
3859                                         lastcount = 0;
3860                                         ranges--;
3861                                 } else {
3862                                         totalcount -= c;
3863                                         lastlba -= c;
3864                                         lastcount -= c;
3865                                         scsi_ulto4b(lastcount,
3866                                             d[ranges - 1].length);
3867                                 }
3868                         }
3869                         /* Align beginning of the new range. */
3870                         c = (lba - softc->unmap_gran_align) % softc->unmap_gran;
3871                         if (c != 0) {
3872                                 c = softc->unmap_gran - c;
3873                                 if (count <= c) {
3874                                         count = 0;
3875                                 } else {
3876                                         lba += c;
3877                                         count -= c;
3878                                 }
3879                         }
3880                 }
3881
3882                 while (count > 0) {
3883                         c = omin(count, UNMAP_RANGE_MAX);
3884                         if (totalcount + c > softc->unmap_max_lba ||
3885                             ranges >= softc->unmap_max_ranges) {
3886                                 xpt_print(periph->path,
3887                                     "%s issuing short delete %ld > %ld"
3888                                     "|| %d >= %d",
3889                                     da_delete_method_desc[softc->delete_method],
3890                                     totalcount + c, softc->unmap_max_lba,
3891                                     ranges, softc->unmap_max_ranges);
3892                                 break;
3893                         }
3894                         scsi_u64to8b(lba, d[ranges].lba);
3895                         scsi_ulto4b(c, d[ranges].length);
3896                         lba += c;
3897                         totalcount += c;
3898                         ranges++;
3899                         count -= c;
3900                         lastlba = lba;
3901                         lastcount = c;
3902                 }
3903                 bp1 = cam_iosched_next_trim(softc->cam_iosched);
3904                 if (bp1 == NULL)
3905                         break;
3906                 if (ranges >= softc->unmap_max_ranges ||
3907                     totalcount + bp1->bio_bcount /
3908                     softc->params.secsize > softc->unmap_max_lba) {
3909                         cam_iosched_put_back_trim(softc->cam_iosched, bp1);
3910                         break;
3911                 }
3912         } while (1);
3913
3914         /* Align length of the last range. */
3915         if ((softc->quirks & DA_Q_STRICT_UNMAP) && softc->unmap_gran != 0 &&
3916             (c = lastcount % softc->unmap_gran) != 0) {
3917                 if (lastcount <= c)
3918                         ranges--;
3919                 else
3920                         scsi_ulto4b(lastcount - c, d[ranges - 1].length);
3921         }
3922
3923         scsi_ulto2b(ranges * 16 + 6, &buf[0]);
3924         scsi_ulto2b(ranges * 16, &buf[2]);
3925
3926         scsi_unmap(&ccb->csio,
3927                    /*retries*/da_retry_count,
3928                    /*cbfcnp*/dadone,
3929                    /*tag_action*/MSG_SIMPLE_Q_TAG,
3930                    /*byte2*/0,
3931                    /*data_ptr*/ buf,
3932                    /*dxfer_len*/ ranges * 16 + 8,
3933                    /*sense_len*/SSD_FULL_SIZE,
3934                    da_default_timeout * 1000);
3935         ccb->ccb_h.ccb_state = DA_CCB_DELETE;
3936         ccb->ccb_h.flags |= CAM_UNLOCKED;
3937         cam_iosched_submit_trim(softc->cam_iosched);
3938 }
3939
3940 static void
3941 da_delete_trim(struct cam_periph *periph, union ccb *ccb, struct bio *bp)
3942 {
3943         struct da_softc *softc = (struct da_softc *)periph->softc;
3944         struct bio *bp1;
3945         uint8_t *buf = softc->unmap_buf;
3946         uint64_t lastlba = (uint64_t)-1;
3947         uint64_t count;
3948         uint64_t lba;
3949         uint32_t lastcount = 0, c, requestcount;
3950         int ranges = 0, off, block_count;
3951
3952         bzero(softc->unmap_buf, sizeof(softc->unmap_buf));
3953         bp1 = bp;
3954         do {
3955                 if (bp1 != bp)//XXX imp XXX
3956                         bioq_insert_tail(&softc->delete_run_queue, bp1);
3957                 lba = bp1->bio_pblkno;
3958                 count = bp1->bio_bcount / softc->params.secsize;
3959                 requestcount = count;
3960
3961                 /* Try to extend the previous range. */
3962                 if (lba == lastlba) {
3963                         c = omin(count, ATA_DSM_RANGE_MAX - lastcount);
3964                         lastcount += c;
3965                         off = (ranges - 1) * 8;
3966                         buf[off + 6] = lastcount & 0xff;
3967                         buf[off + 7] = (lastcount >> 8) & 0xff;
3968                         count -= c;
3969                         lba += c;
3970                 }
3971
3972                 while (count > 0) {
3973                         c = omin(count, ATA_DSM_RANGE_MAX);
3974                         off = ranges * 8;
3975
3976                         buf[off + 0] = lba & 0xff;
3977                         buf[off + 1] = (lba >> 8) & 0xff;
3978                         buf[off + 2] = (lba >> 16) & 0xff;
3979                         buf[off + 3] = (lba >> 24) & 0xff;
3980                         buf[off + 4] = (lba >> 32) & 0xff;
3981                         buf[off + 5] = (lba >> 40) & 0xff;
3982                         buf[off + 6] = c & 0xff;
3983                         buf[off + 7] = (c >> 8) & 0xff;
3984                         lba += c;
3985                         ranges++;
3986                         count -= c;
3987                         lastcount = c;
3988                         if (count != 0 && ranges == softc->trim_max_ranges) {
3989                                 xpt_print(periph->path,
3990                                     "%s issuing short delete %ld > %ld\n",
3991                                     da_delete_method_desc[softc->delete_method],
3992                                     requestcount,
3993                                     (softc->trim_max_ranges - ranges) *
3994                                     ATA_DSM_RANGE_MAX);
3995                                 break;
3996                         }
3997                 }
3998                 lastlba = lba;
3999                 bp1 = cam_iosched_next_trim(softc->cam_iosched);
4000                 if (bp1 == NULL)
4001                         break;
4002                 if (bp1->bio_bcount / softc->params.secsize >
4003                     (softc->trim_max_ranges - ranges) * ATA_DSM_RANGE_MAX) {
4004                         cam_iosched_put_back_trim(softc->cam_iosched, bp1);
4005                         break;
4006                 }
4007         } while (1);
4008
4009         block_count = howmany(ranges, ATA_DSM_BLK_RANGES);
4010         scsi_ata_trim(&ccb->csio,
4011                       /*retries*/da_retry_count,
4012                       /*cbfcnp*/dadone,
4013                       /*tag_action*/MSG_SIMPLE_Q_TAG,
4014                       block_count,
4015                       /*data_ptr*/buf,
4016                       /*dxfer_len*/block_count * ATA_DSM_BLK_SIZE,
4017                       /*sense_len*/SSD_FULL_SIZE,
4018                       da_default_timeout * 1000);
4019         ccb->ccb_h.ccb_state = DA_CCB_DELETE;
4020         ccb->ccb_h.flags |= CAM_UNLOCKED;
4021         cam_iosched_submit_trim(softc->cam_iosched);
4022 }
4023
4024 /*
4025  * We calculate ws_max_blks here based off d_delmaxsize instead
4026  * of using softc->ws_max_blks as it is absolute max for the
4027  * device not the protocol max which may well be lower.
4028  */
4029 static void
4030 da_delete_ws(struct cam_periph *periph, union ccb *ccb, struct bio *bp)
4031 {
4032         struct da_softc *softc;
4033         struct bio *bp1;
4034         uint64_t ws_max_blks;
4035         uint64_t lba;
4036         uint64_t count; /* forward compat with WS32 */
4037
4038         softc = (struct da_softc *)periph->softc;
4039         ws_max_blks = softc->disk->d_delmaxsize / softc->params.secsize;
4040         lba = bp->bio_pblkno;
4041         count = 0;
4042         bp1 = bp;
4043         do {
4044                 if (bp1 != bp)//XXX imp XXX
4045                         bioq_insert_tail(&softc->delete_run_queue, bp1);
4046                 count += bp1->bio_bcount / softc->params.secsize;
4047                 if (count > ws_max_blks) {
4048                         xpt_print(periph->path,
4049                             "%s issuing short delete %ld > %ld\n",
4050                             da_delete_method_desc[softc->delete_method],
4051                             count, ws_max_blks);
4052                         count = omin(count, ws_max_blks);
4053                         break;
4054                 }
4055                 bp1 = cam_iosched_next_trim(softc->cam_iosched);
4056                 if (bp1 == NULL)
4057                         break;
4058                 if (lba + count != bp1->bio_pblkno ||
4059                     count + bp1->bio_bcount /
4060                     softc->params.secsize > ws_max_blks) {
4061                         cam_iosched_put_back_trim(softc->cam_iosched, bp1);
4062                         break;
4063                 }
4064         } while (1);
4065
4066         scsi_write_same(&ccb->csio,
4067                         /*retries*/da_retry_count,
4068                         /*cbfcnp*/dadone,
4069                         /*tag_action*/MSG_SIMPLE_Q_TAG,
4070                         /*byte2*/softc->delete_method ==
4071                             DA_DELETE_ZERO ? 0 : SWS_UNMAP,
4072                         softc->delete_method == DA_DELETE_WS16 ? 16 : 10,
4073                         /*lba*/lba,
4074                         /*block_count*/count,
4075                         /*data_ptr*/ __DECONST(void *, zero_region),
4076                         /*dxfer_len*/ softc->params.secsize,
4077                         /*sense_len*/SSD_FULL_SIZE,
4078                         da_default_timeout * 1000);
4079         ccb->ccb_h.ccb_state = DA_CCB_DELETE;
4080         ccb->ccb_h.flags |= CAM_UNLOCKED;
4081         cam_iosched_submit_trim(softc->cam_iosched);
4082 }
4083
4084 static int
4085 cmd6workaround(union ccb *ccb)
4086 {
4087         struct scsi_rw_6 cmd6;
4088         struct scsi_rw_10 *cmd10;
4089         struct da_softc *softc;
4090         u_int8_t *cdb;
4091         struct bio *bp;
4092         int frozen;
4093
4094         cdb = ccb->csio.cdb_io.cdb_bytes;
4095         softc = (struct da_softc *)xpt_path_periph(ccb->ccb_h.path)->softc;
4096
4097         if (ccb->ccb_h.ccb_state == DA_CCB_DELETE) {
4098                 da_delete_methods old_method = softc->delete_method;
4099
4100                 /*
4101                  * Typically there are two reasons for failure here
4102                  * 1. Delete method was detected as supported but isn't
4103                  * 2. Delete failed due to invalid params e.g. too big
4104                  *
4105                  * While we will attempt to choose an alternative delete method
4106                  * this may result in short deletes if the existing delete
4107                  * requests from geom are big for the new method chosen.
4108                  *
4109                  * This method assumes that the error which triggered this
4110                  * will not retry the io otherwise a panic will occur
4111                  */
4112                 dadeleteflag(softc, old_method, 0);
4113                 dadeletemethodchoose(softc, DA_DELETE_DISABLE);
4114                 if (softc->delete_method == DA_DELETE_DISABLE)
4115                         xpt_print(ccb->ccb_h.path,
4116                                   "%s failed, disabling BIO_DELETE\n",
4117                                   da_delete_method_desc[old_method]);
4118                 else
4119                         xpt_print(ccb->ccb_h.path,
4120                                   "%s failed, switching to %s BIO_DELETE\n",
4121                                   da_delete_method_desc[old_method],
4122                                   da_delete_method_desc[softc->delete_method]);
4123
4124                 while ((bp = bioq_takefirst(&softc->delete_run_queue)) != NULL)
4125                         cam_iosched_queue_work(softc->cam_iosched, bp);
4126                 cam_iosched_queue_work(softc->cam_iosched,
4127                     (struct bio *)ccb->ccb_h.ccb_bp);
4128                 ccb->ccb_h.ccb_bp = NULL;
4129                 return (0);
4130         }
4131
4132         /* Detect unsupported PREVENT ALLOW MEDIUM REMOVAL. */
4133         if ((ccb->ccb_h.flags & CAM_CDB_POINTER) == 0 &&
4134             (*cdb == PREVENT_ALLOW) &&
4135             (softc->quirks & DA_Q_NO_PREVENT) == 0) {
4136                 if (bootverbose)
4137                         xpt_print(ccb->ccb_h.path,
4138                             "PREVENT ALLOW MEDIUM REMOVAL not supported.\n");
4139                 softc->quirks |= DA_Q_NO_PREVENT;
4140                 return (0);
4141         }
4142
4143         /* Detect unsupported SYNCHRONIZE CACHE(10). */
4144         if ((ccb->ccb_h.flags & CAM_CDB_POINTER) == 0 &&
4145             (*cdb == SYNCHRONIZE_CACHE) &&
4146             (softc->quirks & DA_Q_NO_SYNC_CACHE) == 0) {
4147                 if (bootverbose)
4148                         xpt_print(ccb->ccb_h.path,
4149                             "SYNCHRONIZE CACHE(10) not supported.\n");
4150                 softc->quirks |= DA_Q_NO_SYNC_CACHE;
4151                 softc->disk->d_flags &= ~DISKFLAG_CANFLUSHCACHE;
4152                 return (0);
4153         }
4154
4155         /* Translation only possible if CDB is an array and cmd is R/W6 */
4156         if ((ccb->ccb_h.flags & CAM_CDB_POINTER) != 0 ||
4157             (*cdb != READ_6 && *cdb != WRITE_6))
4158                 return 0;
4159
4160         xpt_print(ccb->ccb_h.path, "READ(6)/WRITE(6) not supported, "
4161             "increasing minimum_cmd_size to 10.\n");
4162         softc->minimum_cmd_size = 10;
4163
4164         bcopy(cdb, &cmd6, sizeof(struct scsi_rw_6));
4165         cmd10 = (struct scsi_rw_10 *)cdb;
4166         cmd10->opcode = (cmd6.opcode == READ_6) ? READ_10 : WRITE_10;
4167         cmd10->byte2 = 0;
4168         scsi_ulto4b(scsi_3btoul(cmd6.addr), cmd10->addr);
4169         cmd10->reserved = 0;
4170         scsi_ulto2b(cmd6.length, cmd10->length);
4171         cmd10->control = cmd6.control;
4172         ccb->csio.cdb_len = sizeof(*cmd10);
4173
4174         /* Requeue request, unfreezing queue if necessary */
4175         frozen = (ccb->ccb_h.status & CAM_DEV_QFRZN) != 0;
4176         ccb->ccb_h.status = CAM_REQUEUE_REQ;
4177         xpt_action(ccb);
4178         if (frozen) {
4179                 cam_release_devq(ccb->ccb_h.path,
4180                                  /*relsim_flags*/0,
4181                                  /*reduction*/0,
4182                                  /*timeout*/0,
4183                                  /*getcount_only*/0);
4184         }
4185         return (ERESTART);
4186 }
4187
4188 static void
4189 dazonedone(struct cam_periph *periph, union ccb *ccb)
4190 {
4191         struct da_softc *softc;
4192         struct bio *bp;
4193
4194         softc = periph->softc;
4195         bp = (struct bio *)ccb->ccb_h.ccb_bp;
4196
4197         switch (bp->bio_zone.zone_cmd) {
4198         case DISK_ZONE_OPEN:
4199         case DISK_ZONE_CLOSE:
4200         case DISK_ZONE_FINISH:
4201         case DISK_ZONE_RWP:
4202                 break;
4203         case DISK_ZONE_REPORT_ZONES: {
4204                 uint32_t avail_len;
4205                 struct disk_zone_report *rep;
4206                 struct scsi_report_zones_hdr *hdr;
4207                 struct scsi_report_zones_desc *desc;
4208                 struct disk_zone_rep_entry *entry;
4209                 uint32_t hdr_len, num_avail;
4210                 uint32_t num_to_fill, i;
4211                 int ata;
4212
4213                 rep = &bp->bio_zone.zone_params.report;
4214                 avail_len = ccb->csio.dxfer_len - ccb->csio.resid;
4215                 /*
4216                  * Note that bio_resid isn't normally used for zone
4217                  * commands, but it is used by devstat_end_transaction_bio()
4218                  * to determine how much data was transferred.  Because
4219                  * the size of the SCSI/ATA data structures is different
4220                  * than the size of the BIO interface structures, the
4221                  * amount of data actually transferred from the drive will
4222                  * be different than the amount of data transferred to
4223                  * the user.
4224                  */
4225                 bp->bio_resid = ccb->csio.resid;
4226                 hdr = (struct scsi_report_zones_hdr *)ccb->csio.data_ptr;
4227                 if (avail_len < sizeof(*hdr)) {
4228                         /*
4229                          * Is there a better error than EIO here?  We asked
4230                          * for at least the header, and we got less than
4231                          * that.
4232                          */
4233                         bp->bio_error = EIO;
4234                         bp->bio_flags |= BIO_ERROR;
4235                         bp->bio_resid = bp->bio_bcount;
4236                         break;
4237                 }
4238
4239                 if (softc->zone_interface == DA_ZONE_IF_ATA_PASS)
4240                         ata = 1;
4241                 else
4242                         ata = 0;
4243
4244                 hdr_len = ata ? le32dec(hdr->length) :
4245                                 scsi_4btoul(hdr->length);
4246                 if (hdr_len > 0)
4247                         rep->entries_available = hdr_len / sizeof(*desc);
4248                 else
4249                         rep->entries_available = 0;
4250                 /*
4251                  * NOTE: using the same values for the BIO version of the
4252                  * same field as the SCSI/ATA values.  This means we could
4253                  * get some additional values that aren't defined in bio.h
4254                  * if more values of the same field are defined later.
4255                  */
4256                 rep->header.same = hdr->byte4 & SRZ_SAME_MASK;
4257                 rep->header.maximum_lba = ata ?  le64dec(hdr->maximum_lba) :
4258                                           scsi_8btou64(hdr->maximum_lba);
4259                 /*
4260                  * If the drive reports no entries that match the query,
4261                  * we're done.
4262                  */
4263                 if (hdr_len == 0) {
4264                         rep->entries_filled = 0;
4265                         break;
4266                 }
4267
4268                 num_avail = min((avail_len - sizeof(*hdr)) / sizeof(*desc),
4269                                 hdr_len / sizeof(*desc));
4270                 /*
4271                  * If the drive didn't return any data, then we're done.
4272                  */
4273                 if (num_avail == 0) {
4274                         rep->entries_filled = 0;
4275                         break;
4276                 }
4277
4278                 num_to_fill = min(num_avail, rep->entries_allocated);
4279                 /*
4280                  * If the user didn't allocate any entries for us to fill,
4281                  * we're done.
4282                  */
4283                 if (num_to_fill == 0) {
4284                         rep->entries_filled = 0;
4285                         break;
4286                 }
4287
4288                 for (i = 0, desc = &hdr->desc_list[0], entry=&rep->entries[0];
4289                      i < num_to_fill; i++, desc++, entry++) {
4290                         /*
4291                          * NOTE: we're mapping the values here directly
4292                          * from the SCSI/ATA bit definitions to the bio.h
4293                          * definitons.  There is also a warning in
4294                          * disk_zone.h, but the impact is that if
4295                          * additional values are added in the SCSI/ATA
4296                          * specs these will be visible to consumers of
4297                          * this interface.
4298                          */
4299                         entry->zone_type = desc->zone_type & SRZ_TYPE_MASK;
4300                         entry->zone_condition =
4301                             (desc->zone_flags & SRZ_ZONE_COND_MASK) >>
4302                             SRZ_ZONE_COND_SHIFT;
4303                         entry->zone_flags |= desc->zone_flags &
4304                             (SRZ_ZONE_NON_SEQ|SRZ_ZONE_RESET);
4305                         entry->zone_length =
4306                             ata ? le64dec(desc->zone_length) :
4307                                   scsi_8btou64(desc->zone_length);
4308                         entry->zone_start_lba =
4309                             ata ? le64dec(desc->zone_start_lba) :
4310                                   scsi_8btou64(desc->zone_start_lba);
4311                         entry->write_pointer_lba =
4312                             ata ? le64dec(desc->write_pointer_lba) :
4313                                   scsi_8btou64(desc->write_pointer_lba);
4314                 }
4315                 rep->entries_filled = num_to_fill;
4316                 break;
4317         }
4318         case DISK_ZONE_GET_PARAMS:
4319         default:
4320                 /*
4321                  * In theory we should not get a GET_PARAMS bio, since it
4322                  * should be handled without queueing the command to the
4323                  * drive.
4324                  */
4325                 panic("%s: Invalid zone command %d", __func__,
4326                     bp->bio_zone.zone_cmd);
4327                 break;
4328         }
4329
4330         if (bp->bio_zone.zone_cmd == DISK_ZONE_REPORT_ZONES)
4331                 free(ccb->csio.data_ptr, M_SCSIDA);
4332 }
4333
4334 static void
4335 dadone(struct cam_periph *periph, union ccb *done_ccb)
4336 {
4337         struct bio *bp, *bp1;
4338         struct da_softc *softc;
4339         struct ccb_scsiio *csio;
4340         u_int32_t  priority;
4341         da_ccb_state state;
4342
4343         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone\n"));
4344
4345         softc = (struct da_softc *)periph->softc;
4346         priority = done_ccb->ccb_h.pinfo.priority;
4347         csio = &done_ccb->csio;
4348
4349 #if defined(BUF_TRACKING) || defined(FULL_BUF_TRACKING)
4350         if (csio->bio != NULL)
4351                 biotrack(csio->bio, __func__);
4352 #endif
4353         state = csio->ccb_h.ccb_state & DA_CCB_TYPE_MASK;
4354
4355         cam_periph_lock(periph);
4356         bp = (struct bio *)done_ccb->ccb_h.ccb_bp;
4357         if ((done_ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) {
4358                 int error;
4359                 int sf;
4360
4361                 if ((csio->ccb_h.ccb_state & DA_CCB_RETRY_UA) != 0)
4362                         sf = SF_RETRY_UA;
4363                 else
4364                         sf = 0;
4365
4366                 error = daerror(done_ccb, CAM_RETRY_SELTO, sf);
4367                 if (error == ERESTART) {
4368                         /* A retry was scheduled, so just return. */
4369                         cam_periph_unlock(periph);
4370                         return;
4371                 }
4372                 bp = (struct bio *)done_ccb->ccb_h.ccb_bp;
4373                 if (error != 0) {
4374                         int queued_error;
4375
4376                         /*
4377                          * return all queued I/O with EIO, so that
4378                          * the client can retry these I/Os in the
4379                          * proper order should it attempt to recover.
4380                          */
4381                         queued_error = EIO;
4382
4383                         if (error == ENXIO
4384                          && (softc->flags & DA_FLAG_PACK_INVALID)== 0) {
4385                                 /*
4386                                  * Catastrophic error.  Mark our pack as
4387                                  * invalid.
4388                                  *
4389                                  * XXX See if this is really a media
4390                                  * XXX change first?
4391                                  */
4392                                 xpt_print(periph->path, "Invalidating pack\n");
4393                                 softc->flags |= DA_FLAG_PACK_INVALID;
4394 #ifdef CAM_IO_STATS
4395                                 softc->invalidations++;
4396 #endif
4397                                 queued_error = ENXIO;
4398                         }
4399                         cam_iosched_flush(softc->cam_iosched, NULL,
4400                            queued_error);
4401                         if (bp != NULL) {
4402                                 bp->bio_error = error;
4403                                 bp->bio_resid = bp->bio_bcount;
4404                                 bp->bio_flags |= BIO_ERROR;
4405                         }
4406                 } else if (bp != NULL) {
4407                         if (state == DA_CCB_DELETE)
4408                                 bp->bio_resid = 0;
4409                         else
4410                                 bp->bio_resid = csio->resid;
4411                         bp->bio_error = 0;
4412                         if (bp->bio_resid != 0)
4413                                 bp->bio_flags |= BIO_ERROR;
4414                 }
4415                 if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0)
4416                         cam_release_devq(done_ccb->ccb_h.path,
4417                                          /*relsim_flags*/0,
4418                                          /*reduction*/0,
4419                                          /*timeout*/0,
4420                                          /*getcount_only*/0);
4421         } else if (bp != NULL) {
4422                 if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0)
4423                         panic("REQ_CMP with QFRZN");
4424                 if (bp->bio_cmd == BIO_ZONE)
4425                         dazonedone(periph, done_ccb);
4426                 else if (state == DA_CCB_DELETE)
4427                         bp->bio_resid = 0;
4428                 else
4429                         bp->bio_resid = csio->resid;
4430                 if ((csio->resid > 0) && (bp->bio_cmd != BIO_ZONE))
4431                         bp->bio_flags |= BIO_ERROR;
4432                 if (softc->error_inject != 0) {
4433                         bp->bio_error = softc->error_inject;
4434                         bp->bio_resid = bp->bio_bcount;
4435                         bp->bio_flags |= BIO_ERROR;
4436                         softc->error_inject = 0;
4437                 }
4438         }
4439
4440         if (bp != NULL)
4441                 biotrack(bp, __func__);
4442         LIST_REMOVE(&done_ccb->ccb_h, periph_links.le);
4443         if (LIST_EMPTY(&softc->pending_ccbs))
4444                 softc->flags |= DA_FLAG_WAS_OTAG;
4445
4446         /*
4447          * We need to call cam_iosched before we call biodone so that we don't
4448          * measure any activity that happens in the completion routine, which in
4449          * the case of sendfile can be quite extensive. Release the periph
4450          * refcount taken in dastart() for each CCB.
4451          */
4452         cam_iosched_bio_complete(softc->cam_iosched, bp, done_ccb);
4453         xpt_release_ccb(done_ccb);
4454         KASSERT(softc->refcount >= 1, ("dadone softc %p refcount %d", softc, softc->refcount));
4455         softc->refcount--;
4456         if (state == DA_CCB_DELETE) {
4457                 TAILQ_HEAD(, bio) queue;
4458
4459                 TAILQ_INIT(&queue);
4460                 TAILQ_CONCAT(&queue, &softc->delete_run_queue.queue, bio_queue);
4461                 softc->delete_run_queue.insert_point = NULL;
4462                 /*
4463                  * Normally, the xpt_release_ccb() above would make sure
4464                  * that when we have more work to do, that work would
4465                  * get kicked off. However, we specifically keep
4466                  * delete_running set to 0 before the call above to
4467                  * allow other I/O to progress when many BIO_DELETE
4468                  * requests are pushed down. We set delete_running to 0
4469                  * and call daschedule again so that we don't stall if
4470                  * there are no other I/Os pending apart from BIO_DELETEs.
4471                  */
4472                 cam_iosched_trim_done(softc->cam_iosched);
4473                 daschedule(periph);
4474                 cam_periph_unlock(periph);
4475                 while ((bp1 = TAILQ_FIRST(&queue)) != NULL) {
4476                         TAILQ_REMOVE(&queue, bp1, bio_queue);
4477                         bp1->bio_error = bp->bio_error;
4478                         if (bp->bio_flags & BIO_ERROR) {
4479                                 bp1->bio_flags |= BIO_ERROR;
4480                                 bp1->bio_resid = bp1->bio_bcount;
4481                         } else
4482                                 bp1->bio_resid = 0;
4483                         biodone(bp1);
4484                 }
4485         } else {
4486                 daschedule(periph);
4487                 cam_periph_unlock(periph);
4488         }
4489         if (bp != NULL)
4490                 biodone(bp);
4491         return;
4492 }
4493
4494 static void
4495 dadone_probewp(struct cam_periph *periph, union ccb *done_ccb)
4496 {
4497         struct scsi_mode_header_6 *mode_hdr6;
4498         struct scsi_mode_header_10 *mode_hdr10;
4499         struct da_softc *softc;
4500         struct ccb_scsiio *csio;
4501         u_int32_t  priority;
4502         uint8_t dev_spec;
4503
4504         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_probewp\n"));
4505
4506         softc = (struct da_softc *)periph->softc;
4507         priority = done_ccb->ccb_h.pinfo.priority;
4508         csio = &done_ccb->csio;
4509
4510         cam_periph_assert(periph, MA_OWNED);
4511
4512         if (softc->minimum_cmd_size > 6) {
4513                 mode_hdr10 = (struct scsi_mode_header_10 *)csio->data_ptr;
4514                 dev_spec = mode_hdr10->dev_spec;
4515         } else {
4516                 mode_hdr6 = (struct scsi_mode_header_6 *)csio->data_ptr;
4517                 dev_spec = mode_hdr6->dev_spec;
4518         }
4519         if (cam_ccb_status(done_ccb) == CAM_REQ_CMP) {
4520                 if ((dev_spec & 0x80) != 0)
4521                         softc->disk->d_flags |= DISKFLAG_WRITE_PROTECT;
4522                 else
4523                         softc->disk->d_flags &= ~DISKFLAG_WRITE_PROTECT;
4524         } else {
4525                 int error;
4526
4527                 error = daerror(done_ccb, CAM_RETRY_SELTO,
4528                                 SF_RETRY_UA|SF_NO_PRINT);
4529                 if (error == ERESTART)
4530                         return;
4531                 else if (error != 0) {
4532                         if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0) {
4533                                 /* Don't wedge this device's queue */
4534                                 cam_release_devq(done_ccb->ccb_h.path,
4535                                                  /*relsim_flags*/0,
4536                                                  /*reduction*/0,
4537                                                  /*timeout*/0,
4538                                                  /*getcount_only*/0);
4539                         }
4540                 }
4541         }
4542
4543         free(csio->data_ptr, M_SCSIDA);
4544         xpt_release_ccb(done_ccb);
4545         if ((softc->flags & DA_FLAG_CAN_RC16) != 0)
4546                 softc->state = DA_STATE_PROBE_RC16;
4547         else
4548                 softc->state = DA_STATE_PROBE_RC;
4549         xpt_schedule(periph, priority);
4550         return;
4551 }
4552
4553 static void
4554 dadone_proberc(struct cam_periph *periph, union ccb *done_ccb)
4555 {
4556         struct scsi_read_capacity_data *rdcap;
4557         struct scsi_read_capacity_data_long *rcaplong;
4558         struct da_softc *softc;
4559         struct ccb_scsiio *csio;
4560         da_ccb_state state;
4561         char *announce_buf;
4562         u_int32_t  priority;
4563         int lbp;
4564
4565         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_proberc\n"));
4566
4567         softc = (struct da_softc *)periph->softc;
4568         priority = done_ccb->ccb_h.pinfo.priority;
4569         csio = &done_ccb->csio;
4570         state = csio->ccb_h.ccb_state & DA_CCB_TYPE_MASK;
4571
4572         lbp = 0;
4573         rdcap = NULL;
4574         rcaplong = NULL;
4575         /* XXX TODO: can this be a malloc? */
4576         announce_buf = softc->announce_temp;
4577         bzero(announce_buf, DA_ANNOUNCETMP_SZ);
4578
4579         if (state == DA_CCB_PROBE_RC)
4580                 rdcap =(struct scsi_read_capacity_data *)csio->data_ptr;
4581         else
4582                 rcaplong = (struct scsi_read_capacity_data_long *)
4583                         csio->data_ptr;
4584
4585         cam_periph_assert(periph, MA_OWNED);
4586
4587         if ((csio->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) {
4588                 struct disk_params *dp;
4589                 uint32_t block_size;
4590                 uint64_t maxsector;
4591                 u_int lalba;    /* Lowest aligned LBA. */
4592
4593                 if (state == DA_CCB_PROBE_RC) {
4594                         block_size = scsi_4btoul(rdcap->length);
4595                         maxsector = scsi_4btoul(rdcap->addr);
4596                         lalba = 0;
4597
4598                         /*
4599                          * According to SBC-2, if the standard 10
4600                          * byte READ CAPACITY command returns 2^32,
4601                          * we should issue the 16 byte version of
4602                          * the command, since the device in question
4603                          * has more sectors than can be represented
4604                          * with the short version of the command.
4605                          */
4606                         if (maxsector == 0xffffffff) {
4607                                 free(rdcap, M_SCSIDA);
4608                                 xpt_release_ccb(done_ccb);
4609                                 softc->state = DA_STATE_PROBE_RC16;
4610                                 xpt_schedule(periph, priority);
4611                                 return;
4612                         }
4613                 } else {
4614                         block_size = scsi_4btoul(rcaplong->length);
4615                         maxsector = scsi_8btou64(rcaplong->addr);
4616                         lalba = scsi_2btoul(rcaplong->lalba_lbp);
4617                 }
4618
4619                 /*
4620                  * Because GEOM code just will panic us if we
4621                  * give them an 'illegal' value we'll avoid that
4622                  * here.
4623                  */
4624                 if (block_size == 0) {
4625                         block_size = 512;
4626                         if (maxsector == 0)
4627                                 maxsector = -1;
4628                 }
4629                 if (block_size >= MAXPHYS) {
4630                         xpt_print(periph->path,
4631                             "unsupportable block size %ju\n",
4632                             (uintmax_t) block_size);
4633                         announce_buf = NULL;
4634                         cam_periph_invalidate(periph);
4635                 } else {
4636                         /*
4637                          * We pass rcaplong into dasetgeom(),
4638                          * because it will only use it if it is
4639                          * non-NULL.
4640                          */
4641                         dasetgeom(periph, block_size, maxsector,
4642                                   rcaplong, sizeof(*rcaplong));
4643                         lbp = (lalba & SRC16_LBPME_A);
4644                         dp = &softc->params;
4645                         snprintf(announce_buf, DA_ANNOUNCETMP_SZ,
4646                             "%juMB (%ju %u byte sectors)",
4647                             ((uintmax_t)dp->secsize * dp->sectors) /
4648                              (1024 * 1024),
4649                             (uintmax_t)dp->sectors, dp->secsize);
4650                 }
4651         } else {
4652                 int error;
4653
4654                 /*
4655                  * Retry any UNIT ATTENTION type errors.  They
4656                  * are expected at boot.
4657                  */
4658                 error = daerror(done_ccb, CAM_RETRY_SELTO,
4659                                 SF_RETRY_UA|SF_NO_PRINT);
4660                 if (error == ERESTART) {
4661                         /*
4662                          * A retry was scheuled, so
4663                          * just return.
4664                          */
4665                         return;
4666                 } else if (error != 0) {
4667                         int asc, ascq;
4668                         int sense_key, error_code;
4669                         int have_sense;
4670                         cam_status status;
4671                         struct ccb_getdev cgd;
4672
4673                         /* Don't wedge this device's queue */
4674                         status = done_ccb->ccb_h.status;
4675                         if ((status & CAM_DEV_QFRZN) != 0)
4676                                 cam_release_devq(done_ccb->ccb_h.path,
4677                                                  /*relsim_flags*/0,
4678                                                  /*reduction*/0,
4679                                                  /*timeout*/0,
4680                                                  /*getcount_only*/0);
4681
4682
4683                         xpt_setup_ccb(&cgd.ccb_h, done_ccb->ccb_h.path,
4684                                       CAM_PRIORITY_NORMAL);
4685                         cgd.ccb_h.func_code = XPT_GDEV_TYPE;
4686                         xpt_action((union ccb *)&cgd);
4687
4688                         if (scsi_extract_sense_ccb(done_ccb,
4689                             &error_code, &sense_key, &asc, &ascq))
4690                                 have_sense = TRUE;
4691                         else
4692                                 have_sense = FALSE;
4693
4694                         /*
4695                          * If we tried READ CAPACITY(16) and failed,
4696                          * fallback to READ CAPACITY(10).
4697                          */
4698                         if ((state == DA_CCB_PROBE_RC16) &&
4699                             (softc->flags & DA_FLAG_CAN_RC16) &&
4700                             (((csio->ccb_h.status & CAM_STATUS_MASK) ==
4701                                 CAM_REQ_INVALID) ||
4702                              ((have_sense) &&
4703                               (error_code == SSD_CURRENT_ERROR ||
4704                                error_code == SSD_DESC_CURRENT_ERROR) &&
4705                               (sense_key == SSD_KEY_ILLEGAL_REQUEST)))) {
4706                                 cam_periph_assert(periph, MA_OWNED);
4707                                 softc->flags &= ~DA_FLAG_CAN_RC16;
4708                                 free(rdcap, M_SCSIDA);
4709                                 xpt_release_ccb(done_ccb);
4710                                 softc->state = DA_STATE_PROBE_RC;
4711                                 xpt_schedule(periph, priority);
4712                                 return;
4713                         }
4714
4715                         /*
4716                          * Attach to anything that claims to be a
4717                          * direct access or optical disk device,
4718                          * as long as it doesn't return a "Logical
4719                          * unit not supported" (0x25) error.
4720                          * "Internal Target Failure" (0x44) is also
4721                          * special and typically means that the
4722                          * device is a SATA drive behind a SATL
4723                          * translation that's fallen into a
4724                          * terminally fatal state.
4725                          */
4726                         if ((have_sense)
4727                          && (asc != 0x25) && (asc != 0x44)
4728                          && (error_code == SSD_CURRENT_ERROR
4729                           || error_code == SSD_DESC_CURRENT_ERROR)) {
4730                                 const char *sense_key_desc;
4731                                 const char *asc_desc;
4732
4733                                 dasetgeom(periph, 512, -1, NULL, 0);
4734                                 scsi_sense_desc(sense_key, asc, ascq,
4735                                                 &cgd.inq_data, &sense_key_desc,
4736                                                 &asc_desc);
4737                                 snprintf(announce_buf, DA_ANNOUNCETMP_SZ,
4738                                     "Attempt to query device "
4739                                     "size failed: %s, %s",
4740                                     sense_key_desc, asc_desc);
4741                         } else { 
4742                                 if (have_sense)
4743                                         scsi_sense_print(&done_ccb->csio);
4744                                 else {
4745                                         xpt_print(periph->path,
4746                                             "got CAM status %#x\n",
4747                                             done_ccb->ccb_h.status);
4748                                 }
4749
4750                                 xpt_print(periph->path, "fatal error, "
4751                                     "failed to attach to device\n");
4752
4753                                 announce_buf = NULL;
4754
4755                                 /*
4756                                  * Free up resources.
4757                                  */
4758                                 cam_periph_invalidate(periph);
4759                         } 
4760                 }
4761         }
4762         free(csio->data_ptr, M_SCSIDA);
4763         if (announce_buf != NULL &&
4764             ((softc->flags & DA_FLAG_ANNOUNCED) == 0)) {
4765                 struct sbuf sb;
4766
4767                 sbuf_new(&sb, softc->announcebuf, DA_ANNOUNCE_SZ,
4768                     SBUF_FIXEDLEN);
4769                 xpt_announce_periph_sbuf(periph, &sb, announce_buf);
4770                 xpt_announce_quirks_sbuf(periph, &sb, softc->quirks,
4771                     DA_Q_BIT_STRING);
4772                 sbuf_finish(&sb);
4773                 sbuf_putbuf(&sb);
4774
4775                 /*
4776                  * Create our sysctl variables, now that we know
4777                  * we have successfully attached.
4778                  */
4779                 /* increase the refcount */
4780                 if (da_periph_acquire(periph, DA_REF_SYSCTL) == 0) {
4781                         taskqueue_enqueue(taskqueue_thread,
4782                                           &softc->sysctl_task);
4783                 } else {
4784                         /* XXX This message is useless! */
4785                         xpt_print(periph->path, "fatal error, "
4786                             "could not acquire reference count\n");
4787                 }
4788         }
4789
4790         /* We already probed the device. */
4791         if (softc->flags & DA_FLAG_PROBED) {
4792                 daprobedone(periph, done_ccb);
4793                 return;
4794         }
4795
4796         /* Ensure re-probe doesn't see old delete. */
4797         softc->delete_available = 0;
4798         dadeleteflag(softc, DA_DELETE_ZERO, 1);
4799         if (lbp && (softc->quirks & DA_Q_NO_UNMAP) == 0) {
4800                 /*
4801                  * Based on older SBC-3 spec revisions
4802                  * any of the UNMAP methods "may" be
4803                  * available via LBP given this flag so
4804                  * we flag all of them as available and
4805                  * then remove those which further
4806                  * probes confirm aren't available
4807                  * later.
4808                  *
4809                  * We could also check readcap(16) p_type
4810                  * flag to exclude one or more invalid
4811                  * write same (X) types here
4812                  */
4813                 dadeleteflag(softc, DA_DELETE_WS16, 1);
4814                 dadeleteflag(softc, DA_DELETE_WS10, 1);
4815                 dadeleteflag(softc, DA_DELETE_UNMAP, 1);
4816
4817                 xpt_release_ccb(done_ccb);
4818                 softc->state = DA_STATE_PROBE_LBP;
4819                 xpt_schedule(periph, priority);
4820                 return;
4821         }
4822
4823         xpt_release_ccb(done_ccb);
4824         softc->state = DA_STATE_PROBE_BDC;
4825         xpt_schedule(periph, priority);
4826         return;
4827 }
4828
4829 static void
4830 dadone_probelbp(struct cam_periph *periph, union ccb *done_ccb)
4831 {
4832         struct scsi_vpd_logical_block_prov *lbp;
4833         struct da_softc *softc;
4834         struct ccb_scsiio *csio;
4835         u_int32_t  priority;
4836
4837         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_probelbp\n"));
4838
4839         softc = (struct da_softc *)periph->softc;
4840         priority = done_ccb->ccb_h.pinfo.priority;
4841         csio = &done_ccb->csio;
4842         lbp = (struct scsi_vpd_logical_block_prov *)csio->data_ptr;
4843
4844         cam_periph_assert(periph, MA_OWNED);
4845
4846         if ((csio->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) {
4847                 /*
4848                  * T10/1799-D Revision 31 states at least one of these
4849                  * must be supported but we don't currently enforce this.
4850                  */
4851                 dadeleteflag(softc, DA_DELETE_WS16,
4852                      (lbp->flags & SVPD_LBP_WS16));
4853                 dadeleteflag(softc, DA_DELETE_WS10,
4854                              (lbp->flags & SVPD_LBP_WS10));
4855                 dadeleteflag(softc, DA_DELETE_UNMAP,
4856                              (lbp->flags & SVPD_LBP_UNMAP));
4857         } else {
4858                 int error;
4859                 error = daerror(done_ccb, CAM_RETRY_SELTO,
4860                                 SF_RETRY_UA|SF_NO_PRINT);
4861                 if (error == ERESTART)
4862                         return;
4863                 else if (error != 0) {
4864                         if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0) {
4865                                 /* Don't wedge this device's queue */
4866                                 cam_release_devq(done_ccb->ccb_h.path,
4867                                                  /*relsim_flags*/0,
4868                                                  /*reduction*/0,
4869                                                  /*timeout*/0,
4870                                                  /*getcount_only*/0);
4871                         }
4872
4873                         /*
4874                          * Failure indicates we don't support any SBC-3
4875                          * delete methods with UNMAP
4876                          */
4877                 }
4878         }
4879
4880         free(lbp, M_SCSIDA);
4881         xpt_release_ccb(done_ccb);
4882         softc->state = DA_STATE_PROBE_BLK_LIMITS;
4883         xpt_schedule(periph, priority);
4884         return;
4885 }
4886
4887 static void
4888 dadone_probeblklimits(struct cam_periph *periph, union ccb *done_ccb)
4889 {
4890         struct scsi_vpd_block_limits *block_limits;
4891         struct da_softc *softc;
4892         struct ccb_scsiio *csio;
4893         u_int32_t  priority;
4894
4895         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_probeblklimits\n"));
4896
4897         softc = (struct da_softc *)periph->softc;
4898         priority = done_ccb->ccb_h.pinfo.priority;
4899         csio = &done_ccb->csio;
4900         block_limits = (struct scsi_vpd_block_limits *)csio->data_ptr;
4901
4902         cam_periph_assert(periph, MA_OWNED);
4903
4904         if ((csio->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) {
4905                 uint32_t max_txfer_len = scsi_4btoul(
4906                         block_limits->max_txfer_len);
4907                 uint32_t max_unmap_lba_cnt = scsi_4btoul(
4908                         block_limits->max_unmap_lba_cnt);
4909                 uint32_t max_unmap_blk_cnt = scsi_4btoul(
4910                         block_limits->max_unmap_blk_cnt);
4911                 uint32_t unmap_gran = scsi_4btoul(
4912                         block_limits->opt_unmap_grain);
4913                 uint32_t unmap_gran_align = scsi_4btoul(
4914                         block_limits->unmap_grain_align);
4915                 uint64_t ws_max_blks = scsi_8btou64(
4916                         block_limits->max_write_same_length);
4917
4918                 if (max_txfer_len != 0) {
4919                         softc->disk->d_maxsize = MIN(softc->maxio,
4920                             (off_t)max_txfer_len * softc->params.secsize);
4921                 }
4922
4923                 /*
4924                  * We should already support UNMAP but we check lba
4925                  * and block count to be sure
4926                  */
4927                 if (max_unmap_lba_cnt != 0x00L &&
4928                     max_unmap_blk_cnt != 0x00L) {
4929                         softc->unmap_max_lba = max_unmap_lba_cnt;
4930                         softc->unmap_max_ranges = min(max_unmap_blk_cnt,
4931                                 UNMAP_MAX_RANGES);
4932                         if (unmap_gran > 1) {
4933                                 softc->unmap_gran = unmap_gran;
4934                                 if (unmap_gran_align & 0x80000000) {
4935                                         softc->unmap_gran_align =
4936                                             unmap_gran_align & 0x7fffffff;
4937                                 }
4938                         }
4939                 } else {
4940                         /*
4941                          * Unexpected UNMAP limits which means the
4942                          * device doesn't actually support UNMAP
4943                          */
4944                         dadeleteflag(softc, DA_DELETE_UNMAP, 0);
4945                 }
4946
4947                 if (ws_max_blks != 0x00L)
4948                         softc->ws_max_blks = ws_max_blks;
4949         } else {
4950                 int error;
4951                 error = daerror(done_ccb, CAM_RETRY_SELTO,
4952                                 SF_RETRY_UA|SF_NO_PRINT);
4953                 if (error == ERESTART)
4954                         return;
4955                 else if (error != 0) {
4956                         if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0) {
4957                                 /* Don't wedge this device's queue */
4958                                 cam_release_devq(done_ccb->ccb_h.path,
4959                                                  /*relsim_flags*/0,
4960                                                  /*reduction*/0,
4961                                                  /*timeout*/0,
4962                                                  /*getcount_only*/0);
4963                         }
4964
4965                         /*
4966                          * Failure here doesn't mean UNMAP is not
4967                          * supported as this is an optional page.
4968                          */
4969                         softc->unmap_max_lba = 1;
4970                         softc->unmap_max_ranges = 1;
4971                 }
4972         }
4973
4974         free(block_limits, M_SCSIDA);
4975         xpt_release_ccb(done_ccb);
4976         softc->state = DA_STATE_PROBE_BDC;
4977         xpt_schedule(periph, priority);
4978         return;
4979 }
4980
4981 static void
4982 dadone_probebdc(struct cam_periph *periph, union ccb *done_ccb)
4983 {
4984         struct scsi_vpd_block_device_characteristics *bdc;
4985         struct da_softc *softc;
4986         struct ccb_scsiio *csio;
4987         u_int32_t  priority;
4988
4989         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_probebdc\n"));
4990
4991         softc = (struct da_softc *)periph->softc;
4992         priority = done_ccb->ccb_h.pinfo.priority;
4993         csio = &done_ccb->csio;
4994         bdc = (struct scsi_vpd_block_device_characteristics *)csio->data_ptr;
4995
4996         cam_periph_assert(periph, MA_OWNED);
4997
4998         if ((csio->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) {
4999                 uint32_t valid_len;
5000
5001                 /*
5002                  * Disable queue sorting for non-rotational media
5003                  * by default.
5004                  */
5005                 u_int16_t old_rate = softc->disk->d_rotation_rate;
5006
5007                 valid_len = csio->dxfer_len - csio->resid;
5008                 if (SBDC_IS_PRESENT(bdc, valid_len,
5009                     medium_rotation_rate)) {
5010                         softc->disk->d_rotation_rate =
5011                                 scsi_2btoul(bdc->medium_rotation_rate);
5012                         if (softc->disk->d_rotation_rate ==
5013                             SVPD_BDC_RATE_NON_ROTATING) {
5014                                 cam_iosched_set_sort_queue(
5015                                     softc->cam_iosched, 0);
5016                                 softc->rotating = 0;
5017                         }
5018                         if (softc->disk->d_rotation_rate != old_rate) {
5019                                 disk_attr_changed(softc->disk,
5020                                     "GEOM::rotation_rate", M_NOWAIT);
5021                         }
5022                 }
5023                 if ((SBDC_IS_PRESENT(bdc, valid_len, flags))
5024                  && (softc->zone_mode == DA_ZONE_NONE)) {
5025                         int ata_proto;
5026
5027                         if (scsi_vpd_supported_page(periph,
5028                             SVPD_ATA_INFORMATION))
5029                                 ata_proto = 1;
5030                         else
5031                                 ata_proto = 0;
5032
5033                         /*
5034                          * The Zoned field will only be set for
5035                          * Drive Managed and Host Aware drives.  If
5036                          * they are Host Managed, the device type
5037                          * in the standard INQUIRY data should be
5038                          * set to T_ZBC_HM (0x14).
5039                          */
5040                         if ((bdc->flags & SVPD_ZBC_MASK) ==
5041                              SVPD_HAW_ZBC) {
5042                                 softc->zone_mode = DA_ZONE_HOST_AWARE;
5043                                 softc->zone_interface = (ata_proto) ?
5044                                    DA_ZONE_IF_ATA_SAT : DA_ZONE_IF_SCSI;
5045                         } else if ((bdc->flags & SVPD_ZBC_MASK) ==
5046                              SVPD_DM_ZBC) {
5047                                 softc->zone_mode =DA_ZONE_DRIVE_MANAGED;
5048                                 softc->zone_interface = (ata_proto) ?
5049                                    DA_ZONE_IF_ATA_SAT : DA_ZONE_IF_SCSI;
5050                         } else if ((bdc->flags & SVPD_ZBC_MASK) != 
5051                                   SVPD_ZBC_NR) {
5052                                 xpt_print(periph->path, "Unknown zoned "
5053                                     "type %#x",
5054                                     bdc->flags & SVPD_ZBC_MASK);
5055                         }
5056                 }
5057         } else {
5058                 int error;
5059                 error = daerror(done_ccb, CAM_RETRY_SELTO,
5060                                 SF_RETRY_UA|SF_NO_PRINT);
5061                 if (error == ERESTART)
5062                         return;
5063                 else if (error != 0) {
5064                         if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0) {
5065                                 /* Don't wedge this device's queue */
5066                                 cam_release_devq(done_ccb->ccb_h.path,
5067                                                  /*relsim_flags*/0,
5068                                                  /*reduction*/0,
5069                                                  /*timeout*/0,
5070                                                  /*getcount_only*/0);
5071                         }
5072                 }
5073         }
5074
5075         free(bdc, M_SCSIDA);
5076         xpt_release_ccb(done_ccb);
5077         softc->state = DA_STATE_PROBE_ATA;
5078         xpt_schedule(periph, priority);
5079         return;
5080 }
5081
5082 static void
5083 dadone_probeata(struct cam_periph *periph, union ccb *done_ccb)
5084 {
5085         struct ata_params *ata_params;
5086         struct ccb_scsiio *csio;
5087         struct da_softc *softc;
5088         u_int32_t  priority;
5089         int continue_probe;
5090         int error, i;
5091         int16_t *ptr;
5092
5093         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_probeata\n"));
5094
5095         softc = (struct da_softc *)periph->softc;
5096         priority = done_ccb->ccb_h.pinfo.priority;
5097         csio = &done_ccb->csio;
5098         ata_params = (struct ata_params *)csio->data_ptr;
5099         ptr = (uint16_t *)ata_params;
5100         continue_probe = 0;
5101         error = 0;
5102
5103         cam_periph_assert(periph, MA_OWNED);
5104
5105         if ((csio->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) {
5106                 uint16_t old_rate;
5107
5108                 for (i = 0; i < sizeof(*ata_params) / 2; i++)
5109                         ptr[i] = le16toh(ptr[i]);
5110                 if (ata_params->support_dsm & ATA_SUPPORT_DSM_TRIM &&
5111                     (softc->quirks & DA_Q_NO_UNMAP) == 0) {
5112                         dadeleteflag(softc, DA_DELETE_ATA_TRIM, 1);
5113                         if (ata_params->max_dsm_blocks != 0)
5114                                 softc->trim_max_ranges = min(
5115                                   softc->trim_max_ranges,
5116                                   ata_params->max_dsm_blocks *
5117                                   ATA_DSM_BLK_RANGES);
5118                 }
5119                 /*
5120                  * Disable queue sorting for non-rotational media
5121                  * by default.
5122                  */
5123                 old_rate = softc->disk->d_rotation_rate;
5124                 softc->disk->d_rotation_rate = ata_params->media_rotation_rate;
5125                 if (softc->disk->d_rotation_rate == ATA_RATE_NON_ROTATING) {
5126                         cam_iosched_set_sort_queue(softc->cam_iosched, 0);
5127                         softc->rotating = 0;
5128                 }
5129                 if (softc->disk->d_rotation_rate != old_rate) {
5130                         disk_attr_changed(softc->disk,
5131                             "GEOM::rotation_rate", M_NOWAIT);
5132                 }
5133
5134                 cam_periph_assert(periph, MA_OWNED);
5135                 if (ata_params->capabilities1 & ATA_SUPPORT_DMA)
5136                         softc->flags |= DA_FLAG_CAN_ATA_DMA;
5137
5138                 if (ata_params->support.extension & ATA_SUPPORT_GENLOG)
5139                         softc->flags |= DA_FLAG_CAN_ATA_LOG;
5140
5141                 /*
5142                  * At this point, if we have a SATA host aware drive,
5143                  * we communicate via ATA passthrough unless the
5144                  * SAT layer supports ZBC -> ZAC translation.  In
5145                  * that case,
5146                  *
5147                  * XXX KDM figure out how to detect a host managed
5148                  * SATA drive.
5149                  */
5150                 if (softc->zone_mode == DA_ZONE_NONE) {
5151                         /*
5152                          * Note that we don't override the zone
5153                          * mode or interface if it has already been
5154                          * set.  This is because it has either been
5155                          * set as a quirk, or when we probed the
5156                          * SCSI Block Device Characteristics page,
5157                          * the zoned field was set.  The latter
5158                          * means that the SAT layer supports ZBC to
5159                          * ZAC translation, and we would prefer to
5160                          * use that if it is available.
5161                          */
5162                         if ((ata_params->support3 &
5163                             ATA_SUPPORT_ZONE_MASK) ==
5164                             ATA_SUPPORT_ZONE_HOST_AWARE) {
5165                                 softc->zone_mode = DA_ZONE_HOST_AWARE;
5166                                 softc->zone_interface =
5167                                     DA_ZONE_IF_ATA_PASS;
5168                         } else if ((ata_params->support3 &
5169                                     ATA_SUPPORT_ZONE_MASK) ==
5170                                     ATA_SUPPORT_ZONE_DEV_MANAGED) {
5171                                 softc->zone_mode =DA_ZONE_DRIVE_MANAGED;
5172                                 softc->zone_interface = DA_ZONE_IF_ATA_PASS;
5173                         }
5174                 }
5175
5176         } else {
5177                 error = daerror(done_ccb, CAM_RETRY_SELTO,
5178                                 SF_RETRY_UA|SF_NO_PRINT);
5179                 if (error == ERESTART)
5180                         return;
5181                 else if (error != 0) {
5182                         if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0) {
5183                                 /* Don't wedge this device's queue */
5184                                 cam_release_devq(done_ccb->ccb_h.path,
5185                                                  /*relsim_flags*/0,
5186                                                  /*reduction*/0,
5187                                                  /*timeout*/0,
5188                                                  /*getcount_only*/0);
5189                         }
5190                 }
5191         }
5192
5193         free(ata_params, M_SCSIDA);
5194         if ((softc->zone_mode == DA_ZONE_HOST_AWARE)
5195          || (softc->zone_mode == DA_ZONE_HOST_MANAGED)) {
5196                 /*
5197                  * If the ATA IDENTIFY failed, we could be talking
5198                  * to a SCSI drive, although that seems unlikely,
5199                  * since the drive did report that it supported the 
5200                  * ATA Information VPD page.  If the ATA IDENTIFY
5201                  * succeeded, and the SAT layer doesn't support
5202                  * ZBC -> ZAC translation, continue on to get the
5203                  * directory of ATA logs, and complete the rest of
5204                  * the ZAC probe.  If the SAT layer does support
5205                  * ZBC -> ZAC translation, we want to use that,
5206                  * and we'll probe the SCSI Zoned Block Device
5207                  * Characteristics VPD page next.
5208                  */
5209                 if ((error == 0)
5210                  && (softc->flags & DA_FLAG_CAN_ATA_LOG)
5211                  && (softc->zone_interface == DA_ZONE_IF_ATA_PASS))
5212                         softc->state = DA_STATE_PROBE_ATA_LOGDIR;
5213                 else
5214                         softc->state = DA_STATE_PROBE_ZONE;
5215                 continue_probe = 1;
5216         }
5217         if (continue_probe != 0) {
5218                 xpt_release_ccb(done_ccb);
5219                 xpt_schedule(periph, priority);
5220                 return;
5221         } else
5222                 daprobedone(periph, done_ccb);
5223         return;
5224 }
5225
5226 static void
5227 dadone_probeatalogdir(struct cam_periph *periph, union ccb *done_ccb)
5228 {
5229         struct da_softc *softc;
5230         struct ccb_scsiio *csio;
5231         u_int32_t  priority;
5232         int error;
5233
5234         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_probeatalogdir\n"));
5235
5236         softc = (struct da_softc *)periph->softc;
5237         priority = done_ccb->ccb_h.pinfo.priority;
5238         csio = &done_ccb->csio;
5239
5240         cam_periph_assert(periph, MA_OWNED);
5241         if ((csio->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) {
5242                 error = 0;
5243                 softc->valid_logdir_len = 0;
5244                 bzero(&softc->ata_logdir, sizeof(softc->ata_logdir));
5245                 softc->valid_logdir_len = csio->dxfer_len - csio->resid;
5246                 if (softc->valid_logdir_len > 0)
5247                         bcopy(csio->data_ptr, &softc->ata_logdir,
5248                             min(softc->valid_logdir_len,
5249                                 sizeof(softc->ata_logdir)));
5250                 /*
5251                  * Figure out whether the Identify Device log is
5252                  * supported.  The General Purpose log directory
5253                  * has a header, and lists the number of pages
5254                  * available for each GP log identified by the
5255                  * offset into the list.
5256                  */
5257                 if ((softc->valid_logdir_len >=
5258                     ((ATA_IDENTIFY_DATA_LOG + 1) * sizeof(uint16_t)))
5259                  && (le16dec(softc->ata_logdir.header) == 
5260                      ATA_GP_LOG_DIR_VERSION)
5261                  && (le16dec(&softc->ata_logdir.num_pages[
5262                      (ATA_IDENTIFY_DATA_LOG *
5263                      sizeof(uint16_t)) - sizeof(uint16_t)]) > 0)){
5264                         softc->flags |= DA_FLAG_CAN_ATA_IDLOG;
5265                 } else {
5266                         softc->flags &= ~DA_FLAG_CAN_ATA_IDLOG;
5267                 }
5268         } else {
5269                 error = daerror(done_ccb, CAM_RETRY_SELTO,
5270                                 SF_RETRY_UA|SF_NO_PRINT);
5271                 if (error == ERESTART)
5272                         return;
5273                 else if (error != 0) {
5274                         /*
5275                          * If we can't get the ATA log directory,
5276                          * then ATA logs are effectively not
5277                          * supported even if the bit is set in the
5278                          * identify data.
5279                          */ 
5280                         softc->flags &= ~(DA_FLAG_CAN_ATA_LOG |
5281                                           DA_FLAG_CAN_ATA_IDLOG);
5282                         if ((done_ccb->ccb_h.status &
5283                              CAM_DEV_QFRZN) != 0) {
5284                                 /* Don't wedge this device's queue */
5285                                 cam_release_devq(done_ccb->ccb_h.path,
5286                                                  /*relsim_flags*/0,
5287                                                  /*reduction*/0,
5288                                                  /*timeout*/0,
5289                                                  /*getcount_only*/0);
5290                         }
5291                 }
5292         }
5293
5294         free(csio->data_ptr, M_SCSIDA);
5295
5296         if ((error == 0)
5297          && (softc->flags & DA_FLAG_CAN_ATA_IDLOG)) {
5298                 softc->state = DA_STATE_PROBE_ATA_IDDIR;
5299                 xpt_release_ccb(done_ccb);
5300                 xpt_schedule(periph, priority);
5301                 return;
5302         } 
5303         daprobedone(periph, done_ccb);
5304         return;
5305 }
5306
5307 static void
5308 dadone_probeataiddir(struct cam_periph *periph, union ccb *done_ccb)
5309 {
5310         struct da_softc *softc;
5311         struct ccb_scsiio *csio;
5312         u_int32_t  priority;
5313         int error;
5314
5315         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_probeataiddir\n"));
5316
5317         softc = (struct da_softc *)periph->softc;
5318         priority = done_ccb->ccb_h.pinfo.priority;
5319         csio = &done_ccb->csio;
5320
5321         cam_periph_assert(periph, MA_OWNED);
5322
5323         if ((csio->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) {
5324                 off_t entries_offset, max_entries;
5325                 error = 0;
5326
5327                 softc->valid_iddir_len = 0;
5328                 bzero(&softc->ata_iddir, sizeof(softc->ata_iddir));
5329                 softc->flags &= ~(DA_FLAG_CAN_ATA_SUPCAP |
5330                                   DA_FLAG_CAN_ATA_ZONE);
5331                 softc->valid_iddir_len = csio->dxfer_len - csio->resid;
5332                 if (softc->valid_iddir_len > 0)
5333                         bcopy(csio->data_ptr, &softc->ata_iddir,
5334                             min(softc->valid_iddir_len,
5335                                 sizeof(softc->ata_iddir)));
5336
5337                 entries_offset =
5338                     __offsetof(struct ata_identify_log_pages,entries);
5339                 max_entries = softc->valid_iddir_len - entries_offset;
5340                 if ((softc->valid_iddir_len > (entries_offset + 1))
5341                  && (le64dec(softc->ata_iddir.header) == ATA_IDLOG_REVISION)
5342                  && (softc->ata_iddir.entry_count > 0)) {
5343                         int num_entries, i;
5344
5345                         num_entries = softc->ata_iddir.entry_count;
5346                         num_entries = min(num_entries,
5347                            softc->valid_iddir_len - entries_offset);
5348                         for (i = 0; i < num_entries && i < max_entries; i++) {
5349                                 if (softc->ata_iddir.entries[i] ==
5350                                     ATA_IDL_SUP_CAP)
5351                                         softc->flags |= DA_FLAG_CAN_ATA_SUPCAP;
5352                                 else if (softc->ata_iddir.entries[i] ==
5353                                          ATA_IDL_ZDI)
5354                                         softc->flags |= DA_FLAG_CAN_ATA_ZONE;
5355
5356                                 if ((softc->flags & DA_FLAG_CAN_ATA_SUPCAP)
5357                                  && (softc->flags & DA_FLAG_CAN_ATA_ZONE))
5358                                         break;
5359                         }
5360                 }
5361         } else {
5362                 error = daerror(done_ccb, CAM_RETRY_SELTO,
5363                                 SF_RETRY_UA|SF_NO_PRINT);
5364                 if (error == ERESTART)
5365                         return;
5366                 else if (error != 0) {
5367                         /*
5368                          * If we can't get the ATA Identify Data log
5369                          * directory, then it effectively isn't
5370                          * supported even if the ATA Log directory
5371                          * a non-zero number of pages present for
5372                          * this log.
5373                          */
5374                         softc->flags &= ~DA_FLAG_CAN_ATA_IDLOG;
5375                         if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0) {
5376                                 /* Don't wedge this device's queue */
5377                                 cam_release_devq(done_ccb->ccb_h.path,
5378                                                  /*relsim_flags*/0,
5379                                                  /*reduction*/0,
5380                                                  /*timeout*/0,
5381                                                  /*getcount_only*/0);
5382                         }
5383                 }
5384         }
5385
5386         free(csio->data_ptr, M_SCSIDA);
5387
5388         if ((error == 0) && (softc->flags & DA_FLAG_CAN_ATA_SUPCAP)) {
5389                 softc->state = DA_STATE_PROBE_ATA_SUP;
5390                 xpt_release_ccb(done_ccb);
5391                 xpt_schedule(periph, priority);
5392                 return;
5393         } 
5394         daprobedone(periph, done_ccb);
5395         return;
5396 }
5397
5398 static void
5399 dadone_probeatasup(struct cam_periph *periph, union ccb *done_ccb)
5400 {
5401         struct da_softc *softc;
5402         struct ccb_scsiio *csio;
5403         u_int32_t  priority;
5404         int error;
5405
5406         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_probeatasup\n"));
5407
5408         softc = (struct da_softc *)periph->softc;
5409         priority = done_ccb->ccb_h.pinfo.priority;
5410         csio = &done_ccb->csio;
5411
5412         cam_periph_assert(periph, MA_OWNED);
5413
5414         if ((csio->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) {
5415                 uint32_t valid_len;
5416                 size_t needed_size;
5417                 struct ata_identify_log_sup_cap *sup_cap;
5418                 error = 0;
5419
5420                 sup_cap = (struct ata_identify_log_sup_cap *)csio->data_ptr;
5421                 valid_len = csio->dxfer_len - csio->resid;
5422                 needed_size = __offsetof(struct ata_identify_log_sup_cap,
5423                     sup_zac_cap) + 1 + sizeof(sup_cap->sup_zac_cap);
5424                 if (valid_len >= needed_size) {
5425                         uint64_t zoned, zac_cap;
5426
5427                         zoned = le64dec(sup_cap->zoned_cap);
5428                         if (zoned & ATA_ZONED_VALID) {
5429                                 /*
5430                                  * This should have already been
5431                                  * set, because this is also in the
5432                                  * ATA identify data.
5433                                  */
5434                                 if ((zoned & ATA_ZONED_MASK) ==
5435                                     ATA_SUPPORT_ZONE_HOST_AWARE)
5436                                         softc->zone_mode = DA_ZONE_HOST_AWARE;
5437                                 else if ((zoned & ATA_ZONED_MASK) ==
5438                                     ATA_SUPPORT_ZONE_DEV_MANAGED)
5439                                         softc->zone_mode =
5440                                             DA_ZONE_DRIVE_MANAGED;
5441                         }
5442
5443                         zac_cap = le64dec(sup_cap->sup_zac_cap);
5444                         if (zac_cap & ATA_SUP_ZAC_CAP_VALID) {
5445                                 if (zac_cap & ATA_REPORT_ZONES_SUP)
5446                                         softc->zone_flags |=
5447                                             DA_ZONE_FLAG_RZ_SUP;
5448                                 if (zac_cap & ATA_ND_OPEN_ZONE_SUP)
5449                                         softc->zone_flags |=
5450                                             DA_ZONE_FLAG_OPEN_SUP;
5451                                 if (zac_cap & ATA_ND_CLOSE_ZONE_SUP)
5452                                         softc->zone_flags |=
5453                                             DA_ZONE_FLAG_CLOSE_SUP;
5454                                 if (zac_cap & ATA_ND_FINISH_ZONE_SUP)
5455                                         softc->zone_flags |=
5456                                             DA_ZONE_FLAG_FINISH_SUP;
5457                                 if (zac_cap & ATA_ND_RWP_SUP)
5458                                         softc->zone_flags |=
5459                                             DA_ZONE_FLAG_RWP_SUP;
5460                         } else {
5461                                 /*
5462                                  * This field was introduced in
5463                                  * ACS-4, r08 on April 28th, 2015.
5464                                  * If the drive firmware was written
5465                                  * to an earlier spec, it won't have
5466                                  * the field.  So, assume all
5467                                  * commands are supported.
5468                                  */ 
5469                                 softc->zone_flags |= DA_ZONE_FLAG_SUP_MASK;
5470                         }
5471                                     
5472                 }
5473         } else {
5474                 error = daerror(done_ccb, CAM_RETRY_SELTO,
5475                                 SF_RETRY_UA|SF_NO_PRINT);
5476                 if (error == ERESTART)
5477                         return;
5478                 else if (error != 0) {
5479                         /*
5480                          * If we can't get the ATA Identify Data
5481                          * Supported Capabilities page, clear the
5482                          * flag...
5483                          */
5484                         softc->flags &= ~DA_FLAG_CAN_ATA_SUPCAP;
5485                         /*
5486                          * And clear zone capabilities.
5487                          */
5488                         softc->zone_flags &= ~DA_ZONE_FLAG_SUP_MASK;
5489                         if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0) {
5490                                 /* Don't wedge this device's queue */
5491                                 cam_release_devq(done_ccb->ccb_h.path,
5492                                                  /*relsim_flags*/0,
5493                                                  /*reduction*/0,
5494                                                  /*timeout*/0,
5495                                                  /*getcount_only*/0);
5496                         }
5497                 }
5498         }
5499
5500         free(csio->data_ptr, M_SCSIDA);
5501
5502         if ((error == 0) && (softc->flags & DA_FLAG_CAN_ATA_ZONE)) {
5503                 softc->state = DA_STATE_PROBE_ATA_ZONE;
5504                 xpt_release_ccb(done_ccb);
5505                 xpt_schedule(periph, priority);
5506                 return;
5507         } 
5508         daprobedone(periph, done_ccb);
5509         return;
5510 }
5511
5512 static void
5513 dadone_probeatazone(struct cam_periph *periph, union ccb *done_ccb)
5514 {
5515         struct da_softc *softc;
5516         struct ccb_scsiio *csio;
5517         int error;
5518
5519         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_probeatazone\n"));
5520
5521         softc = (struct da_softc *)periph->softc;
5522         csio = &done_ccb->csio;
5523
5524         cam_periph_assert(periph, MA_OWNED);
5525
5526         if ((csio->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) {
5527                 struct ata_zoned_info_log *zi_log;
5528                 uint32_t valid_len;
5529                 size_t needed_size;
5530
5531                 zi_log = (struct ata_zoned_info_log *)csio->data_ptr;
5532
5533                 valid_len = csio->dxfer_len - csio->resid;
5534                 needed_size = __offsetof(struct ata_zoned_info_log,
5535                     version_info) + 1 + sizeof(zi_log->version_info);
5536                 if (valid_len >= needed_size) {
5537                         uint64_t tmpvar;
5538
5539                         tmpvar = le64dec(zi_log->zoned_cap);
5540                         if (tmpvar & ATA_ZDI_CAP_VALID) {
5541                                 if (tmpvar & ATA_ZDI_CAP_URSWRZ)
5542                                         softc->zone_flags |=
5543                                             DA_ZONE_FLAG_URSWRZ;
5544                                 else
5545                                         softc->zone_flags &=
5546                                             ~DA_ZONE_FLAG_URSWRZ;
5547                         }
5548                         tmpvar = le64dec(zi_log->optimal_seq_zones);
5549                         if (tmpvar & ATA_ZDI_OPT_SEQ_VALID) {
5550                                 softc->zone_flags |= DA_ZONE_FLAG_OPT_SEQ_SET;
5551                                 softc->optimal_seq_zones = (tmpvar &
5552                                     ATA_ZDI_OPT_SEQ_MASK);
5553                         } else {
5554                                 softc->zone_flags &= ~DA_ZONE_FLAG_OPT_SEQ_SET;
5555                                 softc->optimal_seq_zones = 0;
5556                         }
5557
5558                         tmpvar =le64dec(zi_log->optimal_nonseq_zones);
5559                         if (tmpvar & ATA_ZDI_OPT_NS_VALID) {
5560                                 softc->zone_flags |=
5561                                     DA_ZONE_FLAG_OPT_NONSEQ_SET;
5562                                 softc->optimal_nonseq_zones =
5563                                     (tmpvar & ATA_ZDI_OPT_NS_MASK);
5564                         } else {
5565                                 softc->zone_flags &=
5566                                     ~DA_ZONE_FLAG_OPT_NONSEQ_SET;
5567                                 softc->optimal_nonseq_zones = 0;
5568                         }
5569
5570                         tmpvar = le64dec(zi_log->max_seq_req_zones);
5571                         if (tmpvar & ATA_ZDI_MAX_SEQ_VALID) {
5572                                 softc->zone_flags |= DA_ZONE_FLAG_MAX_SEQ_SET;
5573                                 softc->max_seq_zones =
5574                                     (tmpvar & ATA_ZDI_MAX_SEQ_MASK);
5575                         } else {
5576                                 softc->zone_flags &= ~DA_ZONE_FLAG_MAX_SEQ_SET;
5577                                 softc->max_seq_zones = 0;
5578                         }
5579                 }
5580         } else {
5581                 error = daerror(done_ccb, CAM_RETRY_SELTO,
5582                                 SF_RETRY_UA|SF_NO_PRINT);
5583                 if (error == ERESTART)
5584                         return;
5585                 else if (error != 0) {
5586                         softc->flags &= ~DA_FLAG_CAN_ATA_ZONE;
5587                         softc->flags &= ~DA_ZONE_FLAG_SET_MASK;
5588
5589                         if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0) {
5590                                 /* Don't wedge this device's queue */
5591                                 cam_release_devq(done_ccb->ccb_h.path,
5592                                                  /*relsim_flags*/0,
5593                                                  /*reduction*/0,
5594                                                  /*timeout*/0,
5595                                                  /*getcount_only*/0);
5596                         }
5597                 }
5598
5599         }
5600
5601         free(csio->data_ptr, M_SCSIDA);
5602
5603         daprobedone(periph, done_ccb);
5604         return;
5605 }
5606
5607 static void
5608 dadone_probezone(struct cam_periph *periph, union ccb *done_ccb)
5609 {
5610         struct da_softc *softc;
5611         struct ccb_scsiio *csio;
5612         int error;
5613
5614         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_probezone\n"));
5615
5616         softc = (struct da_softc *)periph->softc;
5617         csio = &done_ccb->csio;
5618
5619         cam_periph_assert(periph, MA_OWNED);
5620
5621         if ((csio->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_CMP) {
5622                 uint32_t valid_len;
5623                 size_t needed_len;
5624                 struct scsi_vpd_zoned_bdc *zoned_bdc;
5625
5626                 error = 0;
5627                 zoned_bdc = (struct scsi_vpd_zoned_bdc *)csio->data_ptr;
5628                 valid_len = csio->dxfer_len - csio->resid;
5629                 needed_len = __offsetof(struct scsi_vpd_zoned_bdc,
5630                     max_seq_req_zones) + 1 +
5631                     sizeof(zoned_bdc->max_seq_req_zones);
5632                 if ((valid_len >= needed_len)
5633                  && (scsi_2btoul(zoned_bdc->page_length) >= SVPD_ZBDC_PL)) {
5634                         if (zoned_bdc->flags & SVPD_ZBDC_URSWRZ)
5635                                 softc->zone_flags |= DA_ZONE_FLAG_URSWRZ;
5636                         else
5637                                 softc->zone_flags &= ~DA_ZONE_FLAG_URSWRZ;
5638                         softc->optimal_seq_zones =
5639                             scsi_4btoul(zoned_bdc->optimal_seq_zones);
5640                         softc->zone_flags |= DA_ZONE_FLAG_OPT_SEQ_SET;
5641                         softc->optimal_nonseq_zones = scsi_4btoul(
5642                             zoned_bdc->optimal_nonseq_zones);
5643                         softc->zone_flags |= DA_ZONE_FLAG_OPT_NONSEQ_SET;
5644                         softc->max_seq_zones =
5645                             scsi_4btoul(zoned_bdc->max_seq_req_zones);
5646                         softc->zone_flags |= DA_ZONE_FLAG_MAX_SEQ_SET;
5647                 }
5648                 /*
5649                  * All of the zone commands are mandatory for SCSI
5650                  * devices.
5651                  *
5652                  * XXX KDM this is valid as of September 2015.
5653                  * Re-check this assumption once the SAT spec is
5654                  * updated to support SCSI ZBC to ATA ZAC mapping.
5655                  * Since ATA allows zone commands to be reported
5656                  * as supported or not, this may not necessarily
5657                  * be true for an ATA device behind a SAT (SCSI to
5658                  * ATA Translation) layer.
5659                  */
5660                 softc->zone_flags |= DA_ZONE_FLAG_SUP_MASK;
5661         } else {
5662                 error = daerror(done_ccb, CAM_RETRY_SELTO,
5663                                 SF_RETRY_UA|SF_NO_PRINT);
5664                 if (error == ERESTART)
5665                         return;
5666                 else if (error != 0) {
5667                         if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0) {
5668                                 /* Don't wedge this device's queue */
5669                                 cam_release_devq(done_ccb->ccb_h.path,
5670                                                  /*relsim_flags*/0,
5671                                                  /*reduction*/0,
5672                                                  /*timeout*/0,
5673                                                  /*getcount_only*/0);
5674                         }
5675                 }
5676         }
5677         daprobedone(periph, done_ccb);
5678         return;
5679 }
5680
5681 static void
5682 dadone_tur(struct cam_periph *periph, union ccb *done_ccb)
5683 {
5684         struct da_softc *softc;
5685         struct ccb_scsiio *csio;
5686
5687         CAM_DEBUG(periph->path, CAM_DEBUG_TRACE, ("dadone_tur\n"));
5688
5689         softc = (struct da_softc *)periph->softc;
5690         csio = &done_ccb->csio;
5691
5692         cam_periph_assert(periph, MA_OWNED);
5693
5694         if ((done_ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) {
5695
5696                 if (daerror(done_ccb, CAM_RETRY_SELTO,
5697                     SF_RETRY_UA | SF_NO_RECOVERY | SF_NO_PRINT) == ERESTART)
5698                         return; /* Will complete again, keep reference */
5699                 if ((done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0)
5700                         cam_release_devq(done_ccb->ccb_h.path,
5701                                          /*relsim_flags*/0,
5702                                          /*reduction*/0,
5703                                          /*timeout*/0,
5704                                          /*getcount_only*/0);
5705         }
5706         xpt_release_ccb(done_ccb);
5707         softc->flags &= ~DA_FLAG_TUR_PENDING;
5708         da_periph_release_locked(periph, DA_REF_TUR);
5709         return;
5710 }
5711
5712 static void
5713 dareprobe(struct cam_periph *periph)
5714 {
5715         struct da_softc   *softc;
5716         int status;
5717
5718         softc = (struct da_softc *)periph->softc;
5719
5720         /* Probe in progress; don't interfere. */
5721         if (softc->state != DA_STATE_NORMAL)
5722                 return;
5723
5724         status = da_periph_acquire(periph, DA_REF_REPROBE);
5725         KASSERT(status == 0, ("dareprobe: cam_periph_acquire failed"));
5726
5727         softc->state = DA_STATE_PROBE_WP;
5728         xpt_schedule(periph, CAM_PRIORITY_DEV);
5729 }
5730
5731 static int
5732 daerror(union ccb *ccb, u_int32_t cam_flags, u_int32_t sense_flags)
5733 {
5734         struct da_softc   *softc;
5735         struct cam_periph *periph;
5736         int error, error_code, sense_key, asc, ascq;
5737
5738 #if defined(BUF_TRACKING) || defined(FULL_BUF_TRACKING)
5739         if (ccb->csio.bio != NULL)
5740                 biotrack(ccb->csio.bio, __func__);
5741 #endif
5742
5743         periph = xpt_path_periph(ccb->ccb_h.path);
5744         softc = (struct da_softc *)periph->softc;
5745
5746         cam_periph_assert(periph, MA_OWNED);
5747
5748         /*
5749          * Automatically detect devices that do not support
5750          * READ(6)/WRITE(6) and upgrade to using 10 byte cdbs.
5751          */
5752         error = 0;
5753         if ((ccb->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_INVALID) {
5754                 error = cmd6workaround(ccb);
5755         } else if (scsi_extract_sense_ccb(ccb,
5756             &error_code, &sense_key, &asc, &ascq)) {
5757                 if (sense_key == SSD_KEY_ILLEGAL_REQUEST)
5758                         error = cmd6workaround(ccb);
5759                 /*
5760                  * If the target replied with CAPACITY DATA HAS CHANGED UA,
5761                  * query the capacity and notify upper layers.
5762                  */
5763                 else if (sense_key == SSD_KEY_UNIT_ATTENTION &&
5764                     asc == 0x2A && ascq == 0x09) {
5765                         xpt_print(periph->path, "Capacity data has changed\n");
5766                         softc->flags &= ~DA_FLAG_PROBED;
5767                         dareprobe(periph);
5768                         sense_flags |= SF_NO_PRINT;
5769                 } else if (sense_key == SSD_KEY_UNIT_ATTENTION &&
5770                     asc == 0x28 && ascq == 0x00) {
5771                         softc->flags &= ~DA_FLAG_PROBED;
5772                         disk_media_changed(softc->disk, M_NOWAIT);
5773                 } else if (sense_key == SSD_KEY_UNIT_ATTENTION &&
5774                     asc == 0x3F && ascq == 0x03) {
5775                         xpt_print(periph->path, "INQUIRY data has changed\n");
5776                         softc->flags &= ~DA_FLAG_PROBED;
5777                         dareprobe(periph);
5778                         sense_flags |= SF_NO_PRINT;
5779                 } else if (sense_key == SSD_KEY_NOT_READY &&
5780                     asc == 0x3a && (softc->flags & DA_FLAG_PACK_INVALID) == 0) {
5781                         softc->flags |= DA_FLAG_PACK_INVALID;
5782                         disk_media_gone(softc->disk, M_NOWAIT);
5783                 }
5784         }
5785         if (error == ERESTART)
5786                 return (ERESTART);
5787
5788 #ifdef CAM_IO_STATS
5789         switch (ccb->ccb_h.status & CAM_STATUS_MASK) {
5790         case CAM_CMD_TIMEOUT:
5791                 softc->timeouts++;
5792                 break;
5793         case CAM_REQ_ABORTED:
5794         case CAM_REQ_CMP_ERR:
5795         case CAM_REQ_TERMIO:
5796         case CAM_UNREC_HBA_ERROR:
5797         case CAM_DATA_RUN_ERR:
5798                 softc->errors++;
5799                 break;
5800         default:
5801                 break;
5802         }
5803 #endif
5804
5805         /*
5806          * XXX
5807          * Until we have a better way of doing pack validation,
5808          * don't treat UAs as errors.
5809          */
5810         sense_flags |= SF_RETRY_UA;
5811
5812         if (softc->quirks & DA_Q_RETRY_BUSY)
5813                 sense_flags |= SF_RETRY_BUSY;
5814         return(cam_periph_error(ccb, cam_flags, sense_flags));
5815 }
5816
5817 static void
5818 damediapoll(void *arg)
5819 {
5820         struct cam_periph *periph = arg;
5821         struct da_softc *softc = periph->softc;
5822
5823         if (!cam_iosched_has_work_flags(softc->cam_iosched, DA_WORK_TUR) &&
5824             (softc->flags & DA_FLAG_TUR_PENDING) == 0 &&
5825             LIST_EMPTY(&softc->pending_ccbs)) {
5826                 if (da_periph_acquire(periph, DA_REF_TUR) == 0) {
5827                         cam_iosched_set_work_flags(softc->cam_iosched, DA_WORK_TUR);
5828                         daschedule(periph);
5829                 }
5830         }
5831         /* Queue us up again */
5832         if (da_poll_period != 0)
5833                 callout_schedule(&softc->mediapoll_c, da_poll_period * hz);
5834 }
5835
5836 static void
5837 daprevent(struct cam_periph *periph, int action)
5838 {
5839         struct  da_softc *softc;
5840         union   ccb *ccb;               
5841         int     error;
5842                 
5843         cam_periph_assert(periph, MA_OWNED);
5844         softc = (struct da_softc *)periph->softc;
5845
5846         if (((action == PR_ALLOW)
5847           && (softc->flags & DA_FLAG_PACK_LOCKED) == 0)
5848          || ((action == PR_PREVENT)
5849           && (softc->flags & DA_FLAG_PACK_LOCKED) != 0)) {
5850                 return;
5851         }
5852
5853         ccb = cam_periph_getccb(periph, CAM_PRIORITY_NORMAL);
5854
5855         scsi_prevent(&ccb->csio,
5856                      /*retries*/1,
5857                      /*cbcfp*/NULL,
5858                      MSG_SIMPLE_Q_TAG,
5859                      action,
5860                      SSD_FULL_SIZE,
5861                      5000);
5862
5863         error = cam_periph_runccb(ccb, daerror, CAM_RETRY_SELTO,
5864             SF_RETRY_UA | SF_NO_PRINT, softc->disk->d_devstat);
5865
5866         if (error == 0) {
5867                 if (action == PR_ALLOW)
5868                         softc->flags &= ~DA_FLAG_PACK_LOCKED;
5869                 else
5870                         softc->flags |= DA_FLAG_PACK_LOCKED;
5871         }
5872
5873         xpt_release_ccb(ccb);
5874 }
5875
5876 static void
5877 dasetgeom(struct cam_periph *periph, uint32_t block_len, uint64_t maxsector,
5878           struct scsi_read_capacity_data_long *rcaplong, size_t rcap_len)
5879 {
5880         struct ccb_calc_geometry ccg;
5881         struct da_softc *softc;
5882         struct disk_params *dp;
5883         u_int lbppbe, lalba;
5884         int error;
5885
5886         softc = (struct da_softc *)periph->softc;
5887
5888         dp = &softc->params;
5889         dp->secsize = block_len;
5890         dp->sectors = maxsector + 1;
5891         if (rcaplong != NULL) {
5892                 lbppbe = rcaplong->prot_lbppbe & SRC16_LBPPBE;
5893                 lalba = scsi_2btoul(rcaplong->lalba_lbp);
5894                 lalba &= SRC16_LALBA_A;
5895         } else {
5896                 lbppbe = 0;
5897                 lalba = 0;
5898         }
5899
5900         if (lbppbe > 0) {
5901                 dp->stripesize = block_len << lbppbe;
5902                 dp->stripeoffset = (dp->stripesize - block_len * lalba) %
5903                     dp->stripesize;
5904         } else if (softc->quirks & DA_Q_4K) {
5905                 dp->stripesize = 4096;
5906                 dp->stripeoffset = 0;
5907         } else if (softc->unmap_gran != 0) {
5908                 dp->stripesize = block_len * softc->unmap_gran;
5909                 dp->stripeoffset = (dp->stripesize - block_len *
5910                     softc->unmap_gran_align) % dp->stripesize;
5911         } else {
5912                 dp->stripesize = 0;
5913                 dp->stripeoffset = 0;
5914         }
5915         /*
5916          * Have the controller provide us with a geometry
5917          * for this disk.  The only time the geometry
5918          * matters is when we boot and the controller
5919          * is the only one knowledgeable enough to come
5920          * up with something that will make this a bootable
5921          * device.
5922          */
5923         xpt_setup_ccb(&ccg.ccb_h, periph->path, CAM_PRIORITY_NORMAL);
5924         ccg.ccb_h.func_code = XPT_CALC_GEOMETRY;
5925         ccg.block_size = dp->secsize;
5926         ccg.volume_size = dp->sectors;
5927         ccg.heads = 0;
5928         ccg.secs_per_track = 0;
5929         ccg.cylinders = 0;
5930         xpt_action((union ccb*)&ccg);
5931         if ((ccg.ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) {
5932                 /*
5933                  * We don't know what went wrong here- but just pick
5934                  * a geometry so we don't have nasty things like divide
5935                  * by zero.
5936                  */
5937                 dp->heads = 255;
5938                 dp->secs_per_track = 255;
5939                 dp->cylinders = dp->sectors / (255 * 255);
5940                 if (dp->cylinders == 0) {
5941                         dp->cylinders = 1;
5942                 }
5943         } else {
5944                 dp->heads = ccg.heads;
5945                 dp->secs_per_track = ccg.secs_per_track;
5946                 dp->cylinders = ccg.cylinders;
5947         }
5948
5949         /*
5950          * If the user supplied a read capacity buffer, and if it is
5951          * different than the previous buffer, update the data in the EDT.
5952          * If it's the same, we don't bother.  This avoids sending an
5953          * update every time someone opens this device.
5954          */
5955         if ((rcaplong != NULL)
5956          && (bcmp(rcaplong, &softc->rcaplong,
5957                   min(sizeof(softc->rcaplong), rcap_len)) != 0)) {
5958                 struct ccb_dev_advinfo cdai;
5959
5960                 xpt_setup_ccb(&cdai.ccb_h, periph->path, CAM_PRIORITY_NORMAL);
5961                 cdai.ccb_h.func_code = XPT_DEV_ADVINFO;
5962                 cdai.buftype = CDAI_TYPE_RCAPLONG;
5963                 cdai.flags = CDAI_FLAG_STORE;
5964                 cdai.bufsiz = rcap_len;
5965                 cdai.buf = (uint8_t *)rcaplong;
5966                 xpt_action((union ccb *)&cdai);
5967                 if ((cdai.ccb_h.status & CAM_DEV_QFRZN) != 0)
5968                         cam_release_devq(cdai.ccb_h.path, 0, 0, 0, FALSE);
5969                 if (cdai.ccb_h.status != CAM_REQ_CMP) {
5970                         xpt_print(periph->path, "%s: failed to set read "
5971                                   "capacity advinfo\n", __func__);
5972                         /* Use cam_error_print() to decode the status */
5973                         cam_error_print((union ccb *)&cdai, CAM_ESF_CAM_STATUS,
5974                                         CAM_EPF_ALL);
5975                 } else {
5976                         bcopy(rcaplong, &softc->rcaplong,
5977                               min(sizeof(softc->rcaplong), rcap_len));
5978                 }
5979         }
5980
5981         softc->disk->d_sectorsize = softc->params.secsize;
5982         softc->disk->d_mediasize = softc->params.secsize * (off_t)softc->params.sectors;
5983         softc->disk->d_stripesize = softc->params.stripesize;
5984         softc->disk->d_stripeoffset = softc->params.stripeoffset;
5985         /* XXX: these are not actually "firmware" values, so they may be wrong */
5986         softc->disk->d_fwsectors = softc->params.secs_per_track;
5987         softc->disk->d_fwheads = softc->params.heads;
5988         softc->disk->d_devstat->block_size = softc->params.secsize;
5989         softc->disk->d_devstat->flags &= ~DEVSTAT_BS_UNAVAILABLE;
5990
5991         error = disk_resize(softc->disk, M_NOWAIT);
5992         if (error != 0)
5993                 xpt_print(periph->path, "disk_resize(9) failed, error = %d\n", error);
5994 }
5995
5996 static void
5997 dasendorderedtag(void *arg)
5998 {
5999         struct cam_periph *periph = arg;
6000         struct da_softc *softc = periph->softc;
6001
6002         cam_periph_assert(periph, MA_OWNED);
6003         if (da_send_ordered) {
6004                 if (!LIST_EMPTY(&softc->pending_ccbs)) {
6005                         if ((softc->flags & DA_FLAG_WAS_OTAG) == 0)
6006                                 softc->flags |= DA_FLAG_NEED_OTAG;
6007                         softc->flags &= ~DA_FLAG_WAS_OTAG;
6008                 }
6009         }
6010
6011         /* Queue us up again */
6012         callout_reset(&softc->sendordered_c,
6013             (da_default_timeout * hz) / DA_ORDEREDTAG_INTERVAL,
6014             dasendorderedtag, periph);
6015 }
6016
6017 /*
6018  * Step through all DA peripheral drivers, and if the device is still open,
6019  * sync the disk cache to physical media.
6020  */
6021 static void
6022 dashutdown(void * arg, int howto)
6023 {
6024         struct cam_periph *periph;
6025         struct da_softc *softc;
6026         union ccb *ccb;
6027         int error;
6028
6029         CAM_PERIPH_FOREACH(periph, &dadriver) {
6030                 softc = (struct da_softc *)periph->softc;
6031                 if (SCHEDULER_STOPPED()) {
6032                         /* If we paniced with the lock held, do not recurse. */
6033                         if (!cam_periph_owned(periph) &&
6034                             (softc->flags & DA_FLAG_OPEN)) {
6035                                 dadump(softc->disk, NULL, 0, 0, 0);
6036                         }
6037                         continue;
6038                 }
6039                 cam_periph_lock(periph);
6040
6041                 /*
6042                  * We only sync the cache if the drive is still open, and
6043                  * if the drive is capable of it..
6044                  */
6045                 if (((softc->flags & DA_FLAG_OPEN) == 0)
6046                  || (softc->quirks & DA_Q_NO_SYNC_CACHE)) {
6047                         cam_periph_unlock(periph);
6048                         continue;
6049                 }
6050
6051                 ccb = cam_periph_getccb(periph, CAM_PRIORITY_NORMAL);
6052                 scsi_synchronize_cache(&ccb->csio,
6053                                        /*retries*/0,
6054                                        /*cbfcnp*/NULL,
6055                                        MSG_SIMPLE_Q_TAG,
6056                                        /*begin_lba*/0, /* whole disk */
6057                                        /*lb_count*/0,
6058                                        SSD_FULL_SIZE,
6059                                        60 * 60 * 1000);
6060
6061                 error = cam_periph_runccb(ccb, daerror, /*cam_flags*/0,
6062                     /*sense_flags*/ SF_NO_RECOVERY | SF_NO_RETRY | SF_QUIET_IR,
6063                     softc->disk->d_devstat);
6064                 if (error != 0)
6065                         xpt_print(periph->path, "Synchronize cache failed\n");
6066                 xpt_release_ccb(ccb);
6067                 cam_periph_unlock(periph);
6068         }
6069 }
6070
6071 #else /* !_KERNEL */
6072
6073 /*
6074  * XXX These are only left out of the kernel build to silence warnings.  If,
6075  * for some reason these functions are used in the kernel, the ifdefs should
6076  * be moved so they are included both in the kernel and userland.
6077  */
6078 void
6079 scsi_format_unit(struct ccb_scsiio *csio, u_int32_t retries,
6080                  void (*cbfcnp)(struct cam_periph *, union ccb *),
6081                  u_int8_t tag_action, u_int8_t byte2, u_int16_t ileave,
6082                  u_int8_t *data_ptr, u_int32_t dxfer_len, u_int8_t sense_len,
6083                  u_int32_t timeout)
6084 {
6085         struct scsi_format_unit *scsi_cmd;
6086
6087         scsi_cmd = (struct scsi_format_unit *)&csio->cdb_io.cdb_bytes;
6088         scsi_cmd->opcode = FORMAT_UNIT;
6089         scsi_cmd->byte2 = byte2;
6090         scsi_ulto2b(ileave, scsi_cmd->interleave);
6091
6092         cam_fill_csio(csio,
6093                       retries,
6094                       cbfcnp,
6095                       /*flags*/ (dxfer_len > 0) ? CAM_DIR_OUT : CAM_DIR_NONE,
6096                       tag_action,
6097                       data_ptr,
6098                       dxfer_len,
6099                       sense_len,
6100                       sizeof(*scsi_cmd),
6101                       timeout);
6102 }
6103
6104 void
6105 scsi_read_defects(struct ccb_scsiio *csio, uint32_t retries,
6106                   void (*cbfcnp)(struct cam_periph *, union ccb *),
6107                   uint8_t tag_action, uint8_t list_format,
6108                   uint32_t addr_desc_index, uint8_t *data_ptr,
6109                   uint32_t dxfer_len, int minimum_cmd_size, 
6110                   uint8_t sense_len, uint32_t timeout)
6111 {
6112         uint8_t cdb_len;
6113
6114         /*
6115          * These conditions allow using the 10 byte command.  Otherwise we
6116          * need to use the 12 byte command.
6117          */
6118         if ((minimum_cmd_size <= 10)
6119          && (addr_desc_index == 0) 
6120          && (dxfer_len <= SRDD10_MAX_LENGTH)) {
6121                 struct scsi_read_defect_data_10 *cdb10;
6122
6123                 cdb10 = (struct scsi_read_defect_data_10 *)
6124                         &csio->cdb_io.cdb_bytes;
6125
6126                 cdb_len = sizeof(*cdb10);
6127                 bzero(cdb10, cdb_len);
6128                 cdb10->opcode = READ_DEFECT_DATA_10;
6129                 cdb10->format = list_format;
6130                 scsi_ulto2b(dxfer_len, cdb10->alloc_length);
6131         } else {
6132                 struct scsi_read_defect_data_12 *cdb12;
6133
6134                 cdb12 = (struct scsi_read_defect_data_12 *)
6135                         &csio->cdb_io.cdb_bytes;
6136
6137                 cdb_len = sizeof(*cdb12);
6138                 bzero(cdb12, cdb_len);
6139                 cdb12->opcode = READ_DEFECT_DATA_12;
6140                 cdb12->format = list_format;
6141                 scsi_ulto4b(dxfer_len, cdb12->alloc_length);
6142                 scsi_ulto4b(addr_desc_index, cdb12->address_descriptor_index);
6143         }
6144
6145         cam_fill_csio(csio,
6146                       retries,
6147                       cbfcnp,
6148                       /*flags*/ CAM_DIR_IN,
6149                       tag_action,
6150                       data_ptr,
6151                       dxfer_len,
6152                       sense_len,
6153                       cdb_len,
6154                       timeout);
6155 }
6156
6157 void
6158 scsi_sanitize(struct ccb_scsiio *csio, u_int32_t retries,
6159               void (*cbfcnp)(struct cam_periph *, union ccb *),
6160               u_int8_t tag_action, u_int8_t byte2, u_int16_t control,
6161               u_int8_t *data_ptr, u_int32_t dxfer_len, u_int8_t sense_len,
6162               u_int32_t timeout)
6163 {
6164         struct scsi_sanitize *scsi_cmd;
6165
6166         scsi_cmd = (struct scsi_sanitize *)&csio->cdb_io.cdb_bytes;
6167         scsi_cmd->opcode = SANITIZE;
6168         scsi_cmd->byte2 = byte2;
6169         scsi_cmd->control = control;
6170         scsi_ulto2b(dxfer_len, scsi_cmd->length);
6171
6172         cam_fill_csio(csio,
6173                       retries,
6174                       cbfcnp,
6175                       /*flags*/ (dxfer_len > 0) ? CAM_DIR_OUT : CAM_DIR_NONE,
6176                       tag_action,
6177                       data_ptr,
6178                       dxfer_len,
6179                       sense_len,
6180                       sizeof(*scsi_cmd),
6181                       timeout);
6182 }
6183
6184 #endif /* _KERNEL */
6185
6186 void
6187 scsi_zbc_out(struct ccb_scsiio *csio, uint32_t retries, 
6188              void (*cbfcnp)(struct cam_periph *, union ccb *),
6189              uint8_t tag_action, uint8_t service_action, uint64_t zone_id,
6190              uint8_t zone_flags, uint8_t *data_ptr, uint32_t dxfer_len,
6191              uint8_t sense_len, uint32_t timeout)
6192 {
6193         struct scsi_zbc_out *scsi_cmd;
6194
6195         scsi_cmd = (struct scsi_zbc_out *)&csio->cdb_io.cdb_bytes;
6196         scsi_cmd->opcode = ZBC_OUT;
6197         scsi_cmd->service_action = service_action;
6198         scsi_u64to8b(zone_id, scsi_cmd->zone_id);
6199         scsi_cmd->zone_flags = zone_flags;
6200
6201         cam_fill_csio(csio,
6202                       retries,
6203                       cbfcnp,
6204                       /*flags*/ (dxfer_len > 0) ? CAM_DIR_OUT : CAM_DIR_NONE,
6205                       tag_action,
6206                       data_ptr,
6207                       dxfer_len,
6208                       sense_len,
6209                       sizeof(*scsi_cmd),
6210                       timeout);
6211 }
6212
6213 void
6214 scsi_zbc_in(struct ccb_scsiio *csio, uint32_t retries, 
6215             void (*cbfcnp)(struct cam_periph *, union ccb *),
6216             uint8_t tag_action, uint8_t service_action, uint64_t zone_start_lba,
6217             uint8_t zone_options, uint8_t *data_ptr, uint32_t dxfer_len,
6218             uint8_t sense_len, uint32_t timeout)
6219 {
6220         struct scsi_zbc_in *scsi_cmd;
6221
6222         scsi_cmd = (struct scsi_zbc_in *)&csio->cdb_io.cdb_bytes;
6223         scsi_cmd->opcode = ZBC_IN;
6224         scsi_cmd->service_action = service_action;
6225         scsi_ulto4b(dxfer_len, scsi_cmd->length);
6226         scsi_u64to8b(zone_start_lba, scsi_cmd->zone_start_lba);
6227         scsi_cmd->zone_options = zone_options;
6228
6229         cam_fill_csio(csio,
6230                       retries,
6231                       cbfcnp,
6232                       /*flags*/ (dxfer_len > 0) ? CAM_DIR_IN : CAM_DIR_NONE,
6233                       tag_action,
6234                       data_ptr,
6235                       dxfer_len,
6236                       sense_len,
6237                       sizeof(*scsi_cmd),
6238                       timeout);
6239
6240 }
6241
6242 int
6243 scsi_ata_zac_mgmt_out(struct ccb_scsiio *csio, uint32_t retries, 
6244                       void (*cbfcnp)(struct cam_periph *, union ccb *),
6245                       uint8_t tag_action, int use_ncq,
6246                       uint8_t zm_action, uint64_t zone_id, uint8_t zone_flags,
6247                       uint8_t *data_ptr, uint32_t dxfer_len,
6248                       uint8_t *cdb_storage, size_t cdb_storage_len,
6249                       uint8_t sense_len, uint32_t timeout)
6250 {
6251         uint8_t command_out, protocol, ata_flags;
6252         uint16_t features_out;
6253         uint32_t sectors_out, auxiliary;
6254         int retval;
6255
6256         retval = 0;
6257
6258         if (use_ncq == 0) {
6259                 command_out = ATA_ZAC_MANAGEMENT_OUT;
6260                 features_out = (zm_action & 0xf) | (zone_flags << 8);
6261                 ata_flags = AP_FLAG_BYT_BLOK_BLOCKS;
6262                 if (dxfer_len == 0) {
6263                         protocol = AP_PROTO_NON_DATA;
6264                         ata_flags |= AP_FLAG_TLEN_NO_DATA;
6265                         sectors_out = 0;
6266                 } else {
6267                         protocol = AP_PROTO_DMA;
6268                         ata_flags |= AP_FLAG_TLEN_SECT_CNT |
6269                                      AP_FLAG_TDIR_TO_DEV;
6270                         sectors_out = ((dxfer_len >> 9) & 0xffff);
6271                 }
6272                 auxiliary = 0;
6273         } else {
6274                 ata_flags = AP_FLAG_BYT_BLOK_BLOCKS;
6275                 if (dxfer_len == 0) {
6276                         command_out = ATA_NCQ_NON_DATA;
6277                         features_out = ATA_NCQ_ZAC_MGMT_OUT;
6278                         /*
6279                          * We're assuming the SCSI to ATA translation layer
6280                          * will set the NCQ tag number in the tag field.
6281                          * That isn't clear from the SAT-4 spec (as of rev 05).
6282                          */
6283                         sectors_out = 0;
6284                         ata_flags |= AP_FLAG_TLEN_NO_DATA;
6285                 } else {
6286                         command_out = ATA_SEND_FPDMA_QUEUED;
6287                         /*
6288                          * Note that we're defaulting to normal priority,
6289                          * and assuming that the SCSI to ATA translation
6290                          * layer will insert the NCQ tag number in the tag
6291                          * field.  That isn't clear in the SAT-4 spec (as
6292                          * of rev 05).
6293                          */
6294                         sectors_out = ATA_SFPDMA_ZAC_MGMT_OUT << 8;
6295
6296                         ata_flags |= AP_FLAG_TLEN_FEAT |
6297                                      AP_FLAG_TDIR_TO_DEV;
6298
6299                         /*
6300                          * For SEND FPDMA QUEUED, the transfer length is
6301                          * encoded in the FEATURE register, and 0 means
6302                          * that 65536 512 byte blocks are to be tranferred.
6303                          * In practice, it seems unlikely that we'll see
6304                          * a transfer that large, and it may confuse the
6305                          * the SAT layer, because generally that means that
6306                          * 0 bytes should be transferred.
6307                          */
6308                         if (dxfer_len == (65536 * 512)) {
6309                                 features_out = 0;
6310                         } else if (dxfer_len <= (65535 * 512)) {
6311                                 features_out = ((dxfer_len >> 9) & 0xffff);
6312                         } else {
6313                                 /* The transfer is too big. */
6314                                 retval = 1;
6315                                 goto bailout;
6316                         }
6317
6318                 }
6319
6320                 auxiliary = (zm_action & 0xf) | (zone_flags << 8);
6321                 protocol = AP_PROTO_FPDMA;
6322         }
6323
6324         protocol |= AP_EXTEND;
6325
6326         retval = scsi_ata_pass(csio,
6327             retries,
6328             cbfcnp,
6329             /*flags*/ (dxfer_len > 0) ? CAM_DIR_OUT : CAM_DIR_NONE,
6330             tag_action,
6331             /*protocol*/ protocol,
6332             /*ata_flags*/ ata_flags,
6333             /*features*/ features_out,
6334             /*sector_count*/ sectors_out,
6335             /*lba*/ zone_id,
6336             /*command*/ command_out,
6337             /*device*/ 0,
6338             /*icc*/ 0,
6339             /*auxiliary*/ auxiliary,
6340             /*control*/ 0,
6341             /*data_ptr*/ data_ptr,
6342             /*dxfer_len*/ dxfer_len,
6343             /*cdb_storage*/ cdb_storage,
6344             /*cdb_storage_len*/ cdb_storage_len,
6345             /*minimum_cmd_size*/ 0,
6346             /*sense_len*/ SSD_FULL_SIZE,
6347             /*timeout*/ timeout);
6348
6349 bailout:
6350
6351         return (retval);
6352 }
6353
6354 int
6355 scsi_ata_zac_mgmt_in(struct ccb_scsiio *csio, uint32_t retries, 
6356                      void (*cbfcnp)(struct cam_periph *, union ccb *),
6357                      uint8_t tag_action, int use_ncq,
6358                      uint8_t zm_action, uint64_t zone_id, uint8_t zone_flags,
6359                      uint8_t *data_ptr, uint32_t dxfer_len,
6360                      uint8_t *cdb_storage, size_t cdb_storage_len,
6361                      uint8_t sense_len, uint32_t timeout)
6362 {
6363         uint8_t command_out, protocol;
6364         uint16_t features_out, sectors_out;
6365         uint32_t auxiliary;
6366         int ata_flags;
6367         int retval;
6368
6369         retval = 0;
6370         ata_flags = AP_FLAG_TDIR_FROM_DEV | AP_FLAG_BYT_BLOK_BLOCKS;
6371
6372         if (use_ncq == 0) {
6373                 command_out = ATA_ZAC_MANAGEMENT_IN;
6374                 /* XXX KDM put a macro here */
6375                 features_out = (zm_action & 0xf) | (zone_flags << 8);
6376                 sectors_out = dxfer_len >> 9; /* XXX KDM macro */
6377                 protocol = AP_PROTO_DMA;
6378                 ata_flags |= AP_FLAG_TLEN_SECT_CNT;
6379                 auxiliary = 0;
6380         } else {
6381                 ata_flags |= AP_FLAG_TLEN_FEAT;
6382
6383                 command_out = ATA_RECV_FPDMA_QUEUED;
6384                 sectors_out = ATA_RFPDMA_ZAC_MGMT_IN << 8;
6385
6386                 /*
6387                  * For RECEIVE FPDMA QUEUED, the transfer length is
6388                  * encoded in the FEATURE register, and 0 means
6389                  * that 65536 512 byte blocks are to be tranferred.
6390                  * In practice, it seems unlikely that we'll see
6391                  * a transfer that large, and it may confuse the
6392                  * the SAT layer, because generally that means that
6393                  * 0 bytes should be transferred.
6394                  */
6395                 if (dxfer_len == (65536 * 512)) {
6396                         features_out = 0;
6397                 } else if (dxfer_len <= (65535 * 512)) {
6398                         features_out = ((dxfer_len >> 9) & 0xffff);
6399                 } else {
6400                         /* The transfer is too big. */
6401                         retval = 1;
6402                         goto bailout;
6403                 }
6404                 auxiliary = (zm_action & 0xf) | (zone_flags << 8),
6405                 protocol = AP_PROTO_FPDMA;
6406         }
6407
6408         protocol |= AP_EXTEND;
6409
6410         retval = scsi_ata_pass(csio,
6411             retries,
6412             cbfcnp,
6413             /*flags*/ CAM_DIR_IN,
6414             tag_action,
6415             /*protocol*/ protocol,
6416             /*ata_flags*/ ata_flags,
6417             /*features*/ features_out,
6418             /*sector_count*/ sectors_out,
6419             /*lba*/ zone_id,
6420             /*command*/ command_out,
6421             /*device*/ 0,
6422             /*icc*/ 0,
6423             /*auxiliary*/ auxiliary,
6424             /*control*/ 0,
6425             /*data_ptr*/ data_ptr,
6426             /*dxfer_len*/ (dxfer_len >> 9) * 512, /* XXX KDM */
6427             /*cdb_storage*/ cdb_storage,
6428             /*cdb_storage_len*/ cdb_storage_len,
6429             /*minimum_cmd_size*/ 0,
6430             /*sense_len*/ SSD_FULL_SIZE,
6431             /*timeout*/ timeout);
6432
6433 bailout:
6434         return (retval);
6435 }