diff options
Diffstat (limited to 'drivers/scsi/mpt2sas/mpt2sas_ctl.c')
-rw-r--r-- | drivers/scsi/mpt2sas/mpt2sas_ctl.c | 61 |
1 files changed, 39 insertions, 22 deletions
diff --git a/drivers/scsi/mpt2sas/mpt2sas_ctl.c b/drivers/scsi/mpt2sas/mpt2sas_ctl.c index c2a51018910f..57d724633906 100644 --- a/drivers/scsi/mpt2sas/mpt2sas_ctl.c +++ b/drivers/scsi/mpt2sas/mpt2sas_ctl.c | |||
@@ -3,7 +3,7 @@ | |||
3 | * controllers | 3 | * controllers |
4 | * | 4 | * |
5 | * This code is based on drivers/scsi/mpt2sas/mpt2_ctl.c | 5 | * This code is based on drivers/scsi/mpt2sas/mpt2_ctl.c |
6 | * Copyright (C) 2007-2008 LSI Corporation | 6 | * Copyright (C) 2007-2009 LSI Corporation |
7 | * (mailto:DL-MPTFusionLinux@lsi.com) | 7 | * (mailto:DL-MPTFusionLinux@lsi.com) |
8 | * | 8 | * |
9 | * This program is free software; you can redistribute it and/or | 9 | * This program is free software; you can redistribute it and/or |
@@ -219,23 +219,25 @@ _ctl_display_some_debug(struct MPT2SAS_ADAPTER *ioc, u16 smid, | |||
219 | * mpt2sas_ctl_done - ctl module completion routine | 219 | * mpt2sas_ctl_done - ctl module completion routine |
220 | * @ioc: per adapter object | 220 | * @ioc: per adapter object |
221 | * @smid: system request message index | 221 | * @smid: system request message index |
222 | * @VF_ID: virtual function id | 222 | * @msix_index: MSIX table index supplied by the OS |
223 | * @reply: reply message frame(lower 32bit addr) | 223 | * @reply: reply message frame(lower 32bit addr) |
224 | * Context: none. | 224 | * Context: none. |
225 | * | 225 | * |
226 | * The callback handler when using ioc->ctl_cb_idx. | 226 | * The callback handler when using ioc->ctl_cb_idx. |
227 | * | 227 | * |
228 | * Return nothing. | 228 | * Return 1 meaning mf should be freed from _base_interrupt |
229 | * 0 means the mf is freed from this function. | ||
229 | */ | 230 | */ |
230 | void | 231 | u8 |
231 | mpt2sas_ctl_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) | 232 | mpt2sas_ctl_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, |
233 | u32 reply) | ||
232 | { | 234 | { |
233 | MPI2DefaultReply_t *mpi_reply; | 235 | MPI2DefaultReply_t *mpi_reply; |
234 | 236 | ||
235 | if (ioc->ctl_cmds.status == MPT2_CMD_NOT_USED) | 237 | if (ioc->ctl_cmds.status == MPT2_CMD_NOT_USED) |
236 | return; | 238 | return 1; |
237 | if (ioc->ctl_cmds.smid != smid) | 239 | if (ioc->ctl_cmds.smid != smid) |
238 | return; | 240 | return 1; |
239 | ioc->ctl_cmds.status |= MPT2_CMD_COMPLETE; | 241 | ioc->ctl_cmds.status |= MPT2_CMD_COMPLETE; |
240 | mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); | 242 | mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); |
241 | if (mpi_reply) { | 243 | if (mpi_reply) { |
@@ -247,6 +249,7 @@ mpt2sas_ctl_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) | |||
247 | #endif | 249 | #endif |
248 | ioc->ctl_cmds.status &= ~MPT2_CMD_PENDING; | 250 | ioc->ctl_cmds.status &= ~MPT2_CMD_PENDING; |
249 | complete(&ioc->ctl_cmds.done); | 251 | complete(&ioc->ctl_cmds.done); |
252 | return 1; | ||
250 | } | 253 | } |
251 | 254 | ||
252 | /** | 255 | /** |
@@ -328,22 +331,25 @@ mpt2sas_ctl_add_to_event_log(struct MPT2SAS_ADAPTER *ioc, | |||
328 | /** | 331 | /** |
329 | * mpt2sas_ctl_event_callback - firmware event handler (called at ISR time) | 332 | * mpt2sas_ctl_event_callback - firmware event handler (called at ISR time) |
330 | * @ioc: per adapter object | 333 | * @ioc: per adapter object |
331 | * @VF_ID: virtual function id | 334 | * @msix_index: MSIX table index supplied by the OS |
332 | * @reply: reply message frame(lower 32bit addr) | 335 | * @reply: reply message frame(lower 32bit addr) |
333 | * Context: interrupt. | 336 | * Context: interrupt. |
334 | * | 337 | * |
335 | * This function merely adds a new work task into ioc->firmware_event_thread. | 338 | * This function merely adds a new work task into ioc->firmware_event_thread. |
336 | * The tasks are worked from _firmware_event_work in user context. | 339 | * The tasks are worked from _firmware_event_work in user context. |
337 | * | 340 | * |
338 | * Return nothing. | 341 | * Return 1 meaning mf should be freed from _base_interrupt |
342 | * 0 means the mf is freed from this function. | ||
339 | */ | 343 | */ |
340 | void | 344 | u8 |
341 | mpt2sas_ctl_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply) | 345 | mpt2sas_ctl_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 msix_index, |
346 | u32 reply) | ||
342 | { | 347 | { |
343 | Mpi2EventNotificationReply_t *mpi_reply; | 348 | Mpi2EventNotificationReply_t *mpi_reply; |
344 | 349 | ||
345 | mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); | 350 | mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); |
346 | mpt2sas_ctl_add_to_event_log(ioc, mpi_reply); | 351 | mpt2sas_ctl_add_to_event_log(ioc, mpi_reply); |
352 | return 1; | ||
347 | } | 353 | } |
348 | 354 | ||
349 | /** | 355 | /** |
@@ -507,7 +513,7 @@ _ctl_set_task_mid(struct MPT2SAS_ADAPTER *ioc, struct mpt2_ioctl_command *karg, | |||
507 | 513 | ||
508 | handle = le16_to_cpu(tm_request->DevHandle); | 514 | handle = le16_to_cpu(tm_request->DevHandle); |
509 | spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); | 515 | spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); |
510 | for (i = ioc->request_depth; i && !found; i--) { | 516 | for (i = ioc->scsiio_depth; i && !found; i--) { |
511 | scmd = ioc->scsi_lookup[i - 1].scmd; | 517 | scmd = ioc->scsi_lookup[i - 1].scmd; |
512 | if (scmd == NULL || scmd->device == NULL || | 518 | if (scmd == NULL || scmd->device == NULL || |
513 | scmd->device->hostdata == NULL) | 519 | scmd->device->hostdata == NULL) |
@@ -614,7 +620,7 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, | |||
614 | printk(MPT2SAS_INFO_FMT "%s: ioc is operational\n", | 620 | printk(MPT2SAS_INFO_FMT "%s: ioc is operational\n", |
615 | ioc->name, __func__); | 621 | ioc->name, __func__); |
616 | 622 | ||
617 | smid = mpt2sas_base_get_smid(ioc, ioc->ctl_cb_idx); | 623 | smid = mpt2sas_base_get_smid_scsiio(ioc, ioc->ctl_cb_idx, NULL); |
618 | if (!smid) { | 624 | if (!smid) { |
619 | printk(MPT2SAS_ERR_FMT "%s: failed obtaining a smid\n", | 625 | printk(MPT2SAS_ERR_FMT "%s: failed obtaining a smid\n", |
620 | ioc->name, __func__); | 626 | ioc->name, __func__); |
@@ -737,7 +743,7 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, | |||
737 | (u32)mpt2sas_base_get_sense_buffer_dma(ioc, smid); | 743 | (u32)mpt2sas_base_get_sense_buffer_dma(ioc, smid); |
738 | priv_sense = mpt2sas_base_get_sense_buffer(ioc, smid); | 744 | priv_sense = mpt2sas_base_get_sense_buffer(ioc, smid); |
739 | memset(priv_sense, 0, SCSI_SENSE_BUFFERSIZE); | 745 | memset(priv_sense, 0, SCSI_SENSE_BUFFERSIZE); |
740 | mpt2sas_base_put_smid_scsi_io(ioc, smid, 0, | 746 | mpt2sas_base_put_smid_scsi_io(ioc, smid, |
741 | le16_to_cpu(mpi_request->FunctionDependent1)); | 747 | le16_to_cpu(mpi_request->FunctionDependent1)); |
742 | break; | 748 | break; |
743 | } | 749 | } |
@@ -759,8 +765,7 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, | |||
759 | mutex_lock(&ioc->tm_cmds.mutex); | 765 | mutex_lock(&ioc->tm_cmds.mutex); |
760 | mpt2sas_scsih_set_tm_flag(ioc, le16_to_cpu( | 766 | mpt2sas_scsih_set_tm_flag(ioc, le16_to_cpu( |
761 | tm_request->DevHandle)); | 767 | tm_request->DevHandle)); |
762 | mpt2sas_base_put_smid_hi_priority(ioc, smid, | 768 | mpt2sas_base_put_smid_hi_priority(ioc, smid); |
763 | mpi_request->VF_ID); | ||
764 | break; | 769 | break; |
765 | } | 770 | } |
766 | case MPI2_FUNCTION_SMP_PASSTHROUGH: | 771 | case MPI2_FUNCTION_SMP_PASSTHROUGH: |
@@ -781,7 +786,7 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, | |||
781 | ioc->ioc_link_reset_in_progress = 1; | 786 | ioc->ioc_link_reset_in_progress = 1; |
782 | ioc->ignore_loginfos = 1; | 787 | ioc->ignore_loginfos = 1; |
783 | } | 788 | } |
784 | mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); | 789 | mpt2sas_base_put_smid_default(ioc, smid); |
785 | break; | 790 | break; |
786 | } | 791 | } |
787 | case MPI2_FUNCTION_SAS_IO_UNIT_CONTROL: | 792 | case MPI2_FUNCTION_SAS_IO_UNIT_CONTROL: |
@@ -795,11 +800,11 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, | |||
795 | ioc->ioc_link_reset_in_progress = 1; | 800 | ioc->ioc_link_reset_in_progress = 1; |
796 | ioc->ignore_loginfos = 1; | 801 | ioc->ignore_loginfos = 1; |
797 | } | 802 | } |
798 | mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); | 803 | mpt2sas_base_put_smid_default(ioc, smid); |
799 | break; | 804 | break; |
800 | } | 805 | } |
801 | default: | 806 | default: |
802 | mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); | 807 | mpt2sas_base_put_smid_default(ioc, smid); |
803 | break; | 808 | break; |
804 | } | 809 | } |
805 | 810 | ||
@@ -807,6 +812,7 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, | |||
807 | timeout = MPT2_IOCTL_DEFAULT_TIMEOUT; | 812 | timeout = MPT2_IOCTL_DEFAULT_TIMEOUT; |
808 | else | 813 | else |
809 | timeout = karg.timeout; | 814 | timeout = karg.timeout; |
815 | init_completion(&ioc->ctl_cmds.done); | ||
810 | timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, | 816 | timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, |
811 | timeout*HZ); | 817 | timeout*HZ); |
812 | if (mpi_request->Function == MPI2_FUNCTION_SCSI_TASK_MGMT) { | 818 | if (mpi_request->Function == MPI2_FUNCTION_SCSI_TASK_MGMT) { |
@@ -1371,6 +1377,8 @@ _ctl_diag_register(void __user *arg, enum block_state state) | |||
1371 | mpi_request->Flags = cpu_to_le32(karg.diagnostic_flags); | 1377 | mpi_request->Flags = cpu_to_le32(karg.diagnostic_flags); |
1372 | mpi_request->BufferAddress = cpu_to_le64(request_data_dma); | 1378 | mpi_request->BufferAddress = cpu_to_le64(request_data_dma); |
1373 | mpi_request->BufferLength = cpu_to_le32(request_data_sz); | 1379 | mpi_request->BufferLength = cpu_to_le32(request_data_sz); |
1380 | mpi_request->VF_ID = 0; /* TODO */ | ||
1381 | mpi_request->VP_ID = 0; | ||
1374 | 1382 | ||
1375 | dctlprintk(ioc, printk(MPT2SAS_DEBUG_FMT "%s: diag_buffer(0x%p), " | 1383 | dctlprintk(ioc, printk(MPT2SAS_DEBUG_FMT "%s: diag_buffer(0x%p), " |
1376 | "dma(0x%llx), sz(%d)\n", ioc->name, __func__, request_data, | 1384 | "dma(0x%llx), sz(%d)\n", ioc->name, __func__, request_data, |
@@ -1380,7 +1388,8 @@ _ctl_diag_register(void __user *arg, enum block_state state) | |||
1380 | mpi_request->ProductSpecific[i] = | 1388 | mpi_request->ProductSpecific[i] = |
1381 | cpu_to_le32(ioc->product_specific[buffer_type][i]); | 1389 | cpu_to_le32(ioc->product_specific[buffer_type][i]); |
1382 | 1390 | ||
1383 | mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); | 1391 | mpt2sas_base_put_smid_default(ioc, smid); |
1392 | init_completion(&ioc->ctl_cmds.done); | ||
1384 | timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, | 1393 | timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, |
1385 | MPT2_IOCTL_DEFAULT_TIMEOUT*HZ); | 1394 | MPT2_IOCTL_DEFAULT_TIMEOUT*HZ); |
1386 | 1395 | ||
@@ -1643,8 +1652,11 @@ _ctl_send_release(struct MPT2SAS_ADAPTER *ioc, u8 buffer_type, u8 *issue_reset) | |||
1643 | 1652 | ||
1644 | mpi_request->Function = MPI2_FUNCTION_DIAG_RELEASE; | 1653 | mpi_request->Function = MPI2_FUNCTION_DIAG_RELEASE; |
1645 | mpi_request->BufferType = buffer_type; | 1654 | mpi_request->BufferType = buffer_type; |
1655 | mpi_request->VF_ID = 0; /* TODO */ | ||
1656 | mpi_request->VP_ID = 0; | ||
1646 | 1657 | ||
1647 | mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); | 1658 | mpt2sas_base_put_smid_default(ioc, smid); |
1659 | init_completion(&ioc->ctl_cmds.done); | ||
1648 | timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, | 1660 | timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, |
1649 | MPT2_IOCTL_DEFAULT_TIMEOUT*HZ); | 1661 | MPT2_IOCTL_DEFAULT_TIMEOUT*HZ); |
1650 | 1662 | ||
@@ -1902,8 +1914,11 @@ _ctl_diag_read_buffer(void __user *arg, enum block_state state) | |||
1902 | for (i = 0; i < MPT2_PRODUCT_SPECIFIC_DWORDS; i++) | 1914 | for (i = 0; i < MPT2_PRODUCT_SPECIFIC_DWORDS; i++) |
1903 | mpi_request->ProductSpecific[i] = | 1915 | mpi_request->ProductSpecific[i] = |
1904 | cpu_to_le32(ioc->product_specific[buffer_type][i]); | 1916 | cpu_to_le32(ioc->product_specific[buffer_type][i]); |
1917 | mpi_request->VF_ID = 0; /* TODO */ | ||
1918 | mpi_request->VP_ID = 0; | ||
1905 | 1919 | ||
1906 | mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); | 1920 | mpt2sas_base_put_smid_default(ioc, smid); |
1921 | init_completion(&ioc->ctl_cmds.done); | ||
1907 | timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, | 1922 | timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, |
1908 | MPT2_IOCTL_DEFAULT_TIMEOUT*HZ); | 1923 | MPT2_IOCTL_DEFAULT_TIMEOUT*HZ); |
1909 | 1924 | ||
@@ -2069,6 +2084,7 @@ static long | |||
2069 | _ctl_ioctl(struct file *file, unsigned int cmd, unsigned long arg) | 2084 | _ctl_ioctl(struct file *file, unsigned int cmd, unsigned long arg) |
2070 | { | 2085 | { |
2071 | long ret; | 2086 | long ret; |
2087 | |||
2072 | lock_kernel(); | 2088 | lock_kernel(); |
2073 | ret = _ctl_ioctl_main(file, cmd, (void __user *)arg); | 2089 | ret = _ctl_ioctl_main(file, cmd, (void __user *)arg); |
2074 | unlock_kernel(); | 2090 | unlock_kernel(); |
@@ -2143,6 +2159,7 @@ static long | |||
2143 | _ctl_ioctl_compat(struct file *file, unsigned cmd, unsigned long arg) | 2159 | _ctl_ioctl_compat(struct file *file, unsigned cmd, unsigned long arg) |
2144 | { | 2160 | { |
2145 | long ret; | 2161 | long ret; |
2162 | |||
2146 | lock_kernel(); | 2163 | lock_kernel(); |
2147 | if (cmd == MPT2COMMAND32) | 2164 | if (cmd == MPT2COMMAND32) |
2148 | ret = _ctl_compat_mpt_command(file, cmd, arg); | 2165 | ret = _ctl_compat_mpt_command(file, cmd, arg); |