static void
slugbutt_deferred(device_t self)
{
	struct slugbutt_softc *sc = device_private(self);
	struct ixp425_softc *ixsc = ixp425_softc;
	uint32_t reg;

	sc->sc_dev = self;

	/* Configure the GPIO pins as inputs */
	reg = GPIO_CONF_READ_4(ixsc, IXP425_GPIO_GPOER);
	reg |= SLUGBUTT_PWR_BIT | SLUGBUTT_RST_BIT;
	GPIO_CONF_WRITE_4(ixsc, IXP425_GPIO_GPOER, reg);

	/* Configure the input type: Falling edge */
	reg = GPIO_CONF_READ_4(ixsc, GPIO_TYPE_REG(GPIO_BUTTON_PWR));
	reg &= ~GPIO_TYPE(GPIO_BUTTON_PWR, GPIO_TYPE_MASK);
	reg |= GPIO_TYPE(GPIO_BUTTON_PWR, GPIO_TYPE_EDG_FALLING);
	GPIO_CONF_WRITE_4(ixsc, GPIO_TYPE_REG(GPIO_BUTTON_PWR), reg);

	reg = GPIO_CONF_READ_4(ixsc, GPIO_TYPE_REG(GPIO_BUTTON_RST));
	reg &= ~GPIO_TYPE(GPIO_BUTTON_RST, GPIO_TYPE_MASK);
	reg |= GPIO_TYPE(GPIO_BUTTON_RST, GPIO_TYPE_EDG_FALLING);
	GPIO_CONF_WRITE_4(ixsc, GPIO_TYPE_REG(GPIO_BUTTON_RST), reg);

	/* Clear any existing interrupt */
	GPIO_CONF_WRITE_4(ixsc, IXP425_GPIO_GPISR, SLUGBUTT_PWR_BIT |
	    SLUGBUTT_RST_BIT);

	sysmon_task_queue_init();

	sc->sc_smpwr.smpsw_name = device_xname(sc->sc_dev);
	sc->sc_smpwr.smpsw_type = PSWITCH_TYPE_POWER;

	if (sysmon_pswitch_register(&sc->sc_smpwr) != 0) {
		printf("%s: unable to register power button with sysmon\n",
		    device_xname(sc->sc_dev));
		return;
	}

	sc->sc_smrst.smpsw_name = device_xname(sc->sc_dev);
	sc->sc_smrst.smpsw_type = PSWITCH_TYPE_RESET;

	if (sysmon_pswitch_register(&sc->sc_smrst) != 0) {
		printf("%s: unable to register reset button with sysmon\n",
		    device_xname(sc->sc_dev));
		return;
	}

	/* Hook the interrupts */
	ixp425_intr_establish(BUTTON_PWR_INT, IPL_TTY, power_intr, sc);
	ixp425_intr_establish(BUTTON_RST_INT, IPL_TTY, reset_intr, sc);
}
Example #2
0
static int
ata_avila_attach(device_t dev)
{
	struct ata_avila_softc *sc = device_get_softc(dev);
	struct ixp425_softc *sa = device_get_softc(device_get_parent(dev));
	u_int32_t alt_t_off, ide_gpin, ide_irq;

	sc->sc_dev = dev;
	/* NB: borrow from parent */
	sc->sc_iot = sa->sc_iot;
	sc->sc_exp_ioh = sa->sc_exp_ioh;
	if (EXP_BUS_READ_4(sc, EXP_TIMING_CS2_OFFSET) != 0) {
		/* Avila board */
		if (bus_space_map(sc->sc_iot, IXP425_EXP_BUS_CS1_HWBASE,
		    IXP425_EXP_BUS_CS1_SIZE, 0, &sc->sc_ioh))
			panic("%s: unable to map Expansion Bus CS1 window",
			    __func__);
		if (bus_space_map(sc->sc_iot, IXP425_EXP_BUS_CS2_HWBASE,
		    IXP425_EXP_BUS_CS2_SIZE, 0, &sc->sc_alt_ioh))
			panic("%s: unable to map Expansion Bus CS2 window",
			    __func__);
		ide_gpin = AVILA_IDE_GPIN;
		ide_irq = AVILA_IDE_IRQ;
		sc->sc_16bit_off = EXP_TIMING_CS1_OFFSET;
		alt_t_off = EXP_TIMING_CS2_OFFSET;
	} else {
		/* Pronghorn */
		if (bus_space_map(sc->sc_iot, IXP425_EXP_BUS_CS3_HWBASE,
		    IXP425_EXP_BUS_CS3_SIZE, 0, &sc->sc_ioh))
			panic("%s: unable to map Expansion Bus CS3 window",
			    __func__);
		if (bus_space_map(sc->sc_iot, IXP425_EXP_BUS_CS4_HWBASE,
		    IXP425_EXP_BUS_CS4_SIZE, 0, &sc->sc_alt_ioh))
			panic("%s: unable to map Expansion Bus CS4 window",
			    __func__);
		ide_gpin = PRONGHORN_IDE_GPIN;
		ide_irq = PRONGHORN_IDE_IRQ;
		sc->sc_16bit_off = EXP_TIMING_CS3_OFFSET;
		alt_t_off = EXP_TIMING_CS4_OFFSET;
	}

	/*
	 * Craft special resource for ATA bus space ops
	 * that go through the expansion bus and require
	 * special hackery to ena/dis 16-bit operations.
	 *
	 * XXX probably should just make this generic for
	 * accessing the expansion bus.
	 */
	sc->sc_expbus_tag.bs_cookie = sc;	/* NB: backpointer */
	/* read single */
	sc->sc_expbus_tag.bs_r_1	= ata_bs_r_1,
	sc->sc_expbus_tag.bs_r_2	= ata_bs_r_2,
	/* read multiple */
	sc->sc_expbus_tag.bs_rm_2	= ata_bs_rm_2,
	sc->sc_expbus_tag.bs_rm_2_s	= ata_bs_rm_2_s,
	/* write (single) */
	sc->sc_expbus_tag.bs_w_1	= ata_bs_w_1,
	sc->sc_expbus_tag.bs_w_2	= ata_bs_w_2,
	/* write multiple */
	sc->sc_expbus_tag.bs_wm_2	= ata_bs_wm_2,
	sc->sc_expbus_tag.bs_wm_2_s	= ata_bs_wm_2_s,

	rman_set_bustag(&sc->sc_ata, &sc->sc_expbus_tag);
	rman_set_bushandle(&sc->sc_ata, sc->sc_ioh);
	rman_set_bustag(&sc->sc_alt_ata, &sc->sc_expbus_tag);
	rman_set_bushandle(&sc->sc_alt_ata, sc->sc_alt_ioh);

	GPIO_CONF_WRITE_4(sa, IXP425_GPIO_GPOER, 
	    GPIO_CONF_READ_4(sa, IXP425_GPIO_GPOER) | (1<<ide_gpin));
	/* set interrupt type */
	GPIO_CONF_WRITE_4(sa, GPIO_TYPE_REG(ide_gpin),
	    (GPIO_CONF_READ_4(sa, GPIO_TYPE_REG(ide_gpin)) &~
	     GPIO_TYPE(ide_gpin, GPIO_TYPE_MASK)) |
	     GPIO_TYPE(ide_gpin, GPIO_TYPE_EDG_RISING));

	/* clear ISR */
	GPIO_CONF_WRITE_4(sa, IXP425_GPIO_GPISR, (1<<ide_gpin));

	/* configure CS1/3 window, leaving timing unchanged */
	EXP_BUS_WRITE_4(sc, sc->sc_16bit_off,
	    EXP_BUS_READ_4(sc, sc->sc_16bit_off) |
	        EXP_BYTE_EN | EXP_WR_EN | EXP_BYTE_RD16 | EXP_CS_EN);
	/* configure CS2/4 window, leaving timing unchanged */
	EXP_BUS_WRITE_4(sc, alt_t_off,
	    EXP_BUS_READ_4(sc, alt_t_off) |
	        EXP_BYTE_EN | EXP_WR_EN | EXP_BYTE_RD16 | EXP_CS_EN);

	/* setup interrupt */
	sc->sc_irq = bus_alloc_resource(dev, SYS_RES_IRQ, &sc->sc_rid,
	    ide_irq, ide_irq, 1, RF_ACTIVE);
	if (!sc->sc_irq)
		panic("Unable to allocate irq %u.\n", ide_irq);
	bus_setup_intr(dev, sc->sc_irq,
	    INTR_TYPE_BIO | INTR_MPSAFE | INTR_ENTROPY,
	    NULL, ata_avila_intr, sc, &sc->sc_ih);

	/* attach channel on this controller */
	device_add_child(dev, "ata", devclass_find_free_unit(ata_devclass, 0));
	bus_generic_attach(dev);

	return 0;
}
Example #3
0
void
ixp425_md_attach(device_t dev)
{
	struct ixp425_softc *sc = device_get_softc(device_get_parent(dev));
	struct ixppcib_softc *pci_sc = device_get_softc(dev);
	uint32_t reg;

	
	/* PCI Reset Assert */
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPOUTR);
	reg &= ~(1U << GPIO_PCI_RESET);
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPOUTR, reg);

	/* PCI Clock Disable */
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPCLKR);
	reg &= ~GPCLKR_MUX14;
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPCLKR, reg);

	/*
	 * set GPIO Direction
	 *	Output: PCI_CLK, PCI_RESET
	 *	Input:  PCI_INTA, PCI_INTB, PCI_INTC, PCI_INTD
	 */
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPOER);
	reg &= ~(1U << GPIO_PCI_CLK);
	reg &= ~(1U << GPIO_PCI_RESET);
	reg |= ((1U << GPIO_PCI_INTA) | (1U << GPIO_PCI_INTB) |
		(1U << GPIO_PCI_INTC) | (1U << GPIO_PCI_INTD));
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPOER, reg);

	/*
	 * Set GPIO interrupt type
	 * 	PCI_INT_A, PCI_INTB, PCI_INT_C, PCI_INT_D: Active Low
	 */
	reg = GPIO_CONF_READ_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTA));
	reg &= ~GPIO_TYPE(GPIO_PCI_INTA, GPIO_TYPE_MASK);
	reg |= GPIO_TYPE(GPIO_PCI_INTA, GPIO_TYPE_ACT_LOW);
	GPIO_CONF_WRITE_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTA), reg);

	reg = GPIO_CONF_READ_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTB));
	reg &= ~GPIO_TYPE(GPIO_PCI_INTB, GPIO_TYPE_MASK);
	reg |= GPIO_TYPE(GPIO_PCI_INTB, GPIO_TYPE_ACT_LOW);
	GPIO_CONF_WRITE_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTB), reg);

	reg = GPIO_CONF_READ_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTC));
	reg &= ~GPIO_TYPE(GPIO_PCI_INTC, GPIO_TYPE_MASK);
	reg |= GPIO_TYPE(GPIO_PCI_INTC, GPIO_TYPE_ACT_LOW);
	GPIO_CONF_WRITE_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTC), reg);

	reg = GPIO_CONF_READ_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTD));
	reg &= ~GPIO_TYPE(GPIO_PCI_INTD, GPIO_TYPE_MASK);
	reg |= GPIO_TYPE(GPIO_PCI_INTD, GPIO_TYPE_ACT_LOW);
	GPIO_CONF_WRITE_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTD), reg);

	/* clear ISR */
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPISR,
			  (1U << GPIO_PCI_INTA) | (1U << GPIO_PCI_INTB) |
			  (1U << GPIO_PCI_INTC) | (1U << GPIO_PCI_INTD));

	/* wait 1ms to satisfy "minimum reset assertion time" of the PCI spec */
	DELAY(1000);
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPCLKR);
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPCLKR, reg |
		(0xf << GPCLKR_CLK0DC_SHIFT) | (0xf << GPCLKR_CLK0TC_SHIFT));

	/* PCI Clock Enable */
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPCLKR);
	reg |= GPCLKR_MUX14;
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPCLKR, reg | GPCLKR_MUX14);

	/*
	 * wait 100us to satisfy "minimum reset assertion time from clock stable
	 * requirement of the PCI spec
	 */
	DELAY(100);
        /* PCI Reset deassert */
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPOUTR);
	reg |= 1U << GPIO_PCI_RESET;
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPOUTR, reg | (1U << GPIO_PCI_RESET));
	pci_sc->sc_irq_rman.rm_type = RMAN_ARRAY;
	pci_sc->sc_irq_rman.rm_descr = "IXP425 PCI IRQs";
	CTASSERT(PCI_INT_D < PCI_INT_A);
	/* XXX this overlaps the irq's setup in ixp425_attach */
	if (rman_init(&pci_sc->sc_irq_rman) != 0 ||
	    rman_manage_region(&pci_sc->sc_irq_rman, PCI_INT_D, PCI_INT_A) != 0)
		panic("ixp425_md_attach: failed to set up IRQ rman");
}
Example #4
0
void
ixp425_md_pci_init(struct ixp425_softc *sc)
{
	pci_chipset_tag_t pc = &sc->ia_pci_chipset;
	u_int32_t reg;

	pc->pc_intr_v = sc;
	pc->pc_intr_map = nslu2_pci_intr_map;
	pc->pc_intr_string = nslu2_pci_intr_string;
	pc->pc_intr_evcnt = nslu2_pci_intr_evcnt;
	pc->pc_intr_establish = nslu2_pci_intr_establish;
	pc->pc_intr_disestablish = nslu2_pci_intr_disestablish;

	/* PCI Reset Assert */
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPOUTR);
	reg &= ~(1u << GPIO_PCI_RESET);
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPOUTR, reg);

	/* PCI Clock Disable */
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPCLKR);
	reg &= ~GPCLKR_MUX14;
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPCLKR, reg);

	/*
	 * Set GPIO Direction
	 *	Output: PCI_CLK, PCI_RESET
	 *	Input:  PCI_INTA, PCI_INTB, PCI_INTC
	 */
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPOER);
	reg &= ~((1u << GPIO_PCI_CLK) | (1u << GPIO_PCI_RESET));
	reg |= (1u << GPIO_PCI_INTA) | (1u << GPIO_PCI_INTB) |
	    (1u << GPIO_PCI_INTC);
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPOER, reg);

	/*
	 * Set GPIO interrupt type
	 *      PCI_INT_A, PCI_INTB, PCI_INT_C: Active Low
	 */
	reg = GPIO_CONF_READ_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTA));
	reg &= ~GPIO_TYPE(GPIO_PCI_INTA, GPIO_TYPE_MASK);
	reg |= GPIO_TYPE(GPIO_PCI_INTA, GPIO_TYPE_ACT_LOW);
	GPIO_CONF_WRITE_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTA), reg);

	reg = GPIO_CONF_READ_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTB));
	reg &= ~GPIO_TYPE(GPIO_PCI_INTB, GPIO_TYPE_MASK);
	reg |= GPIO_TYPE(GPIO_PCI_INTB, GPIO_TYPE_ACT_LOW);
	GPIO_CONF_WRITE_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTB), reg);

	reg = GPIO_CONF_READ_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTC));
	reg &= ~GPIO_TYPE(GPIO_PCI_INTC, GPIO_TYPE_MASK);
	reg |= GPIO_TYPE(GPIO_PCI_INTC, GPIO_TYPE_ACT_LOW);
	GPIO_CONF_WRITE_4(sc, GPIO_TYPE_REG(GPIO_PCI_INTC), reg);

	/* Clear ISR */
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPISR, (1u << GPIO_PCI_INTA) |
	    (1u << GPIO_PCI_INTB) | (1u << GPIO_PCI_INTC));

	/* Wait 1ms to satisfy "minimum reset assertion time" of the PCI spec */
	DELAY(1000);
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPCLKR);
	reg |= (0xf << GPCLKR_CLK0DC_SHIFT) | (0xf << GPCLKR_CLK0TC_SHIFT);
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPCLKR, reg);

	/* PCI Clock Enable */
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPCLKR);
	reg |= GPCLKR_MUX14;
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPCLKR, reg);

	/*
	 * Wait 100us to satisfy "minimum reset assertion time from clock stable
	 * requirement of the PCI spec
	 */
	DELAY(100);
        /* PCI Reset deassert */
	reg = GPIO_CONF_READ_4(sc, IXP425_GPIO_GPOUTR);
	reg |= 1u << GPIO_PCI_RESET;
	GPIO_CONF_WRITE_4(sc, IXP425_GPIO_GPOUTR, reg);

	/*
	 * AHB->PCI address translation
	 *	PCI Memory Map allocation in 0x48000000 (64MB)
	 *	see. IXP425_PCI_MEM_HWBASE
	 */
	PCI_CSR_WRITE_4(sc, PCI_PCIMEMBASE, 0x48494a4b);

	/*
	 * PCI->AHB address translation
	 * 	begin at the physical memory start + OFFSET
	 */
