예제 #1
0
파일: srat.c 프로젝트: mulichao/freebsd
/*
 * Look for an ACPI System Resource Affinity Table ("SRAT")
 */
static int
parse_srat(void)
{
	int error;

	if (resource_disabled("srat", 0))
		return (-1);

	srat_physaddr = acpi_find_table(ACPI_SIG_SRAT);
	if (srat_physaddr == 0)
		return (-1);

	/*
	 * Make a pass over the table to populate the cpus[] and
	 * mem_info[] tables.
	 */
	srat = acpi_map_table(srat_physaddr, ACPI_SIG_SRAT);
	error = 0;
	srat_walk_table(srat_parse_entry, &error);
	acpi_unmap_table(srat);
	srat = NULL;
	if (error || check_domains() != 0 || check_phys_avail() != 0 ||
	    renumber_domains() != 0) {
		srat_physaddr = 0;
		return (-1);
	}

#ifdef VM_NUMA_ALLOC
	/* Point vm_phys at our memory affinity table. */
	vm_ndomains = ndomain;
	mem_affinity = mem_info;
#endif

	return (0);
}
예제 #2
0
파일: pckbd.c 프로젝트: 2asoft/freebsd
/* 
 * The back door to the keyboard driver!
 * This function is called by the console driver, via the kbdio module,
 * to tickle keyboard drivers when the low-level console is being initialized.
 * Almost nothing in the kernel has been initialied yet.  Try to probe
 * keyboards if possible.
 * NOTE: because of the way the low-level conole is initialized, this routine
 * may be called more than once!!
 */
static int
pckbd_configure(int flags)
{
	keyboard_t *kbd;
	int arg[2];
	int i;

	/* XXX: a kludge to obtain the device configuration flags */
	if (resource_int_value(DRIVER_NAME, 0, "flags", &i) == 0) {
		flags |= i;
		/* if the driver is disabled, unregister the keyboard if any */
		if (resource_disabled(DRIVER_NAME, 0)) {
			i = kbd_find_keyboard(DRIVER_NAME, PC98KBD_DEFAULT);
			if (i >= 0) {
				kbd = kbd_get_keyboard(i);
				kbd_unregister(kbd);
				kbd->kb_flags &= ~KB_REGISTERED;
				return 0;
			}
		}
	}

	/* probe the default keyboard */
	arg[0] = -1;
	arg[1] = -1;
	kbd = NULL;
	if (pckbd_probe(PC98KBD_DEFAULT, arg, flags))
		return 0;
	if (pckbd_init(PC98KBD_DEFAULT, &kbd, arg, flags))
		return 0;

	/* return the number of found keyboards */
	return 1;
}
예제 #3
0
파일: srat.c 프로젝트: mulichao/freebsd
/*
 * Look for an ACPI System Locality Distance Information Table ("SLIT")
 */
static int
parse_slit(void)
{

	if (resource_disabled("slit", 0)) {
		return (-1);
	}

	slit_physaddr = acpi_find_table(ACPI_SIG_SLIT);
	if (slit_physaddr == 0) {
		return (-1);
	}

	/*
	 * Make a pass over the table to populate the cpus[] and
	 * mem_info[] tables.
	 */
	slit = acpi_map_table(slit_physaddr, ACPI_SIG_SLIT);
	slit_parse_table(slit);
	acpi_unmap_table(slit);
	slit = NULL;

#ifdef VM_NUMA_ALLOC
	/* Tell the VM about it! */
	mem_locality = vm_locality_table;
#endif
	return (0);
}
예제 #4
0
int
sc_get_cons_priority(int *unit, int *flags)
{
	const char *at;
	int f, u;

	*unit = -1;
	for (u = 0; u < 16; u++) {
		if (resource_disabled(SC_DRIVER_NAME, u))
			continue;
		if (resource_string_value(SC_DRIVER_NAME, u, "at", &at) != 0)
			continue;
		if (resource_int_value(SC_DRIVER_NAME, u, "flags", &f) != 0)
			f = 0;
		if (f & SC_KERNEL_CONSOLE) {
			/* the user designates this unit to be the console */
			*unit = u;
			*flags = f;
			break;
		}
		if (*unit < 0) {
			/* ...otherwise remember the first found unit */
			*unit = u;
			*flags = f;
		}
	}
	if (*unit < 0) {
		*unit = 0;
		*flags = 0;
	}
	return (CN_INTERNAL);
}
예제 #5
0
/*
 * Look for an ACPI System Resource Affinity Table ("SRAT")
 */
static void
parse_srat(void *dummy)
{
	int error;

	if (resource_disabled("srat", 0))
		return;

	srat_physaddr = acpi_find_table(ACPI_SIG_SRAT);
	if (srat_physaddr == 0)
		return;

	/*
	 * Make a pass over the table to populate the cpus[] and
	 * mem_info[] tables.
	 */
	srat = acpi_map_table(srat_physaddr, ACPI_SIG_SRAT);
	error = 0;
	srat_walk_table(srat_parse_entry, &error);
	acpi_unmap_table(srat);
	srat = NULL;
	if (error || check_domains() != 0 || check_phys_avail() != 0) {
		srat_physaddr = 0;
		return;
	}

	renumber_domains();

	/* Point vm_phys at our memory affinity table. */
	mem_affinity = mem_info;
}
예제 #6
0
static void
amdsbwd_identify(driver_t *driver, device_t parent)
{
	device_t		child;
	device_t		smb_dev;

	if (resource_disabled("amdsbwd", 0))
		return;
	if (device_find_child(parent, "amdsbwd", -1) != NULL)
		return;

	/*
	 * Try to identify SB600/SB7xx by PCI Device ID of SMBus device
	 * that should be present at bus 0, device 20, function 0.
	 */
	smb_dev = pci_find_bsf(0, 20, 0);
	if (smb_dev == NULL)
		return;
	if (pci_get_devid(smb_dev) != AMDSB_SMBUS_DEVID)
		return;

	child = BUS_ADD_CHILD(parent, ISA_ORDER_SPECULATIVE, "amdsbwd", -1);
	if (child == NULL)
		device_printf(parent, "add amdsbwd child failed\n");
}
예제 #7
0
/* Placeholder for system RAM. */
static void
ram_identify(driver_t *driver, device_t parent)
{

	if (resource_disabled("ram", 0))
		return;	
	if (BUS_ADD_CHILD(parent, 0, "ram", 0) == NULL)
		panic("ram_identify");
}
예제 #8
0
파일: dfs.c 프로젝트: edgar-pek/PerspicuOS
static int
dfs_probe(device_t dev)
{
	if (resource_disabled("dfs", 0))
		return (ENXIO);

	device_set_desc(dev, "Dynamic Frequency Switching");
	return (0);
}
예제 #9
0
파일: pxa_smi.c 프로젝트: AhmadTux/freebsd
static int
pxa_smi_probe(device_t dev)
{

	if (resource_disabled("smi", device_get_unit(dev)))
		return (ENXIO);

	device_set_desc(dev, "Static Memory Interface");
	return (0);
}
예제 #10
0
static int
hv_shutdown_probe(device_t dev)
{
	if (resource_disabled("hvshutdown", 0))
		return ENXIO;

	if (VMBUS_PROBE_GUID(device_get_parent(dev), dev, &service_guid) == 0) {
		device_set_desc(dev, "Hyper-V Shutdown Service");
		return BUS_PROBE_DEFAULT;
	}
	return ENXIO;
}
예제 #11
0
static int
hv_timesync_probe(device_t dev)
{
	if (resource_disabled("hvtimesync", 0))
		return ENXIO;

	if (VMBUS_PROBE_GUID(device_get_parent(dev), dev, &service_guid) == 0) {
		device_set_desc(dev, "Hyper-V Time Synch Service");
		return BUS_PROBE_DEFAULT;
	}
	return ENXIO;
}
예제 #12
0
파일: agp_nvidia.c 프로젝트: coyizumi/cs111
static int
agp_nvidia_probe (device_t dev)
{
	const char *desc;

	if (resource_disabled("agp", device_get_unit(dev)))
		return (ENXIO);
	desc = agp_nvidia_match(dev);
	if (desc) {
		device_set_desc(dev, desc);
		return (BUS_PROBE_DEFAULT);
	}
	return (ENXIO);
}
예제 #13
0
int
sc_get_cons_priority(int *unit, int *flags)
{
    const char *at;
    int f, u;

#ifdef XBOX
    /*
     * The XBox Loader does not support hints, which makes our initial
     * console probe fail. Therefore, if an XBox is found, we hardcode the
     * existence of the console, as it is always there anyway.
     */
    if (arch_i386_is_xbox) {
        *unit = 0;
        *flags = SC_KERNEL_CONSOLE;
        return (CN_INTERNAL);
    }
#endif

    *unit = -1;
    for (u = 0; u < 16; u++) {
        if (resource_disabled(SC_DRIVER_NAME, u))
            continue;
        if (resource_string_value(SC_DRIVER_NAME, u, "at", &at) != 0)
            continue;
        if (resource_int_value(SC_DRIVER_NAME, u, "flags", &f) != 0)
            f = 0;
        if (f & SC_KERNEL_CONSOLE) {
            /* the user designates this unit to be the console */
            *unit = u;
            *flags = f;
            break;
        }
        if (*unit < 0) {
            /* ...otherwise remember the first found unit */
            *unit = u;
            *flags = f;
        }
    }
    if (*unit < 0) {
        *unit = 0;
        *flags = 0;
    }
#if 0
    return ((*flags & SC_KERNEL_CONSOLE) != 0 ? CN_INTERNAL : CN_NORMAL);
#endif
    return (CN_INTERNAL);
}
예제 #14
0
static device_t
atkbdc_isa_add_child(device_t bus, u_int order, const char *name, int unit)
{
	atkbdc_device_t	*ivar;
	atkbdc_softc_t	*sc;
	device_t	child;
	int		t;

	sc = *(atkbdc_softc_t **)device_get_softc(bus);
	ivar = malloc(sizeof(struct atkbdc_device), M_ATKBDDEV,
		M_NOWAIT | M_ZERO);
	if (!ivar)
		return NULL;

	child = device_add_child_ordered(bus, order, name, unit);
	if (child == NULL) {
		free(ivar, M_ATKBDDEV);
		return child;
	}

	resource_list_init(&ivar->resources);
	ivar->rid = order;

	/*
	 * If the device is not created by the PnP BIOS or ACPI, refer
	 * to device hints for IRQ.  We always populate the resource
	 * list entry so we can use a standard bus_get_resource()
	 * method.
	 */
	if (order == KBDC_RID_KBD) {
		if (sc->irq == NULL) {
			if (resource_int_value(name, unit, "irq", &t) != 0)
				t = -1;
		} else
			t = rman_get_start(sc->irq);
		if (t > 0)
			resource_list_add(&ivar->resources, SYS_RES_IRQ,
			    ivar->rid, t, t, 1);
	}

	if (resource_disabled(name, unit))
		device_disable(child);

	device_set_ivars(child, ivar);

	return child;
}
예제 #15
0
void
isa_hinted_child(device_t parent, const char *name, int unit)
{
	device_t	child;
	int		sensitive, start, count;
	int		order;

	/* device-specific flag overrides any wildcard */
	sensitive = 0;
	if (resource_int_value(name, unit, "sensitive", &sensitive) != 0)
		resource_int_value(name, -1, "sensitive", &sensitive);

	if (sensitive)
		order = ISA_ORDER_SENSITIVE;
	else
		order = ISA_ORDER_SPECULATIVE;

	child = BUS_ADD_CHILD(parent, order, name, unit);
	if (child == 0)
		return;

	start = 0;
	count = 0;
	resource_int_value(name, unit, "port", &start);
	resource_int_value(name, unit, "portsize", &count);
	if (start > 0 || count > 0)
		bus_set_resource(child, SYS_RES_IOPORT, 0, start, count);

	start = 0;
	count = 0;
	resource_int_value(name, unit, "maddr", &start);
	resource_int_value(name, unit, "msize", &count);
	if (start > 0 || count > 0)
		bus_set_resource(child, SYS_RES_MEMORY, 0, start, count);

	if (resource_int_value(name, unit, "irq", &start) == 0 && start > 0)
		bus_set_resource(child, SYS_RES_IRQ, 0, start, 1);

	if (resource_int_value(name, unit, "drq", &start) == 0 && start >= 0)
		bus_set_resource(child, SYS_RES_DRQ, 0, start, 1);

	if (resource_disabled(name, unit))
		device_disable(child);

	isa_set_configattr(child, (isa_get_configattr(child)|ISACFGATTR_HINTS));
}
예제 #16
0
static int
acpi_perf_probe(device_t dev)
{
	ACPI_HANDLE handle;
	ACPI_OBJECT *pkg;
	struct resource *res;
	ACPI_BUFFER buf;
	int error, rid, type;

	if (resource_disabled("acpi_perf", 0))
		return (ENXIO);

	/*
	 * Check the performance state registers.  If they are of type
	 * "functional fixed hardware", we attach quietly since we will
	 * only be providing information on settings to other drivers.
	 */
	error = ENXIO;
	handle = acpi_get_handle(dev);
	buf.Pointer = NULL;
	buf.Length = ACPI_ALLOCATE_BUFFER;
	if (ACPI_FAILURE(AcpiEvaluateObject(handle, "_PCT", NULL, &buf)))
		return (error);
	pkg = (ACPI_OBJECT *)buf.Pointer;
	if (ACPI_PKG_VALID(pkg, 2)) {
		rid = 0;
		error = acpi_PkgGas(dev, pkg, 0, &type, &rid, &res, 0);
		switch (error) {
		case 0:
			bus_release_resource(dev, type, rid, res);
			bus_delete_resource(dev, type, rid);
			device_set_desc(dev, "ACPI CPU Frequency Control");
			break;
		case EOPNOTSUPP:
			device_quiet(dev);
			error = 0;
			break;
		}
	}
	AcpiOsFree(buf.Pointer);

	return (error);
}
예제 #17
0
/*
 * Look for an ACPI System Resource Affinity Table ("SRAT"),
 * allocate space for cpu information, and initialize globals.
 */
