Commit 6ed83574 authored by Linus Torvalds's avatar Linus Torvalds

Import 2.3.35pre6

parent 159f5e24
......@@ -30,7 +30,6 @@
struct pci_bus *pci_root;
struct pci_dev *pci_devices = NULL;
static struct pci_dev **pci_last_dev_p = &pci_devices;
static int pci_reverse __initdata = 0;
struct pci_dev *
pci_find_slot(unsigned int bus, unsigned int devfn)
......@@ -270,7 +269,7 @@ static inline unsigned int pci_resource_flags(unsigned int flags)
return IORESOURCE_MEM;
}
void __init pci_read_bases(struct pci_dev *dev, unsigned int howmany, int rom)
static void __init pci_read_bases(struct pci_dev *dev, unsigned int howmany, int rom)
{
unsigned int pos, reg, next;
u32 l, sz, tmp;
......@@ -433,7 +432,7 @@ static __init struct pci_bus *pci_add_new_bus(struct pci_bus *parent, struct pci
/*
* Set up the primary, secondary and subordinate
* bus numbers. Read resource ranges behind the bridge.
* bus numbers.
*/
child->number = child->secondary = busnr;
child->primary = parent->secondary;
......@@ -578,24 +577,29 @@ static __init void pci_read_irq(struct pci_dev *dev)
}
/*
* Read the config data for a PCI device
* and sanity-check it and fill in the dev
* structure...
* Read the config data for a PCI device, sanity-check it
* and fill in the dev structure...
*/
static __init int pci_scan_device(struct pci_bus *bus, struct pci_dev *dev, unsigned int devfn)
static struct pci_dev * __init pci_scan_device(struct pci_dev *temp)
{
unsigned int l, class;
struct pci_dev *dev;
u32 l, class;
if (pci_read_config_dword(dev, PCI_VENDOR_ID, &l))
return -1;
if (pci_read_config_dword(temp, PCI_VENDOR_ID, &l))
return NULL;
/* some broken boards return 0 if a slot is empty: */
/* some broken boards return 0 or ~0 if a slot is empty: */
if (l == 0xffffffff || l == 0x00000000 || l == 0x0000ffff || l == 0xffff0000)
return -1;
return NULL;
dev = kmalloc(sizeof(*dev), GFP_KERNEL);
if (!dev)
return NULL;
memcpy(dev, temp, sizeof(*dev));
dev->vendor = l & 0xffff;
dev->device = (l >> 16) & 0xffff;
sprintf(dev->slot_name, "%02x:%02x.%d", bus->number, PCI_SLOT(devfn), PCI_FUNC(devfn));
sprintf(dev->slot_name, "%02x:%02x.%d", dev->bus->number, PCI_SLOT(dev->devfn), PCI_FUNC(dev->devfn));
pci_name_device(dev);
pci_read_config_dword(dev, PCI_CLASS_REVISION, &class);
......@@ -631,7 +635,8 @@ static __init int pci_scan_device(struct pci_bus *bus, struct pci_dev *dev, unsi
default: /* unknown header */
printk(KERN_ERR "PCI: device %s has unknown header type %02x, ignoring.\n",
dev->slot_name, dev->hdr_type);
return -1;
kfree(dev);
return NULL;
bad:
printk(KERN_ERR "PCI: %s: class %x doesn't match header type %02x. Ignoring class.\n",
......@@ -640,47 +645,32 @@ static __init int pci_scan_device(struct pci_bus *bus, struct pci_dev *dev, unsi
}
/* We found a fine healthy device, go go go... */
return 0;
return dev;
}
static unsigned int __init pci_do_scan_bus(struct pci_bus *bus)
struct pci_dev * __init pci_scan_slot(struct pci_dev *temp)
{
unsigned int devfn, max;
struct pci_dev *dev, **bus_last;
struct pci_bus *bus = temp->bus;
struct pci_dev *dev;
struct pci_dev *first_dev = NULL;
int func = 0;
int is_multi = 0;
u8 hdr_type;
DBG("pci_do_scan_bus for bus %d\n", bus->number);
bus_last = &bus->devices;
max = bus->secondary;
/* Allocate the device ahead of time.. */
dev = kmalloc(sizeof(*dev), GFP_KERNEL);
if (!dev)
return max;
/* Go find them, Rover! */
for (devfn = 0; devfn < 0xff; ++devfn) {
unsigned char hdr_type;
/* not a multi-function device */
if (PCI_FUNC(devfn) && !is_multi)
for (func = 0; func < 8; func++, temp->devfn++) {
if (func && !is_multi) /* not a multi-function device */
continue;
memset(dev, 0, sizeof(*dev));
dev->bus = bus;
dev->sysdata = bus->sysdata;
dev->devfn = devfn;
if (pci_read_config_byte(dev, PCI_HEADER_TYPE, &hdr_type))
if (pci_read_config_byte(temp, PCI_HEADER_TYPE, &hdr_type))
continue;
temp->hdr_type = hdr_type & 0x7f;
if (!PCI_FUNC(devfn))
is_multi = hdr_type & 0x80;
dev->hdr_type = hdr_type & 0x7f;
if (pci_scan_device(bus, dev, devfn))
dev = pci_scan_device(temp);
if (!dev)
continue;
if (!func) {
is_multi = hdr_type & 0x80;
first_dev = dev;
}
DBG("PCI: %02x:%02x [%04x/%04x] %06x %02x\n", bus->number, dev->devfn, dev->vendor, dev->device, class, hdr_type);
......@@ -688,37 +678,41 @@ static unsigned int __init pci_do_scan_bus(struct pci_bus *bus)
* Put it into the global PCI device chain. It's used to
* find devices once everything is set up.
*/
if (!pci_reverse) {
*pci_last_dev_p = dev;
pci_last_dev_p = &dev->next;
} else {
dev->next = pci_devices;
pci_devices = dev;
}
*pci_last_dev_p = dev;
pci_last_dev_p = &dev->next;
/*
* Now insert it into the list of devices held
* by the parent bus.
*/
*bus_last = dev;
bus_last = &dev->sibling;
*bus->last_dev_p = dev;
bus->last_dev_p = &dev->sibling;
/* Fix up broken headers */
pci_fixup_device(PCI_FIXUP_HEADER, dev);
}
return first_dev;
}
#if 0
/*
* Setting of latency timer in case it was less than 32 was
* a great idea, but it confused several broken devices. Grrr.
*/
pci_read_config_byte(dev, PCI_LATENCY_TIMER, &tmp);
if (tmp < 32)
pci_write_config_byte(dev, PCI_LATENCY_TIMER, 32);
#endif
static unsigned int __init pci_do_scan_bus(struct pci_bus *bus)
{
unsigned int devfn, max;
struct pci_dev *dev, dev0;
dev = kmalloc(sizeof(*dev), GFP_KERNEL);
DBG("pci_do_scan_bus for bus %d\n", bus->number);
bus->last_dev_p = &bus->devices;
max = bus->secondary;
/* Create a device template */
memset(&dev0, 0, sizeof(dev0));
dev0.bus = bus;
dev0.sysdata = bus->sysdata;
/* Go find them, Rover! */
for (devfn = 0; devfn < 0x100; devfn += 8) {
dev0.devfn = devfn;
pci_scan_slot(&dev0);
}
kfree(dev);
/*
* After performing arch-dependent fixup of the bus, look behind
......@@ -759,7 +753,7 @@ static int __init pci_bus_exists(struct pci_bus *b, int nr)
return 0;
}
struct pci_bus * __init pci_scan_bus(int bus, struct pci_ops *ops, void *sysdata)
struct pci_bus * __init pci_alloc_primary_bus(int bus)
{
struct pci_bus *b, **r;
......@@ -779,11 +773,19 @@ struct pci_bus * __init pci_scan_bus(int bus, struct pci_ops *ops, void *sysdata
*r = b;
b->number = b->secondary = bus;
b->sysdata = sysdata;
b->ops = ops;
b->resource[0] = &ioport_resource;
b->resource[1] = &iomem_resource;
b->subordinate = pci_do_scan_bus(b);
return b;
}
struct pci_bus * __init pci_scan_bus(int bus, struct pci_ops *ops, void *sysdata)
{
struct pci_bus *b = pci_alloc_primary_bus(bus);
if (b) {
b->sysdata = sysdata;
b->ops = ops;
b->subordinate = pci_do_scan_bus(b);
}
return b;
}
......@@ -804,9 +806,8 @@ static int __init pci_setup(char *str)
if (k)
*k++ = 0;
if (*str && (str = pcibios_setup(str)) && *str) {
if (!strcmp(str, "reverse"))
pci_reverse = 1;
else printk(KERN_ERR "PCI: Unknown option `%s'\n", str);
/* PCI layer options should be handled here */
printk(KERN_ERR "PCI: Unknown option `%s'\n", str);
}
str = k;
}
......
......@@ -25,6 +25,8 @@ EXPORT_SYMBOL(pci_find_device);
EXPORT_SYMBOL(pci_find_slot);
EXPORT_SYMBOL(pci_set_master);
EXPORT_SYMBOL(pci_simple_probe);
EXPORT_SYMBOL(pci_set_power_state);
EXPORT_SYMBOL(pci_assign_resource);
#ifdef CONFIG_PROC_FS
EXPORT_SYMBOL(pci_proc_attach_device);
EXPORT_SYMBOL(pci_proc_detach_device);
......
......@@ -283,20 +283,21 @@ int cb_alloc(socket_info_t *s)
u_char i, hdr, fn, bus = s->cap.cardbus;
cb_config_t *c;
memset(&tmp, 0, sizeof(tmp));
tmp.bus = s->cap.cb_bus; tmp.devfn = 0;
tmp.next = pci_devices; pci_devices = &tmp;
pci_readw(bus, 0, PCI_VENDOR_ID, &vend);
pci_readw(bus, 0, PCI_DEVICE_ID, &dev);
pci_read_config_word(&tmp, PCI_VENDOR_ID, &vend);
pci_read_config_word(&tmp, PCI_DEVICE_ID, &dev);
printk(KERN_INFO "cs: cb_alloc(bus %d): vendor 0x%04x, "
"device 0x%04x\n", bus, vend, dev);
pci_readb(bus, 0, PCI_HEADER_TYPE, &hdr);
pci_read_config_byte(&tmp, PCI_HEADER_TYPE, &hdr);
if (hdr & 0x80) {
/* Count functions */
for (fn = 0; fn < 8; fn++) {
tmp.devfn = fn;
pci_readw(bus, fn, PCI_VENDOR_ID, &v);
pci_read_config_word(&tmp, PCI_VENDOR_ID, &v);
if (v != vend) break;
}
} else fn = 1;
......@@ -307,7 +308,6 @@ int cb_alloc(socket_info_t *s)
memset(c, 0, fn * sizeof(struct cb_config_t));
s->cb_config = c;
pci_devices = tmp.next;
for (i = 0; i < fn; i++) {
c[i].dev.bus = s->cap.cb_bus;
c[i].dev.devfn = i;
......@@ -317,7 +317,7 @@ int cb_alloc(socket_info_t *s)
}
s->cap.cb_bus->devices = &c[0].dev;
/* Link into PCI device chain */
c[s->functions-1].dev.next = pci_devices;
c[fn-1].dev.next = pci_devices;
pci_devices = &c[0].dev;
for (i = 0; i < fn; i++) {
c[i].dev.vendor = vend;
......@@ -338,17 +338,17 @@ void cb_free(socket_info_t *s)
cb_config_t *c = s->cb_config;
if (c) {
struct pci_dev **p, *q;
struct pci_dev **p;
/* Unlink from PCI device chain */
for (p = &pci_devices; *p; p = &((*p)->next))
if (*p == &c[0].dev) break;
for (q = *p; q; q = q->next) {
if (q->bus != (*p)->bus) break;
for (p = &pci_devices; *p; p = &((*p)->next)) {
struct pci_dev * dev = *p;
if (dev->bus != s->cap.cb_bus)
continue;
*p = dev->next;
#ifdef CONFIG_PROC_FS
pci_proc_detach_device(q);
pci_proc_detach_device(dev);
#endif
}
if (*p) *p = q;
s->cap.cb_bus->devices = NULL;
kfree(s->cb_config);
s->cb_config = NULL;
......
......@@ -159,8 +159,6 @@ MODULE_PARM(recov_time, "i");
#ifdef CONFIG_PCI
/* Scan PCI bus? */
static int do_pci_probe = 1;
/* Default memory base address for CardBus controllers */
static u_int cb_mem_base[] = { 0x68000000, 0xf8000000 };
static int fast_pci = -1;
static int hold_time = -1;
/* Override BIOS interrupt routing mode? */
......@@ -173,7 +171,6 @@ static int cb_bus_base = 0;
static int cb_bus_step = 2;
static int cb_write_post = -1;
MODULE_PARM(do_pci_probe, "i");
MODULE_PARM(cb_mem_base, "i");
MODULE_PARM(fast_pci, "i");
MODULE_PARM(hold_time, "i");
MODULE_PARM(irq_mode, "i");
......@@ -249,11 +246,11 @@ typedef struct socket_info_t {
struct proc_dir_entry *proc;
#endif
#ifdef CONFIG_PCI
u_short vendor, device;
u_char revision, bus, devfn;
struct pci_dev *pdev;
u_char revision;
u_short bcr;
u_char pci_lat, cb_lat, sub_bus;
u_char cache, pmcs;
u_char cache;
u_int cb_phys;
char *cb_virt;
#endif
......@@ -294,24 +291,10 @@ static struct timer_list poll_timer;
/*====================================================================*/
#ifdef CONFIG_PCI
#ifndef PCI_VENDOR_ID_INTEL
#define PCI_VENDOR_ID_INTEL 0x8086
#endif
#ifndef PCI_VENDOR_ID_OMEGA
#define PCI_VENDOR_ID_OMEGA 0x119b
#endif
#ifndef PCI_DEVICE_ID_OMEGA_PCMCIA
#define PCI_DEVICE_ID_OMEGA_PCMCIA 0x1221
#endif
/* Default settings for PCI command configuration register */
#define CMD_DFLT (PCI_COMMAND_IO|PCI_COMMAND_MEMORY| \
PCI_COMMAND_MASTER|PCI_COMMAND_WAIT)
#endif
/* These definitions must match the pcic table! */
typedef enum pcic_id {
#ifdef CONFIG_ISA
......@@ -379,9 +362,9 @@ static pcic_t pcic[] = {
{ "O2Micro OZ6730", IS_O2MICRO|IS_PCI|IS_VG_PWR,
PCI_VENDOR_ID_O2, PCI_DEVICE_ID_O2_6730 },
{ "Intel 82092AA", IS_PCI,
PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_OMEGA_PCMCIA },
PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82092AA_0 },
{ "Omega Micro 82C092G", IS_PCI,
PCI_VENDOR_ID_OMEGA, PCI_DEVICE_ID_OMEGA_PCMCIA },
PCI_VENDOR_ID_OMEGA, PCI_DEVICE_ID_OMEGA_82C092G },
{ "Cirrus PD6832", IS_CIRRUS|IS_CARDBUS,
PCI_VENDOR_ID_CIRRUS, PCI_DEVICE_ID_CIRRUS_6832 },
{ "O2Micro OZ6832/OZ6833", IS_O2MICRO|IS_CARDBUS|IS_VG_PWR,
......@@ -443,12 +426,12 @@ static pcic_t pcic[] = {
/* Some PCI shortcuts */
#define pci_readb pcibios_read_config_byte
#define pci_writeb pcibios_write_config_byte
#define pci_readw pcibios_read_config_word
#define pci_writew pcibios_write_config_word
#define pci_readl pcibios_read_config_dword
#define pci_writel pcibios_write_config_dword
#define config_readb(sock, r, v) pci_read_config_byte((sock)->pdev, r, v)
#define config_readw(sock, r, v) pci_read_config_word((sock)->pdev, r, v)
#define config_readl(sock, r, v) pci_read_config_dword((sock)->pdev, r, v)
#define config_writeb(sock, r, v) pci_write_config_byte((sock)->pdev, r, v)
#define config_writew(sock, r, v) pci_write_config_word((sock)->pdev, r, v)
#define config_writel(sock, r, v) pci_write_config_dword((sock)->pdev, r, v)
#define cb_readb(s, r) readb(socket[s].cb_virt + (r))
#define cb_readl(s, r) readl(socket[s].cb_virt + (r))
......@@ -701,21 +684,21 @@ static void ti113x_get_state(u_short s)
{
socket_info_t *t = &socket[s];
ti113x_state_t *p = &socket[s].state.ti113x;
pci_readl(t->bus, t->devfn, TI113X_SYSTEM_CONTROL, &p->sysctl);
pci_readb(t->bus, t->devfn, TI113X_CARD_CONTROL, &p->cardctl);
pci_readb(t->bus, t->devfn, TI113X_DEVICE_CONTROL, &p->devctl);
pci_readb(t->bus, t->devfn, TI1250_DIAGNOSTIC, &p->diag);
config_readl(t, TI113X_SYSTEM_CONTROL, &p->sysctl);
config_readb(t, TI113X_CARD_CONTROL, &p->cardctl);
config_readb(t, TI113X_DEVICE_CONTROL, &p->devctl);
config_readb(t, TI1250_DIAGNOSTIC, &p->diag);
}
static void ti113x_set_state(u_short s)
{
socket_info_t *t = &socket[s];
ti113x_state_t *p = &socket[s].state.ti113x;
pci_writel(t->bus, t->devfn, TI113X_SYSTEM_CONTROL, p->sysctl);
pci_writeb(t->bus, t->devfn, TI113X_CARD_CONTROL, p->cardctl);
pci_writeb(t->bus, t->devfn, TI113X_DEVICE_CONTROL, p->devctl);
pci_writeb(t->bus, t->devfn, TI1250_MULTIMEDIA_CTL, 0);
pci_writeb(t->bus, t->devfn, TI1250_DIAGNOSTIC, p->diag);
config_writel(t, TI113X_SYSTEM_CONTROL, p->sysctl);
config_writeb(t, TI113X_CARD_CONTROL, p->cardctl);
config_writeb(t, TI113X_DEVICE_CONTROL, p->devctl);
config_writeb(t, TI1250_MULTIMEDIA_CTL, 0);
config_writeb(t, TI1250_DIAGNOSTIC, p->diag);
i365_set_pair(s, TI113X_IO_OFFSET(0), 0);
i365_set_pair(s, TI113X_IO_OFFSET(1), 0);
}
......@@ -822,20 +805,20 @@ static void rl5c4xx_get_state(u_short s)
{
socket_info_t *t = &socket[s];
rl5c4xx_state_t *p = &socket[s].state.rl5c4xx;
pci_readw(t->bus, t->devfn, RL5C4XX_MISC, &p->misc);
pci_readw(t->bus, t->devfn, RL5C4XX_16BIT_CTL, &p->ctl);
pci_readw(t->bus, t->devfn, RL5C4XX_16BIT_IO_0, &p->io);
pci_readw(t->bus, t->devfn, RL5C4XX_16BIT_MEM_0, &p->mem);
config_readw(t, RL5C4XX_MISC, &p->misc);
config_readw(t, RL5C4XX_16BIT_CTL, &p->ctl);
config_readw(t, RL5C4XX_16BIT_IO_0, &p->io);
config_readw(t, RL5C4XX_16BIT_MEM_0, &p->mem);
}
static void rl5c4xx_set_state(u_short s)
{
socket_info_t *t = &socket[s];
rl5c4xx_state_t *p = &socket[s].state.rl5c4xx;
pci_writew(t->bus, t->devfn, RL5C4XX_MISC, p->misc);
pci_writew(t->bus, t->devfn, RL5C4XX_16BIT_CTL, p->ctl);
pci_writew(t->bus, t->devfn, RL5C4XX_16BIT_IO_0, p->io);
pci_writew(t->bus, t->devfn, RL5C4XX_16BIT_MEM_0, p->mem);
config_writew(t, RL5C4XX_MISC, p->misc);
config_writew(t, RL5C4XX_16BIT_CTL, p->ctl);
config_writew(t, RL5C4XX_16BIT_IO_0, p->io);
config_writew(t, RL5C4XX_16BIT_MEM_0, p->mem);
}
static u_int __init rl5c4xx_set_opts(u_short s, char *buf)
......@@ -986,20 +969,20 @@ static void topic_get_state(u_short s)
{
socket_info_t *t = &socket[s];
topic_state_t *p = &socket[s].state.topic;
pci_readb(t->bus, t->devfn, TOPIC_SLOT_CONTROL, &p->slot);
pci_readb(t->bus, t->devfn, TOPIC_CARD_CONTROL, &p->ccr);
pci_readb(t->bus, t->devfn, TOPIC_CARD_DETECT, &p->cdr);
pci_readl(t->bus, t->devfn, TOPIC_REGISTER_CONTROL, &p->rcr);
config_readb(t, TOPIC_SLOT_CONTROL, &p->slot);
config_readb(t, TOPIC_CARD_CONTROL, &p->ccr);
config_readb(t, TOPIC_CARD_DETECT, &p->cdr);
config_readl(t, TOPIC_REGISTER_CONTROL, &p->rcr);
}
static void topic_set_state(u_short s)
{
socket_info_t *t = &socket[s];
topic_state_t *p = &socket[s].state.topic;
pci_writeb(t->bus, t->devfn, TOPIC_SLOT_CONTROL, p->slot);
pci_writeb(t->bus, t->devfn, TOPIC_CARD_CONTROL, p->ccr);
pci_writeb(t->bus, t->devfn, TOPIC_CARD_DETECT, p->cdr);
pci_writel(t->bus, t->devfn, TOPIC_REGISTER_CONTROL, p->rcr);
config_writeb(t, TOPIC_SLOT_CONTROL, p->slot);
config_writeb(t, TOPIC_CARD_CONTROL, p->ccr);
config_writeb(t, TOPIC_CARD_DETECT, p->cdr);
config_writel(t, TOPIC_REGISTER_CONTROL, p->rcr);
}
static int topic_set_irq_mode(u_short s, int pcsc, int pint)
......@@ -1040,33 +1023,28 @@ static void cb_get_state(u_short s)
{
socket_info_t *t = &socket[s];
pci_readb(t->bus, t->devfn, PCI_CACHE_LINE_SIZE, &t->cache);
pci_readb(t->bus, t->devfn, PCI_LATENCY_TIMER, &t->pci_lat);
pci_readb(t->bus, t->devfn, CB_LATENCY_TIMER, &t->cb_lat);
pci_readb(t->bus, t->devfn, CB_CARDBUS_BUS, &t->cap.cardbus);
pci_readb(t->bus, t->devfn, CB_SUBORD_BUS, &t->sub_bus);
pci_readw(t->bus, t->devfn, CB_BRIDGE_CONTROL, &t->bcr);
{
struct pci_dev *pdev = pci_find_slot(t->bus, t->devfn);
t->cap.pci_irq = (pdev) ? pdev->irq : 0;
}
if (t->cap.pci_irq >= NR_IRQS) t->cap.pci_irq = 0;
config_readb(t, PCI_CACHE_LINE_SIZE, &t->cache);
config_readb(t, PCI_LATENCY_TIMER, &t->pci_lat);
config_readb(t, CB_LATENCY_TIMER, &t->cb_lat);
config_readb(t, CB_CARDBUS_BUS, &t->cap.cardbus);
config_readb(t, CB_SUBORD_BUS, &t->sub_bus);
config_readw(t, CB_BRIDGE_CONTROL, &t->bcr);
t->cap.pci_irq = t->pdev->irq;
}
static void cb_set_state(u_short s)
{
socket_info_t *t = &socket[s];
if (t->pmcs)
pci_writew(t->bus, t->devfn, t->pmcs, PCI_PMCS_PWR_STATE_D0);
pci_writel(t->bus, t->devfn, CB_LEGACY_MODE_BASE, 0);
pci_writel(t->bus, t->devfn, PCI_BASE_ADDRESS_0, t->cb_phys);
pci_writew(t->bus, t->devfn, PCI_COMMAND, CMD_DFLT);
pci_writeb(t->bus, t->devfn, PCI_CACHE_LINE_SIZE, t->cache);
pci_writeb(t->bus, t->devfn, PCI_LATENCY_TIMER, t->pci_lat);
pci_writeb(t->bus, t->devfn, CB_LATENCY_TIMER, t->cb_lat);
pci_writeb(t->bus, t->devfn, CB_CARDBUS_BUS, t->cap.cardbus);
pci_writeb(t->bus, t->devfn, CB_SUBORD_BUS, t->sub_bus);
pci_writew(t->bus, t->devfn, CB_BRIDGE_CONTROL, t->bcr);
pci_set_power_state(t->pdev, 0); /* FIXME: Do we really need all of this? */
config_writel(t, CB_LEGACY_MODE_BASE, 0);
config_writel(t, PCI_BASE_ADDRESS_0, t->cb_phys);
config_writew(t, PCI_COMMAND, CMD_DFLT);
config_writeb(t, PCI_CACHE_LINE_SIZE, t->cache);
config_writeb(t, PCI_LATENCY_TIMER, t->pci_lat);
config_writeb(t, CB_LATENCY_TIMER, t->cb_lat);
config_writeb(t, CB_CARDBUS_BUS, t->cap.cardbus);
config_writeb(t, CB_SUBORD_BUS, t->sub_bus);
config_writew(t, CB_BRIDGE_CONTROL, t->bcr);
}
static int cb_get_irq_mode(u_short s)
......@@ -1500,13 +1478,11 @@ static void __init add_pcic(int ns, int type)
printk(KERN_INFO " %s", pcic[type].name);
#ifdef CONFIG_PCI
if (t->flags & IS_UNKNOWN)
printk(" [0x%04x 0x%04x]", t->vendor, t->device);
printk(" [0x%04x 0x%04x]", t->pdev->vendor, t->pdev->device);
if (t->flags & IS_CARDBUS)
printk(" PCI-to-CardBus at bus %d slot %d, mem 0x%08x",
t->bus, PCI_SLOT(t->devfn), t->cb_phys);
printk(" PCI-to-CardBus at %s, mem 0x%08x", t->pdev->slot_name, t->cb_phys);
else if (t->flags & IS_PCI)
printk(" PCI-to-PCMCIA at bus %d slot %d, port %#x",
t->bus, PCI_SLOT(t->devfn), t->ioaddr);
printk(" PCI-to-PCMCIA at %s, port %#x", t->pdev->slot_name, t->ioaddr);
else
#endif
printk(" ISA-to-PCMCIA at port %#x ofs 0x%02x",
......@@ -1596,107 +1572,50 @@ static void __init add_pcic(int ns, int type)
#ifdef CONFIG_PCI
typedef struct pci_dev *pci_id_t;
static int __init pci_lookup(u_int class, pci_id_t *id,
u_char *bus, u_char *devfn)
{
if ((*id = pci_find_class(class<<8, *id)) != NULL) {
*bus = (*id)->bus->number;
*devfn = (*id)->devfn;
return 0;
} else return -1;
}
static void __init add_pci_bridge(int type, u_char bus, u_char devfn,
u_short v, u_short d)
static void __init add_pci_bridge(int type, struct pci_dev *dev)
{
socket_info_t *s = &socket[sockets];
u_short i, ns;
u_int addr;
u32 addr = dev->resource[0].start;
if (type == PCIC_COUNT) type = IS_UNK_PCI;
pci_readl(bus, devfn, PCI_BASE_ADDRESS_0, &addr);
addr &= ~0x1;
pci_writew(bus, devfn, PCI_COMMAND, CMD_DFLT);
pci_write_config_word(dev, PCI_COMMAND, CMD_DFLT);
for (i = ns = 0; i < ((type == IS_I82092AA) ? 4 : 2); i++) {
s->bus = bus; s->devfn = devfn;
s->vendor = v; s->device = d;
s->pdev = dev;
add_socket(addr, i, type);
ns++; s++;
}
add_pcic(ns, type);
}
static void __init add_cb_bridge(int type, u_char bus, u_char devfn,
u_short v, u_short d0)
static void __init add_cb_bridge(int type, struct pci_dev *dev0)
{
socket_info_t *s = &socket[sockets];
u_short d, ns, i;
u_char a, b, r, max;
/* PCI bus enumeration is broken on some systems */
for (ns = 0; ns < sockets; ns++)
if ((socket[ns].bus == bus) && (socket[ns].devfn == devfn))
return;
if (type == PCIC_COUNT) type = IS_UNK_CARDBUS;
pci_readb(bus, devfn, PCI_HEADER_TYPE, &a);
pci_readb(bus, devfn, PCI_CLASS_REVISION, &r);
max = (a & 0x80) ? 8 : 1;
for (ns = 0; ns < max; ns++, s++, devfn++) {
if (pci_readw(bus, devfn, PCI_DEVICE_ID, &d) || (d != d0))
break;
s->bus = bus; s->devfn = devfn;
s->vendor = v; s->device = d; s->revision = r;
/* Check for power management capabilities */
pci_readb(bus, devfn, PCI_STATUS, &a);
if (a & PCI_STATUS_CAPLIST) {
pci_readb(bus, devfn, PCI_CB_CAPABILITY_POINTER, &b);
while (b != 0) {
pci_readb(bus, devfn, b+PCI_CAPABILITY_ID, &a);
if (a == PCI_CAPABILITY_PM) {
s->pmcs = b + PCI_PM_CONTROL_STATUS;
break;
}
pci_readb(bus, devfn, b+PCI_NEXT_CAPABILITY, &b);
}
}
/* If capability exists, make sure we're in D0 state */
if (s->pmcs)
pci_writew(bus, devfn, s->pmcs, PCI_PMCS_PWR_STATE_D0);
/* Map CardBus registers if they are not already mapped */
pci_writel(bus, devfn, CB_LEGACY_MODE_BASE, 0);
pci_readl(bus, devfn, PCI_BASE_ADDRESS_0, &s->cb_phys);
if (s->cb_phys == 0) {
pci_writew(bus, devfn, PCI_COMMAND, CMD_DFLT);
for (i = 0; i < sizeof(cb_mem_base)/sizeof(u_int); i++) {
s->cb_phys = cb_mem_base[i];
s->cb_virt = ioremap(s->cb_phys, 0x1000);
pci_writel(bus, devfn, PCI_BASE_ADDRESS_0, s->cb_phys);
/* Simple sanity checks */
if (!(readb(s->cb_virt+0x800+I365_IDENT) & 0x70) &&
!(readb(s->cb_virt+0x800+I365_CSC) &&
readb(s->cb_virt+0x800+I365_CSC) &&
readb(s->cb_virt+0x800+I365_CSC)))
break;
iounmap(s->cb_virt);
}
if (i == sizeof(cb_mem_base)/sizeof(u_int)) {
pci_writel(bus, devfn, PCI_BASE_ADDRESS_0, 0);
s->cb_phys = 0; s->cb_virt = NULL;
printk("\n");
printk(KERN_NOTICE " Bridge register mapping failed:"
" check cb_mem_base setting\n");
u_short i, ns;
u_char a, b;
if (type == PCIC_COUNT)
type = IS_UNK_CARDBUS;
for (ns = 0; ns < 8; ns++, s++) {
struct pci_dev *dev;
dev = pci_find_slot(dev0->bus->number, dev0->devfn + ns);
if (!dev)
break;
}
cb_mem_base[0] = cb_mem_base[i] + PAGE_SIZE;
} else {
s->cb_virt = ioremap(s->cb_phys, 0x1000);
s->pdev = dev;
pci_read_config_byte(dev, PCI_CLASS_REVISION, &s->revision);
/* Map CardBus registers if they are not already mapped */
pci_write_config_dword(dev, CB_LEGACY_MODE_BASE, 0);
s->cb_phys = dev->resource[0].start;
if (!s->cb_phys || !(s->cb_virt = ioremap(s->cb_phys, 0x1000))) {
printk("\n");
printk(KERN_ERR " No control registers found!\n");
break;
}
request_mem_region(s->cb_phys, 0x1000, "i82365");
s->cap.cb_bus = dev->subordinate;
add_socket(0, 0, type);
}
if (ns == 0) return;
......@@ -1704,11 +1623,11 @@ static void __init add_cb_bridge(int type, u_char bus, u_char devfn,
s -= ns;
if (ns == 2) {
/* Nasty special check for bad bus mapping */
pci_readb(bus, s[0].devfn, CB_CARDBUS_BUS, &a);
pci_readb(bus, s[1].devfn, CB_CARDBUS_BUS, &b);
config_readb(&s[0], CB_CARDBUS_BUS, &a);
config_readb(&s[1], CB_CARDBUS_BUS, &b);
if (a == b) {
pci_writeb(bus, s[0].devfn, CB_CARDBUS_BUS, 0);
pci_writeb(bus, s[1].devfn, CB_CARDBUS_BUS, 0);
config_writeb(&s[0], CB_CARDBUS_BUS, 0);
config_writeb(&s[1], CB_CARDBUS_BUS, 0);
}
}
add_pcic(ns, type);
......@@ -1728,43 +1647,19 @@ static void __init add_cb_bridge(int type, u_char bus, u_char devfn,
if (i == 200)
printk(KERN_NOTICE "i82365: card voltage interrogation"
" timed out!\n");
/* Set up PCI bus bridge structures if needed */
for (a = 0; a < ns; a++) {
struct pci_dev *self = pci_find_slot(bus, s[a].devfn);
struct pci_bus *child, *parent = self->bus;
for (child = parent->children; child; child = child->next)
if (child->number == s[a].cap.cardbus) break;
if (!child) {
child = kmalloc(sizeof(struct pci_bus), GFP_KERNEL);
memset(child, 0, sizeof(struct pci_bus));
child->self = self;
child->primary = bus;
child->number = child->secondary = s[a].cap.cardbus;
child->subordinate = s[a].sub_bus;
child->parent = parent;
child->ops = parent->ops;
child->next = parent->children;
}
s[a].cap.cb_bus = parent->children = child;
}
}
static void __init pci_probe(u_int class, void (add_fn)
(int, u_char, u_char, u_short, u_short))
static void __init pci_probe(u_int class, void (add_fn)(int, struct pci_dev *))
{
u_short i, v, d;
u_char bus, devfn;
pci_id_t id;
id = 0;
while (pci_lookup(class, &id, &bus, &devfn) == 0) {
if (PCI_FUNC(devfn) != 0) continue;
pci_readw(bus, devfn, PCI_VENDOR_ID, &v);
pci_readw(bus, devfn, PCI_DEVICE_ID, &d);
struct pci_dev *dev = NULL;
u_short i;
while ((dev = pci_find_class(class << 8, dev))) {
pci_enable_device(dev);
if (PCI_FUNC(dev->devfn) != 0) continue;
for (i = 0; i < PCIC_COUNT; i++)
if ((pcic[i].vendor == v) && (pcic[i].device == d)) break;
add_fn(i, bus, devfn, v, d);
if ((pcic[i].vendor == dev->vendor) && (pcic[i].device == dev->device)) break;
add_fn(i, dev);
}
}
......@@ -2397,7 +2292,7 @@ static int cb_get_socket(u_short sock, socket_state_t *state)
u_short bcr;
cb_get_power(sock, state);
pci_readw(s->bus, s->devfn, CB_BRIDGE_CONTROL, &bcr);
config_readw(s, CB_BRIDGE_CONTROL, &bcr);
state->flags |= (bcr & CB_BCR_CB_RESET) ? SS_RESET : 0;
if (cb_get_irq_mode(sock) != 0)
state->io_irq = s->cap.pci_irq;
......@@ -2454,15 +2349,15 @@ static int cb_get_bridge(u_short sock, struct cb_bridge_map *m)
if (map > 1) return -EINVAL;
m->flags &= MAP_IOSPACE;
map += (m->flags & MAP_IOSPACE) ? 2 : 0;
pci_readl(s->bus, s->devfn, CB_MEM_BASE(map), &m->start);
pci_readl(s->bus, s->devfn, CB_MEM_LIMIT(map), &m->stop);
config_readl(s, CB_MEM_BASE(map), &m->start);
config_readl(s, CB_MEM_LIMIT(map), &m->stop);
if (m->start || m->stop) {
m->flags |= MAP_ACTIVE;
m->stop |= (map > 1) ? 3 : 0x0fff;
}
if (map > 1) {
u_short bcr;
pci_readw(s->bus, s->devfn, CB_BRIDGE_CONTROL, &bcr);
config_readw(s, CB_BRIDGE_CONTROL, &bcr);
m->flags |= (bcr & CB_BCR_PREFETCH(map)) ? MAP_PREFETCH : 0;
}
DEBUG(1, "yenta: GetBridge(%d, %d) = %#2.2x, %#4.4x-%#4.4x\n",
......@@ -2489,17 +2384,17 @@ static int cb_set_bridge(u_short sock, struct cb_bridge_map *m)
u_short bcr;
if ((m->start & 0x0fff) || ((m->stop & 0x0fff) != 0x0fff))
return -EINVAL;
pci_readw(s->bus, s->devfn, CB_BRIDGE_CONTROL, &bcr);
config_readw(s, CB_BRIDGE_CONTROL, &bcr);
bcr &= ~CB_BCR_PREFETCH(map);
bcr |= (m->flags & MAP_PREFETCH) ? CB_BCR_PREFETCH(map) : 0;
pci_writew(s->bus, s->devfn, CB_BRIDGE_CONTROL, bcr);
config_writew(s, CB_BRIDGE_CONTROL, bcr);
}
if (m->flags & MAP_ACTIVE) {
pci_writel(s->bus, s->devfn, CB_MEM_BASE(map), m->start);
pci_writel(s->bus, s->devfn, CB_MEM_LIMIT(map), m->stop);
config_writel(s, CB_MEM_BASE(map), m->start);
config_writel(s, CB_MEM_LIMIT(map), m->stop);
} else {
pci_writel(s->bus, s->devfn, CB_IO_BASE(map), 0);
pci_writel(s->bus, s->devfn, CB_IO_LIMIT(map), 0);
config_writel(s, CB_MEM_BASE(map), 0);
config_writel(s, CB_MEM_LIMIT(map), 0);
}
return 0;
}
......@@ -2525,7 +2420,7 @@ static int proc_read_info(char *buf, char **start, off_t pos,
#ifdef CONFIG_PCI
if (s->flags & (IS_PCI|IS_CARDBUS))
p += sprintf(p, "bus: %02x\ndevfn: %02x.%1x\n",
s->bus, PCI_SLOT(s->devfn), PCI_FUNC(s->devfn));
s->pdev->bus->number, PCI_SLOT(s->pdev->devfn), PCI_FUNC(s->pdev->devfn));
if (s->flags & IS_CARDBUS)
p += sprintf(p, "cardbus: %02x\n", s->cap.cardbus);
#endif
......@@ -2565,16 +2460,15 @@ static int proc_read_pci(char *buf, char **start, off_t pos,
int count, int *eof, void *data)
{
socket_info_t *s = data;
u_char bus = s->bus, devfn = s->devfn;
char *p = buf;
u_int a, b, c, d;
int i;
for (i = 0; i < 0xc0; i += 0x10) {
pci_readl(bus, devfn, i, &a);
pci_readl(bus, devfn, i+4, &b);
pci_readl(bus, devfn, i+8, &c);
pci_readl(bus, devfn, i+12, &d);
config_readl(s, i, &a);
config_readl(s, i+4, &b);
config_readl(s, i+8, &c);
config_readl(s, i+12, &d);
p += sprintf(p, "%08x %08x %08x %08x\n", a, b, c, d);
}
return (p - buf);
......@@ -2801,7 +2695,7 @@ static int __init init_i82365(void)
sockets = 0;
#ifdef CONFIG_PCI
if (do_pci_probe && pcibios_present()) {
if (do_pci_probe) {
pci_probe(PCI_CLASS_BRIDGE_CARDBUS, add_cb_bridge);
pci_probe(PCI_CLASS_BRIDGE_PCMCIA, add_pci_bridge);
}
......@@ -2892,4 +2786,3 @@ module_init(init_i82365);
module_exit(exit_i82365);
/*====================================================================*/
......@@ -437,6 +437,8 @@ struct Scsi_Device_Template
struct module * module; /* Used for loadable modules */
unsigned char scsi_type;
unsigned char major;
unsigned char min_major; /* Minimum major in range. */
unsigned char max_major; /* Maximum major in range. */
unsigned char nr_dev; /* Number currently attached */
unsigned char dev_noticed; /* Number of devices detected. */
unsigned char dev_max; /* Current size of arrays */
......@@ -447,7 +449,8 @@ struct Scsi_Device_Template
void (*finish)(void); /* Perform initialization after attachment */
int (*attach)(Scsi_Device *); /* Attach devices to arrays */
void (*detach)(Scsi_Device *);
int (*init_command)(Scsi_Cmnd *); /* Used by new queueing code. */
int (*init_command)(Scsi_Cmnd *); /* Used by new queueing code.
Selects command for blkdevs */
};
extern struct Scsi_Device_Template sd_template;
......
......@@ -1470,9 +1470,6 @@ void scsi_do_cmd(Scsi_Cmnd * SCpnt, const void *cmnd,
*/
host->host_busy++;
device->device_busy++;
/*
* Our own function scsi_done (which marks the host as not busy, disables
* the timeout counter, etc) will be called by us or by the
......@@ -1575,6 +1572,9 @@ void scsi_done(Scsi_Cmnd * SCpnt)
* Since serial_number is now 0, the error handler cound detect this
* situation and avoid to call the the low level driver abort routine.
* (DB)
*
* FIXME(eric) - I believe that this test is now redundant, due to
* the test of the return status of del_timer().
*/
if (SCpnt->state == SCSI_STATE_TIMEOUT) {
SCSI_LOG_MLCOMPLETE(1, printk("Ignoring completion of %p due to timeout status", SCpnt));
......
......@@ -1778,6 +1778,17 @@ STATIC int scsi_unjam_host(struct Scsi_Host *host)
for (SCpnt = SCdone; SCpnt != NULL; SCpnt = SCdone) {
SCdone = SCpnt->bh_next;
SCpnt->bh_next = NULL;
/*
* Oh, this is a vile hack. scsi_done() expects a timer
* to be running on the command. If there isn't, it assumes
* that the command has actually timed out, and a timer
* handler is running. That may well be how we got into
* this fix, but right now things are stable. We add
* a timer back again so that we can report completion.
* scsi_done() will immediately remove said timer from
* the command, and then process it.
*/
scsi_add_timer(SCpnt, 100, scsi_eh_times_out);
scsi_done(SCpnt);
}
......@@ -1809,7 +1820,14 @@ void scsi_error_handler(void *data)
int rtn;
DECLARE_MUTEX_LOCKED(sem);
/*
* We only listen to signals if the HA was loaded as a module.
* If the HA was compiled into the kernel, then we don't listen
* to any signals.
*/
if( host->loaded_as_module ) {
siginitsetinv(&current->blocked, SHUTDOWN_SIGS);
}
lock_kernel();
......@@ -1844,10 +1862,14 @@ void scsi_error_handler(void *data)
* trying to unload a module.
*/
SCSI_LOG_ERROR_RECOVERY(1, printk("Error handler sleeping\n"));
if( host->loaded_as_module ) {
down_interruptible(&sem);
if (signal_pending(current))
break;
} else {
down(&sem);
}
SCSI_LOG_ERROR_RECOVERY(1, printk("Error handler waking up\n"));
......
......@@ -607,6 +607,22 @@ struct Scsi_Device_Template *scsi_get_request_dev(struct request *req)
if (spnt->blk && spnt->major == major) {
return spnt;
}
/*
* I am still not entirely satisfied with this solution,
* but it is good enough for now. Disks have a number of
* major numbers associated with them, the primary
* 8, which we test above, and a secondary range of 7
* different consecutive major numbers. If this ever
* becomes insufficient, then we could add another function
* to the structure, and generalize this completely.
*/
if( spnt->min_major != 0
&& spnt->max_major != 0
&& major >= spnt->min_major
&& major <= spnt->max_major )
{
return spnt;
}
}
return NULL;
}
......@@ -742,10 +758,15 @@ void scsi_request_fn(request_queue_t * q)
if (!SCpnt) {
break;
}
SHpnt->host_busy++;
SDpnt->device_busy++;
}
/*
* Now bump the usage count for both the host and the
* device.
*/
SHpnt->host_busy++;
SDpnt->device_busy++;
/*
* FIXME(eric)
* I am not sure where the best place to do this is. We need
......
......@@ -290,6 +290,30 @@ __inline static int __scsi_merge_fn(request_queue_t * q,
count = bh->b_size >> 9;
sector = bh->b_rsector;
#if CONFIG_HIGHMEM
/*
* This is a temporary hack for the time being.
* In some cases, the ll_rw_blk layer is creating
* bounce buffers for us - this implies that we don't
* need to down here, but queue management becomes quite
* difficult otherwise. When the ll_rw_blk layer gets
* cleaned up to handle bounce buffers better, then
* this hack can be cleaned up.
*/
if( sector == -1 )
{
struct buffer_head * bh_new;
bh_new = (struct buffer_head *) bh->b_dev_id;
if( bh_new != NULL )
{
sector = bh_new->b_rsector;
}
if( sector == -1 )
{
panic("Unable to merge ambiguous block request");
}
}
#endif
/*
* We come in here in one of two cases. The first is that we
......@@ -765,7 +789,8 @@ __inline static int __init_io(Scsi_Cmnd * SCpnt,
if( scsi_dma_free_sectors > 30 ) {
for (this_count = 0, bh = SCpnt->request.bh;
bh; bh = bh->b_reqnext) {
if( scsi_dma_free_sectors < 30 || this_count == sectors )
if( scsi_dma_free_sectors - this_count < 30
|| this_count == sectors )
{
break;
}
......@@ -831,24 +856,11 @@ static int _FUNCTION(Scsi_Cmnd * SCpnt) \
* We always force "_VALID" to 1. Eventually clean this up
* and get rid of the extra argument.
*/
#if 0
/* Old definitions */
INITIO(scsi_init_io_, 0, 0, 0)
INITIO(scsi_init_io_d, 0, 0, 1)
INITIO(scsi_init_io_c, 0, 1, 0)
INITIO(scsi_init_io_dc, 0, 1, 1)
/* Newer redundant definitions. */
INITIO(scsi_init_io_, 1, 0, 0)
INITIO(scsi_init_io_d, 1, 0, 1)
INITIO(scsi_init_io_c, 1, 1, 0)
INITIO(scsi_init_io_dc, 1, 1, 1)
#endif
INITIO(scsi_init_io_v, 1, 0, 0)
INITIO(scsi_init_io_vd, 1, 0, 1)
INITIO(scsi_init_io_vc, 1, 1, 0)
INITIO(scsi_init_io_vdc, 1, 1, 1)
/*
* Function: initialize_merge_fn()
*
......@@ -881,21 +893,12 @@ void initialize_merge_fn(Scsi_Device * SDpnt)
* If this host has an unlimited tablesize, then don't bother with a
* merge manager. The whole point of the operation is to make sure
* that requests don't grow too large, and this host isn't picky.
*/
if (SHpnt->sg_tablesize == SG_ALL) {
if (!CLUSTERABLE_DEVICE(SHpnt, SDpnt) && SHpnt->unchecked_isa_dma == 0) {
SDpnt->scsi_init_io_fn = scsi_init_io_v;
} else if (!CLUSTERABLE_DEVICE(SHpnt, SDpnt) && SHpnt->unchecked_isa_dma != 0) {
SDpnt->scsi_init_io_fn = scsi_init_io_vd;
} else if (CLUSTERABLE_DEVICE(SHpnt, SDpnt) && SHpnt->unchecked_isa_dma == 0) {
SDpnt->scsi_init_io_fn = scsi_init_io_vc;
} else if (CLUSTERABLE_DEVICE(SHpnt, SDpnt) && SHpnt->unchecked_isa_dma != 0) {
SDpnt->scsi_init_io_fn = scsi_init_io_vdc;
}
return;
}
/*
* Now pick out the correct function.
*
* Note that ll_rw_blk.c is effectively maintaining a segment
* count which is only valid if clustering is used, and it obviously
* doesn't handle the DMA case. In the end, it
* is simply easier to do it ourselves with our own functions
* rather than rely upon the default behavior of ll_rw_blk.
*/
if (!CLUSTERABLE_DEVICE(SHpnt, SDpnt) && SHpnt->unchecked_isa_dma == 0) {
q->merge_fn = scsi_merge_fn_;
......
......@@ -202,6 +202,11 @@ struct Scsi_Device_Template sd_template = {
tag:"sd",
scsi_type:TYPE_DISK,
major:SCSI_DISK0_MAJOR,
/*
* Secondary range of majors that this driver handles.
*/
min_major:SCSI_DISK1_MAJOR,
max_major:SCSI_DISK7_MAJOR,
blk:1,
detect:sd_detect,
init:sd_init,
......@@ -229,7 +234,7 @@ static int sd_init_command(Scsi_Cmnd * SCpnt)
Scsi_Disk *dpnt;
char nbuff[6];
devm = MINOR(SCpnt->request.rq_dev);
devm = SD_PARTITION(SCpnt->request.rq_dev);
dev = DEVICE_NR(SCpnt->request.rq_dev);
block = SCpnt->request.sector;
......@@ -561,7 +566,7 @@ static void rw_intr(Scsi_Cmnd * SCpnt)
default:
break;
}
error_sector -= sd[MINOR(SCpnt->request.rq_dev)].start_sect;
error_sector -= sd[SD_PARTITION(SCpnt->request.rq_dev)].start_sect;
error_sector &= ~(block_sectors - 1);
good_sectors = error_sector - SCpnt->request.sector;
if (good_sectors < 0 || good_sectors >= this_count)
......
......@@ -101,10 +101,17 @@ static int sg_detect(Scsi_Device *);
static void sg_detach(Scsi_Device *);
struct Scsi_Device_Template sg_template = {NULL, NULL, "sg", NULL, 0xff,
SCSI_GENERIC_MAJOR, 0, 0, 0, 0,
sg_detect, sg_init,
sg_finish, sg_attach, sg_detach};
struct Scsi_Device_Template sg_template =
{
tag:"sg",
scsi_type:0xff,
major:SCSI_GENERIC_MAJOR,
detect:sg_detect,
init:sg_init,
finish:sg_finish,
attach:sg_attach,
detach:sg_detach
};
typedef struct sg_scatter_hold /* holding area for scsi scatter gather info */
......
......@@ -147,10 +147,16 @@ static int st_detect(Scsi_Device *);
static void st_detach(Scsi_Device *);
struct Scsi_Device_Template st_template =
{NULL, "tape", "st", NULL, TYPE_TAPE,
SCSI_TAPE_MAJOR, 0, 0, 0, 0,
st_detect, st_init,
NULL, st_attach, st_detach};
{
name:"tape",
tag:"st",
scsi_type:TYPE_TAPE,
major:SCSI_TAPE_MAJOR,
detect:st_detect,
init:st_init,
attach:st_attach,
detach:st_detach
};
static int st_compression(Scsi_Tape *, int);
......
......@@ -360,6 +360,7 @@ struct pci_bus {
struct pci_dev *self; /* bridge device as seen by parent */
struct pci_dev *devices; /* devices behind this bridge */
struct pci_dev **last_dev_p; /* where should next device be linked to */
struct resource *resource[4]; /* address space routed to this bus */
void *sysdata; /* hook for sys-specific extension */
......@@ -449,6 +450,8 @@ int pcibios_find_device (unsigned short vendor, unsigned short dev_id,
void pci_init(void);
struct pci_bus *pci_scan_bus(int bus, struct pci_ops *ops, void *sysdata);
struct pci_bus *pci_alloc_primary_bus(int bus);
struct pci_dev *pci_scan_slot(struct pci_dev *temp);
int pci_proc_attach_device(struct pci_dev *dev);
int pci_proc_detach_device(struct pci_dev *dev);
void pci_name_device(struct pci_dev *dev);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment