6324 Add an `ndp' tool for manipulating the neighbors table
[illumos-gate.git] / usr / src / uts / common / io / pcic.c
bloba05e7fa11282567d2c300cc2a15575c90040d4ac
1 /*
2 * CDDL HEADER START
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
19 * CDDL HEADER END
23 * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
24 * Use is subject to license terms.
28 * PCIC device/interrupt handler
29 * The "pcic" driver handles the Intel 82365SL, Cirrus Logic
30 * and Toshiba (and possibly other clones) PCMCIA adapter chip
31 * sets. It implements a subset of Socket Services as defined
32 * in the Solaris PCMCIA design documents
36 * currently defined "properties"
38 * clock-frequency bus clock frequency
39 * smi system management interrupt override
40 * need-mult-irq need status IRQ for each pair of sockets
41 * disable-audio don't route audio signal to speaker
45 #include <sys/types.h>
46 #include <sys/inttypes.h>
47 #include <sys/param.h>
48 #include <sys/systm.h>
49 #include <sys/user.h>
50 #include <sys/buf.h>
51 #include <sys/file.h>
52 #include <sys/uio.h>
53 #include <sys/conf.h>
54 #include <sys/stat.h>
55 #include <sys/autoconf.h>
56 #include <sys/vtoc.h>
57 #include <sys/dkio.h>
58 #include <sys/ddi.h>
59 #include <sys/sunddi.h>
60 #include <sys/sunndi.h>
61 #include <sys/var.h>
62 #include <sys/callb.h>
63 #include <sys/open.h>
64 #include <sys/ddidmareq.h>
65 #include <sys/dma_engine.h>
66 #include <sys/kstat.h>
67 #include <sys/kmem.h>
68 #include <sys/modctl.h>
69 #include <sys/pci.h>
70 #include <sys/pci_impl.h>
72 #include <sys/pctypes.h>
73 #include <sys/pcmcia.h>
74 #include <sys/sservice.h>
76 #include <sys/note.h>
78 #include <sys/pcic_reg.h>
79 #include <sys/pcic_var.h>
81 #if defined(__i386) || defined(__amd64)
82 #include <sys/pci_cfgspace.h>
83 #endif
85 #if defined(__sparc)
86 #include <sys/pci/pci_nexus.h>
87 #endif
89 #include <sys/hotplug/hpcsvc.h>
90 #include "cardbus/cardbus.h"
92 #define SOFTC_SIZE (sizeof (anp_t))
94 static int pcic_getinfo(dev_info_t *, ddi_info_cmd_t, void *, void **);
95 static int pcic_attach(dev_info_t *, ddi_attach_cmd_t);
96 static int pcic_detach(dev_info_t *, ddi_detach_cmd_t);
97 static int32_t pcic_quiesce(dev_info_t *);
98 static uint_t pcic_intr(caddr_t, caddr_t);
99 static int pcic_do_io_intr(pcicdev_t *, uint32_t);
100 static int pcic_probe(dev_info_t *);
102 static int pcic_open(dev_t *, int, int, cred_t *);
103 static int pcic_close(dev_t, int, int, cred_t *);
104 static int pcic_ioctl(dev_t, int, intptr_t, int, cred_t *, int *);
106 typedef struct pcm_regs pcm_regs_t;
108 static void pcic_init_assigned(dev_info_t *);
109 static int pcic_apply_avail_ranges(dev_info_t *, pcm_regs_t *,
110 pci_regspec_t *, int);
111 int pci_resource_setup_avail(dev_info_t *, pci_regspec_t *, int);
114 * On x86 platforms the ddi_iobp_alloc(9F) and ddi_mem_alloc(9F) calls
115 * are xlated into DMA ctlops. To make this nexus work on x86, we
116 * need to have the default ddi_dma_mctl ctlops in the bus_ops
117 * structure, just to pass the request to the parent. The correct
118 * ctlops should be ddi_no_dma_mctl because so far we don't do DMA.
120 static
121 struct bus_ops pcmciabus_ops = {
122 BUSO_REV,
123 pcmcia_bus_map,
124 NULL,
125 NULL,
126 NULL,
127 i_ddi_map_fault,
128 ddi_no_dma_map,
129 ddi_no_dma_allochdl,
130 ddi_no_dma_freehdl,
131 ddi_no_dma_bindhdl,
132 ddi_no_dma_unbindhdl,
133 ddi_no_dma_flush,
134 ddi_no_dma_win,
135 ddi_dma_mctl,
136 pcmcia_ctlops,
137 pcmcia_prop_op,
138 NULL, /* (*bus_get_eventcookie)(); */
139 NULL, /* (*bus_add_eventcall)(); */
140 NULL, /* (*bus_remove_eventcall)(); */
141 NULL, /* (*bus_post_event)(); */
142 NULL, /* (*bus_intr_ctl)(); */
143 NULL, /* (*bus_config)(); */
144 NULL, /* (*bus_unconfig)(); */
145 NULL, /* (*bus_fm_init)(); */
146 NULL, /* (*bus_fm_fini)(); */
147 NULL, /* (*bus_enter)() */
148 NULL, /* (*bus_exit)() */
149 NULL, /* (*bus_power)() */
150 pcmcia_intr_ops /* (*bus_intr_op)(); */
153 static struct cb_ops pcic_cbops = {
154 pcic_open,
155 pcic_close,
156 nodev,
157 nodev,
158 nodev,
159 nodev,
160 nodev,
161 pcic_ioctl,
162 nodev,
163 nodev,
164 nodev,
165 nochpoll,
166 ddi_prop_op,
167 NULL,
168 #ifdef CARDBUS
169 D_NEW | D_MP | D_HOTPLUG
170 #else
171 D_NEW | D_MP
172 #endif
175 static struct dev_ops pcic_devops = {
176 DEVO_REV,
178 pcic_getinfo,
179 nulldev,
180 pcic_probe,
181 pcic_attach,
182 pcic_detach,
183 nulldev,
184 &pcic_cbops,
185 &pcmciabus_ops,
186 NULL,
187 pcic_quiesce, /* devo_quiesce */
190 void *pcic_soft_state_p = NULL;
191 static int pcic_maxinst = -1;
193 int pcic_do_insertion = 1;
194 int pcic_do_removal = 1;
196 struct irqmap {
197 int irq;
198 int count;
199 } pcic_irq_map[16];
202 int pcic_debug = 0x0;
203 static void pcic_err(dev_info_t *dip, int level, const char *fmt, ...);
204 extern void cardbus_dump_pci_config(dev_info_t *dip);
205 extern void cardbus_dump_socket(dev_info_t *dip);
206 extern int cardbus_validate_iline(dev_info_t *dip, ddi_acc_handle_t handle);
207 static void pcic_dump_debqueue(char *msg);
209 #if defined(PCIC_DEBUG)
210 static void xxdmp_all_regs(pcicdev_t *, int, uint32_t);
212 #define pcic_mutex_enter(a) \
214 pcic_err(NULL, 10, "Set lock at %d\n", __LINE__); \
215 mutex_enter(a); \
218 #define pcic_mutex_exit(a) \
220 pcic_err(NULL, 10, "Clear lock at %d\n", __LINE__); \
221 mutex_exit(a); \
224 #else
225 #define pcic_mutex_enter(a) mutex_enter(a)
226 #define pcic_mutex_exit(a) mutex_exit(a)
227 #endif
229 #define PCIC_VCC_3VLEVEL 1
230 #define PCIC_VCC_5VLEVEL 2
231 #define PCIC_VCC_12LEVEL 3
233 /* bit patterns to select voltage levels */
234 int pcic_vpp_levels[13] = {
235 0, 0, 0,
236 1, /* 3.3V */
238 1, /* 5V */
239 0, 0, 0, 0, 0, 0,
240 2 /* 12V */
243 uint8_t pcic_cbv_levels[13] = {
244 0, 0, 0,
245 3, /* 3.3V */
247 2, /* 5V */
248 0, 0, 0, 0, 0, 0,
249 1 /* 12V */
252 struct power_entry pcic_power[4] = {
254 0, VCC|VPP1|VPP2
257 33, /* 3.3Volt */
258 VCC|VPP1|VPP2
261 5*10, /* 5Volt */
262 VCC|VPP1|VPP2 /* currently only know about this */
265 12*10, /* 12Volt */
266 VPP1|VPP2
271 * Base used to allocate ranges of PCI memory on x86 systems
272 * Each instance gets a chunk above the base that is used to map
273 * in the memory and I/O windows for that device.
274 * Pages below the base are also allocated for the EXCA registers,
275 * one per instance.
277 #define PCIC_PCI_MEMCHUNK 0x1000000
279 static int pcic_wait_insert_time = 5000000; /* In micro-seconds */
280 static int pcic_debounce_time = 200000; /* In micro-seconds */
282 struct debounce {
283 pcic_socket_t *pcs;
284 clock_t expire;
285 struct debounce *next;
288 static struct debounce *pcic_deb_queue = NULL;
289 static kmutex_t pcic_deb_mtx;
290 static kcondvar_t pcic_deb_cv;
291 static kthread_t *pcic_deb_threadid;
293 static inthandler_t *pcic_handlers;
295 static void pcic_setup_adapter(pcicdev_t *);
296 static int pcic_change(pcicdev_t *, int);
297 static int pcic_ll_reset(pcicdev_t *, int);
298 static void pcic_mswait(pcicdev_t *, int, int);
299 static boolean_t pcic_check_ready(pcicdev_t *, int);
300 static void pcic_set_cdtimers(pcicdev_t *, int, uint32_t, int);
301 static void pcic_ready_wait(pcicdev_t *, int);
302 extern int pcmcia_get_intr(dev_info_t *, int);
303 extern int pcmcia_return_intr(dev_info_t *, int);
304 extern void pcmcia_cb_suspended(int);
305 extern void pcmcia_cb_resumed(int);
307 static int pcic_callback(dev_info_t *, int (*)(), int);
308 static int pcic_inquire_adapter(dev_info_t *, inquire_adapter_t *);
309 static int pcic_get_adapter(dev_info_t *, get_adapter_t *);
310 static int pcic_get_page(dev_info_t *, get_page_t *);
311 static int pcic_get_socket(dev_info_t *, get_socket_t *);
312 static int pcic_get_status(dev_info_t *, get_ss_status_t *);
313 static int pcic_get_window(dev_info_t *, get_window_t *);
314 static int pcic_inquire_socket(dev_info_t *, inquire_socket_t *);
315 static int pcic_inquire_window(dev_info_t *, inquire_window_t *);
316 static int pcic_reset_socket(dev_info_t *, int, int);
317 static int pcic_set_page(dev_info_t *, set_page_t *);
318 static int pcic_set_window(dev_info_t *, set_window_t *);
319 static int pcic_set_socket(dev_info_t *, set_socket_t *);
320 static int pcic_set_interrupt(dev_info_t *, set_irq_handler_t *);
321 static int pcic_clear_interrupt(dev_info_t *, clear_irq_handler_t *);
322 static void pcic_pm_detection(void *);
323 static void pcic_iomem_pci_ctl(ddi_acc_handle_t, uchar_t *, unsigned);
324 static int clext_reg_read(pcicdev_t *, int, uchar_t);
325 static void clext_reg_write(pcicdev_t *, int, uchar_t, uchar_t);
326 static int pcic_calc_speed(pcicdev_t *, uint32_t);
327 static int pcic_card_state(pcicdev_t *, pcic_socket_t *);
328 static int pcic_find_pci_type(pcicdev_t *);
329 static void pcic_82092_smiirq_ctl(pcicdev_t *, int, int, int);
330 static void pcic_handle_cd_change(pcicdev_t *, pcic_socket_t *, uint8_t);
331 static uint_t pcic_cd_softint(caddr_t, caddr_t);
332 static uint8_t pcic_getb(pcicdev_t *, int, int);
333 static void pcic_putb(pcicdev_t *, int, int, int8_t);
334 static int pcic_set_vcc_level(pcicdev_t *, set_socket_t *);
335 static uint_t pcic_softintr(caddr_t, caddr_t);
337 static void pcic_debounce(pcic_socket_t *);
338 static void pcic_do_resume(pcicdev_t *);
339 static void *pcic_add_debqueue(pcic_socket_t *, int);
340 static void pcic_rm_debqueue(void *);
341 static void pcic_deb_thread();
343 static boolean_t pcic_load_cardbus(pcicdev_t *pcic, const pcic_socket_t *sockp);
344 static void pcic_unload_cardbus(pcicdev_t *pcic, const pcic_socket_t *sockp);
345 static uint32_t pcic_getcb(pcicdev_t *pcic, int reg);
346 static void pcic_putcb(pcicdev_t *pcic, int reg, uint32_t value);
347 static void pcic_cb_enable_intr(dev_info_t *);
348 static void pcic_cb_disable_intr(dev_info_t *);
349 static void pcic_enable_io_intr(pcicdev_t *pcic, int socket, int irq);
350 static void pcic_disable_io_intr(pcicdev_t *pcic, int socket);
352 static cb_nexus_cb_t pcic_cbnexus_ops = {
353 pcic_cb_enable_intr,
354 pcic_cb_disable_intr
357 static int pcic_exca_powerctl(pcicdev_t *pcic, int socket, int powerlevel);
358 static int pcic_cbus_powerctl(pcicdev_t *pcic, int socket);
360 #if defined(__sparc)
361 static int pcic_fault(enum pci_fault_ops op, void *arg);
362 #endif
366 * pcmcia interface operations structure
367 * this is the private interface that is exported to the nexus
369 pcmcia_if_t pcic_if_ops = {
370 PCIF_MAGIC,
371 PCIF_VERSION,
372 pcic_callback,
373 pcic_get_adapter,
374 pcic_get_page,
375 pcic_get_socket,
376 pcic_get_status,
377 pcic_get_window,
378 pcic_inquire_adapter,
379 pcic_inquire_socket,
380 pcic_inquire_window,
381 pcic_reset_socket,
382 pcic_set_page,
383 pcic_set_window,
384 pcic_set_socket,
385 pcic_set_interrupt,
386 pcic_clear_interrupt,
387 NULL,
391 * chip type identification routines
392 * this list of functions is searched until one of them succeeds
393 * or all fail. i82365SL is assumed if failed.
395 static int pcic_ci_cirrus(pcicdev_t *);
396 static int pcic_ci_vadem(pcicdev_t *);
397 static int pcic_ci_ricoh(pcicdev_t *);
399 int (*pcic_ci_funcs[])(pcicdev_t *) = {
400 pcic_ci_cirrus,
401 pcic_ci_vadem,
402 pcic_ci_ricoh,
403 NULL
406 static struct modldrv modldrv = {
407 &mod_driverops, /* Type of module. This one is a driver */
408 "PCIC PCMCIA adapter driver", /* Name of the module. */
409 &pcic_devops, /* driver ops */
412 static struct modlinkage modlinkage = {
413 MODREV_1, (void *)&modldrv, NULL
417 _init()
419 int stat;
421 /* Allocate soft state */
422 if ((stat = ddi_soft_state_init(&pcic_soft_state_p,
423 SOFTC_SIZE, 2)) != DDI_SUCCESS)
424 return (stat);
426 if ((stat = mod_install(&modlinkage)) != 0)
427 ddi_soft_state_fini(&pcic_soft_state_p);
429 return (stat);
433 _fini()
435 int stat = 0;
437 if ((stat = mod_remove(&modlinkage)) != 0)
438 return (stat);
440 if (pcic_deb_threadid) {
441 mutex_enter(&pcic_deb_mtx);
442 pcic_deb_threadid = 0;
443 while (!pcic_deb_threadid)
444 cv_wait(&pcic_deb_cv, &pcic_deb_mtx);
445 pcic_deb_threadid = 0;
446 mutex_exit(&pcic_deb_mtx);
448 mutex_destroy(&pcic_deb_mtx);
449 cv_destroy(&pcic_deb_cv);
452 ddi_soft_state_fini(&pcic_soft_state_p);
454 return (stat);
458 _info(struct modinfo *modinfop)
460 return (mod_info(&modlinkage, modinfop));
464 * pcic_getinfo()
465 * provide instance/device information about driver
467 /*ARGSUSED*/
468 static int
469 pcic_getinfo(dev_info_t *dip, ddi_info_cmd_t cmd, void *arg, void **result)
471 anp_t *anp;
472 int error = DDI_SUCCESS;
473 minor_t minor;
475 switch (cmd) {
476 case DDI_INFO_DEVT2DEVINFO:
477 minor = getminor((dev_t)arg);
478 minor &= 0x7f;
479 if (!(anp = ddi_get_soft_state(pcic_soft_state_p, minor)))
480 *result = NULL;
481 else
482 *result = anp->an_dip;
483 break;
484 case DDI_INFO_DEVT2INSTANCE:
485 minor = getminor((dev_t)arg);
486 minor &= 0x7f;
487 *result = (void *)((long)minor);
488 break;
489 default:
490 error = DDI_FAILURE;
491 break;
493 return (error);
496 static int
497 pcic_probe(dev_info_t *dip)
499 int value;
500 ddi_device_acc_attr_t attr;
501 ddi_acc_handle_t handle;
502 uchar_t *index, *data;
504 if (ddi_dev_is_sid(dip) == DDI_SUCCESS)
505 return (DDI_PROBE_DONTCARE);
508 * find a PCIC device (any vendor)
509 * while there can be up to 4 such devices in
510 * a system, we currently only look for 1
511 * per probe. There will be up to 2 chips per
512 * instance since they share I/O space
514 attr.devacc_attr_version = DDI_DEVICE_ATTR_V0;
515 attr.devacc_attr_endian_flags = DDI_NEVERSWAP_ACC;
516 attr.devacc_attr_dataorder = DDI_STRICTORDER_ACC;
518 if (ddi_regs_map_setup(dip, PCIC_ISA_CONTROL_REG_NUM,
519 (caddr_t *)&index,
520 PCIC_ISA_CONTROL_REG_OFFSET,
521 PCIC_ISA_CONTROL_REG_LENGTH,
522 &attr, &handle) != DDI_SUCCESS)
523 return (DDI_PROBE_FAILURE);
525 data = index + 1;
527 #if defined(PCIC_DEBUG)
528 if (pcic_debug)
529 cmn_err(CE_CONT, "pcic_probe: entered\n");
530 if (pcic_debug)
531 cmn_err(CE_CONT, "\tindex=%p\n", (void *)index);
532 #endif
533 ddi_put8(handle, index, PCIC_CHIP_REVISION);
534 ddi_put8(handle, data, 0);
535 value = ddi_get8(handle, data);
536 #if defined(PCIC_DEBUG)
537 if (pcic_debug)
538 cmn_err(CE_CONT, "\tchip revision register = %x\n", value);
539 #endif
540 if ((value & PCIC_REV_MASK) >= PCIC_REV_LEVEL_LOW &&
541 (value & 0x30) == 0) {
543 * we probably have a PCIC chip in the system
544 * do a little more checking. If we find one,
545 * reset everything in case of softboot
547 ddi_put8(handle, index, PCIC_MAPPING_ENABLE);
548 ddi_put8(handle, data, 0);
549 value = ddi_get8(handle, data);
550 #if defined(PCIC_DEBUG)
551 if (pcic_debug)
552 cmn_err(CE_CONT, "\tzero test = %x\n", value);
553 #endif
554 /* should read back as zero */
555 if (value == 0) {
557 * we do have one and it is off the bus
559 #if defined(PCIC_DEBUG)
560 if (pcic_debug)
561 cmn_err(CE_CONT, "pcic_probe: success\n");
562 #endif
563 ddi_regs_map_free(&handle);
564 return (DDI_PROBE_SUCCESS);
567 #if defined(PCIC_DEBUG)
568 if (pcic_debug)
569 cmn_err(CE_CONT, "pcic_probe: failed\n");
570 #endif
571 ddi_regs_map_free(&handle);
572 return (DDI_PROBE_FAILURE);
576 * These are just defaults they can also be changed via a property in the
577 * conf file.
579 static int pci_config_reg_num = PCIC_PCI_CONFIG_REG_NUM;
580 static int pci_control_reg_num = PCIC_PCI_CONTROL_REG_NUM;
581 static int pcic_do_pcmcia_sr = 1;
582 static int pcic_use_cbpwrctl = PCF_CBPWRCTL;
585 * enable insertion/removal interrupt for 32bit cards
587 static int
588 cardbus_enable_cd_intr(dev_info_t *dip)
590 ddi_acc_handle_t iohandle;
591 caddr_t ioaddr;
592 ddi_device_acc_attr_t attr;
593 attr.devacc_attr_version = DDI_DEVICE_ATTR_V0;
594 attr.devacc_attr_endian_flags = DDI_STRUCTURE_LE_ACC;
595 attr.devacc_attr_dataorder = DDI_STRICTORDER_ACC;
596 (void) ddi_regs_map_setup(dip, 1,
597 (caddr_t *)&ioaddr,
599 4096,
600 &attr, &iohandle);
602 /* CSC Interrupt: Card detect interrupt on */
603 ddi_put32(iohandle, (uint32_t *)(ioaddr+CB_STATUS_MASK),
604 ddi_get32(iohandle,
605 (uint32_t *)(ioaddr+CB_STATUS_MASK)) | CB_SE_CCDMASK);
607 ddi_put32(iohandle, (uint32_t *)(ioaddr+CB_STATUS_EVENT),
608 ddi_get32(iohandle, (uint32_t *)(ioaddr+CB_STATUS_EVENT)));
610 ddi_regs_map_free(&iohandle);
611 return (1);
615 * quiesce(9E) entry point.
617 * This function is called when the system is single-threaded at high
618 * PIL with preemption disabled. Therefore, this function must not be
619 * blocked.
621 * This function returns DDI_SUCCESS on success, or DDI_FAILURE on failure.
622 * DDI_FAILURE indicates an error condition and should almost never happen.
624 static int32_t
625 pcic_quiesce(dev_info_t *dip)
627 anp_t *anp = ddi_get_driver_private(dip);
628 pcicdev_t *pcic = anp->an_private;
629 int i;
631 for (i = 0; i < pcic->pc_numsockets; i++) {
632 pcic_putb(pcic, i, PCIC_MANAGEMENT_INT, 0);
633 pcic_putb(pcic, i, PCIC_CARD_DETECT, 0);
634 pcic_putb(pcic, i, PCIC_MAPPING_ENABLE, 0);
635 /* disable interrupts and put card into RESET */
636 pcic_putb(pcic, i, PCIC_INTERRUPT, 0);
637 /* poweroff socket */
638 pcic_putb(pcic, i, PCIC_POWER_CONTROL, 0);
639 pcic_putcb(pcic, CB_CONTROL, 0);
642 return (DDI_SUCCESS);
646 * pcic_attach()
647 * attach the PCIC (Intel 82365SL/CirrusLogic/Toshiba) driver
648 * to the system. This is a child of "sysbus" since that is where
649 * the hardware lives, but it provides services to the "pcmcia"
650 * nexus driver. It gives a pointer back via its private data
651 * structure which contains both the dip and socket services entry
652 * points
654 static int
655 pcic_attach(dev_info_t *dip, ddi_attach_cmd_t cmd)
657 anp_t *pcic_nexus;
658 pcicdev_t *pcic;
659 int irqlevel, value;
660 int pci_cfrn, pci_ctrn;
661 int i, j, smi, actual;
662 char *typename;
663 char bus_type[16] = "(unknown)";
664 int len = sizeof (bus_type);
665 ddi_device_acc_attr_t attr;
666 anp_t *anp = ddi_get_driver_private(dip);
667 uint_t pri;
669 #if defined(PCIC_DEBUG)
670 if (pcic_debug) {
671 cmn_err(CE_CONT, "pcic_attach: entered\n");
673 #endif
674 switch (cmd) {
675 case DDI_ATTACH:
676 break;
677 case DDI_RESUME:
678 pcic = anp->an_private;
680 * for now, this is a simulated resume.
681 * a real one may need different things.
683 if (pcic != NULL && pcic->pc_flags & PCF_SUSPENDED) {
684 mutex_enter(&pcic->pc_lock);
685 /* should probe for new sockets showing up */
686 pcic_setup_adapter(pcic);
687 pcic->pc_flags &= ~PCF_SUSPENDED;
688 mutex_exit(&pcic->pc_lock);
689 (void) pcmcia_begin_resume(dip);
691 pcic_do_resume(pcic);
692 #ifdef CARDBUS
693 cardbus_restore_children(ddi_get_child(dip));
694 #endif
697 * for complete implementation need END_RESUME (later)
699 return (DDI_SUCCESS);
702 return (DDI_SUCCESS);
703 default:
704 return (DDI_FAILURE);
708 * Allocate soft state associated with this instance.
710 if (ddi_soft_state_zalloc(pcic_soft_state_p,
711 ddi_get_instance(dip)) != DDI_SUCCESS) {
712 cmn_err(CE_CONT, "pcic%d: Unable to alloc state\n",
713 ddi_get_instance(dip));
714 return (DDI_FAILURE);
717 pcic_nexus = ddi_get_soft_state(pcic_soft_state_p,
718 ddi_get_instance(dip));
720 pcic = kmem_zalloc(sizeof (pcicdev_t), KM_SLEEP);
722 pcic->dip = dip;
723 pcic_nexus->an_dip = dip;
724 pcic_nexus->an_if = &pcic_if_ops;
725 pcic_nexus->an_private = pcic;
726 pcic->pc_numpower = sizeof (pcic_power)/sizeof (pcic_power[0]);
727 pcic->pc_power = pcic_power;
729 pci_ctrn = ddi_getprop(DDI_DEV_T_ANY, dip, DDI_PROP_CANSLEEP,
730 "pci-control-reg-number", pci_control_reg_num);
731 pci_cfrn = ddi_getprop(DDI_DEV_T_ANY, dip, DDI_PROP_CANSLEEP,
732 "pci-config-reg-number", pci_config_reg_num);
734 ddi_set_driver_private(dip, pcic_nexus);
737 * pcic->pc_irq is really the IPL level we want to run at
738 * set the default values here and override from intr spec
740 pcic->pc_irq = ddi_getprop(DDI_DEV_T_ANY, dip, DDI_PROP_CANSLEEP,
741 "interrupt-priorities", -1);
743 if (pcic->pc_irq == -1) {
744 int actual;
745 uint_t pri;
746 ddi_intr_handle_t hdl;
748 /* see if intrspec tells us different */
749 if (ddi_intr_alloc(dip, &hdl, DDI_INTR_TYPE_FIXED,
750 0, 1, &actual, DDI_INTR_ALLOC_NORMAL) == DDI_SUCCESS) {
751 if (ddi_intr_get_pri(hdl, &pri) == DDI_SUCCESS)
752 pcic->pc_irq = pri;
753 else
754 pcic->pc_irq = LOCK_LEVEL + 1;
755 (void) ddi_intr_free(hdl);
758 pcic_nexus->an_ipl = pcic->pc_irq;
761 * Check our parent bus type. We do different things based on which
762 * bus we're on.
764 if (ddi_prop_op(DDI_DEV_T_ANY, ddi_get_parent(dip),
765 PROP_LEN_AND_VAL_BUF, DDI_PROP_CANSLEEP,
766 "device_type", (caddr_t)&bus_type[0], &len) !=
767 DDI_PROP_SUCCESS) {
768 if (ddi_prop_op(DDI_DEV_T_ANY, ddi_get_parent(dip),
769 PROP_LEN_AND_VAL_BUF, DDI_PROP_CANSLEEP,
770 "bus-type", (caddr_t)&bus_type[0], &len) !=
771 DDI_PROP_SUCCESS) {
773 cmn_err(CE_CONT,
774 "pcic%d: can't find parent bus type\n",
775 ddi_get_instance(dip));
777 kmem_free(pcic, sizeof (pcicdev_t));
778 ddi_soft_state_free(pcic_soft_state_p,
779 ddi_get_instance(dip));
780 return (DDI_FAILURE);
782 } /* ddi_prop_op("device_type") */
784 if (strcmp(bus_type, DEVI_PCI_NEXNAME) == 0 ||
785 strcmp(bus_type, DEVI_PCIEX_NEXNAME) == 0) {
786 pcic->pc_flags = PCF_PCIBUS;
787 } else {
788 cmn_err(CE_WARN, "!pcic%d: non-pci mode (%s) not supported, "
789 "set BIOS to yenta mode if applicable\n",
790 ddi_get_instance(dip), bus_type);
791 kmem_free(pcic, sizeof (pcicdev_t));
792 ddi_soft_state_free(pcic_soft_state_p,
793 ddi_get_instance(dip));
794 return (DDI_FAILURE);
797 if ((pcic->bus_speed = ddi_getprop(DDI_DEV_T_ANY, ddi_get_parent(dip),
798 DDI_PROP_CANSLEEP,
799 "clock-frequency", 0)) == 0) {
800 if (pcic->pc_flags & PCF_PCIBUS)
801 pcic->bus_speed = PCIC_PCI_DEF_SYSCLK;
802 else
803 pcic->bus_speed = PCIC_ISA_DEF_SYSCLK;
804 } else {
806 * OBP can declare the speed in Hz...
808 if (pcic->bus_speed > 1000000)
809 pcic->bus_speed /= 1000000;
810 } /* ddi_prop_op("clock-frequency") */
812 pcic->pc_io_type = PCIC_IO_TYPE_82365SL; /* default mode */
814 #ifdef PCIC_DEBUG
815 if (pcic_debug) {
816 cmn_err(CE_CONT,
817 "pcic%d: parent bus type = [%s], speed = %d MHz\n",
818 ddi_get_instance(dip),
819 bus_type, pcic->bus_speed);
821 #endif
824 * The reg properties on a PCI node are different than those
825 * on a non-PCI node. Handle that difference here.
826 * If it turns out to be a CardBus chip, we have even more
827 * differences.
829 if (pcic->pc_flags & PCF_PCIBUS) {
830 int class_code;
831 #if defined(__i386) || defined(__amd64)
832 pcic->pc_base = 0x1000000;
833 pcic->pc_bound = (uint32_t)~0;
834 pcic->pc_iobase = 0x1000;
835 pcic->pc_iobound = 0xefff;
836 #elif defined(__sparc)
837 pcic->pc_base = 0x0;
838 pcic->pc_bound = (uint32_t)~0;
839 pcic->pc_iobase = 0x00000;
840 pcic->pc_iobound = 0xffff;
841 #endif
843 /* usually need to get at config space so map first */
844 attr.devacc_attr_version = DDI_DEVICE_ATTR_V0;
845 attr.devacc_attr_endian_flags = DDI_STRUCTURE_LE_ACC;
846 attr.devacc_attr_dataorder = DDI_STRICTORDER_ACC;
848 if (ddi_regs_map_setup(dip, pci_cfrn,
849 (caddr_t *)&pcic->cfgaddr,
850 PCIC_PCI_CONFIG_REG_OFFSET,
851 PCIC_PCI_CONFIG_REG_LENGTH,
852 &attr,
853 &pcic->cfg_handle) !=
854 DDI_SUCCESS) {
855 cmn_err(CE_CONT,
856 "pcic%d: unable to map config space"
857 "regs\n",
858 ddi_get_instance(dip));
860 kmem_free(pcic, sizeof (pcicdev_t));
861 return (DDI_FAILURE);
862 } /* ddi_regs_map_setup */
864 class_code = ddi_getprop(DDI_DEV_T_ANY, dip,
865 DDI_PROP_CANSLEEP|DDI_PROP_DONTPASS,
866 "class-code", -1);
867 #ifdef PCIC_DEBUG
868 if (pcic_debug) {
869 cmn_err(CE_CONT, "pcic_attach class_code=%x\n",
870 class_code);
872 #endif
874 switch (class_code) {
875 case PCIC_PCI_CARDBUS:
876 pcic->pc_flags |= PCF_CARDBUS;
877 pcic->pc_io_type = PCIC_IO_TYPE_YENTA;
879 * Get access to the adapter registers on the
880 * PCI bus. A 4K memory page
882 #if defined(PCIC_DEBUG)
883 pcic_err(dip, 8, "Is Cardbus device\n");
884 if (pcic_debug) {
885 int nr;
886 long rs;
887 (void) ddi_dev_nregs(dip, &nr);
888 pcic_err(dip, 9, "\tdev, cfgaddr 0x%p,"
889 "cfghndl 0x%p nregs %d",
890 (void *)pcic->cfgaddr,
891 (void *)pcic->cfg_handle, nr);
893 (void) ddi_dev_regsize(dip,
894 PCIC_PCI_CONTROL_REG_NUM, &rs);
896 pcic_err(dip, 9, "\tsize of reg %d is 0x%x\n",
897 PCIC_PCI_CONTROL_REG_NUM, (int)rs);
899 #endif
900 attr.devacc_attr_version = DDI_DEVICE_ATTR_V0;
901 attr.devacc_attr_endian_flags = DDI_STRUCTURE_LE_ACC;
902 attr.devacc_attr_dataorder = DDI_STRICTORDER_ACC;
904 if (ddi_regs_map_setup(dip, pci_ctrn,
905 (caddr_t *)&pcic->ioaddr,
906 PCIC_PCI_CONTROL_REG_OFFSET,
907 PCIC_CB_CONTROL_REG_LENGTH,
908 &attr, &pcic->handle) !=
909 DDI_SUCCESS) {
910 cmn_err(CE_CONT,
911 "pcic%d: unable to map PCI regs\n",
912 ddi_get_instance(dip));
913 ddi_regs_map_free(&pcic->cfg_handle);
914 kmem_free(pcic, sizeof (pcicdev_t));
915 return (DDI_FAILURE);
916 } /* ddi_regs_map_setup */
919 * Find out the chip type - If we're on a PCI bus,
920 * the adapter has that information in the PCI
921 * config space.
922 * Note that we call pcic_find_pci_type here since
923 * it needs a valid mapped pcic->handle to
924 * access some of the adapter registers in
925 * some cases.
927 if (pcic_find_pci_type(pcic) != DDI_SUCCESS) {
928 ddi_regs_map_free(&pcic->handle);
929 ddi_regs_map_free(&pcic->cfg_handle);
930 kmem_free(pcic, sizeof (pcicdev_t));
931 cmn_err(CE_WARN, "pcic: %s: unsupported "
932 "bridge\n", ddi_get_name_addr(dip));
933 return (DDI_FAILURE);
935 break;
937 default:
938 case PCIC_PCI_PCMCIA:
940 * Get access to the adapter IO registers on the
941 * PCI bus config space.
943 attr.devacc_attr_version = DDI_DEVICE_ATTR_V0;
944 attr.devacc_attr_endian_flags = DDI_STRUCTURE_LE_ACC;
945 attr.devacc_attr_dataorder = DDI_STRICTORDER_ACC;
948 * We need a default mapping to the adapter's IO
949 * control register space. For most adapters
950 * that are of class PCIC_PCI_PCMCIA (or of
951 * a default class) the control registers
952 * will be using the 82365-type control/data
953 * format.
955 if (ddi_regs_map_setup(dip, pci_ctrn,
956 (caddr_t *)&pcic->ioaddr,
957 PCIC_PCI_CONTROL_REG_OFFSET,
958 PCIC_PCI_CONTROL_REG_LENGTH,
959 &attr,
960 &pcic->handle) != DDI_SUCCESS) {
961 cmn_err(CE_CONT,
962 "pcic%d: unable to map PCI regs\n",
963 ddi_get_instance(dip));
964 ddi_regs_map_free(&pcic->cfg_handle);
965 kmem_free(pcic, sizeof (pcicdev_t));
966 return (DDI_FAILURE);
967 } /* ddi_regs_map_setup */
970 * Find out the chip type - If we're on a PCI bus,
971 * the adapter has that information in the PCI
972 * config space.
973 * Note that we call pcic_find_pci_type here since
974 * it needs a valid mapped pcic->handle to
975 * access some of the adapter registers in
976 * some cases.
978 if (pcic_find_pci_type(pcic) != DDI_SUCCESS) {
979 ddi_regs_map_free(&pcic->handle);
980 ddi_regs_map_free(&pcic->cfg_handle);
981 kmem_free(pcic, sizeof (pcicdev_t));
982 cmn_err(CE_WARN, "pcic: %s: unsupported "
983 "bridge\n",
984 ddi_get_name_addr(dip));
985 return (DDI_FAILURE);
989 * Some PCI-PCMCIA(R2) adapters are Yenta-compliant
990 * for extended registers even though they are
991 * not CardBus adapters. For those adapters,
992 * re-map pcic->handle to be large enough to
993 * encompass the Yenta registers.
995 switch (pcic->pc_type) {
996 case PCIC_TI_PCI1031:
997 ddi_regs_map_free(&pcic->handle);
999 if (ddi_regs_map_setup(dip,
1000 PCIC_PCI_CONTROL_REG_NUM,
1001 (caddr_t *)&pcic->ioaddr,
1002 PCIC_PCI_CONTROL_REG_OFFSET,
1003 PCIC_CB_CONTROL_REG_LENGTH,
1004 &attr,
1005 &pcic->handle) != DDI_SUCCESS) {
1006 cmn_err(CE_CONT,
1007 "pcic%d: unable to map "
1008 "PCI regs\n",
1009 ddi_get_instance(dip));
1010 ddi_regs_map_free(&pcic->cfg_handle);
1011 kmem_free(pcic, sizeof (pcicdev_t));
1012 return (DDI_FAILURE);
1013 } /* ddi_regs_map_setup */
1014 break;
1015 default:
1016 break;
1017 } /* switch (pcic->pc_type) */
1018 break;
1019 } /* switch (class_code) */
1020 } else {
1022 * We're not on a PCI bus, so assume an ISA bus type
1023 * register property. Get access to the adapter IO
1024 * registers on a non-PCI bus.
1026 attr.devacc_attr_version = DDI_DEVICE_ATTR_V0;
1027 attr.devacc_attr_endian_flags = DDI_NEVERSWAP_ACC;
1028 attr.devacc_attr_dataorder = DDI_STRICTORDER_ACC;
1029 pcic->mem_reg_num = PCIC_ISA_MEM_REG_NUM;
1030 pcic->io_reg_num = PCIC_ISA_IO_REG_NUM;
1032 if (ddi_regs_map_setup(dip, PCIC_ISA_CONTROL_REG_NUM,
1033 (caddr_t *)&pcic->ioaddr,
1034 PCIC_ISA_CONTROL_REG_OFFSET,
1035 PCIC_ISA_CONTROL_REG_LENGTH,
1036 &attr,
1037 &pcic->handle) != DDI_SUCCESS) {
1038 cmn_err(CE_CONT,
1039 "pcic%d: unable to map ISA registers\n",
1040 ddi_get_instance(dip));
1042 kmem_free(pcic, sizeof (pcicdev_t));
1043 return (DDI_FAILURE);
1044 } /* ddi_regs_map_setup */
1046 /* ISA bus is limited to 24-bits, but not first 640K */
1047 pcic->pc_base = 0xd0000;
1048 pcic->pc_bound = (uint32_t)~0;
1049 pcic->pc_iobase = 0x1000;
1050 pcic->pc_iobound = 0xefff;
1051 } /* !PCF_PCIBUS */
1053 #ifdef PCIC_DEBUG
1054 if (pcic_debug) {
1055 cmn_err(CE_CONT, "pcic_attach pc_flags=%x pc_type=%x\n",
1056 pcic->pc_flags, pcic->pc_type);
1058 #endif
1061 * Setup various adapter registers for the PCI case. For the
1062 * non-PCI case, find out the chip type.
1064 if (pcic->pc_flags & PCF_PCIBUS) {
1065 int iline;
1066 #if defined(__sparc)
1067 iline = 0;
1068 #else
1069 iline = cardbus_validate_iline(dip, pcic->cfg_handle);
1070 #endif
1072 /* set flags and socket counts based on chip type */
1073 switch (pcic->pc_type) {
1074 uint32_t cfg;
1075 case PCIC_INTEL_i82092:
1076 cfg = ddi_get8(pcic->cfg_handle,
1077 pcic->cfgaddr + PCIC_82092_PCICON);
1078 /* we can only support 4 Socket version */
1079 if (cfg & PCIC_82092_4_SOCKETS) {
1080 pcic->pc_numsockets = 4;
1081 pcic->pc_type = PCIC_INTEL_i82092;
1082 if (iline != 0xFF)
1083 pcic->pc_intr_mode =
1084 PCIC_INTR_MODE_PCI_1;
1085 else
1086 pcic->pc_intr_mode = PCIC_INTR_MODE_ISA;
1087 } else {
1088 cmn_err(CE_CONT,
1089 "pcic%d: Intel 82092 adapter "
1090 "in unsupported configuration: 0x%x",
1091 ddi_get_instance(pcic->dip), cfg);
1092 pcic->pc_numsockets = 0;
1093 } /* PCIC_82092_4_SOCKETS */
1094 break;
1095 case PCIC_CL_PD6730:
1096 case PCIC_CL_PD6729:
1097 pcic->pc_intr_mode = PCIC_INTR_MODE_PCI_1;
1098 cfg = ddi_getprop(DDI_DEV_T_ANY, dip,
1099 DDI_PROP_CANSLEEP,
1100 "interrupts", 0);
1101 /* if not interrupt pin then must use ISA style IRQs */
1102 if (cfg == 0 || iline == 0xFF)
1103 pcic->pc_intr_mode = PCIC_INTR_MODE_ISA;
1104 else {
1106 * we have the option to use PCI interrupts.
1107 * this might not be optimal but in some cases
1108 * is the only thing possible (sparc case).
1109 * we now deterine what is possible.
1111 pcic->pc_intr_mode = PCIC_INTR_MODE_PCI_1;
1113 pcic->pc_numsockets = 2;
1114 pcic->pc_flags |= PCF_IO_REMAP;
1115 break;
1116 case PCIC_TI_PCI1031:
1117 /* this chip doesn't do CardBus but looks like one */
1118 pcic->pc_flags &= ~PCF_CARDBUS;
1119 /* FALLTHROUGH */
1120 default:
1121 pcic->pc_flags |= PCF_IO_REMAP;
1122 /* FALLTHROUGH */
1123 /* indicate feature even if not supported */
1124 pcic->pc_flags |= PCF_DMA | PCF_ZV;
1125 /* Not sure if these apply to all these chips */
1126 pcic->pc_flags |= (PCF_VPPX|PCF_33VCAP);
1127 pcic->pc_flags |= pcic_use_cbpwrctl;
1129 pcic->pc_numsockets = 1; /* one per function */
1130 if (iline != 0xFF) {
1131 uint8_t cfg;
1132 pcic->pc_intr_mode = PCIC_INTR_MODE_PCI_1;
1134 cfg = ddi_get8(pcic->cfg_handle,
1135 (pcic->cfgaddr + PCIC_BRIDGE_CTL_REG));
1136 cfg &= (~PCIC_FUN_INT_MOD_ISA);
1137 ddi_put8(pcic->cfg_handle, (pcic->cfgaddr +
1138 PCIC_BRIDGE_CTL_REG), cfg);
1140 else
1141 pcic->pc_intr_mode = PCIC_INTR_MODE_ISA;
1142 pcic->pc_io_type = PCIC_IOTYPE_YENTA;
1143 break;
1145 } else {
1147 * We're not on a PCI bus so do some more
1148 * checking for adapter type here.
1149 * For the non-PCI bus case:
1150 * It could be any one of a number of different chips
1151 * If we can't determine anything else, it is assumed
1152 * to be an Intel 82365SL. The Cirrus Logic PD6710
1153 * has an extension register that provides unique
1154 * identification. Toshiba chip isn't detailed as yet.
1157 /* Init the CL id mode */
1158 pcic_putb(pcic, 0, PCIC_CHIP_INFO, 0);
1159 value = pcic_getb(pcic, 0, PCIC_CHIP_INFO);
1161 /* default to Intel i82365SL and then refine */
1162 pcic->pc_type = PCIC_I82365SL;
1163 pcic->pc_chipname = PCIC_TYPE_I82365SL;
1164 for (value = 0; pcic_ci_funcs[value] != NULL; value++) {
1165 /* go until one succeeds or none left */
1166 if (pcic_ci_funcs[value](pcic))
1167 break;
1170 /* any chip specific flags get set here */
1171 switch (pcic->pc_type) {
1172 case PCIC_CL_PD6722:
1173 pcic->pc_flags |= PCF_DMA;
1176 for (i = 0; i < PCIC_MAX_SOCKETS; i++) {
1178 * look for total number of sockets.
1179 * basically check each possible socket for
1180 * presence like in probe
1183 /* turn all windows off */
1184 pcic_putb(pcic, i, PCIC_MAPPING_ENABLE, 0);
1185 value = pcic_getb(pcic, i, PCIC_MAPPING_ENABLE);
1188 * if a zero is read back, then this socket
1189 * might be present. It would be except for
1190 * some systems that map the secondary PCIC
1191 * chip space back to the first.
1193 if (value != 0) {
1194 /* definitely not so skip */
1195 /* note: this is for Compaq support */
1196 continue;
1199 /* further tests */
1200 value = pcic_getb(pcic, i, PCIC_CHIP_REVISION) &
1201 PCIC_REV_MASK;
1202 if (!(value >= PCIC_REV_LEVEL_LOW &&
1203 value <= PCIC_REV_LEVEL_HI))
1204 break;
1206 pcic_putb(pcic, i, PCIC_SYSMEM_0_STARTLOW, 0xaa);
1207 pcic_putb(pcic, i, PCIC_SYSMEM_1_STARTLOW, 0x55);
1208 value = pcic_getb(pcic, i, PCIC_SYSMEM_0_STARTLOW);
1210 j = pcic_getb(pcic, i, PCIC_SYSMEM_1_STARTLOW);
1211 if (value != 0xaa || j != 0x55)
1212 break;
1215 * at this point we know if we have hardware
1216 * of some type and not just the bus holding
1217 * a pattern for us. We still have to determine
1218 * the case where more than 2 sockets are
1219 * really the same due to peculiar mappings of
1220 * hardware.
1222 j = pcic->pc_numsockets++;
1223 pcic->pc_sockets[j].pcs_flags = 0;
1224 pcic->pc_sockets[j].pcs_io = pcic->ioaddr;
1225 pcic->pc_sockets[j].pcs_socket = i;
1227 /* put PC Card into RESET, just in case */
1228 value = pcic_getb(pcic, i, PCIC_INTERRUPT);
1229 pcic_putb(pcic, i, PCIC_INTERRUPT,
1230 value & ~PCIC_RESET);
1233 #if defined(PCIC_DEBUG)
1234 if (pcic_debug)
1235 cmn_err(CE_CONT, "num sockets = %d\n",
1236 pcic->pc_numsockets);
1237 #endif
1238 if (pcic->pc_numsockets == 0) {
1239 ddi_regs_map_free(&pcic->handle);
1240 kmem_free(pcic, sizeof (pcicdev_t));
1241 return (DDI_FAILURE);
1245 * need to think this through again in light of
1246 * Compaq not following the model that all the
1247 * chip vendors recommend. IBM 755 seems to be
1248 * afflicted as well. Basically, if the vendor
1249 * wired things wrong, socket 0 responds for socket 2
1250 * accesses, etc.
1252 if (pcic->pc_numsockets > 2) {
1253 int count = pcic->pc_numsockets / 4;
1254 for (i = 0; i < count; i++) {
1255 /* put pattern into socket 0 */
1256 pcic_putb(pcic, i,
1257 PCIC_SYSMEM_0_STARTLOW, 0x11);
1259 /* put pattern into socket 2 */
1260 pcic_putb(pcic, i + 2,
1261 PCIC_SYSMEM_0_STARTLOW, 0x33);
1263 /* read back socket 0 */
1264 value = pcic_getb(pcic, i,
1265 PCIC_SYSMEM_0_STARTLOW);
1267 /* read back chip 1 socket 0 */
1268 j = pcic_getb(pcic, i + 2,
1269 PCIC_SYSMEM_0_STARTLOW);
1270 if (j == value) {
1271 pcic->pc_numsockets -= 2;
1276 smi = 0xff; /* no more override */
1278 if (ddi_getprop(DDI_DEV_T_NONE, dip,
1279 DDI_PROP_DONTPASS, "need-mult-irq",
1280 0xffff) != 0xffff)
1281 pcic->pc_flags |= PCF_MULT_IRQ;
1283 } /* !PCF_PCIBUS */
1286 * some platforms/busses need to have resources setup
1287 * this is temporary until a real resource allocator is
1288 * implemented.
1291 pcic_init_assigned(dip);
1293 typename = pcic->pc_chipname;
1295 #ifdef PCIC_DEBUG
1296 if (pcic_debug) {
1297 int nregs, nintrs;
1299 if (ddi_dev_nregs(dip, &nregs) != DDI_SUCCESS)
1300 nregs = 0;
1302 if (ddi_dev_nintrs(dip, &nintrs) != DDI_SUCCESS)
1303 nintrs = 0;
1305 cmn_err(CE_CONT,
1306 "pcic%d: %d register sets, %d interrupts\n",
1307 ddi_get_instance(dip), nregs, nintrs);
1309 nintrs = 0;
1310 while (nregs--) {
1311 off_t size;
1313 if (ddi_dev_regsize(dip, nintrs, &size) ==
1314 DDI_SUCCESS) {
1315 cmn_err(CE_CONT,
1316 "\tregnum %d size %ld (0x%lx)"
1317 "bytes",
1318 nintrs, size, size);
1319 if (nintrs ==
1320 (pcic->pc_io_type == PCIC_IO_TYPE_82365SL ?
1321 PCIC_ISA_CONTROL_REG_NUM :
1322 PCIC_PCI_CONTROL_REG_NUM))
1323 cmn_err(CE_CONT,
1324 " mapped at: 0x%p\n",
1325 (void *)pcic->ioaddr);
1326 else
1327 cmn_err(CE_CONT, "\n");
1328 } else {
1329 cmn_err(CE_CONT,
1330 "\tddi_dev_regsize(rnumber"
1331 "= %d) returns DDI_FAILURE\n",
1332 nintrs);
1334 nintrs++;
1335 } /* while */
1336 } /* if (pcic_debug) */
1337 #endif
1339 cv_init(&pcic->pm_cv, NULL, CV_DRIVER, NULL);
1341 if (!ddi_getprop(DDI_DEV_T_NONE, dip, DDI_PROP_DONTPASS,
1342 "disable-audio", 0))
1343 pcic->pc_flags |= PCF_AUDIO;
1345 if (ddi_getprop(DDI_DEV_T_ANY, dip, DDI_PROP_CANSLEEP,
1346 "disable-cardbus", 0))
1347 pcic->pc_flags &= ~PCF_CARDBUS;
1349 (void) ddi_prop_update_string(DDI_DEV_T_NONE, dip, PCICPROP_CTL,
1350 typename);
1353 * Init all socket SMI levels to 0 (no SMI)
1355 for (i = 0; i < PCIC_MAX_SOCKETS; i++) {
1356 pcic->pc_sockets[i].pcs_smi = 0;
1357 pcic->pc_sockets[i].pcs_debounce_id = 0;
1358 pcic->pc_sockets[i].pcs_pcic = pcic;
1360 pcic->pc_lastreg = -1; /* just to make sure we are in sync */
1363 * Setup the IRQ handler(s)
1365 switch (pcic->pc_intr_mode) {
1366 int xx;
1367 case PCIC_INTR_MODE_ISA:
1369 * On a non-PCI bus, we just use whatever SMI IRQ level was
1370 * specified above, and the IO IRQ levels are allocated
1371 * dynamically.
1373 for (xx = 15, smi = 0; xx >= 0; xx--) {
1374 if (PCIC_IRQ(xx) &
1375 PCIC_AVAIL_IRQS) {
1376 smi = pcmcia_get_intr(dip, xx);
1377 if (smi >= 0)
1378 break;
1381 #if defined(PCIC_DEBUG)
1382 if (pcic_debug)
1383 cmn_err(CE_NOTE, "\tselected IRQ %d as SMI\n", smi);
1384 #endif
1385 /* init to same so share is easy */
1386 for (i = 0; i < pcic->pc_numsockets; i++)
1387 pcic->pc_sockets[i].pcs_smi = smi;
1388 /* any special handling of IRQ levels */
1389 if (pcic->pc_flags & PCF_MULT_IRQ) {
1390 for (i = 2; i < pcic->pc_numsockets; i++) {
1391 if ((i & 1) == 0) {
1392 int xx;
1393 for (xx = 15, smi = 0; xx >= 0; xx--) {
1394 if (PCIC_IRQ(xx) &
1395 PCIC_AVAIL_IRQS) {
1396 smi =
1397 pcmcia_get_intr(dip,
1398 xx);
1399 if (smi >= 0)
1400 break;
1404 if (smi >= 0)
1405 pcic->pc_sockets[i].pcs_smi = smi;
1408 pcic->pc_intr_htblp = kmem_alloc(pcic->pc_numsockets *
1409 sizeof (ddi_intr_handle_t), KM_SLEEP);
1410 for (i = 0, irqlevel = -1; i < pcic->pc_numsockets; i++) {
1411 struct intrspec *ispecp;
1412 struct ddi_parent_private_data *pdp;
1414 if (irqlevel == pcic->pc_sockets[i].pcs_smi)
1415 continue;
1416 else {
1417 irqlevel = pcic->pc_sockets[i].pcs_smi;
1420 * now convert the allocated IRQ into an intrspec
1421 * and ask our parent to add it. Don't use
1422 * the ddi_add_intr since we don't have a
1423 * default intrspec in all cases.
1425 * note: this sort of violates DDI but we don't
1426 * get hardware intrspecs for many of the devices.
1427 * at the same time, we know how to allocate them
1428 * so we do the right thing.
1430 if (ddi_intr_alloc(dip, &pcic->pc_intr_htblp[i],
1431 DDI_INTR_TYPE_FIXED, 0, 1, &actual,
1432 DDI_INTR_ALLOC_NORMAL) != DDI_SUCCESS) {
1433 cmn_err(CE_WARN, "%s: ddi_intr_alloc failed",
1434 ddi_get_name(dip));
1435 goto isa_exit1;
1439 * See earlier note:
1440 * Since some devices don't have 'intrspec'
1441 * we make one up in rootnex.
1443 * However, it is not properly initialized as
1444 * the data it needs is present in this driver
1445 * and there is no interface to pass that up.
1446 * Specially 'irqlevel' is very important and
1447 * it is part of pcic struct.
1449 * Set 'intrspec' up here; otherwise adding the
1450 * interrupt will fail.
1452 pdp = ddi_get_parent_data(dip);
1453 ispecp = (struct intrspec *)&pdp->par_intr[0];
1454 ispecp->intrspec_vec = irqlevel;
1455 ispecp->intrspec_pri = pcic->pc_irq;
1457 /* Stay compatible w/ PCMCIA */
1458 pcic->pc_pri = (ddi_iblock_cookie_t)
1459 (uintptr_t)pcic->pc_irq;
1460 pcic->pc_dcookie.idev_priority =
1461 (uintptr_t)pcic->pc_pri;
1462 pcic->pc_dcookie.idev_vector = (ushort_t)irqlevel;
1464 (void) ddi_intr_set_pri(pcic->pc_intr_htblp[i],
1465 pcic->pc_irq);
1467 if (i == 0) {
1468 mutex_init(&pcic->intr_lock, NULL, MUTEX_DRIVER,
1469 DDI_INTR_PRI(pcic->pc_irq));
1470 mutex_init(&pcic->pc_lock, NULL, MUTEX_DRIVER,
1471 NULL);
1474 if (ddi_intr_add_handler(pcic->pc_intr_htblp[i],
1475 pcic_intr, (caddr_t)pcic, NULL)) {
1476 cmn_err(CE_WARN,
1477 "%s: ddi_intr_add_handler failed",
1478 ddi_get_name(dip));
1479 goto isa_exit2;
1482 if (ddi_intr_enable(pcic->pc_intr_htblp[i])) {
1483 cmn_err(CE_WARN, "%s: ddi_intr_enable failed",
1484 ddi_get_name(dip));
1485 for (j = i; j < 0; j--)
1486 (void) ddi_intr_remove_handler(
1487 pcic->pc_intr_htblp[j]);
1488 goto isa_exit2;
1491 break;
1492 case PCIC_INTR_MODE_PCI_1:
1493 case PCIC_INTR_MODE_PCI:
1495 * If we're on a PCI bus, we route all interrupts, both SMI
1496 * and IO interrupts, through a single interrupt line.
1497 * Assign the SMI IRQ level to the IO IRQ level here.
1499 pcic->pc_pci_intr_hdlp = kmem_alloc(sizeof (ddi_intr_handle_t),
1500 KM_SLEEP);
1501 if (ddi_intr_alloc(dip, pcic->pc_pci_intr_hdlp,
1502 DDI_INTR_TYPE_FIXED, 0, 1, &actual,
1503 DDI_INTR_ALLOC_NORMAL) != DDI_SUCCESS)
1504 goto pci_exit1;
1506 if (ddi_intr_get_pri(pcic->pc_pci_intr_hdlp[0],
1507 &pri) != DDI_SUCCESS) {
1508 (void) ddi_intr_free(pcic->pc_pci_intr_hdlp[0]);
1509 goto pci_exit1;
1512 pcic->pc_pri = (void *)(uintptr_t)pri;
1513 mutex_init(&pcic->intr_lock, NULL, MUTEX_DRIVER, pcic->pc_pri);
1514 mutex_init(&pcic->pc_lock, NULL, MUTEX_DRIVER, NULL);
1516 if (ddi_intr_add_handler(pcic->pc_pci_intr_hdlp[0],
1517 pcic_intr, (caddr_t)pcic, NULL))
1518 goto pci_exit2;
1520 if (ddi_intr_enable(pcic->pc_pci_intr_hdlp[0])) {
1521 (void) ddi_intr_remove_handler(
1522 pcic->pc_pci_intr_hdlp[0]);
1523 goto pci_exit2;
1526 /* Stay compatible w/ PCMCIA */
1527 pcic->pc_dcookie.idev_priority = (ushort_t)pri;
1529 /* init to same (PCI) so share is easy */
1530 for (i = 0; i < pcic->pc_numsockets; i++)
1531 pcic->pc_sockets[i].pcs_smi = 0xF; /* any valid */
1532 break;
1536 * Setup the adapter hardware to some reasonable defaults.
1538 mutex_enter(&pcic->pc_lock);
1539 /* mark the driver state as attached */
1540 pcic->pc_flags |= PCF_ATTACHED;
1541 pcic_setup_adapter(pcic);
1543 for (j = 0; j < pcic->pc_numsockets; j++)
1544 if (ddi_intr_add_softint(dip,
1545 &pcic->pc_sockets[j].pcs_cd_softint_hdl,
1546 PCIC_SOFTINT_PRI_VAL, pcic_cd_softint,
1547 (caddr_t)&pcic->pc_sockets[j]) != DDI_SUCCESS)
1548 goto pci_exit2;
1550 #if defined(PCIC_DEBUG)
1551 if (pcic_debug)
1552 cmn_err(CE_CONT, "type = %s sockets = %d\n", typename,
1553 pcic->pc_numsockets);
1554 #endif
1556 pcic_nexus->an_iblock = &pcic->pc_pri;
1557 pcic_nexus->an_idev = &pcic->pc_dcookie;
1559 mutex_exit(&pcic->pc_lock);
1561 #ifdef CARDBUS
1562 (void) cardbus_enable_cd_intr(dip);
1563 if (pcic_debug) {
1565 cardbus_dump_pci_config(dip);
1566 cardbus_dump_socket(dip);
1570 * Give the Cardbus misc module a chance to do it's per-adapter
1571 * instance setup. Note that there is no corresponding detach()
1572 * call.
1574 if (pcic->pc_flags & PCF_CARDBUS)
1575 if (cardbus_attach(dip, &pcic_cbnexus_ops) != DDI_SUCCESS) {
1576 cmn_err(CE_CONT,
1577 "pcic_attach: cardbus_attach failed\n");
1578 goto pci_exit2;
1580 #endif
1583 * Give the PCMCIA misc module a chance to do it's per-adapter
1584 * instance setup.
1586 if ((i = pcmcia_attach(dip, pcic_nexus)) != DDI_SUCCESS)
1587 goto pci_exit2;
1589 if (pcic_maxinst == -1) {
1590 /* This assumes that all instances run at the same IPL. */
1591 mutex_init(&pcic_deb_mtx, NULL, MUTEX_DRIVER, NULL);
1592 cv_init(&pcic_deb_cv, NULL, CV_DRIVER, NULL);
1593 pcic_deb_threadid = thread_create((caddr_t)NULL, 0,
1594 pcic_deb_thread, (caddr_t)NULL, 0, &p0, TS_RUN,
1595 v.v_maxsyspri - 2);
1597 pcic_maxinst = max(pcic_maxinst, ddi_get_instance(dip));
1599 * Setup a debounce timeout to do an initial card detect
1600 * and enable interrupts.
1602 for (j = 0; j < pcic->pc_numsockets; j++) {
1603 pcic->pc_sockets[j].pcs_debounce_id =
1604 pcic_add_debqueue(&pcic->pc_sockets[j],
1605 drv_usectohz(pcic_debounce_time));
1608 return (i);
1610 isa_exit2:
1611 mutex_destroy(&pcic->intr_lock);
1612 mutex_destroy(&pcic->pc_lock);
1613 for (j = i; j < 0; j--)
1614 (void) ddi_intr_free(pcic->pc_intr_htblp[j]);
1615 isa_exit1:
1616 (void) pcmcia_return_intr(dip, pcic->pc_sockets[i].pcs_smi);
1617 ddi_regs_map_free(&pcic->handle);
1618 if (pcic->pc_flags & PCF_PCIBUS)
1619 ddi_regs_map_free(&pcic->cfg_handle);
1620 kmem_free(pcic->pc_intr_htblp, pcic->pc_numsockets *
1621 sizeof (ddi_intr_handle_t));
1622 kmem_free(pcic, sizeof (pcicdev_t));
1623 return (DDI_FAILURE);
1625 pci_exit2:
1626 mutex_destroy(&pcic->intr_lock);
1627 mutex_destroy(&pcic->pc_lock);
1628 (void) ddi_intr_free(pcic->pc_pci_intr_hdlp[0]);
1629 pci_exit1:
1630 ddi_regs_map_free(&pcic->handle);
1631 if (pcic->pc_flags & PCF_PCIBUS)
1632 ddi_regs_map_free(&pcic->cfg_handle);
1633 kmem_free(pcic->pc_pci_intr_hdlp, sizeof (ddi_intr_handle_t));
1634 kmem_free(pcic, sizeof (pcicdev_t));
1635 return (DDI_FAILURE);
1639 * pcic_detach()
1640 * request to detach from the system
1642 static int
1643 pcic_detach(dev_info_t *dip, ddi_detach_cmd_t cmd)
1645 anp_t *anp = ddi_get_driver_private(dip);
1646 pcicdev_t *pcic = anp->an_private;
1647 int i;
1649 switch (cmd) {
1650 case DDI_DETACH:
1651 /* don't detach if the nexus still talks to us */
1652 if (pcic->pc_callback != NULL)
1653 return (DDI_FAILURE);
1655 /* kill off the pm simulation */
1656 if (pcic->pc_pmtimer)
1657 (void) untimeout(pcic->pc_pmtimer);
1659 /* turn everything off for all sockets and chips */
1660 for (i = 0; i < pcic->pc_numsockets; i++) {
1661 if (pcic->pc_sockets[i].pcs_debounce_id)
1662 pcic_rm_debqueue(
1663 pcic->pc_sockets[i].pcs_debounce_id);
1664 pcic->pc_sockets[i].pcs_debounce_id = 0;
1666 pcic_putb(pcic, i, PCIC_MANAGEMENT_INT, 0);
1667 pcic_putb(pcic, i, PCIC_CARD_DETECT, 0);
1668 pcic_putb(pcic, i, PCIC_MAPPING_ENABLE, 0);
1669 /* disable interrupts and put card into RESET */
1670 pcic_putb(pcic, i, PCIC_INTERRUPT, 0);
1672 (void) ddi_intr_disable(pcic->pc_pci_intr_hdlp[0]);
1673 (void) ddi_intr_remove_handler(pcic->pc_pci_intr_hdlp[0]);
1674 (void) ddi_intr_free(pcic->pc_pci_intr_hdlp[0]);
1675 kmem_free(pcic->pc_pci_intr_hdlp, sizeof (ddi_intr_handle_t));
1676 pcic->pc_flags = 0;
1677 mutex_destroy(&pcic->pc_lock);
1678 mutex_destroy(&pcic->intr_lock);
1679 cv_destroy(&pcic->pm_cv);
1680 if (pcic->pc_flags & PCF_PCIBUS)
1681 ddi_regs_map_free(&pcic->cfg_handle);
1682 if (pcic->handle)
1683 ddi_regs_map_free(&pcic->handle);
1684 kmem_free(pcic, sizeof (pcicdev_t));
1685 ddi_soft_state_free(pcic_soft_state_p, ddi_get_instance(dip));
1686 return (DDI_SUCCESS);
1688 case DDI_SUSPEND:
1689 case DDI_PM_SUSPEND:
1691 * we got a suspend event (either real or imagined)
1692 * so notify the nexus proper that all existing cards
1693 * should go away.
1695 mutex_enter(&pcic->pc_lock);
1696 #ifdef CARDBUS
1697 if (pcic->pc_flags & PCF_CARDBUS) {
1698 for (i = 0; i < pcic->pc_numsockets; i++) {
1699 if ((pcic->pc_sockets[i].pcs_flags &
1700 (PCS_CARD_PRESENT|PCS_CARD_ISCARDBUS)) ==
1701 (PCS_CARD_PRESENT|PCS_CARD_ISCARDBUS)) {
1703 pcmcia_cb_suspended(
1704 pcic->pc_sockets[i].pcs_socket);
1708 cardbus_save_children(ddi_get_child(dip));
1710 #endif
1711 /* turn everything off for all sockets and chips */
1712 for (i = 0; i < pcic->pc_numsockets; i++) {
1713 if (pcic->pc_sockets[i].pcs_debounce_id)
1714 pcic_rm_debqueue(
1715 pcic->pc_sockets[i].pcs_debounce_id);
1716 pcic->pc_sockets[i].pcs_debounce_id = 0;
1718 pcic_putb(pcic, i, PCIC_MANAGEMENT_INT, 0);
1719 pcic_putb(pcic, i, PCIC_CARD_DETECT, 0);
1720 pcic_putb(pcic, i, PCIC_MAPPING_ENABLE, 0);
1721 /* disable interrupts and put card into RESET */
1722 pcic_putb(pcic, i, PCIC_INTERRUPT, 0);
1723 pcic_putb(pcic, i, PCIC_POWER_CONTROL, 0);
1724 if (pcic->pc_flags & PCF_CBPWRCTL)
1725 pcic_putcb(pcic, CB_CONTROL, 0);
1727 if (pcic->pc_sockets[i].pcs_flags & PCS_CARD_PRESENT) {
1728 pcic->pc_sockets[i].pcs_flags = PCS_STARTING;
1730 * Because we are half way through a save
1731 * all this does is schedule a removal event
1732 * to cs for when the system comes back.
1733 * This doesn't actually matter.
1735 if (!pcic_do_pcmcia_sr && pcic_do_removal &&
1736 pcic->pc_callback) {
1737 PC_CALLBACK(pcic->dip, pcic->pc_cb_arg,
1738 PCE_CARD_REMOVAL,
1739 pcic->pc_sockets[i].pcs_socket);
1744 pcic->pc_flags |= PCF_SUSPENDED;
1745 mutex_exit(&pcic->pc_lock);
1748 * when true power management exists, save the adapter
1749 * state here to enable a recovery. For the emulation
1750 * condition, the state is gone
1752 return (DDI_SUCCESS);
1754 default:
1755 return (EINVAL);
1759 static uint32_t pcic_tisysctl_onbits = ((1<<27) | (1<<15) | (1<<14));
1760 static uint32_t pcic_tisysctl_offbits = 0;
1761 static uint32_t pcic_default_latency = 0x40;
1763 static void
1764 pcic_setup_adapter(pcicdev_t *pcic)
1766 int i;
1767 int value, flags;
1769 #if defined(__i386) || defined(__amd64)
1770 pci_regspec_t *reg;
1771 uchar_t bus, dev, func;
1772 uint_t classcode;
1773 int length;
1774 #endif
1776 if (pcic->pc_flags & PCF_PCIBUS) {
1778 * all PCI-to-PCMCIA bus bridges need memory and I/O enabled
1780 flags = (PCIC_ENABLE_IO | PCIC_ENABLE_MEM);
1781 pcic_iomem_pci_ctl(pcic->cfg_handle, pcic->cfgaddr, flags);
1783 /* enable each socket */
1784 for (i = 0; i < pcic->pc_numsockets; i++) {
1785 pcic->pc_sockets[i].pcs_flags = 0;
1786 /* find out the socket capabilities (I/O vs memory) */
1787 value = pcic_getb(pcic, i,
1788 PCIC_CHIP_REVISION) & PCIC_REV_ID_MASK;
1789 if (value == PCIC_REV_ID_IO || value == PCIC_REV_ID_BOTH)
1790 pcic->pc_sockets[i].pcs_flags |= PCS_SOCKET_IO;
1792 /* disable all windows just in case */
1793 pcic_putb(pcic, i, PCIC_MAPPING_ENABLE, 0);
1795 switch (pcic->pc_type) {
1796 uint32_t cfg32;
1797 uint16_t cfg16;
1798 uint8_t cfg;
1800 /* enable extended registers for Vadem */
1801 case PCIC_VADEM_VG469:
1802 case PCIC_VADEM:
1804 /* enable card status change interrupt for socket */
1805 break;
1807 case PCIC_I82365SL:
1808 break;
1810 case PCIC_CL_PD6710:
1811 pcic_putb(pcic, 0, PCIC_MISC_CTL_2, PCIC_LED_ENABLE);
1812 break;
1815 * On the CL_6730, we need to set up the interrupt
1816 * signalling mode (PCI mode) and set the SMI and
1817 * IRQ interrupt lines to PCI/level-mode.
1819 case PCIC_CL_PD6730:
1820 switch (pcic->pc_intr_mode) {
1821 case PCIC_INTR_MODE_PCI_1:
1822 clext_reg_write(pcic, i, PCIC_CLEXT_MISC_CTL_3,
1823 ((clext_reg_read(pcic, i,
1824 PCIC_CLEXT_MISC_CTL_3) &
1825 ~PCIC_CLEXT_INT_PCI) |
1826 PCIC_CLEXT_INT_PCI));
1827 clext_reg_write(pcic, i, PCIC_CLEXT_EXT_CTL_1,
1828 (PCIC_CLEXT_IRQ_LVL_MODE |
1829 PCIC_CLEXT_SMI_LVL_MODE));
1830 cfg = PCIC_CL_LP_DYN_MODE;
1831 pcic_putb(pcic, i, PCIC_MISC_CTL_2, cfg);
1832 break;
1833 case PCIC_INTR_MODE_ISA:
1834 break;
1836 break;
1838 * On the CL_6729, we set the SMI and IRQ interrupt
1839 * lines to PCI/level-mode. as well as program the
1840 * correct clock speed divider bit.
1842 case PCIC_CL_PD6729:
1843 switch (pcic->pc_intr_mode) {
1844 case PCIC_INTR_MODE_PCI_1:
1845 clext_reg_write(pcic, i, PCIC_CLEXT_EXT_CTL_1,
1846 (PCIC_CLEXT_IRQ_LVL_MODE |
1847 PCIC_CLEXT_SMI_LVL_MODE));
1849 break;
1850 case PCIC_INTR_MODE_ISA:
1851 break;
1853 if (pcic->bus_speed > PCIC_PCI_25MHZ && i == 0) {
1854 cfg = 0;
1855 cfg |= PCIC_CL_TIMER_CLK_DIV;
1856 pcic_putb(pcic, i, PCIC_MISC_CTL_2, cfg);
1858 break;
1859 case PCIC_INTEL_i82092:
1860 cfg = PCIC_82092_EN_TIMING;
1861 if (pcic->bus_speed < PCIC_SYSCLK_33MHZ)
1862 cfg |= PCIC_82092_PCICLK_25MHZ;
1863 ddi_put8(pcic->cfg_handle, pcic->cfgaddr +
1864 PCIC_82092_PCICON, cfg);
1865 break;
1866 case PCIC_TI_PCI1130:
1867 case PCIC_TI_PCI1131:
1868 case PCIC_TI_PCI1250:
1869 case PCIC_TI_PCI1031:
1870 cfg = ddi_get8(pcic->cfg_handle,
1871 pcic->cfgaddr + PCIC_DEVCTL_REG);
1872 cfg &= ~PCIC_DEVCTL_INTR_MASK;
1873 switch (pcic->pc_intr_mode) {
1874 case PCIC_INTR_MODE_ISA:
1875 cfg |= PCIC_DEVCTL_INTR_ISA;
1876 break;
1878 #ifdef PCIC_DEBUG
1879 if (pcic_debug) {
1880 cmn_err(CE_CONT, "pcic_setup_adapter: "
1881 "write reg 0x%x=%x \n",
1882 PCIC_DEVCTL_REG, cfg);
1884 #endif
1885 ddi_put8(pcic->cfg_handle,
1886 pcic->cfgaddr + PCIC_DEVCTL_REG,
1887 cfg);
1889 cfg = ddi_get8(pcic->cfg_handle,
1890 pcic->cfgaddr + PCIC_CRDCTL_REG);
1891 cfg &= ~(PCIC_CRDCTL_PCIINTR|PCIC_CRDCTL_PCICSC|
1892 PCIC_CRDCTL_PCIFUNC);
1893 switch (pcic->pc_intr_mode) {
1894 case PCIC_INTR_MODE_PCI_1:
1895 cfg |= PCIC_CRDCTL_PCIINTR |
1896 PCIC_CRDCTL_PCICSC |
1897 PCIC_CRDCTL_PCIFUNC;
1898 pcic->pc_flags |= PCF_USE_SMI;
1899 break;
1901 #ifdef PCIC_DEBUG
1902 if (pcic_debug) {
1903 cmn_err(CE_CONT, "pcic_setup_adapter: "
1904 " write reg 0x%x=%x \n",
1905 PCIC_CRDCTL_REG, cfg);
1907 #endif
1908 ddi_put8(pcic->cfg_handle,
1909 pcic->cfgaddr + PCIC_CRDCTL_REG,
1910 cfg);
1911 break;
1912 case PCIC_TI_PCI1221:
1913 case PCIC_TI_PCI1225:
1914 cfg = ddi_get8(pcic->cfg_handle,
1915 pcic->cfgaddr + PCIC_DEVCTL_REG);
1916 cfg |= (PCIC_DEVCTL_INTR_DFLT | PCIC_DEVCTL_3VCAPABLE);
1917 #ifdef PCIC_DEBUG
1918 if (pcic_debug) {
1919 cmn_err(CE_CONT, "pcic_setup_adapter: "
1920 " write reg 0x%x=%x \n",
1921 PCIC_DEVCTL_REG, cfg);
1923 #endif
1924 ddi_put8(pcic->cfg_handle,
1925 pcic->cfgaddr + PCIC_DEVCTL_REG, cfg);
1927 cfg = ddi_get8(pcic->cfg_handle,
1928 pcic->cfgaddr + PCIC_DIAG_REG);
1929 if (pcic->pc_type == PCIC_TI_PCI1225) {
1930 cfg |= (PCIC_DIAG_CSC | PCIC_DIAG_ASYNC);
1931 } else {
1932 cfg |= PCIC_DIAG_ASYNC;
1934 pcic->pc_flags |= PCF_USE_SMI;
1935 #ifdef PCIC_DEBUG
1936 if (pcic_debug) {
1937 cmn_err(CE_CONT, "pcic_setup_adapter: "
1938 " write reg 0x%x=%x \n",
1939 PCIC_DIAG_REG, cfg);
1941 #endif
1942 ddi_put8(pcic->cfg_handle,
1943 pcic->cfgaddr + PCIC_DIAG_REG, cfg);
1944 break;
1945 case PCIC_TI_PCI1520:
1946 case PCIC_TI_PCI1510:
1947 case PCIC_TI_VENDOR:
1948 if (pcic->pc_intr_mode == PCIC_INTR_MODE_ISA) {
1949 /* functional intr routed by ExCA register */
1950 cfg = ddi_get8(pcic->cfg_handle,
1951 pcic->cfgaddr + PCIC_BRIDGE_CTL_REG);
1952 cfg |= PCIC_FUN_INT_MOD_ISA;
1953 ddi_put8(pcic->cfg_handle,
1954 pcic->cfgaddr + PCIC_BRIDGE_CTL_REG,
1955 cfg);
1957 /* IRQ serialized interrupts */
1958 cfg = ddi_get8(pcic->cfg_handle,
1959 pcic->cfgaddr + PCIC_DEVCTL_REG);
1960 cfg &= ~PCIC_DEVCTL_INTR_MASK;
1961 cfg |= PCIC_DEVCTL_INTR_ISA;
1962 ddi_put8(pcic->cfg_handle,
1963 pcic->cfgaddr + PCIC_DEVCTL_REG,
1964 cfg);
1965 break;
1968 /* CSC interrupt routed to PCI */
1969 cfg = ddi_get8(pcic->cfg_handle,
1970 pcic->cfgaddr + PCIC_DIAG_REG);
1971 cfg |= (PCIC_DIAG_CSC | PCIC_DIAG_ASYNC);
1972 ddi_put8(pcic->cfg_handle,
1973 pcic->cfgaddr + PCIC_DIAG_REG, cfg);
1975 #if defined(__i386) || defined(__amd64)
1977 * Some TI chips have 2 cardbus slots(function0 and
1978 * function1), and others may have just 1 cardbus slot.
1979 * The interrupt routing register is shared between the
1980 * 2 functions and can only be accessed through
1981 * function0. Here we check the presence of the second
1982 * cardbus slot and do the right thing.
1985 if (ddi_getlongprop(DDI_DEV_T_ANY, pcic->dip,
1986 DDI_PROP_DONTPASS, "reg", (caddr_t)&reg,
1987 &length) != DDI_PROP_SUCCESS) {
1988 cmn_err(CE_WARN,
1989 "pcic_setup_adapter(), failed to"
1990 " read reg property\n");
1991 break;
1994 bus = PCI_REG_BUS_G(reg->pci_phys_hi);
1995 dev = PCI_REG_DEV_G(reg->pci_phys_hi);
1996 func = PCI_REG_FUNC_G(reg->pci_phys_hi);
1997 kmem_free((caddr_t)reg, length);
1999 if (func != 0) {
2000 break;
2003 classcode = (*pci_getl_func)(bus, dev, 1,
2004 PCI_CONF_REVID);
2005 classcode >>= 8;
2006 if (classcode != 0x060700 &&
2007 classcode != 0x060500) {
2008 break;
2011 /* Parallel PCI interrupts only */
2012 cfg = ddi_get8(pcic->cfg_handle,
2013 pcic->cfgaddr + PCIC_DEVCTL_REG);
2014 cfg &= ~PCIC_DEVCTL_INTR_MASK;
2015 ddi_put8(pcic->cfg_handle,
2016 pcic->cfgaddr + PCIC_DEVCTL_REG,
2017 cfg);
2019 /* tie INTA and INTB together */
2020 cfg = ddi_get8(pcic->cfg_handle,
2021 (pcic->cfgaddr + PCIC_SYSCTL_REG + 3));
2022 cfg |= PCIC_SYSCTL_INTRTIE;
2023 ddi_put8(pcic->cfg_handle, (pcic->cfgaddr +
2024 PCIC_SYSCTL_REG + 3), cfg);
2025 #endif
2027 break;
2028 case PCIC_TI_PCI1410:
2029 cfg = ddi_get8(pcic->cfg_handle,
2030 pcic->cfgaddr + PCIC_DIAG_REG);
2031 cfg |= (PCIC_DIAG_CSC | PCIC_DIAG_ASYNC);
2032 ddi_put8(pcic->cfg_handle,
2033 pcic->cfgaddr + PCIC_DIAG_REG, cfg);
2034 break;
2035 case PCIC_TOSHIBA_TOPIC100:
2036 case PCIC_TOSHIBA_TOPIC95:
2037 case PCIC_TOSHIBA_VENDOR:
2038 cfg = ddi_get8(pcic->cfg_handle, pcic->cfgaddr +
2039 PCIC_TOSHIBA_SLOT_CTL_REG);
2040 cfg |= (PCIC_TOSHIBA_SCR_SLOTON |
2041 PCIC_TOSHIBA_SCR_SLOTEN);
2042 cfg &= (~PCIC_TOSHIBA_SCR_PRT_MASK);
2043 cfg |= PCIC_TOSHIBA_SCR_PRT_3E2;
2044 ddi_put8(pcic->cfg_handle, pcic->cfgaddr +
2045 PCIC_TOSHIBA_SLOT_CTL_REG, cfg);
2046 cfg = ddi_get8(pcic->cfg_handle, pcic->cfgaddr +
2047 PCIC_TOSHIBA_INTR_CTL_REG);
2048 switch (pcic->pc_intr_mode) {
2049 case PCIC_INTR_MODE_ISA:
2050 cfg &= ~PCIC_TOSHIBA_ICR_SRC;
2051 ddi_put8(pcic->cfg_handle,
2052 pcic->cfgaddr +
2053 PCIC_TOSHIBA_INTR_CTL_REG, cfg);
2055 cfg = ddi_get8(pcic->cfg_handle,
2056 pcic->cfgaddr + PCIC_BRIDGE_CTL_REG);
2057 cfg |= PCIC_FUN_INT_MOD_ISA;
2058 ddi_put8(pcic->cfg_handle,
2059 pcic->cfgaddr + PCIC_BRIDGE_CTL_REG,
2060 cfg);
2061 break;
2062 case PCIC_INTR_MODE_PCI_1:
2063 cfg |= PCIC_TOSHIBA_ICR_SRC;
2064 cfg &= (~PCIC_TOSHIBA_ICR_PIN_MASK);
2065 cfg |= PCIC_TOSHIBA_ICR_PIN_INTA;
2066 ddi_put8(pcic->cfg_handle,
2067 pcic->cfgaddr +
2068 PCIC_TOSHIBA_INTR_CTL_REG, cfg);
2069 break;
2071 break;
2072 case PCIC_O2MICRO_VENDOR:
2073 cfg32 = ddi_get32(pcic->cfg_handle,
2074 (uint32_t *)(pcic->cfgaddr +
2075 PCIC_O2MICRO_MISC_CTL));
2076 switch (pcic->pc_intr_mode) {
2077 case PCIC_INTR_MODE_ISA:
2078 cfg32 |= (PCIC_O2MICRO_ISA_LEGACY |
2079 PCIC_O2MICRO_INT_MOD_PCI);
2080 ddi_put32(pcic->cfg_handle,
2081 (uint32_t *)(pcic->cfgaddr +
2082 PCIC_O2MICRO_MISC_CTL),
2083 cfg32);
2084 cfg = ddi_get8(pcic->cfg_handle,
2085 pcic->cfgaddr + PCIC_BRIDGE_CTL_REG);
2086 cfg |= PCIC_FUN_INT_MOD_ISA;
2087 ddi_put8(pcic->cfg_handle,
2088 pcic->cfgaddr + PCIC_BRIDGE_CTL_REG,
2089 cfg);
2090 break;
2091 case PCIC_INTR_MODE_PCI_1:
2092 cfg32 &= ~PCIC_O2MICRO_ISA_LEGACY;
2093 cfg32 |= PCIC_O2MICRO_INT_MOD_PCI;
2094 ddi_put32(pcic->cfg_handle,
2095 (uint32_t *)(pcic->cfgaddr +
2096 PCIC_O2MICRO_MISC_CTL),
2097 cfg32);
2098 break;
2100 break;
2101 case PCIC_RICOH_VENDOR:
2102 if (pcic->pc_intr_mode == PCIC_INTR_MODE_ISA) {
2103 cfg16 = ddi_get16(pcic->cfg_handle,
2104 (uint16_t *)(pcic->cfgaddr +
2105 PCIC_RICOH_MISC_CTL_2));
2106 cfg16 |= (PCIC_RICOH_CSC_INT_MOD |
2107 PCIC_RICOH_FUN_INT_MOD);
2108 ddi_put16(pcic->cfg_handle,
2109 (uint16_t *)(pcic->cfgaddr +
2110 PCIC_RICOH_MISC_CTL_2),
2111 cfg16);
2113 cfg16 = ddi_get16(pcic->cfg_handle,
2114 (uint16_t *)(pcic->cfgaddr +
2115 PCIC_RICOH_MISC_CTL));
2116 cfg16 |= PCIC_RICOH_SIRQ_EN;
2117 ddi_put16(pcic->cfg_handle,
2118 (uint16_t *)(pcic->cfgaddr +
2119 PCIC_RICOH_MISC_CTL),
2120 cfg16);
2122 cfg = ddi_get8(pcic->cfg_handle,
2123 pcic->cfgaddr + PCIC_BRIDGE_CTL_REG);
2124 cfg |= PCIC_FUN_INT_MOD_ISA;
2125 ddi_put8(pcic->cfg_handle,
2126 pcic->cfgaddr + PCIC_BRIDGE_CTL_REG,
2127 cfg);
2129 break;
2130 default:
2131 break;
2132 } /* switch */
2135 * The default value in the EEPROM (loaded on reset) for
2136 * MFUNC0/MFUNC1 may be incorrect. Here we make sure that
2137 * MFUNC0 is connected to INTA, and MFUNC1 is connected to
2138 * INTB. This applies to all TI CardBus controllers.
2140 if ((pcic->pc_type >> 16) == PCIC_TI_VENDORID &&
2141 pcic->pc_intr_mode == PCIC_INTR_MODE_PCI_1) {
2142 value = ddi_get32(pcic->cfg_handle,
2143 (uint32_t *)(pcic->cfgaddr + PCIC_MFROUTE_REG));
2144 value &= ~0xff;
2145 ddi_put32(pcic->cfg_handle, (uint32_t *)(pcic->cfgaddr +
2146 PCIC_MFROUTE_REG), value|PCIC_TI_MFUNC_SEL);
2149 /* setup general card status change interrupt */
2150 switch (pcic->pc_type) {
2151 case PCIC_TI_PCI1225:
2152 case PCIC_TI_PCI1221:
2153 case PCIC_TI_PCI1031:
2154 case PCIC_TI_PCI1520:
2155 case PCIC_TI_PCI1410:
2156 pcic_putb(pcic, i, PCIC_MANAGEMENT_INT,
2157 PCIC_CHANGE_DEFAULT);
2158 break;
2159 default:
2160 if (pcic->pc_intr_mode ==
2161 PCIC_INTR_MODE_PCI_1) {
2162 pcic_putb(pcic, i, PCIC_MANAGEMENT_INT,
2163 PCIC_CHANGE_DEFAULT);
2164 break;
2165 } else {
2166 pcic_putb(pcic, i, PCIC_MANAGEMENT_INT,
2167 PCIC_CHANGE_DEFAULT |
2168 (pcic->pc_sockets[i].pcs_smi << 4));
2169 break;
2173 pcic->pc_flags |= PCF_INTRENAB;
2175 /* take card out of RESET */
2176 pcic_putb(pcic, i, PCIC_INTERRUPT, PCIC_RESET);
2177 /* turn power off and let CS do this */
2178 pcic_putb(pcic, i, PCIC_POWER_CONTROL, 0);
2180 /* final chip specific initialization */
2181 switch (pcic->pc_type) {
2182 case PCIC_VADEM:
2183 pcic_putb(pcic, i, PCIC_VG_CONTROL,
2184 PCIC_VC_DELAYENABLE);
2185 pcic->pc_flags |= PCF_DEBOUNCE;
2186 /* FALLTHROUGH */
2187 case PCIC_I82365SL:
2188 pcic_putb(pcic, i, PCIC_GLOBAL_CONTROL,
2189 PCIC_GC_CSC_WRITE);
2190 /* clear any pending interrupts */
2191 value = pcic_getb(pcic, i, PCIC_CARD_STATUS_CHANGE);
2192 pcic_putb(pcic, i, PCIC_CARD_STATUS_CHANGE, value);
2193 break;
2194 /* The 82092 uses PCI config space to enable interrupts */
2195 case PCIC_INTEL_i82092:
2196 pcic_82092_smiirq_ctl(pcic, i, PCIC_82092_CTL_SMI,
2197 PCIC_82092_INT_ENABLE);
2198 break;
2199 case PCIC_CL_PD6729:
2200 if (pcic->bus_speed >= PCIC_PCI_DEF_SYSCLK && i == 0) {
2201 value = pcic_getb(pcic, i, PCIC_MISC_CTL_2);
2202 pcic_putb(pcic, i, PCIC_MISC_CTL_2,
2203 value | PCIC_CL_TIMER_CLK_DIV);
2205 break;
2206 } /* switch */
2208 #if defined(PCIC_DEBUG)
2209 if (pcic_debug)
2210 cmn_err(CE_CONT,
2211 "socket %d value=%x, flags = %x (%s)\n",
2212 i, value, pcic->pc_sockets[i].pcs_flags,
2213 (pcic->pc_sockets[i].pcs_flags &
2214 PCS_CARD_PRESENT) ?
2215 "card present" : "no card");
2216 #endif
2221 * pcic_intr(caddr_t, caddr_t)
2222 * interrupt handler for the PCIC style adapter
2223 * handles all basic interrupts and also checks
2224 * for status changes and notifies the nexus if
2225 * necessary
2227 * On PCI bus adapters, also handles all card
2228 * IO interrupts.
2230 /*ARGSUSED*/
2231 uint32_t
2232 pcic_intr(caddr_t arg1, caddr_t arg2)
2234 pcicdev_t *pcic = (pcicdev_t *)arg1;
2235 int value = 0, i, ret = DDI_INTR_UNCLAIMED;
2236 uint8_t status;
2237 uint_t io_ints;
2239 #if defined(PCIC_DEBUG)
2240 pcic_err(pcic->dip, 0xf,
2241 "pcic_intr: enter pc_flags=0x%x PCF_ATTACHED=0x%x"
2242 " pc_numsockets=%d \n",
2243 pcic->pc_flags, PCF_ATTACHED, pcic->pc_numsockets);
2244 #endif
2246 if (!(pcic->pc_flags & PCF_ATTACHED))
2247 return (DDI_INTR_UNCLAIMED);
2249 mutex_enter(&pcic->intr_lock);
2251 if (pcic->pc_flags & PCF_SUSPENDED) {
2252 mutex_exit(&pcic->intr_lock);
2253 return (ret);
2257 * need to change to only ACK and touch the slot that
2258 * actually caused the interrupt. Currently everything
2259 * is acked
2261 * we need to look at all known sockets to determine
2262 * what might have happened, so step through the list
2263 * of them
2267 * Set the bitmask for IO interrupts to initially include all sockets
2269 io_ints = (1 << pcic->pc_numsockets) - 1;
2271 for (i = 0; i < pcic->pc_numsockets; i++) {
2272 int card_type;
2273 pcic_socket_t *sockp;
2274 int value_cb = 0;
2276 sockp = &pcic->pc_sockets[i];
2277 /* get the socket's I/O addresses */
2279 if (sockp->pcs_flags & PCS_WAITING) {
2280 io_ints &= ~(1 << i);
2281 continue;
2284 if (sockp->pcs_flags & PCS_CARD_IO)
2285 card_type = IF_IO;
2286 else
2287 card_type = IF_MEMORY;
2289 if (pcic->pc_io_type == PCIC_IO_TYPE_YENTA)
2290 value_cb = pcic_getcb(pcic, CB_STATUS_EVENT);
2292 value = pcic_change(pcic, i);
2294 if ((value != 0) || (value_cb != 0)) {
2295 int x = pcic->pc_cb_arg;
2297 ret = DDI_INTR_CLAIMED;
2299 #if defined(PCIC_DEBUG)
2300 pcic_err(pcic->dip, 0x9,
2301 "card_type = %d, value_cb = 0x%x\n",
2302 card_type,
2303 value_cb ? value_cb :
2304 pcic_getcb(pcic, CB_STATUS_EVENT));
2305 if (pcic_debug)
2306 cmn_err(CE_CONT,
2307 "\tchange on socket %d (%x)\n", i,
2308 value);
2309 #endif
2310 /* find out what happened */
2311 status = pcic_getb(pcic, i, PCIC_INTERFACE_STATUS);
2313 /* acknowledge the interrupt */
2314 if (value_cb)
2315 pcic_putcb(pcic, CB_STATUS_EVENT, value_cb);
2317 if (value)
2318 pcic_putb(pcic, i, PCIC_CARD_STATUS_CHANGE,
2319 value);
2321 if (pcic->pc_callback == NULL) {
2322 /* if not callback handler, nothing to do */
2323 continue;
2326 /* Card Detect */
2327 if (value & PCIC_CD_DETECT ||
2328 value_cb & CB_PS_CCDMASK) {
2329 uint8_t irq;
2330 #if defined(PCIC_DEBUG)
2331 if (pcic_debug)
2332 cmn_err(CE_CONT,
2333 "\tcd_detect: status=%x,"
2334 " flags=%x\n",
2335 status, sockp->pcs_flags);
2336 #else
2337 #ifdef lint
2338 if (status == 0)
2339 status++;
2340 #endif
2341 #endif
2343 * Turn off all interrupts for this socket here.
2345 irq = pcic_getb(pcic, sockp->pcs_socket,
2346 PCIC_MANAGEMENT_INT);
2347 irq &= ~PCIC_CHANGE_MASK;
2348 pcic_putb(pcic, sockp->pcs_socket,
2349 PCIC_MANAGEMENT_INT, irq);
2351 pcic_putcb(pcic, CB_STATUS_MASK, 0x0);
2354 * Put the socket in debouncing state so that
2355 * the leaf driver won't receive interrupts.
2356 * Crucial for handling surprise-removal.
2358 sockp->pcs_flags |= PCS_DEBOUNCING;
2360 if (!sockp->pcs_cd_softint_flg) {
2361 sockp->pcs_cd_softint_flg = 1;
2362 (void) ddi_intr_trigger_softint(
2363 sockp->pcs_cd_softint_hdl, NULL);
2366 io_ints &= ~(1 << i);
2367 } /* PCIC_CD_DETECT */
2369 /* Ready/Change Detect */
2370 sockp->pcs_state ^= SBM_RDYBSY;
2371 if (card_type == IF_MEMORY && value & PCIC_RD_DETECT) {
2372 sockp->pcs_flags |= PCS_READY;
2373 PC_CALLBACK(pcic->dip, x, PCE_CARD_READY, i);
2376 /* Battery Warn Detect */
2377 if (card_type == IF_MEMORY &&
2378 value & PCIC_BW_DETECT &&
2379 !(sockp->pcs_state & SBM_BVD2)) {
2380 sockp->pcs_state |= SBM_BVD2;
2381 PC_CALLBACK(pcic->dip, x,
2382 PCE_CARD_BATTERY_WARN, i);
2385 /* Battery Dead Detect */
2386 if (value & PCIC_BD_DETECT) {
2388 * need to work out event if RI not enabled
2389 * and card_type == IF_IO
2391 if (card_type == IF_MEMORY &&
2392 !(sockp->pcs_state & SBM_BVD1)) {
2393 sockp->pcs_state |= SBM_BVD1;
2394 PC_CALLBACK(pcic->dip, x,
2395 PCE_CARD_BATTERY_DEAD,
2397 } else {
2399 * information in pin replacement
2400 * register if one is available
2402 PC_CALLBACK(pcic->dip, x,
2403 PCE_CARD_STATUS_CHANGE,
2405 } /* IF_MEMORY */
2406 } /* PCIC_BD_DETECT */
2407 } /* if pcic_change */
2409 * for any controllers that we can detect whether a socket
2410 * had an interrupt for the PC Card, we should sort that out
2411 * here.
2413 } /* for pc_numsockets */
2416 * If we're on a PCI bus, we may need to cycle through each IO
2417 * interrupt handler that is registered since they all
2418 * share the same interrupt line.
2422 #if defined(PCIC_DEBUG)
2423 pcic_err(pcic->dip, 0xf,
2424 "pcic_intr: pc_intr_mode=%d pc_type=%x io_ints=0x%x\n",
2425 pcic->pc_intr_mode, pcic->pc_type, io_ints);
2426 #endif
2428 if (io_ints) {
2429 if (pcic_do_io_intr(pcic, io_ints) == DDI_INTR_CLAIMED)
2430 ret = DDI_INTR_CLAIMED;
2433 mutex_exit(&pcic->intr_lock);
2435 #if defined(PCIC_DEBUG)
2436 pcic_err(pcic->dip, 0xf,
2437 "pcic_intr: ret=%d value=%d DDI_INTR_CLAIMED=%d\n",
2438 ret, value, DDI_INTR_CLAIMED);
2439 #endif
2441 return (ret);
2445 * pcic_change()
2446 * check to see if this socket had a change in state
2447 * by checking the status change register
2449 static int
2450 pcic_change(pcicdev_t *pcic, int socket)
2452 return (pcic_getb(pcic, socket, PCIC_CARD_STATUS_CHANGE));
2456 * pcic_do_io_intr - calls client interrupt handlers
2458 static int
2459 pcic_do_io_intr(pcicdev_t *pcic, uint32_t sockets)
2461 inthandler_t *tmp;
2462 int ret = DDI_INTR_UNCLAIMED;
2464 #if defined(PCIC_DEBUG)
2465 pcic_err(pcic->dip, 0xf,
2466 "pcic_do_io_intr: pcic=%p sockets=%d irq_top=%p\n",
2467 (void *)pcic, (int)sockets, (void *)pcic->irq_top);
2468 #endif
2470 if (pcic->irq_top != NULL) {
2471 tmp = pcic->irq_current;
2473 do {
2474 int cur = pcic->irq_current->socket;
2475 pcic_socket_t *sockp =
2476 &pcic->pc_sockets[cur];
2478 #if defined(PCIC_DEBUG)
2479 pcic_err(pcic->dip, 0xf,
2480 "\t pcs_flags=0x%x PCS_CARD_PRESENT=0x%x\n",
2481 sockp->pcs_flags, PCS_CARD_PRESENT);
2482 pcic_err(pcic->dip, 0xf,
2483 "\t sockets=%d cur=%d intr=%p arg1=%p "
2484 "arg2=%p\n",
2485 sockets, cur, (void *)pcic->irq_current->intr,
2486 pcic->irq_current->arg1,
2487 pcic->irq_current->arg2);
2488 #endif
2489 if ((sockp->pcs_flags & PCS_CARD_PRESENT) &&
2490 !(sockp->pcs_flags & PCS_DEBOUNCING) &&
2491 (sockets & (1 << cur))) {
2493 if ((*pcic->irq_current->intr)(pcic->irq_current->arg1,
2494 pcic->irq_current->arg2) == DDI_INTR_CLAIMED)
2495 ret = DDI_INTR_CLAIMED;
2497 #if defined(PCIC_DEBUG)
2498 pcic_err(pcic->dip, 0xf,
2499 "\t ret=%d DDI_INTR_CLAIMED=%d\n",
2500 ret, DDI_INTR_CLAIMED);
2501 #endif
2505 if ((pcic->irq_current = pcic->irq_current->next) == NULL)
2506 pcic->irq_current = pcic->irq_top;
2508 } while (pcic->irq_current != tmp);
2510 if ((pcic->irq_current = pcic->irq_current->next) == NULL)
2511 pcic->irq_current = pcic->irq_top;
2513 } else {
2514 ret = DDI_INTR_UNCLAIMED;
2517 #if defined(PCIC_DEBUG)
2518 pcic_err(pcic->dip, 0xf,
2519 "pcic_do_io_intr: exit ret=%d DDI_INTR_CLAIMED=%d\n",
2520 ret, DDI_INTR_CLAIMED);
2521 #endif
2523 return (ret);
2528 * pcic_inquire_adapter()
2529 * SocketServices InquireAdapter function
2530 * get characteristics of the physical adapter
2532 /*ARGSUSED*/
2533 static int
2534 pcic_inquire_adapter(dev_info_t *dip, inquire_adapter_t *config)
2536 anp_t *anp = ddi_get_driver_private(dip);
2537 pcicdev_t *pcic = anp->an_private;
2539 config->NumSockets = pcic->pc_numsockets;
2540 config->NumWindows = pcic->pc_numsockets * PCIC_NUMWINSOCK;
2541 config->NumEDCs = 0;
2542 config->AdpCaps = 0;
2543 config->ActiveHigh = 0;
2544 config->ActiveLow = PCIC_AVAIL_IRQS;
2545 config->NumPower = pcic->pc_numpower;
2546 config->power_entry = pcic->pc_power; /* until we resolve this */
2547 #if defined(PCIC_DEBUG)
2548 if (pcic_debug) {
2549 cmn_err(CE_CONT, "pcic_inquire_adapter:\n");
2550 cmn_err(CE_CONT, "\tNumSockets=%d\n", config->NumSockets);
2551 cmn_err(CE_CONT, "\tNumWindows=%d\n", config->NumWindows);
2553 #endif
2554 config->ResourceFlags = 0;
2555 switch (pcic->pc_intr_mode) {
2556 case PCIC_INTR_MODE_PCI_1:
2557 config->ResourceFlags |= RES_OWN_IRQ | RES_IRQ_NEXUS |
2558 RES_IRQ_SHAREABLE;
2559 break;
2561 return (SUCCESS);
2565 * pcic_callback()
2566 * The PCMCIA nexus calls us via this function
2567 * in order to set the callback function we are
2568 * to call the nexus with
2570 /*ARGSUSED*/
2571 static int
2572 pcic_callback(dev_info_t *dip, int (*handler)(), int arg)
2574 anp_t *anp = ddi_get_driver_private(dip);
2575 pcicdev_t *pcic = anp->an_private;
2577 if (handler != NULL) {
2578 pcic->pc_callback = handler;
2579 pcic->pc_cb_arg = arg;
2580 pcic->pc_flags |= PCF_CALLBACK;
2581 } else {
2582 pcic->pc_callback = NULL;
2583 pcic->pc_cb_arg = 0;
2584 pcic->pc_flags &= ~PCF_CALLBACK;
2587 * we're now registered with the nexus
2588 * it is acceptable to do callbacks at this point.
2589 * don't call back from here though since it could block
2591 return (PC_SUCCESS);
2595 * pcic_calc_speed (pcicdev_t *pcic, uint32_t speed)
2596 * calculate the speed bits from the specified memory speed
2597 * there may be more to do here
2600 static int
2601 pcic_calc_speed(pcicdev_t *pcic, uint32_t speed)
2603 uint32_t wspeed = 1; /* assume 1 wait state when unknown */
2604 uint32_t bspeed = PCIC_ISA_DEF_SYSCLK;
2606 switch (pcic->pc_type) {
2607 case PCIC_I82365SL:
2608 case PCIC_VADEM:
2609 case PCIC_VADEM_VG469:
2610 default:
2611 /* Intel chip wants it in waitstates */
2612 wspeed = mhztons(PCIC_ISA_DEF_SYSCLK) * 3;
2613 if (speed <= wspeed)
2614 wspeed = 0;
2615 else if (speed <= (wspeed += mhztons(bspeed)))
2616 wspeed = 1;
2617 else if (speed <= (wspeed += mhztons(bspeed)))
2618 wspeed = 2;
2619 else
2620 wspeed = 3;
2621 wspeed <<= 6; /* put in right bit positions */
2622 break;
2624 case PCIC_INTEL_i82092:
2625 wspeed = SYSMEM_82092_80NS;
2626 if (speed > 80)
2627 wspeed = SYSMEM_82092_100NS;
2628 if (speed > 100)
2629 wspeed = SYSMEM_82092_150NS;
2630 if (speed > 150)
2631 wspeed = SYSMEM_82092_200NS;
2632 if (speed > 200)
2633 wspeed = SYSMEM_82092_250NS;
2634 if (speed > 250)
2635 wspeed = SYSMEM_82092_600NS;
2636 wspeed <<= 5; /* put in right bit positions */
2637 break;
2639 } /* switch */
2641 return (wspeed);
2645 * These values are taken from the PC Card Standard Electrical Specification.
2646 * Generally the larger value is taken if 2 are possible.
2648 static struct pcic_card_times {
2649 uint16_t cycle; /* Speed as found in the atribute space of he card. */
2650 uint16_t setup; /* Corresponding address setup time. */
2651 uint16_t width; /* Corresponding width, OE or WE. */
2652 uint16_t hold; /* Corresponding data or address hold time. */
2653 } pcic_card_times[] = {
2656 * Note: The rounded up times for 250, 200 & 150 have been increased
2657 * due to problems with the 3-Com ethernet cards (pcelx) on UBIIi.
2658 * See BugID 00663.
2662 * Rounded up times Original times from
2663 * that add up to the the PCMCIA Spec.
2664 * cycle time.
2666 {600, 180, 370, 140}, /* 100, 300, 70 */
2667 {400, 120, 300, 90}, /* Made this one up */
2668 {250, 100, 190, 70}, /* 30, 150, 30 */
2669 {200, 80, 170, 70}, /* 20, 120, 30 */
2670 {150, 50, 110, 40}, /* 20, 80, 20 */
2671 {100, 40, 80, 40}, /* 10, 60, 15 */
2672 {0, 10, 60, 15} /* 10, 60, 15 */
2676 * pcic_set_cdtimers
2677 * This is specific to several Cirrus Logic chips
2679 static void
2680 pcic_set_cdtimers(pcicdev_t *pcic, int socket, uint32_t speed, int tset)
2682 int cmd, set, rec, offset, clk_pulse;
2683 struct pcic_card_times *ctp;
2685 if ((tset == IOMEM_CLTIMER_SET_1) || (tset == SYSMEM_CLTIMER_SET_1))
2686 offset = 3;
2687 else
2688 offset = 0;
2690 clk_pulse = mhztons(pcic->bus_speed);
2691 for (ctp = pcic_card_times; speed < ctp->cycle; ctp++)
2695 * Add (clk_pulse/2) and an extra 1 to account for rounding errors.
2697 set = ((ctp->setup + 10 + 1 + (clk_pulse/2))/clk_pulse) - 1;
2698 if (set < 0)
2699 set = 0;
2701 cmd = ((ctp->width + 10 + 1 + (clk_pulse/2))/clk_pulse) - 1;
2702 if (cmd < 0)
2703 cmd = 0;
2705 rec = ((ctp->hold + 10 + 1 + (clk_pulse/2))/clk_pulse) - 2;
2706 if (rec < 0)
2707 rec = 0;
2709 #if defined(PCIC_DEBUG)
2710 pcic_err(pcic->dip, 8, "pcic_set_cdtimers(%d, Timer Set %d)\n"
2711 "ct=%d, cp=%d, cmd=0x%x, setup=0x%x, rec=0x%x\n",
2712 (unsigned)speed, offset == 3 ? 1 : 0,
2713 ctp->cycle, clk_pulse, cmd, set, rec);
2714 #endif
2716 pcic_putb(pcic, socket, PCIC_TIME_COMMAND_0 + offset, cmd);
2717 pcic_putb(pcic, socket, PCIC_TIME_SETUP_0 + offset, set);
2718 pcic_putb(pcic, socket, PCIC_TIME_RECOVER_0 + offset, rec);
2722 * pcic_set_window
2723 * essentially the same as the Socket Services specification
2724 * We use socket and not adapter since they are identifiable
2725 * but the rest is the same
2727 * dip pcic driver's device information
2728 * window parameters for the request
2730 static int
2731 pcic_set_window(dev_info_t *dip, set_window_t *window)
2733 anp_t *anp = ddi_get_driver_private(dip);
2734 pcicdev_t *pcic = anp->an_private;
2735 int select;
2736 int socket, pages, which, ret;
2737 pcic_socket_t *sockp = &pcic->pc_sockets[window->socket];
2738 ra_return_t res;
2739 ndi_ra_request_t req;
2740 uint32_t base = window->base;
2742 #if defined(PCIC_DEBUG)
2743 if (pcic_debug) {
2744 cmn_err(CE_CONT, "pcic_set_window: entered\n");
2745 cmn_err(CE_CONT,
2746 "\twindow=%d, socket=%d, WindowSize=%d, speed=%d\n",
2747 window->window, window->socket, window->WindowSize,
2748 window->speed);
2749 cmn_err(CE_CONT,
2750 "\tbase=%x, state=%x\n", (unsigned)window->base,
2751 (unsigned)window->state);
2753 #endif
2756 * do some basic sanity checking on what we support
2757 * we don't do paged mode
2759 if (window->state & WS_PAGED) {
2760 cmn_err(CE_WARN, "pcic_set_window: BAD_ATTRIBUTE\n");
2761 return (BAD_ATTRIBUTE);
2765 * we don't care about previous mappings.
2766 * Card Services will deal with that so don't
2767 * even check
2770 socket = window->socket;
2772 if (!(window->state & WS_IO)) {
2773 int win, tmp;
2774 pcs_memwin_t *memp;
2775 #if defined(PCIC_DEBUG)
2776 if (pcic_debug)
2777 cmn_err(CE_CONT, "\twindow type is memory\n");
2778 #endif
2779 /* this is memory window mapping */
2780 win = window->window % PCIC_NUMWINSOCK;
2781 tmp = window->window / PCIC_NUMWINSOCK;
2783 /* only windows 2-6 can do memory mapping */
2784 if (tmp != window->socket || win < PCIC_IOWINDOWS) {
2785 cmn_err(CE_CONT,
2786 "\tattempt to map to non-mem window\n");
2787 return (BAD_WINDOW);
2790 if (window->WindowSize == 0)
2791 window->WindowSize = MEM_MIN;
2792 else if ((window->WindowSize & (PCIC_PAGE-1)) != 0) {
2793 cmn_err(CE_WARN, "pcic_set_window: BAD_SIZE\n");
2794 return (BAD_SIZE);
2797 mutex_enter(&pcic->pc_lock); /* protect the registers */
2799 memp = &sockp->pcs_windows[win].mem;
2800 memp->pcw_speed = window->speed;
2802 win -= PCIC_IOWINDOWS; /* put in right range */
2804 if (window->WindowSize != memp->pcw_len)
2805 which = memp->pcw_len;
2806 else
2807 which = 0;
2809 if (window->state & WS_ENABLED) {
2810 uint32_t wspeed;
2811 #if defined(PCIC_DEBUG)
2812 if (pcic_debug) {
2813 cmn_err(CE_CONT,
2814 "\tbase=%x, win=%d\n", (unsigned)base,
2815 win);
2816 if (which)
2817 cmn_err(CE_CONT,
2818 "\tneed to remap window\n");
2820 #endif
2822 if (which && (memp->pcw_status & PCW_MAPPED)) {
2823 ddi_regs_map_free(&memp->pcw_handle);
2824 res.ra_addr_lo = memp->pcw_base;
2825 res.ra_len = memp->pcw_len;
2826 (void) pcmcia_free_mem(memp->res_dip, &res);
2827 memp->pcw_status &= ~(PCW_MAPPED|PCW_ENABLED);
2828 memp->pcw_hostmem = NULL;
2829 memp->pcw_base = NULL;
2830 memp->pcw_len = 0;
2833 which = window->WindowSize >> PAGE_SHIFT;
2835 if (!(memp->pcw_status & PCW_MAPPED)) {
2836 ret = 0;
2838 memp->pcw_base = base;
2839 bzero(&req, sizeof (req));
2840 req.ra_len = which << PAGE_SHIFT;
2841 req.ra_addr = (uint64_t)memp->pcw_base;
2842 req.ra_boundbase = pcic->pc_base;
2843 req.ra_boundlen = pcic->pc_bound;
2844 req.ra_flags = (memp->pcw_base ?
2845 NDI_RA_ALLOC_SPECIFIED : 0) |
2846 NDI_RA_ALLOC_BOUNDED;
2847 req.ra_align_mask =
2848 (PAGESIZE - 1) | (PCIC_PAGE - 1);
2849 #if defined(PCIC_DEBUG)
2850 pcic_err(dip, 8,
2851 "\tlen 0x%"PRIx64
2852 "addr 0x%"PRIx64"bbase 0x%"PRIx64
2853 " blen 0x%"PRIx64" flags 0x%x"
2854 " algn 0x%"PRIx64"\n",
2855 req.ra_len, req.ra_addr,
2856 req.ra_boundbase,
2857 req.ra_boundlen, req.ra_flags,
2858 req.ra_align_mask);
2859 #endif
2861 ret = pcmcia_alloc_mem(dip, &req, &res,
2862 &memp->res_dip);
2863 if (ret == DDI_FAILURE) {
2864 mutex_exit(&pcic->pc_lock);
2865 cmn_err(CE_WARN,
2866 "\tpcmcia_alloc_mem() failed\n");
2867 return (BAD_SIZE);
2869 memp->pcw_base = res.ra_addr_lo;
2870 base = memp->pcw_base;
2872 #if defined(PCIC_DEBUG)
2873 if (pcic_debug)
2874 cmn_err(CE_CONT,
2875 "\tsetwindow: new base=%x\n",
2876 (unsigned)memp->pcw_base);
2877 #endif
2878 memp->pcw_len = window->WindowSize;
2880 which = pcmcia_map_reg(pcic->dip,
2881 window->child,
2882 &res,
2883 (uint32_t)(window->state &
2884 0xffff) |
2885 (window->socket << 16),
2886 (caddr_t *)&memp->pcw_hostmem,
2887 &memp->pcw_handle,
2888 &window->attr, NULL);
2890 if (which != DDI_SUCCESS) {
2892 cmn_err(CE_WARN, "\tpcmcia_map_reg() "
2893 "failed\n");
2895 res.ra_addr_lo = memp->pcw_base;
2896 res.ra_len = memp->pcw_len;
2897 (void) pcmcia_free_mem(memp->res_dip,
2898 &res);
2900 mutex_exit(&pcic->pc_lock);
2902 return (BAD_WINDOW);
2904 memp->pcw_status |= PCW_MAPPED;
2905 #if defined(PCIC_DEBUG)
2906 if (pcic_debug)
2907 cmn_err(CE_CONT,
2908 "\tmap=%x, hostmem=%p\n",
2909 which,
2910 (void *)memp->pcw_hostmem);
2911 #endif
2912 } else {
2913 base = memp->pcw_base;
2916 /* report the handle back to caller */
2917 window->handle = memp->pcw_handle;
2919 #if defined(PCIC_DEBUG)
2920 if (pcic_debug) {
2921 cmn_err(CE_CONT,
2922 "\twindow mapped to %x@%x len=%d\n",
2923 (unsigned)window->base,
2924 (unsigned)memp->pcw_base,
2925 memp->pcw_len);
2927 #endif
2929 /* find the register set offset */
2930 select = win * PCIC_MEM_1_OFFSET;
2931 #if defined(PCIC_DEBUG)
2932 if (pcic_debug)
2933 cmn_err(CE_CONT, "\tselect=%x\n", select);
2934 #endif
2937 * at this point, the register window indicator has
2938 * been converted to be an offset from the first
2939 * set of registers that are used for programming
2940 * the window mapping and the offset used to select
2941 * the correct set of registers to access the
2942 * specified socket. This allows basing everything
2943 * off the _0 window
2946 /* map the physical page base address */
2947 which = (window->state & WS_16BIT) ? SYSMEM_DATA_16 : 0;
2948 which |= (window->speed <= MEM_SPEED_MIN) ?
2949 SYSMEM_ZERO_WAIT : 0;
2951 /* need to select register set */
2952 select = PCIC_MEM_1_OFFSET * win;
2954 pcic_putb(pcic, socket,
2955 PCIC_SYSMEM_0_STARTLOW + select,
2956 SYSMEM_LOW(base));
2957 pcic_putb(pcic, socket,
2958 PCIC_SYSMEM_0_STARTHI + select,
2959 SYSMEM_HIGH(base) | which);
2962 * Some adapters can decode window addresses greater
2963 * than 16-bits worth, so handle them here.
2965 switch (pcic->pc_type) {
2966 case PCIC_INTEL_i82092:
2967 pcic_putb(pcic, socket,
2968 PCIC_82092_CPAGE,
2969 SYSMEM_EXT(base));
2970 break;
2971 case PCIC_CL_PD6729:
2972 case PCIC_CL_PD6730:
2973 clext_reg_write(pcic, socket,
2974 PCIC_CLEXT_MMAP0_UA + win,
2975 SYSMEM_EXT(base));
2976 break;
2977 case PCIC_TI_PCI1130:
2979 * Note that the TI chip has one upper byte
2980 * per socket so all windows get bound to a
2981 * 16MB segment. This must be detected and
2982 * handled appropriately. We can detect that
2983 * it is done by seeing if the pc_base has
2984 * changed and changing when the register
2985 * is first set. This will force the bounds
2986 * to be correct.
2988 if (pcic->pc_bound == 0xffffffff) {
2989 pcic_putb(pcic, socket,
2990 PCIC_TI_WINDOW_PAGE_PCI,
2991 SYSMEM_EXT(base));
2992 pcic->pc_base = SYSMEM_EXT(base) << 24;
2993 pcic->pc_bound = 0x1000000;
2995 break;
2996 case PCIC_TI_PCI1031:
2997 case PCIC_TI_PCI1131:
2998 case PCIC_TI_PCI1250:
2999 case PCIC_TI_PCI1225:
3000 case PCIC_TI_PCI1221:
3001 case PCIC_SMC_34C90:
3002 case PCIC_CL_PD6832:
3003 case PCIC_RICOH_RL5C466:
3004 case PCIC_TI_PCI1410:
3005 case PCIC_ENE_1410:
3006 case PCIC_TI_PCI1510:
3007 case PCIC_TI_PCI1520:
3008 case PCIC_O2_OZ6912:
3009 case PCIC_TI_PCI1420:
3010 case PCIC_ENE_1420:
3011 case PCIC_TI_VENDOR:
3012 case PCIC_TOSHIBA_TOPIC100:
3013 case PCIC_TOSHIBA_TOPIC95:
3014 case PCIC_TOSHIBA_VENDOR:
3015 case PCIC_RICOH_VENDOR:
3016 case PCIC_O2MICRO_VENDOR:
3017 pcic_putb(pcic, socket,
3018 PCIC_YENTA_MEM_PAGE + win,
3019 SYSMEM_EXT(base));
3020 break;
3021 default:
3022 cmn_err(CE_NOTE, "pcic_set_window: unknown "
3023 "cardbus vendor:0x%X\n",
3024 pcic->pc_type);
3025 pcic_putb(pcic, socket,
3026 PCIC_YENTA_MEM_PAGE + win,
3027 SYSMEM_EXT(base));
3029 break;
3030 } /* switch */
3033 * specify the length of the mapped range
3034 * we convert to pages (rounding up) so that
3035 * the hardware gets the right thing
3037 pages = (window->WindowSize+PCIC_PAGE-1)/PCIC_PAGE;
3040 * Setup this window's timing.
3042 switch (pcic->pc_type) {
3043 case PCIC_CL_PD6729:
3044 case PCIC_CL_PD6730:
3045 case PCIC_CL_PD6710:
3046 case PCIC_CL_PD6722:
3047 wspeed = SYSMEM_CLTIMER_SET_0;
3048 pcic_set_cdtimers(pcic, socket,
3049 window->speed,
3050 wspeed);
3051 break;
3053 case PCIC_INTEL_i82092:
3054 default:
3055 wspeed = pcic_calc_speed(pcic, window->speed);
3056 break;
3057 } /* switch */
3059 #if defined(PCIC_DEBUG)
3060 if (pcic_debug)
3061 cmn_err(CE_CONT,
3062 "\twindow %d speed bits = %x for "
3063 "%dns\n",
3064 win, (unsigned)wspeed, window->speed);
3065 #endif
3067 pcic_putb(pcic, socket, PCIC_SYSMEM_0_STOPLOW + select,
3068 SYSMEM_LOW(base +
3069 (pages * PCIC_PAGE)-1));
3071 wspeed |= SYSMEM_HIGH(base + (pages * PCIC_PAGE)-1);
3072 pcic_putb(pcic, socket, PCIC_SYSMEM_0_STOPHI + select,
3073 wspeed);
3076 * now map the card's memory pages - we start with page
3078 * we also default to AM -- set page might change it
3080 base = memp->pcw_base;
3081 pcic_putb(pcic, socket,
3082 PCIC_CARDMEM_0_LOW + select,
3083 CARDMEM_LOW(0 - (uint32_t)base));
3085 pcic_putb(pcic, socket,
3086 PCIC_CARDMEM_0_HI + select,
3087 CARDMEM_HIGH(0 - (uint32_t)base) |
3088 CARDMEM_REG_ACTIVE);
3091 * enable the window even though redundant
3092 * and SetPage may do it again.
3094 select = pcic_getb(pcic, socket,
3095 PCIC_MAPPING_ENABLE);
3096 select |= SYSMEM_WINDOW(win);
3097 pcic_putb(pcic, socket, PCIC_MAPPING_ENABLE, select);
3098 memp->pcw_offset = 0;
3099 memp->pcw_status |= PCW_ENABLED;
3100 } else {
3102 * not only do we unmap the memory, the
3103 * window has been turned off.
3105 if (which && memp->pcw_status & PCW_MAPPED) {
3106 ddi_regs_map_free(&memp->pcw_handle);
3107 res.ra_addr_lo = memp->pcw_base;
3108 res.ra_len = memp->pcw_len;
3109 (void) pcmcia_free_mem(memp->res_dip, &res);
3110 memp->pcw_hostmem = NULL;
3111 memp->pcw_status &= ~PCW_MAPPED;
3114 /* disable current mapping */
3115 select = pcic_getb(pcic, socket, PCIC_MAPPING_ENABLE);
3116 select &= ~SYSMEM_WINDOW(win);
3117 pcic_putb(pcic, socket, PCIC_MAPPING_ENABLE, select);
3118 memp->pcw_status &= ~PCW_ENABLED;
3120 memp->pcw_len = window->WindowSize;
3121 window->handle = memp->pcw_handle;
3122 #if defined(PCIC_DEBUG)
3123 if (pcic_debug)
3124 xxdmp_all_regs(pcic, window->socket, -1);
3125 #endif
3126 } else {
3128 * This is a request for an IO window
3130 int win, tmp;
3131 pcs_iowin_t *winp;
3132 /* I/O windows */
3133 #if defined(PCIC_DEBUG)
3134 if (pcic_debug)
3135 cmn_err(CE_CONT, "\twindow type is I/O\n");
3136 #endif
3138 /* only windows 0 and 1 can do I/O */
3139 win = window->window % PCIC_NUMWINSOCK;
3140 tmp = window->window / PCIC_NUMWINSOCK;
3142 if (win >= PCIC_IOWINDOWS || tmp != window->socket) {
3143 cmn_err(CE_WARN,
3144 "\twindow is out of range (%d)\n",
3145 window->window);
3146 return (BAD_WINDOW);
3149 mutex_enter(&pcic->pc_lock); /* protect the registers */
3151 winp = &sockp->pcs_windows[win].io;
3152 winp->pcw_speed = window->speed;
3153 if (window->WindowSize != 1 && window->WindowSize & 1) {
3154 /* we don't want an odd-size window */
3155 window->WindowSize++;
3157 winp->pcw_len = window->WindowSize;
3159 if (window->state & WS_ENABLED) {
3160 if (winp->pcw_status & PCW_MAPPED) {
3161 ddi_regs_map_free(&winp->pcw_handle);
3162 res.ra_addr_lo = winp->pcw_base;
3163 res.ra_len = winp->pcw_len;
3164 (void) pcmcia_free_io(winp->res_dip, &res);
3165 winp->pcw_status &= ~(PCW_MAPPED|PCW_ENABLED);
3169 * if the I/O address wasn't allocated, allocate
3170 * it now. If it was allocated, it better
3171 * be free to use.
3172 * The winp->pcw_offset value is set and used
3173 * later on if the particular adapter
3174 * that we're running on has the ability
3175 * to translate IO accesses to the card
3176 * (such as some adapters in the Cirrus
3177 * Logic family).
3179 winp->pcw_offset = 0;
3182 * Setup the request parameters for the
3183 * requested base and length. If
3184 * we're on an adapter that has
3185 * IO window offset registers, then
3186 * we don't need a specific base
3187 * address, just a length, and then
3188 * we'll cause the correct IO address
3189 * to be generated on the socket by
3190 * setting up the IO window offset
3191 * registers.
3192 * For adapters that support this capability, we
3193 * always use the IO window offset registers,
3194 * even if the passed base/length would be in
3195 * range.
3197 base = window->base;
3198 bzero(&req, sizeof (req));
3199 req.ra_len = window->WindowSize;
3201 req.ra_addr = (uint64_t)
3202 ((pcic->pc_flags & PCF_IO_REMAP) ? 0 : base);
3203 req.ra_flags = (req.ra_addr) ?
3204 NDI_RA_ALLOC_SPECIFIED : 0;
3206 req.ra_flags |= NDI_RA_ALIGN_SIZE;
3207 /* need to rethink this */
3208 req.ra_boundbase = pcic->pc_iobase;
3209 req.ra_boundlen = pcic->pc_iobound;
3210 req.ra_flags |= NDI_RA_ALLOC_BOUNDED;
3212 #if defined(PCIC_DEBUG)
3213 pcic_err(dip, 8,
3214 "\tlen 0x%"PRIx64" addr 0x%"PRIx64
3215 "bbase 0x%"PRIx64
3216 "blen 0x%"PRIx64" flags 0x%x algn 0x%"
3217 PRIx64"\n",
3218 req.ra_len, (uint64_t)req.ra_addr,
3219 req.ra_boundbase,
3220 req.ra_boundlen, req.ra_flags,
3221 req.ra_align_mask);
3222 #endif
3225 * Try to allocate the space. If we fail this,
3226 * return the appropriate error depending
3227 * on whether the caller specified a
3228 * specific base address or not.
3230 if (pcmcia_alloc_io(dip, &req, &res,
3231 &winp->res_dip) == DDI_FAILURE) {
3232 winp->pcw_status &= ~PCW_ENABLED;
3233 mutex_exit(&pcic->pc_lock);
3234 cmn_err(CE_WARN, "Failed to alloc I/O:\n"
3235 "\tlen 0x%" PRIx64 " addr 0x%" PRIx64
3236 "bbase 0x%" PRIx64
3237 "blen 0x%" PRIx64 "flags 0x%x"
3238 "algn 0x%" PRIx64 "\n",
3239 req.ra_len, req.ra_addr,
3240 req.ra_boundbase,
3241 req.ra_boundlen, req.ra_flags,
3242 req.ra_align_mask);
3244 return (base?BAD_BASE:BAD_SIZE);
3245 } /* pcmcia_alloc_io */
3248 * Don't change the original base. Either we use
3249 * the offset registers below (PCF_IO_REMAP is set)
3250 * or it was allocated correctly anyway.
3252 winp->pcw_base = res.ra_addr_lo;
3254 #if defined(PCIC_DEBUG)
3255 pcic_err(dip, 8,
3256 "\tsetwindow: new base=%x orig base 0x%x\n",
3257 (unsigned)winp->pcw_base, base);
3258 #endif
3260 if ((which = pcmcia_map_reg(pcic->dip,
3261 window->child,
3262 &res,
3263 (uint32_t)(window->state &
3264 0xffff) |
3265 (window->socket << 16),
3266 (caddr_t *)&winp->pcw_hostmem,
3267 &winp->pcw_handle,
3268 &window->attr,
3269 base)) != DDI_SUCCESS) {
3271 cmn_err(CE_WARN, "pcmcia_map_reg()"
3272 "failed\n");
3274 res.ra_addr_lo = winp->pcw_base;
3275 res.ra_len = winp->pcw_len;
3276 (void) pcmcia_free_io(winp->res_dip,
3277 &res);
3279 mutex_exit(&pcic->pc_lock);
3280 return (BAD_WINDOW);
3283 window->handle = winp->pcw_handle;
3284 winp->pcw_status |= PCW_MAPPED;
3286 /* find the register set offset */
3287 select = win * PCIC_IO_OFFSET;
3289 #if defined(PCIC_DEBUG)
3290 if (pcic_debug) {
3291 cmn_err(CE_CONT,
3292 "\tenable: window=%d, select=%x, "
3293 "base=%x, handle=%p\n",
3294 win, select,
3295 (unsigned)window->base,
3296 (void *)window->handle);
3298 #endif
3300 * at this point, the register window indicator has
3301 * been converted to be an offset from the first
3302 * set of registers that are used for programming
3303 * the window mapping and the offset used to select
3304 * the correct set of registers to access the
3305 * specified socket. This allows basing everything
3306 * off the _0 window
3309 /* map the I/O base in */
3310 pcic_putb(pcic, socket,
3311 PCIC_IO_ADDR_0_STARTLOW + select,
3312 LOW_BYTE((uint32_t)winp->pcw_base));
3313 pcic_putb(pcic, socket,
3314 PCIC_IO_ADDR_0_STARTHI + select,
3315 HIGH_BYTE((uint32_t)winp->pcw_base));
3317 pcic_putb(pcic, socket,
3318 PCIC_IO_ADDR_0_STOPLOW + select,
3319 LOW_BYTE((uint32_t)winp->pcw_base +
3320 window->WindowSize - 1));
3321 pcic_putb(pcic, socket,
3322 PCIC_IO_ADDR_0_STOPHI + select,
3323 HIGH_BYTE((uint32_t)winp->pcw_base +
3324 window->WindowSize - 1));
3327 * We've got the requested IO space, now see if we
3328 * need to adjust the IO window offset registers
3329 * so that the correct IO address is generated
3330 * at the socket. If this window doesn't have
3331 * this capability, then we're all done setting
3332 * up the IO resources.
3334 if (pcic->pc_flags & PCF_IO_REMAP) {
3338 * Note that only 16 bits are used to program
3339 * the registers but leave 32 bits on pcw_offset
3340 * so that we can generate the original base
3341 * in get_window()
3343 winp->pcw_offset = (base - winp->pcw_base);
3345 pcic_putb(pcic, socket,
3346 PCIC_IO_OFFSET_LOW +
3347 (win * PCIC_IO_OFFSET_OFFSET),
3348 winp->pcw_offset & 0x0ff);
3349 pcic_putb(pcic, socket,
3350 PCIC_IO_OFFSET_HI +
3351 (win * PCIC_IO_OFFSET_OFFSET),
3352 (winp->pcw_offset >> 8) & 0x0ff);
3354 } /* PCF_IO_REMAP */
3356 /* now get the other details (size, etc) right */
3359 * Set the data size control bits here. Most of the
3360 * adapters will ignore IOMEM_16BIT when
3361 * IOMEM_IOCS16 is set, except for the Intel
3362 * 82092, which only pays attention to the
3363 * IOMEM_16BIT bit. Sigh... Intel can't even
3364 * make a proper clone of their own chip.
3365 * The 82092 also apparently can't set the timing
3366 * of I/O windows.
3368 which = (window->state & WS_16BIT) ?
3369 (IOMEM_16BIT | IOMEM_IOCS16) : 0;
3371 switch (pcic->pc_type) {
3372 case PCIC_CL_PD6729:
3373 case PCIC_CL_PD6730:
3374 case PCIC_CL_PD6710:
3375 case PCIC_CL_PD6722:
3376 case PCIC_CL_PD6832:
3378 * Select Timer Set 1 - this will take
3379 * effect when the PCIC_IO_CONTROL
3380 * register is written to later on;
3381 * the call to pcic_set_cdtimers
3382 * just sets up the timer itself.
3384 which |= IOMEM_CLTIMER_SET_1;
3385 pcic_set_cdtimers(pcic, socket,
3386 window->speed,
3387 IOMEM_CLTIMER_SET_1);
3388 which |= IOMEM_IOCS16;
3389 break;
3390 case PCIC_TI_PCI1031:
3392 if (window->state & WS_16BIT)
3393 which |= IOMEM_WAIT16;
3395 break;
3396 case PCIC_TI_PCI1130:
3398 if (window->state & WS_16BIT)
3399 which |= IOMEM_WAIT16;
3401 break;
3402 case PCIC_INTEL_i82092:
3403 break;
3404 default:
3405 if (window->speed >
3406 mhztons(pcic->bus_speed) * 3)
3407 which |= IOMEM_WAIT16;
3408 #ifdef notdef
3409 if (window->speed <
3410 mhztons(pcic->bus_speed) * 6)
3411 which |= IOMEM_ZERO_WAIT;
3412 #endif
3413 break;
3414 } /* switch (pc_type) */
3417 * Setup the data width and timing
3419 select = pcic_getb(pcic, socket, PCIC_IO_CONTROL);
3420 select &= ~(PCIC_IO_WIN_MASK << (win * 4));
3421 select |= IOMEM_SETWIN(win, which);
3422 pcic_putb(pcic, socket, PCIC_IO_CONTROL, select);
3425 * Enable the IO window
3427 select = pcic_getb(pcic, socket, PCIC_MAPPING_ENABLE);
3428 pcic_putb(pcic, socket, PCIC_MAPPING_ENABLE,
3429 select | IOMEM_WINDOW(win));
3431 winp->pcw_status |= PCW_ENABLED;
3433 #if defined(PCIC_DEBUG)
3434 if (pcic_debug) {
3435 cmn_err(CE_CONT,
3436 "\twhich = %x, select = %x (%x)\n",
3437 which, select,
3438 IOMEM_SETWIN(win, which));
3439 xxdmp_all_regs(pcic, window->socket * 0x40, 24);
3441 #endif
3442 } else {
3444 * not only do we unmap the IO space, the
3445 * window has been turned off.
3447 if (winp->pcw_status & PCW_MAPPED) {
3448 ddi_regs_map_free(&winp->pcw_handle);
3449 res.ra_addr_lo = winp->pcw_base;
3450 res.ra_len = winp->pcw_len;
3451 (void) pcmcia_free_io(winp->res_dip, &res);
3452 winp->pcw_status &= ~PCW_MAPPED;
3455 /* disable current mapping */
3456 select = pcic_getb(pcic, socket,
3457 PCIC_MAPPING_ENABLE);
3458 pcic_putb(pcic, socket, PCIC_MAPPING_ENABLE,
3459 select &= ~IOMEM_WINDOW(win));
3460 winp->pcw_status &= ~PCW_ENABLED;
3462 winp->pcw_base = 0;
3463 winp->pcw_len = 0;
3464 winp->pcw_offset = 0;
3465 window->base = 0;
3466 /* now make sure we don't accidentally re-enable */
3467 /* find the register set offset */
3468 select = win * PCIC_IO_OFFSET;
3469 pcic_putb(pcic, socket,
3470 PCIC_IO_ADDR_0_STARTLOW + select, 0);
3471 pcic_putb(pcic, socket,
3472 PCIC_IO_ADDR_0_STARTHI + select, 0);
3473 pcic_putb(pcic, socket,
3474 PCIC_IO_ADDR_0_STOPLOW + select, 0);
3475 pcic_putb(pcic, socket,
3476 PCIC_IO_ADDR_0_STOPHI + select, 0);
3479 mutex_exit(&pcic->pc_lock);
3481 return (SUCCESS);
3485 * pcic_card_state()
3486 * compute the instantaneous Card State information
3488 static int
3489 pcic_card_state(pcicdev_t *pcic, pcic_socket_t *sockp)
3491 int value, result;
3492 #if defined(PCIC_DEBUG)
3493 int orig_value;
3494 #endif
3496 mutex_enter(&pcic->pc_lock); /* protect the registers */
3498 value = pcic_getb(pcic, sockp->pcs_socket, PCIC_INTERFACE_STATUS);
3500 #if defined(PCIC_DEBUG)
3501 orig_value = value;
3502 if (pcic_debug >= 8)
3503 cmn_err(CE_CONT, "pcic_card_state(%p) if status = %b for %d\n",
3504 (void *)sockp,
3505 value,
3506 "\020\1BVD1\2BVD2\3CD1\4CD2\5WP\6RDY\7PWR\10~GPI",
3507 sockp->pcs_socket);
3508 #endif
3510 * Lie to socket services if we are not ready.
3511 * This is when we are starting up or during debounce timeouts
3512 * or if the card is a cardbus card.
3514 if (!(sockp->pcs_flags & (PCS_STARTING|PCS_CARD_ISCARDBUS)) &&
3515 !sockp->pcs_debounce_id &&
3516 (value & PCIC_ISTAT_CD_MASK) == PCIC_CD_PRESENT_OK) {
3517 result = SBM_CD;
3519 if (value & PCIC_WRITE_PROTECT || !(value & PCIC_POWER_ON))
3520 result |= SBM_WP;
3521 if (value & PCIC_POWER_ON) {
3522 if (value & PCIC_READY)
3523 result |= SBM_RDYBSY;
3524 value = (~value) & (PCIC_BVD1 | PCIC_BVD2);
3525 if (value & PCIC_BVD1)
3526 result |= SBM_BVD1;
3527 if (value & PCIC_BVD2)
3528 result |= SBM_BVD2;
3530 } else
3531 result = 0;
3533 mutex_exit(&pcic->pc_lock);
3535 #if defined(PCIC_DEBUG)
3536 pcic_err(pcic->dip, 8,
3537 "pcic_card_state(%p) if status = %b for %d (rval=0x%x)\n",
3538 (void *) sockp, orig_value,
3539 "\020\1BVD1\2BVD2\3CD1\4CD2\5WP\6RDY\7PWR\10~GPI",
3540 sockp->pcs_socket, result);
3541 #endif
3543 return (result);
3547 * pcic_set_page()
3548 * SocketServices SetPage function
3549 * set the page of PC Card memory that should be in the mapped
3550 * window
3552 /*ARGSUSED*/
3553 static int
3554 pcic_set_page(dev_info_t *dip, set_page_t *page)
3556 anp_t *anp = ddi_get_driver_private(dip);
3557 pcicdev_t *pcic = anp->an_private;
3558 int select;
3559 int which, socket, window;
3560 uint32_t base;
3561 pcs_memwin_t *memp;
3563 /* get real socket/window numbers */
3564 window = page->window % PCIC_NUMWINSOCK;
3565 socket = page->window / PCIC_NUMWINSOCK;
3567 #if defined(PCIC_DEBUG)
3568 if (pcic_debug) {
3569 cmn_err(CE_CONT,
3570 "pcic_set_page: window=%d, socket=%d, page=%d\n",
3571 window, socket, page->page);
3573 #endif
3574 /* only windows 2-6 work on memory */
3575 if (window < PCIC_IOWINDOWS)
3576 return (BAD_WINDOW);
3578 /* only one page supported (but any size) */
3579 if (page->page != 0)
3580 return (BAD_PAGE);
3582 mutex_enter(&pcic->pc_lock); /* protect the registers */
3584 memp = &pcic->pc_sockets[socket].pcs_windows[window].mem;
3585 window -= PCIC_IOWINDOWS;
3587 #if defined(PCIC_DEBUG)
3588 if (pcic_debug)
3589 cmn_err(CE_CONT, "\tpcw_base=%x, pcw_hostmem=%p, pcw_len=%x\n",
3590 (uint32_t)memp->pcw_base,
3591 (void *)memp->pcw_hostmem, memp->pcw_len);
3592 #endif
3594 /* window must be enabled */
3595 if (!(memp->pcw_status & PCW_ENABLED))
3596 return (BAD_ATTRIBUTE);
3598 /* find the register set offset */
3599 select = window * PCIC_MEM_1_OFFSET;
3600 #if defined(PCIC_DEBUG)
3601 if (pcic_debug)
3602 cmn_err(CE_CONT, "\tselect=%x\n", select);
3603 #endif
3606 * now map the card's memory pages - we start with page 0
3609 which = 0; /* assume simple case */
3610 if (page->state & PS_ATTRIBUTE) {
3611 which |= CARDMEM_REG_ACTIVE;
3612 memp->pcw_status |= PCW_ATTRIBUTE;
3613 } else {
3614 memp->pcw_status &= ~PCW_ATTRIBUTE;
3618 * if caller says Write Protect, enforce it.
3620 if (page->state & PS_WP) {
3621 which |= CARDMEM_WRITE_PROTECT;
3622 memp->pcw_status |= PCW_WP;
3623 } else {
3624 memp->pcw_status &= ~PCW_WP;
3626 #if defined(PCIC_DEBUG)
3627 if (pcic_debug) {
3628 cmn_err(CE_CONT, "\tmemory type = %s\n",
3629 (which & CARDMEM_REG_ACTIVE) ? "attribute" : "common");
3630 if (which & CARDMEM_WRITE_PROTECT)
3631 cmn_err(CE_CONT, "\twrite protect\n");
3632 cmn_err(CE_CONT, "\tpage offset=%x pcw_base=%x (%x)\n",
3633 (unsigned)page->offset,
3634 (unsigned)memp->pcw_base,
3635 (int)page->offset - (int)memp->pcw_base & 0xffffff);
3637 #endif
3638 /* address computation based on 64MB range and not larger */
3639 base = (uint32_t)memp->pcw_base & 0x3ffffff;
3640 pcic_putb(pcic, socket, PCIC_CARDMEM_0_LOW + select,
3641 CARDMEM_LOW((int)page->offset - (int)base));
3642 (void) pcic_getb(pcic, socket, PCIC_CARDMEM_0_LOW + select);
3643 pcic_putb(pcic, socket, PCIC_CARDMEM_0_HI + select,
3644 CARDMEM_HIGH((int)page->offset - base) | which);
3645 (void) pcic_getb(pcic, socket, PCIC_CARDMEM_0_HI + select);
3648 * while not really necessary, this just makes sure
3649 * nothing turned the window off behind our backs
3651 which = pcic_getb(pcic, socket, PCIC_MAPPING_ENABLE);
3652 which |= SYSMEM_WINDOW(window);
3653 pcic_putb(pcic, socket, PCIC_MAPPING_ENABLE, which);
3654 (void) pcic_getb(pcic, socket, PCIC_MAPPING_ENABLE);
3656 memp->pcw_offset = (off_t)page->offset;
3658 #if defined(PCIC_DEBUG)
3659 if (pcic_debug) {
3660 cmn_err(CE_CONT, "\tbase=%p, *base=%x\n",
3661 (void *)memp->pcw_hostmem,
3662 (uint32_t)*memp->pcw_hostmem);
3664 xxdmp_all_regs(pcic, socket, -1);
3666 cmn_err(CE_CONT, "\tbase=%p, *base=%x\n",
3667 (void *)memp->pcw_hostmem,
3668 (uint32_t)*memp->pcw_hostmem);
3670 #endif
3672 if (which & PCW_ATTRIBUTE)
3673 pcic_mswait(pcic, socket, 2);
3675 mutex_exit(&pcic->pc_lock);
3677 return (SUCCESS);
3681 * pcic_set_vcc_level()
3683 * set voltage based on adapter information
3685 * this routine implements a limited solution for support of 3.3v cards.
3686 * the general solution, which would fully support the pcmcia spec
3687 * as far as allowing client drivers to request which voltage levels
3688 * to be set, requires more framework support and driver changes - ess
3690 static int
3691 pcic_set_vcc_level(pcicdev_t *pcic, set_socket_t *socket)
3693 uint32_t socket_present_state;
3695 #if defined(PCIC_DEBUG)
3696 if (pcic_debug) {
3697 cmn_err(CE_CONT,
3698 "pcic_set_vcc_level(pcic=%p, VccLevel=%d)\n",
3699 (void *)pcic, socket->VccLevel);
3701 #endif
3704 * check VccLevel
3705 * if this is zero, power is being turned off
3706 * if it is non-zero, power is being turned on.
3708 if (socket->VccLevel == 0) {
3709 return (0);
3713 * range checking for sanity's sake
3715 if (socket->VccLevel >= pcic->pc_numpower) {
3716 return (BAD_VCC);
3719 switch (pcic->pc_io_type) {
3721 * Yenta-compliant adapters have vcc info in the extended registers
3722 * Other adapters can be added as needed, but the 'default' case
3723 * has been left as it was previously so as not to break existing
3724 * adapters.
3726 case PCIC_IO_TYPE_YENTA:
3728 * Here we ignore the VccLevel passed in and read the
3729 * card type from the adapter socket present state register
3731 socket_present_state =
3732 ddi_get32(pcic->handle, (uint32_t *)(pcic->ioaddr +
3733 PCIC_PRESENT_STATE_REG));
3734 #if defined(PCIC_DEBUG)
3735 if (pcic_debug) {
3736 cmn_err(CE_CONT,
3737 "socket present state = 0x%x\n",
3738 socket_present_state);
3740 #endif
3741 switch (socket_present_state & PCIC_VCC_MASK) {
3742 case PCIC_VCC_3VCARD:
3743 /* fall through */
3744 case PCIC_VCC_3VCARD|PCIC_VCC_5VCARD:
3745 socket->VccLevel = PCIC_VCC_3VLEVEL;
3746 return
3747 (POWER_3VCARD_ENABLE|POWER_OUTPUT_ENABLE);
3748 case PCIC_VCC_5VCARD:
3749 socket->VccLevel = PCIC_VCC_5VLEVEL;
3750 return
3751 (POWER_CARD_ENABLE|POWER_OUTPUT_ENABLE);
3752 default:
3754 * if no card is present, this can be the
3755 * case of a client making a SetSocket call
3756 * after card removal. In this case we return
3757 * the current power level
3759 return ((unsigned)ddi_get8(pcic->handle,
3760 pcic->ioaddr + CB_R2_OFFSET +
3761 PCIC_POWER_CONTROL));
3764 default:
3766 switch (socket->VccLevel) {
3767 case PCIC_VCC_3VLEVEL:
3768 return (BAD_VCC);
3769 case PCIC_VCC_5VLEVEL:
3770 /* enable Vcc */
3771 return (POWER_CARD_ENABLE|POWER_OUTPUT_ENABLE);
3772 default:
3773 return (BAD_VCC);
3780 * pcic_set_socket()
3781 * Socket Services SetSocket call
3782 * sets basic socket configuration
3784 static int
3785 pcic_set_socket(dev_info_t *dip, set_socket_t *socket)
3787 anp_t *anp = ddi_get_driver_private(dip);
3788 pcicdev_t *pcic = anp->an_private;
3789 pcic_socket_t *sockp = &pcic->pc_sockets[socket->socket];
3790 int irq, interrupt, mirq;
3791 int powerlevel = 0;
3792 int ind, value, orig_pwrctl;
3794 #if defined(PCIC_DEBUG)
3795 if (pcic_debug) {
3796 cmn_err(CE_CONT,
3797 "pcic_set_socket(dip=%p, socket=%d)"
3798 " Vcc=%d Vpp1=%d Vpp2=%d\n", (void *)dip,
3799 socket->socket, socket->VccLevel, socket->Vpp1Level,
3800 socket->Vpp2Level);
3802 #endif
3804 * check VccLevel, etc. before setting mutex
3805 * if this is zero, power is being turned off
3806 * if it is non-zero, power is being turned on.
3807 * the default case is to assume Vcc only.
3810 /* this appears to be very implementation specific */
3812 if (socket->Vpp1Level != socket->Vpp2Level)
3813 return (BAD_VPP);
3815 if (socket->VccLevel == 0 || !(sockp->pcs_flags & PCS_CARD_PRESENT)) {
3816 powerlevel = 0;
3817 sockp->pcs_vcc = 0;
3818 sockp->pcs_vpp1 = 0;
3819 sockp->pcs_vpp2 = 0;
3820 } else {
3821 #if defined(PCIC_DEBUG)
3822 pcic_err(dip, 9, "\tVcc=%d Vpp1Level=%d, Vpp2Level=%d\n",
3823 socket->VccLevel, socket->Vpp1Level, socket->Vpp2Level);
3824 #endif
3825 /* valid Vcc power level? */
3826 if (socket->VccLevel >= pcic->pc_numpower)
3827 return (BAD_VCC);
3829 switch (pcic_power[socket->VccLevel].PowerLevel) {
3830 case 33: /* 3.3V */
3831 case 60: /* for bad CIS in Option GPRS card */
3832 if (!(pcic->pc_flags & PCF_33VCAP)) {
3833 cmn_err(CE_WARN,
3834 "%s%d: Bad Request for 3.3V "
3835 "(Controller incapable)\n",
3836 ddi_get_name(pcic->dip),
3837 ddi_get_instance(pcic->dip));
3838 return (BAD_VCC);
3840 /* FALLTHROUGH */
3841 case 50: /* 5V */
3842 if ((pcic->pc_io_type == PCIC_IO_TYPE_YENTA) &&
3843 pcic_getcb(pcic, CB_PRESENT_STATE) &
3844 CB_PS_33VCARD) {
3846 * This is actually a 3.3V card.
3847 * Solaris Card Services
3848 * doesn't understand 3.3V
3849 * so we cheat and change
3850 * the setting to the one appropriate to 3.3V.
3851 * Note that this is the entry number
3852 * in the pcic_power[] array.
3854 sockp->pcs_vcc = PCIC_VCC_3VLEVEL;
3855 } else
3856 sockp->pcs_vcc = socket->VccLevel;
3857 break;
3858 default:
3859 return (BAD_VCC);
3862 /* enable Vcc */
3863 powerlevel = POWER_CARD_ENABLE;
3865 #if defined(PCIC_DEBUG)
3866 if (pcic_debug) {
3867 cmn_err(CE_CONT, "\tVcc=%d powerlevel=%x\n",
3868 socket->VccLevel, powerlevel);
3870 #endif
3871 ind = 0; /* default index to 0 power */
3872 if ((int)socket->Vpp1Level >= 0 &&
3873 socket->Vpp1Level < pcic->pc_numpower) {
3874 if (!(pcic_power[socket->Vpp1Level].ValidSignals
3875 & VPP1)) {
3876 return (BAD_VPP);
3878 ind = pcic_power[socket->Vpp1Level].PowerLevel/10;
3879 powerlevel |= pcic_vpp_levels[ind];
3880 sockp->pcs_vpp1 = socket->Vpp1Level;
3882 if ((int)socket->Vpp2Level >= 0 &&
3883 socket->Vpp2Level < pcic->pc_numpower) {
3884 if (!(pcic_power[socket->Vpp2Level].ValidSignals
3885 & VPP2)) {
3886 return (BAD_VPP);
3888 ind = pcic_power[socket->Vpp2Level].PowerLevel/10;
3889 powerlevel |= (pcic_vpp_levels[ind] << 2);
3890 sockp->pcs_vpp2 = socket->Vpp2Level;
3893 if (pcic->pc_flags & PCF_VPPX) {
3895 * this adapter doesn't allow separate Vpp1/Vpp2
3896 * if one is turned on, both are turned on and only
3897 * the Vpp1 bits should be set
3899 if (sockp->pcs_vpp2 != sockp->pcs_vpp1) {
3900 /* must be the same if one not zero */
3901 if (sockp->pcs_vpp1 != 0 &&
3902 sockp->pcs_vpp2 != 0) {
3903 cmn_err(CE_WARN,
3904 "%s%d: Bad Power Request "
3905 "(Vpp1/2 not the same)\n",
3906 ddi_get_name(pcic->dip),
3907 ddi_get_instance(pcic->dip));
3908 return (BAD_VPP);
3911 powerlevel &= ~(3<<2);
3914 #if defined(PCIC_DEBUG)
3915 if (pcic_debug) {
3916 cmn_err(CE_CONT, "\tpowerlevel=%x, ind=%x\n",
3917 powerlevel, ind);
3919 #endif
3921 mutex_enter(&pcic->pc_lock); /* protect the registers */
3923 /* turn socket->IREQRouting off while programming */
3924 interrupt = pcic_getb(pcic, socket->socket, PCIC_INTERRUPT);
3925 interrupt &= ~PCIC_INTR_MASK;
3926 if (pcic->pc_flags & PCF_USE_SMI)
3927 interrupt |= PCIC_INTR_ENABLE;
3928 pcic_putb(pcic, socket->socket, PCIC_INTERRUPT, interrupt);
3930 switch (pcic->pc_type) {
3931 case PCIC_INTEL_i82092:
3932 pcic_82092_smiirq_ctl(pcic, socket->socket, PCIC_82092_CTL_IRQ,
3933 PCIC_82092_INT_DISABLE);
3934 break;
3935 default:
3936 break;
3937 } /* switch */
3939 /* the SCIntMask specifies events to detect */
3940 mirq = pcic_getb(pcic, socket->socket, PCIC_MANAGEMENT_INT);
3942 #if defined(PCIC_DEBUG)
3943 if (pcic_debug)
3944 cmn_err(CE_CONT,
3945 "\tSCIntMask=%x, interrupt=%x, mirq=%x\n",
3946 socket->SCIntMask, interrupt, mirq);
3947 #endif
3948 mirq &= ~(PCIC_BD_DETECT|PCIC_BW_DETECT|PCIC_RD_DETECT);
3949 pcic_putb(pcic, socket->socket, PCIC_MANAGEMENT_INT,
3950 mirq & ~PCIC_CHANGE_MASK);
3952 /* save the mask we want to use */
3953 sockp->pcs_intmask = socket->SCIntMask;
3956 * Until there is a card present it's not worth enabling
3957 * any interrupts except "Card detect". This is done
3958 * elsewhere in the driver so don't change things if
3959 * there is no card!
3961 if (sockp->pcs_flags & PCS_CARD_PRESENT) {
3963 /* now update the hardware to reflect events desired */
3964 if (sockp->pcs_intmask & SBM_BVD1 || socket->IFType == IF_IO)
3965 mirq |= PCIC_BD_DETECT;
3967 if (sockp->pcs_intmask & SBM_BVD2)
3968 mirq |= PCIC_BW_DETECT;
3970 if (sockp->pcs_intmask & SBM_RDYBSY)
3971 mirq |= PCIC_RD_DETECT;
3973 if (sockp->pcs_intmask & SBM_CD)
3974 mirq |= PCIC_CD_DETECT;
3977 if (sockp->pcs_flags & PCS_READY) {
3979 * card just came ready.
3980 * make sure enough time elapses
3981 * before touching it.
3983 sockp->pcs_flags &= ~PCS_READY;
3984 pcic_mswait(pcic, socket->socket, 10);
3987 #if defined(PCIC_DEBUG)
3988 if (pcic_debug) {
3989 cmn_err(CE_CONT, "\tstatus change set to %x\n", mirq);
3991 #endif
3993 switch (pcic->pc_type) {
3994 case PCIC_I82365SL:
3995 case PCIC_VADEM:
3996 case PCIC_VADEM_VG469:
3998 * The Intel version has different options. This is a
3999 * special case of GPI which might be used for eject
4002 irq = pcic_getb(pcic, socket->socket, PCIC_CARD_DETECT);
4003 if (sockp->pcs_intmask & (SBM_EJECT|SBM_INSERT) &&
4004 pcic->pc_flags & PCF_GPI_EJECT) {
4005 irq |= PCIC_GPI_ENABLE;
4006 } else {
4007 irq &= ~PCIC_GPI_ENABLE;
4009 pcic_putb(pcic, socket->socket, PCIC_CARD_DETECT, irq);
4010 break;
4011 case PCIC_CL_PD6710:
4012 case PCIC_CL_PD6722:
4013 if (socket->IFType == IF_IO) {
4014 pcic_putb(pcic, socket->socket, PCIC_MISC_CTL_2, 0x0);
4015 value = pcic_getb(pcic, socket->socket,
4016 PCIC_MISC_CTL_1);
4017 if (pcic->pc_flags & PCF_AUDIO)
4018 value |= PCIC_MC_SPEAKER_ENB;
4019 pcic_putb(pcic, socket->socket, PCIC_MISC_CTL_1,
4020 value);
4021 } else {
4022 value = pcic_getb(pcic, socket->socket,
4023 PCIC_MISC_CTL_1);
4024 value &= ~PCIC_MC_SPEAKER_ENB;
4025 pcic_putb(pcic, socket->socket, PCIC_MISC_CTL_1,
4026 value);
4028 break;
4029 case PCIC_CL_PD6729:
4030 case PCIC_CL_PD6730:
4031 case PCIC_CL_PD6832:
4032 value = pcic_getb(pcic, socket->socket, PCIC_MISC_CTL_1);
4033 if ((socket->IFType == IF_IO) && (pcic->pc_flags & PCF_AUDIO)) {
4034 value |= PCIC_MC_SPEAKER_ENB;
4035 } else {
4036 value &= ~PCIC_MC_SPEAKER_ENB;
4039 if (pcic_power[sockp->pcs_vcc].PowerLevel == 33)
4040 value |= PCIC_MC_3VCC;
4041 else
4042 value &= ~PCIC_MC_3VCC;
4044 pcic_putb(pcic, socket->socket, PCIC_MISC_CTL_1, value);
4045 break;
4047 case PCIC_O2_OZ6912:
4048 value = pcic_getcb(pcic, CB_MISCCTRL);
4049 if ((socket->IFType == IF_IO) && (pcic->pc_flags & PCF_AUDIO))
4050 value |= (1<<25);
4051 else
4052 value &= ~(1<<25);
4053 pcic_putcb(pcic, CB_MISCCTRL, value);
4054 if (pcic_power[sockp->pcs_vcc].PowerLevel == 33)
4055 powerlevel |= 0x08;
4056 break;
4058 case PCIC_TI_PCI1250:
4059 case PCIC_TI_PCI1221:
4060 case PCIC_TI_PCI1225:
4061 case PCIC_TI_PCI1410:
4062 case PCIC_ENE_1410:
4063 case PCIC_TI_PCI1510:
4064 case PCIC_TI_PCI1520:
4065 case PCIC_TI_PCI1420:
4066 case PCIC_ENE_1420:
4067 value = ddi_get8(pcic->cfg_handle,
4068 pcic->cfgaddr + PCIC_CRDCTL_REG);
4069 if ((socket->IFType == IF_IO) && (pcic->pc_flags & PCF_AUDIO)) {
4070 value |= PCIC_CRDCTL_SPKR_ENBL;
4071 } else {
4072 value &= ~PCIC_CRDCTL_SPKR_ENBL;
4074 ddi_put8(pcic->cfg_handle,
4075 pcic->cfgaddr + PCIC_CRDCTL_REG, value);
4076 if (pcic_power[sockp->pcs_vcc].PowerLevel == 33)
4077 powerlevel |= 0x08;
4078 break;
4082 * ctlind processing -- we can ignore this
4083 * there aren't any outputs on the chip for this and
4084 * the GUI will display what it thinks is correct
4088 * If outputs are enabled and the power is going off
4089 * turn off outputs first.
4092 /* power setup -- if necessary */
4093 orig_pwrctl = pcic_getb(pcic, socket->socket, PCIC_POWER_CONTROL);
4094 if ((orig_pwrctl & POWER_OUTPUT_ENABLE) && sockp->pcs_vcc == 0) {
4095 orig_pwrctl &= ~POWER_OUTPUT_ENABLE;
4096 pcic_putb(pcic, socket->socket,
4097 PCIC_POWER_CONTROL, orig_pwrctl);
4098 (void) pcic_getb(pcic, socket->socket, PCIC_POWER_CONTROL);
4101 if (pcic->pc_flags & PCF_CBPWRCTL) {
4102 value = pcic_cbus_powerctl(pcic, socket->socket);
4103 powerlevel = 0;
4104 } else
4105 value = pcic_exca_powerctl(pcic, socket->socket, powerlevel);
4107 if (value != SUCCESS) {
4108 mutex_exit(&pcic->pc_lock);
4109 return (value);
4113 * If outputs were disabled and the power is going on
4114 * turn on outputs afterwards.
4116 if (!(orig_pwrctl & POWER_OUTPUT_ENABLE) && sockp->pcs_vcc != 0) {
4117 orig_pwrctl = pcic_getb(pcic, socket->socket,
4118 PCIC_POWER_CONTROL);
4119 orig_pwrctl |= POWER_OUTPUT_ENABLE;
4120 pcic_putb(pcic, socket->socket,
4121 PCIC_POWER_CONTROL, orig_pwrctl);
4122 (void) pcic_getb(pcic, socket->socket, PCIC_POWER_CONTROL);
4126 * Once we have done the power stuff can re-enable management
4127 * interrupts.
4129 pcic_putb(pcic, socket->socket, PCIC_MANAGEMENT_INT, mirq);
4131 #if defined(PCIC_DEBUG)
4132 pcic_err(dip, 8, "\tmanagement int set to %x pwrctl to 0x%x "
4133 "cbctl 0x%x\n",
4134 mirq, pcic_getb(pcic, socket->socket, PCIC_POWER_CONTROL),
4135 pcic_getcb(pcic, CB_CONTROL));
4136 #endif
4138 /* irq processing */
4139 if (socket->IFType == IF_IO) {
4140 /* IRQ only for I/O */
4141 irq = socket->IREQRouting & PCIC_INTR_MASK;
4142 value = pcic_getb(pcic, socket->socket, PCIC_INTERRUPT);
4143 value &= ~PCIC_INTR_MASK;
4145 /* to enable I/O operation */
4146 value |= PCIC_IO_CARD | PCIC_RESET;
4147 sockp->pcs_flags |= PCS_CARD_IO;
4148 if (irq != sockp->pcs_irq) {
4149 if (sockp->pcs_irq != 0)
4150 cmn_err(CE_CONT,
4151 "SetSocket: IRQ mismatch %x != %x!\n",
4152 irq, sockp->pcs_irq);
4153 else
4154 sockp->pcs_irq = irq;
4156 irq = sockp->pcs_irq;
4158 pcic_putb(pcic, socket->socket, PCIC_INTERRUPT, value);
4159 if (socket->IREQRouting & IRQ_ENABLE) {
4160 pcic_enable_io_intr(pcic, socket->socket, irq);
4161 sockp->pcs_flags |= PCS_IRQ_ENABLED;
4162 } else {
4163 pcic_disable_io_intr(pcic, socket->socket);
4164 sockp->pcs_flags &= ~PCS_IRQ_ENABLED;
4166 #if defined(PCIC_DEBUG)
4167 if (pcic_debug) {
4168 cmn_err(CE_CONT,
4169 "\tsocket type is I/O and irq %x is %s\n", irq,
4170 (socket->IREQRouting & IRQ_ENABLE) ?
4171 "enabled" : "not enabled");
4172 xxdmp_all_regs(pcic, socket->socket, 20);
4174 #endif
4175 } else {
4176 /* make sure I/O mode is off */
4178 sockp->pcs_irq = 0;
4180 value = pcic_getb(pcic, socket->socket, PCIC_INTERRUPT);
4181 value &= ~PCIC_IO_CARD;
4182 pcic_putb(pcic, socket->socket, PCIC_INTERRUPT, value);
4183 pcic_disable_io_intr(pcic, socket->socket);
4184 sockp->pcs_flags &= ~(PCS_CARD_IO|PCS_IRQ_ENABLED);
4187 sockp->pcs_state &= ~socket->State;
4189 mutex_exit(&pcic->pc_lock);
4190 return (SUCCESS);
4194 * pcic_inquire_socket()
4195 * SocketServices InquireSocket function
4196 * returns basic characteristics of the socket
4198 /*ARGSUSED*/
4199 static int
4200 pcic_inquire_socket(dev_info_t *dip, inquire_socket_t *socket)
4202 anp_t *anp = ddi_get_driver_private(dip);
4203 pcicdev_t *pcic = anp->an_private;
4204 int value;
4206 socket->SCIntCaps = PCIC_DEFAULT_INT_CAPS;
4207 socket->SCRptCaps = PCIC_DEFAULT_RPT_CAPS;
4208 socket->CtlIndCaps = PCIC_DEFAULT_CTL_CAPS;
4209 value = pcic->pc_sockets[socket->socket].pcs_flags;
4210 socket->SocketCaps = (value & PCS_SOCKET_IO) ? IF_IO : IF_MEMORY;
4211 socket->ActiveHigh = 0;
4212 /* these are the usable IRQs */
4213 socket->ActiveLow = 0xfff0;
4214 return (SUCCESS);
4218 * pcic_inquire_window()
4219 * SocketServices InquireWindow function
4220 * returns detailed characteristics of the window
4221 * this is where windows get tied to sockets
4223 /*ARGSUSED*/
4224 static int
4225 pcic_inquire_window(dev_info_t *dip, inquire_window_t *window)
4227 int type, socket;
4229 type = window->window % PCIC_NUMWINSOCK;
4230 socket = window->window / PCIC_NUMWINSOCK;
4232 #if defined(PCIC_DEBUG)
4233 if (pcic_debug >= 8)
4234 cmn_err(CE_CONT,
4235 "pcic_inquire_window: window = %d/%d socket=%d\n",
4236 window->window, type, socket);
4237 #endif
4238 if (type < PCIC_IOWINDOWS) {
4239 window->WndCaps = WC_IO|WC_WAIT;
4240 type = IF_IO;
4241 } else {
4242 window->WndCaps = WC_COMMON|WC_ATTRIBUTE|WC_WAIT;
4243 type = IF_MEMORY;
4246 /* initialize the socket map - one socket per window */
4247 PR_ZERO(window->Sockets);
4248 PR_SET(window->Sockets, socket);
4250 if (type == IF_IO) {
4251 iowin_char_t *io;
4252 io = &window->iowin_char;
4253 io->IOWndCaps = WC_BASE|WC_SIZE|WC_WENABLE|WC_8BIT|
4254 WC_16BIT;
4255 io->FirstByte = (baseaddr_t)IOMEM_FIRST;
4256 io->LastByte = (baseaddr_t)IOMEM_LAST;
4257 io->MinSize = IOMEM_MIN;
4258 io->MaxSize = IOMEM_MAX;
4259 io->ReqGran = IOMEM_GRAN;
4260 io->AddrLines = IOMEM_DECODE;
4261 io->EISASlot = 0;
4262 } else {
4263 mem_win_char_t *mem;
4264 mem = &window->mem_win_char;
4265 mem->MemWndCaps = WC_BASE|WC_SIZE|WC_WENABLE|WC_8BIT|
4266 WC_16BIT|WC_WP;
4268 mem->FirstByte = (baseaddr_t)MEM_FIRST;
4269 mem->LastByte = (baseaddr_t)MEM_LAST;
4271 mem->MinSize = MEM_MIN;
4272 mem->MaxSize = MEM_MAX;
4273 mem->ReqGran = PCIC_PAGE;
4274 mem->ReqBase = 0;
4275 mem->ReqOffset = PCIC_PAGE;
4276 mem->Slowest = MEM_SPEED_MAX;
4277 mem->Fastest = MEM_SPEED_MIN;
4279 return (SUCCESS);
4283 * pcic_get_adapter()
4284 * SocketServices GetAdapter function
4285 * this is nearly a no-op.
4287 /*ARGSUSED*/
4288 static int
4289 pcic_get_adapter(dev_info_t *dip, get_adapter_t *adapt)
4291 anp_t *anp = ddi_get_driver_private(dip);
4292 pcicdev_t *pcic = anp->an_private;
4294 if (pcic->pc_flags & PCF_INTRENAB)
4295 adapt->SCRouting = IRQ_ENABLE;
4296 adapt->state = 0;
4297 return (SUCCESS);
4301 * pcic_get_page()
4302 * SocketServices GetPage function
4303 * returns info about the window
4305 /*ARGSUSED*/
4306 static int
4307 pcic_get_page(dev_info_t *dip, get_page_t *page)
4309 anp_t *anp = ddi_get_driver_private(dip);
4310 pcicdev_t *pcic = anp->an_private;
4311 int socket, window;
4312 pcs_memwin_t *winp;
4314 socket = page->window / PCIC_NUMWINSOCK;
4315 window = page->window % PCIC_NUMWINSOCK;
4317 /* I/O windows are the first two */
4318 if (window < PCIC_IOWINDOWS || socket >= pcic->pc_numsockets) {
4319 return (BAD_WINDOW);
4322 winp = &pcic->pc_sockets[socket].pcs_windows[window].mem;
4324 if (page->page != 0)
4325 return (BAD_PAGE);
4327 page->state = 0;
4328 if (winp->pcw_status & PCW_ENABLED)
4329 page->state |= PS_ENABLED;
4330 if (winp->pcw_status & PCW_ATTRIBUTE)
4331 page->state |= PS_ATTRIBUTE;
4332 if (winp->pcw_status & PCW_WP)
4333 page->state |= PS_WP;
4335 page->offset = (off_t)winp->pcw_offset;
4337 return (SUCCESS);
4341 * pcic_get_socket()
4342 * SocketServices GetSocket
4343 * returns information about the current socket setting
4345 /*ARGSUSED*/
4346 static int
4347 pcic_get_socket(dev_info_t *dip, get_socket_t *socket)
4349 anp_t *anp = ddi_get_driver_private(dip);
4350 pcicdev_t *pcic = anp->an_private;
4351 int socknum, irq_enabled;
4352 pcic_socket_t *sockp;
4354 socknum = socket->socket;
4355 sockp = &pcic->pc_sockets[socknum];
4357 socket->SCIntMask = sockp->pcs_intmask;
4358 sockp->pcs_state = pcic_card_state(pcic, sockp);
4360 socket->state = sockp->pcs_state;
4361 if (socket->state & SBM_CD) {
4362 socket->VccLevel = sockp->pcs_vcc;
4363 socket->Vpp1Level = sockp->pcs_vpp1;
4364 socket->Vpp2Level = sockp->pcs_vpp2;
4365 irq_enabled = (sockp->pcs_flags & PCS_IRQ_ENABLED) ?
4366 IRQ_ENABLE : 0;
4367 socket->IRQRouting = sockp->pcs_irq | irq_enabled;
4368 socket->IFType = (sockp->pcs_flags & PCS_CARD_IO) ?
4369 IF_IO : IF_MEMORY;
4370 } else {
4371 socket->VccLevel = 0;
4372 socket->Vpp1Level = 0;
4373 socket->Vpp2Level = 0;
4374 socket->IRQRouting = 0;
4375 socket->IFType = IF_MEMORY;
4377 socket->CtlInd = 0; /* no indicators */
4379 return (SUCCESS);
4383 * pcic_get_status()
4384 * SocketServices GetStatus
4385 * returns status information about the PC Card in
4386 * the selected socket
4388 /*ARGSUSED*/
4389 static int
4390 pcic_get_status(dev_info_t *dip, get_ss_status_t *status)
4392 anp_t *anp = ddi_get_driver_private(dip);
4393 pcicdev_t *pcic = anp->an_private;
4394 int socknum, irq_enabled;
4395 pcic_socket_t *sockp;
4397 socknum = status->socket;
4398 sockp = &pcic->pc_sockets[socknum];
4400 status->CardState = pcic_card_state(pcic, sockp);
4401 status->SocketState = sockp->pcs_state;
4402 status->CtlInd = 0; /* no indicators */
4404 if (sockp->pcs_flags & PCS_CARD_PRESENT)
4405 status->SocketState |= SBM_CD;
4406 if (status->CardState & SBM_CD) {
4407 irq_enabled = (sockp->pcs_flags & PCS_CARD_ENABLED) ?
4408 IRQ_ENABLE : 0;
4409 status->IRQRouting = sockp->pcs_irq | irq_enabled;
4410 status->IFType = (sockp->pcs_flags & PCS_CARD_IO) ?
4411 IF_IO : IF_MEMORY;
4412 } else {
4413 status->IRQRouting = 0;
4414 status->IFType = IF_MEMORY;
4417 #if defined(PCIC_DEBUG)
4418 if (pcic_debug >= 8)
4419 cmn_err(CE_CONT, "pcic_get_status: socket=%d, CardState=%x,"
4420 "SocketState=%x\n",
4421 socknum, status->CardState, status->SocketState);
4422 #endif
4423 switch (pcic->pc_type) {
4424 uint32_t present_state;
4425 case PCIC_TI_PCI1410:
4426 case PCIC_TI_PCI1520:
4427 case PCIC_TI_PCI1420:
4428 case PCIC_ENE_1420:
4429 case PCIC_TOSHIBA_TOPIC100:
4430 case PCIC_TOSHIBA_TOPIC95:
4431 case PCIC_TOSHIBA_VENDOR:
4432 case PCIC_O2MICRO_VENDOR:
4433 case PCIC_TI_VENDOR:
4434 case PCIC_RICOH_VENDOR:
4435 present_state = pcic_getcb(pcic, CB_PRESENT_STATE);
4436 if (present_state & PCIC_CB_CARD)
4437 status->IFType = IF_CARDBUS;
4438 #if defined(PCIC_DEBUG)
4439 if (pcic_debug >= 8)
4440 cmn_err(CE_CONT,
4441 "pcic_get_status: present_state=0x%x\n",
4442 present_state);
4443 #endif
4444 break;
4445 default:
4446 break;
4449 return (SUCCESS);
4453 * pcic_get_window()
4454 * SocketServices GetWindow function
4455 * returns state information about the specified window
4457 /*ARGSUSED*/
4458 static int
4459 pcic_get_window(dev_info_t *dip, get_window_t *window)
4461 anp_t *anp = ddi_get_driver_private(dip);
4462 pcicdev_t *pcic = anp->an_private;
4463 int socket, win;
4464 pcic_socket_t *sockp;
4465 pcs_memwin_t *winp;
4467 socket = window->window / PCIC_NUMWINSOCK;
4468 win = window->window % PCIC_NUMWINSOCK;
4469 #if defined(PCIC_DEBUG)
4470 if (pcic_debug) {
4471 cmn_err(CE_CONT, "pcic_get_window(socket=%d, window=%d)\n",
4472 socket, win);
4474 #endif
4476 if (socket > pcic->pc_numsockets)
4477 return (BAD_WINDOW);
4479 sockp = &pcic->pc_sockets[socket];
4480 winp = &sockp->pcs_windows[win].mem;
4482 window->socket = socket;
4483 window->size = winp->pcw_len;
4484 window->speed = winp->pcw_speed;
4485 window->handle = (ddi_acc_handle_t)winp->pcw_handle;
4486 window->base = (uint32_t)winp->pcw_base + winp->pcw_offset;
4488 if (win >= PCIC_IOWINDOWS) {
4489 window->state = 0;
4490 } else {
4491 window->state = WS_IO;
4493 if (winp->pcw_status & PCW_ENABLED)
4494 window->state |= WS_ENABLED;
4496 if (winp->pcw_status & PCS_CARD_16BIT)
4497 window->state |= WS_16BIT;
4498 #if defined(PCIC_DEBUG)
4499 if (pcic_debug)
4500 cmn_err(CE_CONT, "\tsize=%d, speed=%d, base=%p, state=%x\n",
4501 window->size, (unsigned)window->speed,
4502 (void *)window->handle, window->state);
4503 #endif
4505 return (SUCCESS);
4509 * pcic_ll_reset
4510 * low level reset
4511 * separated out so it can be called when already locked
4513 * There are two variables that control the RESET timing:
4514 * pcic_prereset_time - time in mS before asserting RESET
4515 * pcic_reset_time - time in mS to assert RESET
4518 int pcic_prereset_time = 1;
4519 int pcic_reset_time = 10;
4520 int pcic_postreset_time = 20;
4521 int pcic_vpp_is_vcc_during_reset = 0;
4523 static int
4524 pcic_ll_reset(pcicdev_t *pcic, int socket)
4526 int windowbits, iobits;
4527 uint32_t pwr;
4529 /* save windows that were on */
4530 windowbits = pcic_getb(pcic, socket, PCIC_MAPPING_ENABLE);
4531 if (pcic_reset_time == 0)
4532 return (windowbits);
4533 /* turn all windows off */
4534 pcic_putb(pcic, socket, PCIC_MAPPING_ENABLE, 0);
4536 #if defined(PCIC_DEBUG)
4537 pcic_err(pcic->dip, 6,
4538 "pcic_ll_reset(socket %d) powerlevel=%x cbctl 0x%x cbps 0x%x\n",
4539 socket, pcic_getb(pcic, socket, PCIC_POWER_CONTROL),
4540 pcic_getcb(pcic, CB_CONTROL),
4541 pcic_getcb(pcic, CB_PRESENT_STATE));
4542 #endif
4544 if (pcic_vpp_is_vcc_during_reset) {
4547 * Set VPP to VCC for the duration of the reset - for aironet
4548 * card.
4550 if (pcic->pc_flags & PCF_CBPWRCTL) {
4551 pwr = pcic_getcb(pcic, CB_CONTROL);
4552 pcic_putcb(pcic, CB_CONTROL, (pwr&~CB_C_VPPMASK)|CB_C_VPPVCC);
4553 (void) pcic_getcb(pcic, CB_CONTROL);
4554 } else {
4555 pwr = pcic_getb(pcic, socket, PCIC_POWER_CONTROL);
4556 pcic_putb(pcic, socket, PCIC_POWER_CONTROL,
4557 pwr | 1);
4558 (void) pcic_getb(pcic, socket, PCIC_POWER_CONTROL);
4562 if (pcic_prereset_time > 0) {
4563 pcic_err(pcic->dip, 8, "pcic_ll_reset pre_wait %d mS\n",
4564 pcic_prereset_time);
4565 pcic_mswait(pcic, socket, pcic_prereset_time);
4568 /* turn interrupts off and start a reset */
4569 pcic_err(pcic->dip, 8,
4570 "pcic_ll_reset turn interrupts off and start a reset\n");
4571 iobits = pcic_getb(pcic, socket, PCIC_INTERRUPT);
4572 iobits &= ~(PCIC_INTR_MASK | PCIC_RESET);
4573 pcic_putb(pcic, socket, PCIC_INTERRUPT, iobits);
4574 (void) pcic_getb(pcic, socket, PCIC_INTERRUPT);
4576 switch (pcic->pc_type) {
4577 case PCIC_INTEL_i82092:
4578 pcic_82092_smiirq_ctl(pcic, socket, PCIC_82092_CTL_IRQ,
4579 PCIC_82092_INT_DISABLE);
4580 break;
4581 default:
4582 break;
4583 } /* switch */
4585 pcic->pc_sockets[socket].pcs_state = 0;
4587 if (pcic_reset_time > 0) {
4588 pcic_err(pcic->dip, 8, "pcic_ll_reset reset_wait %d mS\n",
4589 pcic_reset_time);
4590 pcic_mswait(pcic, socket, pcic_reset_time);
4593 pcic_err(pcic->dip, 8, "pcic_ll_reset take it out of reset now\n");
4595 /* take it out of RESET now */
4596 pcic_putb(pcic, socket, PCIC_INTERRUPT, PCIC_RESET | iobits);
4597 (void) pcic_getb(pcic, socket, PCIC_INTERRUPT);
4600 * can't access the card for 20ms, but we really don't
4601 * want to sit around that long. The pcic is still usable.
4602 * memory accesses must wait for RDY to come up.
4604 if (pcic_postreset_time > 0) {
4605 pcic_err(pcic->dip, 8, "pcic_ll_reset post_wait %d mS\n",
4606 pcic_postreset_time);
4607 pcic_mswait(pcic, socket, pcic_postreset_time);
4610 if (pcic_vpp_is_vcc_during_reset > 1) {
4613 * Return VPP power to whatever it was before.
4615 if (pcic->pc_flags & PCF_CBPWRCTL) {
4616 pcic_putcb(pcic, CB_CONTROL, pwr);
4617 (void) pcic_getcb(pcic, CB_CONTROL);
4618 } else {
4619 pcic_putb(pcic, socket, PCIC_POWER_CONTROL, pwr);
4620 (void) pcic_getb(pcic, socket, PCIC_POWER_CONTROL);
4624 pcic_err(pcic->dip, 7, "pcic_ll_reset returning 0x%x\n", windowbits);
4626 return (windowbits);
4630 * pcic_reset_socket()
4631 * SocketServices ResetSocket function
4632 * puts the PC Card in the socket into the RESET state
4633 * and then takes it out after the the cycle time
4634 * The socket is back to initial state when done
4636 static int
4637 pcic_reset_socket(dev_info_t *dip, int socket, int mode)
4639 anp_t *anp = ddi_get_driver_private(dip);
4640 pcicdev_t *pcic = anp->an_private;
4641 int value;
4642 int i, mint;
4643 pcic_socket_t *sockp;
4645 #if defined(PCIC_DEBUG)
4646 if (pcic_debug >= 8)
4647 cmn_err(CE_CONT, "pcic_reset_socket(%p, %d, %d/%s)\n",
4648 (void *)dip, socket, mode,
4649 mode == RESET_MODE_FULL ? "full" : "partial");
4650 #endif
4652 mutex_enter(&pcic->pc_lock); /* protect the registers */
4654 /* Turn off management interupts. */
4655 mint = pcic_getb(pcic, socket, PCIC_MANAGEMENT_INT);
4656 pcic_putb(pcic, socket, PCIC_MANAGEMENT_INT, mint & ~PCIC_CHANGE_MASK);
4658 sockp = &pcic->pc_sockets[socket];
4660 value = pcic_ll_reset(pcic, socket);
4661 if (mode == RESET_MODE_FULL) {
4662 /* disable and unmap all mapped windows */
4663 for (i = 0; i < PCIC_NUMWINSOCK; i++) {
4664 if (i < PCIC_IOWINDOWS) {
4665 if (sockp->pcs_windows[i].io.pcw_status &
4666 PCW_MAPPED) {
4667 pcs_iowin_t *io;
4668 io = &sockp->pcs_windows[i].io;
4669 io->pcw_status &= ~PCW_ENABLED;
4671 } else {
4672 if (sockp->pcs_windows[i].mem.pcw_status &
4673 PCW_MAPPED) {
4674 pcs_memwin_t *mem;
4675 mem = &sockp->pcs_windows[i].mem;
4676 mem->pcw_status &= ~PCW_ENABLED;
4680 } else {
4681 /* turn windows back on */
4682 pcic_putb(pcic, socket, PCIC_MAPPING_ENABLE, value);
4683 /* wait the rest of the time here */
4684 pcic_mswait(pcic, socket, 10);
4686 pcic_putb(pcic, socket, PCIC_MANAGEMENT_INT, mint);
4687 mutex_exit(&pcic->pc_lock);
4688 return (SUCCESS);
4692 * pcic_set_interrupt()
4693 * SocketServices SetInterrupt function
4695 static int
4696 pcic_set_interrupt(dev_info_t *dip, set_irq_handler_t *handler)
4698 anp_t *anp = ddi_get_driver_private(dip);
4699 pcicdev_t *pcic = anp->an_private;
4700 int value = DDI_SUCCESS;
4701 inthandler_t *intr;
4703 #if defined(PCIC_DEBUG)
4704 if (pcic_debug) {
4705 cmn_err(CE_CONT,
4706 "pcic_set_interrupt: entered pc_intr_mode=0x%x\n",
4707 pcic->pc_intr_mode);
4708 cmn_err(CE_CONT,
4709 "\t irq_top=%p handler=%p handler_id=%x\n",
4710 (void *)pcic->irq_top, (void *)handler->handler,
4711 handler->handler_id);
4713 #endif
4716 * If we're on a PCI bus, we route all IO IRQs through a single
4717 * PCI interrupt (typically INT A#) so we don't have to do
4718 * much other than add the caller to general interrupt handler
4719 * and set some state.
4722 intr = kmem_zalloc(sizeof (inthandler_t), KM_NOSLEEP);
4723 if (intr == NULL)
4724 return (NO_RESOURCE);
4726 switch (pcic->pc_intr_mode) {
4727 case PCIC_INTR_MODE_PCI_1:
4729 * We only allow above-lock-level IO IRQ handlers
4730 * in the PCI bus case.
4733 mutex_enter(&pcic->intr_lock);
4735 if (pcic->irq_top == NULL) {
4736 pcic->irq_top = intr;
4737 pcic->irq_current = pcic->irq_top;
4738 } else {
4739 while (pcic->irq_current->next != NULL)
4740 pcic->irq_current = pcic->irq_current->next;
4741 pcic->irq_current->next = intr;
4742 pcic->irq_current = pcic->irq_current->next;
4745 pcic->irq_current->intr =
4746 (ddi_intr_handler_t *)handler->handler;
4747 pcic->irq_current->handler_id = handler->handler_id;
4748 pcic->irq_current->arg1 = handler->arg1;
4749 pcic->irq_current->arg2 = handler->arg2;
4750 pcic->irq_current->socket = handler->socket;
4752 mutex_exit(&pcic->intr_lock);
4754 handler->iblk_cookie = &pcic->pc_pri;
4755 handler->idev_cookie = &pcic->pc_dcookie;
4756 break;
4758 default:
4759 intr->intr = (ddi_intr_handler_t *)handler->handler;
4760 intr->handler_id = handler->handler_id;
4761 intr->arg1 = handler->arg1;
4762 intr->arg2 = handler->arg2;
4763 intr->socket = handler->socket;
4764 intr->irq = handler->irq;
4767 * need to revisit this to see if interrupts can be
4768 * shared someday. Note that IRQ is set in the common
4769 * code.
4771 mutex_enter(&pcic->pc_lock);
4772 if (pcic->pc_handlers == NULL) {
4773 pcic->pc_handlers = intr;
4774 intr->next = intr->prev = intr;
4775 } else {
4776 insque(intr, pcic->pc_handlers);
4778 mutex_exit(&pcic->pc_lock);
4780 break;
4784 * need to fill in cookies in event of multiple high priority
4785 * interrupt handlers on same IRQ
4788 #if defined(PCIC_DEBUG)
4789 if (pcic_debug) {
4790 cmn_err(CE_CONT,
4791 "pcic_set_interrupt: exit irq_top=%p value=%d\n",
4792 (void *)pcic->irq_top, value);
4794 #endif
4796 if (value == DDI_SUCCESS) {
4797 return (SUCCESS);
4798 } else {
4799 return (BAD_IRQ);
4804 * pcic_clear_interrupt()
4805 * SocketServices ClearInterrupt function
4807 * Interrupts for PCIC are complicated by the fact that we must
4808 * follow several different models for interrupts.
4809 * ISA: there is an interrupt per adapter and per socket and
4810 * they can't be shared.
4811 * PCI: some adapters have one PCI interrupt available while others
4812 * have up to 4. Solaris may or may not allow us to use more
4813 * than 1 so we essentially share them all at this point.
4814 * Hybrid: PCI bridge but interrupts wired to host interrupt controller.
4815 * This is like ISA but we have to fudge and create an intrspec
4816 * that PCI's parent understands and bypass the PCI nexus.
4817 * multifunction: this requires sharing the interrupts on a per-socket
4818 * basis.
4820 static int
4821 pcic_clear_interrupt(dev_info_t *dip, clear_irq_handler_t *handler)
4823 anp_t *anp = ddi_get_driver_private(dip);
4824 pcicdev_t *pcic = anp->an_private;
4825 inthandler_t *intr, *prev, *current;
4826 int i;
4829 * If we're on a PCI bus, we route all IO IRQs through a single
4830 * PCI interrupt (typically INT A#) so we don't have to do
4831 * much other than remove the caller from the general
4832 * interrupt handler callout list.
4835 #if defined(PCIC_DEBUG)
4836 if (pcic_debug) {
4837 cmn_err(CE_CONT,
4838 "pcic_clear_interrupt: entered pc_intr_mode=0x%x\n",
4839 pcic->pc_intr_mode);
4840 cmn_err(CE_CONT,
4841 "\t irq_top=%p handler=%p handler_id=%x\n",
4842 (void *)pcic->irq_top, (void *)handler->handler,
4843 handler->handler_id);
4845 #endif
4847 switch (pcic->pc_intr_mode) {
4848 case PCIC_INTR_MODE_PCI_1:
4850 mutex_enter(&pcic->intr_lock);
4851 if (pcic->irq_top == NULL) {
4852 mutex_exit(&pcic->intr_lock);
4853 return (BAD_IRQ);
4856 intr = NULL;
4857 pcic->irq_current = pcic->irq_top;
4859 while ((pcic->irq_current != NULL) &&
4860 (pcic->irq_current->handler_id !=
4861 handler->handler_id)) {
4862 intr = pcic->irq_current;
4863 pcic->irq_current = pcic->irq_current->next;
4866 if (pcic->irq_current == NULL) {
4867 mutex_exit(&pcic->intr_lock);
4868 return (BAD_IRQ);
4871 if (intr != NULL) {
4872 intr->next = pcic->irq_current->next;
4873 } else {
4874 pcic->irq_top = pcic->irq_current->next;
4877 current = pcic->irq_current;
4878 pcic->irq_current = pcic->irq_top;
4879 mutex_exit(&pcic->intr_lock);
4880 kmem_free(current, sizeof (inthandler_t));
4882 break;
4884 default:
4886 mutex_enter(&pcic->pc_lock);
4887 intr = pcic_handlers;
4888 prev = (inthandler_t *)&pcic_handlers;
4890 while (intr != NULL) {
4891 if (intr->handler_id == handler->handler_id) {
4892 i = intr->irq & PCIC_INTR_MASK;
4893 if (--pcic_irq_map[i].count == 0) {
4894 /* multi-handler form */
4895 (void) ddi_intr_disable(pcic->pc_intr_htblp[i]);
4896 (void) ddi_intr_remove_handler(
4897 pcic->pc_intr_htblp[i]);
4898 (void) ddi_intr_free(pcic->pc_intr_htblp[i]);
4899 (void) pcmcia_return_intr(pcic->dip, i);
4900 #if defined(PCIC_DEBUG)
4901 if (pcic_debug) {
4902 cmn_err(CE_CONT,
4903 "removing interrupt %d at %s "
4904 "priority\n", i, "high");
4905 cmn_err(CE_CONT,
4906 "ddi_remove_intr(%p, %x, %p)\n",
4907 (void *)dip,
4909 (void *)intr->iblk_cookie);
4911 #endif
4913 prev->next = intr->next;
4914 kmem_free(intr, sizeof (inthandler_t));
4915 intr = prev->next;
4916 } else {
4917 prev = intr;
4918 intr = intr->next;
4919 } /* if (handler_id) */
4920 } /* while */
4922 mutex_exit(&pcic->pc_lock);
4925 #if defined(PCIC_DEBUG)
4926 if (pcic_debug) {
4927 cmn_err(CE_CONT,
4928 "pcic_clear_interrupt: exit irq_top=%p\n",
4929 (void *)pcic->irq_top);
4931 #endif
4934 return (SUCCESS);
4937 struct intel_regs {
4938 char *name;
4939 int off;
4940 char *fmt;
4941 } iregs[] = {
4942 {"ident ", 0},
4943 {"if-status ", 1, "\020\1BVD1\2BVD2\3CD1\4CD2\5WP\6RDY\7PWR\10~GPI"},
4944 {"power ", 2, "\020\1Vpp1c0\2Vpp1c1\3Vpp2c0\4Vpp2c1\5PE\6AUTO"
4945 "\7DRD\10OE"},
4946 {"cardstatus", 4, "\020\1BD\2BW\3RC\4CD\5GPI\6R1\7R2\010R3"},
4947 {"enable ", 6, "\020\1MW0\2MW1\3MW2\4MW3\5MW4\6MEM16\7IO0\10IO1"},
4948 {"cd-gcr ", 0x16, "\020\1MDI16\2CRE\3GPIE\4GPIT\5CDR\6S/W"},
4949 {"GCR ", 0x1e, "\020\1PD\2LEVEL\3WCSC\4PLS14"},
4950 {"int-gcr ", 3, "\020\5INTR\6IO\7~RST\10RI"},
4951 {"management", 5, "\020\1BDE\2BWE\3RE\4CDE"},
4952 {"volt-sense", 0x1f, "\020\1A_VS1\2A_VS2\3B_VS1\4B_VS2"},
4953 {"volt-sel ", 0x2f, "\020\5EXTCONF\6BUSSELECT\7MIXEDV\10ISAV"},
4954 {"VG ext A ", 0x3c, "\20\3IVS\4CABLE\5CSTEP\6TEST\7RIO"},
4955 {"io-ctrl ", 7, "\020\1DS0\2IOCS0\3ZWS0\4WS0\5DS1\6IOS1\7ZWS1\10WS1"},
4956 {"io0-slow ", 8},
4957 {"io0-shi ", 9},
4958 {"io0-elow ", 0xa},
4959 {"io0-ehi ", 0xb},
4960 {"io1-slow ", 0xc},
4961 {"io1-shi ", 0xd},
4962 {"io1-elow ", 0xe},
4963 {"io1-ehi ", 0xf},
4964 {"mem0-slow ", 0x10},
4965 {"mem0-shi ", 0x11, "\020\7ZW\10DS"},
4966 {"mem0-elow ", 0x12},
4967 {"mem0-ehi ", 0x13, "\020\7WS0\10WS1"},
4968 {"card0-low ", 0x14},
4969 {"card0-hi ", 0x15, "\020\7AM\10WP"},
4970 {"mem1-slow ", 0x18},
4971 {"mem1-shi ", 0x19, "\020\7ZW\10DS"},
4972 {"mem1-elow ", 0x1a},
4973 {"mem1-ehi ", 0x1b, "\020\7WS0\10WS1"},
4974 {"card1-low ", 0x1c},
4975 {"card1-hi ", 0x1d, "\020\7AM\10WP"},
4976 {"mem2-slow ", 0x20},
4977 {"mem2-shi ", 0x21, "\020\7ZW\10DS"},
4978 {"mem2-elow ", 0x22},
4979 {"mem2-ehi ", 0x23, "\020\7WS0\10WS1"},
4980 {"card2-low ", 0x24},
4981 {"card2-hi ", 0x25, "\020\7AM\10WP"},
4982 {"mem3-slow ", 0x28},
4983 {"mem3-shi ", 0x29, "\020\7ZW\10DS"},
4984 {"mem3-elow ", 0x2a},
4985 {"mem3-ehi ", 0x2b, "\020\7WS0\10WS1"},
4986 {"card3-low ", 0x2c},
4987 {"card3-hi ", 0x2d, "\020\7AM\10WP"},
4989 {"mem4-slow ", 0x30},
4990 {"mem4-shi ", 0x31, "\020\7ZW\10DS"},
4991 {"mem4-elow ", 0x32},
4992 {"mem4-ehi ", 0x33, "\020\7WS0\10WS1"},
4993 {"card4-low ", 0x34},
4994 {"card4-hi ", 0x35, "\020\7AM\10WP"},
4995 {"mpage0 ", 0x40},
4996 {"mpage1 ", 0x41},
4997 {"mpage2 ", 0x42},
4998 {"mpage3 ", 0x43},
4999 {"mpage4 ", 0x44},
5000 {NULL},
5003 static struct intel_regs cregs[] = {
5004 {"misc-ctl1 ", 0x16, "\20\2VCC3\3PMI\4PSI\5SPKR\10INPACK"},
5005 {"fifo ", 0x17, "\20\6DIOP\7DMEMP\10EMPTY"},
5006 {"misc-ctl2 ", 0x1e, "\20\1XCLK\2LOW\3SUSP\4CORE5V\5TCD\10RIOUT"},
5007 {"chip-info ", 0x1f, "\20\6DUAL"},
5008 {"IO-offlow0", 0x36},
5009 {"IO-offhi0 ", 0x37},
5010 {"IO-offlow1", 0x38},
5011 {"IO-offhi1 ", 0x39},
5012 NULL,
5015 static struct intel_regs cxregs[] = {
5016 {"ext-ctl-1 ", 0x03,
5017 "\20\1VCCLCK\2AUTOCLR\3LED\4INVIRQC\5INVIRQM\6PUC"},
5018 {"misc-ctl3 ", 0x25, "\20\5HWSUSP"},
5019 {"mem0-up ", 0x05},
5020 {"mem1-up ", 0x06},
5021 {"mem2-up ", 0x07},
5022 {"mem3-up ", 0x08},
5023 {"mem4-up ", 0x09},
5024 {NULL}
5027 void
5028 xxdmp_cl_regs(pcicdev_t *pcic, int socket, uint32_t len)
5030 int i, value, j;
5031 char buff[256];
5032 char *fmt;
5034 cmn_err(CE_CONT, "--------- Cirrus Logic Registers --------\n");
5035 for (buff[0] = '\0', i = 0; cregs[i].name != NULL && len-- != 0; i++) {
5036 int sval;
5037 if (cregs[i].off == PCIC_MISC_CTL_2)
5038 sval = 0;
5039 else
5040 sval = socket;
5041 value = pcic_getb(pcic, sval, cregs[i].off);
5042 if (i & 1) {
5043 if (cregs[i].fmt)
5044 fmt = "%s\t%s\t%b\n";
5045 else
5046 fmt = "%s\t%s\t%x\n";
5047 cmn_err(CE_CONT, fmt, buff,
5048 cregs[i].name, value, cregs[i].fmt);
5049 buff[0] = '\0';
5050 } else {
5051 if (cregs[i].fmt)
5052 fmt = "\t%s\t%b";
5053 else
5054 fmt = "\t%s\t%x";
5055 (void) sprintf(buff, fmt,
5056 cregs[i].name, value, cregs[i].fmt);
5057 for (j = strlen(buff); j < 40; j++)
5058 buff[j] = ' ';
5059 buff[40] = '\0';
5062 cmn_err(CE_CONT, "%s\n", buff);
5064 i = pcic_getb(pcic, socket, PCIC_TIME_SETUP_0);
5065 j = pcic_getb(pcic, socket, PCIC_TIME_SETUP_1);
5066 cmn_err(CE_CONT, "\tsetup-tim0\t%x\tsetup-tim1\t%x\n", i, j);
5068 i = pcic_getb(pcic, socket, PCIC_TIME_COMMAND_0);
5069 j = pcic_getb(pcic, socket, PCIC_TIME_COMMAND_1);
5070 cmn_err(CE_CONT, "\tcmd-tim0 \t%x\tcmd-tim1 \t%x\n", i, j);
5072 i = pcic_getb(pcic, socket, PCIC_TIME_RECOVER_0);
5073 j = pcic_getb(pcic, socket, PCIC_TIME_RECOVER_1);
5074 cmn_err(CE_CONT, "\trcvr-tim0 \t%x\trcvr-tim1 \t%x\n", i, j);
5076 cmn_err(CE_CONT, "--------- Extended Registers --------\n");
5078 for (buff[0] = '\0', i = 0; cxregs[i].name != NULL && len-- != 0; i++) {
5079 value = clext_reg_read(pcic, socket, cxregs[i].off);
5080 if (i & 1) {
5081 if (cxregs[i].fmt)
5082 fmt = "%s\t%s\t%b\n";
5083 else
5084 fmt = "%s\t%s\t%x\n";
5085 cmn_err(CE_CONT, fmt, buff,
5086 cxregs[i].name, value, cxregs[i].fmt);
5087 buff[0] = '\0';
5088 } else {
5089 if (cxregs[i].fmt)
5090 fmt = "\t%s\t%b";
5091 else
5092 fmt = "\t%s\t%x";
5093 (void) sprintf(buff, fmt,
5094 cxregs[i].name, value, cxregs[i].fmt);
5095 for (j = strlen(buff); j < 40; j++)
5096 buff[j] = ' ';
5097 buff[40] = '\0';
5102 #if defined(PCIC_DEBUG)
5103 static void
5104 xxdmp_all_regs(pcicdev_t *pcic, int socket, uint32_t len)
5106 int i, value, j;
5107 char buff[256];
5108 char *fmt;
5110 #if defined(PCIC_DEBUG)
5111 if (pcic_debug < 2)
5112 return;
5113 #endif
5114 cmn_err(CE_CONT,
5115 "----------- PCIC Registers for socket %d---------\n",
5116 socket);
5117 cmn_err(CE_CONT,
5118 "\tname value name value\n");
5120 for (buff[0] = '\0', i = 0; iregs[i].name != NULL && len-- != 0; i++) {
5121 value = pcic_getb(pcic, socket, iregs[i].off);
5122 if (i & 1) {
5123 if (iregs[i].fmt)
5124 fmt = "%s\t%s\t%b\n";
5125 else
5126 fmt = "%s\t%s\t%x\n";
5127 cmn_err(CE_CONT, fmt, buff,
5128 iregs[i].name, value, iregs[i].fmt);
5129 buff[0] = '\0';
5130 } else {
5131 if (iregs[i].fmt)
5132 fmt = "\t%s\t%b";
5133 else
5134 fmt = "\t%s\t%x";
5135 (void) sprintf(buff, fmt,
5136 iregs[i].name, value, iregs[i].fmt);
5137 for (j = strlen(buff); j < 40; j++)
5138 buff[j] = ' ';
5139 buff[40] = '\0';
5142 switch (pcic->pc_type) {
5143 case PCIC_CL_PD6710:
5144 case PCIC_CL_PD6722:
5145 case PCIC_CL_PD6729:
5146 case PCIC_CL_PD6832:
5147 (void) xxdmp_cl_regs(pcic, socket, 0xFFFF);
5148 break;
5150 cmn_err(CE_CONT, "%s\n", buff);
5152 #endif
5155 * pcic_mswait(ms)
5156 * sleep ms milliseconds
5157 * call drv_usecwait once for each ms
5159 static void
5160 pcic_mswait(pcicdev_t *pcic, int socket, int ms)
5162 if (ms) {
5163 pcic->pc_sockets[socket].pcs_flags |= PCS_WAITING;
5164 pcic_mutex_exit(&pcic->pc_lock);
5165 delay(drv_usectohz(ms*1000));
5166 pcic_mutex_enter(&pcic->pc_lock);
5167 pcic->pc_sockets[socket].pcs_flags &= ~PCS_WAITING;
5172 * pcic_check_ready(pcic, index, off)
5173 * Wait for card to come ready
5174 * We only wait if the card is NOT in RESET
5175 * and power is on.
5177 static boolean_t
5178 pcic_check_ready(pcicdev_t *pcic, int socket)
5180 int ifstate, intstate;
5182 intstate = pcic_getb(pcic, socket, PCIC_INTERRUPT);
5183 ifstate = pcic_getb(pcic, socket, PCIC_INTERFACE_STATUS);
5185 if ((intstate & PCIC_RESET) &&
5186 ((ifstate & (PCIC_READY|PCIC_POWER_ON|PCIC_ISTAT_CD_MASK)) ==
5187 (PCIC_READY|PCIC_POWER_ON|PCIC_CD_PRESENT_OK)))
5188 return (B_TRUE);
5190 #ifdef PCIC_DEBUG
5191 pcic_err(NULL, 5, "pcic_check_read: Card not ready, intstate = 0x%x, "
5192 "ifstate = 0x%x\n", intstate, ifstate);
5193 if (pcic_debug) {
5194 pcic_debug += 4;
5195 xxdmp_all_regs(pcic, socket, -1);
5196 pcic_debug -= 4;
5198 #endif
5199 return (B_FALSE);
5203 * Cirrus Logic extended register read/write routines
5205 static int
5206 clext_reg_read(pcicdev_t *pcic, int sn, uchar_t ext_reg)
5208 int val;
5210 switch (pcic->pc_io_type) {
5211 case PCIC_IO_TYPE_YENTA:
5212 val = ddi_get8(pcic->handle,
5213 pcic->ioaddr + CB_CLEXT_OFFSET + ext_reg);
5214 break;
5215 default:
5216 pcic_putb(pcic, sn, PCIC_CL_EXINDEX, ext_reg);
5217 val = pcic_getb(pcic, sn, PCIC_CL_EXINDEX + 1);
5218 break;
5221 return (val);
5224 static void
5225 clext_reg_write(pcicdev_t *pcic, int sn, uchar_t ext_reg, uchar_t value)
5227 switch (pcic->pc_io_type) {
5228 case PCIC_IO_TYPE_YENTA:
5229 ddi_put8(pcic->handle,
5230 pcic->ioaddr + CB_CLEXT_OFFSET + ext_reg, value);
5231 break;
5232 default:
5233 pcic_putb(pcic, sn, PCIC_CL_EXINDEX, ext_reg);
5234 pcic_putb(pcic, sn, PCIC_CL_EXINDEX + 1, value);
5235 break;
5240 * Misc PCI functions
5242 static void
5243 pcic_iomem_pci_ctl(ddi_acc_handle_t handle, uchar_t *cfgaddr, unsigned flags)
5245 unsigned cmd;
5247 if (flags & (PCIC_ENABLE_IO | PCIC_ENABLE_MEM)) {
5248 cmd = ddi_get16(handle, (ushort_t *)(cfgaddr + 4));
5249 if ((cmd & (PCI_COMM_IO|PCI_COMM_MAE)) ==
5250 (PCI_COMM_IO|PCI_COMM_MAE))
5251 return;
5253 if (flags & PCIC_ENABLE_IO)
5254 cmd |= PCI_COMM_IO;
5256 if (flags & PCIC_ENABLE_MEM)
5257 cmd |= PCI_COMM_MAE;
5259 ddi_put16(handle, (ushort_t *)(cfgaddr + 4), cmd);
5260 } /* if (PCIC_ENABLE_IO | PCIC_ENABLE_MEM) */
5264 * pcic_find_pci_type - Find and return PCI-PCMCIA adapter type
5266 static int
5267 pcic_find_pci_type(pcicdev_t *pcic)
5269 uint32_t vend, device;
5271 vend = ddi_getprop(DDI_DEV_T_ANY, pcic->dip,
5272 DDI_PROP_CANSLEEP|DDI_PROP_DONTPASS,
5273 "vendor-id", -1);
5274 device = ddi_getprop(DDI_DEV_T_ANY, pcic->dip,
5275 DDI_PROP_CANSLEEP|DDI_PROP_DONTPASS,
5276 "device-id", -1);
5278 device = PCI_ID(vend, device);
5279 pcic->pc_type = device;
5280 pcic->pc_chipname = "PCI:unknown";
5282 switch (device) {
5283 case PCIC_INTEL_i82092:
5284 pcic->pc_chipname = PCIC_TYPE_i82092;
5285 break;
5286 case PCIC_CL_PD6729:
5287 pcic->pc_chipname = PCIC_TYPE_PD6729;
5289 * Some 6730's incorrectly identify themselves
5290 * as a 6729, so we need to do some more tests
5291 * here to see if the device that's claiming
5292 * to be a 6729 is really a 6730.
5294 if ((clext_reg_read(pcic, 0, PCIC_CLEXT_MISC_CTL_3) &
5295 PCIC_CLEXT_MISC_CTL_3_REV_MASK) ==
5296 0) {
5297 pcic->pc_chipname = PCIC_TYPE_PD6730;
5298 pcic->pc_type = PCIC_CL_PD6730;
5300 break;
5301 case PCIC_CL_PD6730:
5302 pcic->pc_chipname = PCIC_TYPE_PD6730;
5303 break;
5304 case PCIC_CL_PD6832:
5305 pcic->pc_chipname = PCIC_TYPE_PD6832;
5306 break;
5307 case PCIC_SMC_34C90:
5308 pcic->pc_chipname = PCIC_TYPE_34C90;
5309 break;
5310 case PCIC_TOSHIBA_TOPIC95:
5311 pcic->pc_chipname = PCIC_TYPE_TOPIC95;
5312 break;
5313 case PCIC_TOSHIBA_TOPIC100:
5314 pcic->pc_chipname = PCIC_TYPE_TOPIC100;
5315 break;
5316 case PCIC_TI_PCI1031:
5317 pcic->pc_chipname = PCIC_TYPE_PCI1031;
5318 break;
5319 case PCIC_TI_PCI1130:
5320 pcic->pc_chipname = PCIC_TYPE_PCI1130;
5321 break;
5322 case PCIC_TI_PCI1131:
5323 pcic->pc_chipname = PCIC_TYPE_PCI1131;
5324 break;
5325 case PCIC_TI_PCI1250:
5326 pcic->pc_chipname = PCIC_TYPE_PCI1250;
5327 break;
5328 case PCIC_TI_PCI1225:
5329 pcic->pc_chipname = PCIC_TYPE_PCI1225;
5330 break;
5331 case PCIC_TI_PCI1410:
5332 pcic->pc_chipname = PCIC_TYPE_PCI1410;
5333 break;
5334 case PCIC_TI_PCI1510:
5335 pcic->pc_chipname = PCIC_TYPE_PCI1510;
5336 break;
5337 case PCIC_TI_PCI1520:
5338 pcic->pc_chipname = PCIC_TYPE_PCI1520;
5339 break;
5340 case PCIC_TI_PCI1221:
5341 pcic->pc_chipname = PCIC_TYPE_PCI1221;
5342 break;
5343 case PCIC_TI_PCI1050:
5344 pcic->pc_chipname = PCIC_TYPE_PCI1050;
5345 break;
5346 case PCIC_ENE_1410:
5347 pcic->pc_chipname = PCIC_TYPE_1410;
5348 break;
5349 case PCIC_O2_OZ6912:
5350 pcic->pc_chipname = PCIC_TYPE_OZ6912;
5351 break;
5352 case PCIC_RICOH_RL5C466:
5353 pcic->pc_chipname = PCIC_TYPE_RL5C466;
5354 break;
5355 case PCIC_TI_PCI1420:
5356 pcic->pc_chipname = PCIC_TYPE_PCI1420;
5357 break;
5358 case PCIC_ENE_1420:
5359 pcic->pc_chipname = PCIC_TYPE_1420;
5360 break;
5361 default:
5362 switch (PCI_ID(vend, (uint32_t)0)) {
5363 case PCIC_TOSHIBA_VENDOR:
5364 pcic->pc_chipname = PCIC_TYPE_TOSHIBA;
5365 pcic->pc_type = PCIC_TOSHIBA_VENDOR;
5366 break;
5367 case PCIC_TI_VENDOR:
5368 pcic->pc_chipname = PCIC_TYPE_TI;
5369 pcic->pc_type = PCIC_TI_VENDOR;
5370 break;
5371 case PCIC_O2MICRO_VENDOR:
5372 pcic->pc_chipname = PCIC_TYPE_O2MICRO;
5373 pcic->pc_type = PCIC_O2MICRO_VENDOR;
5374 break;
5375 case PCIC_RICOH_VENDOR:
5376 pcic->pc_chipname = PCIC_TYPE_RICOH;
5377 pcic->pc_type = PCIC_RICOH_VENDOR;
5378 break;
5379 default:
5380 if (!(pcic->pc_flags & PCF_CARDBUS))
5381 return (DDI_FAILURE);
5382 pcic->pc_chipname = PCIC_TYPE_YENTA;
5383 break;
5386 return (DDI_SUCCESS);
5389 static void
5390 pcic_82092_smiirq_ctl(pcicdev_t *pcic, int socket, int intr, int state)
5392 uchar_t ppirr = ddi_get8(pcic->cfg_handle,
5393 pcic->cfgaddr + PCIC_82092_PPIRR);
5394 uchar_t val;
5396 if (intr == PCIC_82092_CTL_SMI) {
5397 val = PCIC_82092_SMI_CTL(socket,
5398 PCIC_82092_INT_DISABLE);
5399 ppirr &= ~val;
5400 val = PCIC_82092_SMI_CTL(socket, state);
5401 ppirr |= val;
5402 } else {
5403 val = PCIC_82092_IRQ_CTL(socket,
5404 PCIC_82092_INT_DISABLE);
5405 ppirr &= ~val;
5406 val = PCIC_82092_IRQ_CTL(socket, state);
5407 ppirr |= val;
5409 ddi_put8(pcic->cfg_handle, pcic->cfgaddr + PCIC_82092_PPIRR,
5410 ppirr);
5413 static uint_t
5414 pcic_cd_softint(caddr_t arg1, caddr_t arg2)
5416 pcic_socket_t *sockp = (pcic_socket_t *)arg1;
5417 uint_t rc = DDI_INTR_UNCLAIMED;
5419 _NOTE(ARGUNUSED(arg2))
5421 mutex_enter(&sockp->pcs_pcic->pc_lock);
5422 if (sockp->pcs_cd_softint_flg) {
5423 uint8_t status;
5424 sockp->pcs_cd_softint_flg = 0;
5425 rc = DDI_INTR_CLAIMED;
5426 status = pcic_getb(sockp->pcs_pcic, sockp->pcs_socket,
5427 PCIC_INTERFACE_STATUS);
5428 pcic_handle_cd_change(sockp->pcs_pcic, sockp, status);
5430 mutex_exit(&sockp->pcs_pcic->pc_lock);
5431 return (rc);
5434 int pcic_debounce_cnt = PCIC_REM_DEBOUNCE_CNT;
5435 int pcic_debounce_intr_time = PCIC_REM_DEBOUNCE_TIME;
5436 int pcic_debounce_cnt_ok = PCIC_DEBOUNCE_OK_CNT;
5438 #ifdef CARDBUS
5439 static uint32_t pcic_cbps_on = 0;
5440 static uint32_t pcic_cbps_off = CB_PS_NOTACARD | CB_PS_CCDMASK |
5441 CB_PS_XVCARD | CB_PS_YVCARD;
5442 #else
5443 static uint32_t pcic_cbps_on = CB_PS_16BITCARD;
5444 static uint32_t pcic_cbps_off = CB_PS_NOTACARD | CB_PS_CCDMASK |
5445 CB_PS_CBCARD |
5446 CB_PS_XVCARD | CB_PS_YVCARD;
5447 #endif
5448 static void
5449 pcic_handle_cd_change(pcicdev_t *pcic, pcic_socket_t *sockp, uint8_t status)
5451 boolean_t do_debounce = B_FALSE;
5452 int debounce_time = drv_usectohz(pcic_debounce_time);
5453 uint8_t irq;
5454 timeout_id_t debounce;
5457 * Always reset debounce but may need to check original state later.
5459 debounce = sockp->pcs_debounce_id;
5460 sockp->pcs_debounce_id = 0;
5463 * Check to see whether a card is present or not. There are
5464 * only two states that we are concerned with - the state
5465 * where both CD pins are asserted, which means that the
5466 * card is fully seated, and the state where neither CD
5467 * pin is asserted, which means that the card is not
5468 * present.
5469 * The CD signals are generally very noisy and cause a lot of
5470 * contact bounce as the card is being inserted and
5471 * removed, so we need to do some software debouncing.
5474 #ifdef PCIC_DEBUG
5475 pcic_err(pcic->dip, 6,
5476 "pcic%d handle_cd_change: socket %d card status 0x%x"
5477 " deb 0x%p\n", ddi_get_instance(pcic->dip),
5478 sockp->pcs_socket, status, debounce);
5479 #endif
5480 switch (status & PCIC_ISTAT_CD_MASK) {
5481 case PCIC_CD_PRESENT_OK:
5482 sockp->pcs_flags &= ~(PCS_CARD_REMOVED|PCS_CARD_CBREM);
5483 if (!(sockp->pcs_flags & PCS_CARD_PRESENT)) {
5484 uint32_t cbps;
5485 #ifdef PCIC_DEBUG
5486 pcic_err(pcic->dip, 8, "New card (0x%x)\n", sockp->pcs_flags);
5487 #endif
5488 cbps = pcic_getcb(pcic, CB_PRESENT_STATE);
5489 #ifdef PCIC_DEBUG
5490 pcic_err(pcic->dip, 8, "CBus PS (0x%x)\n", cbps);
5491 #endif
5493 * Check the CB bits are sane.
5495 if ((cbps & pcic_cbps_on) != pcic_cbps_on ||
5496 cbps & pcic_cbps_off) {
5497 cmn_err(CE_WARN,
5498 "%s%d: Odd Cardbus Present State 0x%x\n",
5499 ddi_get_name(pcic->dip),
5500 ddi_get_instance(pcic->dip),
5501 cbps);
5502 pcic_putcb(pcic, CB_EVENT_FORCE, CB_EF_CVTEST);
5503 debounce = 0;
5504 debounce_time = drv_usectohz(1000000);
5506 if (debounce) {
5507 sockp->pcs_flags |= PCS_CARD_PRESENT;
5508 if (pcic_do_insertion) {
5510 cbps = pcic_getcb(pcic, CB_PRESENT_STATE);
5512 if (cbps & CB_PS_16BITCARD) {
5513 pcic_err(pcic->dip,
5514 8, "16 bit card inserted\n");
5515 sockp->pcs_flags |= PCS_CARD_IS16BIT;
5516 /* calls pcm_adapter_callback() */
5517 if (pcic->pc_callback) {
5519 (void) ddi_prop_update_string(
5520 DDI_DEV_T_NONE,
5521 pcic->dip, PCM_DEVICETYPE,
5522 "pccard");
5523 PC_CALLBACK(pcic->dip,
5524 pcic->pc_cb_arg,
5525 PCE_CARD_INSERT,
5526 sockp->pcs_socket);
5528 } else if (cbps & CB_PS_CBCARD) {
5529 pcic_err(pcic->dip,
5530 8, "32 bit card inserted\n");
5532 if (pcic->pc_flags & PCF_CARDBUS) {
5533 sockp->pcs_flags |=
5534 PCS_CARD_ISCARDBUS;
5535 #ifdef CARDBUS
5536 if (!pcic_load_cardbus(pcic,
5537 sockp)) {
5538 pcic_unload_cardbus(
5539 pcic, sockp);
5542 #else
5543 cmn_err(CE_NOTE,
5544 "32 bit Cardbus not"
5545 " supported in"
5546 " this device driver\n");
5547 #endif
5548 } else {
5550 * Ignore the card
5552 cmn_err(CE_NOTE,
5553 "32 bit Cardbus not"
5554 " supported on this"
5555 " device\n");
5557 } else {
5558 cmn_err(CE_NOTE,
5559 "Unsupported PCMCIA card"
5560 " inserted\n");
5563 } else {
5564 do_debounce = B_TRUE;
5566 } else {
5568 * It is possible to come through here if the system
5569 * starts up with cards already inserted. Do nothing
5570 * and don't worry about it.
5572 #ifdef PCIC_DEBUG
5573 pcic_err(pcic->dip, 5,
5574 "pcic%d: Odd card insertion indication on socket %d\n",
5575 ddi_get_instance(pcic->dip),
5576 sockp->pcs_socket);
5577 #endif
5579 break;
5581 default:
5582 if (!(sockp->pcs_flags & PCS_CARD_PRESENT)) {
5584 * Someone has started to insert a card so delay a while.
5586 do_debounce = B_TRUE;
5587 break;
5590 * Otherwise this is basically the same as not present
5591 * so fall through.
5594 /* FALLTHRU */
5595 case 0:
5596 if (sockp->pcs_flags & PCS_CARD_PRESENT) {
5597 if (pcic->pc_flags & PCF_CBPWRCTL) {
5598 pcic_putcb(pcic, CB_CONTROL, 0);
5599 } else {
5600 pcic_putb(pcic, sockp->pcs_socket,
5601 PCIC_POWER_CONTROL, 0);
5602 (void) pcic_getb(pcic, sockp->pcs_socket,
5603 PCIC_POWER_CONTROL);
5605 #ifdef PCIC_DEBUG
5606 pcic_err(pcic->dip, 8, "Card removed\n");
5607 #endif
5608 sockp->pcs_flags &= ~PCS_CARD_PRESENT;
5610 if (sockp->pcs_flags & PCS_CARD_IS16BIT) {
5611 sockp->pcs_flags &= ~PCS_CARD_IS16BIT;
5612 if (pcic_do_removal && pcic->pc_callback) {
5613 PC_CALLBACK(pcic->dip, pcic->pc_cb_arg,
5614 PCE_CARD_REMOVAL, sockp->pcs_socket);
5617 if (sockp->pcs_flags & PCS_CARD_ISCARDBUS) {
5618 sockp->pcs_flags &= ~PCS_CARD_ISCARDBUS;
5619 sockp->pcs_flags |= PCS_CARD_CBREM;
5621 sockp->pcs_flags |= PCS_CARD_REMOVED;
5623 do_debounce = B_TRUE;
5625 if (debounce && (sockp->pcs_flags & PCS_CARD_REMOVED)) {
5626 if (sockp->pcs_flags & PCS_CARD_CBREM) {
5628 * Ensure that we do the unloading in the
5629 * debounce handler, that way we're not doing
5630 * nasty things in an interrupt handler. e.g.
5631 * a USB device will wait for data which will
5632 * obviously never come because we've
5633 * unplugged the device, but the wait will
5634 * wait forever because no interrupts can
5635 * come in...
5637 #ifdef CARDBUS
5638 pcic_unload_cardbus(pcic, sockp);
5639 /* pcic_dump_all(pcic); */
5640 #endif
5641 sockp->pcs_flags &= ~PCS_CARD_CBREM;
5643 sockp->pcs_flags &= ~PCS_CARD_REMOVED;
5645 break;
5646 } /* switch */
5648 if (do_debounce) {
5650 * Delay doing
5651 * anything for a while so that things can settle
5652 * down a little. Interrupts are already disabled.
5653 * Reset the state and we'll reevaluate the
5654 * whole kit 'n kaboodle when the timeout fires
5656 #ifdef PCIC_DEBUG
5657 pcic_err(pcic->dip, 8, "Queueing up debounce timeout for "
5658 "socket %d.%d\n",
5659 ddi_get_instance(pcic->dip),
5660 sockp->pcs_socket);
5661 #endif
5662 sockp->pcs_debounce_id =
5663 pcic_add_debqueue(sockp, debounce_time);
5666 * We bug out here without re-enabling interrupts. They will
5667 * be re-enabled when the debounce timeout swings through
5668 * here.
5670 return;
5674 * Turn on Card detect interrupts. Other interrupts will be
5675 * enabled during set_socket calls.
5677 * Note that set_socket only changes interrupt settings when there
5678 * is a card present.
5680 irq = pcic_getb(pcic, sockp->pcs_socket, PCIC_MANAGEMENT_INT);
5681 irq |= PCIC_CD_DETECT;
5682 pcic_putb(pcic, sockp->pcs_socket, PCIC_MANAGEMENT_INT, irq);
5683 pcic_putcb(pcic, CB_STATUS_MASK, CB_SE_CCDMASK);
5685 /* Out from debouncing state */
5686 sockp->pcs_flags &= ~PCS_DEBOUNCING;
5688 pcic_err(pcic->dip, 7, "Leaving pcic_handle_cd_change\n");
5692 * pcic_getb()
5693 * get an I/O byte based on the yardware decode method
5695 static uint8_t
5696 pcic_getb(pcicdev_t *pcic, int socket, int reg)
5698 int work;
5700 #if defined(PCIC_DEBUG)
5701 if (pcic_debug == 0x7fff) {
5702 cmn_err(CE_CONT, "pcic_getb0: pcic=%p socket=%d reg=%d\n",
5703 (void *)pcic, socket, reg);
5704 cmn_err(CE_CONT, "pcic_getb1: type=%d handle=%p ioaddr=%p \n",
5705 pcic->pc_io_type, (void *)pcic->handle,
5706 (void *)pcic->ioaddr);
5708 #endif
5710 switch (pcic->pc_io_type) {
5711 case PCIC_IO_TYPE_YENTA:
5712 return (ddi_get8(pcic->handle,
5713 pcic->ioaddr + CB_R2_OFFSET + reg));
5714 default:
5715 work = (socket * PCIC_SOCKET_1) | reg;
5716 ddi_put8(pcic->handle, pcic->ioaddr, work);
5717 return (ddi_get8(pcic->handle, pcic->ioaddr + 1));
5721 static void
5722 pcic_putb(pcicdev_t *pcic, int socket, int reg, int8_t value)
5724 int work;
5726 #if defined(PCIC_DEBUG)
5727 if (pcic_debug == 0x7fff) {
5728 cmn_err(CE_CONT,
5729 "pcic_putb0: pcic=%p socket=%d reg=%d value=%x \n",
5730 (void *)pcic, socket, reg, value);
5731 cmn_err(CE_CONT,
5732 "pcic_putb1: type=%d handle=%p ioaddr=%p \n",
5733 pcic->pc_io_type, (void *)pcic->handle,
5734 (void *)pcic->ioaddr);
5736 #endif
5739 switch (pcic->pc_io_type) {
5740 case PCIC_IO_TYPE_YENTA:
5741 ddi_put8(pcic->handle, pcic->ioaddr + CB_R2_OFFSET + reg,
5742 value);
5743 break;
5744 default:
5745 work = (socket * PCIC_SOCKET_1) | reg;
5746 ddi_put8(pcic->handle, pcic->ioaddr, work);
5747 ddi_put8(pcic->handle, pcic->ioaddr + 1, value);
5748 break;
5753 * chip identification functions
5757 * chip identification: Cirrus Logic PD6710/6720/6722
5759 static int
5760 pcic_ci_cirrus(pcicdev_t *pcic)
5762 int value1, value2;
5764 /* Init the CL id mode */
5765 value1 = pcic_getb(pcic, 0, PCIC_CHIP_INFO);
5766 pcic_putb(pcic, 0, PCIC_CHIP_INFO, 0);
5767 value1 = pcic_getb(pcic, 0, PCIC_CHIP_INFO);
5768 value2 = pcic_getb(pcic, 0, PCIC_CHIP_INFO);
5770 if ((value1 & PCIC_CI_ID) == PCIC_CI_ID &&
5771 (value2 & PCIC_CI_ID) == 0) {
5772 /* chip is a Cirrus Logic and not Intel */
5773 pcic->pc_type = PCIC_CL_PD6710;
5774 if (value1 & PCIC_CI_SLOTS)
5775 pcic->pc_chipname = PCIC_TYPE_PD6720;
5776 else
5777 pcic->pc_chipname = PCIC_TYPE_PD6710;
5778 /* now fine tune things just in case a 6722 */
5779 value1 = clext_reg_read(pcic, 0, PCIC_CLEXT_DMASK_0);
5780 if (value1 == 0) {
5781 clext_reg_write(pcic, 0, PCIC_CLEXT_SCRATCH, 0x55);
5782 value1 = clext_reg_read(pcic, 0, PCIC_CLEXT_SCRATCH);
5783 if (value1 == 0x55) {
5784 pcic->pc_chipname = PCIC_TYPE_PD6722;
5785 pcic->pc_type = PCIC_CL_PD6722;
5786 clext_reg_write(pcic, 0, PCIC_CLEXT_SCRATCH, 0);
5789 return (1);
5791 return (0);
5795 * chip identification: Vadem (VG365/465/468/469)
5798 static void
5799 pcic_vadem_enable(pcicdev_t *pcic)
5801 ddi_put8(pcic->handle, pcic->ioaddr, PCIC_VADEM_P1);
5802 ddi_put8(pcic->handle, pcic->ioaddr, PCIC_VADEM_P2);
5803 ddi_put8(pcic->handle, pcic->ioaddr, pcic->pc_lastreg);
5806 static int
5807 pcic_ci_vadem(pcicdev_t *pcic)
5809 int value;
5811 pcic_vadem_enable(pcic);
5812 value = pcic_getb(pcic, 0, PCIC_CHIP_REVISION);
5813 pcic_putb(pcic, 0, PCIC_CHIP_REVISION, 0xFF);
5814 if (pcic_getb(pcic, 0, PCIC_CHIP_REVISION) ==
5815 (value | PCIC_VADEM_D3) ||
5816 (pcic_getb(pcic, 0, PCIC_CHIP_REVISION) & PCIC_REV_MASK) ==
5817 PCIC_VADEM_469) {
5818 int vadem, new;
5819 pcic_vadem_enable(pcic);
5820 vadem = pcic_getb(pcic, 0, PCIC_VG_DMA) &
5821 ~(PCIC_V_UNLOCK | PCIC_V_VADEMREV);
5822 new = vadem | (PCIC_V_VADEMREV|PCIC_V_UNLOCK);
5823 pcic_putb(pcic, 0, PCIC_VG_DMA, new);
5824 value = pcic_getb(pcic, 0, PCIC_CHIP_REVISION);
5826 /* want to lock but leave mouse or other on */
5827 pcic_putb(pcic, 0, PCIC_VG_DMA, vadem);
5828 switch (value & PCIC_REV_MASK) {
5829 case PCIC_VADEM_365:
5830 pcic->pc_chipname = PCIC_VG_365;
5831 pcic->pc_type = PCIC_VADEM;
5832 break;
5833 case PCIC_VADEM_465:
5834 pcic->pc_chipname = PCIC_VG_465;
5835 pcic->pc_type = PCIC_VADEM;
5836 pcic->pc_flags |= PCF_1SOCKET;
5837 break;
5838 case PCIC_VADEM_468:
5839 pcic->pc_chipname = PCIC_VG_468;
5840 pcic->pc_type = PCIC_VADEM;
5841 break;
5842 case PCIC_VADEM_469:
5843 pcic->pc_chipname = PCIC_VG_469;
5844 pcic->pc_type = PCIC_VADEM_VG469;
5845 break;
5847 return (1);
5849 return (0);
5853 * chip identification: Ricoh
5855 static int
5856 pcic_ci_ricoh(pcicdev_t *pcic)
5858 int value;
5860 value = pcic_getb(pcic, 0, PCIC_RF_CHIP_IDENT);
5861 switch (value) {
5862 case PCIC_RF_296:
5863 pcic->pc_type = PCIC_RICOH;
5864 pcic->pc_chipname = PCIC_TYPE_RF5C296;
5865 return (1);
5866 case PCIC_RF_396:
5867 pcic->pc_type = PCIC_RICOH;
5868 pcic->pc_chipname = PCIC_TYPE_RF5C396;
5869 return (1);
5871 return (0);
5876 * set up available address spaces in busra
5878 static void
5879 pcic_init_assigned(dev_info_t *dip)
5881 pcm_regs_t *pcic_avail_p;
5882 pci_regspec_t *pci_avail_p, *regs;
5883 int len, entries, rlen;
5884 dev_info_t *pdip;
5886 if (ddi_getlongprop(DDI_DEV_T_ANY, dip, DDI_PROP_DONTPASS,
5887 "available", (caddr_t)&pcic_avail_p, &len) == DDI_PROP_SUCCESS) {
5889 * found "available" property at the cardbus/pcmcia node
5890 * need to translate address space entries from pcmcia
5891 * format to pci format
5893 entries = len / sizeof (pcm_regs_t);
5894 pci_avail_p = kmem_alloc(sizeof (pci_regspec_t) * entries,
5895 KM_SLEEP);
5896 if (pcic_apply_avail_ranges(dip, pcic_avail_p, pci_avail_p,
5897 entries) == DDI_SUCCESS)
5898 (void) pci_resource_setup_avail(dip, pci_avail_p,
5899 entries);
5900 kmem_free(pcic_avail_p, len);
5901 kmem_free(pci_avail_p, entries * sizeof (pci_regspec_t));
5902 return;
5906 * "legacy" platforms will have "available" property in pci node
5908 for (pdip = ddi_get_parent(dip); pdip; pdip = ddi_get_parent(pdip)) {
5909 if (ddi_getlongprop(DDI_DEV_T_ANY, pdip, DDI_PROP_DONTPASS,
5910 "available", (caddr_t)&pci_avail_p, &len) ==
5911 DDI_PROP_SUCCESS) {
5912 /* (void) pci_resource_setup(pdip); */
5913 kmem_free(pci_avail_p, len);
5914 break;
5918 if (pdip == NULL) {
5919 int len;
5920 char bus_type[16] = "(unknown)";
5921 dev_info_t *par;
5923 cmn_err(CE_CONT,
5924 "?pcic_init_assigned: no available property for pcmcia\n");
5927 * This code is taken from pci_resource_setup() but does
5928 * not attempt to use the "available" property to populate
5929 * the ndi maps that are created.
5930 * The fact that we will actually
5931 * free some resource below (that was allocated by OBP)
5932 * should be enough to be going on with.
5934 for (par = dip; par != NULL; par = ddi_get_parent(par)) {
5935 len = sizeof (bus_type);
5937 if ((ddi_prop_op(DDI_DEV_T_ANY, par,
5938 PROP_LEN_AND_VAL_BUF,
5939 DDI_PROP_CANSLEEP | DDI_PROP_DONTPASS,
5940 "device_type",
5941 (caddr_t)&bus_type, &len) == DDI_SUCCESS) &&
5942 (strcmp(bus_type, DEVI_PCI_NEXNAME) == 0 ||
5943 strcmp(bus_type, DEVI_PCIEX_NEXNAME) == 0))
5944 break;
5946 if (par != NULL &&
5947 (ndi_ra_map_setup(par, NDI_RA_TYPE_MEM) != NDI_SUCCESS ||
5948 ndi_ra_map_setup(par, NDI_RA_TYPE_IO) != NDI_SUCCESS))
5949 par = NULL;
5950 } else {
5951 #ifdef CARDBUS
5952 cardbus_bus_range_t *bus_range;
5953 int k;
5955 if (ddi_getlongprop(DDI_DEV_T_ANY, pdip, 0, "bus-range",
5956 (caddr_t)&bus_range, &k) == DDI_PROP_SUCCESS) {
5957 if (bus_range->lo != bus_range->hi)
5958 pcic_err(pdip, 9, "allowable bus range is "
5959 "%u->%u\n", bus_range->lo, bus_range->hi);
5960 else {
5961 pcic_err(pdip, 0,
5962 "!No spare PCI bus numbers, range is "
5963 "%u->%u, cardbus isn't usable\n",
5964 bus_range->lo, bus_range->hi);
5966 kmem_free(bus_range, k);
5967 } else
5968 pcic_err(pdip, 0, "!No bus-range property seems to "
5969 "have been set up\n");
5970 #endif
5972 * Have a valid parent with the "available" property
5974 (void) pci_resource_setup(pdip);
5977 if ((strcmp(ddi_get_name(dip), "pcma") == 0) &&
5978 ddi_getlongprop(DDI_DEV_T_NONE, dip, DDI_PROP_DONTPASS,
5979 "assigned-addresses",
5980 (caddr_t)&regs, &rlen) == DDI_SUCCESS) {
5981 ra_return_t ra;
5984 * On the UltraBook IIi the ranges are assigned under
5985 * openboot. If we don't free them here the first I/O
5986 * space that can be used is up above 0x10000 which
5987 * doesn't work for this driver due to restrictions
5988 * on the PCI I/O addresses the controllers can cope with.
5989 * They are never going to be used by anything else
5990 * so free them up to the general pool. AG.
5992 pcic_err(dip, 1, "Free assigned addresses\n");
5994 if ((PCI_REG_ADDR_G(regs[0].pci_phys_hi) ==
5995 PCI_REG_ADDR_G(PCI_ADDR_MEM32)) &&
5996 regs[0].pci_size_low == 0x1000000) {
5997 ra.ra_addr_lo = regs[0].pci_phys_low;
5998 ra.ra_len = regs[0].pci_size_low;
5999 (void) pcmcia_free_mem(dip, &ra);
6001 if ((PCI_REG_ADDR_G(regs[1].pci_phys_hi) ==
6002 PCI_REG_ADDR_G(PCI_ADDR_IO)) &&
6003 (regs[1].pci_size_low == 0x8000 ||
6004 regs[1].pci_size_low == 0x4000)) /* UB-IIi || UB-I */
6006 ra.ra_addr_lo = regs[1].pci_phys_low;
6007 ra.ra_len = regs[1].pci_size_low;
6008 (void) pcmcia_free_io(dip, &ra);
6010 kmem_free((caddr_t)regs, rlen);
6015 * translate "available" from pcmcia format to pci format
6017 static int
6018 pcic_apply_avail_ranges(dev_info_t *dip, pcm_regs_t *pcic_p,
6019 pci_regspec_t *pci_p, int entries)
6021 int i, range_len, range_entries;
6022 pcic_ranges_t *pcic_range_p;
6024 if (ddi_getlongprop(DDI_DEV_T_ANY, dip, DDI_PROP_DONTPASS, "ranges",
6025 (caddr_t)&pcic_range_p, &range_len) != DDI_PROP_SUCCESS) {
6026 cmn_err(CE_CONT, "?pcic_apply_avail_ranges: "
6027 "no ranges property for pcmcia\n");
6028 return (DDI_FAILURE);
6031 range_entries = range_len / sizeof (pcic_ranges_t);
6033 /* for each "available" entry to be translated */
6034 for (i = 0; i < entries; i++, pcic_p++, pci_p++) {
6035 int j;
6036 pcic_ranges_t *range_p = pcic_range_p;
6037 pci_p->pci_phys_hi = -1u; /* default invalid value */
6039 /* for each "ranges" entry to be searched */
6040 for (j = 0; j < range_entries; j++, range_p++) {
6041 uint64_t range_end = range_p->pcic_range_caddrlo +
6042 range_p->pcic_range_size;
6043 uint64_t avail_end = pcic_p->phys_lo + pcic_p->phys_len;
6045 if ((range_p->pcic_range_caddrhi != pcic_p->phys_hi) ||
6046 (range_p->pcic_range_caddrlo > pcic_p->phys_lo) ||
6047 (range_end < avail_end))
6048 continue;
6050 pci_p->pci_phys_hi = range_p->pcic_range_paddrhi;
6051 pci_p->pci_phys_mid = range_p->pcic_range_paddrmid;
6052 pci_p->pci_phys_low = range_p->pcic_range_paddrlo
6053 + (pcic_p->phys_lo - range_p->pcic_range_caddrlo);
6054 pci_p->pci_size_hi = 0;
6055 pci_p->pci_size_low = pcic_p->phys_len;
6058 kmem_free(pcic_range_p, range_len);
6059 return (DDI_SUCCESS);
6062 static int
6063 pcic_open(dev_t *dev, int flag, int otyp, cred_t *cred)
6065 #ifdef CARDBUS
6066 if (cardbus_is_cb_minor(*dev))
6067 return (cardbus_open(dev, flag, otyp, cred));
6068 #endif
6069 return (EINVAL);
6072 static int
6073 pcic_close(dev_t dev, int flag, int otyp, cred_t *cred)
6075 #ifdef CARDBUS
6076 if (cardbus_is_cb_minor(dev))
6077 return (cardbus_close(dev, flag, otyp, cred));
6078 #endif
6079 return (EINVAL);
6082 static int
6083 pcic_ioctl(dev_t dev, int cmd, intptr_t arg, int mode, cred_t *cred,
6084 int *rval)
6086 #ifdef CARDBUS
6087 if (cardbus_is_cb_minor(dev))
6088 return (cardbus_ioctl(dev, cmd, arg, mode, cred, rval));
6089 #endif
6090 return (EINVAL);
6094 static boolean_t
6095 pcic_load_cardbus(pcicdev_t *pcic, const pcic_socket_t *sockp)
6097 uint32_t present_state;
6098 dev_info_t *dip = pcic->dip;
6099 set_socket_t s;
6100 get_socket_t g;
6101 boolean_t retval;
6102 unsigned vccLevel;
6104 pcic_err(dip, 8, "entering pcic_load_cardbus\n");
6106 pcic_mutex_exit(&pcic->pc_lock);
6108 bzero(&s, sizeof (set_socket_t));
6109 s.socket = sockp->pcs_socket;
6110 s.SCIntMask = SBM_CD|SBM_RDYBSY;
6111 s.IFType = IF_CARDBUS;
6112 s.State = (unsigned)~0;
6114 present_state = pcic_getcb(pcic, CB_PRESENT_STATE);
6115 if (present_state & PCIC_VCC_3VCARD)
6116 s.VccLevel = PCIC_VCC_3VLEVEL;
6117 else if (present_state & PCIC_VCC_5VCARD)
6118 s.VccLevel = PCIC_VCC_5VLEVEL;
6119 else {
6120 cmn_err(CE_CONT,
6121 "pcic_load_cardbus: unsupported card voltage\n");
6122 goto failure;
6124 vccLevel = s.VccLevel;
6125 s.Vpp1Level = s.Vpp2Level = 0;
6127 if (pcic_set_socket(dip, &s) != SUCCESS)
6128 goto failure;
6130 if (pcic_reset_socket(dip, sockp->pcs_socket,
6131 RESET_MODE_CARD_ONLY) != SUCCESS)
6132 goto failure;
6134 bzero(&g, sizeof (get_socket_t));
6135 g.socket = sockp->pcs_socket;
6136 if (pcic_get_socket(dip, &g) != SUCCESS)
6137 goto failure;
6139 bzero(&s, sizeof (set_socket_t));
6140 s.socket = sockp->pcs_socket;
6141 s.SCIntMask = SBM_CD;
6142 s.IREQRouting = g.IRQRouting;
6143 s.IFType = g.IFType;
6144 s.CtlInd = g.CtlInd;
6145 s.State = (unsigned)~0;
6146 s.VccLevel = vccLevel;
6147 s.Vpp1Level = s.Vpp2Level = 0;
6149 retval = pcic_set_socket(dip, &s);
6150 pcmcia_cb_resumed(s.socket);
6151 if (retval != SUCCESS)
6152 goto failure;
6154 retval = cardbus_load_cardbus(dip, sockp->pcs_socket, pcic->pc_base);
6155 goto exit;
6157 failure:
6158 retval = B_FALSE;
6160 exit:
6161 pcic_mutex_enter(&pcic->pc_lock);
6162 pcic_err(dip, 8, "exit pcic_load_cardbus (%s)\n",
6163 retval ? "success" : "failure");
6164 return (retval);
6167 static void
6168 pcic_unload_cardbus(pcicdev_t *pcic, const pcic_socket_t *sockp)
6170 dev_info_t *dip = pcic->dip;
6171 set_socket_t s;
6173 pcic_mutex_exit(&pcic->pc_lock);
6175 cardbus_unload_cardbus(dip);
6177 bzero(&s, sizeof (set_socket_t));
6178 s.socket = sockp->pcs_socket;
6179 s.SCIntMask = SBM_CD|SBM_RDYBSY;
6180 s.IREQRouting = 0;
6181 s.IFType = IF_MEMORY;
6182 s.CtlInd = 0;
6183 s.State = 0;
6184 s.VccLevel = s.Vpp1Level = s.Vpp2Level = 0;
6186 (void) pcic_set_socket(dip, &s);
6188 pcic_mutex_enter(&pcic->pc_lock);
6191 static uint32_t
6192 pcic_getcb(pcicdev_t *pcic, int reg)
6194 ASSERT(pcic->pc_io_type == PCIC_IO_TYPE_YENTA);
6196 return (ddi_get32(pcic->handle,
6197 (uint32_t *)(pcic->ioaddr + CB_CB_OFFSET + reg)));
6200 static void
6201 pcic_putcb(pcicdev_t *pcic, int reg, uint32_t value)
6203 ASSERT(pcic->pc_io_type == PCIC_IO_TYPE_YENTA);
6205 ddi_put32(pcic->handle,
6206 (uint32_t *)(pcic->ioaddr + CB_CB_OFFSET + reg), value);
6209 static void
6210 pcic_enable_io_intr(pcicdev_t *pcic, int socket, int irq)
6212 uint8_t value;
6213 uint16_t brdgctl;
6215 value = pcic_getb(pcic, socket, PCIC_INTERRUPT) & ~PCIC_INTR_MASK;
6216 pcic_putb(pcic, socket, PCIC_INTERRUPT, value | irq);
6218 switch (pcic->pc_type) {
6219 case PCIC_INTEL_i82092:
6220 pcic_82092_smiirq_ctl(pcic, socket, PCIC_82092_CTL_IRQ,
6221 PCIC_82092_INT_ENABLE);
6222 break;
6223 case PCIC_O2_OZ6912:
6224 value = pcic_getb(pcic, 0, PCIC_CENTDMA);
6225 value |= 0x8;
6226 pcic_putb(pcic, 0, PCIC_CENTDMA, value);
6227 break;
6228 case PCIC_CL_PD6832:
6229 case PCIC_TI_PCI1250:
6230 case PCIC_TI_PCI1221:
6231 case PCIC_TI_PCI1225:
6232 case PCIC_TI_PCI1410:
6233 case PCIC_ENE_1410:
6234 case PCIC_TI_PCI1510:
6235 case PCIC_TI_PCI1520:
6236 case PCIC_TI_PCI1420:
6237 case PCIC_ENE_1420:
6238 /* route card functional interrupts to PCI interrupts */
6239 brdgctl = ddi_get16(pcic->cfg_handle,
6240 (uint16_t *)(pcic->cfgaddr + PCI_CBUS_BRIDGE_CTRL));
6241 pcic_err(NULL, 1,
6242 "pcic_enable_io_intr brdgctl(0x%x) was: 0x%x\n",
6243 PCI_CBUS_BRIDGE_CTRL, brdgctl);
6244 brdgctl &= ~PCIC_BRDGCTL_INTR_MASK;
6245 ddi_put16(pcic->cfg_handle,
6246 (uint16_t *)(pcic->cfgaddr + PCI_CBUS_BRIDGE_CTRL),
6247 brdgctl);
6248 /* Flush the write */
6249 (void) ddi_get16(pcic->cfg_handle,
6250 (uint16_t *)(pcic->cfgaddr + PCI_CBUS_BRIDGE_CTRL));
6251 break;
6252 default:
6253 break;
6257 static void
6258 pcic_disable_io_intr(pcicdev_t *pcic, int socket)
6260 uint8_t value;
6261 uint16_t brdgctl;
6263 value = pcic_getb(pcic, socket, PCIC_INTERRUPT) & ~PCIC_INTR_MASK;
6264 pcic_putb(pcic, socket, PCIC_INTERRUPT, value);
6266 switch (pcic->pc_type) {
6267 case PCIC_INTEL_i82092:
6268 pcic_82092_smiirq_ctl(pcic, socket, PCIC_82092_CTL_IRQ,
6269 PCIC_82092_INT_DISABLE);
6270 break;
6271 case PCIC_O2_OZ6912:
6272 value = pcic_getb(pcic, 0, PCIC_CENTDMA);
6273 value &= ~0x8;
6274 pcic_putb(pcic, 0, PCIC_CENTDMA, value);
6275 /* Flush the write */
6276 (void) pcic_getb(pcic, 0, PCIC_CENTDMA);
6277 break;
6278 case PCIC_CL_PD6832:
6279 case PCIC_TI_PCI1250:
6280 case PCIC_TI_PCI1221:
6281 case PCIC_TI_PCI1225:
6282 case PCIC_TI_PCI1410:
6283 case PCIC_ENE_1410:
6284 case PCIC_TI_PCI1510:
6285 case PCIC_TI_PCI1520:
6286 case PCIC_TI_PCI1420:
6287 case PCIC_ENE_1420:
6289 * This maps I/O interrupts to ExCA which
6290 * have been turned off by the write to
6291 * PCIC_INTERRUPT above. It would appear to
6292 * be the only way to actually turn I/O Ints off
6293 * while retaining CS Ints.
6295 brdgctl = ddi_get16(pcic->cfg_handle,
6296 (uint16_t *)(pcic->cfgaddr + PCI_CBUS_BRIDGE_CTRL));
6297 pcic_err(NULL, 1,
6298 "pcic_disable_io_intr brdgctl(0x%x) was: 0x%x\n",
6299 PCI_CBUS_BRIDGE_CTRL, brdgctl);
6300 brdgctl |= PCIC_BRDGCTL_INTR_MASK;
6301 ddi_put16(pcic->cfg_handle,
6302 (uint16_t *)(pcic->cfgaddr + PCI_CBUS_BRIDGE_CTRL),
6303 brdgctl);
6304 /* Flush the write */
6305 (void) ddi_get16(pcic->cfg_handle,
6306 (uint16_t *)(pcic->cfgaddr + PCI_CBUS_BRIDGE_CTRL));
6307 break;
6308 default:
6309 break;
6313 static void
6314 pcic_cb_enable_intr(dev_info_t *dip)
6316 anp_t *anp = ddi_get_driver_private(dip);
6317 pcicdev_t *pcic = anp->an_private;
6319 mutex_enter(&pcic->pc_lock);
6320 pcic_enable_io_intr(pcic, 0, pcic->pc_sockets[0].pcs_irq);
6321 mutex_exit(&pcic->pc_lock);
6324 static void
6325 pcic_cb_disable_intr(dev_info_t *dip)
6327 anp_t *anp = ddi_get_driver_private(dip);
6328 pcicdev_t *pcic = anp->an_private;
6330 mutex_enter(&pcic->pc_lock);
6331 pcic_disable_io_intr(pcic, 0);
6332 mutex_exit(&pcic->pc_lock);
6335 static int
6336 log_pci_cfg_err(ushort_t e, int bridge_secondary)
6338 int nerr = 0;
6339 if (e & PCI_STAT_PERROR) {
6340 nerr++;
6341 cmn_err(CE_CONT, "detected parity error.\n");
6343 if (e & PCI_STAT_S_SYSERR) {
6344 nerr++;
6345 if (bridge_secondary)
6346 cmn_err(CE_CONT, "received system error.\n");
6347 else
6348 cmn_err(CE_CONT, "signalled system error.\n");
6350 if (e & PCI_STAT_R_MAST_AB) {
6351 nerr++;
6352 cmn_err(CE_CONT, "received master abort.\n");
6354 if (e & PCI_STAT_R_TARG_AB)
6355 cmn_err(CE_CONT, "received target abort.\n");
6356 if (e & PCI_STAT_S_TARG_AB)
6357 cmn_err(CE_CONT, "signalled target abort\n");
6358 if (e & PCI_STAT_S_PERROR) {
6359 nerr++;
6360 cmn_err(CE_CONT, "signalled parity error\n");
6362 return (nerr);
6365 #if defined(__sparc)
6366 static int
6367 pcic_fault(enum pci_fault_ops op, void *arg)
6369 pcicdev_t *pcic = (pcicdev_t *)arg;
6370 ushort_t pci_cfg_stat =
6371 pci_config_get16(pcic->cfg_handle, PCI_CONF_STAT);
6372 ushort_t pci_cfg_sec_stat =
6373 pci_config_get16(pcic->cfg_handle, 0x16);
6374 char nm[24];
6375 int nerr = 0;
6377 cardbus_dump_pci_config(pcic->dip);
6379 switch (op) {
6380 case FAULT_LOG:
6381 (void) sprintf(nm, "%s-%d", ddi_driver_name(pcic->dip),
6382 ddi_get_instance(pcic->dip));
6384 cmn_err(CE_WARN, "%s: PCIC fault log start:\n", nm);
6385 cmn_err(CE_WARN, "%s: primary err (%x):\n", nm, pci_cfg_stat);
6386 nerr += log_pci_cfg_err(pci_cfg_stat, 0);
6387 cmn_err(CE_WARN, "%s: sec err (%x):\n", nm, pci_cfg_sec_stat);
6388 nerr += log_pci_cfg_err(pci_cfg_sec_stat, 1);
6389 cmn_err(CE_CONT, "%s: PCI fault log end.\n", nm);
6390 return (nerr);
6391 case FAULT_POKEFINI:
6392 case FAULT_RESET:
6393 pci_config_put16(pcic->cfg_handle,
6394 PCI_CONF_STAT, pci_cfg_stat);
6395 pci_config_put16(pcic->cfg_handle, 0x16, pci_cfg_sec_stat);
6396 break;
6397 case FAULT_POKEFLT:
6398 if (!(pci_cfg_stat & PCI_STAT_S_SYSERR))
6399 return (1);
6400 if (!(pci_cfg_sec_stat & PCI_STAT_R_MAST_AB))
6401 return (1);
6402 break;
6403 default:
6404 break;
6406 return (DDI_SUCCESS);
6408 #endif
6410 static void
6411 pcic_do_resume(pcicdev_t *pcic)
6413 int i, interrupt;
6414 uint8_t cfg;
6417 #if defined(PCIC_DEBUG)
6418 pcic_err(NULL, 6, "pcic_do_resume(): entered\n");
6419 #endif
6421 pcic_mutex_enter(&pcic->pc_lock); /* protect the registers */
6422 for (i = 0; i < pcic->pc_numsockets; i++) {
6423 /* Enable interrupts on PCI if needs be */
6424 interrupt = pcic_getb(pcic, i, PCIC_INTERRUPT);
6425 if (pcic->pc_flags & PCF_USE_SMI)
6426 interrupt |= PCIC_INTR_ENABLE;
6427 pcic_putb(pcic, i, PCIC_INTERRUPT,
6428 PCIC_RESET | interrupt);
6429 pcic->pc_sockets[i].pcs_debounce_id =
6430 pcic_add_debqueue(&pcic->pc_sockets[i],
6431 drv_usectohz(pcic_debounce_time));
6433 pcic_mutex_exit(&pcic->pc_lock); /* protect the registers */
6434 if (pcic_do_pcmcia_sr)
6435 (void) pcmcia_wait_insert(pcic->dip);
6437 * The CardBus controller may be in RESET state after the
6438 * system is resumed from sleeping. The RESET bit is in
6439 * the Bridge Control register. This is true for all(TI,
6440 * Toshiba ToPIC95/97, RICOH, and O2Micro) CardBus
6441 * controllers. Need to clear the RESET bit explicitly.
6443 cfg = ddi_get8(pcic->cfg_handle,
6444 pcic->cfgaddr + PCIC_BRIDGE_CTL_REG);
6445 if (cfg & (1<<6)) {
6446 cfg &= ~(1<<6);
6447 ddi_put8(pcic->cfg_handle,
6448 pcic->cfgaddr + PCIC_BRIDGE_CTL_REG,
6449 cfg);
6450 cfg = ddi_get8(pcic->cfg_handle,
6451 pcic->cfgaddr + PCIC_BRIDGE_CTL_REG);
6452 if (cfg & (1<<6)) {
6453 pcic_err(pcic->dip, 1,
6454 "Failed to take pcic out of reset");
6460 static void
6461 pcic_debounce(pcic_socket_t *pcs)
6463 uint8_t status, stschng;
6465 pcic_mutex_enter(&pcs->pcs_pcic->pc_lock);
6466 pcs->pcs_flags &= ~PCS_STARTING;
6467 stschng = pcic_getb(pcs->pcs_pcic, pcs->pcs_socket,
6468 PCIC_CARD_STATUS_CHANGE);
6469 status = pcic_getb(pcs->pcs_pcic, pcs->pcs_socket,
6470 PCIC_INTERFACE_STATUS);
6471 #ifdef PCIC_DEBUG
6472 pcic_err(pcs->pcs_pcic->dip, 8,
6473 "pcic_debounce(0x%p, dip=0x%p) socket %d st 0x%x "
6474 "chg 0x%x flg 0x%x\n",
6475 (void *)pcs, (void *) pcs->pcs_pcic->dip, pcs->pcs_socket,
6476 status, stschng, pcs->pcs_flags);
6477 #endif
6479 pcic_putb(pcs->pcs_pcic, pcs->pcs_socket, PCIC_CARD_STATUS_CHANGE,
6480 PCIC_CD_DETECT);
6481 pcic_handle_cd_change(pcs->pcs_pcic, pcs, status);
6482 pcic_mutex_exit(&pcs->pcs_pcic->pc_lock);
6485 static void
6486 pcic_deb_thread()
6488 callb_cpr_t cprinfo;
6489 struct debounce *debp;
6490 clock_t lastt;
6492 CALLB_CPR_INIT(&cprinfo, &pcic_deb_mtx,
6493 callb_generic_cpr, "pcic debounce thread");
6494 mutex_enter(&pcic_deb_mtx);
6495 while (pcic_deb_threadid) {
6496 while (pcic_deb_queue) {
6497 #ifdef PCIC_DEBUG
6498 pcic_dump_debqueue("Thread");
6499 #endif
6500 debp = pcic_deb_queue;
6501 (void) drv_getparm(LBOLT, &lastt);
6502 if (lastt >= debp->expire) {
6503 pcic_deb_queue = debp->next;
6504 mutex_exit(&pcic_deb_mtx);
6505 pcic_debounce(debp->pcs);
6506 mutex_enter(&pcic_deb_mtx);
6507 kmem_free(debp, sizeof (*debp));
6508 } else {
6509 (void) cv_timedwait(&pcic_deb_cv,
6510 &pcic_deb_mtx, debp->expire);
6513 CALLB_CPR_SAFE_BEGIN(&cprinfo);
6514 cv_wait(&pcic_deb_cv, &pcic_deb_mtx);
6515 CALLB_CPR_SAFE_END(&cprinfo, &pcic_deb_mtx);
6517 pcic_deb_threadid = (kthread_t *)1;
6518 cv_signal(&pcic_deb_cv);
6519 CALLB_CPR_EXIT(&cprinfo); /* Also exits the mutex */
6520 thread_exit();
6523 static void *
6524 pcic_add_debqueue(pcic_socket_t *pcs, int clocks)
6526 clock_t lbolt;
6527 struct debounce *dbp, **dbpp = &pcic_deb_queue;
6529 (void) drv_getparm(LBOLT, &lbolt);
6530 dbp = kmem_alloc(sizeof (struct debounce), KM_SLEEP);
6532 dbp->expire = lbolt + clocks;
6533 dbp->pcs = pcs;
6534 mutex_enter(&pcic_deb_mtx);
6535 while (*dbpp) {
6536 if (dbp->expire > (*dbpp)->expire)
6537 dbpp = &((*dbpp)->next);
6538 else
6539 break;
6541 dbp->next = *dbpp;
6542 *dbpp = dbp;
6543 #ifdef PCIC_DEBUG
6544 pcic_dump_debqueue("Add");
6545 #endif
6546 cv_signal(&pcic_deb_cv);
6547 mutex_exit(&pcic_deb_mtx);
6548 return (dbp);
6551 static void
6552 pcic_rm_debqueue(void *id)
6554 struct debounce *dbp, **dbpp = &pcic_deb_queue;
6556 dbp = (struct debounce *)id;
6557 mutex_enter(&pcic_deb_mtx);
6558 while (*dbpp) {
6559 if (*dbpp == dbp) {
6560 *dbpp = dbp->next;
6561 kmem_free(dbp, sizeof (*dbp));
6562 #ifdef PCIC_DEBUG
6563 pcic_dump_debqueue("Remove");
6564 #endif
6565 cv_signal(&pcic_deb_cv);
6566 mutex_exit(&pcic_deb_mtx);
6567 return;
6569 dbpp = &((*dbpp)->next);
6571 pcic_err(NULL, 6, "pcic: Failed to find debounce id 0x%p\n", id);
6572 mutex_exit(&pcic_deb_mtx);
6576 static int pcic_powerdelay = 0;
6578 static int
6579 pcic_exca_powerctl(pcicdev_t *pcic, int socket, int powerlevel)
6581 int ind, value, orig_pwrctl;
6583 /* power setup -- if necessary */
6584 orig_pwrctl = pcic_getb(pcic, socket, PCIC_POWER_CONTROL);
6586 #if defined(PCIC_DEBUG)
6587 pcic_err(pcic->dip, 6,
6588 "pcic_exca_powerctl(socket %d) powerlevel=%x orig 0x%x\n",
6589 socket, powerlevel, orig_pwrctl);
6590 #endif
6591 /* Preserve the PCIC_OUTPUT_ENABLE (control lines output enable) bit. */
6592 powerlevel = (powerlevel & ~POWER_OUTPUT_ENABLE) |
6593 (orig_pwrctl & POWER_OUTPUT_ENABLE);
6594 if (powerlevel != orig_pwrctl) {
6595 if (powerlevel & ~POWER_OUTPUT_ENABLE) {
6596 int ifs;
6598 * set power to socket
6599 * note that the powerlevel was calculated earlier
6601 pcic_putb(pcic, socket, PCIC_POWER_CONTROL, powerlevel);
6602 (void) pcic_getb(pcic, socket, PCIC_POWER_CONTROL);
6605 * this second write to the power control register
6606 * is needed to resolve a problem on
6607 * the IBM ThinkPad 750
6608 * where the first write doesn't latch.
6609 * The second write appears to always work and
6610 * doesn't hurt the operation of other chips
6611 * so we can just use it -- this is good since we can't
6612 * determine what chip the 750 actually uses
6613 * (I suspect an early Ricoh).
6615 pcic_putb(pcic, socket, PCIC_POWER_CONTROL, powerlevel);
6617 value = pcic_getb(pcic, socket, PCIC_POWER_CONTROL);
6618 pcic_mswait(pcic, socket, pcic_powerdelay);
6619 #if defined(PCIC_DEBUG)
6620 pcic_err(pcic->dip, 8,
6621 "\tpowerlevel reg = %x (ifs %x)\n",
6622 value, pcic_getb(pcic, socket,
6623 PCIC_INTERFACE_STATUS));
6624 pcic_err(pcic->dip, 8,
6625 "CBus regs: PS 0x%x, Control 0x%x\n",
6626 pcic_getcb(pcic, CB_PRESENT_STATE),
6627 pcic_getcb(pcic, CB_CONTROL));
6628 #endif
6630 * since power was touched, make sure it says it
6631 * is on. This lets it become stable.
6633 for (ind = 0; ind < 20; ind++) {
6634 ifs = pcic_getb(pcic, socket,
6635 PCIC_INTERFACE_STATUS);
6636 if (ifs & PCIC_POWER_ON)
6637 break;
6638 else {
6639 pcic_putb(pcic, socket,
6640 PCIC_POWER_CONTROL, 0);
6641 (void) pcic_getb(pcic, socket,
6642 PCIC_POWER_CONTROL);
6643 pcic_mswait(pcic, socket, 40);
6644 if (ind == 10) {
6645 pcic_putcb(pcic, CB_EVENT_FORCE,
6646 CB_EF_CVTEST);
6647 pcic_mswait(pcic, socket, 100);
6649 pcic_putb(pcic, socket,
6650 PCIC_POWER_CONTROL,
6651 powerlevel & ~POWER_OUTPUT_ENABLE);
6652 (void) pcic_getb(pcic, socket,
6653 PCIC_POWER_CONTROL);
6654 pcic_mswait(pcic, socket,
6655 pcic_powerdelay);
6656 pcic_putb(pcic, socket,
6657 PCIC_POWER_CONTROL, powerlevel);
6658 (void) pcic_getb(pcic, socket,
6659 PCIC_POWER_CONTROL);
6660 pcic_mswait(pcic, socket,
6661 pcic_powerdelay);
6665 if (!(ifs & PCIC_POWER_ON)) {
6666 cmn_err(CE_WARN,
6667 "pcic socket %d: Power didn't get turned"
6668 "on!\nif status 0x%x pwrc 0x%x(x%x) "
6669 "misc1 0x%x igc 0x%x ind %d\n",
6670 socket, ifs,
6671 pcic_getb(pcic, socket, PCIC_POWER_CONTROL),
6672 orig_pwrctl,
6673 pcic_getb(pcic, socket, PCIC_MISC_CTL_1),
6674 pcic_getb(pcic, socket, PCIC_INTERRUPT),
6675 ind);
6676 return (BAD_VCC);
6678 #if defined(PCIC_DEBUG)
6679 pcic_err(pcic->dip, 8,
6680 "\tind = %d, if status %x pwrc 0x%x "
6681 "misc1 0x%x igc 0x%x\n",
6682 ind, ifs,
6683 pcic_getb(pcic, socket, PCIC_POWER_CONTROL),
6684 pcic_getb(pcic, socket, PCIC_MISC_CTL_1),
6685 pcic_getb(pcic, socket, PCIC_INTERRUPT));
6686 #endif
6687 } else {
6688 /* explicitly turned off the power */
6689 pcic_putb(pcic, socket, PCIC_POWER_CONTROL, powerlevel);
6690 (void) pcic_getb(pcic, socket, PCIC_POWER_CONTROL);
6693 return (SUCCESS);
6696 static int pcic_cbdoreset_during_poweron = 1;
6697 static int
6698 pcic_cbus_powerctl(pcicdev_t *pcic, int socket)
6700 uint32_t cbctl = 0, orig_cbctl, cbstev, cbps;
6701 int ind, iobits;
6702 pcic_socket_t *sockp = &pcic->pc_sockets[socket];
6704 pcic_putcb(pcic, CB_STATUS_EVENT, CB_SE_POWER_CYCLE);
6706 ind = pcic_power[sockp->pcs_vpp1].PowerLevel/10;
6707 cbctl |= pcic_cbv_levels[ind];
6709 ind = pcic_power[sockp->pcs_vcc].PowerLevel/10;
6710 cbctl |= (pcic_cbv_levels[ind]<<4);
6712 orig_cbctl = pcic_getcb(pcic, CB_CONTROL);
6714 #if defined(PCIC_DEBUG)
6715 pcic_err(pcic->dip, 6,
6716 "pcic_cbus_powerctl(socket %d) vcc %d vpp1 %d "
6717 "cbctl 0x%x->0x%x\n",
6718 socket, sockp->pcs_vcc, sockp->pcs_vpp1, orig_cbctl, cbctl);
6719 #endif
6720 if (cbctl != orig_cbctl) {
6721 if (pcic_cbdoreset_during_poweron &&
6722 (orig_cbctl & (CB_C_VCCMASK|CB_C_VPPMASK)) == 0) {
6723 iobits = pcic_getb(pcic, socket, PCIC_INTERRUPT);
6724 pcic_putb(pcic, socket, PCIC_INTERRUPT,
6725 iobits & ~PCIC_RESET);
6727 pcic_putcb(pcic, CB_CONTROL, cbctl);
6729 if ((cbctl & CB_C_VCCMASK) == (orig_cbctl & CB_C_VCCMASK)) {
6730 pcic_mswait(pcic, socket, pcic_powerdelay);
6731 return (SUCCESS);
6733 for (ind = 0; ind < 20; ind++) {
6734 cbstev = pcic_getcb(pcic, CB_STATUS_EVENT);
6736 if (cbstev & CB_SE_POWER_CYCLE) {
6739 * delay 400 ms: though the standard defines that the Vcc
6740 * set-up time is 20 ms, some PC-Card bridge requires longer
6741 * duration.
6742 * Note: We should check the status AFTER the delay to give time
6743 * for things to stabilize.
6745 pcic_mswait(pcic, socket, 400);
6747 cbps = pcic_getcb(pcic, CB_PRESENT_STATE);
6748 if (cbctl && !(cbps & CB_PS_POWER_CYCLE)) {
6749 /* break; */
6750 cmn_err(CE_WARN, "cbus_powerctl: power off??\n");
6752 if (cbctl & CB_PS_BADVCC) {
6753 cmn_err(CE_WARN, "cbus_powerctl: bad power request\n");
6754 break;
6757 #if defined(PCIC_DEBUG)
6758 pcic_err(pcic->dip, 8,
6759 "cbstev = 0x%x cbps = 0x%x cbctl 0x%x(0x%x)",
6760 cbstev, pcic_getcb(pcic, CB_PRESENT_STATE),
6761 cbctl, orig_cbctl);
6762 #endif
6763 if (pcic_cbdoreset_during_poweron &&
6764 (orig_cbctl & (CB_C_VCCMASK|CB_C_VPPMASK)) == 0) {
6765 pcic_putb(pcic, socket, PCIC_INTERRUPT, iobits);
6767 return (SUCCESS);
6769 pcic_mswait(pcic, socket, 40);
6771 if (pcic_cbdoreset_during_poweron &&
6772 (orig_cbctl & (CB_C_VCCMASK|CB_C_VPPMASK)) == 0) {
6773 pcic_putb(pcic, socket, PCIC_INTERRUPT, iobits);
6775 cmn_err(CE_WARN,
6776 "pcic socket %d: Power didn't get turned on/off!\n"
6777 "cbstev = 0x%x cbps = 0x%x cbctl 0x%x(0x%x) "
6778 "vcc %d vpp1 %d", socket, cbstev,
6779 pcic_getcb(pcic, CB_PRESENT_STATE),
6780 cbctl, orig_cbctl, sockp->pcs_vcc, sockp->pcs_vpp1);
6781 return (BAD_VCC);
6783 return (SUCCESS);
6786 static int pcic_do_pprintf = 0;
6788 static void
6789 pcic_dump_debqueue(char *msg)
6791 struct debounce *debp = pcic_deb_queue;
6792 clock_t lbolt;
6794 (void) drv_getparm(LBOLT, &lbolt);
6795 pcic_err(NULL, 6, debp ? "pcic debounce list (%s) lbolt 0x%x:\n" :
6796 "pcic debounce_list (%s) EMPTY lbolt 0x%x\n", msg, lbolt);
6797 while (debp) {
6798 pcic_err(NULL, 6, "%p: exp 0x%x next 0x%p id 0x%p\n",
6799 (void *) debp, (int)debp->expire, (void *) debp->next,
6800 debp->pcs->pcs_debounce_id);
6801 debp = debp->next;
6806 /* PRINTFLIKE3 */
6807 static void
6808 pcic_err(dev_info_t *dip, int level, const char *fmt, ...)
6810 if (pcic_debug && (level <= pcic_debug)) {
6811 va_list adx;
6812 int instance;
6813 char buf[256];
6814 const char *name;
6815 #if !defined(PCIC_DEBUG)
6816 int ce;
6817 char qmark = 0;
6819 if (level <= 3)
6820 ce = CE_WARN;
6821 else
6822 ce = CE_CONT;
6823 if (level == 4)
6824 qmark = 1;
6825 #endif
6827 if (dip) {
6828 instance = ddi_get_instance(dip);
6829 /* name = ddi_binding_name(dip); */
6830 name = ddi_driver_name(dip);
6831 } else {
6832 instance = 0;
6833 name = "";
6836 va_start(adx, fmt);
6837 (void) vsprintf(buf, fmt, adx);
6838 va_end(adx);
6840 #if defined(PCIC_DEBUG)
6841 if (pcic_do_pprintf) {
6842 if (dip) {
6843 if (instance >= 0)
6844 prom_printf("%s(%d),0x%p: %s", name,
6845 instance, (void *)dip, buf);
6846 else
6847 prom_printf("%s,0x%p: %s",
6848 name, (void *)dip, buf);
6849 } else
6850 prom_printf(buf);
6851 } else {
6852 if (dip) {
6853 if (instance >= 0)
6854 cmn_err(CE_CONT, "%s(%d),0x%p: %s",
6855 name, instance, (void *) dip, buf);
6856 else
6857 cmn_err(CE_CONT, "%s,0x%p: %s",
6858 name, (void *) dip, buf);
6859 } else
6860 cmn_err(CE_CONT, buf);
6862 #else
6863 if (dip)
6864 cmn_err(ce, qmark ? "?%s%d: %s" : "%s%d: %s", name,
6865 instance, buf);
6866 else
6867 cmn_err(ce, qmark ? "?%s" : buf, buf);
6868 #endif