int
acpi_pxm_init(int ncpus, vm_paddr_t maxphys)
{
	unsigned int idx, size;
	vm_paddr_t addr;

	if (resource_disabled("srat", 0))
		return (-1);

	max_cpus = ncpus;
	last_cpu = -1;
	maxphyaddr = maxphys;
	srat_physaddr = acpi_find_table(ACPI_SIG_SRAT);
	if (srat_physaddr == 0)
		return (-1);

	/*
	 * Allocate data structure:
	 *
	 * Find the last physical memory region and steal some memory from
	 * it. This is done because at this point in the boot process
	 * malloc is still not usable.
	 */
	for (idx = 0; phys_avail[idx + 1] != 0; idx += 2);
	KASSERT(idx != 0, ("phys_avail is empty!"));
	idx -= 2;

	size =  sizeof(*cpus) * max_cpus;
	addr = trunc_page(phys_avail[idx + 1] - size);
	KASSERT(addr >= phys_avail[idx],
	    ("Not enough memory for SRAT table items"));
	phys_avail[idx + 1] = addr - 1;

	/*
	 * We cannot rely on PHYS_TO_DMAP because this code is also used in
	 * i386, so use pmap_mapbios to map the memory, this will end up using
	 * the default memory attribute (WB), and the DMAP when available.
	 */
	cpus = (struct cpu_info *)pmap_mapbios(addr, size);
	bzero(cpus, size);
	return (0);
}
static device_t
atkbdc_isa_add_child(device_t bus, int order, char *name, int unit)
{
	atkbdc_device_t	*ivar;
	device_t	child;
	int		t;

	ivar = malloc(sizeof(struct atkbdc_device), M_ATKBDDEV,
		M_NOWAIT | M_ZERO);
	if (!ivar)
		return NULL;

	child = device_add_child_ordered(bus, order, name, unit);
	if (child == NULL) {
		free(ivar, M_ATKBDDEV);
		return child;
	}

	resource_list_init(&ivar->resources);
	ivar->rid = order;

	/*
	 * If the device is not created by the PnP BIOS or ACPI,
	 * refer to device hints for IRQ.
	 */
	if (ISA_PNP_PROBE(device_get_parent(bus), bus, atkbdc_ids) != 0) {
		if (resource_int_value(name, unit, "irq", &t) != 0)
			t = -1;
	} else {
		t = bus_get_resource_start(bus, SYS_RES_IRQ, ivar->rid);
	}
	if (t > 0)
		resource_list_add(&ivar->resources, SYS_RES_IRQ, ivar->rid,
				  t, t, 1);

	if (resource_disabled(name, unit))
		device_disable(child);

	device_set_ivars(child, ivar);

	return child;
}
예제 #19
0
파일: pxa_smi.c 프로젝트: AhmadTux/freebsd
static void
pxa_smi_add_device(device_t dev, const char *name, int unit)
{
	device_t	child;
	int		start, count;
	struct		smi_ivars *ivars;

	ivars = (struct smi_ivars *)malloc(
	    sizeof(struct smi_ivars), M_PXASMI, M_WAITOK);
	if (ivars == NULL)
		return;

	child = device_add_child(dev, name, unit);
	if (child == NULL) {
		free(ivars, M_PXASMI);
		return;
	}

	device_set_ivars(child, ivars);
	resource_list_init(&ivars->smid_resources);

	start = 0;
	count = 0;
	resource_int_value(name, unit, "mem", &start);
	resource_int_value(name, unit, "size", &count);
	if (start > 0 || count > 0) {
		resource_list_add(&ivars->smid_resources, SYS_RES_MEMORY, 0,
		    start, start + count, count);
		ivars->smid_mem = (bus_addr_t)start;
	}

	start = -1;
	count = 0;
	resource_int_value(name, unit, "irq", &start);
	if (start > -1)
		resource_list_add(&ivars->smid_resources, SYS_RES_IRQ, 0, start,
		     start, 1);

	if (resource_disabled(name, unit))
		device_disable(child);
}
예제 #20
0
/* 
 * The back door to the keyboard driver!
 * This function is called by the console driver, via the kbdio module,
 * to tickle keyboard drivers when the low-level console is being initialized.
 * Almost nothing in the kernel has been initialied yet.  Try to probe
 * keyboards if possible.
 * NOTE: because of the way the low-level console is initialized, this routine
 * may be called more than once!!
 */
