Esempio n. 1
0
static void
prep_pci_get_chipset_tag_indirect(pci_chipset_tag_t pc)
{

	pc->pc_conf_v = (void *)pc;

	pc->pc_attach_hook = genppc_pci_indirect_attach_hook;
	pc->pc_bus_maxdevs = prep_pci_bus_maxdevs;
	pc->pc_make_tag = genppc_pci_indirect_make_tag;
	pc->pc_conf_read = genppc_pci_indirect_conf_read;
	pc->pc_conf_write = genppc_pci_indirect_conf_write;

	pc->pc_intr_v = (void *)pc;

	pc->pc_intr_map = prep_pci_intr_map;
	pc->pc_intr_string = genppc_pci_intr_string;
	pc->pc_intr_evcnt = genppc_pci_intr_evcnt;
	pc->pc_intr_establish = genppc_pci_intr_establish;
	pc->pc_intr_disestablish = genppc_pci_intr_disestablish;

	pc->pc_conf_interrupt = genppc_pci_conf_interrupt;
	pc->pc_decompose_tag = genppc_pci_indirect_decompose_tag;
	pc->pc_conf_hook = prep_pci_conf_hook;

	pc->pc_addr = mapiodev(prep_pci_baseaddr, 4);
	pc->pc_data = mapiodev(prep_pci_basedata, 4);
	pc->pc_bus = 0;
	pc->pc_node = 0;
	pc->pc_memt = 0;
	pc->pc_iot = 0;
}
Esempio n. 2
0
void
memcattach(struct device *parent, struct device *self, void *aux)
{
	struct memc_softc *sc = (struct memc_softc *)self;
	struct confargs *ca = aux;
	uint32_t rev, reg[2];
	char name[32];
	int len;

	OF_getprop(ca->ca_node, "reg", &reg, sizeof(reg));

	len = OF_getprop(ca->ca_node, "name", name, sizeof(name));
	if (len > 0)
		name[len] = 0;

	/* Map the first page in order to access the registers */
	if (strcmp(name, "u3") == 0 || strcmp(name, "u4") == 0)
		sc->sc_baseaddr = mapiodev(reg[1], PAGE_SIZE);
	else
		sc->sc_baseaddr = mapiodev(reg[0], PAGE_SIZE);

	/* Enable the ethernet clock */
	memc_enable(sc, UNINORTH_CLK_OFFSET, UNINORTH_ETHERNET_CTL);
	len = OF_getprop(ca->ca_node, "device-rev", &rev, sizeof(rev));
	if (len < 0)
		rev = 0;

	printf (": %s rev 0x%x\n", name, rev);

	memc_attach_children(sc, ca->ca_node);
}
Esempio n. 3
0
void
cgeightattach(struct device *parent, struct device *self, void *args)
{
	struct cgeight_softc *sc = (struct cgeight_softc *)self;
	struct confargs *ca = args;
	int node = 0;
	volatile struct bt_regs *bt;
	int isconsole = 0;

	/* Map the pfour register. */
	SET(sc->sc_sunfb.sf_flags, FB_PFOUR);
	sc->sc_sunfb.sf_pfour = (volatile u_int32_t *)
	    mapiodev(ca->ca_ra.ra_reg, 0, sizeof(u_int32_t));

	if (cputyp == CPU_SUN4) {
		struct eeprom *eep = (struct eeprom *)eeprom_va;

		/*
		 * Assume this is the console if there's no eeprom info
		 * to be found.
		 */
		if (eep == NULL || eep->ee_diag.eed_console == EED_CONS_P4)
			isconsole = 1;
	}

	/* Map the Brooktree. */
	sc->sc_fbc = (volatile struct fbcontrol *)
	    mapiodev(ca->ca_ra.ra_reg,
		     PFOUR_COLOR_OFF_CMAP, sizeof(struct fbcontrol));

	sc->sc_phys = ca->ca_ra.ra_reg[0];

	/* enable video */
	fb_pfour_burner(sc, 1, 0);
	bt = &sc->sc_fbc->fbc_dac;
	BT_INIT(bt, 0);

	fb_setsize(&sc->sc_sunfb, 1, 1152, 900, node, ca->ca_bustype);
	sc->sc_sunfb.sf_ro.ri_hw = sc;

	/*
	 * Map the overlay and overlay enable planes.
	 */
	sc->sc_enable = (volatile u_char *)mapiodev(ca->ca_ra.ra_reg,
	    PFOUR_COLOR_OFF_ENABLE, round_page(sc->sc_sunfb.sf_fbsize));
	sc->sc_sunfb.sf_ro.ri_bits =  mapiodev(ca->ca_ra.ra_reg,
	    PFOUR_COLOR_OFF_OVERLAY, round_page(sc->sc_sunfb.sf_fbsize));

	cgeight_reset(sc, WSDISPLAYIO_MODE_EMUL);
	printf(": p4, %dx%d", sc->sc_sunfb.sf_width,
	    sc->sc_sunfb.sf_height);

	fbwscons_init(&sc->sc_sunfb, isconsole);
	if (isconsole)
		fbwscons_console_init(&sc->sc_sunfb, -1);

	fbwscons_attach(&sc->sc_sunfb, &cgeight_accessops, isconsole);
}
Esempio n. 4
0
void
pchbattach(struct device *parent, struct device *self, void *aux)
{
	struct pci_attach_args *pa = aux;
	char devinfo[256];
#if NAGP > 0
	struct agpbus_attach_args apa;
#endif
	volatile unsigned char *python;
	uint32_t v;
	
	aprint_normal("\n");

	/*
	 * All we do is print out a description.  Eventually, we
	 * might want to add code that does something that's
	 * possibly chipset-specific.
	 */

	pci_devinfo(pa->pa_id, pa->pa_class, 0, devinfo, sizeof(devinfo));
	aprint_normal("%s: %s (rev. 0x%02x)\n", self->dv_xname, devinfo,
	    PCI_REVISION(pa->pa_class));

	switch (PCI_VENDOR(pa->pa_id)) {
	case PCI_VENDOR_IBM:
		switch (PCI_PRODUCT(pa->pa_id)) {
		case PCI_PRODUCT_IBM_82660:
			ibm82660_print(pa, self);
			break;
		case PCI_PRODUCT_IBM_PYTHON:
			python = mapiodev(0xfeff6000, 0x60);
			v = 0x88b78e01; /* taken from linux */
			out32rb(python+0x30, v);
			v = in32rb(python+0x30);
			aprint_debug("Reset python reg 30 to 0x%x\n", v);
			break;
		}
		break;
	case PCI_VENDOR_MOT:
		switch (PCI_PRODUCT(pa->pa_id)) {
		case PCI_PRODUCT_MOT_MPC105:
			mpc105_print(pa, self);
			break;
		case PCI_PRODUCT_MOT_MPC106:
			mpc106_print(pa, self);
			break;
		}
		break;
	}

#if NAGP > 0
	if (pci_get_capability(pa->pa_pc, pa->pa_tag, PCI_CAP_AGP,
			       NULL, NULL) != 0) {
		apa.apa_pci_args = *pa;
		config_found_ia(self, "agpbus", &apa, agpbusprint);
	}
#endif /* NAGP */
}
Esempio n. 5
0
void
ki2c_attach(struct device *parent, struct device *self, void *aux)
{
	struct ki2c_softc *sc = (struct ki2c_softc *)self;
	struct confargs *ca = aux;
	int node = ca->ca_node;
	int rate, count = 0;
	char name[32];

	ca->ca_reg[0] += ca->ca_baseaddr;

	if (OF_getprop(node, "AAPL,i2c-rate", &rate, 4) != 4) {
		printf(": cannot get i2c-rate\n");
		return;
	}
	if (OF_getprop(node, "AAPL,address", &sc->sc_paddr, 4) != 4) {
		printf(": unable to find i2c address\n");
		return;
	}
	if (OF_getprop(node, "AAPL,address-step", &sc->sc_regstep, 4) != 4) {
		printf(": unable to find i2c address step\n");
		return;
	}
	sc->sc_reg = mapiodev(sc->sc_paddr, (DATA+1)*sc->sc_regstep);

	printf("\n");

	ki2c_writereg(sc, STATUS, 0);
	ki2c_writereg(sc, ISR, 0);
	ki2c_writereg(sc, IER, 0);

	ki2c_setmode(sc, I2C_STDSUBMODE, 0);
	ki2c_setspeed(sc, I2C_100kHz);		/* XXX rate */

	lockinit(&sc->sc_buslock, PZERO, sc->sc_dev.dv_xname, 0, 0);
	ki2c_writereg(sc, IER,I2C_INT_DATA|I2C_INT_ADDR|I2C_INT_STOP);

	for (node = OF_child(ca->ca_node); node; node = OF_peer(node)) {
		if (OF_getprop(node, "name", &name, sizeof name) > 0) {
			if (strcmp(name, "i2c-bus") == 0) {
				ki2c_attach_bus(sc, &sc->sc_bus[count], node);
				if (++count >= KI2C_MAX_BUSSES)
					break;
			}
		}
	}

	/* 
	 * If we didn't find any i2c-bus nodes, there is only a single
	 * i2c bus.
	 */

	if (count == 0)
		ki2c_attach_bus(sc, &sc->sc_bus[0], ca->ca_node);
}
void
pmppc_pci_get_chipset_tag(pci_chipset_tag_t pc)
{
	pc->pc_conf_v = (void *)pc;

	pc->pc_attach_hook = genppc_pci_indirect_attach_hook;
	pc->pc_bus_maxdevs = genppc_pci_bus_maxdevs;
	pc->pc_make_tag = genppc_pci_indirect_make_tag;
	pc->pc_conf_read = genppc_pci_indirect_conf_read;
	pc->pc_conf_write = genppc_pci_indirect_conf_write;

	pc->pc_intr_v = (void *)pc;

	pc->pc_intr_map = pmppc_pci_intr_map;
	pc->pc_intr_string = genppc_pci_intr_string;
	pc->pc_intr_evcnt = genppc_pci_intr_evcnt;
	pc->pc_intr_establish = genppc_pci_intr_establish;
	pc->pc_intr_disestablish = genppc_pci_intr_disestablish;
	pc->pc_intr_setattr = genppc_pci_intr_setattr;

	pc->pc_conf_interrupt = pmppc_pci_conf_interrupt;
	pc->pc_decompose_tag = genppc_pci_indirect_decompose_tag;
	pc->pc_conf_hook = genppc_pci_conf_hook;

	pc->pc_addr = mapiodev(CPC_PCICFGADR, 4, false);
	pc->pc_data = mapiodev(CPC_PCICFGDATA, 4, false);
	pc->pc_bus = 0;
	pc->pc_node = 0;
	pc->pc_memt = 0;
	pc->pc_iot = 0;

	/* the following two lines are required because unlike other ports, 
	 * we cannot just add PHYS_TO_BUS_MEM/BUS_MEM_TO_PHYS defines to
	 * bus.h, because it would impact other evbppc ports.
	 */
	pci_bus_dma_tag._dma_phys_to_bus_mem = phys_to_pci;
	pci_bus_dma_tag._dma_bus_mem_to_phys = pci_to_phys;
}
Esempio n. 7
0
void
uni_n_config(char *name, int handle)
{
	char *baseaddr;
	int *ctladdr;
	u_int32_t address;

	/* sanity test */
	if (strcmp (name, "uni-n") == 0 || strcmp (name, "u3") == 0
	    || strcmp (name, "u4") == 0) {
		if (OF_getprop(handle, "reg", &address,
		    sizeof address) > 0) {
			baseaddr = mapiodev(address, NBPG);
			ctladdr = (void *)(baseaddr + 0x20);
			*ctladdr |= 0x02;
		}
	}
}
Esempio n. 8
0
void
gpio_obio_attach(device_t parent, device_t self, void *aux)
{
    struct gpio_softc *sc = device_private(self);
    struct confargs *ca = aux, ca2;
    int child;
    int namelen;
    int intr[6];
    u_int reg[20];
    char name[32];

    printf("\n");

    sc->sc_port = mapiodev(ca->ca_baseaddr + ca->ca_reg[0], ca->ca_reg[1],
                           false);

    ca2.ca_baseaddr = ca->ca_baseaddr;
    for (child = OF_child(ca->ca_node); child; child = OF_peer(child)) {
        namelen = OF_getprop(child, "name", name, sizeof(name));
        if (namelen < 0)
            continue;
        if (namelen >= sizeof(name))
            continue;

        name[namelen] = 0;
        ca2.ca_name = name;
        ca2.ca_node = child;

        ca2.ca_nreg  = OF_getprop(child, "reg", reg, sizeof(reg));
        ca2.ca_nintr = OF_getprop(child, "AAPL,interrupts", intr,
                                  sizeof(intr));
        if (ca2.ca_nintr == -1)
            ca2.ca_nintr = OF_getprop(child, "interrupts", intr,
                                      sizeof(intr));

        ca2.ca_reg = reg;
        ca2.ca_intr = intr;

        config_found(self, &ca2, gpio_obio_print);
    }
}
Esempio n. 9
0
void
wdc_obio_attach(struct device *parent, struct device *self, void *aux)
{
	struct wdc_obio_softc *sc = (void *)self;
	struct confargs *ca = aux;
	struct channel_softc *chp = &sc->wdc_channel;
	int intr, error;
	bus_addr_t cmdbase;

	sc->sc_use_dma = 0;
	if (ca->ca_nreg >= 16)
		sc->sc_use_dma = 1;	/* Enable dma */

	sc->sc_dmat = ca->ca_dmat;
	if ((error = bus_dmamap_create(sc->sc_dmat,
	    WDC_DMALIST_MAX * DBDMA_COUNT_MAX, WDC_DMALIST_MAX,
	    DBDMA_COUNT_MAX, NBPG, BUS_DMA_NOWAIT, &sc->sc_dmamap)) != 0) {
		printf(": cannot create dma map, error = %d\n", error);
		return;
	}

	if (ca->ca_nintr >= 4 && ca->ca_nreg >= 8) {
		intr = ca->ca_intr[0];
		printf(" irq %d", intr);
	} else if (ca->ca_nintr == -1) {
		intr = WDC_DEFAULT_PIO_IRQ;
		printf(" irq property not found; using %d", intr);
	} else {
		printf(": couldn't get irq property\n");
		return;
	}

	if (sc->sc_use_dma)
		printf(": DMA");

	printf("\n");

	chp->cmd_iot = chp->ctl_iot = ca->ca_iot;
	chp->_vtbl = &wdc_obio_vtbl;

	cmdbase = ca->ca_reg[0];
	sc->sc_cmdsize = ca->ca_reg[1];

	if (bus_space_map(chp->cmd_iot, cmdbase, sc->sc_cmdsize, 0,
	    &chp->cmd_ioh) || bus_space_subregion(chp->cmd_iot, chp->cmd_ioh,
	    /* WDC_AUXREG_OFFSET<<4 */ 0x160, 1, &chp->ctl_ioh)) {
		printf("%s: couldn't map registers\n",
			sc->sc_wdcdev.sc_dev.dv_xname);
		return;
	}
	chp->data32iot = chp->cmd_iot;
	chp->data32ioh = chp->cmd_ioh;

	sc->sc_ih = mac_intr_establish(parent, intr, IST_LEVEL, IPL_BIO,
	    wdcintr, chp, sc->sc_wdcdev.sc_dev.dv_xname);

	sc->sc_wdcdev.set_modes = wdc_obio_adjust_timing;
	if (sc->sc_use_dma) {
		sc->sc_dbdma = dbdma_alloc(sc->sc_dmat, WDC_DMALIST_MAX + 1);
		sc->sc_dmacmd = sc->sc_dbdma->d_addr;

		sc->sc_dmareg = mapiodev(ca->ca_baseaddr + ca->ca_reg[2],
		    sc->sc_dmasize = ca->ca_reg[3]);

		sc->sc_wdcdev.cap |= WDC_CAPABILITY_DMA;
		sc->sc_wdcdev.DMA_cap = 2;
		if (strcmp(ca->ca_name, "ata-4") == 0) {
			sc->sc_wdcdev.cap |= WDC_CAPABILITY_UDMA |
			    WDC_CAPABILITY_MODE;
			sc->sc_wdcdev.UDMA_cap = 4;
			sc->sc_wdcdev.set_modes = wdc_obio_ata4_adjust_timing;
		}
		if (strcmp(ca->ca_name, "ata-6") == 0) {
			sc->sc_wdcdev.cap |= WDC_CAPABILITY_UDMA |
			    WDC_CAPABILITY_MODE;
			sc->sc_wdcdev.UDMA_cap = 5;
			sc->sc_wdcdev.set_modes = wdc_obio_ata6_adjust_timing;
		}
	}
	sc->sc_wdcdev.cap |= WDC_CAPABILITY_DATA16;
	sc->sc_wdcdev.PIO_cap = 4;
	sc->wdc_chanptr = chp;
	sc->sc_wdcdev.channels = &sc->wdc_chanptr;
	sc->sc_wdcdev.nchannels = 1;
	sc->sc_wdcdev.dma_arg = sc;
	sc->sc_wdcdev.dma_init = wdc_obio_dma_init;
	sc->sc_wdcdev.dma_start = wdc_obio_dma_start;
	sc->sc_wdcdev.dma_finish = wdc_obio_dma_finish;
	chp->channel = 0;
	chp->wdc = &sc->sc_wdcdev;

	chp->ch_queue = malloc(sizeof(struct channel_queue), M_DEVBUF,
	    M_NOWAIT);
	if (chp->ch_queue == NULL) {
		printf("%s: can't allocate memory for command queue",
		sc->sc_wdcdev.sc_dev.dv_xname);
		return;
	}

	wdcattach(chp);
	sc->sc_wdcdev.set_modes(chp);
	wdc_print_current_modes(chp);
}
Esempio n. 10
0
void
tcxattach(struct device *parent, struct device *self, void *args)
{
	struct tcx_softc *sc = (struct tcx_softc *)self;
	struct confargs *ca = args;
	int node, pri;
	int isconsole = 0;
	char *nam = NULL;
	vaddr_t thc_offset;

	pri = ca->ca_ra.ra_intr[0].int_pri;
	printf(" pri %d: ", pri);

	node = ca->ca_ra.ra_node;
	isconsole = node == fbnode;

	if (ca->ca_ra.ra_nreg < TCX_NREG) {
		printf("expected %d registers, got %d\n",
		    TCX_NREG, ca->ca_ra.ra_nreg);
		return;
	}

	nam = getpropstring(node, "model");
	if (*nam != '\0')
		printf("%s, ", nam);

	/*
	 * Copy the register address spaces needed for mmap operation.
	 */
	sc->sc_phys[0] = ca->ca_ra.ra_reg[TCX_REG_DFB8];
	sc->sc_phys[1] = ca->ca_ra.ra_reg[TCX_REG_DFB24];

	/*
	 * Can't trust the PROM range len here, it is only 4 bytes on the
	 * 8-bit model. Not that it matters much anyway since we map in
	 * pages.
	 */
	sc->sc_bt = (volatile struct bt_regs *)
	    mapiodev(&ca->ca_ra.ra_reg[TCX_REG_CMAP], 0, sizeof *sc->sc_bt);

	/*
	 * For some reason S24 PROM sets up TEC and THC ranges at the
	 * right addresses (701000 and 301000), while 8 bit TCX doesn't
	 * (and uses 70000 and 30000) - be sure to only compensate on 8 bit
	 * models.
	 */
	if (((vaddr_t)ca->ca_ra.ra_reg[TCX_REG_THC].rr_paddr & 0x1000) != 0)
		thc_offset = 0;
	else
		thc_offset = 0x1000;
	sc->sc_thc = (volatile struct tcx_thc *)
	    mapiodev(&ca->ca_ra.ra_reg[TCX_REG_THC],
	        thc_offset, sizeof *sc->sc_thc);

	/*
	 * Find out frame buffer geometry, so that we know how much
	 * memory to map.
	 */
	fb_setsize(&sc->sc_sunfb, 8, 1152, 900, node, ca->ca_bustype);

	sc->sc_dfb8 = mapiodev(&ca->ca_ra.ra_reg[TCX_REG_DFB8], 0,
	    round_page(sc->sc_sunfb.sf_fbsize));

	/*
	 * If the frame buffer advertizes itself as the 8 bit model, or
	 * if the PROM ranges are too small, limit ourselves to 8 bit
	 * operations.
	 *
	 * Further code needing to know which capabilities the frame buffer
	 * has will rely on sc_cplane being non-zero if 24 bit operation
	 * is possible.
	 */
	if (!node_has_property(node, "tcx-8-bit") &&
	    ca->ca_ra.ra_reg[TCX_REG_RDFB32].rr_len >=
	      sc->sc_sunfb.sf_fbsize * 4) {
		sc->sc_cplane =
		    (paddr_t)ca->ca_ra.ra_reg[TCX_REG_RDFB32].rr_paddr;
	}

	printf("%dx%dx%d\n",
	    sc->sc_sunfb.sf_width, sc->sc_sunfb.sf_height,
	    sc->sc_cplane == 0 ? 8 : 24);

	/*
	 * Set up mappings for the acceleration code. This may fail.
	 */
	tcx_accel_init(sc, ca);

	/* reset cursor & frame buffer controls */
	tcx_reset(sc, 8);

	/* enable video */
	tcx_burner(sc, 1, 0);

	sc->sc_sunfb.sf_ro.ri_hw = sc;
	sc->sc_sunfb.sf_ro.ri_bits = (void *)sc->sc_dfb8;

	fbwscons_init(&sc->sc_sunfb, isconsole);
	fbwscons_setcolormap(&sc->sc_sunfb, tcx_setcolor);

	/*
	 * Now plug accelerated console routines, if possible.
	 */
	tcx_accel_plug(sc, ca);

	sc->sc_ih.ih_fun = tcx_intr;
	sc->sc_ih.ih_arg = sc;
	intr_establish(pri, &sc->sc_ih, IPL_FB, self->dv_xname);

	if (isconsole) {
		fbwscons_console_init(&sc->sc_sunfb, -1);
		shutdownhook_establish(tcx_prom, sc);
	}

	fbwscons_attach(&sc->sc_sunfb, &tcx_accessops, isconsole);
}
Esempio n. 11
0
static void
mbattach(struct device *parent, struct device *self, void *aux)
{
	struct mainbus_softc *sc = (struct mainbus_softc *)self;
	struct confargs nca;
	char name[64], *t = NULL;
	int reg[4], cpucnt;
	int node, len, slen;

	node = OF_peer(0);
	len = OF_getprop(node, "model", name, sizeof(name));
	if (len > 1) {
		name[len] = '\0';
		slen = strlen(name)+1;
		if ((t = malloc(slen, M_DEVBUF, M_NOWAIT)) != NULL)
			strlcpy(t, name, slen);

	}

	len = OF_getprop(node, "compatible", name, sizeof(name));
	if (len > 1) {
		name[len] = '\0';
		/* Old World Macintosh */
		if ((strncmp(name, "AAPL", 4)) == 0) {
			hw_vendor = "Apple Computer, Inc.";
			slen = strlen(t) + strlen(name) - 3;
			if ((hw_prod = malloc(slen, M_DEVBUF, M_NOWAIT)) != NULL) {
				snprintf(hw_prod, slen, "%s %s", t, name + 5);
				free(t, M_DEVBUF);
			}
		} else {
			/* New World Macintosh or Unknown */
			hw_vendor = "Apple Computer, Inc.";
			hw_prod = t;
		}
	}
	printf(": model %s\n", hw_prod);

	sc->sc_bus.bh_dv = (struct device *)sc;
	sc->sc_bus.bh_type = BUS_MAIN;
	sc->sc_bus.bh_intr_establish = mb_intr_establish;
	sc->sc_bus.bh_intr_disestablish = mb_intr_disestablish;
	sc->sc_bus.bh_matchname = mb_matchname;

	/*
	 * Try to find and attach all of the CPUs in the machine.
	 */

	cpucnt = 0;
	node = OF_finddevice("/cpus");
	if (node != -1) {
		for (node = OF_child(node); node != 0; node = OF_peer(node)) {
			u_int32_t cpunum;
			int len;
			len = OF_getprop(node, "reg", &cpunum, sizeof cpunum);
			if (len == 4 && cpucnt == cpunum) {
				nca.ca_name = "cpu";
				nca.ca_bus = &sc->sc_bus;
				nca.ca_reg = reg;
				reg[0] = cpucnt;
				config_found(self, &nca, mbprint);
				cpucnt++;
			}
		}
	}
	if (cpucnt == 0) {
		nca.ca_name = "cpu";
		nca.ca_bus = &sc->sc_bus;
		nca.ca_reg = reg;
		reg[0] = 0;
		config_found(self, &nca, mbprint);
	}

	/*
	 * Special hack for SMP old world macs which lack /cpus and only have
	 * one cpu node.
	 */
	node = OF_finddevice("/hammerhead");
	if (node != -1) {
		len = OF_getprop(node, "reg", reg, sizeof(reg));
		if (len >= 2) {
			u_char *hh_base;
			int twoway = 0;

			if ((hh_base = mapiodev(reg[0], reg[1])) != NULL) {
				twoway = in32rb(hh_base + HH_REG_CONF) & 0x02;
				unmapiodev(hh_base, reg[1]);
			}
			if (twoway) {
				nca.ca_name = "cpu";
				nca.ca_bus = &sc->sc_bus;
				nca.ca_reg = reg;
				reg[0] = 1;
				config_found(self, &nca, mbprint);
			}
		}
	}

	for (node = OF_child(OF_peer(0)); node; node=OF_peer(node)) {
		bzero (name, sizeof(name));
		if (OF_getprop(node, "device_type", name,
		    sizeof(name)) <= 0) {
			if (OF_getprop(node, "name", name,
			    sizeof(name)) <= 0)
				printf ("name not found on node %x\n",
				    node);
				continue;
		}
		if (strcmp(name, "memory") == 0) {
			nca.ca_name = "mem";
			nca.ca_node = node;
			nca.ca_bus = &sc->sc_bus;
			config_found(self, &nca, mbprint);
		}
		if (strcmp(name, "memory-controller") == 0) {
			nca.ca_name = "memc";
			nca.ca_node = node;
			nca.ca_bus = &sc->sc_bus;
			config_found(self, &nca, mbprint);
		}
		if (strcmp(name, "pci") == 0) {
			nca.ca_name = "mpcpcibr";
			nca.ca_node = node;
			nca.ca_bus = &sc->sc_bus;
			config_found(self, &nca, mbprint);
		}
		if (strcmp(name, "ht") == 0) {
			nca.ca_name = "ht";
			nca.ca_node = node;
			nca.ca_bus = &sc->sc_bus;
			config_found(self, &nca, mbprint);
		}
		if (strcmp(name, "smu") == 0) {
			nca.ca_name = "smu";
			nca.ca_node = node;
			nca.ca_bus = &sc->sc_bus;
			config_found(self, &nca, mbprint);
		}
	}
}
Esempio n. 12
0
void
cgtwoattach(struct device *parent, struct device *self, void *args)
{
	struct cgtwo_softc *sc = (struct cgtwo_softc *)self;
	struct confargs *ca = args;
	int node = 0;
	int isconsole = 0;

	if (CPU_ISSUN4) {
		struct eeprom *eep = (struct eeprom *)eeprom_va;
		/*
		 * Assume this is the console if there's no eeprom info
		 * to be found.
		 */
		if (eep == NULL || eep->eeConsole == EE_CONS_COLOR)
			isconsole = 1;
	}

	/*
	 * When the ROM has mapped in a cgtwo display, the address
	 * maps only the video RAM, so in any case we have to map the
	 * registers ourselves.
	 */
	sc->sc_phys = ca->ca_ra.ra_reg[0];
	/* Apparently, the pixels are 32-bit data space */
	sc->sc_phys.rr_iospace = PMAP_VME32;

	sc->sc_reg = (volatile struct cg2statusreg *)
	    mapiodev(ca->ca_ra.ra_reg,
		CG2_ROPMEM_OFF + offsetof(struct cg2fb, status.reg),
		sizeof(struct cg2statusreg));

	sc->sc_ppmask = (volatile u_short *)
	    mapiodev(ca->ca_ra.ra_reg,
		CG2_ROPMEM_OFF + offsetof(struct cg2fb, ppmask.reg),
		sizeof(u_short));

	sc->sc_cmap = (volatile u_short *)
	    mapiodev(ca->ca_ra.ra_reg,
		     CG2_ROPMEM_OFF + offsetof(struct cg2fb, redmap),
		     3 * CG2_CMSIZE * sizeof(u_short));

	/* enable video */
	*sc->sc_ppmask = 0xffff;	/* enable all color planes... */
	cgtwo_burner(sc, 1, 0);		/* ... and video signals */

	fb_setsize(&sc->sc_sunfb, 8, 1152, 900, node, ca->ca_bustype);
	sc->sc_sunfb.sf_ro.ri_bits = mapiodev(&sc->sc_phys, CG2_PIXMAP_OFF,
	    round_page(sc->sc_sunfb.sf_fbsize));
	sc->sc_sunfb.sf_ro.ri_hw = sc;
	fbwscons_init(&sc->sc_sunfb, isconsole ? 0 : RI_CLEAR);
	fbwscons_setcolormap(&sc->sc_sunfb, cgtwo_setcolor);

	printf(": %dx%d\n", sc->sc_sunfb.sf_width, sc->sc_sunfb.sf_height);

	if (isconsole) {
		fbwscons_console_init(&sc->sc_sunfb, -1);
	}

	fbwscons_attach(&sc->sc_sunfb, &cgtwo_accessops, isconsole);
}
Esempio n. 13
0
File: agten.c Progetto: MarginC/kame
void
agtenattach(struct device *parent, struct device *self, void *args)
{
	struct agten_softc *sc = (struct agten_softc *)self;
	struct confargs *ca = args;
	struct wsemuldisplaydev_attach_args waa;
	int node, isconsole;
	char *nam;

	sc->sc_sunfb.sf_flags = self->dv_cfdata->cf_flags;

	node = ca->ca_ra.ra_node;
	nam = getpropstring(node, "model");
	printf(": model %s", nam);

	isconsole = node == fbnode;

	sc->sc_phys = ca->ca_ra.ra_reg[0];

	/*
	 * Map the various beasts of this card we are interested in.
	 */

	sc->sc_physoffset =
	    (off_t)getpropint(node, "i128_fb_physaddr", 0x8000000);
	sc->sc_i128_fb = mapiodev(ca->ca_ra.ra_reg, sc->sc_physoffset,
	    getpropint(node, "i128_fb_size", 0x400000));
	sc->sc_dac = mapiodev(ca->ca_ra.ra_reg,
	    getpropint(node, "p9100_reg_physaddr", 0x10a0000) + 0x200,
	    0x800 - 0x200);

	/*
	 * For some reason the agten does not use the canonical name for
	 * properties, but uses an ffb_ prefix; and the linebytes property is
	 * missing.
	 * The following is a specific version of
	 *   fb_setsize(&sc->sc_sunfb, 8, 1152, 900, node, BUS_SBUS);
	 * using the correct property names.
	 */
#ifdef notyet
	sc->sc_sunfb.sf_depth = 32;
#else
	sc->sc_sunfb.sf_depth = getpropint(node, "ffb_depth", 8);
#endif
	sc->sc_sunfb.sf_width = getpropint(node, "ffb_width", 1152);
	sc->sc_sunfb.sf_height = getpropint(node, "ffb_height", 900);
	sc->sc_sunfb.sf_linebytes =
	    roundup(sc->sc_sunfb.sf_width, sc->sc_sunfb.sf_depth) *
	        sc->sc_sunfb.sf_depth / 8;
	sc->sc_sunfb.sf_fbsize =
	    sc->sc_sunfb.sf_height * sc->sc_sunfb.sf_linebytes;

	printf(", %dx%d, depth %d\n",
	    sc->sc_sunfb.sf_width, sc->sc_sunfb.sf_height,
	    sc->sc_sunfb.sf_depth);

	sc->sc_sunfb.sf_ro.ri_bits = (void *)sc->sc_i128_fb;
	
	sc->sc_sunfb.sf_ro.ri_hw = sc;
	fbwscons_init(&sc->sc_sunfb, isconsole);
	fbwscons_setcolormap(&sc->sc_sunfb, agten_setcolor);

	agten_stdscreen.capabilities = sc->sc_sunfb.sf_ro.ri_caps;
	agten_stdscreen.nrows = sc->sc_sunfb.sf_ro.ri_rows;
	agten_stdscreen.ncols = sc->sc_sunfb.sf_ro.ri_cols;
	agten_stdscreen.textops = &sc->sc_sunfb.sf_ro.ri_ops;

	if (isconsole) {
		fbwscons_console_init(&sc->sc_sunfb, &agten_stdscreen, -1,
		    NULL);
	}

	sbus_establish(&sc->sc_sd, &sc->sc_sunfb.sf_dev);

	waa.console = isconsole;
	waa.scrdata = &agten_screenlist;
	waa.accessops = &agten_accessops;
	waa.accesscookie = sc;
	config_found(self, &waa, wsemuldisplaydevprint);
}
Esempio n. 14
0
void
tslot_attach(struct device *parent, struct device *self, void *args)
{
	struct confargs *ca = args;
	struct tslot_softc *sc = (struct tslot_softc *)self;
	struct romaux *ra;
	struct rom_range ranges[TS102_NUM_RANGES], *range;
	struct tslot_data *td;
	volatile u_int8_t *regs;
	int node, nranges, slot, rnum;

	ra = &ca->ca_ra;
	node = ra->ra_node;
	regs = mapiodev(&ra->ra_reg[0], 0, ra->ra_len);

	/*
	 * Find memory ranges
	 */
	nranges = getproplen(node, "ranges") / sizeof(struct rom_range);
	if (nranges < TS102_NUM_RANGES) {
		printf(": expected %d memory ranges, got %d\n",
		    TS102_NUM_RANGES, nranges);
		return;
	}
	getprop(node, "ranges", ranges, sizeof ranges);

	/*
	 * Ranges being relative to this sbus slot, turn them into absolute
	 * addresses.
	 */
	for (rnum = 0; rnum < TS102_NUM_RANGES; rnum++) {
		ranges[rnum].poffset -= TS102_OFFSET_REGISTERS;
	}

	sc->sc_ih.ih_fun = tslot_intr;
	sc->sc_ih.ih_arg = sc;
	intr_establish(ra->ra_intr[0].int_pri, &sc->sc_ih, -1, self->dv_xname);
	printf(" pri %d", ra->ra_intr[0].int_pri);

	printf(": %d slots\n", TS102_NUM_SLOTS);

	/*
	 * Setup asynchronous event handler
	 */
	sc->sc_events = 0;
	kthread_create_deferred(tslot_create_event_thread, sc);

	sc->sc_pct = (pcmcia_chipset_tag_t)&tslot_functions;

	/*
	 * Setup slots
	 */
	for (slot = 0; slot < TS102_NUM_SLOTS; slot++) {
		td = &sc->sc_slot[slot];
		for (rnum = 0; rnum < TS102_RANGE_CNT; rnum++) {
			range = ranges + (slot * TS102_RANGE_CNT + rnum);
			td->td_rr = ra->ra_reg[0];
			td->td_rr.rr_iospace = range->pspace;
			td->td_rr.rr_paddr = (void *)
			   ((u_int32_t)td->td_rr.rr_paddr + range->poffset);
			td->td_space[rnum] = (vaddr_t)mapiodev(&td->td_rr, 0,
			    TS102_ARBITRARY_MAP_SIZE);
		}
		td->td_parent = sc;
		td->td_regs = regs +
		    slot * (TS102_REG_CARD_B_INT - TS102_REG_CARD_A_INT);
		td->td_slot = slot;
		SET_TAG_LITTLE_ENDIAN(&td->td_rr);
		tslot_reset(td, TS102_ARBITRARY_MAP_SIZE);
	}
}
Esempio n. 15
0
static void
grackle_attach(device_t parent, device_t self, void *aux)
{
	struct grackle_softc *sc = device_private(self);
	pci_chipset_tag_t pc = &sc->sc_pc;
	struct confargs *ca = aux;
	struct pcibus_attach_args pba;
	int len, node = ca->ca_node;
	uint32_t busrange[2];
	struct ranges {
		uint32_t pci_hi, pci_mid, pci_lo;
		uint32_t host;
		uint32_t size_hi, size_lo;
	} ranges[6], *rp = ranges;

	aprint_normal("\n");
	sc->sc_dev = self;

	/* PCI bus number */
	if (OF_getprop(node, "bus-range", busrange, sizeof(busrange)) != 8)
		return;

	/* find i/o tag */
	len = OF_getprop(node, "ranges", ranges, sizeof(ranges));
	if (len == -1)
		return;
	while (len >= sizeof(ranges[0])) {
		if ((rp->pci_hi & OFW_PCI_PHYS_HI_SPACEMASK) ==
		     OFW_PCI_PHYS_HI_SPACE_IO) {
			sc->sc_iot.pbs_base = rp->host;
			sc->sc_iot.pbs_limit = rp->host + rp->size_lo;
			break;
		}
		len -= sizeof(ranges[0]);
		rp++;
	}

	sc->sc_iot.pbs_flags = _BUS_SPACE_LITTLE_ENDIAN|_BUS_SPACE_IO_TYPE;
	sc->sc_iot.pbs_offset = 0;
	if (ofwoea_map_space(RANGE_TYPE_PCI, RANGE_IO, node, &sc->sc_iot,
	    "grackle io") != 0)
		panic("Can't init grackle io tag");

	sc->sc_memt.pbs_flags = _BUS_SPACE_LITTLE_ENDIAN|_BUS_SPACE_MEM_TYPE;
	sc->sc_memt.pbs_base = 0x00000000;
	if (ofwoea_map_space(RANGE_TYPE_PCI, RANGE_MEM, node, &sc->sc_memt,
	    "grackle mem") != 0)
		panic("Can't init grackle mem tag");

	macppc_pci_get_chipset_tag(pc);
	pc->pc_node = node;
	pc->pc_addr = mapiodev(GRACKLE_ADDR, 4, false);
	pc->pc_data = mapiodev(GRACKLE_DATA, 4, false);
	pc->pc_bus = busrange[0];
	pc->pc_conf_read = grackle_conf_read;
	pc->pc_conf_write = grackle_conf_write;
	pc->pc_memt = &sc->sc_memt;
	pc->pc_iot = &sc->sc_iot;

	memset(&pba, 0, sizeof(pba));
	pba.pba_memt = pc->pc_memt;
	pba.pba_iot = pc->pc_iot;
	pba.pba_dmat = &pci_bus_dma_tag;
	pba.pba_dmat64 = NULL;
	pba.pba_bus = pc->pc_bus;
	pba.pba_bridgetag = NULL;
	pba.pba_pc = pc;
	pba.pba_flags = PCI_FLAGS_IO_OKAY | PCI_FLAGS_MEM_OKAY;

	config_found_ia(self, "pcibus", &pba, pcibusprint);
}
Esempio n. 16
0
void
presto_attach(struct device *parent, struct device *self, void *args)
{
	struct presto_softc *sc = (struct presto_softc *)self;
	struct confargs *ca = args;
	char *model, *submodel;
	u_int8_t status;

	/* Get card parameters */
	model = getpropstring(ca->ca_ra.ra_node, "model");
	if (*model == '\0')
		submodel = "fictitious";
	else {
		submodel = memchr(model, ',', strlen(model));
		if (submodel != NULL)
			submodel++;
		else
			submodel = model;
	}
	strncpy(sc->sc_model, submodel, 16);
	sc->sc_memsize = ca->ca_ra.ra_len;

	printf(": %s\n%s: %d MB NVRAM, ", model,
	    sc->sc_dev.dv_xname, sc->sc_memsize >> 20);

	/* Map memory */
	sc->sc_mem = (void *)mapiodev(ca->ca_ra.ra_reg, 0, sc->sc_memsize);

	/*
	 * Clear the ``disconnect battery'' bit.
	 */
	*(u_int8_t *)(sc->sc_mem + PSERVE_BATTERYSTATUS) = 0x00;

	/*
	 * Clear the ``unflushed data'' status. This way, if the card is
	 * reused under SunOS, the system will not try to flush whatever
	 * data the user put in the nvram...
	 */
	*(u_int8_t *)(sc->sc_mem + PSERVE_DATASTATUS) = 0x00;

	/*
	 * Decode battery status
	 */
	status = *(u_int8_t *)(sc->sc_mem + PSERVE_BATTERYSTATUS);
	printf("battery status %x ", status);
	if (ISSET(status, PSBAT_FAULT)) {
		printf("(non-working)");
	} else if (ISSET(status, PSBAT_CONNECTED)) {
		if (ISSET(status, PSBAT_CHARGING))
			printf("(charging)");
		else
			printf("(ok)");
	} else
		printf("(disabled)");
	printf("\n");

#ifdef DEBUG
	printf("%s: status codes %02.2x, %02.2x, %02.2x, %02.2x\n",
	    sc->sc_dev.dv_xname,
	    *(u_int8_t *)(sc->sc_mem + 0x03), *(u_int8_t *)(sc->sc_mem + 0x07),
	    *(u_int8_t *)(sc->sc_mem + 0x0b), *(u_int8_t *)(sc->sc_mem + 0x0f));
#endif

	sc->sc_dk.dk_driver = &presto_dk;
	sc->sc_dk.dk_name = sc->sc_dev.dv_xname;
	disk_attach(&sc->sc_dk);

	/* read the disk label immediately */
	presto_getdisklabel(sc);
}
Esempio n. 17
0
void
cgfourattach(struct device *parent, struct device *self, void *args)
{
	struct cgfour_softc *sc = (struct cgfour_softc *)self;
	struct confargs *ca = args;
	int node = 0;
	volatile struct bt_regs *bt;
	int isconsole = 0;

	printf(": p4");

	/* Map the pfour register. */
	SET(sc->sc_sunfb.sf_flags, FB_PFOUR);
	sc->sc_sunfb.sf_pfour = (volatile u_int32_t *)
		mapiodev(ca->ca_ra.ra_reg, 0, sizeof(u_int32_t));

	if (cputyp == CPU_SUN4) {
		struct eeprom *eep = (struct eeprom *)eeprom_va;

		/*
		 * Assume this is the console if there's no eeprom info
		 * to be found.
		 */
		if (eep == NULL || eep->eeConsole == EE_CONS_P4OPT)
			isconsole = 1;
	}

	/*
	 * When the ROM has mapped in a cgfour display, the address
	 * maps only the video RAM, so in any case we have to map the
	 * registers ourselves.  We only need the video RAM if we are
	 * going to print characters via rconsole.
	 */

	sc->sc_phys = ca->ca_ra.ra_reg[0];

	/* enable video */
	fb_pfour_burner(sc, 1, 0);
	bt = &sc->sc_fbc->fbc_dac;
	BT_INIT(bt, 24);

	/*
	 * XXX should initialize the enable plane, instead of expecting the
	 * PROM to do so for us
	 */

	fb_setsize(&sc->sc_sunfb, 8, 1152, 900, node, ca->ca_bustype);
	/*
	 * XXX this only maps the color plane, not the overlay or the enable
	 * planes
	 */
	sc->sc_sunfb.sf_ro.ri_bits = mapiodev(ca->ca_ra.ra_reg,
	    PFOUR_COLOR_OFF_COLOR, round_page(sc->sc_sunfb.sf_fbsize));
	sc->sc_sunfb.sf_ro.ri_hw = sc;
	fbwscons_init(&sc->sc_sunfb, isconsole ? 0 : RI_CLEAR);
	fbwscons_setcolormap(&sc->sc_sunfb, cgfour_setcolor);

	printf(", %dx%d\n", sc->sc_sunfb.sf_width, sc->sc_sunfb.sf_height);

	if (isconsole) {
		fbwscons_console_init(&sc->sc_sunfb, -1);
	}

	fbwscons_attach(&sc->sc_sunfb, &cgfour_accessops, isconsole);
}
Esempio n. 18
0
void
bmac_attach(struct device *parent, struct device *self, void *aux)
{
	struct confargs *ca = aux;
	struct bmac_softc *sc = (void *)self;
	struct ifnet *ifp = &sc->arpcom.ac_if;
	struct mii_data *mii = &sc->sc_mii;
	u_char laddr[6];
	int nseg, error;

	timeout_set(&sc->sc_tick_ch, bmac_mii_tick, sc);

	sc->sc_flags =0;
	if (strcmp(ca->ca_name, "ethernet") == 0) {
		sc->sc_flags |= BMAC_BMACPLUS;
	}

	ca->ca_reg[0] += ca->ca_baseaddr;
	ca->ca_reg[2] += ca->ca_baseaddr;
	ca->ca_reg[4] += ca->ca_baseaddr;

	sc->sc_regs = (vaddr_t)mapiodev(ca->ca_reg[0], NBPG);

	bmac_write_reg(sc, INTDISABLE, NoEventsMask);

	if (OF_getprop(ca->ca_node, "local-mac-address", laddr, 6) == -1 &&
	    OF_getprop(ca->ca_node, "mac-address", laddr, 6) == -1) {
		printf(": cannot get mac-address\n");
		return;
	}
	bcopy(laddr, sc->arpcom.ac_enaddr, 6);

	sc->sc_dmat = ca->ca_dmat;
	sc->sc_txdma = mapiodev(ca->ca_reg[2], 0x100);
	sc->sc_rxdma = mapiodev(ca->ca_reg[4], 0x100);
	sc->sc_txdbdma = dbdma_alloc(sc->sc_dmat, BMAC_TXBUFS);
	sc->sc_txcmd = sc->sc_txdbdma->d_addr;
	sc->sc_rxdbdma = dbdma_alloc(sc->sc_dmat, BMAC_RXBUFS + 1);
	sc->sc_rxcmd = sc->sc_rxdbdma->d_addr;

	error = bus_dmamem_alloc(sc->sc_dmat, BMAC_BUFSZ,
	    PAGE_SIZE, 0, sc->sc_bufseg, 1, &nseg, BUS_DMA_NOWAIT);
	if (error) {
		printf(": cannot allocate buffers (%d)\n", error);
		return;
	}

	error = bus_dmamem_map(sc->sc_dmat, sc->sc_bufseg, nseg,
	    BMAC_BUFSZ, &sc->sc_txbuf, BUS_DMA_NOWAIT);
	if (error) {
		printf(": cannot map buffers (%d)\n", error);
		bus_dmamem_free(sc->sc_dmat, sc->sc_bufseg, 1);
		return;
	}

	error = bus_dmamap_create(sc->sc_dmat, BMAC_BUFSZ, 1, BMAC_BUFSZ, 0,
	    BUS_DMA_NOWAIT | BUS_DMA_ALLOCNOW, &sc->sc_bufmap);
	if (error) {
		printf(": cannot create buffer dmamap (%d)\n", error);
		bus_dmamem_unmap(sc->sc_dmat, sc->sc_txbuf, BMAC_BUFSZ);
		bus_dmamem_free(sc->sc_dmat, sc->sc_bufseg, 1);
		return;
	}

	error = bus_dmamap_load(sc->sc_dmat, sc->sc_bufmap, sc->sc_txbuf,
	    BMAC_BUFSZ, NULL, BUS_DMA_NOWAIT);
	if (error) {
		printf(": cannot load buffers dmamap (%d)\n", error);
		bus_dmamap_destroy(sc->sc_dmat, sc->sc_bufmap);
		bus_dmamem_unmap(sc->sc_dmat, sc->sc_txbuf, BMAC_BUFSZ);
		bus_dmamem_free(sc->sc_dmat, sc->sc_bufseg, nseg);
		return;
	}

	sc->sc_txbuf_pa = sc->sc_bufmap->dm_segs->ds_addr;
	sc->sc_rxbuf = sc->sc_txbuf + BMAC_BUFLEN * BMAC_TXBUFS;
	sc->sc_rxbuf_pa = sc->sc_txbuf_pa + BMAC_BUFLEN * BMAC_TXBUFS;

	printf(" irq %d,%d: address %s\n", ca->ca_intr[0], ca->ca_intr[2],
		ether_sprintf(laddr));

	mac_intr_establish(parent, ca->ca_intr[0], IST_LEVEL, IPL_NET,
	    bmac_intr, sc, sc->sc_dev.dv_xname);
	mac_intr_establish(parent, ca->ca_intr[2], IST_LEVEL, IPL_NET,
	    bmac_rint, sc, sc->sc_dev.dv_xname);

	bcopy(sc->sc_dev.dv_xname, ifp->if_xname, IFNAMSIZ);
	ifp->if_softc = sc;
	ifp->if_ioctl = bmac_ioctl;
	ifp->if_start = bmac_start;
	ifp->if_flags =
		IFF_BROADCAST | IFF_SIMPLEX | IFF_NOTRAILERS | IFF_MULTICAST;
	ifp->if_watchdog = bmac_watchdog;
	IFQ_SET_READY(&ifp->if_snd);

	mii->mii_ifp = ifp;
	mii->mii_readreg = bmac_mii_readreg;
	mii->mii_writereg = bmac_mii_writereg;
	mii->mii_statchg = bmac_mii_statchg;

	ifmedia_init(&mii->mii_media, 0, bmac_mediachange, bmac_mediastatus);
	mii_attach(&sc->sc_dev, mii, 0xffffffff, MII_PHY_ANY,
	    MII_OFFSET_ANY, 0);

	/* Choose a default media. */
	if (LIST_FIRST(&mii->mii_phys) == NULL) {
		ifmedia_add(&mii->mii_media, IFM_ETHER|IFM_10_T, 0, NULL);
		ifmedia_set(&mii->mii_media, IFM_ETHER|IFM_10_T);
	} else
		ifmedia_set(&mii->mii_media, IFM_ETHER|IFM_AUTO);

	bmac_reset_chip(sc);

	if_attach(ifp);
	ether_ifattach(ifp);
}
Esempio n. 19
0
void
p9000attach(struct device *parent, struct device *self, void *args)
{
    struct p9000_softc *sc = (struct p9000_softc *)self;
    struct confargs *ca = args;
    int node, pri, row, isconsole, scr;
    struct device *btdev;
    extern struct cfdriver btcham_cd;

    pri = ca->ca_ra.ra_intr[0].int_pri;
    printf(" pri %d", pri);

#ifdef DIAGNOSTIC
    if (ca->ca_ra.ra_nreg < P9000_NREG) {
        printf(": expected %d registers, got only %d\n",
               P9000_NREG, ca->ca_ra.ra_nreg);
        return;
    }
#endif

    /*
     * Find the RAMDAC device. It should have attached before, since it
     * attaches at obio. If, for some reason, it did not, it's not worth
     * going any further.
     *
     * We rely upon the PROM to properly initialize the RAMDAC in a safe
     * mode.
     */
    btdev = btcham_cd.cd_ndevs != 0 ? btcham_cd.cd_devs[0] : NULL;
    if (btdev != NULL)
        sc->sc_ramdac = ((struct bt445_softc *)btdev)->sc_regs;

    if (sc->sc_ramdac == NULL) {
        printf(": bt445 did not attach previously\n");
        return;
    }

    sc->sc_phys = ca->ca_ra.ra_reg[P9000_REG_VRAM];

    sc->sc_ctl = mapiodev(&(ca->ca_ra.ra_reg[P9000_REG_CTL]), 0,
                          ca->ca_ra.ra_reg[0].rr_len);
    sc->sc_cmd = mapiodev(&(ca->ca_ra.ra_reg[P9000_REG_CMD]), 0,
                          ca->ca_ra.ra_reg[1].rr_len);

    node = ca->ca_ra.ra_node;
    isconsole = node == fbnode;

    fb_setsize(&sc->sc_sunfb, 8, 640, 480, node, ca->ca_bustype);
    sc->sc_sunfb.sf_ro.ri_bits = mapiodev(&sc->sc_phys, 0,
                                          round_page(sc->sc_sunfb.sf_fbsize));
    sc->sc_sunfb.sf_ro.ri_hw = sc;

    P9000_SELECT_SCR(sc);
    scr = P9000_READ_CTL(sc, P9000_SYSTEM_CONFIG);

    printf(": rev %x, %dx%d\n", scr & SCR_ID_MASK,
           sc->sc_sunfb.sf_width, sc->sc_sunfb.sf_height);

    /* Disable frame buffer interrupts */
    P9000_SELECT_SCR(sc);
    P9000_WRITE_CTL(sc, P9000_INTERRUPT_ENABLE, IER_MASTER_ENABLE | 0);

    sc->sc_ih.ih_fun = p9000_intr;
    sc->sc_ih.ih_arg = sc;
    intr_establish(pri, &sc->sc_ih, IPL_FB, self->dv_xname);

    /*
     * If the framebuffer width is under 1024x768, we will switch from the
     * PROM font to the more adequate 8x16 font here.
     * However, we need to adjust two things in this case:
     * - the display row should be overrided from the current PROM metrics,
     *   to prevent us from overwriting the last few lines of text.
     * - if the 80x34 screen would make a large margin appear around it,
     *   choose to clear the screen rather than keeping old prom output in
     *   the margins.
     * XXX there should be a rasops "clear margins" feature
     */
    fbwscons_init(&sc->sc_sunfb,
                  isconsole && (sc->sc_sunfb.sf_width >= 1024) ? 0 : RI_CLEAR);
    fbwscons_setcolormap(&sc->sc_sunfb, p9000_setcolor);

    /*
     * Plug-in accelerated console operations.
     */
    if (sc->sc_sunfb.sf_dev.dv_cfdata->cf_flags != 0)
        p9000_ras_init(sc);

    /* enable video */
    p9000_burner(sc, 1, 0);

    if (isconsole) {
        if (sc->sc_sunfb.sf_width < 1024)
            row = 0;	/* screen has been cleared above */
        else
            row = -1;

        fbwscons_console_init(&sc->sc_sunfb, row);
    }

    fbwscons_attach(&sc->sc_sunfb, &p9000_accessops, isconsole);
}
Esempio n. 20
0
/*
 * Attach this instance, and then all the sub-devices
 */
