summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMichael Shalayeff <mickey@cvs.openbsd.org>2006-07-31 11:06:37 +0000
committerMichael Shalayeff <mickey@cvs.openbsd.org>2006-07-31 11:06:37 +0000
commita16dbc750c4b285cb2735adb48fe6a70eda9e335 (patch)
tree7f6e8403646ec0915bd64005bbf88141086ae9a2
parentddc115564e2b438356fee3b26bba010e42273466 (diff)
puc@cardbus (only added (commented out) to whom has puc@pci enabled)
tested on puc@pci by fkr and meself on the cardbus. still needs a bit more work but generally works. deraadt@ ok and some input from miod@
-rw-r--r--sys/arch/amd64/conf/GENERIC5
-rw-r--r--sys/arch/i386/conf/GENERIC3
-rw-r--r--sys/arch/i386/isa/pccom.c6
-rw-r--r--sys/arch/i386/isa/pccomvar.h3
-rw-r--r--sys/arch/macppc/conf/GENERIC3
-rw-r--r--sys/dev/cardbus/cardbus_map.c24
-rw-r--r--sys/dev/cardbus/cardbusvar.h4
-rw-r--r--sys/dev/cardbus/files.cardbus6
-rw-r--r--sys/dev/cardbus/puc_cardbus.c187
-rw-r--r--sys/dev/ic/com_subr.c13
-rw-r--r--sys/dev/ic/comreg.h4
-rw-r--r--sys/dev/ic/comvar.h3
-rw-r--r--sys/dev/pci/files.pci4
-rw-r--r--sys/dev/pci/pci_map.c7
-rw-r--r--sys/dev/pci/pcireg.h7
-rw-r--r--sys/dev/pci/puc.c183
-rw-r--r--sys/dev/pci/pucvar.h48
-rw-r--r--sys/dev/puc/com_puc.c33
-rw-r--r--sys/dev/puc/lpt_puc.c21
19 files changed, 434 insertions, 130 deletions
diff --git a/sys/arch/amd64/conf/GENERIC b/sys/arch/amd64/conf/GENERIC
index 95d2b08970d..78e025830dc 100644
--- a/sys/arch/amd64/conf/GENERIC
+++ b/sys/arch/amd64/conf/GENERIC
@@ -1,4 +1,4 @@
-# $OpenBSD: GENERIC,v 1.146 2006/07/31 10:31:38 jsg Exp $
+# $OpenBSD: GENERIC,v 1.147 2006/07/31 11:06:15 mickey Exp $
#
# For further information on compiling OpenBSD kernels, see the config(8)
# man page.
@@ -191,7 +191,8 @@ radio* at udsbr? # USB radio
ugen* at uhub? # USB Generic driver
ural* at uhub? # Ralink RT2500
-puc* at pci? # PCI "universal" communication device
+puc* at pci? # PCI "universal" communication device
+#puc* at cardbus?
sdhc* at pci? # SD Host Controller
sdmmc* at sdhc? # SD/MMC bus
diff --git a/sys/arch/i386/conf/GENERIC b/sys/arch/i386/conf/GENERIC
index 40a775f676a..eed267481f6 100644
--- a/sys/arch/i386/conf/GENERIC
+++ b/sys/arch/i386/conf/GENERIC
@@ -1,4 +1,4 @@
-# $OpenBSD: GENERIC,v 1.513 2006/07/27 04:18:44 deraadt Exp $
+# $OpenBSD: GENERIC,v 1.514 2006/07/31 11:06:18 mickey Exp $
#
# For further information on compiling OpenBSD kernels, see the config(8)
# man page.
@@ -244,6 +244,7 @@ zyd* at uhub? # Zydas ZD1211
#ueagle* at uhub? # Analog Devices Eagle ADSL
udcf* at uhub? # Gude Expert mouseCLOCK
puc* at pci? # PCI "universal" communication device
+#puc* at cardbus?
sdhc* at pci? # SD Host Controller
sdmmc* at sdhc? # SD/MMC bus
diff --git a/sys/arch/i386/isa/pccom.c b/sys/arch/i386/isa/pccom.c
index 86646255ef7..0aa06e3d260 100644
--- a/sys/arch/i386/isa/pccom.c
+++ b/sys/arch/i386/isa/pccom.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: pccom.c,v 1.53 2006/06/23 06:27:08 miod Exp $ */
+/* $OpenBSD: pccom.c,v 1.54 2006/07/31 11:06:20 mickey Exp $ */
/* $NetBSD: com.c,v 1.82.4.1 1996/06/02 09:08:00 mrg Exp $ */
/*
@@ -557,6 +557,7 @@ comopen(dev, flag, mode, p)
case COM_UART_ST16650:
case COM_UART_ST16650V2:
case COM_UART_XR16850:
+ case COM_UART_OX16C950:
bus_space_write_1(iot, ioh, com_lcr, LCR_EFR);
bus_space_write_1(iot, ioh, com_efr, EFR_ECB);
bus_space_write_1(iot, ioh, com_ier, 0);
@@ -586,6 +587,7 @@ comopen(dev, flag, mode, p)
fifo |= FIFO_RCV_TRIGGER_28|FIFO_XMT_TRIGGER_30;
break;
case COM_UART_XR16850:
+ case COM_UART_OX16C950:
pccom_xr16850_fifo_init(iot, ioh);
if (tp->t_ispeed <= 1200)
fifo |= FIFO_RCV3_TRIGGER_8|FIFO_XMT3_TRIGGER_8; /* XXX */
@@ -766,6 +768,7 @@ compwroff(sc)
case COM_UART_ST16650:
case COM_UART_ST16650V2:
case COM_UART_XR16850:
+ case COM_UART_OX16C950:
bus_space_write_1(iot, ioh, com_lcr, LCR_EFR);
bus_space_write_1(iot, ioh, com_efr, EFR_ECB);
bus_space_write_1(iot, ioh, com_ier, IER_SLEEP);
@@ -1051,6 +1054,7 @@ comparam(tp, t)
fifo |= FIFO_RCV_TRIGGER_28|FIFO_XMT_TRIGGER_30;
break;
case COM_UART_XR16850:
+ case COM_UART_OX16C950:
if (t->c_ispeed <= 1200)
fifo |= FIFO_RCV3_TRIGGER_8|FIFO_XMT3_TRIGGER_8; /* XXX */
else
diff --git a/sys/arch/i386/isa/pccomvar.h b/sys/arch/i386/isa/pccomvar.h
index 367f0e509a2..64a18db08ba 100644
--- a/sys/arch/i386/isa/pccomvar.h
+++ b/sys/arch/i386/isa/pccomvar.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: pccomvar.h,v 1.17 2006/05/28 16:48:18 fkr Exp $ */
+/* $OpenBSD: pccomvar.h,v 1.18 2006/07/31 11:06:20 mickey Exp $ */
/* $NetBSD: comvar.h,v 1.5 1996/05/05 19:50:47 christos Exp $ */
/*
@@ -71,6 +71,7 @@ struct com_softc {
#define COM_UART_ST16650V2 0x06 /* 32 byte fifo */
#define COM_UART_TI16750 0x07 /* 64 byte fifo */
#define COM_UART_XR16850 0x10 /* 128 byte fifo */
+#define COM_UART_OX16C950 0x12 /* 128 byte fifo */
u_char sc_uartrev;
u_char sc_hwflags;
diff --git a/sys/arch/macppc/conf/GENERIC b/sys/arch/macppc/conf/GENERIC
index 494b4965abc..51eff4e90c8 100644
--- a/sys/arch/macppc/conf/GENERIC
+++ b/sys/arch/macppc/conf/GENERIC
@@ -1,4 +1,4 @@
-# $OpenBSD: GENERIC,v 1.145 2006/06/26 22:16:23 miod Exp $g
+# $OpenBSD: GENERIC,v 1.146 2006/07/31 11:06:22 mickey Exp $g
#
# For further information on compiling OpenBSD kernels, see the config(8)
# man page.
@@ -166,6 +166,7 @@ eap* at pci? # Ensoniq AudioPCI S5016
emu* at pci? # SB Live!
puc* at pci? # PCI "universal" comm device
+#puc* at cardbus?
com* at puc?
#scsibus* at adv?
diff --git a/sys/dev/cardbus/cardbus_map.c b/sys/dev/cardbus/cardbus_map.c
index 4352398bf76..0ed9544a834 100644
--- a/sys/dev/cardbus/cardbus_map.c
+++ b/sys/dev/cardbus/cardbus_map.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: cardbus_map.c,v 1.6 2006/06/21 11:27:03 fkr Exp $ */
+/* $OpenBSD: cardbus_map.c,v 1.7 2006/07/31 11:06:27 mickey Exp $ */
/* $NetBSD: cardbus_map.c,v 1.10 2000/03/07 00:31:46 mycroft Exp $ */
/*
@@ -64,6 +64,28 @@ static int cardbus_mem_find(cardbus_chipset_tag_t, cardbus_function_tag_t,
cardbustag_t, int, cardbusreg_t, bus_addr_t *, bus_size_t *,
int *);
+int
+cardbus_mapreg_probe(cardbus_chipset_tag_t cc, cardbus_function_tag_t cf,
+ cardbustag_t tag, int reg, pcireg_t *typep)
+{
+ pcireg_t address, mask;
+ int s;
+
+ s = splhigh();
+ address = cardbus_conf_read(cc, cf, tag, reg);
+ cardbus_conf_write(cc, cf, tag, reg, 0xffffffff);
+ mask = cardbus_conf_read(cc, cf, tag, reg);
+ cardbus_conf_write(cc, cf, tag, reg, address);
+ splx(s);
+
+ if (mask == 0) /* unimplemented mapping register */
+ return (0);
+
+ if (typep)
+ *typep = _PCI_MAPREG_TYPEBITS(address);
+ return (1);
+}
+
/*
* static int cardbus_io_find(cardbus_chipset_tag_t cc,
* cardbus_function_tag_t cf, cardbustag_t tag,
diff --git a/sys/dev/cardbus/cardbusvar.h b/sys/dev/cardbus/cardbusvar.h
index 880402dbf04..b13673a24a3 100644
--- a/sys/dev/cardbus/cardbusvar.h
+++ b/sys/dev/cardbus/cardbusvar.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: cardbusvar.h,v 1.10 2006/06/21 11:27:03 fkr Exp $ */
+/* $OpenBSD: cardbusvar.h,v 1.11 2006/07/31 11:06:27 mickey Exp $ */
/* $NetBSD: cardbusvar.h,v 1.17 2000/04/02 19:11:37 mycroft Exp $ */
/*
@@ -388,6 +388,8 @@ void *cardbus_intr_establish(cardbus_chipset_tag_t, cardbus_function_tag_t,
void cardbus_intr_disestablish(cardbus_chipset_tag_t,
cardbus_function_tag_t, void *handler);
+int cardbus_mapreg_probe(cardbus_chipset_tag_t, cardbus_function_tag_t,
+ cardbustag_t, int, pcireg_t *);
int cardbus_mapreg_map(struct cardbus_softc *, int, int, cardbusreg_t,
int, bus_space_tag_t *, bus_space_handle_t *, bus_addr_t *,
bus_size_t *);
diff --git a/sys/dev/cardbus/files.cardbus b/sys/dev/cardbus/files.cardbus
index 11a125d3ff0..61a7aa8f8fa 100644
--- a/sys/dev/cardbus/files.cardbus
+++ b/sys/dev/cardbus/files.cardbus
@@ -1,4 +1,4 @@
-# $OpenBSD: files.cardbus,v 1.18 2005/05/26 18:57:37 nate Exp $
+# $OpenBSD: files.cardbus,v 1.19 2006/07/31 11:06:27 mickey Exp $
# $NetBSD: files.cardbus,v 1.8 2000/01/26 06:37:24 thorpej Exp $
#
# files.cardbus
@@ -19,6 +19,10 @@ file dev/cardbus/rbus.c cardbus
attach com at cardbus with com_cardbus
file dev/cardbus/com_cardbus.c com_cardbus | pccom_cardbus
+# PCI "universal" communication device driver, for com, lpt, etc. ports
+attach puc at cardbus with puc_cardbus
+file dev/cardbus/puc_cardbus.c puc_cardbus
+
#
# 3Com 3C575TX, 3C575BTX, and 3C575CTX
#
diff --git a/sys/dev/cardbus/puc_cardbus.c b/sys/dev/cardbus/puc_cardbus.c
new file mode 100644
index 00000000000..c56c6224d71
--- /dev/null
+++ b/sys/dev/cardbus/puc_cardbus.c
@@ -0,0 +1,187 @@
+/* $OpenBSD: puc_cardbus.c,v 1.1 2006/07/31 11:06:27 mickey Exp $ */
+
+/*
+ * Copyright (c) 2006 Michael Shalayeff
+ * All rights reserved.
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER IN
+ * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
+ * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include <sys/param.h>
+#include <sys/systm.h>
+#include <sys/device.h>
+#include <sys/tty.h>
+
+#include <machine/bus.h>
+#include <dev/ic/comvar.h>
+
+#include <dev/pci/pcireg.h>
+#include <dev/pci/pcivar.h>
+#include <dev/pci/pcidevs.h>
+#include <dev/cardbus/cardbusvar.h>
+
+#include <dev/pci/pucvar.h>
+
+struct puc_cardbus_softc {
+ struct puc_softc sc_psc;
+
+ struct cardbus_devfunc *ct;
+ int intrline;
+};
+
+int puc_cardbus_match(struct device *, void *, void *);
+void puc_cardbus_attach(struct device *, struct device *, void *);
+int puc_cardbus_detach(struct device *, int);
+
+const char *puc_cardbus_intr_string(struct puc_attach_args *);
+void *puc_cardbus_intr_establish(struct puc_attach_args *, int,
+ int (*)(void *), void *, char *);
+
+struct cfattach puc_cardbus_ca = {
+ sizeof(struct puc_cardbus_softc), puc_cardbus_match,
+ puc_cardbus_attach, puc_cardbus_detach
+};
+
+int
+puc_cardbus_match(struct device *parent, void *match, void *aux)
+{
+ struct cardbus_attach_args *ca = aux;
+ struct cardbus_devfunc *ct = ca->ca_ct;
+ cardbus_chipset_tag_t cc = ct->ct_cc;
+ cardbus_function_tag_t cf = ct->ct_cf;
+ cardbusreg_t bhlc, reg;
+
+ bhlc = cardbus_conf_read(cc, cf, ca->ca_tag, CARDBUS_BHLC_REG);
+ if (PCI_HDRTYPE_TYPE(bhlc) != 0)
+ return(0);
+
+ /* this one is some sort of a bridge and not a puc */
+ if (PCI_VENDOR(ca->ca_id) == PCI_VENDOR_OXFORD2 &&
+ PCI_PRODUCT(ca->ca_id) == PCI_PRODUCT_OXFORD2_EXSYS_EX41098)
+ return (0);
+
+ reg = cardbus_conf_read(cc, cf, ca->ca_tag, PCI_SUBSYS_ID_REG);
+ if (puc_find_description(PCI_VENDOR(ca->ca_id),
+ PCI_PRODUCT(ca->ca_id), PCI_VENDOR(reg), PCI_PRODUCT(reg)))
+ return (10);
+
+ return (0);
+}
+
+void
+puc_cardbus_attach(struct device *parent, struct device *self, void *aux)
+{
+ struct puc_cardbus_softc *csc = (struct puc_cardbus_softc *)self;
+ struct puc_softc *sc = &csc->sc_psc;
+ struct cardbus_attach_args *ca = aux;
+ struct cardbus_devfunc *ct = ca->ca_ct;
+ cardbus_chipset_tag_t cc = ct->ct_cc;
+ cardbus_function_tag_t cf = ct->ct_cf;
+ struct puc_attach_args paa;
+ cardbusreg_t reg;
+ int i;
+
+ Cardbus_function_enable(ct);
+
+ csc->ct = ct;
+
+ reg = cardbus_conf_read(cc, cf, ca->ca_tag, PCI_SUBSYS_ID_REG);
+ sc->sc_desc = puc_find_description(PCI_VENDOR(ca->ca_id),
+ PCI_PRODUCT(ca->ca_id), PCI_VENDOR(reg), PCI_PRODUCT(reg));
+
+ puc_print_ports(sc->sc_desc);
+
+ /* the fifth one is some memory we dunno */
+ for (i = 0; i < PUC_NBARS; i++) {
+ cardbusreg_t type;
+ int bar;
+
+ sc->sc_bar_mappings[i].mapped = 0;
+ bar = PCI_MAPREG_START + 4 * i;
+ if (!cardbus_mapreg_probe(cc, cf, ca->ca_tag, bar, &type))
+ continue;
+
+ if (!(sc->sc_bar_mappings[i].mapped = !Cardbus_mapreg_map(ct,
+ bar, type, 0,
+ &sc->sc_bar_mappings[i].t, &sc->sc_bar_mappings[i].h,
+ &sc->sc_bar_mappings[i].a, &sc->sc_bar_mappings[i].s)))
+ printf("%s: couldn't map BAR at offset 0x%lx\n",
+ sc->sc_dev.dv_xname, (long)bar);
+ sc->sc_bar_mappings[i].type = type;
+ }
+
+ csc->intrline = ca->ca_intrline;
+
+ if (cardbus_get_capability(cc, cf, ca->ca_tag, PCI_CAP_PWRMGMT, &reg,
+ 0)) {
+ reg = cardbus_conf_read(cc, cf, ca->ca_tag, reg + 4) & 3;
+ if (reg) {
+ printf("%s: awakening from state D%d\n",
+ sc->sc_dev.dv_xname, reg);
+ cardbus_conf_write(cc, cf, ca->ca_tag, reg + 4, 0);
+ }
+ }
+
+ (*cf->cardbus_ctrl)(cc, CARDBUS_MEM_ENABLE);
+ (*cf->cardbus_ctrl)(cc, CARDBUS_IO_ENABLE);
+ (*cf->cardbus_ctrl)(cc, CARDBUS_BM_ENABLE);
+
+ paa.puc = sc;
+ paa.hwtype = COM_UART_OX16C950; /* XXX */
+ paa.intr_string = &puc_cardbus_intr_string;
+ paa.intr_establish = &puc_cardbus_intr_establish;
+ puc_common_attach(sc, &paa);
+}
+
+const char *
+puc_cardbus_intr_string(struct puc_attach_args *paa)
+{
+ struct puc_cardbus_softc *sc = paa->puc;
+ static char str[16];
+
+ snprintf(str, sizeof str, "irq %d", sc->intrline);
+ return (str);
+}
+
+void *
+puc_cardbus_intr_establish(struct puc_attach_args *paa, int type,
+ int (*func)(void *), void *arg, char *name)
+{
+ struct puc_cardbus_softc *sc = paa->puc;
+ struct cardbus_devfunc *ct = sc->ct;
+
+ return (cardbus_intr_establish(ct->ct_cc, ct->ct_cf, sc->intrline,
+ type, func, arg));
+}
+
+int
+puc_cardbus_detach(struct device *self, int flags)
+{
+ struct puc_cardbus_softc *csc = (struct puc_cardbus_softc *)self;
+ struct puc_softc *sc = &csc->sc_psc;
+ struct cardbus_devfunc *ct = csc->ct;
+ int i, rv;
+
+ for (i = PUC_MAX_PORTS; i--; )
+ if (sc->sc_ports[i].dev)
+ if ((rv = config_detach(sc->sc_ports[i].dev, flags)))
+ return (rv);
+
+ for (i = PUC_NBARS; i--; )
+ if (sc->sc_bar_mappings[i].mapped)
+ Cardbus_mapreg_unmap(ct, sc->sc_bar_mappings[i].type,
+ sc->sc_bar_mappings[i].t, sc->sc_bar_mappings[i].h,
+ sc->sc_bar_mappings[i].s);
+
+ return (0);
+}
diff --git a/sys/dev/ic/com_subr.c b/sys/dev/ic/com_subr.c
index a7036adf2ed..15e2156f560 100644
--- a/sys/dev/ic/com_subr.c
+++ b/sys/dev/ic/com_subr.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: com_subr.c,v 1.6 2006/05/30 21:31:57 fkr Exp $ */
+/* $OpenBSD: com_subr.c,v 1.7 2006/07/31 11:06:30 mickey Exp $ */
/*
* Copyright (c) 1997 - 1999, Jason Downs. All rights reserved.
@@ -173,6 +173,10 @@ com_attach_subr(sc)
/* Attachment driver presets COM_UART_PXA2X0. */
if (sc->sc_uarttype != COM_UART_PXA2X0)
#endif
+#ifdef COM_UART_OX16C950
+ /* Attachment driver presets COM_UART_OX16C950. */
+ if (sc->sc_uarttype != COM_UART_OX16C950)
+#endif
switch(bus_space_read_1(iot, ioh, com_iir) >> 6) {
case 0:
sc->sc_uarttype = COM_UART_16450;
@@ -307,6 +311,13 @@ com_attach_subr(sc)
SET(sc->sc_hwflags, COM_HW_FIFO);
sc->sc_fifolen = 128;
break;
+#ifdef COM_UART_OX16C950
+ case COM_UART_OX16C950:
+ printf(": ox16c950 (rev %d), 128 byte fifo\n", sc->sc_uartrev);
+ SET(sc->sc_hwflags, COM_HW_FIFO);
+ sc->sc_fifolen = 128;
+ break;
+#endif
#endif
default:
panic("comattach: bad fifo type");
diff --git a/sys/dev/ic/comreg.h b/sys/dev/ic/comreg.h
index 88e86567539..8c2c9841db0 100644
--- a/sys/dev/ic/comreg.h
+++ b/sys/dev/ic/comreg.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: comreg.h,v 1.14 2005/07/03 19:46:45 deraadt Exp $ */
+/* $OpenBSD: comreg.h,v 1.15 2006/07/31 11:06:30 mickey Exp $ */
/* $NetBSD: comreg.h,v 1.8 1996/02/05 23:01:50 scottr Exp $ */
/*
@@ -127,7 +127,7 @@
#define LCR_7BITS 0x02 /* 7 bits */
#define LCR_6BITS 0x01 /* 6 bits */
#define LCR_5BITS 0x00 /* 5 bits */
-#define LCR_EFR 0xbf /* ST16650/XR16850 EFR access enable */
+#define LCR_EFR 0xbf /* ST16650/XR16850/OX16C950 EFR access enable */
/* modem control register */
#define MCR_AFE 0x20 /* auto flow control */
diff --git a/sys/dev/ic/comvar.h b/sys/dev/ic/comvar.h
index 7ee7cb7d7cc..1a04a40c114 100644
--- a/sys/dev/ic/comvar.h
+++ b/sys/dev/ic/comvar.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: comvar.h,v 1.38 2006/03/27 06:14:52 deraadt Exp $ */
+/* $OpenBSD: comvar.h,v 1.39 2006/07/31 11:06:30 mickey Exp $ */
/* $NetBSD: comvar.h,v 1.5 1996/05/05 19:50:47 christos Exp $ */
/*
@@ -104,6 +104,7 @@ struct com_softc {
#define COM_UART_TI16750 0x07 /* 64 byte fifo */
#define COM_UART_XR16850 0x10 /* 128 byte fifo */
#define COM_UART_PXA2X0 0x11 /* 16 byte fifo */
+#define COM_UART_OX16C950 0x12 /* 128 byte fifo */
u_char sc_hwflags;
#define COM_HW_NOIEN 0x01
diff --git a/sys/dev/pci/files.pci b/sys/dev/pci/files.pci
index eebbda8ce90..9169b4a29b5 100644
--- a/sys/dev/pci/files.pci
+++ b/sys/dev/pci/files.pci
@@ -1,4 +1,4 @@
-# $OpenBSD: files.pci,v 1.212 2006/07/31 10:03:22 dlg Exp $
+# $OpenBSD: files.pci,v 1.213 2006/07/31 11:06:33 mickey Exp $
# $NetBSD: files.pci,v 1.20 1996/09/24 17:47:15 christos Exp $
#
# Config file and device description for machine-independent PCI code.
@@ -440,7 +440,7 @@ file dev/pci/if_sk.c skc | sk
# PCI "universal" communication device driver, for PCI com, lpt, etc. ports
# (see documentation in the driver for what, exactly, should be supported)
device puc {[port = -1]}
-attach puc at pci
+attach puc at pci with puc_pci
file dev/pci/puc.c puc
file dev/pci/pucdata.c puc
diff --git a/sys/dev/pci/pci_map.c b/sys/dev/pci/pci_map.c
index c95487360bf..c652ebfbf60 100644
--- a/sys/dev/pci/pci_map.c
+++ b/sys/dev/pci/pci_map.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: pci_map.c,v 1.17 2006/07/04 18:07:29 kettenis Exp $ */
+/* $OpenBSD: pci_map.c,v 1.18 2006/07/31 11:06:33 mickey Exp $ */
/* $NetBSD: pci_map.c,v 1.7 2000/05/10 16:58:42 thorpej Exp $ */
/*-
@@ -252,11 +252,6 @@ pci_mem_find(pci_chipset_tag_t pc, pcitag_t pcitag, int reg,
cacheablep));
}
-#define _PCI_MAPREG_TYPEBITS(reg) \
- (PCI_MAPREG_TYPE(reg) == PCI_MAPREG_TYPE_IO ? \
- reg & PCI_MAPREG_TYPE_MASK : \
- reg & (PCI_MAPREG_TYPE_MASK|PCI_MAPREG_MEM_TYPE_MASK))
-
pcireg_t
pci_mapreg_type(pci_chipset_tag_t pc, pcitag_t tag, int reg)
{
diff --git a/sys/dev/pci/pcireg.h b/sys/dev/pci/pcireg.h
index b52fe16d20e..a4a5b4ab8e5 100644
--- a/sys/dev/pci/pcireg.h
+++ b/sys/dev/pci/pcireg.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: pcireg.h,v 1.31 2006/06/01 11:17:31 brad Exp $ */
+/* $OpenBSD: pcireg.h,v 1.32 2006/07/31 11:06:33 mickey Exp $ */
/* $NetBSD: pcireg.h,v 1.26 2000/05/10 16:58:42 thorpej Exp $ */
/*
@@ -406,6 +406,11 @@ typedef u_int8_t pci_revision_t;
#define PCI_MAPREG_MEM_TYPE_32BIT_1M 0x00000002
#define PCI_MAPREG_MEM_TYPE_64BIT 0x00000004
+#define _PCI_MAPREG_TYPEBITS(reg) \
+ (PCI_MAPREG_TYPE(reg) == PCI_MAPREG_TYPE_IO ? \
+ reg & PCI_MAPREG_TYPE_MASK : \
+ reg & (PCI_MAPREG_TYPE_MASK|PCI_MAPREG_MEM_TYPE_MASK))
+
#define PCI_MAPREG_MEM_PREFETCHABLE(mr) \
(((mr) & PCI_MAPREG_MEM_PREFETCHABLE_MASK) != 0)
#define PCI_MAPREG_MEM_PREFETCHABLE_MASK 0x00000008
diff --git a/sys/dev/pci/puc.c b/sys/dev/pci/puc.c
index e36da14241e..78454d47abe 100644
--- a/sys/dev/pci/puc.c
+++ b/sys/dev/pci/puc.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: puc.c,v 1.8 2003/02/28 15:14:08 mickey Exp $ */
+/* $OpenBSD: puc.c,v 1.9 2006/07/31 11:06:33 mickey Exp $ */
/* $NetBSD: puc.c,v 1.3 1999/02/06 06:29:54 cgd Exp $ */
/*
@@ -61,52 +61,31 @@
#include <dev/pci/pcivar.h>
#include <dev/pci/pucvar.h>
-struct puc_softc {
- struct device sc_dev;
-
- /* static configuration data */
- const struct puc_device_description *sc_desc;
-
- /* card-global dynamic data */
- void *sc_ih;
- struct {
- int mapped;
- bus_addr_t a;
- bus_size_t s;
- bus_space_tag_t t;
- bus_space_handle_t h;
- } sc_bar_mappings[6]; /* XXX constant */
-
- /* per-port dynamic data */
- struct {
- struct device *dev;
-
- /* filled in by port attachments */
- int (*ihand)(void *);
- void *ihandarg;
- } sc_ports[PUC_MAX_PORTS];
+struct puc_pci_softc {
+ struct puc_softc sc_psc;
+
+ pci_chipset_tag_t pc;
+ pci_intr_handle_t ih;
};
-int puc_match(struct device *, void *, void *);
-void puc_attach(struct device *, struct device *, void *);
-int puc_print(void *, const char *);
-int puc_submatch(struct device *, void *, void *);
+int puc_pci_match(struct device *, void *, void *);
+void puc_pci_attach(struct device *, struct device *, void *);
+const char *puc_pci_intr_string(struct puc_attach_args *);
+void *puc_pci_intr_establish(struct puc_attach_args *, int,
+ int (*)(void *), void *, char *);
-struct cfattach puc_ca = {
- sizeof(struct puc_softc), puc_match, puc_attach
+struct cfattach puc_pci_ca = {
+ sizeof(struct puc_pci_softc), puc_pci_match, puc_pci_attach
};
struct cfdriver puc_cd = {
NULL, "puc", DV_DULL
};
-static const struct puc_device_description *
- puc_find_description(pcireg_t, pcireg_t, pcireg_t, pcireg_t);
-static const char *
- puc_port_type_name(int);
+const char *puc_port_type_name(int);
int
-puc_match(parent, match, aux)
+puc_pci_match(parent, match, aux)
struct device *parent;
void *match, *aux;
{
@@ -136,17 +115,34 @@ puc_match(parent, match, aux)
return (0);
}
+const char *
+puc_pci_intr_string(struct puc_attach_args *paa)
+{
+ struct puc_pci_softc *sc = paa->puc;
+
+ return (pci_intr_string(sc->pc, sc->ih));
+}
+
+void *
+puc_pci_intr_establish(struct puc_attach_args *paa, int type,
+ int (*func)(void *), void *arg, char *name)
+{
+ struct puc_pci_softc *sc = paa->puc;
+
+ return (pci_intr_establish(sc->pc, sc->ih, type, func, arg, name));
+}
+
void
-puc_attach(parent, self, aux)
+puc_pci_attach(parent, self, aux)
struct device *parent, *self;
void *aux;
{
- struct puc_softc *sc = (struct puc_softc *)self;
+ struct puc_pci_softc *psc = (struct puc_pci_softc *)self;
+ struct puc_softc *sc = &psc->sc_psc;
struct pci_attach_args *pa = aux;
struct puc_attach_args paa;
- pci_intr_handle_t intrhandle;
pcireg_t subsys;
- int i, barindex;
+ int i;
subsys = pci_conf_read(pa->pa_pc, pa->pa_tag, PCI_SUBSYS_ID_REG);
sc->sc_desc = puc_find_description(PCI_VENDOR(pa->pa_id),
@@ -171,11 +167,7 @@ puc_attach(parent, self, aux)
return;
}
- printf(": ");
- for (i = 0; PUC_PORT_VALID(sc->sc_desc, i); i++)
- printf("%s%s", i ? ", " : "",
- puc_port_type_name(sc->sc_desc->ports[i].type));
- printf("\n");
+ puc_print_ports(sc->sc_desc);
/*
* XXX This driver assumes that 'com' ports attached to it
@@ -190,35 +182,46 @@ puc_attach(parent, self, aux)
* XXX definition of PCI/communications/serial, and attach 'com'
* XXX directly on PCI.
*/
- for (i = 0; i < 6; i++) {
- pcireg_t bar, type;
+ for (i = 0; i < PUC_NBARS; i++) {
+ pcireg_t type;
+ int bar;
sc->sc_bar_mappings[i].mapped = 0;
-
- bar = pci_conf_read(pa->pa_pc, pa->pa_tag,
- PCI_MAPREG_START + 4 * i); /* XXX const */
- if (bar == 0) /* BAR not implemented(?) */
+ bar = PCI_MAPREG_START + 4 * i;
+ if (!pci_mapreg_probe(pa->pa_pc, pa->pa_tag, bar, &type))
continue;
- type = (PCI_MAPREG_TYPE(bar) == PCI_MAPREG_TYPE_IO ?
- PCI_MAPREG_TYPE_IO : PCI_MAPREG_MEM_TYPE(bar));
- sc->sc_bar_mappings[i].mapped = (pci_mapreg_map(pa,
- PCI_MAPREG_START + 4 * i, type, 0,
- &sc->sc_bar_mappings[i].t, &sc->sc_bar_mappings[i].h,
+ sc->sc_bar_mappings[i].mapped = (pci_mapreg_map(pa, bar, type,
+ 0, &sc->sc_bar_mappings[i].t, &sc->sc_bar_mappings[i].h,
&sc->sc_bar_mappings[i].a, &sc->sc_bar_mappings[i].s, 0)
== 0);
+ sc->sc_bar_mappings[i].type = type;
if (sc->sc_bar_mappings[i].mapped)
continue;
printf("%s: couldn't map BAR at offset 0x%lx\n",
- sc->sc_dev.dv_xname, (long)(PCI_MAPREG_START + 4 * i));
+ sc->sc_dev.dv_xname, (long)bar);
}
/* Map interrupt. */
- if (pci_intr_map(pa, &intrhandle)) {
+ psc->pc = pa->pa_pc;
+ if (pci_intr_map(pa, &psc->ih)) {
printf("%s: couldn't map interrupt\n", sc->sc_dev.dv_xname);
return;
}
+
+ paa.puc = sc;
+ paa.hwtype = 0; /* autodetect */
+ paa.intr_string = &puc_pci_intr_string;
+ paa.intr_establish = &puc_pci_intr_establish;
+ puc_common_attach(sc, &paa);
+}
+
+void
+puc_common_attach(struct puc_softc *sc, struct puc_attach_args *paa)
+{
+ int i, bar;
+
/*
* XXX the sub-devices establish the interrupts, for the
* XXX following reasons:
@@ -237,11 +240,9 @@ puc_attach(parent, self, aux)
/* Configure each port. */
for (i = 0; PUC_PORT_VALID(sc->sc_desc, i); i++) {
- bus_space_handle_t subregion_handle;
-
/* make sure the base address register is mapped */
- barindex = PUC_PORT_BAR_INDEX(sc->sc_desc->ports[i].bar);
- if (!sc->sc_bar_mappings[barindex].mapped) {
+ bar = PUC_PORT_BAR_INDEX(sc->sc_desc->ports[i].bar);
+ if (!sc->sc_bar_mappings[bar].mapped) {
printf("%s: %s port uses unmapped BAR (0x%x)\n",
sc->sc_dev.dv_xname,
puc_port_type_name(sc->sc_desc->ports[i].type),
@@ -250,36 +251,32 @@ puc_attach(parent, self, aux)
}
/* set up to configure the child device */
- paa.port = i;
- paa.type = sc->sc_desc->ports[i].type;
- paa.flags = sc->sc_desc->ports[i].flags;
- paa.pc = pa->pa_pc;
- paa.intrhandle = intrhandle;
- paa.a = sc->sc_bar_mappings[barindex].a;
- paa.t = sc->sc_bar_mappings[barindex].t;
-
- if (bus_space_subregion(sc->sc_bar_mappings[barindex].t,
- sc->sc_bar_mappings[barindex].h,
- sc->sc_desc->ports[i].offset,
- sc->sc_bar_mappings[barindex].s -
- sc->sc_desc->ports[i].offset,
- &subregion_handle)) {
+ paa->port = i;
+ paa->type = sc->sc_desc->ports[i].type;
+ paa->flags = sc->sc_desc->ports[i].flags;
+ paa->a = sc->sc_bar_mappings[bar].a;
+ paa->t = sc->sc_bar_mappings[bar].t;
+
+ if (bus_space_subregion(sc->sc_bar_mappings[bar].t,
+ sc->sc_bar_mappings[bar].h, sc->sc_desc->ports[i].offset,
+ sc->sc_bar_mappings[bar].s - sc->sc_desc->ports[i].offset,
+ &paa->h)) {
printf("%s: couldn't get subregion for port %d\n",
sc->sc_dev.dv_xname, i);
continue;
}
- paa.h = subregion_handle;
-#if 0
- printf("%s: port %d: %s @ (index %d) 0x%x (0x%lx, 0x%lx)\n",
- sc->sc_dev.dv_xname, paa.port,
- puc_port_type_name(paa.type), barindex, (int)paa.a,
- (long)paa.t, (long)paa.h);
+#ifndef SMALL_KERNEL
+ if (autoconf_verbose)
+ printf("%s: port %d: %s @ (index %d) 0x%x "
+ "(0x%lx, 0x%lx)\n", sc->sc_dev.dv_xname, paa->port,
+ puc_port_type_name(paa->type), bar, (int)paa->a,
+ (long)paa->t, (long)paa->h);
#endif
/* and configure it */
- sc->sc_ports[i].dev = config_found_sm(self, &paa, puc_print,
- puc_submatch);
+ sc->sc_ports[i].dev = config_found_sm(&sc->sc_dev, paa,
+ puc_print, puc_submatch);
}
}
@@ -309,9 +306,9 @@ puc_submatch(parent, vcf, aux)
return ((*cf->cf_attach->ca_match)(parent, cf, aux));
}
-static const struct puc_device_description *
+const struct puc_device_description *
puc_find_description(vend, prod, svend, sprod)
- pcireg_t vend, prod, svend, sprod;
+ u_long vend, prod, svend, sprod;
{
int i;
@@ -335,7 +332,7 @@ puc_find_description(vend, prod, svend, sprod)
return (NULL);
}
-static const char *
+const char *
puc_port_type_name(type)
int type;
{
@@ -349,3 +346,15 @@ puc_port_type_name(type)
panic("puc_port_type_name %d", type);
}
}
+
+void
+puc_print_ports(const struct puc_device_description *desc)
+{
+ int i;
+
+ printf(": ");
+ for (i = 0; PUC_PORT_VALID(desc, i); i++)
+ printf("%s%s", i ? ", " : "",
+ puc_port_type_name(desc->ports[i].type));
+ printf("\n");
+}
diff --git a/sys/dev/pci/pucvar.h b/sys/dev/pci/pucvar.h
index fcfc550ea11..12fc9f11f85 100644
--- a/sys/dev/pci/pucvar.h
+++ b/sys/dev/pci/pucvar.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: pucvar.h,v 1.4 2002/02/17 19:24:38 deraadt Exp $ */
+/* $OpenBSD: pucvar.h,v 1.5 2006/07/31 11:06:33 mickey Exp $ */
/* $NetBSD: pucvar.h,v 1.2 1999/02/06 06:29:54 cgd Exp $ */
/*
@@ -41,8 +41,8 @@
#define PUC_MAX_PORTS 8
struct puc_device_description {
- pcireg_t rval[4];
- pcireg_t rmask[4];
+ u_long rval[4];
+ u_long rmask[4];
struct {
u_char type;
u_char bar;
@@ -71,14 +71,50 @@ struct puc_device_description {
struct puc_attach_args {
int port;
int type;
-
- pci_chipset_tag_t pc;
- pci_intr_handle_t intrhandle;
+ int hwtype;
+ void *puc;
bus_addr_t a;
bus_space_tag_t t;
bus_space_handle_t h;
int flags;
+
+ const char *(*intr_string)(struct puc_attach_args *);
+ void *(*intr_establish)(struct puc_attach_args *, int, int (*)(void *),
+ void *, char *);
};
extern const struct puc_device_description puc_devices[];
+
+#define PUC_NBARS 6
+struct puc_softc {
+ struct device sc_dev;
+
+ /* static configuration data */
+ const struct puc_device_description *sc_desc;
+
+ /* card-global dynamic data */
+ struct {
+ int mapped;
+ u_long type;
+ bus_addr_t a;
+ bus_size_t s;
+ bus_space_tag_t t;
+ bus_space_handle_t h;
+ } sc_bar_mappings[PUC_NBARS];
+
+ /* per-port dynamic data */
+ struct {
+ struct device *dev;
+ /* filled in by port attachments */
+ int (*ihand)(void *);
+ void *ihandarg;
+ } sc_ports[PUC_MAX_PORTS];
+};
+
+const struct puc_device_description *
+ puc_find_description(u_long, u_long, u_long, u_long);
+void puc_print_ports(const struct puc_device_description *);
+void puc_common_attach(struct puc_softc *, struct puc_attach_args *);
+int puc_print(void *, const char *);
+int puc_submatch(struct device *, void *, void *);
diff --git a/sys/dev/puc/com_puc.c b/sys/dev/puc/com_puc.c
index bf6c0078a01..fe4e98318b5 100644
--- a/sys/dev/puc/com_puc.c
+++ b/sys/dev/puc/com_puc.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: com_puc.c,v 1.12 2006/06/01 01:28:40 fkr Exp $ */
+/* $OpenBSD: com_puc.c,v 1.13 2006/07/31 11:06:36 mickey Exp $ */
/*
* Copyright (c) 1997 - 1999, Jason Downs. All rights reserved.
@@ -40,13 +40,11 @@
#include <sys/uio.h>
#include <sys/kernel.h>
#include <sys/syslog.h>
-#include <sys/types.h>
#include <sys/device.h>
#include <machine/intr.h>
#include <machine/bus.h>
-#include <dev/pci/pcivar.h>
#include <dev/pci/pucvar.h>
#include "com.h"
@@ -67,16 +65,17 @@
int com_puc_match(struct device *, void *, void *);
void com_puc_attach(struct device *, struct device *, void *);
+int com_puc_detach(struct device *, int );
#if NCOM > 0
struct cfattach com_puc_ca = {
- sizeof(struct com_softc), com_puc_match, com_puc_attach
+ sizeof(struct com_softc), com_puc_match, com_puc_attach, com_puc_detach
};
#endif
#if NPCCOM > 0
struct cfattach pccom_puc_ca = {
- sizeof(struct com_softc), com_puc_match, com_puc_attach
+ sizeof(struct com_softc), com_puc_match, com_puc_attach, com_puc_detach
};
#endif
@@ -103,10 +102,9 @@ com_puc_attach(parent, self, aux)
const char *intrstr;
/* Grab a PCI interrupt. */
- intrstr = pci_intr_string(pa->pc, pa->intrhandle);
- sc->sc_ih = pci_intr_establish(pa->pc, pa->intrhandle,
- IPL_TTY, comintr, sc,
- sc->sc_dev.dv_xname);
+ intrstr = pa->intr_string(pa);
+ sc->sc_ih = pa->intr_establish(pa, IPL_TTY, comintr, sc,
+ sc->sc_dev.dv_xname);
if (sc->sc_ih == NULL) {
printf(": couldn't establish interrupt");
if (intrstr != NULL)
@@ -123,9 +121,26 @@ com_puc_attach(parent, self, aux)
if (pa->flags)
sc->sc_frequency = pa->flags & PUC_COM_CLOCKMASK;
+printf(" %x ", pa->hwtype);
+ if (pa->hwtype)
+ sc->sc_uarttype = pa->hwtype;
sc->sc_hwflags = 0;
sc->sc_swflags = 0;
com_attach_subr(sc);
}
+
+int
+com_puc_detach(struct device *self, int flags)
+{
+ /* struct com_softc *sc = (void *)self; */
+ int error;
+
+ if ((error = com_detach(self, flags)) != 0)
+ return (error);
+
+ /* cardbus_intr_disestablish(psc->sc_cc, psc->sc_cf, csc->cc_ih); */
+
+ return (0);
+}
diff --git a/sys/dev/puc/lpt_puc.c b/sys/dev/puc/lpt_puc.c
index 4f375d3c513..9b8d8576ee1 100644
--- a/sys/dev/puc/lpt_puc.c
+++ b/sys/dev/puc/lpt_puc.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: lpt_puc.c,v 1.3 2002/03/14 01:27:01 millert Exp $ */
+/* $OpenBSD: lpt_puc.c,v 1.4 2006/07/31 11:06:36 mickey Exp $ */
/* $NetBSD: lpt_puc.c,v 1.1 1998/06/26 18:52:41 cgd Exp $ */
/*
@@ -45,16 +45,16 @@
#include <machine/bus.h>
-#include <dev/pci/pcivar.h>
#include <dev/pci/pucvar.h>
#include <dev/ic/lptreg.h>
#include <dev/ic/lptvar.h>
int lpt_puc_probe(struct device *, void *, void *);
void lpt_puc_attach(struct device *, struct device *, void *);
+int lpt_puc_detach(struct device *, int);
struct cfattach lpt_puc_ca = {
- sizeof(struct lpt_softc), lpt_puc_probe, lpt_puc_attach
+ sizeof(struct lpt_softc), lpt_puc_probe, lpt_puc_attach, lpt_puc_detach
};
int
@@ -85,9 +85,9 @@ lpt_puc_attach(parent, self, aux)
sc->sc_iot = aa->t;
sc->sc_ioh = aa->h;
- intrstr = pci_intr_string(aa->pc, aa->intrhandle);
- sc->sc_ih = pci_intr_establish(aa->pc, aa->intrhandle, IPL_TTY,
- lptintr, sc, sc->sc_dev.dv_xname);
+ intrstr = aa->intr_string(aa);
+ sc->sc_ih = aa->intr_establish(aa, IPL_TTY, lptintr, sc,
+ sc->sc_dev.dv_xname);
if (sc->sc_ih == NULL) {
printf(": couldn't establish interrupt");
if (intrstr != NULL)
@@ -101,3 +101,12 @@ lpt_puc_attach(parent, self, aux)
lpt_attach_common(sc);
}
+
+int
+lpt_puc_detach(struct device *self, int flags)
+{
+
+ /* cardbus_intr_disestablish(psc->sc_cc, psc->sc_cf, csc->cc_ih); */
+
+ return (0);
+}