static int
atkbd_configure(int flags)
{
	keyboard_t *kbd;
	int arg[2];
	int i;

	/*
	 * Probe the keyboard controller, if not present or if the driver
	 * is disabled, unregister the keyboard if any.
	 */
	if (atkbdc_configure() != 0 ||
	    resource_disabled("atkbd", ATKBD_DEFAULT)) {
		i = kbd_find_keyboard(ATKBD_DRIVER_NAME, ATKBD_DEFAULT);
		if (i >= 0) {
			kbd = kbd_get_keyboard(i);
			KBD_ALWAYS_LOCK(kbd);
			kbd_unregister(kbd);
			kbd = NULL; /* huh? */
		}
		return 0;
	}
	
	/* XXX: a kludge to obtain the device configuration flags */
	if (resource_int_value("atkbd", ATKBD_DEFAULT, "flags", &i) == 0)
		flags |= i;

	/* probe the default keyboard */
	arg[0] = -1;
	arg[1] = -1;
	kbd = NULL;
	if (atkbd_probe(ATKBD_DEFAULT, arg, flags)) {
		return 0;
	}
	if (atkbd_init(ATKBD_DEFAULT, &kbd, arg, flags)) {
		return 0;
	}

	/* return the number of found keyboards */
	return 1;
}
예제 #21
0
/*
 * Assign logical CPU IDs to local APICs.
 */
