xref: /dflybsd-src/sys/dev/raid/ips/ips.c (revision a9656fbcd49c376aba5e04370d8b0f1fa96e063c)
1 /*-
2  * Written by: David Jeffery
3  * Copyright (c) 2002 Adaptec Inc.
4  * All rights reserved.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions
8  * are met:
9  * 1. Redistributions of source code must retain the above copyright
10  *    notice, this list of conditions and the following disclaimer.
11  * 2. Redistributions in binary form must reproduce the above copyright
12  *    notice, this list of conditions and the following disclaimer in the
13  *    documentation and/or other materials provided with the distribution.
14  *
15  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
16  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
19  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25  * SUCH DAMAGE.
26  *
27  * $FreeBSD: src/sys/dev/ips/ips.c,v 1.12 2004/05/30 04:01:29 scottl Exp $
28  * $DragonFly: src/sys/dev/raid/ips/ips.c,v 1.19 2006/12/22 23:26:23 swildner Exp $
29  */
30 
31 #include <dev/raid/ips/ips.h>
32 #include <sys/stat.h>
33 #include <sys/time.h>
34 #include <sys/thread2.h>
35 #include <sys/udev.h>
36 #include <machine/clock.h>
37 
38 static d_open_t ips_open;
39 static d_close_t ips_close;
40 static d_ioctl_t ips_ioctl;
41 
42 MALLOC_DEFINE(M_IPSBUF, "ipsbuf", "IPS driver buffer");
43 
44 static struct dev_ops ips_ops = {
45 	{ "ips", IPS_CDEV_MAJOR, D_DISK },
46 	.d_open	= 	ips_open,
47 	.d_close =	ips_close,
48 	.d_ioctl =	ips_ioctl,
49 };
50 
51 static const char *ips_adapter_name[] = {
52 	"N/A",
53 	"ServeRAID (copperhead)",
54 	"ServeRAID II (copperhead refresh)",
55 	"ServeRAID onboard (copperhead)",
56 	"ServeRAID onboard (copperhead)",
57 	"ServeRAID 3H (clarinet)",
58 	"ServeRAID 3L (clarinet lite)",
59 	"ServeRAID 4H (trombone)",
60 	"ServeRAID 4M (morpheus)",
61 	"ServeRAID 4L (morpheus lite)",
62 	"ServeRAID 4Mx (neo)",
63 	"ServeRAID 4Lx (neo lite)",
64 	"ServeRAID 5i II (sarasota)",
65 	"ServeRAID 5i (sarasota)",
66 	"ServeRAID 6M (marco)",
67 	"ServeRAID 6i (sebring)"
68 };
69 
70 
71 static int
72 ips_open(struct dev_open_args *ap)
73 {
74 	cdev_t dev = ap->a_head.a_dev;
75 	ips_softc_t *sc = dev->si_drv1;
76 
77 	sc->state |= IPS_DEV_OPEN;
78 	return 0;
79 }
80 
81 static int
82 ips_close(struct dev_close_args *ap)
83 {
84 	cdev_t dev = ap->a_head.a_dev;
85 	ips_softc_t *sc = dev->si_drv1;
86 
87 	sc->state &= ~IPS_DEV_OPEN;
88 	return 0;
89 }
90 
91 static int
92 ips_ioctl(struct dev_ioctl_args *ap)
93 {
94 	ips_softc_t *sc;
95 
96 	sc = ap->a_head.a_dev->si_drv1;
97 	return ips_ioctl_request(sc, ap->a_cmd, ap->a_data, ap->a_fflag);
98 }
99 
100 static void
101 ips_cmd_dmaload(void *cmdptr, bus_dma_segment_t *segments, int segnum,
102     int error)
103 {
104 	ips_command_t *command = cmdptr;
105 
106 	PRINTF(10, "ips: in ips_cmd_dmaload\n");
107 	if (!error)
108 		command->command_phys_addr = segments[0].ds_addr;
109 
110 }
111 
112 /* is locking needed? what locking guarentees are there on removal? */
113 static int
114 ips_cmdqueue_free(ips_softc_t *sc)
115 {
116 	int i, error = -1;
117 	ips_command_t *command;
118 
119 	crit_enter();
120 	if (sc->used_commands == 0) {
121 		for (i = 0; i < sc->max_cmds; i++) {
122 			command = &sc->commandarray[i];
123 			if (command->command_phys_addr == 0)
124 				continue;
125 			bus_dmamap_unload(sc->command_dmatag,
126 			    command->command_dmamap);
127 			bus_dmamem_free(sc->command_dmatag,
128 			    command->command_buffer,
129 			    command->command_dmamap);
130 			if (command->data_dmamap != NULL)
131 				bus_dmamap_destroy(command->data_dmatag,
132 				    command->data_dmamap);
133 		}
134 		error = 0;
135 		sc->state |= IPS_OFFLINE;
136 	}
137 	sc->staticcmd = NULL;
138 	kfree(sc->commandarray, M_IPSBUF);
139 	crit_exit();
140 	return error;
141 }
142 
143 /*
144  * Places all ips command structs on the free command queue.
145  * The first slot is used exclusively for static commands
146  * No locking as if someone else tries to access this during init,
147  * we have bigger problems
148  */
149 static int
150 ips_cmdqueue_init(ips_softc_t *sc)
151 {
152 	int i;
153 	ips_command_t *command;
154 
155 	sc->commandarray = kmalloc(sizeof(sc->commandarray[0]) * sc->max_cmds,
156 	    M_IPSBUF, M_INTWAIT | M_ZERO);
157 	SLIST_INIT(&sc->free_cmd_list);
158 	for (i = 0; i < sc->max_cmds; i++) {
159 		command = &sc->commandarray[i];
160 		command->id = i;
161 		command->sc = sc;
162 		if (bus_dmamem_alloc(sc->command_dmatag,
163 		    &command->command_buffer, BUS_DMA_NOWAIT,
164 		    &command->command_dmamap))
165 			goto error;
166 		bus_dmamap_load(sc->command_dmatag, command->command_dmamap,
167 		    command->command_buffer, IPS_COMMAND_LEN, ips_cmd_dmaload,
168 		    command, BUS_DMA_NOWAIT);
169 		if (command->command_phys_addr == 0) {
170 			bus_dmamem_free(sc->command_dmatag,
171 			    command->command_buffer, command->command_dmamap);
172 			goto error;
173 		}
174 
175 		if (i == 0)
176 			sc->staticcmd = command;
177 		else {
178 			command->data_dmatag = sc->sg_dmatag;
179 			if (bus_dmamap_create(command->data_dmatag, 0,
180 			    &command->data_dmamap))
181 				goto error;
182 			SLIST_INSERT_HEAD(&sc->free_cmd_list, command, next);
183 		}
184 	}
185 	sc->state &= ~IPS_OFFLINE;
186 	return 0;
187 error:
188 	ips_cmdqueue_free(sc);
189 	return ENOMEM;
190 }
191 
192 /*
193  * returns a free command struct if one is available.
194  * It also blanks out anything that may be a wild pointer/value.
195  * Also, command buffers are not freed.  They are
196  * small so they are saved and kept dmamapped and loaded.
197  */
198 int
199 ips_get_free_cmd(ips_softc_t *sc, ips_command_t **cmd, unsigned long flags)
200 {
201 	ips_command_t *command = NULL;
202 	int error = 0;
203 
204 	crit_enter();
205 	if (sc->state & IPS_OFFLINE) {
206 		error = EIO;
207 		goto bail;
208 	}
209 	if ((flags & IPS_STATIC_FLAG) != 0) {
210 		if (sc->state & IPS_STATIC_BUSY) {
211 			error = EAGAIN;
212 			goto bail;
213 		}
214 		command = sc->staticcmd;
215 		sc->state |= IPS_STATIC_BUSY;
216 	} else {
217 		command = SLIST_FIRST(&sc->free_cmd_list);
218 		if (!command || (sc->state & IPS_TIMEOUT)) {
219 			error = EBUSY;
220 			goto bail;
221 		}
222 		SLIST_REMOVE_HEAD(&sc->free_cmd_list, next);
223 		sc->used_commands++;
224 	}
225 bail:
226 	crit_exit();
227 	if (error != 0)
228 		return error;
229 
230 	bzero(&command->status, (char *)(command + 1) - (char *)(&command->status));
231 	bzero(command->command_buffer, IPS_COMMAND_LEN);
232 	*cmd = command;
233 	return 0;
234 }
235 
236 /* adds a command back to the free command queue */
237 void
238 ips_insert_free_cmd(ips_softc_t *sc, ips_command_t *command)
239 {
240 	crit_enter();
241 	if (command == sc->staticcmd)
242 		sc->state &= ~IPS_STATIC_BUSY;
243 	else {
244 		SLIST_INSERT_HEAD(&sc->free_cmd_list, command, next);
245 		sc->used_commands--;
246 	}
247 	crit_exit();
248 }
249 
250 static const char *
251 ips_diskdev_statename(u_int8_t state)
252 {
253 	static char statebuf[20];
254 
255 	switch(state) {
256 	case IPS_LD_OFFLINE:
257 		return("OFFLINE");
258 		break;
259 	case IPS_LD_OKAY:
260 		return("OK");
261 		break;
262 	case IPS_LD_DEGRADED:
263 		return("DEGRADED");
264 		break;
265 	case IPS_LD_FREE:
266 		return("FREE");
267 		break;
268 	case IPS_LD_SYS:
269 		return("SYS");
270 		break;
271 	case IPS_LD_CRS:
272 		return("CRS");
273 		break;
274 	}
275 	ksprintf(statebuf, "UNKNOWN(0x%02x)", state);
276 	return (statebuf);
277 }
278 
279 static int
280 ips_diskdev_init(ips_softc_t *sc)
281 {
282 	int i;
283 
284 	for (i = 0; i < IPS_MAX_NUM_DRIVES; i++) {
285 		if (sc->drives[i].state == IPS_LD_FREE)
286 			continue;
287 		device_printf(sc->dev,
288 		    "Logical Drive %d: RAID%d sectors: %u, state %s\n", i,
289 		    sc->drives[i].raid_lvl, sc->drives[i].sector_count,
290 		    ips_diskdev_statename(sc->drives[i].state));
291 		if (sc->drives[i].state == IPS_LD_OKAY ||
292 		    sc->drives[i].state == IPS_LD_DEGRADED) {
293 			sc->diskdev[i] = device_add_child(sc->dev, NULL, -1);
294 			device_set_ivars(sc->diskdev[i], (void *)(uintptr_t)i);
295 		}
296 	}
297 	if (bus_generic_attach(sc->dev))
298 		device_printf(sc->dev, "Attaching bus failed\n");
299 	return 0;
300 }
301 
302 static int
303 ips_diskdev_free(ips_softc_t *sc)
304 {
305 	int i;
306 	int error = 0;
307 
308 	for (i = 0; i < IPS_MAX_NUM_DRIVES; i++) {
309 		if (sc->diskdev[i] != NULL) {
310 			error = device_delete_child(sc->dev, sc->diskdev[i]);
311 			if (error)
312 				return error;
313 		}
314 	}
315 	bus_generic_detach(sc->dev);
316 	return 0;
317 }
318 
319 /*
320  * ips_timeout is periodically called to make sure no commands sent
321  * to the card have become stuck.  If it finds a stuck command, it
322  * sets a flag so the driver won't start any more commands and then
323  * is periodically called to see if all outstanding commands have
324  * either finished or timed out.  Once timed out, an attempt to
325  * reinitialize the card is made.  If that fails, the driver gives
326  * up and declares the card dead.
327  */
328 static void
329 ips_timeout(void *arg)
330 {
331 	ips_command_t *command;
332 	ips_softc_t *sc = arg;
333 	int i, state = 0;
334 
335 	lockmgr(&sc->queue_lock, LK_EXCLUSIVE|LK_RETRY);
336 	command = &sc->commandarray[0];
337 	for (i = 0; i < sc->max_cmds; i++) {
338 		if (!command[i].timeout)
339 			continue;
340 		command[i].timeout--;
341 		if (command[i].timeout == 0) {
342 			if (!(sc->state & IPS_TIMEOUT)) {
343 				sc->state |= IPS_TIMEOUT;
344 				device_printf(sc->dev, "WARNING: command timeout. Adapter is in toaster mode, resetting to known state\n");
345 			}
346 			command[i].status.value = IPS_ERROR_STATUS;
347 			command[i].callback(&command[i]);
348 			/* hmm, this should be enough cleanup */
349 		} else
350 			state = 1;
351 	}
352 	if (!state && (sc->state & IPS_TIMEOUT)) {
353 		if (sc->ips_adapter_reinit(sc, 1)) {
354 			device_printf(sc->dev, "AIEE! adapter reset failed, "
355 			    "giving up and going home! Have a nice day.\n");
356 			sc->state |= IPS_OFFLINE;
357 			sc->state &= ~IPS_TIMEOUT;
358 			/*
359 			 * Grr, I hate this solution. I run waiting commands
360 			 * one at a time and error them out just before they
361 			 * would go to the card. This sucks.
362 			 */
363 		} else
364 			sc->state &= ~IPS_TIMEOUT;
365 	}
366 	if (sc->state != IPS_OFFLINE)
367 		callout_reset(&sc->timer, 10 * hz, ips_timeout, sc);
368 	lockmgr(&sc->queue_lock, LK_RELEASE);
369 }
370 
371 /* check card and initialize it */
372 int
373 ips_adapter_init(ips_softc_t *sc)
374 {
375 	int i;
376 	cdev_t dev;
377 
378 	DEVICE_PRINTF(1, sc->dev, "initializing\n");
379 	if (bus_dma_tag_create(	/* parent    */	sc->adapter_dmatag,
380 				/* alignemnt */	1,
381 				/* boundary  */	0,
382 				/* lowaddr   */	BUS_SPACE_MAXADDR_32BIT,
383 				/* highaddr  */	BUS_SPACE_MAXADDR,
384 				/* filter    */	NULL,
385 				/* filterarg */	NULL,
386 				/* maxsize   */	IPS_COMMAND_LEN +
387 						    IPS_MAX_SG_LEN,
388 				/* numsegs   */	1,
389 				/* maxsegsize*/	IPS_COMMAND_LEN +
390 						    IPS_MAX_SG_LEN,
391 				/* flags     */	0,
392 				&sc->command_dmatag) != 0) {
393 		device_printf(sc->dev, "can't alloc command dma tag\n");
394 		goto error;
395 	}
396 	if (bus_dma_tag_create(	/* parent    */	sc->adapter_dmatag,
397 				/* alignemnt */	1,
398 				/* boundary  */	0,
399 				/* lowaddr   */	BUS_SPACE_MAXADDR_32BIT,
400 				/* highaddr  */	BUS_SPACE_MAXADDR,
401 				/* filter    */	NULL,
402 				/* filterarg */	NULL,
403 				/* maxsize   */	IPS_MAX_IOBUF_SIZE,
404 				/* numsegs   */	IPS_MAX_SG_ELEMENTS,
405 				/* maxsegsize*/	IPS_MAX_IOBUF_SIZE,
406 				/* flags     */	0,
407 				&sc->sg_dmatag) != 0) {
408 		device_printf(sc->dev, "can't alloc SG dma tag\n");
409 		goto error;
410 	}
411 	/*
412 	 * create one command buffer until we know how many commands this card
413 	 * can handle
414 	 */
415 	sc->max_cmds = 1;
416 	ips_cmdqueue_init(sc);
417 	callout_init(&sc->timer);
418 	if (sc->ips_adapter_reinit(sc, 0))
419 		goto error;
420 	/* initialize ffdc values */
421 	microtime(&sc->ffdc_resettime);
422 	sc->ffdc_resetcount = 1;
423 	if ((i = ips_ffdc_reset(sc)) != 0) {
424 		device_printf(sc->dev,
425 		    "failed to send ffdc reset to device (%d)\n", i);
426 		goto error;
427 	}
428 	if ((i = ips_get_adapter_info(sc)) != 0) {
429 		device_printf(sc->dev, "failed to get adapter configuration "
430 		    "data from device (%d)\n", i);
431 		goto error;
432 	}
433 	/* no error check as failure doesn't matter */
434 	ips_update_nvram(sc);
435 	if (sc->adapter_type > 0 && sc->adapter_type <= IPS_ADAPTER_MAX_T) {
436 		device_printf(sc->dev, "adapter type: %s\n",
437 		    ips_adapter_name[sc->adapter_type]);
438 	}
439 	if ((i = ips_get_drive_info(sc)) != 0) {
440 		device_printf(sc->dev, "failed to get drive "
441 		    "configuration data from device (%d)\n", i);
442 		goto error;
443 	}
444 	ips_cmdqueue_free(sc);
445 	if (sc->adapter_info.max_concurrent_cmds)
446 		sc->max_cmds = min(128, sc->adapter_info.max_concurrent_cmds);
447 	else
448 		sc->max_cmds = 32;
449 	if (ips_cmdqueue_init(sc)) {
450 		device_printf(sc->dev,
451 		    "failed to initialize command buffers\n");
452 		goto error;
453 	}
454 	dev = make_dev(&ips_ops, device_get_unit(sc->dev),
455 		       UID_ROOT, GID_OPERATOR, S_IRUSR | S_IWUSR,
456 		       "ips%d", device_get_unit(sc->dev));
457 	dev->si_drv1 = sc;
458 	udev_dict_set_cstr(dev, "subsystem", "raid");
459 	udev_dict_set_cstr(dev, "disk-type", "raid");
460 	ips_diskdev_init(sc);
461 	callout_reset(&sc->timer, 10 * hz, ips_timeout, sc);
462 	return 0;
463 error:
464 	ips_adapter_free(sc);
465 	return ENXIO;
466 }
467 
468 /*
469  * see if we should reinitialize the card and wait for it to timeout
470  * or complete initialization
471  */
472 int
473 ips_morpheus_reinit(ips_softc_t *sc, int force)
474 {
475 	u_int32_t tmp;
476 	int i;
477 
478 	tmp = ips_read_4(sc, MORPHEUS_REG_OISR);
479 	if (!force && (ips_read_4(sc, MORPHEUS_REG_OMR0) >= IPS_POST1_OK) &&
480 	    (ips_read_4(sc, MORPHEUS_REG_OMR1) != 0xdeadbeef) && !tmp) {
481 		ips_write_4(sc, MORPHEUS_REG_OIMR, 0);
482 		return 0;
483 	}
484 	ips_write_4(sc, MORPHEUS_REG_OIMR, 0xff);
485 	ips_read_4(sc, MORPHEUS_REG_OIMR);
486 	device_printf(sc->dev,
487 	    "resetting adapter, this may take up to 5 minutes\n");
488 	ips_write_4(sc, MORPHEUS_REG_IDR, 0x80000000);
489 	DELAY(5000000);
490 	pci_read_config(sc->dev, 0, 4);
491 	tmp = ips_read_4(sc, MORPHEUS_REG_OISR);
492 	for (i = 0; i < 45 && !(tmp & MORPHEUS_BIT_POST1); i++) {
493 		DELAY(1000000);
494 		DEVICE_PRINTF(2, sc->dev, "post1: %d\n", i);
495 		tmp = ips_read_4(sc, MORPHEUS_REG_OISR);
496 	}
497 	if (tmp & MORPHEUS_BIT_POST1)
498 		ips_write_4(sc, MORPHEUS_REG_OISR, MORPHEUS_BIT_POST1);
499 
500 	if (i == 45 || ips_read_4(sc, MORPHEUS_REG_OMR0) < IPS_POST1_OK) {
501 		device_printf(sc->dev,
502 		    "Adapter error during initialization.\n");
503 		return 1;
504 	}
505 	for (i = 0; i < 240 && !(tmp & MORPHEUS_BIT_POST2); i++) {
506 		DELAY(1000000);
507 		DEVICE_PRINTF(2, sc->dev, "post2: %d\n", i);
508 		tmp = ips_read_4(sc, MORPHEUS_REG_OISR);
509 	}
510 	if (tmp & MORPHEUS_BIT_POST2)
511 		ips_write_4(sc, MORPHEUS_REG_OISR, MORPHEUS_BIT_POST2);
512 
513 	if (i == 240 || !ips_read_4(sc, MORPHEUS_REG_OMR1)) {
514 		device_printf(sc->dev, "adapter failed config check\n");
515 		return 1;
516 	}
517 	ips_write_4(sc, MORPHEUS_REG_OIMR, 0);
518 	if (force && ips_clear_adapter(sc)) {
519 		device_printf(sc->dev, "adapter clear failed\n");
520 		return 1;
521 	}
522 	return 0;
523 }
524 
525 /* clean up so we can unload the driver. */
526 int
527 ips_adapter_free(ips_softc_t *sc)
528 {
529 	int error = 0;
530 
531 	if (sc->state & IPS_DEV_OPEN)
532 		return EBUSY;
533 	if ((error = ips_diskdev_free(sc)))
534 		return error;
535 	if (ips_cmdqueue_free(sc)) {
536 		device_printf(sc->dev,
537 		    "trying to exit when command queue is not empty!\n");
538 		return EBUSY;
539 	}
540 	DEVICE_PRINTF(1, sc->dev, "free\n");
541 	crit_enter();
542 	callout_stop(&sc->timer);
543 	crit_exit();
544 	if (sc->sg_dmatag)
545 		bus_dma_tag_destroy(sc->sg_dmatag);
546 	if (sc->command_dmatag)
547 		bus_dma_tag_destroy(sc->command_dmatag);
548 	dev_ops_remove_minor(&ips_ops, device_get_unit(sc->dev));
549 	return 0;
550 }
551 
552 static int
553 ips_morpheus_check_intr(void *void_sc)
554 {
555 	ips_softc_t *sc = (ips_softc_t *)void_sc;
556 	u_int32_t oisr, iisr;
557 	ips_cmd_status_t status;
558 	ips_command_t *command;
559 	int cmdnumber;
560 	int found = 0;
561 
562 	iisr =ips_read_4(sc, MORPHEUS_REG_IISR);
563 	oisr =ips_read_4(sc, MORPHEUS_REG_OISR);
564 	PRINTF(9, "interrupt registers in:%x out:%x\n", iisr, oisr);
565 	if (!(oisr & MORPHEUS_BIT_CMD_IRQ)) {
566 		DEVICE_PRINTF(2, sc->dev, "got a non-command irq\n");
567 		return(0);
568 	}
569 	while ((status.value = ips_read_4(sc, MORPHEUS_REG_OQPR))
570 	       != 0xffffffff) {
571 		cmdnumber = status.fields.command_id;
572 		command = &sc->commandarray[cmdnumber];
573 		command->status.value = status.value;
574 		command->timeout = 0;
575 		command->callback(command);
576 		DEVICE_PRINTF(9, sc->dev, "got command %d\n", cmdnumber);
577 		found = 1;
578 	}
579 	return(found);
580 }
581 
582 void
583 ips_morpheus_intr(void *void_sc)
584 {
585 	ips_softc_t *sc = void_sc;
586 
587 	lockmgr(&sc->queue_lock, LK_EXCLUSIVE|LK_RETRY);
588 	ips_morpheus_check_intr(sc);
589 	lockmgr(&sc->queue_lock, LK_RELEASE);
590 }
591 
592 void
593 ips_issue_morpheus_cmd(ips_command_t *command)
594 {
595 	crit_enter();
596 	/* hmmm, is there a cleaner way to do this? */
597 	if (command->sc->state & IPS_OFFLINE) {
598 		crit_exit();
599 		command->status.value = IPS_ERROR_STATUS;
600 		command->callback(command);
601 		return;
602 	}
603 	command->timeout = 10;
604 	ips_write_4(command->sc, MORPHEUS_REG_IQPR, command->command_phys_addr);
605 	crit_exit();
606 }
607 
608 void
609 ips_morpheus_poll(ips_command_t *command)
610 {
611 	uint32_t ts;
612 
613 	ts = time_second + command->timeout;
614 	while (command->timeout != 0 &&
615 	    ips_morpheus_check_intr(command->sc) == 0 &&
616 	    (ts > time_second))
617 		DELAY(1000);
618  }
619 
620 static void
621 ips_copperhead_queue_callback(void *queueptr, bus_dma_segment_t *segments,
622 			      int segnum, int error)
623 {
624 	ips_copper_queue_t *queue = queueptr;
625 
626 	if (error)
627 		return;
628 	queue->base_phys_addr = segments[0].ds_addr;
629 }
630 
631 static int
632 ips_copperhead_queue_init(ips_softc_t *sc)
633 {
634 	bus_dma_tag_t dmatag;
635 	bus_dmamap_t dmamap;
636 	int error;
637 
638 	if (bus_dma_tag_create(	/* parent    */	sc->adapter_dmatag,
639 				/* alignemnt */	1,
640 				/* boundary  */	0,
641 				/* lowaddr   */	BUS_SPACE_MAXADDR_32BIT,
642 				/* highaddr  */	BUS_SPACE_MAXADDR,
643 				/* filter    */	NULL,
644 				/* filterarg */	NULL,
645 				/* maxsize   */	sizeof(ips_copper_queue_t),
646 				/* numsegs   */	1,
647 				/* maxsegsize*/	sizeof(ips_copper_queue_t),
648 				/* flags     */	0,
649 				&dmatag) != 0) {
650 		device_printf(sc->dev, "can't alloc dma tag for statue queue\n");
651 		error = ENOMEM;
652 		goto exit;
653 	}
654 	if (bus_dmamem_alloc(dmatag, (void *)&(sc->copper_queue),
655 	    BUS_DMA_NOWAIT, &dmamap)) {
656 		error = ENOMEM;
657 		goto exit;
658 	}
659 	bzero(sc->copper_queue, sizeof(ips_copper_queue_t));
660 	sc->copper_queue->dmatag = dmatag;
661 	sc->copper_queue->dmamap = dmamap;
662 	sc->copper_queue->nextstatus = 1;
663 	bus_dmamap_load(dmatag, dmamap, &(sc->copper_queue->status[0]),
664 	    IPS_MAX_CMD_NUM * 4, ips_copperhead_queue_callback,
665 	    sc->copper_queue, BUS_DMA_NOWAIT);
666 	if (sc->copper_queue->base_phys_addr == 0) {
667 		error = ENOMEM;
668 		goto exit;
669 	}
670 	ips_write_4(sc, COPPER_REG_SQSR, sc->copper_queue->base_phys_addr);
671 	ips_write_4(sc, COPPER_REG_SQER, sc->copper_queue->base_phys_addr +
672 	    IPS_MAX_CMD_NUM * 4);
673 	ips_write_4(sc, COPPER_REG_SQHR, sc->copper_queue->base_phys_addr + 4);
674 	ips_write_4(sc, COPPER_REG_SQTR, sc->copper_queue->base_phys_addr);
675 	return 0;
676 exit:
677 	bus_dmamem_free(dmatag, sc->copper_queue, dmamap);
678 	bus_dma_tag_destroy(dmatag);
679 	return error;
680 }
681 
682 /*
683  * see if we should reinitialize the card and wait for it to timeout or
684  * complete initialization FIXME
685  */
686 int
687 ips_copperhead_reinit(ips_softc_t *sc, int force)
688 {
689 	u_int32_t postcode = 0, configstatus = 0;
690 	int	  i, j;
691 
692 	ips_write_1(sc, COPPER_REG_SCPR, 0x80);
693 	ips_write_1(sc, COPPER_REG_SCPR, 0);
694 	device_printf(sc->dev,
695 	    "reinitializing adapter, this could take several minutes.\n");
696 	for (j = 0; j < 2; j++) {
697 		postcode <<= 8;
698 		for (i = 0; i < 45; i++) {
699 			if (ips_read_1(sc, COPPER_REG_HISR) & COPPER_GHI_BIT) {
700 				postcode |= ips_read_1(sc, COPPER_REG_ISPR);
701 				ips_write_1(sc, COPPER_REG_HISR,
702 				    COPPER_GHI_BIT);
703 				break;
704 			} else
705 				DELAY(1000000);
706 		}
707 		if (i == 45)
708 			return 1;
709 	}
710 	for (j = 0; j < 2; j++) {
711 		configstatus <<= 8;
712 		for (i = 0; i < 240; i++) {
713 			if (ips_read_1(sc, COPPER_REG_HISR) & COPPER_GHI_BIT) {
714 				configstatus |= ips_read_1(sc, COPPER_REG_ISPR);
715 				ips_write_1(sc, COPPER_REG_HISR,
716 				    COPPER_GHI_BIT);
717 				break;
718 			} else
719 				DELAY(1000000);
720 		}
721 		if (i == 240)
722 			return 1;
723 	}
724 	for (i = 0; i < 240; i++) {
725 		if (!(ips_read_1(sc, COPPER_REG_CBSP) & COPPER_OP_BIT))
726 			break;
727 		else
728 			DELAY(1000000);
729 	}
730 	if (i == 240)
731 		return 1;
732 	ips_write_2(sc, COPPER_REG_CCCR, 0x1000 | COPPER_ILE_BIT);
733 	ips_write_1(sc, COPPER_REG_SCPR, COPPER_EBM_BIT);
734 	ips_copperhead_queue_init(sc);
735 	ips_write_1(sc, COPPER_REG_HISR, COPPER_GHI_BIT);
736 	i = ips_read_1(sc, COPPER_REG_SCPR);
737 	ips_write_1(sc, COPPER_REG_HISR, COPPER_EI_BIT);
738 	if (configstatus == 0) {
739 		device_printf(sc->dev, "adapter initialization failed\n");
740 		return 1;
741 	}
742 	if (force && ips_clear_adapter(sc)) {
743 		device_printf(sc->dev, "adapter clear failed\n");
744 		return 1;
745 	}
746 	return 0;
747 }
748 
749 static u_int32_t
750 ips_copperhead_cmd_status(ips_softc_t *sc)
751 {
752 	u_int32_t value;
753 	int statnum;
754 
755 	statnum = sc->copper_queue->nextstatus++;
756 	if (sc->copper_queue->nextstatus == IPS_MAX_CMD_NUM)
757 		sc->copper_queue->nextstatus = 0;
758 	crit_enter();
759 	value = sc->copper_queue->status[statnum];
760 	ips_write_4(sc, COPPER_REG_SQTR, sc->copper_queue->base_phys_addr +
761 	    4 * statnum);
762 	crit_exit();
763 	return value;
764 }
765 
766 void
767 ips_copperhead_intr(void *void_sc)
768 {
769 	ips_softc_t *sc = (ips_softc_t *)void_sc;
770 	ips_cmd_status_t status;
771 	int cmdnumber;
772 
773 	lockmgr(&sc->queue_lock, LK_EXCLUSIVE|LK_RETRY);
774 	while (ips_read_1(sc, COPPER_REG_HISR) & COPPER_SCE_BIT) {
775 		status.value = ips_copperhead_cmd_status(sc);
776 		cmdnumber = status.fields.command_id;
777 		sc->commandarray[cmdnumber].status.value = status.value;
778 		sc->commandarray[cmdnumber].timeout = 0;
779 		sc->commandarray[cmdnumber].callback(&(sc->commandarray[cmdnumber]));
780 		PRINTF(9, "ips: got command %d\n", cmdnumber);
781 	}
782 	lockmgr(&sc->queue_lock, LK_RELEASE);
783 	return;
784 }
785 
786 void
787 ips_issue_copperhead_cmd(ips_command_t *command)
788 {
789 	int i;
790 
791 	crit_enter();
792 	/* hmmm, is there a cleaner way to do this? */
793 	if (command->sc->state & IPS_OFFLINE) {
794 		crit_exit();
795 		command->status.value = IPS_ERROR_STATUS;
796 		command->callback(command);
797 		return;
798 	}
799 	command->timeout = 10;
800 	for (i = 0; ips_read_4(command->sc, COPPER_REG_CCCR) & COPPER_SEM_BIT;
801 	    i++) {
802 		if (i == 20) {
803 			kprintf("sem bit still set, can't send a command\n");
804 			crit_exit();
805 			return;
806 		}
807 		DELAY(500);	/* need to do a delay here */
808 	}
809 	ips_write_4(command->sc, COPPER_REG_CCSAR, command->command_phys_addr);
810 	ips_write_2(command->sc, COPPER_REG_CCCR, COPPER_CMD_START);
811 	crit_exit();
812 }
813 
814 void
815 ips_copperhead_poll(ips_command_t *command)
816 {
817 	kprintf("ips: cmd polling not implemented for copperhead devices\n");
818 }
819