void
espattach(device_t parent, device_t self, void *aux)
{
	struct esp_softc *esc = device_private(self);
	struct ncr53c9x_softc *sc = &esc->sc_ncr53c9x;
	struct confargs *ca = aux;
	u_int *reg;
	int sz;

	/*
	 * Set up glue for MI code early; we use some of it here.
	 */
	sc->sc_dev = self;
	sc->sc_glue = &esp_glue;

	esc->sc_node = ca->ca_node;
	esc->sc_pri = ca->ca_intr[0];
	aprint_normal(" irq %d", esc->sc_pri);

	/*
	 * Map my registers in.
	 */
	reg = ca->ca_reg;
	esc->sc_reg =    mapiodev(ca->ca_baseaddr + reg[0], reg[1]);
	esc->sc_dmareg = mapiodev(ca->ca_baseaddr + reg[2], reg[3]);

	/* Allocate 16-byte aligned DMA command space */
	esc->sc_dmacmd = dbdma_alloc(sizeof(dbdma_command_t) * 20);

	/* Other settings */
	sc->sc_id = 7;
	sz = OF_getprop(ca->ca_node, "clock-frequency",
	    &sc->sc_freq, sizeof(int));
	if (sz != sizeof(int))
		sc->sc_freq = 25000000;

	/* gimme MHz */
	sc->sc_freq /= 1000000;

	/* esc->sc_dma->sc_esp = esc;*/

	/*
	 * XXX More of this should be in ncr53c9x_attach(), but
	 * XXX should we really poke around the chip that much in
	 * XXX the MI code?  Think about this more...
	 */

	/*
	 * Set up static configuration info.
	 */
	sc->sc_cfg1 = sc->sc_id | NCRCFG1_PARENB;
	sc->sc_cfg2 = NCRCFG2_SCSI2; /* | NCRCFG2_FE */
	sc->sc_cfg3 = NCRCFG3_CDB;
	sc->sc_rev = NCR_VARIANT_NCR53C94;

	/*
	 * XXX minsync and maxxfer _should_ be set up in MI code,
	 * XXX but it appears to have some dependency on what sort
	 * XXX of DMA we're hooked up to, etc.
	 */

	/*
	 * This is the value used to start sync negotiations
	 * Note that the NCR register "SYNCTP" is programmed
	 * in "clocks per byte", and has a minimum value of 4.
	 * The SCSI period used in negotiation is one-fourth
	 * of the time (in nanoseconds) needed to transfer one byte.
	 * Since the chip's clock is given in MHz, we have the following
	 * formula: 4 * period = (1000 / freq) * 4
	 */
	sc->sc_minsync = 1000 / sc->sc_freq;

	sc->sc_maxxfer = 64 * 1024;

	/* and the interuppts */
	intr_establish(esc->sc_pri, IST_EDGE, IPL_BIO, ncr53c9x_intr, sc);

	/* Reset SCSI bus when halt. */
	shutdownhook_establish(esp_shutdownhook, sc);

	/* Do the common parts of attachment. */
	sc->sc_adapter.adapt_minphys = minphys;
	sc->sc_adapter.adapt_request = ncr53c9x_scsipi_request;
	ncr53c9x_attach(sc);

	/* Turn on target selection using the `DMA' method */
	sc->sc_features |= NCR_F_DMASELECT;
}
Esempio n. 21
0
/*
 * Attach a display.  We need to notice if it is the console, too.
 */