static void
assign_cpu_ids(void)
{
	u_int i;

	/* Check for explicitly disabled CPUs. */
	for (i = 0; i <= MAX_APIC_ID; i++) {
		if (!cpu_info[i].cpu_present || cpu_info[i].cpu_bsp)
			continue;

		/* Don't use this CPU if it has been disabled by a tunable. */
		if (resource_disabled("lapic", i)) {
			cpu_info[i].cpu_disabled = 1;
			continue;
		}
	}

	/*
	 * Assign CPU IDs to local APIC IDs and disable any CPUs
	 * beyond MAXCPU.  CPU 0 has already been assigned to the BSP,
	 * so we only have to assign IDs for APs.
	 */
	mp_ncpus = 1;
	for (i = 0; i <= MAX_APIC_ID; i++) {
		if (!cpu_info[i].cpu_present || cpu_info[i].cpu_bsp ||
		    cpu_info[i].cpu_disabled)
			continue;

		if (mp_ncpus < MAXCPU) {
			cpu_apic_ids[mp_ncpus] = i;
			apic_cpuids[i] = mp_ncpus;
			mp_ncpus++;
		} else
			cpu_info[i].cpu_disabled = 1;
	}
	KASSERT(mp_maxid >= mp_ncpus - 1,
	    ("%s: counters out of sync: max %d, count %d", __func__, mp_maxid,
	    mp_ncpus));		
}
예제 #22
0
static void
hwpstate_identify(driver_t *driver, device_t parent)
{

	if (device_find_child(parent, "hwpstate", -1) != NULL)
		return;

	if (cpu_vendor_id != CPU_VENDOR_AMD || CPUID_TO_FAMILY(cpu_id) < 0x10)
		return;

	/*
	 * Check if hardware pstate enable bit is set.
	 */
	if ((amd_pminfo & AMDPM_HW_PSTATE) == 0) {
		HWPSTATE_DEBUG(parent, "hwpstate enable bit is not set.\n");
		return;
	}

	if (resource_disabled("hwpstate", 0))
		return;

	if (BUS_ADD_CHILD(parent, 10, "hwpstate", -1) == NULL)
		device_printf(parent, "hwpstate: add child failed\n");
}
예제 #23
0
/*
 * Look for an ACPI System Locality Distance Information Table ("SLIT")
 */
