From: Markus Lidel Date: Fri, 6 Jan 2006 08:19:32 +0000 (-0800) Subject: [PATCH] I2O: Bugfixes X-Git-Tag: v2.6.16-rc1~936^2~97 X-Git-Url: https://err.no/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=dcceafe25a5f47cf69e5b46b4da6f15186ec8386;p=linux-2.6 [PATCH] I2O: Bugfixes - Removed some kmalloc's with __GFP_ZERO and replace it with memset() because it didn't work properly. - Fixed returned message frame in i2o_cfg_passthru() which caused raidutils to display wrong error message in case a disk was missing. - Fixed size of printk() in i2o_scsi.c. - Fixed get_device() and put_device() in probing of the I2O controller. Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- diff --git a/drivers/message/i2o/driver.c b/drivers/message/i2o/driver.c index 25292b36e2..9c631c873d 100644 --- a/drivers/message/i2o/driver.c +++ b/drivers/message/i2o/driver.c @@ -217,14 +217,15 @@ int i2o_driver_dispatch(struct i2o_controller *c, u32 m) /* cut of header from message size (in 32-bit words) */ size = (le32_to_cpu(msg->u.head[0]) >> 16) - 5; - evt = kmalloc(size * 4 + sizeof(*evt), GFP_ATOMIC | __GFP_ZERO); + evt = kmalloc(size * 4 + sizeof(*evt), GFP_ATOMIC); if (!evt) return -ENOMEM; + memset(evt, 0, size * 4 + sizeof(*evt)); evt->size = size; evt->tcntxt = le32_to_cpu(msg->u.s.tcntxt); evt->event_indicator = le32_to_cpu(msg->body[0]); - memcpy(&evt->tcntxt, &msg->u.s.tcntxt, size * 4); + memcpy(&evt->data, &msg->body[1], size * 4); list_for_each_entry_safe(dev, tmp, &c->devices, list) if (dev->lct_data.tid == tid) { diff --git a/drivers/message/i2o/i2o_config.c b/drivers/message/i2o/i2o_config.c index 4fe73d628c..286fef3240 100644 --- a/drivers/message/i2o/i2o_config.c +++ b/drivers/message/i2o/i2o_config.c @@ -36,12 +36,12 @@ #include -#include "core.h" - #define SG_TABLESIZE 30 -static int i2o_cfg_ioctl(struct inode *inode, struct file *fp, unsigned int cmd, - unsigned long arg); +extern int i2o_parm_issue(struct i2o_device *, int, void *, int, void *, int); + +static int i2o_cfg_ioctl(struct inode *, struct file *, unsigned int, + unsigned long); static spinlock_t i2o_config_lock; @@ -593,9 +593,6 @@ static int i2o_cfg_passthru32(struct file *file, unsigned cmnd, sg_offset = (msg->u.head[0] >> 4) & 0x0f; - msg->u.s.icntxt = cpu_to_le32(i2o_config_driver.context); - msg->u.s.tcntxt = cpu_to_le32(i2o_cntxt_list_add(c, reply)); - memset(sg_list, 0, sizeof(sg_list[0]) * SG_TABLESIZE); if (sg_offset) { struct sg_simple_element *sg; @@ -629,7 +626,7 @@ static int i2o_cfg_passthru32(struct file *file, unsigned cmnd, goto cleanup; } sg_size = sg[i].flag_count & 0xffffff; - p = &(sg_list[sg_index++]); + p = &(sg_list[sg_index]); /* Allocate memory for the transfer */ if (i2o_dma_alloc (&c->pdev->dev, p, sg_size, @@ -640,6 +637,7 @@ static int i2o_cfg_passthru32(struct file *file, unsigned cmnd, rcode = -ENOMEM; goto sg_list_cleanup; } + sg_index++; /* Copy in the user's SG buffer if necessary */ if (sg[i]. flag_count & 0x04000000 /*I2O_SGL_FLAGS_DIR */ ) { @@ -661,8 +659,10 @@ static int i2o_cfg_passthru32(struct file *file, unsigned cmnd, } rcode = i2o_msg_post_wait(c, msg, 60); - if (rcode) + if (rcode) { + reply[4] = ((u32) rcode) << 24; goto sg_list_cleanup; + } if (sg_offset) { u32 msg[I2O_OUTBOUND_MSG_FRAME_SIZE]; @@ -712,6 +712,7 @@ static int i2o_cfg_passthru32(struct file *file, unsigned cmnd, } } + sg_list_cleanup: /* Copy back the reply to user space */ if (reply_size) { // we wrote our own values for context - now restore the user supplied ones @@ -729,7 +730,6 @@ static int i2o_cfg_passthru32(struct file *file, unsigned cmnd, } } - sg_list_cleanup: for (i = 0; i < sg_index; i++) i2o_dma_free(&c->pdev->dev, &sg_list[i]); @@ -827,9 +827,6 @@ static int i2o_cfg_passthru(unsigned long arg) sg_offset = (msg->u.head[0] >> 4) & 0x0f; - msg->u.s.icntxt = cpu_to_le32(i2o_config_driver.context); - msg->u.s.tcntxt = cpu_to_le32(i2o_cntxt_list_add(c, reply)); - memset(sg_list, 0, sizeof(sg_list[0]) * SG_TABLESIZE); if (sg_offset) { struct sg_simple_element *sg; @@ -892,8 +889,10 @@ static int i2o_cfg_passthru(unsigned long arg) } rcode = i2o_msg_post_wait(c, msg, 60); - if (rcode) + if (rcode) { + reply[4] = ((u32) rcode) << 24; goto sg_list_cleanup; + } if (sg_offset) { u32 msg[128]; @@ -943,6 +942,7 @@ static int i2o_cfg_passthru(unsigned long arg) } } + sg_list_cleanup: /* Copy back the reply to user space */ if (reply_size) { // we wrote our own values for context - now restore the user supplied ones @@ -959,7 +959,6 @@ static int i2o_cfg_passthru(unsigned long arg) } } - sg_list_cleanup: for (i = 0; i < sg_index; i++) kfree(sg_list[i]); diff --git a/drivers/message/i2o/i2o_scsi.c b/drivers/message/i2o/i2o_scsi.c index 24061dfd46..76b9516b19 100644 --- a/drivers/message/i2o/i2o_scsi.c +++ b/drivers/message/i2o/i2o_scsi.c @@ -309,9 +309,9 @@ static int i2o_scsi_probe(struct device *dev) sysfs_create_link(&i2o_dev->device.kobj, &scsi_dev->sdev_gendev.kobj, "scsi"); - osm_info("device added (TID: %03x) channel: %d, id: %d, lun: %d\n", + osm_info("device added (TID: %03x) channel: %d, id: %d, lun: %ld\n", i2o_dev->lct_data.tid, channel, le32_to_cpu(id), - (unsigned int)le64_to_cpu(lun)); + (long unsigned int)le64_to_cpu(lun)); return 0; }; diff --git a/drivers/message/i2o/pci.c b/drivers/message/i2o/pci.c index 329d482eee..c5b656cdea 100644 --- a/drivers/message/i2o/pci.c +++ b/drivers/message/i2o/pci.c @@ -339,7 +339,7 @@ static int __devinit i2o_pci_probe(struct pci_dev *pdev, pci_name(pdev)); c->pdev = pdev; - c->device.parent = get_device(&pdev->dev); + c->device.parent = &pdev->dev; /* Cards that fall apart if you hit them with large I/O loads... */ if (pdev->vendor == PCI_VENDOR_ID_NCR && pdev->device == 0x0630) { @@ -410,8 +410,6 @@ static int __devinit i2o_pci_probe(struct pci_dev *pdev, if ((rc = i2o_iop_add(c))) goto uninstall; - get_device(&c->device); - if (i960) pci_write_config_word(i960, 0x42, 0x03ff); @@ -424,7 +422,6 @@ static int __devinit i2o_pci_probe(struct pci_dev *pdev, i2o_pci_free(c); free_controller: - put_device(c->device.parent); i2o_iop_free(c); disable: @@ -454,7 +451,6 @@ static void __devexit i2o_pci_remove(struct pci_dev *pdev) printk(KERN_INFO "%s: Controller removed.\n", c->name); - put_device(c->device.parent); put_device(&c->device); }; diff --git a/include/linux/i2o.h b/include/linux/i2o.h index 4c18b7711b..9ba8067966 100644 --- a/include/linux/i2o.h +++ b/include/linux/i2o.h @@ -384,7 +384,7 @@ /* defines for max_sectors and max_phys_segments */ #define I2O_MAX_SECTORS 1024 -#define I2O_MAX_SECTORS_LIMITED 256 +#define I2O_MAX_SECTORS_LIMITED 128 #define I2O_MAX_PHYS_SEGMENTS MAX_PHYS_SEGMENTS /*