xref: /freebsd/sys/cam/ctl/scsi_ctl.c (revision ddd5b8e9b4d8957fce018c520657cdfa4ecffad3)
1 /*-
2  * Copyright (c) 2008, 2009 Silicon Graphics International Corp.
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions, and the following disclaimer,
10  *    without modification.
11  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
12  *    substantially similar to the "NO WARRANTY" disclaimer below
13  *    ("Disclaimer") and any redistribution must be conditioned upon
14  *    including a substantially similar Disclaimer requirement for further
15  *    binary redistribution.
16  *
17  * NO WARRANTY
18  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
21  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22  * HOLDERS OR CONTRIBUTORS BE LIABLE FOR 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,
26  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
27  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
28  * POSSIBILITY OF SUCH DAMAGES.
29  *
30  * $Id: //depot/users/kenm/FreeBSD-test2/sys/cam/ctl/scsi_ctl.c#4 $
31  */
32 /*
33  * Peripheral driver interface between CAM and CTL (CAM Target Layer).
34  *
35  * Author: Ken Merry <ken@FreeBSD.org>
36  */
37 
38 #include <sys/cdefs.h>
39 __FBSDID("$FreeBSD$");
40 
41 #include <sys/param.h>
42 #include <sys/queue.h>
43 #include <sys/systm.h>
44 #include <sys/kernel.h>
45 #include <sys/lock.h>
46 #include <sys/mutex.h>
47 #include <sys/condvar.h>
48 #include <sys/malloc.h>
49 #include <sys/bus.h>
50 #include <sys/endian.h>
51 #include <sys/sbuf.h>
52 #include <sys/sysctl.h>
53 #include <sys/types.h>
54 #include <sys/systm.h>
55 #include <machine/bus.h>
56 
57 #include <cam/cam.h>
58 #include <cam/cam_ccb.h>
59 #include <cam/cam_periph.h>
60 #include <cam/cam_queue.h>
61 #include <cam/cam_xpt_periph.h>
62 #include <cam/cam_debug.h>
63 #include <cam/cam_sim.h>
64 #include <cam/cam_xpt.h>
65 
66 #include <cam/scsi/scsi_all.h>
67 #include <cam/scsi/scsi_message.h>
68 
69 #include <cam/ctl/ctl_io.h>
70 #include <cam/ctl/ctl.h>
71 #include <cam/ctl/ctl_frontend.h>
72 #include <cam/ctl/ctl_util.h>
73 #include <cam/ctl/ctl_error.h>
74 
75 typedef enum {
76 	CTLFE_CCB_DEFAULT	= 0x00,
77 	CTLFE_CCB_WAITING 	= 0x01
78 } ctlfe_ccb_types;
79 
80 struct ctlfe_softc {
81 	struct ctl_frontend fe;
82 	path_id_t path_id;
83 	struct cam_sim *sim;
84 	char port_name[DEV_IDLEN];
85 	STAILQ_HEAD(, ctlfe_lun_softc) lun_softc_list;
86 	STAILQ_ENTRY(ctlfe_softc) links;
87 };
88 
89 STAILQ_HEAD(, ctlfe_softc) ctlfe_softc_list;
90 struct mtx ctlfe_list_mtx;
91 static char ctlfe_mtx_desc[] = "ctlfelist";
92 static int ctlfe_dma_enabled = 1;
93 #ifdef CTLFE_INIT_ENABLE
94 static int ctlfe_max_targets = 1;
95 static int ctlfe_num_targets = 0;
96 #endif
97 
98 typedef enum {
99 	CTLFE_LUN_NONE		= 0x00,
100 	CTLFE_LUN_WILDCARD	= 0x01
101 } ctlfe_lun_flags;
102 
103 struct ctlfe_lun_softc {
104 	struct ctlfe_softc *parent_softc;
105 	struct cam_periph *periph;
106 	ctlfe_lun_flags flags;
107 	struct callout dma_callout;
108 	uint64_t ccbs_alloced;
109 	uint64_t ccbs_freed;
110 	uint64_t ctios_sent;
111 	uint64_t ctios_returned;
112 	uint64_t atios_sent;
113 	uint64_t atios_returned;
114 	uint64_t inots_sent;
115 	uint64_t inots_returned;
116 	/* bus_dma_tag_t dma_tag; */
117 	TAILQ_HEAD(, ccb_hdr) work_queue;
118 	STAILQ_ENTRY(ctlfe_lun_softc) links;
119 };
120 
121 typedef enum {
122 	CTLFE_CMD_NONE		= 0x00,
123 	CTLFE_CMD_PIECEWISE	= 0x01
124 } ctlfe_cmd_flags;
125 
126 /*
127  * The size limit of this structure is CTL_PORT_PRIV_SIZE, from ctl_io.h.
128  * Currently that is 600 bytes.
129  */
130 struct ctlfe_lun_cmd_info {
131 	int cur_transfer_index;
132 	ctlfe_cmd_flags flags;
133 	/*
134 	 * XXX KDM struct bus_dma_segment is 8 bytes on i386, and 16
135 	 * bytes on amd64.  So with 32 elements, this is 256 bytes on
136 	 * i386 and 512 bytes on amd64.
137 	 */
138 	bus_dma_segment_t cam_sglist[32];
139 };
140 
141 /*
142  * When we register the adapter/bus, request that this many ctl_ios be
143  * allocated.  This should be the maximum supported by the adapter, but we
144  * currently don't have a way to get that back from the path inquiry.
145  * XXX KDM add that to the path inquiry.
146  */
147 #define	CTLFE_REQ_CTL_IO	4096
148 /*
149  * Number of Accept Target I/O CCBs to allocate and queue down to the
150  * adapter per LUN.
151  * XXX KDM should this be controlled by CTL?
152  */
153 #define	CTLFE_ATIO_PER_LUN	1024
154 /*
155  * Number of Immediate Notify CCBs (used for aborts, resets, etc.) to
156  * allocate and queue down to the adapter per LUN.
157  * XXX KDM should this be controlled by CTL?
158  */
159 #define	CTLFE_IN_PER_LUN	1024
160 
161 /*
162  * Timeout (in seconds) on CTIO CCB allocation for doing a DMA or sending
163  * status to the initiator.  The SIM is expected to have its own timeouts,
164  * so we're not putting this timeout around the CCB execution time.  The
165  * SIM should timeout and let us know if it has an issue.
166  */
167 #define	CTLFE_DMA_TIMEOUT	60
168 
169 /*
170  * Turn this on to enable extra debugging prints.
171  */
172 #if 0
173 #define	CTLFE_DEBUG
174 #endif
175 
176 /*
177  * Use randomly assigned WWNN/WWPN values.  This is to work around an issue
178  * in the FreeBSD initiator that makes it unable to rescan the target if
179  * the target gets rebooted and the WWNN/WWPN stay the same.
180  */
181 #if 0
182 #define	RANDOM_WWNN
183 #endif
184 
185 SYSCTL_INT(_kern_cam_ctl, OID_AUTO, dma_enabled, CTLFLAG_RW,
186 	   &ctlfe_dma_enabled, 0, "DMA enabled");
187 MALLOC_DEFINE(M_CTLFE, "CAM CTL FE", "CAM CTL FE interface");
188 
189 #define	ccb_type	ppriv_field0
190 /* This is only used in the ATIO */
191 #define	io_ptr		ppriv_ptr1
192 
193 /* This is only used in the CTIO */
194 #define	ccb_atio	ppriv_ptr1
195 
196 int			ctlfeinitialize(void);
197 void			ctlfeshutdown(void);
198 static periph_init_t	ctlfeinit;
199 static void		ctlfeasync(void *callback_arg, uint32_t code,
200 				   struct cam_path *path, void *arg);
201 static periph_ctor_t	ctlferegister;
202 static periph_oninv_t	ctlfeoninvalidate;
203 static periph_dtor_t	ctlfecleanup;
204 static periph_start_t	ctlfestart;
205 static void		ctlfedone(struct cam_periph *periph,
206 				  union ccb *done_ccb);
207 
208 static void 		ctlfe_onoffline(void *arg, int online);
209 static void 		ctlfe_online(void *arg);
210 static void 		ctlfe_offline(void *arg);
211 static int 		ctlfe_targ_enable(void *arg, struct ctl_id targ_id);
212 static int 		ctlfe_targ_disable(void *arg, struct ctl_id targ_id);
213 static int 		ctlfe_lun_enable(void *arg, struct ctl_id targ_id,
214 					 int lun_id);
215 static int 		ctlfe_lun_disable(void *arg, struct ctl_id targ_id,
216 					  int lun_id);
217 static void		ctlfe_dump_sim(struct cam_sim *sim);
218 static void		ctlfe_dump_queue(struct ctlfe_lun_softc *softc);
219 static void		ctlfe_dma_timeout(void *arg);
220 static void 		ctlfe_datamove_done(union ctl_io *io);
221 static void 		ctlfe_dump(void);
222 
223 static struct periph_driver ctlfe_driver =
224 {
225 	ctlfeinit, "ctl",
226 	TAILQ_HEAD_INITIALIZER(ctlfe_driver.units), /*generation*/ 0
227 };
228 
229 static int ctlfe_module_event_handler(module_t, int /*modeventtype_t*/, void *);
230 
231 /*
232  * We're not using PERIPHDRIVER_DECLARE(), because it runs at SI_SUB_DRIVERS,
233  * and that happens before CTL gets initialised.
234  */
235 static moduledata_t ctlfe_moduledata = {
236 	"ctlfe",
237 	ctlfe_module_event_handler,
238 	NULL
239 };
240 
241 DECLARE_MODULE(ctlfe, ctlfe_moduledata, SI_SUB_CONFIGURE, SI_ORDER_FOURTH);
242 MODULE_VERSION(ctlfe, 1);
243 MODULE_DEPEND(ctlfe, ctl, 1, 1, 1);
244 MODULE_DEPEND(ctlfe, cam, 1, 1, 1);
245 
246 extern struct ctl_softc *control_softc;
247 extern int ctl_disable;
248 
249 void
250 ctlfeshutdown(void)
251 {
252 	return;
253 }
254 
255 void
256 ctlfeinit(void)
257 {
258 	cam_status status;
259 
260 	/* Don't initialize if we're disabled */
261 	if (ctl_disable != 0)
262 		return;
263 
264 	STAILQ_INIT(&ctlfe_softc_list);
265 
266 	mtx_init(&ctlfe_list_mtx, ctlfe_mtx_desc, NULL, MTX_DEF);
267 
268 	KASSERT(control_softc != NULL, ("CTL is not initialized!"));
269 
270 	status = xpt_register_async(AC_PATH_REGISTERED | AC_PATH_DEREGISTERED |
271 				    AC_CONTRACT, ctlfeasync, NULL, NULL);
272 
273 	if (status != CAM_REQ_CMP) {
274 		printf("ctl: Failed to attach async callback due to CAM "
275 		       "status 0x%x!\n", status);
276 	}
277 }
278 
279 static int
280 ctlfe_module_event_handler(module_t mod, int what, void *arg)
281 {
282 
283 	switch (what) {
284 	case MOD_LOAD:
285 		periphdriver_register(&ctlfe_driver);
286 		return (0);
287 	case MOD_UNLOAD:
288 		return (EBUSY);
289 	default:
290 		return (EOPNOTSUPP);
291 	}
292 }
293 
294 static void
295 ctlfeasync(void *callback_arg, uint32_t code, struct cam_path *path, void *arg)
296 {
297 
298 #ifdef CTLFEDEBUG
299 	printf("%s: entered\n", __func__);
300 #endif
301 
302 	/*
303 	 * When a new path gets registered, and it is capable of target
304 	 * mode, go ahead and attach.  Later on, we may need to be more
305 	 * selective, but for now this will be sufficient.
306  	 */
307 	switch (code) {
308 	case AC_PATH_REGISTERED: {
309 		struct ctl_frontend *fe;
310 		struct ctlfe_softc *bus_softc;
311 		struct ccb_pathinq *cpi;
312 		int retval;
313 
314 		cpi = (struct ccb_pathinq *)arg;
315 
316 		/* Don't attach if it doesn't support target mode */
317 		if ((cpi->target_sprt & PIT_PROCESSOR) == 0) {
318 #ifdef CTLFEDEBUG
319 			printf("%s: SIM %s%d doesn't support target mode\n",
320 			       __func__, cpi->dev_name, cpi->unit_number);
321 #endif
322 			break;
323 		}
324 
325 #ifdef CTLFE_INIT_ENABLE
326 		if (ctlfe_num_targets >= ctlfe_max_targets) {
327 			union ccb *ccb;
328 			struct cam_sim *sim;
329 
330 			ccb = (union ccb *)malloc(sizeof(*ccb), M_TEMP,
331 						  M_NOWAIT | M_ZERO);
332 			if (ccb == NULL) {
333 				printf("%s: unable to malloc CCB!\n", __func__);
334 				return;
335 			}
336 			xpt_setup_ccb(&ccb->ccb_h, cpi->ccb_h.path,
337 				      CAM_PRIORITY_NONE);
338 
339 			sim = xpt_path_sim(cpi->ccb_h.path);
340 
341 			ccb->ccb_h.func_code = XPT_SET_SIM_KNOB;
342 			ccb->knob.xport_specific.valid = KNOB_VALID_ROLE;
343 			ccb->knob.xport_specific.fc.role = KNOB_ROLE_INITIATOR;
344 
345 			/* We should hold the SIM lock here */
346 			mtx_assert(sim->mtx, MA_OWNED);
347 
348 			xpt_action(ccb);
349 
350 			if ((ccb->ccb_h.status & CAM_STATUS_MASK) !=
351 			     CAM_REQ_CMP) {
352 				printf("%s: SIM %s%d (path id %d) initiator "
353 				       "enable failed with status %#x\n",
354 				       __func__, cpi->dev_name,
355 				       cpi->unit_number, cpi->ccb_h.path_id,
356 				       ccb->ccb_h.status);
357 			} else {
358 				printf("%s: SIM %s%d (path id %d) initiator "
359 				       "enable succeeded\n",
360 				       __func__, cpi->dev_name,
361 				       cpi->unit_number, cpi->ccb_h.path_id);
362 			}
363 
364 			free(ccb, M_TEMP);
365 
366 			break;
367 		} else {
368 			ctlfe_num_targets++;
369 		}
370 
371 		printf("%s: ctlfe_num_targets = %d\n", __func__,
372 		       ctlfe_num_targets);
373 #endif /* CTLFE_INIT_ENABLE */
374 
375 		/*
376 		 * We're in an interrupt context here, so we have to
377 		 * use M_NOWAIT.  Of course this means trouble if we
378 		 * can't allocate memory.
379 		 */
380 		bus_softc = malloc(sizeof(*bus_softc), M_CTLFE,
381 				   M_NOWAIT | M_ZERO);
382 		if (bus_softc == NULL) {
383 			printf("%s: unable to malloc %zd bytes for softc\n",
384 			       __func__, sizeof(*bus_softc));
385 			return;
386 		}
387 
388 		bus_softc->path_id = cpi->ccb_h.path_id;
389 		bus_softc->sim = xpt_path_sim(cpi->ccb_h.path);
390 		STAILQ_INIT(&bus_softc->lun_softc_list);
391 
392 		fe = &bus_softc->fe;
393 
394 		/*
395 		 * XXX KDM should we be more accurate here ?
396 		 */
397 		if (cpi->transport == XPORT_FC)
398 			fe->port_type = CTL_PORT_FC;
399 		else
400 			fe->port_type = CTL_PORT_SCSI;
401 
402 		/* XXX KDM what should the real number be here? */
403 		fe->num_requested_ctl_io = 4096;
404 		snprintf(bus_softc->port_name, sizeof(bus_softc->port_name),
405 			 "%s%d", cpi->dev_name, cpi->unit_number);
406 		/*
407 		 * XXX KDM it would be nice to allocate storage in the
408 		 * frontend structure itself.
409 	 	 */
410 		fe->port_name = bus_softc->port_name;
411 		fe->physical_port = cpi->unit_number;
412 		fe->virtual_port = cpi->bus_id;
413 		fe->port_online = ctlfe_online;
414 		fe->port_offline = ctlfe_offline;
415 		fe->onoff_arg = bus_softc;
416 		fe->targ_enable = ctlfe_targ_enable;
417 		fe->targ_disable = ctlfe_targ_disable;
418 		fe->lun_enable = ctlfe_lun_enable;
419 		fe->lun_disable = ctlfe_lun_disable;
420 		fe->targ_lun_arg = bus_softc;
421 		fe->fe_datamove = ctlfe_datamove_done;
422 		fe->fe_done = ctlfe_datamove_done;
423 		fe->fe_dump = ctlfe_dump;
424 		/*
425 		 * XXX KDM the path inquiry doesn't give us the maximum
426 		 * number of targets supported.
427 		 */
428 		fe->max_targets = cpi->max_target;
429 		fe->max_target_id = cpi->max_target;
430 
431 		/*
432 		 * XXX KDM need to figure out whether we're the master or
433 		 * slave.
434 		 */
435 #ifdef CTLFEDEBUG
436 		printf("%s: calling ctl_frontend_register() for %s%d\n",
437 		       __func__, cpi->dev_name, cpi->unit_number);
438 #endif
439 		retval = ctl_frontend_register(fe, /*master_SC*/ 1);
440 		if (retval != 0) {
441 			printf("%s: ctl_frontend_register() failed with "
442 			       "error %d!\n", __func__, retval);
443 			free(bus_softc, M_CTLFE);
444 			break;
445 		} else {
446 			mtx_lock(&ctlfe_list_mtx);
447 			STAILQ_INSERT_TAIL(&ctlfe_softc_list, bus_softc, links);
448 			mtx_unlock(&ctlfe_list_mtx);
449 		}
450 
451 		break;
452 	}
453 	case AC_PATH_DEREGISTERED: {
454 		struct ctlfe_softc *softc = NULL;
455 
456 		mtx_lock(&ctlfe_list_mtx);
457 		STAILQ_FOREACH(softc, &ctlfe_softc_list, links) {
458 			if (softc->path_id == xpt_path_path_id(path)) {
459 				STAILQ_REMOVE(&ctlfe_softc_list, softc,
460 						ctlfe_softc, links);
461 				break;
462 			}
463 		}
464 		mtx_unlock(&ctlfe_list_mtx);
465 
466 		if (softc != NULL) {
467 			/*
468 			 * XXX KDM are we certain at this point that there
469 			 * are no outstanding commands for this frontend?
470 			 */
471 			ctl_frontend_deregister(&softc->fe);
472 			free(softc, M_CTLFE);
473 		}
474 		break;
475 	}
476 	case AC_CONTRACT: {
477 		struct ac_contract *ac;
478 
479 		ac = (struct ac_contract *)arg;
480 
481 		switch (ac->contract_number) {
482 		case AC_CONTRACT_DEV_CHG: {
483 			struct ac_device_changed *dev_chg;
484 			struct ctlfe_softc *softc;
485 			int retval, found;
486 
487 			dev_chg = (struct ac_device_changed *)ac->contract_data;
488 
489 			printf("%s: WWPN %#jx port 0x%06x path %u target %u %s\n",
490 			       __func__, dev_chg->wwpn, dev_chg->port,
491 			       xpt_path_path_id(path), dev_chg->target,
492 			       (dev_chg->arrived == 0) ?  "left" : "arrived");
493 
494 			found = 0;
495 
496 			mtx_lock(&ctlfe_list_mtx);
497 			STAILQ_FOREACH(softc, &ctlfe_softc_list, links) {
498 				if (softc->path_id == xpt_path_path_id(path)) {
499 					found = 1;
500 					break;
501 				}
502 			}
503 			mtx_unlock(&ctlfe_list_mtx);
504 
505 			if (found == 0) {
506 				printf("%s: CTL port for CAM path %u not "
507 				       "found!\n", __func__,
508 				       xpt_path_path_id(path));
509 				break;
510 			}
511 			if (dev_chg->arrived != 0) {
512 				retval = ctl_add_initiator(dev_chg->wwpn,
513 					softc->fe.targ_port, dev_chg->target);
514 			} else {
515 				retval = ctl_remove_initiator(
516 					softc->fe.targ_port, dev_chg->target);
517 			}
518 
519 			if (retval != 0) {
520 				printf("%s: could not %s port %d iid %u "
521 				       "WWPN %#jx!\n", __func__,
522 				       (dev_chg->arrived != 0) ? "add" :
523 				       "remove", softc->fe.targ_port,
524 				       dev_chg->target,
525 				       (uintmax_t)dev_chg->wwpn);
526 			}
527 			break;
528 		}
529 		default:
530 			printf("%s: unsupported contract number %ju\n",
531 			       __func__, (uintmax_t)ac->contract_number);
532 			break;
533 		}
534 		break;
535 	}
536 	default:
537 		break;
538 	}
539 }
540 
541 static cam_status
542 ctlferegister(struct cam_periph *periph, void *arg)
543 {
544 	struct ctlfe_softc *bus_softc;
545 	struct ctlfe_lun_softc *softc;
546 	struct cam_sim *sim;
547 	union ccb en_lun_ccb;
548 	cam_status status;
549 	int i;
550 
551 	softc = (struct ctlfe_lun_softc *)arg;
552 	bus_softc = softc->parent_softc;
553 	sim = xpt_path_sim(periph->path);
554 
555 	TAILQ_INIT(&softc->work_queue);
556 	softc->periph = periph;
557 
558 	callout_init_mtx(&softc->dma_callout, sim->mtx, /*flags*/ 0);
559 	periph->softc = softc;
560 
561 	xpt_setup_ccb(&en_lun_ccb.ccb_h, periph->path, CAM_PRIORITY_NONE);
562 	en_lun_ccb.ccb_h.func_code = XPT_EN_LUN;
563 	en_lun_ccb.cel.grp6_len = 0;
564 	en_lun_ccb.cel.grp7_len = 0;
565 	en_lun_ccb.cel.enable = 1;
566 	xpt_action(&en_lun_ccb);
567 	status = (en_lun_ccb.ccb_h.status & CAM_STATUS_MASK);
568 	if (status != CAM_REQ_CMP) {
569 		xpt_print(periph->path, "%s: Enable LUN failed, status 0x%x\n",
570 			  __func__, en_lun_ccb.ccb_h.status);
571 		return (status);
572 	}
573 
574 	status = CAM_REQ_CMP;
575 
576 	for (i = 0; i < CTLFE_ATIO_PER_LUN; i++) {
577 		union ccb *new_ccb;
578 
579 		new_ccb = (union ccb *)malloc(sizeof(*new_ccb), M_CTLFE,
580 					      M_ZERO|M_NOWAIT);
581 		if (new_ccb == NULL) {
582 			status = CAM_RESRC_UNAVAIL;
583 			break;
584 		}
585 		xpt_setup_ccb(&new_ccb->ccb_h, periph->path, /*priority*/ 1);
586 		new_ccb->ccb_h.func_code = XPT_ACCEPT_TARGET_IO;
587 		new_ccb->ccb_h.cbfcnp = ctlfedone;
588 		xpt_action(new_ccb);
589 		softc->atios_sent++;
590 		status = new_ccb->ccb_h.status;
591 		if ((status & CAM_STATUS_MASK) != CAM_REQ_INPROG) {
592 			free(new_ccb, M_CTLFE);
593 			break;
594 		}
595 	}
596 
597 	status = cam_periph_acquire(periph);
598 	if ((status & CAM_STATUS_MASK) != CAM_REQ_CMP) {
599 		xpt_print(periph->path, "%s: could not acquire reference "
600 			  "count, status = %#x\n", __func__, status);
601 		return (status);
602 	}
603 
604 	if (i == 0) {
605 		xpt_print(periph->path, "%s: could not allocate ATIO CCBs, "
606 			  "status 0x%x\n", __func__, status);
607 		return (CAM_REQ_CMP_ERR);
608 	}
609 
610 	for (i = 0; i < CTLFE_IN_PER_LUN; i++) {
611 		union ccb *new_ccb;
612 
613 		new_ccb = (union ccb *)malloc(sizeof(*new_ccb), M_CTLFE,
614 					      M_ZERO|M_NOWAIT);
615 		if (new_ccb == NULL) {
616 			status = CAM_RESRC_UNAVAIL;
617 			break;
618 		}
619 
620 		xpt_setup_ccb(&new_ccb->ccb_h, periph->path, /*priority*/ 1);
621 		new_ccb->ccb_h.func_code = XPT_IMMEDIATE_NOTIFY;
622 		new_ccb->ccb_h.cbfcnp = ctlfedone;
623 		xpt_action(new_ccb);
624 		softc->inots_sent++;
625 		status = new_ccb->ccb_h.status;
626 		if ((status & CAM_STATUS_MASK) != CAM_REQ_INPROG) {
627 			/*
628 			 * Note that we don't free the CCB here.  If the
629 			 * status is not CAM_REQ_INPROG, then we're
630 			 * probably talking to a SIM that says it is
631 			 * target-capable but doesn't support the
632 			 * XPT_IMMEDIATE_NOTIFY CCB.  i.e. it supports the
633 			 * older API.  In that case, it'll call xpt_done()
634 			 * on the CCB, and we need to free it in our done
635 			 * routine as a result.
636 			 */
637 			break;
638 		}
639 	}
640 	if ((i == 0)
641 	 || (status != CAM_REQ_INPROG)) {
642 		xpt_print(periph->path, "%s: could not allocate immediate "
643 			  "notify CCBs, status 0x%x\n", __func__, status);
644 		return (CAM_REQ_CMP_ERR);
645 	}
646 	return (CAM_REQ_CMP);
647 }
648 
649 static void
650 ctlfeoninvalidate(struct cam_periph *periph)
651 {
652 	union ccb en_lun_ccb;
653 	cam_status status;
654 	struct ctlfe_lun_softc *softc;
655 
656 	softc = (struct ctlfe_lun_softc *)periph->softc;
657 
658 	xpt_setup_ccb(&en_lun_ccb.ccb_h, periph->path, CAM_PRIORITY_NONE);
659 	en_lun_ccb.ccb_h.func_code = XPT_EN_LUN;
660 	en_lun_ccb.cel.grp6_len = 0;
661 	en_lun_ccb.cel.grp7_len = 0;
662 	en_lun_ccb.cel.enable = 0;
663 	xpt_action(&en_lun_ccb);
664 	status = (en_lun_ccb.ccb_h.status & CAM_STATUS_MASK);
665 	if (status != CAM_REQ_CMP) {
666 		xpt_print(periph->path, "%s: Disable LUN failed, status 0x%x\n",
667 			  __func__, en_lun_ccb.ccb_h.status);
668 		/*
669 		 * XXX KDM what do we do now?
670 		 */
671 	}
672 	xpt_print(periph->path, "LUN removed, %ju ATIOs outstanding, %ju "
673 		  "INOTs outstanding, %d refs\n", softc->atios_sent -
674 		  softc->atios_returned, softc->inots_sent -
675 		  softc->inots_returned, periph->refcount);
676 }
677 
678 static void
679 ctlfecleanup(struct cam_periph *periph)
680 {
681 	struct ctlfe_lun_softc *softc;
682 	struct ctlfe_softc *bus_softc;
683 
684 	xpt_print(periph->path, "%s: Called\n", __func__);
685 
686 	softc = (struct ctlfe_lun_softc *)periph->softc;
687 	bus_softc = softc->parent_softc;
688 
689 	STAILQ_REMOVE(&bus_softc->lun_softc_list, softc, ctlfe_lun_softc, links);
690 
691 	/*
692 	 * XXX KDM is there anything else that needs to be done here?
693 	 */
694 
695 	callout_stop(&softc->dma_callout);
696 
697 	free(softc, M_CTLFE);
698 }
699 
700 static void
701 ctlfestart(struct cam_periph *periph, union ccb *start_ccb)
702 {
703 	struct ctlfe_lun_softc *softc;
704 	struct ccb_hdr *ccb_h;
705 
706 	softc = (struct ctlfe_lun_softc *)periph->softc;
707 
708 	softc->ccbs_alloced++;
709 
710 	start_ccb->ccb_h.ccb_type = CTLFE_CCB_DEFAULT;
711 
712 	ccb_h = TAILQ_FIRST(&softc->work_queue);
713 	if (periph->immediate_priority <= periph->pinfo.priority) {
714 		panic("shouldn't get to the CCB waiting case!");
715 		start_ccb->ccb_h.ccb_type = CTLFE_CCB_WAITING;
716 		SLIST_INSERT_HEAD(&periph->ccb_list, &start_ccb->ccb_h,
717 				  periph_links.sle);
718 		periph->immediate_priority = CAM_PRIORITY_NONE;
719 		wakeup(&periph->ccb_list);
720 	} else if (ccb_h == NULL) {
721 		softc->ccbs_freed++;
722 		xpt_release_ccb(start_ccb);
723 	} else {
724 		struct ccb_accept_tio *atio;
725 		struct ccb_scsiio *csio;
726 		uint8_t *data_ptr;
727 		uint32_t dxfer_len;
728 		ccb_flags flags;
729 		union ctl_io *io;
730 		uint8_t scsi_status;
731 
732 		/* Take the ATIO off the work queue */
733 		TAILQ_REMOVE(&softc->work_queue, ccb_h, periph_links.tqe);
734 		atio = (struct ccb_accept_tio *)ccb_h;
735 		io = (union ctl_io *)ccb_h->io_ptr;
736 		csio = &start_ccb->csio;
737 
738 		flags = atio->ccb_h.flags &
739 			(CAM_DIS_DISCONNECT|CAM_TAG_ACTION_VALID|CAM_DIR_MASK);
740 
741 		if ((io == NULL)
742 		 || (io->io_hdr.status & CTL_STATUS_MASK) != CTL_STATUS_NONE) {
743 			/*
744 			 * We're done, send status back.
745 			 */
746 			flags |= CAM_SEND_STATUS;
747 			if (io == NULL) {
748 				scsi_status = SCSI_STATUS_BUSY;
749 				csio->sense_len = 0;
750 			} else if ((io->io_hdr.status & CTL_STATUS_MASK) ==
751 				   CTL_CMD_ABORTED) {
752 				io->io_hdr.flags &= ~CTL_FLAG_STATUS_QUEUED;
753 
754 				/*
755 				 * If this command was aborted, we don't
756 				 * need to send status back to the SIM.
757 				 * Just free the CTIO and ctl_io, and
758 				 * recycle the ATIO back to the SIM.
759 				 */
760 				xpt_print(periph->path, "%s: aborted "
761 					  "command 0x%04x discarded\n",
762 					  __func__, io->scsiio.tag_num);
763 				ctl_free_io(io);
764 				/*
765 				 * For a wildcard attachment, commands can
766 				 * come in with a specific target/lun.  Reset
767 				 * the target and LUN fields back to the
768 				 * wildcard values before we send them back
769 				 * down to the SIM.  The SIM has a wildcard
770 				 * LUN enabled, not whatever target/lun
771 				 * these happened to be.
772 				 */
773 				if (softc->flags & CTLFE_LUN_WILDCARD) {
774 					atio->ccb_h.target_id =
775 						CAM_TARGET_WILDCARD;
776 					atio->ccb_h.target_lun =
777 						CAM_LUN_WILDCARD;
778 				}
779 
780 				if ((atio->ccb_h.status & CAM_DEV_QFRZN) != 0) {
781 					cam_release_devq(periph->path,
782 							 /*relsim_flags*/0,
783 							 /*reduction*/0,
784  							 /*timeout*/0,
785 							 /*getcount_only*/0);
786 					atio->ccb_h.status &= ~CAM_DEV_QFRZN;
787 				}
788 
789 				ccb_h = TAILQ_FIRST(&softc->work_queue);
790 
791 				if (atio->ccb_h.func_code !=
792 				    XPT_ACCEPT_TARGET_IO) {
793 					xpt_print(periph->path, "%s: func_code "
794 						  "is %#x\n", __func__,
795 						  atio->ccb_h.func_code);
796 				}
797 				start_ccb->ccb_h.func_code = XPT_ABORT;
798 				start_ccb->cab.abort_ccb = (union ccb *)atio;
799 				start_ccb->ccb_h.cbfcnp = ctlfedone;
800 
801 				/* Tell the SIM that we've aborted this ATIO */
802 				xpt_action(start_ccb);
803 				softc->ccbs_freed++;
804 				xpt_release_ccb(start_ccb);
805 
806 				/*
807 				 * Send the ATIO back down to the SIM.
808 				 */
809 				xpt_action((union ccb *)atio);
810 				softc->atios_sent++;
811 
812 				/*
813 				 * If we still have work to do, ask for
814 				 * another CCB.  Otherwise, deactivate our
815 				 * callout.
816 				 */
817 				if (ccb_h != NULL)
818 					xpt_schedule(periph, /*priority*/ 1);
819 				else
820 					callout_stop(&softc->dma_callout);
821 
822 				return;
823 			} else {
824 				io->io_hdr.flags &= ~CTL_FLAG_STATUS_QUEUED;
825 				scsi_status = io->scsiio.scsi_status;
826 				csio->sense_len = io->scsiio.sense_len;
827 			}
828 			data_ptr = NULL;
829 			dxfer_len = 0;
830 			if (io == NULL) {
831 				printf("%s: tag %04x io is NULL\n", __func__,
832 				       atio->tag_id);
833 			} else {
834 #ifdef CTLFEDEBUG
835 				printf("%s: tag %04x status %x\n", __func__,
836 				       atio->tag_id, io->io_hdr.status);
837 #endif
838 			}
839 			csio->sglist_cnt = 0;
840 			if (csio->sense_len != 0) {
841 				csio->sense_data = io->scsiio.sense_data;
842 				flags |= CAM_SEND_SENSE;
843 			} else if (scsi_status == SCSI_STATUS_CHECK_COND) {
844 				xpt_print(periph->path, "%s: check condition "
845 					  "with no sense\n", __func__);
846 			}
847 		} else {
848 			struct ctlfe_lun_cmd_info *cmd_info;
849 
850 			/*
851 			 * Datamove call, we need to setup the S/G list.
852 			 */
853 
854 			cmd_info = (struct ctlfe_lun_cmd_info *)
855 				io->io_hdr.port_priv;
856 
857 			KASSERT(sizeof(*cmd_info) < CTL_PORT_PRIV_SIZE,
858 				("%s: sizeof(struct ctlfe_lun_cmd_info) %zd < "
859 				"CTL_PORT_PRIV_SIZE %d", __func__,
860 				sizeof(*cmd_info), CTL_PORT_PRIV_SIZE));
861 			io->io_hdr.flags &= ~CTL_FLAG_DMA_QUEUED;
862 
863 			/*
864 			 * Need to zero this, in case it has been used for
865 			 * a previous datamove for this particular I/O.
866 			 */
867 			bzero(cmd_info, sizeof(*cmd_info));
868 			scsi_status = 0;
869 
870 			/*
871 			 * Set the direction, relative to the initiator.
872 			 */
873 			flags &= ~CAM_DIR_MASK;
874 			if ((io->io_hdr.flags & CTL_FLAG_DATA_MASK) ==
875 			     CTL_FLAG_DATA_IN)
876 				flags |= CAM_DIR_IN;
877 			else
878 				flags |= CAM_DIR_OUT;
879 
880 			csio->cdb_len = atio->cdb_len;
881 
882 			flags &= ~CAM_DATA_MASK;
883 			if (io->scsiio.kern_sg_entries == 0) {
884 				/* No S/G list */
885 				data_ptr = io->scsiio.kern_data_ptr;
886 				dxfer_len = io->scsiio.kern_data_len;
887 				csio->sglist_cnt = 0;
888 
889 				if (io->io_hdr.flags & CTL_FLAG_BUS_ADDR)
890 					flags |= CAM_DATA_PADDR;
891 				else
892 					flags |= CAM_DATA_VADDR;
893 			} else if (io->scsiio.kern_sg_entries <=
894 				   (sizeof(cmd_info->cam_sglist)/
895 				   sizeof(cmd_info->cam_sglist[0]))) {
896 				/*
897 				 * S/G list with physical or virtual pointers.
898 				 * Just populate the CAM S/G list with the
899 				 * pointers.
900 				 */
901 				int i;
902 				struct ctl_sg_entry *ctl_sglist;
903 				bus_dma_segment_t *cam_sglist;
904 
905 				ctl_sglist = (struct ctl_sg_entry *)
906 					io->scsiio.kern_data_ptr;
907 				cam_sglist = cmd_info->cam_sglist;
908 
909 				for (i = 0; i < io->scsiio.kern_sg_entries;i++){
910 					cam_sglist[i].ds_addr =
911 						(bus_addr_t)ctl_sglist[i].addr;
912 					cam_sglist[i].ds_len =
913 						ctl_sglist[i].len;
914 				}
915 				csio->sglist_cnt = io->scsiio.kern_sg_entries;
916 				if (io->io_hdr.flags & CTL_FLAG_BUS_ADDR)
917 					flags |= CAM_DATA_SG_PADDR;
918 				else
919 					flags |= CAM_DATA_SG;
920 				data_ptr = (uint8_t *)cam_sglist;
921 				dxfer_len = io->scsiio.kern_data_len;
922 			} else {
923 				/* S/G list with virtual pointers */
924 				struct ctl_sg_entry *sglist;
925 				int *ti;
926 
927 				/*
928 				 * If we have more S/G list pointers than
929 				 * will fit in the available storage in the
930 				 * cmd_info structure inside the ctl_io header,
931 				 * then we need to send down the pointers
932 				 * one element at a time.
933 				 */
934 
935 				sglist = (struct ctl_sg_entry *)
936 					io->scsiio.kern_data_ptr;
937 				ti = &cmd_info->cur_transfer_index;
938 				data_ptr = sglist[*ti].addr;
939 				dxfer_len = sglist[*ti].len;
940 				csio->sglist_cnt = 0;
941 				if (io->io_hdr.flags & CTL_FLAG_BUS_ADDR)
942 					flags |= CAM_DATA_PADDR;
943 				else
944 					flags |= CAM_DATA_VADDR;
945 				cmd_info->flags |= CTLFE_CMD_PIECEWISE;
946 				(*ti)++;
947 			}
948 
949 			io->scsiio.ext_data_filled += dxfer_len;
950 
951 			if (io->scsiio.ext_data_filled >
952 			    io->scsiio.kern_total_len) {
953 				xpt_print(periph->path, "%s: tag 0x%04x "
954 					  "fill len %u > total %u\n",
955 					  __func__, io->scsiio.tag_num,
956 					  io->scsiio.ext_data_filled,
957 					  io->scsiio.kern_total_len);
958 			}
959 		}
960 
961 #ifdef CTLFEDEBUG
962 		printf("%s: %s: tag %04x flags %x ptr %p len %u\n", __func__,
963 		       (flags & CAM_SEND_STATUS) ? "done" : "datamove",
964 		       atio->tag_id, flags, data_ptr, dxfer_len);
965 #endif
966 
967 		/*
968 		 * Valid combinations:
969 		 *  - CAM_SEND_STATUS, SCATTER_VALID = 0, dxfer_len = 0,
970 		 *    sglist_cnt = 0
971 		 *  - CAM_SEND_STATUS = 0, SCATTER_VALID = 0, dxfer_len != 0,
972 		 *    sglist_cnt = 0
973 		 *  - CAM_SEND_STATUS = 0, SCATTER_VALID, dxfer_len != 0,
974 		 *    sglist_cnt != 0
975 		 */
976 #ifdef CTLFEDEBUG
977 		if (((flags & CAM_SEND_STATUS)
978 		  && (((flags & CAM_SCATTER_VALID) != 0)
979 		   || (dxfer_len != 0)
980 		   || (csio->sglist_cnt != 0)))
981 		 || (((flags & CAM_SEND_STATUS) == 0)
982 		  && (dxfer_len == 0))
983 		 || ((flags & CAM_SCATTER_VALID)
984 		  && (csio->sglist_cnt == 0))
985 		 || (((flags & CAM_SCATTER_VALID) == 0)
986 		  && (csio->sglist_cnt != 0))) {
987 			printf("%s: tag %04x cdb %02x flags %#x dxfer_len "
988 			       "%d sg %u\n", __func__, atio->tag_id,
989 			       atio->cdb_io.cdb_bytes[0], flags, dxfer_len,
990 			       csio->sglist_cnt);
991 			if (io != NULL) {
992 				printf("%s: tag %04x io status %#x\n", __func__,
993 				       atio->tag_id, io->io_hdr.status);
994 			} else {
995 				printf("%s: tag %04x no associated io\n",
996 				       __func__, atio->tag_id);
997 			}
998 		}
999 #endif
1000 		cam_fill_ctio(csio,
1001 			      /*retries*/ 2,
1002 			      ctlfedone,
1003 			      flags,
1004 			      (flags & CAM_TAG_ACTION_VALID) ?
1005 			       MSG_SIMPLE_Q_TAG : 0,
1006 			      atio->tag_id,
1007 			      atio->init_id,
1008 			      scsi_status,
1009 			      /*data_ptr*/ data_ptr,
1010 			      /*dxfer_len*/ dxfer_len,
1011 			      /*timeout*/ 5 * 1000);
1012 		start_ccb->ccb_h.ccb_atio = atio;
1013 		if (((flags & CAM_SEND_STATUS) == 0)
1014 		 && (io != NULL))
1015 			io->io_hdr.flags |= CTL_FLAG_DMA_INPROG;
1016 
1017 		softc->ctios_sent++;
1018 
1019 		xpt_action(start_ccb);
1020 
1021 		if ((atio->ccb_h.status & CAM_DEV_QFRZN) != 0) {
1022 			cam_release_devq(periph->path,
1023 					 /*relsim_flags*/0,
1024 					 /*reduction*/0,
1025  					 /*timeout*/0,
1026 					 /*getcount_only*/0);
1027 			atio->ccb_h.status &= ~CAM_DEV_QFRZN;
1028 		}
1029 
1030 		ccb_h = TAILQ_FIRST(&softc->work_queue);
1031 	}
1032 	/*
1033 	 * If we still have work to do, ask for another CCB.  Otherwise,
1034 	 * deactivate our callout.
1035 	 */
1036 	if (ccb_h != NULL)
1037 		xpt_schedule(periph, /*priority*/ 1);
1038 	else
1039 		callout_stop(&softc->dma_callout);
1040 }
1041 
1042 static void
1043 ctlfe_free_ccb(struct cam_periph *periph, union ccb *ccb)
1044 {
1045 	struct ctlfe_lun_softc *softc;
1046 
1047 	softc = (struct ctlfe_lun_softc *)periph->softc;
1048 
1049 	switch (ccb->ccb_h.func_code) {
1050 	case XPT_ACCEPT_TARGET_IO:
1051 		softc->atios_returned++;
1052 		break;
1053 	case XPT_IMMEDIATE_NOTIFY:
1054 	case XPT_NOTIFY_ACKNOWLEDGE:
1055 		softc->inots_returned++;
1056 		break;
1057 	default:
1058 		break;
1059 	}
1060 
1061 	free(ccb, M_CTLFE);
1062 
1063 	KASSERT(softc->atios_returned <= softc->atios_sent, ("%s: "
1064 		"atios_returned %ju > atios_sent %ju", __func__,
1065 		softc->atios_returned, softc->atios_sent));
1066 	KASSERT(softc->inots_returned <= softc->inots_sent, ("%s: "
1067 		"inots_returned %ju > inots_sent %ju", __func__,
1068 		softc->inots_returned, softc->inots_sent));
1069 
1070 	/*
1071 	 * If we have received all of our CCBs, we can release our
1072 	 * reference on the peripheral driver.  It will probably go away
1073 	 * now.
1074 	 */
1075 	if ((softc->atios_returned == softc->atios_sent)
1076 	 && (softc->inots_returned == softc->inots_sent)) {
1077 		cam_periph_release_locked(periph);
1078 	}
1079 }
1080 
1081 static int
1082 ctlfe_adjust_cdb(struct ccb_accept_tio *atio, uint32_t offset)
1083 {
1084 	uint64_t lba;
1085 	uint32_t num_blocks, nbc;
1086 	uint8_t *cmdbyt = (atio->ccb_h.flags & CAM_CDB_POINTER)?
1087 	    atio->cdb_io.cdb_ptr : atio->cdb_io.cdb_bytes;
1088 
1089 	nbc = offset >> 9;	/* ASSUMING 512 BYTE BLOCKS */
1090 
1091 	switch (cmdbyt[0]) {
1092 	case READ_6:
1093 	case WRITE_6:
1094 	{
1095 		struct scsi_rw_6 *cdb = (struct scsi_rw_6 *)cmdbyt;
1096 		lba = scsi_3btoul(cdb->addr);
1097 		lba &= 0x1fffff;
1098 		num_blocks = cdb->length;
1099 		if (num_blocks == 0)
1100 			num_blocks = 256;
1101 		lba += nbc;
1102 		num_blocks -= nbc;
1103 		scsi_ulto3b(lba, cdb->addr);
1104 		cdb->length = num_blocks;
1105 		break;
1106 	}
1107 	case READ_10:
1108 	case WRITE_10:
1109 	{
1110 		struct scsi_rw_10 *cdb = (struct scsi_rw_10 *)cmdbyt;
1111 		lba = scsi_4btoul(cdb->addr);
1112 		num_blocks = scsi_2btoul(cdb->length);
1113 		lba += nbc;
1114 		num_blocks -= nbc;
1115 		scsi_ulto4b(lba, cdb->addr);
1116 		scsi_ulto2b(num_blocks, cdb->length);
1117 		break;
1118 	}
1119 	case READ_12:
1120 	case WRITE_12:
1121 	{
1122 		struct scsi_rw_12 *cdb = (struct scsi_rw_12 *)cmdbyt;
1123 		lba = scsi_4btoul(cdb->addr);
1124 		num_blocks = scsi_4btoul(cdb->length);
1125 		lba += nbc;
1126 		num_blocks -= nbc;
1127 		scsi_ulto4b(lba, cdb->addr);
1128 		scsi_ulto4b(num_blocks, cdb->length);
1129 		break;
1130 	}
1131 	case READ_16:
1132 	case WRITE_16:
1133 	{
1134 		struct scsi_rw_16 *cdb = (struct scsi_rw_16 *)cmdbyt;
1135 		lba = scsi_8btou64(cdb->addr);
1136 		num_blocks = scsi_4btoul(cdb->length);
1137 		lba += nbc;
1138 		num_blocks -= nbc;
1139 		scsi_u64to8b(lba, cdb->addr);
1140 		scsi_ulto4b(num_blocks, cdb->length);
1141 		break;
1142 	}
1143 	default:
1144 		return -1;
1145 	}
1146 	return (0);
1147 }
1148 
1149 static void
1150 ctlfedone(struct cam_periph *periph, union ccb *done_ccb)
1151 {
1152 	struct ctlfe_lun_softc *softc;
1153 	struct ctlfe_softc *bus_softc;
1154 	struct ccb_accept_tio *atio = NULL;
1155 	union ctl_io *io = NULL;
1156 
1157 #ifdef CTLFE_DEBUG
1158 	printf("%s: entered, func_code = %#x, type = %#lx\n", __func__,
1159 	       done_ccb->ccb_h.func_code, done_ccb->ccb_h.ccb_type);
1160 #endif
1161 
1162 	softc = (struct ctlfe_lun_softc *)periph->softc;
1163 	bus_softc = softc->parent_softc;
1164 
1165 	if (done_ccb->ccb_h.ccb_type == CTLFE_CCB_WAITING) {
1166 		panic("shouldn't get to the CCB waiting case!");
1167 		wakeup(&done_ccb->ccb_h.cbfcnp);
1168 		return;
1169 	}
1170 
1171 	/*
1172 	 * If the peripheral is invalid, ATIOs and immediate notify CCBs
1173 	 * need to be freed.  Most of the ATIOs and INOTs that come back
1174 	 * will be CCBs that are being returned from the SIM as a result of
1175 	 * our disabling the LUN.
1176 	 *
1177 	 * Other CCB types are handled in their respective cases below.
1178 	 */
1179 	if (periph->flags & CAM_PERIPH_INVALID) {
1180 		switch (done_ccb->ccb_h.func_code) {
1181 		case XPT_ACCEPT_TARGET_IO:
1182 		case XPT_IMMEDIATE_NOTIFY:
1183 		case XPT_NOTIFY_ACKNOWLEDGE:
1184 			ctlfe_free_ccb(periph, done_ccb);
1185 			return;
1186 		default:
1187 			break;
1188 		}
1189 
1190 	}
1191 	switch (done_ccb->ccb_h.func_code) {
1192 	case XPT_ACCEPT_TARGET_IO: {
1193 
1194 		atio = &done_ccb->atio;
1195 
1196 		softc->atios_returned++;
1197 
1198  resubmit:
1199 		/*
1200 		 * Allocate a ctl_io, pass it to CTL, and wait for the
1201 		 * datamove or done.
1202 		 */
1203 		io = ctl_alloc_io(bus_softc->fe.ctl_pool_ref);
1204 		if (io == NULL) {
1205 			atio->ccb_h.flags &= ~CAM_DIR_MASK;
1206 			atio->ccb_h.flags |= CAM_DIR_NONE;
1207 
1208 			printf("%s: ctl_alloc_io failed!\n", __func__);
1209 
1210 			/*
1211 			 * XXX KDM need to set SCSI_STATUS_BUSY, but there
1212 			 * is no field in the ATIO structure to do that,
1213 			 * and we aren't able to allocate a ctl_io here.
1214 			 * What to do?
1215 			 */
1216 			atio->sense_len = 0;
1217 			done_ccb->ccb_h.io_ptr = NULL;
1218 			TAILQ_INSERT_TAIL(&softc->work_queue, &atio->ccb_h,
1219 					  periph_links.tqe);
1220 			xpt_schedule(periph, /*priority*/ 1);
1221 			break;
1222 		}
1223 		ctl_zero_io(io);
1224 
1225 		/* Save pointers on both sides */
1226 		io->io_hdr.ctl_private[CTL_PRIV_FRONTEND].ptr = done_ccb;
1227 		done_ccb->ccb_h.io_ptr = io;
1228 
1229 		/*
1230 		 * Only SCSI I/O comes down this path, resets, etc. come
1231 		 * down the immediate notify path below.
1232 		 */
1233 		io->io_hdr.io_type = CTL_IO_SCSI;
1234 		io->io_hdr.nexus.initid.id = atio->init_id;
1235 		io->io_hdr.nexus.targ_port = bus_softc->fe.targ_port;
1236 		io->io_hdr.nexus.targ_target.id = atio->ccb_h.target_id;
1237 		io->io_hdr.nexus.targ_lun = atio->ccb_h.target_lun;
1238 		io->scsiio.tag_num = atio->tag_id;
1239 		switch (atio->tag_action) {
1240 		case CAM_TAG_ACTION_NONE:
1241 			io->scsiio.tag_type = CTL_TAG_UNTAGGED;
1242 			break;
1243 		case MSG_SIMPLE_TASK:
1244 			io->scsiio.tag_type = CTL_TAG_SIMPLE;
1245 			break;
1246 		case MSG_HEAD_OF_QUEUE_TASK:
1247         		io->scsiio.tag_type = CTL_TAG_HEAD_OF_QUEUE;
1248 			break;
1249 		case MSG_ORDERED_TASK:
1250         		io->scsiio.tag_type = CTL_TAG_ORDERED;
1251 			break;
1252 		case MSG_ACA_TASK:
1253 			io->scsiio.tag_type = CTL_TAG_ACA;
1254 			break;
1255 		default:
1256 			io->scsiio.tag_type = CTL_TAG_UNTAGGED;
1257 			printf("%s: unhandled tag type %#x!!\n", __func__,
1258 			       atio->tag_action);
1259 			break;
1260 		}
1261 		if (atio->cdb_len > sizeof(io->scsiio.cdb)) {
1262 			printf("%s: WARNING: CDB len %d > ctl_io space %zd\n",
1263 			       __func__, atio->cdb_len, sizeof(io->scsiio.cdb));
1264 		}
1265 		io->scsiio.cdb_len = min(atio->cdb_len, sizeof(io->scsiio.cdb));
1266 		bcopy(atio->cdb_io.cdb_bytes, io->scsiio.cdb,
1267 		      io->scsiio.cdb_len);
1268 
1269 #ifdef CTLFEDEBUG
1270 		printf("%s: %ju:%d:%ju:%d: tag %04x CDB %02x\n", __func__,
1271 		        (uintmax_t)io->io_hdr.nexus.initid.id,
1272 		        io->io_hdr.nexus.targ_port,
1273 		        (uintmax_t)io->io_hdr.nexus.targ_target.id,
1274 		        io->io_hdr.nexus.targ_lun,
1275 			io->scsiio.tag_num, io->scsiio.cdb[0]);
1276 #endif
1277 
1278 		ctl_queue(io);
1279 		break;
1280 	}
1281 	case XPT_CONT_TARGET_IO: {
1282 		int srr = 0;
1283 		uint32_t srr_off = 0;
1284 
1285 		atio = (struct ccb_accept_tio *)done_ccb->ccb_h.ccb_atio;
1286 		io = (union ctl_io *)atio->ccb_h.io_ptr;
1287 
1288 		softc->ctios_returned++;
1289 #ifdef CTLFEDEBUG
1290 		printf("%s: got XPT_CONT_TARGET_IO tag %#x flags %#x\n",
1291 		       __func__, atio->tag_id, done_ccb->ccb_h.flags);
1292 #endif
1293 		/*
1294 		 * Handle SRR case were the data pointer is pushed back hack
1295 		 */
1296 		if ((done_ccb->ccb_h.status & CAM_STATUS_MASK) == CAM_MESSAGE_RECV
1297 		    && done_ccb->csio.msg_ptr != NULL
1298 		    && done_ccb->csio.msg_ptr[0] == MSG_EXTENDED
1299 		    && done_ccb->csio.msg_ptr[1] == 5
1300        		    && done_ccb->csio.msg_ptr[2] == 0) {
1301 			srr = 1;
1302 			srr_off =
1303 			    (done_ccb->csio.msg_ptr[3] << 24)
1304 			    | (done_ccb->csio.msg_ptr[4] << 16)
1305 			    | (done_ccb->csio.msg_ptr[5] << 8)
1306 			    | (done_ccb->csio.msg_ptr[6]);
1307 		}
1308 
1309 		if (srr && (done_ccb->ccb_h.flags & CAM_SEND_STATUS)) {
1310 			/*
1311 			 * If status was being sent, the back end data is now
1312 			 * history. Hack it up and resubmit a new command with
1313 			 * the CDB adjusted. If the SIM does the right thing,
1314 			 * all of the resid math should work.
1315 			 */
1316 			softc->ccbs_freed++;
1317 			xpt_release_ccb(done_ccb);
1318 			ctl_free_io(io);
1319 			if (ctlfe_adjust_cdb(atio, srr_off) == 0) {
1320 				done_ccb = (union ccb *)atio;
1321 				goto resubmit;
1322 			}
1323 			/*
1324 			 * Fall through to doom....
1325 			 */
1326 		} else if (srr) {
1327 			/*
1328 			 * If we have an srr and we're still sending data, we
1329 			 * should be able to adjust offsets and cycle again.
1330 			 */
1331 			io->scsiio.kern_rel_offset =
1332 			    io->scsiio.ext_data_filled = srr_off;
1333 			io->scsiio.ext_data_len = io->scsiio.kern_total_len -
1334 			    io->scsiio.kern_rel_offset;
1335 			softc->ccbs_freed++;
1336 			io->scsiio.io_hdr.status = CTL_STATUS_NONE;
1337 			xpt_release_ccb(done_ccb);
1338 			TAILQ_INSERT_HEAD(&softc->work_queue, &atio->ccb_h,
1339 					  periph_links.tqe);
1340 			xpt_schedule(periph, /*priority*/ 1);
1341 			return;
1342 		}
1343 
1344 		/*
1345 		 * If we were sending status back to the initiator, free up
1346 		 * resources.  If we were doing a datamove, call the
1347 		 * datamove done routine.
1348 		 */
1349 		if (done_ccb->ccb_h.flags & CAM_SEND_STATUS) {
1350 			softc->ccbs_freed++;
1351 			xpt_release_ccb(done_ccb);
1352 			ctl_free_io(io);
1353 			/*
1354 			 * For a wildcard attachment, commands can come in
1355 			 * with a specific target/lun.  Reset the target
1356 			 * and LUN fields back to the wildcard values before
1357 			 * we send them back down to the SIM.  The SIM has
1358 			 * a wildcard LUN enabled, not whatever target/lun
1359 			 * these happened to be.
1360 			 */
1361 			if (softc->flags & CTLFE_LUN_WILDCARD) {
1362 				atio->ccb_h.target_id = CAM_TARGET_WILDCARD;
1363 				atio->ccb_h.target_lun = CAM_LUN_WILDCARD;
1364 			}
1365 			if (periph->flags & CAM_PERIPH_INVALID) {
1366 				ctlfe_free_ccb(periph, (union ccb *)atio);
1367 				return;
1368 			} else {
1369 				xpt_action((union ccb *)atio);
1370 				softc->atios_sent++;
1371 			}
1372 		} else {
1373 			struct ctlfe_lun_cmd_info *cmd_info;
1374 			struct ccb_scsiio *csio;
1375 
1376 			csio = &done_ccb->csio;
1377 			cmd_info = (struct ctlfe_lun_cmd_info *)
1378 				io->io_hdr.port_priv;
1379 
1380 			io->io_hdr.flags &= ~CTL_FLAG_DMA_INPROG;
1381 
1382 			io->scsiio.ext_data_len += csio->dxfer_len;
1383 			if (io->scsiio.ext_data_len >
1384 			    io->scsiio.kern_total_len) {
1385 				xpt_print(periph->path, "%s: tag 0x%04x "
1386 					  "done len %u > total %u sent %u\n",
1387 					  __func__, io->scsiio.tag_num,
1388 					  io->scsiio.ext_data_len,
1389 					  io->scsiio.kern_total_len,
1390 					  io->scsiio.ext_data_filled);
1391 			}
1392 			/*
1393 			 * Translate CAM status to CTL status.  Success
1394 			 * does not change the overall, ctl_io status.  In
1395 			 * that case we just set port_status to 0.  If we
1396 			 * have a failure, though, set a data phase error
1397 			 * for the overall ctl_io.
1398 			 */
1399 			switch (done_ccb->ccb_h.status & CAM_STATUS_MASK) {
1400 			case CAM_REQ_CMP:
1401 				io->io_hdr.port_status = 0;
1402 				break;
1403 			default:
1404 				/*
1405 				 * XXX KDM we probably need to figure out a
1406 				 * standard set of errors that the SIM
1407 				 * drivers should return in the event of a
1408 				 * data transfer failure.  A data phase
1409 				 * error will at least point the user to a
1410 				 * data transfer error of some sort.
1411 				 * Hopefully the SIM printed out some
1412 				 * additional information to give the user
1413 				 * a clue what happened.
1414 				 */
1415 				io->io_hdr.port_status = 0xbad1;
1416 				ctl_set_data_phase_error(&io->scsiio);
1417 				/*
1418 				 * XXX KDM figure out residual.
1419 				 */
1420 				break;
1421 			}
1422 			/*
1423 			 * If we had to break this S/G list into multiple
1424 			 * pieces, figure out where we are in the list, and
1425 			 * continue sending pieces if necessary.
1426 			 */
1427 			if ((cmd_info->flags & CTLFE_CMD_PIECEWISE)
1428 			 && (io->io_hdr.port_status == 0)
1429 			 && (cmd_info->cur_transfer_index <
1430 			     io->scsiio.kern_sg_entries)) {
1431 				struct ctl_sg_entry *sglist;
1432 				ccb_flags flags;
1433 				uint8_t scsi_status;
1434 				uint8_t *data_ptr;
1435 				uint32_t dxfer_len;
1436 				int *ti;
1437 
1438 				sglist = (struct ctl_sg_entry *)
1439 					io->scsiio.kern_data_ptr;
1440 				ti = &cmd_info->cur_transfer_index;
1441 				flags = atio->ccb_h.flags &
1442 					(CAM_DIS_DISCONNECT|
1443 					 CAM_TAG_ACTION_VALID|
1444 					 CAM_DIR_MASK);
1445 
1446 				/*
1447 				 * Set the direction, relative to the initiator.
1448 				 */
1449 				flags &= ~CAM_DIR_MASK;
1450 				if ((io->io_hdr.flags & CTL_FLAG_DATA_MASK) ==
1451 				     CTL_FLAG_DATA_IN)
1452 					flags |= CAM_DIR_IN;
1453 				else
1454 					flags |= CAM_DIR_OUT;
1455 
1456 				data_ptr = sglist[*ti].addr;
1457 				dxfer_len = sglist[*ti].len;
1458 				(*ti)++;
1459 
1460 				scsi_status = 0;
1461 
1462 				if (((flags & CAM_SEND_STATUS) == 0)
1463 				 && (dxfer_len == 0)) {
1464 					printf("%s: tag %04x no status or "
1465 					       "len cdb = %02x\n", __func__,
1466 					       atio->tag_id,
1467 					atio->cdb_io.cdb_bytes[0]);
1468 					printf("%s: tag %04x io status %#x\n",
1469 					       __func__, atio->tag_id,
1470 					       io->io_hdr.status);
1471 				}
1472 
1473 				cam_fill_ctio(csio,
1474 					      /*retries*/ 2,
1475 					      ctlfedone,
1476 					      flags,
1477 					      (flags & CAM_TAG_ACTION_VALID) ?
1478 					       MSG_SIMPLE_Q_TAG : 0,
1479 					      atio->tag_id,
1480 					      atio->init_id,
1481 					      scsi_status,
1482 					      /*data_ptr*/ data_ptr,
1483 					      /*dxfer_len*/ dxfer_len,
1484 					      /*timeout*/ 5 * 1000);
1485 
1486 				csio->resid = 0;
1487 				csio->ccb_h.ccb_atio = atio;
1488 				io->io_hdr.flags |= CTL_FLAG_DMA_INPROG;
1489 				softc->ctios_sent++;
1490 				xpt_action((union ccb *)csio);
1491 			} else {
1492 				/*
1493 				 * Release the CTIO.  The ATIO will be sent back
1494 				 * down to the SIM once we send status.
1495 				 */
1496 				softc->ccbs_freed++;
1497 				xpt_release_ccb(done_ccb);
1498 
1499 				/* Call the backend move done callback */
1500 				io->scsiio.be_move_done(io);
1501 			}
1502 		}
1503 		break;
1504 	}
1505 	case XPT_IMMEDIATE_NOTIFY: {
1506 		union ctl_io *io;
1507 		struct ccb_immediate_notify *inot;
1508 		cam_status status;
1509 		int frozen;
1510 
1511 		inot = &done_ccb->cin1;
1512 
1513 		softc->inots_returned++;
1514 
1515 		frozen = (done_ccb->ccb_h.status & CAM_DEV_QFRZN) != 0;
1516 
1517 		printf("%s: got XPT_IMMEDIATE_NOTIFY status %#x tag %#x "
1518 		       "seq %#x\n", __func__, inot->ccb_h.status,
1519 		       inot->tag_id, inot->seq_id);
1520 
1521 		io = ctl_alloc_io(bus_softc->fe.ctl_pool_ref);
1522 		if (io != NULL) {
1523 			int send_ctl_io;
1524 
1525 			send_ctl_io = 1;
1526 
1527 			ctl_zero_io(io);
1528 			io->io_hdr.io_type = CTL_IO_TASK;
1529 			io->io_hdr.ctl_private[CTL_PRIV_FRONTEND].ptr =done_ccb;
1530 			inot->ccb_h.io_ptr = io;
1531 			io->io_hdr.nexus.initid.id = inot->initiator_id;
1532 			io->io_hdr.nexus.targ_port = bus_softc->fe.targ_port;
1533 			io->io_hdr.nexus.targ_target.id = inot->ccb_h.target_id;
1534 			io->io_hdr.nexus.targ_lun = inot->ccb_h.target_lun;
1535 			/* XXX KDM should this be the tag_id? */
1536 			io->taskio.tag_num = inot->seq_id;
1537 
1538 			status = inot->ccb_h.status & CAM_STATUS_MASK;
1539 			switch (status) {
1540 			case CAM_SCSI_BUS_RESET:
1541 				io->taskio.task_action = CTL_TASK_BUS_RESET;
1542 				break;
1543 			case CAM_BDR_SENT:
1544 				io->taskio.task_action = CTL_TASK_TARGET_RESET;
1545 				break;
1546 			case CAM_MESSAGE_RECV:
1547 				switch (inot->arg) {
1548 				case MSG_ABORT_TASK_SET:
1549 					/*
1550 					 * XXX KDM this isn't currently
1551 					 * supported by CTL.  It ends up
1552 					 * being a no-op.
1553 					 */
1554 					io->taskio.task_action =
1555 						CTL_TASK_ABORT_TASK_SET;
1556 					break;
1557 				case MSG_TARGET_RESET:
1558 					io->taskio.task_action =
1559 						CTL_TASK_TARGET_RESET;
1560 					break;
1561 				case MSG_ABORT_TASK:
1562 					io->taskio.task_action =
1563 						CTL_TASK_ABORT_TASK;
1564 					break;
1565 				case MSG_LOGICAL_UNIT_RESET:
1566 					io->taskio.task_action =
1567 						CTL_TASK_LUN_RESET;
1568 					break;
1569 				case MSG_CLEAR_TASK_SET:
1570 					/*
1571 					 * XXX KDM this isn't currently
1572 					 * supported by CTL.  It ends up
1573 					 * being a no-op.
1574 					 */
1575 					io->taskio.task_action =
1576 						CTL_TASK_CLEAR_TASK_SET;
1577 					break;
1578 				case MSG_CLEAR_ACA:
1579 					io->taskio.task_action =
1580 						CTL_TASK_CLEAR_ACA;
1581 					break;
1582 				case MSG_NOOP:
1583 					send_ctl_io = 0;
1584 					break;
1585 				default:
1586 					xpt_print(periph->path, "%s: "
1587 						  "unsupported message 0x%x\n",
1588 						  __func__, inot->arg);
1589 					send_ctl_io = 0;
1590 					break;
1591 				}
1592 				break;
1593 			case CAM_REQ_ABORTED:
1594 				/*
1595 				 * This request was sent back by the driver.
1596 				 * XXX KDM what do we do here?
1597 				 */
1598 				send_ctl_io = 0;
1599 				break;
1600 			case CAM_REQ_INVALID:
1601 			case CAM_PROVIDE_FAIL:
1602 			default:
1603 				/*
1604 				 * We should only get here if we're talking
1605 				 * to a talking to a SIM that is target
1606 				 * capable but supports the old API.  In
1607 				 * that case, we need to just free the CCB.
1608 				 * If we actually send a notify acknowledge,
1609 				 * it will send that back with an error as
1610 				 * well.
1611 				 */
1612 
1613 				if ((status != CAM_REQ_INVALID)
1614 				 && (status != CAM_PROVIDE_FAIL))
1615 					xpt_print(periph->path, "%s: "
1616 						  "unsupported CAM status "
1617 						  "0x%x\n", __func__, status);
1618 
1619 				ctl_free_io(io);
1620 				ctlfe_free_ccb(periph, done_ccb);
1621 
1622 				return;
1623 			}
1624 			if (send_ctl_io != 0) {
1625 				ctl_queue(io);
1626 			} else {
1627 				ctl_free_io(io);
1628 				done_ccb->ccb_h.status = CAM_REQ_INPROG;
1629 				done_ccb->ccb_h.func_code =
1630 					XPT_NOTIFY_ACKNOWLEDGE;
1631 				xpt_action(done_ccb);
1632 			}
1633 		} else {
1634 			xpt_print(periph->path, "%s: could not allocate "
1635 				  "ctl_io for immediate notify!\n", __func__);
1636 			/* requeue this to the adapter */
1637 			done_ccb->ccb_h.status = CAM_REQ_INPROG;
1638 			done_ccb->ccb_h.func_code = XPT_NOTIFY_ACKNOWLEDGE;
1639 			xpt_action(done_ccb);
1640 		}
1641 
1642 		if (frozen != 0) {
1643 			cam_release_devq(periph->path,
1644 					 /*relsim_flags*/ 0,
1645 					 /*opening reduction*/ 0,
1646 					 /*timeout*/ 0,
1647 					 /*getcount_only*/ 0);
1648 		}
1649 		break;
1650 	}
1651 	case XPT_NOTIFY_ACKNOWLEDGE:
1652 		/*
1653 		 * Queue this back down to the SIM as an immediate notify.
1654 		 */
1655 		done_ccb->ccb_h.func_code = XPT_IMMEDIATE_NOTIFY;
1656 		xpt_action(done_ccb);
1657 		softc->inots_sent++;
1658 		break;
1659 	case XPT_ABORT:
1660 		/*
1661 		 * XPT_ABORT is an immediate CCB, we shouldn't get here.
1662 		 */
1663 		panic("%s: XPT_ABORT CCB returned!", __func__);
1664 		break;
1665 	case XPT_SET_SIM_KNOB:
1666 	case XPT_GET_SIM_KNOB:
1667 		break;
1668 	default:
1669 		panic("%s: unexpected CCB type %#x", __func__,
1670 		      done_ccb->ccb_h.func_code);
1671 		break;
1672 	}
1673 }
1674 
1675 static void
1676 ctlfe_onoffline(void *arg, int online)
1677 {
1678 	struct ctlfe_softc *bus_softc;
1679 	union ccb *ccb;
1680 	cam_status status;
1681 	struct cam_path *path;
1682 	struct cam_sim *sim;
1683 	int set_wwnn;
1684 
1685 	bus_softc = (struct ctlfe_softc *)arg;
1686 
1687 	set_wwnn = 0;
1688 
1689 	sim = bus_softc->sim;
1690 
1691 	mtx_assert(sim->mtx, MA_OWNED);
1692 
1693 	status = xpt_create_path(&path, /*periph*/ NULL, bus_softc->path_id,
1694 		CAM_TARGET_WILDCARD, CAM_LUN_WILDCARD);
1695 	if (status != CAM_REQ_CMP) {
1696 		printf("%s: unable to create path!\n", __func__);
1697 		return;
1698 	}
1699 	ccb = (union ccb *)malloc(sizeof(*ccb), M_TEMP, M_NOWAIT | M_ZERO);
1700 	if (ccb == NULL) {
1701 		printf("%s: unable to malloc CCB!\n", __func__);
1702 		xpt_free_path(path);
1703 		return;
1704 	}
1705 	xpt_setup_ccb(&ccb->ccb_h, path, CAM_PRIORITY_NONE);
1706 
1707 	/*
1708 	 * Copan WWN format:
1709 	 *
1710 	 * Bits 63-60:	0x5		NAA, IEEE registered name
1711 	 * Bits 59-36:	0x000ED5	IEEE Company name assigned to Copan
1712 	 * Bits 35-12:			Copan SSN (Sequential Serial Number)
1713 	 * Bits 11-8:			Type of port:
1714 	 *					1 == N-Port
1715 	 *					2 == F-Port
1716 	 *					3 == NL-Port
1717 	 * Bits 7-0:			0 == Node Name, >0 == Port Number
1718 	 */
1719 
1720 	if (online != 0) {
1721 
1722 		ccb->ccb_h.func_code = XPT_GET_SIM_KNOB;
1723 
1724 
1725 		xpt_action(ccb);
1726 
1727 
1728 		if ((ccb->knob.xport_specific.valid & KNOB_VALID_ADDRESS) != 0){
1729 #ifdef RANDOM_WWNN
1730 			uint64_t random_bits;
1731 #endif
1732 
1733 			printf("%s: %s current WWNN %#jx\n", __func__,
1734 			       bus_softc->port_name,
1735 			       ccb->knob.xport_specific.fc.wwnn);
1736 			printf("%s: %s current WWPN %#jx\n", __func__,
1737 			       bus_softc->port_name,
1738 			       ccb->knob.xport_specific.fc.wwpn);
1739 
1740 #ifdef RANDOM_WWNN
1741 			arc4rand(&random_bits, sizeof(random_bits), 0);
1742 #endif
1743 
1744 			/*
1745 			 * XXX KDM this is a bit of a kludge for now.  We
1746 			 * take the current WWNN/WWPN from the card, and
1747 			 * replace the company identifier and the NL-Port
1748 			 * indicator and the port number (for the WWPN).
1749 			 * This should be replaced later with ddb_GetWWNN,
1750 			 * or possibly a more centralized scheme.  (It
1751 			 * would be nice to have the WWNN/WWPN for each
1752 			 * port stored in the ctl_frontend structure.)
1753 			 */
1754 #ifdef RANDOM_WWNN
1755 			ccb->knob.xport_specific.fc.wwnn =
1756 				(random_bits &
1757 				0x0000000fffffff00ULL) |
1758 				/* Company ID */ 0x5000ED5000000000ULL |
1759 				/* NL-Port */    0x0300;
1760 			ccb->knob.xport_specific.fc.wwpn =
1761 				(random_bits &
1762 				0x0000000fffffff00ULL) |
1763 				/* Company ID */ 0x5000ED5000000000ULL |
1764 				/* NL-Port */    0x3000 |
1765 				/* Port Num */ (bus_softc->fe.targ_port & 0xff);
1766 
1767 			/*
1768 			 * This is a bit of an API break/reversal, but if
1769 			 * we're doing the random WWNN that's a little
1770 			 * different anyway.  So record what we're actually
1771 			 * using with the frontend code so it's reported
1772 			 * accurately.
1773 			 */
1774 			bus_softc->fe.wwnn =
1775 				ccb->knob.xport_specific.fc.wwnn;
1776 			bus_softc->fe.wwpn =
1777 				ccb->knob.xport_specific.fc.wwpn;
1778 			set_wwnn = 1;
1779 #else /* RANDOM_WWNN */
1780 			/*
1781 			 * If the user has specified a WWNN/WWPN, send them
1782 			 * down to the SIM.  Otherwise, record what the SIM
1783 			 * has reported.
1784 			 */
1785 			if ((bus_softc->fe.wwnn != 0)
1786 			 && (bus_softc->fe.wwpn != 0)) {
1787 				ccb->knob.xport_specific.fc.wwnn =
1788 					bus_softc->fe.wwnn;
1789 				ccb->knob.xport_specific.fc.wwpn =
1790 					bus_softc->fe.wwpn;
1791 				set_wwnn = 1;
1792 			} else {
1793 				bus_softc->fe.wwnn =
1794 					ccb->knob.xport_specific.fc.wwnn;
1795 				bus_softc->fe.wwpn =
1796 					ccb->knob.xport_specific.fc.wwpn;
1797 			}
1798 #endif /* RANDOM_WWNN */
1799 
1800 
1801 			if (set_wwnn != 0) {
1802 				printf("%s: %s new WWNN %#jx\n", __func__,
1803 				       bus_softc->port_name,
1804 				ccb->knob.xport_specific.fc.wwnn);
1805 				printf("%s: %s new WWPN %#jx\n", __func__,
1806 				       bus_softc->port_name,
1807 				       ccb->knob.xport_specific.fc.wwpn);
1808 			}
1809 		} else {
1810 			printf("%s: %s has no valid WWNN/WWPN\n", __func__,
1811 			       bus_softc->port_name);
1812 		}
1813 	}
1814 	ccb->ccb_h.func_code = XPT_SET_SIM_KNOB;
1815 	ccb->knob.xport_specific.valid = KNOB_VALID_ROLE;
1816 	if (set_wwnn != 0)
1817 		ccb->knob.xport_specific.valid |= KNOB_VALID_ADDRESS;
1818 
1819 	if (online != 0)
1820 		ccb->knob.xport_specific.fc.role = KNOB_ROLE_TARGET;
1821 	else
1822 		ccb->knob.xport_specific.fc.role = KNOB_ROLE_NONE;
1823 
1824 	xpt_action(ccb);
1825 
1826 	if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) {
1827 		printf("%s: SIM %s (path id %d) target %s failed with "
1828 		       "status %#x\n",
1829 		       __func__, bus_softc->port_name, bus_softc->path_id,
1830 		       (online != 0) ? "enable" : "disable",
1831 		       ccb->ccb_h.status);
1832 	} else {
1833 		printf("%s: SIM %s (path id %d) target %s succeeded\n",
1834 		       __func__, bus_softc->port_name, bus_softc->path_id,
1835 		       (online != 0) ? "enable" : "disable");
1836 	}
1837 
1838 	xpt_free_path(path);
1839 
1840 	free(ccb, M_TEMP);
1841 
1842 	return;
1843 }
1844 
1845 static void
1846 ctlfe_online(void *arg)
1847 {
1848 	struct ctlfe_softc *bus_softc;
1849 	struct cam_path *path;
1850 	cam_status status;
1851 	struct ctlfe_lun_softc *lun_softc;
1852 	struct cam_sim *sim;
1853 
1854 	bus_softc = (struct ctlfe_softc *)arg;
1855 	sim = bus_softc->sim;
1856 
1857 	CAM_SIM_LOCK(sim);
1858 
1859 	/*
1860 	 * Create the wildcard LUN before bringing the port online.
1861 	 */
1862 	status = xpt_create_path(&path, /*periph*/ NULL,
1863 				 bus_softc->path_id, CAM_TARGET_WILDCARD,
1864 				 CAM_LUN_WILDCARD);
1865 	if (status != CAM_REQ_CMP) {
1866 		printf("%s: unable to create path for wildcard periph\n",
1867 				__func__);
1868 		CAM_SIM_UNLOCK(sim);
1869 		return;
1870 	}
1871 
1872 	lun_softc = malloc(sizeof(*lun_softc), M_CTLFE,
1873 			M_NOWAIT | M_ZERO);
1874 	if (lun_softc == NULL) {
1875 		xpt_print(path, "%s: unable to allocate softc for "
1876 				"wildcard periph\n", __func__);
1877 		xpt_free_path(path);
1878 		CAM_SIM_UNLOCK(sim);
1879 		return;
1880 	}
1881 
1882 	lun_softc->parent_softc = bus_softc;
1883 	lun_softc->flags |= CTLFE_LUN_WILDCARD;
1884 
1885 	STAILQ_INSERT_TAIL(&bus_softc->lun_softc_list, lun_softc, links);
1886 
1887 
1888 	status = cam_periph_alloc(ctlferegister,
1889 				  ctlfeoninvalidate,
1890 				  ctlfecleanup,
1891 				  ctlfestart,
1892 				  "ctl",
1893 				  CAM_PERIPH_BIO,
1894 				  path,
1895 				  ctlfeasync,
1896 				  0,
1897 				  lun_softc);
1898 
1899 	if ((status & CAM_STATUS_MASK) != CAM_REQ_CMP) {
1900 		const struct cam_status_entry *entry;
1901 
1902 		entry = cam_fetch_status_entry(status);
1903 
1904 		printf("%s: CAM error %s (%#x) returned from "
1905 		       "cam_periph_alloc()\n", __func__, (entry != NULL) ?
1906 		       entry->status_text : "Unknown", status);
1907 	}
1908 
1909 	xpt_free_path(path);
1910 
1911 	ctlfe_onoffline(arg, /*online*/ 1);
1912 
1913 	CAM_SIM_UNLOCK(sim);
1914 }
1915 
1916 static void
1917 ctlfe_offline(void *arg)
1918 {
1919 	struct ctlfe_softc *bus_softc;
1920 	struct cam_path *path;
1921 	cam_status status;
1922 	struct cam_periph *periph;
1923 	struct cam_sim *sim;
1924 
1925 	bus_softc = (struct ctlfe_softc *)arg;
1926 	sim = bus_softc->sim;
1927 
1928 	CAM_SIM_LOCK(sim);
1929 
1930 	ctlfe_onoffline(arg, /*online*/ 0);
1931 
1932 	/*
1933 	 * Disable the wildcard LUN for this port now that we have taken
1934 	 * the port offline.
1935 	 */
1936 	status = xpt_create_path(&path, /*periph*/ NULL,
1937 				 bus_softc->path_id, CAM_TARGET_WILDCARD,
1938 				 CAM_LUN_WILDCARD);
1939 	if (status != CAM_REQ_CMP) {
1940 		CAM_SIM_UNLOCK(sim);
1941 		printf("%s: unable to create path for wildcard periph\n",
1942 		       __func__);
1943 		return;
1944 	}
1945 
1946 
1947 	if ((periph = cam_periph_find(path, "ctl")) != NULL)
1948 		cam_periph_invalidate(periph);
1949 
1950 	xpt_free_path(path);
1951 
1952 	CAM_SIM_UNLOCK(sim);
1953 }
1954 
1955 static int
1956 ctlfe_targ_enable(void *arg, struct ctl_id targ_id)
1957 {
1958 	return (0);
1959 }
1960 
1961 static int
1962 ctlfe_targ_disable(void *arg, struct ctl_id targ_id)
1963 {
1964 	return (0);
1965 }
1966 
1967 /*
1968  * This will get called to enable a LUN on every bus that is attached to
1969  * CTL.  So we only need to create a path/periph for this particular bus.
1970  */
1971 static int
1972 ctlfe_lun_enable(void *arg, struct ctl_id targ_id, int lun_id)
1973 {
1974 	struct ctlfe_softc *bus_softc;
1975 	struct ctlfe_lun_softc *softc;
1976 	struct cam_path *path;
1977 	struct cam_periph *periph;
1978 	struct cam_sim *sim;
1979 	cam_status status;
1980 
1981 	bus_softc = (struct ctlfe_softc *)arg;
1982 	sim = bus_softc->sim;
1983 
1984 	status = xpt_create_path_unlocked(&path, /*periph*/ NULL,
1985 					  bus_softc->path_id,
1986 					  targ_id.id, lun_id);
1987 	/* XXX KDM need some way to return status to CTL here? */
1988 	if (status != CAM_REQ_CMP) {
1989 		printf("%s: could not create path, status %#x\n", __func__,
1990 		       status);
1991 		return (1);
1992 	}
1993 
1994 	softc = malloc(sizeof(*softc), M_CTLFE, M_WAITOK | M_ZERO);
1995 	CAM_SIM_LOCK(sim);
1996 	periph = cam_periph_find(path, "ctl");
1997 	if (periph != NULL) {
1998 		/* We've already got a periph, no need to alloc a new one. */
1999 		xpt_free_path(path);
2000 		free(softc, M_CTLFE);
2001 		CAM_SIM_UNLOCK(sim);
2002 		return (0);
2003 	}
2004 
2005 	softc->parent_softc = bus_softc;
2006 	STAILQ_INSERT_TAIL(&bus_softc->lun_softc_list, softc, links);
2007 
2008 	status = cam_periph_alloc(ctlferegister,
2009 				  ctlfeoninvalidate,
2010 				  ctlfecleanup,
2011 				  ctlfestart,
2012 				  "ctl",
2013 				  CAM_PERIPH_BIO,
2014 				  path,
2015 				  ctlfeasync,
2016 				  0,
2017 				  softc);
2018 
2019 	xpt_free_path(path);
2020 
2021 	CAM_SIM_UNLOCK(sim);
2022 
2023 	return (0);
2024 }
2025 
2026 /*
2027  * This will get called when the user removes a LUN to disable that LUN
2028  * on every bus that is attached to CTL.
2029  */
2030 static int
2031 ctlfe_lun_disable(void *arg, struct ctl_id targ_id, int lun_id)
2032 {
2033 	struct ctlfe_softc *softc;
2034 	struct ctlfe_lun_softc *lun_softc;
2035 	struct cam_sim *sim;
2036 
2037 	softc = (struct ctlfe_softc *)arg;
2038 	sim = softc->sim;
2039 
2040 	CAM_SIM_LOCK(sim);
2041 	STAILQ_FOREACH(lun_softc, &softc->lun_softc_list, links) {
2042 		struct cam_path *path;
2043 
2044 		path = lun_softc->periph->path;
2045 
2046 		if ((xpt_path_target_id(path) == targ_id.id)
2047 		 && (xpt_path_lun_id(path) == lun_id)) {
2048 			break;
2049 		}
2050 	}
2051 	if (lun_softc == NULL) {
2052 		CAM_SIM_UNLOCK(sim);
2053 		printf("%s: can't find target %d lun %d\n", __func__,
2054 		       targ_id.id, lun_id);
2055 		return (1);
2056 	}
2057 
2058 	cam_periph_invalidate(lun_softc->periph);
2059 
2060 	CAM_SIM_UNLOCK(sim);
2061 
2062 	return (0);
2063 }
2064 
2065 static void
2066 ctlfe_dump_sim(struct cam_sim *sim)
2067 {
2068 	int i;
2069 
2070 	printf("%s%d: max tagged openings: %d, max dev openings: %d\n",
2071 	       sim->sim_name, sim->unit_number,
2072 	       sim->max_tagged_dev_openings, sim->max_dev_openings);
2073 	printf("%s%d: max_ccbs: %u, ccb_count: %u\n",
2074 	       sim->sim_name, sim->unit_number,
2075 	       sim->max_ccbs, sim->ccb_count);
2076 	printf("%s%d: ccb_freeq is %sempty\n",
2077 	       sim->sim_name, sim->unit_number,
2078 	       (SLIST_FIRST(&sim->ccb_freeq) == NULL) ? "" : "NOT ");
2079 	printf("%s%d: alloc_queue.entries %d, alloc_openings %d\n",
2080 	       sim->sim_name, sim->unit_number,
2081 	       sim->devq->alloc_queue.entries, sim->devq->alloc_openings);
2082 	printf("%s%d: qfrozen_cnt:", sim->sim_name, sim->unit_number);
2083 	for (i = 0; i < CAM_RL_VALUES; i++) {
2084 		printf("%s%u", (i != 0) ? ":" : "",
2085 		sim->devq->alloc_queue.qfrozen_cnt[i]);
2086 	}
2087 	printf("\n");
2088 }
2089 
2090 /*
2091  * Assumes that the SIM lock is held.
2092  */
2093 static void
2094 ctlfe_dump_queue(struct ctlfe_lun_softc *softc)
2095 {
2096 	struct ccb_hdr *hdr;
2097 	struct cam_periph *periph;
2098 	int num_items;
2099 
2100 	periph = softc->periph;
2101 	num_items = 0;
2102 
2103 	TAILQ_FOREACH(hdr, &softc->work_queue, periph_links.tqe) {
2104 		union ctl_io *io;
2105 
2106 		io = hdr->io_ptr;
2107 
2108 		num_items++;
2109 
2110 		/*
2111 		 * This can happen when we get an ATIO but can't allocate
2112 		 * a ctl_io.  See the XPT_ACCEPT_TARGET_IO case in ctlfedone().
2113 		 */
2114 		if (io == NULL) {
2115 			struct ccb_scsiio *csio;
2116 
2117 			csio = (struct ccb_scsiio *)hdr;
2118 
2119 			xpt_print(periph->path, "CCB %#x ctl_io allocation "
2120 				  "failed\n", csio->tag_id);
2121 			continue;
2122 		}
2123 
2124 		/*
2125 		 * Only regular SCSI I/O is put on the work
2126 		 * queue, so we can print sense here.  There may be no
2127 		 * sense if it's no the queue for a DMA, but this serves to
2128 		 * print out the CCB as well.
2129 		 *
2130 		 * XXX KDM switch this over to scsi_sense_print() when
2131 		 * CTL is merged in with CAM.
2132 		 */
2133 		ctl_io_error_print(io, NULL);
2134 
2135 		/*
2136 		 * We're sending status back to the
2137 		 * initiator, so we're on the queue waiting
2138 		 * for a CTIO to do that.
2139 		 */
2140 		if ((io->io_hdr.status & CTL_STATUS_MASK) != CTL_STATUS_NONE)
2141 			continue;
2142 
2143 		/*
2144 		 * Otherwise, we're on the queue waiting to
2145 		 * do a data transfer.
2146 		 */
2147 		xpt_print(periph->path, "Total %u, Current %u, Resid %u\n",
2148 			  io->scsiio.kern_total_len, io->scsiio.kern_data_len,
2149 			  io->scsiio.kern_data_resid);
2150 	}
2151 
2152 	xpt_print(periph->path, "%d requests total waiting for CCBs\n",
2153 		  num_items);
2154 	xpt_print(periph->path, "%ju CCBs oustanding (%ju allocated, %ju "
2155 		  "freed)\n", (uintmax_t)(softc->ccbs_alloced -
2156 		  softc->ccbs_freed), (uintmax_t)softc->ccbs_alloced,
2157 		  (uintmax_t)softc->ccbs_freed);
2158 	xpt_print(periph->path, "%ju CTIOs outstanding (%ju sent, %ju "
2159 		  "returned\n", (uintmax_t)(softc->ctios_sent -
2160 		  softc->ctios_returned), softc->ctios_sent,
2161 		  softc->ctios_returned);
2162 }
2163 
2164 /*
2165  * This function is called when we fail to get a CCB for a DMA or status return
2166  * to the initiator within the specified time period.
2167  *
2168  * The callout code should insure that we hold the sim mutex here.
2169  */
2170 static void
2171 ctlfe_dma_timeout(void *arg)
2172 {
2173 	struct ctlfe_lun_softc *softc;
2174 	struct cam_periph *periph;
2175 	struct cam_sim *sim;
2176 	int num_queued;
2177 
2178 	softc = (struct ctlfe_lun_softc *)arg;
2179 	periph = softc->periph;
2180 	sim = xpt_path_sim(periph->path);
2181 	num_queued = 0;
2182 
2183 	/*
2184 	 * Nothing to do...
2185 	 */
2186 	if (TAILQ_FIRST(&softc->work_queue) == NULL) {
2187 		xpt_print(periph->path, "TIMEOUT triggered after %d "
2188 			  "seconds, but nothing on work queue??\n",
2189 			  CTLFE_DMA_TIMEOUT);
2190 		return;
2191 	}
2192 
2193 	xpt_print(periph->path, "TIMEOUT (%d seconds) waiting for DMA to "
2194 		  "start\n", CTLFE_DMA_TIMEOUT);
2195 
2196 	ctlfe_dump_queue(softc);
2197 
2198 	ctlfe_dump_sim(sim);
2199 
2200 	xpt_print(periph->path, "calling xpt_schedule() to attempt to "
2201 		  "unstick our queue\n");
2202 
2203 	xpt_schedule(periph, /*priority*/ 1);
2204 
2205 	xpt_print(periph->path, "xpt_schedule() call complete\n");
2206 }
2207 
2208 /*
2209  * Datamove/done routine called by CTL.  Put ourselves on the queue to
2210  * receive a CCB from CAM so we can queue the continue I/O request down
2211  * to the adapter.
2212  */
2213 static void
2214 ctlfe_datamove_done(union ctl_io *io)
2215 {
2216 	union ccb *ccb;
2217 	struct cam_sim *sim;
2218 	struct cam_periph *periph;
2219 	struct ctlfe_lun_softc *softc;
2220 
2221 	ccb = io->io_hdr.ctl_private[CTL_PRIV_FRONTEND].ptr;
2222 
2223 	sim = xpt_path_sim(ccb->ccb_h.path);
2224 
2225 	CAM_SIM_LOCK(sim);
2226 
2227 	periph = xpt_path_periph(ccb->ccb_h.path);
2228 
2229 	softc = (struct ctlfe_lun_softc *)periph->softc;
2230 
2231 	if (io->io_hdr.io_type == CTL_IO_TASK) {
2232 		/*
2233 		 * Task management commands don't require any further
2234 		 * communication back to the adapter.  Requeue the CCB
2235 		 * to the adapter, and free the CTL I/O.
2236 		 */
2237 		xpt_print(ccb->ccb_h.path, "%s: returning task I/O "
2238 			  "tag %#x seq %#x\n", __func__,
2239 			  ccb->cin1.tag_id, ccb->cin1.seq_id);
2240 		/*
2241 		 * Send the notify acknowledge down to the SIM, to let it
2242 		 * know we processed the task management command.
2243 		 */
2244 		ccb->ccb_h.status = CAM_REQ_INPROG;
2245 		ccb->ccb_h.func_code = XPT_NOTIFY_ACKNOWLEDGE;
2246 		xpt_action(ccb);
2247 		ctl_free_io(io);
2248 	} else {
2249 		if ((io->io_hdr.status & CTL_STATUS_MASK) != CTL_STATUS_NONE)
2250 			io->io_hdr.flags |= CTL_FLAG_STATUS_QUEUED;
2251 		else
2252 			io->io_hdr.flags |= CTL_FLAG_DMA_QUEUED;
2253 
2254 		TAILQ_INSERT_TAIL(&softc->work_queue, &ccb->ccb_h,
2255 				  periph_links.tqe);
2256 
2257 		/*
2258 		 * Reset the timeout for our latest active DMA.
2259 		 */
2260 		callout_reset(&softc->dma_callout,
2261 			      CTLFE_DMA_TIMEOUT * hz,
2262 			      ctlfe_dma_timeout, softc);
2263 		/*
2264 		 * Ask for the CAM transport layer to send us a CCB to do
2265 		 * the DMA or send status, unless ctlfe_dma_enabled is set
2266 		 * to 0.
2267 		 */
2268 		if (ctlfe_dma_enabled != 0)
2269 			xpt_schedule(periph, /*priority*/ 1);
2270 	}
2271 
2272 	CAM_SIM_UNLOCK(sim);
2273 }
2274 
2275 static void
2276 ctlfe_dump(void)
2277 {
2278 	struct ctlfe_softc *bus_softc;
2279 
2280 	STAILQ_FOREACH(bus_softc, &ctlfe_softc_list, links) {
2281 		struct ctlfe_lun_softc *lun_softc;
2282 
2283 		ctlfe_dump_sim(bus_softc->sim);
2284 
2285 		STAILQ_FOREACH(lun_softc, &bus_softc->lun_softc_list, links) {
2286 			ctlfe_dump_queue(lun_softc);
2287 		}
2288 	}
2289 }
2290