static int
parse_slit(void)
{

	if (resource_disabled("slit", 0)) {
		return (-1);
	}

	slit_physaddr = acpi_find_table(ACPI_SIG_SLIT);
	if (slit_physaddr == 0) {
		return (-1);
	}

	/*
	 * Make a pass over the table to populate the cpus[] and
	 * mem_info[] tables.
	 */
	slit = acpi_map_table(slit_physaddr, ACPI_SIG_SLIT);
	slit_parse_table(slit);
	acpi_unmap_table(slit);
	slit = NULL;

	return (0);
}
예제 #24
0
/*
 * Look for an ACPI Multiple APIC Description Table ("APIC")
 */
static int
madt_probe(void)
{
	ACPI_POINTER rsdp_ptr;
	RSDP_DESCRIPTOR *rsdp;
	RSDT_DESCRIPTOR *rsdt;
	XSDT_DESCRIPTOR *xsdt;
	int i, count;

	if (resource_disabled("acpi", 0))
		return (ENXIO);

	/*
	 * Map in the RSDP.  Since ACPI uses AcpiOsMapMemory() which in turn
	 * calls pmap_mapdev() to find the RSDP, we assume that we can use
	 * pmap_mapdev() to map the RSDP.
	 */
	if (AcpiOsGetRootPointer(ACPI_LOGICAL_ADDRESSING, &rsdp_ptr) != AE_OK)
		return (ENXIO);
#ifdef __i386__
	KASSERT(rsdp_ptr.Pointer.Physical < KERNLOAD, ("RSDP too high"));
#endif
	rsdp = pmap_mapdev(rsdp_ptr.Pointer.Physical, sizeof(RSDP_DESCRIPTOR));
	if (rsdp == NULL) {
		if (bootverbose)
			printf("MADT: Failed to map RSDP\n");
		return (ENXIO);
	}

	/*
	 * For ACPI < 2.0, use the RSDT.  For ACPI >= 2.0, use the XSDT.
	 * We map the XSDT and RSDT at page 1 in the crashdump area.
	 * Page 0 is used to map in the headers of candidate ACPI tables.
	 */
	if (rsdp->Revision >= 2) {
		xsdt = madt_map_table(rsdp->XsdtPhysicalAddress, 1, XSDT_SIG);
		if (xsdt == NULL) {
			if (bootverbose)
				printf("MADT: Failed to map XSDT\n");
			return (ENXIO);
		}
		count = (xsdt->Header.Length - sizeof(ACPI_TABLE_HEADER)) /
		    sizeof(UINT64);
		for (i = 0; i < count; i++)
			if (madt_probe_table(xsdt->TableOffsetEntry[i]))
				break;
		madt_unmap_table(xsdt);
	} else {
		rsdt = madt_map_table(rsdp->RsdtPhysicalAddress, 1, RSDT_SIG);
		if (rsdt == NULL) {
			if (bootverbose)
				printf("MADT: Failed to map RSDT\n");
			return (ENXIO);
		}
		count = (rsdt->Header.Length - sizeof(ACPI_TABLE_HEADER)) /
		    sizeof(UINT32);
		for (i = 0; i < count; i++)
			if (madt_probe_table(rsdt->TableOffsetEntry[i]))
				break;
		madt_unmap_table(rsdt);
	}
	pmap_unmapdev((vm_offset_t)rsdp, sizeof(RSDP_DESCRIPTOR));
	if (madt_physaddr == 0) {
		if (bootverbose)
			printf("MADT: No MADT table found\n");
		return (ENXIO);
	}
	if (bootverbose)
		printf("MADT: Found table at 0x%jx\n",
		    (uintmax_t)madt_physaddr);

	return (0);
}
예제 #25
0
/*
 * Return the physical address of the requested table or zero if one
 * is not found.
 */
