xref: /openbsd-src/sys/dev/pcmcia/pcmcia_cis.c (revision b2ea75c1b17e1a9a339660e7ed45cd24946b230e)
1 /*	$OpenBSD: pcmcia_cis.c,v 1.5 2000/06/06 01:02:26 fgsch Exp $	*/
2 /*	$NetBSD: pcmcia_cis.c,v 1.9 1998/08/22 23:41:48 msaitoh Exp $	*/
3 
4 /*
5  * Copyright (c) 1997 Marc Horowitz.  All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  * 3. All advertising materials mentioning features or use of this software
16  *    must display the following acknowledgement:
17  *	This product includes software developed by Marc Horowitz.
18  * 4. The name of the author may not be used to endorse or promote products
19  *    derived from this software without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
22  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
23  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
24  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
25  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
26  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
27  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
28  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
29  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
30  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31  */
32 
33 #include <sys/types.h>
34 #include <sys/param.h>
35 #include <sys/systm.h>
36 #include <sys/device.h>
37 #include <sys/malloc.h>
38 
39 #include <dev/pcmcia/pcmciareg.h>
40 #include <dev/pcmcia/pcmciachip.h>
41 #include <dev/pcmcia/pcmciavar.h>
42 
43 #ifdef PCMCIACISDEBUG
44 #define	DPRINTF(arg) printf arg
45 #else
46 #define	DPRINTF(arg)
47 #endif
48 
49 #define	PCMCIA_CIS_SIZE		1024
50 
51 struct cis_state {
52 	int	count;
53 	int	gotmfc;
54 	struct pcmcia_config_entry temp_cfe;
55 	struct pcmcia_config_entry *default_cfe;
56 	struct pcmcia_card *card;
57 	struct pcmcia_function *pf;
58 };
59 
60 int	pcmcia_parse_cis_tuple __P((struct pcmcia_tuple *, void *));
61 
62 void
63 pcmcia_read_cis(sc)
64 	struct pcmcia_softc *sc;
65 {
66 	struct cis_state state;
67 
68 	state.count = 0;
69 	state.gotmfc = 0;
70 
71 	state.card = &sc->card;
72 
73 	state.card->error = 0;
74 	state.card->cis1_major = -1;
75 	state.card->cis1_minor = -1;
76 	state.card->cis1_info[0] = NULL;
77 	state.card->cis1_info[1] = NULL;
78 	state.card->cis1_info[2] = NULL;
79 	state.card->cis1_info[3] = NULL;
80 	state.card->manufacturer = PCMCIA_VENDOR_INVALID;
81 	state.card->product = PCMCIA_PRODUCT_INVALID;
82 	SIMPLEQ_INIT(&state.card->pf_head);
83 
84 	state.pf = NULL;
85 
86 	if (pcmcia_scan_cis((struct device *)sc, pcmcia_parse_cis_tuple,
87 	    &state) == -1)
88 		state.card->error++;
89 }
90 
91 int
92 pcmcia_scan_cis(dev, fct, arg)
93 	struct device *dev;
94 	int (*fct) __P((struct pcmcia_tuple *, void *));
95 	void *arg;
96 {
97 	struct pcmcia_softc *sc = (struct pcmcia_softc *) dev;
98 	pcmcia_chipset_tag_t pct;
99 	pcmcia_chipset_handle_t pch;
100 	int window;
101 	struct pcmcia_mem_handle pcmh;
102 	struct pcmcia_tuple tuple;
103 	int longlink_present;
104 	int longlink_common;
105 	u_long longlink_addr;
106 	int mfc_count;
107 	int mfc_index;
108 	struct {
109 		int	common;
110 		u_long	addr;
111 	} mfc[256 / 5];
112 	int ret;
113 
114 	ret = 0;
115 
116 	pct = sc->pct;
117 	pch = sc->pch;
118 
119 	/* allocate some memory */
120 
121 	if (pcmcia_chip_mem_alloc(pct, pch, PCMCIA_CIS_SIZE, &pcmh)) {
122 #ifdef DIAGNOSTIC
123 		printf("%s: can't alloc memory to read attributes\n",
124 		    sc->dev.dv_xname);
125 #endif
126 		return -1;
127 	}
128 	tuple.memt = pcmh.memt;
129 	tuple.memh = pcmh.memh;
130 
131 	/* initialize state for the primary tuple chain */
132 	if (pcmcia_chip_mem_map(pct, pch, PCMCIA_MEM_ATTR, 0,
133 	    PCMCIA_CIS_SIZE, &pcmh, &tuple.ptr, &window)) {
134 		pcmcia_chip_mem_free(pct, pch, &pcmh);
135 #ifdef DIAGNOSTIC
136 		printf("%s: can't map memory to read attributes\n",
137 		    sc->dev.dv_xname);
138 #endif
139 		return -1;
140 	}
141 	DPRINTF(("cis mem map %x\n", (unsigned int) tuple.memh));
142 
143 	tuple.mult = 2;
144 
145 	longlink_present = 1;
146 	longlink_common = 1;
147 	longlink_addr = 0;
148 
149 	mfc_count = 0;
150 	mfc_index = 0;
151 
152 	DPRINTF(("%s: CIS tuple chain:\n", sc->dev.dv_xname));
153 
154 	while (1) {
155 		while (1) {
156 			/* get the tuple code */
157 
158 			tuple.code = pcmcia_cis_read_1(&tuple, tuple.ptr);
159 
160 			/* two special-case tuples */
161 
162 			if (tuple.code == PCMCIA_CISTPL_NULL) {
163 				DPRINTF(("CISTPL_NONE\n 00\n"));
164 				tuple.ptr++;
165 				continue;
166 			} else if (tuple.code == PCMCIA_CISTPL_END) {
167 				DPRINTF(("CISTPL_END\n ff\n"));
168 				/* Call the function for the END tuple, since
169 				   the CIS semantics depend on it */
170 				if ((*fct) (&tuple, arg)) {
171 					pcmcia_chip_mem_unmap(pct, pch,
172 							      window);
173 					ret = 1;
174 					goto done;
175 				}
176 				tuple.ptr++;
177 				break;
178 			}
179 			/* now all the normal tuples */
180 
181 			tuple.length = pcmcia_cis_read_1(&tuple, tuple.ptr + 1);
182 			switch (tuple.code) {
183 			case PCMCIA_CISTPL_LONGLINK_A:
184 			case PCMCIA_CISTPL_LONGLINK_C:
185 				if (tuple.length < 4) {
186 					DPRINTF(("CISTPL_LONGLINK_%s too "
187 					    "short %d\n",
188 					    longlink_common ? "C" : "A",
189 					    tuple.length));
190 					break;
191 				}
192 				longlink_present = 1;
193 				longlink_common = (tuple.code ==
194 				    PCMCIA_CISTPL_LONGLINK_C) ? 1 : 0;
195 				longlink_addr = pcmcia_tuple_read_4(&tuple, 0);
196 				DPRINTF(("CISTPL_LONGLINK_%s %lx\n",
197 				    longlink_common ? "C" : "A",
198 				    longlink_addr));
199 				break;
200 			case PCMCIA_CISTPL_NO_LINK:
201 				longlink_present = 0;
202 				DPRINTF(("CISTPL_NO_LINK\n"));
203 				break;
204 			case PCMCIA_CISTPL_CHECKSUM:
205 				if (tuple.length < 5) {
206 					DPRINTF(("CISTPL_CHECKSUM too "
207 					    "short %d\n", tuple.length));
208 					break;
209 				} {
210 					int16_t offset;
211 					u_long addr, length;
212 					u_int cksum, sum;
213 					int i;
214 
215 					*((u_int16_t *) & offset) =
216 					    pcmcia_tuple_read_2(&tuple, 0);
217 					length = pcmcia_tuple_read_2(&tuple, 2);
218 					cksum = pcmcia_tuple_read_1(&tuple, 4);
219 
220 					addr = tuple.ptr + offset;
221 
222 					DPRINTF(("CISTPL_CHECKSUM addr=%lx "
223 					    "len=%lx cksum=%x",
224 					    addr, length, cksum));
225 
226 					/*
227 					 * XXX do more work to deal with
228 					 * distant regions
229 					 */
230 					if ((addr >= PCMCIA_CIS_SIZE) ||
231 					    ((addr + length) < 0) ||
232 					    ((addr + length) >=
233 					      PCMCIA_CIS_SIZE)) {
234 						DPRINTF((" skipped, "
235 						    "too distant\n"));
236 						break;
237 					}
238 					sum = 0;
239 					for (i = 0; i < length; i++)
240 						sum +=
241 						    bus_space_read_1(tuple.memt,
242 						    tuple.memh,
243 						    addr + tuple.mult * i);
244 					if (cksum != (sum & 0xff)) {
245 						DPRINTF((" failed sum=%x\n",
246 						    sum));
247 						printf("%s: CIS checksum "
248 						    "failed\n",
249 						    sc->dev.dv_xname);
250 #if 0
251 						/*
252 						 * XXX Some working cards have
253 						 * XXX bad checksums!!
254 						 */
255 						ret = -1;
256 #endif
257 					} else {
258 						DPRINTF((" ok\n"));
259 					}
260 				}
261 				break;
262 			case PCMCIA_CISTPL_LONGLINK_MFC:
263 				if (tuple.length < 6) {
264 					DPRINTF(("CISTPL_LONGLINK_MFC too "
265 					    "short %d\n", tuple.length));
266 					break;
267 				}
268 				if (((tuple.length - 1) % 5) != 0) {
269 					DPRINTF(("CISTPL_LONGLINK_MFC bogus "
270 					    "length %d\n", tuple.length));
271 					break;
272 				}
273 				{
274 					int i;
275 
276 					mfc_count =
277 					    pcmcia_tuple_read_1(&tuple, 0);
278 					DPRINTF(("CISTPL_LONGLINK_MFC %d",
279 					    mfc_count));
280 					for (i = 0; i < mfc_count; i++) {
281 						mfc[i].common =
282 						    (pcmcia_tuple_read_1(&tuple,
283 						    1 + 5 * i) ==
284 						    PCMCIA_MFC_MEM_COMMON) ?
285 						    1 : 0;
286 						mfc[i].addr =
287 						    pcmcia_tuple_read_4(&tuple,
288 						    1 + 5 * i + 1);
289 						DPRINTF((" %s:%lx",
290 						    mfc[i].common ? "common" :
291 						    "attr", mfc[i].addr));
292 					}
293 					DPRINTF(("\n"));
294 				}
295 				/*
296 				 * for LONGLINK_MFC, fall through to the
297 				 * function.  This tuple has structural and
298 				 * semantic content.
299 				 */
300 			default:
301 				{
302 					if ((*fct) (&tuple, arg)) {
303 						pcmcia_chip_mem_unmap(pct,
304 						    pch, window);
305 						ret = 1;
306 						goto done;
307 					}
308 				}
309 				break;
310 			}	/* switch */
311 #ifdef PCMCIACISDEBUG
312 			/* print the tuple */
313 			{
314 				int i;
315 
316 				DPRINTF((" %02x %02x", tuple.code,
317 				    tuple.length));
318 
319 				for (i = 0; i < tuple.length; i++) {
320 					DPRINTF((" %02x",
321 					    pcmcia_tuple_read_1(&tuple, i)));
322 					if ((i % 16) == 13)
323 						DPRINTF(("\n"));
324 				}
325 				if ((i % 16) != 14)
326 					DPRINTF(("\n"));
327 			}
328 #endif
329 			/* skip to the next tuple */
330 			tuple.ptr += 2 + tuple.length;
331 		}
332 
333 		/*
334 		 * the chain is done.  Clean up and move onto the next one,
335 		 * if any.  The loop is here in the case that there is an MFC
336 		 * card with no longlink (which defaults to existing, == 0).
337 		 * In general, this means that if one pointer fails, it will
338 		 * try the next one, instead of just bailing.
339 		 */
340 
341 		while (1) {
342 			pcmcia_chip_mem_unmap(pct, pch, window);
343 
344 			if (longlink_present) {
345 				/*
346 				 * if the longlink is to attribute memory,
347 				 * then it is unindexed.  That is, if the
348 				 * link value is 0x100, then the actual
349 				 * memory address is 0x200.  This means that
350 				 * we need to multiply by 2 before calling
351 				 * mem_map, and then divide the resulting ptr
352 				 * by 2 after.
353 				 */
354 
355 				if (!longlink_common)
356 					longlink_addr *= 2;
357 
358 				pcmcia_chip_mem_map(pct, pch, longlink_common ?
359 				    PCMCIA_MEM_COMMON : PCMCIA_MEM_ATTR,
360 				    longlink_addr, PCMCIA_CIS_SIZE,
361 				    &pcmh, &tuple.ptr, &window);
362 
363 				if (!longlink_common)
364 					tuple.ptr /= 2;
365 
366 				DPRINTF(("cis mem map %x\n",
367 				    (unsigned int) tuple.memh));
368 
369 				tuple.mult = longlink_common ? 1 : 2;
370 				longlink_present = 0;
371 				longlink_common = 1;
372 				longlink_addr = 0;
373 			} else if (mfc_count && (mfc_index < mfc_count)) {
374 				if (!mfc[mfc_index].common)
375 					mfc[mfc_index].addr *= 2;
376 
377 				pcmcia_chip_mem_map(pct, pch,
378 				    mfc[mfc_index].common ?
379 				    PCMCIA_MEM_COMMON : PCMCIA_MEM_ATTR,
380 				    mfc[mfc_index].addr, PCMCIA_CIS_SIZE,
381 				    &pcmh, &tuple.ptr, &window);
382 
383 				if (!mfc[mfc_index].common)
384 					tuple.ptr /= 2;
385 
386 				DPRINTF(("cis mem map %x\n",
387 				    (unsigned int) tuple.memh));
388 
389 				/* set parse state, and point at the next one */
390 
391 				tuple.mult = mfc[mfc_index].common ? 1 : 2;
392 
393 				mfc_index++;
394 			} else {
395 				goto done;
396 			}
397 
398 			/* make sure that the link is valid */
399 			tuple.code = pcmcia_cis_read_1(&tuple, tuple.ptr);
400 			if (tuple.code != PCMCIA_CISTPL_LINKTARGET) {
401 				DPRINTF(("CISTPL_LINKTARGET expected, "
402 				    "code %02x observed\n", tuple.code));
403 				continue;
404 			}
405 			tuple.length = pcmcia_cis_read_1(&tuple, tuple.ptr + 1);
406 			if (tuple.length < 3) {
407 				DPRINTF(("CISTPL_LINKTARGET too short %d\n",
408 				    tuple.length));
409 				continue;
410 			}
411 			if ((pcmcia_tuple_read_1(&tuple, 0) != 'C') ||
412 			    (pcmcia_tuple_read_1(&tuple, 1) != 'I') ||
413 			    (pcmcia_tuple_read_1(&tuple, 2) != 'S')) {
414 				DPRINTF(("CISTPL_LINKTARGET magic "
415 				    "%02x%02x%02x incorrect\n",
416 				    pcmcia_tuple_read_1(&tuple, 0),
417 				    pcmcia_tuple_read_1(&tuple, 1),
418 				    pcmcia_tuple_read_1(&tuple, 2)));
419 				continue;
420 			}
421 			tuple.ptr += 2 + tuple.length;
422 
423 			break;
424 		}
425 	}
426 
427 	pcmcia_chip_mem_unmap(pct, pch, window);
428 
429 done:
430 	/* Last, free the allocated memory block */
431 	pcmcia_chip_mem_free(pct, pch, &pcmh);
432 
433 	return (ret);
434 }
435 
436 /* XXX this is incredibly verbose.  Not sure what trt is */
437 
438 void
439 pcmcia_print_cis(sc)
440 	struct pcmcia_softc *sc;
441 {
442 	struct pcmcia_card *card = &sc->card;
443 	struct pcmcia_function *pf;
444 	struct pcmcia_config_entry *cfe;
445 	int i;
446 
447 	printf("%s: CIS version ", sc->dev.dv_xname);
448 	if (card->cis1_major == 4) {
449 		if (card->cis1_minor == 0)
450 			printf("PCMCIA 1.0\n");
451 		else if (card->cis1_minor == 1)
452 			printf("PCMCIA 2.0 or 2.1\n");
453 	} else if (card->cis1_major >= 5)
454 		printf("PC Card Standard %d.%d\n", card->cis1_major,
455 		    card->cis1_minor);
456 	else
457 		printf("unknown (major=%d, minor=%d)\n",
458 		    card->cis1_major, card->cis1_minor);
459 
460 	printf("%s: CIS info: ", sc->dev.dv_xname);
461 	for (i = 0; i < 4; i++) {
462 		if (card->cis1_info[i] == NULL)
463 			break;
464 		if (i)
465 			printf(", ");
466 		printf("%s", card->cis1_info[i]);
467 	}
468 	printf("\n");
469 
470 	printf("%s: Manufacturer code 0x%x, product 0x%x\n",
471 	       sc->dev.dv_xname, card->manufacturer, card->product);
472 
473 	for (pf = card->pf_head.sqh_first; pf != NULL;
474 	    pf = pf->pf_list.sqe_next) {
475 		printf("%s: function %d: ", sc->dev.dv_xname, pf->number);
476 
477 		switch (pf->function) {
478 		case PCMCIA_FUNCTION_UNSPEC:
479 			printf("unspecified");
480 			break;
481 		case PCMCIA_FUNCTION_MULTIFUNCTION:
482 			printf("multi-function");
483 			break;
484 		case PCMCIA_FUNCTION_MEMORY:
485 			printf("memory");
486 			break;
487 		case PCMCIA_FUNCTION_SERIAL:
488 			printf("serial port");
489 			break;
490 		case PCMCIA_FUNCTION_PARALLEL:
491 			printf("parallel port");
492 			break;
493 		case PCMCIA_FUNCTION_DISK:
494 			printf("fixed disk");
495 			break;
496 		case PCMCIA_FUNCTION_VIDEO:
497 			printf("video adapter");
498 			break;
499 		case PCMCIA_FUNCTION_NETWORK:
500 			printf("network adapter");
501 			break;
502 		case PCMCIA_FUNCTION_AIMS:
503 			printf("auto incrementing mass storage");
504 			break;
505 		case PCMCIA_FUNCTION_SCSI:
506 			printf("SCSI bridge");
507 			break;
508 		case PCMCIA_FUNCTION_SECURITY:
509 			printf("Security services");
510 			break;
511 		case PCMCIA_FUNCTION_INSTRUMENT:
512 			printf("Instrument");
513 			break;
514 		case PCMCIA_FUNCTION_IOBUS:
515 			printf("Serial I/O Bus Adapter");
516 			break;
517 		default:
518 			printf("unknown (%d)", pf->function);
519 			break;
520 		}
521 
522 		printf(", ccr addr %lx mask %lx\n", pf->ccr_base, pf->ccr_mask);
523 
524 		for (cfe = pf->cfe_head.sqh_first; cfe != NULL;
525 		    cfe = cfe->cfe_list.sqe_next) {
526 			printf("%s: function %d, config table entry %d: ",
527 			    sc->dev.dv_xname, pf->number, cfe->number);
528 
529 			switch (cfe->iftype) {
530 			case PCMCIA_IFTYPE_MEMORY:
531 				printf("memory card");
532 				break;
533 			case PCMCIA_IFTYPE_IO:
534 				printf("I/O card");
535 				break;
536 			default:
537 				printf("card type unknown");
538 				break;
539 			}
540 
541 			printf("; irq mask %x", cfe->irqmask);
542 
543 			if (cfe->num_iospace) {
544 				printf("; iomask %lx, iospace", cfe->iomask);
545 
546 				for (i = 0; i < cfe->num_iospace; i++)
547 					printf(" %lx%s%lx",
548 					    cfe->iospace[i].start,
549 					    cfe->iospace[i].length ? "-" : "",
550 					    cfe->iospace[i].start +
551 					      cfe->iospace[i].length - 1);
552 			}
553 			if (cfe->num_memspace) {
554 				printf("; memspace");
555 
556 				for (i = 0; i < cfe->num_memspace; i++)
557 					printf(" %lx%s%lx%s%lx",
558 					    cfe->memspace[i].cardaddr,
559 					    cfe->memspace[i].length ? "-" : "",
560 					    cfe->memspace[i].cardaddr +
561 					      cfe->memspace[i].length - 1,
562 					    cfe->memspace[i].hostaddr ?
563 					      "@" : "",
564 					    cfe->memspace[i].hostaddr);
565 			}
566 			if (cfe->maxtwins)
567 				printf("; maxtwins %d", cfe->maxtwins);
568 
569 			printf(";");
570 
571 			if (cfe->flags & PCMCIA_CFE_MWAIT_REQUIRED)
572 				printf(" mwait_required");
573 			if (cfe->flags & PCMCIA_CFE_RDYBSY_ACTIVE)
574 				printf(" rdybsy_active");
575 			if (cfe->flags & PCMCIA_CFE_WP_ACTIVE)
576 				printf(" wp_active");
577 			if (cfe->flags & PCMCIA_CFE_BVD_ACTIVE)
578 				printf(" bvd_active");
579 			if (cfe->flags & PCMCIA_CFE_IO8)
580 				printf(" io8");
581 			if (cfe->flags & PCMCIA_CFE_IO16)
582 				printf(" io16");
583 			if (cfe->flags & PCMCIA_CFE_IRQSHARE)
584 				printf(" irqshare");
585 			if (cfe->flags & PCMCIA_CFE_IRQPULSE)
586 				printf(" irqpulse");
587 			if (cfe->flags & PCMCIA_CFE_IRQLEVEL)
588 				printf(" irqlevel");
589 			if (cfe->flags & PCMCIA_CFE_POWERDOWN)
590 				printf(" powerdown");
591 			if (cfe->flags & PCMCIA_CFE_READONLY)
592 				printf(" readonly");
593 			if (cfe->flags & PCMCIA_CFE_AUDIO)
594 				printf(" audio");
595 
596 			printf("\n");
597 		}
598 	}
599 
600 	if (card->error)
601 		printf("%s: %d errors found while parsing CIS\n",
602 		    sc->dev.dv_xname, card->error);
603 }
604 
605 int
606 pcmcia_parse_cis_tuple(tuple, arg)
607 	struct pcmcia_tuple *tuple;
608 	void *arg;
609 {
610 	/* most of these are educated guesses */
611 	static struct pcmcia_config_entry init_cfe = {
612 		-1, PCMCIA_CFE_RDYBSY_ACTIVE | PCMCIA_CFE_WP_ACTIVE |
613 		PCMCIA_CFE_BVD_ACTIVE, PCMCIA_IFTYPE_MEMORY,
614 	};
615 
616 	struct cis_state *state = arg;
617 
618 	switch (tuple->code) {
619 	case PCMCIA_CISTPL_END:
620 		/*
621 		 * If we've seen a LONGLINK_MFC, and this is the first
622 		 * END after it, reset the function list.
623 		 *
624 		 * XXX This might also be the right place to start a
625 		 * new function, but that assumes that a function
626 		 * definition never crosses any longlink, and I'm not
627 		 * sure about that.  This is probably safe for MFC
628 		 * cards, but what we have now isn't broken, so I'd
629 		 * rather not change it.
630 		 */
631 		if (state->gotmfc == 1) {
632 			struct pcmcia_function *pf, *pfnext;
633 
634 			for (pf = state->card->pf_head.sqh_first; pf != NULL;
635 			    pf = pfnext) {
636 				pfnext = pf->pf_list.sqe_next;
637 				free(pf, M_DEVBUF);
638 			}
639 
640 			SIMPLEQ_INIT(&state->card->pf_head);
641 
642 			state->count = 0;
643 			state->gotmfc = 2;
644 			state->pf = NULL;
645 		}
646 		break;
647 
648 	case PCMCIA_CISTPL_LONGLINK_MFC:
649 		/*
650 		 * This tuple's structure was dealt with in scan_cis.  here,
651 		 * record the fact that the MFC tuple was seen, so that
652 		 * functions declared before the MFC link can be cleaned
653 		 * up.
654 		 */
655 		state->gotmfc = 1;
656 		break;
657 
658 #ifdef PCMCIACISDEBUG
659 	case PCMCIA_CISTPL_DEVICE:
660 	case PCMCIA_CISTPL_DEVICE_A:
661 		{
662 			u_int reg, dtype, dspeed;
663 
664 			reg = pcmcia_tuple_read_1(tuple, 0);
665 			dtype = reg & PCMCIA_DTYPE_MASK;
666 			dspeed = reg & PCMCIA_DSPEED_MASK;
667 
668 			DPRINTF(("CISTPL_DEVICE%s type=",
669 			(tuple->code == PCMCIA_CISTPL_DEVICE) ? "" : "_A"));
670 			switch (dtype) {
671 			case PCMCIA_DTYPE_NULL:
672 				DPRINTF(("null"));
673 				break;
674 			case PCMCIA_DTYPE_ROM:
675 				DPRINTF(("rom"));
676 				break;
677 			case PCMCIA_DTYPE_OTPROM:
678 				DPRINTF(("otprom"));
679 				break;
680 			case PCMCIA_DTYPE_EPROM:
681 				DPRINTF(("eprom"));
682 				break;
683 			case PCMCIA_DTYPE_EEPROM:
684 				DPRINTF(("eeprom"));
685 				break;
686 			case PCMCIA_DTYPE_FLASH:
687 				DPRINTF(("flash"));
688 				break;
689 			case PCMCIA_DTYPE_SRAM:
690 				DPRINTF(("sram"));
691 				break;
692 			case PCMCIA_DTYPE_DRAM:
693 				DPRINTF(("dram"));
694 				break;
695 			case PCMCIA_DTYPE_FUNCSPEC:
696 				DPRINTF(("funcspec"));
697 				break;
698 			case PCMCIA_DTYPE_EXTEND:
699 				DPRINTF(("extend"));
700 				break;
701 			default:
702 				DPRINTF(("reserved"));
703 				break;
704 			}
705 			DPRINTF((" speed="));
706 			switch (dspeed) {
707 			case PCMCIA_DSPEED_NULL:
708 				DPRINTF(("null"));
709 				break;
710 			case PCMCIA_DSPEED_250NS:
711 				DPRINTF(("250ns"));
712 				break;
713 			case PCMCIA_DSPEED_200NS:
714 				DPRINTF(("200ns"));
715 				break;
716 			case PCMCIA_DSPEED_150NS:
717 				DPRINTF(("150ns"));
718 				break;
719 			case PCMCIA_DSPEED_100NS:
720 				DPRINTF(("100ns"));
721 				break;
722 			case PCMCIA_DSPEED_EXT:
723 				DPRINTF(("ext"));
724 				break;
725 			default:
726 				DPRINTF(("reserved"));
727 				break;
728 			}
729 		}
730 		DPRINTF(("\n"));
731 		break;
732 #endif
733 
734 	case PCMCIA_CISTPL_VERS_1:
735 		if (tuple->length < 6) {
736 			DPRINTF(("CISTPL_VERS_1 too short %d\n",
737 			    tuple->length));
738 			break;
739 		} {
740 			int start, i, ch, count;
741 
742 			state->card->cis1_major = pcmcia_tuple_read_1(tuple, 0);
743 			state->card->cis1_minor = pcmcia_tuple_read_1(tuple, 1);
744 
745 			for (count = 0, start = 0, i = 0;
746 			    (count < 4) && ((i + 4) < 256); i++) {
747 				ch = pcmcia_tuple_read_1(tuple, 2 + i);
748 				if (ch == 0xff)
749 					break;
750 				state->card->cis1_info_buf[i] = ch;
751 				if (ch == 0) {
752 					state->card->cis1_info[count] =
753 					    state->card->cis1_info_buf + start;
754 					start = i + 1;
755 					count++;
756 				}
757 			}
758 			DPRINTF(("CISTPL_VERS_1\n"));
759 		}
760 		break;
761 
762 	case PCMCIA_CISTPL_MANFID:
763 		if (tuple->length < 4) {
764 			DPRINTF(("CISTPL_MANFID too short %d\n",
765 			    tuple->length));
766 			break;
767 		}
768 		state->card->manufacturer = pcmcia_tuple_read_2(tuple, 0);
769 		state->card->product = pcmcia_tuple_read_2(tuple, 2);
770 		DPRINTF(("CISTPL_MANFID\n"));
771 		break;
772 
773 	case PCMCIA_CISTPL_FUNCID:
774 		if (tuple->length < 2) {
775 			DPRINTF(("CISTPL_FUNCID too short %d\n",
776 			    tuple->length));
777 			break;
778 		}
779 
780 		/*
781 		 * As far as I understand this, manufacturers do multifunction
782 		 * cards in various ways.  Sadly enough I do not have the
783 		 * PC-Card standard (donate!) so I can only guess what can
784 		 * be done.
785 		 * The original code implies FUNCID nodes are above CONFIG
786 		 * nodes in the CIS tree, however Xircom does it the other
787 		 * way round, which of course makes things a bit hard.
788 		 * --niklas@openbsd.org
789 		 */
790 		if (state->pf) {
791 			if (state->pf->function == PCMCIA_FUNCTION_UNSPEC) {
792 				/*
793 				 * This looks like a opportunistic function
794 				 * created by a CONFIG tuple.  Just keep it.
795 				 */
796 			} else {
797 				/*
798 				 * A function is being defined, end it.
799 				 */
800 				state->pf = NULL;
801 			}
802 		}
803 		if (state->pf == NULL) {
804 			state->pf = malloc(sizeof(*state->pf), M_DEVBUF,
805 			    M_NOWAIT);
806 			bzero(state->pf, sizeof(*state->pf));
807 			state->pf->number = state->count++;
808 			state->pf->last_config_index = -1;
809 			SIMPLEQ_INIT(&state->pf->cfe_head);
810 
811 			SIMPLEQ_INSERT_TAIL(&state->card->pf_head, state->pf,
812 			    pf_list);
813 		}
814 		state->pf->function = pcmcia_tuple_read_1(tuple, 0);
815 
816 		DPRINTF(("CISTPL_FUNCID\n"));
817 		break;
818 
819 	case PCMCIA_CISTPL_CONFIG:
820 		if (tuple->length < 5) {
821 			DPRINTF(("CISTPL_CONFIG too short %d\n",
822 			    tuple->length));
823 			break;
824 		} {
825 			u_int reg, rasz, rmsz, rfsz;
826 			int i;
827 
828 			reg = pcmcia_tuple_read_1(tuple, 0);
829 			rasz = 1 + ((reg & PCMCIA_TPCC_RASZ_MASK) >>
830 			    PCMCIA_TPCC_RASZ_SHIFT);
831 			rmsz = 1 + ((reg & PCMCIA_TPCC_RMSZ_MASK) >>
832 			    PCMCIA_TPCC_RMSZ_SHIFT);
833 			rfsz = ((reg & PCMCIA_TPCC_RFSZ_MASK) >>
834 			    PCMCIA_TPCC_RFSZ_SHIFT);
835 
836 			if (tuple->length < (rasz + rmsz + rfsz)) {
837 				DPRINTF(("CISTPL_CONFIG (%d,%d,%d) too "
838 				    "short %d\n", rasz, rmsz, rfsz,
839 				    tuple->length));
840 				break;
841 			}
842 			if (state->pf == NULL) {
843 				state->pf = malloc(sizeof(*state->pf),
844 				    M_DEVBUF, M_NOWAIT);
845 				bzero(state->pf, sizeof(*state->pf));
846 				state->pf->number = state->count++;
847 				state->pf->last_config_index = -1;
848 				SIMPLEQ_INIT(&state->pf->cfe_head);
849 
850 				SIMPLEQ_INSERT_TAIL(&state->card->pf_head,
851 				    state->pf, pf_list);
852 
853 				state->pf->function = PCMCIA_FUNCTION_UNSPEC;
854 			}
855 			state->pf->last_config_index =
856 			    pcmcia_tuple_read_1(tuple, 1);
857 
858 			state->pf->ccr_base = 0;
859 			for (i = 0; i < rasz; i++)
860 				state->pf->ccr_base |=
861 				    ((pcmcia_tuple_read_1(tuple, 2 + i)) <<
862 				    (i * 8));
863 
864 			state->pf->ccr_mask = 0;
865 			for (i = 0; i < rmsz; i++)
866 				state->pf->ccr_mask |=
867 				    ((pcmcia_tuple_read_1(tuple,
868 				    2 + rasz + i)) << (i * 8));
869 
870 			/* skip the reserved area and subtuples */
871 
872 			/* reset the default cfe for each cfe list */
873 			state->temp_cfe = init_cfe;
874 			state->default_cfe = &state->temp_cfe;
875 		}
876 		DPRINTF(("CISTPL_CONFIG\n"));
877 		break;
878 
879 	case PCMCIA_CISTPL_CFTABLE_ENTRY:
880 		if (tuple->length < 2) {
881 			DPRINTF(("CISTPL_CFTABLE_ENTRY too short %d\n",
882 			    tuple->length));
883 			break;
884 		} {
885 			int idx, i, j;
886 			u_int reg, reg2;
887 			u_int intface, def, num;
888 			u_int power, timing, iospace, irq, memspace, misc;
889 			struct pcmcia_config_entry *cfe;
890 
891 			idx = 0;
892 
893 			reg = pcmcia_tuple_read_1(tuple, idx);
894 			idx++;
895 			intface = reg & PCMCIA_TPCE_INDX_INTFACE;
896 			def = reg & PCMCIA_TPCE_INDX_DEFAULT;
897 			num = reg & PCMCIA_TPCE_INDX_NUM_MASK;
898 
899 			/*
900 			 * this is a little messy.  Some cards have only a
901 			 * cfentry with the default bit set.  So, as we go
902 			 * through the list, we add new indexes to the queue,
903 			 * and keep a pointer to the last one with the
904 			 * default bit set.  if we see a record with the same
905 			 * index, as the default, we stash the default and
906 			 * replace the queue entry. otherwise, we just add
907 			 * new entries to the queue, pointing the default ptr
908 			 * at them if the default bit is set.  if we get to
909 			 * the end with the default pointer pointing at a
910 			 * record which hasn't had a matching index, that's
911 			 * ok; it just becomes a cfentry like any other.
912 			 */
913 
914 			/*
915 			 * if the index in the cis differs from the default
916 			 * cis, create new entry in the queue and start it
917 			 * with the current default
918 			 */
919 			if (num != state->default_cfe->number) {
920 				cfe = (struct pcmcia_config_entry *)
921 				    malloc(sizeof(*cfe), M_DEVBUF, M_NOWAIT);
922 
923 				*cfe = *state->default_cfe;
924 
925 				SIMPLEQ_INSERT_TAIL(&state->pf->cfe_head,
926 				    cfe, cfe_list);
927 
928 				cfe->number = num;
929 
930 				/*
931 				 * if the default bit is set in the cis, then
932 				 * point the new default at whatever is being
933 				 * filled in
934 				 */
935 				if (def)
936 					state->default_cfe = cfe;
937 			} else {
938 				/*
939 				 * the cis index matches the default index,
940 				 * fill in the default cfentry.  It is
941 				 * assumed that the cfdefault index is in the
942 				 * queue.  For it to be otherwise, the cis
943 				 * index would have to be -1 (initial
944 				 * condition) which is not possible, or there
945 				 * would have to be a preceding cis entry
946 				 * which had the same cis index and had the
947 				 * default bit unset. Neither condition
948 				 * should happen.  If it does, this cfentry
949 				 * is lost (written into temp space), which
950 				 * is an acceptable failure mode.
951 				 */
952 
953 				cfe = state->default_cfe;
954 
955 				/*
956 				 * if the cis entry does not have the default
957 				 * bit set, copy the default out of the way
958 				 * first.
959 				 */
960 				if (!def) {
961 					state->temp_cfe = *state->default_cfe;
962 					state->default_cfe = &state->temp_cfe;
963 				}
964 			}
965 
966 			if (intface) {
967 				reg = pcmcia_tuple_read_1(tuple, idx);
968 				idx++;
969 				cfe->flags &= ~(PCMCIA_CFE_MWAIT_REQUIRED
970 				    | PCMCIA_CFE_RDYBSY_ACTIVE
971 				    | PCMCIA_CFE_WP_ACTIVE
972 				    | PCMCIA_CFE_BVD_ACTIVE);
973 				if (reg & PCMCIA_TPCE_IF_MWAIT)
974 					cfe->flags |= PCMCIA_CFE_MWAIT_REQUIRED;
975 				if (reg & PCMCIA_TPCE_IF_RDYBSY)
976 					cfe->flags |= PCMCIA_CFE_RDYBSY_ACTIVE;
977 				if (reg & PCMCIA_TPCE_IF_WP)
978 					cfe->flags |= PCMCIA_CFE_WP_ACTIVE;
979 				if (reg & PCMCIA_TPCE_IF_BVD)
980 					cfe->flags |= PCMCIA_CFE_BVD_ACTIVE;
981 				cfe->iftype = reg & PCMCIA_TPCE_IF_IFTYPE;
982 			}
983 			reg = pcmcia_tuple_read_1(tuple, idx);
984 			idx++;
985 
986 			power = reg & PCMCIA_TPCE_FS_POWER_MASK;
987 			timing = reg & PCMCIA_TPCE_FS_TIMING;
988 			iospace = reg & PCMCIA_TPCE_FS_IOSPACE;
989 			irq = reg & PCMCIA_TPCE_FS_IRQ;
990 			memspace = reg & PCMCIA_TPCE_FS_MEMSPACE_MASK;
991 			misc = reg & PCMCIA_TPCE_FS_MISC;
992 
993 			if (power) {
994 				/* skip over power, don't save */
995 				/* for each parameter selection byte */
996 				for (i = 0; i < power; i++) {
997 					reg = pcmcia_tuple_read_1(tuple, idx);
998 					idx++;
999 					/* for each bit */
1000 					for (j = 0; j < 7; j++) {
1001 						/* if the bit is set */
1002 						if ((reg >> j) & 0x01) {
1003 							/* skip over bytes */
1004 							do {
1005 								reg2 = pcmcia_tuple_read_1(tuple, idx);
1006 								idx++;
1007 								/*
1008 								 * until
1009 								 * non-extensi
1010 								 * on byte
1011 								 */
1012 							} while (reg2 & 0x80);
1013 						}
1014 					}
1015 				}
1016 			}
1017 			if (timing) {
1018 				/* skip over timing, don't save */
1019 				reg = pcmcia_tuple_read_1(tuple, idx);
1020 				idx++;
1021 
1022 				if ((reg & PCMCIA_TPCE_TD_RESERVED_MASK) !=
1023 				    PCMCIA_TPCE_TD_RESERVED_MASK)
1024 					idx++;
1025 				if ((reg & PCMCIA_TPCE_TD_RDYBSY_MASK) !=
1026 				    PCMCIA_TPCE_TD_RDYBSY_MASK)
1027 					idx++;
1028 				if ((reg & PCMCIA_TPCE_TD_WAIT_MASK) !=
1029 				    PCMCIA_TPCE_TD_WAIT_MASK)
1030 					idx++;
1031 			}
1032 			if (iospace) {
1033 				if (tuple->length <= idx) {
1034 					DPRINTF(("ran out of space before TPCE_IO\n"));
1035 
1036 					goto abort_cfe;
1037 				}
1038 
1039 				reg = pcmcia_tuple_read_1(tuple, idx);
1040 				idx++;
1041 
1042 				cfe->flags &=
1043 				    ~(PCMCIA_CFE_IO8 | PCMCIA_CFE_IO16);
1044 				if (reg & PCMCIA_TPCE_IO_BUSWIDTH_8BIT)
1045 					cfe->flags |= PCMCIA_CFE_IO8;
1046 				if (reg & PCMCIA_TPCE_IO_BUSWIDTH_16BIT)
1047 					cfe->flags |= PCMCIA_CFE_IO16;
1048 				cfe->iomask =
1049 				    reg & PCMCIA_TPCE_IO_IOADDRLINES_MASK;
1050 
1051 				if (reg & PCMCIA_TPCE_IO_HASRANGE) {
1052 					reg = pcmcia_tuple_read_1(tuple, idx);
1053 					idx++;
1054 
1055 					cfe->num_iospace = 1 + (reg &
1056 					    PCMCIA_TPCE_IO_RANGE_COUNT);
1057 
1058 					if (cfe->num_iospace >
1059 					    (sizeof(cfe->iospace) /
1060 					     sizeof(cfe->iospace[0]))) {
1061 						DPRINTF(("too many io "
1062 						    "spaces %d",
1063 						    cfe->num_iospace));
1064 						state->card->error++;
1065 						break;
1066 					}
1067 					for (i = 0; i < cfe->num_iospace; i++) {
1068 						switch (reg & PCMCIA_TPCE_IO_RANGE_ADDRSIZE_MASK) {
1069 						case PCMCIA_TPCE_IO_RANGE_ADDRSIZE_ONE:
1070 							cfe->iospace[i].start =
1071 								pcmcia_tuple_read_1(tuple, idx);
1072 							idx++;
1073 							break;
1074 						case PCMCIA_TPCE_IO_RANGE_ADDRSIZE_TWO:
1075 							cfe->iospace[i].start =
1076 								pcmcia_tuple_read_2(tuple, idx);
1077 							idx += 2;
1078 							break;
1079 						case PCMCIA_TPCE_IO_RANGE_ADDRSIZE_FOUR:
1080 							cfe->iospace[i].start =
1081 								pcmcia_tuple_read_4(tuple, idx);
1082 							idx += 4;
1083 							break;
1084 						}
1085 						switch (reg &
1086 							PCMCIA_TPCE_IO_RANGE_LENGTHSIZE_MASK) {
1087 						case PCMCIA_TPCE_IO_RANGE_LENGTHSIZE_ONE:
1088 							cfe->iospace[i].length =
1089 								pcmcia_tuple_read_1(tuple, idx);
1090 							idx++;
1091 							break;
1092 						case PCMCIA_TPCE_IO_RANGE_LENGTHSIZE_TWO:
1093 							cfe->iospace[i].length =
1094 								pcmcia_tuple_read_2(tuple, idx);
1095 							idx += 2;
1096 							break;
1097 						case PCMCIA_TPCE_IO_RANGE_LENGTHSIZE_FOUR:
1098 							cfe->iospace[i].length =
1099 								pcmcia_tuple_read_4(tuple, idx);
1100 							idx += 4;
1101 							break;
1102 						}
1103 						cfe->iospace[i].length++;
1104 					}
1105 				} else {
1106 					cfe->num_iospace = 1;
1107 					cfe->iospace[0].start = 0;
1108 					cfe->iospace[0].length =
1109 					    (1 << cfe->iomask);
1110 				}
1111 			}
1112 
1113 			if (irq) {
1114 				if (tuple->length <= idx) {
1115 					DPRINTF(("ran out of space before TPCE_IR\n"));
1116 
1117 					goto abort_cfe;
1118 				}
1119 
1120 				reg = pcmcia_tuple_read_1(tuple, idx);
1121 				idx++;
1122 
1123 				cfe->flags &= ~(PCMCIA_CFE_IRQSHARE
1124 				    | PCMCIA_CFE_IRQPULSE
1125 				    | PCMCIA_CFE_IRQLEVEL);
1126 				if (reg & PCMCIA_TPCE_IR_SHARE)
1127 					cfe->flags |= PCMCIA_CFE_IRQSHARE;
1128 				if (reg & PCMCIA_TPCE_IR_PULSE)
1129 					cfe->flags |= PCMCIA_CFE_IRQPULSE;
1130 				if (reg & PCMCIA_TPCE_IR_LEVEL)
1131 					cfe->flags |= PCMCIA_CFE_IRQLEVEL;
1132 
1133 				if (reg & PCMCIA_TPCE_IR_HASMASK) {
1134 					/*
1135 					 * it's legal to ignore the
1136 					 * special-interrupt bits, so I will
1137 					 */
1138 
1139 					cfe->irqmask =
1140 					    pcmcia_tuple_read_2(tuple, idx);
1141 					idx += 2;
1142 				} else {
1143 					cfe->irqmask =
1144 					    (1 << (reg & PCMCIA_TPCE_IR_IRQ));
1145 				}
1146 			}
1147 			if (memspace) {
1148 				if (tuple->length <= idx) {
1149 					DPRINTF(("ran out of space before TPCE_MS\n"));
1150 					goto abort_cfe;
1151 				}
1152 
1153 				if (memspace == PCMCIA_TPCE_FS_MEMSPACE_NONE) {
1154 					cfe->num_memspace = 0;
1155 				} else if (memspace == PCMCIA_TPCE_FS_MEMSPACE_LENGTH) {
1156 					cfe->num_memspace = 1;
1157 					cfe->memspace[0].length = 256 *
1158 					    pcmcia_tuple_read_2(tuple, idx);
1159 					idx += 2;
1160 					cfe->memspace[0].cardaddr = 0;
1161 					cfe->memspace[0].hostaddr = 0;
1162 				} else if (memspace ==
1163 				    PCMCIA_TPCE_FS_MEMSPACE_LENGTHADDR) {
1164 					cfe->num_memspace = 1;
1165 					cfe->memspace[0].length = 256 *
1166 					    pcmcia_tuple_read_2(tuple, idx);
1167 					idx += 2;
1168 					cfe->memspace[0].cardaddr = 256 *
1169 					    pcmcia_tuple_read_2(tuple, idx);
1170 					idx += 2;
1171 					cfe->memspace[0].hostaddr = cfe->memspace[0].cardaddr;
1172 				} else {
1173 					int lengthsize;
1174 					int cardaddrsize;
1175 					int hostaddrsize;
1176 
1177 					reg = pcmcia_tuple_read_1(tuple, idx);
1178 					idx++;
1179 
1180 					cfe->num_memspace = (reg &
1181 					    PCMCIA_TPCE_MS_COUNT) + 1;
1182 
1183 					if (cfe->num_memspace >
1184 					    (sizeof(cfe->memspace) /
1185 					     sizeof(cfe->memspace[0]))) {
1186 						DPRINTF(("too many mem "
1187 						    "spaces %d",
1188 						    cfe->num_memspace));
1189 						state->card->error++;
1190 						break;
1191 					}
1192 					lengthsize =
1193 						((reg & PCMCIA_TPCE_MS_LENGTH_SIZE_MASK) >>
1194 						 PCMCIA_TPCE_MS_LENGTH_SIZE_SHIFT);
1195 					cardaddrsize =
1196 						((reg & PCMCIA_TPCE_MS_CARDADDR_SIZE_MASK) >>
1197 						 PCMCIA_TPCE_MS_CARDADDR_SIZE_SHIFT);
1198 					hostaddrsize =
1199 						(reg & PCMCIA_TPCE_MS_HOSTADDR) ? cardaddrsize : 0;
1200 
1201 					if (lengthsize == 0) {
1202 						DPRINTF(("cfe memspace "
1203 						    "lengthsize == 0"));
1204 						state->card->error++;
1205 					}
1206 					for (i = 0; i < cfe->num_memspace; i++) {
1207 						if (lengthsize) {
1208 							cfe->memspace[i].length =
1209 								256 * pcmcia_tuple_read_n(tuple, lengthsize,
1210 								       idx);
1211 							idx += lengthsize;
1212 						} else {
1213 							cfe->memspace[i].length = 0;
1214 						}
1215 						if (cfe->memspace[i].length == 0) {
1216 							DPRINTF(("cfe->memspace[%d].length == 0",
1217 								 i));
1218 							state->card->error++;
1219 						}
1220 						if (cardaddrsize) {
1221 							cfe->memspace[i].cardaddr =
1222 								256 * pcmcia_tuple_read_n(tuple, cardaddrsize,
1223 								       idx);
1224 							idx += cardaddrsize;
1225 						} else {
1226 							cfe->memspace[i].cardaddr = 0;
1227 						}
1228 						if (hostaddrsize) {
1229 							cfe->memspace[i].hostaddr =
1230 								256 * pcmcia_tuple_read_n(tuple, hostaddrsize,
1231 								       idx);
1232 							idx += hostaddrsize;
1233 						} else {
1234 							cfe->memspace[i].hostaddr = 0;
1235 						}
1236 					}
1237 				}
1238 			}
1239 			if (misc) {
1240 				if (tuple->length <= idx) {
1241 					DPRINTF(("ran out of space before TPCE_MI\n"));
1242 
1243 					goto abort_cfe;
1244 				}
1245 
1246 				reg = pcmcia_tuple_read_1(tuple, idx);
1247 				idx++;
1248 
1249 				cfe->flags &= ~(PCMCIA_CFE_POWERDOWN
1250 				    | PCMCIA_CFE_READONLY
1251 				    | PCMCIA_CFE_AUDIO);
1252 				if (reg & PCMCIA_TPCE_MI_PWRDOWN)
1253 					cfe->flags |= PCMCIA_CFE_POWERDOWN;
1254 				if (reg & PCMCIA_TPCE_MI_READONLY)
1255 					cfe->flags |= PCMCIA_CFE_READONLY;
1256 				if (reg & PCMCIA_TPCE_MI_AUDIO)
1257 					cfe->flags |= PCMCIA_CFE_AUDIO;
1258 				cfe->maxtwins = reg & PCMCIA_TPCE_MI_MAXTWINS;
1259 
1260 				while (reg & PCMCIA_TPCE_MI_EXT) {
1261 					reg = pcmcia_tuple_read_1(tuple, idx);
1262 					idx++;
1263 				}
1264 			}
1265 			/* skip all the subtuples */
1266 		}
1267 
1268 	abort_cfe:
1269 		DPRINTF(("CISTPL_CFTABLE_ENTRY\n"));
1270 		break;
1271 
1272 	default:
1273 		DPRINTF(("unhandled CISTPL %x\n", tuple->code));
1274 		break;
1275 	}
1276 
1277 	return (0);
1278 }
1279