diff --git a/sys/arch/i386/conf/files.i386 b/sys/arch/i386/conf/files.i386 index 7f3533570ab0..a968d3f87699 100644 --- a/sys/arch/i386/conf/files.i386 +++ b/sys/arch/i386/conf/files.i386 @@ -1,4 +1,4 @@ -# $NetBSD: files.i386,v 1.189 2001/07/14 02:18:02 christos Exp $ +# $NetBSD: files.i386,v 1.190 2001/08/27 08:21:20 haya Exp $ # # new style config file for i386 architecture # @@ -150,6 +150,7 @@ file arch/i386/pci/opti82c700.c pcibios & pcibios_intr_fixup file arch/i386/pci/sis85c503.c pcibios & pcibios_intr_fixup file arch/i386/pci/via82c586.c pcibios & pcibios_intr_fixup file arch/i386/pci/amd756.c pcibios & pcibios_intr_fixup +file arch/i386/pci/ali1543.c pcibios & pcibios_intr_fixup file arch/i386/pci/pci_bus_fixup.c pcibios & pcibios_bus_fixup file arch/i386/pci/pci_addr_fixup.c pcibios & pcibios_addr_fixup defopt PCI_CONF_MODE diff --git a/sys/arch/i386/pci/ali1543.c b/sys/arch/i386/pci/ali1543.c new file mode 100644 index 000000000000..2793cf96b11c --- /dev/null +++ b/sys/arch/i386/pci/ali1543.c @@ -0,0 +1,328 @@ +/* $NetBSD: ali1543.c,v 1.1 2001/08/27 08:21:21 haya Exp $ */ + +/* + * Copyright (c) 2001 + * HAYAKAWA Koichi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +/*- + * Copyright (c) 1999 The NetBSD Foundation, Inc. + * All rights reserved. + * + * This code is derived from software contributed to The NetBSD Foundation + * by Jason R. Thorpe of the Numerical Aerospace Simulation Facility, + * NASA Ames Research Center. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by the NetBSD + * Foundation, Inc. and its contributors. + * 4. Neither the name of The NetBSD Foundation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS + * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED + * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +/* + * Copyright (c) 1999, by UCHIYAMA Yasushi + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. The name of the developer may NOT be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +/* HAYAKAWA Koichi wrote ALi 1543 PCI ICU code basing on VIA82C586 driver */ + +#include +#include +#include +#include +#include +#include + +#include +#include + +#include +#include +#include + +#include +#include + + +int ali1543_getclink (pciintr_icu_handle_t, int, int *); +int ali1543_get_intr (pciintr_icu_handle_t, int, int *); +int ali1543_set_intr (pciintr_icu_handle_t, int, int); +int ali1543_get_trigger (pciintr_icu_handle_t, int, int *); +int ali1543_set_trigger (pciintr_icu_handle_t, int, int); + + +const struct pciintr_icu ali1543_icu = { + ali1543_getclink, + ali1543_get_intr, + ali1543_set_intr, + ali1543_get_trigger, + ali1543_set_trigger, +}; + + +/* + * Linux source code (linux/arch/i386/kernel/pci-irq.c) says that the + * irq order of ALi PCI ICU is shuffled. + */ +const static int ali1543_intr_shuffle_get[16] = { + 0, 9, 3, 10, 4, 5, 7, 6, 1, 11, 0, 12, 0, 14, 0, 15 +}; +const static int ali1543_intr_shuffle_set[16] = { + 0, 8, 0, 2, 4, 5, 7, 6, 0, 1, 3, 9, 11, 0, 13, 15 +}; + +#define ALI1543_IRQ_MASK 0xdefa + +#define ALI1543_LEGAL_LINK(link) (((link) >= 0) && ((link) <= 7)) +#define ALI1543_LEGAL_IRQ(irq) ((1 << (irq)) & ALI1543_IRQ_MASK) + +#define ALI1543_INTR_CFG_REG 0x48 +#define ALI1543_INTR_TRIG_REG 0x4c + +#define ALI1543_INTR_PIRQA_SHIFT 0 +#define ALI1543_INTR_PIRQA_MASK 0x0000000f +#define ALI1543_INTR_PIRQB_SHIFT 4 +#define ALI1543_INTR_PIRQB_MASK 0x000000f0 +#define ALI1543_INTR_PIRQC_SHIFT 8 +#define ALI1543_INTR_PIRQC_MASK 0x00000f00 +#define ALI1543_INTR_PIRQD_SHIFT 12 +#define ALI1543_INTR_PIRQD_MASK 0x0000f000 + +#define ALI1543_INTR_PIRQ_SHIFT(clink) ((clink)*4) +#define ALI1543_INTR_PIRQ_IRQ(reg, clink) \ + (((reg) >> ((clink)*4)) & 0x0f) +#define ALI1543_PIRQ(reg, clink) \ + ali1543_intr_shuffle_get[ALI1543_INTR_PIRQ_IRQ((reg), (clink))] + +#define ALI1543_INTR_TRIG_MASK 0x000000ff +#define ALI1543_INTR_TRIG_LEVEL 0 +#define ALI1543_INTR_TRIG_EDGE 1 +#define ALI1543_INTR_TRIG_GET(reg, link) \ + (((reg) >> (link)) & 0x01) +#define ALI1543_INTR_TRIG_SET(reg, link, val) \ + do { \ + (reg) &= ~(1 << (link)); \ + (reg) |= (((val) & 0x01) << (link)); \ + } while (/* CONSTCOND */0) + + + + +int +ali1543_init(pci_chipset_tag_t pc, bus_space_tag_t iot, pcitag_t tag, + pciintr_icu_tag_t *ptagp, pciintr_icu_handle_t *phandp) +{ + + if (piix_init(pc, iot, tag, ptagp, phandp) == 0) { + *ptagp = &ali1543_icu; + + return (0); + } + + return (1); +} + + + + +int +ali1543_getclink(pciintr_icu_handle_t v, int link, int *clinkp) +{ + + if (ALI1543_LEGAL_LINK(link - 1)) { + *clinkp = link - 1; + return (0); + } + + return (1); +} + + + + +int +ali1543_get_intr(pciintr_icu_handle_t v, int clink, int *irqp) +{ + struct piix_handle *ph = v; + pcireg_t reg; + int val; + + if (ALI1543_LEGAL_LINK(clink) == 0) + return (1); + + reg = pci_conf_read(ph->ph_pc, ph->ph_tag, ALI1543_INTR_CFG_REG); +#ifdef DEBUG_1543 + printf("ali1543: PIRQ reg 0x%08x\n", reg); /* XXX debug */ +#endif /* DEBUG_1543 */ + val = ALI1543_PIRQ(reg, clink); + *irqp = (val == 0) ? + I386_PCI_INTERRUPT_LINE_NO_CONNECTION : val; + + return (0); +} + + + + +int +ali1543_set_intr(pciintr_icu_handle_t v, int clink, int irq) +{ + struct piix_handle *ph = v; + int shift, val; + pcireg_t reg; + + if (ALI1543_LEGAL_LINK(clink) == 0 || ALI1543_LEGAL_IRQ(irq) == 0) + return (1); + + reg = pci_conf_read(ph->ph_pc, ph->ph_tag, ALI1543_INTR_CFG_REG); + ali1543_get_intr(v, clink, &val); + shift = ALI1543_INTR_PIRQ_SHIFT(clink); + reg &= ~(0x0f << shift); + reg |= (ali1543_intr_shuffle_set[irq] << shift); + pci_conf_write(ph->ph_pc, ph->ph_tag, ALI1543_INTR_CFG_REG, reg); + if (ali1543_get_intr(v, clink, &val) != 0 || val != irq) + return (1); + + return (0); +} + + + +int +ali1543_get_trigger(pciintr_icu_handle_t v, int irq, int *triggerp) +{ + struct piix_handle *ph = v; + int i, error, check_consistency, pciirq, pcitrigger = IST_NONE; + pcireg_t reg; + + if (ALI1543_LEGAL_IRQ(irq) == 0) { + return 1; + } + + check_consistency = 0; + for (i = 0; i <= 7; i++) { + ali1543_get_intr(v, i, &pciirq); + if (pciirq == irq) { + reg = pci_conf_read(ph->ph_pc, ph->ph_tag, + ALI1543_INTR_TRIG_REG); + if (ALI1543_INTR_TRIG_GET(reg, i) == ALI1543_INTR_TRIG_EDGE) + pcitrigger = IST_EDGE; + else + pcitrigger = IST_LEVEL; + check_consistency = 1; + break; + } + } + + error = piix_get_trigger(v, irq, triggerp); + if (error == 0 && check_consistency && pcitrigger != *triggerp) + return (1); + return (error); +} + + + +int +ali1543_set_trigger(pciintr_icu_handle_t v, int irq, int trigger) +{ + struct piix_handle *ph = v; + int i, pciirq, testtrig; + pcireg_t reg; + + if (ALI1543_LEGAL_IRQ(irq) == 0) { + return 1; + } + + for (i = 0; i <= 7; i++) { + ali1543_get_intr(v, i, &pciirq); + if (pciirq == irq) { + reg = pci_conf_read(ph->ph_pc, ph->ph_tag, + ALI1543_INTR_TRIG_REG); + if (trigger == IST_LEVEL) { + ALI1543_INTR_TRIG_SET(reg, i, + ALI1543_INTR_TRIG_LEVEL); + } else { + ALI1543_INTR_TRIG_SET(reg, i, + ALI1543_INTR_TRIG_EDGE); + } + + pci_conf_write(ph->ph_pc, ph->ph_tag, + ALI1543_INTR_TRIG_REG, reg); + break; + } + } + + if (piix_set_trigger(v, irq, trigger) != 0 || + ali1543_get_trigger(v, irq, &testtrig) != 0 || + testtrig != trigger) + return (1); + + return (0); +} diff --git a/sys/arch/i386/pci/pci_intr_fixup.c b/sys/arch/i386/pci/pci_intr_fixup.c index b12aa6b3f272..67bd34a723bb 100644 --- a/sys/arch/i386/pci/pci_intr_fixup.c +++ b/sys/arch/i386/pci/pci_intr_fixup.c @@ -1,4 +1,4 @@ -/* $NetBSD: pci_intr_fixup.c,v 1.16 2001/08/01 09:11:19 haya Exp $ */ +/* $NetBSD: pci_intr_fixup.c,v 1.17 2001/08/27 08:21:21 haya Exp $ */ /*- * Copyright (c) 1999 The NetBSD Foundation, Inc. @@ -154,6 +154,9 @@ const struct pciintr_icu_table { { PCI_VENDOR_AMD, PCI_PRODUCT_AMD_PBC756_PMC, amd756_init }, + { PCI_VENDOR_ALI, PCI_PRODUCT_ALI_M1543, + ali1543_init }, + { 0, 0, NULL }, }; diff --git a/sys/arch/i386/pci/pci_intr_fixup.h b/sys/arch/i386/pci/pci_intr_fixup.h index 7c1e286c1051..cc783d53d655 100644 --- a/sys/arch/i386/pci/pci_intr_fixup.h +++ b/sys/arch/i386/pci/pci_intr_fixup.h @@ -1,4 +1,4 @@ -/* $NetBSD: pci_intr_fixup.h,v 1.2 2001/04/19 17:32:40 uch Exp $ */ +/* $NetBSD: pci_intr_fixup.h,v 1.3 2001/08/27 08:21:21 haya Exp $ */ /* * Copyright (c) 1999, by UCHIYAMA Yasushi @@ -65,3 +65,5 @@ int sis85c503_init __P((pci_chipset_tag_t, bus_space_tag_t, pcitag_t, pciintr_icu_tag_t *, pciintr_icu_handle_t *)); int amd756_init __P((pci_chipset_tag_t, bus_space_tag_t, pcitag_t, pciintr_icu_tag_t *, pciintr_icu_handle_t *)); +int ali1543_init __P((pci_chipset_tag_t, bus_space_tag_t, pcitag_t, + pciintr_icu_tag_t *, pciintr_icu_handle_t *));