static void
cgeightattach(struct device *parent, struct device *self, void *aux)
{
#if defined(SUN4)
	union obio_attach_args *uoba = aux;
	struct obio4_attach_args *oba = &uoba->uoba_oba4;
	struct cgeight_softc *sc = device_private(self);
	struct fbdevice *fb = &sc->sc_fb;
	bus_space_handle_t bh;
	volatile struct bt_regs *bt;
	int ramsize, i, isconsole;

	sc->sc_bustag = oba->oba_bustag;
	sc->sc_paddr = (bus_addr_t)oba->oba_paddr;

	/* Map the pfour register. */
	if (bus_space_map(oba->oba_bustag, oba->oba_paddr,
			  sizeof(uint32_t),
			  BUS_SPACE_MAP_LINEAR,
			  &bh) != 0) {
		printf("%s: cannot map pfour register\n", self->dv_xname);
		return;
	}
	fb->fb_pfour = (volatile uint32_t *)bh;

	fb->fb_driver = &cgeightfbdriver;
	fb->fb_device = &sc->sc_dev;
	fb->fb_type.fb_type = FBTYPE_MEMCOLOR;
	fb->fb_flags = device_cfdata(&sc->sc_dev)->cf_flags & FB_USERMASK;
	fb->fb_flags |= FB_PFOUR;

	ramsize = PFOUR_COLOR_OFF_END - PFOUR_COLOR_OFF_OVERLAY;

	fb->fb_type.fb_depth = 24;
	fb_setsize_eeprom(fb, fb->fb_type.fb_depth, 1152, 900);

	sc->sc_fb.fb_type.fb_cmsize = 256;
	sc->sc_fb.fb_type.fb_size = ramsize;
	printf(": cgeight/p4, %d x %d",
		fb->fb_type.fb_width,
		fb->fb_type.fb_height);

	isconsole = 0;

	if (CPU_ISSUN4) {
		struct eeprom *eep = (struct eeprom *)eeprom_va;

		/*
		 * Assume this is the console if there's no eeprom info
		 * to be found.
		 */
		if (eep == NULL || eep->eeConsole == EE_CONS_P4OPT)
			isconsole = fb_is_console(0);
	}

#if 0
	/*
	 * We don't do any of the console handling here.  Instead,
	 * we let the bwtwo driver pick up the overlay plane and
	 * use it instead.  Rconsole should have better performance
	 * with the 1-bit depth.
	 *      -- Jason R. Thorpe <*****@*****.**>
	 */

	/*
	 * When the ROM has mapped in a cgfour display, the address
	 * maps only the video RAM, so in any case we have to map the
	 * registers ourselves.  We only need the video RAM if we are
	 * going to print characters via rconsole.
	 */

	if (isconsole) {
		/* XXX this is kind of a waste */
		fb->fb_pixels = mapiodev(ca->ca_ra.ra_reg,
					 PFOUR_COLOR_OFF_OVERLAY, ramsize);
	}
#endif

	/* Map the Brooktree. */
	if (bus_space_map(oba->oba_bustag,
			  oba->oba_paddr + PFOUR_COLOR_OFF_CMAP,
			  sizeof(struct fbcontrol),
			  BUS_SPACE_MAP_LINEAR,
			  &bh) != 0) {
		printf("%s: cannot map control registers\n", self->dv_xname);
		return;
	}
	sc->sc_fbc = (volatile struct fbcontrol *)bh;

#if 0	/* XXX thorpej ??? */
	/* tell the enable plane to look at the mono image */
	memset(ca->ca_ra.ra_vaddr, 0xff,
	    sc->sc_fb.fb_type.fb_width * sc->sc_fb.fb_type.fb_height / 8);
#endif

	/* grab initial (current) color map */
	bt = &sc->sc_fbc->fbc_dac;
	bt->bt_addr = 0;
	for (i = 0; i < 256 * 3 / 4; i++)
		sc->sc_cmap.cm_chip[i] = bt->bt_cmap;

	BT_INIT(bt, 0);

#if 0	/* see above */
	if (isconsole) {
		printf(" (console)\n");
#if defined(RASTERCONSOLE) && 0	/* XXX been told it doesn't work well. */
		fbrcons_init(fb);
#endif
	} else
#endif /* 0 */
		printf("\n");

	/*
	 * Even though we're not using rconsole, we'd still like
	 * to notice if we're the console framebuffer.
	 */
	fb_attach(&sc->sc_fb, isconsole);
#endif
}
Esempio n. 22
0
/*
 * Attach a found zs.
 *
 * Match slave number to zs unit number, so that misconfiguration will
 * not set up the keyboard as ttya, etc.
 */
