#include <ata_adapter.h>
#include <KernelExport.h>
#include <stdlib.h>
#include <string.h>
#define GENERIC_IDE_PCI_CONTROLLER_MODULE_NAME "busses/ata/generic_ide_pci/driver_v1"
#define GENERIC_IDE_PCI_CHANNEL_MODULE_NAME "busses/ata/generic_ide_pci/channel/v1"
#define ATA_PCI_CONTROLLER_TYPE_NAME "ata pci controller"
ata_for_controller_interface *sATA;
static ata_adapter_interface *sATAAdapter;
device_manager_info *sDeviceManager;
static void
set_channel(void *cookie, ata_channel channel)
{
sATAAdapter->set_channel((ata_adapter_channel_info *)cookie, channel);
}
static status_t
write_command_block_regs(void *channel_cookie, ata_task_file *tf,
ata_reg_mask mask)
{
return sATAAdapter->write_command_block_regs(
(ata_adapter_channel_info *)channel_cookie, tf, mask);
}
static status_t
read_command_block_regs(void *channel_cookie, ata_task_file *tf,
ata_reg_mask mask)
{
return sATAAdapter->read_command_block_regs(
(ata_adapter_channel_info *)channel_cookie, tf, mask);
}
static uint8
get_altstatus(void *channel_cookie)
{
return sATAAdapter->get_altstatus(
(ata_adapter_channel_info *)channel_cookie);
}
static status_t
write_device_control(void *channel_cookie, uint8 val)
{
return sATAAdapter->write_device_control(
(ata_adapter_channel_info *)channel_cookie, val);
}
static status_t
write_pio(void *channel_cookie, uint16 *data, int count, bool force_16bit)
{
return sATAAdapter->write_pio((ata_adapter_channel_info *)channel_cookie,
data, count, force_16bit);
}
static status_t
read_pio(void *channel_cookie, uint16 *data, int count, bool force_16bit)
{
return sATAAdapter->read_pio((ata_adapter_channel_info *)channel_cookie,
data, count, force_16bit);
}
static status_t
prepare_dma(void *channel_cookie,
const physical_entry *sg_list, size_t sg_list_count,
bool to_device)
{
return sATAAdapter->prepare_dma((ata_adapter_channel_info *)channel_cookie,
sg_list, sg_list_count, to_device);
}
static status_t
start_dma(void *channel_cookie)
{
return sATAAdapter->start_dma((ata_adapter_channel_info *)channel_cookie);
}
static status_t
finish_dma(void *channel_cookie)
{
return sATAAdapter->finish_dma((ata_adapter_channel_info *)channel_cookie);
}
static status_t
init_channel(device_node *node, void **channel_cookie)
{
return sATAAdapter->init_channel(node,
(ata_adapter_channel_info **)channel_cookie,
sizeof(ata_adapter_channel_info), sATAAdapter->inthand);
}
static void
uninit_channel(void *channel_cookie)
{
sATAAdapter->uninit_channel((ata_adapter_channel_info *)channel_cookie);
}
static void
channel_removed(void *channel_cookie)
{
sATAAdapter->channel_removed((ata_adapter_channel_info *)channel_cookie);
}
static status_t
init_controller(device_node *node, ata_adapter_controller_info **cookie)
{
return sATAAdapter->init_controller(node, cookie,
sizeof( ata_adapter_controller_info));
}
static void
uninit_controller(ata_adapter_controller_info *controller)
{
sATAAdapter->uninit_controller(controller);
}
static void
controller_removed(ata_adapter_controller_info *controller)
{
return sATAAdapter->controller_removed(controller);
}
static status_t
probe_controller(device_node *parent)
{
return sATAAdapter->probe_controller(parent,
GENERIC_IDE_PCI_CONTROLLER_MODULE_NAME, "generic_ide_pci",
"Generic IDE PCI Controller",
GENERIC_IDE_PCI_CHANNEL_MODULE_NAME,
true,
true,
1,
0xffff,
0x10000,
true);
}
static float
supports_device(device_node *parent)
{
const char *bus;
uint16 baseClass, subClass;
if (sDeviceManager->get_attr_string(parent, B_DEVICE_BUS, &bus, false) != B_OK
|| sDeviceManager->get_attr_uint16(parent, B_DEVICE_TYPE, &baseClass, false) != B_OK
|| sDeviceManager->get_attr_uint16(parent, B_DEVICE_SUB_TYPE, &subClass, false) != B_OK)
return -1;
if (strcmp(bus, "pci") || baseClass != PCI_mass_storage)
return 0.0f;
if (subClass == PCI_ide)
return 0.3f;
if (subClass == PCI_mass_storage_other)
return 0.3f;
return 0.0f;
}
module_dependency module_dependencies[] = {
{ ATA_FOR_CONTROLLER_MODULE_NAME, (module_info **)&sATA },
{ B_DEVICE_MANAGER_MODULE_NAME, (module_info **)&sDeviceManager },
{ ATA_ADAPTER_MODULE_NAME, (module_info **)&sATAAdapter },
{}
};
static ata_controller_interface channel_interface = {
{
{
GENERIC_IDE_PCI_CHANNEL_MODULE_NAME,
0,
NULL
},
NULL,
NULL,
init_channel,
uninit_channel,
NULL,
NULL,
channel_removed,
},
&set_channel,
&write_command_block_regs,
&read_command_block_regs,
&get_altstatus,
&write_device_control,
&write_pio,
&read_pio,
&prepare_dma,
&start_dma,
&finish_dma,
};
static driver_module_info controller_interface = {
{
GENERIC_IDE_PCI_CONTROLLER_MODULE_NAME,
0,
NULL
},
supports_device,
probe_controller,
(status_t (*)(device_node *, void **)) init_controller,
(void (*)(void *)) uninit_controller,
NULL,
NULL,
(void (*)(void *)) controller_removed,
};
module_info *modules[] = {
(module_info *)&controller_interface,
(module_info *)&channel_interface,
NULL
};