#include "grub.h"
#include "pci.h"
#include "isa.h"
#include "nic.h"
#ifdef CONFIG_PCI
static int pci_probe(struct dev *dev, const char *type_name)
{
struct pci_probe_state *state = &dev->state.pci;
printf("Probing pci %s...\n", type_name);
if (dev->how_probe == PROBE_FIRST) {
state->advance = 1;
state->dev.driver = 0;
state->dev.bus = 0;
state->dev.devfn = 0;
dev->index = -1;
}
for(;;) {
if ((dev->how_probe != PROBE_AWAKE) && state->advance) {
find_pci(dev->type, &state->dev);
dev->index = -1;
}
state->advance = 1;
if (state->dev.driver == 0)
break;
#if 0
if (state->dev.romaddr != ((unsigned long) rom.rom_segment << 4)) {
continue;
}
#endif
if (dev->how_probe != PROBE_AWAKE) {
dev->type_index++;
}
dev->devid.bus_type = PCI_BUS_TYPE;
dev->devid.vendor_id = htons(state->dev.vendor);
dev->devid.device_id = htons(state->dev.dev_id);
printf("[%s]", state->dev.name);
if (state->dev.driver->probe(dev, &state->dev)) {
state->advance = (dev->index == -1);
return PROBE_WORKED;
}
putchar('\n');
}
return PROBE_FAILED;
}
#endif
#ifdef CONFIG_ISA
static int isa_probe(struct dev *dev, const char *type_name)
{
struct isa_probe_state *state = &dev->state.isa;
printf("Probing isa %s...\n", type_name);
if (dev->how_probe == PROBE_FIRST) {
state->advance = 0;
state->driver = isa_drivers;
dev->index = -1;
}
for(;;)
{
if ((dev->how_probe != PROBE_AWAKE) && state->advance) {
state->driver++;
dev->index = -1;
}
state->advance = 1;
if (state->driver >= isa_drivers_end)
break;
if (state->driver->type != dev->type)
continue;
if (dev->how_probe != PROBE_AWAKE) {
dev->type_index++;
}
printf("[%s]", state->driver->name);
dev->devid.bus_type = ISA_BUS_TYPE;
if (state->driver->probe(dev, state->driver->ioaddrs)) {
state->advance = (dev->index == -1);
return PROBE_WORKED;
}
putchar('\n');
}
return PROBE_FAILED;
}
#else
#define isa_probe(d,tn) (PROBE_FAILED)
#endif
static const char *driver_name[] = {
"nic",
"disk",
"floppy",
};
int probe(struct dev *dev)
{
const char *type_name;
EnterFunction("probe");
type_name = "";
if ((dev->type >= 0) &&
(dev->type < sizeof(driver_name)/sizeof(driver_name[0]))) {
type_name = driver_name[dev->type];
}
if (dev->how_probe == PROBE_FIRST) {
dev->to_probe = PROBE_PCI;
memset(&dev->state, 0, sizeof(dev->state));
}
if (dev->to_probe == PROBE_PCI) {
dev->how_probe = pci_probe(dev, type_name);
if (dev->how_probe == PROBE_FAILED) {
dev->to_probe = PROBE_ISA;
}
}
if (dev->to_probe == PROBE_ISA) {
dev->how_probe = isa_probe(dev, type_name);
if (dev->how_probe == PROBE_FAILED) {
dev->to_probe = PROBE_NONE;
}
}
if ((dev->to_probe != PROBE_PCI) &&
(dev->to_probe != PROBE_ISA)) {
dev->how_probe = PROBE_FAILED;
}
LeaveFunction("probe");
return dev->how_probe;
}
void disable(struct dev *dev)
{
if (dev->disable) {
dev->disable(dev);
dev->disable = 0;
}
}