void
zsc_attach(struct device *parent, struct device *self, void *aux)
{
	struct zsc_softc *zsc = (void *)self;
	struct confargs *ca = aux;
	struct zsc_attach_args zsc_args;
	volatile struct zschan *zc;
	struct xzs_chanstate *xcs;
	struct zs_chanstate *cs;
	struct zsdevice *zsd;
	int zsc_unit, channel;
	int s, theflags;
	int node, intr[3][3];
	u_int regs[16];

	zsc_unit = zsc->zsc_dev.dv_unit;

	zsd = mapiodev(ca->ca_baseaddr + ca->ca_reg[0], ca->ca_reg[1]);
	node = OF_child(ca->ca_node);	/* ch-a */

	for (channel = 0; channel < 2; channel++) {
		if (OF_getprop(node, "AAPL,interrupts",
			       intr[channel], sizeof(intr[0])) == -1 &&
		    OF_getprop(node, "interrupts",
			       intr[channel], sizeof(intr[0])) == -1) {
			printf(": cannot find interrupt property\n");
			return;
		}

		if (OF_getprop(node, "reg", regs, sizeof(regs)) < 24) {
			printf(": cannot find reg property\n");
			return;
		}
		regs[2] += ca->ca_baseaddr;
		regs[4] += ca->ca_baseaddr;
#ifdef ZS_TXDMA
		zsc->zsc_txdmareg[channel] = mapiodev(regs[2], regs[3]);
		zsc->zsc_txdmacmd[channel] =
			dbdma_alloc(sizeof(dbdma_command_t) * 3);
		memset(zsc->zsc_txdmacmd[channel], 0,
			sizeof(dbdma_command_t) * 3);
		dbdma_reset(zsc->zsc_txdmareg[channel]);
#endif
		node = OF_peer(node);	/* ch-b */
	}

	printf(": irq %d,%d\n", intr[0][0], intr[1][0]);

	/*
	 * Initialize software state for each channel.
	 */
	for (channel = 0; channel < 2; channel++) {
		zsc_args.channel = channel;
		zsc_args.hwflags = zs_hwflags[zsc_unit][channel];
		xcs = &zsc->xzsc_xcs_store[channel];
		cs  = &xcs->xzs_cs;
		zsc->zsc_cs[channel] = cs;

		cs->cs_channel = channel;
		cs->cs_private = NULL;
		cs->cs_ops = &zsops_null;

		zc = (channel == 0) ? &zsd->zs_chan_a : &zsd->zs_chan_b;

		cs->cs_reg_csr  = &zc->zc_csr;
		cs->cs_reg_data = &zc->zc_data;

		memcpy(cs->cs_creg, zs_init_reg, 16);
		memcpy(cs->cs_preg, zs_init_reg, 16);

		/* Current BAUD rate generator clock. */
		/* RTxC is 230400*16, so use 230400 */
		cs->cs_brg_clk = PCLK / 16;
		if (zsc_args.hwflags & ZS_HWFLAG_CONSOLE)
			cs->cs_defspeed = zs_get_speed(cs);
		else
			cs->cs_defspeed =
			    zs_defspeed[zsc_unit][channel];
		cs->cs_defcflag = zs_def_cflag;

		/* Make these correspond to cs_defcflag (-crtscts) */
		cs->cs_rr0_dcd = ZSRR0_DCD;
		cs->cs_rr0_cts = 0;
		cs->cs_wr5_dtr = ZSWR5_DTR;
		cs->cs_wr5_rts = 0;

#ifdef __notyet__
		cs->cs_slave_type = ZS_SLAVE_NONE;
#endif

		/* Define BAUD rate stuff. */
		xcs->cs_clocks[0].clk = PCLK;
		xcs->cs_clocks[0].flags = ZSC_RTXBRG | ZSC_RTXDIV;
		xcs->cs_clocks[1].flags =
			ZSC_RTXBRG | ZSC_RTXDIV | ZSC_VARIABLE | ZSC_EXTERN;
		xcs->cs_clocks[2].flags = ZSC_TRXDIV | ZSC_VARIABLE;
		xcs->cs_clock_count = 3;
		if (channel == 0) {
			theflags = 0; /*mac68k_machine.modem_flags;*/
			/*xcs->cs_clocks[1].clk = mac68k_machine.modem_dcd_clk;*/
			/*xcs->cs_clocks[2].clk = mac68k_machine.modem_cts_clk;*/
			xcs->cs_clocks[1].clk = 0;
			xcs->cs_clocks[2].clk = 0;
		} else {
			theflags = 0; /*mac68k_machine.print_flags;*/
			xcs->cs_clocks[1].flags = ZSC_VARIABLE;
			/*
			 * Yes, we aren't defining ANY clock source enables for the
			 * printer's DCD clock in. The hardware won't let us
			 * use it. But a clock will freak out the chip, so we
			 * let you set it, telling us to bar interrupts on the line.
			 */
			/*xcs->cs_clocks[1].clk = mac68k_machine.print_dcd_clk;*/
			/*xcs->cs_clocks[2].clk = mac68k_machine.print_cts_clk;*/
			xcs->cs_clocks[1].clk = 0;
			xcs->cs_clocks[2].clk = 0;
		}
		if (xcs->cs_clocks[1].clk)
			zsc_args.hwflags |= ZS_HWFLAG_NO_DCD;
		if (xcs->cs_clocks[2].clk)
			zsc_args.hwflags |= ZS_HWFLAG_NO_CTS;

		/* Set defaults in our "extended" chanstate. */
		xcs->cs_csource = 0;
		xcs->cs_psource = 0;
		xcs->cs_cclk_flag = 0;  /* Nothing fancy by default */
		xcs->cs_pclk_flag = 0;

		if (theflags & ZSMAC_RAW) {
			zsc_args.hwflags |= ZS_HWFLAG_RAW;
			printf(" (raw defaults)");
		}

		/*
		 * XXX - This might be better done with a "stub" driver
		 * (to replace zstty) that ignores LocalTalk for now.
		 */
		if (theflags & ZSMAC_LOCALTALK) {
			printf(" shielding from LocalTalk");
			cs->cs_defspeed = 1;
			cs->cs_creg[ZSRR_BAUDLO] = cs->cs_preg[ZSRR_BAUDLO] = 0xff;
			cs->cs_creg[ZSRR_BAUDHI] = cs->cs_preg[ZSRR_BAUDHI] = 0xff;
			zs_write_reg(cs, ZSRR_BAUDLO, 0xff);
			zs_write_reg(cs, ZSRR_BAUDHI, 0xff);
			/*
			 * If we might have LocalTalk, then make sure we have the
			 * Baud rate low-enough to not do any damage.
			 */
		}

		/*
		 * We used to disable chip interrupts here, but we now
		 * do that in zscnprobe, just in case MacOS left the chip on.
		 */
		
		xcs->cs_chip = 0;
		
		/* Stash away a copy of the final H/W flags. */
		xcs->cs_hwflags = zsc_args.hwflags;
		
		/*
		 * Look for a child driver for this channel.
		 * The child attach will setup the hardware.
		 */
		if (!config_found(self, (void *)&zsc_args, zsc_print)) {
			/* No sub-driver.  Just reset it. */
			u_char reset = (channel == 0) ?
				ZSWR9_A_RESET : ZSWR9_B_RESET;
			s = splzs();
			zs_write_reg(cs, 9, reset);
			splx(s);
		}
	}

	/* XXX - Now safe to install interrupt handlers. */
	mac_intr_establish(parent, intr[0][0], IST_LEVEL, IPL_TTY,
	    zshard, NULL, "zs0");
	mac_intr_establish(parent, intr[1][0], IST_LEVEL, IPL_TTY,
	    zshard, NULL, "zs1");
#ifdef ZS_TXDMA
	mac_intr_establish(parent, intr[0][1], IST_LEVEL, IPL_TTY,
	    zs_txdma_int, (void *)0, "zsdma0");
	mac_intr_establish(parent, intr[1][1], IST_LEVEL, IPL_TTY,
	    zs_txdma_int, (void *)1, "zsdma1");
#endif
	zsc->zsc_softintr = softintr_establish(IPL_SOFTTTY, zssoft, zsc);
	if (zsc->zsc_softintr == NULL)
		panic("zsattach: could not establish soft interrupt");

	/*
	 * Set the master interrupt enable and interrupt vector.
	 * (common to both channels, do it on A)
	 */
	cs = zsc->zsc_cs[0];
	s = splzs();
	/* interrupt vector */
	zs_write_reg(cs, 2, zs_init_reg[2]);
	/* master interrupt control (enable) */
	zs_write_reg(cs, 9, zs_init_reg[9]);
	splx(s);

	/* connect power management for port 0 */
	cs->enable = zs_enable;
	cs->disable = zs_disable;
}
Esempio n. 23
0
/*
 * Attach all the sub-devices we can find
 */