vm_paddr_t
acpi_find_table(const char *sig)
{
	ACPI_PHYSICAL_ADDRESS rsdp_ptr;
	ACPI_TABLE_RSDP *rsdp;
	ACPI_TABLE_XSDT *xsdt;
	ACPI_TABLE_HEADER *table;
	vm_paddr_t addr;
	int i, count;

	if (resource_disabled("acpi", 0))
		return (0);

	/*
	 * Map in the RSDP.  Since ACPI uses AcpiOsMapMemory() which in turn
	 * calls pmap_mapbios() to find the RSDP, we assume that we can use
	 * pmap_mapbios() to map the RSDP.
	 */
	if ((rsdp_ptr = AcpiOsGetRootPointer()) == 0)
		return (0);
	rsdp = pmap_mapbios(rsdp_ptr, sizeof(ACPI_TABLE_RSDP));
	if (rsdp == NULL) {
		if (bootverbose)
			printf("ACPI: Failed to map RSDP\n");
		return (0);
	}

	addr = 0;
	if (rsdp->Revision >= 2 && rsdp->XsdtPhysicalAddress != 0) {
		/*
		 * AcpiOsGetRootPointer only verifies the checksum for
		 * the version 1.0 portion of the RSDP.  Version 2.0 has
		 * an additional checksum that we verify first.
		 */
		if (AcpiTbChecksum((UINT8 *)rsdp, ACPI_RSDP_XCHECKSUM_LENGTH)) {
			if (bootverbose)
				printf("ACPI: RSDP failed extended checksum\n");
			return (0);
		}
		xsdt = map_table(rsdp->XsdtPhysicalAddress, 2, ACPI_SIG_XSDT);
		if (xsdt == NULL) {
			if (bootverbose)
				printf("ACPI: Failed to map XSDT\n");
			pmap_unmapbios((vm_offset_t)rsdp,
			    sizeof(ACPI_TABLE_RSDP));
			return (0);
		}
		count = (xsdt->Header.Length - sizeof(ACPI_TABLE_HEADER)) /
		    sizeof(UINT64);
		for (i = 0; i < count; i++)
			if (probe_table(xsdt->TableOffsetEntry[i], sig)) {
				addr = xsdt->TableOffsetEntry[i];
				break;
			}
		acpi_unmap_table(xsdt);
	}
	pmap_unmapbios((vm_offset_t)rsdp, sizeof(ACPI_TABLE_RSDP));

	if (addr == 0) {
		if (bootverbose)
			printf("ACPI: No %s table found\n", sig);
		return (0);
	}
	if (bootverbose)
		printf("%s: Found table at 0x%jx\n", sig, (uintmax_t)addr);

	/*
	 * Verify that we can map the full table and that its checksum is
	 * correct, etc.
	 */
	table = map_table(addr, 0, sig);
	if (table == NULL)
		return (0);
	acpi_unmap_table(table);

	return (addr);
}
예제 #26
0
/*
 * generic PCI ATA device probe
 */
