From ea963c10d14010be3393de2c0bdb2eafe6e80469 Mon Sep 17 00:00:00 2001 From: Michael Lotz Date: Sun, 8 Jun 2008 20:09:12 +0000 Subject: [PATCH] * Adding a driver for the not quite standard IT8211 single channel IDE controller. The device doesn't use the PCI_ide subclass (but PCI_mass_storage_other) and requires not using compatibility mode. Otherwise it's pretty much the generic_ide_pci driver. * Directly adding the driver to the image. This driver could either be merged into the generic ide driver so it supports not quite standard devices, or this could be made into a driver that collects all those non standard devices. Either way, this works for now and lets my machine boot off the IDE drive :-) git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@25868 a95241bf-73f2-0310-859d-f6bbb57e9c96 --- build/jam/HaikuImage | 4 +- src/add-ons/kernel/busses/ide/Jamfile | 1 + src/add-ons/kernel/busses/ide/it8211/Jamfile | 8 + src/add-ons/kernel/busses/ide/it8211/it8211.c | 242 ++++++++++++++++++ 4 files changed, 253 insertions(+), 2 deletions(-) create mode 100644 src/add-ons/kernel/busses/ide/it8211/Jamfile create mode 100644 src/add-ons/kernel/busses/ide/it8211/it8211.c diff --git a/build/jam/HaikuImage b/build/jam/HaikuImage index 7bf35550d3..691758f843 100644 --- a/build/jam/HaikuImage +++ b/build/jam/HaikuImage @@ -145,7 +145,7 @@ AddFilesToHaikuImage beos system add-ons kernel bus_managers AddFilesToHaikuImage beos system add-ons kernel busses agp_gart : $(X86_ONLY)intel ; AddFilesToHaikuImage beos system add-ons kernel busses ide - : generic_ide_pci silicon_image_3112 legacy_sata $(X86_ONLY)ide_isa ; + : generic_ide_pci it8211 legacy_sata silicon_image_3112 $(X86_ONLY)ide_isa ; AddFilesToHaikuImage beos system add-ons kernel busses scsi : ahci ; AddFilesToHaikuImage beos system add-ons kernel busses usb @@ -359,7 +359,7 @@ AddBootModuleSymlinksToHaikuImage pci $(X86_ONLY)isa config_manager ide scsi usb $(PPC_ONLY)openpic block_io ide_adapter locked_pool scsi_periph - generic_ide_pci ahci legacy_sata silicon_image_3112 $(X86_ONLY)ide_isa + ahci generic_ide_pci it8211 legacy_sata silicon_image_3112 $(X86_ONLY)ide_isa uhci ohci ehci scsi_cd scsi_disk usb_disk intel diff --git a/src/add-ons/kernel/busses/ide/Jamfile b/src/add-ons/kernel/busses/ide/Jamfile index 1cb465b96c..04cda2b93a 100644 --- a/src/add-ons/kernel/busses/ide/Jamfile +++ b/src/add-ons/kernel/busses/ide/Jamfile @@ -2,6 +2,7 @@ SubDir HAIKU_TOP src add-ons kernel busses ide ; SubInclude HAIKU_TOP src add-ons kernel busses ide generic_ide_pci ; SubInclude HAIKU_TOP src add-ons kernel busses ide ide_isa ; +SubInclude HAIKU_TOP src add-ons kernel busses ide it8211 ; SubInclude HAIKU_TOP src add-ons kernel busses ide promise_tx2 ; SubInclude HAIKU_TOP src add-ons kernel busses ide silicon_image_3112 ; SubInclude HAIKU_TOP src add-ons kernel busses ide legacy_sata ; diff --git a/src/add-ons/kernel/busses/ide/it8211/Jamfile b/src/add-ons/kernel/busses/ide/it8211/Jamfile new file mode 100644 index 0000000000..423a654ed2 --- /dev/null +++ b/src/add-ons/kernel/busses/ide/it8211/Jamfile @@ -0,0 +1,8 @@ +SubDir HAIKU_TOP src add-ons kernel busses ide it8211 ; + +UsePrivateHeaders kernel ; +UsePrivateHeaders drivers ; + +KernelAddon it8211 : + it8211.c + ; diff --git a/src/add-ons/kernel/busses/ide/it8211/it8211.c b/src/add-ons/kernel/busses/ide/it8211/it8211.c new file mode 100644 index 0000000000..f48a75abc0 --- /dev/null +++ b/src/add-ons/kernel/busses/ide/it8211/it8211.c @@ -0,0 +1,242 @@ +/* + * Copyright 2008, Michael Lotz. All rights reserved. + * Distributed under the terms of the MIT License. + */ +#include +#include +#include + +#include + +#define IT8211_CONTROLLER_MODULE_NAME "busses/ide/it8211/driver_v1" +#define IT8211_CHANNEL_MODULE_NAME "busses/ide/it8211/channel/v1" + +#define PCI_VENDOR_ITE 0x1283 +#define PCI_DEVICE_ITE_IT8211 0x8211 + +static ide_adapter_interface *sIDEAdapter; +static device_manager_info *sDeviceManager; + + +static void +it8211_set_channel(void *channelCookie, ide_channel channel) +{ + sIDEAdapter->set_channel((ide_adapter_channel_info *)channelCookie, + channel); +} + + +static status_t +it8211_write_command_block_regs(void *channelCookie, ide_task_file *taskFile, + ide_reg_mask registerMask) +{ + return sIDEAdapter->write_command_block_regs( + (ide_adapter_channel_info *)channelCookie, taskFile, registerMask); +} + + +static status_t +it8211_read_command_block_regs(void *channelCookie, ide_task_file *taskFile, + ide_reg_mask registerMask) +{ + return sIDEAdapter->read_command_block_regs( + (ide_adapter_channel_info *)channelCookie, taskFile, registerMask); +} + + +static uint8 +it8211_get_altstatus(void *channelCookie) +{ + return sIDEAdapter->get_altstatus((ide_adapter_channel_info *)channelCookie); +} + + +static status_t +it8211_write_device_control(void *channelCookie, uint8 value) +{ + return sIDEAdapter->write_device_control( + (ide_adapter_channel_info *)channelCookie, value); +} + + +static status_t +it8211_write_pio(void *channelCookie, uint16 *data, int count, bool force16bit) +{ + return sIDEAdapter->write_pio( + (ide_adapter_channel_info *)channelCookie, data, count, force16bit); +} + + +static status_t +it8211_read_pio(void *channelCookie, uint16 *data, int count, bool force16bit) +{ + return sIDEAdapter->read_pio( + (ide_adapter_channel_info *)channelCookie, data, count, force16bit); +} + + +static status_t +it8211_prepare_dma(void *channelCookie, const physical_entry *sgList, + size_t sgListCount, bool toDevice) +{ + return sIDEAdapter->prepare_dma((ide_adapter_channel_info *)channelCookie, + sgList, sgListCount, toDevice); +} + + +static status_t +it8211_start_dma(void *channelCookie) +{ + return sIDEAdapter->start_dma((ide_adapter_channel_info *)channelCookie); +} + + +static status_t +it8211_finish_dma(void *channelCookie) +{ + return sIDEAdapter->finish_dma((ide_adapter_channel_info *)channelCookie); +} + + +static status_t +init_channel(device_node *node, void **channelCookie) +{ + return sIDEAdapter->init_channel(node, + (ide_adapter_channel_info **)channelCookie, + sizeof(ide_adapter_channel_info), sIDEAdapter->inthand); +} + + +static void +uninit_channel(void *channelCookie) +{ + sIDEAdapter->uninit_channel((ide_adapter_channel_info *)channelCookie); +} + + +static void +channel_removed(void *channelCookie) +{ + sIDEAdapter->channel_removed((ide_adapter_channel_info *)channelCookie); +} + + +static status_t +init_controller(device_node *node, void **cookie) +{ + return sIDEAdapter->init_controller(node, + (ide_adapter_controller_info **)cookie, + sizeof(ide_adapter_controller_info)); +} + + +static void +uninit_controller(void *cookie) +{ + sIDEAdapter->uninit_controller((ide_adapter_controller_info *)cookie); +} + + +static void +controller_removed(void *cookie) +{ + sIDEAdapter->controller_removed((ide_adapter_controller_info *)cookie); +} + + +static status_t +probe_controller(device_node *parent) +{ + return sIDEAdapter->probe_controller(parent, + IT8211_CONTROLLER_MODULE_NAME, "it8211", + "ITE IT8211", IT8211_CHANNEL_MODULE_NAME, + true, /* DMA */ + true, /* command queuing */ + 1, /* 16 bit alignment */ + 0xffff, /* 64k boundary */ + 0x10000, /* up to 64k per scatter/gather block */ + false); /* no compatibility mode */ +} + + +static float +supports_device(device_node *parent) +{ + const char *bus; + uint16 vendorID; + uint16 deviceID; + + if (sDeviceManager->get_attr_string(parent, B_DEVICE_BUS, &bus, false) != B_OK + || sDeviceManager->get_attr_uint16(parent, B_DEVICE_VENDOR_ID, &vendorID, false) != B_OK + || sDeviceManager->get_attr_uint16(parent, B_DEVICE_ID, &deviceID, false) != B_OK) { + return -1.0f; + } + + if (strcmp(bus, "pci") != 0 || vendorID != PCI_VENDOR_ITE + || deviceID != PCI_DEVICE_ITE_IT8211) + return 0.0f; + + return 1.0f; +} + + +module_dependency module_dependencies[] = { + { B_DEVICE_MANAGER_MODULE_NAME, (module_info **)&sDeviceManager }, + { IDE_ADAPTER_MODULE_NAME, (module_info **)&sIDEAdapter }, + {} +}; + + +// exported interface +static ide_controller_interface sChannelInterface = { + { + { + IT8211_CHANNEL_MODULE_NAME, + 0, + NULL + }, + + NULL, // supports device + NULL, // register device + &init_channel, + &uninit_channel, + NULL, // register child devices + NULL, // rescan + &channel_removed + }, + + &it8211_set_channel, + &it8211_write_command_block_regs, + &it8211_read_command_block_regs, + &it8211_get_altstatus, + &it8211_write_device_control, + &it8211_write_pio, + &it8211_read_pio, + &it8211_prepare_dma, + &it8211_start_dma, + &it8211_finish_dma +}; + + +static driver_module_info sControllerInterface = { + { + IT8211_CONTROLLER_MODULE_NAME, + 0, + NULL + }, + + &supports_device, + &probe_controller, + &init_controller, + &uninit_controller, + NULL, // register child devices + NULL, // rescan + &controller_removed +}; + + +module_info *modules[] = { + (module_info *)&sControllerInterface, + (module_info *)&sChannelInterface, + NULL +};