void
macobio_attach(struct device *parent, struct device *self, void *aux)
{
	struct macobio_softc *sc = (struct macobio_softc *)self;
	struct pci_attach_args *pa = aux;
	struct confargs ca;
	int node, child, namelen;
	u_int32_t reg[20];
	int32_t intr[8];
	char name[32];
	int need_interrupt_controller = 0;

	sc->sc_id = pa->pa_id; /* save of type for later */

	switch (PCI_PRODUCT(pa->pa_id)) {

	/* XXX should not use name */
	case PCI_PRODUCT_APPLE_GC:
		node = OF_finddevice("/bandit/gc");
		need_interrupt_controller = 1;
		break;

	case PCI_PRODUCT_APPLE_OHARE:
		node = OF_finddevice("/bandit/ohare");
		need_interrupt_controller = 1;
		break;

	case PCI_PRODUCT_APPLE_HEATHROW:
	case PCI_PRODUCT_APPLE_PADDINGTON:
		node = OF_finddevice("mac-io");
		if (node == -1)
			node = OF_finddevice("/pci/mac-io");
		if (OF_getprop(node, "assigned-addresses", reg, sizeof(reg))
			== (sizeof (reg[0]) * 5))
		{
			/* always ??? */
			heathrow_FCR = mapiodev(reg[2] + HEATHROW_FCR_OFFSET,
			    4);
		}
		break;
	case PCI_PRODUCT_APPLE_KEYLARGO:
	case PCI_PRODUCT_APPLE_INTREPID:
	case PCI_PRODUCT_APPLE_PANGEA_MACIO:
	case PCI_PRODUCT_APPLE_SHASTA:
	case PCI_PRODUCT_APPLE_K2_MACIO:
		node = OF_finddevice("mac-io");
		if (node == -1)
			node = OF_finddevice("/pci/mac-io");
		if (OF_getprop(node, "assigned-addresses", reg, sizeof(reg))
		    == (sizeof (reg[0]) * 5))
			 sc->obiomem = mapiodev(reg[2], 0x100);
		break;
	default:
		printf(": unknown macobio controller\n");
		return;
	}
	sc->sc_node = node;

	if (OF_getprop(node, "assigned-addresses", reg, sizeof(reg)) < 12)
		return;

	ca.ca_baseaddr = reg[2];

	sc->sc_membus_space.bus_base = ca.ca_baseaddr;

	ca.ca_iot = &sc->sc_membus_space;
	ca.ca_dmat = pa->pa_dmat;

	printf("\n");

	/*
	 * This might be a hack, but it makes the interrupt controller
	 * attach as expected if a device node existed in the OF tree.
	 */
	if (need_interrupt_controller) {
		/* force attachment of legacy interrupt controllers */
		ca.ca_name = "legacy-interrupt-controller";
		ca.ca_node = 0;

		ca.ca_nreg  = 0;
		ca.ca_nintr = 0;

		ca.ca_reg = NULL;
		ca.ca_intr = NULL;

		config_found(self, &ca, macobio_print);
	}

	for (child = OF_child(node); child; child = OF_peer(child)) {
		namelen = OF_getprop(child, "name", name, sizeof(name));
		if (namelen < 0)
			continue;
		if (namelen >= sizeof(name))
			continue;

		name[namelen] = 0;
		ca.ca_name = name;
		ca.ca_node = child;

		ca.ca_nreg  = OF_getprop(child, "reg", reg, sizeof(reg));
		ca.ca_nintr = OF_getprop(child, "AAPL,interrupts", intr,
				sizeof(intr));
		if (ca.ca_nintr == -1)
			ca.ca_nintr = OF_getprop(child, "interrupts", intr,
					sizeof(intr));

		ca.ca_reg = reg;
		ca.ca_intr = intr;

		config_found(self, &ca, macobio_print);
	}
}
Esempio n. 24
0
void
bwtwoattach(struct device *parent, struct device *self, void *args)
{
	struct bwtwo_softc *sc = (struct bwtwo_softc *)self;
	struct confargs *ca = args;
	int node = ca->ca_ra.ra_node;
	int isconsole = 0;
	int sbus = 1;
	char *nam;

	printf(": ");

	/*
	 * Map the control register.
	 */
#if defined(SUN4)
	if (CPU_ISSUN4 && ca->ca_bustype == BUS_OBIO &&
	    fb_pfour_id(ca->ca_ra.ra_vaddr) != PFOUR_NOTPFOUR) {
		SET(sc->sc_sunfb.sf_flags, FB_PFOUR);
		sc->sc_sunfb.sf_pfour = (volatile u_int32_t *)
		    mapiodev(ca->ca_ra.ra_reg, 0, sizeof(u_int32_t));
	} else
#endif
	{
		sc->sc_reg = (volatile struct fbcontrol *)
		    mapiodev(ca->ca_ra.ra_reg, BWREG_REG,
			     sizeof(struct fbcontrol));
	}

	/* Set up default pixel offset.  May be changed below. */
	sc->sc_pixeloffset = BWREG_MEM;

	switch (ca->ca_bustype) {
	case BUS_OBIO:
		if (CPU_ISSUN4M)	/* 4m has framebuffer on obio */
			goto obp_name;

		sbus = node = 0;
#if defined(SUN4)
		if (ISSET(sc->sc_sunfb.sf_flags, FB_PFOUR)) {
			nam = "p4";
			sc->sc_pixeloffset = PFOUR_BW_OFF;
		} else
#endif
			nam = NULL;
		break;

	case BUS_VME32:
	case BUS_VME16:
		sbus = node = 0;
		nam = NULL;
		break;

	case BUS_SBUS:
obp_name:
#if defined(SUN4C) || defined(SUN4M)
		nam = getpropstring(node, "model");
#endif
		break;
	}

	if (nam != NULL && *nam != '\0')
		printf("%s, ", nam);

#if defined(SUN4)
	if (CPU_ISSUN4) {
		struct eeprom *eep = (struct eeprom *)eeprom_va;
		int constype = ISSET(sc->sc_sunfb.sf_flags, FB_PFOUR) ?
		    EE_CONS_P4OPT : EE_CONS_BW;
		/*
		 * Assume this is the console if there's no eeprom info
		 * to be found.
		 */
		if (eep == NULL || eep->eeConsole == constype)
			isconsole = 1;
		else
		/*
		 * On sun4 systems without on-board framebuffers (such as
		 * the 4/3xx models), the PROM will accept the EE_CONS_BW
		 * setting although the framebuffer is a P4.
		 * Accept this setting as well.
		 */
		if (eep->eeConsole == EE_CONS_BW)
			isconsole = 1;
	}
#endif

	if (CPU_ISSUN4COR4M)
		isconsole = node == fbnode;

	sc->sc_phys = ca->ca_ra.ra_reg[0];
	sc->sc_bustype = ca->ca_bustype;

	/* enable video */
	bwtwo_burner(sc, 1, 0);

	fb_setsize(&sc->sc_sunfb, 1, 1152, 900, node, ca->ca_bustype);
	printf("%dx%d\n", sc->sc_sunfb.sf_width, sc->sc_sunfb.sf_height);

	sc->sc_sunfb.sf_ro.ri_bits = mapiodev(ca->ca_ra.ra_reg,
	    sc->sc_pixeloffset, round_page(sc->sc_sunfb.sf_fbsize));
	sc->sc_sunfb.sf_ro.ri_hw = sc;
	fbwscons_init(&sc->sc_sunfb, isconsole ? 0 : RI_CLEAR);

	if (isconsole) {
		fbwscons_console_init(&sc->sc_sunfb, -1);
	}

	fbwscons_attach(&sc->sc_sunfb, &bwtwo_accessops, isconsole);
}
Esempio n. 25
0
/*
 * Attach this instance, and then all the sub-devices
 */