#define	AHB_OFFSET	0x10000000UL
	reg  = (AHB_OFFSET + 0x00000000) >> 0;
	reg |= (AHB_OFFSET + 0x01000000) >> 8;
	reg |= (AHB_OFFSET + 0x02000000) >> 16;
	reg |= (AHB_OFFSET + 0x03000000) >> 24;
	PCI_CSR_WRITE_4(sc, PCI_AHBMEMBASE, reg);

	/* Write Mapping registers PCI Configuration Registers */
	/* Base Address 0 - 3 */
	ixp425_pci_conf_reg_write(sc, PCI_MAPREG_BAR0, AHB_OFFSET + 0x00000000);
	ixp425_pci_conf_reg_write(sc, PCI_MAPREG_BAR1, AHB_OFFSET + 0x01000000);
	ixp425_pci_conf_reg_write(sc, PCI_MAPREG_BAR2, AHB_OFFSET + 0x02000000);
	ixp425_pci_conf_reg_write(sc, PCI_MAPREG_BAR3, AHB_OFFSET + 0x03000000);

	/* Base Address 4 */
	ixp425_pci_conf_reg_write(sc, PCI_MAPREG_BAR4, 0xffffffff);

	/* Base Address 5 */
	ixp425_pci_conf_reg_write(sc, PCI_MAPREG_BAR5, 0x00000000);

	/* Assert some PCI errors */
	PCI_CSR_WRITE_4(sc, PCI_ISR, ISR_AHBE | ISR_PPE | ISR_PFE | ISR_PSE);

	/*
	 * Set up byte lane swapping between little-endian PCI
	 * and the big-endian AHB bus
	 */
	PCI_CSR_WRITE_4(sc, PCI_CSR, CSR_IC | CSR_ABE | CSR_PDS);

	/*
	 * Enable bus mastering and I/O,memory access
	 */
	ixp425_pci_conf_reg_write(sc, PCI_COMMAND_STATUS_REG,
		PCI_COMMAND_IO_ENABLE | PCI_COMMAND_MEM_ENABLE |
		PCI_COMMAND_MASTER_ENABLE);

	/*
	 * Wait some more to ensure PCI devices have stabilised.
	 */
	DELAY(50000);
}