int
ata_pci_probe(device_t dev)
{
    if (resource_disabled("atapci", device_get_unit(dev)))
	 return (ENXIO);

    if (pci_get_class(dev) != PCIC_STORAGE)
	return ENXIO;

    /* if this is an AHCI chipset grab it */
    if (pci_get_subclass(dev) == PCIS_STORAGE_SATA) {
	if (!ata_ahci_ident(dev))
	    return ATA_PROBE_OK;
    }

    /* run through the vendor specific drivers */
    switch (pci_get_vendor(dev)) {
    case ATA_ACARD_ID:
	if (!ata_acard_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_ACER_LABS_ID:
	if (!ata_ali_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_ADAPTEC_ID:
	if (!ata_adaptec_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_AMD_ID:
	if (!ata_amd_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_ATI_ID:
	if (!ata_ati_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_CYRIX_ID:
	if (!ata_cyrix_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_CYPRESS_ID:
	if (!ata_cypress_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_HIGHPOINT_ID:
	if (!ata_highpoint_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_INTEL_ID:
	if (!ata_intel_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_ITE_ID:
	if (!ata_ite_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_JMICRON_ID:
	if (!ata_jmicron_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_MARVELL_ID:
	if (!ata_marvell_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_NATIONAL_ID:
	if (!ata_national_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_NETCELL_ID:
	if (!ata_netcell_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_NVIDIA_ID:
	if (!ata_nvidia_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_PROMISE_ID:
	if (!ata_promise_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_SERVERWORKS_ID:
	if (!ata_serverworks_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_SILICON_IMAGE_ID:
	if (!ata_sii_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_SIS_ID:
	if (!ata_sis_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_VIA_ID:
	if (!ata_via_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_CENATEK_ID:
	if (!ata_cenatek_ident(dev))
	    return ATA_PROBE_OK;
	break;
    case ATA_MICRON_ID:
	if (!ata_micron_ident(dev))
	    return ATA_PROBE_OK;
	break;
    }

    /* unknown chipset, try generic AHCI or DMA if it seems possible */
    if (pci_get_subclass(dev) == PCIS_STORAGE_IDE) {
	uint16_t vendor, device, subvendor, subdevice;
	const struct none_atapci *e;

	vendor = pci_get_vendor(dev);
	device = pci_get_device(dev);
	subvendor = pci_get_subvendor(dev);
	subdevice = pci_get_subdevice(dev);
	for (e = none_atapci_table; e->vendor != 0xffff; ++e) {
	    if (e->vendor == vendor && e->device == device &&
		e->subvendor == subvendor && e->subdevice == subdevice)
		return ENXIO;
	}

	if (!ata_generic_ident(dev))
	    return ATA_PROBE_OK;
    }
    return ENXIO;
}
예제 #27
0
static void
ichss_identify(driver_t *driver, device_t parent)
{
	device_t child;
	uint32_t pmbase;

	if (resource_disabled("ichss", 0))
		return;

	/*
	 * It appears that ICH SpeedStep only requires a single CPU to
	 * set the value (since the chipset is shared by all CPUs.)
	 * Thus, we only add a child to cpu 0.
	 */
	if (device_get_unit(parent) != 0)
		return;

	/* Avoid duplicates. */
	if (device_find_child(parent, "ichss", -1))
		return;

	/*
	 * ICH2/3/4-M I/O Controller Hub is at bus 0, slot 1F, function 0.
	 * E.g. see Section 6.1 "PCI Devices and Functions" and table 6.1 of
	 * Intel(r) 82801BA I/O Controller Hub 2 (ICH2) and Intel(r) 82801BAM
	 * I/O Controller Hub 2 Mobile (ICH2-M).
	 *
	 * TODO: add a quirk to disable if we see the 82815_MC along
	 * with the 82801BA and revision < 5.
	 */
	ich_device = pci_find_bsf(0, 0x1f, 0);
	if (ich_device == NULL ||
	    pci_get_vendor(ich_device) != PCI_VENDOR_INTEL ||
	    (pci_get_device(ich_device) != PCI_DEV_82801BA &&
	    pci_get_device(ich_device) != PCI_DEV_82801CA &&
	    pci_get_device(ich_device) != PCI_DEV_82801DB))
		return;

	/* Find the PMBASE register from our PCI config header. */
	pmbase = pci_read_config(ich_device, ICHSS_PMBASE_OFFSET,
	    sizeof(pmbase));
	if ((pmbase & ICHSS_IO_REG) == 0) {
		printf("ichss: invalid PMBASE memory type\n");
		return;
	}
	pmbase &= ICHSS_PMBASE_MASK;
	if (pmbase == 0) {
		printf("ichss: invalid zero PMBASE address\n");
		return;
	}
	DPRINT("ichss: PMBASE is %#x\n", pmbase);

	child = BUS_ADD_CHILD(parent, 20, "ichss", 0);
	if (child == NULL) {
		device_printf(parent, "add SpeedStep child failed\n");
		return;
	}

	/* Add the bus master arbitration and control registers. */
	bus_set_resource(child, SYS_RES_IOPORT, 0, pmbase + ICHSS_BM_OFFSET,
	    1);
	bus_set_resource(child, SYS_RES_IOPORT, 1, pmbase + ICHSS_CTRL_OFFSET,
	    1);
}