1 /* $MirOS: src/sys/dev/i2o/iop.c,v 1.2 2013/10/31 20:06:50 tg Exp $ */
2 /* $OpenBSD: iop.c,v 1.24 2003/09/04 03:45:53 avsm Exp $ */
3 /* $NetBSD: iop.c,v 1.12 2001/03/21 14:27:05 ad Exp $ */
4
5 /*-
6 * Copyright © 2013
7 * Thorsten “mirabilos” Glaser <tg@mirbsd.org>
8 * Copyright (c) 2000, 2001 The NetBSD Foundation, Inc.
9 * All rights reserved.
10 *
11 * This code is derived from software contributed to The NetBSD Foundation
12 * by Andrew Doran.
13 *
14 * Redistribution and use in source and binary forms, with or without
15 * modification, are permitted provided that the following conditions
16 * are met:
17 * 1. Redistributions of source code must retain the above copyright
18 * notice, this list of conditions and the following disclaimer.
19 * 2. Redistributions in binary form must reproduce the above copyright
20 * notice, this list of conditions and the following disclaimer in the
21 * documentation and/or other materials provided with the distribution.
22 * 3. All advertising materials mentioning features or use of this software
23 * must display the following acknowledgement:
24 * This product includes software developed by the NetBSD
25 * Foundation, Inc. and its contributors.
26 * 4. Neither the name of The NetBSD Foundation nor the names of its
27 * contributors may be used to endorse or promote products derived
28 * from this software without specific prior written permission.
29 *
30 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
31 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
32 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
33 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
34 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
35 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
36 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
37 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
38 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
39 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
40 * POSSIBILITY OF SUCH DAMAGE.
41 */
42
43 /*
44 * Support for I2O IOPs (intelligent I/O processors).
45 */
46
47 #include <sys/param.h>
48 #include <sys/systm.h>
49 #include <sys/kernel.h>
50 #include <sys/device.h>
51 #include <sys/queue.h>
52 #include <sys/proc.h>
53 #include <sys/malloc.h>
54 #include <sys/ioctl.h>
55 #include <sys/endian.h>
56 #include <sys/conf.h>
57 #include <sys/kthread.h>
58
59 #include <uvm/uvm_extern.h>
60
61 #include <machine/bus.h>
62
63 #include <dev/i2o/i2o.h>
64 #include <dev/i2o/iopio.h>
65 #include <dev/i2o/iopreg.h>
66 #include <dev/i2o/iopvar.h>
67
68 #define POLL(ms, cond) \
69 do { \
70 int i; \
71 for (i = (ms) * 10; i; i--) { \
72 if (cond) \
73 break; \
74 DELAY(100); \
75 } \
76 } while (/* CONSTCOND */0);
77
78 #ifdef I2ODEBUG
79 #define DPRINTF(x) printf x
80 #else
81 #define DPRINTF(x)
82 #endif
83
84 #ifdef I2OVERBOSE
85 #define IFVERBOSE(x) x
86 #define COMMENT(x) NULL
87 #else
88 #define IFVERBOSE(x)
89 #define COMMENT(x)
90 #endif
91
92 #define IOP_ICTXHASH_NBUCKETS 16
93 #define IOP_ICTXHASH(ictx) (&iop_ictxhashtbl[(ictx) & iop_ictxhash])
94
95 #define IOP_MAX_SEGS (((IOP_MAX_XFER + PAGE_SIZE - 1) / PAGE_SIZE) + 1)
96
97 #define IOP_TCTX_SHIFT 12
98 #define IOP_TCTX_MASK ((1 << IOP_TCTX_SHIFT) - 1)
99
100 LIST_HEAD(, iop_initiator) *iop_ictxhashtbl;
101 u_long iop_ictxhash;
102 void *iop_sdh;
103 struct i2o_systab *iop_systab;
104 int iop_systab_size;
105
106 struct cfdriver iop_cd = {
107 NULL, "iop", DV_DULL
108 };
109
110 #define IC_CONFIGURE 0x01
111 #define IC_PRIORITY 0x02
112
113 struct iop_class {
114 u_short ic_class;
115 u_short ic_flags;
116 #ifdef I2OVERBOSE
117 const char *ic_caption;
118 #endif
119 } static const iop_class[] = {
120 {
121 I2O_CLASS_EXECUTIVE,
122 0,
123 COMMENT("executive")
124 },
125 {
126 I2O_CLASS_DDM,
127 0,
128 COMMENT("device driver module")
129 },
130 {
131 I2O_CLASS_RANDOM_BLOCK_STORAGE,
132 IC_CONFIGURE | IC_PRIORITY,
133 IFVERBOSE("random block storage")
134 },
135 {
136 I2O_CLASS_SEQUENTIAL_STORAGE,
137 IC_CONFIGURE | IC_PRIORITY,
138 IFVERBOSE("sequential storage")
139 },
140 {
141 I2O_CLASS_LAN,
142 IC_CONFIGURE | IC_PRIORITY,
143 IFVERBOSE("LAN port")
144 },
145 {
146 I2O_CLASS_WAN,
147 IC_CONFIGURE | IC_PRIORITY,
148 IFVERBOSE("WAN port")
149 },
150 {
151 I2O_CLASS_FIBRE_CHANNEL_PORT,
152 IC_CONFIGURE,
153 IFVERBOSE("fibrechannel port")
154 },
155 {
156 I2O_CLASS_FIBRE_CHANNEL_PERIPHERAL,
157 0,
158 COMMENT("fibrechannel peripheral")
159 },
160 {
161 I2O_CLASS_SCSI_PERIPHERAL,
162 0,
163 COMMENT("SCSI peripheral")
164 },
165 {
166 I2O_CLASS_ATE_PORT,
167 IC_CONFIGURE,
168 IFVERBOSE("ATE port")
169 },
170 {
171 I2O_CLASS_ATE_PERIPHERAL,
172 0,
173 COMMENT("ATE peripheral")
174 },
175 {
176 I2O_CLASS_FLOPPY_CONTROLLER,
177 IC_CONFIGURE,
178 IFVERBOSE("floppy controller")
179 },
180 {
181 I2O_CLASS_FLOPPY_DEVICE,
182 0,
183 COMMENT("floppy device")
184 },
185 {
186 I2O_CLASS_BUS_ADAPTER_PORT,
187 IC_CONFIGURE,
188 IFVERBOSE("bus adapter port" )
189 },
190 };
191
192 #if defined(I2ODEBUG) && defined(I2OVERBOSE)
193 static const char * const iop_status[] = {
194 "success",
195 "abort (dirty)",
196 "abort (no data transfer)",
197 "abort (partial transfer)",
198 "error (dirty)",
199 "error (no data transfer)",
200 "error (partial transfer)",
201 "undefined error code",
202 "process abort (dirty)",
203 "process abort (no data transfer)",
204 "process abort (partial transfer)",
205 "transaction error",
206 };
207 #endif
208
209 static inline u_int32_t iop_inl(struct iop_softc *, int);
210 static inline void iop_outl(struct iop_softc *, int, u_int32_t);
211
212 void iop_config_interrupts(struct device *);
213 void iop_configure_devices(struct iop_softc *, int, int);
214 void iop_devinfo(int, char *, size_t);
215 int iop_print(void *, const char *);
216 int iop_reconfigure(struct iop_softc *, u_int);
217 void iop_shutdown(void *);
218 int iop_submatch(struct device *, void *, void *);
219 #ifdef notyet
220 int iop_vendor_print(void *, const char *);
221 #endif
222
223 void iop_adjqparam(struct iop_softc *, int);
224 void iop_create_reconf_thread(void *);
225 int iop_handle_reply(struct iop_softc *, u_int32_t);
226 int iop_hrt_get(struct iop_softc *);
227 int iop_hrt_get0(struct iop_softc *, struct i2o_hrt *, size_t);
228 void iop_intr_event(struct device *, struct iop_msg *, void *);
229 int iop_lct_get0(struct iop_softc *, struct i2o_lct *, size_t, u_int32_t);
230 void iop_msg_poll(struct iop_softc *, struct iop_msg *, int);
231 void iop_msg_wait(struct iop_softc *, struct iop_msg *, int);
232 int iop_ofifo_init(struct iop_softc *);
233 int iop_passthrough(struct iop_softc *, struct ioppt *);
234 int iop_post(struct iop_softc *, u_int32_t *);
235 void iop_reconf_thread(void *);
236 void iop_release_mfa(struct iop_softc *, u_int32_t);
237 int iop_reset(struct iop_softc *);
238 int iop_status_get(struct iop_softc *, int);
239 int iop_systab_set(struct iop_softc *);
240 void iop_tfn_print(struct iop_softc *, struct i2o_fault_notify *);
241
242 #ifdef I2ODEBUG
243 void iop_reply_print(struct iop_softc *, struct i2o_reply *);
244 #endif
245
246 cdev_decl(iop);
247
248 static inline u_int32_t
iop_inl(struct iop_softc * sc,int off)249 iop_inl(struct iop_softc *sc, int off)
250 {
251
252 bus_space_barrier(sc->sc_iot, sc->sc_ioh, off, 4,
253 BUS_SPACE_BARRIER_WRITE | BUS_SPACE_BARRIER_READ);
254 return (bus_space_read_4(sc->sc_iot, sc->sc_ioh, off));
255 }
256
257 static inline void
iop_outl(struct iop_softc * sc,int off,u_int32_t val)258 iop_outl(struct iop_softc *sc, int off, u_int32_t val)
259 {
260
261 bus_space_write_4(sc->sc_iot, sc->sc_ioh, off, val);
262 bus_space_barrier(sc->sc_iot, sc->sc_ioh, off, 4,
263 BUS_SPACE_BARRIER_WRITE);
264 }
265
266 /*
267 * Initialise the IOP and our interface.
268 */
269 void
iop_init(struct iop_softc * sc,const char * intrstr)270 iop_init(struct iop_softc *sc, const char *intrstr)
271 {
272 struct iop_msg *im;
273 u_int32_t mask;
274 char ident[64];
275 int rv, i, nsegs;
276 int state = 0;
277
278 if (iop_ictxhashtbl == NULL) {
279 iop_ictxhashtbl = hashinit(IOP_ICTXHASH_NBUCKETS, M_DEVBUF,
280 M_NOWAIT, &iop_ictxhash);
281 if (iop_ictxhashtbl == NULL) {
282 printf("%s: cannot allocate hashtable\n",
283 sc->sc_dv.dv_xname);
284 return;
285 }
286 }
287
288 /* Reset the IOP and request status. */
289 printf("I2O adapter");
290
291 /* Allocate a scratch DMA map for small miscellaneous shared data. */
292 if (bus_dmamap_create(sc->sc_dmat, PAGE_SIZE, 1, PAGE_SIZE, 0,
293 BUS_DMA_NOWAIT | BUS_DMA_ALLOCNOW, &sc->sc_scr_dmamap) != 0) {
294 printf("%s: cannot create scratch dmamap\n",
295 sc->sc_dv.dv_xname);
296 return;
297 }
298 state++;
299
300 if (bus_dmamem_alloc(sc->sc_dmat, PAGE_SIZE, PAGE_SIZE, 0,
301 sc->sc_scr_seg, 1, &nsegs, BUS_DMA_NOWAIT) != 0) {
302 printf("%s: cannot alloc scratch dmamem\n",
303 sc->sc_dv.dv_xname);
304 goto bail_out;
305 }
306 state++;
307
308 if (bus_dmamem_map(sc->sc_dmat, sc->sc_scr_seg, nsegs, PAGE_SIZE,
309 &sc->sc_scr, 0)) {
310 printf("%s: cannot map scratch dmamem\n", sc->sc_dv.dv_xname);
311 goto bail_out;
312 }
313 state++;
314
315 if (bus_dmamap_load(sc->sc_dmat, sc->sc_scr_dmamap, sc->sc_scr,
316 PAGE_SIZE, NULL, BUS_DMA_NOWAIT)) {
317 printf("%s: cannot load scratch dmamap\n", sc->sc_dv.dv_xname);
318 goto bail_out;
319 }
320 state++;
321
322 if ((rv = iop_reset(sc)) != 0) {
323 printf("%s: not responding (reset)\n", sc->sc_dv.dv_xname);
324 goto bail_out;
325 }
326 if ((rv = iop_status_get(sc, 1)) != 0) {
327 printf("%s: not responding (get status)\n",
328 sc->sc_dv.dv_xname);
329 goto bail_out;
330 }
331 sc->sc_flags |= IOP_HAVESTATUS;
332 iop_strvis(sc, sc->sc_status.productid,
333 sizeof(sc->sc_status.productid), ident, sizeof(ident));
334 printf(" <%s>\n", ident);
335
336 #ifdef I2ODEBUG
337 printf("%s: orgid=0x%04x version=%d\n", sc->sc_dv.dv_xname,
338 letoh16(sc->sc_status.orgid),
339 (letoh32(sc->sc_status.segnumber) >> 12) & 15);
340 printf("%s: type want have cbase\n", sc->sc_dv.dv_xname);
341 printf("%s: mem %04x %04x %08x\n", sc->sc_dv.dv_xname,
342 letoh32(sc->sc_status.desiredprivmemsize),
343 letoh32(sc->sc_status.currentprivmemsize),
344 letoh32(sc->sc_status.currentprivmembase));
345 printf("%s: i/o %04x %04x %08x\n", sc->sc_dv.dv_xname,
346 letoh32(sc->sc_status.desiredpriviosize),
347 letoh32(sc->sc_status.currentpriviosize),
348 letoh32(sc->sc_status.currentpriviobase));
349 #endif
350
351 sc->sc_maxob = letoh32(sc->sc_status.maxoutboundmframes);
352 if (sc->sc_maxob > IOP_MAX_OUTBOUND)
353 sc->sc_maxob = IOP_MAX_OUTBOUND;
354 sc->sc_maxib = letoh32(sc->sc_status.maxinboundmframes);
355 if (sc->sc_maxib > IOP_MAX_INBOUND)
356 sc->sc_maxib = IOP_MAX_INBOUND;
357
358 /* Allocate message wrappers. */
359 im = malloc(sizeof(*im) * sc->sc_maxib, M_DEVBUF, M_NOWAIT);
360 if (!im) {
361 printf("%s: couldn't allocate message", sc->sc_dv.dv_xname);
362 goto bail_out;
363 }
364 state++;
365
366 bzero(im, sizeof(*im) * sc->sc_maxib);
367 sc->sc_ims = im;
368 SLIST_INIT(&sc->sc_im_freelist);
369
370 for (i = 0; i < sc->sc_maxib; i++, im++) {
371 rv = bus_dmamap_create(sc->sc_dmat, IOP_MAX_XFER,
372 IOP_MAX_SEGS, IOP_MAX_XFER, 0,
373 BUS_DMA_NOWAIT | BUS_DMA_ALLOCNOW,
374 &im->im_xfer[0].ix_map);
375 if (rv != 0) {
376 printf("%s: couldn't create dmamap (%d)",
377 sc->sc_dv.dv_xname, rv);
378 goto bail_out;
379 }
380
381 im->im_tctx = i;
382 SLIST_INSERT_HEAD(&sc->sc_im_freelist, im, im_chain);
383 }
384
385 /* Initalise the IOP's outbound FIFO. */
386 if (iop_ofifo_init(sc) != 0) {
387 printf("%s: unable to init outbound FIFO\n",
388 sc->sc_dv.dv_xname);
389 goto bail_out;
390 }
391
392 /* Configure shutdown hook before we start any device activity. */
393 if (iop_sdh == NULL)
394 iop_sdh = shutdownhook_establish(iop_shutdown, NULL);
395
396 /* Ensure interrupts are enabled at the IOP. */
397 mask = iop_inl(sc, IOP_REG_INTR_MASK);
398 iop_outl(sc, IOP_REG_INTR_MASK, mask & ~IOP_INTR_OFIFO);
399
400 if (intrstr != NULL)
401 printf("%s: interrupting at %s\n", sc->sc_dv.dv_xname,
402 intrstr);
403
404 #ifdef I2ODEBUG
405 printf("%s: queue depths: inbound %d/%d, outbound %d/%d\n",
406 sc->sc_dv.dv_xname, sc->sc_maxib,
407 letoh32(sc->sc_status.maxinboundmframes),
408 sc->sc_maxob, letoh32(sc->sc_status.maxoutboundmframes));
409 #endif
410
411 lockinit(&sc->sc_conflock, PRIBIO, "iopconf", 0, 0);
412
413 startuphook_establish((void (*)(void *))iop_config_interrupts, sc);
414 kthread_create_deferred(iop_create_reconf_thread, sc);
415 return;
416
417 bail_out:
418 if (state > 4)
419 free(im, M_DEVBUF);
420 if (state > 3)
421 bus_dmamap_unload(sc->sc_dmat, sc->sc_scr_dmamap);
422 if (state > 2)
423 bus_dmamem_unmap(sc->sc_dmat, sc->sc_scr, PAGE_SIZE);
424 if (state > 1)
425 bus_dmamem_free(sc->sc_dmat, sc->sc_scr_seg, nsegs);
426 if (state > 0)
427 bus_dmamap_destroy(sc->sc_dmat, sc->sc_scr_dmamap);
428 }
429
430 /*
431 * Perform autoconfiguration tasks.
432 */
433 void
iop_config_interrupts(struct device * self)434 iop_config_interrupts(struct device *self)
435 {
436 struct iop_softc *sc, *iop;
437 struct i2o_systab_entry *ste;
438 int rv, i, niop;
439
440 sc = (struct iop_softc *)self;
441 LIST_INIT(&sc->sc_iilist);
442
443 printf("%s: configuring...\n", sc->sc_dv.dv_xname);
444
445 if (iop_hrt_get(sc) != 0) {
446 printf("%s: unable to retrieve HRT\n", sc->sc_dv.dv_xname);
447 return;
448 }
449
450 /*
451 * Build the system table.
452 */
453 if (iop_systab == NULL) {
454 for (i = 0, niop = 0; i < iop_cd.cd_ndevs; i++) {
455 iop = (struct iop_softc *)device_lookup(&iop_cd, i);
456 if (iop == NULL)
457 continue;
458 if ((iop->sc_flags & IOP_HAVESTATUS) == 0)
459 continue;
460 if (iop_status_get(iop, 1) != 0) {
461 printf("%s: unable to retrieve status\n",
462 sc->sc_dv.dv_xname);
463 iop->sc_flags &= ~IOP_HAVESTATUS;
464 continue;
465 }
466 niop++;
467 }
468 if (niop == 0)
469 return;
470
471 i = sizeof(struct i2o_systab_entry) * (niop - 1) +
472 sizeof(struct i2o_systab);
473 iop_systab_size = i;
474 iop_systab = malloc(i, M_DEVBUF, M_NOWAIT);
475 if (!iop_systab)
476 return;
477
478 bzero(iop_systab, i);
479 iop_systab->numentries = niop;
480 iop_systab->version = I2O_VERSION_11;
481
482 for (i = 0, ste = iop_systab->entry; i < iop_cd.cd_ndevs; i++)
483 {
484 iop = (struct iop_softc *)device_lookup(&iop_cd, i);
485 if (iop == NULL)
486 continue;
487 if ((iop->sc_flags & IOP_HAVESTATUS) == 0)
488 continue;
489
490 ste->orgid = iop->sc_status.orgid;
491 ste->iopid = iop->sc_dv.dv_unit + 2;
492 ste->segnumber =
493 htole32(letoh32(iop->sc_status.segnumber) & ~4095);
494 ste->iopcaps = iop->sc_status.iopcaps;
495 ste->inboundmsgframesize =
496 iop->sc_status.inboundmframesize;
497 ste->inboundmsgportaddresslow =
498 htole32(iop->sc_memaddr + IOP_REG_IFIFO);
499 ste++;
500 }
501 }
502
503 /*
504 * Post the system table to the IOP and bring it to the OPERATIONAL
505 * state.
506 */
507 if (iop_systab_set(sc) != 0) {
508 printf("%s: unable to set system table\n", sc->sc_dv.dv_xname);
509 return;
510 }
511 if (iop_simple_cmd(sc, I2O_TID_IOP, I2O_EXEC_SYS_ENABLE, IOP_ICTX, 1,
512 30000) != 0) {
513 printf("%s: unable to enable system\n", sc->sc_dv.dv_xname);
514 return;
515 }
516
517 /*
518 * Set up an event handler for this IOP.
519 */
520 sc->sc_eventii.ii_dv = self;
521 sc->sc_eventii.ii_intr = iop_intr_event;
522 sc->sc_eventii.ii_flags = II_DISCARD | II_UTILITY;
523 sc->sc_eventii.ii_tid = I2O_TID_IOP;
524 iop_initiator_register(sc, &sc->sc_eventii);
525
526 rv = iop_util_eventreg(sc, &sc->sc_eventii,
527 I2O_EVENT_EXEC_RESOURCE_LIMITS |
528 I2O_EVENT_EXEC_CONNECTION_FAIL |
529 I2O_EVENT_EXEC_ADAPTER_FAULT |
530 I2O_EVENT_EXEC_POWER_FAIL |
531 I2O_EVENT_EXEC_RESET_PENDING |
532 I2O_EVENT_EXEC_RESET_IMMINENT |
533 I2O_EVENT_EXEC_HARDWARE_FAIL |
534 I2O_EVENT_EXEC_XCT_CHANGE |
535 I2O_EVENT_EXEC_DDM_AVAILIBILITY |
536 I2O_EVENT_GEN_DEVICE_RESET |
537 I2O_EVENT_GEN_STATE_CHANGE |
538 I2O_EVENT_GEN_GENERAL_WARNING);
539 if (rv != 0) {
540 printf("%s: unable to register for events",
541 sc->sc_dv.dv_xname);
542 return;
543 }
544
545 #ifdef notyet
546 /* Attempt to match and attach a product-specific extension. */
547 ia.ia_class = I2O_CLASS_ANY;
548 ia.ia_tid = I2O_TID_IOP;
549 config_found_sm(self, &ia, iop_vendor_print, iop_submatch);
550 #endif
551
552 lockmgr(&sc->sc_conflock, LK_EXCLUSIVE, NULL, curproc);
553 if ((rv = iop_reconfigure(sc, 0)) == -1) {
554 printf("%s: configure failed (%d)\n", sc->sc_dv.dv_xname, rv);
555 return;
556 }
557 lockmgr(&sc->sc_conflock, LK_RELEASE, NULL, curproc);
558 }
559
560 /*
561 * Create the reconfiguration thread. Called after the standard kernel
562 * threads have been created.
563 */
564 void
iop_create_reconf_thread(void * cookie)565 iop_create_reconf_thread(void *cookie)
566 {
567 struct iop_softc *sc;
568 int rv;
569
570 sc = cookie;
571 sc->sc_flags |= IOP_ONLINE;
572
573 rv = kthread_create(iop_reconf_thread, sc, &sc->sc_reconf_proc,
574 "%s", sc->sc_dv.dv_xname);
575 if (rv != 0) {
576 printf("%s: unable to create reconfiguration thread (%d)",
577 sc->sc_dv.dv_xname, rv);
578 return;
579 }
580 }
581
582 /*
583 * Reconfiguration thread; listens for LCT change notification, and
584 * initiates re-configuration if received.
585 */
586 void
iop_reconf_thread(void * cookie)587 iop_reconf_thread(void *cookie)
588 {
589 struct iop_softc *sc = cookie;
590 struct proc *p = sc->sc_reconf_proc;
591 struct i2o_lct lct;
592 u_int32_t chgind;
593 int rv;
594
595 chgind = sc->sc_chgind + 1;
596
597 for (;;) {
598 DPRINTF(("%s: async reconfig: requested 0x%08x\n",
599 sc->sc_dv.dv_xname, chgind));
600
601 PHOLD(sc->sc_reconf_proc);
602 rv = iop_lct_get0(sc, &lct, sizeof(lct), chgind);
603 PRELE(sc->sc_reconf_proc);
604
605 DPRINTF(("%s: async reconfig: notified (0x%08x, %d)\n",
606 sc->sc_dv.dv_xname, letoh32(lct.changeindicator), rv));
607
608 if (rv == 0 &&
609 lockmgr(&sc->sc_conflock, LK_EXCLUSIVE, NULL, p) == 0) {
610 iop_reconfigure(sc, letoh32(lct.changeindicator));
611 chgind = sc->sc_chgind + 1;
612 lockmgr(&sc->sc_conflock, LK_RELEASE, NULL, p);
613 }
614
615 tsleep(iop_reconf_thread, PWAIT, "iopzzz", hz * 5);
616 }
617 }
618
619 /*
620 * Reconfigure: find new and removed devices.
621 */
622 int
iop_reconfigure(struct iop_softc * sc,u_int chgind)623 iop_reconfigure(struct iop_softc *sc, u_int chgind)
624 {
625 struct iop_msg *im;
626 struct i2o_hba_bus_scan mf;
627 struct i2o_lct_entry *le;
628 struct iop_initiator *ii, *nextii;
629 int rv, tid, i;
630
631 /*
632 * If the reconfiguration request isn't the result of LCT change
633 * notification, then be more thorough: ask all bus ports to scan
634 * their busses. Wait up to 5 minutes for each bus port to complete
635 * the request.
636 */
637 if (chgind == 0) {
638 if ((rv = iop_lct_get(sc)) != 0) {
639 DPRINTF(("iop_reconfigure: unable to read LCT\n"));
640 return (rv);
641 }
642
643 le = sc->sc_lct->entry;
644 for (i = 0; i < sc->sc_nlctent; i++, le++) {
645 if ((letoh16(le->classid) & I2O_CLASS_MASK) !=
646 I2O_CLASS_BUS_ADAPTER_PORT)
647 continue;
648 tid = letoh16(le->localtid) & I2O_CLASS_MASK;
649
650 im = iop_msg_alloc(sc, NULL, IM_WAIT);
651
652 mf.msgflags = I2O_MSGFLAGS(i2o_hba_bus_scan);
653 mf.msgfunc = I2O_MSGFUNC(tid, I2O_HBA_BUS_SCAN);
654 mf.msgictx = IOP_ICTX;
655 mf.msgtctx = im->im_tctx;
656
657 DPRINTF(("%s: scanning bus %d\n", sc->sc_dv.dv_xname,
658 tid));
659
660 rv = iop_msg_post(sc, im, &mf, 5*60*1000);
661 iop_msg_free(sc, im);
662 #ifdef I2ODEBUG
663 if (rv != 0)
664 printf("%s: bus scan failed, status =%d\n",
665 sc->sc_dv.dv_xname, rv);
666 #endif
667 }
668 } else if (chgind <= sc->sc_chgind) {
669 DPRINTF(("%s: LCT unchanged (async)\n", sc->sc_dv.dv_xname));
670 return (0);
671 }
672
673 /* Re-read the LCT and determine if it has changed. */
674 if ((rv = iop_lct_get(sc)) != 0) {
675 DPRINTF(("iop_reconfigure: unable to re-read LCT\n"));
676 return (rv);
677 }
678 DPRINTF(("%s: %d LCT entries\n", sc->sc_dv.dv_xname, sc->sc_nlctent));
679
680 chgind = letoh32(sc->sc_lct->changeindicator);
681 if (chgind == sc->sc_chgind) {
682 DPRINTF(("%s: LCT unchanged\n", sc->sc_dv.dv_xname));
683 return (0);
684 }
685 DPRINTF(("%s: LCT changed\n", sc->sc_dv.dv_xname));
686 sc->sc_chgind = chgind;
687
688 if (sc->sc_tidmap != NULL)
689 free(sc->sc_tidmap, M_DEVBUF);
690 sc->sc_tidmap = malloc(sc->sc_nlctent * sizeof(struct iop_tidmap),
691 M_DEVBUF, M_NOWAIT);
692 if (!sc->sc_tidmap) {
693 DPRINTF(("iop_reconfigure: out of memory\n"));
694 return (ENOMEM);
695 }
696 bzero(sc->sc_tidmap, sc->sc_nlctent * sizeof(struct iop_tidmap));
697
698 /* Allow 1 queued command per device while we're configuring. */
699 iop_adjqparam(sc, 1);
700
701 /*
702 * Match and attach child devices. We configure high-level devices
703 * first so that any claims will propagate throughout the LCT,
704 * hopefully masking off aliased devices as a result.
705 *
706 * Re-reading the LCT at this point is a little dangerous, but we'll
707 * trust the IOP (and the operator) to behave itself...
708 */
709 iop_configure_devices(sc, IC_CONFIGURE | IC_PRIORITY,
710 IC_CONFIGURE | IC_PRIORITY);
711 if ((rv = iop_lct_get(sc)) != 0)
712 DPRINTF(("iop_reconfigure: unable to re-read LCT\n"));
713 iop_configure_devices(sc, IC_CONFIGURE | IC_PRIORITY,
714 IC_CONFIGURE);
715
716 for (ii = LIST_FIRST(&sc->sc_iilist); ii != NULL; ii = nextii) {
717 nextii = LIST_NEXT(ii, ii_list);
718
719 /* Detach devices that were configured, but are now gone. */
720 for (i = 0; i < sc->sc_nlctent; i++)
721 if (ii->ii_tid == sc->sc_tidmap[i].it_tid)
722 break;
723 if (i == sc->sc_nlctent ||
724 (sc->sc_tidmap[i].it_flags & IT_CONFIGURED) == 0)
725 config_detach(ii->ii_dv, DETACH_FORCE);
726
727 /*
728 * Tell initiators that existed before the re-configuration
729 * to re-configure.
730 */
731 if (ii->ii_reconfig == NULL)
732 continue;
733 if ((rv = (*ii->ii_reconfig)(ii->ii_dv)) != 0)
734 printf("%s: %s failed reconfigure (%d)\n",
735 sc->sc_dv.dv_xname, ii->ii_dv->dv_xname, rv);
736 }
737
738 /* Re-adjust queue parameters and return. */
739 if (sc->sc_nii != 0)
740 iop_adjqparam(sc, (sc->sc_maxib - sc->sc_nuii - IOP_MF_RESERVE)
741 / sc->sc_nii);
742
743 return (0);
744 }
745
746 /*
747 * Configure I2O devices into the system.
748 */
749 void
iop_configure_devices(struct iop_softc * sc,int mask,int maskval)750 iop_configure_devices(struct iop_softc *sc, int mask, int maskval)
751 {
752 struct iop_attach_args ia;
753 struct iop_initiator *ii;
754 const struct i2o_lct_entry *le;
755 struct device *dv;
756 int i, j, nent;
757 u_int usertid;
758
759 nent = sc->sc_nlctent;
760 for (i = 0, le = sc->sc_lct->entry; i < nent; i++, le++) {
761 sc->sc_tidmap[i].it_tid =
762 letoh16(le->localtid) & I2O_LCT_ENTRY_TID_MASK;
763
764 /* Ignore the device if it's in use. */
765 usertid = letoh32(le->usertid) & I2O_LCT_ENTRY_TID_MASK;
766 if (usertid != I2O_TID_NONE && usertid != I2O_TID_HOST)
767 continue;
768
769 ia.ia_class = letoh16(le->classid) & I2O_CLASS_MASK;
770 ia.ia_tid = sc->sc_tidmap[i].it_tid;
771
772 /* Ignore uninteresting devices. */
773 for (j = 0; j < sizeof(iop_class) / sizeof(iop_class[0]); j++)
774 if (iop_class[j].ic_class == ia.ia_class)
775 break;
776 if (j < sizeof(iop_class) / sizeof(iop_class[0]) &&
777 (iop_class[j].ic_flags & mask) != maskval)
778 continue;
779
780 /*
781 * Try to configure the device only if it's not already
782 * configured.
783 */
784 LIST_FOREACH(ii, &sc->sc_iilist, ii_list) {
785 if (ia.ia_tid == ii->ii_tid) {
786 sc->sc_tidmap[i].it_flags |= IT_CONFIGURED;
787 strlcpy(sc->sc_tidmap[i].it_dvname,
788 ii->ii_dv->dv_xname,
789 sizeof sc->sc_tidmap[i].it_dvname);
790 break;
791 }
792 }
793 if (ii != NULL)
794 continue;
795 dv = config_found_sm(&sc->sc_dv, &ia, iop_print, iop_submatch);
796 if (dv != NULL) {
797 sc->sc_tidmap[i].it_flags |= IT_CONFIGURED;
798 strlcpy(sc->sc_tidmap[i].it_dvname, dv->dv_xname,
799 sizeof sc->sc_tidmap[i].it_dvname);
800 }
801 }
802 }
803
804 /*
805 * Adjust queue parameters for all child devices.
806 */
807 void
iop_adjqparam(struct iop_softc * sc,int mpi)808 iop_adjqparam(struct iop_softc *sc, int mpi)
809 {
810 struct iop_initiator *ii;
811
812 LIST_FOREACH(ii, &sc->sc_iilist, ii_list)
813 if (ii->ii_adjqparam != NULL)
814 (*ii->ii_adjqparam)(ii->ii_dv, mpi);
815 }
816
817 void
iop_devinfo(int class,char * devinfo,size_t di_len)818 iop_devinfo(int class, char *devinfo, size_t di_len)
819 {
820 #ifdef I2OVERBOSE
821 int i;
822
823 for (i = 0; i < sizeof(iop_class) / sizeof(iop_class[0]); i++)
824 if (class == iop_class[i].ic_class)
825 break;
826
827 if (i == sizeof(iop_class) / sizeof(iop_class[0]))
828 snprintf(devinfo, di_len, "device (class 0x%x)", class);
829 else
830 strlcpy(devinfo, iop_class[i].ic_caption, di_len);
831 #else
832
833 snprintf(devinfo, di_len, "device (class 0x%x)", class);
834 #endif
835 }
836
837 int
iop_print(void * aux,const char * pnp)838 iop_print(void *aux, const char *pnp)
839 {
840 struct iop_attach_args *ia;
841 char devinfo[256];
842
843 ia = aux;
844
845 if (pnp != NULL) {
846 iop_devinfo(ia->ia_class, devinfo, sizeof devinfo);
847 printf("%s at %s", devinfo, pnp);
848 }
849 printf(" tid %d", ia->ia_tid);
850 return (UNCONF);
851 }
852
853 #ifdef notyet
854 int
iop_vendor_print(void * aux,const char * pnp)855 iop_vendor_print(void *aux, const char *pnp)
856 {
857
858 if (pnp != NULL)
859 printf("vendor specific extension at %s", pnp);
860 return (UNCONF);
861 }
862 #endif
863
864 int
iop_submatch(struct device * parent,void * vcf,void * aux)865 iop_submatch(struct device *parent, void *vcf, void *aux)
866 {
867 struct cfdata *cf = vcf;
868 struct iop_attach_args *ia;
869
870 ia = aux;
871
872 if (cf->iopcf_tid != IOPCF_TID_DEFAULT && cf->iopcf_tid != ia->ia_tid)
873 return (0);
874
875 return ((*cf->cf_attach->ca_match)(parent, cf, aux));
876 }
877
878 /*
879 * Shut down all configured IOPs.
880 */
881 void
iop_shutdown(void * junk)882 iop_shutdown(void *junk)
883 {
884 struct iop_softc *sc;
885 int i;
886
887 printf("shutting down iop devices...");
888
889 for (i = 0; i < iop_cd.cd_ndevs; i++) {
890 if (!(sc = (struct iop_softc *)device_lookup(&iop_cd, i)))
891 continue;
892 if ((sc->sc_flags & IOP_ONLINE) == 0)
893 continue;
894 iop_simple_cmd(sc, I2O_TID_IOP, I2O_EXEC_SYS_QUIESCE, IOP_ICTX,
895 0, 5000);
896 iop_simple_cmd(sc, I2O_TID_IOP, I2O_EXEC_IOP_CLEAR, IOP_ICTX,
897 0, 1000);
898 }
899
900 /* Wait. Some boards could still be flushing, stupidly enough. */
901 delay(5000*1000);
902 printf(" done.\n");
903 }
904
905 /*
906 * Retrieve IOP status.
907 */
908 int
iop_status_get(struct iop_softc * sc,int nosleep)909 iop_status_get(struct iop_softc *sc, int nosleep)
910 {
911 struct i2o_exec_status_get mf;
912 paddr_t pa = sc->sc_scr_seg->ds_addr;
913 struct i2o_status *st = (struct i2o_status *)sc->sc_scr;
914 int rv;
915
916 mf.msgflags = I2O_MSGFLAGS(i2o_exec_status_get);
917 mf.msgfunc = I2O_MSGFUNC(I2O_TID_IOP, I2O_EXEC_STATUS_GET);
918 mf.reserved[0] = 0;
919 mf.reserved[1] = 0;
920 mf.reserved[2] = 0;
921 mf.reserved[3] = 0;
922 mf.addrlow = pa & ~(u_int32_t)0;
923 mf.addrhigh = sizeof pa > sizeof mf.addrlow ? pa >> 32 : 0;
924 mf.length = sizeof(*st);
925
926 bzero(st, sizeof(*st));
927 bus_dmamap_sync(sc->sc_dmat, sc->sc_scr_dmamap, 0, sizeof(*st),
928 BUS_DMASYNC_PREREAD);
929
930 if ((rv = iop_post(sc, (u_int32_t *)&mf)))
931 return (rv);
932
933 /* XXX */
934 POLL(2500,
935 (bus_dmamap_sync(sc->sc_dmat, sc->sc_scr_dmamap, 0,
936 sizeof(*st), BUS_DMASYNC_POSTREAD), st->syncbyte == 0xff));
937
938 if (st->syncbyte != 0xff)
939 return (EIO);
940
941 bcopy(st, &sc->sc_status, sizeof(sc->sc_status));
942 return (0);
943 }
944
945 /*
946 * Initalize and populate the IOP's outbound FIFO.
947 */
948 int
iop_ofifo_init(struct iop_softc * sc)949 iop_ofifo_init(struct iop_softc *sc)
950 {
951 bus_addr_t addr;
952 bus_dma_segment_t seg;
953 struct i2o_exec_outbound_init *mf;
954 u_int32_t mb[IOP_MAX_MSG_SIZE / sizeof(u_int32_t)];
955 u_int32_t *sw = (u_int32_t *)sc->sc_scr;
956 int i, rseg, rv;
957
958 mf = (struct i2o_exec_outbound_init *)mb;
959 mf->msgflags = I2O_MSGFLAGS(i2o_exec_outbound_init);
960 mf->msgfunc = I2O_MSGFUNC(I2O_TID_IOP, I2O_EXEC_OUTBOUND_INIT);
961 mf->msgictx = IOP_ICTX;
962 mf->msgtctx = 0;
963 mf->pagesize = PAGE_SIZE;
964 mf->flags = IOP_INIT_CODE | ((IOP_MAX_MSG_SIZE >> 2) << 16);
965 mb[sizeof(*mf) / sizeof(u_int32_t) + 0] = sizeof(*sw) |
966 I2O_SGL_SIMPLE | I2O_SGL_END_BUFFER | I2O_SGL_END;
967 mb[sizeof(*mf) / sizeof(u_int32_t) + 1] = sc->sc_scr_seg->ds_addr;
968 mb[0] += 2 << 16;
969
970 *sw = 0;
971 bus_dmamap_sync(sc->sc_dmat, sc->sc_scr_dmamap, 0, sizeof(*sw),
972 BUS_DMASYNC_PREREAD);
973
974 /*
975 * The I2O spec says that there are two SGLs: one for the status
976 * word, and one for a list of discarded MFAs. It continues to say
977 * that if you don't want to get the list of MFAs, an IGNORE SGL is
978 * necessary; this isn't the case (and is in fact a bad thing).
979 */
980 if ((rv = iop_post(sc, mb)))
981 return (rv);
982
983 /* XXX */
984 POLL(5000,
985 (bus_dmamap_sync(sc->sc_dmat, sc->sc_scr_dmamap, 0, sizeof(*sw),
986 BUS_DMASYNC_POSTREAD),
987 *sw == htole32(I2O_EXEC_OUTBOUND_INIT_COMPLETE)));
988 if (*sw != htole32(I2O_EXEC_OUTBOUND_INIT_COMPLETE)) {
989 printf("%s: outbound FIFO init failed (%d)\n",
990 sc->sc_dv.dv_xname, letoh32(*sw));
991 return (EIO);
992 }
993
994 /* Allocate DMA safe memory for the reply frames. */
995 if (sc->sc_rep_phys == 0) {
996 sc->sc_rep_size = sc->sc_maxob * IOP_MAX_MSG_SIZE;
997
998 rv = bus_dmamem_alloc(sc->sc_dmat, sc->sc_rep_size, PAGE_SIZE,
999 0, &seg, 1, &rseg, BUS_DMA_NOWAIT);
1000 if (rv != 0) {
1001 printf("%s: dma alloc = %d\n", sc->sc_dv.dv_xname,
1002 rv);
1003 return (rv);
1004 }
1005
1006 rv = bus_dmamem_map(sc->sc_dmat, &seg, rseg, sc->sc_rep_size,
1007 &sc->sc_rep, BUS_DMA_NOWAIT | BUS_DMA_COHERENT);
1008 if (rv != 0) {
1009 printf("%s: dma map = %d\n", sc->sc_dv.dv_xname, rv);
1010 return (rv);
1011 }
1012
1013 rv = bus_dmamap_create(sc->sc_dmat, sc->sc_rep_size, 1,
1014 sc->sc_rep_size, 0, BUS_DMA_NOWAIT, &sc->sc_rep_dmamap);
1015 if (rv != 0) {
1016 printf("%s: dma create = %d\n", sc->sc_dv.dv_xname,
1017 rv);
1018 return (rv);
1019 }
1020
1021 rv = bus_dmamap_load(sc->sc_dmat, sc->sc_rep_dmamap,
1022 sc->sc_rep, sc->sc_rep_size, NULL, BUS_DMA_NOWAIT);
1023 if (rv != 0) {
1024 printf("%s: dma load = %d\n", sc->sc_dv.dv_xname, rv);
1025 return (rv);
1026 }
1027
1028 sc->sc_rep_phys = sc->sc_rep_dmamap->dm_segs[0].ds_addr;
1029 }
1030
1031 /* Populate the outbound FIFO. */
1032 for (i = sc->sc_maxob, addr = sc->sc_rep_phys; i != 0; i--) {
1033 iop_outl(sc, IOP_REG_OFIFO, (u_int32_t)addr);
1034 addr += IOP_MAX_MSG_SIZE;
1035 }
1036
1037 return (0);
1038 }
1039
1040 /*
1041 * Read the specified number of bytes from the IOP's hardware resource table.
1042 */
1043 int
iop_hrt_get0(struct iop_softc * sc,struct i2o_hrt * hrt,size_t size)1044 iop_hrt_get0(struct iop_softc *sc, struct i2o_hrt *hrt, size_t size)
1045 {
1046 struct iop_msg *im;
1047 struct i2o_exec_hrt_get *mf;
1048 u_int32_t mb[IOP_MAX_MSG_SIZE / sizeof(u_int32_t)];
1049 int rv;
1050
1051 im = iop_msg_alloc(sc, NULL, IM_WAIT);
1052 mf = (struct i2o_exec_hrt_get *)mb;
1053 mf->msgflags = I2O_MSGFLAGS(i2o_exec_hrt_get);
1054 mf->msgfunc = I2O_MSGFUNC(I2O_TID_IOP, I2O_EXEC_HRT_GET);
1055 mf->msgictx = IOP_ICTX;
1056 mf->msgtctx = im->im_tctx;
1057
1058 iop_msg_map(sc, im, mb, hrt, size, 0);
1059 rv = iop_msg_post(sc, im, mb, 30000);
1060 iop_msg_unmap(sc, im);
1061 iop_msg_free(sc, im);
1062 return (rv);
1063 }
1064
1065 /*
1066 * Read the IOP's hardware resource table.
1067 */
1068 int
iop_hrt_get(struct iop_softc * sc)1069 iop_hrt_get(struct iop_softc *sc)
1070 {
1071 struct i2o_hrt hrthdr, *hrt;
1072 size_t size;
1073 int rv;
1074
1075 PHOLD(curproc);
1076 rv = iop_hrt_get0(sc, &hrthdr, sizeof(hrthdr));
1077 PRELE(curproc);
1078 if (rv != 0)
1079 return (rv);
1080
1081 DPRINTF(("%s: %d hrt entries\n", sc->sc_dv.dv_xname,
1082 letoh16(hrthdr.numentries)));
1083
1084 size = sizeof(struct i2o_hrt) +
1085 (letoh16(hrthdr.numentries) - 1) * sizeof(struct i2o_hrt_entry);
1086 hrt = (struct i2o_hrt *)malloc(size, M_DEVBUF, M_NOWAIT);
1087 if (!hrt)
1088 return (ENOMEM);
1089
1090 if ((rv = iop_hrt_get0(sc, hrt, size)) != 0) {
1091 free(hrt, M_DEVBUF);
1092 return (rv);
1093 }
1094
1095 if (sc->sc_hrt != NULL)
1096 free(sc->sc_hrt, M_DEVBUF);
1097 sc->sc_hrt = hrt;
1098 return (0);
1099 }
1100
1101 /*
1102 * Request the specified number of bytes from the IOP's logical
1103 * configuration table. If a change indicator is specified, this
1104 * is a verbatim notification request, so the caller is prepared
1105 * to wait indefinitely.
1106 */
1107 int
iop_lct_get0(struct iop_softc * sc,struct i2o_lct * lct,size_t size,u_int32_t chgind)1108 iop_lct_get0(struct iop_softc *sc, struct i2o_lct *lct, size_t size,
1109 u_int32_t chgind)
1110 {
1111 struct iop_msg *im;
1112 struct i2o_exec_lct_notify *mf;
1113 int rv;
1114 u_int32_t mb[IOP_MAX_MSG_SIZE / sizeof(u_int32_t)];
1115
1116 im = iop_msg_alloc(sc, NULL, IM_WAIT);
1117 memset(lct, 0, size);
1118
1119 mf = (struct i2o_exec_lct_notify *)mb;
1120 mf->msgflags = I2O_MSGFLAGS(i2o_exec_lct_notify);
1121 mf->msgfunc = I2O_MSGFUNC(I2O_TID_IOP, I2O_EXEC_LCT_NOTIFY);
1122 mf->msgictx = IOP_ICTX;
1123 mf->msgtctx = im->im_tctx;
1124 mf->classid = I2O_CLASS_ANY;
1125 mf->changeindicator = chgind;
1126
1127 #ifdef I2ODEBUG
1128 printf("iop_lct_get0: reading LCT");
1129 if (chgind != 0)
1130 printf(" (async)");
1131 printf("\n");
1132 #endif
1133
1134 iop_msg_map(sc, im, mb, lct, size, 0);
1135 rv = iop_msg_post(sc, im, mb, (chgind == 0 ? 120*1000 : 0));
1136 iop_msg_unmap(sc, im);
1137 iop_msg_free(sc, im);
1138 return (rv);
1139 }
1140
1141 /*
1142 * Read the IOP's logical configuration table.
1143 */
1144 int
iop_lct_get(struct iop_softc * sc)1145 iop_lct_get(struct iop_softc *sc)
1146 {
1147 size_t esize, size;
1148 int rv;
1149 struct i2o_lct *lct;
1150
1151 esize = letoh32(sc->sc_status.expectedlctsize);
1152 lct = (struct i2o_lct *)malloc(esize, M_DEVBUF, M_WAITOK);
1153 if (lct == NULL)
1154 return (ENOMEM);
1155
1156 if ((rv = iop_lct_get0(sc, lct, esize, 0)) != 0) {
1157 free(lct, M_DEVBUF);
1158 return (rv);
1159 }
1160
1161 size = letoh16(lct->tablesize) << 2;
1162 if (esize != size) {
1163 free(lct, M_DEVBUF);
1164 lct = (struct i2o_lct *)malloc(size, M_DEVBUF, M_WAITOK);
1165 if (lct == NULL)
1166 return (ENOMEM);
1167
1168 if ((rv = iop_lct_get0(sc, lct, size, 0)) != 0) {
1169 free(lct, M_DEVBUF);
1170 return (rv);
1171 }
1172 }
1173
1174 /* Swap in the new LCT. */
1175 if (sc->sc_lct != NULL)
1176 free(sc->sc_lct, M_DEVBUF);
1177 sc->sc_lct = lct;
1178 sc->sc_nlctent = ((letoh16(sc->sc_lct->tablesize) << 2) -
1179 sizeof(struct i2o_lct) + sizeof(struct i2o_lct_entry)) /
1180 sizeof(struct i2o_lct_entry);
1181 return (0);
1182 }
1183
1184 /*
1185 * Request the specified parameter group from the target. If an initiator
1186 * is specified (a) don't wait for the operation to complete, but instead
1187 * let the initiator's interrupt handler deal with the reply and (b) place a
1188 * pointer to the parameter group op in the wrapper's `im_dvcontext' field.
1189 */
1190 int
iop_param_op(struct iop_softc * sc,int tid,struct iop_initiator * ii,int write,int group,void * buf,size_t size)1191 iop_param_op(struct iop_softc *sc, int tid, struct iop_initiator *ii,
1192 int write, int group, void *buf, size_t size)
1193 {
1194 struct iop_msg *im;
1195 struct i2o_util_params_op *mf;
1196 struct i2o_reply *rf;
1197 int rv, func, op;
1198 struct iop_pgop *pgop;
1199 u_int32_t mb[IOP_MAX_MSG_SIZE / sizeof(u_int32_t)];
1200
1201 im = iop_msg_alloc(sc, ii, (ii == NULL ? IM_WAIT : 0) | IM_NOSTATUS);
1202 if ((pgop = malloc(sizeof(*pgop), M_DEVBUF, M_WAITOK)) == NULL) {
1203 iop_msg_free(sc, im);
1204 return (ENOMEM);
1205 }
1206 if ((rf = malloc(sizeof(*rf), M_DEVBUF, M_WAITOK)) == NULL) {
1207 iop_msg_free(sc, im);
1208 free(pgop, M_DEVBUF);
1209 return (ENOMEM);
1210 }
1211 im->im_dvcontext = pgop;
1212 im->im_rb = rf;
1213
1214 if (write) {
1215 func = I2O_UTIL_PARAMS_SET;
1216 op = I2O_PARAMS_OP_FIELD_SET;
1217 } else {
1218 func = I2O_UTIL_PARAMS_GET;
1219 op = I2O_PARAMS_OP_FIELD_GET;
1220 }
1221
1222 mf = (struct i2o_util_params_op *)mb;
1223 mf->msgflags = I2O_MSGFLAGS(i2o_util_params_op);
1224 mf->msgfunc = I2O_MSGFUNC(tid, func);
1225 mf->msgictx = IOP_ICTX;
1226 mf->msgtctx = im->im_tctx;
1227 mf->flags = 0;
1228
1229 pgop->olh.count = htole16(1);
1230 pgop->olh.reserved = htole16(0);
1231 pgop->oat.operation = htole16(op);
1232 pgop->oat.fieldcount = htole16(0xffff);
1233 pgop->oat.group = htole16(group);
1234
1235 if (ii == NULL)
1236 PHOLD(curproc);
1237
1238 memset(buf, 0, size);
1239 iop_msg_map(sc, im, mb, pgop, sizeof(*pgop), 1);
1240 iop_msg_map(sc, im, mb, buf, size, write);
1241 rv = iop_msg_post(sc, im, mb, (ii == NULL ? 30000 : 0));
1242
1243 if (ii == NULL)
1244 PRELE(curproc);
1245
1246 /* Detect errors; let partial transfers to count as success. */
1247 if (ii == NULL && rv == 0) {
1248 if (rf->reqstatus == I2O_STATUS_ERROR_PARTIAL_XFER &&
1249 rf->detail == htole16(I2O_DSC_UNKNOWN_ERROR))
1250 rv = 0;
1251 else
1252 rv = (rf->reqstatus != 0 ? EIO : 0);
1253 }
1254
1255 if (ii == NULL || rv != 0) {
1256 iop_msg_unmap(sc, im);
1257 iop_msg_free(sc, im);
1258 free(pgop, M_DEVBUF);
1259 free(rf, M_DEVBUF);
1260 }
1261
1262 return (rv);
1263 }
1264
1265 /*
1266 * Execute a simple command (no parameters).
1267 */
1268 int
iop_simple_cmd(struct iop_softc * sc,int tid,int function,int ictx,int async,int timo)1269 iop_simple_cmd(struct iop_softc *sc, int tid, int function, int ictx,
1270 int async, int timo)
1271 {
1272 struct iop_msg *im;
1273 struct i2o_msg mf;
1274 int rv, fl;
1275
1276 fl = (async != 0 ? IM_WAIT : IM_POLL);
1277 im = iop_msg_alloc(sc, NULL, fl);
1278
1279 mf.msgflags = I2O_MSGFLAGS(i2o_msg);
1280 mf.msgfunc = I2O_MSGFUNC(tid, function);
1281 mf.msgictx = ictx;
1282 mf.msgtctx = im->im_tctx;
1283
1284 rv = iop_msg_post(sc, im, &mf, timo);
1285 iop_msg_free(sc, im);
1286 return (rv);
1287 }
1288
1289 /*
1290 * Post the system table to the IOP.
1291 */
1292 int
iop_systab_set(struct iop_softc * sc)1293 iop_systab_set(struct iop_softc *sc)
1294 {
1295 struct i2o_exec_sys_tab_set *mf;
1296 struct iop_msg *im;
1297 bus_space_handle_t bsh;
1298 bus_addr_t boo;
1299 u_int32_t mema[2], ioa[2];
1300 int rv;
1301 u_int32_t mb[IOP_MAX_MSG_SIZE / sizeof(u_int32_t)];
1302
1303 im = iop_msg_alloc(sc, NULL, IM_WAIT);
1304
1305 mf = (struct i2o_exec_sys_tab_set *)mb;
1306 mf->msgflags = I2O_MSGFLAGS(i2o_exec_sys_tab_set);
1307 mf->msgfunc = I2O_MSGFUNC(I2O_TID_IOP, I2O_EXEC_SYS_TAB_SET);
1308 mf->msgictx = IOP_ICTX;
1309 mf->msgtctx = im->im_tctx;
1310 mf->iopid = (sc->sc_dv.dv_unit + 2) << 12;
1311 mf->segnumber = 0;
1312
1313 mema[1] = sc->sc_status.desiredprivmemsize;
1314 ioa[1] = sc->sc_status.desiredpriviosize;
1315
1316 if (mema[1] != 0) {
1317 /*
1318 * XXX This will waste virtual memory. We need a flag to tell
1319 * bus_space_alloc to just reserve, not actually map the area.
1320 */
1321 rv = bus_space_alloc(sc->sc_bus_memt, 0, 0xffffffff,
1322 letoh32(mema[1]), PAGE_SIZE, 0, 0, &boo, &bsh);
1323 mema[0] = htole32(boo);
1324 if (rv != 0) {
1325 printf("%s: can't alloc priv mem space, err = %d\n",
1326 sc->sc_dv.dv_xname, rv);
1327 mema[0] = 0;
1328 mema[1] = 0;
1329 }
1330 }
1331
1332 if (ioa[1] != 0) {
1333 /*
1334 * XXX This will potentially waste virtual memory. We
1335 * need a flag to tell bus_space_alloc to just
1336 * reserve, not actually map the area.
1337 */
1338 rv = bus_space_alloc(sc->sc_bus_iot, 0, 0xffff,
1339 letoh32(ioa[1]), 0, 0, 0, &boo, &bsh);
1340 ioa[0] = htole32(boo);
1341 if (rv != 0) {
1342 printf("%s: can't alloc priv i/o space, err = %d\n",
1343 sc->sc_dv.dv_xname, rv);
1344 ioa[0] = 0;
1345 ioa[1] = 0;
1346 }
1347 }
1348
1349 PHOLD(curproc);
1350 iop_msg_map(sc, im, mb, iop_systab, iop_systab_size, 1);
1351 iop_msg_map(sc, im, mb, mema, sizeof(mema), 1);
1352 iop_msg_map(sc, im, mb, ioa, sizeof(ioa), 1);
1353 rv = iop_msg_post(sc, im, mb, 5000);
1354 iop_msg_unmap(sc, im);
1355 iop_msg_free(sc, im);
1356 PRELE(curproc);
1357 return (rv);
1358 }
1359
1360 /*
1361 * Reset the IOP. Must be called with interrupts disabled.
1362 */
1363 int
iop_reset(struct iop_softc * sc)1364 iop_reset(struct iop_softc *sc)
1365 {
1366 struct i2o_exec_iop_reset mf;
1367 paddr_t pa = sc->sc_scr_seg->ds_addr;
1368 u_int32_t *sw = (u_int32_t *)sc->sc_scr;
1369 u_int32_t mfa;
1370 int rv = 0;
1371
1372 mf.msgflags = I2O_MSGFLAGS(i2o_exec_iop_reset);
1373 mf.msgfunc = I2O_MSGFUNC(I2O_TID_IOP, I2O_EXEC_IOP_RESET);
1374 mf.reserved[0] = 0;
1375 mf.reserved[1] = 0;
1376 mf.reserved[2] = 0;
1377 mf.reserved[3] = 0;
1378 mf.statuslow = pa & ~(u_int32_t)0;
1379 mf.statushigh = sizeof pa > sizeof mf.statuslow ? pa >> 32 : 0;
1380
1381 *sw = htole32(0);
1382 bus_dmamap_sync(sc->sc_dmat, sc->sc_scr_dmamap, 0, sizeof(*sw),
1383 BUS_DMASYNC_PREREAD);
1384
1385 if ((rv = iop_post(sc, (u_int32_t *)&mf)))
1386 return (rv);
1387
1388 /* XXX */
1389 POLL(2500,
1390 (bus_dmamap_sync(sc->sc_dmat, sc->sc_scr_dmamap, 0, sizeof(*sw),
1391 BUS_DMASYNC_POSTREAD), *sw != htole32(0)));
1392 if (*sw != htole32(I2O_RESET_IN_PROGRESS)) {
1393 printf("%s: reset rejected, status 0x%x\n",
1394 sc->sc_dv.dv_xname, letoh32(*sw));
1395 return (EIO);
1396 }
1397
1398 /*
1399 * IOP is now in the INIT state. Wait no more than 10 seconds for
1400 * the inbound queue to become responsive.
1401 */
1402 POLL(10000, (mfa = iop_inl(sc, IOP_REG_IFIFO)) != IOP_MFA_EMPTY);
1403 if (mfa == IOP_MFA_EMPTY) {
1404 printf("%s: reset failed\n", sc->sc_dv.dv_xname);
1405 return (EIO);
1406 }
1407
1408 iop_release_mfa(sc, mfa);
1409
1410 return (0);
1411 }
1412
1413 /*
1414 * Register a new initiator. Must be called with the configuration lock
1415 * held.
1416 */
1417 void
iop_initiator_register(struct iop_softc * sc,struct iop_initiator * ii)1418 iop_initiator_register(struct iop_softc *sc, struct iop_initiator *ii)
1419 {
1420 static int ictxgen;
1421 int s;
1422
1423 /* 0 is reserved (by us) for system messages. */
1424 ii->ii_ictx = ++ictxgen;
1425
1426 /*
1427 * `Utility initiators' don't make it onto the per-IOP initiator list
1428 * (which is used only for configuration), but do get one slot on
1429 * the inbound queue.
1430 */
1431 if ((ii->ii_flags & II_UTILITY) == 0) {
1432 LIST_INSERT_HEAD(&sc->sc_iilist, ii, ii_list);
1433 sc->sc_nii++;
1434 } else
1435 sc->sc_nuii++;
1436
1437 s = splbio();
1438 LIST_INSERT_HEAD(IOP_ICTXHASH(ii->ii_ictx), ii, ii_hash);
1439 splx(s);
1440 }
1441
1442 /*
1443 * Unregister an initiator. Must be called with the configuration lock
1444 * held.
1445 */
1446 void
iop_initiator_unregister(struct iop_softc * sc,struct iop_initiator * ii)1447 iop_initiator_unregister(struct iop_softc *sc, struct iop_initiator *ii)
1448 {
1449 int s;
1450
1451 if ((ii->ii_flags & II_UTILITY) == 0) {
1452 LIST_REMOVE(ii, ii_list);
1453 sc->sc_nii--;
1454 } else
1455 sc->sc_nuii--;
1456
1457 s = splbio();
1458 LIST_REMOVE(ii, ii_hash);
1459 splx(s);
1460 }
1461
1462 /*
1463 * Handle a reply frame from the IOP.
1464 */
1465 int
iop_handle_reply(struct iop_softc * sc,u_int32_t rmfa)1466 iop_handle_reply(struct iop_softc *sc, u_int32_t rmfa)
1467 {
1468 struct iop_msg *im;
1469 struct i2o_reply *rb;
1470 struct i2o_fault_notify *fn;
1471 struct iop_initiator *ii;
1472 u_int off, ictx, tctx, status, size;
1473
1474 off = (int)(rmfa - sc->sc_rep_phys);
1475 rb = (struct i2o_reply *)(sc->sc_rep + off);
1476
1477 /* Perform reply queue DMA synchronisation. XXX This is rubbish. */
1478 bus_dmamap_sync(sc->sc_dmat, sc->sc_rep_dmamap, off,
1479 sc->sc_rep_dmamap->dm_mapsize, BUS_DMASYNC_POSTREAD);
1480 if (--sc->sc_curib != 0)
1481 bus_dmamap_sync(sc->sc_dmat, sc->sc_rep_dmamap, 0,
1482 sc->sc_rep_size, BUS_DMASYNC_PREREAD);
1483
1484 #ifdef I2ODEBUG
1485 if ((letoh32(rb->msgflags) & I2O_MSGFLAGS_64BIT) != 0)
1486 panic("iop_handle_reply: 64-bit reply");
1487 #endif
1488 /*
1489 * Find the initiator.
1490 */
1491 ictx = letoh32(rb->msgictx);
1492 if (ictx == IOP_ICTX)
1493 ii = NULL;
1494 else {
1495 ii = LIST_FIRST(IOP_ICTXHASH(ictx));
1496 for (; ii != NULL; ii = LIST_NEXT(ii, ii_hash))
1497 if (ii->ii_ictx == ictx)
1498 break;
1499 if (ii == NULL) {
1500 #ifdef I2ODEBUG
1501 iop_reply_print(sc, rb);
1502 #endif
1503 printf("%s: WARNING: bad ictx returned (%x)\n",
1504 sc->sc_dv.dv_xname, ictx);
1505 return (-1);
1506 }
1507 }
1508
1509 /*
1510 * If we received a transport failure notice, we've got to dig the
1511 * transaction context (if any) out of the original message frame,
1512 * and then release the original MFA back to the inbound FIFO.
1513 */
1514 if ((rb->msgflags & I2O_MSGFLAGS_FAIL) != 0) {
1515 status = I2O_STATUS_SUCCESS;
1516
1517 fn = (struct i2o_fault_notify *)rb;
1518 tctx = iop_inl(sc, fn->lowmfa + 12); /* XXX */
1519 iop_release_mfa(sc, fn->lowmfa);
1520 iop_tfn_print(sc, fn);
1521 } else {
1522 status = rb->reqstatus;
1523 tctx = letoh32(rb->msgtctx);
1524 }
1525
1526 if (ii == NULL || (ii->ii_flags & II_DISCARD) == 0) {
1527 /*
1528 * This initiator tracks state using message wrappers.
1529 *
1530 * Find the originating message wrapper, and if requested
1531 * notify the initiator.
1532 */
1533 im = sc->sc_ims + (tctx & IOP_TCTX_MASK);
1534 if ((tctx & IOP_TCTX_MASK) > sc->sc_maxib ||
1535 (im->im_flags & IM_ALLOCED) == 0 ||
1536 tctx != im->im_tctx) {
1537 printf("%s: WARNING: bad tctx returned (0x%08x, %p)\n",
1538 sc->sc_dv.dv_xname, tctx, im);
1539 if (im != NULL)
1540 printf("%s: flags=0x%08x tctx=0x%08x\n",
1541 sc->sc_dv.dv_xname, im->im_flags,
1542 im->im_tctx);
1543 #ifdef I2ODEBUG
1544 if ((rb->msgflags & I2O_MSGFLAGS_FAIL) == 0)
1545 iop_reply_print(sc, rb);
1546 #endif
1547 return (-1);
1548 }
1549
1550 if ((rb->msgflags & I2O_MSGFLAGS_FAIL) != 0)
1551 im->im_flags |= IM_FAIL;
1552
1553 #ifdef I2ODEBUG
1554 if ((im->im_flags & IM_REPLIED) != 0)
1555 panic("%s: dup reply", sc->sc_dv.dv_xname);
1556 #endif
1557 im->im_flags |= IM_REPLIED;
1558
1559 #ifdef I2ODEBUG
1560 if (status != I2O_STATUS_SUCCESS)
1561 iop_reply_print(sc, rb);
1562 #endif
1563 im->im_reqstatus = status;
1564
1565 /* Copy the reply frame, if requested. */
1566 if (im->im_rb != NULL) {
1567 size = (letoh32(rb->msgflags) >> 14) & ~3;
1568 #ifdef I2ODEBUG
1569 if (size > IOP_MAX_MSG_SIZE)
1570 panic("iop_handle_reply: reply too large");
1571 #endif
1572 memcpy(im->im_rb, rb, size);
1573 }
1574
1575 /* Notify the initiator. */
1576 if ((im->im_flags & IM_WAIT) != 0)
1577 wakeup(im);
1578 else if ((im->im_flags & (IM_POLL | IM_POLL_INTR)) != IM_POLL)
1579 (*ii->ii_intr)(ii->ii_dv, im, rb);
1580 } else {
1581 /*
1582 * This initiator discards message wrappers.
1583 *
1584 * Simply pass the reply frame to the initiator.
1585 */
1586 (*ii->ii_intr)(ii->ii_dv, NULL, rb);
1587 }
1588
1589 return (status);
1590 }
1591
1592 /*
1593 * Handle an interrupt from the IOP.
1594 */
1595 int
iop_intr(void * arg)1596 iop_intr(void *arg)
1597 {
1598 struct iop_softc *sc;
1599 u_int32_t rmfa;
1600
1601 sc = arg;
1602
1603 if ((iop_inl(sc, IOP_REG_INTR_STATUS) & IOP_INTR_OFIFO) == 0)
1604 return (0);
1605
1606 for (;;) {
1607 /* Double read to account for IOP bug. */
1608 if ((rmfa = iop_inl(sc, IOP_REG_OFIFO)) == IOP_MFA_EMPTY) {
1609 rmfa = iop_inl(sc, IOP_REG_OFIFO);
1610 if (rmfa == IOP_MFA_EMPTY)
1611 break;
1612 }
1613 iop_handle_reply(sc, rmfa);
1614 iop_outl(sc, IOP_REG_OFIFO, rmfa);
1615 }
1616
1617 return (1);
1618 }
1619
1620 /*
1621 * Handle an event signalled by the executive.
1622 */
1623 void
iop_intr_event(struct device * dv,struct iop_msg * im,void * reply)1624 iop_intr_event(struct device *dv, struct iop_msg *im, void *reply)
1625 {
1626 struct i2o_util_event_register_reply *rb;
1627 struct iop_softc *sc;
1628 u_int event;
1629
1630 sc = (struct iop_softc *)dv;
1631 rb = reply;
1632
1633 if ((rb->msgflags & I2O_MSGFLAGS_FAIL) != 0)
1634 return;
1635
1636 event = letoh32(rb->event);
1637 printf("%s: event 0x%08x received\n", dv->dv_xname, event);
1638 }
1639
1640 /*
1641 * Allocate a message wrapper.
1642 */
1643 struct iop_msg *
iop_msg_alloc(struct iop_softc * sc,struct iop_initiator * ii,int flags)1644 iop_msg_alloc(struct iop_softc *sc, struct iop_initiator *ii, int flags)
1645 {
1646 struct iop_msg *im;
1647 static u_int tctxgen;
1648 int s, i;
1649
1650 #ifdef I2ODEBUG
1651 if ((flags & IM_SYSMASK) != 0)
1652 panic("iop_msg_alloc: system flags specified");
1653 #endif
1654
1655 s = splbio(); /* XXX */
1656 im = SLIST_FIRST(&sc->sc_im_freelist);
1657 #if defined(DIAGNOSTIC) || defined(I2ODEBUG)
1658 if (im == NULL)
1659 panic("iop_msg_alloc: no free wrappers");
1660 #endif
1661 SLIST_REMOVE_HEAD(&sc->sc_im_freelist, im_chain);
1662 splx(s);
1663
1664 if (ii != NULL && (ii->ii_flags & II_DISCARD) != 0)
1665 flags |= IM_DISCARD;
1666
1667 im->im_tctx = (im->im_tctx & IOP_TCTX_MASK) | tctxgen;
1668 tctxgen += (1 << IOP_TCTX_SHIFT);
1669 im->im_flags = flags | IM_ALLOCED;
1670 im->im_rb = NULL;
1671 i = 0;
1672 do {
1673 im->im_xfer[i++].ix_size = 0;
1674 } while (i < IOP_MAX_MSG_XFERS);
1675
1676 return (im);
1677 }
1678
1679 /*
1680 * Free a message wrapper.
1681 */
1682 void
iop_msg_free(struct iop_softc * sc,struct iop_msg * im)1683 iop_msg_free(struct iop_softc *sc, struct iop_msg *im)
1684 {
1685 int s;
1686
1687 #ifdef I2ODEBUG
1688 if ((im->im_flags & IM_ALLOCED) == 0)
1689 panic("iop_msg_free: wrapper not allocated");
1690 #endif
1691
1692 im->im_flags = 0;
1693 s = splbio();
1694 SLIST_INSERT_HEAD(&sc->sc_im_freelist, im, im_chain);
1695 splx(s);
1696 }
1697
1698 /*
1699 * Map a data transfer. Write a scatter-gather list into the message frame.
1700 */
1701 int
iop_msg_map(struct iop_softc * sc,struct iop_msg * im,u_int32_t * mb,void * xferaddr,size_t xfersize,int out)1702 iop_msg_map(struct iop_softc *sc, struct iop_msg *im, u_int32_t *mb,
1703 void *xferaddr, size_t xfersize, int out)
1704 {
1705 bus_dmamap_t dm;
1706 bus_dma_segment_t *ds;
1707 struct iop_xfer *ix;
1708 u_int rv, i, nsegs, flg, off, xn;
1709 u_int32_t *p;
1710
1711 for (xn = 0, ix = im->im_xfer; xn < IOP_MAX_MSG_XFERS; xn++, ix++)
1712 if (ix->ix_size == 0)
1713 break;
1714
1715 #ifdef I2ODEBUG
1716 if (xfersize == 0)
1717 panic("iop_msg_map: null transfer");
1718 if (xfersize > IOP_MAX_XFER)
1719 panic("iop_msg_map: transfer too large");
1720 if (xn == IOP_MAX_MSG_XFERS)
1721 panic("iop_msg_map: too many xfers");
1722 #endif
1723
1724 /*
1725 * Only the first DMA map is static.
1726 */
1727 if (xn != 0) {
1728 rv = bus_dmamap_create(sc->sc_dmat, IOP_MAX_XFER,
1729 IOP_MAX_SEGS, IOP_MAX_XFER, 0,
1730 BUS_DMA_NOWAIT | BUS_DMA_ALLOCNOW, &ix->ix_map);
1731 if (rv != 0)
1732 return (rv);
1733 }
1734
1735 dm = ix->ix_map;
1736 rv = bus_dmamap_load(sc->sc_dmat, dm, xferaddr, xfersize, NULL, 0);
1737 if (rv != 0)
1738 goto bad;
1739
1740 /*
1741 * How many SIMPLE SG elements can we fit in this message?
1742 */
1743 off = mb[0] >> 16;
1744 p = mb + off;
1745 nsegs = ((IOP_MAX_MSG_SIZE / sizeof *mb) - off) >> 1;
1746
1747 if (dm->dm_nsegs > nsegs) {
1748 bus_dmamap_unload(sc->sc_dmat, ix->ix_map);
1749 rv = EFBIG;
1750 DPRINTF(("iop_msg_map: too many segs\n"));
1751 goto bad;
1752 }
1753
1754 nsegs = dm->dm_nsegs;
1755 xfersize = 0;
1756
1757 /*
1758 * Write out the SG list.
1759 */
1760 if (out)
1761 flg = I2O_SGL_SIMPLE | I2O_SGL_DATA_OUT;
1762 else
1763 flg = I2O_SGL_SIMPLE;
1764
1765 for (i = nsegs, ds = dm->dm_segs; i > 1; i--, p += 2, ds++) {
1766 p[0] = (u_int32_t)ds->ds_len | flg;
1767 p[1] = (u_int32_t)ds->ds_addr;
1768 xfersize += ds->ds_len;
1769 }
1770
1771 p[0] = (u_int32_t)ds->ds_len | flg | I2O_SGL_END_BUFFER;
1772 p[1] = (u_int32_t)ds->ds_addr;
1773 xfersize += ds->ds_len;
1774
1775 /* Fix up the transfer record, and sync the map. */
1776 ix->ix_flags = (out ? IX_OUT : IX_IN);
1777 ix->ix_size = xfersize;
1778 bus_dmamap_sync(sc->sc_dmat, ix->ix_map, 0, xfersize,
1779 out ? BUS_DMASYNC_POSTWRITE : BUS_DMASYNC_POSTREAD);
1780
1781 /*
1782 * If this is the first xfer we've mapped for this message, adjust
1783 * the SGL offset field in the message header.
1784 */
1785 if ((im->im_flags & IM_SGLOFFADJ) == 0) {
1786 mb[0] += (mb[0] >> 12) & 0xf0;
1787 im->im_flags |= IM_SGLOFFADJ;
1788 }
1789 mb[0] += (nsegs << 17);
1790 return (0);
1791
1792 bad:
1793 if (xn != 0)
1794 bus_dmamap_destroy(sc->sc_dmat, ix->ix_map);
1795 return (rv);
1796 }
1797
1798 /*
1799 * Map a block I/O data transfer (different in that there's only one per
1800 * message maximum, and PAGE addressing may be used). Write a scatter
1801 * gather list into the message frame.
1802 */
1803 int
iop_msg_map_bio(struct iop_softc * sc,struct iop_msg * im,u_int32_t * mb,void * xferaddr,int xfersize,int out)1804 iop_msg_map_bio(struct iop_softc *sc, struct iop_msg *im, u_int32_t *mb,
1805 void *xferaddr, int xfersize, int out)
1806 {
1807 bus_dma_segment_t *ds;
1808 bus_dmamap_t dm;
1809 struct iop_xfer *ix;
1810 u_int rv, i, nsegs, off, slen, tlen, flg;
1811 paddr_t saddr, eaddr;
1812 u_int32_t *p;
1813
1814 #ifdef I2ODEBUG
1815 if (xfersize == 0)
1816 panic("iop_msg_map_bio: null transfer");
1817 if (xfersize > IOP_MAX_XFER)
1818 panic("iop_msg_map_bio: transfer too large");
1819 if ((im->im_flags & IM_SGLOFFADJ) != 0)
1820 panic("iop_msg_map_bio: SGLOFFADJ");
1821 #endif
1822
1823 ix = im->im_xfer;
1824 dm = ix->ix_map;
1825 rv = bus_dmamap_load(sc->sc_dmat, dm, xferaddr, xfersize, NULL, 0);
1826 if (rv != 0)
1827 return (rv);
1828
1829 off = mb[0] >> 16;
1830 nsegs = ((IOP_MAX_MSG_SIZE / 4) - off) >> 1;
1831
1832 /*
1833 * If the transfer is highly fragmented and won't fit using SIMPLE
1834 * elements, use PAGE_LIST elements instead. SIMPLE elements are
1835 * potentially more efficient, both for us and the IOP.
1836 */
1837 if (dm->dm_nsegs > nsegs) {
1838 nsegs = 1;
1839 p = mb + off + 1;
1840
1841 /* XXX This should be done with a bus_space flag. */
1842 for (i = dm->dm_nsegs, ds = dm->dm_segs; i > 0; i--, ds++) {
1843 slen = ds->ds_len;
1844 saddr = ds->ds_addr;
1845
1846 while (slen > 0) {
1847 eaddr = (saddr + PAGE_SIZE) & ~(PAGE_SIZE - 1);
1848 tlen = min(eaddr - saddr, slen);
1849 slen -= tlen;
1850 *p++ = letoh32(saddr);
1851 saddr = eaddr;
1852 nsegs++;
1853 }
1854 }
1855
1856 mb[off] = xfersize | I2O_SGL_PAGE_LIST | I2O_SGL_END_BUFFER |
1857 I2O_SGL_END;
1858 if (out)
1859 mb[off] |= I2O_SGL_DATA_OUT;
1860 } else {
1861 p = mb + off;
1862 nsegs = dm->dm_nsegs;
1863
1864 if (out)
1865 flg = I2O_SGL_SIMPLE | I2O_SGL_DATA_OUT;
1866 else
1867 flg = I2O_SGL_SIMPLE;
1868
1869 for (i = nsegs, ds = dm->dm_segs; i > 1; i--, p += 2, ds++) {
1870 p[0] = (u_int32_t)ds->ds_len | flg;
1871 p[1] = (u_int32_t)ds->ds_addr;
1872 }
1873
1874 p[0] = (u_int32_t)ds->ds_len | flg | I2O_SGL_END_BUFFER |
1875 I2O_SGL_END;
1876 p[1] = (u_int32_t)ds->ds_addr;
1877 nsegs <<= 1;
1878 }
1879
1880 /* Fix up the transfer record, and sync the map. */
1881 ix->ix_flags = (out ? IX_OUT : IX_IN);
1882 ix->ix_size = xfersize;
1883 bus_dmamap_sync(sc->sc_dmat, ix->ix_map, 0,
1884 ix->ix_map->dm_mapsize,
1885 out ? BUS_DMASYNC_POSTWRITE : BUS_DMASYNC_POSTREAD);
1886
1887 /*
1888 * Adjust the SGL offset and total message size fields. We don't
1889 * set IM_SGLOFFADJ, since it's used only for SIMPLE elements.
1890 */
1891 mb[0] += ((off << 4) + (nsegs << 16));
1892 return (0);
1893 }
1894
1895 /*
1896 * Unmap all data transfers associated with a message wrapper.
1897 */
1898 void
iop_msg_unmap(struct iop_softc * sc,struct iop_msg * im)1899 iop_msg_unmap(struct iop_softc *sc, struct iop_msg *im)
1900 {
1901 struct iop_xfer *ix;
1902 int i;
1903
1904 #ifdef I2ODEBUG
1905 if (im->im_xfer[0].ix_size == 0)
1906 panic("iop_msg_unmap: no transfers mapped");
1907 #endif
1908
1909 for (ix = im->im_xfer, i = 0;;) {
1910 bus_dmamap_sync(sc->sc_dmat, ix->ix_map, 0, ix->ix_size,
1911 ix->ix_flags & IX_OUT ? BUS_DMASYNC_POSTWRITE :
1912 BUS_DMASYNC_POSTREAD);
1913 bus_dmamap_unload(sc->sc_dmat, ix->ix_map);
1914
1915 /* Only the first DMA map is static. */
1916 if (i != 0)
1917 bus_dmamap_destroy(sc->sc_dmat, ix->ix_map);
1918 if ((++ix)->ix_size == 0)
1919 break;
1920 if (++i >= IOP_MAX_MSG_XFERS)
1921 break;
1922 }
1923 }
1924
1925 /*
1926 * Post a message frame to the IOP's inbound queue.
1927 */
1928 int
iop_post(struct iop_softc * sc,u_int32_t * mb)1929 iop_post(struct iop_softc *sc, u_int32_t *mb)
1930 {
1931 u_int32_t mfa;
1932 int s;
1933 size_t size = mb[0] >> 14 & ~3;
1934
1935 /* ZZZ */
1936 if (size > IOP_MAX_MSG_SIZE)
1937 panic("iop_post: frame too large");
1938
1939 #ifdef I2ODEBUG
1940 {
1941 int i;
1942
1943 printf("\niop_post\n");
1944 for (i = 0; i < size / sizeof *mb; i++)
1945 printf("%4d %08x\n", i, mb[i]);
1946 }
1947 #endif
1948
1949 s = splbio(); /* XXX */
1950
1951 /* Allocate a slot with the IOP. */
1952 if ((mfa = iop_inl(sc, IOP_REG_IFIFO)) == IOP_MFA_EMPTY)
1953 if ((mfa = iop_inl(sc, IOP_REG_IFIFO)) == IOP_MFA_EMPTY) {
1954 splx(s);
1955 printf("%s: mfa not forthcoming\n",
1956 sc->sc_dv.dv_xname);
1957 return (EAGAIN);
1958 }
1959
1960 #ifdef I2ODEBUG
1961 printf("mfa = %u\n", mfa);
1962 #endif
1963
1964 /* Perform reply buffer DMA synchronisation. XXX This is rubbish. */
1965 if (sc->sc_curib++ == 0)
1966 bus_dmamap_sync(sc->sc_dmat, sc->sc_rep_dmamap, 0,
1967 sc->sc_rep_size, BUS_DMASYNC_PREREAD);
1968
1969 /* Copy out the message frame. */
1970 bus_space_write_region_4(sc->sc_iot, sc->sc_ioh, mfa, mb,
1971 size / sizeof *mb);
1972 bus_space_barrier(sc->sc_iot, sc->sc_ioh, mfa, size,
1973 BUS_SPACE_BARRIER_WRITE);
1974
1975 /* Post the MFA back to the IOP. */
1976 iop_outl(sc, IOP_REG_IFIFO, mfa);
1977
1978 splx(s);
1979 return (0);
1980 }
1981
1982 /*
1983 * Post a message to the IOP and deal with completion.
1984 */
1985 int
iop_msg_post(struct iop_softc * sc,struct iop_msg * im,void * xmb,int timo)1986 iop_msg_post(struct iop_softc *sc, struct iop_msg *im, void *xmb, int timo)
1987 {
1988 u_int32_t *mb = xmb;
1989 int rv, s;
1990 size_t size = mb[0] >> 14 & 3;
1991
1992 /* Terminate the scatter/gather list chain. */
1993 if ((im->im_flags & IM_SGLOFFADJ) != 0)
1994 mb[size - 2] |= I2O_SGL_END;
1995
1996 if ((rv = iop_post(sc, mb)) != 0)
1997 return (rv);
1998
1999 if ((im->im_flags & IM_DISCARD) != 0)
2000 iop_msg_free(sc, im);
2001 else if ((im->im_flags & IM_POLL) != 0 && timo == 0) {
2002 /* XXX For ofifo_init(). */
2003 rv = 0;
2004 } else if ((im->im_flags & (IM_POLL | IM_WAIT)) != 0) {
2005 if ((im->im_flags & IM_POLL) != 0)
2006 iop_msg_poll(sc, im, timo);
2007 else
2008 iop_msg_wait(sc, im, timo);
2009
2010 s = splbio();
2011 if ((im->im_flags & IM_REPLIED) != 0) {
2012 if ((im->im_flags & IM_NOSTATUS) != 0)
2013 rv = 0;
2014 else if ((im->im_flags & IM_FAIL) != 0)
2015 rv = ENXIO;
2016 else if (im->im_reqstatus != I2O_STATUS_SUCCESS)
2017 rv = EIO;
2018 else
2019 rv = 0;
2020 } else
2021 rv = EBUSY;
2022 splx(s);
2023 } else
2024 rv = 0;
2025
2026 return (rv);
2027 }
2028
2029 /*
2030 * Spin until the specified message is replied to.
2031 */
2032 void
iop_msg_poll(struct iop_softc * sc,struct iop_msg * im,int timo)2033 iop_msg_poll(struct iop_softc *sc, struct iop_msg *im, int timo)
2034 {
2035 u_int32_t rmfa;
2036 int s, status;
2037
2038 s = splbio(); /* XXX */
2039
2040 /* Wait for completion. */
2041 for (timo *= 10; timo != 0; timo--) {
2042 if ((iop_inl(sc, IOP_REG_INTR_STATUS) & IOP_INTR_OFIFO) != 0) {
2043 /* Double read to account for IOP bug. */
2044 rmfa = iop_inl(sc, IOP_REG_OFIFO);
2045 if (rmfa == IOP_MFA_EMPTY)
2046 rmfa = iop_inl(sc, IOP_REG_OFIFO);
2047 if (rmfa != IOP_MFA_EMPTY) {
2048 status = iop_handle_reply(sc, rmfa);
2049
2050 /*
2051 * Return the reply frame to the IOP's
2052 * outbound FIFO.
2053 */
2054 iop_outl(sc, IOP_REG_OFIFO, rmfa);
2055 }
2056 }
2057 if ((im->im_flags & IM_REPLIED) != 0)
2058 break;
2059 DELAY(100);
2060 }
2061
2062 if (timo == 0) {
2063 #ifdef I2ODEBUG
2064 printf("%s: poll - no reply\n", sc->sc_dv.dv_xname);
2065 if (iop_status_get(sc, 1) != 0)
2066 printf("iop_msg_poll: unable to retrieve status\n");
2067 else
2068 printf("iop_msg_poll: IOP state = %d\n",
2069 (letoh32(sc->sc_status.segnumber) >> 16) & 0xff);
2070 #endif
2071 }
2072
2073 splx(s);
2074 }
2075
2076 /*
2077 * Sleep until the specified message is replied to.
2078 */
2079 void
iop_msg_wait(struct iop_softc * sc,struct iop_msg * im,int timo)2080 iop_msg_wait(struct iop_softc *sc, struct iop_msg *im, int timo)
2081 {
2082 int s, rv;
2083
2084 s = splbio();
2085 if ((im->im_flags & IM_REPLIED) != 0) {
2086 splx(s);
2087 return;
2088 }
2089 rv = tsleep(im, PRIBIO, "iopmsg", timo * hz / 1000);
2090 splx(s);
2091
2092 #ifdef I2ODEBUG
2093 if (rv != 0) {
2094 printf("iop_msg_wait: tsleep() == %d\n", rv);
2095 if (iop_status_get(sc, 0) != 0)
2096 printf("iop_msg_wait: unable to retrieve status\n");
2097 else
2098 printf("iop_msg_wait: IOP state = %d\n",
2099 (letoh32(sc->sc_status.segnumber) >> 16) & 0xff);
2100 }
2101 #endif
2102 }
2103
2104 /*
2105 * Release an unused message frame back to the IOP's inbound fifo.
2106 */
2107 void
iop_release_mfa(struct iop_softc * sc,u_int32_t mfa)2108 iop_release_mfa(struct iop_softc *sc, u_int32_t mfa)
2109 {
2110
2111 /* Use the frame to issue a no-op. */
2112 iop_outl(sc, mfa, I2O_VERSION_11 | (4 << 16));
2113 iop_outl(sc, mfa + 4, I2O_MSGFUNC(I2O_TID_IOP, I2O_UTIL_NOP));
2114 iop_outl(sc, mfa + 8, 0);
2115 iop_outl(sc, mfa + 12, 0);
2116
2117 iop_outl(sc, IOP_REG_IFIFO, mfa);
2118 }
2119
2120 #ifdef I2ODEBUG
2121 /*
2122 * Dump a reply frame header.
2123 */
2124 void
iop_reply_print(struct iop_softc * sc,struct i2o_reply * rb)2125 iop_reply_print(struct iop_softc *sc, struct i2o_reply *rb)
2126 {
2127 u_int function, detail;
2128 #ifdef I2OVERBOSE
2129 const char *statusstr;
2130 #endif
2131
2132 function = (letoh32(rb->msgfunc) >> 24) & 0xff;
2133 detail = letoh16(rb->detail);
2134
2135 printf("%s: reply:\n", sc->sc_dv.dv_xname);
2136
2137 #ifdef I2OVERBOSE
2138 if (rb->reqstatus < sizeof(iop_status) / sizeof(iop_status[0]))
2139 statusstr = iop_status[rb->reqstatus];
2140 else
2141 statusstr = "undefined error code";
2142
2143 printf("%s: function=0x%02x status=0x%02x (%s)\n",
2144 sc->sc_dv.dv_xname, function, rb->reqstatus, statusstr);
2145 #else
2146 printf("%s: function=0x%02x status=0x%02x\n",
2147 sc->sc_dv.dv_xname, function, rb->reqstatus);
2148 #endif
2149 printf("%s: detail=0x%04x ictx=0x%08x tctx=0x%08x\n",
2150 sc->sc_dv.dv_xname, detail, letoh32(rb->msgictx),
2151 letoh32(rb->msgtctx));
2152 printf("%s: tidi=%d tidt=%d flags=0x%02x\n", sc->sc_dv.dv_xname,
2153 (letoh32(rb->msgfunc) >> 12) & 4095, letoh32(rb->msgfunc) & 4095,
2154 (letoh32(rb->msgflags) >> 8) & 0xff);
2155 }
2156 #endif
2157
2158 /*
2159 * Dump a transport failure reply.
2160 */
2161 void
iop_tfn_print(struct iop_softc * sc,struct i2o_fault_notify * fn)2162 iop_tfn_print(struct iop_softc *sc, struct i2o_fault_notify *fn)
2163 {
2164
2165 printf("%s: WARNING: transport failure:\n", sc->sc_dv.dv_xname);
2166
2167 printf("%s: ictx=0x%08x tctx=0x%08x\n", sc->sc_dv.dv_xname,
2168 letoh32(fn->msgictx), letoh32(fn->msgtctx));
2169 printf("%s: failurecode=0x%02x severity=0x%02x\n",
2170 sc->sc_dv.dv_xname, fn->failurecode, fn->severity);
2171 printf("%s: highestver=0x%02x lowestver=0x%02x\n",
2172 sc->sc_dv.dv_xname, fn->highestver, fn->lowestver);
2173 }
2174
2175 /*
2176 * Translate an I2O ASCII field into a C string.
2177 */
2178 void
iop_strvis(struct iop_softc * sc,const char * src,int slen,char * dst,int dlen)2179 iop_strvis(struct iop_softc *sc, const char *src, int slen, char *dst, int dlen)
2180 {
2181 int hc, lc, i, nit;
2182
2183 dlen--;
2184 lc = 0;
2185 hc = 0;
2186 i = 0;
2187
2188 /*
2189 * DPT use NUL as a space, whereas AMI use it as a terminator. The
2190 * spec has nothing to say about it. Since AMI fields are usually
2191 * filled with junk after the terminator, ...
2192 */
2193 nit = (letoh16(sc->sc_status.orgid) != I2O_ORG_DPT);
2194
2195 while (slen-- != 0 && dlen-- != 0) {
2196 if (nit && *src == '\0')
2197 break;
2198 else if (*src <= 0x20 || *src >= 0x7f) {
2199 if (hc)
2200 dst[i++] = ' ';
2201 } else {
2202 hc = 1;
2203 dst[i++] = *src;
2204 lc = i;
2205 }
2206 src++;
2207 }
2208
2209 dst[lc] = '\0';
2210 }
2211
2212 /*
2213 * Retrieve the DEVICE_IDENTITY parameter group from the target and dump it.
2214 */
2215 int
iop_print_ident(struct iop_softc * sc,int tid)2216 iop_print_ident(struct iop_softc *sc, int tid)
2217 {
2218 struct {
2219 struct i2o_param_op_results pr;
2220 struct i2o_param_read_results prr;
2221 struct i2o_param_device_identity di;
2222 } __attribute__((__packed__)) p;
2223 char buf[32];
2224 int rv;
2225
2226 rv = iop_param_op(sc, tid, NULL, 0, I2O_PARAM_DEVICE_IDENTITY, &p,
2227 sizeof(p));
2228 if (rv != 0)
2229 return (rv);
2230
2231 iop_strvis(sc, p.di.vendorinfo, sizeof(p.di.vendorinfo), buf,
2232 sizeof(buf));
2233 printf(" <%s, ", buf);
2234 iop_strvis(sc, p.di.productinfo, sizeof(p.di.productinfo), buf,
2235 sizeof(buf));
2236 printf("%s, ", buf);
2237 iop_strvis(sc, p.di.revlevel, sizeof(p.di.revlevel), buf, sizeof(buf));
2238 printf("%s>", buf);
2239
2240 return (0);
2241 }
2242
2243 /*
2244 * Claim or unclaim the specified TID.
2245 */
2246 int
iop_util_claim(struct iop_softc * sc,struct iop_initiator * ii,int release,int flags)2247 iop_util_claim(struct iop_softc *sc, struct iop_initiator *ii, int release,
2248 int flags)
2249 {
2250 struct iop_msg *im;
2251 struct i2o_util_claim mf;
2252 int rv, func;
2253
2254 func = release ? I2O_UTIL_CLAIM_RELEASE : I2O_UTIL_CLAIM;
2255 im = iop_msg_alloc(sc, ii, IM_WAIT);
2256
2257 /* We can use the same structure, as they're identical. */
2258 mf.msgflags = I2O_MSGFLAGS(i2o_util_claim);
2259 mf.msgfunc = I2O_MSGFUNC(ii->ii_tid, func);
2260 mf.msgictx = ii->ii_ictx;
2261 mf.msgtctx = im->im_tctx;
2262 mf.flags = flags;
2263
2264 rv = iop_msg_post(sc, im, &mf, 5000);
2265 iop_msg_free(sc, im);
2266 return (rv);
2267 }
2268
2269 /*
2270 * Perform an abort.
2271 */
iop_util_abort(struct iop_softc * sc,struct iop_initiator * ii,int func,int tctxabort,int flags)2272 int iop_util_abort(struct iop_softc *sc, struct iop_initiator *ii, int func,
2273 int tctxabort, int flags)
2274 {
2275 struct iop_msg *im;
2276 struct i2o_util_abort mf;
2277 int rv;
2278
2279 im = iop_msg_alloc(sc, ii, IM_WAIT);
2280
2281 mf.msgflags = I2O_MSGFLAGS(i2o_util_abort);
2282 mf.msgfunc = I2O_MSGFUNC(ii->ii_tid, I2O_UTIL_ABORT);
2283 mf.msgictx = ii->ii_ictx;
2284 mf.msgtctx = im->im_tctx;
2285 mf.flags = (func << 24) | flags;
2286 mf.tctxabort = tctxabort;
2287
2288 rv = iop_msg_post(sc, im, &mf, 5000);
2289 iop_msg_free(sc, im);
2290 return (rv);
2291 }
2292
2293 /*
2294 * Enable or disable reception of events for the specified device.
2295 */
iop_util_eventreg(struct iop_softc * sc,struct iop_initiator * ii,int mask)2296 int iop_util_eventreg(struct iop_softc *sc, struct iop_initiator *ii, int mask)
2297 {
2298 struct iop_msg *im;
2299 struct i2o_util_event_register mf;
2300
2301 im = iop_msg_alloc(sc, ii, 0);
2302
2303 mf.msgflags = I2O_MSGFLAGS(i2o_util_event_register);
2304 mf.msgfunc = I2O_MSGFUNC(ii->ii_tid, I2O_UTIL_EVENT_REGISTER);
2305 mf.msgictx = ii->ii_ictx;
2306 mf.msgtctx = im->im_tctx;
2307 mf.eventmask = mask;
2308
2309 /* This message is replied to only when events are signalled. */
2310 return (iop_msg_post(sc, im, &mf, 0));
2311 }
2312
2313 int
iopopen(dev_t dev,int flag,int mode,struct proc * p)2314 iopopen(dev_t dev, int flag, int mode, struct proc *p)
2315 {
2316 struct iop_softc *sc;
2317
2318 if (!(sc = (struct iop_softc *)device_lookup(&iop_cd, minor(dev))))
2319 return (ENXIO);
2320 if ((sc->sc_flags & IOP_ONLINE) == 0)
2321 return (ENXIO);
2322 if ((sc->sc_flags & IOP_OPEN) != 0)
2323 return (EBUSY);
2324 sc->sc_flags |= IOP_OPEN;
2325
2326 sc->sc_ptb = malloc(IOP_MAX_XFER * IOP_MAX_MSG_XFERS, M_DEVBUF,
2327 M_WAITOK);
2328 if (sc->sc_ptb == NULL) {
2329 sc->sc_flags ^= IOP_OPEN;
2330 return (ENOMEM);
2331 }
2332
2333 return (0);
2334 }
2335
2336 int
iopclose(dev_t dev,int flag,int mode,struct proc * p)2337 iopclose(dev_t dev, int flag, int mode, struct proc *p)
2338 {
2339 struct iop_softc *sc;
2340
2341 sc = (struct iop_softc *)device_lookup(&iop_cd, minor(dev)); /* XXX */
2342 free(sc->sc_ptb, M_DEVBUF);
2343 sc->sc_flags &= ~IOP_OPEN;
2344 return (0);
2345 }
2346
2347 int
iopioctl(dev_t dev,u_long cmd,caddr_t data,int flag,struct proc * p)2348 iopioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
2349 {
2350 struct iop_softc *sc;
2351 struct iovec *iov;
2352 int rv, i;
2353
2354 if (securelevel >= 2)
2355 return (EPERM);
2356
2357 sc = (struct iop_softc *)device_lookup(&iop_cd, minor(dev)); /* XXX */
2358
2359 switch (cmd) {
2360 case IOPIOCPT:
2361 return (iop_passthrough(sc, (struct ioppt *)data));
2362
2363 case IOPIOCGSTATUS:
2364 iov = (struct iovec *)data;
2365 i = sizeof(struct i2o_status);
2366 if (i > iov->iov_len)
2367 i = iov->iov_len;
2368 else
2369 iov->iov_len = i;
2370 if ((rv = iop_status_get(sc, 0)) == 0)
2371 rv = copyout(&sc->sc_status, iov->iov_base, i);
2372 return (rv);
2373
2374 case IOPIOCGLCT:
2375 case IOPIOCGTIDMAP:
2376 case IOPIOCRECONFIG:
2377 break;
2378
2379 default:
2380 #if defined(DIAGNOSTIC) || defined(I2ODEBUG)
2381 printf("%s: unknown ioctl %lx\n", sc->sc_dv.dv_xname, cmd);
2382 #endif
2383 return (ENOTTY);
2384 }
2385
2386 if ((rv = lockmgr(&sc->sc_conflock, LK_SHARED, NULL, p)) != 0)
2387 return (rv);
2388
2389 switch (cmd) {
2390 case IOPIOCGLCT:
2391 iov = (struct iovec *)data;
2392 i = letoh16(sc->sc_lct->tablesize) << 2;
2393 if (i > iov->iov_len)
2394 i = iov->iov_len;
2395 else
2396 iov->iov_len = i;
2397 rv = copyout(sc->sc_lct, iov->iov_base, i);
2398 break;
2399
2400 case IOPIOCRECONFIG:
2401 rv = iop_reconfigure(sc, 0);
2402 break;
2403
2404 case IOPIOCGTIDMAP:
2405 iov = (struct iovec *)data;
2406 i = sizeof(struct iop_tidmap) * sc->sc_nlctent;
2407 if (i > iov->iov_len)
2408 i = iov->iov_len;
2409 else
2410 iov->iov_len = i;
2411 rv = copyout(sc->sc_tidmap, iov->iov_base, i);
2412 break;
2413 }
2414
2415 lockmgr(&sc->sc_conflock, LK_RELEASE, NULL, p);
2416 return (rv);
2417 }
2418
2419 int
iop_passthrough(struct iop_softc * sc,struct ioppt * pt)2420 iop_passthrough(struct iop_softc *sc, struct ioppt *pt)
2421 {
2422 struct iop_msg *im;
2423 struct i2o_msg *mf;
2424 struct ioppt_buf *ptb;
2425 int rv, i, mapped;
2426 void *buf;
2427
2428 mf = NULL;
2429 im = NULL;
2430 mapped = 1;
2431
2432 if (pt->pt_msglen > IOP_MAX_MSG_SIZE ||
2433 pt->pt_msglen > (letoh16(sc->sc_status.inboundmframesize) << 2) ||
2434 pt->pt_msglen < sizeof(struct i2o_msg) ||
2435 pt->pt_nbufs > IOP_MAX_MSG_XFERS ||
2436 pt->pt_nbufs < 0 || pt->pt_replylen < 0 ||
2437 pt->pt_timo < 1000 || pt->pt_timo > 5*60*1000)
2438 return (EINVAL);
2439
2440 for (i = 0; i < pt->pt_nbufs; i++)
2441 if (pt->pt_bufs[i].ptb_datalen > IOP_MAX_XFER) {
2442 rv = ENOMEM;
2443 goto bad;
2444 }
2445
2446 mf = malloc(IOP_MAX_MSG_SIZE, M_DEVBUF, M_WAITOK);
2447 if (mf == NULL)
2448 return (ENOMEM);
2449
2450 if ((rv = copyin(pt->pt_msg, mf, pt->pt_msglen)) != 0)
2451 goto bad;
2452
2453 im = iop_msg_alloc(sc, NULL, IM_WAIT | IM_NOSTATUS);
2454 im->im_rb = (struct i2o_reply *)mf;
2455 mf->msgictx = IOP_ICTX;
2456 mf->msgtctx = im->im_tctx;
2457
2458 for (i = 0; i < pt->pt_nbufs; i++) {
2459 ptb = &pt->pt_bufs[i];
2460 buf = sc->sc_ptb + i * IOP_MAX_XFER;
2461
2462 if ((u_int)ptb->ptb_datalen > IOP_MAX_XFER) {
2463 rv = EINVAL;
2464 goto bad;
2465 }
2466
2467 if (ptb->ptb_out != 0) {
2468 rv = copyin(ptb->ptb_data, buf, ptb->ptb_datalen);
2469 if (rv != 0)
2470 goto bad;
2471 }
2472
2473 rv = iop_msg_map(sc, im, (u_int32_t *)mf, buf,
2474 ptb->ptb_datalen, ptb->ptb_out != 0);
2475 if (rv != 0)
2476 goto bad;
2477 mapped = 1;
2478 }
2479
2480 if ((rv = iop_msg_post(sc, im, mf, pt->pt_timo)) != 0)
2481 goto bad;
2482
2483 i = (letoh32(im->im_rb->msgflags) >> 14) & ~3;
2484 if (i > IOP_MAX_MSG_SIZE)
2485 i = IOP_MAX_MSG_SIZE;
2486 if (i > pt->pt_replylen)
2487 i = pt->pt_replylen;
2488 if ((rv = copyout(im->im_rb, pt->pt_reply, i)) != 0)
2489 goto bad;
2490
2491 iop_msg_unmap(sc, im);
2492 mapped = 0;
2493
2494 for (i = 0; i < pt->pt_nbufs; i++) {
2495 ptb = &pt->pt_bufs[i];
2496 if (ptb->ptb_out != 0)
2497 continue;
2498 buf = sc->sc_ptb + i * IOP_MAX_XFER;
2499 rv = copyout(buf, ptb->ptb_data, ptb->ptb_datalen);
2500 if (rv != 0)
2501 break;
2502 }
2503
2504 bad:
2505 if (mapped != 0)
2506 iop_msg_unmap(sc, im);
2507 if (im != NULL)
2508 iop_msg_free(sc, im);
2509 if (mf != NULL)
2510 free(mf, M_DEVBUF);
2511 return (rv);
2512 }
2513