From: "Bagalkote, Sreenivas" We are releasing megaraid 2.20.4.1 driver. This version fixes two issues - - Handle IOCTL command timeouts properly - Replace incorrectly introduced pci_dma_sync_{sg,single}_for_cpu with correct pci_dma_sync_{sg,single}_for_device. Signed-off-by: Andrew Morton --- 25-akpm/Documentation/scsi/ChangeLog.megaraid | 11 ++++ 25-akpm/drivers/scsi/megaraid/megaraid_ioctl.h | 6 +- 25-akpm/drivers/scsi/megaraid/megaraid_mbox.c | 8 +-- 25-akpm/drivers/scsi/megaraid/megaraid_mbox.h | 4 - 25-akpm/drivers/scsi/megaraid/megaraid_mm.c | 64 +++++++++++++++++++++++-- 25-akpm/drivers/scsi/megaraid/megaraid_mm.h | 4 - 6 files changed, 84 insertions(+), 13 deletions(-) diff -puN Documentation/scsi/ChangeLog.megaraid~megaraid-22041-driver Documentation/scsi/ChangeLog.megaraid --- 25/Documentation/scsi/ChangeLog.megaraid~megaraid-22041-driver Fri Nov 5 16:23:05 2004 +++ 25-akpm/Documentation/scsi/ChangeLog.megaraid Fri Nov 5 16:23:05 2004 @@ -1,3 +1,14 @@ +Release Date : Thu Nov 4 18:24:56 EST 2004 - Sreenivas Bagalkote + +Current Version : 2.20.4.1 (scsi module), 2.20.2.2 (cmm module) +Older Version : 2.20.4.0 (scsi module), 2.20.2.1 (cmm module) + +i. Handle IOCTL cmd timeouts more properly. + +ii. pci_dma_sync_{sg,single}_for_cpu was introduced into megaraid_mbox + incorrectly (instead of _for_device). Changed to appropriate + pci_dma_sync_{sg,single}_for_device. + Release Date : Wed Oct 06 11:15:29 EDT 2004 - Sreenivas Bagalkote Current Version : 2.20.4.0 (scsi module), 2.20.2.1 (cmm module) Older Version : 2.20.4.0 (scsi module), 2.20.2.0 (cmm module) diff -puN drivers/scsi/megaraid/megaraid_ioctl.h~megaraid-22041-driver drivers/scsi/megaraid/megaraid_ioctl.h --- 25/drivers/scsi/megaraid/megaraid_ioctl.h~megaraid-22041-driver Fri Nov 5 16:23:05 2004 +++ 25-akpm/drivers/scsi/megaraid/megaraid_ioctl.h Fri Nov 5 16:23:05 2004 @@ -145,6 +145,8 @@ typedef struct uioc { uint8_t pool_index; uint8_t free_buf; + uint8_t timedout; + } __attribute__ ((aligned(1024),packed)) uioc_t; @@ -247,6 +249,7 @@ typedef struct mm_dmapool { * @pdev : pci dev; used for allocating dma'ble memory * @issue_uioc : Driver supplied routine to issue uioc_t commands * : issue_uioc(drvr_data, kioc, ISSUE/ABORT, uioc_done) + * @quiescent : flag to indicate if ioctl can be issued to this adp * @list : attach with the global list of adapters * @kioc_list : block of mem for @max_kioc number of kiocs * @kioc_pool : pool of free kiocs @@ -264,7 +267,7 @@ typedef struct mraid_mmadp { uint32_t unique_id; uint32_t drvr_type; unsigned long drvr_data; - uint8_t timeout; + uint16_t timeout; uint8_t max_kioc; struct pci_dev *pdev; @@ -272,6 +275,7 @@ typedef struct mraid_mmadp { int(*issue_uioc)(unsigned long, uioc_t *, uint32_t); /* Maintained by common module */ + uint32_t quiescent; struct list_head list; uioc_t *kioc_list; diff -puN drivers/scsi/megaraid/megaraid_mbox.c~megaraid-22041-driver drivers/scsi/megaraid/megaraid_mbox.c --- 25/drivers/scsi/megaraid/megaraid_mbox.c~megaraid-22041-driver Fri Nov 5 16:23:05 2004 +++ 25-akpm/drivers/scsi/megaraid/megaraid_mbox.c Fri Nov 5 16:23:05 2004 @@ -10,7 +10,7 @@ * 2 of the License, or (at your option) any later version. * * FILE : megaraid_mbox.c - * Version : v2.20.4 (September 27 2004) + * Version : v2.20.4.1 (Nov 04 2004) * * Authors: * Atul Mukker @@ -1559,12 +1559,12 @@ mbox_post_cmd(adapter_t *adapter, scb_t if (scb->dma_direction == PCI_DMA_TODEVICE) { if (!scb->scp->use_sg) { // sg list not used - pci_dma_sync_single_for_cpu(adapter->pdev, ccb->buf_dma_h, + pci_dma_sync_single_for_device(adapter->pdev, ccb->buf_dma_h, scb->scp->request_bufflen, PCI_DMA_TODEVICE); } else { - pci_dma_sync_sg_for_cpu(adapter->pdev, scb->scp->request_buffer, + pci_dma_sync_sg_for_device(adapter->pdev, scb->scp->request_buffer, scb->scp->use_sg, PCI_DMA_TODEVICE); } } @@ -3596,7 +3596,7 @@ megaraid_cmm_register(adapter_t *adapter adp.drvr_data = (unsigned long)adapter; adp.pdev = adapter->pdev; adp.issue_uioc = megaraid_mbox_mm_handler; - adp.timeout = 30; + adp.timeout = 300; adp.max_kioc = MBOX_MAX_USER_CMDS; if ((rval = mraid_mm_register_adp(&adp)) != 0) { diff -puN drivers/scsi/megaraid/megaraid_mbox.h~megaraid-22041-driver drivers/scsi/megaraid/megaraid_mbox.h --- 25/drivers/scsi/megaraid/megaraid_mbox.h~megaraid-22041-driver Fri Nov 5 16:23:05 2004 +++ 25-akpm/drivers/scsi/megaraid/megaraid_mbox.h Fri Nov 5 16:23:05 2004 @@ -21,8 +21,8 @@ #include "megaraid_ioctl.h" -#define MEGARAID_VERSION "2.20.4.0" -#define MEGARAID_EXT_VERSION "(Release Date: Mon Sep 27 22:15:07 EDT 2004)" +#define MEGARAID_VERSION "2.20.4.1" +#define MEGARAID_EXT_VERSION "(Release Date: Thu Nov 4 17:44:59 EST 2004)" /* diff -puN drivers/scsi/megaraid/megaraid_mm.c~megaraid-22041-driver drivers/scsi/megaraid/megaraid_mm.c --- 25/drivers/scsi/megaraid/megaraid_mm.c~megaraid-22041-driver Fri Nov 5 16:23:05 2004 +++ 25-akpm/drivers/scsi/megaraid/megaraid_mm.c Fri Nov 5 16:23:05 2004 @@ -10,7 +10,7 @@ * 2 of the License, or (at your option) any later version. * * FILE : megaraid_mm.c - * Version : v2.20.2.1 (Oct 06 2004) + * Version : v2.20.2.2 (Nov 04 2004) * * Common management module */ @@ -156,6 +156,17 @@ mraid_mm_ioctl(struct inode *inode, stru } /* + * Check if adapter can accept ioctl. We may have marked it offline + * if any previous kioc had timedout on this controller. + */ + if (!adp->quiescent) { + con_log(CL_ANN, (KERN_WARNING + "megaraid cmm: controller cannot accept cmds due to " + "earlier errors\n" )); + return -EFAULT; + } + + /* * The following call will block till a kioc is available */ kioc = mraid_mm_alloc_kioc(adp); @@ -171,10 +182,15 @@ mraid_mm_ioctl(struct inode *inode, stru kioc->done = ioctl_done; /* - * Issue the IOCTL to the low level driver + * Issue the IOCTL to the low level driver. After the IOCTL completes + * release the kioc if and only if it was _not_ timedout. If it was + * timedout, that means that resources are still with low level driver. */ if ((rval = lld_ioctl(adp, kioc))) { - mraid_mm_dealloc_kioc(adp, kioc); + + if (!kioc->timedout) + mraid_mm_dealloc_kioc(adp, kioc); + return rval; } @@ -581,6 +597,7 @@ mraid_mm_alloc_kioc(mraid_mmadp_t *adp) kioc->user_data = NULL; kioc->user_data_len = 0; kioc->user_pthru = NULL; + kioc->timedout = 0; return kioc; } @@ -667,6 +684,14 @@ lld_ioctl(mraid_mmadp_t *adp, uioc_t *ki del_timer_sync(tp); } + /* + * If the command had timedout, we mark the controller offline + * before returning + */ + if (kioc->timedout) { + adp->quiescent = 0; + } + return kioc->status; } @@ -679,6 +704,10 @@ lld_ioctl(mraid_mmadp_t *adp, uioc_t *ki static void ioctl_done(uioc_t *kioc) { + uint32_t adapno; + int iterator; + mraid_mmadp_t* adapter; + /* * When the kioc returns from driver, make sure it still doesn't * have ENODATA in status. Otherwise, driver will hang on wait_event @@ -691,7 +720,32 @@ ioctl_done(uioc_t *kioc) kioc->status = -EINVAL; } - wake_up(&wait_q); + /* + * Check if this kioc was timedout before. If so, nobody is waiting + * on this kioc. We don't have to wake up anybody. Instead, we just + * have to free the kioc + */ + if (kioc->timedout) { + iterator = 0; + adapter = NULL; + adapno = kioc->adapno; + + con_log(CL_ANN, ( KERN_WARNING "megaraid cmm: completed " + "ioctl that was timedout before\n")); + + list_for_each_entry(adapter, &adapters_list_g, list) { + if (iterator++ == adapno) break; + } + + kioc->timedout = 0; + + if (adapter) { + mraid_mm_dealloc_kioc( adapter, kioc ); + } + } + else { + wake_up(&wait_q); + } } @@ -706,6 +760,7 @@ lld_timedout(unsigned long ptr) uioc_t *kioc = (uioc_t *)ptr; kioc->status = -ETIME; + kioc->timedout = 1; con_log(CL_ANN, (KERN_WARNING "megaraid cmm: ioctl timed out\n")); @@ -850,6 +905,7 @@ mraid_mm_register_adp(mraid_mmadp_t *lld adapter->issue_uioc = lld_adp->issue_uioc; adapter->timeout = lld_adp->timeout; adapter->max_kioc = lld_adp->max_kioc; + adapter->quiescent = 1; /* * Allocate single blocks of memory for all required kiocs, diff -puN drivers/scsi/megaraid/megaraid_mm.h~megaraid-22041-driver drivers/scsi/megaraid/megaraid_mm.h --- 25/drivers/scsi/megaraid/megaraid_mm.h~megaraid-22041-driver Fri Nov 5 16:23:05 2004 +++ 25-akpm/drivers/scsi/megaraid/megaraid_mm.h Fri Nov 5 16:23:05 2004 @@ -29,9 +29,9 @@ #include "megaraid_ioctl.h" -#define LSI_COMMON_MOD_VERSION "2.20.2.1" +#define LSI_COMMON_MOD_VERSION "2.20.2.2" #define LSI_COMMON_MOD_EXT_VERSION \ - "(Release Date: Wed Oct 06 11:15:29 EDT 2004)" + "(Release Date: Thu Nov 4 17:46:29 EST 2004)" #define LSI_DBGLVL dbglevel _