void
espattach(struct device *parent, struct device *self, void *aux)
{
	struct confargs *ca = aux;
	struct esp_softc *esc = (void *)self;
	struct ncr53c9x_softc *sc = &esc->sc_ncr53c9x;
	u_int *reg;
	int sz, error;

	/*
	 * Set up glue for MI code early; we use some of it here.
	 */
	sc->sc_glue = &esp_glue;

	esc->sc_node = ca->ca_node;
	esc->sc_intr = ca->ca_intr[0];
	printf(" irq %d", esc->sc_intr);

	/*
	 * Map my registers in.
	 */
	reg = ca->ca_reg;
	esc->sc_reg = mapiodev(ca->ca_baseaddr + reg[0], reg[1]);
	esc->sc_dmareg = mapiodev(ca->ca_baseaddr + reg[2], reg[3]);

	esc->sc_dmat = ca->ca_dmat;
	if ((error = bus_dmamap_create(esc->sc_dmat,
	    ESP_DMALIST_MAX * DBDMA_COUNT_MAX, ESP_DMALIST_MAX,
	    DBDMA_COUNT_MAX, NBPG, BUS_DMA_NOWAIT, &esc->sc_dmamap)) != 0) {
		printf(": cannot create dma map, error = %d\n", error);
		return;
	}

	/* Allocate 16-byte aligned DMA command space */
	esc->sc_dbdma = dbdma_alloc(esc->sc_dmat, ESP_DMALIST_MAX);
	esc->sc_dmacmd = esc->sc_dbdma->d_addr;

	/* Other settings */
	sc->sc_id = 7;
	sz = OF_getprop(ca->ca_node, "clock-frequency",
		&sc->sc_freq, sizeof(int));
	if (sz != sizeof(int))
		sc->sc_freq = 25000000;

	/* gimme MHz */
	sc->sc_freq /= 1000000;

	/*
	 * Set up static configuration info.
	 */
	sc->sc_cfg1 = sc->sc_id | NCRCFG1_PARENB;
	sc->sc_cfg2 = NCRCFG2_SCSI2; /* | NCRCFG2_FE */
	sc->sc_cfg3 = NCRCFG3_CDB;
	sc->sc_rev = NCR_VARIANT_NCR53C94;

	/*
	 * This is the value used to start sync negotiations
	 * Note that the NCR register "SYNCTP" is programmed
	 * in "clocks per byte", and has a minimum value of 4.
	 * The SCSI period used in negotiation is one-fourth
	 * of the time (in nanoseconds) needed to transfer one byte.
	 * Since the chip's clock is given in MHz, we have the following
	 * formula: 4 * period = (1000 / freq) * 4
	 */
	sc->sc_minsync = 1000 / sc->sc_freq;

	sc->sc_maxxfer = 64 * 1024;

	/* and the interuppts */
	mac_intr_establish(parent, esc->sc_intr, IST_LEVEL, IPL_BIO,
	    ncr53c9x_intr, sc, sc->sc_dev.dv_xname);

	/* Turn on target selection using the `DMA' method */
	sc->sc_features |= NCR_F_DMASELECT;

	ncr53c9x_attach(sc);

}
Esempio n. 26
0
void
mc_attach(struct device *parent, struct device *self, void *aux)
{
	struct confargs *ca = aux;
	struct mc_softc *sc = (struct mc_softc *)self;
	struct ifnet *ifp = &sc->sc_arpcom.ac_if;
	u_int8_t lladdr[ETHER_ADDR_LEN];
	int nseg, error;

	if (OF_getprop(ca->ca_node, "local-mac-address", lladdr,
	    ETHER_ADDR_LEN) != ETHER_ADDR_LEN) {
		printf(": failed to get MAC address.\n");
		return;
	}

	ca->ca_reg[0] += ca->ca_baseaddr;
	ca->ca_reg[2] += ca->ca_baseaddr;
	ca->ca_reg[4] += ca->ca_baseaddr;

	if ((sc->sc_reg = mapiodev(ca->ca_reg[0], ca->ca_reg[1])) == NULL) {
		printf(": cannot map registers\n");
		return;
	}

	sc->sc_dmat = ca->ca_dmat;
	sc->sc_tail = 0;

	if ((sc->sc_txdma = mapiodev(ca->ca_reg[2], ca->ca_reg[3])) == NULL) {
		printf(": cannot map TX DMA registers\n");
		goto notxdma;
	}
	if ((sc->sc_rxdma = mapiodev(ca->ca_reg[4], ca->ca_reg[5])) == NULL) {
		printf(": cannot map RX DMA registers\n");
		goto norxdma;
	}
	if ((sc->sc_txdbdma = dbdma_alloc(sc->sc_dmat, 2)) == NULL) {
		printf(": cannot alloc TX DMA descriptors\n");
		goto notxdbdma;
	}
	sc->sc_txdmacmd = sc->sc_txdbdma->d_addr;

	if ((sc->sc_rxdbdma = dbdma_alloc(sc->sc_dmat, 8 + 1)) == NULL) {
		printf(": cannot alloc RX DMA descriptors\n");
		goto norxdbdma;
	}
	sc->sc_rxdmacmd = sc->sc_rxdbdma->d_addr;

	if ((error = bus_dmamem_alloc(sc->sc_dmat, MACE_BUFSZ, PAGE_SIZE, 0,
	    sc->sc_bufseg, 1, &nseg, BUS_DMA_NOWAIT))) {
		printf(": cannot allocate DMA mem (%d)\n", error);
		goto nodmamem;
	}

	if ((error = bus_dmamem_map(sc->sc_dmat, sc->sc_bufseg, nseg,
	    MACE_BUFSZ, &sc->sc_txbuf, BUS_DMA_NOWAIT))) {
		printf(": cannot map DMA mem (%d)\n", error);
		goto nodmamap;
	}

	if ((error = bus_dmamap_create(sc->sc_dmat, MACE_BUFSZ, 1, MACE_BUFSZ,
	    0, BUS_DMA_NOWAIT | BUS_DMA_ALLOCNOW, &sc->sc_bufmap))) {
		printf(": cannot create DMA map (%d)\n", error);
		goto nodmacreate;
	}

	if ((error = bus_dmamap_load(sc->sc_dmat, sc->sc_bufmap, sc->sc_txbuf,
	    MACE_BUFSZ, NULL, BUS_DMA_NOWAIT))) {
		printf(": cannot load DMA map (%d)\n", error);
		goto nodmaload;
	}

	sc->sc_txbuf_pa = sc->sc_bufmap->dm_segs->ds_addr;
	sc->sc_rxbuf = sc->sc_txbuf + MACE_BUFLEN * MACE_TXBUFS;
	sc->sc_rxbuf_pa = sc->sc_txbuf_pa + MACE_BUFLEN * MACE_TXBUFS;

	printf(": irq %d,%d,%d", ca->ca_intr[0], ca->ca_intr[1],
	    ca->ca_intr[2]);

	/* disable receive DMA */
	dbdma_reset(sc->sc_rxdma);

	/* disable transmit DMA */
	dbdma_reset(sc->sc_txdma);

	/* install interrupt handlers */
	mac_intr_establish(parent, ca->ca_intr[2], IST_LEVEL, IPL_NET,
	    mc_dmaintr, sc, sc->sc_dev.dv_xname);
	mac_intr_establish(parent, ca->ca_intr[0],  IST_LEVEL, IPL_NET,
	    mc_intr, sc, sc->sc_dev.dv_xname);

	sc->sc_biucc = XMTSP_64;
	sc->sc_fifocc = XMTFW_16 | RCVFW_64 | XMTFWU | RCVFWU |
	    XMTBRST | RCVBRST;
	sc->sc_plscc = PORTSEL_GPSI | ENPLSIO;

	/* reset the chip and disable all interrupts */
	NIC_PUT(sc, MACE_BIUCC, SWRST);
	DELAY(100);

	NIC_PUT(sc, MACE_IMR, ~0);

	bcopy(lladdr, sc->sc_enaddr, ETHER_ADDR_LEN);
	bcopy(sc->sc_enaddr, sc->sc_arpcom.ac_enaddr, ETHER_ADDR_LEN);
	printf(": address %s\n", ether_sprintf(lladdr));

	bcopy(sc->sc_dev.dv_xname, ifp->if_xname, IFNAMSIZ);
	ifp->if_softc = sc;
	ifp->if_ioctl = mc_ioctl;
	ifp->if_start = mc_start;
	ifp->if_flags =
		IFF_BROADCAST | IFF_SIMPLEX | IFF_NOTRAILERS | IFF_MULTICAST;
	ifp->if_watchdog = mc_watchdog;
	ifp->if_timer = 0;
	IFQ_SET_READY(&ifp->if_snd);

	if_attach(ifp);
	ether_ifattach(ifp);

	return;
nodmaload:
	bus_dmamap_destroy(sc->sc_dmat, sc->sc_bufmap);
nodmacreate:
	bus_dmamem_unmap(sc->sc_dmat, sc->sc_txbuf, MACE_BUFSZ);
nodmamap:
	bus_dmamem_free(sc->sc_dmat, sc->sc_bufseg, 1);
nodmamem:
	dbdma_free(sc->sc_rxdbdma);
norxdbdma:
	dbdma_free(sc->sc_txdbdma);
notxdbdma:
	unmapiodev((void *)sc->sc_rxdma, ca->ca_reg[5]);
norxdma:
	unmapiodev((void *)sc->sc_txdma, ca->ca_reg[3]);
notxdma:
	unmapiodev(sc->sc_reg, ca->ca_reg[1]);
}
Esempio n. 27
0
void
cgthreeattach(struct device *parent, struct device *self, void *args)
{
	struct cgthree_softc *sc = (struct cgthree_softc *)self;
	struct confargs *ca = args;
	int node, pri, isrdi = 0, i;
	volatile struct bt_regs *bt;
	int isconsole;
	char *nam;

	pri = ca->ca_ra.ra_intr[0].int_pri;
	printf(" pri %d: ", pri);

	node = ca->ca_ra.ra_node;

	if (strcmp(ca->ca_ra.ra_name, "cgRDI") == 0) {
		isrdi = 1;
		nam = "cgRDI";
	} else
		nam = getpropstring(node, "model");

	if (nam != NULL && *nam != '\0')
		printf("%s, ", nam);

	isconsole = node == fbnode;

	sc->sc_fbc = (volatile struct fbcontrol *)
	    mapiodev(ca->ca_ra.ra_reg, CG3REG_REG,
		     sizeof(struct fbcontrol));

	/* Transfer video magic to board, if it's not running */
	if (isrdi == 0 && (sc->sc_fbc->fbc_ctrl & FBC_TIMING) == 0)
		for (i = 0; i < sizeof(cg3_videoctrl)/sizeof(cg3_videoctrl[0]);
		     i++) {
			volatile struct fbcontrol *fbc = sc->sc_fbc;
			if (cg3_videoctrl[i].sense == 0xff ||
			    (fbc->fbc_status & FBS_MSENSE) ==
			     cg3_videoctrl[i].sense) {
				int j;
#ifdef DEBUG
				printf(" (setting video ctrl)");
#endif
				for (j = 0; j < 12; j++)
					fbc->fbc_vcontrol[j] =
						cg3_videoctrl[i].vctrl[j];
				fbc->fbc_ctrl |= FBC_TIMING;
				break;
			}
		}

	sc->sc_phys = ca->ca_ra.ra_reg[0];

	sc->sc_ih.ih_fun = cgthree_intr;
	sc->sc_ih.ih_arg = sc;
	intr_establish(pri, &sc->sc_ih, IPL_FB, self->dv_xname);

	/* enable video */
	cgthree_burner(sc, 1, 0);
	bt = &sc->sc_fbc->fbc_dac;
	BT_INIT(bt, 0);

	fb_setsize(&sc->sc_sunfb, 8, 1152, 900, node, ca->ca_bustype);
	sc->sc_sunfb.sf_ro.ri_bits = mapiodev(ca->ca_ra.ra_reg, CG3REG_MEM,
	    round_page(sc->sc_sunfb.sf_fbsize));
	sc->sc_sunfb.sf_ro.ri_hw = sc;

	printf("%dx%d\n", sc->sc_sunfb.sf_width, sc->sc_sunfb.sf_height);

	/*
	 * If the framebuffer width is under 1024x768, which is the case for
	 * some clones on laptops, as well as with the VS10-EK, switch from
	 * the PROM font to the more adequate 8x16 font here.
	 * However, we need to adjust two things in this case:
	 * - the display row should be overrided from the current PROM metrics,
	 *   to prevent us from overwriting the last few lines of text.
	 * - if the 80x34 screen would make a large margin appear around it,
	 *   choose to clear the screen rather than keeping old prom output in
	 *   the margins.
	 * XXX there should be a rasops "clear margins" feature
	 */
	fbwscons_init(&sc->sc_sunfb, isconsole &&
	    (sc->sc_sunfb.sf_width >= 1024) ? 0 : RI_CLEAR);
	fbwscons_setcolormap(&sc->sc_sunfb, cgthree_setcolor);

	if (isconsole) {
		fbwscons_console_init(&sc->sc_sunfb,
		    sc->sc_sunfb.sf_width >= 1024 ? -1 : 0);
	}

	fbwscons_attach(&sc->sc_sunfb, &cgthree_accessops, isconsole);
}
Esempio n. 28
0
static void
uninorth_attach(device_t parent, device_t self, void *aux)
{
	struct uninorth_softc *sc = device_private(self);
	pci_chipset_tag_t pc = &sc->sc_pc;
	struct confargs *ca = aux;
	struct pcibus_attach_args pba;
	int len, child, node = ca->ca_node;
	uint32_t reg[2], busrange[2];
	char compat[32];
	int ver;
	struct ranges {
		uint32_t pci_hi, pci_mid, pci_lo;
		uint32_t host;
		uint32_t size_hi, size_lo;
	} ranges[6], *rp = ranges;

	printf("\n");
	sc->sc_dev = self;

	memset(compat, 0, sizeof(compat));
	OF_getprop(ca->ca_node, "compatible", compat, sizeof(compat));
	if (strcmp(compat, "u3-agp") == 0)
		ver = 3;
	else if (strcmp(compat, "u4-pcie") == 0)
		ver = 4;
	else
		ver = 0;

	/* UniNorth address */
	if (OF_getprop(node, "reg", reg, sizeof(reg)) < 8)
		return;

	/* PCI bus number */
	if (OF_getprop(node, "bus-range", busrange, sizeof(busrange)) != 8)
		return;

	memset(&sc->sc_iot, 0, sizeof(sc->sc_iot));

	/* find i/o tag */
	len = OF_getprop(node, "ranges", ranges, sizeof(ranges));
	if (len == -1)
		return;
	while (len >= sizeof(ranges[0])) {
		if ((rp->pci_hi & OFW_PCI_PHYS_HI_SPACEMASK) ==
		     OFW_PCI_PHYS_HI_SPACE_IO) {
			sc->sc_iot.pbs_base = rp->host;
			sc->sc_iot.pbs_limit = rp->host + rp->size_lo;
			break;
		}
		len -= sizeof(ranges[0]);
		rp++;
	}

	/* XXX enable gmac ethernet */
	for (child = OF_child(node); child; child = OF_peer(child)) {
		volatile int *gmac_gbclock_en = (void *)0xf8000020;

		memset(compat, 0, sizeof(compat));
		OF_getprop(child, "compatible", compat, sizeof(compat));
		if (strcmp(compat, "gmac") == 0)
			*gmac_gbclock_en |= 0x02;
	}

	sc->sc_iot.pbs_flags = _BUS_SPACE_LITTLE_ENDIAN|_BUS_SPACE_IO_TYPE;
	sc->sc_iot.pbs_offset = 0;
	if (ofwoea_map_space(RANGE_TYPE_PCI, RANGE_IO, node, &sc->sc_iot,
	    "uninorth io-space") != 0)
		panic("Can't init uninorth io tag");

	memset(&sc->sc_memt, 0, sizeof(sc->sc_memt));
	sc->sc_memt.pbs_flags = _BUS_SPACE_LITTLE_ENDIAN|_BUS_SPACE_MEM_TYPE;
	sc->sc_memt.pbs_base = 0x00000000;
	if (ofwoea_map_space(RANGE_TYPE_PCI, RANGE_MEM, node, &sc->sc_memt,
	    "uninorth mem-space") != 0)
		panic("Can't init uninorth mem tag");

	macppc_pci_get_chipset_tag(pc);
	pc->pc_node = node;
	pc->pc_bus = busrange[0];
	pc->pc_iot = &sc->sc_iot;
	pc->pc_memt = &sc->sc_memt;

	if (ver < 3) {
		pc->pc_addr = mapiodev(reg[0] + 0x800000, 4, false);
		pc->pc_data = mapiodev(reg[0] + 0xc00000, 8, false);
		pc->pc_conf_read = uninorth_conf_read;
		pc->pc_conf_write = uninorth_conf_write;
	} else {
		pc->pc_addr = mapiodev(reg[1] + 0x800000, 4, false);
		pc->pc_data = mapiodev(reg[1] + 0xc00000, 8, false);
		pc->pc_conf_read = uninorth_conf_read_v3;
		pc->pc_conf_write = uninorth_conf_write_v3;
	}

	memset(&pba, 0, sizeof(pba));
	pba.pba_memt = pc->pc_memt;
	pba.pba_iot = pc->pc_iot;
	pba.pba_dmat = &pci_bus_dma_tag;
	pba.pba_dmat64 = NULL;
	pba.pba_bus = pc->pc_bus;
	pba.pba_bridgetag = NULL;
	pba.pba_pc = pc;
	pba.pba_flags = PCI_FLAGS_IO_OKAY | PCI_FLAGS_MEM_OKAY;

	config_found_ia(self, "pcibus", &pba, pcibusprint);
}
Esempio n. 29
0
hide void
mc_attach(device_t parent, device_t self, void *aux)
{
	struct confargs *ca = aux;
	struct mc_softc *sc = device_private(self);
	u_int8_t myaddr[ETHER_ADDR_LEN];
	u_int *reg;

	sc->sc_dev = self;
	sc->sc_node = ca->ca_node;
	sc->sc_regt = ca->ca_tag;

	reg  = ca->ca_reg;
	reg[0] += ca->ca_baseaddr;
	reg[2] += ca->ca_baseaddr;
	reg[4] += ca->ca_baseaddr;

	sc->sc_txdma = mapiodev(reg[2], reg[3], false);
	sc->sc_rxdma = mapiodev(reg[4], reg[5], false);
	bus_space_map(sc->sc_regt, reg[0], reg[1], 0, &sc->sc_regh);

	sc->sc_tail = 0;
	sc->sc_txdmacmd = dbdma_alloc(sizeof(dbdma_command_t) * 2, NULL);
	sc->sc_rxdmacmd = (void *)dbdma_alloc(sizeof(dbdma_command_t) * 8,
	    NULL);
	memset(sc->sc_txdmacmd, 0, sizeof(dbdma_command_t) * 2);
	memset(sc->sc_rxdmacmd, 0, sizeof(dbdma_command_t) * 8);

	printf(": irq %d,%d,%d",
		ca->ca_intr[0], ca->ca_intr[1], ca->ca_intr[2]);

	if (OF_getprop(sc->sc_node, "local-mac-address", myaddr, 6) != 6) {
		printf(": failed to get MAC address.\n");
		return;
	}

	/* allocate memory for transmit buffer and mark it non-cacheable */
	sc->sc_txbuf = malloc(PAGE_SIZE, M_DEVBUF, M_WAITOK);
	sc->sc_txbuf_phys = kvtop(sc->sc_txbuf);
	memset(sc->sc_txbuf, 0, PAGE_SIZE);

	/*
	 * allocate memory for receive buffer and mark it non-cacheable
	 * XXX This should use the bus_dma interface, since the buffer
	 * needs to be physically contiguous. However, it seems that
	 * at least on my system, malloc() does allocate contiguous
	 * memory. If it's not, suggest reducing the number of buffers
	 * to 2, which will fit in one 4K page.
	 */
	sc->sc_rxbuf = malloc(MC_NPAGES * PAGE_SIZE, M_DEVBUF, M_WAITOK);
	sc->sc_rxbuf_phys = kvtop(sc->sc_rxbuf);
	memset(sc->sc_rxbuf, 0, MC_NPAGES * PAGE_SIZE);

	if ((int)sc->sc_txbuf & PGOFSET)
		printf("txbuf is not page-aligned\n");
	if ((int)sc->sc_rxbuf & PGOFSET)
		printf("rxbuf is not page-aligned\n");

	sc->sc_bus_init = mc_init;
	sc->sc_putpacket = mc_putpacket;


	/* disable receive DMA */
	dbdma_reset(sc->sc_rxdma);

	/* disable transmit DMA */
	dbdma_reset(sc->sc_txdma);

	/* install interrupt handlers */
	/*intr_establish(ca->ca_intr[1], IST_EDGE, IPL_NET, mc_dmaintr, sc);*/
	intr_establish(ca->ca_intr[2], IST_EDGE, IPL_NET, mc_dmaintr, sc);
	intr_establish(ca->ca_intr[0], IST_EDGE, IPL_NET, mcintr, sc);

	sc->sc_biucc = XMTSP_64;
	sc->sc_fifocc = XMTFW_16 | RCVFW_64 | XMTFWU | RCVFWU |
	    XMTBRST | RCVBRST;
	/*sc->sc_plscc = PORTSEL_10BT;*/
	sc->sc_plscc = PORTSEL_GPSI | ENPLSIO;

	/* mcsetup returns 1 if something fails */
	if (mcsetup(sc, myaddr)) {
		printf("mcsetup returns non zero\n");
		return;
	}
#ifdef NOTYET
	sc->sc_mediachange = mc_mediachange;
	sc->sc_mediastatus = mc_mediastatus;
	sc->sc_supmedia = mc_supmedia;
	sc->sc_nsupmedia = N_SUPMEDIA;
	sc->sc_defaultmedia = IFM_ETHER | IFM_10_T;
#endif
}
Esempio n. 30
0
void
cgtwelveattach(struct device *parent, struct device *self, void *args)
{
	struct cgtwelve_softc *sc = (struct cgtwelve_softc *)self;
	struct confargs *ca = args;
	int node;
	int isconsole = 0;
	char *ps;

	node = ca->ca_ra.ra_node;

	printf(": %s", getpropstring(node, "model"));
	ps = getpropstring(node, "dev_id");
	if (*ps != '\0')
		printf(" (%s)", ps);
	printf("\n");

	isconsole = node == fbnode;

	sc->sc_phys = ca->ca_ra.ra_reg[0];

	/*
	 * Map registers
	 */
	sc->sc_dpu = (struct cgtwelve_dpu *)mapiodev(ca->ca_ra.ra_reg,
	    CG12_OFF_DPU, sizeof(struct cgtwelve_dpu));
	sc->sc_apu = (struct cgtwelve_apu *)mapiodev(ca->ca_ra.ra_reg,
	    CG12_OFF_APU, sizeof(struct cgtwelve_apu));
	sc->sc_ramdac = (struct cgtwelve_dac *)mapiodev(ca->ca_ra.ra_reg,
	    CG12_OFF_DAC, sizeof(struct cgtwelve_dac));

	/*
	 * The console is using the 1-bit overlay plane, while the prom
	 * will correctly report 32 bit depth.
	 */
	fb_setsize(&sc->sc_sunfb, 1, CG12_WIDTH, CG12_HEIGHT,
	    node, ca->ca_bustype);
	sc->sc_sunfb.sf_depth = 1;
	sc->sc_sunfb.sf_linebytes = sc->sc_sunfb.sf_width / 8;
	sc->sc_sunfb.sf_fbsize = sc->sc_sunfb.sf_height *
	    sc->sc_sunfb.sf_linebytes;

	sc->sc_highres = sc->sc_sunfb.sf_width == CG12_WIDTH_HR;

	/*
	 * Map planes
	 */
	sc->sc_overlay = mapiodev(ca->ca_ra.ra_reg,
	    sc->sc_highres ? CG12_OFF_OVERLAY0_HR : CG12_OFF_OVERLAY0,
	    round_page(sc->sc_highres ? CG12_SIZE_OVERLAY_HR :
	        CG12_SIZE_OVERLAY));
	sc->sc_inten = mapiodev(ca->ca_ra.ra_reg,
	    sc->sc_highres ? CG12_OFF_INTEN_HR : CG12_OFF_INTEN,
	    round_page(sc->sc_highres ? CG12_SIZE_COLOR24_HR :
	        CG12_SIZE_COLOR24));

	/* reset cursor & frame buffer controls */
	sc->sc_sunfb.sf_depth = 0;	/* force action */
	cgtwelve_reset(sc, 1);

	sc->sc_sunfb.sf_ro.ri_bits = (void *)sc->sc_overlay;
	sc->sc_sunfb.sf_ro.ri_hw = sc;
	fbwscons_init(&sc->sc_sunfb, isconsole ? 0 : RI_CLEAR);

	if (isconsole) {
		fbwscons_console_init(&sc->sc_sunfb, -1);
		shutdownhook_establish(cgtwelve_prom, sc);
	}

	printf("%s: %dx%d", self->dv_xname,
	    sc->sc_sunfb.sf_width, sc->sc_sunfb.sf_height);
	ps = getpropstring(node, "ucoderev");
	if (*ps != '\0')
		printf(", microcode rev. %s", ps);
	printf("\n");

	fbwscons_attach(&sc->sc_sunfb, &cgtwelve_accessops, isconsole);
}