Whamcloud - gitweb
b=16395
[fs/lustre-release.git] / lustre / kernel_patches / patches / mpt-fusion-downgrade-to-3_02_73-rhel4.patch
1 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/csmi/csmisas.c linux-2.6.9-55.0.12/drivers/message/fusion/csmi/csmisas.c
2 --- linux-2.6.9-67.0.1/drivers/message/fusion/csmi/csmisas.c    2007-12-21 11:40:54.000000000 +0100
3 +++ linux-2.6.9-55.0.12/drivers/message/fusion/csmi/csmisas.c   1970-01-01 01:00:00.000000000 +0100
4 @@ -1,5894 +0,0 @@
5 -#define MPT_CSMI_DESCRIPTION "LSI Logic Corporation: Fusion MPT Driver "MPT_LINUX_VERSION_COMMON
6 -#define csmisas_is_this_sas_cntr(ioc) (ioc->bus_type == SAS) ? 1 : 0
7 -
8 -static int csmisas_do_raid(MPT_ADAPTER *ioc, u8 action, u8 PhysDiskNum, u8 VolumeBus,
9 -    u8 VolumeId, pMpiRaidActionReply_t reply);
10 -static u8  map_sas_status_to_csmi(u8 mpi_sas_status);
11 -
12 -/**
13 - * reverse_byte_order64
14 - *
15 - * @data64
16 - *
17 - **/
18 -static u64
19 -reverse_byte_order64(u64 data64)
20 -{
21 -       int i;
22 -       u64 rc;
23 -       u8  *inWord = (u8*)&data64, *outWord = (u8*)&rc;
24 -
25 -       for (i = 0 ; i < 8 ; i++)
26 -               outWord[i] = inWord[7-i];
27 -
28 -       return rc;
29 -}
30 -
31 -/**
32 - * csmisas_is_sata
33 - *
34 - * @phys_disk
35 - *
36 - **/
37 -static int
38 -csmisas_is_sata(RaidPhysDiskPage0_t *phys_disk)
39 -{
40 -       if ((phys_disk->ExtDiskIdentifier[0] == 'A') &&
41 -           (phys_disk->ExtDiskIdentifier[1] == 'T') &&
42 -           (phys_disk->ExtDiskIdentifier[2] == 'A'))
43 -               return 1;
44 -       else
45 -               return 0;
46 -}
47 -
48 -/**
49 - * csmisas_is_end_device
50 - *
51 - * @attached
52 - *
53 - **/
54 -static inline int
55 -csmisas_is_end_device(struct mptsas_devinfo * attached)
56 -{
57 -       if ((attached->sas_address) &&
58 -           (attached->device_info &
59 -           MPI_SAS_DEVICE_INFO_END_DEVICE) &&
60 -           ((attached->device_info &
61 -           MPI_SAS_DEVICE_INFO_SSP_TARGET) |
62 -           (attached->device_info &
63 -           MPI_SAS_DEVICE_INFO_STP_TARGET) |
64 -           (attached->device_info &
65 -           MPI_SAS_DEVICE_INFO_SATA_DEVICE)))
66 -               return 1;
67 -       else
68 -               return 0;
69 -}
70 -
71 -/**
72 - * csmisas_is_phys_disk
73 - *
74 - * returns (1) success (0) fail - not a phys disk
75 - **/
76 -int
77 -csmisas_is_phys_disk(MPT_ADAPTER *ioc, int channel, int id)
78 -{
79 -       struct inactive_raid_component_info *component_info;
80 -       int i;
81 -       int rc = 0;
82 -
83 -       if (!ioc->raid_data.pIocPg3)
84 -               goto out;
85 -       for (i = 0; i < ioc->raid_data.pIocPg3->NumPhysDisks; i++) {
86 -               if ((id == ioc->raid_data.pIocPg3->PhysDisk[i].PhysDiskID) &&
87 -                   (channel == ioc->raid_data.pIocPg3->PhysDisk[i].PhysDiskBus)) {
88 -                       rc = 1;
89 -                       goto out;
90 -               }
91 -       }
92 -
93 -       /*
94 -        * Check inactive list for matching phys disks
95 -        */
96 -       if (list_empty(&ioc->raid_data.inactive_list))
97 -               goto out;
98 -
99 -       down(&ioc->raid_data.inactive_list_mutex);
100 -       list_for_each_entry(component_info, &ioc->raid_data.inactive_list,
101 -           list) {
102 -               if ((component_info->d.PhysDiskID == id) &&
103 -                   (component_info->d.PhysDiskBus == channel))
104 -                       rc = 1;
105 -       }
106 -       up(&ioc->raid_data.inactive_list_mutex);
107 -
108 - out:
109 -       return rc;
110 -}
111 -
112 -/**
113 - * csmisas_raid_id_to_num
114 - *
115 - * Obtains the phys disk num for given H:C:T nexus
116 - *
117 - * input (channel/id)
118 - * output (phys disk number - used by SCSI_IO_PASSTHRU to access hidden component)
119 - *
120 - * returns - signed return means failure
121 - **/
122 -s8
123 -csmisas_raid_id_to_num(MPT_ADAPTER *ioc, u8 channel, u8 id)
124 -{
125 -       struct inactive_raid_component_info *component_info;
126 -       int i;
127 -       s8 rc = -ENXIO;
128 -
129 -       if (!ioc->raid_data.pIocPg3)
130 -               goto out;
131 -       for (i = 0; i < ioc->raid_data.pIocPg3->NumPhysDisks; i++) {
132 -               if ((id == ioc->raid_data.pIocPg3->PhysDisk[i].PhysDiskID) &&
133 -                   (channel == ioc->raid_data.pIocPg3->PhysDisk[i].PhysDiskBus)) {
134 -                       rc = ioc->raid_data.pIocPg3->PhysDisk[i].PhysDiskNum;
135 -                       goto out;
136 -               }
137 -       }
138 -
139 -       /*
140 -        * Check inactive list for matching phys disks
141 -        */
142 -       if (list_empty(&ioc->raid_data.inactive_list))
143 -               goto out;
144 -
145 -       down(&ioc->raid_data.inactive_list_mutex);
146 -       list_for_each_entry(component_info, &ioc->raid_data.inactive_list,
147 -           list) {
148 -               if ((component_info->d.PhysDiskID == id) &&
149 -                   (component_info->d.PhysDiskBus == channel))
150 -                       rc = component_info->d.PhysDiskNum;
151 -       }
152 -       up(&ioc->raid_data.inactive_list_mutex);
153 -
154 - out:
155 -       return rc;
156 -}
157 -
158 -/**
159 - * csmisas_get_device_component_by_os
160 - *
161 - * Obtain device component object by operating system mapping
162 - *
163 - * @ioc
164 - * @channel
165 - * @id
166 - *
167 - **/
168 -static struct sas_device_info *
169 -csmisas_get_device_component_by_os(MPT_ADAPTER *ioc, u8 channel, u8 id)
170 -{
171 -       struct sas_device_info *sas_info, *p;
172 -
173 -       sas_info = NULL;
174 -
175 -       down(&ioc->sas_device_info_mutex);
176 -       list_for_each_entry(p, &ioc->sas_device_info_list, list) {
177 -               if (p->os.channel == channel && p->os.id == id) {
178 -                       sas_info = p;
179 -                       goto out;
180 -               }
181 -       }
182 -
183 - out:
184 -       up(&ioc->sas_device_info_mutex);
185 -       return sas_info;
186 -}
187 -
188 -/**
189 - * csmisas_get_device_component
190 - *
191 - * Obtain device component object by firmware system mapping
192 - *
193 - * @ioc
194 - * @channel
195 - * @id
196 - *
197 - **/
198 -static struct sas_device_info *
199 -csmisas_get_device_component_by_fw(MPT_ADAPTER *ioc, u8 channel, u8 id)
200 -{
201 -       struct sas_device_info *sas_info, *p;
202 -
203 -       sas_info = NULL;
204 -
205 -       down(&ioc->sas_device_info_mutex);
206 -       list_for_each_entry(p, &ioc->sas_device_info_list, list) {
207 -               if (p->fw.channel == channel && p->fw.id == id) {
208 -                       sas_info = p;
209 -                       goto out;
210 -               }
211 -       }
212 -
213 - out:
214 -       up(&ioc->sas_device_info_mutex);
215 -       return sas_info;
216 -}
217 -
218 -
219 -/**
220 - * csmisas_get_device_component_by_sas_addr
221 - *
222 - * Obtain device component object by sas address
223 - *
224 - * @ioc
225 - * @channel
226 - * @id
227 - *
228 - **/
229 -static struct sas_device_info *
230 -csmisas_get_device_component_by_sas_addr(MPT_ADAPTER *ioc, u64 sas_address)
231 -{
232 -       struct sas_device_info *sas_info, *p;
233 -
234 -       sas_info = NULL;
235 -
236 -       down(&ioc->sas_device_info_mutex);
237 -       list_for_each_entry(p, &ioc->sas_device_info_list, list) {
238 -               dcsmisasprintk((KERN_ERR
239 -                   ":%s()"
240 -                   " looking for SASAddress=%llX entry SASAddress=%llX\n",
241 -                   __FUNCTION__, sas_address, p->sas_address));
242 -               if (p->sas_address == sas_address) {
243 -                       sas_info = p;
244 -                       dcsmisasprintk((KERN_ERR
245 -                               ":%s()"
246 -                               " found SASAddress=%llX\n",
247 -                               __FUNCTION__, sas_address));
248 -                       goto out;
249 -               }
250 -       }
251 -
252 - out:
253 -       up(&ioc->sas_device_info_mutex);
254 -       return sas_info;
255 -}
256 -
257 -/**
258 - * csmisas_send_command_wait
259 - *
260 - * Send mf to firmware
261 - *
262 - * @ioc
263 - * @mf
264 - * @timeout - timeout
265 - *
266 - *     Return: 0 for success
267 - *     non-zero, failure
268 - **/
269 -static int
270 -csmisas_send_command_wait(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, int timeout)
271 -{
272 -       int rc;
273 -       int mf_timeout;
274 -
275 -       mf_timeout = max_t(int, MPT_IOCTL_DEFAULT_TIMEOUT, timeout);
276 -       INITIALIZE_IOCTL_STATUS(ioc->ioctl->status)
277 -       ioc->ioctl->wait_done = 0;
278 -       rc = 0;
279 -
280 -#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0))
281 -       ioc->ioctl->timer.expires = jiffies + (MPT_JIFFY * mf_timeout);
282 -       ioc->ioctl->status |= MPT_IOCTL_STATUS_TIMER_ACTIVE;
283 -       ADD_TIMER(&ioc->ioctl->timer);
284 -#endif
285 -
286 -       mpt_put_msg_frame(mptctl_id, ioc, mf);
287 -
288 -#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0))
289 -       WAIT_EVENT(mptctl_wait, ioc->ioctl->wait_done);
290 -#else
291 -       if ((wait_event_timeout(mptctl_wait,
292 -           ioc->ioctl->wait_done == 1, HZ * mf_timeout) <=0) &&
293 -           ioc->ioctl->wait_done != 1 ) {
294 -               mpt_free_msg_frame(ioc, mf);
295 -               mptctl_timeout_expired(ioc->ioctl);
296 -               rc = -1;
297 -       }
298 -#endif
299 -
300 -       if (rc != 0)
301 -               dfailprintk((KERN_ERR "%s@%d::%s() - "
302 -                   "%s IOCTL timeout (%d)\n",
303 -                   __FILE__, __LINE__, __FUNCTION__,
304 -                   ioc->name, mf_timeout));
305 -
306 -       return rc;
307 -}
308 -
309 -/**
310 - * csmisas_send_handshake_wait
311 - *
312 - * Handshake a mf to firmware
313 - *
314 - * @ioc
315 - * @mf
316 - * @mf_size
317 - * @timeout - timeout
318 - *
319 - *     Return: 0 for success
320 - *     non-zero, failure
321 - **/
322 -static int
323 -csmisas_send_handshake_wait(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, int timeout)
324 -{
325 -       int rc;
326 -       int mf_timeout;
327 -
328 -       mf_timeout = max_t(int, MPT_IOCTL_DEFAULT_TIMEOUT, timeout);
329 -       INITIALIZE_IOCTL_STATUS(ioc->ioctl->status)
330 -       ioc->ioctl->wait_done = 0;
331 -       rc = 0;
332 -
333 -#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0))
334 -       ioc->ioctl->timer.expires = jiffies + (MPT_JIFFY * mf_timeout);
335 -       ioc->ioctl->status |= MPT_IOCTL_STATUS_TIMER_ACTIVE;
336 -       ADD_TIMER(&ioc->ioctl->timer);
337 -#endif
338 -
339 -       rc = mpt_send_handshake_request(mptctl_id, ioc,
340 -           sizeof(SCSITaskMgmt_t), (u32*)mf,timeout, CAN_SLEEP);
341 -       if (rc != 0)
342 -               return rc;
343 -
344 -#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0))
345 -       WAIT_EVENT(mptctl_wait, ioc->ioctl->wait_done);
346 -#else
347 -       if ((wait_event_timeout(mptctl_wait,
348 -           ioc->ioctl->wait_done == 1, HZ * mf_timeout) <=0) &&
349 -           ioc->ioctl->wait_done != 1 ) {
350 -               mpt_free_msg_frame(ioc, mf);
351 -               mptctl_timeout_expired(ioc->ioctl);
352 -               rc = -1;
353 -       }
354 -#endif
355 -
356 -       if (rc != 0)
357 -               dfailprintk((KERN_ERR "%s@%d::%s() - "
358 -                   "%s IOCTL timeout (%d)\n", __FILE__, __LINE__,
359 -                   __FUNCTION__, ioc->name, mf_timeout));
360 -
361 -       return rc;
362 -}
363 -
364 -/**
365 - *     csmisas_get_manufacture_pg0 - Manufacturing Page 0.
366 - *     @ioc: Pointer to MPT_ADAPTER structure
367 - *     @mfgPage0: read only info set at manufacturing time
368 - *
369 - *     Return: 0 for success
370 - *     -ENOMEM if no memory available
371 - *             -EPERM if not allowed due to ISR context
372 - *             -EAGAIN if no msg frames currently available
373 - *             -EFAULT for non-successful reply or no reply (timeout)
374 - **/
375 -static int
376 -csmisas_get_manufacture_pg0(MPT_ADAPTER *ioc, ManufacturingPage0_t *mfgPage0)
377 -{
378 -
379 -       ConfigPageHeader_t       hdr;
380 -       CONFIGPARMS              cfg;
381 -       ManufacturingPage0_t     *buffer = NULL;
382 -       dma_addr_t               dma_handle;
383 -       int                      data_sz;
384 -       int                      rc;
385 -
386 -       /*
387 -        * Get Manufacturing Page 0 header
388 -        */
389 -       data_sz = 0;
390 -       hdr.PageVersion = MPI_MANUFACTURING0_PAGEVERSION;
391 -       hdr.PageLength = 0;
392 -       hdr.PageNumber = 0;
393 -       hdr.PageType = MPI_CONFIG_PAGETYPE_MANUFACTURING;
394 -       cfg.cfghdr.hdr = &hdr;
395 -       cfg.physAddr = -1;
396 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
397 -       cfg.dir = 0;
398 -       cfg.pageAddr = 0;
399 -       cfg.timeout = 0;
400 -
401 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
402 -               goto get_manufacture_pg0_out;
403 -
404 -       if (hdr.PageLength == 0) {
405 -               rc = -EFAULT;
406 -               goto get_manufacture_pg0_out;
407 -       }
408 -
409 -       data_sz = hdr.PageLength * 4;
410 -       buffer = (ManufacturingPage0_t *) pci_alloc_consistent(ioc->pcidev,
411 -               data_sz, &dma_handle);
412 -       if (!buffer) {
413 -               rc = -ENOMEM;
414 -               goto get_manufacture_pg0_out;
415 -       }
416 -
417 -       memset((u8 *)buffer, 0, data_sz);
418 -       cfg.physAddr = dma_handle;
419 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
420 -
421 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
422 -               goto get_manufacture_pg0_out;
423 -
424 -       strncpy(mfgPage0->ChipName, buffer->ChipName, 16);
425 -       strncpy(mfgPage0->ChipRevision, buffer->ChipRevision, 8);
426 -       strncpy(mfgPage0->BoardName, buffer->BoardName, 16);
427 -       strncpy(mfgPage0->BoardAssembly, buffer->BoardAssembly, 16);
428 -       strncpy(mfgPage0->BoardTracerNumber, buffer->BoardTracerNumber, 16);
429 -
430 -       dcsmisasprintk(("ChipName=%s\n",buffer->ChipName));
431 -       dcsmisasprintk(("ChipRevision=%s\n",buffer->ChipRevision));
432 -       dcsmisasprintk(("BoardName=%s\n",buffer->BoardName));
433 -       dcsmisasprintk(("BoardAssembly=%s\n",buffer->BoardAssembly));
434 -       dcsmisasprintk(("BoardTracerNumber=%s\n",buffer->BoardTracerNumber));
435 -
436 - get_manufacture_pg0_out:
437 -
438 -       if (buffer)
439 -               pci_free_consistent(ioc->pcidev, data_sz,
440 -                   (u8 *) buffer, dma_handle);
441 -
442 -
443 -       return rc;
444 -}
445 -
446 -/**
447 - *     csmisas_get_number_hotspares - returns num hot spares in this ioc
448 - *     @ioc: Pointer to MPT_ADAPTER structure
449 - *
450 - *     Return: number of hotspares
451 - *
452 - **/
453 -static int
454 -csmisas_get_number_hotspares(MPT_ADAPTER *ioc)
455 -{
456 -       ConfigPageHeader_t       hdr;
457 -       CONFIGPARMS              cfg;
458 -       IOCPage5_t               *buffer = NULL;
459 -       dma_addr_t               dma_handle;
460 -       int                      data_sz;
461 -       int                      rc;
462 -
463 -       memset(&hdr, 0, sizeof(ConfigPageHeader_t));
464 -       memset(&cfg, 0, sizeof(CONFIGPARMS));
465 -
466 -       rc = 0;
467 -       data_sz = 0;
468 -       hdr.PageNumber = 5;
469 -       hdr.PageType = MPI_CONFIG_PAGETYPE_IOC;
470 -       cfg.cfghdr.hdr = &hdr;
471 -       cfg.physAddr = -1;
472 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
473 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
474 -
475 -       if (mpt_config(ioc, &cfg) != 0)
476 -               goto get_ioc_pg5;
477 -
478 -       if (hdr.PageLength == 0)
479 -               goto get_ioc_pg5;
480 -
481 -       data_sz = hdr.PageLength * 4;
482 -       buffer = (IOCPage5_t *) pci_alloc_consistent(ioc->pcidev,
483 -               data_sz, &dma_handle);
484 -       if (!buffer)
485 -               goto get_ioc_pg5;
486 -
487 -       memset((u8 *)buffer, 0, data_sz);
488 -       cfg.physAddr = dma_handle;
489 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
490 -
491 -       if (mpt_config(ioc, &cfg) != 0)
492 -               goto get_ioc_pg5;
493 -
494 -       rc = buffer->NumHotSpares;
495 -
496 - get_ioc_pg5:
497 -
498 -       if (buffer)
499 -               pci_free_consistent(ioc->pcidev, data_sz,
500 -                   (u8 *) buffer, dma_handle);
501 -
502 -       return rc;
503 -}
504 -
505 -
506 -/**
507 - *     csmisas_get_ioc_pg5 - ioc Page 5 hot spares
508 - *     @ioc: Pointer to MPT_ADAPTER structure
509 - *     @pIocPage5: ioc page 5
510 - *     @data_size: expected data size(units=bytes)
511 - *
512 - *     Return: 0 for success
513 - *     -ENOMEM if no memory available
514 - *             -EPERM if not allowed due to ISR context
515 - *             -EAGAIN if no msg frames currently available
516 - *             -EFAULT for non-successful reply or no reply (timeout)
517 - **/
518 -static int
519 -csmisas_get_ioc_pg5(MPT_ADAPTER *ioc, IOCPage5_t *iocPage5, int data_size)
520 -{
521 -       ConfigPageHeader_t       hdr;
522 -       CONFIGPARMS              cfg;
523 -       IOCPage5_t               *buffer = NULL;
524 -       dma_addr_t               dma_handle;
525 -       int                      data_sz;
526 -       int                      rc;
527 -
528 -       memset(&hdr, 0, sizeof(ConfigPageHeader_t));
529 -       memset(&cfg, 0, sizeof(CONFIGPARMS));
530 -
531 -       rc = 0;
532 -       data_sz = 0;
533 -       hdr.PageNumber = 5;
534 -       hdr.PageType = MPI_CONFIG_PAGETYPE_IOC;
535 -       cfg.cfghdr.hdr = &hdr;
536 -       cfg.physAddr = -1;
537 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
538 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
539 -
540 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
541 -               goto get_ioc_pg5;
542 -
543 -       if (hdr.PageLength == 0) {
544 -               rc = -EFAULT;
545 -               goto get_ioc_pg5;
546 -       }
547 -
548 -       data_sz = hdr.PageLength * 4;
549 -       buffer = (IOCPage5_t *) pci_alloc_consistent(ioc->pcidev,
550 -               data_sz, &dma_handle);
551 -       if (!buffer) {
552 -               rc = -ENOMEM;
553 -               goto get_ioc_pg5;
554 -       }
555 -
556 -       memset((u8 *)buffer, 0, data_sz);
557 -       cfg.physAddr = dma_handle;
558 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
559 -
560 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
561 -               goto get_ioc_pg5;
562 -
563 -       memcpy(iocPage5, buffer, data_size);
564 -
565 - get_ioc_pg5:
566 -
567 -       if (buffer)
568 -               pci_free_consistent(ioc->pcidev, data_sz,
569 -                   (u8 *) buffer, dma_handle);
570 -
571 -       return rc;
572 -}
573 -
574 -/**
575 - *     csmisas_sas_device_pg0 - sas device page 0
576 - *     @ioc: Pointer to MPT_ADAPTER structure
577 - *     @mptsas_devinfo: structure found in mptsas.h
578 - *     @form, @form_specific - defines the Page Address field in the config page
579 - *             (pls refer to chapter 5.1 in the mpi spec)
580 - *
581 - *     Return: 0 for success
582 - *     -ENOMEM if no memory available
583 - *             -EPERM if not allowed due to ISR context
584 - *             -EAGAIN if no msg frames currently available
585 - *             -EFAULT for non-successful reply or no reply (timeout)
586 - **/
587 -static int
588 -csmisas_sas_device_pg0(MPT_ADAPTER *ioc, struct mptsas_devinfo *device_info,
589 -               u32 form, u32 form_specific)
590 -{
591 -       ConfigExtendedPageHeader_t hdr;
592 -       CONFIGPARMS cfg;
593 -       SasDevicePage0_t *buffer;
594 -       dma_addr_t dma_handle;
595 -       u64 sas_address;
596 -       int rc;
597 -
598 -       rc = 0;
599 -       hdr.PageVersion = MPI_SASDEVICE0_PAGEVERSION;
600 -       hdr.ExtPageLength = 0;
601 -       hdr.PageNumber = 0;
602 -       hdr.Reserved1 = 0;
603 -       hdr.Reserved2 = 0;
604 -       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
605 -       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_DEVICE;
606 -
607 -       cfg.cfghdr.ehdr = &hdr;
608 -       cfg.pageAddr = form + form_specific;
609 -       cfg.physAddr = -1;
610 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
611 -       cfg.dir = 0;    /* read */
612 -       cfg.timeout = 10;
613 -
614 -       memset(device_info, 0, sizeof(struct mptsas_devinfo));
615 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
616 -               goto out;
617 -
618 -       if (!hdr.ExtPageLength) {
619 -               rc = -ENXIO;
620 -               goto out;
621 -       }
622 -
623 -       buffer = pci_alloc_consistent(ioc->pcidev,
624 -           hdr.ExtPageLength * 4, &dma_handle);
625 -       if (!buffer) {
626 -               rc = -ENOMEM;
627 -               goto out;
628 -       }
629 -
630 -       cfg.physAddr = dma_handle;
631 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
632 -
633 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
634 -               goto out_free_consistent;
635 -
636 -       device_info->handle = le16_to_cpu(buffer->DevHandle);
637 -       device_info->handle_parent = le16_to_cpu(buffer->ParentDevHandle);
638 -       device_info->handle_enclosure =
639 -           le16_to_cpu(buffer->EnclosureHandle);
640 -       device_info->slot = le16_to_cpu(buffer->Slot);
641 -       device_info->phy_id = buffer->PhyNum;
642 -       device_info->port_id = buffer->PhysicalPort;
643 -       device_info->id = buffer->TargetID;
644 -       device_info->channel = buffer->Bus;
645 -       memcpy(&sas_address, &buffer->SASAddress, sizeof(u64));
646 -       device_info->sas_address = le64_to_cpu(sas_address);
647 -       device_info->device_info =
648 -           le32_to_cpu(buffer->DeviceInfo);
649 -
650 - out_free_consistent:
651 -       pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
652 -                           buffer, dma_handle);
653 - out:
654 -       return rc;
655 -}
656 -
657 -/**
658 - * Routine for the CSMI Sas Get Driver Info command.
659 - *
660 - * Outputs:    None.
661 - * Return:     0 if successful
662 - *             -EFAULT if data unavailable
663 - *             -ENODEV if no such device/adapter
664 - **/
665 -static int
666 -csmisas_get_driver_info(unsigned long arg)
667 -{
668 -
669 -       CSMI_SAS_DRIVER_INFO_BUFFER __user *uarg = (void __user *) arg;
670 -       CSMI_SAS_DRIVER_INFO_BUFFER     karg;
671 -       MPT_ADAPTER     *ioc = NULL;
672 -       int             iocnum;
673 -
674 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
675 -
676 -       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_DRIVER_INFO_BUFFER))) {
677 -               printk(KERN_ERR "%s@%d::%s - "
678 -             "Unable to read in csmi_sas_get_driver_info_buffer struct @ %p\n",
679 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
680 -               return -EFAULT;
681 -       }
682 -
683 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
684 -           &ioc)) < 0) || (ioc == NULL)) {
685 -               dcsmisasprintk((KERN_ERR
686 -                   "%s::%s() @%d - ioc%d not found!\n",
687 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
688 -               return -ENODEV;
689 -       }
690 -
691 -       if (!csmisas_is_this_sas_cntr(ioc)) {
692 -               dcsmisasprintk((KERN_ERR
693 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
694 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
695 -               return -ENODEV;
696 -       }
697 -
698 -       /* Fill in the data and return the structure to the calling
699 -        * program
700 -        */
701 -       memcpy( karg.Information.szName, MPT_MISCDEV_BASENAME,
702 -           sizeof(MPT_MISCDEV_BASENAME));
703 -       memcpy( karg.Information.szDescription, MPT_CSMI_DESCRIPTION,
704 -           sizeof(MPT_CSMI_DESCRIPTION));
705 -
706 -       karg.Information.usMajorRevision = MPT_LINUX_MAJOR_VERSION;
707 -       karg.Information.usMinorRevision = MPT_LINUX_MINOR_VERSION;
708 -       karg.Information.usBuildRevision = MPT_LINUX_BUILD_VERSION;
709 -       karg.Information.usReleaseRevision = MPT_LINUX_RELEASE_VERSION;
710 -
711 -       karg.Information.usCSMIMajorRevision = CSMI_MAJOR_REVISION;
712 -       karg.Information.usCSMIMinorRevision = CSMI_MINOR_REVISION;
713 -
714 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
715 -
716 -       /* Copy the data from kernel memory to user memory
717 -        */
718 -       if (copy_to_user((char *)arg, &karg,
719 -               sizeof(CSMI_SAS_DRIVER_INFO_BUFFER))) {
720 -               printk(KERN_ERR "%s@%d::%s - "
721 -                  "Unable to write out csmi_sas_get_driver_info_buffer @ %p\n",
722 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
723 -               return -EFAULT;
724 -       }
725 -
726 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
727 -       return 0;
728 -}
729 -
730 -/**
731 - * Prototype Routine for the CSMI_SAS_GET_CNTLR_CONFIG command.
732 - *
733 - * Outputs:    None.
734 - * Return:     0 if successful
735 - *             -EFAULT if data unavailable
736 - *             -ENODEV if no such device/adapter
737 - **/
738 -static int
739 -csmisas_get_cntlr_config(unsigned long arg)
740 -{
741 -
742 -       CSMI_SAS_CNTLR_CONFIG_BUFFER __user *uarg = (void __user *) arg;
743 -       CSMI_SAS_CNTLR_CONFIG_BUFFER    karg;
744 -       MPT_ADAPTER     *ioc = NULL;
745 -       int             iocnum;
746 -       int             ii,msize,psize;
747 -       unsigned int    reg;
748 -       u32             l;
749 -       ManufacturingPage0_t mfgPage0;
750 -
751 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
752 -
753 -       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_CNTLR_CONFIG_BUFFER))) {
754 -               printk(KERN_ERR "%s@%d::%s - "
755 -            "Unable to read in csmi_sas_get_cntlr_config_buffer struct @ %p\n",
756 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
757 -               return -EFAULT;
758 -       }
759 -
760 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
761 -           &ioc)) < 0) || (ioc == NULL)) {
762 -               dcsmisasprintk((KERN_ERR
763 -             "%s::%s() @%d - ioc%d not found!\n",
764 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
765 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
766 -               return -ENODEV;
767 -       }
768 -
769 -       if (!csmisas_is_this_sas_cntr(ioc)) {
770 -               dcsmisasprintk((KERN_ERR
771 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
772 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
773 -               return -ENODEV;
774 -       }
775 -
776 -       /* Clear the struct before filling in data. */
777 -       memset( &karg.Configuration, 0, sizeof(CSMI_SAS_CNTLR_CONFIG));
778 -
779 -       /* Fill in the data and return the structure to the calling
780 -        * program
781 -        */
782 -
783 -       /* Get Base IO and Mem Mapped Addresses. */
784 -msize = psize = 0;
785 -for(ii=0; ii < DEVICE_COUNT_RESOURCE; ii++) {
786 -               reg = PCI_BASE_ADDRESS_0 + (ii << 2);
787 -               pci_read_config_dword(ioc->pcidev, reg, &l);
788 -
789 -               if ((l & PCI_BASE_ADDRESS_SPACE) ==
790 -                       PCI_BASE_ADDRESS_SPACE_MEMORY) {
791 -                   if(msize)
792 -                         continue;
793 -                   msize=1;
794 -               karg.Configuration.BaseMemoryAddress.uLowPart =
795 -                           l & PCI_BASE_ADDRESS_MEM_MASK;
796 -
797 -               if ((l & (PCI_BASE_ADDRESS_SPACE |
798 -                   PCI_BASE_ADDRESS_MEM_TYPE_MASK))
799 -                   == (PCI_BASE_ADDRESS_SPACE_MEMORY |
800 -                   PCI_BASE_ADDRESS_MEM_TYPE_64)) {
801 -                     pci_read_config_dword(ioc->pcidev, reg+4, &l);
802 -                     karg.Configuration.BaseMemoryAddress.uHighPart = l;
803 -                  }
804 -               }
805 -
806 -
807 -                  else {
808 -                       if(psize)
809 -                       continue;
810 -                       psize=1;
811 -                       karg.Configuration.uBaseIoAddress =
812 -                           l & PCI_BASE_ADDRESS_IO_MASK;
813 -               }
814 -
815 -       }
816 -
817 -       karg.Configuration.uBoardID = (ioc->pcidev->subsystem_device << 16) |
818 -           (ioc->pcidev->subsystem_vendor);
819 -
820 -       karg.Configuration.usSlotNumber =
821 -           (ioc->pci_slot_number = 0xff) ?
822 -           SLOT_NUMBER_UNKNOWN : ioc->pci_slot_number;
823 -       karg.Configuration.bControllerClass = CSMI_SAS_CNTLR_CLASS_HBA;
824 -       karg.Configuration.bIoBusType = CSMI_SAS_BUS_TYPE_PCI;
825 -       karg.Configuration.BusAddress.PciAddress.bBusNumber =
826 -           ioc->pcidev->bus->number;
827 -       karg.Configuration.BusAddress.PciAddress.bDeviceNumber =
828 -           PCI_SLOT(ioc->pcidev->devfn);
829 -       karg.Configuration.BusAddress.PciAddress.bFunctionNumber =
830 -           PCI_FUNC(ioc->pcidev->devfn);
831 -       karg.Configuration.BusAddress.PciAddress.bReserved = 0;
832 -       if (!csmisas_get_manufacture_pg0(ioc, &mfgPage0))
833 -               memcpy( &karg.Configuration.szSerialNumber,
834 -                   mfgPage0.BoardTracerNumber, 16 );
835 -       karg.Configuration.usMajorRevision = ioc->facts.FWVersion.Struct.Major;
836 -       karg.Configuration.usMinorRevision = ioc->facts.FWVersion.Struct.Minor;
837 -       karg.Configuration.usBuildRevision = ioc->facts.FWVersion.Struct.Unit;
838 -       karg.Configuration.usReleaseRevision = ioc->facts.FWVersion.Struct.Dev;
839 -       karg.Configuration.usBIOSMajorRevision =
840 -           (ioc->biosVersion & 0xFF000000) >> 24;
841 -       karg.Configuration.usBIOSMinorRevision =
842 -           (ioc->biosVersion & 0x00FF0000) >> 16;
843 -       karg.Configuration.usBIOSBuildRevision =
844 -           (ioc->biosVersion & 0x0000FF00) >> 8;
845 -       karg.Configuration.usBIOSReleaseRevision =
846 -           (ioc->biosVersion & 0x000000FF);
847 -       karg.Configuration.uControllerFlags = CSMI_SAS_CNTLR_SAS_HBA |
848 -           CSMI_SAS_CNTLR_FWD_SUPPORT | CSMI_SAS_CNTLR_FWD_ONLINE |
849 -           CSMI_SAS_CNTLR_FWD_SRESET ;
850 -
851 -       /*
852 -        * Enabling CSMI_SAS_CNTLR_SAS_RAID bit when IR fw detected
853 -        */
854 -       if (ioc->ir_firmware)
855 -               karg.Configuration.uControllerFlags |= CSMI_SAS_CNTLR_SAS_RAID;
856 -
857 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
858 -
859 -       /* All Rrom entries will be zero. Skip them. */
860 -       /* bReserved will also be zeros. */
861 -       /* Copy the data from kernel memory to user memory
862 -        */
863 -       if (copy_to_user((char *)arg, &karg,
864 -               sizeof(CSMI_SAS_DRIVER_INFO_BUFFER))) {
865 -               printk(KERN_ERR "%s@%d::%s - "
866 -               "Unable to write out csmi_sas_get_driver_info_buffer @ %p\n",
867 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
868 -               return -EFAULT;
869 -       }
870 -
871 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
872 -       return 0;
873 -}
874 -
875 -/**
876 - * Prototype Routine for the CSMI Sas Get Controller Status command.
877 - *
878 - * Outputs:    None.
879 - * Return:     0 if successful
880 - *             -EFAULT if data unavailable
881 - *             -ENODEV if no such device/adapter
882 - **/
883 -static int
884 -csmisas_get_cntlr_status(unsigned long arg)
885 -{
886 -
887 -       CSMI_SAS_CNTLR_STATUS_BUFFER  __user *uarg = (void __user *) arg;
888 -       MPT_ADAPTER             *ioc = NULL;
889 -       CSMI_SAS_CNTLR_STATUS_BUFFER    karg;
890 -       int                     iocnum;
891 -       int                     rc;
892 -
893 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
894 -
895 -       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_CNTLR_STATUS_BUFFER))) {
896 -               printk(KERN_ERR "%s@%d::%s - "
897 -            "Unable to read in csmi_sas_get_cntlr_status_buffer struct @ %p\n",
898 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
899 -               return -EFAULT;
900 -       }
901 -
902 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
903 -           &ioc)) < 0) || (ioc == NULL)) {
904 -               dcsmisasprintk((KERN_ERR
905 -                   "%s::%s() @%d - ioc%d not found!\n",
906 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
907 -               return -ENODEV;
908 -       }
909 -
910 -       if (!csmisas_is_this_sas_cntr(ioc)) {
911 -               dcsmisasprintk((KERN_ERR
912 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
913 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
914 -               return -ENODEV;
915 -       }
916 -
917 -       /* Fill in the data and return the structure to the calling
918 -        * program
919 -        */
920 -
921 -       rc = mpt_GetIocState(ioc, 1);
922 -       switch (rc) {
923 -       case MPI_IOC_STATE_OPERATIONAL:
924 -               karg.Status.uStatus =  CSMI_SAS_CNTLR_STATUS_GOOD;
925 -               karg.Status.uOfflineReason = 0;
926 -               break;
927 -
928 -       case MPI_IOC_STATE_FAULT:
929 -               karg.Status.uStatus = CSMI_SAS_CNTLR_STATUS_FAILED;
930 -               karg.Status.uOfflineReason = 0;
931 -               break;
932 -
933 -       case MPI_IOC_STATE_RESET:
934 -       case MPI_IOC_STATE_READY:
935 -       default:
936 -               karg.Status.uStatus =  CSMI_SAS_CNTLR_STATUS_OFFLINE;
937 -               karg.Status.uOfflineReason =
938 -                   CSMI_SAS_OFFLINE_REASON_INITIALIZING;
939 -               break;
940 -       }
941 -
942 -       memset(&karg.Status.bReserved, 0, 28);
943 -
944 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
945 -
946 -       /* Copy the data from kernel memory to user memory
947 -        */
948 -       if (copy_to_user((char *)arg, &karg,
949 -               sizeof(CSMI_SAS_CNTLR_STATUS_BUFFER))) {
950 -               printk(KERN_ERR "%s@%d::%s - "
951 -                   "Unable to write out csmi_sas_get_cntlr_status @ %p\n",
952 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
953 -               return -EFAULT;
954 -       }
955 -
956 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
957 -       return 0;
958 -}
959 -
960 -/**
961 - * Prototype Routine for the CSMI Sas Get Phy Info command.
962 - *
963 - * Outputs:    None.
964 - * Return:     0 if successful
965 - *             -EFAULT if data unavailable
966 - *             -ENODEV if no such device/adapter
967 - **/
968 -static int
969 -csmisas_get_phy_info(unsigned long arg)
970 -{
971 -       CSMI_SAS_PHY_INFO_BUFFER __user *uarg = (void __user *) arg;
972 -       CSMI_SAS_PHY_INFO_BUFFER  karg;
973 -       MPT_ADAPTER             *ioc = NULL;
974 -       ConfigExtendedPageHeader_t  hdr;
975 -       CONFIGPARMS             cfg;
976 -       SasIOUnitPage0_t        *sasIoUnitPg0;
977 -       dma_addr_t              sasIoUnitPg0_dma;
978 -       int                     sasIoUnitPg0_data_sz;
979 -       SasPhyPage0_t           *sasPhyPg0;
980 -       dma_addr_t              sasPhyPg0_dma;
981 -       int                     sasPhyPg0_data_sz;
982 -       u16                     protocol;
983 -       int                     iocnum;
984 -       int                     rc;
985 -       int                     ii;
986 -       u64                     sas_address;
987 -       struct mptsas_devinfo   device_info;
988 -
989 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
990 -       sasIoUnitPg0=NULL;
991 -       sasPhyPg0=NULL;
992 -       sasIoUnitPg0_data_sz=0;
993 -       sasPhyPg0_data_sz=0;
994 -
995 -       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_PHY_INFO_BUFFER))) {
996 -               printk(KERN_ERR "%s@%d::%s - "
997 -               "Unable to read in csmisas_get_phy_info_buffer struct @ %p\n",
998 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
999 -               return -EFAULT;
1000 -       }
1001 -
1002 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
1003 -           &ioc)) < 0) || (ioc == NULL)) {
1004 -               dcsmisasprintk((KERN_ERR
1005 -                   "%s::%s() @%d - ioc%d not found!\n",
1006 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
1007 -               return -ENODEV;
1008 -       }
1009 -
1010 -       if (!csmisas_is_this_sas_cntr(ioc)) {
1011 -               dcsmisasprintk((KERN_ERR
1012 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
1013 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
1014 -               return -ENODEV;
1015 -       }
1016 -
1017 -       /* Fill in the data and return the structure to the calling
1018 -        * program
1019 -        */
1020 -       memset(&karg.Information, 0, sizeof(CSMI_SAS_PHY_INFO));
1021 -
1022 -       /* Issue a config request to get the number of phys
1023 -        */
1024 -       hdr.PageVersion = MPI_SASIOUNITPAGE0_PAGEVERSION;
1025 -       hdr.ExtPageLength = 0;
1026 -       hdr.PageNumber = 0;
1027 -       hdr.Reserved1 = 0;
1028 -       hdr.Reserved2 = 0;
1029 -       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
1030 -       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_IO_UNIT;
1031 -
1032 -       cfg.cfghdr.ehdr = &hdr;
1033 -       cfg.physAddr = -1;
1034 -       cfg.pageAddr = 0;
1035 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
1036 -       cfg.dir = 0;    /* read */
1037 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
1038 -
1039 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
1040 -               /* Don't check if this failed.  Already in a
1041 -                * failure case.
1042 -                */
1043 -               dcsmisasprintk((
1044 -                   ": FAILED: MPI_SASIOUNITPAGE0_PAGEVERSION: HEADER\n"));
1045 -               dcsmisasprintk((": rc=%x\n",rc));
1046 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1047 -               goto sas_get_phy_info_exit;
1048 -       }
1049 -
1050 -       if (hdr.ExtPageLength == 0) {
1051 -               /* Don't check if this failed.  Already in a
1052 -                * failure case.
1053 -                */
1054 -               dcsmisasprintk((": hdr.ExtPageLength == 0\n"));
1055 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1056 -               goto sas_get_phy_info_exit;
1057 -       }
1058 -
1059 -       sasIoUnitPg0_data_sz = hdr.ExtPageLength * 4;
1060 -       rc = -ENOMEM;
1061 -
1062 -       sasIoUnitPg0 = (SasIOUnitPage0_t *) pci_alloc_consistent(ioc->pcidev,
1063 -           sasIoUnitPg0_data_sz, &sasIoUnitPg0_dma);
1064 -
1065 -       if (!sasIoUnitPg0) {
1066 -               dcsmisasprintk((": pci_alloc_consistent: FAILED\n"));
1067 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1068 -               goto sas_get_phy_info_exit;
1069 -       }
1070 -
1071 -       memset((u8 *)sasIoUnitPg0, 0, sasIoUnitPg0_data_sz);
1072 -       cfg.physAddr = sasIoUnitPg0_dma;
1073 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
1074 -
1075 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
1076 -
1077 -               /* Don't check if this failed.  Already in a
1078 -                * failure case.
1079 -                */
1080 -               dcsmisasprintk((
1081 -                   ": FAILED: MPI_SASIOUNITPAGE0_PAGEVERSION: PAGE\n"));
1082 -               dcsmisasprintk((": rc=%x\n",rc));
1083 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1084 -               goto sas_get_phy_info_exit;
1085 -       }
1086 -
1087 -       /* Number of Phys. */
1088 -       karg.Information.bNumberOfPhys = sasIoUnitPg0->NumPhys;
1089 -
1090 -       /* Fill in information for each phy. */
1091 -       for (ii = 0; ii < karg.Information.bNumberOfPhys; ii++) {
1092 -
1093 -/* EDM : dump IO Unit Page 0 data*/
1094 -               dcsmisasprintk(("---- IO UNIT PAGE 0 ------------\n"));
1095 -               dcsmisasprintk(("Handle=0x%X\n",
1096 -                   le16_to_cpu(sasIoUnitPg0->PhyData[ii].AttachedDeviceHandle)));
1097 -               dcsmisasprintk(("Controller Handle=0x%X\n",
1098 -                   le16_to_cpu(sasIoUnitPg0->PhyData[ii].ControllerDevHandle)));
1099 -               dcsmisasprintk(("Port=0x%X\n",
1100 -                   sasIoUnitPg0->PhyData[ii].Port));
1101 -               dcsmisasprintk(("Port Flags=0x%X\n",
1102 -                   sasIoUnitPg0->PhyData[ii].PortFlags));
1103 -               dcsmisasprintk(("PHY Flags=0x%X\n",
1104 -                   sasIoUnitPg0->PhyData[ii].PhyFlags));
1105 -               dcsmisasprintk(("Negotiated Link Rate=0x%X\n",
1106 -                   sasIoUnitPg0->PhyData[ii].NegotiatedLinkRate));
1107 -               dcsmisasprintk(("Controller PHY Device Info=0x%X\n",
1108 -                   le32_to_cpu(sasIoUnitPg0->PhyData[ii].ControllerPhyDeviceInfo)));
1109 -               dcsmisasprintk(("DiscoveryStatus=0x%X\n",
1110 -                   le32_to_cpu(sasIoUnitPg0->PhyData[ii].DiscoveryStatus)));
1111 -               dcsmisasprintk(("\n"));
1112 -/* EDM : debug data */
1113 -
1114 -               /* PHY stuff. */
1115 -               karg.Information.Phy[ii].bPortIdentifier =
1116 -                   sasIoUnitPg0->PhyData[ii].Port;
1117 -
1118 -               /* Get the negotiated link rate for the phy. */
1119 -               switch (sasIoUnitPg0->PhyData[ii].NegotiatedLinkRate) {
1120 -
1121 -               case MPI_SAS_IOUNIT0_RATE_PHY_DISABLED:
1122 -                       karg.Information.Phy[ii].bNegotiatedLinkRate =
1123 -                           CSMI_SAS_PHY_DISABLED;
1124 -                       break;
1125 -
1126 -               case MPI_SAS_IOUNIT0_RATE_FAILED_SPEED_NEGOTIATION:
1127 -                       karg.Information.Phy[ii].bNegotiatedLinkRate =
1128 -                           CSMI_SAS_LINK_RATE_FAILED;
1129 -                       break;
1130 -
1131 -               case MPI_SAS_IOUNIT0_RATE_SATA_OOB_COMPLETE:
1132 -                       break;
1133 -
1134 -               case MPI_SAS_IOUNIT0_RATE_1_5:
1135 -                       karg.Information.Phy[ii].bNegotiatedLinkRate =
1136 -                           CSMI_SAS_LINK_RATE_1_5_GBPS;
1137 -                       break;
1138 -
1139 -               case MPI_SAS_IOUNIT0_RATE_3_0:
1140 -                       karg.Information.Phy[ii].bNegotiatedLinkRate =
1141 -                           CSMI_SAS_LINK_RATE_3_0_GBPS;
1142 -                       break;
1143 -
1144 -               case MPI_SAS_IOUNIT0_RATE_UNKNOWN:
1145 -               default:
1146 -                       karg.Information.Phy[ii].bNegotiatedLinkRate =
1147 -                           CSMI_SAS_LINK_RATE_UNKNOWN;
1148 -                       break;
1149 -               }
1150 -
1151 -               if (sasIoUnitPg0->PhyData[ii].PortFlags &
1152 -                   MPI_SAS_IOUNIT0_PORT_FLAGS_DISCOVERY_IN_PROGRESS) {
1153 -                       karg.Information.Phy[ii].bAutoDiscover =
1154 -                           CSMI_SAS_DISCOVER_IN_PROGRESS;
1155 -               } else {
1156 -                       karg.Information.Phy[ii].bAutoDiscover =
1157 -                           CSMI_SAS_DISCOVER_COMPLETE;
1158 -               }
1159 -
1160 -               /* Issue a config request to get
1161 -                * phy information.
1162 -                */
1163 -               hdr.PageVersion = MPI_SASPHY0_PAGEVERSION;
1164 -               hdr.ExtPageLength = 0;
1165 -               hdr.PageNumber = 0;
1166 -               hdr.Reserved1 = 0;
1167 -               hdr.Reserved2 = 0;
1168 -               hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
1169 -               hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_PHY;
1170 -
1171 -               cfg.cfghdr.ehdr = &hdr;
1172 -               cfg.physAddr = -1;
1173 -               cfg.pageAddr = ii;
1174 -               cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
1175 -               cfg.dir = 0;    /* read */
1176 -               cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
1177 -
1178 -               if ((rc = mpt_config(ioc, &cfg)) != 0) {
1179 -                       dcsmisasprintk((
1180 -                           ": FAILED: MPI_SASPHY0_PAGEVERSION: HEADER\n"));
1181 -                       dcsmisasprintk((": rc=%x\n",rc));
1182 -                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1183 -                       goto sas_get_phy_info_exit;
1184 -               }
1185 -
1186 -               if (hdr.ExtPageLength == 0) {
1187 -                       dcsmisasprintk((": pci_alloc_consistent: FAILED\n"));
1188 -                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1189 -                       goto sas_get_phy_info_exit;
1190 -               }
1191 -
1192 -               sasPhyPg0_data_sz = hdr.ExtPageLength * 4;
1193 -               rc = -ENOMEM;
1194 -
1195 -               sasPhyPg0 = (SasPhyPage0_t *) pci_alloc_consistent(
1196 -                   ioc->pcidev, sasPhyPg0_data_sz, &sasPhyPg0_dma);
1197 -
1198 -               if (! sasPhyPg0) {
1199 -                       dcsmisasprintk((": pci_alloc_consistent: FAILED\n"));
1200 -                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1201 -                       goto sas_get_phy_info_exit;
1202 -               }
1203 -
1204 -               memset((u8 *)sasPhyPg0, 0, sasPhyPg0_data_sz);
1205 -               cfg.physAddr = sasPhyPg0_dma;
1206 -               cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
1207 -
1208 -               if ((rc = mpt_config(ioc, &cfg)) != 0) {
1209 -                       dcsmisasprintk((
1210 -                           ": FAILED: MPI_SASPHY0_PAGEVERSION: PAGE\n"));
1211 -                       dcsmisasprintk((": rc=%x\n",rc));
1212 -                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1213 -                       pci_free_consistent(ioc->pcidev, sasPhyPg0_data_sz,
1214 -                           (u8 *) sasPhyPg0, sasPhyPg0_dma);
1215 -                       goto sas_get_phy_info_exit;
1216 -               }
1217 -
1218 -/* EDM : dump PHY Page 0 data*/
1219 -               memcpy(&sas_address, &sasPhyPg0->SASAddress, sizeof(u64));
1220 -               dcsmisasprintk(("---- SAS PHY PAGE 0 ------------\n"));
1221 -               dcsmisasprintk(("Handle=0x%X\n",
1222 -                   le16_to_cpu(sasPhyPg0->AttachedDevHandle)));
1223 -               dcsmisasprintk(("SAS Address=0x%llX\n",
1224 -                   (unsigned long long)sas_address));
1225 -               dcsmisasprintk(("Attached PHY Identifier=0x%X\n",
1226 -                   sasPhyPg0->AttachedPhyIdentifier));
1227 -               dcsmisasprintk(("Attached Device Info=0x%X\n",
1228 -                   le32_to_cpu(sasPhyPg0->AttachedDeviceInfo)));
1229 -               dcsmisasprintk(("Programmed Link Rate=0x%X\n",
1230 -                   sasPhyPg0->ProgrammedLinkRate));
1231 -               dcsmisasprintk(("Hardware Link Rate=0x%X\n",
1232 -                   sasPhyPg0->HwLinkRate));
1233 -               dcsmisasprintk(("Change Count=0x%X\n",
1234 -                   sasPhyPg0->ChangeCount));
1235 -               dcsmisasprintk(("PHY Info=0x%X\n",
1236 -                   le32_to_cpu(sasPhyPg0->PhyInfo)));
1237 -               dcsmisasprintk(("\n"));
1238 -/* EDM : debug data */
1239 -
1240 -               /* save the data */
1241 -
1242 -               /* Set Max hardware link rate.
1243 -                * This value is hard coded
1244 -                * because the HW link rate
1245 -                * is currently being
1246 -                * overwritten in FW.
1247 -                */
1248 -
1249 -               /* Set Max hardware link rate. */
1250 -               switch (sasPhyPg0->HwLinkRate &
1251 -                   MPI_SAS_PHY0_PRATE_MAX_RATE_MASK) {
1252 -
1253 -               case MPI_SAS_PHY0_HWRATE_MAX_RATE_1_5:
1254 -                       karg.Information.Phy[ii].bMaximumLinkRate =
1255 -                           CSMI_SAS_LINK_RATE_1_5_GBPS;
1256 -                       break;
1257 -
1258 -               case MPI_SAS_PHY0_PRATE_MAX_RATE_3_0:
1259 -                       karg.Information.Phy[ii].bMaximumLinkRate =
1260 -                           CSMI_SAS_LINK_RATE_3_0_GBPS;
1261 -                       break;
1262 -               default:
1263 -                       break;
1264 -               }
1265 -
1266 -               /* Set Max programmed link rate. */
1267 -               switch (sasPhyPg0->ProgrammedLinkRate &
1268 -                   MPI_SAS_PHY0_PRATE_MAX_RATE_MASK) {
1269 -
1270 -               case MPI_SAS_PHY0_PRATE_MAX_RATE_1_5:
1271 -                       karg.Information.Phy[ii].bMaximumLinkRate |=
1272 -                           (CSMI_SAS_PROGRAMMED_LINK_RATE_1_5_GBPS << 4);
1273 -                       break;
1274 -
1275 -               case MPI_SAS_PHY0_PRATE_MAX_RATE_3_0:
1276 -                       karg.Information.Phy[ii].bMaximumLinkRate |=
1277 -                           (CSMI_SAS_PROGRAMMED_LINK_RATE_3_0_GBPS << 4);
1278 -                       break;
1279 -               default:
1280 -                       break;
1281 -               }
1282 -
1283 -               /* Set Min hardware link rate. */
1284 -               switch (sasPhyPg0->HwLinkRate &
1285 -                   MPI_SAS_PHY0_HWRATE_MIN_RATE_MASK) {
1286 -
1287 -               case MPI_SAS_PHY0_HWRATE_MIN_RATE_1_5:
1288 -                       karg.Information.Phy[ii].bMinimumLinkRate =
1289 -                           CSMI_SAS_LINK_RATE_1_5_GBPS;
1290 -                       break;
1291 -
1292 -               case MPI_SAS_PHY0_PRATE_MIN_RATE_3_0:
1293 -                       karg.Information.Phy[ii].bMinimumLinkRate =
1294 -                           CSMI_SAS_LINK_RATE_3_0_GBPS;
1295 -                       break;
1296 -               default:
1297 -                       break;
1298 -               }
1299 -
1300 -               /* Set Min programmed link rate. */
1301 -               switch (sasPhyPg0->ProgrammedLinkRate &
1302 -                   MPI_SAS_PHY0_PRATE_MIN_RATE_MASK) {
1303 -
1304 -               case MPI_SAS_PHY0_PRATE_MIN_RATE_1_5:
1305 -                       karg.Information.Phy[ii].bMinimumLinkRate |=
1306 -                           (CSMI_SAS_PROGRAMMED_LINK_RATE_1_5_GBPS << 4);
1307 -                       break;
1308 -
1309 -               case MPI_SAS_PHY0_PRATE_MIN_RATE_3_0:
1310 -                       karg.Information.Phy[ii].bMinimumLinkRate |=
1311 -                           (CSMI_SAS_PROGRAMMED_LINK_RATE_3_0_GBPS << 4);
1312 -                       break;
1313 -               default:
1314 -                       break;
1315 -               }
1316 -
1317 -               karg.Information.Phy[ii].bPhyChangeCount = sasPhyPg0->ChangeCount;
1318 -               if( sasPhyPg0->PhyInfo & MPI_SAS_PHY0_PHYINFO_VIRTUAL_PHY )
1319 -                       karg.Information.Phy[ii].bPhyFeatures = CSMI_SAS_PHY_VIRTUAL_SMP;
1320 -
1321 -               /* Fill in Attached Device
1322 -                * Initiator Port Protocol.
1323 -                * Bits 6:3
1324 -                * More than one bit can be set.
1325 -                */
1326 -               protocol = le32_to_cpu(sasPhyPg0->AttachedDeviceInfo) & 0x78;
1327 -               karg.Information.Phy[ii].Attached.bInitiatorPortProtocol = 0;
1328 -               if (protocol & MPI_SAS_DEVICE_INFO_SSP_INITIATOR)
1329 -                     karg.Information.Phy[ii].Attached.bInitiatorPortProtocol =
1330 -                           CSMI_SAS_PROTOCOL_SSP;
1331 -               if (protocol & MPI_SAS_DEVICE_INFO_STP_INITIATOR)
1332 -                    karg.Information.Phy[ii].Attached.bInitiatorPortProtocol |=
1333 -                           CSMI_SAS_PROTOCOL_STP;
1334 -               if (protocol & MPI_SAS_DEVICE_INFO_SMP_INITIATOR)
1335 -                    karg.Information.Phy[ii].Attached.bInitiatorPortProtocol |=
1336 -                           CSMI_SAS_PROTOCOL_SMP;
1337 -               if (protocol & MPI_SAS_DEVICE_INFO_SATA_HOST)
1338 -                    karg.Information.Phy[ii].Attached.bInitiatorPortProtocol |=
1339 -                           CSMI_SAS_PROTOCOL_SATA;
1340 -
1341 -               /* Fill in Phy Target Port
1342 -                * Protocol. Bits 10:7
1343 -                * More than one bit can be set.
1344 -                */
1345 -               protocol = le32_to_cpu(sasPhyPg0->AttachedDeviceInfo) & 0x780;
1346 -               karg.Information.Phy[ii].Attached.bTargetPortProtocol = 0;
1347 -               if (protocol & MPI_SAS_DEVICE_INFO_SSP_TARGET)
1348 -                       karg.Information.Phy[ii].Attached.bTargetPortProtocol |=
1349 -                           CSMI_SAS_PROTOCOL_SSP;
1350 -               if (protocol & MPI_SAS_DEVICE_INFO_STP_TARGET)
1351 -                       karg.Information.Phy[ii].Attached.bTargetPortProtocol |=
1352 -                           CSMI_SAS_PROTOCOL_STP;
1353 -               if (protocol & MPI_SAS_DEVICE_INFO_SMP_TARGET)
1354 -                       karg.Information.Phy[ii].Attached.bTargetPortProtocol |=
1355 -                           CSMI_SAS_PROTOCOL_SMP;
1356 -               if (protocol & MPI_SAS_DEVICE_INFO_SATA_DEVICE)
1357 -                       karg.Information.Phy[ii].Attached.bTargetPortProtocol |=
1358 -                           CSMI_SAS_PROTOCOL_SATA;
1359 -
1360 -
1361 -               /* Fill in Attached device type */
1362 -               switch (le32_to_cpu(sasPhyPg0->AttachedDeviceInfo) &
1363 -                   MPI_SAS_DEVICE_INFO_MASK_DEVICE_TYPE) {
1364 -
1365 -               case MPI_SAS_DEVICE_INFO_NO_DEVICE:
1366 -                       karg.Information.Phy[ii].Attached.bDeviceType =
1367 -                           CSMI_SAS_NO_DEVICE_ATTACHED;
1368 -                       break;
1369 -
1370 -               case MPI_SAS_DEVICE_INFO_END_DEVICE:
1371 -                       karg.Information.Phy[ii].Attached.bDeviceType =
1372 -                           CSMI_SAS_END_DEVICE;
1373 -                       break;
1374 -
1375 -               case MPI_SAS_DEVICE_INFO_EDGE_EXPANDER:
1376 -                       karg.Information.Phy[ii].Attached.bDeviceType =
1377 -                           CSMI_SAS_EDGE_EXPANDER_DEVICE;
1378 -                       break;
1379 -
1380 -               case MPI_SAS_DEVICE_INFO_FANOUT_EXPANDER:
1381 -                       karg.Information.Phy[ii].Attached.bDeviceType =
1382 -                           CSMI_SAS_FANOUT_EXPANDER_DEVICE;
1383 -                       break;
1384 -               }
1385 -
1386 -               /* Identify Info. */
1387 -               switch (le32_to_cpu(sasIoUnitPg0->PhyData[ii].ControllerPhyDeviceInfo) &
1388 -                   MPI_SAS_DEVICE_INFO_MASK_DEVICE_TYPE) {
1389 -
1390 -               case MPI_SAS_DEVICE_INFO_NO_DEVICE:
1391 -                       karg.Information.Phy[ii].Identify.bDeviceType =
1392 -                           CSMI_SAS_NO_DEVICE_ATTACHED;
1393 -                       break;
1394 -
1395 -               case MPI_SAS_DEVICE_INFO_END_DEVICE:
1396 -                       karg.Information.Phy[ii].Identify.bDeviceType =
1397 -                           CSMI_SAS_END_DEVICE;
1398 -                       break;
1399 -
1400 -               case MPI_SAS_DEVICE_INFO_EDGE_EXPANDER:
1401 -                       karg.Information.Phy[ii].Identify.bDeviceType =
1402 -                           CSMI_SAS_EDGE_EXPANDER_DEVICE;
1403 -                       break;
1404 -
1405 -               case MPI_SAS_DEVICE_INFO_FANOUT_EXPANDER:
1406 -                       karg.Information.Phy[ii].Identify.bDeviceType =
1407 -                           CSMI_SAS_FANOUT_EXPANDER_DEVICE;
1408 -                       break;
1409 -               }
1410 -
1411 -               /* Fill in Phy Initiator Port Protocol. Bits 6:3
1412 -                * More than one bit can be set, fall through cases.
1413 -                */
1414 -               protocol = le32_to_cpu(
1415 -                   sasIoUnitPg0->PhyData[ii].ControllerPhyDeviceInfo) & 0x78;
1416 -               karg.Information.Phy[ii].Identify.bInitiatorPortProtocol = 0;
1417 -               if( protocol & MPI_SAS_DEVICE_INFO_SSP_INITIATOR )
1418 -                    karg.Information.Phy[ii].Identify.bInitiatorPortProtocol |=
1419 -                           CSMI_SAS_PROTOCOL_SSP;
1420 -               if( protocol & MPI_SAS_DEVICE_INFO_STP_INITIATOR )
1421 -                    karg.Information.Phy[ii].Identify.bInitiatorPortProtocol |=
1422 -                           CSMI_SAS_PROTOCOL_STP;
1423 -               if( protocol & MPI_SAS_DEVICE_INFO_SMP_INITIATOR )
1424 -                    karg.Information.Phy[ii].Identify.bInitiatorPortProtocol |=
1425 -                           CSMI_SAS_PROTOCOL_SMP;
1426 -               if( protocol & MPI_SAS_DEVICE_INFO_SATA_HOST )
1427 -                    karg.Information.Phy[ii].Identify.bInitiatorPortProtocol |=
1428 -                           CSMI_SAS_PROTOCOL_SATA;
1429 -
1430 -               /* Fill in Phy Target Port Protocol. Bits 10:7
1431 -                * More than one bit can be set, fall through cases.
1432 -                */
1433 -               protocol = le32_to_cpu(
1434 -                   sasIoUnitPg0->PhyData[ii].ControllerPhyDeviceInfo) & 0x780;
1435 -               karg.Information.Phy[ii].Identify.bTargetPortProtocol = 0;
1436 -               if( protocol & MPI_SAS_DEVICE_INFO_SSP_TARGET )
1437 -                       karg.Information.Phy[ii].Identify.bTargetPortProtocol |=
1438 -                           CSMI_SAS_PROTOCOL_SSP;
1439 -               if( protocol & MPI_SAS_DEVICE_INFO_STP_TARGET )
1440 -                       karg.Information.Phy[ii].Identify.bTargetPortProtocol |=
1441 -                           CSMI_SAS_PROTOCOL_STP;
1442 -               if( protocol & MPI_SAS_DEVICE_INFO_SMP_TARGET )
1443 -                       karg.Information.Phy[ii].Identify.bTargetPortProtocol |=
1444 -                           CSMI_SAS_PROTOCOL_SMP;
1445 -               if( protocol & MPI_SAS_DEVICE_INFO_SATA_DEVICE )
1446 -                       karg.Information.Phy[ii].Identify.bTargetPortProtocol |=
1447 -                           CSMI_SAS_PROTOCOL_SATA;
1448 -
1449 -               /* Setup SAS Address for the attached device */
1450 -               if (sasPhyPg0->AttachedDevHandle) {
1451 -                       sas_address = reverse_byte_order64(sas_address);
1452 -                       memcpy(karg.Information.Phy[ii].Attached.bSASAddress,
1453 -                           &sas_address, sizeof(u64));
1454 -                       karg.Information.Phy[ii].Attached.bPhyIdentifier =
1455 -                           sasPhyPg0->AttachedPhyIdentifier;
1456 -               }
1457 -
1458 -               /* Setup SAS Address for the parent device */
1459 -               csmisas_sas_device_pg0(ioc, &device_info,
1460 -                   (MPI_SAS_DEVICE_PGAD_FORM_HANDLE <<
1461 -                   MPI_SAS_DEVICE_PGAD_FORM_SHIFT),
1462 -                   sasIoUnitPg0->PhyData[ii].ControllerDevHandle);
1463 -               sas_address = reverse_byte_order64(device_info.sas_address);
1464 -               memcpy(karg.Information.Phy[ii].Identify.bSASAddress,
1465 -                   &sas_address, sizeof(u64));
1466 -               karg.Information.Phy[ii].Identify.bPhyIdentifier = ii;
1467 -
1468 -               pci_free_consistent(ioc->pcidev, sasPhyPg0_data_sz,
1469 -                   (u8 *) sasPhyPg0, sasPhyPg0_dma);
1470 -       }
1471 -
1472 -sas_get_phy_info_exit:
1473 -
1474 -       if (sasIoUnitPg0)
1475 -               pci_free_consistent(ioc->pcidev, sasIoUnitPg0_data_sz,
1476 -                   (u8 *) sasIoUnitPg0, sasIoUnitPg0_dma);
1477 -
1478 -       /* Copy the data from kernel memory to user memory
1479 -        */
1480 -       if (copy_to_user((char *)arg, &karg,
1481 -           sizeof(CSMI_SAS_PHY_INFO_BUFFER))) {
1482 -               printk(KERN_ERR "%s@%d::%s - "
1483 -                   "Unable to write out csmisas_get_phy_info_buffer @ %p\n",
1484 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
1485 -               return -EFAULT;
1486 -       }
1487 -
1488 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
1489 -       return 0;
1490 -}
1491 -
1492 -/**
1493 - * Prototype Routine for the CSMI SAS Set PHY Info command.
1494 - *
1495 - * Outputs:    None.
1496 - * Return:     0 if successful
1497 - *             -EFAULT if data unavailable
1498 - *             -ENODEV if no such device/adapter
1499 - **/
1500 -static int
1501 -csmisas_set_phy_info(unsigned long arg)
1502 -{
1503 -       CSMI_SAS_SET_PHY_INFO_BUFFER __user *uarg = (void __user *) arg;
1504 -       CSMI_SAS_SET_PHY_INFO_BUFFER     karg;
1505 -       MPT_ADAPTER                     *ioc = NULL;
1506 -       int                             iocnum;
1507 -
1508 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
1509 -
1510 -       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_SET_PHY_INFO_BUFFER))) {
1511 -               printk(KERN_ERR "%s@%d::%s() - "
1512 -                   "Unable to read in csmi_sas_set_phy_info struct @ %p\n",
1513 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
1514 -               return -EFAULT;
1515 -       }
1516 -
1517 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
1518 -           &ioc)) < 0) || (ioc == NULL)) {
1519 -               dcsmisasprintk((KERN_ERR
1520 -               "%s::%s() @%d - ioc%d not found!\n",
1521 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
1522 -               return -ENODEV;
1523 -       }
1524 -
1525 -       if (!csmisas_is_this_sas_cntr(ioc)) {
1526 -               dcsmisasprintk((KERN_ERR
1527 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
1528 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
1529 -               return -ENODEV;
1530 -       }
1531 -
1532 -/* TODO - implement IOCTL here */
1533 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_BAD_CNTL_CODE;
1534 -       dcsmisasprintk((": not implemented\n"));
1535 -
1536 -// cim_set_phy_info_exit:
1537 -
1538 -       /* Copy the data from kernel memory to user memory
1539 -        */
1540 -       if (copy_to_user((char *)arg, &karg,
1541 -                               sizeof(CSMI_SAS_SET_PHY_INFO_BUFFER))) {
1542 -               printk(KERN_ERR "%s@%d::%s() - "
1543 -                       "Unable to write out csmi_sas_set_phy_info @ %p\n",
1544 -                               __FILE__, __LINE__, __FUNCTION__, uarg);
1545 -               return -EFAULT;
1546 -       }
1547 -
1548 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
1549 -       return 0;
1550 -
1551 -}
1552 -
1553 -/**
1554 - * Prototype Routine for the CSMI Sas Get SCSI Address command.
1555 - *
1556 - * Outputs:    None.
1557 - * Return:     0 if successful
1558 - *             -EFAULT if data unavailable
1559 - *             -ENODEV if no such device/adapter
1560 - **/
1561 -static int
1562 -csmisas_get_scsi_address(unsigned long arg)
1563 -{
1564 -       CSMI_SAS_GET_SCSI_ADDRESS_BUFFER __user *uarg = (void __user *) arg;
1565 -       CSMI_SAS_GET_SCSI_ADDRESS_BUFFER         karg;
1566 -       MPT_ADAPTER             *ioc = NULL;
1567 -       int                     iocnum;
1568 -       u64                     sas_address;
1569 -       struct sas_device_info  *sas_info;
1570 -
1571 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
1572 -
1573 -       if (copy_from_user(&karg, uarg,
1574 -           sizeof(CSMI_SAS_GET_SCSI_ADDRESS_BUFFER))) {
1575 -               printk(KERN_ERR "%s@%d::%s() - "
1576 -                   "Unable to read in csmi_sas_get_scsi_address struct @ %p\n",
1577 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
1578 -               return -EFAULT;
1579 -       }
1580 -
1581 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
1582 -           &ioc)) < 0) || (ioc == NULL)) {
1583 -               dcsmisasprintk((KERN_ERR
1584 -             "%s::%s() @%d - ioc%d not found!\n",
1585 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
1586 -               return -ENODEV;
1587 -       }
1588 -
1589 -       if (!csmisas_is_this_sas_cntr(ioc)) {
1590 -               dcsmisasprintk((KERN_ERR
1591 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
1592 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
1593 -               return -ENODEV;
1594 -       }
1595 -
1596 -       /* reverse byte order the sas address */
1597 -       memcpy(&sas_address, karg.bSASAddress, sizeof(u64));
1598 -       sas_address = reverse_byte_order64(sas_address);
1599 -
1600 -       /* Search the list for the matching SAS address. */
1601 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_NO_SCSI_ADDRESS;
1602 -       karg.bPathId = 0;
1603 -       karg.bTargetId = 0;
1604 -       karg.bLun = 0;
1605 -
1606 -       sas_info = csmisas_get_device_component_by_sas_addr(ioc, sas_address);
1607 -       if (!sas_info || sas_info->is_cached || sas_info->is_logical_volume)
1608 -               goto csmisas_get_scsi_address_exit;
1609 -
1610 -       karg.bPathId = sas_info->os.channel;
1611 -       karg.bTargetId = sas_info->os.id;
1612 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
1613 -
1614 - csmisas_get_scsi_address_exit:
1615 -
1616 -       /* Copy the data from kernel memory to user memory
1617 -        */
1618 -       if (copy_to_user((char *)arg, &karg,
1619 -           sizeof(CSMI_SAS_GET_SCSI_ADDRESS_BUFFER))) {
1620 -               printk(KERN_ERR "%s@%d::%s() - "
1621 -                   "Unable to write out csmi_sas_get_scsi_address @ %p\n",
1622 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
1623 -               return -EFAULT;
1624 -       }
1625 -
1626 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
1627 -       return 0;
1628 -}
1629 -
1630 -/**
1631 - * Prototype Routine for the CSMI Sas Get SCSI Address command.
1632 - *
1633 - * Outputs:    None.
1634 - * Return:     0 if successful
1635 - *             -EFAULT if data unavailable
1636 - *             -ENODEV if no such device/adapter
1637 - **/
1638 -static int
1639 -csmisas_get_sata_signature(unsigned long arg)
1640 -{
1641 -       CSMI_SAS_SATA_SIGNATURE_BUFFER  __user *uarg = (void __user *) arg;
1642 -       CSMI_SAS_SATA_SIGNATURE_BUFFER   karg;
1643 -       MPT_ADAPTER                     *ioc = NULL;
1644 -       int                             iocnum;
1645 -       int                             rc, jj;
1646 -       ConfigExtendedPageHeader_t      hdr;
1647 -       CONFIGPARMS                     cfg;
1648 -       SasPhyPage0_t                   *sasPhyPg0;
1649 -       dma_addr_t                      sasPhyPg0_dma;
1650 -       int                             sasPhyPg0_data_sz;
1651 -       SasDevicePage1_t                *sasDevicePg1;
1652 -       dma_addr_t                      sasDevicePg1_dma;
1653 -       int                             sasDevicePg1_data_sz;
1654 -       u8                              phyId;
1655 -
1656 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
1657 -       sasPhyPg0=NULL;
1658 -       sasPhyPg0_data_sz=0;
1659 -       sasDevicePg1=NULL;
1660 -       sasDevicePg1_data_sz=0;
1661 -
1662 -       if (copy_from_user(&karg, uarg,
1663 -            sizeof(CSMI_SAS_SATA_SIGNATURE_BUFFER))) {
1664 -               printk(KERN_ERR "%s@%d::%s() - "
1665 -                   "Unable to read in csmi_sas_sata_signature struct @ %p\n",
1666 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
1667 -               return -EFAULT;
1668 -       }
1669 -
1670 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
1671 -           &ioc)) < 0) || (ioc == NULL)) {
1672 -               dcsmisasprintk((KERN_ERR
1673 -           "%s::%s() @%d - ioc%d not found!\n",
1674 -                    __FILE__, __FUNCTION__, __LINE__, iocnum));
1675 -               return -ENODEV;
1676 -       }
1677 -
1678 -       if (!csmisas_is_this_sas_cntr(ioc)) {
1679 -               dcsmisasprintk((KERN_ERR
1680 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
1681 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
1682 -               return -ENODEV;
1683 -       }
1684 -
1685 -       phyId = karg.Signature.bPhyIdentifier;
1686 -       if (phyId >= ioc->num_ports) {
1687 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_PHY_DOES_NOT_EXIST;
1688 -               dcsmisasprintk((": phyId >= ioc->num_ports\n"));
1689 -               goto cim_sata_signature_exit;
1690 -       }
1691 -
1692 -       /* Default to success.*/
1693 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
1694 -
1695 -       /* Issue a config request to get the devHandle of the attached device
1696 -        */
1697 -
1698 -       /* Issue a config request to get phy information. */
1699 -       hdr.PageVersion = MPI_SASPHY0_PAGEVERSION;
1700 -       hdr.ExtPageLength = 0;
1701 -       hdr.PageNumber = 0;
1702 -       hdr.Reserved1 = 0;
1703 -       hdr.Reserved2 = 0;
1704 -       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
1705 -       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_PHY;
1706 -
1707 -       cfg.cfghdr.ehdr = &hdr;
1708 -       cfg.physAddr = -1;
1709 -       cfg.pageAddr = phyId;
1710 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
1711 -       cfg.dir = 0;    /* read */
1712 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
1713 -
1714 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
1715 -               /* Don't check if this failed.  Already in a
1716 -                * failure case.
1717 -                */
1718 -               dcsmisasprintk((": FAILED: MPI_SASPHY0_PAGEVERSION: HEADER\n"));
1719 -               dcsmisasprintk((": rc=%x\n",rc));
1720 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1721 -               goto cim_sata_signature_exit;
1722 -       }
1723 -
1724 -       if (hdr.ExtPageLength == 0) {
1725 -               /* Don't check if this failed.  Already in a
1726 -                * failure case.
1727 -                */
1728 -               dcsmisasprintk((": hdr.ExtPageLength == 0\n"));
1729 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1730 -               goto cim_sata_signature_exit;
1731 -       }
1732 -
1733 -
1734 -       sasPhyPg0_data_sz = hdr.ExtPageLength * 4;
1735 -       rc = -ENOMEM;
1736 -
1737 -       sasPhyPg0 = (SasPhyPage0_t *) pci_alloc_consistent(ioc->pcidev,
1738 -           sasPhyPg0_data_sz, &sasPhyPg0_dma);
1739 -
1740 -       if (! sasPhyPg0) {
1741 -               dcsmisasprintk((": pci_alloc_consistent: FAILED\n"));
1742 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1743 -               goto cim_sata_signature_exit;
1744 -       }
1745 -
1746 -       memset((u8 *)sasPhyPg0, 0, sasPhyPg0_data_sz);
1747 -       cfg.physAddr = sasPhyPg0_dma;
1748 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
1749 -
1750 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
1751 -               /* Don't check if this failed.  Already in a
1752 -                * failure case.
1753 -                */
1754 -               dcsmisasprintk((": FAILED: MPI_SASPHY0_PAGEVERSION: PAGE\n"));
1755 -               dcsmisasprintk((": rc=%x\n",rc));
1756 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1757 -               goto cim_sata_signature_exit;
1758 -       }
1759 -
1760 -       /* Make sure a SATA device is attached. */
1761 -       if ((le32_to_cpu(sasPhyPg0->AttachedDeviceInfo) &
1762 -           MPI_SAS_DEVICE_INFO_SATA_DEVICE) == 0) {
1763 -               dcsmisasprintk((": NOT A SATA DEVICE\n"));
1764 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_NO_SATA_DEVICE;
1765 -               goto cim_sata_signature_exit;
1766 -       }
1767 -
1768 -       /* Get device page 1 for FIS  signature. */
1769 -       hdr.PageVersion = MPI_SASDEVICE1_PAGEVERSION;
1770 -       hdr.ExtPageLength = 0;
1771 -       hdr.PageNumber = 1 /* page number 1 */;
1772 -       hdr.Reserved1 = 0;
1773 -       hdr.Reserved2 = 0;
1774 -       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
1775 -       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_DEVICE;
1776 -
1777 -       cfg.cfghdr.ehdr = &hdr;
1778 -       cfg.physAddr = -1;
1779 -
1780 -       cfg.pageAddr = ((MPI_SAS_DEVICE_PGAD_FORM_HANDLE <<
1781 -           MPI_SAS_DEVICE_PGAD_FORM_SHIFT) |
1782 -           le16_to_cpu(sasPhyPg0->AttachedDevHandle));
1783 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
1784 -       cfg.dir = 0;    /* read */
1785 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
1786 -
1787 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
1788 -               dcsmisasprintk((": FAILED: MPI_SASDEVICE1_PAGEVERSION: HEADER\n"));
1789 -               dcsmisasprintk((": rc=%x\n",rc));
1790 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1791 -               goto cim_sata_signature_exit;
1792 -       }
1793 -
1794 -       if (hdr.ExtPageLength == 0) {
1795 -               dcsmisasprintk((": hdr.ExtPageLength == 0\n"));
1796 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1797 -               goto cim_sata_signature_exit;
1798 -       }
1799 -
1800 -       sasDevicePg1_data_sz = hdr.ExtPageLength * 4;
1801 -       rc = -ENOMEM;
1802 -
1803 -       sasDevicePg1 = (SasDevicePage1_t *) pci_alloc_consistent
1804 -           (ioc->pcidev, sasDevicePg1_data_sz, &sasDevicePg1_dma);
1805 -
1806 -       if (! sasDevicePg1) {
1807 -               dcsmisasprintk((": pci_alloc_consistent: FAILED\n"));
1808 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1809 -               goto cim_sata_signature_exit;
1810 -       }
1811 -
1812 -       memset((u8 *)sasDevicePg1, 0, sasDevicePg1_data_sz);
1813 -       cfg.physAddr = sasDevicePg1_dma;
1814 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
1815 -
1816 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
1817 -               dcsmisasprintk((": FAILED: MPI_SASDEVICE1_PAGEVERSION: PAGE\n"));
1818 -               dcsmisasprintk((": rc=%x\n",rc));
1819 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
1820 -               goto cim_sata_signature_exit;
1821 -       }
1822 -
1823 -/* EDM : dump Device Page 1 data*/
1824 -       dcsmisasprintk(("---- SAS DEVICE PAGE 1 ---------\n"));
1825 -       dcsmisasprintk(("Handle=0x%x\n",sasDevicePg1->DevHandle));
1826 -       dcsmisasprintk(("SAS Address="));
1827 -       for(jj=0;jj<8;jj++)
1828 -               dcsmisasprintk(("%02x ",
1829 -               ((u8 *)&sasDevicePg1->SASAddress)[jj]));
1830 -       dcsmisasprintk(("\n"));
1831 -       dcsmisasprintk(("Target ID=0x%x\n",sasDevicePg1->TargetID));
1832 -       dcsmisasprintk(("Bus=0x%x\n",sasDevicePg1->Bus));
1833 -       dcsmisasprintk(("Initial Reg Device FIS="));
1834 -       for(jj=0;jj<20;jj++)
1835 -               dcsmisasprintk(("%02x ",
1836 -               ((u8 *)&sasDevicePg1->InitialRegDeviceFIS)[jj]));
1837 -       dcsmisasprintk(("\n\n"));
1838 -/* EDM : debug data */
1839 -
1840 -       memcpy(karg.Signature.bSignatureFIS,
1841 -               sasDevicePg1->InitialRegDeviceFIS,20);
1842 -
1843 - cim_sata_signature_exit:
1844 -
1845 -       if (sasPhyPg0)
1846 -               pci_free_consistent(ioc->pcidev, sasPhyPg0_data_sz,
1847 -                   (u8 *) sasPhyPg0, sasPhyPg0_dma);
1848 -
1849 -       if (sasDevicePg1)
1850 -               pci_free_consistent(ioc->pcidev, sasDevicePg1_data_sz,
1851 -                   (u8 *) sasDevicePg1, sasDevicePg1_dma);
1852 -
1853 -       /* Copy the data from kernel memory to user memory
1854 -        */
1855 -       if (copy_to_user((char *)arg, &karg,
1856 -           sizeof(CSMI_SAS_SATA_SIGNATURE_BUFFER))) {
1857 -               printk(KERN_ERR "%s@%d::%s() - "
1858 -                   "Unable to write out csmi_sas_sata_signature @ %p\n",
1859 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
1860 -               return -EFAULT;
1861 -       }
1862 -
1863 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
1864 -       return 0;
1865 -}
1866 -
1867 -/**
1868 - * Prototype Routine for the CSMI Sas Get SCSI Address command.
1869 - *
1870 - * Outputs:    None.
1871 - * Return:     0 if successful
1872 - *             -EFAULT if data unavailable
1873 - *             -ENODEV if no such device/adapter
1874 - **/
1875 -static int
1876 -csmisas_get_device_address(unsigned long arg)
1877 -{
1878 -       CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER __user *uarg = (void __user *) arg;
1879 -       CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER       karg;
1880 -       MPT_ADAPTER             *ioc = NULL;
1881 -       int                     iocnum;
1882 -       struct sas_device_info  *sas_info;
1883 -       u64                     sas_address;
1884 -
1885 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
1886 -
1887 -       if (copy_from_user(&karg, uarg,
1888 -           sizeof(CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER))) {
1889 -               printk(KERN_ERR "%s@%d::%s() - "
1890 -          "Unable to read in csmi_sas_get_device_address_buffer struct @ %p\n",
1891 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
1892 -               return -EFAULT;
1893 -       }
1894 -
1895 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
1896 -           &ioc)) < 0) || (ioc == NULL)) {
1897 -               dcsmisasprintk((KERN_ERR
1898 -           "%s::%s() @%d - ioc%d not found!\n",
1899 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
1900 -               return -ENODEV;
1901 -       }
1902 -
1903 -       if (!csmisas_is_this_sas_cntr(ioc)) {
1904 -               dcsmisasprintk((KERN_ERR
1905 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
1906 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
1907 -               return -ENODEV;
1908 -       }
1909 -
1910 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_NO_DEVICE_ADDRESS;
1911 -       memset(karg.bSASAddress, 0, sizeof(u64));
1912 -       memset(karg.bSASLun, 0, sizeof(karg.bSASLun));
1913 -
1914 -       /* Search the list for the matching SAS address. */
1915 -       sas_info = csmisas_get_device_component_by_os(ioc, karg.bPathId,
1916 -           karg.bTargetId);
1917 -       if (!sas_info || sas_info->is_cached || sas_info->is_logical_volume)
1918 -               goto csmisas_get_device_address_exit;
1919 -
1920 -       sas_address = reverse_byte_order64(sas_info->sas_address);
1921 -       memcpy(karg.bSASAddress, &sas_address, sizeof(u64));
1922 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
1923 -
1924 - csmisas_get_device_address_exit:
1925 -
1926 -       /* Copy the data from kernel memory to user memory
1927 -        */
1928 -       if (copy_to_user((char *)arg, &karg,
1929 -           sizeof(CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER))) {
1930 -               printk(KERN_ERR "%s@%d::%s() - "
1931 -               "Unable to write out csmi_sas_get_device_address_buffer @ %p\n",
1932 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
1933 -               return -EFAULT;
1934 -       }
1935 -
1936 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
1937 -       return 0;
1938 -}
1939 -
1940 -/**
1941 - * Prototype Routine for the CSMI Sas Get Link Errors command.
1942 - *
1943 - * Outputs:    None.
1944 - * Return:     0 if successful
1945 - *             -EFAULT if data unavailable
1946 - *             -ENODEV if no such device/adapter
1947 - **/
1948 -static int
1949 -csmisas_get_link_errors(unsigned long arg)
1950 -{
1951 -       CSMI_SAS_LINK_ERRORS_BUFFER __user *uarg = (void __user *) arg;
1952 -       CSMI_SAS_LINK_ERRORS_BUFFER      karg;
1953 -       MPT_ADAPTER                     *ioc = NULL;
1954 -       MPT_FRAME_HDR                   *mf = NULL;
1955 -       MPIHeader_t                     *mpi_hdr;
1956 -       int                             iocnum;
1957 -       int                             rc;
1958 -       ConfigExtendedPageHeader_t      hdr;
1959 -       CONFIGPARMS                     cfg;
1960 -       SasPhyPage1_t                   *sasPhyPage1;
1961 -       dma_addr_t                      sasPhyPage1_dma;
1962 -       int                             sasPhyPage1_data_sz;
1963 -       SasIoUnitControlRequest_t       *sasIoUnitCntrReq;
1964 -       SasIoUnitControlReply_t         *sasIoUnitCntrReply;
1965 -       u8                              phyId;
1966 -       u16                             ioc_status;
1967 -
1968 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
1969 -       sasPhyPage1=NULL;
1970 -       sasPhyPage1_data_sz=0;
1971 -
1972 -       if (copy_from_user(&karg, uarg,
1973 -            sizeof(CSMI_SAS_LINK_ERRORS_BUFFER))) {
1974 -               printk(KERN_ERR "%s@%d::%s() - "
1975 -                   "Unable to read in csmisas_get_link_errors struct @ %p\n",
1976 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
1977 -               return -EFAULT;
1978 -       }
1979 -
1980 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
1981 -           &ioc)) < 0) || (ioc == NULL)) {
1982 -               dcsmisasprintk((KERN_ERR
1983 -           "%s::%s() @%d - ioc%d not found!\n",
1984 -                    __FILE__, __FUNCTION__, __LINE__, iocnum));
1985 -               return -ENODEV;
1986 -       }
1987 -
1988 -       if (!csmisas_is_this_sas_cntr(ioc)) {
1989 -               dcsmisasprintk((KERN_ERR
1990 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
1991 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
1992 -               return -ENODEV;
1993 -       }
1994 -
1995 -       phyId = karg.Information.bPhyIdentifier;
1996 -       if (phyId >= ioc->num_ports) {
1997 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_PHY_DOES_NOT_EXIST;
1998 -               dcsmisasprintk((": phyId >= ioc->num_ports\n"));
1999 -               goto cim_get_link_errors_exit;
2000 -       }
2001 -
2002 -       /* Default to success.*/
2003 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
2004 -
2005 -       /* Issue a config request to get the devHandle of the attached device
2006 -        */
2007 -
2008 -       /* Issue a config request to get phy information. */
2009 -       hdr.PageVersion = MPI_SASPHY1_PAGEVERSION;
2010 -       hdr.ExtPageLength = 0;
2011 -       hdr.PageNumber = 1 /* page number 1*/;
2012 -       hdr.Reserved1 = 0;
2013 -       hdr.Reserved2 = 0;
2014 -       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
2015 -       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_PHY;
2016 -
2017 -       cfg.cfghdr.ehdr = &hdr;
2018 -       cfg.physAddr = -1;
2019 -       cfg.pageAddr = phyId;
2020 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
2021 -       cfg.dir = 0;    /* read */
2022 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
2023 -
2024 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
2025 -               /* Don't check if this failed.  Already in a
2026 -                * failure case.
2027 -                */
2028 -               dcsmisasprintk((": FAILED: MPI_SASPHY1_PAGEVERSION: HEADER\n"));
2029 -               dcsmisasprintk((": rc=%x\n",rc));
2030 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2031 -               goto cim_get_link_errors_exit;
2032 -       }
2033 -
2034 -       if (hdr.ExtPageLength == 0) {
2035 -               /* Don't check if this failed.  Already in a
2036 -                * failure case.
2037 -                */
2038 -               dcsmisasprintk((": hdr.ExtPageLength == 0\n"));
2039 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2040 -               goto cim_get_link_errors_exit;
2041 -       }
2042 -
2043 -
2044 -       sasPhyPage1_data_sz = hdr.ExtPageLength * 4;
2045 -       rc = -ENOMEM;
2046 -
2047 -       sasPhyPage1 = (SasPhyPage1_t *) pci_alloc_consistent(ioc->pcidev,
2048 -           sasPhyPage1_data_sz, &sasPhyPage1_dma);
2049 -
2050 -       if (! sasPhyPage1) {
2051 -               dcsmisasprintk((": pci_alloc_consistent: FAILED\n"));
2052 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2053 -               goto cim_get_link_errors_exit;
2054 -       }
2055 -
2056 -       memset((u8 *)sasPhyPage1, 0, sasPhyPage1_data_sz);
2057 -       cfg.physAddr = sasPhyPage1_dma;
2058 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
2059 -
2060 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
2061 -               /* Don't check if this failed.  Already in a
2062 -                * failure case.
2063 -                */
2064 -               dcsmisasprintk((": FAILED: MPI_SASPHY1_PAGEVERSION: PAGE\n"));
2065 -               dcsmisasprintk((": rc=%x\n",rc));
2066 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2067 -               goto cim_get_link_errors_exit;
2068 -       }
2069 -
2070 -/* EDM : dump PHY Page 1 data*/
2071 -       dcsmisasprintk(("---- SAS PHY PAGE 1 ------------\n"));
2072 -       dcsmisasprintk(("Invalid Dword Count=0x%x\n",
2073 -           sasPhyPage1->InvalidDwordCount));
2074 -       dcsmisasprintk(("Running Disparity Error Count=0x%x\n",
2075 -           sasPhyPage1->RunningDisparityErrorCount));
2076 -       dcsmisasprintk(("Loss Dword Synch Count=0x%x\n",
2077 -           sasPhyPage1->LossDwordSynchCount));
2078 -       dcsmisasprintk(("PHY Reset Problem Count=0x%x\n",
2079 -           sasPhyPage1->PhyResetProblemCount));
2080 -       dcsmisasprintk(("\n\n"));
2081 -/* EDM : debug data */
2082 -
2083 -       karg.Information.uInvalidDwordCount =
2084 -               le32_to_cpu(sasPhyPage1->InvalidDwordCount);
2085 -       karg.Information.uRunningDisparityErrorCount =
2086 -               le32_to_cpu(sasPhyPage1->RunningDisparityErrorCount);
2087 -       karg.Information.uLossOfDwordSyncCount =
2088 -               le32_to_cpu(sasPhyPage1->LossDwordSynchCount);
2089 -       karg.Information.uPhyResetProblemCount =
2090 -               le32_to_cpu(sasPhyPage1->PhyResetProblemCount);
2091 -
2092 -       if (karg.Information.bResetCounts ==
2093 -           CSMI_SAS_LINK_ERROR_DONT_RESET_COUNTS ) {
2094 -               goto cim_get_link_errors_exit;
2095 -       }
2096 -
2097 -       /* Clear Error log
2098 -        *
2099 -        * Issue IOUNIT Control Reqeust Message
2100 -        */
2101 -
2102 -       /* Get a MF for this command.
2103 -        */
2104 -       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
2105 -               dcsmisasprintk((": no msg frames!\n"));
2106 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2107 -               goto cim_get_link_errors_exit;
2108 -        }
2109 -
2110 -       mpi_hdr = (MPIHeader_t *) mf;
2111 -       sasIoUnitCntrReq = (SasIoUnitControlRequest_t *)mf;
2112 -       memset(sasIoUnitCntrReq,0,sizeof(SasIoUnitControlRequest_t));
2113 -       sasIoUnitCntrReq->Function = MPI_FUNCTION_SAS_IO_UNIT_CONTROL;
2114 -       sasIoUnitCntrReq->MsgContext = mpi_hdr->MsgContext;
2115 -       sasIoUnitCntrReq->PhyNum = phyId;
2116 -       sasIoUnitCntrReq->Operation = MPI_SAS_OP_PHY_CLEAR_ERROR_LOG;
2117 -
2118 -       if (csmisas_send_command_wait(ioc, mf, karg.IoctlHeader.Timeout) != 0) {
2119 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2120 -               goto cim_get_link_errors_exit;
2121 -       }
2122 -
2123 -       /* process the completed Reply Message Frame */
2124 -       if (ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) {
2125 -
2126 -               sasIoUnitCntrReply =
2127 -                   (SasIoUnitControlReply_t *)ioc->ioctl->ReplyFrame;
2128 -               ioc_status = le16_to_cpu(sasIoUnitCntrReply->IOCStatus)
2129 -                   & MPI_IOCSTATUS_MASK;
2130 -
2131 -               if (ioc_status != MPI_IOCSTATUS_SUCCESS) {
2132 -                       dcsmisasprintk((": SAS IO Unit Control: "));
2133 -                       dcsmisasprintk(("IOCStatus=0x%X IOCLogInfo=0x%X\n",
2134 -                           sasIoUnitCntrReply->IOCStatus,
2135 -                           sasIoUnitCntrReply->IOCLogInfo));
2136 -               }
2137 -       }
2138 -
2139 - cim_get_link_errors_exit:
2140 -
2141 -       if (sasPhyPage1)
2142 -               pci_free_consistent(ioc->pcidev, sasPhyPage1_data_sz,
2143 -                   (u8 *) sasPhyPage1, sasPhyPage1_dma);
2144 -
2145 -       /* Copy the data from kernel memory to user memory
2146 -        */
2147 -       if (copy_to_user((char *)arg, &karg,
2148 -           sizeof(CSMI_SAS_LINK_ERRORS_BUFFER))) {
2149 -               printk(KERN_ERR "%s@%d::%s() - "
2150 -                   "Unable to write out csmisas_get_link_errors @ %p\n",
2151 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
2152 -               return -EFAULT;
2153 -       }
2154 -
2155 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
2156 -       return 0;
2157 -
2158 -}
2159 -
2160 -/**
2161 - * Prototype Routine for the CSMI SAS SMP Passthru command.
2162 - *
2163 - * Outputs:    None.
2164 - * Return:     0 if successful
2165 - *             -EFAULT if data unavailable
2166 - *             -ENODEV if no such device/adapter
2167 - **/
2168 -static int
2169 -csmisas_smp_passthru(unsigned long arg)
2170 -{
2171 -       CSMI_SAS_SMP_PASSTHRU_BUFFER __user *uarg = (void __user *) arg;
2172 -       MPT_ADAPTER                     *ioc;
2173 -       CSMI_SAS_SMP_PASSTHRU_BUFFER     karg;
2174 -       pSmpPassthroughRequest_t        smpReq;
2175 -       pSmpPassthroughReply_t          smpReply;
2176 -       MPT_FRAME_HDR                   *mf = NULL;
2177 -       MPIHeader_t                     *mpi_hdr;
2178 -       char                            *psge;
2179 -       int                             iocnum, flagsLength;
2180 -       void *                          request_data;
2181 -       dma_addr_t                      request_data_dma;
2182 -       u32                             request_data_sz;
2183 -       void *                          response_data;
2184 -       dma_addr_t                      response_data_dma;
2185 -       u32                             response_data_sz;
2186 -       u16                             ioc_status;
2187 -       u64                             sas_address;
2188 -
2189 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
2190 -
2191 -       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_SMP_PASSTHRU_BUFFER))) {
2192 -               printk(KERN_ERR "%s@%d::%s() - "
2193 -                   "Unable to read in csmi_sas_smp_passthru struct @ %p\n",
2194 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
2195 -               return -EFAULT;
2196 -       }
2197 -
2198 -       request_data = NULL;
2199 -       response_data = NULL;
2200 -       response_data_sz = sizeof(CSMI_SAS_SMP_RESPONSE);
2201 -       request_data_sz  = karg.Parameters.uRequestLength;
2202 -
2203 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
2204 -           &ioc)) < 0) || (ioc == NULL)) {
2205 -               dcsmisasprintk((KERN_ERR
2206 -               "%s::%s() @%d - ioc%d not found!\n",
2207 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
2208 -               return -ENODEV;
2209 -       }
2210 -
2211 -       if (!csmisas_is_this_sas_cntr(ioc)) {
2212 -               dcsmisasprintk((KERN_ERR
2213 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
2214 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
2215 -               return -ENODEV;
2216 -       }
2217 -
2218 -       /* Make sure the adapter is not being reset. */
2219 -       if (!ioc->ioctl) {
2220 -               printk(KERN_ERR "%s@%d::%s - "
2221 -                   "No memory available during driver init.\n",
2222 -                   __FILE__, __LINE__,__FUNCTION__);
2223 -               return -ENOMEM;
2224 -       } else if (ioc->ioctl->status & MPT_IOCTL_STATUS_DID_IOCRESET) {
2225 -               printk(KERN_ERR "%s@%d::%s - "
2226 -                   "Busy with IOC Reset \n",
2227 -                   __FILE__, __LINE__,__FUNCTION__);
2228 -               return -EBUSY;
2229 -       }
2230 -
2231 -       /* Default to success.*/
2232 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
2233 -
2234 -       /* Do some error checking on the request. */
2235 -       if (karg.Parameters.bPortIdentifier == CSMI_SAS_IGNORE_PORT) {
2236 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_SELECT_PHY_OR_PORT;
2237 -               goto cim_smp_passthru_exit;
2238 -       }
2239 -
2240 -       if ((request_data_sz > 0xFFFF) || (!request_data_sz)) {
2241 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2242 -               goto cim_smp_passthru_exit;
2243 -       }
2244 -
2245 -       /* Get a free request frame and save the message context.
2246 -        */
2247 -       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
2248 -               dcsmisasprintk((": no msg frames!\n"));
2249 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2250 -               goto cim_smp_passthru_exit;
2251 -        }
2252 -
2253 -       mpi_hdr = (MPIHeader_t *) mf;
2254 -       smpReq = (pSmpPassthroughRequest_t ) mf;
2255 -
2256 -       memset(smpReq,0,ioc->req_sz);
2257 -
2258 -       memcpy(&sas_address, karg.Parameters.bDestinationSASAddress,
2259 -           sizeof(u64));
2260 -       sas_address = cpu_to_le64(reverse_byte_order64(sas_address));
2261 -       memcpy(&smpReq->SASAddress, &sas_address, sizeof(u64));
2262 -
2263 -       /* Fill in smp request. */
2264 -       smpReq->PhysicalPort = karg.Parameters.bPortIdentifier;
2265 -       smpReq->Function = MPI_FUNCTION_SMP_PASSTHROUGH;
2266 -       smpReq->RequestDataLength = cpu_to_le16(request_data_sz);
2267 -       smpReq->ConnectionRate = karg.Parameters.bConnectionRate;
2268 -       smpReq->MsgContext = mpi_hdr->MsgContext;
2269 -       smpReq->Reserved2 = 0;
2270 -       smpReq->Reserved3 = 0;
2271 -
2272 -       /*
2273 -        * Prepare the necessary pointers to run
2274 -        * through the SGL generation
2275 -        */
2276 -
2277 -       psge = (char *)&smpReq->SGL;
2278 -
2279 -       /* setup the *Request* payload SGE */
2280 -       flagsLength = MPI_SGE_FLAGS_SIMPLE_ELEMENT |
2281 -               MPI_SGE_FLAGS_SYSTEM_ADDRESS |
2282 -               MPI_SGE_FLAGS_32_BIT_ADDRESSING |
2283 -               MPI_SGE_FLAGS_HOST_TO_IOC |
2284 -               MPI_SGE_FLAGS_END_OF_BUFFER;
2285 -
2286 -       if (sizeof(dma_addr_t) == sizeof(u64)) {
2287 -               flagsLength |= MPI_SGE_FLAGS_64_BIT_ADDRESSING;
2288 -       }
2289 -       flagsLength = flagsLength << MPI_SGE_FLAGS_SHIFT;
2290 -       flagsLength |= request_data_sz;
2291 -
2292 -       request_data = pci_alloc_consistent(
2293 -           ioc->pcidev, request_data_sz, &request_data_dma);
2294 -
2295 -       if (!request_data) {
2296 -               dcsmisasprintk((": pci_alloc_consistent: FAILED\n"));
2297 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2298 -               mpt_free_msg_frame(ioc, mf);
2299 -               goto cim_smp_passthru_exit;
2300 -       }
2301 -
2302 -       mpt_add_sge(psge, flagsLength, request_data_dma);
2303 -       psge += (sizeof(u32) + sizeof(dma_addr_t));
2304 -
2305 -       memcpy(request_data,&karg.Parameters.Request,request_data_sz);
2306 -
2307 -       /* setup the *Response* payload SGE */
2308 -       response_data = pci_alloc_consistent(
2309 -           ioc->pcidev, response_data_sz, &response_data_dma);
2310 -
2311 -       if (!response_data) {
2312 -               dcsmisasprintk((": pci_alloc_consistent: FAILED\n"));
2313 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2314 -               mpt_free_msg_frame(ioc, mf);
2315 -               goto cim_smp_passthru_exit;
2316 -       }
2317 -
2318 -       flagsLength = MPI_SGE_FLAGS_SIMPLE_ELEMENT |
2319 -               MPI_SGE_FLAGS_SYSTEM_ADDRESS |
2320 -               MPI_SGE_FLAGS_32_BIT_ADDRESSING |
2321 -               MPI_SGE_FLAGS_IOC_TO_HOST |
2322 -               MPI_SGE_FLAGS_END_OF_BUFFER;
2323 -
2324 -       if (sizeof(dma_addr_t) == sizeof(u64)) {
2325 -               flagsLength |= MPI_SGE_FLAGS_64_BIT_ADDRESSING;
2326 -       }
2327 -
2328 -       flagsLength = flagsLength << MPI_SGE_FLAGS_SHIFT;
2329 -       flagsLength |= response_data_sz;
2330 -
2331 -       mpt_add_sge(psge, flagsLength, response_data_dma);
2332 -
2333 -       if (csmisas_send_command_wait(ioc, mf, karg.IoctlHeader.Timeout) != 0) {
2334 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2335 -               goto cim_smp_passthru_exit;
2336 -       }
2337 -
2338 -       if ((ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) == 0) {
2339 -               dcsmisasprintk((": SMP Passthru: oh no, there is no reply!!"));
2340 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2341 -               goto cim_smp_passthru_exit;
2342 -       }
2343 -
2344 -       /* process the completed Reply Message Frame */
2345 -       smpReply = (pSmpPassthroughReply_t )ioc->ioctl->ReplyFrame;
2346 -       ioc_status = le16_to_cpu(smpReply->IOCStatus) & MPI_IOCSTATUS_MASK;
2347 -
2348 -       if ((ioc_status != MPI_IOCSTATUS_SUCCESS) &&
2349 -           (ioc_status != MPI_IOCSTATUS_SCSI_DATA_UNDERRUN)) {
2350 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2351 -               dcsmisasprintk((": SMP Passthru: "));
2352 -               dcsmisasprintk(("IOCStatus=0x%X IOCLogInfo=0x%X SASStatus=0x%X\n",
2353 -                   le16_to_cpu(smpReply->IOCStatus),
2354 -                   le32_to_cpu(smpReply->IOCLogInfo),
2355 -                   smpReply->SASStatus));
2356 -               goto cim_smp_passthru_exit;
2357 -       }
2358 -
2359 -       karg.Parameters.bConnectionStatus =
2360 -           map_sas_status_to_csmi(smpReply->SASStatus);
2361 -
2362 -
2363 -       if (le16_to_cpu(smpReply->ResponseDataLength)) {
2364 -               karg.Parameters.uResponseBytes = le16_to_cpu(smpReply->ResponseDataLength);
2365 -               memcpy(&karg.Parameters.Response,
2366 -                   response_data, le16_to_cpu(smpReply->ResponseDataLength));
2367 -       }
2368 -
2369 - cim_smp_passthru_exit:
2370 -
2371 -       if (request_data)
2372 -               pci_free_consistent(ioc->pcidev, request_data_sz,
2373 -                   (u8 *)request_data, request_data_dma);
2374 -
2375 -       if (response_data)
2376 -               pci_free_consistent(ioc->pcidev, response_data_sz,
2377 -                   (u8 *)response_data, response_data_dma);
2378 -
2379 -
2380 -       /* Copy the data from kernel memory to user memory
2381 -        */
2382 -       if (copy_to_user((char *)arg, &karg,
2383 -                               sizeof(CSMI_SAS_SMP_PASSTHRU_BUFFER))) {
2384 -               printk(KERN_ERR "%s@%d::%s() - "
2385 -                       "Unable to write out csmi_sas_smp_passthru @ %p\n",
2386 -                               __FILE__, __LINE__, __FUNCTION__, uarg);
2387 -               return -EFAULT;
2388 -       }
2389 -
2390 -       dcsmisasprintk((": %s exit.\n",__FUNCTION__));
2391 -       return 0;
2392 -}
2393 -
2394 -/**
2395 - * Prototype Routine for the CSMI SAS SSP Passthru command.
2396 - *
2397 - * Outputs:    None.
2398 - * Return:     0 if successful
2399 - *             -EFAULT if data unavailable
2400 - *             -ENODEV if no such device/adapter
2401 - **/
2402 -static int csmisas_ssp_passthru(unsigned long arg)
2403 -{
2404 -       CSMI_SAS_SSP_PASSTHRU_BUFFER __user *uarg = (void __user *) arg;
2405 -       CSMI_SAS_SSP_PASSTHRU_BUFFER     karg_hdr, * karg;
2406 -       MPT_ADAPTER                     *ioc = NULL;
2407 -       pSCSIIORequest_t                pScsiRequest;
2408 -       pSCSIIOReply_t                  pScsiReply;
2409 -       MPT_FRAME_HDR                   *mf = NULL;
2410 -       MPIHeader_t                     *mpi_hdr;
2411 -       int                             iocnum,ii;
2412 -       u64                             sas_address;
2413 -       u16                             req_idx;
2414 -       char                            *psge;
2415 -       int                             flagsLength;
2416 -       void *                          request_data;
2417 -       dma_addr_t                      request_data_dma;
2418 -       u32                             request_data_sz;
2419 -       int                             malloc_data_sz;
2420 -       int                             memory_pages;
2421 -       u16                             ioc_status;
2422 -       u8                              volume_id;
2423 -       u8                              volume_bus;
2424 -       u8                              is_hidden_raid_component;
2425 -       u8                              channel;
2426 -       u8                              id;
2427 -       struct sas_device_info          *sas_info;
2428 -
2429 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
2430 -
2431 -       if (copy_from_user(&karg_hdr, uarg, sizeof(CSMI_SAS_SSP_PASSTHRU_BUFFER))) {
2432 -               printk(KERN_ERR "%s@%d::%s() - "
2433 -                   "Unable to read in csmi_sas_ssp_passthru struct @ %p\n",
2434 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
2435 -               return -EFAULT;
2436 -       }
2437 -
2438 -       request_data = NULL;
2439 -       request_data_sz = karg_hdr.Parameters.uDataLength;
2440 -       channel = 0;
2441 -       id = 0;
2442 -       volume_id = 0;
2443 -       volume_bus = 0;
2444 -       is_hidden_raid_component = 0;
2445 -
2446 -       malloc_data_sz = (request_data_sz +
2447 -           offsetof(CSMI_SAS_SSP_PASSTHRU_BUFFER,bDataBuffer));
2448 -       memory_pages = get_order(malloc_data_sz);
2449 -       karg = (CSMI_SAS_SSP_PASSTHRU_BUFFER *)__get_free_pages(
2450 -               GFP_KERNEL, memory_pages);
2451 -       if (!karg){
2452 -               printk(KERN_ERR "%s@%d::%s() - "
2453 -                       "Unable to malloc SAS_SSP_PASSTHRU_BUFFER "
2454 -                       "malloc_data_sz=%d memory_pages=%d\n",
2455 -                       __FILE__, __LINE__, __FUNCTION__,
2456 -                       malloc_data_sz, memory_pages);
2457 -               return -ENOMEM;
2458 -       }
2459 -
2460 -       dcsmisasprintk((KERN_ERR "%s@%d::%s() - "
2461 -                       "malloc'ed SAS_SSP_PASSTHRU_BUFFER "
2462 -                       "malloc_data_sz=%d memory_pages=%d\n",
2463 -                       __FILE__, __LINE__, __FUNCTION__,
2464 -                       malloc_data_sz, memory_pages));
2465 -
2466 -       memset(karg, 0, sizeof(*karg));
2467 -
2468 -       if (copy_from_user(karg, uarg, request_data_sz +
2469 -           offsetof(CSMI_SAS_SSP_PASSTHRU_BUFFER,bDataBuffer))) {
2470 -               printk(KERN_ERR "%s@%d::%s() - "
2471 -                   "Unable to read in csmi_sas_ssp_passthru struct @ %p\n",
2472 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
2473 -               free_pages((unsigned long)karg, memory_pages);
2474 -               return -EFAULT;
2475 -       }
2476 -
2477 -       /*
2478 -        * some checks of the incoming frame
2479 -        */
2480 -       if ( offsetof(CSMI_SAS_SSP_PASSTHRU_BUFFER,bDataBuffer) +
2481 -           request_data_sz - sizeof(IOCTL_HEADER) >
2482 -           karg->IoctlHeader.Length ) {
2483 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
2484 -               dcsmisasprintk((KERN_ERR
2485 -                   "%s::%s()"
2486 -                   " @%d - expected datalen incorrect!\n",
2487 -                   __FILE__, __FUNCTION__, __LINE__));
2488 -               goto cim_ssp_passthru_exit;
2489 -       }
2490 -
2491 -       if (((iocnum = mpt_verify_adapter(karg->IoctlHeader.IOControllerNumber,
2492 -           &ioc)) < 0) || (ioc == NULL)) {
2493 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
2494 -               dcsmisasprintk((KERN_ERR
2495 -               "%s::%s() @%d - ioc%d not found!\n",
2496 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
2497 -               goto cim_ssp_passthru_exit;
2498 -       }
2499 -
2500 -       if (!csmisas_is_this_sas_cntr(ioc)) {
2501 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
2502 -               dcsmisasprintk((KERN_ERR
2503 -                   "%s::%s()"
2504 -                   " @%d - ioc%d not SAS controller!\n",
2505 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
2506 -               goto cim_ssp_passthru_exit;
2507 -       }
2508 -
2509 -       /* Default to success.
2510 -        */
2511 -       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
2512 -
2513 -       /* Neither a phy nor a port has been selected.
2514 -        */
2515 -       if ((karg->Parameters.bPhyIdentifier == CSMI_SAS_USE_PORT_IDENTIFIER) &&
2516 -               (karg->Parameters.bPortIdentifier == CSMI_SAS_IGNORE_PORT)) {
2517 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_SELECT_PHY_OR_PORT;
2518 -               dcsmisasprintk((KERN_ERR
2519 -                   "%s::%s()"
2520 -                   " @%d - incorrect bPhyIdentifier and bPortIdentifier!\n",
2521 -                   __FILE__, __FUNCTION__, __LINE__));
2522 -               goto cim_ssp_passthru_exit;
2523 -       }
2524 -
2525 -       /* A phy has been selected. Verify that it's valid.
2526 -        */
2527 -       if (karg->Parameters.bPortIdentifier == CSMI_SAS_IGNORE_PORT) {
2528 -
2529 -               /* Is the phy in range? */
2530 -               if (karg->Parameters.bPhyIdentifier >= ioc->num_ports) {
2531 -                       dcsmisasprintk((": phyId >= ioc->num_ports (%d %d)\n",
2532 -                           karg->Parameters.bPhyIdentifier,
2533 -                           ioc->num_ports));
2534 -                       karg->IoctlHeader.ReturnCode =
2535 -                           CSMI_SAS_PHY_DOES_NOT_EXIST;
2536 -                       goto cim_ssp_passthru_exit;
2537 -               }
2538 -       }
2539 -
2540 -       if(karg->Parameters.bAdditionalCDBLength) {
2541 -       /* TODO - SCSI IO (32) Request Message support
2542 -        */
2543 -               dcsmisasprintk((": greater than 16-byte cdb is not supported!\n"));
2544 -               karg->IoctlHeader.ReturnCode =
2545 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
2546 -               goto cim_ssp_passthru_exit;
2547 -       }
2548 -
2549 -       /* we will use SAS address to resolve the scsi adddressing
2550 -        */
2551 -       memcpy(&sas_address, karg->Parameters.bDestinationSASAddress,
2552 -           sizeof(u64));
2553 -       sas_address = reverse_byte_order64(sas_address);
2554 -
2555 -       /* Search the list for the matching SAS address.
2556 -        */
2557 -       sas_info = csmisas_get_device_component_by_sas_addr(ioc, sas_address);
2558 -       if (!sas_info || sas_info->is_cached) {
2559 -               /*
2560 -                *Invalid SAS address
2561 -                */
2562 -               karg->IoctlHeader.ReturnCode =
2563 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
2564 -               dcsmisasprintk((KERN_ERR
2565 -                   "%s::%s()"
2566 -                   " @%d - couldn't find associated SASAddress=%llX!\n",
2567 -                   __FILE__, __FUNCTION__, __LINE__, sas_address));
2568 -               goto cim_ssp_passthru_exit;
2569 -       }
2570 -
2571 -       id = sas_info->fw.id;
2572 -       channel = sas_info->fw.channel;
2573 -
2574 -       if (csmisas_is_phys_disk(ioc, channel, id)) {
2575 -               id = csmisas_raid_id_to_num(ioc, channel, id);
2576 -               channel = 0;
2577 -               is_hidden_raid_component = 1;
2578 -       }
2579 -
2580 -       /* Get a free request frame and save the message context.
2581 -        */
2582 -       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
2583 -               dcsmisasprintk((": no msg frames!\n"));
2584 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2585 -               goto cim_ssp_passthru_exit;
2586 -        }
2587 -
2588 -       mpi_hdr = (MPIHeader_t *) mf;
2589 -       pScsiRequest = (pSCSIIORequest_t) mf;
2590 -       req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
2591 -
2592 -       memset(pScsiRequest,0,sizeof(SCSIIORequest_t));
2593 -
2594 -       /* Fill in SCSI IO (16) request.
2595 -        */
2596 -
2597 -       pScsiRequest->Function = (is_hidden_raid_component == 1) ?
2598 -           MPI_FUNCTION_RAID_SCSI_IO_PASSTHROUGH : MPI_FUNCTION_SCSI_IO_REQUEST;
2599 -       pScsiRequest->TargetID = id;
2600 -       pScsiRequest->Bus = channel;
2601 -       memcpy(pScsiRequest->LUN, &karg->Parameters.bLun, 8);
2602 -       pScsiRequest->CDBLength = karg->Parameters.bCDBLength;
2603 -       pScsiRequest->DataLength = cpu_to_le32(request_data_sz);
2604 -       pScsiRequest->MsgContext = mpi_hdr->MsgContext;
2605 -       memcpy(pScsiRequest->CDB, karg->Parameters.bCDB,
2606 -           pScsiRequest->CDBLength);
2607 -
2608 -       #if defined(MPT_DEBUG_CSMISAS)
2609 -       {
2610 -       int k;
2611 -               printk("\tchannel=%d id=%d ", sas_info->fw.channel,
2612 -                   sas_info->fw.id);
2613 -               if (is_hidden_raid_component)
2614 -                       printk("num_id=%d ", id);
2615 -               printk("\n");
2616 -               printk("\tcdb_len = %d data_len=%d\n",
2617 -                   pScsiRequest->CDBLength, request_data_sz);
2618 -               printk("\t");
2619 -               for (k = 0; k < pScsiRequest->CDBLength; ++k)
2620 -                       printk(" %02x", pScsiRequest->CDB[k]);
2621 -               printk("\n");
2622 -       }
2623 -       #endif
2624 -
2625 -       /* direction
2626 -        */
2627 -       if (karg->Parameters.uFlags & CSMI_SAS_SSP_READ) {
2628 -               pScsiRequest->Control = cpu_to_le32(MPI_SCSIIO_CONTROL_READ);
2629 -       } else if (karg->Parameters.uFlags & CSMI_SAS_SSP_WRITE) {
2630 -               pScsiRequest->Control = cpu_to_le32(MPI_SCSIIO_CONTROL_WRITE);
2631 -       } else if ((karg->Parameters.uFlags & CSMI_SAS_SSP_UNSPECIFIED) &&
2632 -           (!karg->Parameters.uDataLength)) {
2633 -               /* no data transfer
2634 -                */
2635 -               pScsiRequest->Control = cpu_to_le32(MPI_SCSIIO_CONTROL_NODATATRANSFER);
2636 -       } else {
2637 -               /* no direction specified
2638 -                */
2639 -               pScsiRequest->Control = cpu_to_le32(MPI_SCSIIO_CONTROL_READ);
2640 -               pScsiRequest->MsgFlags =
2641 -                   MPI_SCSIIO_MSGFLGS_CMD_DETERMINES_DATA_DIR;
2642 -       }
2643 -
2644 -       pScsiRequest->MsgFlags |= mpt_msg_flags();
2645 -       /* task attributes
2646 -        */
2647 -       if((karg->Parameters.uFlags && 0xFF) == 0) {
2648 -               pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_SIMPLEQ);
2649 -       } else if (karg->Parameters.uFlags &
2650 -           CSMI_SAS_SSP_TASK_ATTRIBUTE_HEAD_OF_QUEUE) {
2651 -               pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_HEADOFQ);
2652 -       } else if (karg->Parameters.uFlags &
2653 -           CSMI_SAS_SSP_TASK_ATTRIBUTE_ORDERED) {
2654 -               pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_ORDEREDQ);
2655 -       } else if (karg->Parameters.uFlags &
2656 -           CSMI_SAS_SSP_TASK_ATTRIBUTE_ACA) {
2657 -               pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_ACAQ);
2658 -       } else {
2659 -               pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_UNTAGGED);
2660 -       }
2661 -
2662 -       /* setup sense
2663 -        */
2664 -       pScsiRequest->SenseBufferLength = MPT_SENSE_BUFFER_SIZE;
2665 -       pScsiRequest->SenseBufferLowAddr = cpu_to_le32(ioc->sense_buf_low_dma +
2666 -           (req_idx * MPT_SENSE_BUFFER_ALLOC));
2667 -
2668 -       /* setup databuffer sg, assuming we fit everything one contiguous buffer
2669 -        */
2670 -       psge = (char *)&pScsiRequest->SGL;
2671 -
2672 -       if (karg->Parameters.uFlags & CSMI_SAS_SSP_WRITE) {
2673 -               flagsLength = MPT_SGE_FLAGS_SSIMPLE_WRITE;
2674 -       } else if (karg->Parameters.uFlags & CSMI_SAS_SSP_READ) {
2675 -               flagsLength = MPT_SGE_FLAGS_SSIMPLE_READ;
2676 -       }else {
2677 -               flagsLength = ( MPI_SGE_FLAGS_SIMPLE_ELEMENT |
2678 -                               MPI_SGE_FLAGS_DIRECTION |
2679 -                               mpt_addr_size() )
2680 -                               << MPI_SGE_FLAGS_SHIFT;
2681 -       }
2682 -       flagsLength |= request_data_sz;
2683 -
2684 -       if ( request_data_sz > 0) {
2685 -               request_data = pci_alloc_consistent(
2686 -                   ioc->pcidev, request_data_sz, &request_data_dma);
2687 -
2688 -               if (request_data == NULL) {
2689 -                       dcsmisasprintk((": pci_alloc_consistent: FAILED "
2690 -                           "request_data_sz=%d\n", request_data_sz));
2691 -                       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2692 -                       mpt_free_msg_frame(ioc, mf);
2693 -                       goto cim_ssp_passthru_exit;
2694 -               }
2695 -
2696 -               mpt_add_sge(psge, flagsLength, request_data_dma);
2697 -               if (karg->Parameters.uFlags & CSMI_SAS_SSP_WRITE)
2698 -                       memcpy(request_data, karg->bDataBuffer, request_data_sz);
2699 -       } else {
2700 -               mpt_add_sge(psge, flagsLength, (dma_addr_t) -1);
2701 -       }
2702 -
2703 -       if (csmisas_send_command_wait(ioc, mf, karg->IoctlHeader.Timeout) != 0) {
2704 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2705 -               goto cim_ssp_passthru_exit;
2706 -       }
2707 -
2708 -       memset(&karg->Status,0,sizeof(CSMI_SAS_SSP_PASSTHRU_STATUS));
2709 -       karg->Status.bConnectionStatus = CSMI_SAS_OPEN_ACCEPT;
2710 -       karg->Status.bDataPresent = CSMI_SAS_SSP_NO_DATA_PRESENT;
2711 -       karg->Status.bStatus = GOOD;
2712 -       karg->Status.bResponseLength[0] = 0;
2713 -       karg->Status.bResponseLength[1] = 0;
2714 -       karg->Status.uDataBytes = request_data_sz;
2715 -
2716 -       /* process the completed Reply Message Frame */
2717 -       if (ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) {
2718 -
2719 -               pScsiReply = (pSCSIIOReply_t ) ioc->ioctl->ReplyFrame;
2720 -               karg->Status.bStatus = pScsiReply->SCSIStatus;
2721 -               karg->Status.uDataBytes = min(le32_to_cpu(pScsiReply->TransferCount),
2722 -                   request_data_sz);
2723 -               ioc_status = le16_to_cpu(pScsiReply->IOCStatus) & MPI_IOCSTATUS_MASK;
2724 -
2725 -               if (pScsiReply->SCSIState ==
2726 -                   MPI_SCSI_STATE_AUTOSENSE_VALID) {
2727 -                       karg->Status.bConnectionStatus =
2728 -                           CSMI_SAS_SSP_SENSE_DATA_PRESENT;
2729 -                       karg->Status.bResponseLength[0] =
2730 -                               (u8)le32_to_cpu(pScsiReply->SenseCount) & 0xFF;
2731 -                       memcpy(karg->Status.bResponse,
2732 -                           ioc->ioctl->sense, le32_to_cpu(pScsiReply->SenseCount));
2733 -               } else if(pScsiReply->SCSIState ==
2734 -                   MPI_SCSI_STATE_RESPONSE_INFO_VALID) {
2735 -                       karg->Status.bDataPresent =
2736 -                           CSMI_SAS_SSP_RESPONSE_DATA_PRESENT;
2737 -                       karg->Status.bResponseLength[0] =
2738 -                               sizeof(pScsiReply->ResponseInfo);
2739 -                       for (ii=0;ii<sizeof(pScsiReply->ResponseInfo);ii++) {
2740 -                               karg->Status.bResponse[ii] =
2741 -                               ((u8*)&pScsiReply->ResponseInfo)[
2742 -                                   (sizeof(pScsiReply->ResponseInfo)-1)-ii];
2743 -                       }
2744 -               } else if ((ioc_status != MPI_IOCSTATUS_SUCCESS) &&
2745 -                   (ioc_status !=  MPI_IOCSTATUS_SCSI_RECOVERED_ERROR) &&
2746 -                   (ioc_status != MPI_IOCSTATUS_SCSI_DATA_UNDERRUN)) {
2747 -                       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2748 -                       dcsmisasprintk((": SCSI IO : "));
2749 -                       dcsmisasprintk(("IOCStatus=0x%X IOCLogInfo=0x%X\n",
2750 -                           pScsiReply->IOCStatus,
2751 -                           pScsiReply->IOCLogInfo));
2752 -               }
2753 -       }
2754 -
2755 -       if ((karg->Status.uDataBytes) && (request_data) &&
2756 -           (karg->Parameters.uFlags & CSMI_SAS_SSP_READ)) {
2757 -               if (copy_to_user((char *)uarg->bDataBuffer,
2758 -                   request_data, karg->Status.uDataBytes)) {
2759 -                       printk(KERN_ERR "%s@%d::%s - "
2760 -                           "Unable to write data to user %p\n",
2761 -                           __FILE__, __LINE__,__FUNCTION__,
2762 -                           (void*)karg->bDataBuffer);
2763 -                       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2764 -               }
2765 -       }
2766 -
2767 - cim_ssp_passthru_exit:
2768 -
2769 -
2770 -       if (request_data)
2771 -               pci_free_consistent(ioc->pcidev, request_data_sz,
2772 -                   (u8 *)request_data, request_data_dma);
2773 -
2774 -       /* Copy the data from kernel memory to user memory
2775 -        */
2776 -       if (copy_to_user((char *)arg, karg,
2777 -           offsetof(CSMI_SAS_SSP_PASSTHRU_BUFFER, bDataBuffer))) {
2778 -               printk(KERN_ERR "%s@%d::%s() - "
2779 -                       "Unable to write out csmi_sas_ssp_passthru @ %p\n",
2780 -                               __FILE__, __LINE__, __FUNCTION__, uarg);
2781 -               free_pages((unsigned long)karg, memory_pages);
2782 -               return -EFAULT;
2783 -       }
2784 -
2785 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
2786 -       free_pages((unsigned long)karg, memory_pages);
2787 -       return 0;
2788 -}
2789 -
2790 -/**
2791 - * Prototype Routine for the CSMI SAS STP Passthru command.
2792 - *
2793 - * Outputs:    None.
2794 - * Return:     0 if successful
2795 - *             -EFAULT if data unavailable
2796 - *             -ENODEV if no such device/adapter
2797 - **/
2798 -static int
2799 -csmisas_stp_passthru(unsigned long arg)
2800 -{
2801 -       CSMI_SAS_STP_PASSTHRU_BUFFER __user *uarg = (void __user *) arg;
2802 -       CSMI_SAS_STP_PASSTHRU_BUFFER     karg;
2803 -       MPT_ADAPTER                     *ioc = NULL;
2804 -       pSataPassthroughRequest_t       pSataRequest;
2805 -       pSataPassthroughReply_t         pSataReply;
2806 -       MPT_FRAME_HDR                   *mf = NULL;
2807 -       MPIHeader_t                     *mpi_hdr;
2808 -       int                             iocnum;
2809 -       u32                             data_sz;
2810 -       u64                             sas_address;
2811 -       u16                             req_idx;
2812 -       char                            *psge;
2813 -       int                             flagsLength;
2814 -       void *                          request_data;
2815 -       dma_addr_t                      request_data_dma;
2816 -       u32                             request_data_sz;
2817 -       u8                              channel;
2818 -       u8                              id;
2819 -       u8                              volume_id;
2820 -       u8                              volume_bus;
2821 -       struct sas_device_info          *sas_info;
2822 -       u16                             ioc_status;
2823 -
2824 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
2825 -
2826 -       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_STP_PASSTHRU_BUFFER))) {
2827 -               printk(KERN_ERR "%s@%d::%s() - "
2828 -                   "Unable to read struct @ %p\n",
2829 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
2830 -               return -EFAULT;
2831 -       }
2832 -
2833 -       request_data=NULL;
2834 -       request_data_sz = karg.Parameters.uDataLength;
2835 -       volume_id = 0;
2836 -       volume_bus = 0;
2837 -       channel = 0;
2838 -       id = 0;
2839 -
2840 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
2841 -           &ioc)) < 0) || (ioc == NULL)) {
2842 -               dcsmisasprintk((KERN_ERR
2843 -               "%s::%s @%d - ioc%d not found!\n",
2844 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
2845 -               return -ENODEV;
2846 -       }
2847 -
2848 -       if (!csmisas_is_this_sas_cntr(ioc)) {
2849 -               dcsmisasprintk((KERN_ERR
2850 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
2851 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
2852 -               return -ENODEV;
2853 -       }
2854 -
2855 -       /* Default to success.
2856 -        */
2857 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
2858 -
2859 -       /* Neither a phy nor a port has been selected.
2860 -        */
2861 -       if ((karg.Parameters.bPhyIdentifier == CSMI_SAS_USE_PORT_IDENTIFIER) &&
2862 -               (karg.Parameters.bPortIdentifier == CSMI_SAS_IGNORE_PORT)) {
2863 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_SELECT_PHY_OR_PORT;
2864 -               dcsmisasprintk((KERN_ERR
2865 -                   "%s::%s() @%d - incorrect bPhyIdentifier and bPortIdentifier!\n",
2866 -                   __FILE__,__FUNCTION__, __LINE__));
2867 -               goto cim_stp_passthru_exit;
2868 -       }
2869 -
2870 -       /* A phy has been selected. Verify that it's valid.
2871 -        */
2872 -       if (karg.Parameters.bPortIdentifier == CSMI_SAS_IGNORE_PORT) {
2873 -
2874 -               /* Is the phy in range? */
2875 -               if (karg.Parameters.bPhyIdentifier >= ioc->num_ports) {
2876 -                       karg.IoctlHeader.ReturnCode =
2877 -                           CSMI_SAS_PHY_DOES_NOT_EXIST;
2878 -                       goto cim_stp_passthru_exit;
2879 -               }
2880 -       }
2881 -
2882 -       /* some checks of the incoming frame
2883 -        */
2884 -       if (request_data_sz > 0xFFFF) {
2885 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2886 -               dcsmisasprintk((KERN_ERR
2887 -                   "%s::%s() @%d - uDataLength > 0xFFFF!\n",
2888 -                   __FILE__, __FUNCTION__, __LINE__));
2889 -               goto cim_stp_passthru_exit;
2890 -       }
2891 -
2892 -       data_sz = sizeof(CSMI_SAS_STP_PASSTHRU_BUFFER) -
2893 -           sizeof(IOCTL_HEADER) - sizeof(u8*) +
2894 -           request_data_sz;
2895 -
2896 -       if ( data_sz > karg.IoctlHeader.Length ) {
2897 -               karg.IoctlHeader.ReturnCode =
2898 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
2899 -               dcsmisasprintk((KERN_ERR
2900 -                   "%s::%s() @%d - expected datalen incorrect!\n",
2901 -                   __FILE__, __FUNCTION__,__LINE__));
2902 -               goto cim_stp_passthru_exit;
2903 -       }
2904 -
2905 -
2906 -       /* we will use SAS address to resolve the scsi adddressing
2907 -        */
2908 -       memcpy(&sas_address, karg.Parameters.bDestinationSASAddress,
2909 -           sizeof(u64));
2910 -       sas_address = reverse_byte_order64(sas_address);
2911 -
2912 -       /* Search the list for the matching SAS address.
2913 -        */
2914 -       sas_info = csmisas_get_device_component_by_sas_addr(ioc, sas_address);
2915 -       if (!sas_info || sas_info->is_cached || sas_info->is_logical_volume) {
2916 -               /*
2917 -                *Invalid SAS address
2918 -                */
2919 -               karg.IoctlHeader.ReturnCode =
2920 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
2921 -               dcsmisasprintk((KERN_ERR
2922 -                   "%s::%s()"
2923 -                   " @%d - couldn't find associated SASAddress=%llX!\n",
2924 -                   __FILE__, __FUNCTION__, __LINE__, sas_address));
2925 -               goto cim_stp_passthru_exit;
2926 -       }
2927 -
2928 -       id = sas_info->fw.id;
2929 -       channel = sas_info->fw.channel;
2930 -
2931 -       /* check that this is an STP or SATA target device
2932 -        */
2933 -       if ( !(sas_info->device_info & MPI_SAS_DEVICE_INFO_STP_TARGET ) &&
2934 -            !(sas_info->device_info & MPI_SAS_DEVICE_INFO_SATA_DEVICE )) {
2935 -               karg.IoctlHeader.ReturnCode =
2936 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
2937 -               goto cim_stp_passthru_exit;
2938 -       }
2939 -
2940 -       /* Get a free request frame and save the message context.
2941 -        */
2942 -       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
2943 -               dcsmisasprintk((": no msg frames!\n"));
2944 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2945 -               goto cim_stp_passthru_exit;
2946 -        }
2947 -
2948 -       mpi_hdr = (MPIHeader_t *) mf;
2949 -       pSataRequest = (pSataPassthroughRequest_t) mf;
2950 -       req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
2951 -
2952 -       memset(pSataRequest,0,sizeof(pSataPassthroughRequest_t));
2953 -
2954 -       pSataRequest->TargetID = id;
2955 -       pSataRequest->Bus = channel;
2956 -       pSataRequest->Function = MPI_FUNCTION_SATA_PASSTHROUGH;
2957 -       pSataRequest->PassthroughFlags = cpu_to_le16(karg.Parameters.uFlags);
2958 -       pSataRequest->ConnectionRate = karg.Parameters.bConnectionRate;
2959 -       pSataRequest->MsgContext = mpi_hdr->MsgContext;
2960 -       pSataRequest->DataLength = cpu_to_le32(request_data_sz);
2961 -       pSataRequest->MsgFlags = 0;
2962 -       memcpy( pSataRequest->CommandFIS,karg.Parameters.bCommandFIS, 20);
2963 -
2964 -       psge = (char *)&pSataRequest->SGL;
2965 -       if (karg.Parameters.uFlags & CSMI_SAS_STP_WRITE) {
2966 -               flagsLength = MPT_SGE_FLAGS_SSIMPLE_WRITE;
2967 -       } else if (karg.Parameters.uFlags & CSMI_SAS_STP_READ) {
2968 -               flagsLength = MPT_SGE_FLAGS_SSIMPLE_READ;
2969 -       }else {
2970 -               flagsLength = ( MPI_SGE_FLAGS_SIMPLE_ELEMENT |
2971 -                               MPI_SGE_FLAGS_DIRECTION |
2972 -                               mpt_addr_size() )
2973 -                               << MPI_SGE_FLAGS_SHIFT;
2974 -       }
2975 -
2976 -       flagsLength |= request_data_sz;
2977 -       if (request_data_sz > 0) {
2978 -               request_data = pci_alloc_consistent(
2979 -                   ioc->pcidev, request_data_sz, &request_data_dma);
2980 -
2981 -               if (request_data == NULL) {
2982 -                       dcsmisasprintk((": pci_alloc_consistent: FAILED\n"));
2983 -                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2984 -                       mpt_free_msg_frame(ioc, mf);
2985 -                       goto cim_stp_passthru_exit;
2986 -               }
2987 -
2988 -               mpt_add_sge(psge, flagsLength, request_data_dma);
2989 -               if (karg.Parameters.uFlags & CSMI_SAS_STP_WRITE) {
2990 -                       if (copy_from_user(request_data,
2991 -                           karg.bDataBuffer,
2992 -                           request_data_sz)) {
2993 -                               printk(KERN_ERR
2994 -                                   "%s::%s() @%d - Unable to read user data "
2995 -                                   "struct @ %p\n",
2996 -                                   __FILE__, __FUNCTION__, __LINE__,
2997 -                                   (void*)karg.bDataBuffer);
2998 -                               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
2999 -                               mpt_free_msg_frame(ioc, mf);
3000 -                               goto cim_stp_passthru_exit;
3001 -                       }
3002 -               }
3003 -       } else {
3004 -               mpt_add_sge(psge, flagsLength, (dma_addr_t) -1);
3005 -       }
3006 -
3007 -       if (csmisas_send_command_wait(ioc, mf, karg.IoctlHeader.Timeout) != 0) {
3008 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3009 -               goto cim_stp_passthru_exit;
3010 -       }
3011 -
3012 -       memset(&karg.Status,0,sizeof(CSMI_SAS_STP_PASSTHRU_STATUS));
3013 -
3014 -       if ((ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) == 0) {
3015 -               dcsmisasprintk((": STP Passthru: oh no, there is no reply!!"));
3016 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3017 -               goto cim_stp_passthru_exit;
3018 -       }
3019 -
3020 -       /* process the completed Reply Message Frame */
3021 -       pSataReply = (pSataPassthroughReply_t ) ioc->ioctl->ReplyFrame;
3022 -       ioc_status = le16_to_cpu(pSataReply->IOCStatus) & MPI_IOCSTATUS_MASK;
3023 -
3024 -       if (ioc_status != MPI_IOCSTATUS_SUCCESS &&
3025 -           ioc_status != MPI_IOCSTATUS_SCSI_DATA_UNDERRUN) {
3026 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3027 -               dcsmisasprintk((": STP Passthru: "));
3028 -               dcsmisasprintk(("IOCStatus=0x%X IOCLogInfo=0x%X SASStatus=0x%X\n",
3029 -                   le16_to_cpu(pSataReply->IOCStatus),
3030 -                   le32_to_cpu(pSataReply->IOCLogInfo),
3031 -                   pSataReply->SASStatus));
3032 -       }
3033 -
3034 -       karg.Status.bConnectionStatus =
3035 -           map_sas_status_to_csmi(pSataReply->SASStatus);
3036 -
3037 -       memcpy(karg.Status.bStatusFIS,pSataReply->StatusFIS, 20);
3038 -
3039 -       /*
3040 -        * for now, just zero out uSCR array,
3041 -        * then copy the one dword returned
3042 -        * in the reply frame into uSCR[0]
3043 -        */
3044 -       memset( karg.Status.uSCR, 0, 64);
3045 -       karg.Status.uSCR[0] = le32_to_cpu(pSataReply->StatusControlRegisters);
3046 -
3047 -       if((le32_to_cpu(pSataReply->TransferCount)) && (request_data) &&
3048 -           (karg.Parameters.uFlags & CSMI_SAS_STP_READ)) {
3049 -               karg.Status.uDataBytes =
3050 -                   min(le32_to_cpu(pSataReply->TransferCount),request_data_sz);
3051 -               if (copy_to_user((char *)uarg->bDataBuffer,
3052 -                   request_data, karg.Status.uDataBytes)) {
3053 -                       printk(KERN_ERR "%s::%s() @%d - "
3054 -                           "Unable to write data to user %p\n",
3055 -                           __FILE__, __FUNCTION__, __LINE__,
3056 -                           (void*)karg.bDataBuffer);
3057 -                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3058 -               }
3059 -       }
3060 -
3061 - cim_stp_passthru_exit:
3062 -
3063 -       if (request_data)
3064 -               pci_free_consistent(ioc->pcidev, request_data_sz,
3065 -                   (u8 *)request_data, request_data_dma);
3066 -
3067 -       /* Copy th data from kernel memory to user memory
3068 -        */
3069 -       if (copy_to_user((char *)arg, &karg,
3070 -           offsetof(CSMI_SAS_STP_PASSTHRU_BUFFER,bDataBuffer))) {
3071 -               printk(KERN_ERR "%s@%d::%s() - "
3072 -                       "Unable to write out csmi_sas_ssp_passthru @ %p\n",
3073 -                               __FILE__, __LINE__, __FUNCTION__, uarg);
3074 -               return -EFAULT;
3075 -       }
3076 -
3077 -       dcsmisasprintk((": %s exit.\n",__FUNCTION__));
3078 -       return 0;
3079 -}
3080 -
3081 -/**
3082 - * Prototype Routine for the CSMI SAS Firmware Download command.
3083 - *
3084 - * Outputs:    None.
3085 - * Return:     0 if successful
3086 - *             -EFAULT if data unavailable
3087 - *             -ENODEV if no such device/adapter
3088 - **/
3089 -static int
3090 -csmisas_firmware_download(unsigned long arg)
3091 -{
3092 -       CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER __user *uarg = (void __user *) arg;
3093 -       CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER        karg;
3094 -       MPT_ADAPTER                     *ioc = NULL;
3095 -       int                             iocnum;
3096 -       pMpiFwHeader_t                  pFwHeader=NULL;
3097 -
3098 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
3099 -
3100 -       if (copy_from_user(&karg, uarg,
3101 -               sizeof(CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER))) {
3102 -               printk(KERN_ERR "%s@%d::%s() - "
3103 -                   "Unable to read in csmi_sas_firmware_download struct @ %p\n",
3104 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
3105 -               return -EFAULT;
3106 -       }
3107 -
3108 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
3109 -           &ioc)) < 0) || (ioc == NULL)) {
3110 -               dcsmisasprintk((KERN_ERR
3111 -               "%s::%s() @%d - ioc%d not found!\n",
3112 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
3113 -               return -ENODEV;
3114 -       }
3115 -
3116 -       if (!csmisas_is_this_sas_cntr(ioc)) {
3117 -               dcsmisasprintk((KERN_ERR
3118 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
3119 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
3120 -               return -ENODEV;
3121 -       }
3122 -
3123 -       /* Default to success.*/
3124 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
3125 -       karg.Information.usStatus = CSMI_SAS_FWD_SUCCESS;
3126 -       karg.Information.usSeverity = CSMI_SAS_FWD_INFORMATION;
3127 -
3128 -       /* some checks of the incoming frame */
3129 -       if ((karg.Information.uBufferLength +
3130 -           sizeof(CSMI_SAS_FIRMWARE_DOWNLOAD)) >
3131 -           karg.IoctlHeader.Length) {
3132 -               karg.IoctlHeader.ReturnCode =
3133 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
3134 -               karg.Information.usStatus = CSMI_SAS_FWD_FAILED;
3135 -               goto cim_firmware_download_exit;
3136 -       }
3137 -
3138 -       if ( karg.Information.uDownloadFlags &
3139 -           (CSMI_SAS_FWD_SOFT_RESET | CSMI_SAS_FWD_VALIDATE)) {
3140 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3141 -               karg.Information.usStatus = CSMI_SAS_FWD_REJECT;
3142 -               karg.Information.usSeverity = CSMI_SAS_FWD_ERROR;
3143 -               goto cim_firmware_download_exit;
3144 -       }
3145 -
3146 -       /* now we need to alloc memory so we can pull in the
3147 -        * fw image attached to end of incoming packet.
3148 -        */
3149 -       pFwHeader = kmalloc(karg.Information.uBufferLength, GFP_KERNEL);
3150 -       if (!pFwHeader){
3151 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3152 -               karg.Information.usStatus = CSMI_SAS_FWD_REJECT;
3153 -               karg.Information.usSeverity = CSMI_SAS_FWD_ERROR;
3154 -               goto cim_firmware_download_exit;
3155 -       }
3156 -       memset(pFwHeader, 0, sizeof(*pFwHeader));
3157 -
3158 -       if (copy_from_user(pFwHeader, uarg->bDataBuffer,
3159 -               karg.Information.uBufferLength)) {
3160 -               printk(KERN_ERR "%s@%d::%s() - "
3161 -                   "Unable to read in pFwHeader @ %p\n",
3162 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
3163 -               return -EFAULT;
3164 -       }
3165 -
3166 -       if ( !((pFwHeader->Signature0 == MPI_FW_HEADER_SIGNATURE_0) &&
3167 -           (pFwHeader->Signature1 == MPI_FW_HEADER_SIGNATURE_1) &&
3168 -           (pFwHeader->Signature2 == MPI_FW_HEADER_SIGNATURE_2))) {
3169 -               // the signature check failed
3170 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3171 -               karg.Information.usStatus = CSMI_SAS_FWD_REJECT;
3172 -               karg.Information.usSeverity = CSMI_SAS_FWD_ERROR;
3173 -               goto cim_firmware_download_exit;
3174 -       }
3175 -
3176 -       if ( mptctl_do_fw_download(karg.IoctlHeader.IOControllerNumber,
3177 -           uarg->bDataBuffer, karg.Information.uBufferLength)
3178 -           != 0) {
3179 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3180 -               karg.Information.usStatus = CSMI_SAS_FWD_FAILED;
3181 -               karg.Information.usSeverity = CSMI_SAS_FWD_FATAL;
3182 -               goto cim_firmware_download_exit;
3183 -       }
3184 -
3185 -       if((karg.Information.uDownloadFlags & CSMI_SAS_FWD_SOFT_RESET) ||
3186 -           (karg.Information.uDownloadFlags & CSMI_SAS_FWD_HARD_RESET)) {
3187 -               if (mpt_HardResetHandler(ioc, CAN_SLEEP) != 0) {
3188 -                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3189 -                       karg.Information.usStatus = CSMI_SAS_FWD_FAILED;
3190 -                       karg.Information.usSeverity = CSMI_SAS_FWD_FATAL;
3191 -               }
3192 -       }
3193 -
3194 - cim_firmware_download_exit:
3195 -
3196 -       if(pFwHeader)
3197 -               kfree(pFwHeader);
3198 -
3199 -       /* Copy the data from kernel memory to user memory
3200 -        */
3201 -       if (copy_to_user((char *)arg, &karg,
3202 -                               sizeof(CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER))) {
3203 -               printk(KERN_ERR "%s@%d::%s() - "
3204 -                       "Unable to write out csmi_sas_firmware_download @ %p\n",
3205 -                               __FILE__, __LINE__, __FUNCTION__, uarg);
3206 -               return -EFAULT;
3207 -       }
3208 -
3209 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
3210 -       return 0;
3211 -}
3212 -
3213 -/**
3214 - * Prototype Routine for the CSMI SAS Get RAID Info command.
3215 - *
3216 - * Outputs:    None.
3217 - * Return:     0 if successful
3218 - *             -EFAULT if data unavailable
3219 - *             -ENODEV if no such device/adapter
3220 - **/
3221 -static int
3222 -csmisas_get_raid_info(unsigned long arg)
3223 -{
3224 -       CSMI_SAS_RAID_INFO_BUFFER __user *uarg =  (void __user *) arg;
3225 -       CSMI_SAS_RAID_INFO_BUFFER        karg;
3226 -       MPT_ADAPTER                     *ioc = NULL;
3227 -       int                             iocnum;
3228 -       u32                             raidFlags;
3229 -       u8                              maxRaidTypes;
3230 -       u8                              maxDrivesPerSet;
3231 -
3232 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
3233 -
3234 -       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_RAID_INFO_BUFFER))) {
3235 -               printk(KERN_ERR "%s@%d::%s() - "
3236 -                   "Unable to read in csmi_sas_get_raid_info struct @ %p\n",
3237 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
3238 -               return -EFAULT;
3239 -       }
3240 -
3241 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
3242 -           &ioc)) < 0) || (ioc == NULL)) {
3243 -               dcsmisasprintk((KERN_ERR
3244 -               "%s::%s() @%d - ioc%d not found!\n",
3245 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
3246 -               return -ENODEV;
3247 -       }
3248 -
3249 -       if (!csmisas_is_this_sas_cntr(ioc)) {
3250 -               dcsmisasprintk((KERN_ERR
3251 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
3252 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
3253 -               return -ENODEV;
3254 -       }
3255 -
3256 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3257 -       if (!ioc->raid_data.pIocPg2)
3258 -               goto csmisas_get_raid_info_out;
3259 -       karg.Information.uNumRaidSets =
3260 -           ioc->raid_data.pIocPg2->NumActiveVolumes;
3261 -       karg.Information.uMaxRaidSets = ioc->raid_data.pIocPg2->MaxVolumes;
3262 -       if( ioc->raid_data.pIocPg6 ) {
3263 -               // get absolute maximum for all RAID sets
3264 -               maxDrivesPerSet = ioc->raid_data.pIocPg6->MaxDrivesIS;
3265 -               maxDrivesPerSet = max(ioc->raid_data.pIocPg6->MaxDrivesIM,
3266 -                   maxDrivesPerSet);
3267 -               maxDrivesPerSet = max(ioc->raid_data.pIocPg6->MaxDrivesIME,
3268 -                   maxDrivesPerSet);
3269 -               karg.Information.uMaxDrivesPerSet = maxDrivesPerSet;
3270 -       }
3271 -       else
3272 -               karg.Information.uMaxDrivesPerSet = 8;
3273 -       // For bMaxRaidSets, count bits set in bits 0-6 of CapabilitiesFlags
3274 -       raidFlags = ioc->raid_data.pIocPg2->CapabilitiesFlags & 0x0000007F;
3275 -       for( maxRaidTypes=0; raidFlags; maxRaidTypes++ )
3276 -               raidFlags &= raidFlags - 1;
3277 -       karg.Information.bMaxRaidTypes = maxRaidTypes;
3278 -       // ulMinRaidSetBlocks hard coded to 1MB until available from config page
3279 -       karg.Information.ulMinRaidSetBlocks.uLowPart = 2048;
3280 -       karg.Information.ulMinRaidSetBlocks.uHighPart = 0;
3281 -       karg.Information.ulMaxRaidSetBlocks.uLowPart = 0xffffffff;
3282 -       if( ioc->raid_data.pIocPg2->CapabilitiesFlags &
3283 -           MPI_IOCPAGE2_CAP_FLAGS_RAID_64_BIT_ADDRESSING )
3284 -               karg.Information.ulMaxRaidSetBlocks.uHighPart = 0xffffffff;
3285 -       else
3286 -               karg.Information.ulMaxRaidSetBlocks.uHighPart = 0;
3287 -       karg.Information.uMaxPhysicalDrives =
3288 -           ioc->raid_data.pIocPg2->MaxPhysDisks;
3289 -       karg.Information.uMaxExtents = 1;
3290 -       karg.Information.uMaxModules = 0;
3291 -       karg.Information.uMaxTransformationMemory = 0;
3292 -       karg.Information.uChangeCount = ioc->csmi_change_count;
3293 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
3294 -
3295 -csmisas_get_raid_info_out:
3296 -
3297 -       /* Copy the data from kernel memory to user memory
3298 -        */
3299 -       if (copy_to_user((char *)arg, &karg,
3300 -                               sizeof(CSMI_SAS_RAID_INFO_BUFFER))) {
3301 -               printk(KERN_ERR "%s@%d::%s() - "
3302 -                       "Unable to write out csmi_sas_get_raid_info @ %p\n",
3303 -                               __FILE__, __LINE__, __FUNCTION__, uarg);
3304 -               return -EFAULT;
3305 -       }
3306 -
3307 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
3308 -       return 0;
3309 -}
3310 -
3311 -/**
3312 - *     csmisas_do_raid - Format and Issue a RAID volume request message.
3313 - *     @ioc: Pointer to MPT_ADAPTER structure
3314 - *     @action: What do be done.
3315 - *     @PhysDiskNum: Logical target id.
3316 - *     @VolumeBus: Target locations bus.
3317 - *     @VolumeId: Volume id
3318 - *
3319 - *     Returns: < 0 on a fatal error
3320 - *             0 on success
3321 - *
3322 - *     Remark: Wait to return until reply processed by the ISR.
3323 - **/
3324 -static int
3325 -csmisas_do_raid(MPT_ADAPTER *ioc, u8 action, u8 PhysDiskNum, u8 VolumeBus, u8 VolumeId, pMpiRaidActionReply_t reply)
3326 -{
3327 -       MpiRaidActionRequest_t  *pReq;
3328 -       MpiRaidActionReply_t    *pReply;
3329 -       MPT_FRAME_HDR           *mf;
3330 -
3331 -       /* Get and Populate a free Frame
3332 -        */
3333 -       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
3334 -               dcsmisasprintk((": no msg frames!\n"));
3335 -               return -EAGAIN;
3336 -       }
3337 -       pReq = (MpiRaidActionRequest_t *)mf;
3338 -       pReq->Action = action;
3339 -       pReq->Reserved1 = 0;
3340 -       pReq->ChainOffset = 0;
3341 -       pReq->Function = MPI_FUNCTION_RAID_ACTION;
3342 -       pReq->VolumeID = VolumeId;
3343 -       pReq->VolumeBus = VolumeBus;
3344 -       pReq->PhysDiskNum = PhysDiskNum;
3345 -       pReq->MsgFlags = 0;
3346 -       pReq->Reserved2 = 0;
3347 -       pReq->ActionDataWord = 0; /* Reserved for this action */
3348 -       //pReq->ActionDataSGE = 0;
3349 -
3350 -       mpt_add_sge((char *)&pReq->ActionDataSGE,
3351 -               MPT_SGE_FLAGS_SSIMPLE_READ | 0, (dma_addr_t) -1);
3352 -
3353 -       if (csmisas_send_command_wait(ioc, mf, MPT_IOCTL_DEFAULT_TIMEOUT) != 0)
3354 -               return -ENODATA;
3355 -
3356 -       if ((ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) &&
3357 -           (reply != NULL)){
3358 -               pReply = (MpiRaidActionReply_t *)&(ioc->ioctl->ReplyFrame);
3359 -               memcpy(reply, pReply,
3360 -                       min(ioc->reply_sz,
3361 -                       4*pReply->MsgLength));
3362 -       }
3363 -
3364 -       return 0;
3365 -}
3366 -
3367 -/**
3368 - * csmisas_raid_inq
3369 - * @ioc = per host instance
3370 - * @opcode = MPI_FUNCTION_RAID_SCSI_IO_PASSTHROUGH or
3371 - *          MPI_FUNCTION_SCSI_IO_REQUEST
3372 - * @id = target id
3373 - * @bus = target bus
3374 - * @inq_vpd = inquiry data, returned
3375 - * @inq_vpd_sz = maximum size of inquiry data
3376 - *
3377 - * Return = 0(sucess), non-zero(failure)
3378 - **/
3379 -static int
3380 -csmisas_raid_inq(MPT_ADAPTER *ioc, u8 opcode, u8 bus, u8 id, u8 inq_vpd_page,
3381 -    u8 * inq_vpd, u32 inq_vpd_sz)
3382 -{
3383 -       MPT_FRAME_HDR           *mf = NULL;
3384 -       MPIHeader_t             *mpi_hdr;
3385 -       pSCSIIORequest_t        pScsiRequest;
3386 -       u16                     req_idx;
3387 -       char                    *psge;
3388 -       u8                      inq_vpd_cdb[6];
3389 -       u8                      *request_data=NULL;
3390 -       dma_addr_t              request_data_dma;
3391 -       u32                     request_data_sz;
3392 -       int                     rc = 0;
3393 -
3394 -       request_data_sz = inq_vpd_sz;
3395 -
3396 -       /* fill-in cdb */
3397 -       memset(inq_vpd_cdb, 0, sizeof(inq_vpd_cdb));
3398 -       inq_vpd_cdb[0] = 0x12;
3399 -       if (inq_vpd_page) {
3400 -               inq_vpd_cdb[1] = 0x01; /* evpd bit */
3401 -               inq_vpd_cdb[2] = inq_vpd_page;
3402 -       }
3403 -       inq_vpd_cdb[3] = (u8)(request_data_sz >> 8);
3404 -       inq_vpd_cdb[4] = (u8)request_data_sz;
3405 -
3406 -       /* Get a free request frame and save the message context.
3407 -        */
3408 -       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
3409 -               dcsmisasprintk((": no msg frames!\n"));
3410 -               goto csmisas_raid_inq_exit;
3411 -       }
3412 -
3413 -       mpi_hdr = (MPIHeader_t *) mf;
3414 -       pScsiRequest = (pSCSIIORequest_t) mf;
3415 -       req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
3416 -
3417 -       memset(pScsiRequest,0,sizeof(SCSIIORequest_t));
3418 -       pScsiRequest->Function = opcode;
3419 -       pScsiRequest->TargetID = id;
3420 -       pScsiRequest->Bus = bus;
3421 -       pScsiRequest->CDBLength = 6;
3422 -       pScsiRequest->DataLength = cpu_to_le32(request_data_sz);
3423 -       pScsiRequest->MsgContext = mpi_hdr->MsgContext;
3424 -       memcpy(pScsiRequest->CDB,inq_vpd_cdb,pScsiRequest->CDBLength);
3425 -       pScsiRequest->Control = cpu_to_le32(MPI_SCSIIO_CONTROL_READ);
3426 -       pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_SIMPLEQ);
3427 -       pScsiRequest->MsgFlags = mpt_msg_flags();
3428 -
3429 -       /* setup sense
3430 -        */
3431 -       pScsiRequest->SenseBufferLength = MPT_SENSE_BUFFER_SIZE;
3432 -       pScsiRequest->SenseBufferLowAddr = cpu_to_le32(ioc->sense_buf_low_dma +
3433 -           (req_idx * MPT_SENSE_BUFFER_ALLOC));
3434 -
3435 -       request_data = pci_alloc_consistent(
3436 -           ioc->pcidev, request_data_sz, &request_data_dma);
3437 -
3438 -       if (request_data == NULL) {
3439 -               mpt_free_msg_frame(ioc, mf);
3440 -               rc=-1;
3441 -               goto csmisas_raid_inq_exit;
3442 -       }
3443 -
3444 -       memset(request_data,0,request_data_sz);
3445 -       psge = (char *)&pScsiRequest->SGL;
3446 -       mpt_add_sge(psge, (MPT_SGE_FLAGS_SSIMPLE_READ | 0xFC) ,
3447 -           request_data_dma);
3448 -
3449 -       if (csmisas_send_command_wait(ioc, mf, MPT_IOCTL_DEFAULT_TIMEOUT) != 0) {
3450 -               rc=-1;
3451 -               goto csmisas_raid_inq_exit;
3452 -       }
3453 -
3454 -       /* copy the request_data */
3455 -       memcpy(inq_vpd, request_data, request_data_sz);
3456 -
3457 - csmisas_raid_inq_exit:
3458 -
3459 -       if (request_data)
3460 -               pci_free_consistent(ioc->pcidev, request_data_sz,
3461 -                   request_data, request_data_dma);
3462 -
3463 -       return rc;
3464 -}
3465 -
3466 -/**
3467 - * Prototype Routine for the CSMI SAS Get RAID Config command.
3468 - *
3469 - * Outputs:    None.
3470 - * Return:     0 if successful
3471 - *             -EFAULT if data unavailable
3472 - *             -ENODEV if no such device/adapter
3473 - **/
3474 -static int
3475 -csmisas_get_raid_config(unsigned long arg)
3476 -{
3477 -       CSMI_SAS_RAID_CONFIG_BUFFER __user *uarg = (void __user *) arg;
3478 -       CSMI_SAS_RAID_CONFIG_BUFFER      karg,*pKarg=NULL;
3479 -       CONFIGPARMS                     cfg;
3480 -       ConfigPageHeader_t              header;
3481 -       MPT_ADAPTER                     *ioc = NULL;
3482 -       int                             iocnum;
3483 -       u8                              volumeID, VolumeBus;
3484 -       u8                              physDiskNum, physDiskNumMax;
3485 -       int                             volumepage0sz = 0;
3486 -       int                             physdiskpage0sz = 0, ioc_page5_sz = 0;
3487 -       dma_addr_t                      volume0_dma, physdisk0_dma;
3488 -       dma_addr_t                      ioc_page5_dma = 0;
3489 -       pRaidVolumePage0_t              pVolume0 = NULL;
3490 -       pRaidPhysDiskPage0_t            pPhysDisk0 = NULL;
3491 -       pMpiRaidActionReply_t           pRaidActionReply = NULL;
3492 -       u32                             device_info = 0;
3493 -       pIOCPage5_t                     pIocPage5 = NULL;
3494 -       int                             i, idx, csmi_sas_raid_config_buffer_sz;
3495 -       int                             memory_pages;
3496 -       int                             copy_buffer_sz = 0;
3497 -       u64                             totalMaxLBA, tmpTotalMaxLBA;
3498 -       u64                             sas_address;
3499 -       struct sas_device_info          *sas_info;
3500 -
3501 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
3502 -
3503 -       if (copy_from_user(&karg, uarg, sizeof(IOCTL_HEADER))) {
3504 -               printk(KERN_ERR "%s@%d::%s() - "
3505 -                   "Unable to read in csmisas_get_raid_config struct @ %p\n",
3506 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
3507 -               return -EFAULT;
3508 -       }
3509 -
3510 -       csmi_sas_raid_config_buffer_sz = karg.IoctlHeader.Length;
3511 -       memory_pages = get_order(csmi_sas_raid_config_buffer_sz);
3512 -       pKarg = (CSMI_SAS_RAID_CONFIG_BUFFER *)__get_free_pages(
3513 -               GFP_KERNEL, memory_pages);
3514 -       if (!pKarg){
3515 -               printk(KERN_ERR "%s@%d::%s() - "
3516 -                   "Unable to malloc RAID_CONFIG_BUFFER "
3517 -                       "csmi_sas_raid_config_buffer_sz=%d memory_pages=%d\n",
3518 -                       __FILE__, __LINE__, __FUNCTION__,
3519 -                       csmi_sas_raid_config_buffer_sz, memory_pages);
3520 -               return -ENOMEM;
3521 -       }
3522 -       memset(pKarg, 0, sizeof(*pKarg));
3523 -
3524 -       if (copy_from_user(pKarg, uarg, csmi_sas_raid_config_buffer_sz)) {
3525 -               printk(KERN_ERR "%s@%d::%s() - "
3526 -                   "Unable to read in csmisas_get_raid_config struct @ %p\n",
3527 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
3528 -               free_pages((unsigned long)pKarg, memory_pages);
3529 -               return -EFAULT;
3530 -       }
3531 -
3532 -       if (((iocnum = mpt_verify_adapter(pKarg->IoctlHeader.IOControllerNumber,
3533 -           &ioc)) < 0) || (ioc == NULL)) {
3534 -               dcsmisasprintk((KERN_ERR
3535 -               "%s::%s() @%d - ioc%d not found!\n",
3536 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
3537 -               free_pages((unsigned long)pKarg, memory_pages);
3538 -               return -ENODEV;
3539 -       }
3540 -
3541 -       if (!csmisas_is_this_sas_cntr(ioc)) {
3542 -               dcsmisasprintk((KERN_ERR
3543 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
3544 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
3545 -               free_pages((unsigned long)pKarg, memory_pages);
3546 -               return -ENODEV;
3547 -       }
3548 -
3549 -       if (pKarg->Configuration.uChangeCount != 0 &&
3550 -               pKarg->Configuration.uChangeCount != ioc->csmi_change_count ) {
3551 -               pKarg->IoctlHeader.ReturnCode =
3552 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
3553 -               pKarg->Configuration.uFailureCode =
3554 -                   CSMI_SAS_FAIL_CODE_CHANGE_COUNT_INVALID;
3555 -               goto cim_get_raid_config_exit;
3556 -       }
3557 -
3558 -       if (!ioc->raid_data.pIocPg2) {
3559 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3560 -               goto cim_get_raid_config_exit;
3561 -       }
3562 -
3563 -       /*
3564 -        * Check to see if the input uRaidSetIndex is
3565 -        * greater than the number of RAID sets
3566 -        */
3567 -       if (pKarg->Configuration.uRaidSetIndex >=
3568 -           ioc->raid_data.pIocPg2->NumActiveVolumes) {
3569 -               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_RAID_SET_OUT_OF_RANGE;
3570 -               goto cim_get_raid_config_exit;
3571 -       }
3572 -
3573 -       /*
3574 -        * get RAID Volume Page 0
3575 -        */
3576 -       volumeID = ioc->raid_data.pIocPg2->RaidVolume[pKarg->Configuration.uRaidSetIndex].VolumeID;
3577 -       VolumeBus = ioc->raid_data.pIocPg2->RaidVolume[pKarg->Configuration.uRaidSetIndex].VolumeBus;
3578 -
3579 -       header.PageVersion = 0;
3580 -       header.PageLength = 0;
3581 -       header.PageNumber = 0;
3582 -       header.PageType = MPI_CONFIG_PAGETYPE_RAID_VOLUME;
3583 -       cfg.cfghdr.hdr = &header;
3584 -       cfg.physAddr = -1;
3585 -       cfg.pageAddr = (VolumeBus << 8) + volumeID;
3586 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
3587 -       cfg.dir = 0;
3588 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
3589 -       if (mpt_config(ioc, &cfg) != 0) {
3590 -               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3591 -               goto cim_get_raid_config_exit;
3592 -       }
3593 -
3594 -       if (header.PageLength == 0) {
3595 -               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3596 -               goto cim_get_raid_config_exit;
3597 -       }
3598 -
3599 -       volumepage0sz = header.PageLength * 4;
3600 -       pVolume0 = pci_alloc_consistent(ioc->pcidev, volumepage0sz,
3601 -           &volume0_dma);
3602 -       if (!pVolume0) {
3603 -               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3604 -               goto cim_get_raid_config_exit;
3605 -       }
3606 -
3607 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
3608 -       cfg.physAddr = volume0_dma;
3609 -       if (mpt_config(ioc, &cfg) != 0) {
3610 -               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3611 -               goto cim_get_raid_config_exit;
3612 -       }
3613 -
3614 -       totalMaxLBA = (u64)le32_to_cpu(pVolume0->MaxLBA) |
3615 -           ((u64)le32_to_cpu(pVolume0->MaxLBAHigh)) << 32;
3616 -       tmpTotalMaxLBA = totalMaxLBA + 1;
3617 -       do_div(tmpTotalMaxLBA, 2048);
3618 -       pKarg->Configuration.uCapacity = tmpTotalMaxLBA;
3619 -       pKarg->Configuration.uStripeSize =
3620 -               le32_to_cpu(pVolume0->StripeSize)/2;
3621 -
3622 -       switch(pVolume0->VolumeType) {
3623 -       case MPI_RAID_VOL_TYPE_IS:
3624 -               pKarg->Configuration.bRaidType = CSMI_SAS_RAID_TYPE_0;
3625 -               break;
3626 -       case MPI_RAID_VOL_TYPE_IME:
3627 -               pKarg->Configuration.bRaidType = CSMI_SAS_RAID_TYPE_10;
3628 -               break;
3629 -       case MPI_RAID_VOL_TYPE_IM:
3630 -               pKarg->Configuration.bRaidType = CSMI_SAS_RAID_TYPE_1;
3631 -               break;
3632 -       default:
3633 -               pKarg->Configuration.bRaidType = CSMI_SAS_RAID_TYPE_OTHER;
3634 -               break;
3635 -       }
3636 -
3637 -       switch (pVolume0->VolumeStatus.State) {
3638 -       case MPI_RAIDVOL0_STATUS_STATE_OPTIMAL:
3639 -               pKarg->Configuration.bStatus = CSMI_SAS_RAID_SET_STATUS_OK;
3640 -               break;
3641 -       case MPI_RAIDVOL0_STATUS_STATE_DEGRADED:
3642 -               /* Volume is degraded, check if Resyncing or Inactive */
3643 -               pKarg->Configuration.bStatus = CSMI_SAS_RAID_SET_STATUS_DEGRADED;
3644 -               break;
3645 -       case MPI_RAIDVOL0_STATUS_STATE_FAILED:
3646 -               pKarg->Configuration.bStatus = CSMI_SAS_RAID_SET_STATUS_FAILED;
3647 -               break;
3648 -       }
3649 -
3650 -       /* check flags */
3651 -       if (pVolume0->VolumeStatus.Flags &
3652 -           MPI_RAIDVOL0_STATUS_FLAG_VOLUME_INACTIVE)
3653 -               pKarg->Configuration.bStatus = CSMI_SAS_RAID_SET_STATUS_OFFLINE;
3654 -       else if (pVolume0->VolumeStatus.Flags &
3655 -           MPI_RAIDVOL0_STATUS_FLAG_RESYNC_IN_PROGRESS)
3656 -               pKarg->Configuration.bStatus = CSMI_SAS_RAID_SET_STATUS_REBUILDING;
3657 -
3658 -       pKarg->Configuration.bInformation = 0;  /* default */
3659 -       if(pVolume0->VolumeStatus.Flags &
3660 -           MPI_RAIDVOL0_STATUS_FLAG_RESYNC_IN_PROGRESS ) {
3661 -
3662 -               uint64_t        * ptrUint64;
3663 -               uint64_t        totalBlocks64, blocksRemaining64;
3664 -               uint32_t        totalBlocks32, blocksRemaining32;
3665 -
3666 -               /* get percentage complete */
3667 -               pRaidActionReply = kmalloc( sizeof(MPI_RAID_VOL_INDICATOR) +
3668 -                   offsetof(MSG_RAID_ACTION_REPLY,ActionData),
3669 -                   GFP_KERNEL);
3670 -
3671 -               if (!pRaidActionReply){
3672 -                       printk(KERN_ERR "%s@%d::%s() - "
3673 -                           "Unable to malloc @ %p\n",
3674 -                           __FILE__, __LINE__, __FUNCTION__,pKarg);
3675 -                       goto cim_get_raid_config_exit;
3676 -               }
3677 -               memset(pRaidActionReply, 0, sizeof(*pRaidActionReply));
3678 -
3679 -               csmisas_do_raid(ioc,
3680 -                   MPI_RAID_ACTION_INDICATOR_STRUCT,
3681 -                   0, VolumeBus, volumeID, pRaidActionReply);
3682 -
3683 -               ptrUint64       = (uint64_t *)&pRaidActionReply->ActionData;
3684 -               totalBlocks64     = *ptrUint64;
3685 -               ptrUint64++;
3686 -               blocksRemaining64 = *ptrUint64;
3687 -               while(totalBlocks64 > 0xFFFFFFFFUL){
3688 -                       totalBlocks64 = totalBlocks64 >> 1;
3689 -                       blocksRemaining64 = blocksRemaining64 >> 1;
3690 -               }
3691 -               totalBlocks32 = (uint32_t)totalBlocks64;
3692 -               blocksRemaining32 = (uint32_t)blocksRemaining64;
3693 -
3694 -               if(totalBlocks32)
3695 -                       pKarg->Configuration.bInformation =
3696 -                           (totalBlocks32 - blocksRemaining32) /
3697 -                           (totalBlocks32 / 100);
3698 -
3699 -               kfree(pRaidActionReply);
3700 -       }
3701 -
3702 -       /* fill-in more information depending on data type */
3703 -       if (pKarg->Configuration.bDataType ==
3704 -           CSMI_SAS_RAID_DATA_ADDITIONAL_DATA) {
3705 -               pKarg->Configuration.Data->bLabel[0] = '\0';
3706 -               pKarg->Configuration.Data->bRaidSetLun[1] = 0;
3707 -               pKarg->Configuration.Data->bWriteProtection =
3708 -                       CSMI_SAS_RAID_SET_WRITE_PROTECT_UNKNOWN;
3709 -               pKarg->Configuration.Data->bCacheSetting =
3710 -                       CSMI_SAS_RAID_SET_CACHE_UNKNOWN;
3711 -               pKarg->Configuration.Data->bCacheRatio = 0;
3712 -               pKarg->Configuration.Data->usBlockSize = 512;
3713 -               pKarg->Configuration.Data->ulRaidSetExtentOffset.uLowPart = 0;
3714 -               pKarg->Configuration.Data->ulRaidSetExtentOffset.uHighPart = 0;
3715 -               pKarg->Configuration.Data->ulRaidSetBlocks.uLowPart =
3716 -                   le32_to_cpu(pVolume0->MaxLBA);
3717 -               pKarg->Configuration.Data->ulRaidSetBlocks.uHighPart =
3718 -                   le32_to_cpu(pVolume0->MaxLBAHigh);
3719 -               if (pVolume0->VolumeType == MPI_RAID_VOL_TYPE_IS ||
3720 -                   pVolume0->VolumeType == MPI_RAID_VOL_TYPE_IME ) {
3721 -                       pKarg->Configuration.Data->uStripeSizeInBlocks =
3722 -                           le32_to_cpu(pVolume0->StripeSize);
3723 -               } else {
3724 -                       pKarg->Configuration.Data->uStripeSizeInBlocks = 0;
3725 -               }
3726 -               pKarg->Configuration.Data->uSectorsPerTrack = 128;
3727 -               for (i=0; i<16; i++) {
3728 -                       // unsupported
3729 -                       pKarg->Configuration.Data->bApplicationScratchPad[i] =
3730 -                           0xFF;
3731 -               }
3732 -               pKarg->Configuration.Data->uNumberOfHeads = 16;
3733 -
3734 -               tmpTotalMaxLBA = totalMaxLBA;
3735 -               do_div(tmpTotalMaxLBA,
3736 -                   (pKarg->Configuration.Data->uNumberOfHeads *
3737 -                    pKarg->Configuration.Data->uSectorsPerTrack));
3738 -               pKarg->Configuration.Data->uNumberOfTracks = tmpTotalMaxLBA;
3739 -               pKarg->Configuration.bDriveCount = 1;
3740 -       } else if ( pKarg->Configuration.bDataType ==
3741 -           CSMI_SAS_RAID_DATA_DEVICE_ID ) {
3742 -               /* Send inquiry to get VPD Page 0x83 */
3743 -               u32 vpd_page_sz;
3744 -               vpd_page_sz = csmi_sas_raid_config_buffer_sz -
3745 -                   offsetof(CSMI_SAS_RAID_CONFIG,DeviceId);
3746 -               if (csmisas_raid_inq(ioc, MPI_FUNCTION_SCSI_IO_REQUEST,
3747 -                       VolumeBus, volumeID, 0x83,
3748 -                       (u8*)&pKarg->Configuration.DeviceId->bDeviceIdentificationVPDPage,
3749 -                       vpd_page_sz) != 0) {
3750 -                       pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3751 -                       goto cim_get_raid_config_exit;
3752 -               }
3753 -               pKarg->Configuration.bDriveCount = 1;
3754 -       }
3755 -
3756 -       if (pKarg->Configuration.bDataType != CSMI_SAS_RAID_DATA_DRIVES) {
3757 -               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
3758 -               goto cim_get_raid_config_exit;
3759 -       }
3760 -
3761 -       /* suppress drive information */
3762 -       if (pKarg->Configuration.bDriveCount ==
3763 -               CSMI_SAS_RAID_DRIVE_COUNT_SUPRESSED) {
3764 -               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
3765 -               goto cim_get_raid_config_exit;
3766 -       }
3767 -
3768 -       /* get hotspare info, used later in this function */
3769 -       if (pVolume0->VolumeSettings.HotSparePool) {
3770 -               /* Read and save IOC Page 5
3771 -                */
3772 -               header.PageVersion = 0;
3773 -               header.PageLength = 0;
3774 -               header.PageNumber = 5;
3775 -               header.PageType = MPI_CONFIG_PAGETYPE_IOC;
3776 -               cfg.cfghdr.hdr = &header;
3777 -               cfg.physAddr = -1;
3778 -               cfg.pageAddr = 0;
3779 -               cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
3780 -               cfg.dir = 0;
3781 -               cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
3782 -               if ((mpt_config(ioc, &cfg) == 0) && (header.PageLength)) {
3783 -                       ioc_page5_sz = header.PageLength * 4;
3784 -                       pIocPage5 = pci_alloc_consistent(ioc->pcidev,
3785 -                           ioc_page5_sz,
3786 -                           &ioc_page5_dma);
3787 -                       memset(pIocPage5,0,ioc_page5_sz);
3788 -                       if (ioc_page5_dma) {
3789 -                               cfg.physAddr = ioc_page5_dma;
3790 -                               cfg.action =
3791 -                                   MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
3792 -                               mpt_config(ioc, &cfg);
3793 -                       }
3794 -               }
3795 -       }
3796 -
3797 -       /*
3798 -        * get RAID Physical Disk Page 0
3799 -        */
3800 -       header.PageVersion = 0;
3801 -       header.PageLength = 0;
3802 -       header.PageNumber = 0;
3803 -       header.PageType = MPI_CONFIG_PAGETYPE_RAID_PHYSDISK;
3804 -       cfg.cfghdr.hdr = &header;
3805 -       cfg.physAddr = -1;
3806 -       cfg.pageAddr = 0;
3807 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
3808 -       cfg.dir = 0;
3809 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
3810 -       if (mpt_config(ioc, &cfg) != 0) {
3811 -               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3812 -               goto cim_get_raid_config_exit;
3813 -       }
3814 -
3815 -       if (header.PageLength == 0) {
3816 -               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3817 -               goto cim_get_raid_config_exit;
3818 -       }
3819 -
3820 -       physdiskpage0sz = header.PageLength * 4;
3821 -       pPhysDisk0 = pci_alloc_consistent(ioc->pcidev, physdiskpage0sz,
3822 -           &physdisk0_dma);
3823 -       if (!pPhysDisk0) {
3824 -               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3825 -               goto cim_get_raid_config_exit;
3826 -       }
3827 -       cfg.physAddr = physdisk0_dma;
3828 -
3829 -       physDiskNumMax = (csmi_sas_raid_config_buffer_sz -
3830 -           offsetof(CSMI_SAS_RAID_CONFIG,Drives))
3831 -           / sizeof(CSMI_SAS_RAID_DRIVES);
3832 -
3833 -       pKarg->Configuration.bDriveCount=0;
3834 -
3835 -       tmpTotalMaxLBA = totalMaxLBA;
3836 -       if (pVolume0->VolumeType == MPI_RAID_VOL_TYPE_IS) {
3837 -               do_div(tmpTotalMaxLBA, pVolume0->NumPhysDisks);
3838 -               dcsmisasprintk(("IS Volume tmpTotalMaxLBA=%llX\n",
3839 -               (unsigned long long)tmpTotalMaxLBA));
3840 -       }
3841 -       else if (pVolume0->VolumeType == MPI_RAID_VOL_TYPE_IME) {
3842 -               do_div(tmpTotalMaxLBA, pVolume0->NumPhysDisks * 2);
3843 -               dcsmisasprintk(("IME Volume tmpTotalMaxLBA=%llX\n",
3844 -               (unsigned long long)tmpTotalMaxLBA));
3845 -       } else {
3846 -               dcsmisasprintk(("IM Volume tmpTotalMaxLBA=%llX\n",
3847 -               (unsigned long long)tmpTotalMaxLBA));
3848 -       }
3849 -
3850 -       for (i=0; i< min(pVolume0->NumPhysDisks, physDiskNumMax); i++) {
3851 -
3852 -               physDiskNum = pVolume0->PhysDisk[i].PhysDiskNum;
3853 -               cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
3854 -               cfg.pageAddr = physDiskNum;
3855 -               if (mpt_config(ioc, &cfg) != 0){
3856 -                       pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
3857 -                       goto cim_get_raid_config_exit;
3858 -               }
3859 -
3860 -               /* Search the list for the matching SAS address. */
3861 -               sas_info = csmisas_get_device_component_by_fw(ioc, pPhysDisk0->PhysDiskBus,
3862 -                   pPhysDisk0->PhysDiskID);
3863 -
3864 -               if (!sas_info)
3865 -                       continue;
3866 -
3867 -               sas_address = reverse_byte_order64(sas_info->sas_address);
3868 -               memcpy(pKarg->Configuration.Drives[i].bSASAddress,
3869 -                  &sas_address,sizeof(u64));
3870 -               if (!device_info)
3871 -                       device_info = sas_info->device_info;
3872 -
3873 -               memcpy(pKarg->Configuration.Drives[i].bModel,
3874 -                   pPhysDisk0->InquiryData.VendorID,
3875 -                   offsetof(RAID_PHYS_DISK0_INQUIRY_DATA,ProductRevLevel));
3876 -               memcpy(pKarg->Configuration.Drives[i].bFirmware,
3877 -                       pPhysDisk0->InquiryData.ProductRevLevel,
3878 -                       sizeof(pPhysDisk0->InquiryData.ProductRevLevel));
3879 -               if (csmisas_is_sata(pPhysDisk0)) {
3880 -                       memcpy(&pKarg->Configuration.Drives[i].bSerialNumber,
3881 -                               &pPhysDisk0->ExtDiskIdentifier[4],
3882 -                               4);
3883 -                       memcpy(&pKarg->Configuration.Drives[i].bSerialNumber[4],
3884 -                               &pPhysDisk0->DiskIdentifier,
3885 -                               sizeof(pPhysDisk0->DiskIdentifier));
3886 -               } else {
3887 -                       memcpy(pKarg->Configuration.Drives[i].bSerialNumber,
3888 -                               pPhysDisk0->DiskIdentifier,
3889 -                               sizeof(pPhysDisk0->DiskIdentifier));
3890 -               }
3891 -
3892 -               pKarg->Configuration.Drives[i].bDriveUsage =
3893 -                   (pPhysDisk0->PhysDiskStatus.Flags &
3894 -                   MPI_PHYSDISK0_STATUS_FLAG_INACTIVE_VOLUME) ?
3895 -                   CSMI_SAS_DRIVE_CONFIG_NOT_USED :
3896 -                   CSMI_SAS_DRIVE_CONFIG_MEMBER;
3897 -
3898 -               pKarg->Configuration.Drives[i].bDriveStatus =
3899 -                   CSMI_SAS_DRIVE_STATUS_OK;
3900 -               if (pPhysDisk0->PhysDiskStatus.State ==
3901 -                   MPI_PHYSDISK0_STATUS_OFFLINE_REQUESTED) {
3902 -                       pKarg->Configuration.Drives[i].bDriveStatus =
3903 -                           CSMI_SAS_DRIVE_STATUS_OFFLINE;
3904 -               } else if(pPhysDisk0->PhysDiskStatus.State) {
3905 -                       pKarg->Configuration.Drives[i].bDriveStatus =
3906 -                           CSMI_SAS_DRIVE_STATUS_FAILED;
3907 -                       if(pKarg->Configuration.bStatus ==
3908 -                           CSMI_SAS_RAID_SET_STATUS_DEGRADED)
3909 -                               pKarg->Configuration.bInformation = i;
3910 -               } else if((pVolume0->VolumeStatus.Flags &
3911 -                   MPI_RAIDVOL0_STATUS_FLAG_RESYNC_IN_PROGRESS) &&
3912 -                   (pPhysDisk0->PhysDiskStatus.Flags &
3913 -                   MPI_PHYSDISK0_STATUS_FLAG_OUT_OF_SYNC))
3914 -                       pKarg->Configuration.Drives[i].bDriveStatus =
3915 -                           CSMI_SAS_DRIVE_STATUS_REBUILDING;
3916 -               else if(pPhysDisk0->ErrorData.SmartCount ||
3917 -                   (pPhysDisk0->PhysDiskStatus.Flags &
3918 -                   MPI_PHYSDISK0_STATUS_FLAG_OUT_OF_SYNC))
3919 -                       pKarg->Configuration.Drives[i].bDriveStatus =
3920 -                       CSMI_SAS_DRIVE_STATUS_DEGRADED;
3921 -
3922 -               memset(pKarg->Configuration.Drives[i].bSASLun,
3923 -                   0, sizeof(pKarg->Configuration.Drives[i].bSASLun));
3924 -               if (csmisas_is_sata(pPhysDisk0)) {
3925 -                       pKarg->Configuration.Drives[i].bDriveType =
3926 -                       CSMI_SAS_DRIVE_TYPE_SATA;
3927 -               } else { /* drive in a volume can only be SAS/SATA */
3928 -                       pKarg->Configuration.Drives[i].bDriveType =
3929 -                               CSMI_SAS_DRIVE_TYPE_SINGLE_PORT_SAS;
3930 -               }
3931 -
3932 -               pKarg->Configuration.Drives[i].usBlockSize = 512;
3933 -                       pKarg->Configuration.Drives[i].uDriveIndex =
3934 -                           pPhysDisk0->PhysDiskNum;
3935 -               pKarg->Configuration.Drives[i].ulTotalUserBlocks.uLowPart =
3936 -                   (u32)tmpTotalMaxLBA;
3937 -               pKarg->Configuration.Drives[i].ulTotalUserBlocks.uHighPart =
3938 -                   (u32)(tmpTotalMaxLBA >> 32);
3939 -               pKarg->Configuration.bDriveCount++;
3940 -       }
3941 -
3942 -       /* adding hot spare info at the end */
3943 -       if ((pVolume0->VolumeSettings.HotSparePool) && (pIocPage5) &&
3944 -           (pVolume0->VolumeType != MPI_RAID_VOL_TYPE_IS)) {
3945 -               for (idx = 0, i = pVolume0->NumPhysDisks ;
3946 -                   idx < pIocPage5->NumHotSpares ; idx++) {
3947 -                       if (i >= physDiskNumMax)
3948 -                               break;
3949 -                       if ((pVolume0->VolumeSettings.HotSparePool &
3950 -                           pIocPage5->HotSpare[idx].HotSparePool) == 0)
3951 -                               continue;
3952 -                       if(pIocPage5->HotSpare[idx].Flags !=
3953 -                           MPI_IOC_PAGE_5_HOT_SPARE_ACTIVE)
3954 -                           continue;
3955 -                       physDiskNum = pIocPage5->HotSpare[idx].PhysDiskNum;
3956 -                       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
3957 -                       cfg.pageAddr = physDiskNum;
3958 -                       if (mpt_config(ioc, &cfg) != 0)
3959 -                               continue;
3960 -
3961 -                       /* Search the list for the matching SAS address. */
3962 -                       sas_info = csmisas_get_device_component_by_fw(ioc,
3963 -                           pPhysDisk0->PhysDiskBus, pPhysDisk0->PhysDiskID);
3964 -
3965 -                       if (!sas_info)
3966 -                               continue;
3967 -
3968 -                       sas_address = reverse_byte_order64(sas_info->sas_address);
3969 -                       memcpy(pKarg->Configuration.Drives[i].bSASAddress,
3970 -                          &sas_address,sizeof(u64));
3971 -
3972 -                       /* don't mix SSP hot spare
3973 -                        * in SATA volume
3974 -                        */
3975 -                       if (!csmisas_is_sata(pPhysDisk0) &&
3976 -                           (device_info &
3977 -                           MPI_SAS_DEVICE_INFO_SATA_DEVICE))
3978 -                               continue;
3979 -
3980 -                       /* don't mix SATA hot spare
3981 -                        * in SSP volume
3982 -                        */
3983 -                       if (csmisas_is_sata(pPhysDisk0) &&
3984 -                           (device_info &
3985 -                           MPI_SAS_DEVICE_INFO_SSP_TARGET))
3986 -                               continue;
3987 -
3988 -                       /* capacity check for IM volumes*/
3989 -                       if ((pVolume0->VolumeType ==
3990 -                           MPI_RAID_VOL_TYPE_IM) &&
3991 -                           (totalMaxLBA +
3992 -                           (64*2*1024) /* metadata = 64MB*/ >
3993 -                           le32_to_cpu(pPhysDisk0->MaxLBA)))
3994 -                               continue;
3995 -
3996 -                       tmpTotalMaxLBA = totalMaxLBA;
3997 -                       do_div(tmpTotalMaxLBA, pVolume0->NumPhysDisks);
3998 -                       /* capacity check for IME volumes*/
3999 -                       if ((pVolume0->VolumeType ==
4000 -                               MPI_RAID_VOL_TYPE_IME) &&
4001 -                           ((tmpTotalMaxLBA * 2) +
4002 -                            (64*2*1024 ) /*metadata = 64MB*/ >
4003 -                           le32_to_cpu(pPhysDisk0->MaxLBA)))
4004 -                               break;
4005 -
4006 -                       /* capacity check for IME volumes*/
4007 -                       if ((pVolume0->VolumeType ==
4008 -                           MPI_RAID_VOL_TYPE_IME) &&
4009 -                           (((totalMaxLBA +
4010 -                           pVolume0->NumPhysDisks) * 2) +
4011 -                           (64*2*1024 ) /*metadata = 64MB*/ >
4012 -                           le32_to_cpu(pPhysDisk0->MaxLBA)))
4013 -                               continue;
4014 -
4015 -                       memcpy(pKarg->Configuration.Drives[i].bModel,
4016 -                           pPhysDisk0->InquiryData.VendorID,
4017 -                           offsetof(RAID_PHYS_DISK0_INQUIRY_DATA,ProductRevLevel));
4018 -                       memcpy(pKarg->Configuration.Drives[i].bFirmware,
4019 -                               pPhysDisk0->InquiryData.ProductRevLevel,
4020 -                               sizeof(pPhysDisk0->InquiryData.ProductRevLevel));
4021 -                       if (csmisas_is_sata(pPhysDisk0)) {
4022 -                               memcpy(&pKarg->Configuration.Drives[i].bSerialNumber,
4023 -                                       &pPhysDisk0->ExtDiskIdentifier[4],
4024 -                                       4);
4025 -                               memcpy(&pKarg->Configuration.Drives[i].bSerialNumber[4],
4026 -                                       &pPhysDisk0->DiskIdentifier,
4027 -                                       sizeof(pPhysDisk0->DiskIdentifier));
4028 -                       } else {
4029 -                               memcpy(pKarg->Configuration.Drives[i].bSerialNumber,
4030 -                                       pPhysDisk0->DiskIdentifier,
4031 -                                       sizeof(pPhysDisk0->DiskIdentifier));
4032 -                       }
4033 -                       pKarg->Configuration.Drives[i].bDriveStatus =
4034 -                           CSMI_SAS_DRIVE_STATUS_OK;
4035 -                       if(pPhysDisk0->PhysDiskStatus.State)
4036 -                               pKarg->Configuration.Drives[i].bDriveStatus =
4037 -                                   CSMI_SAS_DRIVE_STATUS_FAILED;
4038 -                       else if(pPhysDisk0->ErrorData.SmartCount)
4039 -                               pKarg->Configuration.Drives[i].bDriveStatus =
4040 -                                   CSMI_SAS_DRIVE_STATUS_DEGRADED;
4041 -                       pKarg->Configuration.Drives[i].bDriveUsage =
4042 -                           CSMI_SAS_DRIVE_CONFIG_SPARE;
4043 -                       pKarg->Configuration.Drives[i].usBlockSize = 512;
4044 -                       pKarg->Configuration.Drives[i].uDriveIndex =
4045 -                           pPhysDisk0->PhysDiskNum;
4046 -                       if (csmisas_is_sata(pPhysDisk0)) {
4047 -                               pKarg->Configuration.Drives[i].bDriveType =
4048 -                               CSMI_SAS_DRIVE_TYPE_SATA;
4049 -                       } else { /* drive in a volume can only be SAS/SATA */
4050 -                               pKarg->Configuration.Drives[i].bDriveType =
4051 -                                       CSMI_SAS_DRIVE_TYPE_SINGLE_PORT_SAS;
4052 -                       }
4053 -
4054 -                       i++;
4055 -                       pKarg->Configuration.bDriveCount++;
4056 -               }
4057 -       }
4058 -
4059 -       // Only return data on the first 240 drives
4060 -       if( pKarg->Configuration.bDriveCount > 0xF0 )
4061 -               pKarg->Configuration.bDriveCount =
4062 -                   CSMI_SAS_RAID_DRIVE_COUNT_TOO_BIG;
4063 -
4064 -       pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
4065 -
4066 - cim_get_raid_config_exit:
4067 -
4068 -       if (pVolume0 != NULL)
4069 -               pci_free_consistent(ioc->pcidev, volumepage0sz, pVolume0,
4070 -                   volume0_dma);
4071 -
4072 -       if(pPhysDisk0 != NULL)
4073 -               pci_free_consistent(ioc->pcidev, physdiskpage0sz, pPhysDisk0,
4074 -                   physdisk0_dma);
4075 -
4076 -       if(pIocPage5 != NULL)
4077 -               pci_free_consistent(ioc->pcidev, ioc_page5_sz, pIocPage5,
4078 -                   ioc_page5_dma);
4079 -
4080 -       /* Copy the data from kernel memory to user memory
4081 -        */
4082 -
4083 -       /* find the buffer size to copy depending on how much is filled-in */
4084 -       switch (pKarg->Configuration.bDataType) {
4085 -       case CSMI_SAS_RAID_DATA_ADDITIONAL_DATA:
4086 -               copy_buffer_sz = sizeof(IOCTL_HEADER) +
4087 -                   offsetof(CSMI_SAS_RAID_CONFIG,Data) +
4088 -                   sizeof(CSMI_SAS_RAID_SET_ADDITIONAL_DATA);
4089 -               break;
4090 -       case CSMI_SAS_RAID_DATA_DRIVES:
4091 -               if (pKarg->Configuration.bDriveCount ==
4092 -                   CSMI_SAS_RAID_DRIVE_COUNT_SUPRESSED)
4093 -                       copy_buffer_sz = sizeof(IOCTL_HEADER) +
4094 -                           offsetof(CSMI_SAS_RAID_CONFIG,Drives);
4095 -               else
4096 -                       copy_buffer_sz = sizeof(IOCTL_HEADER) +
4097 -                           offsetof(CSMI_SAS_RAID_CONFIG,Drives) +
4098 -                           (pKarg->Configuration.bDriveCount *
4099 -                           sizeof(CSMI_SAS_RAID_DRIVES));
4100 -               break;
4101 -       case CSMI_SAS_RAID_DATA_DEVICE_ID:
4102 -               copy_buffer_sz = csmi_sas_raid_config_buffer_sz;
4103 -               break;
4104 -       }
4105 -
4106 -       if (copy_to_user((char *)arg, pKarg, copy_buffer_sz)) {
4107 -               printk(KERN_ERR "%s@%d::%s() - "
4108 -                      "Unable to write out csmi_sas_get_raid_config @ %p\n",
4109 -                          __FILE__, __LINE__, __FUNCTION__, uarg);
4110 -               free_pages((unsigned long)pKarg, memory_pages);
4111 -               return -EFAULT;
4112 -       }
4113 -
4114 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
4115 -       free_pages((unsigned long)pKarg, memory_pages);
4116 -       return 0;
4117 -}
4118 -
4119 -/**
4120 - * Prototype Routine for the CSMI SAS Get RAID Features command.
4121 - *
4122 - * Outputs:    None.
4123 - * Return:     0 if successful
4124 - *             -EFAULT if data unavailable
4125 - *             -ENODEV if no such device/adapter
4126 - **/
4127 -static int
4128 -csmisas_get_raid_features(unsigned long arg)
4129 -{
4130 -       CSMI_SAS_RAID_FEATURES_BUFFER __user *uarg = (void __user *) arg;
4131 -       CSMI_SAS_RAID_FEATURES_BUFFER karg, *pKarg=NULL;
4132 -       int csmi_sas_raid_features_buffer_sz, iocnum;
4133 -       int                             memory_pages;
4134 -       MPT_ADAPTER             *ioc = NULL;
4135 -
4136 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
4137 -
4138 -       if (copy_from_user(&karg, uarg, sizeof(IOCTL_HEADER))) {
4139 -               printk(KERN_ERR "%s@%d::%s() - "
4140 -                   "Unable to read in csmi_sas_get_raid_features struct @ %p\n",
4141 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
4142 -               return -EFAULT;
4143 -       }
4144 -
4145 -       csmi_sas_raid_features_buffer_sz = karg.IoctlHeader.Length;
4146 -       memory_pages = get_order(csmi_sas_raid_features_buffer_sz);
4147 -       pKarg = (CSMI_SAS_RAID_FEATURES_BUFFER *)__get_free_pages(
4148 -               GFP_KERNEL, memory_pages);
4149 -       if (!pKarg){
4150 -               printk(KERN_ERR "%s@%d::%s() - "
4151 -                   "Unable to malloc RAID_FEATURES_BUFFER "
4152 -                       "csmi_sas_raid_features_buffer_sz=%d memory_pages=%d\n",
4153 -                       __FILE__, __LINE__, __FUNCTION__,
4154 -                       csmi_sas_raid_features_buffer_sz, memory_pages);
4155 -               return -ENOMEM;
4156 -       }
4157 -       memset(pKarg, 0, sizeof(*pKarg));
4158 -
4159 -       if (copy_from_user(pKarg, uarg, csmi_sas_raid_features_buffer_sz)) {
4160 -               printk(KERN_ERR "%s@%d::%s() - "
4161 -                   "Unable to read in csmi_sas_get_raid_features struct @ %p\n",
4162 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
4163 -               free_pages((unsigned long)pKarg, memory_pages);
4164 -               return -EFAULT;
4165 -       }
4166 -
4167 -       if (((iocnum = mpt_verify_adapter(pKarg->IoctlHeader.IOControllerNumber,
4168 -           &ioc)) < 0) || (ioc == NULL)) {
4169 -               dcsmisasprintk((KERN_ERR
4170 -               "%s::%s() @%d - ioc%d not found!\n",
4171 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4172 -               free_pages((unsigned long)pKarg, memory_pages);
4173 -               return -ENODEV;
4174 -       }
4175 -
4176 -       if (!csmisas_is_this_sas_cntr(ioc)) {
4177 -               dcsmisasprintk((KERN_ERR
4178 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
4179 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4180 -               free_pages((unsigned long)pKarg, memory_pages);
4181 -               return -ENODEV;
4182 -       }
4183 -
4184 -       if (pKarg->Information.uChangeCount != 0 &&
4185 -           pKarg->Information.uChangeCount != ioc->csmi_change_count ) {
4186 -               pKarg->IoctlHeader.ReturnCode =
4187 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
4188 -               pKarg->Information.uFailureCode =
4189 -                   CSMI_SAS_FAIL_CODE_CHANGE_COUNT_INVALID;
4190 -               goto cim_get_raid_features_exit;
4191 -       }
4192 -
4193 -       pKarg->Information.uFeatures = CSMI_SAS_RAID_FEATURE_REBUILD |
4194 -           CSMI_SAS_RAID_FEATURE_SURFACE_SCAN |
4195 -           CSMI_SAS_RAID_FEATURE_SPARES_SHARED;
4196 -       pKarg->Information.bDefaultTransformPriority =
4197 -           CSMI_SAS_PRIORITY_UNKNOWN;
4198 -       pKarg->Information.bTransformPriority = CSMI_SAS_PRIORITY_UNKNOWN;
4199 -       pKarg->Information.bDefaultRebuildPriority = CSMI_SAS_PRIORITY_UNKNOWN;
4200 -       pKarg->Information.bRebuildPriority =
4201 -           pKarg->Information.bDefaultRebuildPriority;
4202 -       pKarg->Information.bDefaultSurfaceScanPriority =
4203 -           CSMI_SAS_PRIORITY_UNKNOWN;
4204 -       pKarg->Information.bSurfaceScanPriority = CSMI_SAS_PRIORITY_UNKNOWN;
4205 -       pKarg->Information.uRaidSetTransformationRules = 0;
4206 -
4207 -        /* IS */
4208 -       pKarg->Information.RaidType[0].bRaidType = CSMI_SAS_RAID_TYPE_0;
4209 -       pKarg->Information.RaidType[0].uSupportedStripeSizeMap = 0x80;
4210 -
4211 -       /* IM */
4212 -       pKarg->Information.RaidType[1].bRaidType = CSMI_SAS_RAID_TYPE_1;
4213 -       pKarg->Information.RaidType[1].uSupportedStripeSizeMap = 0;
4214 -
4215 -       /* IME */
4216 -       pKarg->Information.RaidType[2].bRaidType = CSMI_SAS_RAID_TYPE_1E;
4217 -       pKarg->Information.RaidType[2].uSupportedStripeSizeMap = 0x80;
4218 -
4219 -       pKarg->Information.RaidType[3].bRaidType = CSMI_SAS_RAID_TYPE_END;
4220 -       pKarg->Information.bCacheRatiosSupported[0] =
4221 -           CSMI_SAS_RAID_CACHE_RATIO_END;
4222 -
4223 - cim_get_raid_features_exit:
4224 -
4225 -       /*
4226 -        * Copy the data from kernel memory to user memory
4227 -        */
4228 -       if (copy_to_user((char *)arg, pKarg,
4229 -           sizeof(CSMI_SAS_RAID_FEATURES_BUFFER))) {
4230 -               printk(KERN_ERR "%s@%d::%s() - "
4231 -               "Unable to write out csmi_sas_get_raid_features @ %p\n",
4232 -               __FILE__, __LINE__, __FUNCTION__, uarg);
4233 -               free_pages((unsigned long)pKarg, memory_pages);
4234 -               return -EFAULT;
4235 -       }
4236 -
4237 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
4238 -       free_pages((unsigned long)pKarg, memory_pages);
4239 -       return 0;
4240 -}
4241 -
4242 -/**
4243 - * Prototype Routine for the CSMI SAS Set RAID Control command.
4244 - *
4245 - * Outputs:    None.
4246 - * Return:     0 if successful
4247 - *             -EFAULT if data unavailable
4248 - *             -ENODEV if no such device/adapter
4249 - **/
4250 -static int
4251 -csmisas_set_raid_control(unsigned long arg)
4252 -{
4253 -       CSMI_SAS_RAID_CONTROL_BUFFER __user *uarg = (void __user *) arg;
4254 -       CSMI_SAS_RAID_CONTROL_BUFFER karg, *pKarg=NULL;
4255 -       int csmi_sas_raid_control_buffer_sz, iocnum;
4256 -       int                             memory_pages;
4257 -       MPT_ADAPTER     *ioc = NULL;
4258 -
4259 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
4260 -
4261 -       if (copy_from_user(&karg, uarg, sizeof(IOCTL_HEADER))) {
4262 -               printk(KERN_ERR "%s@%d::%s() - "
4263 -                   "Unable to read in csmi_sas_set_raid_control struct @ %p\n",
4264 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
4265 -               return -EFAULT;
4266 -       }
4267 -
4268 -       csmi_sas_raid_control_buffer_sz = karg.IoctlHeader.Length;
4269 -       memory_pages = get_order(csmi_sas_raid_control_buffer_sz);
4270 -       pKarg = (CSMI_SAS_RAID_CONTROL_BUFFER *)__get_free_pages(
4271 -               GFP_KERNEL, memory_pages);
4272 -       if (!pKarg){
4273 -               printk(KERN_ERR "%s@%d::%s() - "
4274 -                   "Unable to malloc RAID_CONTROL_BUFFER "
4275 -                       "csmi_sas_raid_control_buffer_sz=%d memory_pages=%d\n",
4276 -                       __FILE__, __LINE__, __FUNCTION__,
4277 -                       csmi_sas_raid_control_buffer_sz, memory_pages);
4278 -               return -ENOMEM;
4279 -       }
4280 -       memset(pKarg, 0, sizeof(*pKarg));
4281 -
4282 -       if (copy_from_user(pKarg, uarg, csmi_sas_raid_control_buffer_sz)) {
4283 -               printk(KERN_ERR "%s@%d::%s() - "
4284 -                   "Unable to read in csmi_sas_set_raid_control struct @ %p\n",
4285 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
4286 -               free_pages((unsigned long)pKarg, memory_pages);
4287 -               return -EFAULT;
4288 -       }
4289 -
4290 -       if (((iocnum = mpt_verify_adapter(pKarg->IoctlHeader.IOControllerNumber,
4291 -           &ioc)) < 0) || (ioc == NULL)) {
4292 -               dcsmisasprintk((KERN_ERR
4293 -               "%s::%s() @%d - ioc%d not found!\n",
4294 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4295 -               free_pages((unsigned long)pKarg, memory_pages);
4296 -               return -ENODEV;
4297 -       }
4298 -
4299 -       if (!csmisas_is_this_sas_cntr(ioc)) {
4300 -               dcsmisasprintk((KERN_ERR
4301 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
4302 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4303 -               free_pages((unsigned long)pKarg, memory_pages);
4304 -               return -ENODEV;
4305 -       }
4306 -
4307 -       if (pKarg->Information.uChangeCount != 0 &&
4308 -               pKarg->Information.uChangeCount != ioc->csmi_change_count ) {
4309 -               pKarg->IoctlHeader.ReturnCode =
4310 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
4311 -               pKarg->Information.uFailureCode =
4312 -                   CSMI_SAS_FAIL_CODE_CHANGE_COUNT_INVALID;
4313 -               goto cim_set_raid_control_exit;
4314 -       }
4315 -
4316 -       if (pKarg->Information.bTransformPriority !=
4317 -           CSMI_SAS_PRIORITY_UNCHANGED) {
4318 -               pKarg->IoctlHeader.ReturnCode =
4319 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
4320 -               pKarg->Information.uFailureCode =
4321 -                   CSMI_SAS_FAIL_CODE_TRANSFORM_PRIORITY_INVALID;
4322 -               goto cim_set_raid_control_exit;
4323 -       }
4324 -
4325 -       if (pKarg->Information.bRebuildPriority !=
4326 -           CSMI_SAS_PRIORITY_AUTO &&
4327 -               pKarg->Information.bRebuildPriority !=
4328 -               CSMI_SAS_PRIORITY_UNCHANGED) {
4329 -               pKarg->IoctlHeader.ReturnCode =
4330 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
4331 -               pKarg->Information.uFailureCode =
4332 -                   CSMI_SAS_FAIL_CODE_REBUILD_PRIORITY_INVALID;
4333 -               goto cim_set_raid_control_exit;
4334 -       }
4335 -
4336 -       if (pKarg->Information.bCacheRatioFlag ==
4337 -           CSMI_SAS_RAID_CACHE_RATIO_DISABLE) {
4338 -               pKarg->IoctlHeader.ReturnCode =
4339 -                   CSMI_SAS_STATUS_INVALID_PARAMETER;
4340 -               pKarg->Information.uFailureCode =
4341 -                   CSMI_SAS_FAIL_CODE_CACHE_RATIO_INVALID;
4342 -               goto cim_set_raid_control_exit;
4343 -       }
4344 -
4345 -       if( !strcmp(pKarg->Information.bClearConfiguration,
4346 -               CSMI_SAS_RAID_CLEAR_CONFIGURATION_SIGNATURE) ) {
4347 -               pKarg->IoctlHeader.ReturnCode =
4348 -                       CSMI_SAS_STATUS_INVALID_PARAMETER;
4349 -               pKarg->Information.uFailureCode =
4350 -                       CSMI_SAS_FAIL_CODE_CLEAR_CONFIGURATION_INVALID;
4351 -               goto cim_set_raid_control_exit;
4352 -       }
4353 -
4354 -       pKarg->Information.bFailureDescription[0] = '\0';
4355 -
4356 - cim_set_raid_control_exit:
4357 -
4358 -       /*
4359 -        * Copy the data from kernel memory to user memory
4360 -        */
4361 -       if (copy_to_user((char *)arg, pKarg,
4362 -               sizeof(CSMI_SAS_RAID_CONTROL_BUFFER))) {
4363 -               printk(KERN_ERR "%s@%d::%s() - "
4364 -               "Unable to write out csmi_sas_set_raid_control @ %p\n",
4365 -               __FILE__, __LINE__, __FUNCTION__, uarg);
4366 -               free_pages((unsigned long)pKarg, memory_pages);
4367 -               return -EFAULT;
4368 -       }
4369 -
4370 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
4371 -       free_pages((unsigned long)pKarg, memory_pages);
4372 -       return 0;
4373 -}
4374 -
4375 -/**
4376 - * Prototype Routine for the CSMI SAS Get Raid Element.
4377 - *
4378 - * Outputs:    None.
4379 - * Return:     0 if successful
4380 - *             -EFAULT if data unavailable
4381 - *             -ENODEV if no such device/adapter
4382 - **/
4383 -static int
4384 -csmisas_get_raid_element(unsigned long arg)
4385 -{
4386 -       CSMI_SAS_RAID_ELEMENT_BUFFER __user *uarg = (void __user *) arg;
4387 -       CSMI_SAS_RAID_ELEMENT_BUFFER     karg;
4388 -       MPT_ADAPTER                     *ioc = NULL;
4389 -       int                             iocnum;
4390 -
4391 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
4392 -
4393 -       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_RAID_ELEMENT_BUFFER))) {
4394 -               printk(KERN_ERR "%s@%d::%s() - "
4395 -                   "Unable to read in csmisas_get_raid_element struct @ %p\n",
4396 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
4397 -               return -EFAULT;
4398 -       }
4399 -
4400 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
4401 -           &ioc)) < 0) || (ioc == NULL)) {
4402 -               dcsmisasprintk((KERN_ERR
4403 -               "%s::%s() @%d - ioc%d not found!\n",
4404 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4405 -               return -ENODEV;
4406 -       }
4407 -
4408 -       if (!csmisas_is_this_sas_cntr(ioc)) {
4409 -               dcsmisasprintk((KERN_ERR
4410 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
4411 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4412 -               return -ENODEV;
4413 -       }
4414 -
4415 -/* TODO - implement IOCTL here */
4416 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_BAD_CNTL_CODE;
4417 -       dcsmisasprintk((": not implemented\n"));
4418 -
4419 -// csmisas_get_raid_element_exit:
4420 -
4421 -       /* Copy the data from kernel memory to user memory
4422 -        */
4423 -       if (copy_to_user((char *)arg, &karg,
4424 -                               sizeof(CSMI_SAS_RAID_ELEMENT_BUFFER))) {
4425 -               printk(KERN_ERR "%s@%d::%s() - "
4426 -                       "Unable to write out csmisas_get_raid_element @ %p\n",
4427 -                               __FILE__, __LINE__, __FUNCTION__, uarg);
4428 -               return -EFAULT;
4429 -       }
4430 -
4431 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
4432 -       return 0;
4433 -
4434 -}
4435 -
4436 -/**
4437 - * Prototype Routine for the CSMI SAS Set Raid Operation
4438 - *
4439 - * Outputs:    None.
4440 - * Return:     0 if successful
4441 - *             -EFAULT if data unavailable
4442 - *             -ENODEV if no such device/adapter
4443 - **/
4444 -static int
4445 -csmisas_set_raid_operation(unsigned long arg)
4446 -{
4447 -       CSMI_SAS_RAID_SET_OPERATION_BUFFER __user *uarg = (void __user *) arg;
4448 -       CSMI_SAS_RAID_SET_OPERATION_BUFFER       karg;
4449 -       MPT_ADAPTER                     *ioc = NULL;
4450 -       int                             iocnum;
4451 -
4452 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
4453 -
4454 -       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_RAID_SET_OPERATION_BUFFER))) {
4455 -               printk(KERN_ERR "%s@%d::%s() - "
4456 -                   "Unable to read in csmi_set_raid_operation struct @ %p\n",
4457 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
4458 -               return -EFAULT;
4459 -       }
4460 -
4461 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
4462 -           &ioc)) < 0) || (ioc == NULL)) {
4463 -               dcsmisasprintk((KERN_ERR
4464 -               "%s::%s() @%d - ioc%d not found!\n",
4465 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4466 -               return -ENODEV;
4467 -       }
4468 -
4469 -       if (!csmisas_is_this_sas_cntr(ioc)) {
4470 -               dcsmisasprintk((KERN_ERR
4471 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
4472 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4473 -               return -ENODEV;
4474 -       }
4475 -
4476 -/* TODO - implement IOCTL here */
4477 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_BAD_CNTL_CODE;
4478 -       dcsmisasprintk((": not implemented\n"));
4479 -
4480 -// cim_set_raid_operation:
4481 -
4482 -       /* Copy the data from kernel memory to user memory
4483 -        */
4484 -       if (copy_to_user((char *)arg, &karg,
4485 -                               sizeof(CSMI_SAS_RAID_SET_OPERATION_BUFFER))) {
4486 -               printk(KERN_ERR "%s@%d::%s() - "
4487 -                       "Unable to write out csmi_set_raid_operation @ %p\n",
4488 -                               __FILE__, __LINE__, __FUNCTION__, uarg);
4489 -               return -EFAULT;
4490 -       }
4491 -
4492 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
4493 -       return 0;
4494 -
4495 -}
4496 -
4497 -
4498 -/**
4499 - * Prototype Routine for the CSMI SAS Task Managment Config command.
4500 - *
4501 - * Outputs:    None.
4502 - * Return:     0 if successful
4503 - *             -EFAULT if data unavailable
4504 - *             -ENODEV if no such device/adapter
4505 - **/
4506 -static int
4507 -csmisas_task_managment(unsigned long arg)
4508 -{
4509 -       CSMI_SAS_SSP_TASK_IU_BUFFER __user *uarg = (void __user *) arg;
4510 -       CSMI_SAS_SSP_TASK_IU_BUFFER      karg;
4511 -       pSCSITaskMgmt_t                 pScsiTm;
4512 -       pSCSITaskMgmtReply_t            pScsiTmReply;
4513 -       MPT_ADAPTER                     *ioc = NULL;
4514 -       MPT_SCSI_HOST                   *hd;
4515 -       MPT_FRAME_HDR                   *mf = NULL;
4516 -       MPIHeader_t                     *mpi_hdr;
4517 -       int                             iocnum;
4518 -       u8                              taskType;
4519 -       u8                              channel;
4520 -       u8                              id;
4521 -       u8                              queueTag;
4522 -       u32                             msgContext = 0;
4523 -       int                             i;
4524 -       u8                              found_qtag;
4525 -       struct sas_device_info          *sas_info;
4526 -       u16                             ioc_status;
4527 -
4528 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
4529 -
4530 -       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_SSP_TASK_IU_BUFFER))) {
4531 -               printk(KERN_ERR "%s@%d::%s() - "
4532 -                   "Unable to read in csmi_sas_task_managment struct @ %p\n",
4533 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
4534 -               return -EFAULT;
4535 -       }
4536 -
4537 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
4538 -           &ioc)) < 0) || (ioc == NULL)) {
4539 -               dcsmisasprintk((KERN_ERR
4540 -               "%s::%s() @%d - ioc%d not found!\n",
4541 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4542 -               return -ENODEV;
4543 -       }
4544 -
4545 -       if (!csmisas_is_this_sas_cntr(ioc)) {
4546 -               dcsmisasprintk((KERN_ERR
4547 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
4548 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4549 -               return -ENODEV;
4550 -       }
4551 -
4552 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
4553 -
4554 -       sas_info = csmisas_get_device_component_by_os(ioc,
4555 -           karg.Parameters.bPathId, karg.Parameters.bTargetId);
4556 -       if (!sas_info || sas_info->is_cached || sas_info->is_logical_volume)
4557 -               goto cim_get_task_managment_exit;
4558 -
4559 -       channel = sas_info->fw.channel;
4560 -       id = sas_info->fw.id;
4561 -       queueTag = (u8)karg.Parameters.uQueueTag & 0xFF;
4562 -       hd = (MPT_SCSI_HOST *) ioc->sh->hostdata;
4563 -
4564 -       /* try to catch an error
4565 -        */
4566 -       if ((karg.Parameters.uFlags & CSMI_SAS_TASK_IU) &&
4567 -           (karg.Parameters.uFlags & CSMI_SAS_HARD_RESET_SEQUENCE))
4568 -               goto cim_get_task_managment_exit;
4569 -
4570 -       if (karg.Parameters.uFlags & CSMI_SAS_TASK_IU) {
4571 -               switch (karg.Parameters.bTaskManagementFunction) {
4572 -
4573 -               case CSMI_SAS_SSP_ABORT_TASK:
4574 -                       taskType = MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK;
4575 -                       break;
4576 -               case CSMI_SAS_SSP_ABORT_TASK_SET:
4577 -                       taskType = MPI_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET;
4578 -                       break;
4579 -               case CSMI_SAS_SSP_CLEAR_TASK_SET:
4580 -                       taskType = MPI_SCSITASKMGMT_TASKTYPE_CLEAR_TASK_SET;
4581 -                       break;
4582 -               case CSMI_SAS_SSP_LOGICAL_UNIT_RESET:
4583 -                       taskType = MPI_SCSITASKMGMT_TASKTYPE_LOGICAL_UNIT_RESET;
4584 -                       break;
4585 -               case CSMI_SAS_SSP_CLEAR_ACA:
4586 -               case CSMI_SAS_SSP_QUERY_TASK:
4587 -               default:
4588 -                       goto cim_get_task_managment_exit;
4589 -               }
4590 -       } else if (karg.Parameters.uFlags & CSMI_SAS_HARD_RESET_SEQUENCE)
4591 -               taskType = MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET;
4592 -       else
4593 -               goto cim_get_task_managment_exit;
4594 -
4595 -       switch (karg.Parameters.uInformation) {
4596 -               case CSMI_SAS_SSP_TEST:
4597 -                       dcsmisasprintk(("TM request for test purposes\n"));
4598 -                       break;
4599 -               case CSMI_SAS_SSP_EXCEEDED:
4600 -                       dcsmisasprintk(("TM request due to timeout\n"));
4601 -                       break;
4602 -               case CSMI_SAS_SSP_DEMAND:
4603 -                       dcsmisasprintk(("TM request demanded by app\n"));
4604 -                       break;
4605 -               case CSMI_SAS_SSP_TRIGGER:
4606 -                       dcsmisasprintk(("TM request sent to trigger event\n"));
4607 -                       break;
4608 -       }
4609 -
4610 -       switch (taskType) {
4611 -
4612 -       case MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK:
4613 -       /*
4614 -        * look up qtag in the ScsiLookup[] table
4615 -        */
4616 -               for (i = 0, found_qtag = 0; i < hd->ioc->req_depth; i++) {
4617 -#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0))
4618 -                       if ((hd->ScsiLookup[i]) &&
4619 -                           (hd->ScsiLookup[i]->tag == queueTag)) {
4620 -#else
4621 -                       if ((ioc->ScsiLookup[i]) &&
4622 -                           (ioc->ScsiLookup[i]->tag == queueTag)) {
4623 -#endif
4624 -                               mf = MPT_INDEX_2_MFPTR(hd->ioc, i);
4625 -                               msgContext =
4626 -                                   mf->u.frame.hwhdr.msgctxu.MsgContext;
4627 -                               found_qtag=1;
4628 -                               break;
4629 -                       }
4630 -               }
4631 -
4632 -               if(!found_qtag)
4633 -                       goto cim_get_task_managment_exit;
4634 -
4635 -       case MPI_SCSITASKMGMT_TASKTYPE_LOGICAL_UNIT_RESET:
4636 -       case MPI_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET:
4637 -       case MPI_SCSITASKMGMT_TASKTYPE_CLEAR_TASK_SET:
4638 -       /* for now, this should work
4639 -        */
4640 -       case MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET:
4641 -
4642 -               /* Single threading ....
4643 -                */
4644 -#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0))
4645 -               if (mptctl_set_tm_flags(hd) != 0) {
4646 -                       karg.IoctlHeader.ReturnCode =
4647 -                           CSMI_SAS_STATUS_FAILED;
4648 -                       goto cim_get_task_managment_exit;
4649 -               }
4650 -#endif
4651 -
4652 -               /* Send request
4653 -                */
4654 -               if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
4655 -                       dcsmisasprintk((": no msg frames!\n"));
4656 -#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0))
4657 -                       mptctl_free_tm_flags(ioc);
4658 -#endif
4659 -                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
4660 -                       goto cim_get_task_managment_exit;
4661 -               }
4662 -
4663 -               mpi_hdr = (MPIHeader_t *) mf;
4664 -               pScsiTm = (pSCSITaskMgmt_t ) mf;
4665 -
4666 -               memset(pScsiTm,0,sizeof(SCSITaskMgmt_t));
4667 -               pScsiTm->TaskType = taskType;
4668 -               pScsiTm->Bus = channel;
4669 -               pScsiTm->TargetID = id;
4670 -#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,15))
4671 -               int_to_scsilun(karg.Parameters.bLun,
4672 -                   (struct scsi_lun *)pScsiTm->LUN);
4673 -#else
4674 -               pScsiTm->LUN[1] = karg.Parameters.bLun;
4675 -#endif
4676 -               pScsiTm->MsgContext = mpi_hdr->MsgContext;
4677 -               pScsiTm->TaskMsgContext = msgContext;
4678 -               pScsiTm->Function = MPI_FUNCTION_SCSI_TASK_MGMT;
4679 -
4680 -               if (csmisas_send_handshake_wait(ioc, mf,
4681 -                   karg.IoctlHeader.Timeout) != 0)  {
4682 -                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
4683 -                       goto cim_get_task_managment_exit;
4684 -               }
4685 -
4686 -               if (ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) {
4687 -
4688 -                       pScsiTmReply =
4689 -                           (pSCSITaskMgmtReply_t ) ioc->ioctl->ReplyFrame;
4690 -
4691 -                       ioc_status = le16_to_cpu(pScsiTmReply->IOCStatus)
4692 -                           & MPI_IOCSTATUS_MASK;
4693 -
4694 -                       memset(&karg.Status,0,
4695 -                           sizeof(CSMI_SAS_SSP_PASSTHRU_STATUS));
4696 -
4697 -                       if(ioc_status == MPI_IOCSTATUS_SUCCESS) {
4698 -                               karg.IoctlHeader.ReturnCode =
4699 -                                   CSMI_SAS_STATUS_SUCCESS;
4700 -                               karg.Status.bSSPStatus =
4701 -                                   CSMI_SAS_SSP_STATUS_COMPLETED;
4702 -                       }else if(ioc_status == MPI_IOCSTATUS_INSUFFICIENT_RESOURCES) {
4703 -                               karg.IoctlHeader.ReturnCode =
4704 -                                   CSMI_SAS_STATUS_SUCCESS;
4705 -                               karg.Status.bSSPStatus =
4706 -                                   CSMI_SAS_SSP_STATUS_RETRY;
4707 -                       }else {
4708 -                               karg.IoctlHeader.ReturnCode =
4709 -                                   CSMI_SAS_STATUS_FAILED;
4710 -                               karg.Status.bSSPStatus =
4711 -                                   CSMI_SAS_SSP_STATUS_FATAL_ERROR;
4712 -                       }
4713 -               } else
4714 -                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
4715 -
4716 -               break;
4717 -
4718 -       default:
4719 -               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
4720 -               break;
4721 -       }
4722 -
4723 -
4724 - cim_get_task_managment_exit:
4725 -
4726 -       /* Copy the data from kernel memory to user memory
4727 -        */
4728 -       if (copy_to_user((char *)arg, &karg,
4729 -                               sizeof(CSMI_SAS_SSP_TASK_IU_BUFFER))) {
4730 -               printk(KERN_ERR "%s@%d::%s() - "
4731 -                       "Unable to write out csmi_sas_task_managment @ %p\n",
4732 -                               __FILE__, __LINE__, __FUNCTION__, uarg);
4733 -               return -EFAULT;
4734 -       }
4735 -
4736 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
4737 -       return 0;
4738 -}
4739 -
4740 -/**
4741 - *     map_sas_status_to_csmi - Conversion  for Connection Status
4742 - *     @mpi_sas_status: Sas status returned by the firmware
4743 - *
4744 - *     Returns converted connection status
4745 - *
4746 - **/
4747 -static u8
4748 -map_sas_status_to_csmi(u8 mpi_sas_status)
4749 -{
4750 -       u8  csmi_connect_status;
4751 -
4752 -       switch (mpi_sas_status) {
4753 -
4754 -       case MPI_SASSTATUS_SUCCESS:
4755 -               csmi_connect_status = CSMI_SAS_OPEN_ACCEPT;
4756 -               break;
4757 -
4758 -       case MPI_SASSTATUS_UTC_BAD_DEST:
4759 -               csmi_connect_status = CSMI_SAS_OPEN_REJECT_BAD_DESTINATION;
4760 -               break;
4761 -
4762 -       case MPI_SASSTATUS_UTC_CONNECT_RATE_NOT_SUPPORTED:
4763 -               csmi_connect_status = CSMI_SAS_OPEN_REJECT_RATE_NOT_SUPPORTED;
4764 -               break;
4765 -
4766 -       case MPI_SASSTATUS_UTC_PROTOCOL_NOT_SUPPORTED:
4767 -               csmi_connect_status =
4768 -                   CSMI_SAS_OPEN_REJECT_PROTOCOL_NOT_SUPPORTED;
4769 -               break;
4770 -
4771 -       case MPI_SASSTATUS_UTC_STP_RESOURCES_BUSY:
4772 -               csmi_connect_status = CSMI_SAS_OPEN_REJECT_STP_RESOURCES_BUSY;
4773 -               break;
4774 -
4775 -       case MPI_SASSTATUS_UTC_WRONG_DESTINATION:
4776 -               csmi_connect_status = CSMI_SAS_OPEN_REJECT_WRONG_DESTINATION;
4777 -               break;
4778 -
4779 -       case MPI_SASSTATUS_SDSF_NAK_RECEIVED:
4780 -               csmi_connect_status = CSMI_SAS_OPEN_REJECT_RETRY;
4781 -               break;
4782 -
4783 -       case MPI_SASSTATUS_SDSF_CONNECTION_FAILED:
4784 -               csmi_connect_status = CSMI_SAS_OPEN_REJECT_PATHWAY_BLOCKED;
4785 -               break;
4786 -
4787 -       case MPI_SASSTATUS_INITIATOR_RESPONSE_TIMEOUT:
4788 -               csmi_connect_status =  CSMI_SAS_OPEN_REJECT_NO_DESTINATION;
4789 -               break;
4790 -
4791 -       case MPI_SASSTATUS_UNKNOWN_ERROR:
4792 -       case MPI_SASSTATUS_INVALID_FRAME:
4793 -       case MPI_SASSTATUS_UTC_BREAK_RECEIVED:
4794 -       case MPI_SASSTATUS_UTC_PORT_LAYER_REQUEST:
4795 -       case MPI_SASSTATUS_SHORT_INFORMATION_UNIT:
4796 -       case MPI_SASSTATUS_LONG_INFORMATION_UNIT:
4797 -       case MPI_SASSTATUS_XFER_RDY_INCORRECT_WRITE_DATA:
4798 -       case MPI_SASSTATUS_XFER_RDY_REQUEST_OFFSET_ERROR:
4799 -       case MPI_SASSTATUS_XFER_RDY_NOT_EXPECTED:
4800 -       case MPI_SASSTATUS_DATA_INCORRECT_DATA_LENGTH:
4801 -       case MPI_SASSTATUS_DATA_TOO_MUCH_READ_DATA:
4802 -       case MPI_SASSTATUS_DATA_OFFSET_ERROR:
4803 -               csmi_connect_status = CSMI_SAS_OPEN_REJECT_RESERVE_STOP;
4804 -               break;
4805 -
4806 -       default:
4807 -               csmi_connect_status = CSMI_SAS_OPEN_REJECT_RESERVE_STOP;
4808 -               break;
4809 -       }
4810 -
4811 -       return csmi_connect_status;
4812 -}
4813 -
4814 -/**
4815 - *                      csmisas_phy_reset
4816 - *     Issues a phy link reset or phy hard reset
4817 - *
4818 - *     @ioc - Pointer to MPT_ADAPTER structure
4819 - *     @PhyNum - phy number
4820 - *     @opcode - {MPI_SAS_OP_PHY_LINK_RESET,MPI_SAS_OP_PHY_HARD_RESET}
4821 - *
4822 - *     Returns: 0 for success, non-zero error
4823 - **/
4824 -static int
4825 -csmisas_phy_reset(MPT_ADAPTER *ioc, u8 PhyNum, u8 opcode)
4826 -{
4827 -       SasIoUnitControlRequest_t       *sasIoUnitCntrReq;
4828 -       SasIoUnitControlReply_t         *sasIoUnitCntrReply;
4829 -       MPT_FRAME_HDR                   *mf = NULL;
4830 -       MPIHeader_t                     *mpi_hdr;
4831 -       u16                             ioc_status;
4832 -
4833 -       if ((opcode != MPI_SAS_OP_PHY_LINK_RESET) &&
4834 -           (opcode != MPI_SAS_OP_PHY_HARD_RESET))
4835 -           return -1;
4836 -
4837 -       /* Get a MF for this command.
4838 -        */
4839 -       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
4840 -               dcsmisasprintk((": no msg frames!\n"));
4841 -               return -1;
4842 -        }
4843 -
4844 -       mpi_hdr = (MPIHeader_t *) mf;
4845 -       sasIoUnitCntrReq = (SasIoUnitControlRequest_t *)mf;
4846 -       memset(sasIoUnitCntrReq,0,sizeof(SasIoUnitControlRequest_t));
4847 -       sasIoUnitCntrReq->Function = MPI_FUNCTION_SAS_IO_UNIT_CONTROL;
4848 -       sasIoUnitCntrReq->MsgContext = mpi_hdr->MsgContext;
4849 -       sasIoUnitCntrReq->Operation = opcode;
4850 -       sasIoUnitCntrReq->PhyNum = PhyNum;
4851 -
4852 -       if (csmisas_send_command_wait(ioc, mf, MPT_IOCTL_DEFAULT_TIMEOUT) != 0)
4853 -               return -1;
4854 -
4855 -       if ((ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) == 0)
4856 -               return -1;
4857 -
4858 -       /* process the completed Reply Message Frame */
4859 -       sasIoUnitCntrReply = (SasIoUnitControlReply_t *)ioc->ioctl->ReplyFrame;
4860 -       ioc_status = le16_to_cpu(sasIoUnitCntrReply->IOCStatus)
4861 -           & MPI_IOCSTATUS_MASK;
4862 -       if (ioc_status != MPI_IOCSTATUS_SUCCESS) {
4863 -               printk("%s: IOCStatus=0x%X IOCLogInfo=0x%X\n",
4864 -                   __FUNCTION__,
4865 -                   sasIoUnitCntrReply->IOCStatus,
4866 -                   sasIoUnitCntrReply->IOCLogInfo);
4867 -               return -1;
4868 -       }
4869 -       return 0;
4870 -}
4871 -
4872 -/** Prototype Routine for the CSMI SAS Phy Control command.
4873 - *
4874 - * Outputs:    None.
4875 - * Return:     0 if successful
4876 - *             -EFAULT if data unavailable
4877 - *             -ENODEV if no such device/adapter
4878 - **/
4879 -static int
4880 -csmisas_phy_control(unsigned long arg)
4881 -{
4882 -       CSMI_SAS_PHY_CONTROL_BUFFER __user *uarg = (void __user *) arg;
4883 -       IOCTL_HEADER                    ioctl_header;
4884 -       PCSMI_SAS_PHY_CONTROL_BUFFER    karg;
4885 -       SasIOUnitPage0_t                *sasIoUnitPg0=NULL;
4886 -       dma_addr_t                      sasIoUnitPg0_dma;
4887 -       int                             sasIoUnitPg0_data_sz=0;
4888 -       SasIOUnitPage1_t                *sasIoUnitPg1=NULL;
4889 -       dma_addr_t                      sasIoUnitPg1_dma;
4890 -       int                             sasIoUnitPg1_data_sz=0;
4891 -       ConfigExtendedPageHeader_t      hdr;
4892 -       CONFIGPARMS                     cfg;
4893 -       MPT_ADAPTER                     *ioc = NULL;
4894 -       int                             iocnum;
4895 -       int                             csmi_sas_phy_control_buffer_sz;
4896 -       int                             memory_pages;
4897 -
4898 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
4899 -
4900 -       if (copy_from_user(&ioctl_header, uarg, sizeof(IOCTL_HEADER))) {
4901 -               printk(KERN_ERR "%s@%d::%s() - "
4902 -                   "Unable to read in IOCTL_HEADER"
4903 -                   "struct @ %p\n", __FILE__, __LINE__, __FUNCTION__, uarg);
4904 -               return -EFAULT;
4905 -       }
4906 -
4907 -       csmi_sas_phy_control_buffer_sz = ioctl_header.Length;
4908 -       memory_pages = get_order(csmi_sas_phy_control_buffer_sz);
4909 -       karg = (PCSMI_SAS_PHY_CONTROL_BUFFER)__get_free_pages(
4910 -               GFP_KERNEL, memory_pages);
4911 -       if (!karg){
4912 -               printk(KERN_ERR "%s@%d::%s() - "
4913 -                   "Unable to malloc SAS_PHY_CONTROL_BUFFER "
4914 -                       "csmi_sas_phy_control_buffer_sz=%d memory_pages=%d\n",
4915 -                       __FILE__, __LINE__, __FUNCTION__,
4916 -                       csmi_sas_phy_control_buffer_sz, memory_pages);
4917 -               return -ENOMEM;
4918 -       }
4919 -       memset(karg, 0, sizeof(*karg));
4920 -
4921 -       if (copy_from_user(karg, uarg, csmi_sas_phy_control_buffer_sz)) {
4922 -               printk(KERN_ERR "%s@%d::%s() - "
4923 -                   "Unable to read in csmi_sas_phy_control_buffer "
4924 -                   "struct @ %p\n", __FILE__, __LINE__, __FUNCTION__, uarg);
4925 -               free_pages((unsigned long)karg, memory_pages);
4926 -               return -EFAULT;
4927 -       }
4928 -
4929 -       if (((iocnum = mpt_verify_adapter(ioctl_header.IOControllerNumber,
4930 -           &ioc)) < 0) || (ioc == NULL)) {
4931 -               dcsmisasprintk((KERN_ERR
4932 -               "%s::%s() @%d - ioc%d not found!\n",
4933 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4934 -               free_pages((unsigned long)karg, memory_pages);
4935 -               return -ENODEV;
4936 -       }
4937 -
4938 -       if (!csmisas_is_this_sas_cntr(ioc)) {
4939 -               dcsmisasprintk((KERN_ERR
4940 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
4941 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
4942 -               free_pages((unsigned long)karg, memory_pages);
4943 -               return -ENODEV;
4944 -       }
4945 -
4946 -       if (karg->bPhyIdentifier >= ioc->num_ports) {
4947 -               karg->IoctlHeader.ReturnCode =
4948 -                  CSMI_SAS_STATUS_INVALID_PARAMETER;
4949 -               goto cim_sas_phy_control_exit;
4950 -       }
4951 -
4952 -       /*
4953 -        *  Retreive SAS IOUNIT PAGE 0
4954 -        */
4955 -
4956 -       hdr.PageVersion = MPI_SASIOUNITPAGE0_PAGEVERSION;
4957 -       hdr.ExtPageLength = 0;
4958 -       hdr.PageNumber = 0;
4959 -       hdr.Reserved1 = 0;
4960 -       hdr.Reserved2 = 0;
4961 -       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
4962 -       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_IO_UNIT;
4963 -
4964 -       cfg.cfghdr.ehdr = &hdr;
4965 -       cfg.physAddr = -1;
4966 -       cfg.pageAddr = 0;
4967 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
4968 -       cfg.dir = 0;    /* read */
4969 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
4970 -
4971 -       if (mpt_config(ioc, &cfg) != 0) {
4972 -               dcsmisasprintk((
4973 -                   ": FAILED: READ MPI_SASIOUNITPAGE0: HEADER\n"));
4974 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
4975 -               goto cim_sas_phy_control_exit;
4976 -       }
4977 -
4978 -       if (hdr.ExtPageLength == 0) {
4979 -               dcsmisasprintk((": hdr.ExtPageLength == 0\n"));
4980 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
4981 -               goto cim_sas_phy_control_exit;
4982 -       }
4983 -
4984 -       sasIoUnitPg0_data_sz = hdr.ExtPageLength * 4;
4985 -       sasIoUnitPg0 = (SasIOUnitPage0_t *) pci_alloc_consistent(ioc->pcidev,
4986 -           sasIoUnitPg0_data_sz, &sasIoUnitPg0_dma);
4987 -
4988 -       if (!sasIoUnitPg0) {
4989 -               dcsmisasprintk((": pci_alloc_consistent: FAILED\n"));
4990 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
4991 -               goto cim_sas_phy_control_exit;
4992 -       }
4993 -
4994 -       memset((u8 *)sasIoUnitPg0, 0, sasIoUnitPg0_data_sz);
4995 -       cfg.physAddr = sasIoUnitPg0_dma;
4996 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
4997 -
4998 -       if (mpt_config(ioc, &cfg) != 0) {
4999 -               dcsmisasprintk((
5000 -                   ": FAILED: READ MPI_SASIOUNITPAGE0: CURRENT\n"));
5001 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
5002 -               goto cim_sas_phy_control_exit;
5003 -       }
5004 -
5005 -       /*
5006 -        *  Retreive SAS IOUNIT PAGE 1
5007 -        */
5008 -
5009 -       hdr.PageVersion = MPI_SASIOUNITPAGE0_PAGEVERSION;
5010 -       hdr.ExtPageLength = 0;
5011 -       hdr.PageNumber = 1;
5012 -       hdr.Reserved1 = 0;
5013 -       hdr.Reserved2 = 0;
5014 -       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
5015 -       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_IO_UNIT;
5016 -
5017 -       cfg.cfghdr.ehdr = &hdr;
5018 -       cfg.physAddr = -1;
5019 -       cfg.pageAddr = 0;
5020 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5021 -       cfg.dir = 0;    /* read */
5022 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
5023 -
5024 -       if (mpt_config(ioc, &cfg) != 0) {
5025 -               dcsmisasprintk((
5026 -                   ": FAILED: READ MPI_SASIOUNITPAGE1: HEADER\n"));
5027 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
5028 -               goto cim_sas_phy_control_exit;
5029 -       }
5030 -
5031 -       if (hdr.ExtPageLength == 0) {
5032 -               dcsmisasprintk((": hdr.ExtPageLength == 0\n"));
5033 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
5034 -               goto cim_sas_phy_control_exit;
5035 -       }
5036 -
5037 -       sasIoUnitPg1_data_sz = hdr.ExtPageLength * 4;
5038 -       sasIoUnitPg1 = (SasIOUnitPage1_t *) pci_alloc_consistent(ioc->pcidev,
5039 -           sasIoUnitPg1_data_sz, &sasIoUnitPg1_dma);
5040 -
5041 -       if (!sasIoUnitPg1) {
5042 -               dcsmisasprintk((": pci_alloc_consistent: FAILED\n"));
5043 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
5044 -               goto cim_sas_phy_control_exit;
5045 -       }
5046 -
5047 -       memset((u8 *)sasIoUnitPg1, 0, sasIoUnitPg1_data_sz);
5048 -       cfg.physAddr = sasIoUnitPg1_dma;
5049 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5050 -
5051 -       if (mpt_config(ioc, &cfg) != 0) {
5052 -               dcsmisasprintk((
5053 -                   ": FAILED:  READ MPI_SASIOUNITPAGE1: CURRENT\n"));
5054 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
5055 -               goto cim_sas_phy_control_exit;
5056 -       }
5057 -
5058 -       switch (karg->uFunction) {
5059 -
5060 -       case CSMI_SAS_PC_LINK_RESET:
5061 -       case CSMI_SAS_PC_HARD_RESET:
5062 -       {
5063 -               u8 opcode = (karg->uFunction==CSMI_SAS_PC_LINK_RESET) ?
5064 -                   MPI_SAS_OP_PHY_LINK_RESET : MPI_SAS_OP_PHY_HARD_RESET;
5065 -
5066 -               if((karg->uLinkFlags & CSMI_SAS_PHY_ACTIVATE_CONTROL) &&
5067 -                   (karg->usLengthOfControl >= sizeof(CSMI_SAS_PHY_CONTROL)) &&
5068 -                   (karg->bNumberOfControls > 0)){
5069 -                       if(karg->Control[0].bRate ==
5070 -                          CSMI_SAS_LINK_RATE_1_5_GBPS) {
5071 -                               sasIoUnitPg1->PhyData[karg->bPhyIdentifier].MaxMinLinkRate =
5072 -                               MPI_SAS_IOUNIT1_MAX_RATE_1_5 |
5073 -                               MPI_SAS_IOUNIT1_MIN_RATE_1_5;
5074 -                       }
5075 -                       else if(karg->Control[0].bRate ==
5076 -                          CSMI_SAS_LINK_RATE_3_0_GBPS) {
5077 -                               sasIoUnitPg1->PhyData[karg->bPhyIdentifier].MaxMinLinkRate =
5078 -                               MPI_SAS_IOUNIT1_MAX_RATE_3_0 |
5079 -                               MPI_SAS_IOUNIT1_MIN_RATE_3_0;
5080 -                       }
5081 -                       sasIoUnitPg1->PhyData[karg->bPhyIdentifier].PhyFlags &=
5082 -                           ~MPI_SAS_IOUNIT1_PHY_FLAGS_PHY_DISABLE;
5083 -                       cfg.dir = 1;
5084 -                       cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_NVRAM;
5085 -                       if (mpt_config(ioc, &cfg) != 0) {
5086 -                               dcsmisasprintk((
5087 -                           ": FAILED: WRITE MPI_SASIOUNITPAGE1 NVRAM\n"));
5088 -                               karg->IoctlHeader.ReturnCode =
5089 -                                  CSMI_SAS_STATUS_FAILED;
5090 -                               goto cim_sas_phy_control_exit;
5091 -                       }
5092 -                       cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_CURRENT;
5093 -                       if (mpt_config(ioc, &cfg) != 0) {
5094 -                               dcsmisasprintk((
5095 -                        ": FAILED: WRITE MPI_SASIOUNITPAGE1 CURRENT\n"));
5096 -                               karg->IoctlHeader.ReturnCode =
5097 -                                  CSMI_SAS_STATUS_FAILED;
5098 -                               goto cim_sas_phy_control_exit;
5099 -                       }
5100 -               }
5101 -               if (csmisas_phy_reset(ioc,
5102 -                   karg->bPhyIdentifier, opcode) != 0) {
5103 -                       dcsmisasprintk((
5104 -                           ": FAILED: csmisas_phy_reset\n"));
5105 -                       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
5106 -                       goto cim_sas_phy_control_exit;
5107 -               }
5108 -               break;
5109 -
5110 -       }
5111 -       case CSMI_SAS_PC_PHY_DISABLE:
5112 -               if(karg->usLengthOfControl || karg->bNumberOfControls) {
5113 -                       karg->IoctlHeader.ReturnCode =
5114 -                           CSMI_SAS_STATUS_INVALID_PARAMETER;
5115 -                       break;
5116 -               }
5117 -               sasIoUnitPg1->PhyData[karg->bPhyIdentifier].PhyFlags |=
5118 -                   MPI_SAS_IOUNIT1_PHY_FLAGS_PHY_DISABLE;
5119 -               cfg.dir = 1;
5120 -               cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_NVRAM;
5121 -               if (mpt_config(ioc, &cfg) != 0) {
5122 -                       dcsmisasprintk((
5123 -                           ": FAILED: WRITE MPI_SASIOUNITPAGE1 NVRAM\n"));
5124 -                       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
5125 -                       goto cim_sas_phy_control_exit;
5126 -               }
5127 -               cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_CURRENT;
5128 -               if (mpt_config(ioc, &cfg) != 0) {
5129 -                       dcsmisasprintk((
5130 -                           ": FAILED: WRITE MPI_SASIOUNITPAGE1 CURRENT\n"));
5131 -                       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
5132 -                       goto cim_sas_phy_control_exit;
5133 -               }
5134 -               if (csmisas_phy_reset(ioc,
5135 -                   karg->bPhyIdentifier, MPI_SAS_OP_PHY_HARD_RESET) != 0) {
5136 -                       dcsmisasprintk((
5137 -                           ": FAILED: csmisas_phy_reset\n"));
5138 -                       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
5139 -                       goto cim_sas_phy_control_exit;
5140 -               }
5141 -               break;
5142 -
5143 -       case CSMI_SAS_PC_GET_PHY_SETTINGS:
5144 -               if(karg->usLengthOfControl || karg->bNumberOfControls) {
5145 -                       karg->IoctlHeader.ReturnCode =
5146 -                           CSMI_SAS_STATUS_INVALID_PARAMETER;
5147 -                       break;
5148 -               }
5149 -               if(csmi_sas_phy_control_buffer_sz <
5150 -                   offsetof(CSMI_SAS_PHY_CONTROL_BUFFER,Control) +
5151 -                   (4* sizeof(CSMI_SAS_PHY_CONTROL))) {
5152 -                       karg->IoctlHeader.ReturnCode =
5153 -                           CSMI_SAS_STATUS_INVALID_PARAMETER;
5154 -                       break;
5155 -               }
5156 -               karg->usLengthOfControl = sizeof(CSMI_SAS_PHY_CONTROL);
5157 -               karg->bNumberOfControls = 4;
5158 -               karg->Control[0].bType = CSMI_SAS_SAS;
5159 -               karg->Control[0].bRate = CSMI_SAS_LINK_RATE_1_5_GBPS;
5160 -               karg->Control[1].bType = CSMI_SAS_SAS;
5161 -               karg->Control[1].bRate = CSMI_SAS_LINK_RATE_3_0_GBPS;
5162 -               karg->Control[2].bType = CSMI_SAS_SATA;
5163 -               karg->Control[2].bRate = CSMI_SAS_LINK_RATE_1_5_GBPS;
5164 -               karg->Control[3].bType = CSMI_SAS_SATA;
5165 -               karg->Control[3].bRate = CSMI_SAS_LINK_RATE_3_0_GBPS;
5166 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
5167 -               break;
5168 -       default:
5169 -               break;
5170 -       }
5171 -
5172 - cim_sas_phy_control_exit:
5173 -
5174 -       if (sasIoUnitPg0)
5175 -               pci_free_consistent(ioc->pcidev, sasIoUnitPg0_data_sz,
5176 -                   (u8 *) sasIoUnitPg0, sasIoUnitPg0_dma);
5177 -
5178 -       if (sasIoUnitPg1)
5179 -               pci_free_consistent(ioc->pcidev, sasIoUnitPg1_data_sz,
5180 -                   (u8 *) sasIoUnitPg1, sasIoUnitPg1_dma);
5181 -
5182 -       /* Copy the data from kernel memory to user memory
5183 -        */
5184 -       if (copy_to_user((char *)arg,karg,csmi_sas_phy_control_buffer_sz)) {
5185 -               printk(KERN_ERR "%s@%d::%s() - "
5186 -                   "Unable to write out csmi_sas_phy_control_buffer @ %p\n",
5187 -                   __FILE__, __LINE__, __FUNCTION__, uarg);
5188 -               free_pages((unsigned long)karg, memory_pages);
5189 -               return -EFAULT;
5190 -       }
5191 -
5192 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
5193 -       free_pages((unsigned long)karg, memory_pages);
5194 -       return 0;
5195 -}
5196 -
5197 -/**
5198 - *     csmisas_get_manuf_pg_7 - Fetch Manufacturing config Page7.
5199 - * @ioc: Pointer to MPT_ADAPTER structure
5200 - * @mfgpage7_buffer: pointer to ManufacturingPage7_t that returns config
5201 - *                    page data
5202 - * @mfg_size - max size of buffer
5203 - *
5204 - *     Return: 0 for success
5205 - *     -ENOMEM if no memory available
5206 - *             -EPERM if not allowed due to ISR context
5207 - *             -EAGAIN if no msg frames currently available
5208 - *             -EFAULT for non-successful reply or no reply (timeout)
5209 - **/
5210 -static int
5211 -csmisas_get_manuf_pg_7(MPT_ADAPTER *ioc, ManufacturingPage7_t *mfgpage7_buffer, int mfg_size)
5212 -{
5213 -       ConfigPageHeader_t hdr;
5214 -       CONFIGPARMS     cfg;
5215 -       ManufacturingPage7_t *mfgPage7 = NULL;
5216 -       dma_addr_t      mfgPage7_dma;
5217 -       int             data_sz = 0;
5218 -       int             rc;
5219 -
5220 -       /* Get Manufacturing Page 7 header */
5221 -       hdr.PageVersion = MPI_MANUFACTURING0_PAGEVERSION;
5222 -       hdr.PageLength = 0;
5223 -       hdr.PageNumber = 7;
5224 -       hdr.PageType = MPI_CONFIG_PAGETYPE_MANUFACTURING;
5225 -       cfg.cfghdr.hdr = &hdr;
5226 -       cfg.physAddr = -1;
5227 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5228 -       cfg.dir = 0;
5229 -       cfg.pageAddr = 0;
5230 -       cfg.timeout = 0;
5231 -
5232 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
5233 -               goto csmisas_get_manuf_pg_7_exit;
5234 -
5235 -       if (hdr.PageLength == 0) {
5236 -               rc = -EFAULT;
5237 -               goto csmisas_get_manuf_pg_7_exit;
5238 -       }
5239 -
5240 -       data_sz = hdr.PageLength * 4;
5241 -       mfgPage7 = pci_alloc_consistent(ioc->pcidev, data_sz, &mfgPage7_dma);
5242 -       if (!mfgPage7) {
5243 -               rc = -ENOMEM;
5244 -               goto csmisas_get_manuf_pg_7_exit;
5245 -       }
5246 -
5247 -       memset((u8 *)mfgPage7, 0, data_sz);
5248 -       cfg.physAddr = mfgPage7_dma;
5249 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5250 -
5251 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
5252 -               goto csmisas_get_manuf_pg_7_exit;
5253 -
5254 -       /* copy buffer back to user */
5255 -       memcpy(mfgpage7_buffer, mfgPage7, min(data_sz, mfg_size));
5256 -
5257 - csmisas_get_manuf_pg_7_exit:
5258 -
5259 -       if (mfgPage7)
5260 -               pci_free_consistent(ioc->pcidev, data_sz, (u8 *)mfgPage7,
5261 -                   mfgPage7_dma);
5262 -
5263 -       return rc;
5264 -}
5265 -
5266 -/**
5267 - * Prototype Routine for the CSMI SAS Get Connector info command.
5268 - *
5269 - * Outputs:    None.
5270 - * Return:     0 if successful
5271 - *             -EFAULT if data unavailable
5272 - *             -ENODEV if no such device/adapter
5273 - **/
5274 -static int
5275 -csmisas_get_connector_info(unsigned long arg)
5276 -{
5277 -       CSMI_SAS_CONNECTOR_INFO_BUFFER __user *uarg = (void __user *) arg;
5278 -       CSMI_SAS_CONNECTOR_INFO_BUFFER   karg;
5279 -       MPT_ADAPTER                     *ioc = NULL;
5280 -       ManufacturingPage7_t            *mfgPg7 = NULL;
5281 -       int                             mfgPg7_sz;
5282 -       int                             iocnum;
5283 -       int                             i;
5284 -
5285 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
5286 -
5287 -       if (copy_from_user(&karg, uarg,
5288 -               sizeof(CSMI_SAS_CONNECTOR_INFO_BUFFER))) {
5289 -               printk(KERN_ERR "%s@%d::%s() - "
5290 -                  "Unable to read in csmi_sas_connector_info_buffer"
5291 -                  " struct @ %p\n",
5292 -                  __FILE__, __LINE__, __FUNCTION__, uarg);
5293 -               return -EFAULT;
5294 -       }
5295 -
5296 -       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
5297 -           &ioc)) < 0) || (ioc == NULL)) {
5298 -               dcsmisasprintk((KERN_ERR
5299 -               "%s::%s() @%d - ioc%d not found!\n",
5300 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
5301 -               return -ENODEV;
5302 -       }
5303 -
5304 -       if (!csmisas_is_this_sas_cntr(ioc)) {
5305 -               dcsmisasprintk((KERN_ERR
5306 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
5307 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
5308 -               return -ENODEV;
5309 -       }
5310 -
5311 -       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
5312 -
5313 -       /* `32` is the sizeof MPI_MANPAGE7_CONNECTOR_INFO */
5314 -       for (i = 0; i < 32; i++) {
5315 -               karg.Reference[i].uPinout = CSMI_SAS_CON_UNKNOWN;
5316 -               strcpy(karg.Reference[i].bConnector,"");
5317 -               karg.Reference[i].bLocation = CSMI_SAS_CON_UNKNOWN;
5318 -       }
5319 -
5320 -       mfgPg7_sz = offsetof(CONFIG_PAGE_MANUFACTURING_7,ConnectorInfo) +
5321 -           (ioc->num_ports * sizeof(MPI_MANPAGE7_CONNECTOR_INFO));
5322 -       mfgPg7 = kmalloc(mfgPg7_sz, GFP_KERNEL);
5323 -       if (!mfgPg7){
5324 -               printk(KERN_ERR "%s@%d::%s() - "
5325 -                   "Unable to malloc @ %p\n",
5326 -                   __FILE__, __LINE__, __FUNCTION__, mfgPg7);
5327 -               return -EFAULT;
5328 -       }
5329 -       memset(mfgPg7, 0, mfgPg7_sz);
5330 -
5331 -       if (!csmisas_get_manuf_pg_7(ioc, mfgPg7, mfgPg7_sz)) {
5332 -               for (i = 0; i < ioc->num_ports; i++) {
5333 -                       karg.Reference[i].uPinout =
5334 -                           le32_to_cpu(mfgPg7->ConnectorInfo[i].Pinout);
5335 -                       /*endian conversion , this is u8 * 16 ?? */
5336 -                       strncpy(karg.Reference[i].bConnector,
5337 -                           mfgPg7->ConnectorInfo[i].Connector, 16);
5338 -                       karg.Reference[i].bLocation =
5339 -                           mfgPg7->ConnectorInfo[i].Location;
5340 -               }
5341 -       }
5342 -
5343 -       kfree(mfgPg7);
5344 -
5345 -       /* Copy the data from kernel memory to user memory
5346 -        */
5347 -       if (copy_to_user((char *)arg, &karg,
5348 -               sizeof(CSMI_SAS_CONNECTOR_INFO_BUFFER))) {
5349 -               printk(KERN_ERR "%s@%d::%s() - "
5350 -               "Unable to write out csmi_sas_connector_info_buffer @"
5351 -              "%p\n",
5352 -               __FILE__, __LINE__, __FUNCTION__, uarg);
5353 -               return -EFAULT;
5354 -       }
5355 -
5356 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
5357 -       return 0;
5358 -}
5359 -
5360 -/**
5361 - *                 csmisas_fill_location_data
5362 - *
5363 - * Outputs:    None.
5364 - * Return:     0 if successful
5365 - **/
5366 -static int
5367 -csmisas_fill_location_data(MPT_ADAPTER *ioc, u8 bus, u8 id, u8 opcode,
5368 -       CSMI_SAS_LOCATION_IDENTIFIER * location_ident)
5369 -{
5370 -
5371 -       ConfigExtendedPageHeader_t      hdr;
5372 -       CONFIGPARMS                     cfg;
5373 -       int                             rc;
5374 -       SasDevicePage0_t                *sasDevicePg0=NULL;
5375 -       SasEnclosurePage0_t             *sasEnclosurePg0=NULL;
5376 -       dma_addr_t                      sasDevicePg0_dma,sasEnclosurePg0_dma;
5377 -       int                             sasDevicePg0_data_sz=0;
5378 -       int                             sasEnclosurePg0_data_sz=0;
5379 -       u64                             sas_address;
5380 -
5381 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
5382 -       memset (location_ident, 0, sizeof(*location_ident));
5383 -
5384 -       /* SAS Device Page 0 */
5385 -       hdr.PageVersion = MPI_SASDEVICE0_PAGEVERSION;
5386 -       hdr.ExtPageLength = 0;
5387 -       hdr.PageNumber = 0;
5388 -       hdr.Reserved1 = 0;
5389 -       hdr.Reserved2 = 0;
5390 -       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
5391 -       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_DEVICE;
5392 -
5393 -       cfg.cfghdr.ehdr = &hdr;
5394 -       cfg.physAddr = -1;
5395 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5396 -       cfg.dir = 0;    /* read */
5397 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
5398 -
5399 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
5400 -               rc=-1;
5401 -               goto fill_location_data_exit;
5402 -       }
5403 -
5404 -       if (hdr.ExtPageLength == 0) {
5405 -               rc=-1;
5406 -               goto fill_location_data_exit;
5407 -       }
5408 -
5409 -       sasDevicePg0_data_sz = hdr.ExtPageLength * 4;
5410 -       sasDevicePg0 = (SasDevicePage0_t *) pci_alloc_consistent(
5411 -           ioc->pcidev, sasDevicePg0_data_sz, &sasDevicePg0_dma);
5412 -       if (!sasDevicePg0) {
5413 -               rc=-1;
5414 -               goto fill_location_data_exit;
5415 -       }
5416 -
5417 -       memset((u8 *)sasDevicePg0, 0, sasDevicePg0_data_sz);
5418 -       cfg.physAddr = sasDevicePg0_dma;
5419 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5420 -       cfg.pageAddr = (bus << 8) + id
5421 -           + (MPI_SAS_DEVICE_PGAD_FORM_BUS_TARGET_ID <<
5422 -                       MPI_SAS_DEVICE_PGAD_FORM_SHIFT);
5423 -
5424 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
5425 -               rc=-1;
5426 -               goto fill_location_data_exit;
5427 -       }
5428 -
5429 -       location_ident->bLocationFlags |= CSMI_SAS_LOCATE_SAS_ADDRESS_VALID;
5430 -       memcpy(&sas_address, &sasDevicePg0->SASAddress, sizeof(u64));
5431 -       sas_address = reverse_byte_order64(sas_address);
5432 -       memcpy(location_ident->bSASAddress, &sas_address, sizeof(u64));
5433 -
5434 -       location_ident->bLocationFlags |= CSMI_SAS_LOCATE_SAS_LUN_VALID;
5435 -       memset(location_ident->bSASLun, 0, sizeof(location_ident->bSASLun));
5436 -
5437 -       /* SAS Enclosure Page 0 */
5438 -       hdr.PageVersion = MPI_SASENCLOSURE0_PAGEVERSION;
5439 -       hdr.ExtPageLength = 0;
5440 -       hdr.PageNumber = 0;
5441 -       hdr.Reserved1 = 0;
5442 -       hdr.Reserved2 = 0;
5443 -       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
5444 -       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_ENCLOSURE;
5445 -
5446 -       cfg.cfghdr.ehdr = &hdr;
5447 -       cfg.physAddr = -1;
5448 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5449 -       cfg.dir = 0;    /* read */
5450 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
5451 -
5452 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
5453 -               rc=0;
5454 -               goto fill_location_data_exit;
5455 -       }
5456 -
5457 -       if (hdr.ExtPageLength == 0) {
5458 -               rc=0;
5459 -               goto fill_location_data_exit;
5460 -       }
5461 -
5462 -       sasEnclosurePg0_data_sz = hdr.ExtPageLength * 4;
5463 -       sasEnclosurePg0 = (SasEnclosurePage0_t *) pci_alloc_consistent(
5464 -           ioc->pcidev, sasEnclosurePg0_data_sz, &sasEnclosurePg0_dma);
5465 -       if (!sasEnclosurePg0) {
5466 -               rc=0;
5467 -               goto fill_location_data_exit;
5468 -       }
5469 -       cfg.physAddr = sasEnclosurePg0_dma;
5470 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5471 -       cfg.pageAddr = sasDevicePg0->EnclosureHandle
5472 -           + (MPI_SAS_ENCLOS_PGAD_FORM_HANDLE << MPI_SAS_ENCLOS_PGAD_FORM_SHIFT);
5473 -
5474 -       if ((rc = mpt_config(ioc, &cfg)) != 0) {
5475 -               rc=0;
5476 -               goto fill_location_data_exit;
5477 -       }
5478 -
5479 -       location_ident->bLocationFlags |= CSMI_SAS_LOCATE_ENCLOSURE_IDENTIFIER_VALID;
5480 -       memcpy(&sas_address, &sasEnclosurePg0->EnclosureLogicalID, sizeof(u64));
5481 -       sas_address = reverse_byte_order64(sas_address);
5482 -       if (sas_address)
5483 -               memcpy(location_ident->bEnclosureIdentifier, &sas_address, sizeof(u64));
5484 -       else
5485 -               strcpy(location_ident->bEnclosureIdentifier,"Internal");
5486 -
5487 -// bBayPrefix - not supported
5488 -
5489 -// TODO - We need to look at sasEnclosurePg0-.Flags , to determine
5490 -//     whether SEP BUS/TargetID is valid.  Ifs its a SES device, then
5491 -//     issue internal inquiry to (bus/id) to gather the Enclosure name.
5492 -//     If the device is SMP, then issue SMP_MANUFACTURING to get enclosure name
5493 -//     If its direct attached, there is no enclosure name
5494 -       location_ident->bLocationFlags |= CSMI_SAS_LOCATE_ENCLOSURE_NAME_VALID;
5495 -       strcpy(location_ident->bEnclosureName,"Not Supported");
5496 -
5497 -       location_ident->bLocationFlags |= CSMI_SAS_LOCATE_LOCATION_STATE_VALID;
5498 -       location_ident->bLocationState = CSMI_SAS_LOCATE_UNKNOWN;
5499 -
5500 -       location_ident->bLocationFlags |= CSMI_SAS_LOCATE_BAY_IDENTIFIER_VALID;
5501 -       location_ident->bBayIdentifier = le16_to_cpu(sasDevicePg0->Slot);
5502 -
5503 -
5504 -// TODO - illuminating LEDs,
5505 -// karg->bIdentify = CSMI_SAS_LOCATE_FORCE_OFF, CSMI_SAS_LOCATE_FORCE_ON
5506 -// We can enable/disable LEDs by SCSI Enclosure Processor MPI request message
5507 -// printk("Flags=0x%x\n",sasEnclosurePg0->Flags);
5508 -
5509 -/* check sasEnclosurePg0->Flags -
5510 - * to validate whether we need to send the SEPRequest
5511 - * bit:5 should be set
5512 - * bit:3-0 any bit should be set.  If zero, then SEPRequest will fail
5513 -*/
5514 -
5515 -/* MPI_FUNCTION_SCSI_ENCLOSURE_PROCESSOR
5516 - * Look in mpi_init.h
5517 - * SEPRequest_t = structure
5518 - *
5519 - * SEPRequest_t->Action should be set to MPI_SEP_REQ_ACTION_WRITE_STATUS
5520 - *
5521 - * SEPRequest_t->Flags should be set to
5522 - * MPI_SEP_REQ_FLAGS_ENCLOSURE_SLOT_ADDRESS, to pass along enclosure/slot ids
5523 - *
5524 - * SEPRequest_t->SlotStatus |= MPI_SEP_REQ_SLOTSTATUS_IDENTIFY_REQUEST - this
5525 - * will illuminate the LEDs
5526 - */
5527 -
5528 -fill_location_data_exit:
5529 -
5530 -       if (sasDevicePg0 != NULL)
5531 -               pci_free_consistent(ioc->pcidev, sasDevicePg0_data_sz,
5532 -                   sasDevicePg0, sasDevicePg0_dma);
5533 -
5534 -       if (sasEnclosurePg0 != NULL)
5535 -               pci_free_consistent(ioc->pcidev, sasEnclosurePg0_data_sz,
5536 -                   sasEnclosurePg0, sasEnclosurePg0_dma);
5537 -
5538 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
5539 -       return rc;
5540 -}
5541 -
5542 -static int
5543 -csmisas_fill_location_data_raid(MPT_ADAPTER *ioc, PCSMI_SAS_GET_LOCATION_BUFFER karg, u8 VolumeBus,
5544 -       u8 volumeID)
5545 -{
5546 -       pRaidVolumePage0_t              pVolume0 = NULL;
5547 -       pRaidPhysDiskPage0_t            pPhysDisk0 = NULL;
5548 -       CONFIGPARMS                     cfg;
5549 -       ConfigPageHeader_t              header;
5550 -       u8                              physDiskNumMax;
5551 -       int                             volumepage0sz = 0, physdiskpage0sz = 0;
5552 -       dma_addr_t                      volume0_dma, physdisk0_dma;
5553 -       int                             csmi_sas_get_location_sz;
5554 -       int                             rc = 0, i, idx;
5555 -       int                             num_hotpares;
5556 -       u64                             totalMaxLBA, tmpTotalMaxLBA;
5557 -       IOCPage5_t                      *iocPage5 = NULL;
5558 -       u32                             device_info = 0;
5559 -       struct sas_device_info          *sas_info;
5560 -
5561 -       int                             sz;
5562 -
5563 -       csmi_sas_get_location_sz = karg->IoctlHeader.Length;
5564 -       physDiskNumMax = (csmi_sas_get_location_sz -
5565 -           offsetof(CSMI_SAS_GET_LOCATION_BUFFER,Location))
5566 -           / sizeof(CSMI_SAS_LOCATION_IDENTIFIER);
5567 -       karg->bNumberOfLocationIdentifiers=0;
5568 -
5569 -       /*
5570 -        * get RAID Volume Page 0
5571 -        */
5572 -
5573 -       header.PageVersion = 0;
5574 -       header.PageLength = 0;
5575 -       header.PageNumber = 0;
5576 -       header.PageType = MPI_CONFIG_PAGETYPE_RAID_VOLUME;
5577 -       cfg.cfghdr.hdr = &header;
5578 -       cfg.physAddr = -1;
5579 -       cfg.pageAddr = (VolumeBus << 8) + volumeID;
5580 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5581 -       cfg.dir = 0;
5582 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
5583 -       if (mpt_config(ioc, &cfg) != 0) {
5584 -               rc = -1;
5585 -               goto sas_fill_location_data_raid_exit;
5586 -       }
5587 -
5588 -       if (header.PageLength == 0) {
5589 -               rc = -1;
5590 -               goto sas_fill_location_data_raid_exit;
5591 -       }
5592 -
5593 -       volumepage0sz = header.PageLength * 4;
5594 -       pVolume0 = pci_alloc_consistent(ioc->pcidev, volumepage0sz,
5595 -           &volume0_dma);
5596 -       if (!pVolume0) {
5597 -               rc = -1;
5598 -               goto sas_fill_location_data_raid_exit;
5599 -       }
5600 -
5601 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5602 -       cfg.physAddr = volume0_dma;
5603 -       if (mpt_config(ioc, &cfg) != 0){
5604 -               rc = -1;
5605 -               goto sas_fill_location_data_raid_exit;
5606 -       }
5607 -
5608 -       totalMaxLBA = (u64)le32_to_cpu(pVolume0->MaxLBA) |
5609 -           ((u64)le32_to_cpu(pVolume0->MaxLBAHigh)) << 32;
5610 -
5611 -       /*
5612 -        * get RAID Physical Disk Page 0
5613 -        */
5614 -       header.PageVersion = 0;
5615 -       header.PageLength = 0;
5616 -       header.PageNumber = 0;
5617 -       header.PageType = MPI_CONFIG_PAGETYPE_RAID_PHYSDISK;
5618 -       cfg.cfghdr.hdr = &header;
5619 -       cfg.physAddr = -1;
5620 -       cfg.pageAddr = 0;
5621 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5622 -       cfg.dir = 0;
5623 -       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
5624 -       if (mpt_config(ioc, &cfg) != 0) {
5625 -               rc = -1;
5626 -               goto sas_fill_location_data_raid_exit;
5627 -       }
5628 -
5629 -       if (header.PageLength == 0) {
5630 -               rc = -1;
5631 -               goto sas_fill_location_data_raid_exit;
5632 -       }
5633 -
5634 -       physdiskpage0sz = header.PageLength * 4;
5635 -       pPhysDisk0 = pci_alloc_consistent(ioc->pcidev, physdiskpage0sz,
5636 -           &physdisk0_dma);
5637 -       if (!pPhysDisk0) {
5638 -               rc = -1;
5639 -               goto sas_fill_location_data_raid_exit;
5640 -       }
5641 -       cfg.physAddr = physdisk0_dma;
5642 -
5643 -       for (i=0; i < min(pVolume0->NumPhysDisks, physDiskNumMax); i++) {
5644 -
5645 -               /* obtain a refresh of pPhysDisk0 */
5646 -               cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5647 -               cfg.pageAddr = pVolume0->PhysDisk[i].PhysDiskNum;
5648 -               if (mpt_config(ioc, &cfg) != 0){
5649 -                       rc = -1;
5650 -                       goto sas_fill_location_data_raid_exit;
5651 -               }
5652 -
5653 -               if((csmisas_fill_location_data(ioc, pPhysDisk0->PhysDiskBus,
5654 -                   pPhysDisk0->PhysDiskID, karg->bIdentify,
5655 -                   &karg->Location[karg->bNumberOfLocationIdentifiers])) == 0)
5656 -                       karg->bNumberOfLocationIdentifiers++;
5657 -
5658 -               if (device_info)
5659 -                       continue;
5660 -               sas_info = csmisas_get_device_component_by_fw(ioc,
5661 -                   pPhysDisk0->PhysDiskBus, pPhysDisk0->PhysDiskID);
5662 -               if (!sas_info || sas_info->is_cached)
5663 -                       continue;
5664 -               device_info = sas_info->device_info;
5665 -       }
5666 -
5667 -       if (pVolume0->VolumeType == MPI_RAID_VOL_TYPE_IS)
5668 -               goto sas_fill_location_data_raid_exit;
5669 -
5670 -       /*
5671 -        * hot spare support
5672 -        *
5673 -        */
5674 -
5675 -       num_hotpares = csmisas_get_number_hotspares(ioc);
5676 -
5677 -       if (num_hotpares) {
5678 -
5679 -               sz = offsetof(IOCPage5_t, HotSpare) +
5680 -                   num_hotpares * sizeof(IOC_5_HOT_SPARE);
5681 -               iocPage5 = kmalloc(sz, GFP_KERNEL);
5682 -
5683 -               if (!iocPage5)
5684 -                       goto sas_fill_location_data_raid_exit;
5685 -               memset(iocPage5, 0, sizeof(*iocPage5));
5686 -
5687 -               if (csmisas_get_ioc_pg5(ioc, iocPage5, sz) != 0)
5688 -                       goto sas_fill_location_data_raid_exit;
5689 -
5690 -               for(i = 0, idx = pVolume0->NumPhysDisks ; i < num_hotpares;
5691 -                   i++, idx++) {
5692 -
5693 -                       if (idx >= physDiskNumMax)
5694 -                               break;
5695 -
5696 -                       /* obtain a refresh of pPhysDisk0 */
5697 -                       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5698 -                       cfg.pageAddr = iocPage5->HotSpare[i].PhysDiskNum;
5699 -                       if (mpt_config(ioc, &cfg) != 0)
5700 -                               goto sas_fill_location_data_raid_exit;
5701 -
5702 -                       /* Search the list for the matching SAS address. */
5703 -                       sas_info = csmisas_get_device_component_by_fw(ioc,
5704 -                           pPhysDisk0->PhysDiskBus, pPhysDisk0->PhysDiskID);
5705 -
5706 -                       if (!sas_info || sas_info->is_cached)
5707 -                               continue;
5708 -
5709 -                       /* don't mix SSP hot spare
5710 -                        * in SATA volume
5711 -                        */
5712 -                       if (!csmisas_is_sata(pPhysDisk0) &&
5713 -                           (device_info &
5714 -                           MPI_SAS_DEVICE_INFO_SATA_DEVICE))
5715 -                               continue;
5716 -
5717 -                       /* don't mix SATA hot spare
5718 -                        * in SSP volume
5719 -                        */
5720 -                       if (csmisas_is_sata(pPhysDisk0) &&
5721 -                           (device_info &
5722 -                           MPI_SAS_DEVICE_INFO_SSP_TARGET))
5723 -                               continue;
5724 -
5725 -                       /* capacity check for IM volumes*/
5726 -                       if ((pVolume0->VolumeType ==
5727 -                           MPI_RAID_VOL_TYPE_IM) &&
5728 -                           (totalMaxLBA +
5729 -                           (64*2*1024) /* metadata = 64MB*/ >
5730 -                           le32_to_cpu(pPhysDisk0->MaxLBA)))
5731 -                               continue;
5732 -
5733 -                       tmpTotalMaxLBA = totalMaxLBA;
5734 -                       do_div(tmpTotalMaxLBA, pVolume0->NumPhysDisks);
5735 -                       /* capacity check for IME volumes*/
5736 -                       if ((pVolume0->VolumeType ==
5737 -                               MPI_RAID_VOL_TYPE_IME) &&
5738 -                           ((tmpTotalMaxLBA * 2) +
5739 -                            (64*2*1024 ) /*metadata = 64MB*/ >
5740 -                           le32_to_cpu(pPhysDisk0->MaxLBA)))
5741 -                               continue;
5742 -
5743 -                       if((csmisas_fill_location_data(ioc,
5744 -                           pPhysDisk0->PhysDiskBus, pPhysDisk0->PhysDiskID,
5745 -                           karg->bIdentify,
5746 -                           &karg->Location[karg->bNumberOfLocationIdentifiers])) == 0)
5747 -                               karg->bNumberOfLocationIdentifiers++;
5748 -               }
5749 -       }
5750 -
5751 -
5752 - sas_fill_location_data_raid_exit:
5753 -
5754 -       kfree(iocPage5);
5755 -
5756 -       if (pVolume0)
5757 -               pci_free_consistent(ioc->pcidev, volumepage0sz, pVolume0,
5758 -                   volume0_dma);
5759 -
5760 -       if(pPhysDisk0)
5761 -               pci_free_consistent(ioc->pcidev, physdiskpage0sz, pPhysDisk0,
5762 -                   physdisk0_dma);
5763 -
5764 -       return rc;
5765 -}
5766 -
5767 -/**
5768 - * Prototype Routine for the CSMI SAS Get location command.
5769 - *
5770 - * Outputs:    None.
5771 - * Return:     0 if successful
5772 - *             -EFAULT if data unavailable
5773 - *             -ENODEV if no such device/adapter
5774 - */
5775 -static int
5776 -csmisas_get_location(unsigned long arg)
5777 -{
5778 -       CSMI_SAS_GET_LOCATION_BUFFER __user *uarg = (void __user *) arg;
5779 -       PCSMI_SAS_GET_LOCATION_BUFFER   karg;
5780 -       IOCTL_HEADER                    ioctl_header;
5781 -       MPT_ADAPTER                     *ioc = NULL;
5782 -       int                             iocnum,i;
5783 -       int                             csmi_sas_get_location_sz;
5784 -       int                             memory_pages;
5785 -       struct sas_device_info          *sas_info;
5786 -
5787 -       dcsmisasprintk(("%s enter.\n",__FUNCTION__));
5788 -
5789 -       if (copy_from_user(&ioctl_header, uarg, sizeof(IOCTL_HEADER))) {
5790 -               printk(KERN_ERR "%s@%d::%s() - "
5791 -                   "Unable to read in IOCTL_HEADER"
5792 -                   "struct @ %p\n", __FILE__, __LINE__, __FUNCTION__, uarg);
5793 -               return -EFAULT;
5794 -       }
5795 -
5796 -       csmi_sas_get_location_sz = ioctl_header.Length;
5797 -       memory_pages = get_order(csmi_sas_get_location_sz);
5798 -       karg = (PCSMI_SAS_GET_LOCATION_BUFFER)__get_free_pages(
5799 -               GFP_KERNEL, memory_pages);
5800 -       if (!karg){
5801 -               printk(KERN_ERR "%s@%d::%s() - "
5802 -                       "Unable to malloc GET_LOCATION_BUFFER "
5803 -                       "csmi_sas_get_location_sz=%d memory_pages=%d\n",
5804 -                       __FILE__, __LINE__, __FUNCTION__,
5805 -                       csmi_sas_get_location_sz, memory_pages);
5806 -               return -ENOMEM;
5807 -       }
5808 -       memset(karg, 0, sizeof(*karg));
5809 -
5810 -       if (copy_from_user(karg, uarg, csmi_sas_get_location_sz)) {
5811 -               printk(KERN_ERR "%s@%d::%s() - "
5812 -                   "Unable to read in csmi_sas_phy_control_buffer "
5813 -                   "struct @ %p\n", __FILE__, __LINE__, __FUNCTION__, uarg);
5814 -               free_pages((unsigned long)karg, memory_pages);
5815 -               return -EFAULT;
5816 -       }
5817 -
5818 -       if (((iocnum = mpt_verify_adapter(karg->IoctlHeader.IOControllerNumber,
5819 -           &ioc)) < 0) || (ioc == NULL)) {
5820 -               dcsmisasprintk((KERN_ERR
5821 -               "%s::%s() @%d - ioc%d not found!\n",
5822 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
5823 -               free_pages((unsigned long)karg, memory_pages);
5824 -               return -ENODEV;
5825 -       }
5826 -
5827 -       if (!csmisas_is_this_sas_cntr(ioc)) {
5828 -               dcsmisasprintk((KERN_ERR
5829 -                   "%s::%s() @%d - ioc%d not SAS controller!\n",
5830 -                   __FILE__, __FUNCTION__, __LINE__, iocnum));
5831 -               free_pages((unsigned long)karg, memory_pages);
5832 -               return -ENODEV;
5833 -       }
5834 -
5835 -       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
5836 -       if(karg->bLengthOfLocationIdentifier !=
5837 -           sizeof(CSMI_SAS_LOCATION_IDENTIFIER))
5838 -               goto cim_sas_get_location_exit;
5839 -
5840 -       sas_info = csmisas_get_device_component_by_os(ioc, karg->bPathId,
5841 -           karg->bTargetId);
5842 -       if (!sas_info)
5843 -               goto cim_sas_get_location_exit;
5844 -
5845 -       /* RAID SUPPORT */
5846 -       if (ioc->raid_data.pIocPg2 && sas_info->is_logical_volume) {
5847 -               for (i=0; i<ioc->raid_data.pIocPg2->NumActiveVolumes; i++){
5848 -                       if (sas_info->fw.id ==
5849 -                           ioc->raid_data.pIocPg2->RaidVolume[i].VolumeID &&
5850 -                           sas_info->fw.channel ==
5851 -                           ioc->raid_data.pIocPg2->RaidVolume[i].VolumeBus) {
5852 -                               if(csmisas_fill_location_data_raid(ioc, karg,
5853 -                                   ioc->raid_data.pIocPg2->RaidVolume[i].VolumeBus,
5854 -                                   ioc->raid_data.pIocPg2->RaidVolume[i].VolumeID) == 0)
5855 -                                       karg->IoctlHeader.ReturnCode =
5856 -                                           CSMI_SAS_STATUS_SUCCESS;
5857 -                               else
5858 -                                       karg->IoctlHeader.ReturnCode =
5859 -                                           CSMI_SAS_STATUS_FAILED;
5860 -                               goto cim_sas_get_location_exit;
5861 -                       }
5862 -               }
5863 -       }
5864 -
5865 -       /* NON-RAID SUPPORT */
5866 -       if (sas_info->is_cached || sas_info->is_logical_volume)
5867 -               goto cim_sas_get_location_exit;
5868 -
5869 -       /* make sure there's enough room to populate the Location[] struct */
5870 -       if ((csmi_sas_get_location_sz -
5871 -           offsetof(CSMI_SAS_GET_LOCATION_BUFFER,Location)) <
5872 -           sizeof(CSMI_SAS_LOCATION_IDENTIFIER))
5873 -               goto cim_sas_get_location_exit;
5874 -
5875 -       karg->bNumberOfLocationIdentifiers=1;
5876 -       karg->Location[0].bLocationFlags=0;
5877 -       if((csmisas_fill_location_data(ioc, sas_info->fw.channel,
5878 -           sas_info->fw.id, karg->bIdentify, &karg->Location[0])) == 0)
5879 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
5880 -       else
5881 -               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
5882 -
5883 - cim_sas_get_location_exit:
5884 -
5885 -       /* Copy the data from kernel memory to user memory
5886 -        */
5887 -       if (copy_to_user((char *)arg, karg, csmi_sas_get_location_sz)) {
5888 -               printk(KERN_ERR "%s@%d::%s() - "
5889 -                   "Unable to write out csmi_sas_get_location_buffer "
5890 -                   "@ %p\n",__FILE__, __LINE__, __FUNCTION__, uarg);
5891 -               free_pages((unsigned long)karg, memory_pages);
5892 -               return -EFAULT;
5893 -       }
5894 -
5895 -       dcsmisasprintk(("%s exit.\n",__FUNCTION__));
5896 -       free_pages((unsigned long)karg, memory_pages);
5897 -       return 0;
5898 -}
5899 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/csmi/csmisas.h linux-2.6.9-55.0.12/drivers/message/fusion/csmi/csmisas.h
5900 --- linux-2.6.9-67.0.1/drivers/message/fusion/csmi/csmisas.h    2007-12-21 11:40:54.000000000 +0100
5901 +++ linux-2.6.9-55.0.12/drivers/message/fusion/csmi/csmisas.h   1970-01-01 01:00:00.000000000 +0100
5902 @@ -1,1854 +0,0 @@
5903 -/**************************************************************************
5904 -
5905 -Module Name:
5906 -
5907 -   CSMISAS.H
5908 -
5909 -
5910 -Abstract:
5911 -
5912 -   This file contains constants and data structure definitions used by drivers
5913 -   that support the Common Storage Management Interface specification for
5914 -   SAS or SATA in either the Windows or Linux.
5915 -
5916 -   This should be considered as a reference implementation only.  Changes may
5917 -   be necessary to accommodate a specific build environment or target OS.
5918 -
5919 -Revision History:
5920 -
5921 -   001  SEF   8/12/03  Initial release.
5922 -   002  SEF   8/20/03  Cleanup to match documentation.
5923 -   003  SEF   9/12/03  Additional cleanup, created combined header
5924 -   004  SEF   9/23/03  Changed base types to match linux defaults
5925 -                       Added RAID signature
5926 -                       Added bControllerFlags to CSMI_SAS_CNTLR_CONFIG
5927 -                       Changed CSMI_SAS_BEGIN_PACK to 8 for common structures
5928 -                       Fixed other typos identified in first compilation test
5929 -   005  SEF  10/03/03  Additions to match first version of CSMI document
5930 -   006  SEF  10/14/03  Fixed typedef struct _CSMI_SAS_SMP_PASSTHRU_BUFFER
5931 -                       Added defines for bConnectionRate
5932 -   007  SEF  10/15/03  Added Firmware Download Control Code and support
5933 -                       Added CSMI revision support
5934 -   008  SEF  10/30/03  No functional change, just updated version to track
5935 -                       spec changes
5936 -   009  SEF  12/09/03  No functional change, just updated version to track
5937 -                       spec changes
5938 -   010  SEF   3/11/04  Fixed typedef struct CSMI_SAS_RAID_DRIVES to include the
5939 -                       bFirmware member that is defined in the spec, but
5940 -                       was missing in this file,
5941 -                       added CC_CSMI_SAS_TASK_MANAGEMENT
5942 -   011  SEF   4/02/04  No functional change, added comment line before
5943 -                       CC_CSMI_SAS_TASK_MANAGEMENT
5944 -   012  SEF   4/16/04  Added IOControllerNumber to linux header,
5945 -                       Modified linux control codes to have upper word of
5946 -                       0xCC77.... to indicate CSMI version 77
5947 -                       Added bSignalClass to CC_CSMI_SET_PHY_INFO
5948 -                       Added CC_CSMI_SAS_PHY_CONTROL support
5949 -   013  SEF   5/14/04  Added CC_CSMI_SAS_GET_CONNECTOR_INFO support
5950 -   014  SEF   5/24/04  No functional change, just updated version to track spec
5951 -                       changes
5952 -   015  SEF   6/16/04  changed bPinout to uPinout to reflect proper size,
5953 -                       changed width of bLocation defines to reflect size
5954 -   016  SEF   6/17/04  changed bLengthOfControls in CSMI_SAS_PHY_CONTROL
5955 -                       to be proper size
5956 -   017  SEF   9/17/04  added CSMI_SAS_SATA_PORT_SELECTOR,
5957 -                       CSMI_SAS_LINK_VIRTUAL, CSMI_SAS_CON_NOT_PRESENT, and
5958 -                       CSMI_SAS_CON_NOT_CONNECTED
5959 -   018  SEF   9/20/04  added CSMI_SAS_PHY_USER_PATTERN,
5960 -                       changed definition of CSMI_SAS_PHY_FIXED_PATTERN to not
5961 -                       conflict with activate definition
5962 -   019  SEF  12/06/04  added CSMI_SAS_GET_LOCATION
5963 -                       added bSSPStatus to CSMI_SAS_SSP_PASSTHRU_STATUS
5964 -                       structure
5965 -   020  SEF   5/25/05  added CSMI_SAS_PHY_VIRTUAL_SMP, and changes to
5966 -                       CSMI_SAS_GET_LOCATION
5967 -   021  SEF  11/03/05  added new RAID creation functionality
5968 -   022  SEF   2/01/06  corrected typo bNegotitiatedLInkRate
5969 -                       Added two more RAID_TYPES, 7 and 8
5970 -   023  SEF   4/04/06  added CSMI_RAID_TYPE_1E
5971 -                       changed structures that contained surface scan
5972 -                       to priority approach rather than time, causes
5973 -                       0.89 to incompatible with 0.87, so a version
5974 -                       check is necessary when interpreting the
5975 -                       raid structures
5976 -                       Added netware section
5977 -   024 DRG    5/22/06  Added uFailureCode to CSMI_SAS_RAID_CONFIG and
5978 -                       CSMI_SAS_RAID_FEATURES
5979 -                       Changed __u64 fields to high and low __u32 fields in
5980 -                       order to avoid backward compatibility issues with
5981 -                       packing and alignment.
5982 -                       Fixed alignment problem in CSMI_SAS_RAID_DRIVES.
5983 -                       Added CSMI_SAS_CNTLR_SMART_ARRAY to uControllerFlags
5984 -                       Reassigned the value of CSMI_SAS_CNTLR_RAID_CFG_SUPPORT
5985 -                       to avoid a conflict.
5986 -
5987 -**************************************************************************/
5988 -
5989 -#ifndef _CSMI_SAS_H_
5990 -#define _CSMI_SAS_H_
5991 -
5992 -// CSMI Specification Revision, the intent is that all versions of the
5993 -// specification will be backward compatible after the 1.00 release.
5994 -// Major revision number, corresponds to xxxx. of CSMI specification
5995 -// Minor revision number, corresponds to .xxxx of CSMI specification
5996 -#define CSMI_MAJOR_REVISION   0
5997 -#define CSMI_MINOR_REVISION   90
5998 -
5999 -/*************************************************************************/
6000 -/* PATCHES FOR TYPOS                                                     */
6001 -/*************************************************************************/
6002 -
6003 -#define bNegotitiatedLInkRate bNegotiatedLinkRate
6004 -
6005 -/*************************************************************************/
6006 -/* TARGET OS LINUX SPECIFIC CODE                                         */
6007 -/*************************************************************************/
6008 -
6009 -// EDM #ifdef _linux
6010 -#ifdef __KERNEL__
6011 -
6012 -// Linux base types
6013 -
6014 -#include <linux/types.h>
6015 -
6016 -#define __i8    char
6017 -
6018 -// pack definition
6019 -
6020 -// EDM #define CSMI_SAS_BEGIN_PACK(x)    pack(x)
6021 -// EDM #define CSMI_SAS_END_PACK         pack()
6022 -
6023 -// IOCTL Control Codes
6024 -// (IoctlHeader.ControlCode)
6025 -
6026 -// Control Codes prior to 0.77
6027 -
6028 -// Control Codes requiring CSMI_ALL_SIGNATURE
6029 -
6030 -// #define CC_CSMI_SAS_GET_DRIVER_INFO    0x12345678
6031 -// #define CC_CSMI_SAS_GET_CNTLR_CONFIG   0x23456781
6032 -// #define CC_CSMI_SAS_GET_CNTLR_STATUS   0x34567812
6033 -// #define CC_CSMI_SAS_FIRMWARE_DOWNLOAD  0x92345678
6034 -
6035 -// Control Codes requiring CSMI_RAID_SIGNATURE
6036 -
6037 -// #define CC_CSMI_SAS_GET_RAID_INFO      0x45678123
6038 -// #define CC_CSMI_SAS_GET_RAID_CONFIG    0x56781234
6039 -
6040 -// Control Codes requiring CSMI_SAS_SIGNATURE
6041 -
6042 -// #define CC_CSMI_SAS_GET_PHY_INFO       0x67812345
6043 -// #define CC_CSMI_SAS_SET_PHY_INFO       0x78123456
6044 -// #define CC_CSMI_SAS_GET_LINK_ERRORS    0x81234567
6045 -// #define CC_CSMI_SAS_SMP_PASSTHRU       0xA1234567
6046 -// #define CC_CSMI_SAS_SSP_PASSTHRU       0xB1234567
6047 -// #define CC_CSMI_SAS_STP_PASSTHRU       0xC1234567
6048 -// #define CC_CSMI_SAS_GET_SATA_SIGNATURE 0xD1234567
6049 -// #define CC_CSMI_SAS_GET_SCSI_ADDRESS   0xE1234567
6050 -// #define CC_CSMI_SAS_GET_DEVICE_ADDRESS 0xF1234567
6051 -// #define CC_CSMI_SAS_TASK_MANAGEMENT    0xA2345678
6052 -
6053 -// Control Codes for 0.77 and later
6054 -
6055 -// Control Codes requiring CSMI_ALL_SIGNATURE
6056 -
6057 -#define CC_CSMI_SAS_GET_DRIVER_INFO    0xCC770001
6058 -#define CC_CSMI_SAS_GET_CNTLR_CONFIG   0xCC770002
6059 -#define CC_CSMI_SAS_GET_CNTLR_STATUS   0xCC770003
6060 -#define CC_CSMI_SAS_FIRMWARE_DOWNLOAD  0xCC770004
6061 -
6062 -// Control Codes requiring CSMI_RAID_SIGNATURE
6063 -
6064 -#define CC_CSMI_SAS_GET_RAID_INFO      0xCC77000A
6065 -#define CC_CSMI_SAS_GET_RAID_CONFIG    0xCC77000B
6066 -#define CC_CSMI_SAS_GET_RAID_FEATURES  0xCC77000C
6067 -#define CC_CSMI_SAS_SET_RAID_CONTROL   0xCC77000D
6068 -#define CC_CSMI_SAS_GET_RAID_ELEMENT   0xCC77000E
6069 -#define CC_CSMI_SAS_SET_RAID_OPERATION 0xCC77000F
6070 -
6071 -// Control Codes requiring CSMI_SAS_SIGNATURE
6072 -
6073 -#define CC_CSMI_SAS_GET_PHY_INFO       0xCC770014
6074 -#define CC_CSMI_SAS_SET_PHY_INFO       0xCC770015
6075 -#define CC_CSMI_SAS_GET_LINK_ERRORS    0xCC770016
6076 -#define CC_CSMI_SAS_SMP_PASSTHRU       0xCC770017
6077 -#define CC_CSMI_SAS_SSP_PASSTHRU       0xCC770018
6078 -#define CC_CSMI_SAS_STP_PASSTHRU       0xCC770019
6079 -#define CC_CSMI_SAS_GET_SATA_SIGNATURE 0xCC770020
6080 -#define CC_CSMI_SAS_GET_SCSI_ADDRESS   0xCC770021
6081 -#define CC_CSMI_SAS_GET_DEVICE_ADDRESS 0xCC770022
6082 -#define CC_CSMI_SAS_TASK_MANAGEMENT    0xCC770023
6083 -#define CC_CSMI_SAS_GET_CONNECTOR_INFO 0xCC770024
6084 -#define CC_CSMI_SAS_GET_LOCATION       0xCC770025
6085 -
6086 -
6087 -// Control Codes requiring CSMI_PHY_SIGNATURE
6088 -
6089 -#define CC_CSMI_SAS_PHY_CONTROL        0xCC77003C
6090 -
6091 -// EDM #pragma CSMI_SAS_BEGIN_PACK(8)
6092 -#pragma pack(8)
6093 -
6094 -// IOCTL_HEADER
6095 -typedef struct _IOCTL_HEADER {
6096 -    __u32 IOControllerNumber;
6097 -    __u32 Length;
6098 -    __u32 ReturnCode;
6099 -    __u32 Timeout;
6100 -    __u16 Direction;
6101 -} IOCTL_HEADER,
6102 -  *PIOCTL_HEADER;
6103 -
6104 -// EDM #pragma CSMI_SAS_END_PACK
6105 -#pragma pack()
6106 -
6107 -#endif
6108 -
6109 -/*************************************************************************/
6110 -/* TARGET OS WINDOWS SPECIFIC CODE                                       */
6111 -/*************************************************************************/
6112 -
6113 -#ifdef _WIN32
6114 -
6115 -// windows IOCTL definitions
6116 -
6117 -#ifndef _NTDDSCSIH_
6118 -#include <ntddscsi.h>
6119 -#endif
6120 -
6121 -// pack definition
6122 -
6123 -#if defined _MSC_VER
6124 -   #define CSMI_SAS_BEGIN_PACK(x)    pack(push,x)
6125 -   #define CSMI_SAS_END_PACK         pack(pop)
6126 -#elif defined __BORLANDC__
6127 -   #define CSMI_SAS_BEGIN_PACK(x)    option -a##x
6128 -   #define CSMI_SAS_END_PACK         option -a.
6129 -#else
6130 -   #error "CSMISAS.H - Must externally define a pack compiler designator."
6131 -#endif
6132 -
6133 -// base types
6134 -
6135 -#define __u8    unsigned char
6136 -#define __u16   unsigned short
6137 -#define __u32   unsigned long
6138 -#define __u64   unsigned __int64
6139 -
6140 -#define __i8    char
6141 -
6142 -// IOCTL Control Codes
6143 -// (IoctlHeader.ControlCode)
6144 -
6145 -// Control Codes requiring CSMI_ALL_SIGNATURE
6146 -
6147 -#define CC_CSMI_SAS_GET_DRIVER_INFO    1
6148 -#define CC_CSMI_SAS_GET_CNTLR_CONFIG   2
6149 -#define CC_CSMI_SAS_GET_CNTLR_STATUS   3
6150 -#define CC_CSMI_SAS_FIRMWARE_DOWNLOAD  4
6151 -
6152 -// Control Codes requiring CSMI_RAID_SIGNATURE
6153 -
6154 -#define CC_CSMI_SAS_GET_RAID_INFO      10
6155 -#define CC_CSMI_SAS_GET_RAID_CONFIG    11
6156 -#define CC_CSMI_SAS_GET_RAID_FEATURES  12
6157 -#define CC_CSMI_SAS_SET_RAID_CONTROL   13
6158 -#define CC_CSMI_SAS_GET_RAID_ELEMENT   14
6159 -#define CC_CSMI_SAS_SET_RAID_OPERATION 15
6160 -
6161 -// Control Codes requiring CSMI_SAS_SIGNATURE
6162 -
6163 -#define CC_CSMI_SAS_GET_PHY_INFO       20
6164 -#define CC_CSMI_SAS_SET_PHY_INFO       21
6165 -#define CC_CSMI_SAS_GET_LINK_ERRORS    22
6166 -#define CC_CSMI_SAS_SMP_PASSTHRU       23
6167 -#define CC_CSMI_SAS_SSP_PASSTHRU       24
6168 -#define CC_CSMI_SAS_STP_PASSTHRU       25
6169 -#define CC_CSMI_SAS_GET_SATA_SIGNATURE 26
6170 -#define CC_CSMI_SAS_GET_SCSI_ADDRESS   27
6171 -#define CC_CSMI_SAS_GET_DEVICE_ADDRESS 28
6172 -#define CC_CSMI_SAS_TASK_MANAGEMENT    29
6173 -#define CC_CSMI_SAS_GET_CONNECTOR_INFO 30
6174 -#define CC_CSMI_SAS_GET_LOCATION       31
6175 -
6176 -// Control Codes requiring CSMI_PHY_SIGNATURE
6177 -
6178 -#define CC_CSMI_SAS_PHY_CONTROL        60
6179 -
6180 -#define IOCTL_HEADER SRB_IO_CONTROL
6181 -#define PIOCTL_HEADER PSRB_IO_CONTROL
6182 -
6183 -#endif
6184 -
6185 -/*************************************************************************/
6186 -/* TARGET OS NETWARE SPECIFIC CODE                                       */
6187 -/*************************************************************************/
6188 -
6189 -#ifdef _NETWARE
6190 -
6191 -// NetWare IOCTL definitions
6192 -
6193 -#define CSMI_SAS_BEGIN_PACK(x)    pack(x)
6194 -#define CSMI_SAS_END_PACK         pack()
6195 -
6196 -#ifndef LONG
6197 -typedef unsigned long LONG;
6198 -#endif
6199 -
6200 -#ifndef WORD
6201 -typedef unsigned short WORD;
6202 -#endif
6203 -
6204 -#ifndef BYTE
6205 -typedef unsigned char BYTE;
6206 -#endif
6207 -
6208 -/* Need to have these definitions for Netware */
6209 -#define __u8    unsigned char
6210 -#define __u16   unsigned short
6211 -#define __u32   unsigned long
6212 -#define __u64   unsigned __int64
6213 -
6214 -#define __i8    char
6215 -
6216 -
6217 -// EDM #pragma CSMI_SAS_BEGIN_PACK(8)
6218 -#pragma pack(8)
6219 -
6220 -// IOCTL_HEADER
6221 -typedef struct _IOCTL_HEADER {
6222 -    __u32 Length;
6223 -    __u32 ReturnCode;
6224 -} IOCTL_HEADER,
6225 -  *PIOCTL_HEADER;
6226 -
6227 -// EDM #pragma CSMI_SAS_END_PACK
6228 -#pragma pack()
6229 -
6230 -// IOCTL Control Codes
6231 -// (IoctlHeader.ControlCode)
6232 -
6233 -// Control Codes requiring CSMI_ALL_SIGNATURE
6234 -
6235 -#define CC_CSMI_SAS_GET_DRIVER_INFO    0x01FF0001
6236 -#define CC_CSMI_SAS_GET_CNTLR_CONFIG   0x01FF0002
6237 -#define CC_CSMI_SAS_GET_CNTLR_STATUS   0x01FF0003
6238 -#define CC_CSMI_SAS_FIRMWARE_DOWNLOAD  0x01FF0004
6239 -
6240 -// Control Codes requiring CSMI_RAID_SIGNATURE
6241 -
6242 -#define CC_CSMI_SAS_GET_RAID_INFO      0x01FF000A
6243 -#define CC_CSMI_SAS_GET_RAID_CONFIG    0x01FF000B
6244 -#define CC_CSMI_SAS_GET_RAID_FEATURES  0x01FF000C
6245 -#define CC_CSMI_SAS_SET_RAID_CONTROL   0x01FF000D
6246 -#define CC_CSMI_SAS_GET_RAID_ELEMENT   0x01FF000E
6247 -#define CC_CSMI_SAS_SET_RAID_OPERATION 0x01FF000F
6248 -
6249 -// Control Codes requiring CSMI_SAS_SIGNATURE
6250 -
6251 -#define CC_CSMI_SAS_GET_PHY_INFO       0x01FF0014
6252 -#define CC_CSMI_SAS_SET_PHY_INFO       0x01FF0015
6253 -#define CC_CSMI_SAS_GET_LINK_ERRORS    0x01FF0016
6254 -#define CC_CSMI_SAS_SMP_PASSTHRU       0x01FF0017
6255 -#define CC_CSMI_SAS_SSP_PASSTHRU       0x01FF0018
6256 -#define CC_CSMI_SAS_STP_PASSTHRU       0x01FF0019
6257 -#define CC_CSMI_SAS_GET_SATA_SIGNATURE 0x01FF001A
6258 -#define CC_CSMI_SAS_GET_SCSI_ADDRESS   0x01FF001B
6259 -#define CC_CSMI_SAS_GET_DEVICE_ADDRESS 0x01FF001C
6260 -#define CC_CSMI_SAS_TASK_MANAGEMENT    0x01FF001D
6261 -#define CC_CSMI_SAS_GET_CONNECTOR_INFO 0x01FF001E
6262 -#define CC_CSMI_SAS_GET_LOCATION       0x01FF001F
6263 -
6264 -// Control Codes requiring CSMI_PHY_SIGNATURE
6265 -
6266 -#define CC_CSMI_SAS_PHY_CONTROL        60
6267 -
6268 -#endif
6269 -
6270 -/*************************************************************************/
6271 -/* TARGET OS NOT DEFINED ERROR                                           */
6272 -/*************************************************************************/
6273 -
6274 -// EDM
6275 -//#if (!_WIN32 && !_linux && !_NETWARE)
6276 -//   #error "Unknown target OS."
6277 -//#endif
6278 -
6279 -/*************************************************************************/
6280 -/* OS INDEPENDENT CODE                                                   */
6281 -/*************************************************************************/
6282 -
6283 -/* * * * * * * * * * Class Independent IOCTL Constants * * * * * * * * * */
6284 -
6285 -// Return codes for all IOCTL's regardless of class
6286 -// (IoctlHeader.ReturnCode)
6287 -
6288 -#define CSMI_SAS_STATUS_SUCCESS              0
6289 -#define CSMI_SAS_STATUS_FAILED               1
6290 -#define CSMI_SAS_STATUS_BAD_CNTL_CODE        2
6291 -#define CSMI_SAS_STATUS_INVALID_PARAMETER    3
6292 -#define CSMI_SAS_STATUS_WRITE_ATTEMPTED      4
6293 -
6294 -// Signature value
6295 -// (IoctlHeader.Signature)
6296 -
6297 -#define CSMI_ALL_SIGNATURE    "CSMIALL"
6298 -
6299 -// Timeout value default of 60 seconds
6300 -// (IoctlHeader.Timeout)
6301 -
6302 -#define CSMI_ALL_TIMEOUT      60
6303 -
6304 -//  Direction values for data flow on this IOCTL
6305 -// (IoctlHeader.Direction, Linux only)
6306 -#define CSMI_SAS_DATA_READ    0
6307 -#define CSMI_SAS_DATA_WRITE   1
6308 -
6309 -// I/O Bus Types
6310 -// ISA and EISA bus types are not supported
6311 -// (bIoBusType)
6312 -
6313 -#define CSMI_SAS_BUS_TYPE_PCI       3
6314 -#define CSMI_SAS_BUS_TYPE_PCMCIA    4
6315 -
6316 -// Controller Status
6317 -// (uStatus)
6318 -
6319 -#define CSMI_SAS_CNTLR_STATUS_GOOD     1
6320 -#define CSMI_SAS_CNTLR_STATUS_FAILED   2
6321 -#define CSMI_SAS_CNTLR_STATUS_OFFLINE  3
6322 -#define CSMI_SAS_CNTLR_STATUS_POWEROFF 4
6323 -
6324 -// Offline Status Reason
6325 -// (uOfflineReason)
6326 -
6327 -#define CSMI_SAS_OFFLINE_REASON_NO_REASON             0
6328 -#define CSMI_SAS_OFFLINE_REASON_INITIALIZING          1
6329 -#define CSMI_SAS_OFFLINE_REASON_BACKSIDE_BUS_DEGRADED 2
6330 -#define CSMI_SAS_OFFLINE_REASON_BACKSIDE_BUS_FAILURE  3
6331 -
6332 -// Controller Class
6333 -// (bControllerClass)
6334 -
6335 -#define CSMI_SAS_CNTLR_CLASS_HBA    5
6336 -
6337 -// Controller Flag bits
6338 -// (uControllerFlags)
6339 -
6340 -#define CSMI_SAS_CNTLR_SAS_HBA          0x00000001
6341 -#define CSMI_SAS_CNTLR_SAS_RAID         0x00000002
6342 -#define CSMI_SAS_CNTLR_SATA_HBA         0x00000004
6343 -#define CSMI_SAS_CNTLR_SATA_RAID        0x00000008
6344 -#define CSMI_SAS_CNTLR_SMART_ARRAY      0x00000010
6345 -
6346 -// for firmware download
6347 -#define CSMI_SAS_CNTLR_FWD_SUPPORT      0x00010000
6348 -#define CSMI_SAS_CNTLR_FWD_ONLINE       0x00020000
6349 -#define CSMI_SAS_CNTLR_FWD_SRESET       0x00040000
6350 -#define CSMI_SAS_CNTLR_FWD_HRESET       0x00080000
6351 -#define CSMI_SAS_CNTLR_FWD_RROM         0x00100000
6352 -
6353 -// for RAID configuration supported
6354 -#define CSMI_SAS_CNTLR_RAID_CFG_SUPPORT 0x01000000
6355 -
6356 -// Download Flag bits
6357 -// (uDownloadFlags)
6358 -#define CSMI_SAS_FWD_VALIDATE       0x00000001
6359 -#define CSMI_SAS_FWD_SOFT_RESET     0x00000002
6360 -#define CSMI_SAS_FWD_HARD_RESET     0x00000004
6361 -
6362 -// Firmware Download Status
6363 -// (usStatus)
6364 -#define CSMI_SAS_FWD_SUCCESS        0
6365 -#define CSMI_SAS_FWD_FAILED         1
6366 -#define CSMI_SAS_FWD_USING_RROM     2
6367 -#define CSMI_SAS_FWD_REJECT         3
6368 -#define CSMI_SAS_FWD_DOWNREV        4
6369 -
6370 -// Firmware Download Severity
6371 -// (usSeverity>
6372 -#define CSMI_SAS_FWD_INFORMATION    0
6373 -#define CSMI_SAS_FWD_WARNING        1
6374 -#define CSMI_SAS_FWD_ERROR          2
6375 -#define CSMI_SAS_FWD_FATAL          3
6376 -
6377 -/* * * * * * * * * * SAS RAID Class IOCTL Constants  * * * * * * * * */
6378 -
6379 -// Return codes for the RAID IOCTL's regardless of class
6380 -// (IoctlHeader.ReturnCode)
6381 -
6382 -#define CSMI_SAS_RAID_SET_OUT_OF_RANGE       1000
6383 -#define CSMI_SAS_RAID_SET_BUFFER_TOO_SMALL   1001
6384 -#define CSMI_SAS_RAID_SET_DATA_CHANGED       1002
6385 -
6386 -// Signature value
6387 -// (IoctlHeader.Signature)
6388 -
6389 -#define CSMI_RAID_SIGNATURE    "CSMIARY"
6390 -
6391 -// Timeout value default of 60 seconds
6392 -// (IoctlHeader.Timeout)
6393 -
6394 -#define CSMI_RAID_TIMEOUT      60
6395 -
6396 -// RAID Types
6397 -// (bRaidType)
6398 -#define CSMI_SAS_RAID_TYPE_NONE     0
6399 -#define CSMI_SAS_RAID_TYPE_0        1
6400 -#define CSMI_SAS_RAID_TYPE_1        2
6401 -#define CSMI_SAS_RAID_TYPE_10       3
6402 -#define CSMI_SAS_RAID_TYPE_5        4
6403 -#define CSMI_SAS_RAID_TYPE_15       5
6404 -#define CSMI_SAS_RAID_TYPE_6        6
6405 -#define CSMI_SAS_RAID_TYPE_50       7
6406 -#define CSMI_SAS_RAID_TYPE_VOLUME   8
6407 -#define CSMI_SAS_RAID_TYPE_1E       9
6408 -#define CSMI_SAS_RAID_TYPE_OTHER    255
6409 -// the last value 255 was already defined for other
6410 -// so end is defined as 254
6411 -#define CSMI_SAS_RAID_TYPE_END      254
6412 -
6413 -// RAID Status
6414 -// (bStatus)
6415 -#define CSMI_SAS_RAID_SET_STATUS_OK             0
6416 -#define CSMI_SAS_RAID_SET_STATUS_DEGRADED       1
6417 -#define CSMI_SAS_RAID_SET_STATUS_REBUILDING     2
6418 -#define CSMI_SAS_RAID_SET_STATUS_FAILED         3
6419 -#define CSMI_SAS_RAID_SET_STATUS_OFFLINE        4
6420 -#define CSMI_SAS_RAID_SET_STATUS_TRANSFORMING   5
6421 -#define CSMI_SAS_RAID_SET_STATUS_QUEUED_FOR_REBUILD         6
6422 -#define CSMI_SAS_RAID_SET_STATUS_QUEUED_FOR_TRANSFORMATION  7
6423 -
6424 -// RAID Drive Count
6425 -// (bDriveCount, 0xF1 to 0xFF are reserved)
6426 -#define CSMI_SAS_RAID_DRIVE_COUNT_TOO_BIG   0xF1
6427 -#define CSMI_SAS_RAID_DRIVE_COUNT_SUPRESSED 0xF2
6428 -
6429 -// RAID Data Type
6430 -// (bDataType)
6431 -#define CSMI_SAS_RAID_DATA_DRIVES           0
6432 -#define CSMI_SAS_RAID_DATA_DEVICE_ID        1
6433 -#define CSMI_SAS_RAID_DATA_ADDITIONAL_DATA  2
6434 -
6435 -// RAID Drive Status
6436 -// (bDriveStatus)
6437 -#define CSMI_SAS_DRIVE_STATUS_OK          0
6438 -#define CSMI_SAS_DRIVE_STATUS_REBUILDING  1
6439 -#define CSMI_SAS_DRIVE_STATUS_FAILED      2
6440 -#define CSMI_SAS_DRIVE_STATUS_DEGRADED    3
6441 -#define CSMI_SAS_DRIVE_STATUS_OFFLINE     4
6442 -#define CSMI_SAS_DRIVE_STATUS_QUEUED_FOR_REBUILD 5
6443 -
6444 -// RAID Drive Usage
6445 -// (bDriveUsage)
6446 -#define CSMI_SAS_DRIVE_CONFIG_NOT_USED      0
6447 -#define CSMI_SAS_DRIVE_CONFIG_MEMBER        1
6448 -#define CSMI_SAS_DRIVE_CONFIG_SPARE         2
6449 -#define CSMI_SAS_DRIVE_CONFIG_SPARE_ACTIVE  3
6450 -
6451 -// RAID Drive Type
6452 -// (bDriveType)
6453 -#define CSMI_SAS_DRIVE_TYPE_UNKNOWN         0
6454 -#define CSMI_SAS_DRIVE_TYPE_SINGLE_PORT_SAS 1
6455 -#define CSMI_SAS_DRIVE_TYPE_DUAL_PORT_SAS   2
6456 -#define CSMI_SAS_DRIVE_TYPE_SATA            3
6457 -#define CSMI_SAS_DRIVE_TYPE_SATA_PS         4
6458 -#define CSMI_SAS_DRIVE_TYPE_OTHER           255
6459 -
6460 -// RAID Write Protect
6461 -// (bWriteProtect)
6462 -#define CSMI_SAS_RAID_SET_WRITE_PROTECT_UNKNOWN     0
6463 -#define CSMI_SAS_RAID_SET_WRITE_PROTECT_UNCHANGED   0
6464 -#define CSMI_SAS_RAID_SET_WRITE_PROTECT_ENABLED     1
6465 -#define CSMI_SAS_RAID_SET_WRITE_PROTECT_DISABLED    2
6466 -
6467 -// RAID Cache Setting
6468 -// (bCacheSetting)
6469 -#define CSMI_SAS_RAID_SET_CACHE_UNKNOWN             0
6470 -#define CSMI_SAS_RAID_SET_CACHE_UNCHANGED           0
6471 -#define CSMI_SAS_RAID_SET_CACHE_ENABLED             1
6472 -#define CSMI_SAS_RAID_SET_CACHE_DISABLED            2
6473 -#define CSMI_SAS_RAID_SET_CACHE_CORRUPT             3
6474 -
6475 -// RAID Features
6476 -// (uFeatures)
6477 -#define CSMI_SAS_RAID_FEATURE_TRANSFORMATION    0x00000001
6478 -#define CSMI_SAS_RAID_FEATURE_REBUILD           0x00000002
6479 -#define CSMI_SAS_RAID_FEATURE_SPLIT_MIRROR      0x00000004
6480 -#define CSMI_SAS_RAID_FEATURE_MERGE_MIRROR      0x00000008
6481 -#define CSMI_SAS_RAID_FEATURE_LUN_RENUMBER      0x00000010
6482 -#define CSMI_SAS_RAID_FEATURE_SURFACE_SCAN      0x00000020
6483 -#define CSMI_SAS_RAID_FEATURE_SPARES_SHARED     0x00000040
6484 -
6485 -// RAID Priority
6486 -// (bDefaultTransformPriority, etc.)
6487 -#define CSMI_SAS_PRIORITY_UNKNOWN   0
6488 -#define CSMI_SAS_PRIORITY_UNCHANGED 0
6489 -#define CSMI_SAS_PRIORITY_AUTO      1
6490 -#define CSMI_SAS_PRIORITY_OFF       2
6491 -#define CSMI_SAS_PRIORITY_LOW       3
6492 -#define CSMI_SAS_PRIORITY_MEDIUM    4
6493 -#define CSMI_SAS_PRIORITY_HIGH      5
6494 -
6495 -// RAID Transformation Rules
6496 -// (uRaidSetTransformationRules)
6497 -#define CSMI_SAS_RAID_RULE_AVAILABLE_MEMORY     0x00000001
6498 -#define CSMI_SAS_RAID_RULE_OVERLAPPED_EXTENTS   0x00000002
6499 -
6500 -// RAID Cache Ratios Supported
6501 -// (bCacheRatiosSupported)
6502 -// from 0 to 100 defines the write to read ratio, 0 is 100% write
6503 -#define CSMI_SAS_RAID_CACHE_RATIO_RANGE     101
6504 -#define CSMI_SAS_RAID_CACHE_RATIO_FIXED     102
6505 -#define CSMI_SAS_RAID_CACHE_RATIO_AUTO      103
6506 -#define CSMI_SAS_RAID_CACHE_RATIO_END       255
6507 -
6508 -// RAID Cache Ratio Flag
6509 -// (bCacheRatioFlag)
6510 -#define CSMI_SAS_RAID_CACHE_RATIO_DISABLE   0
6511 -#define CSMI_SAS_RAID_CACHE_RATIO_ENABLE    1
6512 -
6513 -// RAID Clear Configuration Signature
6514 -// (bClearConfiguration)
6515 -#define CSMI_SAS_RAID_CLEAR_CONFIGURATION_SIGNATURE "RAIDCLR"
6516 -
6517 -// RAID Failure Codes
6518 -// (uFailureCode)
6519 -#define CSMI_SAS_FAIL_CODE_OK                           0
6520 -#define CSMI_SAS_FAIL_CODE_PARAMETER_INVALID            1000
6521 -#define CSMI_SAS_FAIL_CODE_TRANSFORM_PRIORITY_INVALID   1001
6522 -#define CSMI_SAS_FAIL_CODE_REBUILD_PRIORITY_INVALID     1002
6523 -#define CSMI_SAS_FAIL_CODE_CACHE_RATIO_INVALID          1003
6524 -#define CSMI_SAS_FAIL_CODE_SURFACE_SCAN_INVALID         1004
6525 -#define CSMI_SAS_FAIL_CODE_CLEAR_CONFIGURATION_INVALID  1005
6526 -#define CSMI_SAS_FAIL_CODE_ELEMENT_INDEX_INVALID        1006
6527 -#define CSMI_SAS_FAIL_CODE_SUBELEMENT_INDEX_INVALID     1007
6528 -#define CSMI_SAS_FAIL_CODE_EXTENT_INVALID               1008
6529 -#define CSMI_SAS_FAIL_CODE_BLOCK_COUNT_INVALID          1009
6530 -#define CSMI_SAS_FAIL_CODE_DRIVE_INDEX_INVALID          1010
6531 -#define CSMI_SAS_FAIL_CODE_EXISTING_LUN_INVALID         1011
6532 -#define CSMI_SAS_FAIL_CODE_RAID_TYPE_INVALID            1012
6533 -#define CSMI_SAS_FAIL_CODE_STRIPE_SIZE_INVALID          1013
6534 -#define CSMI_SAS_FAIL_CODE_TRANSFORMATION_INVALID       1014
6535 -#define CSMI_SAS_FAIL_CODE_CHANGE_COUNT_INVALID         1015
6536 -#define CSMI_SAS_FAIL_CODE_ENUMERATION_TYPE_INVALID     1016
6537 -
6538 -#define CSMI_SAS_FAIL_CODE_EXCEEDED_RAID_SET_COUNT      2000
6539 -#define CSMI_SAS_FAIL_CODE_DUPLICATE_LUN                2001
6540 -
6541 -#define CSMI_SAS_FAIL_CODE_WAIT_FOR_OPERATION           3000
6542 -
6543 -// RAID Enumeration Types
6544 -// (uEnumerationType)
6545 -#define CSMI_SAS_RAID_ELEMENT_TYPE_DRIVE                0
6546 -#define CSMI_SAS_RAID_ELEMENT_TYPE_MODULE               1
6547 -#define CSMI_SAS_RAID_ELEMENT_TYPE_DRIVE_RAID_SET       2
6548 -#define CSMI_SAS_RAID_ELEMENT_TYPE_EXTENT_DRIVE         3
6549 -
6550 -// RAID Extent Types
6551 -// (bExtentType)
6552 -#define CSMI_SAS_RAID_EXTENT_RESERVED       0
6553 -#define CSMI_SAS_RAID_EXTENT_METADATA       1
6554 -#define CSMI_SAS_RAID_EXTENT_ALLOCATED      2
6555 -#define CSMI_SAS_RAID_EXTENT_UNALLOCATED    3
6556 -
6557 -// RAID Operation Types
6558 -// (uOperationType)
6559 -#define CSMI_SAS_RAID_SET_CREATE            0
6560 -#define CSMI_SAS_RAID_SET_LABEL             1
6561 -#define CSMI_SAS_RAID_SET_TRANSFORM         2
6562 -#define CSMI_SAS_RAID_SET_DELETE            3
6563 -#define CSMI_SAS_RAID_SET_WRITE_PROTECT     4
6564 -#define CSMI_SAS_RAID_SET_CACHE             5
6565 -#define CSMI_SAS_RAID_SET_ONLINE_STATE      6
6566 -#define CSMI_SAS_RAID_SET_SPARE             7
6567 -
6568 -// RAID Transform Types
6569 -// (bTransformType)
6570 -#define CSMI_SAS_RAID_SET_TRANSFORM_SPLIT_MIRROR    0
6571 -#define CSMI_SAS_RAID_SET_TRANSFORM_MERGE_RAID_0    1
6572 -#define CSMI_SAS_RAID_SET_TRANSFORM_LUN_RENUMBER    2
6573 -#define CSMI_SAS_RAID_SET_TRANSFORM_RAID_SET        3
6574 -
6575 -// RAID Online State
6576 -// (bOnlineState)
6577 -#define CSMI_SAS_RAID_SET_STATE_UNKNOWN     0
6578 -#define CSMI_SAS_RAID_SET_STATE_ONLINE      1
6579 -#define CSMI_SAS_RAID_SET_STATE_OFFLINE     2
6580 -
6581 -/* * * * * * * * * * SAS HBA Class IOCTL Constants * * * * * * * * * */
6582 -
6583 -// Return codes for SAS IOCTL's
6584 -// (IoctlHeader.ReturnCode)
6585 -
6586 -#define CSMI_SAS_PHY_INFO_CHANGED            CSMI_SAS_STATUS_SUCCESS
6587 -#define CSMI_SAS_PHY_INFO_NOT_CHANGEABLE     2000
6588 -#define CSMI_SAS_LINK_RATE_OUT_OF_RANGE      2001
6589 -
6590 -#define CSMI_SAS_PHY_DOES_NOT_EXIST          2002
6591 -#define CSMI_SAS_PHY_DOES_NOT_MATCH_PORT     2003
6592 -#define CSMI_SAS_PHY_CANNOT_BE_SELECTED      2004
6593 -#define CSMI_SAS_SELECT_PHY_OR_PORT          2005
6594 -#define CSMI_SAS_PORT_DOES_NOT_EXIST         2006
6595 -#define CSMI_SAS_PORT_CANNOT_BE_SELECTED     2007
6596 -#define CSMI_SAS_CONNECTION_FAILED           2008
6597 -
6598 -#define CSMI_SAS_NO_SATA_DEVICE              2009
6599 -#define CSMI_SAS_NO_SATA_SIGNATURE           2010
6600 -#define CSMI_SAS_SCSI_EMULATION              2011
6601 -#define CSMI_SAS_NOT_AN_END_DEVICE           2012
6602 -#define CSMI_SAS_NO_SCSI_ADDRESS             2013
6603 -#define CSMI_SAS_NO_DEVICE_ADDRESS           2014
6604 -
6605 -// Signature value
6606 -// (IoctlHeader.Signature)
6607 -
6608 -#define CSMI_SAS_SIGNATURE    "CSMISAS"
6609 -
6610 -// Timeout value default of 60 seconds
6611 -// (IoctlHeader.Timeout)
6612 -
6613 -#define CSMI_SAS_TIMEOUT      60
6614 -
6615 -// Device types
6616 -// (bDeviceType)
6617 -
6618 -#define CSMI_SAS_PHY_UNUSED               0x00
6619 -#define CSMI_SAS_NO_DEVICE_ATTACHED       0x00
6620 -#define CSMI_SAS_END_DEVICE               0x10
6621 -#define CSMI_SAS_EDGE_EXPANDER_DEVICE     0x20
6622 -#define CSMI_SAS_FANOUT_EXPANDER_DEVICE   0x30
6623 -
6624 -// Protocol options
6625 -// (bInitiatorPortProtocol, bTargetPortProtocol)
6626 -
6627 -#define CSMI_SAS_PROTOCOL_SATA   0x01
6628 -#define CSMI_SAS_PROTOCOL_SMP    0x02
6629 -#define CSMI_SAS_PROTOCOL_STP    0x04
6630 -#define CSMI_SAS_PROTOCOL_SSP    0x08
6631 -
6632 -// Negotiated and hardware link rates
6633 -// (bNegotiatedLinkRate, bMinimumLinkRate, bMaximumLinkRate)
6634 -
6635 -#define CSMI_SAS_LINK_RATE_UNKNOWN  0x00
6636 -#define CSMI_SAS_PHY_DISABLED       0x01
6637 -#define CSMI_SAS_LINK_RATE_FAILED   0x02
6638 -#define CSMI_SAS_SATA_SPINUP_HOLD   0x03
6639 -#define CSMI_SAS_SATA_PORT_SELECTOR 0x04
6640 -#define CSMI_SAS_LINK_RATE_1_5_GBPS 0x08
6641 -#define CSMI_SAS_LINK_RATE_3_0_GBPS 0x09
6642 -#define CSMI_SAS_LINK_VIRTUAL       0x10
6643 -
6644 -// Discover state
6645 -// (bAutoDiscover)
6646 -
6647 -#define CSMI_SAS_DISCOVER_NOT_SUPPORTED   0x00
6648 -#define CSMI_SAS_DISCOVER_NOT_STARTED     0x01
6649 -#define CSMI_SAS_DISCOVER_IN_PROGRESS     0x02
6650 -#define CSMI_SAS_DISCOVER_COMPLETE        0x03
6651 -#define CSMI_SAS_DISCOVER_ERROR           0x04
6652 -
6653 -// Phy features
6654 -
6655 -#define CSMI_SAS_PHY_VIRTUAL_SMP          0x01
6656 -
6657 -// Programmed link rates
6658 -// (bMinimumLinkRate, bMaximumLinkRate)
6659 -// (bProgrammedMinimumLinkRate, bProgrammedMaximumLinkRate)
6660 -
6661 -#define CSMI_SAS_PROGRAMMED_LINK_RATE_UNCHANGED 0x00
6662 -#define CSMI_SAS_PROGRAMMED_LINK_RATE_1_5_GBPS  0x08
6663 -#define CSMI_SAS_PROGRAMMED_LINK_RATE_3_0_GBPS  0x09
6664 -
6665 -// Link rate
6666 -// (bNegotiatedLinkRate in CSMI_SAS_SET_PHY_INFO)
6667 -
6668 -#define CSMI_SAS_LINK_RATE_NEGOTIATE      0x00
6669 -#define CSMI_SAS_LINK_RATE_PHY_DISABLED   0x01
6670 -
6671 -// Signal class
6672 -// (bSignalClass in CSMI_SAS_SET_PHY_INFO)
6673 -
6674 -#define CSMI_SAS_SIGNAL_CLASS_UNKNOWN     0x00
6675 -#define CSMI_SAS_SIGNAL_CLASS_DIRECT      0x01
6676 -#define CSMI_SAS_SIGNAL_CLASS_SERVER      0x02
6677 -#define CSMI_SAS_SIGNAL_CLASS_ENCLOSURE   0x03
6678 -
6679 -// Link error reset
6680 -// (bResetCounts)
6681 -
6682 -#define CSMI_SAS_LINK_ERROR_DONT_RESET_COUNTS   0x00
6683 -#define CSMI_SAS_LINK_ERROR_RESET_COUNTS        0x01
6684 -
6685 -// Phy identifier
6686 -// (bPhyIdentifier)
6687 -
6688 -#define CSMI_SAS_USE_PORT_IDENTIFIER   0xFF
6689 -
6690 -// Port identifier
6691 -// (bPortIdentifier)
6692 -
6693 -#define CSMI_SAS_IGNORE_PORT           0xFF
6694 -
6695 -// Programmed link rates
6696 -// (bConnectionRate)
6697 -
6698 -#define CSMI_SAS_LINK_RATE_NEGOTIATED  0x00
6699 -#define CSMI_SAS_LINK_RATE_1_5_GBPS    0x08
6700 -#define CSMI_SAS_LINK_RATE_3_0_GBPS    0x09
6701 -
6702 -// Connection status
6703 -// (bConnectionStatus)
6704 -
6705 -#define CSMI_SAS_OPEN_ACCEPT                          0
6706 -#define CSMI_SAS_OPEN_REJECT_BAD_DESTINATION          1
6707 -#define CSMI_SAS_OPEN_REJECT_RATE_NOT_SUPPORTED       2
6708 -#define CSMI_SAS_OPEN_REJECT_NO_DESTINATION           3
6709 -#define CSMI_SAS_OPEN_REJECT_PATHWAY_BLOCKED          4
6710 -#define CSMI_SAS_OPEN_REJECT_PROTOCOL_NOT_SUPPORTED   5
6711 -#define CSMI_SAS_OPEN_REJECT_RESERVE_ABANDON          6
6712 -#define CSMI_SAS_OPEN_REJECT_RESERVE_CONTINUE         7
6713 -#define CSMI_SAS_OPEN_REJECT_RESERVE_INITIALIZE       8
6714 -#define CSMI_SAS_OPEN_REJECT_RESERVE_STOP             9
6715 -#define CSMI_SAS_OPEN_REJECT_RETRY                    10
6716 -#define CSMI_SAS_OPEN_REJECT_STP_RESOURCES_BUSY       11
6717 -#define CSMI_SAS_OPEN_REJECT_WRONG_DESTINATION        12
6718 -
6719 -// SSP Status
6720 -// (bSSPStatus)
6721 -
6722 -#define CSMI_SAS_SSP_STATUS_UNKNOWN     0x00
6723 -#define CSMI_SAS_SSP_STATUS_WAITING     0x01
6724 -#define CSMI_SAS_SSP_STATUS_COMPLETED   0x02
6725 -#define CSMI_SAS_SSP_STATUS_FATAL_ERROR 0x03
6726 -#define CSMI_SAS_SSP_STATUS_RETRY       0x04
6727 -#define CSMI_SAS_SSP_STATUS_NO_TAG      0x05
6728 -
6729 -// SSP Flags
6730 -// (uFlags)
6731 -
6732 -#define CSMI_SAS_SSP_READ           0x00000001
6733 -#define CSMI_SAS_SSP_WRITE          0x00000002
6734 -#define CSMI_SAS_SSP_UNSPECIFIED    0x00000004
6735 -
6736 -#define CSMI_SAS_SSP_TASK_ATTRIBUTE_SIMPLE         0x00000000
6737 -#define CSMI_SAS_SSP_TASK_ATTRIBUTE_HEAD_OF_QUEUE  0x00000010
6738 -#define CSMI_SAS_SSP_TASK_ATTRIBUTE_ORDERED        0x00000020
6739 -#define CSMI_SAS_SSP_TASK_ATTRIBUTE_ACA            0x00000040
6740 -
6741 -// SSP Data present
6742 -// (bDataPresent)
6743 -
6744 -#define CSMI_SAS_SSP_NO_DATA_PRESENT         0x00
6745 -#define CSMI_SAS_SSP_RESPONSE_DATA_PRESENT   0x01
6746 -#define CSMI_SAS_SSP_SENSE_DATA_PRESENT      0x02
6747 -
6748 -// STP Flags
6749 -// (uFlags)
6750 -
6751 -#define CSMI_SAS_STP_READ           0x00000001
6752 -#define CSMI_SAS_STP_WRITE          0x00000002
6753 -#define CSMI_SAS_STP_UNSPECIFIED    0x00000004
6754 -#define CSMI_SAS_STP_PIO            0x00000010
6755 -#define CSMI_SAS_STP_DMA            0x00000020
6756 -#define CSMI_SAS_STP_PACKET         0x00000040
6757 -#define CSMI_SAS_STP_DMA_QUEUED     0x00000080
6758 -#define CSMI_SAS_STP_EXECUTE_DIAG   0x00000100
6759 -#define CSMI_SAS_STP_RESET_DEVICE   0x00000200
6760 -
6761 -// Task Management Flags
6762 -// (uFlags)
6763 -
6764 -#define CSMI_SAS_TASK_IU               0x00000001
6765 -#define CSMI_SAS_HARD_RESET_SEQUENCE   0x00000002
6766 -#define CSMI_SAS_SUPPRESS_RESULT       0x00000004
6767 -
6768 -// Task Management Functions
6769 -// (bTaskManagement)
6770 -
6771 -#define CSMI_SAS_SSP_ABORT_TASK           0x01
6772 -#define CSMI_SAS_SSP_ABORT_TASK_SET       0x02
6773 -#define CSMI_SAS_SSP_CLEAR_TASK_SET       0x04
6774 -#define CSMI_SAS_SSP_LOGICAL_UNIT_RESET   0x08
6775 -#define CSMI_SAS_SSP_CLEAR_ACA            0x40
6776 -#define CSMI_SAS_SSP_QUERY_TASK           0x80
6777 -
6778 -// Task Management Information
6779 -// (uInformation)
6780 -
6781 -#define CSMI_SAS_SSP_TEST           1
6782 -#define CSMI_SAS_SSP_EXCEEDED       2
6783 -#define CSMI_SAS_SSP_DEMAND         3
6784 -#define CSMI_SAS_SSP_TRIGGER        4
6785 -
6786 -// Connector Pinout Information
6787 -// (uPinout)
6788 -
6789 -#define CSMI_SAS_CON_UNKNOWN              0x00000001
6790 -#define CSMI_SAS_CON_SFF_8482             0x00000002
6791 -#define CSMI_SAS_CON_SFF_8470_LANE_1      0x00000100
6792 -#define CSMI_SAS_CON_SFF_8470_LANE_2      0x00000200
6793 -#define CSMI_SAS_CON_SFF_8470_LANE_3      0x00000400
6794 -#define CSMI_SAS_CON_SFF_8470_LANE_4      0x00000800
6795 -#define CSMI_SAS_CON_SFF_8484_LANE_1      0x00010000
6796 -#define CSMI_SAS_CON_SFF_8484_LANE_2      0x00020000
6797 -#define CSMI_SAS_CON_SFF_8484_LANE_3      0x00040000
6798 -#define CSMI_SAS_CON_SFF_8484_LANE_4      0x00080000
6799 -
6800 -// Connector Location Information
6801 -// (bLocation)
6802 -
6803 -// same as uPinout above...
6804 -// #define CSMI_SAS_CON_UNKNOWN              0x01
6805 -#define CSMI_SAS_CON_INTERNAL             0x02
6806 -#define CSMI_SAS_CON_EXTERNAL             0x04
6807 -#define CSMI_SAS_CON_SWITCHABLE           0x08
6808 -#define CSMI_SAS_CON_AUTO                 0x10
6809 -#define CSMI_SAS_CON_NOT_PRESENT          0x20
6810 -#define CSMI_SAS_CON_NOT_CONNECTED        0x80
6811 -
6812 -// Device location identification
6813 -// (bIdentify)
6814 -
6815 -#define CSMI_SAS_LOCATE_UNKNOWN           0x00
6816 -#define CSMI_SAS_LOCATE_FORCE_OFF         0x01
6817 -#define CSMI_SAS_LOCATE_FORCE_ON          0x02
6818 -
6819 -// Location Valid flags
6820 -// (uLocationFlags)
6821 -
6822 -#define CSMI_SAS_LOCATE_SAS_ADDRESS_VALID           0x00000001
6823 -#define CSMI_SAS_LOCATE_SAS_LUN_VALID               0x00000002
6824 -#define CSMI_SAS_LOCATE_ENCLOSURE_IDENTIFIER_VALID  0x00000004
6825 -#define CSMI_SAS_LOCATE_ENCLOSURE_NAME_VALID        0x00000008
6826 -#define CSMI_SAS_LOCATE_BAY_PREFIX_VALID            0x00000010
6827 -#define CSMI_SAS_LOCATE_BAY_IDENTIFIER_VALID        0x00000020
6828 -#define CSMI_SAS_LOCATE_LOCATION_STATE_VALID        0x00000040
6829 -
6830 -/* * * * * * * * SAS Phy Control Class IOCTL Constants * * * * * * * * */
6831 -
6832 -// Return codes for SAS Phy Control IOCTL's
6833 -// (IoctlHeader.ReturnCode)
6834 -
6835 -// Signature value
6836 -// (IoctlHeader.Signature)
6837 -
6838 -#define CSMI_PHY_SIGNATURE    "CSMIPHY"
6839 -
6840 -// Phy Control Functions
6841 -// (bFunction)
6842 -
6843 -// values 0x00 to 0xFF are consistent in definition with the SMP PHY CONTROL
6844 -// function defined in the SAS spec
6845 -#define CSMI_SAS_PC_NOP                   0x00000000
6846 -#define CSMI_SAS_PC_LINK_RESET            0x00000001
6847 -#define CSMI_SAS_PC_HARD_RESET            0x00000002
6848 -#define CSMI_SAS_PC_PHY_DISABLE           0x00000003
6849 -// 0x04 to 0xFF reserved...
6850 -#define CSMI_SAS_PC_GET_PHY_SETTINGS      0x00000100
6851 -
6852 -// Link Flags
6853 -#define CSMI_SAS_PHY_ACTIVATE_CONTROL     0x00000001
6854 -#define CSMI_SAS_PHY_UPDATE_SPINUP_RATE   0x00000002
6855 -#define CSMI_SAS_PHY_AUTO_COMWAKE         0x00000004
6856 -
6857 -// Device Types for Phy Settings
6858 -// (bType)
6859 -#define CSMI_SAS_UNDEFINED 0x00
6860 -#define CSMI_SAS_SATA      0x01
6861 -#define CSMI_SAS_SAS       0x02
6862 -
6863 -// Transmitter Flags
6864 -// (uTransmitterFlags)
6865 -#define CSMI_SAS_PHY_PREEMPHASIS_DISABLED    0x00000001
6866 -
6867 -// Receiver Flags
6868 -// (uReceiverFlags)
6869 -#define CSMI_SAS_PHY_EQUALIZATION_DISABLED   0x00000001
6870 -
6871 -// Pattern Flags
6872 -// (uPatternFlags)
6873 -// #define CSMI_SAS_PHY_ACTIVATE_CONTROL     0x00000001
6874 -#define CSMI_SAS_PHY_DISABLE_SCRAMBLING      0x00000002
6875 -#define CSMI_SAS_PHY_DISABLE_ALIGN           0x00000004
6876 -#define CSMI_SAS_PHY_DISABLE_SSC             0x00000008
6877 -
6878 -#define CSMI_SAS_PHY_FIXED_PATTERN           0x00000010
6879 -#define CSMI_SAS_PHY_USER_PATTERN            0x00000020
6880 -
6881 -// Fixed Patterns
6882 -// (bFixedPattern)
6883 -#define CSMI_SAS_PHY_CJPAT                   0x00000001
6884 -#define CSMI_SAS_PHY_ALIGN                   0x00000002
6885 -
6886 -// Type Flags
6887 -// (bTypeFlags)
6888 -#define CSMI_SAS_PHY_POSITIVE_DISPARITY      0x01
6889 -#define CSMI_SAS_PHY_NEGATIVE_DISPARITY      0x02
6890 -#define CSMI_SAS_PHY_CONTROL_CHARACTER       0x04
6891 -
6892 -// Miscellaneous
6893 -#define SLOT_NUMBER_UNKNOWN   0xFFFF
6894 -
6895 -/*************************************************************************/
6896 -/* DATA STRUCTURES                                                       */
6897 -/*************************************************************************/
6898 -
6899 -/* * * * * * * * * * Class Independent Structures * * * * * * * * * */
6900 -
6901 -// EDM #pragma CSMI_SAS_BEGIN_PACK(8)
6902 -#pragma pack(8)
6903 -
6904 -// CC_CSMI_SAS_DRIVER_INFO
6905 -
6906 -typedef struct _CSMI_SAS_DRIVER_INFO {
6907 -   __u8  szName[81];
6908 -   __u8  szDescription[81];
6909 -   __u16 usMajorRevision;
6910 -   __u16 usMinorRevision;
6911 -   __u16 usBuildRevision;
6912 -   __u16 usReleaseRevision;
6913 -   __u16 usCSMIMajorRevision;
6914 -   __u16 usCSMIMinorRevision;
6915 -} CSMI_SAS_DRIVER_INFO,
6916 -  *PCSMI_SAS_DRIVER_INFO;
6917 -
6918 -typedef struct _CSMI_SAS_DRIVER_INFO_BUFFER {
6919 -   IOCTL_HEADER IoctlHeader;
6920 -   CSMI_SAS_DRIVER_INFO Information;
6921 -} CSMI_SAS_DRIVER_INFO_BUFFER,
6922 -  *PCSMI_SAS_DRIVER_INFO_BUFFER;
6923 -
6924 -// CC_CSMI_SAS_CNTLR_CONFIGURATION
6925 -
6926 -typedef struct _CSMI_SAS_PCI_BUS_ADDRESS {
6927 -   __u8  bBusNumber;
6928 -   __u8  bDeviceNumber;
6929 -   __u8  bFunctionNumber;
6930 -   __u8  bReserved;
6931 -} CSMI_SAS_PCI_BUS_ADDRESS,
6932 -  *PCSMI_SAS_PCI_BUS_ADDRESS;
6933 -
6934 -typedef union _CSMI_SAS_IO_BUS_ADDRESS {
6935 -   CSMI_SAS_PCI_BUS_ADDRESS PciAddress;
6936 -   __u8  bReserved[32];
6937 -} CSMI_SAS_IO_BUS_ADDRESS,
6938 -  *PCSMI_SAS_IO_BUS_ADDRESS;
6939 -
6940 -typedef struct _CSMI_SAS_CNTLR_CONFIG {
6941 -   __u32 uBaseIoAddress;
6942 -   struct {
6943 -      __u32 uLowPart;
6944 -      __u32 uHighPart;
6945 -   } BaseMemoryAddress;
6946 -   __u32 uBoardID;
6947 -   __u16 usSlotNumber;
6948 -   __u8  bControllerClass;
6949 -   __u8  bIoBusType;
6950 -   CSMI_SAS_IO_BUS_ADDRESS BusAddress;
6951 -   __u8  szSerialNumber[81];
6952 -   __u16 usMajorRevision;
6953 -   __u16 usMinorRevision;
6954 -   __u16 usBuildRevision;
6955 -   __u16 usReleaseRevision;
6956 -   __u16 usBIOSMajorRevision;
6957 -   __u16 usBIOSMinorRevision;
6958 -   __u16 usBIOSBuildRevision;
6959 -   __u16 usBIOSReleaseRevision;
6960 -   __u32 uControllerFlags;
6961 -   __u16 usRromMajorRevision;
6962 -   __u16 usRromMinorRevision;
6963 -   __u16 usRromBuildRevision;
6964 -   __u16 usRromReleaseRevision;
6965 -   __u16 usRromBIOSMajorRevision;
6966 -   __u16 usRromBIOSMinorRevision;
6967 -   __u16 usRromBIOSBuildRevision;
6968 -   __u16 usRromBIOSReleaseRevision;
6969 -   __u8  bReserved[7];
6970 -} CSMI_SAS_CNTLR_CONFIG,
6971 -  *PCSMI_SAS_CNTLR_CONFIG;
6972 -
6973 -typedef struct _CSMI_SAS_CNTLR_CONFIG_BUFFER {
6974 -   IOCTL_HEADER IoctlHeader;
6975 -   CSMI_SAS_CNTLR_CONFIG Configuration;
6976 -} CSMI_SAS_CNTLR_CONFIG_BUFFER,
6977 -  *PCSMI_SAS_CNTLR_CONFIG_BUFFER;
6978 -
6979 -// CC_CSMI_SAS_CNTLR_STATUS
6980 -
6981 -typedef struct _CSMI_SAS_CNTLR_STATUS {
6982 -   __u32 uStatus;
6983 -   __u32 uOfflineReason;
6984 -   __u8  bReserved[28];
6985 -} CSMI_SAS_CNTLR_STATUS,
6986 -  *PCSMI_SAS_CNTLR_STATUS;
6987 -
6988 -typedef struct _CSMI_SAS_CNTLR_STATUS_BUFFER {
6989 -   IOCTL_HEADER IoctlHeader;
6990 -   CSMI_SAS_CNTLR_STATUS Status;
6991 -} CSMI_SAS_CNTLR_STATUS_BUFFER,
6992 -  *PCSMI_SAS_CNTLR_STATUS_BUFFER;
6993 -
6994 -// CC_CSMI_SAS_FIRMWARE_DOWNLOAD
6995 -
6996 -typedef struct _CSMI_SAS_FIRMWARE_DOWNLOAD {
6997 -   __u32 uBufferLength;
6998 -   __u32 uDownloadFlags;
6999 -   __u8  bReserved[32];
7000 -   __u16 usStatus;
7001 -   __u16 usSeverity;
7002 -} CSMI_SAS_FIRMWARE_DOWNLOAD,
7003 -  *PCSMI_SAS_FIRMWARE_DOWNLOAD;
7004 -
7005 -typedef struct _CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER {
7006 -   IOCTL_HEADER IoctlHeader;
7007 -   CSMI_SAS_FIRMWARE_DOWNLOAD Information;
7008 -   __u8  bDataBuffer[1];
7009 -} CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER,
7010 -  *PCSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER;
7011 -
7012 -// CC_CSMI_SAS_RAID_INFO
7013 -
7014 -typedef struct _CSMI_SAS_RAID_INFO {
7015 -   __u32 uNumRaidSets;
7016 -   __u32 uMaxDrivesPerSet;
7017 -   __u32 uMaxRaidSets;
7018 -   __u8  bMaxRaidTypes;
7019 -   __u8  bReservedByteFields[7];
7020 -   struct
7021 -   {
7022 -      __u32 uLowPart;
7023 -      __u32 uHighPart;
7024 -   } ulMinRaidSetBlocks;
7025 -   struct
7026 -   {
7027 -      __u32 uLowPart;
7028 -      __u32 uHighPart;
7029 -   } ulMaxRaidSetBlocks;
7030 -   __u32 uMaxPhysicalDrives;
7031 -   __u32 uMaxExtents;
7032 -   __u32 uMaxModules;
7033 -   __u32 uMaxTransformationMemory;
7034 -   __u32 uChangeCount;
7035 -   __u8  bReserved[44];
7036 -} CSMI_SAS_RAID_INFO,
7037 -  *PCSMI_SAS_RAID_INFO;
7038 -
7039 -typedef struct _CSMI_SAS_RAID_INFO_BUFFER {
7040 -   IOCTL_HEADER IoctlHeader;
7041 -   CSMI_SAS_RAID_INFO Information;
7042 -} CSMI_SAS_RAID_INFO_BUFFER,
7043 -  *PCSMI_SAS_RAID_INFO_BUFFER;
7044 -
7045 -// CC_CSMI_SAS_GET_RAID_CONFIG
7046 -
7047 -typedef struct _CSMI_SAS_RAID_DRIVES {
7048 -   __u8  bModel[40];
7049 -   __u8  bFirmware[8];
7050 -   __u8  bSerialNumber[40];
7051 -   __u8  bSASAddress[8];
7052 -   __u8  bSASLun[8];
7053 -   __u8  bDriveStatus;
7054 -   __u8  bDriveUsage;
7055 -   __u16 usBlockSize;
7056 -   __u8  bDriveType;
7057 -   __u8  bReserved[15];
7058 -   __u32 uDriveIndex;
7059 -   struct
7060 -   {
7061 -      __u32 uLowPart;
7062 -      __u32 uHighPart;
7063 -   } ulTotalUserBlocks;
7064 -} CSMI_SAS_RAID_DRIVES,
7065 -  *PCSMI_SAS_RAID_DRIVES;
7066 -
7067 -typedef struct _CSMI_SAS_RAID_DEVICE_ID {
7068 -   __u8  bDeviceIdentificationVPDPage[1];
7069 -} CSMI_SAS_RAID_DEVICE_ID,
7070 -  *PCSMI_SAS_RAID_DEVICE_ID;
7071 -
7072 -typedef struct _CSMI_SAS_RAID_SET_ADDITIONAL_DATA {
7073 -   __u8  bLabel[16];
7074 -   __u8  bRaidSetLun[8];
7075 -   __u8  bWriteProtection;
7076 -   __u8  bCacheSetting;
7077 -   __u8  bCacheRatio;
7078 -   __u16 usBlockSize;
7079 -   __u8  bReservedBytes[11];
7080 -   struct
7081 -   {
7082 -      __u32 uLowPart;
7083 -      __u32 uHighPart;
7084 -   } ulRaidSetExtentOffset;
7085 -   struct
7086 -   {
7087 -      __u32 uLowPart;
7088 -      __u32 uHighPart;
7089 -   } ulRaidSetBlocks;
7090 -   __u32 uStripeSizeInBlocks;
7091 -   __u32 uSectorsPerTrack;
7092 -   __u8  bApplicationScratchPad[16];
7093 -   __u32 uNumberOfHeads;
7094 -   __u32 uNumberOfTracks;
7095 -   __u8  bReserved[24];
7096 -} CSMI_SAS_RAID_SET_ADDITIONAL_DATA,
7097 -  *PCSMI_SAS_RAID_SET_ADDITIONAL_DATA;
7098 -
7099 -typedef struct _CSMI_SAS_RAID_CONFIG {
7100 -   __u32 uRaidSetIndex;
7101 -   __u32 uCapacity;
7102 -   __u32 uStripeSize;
7103 -   __u8  bRaidType;
7104 -   __u8  bStatus;
7105 -   __u8  bInformation;
7106 -   __u8  bDriveCount;
7107 -   __u8  bDataType;
7108 -   __u8  bReserved[11];
7109 -   __u32 uFailureCode;
7110 -   __u32 uChangeCount;
7111 -   union {
7112 -      CSMI_SAS_RAID_DRIVES Drives[1];
7113 -      CSMI_SAS_RAID_DEVICE_ID DeviceId[1];
7114 -      CSMI_SAS_RAID_SET_ADDITIONAL_DATA Data[1];
7115 -   };
7116 -} CSMI_SAS_RAID_CONFIG,
7117 -   *PCSMI_SAS_RAID_CONFIG;
7118 -
7119 -typedef struct _CSMI_SAS_RAID_CONFIG_BUFFER {
7120 -   IOCTL_HEADER IoctlHeader;
7121 -   CSMI_SAS_RAID_CONFIG Configuration;
7122 -} CSMI_SAS_RAID_CONFIG_BUFFER,
7123 -  *PCSMI_SAS_RAID_CONFIG_BUFFER;
7124 -
7125 -// CC_CSMI_SAS_GET_RAID_FEATURES
7126 -
7127 -typedef struct _CSMI_SAS_RAID_TYPE_DESCRIPTION {
7128 -  __u8  bRaidType;
7129 -  __u8  bReservedBytes[7];
7130 -  __u32 uSupportedStripeSizeMap;
7131 -  __u8  bReserved[24];
7132 -} CSMI_SAS_RAID_TYPE_DESCRIPTION,
7133 -  *PCSMI_SAS_RAID_TYPE_DESCRIPTION;
7134 -
7135 -typedef struct _CSMI_SAS_RAID_FEATURES {
7136 -   __u32 uFeatures;
7137 -   __u8  bReservedFeatures[32];
7138 -   __u8  bDefaultTransformPriority;
7139 -   __u8  bTransformPriority;
7140 -   __u8  bDefaultRebuildPriority;
7141 -   __u8  bRebuildPriority;
7142 -   __u8  bDefaultSurfaceScanPriority;
7143 -   __u8  bSurfaceScanPriority;
7144 -   __u16 usReserved;
7145 -   __u32 uRaidSetTransformationRules;
7146 -   __u32 uReserved[11];
7147 -   CSMI_SAS_RAID_TYPE_DESCRIPTION RaidType[24];
7148 -   __u8  bCacheRatiosSupported[104];
7149 -   __u32 uChangeCount;
7150 -   __u32 uFailureCode;
7151 -   __u8  bReserved[120];
7152 -} CSMI_SAS_RAID_FEATURES,
7153 -  *PCSMI_SAS_RAID_FEATURES;
7154 -
7155 -typedef struct _CSMI_SAS_RAID_FEATURES_BUFFER {
7156 -   IOCTL_HEADER IoctlHeader;
7157 -   CSMI_SAS_RAID_FEATURES Information;
7158 -} CSMI_SAS_RAID_FEATURES_BUFFER,
7159 -  *PCSMI_SAS_RAID_FEATURES_BUFFER;
7160 -
7161 -// CC_CSMI_SAS_SET_RAID_CONTROL
7162 -
7163 -typedef struct _CSMI_SAS_RAID_CONTROL {
7164 -   __u8  bTransformPriority;
7165 -   __u8  bRebuildPriority;
7166 -   __u8  bCacheRatioFlag;
7167 -   __u8  bCacheRatio;
7168 -   __u8  bSurfaceScanPriority;
7169 -   __u8  bReservedBytes[15];
7170 -   __u8  bClearConfiguration[8];
7171 -   __u32 uChangeCount;
7172 -   __u8  bReserved[88];
7173 -   __u32 uFailureCode;
7174 -   __u8  bFailureDescription[80];
7175 -} CSMI_SAS_RAID_CONTROL,
7176 -  *PCSMI_SAS_RAID_CONTROL;
7177 -
7178 -typedef struct _CSMI_SAS_RAID_CONTROL_BUFFER {
7179 -   IOCTL_HEADER IoctlHeader;
7180 -   CSMI_SAS_RAID_CONTROL Information;
7181 -} CSMI_SAS_RAID_CONTROL_BUFFER,
7182 -  *PCSMI_SAS_RAID_CONTROL_BUFFER;
7183 -
7184 -// CC_CSMI_SAS_GET_RAID_ELEMENT
7185 -
7186 -typedef struct _CSMI_SAS_DRIVE_EXTENT_INFO {
7187 -   __u32 uDriveIndex;
7188 -   __u8  bExtentType;
7189 -   __u8  bReservedBytes[7];
7190 -   struct
7191 -   {
7192 -      __u32 uLowPart;
7193 -      __u32 uHighPart;
7194 -   } ulExtentOffset;
7195 -   struct
7196 -   {
7197 -      __u32 uLowPart;
7198 -      __u32 uHighPart;
7199 -   } ulExtentBlocks;
7200 -   __u32 uRaidSetIndex;
7201 -   __u8  bReserved[96];
7202 -} CSMI_SAS_DRIVE_EXTENT_INFO,
7203 -  *PCSMI_SAS_DRIVE_EXTENT_INFO;
7204 -
7205 -typedef struct _CSMI_SAS_RAID_MODULE_INFO {
7206 -   __u8  bReserved[128];
7207 -} CSMI_SAS_RAID_MODULE_INFO,
7208 -  *PCSMI_SAS_RAID_MODULE_INFO;
7209 -
7210 -typedef struct _CSMI_SAS_DRIVE_LOCATION {
7211 -   __u8  bConnector[16];
7212 -   __u8  bBoxName[16];
7213 -   __u32 uBay;
7214 -   __u8  bReservedBytes[4];
7215 -   __u8  bAttachedSASAddress[8];
7216 -   __u8  bAttachedPhyIdentifier;
7217 -   __u8  bReserved[79];
7218 -} CSMI_SAS_DRIVE_LOCATION,
7219 -  *PCSMI_SAS_DRIVE_LOCATION;
7220 -
7221 -typedef struct _CSMI_SAS_RAID_DRIVES_ADDITIONAL_DATA {
7222 -   __u8  bNegotiatedLinkRate[2];
7223 -   __u8  bReserved[126];
7224 -} CSMI_SAS_RAID_DRIVES_ADDITIONAL_DATA,
7225 -  *PCSMI_SAS_RAID_DRIVES_ADDITIONAL_DATA;
7226 -
7227 -typedef struct _CSMI_SAS_DRIVE_INFO {
7228 -   CSMI_SAS_RAID_DRIVES Device;
7229 -   CSMI_SAS_RAID_DRIVES_ADDITIONAL_DATA Data;
7230 -   CSMI_SAS_DRIVE_LOCATION Location;
7231 -   __u8  bReserved[16];
7232 -} CSMI_SAS_DRIVE_INFO,
7233 -  *PCSMI_SAS_DRIVE_INFO;
7234 -
7235 -typedef struct _CSMI_SAS_RAID_ELEMENT {
7236 -   __u32 uEnumerationType;
7237 -   __u32 uElementIndex;
7238 -   __u32 uNumElements;
7239 -   __u32 uChangeCount;
7240 -   __u32 uSubElementIndex;
7241 -   __u8  bReserved[32];
7242 -   __u32 uFailureCode;
7243 -   __u8  bFailureDescription[80];
7244 -   union {
7245 -       CSMI_SAS_DRIVE_INFO Drive;
7246 -       CSMI_SAS_RAID_MODULE_INFO Module;
7247 -       CSMI_SAS_DRIVE_EXTENT_INFO Extent;
7248 -   } Element;
7249 -} CSMI_SAS_RAID_ELEMENT,
7250 -  *PCSMI_SAS_RAID_ELEMENT;
7251 -
7252 -typedef struct _CSMI_SAS_RAID_ELEMENT_BUFFER {
7253 -   IOCTL_HEADER IoctlHeader;
7254 -   CSMI_SAS_RAID_ELEMENT Information;
7255 -} CSMI_SAS_RAID_ELEMENT_BUFFER,
7256 -  *PCSMI_SAS_RAID_ELEMENT_BUFFER;
7257 -
7258 -// CC_CSMI_SAS_SET_RAID_OPERATION
7259 -
7260 -typedef struct _CSMI_SAS_RAID_SET_LIST {
7261 -   __u32 uRaidSetIndex;
7262 -   __u8  bExistingLun[8];
7263 -   __u8  bNewLun[8];
7264 -   __u8  bReserved[12];
7265 -} CSMI_SAS_RAID_SET_LIST,
7266 -  *PCSMI_SAS_RAID_SET_LIST;
7267 -
7268 -typedef struct _CSMI_SAS_RAID_SET_DRIVE_LIST {
7269 -   __u32 uDriveIndex;
7270 -   __u8  bDriveUsage;
7271 -   __u8  bReserved[27];
7272 -} CSMI_SAS_RAID_SET_DRIVE_LIST,
7273 -  *PCSMI_SAS_RAID_SET_DRIVE_LIST;
7274 -
7275 -typedef struct _CSMI_SAS_RAID_SET_SPARE_INFO {
7276 -   __u32 uRaidSetIndex;
7277 -   __u32 uDriveCount;
7278 -   __u8  bApplicationScratchPad[16];
7279 -   __u8  bReserved[104];
7280 -} CSMI_SAS_RAID_SET_SPARE_INFO,
7281 -  *PCSMI_SAS_RAID_SET_SPARE_INFO;
7282 -
7283 -typedef struct _CSMI_SAS_RAID_SET_ONLINE_STATE_INFO {
7284 -   __u32 uRaidSetIndex;
7285 -   __u8  bOnlineState;
7286 -   __u8  bReserved[123];
7287 -} CSMI_SAS_RAID_SET_ONLINE_STATE_INFO,
7288 -  *PCSMI_SAS_RAID_SET_ONLINE_STATE_INFO;
7289 -
7290 -typedef struct _CSMI_SAS_RAID_SET_CACHE_INFO {
7291 -   __u32 uRaidSetIndex;
7292 -   __u8  bCacheSetting;
7293 -   __u8  bCacheRatioFlag;
7294 -   __u8  bCacheRatio;
7295 -   __u8  bReserved[121];
7296 -} CSMI_SAS_RAID_SET_CACHE_INFO,
7297 -  *PCSMI_SAS_RAID_SET_CACHE_INFO;
7298 -
7299 -typedef struct _CSMI_SAS_RAID_SET_WRITE_PROTECT_INFO {
7300 -   __u32 uRaidSetIndex;
7301 -   __u8  bWriteProtectSetting;
7302 -   __u8  bReserved[123];
7303 -} CSMI_SAS_RAID_SET_WRITE_PROTECT_INFO,
7304 -  *PCSMI_SAS_RAID_SET_WRITE_PROTECT_INFO;
7305 -
7306 -typedef struct _CSMI_SAS_RAID_SET_DELETE_INFO {
7307 -   __u32 uRaidSetIndex;
7308 -   __u8  bReserved[124];
7309 -} CSMI_SAS_RAID_SET_DELETE_INFO,
7310 -  *PCSMI_SAS_RAID_SET_DELETE_INFO;
7311 -
7312 -typedef struct _CSMI_SAS_RAID_SET_MODIFY_INFO {
7313 -   __u8  bRaidType;
7314 -   __u8  bReservedBytes[7];
7315 -   __u32 uStripeSize;
7316 -   struct
7317 -   {
7318 -      __u32 uLowPart;
7319 -      __u32 uHighPart;
7320 -   } ulRaidSetBlocks;
7321 -   struct
7322 -   {
7323 -      __u32 uLowPart;
7324 -      __u32 uHighPart;
7325 -   } ulRaidSetExtentOffset;
7326 -   __u32 uDriveCount;
7327 -   __u8  bReserved[96];
7328 -} CSMI_SAS_RAID_SET_MODIFY_INFO,
7329 -  *PCSMI_SAS_RAID_SET_MODIFY_INFO;
7330 -
7331 -typedef struct _CSMI_SAS_RAID_SET_TRANSFORM_INFO {
7332 -   __u8  bTransformType;
7333 -   __u8  bReservedBytes[3];
7334 -   __u32 uRaidSetIndex;
7335 -   __u8  bRaidType;
7336 -   __u8  bReservedBytes2[11];
7337 -   __u32 uAdditionalRaidSetIndex;
7338 -   __u32 uRaidSetCount;
7339 -   __u8  bApplicationScratchPad[16];
7340 -   CSMI_SAS_RAID_SET_MODIFY_INFO Modify;
7341 -   __u8  bReserved[80];
7342 -} CSMI_SAS_RAID_SET_TRANSFORM_INFO,
7343 -  *PCSMI_SAS_RAID_SET_TRANSFORM_INFO;
7344 -
7345 -typedef struct _CSMI_SAS_RAID_SET_LABEL_INFO {
7346 -   __u32 uRaidSetIndex;
7347 -   __u8  bLabel[16];
7348 -   __u8  bReserved[108];
7349 -} CSMI_SAS_RAID_SET_LABEL_INFO,
7350 -  *PCSMI_SAS_RAID_SET_LABEL_INFO;
7351 -
7352 -typedef struct _CSMI_SAS_RAID_SET_CREATE_INFO {
7353 -   __u8  bRaidType;
7354 -   __u8  bReservedBytes[7];
7355 -   __u32 uStripeSize;
7356 -   __u32 uTrackSectorCount;
7357 -   struct
7358 -   {
7359 -      __u32 uLowPart;
7360 -      __u32 uHighPart;
7361 -   } ulRaidSetBlocks;
7362 -   struct
7363 -   {
7364 -      __u32 uLowPart;
7365 -      __u32 uHighPart;
7366 -   } ulRaidSetExtentOffset;
7367 -   __u32 uDriveCount;
7368 -   __u8  bLabel[16];
7369 -   __u32 uRaidSetIndex;
7370 -   __u8  bApplicationScratchPad[16];
7371 -   __u32 uNumberOfHeads;
7372 -   __u32 uNumberOfTracks;
7373 -   __u8  bReserved[48];
7374 -} CSMI_SAS_RAID_SET_CREATE_INFO,
7375 -  *PCSMI_SAS_RAID_SET_CREATE_INFO;
7376 -
7377 -typedef struct _CSMI_SAS_RAID_SET_OPERATION {
7378 -   __u32 uOperationType;
7379 -   __u32 uChangeCount;
7380 -   __u32 uFailureCode;
7381 -   __u8  bFailureDescription[80];
7382 -   __u8  bReserved[28];
7383 -   union {
7384 -       CSMI_SAS_RAID_SET_CREATE_INFO Create;
7385 -       CSMI_SAS_RAID_SET_LABEL_INFO Label;
7386 -       CSMI_SAS_RAID_SET_TRANSFORM_INFO Transform;
7387 -       CSMI_SAS_RAID_SET_DELETE_INFO Delete;
7388 -       CSMI_SAS_RAID_SET_WRITE_PROTECT_INFO Protect;
7389 -       CSMI_SAS_RAID_SET_CACHE_INFO Cache;
7390 -       CSMI_SAS_RAID_SET_ONLINE_STATE_INFO State;
7391 -       CSMI_SAS_RAID_SET_SPARE_INFO Spare;
7392 -   } Operation;
7393 -   union {
7394 -       CSMI_SAS_RAID_SET_DRIVE_LIST DriveList[1];
7395 -       CSMI_SAS_RAID_SET_LIST RaidSetList[1];
7396 -   } Parameters;
7397 -} CSMI_SAS_RAID_SET_OPERATION,
7398 -  *PCSMI_SAS_RAID_SET_OPERATION;
7399 -
7400 -typedef struct _CSMI_SAS_RAID_SET_OPERATION_BUFFER {
7401 -   IOCTL_HEADER IoctlHeader;
7402 -   CSMI_SAS_RAID_SET_OPERATION Information;
7403 -} CSMI_SAS_RAID_SET_OPERATION_BUFFER,
7404 -  *PCSMI_SAS_RAID_SET_OPERATION_BUFFER;
7405 -
7406 -/* * * * * * * * * * SAS HBA Class Structures * * * * * * * * * */
7407 -
7408 -// CC_CSMI_SAS_GET_PHY_INFO
7409 -
7410 -typedef struct _CSMI_SAS_IDENTIFY {
7411 -   __u8  bDeviceType;
7412 -   __u8  bRestricted;
7413 -   __u8  bInitiatorPortProtocol;
7414 -   __u8  bTargetPortProtocol;
7415 -   __u8  bRestricted2[8];
7416 -   __u8  bSASAddress[8];
7417 -   __u8  bPhyIdentifier;
7418 -   __u8  bSignalClass;
7419 -   __u8  bReserved[6];
7420 -} CSMI_SAS_IDENTIFY,
7421 -  *PCSMI_SAS_IDENTIFY;
7422 -
7423 -typedef struct _CSMI_SAS_PHY_ENTITY {
7424 -   CSMI_SAS_IDENTIFY Identify;
7425 -   __u8  bPortIdentifier;
7426 -   __u8  bNegotiatedLinkRate;
7427 -   __u8  bMinimumLinkRate;
7428 -   __u8  bMaximumLinkRate;
7429 -   __u8  bPhyChangeCount;
7430 -   __u8  bAutoDiscover;
7431 -   __u8  bPhyFeatures;
7432 -   __u8  bReserved;
7433 -   CSMI_SAS_IDENTIFY Attached;
7434 -} CSMI_SAS_PHY_ENTITY,
7435 -  *PCSMI_SAS_PHY_ENTITY;
7436 -
7437 -typedef struct _CSMI_SAS_PHY_INFO {
7438 -   __u8  bNumberOfPhys;
7439 -   __u8  bReserved[3];
7440 -   CSMI_SAS_PHY_ENTITY Phy[32];
7441 -} CSMI_SAS_PHY_INFO,
7442 -  *PCSMI_SAS_PHY_INFO;
7443 -
7444 -typedef struct _CSMI_SAS_PHY_INFO_BUFFER {
7445 -   IOCTL_HEADER IoctlHeader;
7446 -   CSMI_SAS_PHY_INFO Information;
7447 -} CSMI_SAS_PHY_INFO_BUFFER,
7448 -  *PCSMI_SAS_PHY_INFO_BUFFER;
7449 -
7450 -// CC_CSMI_SAS_SET_PHY_INFO
7451 -
7452 -typedef struct _CSMI_SAS_SET_PHY_INFO {
7453 -   __u8  bPhyIdentifier;
7454 -   __u8  bNegotiatedLinkRate;
7455 -   __u8  bProgrammedMinimumLinkRate;
7456 -   __u8  bProgrammedMaximumLinkRate;
7457 -   __u8  bSignalClass;
7458 -   __u8  bReserved[3];
7459 -} CSMI_SAS_SET_PHY_INFO,
7460 -  *PCSMI_SAS_SET_PHY_INFO;
7461 -
7462 -typedef struct _CSMI_SAS_SET_PHY_INFO_BUFFER {
7463 -   IOCTL_HEADER IoctlHeader;
7464 -   CSMI_SAS_SET_PHY_INFO Information;
7465 -} CSMI_SAS_SET_PHY_INFO_BUFFER,
7466 -  *PCSMI_SAS_SET_PHY_INFO_BUFFER;
7467 -
7468 -// CC_CSMI_SAS_GET_LINK_ERRORS
7469 -
7470 -typedef struct _CSMI_SAS_LINK_ERRORS {
7471 -   __u8  bPhyIdentifier;
7472 -   __u8  bResetCounts;
7473 -   __u8  bReserved[2];
7474 -   __u32 uInvalidDwordCount;
7475 -   __u32 uRunningDisparityErrorCount;
7476 -   __u32 uLossOfDwordSyncCount;
7477 -   __u32 uPhyResetProblemCount;
7478 -} CSMI_SAS_LINK_ERRORS,
7479 -  *PCSMI_SAS_LINK_ERRORS;
7480 -
7481 -typedef struct _CSMI_SAS_LINK_ERRORS_BUFFER {
7482 -   IOCTL_HEADER IoctlHeader;
7483 -   CSMI_SAS_LINK_ERRORS Information;
7484 -} CSMI_SAS_LINK_ERRORS_BUFFER,
7485 -  *PCSMI_SAS_LINK_ERRORS_BUFFER;
7486 -
7487 -// CC_CSMI_SAS_SMP_PASSTHRU
7488 -
7489 -typedef struct _CSMI_SAS_SMP_REQUEST {
7490 -   __u8  bFrameType;
7491 -   __u8  bFunction;
7492 -   __u8  bReserved[2];
7493 -   __u8  bAdditionalRequestBytes[1016];
7494 -} CSMI_SAS_SMP_REQUEST,
7495 -  *PCSMI_SAS_SMP_REQUEST;
7496 -
7497 -typedef struct _CSMI_SAS_SMP_RESPONSE {
7498 -   __u8  bFrameType;
7499 -   __u8  bFunction;
7500 -   __u8  bFunctionResult;
7501 -   __u8  bReserved;
7502 -   __u8  bAdditionalResponseBytes[1016];
7503 -} CSMI_SAS_SMP_RESPONSE,
7504 -  *PCSMI_SAS_SMP_RESPONSE;
7505 -
7506 -typedef struct _CSMI_SAS_SMP_PASSTHRU {
7507 -   __u8  bPhyIdentifier;
7508 -   __u8  bPortIdentifier;
7509 -   __u8  bConnectionRate;
7510 -   __u8  bReserved;
7511 -   __u8  bDestinationSASAddress[8];
7512 -   __u32 uRequestLength;
7513 -   CSMI_SAS_SMP_REQUEST Request;
7514 -   __u8  bConnectionStatus;
7515 -   __u8  bReserved2[3];
7516 -   __u32 uResponseBytes;
7517 -   CSMI_SAS_SMP_RESPONSE Response;
7518 -} CSMI_SAS_SMP_PASSTHRU,
7519 -  *PCSMI_SAS_SMP_PASSTHRU;
7520 -
7521 -typedef struct _CSMI_SAS_SMP_PASSTHRU_BUFFER {
7522 -   IOCTL_HEADER IoctlHeader;
7523 -   CSMI_SAS_SMP_PASSTHRU Parameters;
7524 -} CSMI_SAS_SMP_PASSTHRU_BUFFER,
7525 -  *PCSMI_SAS_SMP_PASSTHRU_BUFFER;
7526 -
7527 -// CC_CSMI_SAS_SSP_PASSTHRU
7528 -
7529 -typedef struct _CSMI_SAS_SSP_PASSTHRU {
7530 -   __u8  bPhyIdentifier;
7531 -   __u8  bPortIdentifier;
7532 -   __u8  bConnectionRate;
7533 -   __u8  bReserved;
7534 -   __u8  bDestinationSASAddress[8];
7535 -   __u8  bLun[8];
7536 -   __u8  bCDBLength;
7537 -   __u8  bAdditionalCDBLength;
7538 -   __u8  bReserved2[2];
7539 -   __u8  bCDB[16];
7540 -   __u32 uFlags;
7541 -   __u8  bAdditionalCDB[24];
7542 -   __u32 uDataLength;
7543 -} CSMI_SAS_SSP_PASSTHRU,
7544 -  *PCSMI_SAS_SSP_PASSTHRU;
7545 -
7546 -typedef struct _CSMI_SAS_SSP_PASSTHRU_STATUS {
7547 -   __u8  bConnectionStatus;
7548 -   __u8  bSSPStatus;
7549 -   __u8  bReserved[2];
7550 -   __u8  bDataPresent;
7551 -   __u8  bStatus;
7552 -   __u8  bResponseLength[2];
7553 -   __u8  bResponse[256];
7554 -   __u32 uDataBytes;
7555 -} CSMI_SAS_SSP_PASSTHRU_STATUS,
7556 -  *PCSMI_SAS_SSP_PASSTHRU_STATUS;
7557 -
7558 -typedef struct _CSMI_SAS_SSP_PASSTHRU_BUFFER {
7559 -   IOCTL_HEADER IoctlHeader;
7560 -   CSMI_SAS_SSP_PASSTHRU Parameters;
7561 -   CSMI_SAS_SSP_PASSTHRU_STATUS Status;
7562 -   __u8  bDataBuffer[1];
7563 -} CSMI_SAS_SSP_PASSTHRU_BUFFER,
7564 -  *PCSMI_SAS_SSP_PASSTHRU_BUFFER;
7565 -
7566 -// CC_CSMI_SAS_STP_PASSTHRU
7567 -
7568 -typedef struct _CSMI_SAS_STP_PASSTHRU {
7569 -   __u8  bPhyIdentifier;
7570 -   __u8  bPortIdentifier;
7571 -   __u8  bConnectionRate;
7572 -   __u8  bReserved;
7573 -   __u8  bDestinationSASAddress[8];
7574 -   __u8  bReserved2[4];
7575 -   __u8  bCommandFIS[20];
7576 -   __u32 uFlags;
7577 -   __u32 uDataLength;
7578 -} CSMI_SAS_STP_PASSTHRU,
7579 -  *PCSMI_SAS_STP_PASSTHRU;
7580 -
7581 -typedef struct _CSMI_SAS_STP_PASSTHRU_STATUS {
7582 -   __u8  bConnectionStatus;
7583 -   __u8  bReserved[3];
7584 -   __u8  bStatusFIS[20];
7585 -   __u32 uSCR[16];
7586 -   __u32 uDataBytes;
7587 -} CSMI_SAS_STP_PASSTHRU_STATUS,
7588 -  *PCSMI_SAS_STP_PASSTHRU_STATUS;
7589 -
7590 -typedef struct _CSMI_SAS_STP_PASSTHRU_BUFFER {
7591 -   IOCTL_HEADER IoctlHeader;
7592 -   CSMI_SAS_STP_PASSTHRU Parameters;
7593 -   CSMI_SAS_STP_PASSTHRU_STATUS Status;
7594 -   __u8  bDataBuffer[1];
7595 -} CSMI_SAS_STP_PASSTHRU_BUFFER,
7596 -  *PCSMI_SAS_STP_PASSTHRU_BUFFER;
7597 -
7598 -// CC_CSMI_SAS_GET_SATA_SIGNATURE
7599 -
7600 -typedef struct _CSMI_SAS_SATA_SIGNATURE {
7601 -   __u8  bPhyIdentifier;
7602 -   __u8  bReserved[3];
7603 -   __u8  bSignatureFIS[20];
7604 -} CSMI_SAS_SATA_SIGNATURE,
7605 -  *PCSMI_SAS_SATA_SIGNATURE;
7606 -
7607 -typedef struct _CSMI_SAS_SATA_SIGNATURE_BUFFER {
7608 -   IOCTL_HEADER IoctlHeader;
7609 -   CSMI_SAS_SATA_SIGNATURE Signature;
7610 -} CSMI_SAS_SATA_SIGNATURE_BUFFER,
7611 -  *PCSMI_SAS_SATA_SIGNATURE_BUFFER;
7612 -
7613 -// CC_CSMI_SAS_GET_SCSI_ADDRESS
7614 -
7615 -typedef struct _CSMI_SAS_GET_SCSI_ADDRESS_BUFFER {
7616 -   IOCTL_HEADER IoctlHeader;
7617 -   __u8  bSASAddress[8];
7618 -   __u8  bSASLun[8];
7619 -   __u8  bHostIndex;
7620 -   __u8  bPathId;
7621 -   __u8  bTargetId;
7622 -   __u8  bLun;
7623 -} CSMI_SAS_GET_SCSI_ADDRESS_BUFFER,
7624 -   *PCSMI_SAS_GET_SCSI_ADDRESS_BUFFER;
7625 -
7626 -// CC_CSMI_SAS_GET_DEVICE_ADDRESS
7627 -
7628 -typedef struct _CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER {
7629 -   IOCTL_HEADER IoctlHeader;
7630 -   __u8  bHostIndex;
7631 -   __u8  bPathId;
7632 -   __u8  bTargetId;
7633 -   __u8  bLun;
7634 -   __u8  bSASAddress[8];
7635 -   __u8  bSASLun[8];
7636 -} CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER,
7637 -  *PCSMI_SAS_GET_DEVICE_ADDRESS_BUFFER;
7638 -
7639 -// CC_CSMI_SAS_TASK_MANAGEMENT
7640 -
7641 -typedef struct _CSMI_SAS_SSP_TASK_IU {
7642 -   __u8  bHostIndex;
7643 -   __u8  bPathId;
7644 -   __u8  bTargetId;
7645 -   __u8  bLun;
7646 -   __u32 uFlags;
7647 -   __u32 uQueueTag;
7648 -   __u32 uReserved;
7649 -   __u8  bTaskManagementFunction;
7650 -   __u8  bReserved[7];
7651 -   __u32 uInformation;
7652 -} CSMI_SAS_SSP_TASK_IU,
7653 -  *PCSMI_SAS_SSP_TASK_IU;
7654 -
7655 -typedef struct _CSMI_SAS_SSP_TASK_IU_BUFFER {
7656 -   IOCTL_HEADER IoctlHeader;
7657 -   CSMI_SAS_SSP_TASK_IU Parameters;
7658 -   CSMI_SAS_SSP_PASSTHRU_STATUS Status;
7659 -} CSMI_SAS_SSP_TASK_IU_BUFFER,
7660 -  *PCSMI_SAS_SSP_TASK_IU_BUFFER;
7661 -
7662 -// CC_CSMI_SAS_GET_CONNECTOR_INFO
7663 -
7664 -typedef struct _CSMI_SAS_GET_CONNECTOR_INFO {
7665 -   __u32 uPinout;
7666 -   __u8  bConnector[16];
7667 -   __u8  bLocation;
7668 -   __u8  bReserved[15];
7669 -} CSMI_SAS_CONNECTOR_INFO,
7670 -  *PCSMI_SAS_CONNECTOR_INFO;
7671 -
7672 -typedef struct _CSMI_SAS_CONNECTOR_INFO_BUFFER {
7673 -   IOCTL_HEADER IoctlHeader;
7674 -   CSMI_SAS_CONNECTOR_INFO Reference[32];
7675 -} CSMI_SAS_CONNECTOR_INFO_BUFFER,
7676 -  *PCSMI_SAS_CONNECTOR_INFO_BUFFER;
7677 -
7678 -// CC_CSMI_SAS_GET_LOCATION
7679 -
7680 -typedef struct _CSMI_SAS_LOCATION_IDENTIFIER {
7681 -   __u32 bLocationFlags;
7682 -   __u8  bSASAddress[8];
7683 -   __u8  bSASLun[8];
7684 -   __u8  bEnclosureIdentifier[8];
7685 -   __u8  bEnclosureName[32];
7686 -   __u8  bBayPrefix[32];
7687 -   __u8  bBayIdentifier;
7688 -   __u8  bLocationState;
7689 -   __u8  bReserved[2];
7690 -} CSMI_SAS_LOCATION_IDENTIFIER,
7691 -  *PCSMI_SAS_LOCATION_IDENTIFIER;
7692 -
7693 -typedef struct _CSMI_SAS_GET_LOCATION_BUFFER {
7694 -   IOCTL_HEADER IoctlHeader;
7695 -   __u8  bHostIndex;
7696 -   __u8  bPathId;
7697 -   __u8  bTargetId;
7698 -   __u8  bLun;
7699 -   __u8  bIdentify;
7700 -   __u8  bNumberOfLocationIdentifiers;
7701 -   __u8  bLengthOfLocationIdentifier;
7702 -   CSMI_SAS_LOCATION_IDENTIFIER Location[1];
7703 -} CSMI_SAS_GET_LOCATION_BUFFER,
7704 -  *PCSMI_SAS_GET_LOCATION_BUFFER;
7705 -
7706 -// CC_CSMI_SAS_PHY_CONTROL
7707 -
7708 -typedef struct _CSMI_SAS_CHARACTER {
7709 -   __u8  bTypeFlags;
7710 -   __u8  bValue;
7711 -} CSMI_SAS_CHARACTER,
7712 -  *PCSMI_SAS_CHARACTER;
7713 -
7714 -typedef struct _CSMI_SAS_PHY_CONTROL {
7715 -   __u8  bType;
7716 -   __u8  bRate;
7717 -   __u8  bReserved[6];
7718 -   __u32 uVendorUnique[8];
7719 -   __u32 uTransmitterFlags;
7720 -   __i8  bTransmitAmplitude;
7721 -   __i8  bTransmitterPreemphasis;
7722 -   __i8  bTransmitterSlewRate;
7723 -   __i8  bTransmitterReserved[13];
7724 -   __u8  bTransmitterVendorUnique[64];
7725 -   __u32 uReceiverFlags;
7726 -   __i8  bReceiverThreshold;
7727 -   __i8  bReceiverEqualizationGain;
7728 -   __i8  bReceiverReserved[14];
7729 -   __u8  bReceiverVendorUnique[64];
7730 -   __u32 uPatternFlags;
7731 -   __u8  bFixedPattern;
7732 -   __u8  bUserPatternLength;
7733 -   __u8  bPatternReserved[6];
7734 -   CSMI_SAS_CHARACTER UserPatternBuffer[16];
7735 -} CSMI_SAS_PHY_CONTROL,
7736 -  *PCSMI_SAS_PHY_CONTROL;
7737 -
7738 -typedef struct _CSMI_SAS_PHY_CONTROL_BUFFER {
7739 -   IOCTL_HEADER IoctlHeader;
7740 -   __u32 uFunction;
7741 -   __u8  bPhyIdentifier;
7742 -   __u16 usLengthOfControl;
7743 -   __u8  bNumberOfControls;
7744 -   __u8  bReserved[4];
7745 -   __u32 uLinkFlags;
7746 -   __u8  bSpinupRate;
7747 -   __u8  bLinkReserved[7];
7748 -   __u32 uVendorUnique[8];
7749 -   CSMI_SAS_PHY_CONTROL Control[1];
7750 -} CSMI_SAS_PHY_CONTROL_BUFFER,
7751 -  *PCSMI_SAS_PHY_CONTROL_BUFFER;
7752 -
7753 -//EDM #pragma CSMI_SAS_END_PACK
7754 -#pragma pack()
7755 -
7756 -#endif // _CSMI_SAS_H_
7757 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/csmisas.c linux-2.6.9-55.0.12/drivers/message/fusion/csmisas.c
7758 --- linux-2.6.9-67.0.1/drivers/message/fusion/csmisas.c 1970-01-01 01:00:00.000000000 +0100
7759 +++ linux-2.6.9-55.0.12/drivers/message/fusion/csmisas.c        2007-11-02 09:10:23.000000000 +0100
7760 @@ -0,0 +1,5095 @@
7761 +#define mptctl_is_this_sas_cntr(ioc) (ioc->bus_type == SAS) ? 1 : 0
7762 +
7763 +#ifndef TRUE
7764 +#define TRUE     (1)
7765 +#endif
7766 +#ifndef FALSE
7767 +#define FALSE    (0)
7768 +#endif
7769 +
7770 +#ifdef QUIESE_IO
7771 +static int mptctl_raid_get_volume_id(MPT_ADAPTER *ioc, u8 PhysDiskNum, u8 *VolumeID,
7772 +    u8 *VolumeBus);
7773 +#endif
7774 +static int mptctl_do_raid(MPT_ADAPTER *ioc, u8 action, u8 PhysDiskNum, u8 VolumeBus,
7775 +    u8 VolumeId, pMpiRaidActionReply_t reply);
7776 +static u8  map_sas_status_to_csmi(u8 mpi_sas_status);
7777 +
7778 +static u64 reverse_byte_order64(u64 * data64)
7779 +{
7780 +       int i;
7781 +       u64 rc;
7782 +       u8  * inWord = (u8 *)data64, * outWord = (u8 *)&rc;
7783 +
7784 +       for (i=0;i<8;i++) outWord[i] = inWord[7-i];
7785 +
7786 +       return rc;
7787 +}
7788 +
7789 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
7790 +/* Routine for the CSMI Sas Get Driver Info command.
7791 + *
7792 + * Outputs:    None.
7793 + * Return:     0 if successful
7794 + *             -EFAULT if data unavailable
7795 + *             -ENODEV if no such device/adapter
7796 + */
7797 +static int
7798 +mptctl_csmi_sas_get_driver_info(unsigned long arg)
7799 +{
7800 +
7801 +       CSMI_SAS_DRIVER_INFO_BUFFER __user *uarg = (void __user *) arg;
7802 +       CSMI_SAS_DRIVER_INFO_BUFFER     karg;
7803 +       MPT_ADAPTER     *ioc = NULL;
7804 +       int             iocnum;
7805 +
7806 +       dctlprintk((": %s called.\n",__FUNCTION__));
7807 +
7808 +       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_DRIVER_INFO_BUFFER))) {
7809 +               printk(KERN_ERR "%s@%d::%s - "
7810 +             "Unable to read in csmi_sas_get_driver_info_buffer struct @ %p\n",
7811 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
7812 +               return -EFAULT;
7813 +       }
7814 +
7815 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
7816 +           &ioc)) < 0) || (ioc == NULL)) {
7817 +               dctlprintk((KERN_ERR
7818 +                   "%s::%s() @%d - ioc%d not found!\n",
7819 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
7820 +               return -ENODEV;
7821 +       }
7822 +
7823 +       if (!mptctl_is_this_sas_cntr(ioc)) {
7824 +               dctlprintk((KERN_ERR
7825 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
7826 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
7827 +               return -ENODEV;
7828 +       }
7829 +
7830 +       /* Fill in the data and return the structure to the calling
7831 +        * program
7832 +        */
7833 +       memcpy( karg.Information.szName, MPT_MISCDEV_BASENAME,
7834 +           sizeof(MPT_MISCDEV_BASENAME));
7835 +       memcpy( karg.Information.szDescription, MPT_CSMI_DESCRIPTION,
7836 +           sizeof(MPT_CSMI_DESCRIPTION));
7837 +
7838 +       karg.Information.usMajorRevision = MPT_LINUX_MAJOR_VERSION;
7839 +       karg.Information.usMinorRevision = MPT_LINUX_MINOR_VERSION;
7840 +       karg.Information.usBuildRevision = MPT_LINUX_BUILD_VERSION;
7841 +       karg.Information.usReleaseRevision = MPT_LINUX_RELEASE_VERSION;
7842 +
7843 +       karg.Information.usCSMIMajorRevision = CSMI_MAJOR_REVISION;
7844 +       karg.Information.usCSMIMinorRevision = CSMI_MINOR_REVISION;
7845 +
7846 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
7847 +
7848 +       /* Copy the data from kernel memory to user memory
7849 +        */
7850 +       if (copy_to_user((char *)arg, &karg,
7851 +               sizeof(CSMI_SAS_DRIVER_INFO_BUFFER))) {
7852 +               printk(KERN_ERR "%s@%d::%s - "
7853 +                  "Unable to write out csmi_sas_get_driver_info_buffer @ %p\n",
7854 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
7855 +               return -EFAULT;
7856 +       }
7857 +
7858 +       return 0;
7859 +}
7860 +
7861 +
7862 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
7863 +/* Prototype Routine for the CSMI_SAS_GET_CNTLR_CONFIG command.
7864 + *
7865 + * Outputs:    None.
7866 + * Return:     0 if successful
7867 + *             -EFAULT if data unavailable
7868 + *             -ENODEV if no such device/adapter
7869 + */
7870 +static int
7871 +mptctl_csmi_sas_get_cntlr_config(unsigned long arg)
7872 +{
7873 +
7874 +       CSMI_SAS_CNTLR_CONFIG_BUFFER __user *uarg = (void __user *) arg;
7875 +       CSMI_SAS_CNTLR_CONFIG_BUFFER    karg;
7876 +       MPT_ADAPTER     *ioc = NULL;
7877 +       int             iocnum;
7878 +       int             ii;
7879 +       unsigned int    reg;
7880 +       u32             l;
7881 +
7882 +       dctlprintk((": %s called.\n",__FUNCTION__));
7883 +
7884 +       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_CNTLR_CONFIG_BUFFER))) {
7885 +               printk(KERN_ERR "%s@%d::%s - "
7886 +            "Unable to read in csmi_sas_get_cntlr_config_buffer struct @ %p\n",
7887 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
7888 +               return -EFAULT;
7889 +       }
7890 +
7891 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
7892 +           &ioc)) < 0) || (ioc == NULL)) {
7893 +               dctlprintk((KERN_ERR
7894 +             "%s::%s() @%d - ioc%d not found!\n",
7895 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
7896 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
7897 +               return -ENODEV;
7898 +       }
7899 +
7900 +       if (!mptctl_is_this_sas_cntr(ioc)) {
7901 +               dctlprintk((KERN_ERR
7902 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
7903 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
7904 +               return -ENODEV;
7905 +       }
7906 +
7907 +       /* Clear the struct before filling in data. */
7908 +       memset( &karg.Configuration, 0, sizeof(CSMI_SAS_CNTLR_CONFIG));
7909 +
7910 +       /* Fill in the data and return the structure to the calling
7911 +        * program
7912 +        */
7913 +
7914 +       /* Get Base IO and Mem Mapped Addresses. */
7915 +       for(ii=0; ii < DEVICE_COUNT_RESOURCE; ii++) {
7916 +               reg = PCI_BASE_ADDRESS_0 + (ii << 2);
7917 +               pci_read_config_dword(ioc->pcidev, reg, &l);
7918 +
7919 +               if ((l & PCI_BASE_ADDRESS_SPACE) ==
7920 +                   PCI_BASE_ADDRESS_SPACE_MEMORY) {
7921 +                       karg.Configuration.BaseMemoryAddress.uLowPart =
7922 +                           l & PCI_BASE_ADDRESS_MEM_MASK;
7923 +               }
7924 +               else {
7925 +                       karg.Configuration.uBaseIoAddress =
7926 +                           l & PCI_BASE_ADDRESS_IO_MASK;
7927 +               }
7928 +
7929 +               if ((l & (PCI_BASE_ADDRESS_SPACE |
7930 +                   PCI_BASE_ADDRESS_MEM_TYPE_MASK))
7931 +                   == (PCI_BASE_ADDRESS_SPACE_MEMORY |
7932 +                   PCI_BASE_ADDRESS_MEM_TYPE_64)) {
7933 +                       pci_read_config_dword(ioc->pcidev, reg+4, &l);
7934 +                       karg.Configuration.BaseMemoryAddress.uHighPart = l;
7935 +               }
7936 +               if ((l & PCI_BASE_ADDRESS_SPACE) ==
7937 +                   PCI_BASE_ADDRESS_SPACE_MEMORY) {
7938 +                       break;
7939 +               }
7940 +       }
7941 +
7942 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,0)
7943 +       karg.Configuration.uBoardID = (ioc->pcidev->subsystem_device << 16) |
7944 +           (ioc->pcidev->subsystem_vendor);
7945 +#endif
7946 +
7947 +       karg.Configuration.usSlotNumber =
7948 +           (ioc->pci_slot_number = 0xff) ?
7949 +           SLOT_NUMBER_UNKNOWN : ioc->pci_slot_number;
7950 +       karg.Configuration.bControllerClass = CSMI_SAS_CNTLR_CLASS_HBA;
7951 +       karg.Configuration.bIoBusType = CSMI_SAS_BUS_TYPE_PCI;
7952 +       karg.Configuration.BusAddress.PciAddress.bBusNumber =
7953 +           ioc->pcidev->bus->number;
7954 +       karg.Configuration.BusAddress.PciAddress.bDeviceNumber =
7955 +           PCI_SLOT(ioc->pcidev->devfn);
7956 +       karg.Configuration.BusAddress.PciAddress.bFunctionNumber =
7957 +           PCI_FUNC(ioc->pcidev->devfn);
7958 +       karg.Configuration.BusAddress.PciAddress.bReserved = 0;
7959 +       memcpy( &karg.Configuration.szSerialNumber,ioc->BoardTracerNumber, 16 );
7960 +       karg.Configuration.usMajorRevision = ioc->facts.FWVersion.Struct.Major;
7961 +       karg.Configuration.usMinorRevision = ioc->facts.FWVersion.Struct.Minor;
7962 +       karg.Configuration.usBuildRevision = ioc->facts.FWVersion.Struct.Unit;
7963 +       karg.Configuration.usReleaseRevision = ioc->facts.FWVersion.Struct.Dev;
7964 +       karg.Configuration.usBIOSMajorRevision =
7965 +           (ioc->biosVersion & 0xFF000000) >> 24;
7966 +       karg.Configuration.usBIOSMinorRevision =
7967 +           (ioc->biosVersion & 0x00FF0000) >> 16;
7968 +       karg.Configuration.usBIOSBuildRevision =
7969 +           (ioc->biosVersion & 0x0000FF00) >> 8;
7970 +       karg.Configuration.usBIOSReleaseRevision =
7971 +           (ioc->biosVersion & 0x000000FF);
7972 +       karg.Configuration.uControllerFlags =
7973 +           CSMI_SAS_CNTLR_SAS_HBA | CSMI_SAS_CNTLR_SAS_RAID | 
7974 +           CSMI_SAS_CNTLR_FWD_SUPPORT | CSMI_SAS_CNTLR_FWD_ONLINE | 
7975 +           CSMI_SAS_CNTLR_FWD_SRESET ;
7976 +
7977 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
7978 +
7979 +       /* All Rrom entries will be zero. Skip them. */
7980 +       /* bReserved will also be zeros. */
7981 +       /* Copy the data from kernel memory to user memory
7982 +        */
7983 +       if (copy_to_user((char *)arg, &karg,
7984 +               sizeof(CSMI_SAS_DRIVER_INFO_BUFFER))) {
7985 +               printk(KERN_ERR "%s@%d::%s - "
7986 +               "Unable to write out csmi_sas_get_driver_info_buffer @ %p\n",
7987 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
7988 +               return -EFAULT;
7989 +       }
7990 +
7991 +       return 0;
7992 +}
7993 +
7994 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
7995 +/* Prototype Routine for the CSMI Sas Get Controller Status command.
7996 + *
7997 + * Outputs:    None.
7998 + * Return:     0 if successful
7999 + *             -EFAULT if data unavailable
8000 + *             -ENODEV if no such device/adapter
8001 + */
8002 +static int
8003 +mptctl_csmi_sas_get_cntlr_status(unsigned long arg)
8004 +{
8005 +
8006 +       CSMI_SAS_CNTLR_STATUS_BUFFER  __user *uarg = (void __user *) arg;
8007 +       MPT_ADAPTER             *ioc = NULL;
8008 +       CSMI_SAS_CNTLR_STATUS_BUFFER    karg;
8009 +       int                     iocnum;
8010 +       int                     rc;
8011 +
8012 +       dctlprintk((": %s called.\n",__FUNCTION__));
8013 +
8014 +       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_CNTLR_STATUS_BUFFER))) {
8015 +               printk(KERN_ERR "%s@%d::%s - "
8016 +            "Unable to read in csmi_sas_get_cntlr_status_buffer struct @ %p\n",
8017 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
8018 +               return -EFAULT;
8019 +       }
8020 +
8021 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
8022 +           &ioc)) < 0) || (ioc == NULL)) {
8023 +               dctlprintk((KERN_ERR
8024 +                   "%s::%s() @%d - ioc%d not found!\n",
8025 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
8026 +               return -ENODEV;
8027 +       }
8028 +
8029 +       if (!mptctl_is_this_sas_cntr(ioc)) {
8030 +               dctlprintk((KERN_ERR
8031 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
8032 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
8033 +               return -ENODEV;
8034 +       }
8035 +
8036 +       /* Fill in the data and return the structure to the calling
8037 +        * program
8038 +        */
8039 +
8040 +       rc = mpt_GetIocState(ioc, 1);
8041 +       switch (rc) {
8042 +       case MPI_IOC_STATE_OPERATIONAL:
8043 +               karg.Status.uStatus =  CSMI_SAS_CNTLR_STATUS_GOOD;
8044 +               karg.Status.uOfflineReason = 0;
8045 +               break;
8046 +
8047 +       case MPI_IOC_STATE_FAULT:
8048 +               karg.Status.uStatus = CSMI_SAS_CNTLR_STATUS_FAILED;
8049 +               karg.Status.uOfflineReason = 0;
8050 +               break;
8051 +
8052 +       case MPI_IOC_STATE_RESET:
8053 +       case MPI_IOC_STATE_READY:
8054 +       default:
8055 +               karg.Status.uStatus =  CSMI_SAS_CNTLR_STATUS_OFFLINE;
8056 +               karg.Status.uOfflineReason =
8057 +                   CSMI_SAS_OFFLINE_REASON_INITIALIZING;
8058 +               break;
8059 +       }
8060 +
8061 +       memset(&karg.Status.bReserved, 0, 28);
8062 +
8063 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
8064 +
8065 +       /* Copy the data from kernel memory to user memory
8066 +        */
8067 +       if (copy_to_user((char *)arg, &karg,
8068 +               sizeof(CSMI_SAS_CNTLR_STATUS_BUFFER))) {
8069 +               printk(KERN_ERR "%s@%d::%s - "
8070 +                   "Unable to write out csmi_sas_get_cntlr_status @ %p\n",
8071 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
8072 +               return -EFAULT;
8073 +       }
8074 +
8075 +       return 0;
8076 +}
8077 +
8078 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
8079 +/* Prototype Routine for the CSMI Sas Get Phy Info command.
8080 + *
8081 + * Outputs:    None.
8082 + * Return:     0 if successful
8083 + *             -EFAULT if data unavailable
8084 + *             -ENODEV if no such device/adapter
8085 + */
8086 +static int
8087 +mptctl_csmi_sas_get_phy_info(unsigned long arg)
8088 +{
8089 +       CSMI_SAS_PHY_INFO_BUFFER __user *uarg = (void __user *) arg;
8090 +       CSMI_SAS_PHY_INFO_BUFFER  karg;
8091 +       MPT_ADAPTER             *ioc = NULL;
8092 +       ConfigExtendedPageHeader_t  hdr;
8093 +       CONFIGPARMS             cfg;
8094 +       SasIOUnitPage0_t        *sasIoUnitPg0;
8095 +       dma_addr_t              sasIoUnitPg0_dma;
8096 +       int                     sasIoUnitPg0_data_sz;
8097 +       SasPhyPage0_t           *sasPhyPg0;
8098 +       dma_addr_t              sasPhyPg0_dma;
8099 +       int                     sasPhyPg0_data_sz;
8100 +       u16                     protocol;
8101 +       int                     iocnum;
8102 +       int                     rc;
8103 +       int                     ii;
8104 +       u64                     SASAddress64;
8105 +
8106 +       dctlprintk((": %s called.\n",__FUNCTION__));
8107 +       sasIoUnitPg0=NULL;
8108 +       sasPhyPg0=NULL;
8109 +       sasIoUnitPg0_data_sz=0;
8110 +       sasPhyPg0_data_sz=0;
8111 +
8112 +       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_PHY_INFO_BUFFER))) {
8113 +               printk(KERN_ERR "%s@%d::%s - "
8114 +               "Unable to read in csmi_sas_get_phy_info_buffer struct @ %p\n",
8115 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
8116 +               return -EFAULT;
8117 +       }
8118 +
8119 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
8120 +           &ioc)) < 0) || (ioc == NULL)) {
8121 +               dctlprintk((KERN_ERR
8122 +                   "%s::%s() @%d - ioc%d not found!\n",
8123 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
8124 +               return -ENODEV;
8125 +       }
8126 +
8127 +       if (!mptctl_is_this_sas_cntr(ioc)) {
8128 +               dctlprintk((KERN_ERR
8129 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
8130 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
8131 +               return -ENODEV;
8132 +       }
8133 +
8134 +       /* Fill in the data and return the structure to the calling
8135 +        * program
8136 +        */
8137 +       memset( &karg.Information, 0, sizeof(CSMI_SAS_PHY_INFO));
8138 +
8139 +       /* Issue a config request to get the number of phys
8140 +        */
8141 +       hdr.PageVersion = MPI_SASIOUNITPAGE0_PAGEVERSION;
8142 +       hdr.ExtPageLength = 0;
8143 +       hdr.PageNumber = 0;
8144 +       hdr.Reserved1 = 0;
8145 +       hdr.Reserved2 = 0;
8146 +       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
8147 +       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_IO_UNIT;
8148 +
8149 +       cfg.cfghdr.ehdr = &hdr;
8150 +       cfg.physAddr = -1;
8151 +       cfg.pageAddr = 0;
8152 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
8153 +       cfg.dir = 0;    /* read */
8154 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
8155 +
8156 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
8157 +               /* Don't check if this failed.  Already in a
8158 +                * failure case.
8159 +                */
8160 +               dctlprintk((
8161 +                   ": FAILED: MPI_SASIOUNITPAGE0_PAGEVERSION: HEADER\n"));
8162 +               dctlprintk((": rc=%x\n",rc));
8163 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8164 +               goto sas_get_phy_info_exit;
8165 +       }
8166 +
8167 +       if (hdr.ExtPageLength == 0) {
8168 +               /* Don't check if this failed.  Already in a
8169 +                * failure case.
8170 +                */
8171 +               dctlprintk((": hdr.ExtPageLength == 0\n"));
8172 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8173 +               goto sas_get_phy_info_exit;
8174 +       }
8175 +
8176 +       sasIoUnitPg0_data_sz = hdr.ExtPageLength * 4;
8177 +       rc = -ENOMEM;
8178 +
8179 +       sasIoUnitPg0 = (SasIOUnitPage0_t *) pci_alloc_consistent(ioc->pcidev,
8180 +           sasIoUnitPg0_data_sz, &sasIoUnitPg0_dma);
8181 +
8182 +       if (!sasIoUnitPg0) {
8183 +               dctlprintk((": pci_alloc_consistent: FAILED\n"));
8184 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8185 +               goto sas_get_phy_info_exit;
8186 +       }
8187 +
8188 +       memset((u8 *)sasIoUnitPg0, 0, sasIoUnitPg0_data_sz);
8189 +       cfg.physAddr = sasIoUnitPg0_dma;
8190 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
8191 +
8192 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
8193 +
8194 +               /* Don't check if this failed.  Already in a
8195 +                * failure case.
8196 +                */
8197 +               dctlprintk((
8198 +                   ": FAILED: MPI_SASIOUNITPAGE0_PAGEVERSION: PAGE\n"));
8199 +               dctlprintk((": rc=%x\n",rc));
8200 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8201 +               goto sas_get_phy_info_exit;
8202 +       }
8203 +
8204 +
8205 +       /* Number of Phys. */
8206 +       karg.Information.bNumberOfPhys = sasIoUnitPg0->NumPhys;
8207 +
8208 +       /* Fill in information for each phy. */
8209 +       for (ii = 0; ii < karg.Information.bNumberOfPhys; ii++) {
8210 +
8211 +/* EDM : dump IO Unit Page 0 data*/
8212 +               dsasprintk(("---- IO UNIT PAGE 0 ------------\n"));
8213 +               dsasprintk(("Handle=0x%X\n",
8214 +                   le16_to_cpu(sasIoUnitPg0->PhyData[ii].AttachedDeviceHandle)));
8215 +               dsasprintk(("Controller Handle=0x%X\n",
8216 +                   le16_to_cpu(sasIoUnitPg0->PhyData[ii].ControllerDevHandle)));
8217 +               dsasprintk(("Port=0x%X\n",
8218 +                   sasIoUnitPg0->PhyData[ii].Port));
8219 +               dsasprintk(("Port Flags=0x%X\n",
8220 +                   sasIoUnitPg0->PhyData[ii].PortFlags));
8221 +               dsasprintk(("PHY Flags=0x%X\n",
8222 +                   sasIoUnitPg0->PhyData[ii].PhyFlags));
8223 +               dsasprintk(("Negotiated Link Rate=0x%X\n",
8224 +                   sasIoUnitPg0->PhyData[ii].NegotiatedLinkRate));
8225 +               dsasprintk(("Controller PHY Device Info=0x%X\n",
8226 +                   le32_to_cpu(sasIoUnitPg0->PhyData[ii].ControllerPhyDeviceInfo)));
8227 +               dsasprintk(("DiscoveryStatus=0x%X\n",
8228 +                   le32_to_cpu(sasIoUnitPg0->PhyData[ii].DiscoveryStatus)));
8229 +               dsasprintk(("\n"));
8230 +/* EDM : debug data */
8231 +
8232 +               /* PHY stuff. */
8233 +               karg.Information.Phy[ii].bPortIdentifier =
8234 +                   sasIoUnitPg0->PhyData[ii].Port;
8235 +
8236 +               /* Get the negotiated link rate for the phy. */
8237 +               switch (sasIoUnitPg0->PhyData[ii].NegotiatedLinkRate) {
8238 +
8239 +               case MPI_SAS_IOUNIT0_RATE_PHY_DISABLED:
8240 +                       karg.Information.Phy[ii].bNegotiatedLinkRate =
8241 +                           CSMI_SAS_PHY_DISABLED;
8242 +                       break;
8243 +
8244 +               case MPI_SAS_IOUNIT0_RATE_FAILED_SPEED_NEGOTIATION:
8245 +                       karg.Information.Phy[ii].bNegotiatedLinkRate =
8246 +                           CSMI_SAS_LINK_RATE_FAILED;
8247 +                       break;
8248 +
8249 +               case MPI_SAS_IOUNIT0_RATE_SATA_OOB_COMPLETE:
8250 +                       break;
8251 +
8252 +               case MPI_SAS_IOUNIT0_RATE_1_5:
8253 +                       karg.Information.Phy[ii].bNegotiatedLinkRate =
8254 +                           CSMI_SAS_LINK_RATE_1_5_GBPS;
8255 +                       break;
8256 +
8257 +               case MPI_SAS_IOUNIT0_RATE_3_0:
8258 +                       karg.Information.Phy[ii].bNegotiatedLinkRate =
8259 +                           CSMI_SAS_LINK_RATE_3_0_GBPS;
8260 +                       break;
8261 +
8262 +               case MPI_SAS_IOUNIT0_RATE_UNKNOWN:
8263 +               default:
8264 +                       karg.Information.Phy[ii].bNegotiatedLinkRate =
8265 +                           CSMI_SAS_LINK_RATE_UNKNOWN;
8266 +                       break;
8267 +               }
8268 +
8269 +               if (sasIoUnitPg0->PhyData[ii].PortFlags &
8270 +                   MPI_SAS_IOUNIT0_PORT_FLAGS_DISCOVERY_IN_PROGRESS) {
8271 +                       karg.Information.Phy[ii].bAutoDiscover =
8272 +                           CSMI_SAS_DISCOVER_IN_PROGRESS;
8273 +               } else {
8274 +                       karg.Information.Phy[ii].bAutoDiscover =
8275 +                           CSMI_SAS_DISCOVER_COMPLETE;
8276 +               }
8277 +
8278 +               /* Issue a config request to get
8279 +                * phy information.
8280 +                */
8281 +               hdr.PageVersion = MPI_SASPHY0_PAGEVERSION;
8282 +               hdr.ExtPageLength = 0;
8283 +               hdr.PageNumber = 0;
8284 +               hdr.Reserved1 = 0;
8285 +               hdr.Reserved2 = 0;
8286 +               hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
8287 +               hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_PHY;
8288 +
8289 +               cfg.cfghdr.ehdr = &hdr;
8290 +               cfg.physAddr = -1;
8291 +               cfg.pageAddr = ii;
8292 +               cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
8293 +               cfg.dir = 0;    /* read */
8294 +               cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
8295 +
8296 +               if ((rc = mpt_config(ioc, &cfg)) != 0) {
8297 +                       dctlprintk((
8298 +                           ": FAILED: MPI_SASPHY0_PAGEVERSION: HEADER\n"));
8299 +                       dctlprintk((": rc=%x\n",rc));
8300 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8301 +                       goto sas_get_phy_info_exit;
8302 +               }
8303 +
8304 +               if (hdr.ExtPageLength == 0) {
8305 +                       dctlprintk((": pci_alloc_consistent: FAILED\n"));
8306 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8307 +                       goto sas_get_phy_info_exit;
8308 +               }
8309 +
8310 +               sasPhyPg0_data_sz = hdr.ExtPageLength * 4;
8311 +               rc = -ENOMEM;
8312 +
8313 +               sasPhyPg0 = (SasPhyPage0_t *) pci_alloc_consistent(
8314 +                   ioc->pcidev, sasPhyPg0_data_sz, &sasPhyPg0_dma);
8315 +
8316 +               if (! sasPhyPg0) {
8317 +                       dctlprintk((": pci_alloc_consistent: FAILED\n"));
8318 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8319 +                       goto sas_get_phy_info_exit;
8320 +               }
8321 +
8322 +               memset((u8 *)sasPhyPg0, 0, sasPhyPg0_data_sz);
8323 +               cfg.physAddr = sasPhyPg0_dma;
8324 +               cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
8325 +
8326 +               if ((rc = mpt_config(ioc, &cfg)) != 0) {
8327 +                       dctlprintk((
8328 +                           ": FAILED: MPI_SASPHY0_PAGEVERSION: PAGE\n"));
8329 +                       dctlprintk((": rc=%x\n",rc));
8330 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8331 +                       pci_free_consistent(ioc->pcidev, sasPhyPg0_data_sz,
8332 +                           (u8 *) sasPhyPg0, sasPhyPg0_dma);
8333 +                       goto sas_get_phy_info_exit;
8334 +               }
8335 +
8336 +               le64_to_cpus((u64 *)&sasPhyPg0->SASAddress);
8337 +               memcpy(&SASAddress64, &sasPhyPg0->SASAddress, sizeof(u64));
8338 +
8339 +/* EDM : dump PHY Page 0 data*/
8340 +               dsasprintk(("---- SAS PHY PAGE 0 ------------\n"));
8341 +               dsasprintk(("Handle=0x%X\n",
8342 +                   le16_to_cpu(sasPhyPg0->AttachedDevHandle)));
8343 +               dsasprintk(("SAS Address=0x%llX\n",SASAddress64));
8344 +               dsasprintk(("Attached PHY Identifier=0x%X\n",
8345 +                   sasPhyPg0->AttachedPhyIdentifier));
8346 +               dsasprintk(("Attached Device Info=0x%X\n",
8347 +                   le32_to_cpu(sasPhyPg0->AttachedDeviceInfo)));
8348 +               dsasprintk(("Programmed Link Rate=0x%X\n",
8349 +                   sasPhyPg0->ProgrammedLinkRate));
8350 +               dsasprintk(("Hardware Link Rate=0x%X\n",
8351 +                   ioc->sasPhyInfo[ii].hwLinkRate));
8352 +               dsasprintk(("Change Count=0x%X\n",
8353 +                   sasPhyPg0->ChangeCount));
8354 +               dsasprintk(("PHY Info=0x%X\n",
8355 +                   le32_to_cpu(sasPhyPg0->PhyInfo)));
8356 +               dsasprintk(("\n"));
8357 +/* EDM : debug data */
8358 +
8359 +               /* save the data */
8360 +
8361 +               /* Set Max hardware link rate.
8362 +                * This value is hard coded
8363 +                * because the HW link rate
8364 +                * is currently being
8365 +                * overwritten in FW.
8366 +                */
8367 +
8368 +               /* Set Max hardware link rate. */
8369 +               switch (sasPhyPg0->HwLinkRate &
8370 +                   MPI_SAS_PHY0_PRATE_MAX_RATE_MASK) {
8371 +
8372 +               case MPI_SAS_PHY0_HWRATE_MAX_RATE_1_5:
8373 +                       karg.Information.Phy[ii].bMaximumLinkRate =
8374 +                           CSMI_SAS_LINK_RATE_1_5_GBPS;
8375 +                       break;
8376 +
8377 +               case MPI_SAS_PHY0_PRATE_MAX_RATE_3_0:
8378 +                       karg.Information.Phy[ii].bMaximumLinkRate =
8379 +                           CSMI_SAS_LINK_RATE_3_0_GBPS;
8380 +                       break;
8381 +               default:
8382 +                       break;
8383 +               }
8384 +
8385 +               /* Set Max programmed link rate. */
8386 +               switch (sasPhyPg0->ProgrammedLinkRate &
8387 +                   MPI_SAS_PHY0_PRATE_MAX_RATE_MASK) {
8388 +
8389 +               case MPI_SAS_PHY0_PRATE_MAX_RATE_1_5:
8390 +                       karg.Information.Phy[ii].bMaximumLinkRate |=
8391 +                           (CSMI_SAS_PROGRAMMED_LINK_RATE_1_5_GBPS << 4);
8392 +                       break;
8393 +
8394 +               case MPI_SAS_PHY0_PRATE_MAX_RATE_3_0:
8395 +                       karg.Information.Phy[ii].bMaximumLinkRate |=
8396 +                           (CSMI_SAS_PROGRAMMED_LINK_RATE_3_0_GBPS << 4);
8397 +                       break;
8398 +               default:
8399 +                       break;
8400 +               }
8401 +
8402 +               /* Set Min hardware link rate. */
8403 +               switch (sasPhyPg0->HwLinkRate &
8404 +                   MPI_SAS_PHY0_HWRATE_MIN_RATE_MASK) {
8405 +
8406 +               case MPI_SAS_PHY0_HWRATE_MIN_RATE_1_5:
8407 +                       karg.Information.Phy[ii].bMinimumLinkRate =
8408 +                           CSMI_SAS_LINK_RATE_1_5_GBPS;
8409 +                       break;
8410 +
8411 +               case MPI_SAS_PHY0_PRATE_MIN_RATE_3_0:
8412 +                       karg.Information.Phy[ii].bMinimumLinkRate =
8413 +                           CSMI_SAS_LINK_RATE_3_0_GBPS;
8414 +                       break;
8415 +               default:
8416 +                       break;
8417 +               }
8418 +
8419 +               /* Set Min programmed link rate. */
8420 +               switch (sasPhyPg0->ProgrammedLinkRate &
8421 +                   MPI_SAS_PHY0_PRATE_MIN_RATE_MASK) {
8422 +
8423 +               case MPI_SAS_PHY0_PRATE_MIN_RATE_1_5:
8424 +                       karg.Information.Phy[ii].bMinimumLinkRate |=
8425 +                           (CSMI_SAS_PROGRAMMED_LINK_RATE_1_5_GBPS << 4);
8426 +                       break;
8427 +
8428 +               case MPI_SAS_PHY0_PRATE_MIN_RATE_3_0:
8429 +                       karg.Information.Phy[ii].bMinimumLinkRate |=
8430 +                           (CSMI_SAS_PROGRAMMED_LINK_RATE_3_0_GBPS << 4);
8431 +                       break;
8432 +               default:
8433 +                       break;
8434 +               }
8435 +
8436 +               /* Fill in Attached Device
8437 +                * Initiator Port Protocol.
8438 +                * Bits 6:3
8439 +                * More than one bit can be set.
8440 +                */
8441 +               protocol = le32_to_cpu(sasPhyPg0->AttachedDeviceInfo) & 0x78;
8442 +               karg.Information.Phy[ii].Attached.bInitiatorPortProtocol = 0;
8443 +               if (protocol & MPI_SAS_DEVICE_INFO_SSP_INITIATOR)
8444 +                     karg.Information.Phy[ii].Attached.bInitiatorPortProtocol =
8445 +                           CSMI_SAS_PROTOCOL_SSP;
8446 +               if (protocol & MPI_SAS_DEVICE_INFO_STP_INITIATOR)
8447 +                    karg.Information.Phy[ii].Attached.bInitiatorPortProtocol |=
8448 +                           CSMI_SAS_PROTOCOL_STP;
8449 +               if (protocol & MPI_SAS_DEVICE_INFO_SMP_INITIATOR)
8450 +                    karg.Information.Phy[ii].Attached.bInitiatorPortProtocol |=
8451 +                           CSMI_SAS_PROTOCOL_SMP;
8452 +               if (protocol & MPI_SAS_DEVICE_INFO_SATA_HOST)
8453 +                    karg.Information.Phy[ii].Attached.bInitiatorPortProtocol |=
8454 +                           CSMI_SAS_PROTOCOL_SATA;
8455 +
8456 +
8457 +               /* Fill in Phy Target Port
8458 +                * Protocol. Bits 10:7
8459 +                * More than one bit can be set.
8460 +                */
8461 +               protocol = le32_to_cpu(sasPhyPg0->AttachedDeviceInfo) & 0x780;
8462 +               karg.Information.Phy[ii].Attached.bTargetPortProtocol = 0;
8463 +               if (protocol & MPI_SAS_DEVICE_INFO_SSP_TARGET)
8464 +                       karg.Information.Phy[ii].Attached.bTargetPortProtocol |=
8465 +                           CSMI_SAS_PROTOCOL_SSP;
8466 +               if (protocol & MPI_SAS_DEVICE_INFO_STP_TARGET)
8467 +                       karg.Information.Phy[ii].Attached.bTargetPortProtocol |=
8468 +                           CSMI_SAS_PROTOCOL_STP;
8469 +               if (protocol & MPI_SAS_DEVICE_INFO_SMP_TARGET)
8470 +                       karg.Information.Phy[ii].Attached.bTargetPortProtocol |=
8471 +                           CSMI_SAS_PROTOCOL_SMP;
8472 +               if (protocol & MPI_SAS_DEVICE_INFO_SATA_DEVICE)
8473 +                       karg.Information.Phy[ii].Attached.bTargetPortProtocol |=
8474 +                           CSMI_SAS_PROTOCOL_SATA;
8475 +
8476 +
8477 +               /* Fill in Attached device type */
8478 +               switch (le32_to_cpu(sasPhyPg0->AttachedDeviceInfo) &
8479 +                   MPI_SAS_DEVICE_INFO_MASK_DEVICE_TYPE) {
8480 +
8481 +               case MPI_SAS_DEVICE_INFO_NO_DEVICE:
8482 +                       karg.Information.Phy[ii].Attached.bDeviceType =
8483 +                           CSMI_SAS_NO_DEVICE_ATTACHED;
8484 +                       break;
8485 +
8486 +               case MPI_SAS_DEVICE_INFO_END_DEVICE:
8487 +                       karg.Information.Phy[ii].Attached.bDeviceType =
8488 +                           CSMI_SAS_END_DEVICE;
8489 +                       break;
8490 +
8491 +               case MPI_SAS_DEVICE_INFO_EDGE_EXPANDER:
8492 +                       karg.Information.Phy[ii].Attached.bDeviceType =
8493 +                           CSMI_SAS_EDGE_EXPANDER_DEVICE;
8494 +                       break;
8495 +
8496 +               case MPI_SAS_DEVICE_INFO_FANOUT_EXPANDER:
8497 +                       karg.Information.Phy[ii].Attached.bDeviceType =
8498 +                           CSMI_SAS_FANOUT_EXPANDER_DEVICE;
8499 +                       break;
8500 +               }
8501 +
8502 +               /* Identify Info. */
8503 +               switch (le32_to_cpu(sasIoUnitPg0->PhyData[ii].ControllerPhyDeviceInfo) &
8504 +                   MPI_SAS_DEVICE_INFO_MASK_DEVICE_TYPE) {
8505 +
8506 +               case MPI_SAS_DEVICE_INFO_NO_DEVICE:
8507 +                       karg.Information.Phy[ii].Identify.bDeviceType =
8508 +                           CSMI_SAS_NO_DEVICE_ATTACHED;
8509 +                       break;
8510 +
8511 +               case MPI_SAS_DEVICE_INFO_END_DEVICE:
8512 +                       karg.Information.Phy[ii].Identify.bDeviceType =
8513 +                           CSMI_SAS_END_DEVICE;
8514 +                       break;
8515 +
8516 +               case MPI_SAS_DEVICE_INFO_EDGE_EXPANDER:
8517 +                       karg.Information.Phy[ii].Identify.bDeviceType =
8518 +                           CSMI_SAS_EDGE_EXPANDER_DEVICE;
8519 +                       break;
8520 +
8521 +               case MPI_SAS_DEVICE_INFO_FANOUT_EXPANDER:
8522 +                       karg.Information.Phy[ii].Identify.bDeviceType =
8523 +                           CSMI_SAS_FANOUT_EXPANDER_DEVICE;
8524 +                       break;
8525 +               }
8526 +
8527 +               /* Fill in Phy Initiator Port Protocol. Bits 6:3
8528 +                * More than one bit can be set, fall through cases.
8529 +                */
8530 +               protocol = le32_to_cpu(sasIoUnitPg0->PhyData[ii].ControllerPhyDeviceInfo)
8531 +                   & 0x78;
8532 +               karg.Information.Phy[ii].Identify.bInitiatorPortProtocol = 0;
8533 +               if( protocol & MPI_SAS_DEVICE_INFO_SSP_INITIATOR )
8534 +                    karg.Information.Phy[ii].Identify.bInitiatorPortProtocol |=
8535 +                           CSMI_SAS_PROTOCOL_SSP;
8536 +               if( protocol & MPI_SAS_DEVICE_INFO_STP_INITIATOR )
8537 +                    karg.Information.Phy[ii].Identify.bInitiatorPortProtocol |=
8538 +                           CSMI_SAS_PROTOCOL_STP;
8539 +               if( protocol & MPI_SAS_DEVICE_INFO_SMP_INITIATOR )
8540 +                    karg.Information.Phy[ii].Identify.bInitiatorPortProtocol |=
8541 +                           CSMI_SAS_PROTOCOL_SMP;
8542 +               if( protocol & MPI_SAS_DEVICE_INFO_SATA_HOST )
8543 +                    karg.Information.Phy[ii].Identify.bInitiatorPortProtocol |=
8544 +                           CSMI_SAS_PROTOCOL_SATA;
8545 +
8546 +               /* Fill in Phy Target Port Protocol. Bits 10:7
8547 +                * More than one bit can be set, fall through cases.
8548 +                */
8549 +               protocol = le32_to_cpu(sasIoUnitPg0->PhyData[ii].ControllerPhyDeviceInfo)
8550 +                   & 0x780;
8551 +               karg.Information.Phy[ii].Identify.bTargetPortProtocol = 0;
8552 +               if( protocol & MPI_SAS_DEVICE_INFO_SSP_TARGET )
8553 +                       karg.Information.Phy[ii].Identify.bTargetPortProtocol |=
8554 +                           CSMI_SAS_PROTOCOL_SSP;
8555 +               if( protocol & MPI_SAS_DEVICE_INFO_STP_TARGET )
8556 +                       karg.Information.Phy[ii].Identify.bTargetPortProtocol |=
8557 +                           CSMI_SAS_PROTOCOL_STP;
8558 +               if( protocol & MPI_SAS_DEVICE_INFO_SMP_TARGET )
8559 +                       karg.Information.Phy[ii].Identify.bTargetPortProtocol |=
8560 +                           CSMI_SAS_PROTOCOL_SMP;
8561 +               if( protocol & MPI_SAS_DEVICE_INFO_SATA_DEVICE )
8562 +                       karg.Information.Phy[ii].Identify.bTargetPortProtocol |=
8563 +                           CSMI_SAS_PROTOCOL_SATA;
8564 +
8565 +
8566 +               /* Setup Identify SAS Address and Phy Identifier
8567 +                *
8568 +                * Get phy Sas address from device list.
8569 +                * Search the list for the matching
8570 +                * devHandle.
8571 +                */
8572 +
8573 +               /* Setup SAS Address for the Phy */
8574 +               SASAddress64 = reverse_byte_order64((u64 *)&ioc->sasPhyInfo[ii].SASAddress);
8575 +               memcpy(karg.Information.Phy[ii].Identify.bSASAddress,&SASAddress64,
8576 +                   sizeof(u64));
8577 +
8578 +               karg.Information.Phy[ii].Identify.bPhyIdentifier = ii;
8579 +
8580 +               /* Setup SAS Address for the attached device */
8581 +               SASAddress64 = reverse_byte_order64((u64 *)&sasPhyPg0->SASAddress);
8582 +               memcpy(karg.Information.Phy[ii].Attached.bSASAddress,&SASAddress64,
8583 +                   sizeof(u64));
8584 +
8585 +               karg.Information.Phy[ii].Attached.bPhyIdentifier =
8586 +                   sasPhyPg0->AttachedPhyIdentifier;
8587 +
8588 +               pci_free_consistent(ioc->pcidev, sasPhyPg0_data_sz,
8589 +                   (u8 *) sasPhyPg0, sasPhyPg0_dma);
8590 +       }
8591 +
8592 +sas_get_phy_info_exit:
8593 +
8594 +       if (sasIoUnitPg0)
8595 +               pci_free_consistent(ioc->pcidev, sasIoUnitPg0_data_sz,
8596 +                   (u8 *) sasIoUnitPg0, sasIoUnitPg0_dma);
8597 +
8598 +       /* Copy the data from kernel memory to user memory
8599 +        */
8600 +       if (copy_to_user((char *)arg, &karg,
8601 +           sizeof(CSMI_SAS_PHY_INFO_BUFFER))) {
8602 +               printk(KERN_ERR "%s@%d::%s - "
8603 +                   "Unable to write out csmi_sas_get_phy_info_buffer @ %p\n",
8604 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
8605 +               return -EFAULT;
8606 +       }
8607 +
8608 +       return 0;
8609 +}
8610 +
8611 +
8612 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
8613 +/* Prototype Routine for the CSMI SAS Set PHY Info command.
8614 + *
8615 + * Outputs:    None.
8616 + * Return:     0 if successful
8617 + *             -EFAULT if data unavailable
8618 + *             -ENODEV if no such device/adapter
8619 + */
8620 +static int
8621 +mptctl_csmi_sas_set_phy_info(unsigned long arg)
8622 +{
8623 +       CSMI_SAS_SET_PHY_INFO_BUFFER __user *uarg = (void __user *) arg;
8624 +       CSMI_SAS_SET_PHY_INFO_BUFFER     karg;
8625 +       MPT_ADAPTER                     *ioc = NULL;
8626 +       int                             iocnum;
8627 +
8628 +       dctlprintk((": %s called.\n",__FUNCTION__));
8629 +
8630 +       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_SET_PHY_INFO_BUFFER))) {
8631 +               printk(KERN_ERR "%s@%d::%s() - "
8632 +                   "Unable to read in csmi_sas_set_phy_info struct @ %p\n",
8633 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
8634 +               return -EFAULT;
8635 +       }
8636 +
8637 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
8638 +           &ioc)) < 0) || (ioc == NULL)) {
8639 +               dctlprintk((KERN_ERR
8640 +               "%s::%s() @%d - ioc%d not found!\n",
8641 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
8642 +               return -ENODEV;
8643 +       }
8644 +
8645 +       if (!mptctl_is_this_sas_cntr(ioc)) {
8646 +               dctlprintk((KERN_ERR
8647 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
8648 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
8649 +               return -ENODEV;
8650 +       }
8651 +
8652 +/* TODO - implement IOCTL here */
8653 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8654 +       dctlprintk((": not implemented\n"));
8655 +
8656 +// cim_set_phy_info_exit:
8657 +
8658 +       /* Copy the data from kernel memory to user memory
8659 +        */
8660 +       if (copy_to_user((char *)arg, &karg,
8661 +                               sizeof(CSMI_SAS_SET_PHY_INFO_BUFFER))) {
8662 +               printk(KERN_ERR "%s@%d::%s() - "
8663 +                       "Unable to write out csmi_sas_set_phy_info @ %p\n",
8664 +                               __FILE__, __LINE__, __FUNCTION__, uarg);
8665 +               return -EFAULT;
8666 +       }
8667 +
8668 +       return 0;
8669 +
8670 +}
8671 +
8672 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
8673 +/* Prototype Routine for the CSMI Sas Get SCSI Address command.
8674 + *
8675 + * Outputs:    None.
8676 + * Return:     0 if successful
8677 + *             -EFAULT if data unavailable
8678 + *             -ENODEV if no such device/adapter
8679 + */
8680 +static int
8681 +mptctl_csmi_sas_get_scsi_address(unsigned long arg)
8682 +{
8683 +       CSMI_SAS_GET_SCSI_ADDRESS_BUFFER __user *uarg = (void __user *) arg;
8684 +       CSMI_SAS_GET_SCSI_ADDRESS_BUFFER         karg;
8685 +       MPT_ADAPTER             *ioc = NULL;
8686 +       int                     iocnum;
8687 +       sas_device_info_t       *sasDevice;
8688 +       u64                     SASAddress64;
8689 +
8690 +       dctlprintk((": %s called.\n",__FUNCTION__));
8691 +
8692 +       if (copy_from_user(&karg, uarg,
8693 +           sizeof(CSMI_SAS_GET_SCSI_ADDRESS_BUFFER))) {
8694 +               printk(KERN_ERR "%s@%d::%s() - "
8695 +                   "Unable to read in csmi_sas_get_scsi_address struct @ %p\n",
8696 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
8697 +               return -EFAULT;
8698 +       }
8699 +
8700 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
8701 +           &ioc)) < 0) || (ioc == NULL)) {
8702 +               dctlprintk((KERN_ERR
8703 +             "%s::%s() @%d - ioc%d not found!\n",
8704 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
8705 +               return -ENODEV;
8706 +       }
8707 +
8708 +       if (!mptctl_is_this_sas_cntr(ioc)) {
8709 +               dctlprintk((KERN_ERR
8710 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
8711 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
8712 +               return -ENODEV;
8713 +       }
8714 +
8715 +       /* Fill in the data and return the structure to the calling
8716 +        * program
8717 +        */
8718 +
8719 +       /* Copy the SAS address in reverse byte order. */
8720 +       SASAddress64 = reverse_byte_order64((u64 *)&karg.bSASAddress);
8721 +
8722 +       /* Search the list for the matching SAS address. */
8723 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_NO_SCSI_ADDRESS;
8724 +       list_for_each_entry(sasDevice, &ioc->sasDeviceList, list) {
8725 +
8726 +               /* Found the matching device. */
8727 +               if ((memcmp(&sasDevice->SASAddress,
8728 +                   &SASAddress64, sizeof(u64)) != 0))
8729 +                       continue;
8730 +
8731 +               karg.bPathId = sasDevice->Bus;
8732 +               karg.bTargetId = sasDevice->TargetId;
8733 +               karg.bLun = karg.bSASLun[0];
8734 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
8735 +
8736 +               if (((sasDevice->DeviceInfo & 0x00000003) ==
8737 +                       MPI_SAS_DEVICE_INFO_FANOUT_EXPANDER) ||
8738 +                       ((sasDevice->DeviceInfo & 0x00000003) ==
8739 +                        MPI_SAS_DEVICE_INFO_EDGE_EXPANDER))
8740 +                       karg.IoctlHeader.ReturnCode =
8741 +                           CSMI_SAS_NOT_AN_END_DEVICE;
8742 +               break;
8743 +       }
8744 +
8745 +       /* Copy the data from kernel memory to user memory
8746 +        */
8747 +       if (copy_to_user((char *)arg, &karg,
8748 +           sizeof(CSMI_SAS_GET_SCSI_ADDRESS_BUFFER))) {
8749 +               printk(KERN_ERR "%s@%d::%s() - "
8750 +                   "Unable to write out csmi_sas_get_scsi_address @ %p\n",
8751 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
8752 +               return -EFAULT;
8753 +       }
8754 +
8755 +       return 0;
8756 +
8757 +}
8758 +
8759 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
8760 +/* Prototype Routine for the CSMI Sas Get SCSI Address command.
8761 + *
8762 + * Outputs:    None.
8763 + * Return:     0 if successful
8764 + *             -EFAULT if data unavailable
8765 + *             -ENODEV if no such device/adapter
8766 + */
8767 +static int
8768 +mptctl_csmi_sas_get_sata_signature(unsigned long arg)
8769 +{
8770 +       CSMI_SAS_SATA_SIGNATURE_BUFFER  __user *uarg = (void __user *) arg;
8771 +       CSMI_SAS_SATA_SIGNATURE_BUFFER   karg;
8772 +       MPT_ADAPTER                     *ioc = NULL;
8773 +       int                             iocnum;
8774 +       int                             rc, jj;
8775 +       ConfigExtendedPageHeader_t      hdr;
8776 +       CONFIGPARMS                     cfg;
8777 +       SasPhyPage0_t                   *sasPhyPg0;
8778 +       dma_addr_t                      sasPhyPg0_dma;
8779 +       int                             sasPhyPg0_data_sz;
8780 +       SasDevicePage1_t                *sasDevicePg1;
8781 +       dma_addr_t                      sasDevicePg1_dma;
8782 +       int                             sasDevicePg1_data_sz;
8783 +       u8                              phyId;
8784 +
8785 +       dctlprintk((": %s called.\n",__FUNCTION__));
8786 +       sasPhyPg0=NULL;
8787 +       sasPhyPg0_data_sz=0;
8788 +       sasDevicePg1=NULL;
8789 +       sasDevicePg1_data_sz=0;
8790 +
8791 +       if (copy_from_user(&karg, uarg,
8792 +            sizeof(CSMI_SAS_SATA_SIGNATURE_BUFFER))) {
8793 +               printk(KERN_ERR "%s@%d::%s() - "
8794 +                   "Unable to read in csmi_sas_sata_signature struct @ %p\n",
8795 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
8796 +               return -EFAULT;
8797 +       }
8798 +
8799 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
8800 +           &ioc)) < 0) || (ioc == NULL)) {
8801 +               dctlprintk((KERN_ERR
8802 +           "%s::%s() @%d - ioc%d not found!\n",
8803 +                    __FILE__, __FUNCTION__, __LINE__, iocnum));
8804 +               return -ENODEV;
8805 +       }
8806 +
8807 +       if (!mptctl_is_this_sas_cntr(ioc)) {
8808 +               dctlprintk((KERN_ERR
8809 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
8810 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
8811 +               return -ENODEV;
8812 +       }
8813 +
8814 +       phyId = karg.Signature.bPhyIdentifier;
8815 +       if (phyId >= ioc->numPhys) {
8816 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_PHY_DOES_NOT_EXIST;
8817 +               dctlprintk((": phyId >= ioc->numPhys\n"));
8818 +               goto cim_sata_signature_exit;
8819 +       }
8820 +
8821 +       /* Default to success.*/
8822 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
8823 +
8824 +       /* Issue a config request to get the devHandle of the attached device
8825 +        */
8826 +
8827 +       /* Issue a config request to get phy information. */
8828 +       hdr.PageVersion = MPI_SASPHY0_PAGEVERSION;
8829 +       hdr.ExtPageLength = 0;
8830 +       hdr.PageNumber = 0;
8831 +       hdr.Reserved1 = 0;
8832 +       hdr.Reserved2 = 0;
8833 +       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
8834 +       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_PHY;
8835 +
8836 +       cfg.cfghdr.ehdr = &hdr;
8837 +       cfg.physAddr = -1;
8838 +       cfg.pageAddr = phyId;
8839 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
8840 +       cfg.dir = 0;    /* read */
8841 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
8842 +
8843 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
8844 +               /* Don't check if this failed.  Already in a
8845 +                * failure case.
8846 +                */
8847 +               dctlprintk((": FAILED: MPI_SASPHY0_PAGEVERSION: HEADER\n"));
8848 +               dctlprintk((": rc=%x\n",rc));
8849 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8850 +               goto cim_sata_signature_exit;
8851 +       }
8852 +
8853 +       if (hdr.ExtPageLength == 0) {
8854 +               /* Don't check if this failed.  Already in a
8855 +                * failure case.
8856 +                */
8857 +               dctlprintk((": hdr.ExtPageLength == 0\n"));
8858 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8859 +               goto cim_sata_signature_exit;
8860 +       }
8861 +
8862 +
8863 +       sasPhyPg0_data_sz = hdr.ExtPageLength * 4;
8864 +       rc = -ENOMEM;
8865 +
8866 +       sasPhyPg0 = (SasPhyPage0_t *) pci_alloc_consistent(ioc->pcidev,
8867 +           sasPhyPg0_data_sz, &sasPhyPg0_dma);
8868 +
8869 +       if (! sasPhyPg0) {
8870 +               dctlprintk((": pci_alloc_consistent: FAILED\n"));
8871 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8872 +               goto cim_sata_signature_exit;
8873 +       }
8874 +
8875 +       memset((u8 *)sasPhyPg0, 0, sasPhyPg0_data_sz);
8876 +       cfg.physAddr = sasPhyPg0_dma;
8877 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
8878 +
8879 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
8880 +               /* Don't check if this failed.  Already in a
8881 +                * failure case.
8882 +                */
8883 +               dctlprintk((": FAILED: MPI_SASPHY0_PAGEVERSION: PAGE\n"));
8884 +               dctlprintk((": rc=%x\n",rc));
8885 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8886 +               goto cim_sata_signature_exit;
8887 +       }
8888 +
8889 +       /* Make sure a SATA device is attached. */
8890 +       if ((le32_to_cpu(sasPhyPg0->AttachedDeviceInfo) &
8891 +           MPI_SAS_DEVICE_INFO_SATA_DEVICE) == 0) {
8892 +               dctlprintk((": NOT A SATA DEVICE\n"));
8893 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_NO_SATA_DEVICE;
8894 +               goto cim_sata_signature_exit;
8895 +       }
8896 +
8897 +       /* Get device page 1 for FIS  signature. */
8898 +       hdr.PageVersion = MPI_SASDEVICE1_PAGEVERSION;
8899 +       hdr.ExtPageLength = 0;
8900 +       hdr.PageNumber = 1 /* page number 1 */;
8901 +       hdr.Reserved1 = 0;
8902 +       hdr.Reserved2 = 0;
8903 +       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
8904 +       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_DEVICE;
8905 +
8906 +       cfg.cfghdr.ehdr = &hdr;
8907 +       cfg.physAddr = -1;
8908 +
8909 +       cfg.pageAddr = ((MPI_SAS_DEVICE_PGAD_FORM_HANDLE <<
8910 +           MPI_SAS_DEVICE_PGAD_FORM_SHIFT) |
8911 +           le16_to_cpu(sasPhyPg0->AttachedDevHandle));
8912 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
8913 +       cfg.dir = 0;    /* read */
8914 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
8915 +
8916 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
8917 +               dctlprintk((": FAILED: MPI_SASDEVICE1_PAGEVERSION: HEADER\n"));
8918 +               dctlprintk((": rc=%x\n",rc));
8919 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8920 +               goto cim_sata_signature_exit;
8921 +       }
8922 +
8923 +       if (hdr.ExtPageLength == 0) {
8924 +               dctlprintk((": hdr.ExtPageLength == 0\n"));
8925 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8926 +               goto cim_sata_signature_exit;
8927 +       }
8928 +
8929 +       sasDevicePg1_data_sz = hdr.ExtPageLength * 4;
8930 +       rc = -ENOMEM;
8931 +
8932 +       sasDevicePg1 = (SasDevicePage1_t *) pci_alloc_consistent
8933 +           (ioc->pcidev, sasDevicePg1_data_sz, &sasDevicePg1_dma);
8934 +
8935 +       if (! sasDevicePg1) {
8936 +               dctlprintk((": pci_alloc_consistent: FAILED\n"));
8937 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8938 +               goto cim_sata_signature_exit;
8939 +       }
8940 +
8941 +       memset((u8 *)sasDevicePg1, 0, sasDevicePg1_data_sz);
8942 +       cfg.physAddr = sasDevicePg1_dma;
8943 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
8944 +
8945 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
8946 +               dctlprintk((": FAILED: MPI_SASDEVICE1_PAGEVERSION: PAGE\n"));
8947 +               dctlprintk((": rc=%x\n",rc));
8948 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
8949 +               goto cim_sata_signature_exit;
8950 +       }
8951 +
8952 +/* EDM : dump Device Page 1 data*/
8953 +       dsasprintk(("---- SAS DEVICE PAGE 1 ---------\n"));
8954 +       dsasprintk(("Handle=0x%x\n",sasDevicePg1->DevHandle));
8955 +       dsasprintk(("SAS Address="));
8956 +       for(jj=0;jj<8;jj++)
8957 +               dsasprintk(("%02x ",
8958 +               ((u8 *)&sasDevicePg1->SASAddress)[jj]));
8959 +       dsasprintk(("\n"));
8960 +       dsasprintk(("Target ID=0x%x\n",sasDevicePg1->TargetID));
8961 +       dsasprintk(("Bus=0x%x\n",sasDevicePg1->Bus));
8962 +       dsasprintk(("Initial Reg Device FIS="));
8963 +       for(jj=0;jj<20;jj++)
8964 +               dsasprintk(("%02x ",
8965 +               ((u8 *)&sasDevicePg1->InitialRegDeviceFIS)[jj]));
8966 +       dsasprintk(("\n\n"));
8967 +/* EDM : debug data */
8968 +
8969 +       memcpy(karg.Signature.bSignatureFIS,
8970 +               sasDevicePg1->InitialRegDeviceFIS,20);
8971 +
8972 +cim_sata_signature_exit:
8973 +
8974 +       if (sasPhyPg0)
8975 +               pci_free_consistent(ioc->pcidev, sasPhyPg0_data_sz,
8976 +                   (u8 *) sasPhyPg0, sasPhyPg0_dma);
8977 +
8978 +       if (sasDevicePg1)
8979 +               pci_free_consistent(ioc->pcidev, sasDevicePg1_data_sz,
8980 +                   (u8 *) sasDevicePg1, sasDevicePg1_dma);
8981 +
8982 +       /* Copy the data from kernel memory to user memory
8983 +        */
8984 +       if (copy_to_user((char *)arg, &karg,
8985 +           sizeof(CSMI_SAS_SATA_SIGNATURE_BUFFER))) {
8986 +               printk(KERN_ERR "%s@%d::%s() - "
8987 +                   "Unable to write out csmi_sas_sata_signature @ %p\n",
8988 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
8989 +               return -EFAULT;
8990 +       }
8991 +
8992 +       return 0;
8993 +}
8994 +
8995 +
8996 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
8997 +/* Prototype Routine for the CSMI Sas Get SCSI Address command.
8998 + *
8999 + * Outputs:    None.
9000 + * Return:     0 if successful
9001 + *             -EFAULT if data unavailable
9002 + *             -ENODEV if no such device/adapter
9003 + */
9004 +static int
9005 +mptctl_csmi_sas_get_device_address(unsigned long arg)
9006 +{
9007 +       CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER __user *uarg = (void __user *) arg;
9008 +       CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER       karg;
9009 +       MPT_ADAPTER             *ioc = NULL;
9010 +       int                     iocnum;
9011 +       sas_device_info_t       *sasDevice;
9012 +       u64                     SASAddress64;
9013 +
9014 +       dctlprintk((": %s called.\n",__FUNCTION__));
9015 +
9016 +       if (copy_from_user(&karg, uarg,
9017 +           sizeof(CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER))) {
9018 +               printk(KERN_ERR "%s@%d::%s() - "
9019 +          "Unable to read in csmi_sas_get_device_address_buffer struct @ %p\n",
9020 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
9021 +               return -EFAULT;
9022 +       }
9023 +
9024 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
9025 +           &ioc)) < 0) || (ioc == NULL)) {
9026 +               dctlprintk((KERN_ERR
9027 +           "%s::%s() @%d - ioc%d not found!\n",
9028 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
9029 +               return -ENODEV;
9030 +       }
9031 +
9032 +       if (!mptctl_is_this_sas_cntr(ioc)) {
9033 +               dctlprintk((KERN_ERR
9034 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
9035 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
9036 +               return -ENODEV;
9037 +       }
9038 +
9039 +       /* Fill in the data and return the structure to the calling
9040 +        * program
9041 +        */
9042 +
9043 +       /* Search the list for the matching SAS address. */
9044 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_NO_DEVICE_ADDRESS;
9045 +       list_for_each_entry(sasDevice, &ioc->sasDeviceList, list) {
9046 +
9047 +               /* Find the matching device. */
9048 +               if ((karg.bPathId == sasDevice->Bus) &&
9049 +                       (karg.bTargetId == sasDevice->TargetId)) {
9050 +
9051 +                       SASAddress64 = reverse_byte_order64(&sasDevice->SASAddress);
9052 +                       memcpy(&karg.bSASAddress,&SASAddress64,sizeof(u64));
9053 +                       karg.bSASLun[0] = karg.bLun;
9054 +                       memset(karg.bSASLun, 0, sizeof(karg.bSASLun));
9055 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
9056 +                       break;
9057 +               } else
9058 +                       /* Keep looking. */
9059 +                       continue;
9060 +       }
9061 +
9062 +       /* Copy the data from kernel memory to user memory
9063 +        */
9064 +       if (copy_to_user((char *)arg, &karg,
9065 +           sizeof(CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER))) {
9066 +               printk(KERN_ERR "%s@%d::%s() - "
9067 +               "Unable to write out csmi_sas_get_device_address_buffer @ %p\n",
9068 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
9069 +               return -EFAULT;
9070 +       }
9071 +
9072 +       return 0;
9073 +
9074 +}
9075 +
9076 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
9077 +/* Prototype Routine for the CSMI Sas Get Link Errors command.
9078 + *
9079 + * Outputs:    None.
9080 + * Return:     0 if successful
9081 + *             -EFAULT if data unavailable
9082 + *             -ENODEV if no such device/adapter
9083 + */
9084 +static int
9085 +mptctl_csmi_sas_get_link_errors(unsigned long arg)
9086 +{
9087 +       CSMI_SAS_LINK_ERRORS_BUFFER __user *uarg = (void __user *) arg;
9088 +       CSMI_SAS_LINK_ERRORS_BUFFER      karg;
9089 +       MPT_ADAPTER                     *ioc = NULL;
9090 +       MPT_FRAME_HDR                   *mf = NULL;
9091 +       MPIHeader_t                     *mpi_hdr;
9092 +       int                             iocnum;
9093 +       int                             rc,ii;
9094 +       ConfigExtendedPageHeader_t      hdr;
9095 +       CONFIGPARMS                     cfg;
9096 +       SasPhyPage1_t                   *sasPhyPage1;
9097 +       dma_addr_t                      sasPhyPage1_dma;
9098 +       int                             sasPhyPage1_data_sz;
9099 +       SasIoUnitControlRequest_t       *sasIoUnitCntrReq;
9100 +       SasIoUnitControlReply_t         *sasIoUnitCntrReply;
9101 +       u8                              phyId;
9102 +       int                             wait_timeout;
9103 +
9104 +       dctlprintk((": %s called.\n",__FUNCTION__));
9105 +       sasPhyPage1=NULL;
9106 +       sasPhyPage1_data_sz=0;
9107 +
9108 +       if (copy_from_user(&karg, uarg,
9109 +            sizeof(CSMI_SAS_LINK_ERRORS_BUFFER))) {
9110 +               printk(KERN_ERR "%s@%d::%s() - "
9111 +                   "Unable to read in mptctl_csmi_sas_get_link_errors struct @ %p\n",
9112 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
9113 +               return -EFAULT;
9114 +       }
9115 +
9116 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
9117 +           &ioc)) < 0) || (ioc == NULL)) {
9118 +               dctlprintk((KERN_ERR
9119 +           "%s::%s() @%d - ioc%d not found!\n",
9120 +                    __FILE__, __FUNCTION__, __LINE__, iocnum));
9121 +               return -ENODEV;
9122 +       }
9123 +
9124 +       if (!mptctl_is_this_sas_cntr(ioc)) {
9125 +               dctlprintk((KERN_ERR
9126 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
9127 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
9128 +               return -ENODEV;
9129 +       }
9130 +
9131 +       phyId = karg.Information.bPhyIdentifier;
9132 +       if (phyId >= ioc->numPhys) {
9133 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_PHY_DOES_NOT_EXIST;
9134 +               dctlprintk((": phyId >= ioc->numPhys\n"));
9135 +               goto cim_get_link_errors_exit;
9136 +       }
9137 +
9138 +       /* Default to success.*/
9139 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
9140 +
9141 +       /* Issue a config request to get the devHandle of the attached device
9142 +        */
9143 +
9144 +       /* Issue a config request to get phy information. */
9145 +       hdr.PageVersion = MPI_SASPHY1_PAGEVERSION;
9146 +       hdr.ExtPageLength = 0;
9147 +       hdr.PageNumber = 1 /* page number 1*/;
9148 +       hdr.Reserved1 = 0;
9149 +       hdr.Reserved2 = 0;
9150 +       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
9151 +       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_PHY;
9152 +
9153 +       cfg.cfghdr.ehdr = &hdr;
9154 +       cfg.physAddr = -1;
9155 +       cfg.pageAddr = phyId;
9156 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
9157 +       cfg.dir = 0;    /* read */
9158 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
9159 +
9160 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
9161 +               /* Don't check if this failed.  Already in a
9162 +                * failure case.
9163 +                */
9164 +               dctlprintk((": FAILED: MPI_SASPHY1_PAGEVERSION: HEADER\n"));
9165 +               dctlprintk((": rc=%x\n",rc));
9166 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9167 +               goto cim_get_link_errors_exit;
9168 +       }
9169 +
9170 +       if (hdr.ExtPageLength == 0) {
9171 +               /* Don't check if this failed.  Already in a
9172 +                * failure case.
9173 +                */
9174 +               dctlprintk((": hdr.ExtPageLength == 0\n"));
9175 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9176 +               goto cim_get_link_errors_exit;
9177 +       }
9178 +
9179 +
9180 +       sasPhyPage1_data_sz = hdr.ExtPageLength * 4;
9181 +       rc = -ENOMEM;
9182 +
9183 +       sasPhyPage1 = (SasPhyPage1_t *) pci_alloc_consistent(ioc->pcidev,
9184 +           sasPhyPage1_data_sz, &sasPhyPage1_dma);
9185 +
9186 +       if (! sasPhyPage1) {
9187 +               dctlprintk((": pci_alloc_consistent: FAILED\n"));
9188 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9189 +               goto cim_get_link_errors_exit;
9190 +       }
9191 +
9192 +       memset((u8 *)sasPhyPage1, 0, sasPhyPage1_data_sz);
9193 +       cfg.physAddr = sasPhyPage1_dma;
9194 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
9195 +
9196 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
9197 +               /* Don't check if this failed.  Already in a
9198 +                * failure case.
9199 +                */
9200 +               dctlprintk((": FAILED: MPI_SASPHY1_PAGEVERSION: PAGE\n"));
9201 +               dctlprintk((": rc=%x\n",rc));
9202 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9203 +               goto cim_get_link_errors_exit;
9204 +       }
9205 +
9206 +/* EDM : dump PHY Page 1 data*/
9207 +       dsasprintk(("---- SAS PHY PAGE 1 ------------\n"));
9208 +       dsasprintk(("Invalid Dword Count=0x%x\n",
9209 +           sasPhyPage1->InvalidDwordCount));
9210 +       dsasprintk(("Running Disparity Error Count=0x%x\n",
9211 +           sasPhyPage1->RunningDisparityErrorCount));
9212 +       dsasprintk(("Loss Dword Synch Count=0x%x\n",
9213 +           sasPhyPage1->LossDwordSynchCount));
9214 +       dsasprintk(("PHY Reset Problem Count=0x%x\n",
9215 +           sasPhyPage1->PhyResetProblemCount));
9216 +       dsasprintk(("\n\n"));
9217 +/* EDM : debug data */
9218 +
9219 +       karg.Information.uInvalidDwordCount =
9220 +               le32_to_cpu(sasPhyPage1->InvalidDwordCount);
9221 +       karg.Information.uRunningDisparityErrorCount =
9222 +               le32_to_cpu(sasPhyPage1->RunningDisparityErrorCount);
9223 +       karg.Information.uLossOfDwordSyncCount =
9224 +               le32_to_cpu(sasPhyPage1->LossDwordSynchCount);
9225 +       karg.Information.uPhyResetProblemCount =
9226 +               le32_to_cpu(sasPhyPage1->PhyResetProblemCount);
9227 +
9228 +       if (karg.Information.bResetCounts ==
9229 +           CSMI_SAS_LINK_ERROR_DONT_RESET_COUNTS ) {
9230 +               goto cim_get_link_errors_exit;
9231 +       }
9232 +
9233 +       /* Clear Error log
9234 +        *
9235 +        * Issue IOUNIT Control Reqeust Message
9236 +        */
9237 +
9238 +       /* Get a MF for this command.
9239 +        */
9240 +       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
9241 +               dctlprintk((": no msg frames!\n"));
9242 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9243 +               goto cim_get_link_errors_exit;
9244 +        }
9245 +
9246 +       mpi_hdr = (MPIHeader_t *) mf;
9247 +       sasIoUnitCntrReq = (SasIoUnitControlRequest_t *)mf;
9248 +       memset(sasIoUnitCntrReq,0,sizeof(SasIoUnitControlRequest_t));
9249 +       sasIoUnitCntrReq->Function = MPI_FUNCTION_SAS_IO_UNIT_CONTROL;
9250 +       sasIoUnitCntrReq->MsgContext = mpi_hdr->MsgContext;
9251 +       sasIoUnitCntrReq->PhyNum = phyId;
9252 +       sasIoUnitCntrReq->Operation = MPI_SAS_OP_PHY_CLEAR_ERROR_LOG;
9253 +
9254 +       ioc->ioctl->wait_done = 0;
9255 +       mpt_put_msg_frame(mptctl_id, ioc, mf);
9256 +
9257 +       /* Now wait for the command to complete */
9258 +       wait_timeout=max_t(int,MPT_IOCTL_DEFAULT_TIMEOUT,karg.IoctlHeader.Timeout);
9259 +       ii = wait_event_timeout(mptctl_wait,
9260 +            ioc->ioctl->wait_done == 1,
9261 +            HZ*wait_timeout);
9262 +
9263 +       if(ii <=0 && (ioc->ioctl->wait_done != 1 )) {
9264 +       /* Now we need to reset the board */
9265 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9266 +               mpt_free_msg_frame(ioc, mf);
9267 +               mptctl_timeout_expired(ioc->ioctl);
9268 +               goto cim_get_link_errors_exit;
9269 +       }
9270 +
9271 +       /* process the completed Reply Message Frame */
9272 +       if (ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) {
9273 +
9274 +               sasIoUnitCntrReply =
9275 +                   (SasIoUnitControlReply_t *)ioc->ioctl->ReplyFrame;
9276 +
9277 +               if ( le16_to_cpu(sasIoUnitCntrReply->IOCStatus) != MPI_IOCSTATUS_SUCCESS) {
9278 +                       dctlprintk((": SAS IO Unit Control: "));
9279 +                       dctlprintk(("IOCStatus=0x%X IOCLogInfo=0x%X\n",
9280 +                           sasIoUnitCntrReply->IOCStatus,
9281 +                           sasIoUnitCntrReply->IOCLogInfo));
9282 +               }
9283 +       }
9284 +
9285 +cim_get_link_errors_exit:
9286 +
9287 +       ioc->ioctl->status &= ~(MPT_IOCTL_STATUS_TM_FAILED |
9288 +           MPT_IOCTL_STATUS_COMMAND_GOOD | MPT_IOCTL_STATUS_SENSE_VALID |
9289 +           MPT_IOCTL_STATUS_RF_VALID);
9290 +
9291 +       if (sasPhyPage1)
9292 +               pci_free_consistent(ioc->pcidev, sasPhyPage1_data_sz,
9293 +                   (u8 *) sasPhyPage1, sasPhyPage1_dma);
9294 +
9295 +       /* Copy the data from kernel memory to user memory
9296 +        */
9297 +       if (copy_to_user((char *)arg, &karg,
9298 +           sizeof(CSMI_SAS_LINK_ERRORS_BUFFER))) {
9299 +               printk(KERN_ERR "%s@%d::%s() - "
9300 +                   "Unable to write out mptctl_csmi_sas_get_link_errors @ %p\n",
9301 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
9302 +               return -EFAULT;
9303 +       }
9304 +
9305 +       return 0;
9306 +
9307 +}
9308 +
9309 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
9310 +/* Prototype Routine for the CSMI SAS SMP Passthru command.
9311 + *
9312 + * Outputs:    None.
9313 + * Return:     0 if successful
9314 + *             -EFAULT if data unavailable
9315 + *             -ENODEV if no such device/adapter
9316 + */
9317 +static int
9318 +mptctl_csmi_sas_smp_passthru(unsigned long arg)
9319 +{
9320 +       CSMI_SAS_SMP_PASSTHRU_BUFFER __user *uarg = (void __user *) arg;
9321 +       MPT_ADAPTER                     *ioc;
9322 +       CSMI_SAS_SMP_PASSTHRU_BUFFER     karg;
9323 +       pSmpPassthroughRequest_t        smpReq;
9324 +       pSmpPassthroughReply_t          smpReply;
9325 +       MPT_FRAME_HDR                   *mf = NULL;
9326 +       MPIHeader_t                     *mpi_hdr;
9327 +       char                            *psge;
9328 +       int                             iocnum, flagsLength,ii;
9329 +       u8                              index;
9330 +       void *                          request_data;
9331 +       dma_addr_t                      request_data_dma;
9332 +       u32                             request_data_sz;
9333 +       void *                          response_data;
9334 +       dma_addr_t                      response_data_dma;
9335 +       u32                             response_data_sz;
9336 +       u16                             ioc_stat;
9337 +       int                             wait_timeout;
9338 +
9339 +       dctlprintk((": %s called.\n",__FUNCTION__));
9340 +
9341 +       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_SMP_PASSTHRU_BUFFER))) {
9342 +               printk(KERN_ERR "%s@%d::%s() - "
9343 +                   "Unable to read in csmi_sas_smp_passthru struct @ %p\n",
9344 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
9345 +               return -EFAULT;
9346 +       }
9347 +
9348 +       request_data = NULL;
9349 +       response_data = NULL;
9350 +       response_data_sz = sizeof(CSMI_SAS_SMP_RESPONSE);
9351 +       request_data_sz  = karg.Parameters.uRequestLength;
9352 +
9353 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
9354 +           &ioc)) < 0) || (ioc == NULL)) {
9355 +               dctlprintk((KERN_ERR
9356 +               "%s::%s() @%d - ioc%d not found!\n",
9357 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
9358 +               return -ENODEV;
9359 +       }
9360 +
9361 +       if (!mptctl_is_this_sas_cntr(ioc)) {
9362 +               dctlprintk((KERN_ERR
9363 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
9364 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
9365 +               return -ENODEV;
9366 +       }
9367 +
9368 +       /* Make sure the adapter is not being reset. */
9369 +       if (!ioc->ioctl) {
9370 +               printk(KERN_ERR "%s@%d::%s - "
9371 +                   "No memory available during driver init.\n",
9372 +                   __FILE__, __LINE__,__FUNCTION__);
9373 +               return -ENOMEM;
9374 +       } else if (ioc->ioctl->status & MPT_IOCTL_STATUS_DID_IOCRESET) {
9375 +               printk(KERN_ERR "%s@%d::%s - "
9376 +                   "Busy with IOC Reset \n",
9377 +                   __FILE__, __LINE__,__FUNCTION__);
9378 +               return -EBUSY;
9379 +       }
9380 +
9381 +       /* Default to success.*/
9382 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
9383 +
9384 +       /* Do some error checking on the request. */
9385 +       if (karg.Parameters.bPortIdentifier == CSMI_SAS_IGNORE_PORT) {
9386 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_SELECT_PHY_OR_PORT;
9387 +               goto cim_smp_passthru_exit;
9388 +       }
9389 +
9390 +       if ((request_data_sz > 0xFFFF) || (!request_data_sz)) {
9391 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9392 +               goto cim_smp_passthru_exit;
9393 +       }
9394 +
9395 +       /* Get a free request frame and save the message context.
9396 +        */
9397 +       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
9398 +               dctlprintk((": no msg frames!\n"));
9399 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9400 +               goto cim_smp_passthru_exit;
9401 +        }
9402 +
9403 +       mpi_hdr = (MPIHeader_t *) mf;
9404 +       smpReq = (pSmpPassthroughRequest_t ) mf;
9405 +
9406 +       memset(smpReq,0,ioc->req_sz);
9407 +
9408 +       /* Fill in smp request. */
9409 +       smpReq->PhysicalPort = karg.Parameters.bPortIdentifier;
9410 +       smpReq->Function = MPI_FUNCTION_SMP_PASSTHROUGH;
9411 +       smpReq->RequestDataLength = cpu_to_le16(request_data_sz);
9412 +       smpReq->ConnectionRate = karg.Parameters.bConnectionRate;
9413 +       smpReq->MsgContext = mpi_hdr->MsgContext;
9414 +       for ( index = 0; index < 8; index++ ) {
9415 +               ((u8*)&smpReq->SASAddress)[7 - index] =
9416 +                   karg.Parameters.bDestinationSASAddress[index];
9417 +       }
9418 +       smpReq->Reserved2 = 0;
9419 +       smpReq->Reserved3 = 0;
9420 +
9421 +       /*
9422 +        * Prepare the necessary pointers to run
9423 +        * through the SGL generation
9424 +        */
9425 +
9426 +       psge = (char *)&smpReq->SGL;
9427 +
9428 +       /* setup the *Request* payload SGE */
9429 +       flagsLength = MPI_SGE_FLAGS_SIMPLE_ELEMENT |
9430 +               MPI_SGE_FLAGS_SYSTEM_ADDRESS |
9431 +               MPI_SGE_FLAGS_32_BIT_ADDRESSING |
9432 +               MPI_SGE_FLAGS_HOST_TO_IOC |
9433 +               MPI_SGE_FLAGS_END_OF_BUFFER;
9434 +
9435 +       if (sizeof(dma_addr_t) == sizeof(u64)) {
9436 +               flagsLength |= MPI_SGE_FLAGS_64_BIT_ADDRESSING;
9437 +       }
9438 +       flagsLength = flagsLength << MPI_SGE_FLAGS_SHIFT;
9439 +       flagsLength |= request_data_sz;
9440 +
9441 +       request_data = pci_alloc_consistent(
9442 +           ioc->pcidev, request_data_sz, &request_data_dma);
9443 +
9444 +       if (!request_data) {
9445 +               dctlprintk((": pci_alloc_consistent: FAILED\n"));
9446 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9447 +               mpt_free_msg_frame(ioc, mf);
9448 +               goto cim_smp_passthru_exit;
9449 +       }
9450 +
9451 +       mpt_add_sge(psge, flagsLength, request_data_dma);
9452 +       psge += (sizeof(u32) + sizeof(dma_addr_t));
9453 +
9454 +       memcpy(request_data,&karg.Parameters.Request,request_data_sz);
9455 +
9456 +       /* setup the *Response* payload SGE */
9457 +       response_data = pci_alloc_consistent(
9458 +           ioc->pcidev, response_data_sz, &response_data_dma);
9459 +
9460 +       if (!response_data) {
9461 +               dctlprintk((": pci_alloc_consistent: FAILED\n"));
9462 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9463 +               mpt_free_msg_frame(ioc, mf);
9464 +               goto cim_smp_passthru_exit;
9465 +       }
9466 +
9467 +       flagsLength = MPI_SGE_FLAGS_SIMPLE_ELEMENT |
9468 +               MPI_SGE_FLAGS_SYSTEM_ADDRESS |
9469 +               MPI_SGE_FLAGS_32_BIT_ADDRESSING |
9470 +               MPI_SGE_FLAGS_IOC_TO_HOST |
9471 +               MPI_SGE_FLAGS_END_OF_BUFFER;
9472 +
9473 +       if (sizeof(dma_addr_t) == sizeof(u64)) {
9474 +               flagsLength |= MPI_SGE_FLAGS_64_BIT_ADDRESSING;
9475 +       }
9476 +
9477 +       flagsLength = flagsLength << MPI_SGE_FLAGS_SHIFT;
9478 +       flagsLength |= response_data_sz;
9479 +
9480 +       mpt_add_sge(psge, flagsLength, response_data_dma);
9481 +
9482 +       /* The request is complete. Set the timer parameters
9483 +        * and issue the request.
9484 +        */
9485 +       ioc->ioctl->wait_done = 0;
9486 +       mpt_put_msg_frame(mptctl_id, ioc, mf);
9487 +
9488 +       /* Now wait for the command to complete */
9489 +       wait_timeout=max_t(int,MPT_IOCTL_DEFAULT_TIMEOUT,karg.IoctlHeader.Timeout);
9490 +       ii = wait_event_timeout(mptctl_wait,
9491 +            ioc->ioctl->wait_done == 1,
9492 +            HZ*wait_timeout);
9493 +
9494 +       if(ii <=0 && (ioc->ioctl->wait_done != 1 )) {
9495 +       /* Now we need to reset the board */
9496 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9497 +               mpt_free_msg_frame(ioc, mf);
9498 +               mptctl_timeout_expired(ioc->ioctl);
9499 +               goto cim_smp_passthru_exit;
9500 +       }
9501 +
9502 +       if ((ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) == 0) {
9503 +               dctlprintk((": SMP Passthru: oh no, there is no reply!!"));
9504 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9505 +               goto cim_smp_passthru_exit;
9506 +       }
9507 +
9508 +       /* process the completed Reply Message Frame */
9509 +       smpReply = (pSmpPassthroughReply_t )ioc->ioctl->ReplyFrame;
9510 +       ioc_stat = le16_to_cpu(smpReply->IOCStatus) & MPI_IOCSTATUS_MASK;
9511 +
9512 +       if ((ioc_stat != MPI_IOCSTATUS_SUCCESS) &&
9513 +           (ioc_stat != MPI_IOCSTATUS_SCSI_DATA_UNDERRUN)) {
9514 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9515 +               dctlprintk((": SMP Passthru: "));
9516 +               dctlprintk(("IOCStatus=0x%X IOCLogInfo=0x%X SASStatus=0x%X\n",
9517 +                   smpReply->IOCStatus,
9518 +                   smpReply->IOCLogInfo,
9519 +                   smpReply->SASStatus));
9520 +               goto cim_smp_passthru_exit;
9521 +       }
9522 +
9523 +       karg.Parameters.bConnectionStatus =
9524 +           map_sas_status_to_csmi(smpReply->SASStatus);
9525 +
9526 +
9527 +       if (le16_to_cpu(smpReply->ResponseDataLength)) {
9528 +               karg.Parameters.uResponseBytes = le16_to_cpu(smpReply->ResponseDataLength);
9529 +               memcpy(&karg.Parameters.Response,
9530 +                   response_data, le16_to_cpu(smpReply->ResponseDataLength));
9531 +       }
9532 +
9533 +cim_smp_passthru_exit:
9534 +
9535 +       ioc->ioctl->status &= ~( MPT_IOCTL_STATUS_TM_FAILED |
9536 +           MPT_IOCTL_STATUS_COMMAND_GOOD | MPT_IOCTL_STATUS_SENSE_VALID |
9537 +           MPT_IOCTL_STATUS_RF_VALID);
9538 +
9539 +       if (request_data)
9540 +               pci_free_consistent(ioc->pcidev, request_data_sz,
9541 +                   (u8 *)request_data, request_data_dma);
9542 +
9543 +       if (response_data)
9544 +               pci_free_consistent(ioc->pcidev, response_data_sz,
9545 +                   (u8 *)response_data, response_data_dma);
9546 +
9547 +
9548 +       /* Copy the data from kernel memory to user memory
9549 +        */
9550 +       if (copy_to_user((char *)arg, &karg,
9551 +                               sizeof(CSMI_SAS_SMP_PASSTHRU_BUFFER))) {
9552 +               printk(KERN_ERR "%s@%d::%s() - "
9553 +                       "Unable to write out csmi_sas_smp_passthru @ %p\n",
9554 +                               __FILE__, __LINE__, __FUNCTION__, uarg);
9555 +               return -EFAULT;
9556 +       }
9557 +
9558 +       return 0;
9559 +
9560 +}
9561 +
9562 +
9563 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
9564 +/* Prototype Routine for the CSMI SAS SSP Passthru command.
9565 + *
9566 + * Outputs:    None.
9567 + * Return:     0 if successful
9568 + *             -EFAULT if data unavailable
9569 + *             -ENODEV if no such device/adapter
9570 + */
9571 +static int mptctl_csmi_sas_ssp_passthru(unsigned long arg)
9572 +{
9573 +       CSMI_SAS_SSP_PASSTHRU_BUFFER __user *uarg = (void __user *) arg;
9574 +       CSMI_SAS_SSP_PASSTHRU_BUFFER     karg;
9575 +       MPT_ADAPTER                     *ioc = NULL;
9576 +       pSCSIIORequest_t                pScsiRequest;
9577 +       pSCSIIOReply_t                  pScsiReply;
9578 +       MPT_FRAME_HDR                   *mf = NULL;
9579 +       MPIHeader_t                     *mpi_hdr;
9580 +       int                             iocnum,ii;
9581 +       u32                             data_sz;
9582 +       u64                             SASAddress64;
9583 +       sas_device_info_t               *sasDevice;
9584 +       u16                             req_idx;
9585 +       char                            *psge;
9586 +       int                             flagsLength;
9587 +       void *                          request_data;
9588 +       dma_addr_t                      request_data_dma;
9589 +       u32                             request_data_sz;
9590 +       u8                              found;
9591 +       u16                             ioc_stat;
9592 +       u8                              volume_id;
9593 +       u8                              volume_bus;
9594 +       u8                              quiese_io_flag=0;
9595 +       u8                              bus;
9596 +       u8                              target;
9597 +       int                             wait_timeout;
9598 +
9599 +       dctlprintk((": %s called.\n",__FUNCTION__));
9600 +
9601 +       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_SSP_PASSTHRU_BUFFER))) {
9602 +               printk(KERN_ERR "%s@%d::%s() - "
9603 +                   "Unable to read in csmi_sas_ssp_passthru struct @ %p\n",
9604 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
9605 +               return -EFAULT;
9606 +       }
9607 +
9608 +       request_data=NULL;
9609 +       request_data_sz = karg.Parameters.uDataLength;
9610 +       bus=0;
9611 +       target=0;
9612 +       volume_id=0;
9613 +       volume_bus=0;
9614 +
9615 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
9616 +           &ioc)) < 0) || (ioc == NULL)) {
9617 +               dctlprintk((KERN_ERR
9618 +               "%s::%s() @%d - ioc%d not found!\n",
9619 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
9620 +               return -ENODEV;
9621 +       }
9622 +
9623 +       if (!mptctl_is_this_sas_cntr(ioc)) {
9624 +               dctlprintk((KERN_ERR
9625 +                   "%s::%s()"
9626 +                   " @%d - ioc%d not SAS controller!\n",
9627 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
9628 +               return -ENODEV;
9629 +       }
9630 +
9631 +       /* Default to success.
9632 +        */
9633 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
9634 +
9635 +       /* Neither a phy nor a port has been selected.
9636 +        */
9637 +       if ((karg.Parameters.bPhyIdentifier == CSMI_SAS_USE_PORT_IDENTIFIER) &&
9638 +               (karg.Parameters.bPortIdentifier == CSMI_SAS_IGNORE_PORT)) {
9639 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_SELECT_PHY_OR_PORT;
9640 +               dctlprintk((KERN_ERR
9641 +                   "%s::%s()"
9642 +                   " @%d - incorrect bPhyIdentifier and bPortIdentifier!\n",
9643 +                   __FILE__, __FUNCTION__, __LINE__));
9644 +               goto cim_ssp_passthru_exit;
9645 +       }
9646 +
9647 +       /* A phy has been selected. Verify that it's valid.
9648 +        */
9649 +       if (karg.Parameters.bPortIdentifier == CSMI_SAS_IGNORE_PORT) {
9650 +
9651 +               /* Is the phy in range? */
9652 +               if (karg.Parameters.bPhyIdentifier >= ioc->numPhys) {
9653 +                       karg.IoctlHeader.ReturnCode =
9654 +                           CSMI_SAS_PHY_DOES_NOT_EXIST;
9655 +                       goto cim_ssp_passthru_exit;
9656 +               }
9657 +       }
9658 +
9659 +       /* some checks of the incoming frame
9660 +        */
9661 +       if (request_data_sz > 0xFFFF) {
9662 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9663 +               dctlprintk((KERN_ERR
9664 +                   "%s::%s()"
9665 +                   " @%d - uDataLength > 0xFFFF!\n",
9666 +                   __FILE__, __FUNCTION__, __LINE__));
9667 +               goto cim_ssp_passthru_exit;
9668 +       }
9669 +
9670 +       data_sz = sizeof(CSMI_SAS_SSP_PASSTHRU_BUFFER) -
9671 +           sizeof(IOCTL_HEADER) - sizeof(u8*) +
9672 +           request_data_sz;
9673 +
9674 +       if ( data_sz > karg.IoctlHeader.Length ) {
9675 +               karg.IoctlHeader.ReturnCode =
9676 +                   CSMI_SAS_STATUS_INVALID_PARAMETER;
9677 +               dctlprintk((KERN_ERR
9678 +                   "%s::%s()"
9679 +                   " @%d - expected datalen incorrect!\n",
9680 +                   __FILE__, __FUNCTION__, __LINE__));
9681 +               goto cim_ssp_passthru_exit;
9682 +       }
9683 +
9684 +       /* we will use SAS address to resolve the scsi adddressing
9685 +        */
9686 +       memcpy(&SASAddress64,karg.Parameters.bDestinationSASAddress,
9687 +           sizeof(u64));
9688 +       SASAddress64 = reverse_byte_order64(&SASAddress64);
9689 +
9690 +       /* Search the list for the matching SAS address.
9691 +        */
9692 +       found = FALSE;
9693 +       list_for_each_entry(sasDevice, &ioc->sasDeviceList, list) {
9694 +
9695 +               /* Find the matching device.
9696 +                */
9697 +               if (sasDevice->SASAddress != SASAddress64)
9698 +                       continue;
9699 +
9700 +               found = TRUE;
9701 +               bus = sasDevice->Bus;
9702 +               target = sasDevice->TargetId;
9703 +               break;
9704 +       }
9705 +
9706 +       /* Invalid SAS address
9707 +        */
9708 +       if (found == FALSE) {
9709 +               karg.IoctlHeader.ReturnCode =
9710 +                   CSMI_SAS_STATUS_INVALID_PARAMETER;
9711 +               dctlprintk((KERN_ERR
9712 +                   "%s::%s()"
9713 +                   " @%d - couldn't find associated SASAddress!\n",
9714 +                   __FILE__, __FUNCTION__, __LINE__));
9715 +               goto cim_ssp_passthru_exit;
9716 +       }
9717 +
9718 +       if(karg.Parameters.bAdditionalCDBLength) {
9719 +       /* TODO - SCSI IO (32) Request Message support
9720 +        */
9721 +               dctlprintk((": greater than 16-byte cdb is not supported!\n"));
9722 +               karg.IoctlHeader.ReturnCode =
9723 +                   CSMI_SAS_STATUS_INVALID_PARAMETER;
9724 +               goto cim_ssp_passthru_exit;
9725 +       }
9726 +
9727 +       /* see if this is for raid phy disk */
9728 +       if (ioc->raid_data.isRaid && ioc->raid_data.pIocPg3) {
9729 +               for (ii = 0; (ii<ioc->raid_data.pIocPg3->NumPhysDisks &&
9730 +                   quiese_io_flag==0); ii++) {
9731 +                       if (target == ioc->raid_data.pIocPg3->PhysDisk[ii].PhysDiskID) {
9732 +                               target = ioc->raid_data.pIocPg3->PhysDisk[ii].PhysDiskNum;
9733 +                               quiese_io_flag=1;
9734 +                       }
9735 +               }
9736 +       }
9737 +#ifdef QUIESE_IO
9738 +       /* if RAID Volume, then quiesce io to phys disk*/
9739 +       if (quiese_io_flag==1) {
9740 +               if (mptctl_raid_get_volume_id(ioc, target,
9741 +                   &volume_id, &volume_bus) != 0) {
9742 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9743 +                       goto cim_ssp_passthru_exit;
9744 +               }
9745 +               mptctl_do_raid(ioc,
9746 +                   MPI_RAID_ACTION_QUIESCE_PHYS_IO,
9747 +                   target, volume_bus, volume_id, NULL);
9748 +       }
9749 +#endif
9750 +       /* Get a free request frame and save the message context.
9751 +        */
9752 +       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
9753 +               dctlprintk((": no msg frames!\n"));
9754 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9755 +               goto cim_ssp_passthru_exit;
9756 +        }
9757 +
9758 +       mpi_hdr = (MPIHeader_t *) mf;
9759 +       pScsiRequest = (pSCSIIORequest_t) mf;
9760 +       req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
9761 +
9762 +       memset(pScsiRequest,0,sizeof(SCSIIORequest_t));
9763 +
9764 +       /* Fill in SCSI IO (16) request.
9765 +        */
9766 +
9767 +       pScsiRequest->Function = (quiese_io_flag==1) ?
9768 +           MPI_FUNCTION_RAID_SCSI_IO_PASSTHROUGH : MPI_FUNCTION_SCSI_IO_REQUEST;
9769 +       pScsiRequest->TargetID = target;
9770 +       pScsiRequest->Bus = bus;
9771 +       memcpy(pScsiRequest->LUN,karg.Parameters.bLun,8);
9772 +       pScsiRequest->CDBLength = karg.Parameters.bCDBLength;
9773 +       pScsiRequest->DataLength = cpu_to_le16(request_data_sz);
9774 +       pScsiRequest->MsgContext = mpi_hdr->MsgContext;
9775 +       memcpy(pScsiRequest->CDB,karg.Parameters.bCDB,
9776 +           pScsiRequest->CDBLength);
9777 +
9778 +       /* direction
9779 +        */
9780 +       if (karg.Parameters.uFlags & CSMI_SAS_SSP_READ) {
9781 +               pScsiRequest->Control = cpu_to_le32(MPI_SCSIIO_CONTROL_READ);
9782 +       } else if (karg.Parameters.uFlags & CSMI_SAS_SSP_WRITE) {
9783 +               pScsiRequest->Control = cpu_to_le32(MPI_SCSIIO_CONTROL_WRITE);
9784 +       } else if ((karg.Parameters.uFlags & CSMI_SAS_SSP_UNSPECIFIED) &&
9785 +           (!karg.Parameters.uDataLength)) {
9786 +               /* no data transfer
9787 +                */
9788 +               pScsiRequest->Control = cpu_to_le32(MPI_SCSIIO_CONTROL_NODATATRANSFER);
9789 +       } else {
9790 +               /* no direction specified
9791 +                */
9792 +               pScsiRequest->Control = cpu_to_le32(MPI_SCSIIO_CONTROL_READ);
9793 +               pScsiRequest->MsgFlags =
9794 +                   MPI_SCSIIO_MSGFLGS_CMD_DETERMINES_DATA_DIR;
9795 +       }
9796 +
9797 +       /* task attributes
9798 +        */
9799 +       if((karg.Parameters.uFlags && 0xFF) == 0) {
9800 +               pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_SIMPLEQ);
9801 +       } else if (karg.Parameters.uFlags &
9802 +           CSMI_SAS_SSP_TASK_ATTRIBUTE_HEAD_OF_QUEUE) {
9803 +               pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_HEADOFQ);
9804 +       } else if (karg.Parameters.uFlags &
9805 +           CSMI_SAS_SSP_TASK_ATTRIBUTE_ORDERED) {
9806 +               pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_ORDEREDQ);
9807 +       } else if (karg.Parameters.uFlags &
9808 +           CSMI_SAS_SSP_TASK_ATTRIBUTE_ACA) {
9809 +               pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_ACAQ);
9810 +       } else {
9811 +               pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_UNTAGGED);
9812 +       }
9813 +
9814 +       /* setup sense
9815 +        */
9816 +       pScsiRequest->SenseBufferLength = MPT_SENSE_BUFFER_SIZE;
9817 +       pScsiRequest->SenseBufferLowAddr = cpu_to_le32(ioc->sense_buf_low_dma +
9818 +           (req_idx * MPT_SENSE_BUFFER_ALLOC));
9819 +
9820 +       /* setup databuffer sg, assuming we fit everything one contiguous buffer
9821 +        */
9822 +       psge = (char *)&pScsiRequest->SGL;
9823 +
9824 +       if (karg.Parameters.uFlags & CSMI_SAS_SSP_WRITE) {
9825 +               flagsLength = MPT_SGE_FLAGS_SSIMPLE_WRITE;
9826 +       } else if (karg.Parameters.uFlags & CSMI_SAS_SSP_READ) {
9827 +               flagsLength = MPT_SGE_FLAGS_SSIMPLE_READ;
9828 +       }else {
9829 +               flagsLength = ( MPI_SGE_FLAGS_SIMPLE_ELEMENT |
9830 +                               MPI_SGE_FLAGS_DIRECTION |
9831 +                               mpt_addr_size() )
9832 +                               << MPI_SGE_FLAGS_SHIFT;
9833 +       }
9834 +       flagsLength |= request_data_sz;
9835 +
9836 +       if ( request_data_sz > 0) {
9837 +               request_data = pci_alloc_consistent(
9838 +                   ioc->pcidev, request_data_sz, &request_data_dma);
9839 +
9840 +               if (request_data == NULL) {
9841 +                       dctlprintk((": pci_alloc_consistent: FAILED request_data_sz=%d\n", request_data_sz));
9842 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9843 +                       mpt_free_msg_frame(ioc, mf);
9844 +                       goto cim_ssp_passthru_exit;
9845 +               }
9846 +
9847 +               mpt_add_sge(psge, flagsLength, request_data_dma);
9848 +
9849 +               if (karg.Parameters.uFlags & CSMI_SAS_SSP_WRITE) {
9850 +
9851 +                       if (copy_from_user(request_data,
9852 +                           karg.bDataBuffer,
9853 +                           request_data_sz)) {
9854 +                               printk(KERN_ERR
9855 +                               "%s@%d::%s - Unable "
9856 +                                   "to read user data "
9857 +                                   "struct @ %p\n",
9858 +                                   __FILE__, __LINE__,__FUNCTION__,
9859 +                                   (void*)karg.bDataBuffer);
9860 +                               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9861 +                               mpt_free_msg_frame(ioc, mf);
9862 +                               goto cim_ssp_passthru_exit;
9863 +                       }
9864 +               }
9865 +       } else {
9866 +               mpt_add_sge(psge, flagsLength, (dma_addr_t) -1);
9867 +       }
9868 +
9869 +       /* The request is complete. Set the timer parameters
9870 +        * and issue the request.
9871 +        */
9872 +       ioc->ioctl->wait_done = 0;
9873 +       mpt_put_msg_frame(mptctl_id, ioc, mf);
9874 +
9875 +       /* Now wait for the command to complete */
9876 +       wait_timeout=max_t(int,MPT_IOCTL_DEFAULT_TIMEOUT,karg.IoctlHeader.Timeout);
9877 +       ii = wait_event_timeout(mptctl_wait,
9878 +            ioc->ioctl->wait_done == 1,
9879 +            HZ*wait_timeout);
9880 +
9881 +       if(ii <=0 && (ioc->ioctl->wait_done != 1 )) {
9882 +       /* Now we need to reset the board */
9883 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9884 +               mpt_free_msg_frame(ioc, mf);
9885 +               mptctl_timeout_expired(ioc->ioctl);
9886 +               goto cim_ssp_passthru_exit;
9887 +       }
9888 +
9889 +       memset(&karg.Status,0,sizeof(CSMI_SAS_SSP_PASSTHRU_STATUS));
9890 +       karg.Status.bConnectionStatus = CSMI_SAS_OPEN_ACCEPT;
9891 +       karg.Status.bDataPresent = CSMI_SAS_SSP_NO_DATA_PRESENT;
9892 +       karg.Status.bStatus = GOOD;
9893 +       karg.Status.bResponseLength[0] = 0;
9894 +       karg.Status.bResponseLength[1] = 0;
9895 +       karg.Status.uDataBytes = request_data_sz;
9896 +
9897 +       /* process the completed Reply Message Frame */
9898 +       if (ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) {
9899 +
9900 +               pScsiReply = (pSCSIIOReply_t ) ioc->ioctl->ReplyFrame;
9901 +               karg.Status.bStatus = pScsiReply->SCSIStatus;
9902 +               karg.Status.uDataBytes = min(le32_to_cpu(pScsiReply->TransferCount),
9903 +                   request_data_sz);
9904 +               ioc_stat = le16_to_cpu(pScsiReply->IOCStatus) & MPI_IOCSTATUS_MASK;
9905 +
9906 +               if (pScsiReply->SCSIState ==
9907 +                   MPI_SCSI_STATE_AUTOSENSE_VALID) {
9908 +                       karg.Status.bConnectionStatus =
9909 +                           CSMI_SAS_SSP_SENSE_DATA_PRESENT;
9910 +                       karg.Status.bResponseLength[0] =
9911 +                               (u8)le32_to_cpu(pScsiReply->SenseCount) & 0xFF;
9912 +                       memcpy(karg.Status.bResponse,
9913 +                           ioc->ioctl->sense, le32_to_cpu(pScsiReply->SenseCount));
9914 +               } else if(pScsiReply->SCSIState ==
9915 +                   MPI_SCSI_STATE_RESPONSE_INFO_VALID) {
9916 +                       karg.Status.bDataPresent =
9917 +                           CSMI_SAS_SSP_RESPONSE_DATA_PRESENT;
9918 +                       karg.Status.bResponseLength[0] =
9919 +                               sizeof(pScsiReply->ResponseInfo);
9920 +                       for (ii=0;ii<sizeof(pScsiReply->ResponseInfo);ii++) {
9921 +                               karg.Status.bResponse[ii] =
9922 +                               ((u8*)&pScsiReply->ResponseInfo)[
9923 +                                   (sizeof(pScsiReply->ResponseInfo)-1)-ii];
9924 +                       }
9925 +               } else if ((ioc_stat != MPI_IOCSTATUS_SUCCESS) &&
9926 +                   (ioc_stat !=  MPI_IOCSTATUS_SCSI_RECOVERED_ERROR) &&
9927 +                   (ioc_stat != MPI_IOCSTATUS_SCSI_DATA_UNDERRUN)) {
9928 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9929 +                       dctlprintk((": SCSI IO : "));
9930 +                       dctlprintk(("IOCStatus=0x%X IOCLogInfo=0x%X\n",
9931 +                           pScsiReply->IOCStatus,
9932 +                           pScsiReply->IOCLogInfo));
9933 +               }
9934 +       }
9935 +
9936 +       if ((karg.Status.uDataBytes) && (request_data) &&
9937 +           (karg.Parameters.uFlags & CSMI_SAS_SSP_READ)) {
9938 +               if (copy_to_user((char *)uarg->bDataBuffer,
9939 +                   request_data, karg.Status.uDataBytes)) {
9940 +                       printk(KERN_ERR "%s@%d::%s - "
9941 +                           "Unable to write data to user %p\n",
9942 +                           __FILE__, __LINE__,__FUNCTION__,
9943 +                           (void*)karg.bDataBuffer);
9944 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
9945 +               }
9946 +       }
9947 +
9948 +cim_ssp_passthru_exit:
9949 +
9950 +       ioc->ioctl->status &= ~(  MPT_IOCTL_STATUS_TM_FAILED |
9951 +           MPT_IOCTL_STATUS_COMMAND_GOOD | MPT_IOCTL_STATUS_SENSE_VALID |
9952 +           MPT_IOCTL_STATUS_RF_VALID);
9953 +
9954 +       if (request_data)
9955 +               pci_free_consistent(ioc->pcidev, request_data_sz,
9956 +                   (u8 *)request_data, request_data_dma);
9957 +
9958 +#ifdef QUIESE_IO
9959 +       if (quiese_io_flag) {
9960 +               mptctl_do_raid(ioc,
9961 +                   MPI_RAID_ACTION_ENABLE_PHYS_IO,
9962 +                   target, volume_bus, volume_id, NULL);
9963 +       }
9964 +#endif
9965 +       /* Copy the data from kernel memory to user memory
9966 +        */
9967 +       if (copy_to_user((char *)arg, &karg,
9968 +           offsetof(CSMI_SAS_SSP_PASSTHRU_BUFFER,bDataBuffer))) {
9969 +               printk(KERN_ERR "%s@%d::%s() - "
9970 +                       "Unable to write out csmi_sas_ssp_passthru @ %p\n",
9971 +                               __FILE__, __LINE__, __FUNCTION__, uarg);
9972 +               return -EFAULT;
9973 +       }
9974 +
9975 +       return 0;
9976 +}
9977 +
9978 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
9979 +/* Prototype Routine for the CSMI SAS STP Passthru command.
9980 + *
9981 + * Outputs:    None.
9982 + * Return:     0 if successful
9983 + *             -EFAULT if data unavailable
9984 + *             -ENODEV if no such device/adapter
9985 + */
9986 +static int
9987 +mptctl_csmi_sas_stp_passthru(unsigned long arg)
9988 +{
9989 +       CSMI_SAS_STP_PASSTHRU_BUFFER __user *uarg = (void __user *) arg;
9990 +       CSMI_SAS_STP_PASSTHRU_BUFFER     karg;
9991 +       MPT_ADAPTER                     *ioc = NULL;
9992 +       pSataPassthroughRequest_t       pSataRequest;
9993 +       pSataPassthroughReply_t         pSataReply;
9994 +       MPT_FRAME_HDR                   *mf = NULL;
9995 +       MPIHeader_t                     *mpi_hdr;
9996 +       int                             iocnum,ii;
9997 +       u32                             data_sz;
9998 +       u64                             SASAddress64;
9999 +       sas_device_info_t               *sasDevice=NULL;
10000 +       u16                             req_idx;
10001 +       char                            *psge;
10002 +       int                             flagsLength;
10003 +       void *                          request_data;
10004 +       dma_addr_t                      request_data_dma;
10005 +       u32                             request_data_sz;
10006 +       u8                              found;
10007 +       u8                              bus;
10008 +       u8                              target;
10009 +       u8                              volume_id;
10010 +       u8                              volume_bus;
10011 +#ifdef QUIESE_IO
10012 +       u8                              quiese_io_flag=0;
10013 +       u8                              phys_disk_num=0;
10014 +#endif
10015 +       int                             wait_timeout;
10016 +
10017 +       dctlprintk((": %s called.\n",__FUNCTION__));
10018 +
10019 +       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_STP_PASSTHRU_BUFFER))) {
10020 +               printk(KERN_ERR "%s@%d::%s() - "
10021 +                   "Unable to read struct @ %p\n",
10022 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
10023 +               return -EFAULT;
10024 +       }
10025 +
10026 +       request_data=NULL;
10027 +       request_data_sz = karg.Parameters.uDataLength;
10028 +       volume_id=0;
10029 +       volume_bus=0;
10030 +       bus=0;
10031 +       target=0;
10032 +
10033 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
10034 +           &ioc)) < 0) || (ioc == NULL)) {
10035 +               dctlprintk((KERN_ERR
10036 +               "%s::%s @%d - ioc%d not found!\n",
10037 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
10038 +               return -ENODEV;
10039 +       }
10040 +
10041 +       if (!mptctl_is_this_sas_cntr(ioc)) {
10042 +               dctlprintk((KERN_ERR
10043 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
10044 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
10045 +               return -ENODEV;
10046 +       }
10047 +
10048 +       /* Default to success.
10049 +        */
10050 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
10051 +
10052 +       /* Neither a phy nor a port has been selected.
10053 +        */
10054 +       if ((karg.Parameters.bPhyIdentifier == CSMI_SAS_USE_PORT_IDENTIFIER) &&
10055 +               (karg.Parameters.bPortIdentifier == CSMI_SAS_IGNORE_PORT)) {
10056 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_SELECT_PHY_OR_PORT;
10057 +               dctlprintk((KERN_ERR
10058 +                   "%s::%s() @%d - incorrect bPhyIdentifier and bPortIdentifier!\n",
10059 +                   __FILE__,__FUNCTION__, __LINE__));
10060 +               goto cim_stp_passthru_exit;
10061 +       }
10062 +
10063 +       /* A phy has been selected. Verify that it's valid.
10064 +        */
10065 +       if (karg.Parameters.bPortIdentifier == CSMI_SAS_IGNORE_PORT) {
10066 +
10067 +               /* Is the phy in range? */
10068 +               if (karg.Parameters.bPhyIdentifier >= ioc->numPhys) {
10069 +                       karg.IoctlHeader.ReturnCode =
10070 +                           CSMI_SAS_PHY_DOES_NOT_EXIST;
10071 +                       goto cim_stp_passthru_exit;
10072 +               }
10073 +       }
10074 +
10075 +       /* some checks of the incoming frame
10076 +        */
10077 +       if (request_data_sz > 0xFFFF) {
10078 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10079 +               dctlprintk((KERN_ERR
10080 +                   "%s::%s() @%d - uDataLength > 0xFFFF!\n",
10081 +                   __FILE__, __FUNCTION__, __LINE__));
10082 +               goto cim_stp_passthru_exit;
10083 +       }
10084 +
10085 +       data_sz = sizeof(CSMI_SAS_STP_PASSTHRU_BUFFER) -
10086 +           sizeof(IOCTL_HEADER) - sizeof(u8*) +
10087 +           request_data_sz;
10088 +
10089 +       if ( data_sz > karg.IoctlHeader.Length ) {
10090 +               karg.IoctlHeader.ReturnCode =
10091 +                   CSMI_SAS_STATUS_INVALID_PARAMETER;
10092 +               dctlprintk((KERN_ERR
10093 +                   "%s::%s() @%d - expected datalen incorrect!\n",
10094 +                   __FILE__, __FUNCTION__,__LINE__));
10095 +               goto cim_stp_passthru_exit;
10096 +       }
10097 +
10098 +       /* we will use SAS address to resolve the scsi adddressing
10099 +        */
10100 +       memcpy(&SASAddress64,karg.Parameters.bDestinationSASAddress,
10101 +           sizeof(u64));
10102 +       SASAddress64 = reverse_byte_order64(&SASAddress64);
10103 +
10104 +       /* Search the list for the matching SAS address.
10105 +        */
10106 +       found = FALSE;
10107 +       list_for_each_entry(sasDevice, &ioc->sasDeviceList, list) {
10108 +
10109 +               /* Find the matching device.
10110 +                */
10111 +               if (sasDevice->SASAddress != SASAddress64)
10112 +                       continue;
10113 +
10114 +               found = TRUE;
10115 +               bus = sasDevice->Bus;
10116 +               target = sasDevice->TargetId;;
10117 +               break;
10118 +       }
10119 +
10120 +       /* Invalid SAS address
10121 +        */
10122 +       if (found == FALSE) {
10123 +               karg.IoctlHeader.ReturnCode =
10124 +                   CSMI_SAS_STATUS_INVALID_PARAMETER;
10125 +               dctlprintk((KERN_ERR
10126 +                   "%s::%s() @%d - couldn't find associated SASAddress!\n",
10127 +                   __FILE__, __FUNCTION__, __LINE__));
10128 +               goto cim_stp_passthru_exit;
10129 +       }
10130 +
10131 +       /* check that this is an STP or SATA target device
10132 +        */
10133 +       if ( !(sasDevice->DeviceInfo & MPI_SAS_DEVICE_INFO_STP_TARGET ) &&
10134 +            !(sasDevice->DeviceInfo & MPI_SAS_DEVICE_INFO_SATA_DEVICE )) {
10135 +               karg.IoctlHeader.ReturnCode =
10136 +                   CSMI_SAS_STATUS_INVALID_PARAMETER;
10137 +               goto cim_stp_passthru_exit;
10138 +       }
10139 +
10140 +#ifdef QUIESE_IO
10141 +       /* see if this is for raid phy disk */
10142 +       if (ioc->raid_data.isRaid && ioc->raid_data.pIocPg3) {
10143 +               for (ii = 0; (ii<ioc->raid_data.pIocPg3->NumPhysDisks &&
10144 +                   quiese_io_flag==0); ii++)
10145 +                       if (target == ioc->raid_data.pIocPg3->PhysDisk[ii].PhysDiskID) {
10146 +                               phys_disk_num = ioc->raid_data.pIocPg3->PhysDisk[ii].PhysDiskNum;
10147 +                               quiese_io_flag=1;
10148 +                       }
10149 +       }
10150 +       /* if RAID Volume, then quiesce io to phys disk*/
10151 +       if (quiese_io_flag==1) {
10152 +               if (mptctl_raid_get_volume_id(ioc, phys_disk_num,
10153 +                   &volume_id, &volume_bus) != 0) {
10154 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10155 +                       goto cim_stp_passthru_exit;
10156 +               }
10157 +               mptctl_do_raid(ioc,
10158 +                   MPI_RAID_ACTION_QUIESCE_PHYS_IO,
10159 +                   phys_disk_num, volume_bus, volume_id, NULL);
10160 +       }
10161 +#endif
10162 +       /* Get a free request frame and save the message context.
10163 +        */
10164 +       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
10165 +               dctlprintk((": no msg frames!\n"));
10166 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10167 +               goto cim_stp_passthru_exit;
10168 +        }
10169 +
10170 +       mpi_hdr = (MPIHeader_t *) mf;
10171 +       pSataRequest = (pSataPassthroughRequest_t) mf;
10172 +       req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
10173 +
10174 +       memset(pSataRequest,0,sizeof(pSataPassthroughRequest_t));
10175 +
10176 +       pSataRequest->TargetID = target;
10177 +       pSataRequest->Bus = bus;
10178 +       pSataRequest->Function = MPI_FUNCTION_SATA_PASSTHROUGH;
10179 +       pSataRequest->PassthroughFlags = cpu_to_le16(karg.Parameters.uFlags);
10180 +       pSataRequest->ConnectionRate = karg.Parameters.bConnectionRate;
10181 +       pSataRequest->MsgContext = mpi_hdr->MsgContext;
10182 +       pSataRequest->DataLength = cpu_to_le32(request_data_sz);
10183 +       pSataRequest->MsgFlags = 0;
10184 +       memcpy( pSataRequest->CommandFIS,karg.Parameters.bCommandFIS, 20);
10185 +
10186 +       psge = (char *)&pSataRequest->SGL;
10187 +       if (karg.Parameters.uFlags & CSMI_SAS_STP_WRITE) {
10188 +               flagsLength = MPT_SGE_FLAGS_SSIMPLE_WRITE;
10189 +       } else if (karg.Parameters.uFlags & CSMI_SAS_STP_READ) {
10190 +               flagsLength = MPT_SGE_FLAGS_SSIMPLE_READ;
10191 +       }else {
10192 +               flagsLength = ( MPI_SGE_FLAGS_SIMPLE_ELEMENT |
10193 +                               MPI_SGE_FLAGS_DIRECTION |
10194 +                               mpt_addr_size() )
10195 +                               << MPI_SGE_FLAGS_SHIFT;
10196 +       }
10197 +
10198 +       flagsLength |= request_data_sz;
10199 +       if (request_data_sz > 0) {
10200 +               request_data = pci_alloc_consistent(
10201 +                   ioc->pcidev, request_data_sz, &request_data_dma);
10202 +
10203 +               if (request_data == NULL) {
10204 +                       dctlprintk((": pci_alloc_consistent: FAILED\n"));
10205 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10206 +                       mpt_free_msg_frame(ioc, mf);
10207 +                       goto cim_stp_passthru_exit;
10208 +               }
10209 +
10210 +               mpt_add_sge(psge, flagsLength, request_data_dma);
10211 +               if (karg.Parameters.uFlags & CSMI_SAS_STP_WRITE) {
10212 +                       if (copy_from_user(request_data,
10213 +                           karg.bDataBuffer,
10214 +                           request_data_sz)) {
10215 +                               printk(KERN_ERR
10216 +                                   "%s::%s() @%d - Unable to read user data "
10217 +                                   "struct @ %p\n",
10218 +                                   __FILE__, __FUNCTION__, __LINE__,
10219 +                                   (void*)karg.bDataBuffer);
10220 +                               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10221 +                               mpt_free_msg_frame(ioc, mf);
10222 +                               goto cim_stp_passthru_exit;
10223 +                       }
10224 +               }
10225 +       } else {
10226 +               mpt_add_sge(psge, flagsLength, (dma_addr_t) -1);
10227 +       }
10228 +
10229 +       /* The request is complete. Set the timer parameters
10230 +        * and issue the request.
10231 +        */
10232 +       ioc->ioctl->wait_done = 0;
10233 +       mpt_put_msg_frame(mptctl_id, ioc, mf);
10234 +
10235 +       /* Now wait for the command to complete */
10236 +       wait_timeout=max_t(int,MPT_IOCTL_DEFAULT_TIMEOUT,karg.IoctlHeader.Timeout);
10237 +       ii = wait_event_timeout(mptctl_wait,
10238 +            ioc->ioctl->wait_done == 1,
10239 +            HZ*wait_timeout);
10240 +
10241 +       if(ii <=0 && (ioc->ioctl->wait_done != 1 )) {
10242 +       /* Now we need to reset the board */
10243 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10244 +               mpt_free_msg_frame(ioc, mf);
10245 +               mptctl_timeout_expired(ioc->ioctl);
10246 +               goto cim_stp_passthru_exit;
10247 +       }
10248 +
10249 +       memset(&karg.Status,0,sizeof(CSMI_SAS_STP_PASSTHRU_STATUS));
10250 +
10251 +       if ((ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) == 0) {
10252 +               dctlprintk((": STP Passthru: oh no, there is no reply!!"));
10253 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10254 +               goto cim_stp_passthru_exit;
10255 +       }
10256 +
10257 +       /* process the completed Reply Message Frame */
10258 +       pSataReply = (pSataPassthroughReply_t ) ioc->ioctl->ReplyFrame;
10259 +
10260 +       if ((le16_to_cpu(pSataReply->IOCStatus) != MPI_IOCSTATUS_SUCCESS) &&
10261 +           (le16_to_cpu(pSataReply->IOCStatus) != MPI_IOCSTATUS_SCSI_DATA_UNDERRUN )) {
10262 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10263 +               dctlprintk((": STP Passthru: "));
10264 +               dctlprintk(("IOCStatus=0x%X IOCLogInfo=0x%X SASStatus=0x%X\n",
10265 +                   le16_to_cpu(pSataReply->IOCStatus),
10266 +                   le32_to_cpu(pSataReply->IOCLogInfo),
10267 +                   pSataReply->SASStatus));
10268 +       }
10269 +
10270 +       karg.Status.bConnectionStatus =
10271 +           map_sas_status_to_csmi(pSataReply->SASStatus);
10272 +
10273 +       memcpy(karg.Status.bStatusFIS,pSataReply->StatusFIS, 20);
10274 +
10275 +       /*
10276 +        * for now, just zero out uSCR array,
10277 +        * then copy the one dword returned
10278 +        * in the reply frame into uSCR[0]
10279 +        */
10280 +       memset( karg.Status.uSCR, 0, 64);
10281 +       karg.Status.uSCR[0] = le32_to_cpu(pSataReply->StatusControlRegisters);
10282 +
10283 +       if((le32_to_cpu(pSataReply->TransferCount)) && (request_data) &&
10284 +           (karg.Parameters.uFlags & CSMI_SAS_STP_READ)) {
10285 +               karg.Status.uDataBytes =
10286 +                   min(le32_to_cpu(pSataReply->TransferCount),request_data_sz);
10287 +               if (copy_to_user((char *)uarg->bDataBuffer,
10288 +                   request_data, karg.Status.uDataBytes)) {
10289 +                       printk(KERN_ERR "%s::%s() @%d - "
10290 +                           "Unable to write data to user %p\n",
10291 +                           __FILE__, __FUNCTION__, __LINE__,
10292 +                           (void*)karg.bDataBuffer);
10293 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10294 +               }
10295 +       }
10296 +
10297 +cim_stp_passthru_exit:
10298 +
10299 +       ioc->ioctl->status &= ~( MPT_IOCTL_STATUS_TM_FAILED |
10300 +           MPT_IOCTL_STATUS_COMMAND_GOOD | MPT_IOCTL_STATUS_SENSE_VALID |
10301 +           MPT_IOCTL_STATUS_RF_VALID );
10302 +
10303 +       if (request_data)
10304 +               pci_free_consistent(ioc->pcidev, request_data_sz,
10305 +                   (u8 *)request_data, request_data_dma);
10306 +
10307 +#ifdef QUIESE_IO
10308 +       if (quiese_io_flag)
10309 +               mptctl_do_raid(ioc,
10310 +                   MPI_RAID_ACTION_ENABLE_PHYS_IO,
10311 +                   phys_disk_num, volume_bus, volume_id, NULL);
10312 +#endif
10313 +
10314 +       /* Copy th data from kernel memory to user memory
10315 +        */
10316 +       if (copy_to_user((char *)arg, &karg,
10317 +           offsetof(CSMI_SAS_STP_PASSTHRU_BUFFER,bDataBuffer))) {
10318 +               printk(KERN_ERR "%s@%d::%s() - "
10319 +                       "Unable to write out csmi_sas_ssp_passthru @ %p\n",
10320 +                               __FILE__, __LINE__, __FUNCTION__, uarg);
10321 +               return -EFAULT;
10322 +       }
10323 +
10324 +       return 0;
10325 +
10326 +}
10327 +
10328 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
10329 +/* Prototype Routine for the CSMI SAS Firmware Download command.
10330 + *
10331 + * Outputs:    None.
10332 + * Return:     0 if successful
10333 + *             -EFAULT if data unavailable
10334 + *             -ENODEV if no such device/adapter
10335 + */
10336 +static int
10337 +mptctl_csmi_sas_firmware_download(unsigned long arg)
10338 +{
10339 +       CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER __user *uarg = (void __user *) arg;
10340 +       CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER        karg;
10341 +       MPT_ADAPTER                     *ioc = NULL;
10342 +       int                             iocnum;
10343 +       pMpiFwHeader_t                  pFwHeader=NULL;
10344 +
10345 +       dctlprintk((": %s called.\n",__FUNCTION__));
10346 +
10347 +       if (copy_from_user(&karg, uarg,
10348 +               sizeof(CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER))) {
10349 +               printk(KERN_ERR "%s@%d::%s() - "
10350 +                   "Unable to read in csmi_sas_firmware_download struct @ %p\n",
10351 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
10352 +               return -EFAULT;
10353 +       }
10354 +
10355 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
10356 +           &ioc)) < 0) || (ioc == NULL)) {
10357 +               dctlprintk((KERN_ERR
10358 +               "%s::%s() @%d - ioc%d not found!\n",
10359 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
10360 +               return -ENODEV;
10361 +       }
10362 +
10363 +       if (!mptctl_is_this_sas_cntr(ioc)) {
10364 +               dctlprintk((KERN_ERR
10365 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
10366 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
10367 +               return -ENODEV;
10368 +       }
10369 +
10370 +       /* Default to success.*/
10371 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
10372 +       karg.Information.usStatus = CSMI_SAS_FWD_SUCCESS;
10373 +       karg.Information.usSeverity = CSMI_SAS_FWD_INFORMATION;
10374 +
10375 +       /* some checks of the incoming frame */
10376 +       if ((karg.Information.uBufferLength +
10377 +           sizeof(CSMI_SAS_FIRMWARE_DOWNLOAD)) >
10378 +           karg.IoctlHeader.Length) {
10379 +               karg.IoctlHeader.ReturnCode =
10380 +                   CSMI_SAS_STATUS_INVALID_PARAMETER;
10381 +               karg.Information.usStatus = CSMI_SAS_FWD_FAILED;
10382 +               goto cim_firmware_download_exit;
10383 +       }
10384 +
10385 +       if ( karg.Information.uDownloadFlags &
10386 +           (CSMI_SAS_FWD_SOFT_RESET | CSMI_SAS_FWD_VALIDATE)) {
10387 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10388 +               karg.Information.usStatus = CSMI_SAS_FWD_REJECT;
10389 +               karg.Information.usSeverity = CSMI_SAS_FWD_ERROR;
10390 +               goto cim_firmware_download_exit;
10391 +       }
10392 +
10393 +       /* now we need to alloc memory so we can pull in the
10394 +        * fw image attached to end of incomming packet.
10395 +        */
10396 +       pFwHeader = kmalloc(karg.Information.uBufferLength, GFP_KERNEL);
10397 +       if(pFwHeader==NULL){
10398 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10399 +               karg.Information.usStatus = CSMI_SAS_FWD_REJECT;
10400 +               karg.Information.usSeverity = CSMI_SAS_FWD_ERROR;
10401 +               goto cim_firmware_download_exit;
10402 +       }
10403 +
10404 +       if (copy_from_user(pFwHeader, uarg->bDataBuffer,
10405 +               karg.Information.uBufferLength)) {
10406 +               printk(KERN_ERR "%s@%d::%s() - "
10407 +                   "Unable to read in pFwHeader @ %p\n",
10408 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
10409 +               return -EFAULT;
10410 +       }
10411 +
10412 +       if ( !((pFwHeader->Signature0 == MPI_FW_HEADER_SIGNATURE_0) &&
10413 +           (pFwHeader->Signature1 == MPI_FW_HEADER_SIGNATURE_1) &&
10414 +           (pFwHeader->Signature2 == MPI_FW_HEADER_SIGNATURE_2))) {
10415 +               // the signature check failed
10416 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10417 +               karg.Information.usStatus = CSMI_SAS_FWD_REJECT;
10418 +               karg.Information.usSeverity = CSMI_SAS_FWD_ERROR;
10419 +               goto cim_firmware_download_exit;
10420 +       }
10421 +
10422 +       if ( mptctl_do_fw_download(karg.IoctlHeader.IOControllerNumber,
10423 +           uarg->bDataBuffer, karg.Information.uBufferLength)
10424 +           != 0) {
10425 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10426 +               karg.Information.usStatus = CSMI_SAS_FWD_FAILED;
10427 +               karg.Information.usSeverity = CSMI_SAS_FWD_FATAL;
10428 +               goto cim_firmware_download_exit;
10429 +       }
10430 +
10431 +       if((karg.Information.uDownloadFlags & CSMI_SAS_FWD_SOFT_RESET) ||
10432 +           (karg.Information.uDownloadFlags & CSMI_SAS_FWD_HARD_RESET)) {
10433 +               if (mpt_HardResetHandler(ioc, CAN_SLEEP) != 0) {
10434 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10435 +                       karg.Information.usStatus = CSMI_SAS_FWD_FAILED;
10436 +                       karg.Information.usSeverity = CSMI_SAS_FWD_FATAL;
10437 +               }
10438 +       }
10439 +
10440 +cim_firmware_download_exit:
10441 +
10442 +       if(pFwHeader)
10443 +               kfree(pFwHeader);
10444 +
10445 +       /* Copy the data from kernel memory to user memory
10446 +        */
10447 +       if (copy_to_user((char *)arg, &karg,
10448 +                               sizeof(CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER))) {
10449 +               printk(KERN_ERR "%s@%d::%s() - "
10450 +                       "Unable to write out csmi_sas_firmware_download @ %p\n",
10451 +                               __FILE__, __LINE__, __FUNCTION__, uarg);
10452 +               return -EFAULT;
10453 +       }
10454 +
10455 +       return 0;
10456 +}
10457 +
10458 +
10459 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
10460 +/* Prototype Routine for the CSMI SAS Get RAID Info command.
10461 + *
10462 + * Outputs:    None.
10463 + * Return:     0 if successful
10464 + *             -EFAULT if data unavailable
10465 + *             -ENODEV if no such device/adapter
10466 + */
10467 +static int
10468 +mptctl_csmi_sas_get_raid_info(unsigned long arg)
10469 +{
10470 +       CSMI_SAS_RAID_INFO_BUFFER __user *uarg =  (void __user *) arg;
10471 +       CSMI_SAS_RAID_INFO_BUFFER        karg;
10472 +       MPT_ADAPTER             *ioc = NULL;
10473 +       int                             iocnum;
10474 +    u32             raidFlags;
10475 +       u8                              maxRaidTypes;
10476 +
10477 +       dctlprintk((": %s called.\n",__FUNCTION__));
10478 +
10479 +       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_RAID_INFO_BUFFER))) {
10480 +               printk(KERN_ERR "%s@%d::%s() - "
10481 +                   "Unable to read in csmi_sas_get_raid_info struct @ %p\n",
10482 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
10483 +               return -EFAULT;
10484 +       }
10485 +
10486 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
10487 +           &ioc)) < 0) || (ioc == NULL)) {
10488 +               dctlprintk((KERN_ERR
10489 +               "%s::%s() @%d - ioc%d not found!\n",
10490 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
10491 +               return -ENODEV;
10492 +       }
10493 +
10494 +       if (!mptctl_is_this_sas_cntr(ioc)) {
10495 +               dctlprintk((KERN_ERR
10496 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
10497 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
10498 +               return -ENODEV;
10499 +       }
10500 +
10501 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10502 +       if( !mpt_findImVolumes(ioc)) {
10503 +               if ( ioc->raid_data.pIocPg2 ) {
10504 +                       karg.Information.uNumRaidSets = ioc->raid_data.pIocPg2->NumActiveVolumes;
10505 +            // uMaxDrivesPerSet hard coded until value is available through RAID config page
10506 +                       karg.Information.uMaxDrivesPerSet = 8;
10507 +            karg.Information.uMaxRaidSets = ioc->raid_data.pIocPg2->MaxVolumes;
10508 +            // For bMaxRaidSets, count bits set in bits 0-6 of CapabilitiesFlags
10509 +            raidFlags = ioc->raid_data.pIocPg2->CapabilitiesFlags & 0x0000007F;
10510 +            for( maxRaidTypes=0; raidFlags; maxRaidTypes++ )
10511 +            {
10512 +                raidFlags &= raidFlags - 1;
10513 +            }
10514 +            karg.Information.bMaxRaidTypes = maxRaidTypes;
10515 +            // ulMinRaidSetBlocks hard coded to 1MB until available from config page
10516 +            karg.Information.ulMinRaidSetBlocks = 2048;
10517 +            karg.Information.ulMaxRaidSetBlocks = 
10518 +                (ioc->raid_data.pIocPg2->CapabilitiesFlags & 
10519 +                 MPI_IOCPAGE2_CAP_FLAGS_RAID_64_BIT_ADDRESSING)
10520 +                ? 0xffffffffffffffffULL : 0x00000000ffffffffULL;
10521 +            karg.Information.uMaxPhysicalDrives = ioc->raid_data.pIocPg2->MaxPhysDisks;
10522 +            karg.Information.uMaxExtents = 1;
10523 +            karg.Information.uMaxModules = 0;
10524 +            karg.Information.uMaxTransformationMemory = 0;
10525 +            karg.Information.uChangeCount = ioc->csmi_change_count;
10526 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
10527 +               }
10528 +       }
10529 +
10530 +       /* Copy the data from kernel memory to user memory
10531 +        */
10532 +       if (copy_to_user((char *)arg, &karg,
10533 +                               sizeof(CSMI_SAS_RAID_INFO_BUFFER))) {
10534 +               printk(KERN_ERR "%s@%d::%s() - "
10535 +                       "Unable to write out csmi_sas_get_raid_info @ %p\n",
10536 +                               __FILE__, __LINE__, __FUNCTION__, uarg);
10537 +               return -EFAULT;
10538 +       }
10539 +
10540 +       return 0;
10541 +
10542 +}
10543 +
10544 +
10545 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
10546 +/*     mptscsih_do_raid - Format and Issue a RAID volume request message.
10547 + *     @ioc: Pointer to MPT_ADAPTER structure
10548 + *     @action: What do be done.
10549 + *     @PhysDiskNum: Logical target id.
10550 + *     @VolumeBus: Target locations bus.
10551 + *     @VolumeId: Volume id
10552 + *
10553 + *     Returns: < 0 on a fatal error
10554 + *             0 on success
10555 + *
10556 + *     Remark: Wait to return until reply processed by the ISR.
10557 + */
10558 +static int
10559 +mptctl_do_raid(MPT_ADAPTER *ioc, u8 action, u8 PhysDiskNum, u8 VolumeBus, u8 VolumeId, pMpiRaidActionReply_t reply)
10560 +{
10561 +       MpiRaidActionRequest_t  *pReq;
10562 +       MpiRaidActionReply_t    *pReply;
10563 +       MPT_FRAME_HDR           *mf;
10564 +       int ii;
10565 +
10566 +       /* Get and Populate a free Frame
10567 +        */
10568 +       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
10569 +               dctlprintk((": no msg frames!\n"));
10570 +               return -EAGAIN;
10571 +       }
10572 +       pReq = (MpiRaidActionRequest_t *)mf;
10573 +       pReq->Action = action;
10574 +       pReq->Reserved1 = 0;
10575 +       pReq->ChainOffset = 0;
10576 +       pReq->Function = MPI_FUNCTION_RAID_ACTION;
10577 +       pReq->VolumeID = VolumeId;
10578 +       pReq->VolumeBus = VolumeBus;
10579 +       pReq->PhysDiskNum = PhysDiskNum;
10580 +       pReq->MsgFlags = 0;
10581 +       pReq->Reserved2 = 0;
10582 +       pReq->ActionDataWord = 0; /* Reserved for this action */
10583 +       //pReq->ActionDataSGE = 0;
10584 +
10585 +       mpt_add_sge((char *)&pReq->ActionDataSGE,
10586 +               MPT_SGE_FLAGS_SSIMPLE_READ | 0, (dma_addr_t) -1);
10587 +
10588 +       ioc->ioctl->wait_done = 0;
10589 +       mpt_put_msg_frame(mptctl_id, ioc, mf);
10590 +
10591 +       /* Now wait for the command to complete */
10592 +       ii = wait_event_timeout(mptctl_wait,
10593 +            ioc->ioctl->wait_done == 1,
10594 +            HZ*MPT_IOCTL_DEFAULT_TIMEOUT /* 10 sec */);
10595 +
10596 +       if(ii <=0 && (ioc->ioctl->wait_done != 1 )) {
10597 +       /* Now we need to reset the board */
10598 +               mpt_free_msg_frame(ioc, mf);
10599 +               mptctl_timeout_expired(ioc->ioctl);
10600 +               return -ENODATA;
10601 +       }
10602 +
10603 +       if ((ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) &&
10604 +           (reply != NULL)){
10605 +               pReply = (MpiRaidActionReply_t *)&(ioc->ioctl->ReplyFrame);
10606 +               memcpy(reply, pReply,
10607 +                       min(ioc->reply_sz,
10608 +                       4*pReply->MsgLength));
10609 +       }
10610 +
10611 +       return 0;
10612 +}
10613 +
10614 +#ifdef QUIESE_IO
10615 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
10616 +/*     mptctl_raid_get_volume_id - figures out which Volume a PhysDisk belongs to.
10617 + *     @ioc: Pointer to MPT_ADAPTER structure
10618 + *     @PhysDiskNum: an unique number assigned by IOC to identify a specific IR phy disk
10619 + *
10620 + *     Returns: < 0 on a fatal error
10621 + *             0 on success
10622 + *
10623 + *     Following parameters are valid when successful return
10624 + *     @VolumeID - target device identification number of the volume
10625 + *     @VolumeBus - the SCSI bus number of the volume
10626 + *
10627 + */
10628 +static int
10629 +mptctl_raid_get_volume_id(MPT_ADAPTER *ioc, u8 PhysDiskNum, u8 *VolumeID, u8 *VolumeBus)
10630 +{
10631 +       CONFIGPARMS             cfg;
10632 +       ConfigPageHeader_t      header;
10633 +       dma_addr_t              volume0_dma;
10634 +       int                     i,j;
10635 +       int                     rc=0;
10636 +       int                     volumepage0sz = 0;
10637 +       pRaidVolumePage0_t      pVolume0 = NULL;
10638 +
10639 +       /*
10640 +        * get RAID Volume Page 0
10641 +        */
10642 +       header.PageVersion = 0;
10643 +       header.PageLength = 0;
10644 +       header.PageNumber = 0;
10645 +       header.PageType = MPI_CONFIG_PAGETYPE_RAID_VOLUME;
10646 +       cfg.cfghdr.hdr = &header;
10647 +       cfg.physAddr = -1;
10648 +       cfg.pageAddr = 0;
10649 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
10650 +       cfg.dir = 0;
10651 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
10652 +       if (mpt_config(ioc, &cfg) != 0) {
10653 +               rc = -1;
10654 +               goto mptctl_raid_get_volume_id_exit;
10655 +       }
10656 +
10657 +       if (header.PageLength == 0) {
10658 +               rc = -1;
10659 +               goto mptctl_raid_get_volume_id_exit;
10660 +       }
10661 +
10662 +       volumepage0sz = header.PageLength * 4;
10663 +       pVolume0 = pci_alloc_consistent(ioc->pcidev, volumepage0sz,
10664 +           &volume0_dma);
10665 +       if (!pVolume0) {
10666 +               rc = -1;
10667 +               goto mptctl_raid_get_volume_id_exit;
10668 +       }
10669 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
10670 +       cfg.physAddr = volume0_dma;
10671 +
10672 +       for (i=0; i<ioc->raid_data.pIocPg2->NumActiveVolumes; i++){
10673 +               *VolumeID = ioc->raid_data.pIocPg2->RaidVolume[i].VolumeID;
10674 +               *VolumeBus = ioc->raid_data.pIocPg2->RaidVolume[i].VolumeBus;
10675 +               cfg.pageAddr = (*VolumeBus << 8) + *VolumeID;
10676 +               if (mpt_config(ioc, &cfg) != 0){
10677 +                       rc = -1;
10678 +                       goto mptctl_raid_get_volume_id_exit;
10679 +               }
10680 +               for (j=0; j<pVolume0->NumPhysDisks; j++){
10681 +                       if (PhysDiskNum == pVolume0->PhysDisk[i].PhysDiskNum)
10682 +                               goto mptctl_raid_get_volume_id_exit;
10683 +               }
10684 +       }
10685 +
10686 +mptctl_raid_get_volume_id_exit:
10687 +
10688 +       if (pVolume0 != NULL)
10689 +               pci_free_consistent(ioc->pcidev, volumepage0sz, pVolume0,
10690 +                   volume0_dma);
10691 +
10692 +       return rc;
10693 +}
10694 +#endif
10695 +
10696 +
10697 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
10698 +/* mptctl_raid_inq
10699 + * @ioc = per host instance
10700 + * @opcode = MPI_FUNCTION_RAID_SCSI_IO_PASSTHROUGH or MPI_FUNCTION_SCSI_IO_REQUEST
10701 + * @target = target id
10702 + * @inq_vpd = inquiry data, returned
10703 + * @inq_vpd_sz = maximum size of inquiry data
10704 + *
10705 + * Return = 0(sucess), non-zero(failure)
10706 + */
10707 +static int
10708 +mptctl_raid_inq(MPT_ADAPTER *ioc, u8 opcode, u8 target, u8 inq_vpd_page, u8 * inq_vpd, u32 inq_vpd_sz)
10709 +{
10710 +       MPT_FRAME_HDR           *mf = NULL;
10711 +       MPIHeader_t             *mpi_hdr;
10712 +       pSCSIIORequest_t        pScsiRequest;
10713 +       u16                             req_idx;
10714 +       char                        *psge;
10715 +       u8                              inq_vpd_cdb[6];
10716 +       u8                              *request_data=NULL;
10717 +       dma_addr_t                  request_data_dma;
10718 +       u32                             request_data_sz;
10719 +       int                         rc=0,ii;
10720 +
10721 +       request_data_sz = 0xFFFF; /* max data size */
10722 +
10723 +    /* fill-in cdb */
10724 +    inq_vpd_cdb[0] = 0x12;
10725 +    if (inq_vpd_page) {
10726 +        inq_vpd_cdb[1] = 0x01; /* evpd bit */
10727 +        inq_vpd_cdb[2] = inq_vpd_page;
10728 +    }
10729 +    inq_vpd_cdb[3] = (u8)(request_data_sz >> 8);
10730 +    inq_vpd_cdb[4] = (u8)request_data_sz;
10731 +
10732 +       /* Get a free request frame and save the message context.
10733 +        */
10734 +       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
10735 +               dctlprintk((": no msg frames!\n"));
10736 +               goto mptctl_raid_inq_exit;
10737 +    }
10738 +
10739 +       mpi_hdr = (MPIHeader_t *) mf;
10740 +       pScsiRequest = (pSCSIIORequest_t) mf;
10741 +       req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
10742 +
10743 +       memset(pScsiRequest,0,sizeof(SCSIIORequest_t));
10744 +       pScsiRequest->Function = opcode;
10745 +       pScsiRequest->TargetID = target;
10746 +       pScsiRequest->Bus = 0;
10747 +       pScsiRequest->CDBLength = 6;
10748 +       pScsiRequest->DataLength = cpu_to_le16(request_data_sz);
10749 +       pScsiRequest->MsgContext = mpi_hdr->MsgContext;
10750 +       memcpy(pScsiRequest->CDB,inq_vpd_cdb,pScsiRequest->CDBLength);
10751 +       pScsiRequest->Control = cpu_to_le32(MPI_SCSIIO_CONTROL_READ);
10752 +       pScsiRequest->Control |= cpu_to_le32(MPI_SCSIIO_CONTROL_SIMPLEQ);
10753 +
10754 +       /* setup sense
10755 +        */
10756 +       pScsiRequest->SenseBufferLength = MPT_SENSE_BUFFER_SIZE;
10757 +       pScsiRequest->SenseBufferLowAddr = cpu_to_le32(ioc->sense_buf_low_dma +
10758 +           (req_idx * MPT_SENSE_BUFFER_ALLOC));
10759 +
10760 +       request_data = pci_alloc_consistent(
10761 +           ioc->pcidev, request_data_sz, &request_data_dma);
10762 +
10763 +       if (request_data == NULL) {
10764 +               mpt_free_msg_frame(ioc, mf);
10765 +               rc=-1;
10766 +               goto mptctl_raid_inq_exit;
10767 +       }
10768 +
10769 +       memset(request_data,0,request_data_sz);
10770 +       psge = (char *)&pScsiRequest->SGL;
10771 +       mpt_add_sge(psge, (MPT_SGE_FLAGS_SSIMPLE_READ | 0xFC) , request_data_dma);
10772 +
10773 +       /* The request is complete. Set the timer parameters
10774 +        * and issue the request.
10775 +        */
10776 +       ioc->ioctl->wait_done = 0;
10777 +       mpt_put_msg_frame(mptctl_id, ioc, mf);
10778 +
10779 +       /* Now wait for the command to complete */
10780 +       ii = wait_event_timeout(mptctl_wait,
10781 +            ioc->ioctl->wait_done == 1,
10782 +            HZ*MPT_IOCTL_DEFAULT_TIMEOUT /* 10 sec */);
10783 +
10784 +       if(ii <=0 && (ioc->ioctl->wait_done != 1 )) {
10785 +       /* Now we need to reset the board */
10786 +               rc=-1;
10787 +               mpt_free_msg_frame(ioc, mf);
10788 +               mptctl_timeout_expired(ioc->ioctl);
10789 +               goto mptctl_raid_inq_exit;
10790 +       }
10791 +
10792 +    /* copy the request_data */
10793 +    memcpy(inq_vpd,request_data,min(request_data_sz,inq_vpd_sz));
10794 +
10795 +mptctl_raid_inq_exit:
10796 +
10797 +       if (request_data)
10798 +               pci_free_consistent(ioc->pcidev, request_data_sz,
10799 +                   request_data, request_data_dma);
10800 +
10801 +    return rc;
10802 +}
10803 +
10804 +
10805 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
10806 +/* Prototype Routine for the CSMI SAS Get RAID Config command.
10807 + *
10808 + * Outputs:    None.
10809 + * Return:     0 if successful
10810 + *             -EFAULT if data unavailable
10811 + *             -ENODEV if no such device/adapter
10812 + */
10813 +static int
10814 +mptctl_csmi_sas_get_raid_config(unsigned long arg)
10815 +{
10816 +       CSMI_SAS_RAID_CONFIG_BUFFER __user *uarg = (void __user *) arg;
10817 +       CSMI_SAS_RAID_CONFIG_BUFFER      karg,*pKarg=NULL;
10818 +       CONFIGPARMS                     cfg;
10819 +       ConfigPageHeader_t              header;
10820 +       MPT_ADAPTER                     *ioc = NULL;
10821 +       int                             iocnum;
10822 +       u8                              volumeID, VolumeBus, physDiskNum, physDiskNumMax, found;
10823 +       int                             volumepage0sz = 0, physdiskpage0sz = 0, ioc_page5_sz = 0;
10824 +       dma_addr_t                      volume0_dma, physdisk0_dma, ioc_page5_dma;
10825 +       pRaidVolumePage0_t              pVolume0 = NULL;
10826 +       pRaidPhysDiskPage0_t            pPhysDisk0 = NULL;
10827 +       pMpiRaidActionReply_t           pRaidActionReply = NULL;
10828 +       pIOCPage5_t                     pIocPage5 = NULL;
10829 +       int                             i, idx, csmi_sas_raid_config_buffer_sz;
10830 +    int                 copy_buffer_sz=0;
10831 +       sas_device_info_t               *sasDevice;
10832 +       u32                             device_info=0;
10833 +
10834 +       dctlprintk((": %s called.\n",__FUNCTION__));
10835 +
10836 +       if (copy_from_user(&karg, uarg, sizeof(IOCTL_HEADER))) {
10837 +               printk(KERN_ERR "%s@%d::%s() - "
10838 +                   "Unable to read in csmi_sas_get_raid_config struct @ %p\n",
10839 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
10840 +               return -EFAULT;
10841 +       }
10842 +
10843 +       csmi_sas_raid_config_buffer_sz = karg.IoctlHeader.Length;
10844 +       pKarg = kmalloc(csmi_sas_raid_config_buffer_sz, GFP_KERNEL);
10845 +       if(!pKarg){
10846 +               printk(KERN_ERR "%s@%d::%s() - "
10847 +                   "Unable to malloc @ %p\n",
10848 +                   __FILE__, __LINE__, __FUNCTION__,pKarg);
10849 +               return -EFAULT;
10850 +       }
10851 +
10852 +       if (copy_from_user(pKarg, uarg, csmi_sas_raid_config_buffer_sz)) {
10853 +               printk(KERN_ERR "%s@%d::%s() - "
10854 +                   "Unable to read in csmi_sas_get_raid_config struct @ %p\n",
10855 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
10856 +               kfree(pKarg);
10857 +               return -EFAULT;
10858 +       }
10859 +
10860 +       if (((iocnum = mpt_verify_adapter(pKarg->IoctlHeader.IOControllerNumber,
10861 +           &ioc)) < 0) || (ioc == NULL)) {
10862 +               dctlprintk((KERN_ERR
10863 +               "%s::%s() @%d - ioc%d not found!\n",
10864 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
10865 +               kfree(pKarg);
10866 +               return -ENODEV;
10867 +       }
10868 +
10869 +       if (!mptctl_is_this_sas_cntr(ioc)) {
10870 +               dctlprintk((KERN_ERR
10871 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
10872 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
10873 +               kfree(pKarg);
10874 +               return -ENODEV;
10875 +       }
10876 +
10877 +       if (!ioc->raid_data.isRaid) {
10878 +               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10879 +               goto cim_get_raid_config_exit;
10880 +       }
10881 +
10882 +    if (pKarg->Configuration.uChangeCount != 0 &&
10883 +        pKarg->Configuration.uChangeCount != ioc->csmi_change_count ) {
10884 +        pKarg->IoctlHeader.ReturnCode = 
10885 +               CSMI_SAS_STATUS_INVALID_PARAMETER;
10886 +        //pKarg->Configuration.uFailureCode = 
10887 +           //  CSMI_SAS_FAIL_CODE_CHANGE_COUNT_INVALID;
10888 +        goto cim_get_raid_config_exit;
10889 +    }
10890 +
10891 +       /* check to see if the input uRaidSetIndex is greater than the number of RAID sets */
10892 +       if(pKarg->Configuration.uRaidSetIndex >=
10893 +           ioc->raid_data.pIocPg2->NumActiveVolumes) {
10894 +               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_RAID_SET_OUT_OF_RANGE;
10895 +               goto cim_get_raid_config_exit;
10896 +       }
10897 +
10898 +       /*
10899 +        * get RAID Volume Page 0
10900 +        */
10901 +       volumeID = ioc->raid_data.pIocPg2->RaidVolume[pKarg->Configuration.uRaidSetIndex].VolumeID;
10902 +       VolumeBus = ioc->raid_data.pIocPg2->RaidVolume[pKarg->Configuration.uRaidSetIndex].VolumeBus;
10903 +
10904 +       header.PageVersion = 0;
10905 +       header.PageLength = 0;
10906 +       header.PageNumber = 0;
10907 +       header.PageType = MPI_CONFIG_PAGETYPE_RAID_VOLUME;
10908 +       cfg.cfghdr.hdr = &header;
10909 +       cfg.physAddr = -1;
10910 +       cfg.pageAddr = (VolumeBus << 8) + volumeID;
10911 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
10912 +       cfg.dir = 0;
10913 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
10914 +       if (mpt_config(ioc, &cfg) != 0) {
10915 +               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10916 +               goto cim_get_raid_config_exit;
10917 +       }
10918 +
10919 +       if (header.PageLength == 0) {
10920 +               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10921 +               goto cim_get_raid_config_exit;
10922 +       }
10923 +
10924 +       volumepage0sz = header.PageLength * 4;
10925 +       pVolume0 = pci_alloc_consistent(ioc->pcidev, volumepage0sz,
10926 +           &volume0_dma);
10927 +       if (!pVolume0) {
10928 +               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10929 +               goto cim_get_raid_config_exit;
10930 +       }
10931 +
10932 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
10933 +       cfg.physAddr = volume0_dma;
10934 +       if (mpt_config(ioc, &cfg) != 0){
10935 +               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
10936 +               goto cim_get_raid_config_exit;
10937 +       }
10938 +
10939 +       pKarg->Configuration.uCapacity =
10940 +               (le32_to_cpu(pVolume0->MaxLBA)+1)/2048;
10941 +       pKarg->Configuration.uStripeSize =
10942 +               le32_to_cpu(pVolume0->StripeSize)/2;
10943 +
10944 +       switch(pVolume0->VolumeType) {
10945 +       case MPI_RAID_VOL_TYPE_IS:
10946 +               pKarg->Configuration.bRaidType = CSMI_SAS_RAID_TYPE_0;
10947 +               break;
10948 +       case MPI_RAID_VOL_TYPE_IME:
10949 +               pKarg->Configuration.bRaidType = CSMI_SAS_RAID_TYPE_10;
10950 +               break;
10951 +       case MPI_RAID_VOL_TYPE_IM:
10952 +               pKarg->Configuration.bRaidType = CSMI_SAS_RAID_TYPE_1;
10953 +               break;
10954 +       default:
10955 +               pKarg->Configuration.bRaidType = CSMI_SAS_RAID_TYPE_OTHER;
10956 +               break;
10957 +       }
10958 +
10959 +    switch (pVolume0->VolumeStatus.State) {
10960 +       case MPI_RAIDVOL0_STATUS_STATE_OPTIMAL:
10961 +               pKarg->Configuration.bStatus = CSMI_SAS_RAID_SET_STATUS_OK;
10962 +               break;
10963 +    case MPI_RAIDVOL0_STATUS_STATE_DEGRADED:
10964 +        /* Volume is degraded, check if Resyncing or Inactive */
10965 +        if (pVolume0->VolumeStatus.State & 
10966 +            MPI_RAIDVOL0_STATUS_FLAG_RESYNC_IN_PROGRESS) {
10967 +            pKarg->Configuration.bStatus = CSMI_SAS_RAID_SET_STATUS_REBUILDING;
10968 +        }
10969 +        else if (pVolume0->VolumeStatus.State & 
10970 +                 MPI_RAIDVOL0_STATUS_FLAG_VOLUME_INACTIVE) {
10971 +            pKarg->Configuration.bStatus = CSMI_SAS_RAID_SET_STATUS_OFFLINE;
10972 +        }
10973 +        else {
10974 +            pKarg->Configuration.bStatus = CSMI_SAS_RAID_SET_STATUS_DEGRADED;
10975 +        }
10976 +               break;
10977 +       case MPI_RAIDVOL0_STATUS_STATE_FAILED:
10978 +               pKarg->Configuration.bStatus = CSMI_SAS_RAID_SET_STATUS_FAILED;
10979 +               break;
10980 +       }
10981 +
10982 +    pKarg->Configuration.bInformation = 0;  /* default */
10983 +       if(pVolume0->VolumeStatus.Flags &
10984 +           MPI_RAIDVOL0_STATUS_FLAG_RESYNC_IN_PROGRESS ) {
10985 +
10986 +               uint64_t        * ptrUint64;
10987 +               uint64_t        totalBlocks64, blocksRemaining64;
10988 +               uint32_t        totalBlocks32, blocksRemaining32;
10989 +
10990 +               /* get percentage complete */
10991 +               pRaidActionReply = kmalloc( sizeof(MPI_RAID_VOL_INDICATOR) +
10992 +                   offsetof(MSG_RAID_ACTION_REPLY,ActionData),
10993 +                   GFP_KERNEL);
10994 +
10995 +               if(pRaidActionReply == NULL){
10996 +                       printk(KERN_ERR "%s@%d::%s() - "
10997 +                           "Unable to malloc @ %p\n",
10998 +                           __FILE__, __LINE__, __FUNCTION__,pKarg);
10999 +                       goto cim_get_raid_config_exit;
11000 +               }
11001 +
11002 +               mptctl_do_raid(ioc,
11003 +                   MPI_RAID_ACTION_INDICATOR_STRUCT,
11004 +                   0, VolumeBus, volumeID, pRaidActionReply);
11005 +
11006 +               ptrUint64       = (uint64_t *)&pRaidActionReply->ActionData;
11007 +               totalBlocks64     = *ptrUint64;
11008 +               ptrUint64++;
11009 +               blocksRemaining64 = *ptrUint64;
11010 +               while(totalBlocks64 > 0xFFFFFFFFUL){
11011 +                       totalBlocks64 = totalBlocks64 >> 1;
11012 +                       blocksRemaining64 = blocksRemaining64 >> 1;
11013 +               }
11014 +               totalBlocks32 = (uint32_t)totalBlocks64;
11015 +               blocksRemaining32 = (uint32_t)blocksRemaining64;
11016 +
11017 +               if(totalBlocks32)
11018 +                       pKarg->Configuration.bInformation =
11019 +                           (totalBlocks32 - blocksRemaining32) /
11020 +                           (totalBlocks32 / 100);
11021 +
11022 +               kfree(pRaidActionReply);
11023 +       }
11024 +
11025 +    /* fill-in more information depending on data type */
11026 +    if (pKarg->Configuration.bDataType == CSMI_SAS_RAID_DATA_ADDITIONAL_DATA) {
11027 +        pKarg->Configuration.Data->bLabel[0] = '\0';
11028 +        pKarg->Configuration.Data->bRaidSetLun[1] = 0;
11029 +        pKarg->Configuration.Data->bWriteProtection = 
11030 +            CSMI_SAS_RAID_SET_WRITE_PROTECT_UNKNOWN;
11031 +        pKarg->Configuration.Data->bCacheSetting = 
11032 +            CSMI_SAS_RAID_SET_CACHE_UNKNOWN;
11033 +        pKarg->Configuration.Data->bCacheRatio = 0;
11034 +        pKarg->Configuration.Data->usBlockSize = 512;
11035 +        pKarg->Configuration.Data->ulRaidSetExtentOffset = 0;
11036 +        pKarg->Configuration.Data->ulRaidSetBlocks = le32_to_cpu(pVolume0->MaxLBA);
11037 +        if (pVolume0->VolumeType == MPI_RAID_VOL_TYPE_IS ||
11038 +            pVolume0->VolumeType == MPI_RAID_VOL_TYPE_IME ) {
11039 +            pKarg->Configuration.Data->uStripeSizeInBlocks = 
11040 +                le32_to_cpu(pVolume0->StripeSize);
11041 +        }
11042 +        else {
11043 +            pKarg->Configuration.Data->uStripeSizeInBlocks = 0;
11044 +        }
11045 +        pKarg->Configuration.Data->uSectorsPerTrack = 128;
11046 +        for (i=0; i<16; i++) {
11047 +            // unsupported
11048 +            pKarg->Configuration.Data->bApplicationScratchPad[i] = 0xFF;
11049 +        }
11050 +    }
11051 +    else if( pKarg->Configuration.bDataType == CSMI_SAS_RAID_DATA_DEVICE_ID ) {
11052 +        /* Send inquiry to get VPD Page 0x83 */
11053 +        u8 * vpd_page=NULL;
11054 +        u32 vpd_page_sz;
11055 +        vpd_page_sz = pKarg->IoctlHeader.Length - sizeof(CSMI_SAS_RAID_CONFIG);
11056 +               vpd_page = kmalloc(vpd_page_sz, GFP_KERNEL);
11057 +        if (mptctl_raid_inq(ioc, MPI_FUNCTION_SCSI_IO_REQUEST, volumeID, 0x83, vpd_page, vpd_page_sz) != 0) {
11058 +            pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
11059 +                       kfree(vpd_page);
11060 +            goto cim_get_raid_config_exit;
11061 +        }
11062 +        memset(&pKarg->Configuration.DeviceId->bDeviceIdentificationVPDPage,
11063 +               0,vpd_page_sz);
11064 +        memcpy(&pKarg->Configuration.DeviceId->bDeviceIdentificationVPDPage, 
11065 +               vpd_page,vpd_page_sz);
11066 +               kfree(vpd_page);
11067 +    }
11068 +
11069 +    if (pKarg->Configuration.bDataType != CSMI_SAS_RAID_DATA_DRIVES) {
11070 +        pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
11071 +        goto cim_get_raid_config_exit;
11072 +    }
11073 +
11074 +    /* suppress drive information */
11075 +    if (pKarg->Configuration.bDriveCount == 
11076 +        CSMI_SAS_RAID_DRIVE_COUNT_SUPRESSED) {
11077 +            pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
11078 +            goto cim_get_raid_config_exit;
11079 +    }
11080 +
11081 +       /* get hotspare info, used later in this function */
11082 +       if (pVolume0->VolumeSettings.HotSparePool) {
11083 +               /* Read and save IOC Page 5
11084 +                */
11085 +               header.PageVersion = 0;
11086 +               header.PageLength = 0;
11087 +               header.PageNumber = 5;
11088 +               header.PageType = MPI_CONFIG_PAGETYPE_IOC;
11089 +               cfg.cfghdr.hdr = &header;
11090 +               cfg.physAddr = -1;
11091 +               cfg.pageAddr = 0;
11092 +               cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
11093 +               cfg.dir = 0;
11094 +               cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
11095 +               if ((mpt_config(ioc, &cfg)==0) && (header.PageLength)) {
11096 +                       ioc_page5_sz = header.PageLength * 4;
11097 +                       pIocPage5 = pci_alloc_consistent(ioc->pcidev,
11098 +                           ioc_page5_sz,
11099 +                           &ioc_page5_dma);
11100 +                       memset(pIocPage5,0,ioc_page5_sz);
11101 +                       if (ioc_page5_dma) {
11102 +                               cfg.physAddr = ioc_page5_dma;
11103 +                               cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
11104 +                               mpt_config(ioc, &cfg);
11105 +                       }
11106 +               }
11107 +       }
11108 +
11109 +       /*
11110 +        * get RAID Physical Disk Page 0
11111 +        */
11112 +       header.PageVersion = 0;
11113 +       header.PageLength = 0;
11114 +       header.PageNumber = 0;
11115 +       header.PageType = MPI_CONFIG_PAGETYPE_RAID_PHYSDISK;
11116 +       cfg.cfghdr.hdr = &header;
11117 +       cfg.physAddr = -1;
11118 +       cfg.pageAddr = 0;
11119 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
11120 +       cfg.dir = 0;
11121 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
11122 +       if (mpt_config(ioc, &cfg) != 0) {
11123 +               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
11124 +               goto cim_get_raid_config_exit;
11125 +       }
11126 +
11127 +       if (header.PageLength == 0) {
11128 +               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
11129 +               goto cim_get_raid_config_exit;
11130 +       }
11131 +
11132 +       physdiskpage0sz = header.PageLength * 4;
11133 +       pPhysDisk0 = pci_alloc_consistent(ioc->pcidev, physdiskpage0sz,
11134 +           &physdisk0_dma);
11135 +       if (!pPhysDisk0) {
11136 +               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
11137 +               goto cim_get_raid_config_exit;
11138 +       }
11139 +       cfg.physAddr = physdisk0_dma;
11140 +
11141 +       physDiskNumMax = (csmi_sas_raid_config_buffer_sz -
11142 +           offsetof(CSMI_SAS_RAID_CONFIG,Drives))
11143 +           / sizeof(CSMI_SAS_RAID_DRIVES);
11144 +
11145 +       pKarg->Configuration.bDriveCount=0;
11146 +
11147 +       for (i=0; i< min(pVolume0->NumPhysDisks, physDiskNumMax); i++) {
11148 +
11149 +               physDiskNum = pVolume0->PhysDisk[i].PhysDiskNum;
11150 +               cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
11151 +               cfg.pageAddr = physDiskNum;
11152 +               if (mpt_config(ioc, &cfg) != 0){
11153 +                       pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
11154 +                       goto cim_get_raid_config_exit;
11155 +               }
11156 +               memset(&pKarg->Configuration.Drives[i],0,
11157 +                   sizeof(CSMI_SAS_RAID_DRIVES));
11158 +               memcpy(pKarg->Configuration.Drives[i].bModel,
11159 +                   pPhysDisk0->InquiryData.VendorID,
11160 +                   offsetof(RAID_PHYS_DISK0_INQUIRY_DATA,ProductRevLevel));
11161 +               memcpy(pKarg->Configuration.Drives[i].bFirmware,
11162 +                       pPhysDisk0->InquiryData.ProductRevLevel,
11163 +                       sizeof(pPhysDisk0->InquiryData.ProductRevLevel));
11164 +               if ((pPhysDisk0->ExtDiskIdentifier[0] == 'A') &&
11165 +                   (pPhysDisk0->ExtDiskIdentifier[1] == 'T') &&
11166 +                   (pPhysDisk0->ExtDiskIdentifier[2] == 'A')) {
11167 +                       memcpy(&pKarg->Configuration.Drives[i].bSerialNumber,
11168 +                               &pPhysDisk0->ExtDiskIdentifier[4],
11169 +                               4);
11170 +                       memcpy(&pKarg->Configuration.Drives[i].bSerialNumber[4],
11171 +                               &pPhysDisk0->DiskIdentifier,
11172 +                               sizeof(pPhysDisk0->DiskIdentifier));
11173 +               } else {
11174 +                       memcpy(pKarg->Configuration.Drives[i].bSerialNumber,
11175 +                               pPhysDisk0->DiskIdentifier,
11176 +                               sizeof(pPhysDisk0->DiskIdentifier));
11177 +               }
11178 +
11179 +               pKarg->Configuration.Drives[i].bDriveUsage =
11180 +                   (pPhysDisk0->PhysDiskStatus.Flags &
11181 +                   MPI_PHYSDISK0_STATUS_FLAG_INACTIVE_VOLUME) ?
11182 +                   CSMI_SAS_DRIVE_CONFIG_NOT_USED :
11183 +                   CSMI_SAS_DRIVE_CONFIG_MEMBER;
11184 +
11185 +               pKarg->Configuration.Drives[i].bDriveStatus =
11186 +                   CSMI_SAS_DRIVE_STATUS_OK;
11187 +        if (pPhysDisk0->PhysDiskStatus.State == 
11188 +            MPI_PHYSDISK0_STATUS_OFFLINE_REQUESTED) {
11189 +            pKarg->Configuration.Drives[i].bDriveStatus = 
11190 +                CSMI_SAS_DRIVE_STATUS_OFFLINE;
11191 +        }
11192 +        else if(pPhysDisk0->PhysDiskStatus.State) {
11193 +                       pKarg->Configuration.Drives[i].bDriveStatus =
11194 +                           CSMI_SAS_DRIVE_STATUS_FAILED;
11195 +                       if(pKarg->Configuration.bStatus ==
11196 +                           CSMI_SAS_RAID_SET_STATUS_DEGRADED)
11197 +                               pKarg->Configuration.bInformation = i;
11198 +               }
11199 +               else if((pVolume0->VolumeStatus.Flags &
11200 +                   MPI_RAIDVOL0_STATUS_FLAG_RESYNC_IN_PROGRESS) &&
11201 +                   (pPhysDisk0->PhysDiskStatus.Flags &
11202 +                   MPI_PHYSDISK0_STATUS_FLAG_OUT_OF_SYNC))
11203 +                       pKarg->Configuration.Drives[i].bDriveStatus =
11204 +                           CSMI_SAS_DRIVE_STATUS_REBUILDING;
11205 +               else if(pPhysDisk0->ErrorData.SmartCount)
11206 +                       pKarg->Configuration.Drives[i].bDriveStatus =
11207 +                       CSMI_SAS_DRIVE_STATUS_DEGRADED;
11208 +
11209 +               /* Search the list for the matching SAS address. */
11210 +               found = FALSE;
11211 +               list_for_each_entry(sasDevice, &ioc->sasDeviceList, list) {
11212 +
11213 +                       /* Found the matching device. */
11214 +                       if ((pPhysDisk0->PhysDiskIOC == sasDevice->Bus) &&
11215 +                               (pPhysDisk0->PhysDiskID ==
11216 +                                sasDevice->TargetId)) {
11217 +                               u64 SASAddress64;
11218 +                               found = TRUE;
11219 +
11220 +                               SASAddress64 =
11221 +                                   reverse_byte_order64(&sasDevice->SASAddress);
11222 +                               memcpy(pKarg->Configuration.Drives[i].bSASAddress,
11223 +                                  &SASAddress64,sizeof(u64));
11224 +                               memset(pKarg->Configuration.Drives[i].bSASLun,
11225 +                                   0, sizeof(pKarg->Configuration.Drives[i].bSASLun));
11226 +                               device_info = sasDevice->DeviceInfo;
11227 +                if (device_info & MPI_SAS_DEVICE_INFO_SATA_DEVICE) {
11228 +                    pKarg->Configuration.Drives[i].bDriveType = 
11229 +                        CSMI_SAS_DRIVE_TYPE_SATA;
11230 +                }
11231 +                else { /* drive in a volume can only be SAS/SATA */
11232 +                    pKarg->Configuration.Drives[i].bDriveType = 
11233 +                        CSMI_SAS_DRIVE_TYPE_SINGLE_PORT_SAS;
11234 +                }
11235 +                               break;
11236 +                       } else
11237 +                               continue; /* Keep looking. */
11238 +               }
11239 +        pKarg->Configuration.Drives[i].usBlockSize = 512;
11240 +               pKarg->Configuration.Drives[i].uDriveIndex = pPhysDisk0->PhysDiskNum;
11241 +        if (pVolume0->VolumeType == MPI_RAID_VOL_TYPE_IM) {
11242 +            pKarg->Configuration.Drives[i].ulTotalUserBlocks = 
11243 +                le32_to_cpu(pVolume0->MaxLBA) + 1;
11244 +        }
11245 +        else if (pVolume0->VolumeType == MPI_RAID_VOL_TYPE_IS) {
11246 +            pKarg->Configuration.Drives[i].ulTotalUserBlocks = 
11247 +                (le32_to_cpu(pVolume0->MaxLBA) + 1) / (pVolume0->NumPhysDisks);
11248 +        }
11249 +        else if (pVolume0->VolumeType == MPI_RAID_VOL_TYPE_IME) {
11250 +            pKarg->Configuration.Drives[i].ulTotalUserBlocks = 
11251 +                ((le32_to_cpu(pVolume0->MaxLBA) + 1) / (pVolume0->NumPhysDisks)) * 2;
11252 +        }
11253 +        pKarg->Configuration.bDriveCount++;
11254 +       }
11255 +
11256 +       /* adding hot spare info at the end */
11257 +       if ((pVolume0->VolumeSettings.HotSparePool) && (pIocPage5 != NULL)) {
11258 +               for (idx = 0, i = pVolume0->NumPhysDisks ;
11259 +                   idx < pIocPage5->NumHotSpares ; idx++) {
11260 +                       if (i >= physDiskNumMax)
11261 +                               break;
11262 +                       if ((pVolume0->VolumeSettings.HotSparePool &
11263 +                           pIocPage5->HotSpare[idx].HotSparePool) == 0)
11264 +                               continue;
11265 +                       if(pIocPage5->HotSpare[idx].Flags !=
11266 +                           MPI_IOC_PAGE_5_HOT_SPARE_ACTIVE)
11267 +                           continue;
11268 +                       physDiskNum = pIocPage5->HotSpare[idx].PhysDiskNum;
11269 +                       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
11270 +                       cfg.pageAddr = physDiskNum;
11271 +                       if (mpt_config(ioc, &cfg) != 0)
11272 +                               continue;
11273 +                       /* Search the list for the matching SAS address. */
11274 +                       found = FALSE;
11275 +                       list_for_each_entry(sasDevice, &ioc->sasDeviceList,
11276 +                           list) {
11277 +                               /* Found the matching device. */
11278 +                               if ((pPhysDisk0->PhysDiskIOC ==
11279 +                                       sasDevice->Bus) &&
11280 +                                       (pPhysDisk0->PhysDiskID ==
11281 +                                        sasDevice->TargetId)) {
11282 +                                       u64 SASAddress64;
11283 +
11284 +                                       /* sanity checks */
11285 +
11286 +                                       /* don't mix SSP hot spare
11287 +                                        * in SATA volume
11288 +                                        */
11289 +                                       if ((sasDevice->DeviceInfo &
11290 +                                           MPI_SAS_DEVICE_INFO_SSP_TARGET) &&
11291 +                                           (device_info &
11292 +                                           MPI_SAS_DEVICE_INFO_SATA_DEVICE))
11293 +                                               break;
11294 +
11295 +                                       /* don't mix SATA hot spare
11296 +                                        * in SSP volume
11297 +                                        */
11298 +                                       if ((sasDevice->DeviceInfo &
11299 +                                           MPI_SAS_DEVICE_INFO_SATA_DEVICE) &&
11300 +                                           (device_info &
11301 +                                           MPI_SAS_DEVICE_INFO_SSP_TARGET))
11302 +                                               break;
11303 +
11304 +                                       /* capacity check for IM volumes*/
11305 +                                       if ((pVolume0->VolumeType ==
11306 +                                               MPI_RAID_VOL_TYPE_IM) &&
11307 +                                           (le32_to_cpu(pVolume0->MaxLBA) +
11308 +                                            (64*2*1024) /* metadata = 64MB*/ >
11309 +                                           le32_to_cpu(pPhysDisk0->MaxLBA)))
11310 +                                               break;
11311 +
11312 +                                       /* capacity check for IME volumes*/
11313 +                                       if ((pVolume0->VolumeType ==
11314 +                                               MPI_RAID_VOL_TYPE_IME) &&
11315 +                                           (((le32_to_cpu(pVolume0->MaxLBA)/
11316 +                                             pVolume0->NumPhysDisks) * 2) +
11317 +                                            (64*2*1024 ) /*metadata = 64MB*/ >
11318 +                                           le32_to_cpu(pPhysDisk0->MaxLBA)))
11319 +                                               break;
11320 +
11321 +                                       found = TRUE;
11322 +
11323 +                                       SASAddress64 =
11324 +                                           reverse_byte_order64(&sasDevice->SASAddress);
11325 +                                       memcpy(pKarg->Configuration.Drives[i].bSASAddress,
11326 +                                          &SASAddress64,sizeof(u64));
11327 +                                       memset(pKarg->Configuration.Drives[i].bSASLun, 0,
11328 +                                            sizeof(pKarg->Configuration.Drives[i].bSASLun));
11329 +                                       break;
11330 +                               } else
11331 +                                       continue; /* Keep looking. */
11332 +                       }
11333 +                       if (found==FALSE)
11334 +                               continue;
11335 +                       memset(&pKarg->Configuration.Drives[i],0,
11336 +                           sizeof(CSMI_SAS_RAID_DRIVES));
11337 +                       memcpy(pKarg->Configuration.Drives[i].bModel,
11338 +                           pPhysDisk0->InquiryData.VendorID,
11339 +                           offsetof(RAID_PHYS_DISK0_INQUIRY_DATA,ProductRevLevel));
11340 +                       memcpy(pKarg->Configuration.Drives[i].bFirmware,
11341 +                               pPhysDisk0->InquiryData.ProductRevLevel,
11342 +                               sizeof(pPhysDisk0->InquiryData.ProductRevLevel));
11343 +                       if ((pPhysDisk0->ExtDiskIdentifier[0] == 'A') &&
11344 +                           (pPhysDisk0->ExtDiskIdentifier[1] == 'T') &&
11345 +                           (pPhysDisk0->ExtDiskIdentifier[2] == 'A')) {
11346 +                               memcpy(&pKarg->Configuration.Drives[i].bSerialNumber,
11347 +                                       &pPhysDisk0->ExtDiskIdentifier[4],
11348 +                                       4);
11349 +                               memcpy(&pKarg->Configuration.Drives[i].bSerialNumber[4],
11350 +                                       &pPhysDisk0->DiskIdentifier,
11351 +                                       sizeof(pPhysDisk0->DiskIdentifier));
11352 +                       } else {
11353 +                               memcpy(pKarg->Configuration.Drives[i].bSerialNumber,
11354 +                                       pPhysDisk0->DiskIdentifier,
11355 +                                       sizeof(pPhysDisk0->DiskIdentifier));
11356 +                       }
11357 +                       pKarg->Configuration.Drives[i].bDriveStatus =
11358 +                           CSMI_SAS_DRIVE_STATUS_OK;
11359 +                       if(pPhysDisk0->PhysDiskStatus.State)
11360 +                               pKarg->Configuration.Drives[i].bDriveStatus =
11361 +                                   CSMI_SAS_DRIVE_STATUS_FAILED;
11362 +                       else if(pPhysDisk0->ErrorData.SmartCount)
11363 +                               pKarg->Configuration.Drives[i].bDriveStatus =
11364 +                                   CSMI_SAS_DRIVE_STATUS_DEGRADED;
11365 +                       pKarg->Configuration.Drives[i].bDriveUsage =
11366 +                           CSMI_SAS_DRIVE_CONFIG_SPARE;
11367 +                       i++;
11368 +                       pKarg->Configuration.bDriveCount++;
11369 +               }
11370 +       }
11371 +
11372 +    // Only return data on the first 240 drives
11373 +    if( pKarg->Configuration.bDriveCount > 0xF0 ) {
11374 +        pKarg->Configuration.bDriveCount = 
11375 +            CSMI_SAS_RAID_DRIVE_COUNT_TOO_BIG;
11376 +    }
11377 +
11378 +       pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
11379 +
11380 +cim_get_raid_config_exit:
11381 +
11382 +       if (pVolume0 != NULL)
11383 +               pci_free_consistent(ioc->pcidev, volumepage0sz, pVolume0,
11384 +                   volume0_dma);
11385 +
11386 +       if(pPhysDisk0 != NULL)
11387 +               pci_free_consistent(ioc->pcidev, physdiskpage0sz, pPhysDisk0,
11388 +                   physdisk0_dma);
11389 +
11390 +       if(pIocPage5 != NULL)
11391 +               pci_free_consistent(ioc->pcidev, ioc_page5_sz, pIocPage5,
11392 +                   ioc_page5_dma);
11393 +
11394 +       /* Copy the data from kernel memory to user memory
11395 +        */
11396 +
11397 +    /* find the buffer size to copy depending on how much is filled-in */
11398 +    switch (pKarg->Configuration.bDataType) {
11399 +    case CSMI_SAS_RAID_DATA_ADDITIONAL_DATA:
11400 +        copy_buffer_sz = sizeof(IOCTL_HEADER) +
11401 +            offsetof(CSMI_SAS_RAID_CONFIG,Data) +
11402 +            sizeof(CSMI_SAS_RAID_SET_ADDITIONAL_DATA);
11403 +        break;
11404 +    case CSMI_SAS_RAID_DATA_DRIVES:
11405 +        if (pKarg->Configuration.bDriveCount == 
11406 +            CSMI_SAS_RAID_DRIVE_COUNT_SUPRESSED) {
11407 +            copy_buffer_sz = sizeof(IOCTL_HEADER) +
11408 +                offsetof(CSMI_SAS_RAID_CONFIG,Drives);
11409 +        }
11410 +        else {
11411 +            copy_buffer_sz = sizeof(IOCTL_HEADER) +
11412 +                offsetof(CSMI_SAS_RAID_CONFIG,Drives) +
11413 +                (pKarg->Configuration.bDriveCount * sizeof(CSMI_SAS_RAID_DRIVES));
11414 +        }
11415 +        break;
11416 +    case CSMI_SAS_RAID_DATA_DEVICE_ID:
11417 +        copy_buffer_sz = sizeof(IOCTL_HEADER) +
11418 +            offsetof(CSMI_SAS_RAID_CONFIG,DeviceId) +
11419 +            sizeof(CSMI_SAS_RAID_DEVICE_ID);
11420 +        break;
11421 +    }
11422 +
11423 +    if (copy_to_user((char *)arg, pKarg, copy_buffer_sz)) {
11424 +               printk(KERN_ERR "%s@%d::%s() - "
11425 +                      "Unable to write out csmi_sas_get_raid_config @ %p\n",
11426 +                          __FILE__, __LINE__, __FUNCTION__, uarg);
11427 +               kfree(pKarg);
11428 +               return -EFAULT;
11429 +    }
11430 +
11431 +    kfree(pKarg);
11432 +
11433 +       return 0;
11434 +}
11435 +
11436 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
11437 +/* Prototype Routine for the CSMI SAS Get RAID Features command.
11438 + *
11439 + * Outputs:    None.
11440 + * Return:     0 if successful
11441 + *             -EFAULT if data unavailable
11442 + *             -ENODEV if no such device/adapter
11443 + */
11444 +static int
11445 +mptctl_csmi_sas_get_raid_features(unsigned long arg)
11446 +{
11447 +       CSMI_SAS_RAID_FEATURES_BUFFER __user *uarg = (void __user *) arg;
11448 +       CSMI_SAS_RAID_FEATURES_BUFFER karg, *pKarg=NULL;
11449 +       int i, csmi_sas_raid_features_buffer_sz, iocnum;
11450 +    MPT_ADAPTER                        *ioc = NULL;
11451 +
11452 +    u8 raidTypes[4] = { CSMI_SAS_RAID_TYPE_0, CSMI_SAS_RAID_TYPE_10,
11453 +                        CSMI_SAS_RAID_TYPE_1, CSMI_SAS_RAID_TYPE_1E };
11454 +
11455 +       dctlprintk((": %s called.\n",__FUNCTION__));
11456 +
11457 +       if (copy_from_user(&karg, uarg, sizeof(IOCTL_HEADER))) {
11458 +               printk(KERN_ERR "%s@%d::%s() - "
11459 +                   "Unable to read in csmi_sas_get_raid_features struct @ %p\n",
11460 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
11461 +               return -EFAULT;
11462 +       }
11463 +
11464 +       csmi_sas_raid_features_buffer_sz = karg.IoctlHeader.Length;
11465 +       pKarg = kmalloc(csmi_sas_raid_features_buffer_sz, GFP_KERNEL);
11466 +       if(!pKarg){
11467 +               printk(KERN_ERR "%s@%d::%s() - "
11468 +                   "Unable to malloc @ %p\n",
11469 +                   __FILE__, __LINE__, __FUNCTION__,pKarg);
11470 +               return -EFAULT;
11471 +       }
11472 +
11473 +       if (copy_from_user(pKarg, uarg, csmi_sas_raid_features_buffer_sz)) {
11474 +               printk(KERN_ERR "%s@%d::%s() - "
11475 +                   "Unable to read in csmi_sas_get_raid_features struct @ %p\n",
11476 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
11477 +               kfree(pKarg);
11478 +               return -EFAULT;
11479 +       }
11480 +
11481 +       if (((iocnum = mpt_verify_adapter(pKarg->IoctlHeader.IOControllerNumber,
11482 +           &ioc)) < 0) || (ioc == NULL)) {
11483 +               dctlprintk((KERN_ERR
11484 +               "%s::%s() @%d - ioc%d not found!\n",
11485 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
11486 +               kfree(pKarg);
11487 +               return -ENODEV;
11488 +       }
11489 +
11490 +       if (!mptctl_is_this_sas_cntr(ioc)) {
11491 +               dctlprintk((KERN_ERR
11492 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
11493 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
11494 +               kfree(pKarg);
11495 +               return -ENODEV;
11496 +       }
11497 +
11498 +    if (pKarg->Information.uChangeCount != 0 &&
11499 +        pKarg->Information.uChangeCount != ioc->csmi_change_count ) {
11500 +        pKarg->IoctlHeader.ReturnCode = 
11501 +                       CSMI_SAS_STATUS_INVALID_PARAMETER;
11502 +        //pKarg->Information.uFailureCode = 
11503 +               //      CSMI_SAS_FAIL_CODE_CHANGE_COUNT_INVALID;
11504 +        goto cim_get_raid_features_exit;
11505 +    }
11506 +
11507 +    pKarg->Information.uFeatures = CSMI_SAS_RAID_FEATURE_REBUILD;
11508 +    pKarg->Information.bDefaultTransformPriority = CSMI_SAS_PRIORITY_UNKNOWN;
11509 +    pKarg->Information.bTransformPriority = CSMI_SAS_PRIORITY_UNKNOWN;
11510 +    pKarg->Information.bDefaultRebuildPriority = CSMI_SAS_PRIORITY_UNKNOWN;
11511 +    pKarg->Information.bRebuildPriority = pKarg->Information.bDefaultRebuildPriority;
11512 +    pKarg->Information.bDefaultSurfaceScanPriority = CSMI_SAS_PRIORITY_UNKNOWN;
11513 +    pKarg->Information.bSurfaceScanPriority = CSMI_SAS_PRIORITY_UNKNOWN;
11514 +    pKarg->Information.uRaidSetTransformationRules = 0;
11515 +    for (i=0; i<4; i++) {
11516 +        pKarg->Information.RaidType[i].bRaidType = raidTypes[i];
11517 +        // Only support 64K stripe size
11518 +        pKarg->Information.RaidType[i].uSupportedStripeSizeMap = 0x80;
11519 +    }
11520 +    pKarg->Information.RaidType[i].bRaidType = CSMI_SAS_RAID_TYPE_END;
11521 +    pKarg->Information.bCacheRatiosSupported[0] = CSMI_SAS_RAID_CACHE_RATIO_END;
11522 +
11523 +cim_get_raid_features_exit:
11524 +
11525 +    /*
11526 +     * Copy the data from kernel memory to user memory
11527 +     */
11528 +    if (copy_to_user((char *)arg, pKarg,
11529 +        sizeof(CSMI_SAS_RAID_FEATURES_BUFFER))) {
11530 +        printk(KERN_ERR "%s@%d::%s() - "
11531 +               "Unable to write out csmi_sas_get_raid_features @ %p\n",
11532 +               __FILE__, __LINE__, __FUNCTION__, uarg);
11533 +        kfree(pKarg);
11534 +        return -EFAULT;
11535 +    }
11536 +
11537 +    kfree(pKarg);
11538 +
11539 +    return 0;
11540 +}
11541 +
11542 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
11543 +/* Prototype Routine for the CSMI SAS Get RAID Control command.
11544 + *
11545 + * Outputs:    None.
11546 + * Return:     0 if successful
11547 + *             -EFAULT if data unavailable
11548 + *             -ENODEV if no such device/adapter
11549 + */
11550 +static int
11551 +mptctl_csmi_sas_get_raid_control(unsigned long arg)
11552 +{
11553 +       CSMI_SAS_RAID_CONTROL_BUFFER __user *uarg = (void __user *) arg;
11554 +       CSMI_SAS_RAID_CONTROL_BUFFER karg, *pKarg=NULL;
11555 +       int csmi_sas_raid_control_buffer_sz, iocnum;
11556 +    MPT_ADAPTER                        *ioc = NULL;
11557 +
11558 +       dctlprintk((": %s called.\n",__FUNCTION__));
11559 +
11560 +       if (copy_from_user(&karg, uarg, sizeof(IOCTL_HEADER))) {
11561 +               printk(KERN_ERR "%s@%d::%s() - "
11562 +                   "Unable to read in csmi_sas_get_raid_control struct @ %p\n",
11563 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
11564 +               return -EFAULT;
11565 +       }
11566 +
11567 +       csmi_sas_raid_control_buffer_sz = karg.IoctlHeader.Length;
11568 +       pKarg = kmalloc(csmi_sas_raid_control_buffer_sz, GFP_KERNEL);
11569 +       if(!pKarg){
11570 +               printk(KERN_ERR "%s@%d::%s() - "
11571 +                   "Unable to malloc @ %p\n",
11572 +                   __FILE__, __LINE__, __FUNCTION__,pKarg);
11573 +               return -EFAULT;
11574 +       }
11575 +
11576 +       if (copy_from_user(pKarg, uarg, csmi_sas_raid_control_buffer_sz)) {
11577 +               printk(KERN_ERR "%s@%d::%s() - "
11578 +                   "Unable to read in csmi_sas_get_raid_features struct @ %p\n",
11579 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
11580 +               kfree(pKarg);
11581 +               return -EFAULT;
11582 +       }
11583 +
11584 +       if (((iocnum = mpt_verify_adapter(pKarg->IoctlHeader.IOControllerNumber,
11585 +           &ioc)) < 0) || (ioc == NULL)) {
11586 +               dctlprintk((KERN_ERR
11587 +               "%s::%s() @%d - ioc%d not found!\n",
11588 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
11589 +               kfree(pKarg);
11590 +               return -ENODEV;
11591 +       }
11592 +
11593 +       if (!mptctl_is_this_sas_cntr(ioc)) {
11594 +               dctlprintk((KERN_ERR
11595 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
11596 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
11597 +               kfree(pKarg);
11598 +               return -ENODEV;
11599 +       }
11600 +
11601 +       if (!ioc->raid_data.isRaid) {
11602 +               pKarg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
11603 +               goto cim_get_raid_control_exit;
11604 +       }
11605 +
11606 +    if (pKarg->Information.uChangeCount != 0 &&
11607 +        pKarg->Information.uChangeCount != ioc->csmi_change_count ) {
11608 +        pKarg->IoctlHeader.ReturnCode = 
11609 +                       CSMI_SAS_STATUS_INVALID_PARAMETER;
11610 +        pKarg->Information.uFailureCode = 
11611 +                       CSMI_SAS_FAIL_CODE_CHANGE_COUNT_INVALID;
11612 +        goto cim_get_raid_control_exit;
11613 +    }
11614 +
11615 +    if (pKarg->Information.bTransformPriority != CSMI_SAS_PRIORITY_UNCHANGED) {
11616 +        pKarg->IoctlHeader.ReturnCode = 
11617 +                       CSMI_SAS_STATUS_INVALID_PARAMETER;
11618 +        //pKarg->Information.uFailureCode = 
11619 +               //      CSMI_SAS_FAIL_CODE_EXPANSION_PRIORITY_INVALID;
11620 +    }
11621 +    if (pKarg->Information.bRebuildPriority != CSMI_SAS_PRIORITY_AUTO &&
11622 +        pKarg->Information.bRebuildPriority != CSMI_SAS_PRIORITY_UNCHANGED) {
11623 +        pKarg->IoctlHeader.ReturnCode = 
11624 +                       CSMI_SAS_STATUS_INVALID_PARAMETER;
11625 +        pKarg->Information.uFailureCode = 
11626 +                       CSMI_SAS_FAIL_CODE_REBUILD_PRIORITY_INVALID;
11627 +    }
11628 +    if (pKarg->Information.bCacheRatioFlag == CSMI_SAS_RAID_CACHE_RATIO_ENABLE) {
11629 +        pKarg->IoctlHeader.ReturnCode = 
11630 +                       CSMI_SAS_STATUS_INVALID_PARAMETER;
11631 +        pKarg->Information.uFailureCode = 
11632 +                       CSMI_SAS_FAIL_CODE_CACHE_RATIO_INVALID;
11633 +    }
11634 +    pKarg->Information.bFailureDescription[0] = '\0';
11635 +
11636 +cim_get_raid_control_exit:
11637 +
11638 +    /*
11639 +     * Copy the data from kernel memory to user memory
11640 +     */
11641 +    if (copy_to_user((char *)arg, pKarg,
11642 +        sizeof(CSMI_SAS_RAID_CONTROL_BUFFER))) {
11643 +        printk(KERN_ERR "%s@%d::%s() - "
11644 +               "Unable to write out csmi_sas_get_raid_control @ %p\n",
11645 +               __FILE__, __LINE__, __FUNCTION__, uarg);
11646 +        kfree(pKarg);
11647 +        return -EFAULT;
11648 +    }
11649 +
11650 +    kfree(pKarg);
11651 +
11652 +    return 0;
11653 +}
11654 +
11655 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
11656 +/* Prototype Routine for the CSMI SAS Task Managment Config command.
11657 + *
11658 + * Outputs:    None.
11659 + * Return:     0 if successful
11660 + *             -EFAULT if data unavailable
11661 + *             -ENODEV if no such device/adapter
11662 + */
11663 +static int
11664 +mptctl_csmi_sas_task_managment(unsigned long arg)
11665 +{
11666 +       CSMI_SAS_SSP_TASK_IU_BUFFER __user *uarg = (void __user *) arg;
11667 +       CSMI_SAS_SSP_TASK_IU_BUFFER      karg;
11668 +       pSCSITaskMgmt_t                 pScsiTm;
11669 +       pSCSITaskMgmtReply_t            pScsiTmReply;
11670 +       MPT_ADAPTER                     *ioc = NULL;
11671 +       MPT_SCSI_HOST                   *hd;
11672 +       MPT_FRAME_HDR                   *mf = NULL;
11673 +       MPIHeader_t                     *mpi_hdr;
11674 +       int                             iocnum;
11675 +       u8                              taskType;
11676 +       u8                              path;
11677 +       u8                              target;
11678 +       u8                              lun;
11679 +       u8                              queueTag;
11680 +       u32                             msgContext = 0;
11681 +       int                             retval;
11682 +       int                             i, ii;
11683 +       u8                              found_qtag;
11684 +       int                             wait_timeout;
11685 +
11686 +       dctlprintk((": %s called.\n",__FUNCTION__));
11687 +
11688 +       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_SSP_TASK_IU_BUFFER))) {
11689 +               printk(KERN_ERR "%s@%d::%s() - "
11690 +                   "Unable to read in csmi_sas_task_managment struct @ %p\n",
11691 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
11692 +               return -EFAULT;
11693 +       }
11694 +
11695 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
11696 +           &ioc)) < 0) || (ioc == NULL)) {
11697 +               dctlprintk((KERN_ERR
11698 +               "%s::%s() @%d - ioc%d not found!\n",
11699 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
11700 +               return -ENODEV;
11701 +       }
11702 +
11703 +       if (!mptctl_is_this_sas_cntr(ioc)) {
11704 +               dctlprintk((KERN_ERR
11705 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
11706 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
11707 +               return -ENODEV;
11708 +       }
11709 +
11710 +       /* try to catch an error
11711 +        */
11712 +       if ((karg.Parameters.uFlags & CSMI_SAS_TASK_IU) &&
11713 +           (karg.Parameters.uFlags & CSMI_SAS_HARD_RESET_SEQUENCE)) {
11714 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
11715 +               goto cim_get_task_managment_exit;
11716 +       }
11717 +
11718 +       if (karg.Parameters.uFlags & CSMI_SAS_TASK_IU) {
11719 +               switch (karg.Parameters.bTaskManagementFunction) {
11720 +
11721 +               case CSMI_SAS_SSP_ABORT_TASK:
11722 +                       taskType = MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK;
11723 +                       break;
11724 +               case CSMI_SAS_SSP_ABORT_TASK_SET:
11725 +                       taskType = MPI_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET;
11726 +                       break;
11727 +               case CSMI_SAS_SSP_CLEAR_TASK_SET:
11728 +                       taskType = MPI_SCSITASKMGMT_TASKTYPE_CLEAR_TASK_SET;
11729 +                       break;
11730 +               case CSMI_SAS_SSP_LOGICAL_UNIT_RESET:
11731 +                       taskType = MPI_SCSITASKMGMT_TASKTYPE_LOGICAL_UNIT_RESET;
11732 +                       break;
11733 +               case CSMI_SAS_SSP_CLEAR_ACA:
11734 +               case CSMI_SAS_SSP_QUERY_TASK:
11735 +               default:
11736 +                       karg.IoctlHeader.ReturnCode =
11737 +                           CSMI_SAS_STATUS_INVALID_PARAMETER;
11738 +                       goto cim_get_task_managment_exit;
11739 +               }
11740 +       }else if (karg.Parameters.uFlags & CSMI_SAS_HARD_RESET_SEQUENCE) {
11741 +               /* set the code up to do a hard reset
11742 +                */
11743 +               taskType = MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET;
11744 +       }else {
11745 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
11746 +               goto cim_get_task_managment_exit;
11747 +       }
11748 +
11749 +       path = karg.Parameters.bPathId;
11750 +       target = karg.Parameters.bTargetId;
11751 +       lun = karg.Parameters.bLun;
11752 +       queueTag = (u8)karg.Parameters.uQueueTag & 0xFF;
11753 +
11754 +       if ((ioc->sh == NULL) || (ioc->sh->hostdata == NULL)) {
11755 +               karg.IoctlHeader.ReturnCode =
11756 +                   CSMI_SAS_STATUS_INVALID_PARAMETER;
11757 +               goto cim_get_task_managment_exit;
11758 +       }
11759 +       else
11760 +               hd = (MPT_SCSI_HOST *) ioc->sh->hostdata;
11761 +
11762 +       switch ( karg.Parameters.uInformation ) {
11763 +               case CSMI_SAS_SSP_TEST:
11764 +                       dsasprintk(("TM request for test purposes\n"));
11765 +                       break;
11766 +               case CSMI_SAS_SSP_EXCEEDED:
11767 +                       dsasprintk(("TM request due to timeout\n"));
11768 +                       break;
11769 +               case CSMI_SAS_SSP_DEMAND:
11770 +                       dsasprintk(("TM request demanded by app\n"));
11771 +                       break;
11772 +               case CSMI_SAS_SSP_TRIGGER:
11773 +                       dsasprintk(("TM request sent to trigger event\n"));
11774 +                       break;
11775 +       }
11776 +
11777 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
11778 +
11779 +       switch (taskType) {
11780 +
11781 +       case MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK:
11782 +       /*
11783 +        * look up qtag in the ScsiLookup[] table
11784 +        */
11785 +               for (i=0,found_qtag=0;i<hd->ioc->req_depth;i++) {
11786 +                       if ((hd->ScsiLookup[i]) &&
11787 +                           (hd->ScsiLookup[i]->tag == queueTag)) {
11788 +                               mf = MPT_INDEX_2_MFPTR(hd->ioc, i);
11789 +                               msgContext =
11790 +                                   mf->u.frame.hwhdr.msgctxu.MsgContext;
11791 +                               found_qtag=1;
11792 +                               break;
11793 +                       }
11794 +               }
11795 +
11796 +               if(!found_qtag) {
11797 +                       karg.IoctlHeader.ReturnCode =
11798 +                           CSMI_SAS_STATUS_INVALID_PARAMETER;
11799 +                       goto cim_get_task_managment_exit;
11800 +               }
11801 +
11802 +       case MPI_SCSITASKMGMT_TASKTYPE_LOGICAL_UNIT_RESET:
11803 +       case MPI_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET:
11804 +       case MPI_SCSITASKMGMT_TASKTYPE_CLEAR_TASK_SET:
11805 +       /* for now, this should work
11806 +        */
11807 +       case MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET:
11808 +
11809 +               /* Single threading ....
11810 +                */
11811 +               if (mptctl_set_tm_flags(hd) != 0) {
11812 +                       karg.IoctlHeader.ReturnCode =
11813 +                           CSMI_SAS_STATUS_FAILED;
11814 +                       goto cim_get_task_managment_exit;
11815 +               }
11816 +
11817 +               /* Send request
11818 +                */
11819 +               if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
11820 +                       dctlprintk((": no msg frames!\n"));
11821 +                       mptctl_free_tm_flags(ioc);
11822 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
11823 +                       goto cim_get_task_managment_exit;
11824 +               }
11825 +
11826 +               mpi_hdr = (MPIHeader_t *) mf;
11827 +               pScsiTm = (pSCSITaskMgmt_t ) mf;
11828 +
11829 +               memset(pScsiTm,0,sizeof(SCSITaskMgmt_t));
11830 +               pScsiTm->TaskType = taskType;
11831 +               pScsiTm->Bus = path;
11832 +               pScsiTm->TargetID = target;
11833 +               pScsiTm->LUN[1] = lun;
11834 +               pScsiTm->MsgContext = mpi_hdr->MsgContext;
11835 +               pScsiTm->TaskMsgContext = msgContext;
11836 +               pScsiTm->Function = MPI_FUNCTION_SCSI_TASK_MGMT;
11837 +
11838 +               ioc->ioctl->wait_done = 0;
11839 +
11840 +               DBG_DUMP_TM_REQUEST_FRAME((u32 *)mf);
11841 +
11842 +               if ((retval = mpt_send_handshake_request(mptctl_id, ioc->ioctl->ioc,
11843 +                    sizeof(SCSITaskMgmt_t), (u32*)pScsiTm, CAN_SLEEP)) != 0) {
11844 +                       dfailprintk((MYIOC_s_ERR_FMT "_send_handshake FAILED!"
11845 +                               " (hd %p, ioc %p, mf %p) \n", hd->ioc->name, hd,
11846 +                               hd->ioc, mf));
11847 +                       goto cim_get_task_managment_exit;
11848 +               }
11849 +
11850 +               /* Now wait for the command to complete */
11851 +               wait_timeout=max_t(int,MPT_IOCTL_DEFAULT_TIMEOUT,karg.IoctlHeader.Timeout);
11852 +               ii = wait_event_timeout(mptctl_wait,
11853 +                    ioc->ioctl->wait_done == 1,
11854 +                    HZ*wait_timeout);
11855 +
11856 +               if(ii <=0 && (ioc->ioctl->wait_done != 1 )) {
11857 +               /* Now we need to reset the board */
11858 +                       mptctl_free_tm_flags(ioc);
11859 +                       mpt_free_msg_frame(hd->ioc, mf);
11860 +                       mptctl_timeout_expired(ioc->ioctl);
11861 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
11862 +                       goto cim_get_task_managment_exit;
11863 +               }
11864 +
11865 +               if (ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) {
11866 +                       pScsiTmReply =
11867 +                           (pSCSITaskMgmtReply_t ) ioc->ioctl->ReplyFrame;
11868 +
11869 +                       memset(&karg.Status,0,
11870 +                           sizeof(CSMI_SAS_SSP_PASSTHRU_STATUS));
11871 +
11872 +                       if(le16_to_cpu(pScsiTmReply->IOCStatus) == MPI_IOCSTATUS_SUCCESS) {
11873 +                               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
11874 +                               karg.Status.bSSPStatus = CSMI_SAS_SSP_STATUS_COMPLETED;
11875 +                       }else if(le16_to_cpu(pScsiTmReply->IOCStatus) ==
11876 +                           MPI_IOCSTATUS_INSUFFICIENT_RESOURCES) {
11877 +                               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
11878 +                               karg.Status.bSSPStatus = CSMI_SAS_SSP_STATUS_RETRY;
11879 +                       }else {
11880 +                               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
11881 +                               karg.Status.bSSPStatus = CSMI_SAS_SSP_STATUS_FATAL_ERROR;
11882 +                       }
11883 +               }else{
11884 +                       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
11885 +               }
11886 +
11887 +               break;
11888 +
11889 +       default:
11890 +               karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
11891 +               break;
11892 +       }
11893 +
11894 +
11895 +cim_get_task_managment_exit:
11896 +
11897 +       /* Copy the data from kernel memory to user memory
11898 +        */
11899 +       if (copy_to_user((char *)arg, &karg,
11900 +                               sizeof(CSMI_SAS_SSP_TASK_IU_BUFFER))) {
11901 +               printk(KERN_ERR "%s@%d::%s() - "
11902 +                       "Unable to write out csmi_sas_task_managment @ %p\n",
11903 +                               __FILE__, __LINE__, __FUNCTION__, uarg);
11904 +               return -EFAULT;
11905 +       }
11906 +
11907 +       return 0;
11908 +}
11909 +
11910 +
11911 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
11912 +/*
11913 + *     map_sas_status_to_csmi - Conversion  for Connection Status
11914 + *     @mpi_sas_status: Sas status returned by the firmware
11915 + *
11916 + *     Returns converted connection status
11917 + *
11918 + */
11919 +static u8
11920 +map_sas_status_to_csmi(u8 mpi_sas_status)
11921 +{
11922 +       u8  csmi_connect_status;
11923 +
11924 +       switch (mpi_sas_status) {
11925 +
11926 +       case MPI_SASSTATUS_SUCCESS:
11927 +               csmi_connect_status = CSMI_SAS_OPEN_ACCEPT;
11928 +               break;
11929 +
11930 +       case MPI_SASSTATUS_UTC_BAD_DEST:
11931 +               csmi_connect_status = CSMI_SAS_OPEN_REJECT_BAD_DESTINATION;
11932 +               break;
11933 +
11934 +       case MPI_SASSTATUS_UTC_CONNECT_RATE_NOT_SUPPORTED:
11935 +               csmi_connect_status = CSMI_SAS_OPEN_REJECT_RATE_NOT_SUPPORTED;
11936 +               break;
11937 +
11938 +       case MPI_SASSTATUS_UTC_PROTOCOL_NOT_SUPPORTED:
11939 +               csmi_connect_status = CSMI_SAS_OPEN_REJECT_PROTOCOL_NOT_SUPPORTED;
11940 +               break;
11941 +
11942 +       case MPI_SASSTATUS_UTC_STP_RESOURCES_BUSY:
11943 +               csmi_connect_status = CSMI_SAS_OPEN_REJECT_STP_RESOURCES_BUSY;
11944 +               break;
11945 +
11946 +       case MPI_SASSTATUS_UTC_WRONG_DESTINATION:
11947 +               csmi_connect_status = CSMI_SAS_OPEN_REJECT_WRONG_DESTINATION;
11948 +               break;
11949 +
11950 +       case MPI_SASSTATUS_SDSF_NAK_RECEIVED:
11951 +               csmi_connect_status = CSMI_SAS_OPEN_REJECT_RETRY;
11952 +               break;
11953 +
11954 +       case MPI_SASSTATUS_SDSF_CONNECTION_FAILED:
11955 +               csmi_connect_status = CSMI_SAS_OPEN_REJECT_PATHWAY_BLOCKED;
11956 +               break;
11957 +
11958 +       case MPI_SASSTATUS_INITIATOR_RESPONSE_TIMEOUT:
11959 +               csmi_connect_status =  CSMI_SAS_OPEN_REJECT_NO_DESTINATION;
11960 +               break;
11961 +
11962 +       case MPI_SASSTATUS_UNKNOWN_ERROR:
11963 +       case MPI_SASSTATUS_INVALID_FRAME:
11964 +       case MPI_SASSTATUS_UTC_BREAK_RECEIVED:
11965 +       case MPI_SASSTATUS_UTC_PORT_LAYER_REQUEST:
11966 +       case MPI_SASSTATUS_SHORT_INFORMATION_UNIT:
11967 +       case MPI_SASSTATUS_LONG_INFORMATION_UNIT:
11968 +       case MPI_SASSTATUS_XFER_RDY_INCORRECT_WRITE_DATA:
11969 +       case MPI_SASSTATUS_XFER_RDY_REQUEST_OFFSET_ERROR:
11970 +       case MPI_SASSTATUS_XFER_RDY_NOT_EXPECTED:
11971 +       case MPI_SASSTATUS_DATA_INCORRECT_DATA_LENGTH:
11972 +       case MPI_SASSTATUS_DATA_TOO_MUCH_READ_DATA:
11973 +       case MPI_SASSTATUS_DATA_OFFSET_ERROR:
11974 +               csmi_connect_status = CSMI_SAS_OPEN_REJECT_RESERVE_STOP;
11975 +               break;
11976 +
11977 +       default:
11978 +               csmi_connect_status = CSMI_SAS_OPEN_REJECT_RESERVE_STOP;
11979 +               break;
11980 +       }
11981 +
11982 +       return csmi_connect_status;
11983 +}
11984 +
11985 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
11986 +/*                      mptctl_csmi_sas_phy_reset
11987 + *     Issues a phy link reset or phy hard reset
11988 + *
11989 + *     @ioc - Pointer to MPT_ADAPTER structure
11990 + *     @PhyNum - phy number
11991 + *     @opcode - {MPI_SAS_OP_PHY_LINK_RESET,MPI_SAS_OP_PHY_HARD_RESET}
11992 + *
11993 + *     Returns: 0 for success, non-zero error
11994 + */
11995 +static int
11996 +mptctl_csmi_sas_phy_reset(MPT_ADAPTER *ioc, u8 PhyNum, u8 opcode)
11997 +{
11998 +       SasIoUnitControlRequest_t       *sasIoUnitCntrReq;
11999 +       SasIoUnitControlReply_t         *sasIoUnitCntrReply;
12000 +       MPT_FRAME_HDR                   *mf = NULL;
12001 +       MPIHeader_t                     *mpi_hdr;
12002 +       int                             ii;
12003 +
12004 +       if ((opcode != MPI_SAS_OP_PHY_LINK_RESET) &&
12005 +           (opcode != MPI_SAS_OP_PHY_HARD_RESET))
12006 +           return -1;
12007 +
12008 +       /* Get a MF for this command.
12009 +        */
12010 +       if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
12011 +               dctlprintk((": no msg frames!\n"));
12012 +               return -1;
12013 +        }
12014 +
12015 +       mpi_hdr = (MPIHeader_t *) mf;
12016 +       sasIoUnitCntrReq = (SasIoUnitControlRequest_t *)mf;
12017 +       memset(sasIoUnitCntrReq,0,sizeof(SasIoUnitControlRequest_t));
12018 +       sasIoUnitCntrReq->Function = MPI_FUNCTION_SAS_IO_UNIT_CONTROL;
12019 +       sasIoUnitCntrReq->MsgContext = mpi_hdr->MsgContext;
12020 +       sasIoUnitCntrReq->Operation = opcode;
12021 +       sasIoUnitCntrReq->PhyNum = PhyNum;
12022 +
12023 +       ioc->ioctl->wait_done = 0;
12024 +       mpt_put_msg_frame(mptctl_id, ioc, mf);
12025 +
12026 +       /* Now wait for the command to complete */
12027 +       ii = wait_event_timeout(mptctl_wait,
12028 +            ioc->ioctl->wait_done == 1,
12029 +            HZ*MPT_IOCTL_DEFAULT_TIMEOUT /* 10 sec */);
12030 +
12031 +       if(ii <=0 && (ioc->ioctl->wait_done != 1 )) {
12032 +               /* Now we need to reset the board */
12033 +               mpt_free_msg_frame(ioc, mf);
12034 +               mptctl_timeout_expired(ioc->ioctl);
12035 +               return -1;
12036 +       }
12037 +
12038 +       if ((ioc->ioctl->status & MPT_IOCTL_STATUS_RF_VALID) == 0)
12039 +               return -1;
12040 +
12041 +       /* process the completed Reply Message Frame */
12042 +       sasIoUnitCntrReply = (SasIoUnitControlReply_t *)ioc->ioctl->ReplyFrame;
12043 +       if (sasIoUnitCntrReply->IOCStatus != MPI_IOCSTATUS_SUCCESS) {
12044 +               printk("%s: IOCStatus=0x%X IOCLogInfo=0x%X\n",
12045 +                   __FUNCTION__,
12046 +                   sasIoUnitCntrReply->IOCStatus,
12047 +                   sasIoUnitCntrReply->IOCLogInfo);
12048 +               return -1;
12049 +       }
12050 +       return 0;
12051 +}
12052 +
12053 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
12054 +/* Prototype Routine for the CSMI SAS Phy Control command.
12055 + *
12056 + * Outputs:    None.
12057 + * Return:     0 if successful
12058 + *             -EFAULT if data unavailable
12059 + *             -ENODEV if no such device/adapter
12060 + */
12061 +static int
12062 +mptctl_csmi_sas_phy_control(unsigned long arg)
12063 +{
12064 +       CSMI_SAS_PHY_CONTROL_BUFFER __user *uarg = (void __user *) arg;
12065 +       IOCTL_HEADER                    ioctl_header;
12066 +       PCSMI_SAS_PHY_CONTROL_BUFFER    karg;
12067 +       SasIOUnitPage0_t                *sasIoUnitPg0=NULL;
12068 +       dma_addr_t                      sasIoUnitPg0_dma;
12069 +       int                             sasIoUnitPg0_data_sz=0;
12070 +       SasIOUnitPage1_t                *sasIoUnitPg1=NULL;
12071 +       dma_addr_t                      sasIoUnitPg1_dma;
12072 +       int                             sasIoUnitPg1_data_sz=0;
12073 +       ConfigExtendedPageHeader_t      hdr;
12074 +       CONFIGPARMS                     cfg;
12075 +       MPT_ADAPTER                     *ioc = NULL;
12076 +       int                             iocnum;
12077 +       int                             csmi_sas_phy_control_buffer_sz;
12078 +
12079 +       dctlprintk((": %s called.\n",__FUNCTION__));
12080 +
12081 +       if (copy_from_user(&ioctl_header, uarg, sizeof(IOCTL_HEADER))) {
12082 +               printk(KERN_ERR "%s@%d::%s() - "
12083 +                   "Unable to read in IOCTL_HEADER"
12084 +                   "struct @ %p\n", __FILE__, __LINE__, __FUNCTION__, uarg);
12085 +               return -EFAULT;
12086 +       }
12087 +
12088 +       csmi_sas_phy_control_buffer_sz = ioctl_header.Length;
12089 +       karg = kmalloc(csmi_sas_phy_control_buffer_sz,GFP_KERNEL);
12090 +       if(karg==NULL){
12091 +               printk(KERN_ERR "%s@%d::%s() - "
12092 +                   "Unable to malloc @ %p\n",
12093 +                   __FILE__, __LINE__, __FUNCTION__,karg);
12094 +               return -EFAULT;
12095 +       }
12096 +
12097 +       if (copy_from_user(karg, uarg, csmi_sas_phy_control_buffer_sz)) {
12098 +               printk(KERN_ERR "%s@%d::%s() - "
12099 +                   "Unable to read in csmi_sas_phy_control_buffer "
12100 +                   "struct @ %p\n", __FILE__, __LINE__, __FUNCTION__, uarg);
12101 +               kfree(karg);
12102 +               return -EFAULT;
12103 +       }
12104 +
12105 +       if (((iocnum = mpt_verify_adapter(ioctl_header.IOControllerNumber,
12106 +           &ioc)) < 0) || (ioc == NULL)) {
12107 +               dctlprintk((KERN_ERR
12108 +               "%s::%s() @%d - ioc%d not found!\n",
12109 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
12110 +               kfree(karg);
12111 +               return -ENODEV;
12112 +       }
12113 +
12114 +       if (!mptctl_is_this_sas_cntr(ioc)) {
12115 +               dctlprintk((KERN_ERR
12116 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
12117 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
12118 +               kfree(karg);
12119 +               return -ENODEV;
12120 +       }
12121 +
12122 +       if (karg->bPhyIdentifier >= ioc->numPhys) {
12123 +               karg->IoctlHeader.ReturnCode =
12124 +                  CSMI_SAS_STATUS_INVALID_PARAMETER;
12125 +               goto cim_sas_phy_control_exit;
12126 +       }
12127 +
12128 +       /*
12129 +        *  Retreive SAS IOUNIT PAGE 0
12130 +        */
12131 +
12132 +       hdr.PageVersion = MPI_SASIOUNITPAGE0_PAGEVERSION;
12133 +       hdr.ExtPageLength = 0;
12134 +       hdr.PageNumber = 0;
12135 +       hdr.Reserved1 = 0;
12136 +       hdr.Reserved2 = 0;
12137 +       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
12138 +       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_IO_UNIT;
12139 +
12140 +       cfg.cfghdr.ehdr = &hdr;
12141 +       cfg.physAddr = -1;
12142 +       cfg.pageAddr = 0;
12143 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
12144 +       cfg.dir = 0;    /* read */
12145 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
12146 +
12147 +       if (mpt_config(ioc, &cfg) != 0) {
12148 +               dctlprintk((
12149 +                   ": FAILED: READ MPI_SASIOUNITPAGE0: HEADER\n"));
12150 +               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12151 +               goto cim_sas_phy_control_exit;
12152 +       }
12153 +
12154 +       if (hdr.ExtPageLength == 0) {
12155 +               dctlprintk((": hdr.ExtPageLength == 0\n"));
12156 +               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12157 +               goto cim_sas_phy_control_exit;
12158 +       }
12159 +
12160 +       sasIoUnitPg0_data_sz = hdr.ExtPageLength * 4;
12161 +       sasIoUnitPg0 = (SasIOUnitPage0_t *) pci_alloc_consistent(ioc->pcidev,
12162 +           sasIoUnitPg0_data_sz, &sasIoUnitPg0_dma);
12163 +
12164 +       if (!sasIoUnitPg0) {
12165 +               dctlprintk((": pci_alloc_consistent: FAILED\n"));
12166 +               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12167 +               goto cim_sas_phy_control_exit;
12168 +       }
12169 +
12170 +       memset((u8 *)sasIoUnitPg0, 0, sasIoUnitPg0_data_sz);
12171 +       cfg.physAddr = sasIoUnitPg0_dma;
12172 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
12173 +
12174 +       if (mpt_config(ioc, &cfg) != 0) {
12175 +               dctlprintk((
12176 +                   ": FAILED: READ MPI_SASIOUNITPAGE0: CURRENT\n"));
12177 +               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12178 +               goto cim_sas_phy_control_exit;
12179 +       }
12180 +
12181 +       /*
12182 +        *  Retreive SAS IOUNIT PAGE 1
12183 +        */
12184 +
12185 +       hdr.PageVersion = MPI_SASIOUNITPAGE0_PAGEVERSION;
12186 +       hdr.ExtPageLength = 0;
12187 +       hdr.PageNumber = 1;
12188 +       hdr.Reserved1 = 0;
12189 +       hdr.Reserved2 = 0;
12190 +       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
12191 +       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_IO_UNIT;
12192 +
12193 +       cfg.cfghdr.ehdr = &hdr;
12194 +       cfg.physAddr = -1;
12195 +       cfg.pageAddr = 0;
12196 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
12197 +       cfg.dir = 0;    /* read */
12198 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
12199 +
12200 +       if (mpt_config(ioc, &cfg) != 0) {
12201 +               dctlprintk((
12202 +                   ": FAILED: READ MPI_SASIOUNITPAGE1: HEADER\n"));
12203 +               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12204 +               goto cim_sas_phy_control_exit;
12205 +       }
12206 +
12207 +       if (hdr.ExtPageLength == 0) {
12208 +               dctlprintk((": hdr.ExtPageLength == 0\n"));
12209 +               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12210 +               goto cim_sas_phy_control_exit;
12211 +       }
12212 +
12213 +       sasIoUnitPg1_data_sz = hdr.ExtPageLength * 4;
12214 +       sasIoUnitPg1 = (SasIOUnitPage1_t *) pci_alloc_consistent(ioc->pcidev,
12215 +           sasIoUnitPg1_data_sz, &sasIoUnitPg1_dma);
12216 +
12217 +       if (!sasIoUnitPg1) {
12218 +               dctlprintk((": pci_alloc_consistent: FAILED\n"));
12219 +               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12220 +               goto cim_sas_phy_control_exit;
12221 +       }
12222 +
12223 +       memset((u8 *)sasIoUnitPg1, 0, sasIoUnitPg1_data_sz);
12224 +       cfg.physAddr = sasIoUnitPg1_dma;
12225 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
12226 +
12227 +       if (mpt_config(ioc, &cfg) != 0) {
12228 +               dctlprintk((
12229 +                   ": FAILED:  READ MPI_SASIOUNITPAGE1: CURRENT\n"));
12230 +               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12231 +               goto cim_sas_phy_control_exit;
12232 +       }
12233 +
12234 +       switch (karg->uFunction) {
12235 +
12236 +       case CSMI_SAS_PC_LINK_RESET:
12237 +       case CSMI_SAS_PC_HARD_RESET:
12238 +       {
12239 +               u8 opcode = (karg->uFunction==CSMI_SAS_PC_LINK_RESET) ?
12240 +                   MPI_SAS_OP_PHY_LINK_RESET : MPI_SAS_OP_PHY_HARD_RESET;
12241 +
12242 +               if((karg->uLinkFlags & CSMI_SAS_PHY_ACTIVATE_CONTROL) &&
12243 +                   (karg->usLengthOfControl >= sizeof(CSMI_SAS_PHY_CONTROL)) &&
12244 +                   (karg->bNumberOfControls > 0)){
12245 +                       if(karg->Control[0].bRate ==
12246 +                          CSMI_SAS_LINK_RATE_1_5_GBPS) {
12247 +                               sasIoUnitPg1->PhyData[karg->bPhyIdentifier].MaxMinLinkRate =
12248 +                               MPI_SAS_IOUNIT1_MAX_RATE_1_5 |
12249 +                               MPI_SAS_IOUNIT1_MIN_RATE_1_5;
12250 +                       }
12251 +                       else if(karg->Control[0].bRate ==
12252 +                          CSMI_SAS_LINK_RATE_3_0_GBPS) {
12253 +                               sasIoUnitPg1->PhyData[karg->bPhyIdentifier].MaxMinLinkRate =
12254 +                               MPI_SAS_IOUNIT1_MAX_RATE_3_0 |
12255 +                               MPI_SAS_IOUNIT1_MIN_RATE_3_0;
12256 +                       }
12257 +                       sasIoUnitPg1->PhyData[karg->bPhyIdentifier].PhyFlags &=
12258 +                           ~MPI_SAS_IOUNIT1_PHY_FLAGS_PHY_DISABLE;
12259 +                       cfg.dir = 1;
12260 +                       cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_NVRAM;
12261 +                       if (mpt_config(ioc, &cfg) != 0) {
12262 +                               dctlprintk((
12263 +                           ": FAILED: WRITE MPI_SASIOUNITPAGE1 NVRAM\n"));
12264 +                               karg->IoctlHeader.ReturnCode =
12265 +                                  CSMI_SAS_STATUS_FAILED;
12266 +                               goto cim_sas_phy_control_exit;
12267 +                       }
12268 +                       cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_CURRENT;
12269 +                       if (mpt_config(ioc, &cfg) != 0) {
12270 +                               dctlprintk((
12271 +                        ": FAILED: WRITE MPI_SASIOUNITPAGE1 CURRENT\n"));
12272 +                               karg->IoctlHeader.ReturnCode =
12273 +                                  CSMI_SAS_STATUS_FAILED;
12274 +                               goto cim_sas_phy_control_exit;
12275 +                       }
12276 +               }
12277 +               if (mptctl_csmi_sas_phy_reset(ioc,
12278 +                   karg->bPhyIdentifier, opcode) != 0) {
12279 +                       dctlprintk((
12280 +                           ": FAILED: mptctl_csmi_sas_phy_reset\n"));
12281 +                       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12282 +                       goto cim_sas_phy_control_exit;
12283 +               }
12284 +               break;
12285 +
12286 +       }
12287 +       case CSMI_SAS_PC_PHY_DISABLE:
12288 +               if(karg->usLengthOfControl || karg->bNumberOfControls) {
12289 +                       karg->IoctlHeader.ReturnCode =
12290 +                           CSMI_SAS_STATUS_INVALID_PARAMETER;
12291 +                       break;
12292 +               }
12293 +               sasIoUnitPg1->PhyData[karg->bPhyIdentifier].PhyFlags |=
12294 +                   MPI_SAS_IOUNIT1_PHY_FLAGS_PHY_DISABLE;
12295 +               cfg.dir = 1;
12296 +               cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_NVRAM;
12297 +               if (mpt_config(ioc, &cfg) != 0) {
12298 +                       dctlprintk((
12299 +                           ": FAILED: WRITE MPI_SASIOUNITPAGE1 NVRAM\n"));
12300 +                       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12301 +                       goto cim_sas_phy_control_exit;
12302 +               }
12303 +               cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_CURRENT;
12304 +               if (mpt_config(ioc, &cfg) != 0) {
12305 +                       dctlprintk((
12306 +                           ": FAILED: WRITE MPI_SASIOUNITPAGE1 CURRENT\n"));
12307 +                       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12308 +                       goto cim_sas_phy_control_exit;
12309 +               }
12310 +               if (mptctl_csmi_sas_phy_reset(ioc,
12311 +                   karg->bPhyIdentifier, MPI_SAS_OP_PHY_HARD_RESET) != 0) {
12312 +                       dctlprintk((
12313 +                           ": FAILED: mptctl_csmi_sas_phy_reset\n"));
12314 +                       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12315 +                       goto cim_sas_phy_control_exit;
12316 +               }
12317 +               break;
12318 +
12319 +       case CSMI_SAS_PC_GET_PHY_SETTINGS:
12320 +               if(karg->usLengthOfControl || karg->bNumberOfControls) {
12321 +                       karg->IoctlHeader.ReturnCode =
12322 +                           CSMI_SAS_STATUS_INVALID_PARAMETER;
12323 +                       break;
12324 +               }
12325 +               if(csmi_sas_phy_control_buffer_sz <
12326 +                   offsetof(CSMI_SAS_PHY_CONTROL_BUFFER,Control) +
12327 +                   (4* sizeof(CSMI_SAS_PHY_CONTROL))) {
12328 +                       karg->IoctlHeader.ReturnCode =
12329 +                           CSMI_SAS_STATUS_INVALID_PARAMETER;
12330 +                       break;
12331 +               }
12332 +               karg->usLengthOfControl = sizeof(CSMI_SAS_PHY_CONTROL);
12333 +               karg->bNumberOfControls = 4;
12334 +               karg->Control[0].bType = CSMI_SAS_SAS;
12335 +               karg->Control[0].bRate = CSMI_SAS_LINK_RATE_1_5_GBPS;
12336 +               karg->Control[1].bType = CSMI_SAS_SAS;
12337 +               karg->Control[1].bRate = CSMI_SAS_LINK_RATE_3_0_GBPS;
12338 +               karg->Control[2].bType = CSMI_SAS_SATA;
12339 +               karg->Control[2].bRate = CSMI_SAS_LINK_RATE_1_5_GBPS;
12340 +               karg->Control[3].bType = CSMI_SAS_SATA;
12341 +               karg->Control[3].bRate = CSMI_SAS_LINK_RATE_3_0_GBPS;
12342 +               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
12343 +               break;
12344 +       default:
12345 +               break;
12346 +       }
12347 +
12348 +cim_sas_phy_control_exit:
12349 +
12350 +       if (sasIoUnitPg0)
12351 +               pci_free_consistent(ioc->pcidev, sasIoUnitPg0_data_sz,
12352 +                   (u8 *) sasIoUnitPg0, sasIoUnitPg0_dma);
12353 +
12354 +       if (sasIoUnitPg1)
12355 +               pci_free_consistent(ioc->pcidev, sasIoUnitPg1_data_sz,
12356 +                   (u8 *) sasIoUnitPg1, sasIoUnitPg1_dma);
12357 +
12358 +       /* Copy the data from kernel memory to user memory
12359 +        */
12360 +       if (copy_to_user((char *)arg,karg,csmi_sas_phy_control_buffer_sz)) {
12361 +               printk(KERN_ERR "%s@%d::%s() - "
12362 +                   "Unable to write out csmi_sas_phy_control_buffer @ %p\n",
12363 +                   __FILE__, __LINE__, __FUNCTION__, uarg);
12364 +               kfree(karg);
12365 +               return -EFAULT;
12366 +       }
12367 +
12368 +       kfree(karg);
12369 +       return 0;
12370 +}
12371 +
12372 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
12373 +/* Prototype Routine for the CSMI SAS Get Connector info command.
12374 + *
12375 + * Outputs:    None.
12376 + * Return:     0 if successful
12377 + *             -EFAULT if data unavailable
12378 + *             -ENODEV if no such device/adapter
12379 + */
12380 +static int
12381 +mptctl_csmi_sas_get_connector_info(unsigned long arg)
12382 +{
12383 +       CSMI_SAS_CONNECTOR_INFO_BUFFER __user *uarg = (void __user *) arg;
12384 +       CSMI_SAS_CONNECTOR_INFO_BUFFER   karg;
12385 +       MPT_ADAPTER                     *ioc = NULL;
12386 +       int                             iocnum;
12387 +       int                             i;
12388 +
12389 +       dctlprintk((": %s called.\n",__FUNCTION__));
12390 +
12391 +       if (copy_from_user(&karg, uarg, sizeof(CSMI_SAS_CONNECTOR_INFO_BUFFER))) {
12392 +               printk(KERN_ERR "%s@%d::%s() - "
12393 +                  "Unable to read in csmi_sas_connector_info_buffer"
12394 +                  " struct @ %p\n",
12395 +                  __FILE__, __LINE__, __FUNCTION__, uarg);
12396 +               return -EFAULT;
12397 +       }
12398 +
12399 +       if (((iocnum = mpt_verify_adapter(karg.IoctlHeader.IOControllerNumber,
12400 +           &ioc)) < 0) || (ioc == NULL)) {
12401 +               dctlprintk((KERN_ERR
12402 +               "%s::%s() @%d - ioc%d not found!\n",
12403 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
12404 +               return -ENODEV;
12405 +       }
12406 +
12407 +       if (!mptctl_is_this_sas_cntr(ioc)) {
12408 +               dctlprintk((KERN_ERR
12409 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
12410 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
12411 +               return -ENODEV;
12412 +       }
12413 +
12414 +       karg.IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
12415 +// TODO - to be implemented - This requires MPI changes to a Manufacturing page
12416 +       for (i=0;i< ioc->numPhys;i++) {
12417 +               karg.Reference[i].uPinout = CSMI_SAS_CON_UNKNOWN;
12418 +               strcpy(karg.Reference[i].bConnector,"");
12419 +               karg.Reference[i].bLocation = CSMI_SAS_CON_UNKNOWN;
12420 +       }
12421 +
12422 +// cim_sas_get_connector_info_exit:
12423 +
12424 +       /* Copy the data from kernel memory to user memory
12425 +        */
12426 +       if (copy_to_user((char *)arg, &karg,
12427 +               sizeof(CSMI_SAS_CONNECTOR_INFO_BUFFER))) {
12428 +               printk(KERN_ERR "%s@%d::%s() - "
12429 +               "Unable to write out csmi_sas_connector_info_buffer @"
12430 +              "%p\n",
12431 +               __FILE__, __LINE__, __FUNCTION__, uarg);
12432 +               return -EFAULT;
12433 +       }
12434 +
12435 +       return 0;
12436 +
12437 +}
12438 +
12439 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
12440 +/*                 mptctl_csmi_sas_fill_location_data
12441 + *
12442 + * Outputs:    None.
12443 + * Return:     0 if successful
12444 + */
12445 +static int
12446 +mptctl_csmi_sas_fill_location_data(MPT_ADAPTER *ioc, u8 target, u8 bus, u8 opcode, CSMI_SAS_LOCATION_IDENTIFIER * location_ident)
12447 +{
12448 +
12449 +       ConfigExtendedPageHeader_t      hdr;
12450 +       CONFIGPARMS                     cfg;
12451 +       int                             rc;
12452 +       SasDevicePage0_t                *sasDevicePg0=NULL;
12453 +       SasEnclosurePage0_t             *sasEnclosurePg0=NULL;
12454 +       dma_addr_t                      sasDevicePg0_dma,sasEnclosurePg0_dma;
12455 +       int                             sasDevicePg0_data_sz=0;
12456 +       int                             sasEnclosurePg0_data_sz=0;
12457 +       u64                             SASAddress64;
12458 +
12459 +       dctlprintk((": %s called.\n",__FUNCTION__));
12460 +
12461 +       /* SAS Device Page 0 */
12462 +       hdr.PageVersion = MPI_SASDEVICE0_PAGEVERSION;
12463 +       hdr.ExtPageLength = 0;
12464 +       hdr.PageNumber = 0;
12465 +       hdr.Reserved1 = 0;
12466 +       hdr.Reserved2 = 0;
12467 +       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
12468 +       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_DEVICE;
12469 +
12470 +       cfg.cfghdr.ehdr = &hdr;
12471 +       cfg.physAddr = -1;
12472 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
12473 +       cfg.dir = 0;    /* read */
12474 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
12475 +
12476 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
12477 +               rc=-1;
12478 +               goto fill_location_data_exit;
12479 +       }
12480 +
12481 +       if (hdr.ExtPageLength == 0) {
12482 +               rc=-1;
12483 +               goto fill_location_data_exit;
12484 +       }
12485 +
12486 +       sasDevicePg0_data_sz = hdr.ExtPageLength * 4;
12487 +       sasDevicePg0 = (SasDevicePage0_t *) pci_alloc_consistent(
12488 +           ioc->pcidev, sasDevicePg0_data_sz, &sasDevicePg0_dma);
12489 +       if (!sasDevicePg0) {
12490 +               rc=-1;
12491 +               goto fill_location_data_exit;
12492 +       }
12493 +
12494 +       memset((u8 *)sasDevicePg0, 0, sasDevicePg0_data_sz);
12495 +       cfg.physAddr = sasDevicePg0_dma;
12496 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
12497 +       cfg.pageAddr = (bus << 8) + target
12498 +           + (MPI_SAS_DEVICE_PGAD_FORM_BUS_TARGET_ID <<
12499 +               MPI_SAS_DEVICE_PGAD_FORM_SHIFT);
12500 +
12501 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
12502 +               rc=-1;
12503 +               goto fill_location_data_exit;
12504 +       }
12505 +
12506 +       location_ident->bLocationFlags |= CSMI_SAS_LOCATE_SAS_ADDRESS_VALID;
12507 +       SASAddress64 = reverse_byte_order64((u64 *)&sasDevicePg0->SASAddress);
12508 +       memcpy(&location_ident->bSASAddress,&SASAddress64,sizeof(u64));
12509 +
12510 +       location_ident->bLocationFlags |= CSMI_SAS_LOCATE_SAS_LUN_VALID;
12511 +       memset(location_ident->bSASLun, 0, sizeof(location_ident->bSASLun));
12512 +
12513 +       /* SAS Enclosure Page 0 */
12514 +       hdr.PageVersion = MPI_SASENCLOSURE0_PAGEVERSION;
12515 +       hdr.ExtPageLength = 0;
12516 +       hdr.PageNumber = 0;
12517 +       hdr.Reserved1 = 0;
12518 +       hdr.Reserved2 = 0;
12519 +       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
12520 +       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_ENCLOSURE;
12521 +
12522 +       cfg.cfghdr.ehdr = &hdr;
12523 +       cfg.physAddr = -1;
12524 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
12525 +       cfg.dir = 0;    /* read */
12526 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
12527 +
12528 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
12529 +               rc=0;
12530 +               goto fill_location_data_exit;
12531 +       }
12532 +
12533 +       if (hdr.ExtPageLength == 0) {
12534 +               rc=0;
12535 +               goto fill_location_data_exit;
12536 +       }
12537 +
12538 +       sasEnclosurePg0_data_sz = hdr.ExtPageLength * 4;
12539 +       sasEnclosurePg0 = (SasEnclosurePage0_t *) pci_alloc_consistent(
12540 +           ioc->pcidev, sasEnclosurePg0_data_sz, &sasEnclosurePg0_dma);
12541 +       if (!sasEnclosurePg0) {
12542 +               rc=0;
12543 +               goto fill_location_data_exit;
12544 +       }
12545 +       cfg.physAddr = sasEnclosurePg0_dma;
12546 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
12547 +       cfg.pageAddr = le16_to_cpu(sasDevicePg0->EnclosureHandle)
12548 +           + (MPI_SAS_ENCLOS_PGAD_FORM_HANDLE <<
12549 +           MPI_SAS_ENCLOS_PGAD_FORM_SHIFT);
12550 +
12551 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
12552 +               rc=0;
12553 +               goto fill_location_data_exit;
12554 +       }
12555 +
12556 +       location_ident->bLocationFlags |=
12557 +           CSMI_SAS_LOCATE_ENCLOSURE_IDENTIFIER_VALID;
12558 +       SASAddress64 = reverse_byte_order64(
12559 +           (u64 *)&sasEnclosurePg0->EnclosureLogicalID);
12560 +       if (SASAddress64)
12561 +               memcpy(&location_ident->bEnclosureIdentifier,
12562 +                   &SASAddress64,sizeof(u64));
12563 +       else
12564 +               strcpy(location_ident->bEnclosureIdentifier,"Internal");
12565 +
12566 +// bBayPrefix - not supported
12567 +
12568 +// TODO - We need to look at sasEnclosurePg0-.Flags , to determine
12569 +//     whether SEP BUS/TargetID is valid.  Ifs its a SES device, then
12570 +//     issue internal inquiry to (bus/target) to gather the Enclosure name.
12571 +//     If the device is SMP, then issue SMP_MANUFACTURING to get enclosure name
12572 +//     If its direct attached, there is no enclosure name
12573 +       location_ident->bLocationFlags |= CSMI_SAS_LOCATE_ENCLOSURE_NAME_VALID;
12574 +       strcpy(location_ident->bEnclosureName,"Not Supported");
12575 +
12576 +       location_ident->bLocationFlags |= CSMI_SAS_LOCATE_LOCATION_STATE_VALID;
12577 +       location_ident->bLocationState = CSMI_SAS_LOCATE_UNKNOWN;
12578 +
12579 +       location_ident->bLocationFlags |= CSMI_SAS_LOCATE_BAY_IDENTIFIER_VALID;
12580 +       location_ident->bBayIdentifier = le16_to_cpu(sasDevicePg0->Slot);
12581 +
12582 +
12583 +// TODO - illuminating LEDs,
12584 +// karg->bIdentify = CSMI_SAS_LOCATE_FORCE_OFF, CSMI_SAS_LOCATE_FORCE_ON
12585 +// We can enable/disable LEDs by SCSI Enclosure Processor MPI request message
12586 +// printk("Flags=0x%x\n",sasEnclosurePg0->Flags);
12587 +
12588 +/* check sasEnclosurePg0->Flags -
12589 + * to validate whether we need to send the SEPRequest
12590 + * bit:5 should be set
12591 + * bit:3-0 any bit should be set.  If zero, then SEPRequest will fail
12592 +*/
12593 +
12594 +/* MPI_FUNCTION_SCSI_ENCLOSURE_PROCESSOR
12595 + * Look in mpi_init.h
12596 + * SEPRequest_t = structure
12597 + *
12598 + * SEPRequest_t->Action should be set to MPI_SEP_REQ_ACTION_WRITE_STATUS
12599 + *
12600 + * SEPRequest_t->Flags should be set to
12601 + * MPI_SEP_REQ_FLAGS_ENCLOSURE_SLOT_ADDRESS, to pass along enclosure/slot ids
12602 + *
12603 + * SEPRequest_t->SlotStatus |= MPI_SEP_REQ_SLOTSTATUS_IDENTIFY_REQUEST - this
12604 + * will illuminate the LEDs
12605 + */
12606 +
12607 +fill_location_data_exit:
12608 +
12609 +       if (sasDevicePg0 != NULL)
12610 +               pci_free_consistent(ioc->pcidev, sasDevicePg0_data_sz,
12611 +                   sasDevicePg0, sasDevicePg0_dma);
12612 +
12613 +       if (sasEnclosurePg0 != NULL)
12614 +               pci_free_consistent(ioc->pcidev, sasEnclosurePg0_data_sz,
12615 +                   sasEnclosurePg0, sasEnclosurePg0_dma);
12616 +       return rc;
12617 +}
12618 +
12619 +
12620 +static int
12621 +mptctl_csmi_sas_fill_location_data_raid(MPT_ADAPTER *ioc, PCSMI_SAS_GET_LOCATION_BUFFER karg, u8 volumeID, u8 VolumeBus)
12622 +{
12623 +       pRaidVolumePage0_t              pVolume0 = NULL;
12624 +       pRaidPhysDiskPage0_t            pPhysDisk0 = NULL;
12625 +       CONFIGPARMS                     cfg;
12626 +       ConfigPageHeader_t              header;
12627 +       u8                              physDiskNumMax,physDiskNum;
12628 +       int                             volumepage0sz = 0, physdiskpage0sz = 0;
12629 +       dma_addr_t                      volume0_dma, physdisk0_dma;
12630 +       int                             csmi_sas_get_location_sz;
12631 +       int                             rc = 0,i;
12632 +
12633 +       csmi_sas_get_location_sz = karg->IoctlHeader.Length;
12634 +       physDiskNumMax = (csmi_sas_get_location_sz -
12635 +           offsetof(CSMI_SAS_GET_LOCATION_BUFFER,Location))
12636 +           / sizeof(CSMI_SAS_LOCATION_IDENTIFIER);
12637 +       karg->bNumberOfLocationIdentifiers=0;
12638 +
12639 +       /*
12640 +        * get RAID Volume Page 0
12641 +        */
12642 +
12643 +       header.PageVersion = 0;
12644 +       header.PageLength = 0;
12645 +       header.PageNumber = 0;
12646 +       header.PageType = MPI_CONFIG_PAGETYPE_RAID_VOLUME;
12647 +       cfg.cfghdr.hdr = &header;
12648 +       cfg.physAddr = -1;
12649 +       cfg.pageAddr = (VolumeBus << 8) + volumeID;
12650 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
12651 +       cfg.dir = 0;
12652 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
12653 +       if (mpt_config(ioc, &cfg) != 0) {
12654 +               rc = -1;
12655 +               goto sas_fill_location_data_raid_exit;
12656 +       }
12657 +
12658 +       if (header.PageLength == 0) {
12659 +               rc = -1;
12660 +               goto sas_fill_location_data_raid_exit;
12661 +       }
12662 +
12663 +       volumepage0sz = header.PageLength * 4;
12664 +       pVolume0 = pci_alloc_consistent(ioc->pcidev, volumepage0sz,
12665 +           &volume0_dma);
12666 +       if (!pVolume0) {
12667 +               rc = -1;
12668 +               goto sas_fill_location_data_raid_exit;
12669 +       }
12670 +
12671 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
12672 +       cfg.physAddr = volume0_dma;
12673 +       if (mpt_config(ioc, &cfg) != 0){
12674 +               rc = -1;
12675 +               goto sas_fill_location_data_raid_exit;
12676 +       }
12677 +
12678 +
12679 +       /*
12680 +        * get RAID Physical Disk Page 0
12681 +        */
12682 +       header.PageVersion = 0;
12683 +       header.PageLength = 0;
12684 +       header.PageNumber = 0;
12685 +       header.PageType = MPI_CONFIG_PAGETYPE_RAID_PHYSDISK;
12686 +       cfg.cfghdr.hdr = &header;
12687 +       cfg.physAddr = -1;
12688 +       cfg.pageAddr = 0;
12689 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
12690 +       cfg.dir = 0;
12691 +       cfg.timeout = MPT_IOCTL_DEFAULT_TIMEOUT;
12692 +       if (mpt_config(ioc, &cfg) != 0) {
12693 +               rc = -1;
12694 +               goto sas_fill_location_data_raid_exit;
12695 +       }
12696 +
12697 +       if (header.PageLength == 0) {
12698 +               rc = -1;
12699 +               goto sas_fill_location_data_raid_exit;
12700 +       }
12701 +
12702 +       physdiskpage0sz = header.PageLength * 4;
12703 +       pPhysDisk0 = pci_alloc_consistent(ioc->pcidev, physdiskpage0sz,
12704 +           &physdisk0_dma);
12705 +       if (!pPhysDisk0) {
12706 +               rc = -1;
12707 +               goto sas_fill_location_data_raid_exit;
12708 +       }
12709 +       cfg.physAddr = physdisk0_dma;
12710 +
12711 +       for (i=0; i< min(pVolume0->NumPhysDisks, physDiskNumMax); i++) {
12712 +
12713 +               physDiskNum = pVolume0->PhysDisk[i].PhysDiskNum;
12714 +               cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
12715 +               cfg.pageAddr = physDiskNum;
12716 +               if (mpt_config(ioc, &cfg) != 0){
12717 +                       rc = -1;
12718 +                       goto sas_fill_location_data_raid_exit;
12719 +               }
12720 +
12721 +               if((mptctl_csmi_sas_fill_location_data(ioc,
12722 +                  pPhysDisk0->PhysDiskID,
12723 +                  karg->bPathId, karg->bIdentify,
12724 +                  &karg->Location[karg->bNumberOfLocationIdentifiers])) == 0)
12725 +                       karg->bNumberOfLocationIdentifiers++;
12726 +       }
12727 +
12728 +
12729 +sas_fill_location_data_raid_exit:
12730 +
12731 +       if (pVolume0 != NULL)
12732 +               pci_free_consistent(ioc->pcidev, volumepage0sz, pVolume0,
12733 +                   volume0_dma);
12734 +
12735 +       if(pPhysDisk0 != NULL)
12736 +               pci_free_consistent(ioc->pcidev, physdiskpage0sz, pPhysDisk0,
12737 +                   physdisk0_dma);
12738 +
12739 +       return rc;
12740 +}
12741 +
12742 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
12743 +/* Prototype Routine for the CSMI SAS Get location command.
12744 + *
12745 + * Outputs:    None.
12746 + * Return:     0 if successful
12747 + *             -EFAULT if data unavailable
12748 + *             -ENODEV if no such device/adapter
12749 + */
12750 +static int
12751 +mptctl_csmi_sas_get_location(unsigned long arg)
12752 +{
12753 +       CSMI_SAS_GET_LOCATION_BUFFER __user *uarg = (void __user *) arg;
12754 +       PCSMI_SAS_GET_LOCATION_BUFFER   karg;
12755 +       IOCTL_HEADER                    ioctl_header;
12756 +       MPT_ADAPTER                     *ioc = NULL;
12757 +       int                             iocnum,i;
12758 +       int                             csmi_sas_get_location_sz;
12759 +
12760 +       dctlprintk((": %s called.\n",__FUNCTION__));
12761 +
12762 +       if (copy_from_user(&ioctl_header, uarg, sizeof(IOCTL_HEADER))) {
12763 +               printk(KERN_ERR "%s@%d::%s() - "
12764 +                   "Unable to read in IOCTL_HEADER"
12765 +                   "struct @ %p\n", __FILE__, __LINE__, __FUNCTION__, uarg);
12766 +               return -EFAULT;
12767 +       }
12768 +
12769 +       csmi_sas_get_location_sz = ioctl_header.Length;
12770 +       karg = kmalloc(csmi_sas_get_location_sz,GFP_KERNEL);
12771 +       if(karg==NULL){
12772 +               printk(KERN_ERR "%s@%d::%s() - "
12773 +                   "Unable to malloc @ %p\n",
12774 +                   __FILE__, __LINE__, __FUNCTION__,karg);
12775 +               return -EFAULT;
12776 +       }
12777 +
12778 +       if (copy_from_user(karg, uarg, csmi_sas_get_location_sz)) {
12779 +               printk(KERN_ERR "%s@%d::%s() - "
12780 +                   "Unable to read in csmi_sas_phy_control_buffer "
12781 +                   "struct @ %p\n", __FILE__, __LINE__, __FUNCTION__, uarg);
12782 +               kfree(karg);
12783 +               return -EFAULT;
12784 +       }
12785 +
12786 +       if (((iocnum = mpt_verify_adapter(karg->IoctlHeader.IOControllerNumber,
12787 +           &ioc)) < 0) || (ioc == NULL)) {
12788 +               dctlprintk((KERN_ERR
12789 +               "%s::%s() @%d - ioc%d not found!\n",
12790 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
12791 +               kfree(karg);
12792 +               return -ENODEV;
12793 +       }
12794 +
12795 +       if (!mptctl_is_this_sas_cntr(ioc)) {
12796 +               dctlprintk((KERN_ERR
12797 +                   "%s::%s() @%d - ioc%d not SAS controller!\n",
12798 +                   __FILE__, __FUNCTION__, __LINE__, iocnum));
12799 +               kfree(karg);
12800 +               return -ENODEV;
12801 +       }
12802 +
12803 +       karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_INVALID_PARAMETER;
12804 +       if(karg->bLengthOfLocationIdentifier != sizeof(CSMI_SAS_LOCATION_IDENTIFIER))
12805 +               goto cim_sas_get_location_exit;
12806 +
12807 +
12808 +       /* RAID SUPPORT */
12809 +       if (ioc->raid_data.isRaid && ioc->raid_data.pIocPg2) {
12810 +               for (i=0; i<ioc->raid_data.pIocPg2->NumActiveVolumes; i++){
12811 +                       if (karg->bTargetId ==
12812 +                           ioc->raid_data.pIocPg2->RaidVolume[i].VolumeID) {
12813 +                               if(mptctl_csmi_sas_fill_location_data_raid(ioc, karg,
12814 +                                   ioc->raid_data.pIocPg2->RaidVolume[i].VolumeID,
12815 +                                   ioc->raid_data.pIocPg2->RaidVolume[i].VolumeBus) == 0)
12816 +                                       karg->IoctlHeader.ReturnCode =
12817 +                                           CSMI_SAS_STATUS_SUCCESS;
12818 +                               else
12819 +                                       karg->IoctlHeader.ReturnCode =
12820 +                                           CSMI_SAS_STATUS_FAILED;
12821 +                               goto cim_sas_get_location_exit;
12822 +                       }
12823 +               }
12824 +       }
12825 +
12826 +       /* NON-RAID SUPPORT */
12827 +
12828 +       /* make sure there's enough room to populate the Location[] struct */
12829 +       if ((csmi_sas_get_location_sz -
12830 +           offsetof(CSMI_SAS_GET_LOCATION_BUFFER,Location)) <
12831 +           sizeof(CSMI_SAS_LOCATION_IDENTIFIER))
12832 +               goto cim_sas_get_location_exit;
12833 +
12834 +       karg->bNumberOfLocationIdentifiers=1; 
12835 +       karg->Location[0].bLocationFlags=0;
12836 +       if((mptctl_csmi_sas_fill_location_data(ioc, karg->bTargetId,
12837 +                  karg->bPathId, karg->bIdentify, &karg->Location[0])) == 0)
12838 +               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_SUCCESS;
12839 +       else
12840 +               karg->IoctlHeader.ReturnCode = CSMI_SAS_STATUS_FAILED;
12841 +
12842 +cim_sas_get_location_exit:
12843 +
12844 +       /* Copy the data from kernel memory to user memory
12845 +        */
12846 +       if (copy_to_user((char *)arg, karg, csmi_sas_get_location_sz)) {
12847 +               printk(KERN_ERR "%s@%d::%s() - "
12848 +                   "Unable to write out csmi_sas_get_location_buffer "
12849 +                   "@ %p\n",__FILE__, __LINE__, __FUNCTION__, uarg);
12850 +               return -EFAULT;
12851 +       }
12852 +
12853 +       kfree(karg);
12854 +       return 0;
12855 +}
12856 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/csmisas.h linux-2.6.9-55.0.12/drivers/message/fusion/csmisas.h
12857 --- linux-2.6.9-67.0.1/drivers/message/fusion/csmisas.h 1970-01-01 01:00:00.000000000 +0100
12858 +++ linux-2.6.9-55.0.12/drivers/message/fusion/csmisas.h        2007-11-02 09:10:23.000000000 +0100
12859 @@ -0,0 +1,1796 @@
12860 +/**************************************************************************
12861 +
12862 +Module Name:
12863 +
12864 +   CSMISAS.H
12865 +
12866 +
12867 +Abstract:
12868 +
12869 +   This file contains constants and data structure definitions used by drivers
12870 +   that support the Common Storage Management Interface specification for
12871 +   SAS or SATA in either the Windows or Linux.
12872 +
12873 +   This should be considered as a reference implementation only.  Changes may 
12874 +   be necessary to accommodate a specific build environment or target OS.
12875 +
12876 +Revision History:
12877 +
12878 +   001  SEF   8/12/03  Initial release.
12879 +   002  SEF   8/20/03  Cleanup to match documentation.
12880 +   003  SEF   9/12/03  Additional cleanup, created combined header
12881 +   004  SEF   9/23/03  Changed base types to match linux defaults
12882 +                       Added RAID signature
12883 +                       Added bControllerFlags to CSMI_SAS_CNTLR_CONFIG
12884 +                       Changed CSMI_SAS_BEGIN_PACK to 8 for common structures
12885 +                       Fixed other typos identified in first compilation test
12886 +   005  SEF  10/03/03  Additions to match first version of CSMI document
12887 +   006  SEF  10/14/03  Fixed typedef struct _CSMI_SAS_SMP_PASSTHRU_BUFFER
12888 +                       Added defines for bConnectionRate
12889 +   007  SEF  10/15/03  Added Firmware Download Control Code and support
12890 +                       Added CSMI revision support
12891 +   008  SEF  10/30/03  No functional change, just updated version to track
12892 +                       spec changes
12893 +   009  SEF  12/09/03  No functional change, just updated version to track
12894 +                       spec changes
12895 +   010  SEF   3/11/04  Fixed typedef struct CSMI_SAS_RAID_DRIVES to include the
12896 +                       bFirmware member that is defined in the spec, but
12897 +                       was missing in this file,
12898 +                       added CC_CSMI_SAS_TASK_MANAGEMENT
12899 +   011  SEF   4/02/04  No functional change, added comment line before
12900 +                       CC_CSMI_SAS_TASK_MANAGEMENT
12901 +   012  SEF   4/16/04  Added IOControllerNumber to linux header,
12902 +                       Modified linux control codes to have upper word of
12903 +                       0xCC77.... to indicate CSMI version 77
12904 +                       Added bSignalClass to CC_CSMI_SET_PHY_INFO
12905 +                       Added CC_CSMI_SAS_PHY_CONTROL support
12906 +   013  SEF   5/14/04  Added CC_CSMI_SAS_GET_CONNECTOR_INFO support
12907 +   014  SEF   5/24/04  No functional change, just updated version to track spec
12908 +                       changes
12909 +   015  SEF   6/16/04  changed bPinout to uPinout to reflect proper size,
12910 +                       changed width of bLocation defines to reflect size
12911 +   016  SEF   6/17/04  changed bLengthOfControls in CSMI_SAS_PHY_CONTROL
12912 +                       to be proper size
12913 +   017  SEF   9/17/04  added CSMI_SAS_SATA_PORT_SELECTOR,
12914 +                       CSMI_SAS_LINK_VIRTUAL, CSMI_SAS_CON_NOT_PRESENT, and
12915 +                       CSMI_SAS_CON_NOT_CONNECTED
12916 +   018  SEF   9/20/04  added CSMI_SAS_PHY_USER_PATTERN, 
12917 +                       changed definition of CSMI_SAS_PHY_FIXED_PATTERN to not
12918 +                       conflict with activate definition
12919 +   019  SEF  12/06/04  added CSMI_SAS_GET_LOCATION
12920 +                       added bSSPStatus to CSMI_SAS_SSP_PASSTHRU_STATUS 
12921 +                       structure
12922 +   020  SEF   5/25/05  added CSMI_SAS_PHY_VIRTUAL_SMP, and changes to 
12923 +                       CSMI_SAS_GET_LOCATION
12924 +   021  SEF  11/03/05  added new RAID creation functionality 
12925 +   022  SEF   2/01/06  corrected typo bNegotitiatedLInkRate
12926 +                       Added two more RAID_TYPES, 7 and 8
12927 +   023  SEF   4/04/06  added CSMI_RAID_TYPE_1E
12928 +                       changed structures that contained surface scan
12929 +                       to priority approach rather than time, causes
12930 +                       0.89 to incompatible with 0.87, so a version 
12931 +                       check is necessary when interpreting the 
12932 +                       raid structures
12933 +                       Added netware section
12934 +
12935 +**************************************************************************/
12936 +
12937 +#ifndef _CSMI_SAS_H_
12938 +#define _CSMI_SAS_H_
12939 +
12940 +// CSMI Specification Revision, the intent is that all versions of the
12941 +// specification will be backward compatible after the 1.00 release.
12942 +// Major revision number, corresponds to xxxx. of CSMI specification
12943 +// Minor revision number, corresponds to .xxxx of CSMI specification
12944 +#define CSMI_MAJOR_REVISION   0
12945 +#define CSMI_MINOR_REVISION   89
12946 +
12947 +/*************************************************************************/
12948 +/* PATCHES FOR TYPOS                                                     */
12949 +/*************************************************************************/
12950 +
12951 +#define bNegotitiatedLInkRate bNegotiatedLinkRate
12952 +
12953 +/*************************************************************************/
12954 +/* TARGET OS LINUX SPECIFIC CODE                                         */
12955 +/*************************************************************************/
12956 +
12957 +// EDM #ifdef _linux
12958 +#ifdef __KERNEL__
12959 +
12960 +// Linux base types
12961 +
12962 +#include <linux/types.h>
12963 +
12964 +#define __i8    char
12965 +
12966 +// pack definition
12967 +
12968 +// EDM #define CSMI_SAS_BEGIN_PACK(x)    pack(x)
12969 +// EDM #define CSMI_SAS_END_PACK         pack()
12970 +
12971 +// IOCTL Control Codes
12972 +// (IoctlHeader.ControlCode)
12973 +
12974 +// Control Codes prior to 0.77
12975 +
12976 +// Control Codes requiring CSMI_ALL_SIGNATURE
12977 +
12978 +// #define CC_CSMI_SAS_GET_DRIVER_INFO    0x12345678
12979 +// #define CC_CSMI_SAS_GET_CNTLR_CONFIG   0x23456781
12980 +// #define CC_CSMI_SAS_GET_CNTLR_STATUS   0x34567812
12981 +// #define CC_CSMI_SAS_FIRMWARE_DOWNLOAD  0x92345678
12982 +
12983 +// Control Codes requiring CSMI_RAID_SIGNATURE
12984 +
12985 +// #define CC_CSMI_SAS_GET_RAID_INFO      0x45678123
12986 +// #define CC_CSMI_SAS_GET_RAID_CONFIG    0x56781234
12987 +
12988 +// Control Codes requiring CSMI_SAS_SIGNATURE
12989 +
12990 +// #define CC_CSMI_SAS_GET_PHY_INFO       0x67812345
12991 +// #define CC_CSMI_SAS_SET_PHY_INFO       0x78123456
12992 +// #define CC_CSMI_SAS_GET_LINK_ERRORS    0x81234567
12993 +// #define CC_CSMI_SAS_SMP_PASSTHRU       0xA1234567
12994 +// #define CC_CSMI_SAS_SSP_PASSTHRU       0xB1234567
12995 +// #define CC_CSMI_SAS_STP_PASSTHRU       0xC1234567
12996 +// #define CC_CSMI_SAS_GET_SATA_SIGNATURE 0xD1234567
12997 +// #define CC_CSMI_SAS_GET_SCSI_ADDRESS   0xE1234567
12998 +// #define CC_CSMI_SAS_GET_DEVICE_ADDRESS 0xF1234567
12999 +// #define CC_CSMI_SAS_TASK_MANAGEMENT    0xA2345678
13000 +
13001 +// Control Codes for 0.77 and later
13002 +
13003 +// Control Codes requiring CSMI_ALL_SIGNATURE
13004 +
13005 +#define CC_CSMI_SAS_GET_DRIVER_INFO    0xCC770001
13006 +#define CC_CSMI_SAS_GET_CNTLR_CONFIG   0xCC770002
13007 +#define CC_CSMI_SAS_GET_CNTLR_STATUS   0xCC770003
13008 +#define CC_CSMI_SAS_FIRMWARE_DOWNLOAD  0xCC770004
13009 +
13010 +// Control Codes requiring CSMI_RAID_SIGNATURE
13011 +
13012 +#define CC_CSMI_SAS_GET_RAID_INFO      0xCC77000A
13013 +#define CC_CSMI_SAS_GET_RAID_CONFIG    0xCC77000B
13014 +#define CC_CSMI_SAS_GET_RAID_FEATURES  0xCC77000C
13015 +#define CC_CSMI_SAS_SET_RAID_CONTROL   0xCC77000D
13016 +#define CC_CSMI_SAS_GET_RAID_ELEMENT   0xCC77000E
13017 +#define CC_CSMI_SAS_SET_RAID_OPERATION 0xCC77000F
13018 +
13019 +// Control Codes requiring CSMI_SAS_SIGNATURE
13020 +
13021 +#define CC_CSMI_SAS_GET_PHY_INFO       0xCC770014
13022 +#define CC_CSMI_SAS_SET_PHY_INFO       0xCC770015
13023 +#define CC_CSMI_SAS_GET_LINK_ERRORS    0xCC770016
13024 +#define CC_CSMI_SAS_SMP_PASSTHRU       0xCC770017
13025 +#define CC_CSMI_SAS_SSP_PASSTHRU       0xCC770018
13026 +#define CC_CSMI_SAS_STP_PASSTHRU       0xCC770019
13027 +#define CC_CSMI_SAS_GET_SATA_SIGNATURE 0xCC770020
13028 +#define CC_CSMI_SAS_GET_SCSI_ADDRESS   0xCC770021
13029 +#define CC_CSMI_SAS_GET_DEVICE_ADDRESS 0xCC770022
13030 +#define CC_CSMI_SAS_TASK_MANAGEMENT    0xCC770023
13031 +#define CC_CSMI_SAS_GET_CONNECTOR_INFO 0xCC770024
13032 +#define CC_CSMI_SAS_GET_LOCATION       0xCC770025
13033 +
13034 +
13035 +// Control Codes requiring CSMI_PHY_SIGNATURE
13036 +
13037 +#define CC_CSMI_SAS_PHY_CONTROL        0xCC77003C
13038 +
13039 +// EDM #pragma CSMI_SAS_BEGIN_PACK(8)
13040 +#pragma pack(8)
13041 +
13042 +// IOCTL_HEADER
13043 +typedef struct _IOCTL_HEADER {
13044 +   __u32 IOControllerNumber;
13045 +    __u32 Length;
13046 +    __u32 ReturnCode;
13047 +    __u32 Timeout;
13048 +    __u16 Direction;
13049 +} IOCTL_HEADER, 
13050 +  *PIOCTL_HEADER;
13051 +
13052 +// EDM #pragma CSMI_SAS_END_PACK
13053 +#pragma pack()
13054 +
13055 +#endif
13056 +
13057 +/*************************************************************************/
13058 +/* TARGET OS WINDOWS SPECIFIC CODE                                       */
13059 +/*************************************************************************/
13060 +
13061 +#ifdef _WIN32
13062 +
13063 +// windows IOCTL definitions
13064 +
13065 +#ifndef _NTDDSCSIH_
13066 +#include <ntddscsi.h>
13067 +#endif
13068 +
13069 +// pack definition
13070 +
13071 +#if defined _MSC_VER
13072 +   #define CSMI_SAS_BEGIN_PACK(x)    pack(push,x)
13073 +   #define CSMI_SAS_END_PACK         pack(pop)
13074 +#elif defined __BORLANDC__
13075 +   #define CSMI_SAS_BEGIN_PACK(x)    option -a##x
13076 +   #define CSMI_SAS_END_PACK         option -a.
13077 +#else
13078 +   #error "CSMISAS.H - Must externally define a pack compiler designator."
13079 +#endif
13080 +
13081 +// base types
13082 +
13083 +#define __u8    unsigned char
13084 +#define __u16   unsigned short
13085 +#define __u32   unsigned long
13086 +#define __u64   unsigned __int64
13087 +
13088 +#define __i8    char
13089 +
13090 +// IOCTL Control Codes
13091 +// (IoctlHeader.ControlCode)
13092 +
13093 +// Control Codes requiring CSMI_ALL_SIGNATURE
13094 +
13095 +#define CC_CSMI_SAS_GET_DRIVER_INFO    1
13096 +#define CC_CSMI_SAS_GET_CNTLR_CONFIG   2
13097 +#define CC_CSMI_SAS_GET_CNTLR_STATUS   3
13098 +#define CC_CSMI_SAS_FIRMWARE_DOWNLOAD  4
13099 +
13100 +// Control Codes requiring CSMI_RAID_SIGNATURE
13101 +
13102 +#define CC_CSMI_SAS_GET_RAID_INFO      10
13103 +#define CC_CSMI_SAS_GET_RAID_CONFIG    11
13104 +#define CC_CSMI_SAS_GET_RAID_FEATURES  12
13105 +#define CC_CSMI_SAS_SET_RAID_CONTROL   13
13106 +#define CC_CSMI_SAS_GET_RAID_ELEMENT   14
13107 +#define CC_CSMI_SAS_SET_RAID_OPERATION 15
13108 +
13109 +// Control Codes requiring CSMI_SAS_SIGNATURE
13110 +
13111 +#define CC_CSMI_SAS_GET_PHY_INFO       20
13112 +#define CC_CSMI_SAS_SET_PHY_INFO       21
13113 +#define CC_CSMI_SAS_GET_LINK_ERRORS    22
13114 +#define CC_CSMI_SAS_SMP_PASSTHRU       23
13115 +#define CC_CSMI_SAS_SSP_PASSTHRU       24
13116 +#define CC_CSMI_SAS_STP_PASSTHRU       25
13117 +#define CC_CSMI_SAS_GET_SATA_SIGNATURE 26
13118 +#define CC_CSMI_SAS_GET_SCSI_ADDRESS   27
13119 +#define CC_CSMI_SAS_GET_DEVICE_ADDRESS 28
13120 +#define CC_CSMI_SAS_TASK_MANAGEMENT    29
13121 +#define CC_CSMI_SAS_GET_CONNECTOR_INFO 30
13122 +#define CC_CSMI_SAS_GET_LOCATION       31
13123 +
13124 +// Control Codes requiring CSMI_PHY_SIGNATURE
13125 +
13126 +#define CC_CSMI_SAS_PHY_CONTROL        60
13127 +
13128 +#define IOCTL_HEADER SRB_IO_CONTROL
13129 +#define PIOCTL_HEADER PSRB_IO_CONTROL
13130 +
13131 +#endif
13132 +
13133 +/*************************************************************************/
13134 +/* TARGET OS NETWARE SPECIFIC CODE                                       */
13135 +/*************************************************************************/
13136 +
13137 +#ifdef _NETWARE
13138 +
13139 +// NetWare IOCTL definitions
13140 +
13141 +#define CSMI_SAS_BEGIN_PACK(x)    pack(x)
13142 +#define CSMI_SAS_END_PACK         pack()
13143 +
13144 +#ifndef LONG
13145 +typedef unsigned long LONG;
13146 +#endif
13147 +
13148 +#ifndef WORD
13149 +typedef unsigned short WORD;
13150 +#endif
13151 +
13152 +#ifndef BYTE
13153 +typedef unsigned char BYTE;
13154 +#endif
13155 +
13156 +/* Need to have these definitions for Netware */
13157 +#define __u8    unsigned char
13158 +#define __u16   unsigned short
13159 +#define __u32   unsigned long
13160 +#define __u64   unsigned __int64
13161 +
13162 +#define __i8    char
13163 +
13164 +
13165 +#pragma CSMI_SAS_BEGIN_PACK(8)
13166 +
13167 +// IOCTL_HEADER
13168 +typedef struct _IOCTL_HEADER {
13169 +    __u32 Length;
13170 +    __u32 ReturnCode;
13171 +} IOCTL_HEADER, 
13172 +  *PIOCTL_HEADER;
13173 +
13174 +#pragma CSMI_SAS_END_PACK
13175 +
13176 +// IOCTL Control Codes
13177 +// (IoctlHeader.ControlCode)
13178 +
13179 +// Control Codes requiring CSMI_ALL_SIGNATURE
13180 +
13181 +#define CC_CSMI_SAS_GET_DRIVER_INFO    0x01FF0001
13182 +#define CC_CSMI_SAS_GET_CNTLR_CONFIG   0x01FF0002
13183 +#define CC_CSMI_SAS_GET_CNTLR_STATUS   0x01FF0003
13184 +#define CC_CSMI_SAS_FIRMWARE_DOWNLOAD  0x01FF0004
13185 +
13186 +// Control Codes requiring CSMI_RAID_SIGNATURE
13187 +
13188 +#define CC_CSMI_SAS_GET_RAID_INFO      0x01FF000A
13189 +#define CC_CSMI_SAS_GET_RAID_CONFIG    0x01FF000B
13190 +#define CC_CSMI_SAS_GET_RAID_FEATURES  0x01FF000C
13191 +#define CC_CSMI_SAS_SET_RAID_CONTROL   0x01FF000D
13192 +#define CC_CSMI_SAS_GET_RAID_ELEMENT   0x01FF000E
13193 +#define CC_CSMI_SAS_SET_RAID_OPERATION 0x01FF000F
13194 +
13195 +// Control Codes requiring CSMI_SAS_SIGNATURE
13196 +
13197 +#define CC_CSMI_SAS_GET_PHY_INFO       0x01FF0014
13198 +#define CC_CSMI_SAS_SET_PHY_INFO       0x01FF0015
13199 +#define CC_CSMI_SAS_GET_LINK_ERRORS    0x01FF0016
13200 +#define CC_CSMI_SAS_SMP_PASSTHRU       0x01FF0017
13201 +#define CC_CSMI_SAS_SSP_PASSTHRU       0x01FF0018
13202 +#define CC_CSMI_SAS_STP_PASSTHRU       0x01FF0019
13203 +#define CC_CSMI_SAS_GET_SATA_SIGNATURE 0x01FF001A
13204 +#define CC_CSMI_SAS_GET_SCSI_ADDRESS   0x01FF001B
13205 +#define CC_CSMI_SAS_GET_DEVICE_ADDRESS 0x01FF001C
13206 +#define CC_CSMI_SAS_TASK_MANAGEMENT    0x01FF001D
13207 +#define CC_CSMI_SAS_GET_CONNECTOR_INFO 0x01FF001E
13208 +#define CC_CSMI_SAS_GET_LOCATION       0x01FF001F
13209 +
13210 +// Control Codes requiring CSMI_PHY_SIGNATURE
13211 +
13212 +#define CC_CSMI_SAS_PHY_CONTROL        60
13213 +
13214 +#endif
13215 +
13216 +/*************************************************************************/
13217 +/* TARGET OS NOT DEFINED ERROR                                           */
13218 +/*************************************************************************/
13219 +
13220 +// EDM #if (!_WIN32 && !_linux && !_NETWARE)
13221 +//#if (!_WIN32 && !__KERNEL__ && !_NETWARE)
13222 +//   #error "Unknown target OS."
13223 +//#endif
13224 +
13225 +/*************************************************************************/
13226 +/* OS INDEPENDENT CODE                                                   */
13227 +/*************************************************************************/
13228 +
13229 +/* * * * * * * * * * Class Independent IOCTL Constants * * * * * * * * * */
13230 +
13231 +// Return codes for all IOCTL's regardless of class
13232 +// (IoctlHeader.ReturnCode)
13233 +
13234 +#define CSMI_SAS_STATUS_SUCCESS              0
13235 +#define CSMI_SAS_STATUS_FAILED               1
13236 +#define CSMI_SAS_STATUS_BAD_CNTL_CODE        2
13237 +#define CSMI_SAS_STATUS_INVALID_PARAMETER    3
13238 +#define CSMI_SAS_STATUS_WRITE_ATTEMPTED      4
13239 +
13240 +// Signature value
13241 +// (IoctlHeader.Signature)
13242 +
13243 +#define CSMI_ALL_SIGNATURE    "CSMIALL"
13244 +
13245 +// Timeout value default of 60 seconds
13246 +// (IoctlHeader.Timeout)
13247 +
13248 +#define CSMI_ALL_TIMEOUT      60
13249 +
13250 +//  Direction values for data flow on this IOCTL
13251 +// (IoctlHeader.Direction, Linux only)
13252 +#define CSMI_SAS_DATA_READ    0
13253 +#define CSMI_SAS_DATA_WRITE   1
13254 +
13255 +// I/O Bus Types
13256 +// ISA and EISA bus types are not supported
13257 +// (bIoBusType)
13258 +
13259 +#define CSMI_SAS_BUS_TYPE_PCI       3
13260 +#define CSMI_SAS_BUS_TYPE_PCMCIA    4
13261 +
13262 +// Controller Status
13263 +// (uStatus)
13264 +
13265 +#define CSMI_SAS_CNTLR_STATUS_GOOD     1
13266 +#define CSMI_SAS_CNTLR_STATUS_FAILED   2
13267 +#define CSMI_SAS_CNTLR_STATUS_OFFLINE  3
13268 +#define CSMI_SAS_CNTLR_STATUS_POWEROFF 4
13269 +
13270 +// Offline Status Reason
13271 +// (uOfflineReason)
13272 +
13273 +#define CSMI_SAS_OFFLINE_REASON_NO_REASON             0
13274 +#define CSMI_SAS_OFFLINE_REASON_INITIALIZING          1
13275 +#define CSMI_SAS_OFFLINE_REASON_BACKSIDE_BUS_DEGRADED 2
13276 +#define CSMI_SAS_OFFLINE_REASON_BACKSIDE_BUS_FAILURE  3
13277 +
13278 +// Controller Class
13279 +// (bControllerClass)
13280 +
13281 +#define CSMI_SAS_CNTLR_CLASS_HBA    5
13282 +
13283 +// Controller Flag bits
13284 +// (uControllerFlags)
13285 +
13286 +#define CSMI_SAS_CNTLR_SAS_HBA   0x00000001
13287 +#define CSMI_SAS_CNTLR_SAS_RAID  0x00000002
13288 +#define CSMI_SAS_CNTLR_SATA_HBA  0x00000004
13289 +#define CSMI_SAS_CNTLR_SATA_RAID 0x00000008
13290 +
13291 +// for firmware download
13292 +#define CSMI_SAS_CNTLR_FWD_SUPPORT  0x00010000
13293 +#define CSMI_SAS_CNTLR_FWD_ONLINE   0x00020000
13294 +#define CSMI_SAS_CNTLR_FWD_SRESET   0x00040000
13295 +#define CSMI_SAS_CNTLR_FWD_HRESET   0x00080000
13296 +#define CSMI_SAS_CNTLR_FWD_RROM     0x00100000
13297 +
13298 +// for RAID configuration supported
13299 +#define CSMI_SAS_CNTLR_RAID_CFG_SUPPORT  0x010000
13300 +
13301 +// Download Flag bits
13302 +// (uDownloadFlags)
13303 +#define CSMI_SAS_FWD_VALIDATE       0x00000001
13304 +#define CSMI_SAS_FWD_SOFT_RESET     0x00000002
13305 +#define CSMI_SAS_FWD_HARD_RESET     0x00000004
13306 +
13307 +// Firmware Download Status
13308 +// (usStatus)
13309 +#define CSMI_SAS_FWD_SUCCESS        0
13310 +#define CSMI_SAS_FWD_FAILED         1
13311 +#define CSMI_SAS_FWD_USING_RROM     2
13312 +#define CSMI_SAS_FWD_REJECT         3
13313 +#define CSMI_SAS_FWD_DOWNREV        4
13314 +
13315 +// Firmware Download Severity
13316 +// (usSeverity>
13317 +#define CSMI_SAS_FWD_INFORMATION    0
13318 +#define CSMI_SAS_FWD_WARNING        1
13319 +#define CSMI_SAS_FWD_ERROR          2
13320 +#define CSMI_SAS_FWD_FATAL          3
13321 +
13322 +/* * * * * * * * * * SAS RAID Class IOCTL Constants  * * * * * * * * */
13323 +
13324 +// Return codes for the RAID IOCTL's regardless of class
13325 +// (IoctlHeader.ReturnCode)
13326 +
13327 +#define CSMI_SAS_RAID_SET_OUT_OF_RANGE       1000
13328 +#define CSMI_SAS_RAID_SET_BUFFER_TOO_SMALL   1001
13329 +#define CSMI_SAS_RAID_SET_DATA_CHANGED       1002
13330 +
13331 +// Signature value
13332 +// (IoctlHeader.Signature)
13333 +
13334 +#define CSMI_RAID_SIGNATURE    "CSMIARY"
13335 +
13336 +// Timeout value default of 60 seconds
13337 +// (IoctlHeader.Timeout)
13338 +
13339 +#define CSMI_RAID_TIMEOUT      60
13340 +
13341 +// RAID Types
13342 +// (bRaidType)
13343 +#define CSMI_SAS_RAID_TYPE_NONE     0
13344 +#define CSMI_SAS_RAID_TYPE_0        1
13345 +#define CSMI_SAS_RAID_TYPE_1        2
13346 +#define CSMI_SAS_RAID_TYPE_10       3
13347 +#define CSMI_SAS_RAID_TYPE_5        4
13348 +#define CSMI_SAS_RAID_TYPE_15       5
13349 +#define CSMI_SAS_RAID_TYPE_6        6
13350 +#define CSMI_SAS_RAID_TYPE_50       7
13351 +#define CSMI_SAS_RAID_TYPE_VOLUME   8
13352 +#define CSMI_SAS_RAID_TYPE_1E       9
13353 +#define CSMI_SAS_RAID_TYPE_OTHER    255
13354 +// the last value 255 was already defined for other
13355 +// so end is defined as 254
13356 +#define CSMI_SAS_RAID_TYPE_END      254
13357 +
13358 +// RAID Status
13359 +// (bStatus)
13360 +#define CSMI_SAS_RAID_SET_STATUS_OK             0
13361 +#define CSMI_SAS_RAID_SET_STATUS_DEGRADED       1
13362 +#define CSMI_SAS_RAID_SET_STATUS_REBUILDING     2
13363 +#define CSMI_SAS_RAID_SET_STATUS_FAILED         3
13364 +#define CSMI_SAS_RAID_SET_STATUS_OFFLINE        4
13365 +#define CSMI_SAS_RAID_SET_STATUS_TRANSFORMING   5
13366 +#define CSMI_SAS_RAID_SET_STATUS_QUEUED_FOR_REBUILD         6
13367 +#define CSMI_SAS_RAID_SET_STATUS_QUEUED_FOR_TRANSFORMATION  7
13368 +
13369 +// RAID Drive Count
13370 +// (bDriveCount, 0xF1 to 0xFF are reserved)
13371 +#define CSMI_SAS_RAID_DRIVE_COUNT_TOO_BIG   0xF1
13372 +#define CSMI_SAS_RAID_DRIVE_COUNT_SUPRESSED 0xF2
13373 +
13374 +// RAID Data Type
13375 +// (bDataType)
13376 +#define CSMI_SAS_RAID_DATA_DRIVES           0
13377 +#define CSMI_SAS_RAID_DATA_DEVICE_ID        1
13378 +#define CSMI_SAS_RAID_DATA_ADDITIONAL_DATA  2
13379 +
13380 +// RAID Drive Status
13381 +// (bDriveStatus)
13382 +#define CSMI_SAS_DRIVE_STATUS_OK          0
13383 +#define CSMI_SAS_DRIVE_STATUS_REBUILDING  1
13384 +#define CSMI_SAS_DRIVE_STATUS_FAILED      2
13385 +#define CSMI_SAS_DRIVE_STATUS_DEGRADED    3
13386 +#define CSMI_SAS_DRIVE_STATUS_OFFLINE     4
13387 +#define CSMI_SAS_DRIVE_STATUS_QUEUED_FOR_REBUILD 5
13388 +
13389 +// RAID Drive Usage
13390 +// (bDriveUsage)
13391 +#define CSMI_SAS_DRIVE_CONFIG_NOT_USED      0
13392 +#define CSMI_SAS_DRIVE_CONFIG_MEMBER        1
13393 +#define CSMI_SAS_DRIVE_CONFIG_SPARE         2
13394 +#define CSMI_SAS_DRIVE_CONFIG_SPARE_ACTIVE  3
13395 +
13396 +// RAID Drive Type
13397 +// (bDriveType)
13398 +#define CSMI_SAS_DRIVE_TYPE_UNKNOWN         0
13399 +#define CSMI_SAS_DRIVE_TYPE_SINGLE_PORT_SAS 1
13400 +#define CSMI_SAS_DRIVE_TYPE_DUAL_PORT_SAS   2
13401 +#define CSMI_SAS_DRIVE_TYPE_SATA            3
13402 +#define CSMI_SAS_DRIVE_TYPE_SATA_PS         4
13403 +#define CSMI_SAS_DRIVE_TYPE_OTHER           255
13404 +
13405 +// RAID Write Protect
13406 +// (bWriteProtect)
13407 +#define CSMI_SAS_RAID_SET_WRITE_PROTECT_UNKNOWN     0
13408 +#define CSMI_SAS_RAID_SET_WRITE_PROTECT_UNCHANGED   0
13409 +#define CSMI_SAS_RAID_SET_WRITE_PROTECT_ENABLED     1
13410 +#define CSMI_SAS_RAID_SET_WRITE_PROTECT_DISABLED    2
13411 +
13412 +// RAID Cache Setting
13413 +// (bCacheSetting)
13414 +#define CSMI_SAS_RAID_SET_CACHE_UNKNOWN             0
13415 +#define CSMI_SAS_RAID_SET_CACHE_UNCHANGED           0
13416 +#define CSMI_SAS_RAID_SET_CACHE_ENABLED             1
13417 +#define CSMI_SAS_RAID_SET_CACHE_DISABLED            2
13418 +#define CSMI_SAS_RAID_SET_CACHE_CORRUPT             3
13419 +
13420 +// RAID Features
13421 +// (uFeatures)
13422 +#define CSMI_SAS_RAID_FEATURE_TRANSFORMATION    0x00000001
13423 +#define CSMI_SAS_RAID_FEATURE_REBUILD           0x00000002
13424 +#define CSMI_SAS_RAID_FEATURE_SPLIT_MIRROR      0x00000004
13425 +#define CSMI_SAS_RAID_FEATURE_MERGE_MIRROR      0x00000008
13426 +#define CSMI_SAS_RAID_FEATURE_LUN_RENUMBER      0x00000010
13427 +#define CSMI_SAS_RAID_FEATURE_SURFACE_SCAN      0x00000020
13428 +#define CSMI_SAS_RAID_FEATURE_SPARES_SHARED     0x00000040
13429 +
13430 +// RAID Priority
13431 +// (bDefaultTransformPriority, etc.)
13432 +#define CSMI_SAS_PRIORITY_UNKNOWN   0
13433 +#define CSMI_SAS_PRIORITY_UNCHANGED 0
13434 +#define CSMI_SAS_PRIORITY_AUTO      1
13435 +#define CSMI_SAS_PRIORITY_OFF       2
13436 +#define CSMI_SAS_PRIORITY_LOW       3
13437 +#define CSMI_SAS_PRIORITY_MEDIUM    4
13438 +#define CSMI_SAS_PRIORITY_HIGH      5
13439 +
13440 +// RAID Transformation Rules
13441 +// (uRaidSetTransformationRules)
13442 +#define CSMI_SAS_RAID_RULE_AVAILABLE_MEMORY     0x00000001
13443 +#define CSMI_SAS_RAID_RULE_OVERLAPPED_EXTENTS   0x00000002
13444 +
13445 +// RAID Cache Ratios Supported
13446 +// (bCacheRatiosSupported)
13447 +// from 0 to 100 defines the write to read ratio, 0 is 100% write
13448 +#define CSMI_SAS_RAID_CACHE_RATIO_RANGE     101
13449 +#define CSMI_SAS_RAID_CACHE_RATIO_FIXED     102
13450 +#define CSMI_SAS_RAID_CACHE_RATIO_AUTO      103
13451 +#define CSMI_SAS_RAID_CACHE_RATIO_END       255
13452 +
13453 +// RAID Cache Ratio Flag
13454 +// (bCacheRatioFlag)
13455 +#define CSMI_SAS_RAID_CACHE_RATIO_DISABLE   0
13456 +#define CSMI_SAS_RAID_CACHE_RATIO_ENABLE    1
13457 +
13458 +// RAID Clear Configuration Signature
13459 +// (bClearConfiguration)
13460 +#define CSMI_SAS_RAID_CLEAR_CONFIGURATION_SIGNATURE "RAIDCLR"
13461 +
13462 +// RAID Failure Codes
13463 +// (uFailCode)
13464 +#define CSMI_SAS_FAIL_CODE_OK                           0
13465 +#define CSMI_SAS_FAIL_CODE_PARAMETER_INVALID            1000
13466 +#define CSMI_SAS_FAIL_CODE_TRANSFORM_PRIORITY_INVALID   1001
13467 +#define CSMI_SAS_FAIL_CODE_REBUILD_PRIORITY_INVALID     1002
13468 +#define CSMI_SAS_FAIL_CODE_CACHE_RATIO_INVALID          1003
13469 +#define CSMI_SAS_FAIL_CODE_SURFACE_SCAN_INVALID         1004
13470 +#define CSMI_SAS_FAIL_CODE_CLEAR_CONFIGURATION_INVALID  1005
13471 +#define CSMI_SAS_FAIL_CODE_ELEMENT_INDEX_INVALID        1006
13472 +#define CSMI_SAS_FAIL_CODE_SUBELEMENT_INDEX_INVALID     1007
13473 +#define CSMI_SAS_FAIL_CODE_EXTENT_INVALID               1008
13474 +#define CSMI_SAS_FAIL_CODE_BLOCK_COUNT_INVALID          1009
13475 +#define CSMI_SAS_FAIL_CODE_DRIVE_INDEX_INVALID          1010
13476 +#define CSMI_SAS_FAIL_CODE_EXISTING_LUN_INVALID         1011
13477 +#define CSMI_SAS_FAIL_CODE_RAID_TYPE_INVALID            1012
13478 +#define CSMI_SAS_FAIL_CODE_STRIPE_SIZE_INVALID          1013
13479 +#define CSMI_SAS_FAIL_CODE_TRANSFORMATION_INVALID       1014
13480 +#define CSMI_SAS_FAIL_CODE_CHANGE_COUNT_INVALID         1015
13481 +#define CSMI_SAS_FAIL_CODE_ENUMERATION_TYPE_INVALID     1016
13482 +
13483 +#define CSMI_SAS_FAIL_CODE_EXCEEDED_RAID_SET_COUNT      2000
13484 +#define CSMI_SAS_FAIL_CODE_DUPLICATE_LUN                2001
13485 +
13486 +#define CSMI_SAS_FAIL_CODE_WAIT_FOR_OPERATION           3000
13487 +
13488 +// RAID Enumeration Types
13489 +// (uEnumerationType)
13490 +#define CSMI_SAS_RAID_ELEMENT_TYPE_DRIVE                0
13491 +#define CSMI_SAS_RAID_ELEMENT_TYPE_MODULE               1
13492 +#define CSMI_SAS_RAID_ELEMENT_TYPE_DRIVE_RAID_SET       2
13493 +#define CSMI_SAS_RAID_ELEMENT_TYPE_EXTENT_DRIVE         3
13494 +
13495 +// RAID Extent Types
13496 +// (bExtentType)
13497 +#define CSMI_SAS_RAID_EXTENT_RESERVED       0
13498 +#define CSMI_SAS_RAID_EXTENT_METADATA       1
13499 +#define CSMI_SAS_RAID_EXTENT_ALLOCATED      2
13500 +#define CSMI_SAS_RAID_EXTENT_UNALLOCATED    3
13501 +
13502 +// RAID Operation Types
13503 +// (uOperationType)
13504 +#define CSMI_SAS_RAID_SET_CREATE            0
13505 +#define CSMI_SAS_RAID_SET_LABEL             1
13506 +#define CSMI_SAS_RAID_SET_TRANSFORM         2
13507 +#define CSMI_SAS_RAID_SET_DELETE            3
13508 +#define CSMI_SAS_RAID_SET_WRITE_PROTECT     4
13509 +#define CSMI_SAS_RAID_SET_CACHE             5
13510 +#define CSMI_SAS_RAID_SET_ONLINE_STATE      6
13511 +#define CSMI_SAS_RAID_SET_SPARE             7
13512 +
13513 +// RAID Transform Types
13514 +// (bTransformType)
13515 +#define CSMI_SAS_RAID_SET_TRANSFORM_SPLIT_MIRROR    0
13516 +#define CSMI_SAS_RAID_SET_TRANSFORM_MERGE_RAID_0    1
13517 +#define CSMI_SAS_RAID_SET_TRANSFORM_LUN_RENUMBER    2
13518 +#define CSMI_SAS_RAID_SET_TRANSFORM_RAID_SET        3
13519 +
13520 +// RAID Online State
13521 +// (bOnlineState)
13522 +#define CSMI_SAS_RAID_SET_STATE_UNKNOWN     0
13523 +#define CSMI_SAS_RAID_SET_STATE_ONLINE      1
13524 +#define CSMI_SAS_RAID_SET_STATE_OFFLINE     2
13525 +
13526 +/* * * * * * * * * * SAS HBA Class IOCTL Constants * * * * * * * * * */
13527 +
13528 +// Return codes for SAS IOCTL's
13529 +// (IoctlHeader.ReturnCode)
13530 +
13531 +#define CSMI_SAS_PHY_INFO_CHANGED            CSMI_SAS_STATUS_SUCCESS
13532 +#define CSMI_SAS_PHY_INFO_NOT_CHANGEABLE     2000
13533 +#define CSMI_SAS_LINK_RATE_OUT_OF_RANGE      2001
13534 +
13535 +#define CSMI_SAS_PHY_DOES_NOT_EXIST          2002
13536 +#define CSMI_SAS_PHY_DOES_NOT_MATCH_PORT     2003
13537 +#define CSMI_SAS_PHY_CANNOT_BE_SELECTED      2004
13538 +#define CSMI_SAS_SELECT_PHY_OR_PORT          2005
13539 +#define CSMI_SAS_PORT_DOES_NOT_EXIST         2006
13540 +#define CSMI_SAS_PORT_CANNOT_BE_SELECTED     2007
13541 +#define CSMI_SAS_CONNECTION_FAILED           2008
13542 +
13543 +#define CSMI_SAS_NO_SATA_DEVICE              2009
13544 +#define CSMI_SAS_NO_SATA_SIGNATURE           2010
13545 +#define CSMI_SAS_SCSI_EMULATION              2011
13546 +#define CSMI_SAS_NOT_AN_END_DEVICE           2012
13547 +#define CSMI_SAS_NO_SCSI_ADDRESS             2013
13548 +#define CSMI_SAS_NO_DEVICE_ADDRESS           2014
13549 +
13550 +// Signature value
13551 +// (IoctlHeader.Signature)
13552 +
13553 +#define CSMI_SAS_SIGNATURE    "CSMISAS"
13554 +
13555 +// Timeout value default of 60 seconds
13556 +// (IoctlHeader.Timeout)
13557 +
13558 +#define CSMI_SAS_TIMEOUT      60
13559 +
13560 +// Device types
13561 +// (bDeviceType)
13562 +
13563 +#define CSMI_SAS_PHY_UNUSED               0x00
13564 +#define CSMI_SAS_NO_DEVICE_ATTACHED       0x00
13565 +#define CSMI_SAS_END_DEVICE               0x10
13566 +#define CSMI_SAS_EDGE_EXPANDER_DEVICE     0x20
13567 +#define CSMI_SAS_FANOUT_EXPANDER_DEVICE   0x30
13568 +
13569 +// Protocol options
13570 +// (bInitiatorPortProtocol, bTargetPortProtocol)
13571 +
13572 +#define CSMI_SAS_PROTOCOL_SATA   0x01
13573 +#define CSMI_SAS_PROTOCOL_SMP    0x02
13574 +#define CSMI_SAS_PROTOCOL_STP    0x04
13575 +#define CSMI_SAS_PROTOCOL_SSP    0x08
13576 +
13577 +// Negotiated and hardware link rates
13578 +// (bNegotiatedLinkRate, bMinimumLinkRate, bMaximumLinkRate)
13579 +
13580 +#define CSMI_SAS_LINK_RATE_UNKNOWN  0x00
13581 +#define CSMI_SAS_PHY_DISABLED       0x01
13582 +#define CSMI_SAS_LINK_RATE_FAILED   0x02
13583 +#define CSMI_SAS_SATA_SPINUP_HOLD   0x03
13584 +#define CSMI_SAS_SATA_PORT_SELECTOR 0x04
13585 +#define CSMI_SAS_LINK_RATE_1_5_GBPS 0x08
13586 +#define CSMI_SAS_LINK_RATE_3_0_GBPS 0x09
13587 +#define CSMI_SAS_LINK_VIRTUAL       0x10
13588 +
13589 +// Discover state
13590 +// (bAutoDiscover)
13591 +
13592 +#define CSMI_SAS_DISCOVER_NOT_SUPPORTED   0x00
13593 +#define CSMI_SAS_DISCOVER_NOT_STARTED     0x01
13594 +#define CSMI_SAS_DISCOVER_IN_PROGRESS     0x02
13595 +#define CSMI_SAS_DISCOVER_COMPLETE        0x03
13596 +#define CSMI_SAS_DISCOVER_ERROR           0x04
13597 +
13598 +// Phy features
13599 +
13600 +#define CSMI_SAS_PHY_VIRTUAL_SMP          0x01
13601 +
13602 +// Programmed link rates
13603 +// (bMinimumLinkRate, bMaximumLinkRate)
13604 +// (bProgrammedMinimumLinkRate, bProgrammedMaximumLinkRate)
13605 +
13606 +#define CSMI_SAS_PROGRAMMED_LINK_RATE_UNCHANGED 0x00
13607 +#define CSMI_SAS_PROGRAMMED_LINK_RATE_1_5_GBPS  0x08
13608 +#define CSMI_SAS_PROGRAMMED_LINK_RATE_3_0_GBPS  0x09
13609 +
13610 +// Link rate
13611 +// (bNegotiatedLinkRate in CSMI_SAS_SET_PHY_INFO)
13612 +
13613 +#define CSMI_SAS_LINK_RATE_NEGOTIATE      0x00
13614 +#define CSMI_SAS_LINK_RATE_PHY_DISABLED   0x01
13615 +
13616 +// Signal class
13617 +// (bSignalClass in CSMI_SAS_SET_PHY_INFO)
13618 +
13619 +#define CSMI_SAS_SIGNAL_CLASS_UNKNOWN     0x00
13620 +#define CSMI_SAS_SIGNAL_CLASS_DIRECT      0x01
13621 +#define CSMI_SAS_SIGNAL_CLASS_SERVER      0x02
13622 +#define CSMI_SAS_SIGNAL_CLASS_ENCLOSURE   0x03
13623 +
13624 +// Link error reset
13625 +// (bResetCounts)
13626 +
13627 +#define CSMI_SAS_LINK_ERROR_DONT_RESET_COUNTS   0x00
13628 +#define CSMI_SAS_LINK_ERROR_RESET_COUNTS        0x01
13629 +
13630 +// Phy identifier
13631 +// (bPhyIdentifier)
13632 +
13633 +#define CSMI_SAS_USE_PORT_IDENTIFIER   0xFF
13634 +
13635 +// Port identifier
13636 +// (bPortIdentifier)
13637 +
13638 +#define CSMI_SAS_IGNORE_PORT           0xFF
13639 +
13640 +// Programmed link rates
13641 +// (bConnectionRate)
13642 +
13643 +#define CSMI_SAS_LINK_RATE_NEGOTIATED  0x00
13644 +#define CSMI_SAS_LINK_RATE_1_5_GBPS    0x08
13645 +#define CSMI_SAS_LINK_RATE_3_0_GBPS    0x09
13646 +
13647 +// Connection status
13648 +// (bConnectionStatus)
13649 +
13650 +#define CSMI_SAS_OPEN_ACCEPT                          0
13651 +#define CSMI_SAS_OPEN_REJECT_BAD_DESTINATION          1
13652 +#define CSMI_SAS_OPEN_REJECT_RATE_NOT_SUPPORTED       2
13653 +#define CSMI_SAS_OPEN_REJECT_NO_DESTINATION           3
13654 +#define CSMI_SAS_OPEN_REJECT_PATHWAY_BLOCKED          4
13655 +#define CSMI_SAS_OPEN_REJECT_PROTOCOL_NOT_SUPPORTED   5
13656 +#define CSMI_SAS_OPEN_REJECT_RESERVE_ABANDON          6
13657 +#define CSMI_SAS_OPEN_REJECT_RESERVE_CONTINUE         7
13658 +#define CSMI_SAS_OPEN_REJECT_RESERVE_INITIALIZE       8
13659 +#define CSMI_SAS_OPEN_REJECT_RESERVE_STOP             9
13660 +#define CSMI_SAS_OPEN_REJECT_RETRY                    10
13661 +#define CSMI_SAS_OPEN_REJECT_STP_RESOURCES_BUSY       11
13662 +#define CSMI_SAS_OPEN_REJECT_WRONG_DESTINATION        12
13663 +
13664 +// SSP Status
13665 +// (bSSPStatus)
13666 +
13667 +#define CSMI_SAS_SSP_STATUS_UNKNOWN     0x00
13668 +#define CSMI_SAS_SSP_STATUS_WAITING     0x01
13669 +#define CSMI_SAS_SSP_STATUS_COMPLETED   0x02
13670 +#define CSMI_SAS_SSP_STATUS_FATAL_ERROR 0x03
13671 +#define CSMI_SAS_SSP_STATUS_RETRY       0x04
13672 +#define CSMI_SAS_SSP_STATUS_NO_TAG      0x05
13673 +
13674 +// SSP Flags
13675 +// (uFlags)
13676 +
13677 +#define CSMI_SAS_SSP_READ           0x00000001
13678 +#define CSMI_SAS_SSP_WRITE          0x00000002
13679 +#define CSMI_SAS_SSP_UNSPECIFIED    0x00000004
13680 +
13681 +#define CSMI_SAS_SSP_TASK_ATTRIBUTE_SIMPLE         0x00000000
13682 +#define CSMI_SAS_SSP_TASK_ATTRIBUTE_HEAD_OF_QUEUE  0x00000010
13683 +#define CSMI_SAS_SSP_TASK_ATTRIBUTE_ORDERED        0x00000020
13684 +#define CSMI_SAS_SSP_TASK_ATTRIBUTE_ACA            0x00000040
13685 +
13686 +// SSP Data present
13687 +// (bDataPresent)
13688 +
13689 +#define CSMI_SAS_SSP_NO_DATA_PRESENT         0x00
13690 +#define CSMI_SAS_SSP_RESPONSE_DATA_PRESENT   0x01
13691 +#define CSMI_SAS_SSP_SENSE_DATA_PRESENT      0x02
13692 +
13693 +// STP Flags
13694 +// (uFlags)
13695 +
13696 +#define CSMI_SAS_STP_READ           0x00000001
13697 +#define CSMI_SAS_STP_WRITE          0x00000002
13698 +#define CSMI_SAS_STP_UNSPECIFIED    0x00000004
13699 +#define CSMI_SAS_STP_PIO            0x00000010
13700 +#define CSMI_SAS_STP_DMA            0x00000020
13701 +#define CSMI_SAS_STP_PACKET         0x00000040
13702 +#define CSMI_SAS_STP_DMA_QUEUED     0x00000080
13703 +#define CSMI_SAS_STP_EXECUTE_DIAG   0x00000100
13704 +#define CSMI_SAS_STP_RESET_DEVICE   0x00000200
13705 +
13706 +// Task Management Flags
13707 +// (uFlags)
13708 +
13709 +#define CSMI_SAS_TASK_IU               0x00000001
13710 +#define CSMI_SAS_HARD_RESET_SEQUENCE   0x00000002
13711 +#define CSMI_SAS_SUPPRESS_RESULT       0x00000004
13712 +
13713 +// Task Management Functions
13714 +// (bTaskManagement)
13715 +
13716 +#define CSMI_SAS_SSP_ABORT_TASK           0x01
13717 +#define CSMI_SAS_SSP_ABORT_TASK_SET       0x02
13718 +#define CSMI_SAS_SSP_CLEAR_TASK_SET       0x04
13719 +#define CSMI_SAS_SSP_LOGICAL_UNIT_RESET   0x08
13720 +#define CSMI_SAS_SSP_CLEAR_ACA            0x40
13721 +#define CSMI_SAS_SSP_QUERY_TASK           0x80
13722 +
13723 +// Task Management Information
13724 +// (uInformation)
13725 +
13726 +#define CSMI_SAS_SSP_TEST           1
13727 +#define CSMI_SAS_SSP_EXCEEDED       2
13728 +#define CSMI_SAS_SSP_DEMAND         3
13729 +#define CSMI_SAS_SSP_TRIGGER        4
13730 +
13731 +// Connector Pinout Information
13732 +// (uPinout)
13733 +
13734 +#define CSMI_SAS_CON_UNKNOWN              0x00000001
13735 +#define CSMI_SAS_CON_SFF_8482             0x00000002
13736 +#define CSMI_SAS_CON_SFF_8470_LANE_1      0x00000100
13737 +#define CSMI_SAS_CON_SFF_8470_LANE_2      0x00000200
13738 +#define CSMI_SAS_CON_SFF_8470_LANE_3      0x00000400
13739 +#define CSMI_SAS_CON_SFF_8470_LANE_4      0x00000800
13740 +#define CSMI_SAS_CON_SFF_8484_LANE_1      0x00010000
13741 +#define CSMI_SAS_CON_SFF_8484_LANE_2      0x00020000
13742 +#define CSMI_SAS_CON_SFF_8484_LANE_3      0x00040000
13743 +#define CSMI_SAS_CON_SFF_8484_LANE_4      0x00080000
13744 +
13745 +// Connector Location Information
13746 +// (bLocation)
13747 +
13748 +// same as uPinout above...
13749 +// #define CSMI_SAS_CON_UNKNOWN              0x01
13750 +#define CSMI_SAS_CON_INTERNAL             0x02
13751 +#define CSMI_SAS_CON_EXTERNAL             0x04
13752 +#define CSMI_SAS_CON_SWITCHABLE           0x08
13753 +#define CSMI_SAS_CON_AUTO                 0x10
13754 +#define CSMI_SAS_CON_NOT_PRESENT          0x20
13755 +#define CSMI_SAS_CON_NOT_CONNECTED        0x80
13756 +
13757 +// Device location identification
13758 +// (bIdentify)
13759 +
13760 +#define CSMI_SAS_LOCATE_UNKNOWN           0x00
13761 +#define CSMI_SAS_LOCATE_FORCE_OFF         0x01
13762 +#define CSMI_SAS_LOCATE_FORCE_ON          0x02
13763 +
13764 +// Location Valid flags
13765 +// (uLocationFlags)
13766 +
13767 +#define CSMI_SAS_LOCATE_SAS_ADDRESS_VALID           0x00000001
13768 +#define CSMI_SAS_LOCATE_SAS_LUN_VALID               0x00000002
13769 +#define CSMI_SAS_LOCATE_ENCLOSURE_IDENTIFIER_VALID  0x00000004
13770 +#define CSMI_SAS_LOCATE_ENCLOSURE_NAME_VALID        0x00000008
13771 +#define CSMI_SAS_LOCATE_BAY_PREFIX_VALID            0x00000010
13772 +#define CSMI_SAS_LOCATE_BAY_IDENTIFIER_VALID        0x00000020
13773 +#define CSMI_SAS_LOCATE_LOCATION_STATE_VALID        0x00000040
13774 +
13775 +/* * * * * * * * SAS Phy Control Class IOCTL Constants * * * * * * * * */
13776 +
13777 +// Return codes for SAS Phy Control IOCTL's
13778 +// (IoctlHeader.ReturnCode)
13779 +
13780 +// Signature value
13781 +// (IoctlHeader.Signature)
13782 +
13783 +#define CSMI_PHY_SIGNATURE    "CSMIPHY"
13784 +
13785 +// Phy Control Functions
13786 +// (bFunction)
13787 +
13788 +// values 0x00 to 0xFF are consistent in definition with the SMP PHY CONTROL 
13789 +// function defined in the SAS spec
13790 +#define CSMI_SAS_PC_NOP                   0x00000000
13791 +#define CSMI_SAS_PC_LINK_RESET            0x00000001
13792 +#define CSMI_SAS_PC_HARD_RESET            0x00000002
13793 +#define CSMI_SAS_PC_PHY_DISABLE           0x00000003
13794 +// 0x04 to 0xFF reserved...
13795 +#define CSMI_SAS_PC_GET_PHY_SETTINGS      0x00000100
13796 +
13797 +// Link Flags
13798 +#define CSMI_SAS_PHY_ACTIVATE_CONTROL     0x00000001
13799 +#define CSMI_SAS_PHY_UPDATE_SPINUP_RATE   0x00000002
13800 +#define CSMI_SAS_PHY_AUTO_COMWAKE         0x00000004
13801 +
13802 +// Device Types for Phy Settings
13803 +// (bType)
13804 +#define CSMI_SAS_UNDEFINED 0x00
13805 +#define CSMI_SAS_SATA      0x01
13806 +#define CSMI_SAS_SAS       0x02
13807 +
13808 +// Transmitter Flags
13809 +// (uTransmitterFlags)
13810 +#define CSMI_SAS_PHY_PREEMPHASIS_DISABLED    0x00000001
13811 +
13812 +// Receiver Flags
13813 +// (uReceiverFlags)
13814 +#define CSMI_SAS_PHY_EQUALIZATION_DISABLED   0x00000001
13815 +
13816 +// Pattern Flags
13817 +// (uPatternFlags)
13818 +// #define CSMI_SAS_PHY_ACTIVATE_CONTROL     0x00000001
13819 +#define CSMI_SAS_PHY_DISABLE_SCRAMBLING      0x00000002
13820 +#define CSMI_SAS_PHY_DISABLE_ALIGN           0x00000004
13821 +#define CSMI_SAS_PHY_DISABLE_SSC             0x00000008
13822 +
13823 +#define CSMI_SAS_PHY_FIXED_PATTERN           0x00000010
13824 +#define CSMI_SAS_PHY_USER_PATTERN            0x00000020
13825 +
13826 +// Fixed Patterns
13827 +// (bFixedPattern)
13828 +#define CSMI_SAS_PHY_CJPAT                   0x00000001
13829 +#define CSMI_SAS_PHY_ALIGN                   0x00000002
13830 +
13831 +// Type Flags
13832 +// (bTypeFlags)
13833 +#define CSMI_SAS_PHY_POSITIVE_DISPARITY      0x01
13834 +#define CSMI_SAS_PHY_NEGATIVE_DISPARITY      0x02
13835 +#define CSMI_SAS_PHY_CONTROL_CHARACTER       0x04
13836 +
13837 +// Miscellaneous
13838 +#define SLOT_NUMBER_UNKNOWN   0xFFFF
13839 +
13840 +/*************************************************************************/
13841 +/* DATA STRUCTURES                                                       */
13842 +/*************************************************************************/
13843 +
13844 +/* * * * * * * * * * Class Independent Structures * * * * * * * * * */
13845 +
13846 +// EDM #pragma CSMI_SAS_BEGIN_PACK(8)
13847 +#pragma pack(8)
13848 +
13849 +// CC_CSMI_SAS_DRIVER_INFO
13850 +
13851 +typedef struct _CSMI_SAS_DRIVER_INFO {
13852 +   __u8  szName[81];
13853 +   __u8  szDescription[81];
13854 +   __u16 usMajorRevision;
13855 +   __u16 usMinorRevision;
13856 +   __u16 usBuildRevision;
13857 +   __u16 usReleaseRevision;
13858 +   __u16 usCSMIMajorRevision;
13859 +   __u16 usCSMIMinorRevision;
13860 +} CSMI_SAS_DRIVER_INFO,
13861 +  *PCSMI_SAS_DRIVER_INFO;
13862 +
13863 +typedef struct _CSMI_SAS_DRIVER_INFO_BUFFER {
13864 +   IOCTL_HEADER IoctlHeader;
13865 +   CSMI_SAS_DRIVER_INFO Information;
13866 +} CSMI_SAS_DRIVER_INFO_BUFFER,
13867 +  *PCSMI_SAS_DRIVER_INFO_BUFFER;
13868 +
13869 +// CC_CSMI_SAS_CNTLR_CONFIGURATION
13870 +
13871 +typedef struct _CSMI_SAS_PCI_BUS_ADDRESS {
13872 +   __u8  bBusNumber;
13873 +   __u8  bDeviceNumber;
13874 +   __u8  bFunctionNumber;
13875 +   __u8  bReserved;
13876 +} CSMI_SAS_PCI_BUS_ADDRESS,
13877 +  *PCSMI_SAS_PCI_BUS_ADDRESS;
13878 +
13879 +typedef union _CSMI_SAS_IO_BUS_ADDRESS {
13880 +   CSMI_SAS_PCI_BUS_ADDRESS PciAddress;
13881 +   __u8  bReserved[32];
13882 +} CSMI_SAS_IO_BUS_ADDRESS,
13883 +  *PCSMI_SAS_IO_BUS_ADDRESS;
13884 +
13885 +typedef struct _CSMI_SAS_CNTLR_CONFIG {
13886 +   __u32 uBaseIoAddress;
13887 +   struct {
13888 +      __u32 uLowPart;
13889 +      __u32 uHighPart;
13890 +   } BaseMemoryAddress;
13891 +   __u32 uBoardID;
13892 +   __u16 usSlotNumber;
13893 +   __u8  bControllerClass;
13894 +   __u8  bIoBusType;
13895 +   CSMI_SAS_IO_BUS_ADDRESS BusAddress;
13896 +   __u8  szSerialNumber[81];
13897 +   __u16 usMajorRevision;
13898 +   __u16 usMinorRevision;
13899 +   __u16 usBuildRevision;
13900 +   __u16 usReleaseRevision;
13901 +   __u16 usBIOSMajorRevision;
13902 +   __u16 usBIOSMinorRevision;
13903 +   __u16 usBIOSBuildRevision;
13904 +   __u16 usBIOSReleaseRevision;
13905 +   __u32 uControllerFlags;
13906 +   __u16 usRromMajorRevision;
13907 +   __u16 usRromMinorRevision;
13908 +   __u16 usRromBuildRevision;
13909 +   __u16 usRromReleaseRevision;
13910 +   __u16 usRromBIOSMajorRevision;
13911 +   __u16 usRromBIOSMinorRevision;
13912 +   __u16 usRromBIOSBuildRevision;
13913 +   __u16 usRromBIOSReleaseRevision;
13914 +   __u8  bReserved[7];
13915 +} CSMI_SAS_CNTLR_CONFIG,
13916 +  *PCSMI_SAS_CNTLR_CONFIG;
13917 +
13918 +typedef struct _CSMI_SAS_CNTLR_CONFIG_BUFFER {
13919 +   IOCTL_HEADER IoctlHeader;
13920 +   CSMI_SAS_CNTLR_CONFIG Configuration;
13921 +} CSMI_SAS_CNTLR_CONFIG_BUFFER,
13922 +  *PCSMI_SAS_CNTLR_CONFIG_BUFFER;
13923 +
13924 +// CC_CSMI_SAS_CNTLR_STATUS
13925 +
13926 +typedef struct _CSMI_SAS_CNTLR_STATUS {
13927 +   __u32 uStatus;
13928 +   __u32 uOfflineReason;
13929 +   __u8  bReserved[28];
13930 +} CSMI_SAS_CNTLR_STATUS,
13931 +  *PCSMI_SAS_CNTLR_STATUS;
13932 +
13933 +typedef struct _CSMI_SAS_CNTLR_STATUS_BUFFER {
13934 +   IOCTL_HEADER IoctlHeader;
13935 +   CSMI_SAS_CNTLR_STATUS Status;
13936 +} CSMI_SAS_CNTLR_STATUS_BUFFER,
13937 +  *PCSMI_SAS_CNTLR_STATUS_BUFFER;
13938 +
13939 +// CC_CSMI_SAS_FIRMWARE_DOWNLOAD
13940 +
13941 +typedef struct _CSMI_SAS_FIRMWARE_DOWNLOAD {
13942 +   __u32 uBufferLength;
13943 +   __u32 uDownloadFlags;
13944 +   __u8  bReserved[32];
13945 +   __u16 usStatus;
13946 +   __u16 usSeverity;
13947 +} CSMI_SAS_FIRMWARE_DOWNLOAD,
13948 +  *PCSMI_SAS_FIRMWARE_DOWNLOAD;
13949 +
13950 +typedef struct _CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER {
13951 +   IOCTL_HEADER IoctlHeader;
13952 +   CSMI_SAS_FIRMWARE_DOWNLOAD Information;
13953 +   __u8  bDataBuffer[1];
13954 +} CSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER,
13955 +  *PCSMI_SAS_FIRMWARE_DOWNLOAD_BUFFER;
13956 +
13957 +// CC_CSMI_SAS_RAID_INFO
13958 +
13959 +typedef struct _CSMI_SAS_RAID_INFO {
13960 +   __u32 uNumRaidSets;
13961 +   __u32 uMaxDrivesPerSet;
13962 +   __u32 uMaxRaidSets;
13963 +   __u8  bMaxRaidTypes;
13964 +   __u8  bReservedByteFields[7];
13965 +   __u64 ulMinRaidSetBlocks;
13966 +   __u64 ulMaxRaidSetBlocks;
13967 +   __u32 uMaxPhysicalDrives;
13968 +   __u32 uMaxExtents;
13969 +   __u32 uMaxModules;
13970 +   __u32 uMaxTransformationMemory;
13971 +   __u32 uChangeCount;
13972 +   __u8  bReserved[44];
13973 +} CSMI_SAS_RAID_INFO,
13974 +  *PCSMI_SAS_RAID_INFO;
13975 +
13976 +typedef struct _CSMI_SAS_RAID_INFO_BUFFER {
13977 +   IOCTL_HEADER IoctlHeader;
13978 +   CSMI_SAS_RAID_INFO Information;
13979 +} CSMI_SAS_RAID_INFO_BUFFER,
13980 +  *PCSMI_SAS_RAID_INFO_BUFFER;
13981 +
13982 +// CC_CSMI_SAS_GET_RAID_CONFIG
13983 +
13984 +typedef struct _CSMI_SAS_RAID_DRIVES {
13985 +   __u8  bModel[40];
13986 +   __u8  bFirmware[8];
13987 +   __u8  bSerialNumber[40];
13988 +   __u8  bSASAddress[8];
13989 +   __u8  bSASLun[8];
13990 +   __u8  bDriveStatus;
13991 +   __u8  bDriveUsage;
13992 +   __u8  bDriveType;
13993 +   __u16 usBlockSize;
13994 +   __u8  bReserved[15];
13995 +   __u32 uDriveIndex;
13996 +   __u64 ulTotalUserBlocks;
13997 +} CSMI_SAS_RAID_DRIVES,
13998 +  *PCSMI_SAS_RAID_DRIVES;
13999 +
14000 +typedef struct _CSMI_SAS_RAID_DEVICE_ID {
14001 +   __u8  bDeviceIdentificationVPDPage[1];
14002 +} CSMI_SAS_RAID_DEVICE_ID,
14003 +  *PCSMI_SAS_RAID_DEVICE_ID;
14004 +
14005 +typedef struct _CSMI_SAS_RAID_SET_ADDITIONAL_DATA {
14006 +   __u8  bLabel[16];
14007 +   __u8  bRaidSetLun[8];
14008 +   __u8  bWriteProtection;
14009 +   __u8  bCacheSetting;
14010 +   __u8  bCacheRatio;
14011 +   __u16 usBlockSize;
14012 +   __u8  bReservedBytes[11];
14013 +   __u64 ulRaidSetExtentOffset;
14014 +   __u64 ulRaidSetBlocks;
14015 +   __u32 uStripeSizeInBlocks;
14016 +   __u32 uSectorsPerTrack;
14017 +   __u8  bApplicationScratchPad[16];
14018 +   __u32 uNumberOfHeads;
14019 +   __u32 uNumberOfTracks;
14020 +   __u8  bReserved[24];
14021 +} CSMI_SAS_RAID_SET_ADDITIONAL_DATA,
14022 +  *PCSMI_SAS_RAID_SET_ADDITIONAL_DATA;
14023 +
14024 +typedef struct _CSMI_SAS_RAID_CONFIG {
14025 +   __u32 uRaidSetIndex;
14026 +   __u32 uCapacity;
14027 +   __u32 uStripeSize;
14028 +   __u8  bRaidType;
14029 +   __u8  bStatus;
14030 +   __u8  bInformation;
14031 +   __u8  bDriveCount;
14032 +   __u8  bDataType;
14033 +   __u8  bReserved[15];
14034 +   __u32 uChangeCount;
14035 +   union {
14036 +      CSMI_SAS_RAID_DRIVES Drives[1];
14037 +      CSMI_SAS_RAID_DEVICE_ID DeviceId[1];
14038 +      CSMI_SAS_RAID_SET_ADDITIONAL_DATA Data[1];
14039 +   };
14040 +} CSMI_SAS_RAID_CONFIG,
14041 +   *PCSMI_SAS_RAID_CONFIG;
14042 +
14043 +typedef struct _CSMI_SAS_RAID_CONFIG_BUFFER {
14044 +   IOCTL_HEADER IoctlHeader;
14045 +   CSMI_SAS_RAID_CONFIG Configuration;
14046 +} CSMI_SAS_RAID_CONFIG_BUFFER,
14047 +  *PCSMI_SAS_RAID_CONFIG_BUFFER;
14048 +
14049 +// CC_CSMI_SAS_GET_RAID_FEATURES
14050 +
14051 +typedef struct _CSMI_SAS_RAID_TYPE_DESCRIPTION {
14052 +  __u8  bRaidType;
14053 +  __u8  bReservedBytes[7];
14054 +  __u32 uSupportedStripeSizeMap;
14055 +  __u8  bReserved[24];
14056 +} CSMI_SAS_RAID_TYPE_DESCRIPTION, 
14057 +  *PCSMI_SAS_RAID_TYPE_DESCRIPTION;
14058 +
14059 +typedef struct _CSMI_SAS_RAID_FEATURES {
14060 +   __u32 uFeatures;
14061 +   __u8  bReservedFeatures[32];
14062 +   __u8  bDefaultTransformPriority;
14063 +   __u8  bTransformPriority;
14064 +   __u8  bDefaultRebuildPriority;
14065 +   __u8  bRebuildPriority;
14066 +   __u8  bDefaultSurfaceScanPriority;
14067 +   __u8  bSurfaceScanPriority;
14068 +   __u16 usReserved;
14069 +   __u32 uRaidSetTransformationRules;
14070 +   __u32 uReserved[11];
14071 +   CSMI_SAS_RAID_TYPE_DESCRIPTION RaidType[24];
14072 +   __u8  bCacheRatiosSupported[104];
14073 +   __u32 uChangeCount;
14074 +   __u8  bReserved[124];
14075 +} CSMI_SAS_RAID_FEATURES,
14076 +  *PCSMI_SAS_RAID_FEATURES;
14077 +
14078 +typedef struct _CSMI_SAS_RAID_FEATURES_BUFFER {
14079 +   IOCTL_HEADER IoctlHeader;
14080 +   CSMI_SAS_RAID_FEATURES Information;
14081 +} CSMI_SAS_RAID_FEATURES_BUFFER,
14082 +  *PCSMI_SAS_RAID_FEATURES_BUFFER;
14083 +
14084 +// CC_CSMI_SAS_SET_RAID_CONTROL
14085 +
14086 +typedef struct _CSMI_SAS_RAID_CONTROL {
14087 +   __u8  bTransformPriority;
14088 +   __u8  bRebuildPriority;
14089 +   __u8  bCacheRatioFlag;
14090 +   __u8  bCacheRatio;
14091 +   __u8  bSurfaceScanPriority;
14092 +   __u8  bReservedBytes[15];
14093 +   __u8  bClearConfiguration[8];
14094 +   __u32 uChangeCount;
14095 +   __u8  bReserved[88];
14096 +   __u32 uFailureCode;
14097 +   __u8  bFailureDescription[80];
14098 +} CSMI_SAS_RAID_CONTROL,
14099 +  *PCSMI_SAS_RAID_CONTROL;
14100 +
14101 +typedef struct _CSMI_SAS_RAID_CONTROL_BUFFER {
14102 +   IOCTL_HEADER IoctlHeader;
14103 +   CSMI_SAS_RAID_CONTROL Information;
14104 +} CSMI_SAS_RAID_CONTROL_BUFFER,
14105 +  *PCSMI_SAS_RAID_CONTROL_BUFFER;
14106 +
14107 +// CC_CSMI_SAS_GET_RAID_ELEMENT
14108 +
14109 +typedef struct _CSMI_SAS_DRIVE_EXTENT_INFO {
14110 +   __u32 uDriveIndex;
14111 +   __u8  bExtentType;
14112 +   __u8  bReservedBytes[7];
14113 +   __u64 ulExtentOffset;
14114 +   __u64 ulExtentBlocks;
14115 +   __u32 uRaidSetIndex;
14116 +   __u8  bReserved[96];
14117 +} CSMI_SAS_DRIVE_EXTENT_INFO, 
14118 +  *PCSMI_SAS_DRIVE_EXTENT_INFO;
14119 +
14120 +typedef struct _CSMI_SAS_RAID_MODULE_INFO {
14121 +   __u8  bReserved[128];
14122 +} CSMI_SAS_RAID_MODULE_INFO, 
14123 +  *PCSMI_SAS_RAID_MODULE_INFO;
14124 +
14125 +typedef struct _CSMI_SAS_DRIVE_LOCATION {
14126 +   __u8  bConnector[16];
14127 +   __u8  bBoxName[16];
14128 +   __u32 uBay;
14129 +   __u8  bReservedBytes[4];
14130 +   __u8  bAttachedSASAddress[8];
14131 +   __u8  bAttachedPhyIdentifier;
14132 +   __u8  bReserved[79];
14133 +} CSMI_SAS_DRIVE_LOCATION, 
14134 +  *PCSMI_SAS_DRIVE_LOCATION;
14135 +
14136 +typedef struct _CSMI_SAS_RAID_DRIVES_ADDITIONAL_DATA {
14137 +   __u8  bNegotiatedLinkRate[2];
14138 +   __u8  bReserved[126];
14139 +} CSMI_SAS_RAID_DRIVES_ADDITIONAL_DATA, 
14140 +  *PCSMI_SAS_RAID_DRIVES_ADDITIONAL_DATA;
14141 +
14142 +typedef struct _CSMI_SAS_DRIVE_INFO {
14143 +   CSMI_SAS_RAID_DRIVES Device;
14144 +   CSMI_SAS_RAID_DRIVES_ADDITIONAL_DATA Data;
14145 +   CSMI_SAS_DRIVE_LOCATION Location; 
14146 +   __u8  bReserved[16];
14147 +} CSMI_SAS_DRIVE_INFO, 
14148 +  *PCSMI_SAS_DRIVE_INFO;
14149 +
14150 +typedef struct _CSMI_SAS_RAID_ELEMENT { 
14151 +   __u32 uEnumerationType;
14152 +   __u32 uElementIndex;
14153 +   __u32 uNumElements;
14154 +   __u32 uChangeCount;
14155 +   __u32 uSubElementIndex;
14156 +   __u8  bReserved[32];
14157 +   __u32 uFailureCode;
14158 +   __u8  bFailureDescription[80];
14159 +   union {
14160 +       CSMI_SAS_DRIVE_INFO Drive;
14161 +       CSMI_SAS_RAID_MODULE_INFO Module;
14162 +       CSMI_SAS_DRIVE_EXTENT_INFO Extent;
14163 +   } Element;
14164 +} CSMI_SAS_RAID_ELEMENT,
14165 +  *PCSMI_SAS_RAID_ELEMENT;
14166 +
14167 +typedef struct _CSMI_SAS_RAID_ELEMENT_BUFFER {
14168 +   IOCTL_HEADER IoctlHeader;
14169 +   CSMI_SAS_RAID_ELEMENT Information;
14170 +} CSMI_SAS_RAID_ELEMENT_BUFFER,
14171 +  *PCSMI_SAS_RAID_ELEMENT_BUFFER;
14172 +
14173 +// CC_CSMI_SAS_SET_RAID_OPERATION
14174 +
14175 +typedef struct _CSMI_SAS_RAID_SET_LIST {
14176 +   __u32 uRaidSetIndex;
14177 +   __u8  bExistingLun[8]; 
14178 +   __u8  bNewLun[8]; 
14179 +   __u8  bReserved[12];
14180 +} CSMI_SAS_RAID_SET_LIST, 
14181 +  *PCSMI_SAS_RAID_SET_LIST;
14182 +
14183 +typedef struct _CSMI_SAS_RAID_SET_DRIVE_LIST {
14184 +   __u32 uDriveIndex;
14185 +   __u8  bDriveUsage;
14186 +   __u8  bReserved[27];
14187 +} CSMI_SAS_RAID_SET_DRIVE_LIST, 
14188 +  *PCSMI_SAS_RAID_SET_DRIVE_LIST;
14189 +
14190 +typedef struct _CSMI_SAS_RAID_SET_SPARE_INFO {
14191 +   __u32 uRaidSetIndex;
14192 +   __u32 uDriveCount;
14193 +   __u8  bApplicationScratchPad[16];
14194 +   __u8  bReserved[104];  
14195 +} CSMI_SAS_RAID_SET_SPARE_INFO, 
14196 +  *PCSMI_SAS_RAID_SET_SPARE_INFO;
14197 +
14198 +typedef struct _CSMI_SAS_RAID_SET_ONLINE_STATE_INFO {
14199 +   __u32 uRaidSetIndex;
14200 +   __u8  bOnlineState;
14201 +   __u8  bReserved[123];  
14202 +} CSMI_SAS_RAID_SET_ONLINE_STATE_INFO, 
14203 +  *PCSMI_SAS_RAID_SET_ONLINE_STATE_INFO;
14204 +
14205 +typedef struct _CSMI_SAS_RAID_SET_CACHE_INFO {
14206 +   __u32 uRaidSetIndex;
14207 +   __u8  bCacheSetting;
14208 +   __u8  bCacheRatioFlag;
14209 +   __u8  bCacheRatio;
14210 +   __u8  bReserved[121];  
14211 +} CSMI_SAS_RAID_SET_CACHE_INFO, 
14212 +  *PCSMI_SAS_RAID_SET_CACHE_INFO;
14213 +
14214 +typedef struct _CSMI_SAS_RAID_SET_WRITE_PROTECT_INFO {
14215 +   __u32 uRaidSetIndex;
14216 +   __u8  bWriteProtectSetting;
14217 +   __u8  bReserved[123];  
14218 +} CSMI_SAS_RAID_SET_WRITE_PROTECT_INFO, 
14219 +  *PCSMI_SAS_RAID_SET_WRITE_PROTECT_INFO;
14220 +
14221 +typedef struct _CSMI_SAS_RAID_SET_DELETE_INFO {
14222 +   __u32 uRaidSetIndex;
14223 +   __u8  bReserved[124];  
14224 +} CSMI_SAS_RAID_SET_DELETE_INFO, 
14225 +  *PCSMI_SAS_RAID_SET_DELETE_INFO;
14226 +
14227 +typedef struct _CSMI_SAS_RAID_SET_MODIFY_INFO {
14228 +   __u8  bRaidType;
14229 +   __u8  bReservedBytes[7];
14230 +   __u32 uStripeSize;
14231 +   __u64 ulRaidSetBlocks;
14232 +   __u64 ulRaidSetExtentOffset;
14233 +   __u32 uDriveCount;
14234 +   __u8  bReserved[96];
14235 +} CSMI_SAS_RAID_SET_MODIFY_INFO, 
14236 +  *PCSMI_SAS_RAID_SET_MODIFY_INFO;
14237 +
14238 +typedef struct _CSMI_SAS_RAID_SET_TRANSFORM_INFO {
14239 +   __u8  bTransformType;
14240 +   __u8  bReservedBytes[3];
14241 +   __u32 uRaidSetIndex;
14242 +   __u8  bRaidType;
14243 +   __u8  bReservedBytes2[11];
14244 +   __u32 uAdditionalRaidSetIndex;
14245 +   __u32 uRaidSetCount;
14246 +   __u8  bApplicationScratchPad[16];
14247 +   CSMI_SAS_RAID_SET_MODIFY_INFO Modify;
14248 +   __u8  bReserved[80];
14249 +} CSMI_SAS_RAID_SET_TRANSFORM_INFO, 
14250 +  *PCSMI_SAS_RAID_SET_TRANSFORM_INFO;
14251 +
14252 +typedef struct _CSMI_SAS_RAID_SET_LABEL_INFO {
14253 +   __u32 uRaidSetIndex;
14254 +   __u8  bLabel[16];
14255 +   __u8  bReserved[108];  
14256 +} CSMI_SAS_RAID_SET_LABEL_INFO, 
14257 +  *PCSMI_SAS_RAID_SET_LABEL_INFO;
14258 +
14259 +typedef struct _CSMI_SAS_RAID_SET_CREATE_INFO {
14260 +   __u8  bRaidType;
14261 +   __u8  bReservedBytes[7];
14262 +   __u32 uStripeSize;
14263 +   __u32 uTrackSectorCount;
14264 +   __u64 ulRaidSetBlocks; 
14265 +   __u64 ulRaidSetExtentOffset;
14266 +   __u32 uDriveCount;
14267 +   __u8  bLabel[16];
14268 +   __u32 uRaidSetIndex;
14269 +   __u8  bApplicationScratchPad[16];
14270 +   __u32 uNumberOfHeads;
14271 +   __u32 uNumberOfTracks;
14272 +   __u8  bReserved[48];  
14273 +} CSMI_SAS_RAID_SET_CREATE_INFO, 
14274 +  *PCSMI_SAS_RAID_SET_CREATE_INFO;
14275 +
14276 +typedef struct _CSMI_SAS_RAID_SET_OPERATION { 
14277 +   __u32 uOperationType;
14278 +   __u32 uChangeCount;
14279 +   __u32 uFailureCode;
14280 +   __u8  bFailureDescription[80];
14281 +   __u8  bReserved[28];
14282 +   union {
14283 +       CSMI_SAS_RAID_SET_CREATE_INFO Create;
14284 +       CSMI_SAS_RAID_SET_LABEL_INFO Label;
14285 +       CSMI_SAS_RAID_SET_TRANSFORM_INFO Transform;
14286 +       CSMI_SAS_RAID_SET_DELETE_INFO Delete;
14287 +       CSMI_SAS_RAID_SET_WRITE_PROTECT_INFO Protect;
14288 +       CSMI_SAS_RAID_SET_CACHE_INFO Cache;
14289 +       CSMI_SAS_RAID_SET_ONLINE_STATE_INFO State;
14290 +       CSMI_SAS_RAID_SET_SPARE_INFO Spare;
14291 +   } Operation;
14292 +   union {
14293 +       CSMI_SAS_RAID_SET_DRIVE_LIST DriveList[1];
14294 +       CSMI_SAS_RAID_SET_LIST RaidSetList[1];
14295 +   } Parameters;
14296 +} CSMI_SAS_RAID_SET_OPERATION,
14297 +  *PCSMI_SAS_RAID_SET_OPERATION;
14298 +
14299 +typedef struct _CSMI_SAS_RAID_SET_OPERATION_BUFFER {
14300 +   IOCTL_HEADER IoctlHeader;
14301 +   CSMI_SAS_RAID_SET_OPERATION Information;
14302 +} CSMI_SAS_RAID_SET_OPERATION_BUFFER,
14303 +  *PCSMI_SAS_RAID_SET_OPERATION_BUFFER;
14304 +
14305 +/* * * * * * * * * * SAS HBA Class Structures * * * * * * * * * */
14306 +
14307 +// CC_CSMI_SAS_GET_PHY_INFO
14308 +
14309 +typedef struct _CSMI_SAS_IDENTIFY {
14310 +   __u8  bDeviceType;
14311 +   __u8  bRestricted;
14312 +   __u8  bInitiatorPortProtocol;
14313 +   __u8  bTargetPortProtocol;
14314 +   __u8  bRestricted2[8];
14315 +   __u8  bSASAddress[8];
14316 +   __u8  bPhyIdentifier;
14317 +   __u8  bSignalClass;
14318 +   __u8  bReserved[6];
14319 +} CSMI_SAS_IDENTIFY,
14320 +  *PCSMI_SAS_IDENTIFY;
14321 +
14322 +typedef struct _CSMI_SAS_PHY_ENTITY {
14323 +   CSMI_SAS_IDENTIFY Identify;
14324 +   __u8  bPortIdentifier;
14325 +   __u8  bNegotiatedLinkRate;
14326 +   __u8  bMinimumLinkRate;
14327 +   __u8  bMaximumLinkRate;
14328 +   __u8  bPhyChangeCount;
14329 +   __u8  bAutoDiscover;
14330 +   __u8  bPhyFeatures;
14331 +   __u8  bReserved;
14332 +   CSMI_SAS_IDENTIFY Attached;
14333 +} CSMI_SAS_PHY_ENTITY,
14334 +  *PCSMI_SAS_PHY_ENTITY;
14335 +
14336 +typedef struct _CSMI_SAS_PHY_INFO {
14337 +   __u8  bNumberOfPhys;
14338 +   __u8  bReserved[3];
14339 +   CSMI_SAS_PHY_ENTITY Phy[32];
14340 +} CSMI_SAS_PHY_INFO,
14341 +  *PCSMI_SAS_PHY_INFO;
14342 +
14343 +typedef struct _CSMI_SAS_PHY_INFO_BUFFER {
14344 +   IOCTL_HEADER IoctlHeader;
14345 +   CSMI_SAS_PHY_INFO Information;
14346 +} CSMI_SAS_PHY_INFO_BUFFER,
14347 +  *PCSMI_SAS_PHY_INFO_BUFFER;
14348 +
14349 +// CC_CSMI_SAS_SET_PHY_INFO
14350 +
14351 +typedef struct _CSMI_SAS_SET_PHY_INFO {
14352 +   __u8  bPhyIdentifier;
14353 +   __u8  bNegotiatedLinkRate;
14354 +   __u8  bProgrammedMinimumLinkRate;
14355 +   __u8  bProgrammedMaximumLinkRate;
14356 +   __u8  bSignalClass;
14357 +   __u8  bReserved[3];
14358 +} CSMI_SAS_SET_PHY_INFO,
14359 +  *PCSMI_SAS_SET_PHY_INFO;
14360 +
14361 +typedef struct _CSMI_SAS_SET_PHY_INFO_BUFFER {
14362 +   IOCTL_HEADER IoctlHeader;
14363 +   CSMI_SAS_SET_PHY_INFO Information;
14364 +} CSMI_SAS_SET_PHY_INFO_BUFFER,
14365 +  *PCSMI_SAS_SET_PHY_INFO_BUFFER;
14366 +
14367 +// CC_CSMI_SAS_GET_LINK_ERRORS
14368 +
14369 +typedef struct _CSMI_SAS_LINK_ERRORS {
14370 +   __u8  bPhyIdentifier;
14371 +   __u8  bResetCounts;
14372 +   __u8  bReserved[2];
14373 +   __u32 uInvalidDwordCount;
14374 +   __u32 uRunningDisparityErrorCount;
14375 +   __u32 uLossOfDwordSyncCount;
14376 +   __u32 uPhyResetProblemCount;
14377 +} CSMI_SAS_LINK_ERRORS,
14378 +  *PCSMI_SAS_LINK_ERRORS;
14379 +
14380 +typedef struct _CSMI_SAS_LINK_ERRORS_BUFFER {
14381 +   IOCTL_HEADER IoctlHeader;
14382 +   CSMI_SAS_LINK_ERRORS Information;
14383 +} CSMI_SAS_LINK_ERRORS_BUFFER,
14384 +  *PCSMI_SAS_LINK_ERRORS_BUFFER;
14385 +
14386 +// CC_CSMI_SAS_SMP_PASSTHRU
14387 +
14388 +typedef struct _CSMI_SAS_SMP_REQUEST {
14389 +   __u8  bFrameType;
14390 +   __u8  bFunction;
14391 +   __u8  bReserved[2];
14392 +   __u8  bAdditionalRequestBytes[1016];
14393 +} CSMI_SAS_SMP_REQUEST,
14394 +  *PCSMI_SAS_SMP_REQUEST;
14395 +
14396 +typedef struct _CSMI_SAS_SMP_RESPONSE {
14397 +   __u8  bFrameType;
14398 +   __u8  bFunction;
14399 +   __u8  bFunctionResult;
14400 +   __u8  bReserved;
14401 +   __u8  bAdditionalResponseBytes[1016];
14402 +} CSMI_SAS_SMP_RESPONSE,
14403 +  *PCSMI_SAS_SMP_RESPONSE;
14404 +
14405 +typedef struct _CSMI_SAS_SMP_PASSTHRU {
14406 +   __u8  bPhyIdentifier;
14407 +   __u8  bPortIdentifier;
14408 +   __u8  bConnectionRate;
14409 +   __u8  bReserved;
14410 +   __u8  bDestinationSASAddress[8];
14411 +   __u32 uRequestLength;
14412 +   CSMI_SAS_SMP_REQUEST Request;
14413 +   __u8  bConnectionStatus;
14414 +   __u8  bReserved2[3];
14415 +   __u32 uResponseBytes;
14416 +   CSMI_SAS_SMP_RESPONSE Response;
14417 +} CSMI_SAS_SMP_PASSTHRU,
14418 +  *PCSMI_SAS_SMP_PASSTHRU;
14419 +
14420 +typedef struct _CSMI_SAS_SMP_PASSTHRU_BUFFER {
14421 +   IOCTL_HEADER IoctlHeader;
14422 +   CSMI_SAS_SMP_PASSTHRU Parameters;
14423 +} CSMI_SAS_SMP_PASSTHRU_BUFFER,
14424 +  *PCSMI_SAS_SMP_PASSTHRU_BUFFER;
14425 +
14426 +// CC_CSMI_SAS_SSP_PASSTHRU
14427 +
14428 +typedef struct _CSMI_SAS_SSP_PASSTHRU {
14429 +   __u8  bPhyIdentifier;
14430 +   __u8  bPortIdentifier;
14431 +   __u8  bConnectionRate;
14432 +   __u8  bReserved;
14433 +   __u8  bDestinationSASAddress[8];
14434 +   __u8  bLun[8];
14435 +   __u8  bCDBLength;
14436 +   __u8  bAdditionalCDBLength;
14437 +   __u8  bReserved2[2];
14438 +   __u8  bCDB[16];
14439 +   __u32 uFlags;
14440 +   __u8  bAdditionalCDB[24];
14441 +   __u32 uDataLength;
14442 +} CSMI_SAS_SSP_PASSTHRU,
14443 +  *PCSMI_SAS_SSP_PASSTHRU;
14444 +
14445 +typedef struct _CSMI_SAS_SSP_PASSTHRU_STATUS {
14446 +   __u8  bConnectionStatus;
14447 +   __u8  bSSPStatus;
14448 +   __u8  bReserved[2];
14449 +   __u8  bDataPresent;
14450 +   __u8  bStatus;
14451 +   __u8  bResponseLength[2];
14452 +   __u8  bResponse[256];
14453 +   __u32 uDataBytes;
14454 +} CSMI_SAS_SSP_PASSTHRU_STATUS,
14455 +  *PCSMI_SAS_SSP_PASSTHRU_STATUS;
14456 +
14457 +typedef struct _CSMI_SAS_SSP_PASSTHRU_BUFFER {
14458 +   IOCTL_HEADER IoctlHeader;
14459 +   CSMI_SAS_SSP_PASSTHRU Parameters;
14460 +   CSMI_SAS_SSP_PASSTHRU_STATUS Status;
14461 +   __u8  bDataBuffer[1];
14462 +} CSMI_SAS_SSP_PASSTHRU_BUFFER,
14463 +  *PCSMI_SAS_SSP_PASSTHRU_BUFFER;
14464 +
14465 +// CC_CSMI_SAS_STP_PASSTHRU
14466 +
14467 +typedef struct _CSMI_SAS_STP_PASSTHRU {
14468 +   __u8  bPhyIdentifier;
14469 +   __u8  bPortIdentifier;
14470 +   __u8  bConnectionRate;
14471 +   __u8  bReserved;
14472 +   __u8  bDestinationSASAddress[8];
14473 +   __u8  bReserved2[4];
14474 +   __u8  bCommandFIS[20];
14475 +   __u32 uFlags;
14476 +   __u32 uDataLength;
14477 +} CSMI_SAS_STP_PASSTHRU,
14478 +  *PCSMI_SAS_STP_PASSTHRU;
14479 +
14480 +typedef struct _CSMI_SAS_STP_PASSTHRU_STATUS {
14481 +   __u8  bConnectionStatus;
14482 +   __u8  bReserved[3];
14483 +   __u8  bStatusFIS[20];
14484 +   __u32 uSCR[16];
14485 +   __u32 uDataBytes;
14486 +} CSMI_SAS_STP_PASSTHRU_STATUS,
14487 +  *PCSMI_SAS_STP_PASSTHRU_STATUS;
14488 +
14489 +typedef struct _CSMI_SAS_STP_PASSTHRU_BUFFER {
14490 +   IOCTL_HEADER IoctlHeader;
14491 +   CSMI_SAS_STP_PASSTHRU Parameters;
14492 +   CSMI_SAS_STP_PASSTHRU_STATUS Status;
14493 +   __u8  bDataBuffer[1];
14494 +} CSMI_SAS_STP_PASSTHRU_BUFFER,
14495 +  *PCSMI_SAS_STP_PASSTHRU_BUFFER;
14496 +
14497 +// CC_CSMI_SAS_GET_SATA_SIGNATURE
14498 +
14499 +typedef struct _CSMI_SAS_SATA_SIGNATURE {
14500 +   __u8  bPhyIdentifier;
14501 +   __u8  bReserved[3];
14502 +   __u8  bSignatureFIS[20];
14503 +} CSMI_SAS_SATA_SIGNATURE,
14504 +  *PCSMI_SAS_SATA_SIGNATURE;
14505 +
14506 +typedef struct _CSMI_SAS_SATA_SIGNATURE_BUFFER {
14507 +   IOCTL_HEADER IoctlHeader;
14508 +   CSMI_SAS_SATA_SIGNATURE Signature;
14509 +} CSMI_SAS_SATA_SIGNATURE_BUFFER,
14510 +  *PCSMI_SAS_SATA_SIGNATURE_BUFFER;
14511 +
14512 +// CC_CSMI_SAS_GET_SCSI_ADDRESS
14513 +
14514 +typedef struct _CSMI_SAS_GET_SCSI_ADDRESS_BUFFER {
14515 +   IOCTL_HEADER IoctlHeader;
14516 +   __u8  bSASAddress[8];
14517 +   __u8  bSASLun[8];
14518 +   __u8  bHostIndex;
14519 +   __u8  bPathId;
14520 +   __u8  bTargetId;
14521 +   __u8  bLun;
14522 +} CSMI_SAS_GET_SCSI_ADDRESS_BUFFER,
14523 +   *PCSMI_SAS_GET_SCSI_ADDRESS_BUFFER;
14524 +
14525 +// CC_CSMI_SAS_GET_DEVICE_ADDRESS
14526 +
14527 +typedef struct _CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER {
14528 +   IOCTL_HEADER IoctlHeader;
14529 +   __u8  bHostIndex;
14530 +   __u8  bPathId;
14531 +   __u8  bTargetId;
14532 +   __u8  bLun;
14533 +   __u8  bSASAddress[8];
14534 +   __u8  bSASLun[8];
14535 +} CSMI_SAS_GET_DEVICE_ADDRESS_BUFFER,
14536 +  *PCSMI_SAS_GET_DEVICE_ADDRESS_BUFFER;
14537 +
14538 +// CC_CSMI_SAS_TASK_MANAGEMENT
14539 +
14540 +typedef struct _CSMI_SAS_SSP_TASK_IU {
14541 +   __u8  bHostIndex;
14542 +   __u8  bPathId;
14543 +   __u8  bTargetId;
14544 +   __u8  bLun;
14545 +   __u32 uFlags;
14546 +   __u32 uQueueTag;
14547 +   __u32 uReserved;
14548 +   __u8  bTaskManagementFunction;
14549 +   __u8  bReserved[7];
14550 +   __u32 uInformation;
14551 +} CSMI_SAS_SSP_TASK_IU,
14552 +  *PCSMI_SAS_SSP_TASK_IU;
14553 +
14554 +typedef struct _CSMI_SAS_SSP_TASK_IU_BUFFER {
14555 +   IOCTL_HEADER IoctlHeader;
14556 +   CSMI_SAS_SSP_TASK_IU Parameters;
14557 +   CSMI_SAS_SSP_PASSTHRU_STATUS Status;
14558 +} CSMI_SAS_SSP_TASK_IU_BUFFER,
14559 +  *PCSMI_SAS_SSP_TASK_IU_BUFFER;
14560 +
14561 +// CC_CSMI_SAS_GET_CONNECTOR_INFO
14562 +
14563 +typedef struct _CSMI_SAS_GET_CONNECTOR_INFO {
14564 +   __u32 uPinout;
14565 +   __u8  bConnector[16];
14566 +   __u8  bLocation;
14567 +   __u8  bReserved[15];
14568 +} CSMI_SAS_CONNECTOR_INFO,
14569 +  *PCSMI_SAS_CONNECTOR_INFO;
14570 +
14571 +typedef struct _CSMI_SAS_CONNECTOR_INFO_BUFFER {
14572 +   IOCTL_HEADER IoctlHeader;
14573 +   CSMI_SAS_CONNECTOR_INFO Reference[32];
14574 +} CSMI_SAS_CONNECTOR_INFO_BUFFER,
14575 +  *PCSMI_SAS_CONNECTOR_INFO_BUFFER;
14576 +
14577 +// CC_CSMI_SAS_GET_LOCATION
14578 +
14579 +typedef struct _CSMI_SAS_LOCATION_IDENTIFIER {
14580 +   __u32 bLocationFlags;
14581 +   __u8  bSASAddress[8];
14582 +   __u8  bSASLun[8];
14583 +   __u8  bEnclosureIdentifier[8];
14584 +   __u8  bEnclosureName[32];
14585 +   __u8  bBayPrefix[32];
14586 +   __u8  bBayIdentifier;
14587 +   __u8  bLocationState;
14588 +   __u8  bReserved[2];
14589 +} CSMI_SAS_LOCATION_IDENTIFIER,
14590 +  *PCSMI_SAS_LOCATION_IDENTIFIER;
14591 +
14592 +typedef struct _CSMI_SAS_GET_LOCATION_BUFFER {
14593 +   IOCTL_HEADER IoctlHeader;
14594 +   __u8  bHostIndex;
14595 +   __u8  bPathId;
14596 +   __u8  bTargetId;
14597 +   __u8  bLun;
14598 +   __u8  bIdentify;
14599 +   __u8  bNumberOfLocationIdentifiers;
14600 +   __u8  bLengthOfLocationIdentifier;
14601 +   CSMI_SAS_LOCATION_IDENTIFIER Location[1];
14602 +} CSMI_SAS_GET_LOCATION_BUFFER,
14603 +  *PCSMI_SAS_GET_LOCATION_BUFFER;
14604 +
14605 +// CC_CSMI_SAS_PHY_CONTROL
14606 +
14607 +typedef struct _CSMI_SAS_CHARACTER {
14608 +   __u8  bTypeFlags;
14609 +   __u8  bValue;
14610 +} CSMI_SAS_CHARACTER,
14611 +  *PCSMI_SAS_CHARACTER;
14612 +
14613 +typedef struct _CSMI_SAS_PHY_CONTROL {
14614 +   __u8  bType;
14615 +   __u8  bRate;
14616 +   __u8  bReserved[6];
14617 +   __u32 uVendorUnique[8];
14618 +   __u32 uTransmitterFlags;
14619 +   __i8  bTransmitAmplitude;
14620 +   __i8  bTransmitterPreemphasis;
14621 +   __i8  bTransmitterSlewRate;
14622 +   __i8  bTransmitterReserved[13];
14623 +   __u8  bTransmitterVendorUnique[64];
14624 +   __u32 uReceiverFlags;
14625 +   __i8  bReceiverThreshold;
14626 +   __i8  bReceiverEqualizationGain;
14627 +   __i8  bReceiverReserved[14];
14628 +   __u8  bReceiverVendorUnique[64];
14629 +   __u32 uPatternFlags;
14630 +   __u8  bFixedPattern;
14631 +   __u8  bUserPatternLength;
14632 +   __u8  bPatternReserved[6];
14633 +   CSMI_SAS_CHARACTER UserPatternBuffer[16];
14634 +} CSMI_SAS_PHY_CONTROL,
14635 +  *PCSMI_SAS_PHY_CONTROL;
14636 +
14637 +typedef struct _CSMI_SAS_PHY_CONTROL_BUFFER {
14638 +   IOCTL_HEADER IoctlHeader;
14639 +   __u32 uFunction;
14640 +   __u8  bPhyIdentifier;
14641 +   __u16 usLengthOfControl;
14642 +   __u8  bNumberOfControls;
14643 +   __u8  bReserved[4];
14644 +   __u32 uLinkFlags;
14645 +   __u8  bSpinupRate;
14646 +   __u8  bLinkReserved[7];
14647 +   __u32 uVendorUnique[8];
14648 +   CSMI_SAS_PHY_CONTROL Control[1];
14649 +} CSMI_SAS_PHY_CONTROL_BUFFER,
14650 +  *PCSMI_SAS_PHY_CONTROL_BUFFER;
14651 +
14652 +// EDN #pragma CSMI_SAS_END_PACK
14653 +#pragma pack()
14654 +
14655 +#endif // _CSMI_SAS_H_
14656 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/Makefile linux-2.6.9-55.0.12/drivers/message/fusion/Makefile
14657 --- linux-2.6.9-67.0.1/drivers/message/fusion/Makefile  2007-12-21 11:40:54.000000000 +0100
14658 +++ linux-2.6.9-55.0.12/drivers/message/fusion/Makefile 2007-11-02 09:10:23.000000000 +0100
14659 @@ -8,8 +8,6 @@
14660  #EXTRA_CFLAGS += -DMPT_DEBUG_EXIT
14661  #EXTRA_CFLAGS += -DMPT_DEBUG_FAIL
14662  #EXTRA_CFLAGS  += -DMPT_DEBUG_SAS
14663 -EXTRA_CFLAGS += -DCPQ_CIM
14664 -EXTRA_CFLAGS += -DMPT_SUPPORT_FWDLB_IOCTL
14665  
14666  #
14667  # driver/module specifics...
14668 @@ -31,6 +29,7 @@ EXTRA_CFLAGS += -DMPT_SUPPORT_FWDLB_IOCT
14669  #
14670  #  For mptctl:
14671  #CFLAGS_mptctl.o += -DMPT_DEBUG_IOCTL
14672 +CFLAGS_mptctl.o  += -DCPQ_CIM
14673  #
14674  #  For mptsas:
14675  #CFLAGS_mptsas.o += -DMPT_DEBUG_HOTPLUG
14676 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptbase.c linux-2.6.9-55.0.12/drivers/message/fusion/mptbase.c
14677 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptbase.c 2007-12-21 11:40:54.000000000 +0100
14678 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptbase.c        2007-11-02 09:10:23.000000000 +0100
14679 @@ -5,8 +5,8 @@
14680   *      For use with LSI Logic PCI chip/adapter(s)
14681   *      running LSI Logic Fusion MPT (Message Passing Technology) firmware.
14682   *
14683 - *  Copyright (c) 1999-2007 LSI Logic Corporation
14684 - *  (mailto:mpt_linux_developer@lsi.com)
14685 + *  Copyright (c) 1999-2005 LSI Logic Corporation
14686 + *  (mailto:mpt_linux_developer@lsil.com)
14687   *
14688   *  $Id: mptbase.c,v 1.130 2003/05/07 14:08:30 Exp $
14689   */
14690 @@ -93,8 +93,6 @@ MODULE_VERSION(MPT_LINUX_VERSION_COMMON)
14691  char *mptbase = NULL;
14692  
14693  /* Command line args */
14694 -
14695 -
14696  int mpt_can_queue = 128;
14697  module_param(mpt_can_queue, int, 0);
14698  MODULE_PARM_DESC(mpt_can_queue, " Max IO depth per controller (default=128)");
14699 @@ -115,11 +113,6 @@ static int mpt_msi_enable = 0;
14700  module_param(mpt_msi_enable, int, 0);
14701  MODULE_PARM_DESC(mpt_msi_enable, " MSI Support Enable (default=0)");
14702  
14703 -int mpt_enable_deadioc_detect = 0;
14704 -module_param(mpt_enable_deadioc_detect, int, 0);
14705 -MODULE_PARM_DESC(mpt_enable_deadioc_detect, "Detection of Dead IOC Enable (default=0)");
14706 -
14707 -//@@@@
14708  #ifdef MFCNT
14709  static int mfcounter = 0;
14710  #define PRINT_MF_COUNT 20000
14711 @@ -163,13 +156,10 @@ static DECLARE_WAIT_QUEUE_HEAD(mpt_waitq
14712   */
14713  static irqreturn_t mpt_interrupt(int irq, void *bus_id, struct pt_regs *r);
14714  static int     mpt_base_reply(MPT_ADAPTER *ioc, MPT_FRAME_HDR *req, MPT_FRAME_HDR *reply);
14715 -int    mpt_handshake_req_reply_wait(MPT_ADAPTER *ioc, int reqBytes,
14716 +static int     mpt_handshake_req_reply_wait(MPT_ADAPTER *ioc, int reqBytes,
14717                         u32 *req, int replyBytes, u16 *u16reply, int maxwait,
14718                         int sleepFlag);
14719 -int                    mpt_do_ioc_recovery(MPT_ADAPTER *ioc, u32 reason, int sleepFlag);
14720 -int             mpt_writeSDP1(MPT_ADAPTER *hd, int portnum, int id, int flags);
14721 -void    mpt_setSDP1parameters (u8 width, u8 factor, u8 offset, u8 flags, int *requestedPtr, int *configurationPtr);
14722 -
14723 +static int     mpt_do_ioc_recovery(MPT_ADAPTER *ioc, u32 reason, int sleepFlag);
14724  static void    mpt_detect_bound_ports(MPT_ADAPTER *ioc, struct pci_dev *pdev);
14725  static void    mpt_adapter_disable(MPT_ADAPTER *ioc);
14726  static void    mpt_adapter_dispose(MPT_ADAPTER *ioc);
14727 @@ -187,7 +177,7 @@ static int  mpt_do_upload(MPT_ADAPTER *io
14728  int            mpt_downloadboot(MPT_ADAPTER *ioc, MpiFwHeader_t *pFwHeader, int sleepFlag);
14729  static int     mpt_diag_reset(MPT_ADAPTER *ioc, int ignore, int sleepFlag);
14730  static int     KickStart(MPT_ADAPTER *ioc, int ignore, int sleepFlag);
14731 -int             mpt_SendIocReset(MPT_ADAPTER *ioc, u8 reset_type, int sleepFlag);
14732 +static int     SendIocReset(MPT_ADAPTER *ioc, u8 reset_type, int sleepFlag);
14733  static int     PrimeIocFifos(MPT_ADAPTER *ioc);
14734  static int     WaitForDoorbellAck(MPT_ADAPTER *ioc, int howlong, int sleepFlag);
14735  static int     WaitForDoorbellInt(MPT_ADAPTER *ioc, int howlong, int sleepFlag);
14736 @@ -197,6 +187,9 @@ static int  GetFcPortPage0(MPT_ADAPTER *i
14737  static int     GetIoUnitPage2(MPT_ADAPTER *ioc);
14738  static int     GetManufPage5(MPT_ADAPTER *ioc, int numPorts);
14739  static int     GetManufPage0(MPT_ADAPTER *ioc);
14740 +int            mpt_sas_get_info(MPT_ADAPTER *ioc);
14741 +static void    mptbase_sas_process_event_data(MPT_ADAPTER *ioc,
14742 +                   MpiEventDataSasDeviceStatusChange_t * pSasEventData);
14743  int            mptbase_sas_persist_operation(MPT_ADAPTER *ioc, u8 persist_opcode);
14744  static void    mptbase_raid_process_event_data(MPT_ADAPTER *ioc,
14745                     MpiEventDataRaid_t * pRaidEventData);
14746 @@ -204,7 +197,6 @@ static int  mpt_GetScsiPortSettings(MPT_A
14747  static int     mpt_readScsiDevicePageHeaders(MPT_ADAPTER *ioc, int portnum);
14748  static void    mpt_read_ioc_pg_1(MPT_ADAPTER *ioc);
14749  static void    mpt_read_ioc_pg_4(MPT_ADAPTER *ioc);
14750 -static void    mpt_read_ioc_pg_6(MPT_ADAPTER *ioc);
14751  static void    mpt_timer_expired(unsigned long data);
14752  static int     SendEventNotification(MPT_ADAPTER *ioc, u8 EvSwitch);
14753  static int     SendEventAck(MPT_ADAPTER *ioc, EventNotificationReply_t *evnp);
14754 @@ -227,7 +219,6 @@ static void mpt_sp_ioc_info(MPT_ADAPTER 
14755  static void    mpt_fc_log_info(MPT_ADAPTER *ioc, u32 log_info);
14756  static void    mpt_spi_log_info(MPT_ADAPTER *ioc, u32 log_info);
14757  static void    mpt_sas_log_info(MPT_ADAPTER *ioc, u32 log_info);
14758 -static void    mpt_inactive_raid_list_free(MPT_ADAPTER *ioc);
14759  
14760  /* module entry point */
14761  static int  __init    fusion_init  (void);
14762 @@ -273,10 +264,10 @@ mpt_turbo_reply(MPT_ADAPTER *ioc, u32 pa
14763  {
14764         MPT_FRAME_HDR *mf = NULL;
14765         MPT_FRAME_HDR *mr = NULL;
14766 -       int req_idx;
14767 +       int req_idx = 0;
14768         int cb_idx;
14769  
14770 -       dmfprintk((MYIOC_s_INFO_FMT "Got TURBO reply pa=%08x\n",
14771 +       dmfprintk((MYIOC_s_INFO_FMT "Got TURBO reply req_idx=%08x\n",
14772                                 ioc->name, pa));
14773  
14774         switch (pa >> MPI_CONTEXT_REPLY_TYPE_SHIFT) {
14775 @@ -312,9 +303,7 @@ mpt_turbo_reply(MPT_ADAPTER *ioc, u32 pa
14776                 break;
14777         default:
14778                 cb_idx = 0;
14779 -               printk(MYIOC_s_WARN_FMT "%s: Invalid REPLY_TYPE in pa=%08x!\n",
14780 -                       __FUNCTION__, ioc->name, pa);
14781 -//             BUG();
14782 +               BUG();
14783         }
14784  
14785         /*  Check for (valid) IO callback!  */
14786 @@ -342,12 +331,6 @@ mpt_reply(MPT_ADAPTER *ioc, u32 pa)
14787  
14788         u32 reply_dma_low;
14789         u16 ioc_stat;
14790 -#ifdef MPT_DEBUG_REPLY
14791 -       u8  function;
14792 -       MPT_FRAME_HDR *chain;
14793 -       int chain_idx, chain_number, next;
14794 -#endif
14795 -
14796  
14797         /* non-TURBO reply!  Hmmm, something may be up...
14798          *  Newest turbo reply mechanism; get address
14799 @@ -367,44 +350,21 @@ mpt_reply(MPT_ADAPTER *ioc, u32 pa)
14800         cb_idx = mr->u.frame.hwhdr.msgctxu.fld.cb_idx;
14801         mf = MPT_INDEX_2_MFPTR(ioc, req_idx);
14802  
14803 -       ioc_stat = le16_to_cpu(mr->u.reply.IOCStatus);
14804 -#ifdef MPT_DEBUG_REPLY
14805 -         if ((ioc_stat != MPI_IOCSTATUS_SCSI_DEVICE_NOT_THERE) && /* 0x0043 */
14806 -             (ioc_stat != MPI_IOCSTATUS_SCSI_DATA_UNDERRUN)) {    /* 0x0045 */
14807 -               function = mr->u.hdr.Function;
14808 -               dreplyprintk((MYIOC_s_WARN_FMT "non-TURBO reply context=%04x%04x Function=%x IOCStatus=%04x\n",
14809 -                       ioc->name, cb_idx, req_idx, function, ioc_stat));
14810 -               DBG_DUMP_REPLY_FRAME(mr)
14811 -
14812 -               printk("Request:\n");
14813 -                DBG_DUMP_REPLYS_REQUEST_FRAME(ioc, mf)
14814 -               chain_number = 1;
14815 -               chain_idx = ioc->ReqToChain[req_idx];
14816 -               while (chain_idx != MPT_HOST_NO_CHAIN) {
14817 -                       next = ioc->ChainToChain[chain_idx];
14818 -                       chain = (MPT_FRAME_HDR *) (ioc->ChainBuffer
14819 -                               + (chain_idx * ioc->req_sz));
14820 -                       printk("Chain %d:\n", chain_number++);
14821 -                        DBG_DUMP_REPLYS_REQUEST_FRAME(ioc, chain)
14822 -                       chain_idx = next;
14823 -               }
14824 -       }
14825 -#endif
14826 +       dmfprintk((MYIOC_s_INFO_FMT "Got non-TURBO reply=%p req_idx=%x cb_idx=%x Function=%x\n",
14827 +                       ioc->name, mr, req_idx, cb_idx, mr->u.hdr.Function));
14828 +       DBG_DUMP_REPLY_FRAME(mr)
14829  
14830          /*  Check/log IOC log info
14831          */
14832 +       ioc_stat = le16_to_cpu(mr->u.reply.IOCStatus);
14833         if (ioc_stat & MPI_IOCSTATUS_FLAG_LOG_INFO_AVAILABLE) {
14834                 u32      log_info = le32_to_cpu(mr->u.reply.IOCLogInfo);
14835                 if (ioc->bus_type == FC)
14836                         mpt_fc_log_info(ioc, log_info);
14837                 else if (ioc->bus_type == SPI)
14838                         mpt_spi_log_info(ioc, log_info);
14839 -               else if (ioc->bus_type == SAS) {
14840 -                       printk(MYIOC_s_INFO_FMT
14841 -                               "IOCStatus=%04x LogInfo=%08x ",
14842 -                               ioc->name, ioc_stat, log_info);
14843 +               else if (ioc->bus_type == SAS)
14844                         mpt_sas_log_info(ioc, log_info);
14845 -               }
14846         }
14847         if (ioc_stat & MPI_IOCSTATUS_MASK) {
14848                 if (ioc->bus_type == SPI &&
14849 @@ -432,31 +392,6 @@ mpt_reply(MPT_ADAPTER *ioc, u32 pa)
14850         if (freeme)
14851                 mpt_free_msg_frame(ioc, mf);
14852         mb();
14853 -if (ioc->CheckFcLinkSpeed &&
14854 -           ioc->FcLinkSpeedCheckNeeded &&
14855 -           ioc->FcLinkSpeedReqActive == NULL &&
14856 -           (mf = mpt_get_msg_frame(mpt_base_index, ioc))) {
14857 -               pConfig_t       pConfigMsg;
14858 -               dma_addr_t      physAddr;
14859 -
14860 -               ioc->FcLinkSpeedCheckNeeded = 0;
14861 -               ioc->FcLinkSpeedReqActive = mf;
14862 -               pConfigMsg = (pConfig_t)mf;
14863 -               /* there's enough room, so FCPortPage0 will be put in the mf */
14864 -               physAddr = ioc->req_frames_dma + sizeof(pConfig_t) +
14865 -                       (u8 *)mf - (u8 *)ioc->req_frames;
14866 -               memset(pConfigMsg, 0, ioc->req_sz);
14867 -               pConfigMsg->Action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
14868 -               pConfigMsg->Function = MPI_FUNCTION_CONFIG;
14869 -               pConfigMsg->Header.PageType = MPI_CONFIG_PAGETYPE_FC_PORT;
14870 -               pConfigMsg->Header.PageNumber = 0;
14871 -               pConfigMsg->Header.PageLength = sizeof(FCPortPage0_t) / 4;
14872 -               pConfigMsg->Header.PageVersion = MPI_FCPORTPAGE0_PAGEVERSION;
14873 -               mpt_add_sge((char *)&pConfigMsg->PageBufferSGE,
14874 -                       MPT_SGE_FLAGS_SSIMPLE_READ + sizeof(FCPortPage0_t),
14875 -                       physAddr);
14876 -               mpt_put_msg_frame(mpt_base_index, ioc, mf);
14877 -        }
14878  }
14879  
14880  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
14881 @@ -543,17 +478,15 @@ mpt_base_reply(MPT_ADAPTER *ioc, MPT_FRA
14882                 }
14883  
14884                 /*
14885 -                *       EventNotificationReply is an exception
14886 +                *      Hmmm...  It seems that EventNotificationReply is an exception
14887                  *      to the rule of one reply per request.
14888                  */
14889                 if (pEvReply->MsgFlags & MPI_MSGFLAGS_CONTINUATION_REPLY) {
14890                         freereq = 0;
14891                 } else {
14892 -                    devtprintk((MYIOC_s_WARN_FMT "EVENT_NOTIFICATION reply %p returns mf=%p evnp=%p\n", ioc->name, pEvReply, mf, ioc->evnp));
14893 -              if ( (MPT_FRAME_HDR *)ioc->evnp == mf ) {
14894 -                         ioc->evnp = NULL;
14895 -                   }
14896 - }
14897 +                       devtprintk((MYIOC_s_WARN_FMT "EVENT_NOTIFICATION reply %p returns Request frame\n",
14898 +                               ioc->name, pEvReply));
14899 +               }
14900  
14901  #ifdef CONFIG_PROC_FS
14902  //             LogEvent(ioc, pEvReply);
14903 @@ -562,7 +495,7 @@ mpt_base_reply(MPT_ADAPTER *ioc, MPT_FRA
14904         } else if (func == MPI_FUNCTION_EVENT_ACK) {
14905                 dprintk((MYIOC_s_INFO_FMT "mpt_base_reply, EventAck reply received\n",
14906                                 ioc->name));
14907 -       } else if (func == MPI_FUNCTION_CONFIG ) {
14908 +       } else if (func == MPI_FUNCTION_CONFIG) {
14909                 CONFIGPARMS *pCfg;
14910                 unsigned long flags;
14911  
14912 @@ -617,29 +550,7 @@ mpt_base_reply(MPT_ADAPTER *ioc, MPT_FRA
14913                          */
14914                         pCfg->wait_done = 1;
14915                         wake_up(&mpt_waitq);
14916 -               }else if (mf == ioc->FcLinkSpeedReqActive) {
14917 -     pFCPortPage0_t  pFCPortPage0 = (pFCPortPage0_t)((u8 *)mf + sizeof(pConfig_t));
14918 -                u8 OldSpeed = ioc->FcLinkSpeed;
14919 -               u8 NewSpeed = pFCPortPage0->CurrentSpeed;
14920 -               u8 State = pFCPortPage0->PortState;
14921 -                ioc->FcLinkSpeedReqActive = NULL;
14922 -                       if (State != MPI_FCPORTPAGE0_PORTSTATE_OFFLINE &&
14923 -                           NewSpeed != MPI_FCPORTPAGE0_CURRENT_SPEED_UKNOWN) {
14924 -                               char    *old;
14925 -                               char    *new;
14926 - old = OldSpeed == MPI_FCPORTPAGE0_CURRENT_SPEED_1GBIT ? "1 Gbps" :OldSpeed == MPI_FCPORTPAGE0_CURRENT_SPEED_2GBIT ? "2 Gbps" :OldSpeed == MPI_FCPORTPAGE0_CURRENT_SPEED_4GBIT ? "4 Gbps" :
14927 - "Unknown";
14928 -new = NewSpeed == MPI_FCPORTPAGE0_CURRENT_SPEED_1GBIT ? "1 Gbps" :NewSpeed == MPI_FCPORTPAGE0_CURRENT_SPEED_2GBIT ? "2 Gbps" :
14929 -NewSpeed == MPI_FCPORTPAGE0_CURRENT_SPEED_4GBIT ? "4 Gbps" : "Unknown";
14930 -
14931 -if (OldSpeed == 0) { printk(MYIOC_s_NOTE_FMT "FC Link Established, Speed = %s\n", ioc->name, new);
14932 -       } else if (OldSpeed != NewSpeed)
14933 -{
14934 -printk(MYIOC_s_WARN_FMT "FC Link Speed Change, Old Speed = %s, New Speed = %s\n",ioc->name, old, new);
14935 -}
14936 -ioc->FcLinkSpeed = NewSpeed;
14937 -}
14938 -}
14939 +               }
14940         } else if (func == MPI_FUNCTION_SAS_IO_UNIT_CONTROL) {
14941                 /* we should be always getting a reply frame */
14942                 memcpy(ioc->persist_reply_frame, reply,
14943 @@ -868,10 +779,6 @@ MPT_FRAME_HDR*
14944  mpt_get_msg_frame(int handle, MPT_ADAPTER *ioc)
14945  {
14946         MPT_FRAME_HDR *mf;
14947 -        #ifdef MPT_DEBUG_FAIL
14948 -          u8      *mem;
14949 -        #endif
14950 -
14951         unsigned long flags;
14952         u16      req_idx;       /* Request index */
14953  
14954 @@ -884,10 +791,7 @@ mpt_get_msg_frame(int handle, MPT_ADAPTE
14955  
14956         /* If interrupts are not attached, do not return a request frame */
14957         if (!ioc->active)
14958 -       {
14959 -            printk(KERN_WARNING "IOC Not Active! mpt_get_msg_frame!!\n");
14960                 return NULL;
14961 -       }
14962  
14963         spin_lock_irqsave(&ioc->FreeQlock, flags);
14964         if (!list_empty(&ioc->FreeQ)) {
14965 @@ -907,36 +811,10 @@ mpt_get_msg_frame(int handle, MPT_ADAPTE
14966  #ifdef MFCNT
14967                 ioc->mfcnt++;
14968  #endif
14969 -       } else {
14970 -#ifdef MPT_DEBUG_FAIL
14971 -dfailprintk((MYIOC_s_WARN_FMT "%s, No Free Message Frame!!\n",
14972 -     ioc->name,__FUNCTION__));
14973 -               mem = (u8 *) ioc->req_frames;
14974 -               for (req_idx = 0; req_idx < 10; req_idx++) {
14975 -       {
14976 -               u32     *m = (u32 *)(mem);
14977 -               int      ii, n;
14978 -
14979 -               printk(KERN_WARNING MYNAM ": %s: msg frame %d @ %p:\n" KERN_INFO " ",
14980 -                               ioc->name, req_idx, m);
14981 -               n = ioc->req_sz/4;
14982 -               for (ii=0; ii<n; ii++) {
14983 -                       if (ii && ((ii%8)==0))
14984 -                               printk("\n");
14985 -                       printk("%08x ", le32_to_cpu(m[ii]));
14986 -               }
14987 -               printk("\n");
14988 -          }
14989 -               mem += ioc->req_sz;
14990 -               }
14991 -#endif
14992 -
14993 -
14994 -
14995 -mf = NULL;
14996 -}
14997 -spin_unlock_irqrestore(&ioc->FreeQlock, flags);
14998 -
14999 +       }
15000 +       else
15001 +               mf = NULL;
15002 +       spin_unlock_irqrestore(&ioc->FreeQlock, flags);
15003  
15004  #ifdef MFCNT
15005         if (mf == NULL)
15006 @@ -984,13 +862,13 @@ mpt_put_msg_frame(int handle, MPT_ADAPTE
15007  
15008                 printk(KERN_INFO MYNAM ": %s: About to Put msg frame @ %p:\n" KERN_INFO " ",
15009                                 ioc->name, m);
15010 -               n = ioc->req_sz/4 ;
15011 +               n = ioc->req_sz/4 - 1;
15012                 while (m[n] == 0)
15013                         n--;
15014                 for (ii=0; ii<=n; ii++) {
15015                         if (ii && ((ii%8)==0))
15016                                 printk("\n" KERN_INFO " ");
15017 -                       printk("%08x ", le32_to_cpu(m[ii]));
15018 +                       printk(" %08x", le32_to_cpu(m[ii]));
15019                 }
15020                 printk("\n");
15021         }
15022 @@ -1074,14 +952,16 @@ mpt_add_sge(char *pAddr, u32 flagslength
15023   *     Returns 0 for success, non-zero for failure.
15024   */
15025  int
15026 -mpt_send_handshake_request(int handle, MPT_ADAPTER *ioc, int reqBytes, u32 *req, ulong timeout, int sleepFlag)
15027 +mpt_send_handshake_request(int handle, MPT_ADAPTER *ioc, int reqBytes, u32 *req, int sleepFlag)
15028  {
15029 -       int     r = 0;
15030 +       int              r = 0;
15031         u8      *req_as_bytes;
15032 -       int     ii;
15033 +       int      ii;
15034  
15035 -       dtmprintk((KERN_WARNING MYNAM ": %s: mpt_send_handshake_request reqBytes=%d\n",
15036 -               ioc->name, reqBytes));
15037 +       /* State is known to be good upon entering
15038 +        * this function so issue the bus reset
15039 +        * request.
15040 +        */
15041  
15042         /*
15043          * Emulate what mpt_put_msg_frame() does /wrt to sanity
15044 @@ -1089,16 +969,12 @@ mpt_send_handshake_request(int handle, M
15045          * is in proper (pre-alloc'd) request buffer range...
15046          */
15047         ii = MFPTR_2_MPT_INDEX(ioc,(MPT_FRAME_HDR*)req);
15048 -       if (ii >= 0 && ii < ioc->req_depth) {
15049 +       if (reqBytes >= 12 && ii >= 0 && ii < ioc->req_depth) {
15050                 MPT_FRAME_HDR *mf = (MPT_FRAME_HDR*)req;
15051                 mf->u.frame.hwhdr.msgctxu.fld.req_idx = cpu_to_le16(ii);
15052                 mf->u.frame.hwhdr.msgctxu.fld.cb_idx = handle;
15053         }
15054  
15055 -               ioc->tmPtr = (MPT_FRAME_HDR *)req;
15056 -               ioc->TMtimer.expires = jiffies + HZ*timeout;  /* seconds */
15057 -               add_timer(&ioc->TMtimer);
15058 -
15059         /* Make sure there are no doorbells */
15060         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
15061  
15062 @@ -1108,25 +984,20 @@ mpt_send_handshake_request(int handle, M
15063  
15064         /* Wait for IOC doorbell int */
15065         if ((ii = WaitForDoorbellInt(ioc, 5, sleepFlag)) < 0) {
15066 -               r= ii;
15067 -                goto mpt_send_handshake_failed;
15068 +               return ii;
15069         }
15070  
15071         /* Read doorbell and check for active bit */
15072 -       if (!(CHIPREG_READ32(&ioc->chip->Doorbell) & MPI_DOORBELL_ACTIVE)){
15073 -               r= -5;
15074 -                goto mpt_send_handshake_failed;
15075 -           }
15076 -
15077 +       if (!(CHIPREG_READ32(&ioc->chip->Doorbell) & MPI_DOORBELL_ACTIVE))
15078 +               return -5;
15079  
15080         dhsprintk((KERN_INFO MYNAM ": %s: mpt_send_handshake_request start, WaitCnt=%d\n",
15081                 ioc->name, ii));
15082  
15083         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
15084  
15085 -        if ((WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0) {
15086 -            r=-2;
15087 -             goto mpt_send_handshake_failed;
15088 +       if ((r = WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0) {
15089 +               return -2;
15090         }
15091  
15092         /* Send request via doorbell handshake */
15093 @@ -1138,33 +1009,21 @@ mpt_send_handshake_request(int handle, M
15094                         (req_as_bytes[(ii*4) + 1] <<  8) |
15095                         (req_as_bytes[(ii*4) + 2] << 16) |
15096                         (req_as_bytes[(ii*4) + 3] << 24));
15097 -dtmprintk((KERN_WARNING MYNAM ": %s: mpt_send_handshake_request word=%08x ii=%d\n",ioc->name, word, ii));
15098 -
15099                 CHIPREG_WRITE32(&ioc->chip->Doorbell, word);
15100 -               if ( WaitForDoorbellAck(ioc, 5, sleepFlag) < 0) {
15101 +               if ((r = WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0) {
15102                         r = -3;
15103 -                       goto mpt_send_handshake_failed;
15104 +                       break;
15105                 }
15106         }
15107  
15108 -       dtmprintk((KERN_WARNING MYNAM ": %s: mpt_send_handshake_request reqBytes=%d sent, WaitForDoorbellInt\n",
15109 -               ioc->name, reqBytes));
15110 -
15111 -       if ( WaitForDoorbellInt(ioc, 10, sleepFlag)< 0)
15112 +       if (r >= 0 && WaitForDoorbellInt(ioc, 10, sleepFlag) >= 0)
15113 +               r = 0;
15114 +       else
15115                 r = -4;
15116  
15117         /* Make sure there are no doorbells */
15118         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
15119  
15120 -mpt_send_handshake_failed:
15121 -       if (r < 0) {
15122 -               del_timer(&ioc->TMtimer);
15123 -               ioc->tmPtr = NULL;
15124 -       }
15125 -       dtmprintk((KERN_WARNING MYNAM ": %s: mpt_send_handshake_request r=%d\n",
15126 -               ioc->name, r));
15127 -
15128 -
15129         return r;
15130  }
15131  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
15132 @@ -1186,6 +1045,7 @@ mpt_send_handshake_failed:
15133  static int
15134  mpt_host_page_access_control(MPT_ADAPTER *ioc, u8 access_control_value, int sleepFlag)
15135  {
15136 +       int      r = 0;
15137  
15138         /* return if in use */
15139         if (CHIPREG_READ32(&ioc->chip->Doorbell)
15140 @@ -1200,7 +1060,7 @@ mpt_host_page_access_control(MPT_ADAPTER
15141                  (access_control_value<<12)));
15142  
15143         /* Wait for IOC to clear Doorbell Status bit */
15144 -       if (( WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0) {
15145 +       if ((r = WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0) {
15146                 return -2;
15147         }else
15148                 return 0;
15149 @@ -1344,10 +1204,20 @@ mpt_bringup_adapter(MPT_ADAPTER *ioc, in
15150  {
15151         int r;
15152  
15153 +       if(ioc->alt_ioc) {
15154 +               if((r=mpt_alt_ioc_wait(ioc->alt_ioc)!=0))
15155 +                       return r;
15156 +       }
15157  
15158         r = mpt_do_ioc_recovery(ioc, MPT_HOSTEVENT_IOC_BRINGUP,
15159             CAN_SLEEP);
15160  
15161 +       if(ioc->alt_ioc) {
15162 +               spin_lock(&ioc->alt_ioc->initializing_hba_lock);
15163 +               ioc->alt_ioc->initializing_hba_lock_flag=0;
15164 +               spin_unlock(&ioc->alt_ioc->initializing_hba_lock);
15165 +       }
15166 +
15167  return r;
15168  }
15169  
15170 @@ -1383,8 +1253,6 @@ mpt_attach(struct pci_dev *pdev, const s
15171         u8               revision;
15172         u8               pcixcmd;
15173         static int       mpt_ids = 0;
15174 -        unsigned long flags;
15175 -
15176  #ifdef CONFIG_PROC_FS
15177         struct proc_dir_entry *dent, *ent;
15178  #endif
15179 @@ -1420,7 +1288,6 @@ mpt_attach(struct pci_dev *pdev, const s
15180         ioc->reply_sz = MPT_REPLY_FRAME_SIZE;
15181  
15182         ioc->pcidev = pdev;
15183 -        ioc->IOCResetInProgress = 0;
15184         ioc->diagPending = 0;
15185         spin_lock_init(&ioc->diagLock);
15186         spin_lock_init(&ioc->initializing_hba_lock);
15187 @@ -1596,17 +1463,10 @@ mpt_attach(struct pci_dev *pdev, const s
15188         if(ioc->errata_flag_1064) {
15189                 pci_disable_io_access(pdev);
15190         }
15191 -           if(ioc->bus_type == FC) {
15192 -               ioc->CheckFcLinkSpeed = 1;
15193 -               ioc->FcLinkSpeed = 0;
15194 -        }
15195 -
15196  
15197         sprintf(ioc->name, "ioc%d", ioc->id);
15198  
15199         spin_lock_init(&ioc->FreeQlock);
15200 -        spin_lock_init(&ioc->PendingMFlock);
15201 -
15202  
15203         /* Disable all! */
15204         CHIPREG_WRITE32(&ioc->chip->IntMask, 0xFFFFFFFF);
15205 @@ -1659,43 +1519,22 @@ mpt_attach(struct pci_dev *pdev, const s
15206          */
15207         mpt_detect_bound_ports(ioc, pdev);
15208  
15209 -if(mpt_enable_deadioc_detect){
15210 -/* The following list initializations is moved from PrimeIocFifos
15211 -                because the lists will not get initialize for non-operational
15212 -                IOCs and which cause a crash when the lists are accessed later
15213 -                */
15214 -/* Initialize the free chain Q.*/
15215 -
15216 -        INIT_LIST_HEAD(&ioc->FreeChainQ);
15217 -        spin_lock_irqsave(&ioc->FreeQlock, flags);
15218 -        INIT_LIST_HEAD(&ioc->FreeQ);
15219 -        spin_unlock_irqrestore(&ioc->FreeQlock, flags);
15220 -        init_MUTEX(&ioc->raid_data.inactive_list_mutex);
15221 -        INIT_LIST_HEAD(&ioc->raid_data.inactive_list);
15222 -
15223 -       /* Even If there is any error in IOC bringup, the IOC is allowed to
15224 -               be attached with MPT drivers, This change is done to support
15225 -               Firmware download boot functionality for FW dead IOC */
15226 -       mpt_bringup_adapter(ioc, CAN_SLEEP);
15227 -     }
15228 -
15229 -else {
15230 -        if ((r = mpt_bringup_adapter(ioc, CAN_SLEEP)) != 0){
15231 -            printk(KERN_WARNING MYNAM
15232 -               ": WARNING - %s did not initialize properly! (%d)\n",
15233 -               ioc->name, r);
15234 -               list_del(&ioc->list);
15235 -               free_irq(ioc->pci_irq, ioc);
15236 -               if (mpt_msi_enable == 1) {
15237 -                      pci_disable_msi(pdev);
15238 -               }
15239 -               iounmap(mem);
15240 -               kfree(ioc);
15241 -              pci_set_drvdata(pdev, NULL);
15242 -               return r;
15243 +       if ((r = mpt_bringup_adapter(ioc, CAN_SLEEP)) != 0){
15244 +               printk(KERN_WARNING MYNAM
15245 +                 ": WARNING - %s did not initialize properly! (%d)\n",
15246 +                 ioc->name, r);
15247 +
15248 +               list_del(&ioc->list);
15249 +               free_irq(ioc->pci_irq, ioc);
15250 +               if (mpt_msi_enable == 1) {
15251 +                       pci_disable_msi(pdev);
15252 +               }
15253 +               iounmap(mem);
15254 +               kfree(ioc);
15255 +               pci_set_drvdata(pdev, NULL);
15256 +               return r;
15257         }
15258  
15259 -}
15260         /* call per device driver probe entry point */
15261         for(ii=0; ii<MPT_MAX_PROTOCOL_DRIVERS; ii++) {
15262                 if(MptDeviceDriverHandlers[ii] &&
15263 @@ -1812,7 +1651,7 @@ mpt_suspend(struct pci_dev *pdev, pm_mes
15264  #endif
15265  
15266         /* put ioc into READY_STATE */
15267 -       if(mpt_SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, CAN_SLEEP)) {
15268 +       if(SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, CAN_SLEEP)) {
15269                 printk(MYIOC_s_ERR_FMT
15270                 "pci-suspend:  IOC msg unit reset failed!\n", ioc->name);
15271         }
15272 @@ -1864,8 +1703,7 @@ mpt_resume(struct pci_dev *pdev)
15273         if(!CHIPREG_READ32(&ioc->chip->Doorbell)) {
15274                 /* enable domain validation flags */
15275                 for (ii=0; ii < MPT_MAX_SCSI_DEVICES; ii++) {
15276 -                       ioc->spi_data.dvStatus[ii] |= (MPT_SCSICFG_NEED_DV |
15277 -                                                             MPT_SCSICFG_DV_NOT_DONE);
15278 +                       ioc->spi_data.dvStatus[ii] |= MPT_SCSICFG_NEED_DV;
15279                 }
15280         }
15281  
15282 @@ -1905,19 +1743,23 @@ mpt_resume(struct pci_dev *pdev)
15283   *
15284   *     Returns:
15285   *              0 for success
15286 - *             -1 if failed to get board READY
15287 + *             -1 if failed to get boardMODULE_VERSION(MPT_LINUX_VERSION_COMMON);
15288 + READY
15289   *             -2 if READY but IOCFacts Failed
15290   *             -3 if READY but PrimeIOCFifos Failed
15291   *             -4 if READY but IOCInit Failed
15292   */
15293 -int mpt_do_ioc_recovery(MPT_ADAPTER *ioc, u32 reason, int sleepFlag)
15294 -{       unsigned long flags;
15295 +static int
15296 +mpt_do_ioc_recovery(MPT_ADAPTER *ioc, u32 reason, int sleepFlag)
15297 +{
15298         int      hard_reset_done = 0;
15299 +       int      alt_ioc_ready = 0;
15300         int      hard;
15301         int      rc = 0;
15302         int      ii;
15303 +       int      handlers;
15304         int      ret = 0;
15305 -
15306 +       int      reset_alt_ioc_active = 0;
15307  
15308         printk(KERN_INFO MYNAM ": Initiating %s %s\n",
15309                         ioc->name, reason==MPT_HOSTEVENT_IOC_BRINGUP ? "bringup" : "recovery");
15310 @@ -1926,15 +1768,13 @@ int mpt_do_ioc_recovery(MPT_ADAPTER *ioc
15311         CHIPREG_WRITE32(&ioc->chip->IntMask, 0xFFFFFFFF);
15312         ioc->active = 0;
15313  
15314 -/* If an event notification has not returned
15315 - * its request frame,
15316 - * free resources associated with this request.
15317 - */
15318 -        if (ioc->evnp) {
15319 -            drsprintk((MYIOC_s_WARN_FMT "do_ioc_recovery: freeing evnp=%p\n",
15320 -                 ioc->name, ioc->evnp));
15321 -            mpt_free_msg_frame(ioc, (MPT_FRAME_HDR *)ioc->evnp);
15322 -            ioc->evnp = NULL;
15323 +       if (ioc->alt_ioc) {
15324 +               if (ioc->alt_ioc->active)
15325 +                       reset_alt_ioc_active = 1;
15326 +
15327 +               /* Disable alt-IOC's reply interrupts (and FreeQ) for a bit ... */
15328 +               CHIPREG_WRITE32(&ioc->alt_ioc->chip->IntMask, 0xFFFFFFFF);
15329 +               ioc->alt_ioc->active = 0;
15330         }
15331  
15332         hard = 1;
15333 @@ -1945,39 +1785,68 @@ int mpt_do_ioc_recovery(MPT_ADAPTER *ioc
15334                 if (hard_reset_done == -4) {
15335                         printk(KERN_WARNING MYNAM ": %s Owned by PEER..skipping!\n",
15336                                         ioc->name);
15337 +
15338 +                       if (reset_alt_ioc_active && ioc->alt_ioc) {
15339 +                               /* (re)Enable alt-IOC! (reply interrupt, FreeQ) */
15340 +                               dprintk((KERN_INFO MYNAM ": alt-%s reply irq re-enabled\n",
15341 +                                               ioc->alt_ioc->name));
15342 +                               CHIPREG_WRITE32(&ioc->alt_ioc->chip->IntMask, MPI_HIM_DIM);
15343 +                               ioc->alt_ioc->active = 1;
15344 +                       }
15345 +
15346                 } else {
15347                         printk(KERN_WARNING MYNAM ": %s NOT READY WARNING!\n",
15348                                         ioc->name);
15349                 }
15350 -
15351 -               spin_lock_irqsave(&ioc->diagLock, flags);
15352 -               ioc->IOCResetInProgress = 0;
15353 -               spin_unlock_irqrestore(&ioc->diagLock, flags);
15354                 return -1;
15355         }
15356  
15357 +       /* hard_reset_done = 0 if a soft reset was performed
15358 +        * and 1 if a hard reset was performed.
15359 +        */
15360 +       if (hard_reset_done && reset_alt_ioc_active && ioc->alt_ioc) {
15361 +               if ((rc = MakeIocReady(ioc->alt_ioc, 0, sleepFlag)) == 0)
15362 +                       alt_ioc_ready = 1;
15363 +               else
15364 +                       printk(KERN_WARNING MYNAM
15365 +                                       ": alt-%s: Not ready WARNING!\n",
15366 +                                       ioc->alt_ioc->name);
15367 +       }
15368 +
15369 +       for (ii=0; ii<5; ii++) {
15370 +               /* Get IOC facts! Allow 5 retries */
15371 +               if ((rc = GetIocFacts(ioc, sleepFlag, reason)) == 0)
15372 +                       break;
15373 +       }
15374  
15375 -if (reason == MPT_HOSTEVENT_IOC_BRINGUP ||
15376 -                        mpt_enable_deadioc_detect){
15377 -             for (ii=0; ii<5; ii++) {
15378 -                /* Get IOC facts! Allow 5 retries */
15379 -                   if ((rc = GetIocFacts(ioc, sleepFlag, reason)) == 0)
15380 -                               break;
15381 -}
15382  
15383 +       if (ii == 5) {
15384 +               dinitprintk((MYIOC_s_INFO_FMT "Retry IocFacts failed rc=%x\n", ioc->name, rc));
15385 +               ret = -2;
15386 +       } else if (reason == MPT_HOSTEVENT_IOC_BRINGUP) {
15387 +               MptDisplayIocCapabilities(ioc);
15388 +       }
15389  
15390 -if(ii==5) {
15391 -dinitprintk((MYIOC_s_INFO_FMT "Retry IocFacts failed rc=%x\n", ioc->name , rc));
15392 -             ret = -2;
15393 -        } else {
15394 -       if (reason == MPT_HOSTEVENT_IOC_BRINGUP)
15395 -         MptDisplayIocCapabilities(ioc);
15396 +       if (alt_ioc_ready) {
15397 +               if ((rc = GetIocFacts(ioc->alt_ioc, sleepFlag, reason)) != 0) {
15398 +                       dinitprintk((MYIOC_s_INFO_FMT "Initial Alt IocFacts failed rc=%x\n", ioc->name, rc));
15399 +                       /* Retry - alt IOC was initialized once
15400 +                        */
15401 +                       rc = GetIocFacts(ioc->alt_ioc, sleepFlag, reason);
15402 +               }
15403 +               if (rc) {
15404 +                       dinitprintk((MYIOC_s_INFO_FMT "Retry Alt IocFacts failed rc=%x\n", ioc->name, rc));
15405 +                       alt_ioc_ready = 0;
15406 +                       reset_alt_ioc_active = 0;
15407 +               } else if (reason == MPT_HOSTEVENT_IOC_BRINGUP) {
15408 +                       MptDisplayIocCapabilities(ioc->alt_ioc);
15409                 }
15410         }
15411  
15412         /* Prime reply & request queues!
15413          * (mucho alloc's) Must be done prior to
15414          * init as upper addresses are needed for init.
15415 +        * If fails, continue with alt-ioc processing
15416          */
15417         if ((ret == 0) && ((rc = PrimeIocFifos(ioc)) != 0))
15418                 ret = -3;
15419 @@ -1987,6 +1856,23 @@ dinitprintk((MYIOC_s_INFO_FMT "Retry Ioc
15420          */
15421         if ((ret == 0) && ((rc = SendIocInit(ioc, sleepFlag)) != 0))
15422                 ret = -4;
15423 +// NEW!
15424 +       if (alt_ioc_ready && ((rc = PrimeIocFifos(ioc->alt_ioc)) != 0)) {
15425 +               printk(KERN_WARNING MYNAM ": alt-%s: (%d) FIFO mgmt alloc WARNING!\n",
15426 +                               ioc->alt_ioc->name, rc);
15427 +               alt_ioc_ready = 0;
15428 +               reset_alt_ioc_active = 0;
15429 +       }
15430 +
15431 +       if (alt_ioc_ready) {
15432 +               if ((rc = SendIocInit(ioc->alt_ioc, sleepFlag)) != 0) {
15433 +                       alt_ioc_ready = 0;
15434 +                       reset_alt_ioc_active = 0;
15435 +                       printk(KERN_WARNING MYNAM
15436 +                               ": alt-%s: (%d) init failure WARNING!\n",
15437 +                                       ioc->alt_ioc->name, rc);
15438 +               }
15439 +       }
15440  
15441         if (reason == MPT_HOSTEVENT_IOC_BRINGUP){
15442                 if (ioc->upload_fw) {
15443 @@ -2024,6 +1910,13 @@ dinitprintk((MYIOC_s_INFO_FMT "Retry Ioc
15444                 ioc->active = 1;
15445         }
15446  
15447 +       if (reset_alt_ioc_active && ioc->alt_ioc) {
15448 +               /* (re)Enable alt-IOC! (reply interrupt) */
15449 +               dinitprintk((KERN_INFO MYNAM ": alt-%s reply irq re-enabled\n",
15450 +                               ioc->alt_ioc->name));
15451 +               CHIPREG_WRITE32(&ioc->alt_ioc->chip->IntMask, MPI_HIM_DIM);
15452 +               ioc->alt_ioc->active = 1;
15453 +       }
15454  
15455         /*  Enable MPT base driver management of EventNotification
15456          *  and EventAck handling.
15457 @@ -2031,6 +1924,9 @@ dinitprintk((MYIOC_s_INFO_FMT "Retry Ioc
15458         if ((ret == 0) && (!ioc->facts.EventState))
15459                 (void) SendEventNotification(ioc, 1);   /* 1=Enable EventNotification */
15460  
15461 +       if (ioc->alt_ioc && alt_ioc_ready && !ioc->alt_ioc->facts.EventState)
15462 +               (void) SendEventNotification(ioc->alt_ioc, 1);  /* 1=Enable EventNotification */
15463 +
15464         /*      Add additional "reason" check before call to GetLanConfigPages
15465          *      (combined with GetIoUnitPage2 call).  This prevents a somewhat
15466          *      recursive scenario; GetLanConfigPages times out, timer expired
15467 @@ -2038,30 +1934,32 @@ dinitprintk((MYIOC_s_INFO_FMT "Retry Ioc
15468          *      and we try GetLanConfigPages again...
15469          */
15470         if ((ret == 0) && (reason == MPT_HOSTEVENT_IOC_BRINGUP)) {
15471 -
15472 -               /*
15473 -                * Initalize link list for inactive raid volumes.
15474 -                */
15475 -               init_MUTEX(&ioc->raid_data.inactive_list_mutex);
15476 -               INIT_LIST_HEAD(&ioc->raid_data.inactive_list);
15477 -
15478                 if (ioc->bus_type == SAS) {
15479 +
15480                         /*
15481                          * Pre-fetch SAS Address for each port
15482                          */
15483                         GetManufPage5(ioc, ioc->facts.NumberOfPorts);
15484  
15485 +                       /*
15486 +                        * Pre-fetch Serial number for the board.
15487 +                        */
15488 +                       GetManufPage0(ioc);
15489 +
15490 +                       /*
15491 +                        * Pre-fetch Hw Link Rates. (These may get
15492 +                        * overwritten so need to save them.)
15493 +                        * Save other SAS data needed for Ioctls.
15494 +                        */
15495 +                       mpt_sas_get_info(ioc);
15496 +
15497                         /* clear persistency table */
15498                         if(ioc->facts.IOCExceptions &
15499                             MPI_IOCFACTS_EXCEPT_PERSISTENT_TABLE_FULL) {
15500                                 ret = mptbase_sas_persist_operation(ioc,
15501                                     MPI_SAS_OP_CLEAR_NOT_PRESENT);
15502 -                               if(ret != 0){
15503 -                                 spin_lock_irqsave(&ioc->diagLock, flags);
15504 -                                       ioc->IOCResetInProgress = 0;
15505 -                                       spin_unlock_irqrestore(&ioc->diagLock, flags);
15506 +                               if(ret != 0)
15507                                         return -1;
15508 -                                        }
15509                         }
15510  
15511                         /* Find IM volumes
15512 @@ -2118,11 +2016,6 @@ dinitprintk((MYIOC_s_INFO_FMT "Retry Ioc
15513                 }
15514  
15515                 GetIoUnitPage2(ioc);
15516 -
15517 -               /*
15518 -                * Pre-fetch Serial number for the board.
15519 -                */
15520 -               GetManufPage0(ioc);
15521         }
15522  
15523         /*
15524 @@ -2131,35 +2024,26 @@ dinitprintk((MYIOC_s_INFO_FMT "Retry Ioc
15525          * NOTE: If we're doing _IOC_BRINGUP, there can be no
15526          * MptResetHandlers[] registered yet.
15527          */
15528 -                if (ret == 0) {
15529 -                       rc = 0;
15530 -
15531 -               for (ii=MPT_MAX_PROTOCOL_DRIVERS-1; ii; ii--) {
15532 -                         if (MptResetHandlers[ii]) {
15533 -       drsprintk((MYIOC_s_INFO_FMT "Calling IOC post_reset handler #%d\ n",ioc->name, ii));
15534 -
15535 +       if (hard_reset_done) {
15536 +               rc = handlers = 0;
15537 +               for (ii=MPT_MAX_PROTOCOL_DRIVERS-1; ii; ii--) {
15538 +                       if ((ret == 0) && MptResetHandlers[ii]) {
15539 +                               dprintk((MYIOC_s_INFO_FMT "Calling IOC post_reset handler #%d\n",
15540 +                                               ioc->name, ii));
15541                                 rc += (*(MptResetHandlers[ii]))(ioc, MPT_IOC_POST_RESET);
15542 +                               handlers++;
15543 +                       }
15544  
15545 +                       if (alt_ioc_ready && MptResetHandlers[ii]) {
15546 +                               drsprintk((MYIOC_s_INFO_FMT "Calling alt-%s post_reset handler #%d\n",
15547 +                                               ioc->name, ioc->alt_ioc->name, ii));
15548 +                               rc += (*(MptResetHandlers[ii]))(ioc->alt_ioc, MPT_IOC_POST_RESET);
15549 +                               handlers++;
15550                         }
15551                 }
15552 +               /* FIXME?  Examine results here? */
15553         }
15554  
15555 -if (ioc->bus_type == FC) {
15556 -               ioc->FcLinkSpeedCheckNeeded = 1;
15557 -       }
15558 -
15559 -       if (ioc->bus_type == SPI) {
15560 -               drsprintk((MYIOC_s_WARN_FMT "%s: calling writeSDP1: ALL_IDS USE_NVRAM\n",
15561 -                       ioc->name, __FUNCTION__));
15562 -               dnegoprintk((MYIOC_s_WARN_FMT "%s: calling writeSDP1: ALL_IDS USE_NVRAM\n",
15563 -                       ioc->name, __FUNCTION__));
15564 -               mpt_writeSDP1(ioc, 0, 0, (MPT_SCSICFG_ALL_IDS | MPT_SCSICFG_USE_NVRAM));
15565 -       }
15566 -
15567 -       spin_lock_irqsave(&ioc->diagLock, flags);
15568 -       ioc->IOCResetInProgress = 0;
15569 -       spin_unlock_irqrestore(&ioc->diagLock, flags);
15570 -
15571         return ret;
15572  }
15573  
15574 @@ -2224,11 +2108,9 @@ mpt_detect_bound_ports(MPT_ADAPTER *ioc,
15575  static void
15576  mpt_adapter_disable(MPT_ADAPTER *ioc)
15577  {
15578 -       struct _MPT_DEVICE      *pMptTarget;
15579 -       VirtDevice              *pTarget;
15580 +       sas_device_info_t *sasDevice, * pNext;
15581         int sz;
15582         int ret, ii;
15583 -       int bus, id;
15584         void *                  request_data;
15585         dma_addr_t              request_data_dma;
15586         u32                     request_data_sz;
15587 @@ -2253,7 +2135,7 @@ mpt_adapter_disable(MPT_ADAPTER *ioc)
15588                 if ( request_data ) {
15589                         request_data_sz = ioc->DiagBuffer_sz[ii];
15590                         request_data_dma = ioc->DiagBuffer_dma[ii];
15591 -                       dexitprintk((KERN_INFO MYNAM ": %s: free DiagBuffer[%d] @ %p, sz=%d bytes\n",
15592 +                       dexitprintk((KERN_INFO MYNAM ": %s free DiagBuffer[%d] @ %p, sz=%d bytes\n",
15593                                 ioc->name, ii, request_data, request_data_sz));
15594                         pci_free_consistent(ioc->pcidev, request_data_sz,
15595                                 request_data,
15596 @@ -2264,7 +2146,7 @@ mpt_adapter_disable(MPT_ADAPTER *ioc)
15597         }
15598         if (ioc->alloc != NULL) {
15599                 sz = ioc->alloc_sz;
15600 -               dexitprintk((KERN_INFO MYNAM ": %s: free alloc @ %p, sz=%d bytes\n",
15601 +               dexitprintk((KERN_INFO MYNAM ": %s free alloc @ %p, sz=%d bytes\n",
15602                         ioc->name, ioc->alloc, ioc->alloc_sz));
15603                 pci_free_consistent(ioc->pcidev, sz,
15604                                 ioc->alloc, ioc->alloc_dma);
15605 @@ -2276,7 +2158,7 @@ mpt_adapter_disable(MPT_ADAPTER *ioc)
15606  
15607         if (ioc->sense_buf_pool != NULL) {
15608                 sz = (ioc->req_depth * MPT_SENSE_BUFFER_ALLOC);
15609 -               dexitprintk((KERN_INFO MYNAM ": %s: free sense_buf_pool @ %p, sz=%d bytes\n",
15610 +               dexitprintk((KERN_INFO MYNAM ": %s free sense_buf_pool @ %p, sz=%d bytes\n",
15611                         ioc->name, ioc->sense_buf_pool, sz));
15612                 pci_free_consistent(ioc->pcidev, sz,
15613                                 ioc->sense_buf_pool, ioc->sense_buf_pool_dma);
15614 @@ -2286,7 +2168,7 @@ mpt_adapter_disable(MPT_ADAPTER *ioc)
15615  
15616         if (ioc->events != NULL){
15617                 sz = MPTCTL_EVENT_LOG_SIZE * sizeof(MPT_IOCTL_EVENTS);
15618 -               dexitprintk((KERN_INFO MYNAM ": %s: free events @ %p, sz=%d bytes\n",
15619 +               dexitprintk((KERN_INFO MYNAM ": %s free events @ %p, sz=%d bytes\n",
15620                         ioc->name, ioc->events, sz));
15621                 kfree(ioc->events);
15622                 ioc->events = NULL;
15623 @@ -2295,7 +2177,7 @@ mpt_adapter_disable(MPT_ADAPTER *ioc)
15624  
15625         if (ioc->cached_fw != NULL) {
15626                 sz = ioc->facts.FWImageSize;
15627 -               dexitprintk((KERN_INFO MYNAM ": %s: free cached_fw @ %p, sz=%d bytes\n",
15628 +               dexitprintk((KERN_INFO MYNAM ": %s free cached_fw @ %p, sz=%d bytes\n",
15629                         ioc->name, ioc->cached_fw, sz));
15630                 pci_free_consistent(ioc->pcidev, sz,
15631                         ioc->cached_fw, ioc->cached_fw_dma);
15632 @@ -2304,29 +2186,22 @@ mpt_adapter_disable(MPT_ADAPTER *ioc)
15633         }
15634  
15635         if (ioc->spi_data.nvram != NULL) {
15636 -               dexitprintk((KERN_INFO MYNAM ": %s: free spi_data.nvram @ %p\n",
15637 +               dexitprintk((KERN_INFO MYNAM ": %s free spi_data.nvram @ %p\n",
15638                         ioc->name, ioc->spi_data.nvram));
15639                 kfree(ioc->spi_data.nvram);
15640                 ioc->spi_data.nvram = NULL;
15641         }
15642  
15643         if (ioc->raid_data.pIocPg3 != NULL) {
15644 -               dexitprintk((KERN_INFO MYNAM ": %s: free spi_data.pIocPg3 @ %p\n",
15645 +               dexitprintk((KERN_INFO MYNAM ": %s free spi_data.pIocPg3 @ %p\n",
15646                         ioc->name, ioc->raid_data.pIocPg3));
15647                 kfree(ioc->raid_data.pIocPg3);
15648                 ioc->raid_data.pIocPg3 = NULL;
15649         }
15650  
15651 -       if (ioc->raid_data.pIocPg6 != NULL) {
15652 -               dexitprintk((KERN_INFO MYNAM ": %s: free raid_data.pIocPg6 @ %p\n",
15653 -                       ioc->name, ioc->raid_data.pIocPg6));
15654 -               kfree(ioc->raid_data.pIocPg6);
15655 -               ioc->raid_data.pIocPg6 = NULL;
15656 -       }
15657 -
15658         if (ioc->spi_data.pIocPg4 != NULL) {
15659                 sz = ioc->spi_data.IocPg4Sz;
15660 -               dexitprintk((KERN_INFO MYNAM ": %s: free spi_data.pIocPg4 @ %p size=%d\n",
15661 +               dexitprintk((KERN_INFO MYNAM ": %s free spi_data.pIocPg4 @ %p size=%d\n",
15662                         ioc->name, ioc->spi_data.pIocPg4, sz));
15663                 pci_free_consistent(ioc->pcidev, sz,
15664                         ioc->spi_data.pIocPg4,
15665 @@ -2336,41 +2211,38 @@ mpt_adapter_disable(MPT_ADAPTER *ioc)
15666         }
15667  
15668         if (ioc->ReqToChain != NULL) {
15669 -               dexitprintk((KERN_INFO MYNAM ": %s: free ReqToChain @ %p\n",
15670 +               dexitprintk((KERN_INFO MYNAM ": %s free ReqToChain @ %p\n",
15671                         ioc->name, ioc->ReqToChain));
15672                 kfree(ioc->ReqToChain);
15673                 ioc->ReqToChain = NULL;
15674         }
15675  
15676         if (ioc->RequestNB != NULL) {
15677 -               dexitprintk((KERN_INFO MYNAM ": %s: free RequestNB @ %p\n",
15678 +               dexitprintk((KERN_INFO MYNAM ": %s free RequestNB @ %p\n",
15679                         ioc->name, ioc->RequestNB));
15680                 kfree(ioc->RequestNB);
15681                 ioc->RequestNB = NULL;
15682         }
15683  
15684         if (ioc->ChainToChain != NULL) {
15685 -               dexitprintk((KERN_INFO MYNAM ": %s: free ChainToChain @ %p\n",
15686 +               dexitprintk((KERN_INFO MYNAM ": %s free ChainToChain @ %p\n",
15687                         ioc->name, ioc->ChainToChain));
15688                 kfree(ioc->ChainToChain);
15689                 ioc->ChainToChain = NULL;
15690         }
15691  
15692 -       mpt_inactive_raid_list_free(ioc);
15693 +       list_for_each_entry_safe(sasDevice, pNext, &ioc->sasDeviceList, list) {
15694 +               list_del(&sasDevice->list);
15695 +               dexitprintk((KERN_INFO MYNAM ": %s free sasDevice @ %p\n",
15696 +                       ioc->name, sasDevice));
15697 +               kfree(sasDevice);
15698 +       }
15699  
15700 -       for (bus = 0; bus < ioc->NumberOfBuses; bus++) {
15701 -               if ((pMptTarget = ioc->Target_List[bus])) {
15702 -                       for (id = 0; id < ioc->DevicesPerBus; id++) {
15703 -                               if ((pTarget = pMptTarget->Target[id])) {
15704 -                                       dexitprintk((KERN_INFO MYNAM ": %s: free bus=%d id=%d pTarget=%p\n",
15705 -                                               ioc->name, bus, id, pTarget));
15706 -                                       kfree (pTarget);
15707 -                               }
15708 -                       }
15709 -                       dexitprintk((KERN_INFO MYNAM ": %s: free bus=%d pMptTarget=%p\n",
15710 -                               ioc->name, bus, pMptTarget));
15711 -                       kfree (pMptTarget);
15712 -               }
15713 +       if (ioc->sasPhyInfo != NULL) {
15714 +               dexitprintk((KERN_INFO MYNAM ": %s free sasPhyInfo @ %p\n",
15715 +                       ioc->name, ioc->sasPhyInfo));
15716 +               kfree(ioc->sasPhyInfo);
15717 +               ioc->sasPhyInfo = NULL;
15718         }
15719  
15720  /* emoore@lsil.com : Host Page Buffer Suport, start */
15721 @@ -2381,7 +2253,7 @@ mpt_adapter_disable(MPT_ADAPTER *ioc)
15722                            ": %s: host page buffers free failed (%d)!\n",
15723                             __FUNCTION__, ret);
15724                 }
15725 -               dexitprintk((KERN_INFO MYNAM ": %s: HostPageBuffer free  @ %p, sz=%d bytes\n",
15726 +               dexitprintk((KERN_INFO MYNAM ": %s HostPageBuffer free  @ %p, sz=%d bytes\n",
15727                         ioc->name, ioc->HostPageBuffer, ioc->HostPageBuffer_sz));
15728                 pci_free_consistent(ioc->pcidev, ioc->HostPageBuffer_sz,
15729                                 ioc->HostPageBuffer,
15730 @@ -2441,7 +2313,7 @@ mpt_adapter_dispose(MPT_ADAPTER *ioc)
15731         dexitprintk((KERN_INFO MYNAM ": %s: free'd %d of %d bytes\n",
15732                 ioc->name, sz_first-sz_last+(int)sizeof(MPT_ADAPTER), sz_first));
15733         dexitprintk((KERN_INFO MYNAM ": %s: sz_first=%d sz_last=%d sizeof(MPT_ADAPTER)=%d\n",
15734 -               ioc->name, sz_first, sz_last, (int)sizeof(MPT_ADAPTER)));
15735 +               ioc->name, sz_first, sz_last, sizeof(MPT_ADAPTER)));
15736  
15737         if (ioc->alt_ioc)
15738                 ioc->alt_ioc->alt_ioc = NULL;
15739 @@ -2521,17 +2393,12 @@ MakeIocReady(MPT_ADAPTER *ioc, int force
15740  
15741         /* Get current [raw] IOC state  */
15742         ioc_state = mpt_GetIocState(ioc, 0);
15743 -       drsprintk((KERN_INFO MYNAM ": %s : MakeIocReady [raw] state=%08x\n", ioc->name, ioc_state));
15744 +       dhsprintk((KERN_INFO MYNAM "::MakeIocReady, %s [raw] state=%08x\n", ioc->name, ioc_state));
15745  
15746         for ( ii = 0; ii < MPI_DIAG_BUF_TYPE_COUNT; ii++) {
15747                 ioc->DiagBuffer[ii] = NULL;
15748                 ioc->DiagBuffer_Status[ii] = 0;
15749         }
15750 -if (ioc->bus_type == FC) {
15751 -      ioc->FcLinkSpeedCheckNeeded = 0;
15752 -      ioc->FcLinkSpeedReqActive = NULL;
15753 -}
15754 -
15755  
15756         /*
15757          *      Check to see if IOC got left/stuck in doorbell handshake
15758 @@ -2544,12 +2411,9 @@ if (ioc->bus_type == FC) {
15759         }
15760  
15761         /* Is it already READY? */
15762 -       if (!statefault && (ioc_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_READY)  {
15763 -drsprintk((KERN_INFO MYNAM ": %s : MakeIocReady ioc_state=%08x = READY\n", ioc->name, ioc_state));
15764 -             /* Dont return for SAS IOCs */
15765 -             if (ioc->bus_type != SAS)
15766 -               return 0;
15767 -              }
15768 +       if (!statefault && (ioc_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_READY) 
15769 +               return 0;
15770 +
15771         /*
15772          *      Check to see if IOC is in FAULT state.
15773          */
15774 @@ -2581,7 +2445,7 @@ drsprintk((KERN_INFO MYNAM ": %s : MakeI
15775                         return -4;
15776                 else {
15777                         if ((statefault == 0 ) && (force == 0)) {
15778 -if ((r = mpt_SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, sleepFlag)) == 0)
15779 +                               if ((r = SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, sleepFlag)) == 0)
15780                                         return 0;
15781                         }
15782                         statefault = 3;
15783 @@ -2604,7 +2468,7 @@ if ((r = mpt_SendIocReset(ioc, MPI_FUNCT
15784                          *  BIOS or previous driver load left IOC in OP state.
15785                          *  Reset messaging FIFOs.
15786                          */
15787 -if ((r = mpt_SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, sleepFlag)) != 0) {
15788 +                       if ((r = SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, sleepFlag)) != 0) {
15789                                 printk(MYIOC_s_ERR_FMT "IOC msg unit reset failed!\n", ioc->name);
15790                                 return -2;
15791                         }
15792 @@ -2613,7 +2477,7 @@ if ((r = mpt_SendIocReset(ioc, MPI_FUNCT
15793                          *  Something is wrong.  Try to get IOC back
15794                          *  to a known state.
15795                          */
15796 -if ((r = mpt_SendIocReset(ioc, MPI_FUNCTION_IO_UNIT_RESET, sleepFlag)) != 0) {
15797 +                       if ((r = SendIocReset(ioc, MPI_FUNCTION_IO_UNIT_RESET, sleepFlag)) != 0) {
15798                                 printk(MYIOC_s_ERR_FMT "IO unit reset failed!\n", ioc->name);
15799                                 return -3;
15800                         }
15801 @@ -2629,7 +2493,7 @@ if ((r = mpt_SendIocReset(ioc, MPI_FUNCT
15802                 if (sleepFlag == CAN_SLEEP)
15803                         msleep_interruptible(1);
15804                 else
15805 -                       MPT_MDELAY(1);  /* 1 msec delay */
15806 +                       MPT_MDELAY(1);  /* 1 msec delay */
15807  
15808         }
15809  
15810 @@ -2766,9 +2630,6 @@ GetIocFacts(MPT_ADAPTER *ioc, int sleepF
15811                         facts->FWVersion.Word = le32_to_cpu(facts->FWVersion.Word);
15812  
15813                 facts->ProductID = le16_to_cpu(facts->ProductID);
15814 -               if ((ioc->facts.ProductID & MPI_FW_HEADER_PID_PROD_MASK)
15815 -                   > MPI_FW_HEADER_PID_PROD_TARGET_SCSI)
15816 -                       ioc->ir_firmware = 1;
15817                 facts->CurrentHostMfaHighAddr =
15818                                 le32_to_cpu(facts->CurrentHostMfaHighAddr);
15819                 facts->GlobalCredits = le16_to_cpu(facts->GlobalCredits);
15820 @@ -2814,9 +2675,7 @@ GetIocFacts(MPT_ADAPTER *ioc, int sleepF
15821                 dinitprintk((MYIOC_s_INFO_FMT "NB_for_64_byte_frame=%x NBShiftFactor=%x BlockSize=%x\n",
15822                                         ioc->name, vv, shiftFactor, r));
15823  
15824 -/* Allow dead IOCs to get detected after FWDLB*/
15825 - if (reason == MPT_HOSTEVENT_IOC_BRINGUP ||mpt_enable_deadioc_detect) {
15826 -
15827 +               if (reason == MPT_HOSTEVENT_IOC_BRINGUP) {
15828                         /*
15829                          * Set values for this IOC's request & reply frame sizes,
15830                          * and request & reply queue depths...
15831 @@ -2870,7 +2729,6 @@ GetPortFacts(MPT_ADAPTER *ioc, int portn
15832         int                      ii;
15833         int                      req_sz;
15834         int                      reply_sz;
15835 -       int                      max_id;
15836  
15837         /* IOC *must* NOT be in RESET state! */
15838         if (ioc->last_state == MPI_IOC_STATE_RESET) {
15839 @@ -2913,31 +2771,6 @@ GetPortFacts(MPT_ADAPTER *ioc, int portn
15840         pfacts->IOCLogInfo = le32_to_cpu(pfacts->IOCLogInfo);
15841         pfacts->MaxDevices = le16_to_cpu(pfacts->MaxDevices);
15842         pfacts->PortSCSIID = le16_to_cpu(pfacts->PortSCSIID);
15843 -
15844 -       switch (ioc->bus_type) {
15845 -       case SAS:
15846 -               max_id = pfacts->PortSCSIID;
15847 -               break;
15848 -       case FC:
15849 -               max_id = pfacts->MaxDevices;
15850 -               break;
15851 -       case SPI:
15852 -       default:
15853 -               max_id = MPT_MAX_SCSI_DEVICES;
15854 -               break;
15855 -       }
15856 -
15857 -       ioc->DevicesPerBus = (max_id > 255) ? 256 : max_id;
15858 -       ioc->NumberOfBuses = (ioc->DevicesPerBus < 256) ? 1 : max_id/256;
15859 -       if ( ioc->NumberOfBuses > MPT_MAX_BUSES ) {
15860 -               dinitprintk((MYIOC_s_WARN_FMT "NumberOfBuses=%d > MPT_MAX_BUSES=%d\n",
15861 -                  ioc->name, ioc->NumberOfBuses, MPT_MAX_BUSES));
15862 -               ioc->NumberOfBuses = MPT_MAX_BUSES;
15863 -       }
15864 -
15865 -       dinitprintk((MYIOC_s_WARN_FMT "Buses=%d MaxDevices=%d DevicesPerBus=%d\n",
15866 -                  ioc->name, ioc->NumberOfBuses, max_id, ioc->DevicesPerBus));
15867 -
15868         pfacts->ProtocolFlags = le16_to_cpu(pfacts->ProtocolFlags);
15869         pfacts->MaxPostedCmdBuffers = le16_to_cpu(pfacts->MaxPostedCmdBuffers);
15870         pfacts->MaxPersistentIDs = le16_to_cpu(pfacts->MaxPersistentIDs);
15871 @@ -2983,11 +2816,15 @@ SendIocInit(MPT_ADAPTER *ioc, int sleepF
15872         dinitprintk((MYIOC_s_INFO_FMT "upload_fw %d facts.Flags=%x\n",
15873                    ioc->name, ioc->upload_fw, ioc->facts.Flags));
15874  
15875 -       ioc_init.MaxDevices = ioc->DevicesPerBus;
15876 -       ioc_init.MaxBuses = ioc->NumberOfBuses;
15877 -
15878 -       dinitprintk((MYIOC_s_INFO_FMT "ioc_init.MaxDevices=%d MaxBuses=%d\n",
15879 -                  ioc->name, ioc_init.MaxDevices, ioc_init.MaxBuses));
15880 +       if(ioc->bus_type == SAS)
15881 +               ioc_init.MaxDevices = ioc->facts.MaxDevices;
15882 +       else if(ioc->bus_type == FC)
15883 +               ioc_init.MaxDevices = MPT_MAX_FC_DEVICES;
15884 +       else
15885 +               ioc_init.MaxDevices = MPT_MAX_SCSI_DEVICES;
15886 +       ioc_init.MaxBuses = MPT_MAX_BUS;
15887 +       dinitprintk((MYIOC_s_INFO_FMT "ioc_init.MaxDevice=%d\n",
15888 +                  ioc->name, ioc_init.MaxDevices));
15889         dinitprintk((MYIOC_s_INFO_FMT "facts.MsgVersion=%x\n",
15890                    ioc->name, ioc->facts.MsgVersion));
15891  /* emoore@lsil.com : Host Page Buffer Suport, start */
15892 @@ -3110,7 +2947,9 @@ SendPortEnable(MPT_ADAPTER *ioc, int por
15893  
15894         /* RAID FW may take a long time to enable
15895          */
15896 -       if (ioc->ir_firmware || ioc->bus_type == SAS) {
15897 +       if (((ioc->facts.ProductID & MPI_FW_HEADER_PID_PROD_MASK)
15898 +           > MPI_FW_HEADER_PID_PROD_TARGET_SCSI) ||
15899 +           (ioc->bus_type == SAS)) {
15900                 rc = mpt_handshake_req_reply_wait(ioc, req_sz,
15901                 (u32*)&port_enable, reply_sz, (u16*)&reply_buf,
15902                 300 /*seconds*/, sleepFlag);
15903 @@ -3151,7 +2990,7 @@ mpt_free_fw_memory(MPT_ADAPTER *ioc)
15904         int sz;
15905  
15906         sz = ioc->facts.FWImageSize;
15907 -       dinitprintk((KERN_INFO MYNAM ": free_fw_memory: FW Image  @ %p[%p], sz=%d[%x] bytes\n",
15908 +       dinitprintk((KERN_INFO MYNAM "free_fw_memory: FW Image  @ %p[%p], sz=%d[%x] bytes\n",
15909                  ioc->cached_fw, (void *)(ulong)ioc->cached_fw_dma, sz, sz));
15910         pci_free_consistent(ioc->pcidev, sz,
15911                         ioc->cached_fw, ioc->cached_fw_dma);
15912 @@ -3285,43 +3124,14 @@ mpt_downloadboot(MPT_ADAPTER *ioc, MpiFw
15913         u32                      diag0val;
15914         int                      count;
15915         u32                     *ptrFw;
15916 -       u32                      diagRwData,doorbell;
15917 +       u32                      diagRwData;
15918         u32                      nextImage;
15919         u32                      load_addr;
15920 +       u32                      ioc_state=0;
15921  
15922 -ddlprintk((MYIOC_s_WARN_FMT "downloadboot: pFwHeader=%p\n",ioc->name, pFwHeader));
15923 -       nextImage = pFwHeader->NextImageHeaderOffset;
15924 -       if (ioc->bus_type == SAS) {
15925 -               while (nextImage) {
15926 -                       if ( (pExtImage = (MpiExtImageHeader_t *) ((char *)pFwHeader + nextImage)) ) {
15927 -                               ddlprintk((MYIOC_s_WARN_FMT "downloadboot: SAS nextImage=%x pExtImage=%p ImageType=%x\n",
15928 -                                       ioc->name, nextImage, pExtImage,
15929 -                                       pExtImage->ImageType));
15930 -                       } else {
15931 -                               ddlprintk((MYIOC_s_WARN_FMT "downloadboot: SAS nextImage=%x pExtImage=%p is NULL!\n",
15932 -                                       ioc->name, nextImage, pExtImage));
15933 -                               return -EFAULT;
15934 -                       }
15935 -
15936 -                       if ( pExtImage->ImageType == MPI_EXT_IMAGE_TYPE_BOOTLOADER ) {
15937 -                               fwSize = (pExtImage->ImageSize + 3)/4;
15938 -                               ptrFw = (u32 *) pExtImage;
15939 -                               load_addr = pExtImage->LoadStartAddress;
15940 -                               goto imageFound;
15941 -                       }
15942 -                       nextImage = pExtImage->NextImageHeaderOffset;
15943 -               }
15944 -               ddlprintk((MYIOC_s_WARN_FMT "downloadboot: SAS BOOTLOADER not found\n",
15945 -                       ioc->name));
15946 -               /* Allow this image to be downloaded */
15947 -       }
15948 -       fwSize = (pFwHeader->ImageSize + 3)/4;
15949 -       ptrFw = (u32 *) pFwHeader;
15950 -       load_addr = pFwHeader->LoadStartAddress;
15951 +       ddlprintk((MYIOC_s_INFO_FMT "downloadboot: fw size 0x%x (%d), FW Ptr %p\n",
15952 +                               ioc->name, pFwHeader->ImageSize, pFwHeader->ImageSize, pFwHeader));
15953  
15954 -imageFound:
15955 -       ddlprintk((MYIOC_s_WARN_FMT "downloadboot: fw size 0x%x (%d), FW Ptr %p load_addr=%x\n",
15956 -               ioc->name, fwSize, fwSize, ptrFw, load_addr));
15957  
15958         CHIPREG_WRITE32(&ioc->chip->WriteSequence, 0xFF);
15959         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_1ST_KEY_VALUE);
15960 @@ -3345,7 +3155,7 @@ imageFound:
15961         for (count = 0; count < 30; count ++) {
15962                 diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
15963                 if (!(diag0val & MPI_DIAG_RESET_ADAPTER)) {
15964 -                      ddlprintk((MYIOC_s_WARN_FMT "RESET_ADAPTER cleared, count=%d\n",
15965 +                       ddlprintk((MYIOC_s_INFO_FMT "RESET_ADAPTER cleared, count=%d\n",
15966                                 ioc->name, count));
15967                         break;
15968                 }
15969 @@ -3357,7 +3167,7 @@ imageFound:
15970         }
15971  
15972         if ( count == 30 ) {
15973 -               ddlprintk((MYIOC_s_WARN_FMT "downloadboot failed! Unable to get MPI_DIAG_DRWE mode, diag0val=%x\n",
15974 +               ddlprintk((MYIOC_s_INFO_FMT "downloadboot failed! Unable to get MPI_DIAG_DRWE mode, diag0val=%x\n",
15975                 ioc->name, diag0val));
15976                 return -3;
15977         }
15978 @@ -3370,9 +3180,10 @@ imageFound:
15979         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_5TH_KEY_VALUE);
15980  
15981         /* Set the DiagRwEn and Disable ARM bits */
15982 +       CHIPREG_WRITE32(&ioc->chip->Diagnostic, (MPI_DIAG_RW_ENABLE | MPI_DIAG_DISABLE_ARM));
15983  
15984 -        diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
15985 -CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val | (MPI_DIAG_RW_ENABLE | MPI_DIAG_DISABLE_ARM));
15986 +       fwSize = (pFwHeader->ImageSize + 3)/4;
15987 +       ptrFw = (u32 *) pFwHeader;
15988  
15989         /* Write the LoadStartAddress to the DiagRw Address Register
15990          * using Programmed IO
15991 @@ -3380,28 +3191,26 @@ CHIPREG_WRITE32(&ioc->chip->Diagnostic, 
15992         if(ioc->errata_flag_1064) {
15993                 pci_enable_io_access(ioc->pcidev);
15994         }
15995 -CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwAddress, load_addr);
15996 +       CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwAddress, pFwHeader->LoadStartAddress);
15997 +       ddlprintk((MYIOC_s_INFO_FMT "LoadStart addr written 0x%x \n",
15998 +               ioc->name, pFwHeader->LoadStartAddress));
15999  
16000 -ddlprintk((MYIOC_s_WARN_FMT "LoadStart addr written 0x%x \n",ioc->name, load_addr));
16001 -ddlprintk((MYIOC_s_WARN_FMT "Write FW Image: 0x%x (%d) bytes @ %p\n",
16002 -                                ioc->name, fwSize*4, fwSize*4, ptrFw));
16003 +       ddlprintk((MYIOC_s_INFO_FMT "Write FW Image: 0x%x (%d) bytes @ %p\n",
16004 +                               ioc->name, fwSize*4, fwSize*4, ptrFw));
16005         while (fwSize--) {
16006                 CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwData, *ptrFw++);
16007         }
16008  
16009 -       if (ioc->bus_type == SAS) {
16010 -               pFwHeader->IopResetVectorValue = load_addr + 0x18;
16011 -       } else {
16012 -
16013 -               while (nextImage) {
16014 -                       pExtImage = (MpiExtImageHeader_t *) ((char *)pFwHeader + nextImage);
16015 +       nextImage = pFwHeader->NextImageHeaderOffset;
16016 +       while (nextImage) {
16017 +               pExtImage = (MpiExtImageHeader_t *) ((char *)pFwHeader + nextImage);
16018  
16019                 load_addr = pExtImage->LoadStartAddress;
16020  
16021                 fwSize = (pExtImage->ImageSize + 3) >> 2;
16022                 ptrFw = (u32 *)pExtImage;
16023  
16024 -               ddlprintk((MYIOC_s_WARN_FMT "Write Ext Image: 0x%x (%d) bytes @ %p load_addr=%x\n",
16025 +               ddlprintk((MYIOC_s_INFO_FMT "Write Ext Image: 0x%x (%d) bytes @ %p load_addr=%x\n",
16026                                                 ioc->name, fwSize*4, fwSize*4, ptrFw, load_addr));
16027                 CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwAddress, load_addr);
16028  
16029 @@ -3411,18 +3220,20 @@ ddlprintk((MYIOC_s_WARN_FMT "Write FW Im
16030                 nextImage = pExtImage->NextImageHeaderOffset;
16031         }
16032  
16033 - }
16034         /* Write the IopResetVectorRegAddr */
16035 -       ddlprintk((MYIOC_s_WARN_FMT "Write IopResetVector Addr=%x! \n", ioc->name,      pFwHeader->IopResetRegAddr));
16036 +       ddlprintk((MYIOC_s_INFO_FMT "Write IopResetVector Addr=%x! \n", ioc->name,      pFwHeader->IopResetRegAddr));
16037         CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwAddress, pFwHeader->IopResetRegAddr);
16038  
16039         /* Write the IopResetVectorValue */
16040 -       ddlprintk((MYIOC_s_WARN_FMT "Write IopResetVector Value=%x! \n", ioc->name, pFwHeader->IopResetVectorValue));
16041 +       ddlprintk((MYIOC_s_INFO_FMT "Write IopResetVector Value=%x! \n", ioc->name, pFwHeader->IopResetVectorValue));
16042         CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwData, pFwHeader->IopResetVectorValue);
16043  
16044 +       /* Clear the internal flash bad bit - autoincrementing register,
16045 +        * so must do two writes.
16046 +        */
16047         if (ioc->bus_type == SPI) {
16048                 /*
16049 -                * 1030 H/W errata, workaround to access
16050 +                * 1030 and 1035 H/W errata, workaround to access
16051                  * the ClearFlashBadSignatureBit
16052                  */
16053                 CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwAddress, 0x3F000000);
16054 @@ -3431,6 +3242,16 @@ ddlprintk((MYIOC_s_WARN_FMT "Write FW Im
16055                 CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwAddress, 0x3F000000);
16056                 CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwData, diagRwData);
16057  
16058 +       } else /* if((ioc->bus_type == SAS) || (ioc->bus_type == FC)) */ {
16059 +               diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
16060 +               CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val |
16061 +                   MPI_DIAG_CLEAR_FLASH_BAD_SIG);
16062 +
16063 +               /* wait 1 msec */
16064 +               if (sleepFlag == CAN_SLEEP)
16065 +                       msleep_interruptible(1);
16066 +               else
16067 +                       MPT_MDELAY(1);
16068         }
16069  
16070         if(ioc->errata_flag_1064) {
16071 @@ -3438,77 +3259,48 @@ ddlprintk((MYIOC_s_WARN_FMT "Write FW Im
16072         }
16073  
16074         diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
16075 -       ddlprintk((MYIOC_s_WARN_FMT "downloadboot diag0val=%x, turning off PREVENT_IOC_BOOT, DISABLE_ARM, RW_ENABLE\n",
16076 +       ddlprintk((MYIOC_s_INFO_FMT "downloadboot diag0val=%x, turning off PREVENT_IOC_BOOT, DISABLE_ARM, RW_ENABLE\n",
16077                 ioc->name, diag0val));
16078 -
16079 -diag0val &= ~(MPI_DIAG_PREVENT_IOC_BOOT | MPI_DIAG_DISABLE_ARM);
16080 -ddlprintk((MYIOC_s_WARN_FMT "downloadboot: now diag0val=%x\n",
16081 +       diag0val &= ~(MPI_DIAG_PREVENT_IOC_BOOT | MPI_DIAG_DISABLE_ARM | MPI_DIAG_RW_ENABLE);
16082 +       ddlprintk((MYIOC_s_INFO_FMT "downloadboot now diag0val=%x\n",
16083                 ioc->name, diag0val));
16084         CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val);
16085  
16086 -if (ioc->bus_type == SAS ) {
16087 -/* wait 1 sec */
16088 -if (sleepFlag == CAN_SLEEP)
16089 -{
16090 -msleep_interruptible(1000);
16091 -
16092 -}
16093 -else
16094 -MPT_MDELAY(1000);
16095 -
16096 -
16097 -
16098 +       /* Write 0xFF to reset the sequencer */
16099 +       CHIPREG_WRITE32(&ioc->chip->WriteSequence, 0xFF);
16100  
16101 -diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
16102 -ddlprintk((MYIOC_s_WARN_FMT "downloadboot: diag0val=%x, turning off RW_ENABLE\n"
16103 -            ioc->name, diag0val));
16104 -diag0val &= ~(MPI_DIAG_RW_ENABLE);
16105 -ddlprintk((MYIOC_s_WARN_FMT "downloadboot: now diag0val=%x\n",
16106 -                   ioc->name, diag0val));
16107 -CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val);
16108 -diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
16109 -if (diag0val & MPI_DIAG_FLASH_BAD_SIG) {
16110 -diag0val |= MPI_DIAG_CLEAR_FLASH_BAD_SIG;
16111 -CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val);
16112 -diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
16113 +       if (ioc->bus_type == SAS) {
16114 +               ioc_state = mpt_GetIocState(ioc, 0);
16115 +               if ( (GetIocFacts(ioc, sleepFlag,
16116 +                               MPT_HOSTEVENT_IOC_BRINGUP)) != 0 ) {
16117 +                       ddlprintk((MYIOC_s_INFO_FMT "GetIocFacts failed: IocState=%x\n",
16118 +                                       ioc->name, ioc_state));
16119 +                       return -EFAULT;
16120                 }
16121 -diag0val &= ~(MPI_DIAG_DISABLE_ARM);
16122 -CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val);
16123 -diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
16124 -CHIPREG_WRITE32(&ioc->chip->DiagRwAddress, 0x3f000004);
16125         }
16126 -/* Write 0xFF to reset the sequencer */
16127 -CHIPREG_WRITE32(&ioc->chip->WriteSequence, 0xFF);
16128 -
16129 -        for (count = 0; count < 30; count ++) {
16130 -           doorbell = CHIPREG_READ32(&ioc->chip->Doorbell);
16131 -           doorbell &= MPI_IOC_STATE_MASK;
16132 -
16133 -                   if (doorbell == MPI_IOC_STATE_READY) {
16134  
16135 +       for (count=0; count<HZ*20; count++) {
16136 +               if ((ioc_state = mpt_GetIocState(ioc, 0)) & MPI_IOC_STATE_READY) {
16137 +                       ddlprintk((MYIOC_s_INFO_FMT "downloadboot successful! (count=%d) IocState=%x\n",
16138 +                                       ioc->name, count, ioc_state));
16139                         if (ioc->bus_type == SAS) {
16140                                 return 0;
16141                         }
16142 -
16143 -
16144 -       if ((SendIocInit(ioc, sleepFlag)) != 0) {
16145 -                               ddlprintk((MYIOC_s_WARN_FMT "downloadboot: SendIocInit failed\n",
16146 +                       if ((SendIocInit(ioc, sleepFlag)) != 0) {
16147 +                               ddlprintk((MYIOC_s_INFO_FMT "downloadboot: SendIocInit failed\n",
16148                                         ioc->name));
16149                                 return -EFAULT;
16150                         }
16151 -                       ddlprintk((MYIOC_s_WARN_FMT "downloadboot: SendIocInit successful\n",
16152 +                       ddlprintk((MYIOC_s_INFO_FMT "downloadboot: SendIocInit successful\n",
16153                                         ioc->name));
16154                         return 0;
16155                 }
16156 -       ddlprintk((MYIOC_s_WARN_FMT "downloadboot: looking for READY STATE:doorbell=%x count=%d\n",ioc->name, doorbell, count));
16157 -                     /* wait 1 sec */
16158 -
16159                 if (sleepFlag == CAN_SLEEP)
16160 -                       msleep_interruptible(1000);
16161 +                       msleep_interruptible(10);
16162                 else
16163 -                       MPT_MDELAY(1000);
16164 +                       MPT_MDELAY(10);
16165         }
16166 -       ddlprintk((MYIOC_s_WARN_FMT "downloadboot failed! IocState=%x\n",
16167 +       ddlprintk((MYIOC_s_INFO_FMT "downloadboot failed! IocState=%x\n",
16168                 ioc->name, ioc_state));
16169         return -EFAULT;
16170  }
16171 @@ -3552,7 +3344,8 @@ KickStart(MPT_ADAPTER *ioc, int force, i
16172                 /* Always issue a Msg Unit Reset first. This will clear some
16173                  * SCSI bus hang conditions.
16174                  */
16175 -            mpt_SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, sleepFlag);
16176 +               SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, sleepFlag);
16177 +
16178                 if (sleepFlag == CAN_SLEEP)
16179                         msleep_interruptible(1000);
16180                 else
16181 @@ -3624,26 +3417,6 @@ mpt_diag_reset(MPT_ADAPTER *ioc, int ign
16182                         msleep_interruptible(1);
16183                 else
16184                         MPT_MDELAY(1);
16185 -/*
16186 -                * Call each currently registered protocol IOC reset handler
16187 -                * with post-reset indication.
16188 -                * NOTE: If we're doing _IOC_BRINGUP, there can be no
16189 -                * MptResetHandlers[] registered yet.
16190 - */
16191 -                  {
16192 -                      int       ii;
16193 -                      int        r=0;
16194 -
16195 -                  for (ii=MPT_MAX_PROTOCOL_DRIVERS-1; ii; ii--) {
16196 -                              if (MptResetHandlers[ii]) {
16197 -  drsprintk((MYIOC_s_INFO_FMT "Calling IOC post_reset handler #%d\n",ioc->name, ii));
16198 -  r += (*(MptResetHandlers[ii]))(ioc, MPT_IOC_POST_RESET);
16199 -
16200 -   }
16201 -}
16202 -/* FIXME?  Examine results here? */
16203 -
16204 -}
16205  
16206                 for (count = 0; count < 60; count ++) {
16207                         doorbell = CHIPREG_READ32(&ioc->chip->Doorbell);
16208 @@ -3746,11 +3519,11 @@ mpt_diag_reset(MPT_ADAPTER *ioc, int ign
16209  
16210                         for (ii=MPT_MAX_PROTOCOL_DRIVERS-1; ii; ii--) {
16211                                 if (MptResetHandlers[ii]) {
16212 -                                       drsprintk((MYIOC_s_INFO_FMT "Calling IOC pre_reset handler #%d\n",
16213 +                                       dprintk((MYIOC_s_INFO_FMT "Calling IOC pre_reset handler #%d\n",
16214                                                         ioc->name, ii));
16215                                         r += (*(MptResetHandlers[ii]))(ioc, MPT_IOC_PRE_RESET);
16216                                         if (ioc->alt_ioc) {
16217 -                                               drsprintk((MYIOC_s_INFO_FMT "Calling alt-%s pre_reset handler #%d\n",
16218 +                                               dprintk((MYIOC_s_INFO_FMT "Calling alt-%s pre_reset handler #%d\n",
16219                                                                 ioc->name, ioc->alt_ioc->name, ii));
16220                                                 r += (*(MptResetHandlers[ii]))(ioc->alt_ioc, MPT_IOC_PRE_RESET);
16221                                         }
16222 @@ -3901,31 +3674,18 @@ mpt_diag_reset(MPT_ADAPTER *ioc, int ign
16223   *
16224   *     Returns 0 for success, non-zero for failure.
16225   */
16226 -int
16227 -mpt_SendIocReset(MPT_ADAPTER *ioc, u8 reset_type, int sleepFlag)
16228 +static int
16229 +SendIocReset(MPT_ADAPTER *ioc, u8 reset_type, int sleepFlag)
16230  {
16231 -        unsigned long flags;
16232         int r;
16233 -       u32 state, Doorbell;
16234 +       u32 state;
16235         int cntdn, count;
16236  
16237 -Doorbell = (reset_type<<MPI_DOORBELL_FUNCTION_SHIFT);
16238 -
16239 -drsprintk((MYIOC_s_WARN_FMT ": %s: reset_type=%02x Doorbell=%08x!\n",
16240 -ioc->name, __FUNCTION__, reset_type, Doorbell));
16241 -CHIPREG_WRITE32(&ioc->chip->Doorbell, Doorbell);
16242 -
16243 -if ((r = WaitForDoorbellAck(ioc, 15, sleepFlag)) < 0){
16244 -                drsprintk((MYIOC_s_WARN_FMT ": %s: WaitForDoorbellAck failed r=%d after IOC Rese
16245 -t type=%02x!\n",
16246 -                        ioc->name, __FUNCTION__, r, reset_type));
16247 - return r;
16248 -}
16249 -
16250 -spin_lock_irqsave(&ioc->diagLock, flags);
16251 -ioc->IOCResetInProgress = 1;
16252 -spin_unlock_irqrestore(&ioc->diagLock, flags);
16253 -
16254 +       drsprintk((KERN_INFO MYNAM ": %s: Sending IOC reset(0x%02x)!\n",
16255 +                       ioc->name, reset_type));
16256 +       CHIPREG_WRITE32(&ioc->chip->Doorbell, reset_type<<MPI_DOORBELL_FUNCTION_SHIFT);
16257 +       if ((r = WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0)
16258 +               return r;
16259  
16260         /* FW ACK'd request, wait for READY state
16261          */
16262 @@ -3950,13 +3710,13 @@ spin_unlock_irqrestore(&ioc->diagLock, f
16263                         MPT_MDELAY(1);  /* 1 msec delay */
16264         }
16265  
16266 +       /* TODO!
16267 +        *  Cleanup all event stuff for this IOC; re-issue EventNotification
16268 +        *  request if needed.
16269 +        */
16270         if (ioc->facts.Function)
16271                 ioc->facts.EventState = 0;
16272 -spin_lock_irqsave(&ioc->diagLock, flags);
16273 -ioc->IOCResetInProgress = 0;
16274 -spin_unlock_irqrestore(&ioc->diagLock, flags);
16275 -drsprintk((MYIOC_s_WARN_FMT ": %s: IOC reset completed successfully state=%08x count=%d\ n",
16276 -ioc->name, __FUNCTION__, state, count));
16277 +
16278         return 0;
16279  }
16280  
16281 @@ -4044,9 +3804,8 @@ PrimeIocFifos(MPT_ADAPTER *ioc)
16282         unsigned long flags;
16283         dma_addr_t alloc_dma;
16284         u8 *mem;
16285 -       int i, reply_sz, req_sz, sz, total_size, num_chain, total_num_chain;
16286 -        int scale, scale1, num_sge, numSGE, maxSGEs, SGE_size;
16287 -       int max_sg_tablesize;
16288 +       int i, reply_sz, sz, total_size, num_chain, total_num_chain;
16289 +       int scale, scale1, num_sge, numSGE, maxSGEs, SGE_size;
16290  
16291         /*  Prime reply FIFO...  */
16292  
16293 @@ -4073,13 +3832,12 @@ PrimeIocFifos(MPT_ADAPTER *ioc)
16294                         " numSGE=%d MaxChainDepth=%d maxSGEs=%d mpt_sg_tablesize=%d\n",
16295                         ioc->name, ioc->req_sz, SGE_size, scale, num_sge, numSGE, 
16296                         ioc->facts.MaxChainDepth, maxSGEs, mpt_sg_tablesize));
16297 -               max_sg_tablesize = mpt_sg_tablesize;
16298 -               if (max_sg_tablesize > maxSGEs) {
16299 -                       max_sg_tablesize = maxSGEs;
16300 -                       dinitprintk((KERN_INFO MYNAM ": %s max_sg_tablesize=%d now\n",
16301 -                               ioc->name, max_sg_tablesize));
16302 -               } else if (max_sg_tablesize < maxSGEs) {
16303 -                       numSGE = max_sg_tablesize - num_sge;
16304 +               if (mpt_sg_tablesize > maxSGEs) {
16305 +                       mpt_sg_tablesize = maxSGEs;
16306 +                       dinitprintk((KERN_INFO MYNAM ": %s mpt_sg_tablesize=%d now\n",
16307 +                               ioc->name, mpt_sg_tablesize));
16308 +               } else if (mpt_sg_tablesize < maxSGEs) {
16309 +                       numSGE = mpt_sg_tablesize - num_sge;
16310                         dinitprintk((KERN_INFO MYNAM ": %s numSGE=%d now\n",
16311                                 ioc->name, numSGE));
16312                 }
16313 @@ -4099,12 +3857,11 @@ PrimeIocFifos(MPT_ADAPTER *ioc)
16314  
16315                 numSGE = scale1 * (total_num_chain-1);
16316                 maxSGEs = num_sge + numSGE;
16317 -               if (max_sg_tablesize > maxSGEs) {
16318 -                       max_sg_tablesize = maxSGEs;
16319 -                       dinitprintk((KERN_INFO MYNAM ": %s max_sg_tablesize=%d now, maxSGEs=%d numSGE=%d\n",
16320 -                               ioc->name, max_sg_tablesize, maxSGEs, numSGE));
16321 +               if (mpt_sg_tablesize > maxSGEs) {
16322 +                       mpt_sg_tablesize = maxSGEs;
16323 +                       dinitprintk((KERN_INFO MYNAM ": %s mpt_sg_tablesize=%d now, maxSGEs=%d numSGE=%d\n",
16324 +                               ioc->name, mpt_sg_tablesize, maxSGEs, numSGE));
16325                 }
16326 -               ioc->sg_tablesize = max_sg_tablesize;
16327  
16328                 dinitprintk((KERN_INFO MYNAM ": %s req_depth=%d max num_chain=%d mpt_chain_alloc_percent=%d total_num_chain=%d\n",
16329                         ioc->name, ioc->req_depth, num_chain, mpt_chain_alloc_percent, total_num_chain));
16330 @@ -4116,17 +3873,14 @@ PrimeIocFifos(MPT_ADAPTER *ioc)
16331                 dinitprintk((KERN_INFO MYNAM ": %s Total ReplyBuffer sz=%d[%x] bytes\n",
16332                                 ioc->name, reply_sz, reply_sz));
16333  
16334 -                req_sz = ioc->req_sz;
16335 -                sz = (req_sz * ioc->req_depth);
16336 -
16337 -       dinitprintk((KERN_INFO MYNAM ": %s RequestBuffer sz=%d bytes, RequestDepth=%d\n",
16338 -                               ioc->name, req_sz, ioc->req_depth));
16339 -
16340 +               sz = (ioc->req_sz * ioc->req_depth);
16341 +               dinitprintk((KERN_INFO MYNAM ": %s RequestBuffer sz=%d bytes, RequestDepth=%d\n",
16342 +                               ioc->name, ioc->req_sz, ioc->req_depth));
16343                 dinitprintk((KERN_INFO MYNAM ": %s Total RequestBuffer sz=%d[%x] bytes\n",
16344                                 ioc->name, sz, sz));
16345                 total_size += sz;
16346  
16347 -               sz = total_num_chain *req_sz; /* chain buffer pool size */
16348 +               sz = total_num_chain * ioc->req_sz; /* chain buffer pool size */
16349                 dinitprintk((KERN_INFO MYNAM ": %s Total ChainBuffer sz=%d[%x] bytes total_num_chain=%d\n",
16350                                 ioc->name, sz, sz, total_num_chain));
16351  
16352 @@ -4182,14 +3936,14 @@ PrimeIocFifos(MPT_ADAPTER *ioc)
16353  #endif
16354  
16355                 for (i = 0; i < ioc->req_depth; i++) {
16356 -                       alloc_dma += req_sz;
16357 -                       mem += req_sz;
16358 +                       alloc_dma += ioc->req_sz;
16359 +                       mem += ioc->req_sz;
16360                 }
16361  
16362                 ioc->ChainBuffer = mem;
16363                 ioc->ChainBufferDMA = alloc_dma;
16364  
16365 -               dinitprintk((KERN_INFO MYNAM ": %s ChainBuffers @ %p(%p)\n",
16366 +               dinitprintk((KERN_INFO MYNAM " :%s ChainBuffers @ %p(%p)\n",
16367                         ioc->name, ioc->ChainBuffer, (void *)(ulong)ioc->ChainBufferDMA));
16368  
16369                 /* Initialize the free chain Q.
16370 @@ -4197,6 +3951,10 @@ PrimeIocFifos(MPT_ADAPTER *ioc)
16371  
16372                 INIT_LIST_HEAD(&ioc->FreeChainQ);
16373  
16374 +               /* initialize the SAS device list */
16375 +
16376 +               INIT_LIST_HEAD(&ioc->sasDeviceList);
16377 +
16378                 /* Post the chain buffers to the FreeChainQ.
16379                 */
16380                 mem = (u8 *)ioc->ChainBuffer;
16381 @@ -4205,7 +3963,7 @@ PrimeIocFifos(MPT_ADAPTER *ioc)
16382                         list_add_tail(&mf->u.frame.linkage.list, &ioc->FreeChainQ);
16383  //                     dinitprintk((MYIOC_s_INFO_FMT "Adding %p to FreeChainQ at %d\n",
16384   //                            ioc->name, mf, i));
16385 -                       mem += req_sz;
16386 +                       mem += ioc->req_sz;
16387                 }
16388  
16389                 /* Initialize Request frames linked list
16390 @@ -4220,7 +3978,7 @@ PrimeIocFifos(MPT_ADAPTER *ioc)
16391  
16392                         /*  Queue REQUESTs *internally*!  */
16393                         list_add_tail(&mf->u.frame.linkage.list, &ioc->FreeQ);
16394 -                       mem += req_sz;
16395 +                       mem += ioc->req_sz;
16396                 }
16397                 spin_unlock_irqrestore(&ioc->FreeQlock, flags);
16398  
16399 @@ -4293,7 +4051,8 @@ out_fail:
16400   *
16401   *     Returns 0 for success, non-zero for failure.
16402   */
16403 -int mpt_handshake_req_reply_wait(MPT_ADAPTER *ioc, int reqBytes, u32 *req,
16404 +static int
16405 +mpt_handshake_req_reply_wait(MPT_ADAPTER *ioc, int reqBytes, u32 *req,
16406                 int replyBytes, u16 *u16reply, int maxwait, int sleepFlag)
16407  {
16408         MPIDefaultReply_t *mptReply;
16409 @@ -4412,7 +4171,7 @@ WaitForDoorbellAck(MPT_ADAPTER *ioc, int
16410                         intstat = CHIPREG_READ32(&ioc->chip->IntStatus);
16411                         if (! (intstat & MPI_HIS_IOP_DOORBELL_STATUS))
16412                                 break;
16413 -                       msleep_interruptible(10);
16414 +                       msleep_interruptible(1);
16415                         count++;
16416                 }
16417         } else {
16418 @@ -4420,7 +4179,7 @@ WaitForDoorbellAck(MPT_ADAPTER *ioc, int
16419                         intstat = CHIPREG_READ32(&ioc->chip->IntStatus);
16420                         if (! (intstat & MPI_HIS_IOP_DOORBELL_STATUS))
16421                                 break;
16422 -                          udelay(1000);
16423 +                       MPT_MDELAY(1);
16424                         count++;
16425                 }
16426         }
16427 @@ -4461,7 +4220,7 @@ WaitForDoorbellInt(MPT_ADAPTER *ioc, int
16428                         intstat = CHIPREG_READ32(&ioc->chip->IntStatus);
16429                         if (intstat & MPI_HIS_DOORBELL_INTERRUPT)
16430                                 break;
16431 -                       msleep_interruptible(10);
16432 +                       msleep_interruptible(1);
16433                         count++;
16434                 }
16435         } else {
16436 @@ -4469,7 +4228,7 @@ WaitForDoorbellInt(MPT_ADAPTER *ioc, int
16437                         intstat = CHIPREG_READ32(&ioc->chip->IntStatus);
16438                         if (intstat & MPI_HIS_DOORBELL_INTERRUPT)
16439                                 break;
16440 -                          udelay(1000);
16441 +                       MPT_MDELAY(1);
16442                         count++;
16443                 }
16444         }
16445 @@ -4944,40 +4703,481 @@ GetManufPage0_exit:
16446         return rc;
16447  }
16448  
16449 +
16450  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
16451  /*
16452 - *     mptbase_sas_persist_operation - Perform operation on SAS Persitent Table
16453 + *     mpt_sas_get_info - Fetch Hw Max and Min Link Rates.  These values
16454 + *               get overwritten, so must be saved at init time.
16455   *     @ioc: Pointer to MPT_ADAPTER structure
16456 - *     @sas_address: 64bit SAS Address for operation.
16457 - *     @target_id: specified target for operation
16458 - *     @bus: specified bus for operation
16459 - *     @persist_opcode: see below
16460 - *
16461 - *     MPI_SAS_OP_CLEAR_NOT_PRESENT - Free all persist TargetID mappings for
16462 - *             devices not currently present.
16463 - *     MPI_SAS_OP_CLEAR_ALL_PERSISTENT - Clear al persist TargetID mappings
16464 - *
16465 - *     NOTE: Don't use not this function during interrupt time.
16466 + *     @numPorts: number of ports for this IOC
16467   *
16468 - *     Returns: 0 for success, non-zero error
16469 + *     Return: 0 for success
16470 + *     -ENOMEM if no memory available
16471 + *             -EPERM if not allowed due to ISR context
16472 + *             -EAGAIN if no msg frames currently available
16473 + *             -EFAULT for non-successful reply or no reply (timeout)
16474   */
16475 -
16476 -/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
16477  int
16478 -mptbase_sas_persist_operation(MPT_ADAPTER *ioc, u8 persist_opcode)
16479 +mpt_sas_get_info(MPT_ADAPTER *ioc)
16480  {
16481 -       SasIoUnitControlRequest_t       *sasIoUnitCntrReq;
16482 -       SasIoUnitControlReply_t         *sasIoUnitCntrReply;
16483 -       MPT_FRAME_HDR                   *mf = NULL;
16484 -       MPIHeader_t                     *mpi_hdr;
16485 +       ConfigExtendedPageHeader_t hdr;
16486 +       CONFIGPARMS             cfg;
16487 +       SasIOUnitPage0_t        *sasIoUnitPg0=NULL;
16488 +       dma_addr_t              sasIoUnitPg0_dma;
16489 +       SasPhyPage0_t           *sasPhyPg0=NULL;
16490 +       dma_addr_t              sasPhyPg0_dma;
16491 +       SasDevicePage0_t        *sasDevicePg0=NULL;
16492 +       dma_addr_t              sasDevicePg0_dma;
16493 +       sas_device_info_t       *sasDevice;
16494 +       u32                     devHandle;
16495 +       int                     sasIoUnitPg0_data_sz=0;
16496 +       int                     sasPhyPg0_data_sz=0;
16497 +       int                     sasDevicePg0_data_sz=0;
16498 +       int                     sz;
16499 +       int                     rc;
16500 +       int                     ii;
16501 +       int                     phyCounter;
16502 +       u8                      *mem;
16503 +       u64                     SASAddress64;
16504 +       char                    *ds = NULL;
16505  
16506 +       /* Issue a config request to get the number of phys
16507 +        */
16508 +       ioc->sasPhyInfo=NULL;
16509  
16510 -       /* insure garbage is not sent to fw */
16511 -       switch(persist_opcode) {
16512 +       hdr.PageVersion = MPI_SASIOUNITPAGE0_PAGEVERSION;
16513 +       hdr.ExtPageLength = 0;
16514 +       hdr.PageNumber = 0;
16515 +       hdr.Reserved1 = 0;
16516 +       hdr.Reserved2 = 0;
16517 +       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
16518 +       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_IO_UNIT;
16519  
16520 -       case MPI_SAS_OP_CLEAR_NOT_PRESENT:
16521 -       case MPI_SAS_OP_CLEAR_ALL_PERSISTENT:
16522 -               break;
16523 +       cfg.cfghdr.ehdr = &hdr;
16524 +       cfg.physAddr = -1;
16525 +       cfg.pageAddr = 0;
16526 +       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
16527 +       cfg.dir = 0;    /* read */
16528 +       cfg.timeout = 10;
16529 +
16530 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
16531 +               goto mpt_sas_get_info_exit;
16532 +       }
16533 +
16534 +       if (hdr.ExtPageLength == 0) {
16535 +               rc = -EFAULT;
16536 +               goto mpt_sas_get_info_exit;
16537 +       }
16538 +
16539 +       sasIoUnitPg0_data_sz = hdr.ExtPageLength * 4;
16540 +       sasIoUnitPg0 = (SasIOUnitPage0_t *) pci_alloc_consistent(ioc->pcidev,
16541 +           sasIoUnitPg0_data_sz, &sasIoUnitPg0_dma);
16542 +       if (!sasIoUnitPg0) {
16543 +               rc = -ENOMEM;
16544 +               goto mpt_sas_get_info_exit;
16545 +       }
16546 +
16547 +       memset((u8 *)sasIoUnitPg0, 0, sasIoUnitPg0_data_sz);
16548 +       cfg.physAddr = sasIoUnitPg0_dma;
16549 +       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
16550 +
16551 +       if ((rc = mpt_config(ioc, &cfg)) != 0) {
16552 +               goto mpt_sas_get_info_exit;
16553 +       }
16554 +
16555 +       /* save the data */
16556 +       ioc->numPhys = sasIoUnitPg0->NumPhys;
16557 +
16558 +       dsasprintk((MYIOC_s_INFO_FMT "Number of PHYS=%d\n",
16559 +           ioc->name, sasIoUnitPg0->NumPhys));
16560 +
16561 +       sz = ioc->numPhys * sizeof (sas_phy_info_t);
16562 +
16563 +       if ((mem = kmalloc(sz, GFP_ATOMIC)) == NULL) {
16564 +               rc = -ENOMEM;
16565 +               goto mpt_sas_get_info_exit;
16566 +       }
16567 +
16568 +       memset(mem, 0, sz);
16569 +       ioc->alloc_total += sz;
16570 +       ioc->sasPhyInfo = (sas_phy_info_t *) mem;
16571 +
16572 +       /* Issue a config request to get phy information. */
16573 +       hdr.PageVersion = MPI_SASPHY0_PAGEVERSION;
16574 +       hdr.ExtPageLength = 0;
16575 +       hdr.PageNumber = 0;
16576 +       hdr.Reserved1 = 0;
16577 +       hdr.Reserved2 = 0;
16578 +       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
16579 +       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_PHY;
16580 +
16581 +       cfg.cfghdr.ehdr = &hdr;
16582 +       cfg.dir = 0;    /* read */
16583 +       cfg.timeout = 10;
16584 +
16585 +       /* Fill in information for each phy. */
16586 +       for (ii = 0; ii < ioc->numPhys; ii++) {
16587 +
16588 +               /* Get Phy Pg 0 for each Phy. */
16589 +               cfg.pageAddr = ii;
16590 +               cfg.physAddr = -1;
16591 +               cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
16592 +
16593 +               if ((rc = mpt_config(ioc, &cfg)) != 0) {
16594 +                       goto mpt_sas_get_info_exit;
16595 +               }
16596 +
16597 +               if (hdr.ExtPageLength == 0) {
16598 +                       rc = -EFAULT;
16599 +                       goto mpt_sas_get_info_exit;
16600 +               }
16601 +
16602 +               sasPhyPg0_data_sz = hdr.ExtPageLength * 4;
16603 +               sasPhyPg0 = (SasPhyPage0_t *) pci_alloc_consistent(
16604 +                   ioc->pcidev, sasPhyPg0_data_sz, &sasPhyPg0_dma);
16605 +               if (!sasPhyPg0) {
16606 +                       rc = -ENOMEM;
16607 +                       goto mpt_sas_get_info_exit;
16608 +               }
16609 +
16610 +               memset((u8 *)sasPhyPg0, 0, sasPhyPg0_data_sz);
16611 +               cfg.physAddr = sasPhyPg0_dma;
16612 +               cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
16613 +
16614 +               /* Save HwLinkRate.
16615 +                * It may be modified accidently via FW
16616 +                */
16617 +               if ((rc = mpt_config(ioc, &cfg)) != 0) {
16618 +                       goto mpt_sas_get_info_exit;
16619 +               }
16620 +
16621 +               ioc->sasPhyInfo[ii].hwLinkRate = sasPhyPg0->HwLinkRate;
16622 +               ioc->sasPhyInfo[ii].phyId = ii;
16623 +               ioc->sasPhyInfo[ii].port = sasIoUnitPg0->PhyData[ii].Port;
16624 +               ioc->sasPhyInfo[ii].ControllerDevHandle =
16625 +                   le16_to_cpu(sasIoUnitPg0->PhyData[ii].ControllerDevHandle);
16626 +               ioc->sasPhyInfo[ii].PortFlags =
16627 +                   sasIoUnitPg0->PhyData[ii].PortFlags;
16628 +               ioc->sasPhyInfo[ii].PhyFlags =
16629 +                   sasIoUnitPg0->PhyData[ii].PhyFlags;
16630 +               ioc->sasPhyInfo[ii].NegotiatedLinkRate =
16631 +                   sasIoUnitPg0->PhyData[ii].NegotiatedLinkRate;
16632 +               ioc->sasPhyInfo[ii].ControllerPhyDeviceInfo =
16633 +                   le32_to_cpu(sasIoUnitPg0->PhyData[ii].ControllerPhyDeviceInfo);
16634 +
16635 +               memcpy(&SASAddress64,&sasPhyPg0->SASAddress,sizeof(sasPhyPg0->SASAddress));
16636 +               le64_to_cpus(&SASAddress64);
16637 +               if (SASAddress64) {
16638 +                       dsasprintk(("---- SAS PHY PAGE 0 ------------\n"));
16639 +                       dsasprintk(("Handle=0x%X\n",
16640 +                           le16_to_cpu(sasPhyPg0->AttachedDevHandle)));
16641 +                       dsasprintk(("SAS Address=0x%llX\n",SASAddress64));
16642 +                       dsasprintk(("Attached PHY Identifier=0x%X\n",
16643 +                           sasPhyPg0->AttachedPhyIdentifier));
16644 +                       dsasprintk(("Attached Device Info=0x%X\n",
16645 +                           le32_to_cpu(sasPhyPg0->AttachedDeviceInfo)));
16646 +                       dsasprintk(("Programmed Link Rate=0x%X\n",
16647 +                           sasPhyPg0->ProgrammedLinkRate));
16648 +                       dsasprintk(("Hardware Link Rate=0x%X\n",
16649 +                           ioc->sasPhyInfo[ii].hwLinkRate));
16650 +                       dsasprintk(("Change Count=0x%X\n",
16651 +                           sasPhyPg0->ChangeCount));
16652 +                       dsasprintk(("PHY Info=0x%X\n",
16653 +                           le32_to_cpu(sasPhyPg0->PhyInfo)));
16654 +                       dsasprintk(("\n"));
16655 +               }
16656 +
16657 +               pci_free_consistent(ioc->pcidev, sasPhyPg0_data_sz,
16658 +                   (u8 *) sasPhyPg0, sasPhyPg0_dma);
16659 +
16660 +               sasPhyPg0=NULL;
16661 +       }
16662 +
16663 +
16664 +       /* Get all Device info and store in linked list. */
16665 +       devHandle = 0xFFFF;
16666 +       phyCounter=0;
16667 +       while(1) {
16668 +               /* Get SAS device page 0 */
16669 +
16670 +               hdr.PageVersion = MPI_SASDEVICE0_PAGEVERSION;
16671 +               hdr.ExtPageLength = 0;
16672 +               hdr.PageNumber = 0;
16673 +               hdr.Reserved1 = 0;
16674 +               hdr.Reserved2 = 0;
16675 +               hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
16676 +               hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_DEVICE;
16677 +
16678 +               cfg.cfghdr.ehdr = &hdr;
16679 +               cfg.physAddr = -1;
16680 +               cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
16681 +               cfg.dir = 0;    /* read */
16682 +               cfg.timeout = 10;
16683 +
16684 +               if ((rc = mpt_config(ioc, &cfg)) != 0) {
16685 +                       goto mpt_sas_get_info_exit;
16686 +               }
16687 +
16688 +               if (hdr.ExtPageLength == 0) {
16689 +                       rc = -EFAULT;
16690 +                       goto mpt_sas_get_info_exit;
16691 +               }
16692 +
16693 +               sasDevicePg0_data_sz = hdr.ExtPageLength * 4;
16694 +               sasDevicePg0 = (SasDevicePage0_t *) pci_alloc_consistent(
16695 +                   ioc->pcidev, sasDevicePg0_data_sz, &sasDevicePg0_dma);
16696 +               if (!sasDevicePg0) {
16697 +                       rc = -ENOMEM;
16698 +                       goto mpt_sas_get_info_exit;
16699 +               }
16700 +
16701 +               memset((u8 *)sasDevicePg0, 0, sasDevicePg0_data_sz);
16702 +               cfg.physAddr = sasDevicePg0_dma;
16703 +               cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
16704 +               cfg.pageAddr = devHandle;
16705 +
16706 +               if ((rc = mpt_config(ioc, &cfg)) != 0) {
16707 +
16708 +               /*
16709 +                * break from the while loop when this fails
16710 +                * which means we have discovered all devices
16711 +                */
16712 +                       rc=0;
16713 +                       goto mpt_sas_get_info_exit;
16714 +               }
16715 +
16716 +               dsasprintk(("---- SAS DEVICE PAGE 0 ---------\n"));
16717 +               dsasprintk(("Handle=0x%X\n",le16_to_cpu(sasDevicePg0->DevHandle)));
16718 +               dsasprintk(("Enclosure Handle=0x%X\n",le16_to_cpu(sasDevicePg0->EnclosureHandle)));
16719 +               dsasprintk(("Slot=0x%X\n",le16_to_cpu(sasDevicePg0->Slot)));
16720 +               memcpy(&SASAddress64,&sasDevicePg0->SASAddress,sizeof(sasDevicePg0->SASAddress));
16721 +               le64_to_cpus(&SASAddress64);
16722 +               dsasprintk(("SAS Address=0x%llX\n",SASAddress64));
16723 +               dsasprintk(("Target ID=0x%X\n",sasDevicePg0->TargetID));
16724 +               dsasprintk(("Bus=0x%X\n",sasDevicePg0->Bus));
16725 +               dsasprintk(("PhyNum=0x%X\n",sasDevicePg0->PhyNum));
16726 +               dsasprintk(("AccessStatus=0x%X\n",le16_to_cpu(sasDevicePg0->AccessStatus)));
16727 +               dsasprintk(("Device Info=0x%X\n",le32_to_cpu(sasDevicePg0->DeviceInfo)));
16728 +               dsasprintk(("Flags=0x%X\n",le16_to_cpu(sasDevicePg0->Flags)));
16729 +               dsasprintk(("Physical Port=0x%X\n",sasDevicePg0->PhysicalPort));
16730 +               dsasprintk(("\n"));
16731 +
16732 +               if(phyCounter < ioc->numPhys) {
16733 +                       ioc->sasPhyInfo[phyCounter].SASAddress = SASAddress64;
16734 +                       ioc->sasPhyInfo[phyCounter].devHandle =
16735 +                               le16_to_cpu(sasDevicePg0->DevHandle);
16736 +                       phyCounter++;
16737 +               }else {
16738 +                       if (le32_to_cpu(sasDevicePg0->DeviceInfo) &
16739 +                           (MPI_SAS_DEVICE_INFO_SSP_TARGET |
16740 +                            MPI_SAS_DEVICE_INFO_STP_TARGET |
16741 +                            MPI_SAS_DEVICE_INFO_SATA_DEVICE )) {
16742 +
16743 +                               if ((sasDevice = kmalloc(sizeof (sas_device_info_t),
16744 +                                   GFP_ATOMIC)) == NULL) {
16745 +                                       rc = -ENOMEM;
16746 +                                       goto mpt_sas_get_info_exit;
16747 +                               }
16748 +
16749 +                               memset(sasDevice, 0, sizeof (sas_device_info_t));
16750 +                               ioc->alloc_total += sizeof (sas_device_info_t);
16751 +                               list_add_tail(&sasDevice->list, &ioc->sasDeviceList);
16752 +                               sasDevice->SASAddress = SASAddress64;
16753 +                               sasDevice->TargetId = sasDevicePg0->TargetID;
16754 +                               sasDevice->Bus = sasDevicePg0->Bus;
16755 +                               sasDevice->DeviceInfo =
16756 +                                 le32_to_cpu(sasDevicePg0->DeviceInfo);
16757 +                               sasDevice->DevHandle =
16758 +                                  le16_to_cpu(sasDevicePg0->DevHandle);
16759 +                               sasDevice->Flags =
16760 +                                   le16_to_cpu(sasDevicePg0->Flags);
16761 +                               sasDevice->PhyNum = sasDevicePg0->PhyNum;
16762 +                               sasDevice->PhysicalPort =
16763 +                                   sasDevicePg0->PhysicalPort;
16764 +                               if(sasDevice->DeviceInfo &
16765 +                                   MPI_SAS_DEVICE_INFO_SSP_TARGET)
16766 +                                       ds = "sas";
16767 +                               if(sasDevice->DeviceInfo &
16768 +                                   MPI_SAS_DEVICE_INFO_STP_TARGET)
16769 +                                       ds = "stp";
16770 +                               if(sasDevice->DeviceInfo &
16771 +                                   MPI_SAS_DEVICE_INFO_SATA_DEVICE)
16772 +                                       ds = "sata";
16773 +                               dsasprintk(( 
16774 +                                       "Inserting %s device, channel %d, id %d, phy %d\n\n",
16775 +                                       ds,sasDevice->Bus,
16776 +                                       sasDevice->TargetId,
16777 +                                       sasDevicePg0->PhyNum));
16778 +                       }
16779 +               }
16780 +
16781 +               devHandle = (MPI_SAS_DEVICE_PGAD_FORM_GET_NEXT_HANDLE
16782 +                       << MPI_SAS_DEVICE_PGAD_FORM_SHIFT) |
16783 +                       le16_to_cpu(sasDevicePg0->DevHandle);
16784 +
16785 +               pci_free_consistent(ioc->pcidev, sasDevicePg0_data_sz,
16786 +                           (u8 *) sasDevicePg0, sasDevicePg0_dma);
16787 +
16788 +               sasDevicePg0=NULL;
16789 +
16790 +       };
16791 +
16792 +mpt_sas_get_info_exit:
16793 +
16794 +
16795 +       if (sasPhyPg0)
16796 +               pci_free_consistent(ioc->pcidev, sasPhyPg0_data_sz,
16797 +                   (u8 *) sasPhyPg0, sasPhyPg0_dma);
16798 +
16799 +       if (sasIoUnitPg0)
16800 +               pci_free_consistent(ioc->pcidev, sasIoUnitPg0_data_sz,
16801 +                   (u8 *) sasIoUnitPg0, sasIoUnitPg0_dma);
16802 +
16803 +       if (sasDevicePg0)
16804 +               pci_free_consistent(ioc->pcidev, sasDevicePg0_data_sz,
16805 +                           (u8 *) sasDevicePg0, sasDevicePg0_dma);
16806 +
16807 +       return rc;
16808 +}
16809 +
16810 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
16811 +
16812 +static void
16813 +mptbase_sas_process_event_data(MPT_ADAPTER *ioc,
16814 +    MpiEventDataSasDeviceStatusChange_t * pSasEventData)
16815 +{
16816 +       sas_device_info_t       *sasDevice;
16817 +       int                     ii;
16818 +       char                    *ds=NULL;
16819 +
16820 +       switch(pSasEventData->ReasonCode) {
16821 +       case MPI_EVENT_SAS_DEV_STAT_RC_ADDED:
16822 +
16823 +               // sanity check so we are not adding a target that is already in the list.
16824 +               list_for_each_entry(sasDevice, &ioc->sasDeviceList, list) {
16825 +                       if (pSasEventData->TargetID ==
16826 +                           sasDevice->TargetId)
16827 +                               return;
16828 +                               break; 
16829 +               }
16830 +
16831 +               if ((le32_to_cpu(pSasEventData->DeviceInfo) &
16832 +                   (MPI_SAS_DEVICE_INFO_SSP_TARGET |
16833 +                    MPI_SAS_DEVICE_INFO_STP_TARGET |
16834 +                    MPI_SAS_DEVICE_INFO_SATA_DEVICE )) == 0) {
16835 +                       break;
16836 +               }
16837 +
16838 +               if ((sasDevice = kmalloc(sizeof (sas_device_info_t),
16839 +                   GFP_ATOMIC)) == NULL) {
16840 +                       break;
16841 +               }
16842 +
16843 +               memset(sasDevice, 0, sizeof (sas_device_info_t));
16844 +               list_add_tail(&sasDevice->list, &ioc->sasDeviceList);
16845 +               ioc->alloc_total += sizeof (sas_device_info_t);
16846 +
16847 +               memcpy(&sasDevice->SASAddress,&pSasEventData->SASAddress,sizeof(u64));
16848 +               le64_to_cpus(&sasDevice->SASAddress);
16849 +               sasDevice->TargetId = pSasEventData->TargetID;
16850 +               sasDevice->Bus = pSasEventData->Bus;
16851 +               sasDevice->DeviceInfo =
16852 +                   le32_to_cpu(pSasEventData->DeviceInfo);
16853 +               sasDevice->DevHandle =
16854 +                   le16_to_cpu(pSasEventData->DevHandle);
16855 +               sasDevice->PhyNum = pSasEventData->PhyNum;
16856 +               pSasEventData->ParentDevHandle =
16857 +                   le16_to_cpu(pSasEventData->ParentDevHandle);
16858 +
16859 +               for(ii=0;ii<ioc->numPhys;ii++) {
16860 +                       if(pSasEventData->ParentDevHandle ==
16861 +                           ioc->sasPhyInfo[ii].ControllerDevHandle) {
16862 +                               sasDevice->PhysicalPort =
16863 +                                   ioc->sasPhyInfo[ii].port;
16864 +                       }
16865 +               }
16866 +
16867 +               if(sasDevice->DeviceInfo &
16868 +                   MPI_SAS_DEVICE_INFO_SSP_TARGET)
16869 +                       ds = "sas";
16870 +               if(sasDevice->DeviceInfo &
16871 +                   MPI_SAS_DEVICE_INFO_STP_TARGET)
16872 +                       ds = "stp";
16873 +               if(sasDevice->DeviceInfo &
16874 +                   MPI_SAS_DEVICE_INFO_SATA_DEVICE)
16875 +                       ds = "sata";
16876 +               dsasprintk(( 
16877 +                       "Inserting %s device, channel %d, id %d, phy %d\n\n",
16878 +                       ds,sasDevice->Bus,
16879 +                       sasDevice->TargetId,
16880 +                       sasDevice->PhyNum));
16881 +               dsasprintk(("SAS Address=0x%llX\n",sasDevice->SASAddress));
16882 +               dsasprintk(("Device Info=0x%X\n",sasDevice->DeviceInfo));
16883 +               dsasprintk(("Physical Port=0x%X\n",sasDevice->PhysicalPort));
16884 +               dsasprintk(("\n"));
16885 +
16886 +               break;
16887 +
16888 +       case MPI_EVENT_SAS_DEV_STAT_RC_NOT_RESPONDING:
16889 +
16890 +               list_for_each_entry(sasDevice, &ioc->sasDeviceList, list) {
16891 +
16892 +                       if (le16_to_cpu(pSasEventData->DevHandle) ==
16893 +                           sasDevice->DevHandle) {
16894 +
16895 +                               dsasprintk(("Removing device from link list!!!\n\n"));
16896 +                               list_del(&sasDevice->list);
16897 +                               kfree(sasDevice);
16898 +                               ioc->alloc_total -= sizeof (sas_device_info_t);
16899 +                               break;
16900 +                       }
16901 +               }
16902 +               break;
16903 +
16904 +       case MPI_EVENT_SAS_DEV_STAT_RC_SMART_DATA:
16905 +       case MPI_EVENT_SAS_DEV_STAT_RC_NO_PERSIST_ADDED:
16906 +       case MPI_EVENT_SAS_DEV_STAT_RC_UNSUPPORTED:
16907 +       default:
16908 +               break;
16909 +       }
16910 +
16911 +
16912 +}
16913 +
16914 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
16915 +/*
16916 + *     mptbase_sas_persist_operation - Perform operation on SAS Persitent Table
16917 + *     @ioc: Pointer to MPT_ADAPTER structure
16918 + *     @sas_address: 64bit SAS Address for operation.
16919 + *     @target_id: specified target for operation
16920 + *     @bus: specified bus for operation
16921 + *     @persist_opcode: see below
16922 + *
16923 + *     MPI_SAS_OP_CLEAR_NOT_PRESENT - Free all persist TargetID mappings for
16924 + *             devices not currently present.
16925 + *     MPI_SAS_OP_CLEAR_ALL_PERSISTENT - Clear al persist TargetID mappings
16926 + *
16927 + *     NOTE: Don't use not this function during interrupt time.
16928 + *
16929 + *     Returns: 0 for success, non-zero error
16930 + */
16931 +
16932 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
16933 +int
16934 +mptbase_sas_persist_operation(MPT_ADAPTER *ioc, u8 persist_opcode)
16935 +{
16936 +       SasIoUnitControlRequest_t       *sasIoUnitCntrReq;
16937 +       SasIoUnitControlReply_t         *sasIoUnitCntrReply;
16938 +       MPT_FRAME_HDR                   *mf = NULL;
16939 +       MPIHeader_t                     *mpi_hdr;
16940 +
16941 +
16942 +       /* insure garbage is not sent to fw */
16943 +       switch(persist_opcode) {
16944 +
16945 +       case MPI_SAS_OP_CLEAR_NOT_PRESENT:
16946 +       case MPI_SAS_OP_CLEAR_ALL_PERSISTENT:
16947 +               break;
16948  
16949         default:
16950                 return -1;
16951 @@ -4992,7 +5192,7 @@ mptbase_sas_persist_operation(MPT_ADAPTE
16952                 dfailprintk((MYIOC_s_WARN_FMT "%s, no msg frames!!\n",
16953                     ioc->name,__FUNCTION__));
16954                 return -1;
16955 -        }
16956 +       }
16957  
16958         mpi_hdr = (MPIHeader_t *) mf;
16959         sasIoUnitCntrReq = (SasIoUnitControlRequest_t *)mf;
16960 @@ -5303,7 +5503,7 @@ mpt_GetScsiPortSettings(MPT_ADAPTER *ioc
16961  
16962                                 if ( (pPP0->Capabilities & MPI_SCSIPORTPAGE0_CAP_QAS) == 0 ) {
16963                                         ioc->spi_data.noQas |= MPT_TARGET_NO_NEGO_QAS;
16964 -                                       ddvprintk((KERN_INFO MYNAM ": %s noQas due to Capabilities=%x\n",
16965 +                                       ddvprintk((KERN_INFO MYNAM " :%s noQas due to Capabilities=%x\n",
16966                                                 ioc->name, pPP0->Capabilities));
16967                                 }
16968                                 ioc->spi_data.maxBusWidth = pPP0->Capabilities & MPI_SCSIPORTPAGE0_CAP_WIDE ? 1 : 0;
16969 @@ -5452,188 +5652,6 @@ mpt_readScsiDevicePageHeaders(MPT_ADAPTE
16970         return 0;
16971  }
16972  
16973 -/**
16974 - *     mpt_raid_phys_disk_pg0 - returns phys disk page zero
16975 - *     @ioc: Pointer to a Adapter Structure
16976 - *     @phys_disk_num: io unit unique phys disk num generated by the ioc
16977 - *     @phys_disk: requested payload data returned
16978 - *
16979 - *     Return:
16980 - *     0 on success
16981 - *     -EFAULT if read of config page header fails or data pointer not NULL
16982 - *     -ENOMEM if pci_alloc failed
16983 - **/
16984 -int
16985 -mpt_raid_phys_disk_pg0(MPT_ADAPTER *ioc, u8 phys_disk_num, pRaidPhysDiskPage0_t phys_disk)
16986 -{
16987 -       CONFIGPARMS                     cfg;
16988 -       ConfigPageHeader_t              hdr;
16989 -       dma_addr_t                      dma_handle;
16990 -       pRaidPhysDiskPage0_t            buffer = NULL;
16991 -       int                             rc;
16992 -
16993 -       memset(&cfg, 0 , sizeof(CONFIGPARMS));
16994 -       memset(&hdr, 0 , sizeof(ConfigPageHeader_t));
16995 -
16996 -       hdr.PageType = MPI_CONFIG_PAGETYPE_RAID_PHYSDISK;
16997 -       cfg.cfghdr.hdr = &hdr;
16998 -       cfg.physAddr = -1;
16999 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
17000 -
17001 -       if (mpt_config(ioc, &cfg) != 0) {
17002 -               rc = -EFAULT;
17003 -               goto out;
17004 -       }
17005 -
17006 -       if (!hdr.PageLength) {
17007 -               rc = -EFAULT;
17008 -               goto out;
17009 -       }
17010 -
17011 -       buffer = pci_alloc_consistent(ioc->pcidev, hdr.PageLength * 4,
17012 -           &dma_handle);
17013 -
17014 -       if (!buffer) {
17015 -               rc = -ENOMEM;
17016 -               goto out;
17017 -       }
17018 -
17019 -       cfg.physAddr = dma_handle;
17020 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
17021 -       cfg.pageAddr = phys_disk_num;
17022 -
17023 -       if (mpt_config(ioc, &cfg) != 0) {
17024 -               rc = -EFAULT;
17025 -               goto out;
17026 -       }
17027 -
17028 -       rc = 0;
17029 -       memcpy(phys_disk, buffer, sizeof(*buffer));
17030 -       phys_disk->MaxLBA = le32_to_cpu(buffer->MaxLBA);
17031 -
17032 - out:
17033 -
17034 -       if (buffer)
17035 -               pci_free_consistent(ioc->pcidev, hdr.PageLength * 4, buffer,
17036 -                   dma_handle);
17037 -
17038 -       return rc;
17039 -}
17040 -
17041 -/**
17042 - * mpt_inactive_raid_list_free
17043 - *
17044 - * This clears this link list.
17045 - *
17046 - * @ioc - pointer to per adapter structure
17047 - *
17048 - **/
17049 -static void
17050 -mpt_inactive_raid_list_free(MPT_ADAPTER *ioc)
17051 -{
17052 -       struct inactive_raid_component_info *component_info, *pNext;
17053 -
17054 -       if (list_empty(&ioc->raid_data.inactive_list))
17055 -               return;
17056 -
17057 -       down(&ioc->raid_data.inactive_list_mutex);
17058 -       list_for_each_entry_safe(component_info, pNext,
17059 -           &ioc->raid_data.inactive_list, list) {
17060 -               list_del(&component_info->list);
17061 -               kfree(component_info);
17062 -       }
17063 -       up(&ioc->raid_data.inactive_list_mutex);
17064 -}
17065 -
17066 -/**
17067 - * mpt_inactive_raid_volumes
17068 - *
17069 - * This sets up link list of phy_disk_nums for devices belonging in an inactive volume
17070 - *
17071 - * @ioc - pointer to per adapter structure
17072 - * @channel - volume channel
17073 - * @id - volume target id
17074 - *
17075 - *
17076 - **/
17077 -static void
17078 -mpt_inactive_raid_volumes(MPT_ADAPTER *ioc, u8 channel, u8 id)
17079 -{
17080 -       CONFIGPARMS                     cfg;
17081 -       ConfigPageHeader_t              hdr;
17082 -       dma_addr_t                      dma_handle;
17083 -       pRaidVolumePage0_t              buffer = NULL;
17084 -       int                             i;
17085 -       RaidPhysDiskPage0_t             phys_disk;
17086 -       struct inactive_raid_component_info *component_info;
17087 -       int                             handle_inactive_volumes;
17088 -
17089 -       memset(&cfg, 0 , sizeof(CONFIGPARMS));
17090 -       memset(&hdr, 0 , sizeof(ConfigPageHeader_t));
17091 -       hdr.PageType = MPI_CONFIG_PAGETYPE_RAID_VOLUME;
17092 -       cfg.pageAddr = (channel << 8) + id;
17093 -       cfg.cfghdr.hdr = &hdr;
17094 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
17095 -
17096 -       if (mpt_config(ioc, &cfg) != 0)
17097 -               goto out;
17098 -
17099 -       if (!hdr.PageLength)
17100 -               goto out;
17101 -
17102 -       buffer = pci_alloc_consistent(ioc->pcidev, hdr.PageLength * 4,
17103 -           &dma_handle);
17104 -
17105 -       if (!buffer)
17106 -               goto out;
17107 -
17108 -       cfg.physAddr = dma_handle;
17109 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
17110 -
17111 -       if (mpt_config(ioc, &cfg) != 0)
17112 -               goto out;
17113 -
17114 -       if (!buffer->NumPhysDisks)
17115 -               goto out;
17116 -
17117 -       handle_inactive_volumes =
17118 -          (buffer->VolumeStatus.Flags & MPI_RAIDVOL0_STATUS_FLAG_VOLUME_INACTIVE ||
17119 -          (buffer->VolumeStatus.Flags & MPI_RAIDVOL0_STATUS_FLAG_ENABLED) == 0 ||
17120 -           buffer->VolumeStatus.State == MPI_RAIDVOL0_STATUS_STATE_FAILED ||
17121 -           buffer->VolumeStatus.State == MPI_RAIDVOL0_STATUS_STATE_MISSING) ? 1 : 0;
17122 -
17123 -       if (!handle_inactive_volumes)
17124 -               goto out;
17125 -
17126 -       down(&ioc->raid_data.inactive_list_mutex);
17127 -       for (i = 0; i < buffer->NumPhysDisks; i++) {
17128 -               if(mpt_raid_phys_disk_pg0(ioc,
17129 -                   buffer->PhysDisk[i].PhysDiskNum, &phys_disk) != 0)
17130 -                       continue;
17131 -
17132 -               if ((component_info = kmalloc(sizeof (*component_info),
17133 -                GFP_KERNEL)) == NULL)
17134 -                       continue;
17135 -
17136 -               component_info->volumeID = id;
17137 -               component_info->volumeBus = channel;
17138 -               component_info->d.PhysDiskNum = phys_disk.PhysDiskNum;
17139 -               component_info->d.PhysDiskBus = phys_disk.PhysDiskBus;
17140 -               component_info->d.PhysDiskID = phys_disk.PhysDiskID;
17141 -               component_info->d.PhysDiskIOC = phys_disk.PhysDiskIOC;
17142 -
17143 -               list_add_tail(&component_info->list,
17144 -                   &ioc->raid_data.inactive_list);
17145 -       }
17146 -       up(&ioc->raid_data.inactive_list_mutex);
17147 -
17148 - out:
17149 -       if (buffer)
17150 -               pci_free_consistent(ioc->pcidev, hdr.PageLength * 4, buffer,
17151 -                   dma_handle);
17152 -}
17153 -
17154 -
17155  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
17156  /**
17157   *     mpt_findImVolumes - Identify IDs of hidden disks and RAID Volumes
17158 @@ -5657,16 +5675,8 @@ mpt_findImVolumes(MPT_ADAPTER *ioc)
17159         int                      jj;
17160         int                      rc = 0;
17161         int                      iocpage2sz;
17162 -
17163 -       if (!ioc->ir_firmware)
17164 -               return 0;
17165 -
17166 -       /* Free the old page
17167 -        */
17168 -       kfree(ioc->raid_data.pIocPg2);
17169 -       ioc->raid_data.pIocPg2 = NULL;
17170 -       mpt_inactive_raid_list_free(ioc);
17171 -       ioc->raid_data.isRaid = 0;
17172 +       u8                       nVols, nPhys;
17173 +       u8                       vid, vbus, vioc;
17174  
17175         /* Read IOCP2 header then the page.
17176          */
17177 @@ -5696,35 +5706,53 @@ mpt_findImVolumes(MPT_ADAPTER *ioc)
17178         if (mpt_config(ioc, &cfg) != 0)
17179                 goto done_and_free;
17180  
17181 -       mem = kmalloc(iocpage2sz, GFP_ATOMIC);
17182 -       if (!mem)
17183 -               goto done_and_free;
17184 -
17185 +       if ( (mem = (u8 *)ioc->raid_data.pIocPg2) == NULL ) {
17186 +               mem = kmalloc(iocpage2sz, GFP_ATOMIC);
17187 +               if (mem) {
17188 +                       ioc->raid_data.pIocPg2 = (IOCPage2_t *) mem;
17189 +               } else {
17190 +                       goto done_and_free;
17191 +               }
17192 +       }
17193         memcpy(mem, (u8 *)pIoc2, iocpage2sz);
17194 -       ioc->raid_data.pIocPg2 = (IOCPage2_t *) mem;
17195  
17196         /* Identify RAID Volume Id's */
17197 -       if (pIoc2->NumActiveVolumes) {
17198 -
17199 -               pIocRv = pIoc2->RaidVolume;
17200 -               /*
17201 -                * WARNING - ioc->raid_data.isRaid
17202 -                * doesn't consider channels
17203 +       nVols = pIoc2->NumActiveVolumes;
17204 +       if ( nVols == 0) {
17205 +               /* No RAID Volume.
17206                  */
17207 -               for (jj = 0; jj < pIoc2->NumActiveVolumes; jj++, pIocRv++) {
17208 -                       if (pIocRv->VolumeBus)
17209 -                               continue;
17210 -                       ioc->raid_data.isRaid |= (1 << pIocRv->VolumeID);
17211 -                       mpt_inactive_raid_volumes(ioc,
17212 -                           pIoc2->RaidVolume[jj].VolumeBus,
17213 -                           pIoc2->RaidVolume[jj].VolumeID);
17214 +               goto done_and_free;
17215 +       } else {
17216 +               /* At least 1 RAID Volume
17217 +                */
17218 +               pIocRv = pIoc2->RaidVolume;
17219 +               ioc->raid_data.isRaid = 0;
17220 +               for (jj = 0; jj < nVols; jj++, pIocRv++) {
17221 +                       vid = pIocRv->VolumeID;
17222 +                       vbus = pIocRv->VolumeBus;
17223 +                       vioc = pIocRv->VolumeIOC;
17224 +
17225 +                       /* find the match
17226 +                        */
17227 +                       if (vbus == 0) {
17228 +                               ioc->raid_data.isRaid |= (1 << vid);
17229 +                       } else {
17230 +                               /* Error! Always bus 0
17231 +                                */
17232 +                       }
17233                 }
17234 -                    mpt_read_ioc_pg_3(ioc);
17235 -                     mpt_read_ioc_pg_6(ioc);
17236 -        }
17237 +       }
17238  
17239 +       /* Identify Hidden Physical Disk Id's */
17240 +       nPhys = pIoc2->NumActivePhysDisks;
17241 +       if (nPhys == 0) {
17242 +               /* No physical disks.
17243 +                */
17244 +       } else {
17245 +               mpt_read_ioc_pg_3(ioc);
17246 +       }
17247  
17248 - done_and_free:
17249 +done_and_free:
17250         pci_free_consistent(ioc->pcidev, iocpage2sz, pIoc2, ioc2_dma);
17251  
17252         return rc;
17253 @@ -5845,65 +5873,6 @@ mpt_read_ioc_pg_4(MPT_ADAPTER *ioc)
17254  }
17255  
17256  static void
17257 -mpt_read_ioc_pg_6(MPT_ADAPTER *ioc)
17258 -{
17259 -       IOCPage6_t              *pIoc6;
17260 -       u8                      *mem;
17261 -       CONFIGPARMS              cfg;
17262 -       ConfigPageHeader_t       header;
17263 -       dma_addr_t               ioc6_dma;
17264 -       int                      iocpage6sz = 0;
17265 -
17266 -       /* Free the old page
17267 -        */
17268 -       if (ioc->raid_data.pIocPg6) {
17269 -               kfree(ioc->raid_data.pIocPg6);
17270 -               ioc->raid_data.pIocPg6 = NULL;
17271 -       }
17272 -
17273 -       /* There is at least one physical disk.
17274 -        * Read and save IOC Page 3
17275 -        */
17276 -       header.PageVersion = 0;
17277 -       header.PageLength = 0;
17278 -       header.PageNumber = 6;
17279 -       header.PageType = MPI_CONFIG_PAGETYPE_IOC;
17280 -       cfg.cfghdr.hdr = &header;
17281 -       cfg.physAddr = -1;
17282 -       cfg.pageAddr = 0;
17283 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
17284 -       cfg.dir = 0;
17285 -       cfg.timeout = 0;
17286 -       if (mpt_config(ioc, &cfg) != 0)
17287 -               return;
17288 -
17289 -       if (header.PageLength == 0)
17290 -               return;
17291 -
17292 -       /* Read Header good, alloc memory
17293 -        */
17294 -       iocpage6sz = header.PageLength * 4;
17295 -       pIoc6 = pci_alloc_consistent(ioc->pcidev, iocpage6sz, &ioc6_dma);
17296 -       if (!pIoc6)
17297 -               return;
17298 -
17299 -       /* Read the Page and save the data
17300 -        * into malloc'd memory.
17301 -        */
17302 -       cfg.physAddr = ioc6_dma;
17303 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
17304 -       if (mpt_config(ioc, &cfg) == 0) {
17305 -               mem = kmalloc(iocpage6sz, GFP_ATOMIC);
17306 -               if (mem) {
17307 -                       memcpy(mem, (u8 *)pIoc6, iocpage6sz);
17308 -                       ioc->raid_data.pIocPg6 = (IOCPage6_t *) mem;
17309 -               }
17310 -       }
17311 -
17312 -       pci_free_consistent(ioc->pcidev, iocpage6sz, pIoc6, ioc6_dma);
17313 -}
17314 -
17315 -static void
17316  mpt_read_ioc_pg_1(MPT_ADAPTER *ioc)
17317  {
17318         IOCPage1_t              *pIoc1;
17319 @@ -6007,12 +5976,13 @@ SendEventNotification(MPT_ADAPTER *ioc, 
17320                     ioc->name,__FUNCTION__));
17321                 return 0;
17322         }
17323 -       ioc->evnp = evnp;
17324 -        memset(evnp, 0, sizeof(*evnp));
17325 +       memset(evnp, 0, sizeof(*evnp));
17326  
17327         devtprintk((MYIOC_s_INFO_FMT "Sending EventNotification (%d) request %p\n", ioc->name, EvSwitch, evnp));
17328  
17329         evnp->Function = MPI_FUNCTION_EVENT_NOTIFICATION;
17330 +       evnp->ChainOffset = 0;
17331 +       evnp->MsgFlags = 0;
17332         evnp->Switch = EvSwitch;
17333  
17334         mpt_put_msg_frame(mpt_base_index, ioc, (MPT_FRAME_HDR *)evnp);
17335 @@ -6037,10 +6007,13 @@ SendEventAck(MPT_ADAPTER *ioc, EventNoti
17336                 return -1;
17337         }
17338  
17339 -       devtprintk((MYIOC_s_INFO__FMT "Sending EventAck\n", ioc->name));
17340 -        memset(pAck, 0, sizeof(*pAck));
17341 +       devtprintk((MYIOC_s_WARN_FMT "Sending EventAck\n", ioc->name));
17342  
17343         pAck->Function     = MPI_FUNCTION_EVENT_ACK;
17344 +       pAck->ChainOffset  = 0;
17345 +       pAck->Reserved[0]  = pAck->Reserved[1] = 0;
17346 +       pAck->MsgFlags     = 0;
17347 +       pAck->Reserved1[0] = pAck->Reserved1[1] = pAck->Reserved1[2] = 0;
17348         pAck->Event        = evnp->Event;
17349         pAck->EventContext = evnp->EventContext;
17350         DBG_DUMP_EVENT_REQUEST_FRAME(pAck);
17351 @@ -6080,7 +6053,7 @@ mpt_config(MPT_ADAPTER *ioc, CONFIGPARMS
17352          */
17353         in_isr = in_interrupt();
17354         if (in_isr) {
17355 -               dfailprintk((MYIOC_s_WARN_FMT "Config request not allowed in ISR context!\n",
17356 +               dcprintk((MYIOC_s_WARN_FMT "Config request not allowed in ISR context!\n",
17357                                 ioc->name));
17358                 return -EPERM;
17359         }
17360 @@ -6607,12 +6580,11 @@ mpt_HardResetHandler(MPT_ADAPTER *ioc, i
17361          * mpt_do_ioc_recovery at any instant in time.
17362          */
17363         spin_lock_irqsave(&ioc->diagLock, flags);
17364 -          if (ioc->IOCResetInProgress){
17365 +       if ((ioc->diagPending) || (ioc->alt_ioc && ioc->alt_ioc->diagPending)){
17366                 spin_unlock_irqrestore(&ioc->diagLock, flags);
17367 -       dtmprintk((MYIOC_s_INFO_FMT "HardResetHandler: IOCResetInProgress!\n",
17368 -              ioc->name));
17369 -
17370 -                return 0;
17371 +               return 0;
17372 +       } else {
17373 +               ioc->diagPending = 1;
17374         }
17375         spin_unlock_irqrestore(&ioc->diagLock, flags);
17376  
17377 @@ -6633,6 +6605,11 @@ mpt_HardResetHandler(MPT_ADAPTER *ioc, i
17378                                 dtmprintk((MYIOC_s_INFO_FMT "Calling IOC reset_setup handler #%d\n",
17379                                                 ioc->name, ii));
17380                                 r += (*(MptResetHandlers[ii]))(ioc, MPT_IOC_SETUP_RESET);
17381 +                               if (ioc->alt_ioc) {
17382 +                                       dtmprintk((MYIOC_s_INFO_FMT "Calling alt-%s setup reset handler #%d\n",
17383 +                                                       ioc->name, ioc->alt_ioc->name, ii));
17384 +                                       r += (*(MptResetHandlers[ii]))(ioc->alt_ioc, MPT_IOC_SETUP_RESET);
17385 +                               }
17386                         }
17387                 }
17388         }
17389 @@ -6642,307 +6619,23 @@ mpt_HardResetHandler(MPT_ADAPTER *ioc, i
17390                         rc, ioc->name);
17391         }
17392         ioc->reload_fw = 0;
17393 +       if (ioc->alt_ioc)
17394 +               ioc->alt_ioc->reload_fw = 0;
17395  
17396 -       if (ioc->alt_ioc) {
17397 -  dtmprintk((MYIOC_s_INFO_FMT "HardResetHandler alt_ioc: checking IOCResetInProgress=%d\n",
17398 -                       ioc->alt_ioc->name, ioc->alt_ioc->IOCResetInProgress));
17399 -       spin_lock_irqsave(&ioc->alt_ioc->diagLock, flags);
17400 -
17401 -if (ioc->alt_ioc->IOCResetInProgress) {
17402 - dtmprintk((MYIOC_s_INFO_FMT "HardResetHandler: alt_ioc IOCResetInProgress!\n", ioc->alt_ioc->name));
17403 -
17404 -spin_unlock_irqrestore(&ioc->alt_ioc->diagLock, flags);
17405 -return 0;
17406 -}
17407 -spin_unlock_irqrestore(&ioc->alt_ioc->diagLock, flags);
17408 -if ((rc = mpt_do_ioc_recovery(ioc->alt_ioc, MPT_HOSTEVENT_IOC_RECOVER,
17409 -sleepFlag)) != 0) {
17410 -printk(KERN_WARNING MYNAM ": WARNING - alt_%s mpt_do_ioc_recovery failed rc=%x\n", ioc->name,   rc );
17411 -     }
17412 -ioc->alt_ioc->reload_fw = 0;
17413 -}
17414 -
17415 +       spin_lock_irqsave(&ioc->diagLock, flags);
17416 +       ioc->diagPending = 0;
17417 +       if (ioc->alt_ioc)
17418 +               ioc->alt_ioc->diagPending = 0;
17419 +       spin_unlock_irqrestore(&ioc->diagLock, flags);
17420  
17421         dtmprintk((MYIOC_s_INFO_FMT "HardResetHandler rc = %d!\n", ioc->name, rc));
17422  
17423         return rc;
17424  }
17425  
17426 -/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
17427 -/*     mpt_writeSDP1  - write SCSI Device Page 1
17428 - *     @ioc: Pointer to a SCSI Host Adapter Structure
17429 - *     @portnum: IOC port number
17430 - *     @id: writeSDP1 for single ID
17431 - *     @flags: MPT_SCSICFG_ALL_IDS, MPT_SCSICFG_USE_NVRAM, MPT_SCSICFG_BLK_NEGO
17432 - *
17433 - *     Return: -EFAULT if read of config page header fails
17434 - *             or 0 if success.
17435 - *
17436 - *     Remark: If a target has been found, the settings from the
17437 - *             target structure are used, else the device is set
17438 - *             to async/narrow.
17439 - *
17440 - *     Remark: Called during init and after a FW reload.
17441 - *     Remark: We do not wait for a return, write pages sequentially.
17442 - */
17443 -int
17444 -mpt_writeSDP1(MPT_ADAPTER *ioc, int portnum, int id, int flags)
17445 -{
17446 -       Config_t                *pReq;
17447 -       SCSIDevicePage1_t       *pData;
17448 -       struct _MPT_DEVICE      *pMptTarget;
17449 -       VirtDevice              *pTarget;
17450 -       MPT_FRAME_HDR           *mf;
17451 -       dma_addr_t               dataDma;
17452 -       u16                      req_idx;
17453 -       u32                      frameOffset;
17454 -       u32                      requested, configuration, flagsLength;
17455 -       int                      ii, nvram;
17456 -       int                      loop_id, loop_end;
17457 -       u8                       width;
17458 -       u8                       factor;
17459 -       u8                       offset;
17460 -       u8                       bus = 0;
17461 -       u8                       negoFlags;
17462 -       u8                       maxwidth, maxoffset, maxfactor;
17463 -
17464 -       if ((pMptTarget = ioc->Target_List[0]) == NULL)
17465 -               return 0;
17466 -
17467 -       if (ioc->spi_data.sdp1length == 0)
17468 -               return 0;
17469 -
17470 -       if (flags & MPT_SCSICFG_ALL_IDS) {
17471 -               loop_id = 0;
17472 -               loop_end = ioc->DevicesPerBus;
17473 -       } else {
17474 -               loop_id = id;
17475 -               loop_end = id+1;
17476 -       }
17477 -
17478 -       for (; loop_id < loop_end; loop_id++) {
17479 -
17480 -               if (loop_id == ioc->pfacts[portnum].PortSCSIID)
17481 -                       continue;
17482 -
17483 -
17484 -               pTarget = pMptTarget->Target[loop_id];
17485 -
17486 -               /* Use NVRAM to get adapter and target maximums
17487 -                * Data over-riden by target structure information, if present
17488 -                */
17489 -               maxwidth = ioc->spi_data.maxBusWidth;
17490 -               maxoffset = ioc->spi_data.maxSyncOffset;
17491 -               maxfactor = ioc->spi_data.minSyncFactor;
17492 -               if (ioc->spi_data.nvram && (ioc->spi_data.nvram[loop_id] != MPT_HOST_NVRAM_INVALID)) {
17493 -                       nvram = ioc->spi_data.nvram[loop_id];
17494 -
17495 -                       if (maxwidth)
17496 -                               maxwidth = nvram & MPT_NVRAM_WIDE_DISABLE ? 0 : 1;
17497 -
17498 -                       if (maxoffset > 0) {
17499 -                               maxfactor = (nvram & MPT_NVRAM_SYNC_MASK) >> 8;
17500 -                               if (maxfactor == 0) {
17501 -                                       /* Key for async */
17502 -                                       maxfactor = MPT_ASYNC;
17503 -                                       maxoffset = 0;
17504 -                               } else if (maxfactor < ioc->spi_data.minSyncFactor) {
17505 -                                       maxfactor = ioc->spi_data.minSyncFactor;
17506 -                               }
17507 -                       } else
17508 -                               maxfactor = MPT_ASYNC;
17509 -               }
17510 -
17511 -               /* Set the negotiation flags.
17512 -                */
17513 -               negoFlags = ioc->spi_data.noQas;
17514 -               if (!maxwidth)
17515 -                       negoFlags |= MPT_TARGET_NO_NEGO_WIDE;
17516 -
17517 -               if (!maxoffset)
17518 -                       negoFlags |= MPT_TARGET_NO_NEGO_SYNC;
17519 -
17520 -               if (flags & MPT_SCSICFG_USE_NVRAM) {
17521 -                       width = maxwidth;
17522 -                       factor = maxfactor;
17523 -                       offset = maxoffset;
17524 -                       dnegoprintk(("%s: writeSDP1: USE_NVRAM id=%d width=%d factor=%x offset=%x negoFlags=%x\n",
17525 -                               ioc->name, loop_id, width, factor, offset, negoFlags));
17526 -               } else {
17527 -                       width = 0;
17528 -                       factor = MPT_ASYNC;
17529 -                       offset = 0;
17530 -                       //negoFlags = 0;
17531 -                       //negoFlags = MPT_TARGET_NO_NEGO_SYNC;
17532 -                       dnegoprintk(("%s: writeSDP1: !USE_NVRAM: Going Async/Narrow id=%d width=%d factor=%x offset=%x negoFlags=%x\n",
17533 -                               ioc->name, loop_id, width, factor, offset, negoFlags));
17534 -               }
17535 -
17536 -               /* If id is not a raid volume, get the updated
17537 -                * transmission settings from the target structure.
17538 -                */
17539 -               if ( pTarget && !pTarget->raidVolume) {
17540 -                       width = pTarget->maxWidth;
17541 -                       factor = pTarget->minSyncFactor;
17542 -                       offset = pTarget->maxOffset;
17543 -                       negoFlags |= pTarget->negoFlags;
17544 -                       dnegoprintk(("%s: writeSDP1: NOT RAID id=%d width=%d factor=%x offset=%x negoFlags=%x\n",
17545 -                               ioc->name, loop_id, width, factor, offset, negoFlags));
17546 -               }
17547 -
17548 -#ifdef MPTSCSIH_ENABLE_DOMAIN_VALIDATION
17549 -               /* Force to async and narrow if DV has not been executed
17550 -                * for this ID
17551 -                */
17552 -               if ((ioc->spi_data.dvStatus[loop_id] & MPT_SCSICFG_DV_NOT_DONE) != 0) {
17553 -                       width = 0;
17554 -                       factor = MPT_ASYNC;
17555 -                       offset = 0;
17556 -                       dnegoprintk(("%s: writeSDP1: DV_NOT_DONE: Going Async/Narrow id=%d width=%d factor=%x offset=%x negoFlags=%x\n",
17557 -                               ioc->name, loop_id, width, factor, offset, negoFlags));
17558 -               }
17559 -#endif
17560 -
17561 -               if (flags & MPT_SCSICFG_BLK_NEGO) {
17562 -                       negoFlags |= MPT_TARGET_NO_NEGO_WIDE | MPT_TARGET_NO_NEGO_SYNC;
17563 -                       dnegoprintk(("%s: writeSDP1: BLK_NEGO id=%d width=%d factor=%x offset=%x negoFlags=%x\n",
17564 -                               ioc->name, loop_id, width, factor, offset, negoFlags));
17565 -               }
17566 -
17567 -               mpt_setSDP1parameters(width, factor, offset, negoFlags,
17568 -                               &requested, &configuration);
17569 -
17570 -               /* Get a MF for this command.
17571 -                */
17572 -               if ((mf = mpt_get_msg_frame(ioc->DoneCtx, ioc)) == NULL) {
17573 -                       dfailprintk((MYIOC_s_WARN_FMT "%s, no msg frames!!\n",
17574 -                           ioc->name,__FUNCTION__));
17575 -                       return -EAGAIN;
17576 -               }
17577 -
17578 -               /* Set the request and the data pointers.
17579 -                * Request takes: 36 bytes (32 bit SGE)
17580 -                * SCSI Device Page 1 requires 16 bytes
17581 -                * 40 + 16 <= size of SCSI IO Request = 56 bytes
17582 -                * and MF size >= 64 bytes.
17583 -                * Place data at end of MF.
17584 -                */
17585 -               pReq = (Config_t *)mf;
17586 -
17587 -               req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
17588 -               frameOffset = ioc->req_sz - sizeof(SCSIDevicePage1_t);
17589 -
17590 -               pData = (SCSIDevicePage1_t *)((u8 *) mf + frameOffset);
17591 -               dataDma = ioc->req_frames_dma + (req_idx * ioc->req_sz) + frameOffset;
17592 -
17593 -               /* Complete the request frame (same for all requests).
17594 -                */
17595 -               pReq->Action = MPI_CONFIG_ACTION_PAGE_WRITE_CURRENT;
17596 -               pReq->Reserved = 0;
17597 -               pReq->ChainOffset = 0;
17598 -               pReq->Function = MPI_FUNCTION_CONFIG;
17599 -               pReq->ExtPageLength = 0;
17600 -               pReq->ExtPageType = 0;
17601 -               pReq->MsgFlags = 0;
17602 -               for (ii=0; ii < 8; ii++) {
17603 -                       pReq->Reserved2[ii] = 0;
17604 -               }
17605 -               pReq->Header.PageVersion = ioc->spi_data.sdp1version;
17606 -               pReq->Header.PageLength = ioc->spi_data.sdp1length;
17607 -               pReq->Header.PageNumber = 1;
17608 -               pReq->Header.PageType = MPI_CONFIG_PAGETYPE_SCSI_DEVICE;
17609 -               pReq->PageAddress = cpu_to_le32(loop_id | (bus << 8 ));
17610 -
17611 -               /* Add a SGE to the config request.
17612 -                */
17613 -               flagsLength = MPT_SGE_FLAGS_SSIMPLE_WRITE | ioc->spi_data.sdp1length * 4;
17614 -
17615 -               mpt_add_sge((char *)&pReq->PageBufferSGE, flagsLength, dataDma);
17616 -
17617 -               /* Set up the common data portion
17618 -                */
17619 -               pData->Header.PageVersion = pReq->Header.PageVersion;
17620 -               pData->Header.PageLength = pReq->Header.PageLength;
17621 -               pData->Header.PageNumber = pReq->Header.PageNumber;
17622 -               pData->Header.PageType = pReq->Header.PageType;
17623 -               pData->RequestedParameters = cpu_to_le32(requested);
17624 -               pData->Reserved = 0;
17625 -               pData->Configuration = cpu_to_le32(configuration);
17626 -
17627 -               if ( pTarget ) {
17628 -                       if ( requested & MPI_SCSIDEVPAGE1_RP_IU ) {
17629 -                               pTarget->last_lun = MPT_LAST_LUN;
17630 -                       } else {
17631 -                               pTarget->last_lun = MPT_NON_IU_LAST_LUN;
17632 -                       }
17633 -                       dsprintk((MYIOC_s_INFO_FMT
17634 -                               "writeSDP1: last_lun=%d on id=%d\n",
17635 -                               ioc->name, pTarget->last_lun, loop_id));
17636 -               }
17637 -
17638 -               dnegoprintk((MYIOC_s_INFO_FMT
17639 -                       "write SDP1: id=%d pgaddr=0x%x requested=%08x configuration=%08x\n",
17640 -                               ioc->name, loop_id, (loop_id | (bus<<8)),
17641 -                               requested, configuration));
17642 -
17643 -               mpt_put_msg_frame(ioc->DoneCtx, ioc, mf);
17644 -       }
17645 -       return 0;
17646 -}
17647 -
17648 -/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
17649 -/*     mpt_setSDP1parameters  - set SDP1 Requested and Configuration
17650 - *     fields based on width, factor, offset and flags parameters.
17651 - *     @width: bus width
17652 - *     @factor: sync factor
17653 - *     @offset: sync offset
17654 - *     @flags: flags to block WDTR or SDTR negotiation
17655 - *     @requestedPtr: pointer to SDP1 Requested value (updated)
17656 - *     @configurationPtr: pointer to SDP1 Configuration value (updated)
17657 - *
17658 - *     Return: None.
17659 - *
17660 - *     Remark: Called by writeSDP1 and _dv_params
17661 - */
17662 -void
17663 -mpt_setSDP1parameters (u8 width, u8 factor, u8 offset, u8 flags, int *requestedPtr, int *configurationPtr)
17664 -{
17665 -       u8 nowide = flags & MPT_TARGET_NO_NEGO_WIDE;
17666 -       u8 nosync = flags & MPT_TARGET_NO_NEGO_SYNC;
17667 -
17668 -       *configurationPtr = 0;
17669 -       *requestedPtr = width ? MPI_SCSIDEVPAGE1_RP_WIDE : 0;
17670 -       *requestedPtr |= (offset << 16) | (factor << 8);
17671 -
17672 -       if (width && offset && !nowide && !nosync) {
17673 -               if (factor < MPT_ULTRA160) {
17674 -                       *requestedPtr |= (MPI_SCSIDEVPAGE1_RP_IU + MPI_SCSIDEVPAGE1_RP_DT);
17675 -                       if ((flags & MPT_TARGET_NO_NEGO_QAS) == 0)
17676 -                               *requestedPtr |= MPI_SCSIDEVPAGE1_RP_QAS;
17677 -                       if (flags & MPT_TAPE_NEGO_IDP)
17678 -                               *requestedPtr |= 0x08000000;
17679 -               } else if (factor < MPT_ULTRA2) {
17680 -                       *requestedPtr |= MPI_SCSIDEVPAGE1_RP_DT;
17681 -               }
17682 -       }
17683 -
17684 -       if (nowide)
17685 -               *configurationPtr |= MPI_SCSIDEVPAGE1_CONF_WDTR_DISALLOWED;
17686 -
17687 -       if (nosync)
17688 -               *configurationPtr |= MPI_SCSIDEVPAGE1_CONF_SDTR_DISALLOWED;
17689 -
17690 -       return;
17691 -}
17692 -
17693  # define EVENT_DESCR_STR_SZ            100
17694  
17695  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
17696 -
17697 -
17698 -
17699 -
17700 -
17701  static void
17702  EventDescriptionStr(u8 event, u32 evData0, char *evStr)
17703  {
17704 @@ -6969,6 +6662,9 @@ EventDescriptionStr(u8 event, u32 evData
17705                 break;
17706         case MPI_EVENT_RESCAN:
17707                 ds = "Bus Rescan Event";
17708 +               /* Ok, do we need to do anything here? As far as
17709 +                  I can tell, this is when a new device gets added
17710 +                  to the loop. */
17711                 break;
17712         case MPI_EVENT_LINK_STATUS_CHANGE:
17713                 if (evData0 == MPI_EVENT_LINK_STATUS_FAILURE)
17714 @@ -6980,9 +6676,9 @@ EventDescriptionStr(u8 event, u32 evData
17715                 if (evData0 == MPI_EVENT_LOOP_STATE_CHANGE_LIP)
17716                         ds = "Loop State(LIP) Change";
17717                 else if (evData0 == MPI_EVENT_LOOP_STATE_CHANGE_LPE)
17718 -                       ds = "Loop State(LPE) Change";          /* ??? */
17719 +                       ds = "Loop State(LPE) Change";                  /* ??? */
17720                 else
17721 -                       ds = "Loop State(LPB) Change";          /* ??? */
17722 +                       ds = "Loop State(LPB) Change";                  /* ??? */
17723                 break;
17724         case MPI_EVENT_LOGOUT:
17725                 ds = "Logout";
17726 @@ -6995,6 +6691,9 @@ EventDescriptionStr(u8 event, u32 evData
17727                 break;
17728         case MPI_EVENT_INTEGRATED_RAID:
17729         {
17730 +#if defined(CPQ_CIM)
17731 +        ioc->csmi_change_count++;
17732 +#endif
17733                 u8 ReasonCode = (u8)(evData0 >> 16);
17734                 switch (ReasonCode) {
17735                 case MPI_EVENT_RAID_RC_VOLUME_CREATED :
17736 @@ -7044,65 +6743,36 @@ EventDescriptionStr(u8 event, u32 evData
17737                 break;
17738         case MPI_EVENT_SAS_DEVICE_STATUS_CHANGE:
17739         {
17740 -               u8 id = (u8)(evData0);
17741 -               u8 channel = (u8)(evData0 >> 8);
17742 +        u8 id = (u8)(evData0);
17743                 u8 ReasonCode = (u8)(evData0 >> 16);
17744                 switch (ReasonCode) {
17745                 case MPI_EVENT_SAS_DEV_STAT_RC_ADDED:
17746                         snprintf(evStr, EVENT_DESCR_STR_SZ,
17747 -                           "SAS Device Status Change: Added: "
17748 -                           "id=%d channel=%d", id, channel);
17749 +                           "SAS Device Status Change: Added: id=%d", id);
17750                         break;
17751                 case MPI_EVENT_SAS_DEV_STAT_RC_NOT_RESPONDING:
17752                         snprintf(evStr, EVENT_DESCR_STR_SZ,
17753 -                           "SAS Device Status Change: Deleted: "
17754 -                           "id=%d channel=%d", id, channel);
17755 +                           "SAS Device Status Change: Deleted: id=%d", id);
17756                         break;
17757                 case MPI_EVENT_SAS_DEV_STAT_RC_SMART_DATA:
17758                         snprintf(evStr, EVENT_DESCR_STR_SZ,
17759 -                           "SAS Device Status Change: SMART Data: "
17760 -                           "id=%d channel=%d", id, channel);
17761 +                           "SAS Device Status Change: SMART Data: id=%d",
17762 +                           id);
17763                         break;
17764                 case MPI_EVENT_SAS_DEV_STAT_RC_NO_PERSIST_ADDED:
17765                         snprintf(evStr, EVENT_DESCR_STR_SZ,
17766 -                           "SAS Device Status Change: No Persistancy: "
17767 -                           "id=%d channel=%d", id, channel);
17768 -                       break;
17769 -               case MPI_EVENT_SAS_DEV_STAT_RC_UNSUPPORTED:
17770 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17771 -                           "SAS Device Status Change: Unsupported Device "
17772 -                           "Discovered : id=%d channel=%d", id, channel);
17773 -                       break;
17774 -               case MPI_EVENT_SAS_DEV_STAT_RC_INTERNAL_DEVICE_RESET:
17775 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17776 -                           "SAS Device Status Change: Internal Device "
17777 -                           "Reset : id=%d channel=%d", id, channel);
17778 -                       break;
17779 -               case MPI_EVENT_SAS_DEV_STAT_RC_TASK_ABORT_INTERNAL:
17780 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17781 -                           "SAS Device Status Change: Internal Task "
17782 -                           "Abort : id=%d channel=%d", id, channel);
17783 -                       break;
17784 -               case MPI_EVENT_SAS_DEV_STAT_RC_ABORT_TASK_SET_INTERNAL:
17785 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17786 -                           "SAS Device Status Change: Internal Abort "
17787 -                           "Task Set : id=%d channel=%d", id, channel);
17788 -                       break;
17789 -               case MPI_EVENT_SAS_DEV_STAT_RC_CLEAR_TASK_SET_INTERNAL:
17790 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17791 -                           "SAS Device Status Change: Internal Clear "
17792 -                           "Task Set : id=%d channel=%d", id, channel);
17793 -                       break;
17794 -               case MPI_EVENT_SAS_DEV_STAT_RC_QUERY_TASK_INTERNAL:
17795 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17796 -                           "SAS Device Status Change: Internal Query "
17797 -                           "Task : id=%d channel=%d", id, channel);
17798 +                           "SAS Device Status Change: No Persistancy "
17799 +                           "Added: id=%d", id);
17800                         break;
17801 +        case MPI_EVENT_SAS_DEV_STAT_RC_INTERNAL_DEVICE_RESET:
17802 +            snprintf(evStr, EVENT_DESCR_STR_SZ,
17803 +                "SAS Device Status Change: Internal Device Reset: "
17804 +                "id=%d", id);
17805 +            break;
17806                 default:
17807                         snprintf(evStr, EVENT_DESCR_STR_SZ,
17808 -                           "SAS Device Status Change: Unknown: "
17809 -                           "id=%d channel=%d", id, channel);
17810 -                       break;
17811 +                           "SAS Device Status Change: Unknown: id=%d", id);
17812 +                       break;          
17813                 }
17814                 break;
17815         }
17816 @@ -7205,86 +6875,15 @@ EventDescriptionStr(u8 event, u32 evData
17817         }
17818         case MPI_EVENT_SAS_DISCOVERY:
17819         {
17820 -               if (evData0)
17821 -                       ds = "SAS Discovery: Start";
17822 -               else
17823 -                       ds = "SAS Discovery: Stop";
17824 +               char buf[40];
17825 +               sprintf(buf,"SAS Discovery: Condition=0x%x:",evData0);
17826 +               ds = buf;
17827                 break;
17828         }
17829         case MPI_EVENT_LOG_ENTRY_ADDED:
17830                 ds = "SAS Log Entry Added";
17831                 break;
17832  
17833 -       case MPI_EVENT_SAS_BROADCAST_PRIMITIVE:
17834 -       {
17835 -               u8 phy_num = (u8)(evData0);
17836 -               u8 port_num = (u8)(evData0 >> 8);
17837 -               u8 port_width = (u8)(evData0 >> 16);
17838 -               u8 primative = (u8)(evData0 >> 24);
17839 -               snprintf(evStr, EVENT_DESCR_STR_SZ,
17840 -                   "SAS Broadcase Primative: phy=%d port=%d "
17841 -                   "width=%d primative=0x%02x",
17842 -                   phy_num, port_num, port_width, primative);
17843 -               break;
17844 -       }
17845 -
17846 -       case MPI_EVENT_SAS_INIT_DEVICE_STATUS_CHANGE:
17847 -       {
17848 -               u8 reason = (u8)(evData0);
17849 -               u8 port_num = (u8)(evData0 >> 8);
17850 -               u16 handle = le16_to_cpu(evData0 >> 16);
17851 -
17852 -               snprintf(evStr, EVENT_DESCR_STR_SZ,
17853 -                   "SAS Initiator Device Status Change: reason=0x%02x "
17854 -                   "port=%d handle=0x%04x",
17855 -                   reason, port_num, handle);
17856 -               break;
17857 -       }
17858 -
17859 -       case MPI_EVENT_SAS_INIT_TABLE_OVERFLOW:
17860 -       {
17861 -               u8 max_init = (u8)(evData0);
17862 -               u8 current_init = (u8)(evData0 >> 8);
17863 -
17864 -               snprintf(evStr, EVENT_DESCR_STR_SZ,
17865 -                   "SAS Initiator Device Table Overflow: max initiators=%02d "
17866 -                   "current initators=%02d",
17867 -                   max_init, current_init);
17868 -               break;
17869 -       }
17870 -       case MPI_EVENT_SAS_SMP_ERROR:
17871 -       {
17872 -               u8 status = (u8)(evData0);
17873 -               u8 port_num = (u8)(evData0 >> 8);
17874 -               u8 result = (u8)(evData0 >> 16);
17875 -
17876 -               if (status == MPI_EVENT_SAS_SMP_FUNCTION_RESULT_VALID)
17877 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17878 -                           "SAS SMP Error: port=%d result=0x%02x",
17879 -                           port_num, result);
17880 -               else if (status == MPI_EVENT_SAS_SMP_CRC_ERROR)
17881 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17882 -                           "SAS SMP Error: port=%d : CRC Error",
17883 -                           port_num);
17884 -               else if (status == MPI_EVENT_SAS_SMP_TIMEOUT)
17885 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17886 -                           "SAS SMP Error: port=%d : Timeout",
17887 -                           port_num);
17888 -               else if (status == MPI_EVENT_SAS_SMP_NO_DESTINATION)
17889 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17890 -                           "SAS SMP Error: port=%d : No Destination",
17891 -                           port_num);
17892 -               else if (status == MPI_EVENT_SAS_SMP_BAD_DESTINATION)
17893 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17894 -                           "SAS SMP Error: port=%d : Bad Destination",
17895 -                           port_num);
17896 -               else
17897 -                       snprintf(evStr, EVENT_DESCR_STR_SZ,
17898 -                           "SAS SMP Error: port=%d : status=0x%02x",
17899 -                           port_num, status);
17900 -               break;
17901 -       }
17902 -
17903         /*
17904          *  MPT base "custom" events may be added here...
17905          */
17906 @@ -7329,20 +6928,24 @@ ProcessEventNotification(MPT_ADAPTER *io
17907         }
17908  
17909         EventDescriptionStr(event, evData0, evStr);
17910 -       devtprintk((MYIOC_s_WARN_FMT "MPT event:(%02Xh) : %s\n",
17911 -           ioc->name, event, evStr));
17912 +       devtprintk((MYIOC_s_WARN_FMT "MPT Event=%02Xh (%s) detected!\n",
17913 +                       ioc->name, event, evStr));
17914 +
17915  #if defined(MPT_DEBUG) || defined(MPT_DEBUG_EVENTS)
17916 -       printk(KERN_WARN MYNAM ": Event data:\n" KERN_INFO);
17917 -       for (ii = 0; ii < evDataLen; ii++)
17918 -               printk(" %08x", le32_to_cpu(pEventReply->Data[ii]));
17919 -       printk("\n");
17920 +       printk(KERN_INFO MYNAM ": Event data:\n" KERN_INFO);
17921 +       for (ii = 0; ii < evDataLen; ii++)
17922 +               printk(" %08x", le32_to_cpu(pEventReply->Data[ii]));
17923 +       printk("\n");
17924  #endif
17925  
17926 -
17927 -       /*
17928 +       /*
17929          *  Do general / base driver event processing
17930          */
17931         switch(event) {
17932 +       case MPI_EVENT_SAS_DEVICE_STATUS_CHANGE: /* 0F */
17933 +               mptbase_sas_process_event_data(ioc,
17934 +                   (MpiEventDataSasDeviceStatusChange_t *)pEventReply->Data);
17935 +               break;
17936         case MPI_EVENT_EVENT_CHANGE:            /* 0A */
17937                 if (evDataLen) {
17938                         u8 evState = evData0 & 0xFF;
17939 @@ -7359,11 +6962,6 @@ ProcessEventNotification(MPT_ADAPTER *io
17940                 mptbase_raid_process_event_data(ioc,
17941                     (MpiEventDataRaid_t *)pEventReply->Data);
17942                 break;
17943 -case MPI_EVENT_RESCAN:
17944 -case MPI_EVENT_LINK_STATUS_CHANGE:
17945 -ioc->FcLinkSpeedCheckNeeded = 1;
17946 -break;
17947 -
17948         default:
17949                 break;
17950         }
17951 @@ -7396,10 +6994,9 @@ break;
17952          */
17953         for (ii=MPT_MAX_PROTOCOL_DRIVERS-1; ii; ii--) {
17954                 if (MptEvHandlers[ii]) {
17955 -               devtprintk((MYIOC_s_WARN_FMT "Routing Event to event handler #%d\n",
17956 -                                 ioc->name, ii));
17957 -
17958 -                       r += (*(MptEvHandlers[ii]))(ioc, pEventReply);
17959 +                       devtprintk((MYIOC_s_INFO_FMT "Routing Event to event handler #%d\n",
17960 +                                       ioc->name, ii));
17961 +                       r += (*(MptEvHandlers[ii]))(ioc, pEventReply);
17962                         handlers++;
17963                 }
17964         }
17965 @@ -7412,7 +7009,7 @@ break;
17966                 devtprintk((MYIOC_s_WARN_FMT
17967                         "EventAck required\n",ioc->name));
17968                 if ((ii = SendEventAck(ioc, pEventReply)) != 0) {
17969 -                       devtprintk((MYIOC_s_INFO_FMT "SendEventAck returned %d\n",
17970 +                       devtprintk((MYIOC_s_WARN_FMT "SendEventAck returned %d\n",
17971                                         ioc->name, ii));
17972                 }
17973         }
17974 @@ -7599,14 +7196,20 @@ union loginfo_type {
17975         }
17976  
17977         if (code_desc != NULL)
17978 -               printk("Originator={%s}, Code={%s},"
17979 +               printk(MYIOC_s_INFO_FMT
17980 +                       "LogInfo(0x%08x): Originator={%s}, Code={%s},"
17981                         " SubCode(0x%04x)\n",
17982 +                       ioc->name,
17983 +                       log_info,
17984                         originator_str[sas_loginfo.dw.originator],
17985                         code_desc,
17986                         sas_loginfo.dw.subcode);
17987         else
17988 -               printk("Originator={%s}, Code=(0x%02x),"
17989 +               printk(MYIOC_s_INFO_FMT
17990 +                       "LogInfo(0x%08x): Originator={%s}, Code=(0x%02x),"
17991                         " SubCode(0x%04x)\n",
17992 +                       ioc->name,
17993 +                       log_info,
17994                         originator_str[sas_loginfo.dw.originator],
17995                         sas_loginfo.dw.code,
17996                         sas_loginfo.dw.subcode);
17997 @@ -7625,12 +7228,7 @@ static void
17998  mpt_sp_ioc_info(MPT_ADAPTER *ioc, u32 ioc_status, MPT_FRAME_HDR *mf)
17999  {
18000         u32 status = ioc_status & MPI_IOCSTATUS_MASK;
18001 -       char *desc = NULL;
18002 -
18003 -       SCSIIORequest_t *pScsiReq = (SCSIIORequest_t *) mf;
18004 -       U8 cdb = pScsiReq->CDB[0];
18005 -       U8 id = pScsiReq->TargetID;
18006 -       U8 lun = pScsiReq->LUN[1];
18007 +       char *desc = "";
18008  
18009         switch (status) {
18010         case MPI_IOCSTATUS_INVALID_FUNCTION: /* 0x0001 */
18011 @@ -7639,8 +7237,6 @@ mpt_sp_ioc_info(MPT_ADAPTER *ioc, u32 io
18012  
18013         case MPI_IOCSTATUS_BUSY: /* 0x0002 */
18014                 desc = "Busy";
18015 -                ddvprintk (("%s IOCSTATUS_BUSY", ioc->name));
18016 -                DBG_DUMP_RESET_REQUEST_FRAME(ioc, mf)
18017                 break;
18018  
18019         case MPI_IOCSTATUS_INVALID_SGL: /* 0x0003 */
18020 @@ -7692,11 +7288,11 @@ mpt_sp_ioc_info(MPT_ADAPTER *ioc, u32 io
18021  
18022         case MPI_IOCSTATUS_SCSI_DEVICE_NOT_THERE: /* 0x0043 */
18023           {
18024 -#ifdef MPT_DEBUG_REPLY
18025 +               SCSIIORequest_t *pScsiReq = (SCSIIORequest_t *) mf;
18026 +               U8 cdb = pScsiReq->CDB[0];
18027                 if (cdb != 0x12) { /* Inquiry is issued for device scanning */
18028                         desc = "SCSI Device Not There";
18029                 }
18030 -#endif
18031                 break;
18032           }
18033  
18034 @@ -7742,16 +7338,8 @@ mpt_sp_ioc_info(MPT_ADAPTER *ioc, u32 io
18035                 desc = "Others";
18036                 break;
18037         }
18038 -       if (desc != NULL) {
18039 -               U8 function = pScsiReq->Function;
18040 -               if (function == MPI_FUNCTION_SCSI_IO_REQUEST ||
18041 -                   function == MPI_FUNCTION_RAID_SCSI_IO_PASSTHROUGH) {
18042 -                       printk(MYIOC_s_WARN_FMT "IOCStatus(0x%04x): %s on CDB=%x id=%d lun=%d\n", ioc->name, status, desc, cdb, id, lun);
18043 -               } else {
18044 -                       printk(MYIOC_s_WARN_FMT "IOCStatus(0x%04x): %s on Function=%02x\n", ioc->name, status, desc, function);
18045 -               }
18046 -                DBG_DUMP_REPLYS_REQUEST_FRAME(ioc, mf)
18047 -       }
18048 +       if (desc != "")
18049 +               printk(MYIOC_s_INFO_FMT "IOCStatus(0x%04x): %s\n", ioc->name, status, desc);
18050  }
18051  
18052  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
18053 @@ -7770,6 +7358,7 @@ mpt_poll_interrupt(MPT_ADAPTER *ioc)
18054         if (intstat & MPI_HIS_REPLY_MESSAGE_INTERRUPT)
18055                 mpt_interrupt(0, ioc, NULL);
18056  }
18057 +
18058  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
18059  EXPORT_SYMBOL(mpt_attach);
18060  EXPORT_SYMBOL(mpt_detach);
18061 @@ -7779,6 +7368,7 @@ EXPORT_SYMBOL(mpt_suspend);
18062  #endif
18063  EXPORT_SYMBOL(ioc_list);
18064  EXPORT_SYMBOL(mpt_can_queue);
18065 +EXPORT_SYMBOL(mpt_sg_tablesize);
18066  EXPORT_SYMBOL(mpt_proc_root_dir);
18067  EXPORT_SYMBOL(mpt_register);
18068  EXPORT_SYMBOL(mpt_deregister);
18069 @@ -7800,21 +7390,16 @@ EXPORT_SYMBOL(mpt_print_ioc_summary);
18070  EXPORT_SYMBOL(mpt_lan_index);
18071  EXPORT_SYMBOL(mpt_stm_index);
18072  EXPORT_SYMBOL(mpt_HardResetHandler);
18073 -EXPORT_SYMBOL(mpt_SendIocReset);
18074 -EXPORT_SYMBOL(mpt_do_ioc_recovery);
18075 -EXPORT_SYMBOL(mpt_writeSDP1);
18076 -EXPORT_SYMBOL(mpt_setSDP1parameters);
18077  EXPORT_SYMBOL(mpt_config);
18078  EXPORT_SYMBOL(mpt_findImVolumes);
18079  EXPORT_SYMBOL(mpt_read_ioc_pg_3);
18080  EXPORT_SYMBOL(mpt_alloc_fw_memory);
18081  EXPORT_SYMBOL(mpt_free_fw_memory);
18082  EXPORT_SYMBOL(mptbase_sas_persist_operation);
18083 +EXPORT_SYMBOL(mpt_sas_get_info);
18084  EXPORT_SYMBOL_GPL(mpt_poll_interrupt);
18085  EXPORT_SYMBOL(mpt_alt_ioc_wait);
18086 -EXPORT_SYMBOL(mpt_raid_phys_disk_pg0);
18087 -EXPORT_SYMBOL(mpt_enable_deadioc_detect);
18088 -EXPORT_SYMBOL(mpt_handshake_req_reply_wait);
18089 +
18090  
18091  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
18092  /*
18093 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptbase.h linux-2.6.9-55.0.12/drivers/message/fusion/mptbase.h
18094 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptbase.h 2007-12-21 11:40:54.000000000 +0100
18095 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptbase.h        2007-11-02 09:10:23.000000000 +0100
18096 @@ -5,8 +5,8 @@
18097   *          LSIFC9xx/LSI409xx Fibre Channel
18098   *      running LSI Logic Fusion MPT (Message Passing Technology) firmware.
18099   *
18100 - *  Copyright (c) 1999-2007 LSI Logic Corporation
18101 - *  (    mpt_linux_developer@lsi.com)
18102 + *  Copyright (c) 1999-2005 LSI Logic Corporation
18103 + *  (mailto:mpt_linux_developer@lsil.com)
18104   *
18105   *  $Id: mptbase.h,v 1.149 2003/05/07 14:08:31 Exp $
18106   */
18107 @@ -78,14 +78,14 @@
18108  #endif
18109  
18110  #ifndef COPYRIGHT
18111 -#define COPYRIGHT      "Copyright (c) 1999-2007 " MODULEAUTHOR
18112 +#define COPYRIGHT      "Copyright (c) 1999-2006 " MODULEAUTHOR
18113  #endif
18114  
18115 -#define MPT_LINUX_VERSION_COMMON       "3.02.99.00rh"
18116 -#define MPT_LINUX_PACKAGE_NAME         "@(#)mptlinux-3.02.99.00rh"
18117 +#define MPT_LINUX_VERSION_COMMON       "3.02.73rh"
18118 +#define MPT_LINUX_PACKAGE_NAME         "@(#)mptlinux-3.02.73rh"
18119  #define MPT_LINUX_MAJOR_VERSION                3
18120  #define MPT_LINUX_MINOR_VERSION                02
18121 -#define MPT_LINUX_BUILD_VERSION                99
18122 +#define MPT_LINUX_BUILD_VERSION                73
18123  #define MPT_LINUX_RELEASE_VERSION      00
18124  #define WHAT_MAGIC_STRING              "@" "(" "#" ")"
18125  
18126 @@ -96,8 +96,10 @@
18127  /*
18128   *  Fusion MPT(linux) driver configurable stuff...
18129   */
18130 +#define MPT_MAX_ADAPTERS               18
18131  #define MPT_MAX_PROTOCOL_DRIVERS       16
18132 -#define MPT_MAX_BUSES                  8
18133 +#define MPT_MAX_BUS                    1       /* Do not change */
18134 +#define MPT_MAX_FC_DEVICES             255
18135  #define MPT_MAX_SCSI_DEVICES           16
18136  #define MPT_LAST_LUN                   255
18137  #define MPT_NON_IU_LAST_LUN            63
18138 @@ -137,9 +139,6 @@
18139  #define         CAN_SLEEP                      1
18140  #define  NO_SLEEP                      0
18141  
18142 -#define MPT_HZ                         1000
18143 -#define MPT_JIFFY                      100
18144 -
18145  #define MPT_COALESCING_TIMEOUT         0x10
18146  
18147  /*
18148 @@ -170,9 +169,7 @@
18149  /*
18150   * Default MAX_SGE value.  Can be changed by using mptbase sg_count parameter.
18151   */
18152 -#ifndef CONFIG_FUSION_MAX_SGE
18153 -#define CONFIG_FUSION_MAX_SGE  128
18154 -#endif
18155 +#define MPT_SCSI_SG_DEPTH      128
18156  
18157  #ifdef __KERNEL__      /* { */
18158  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
18159 @@ -218,6 +215,8 @@ typedef union _MPT_FRAME_TRACKER {
18160         struct {
18161                 struct list_head        list;
18162                 u32                      arg1;
18163 +               u32                      pad;
18164 +               void                    *argp1;
18165         } linkage;
18166         /*
18167          * NOTE: When request frames are free, on the linkage structure
18168 @@ -277,12 +276,6 @@ typedef struct _MPT_FRAME_HDR {
18169         } u;
18170  } MPT_FRAME_HDR;
18171  
18172 -typedef struct _MPT_LINKAGE {
18173 -               struct list_head        list;
18174 -               MPT_FRAME_HDR           *mf;
18175 -} MPT_LINKAGE;
18176 -
18177 -
18178  #define MPT_REQ_MSGFLAGS_DROPME                0x80
18179  
18180  typedef struct _MPT_SGL_HDR {
18181 @@ -336,31 +329,15 @@ typedef struct _SYSIF_REGS
18182  #define MPT_TARGET_NO_NEGO_QAS         0x04
18183  #define MPT_TAPE_NEGO_IDP              0x08
18184  
18185 -#if defined(CPQ_CIM)
18186 -struct sas_mapping{
18187 -       u8                      id;
18188 -       u8                      channel;
18189 -};
18190 -
18191 -struct sas_device_info {
18192 -       struct list_head        list;
18193 -       struct sas_mapping      os;     /* operating system mapping*/
18194 -       struct sas_mapping      fw;     /* firmware mapping */
18195 -       u64                     sas_address;
18196 -       u32                     device_info; /* specific bits for devices */
18197 -       u8                      is_logical_volume; /* is this logical volume */
18198 -       u8                      is_cached;      /* cached data for a removed device */
18199 -};
18200 -#endif
18201 -
18202  /*
18203   *     VirtDevice - FC LUN device or SCSI target device
18204   */
18205  typedef struct _VirtDevice {
18206 -        struct _MPT_ADAPTER    *ioc;
18207 +       struct scsi_device      *device;
18208         u16                      tflags;
18209 -       u8                       id;
18210 -       u8                       bus;
18211 +       u8                       ioc_id;
18212 +       u8                       target_id;
18213 +       u8                       bus_id;
18214         u8                       minSyncFactor; /* 0xFF is async */
18215         u8                       maxOffset;     /* 0 if async */
18216         u8                       maxWidth;      /* 0 if narrow, 1 if wide */
18217 @@ -385,13 +362,9 @@ typedef struct _VirtDevice {
18218         u8                       pad2[4];
18219         U64                      WWPN;
18220         U64                      WWNN;
18221 -       struct work_struct        dvTask;
18222 -       u8                       configured_lun;
18223 +       u8                       configured_lun;
18224  } VirtDevice;
18225  
18226 -typedef struct _MPT_DEVICE {
18227 -       VirtDevice      *Target[0];
18228 -} MPT_DEVICE;
18229  /*
18230   *  Fibre Channel (SCSI) target device and associated defines...
18231   */
18232 @@ -440,6 +413,7 @@ do { \
18233  #define MPT_IOCTL_STATUS_SENSE_VALID   0x08    /* Sense data is valid */
18234  #define MPT_IOCTL_STATUS_COMMAND_GOOD  0x10    /* Command Status GOOD */
18235  #define MPT_IOCTL_STATUS_TMTIMER_ACTIVE        0x20    /* The TM timer is running */
18236 +#define MPT_IOCTL_STATUS_TM_FAILED     0x40    /* User TM request failed */
18237  
18238  #define MPTCTL_RESET_OK                        0x01    /* Issue Bus Reset */
18239  
18240 @@ -448,10 +422,10 @@ typedef struct _MPT_IOCTL {
18241         u8                       ReplyFrame[MPT_DEFAULT_FRAME_SIZE];    /* reply frame data */
18242         u8                       sense[MPT_SENSE_BUFFER_ALLOC];
18243         int                      wait_done;     /* wake-up value for this ioc */
18244 +       u8                       rsvd;
18245         u8                       status;        /* current command status */
18246         u8                       reset;         /* 1 if bus reset allowed */
18247 -       u8                       bus;           /* bus */
18248 -       u8                       id;            /* id for reset */
18249 +       u8                       target;        /* target for reset */
18250         struct semaphore         sem_ioc;
18251  } MPT_IOCTL;
18252  
18253 @@ -462,7 +436,7 @@ typedef struct _MPT_IOCTL {
18254  typedef struct _mpt_ioctl_events {
18255         u32     event;          /* Specified by define above */
18256         u32     eventContext;   /* Index or counter */
18257 -       u32     data[2];        /* First 8 bytes of Event Data */
18258 +       int     data[2];        /* First 8 bytes of Event Data */
18259  } MPT_IOCTL_EVENTS;
18260  
18261  /*
18262 @@ -477,14 +451,14 @@ typedef struct _mpt_ioctl_events {
18263                                                 /* dvStatus defines: */
18264  #define MPT_SCSICFG_NEGOTIATE          0x01    /* Negotiate on next IO */
18265  #define MPT_SCSICFG_NEED_DV            0x02    /* Schedule DV */
18266 -#define MPT_SCSICFG_DV_IN_PROGRESS     0x04    /* DV on this physical id*/
18267 +#define MPT_SCSICFG_DV_PENDING         0x04    /* DV on this physical id pending */
18268  #define MPT_SCSICFG_DV_NOT_DONE                0x08    /* DV has not been performed */
18269 -#define MPT_SCSICFG_PHYSDISK_DV_ONLY   0x10    /* DV only on this PhysDisk*/
18270 -#define MPT_SCSICFG_BLK_NEGO           0x20    /* WriteSDP1 with WDTR and SDTR disabled*/
18271 -#define MPT_SCSICFG_RELOAD_IOC_PG3     0x40    /* IOC Pg 3 data is obsolete */
18272 +#define MPT_SCSICFG_BLK_NEGO           0x10    /* WriteSDP1 with WDTR and SDTR disabled */
18273 +#define MPT_SCSICFG_RELOAD_IOC_PG3     0x20    /* IOC Pg 3 data is obsolete */
18274                                                 /* Args passed to writeSDP1: */
18275  #define MPT_SCSICFG_USE_NVRAM          0x01    /* WriteSDP1 using NVRAM */
18276  #define MPT_SCSICFG_ALL_IDS            0x02    /* WriteSDP1 to all IDS */
18277 +/* #define MPT_SCSICFG_BLK_NEGO                0x10       WriteSDP1 with WDTR and SDTR disabled */
18278  
18279  typedef        struct _SpiCfgData {
18280         u32              PortFlags;
18281 @@ -520,36 +494,48 @@ typedef   struct _SasCfgData {
18282                                                  * automatic clearing.
18283                                                  */
18284         u8              mpt_sas_hot_plug_enable;  /* disables hot swap device remove support */
18285 -    ManufacturingPage7_t    *pManufPg7; /* Connector Info on SAS controllers */
18286  }SasCfgData;
18287  
18288 -/*
18289 - * Inactive volume link list of raid component data
18290 - * @inactive_list
18291 - */
18292 -struct inactive_raid_component_info {
18293 -       struct   list_head list;
18294 -       u8               volumeID;              /* volume target id */
18295 -       u8               volumeBus;             /* volume channel */
18296 -       IOC_3_PHYS_DISK  d;                     /* phys disk info */
18297 -};
18298 -
18299  typedef        struct _RaidCfgData {
18300         IOCPage2_t      *pIocPg2;               /* table of Raid Volumes */
18301         IOCPage3_t      *pIocPg3;               /* table of physical disks */
18302 -       IOCPage6_t      *pIocPg6;       /* table of IR static data */
18303 -       int              isRaid;                    /* bit field, 1 if RAID */
18304 -       struct semaphore        inactive_list_mutex;
18305 -       struct list_head        inactive_list; /* link list for physical
18306 -                                               disk that belong in
18307 -                                               inactive volumes */
18308 +       int              isRaid;                /* bit field, 1 if RAID */
18309  } RaidCfgData;
18310  
18311  /*
18312 - *  Adapter Structure - pci_dev specific.
18313 + * sas device info link list
18314   */
18315 +typedef struct _sas_device_info {
18316 +       struct list_head list;
18317 +       u64     SASAddress;
18318 +       u8      TargetId;
18319 +       u8      Bus;
18320 +       u8      PhysicalPort;
18321 +       u8      PhyNum;
18322 +       u32     DeviceInfo;
18323 +       u16     DevHandle;
18324 +       u16     Flags;
18325 +} sas_device_info_t;
18326 +
18327 +/*
18328 + * hba phy info array
18329 + */
18330 +typedef struct _sas_phy_info {
18331 +       u64     SASAddress;
18332 +       u8      port;
18333 +       u8      PortFlags;
18334 +       u8      PhyFlags;
18335 +       u8      NegotiatedLinkRate;
18336 +       u16     ControllerDevHandle;
18337 +       u16     devHandle;
18338 +       u32     ControllerPhyDeviceInfo;
18339 +       u8      phyId;
18340 +       u8      hwLinkRate;
18341 +       u8      reserved;
18342 +} sas_phy_info_t;
18343 +
18344  /*
18345 - *  Adapter Structure - pci_dev specific.
18346 + *  Adapter Structure - pci_dev specific. Maximum: MPT_MAX_ADAPTERS
18347   */
18348  typedef struct _MPT_ADAPTER
18349  {
18350 @@ -561,18 +547,13 @@ typedef struct _MPT_ADAPTER
18351         SYSIF_REGS __iomem      *pio_chip;      /* Programmed IO (downloadboot) */
18352         u8                       bus_type;      /* Parallel SCSI i/f */
18353         u8                       pci_slot_number; /* ioc page 1 - pci slot number */
18354 -       u8                       ir_firmware; /* =1 if IR firmware detected */
18355         u16                      deviceID;
18356         u32                      mem_phys;      /* == f4020000 (mmap) */
18357         u32                      pio_mem_phys;  /* Programmed IO (downloadboot) */
18358         int                      mem_size;      /* mmap memory size */
18359 -       int                      sg_tablesize;  /* max SGE's per IO */
18360 -       int                      NumberOfBuses;
18361 -       int                      DevicesPerBus;
18362         int                      alloc_total;
18363         u32                      last_state;
18364         int                      active;
18365 -       struct _MPT_DEVICE      *Target_List[MPT_MAX_BUSES];
18366         u8                      *alloc;         /* frames alloc ptr */
18367         dma_addr_t               alloc_dma;
18368         u32                      alloc_sz;
18369 @@ -600,12 +581,7 @@ typedef struct _MPT_ADAPTER
18370         int                      req_depth;     /* Number of request frames */
18371         int                      req_sz;        /* Request frame size (bytes) */
18372         spinlock_t               FreeQlock;
18373 -       spinlock_t               PendingMFlock;
18374         struct list_head         FreeQ;
18375 -       MPT_FRAME_HDR           *PendingMF;
18376 -       struct scsi_cmnd        *PendingSCpnt;
18377 -       struct timer_list         TMtimer;      /* Timer for TM commands ONLY */
18378 -       MPT_FRAME_HDR            *tmPtr;        /* Ptr to TM request*/
18379                 /* Pool of SCSI sense buffers for commands coming from
18380                  * the SCSI mid-layer.  We have one 256 byte sense buffer
18381                  * for each REQ entry.
18382 @@ -638,12 +614,10 @@ typedef struct _MPT_ADAPTER
18383         struct _MPT_ADAPTER     *alt_ioc;       /* ptr to 929 bound adapter port */
18384         spinlock_t               diagLock;      /* diagnostic reset lock */
18385         int                      diagPending;
18386 -       int                      IOCResetInProgress;
18387         u32                      biosVersion;   /* BIOS version from IO Unit Page 2 */
18388         int                      eventTypes;    /* Event logging parameters */
18389         int                      eventContext;  /* Next event context */
18390         struct _mpt_ioctl_events *events;       /* pointer to event log */
18391 -       EventNotification_t     *evnp;          /* event message frame pointer */
18392         u8                      *cached_fw;     /* Pointer to FW */
18393         dma_addr_t              cached_fw_dma;
18394         struct list_head         configQ;       /* linked list of config. requests */
18395 @@ -662,12 +636,10 @@ typedef struct _MPT_ADAPTER
18396  /* emoore@lsil.com - sas support - start */
18397         U64                      sas_port_WWID[4];
18398         u8                       BoardTracerNumber[16];
18399 +       u8                       numPhys;
18400         u16                      vendorID;
18401 -#if defined(CPQ_CIM)
18402 -       struct list_head         sas_device_info_list;
18403 -       struct semaphore         sas_device_info_mutex;
18404 -       u32                      num_ports;
18405 -#endif
18406 +       sas_phy_info_t           *sasPhyInfo;
18407 +       struct list_head         sasDeviceList;
18408         struct semaphore         hot_plug_semaphore;
18409         struct work_struct       mptscsih_persistTask;
18410         struct timer_list        persist_timer; /* persist table timer */
18411 @@ -680,7 +652,7 @@ typedef struct _MPT_ADAPTER
18412         u32                      PciState[64];     /* save PCI state to this area */
18413  #endif
18414  #if defined(CPQ_CIM)
18415 -       u32         csmi_change_count;    /* count to track all IR events for CSMI */
18416 +    u32         csmi_change_count;    /* count to track all IR events for CSMI */
18417  #endif
18418         /*  
18419          * Description: errata_flag_1064
18420 @@ -694,11 +666,7 @@ typedef struct _MPT_ADAPTER
18421         u8                       upload_fw;     /* If set, do a fw upload */
18422         u8                       reload_fw;     /* Force a FW Reload on next reset */
18423         u8                       NBShiftFactor;  /* NB Shift Factor based on Block Size (Facts)  */
18424 -       u8                       pad1;
18425 -       u8                       CheckFcLinkSpeed;
18426 -       u8                       FcLinkSpeedCheckNeeded;
18427 -       u8                       FcLinkSpeed;
18428 -       MPT_FRAME_HDR           *FcLinkSpeedReqActive;
18429 +       u8                       pad1[4];
18430         int                      DoneCtx;
18431         int                      TaskCtx;
18432         int                      InternalCtx;
18433 @@ -811,25 +779,6 @@ typedef struct _mpt_sge {
18434  #define DBG_DUMP_EVENT_REQUEST_FRAME(mfp)
18435  #endif
18436  
18437 -#ifdef MPT_DEBUG_PEND
18438 -#define dpendprintk(x)  printk x
18439 -#define DBG_DUMP_PENDING_REQUEST_FRAME(ioc, mfp) \
18440 -       {       int  i, n = ioc->req_sz/4;                                              \
18441 -               u32 *m = (u32 *)(mfp);                                  \
18442 -               for (i=0; i<n; i++) {                                   \
18443 -                       if (i && ((i%8)==0))                            \
18444 -                               printk("\n");                           \
18445 -                       printk("%08x ", le32_to_cpu(m[i]));             \
18446 -               }                                                       \
18447 -               printk("\n");                                           \
18448 -       }
18449 -#else
18450 -#define dpendprintk(x)
18451 -#define DBG_DUMP_PENDING_REQUEST_FRAME(ioc, mfp)
18452 -#endif
18453 -
18454 -
18455 -
18456  #ifdef MPT_DEBUG_HOTPLUG
18457  #define dhotpprintk(x)  printk x
18458  #else
18459 @@ -838,51 +787,16 @@ typedef struct _mpt_sge {
18460  
18461  #ifdef MPT_DEBUG_RESET
18462  #define drsprintk(x)  printk x
18463 -#define DBG_DUMP_RESET_REQUEST_FRAME(ioc, mfp) \
18464 -       {       int  i, n = ioc->req_sz/4;                                              \
18465 -               u32 *m = (u32 *)(mfp);                                  \
18466 -               for (i=0; i<n; i++) {                                   \
18467 -                       if (i && ((i%8)==0))                            \
18468 -                               printk("\n");                           \
18469 -                       printk("%08x ", le32_to_cpu(m[i]));             \
18470 -               }                                                       \
18471 -               printk("\n");                                           \
18472 -       }
18473  #else
18474  #define drsprintk(x)
18475 -#define DBG_DUMP_RESET_REQUEST_FRAME(ioc, mfp)
18476  #endif
18477  
18478  //#if defined(MPT_DEBUG) || defined(MPT_DEBUG_MSG_FRAME)
18479  #if defined(MPT_DEBUG_MSG_FRAME)
18480  #define dmfprintk(x)  printk x
18481 -#define DBG_DUMP_REQUEST_FRAME(ioc,mfp) \
18482 -       {       int  i, n = ioc->req_sz/4;
18483 -               u32 *m = (u32 *)(mfp);                                  \
18484 -               for (i=0; i<n; i++) {                                   \
18485 -                       if (i && ((i%8)==0))                            \
18486 -                               printk("\n");                           \
18487 -                       printk("%08x ", le32_to_cpu(m[i]));             \
18488 -               }                                                       \
18489 -               printk("\n");                                           \
18490 -       }
18491 -#else
18492 -#define dmfprintk(x)
18493 -#define DBG_DUMP_REQUEST_FRAME(ioc,mfp)
18494 -#endif
18495 -
18496 -#if defined(MPT_DEBUG_IOS)
18497 -#define dioprintk(x)  printk x
18498 -#else
18499 -#define dioprintk(x)
18500 -#endif
18501 -
18502 -
18503 -#if defined(MPT_DEBUG_CSMI)
18504 -#define DBG_DUMP_CSMI_FRAME(mfp) \
18505 +#define DBG_DUMP_REQUEST_FRAME(mfp) \
18506         {       int  i, n = 24;                                         \
18507                 u32 *m = (u32 *)(mfp);                                  \
18508 -               printk("CSMI MessageFrame:\n");                 \
18509                 for (i=0; i<n; i++) {                                   \
18510                         if (i && ((i%8)==0))                            \
18511                                 printk("\n");                           \
18512 @@ -891,7 +805,8 @@ typedef struct _mpt_sge {
18513                 printk("\n");                                           \
18514         }
18515  #else
18516 -#define DBG_DUMP_CSMI_FRAME(mfp)
18517 +#define dmfprintk(x)
18518 +#define DBG_DUMP_REQUEST_FRAME(mfp)
18519  #endif
18520  
18521  #ifdef MPT_DEBUG_SG
18522 @@ -918,22 +833,28 @@ typedef struct _mpt_sge {
18523  #define dnegoprintk(x)
18524  #endif
18525  
18526 +#if defined(MPT_DEBUG_DV) || defined(MPT_DEBUG_DV_TINY)
18527 +#define ddvtprintk(x)  printk x
18528 +#else
18529 +#define ddvtprintk(x)
18530 +#endif
18531 +
18532  #ifdef MPT_DEBUG_IOCTL
18533  #define dctlprintk(x) printk x
18534  #else
18535  #define dctlprintk(x)
18536  #endif
18537  
18538 -#ifdef MPT_DEBUG_SAS
18539 -#define dsasprintk(x) printk x
18540 +#ifdef MPT_DEBUG_REPLY
18541 +#define dreplyprintk(x) printk x
18542  #else
18543 -#define dsasprintk(x)
18544 +#define dreplyprintk(x)
18545  #endif
18546  
18547 -#ifdef MPT_DEBUG_CSMISAS
18548 -#define dcsmisasprintk(x) printk x
18549 +#ifdef MPT_DEBUG_SAS
18550 +#define dsasprintk(x) printk x
18551  #else
18552 -#define dcsmisasprintk(x)
18553 +#define dsasprintk(x)
18554  #endif
18555  
18556  #ifdef MPT_DEBUG_TM
18557 @@ -988,8 +909,7 @@ typedef struct _mpt_sge {
18558  #define MPT_INDEX_2_RFPTR(ioc,idx) \
18559         (MPT_FRAME_HDR*)( (u8*)(ioc)->reply_frames + (ioc)->req_sz * (idx) )
18560  
18561 -#if defined(MPT_DEBUG_REPLY) || defined(MPT_DEBUG_MSG_FRAME) || defined(MPT_DEBUG_HANDSHAKE)
18562 -#define dreplyprintk(x) printk x
18563 +#if defined(MPT_DEBUG) || defined(MPT_DEBUG_MSG_FRAME) || defined(MPT_DEBUG_HANDSHAKE)
18564  #define DBG_DUMP_REPLY_FRAME(mfp) \
18565         {       u32 *m = (u32 *)(mfp);                                  \
18566                 int  i, n = (le32_to_cpu(m[0]) & 0x00FF0000) >> 16;     \
18567 @@ -1006,36 +926,9 @@ typedef struct _mpt_sge {
18568                         printk(" %08x", le32_to_cpu(m[i]));             \
18569                 printk("\n");                                           \
18570         }
18571 -#define DBG_DUMP_REPLYS_REQUEST_FRAME(ioc,mfp) \
18572 -       {       int  i, n = ioc->req_sz/4;;                                             \
18573 -               u32 *m = (u32 *)(mfp);                                  \
18574 -               for (i=0; i<n; i++) {                                   \
18575 -                       if (i && ((i%8)==0))                            \
18576 -                               printk("\n");                           \
18577 -                       printk("%08x ", le32_to_cpu(m[i]));             \
18578 -               }                                                       \
18579 -               printk("\n");                                           \
18580 -       }
18581 -#define DBG_DUMP_SENSE_DATA(mfp) \
18582 -       {       int  i, n = 8;                                          \
18583 -               u32 *m = (u32 *)(mfp);                                  \
18584 -               printk(KERN_INFO "SENSE DATA: ");                                       \
18585 -               for (i=0; i<n; i++)                                     \
18586 -                       printk(" %08x", le32_to_cpu(m[i]));             \
18587 -               printk("\n");                                           \
18588 -       }
18589  #else
18590 -#define dreplyprintk(x)
18591  #define DBG_DUMP_REPLY_FRAME(mfp)
18592  #define DBG_DUMP_REQUEST_FRAME_HDR(mfp)
18593 -#define DBG_DUMP_REPLYS_REQUEST_FRAME(ioc,mfp)
18594 -#define DBG_DUMP_SENSE_DATA(mfp)
18595 -#endif
18596 -
18597 -#if defined (MPT_DEBUG_ERROR) || defined(MPT_DEBUG_REPLY)
18598 -#define derrprintk(x) printk x
18599 -#else
18600 -#define derrprintk(x)
18601  #endif
18602  
18603  
18604 @@ -1095,34 +988,32 @@ typedef struct _MPT_SCSI_HOST {
18605         u32                       pad0;
18606         struct scsi_cmnd        **ScsiLookup;
18607         struct scsi_device       *device;
18608 +       VirtDevice              **Targets;
18609         MPT_LOCAL_REPLY          *pLocal;               /* used for internal commands */
18610 -       struct timer_list         InternalCmdTimer;
18611 +       struct timer_list         timer;
18612                 /* Pool of memory for holding SCpnts before doing
18613                  * OS callbacks. freeQ is the free pool.
18614                  */
18615         u8                        tmPending;
18616         u8                        resetPending;
18617 +       u8                        negoNvram;            /* DV disabled, nego NVRAM */
18618 +       u8                        pad1;
18619         u8                        tmState;
18620 -       u8                        rsvd[4];
18621 +       u8                        rsvd[2];
18622         MPT_FRAME_HDR            *cmdPtr;               /* Ptr to nonOS request */
18623         struct scsi_cmnd         *abortSCpnt;
18624         MPT_LOCAL_REPLY           localReply;           /* internal cmd reply struct */
18625         unsigned long             hard_resets;          /* driver forced bus resets count */
18626         unsigned long             soft_resets;          /* fw/external bus resets count */
18627         unsigned long             timeouts;             /* cmd timeouts */
18628 -       ushort                    sel_timeout[MPT_MAX_SCSI_DEVICES];
18629 +       ushort                    sel_timeout[MPT_MAX_FC_DEVICES];
18630         char                      *info_kbuf;
18631         wait_queue_head_t         scandv_waitq;
18632         int                       scandv_wait_done;
18633 -       wait_queue_head_t         TM_waitq;
18634 -       int                       TM_wait_done;
18635         long                      last_queue_full;
18636 -       u8                        mpt_pq_filter;
18637 -       u16                       tm_iocstatus;
18638 -       struct list_head          target_reset_list;
18639 +       u8                        mpt_pq_filter;
18640  } MPT_SCSI_HOST;
18641  
18642 -
18643  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
18644  /*
18645   *     More Dynamic Multi-Pathing stuff...
18646 @@ -1176,29 +1067,20 @@ extern void      mpt_free_msg_frame(MPT_ADAP
18647  extern void     mpt_put_msg_frame(int handle, MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf);
18648  extern void     mpt_add_sge(char *pAddr, u32 flagslength, dma_addr_t dma_addr);
18649  
18650 -extern int      mpt_send_handshake_request(int handle, MPT_ADAPTER *ioc, int reqBytes,
18651 -u32 *req, ulong timeout, int sleepFlag);
18652 -
18653 +extern int      mpt_send_handshake_request(int handle, MPT_ADAPTER *ioc, int reqBytes, u32 *req, int sleepFlag);
18654  extern int      mpt_verify_adapter(int iocid, MPT_ADAPTER **iocpp);
18655  extern u32      mpt_GetIocState(MPT_ADAPTER *ioc, int cooked);
18656  extern void     mpt_print_ioc_summary(MPT_ADAPTER *ioc, char *buf, int *size, int len, int showlan);
18657  extern int      mpt_HardResetHandler(MPT_ADAPTER *ioc, int sleepFlag);
18658 -
18659 -extern int       mpt_SendIocReset(MPT_ADAPTER *ioc, u8 reset_type, int sleepFlag);
18660 -extern void      mptscsih_TM_timeout(unsigned long data);
18661 -
18662  extern int      mpt_config(MPT_ADAPTER *ioc, CONFIGPARMS *cfg);
18663 -extern int       mpt_do_ioc_recovery(MPT_ADAPTER *ioc, u32 reason, int sleepFlag);
18664 -extern int       mpt_writeSDP1(MPT_ADAPTER *ioc, int portnum, int id, int flags);
18665 -extern void  mpt_setSDP1parameters (u8 width, u8 factor, u8 offset, u8 flags, int *requestedPtr, int *configurationPtr);
18666  extern void     mpt_alloc_fw_memory(MPT_ADAPTER *ioc, int size);
18667  extern void     mpt_free_fw_memory(MPT_ADAPTER *ioc);
18668  extern int      mpt_findImVolumes(MPT_ADAPTER *ioc);
18669  extern int      mpt_read_ioc_pg_3(MPT_ADAPTER *ioc);
18670  extern int      mptbase_sas_persist_operation(MPT_ADAPTER *ioc, u8 persist_opcode);
18671 +extern int      mpt_sas_get_info(MPT_ADAPTER *ioc);
18672 +extern void     mpt_poll_interrupt(MPT_ADAPTER *ioc);
18673  extern int      mpt_alt_ioc_wait(MPT_ADAPTER *ioc);
18674 -extern void      mpt_poll_interrupt(MPT_ADAPTER *ioc);
18675 -extern int      mpt_raid_phys_disk_pg0(MPT_ADAPTER *ioc, u8 phys_disk_num, pRaidPhysDiskPage0_t phys_disk);
18676  
18677  /*
18678   *  Public data decl's...
18679 @@ -1237,7 +1119,7 @@ extern int                mpt_sg_tablesize;
18680  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
18681  #endif         /* } __KERNEL__ */
18682  
18683 -#if defined(__alpha__) || defined(__sparc_v9__) || defined(__ia64__) || defined(__x86_64__) || defined(__powerpc__)
18684 +#if defined(__alpha__) || defined(__sparc_v9__) || defined(__ia64__) || defined(__x86_64__)
18685  #define CAST_U32_TO_PTR(x)     ((void *)(u64)x)
18686  #define CAST_PTR_TO_U32(x)     ((u32)(u64)x)
18687  #else
18688 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptctl.c linux-2.6.9-55.0.12/drivers/message/fusion/mptctl.c
18689 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptctl.c  2007-12-21 11:40:54.000000000 +0100
18690 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptctl.c 2007-11-02 09:10:23.000000000 +0100
18691 @@ -4,8 +4,8 @@
18692   *      For use with LSI Logic PCI chip/adapters
18693   *      running LSI Logic Fusion MPT (Message Passing Technology) firmware.
18694   *
18695 - *  Copyright (c) 1999-2007 LSI Logic Corporation
18696 - *  (mailto:mpt_linux_developer@lsi.com)
18697 + *  Copyright (c) 1999-2005 LSI Logic Corporation
18698 + *  (mailto:mpt_linux_developer@lsil.com)
18699   *
18700   */
18701  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
18702 @@ -57,6 +57,9 @@
18703  #include <linux/miscdevice.h>
18704  #include <linux/smp_lock.h>
18705  #include <linux/compat.h>
18706 +#if defined(CPQ_CIM)
18707 +#include "csmisas.h"
18708 +#endif // CPQ_CIM
18709  
18710  #include <asm/io.h>
18711  #include <asm/uaccess.h>
18712 @@ -67,16 +70,11 @@
18713  #include <scsi/scsi_host.h>
18714  #include <scsi/scsi_tcq.h>
18715  
18716 -#define COPYRIGHT      "Copyright (c) 1999-2007 LSI Logic Corporation"
18717 +#define COPYRIGHT      "Copyright (c) 1999-2005 LSI Logic Corporation"
18718  #define MODULEAUTHOR   "LSI Logic Corporation"
18719  #include "mptbase.h"
18720  #include "mptctl.h"
18721  
18722 -#if defined(CPQ_CIM)
18723 -#include "mptsas.h"
18724 -#include "csmi/csmisas.h"
18725 -#endif // CPQ_CIM
18726 -
18727  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
18728  #define my_NAME                "Fusion MPT misc device (ioctl) driver"
18729  #define my_VERSION     MPT_LINUX_VERSION_COMMON
18730 @@ -85,12 +83,10 @@
18731  MODULE_AUTHOR(MODULEAUTHOR);
18732  MODULE_DESCRIPTION(my_NAME);
18733  MODULE_LICENSE("GPL");
18734 -MODULE_VERSION(my_VERSION);
18735  
18736  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
18737  
18738  extern int mpt_downloadboot(MPT_ADAPTER *ioc, MpiFwHeader_t *pFwHeader, int sleepFlag);
18739 -extern int     mpt_handshake_req_reply_wait(MPT_ADAPTER *ioc, int reqBytes, u32 *req, int replyBytes, u16 *u16reply, int maxwait, int sleepFlag);
18740  
18741  static int mptctl_id = -1;
18742  
18743 @@ -119,10 +115,6 @@ static int mptctl_eventenable(unsigned l
18744  static int mptctl_eventreport(unsigned long arg);
18745  static int mptctl_replace_fw(unsigned long arg);
18746  
18747 -#ifdef MPT_SUPPORT_FWDLB_IOCTL
18748 -static int mptctl_hba_pciinfo(unsigned long arg);
18749 -#endif
18750 -
18751  static int mptctl_do_reset(unsigned long arg);
18752  static int mptctl_hp_hostinfo(unsigned long arg, unsigned int cmd);
18753  static int mptctl_hp_targetinfo(unsigned long arg);
18754 @@ -133,29 +125,27 @@ static int mptctl_unregister_diag_buffer
18755  static int mptctl_query_diag_buffer(unsigned long arg);
18756  static int mptctl_read_diag_buffer(unsigned long arg);
18757  #if defined(CPQ_CIM)
18758 -static int csmisas_get_driver_info(unsigned long arg);
18759 -static int csmisas_get_cntlr_status(unsigned long arg);
18760 -static int csmisas_get_cntlr_config(unsigned long arg);
18761 -static int csmisas_get_phy_info(unsigned long arg);
18762 -static int csmisas_get_scsi_address(unsigned long arg);
18763 -static int csmisas_get_link_errors(unsigned long arg);
18764 -static int csmisas_smp_passthru(unsigned long arg);
18765 -static int csmisas_firmware_download(unsigned long arg);
18766 -static int csmisas_get_raid_info(unsigned long arg);
18767 -static int csmisas_get_raid_config(unsigned long arg);
18768 -static int csmisas_get_raid_features(unsigned long arg);
18769 -static int csmisas_set_raid_control(unsigned long arg);
18770 -static int csmisas_get_raid_element(unsigned long arg);
18771 -static int csmisas_set_raid_operation(unsigned long arg);
18772 -static int csmisas_set_phy_info(unsigned long arg);
18773 -static int csmisas_ssp_passthru(unsigned long arg);
18774 -static int csmisas_stp_passthru(unsigned long arg);
18775 -static int csmisas_get_sata_signature(unsigned long arg);
18776 -static int csmisas_get_device_address(unsigned long arg);
18777 -static int csmisas_task_managment(unsigned long arg);
18778 -static int csmisas_phy_control(unsigned long arg);
18779 -static int csmisas_get_connector_info(unsigned long arg);
18780 -static int csmisas_get_location(unsigned long arg);
18781 +static int mptctl_csmi_sas_get_driver_info(unsigned long arg);
18782 +static int mptctl_csmi_sas_get_cntlr_status(unsigned long arg);
18783 +static int mptctl_csmi_sas_get_cntlr_config(unsigned long arg);
18784 +static int mptctl_csmi_sas_get_phy_info(unsigned long arg);
18785 +static int mptctl_csmi_sas_get_scsi_address(unsigned long arg);
18786 +static int mptctl_csmi_sas_get_link_errors(unsigned long arg);
18787 +static int mptctl_csmi_sas_smp_passthru(unsigned long arg);
18788 +static int mptctl_csmi_sas_firmware_download(unsigned long arg);
18789 +static int mptctl_csmi_sas_get_raid_info(unsigned long arg);
18790 +static int mptctl_csmi_sas_get_raid_config(unsigned long arg);
18791 +static int mptctl_csmi_sas_get_raid_features(unsigned long arg);
18792 +static int mptctl_csmi_sas_get_raid_control(unsigned long arg);
18793 +static int mptctl_csmi_sas_set_phy_info(unsigned long arg);
18794 +static int mptctl_csmi_sas_ssp_passthru(unsigned long arg);
18795 +static int mptctl_csmi_sas_stp_passthru(unsigned long arg);
18796 +static int mptctl_csmi_sas_get_sata_signature(unsigned long arg);
18797 +static int mptctl_csmi_sas_get_device_address(unsigned long arg);
18798 +static int mptctl_csmi_sas_task_managment(unsigned long arg);
18799 +static int mptctl_csmi_sas_phy_control(unsigned long arg);
18800 +static int mptctl_csmi_sas_get_connector_info(unsigned long arg);
18801 +static int mptctl_csmi_sas_get_location(unsigned long arg);
18802  #endif // CPQ_CIM
18803  
18804  static int  mptctl_probe(struct pci_dev *, const struct pci_device_id *);
18805 @@ -230,7 +220,7 @@ static inline int
18806  mptctl_syscall_down(MPT_ADAPTER *ioc, int nonblock)
18807  {
18808         int rc = 0;
18809 -       dctlprintk((KERN_INFO MYNAM ": mptctl_syscall_down(%p,%d) called\n", ioc, nonblock));
18810 +       dctlprintk((KERN_INFO MYNAM "::mptctl_syscall_down(%p,%d) called\n", ioc, nonblock));
18811  
18812         if (nonblock) {
18813                 if (down_trylock(&ioc->ioctl->sem_ioc))
18814 @@ -239,7 +229,7 @@ mptctl_syscall_down(MPT_ADAPTER *ioc, in
18815                 if (down_interruptible(&ioc->ioctl->sem_ioc))
18816                         rc = -ERESTARTSYS;
18817         }
18818 -       dctlprintk((KERN_INFO MYNAM ": mptctl_syscall_down return %d\n", rc));
18819 +       dctlprintk((KERN_INFO MYNAM "::mptctl_syscall_down return %d\n", rc));
18820         return rc;
18821  }
18822  
18823 @@ -304,17 +294,9 @@ mptctl_reply(MPT_ADAPTER *ioc, MPT_FRAME
18824  
18825                 if ((cmd == MPI_FUNCTION_SCSI_IO_REQUEST) ||
18826                         (cmd == MPI_FUNCTION_RAID_SCSI_IO_PASSTHROUGH)) {
18827 -
18828 -                       dcsmisasprintk(("\tiocstatus = 0x%x, "
18829 -                               "scsi_status = 0x%x, scsi_state = 0x%x\n",
18830 -                               reply->u.sreply.IOCStatus,
18831 -                               reply->u.sreply.SCSIStatus,
18832 -                               reply->u.sreply.SCSIState));
18833 -
18834                         ioc->ioctl->reset &= ~MPTCTL_RESET_OK;
18835  
18836                         if ((iocStatus == MPI_IOCSTATUS_SCSI_DATA_UNDERRUN) ||
18837 -                                (iocStatus == MPI_IOCSTATUS_SCSI_RESIDUAL_MISMATCH) ||
18838                                 (iocStatus == MPI_IOCSTATUS_SCSI_RECOVERED_ERROR)) {
18839                                 ioc->ioctl->status |= MPT_IOCTL_STATUS_COMMAND_GOOD;
18840                         }
18841 @@ -438,8 +420,8 @@ mptctl_bus_reset(MPT_IOCTL *ioctl)
18842                         ioctl->ioc->name, mf));
18843  
18844         pScsiTm = (SCSITaskMgmt_t *) mf;
18845 -       pScsiTm->TargetID = ioctl->id;
18846 -       pScsiTm->Bus = ioctl->bus;
18847 +       pScsiTm->TargetID = ioctl->target;
18848 +       pScsiTm->Bus = hd->port;        /* 0 */
18849         pScsiTm->ChainOffset = 0;
18850         pScsiTm->Function = MPI_FUNCTION_SCSI_TASK_MGMT;
18851         pScsiTm->Reserved = 0;
18852 @@ -460,7 +442,7 @@ mptctl_bus_reset(MPT_IOCTL *ioctl)
18853  
18854         ioctl->wait_done=0;
18855         if ((retval = mpt_send_handshake_request(mptctl_id, ioctl->ioc,
18856 -           sizeof(SCSITaskMgmt_t), (u32*)pScsiTm,10, CAN_SLEEP)) != 0) {
18857 +            sizeof(SCSITaskMgmt_t), (u32*)pScsiTm, CAN_SLEEP)) != 0) {
18858                 dfailprintk((MYIOC_s_ERR_FMT "_send_handshake FAILED!"
18859                         " (hd %p, ioc %p, mf %p) \n", hd->ioc->name, hd,
18860                         hd->ioc, mf));
18861 @@ -652,7 +634,7 @@ __mptctl_ioctl(struct file *file, unsign
18862         dctlprintk(("mptctl_ioctl() called with cmd=%x\n", cmd));
18863  
18864         if (copy_from_user(&khdr, uhdr, sizeof(khdr))) {
18865 -               printk(KERN_ERR "%s: mptctl_ioctl() @%d - "
18866 +               printk(KERN_ERR "%s::mptctl_ioctl() @%d - "
18867                                 "Unable to copy mpt_ioctl_header data @ %p\n",
18868                                 __FILE__, __LINE__, uhdr);
18869                 return -EFAULT;
18870 @@ -693,38 +675,28 @@ __mptctl_ioctl(struct file *file, unsign
18871                 return mptctl_query_diag_buffer(arg);
18872         } else if (cmd == MPTDIAGUNREGISTER) {
18873                 return mptctl_unregister_diag_buffer(arg);
18874 -
18875 -       }
18876 -#ifdef MPT_SUPPORT_FWDLB_IOCTL
18877 -        else if (cmd == MPTHBAPCIINFO) {
18878 -               return mptctl_hba_pciinfo(arg);
18879         }
18880 -#endif
18881  
18882  #if defined(CPQ_CIM)
18883         else if (cmd == CC_CSMI_SAS_GET_DRIVER_INFO) {
18884 -               return csmisas_get_driver_info(arg);
18885 +               return mptctl_csmi_sas_get_driver_info(arg);
18886         } else if (cmd == CC_CSMI_SAS_GET_CNTLR_CONFIG) {
18887 -               return csmisas_get_cntlr_config(arg);
18888 +               return mptctl_csmi_sas_get_cntlr_config(arg);
18889         } else if (cmd == CC_CSMI_SAS_GET_CNTLR_STATUS) {
18890 -               return csmisas_get_cntlr_status(arg);
18891 +               return mptctl_csmi_sas_get_cntlr_status(arg);
18892         } else if (cmd == CC_CSMI_SAS_GET_SCSI_ADDRESS) {
18893 -               return csmisas_get_scsi_address(arg);
18894 +               return mptctl_csmi_sas_get_scsi_address(arg);
18895         } else if (cmd == CC_CSMI_SAS_GET_DEVICE_ADDRESS){
18896 -               return csmisas_get_device_address(arg);
18897 +               return mptctl_csmi_sas_get_device_address(arg);
18898         }
18899  #endif // CPQ_CIM
18900  
18901 -       dctlprintk(("mptctl_ioctl() called with cmd=%x, interrupt required\n", cmd));
18902         /* All of these commands require an interrupt or
18903          * are unknown/illegal.
18904          */
18905 -       if ((ret = mptctl_syscall_down(iocp, nonblock)) != 0) {
18906 -               dctlprintk(("mptctl_ioctl() called with cmd=%x ret=%d, syscall_down failed\n", cmd, ret));
18907 +       if ((ret = mptctl_syscall_down(iocp, nonblock)) != 0)
18908                 return ret;
18909 -       }
18910  
18911 -       dctlprintk(("mptctl_ioctl() called with cmd=%x, syscall_down completed\n", cmd));
18912         if (cmd == MPTFWDOWNLOAD)
18913                 ret = mptctl_fw_download(arg);
18914         else if (cmd == MPTFWDOWNLOADBOOT)
18915 @@ -745,41 +717,37 @@ __mptctl_ioctl(struct file *file, unsign
18916                 ret = mptctl_read_diag_buffer(arg);
18917  #if defined(CPQ_CIM)
18918         else if (cmd == CC_CSMI_SAS_GET_PHY_INFO)
18919 -               ret = csmisas_get_phy_info(arg);
18920 +               ret = mptctl_csmi_sas_get_phy_info(arg);
18921         else if (cmd == CC_CSMI_SAS_GET_SATA_SIGNATURE)
18922 -               ret = csmisas_get_sata_signature(arg);
18923 +               ret = mptctl_csmi_sas_get_sata_signature(arg);
18924         else if (cmd == CC_CSMI_SAS_GET_LINK_ERRORS)
18925 -               ret = csmisas_get_link_errors(arg);
18926 +               ret = mptctl_csmi_sas_get_link_errors(arg);
18927         else if (cmd == CC_CSMI_SAS_SMP_PASSTHRU)
18928 -               ret = csmisas_smp_passthru(arg);
18929 +               ret = mptctl_csmi_sas_smp_passthru(arg);
18930         else if (cmd == CC_CSMI_SAS_SSP_PASSTHRU)
18931 -               ret = csmisas_ssp_passthru(arg);
18932 +               ret = mptctl_csmi_sas_ssp_passthru(arg);
18933         else if (cmd == CC_CSMI_SAS_FIRMWARE_DOWNLOAD)
18934 -               ret = csmisas_firmware_download(arg);
18935 +               ret = mptctl_csmi_sas_firmware_download(arg);
18936         else if (cmd == CC_CSMI_SAS_GET_RAID_INFO)
18937 -               ret = csmisas_get_raid_info(arg);
18938 +               ret = mptctl_csmi_sas_get_raid_info(arg);
18939         else if (cmd == CC_CSMI_SAS_GET_RAID_CONFIG)
18940 -               ret = csmisas_get_raid_config(arg);
18941 -       else if (cmd == CC_CSMI_SAS_GET_RAID_FEATURES)
18942 -               ret = csmisas_get_raid_features(arg);
18943 -       else if (cmd == CC_CSMI_SAS_SET_RAID_CONTROL)
18944 -               ret = csmisas_set_raid_control(arg);
18945 -       else if (cmd == CC_CSMI_SAS_GET_RAID_ELEMENT)
18946 -               ret = csmisas_get_raid_element(arg);
18947 -       else if (cmd == CC_CSMI_SAS_SET_RAID_OPERATION)
18948 -               ret = csmisas_set_raid_operation(arg);
18949 +               ret = mptctl_csmi_sas_get_raid_config(arg);
18950 +    else if (cmd == CC_CSMI_SAS_GET_RAID_FEATURES)
18951 +               ret = mptctl_csmi_sas_get_raid_features(arg);
18952 +    else if (cmd == CC_CSMI_SAS_SET_RAID_CONTROL)
18953 +               ret = mptctl_csmi_sas_get_raid_control(arg);
18954         else if (cmd == CC_CSMI_SAS_SET_PHY_INFO)
18955 -               ret = csmisas_set_phy_info(arg);
18956 +               ret = mptctl_csmi_sas_set_phy_info(arg);
18957         else if (cmd == CC_CSMI_SAS_STP_PASSTHRU)
18958 -               ret = csmisas_stp_passthru(arg);
18959 +               ret = mptctl_csmi_sas_stp_passthru(arg);
18960         else if (cmd == CC_CSMI_SAS_TASK_MANAGEMENT)
18961 -               ret = csmisas_task_managment(arg);
18962 +               ret = mptctl_csmi_sas_task_managment(arg);
18963         else if (cmd == CC_CSMI_SAS_PHY_CONTROL)
18964 -               ret = csmisas_phy_control(arg);
18965 +               ret = mptctl_csmi_sas_phy_control(arg);
18966         else if (cmd == CC_CSMI_SAS_GET_CONNECTOR_INFO)
18967 -               ret = csmisas_get_connector_info(arg);
18968 +               ret = mptctl_csmi_sas_get_connector_info(arg);
18969         else if (cmd == CC_CSMI_SAS_GET_LOCATION)
18970 -               ret = csmisas_get_location(arg);
18971 +               ret = mptctl_csmi_sas_get_location(arg);
18972  #endif // CPQ_CIM
18973         else {
18974                 dctlprintk(("mptctl_ioctl() cmd=%x not found\n", cmd));
18975 @@ -788,7 +756,6 @@ __mptctl_ioctl(struct file *file, unsign
18976  
18977         up(&iocp->ioctl->sem_ioc);
18978  
18979 -       dctlprintk(("mptctl_ioctl() called with cmd=%x ret=%d, up completed\n", cmd, ret));
18980         return ret;
18981  }
18982  
18983 @@ -813,7 +780,7 @@ static int mptctl_do_reset(unsigned long
18984         dctlprintk(("mptctl_do_reset called.\n"));
18985  
18986         if (copy_from_user(&krinfo, urinfo, sizeof(struct mpt_ioctl_diag_reset))) {
18987 -               printk(KERN_ERR "%s@%d: mptctl_do_reset - "
18988 +               printk(KERN_ERR "%s@%d::mptctl_do_reset - "
18989                                 "Unable to copy mpt_ioctl_diag_reset struct @ %p\n",
18990                                 __FILE__, __LINE__, urinfo);
18991                 return -EFAULT;
18992 @@ -858,7 +825,7 @@ mptctl_fw_download(unsigned long arg)
18993  
18994         dctlprintk(("mptctl_fwdl called. mptctl_id = %xh\n", mptctl_id)); //tc
18995         if (copy_from_user(&kfwdl, ufwdl, sizeof(struct mpt_fw_xfer))) {
18996 -               printk(KERN_ERR "%s@%d: _ioctl_fwdl - "
18997 +               printk(KERN_ERR "%s@%d::_ioctl_fwdl - "
18998                                 "Unable to copy mpt_fw_xfer struct @ %p\n",
18999                                 __FILE__, __LINE__, ufwdl);
19000                 return -EFAULT;
19001 @@ -1014,7 +981,7 @@ mptctl_do_fw_download(int ioc, char __us
19002                         mpt_add_sge(sgOut, sgIn->FlagsLength, sgIn->Address);
19003                         n++;
19004                         if (copy_from_user(bl->kptr, ufwbuf+fw_bytes_copied, bl->len)) {
19005 -                               printk(KERN_ERR "%s@%d: _ioctl_fwdl - "
19006 +                               printk(KERN_ERR "%s@%d::_ioctl_fwdl - "
19007                                                 "Unable to copy f/w buffer hunk#%d @ %p\n",
19008                                                 __FILE__, __LINE__, n, ufwbuf);
19009                                 goto fwdl_out;
19010 @@ -1040,9 +1007,6 @@ mptctl_do_fw_download(int ioc, char __us
19011          * Finally, perform firmware download.
19012          */
19013         ReplyMsg = NULL;
19014 -       iocp->ioctl->wait_done = 0;
19015 -       INITIALIZE_IOCTL_STATUS(iocp->ioctl->status)
19016 -
19017         mpt_put_msg_frame(mptctl_id, iocp, mf);
19018  
19019         /* Now wait for the command to complete */
19020 @@ -1075,7 +1039,7 @@ mptctl_do_fw_download(int ioc, char __us
19021                 printk(KERN_WARNING MYNAM ": (try again later?)\n");
19022                 return -EBUSY;
19023         } else {
19024 -               printk(KERN_WARNING MYNAM ": ioctl_fwdl() ERROR!  %s returned [bad] status = %04xh\n",
19025 +               printk(KERN_WARNING MYNAM "::ioctl_fwdl() ERROR!  %s returned [bad] status = %04xh\n",
19026                                     iocp->name, iocstat);
19027                 printk(KERN_WARNING MYNAM ": (bad VooDoo)\n");
19028                 return -ENOMSG;
19029 @@ -1111,7 +1075,7 @@ mptctl_fw_downloadboot(unsigned long arg
19030  
19031         dctlprintk(("mptctl_fwdlboot called. mptctl_id = %xh\n", mptctl_id)); //tc
19032         if (copy_from_user(&kfwdl, ufwdl, sizeof(struct mpt_fw_xfer))) {
19033 -               printk(KERN_ERR "%s@%d: _ioctl_fwdl - "
19034 +               printk(KERN_ERR "%s@%d::_ioctl_fwdl - "
19035                                 "Unable to copy mpt_fw_xfer struct @ %p\n",
19036                                 __FILE__, __LINE__, ufwdl);
19037                 return -EFAULT;
19038 @@ -1149,20 +1113,11 @@ mptctl_do_fw_downloadboot(int ioc_num, c
19039                 return -ENODEV; /* (-6) No such device or address */
19040         }
19041  
19042 -       pbuf = (char *)__get_free_pages(GFP_KERNEL, get_order(fwlen));
19043 -       if (pbuf==NULL) {
19044 -               printk(KERN_ERR "%s@%d: _ioctl_fwdlboot - "
19045 -                               "Unable to allocate memory\n",
19046 -                               __FILE__, __LINE__);
19047 -               return -ENOMEM;
19048 -       }
19049 -
19050 -
19051 -if (copy_from_user(pbuf, ufwbuf, fwlen)) {
19052 -               printk(KERN_ERR "%s@%d: _ioctl_fwdlboot - "
19053 +       pbuf = kmalloc(fwlen, GFP_KERNEL);
19054 +       if (copy_from_user(pbuf, ufwbuf, fwlen)) {
19055 +               printk(KERN_ERR "%s@%d::_ioctl_fwdlboot - "
19056                                 "Unable to copy mpt_fw @ %p\n",
19057                                 __FILE__, __LINE__, (void*)ufwbuf);
19058 -free_pages((unsigned long)pbuf, get_order(fwlen));
19059                 return -EFAULT;
19060         }
19061  
19062 @@ -1171,10 +1126,7 @@ free_pages((unsigned long)pbuf, get_orde
19063  
19064         rc = mpt_downloadboot(ioc, (MpiFwHeader_t *)pbuf, CAN_SLEEP);
19065         ddlprintk((MYIOC_s_INFO_FMT "mptctl_do_fw_downloadboot rc=%x\n",
19066 -
19067                                 ioc->name, rc));
19068 -#if 0
19069 -
19070         if ( (rc == 0) && (ioc->bus_type == SAS) ) {
19071  /*             if ((rc = mptctl_syscall_down(ioc, nonblock)) != 0)
19072                         return rc; */
19073 @@ -1194,12 +1146,10 @@ free_pages((unsigned long)pbuf, get_orde
19074                         ioc->name));
19075                 } */
19076         }
19077 -#endif
19078 -free_pages((unsigned long)pbuf, get_order(fwlen));
19079 +       kfree(pbuf);
19080         return rc;
19081  }
19082  
19083 -
19084  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
19085  /*
19086   * SGE Allocation routine
19087 @@ -1278,9 +1228,9 @@ kbuf_alloc_2_sgl(int bytes, u32 sgdir, i
19088                 if (buflist[buflist_ent].kptr == NULL) {
19089                         alloc_sz = alloc_sz / 2;
19090                         if (alloc_sz == 0) {
19091 -                               printk(KERN_WARNING MYNAM ": -SG: No can do - "
19092 +                               printk(KERN_WARNING MYNAM "-SG: No can do - "
19093                                                     "not enough memory!   :-(\n");
19094 -                               printk(KERN_WARNING MYNAM ": -SG: (freeing %d frags)\n",
19095 +                               printk(KERN_WARNING MYNAM "-SG: (freeing %d frags)\n",
19096                                                     numfrags);
19097                                 goto free_and_fail;
19098                         }
19099 @@ -1304,17 +1254,17 @@ kbuf_alloc_2_sgl(int bytes, u32 sgdir, i
19100  
19101                 /* Need to chain? */
19102                 if (fragcnt == sg_spill) {
19103 -                       printk(KERN_WARNING MYNAM ": -SG: No can do - " "Chain required!   :-(\n");
19104 -                       printk(KERN_WARNING MYNAM ": (freeing %d frags)\n", numfrags);
19105 +                       printk(KERN_WARNING MYNAM "-SG: No can do - " "Chain required!   :-(\n");
19106 +                       printk(KERN_WARNING MYNAM "(freeing %d frags)\n", numfrags);
19107                         goto free_and_fail;
19108                 }
19109  
19110                 /* overflow check... */
19111                 if (numfrags*8 > MAX_SGL_BYTES){
19112                         /* GRRRRR... */
19113 -                       printk(KERN_WARNING MYNAM ": -SG: No can do - "
19114 +                       printk(KERN_WARNING MYNAM "-SG: No can do - "
19115                                             "too many SG frags!   :-(\n");
19116 -                       printk(KERN_WARNING MYNAM ": -SG: (freeing %d frags)\n",
19117 +                       printk(KERN_WARNING MYNAM "-SG: (freeing %d frags)\n",
19118                                             numfrags);
19119                         goto free_and_fail;
19120                 }
19121 @@ -1435,16 +1385,18 @@ mptctl_getiocinfo (unsigned long arg, un
19122         struct mpt_ioctl_iocinfo __user *uarg = (void __user *) arg;
19123         struct mpt_ioctl_iocinfo *karg;
19124         MPT_ADAPTER             *ioc;
19125 -       struct _MPT_DEVICE      *pMptTarget;
19126 -       VirtDevice              *pTarget;
19127         struct pci_dev          *pdev;
19128 +       struct Scsi_Host        *sh;
19129 +       MPT_SCSI_HOST           *hd;
19130         int                     iocnum;
19131         int                     numDevices = 0;
19132 -       int                     id, bus;
19133 +       unsigned int            max_id;
19134 +       int                     ii;
19135         unsigned int            port;
19136         int                     cim_rev;
19137         u8                      revision;
19138  
19139 +       dctlprintk(("mptctl_getiocinfo called.\n"));
19140         /* Add of PCI INFO results in unaligned access for
19141          * IA64 and Sparc. Reset long to int. Return no PCI
19142          * data for obsolete format.
19143 @@ -1457,20 +1409,18 @@ mptctl_getiocinfo (unsigned long arg, un
19144                 cim_rev = 2;
19145         else if (data_size == (sizeof(struct mpt_ioctl_iocinfo_rev0)+12))
19146                 cim_rev = 0;    /* obsolete */
19147 -       else {
19148 -               dctlprintk(("mptctl_getiocinfo called.i Invalid data_size=%d\n", data_size));
19149 +       else
19150                 return -EFAULT;
19151 -       }
19152  
19153         karg = kmalloc(data_size, GFP_KERNEL);
19154         if (karg == NULL) {
19155 -               printk(KERN_ERR "%s: mpt_ioctl_iocinfo() @%d - no memory available!\n",
19156 +               printk(KERN_ERR "%s::mpt_ioctl_iocinfo() @%d - no memory available!\n",
19157                                 __FILE__, __LINE__);
19158                 return -ENOMEM;
19159         }
19160  
19161         if (copy_from_user(karg, uarg, data_size)) {
19162 -               printk(KERN_ERR "%s@%d: mptctl_getiocinfo - "
19163 +               printk(KERN_ERR "%s@%d::mptctl_getiocinfo - "
19164                         "Unable to read in mpt_ioctl_iocinfo struct @ %p\n",
19165                                 __FILE__, __LINE__, (void*)uarg);
19166                 kfree(karg);
19167 @@ -1484,11 +1434,10 @@ mptctl_getiocinfo (unsigned long arg, un
19168                 kfree(karg);
19169                 return -ENODEV;
19170         }
19171 -       dctlprintk(("ioc%d: mptctl_getiocinfo called.\n", iocnum));
19172  
19173         /* Verify the data transfer size is correct. */
19174         if (karg->hdr.maxDataSize != data_size) {
19175 -               printk(KERN_ERR "%s@%d: mptctl_getiocinfo - "
19176 +               printk(KERN_ERR "%s@%d::mptctl_getiocinfo - "
19177                         "Structure size mismatch. Command not completed.\n",
19178                                 __FILE__, __LINE__);
19179                 kfree(karg);
19180 @@ -1535,11 +1484,18 @@ mptctl_getiocinfo (unsigned long arg, un
19181  
19182         /* Get number of devices
19183           */
19184 -       for (bus = 0; bus < ioc->NumberOfBuses; bus++) {
19185 -               if ((pMptTarget = ioc->Target_List[bus])) {
19186 -                       for (id = 0; id < ioc->DevicesPerBus; id++) {
19187 -                               pTarget = pMptTarget->Target[id];
19188 -                               if (pTarget)
19189 +       if ((sh = ioc->sh) != NULL) {
19190 +                /* sh->max_id = maximum target ID + 1
19191 +                */
19192 +               max_id = sh->max_id - 1;
19193 +               hd = (MPT_SCSI_HOST *) sh->hostdata;
19194 +
19195 +               /* Check all of the target structures and
19196 +                * keep a counter.
19197 +                */
19198 +               if (hd && hd->Targets) {
19199 +                       for (ii = 0; ii <= max_id; ii++) {
19200 +                               if (hd->Targets[ii])
19201                                         numDevices++;
19202                         }
19203                 }
19204 @@ -1563,7 +1519,7 @@ mptctl_getiocinfo (unsigned long arg, un
19205         /* Copy the data from kernel memory to user memory
19206          */
19207         if (copy_to_user((char __user *)arg, karg, data_size)) {
19208 -               printk(KERN_ERR "%s@%d: mptctl_getiocinfo - "
19209 +               printk(KERN_ERR "%s@%d::mptctl_getiocinfo - "
19210                         "Unable to write out mpt_ioctl_iocinfo struct @ %p\n",
19211                                 __FILE__, __LINE__, uarg);
19212                 kfree(karg);
19213 @@ -1590,22 +1546,25 @@ mptctl_gettargetinfo (unsigned long arg)
19214         struct mpt_ioctl_targetinfo __user *uarg = (void __user *) arg;
19215         struct mpt_ioctl_targetinfo karg;
19216         MPT_ADAPTER             *ioc;
19217 -       struct _MPT_DEVICE      *pMptTarget;
19218 -       VirtDevice              *pTarget;
19219 +       struct Scsi_Host        *sh;
19220 +       MPT_SCSI_HOST           *hd;
19221 +       VirtDevice              *vdev;
19222         char                    *pmem;
19223         int                     *pdata;
19224         IOCPage2_t              *pIoc2;
19225         IOCPage3_t              *pIoc3;
19226         int                     iocnum;
19227         int                     numDevices = 0;
19228 +       unsigned int            max_id;
19229         int                     id, jj, indexed_lun, lun_index;
19230         u32                     lun;
19231         int                     maxWordsLeft;
19232         int                     numBytes;
19233 -       u8                      port, devType, bus;
19234 +       u8                      port, devType, bus_id;
19235  
19236 +       dctlprintk(("mptctl_gettargetinfo called.\n"));
19237         if (copy_from_user(&karg, uarg, sizeof(struct mpt_ioctl_targetinfo))) {
19238 -               printk(KERN_ERR "%s@%d: mptctl_gettargetinfo - "
19239 +               printk(KERN_ERR "%s@%d::mptctl_gettargetinfo - "
19240                         "Unable to read in mpt_ioctl_targetinfo struct @ %p\n",
19241                                 __FILE__, __LINE__, uarg);
19242                 return -EFAULT;
19243 @@ -1618,7 +1577,6 @@ mptctl_gettargetinfo (unsigned long arg)
19244                 return -ENODEV;
19245         }
19246  
19247 -       dctlprintk(("ioc%ds: mptctl_gettargetinfo called.\n", iocnum));
19248         /* Get the port number and set the maximum number of bytes
19249          * in the returned structure.
19250          * Ignore the port setting.
19251 @@ -1628,7 +1586,7 @@ mptctl_gettargetinfo (unsigned long arg)
19252         port = karg.hdr.port;
19253  
19254         if (maxWordsLeft <= 0) {
19255 -               printk(KERN_ERR "%s: mptctl_gettargetinfo() @%d - no memory available!\n",
19256 +               printk(KERN_ERR "%s::mptctl_gettargetinfo() @%d - no memory available!\n",
19257                                 __FILE__, __LINE__);
19258                 return -ENOMEM;
19259         }
19260 @@ -1649,7 +1607,7 @@ mptctl_gettargetinfo (unsigned long arg)
19261          */
19262         pmem = kmalloc(numBytes, GFP_KERNEL);
19263         if (pmem == NULL) {
19264 -               printk(KERN_ERR "%s: mptctl_gettargetinfo() @%d - no memory available!\n",
19265 +               printk(KERN_ERR "%s::mptctl_gettargetinfo() @%d - no memory available!\n",
19266                                 __FILE__, __LINE__);
19267                 return -ENOMEM;
19268         }
19269 @@ -1658,68 +1616,71 @@ mptctl_gettargetinfo (unsigned long arg)
19270  
19271         /* Get number of devices
19272           */
19273 -       /* Check all of the target structures.
19274 -        * Save the Id and increment the counter,
19275 -        * if ptr non-null.
19276 -        */
19277 -       mpt_findImVolumes(ioc);
19278 -       pIoc2 = ioc->raid_data.pIocPg2;
19279 -       for (bus = 0; bus < ioc->NumberOfBuses; bus++) {
19280 -               for ( id = 0; id < ioc->DevicesPerBus; ) {
19281 -                       if ( pIoc2 && pIoc2->NumActiveVolumes ) {
19282 -                               if ( id == pIoc2->RaidVolume[0].VolumeID ) {
19283 -                                       if (maxWordsLeft <= 0) {
19284 -                                               printk(KERN_ERR "mptctl_gettargetinfo - "
19285 -               "buffer is full but volume is available on ioc %d\n, numDevices=%d", iocnum, numDevices);
19286 -                                               goto data_space_full;
19287 -                                       }
19288 -                                       if ( ( pIoc2->RaidVolume[0].Flags & MPI_IOCPAGE2_FLAG_VOLUME_INACTIVE ) == 0 )
19289 -                                               devType = 0x80;
19290 -                                       else
19291 -                                               devType = 0xC0;
19292 -                                       if ( bus == pIoc2->RaidVolume[0].VolumeBus) {
19293 -                                               numDevices++;
19294 -                                               *pdata = ( (devType << 24) | (bus<< 8) | id );
19295 +       if ((sh = ioc->sh) != NULL) {
19296 +
19297 +               max_id = sh->max_id - 1;
19298 +               hd = (MPT_SCSI_HOST *) sh->hostdata;
19299 +
19300 +               /* Check all of the target structures.
19301 +                * Save the Id and increment the counter,
19302 +                * if ptr non-null.
19303 +                * sh->max_id = maximum target ID + 1
19304 +                */
19305 +               if (hd && hd->Targets) {
19306 +                       mpt_findImVolumes(ioc);
19307 +                       pIoc2 = ioc->raid_data.pIocPg2;
19308 +                       for ( id = 0; id <= max_id; ) {
19309 +                               if ( pIoc2 && pIoc2->NumActiveVolumes ) {
19310 +                                       if ( id == pIoc2->RaidVolume[0].VolumeID ) {
19311 +                                               if (maxWordsLeft <= 0) {
19312 +                                                       printk(KERN_ERR "mptctl_gettargetinfo - "
19313 +                       "buffer is full but volume is available on ioc %d\n, numDevices=%d", iocnum, numDevices);
19314 +                                                       goto data_space_full;
19315 +                                               }
19316 +                                               if ( ( pIoc2->RaidVolume[0].Flags & MPI_IOCPAGE2_FLAG_VOLUME_INACTIVE ) == 0 )
19317 +                                                       devType = 0x80;
19318 +                                               else
19319 +                                                       devType = 0xC0;
19320 +                                               bus_id = pIoc2->RaidVolume[0].VolumeBus;
19321 +                                               numDevices++;
19322 +                                               *pdata = ( (devType << 24) | (bus_id << 8) | id );
19323                                                 dctlprintk((KERN_ERR "mptctl_gettargetinfo - "
19324                 "volume ioc=%d target=%x numDevices=%d pdata=%p\n", iocnum, *pdata, numDevices, pdata));
19325 -                                               pdata++;
19326 +                                               pdata++;
19327                                                 --maxWordsLeft;
19328                                                 goto next_id;
19329 -                                       }
19330 -                               } else {
19331 -                                       pIoc3 = ioc->raid_data.pIocPg3;
19332 -                                       for ( jj = 0; jj < pIoc3->NumPhysDisks; jj++ ) {
19333 -                                               if ((pIoc3->PhysDisk[jj].PhysDiskID == id) && (pIoc3->PhysDisk[jj].PhysDiskBus == bus))
19334 -                                                       goto next_id;
19335 +                                       } else {
19336 +                                               pIoc3 = ioc->raid_data.pIocPg3;
19337 +                                               for ( jj = 0; jj < pIoc3->NumPhysDisks; jj++ ) {
19338 +                                                       if ( pIoc3->PhysDisk[jj].PhysDiskID == id )
19339 +                                                               goto next_id;
19340 +                                               }
19341                                         }
19342                                 }
19343 -                       }
19344 -                       if ((pMptTarget = ioc->Target_List[bus])) {
19345 -                               pTarget = pMptTarget->Target[id];
19346 -                               if (pTarget) {
19347 +                               if ( (vdev = hd->Targets[id]) ) {
19348                                         for (jj = 0; jj <= MPT_LAST_LUN; jj++) {
19349                                                 lun_index = (jj >> 5);
19350                                                 indexed_lun = (jj % 32);
19351                                                 lun = (1 << indexed_lun);
19352 -                                               if (pTarget->luns[lun_index] & lun) {
19353 +                                               if (vdev->luns[lun_index] & lun) {
19354                                                         if (maxWordsLeft <= 0) {
19355                                                                 printk(KERN_ERR "mptctl_gettargetinfo - "
19356 -                               "buffer is full but more targets are available on ioc %d numDevices=%d\n", iocnum, numDevices);
19357 +                       "buffer is full but more targets are available on ioc %d numDevices=%d\n", iocnum, numDevices);
19358                                                                 goto data_space_full;
19359                                                         }
19360 -                                                       bus = pTarget->bus;
19361 +                                                       bus_id = vdev->bus_id;
19362                                                         numDevices++;
19363 -                                                       *pdata = ( (jj << 16) | (bus << 8) | id );
19364 +                                                       *pdata = ( (jj << 16) | (bus_id << 8) | id );
19365                                                         dctlprintk((KERN_ERR "mptctl_gettargetinfo - "
19366 -                       "target ioc=%d target=%x numDevices=%d pdata=%p\n", iocnum, *pdata, numDevices, pdata));
19367 +               "target ioc=%d target=%x numDevices=%d pdata=%p\n", iocnum, *pdata, numDevices, pdata));
19368                                                         pdata++;
19369                                                         --maxWordsLeft;
19370                                                 }
19371                                         }
19372                                 }
19373 -                       }
19374  next_id:
19375 -                       id++;
19376 +                               id++;
19377 +                       }
19378                 }
19379         }
19380  data_space_full:
19381 @@ -1729,7 +1690,7 @@ data_space_full:
19382          */
19383         if (copy_to_user((char __user *)arg, &karg,
19384                                 sizeof(struct mpt_ioctl_targetinfo))) {
19385 -               printk(KERN_ERR "%s@%d: mptctl_gettargetinfo - "
19386 +               printk(KERN_ERR "%s@%d::mptctl_gettargetinfo - "
19387                         "Unable to write out mpt_ioctl_targetinfo struct @ %p\n",
19388                                 __FILE__, __LINE__, uarg);
19389                 kfree(pmem);
19390 @@ -1739,7 +1700,7 @@ data_space_full:
19391         /* Copy the remaining data from kernel memory to user memory
19392          */
19393         if (copy_to_user(uarg->targetInfo, pmem, numBytes)) {
19394 -               printk(KERN_ERR "%s@%d: mptctl_gettargetinfo - "
19395 +               printk(KERN_ERR "%s@%d::mptctl_gettargetinfo - "
19396                         "Unable to write out mpt_ioctl_targetinfo struct @ %p\n",
19397                                 __FILE__, __LINE__, pdata);
19398                 kfree(pmem);
19399 @@ -1751,70 +1712,6 @@ data_space_full:
19400         return 0;
19401  }
19402  
19403 -#ifdef MPT_SUPPORT_FWDLB_IOCTL
19404 -/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
19405 -/*
19406 - *     mptctl_hba_pciinfo - Obtain all mpt HBAs pci (Config Space) information.
19407 - *     @arg: User space argument
19408 - *
19409 - * Outputs:    None.
19410 - * Return:     0 if successful
19411 - *             -EFAULT if data unavailable
19412 - */
19413 -static int
19414 -mptctl_hba_pciinfo (unsigned long arg)
19415 -{
19416 -       struct mpt_ioctl_hbapciinfo *uarg = (struct mpt_ioctl_hbapciinfo *) arg;
19417 -       struct mpt_ioctl_hbapciinfo karg;
19418 -
19419 -       MPT_ADAPTER     *ioc;
19420 -       int             ioc_num=0, data_size;
19421 -       u8                      revision;
19422 -
19423 -       data_size = sizeof(mpt_ioctl_header)+4;
19424 -       /* Clear the struct before filling in data. */
19425 -       memset( &karg, 0, (uarg->hdr.maxDataSize + data_size) );
19426 -
19427 -       dctlprintk((KERN_INFO MYNAM ": Checking for MPT adapters...maxDataSize=%d data_size=%d\n", uarg->hdr.maxDataSize, data_size));
19428 -
19429 -       list_for_each_entry(ioc,&ioc_list,list) {
19430 -               data_size += sizeof (struct mpt_ioctl_mptpciinfo);
19431 -               if ( data_size >= uarg->hdr.maxDataSize ) {
19432 -                       dctlprintk((KERN_INFO MYNAM ": data_size=%d >= maxDataSize=%d\n", data_size, uarg->hdr.maxDataSize));
19433 -                       break;
19434 -               }
19435 -               karg.hbapciinfo[ioc_num].iocNumber = ioc_num;
19436 -               karg.hbapciinfo[ioc_num].deviceID = ioc->deviceID;
19437 -               karg.hbapciinfo[ioc_num].vendorID = ioc->vendorID;
19438 -
19439 -               pci_read_config_byte(ioc->pcidev, PCI_CLASS_REVISION, &revision);
19440 -
19441 -               karg.hbapciinfo[ioc_num].subSystemVendorID = ioc->pcidev->subsystem_vendor;
19442 -               karg.hbapciinfo[ioc_num].subSystemID = ioc->pcidev->subsystem_device;
19443 -
19444 -               karg.hbapciinfo[ioc_num].revisionID = revision;
19445 -               mpt_GetIocState(ioc, 1);
19446 -               karg.hbapciinfo[ioc_num++].iocState = (ioc->last_state >> MPI_IOC_STATE_SHIFT);
19447 -       }
19448 -
19449 -       karg.totalIOC = ioc_num;
19450 -
19451 -       dctlprintk((KERN_INFO MYNAM ": %d MPT adapters found, arg=%p karg=%p size=%d\n",
19452 -                karg.totalIOC, (char *)arg, &karg, (int)sizeof(struct mpt_ioctl_hbapciinfo)));
19453 -
19454 -       /* Copy the data from kernel memory to user memory
19455 -        */
19456 -       if (copy_to_user((char *)arg, &karg, sizeof(struct mpt_ioctl_hbapciinfo))) {
19457 -               printk(KERN_ERR "%s@%d::mptctl_eventquery - "
19458 -                       "Unable to write out mpt_ioctl_eventquery struct @ %p\n",
19459 -                               __FILE__, __LINE__, (void*)uarg);
19460 -               return -EFAULT;
19461 -       }
19462 -       return 0;
19463 -}
19464 -#endif
19465 -
19466 -
19467  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
19468  /* MPT IOCTL Test function.
19469   *
19470 @@ -1833,7 +1730,7 @@ mptctl_readtest (unsigned long arg)
19471  
19472         dctlprintk(("mptctl_readtest called.\n"));
19473         if (copy_from_user(&karg, uarg, sizeof(struct mpt_ioctl_test))) {
19474 -               printk(KERN_ERR "%s@%d: mptctl_readtest - "
19475 +               printk(KERN_ERR "%s@%d::mptctl_readtest - "
19476                         "Unable to read in mpt_ioctl_test struct @ %p\n",
19477                                 __FILE__, __LINE__, uarg);
19478                 return -EFAULT;
19479 @@ -1863,7 +1760,7 @@ mptctl_readtest (unsigned long arg)
19480         /* Copy the data from kernel memory to user memory
19481          */
19482         if (copy_to_user((char __user *)arg, &karg, sizeof(struct mpt_ioctl_test))) {
19483 -               printk(KERN_ERR "%s@%d: mptctl_readtest - "
19484 +               printk(KERN_ERR "%s@%d::mptctl_readtest - "
19485                         "Unable to write out mpt_ioctl_test struct @ %p\n",
19486                                 __FILE__, __LINE__, uarg);
19487                 return -EFAULT;
19488 @@ -1893,7 +1790,7 @@ mptctl_eventquery (unsigned long arg)
19489  
19490         dctlprintk(("mptctl_eventquery called.\n"));
19491         if (copy_from_user(&karg, uarg, sizeof(struct mpt_ioctl_eventquery))) {
19492 -               printk(KERN_ERR "%s@%d: mptctl_eventquery - "
19493 +               printk(KERN_ERR "%s@%d::mptctl_eventquery - "
19494                         "Unable to read in mpt_ioctl_eventquery struct @ %p\n",
19495                                 __FILE__, __LINE__, uarg);
19496                 return -EFAULT;
19497 @@ -1912,7 +1809,7 @@ mptctl_eventquery (unsigned long arg)
19498         /* Copy the data from kernel memory to user memory
19499          */
19500         if (copy_to_user((char __user *)arg, &karg, sizeof(struct mpt_ioctl_eventquery))) {
19501 -               printk(KERN_ERR "%s@%d: mptctl_eventquery - "
19502 +               printk(KERN_ERR "%s@%d::mptctl_eventquery - "
19503                         "Unable to write out mpt_ioctl_eventquery struct @ %p\n",
19504                                 __FILE__, __LINE__, uarg);
19505                 return -EFAULT;
19506 @@ -1931,7 +1828,7 @@ mptctl_eventenable (unsigned long arg)
19507  
19508         dctlprintk(("mptctl_eventenable called.\n"));
19509         if (copy_from_user(&karg, uarg, sizeof(struct mpt_ioctl_eventenable))) {
19510 -               printk(KERN_ERR "%s@%d: mptctl_eventenable - "
19511 +               printk(KERN_ERR "%s@%d::mptctl_eventenable - "
19512                         "Unable to read in mpt_ioctl_eventenable struct @ %p\n",
19513                                 __FILE__, __LINE__, uarg);
19514                 return -EFAULT;
19515 @@ -1978,7 +1875,7 @@ mptctl_eventreport (unsigned long arg)
19516  
19517         dctlprintk(("mptctl_eventreport called.\n"));
19518         if (copy_from_user(&karg, uarg, sizeof(struct mpt_ioctl_eventreport))) {
19519 -               printk(KERN_ERR "%s@%d: mptctl_eventreport - "
19520 +               printk(KERN_ERR "%s@%d::mptctl_eventreport - "
19521                         "Unable to read in mpt_ioctl_eventreport struct @ %p\n",
19522                                 __FILE__, __LINE__, uarg);
19523                 return -EFAULT;
19524 @@ -2010,7 +1907,7 @@ mptctl_eventreport (unsigned long arg)
19525          */
19526         numBytes = max * sizeof(MPT_IOCTL_EVENTS);
19527         if (copy_to_user(uarg->eventData, ioc->events, numBytes)) {
19528 -               printk(KERN_ERR "%s@%d: mptctl_eventreport - "
19529 +               printk(KERN_ERR "%s@%d::mptctl_eventreport - "
19530                         "Unable to write out mpt_ioctl_eventreport struct @ %p\n",
19531                                 __FILE__, __LINE__, ioc->events);
19532                 return -EFAULT;
19533 @@ -2031,7 +1928,7 @@ mptctl_replace_fw (unsigned long arg)
19534  
19535         dctlprintk(("mptctl_replace_fw called.\n"));
19536         if (copy_from_user(&karg, uarg, sizeof(struct mpt_ioctl_replace_fw))) {
19537 -               printk(KERN_ERR "%s@%d: mptctl_replace_fw - "
19538 +               printk(KERN_ERR "%s@%d::mptctl_replace_fw - "
19539                         "Unable to read in mpt_ioctl_replace_fw struct @ %p\n",
19540                                 __FILE__, __LINE__, uarg);
19541                 return -EFAULT;
19542 @@ -2067,7 +1964,7 @@ mptctl_replace_fw (unsigned long arg)
19543         /* Copy the data from user memory to kernel space
19544          */
19545         if (copy_from_user(ioc->cached_fw, uarg->newImage, newFwSize)) {
19546 -               printk(KERN_ERR "%s@%d: mptctl_replace_fw - "
19547 +               printk(KERN_ERR "%s@%d::mptctl_replace_fw - "
19548                         "Unable to read in mpt_ioctl_replace_fw image @ %p\n",
19549                         __FILE__, __LINE__, uarg);
19550                 mpt_free_fw_memory(ioc);
19551 @@ -2104,7 +2001,7 @@ mptctl_mpt_command (unsigned long arg)
19552         dctlprintk(("mptctl_command called.\n"));
19553  
19554         if (copy_from_user(&karg, uarg, sizeof(struct mpt_ioctl_command))) {
19555 -               printk(KERN_ERR "%s@%d: mptctl_mpt_command - "
19556 +               printk(KERN_ERR "%s@%d::mptctl_mpt_command - "
19557                         "Unable to read in mpt_ioctl_command struct @ %p\n",
19558                                 __FILE__, __LINE__, uarg);
19559                 return -EFAULT;
19560 @@ -2149,11 +2046,10 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19561         int             iocnum, flagsLength;
19562         int             sz, rc = 0;
19563         int             msgContext;
19564 -       u16             req_idx=0;
19565 +       u16             req_idx;
19566         ulong           timeout;
19567 -        MPT_FRAME_HDR   *SAS_handshake_mf=NULL;
19568 -        char            *SAS_handshake_reply=NULL;
19569 -        u16             msgSize=0;
19570 +
19571 +       dctlprintk(("mptctl_do_mpt_command called.\n"));
19572         bufIn.kptr = bufOut.kptr = NULL;
19573  
19574         if (((iocnum = mpt_verify_adapter(karg.hdr.iocnum, &ioc)) < 0) ||
19575 @@ -2162,14 +2058,13 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19576                                 iocnum));
19577                 return -ENODEV;
19578         }
19579 -       dctlprintk(("ioc%d: mptctl_do_mpt_command called.\n", iocnum));
19580         if (!ioc->ioctl) {
19581 -               printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19582 +               printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19583                         "No memory available during driver init.\n",
19584                                 __FILE__, __LINE__);
19585                 return -ENOMEM;
19586         } else if (ioc->ioctl->status & MPT_IOCTL_STATUS_DID_IOCRESET) {
19587 -               printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19588 +               printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19589                         "Busy with IOC Reset \n", __FILE__, __LINE__);
19590                 return -EBUSY;
19591         }
19592 @@ -2183,7 +2078,7 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19593                 sz += sizeof(dma_addr_t) + sizeof(u32);
19594  
19595         if (sz > ioc->req_sz) {
19596 -               printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19597 +               printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19598                         "Request frame too large (%d) maximum (%d)\n",
19599                                 __FILE__, __LINE__, sz, ioc->req_sz);
19600                 return -EFAULT;
19601 @@ -2191,44 +2086,18 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19602  
19603         /* Get a free request frame and save the message context.
19604          */
19605 -       if (((MPIHeader_t *)(mfPtr))->MsgContext == 0x02012020) {
19606 -               msgSize = karg.hdr.port >> 16;
19607 -               if ( (mf = (MPT_FRAME_HDR *)kmalloc(msgSize, GFP_KERNEL)) == NULL) {
19608 -                       dfailprintk(("%s: mptctl_do_mpt_command, Unable to kmalloc msgSize=%d for SAS_handshake!!\n",
19609 -                       ioc->name, msgSize));
19610 -                       return -ENOMEM;
19611 -               }
19612 -               SAS_handshake_mf = mf;
19613 -               if (karg.maxReplyBytes) {
19614 -                       if ( (SAS_handshake_reply = (char *)kmalloc(karg.maxReplyBytes, GFP_KERNEL)) == NULL) {
19615 -                               kfree(SAS_handshake_mf);
19616 -                               dfailprintk(("%s: mptctl_do_mpt_command, Unable to kmalloc maxReplyBytes=%d for SAS_handshake!!\n",
19617 -                                       ioc->name, karg.maxReplyBytes));
19618 -                               return -ENOMEM;
19619 -                       }
19620 -               }
19621 -               hdr = (MPIHeader_t *) mf;
19622 -               msgContext = le32_to_cpu(0x02012020);
19623 -               karg.hdr.port &= 0x0000ffff;
19624 -       } else {
19625 -               if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL) {
19626 -                       dfailprintk((MYIOC_s_WARN_FMT "%s: no msg frames!!\n",
19627 -                           ioc->name,__FUNCTION__));
19628 -                       return -EAGAIN;
19629 -               } else {
19630 -                       hdr = (MPIHeader_t *) mf;
19631 -                       msgContext = le32_to_cpu(hdr->MsgContext);
19632 -                       req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
19633 -               }
19634 -       }
19635 +        if ((mf = mpt_get_msg_frame(mptctl_id, ioc)) == NULL)
19636 +                return -EAGAIN;
19637  
19638 +       hdr = (MPIHeader_t *) mf;
19639 +       msgContext = le32_to_cpu(hdr->MsgContext);
19640 +       req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
19641  
19642 -//@@@@@
19643         /* Copy the request frame
19644          * Reset the saved message context.
19645          */
19646         if (copy_from_user(mf, mfPtr, karg.dataSgeOffset * 4)) {
19647 -               printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19648 +               printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19649                         "Unable to read MF from mpt_ioctl_command struct @ %p\n",
19650                         __FILE__, __LINE__, mfPtr);
19651                 rc = -EFAULT;
19652 @@ -2259,34 +2128,17 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19653         case MPI_FUNCTION_SCSI_IO_REQUEST:
19654                 if (ioc->sh) {
19655                         SCSIIORequest_t *pScsiReq = (SCSIIORequest_t *) mf;
19656 -                       struct _MPT_DEVICE      *pMptTarget;
19657                         VirtDevice      *pTarget = NULL;
19658                         MPT_SCSI_HOST   *hd = NULL;
19659                         int qtag = MPI_SCSIIO_CONTROL_UNTAGGED;
19660                         int scsidir = 0;
19661 -                       int id = (int) pScsiReq->TargetID;
19662 -                       int bus = (int) pScsiReq->Bus;
19663 +                       int target = (int) pScsiReq->TargetID;
19664                         int dataSize;
19665  
19666 -                       if ((id < 0) || (id > ioc->DevicesPerBus)) {
19667 -                               printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19668 -                                       "Target ID=%d out of bounds.  DevicesPerBus=%d\n",
19669 -                                       __FILE__, __LINE__, id, ioc->DevicesPerBus);
19670 -                               rc = -ENODEV;
19671 -                               goto done_free_mem;
19672 -                       }
19673 -
19674 -                       if ((bus < 0) || (bus >= ioc->NumberOfBuses)) {
19675 -                               printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19676 -                                       "Target Bus=%d out of bounds.  NumberOfBuses=%d\n",
19677 -                                       __FILE__, __LINE__, bus, ioc->NumberOfBuses);
19678 -                               rc = -ENODEV;
19679 -                               goto done_free_mem;
19680 -                       }
19681 -                       if ((pMptTarget = ioc->Target_List[bus]) == NULL) {
19682 -                               printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19683 -                                       "Target_List=NULL for %s bus=%d\n",
19684 -                                       __FILE__, __LINE__, ioc->name, bus);
19685 +                       if ((target < 0) || (target >= ioc->sh->max_id)) {
19686 +                               printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19687 +                                       "Target ID out of bounds. \n",
19688 +                                       __FILE__, __LINE__);
19689                                 rc = -ENODEV;
19690                                 goto done_free_mem;
19691                         }
19692 @@ -2310,7 +2162,8 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19693                                    + (req_idx * MPT_SENSE_BUFFER_ALLOC));
19694  
19695                         if ((hd = (MPT_SCSI_HOST *) ioc->sh->hostdata)) {
19696 -                               pTarget = pMptTarget->Target[id];
19697 +                               if (hd->Targets)
19698 +                                       pTarget = hd->Targets[target];
19699                         }
19700  
19701                         if (pTarget &&(pTarget->tflags & MPT_TARGET_FLAGS_Q_YES))
19702 @@ -2331,10 +2184,10 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19703                         pScsiReq->DataLength = cpu_to_le32(dataSize);
19704  
19705                         ioc->ioctl->reset = MPTCTL_RESET_OK;
19706 -                       ioc->ioctl->id = id;
19707 +                       ioc->ioctl->target = target;
19708  
19709                 } else {
19710 -                       printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19711 +                       printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19712                                 "SCSI driver is not loaded. \n",
19713                                         __FILE__, __LINE__);
19714                         rc = -EFAULT;
19715 @@ -2353,7 +2206,7 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19716  
19717         case MPI_FUNCTION_SATA_PASSTHROUGH:
19718                 if (!ioc->sh) {
19719 -                       printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19720 +                       printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19721                                 "SCSI driver is not loaded. \n",
19722                                         __FILE__, __LINE__);
19723                         rc = -EFAULT;
19724 @@ -2409,10 +2262,9 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19725                         pScsiReq->DataLength = cpu_to_le32(dataSize);
19726  
19727                         ioc->ioctl->reset = MPTCTL_RESET_OK;
19728 -                       ioc->ioctl->id = pScsiReq->TargetID;
19729 -                       ioc->ioctl->bus = pScsiReq->Bus;
19730 +                       ioc->ioctl->target = pScsiReq->TargetID;
19731                 } else {
19732 -                       printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19733 +                       printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19734                                 "SCSI driver is not loaded. \n",
19735                                         __FILE__, __LINE__);
19736                         rc = -EFAULT;
19737 @@ -2424,7 +2276,7 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19738                 {
19739                         MPT_SCSI_HOST *hd = NULL;
19740                         if ((ioc->sh == NULL) || ((hd = (MPT_SCSI_HOST *)ioc->sh->hostdata) == NULL)) {
19741 -                               printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19742 +                               printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19743                                         "SCSI driver not loaded or SCSI host not found. \n",
19744                                         __FILE__, __LINE__);
19745                                 rc = -EFAULT;
19746 @@ -2457,7 +2309,7 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19747                                 (pInit->ReplyFrameSize != cpu_to_le16(ioc->reply_sz)) ||
19748                                 (pInit->HostMfaHighAddr != high_addr) ||
19749                                 (pInit->SenseBufferHighAddr != sense_high)) {
19750 -                               printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19751 +                               printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19752                                         "IOC_INIT issued with 1 or more incorrect parameters. Rejected.\n",
19753                                         __FILE__, __LINE__);
19754                                 rc = -EFAULT;
19755 @@ -2490,7 +2342,7 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19756                         MPI_FUNCTION_LAN_RESET
19757                 */
19758  
19759 -               printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19760 +               printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19761                         "Illegal request (function 0x%x) \n",
19762                         __FILE__, __LINE__, hdr->Function);
19763                 rc = -EFAULT;
19764 @@ -2550,7 +2402,7 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19765                                                 karg.dataOutBufPtr,
19766                                                 bufOut.len)) {
19767                                         printk(KERN_ERR
19768 -                                               "%s@%d: mptctl_do_mpt_command - Unable "
19769 +                                               "%s@%d::mptctl_do_mpt_command - Unable "
19770                                                 "to read user data "
19771                                                 "struct @ %p\n",
19772                                                 __FILE__, __LINE__,karg.dataOutBufPtr);
19773 @@ -2561,7 +2413,16 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19774                 }
19775  
19776                 if (karg.dataInSize > 0) {
19777 -                       flagsLength = MPT_SGE_FLAGS_SSIMPLE_READ;
19778 +                       if ((karg.dataOutSize > 0) &&
19779 +                           (hdr->Function == MPI_FUNCTION_SMP_PASSTHROUGH)){
19780 +                               flagsLength = ( MPI_SGE_FLAGS_SIMPLE_ELEMENT |
19781 +                                               MPI_SGE_FLAGS_END_OF_BUFFER |
19782 +                                               MPI_SGE_FLAGS_DIRECTION |
19783 +                                               mpt_addr_size() )
19784 +                                               << MPI_SGE_FLAGS_SHIFT;
19785 +                       } else {
19786 +                               flagsLength = MPT_SGE_FLAGS_SSIMPLE_READ;
19787 +                       }
19788                         flagsLength |= karg.dataInSize;
19789  
19790                         bufIn.len = karg.dataInSize;
19791 @@ -2585,14 +2446,13 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19792         }
19793  
19794         ioc->ioctl->wait_done = 0;
19795 -       INITIALIZE_IOCTL_STATUS(ioc->ioctl->status)
19796 -
19797         if (hdr->Function == MPI_FUNCTION_SCSI_TASK_MGMT) {
19798  
19799                 DBG_DUMP_TM_REQUEST_FRAME((u32 *)mf);
19800  
19801                 if (mpt_send_handshake_request(mptctl_id, ioc,
19802 -                   sizeof(SCSITaskMgmt_t), (u32*)mf,10, CAN_SLEEP) != 0) {
19803 +                       sizeof(SCSITaskMgmt_t), (u32*)mf,
19804 +                       CAN_SLEEP) != 0) {
19805                         dfailprintk((MYIOC_s_ERR_FMT "_send_handshake FAILED!"
19806                                 " (ioc %p, mf %p) \n", ioc->name,
19807                                 ioc, mf));
19808 @@ -2600,73 +2460,27 @@ mptctl_do_mpt_command (struct mpt_ioctl_
19809                         rc = -ENODATA;
19810                         goto done_free_mem;
19811                 }
19812 -timeout = (karg.timeout > 0) ? karg.timeout : MPT_IOCTL_DEFAULT_TIMEOUT;
19813 -timeout = wait_event_timeout(mptctl_wait,ioc->ioctl->wait_done == 1,HZ*timeout);
19814  
19815 - if(timeout <=0 && (ioc->ioctl->wait_done != 1 )) {
19816 -               /* Now we need to reset the board */
19817 -                       mptctl_free_tm_flags(ioc);
19818 -                       mptctl_timeout_expired(ioc->ioctl);
19819 -                       rc = -ENODATA;
19820 -                       goto done_free_mem;
19821 -               }
19822 -} else {
19823 -               if ( SAS_handshake_mf ) {
19824 -                       dctlprintk(("SAS_handshake_message Function=%x\n",
19825 -                               hdr->Function));
19826 -
19827 -                       timeout = (karg.timeout > 0) ? karg.timeout : MPT_IOCTL_DEFAULT_TIMEOUT;
19828 -                       rc = mpt_handshake_req_reply_wait(ioc,
19829 -                               msgSize,
19830 -                               (u32*)SAS_handshake_mf,
19831 -                              karg.maxReplyBytes,
19832 -                              (u16*)SAS_handshake_reply, timeout /*seconds*/,
19833 -                               CAN_SLEEP);
19834 -                       kfree(SAS_handshake_mf);
19835 -                       SAS_handshake_mf = NULL;
19836 -              if (rc == 0) {
19837 -              dctlprintk(("SAS_handshake_message Function=%x completed successfully\n",
19838 -                               hdr->Function));
19839 -                               sz = karg.maxReplyBytes;
19840 -                               if (sz > 0) {
19841 -                    if (copy_to_user((char *)karg.replyFrameBufPtr,SAS_handshake_reply, sz)){
19842 -printk(KERN_ERR "%s@%d::mptctl_do_mpt_command -" "Unable to write out reply frame %p\n",__FILE__, __LINE__, (void*)karg.replyFrameBufPtr);
19843 -                               rc =  -ENODATA;
19844 -                              }
19845 -                       }else {
19846 -
19847 -                                rc =  -ENODATA;
19848 -                               dctlprintk(("SAS_handshake_message failed sz=%d\n", sz));
19849 -                                }
19850 -                               kfree(SAS_handshake_reply);
19851 -                               SAS_handshake_reply = NULL;
19852 -                               goto done_free_mem;
19853 -                             }
19854 -                            else
19855 -                            {
19856 -                               rc = -ENODATA;
19857 -                               kfree(SAS_handshake_reply);
19858 -                               SAS_handshake_reply = NULL;
19859 -                               goto done_free_mem;
19860 -                            }
19861 -                         }else {
19862 -                               mpt_put_msg_frame(mptctl_id, ioc, mf);
19863 -                       /* Now wait for the command to complete */
19864 -                       timeout = (karg.timeout > 0) ? karg.timeout : MPT_IOCTL_DEFAULT_TIMEOUT;
19865 -                       timeout = wait_event_timeout(mptctl_wait,
19866 -                        ioc->ioctl->wait_done == 1,
19867 -                            HZ*timeout);
19868 +       } else
19869 +               mpt_put_msg_frame(mptctl_id, ioc, mf);
19870  
19871 -                if(timeout <=0 && (ioc->ioctl->wait_done != 1 )) {
19872 +       /* Now wait for the command to complete */
19873 +       timeout = (karg.timeout > 0) ? karg.timeout : MPT_IOCTL_DEFAULT_TIMEOUT;
19874 +       timeout = wait_event_timeout(mptctl_wait,
19875 +            ioc->ioctl->wait_done == 1,
19876 +            HZ*timeout);
19877  
19878 +       if(timeout <=0 && (ioc->ioctl->wait_done != 1 )) {
19879         /* Now we need to reset the board */
19880  
19881 +               if (hdr->Function == MPI_FUNCTION_SCSI_TASK_MGMT)
19882 +                       mptctl_free_tm_flags(ioc);
19883 +
19884                 mptctl_timeout_expired(ioc->ioctl);
19885                 rc = -ENODATA;
19886                 goto done_free_mem;
19887 -              }
19888 -       }
19889 -}
19890 +       }
19891 +
19892  
19893         mf = NULL;
19894  
19895 @@ -2684,7 +2498,7 @@ printk(KERN_ERR "%s@%d::mptctl_do_mpt_co
19896                         if (copy_to_user(karg.replyFrameBufPtr,
19897                                  &ioc->ioctl->ReplyFrame, sz)){
19898  
19899 -                                printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19900 +                                printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19901                                  "Unable to write out reply frame %p\n",
19902                                  __FILE__, __LINE__, karg.replyFrameBufPtr);
19903                                  rc =  -ENODATA;
19904 @@ -2699,7 +2513,7 @@ printk(KERN_ERR "%s@%d::mptctl_do_mpt_co
19905                 sz = min(karg.maxSenseBytes, MPT_SENSE_BUFFER_SIZE);
19906                 if (sz > 0) {
19907                         if (copy_to_user(karg.senseDataPtr, ioc->ioctl->sense, sz)) {
19908 -                               printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19909 +                               printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19910                                 "Unable to write sense data to user %p\n",
19911                                 __FILE__, __LINE__,
19912                                 karg.senseDataPtr);
19913 @@ -2716,7 +2530,7 @@ printk(KERN_ERR "%s@%d::mptctl_do_mpt_co
19914                                 (karg.dataInSize > 0) && (bufIn.kptr)) {
19915                 if (copy_to_user(karg.dataInBufPtr,
19916                          bufIn.kptr, karg.dataInSize)) {
19917 -                       printk(KERN_ERR "%s@%d: mptctl_do_mpt_command - "
19918 +                       printk(KERN_ERR "%s@%d::mptctl_do_mpt_command - "
19919                                 "Unable to write data to user %p\n",
19920                                 __FILE__, __LINE__,
19921                                 karg.dataInBufPtr);
19922 @@ -2726,6 +2540,10 @@ printk(KERN_ERR "%s@%d::mptctl_do_mpt_co
19923  
19924  done_free_mem:
19925  
19926 +       ioc->ioctl->status &= ~(MPT_IOCTL_STATUS_COMMAND_GOOD |
19927 +               MPT_IOCTL_STATUS_SENSE_VALID |
19928 +               MPT_IOCTL_STATUS_RF_VALID );
19929 +
19930         /* Free the allocated memory.
19931          */
19932          if (bufOut.kptr != NULL) {
19933 @@ -2738,14 +2556,6 @@ done_free_mem:
19934                         bufIn.len, (void *) bufIn.kptr, dma_addr_in);
19935         }
19936  
19937 -if (SAS_handshake_mf) {
19938 -               kfree(SAS_handshake_mf);
19939 -               mf=NULL;
19940 -       }
19941 -if (SAS_handshake_reply)
19942 -               kfree(SAS_handshake_reply);
19943 -
19944 -
19945         /* mf is null if command issued successfully
19946          * otherwise, failure occured after mf acquired.
19947          */
19948 @@ -2792,7 +2602,7 @@ mptctl_hp_hostinfo(unsigned long arg, un
19949                 return -EFAULT;
19950  
19951         if (copy_from_user(&karg, uarg, sizeof(hp_host_info_t))) {
19952 -               printk(KERN_ERR "%s@%d: mptctl_hp_host_info - "
19953 +               printk(KERN_ERR "%s@%d::mptctl_hp_host_info - "
19954                         "Unable to read in hp_host_info struct @ %p\n",
19955                                 __FILE__, __LINE__, uarg);
19956                 return -EFAULT;
19957 @@ -2914,8 +2724,6 @@ mptctl_hp_hostinfo(unsigned long arg, un
19958             (MPT_SGE_FLAGS_SSIMPLE_READ|4), buf_dma);
19959  
19960         ioc->ioctl->wait_done = 0;
19961 -       INITIALIZE_IOCTL_STATUS(ioc->ioctl->status)
19962 -
19963         mpt_put_msg_frame(mptctl_id, ioc, mf);
19964  
19965         rc = wait_event_timeout(mptctl_wait,
19966 @@ -2947,7 +2755,7 @@ mptctl_hp_hostinfo(unsigned long arg, un
19967         /* Copy the data from kernel memory to user memory
19968          */
19969         if (copy_to_user((char __user *)arg, &karg, sizeof(hp_host_info_t))) {
19970 -               printk(KERN_ERR "%s@%d: mptctl_hpgethostinfo - "
19971 +               printk(KERN_ERR "%s@%d::mptctl_hpgethostinfo - "
19972                         "Unable to write out hp_host_info @ %p\n",
19973                                 __FILE__, __LINE__, uarg);
19974                 return -EFAULT;
19975 @@ -2986,7 +2794,7 @@ mptctl_hp_targetinfo(unsigned long arg)
19976  
19977         dctlprintk(("mptctl_hp_targetinfo called.\n"));
19978         if (copy_from_user(&karg, uarg, sizeof(hp_target_info_t))) {
19979 -               printk(KERN_ERR "%s@%d: mptctl_hp_targetinfo - "
19980 +               printk(KERN_ERR "%s@%d::mptctl_hp_targetinfo - "
19981                         "Unable to read in hp_host_targetinfo struct @ %p\n",
19982                                 __FILE__, __LINE__, uarg);
19983                 return -EFAULT;
19984 @@ -3097,7 +2905,7 @@ mptctl_hp_targetinfo(unsigned long arg)
19985         /* Copy the data from kernel memory to user memory
19986          */
19987         if (copy_to_user((char __user *)arg, &karg, sizeof(hp_target_info_t))) {
19988 -               printk(KERN_ERR "%s@%d: mptctl_hp_target_info - "
19989 +               printk(KERN_ERR "%s@%d::mptctl_hp_target_info - "
19990                         "Unable to write out mpt_ioctl_targetinfo struct @ %p\n",
19991                                 __FILE__, __LINE__, uarg);
19992                 return -EFAULT;
19993 @@ -3231,8 +3039,6 @@ allocDiagBuffer:
19994         DiagBufferPostRequest->BufferAddress.Low = cpu_to_le32(tmp);
19995  
19996         ioc->ioctl->wait_done = 0;
19997 -       INITIALIZE_IOCTL_STATUS(ioc->ioctl->status)
19998 -
19999         mpt_put_msg_frame(mptctl_id, ioc, mf);
20000  
20001         /* Now wait for the command to complete */
20002 @@ -3275,6 +3081,10 @@ allocDiagBuffer:
20003  
20004  mptctl_register_diag_buffer_out:
20005  
20006 +       ioc->ioctl->status &= ~( MPT_IOCTL_STATUS_TM_FAILED |
20007 +           MPT_IOCTL_STATUS_COMMAND_GOOD | MPT_IOCTL_STATUS_SENSE_VALID |
20008 +           MPT_IOCTL_STATUS_RF_VALID );
20009 +
20010         if ( rc ) {
20011                 pci_free_consistent(ioc->pcidev, request_data_sz,
20012                         request_data,
20013 @@ -3371,8 +3181,6 @@ mptctl_release_diag_buffer (unsigned lon
20014         DiagRelease->MsgFlags = 0;
20015  
20016         ioc->ioctl->wait_done = 0;
20017 -       INITIALIZE_IOCTL_STATUS(ioc->ioctl->status)
20018 -
20019         mpt_put_msg_frame(mptctl_id, ioc, mf);
20020  
20021         /* Now wait for the command to complete */
20022 @@ -3410,6 +3218,10 @@ mptctl_release_diag_buffer (unsigned lon
20023  
20024  mptctl_release_diag_buffer_out:
20025  
20026 +       ioc->ioctl->status &= ~( MPT_IOCTL_STATUS_TM_FAILED |
20027 +           MPT_IOCTL_STATUS_COMMAND_GOOD | MPT_IOCTL_STATUS_SENSE_VALID |
20028 +           MPT_IOCTL_STATUS_RF_VALID);
20029 +
20030         return rc;
20031  }
20032  
20033 @@ -3706,8 +3518,6 @@ mptctl_read_diag_buffer (unsigned long a
20034                 DiagBufferPostRequest->BufferAddress.Low = cpu_to_le32(tmp);
20035  
20036                 ioc->ioctl->wait_done = 0;
20037 -               INITIALIZE_IOCTL_STATUS(ioc->ioctl->status)
20038 -
20039                 mpt_put_msg_frame(mptctl_id, ioc, mf);
20040  
20041                 /* Now wait for the command to complete */
20042 @@ -3746,8 +3556,14 @@ mptctl_read_diag_buffer (unsigned long a
20043                                 ioc->ioctl->status));
20044                         rc = -EFAULT;
20045                 }
20046 -       }
20047 +
20048  mptctl_read_diag_buffer_out:
20049 +
20050 +               ioc->ioctl->status &= ~( MPT_IOCTL_STATUS_TM_FAILED |
20051 +                   MPT_IOCTL_STATUS_COMMAND_GOOD | MPT_IOCTL_STATUS_SENSE_VALID |
20052 +                   MPT_IOCTL_STATUS_RF_VALID);
20053 +
20054 +       }
20055         return rc;
20056  }
20057  
20058 @@ -3796,7 +3612,7 @@ compat_mptctl_ioctl(unsigned int fd, uns
20059         int ret;
20060  
20061         lock_kernel();
20062 -       dctlprintk((KERN_INFO MYNAM ": compat_mptctl_ioctl() called\n"));
20063 +       dctlprintk((KERN_INFO MYNAM "::compat_mptctl_ioctl() called\n"));
20064         ret = mptctl_ioctl(filp->f_dentry->d_inode, filp, cmd, arg);
20065         unlock_kernel();
20066         return ret;
20067 @@ -3820,7 +3636,7 @@ compat_mptfwxfer_ioctl(struct file *filp
20068         int nonblock = (filp->f_flags & O_NONBLOCK);
20069         int ret;
20070  
20071 -       dctlprintk((KERN_INFO MYNAM ": compat_mptfwxfer_ioctl() called\n"));
20072 +       dctlprintk((KERN_INFO MYNAM "::compat_mptfwxfer_ioctl() called\n"));
20073  
20074         if (copy_from_user(&kfw32, (char __user *)arg, sizeof(kfw32)))
20075                 return -EFAULT;
20076 @@ -3829,7 +3645,7 @@ compat_mptfwxfer_ioctl(struct file *filp
20077         iocnumX = kfw32.iocnum & 0xFF;
20078         if (((iocnum = mpt_verify_adapter(iocnumX, &iocp)) < 0) ||
20079             (iocp == NULL)) {
20080 -               dctlprintk((KERN_ERR MYNAM ": compat_mptfwxfer_ioctl @%d - ioc%d not found!\n",
20081 +               dctlprintk((KERN_ERR MYNAM "::compat_mptfwxfer_ioctl @%d - ioc%d not found!\n",
20082                                 __LINE__, iocnumX));
20083                 return -ENODEV;
20084         }
20085 @@ -3866,7 +3682,7 @@ compat_mpt_command(struct file *filp, un
20086         int nonblock = (filp->f_flags & O_NONBLOCK);
20087         int ret;
20088  
20089 -       dctlprintk((KERN_INFO MYNAM ": compat_mpt_command() called\n"));
20090 +       dctlprintk((KERN_INFO MYNAM "::compat_mpt_command() called\n"));
20091  
20092         if (copy_from_user(&karg32, (char __user *)arg, sizeof(karg32)))
20093                 return -EFAULT;
20094 @@ -3875,7 +3691,7 @@ compat_mpt_command(struct file *filp, un
20095         iocnumX = karg32.hdr.iocnum & 0xFF;
20096         if (((iocnum = mpt_verify_adapter(iocnumX, &iocp)) < 0) ||
20097             (iocp == NULL)) {
20098 -               dctlprintk((KERN_ERR MYNAM ": compat_mpt_command @%d - ioc%d not found!\n",
20099 +               dctlprintk((KERN_ERR MYNAM "::compat_mpt_command @%d - ioc%d not found!\n",
20100                                 __LINE__, iocnumX));
20101                 return -ENODEV;
20102         }
20103 @@ -4087,14 +3903,6 @@ static int __init mptctl_init(void)
20104         if (++where && err) goto out_fail;
20105         err = register_ioctl32_conversion(CC_CSMI_SAS_GET_RAID_CONFIG, compat_mptctl_ioctl);
20106         if (++where && err) goto out_fail;
20107 -       err = register_ioctl32_conversion(CC_CSMI_SAS_GET_RAID_FEATURES, compat_mptctl_ioctl);
20108 -       if (++where && err) goto out_fail;
20109 -       err = register_ioctl32_conversion(CC_CSMI_SAS_SET_RAID_CONTROL, compat_mptctl_ioctl);
20110 -       if (++where && err) goto out_fail;
20111 -       err = register_ioctl32_conversion(CC_CSMI_SAS_GET_RAID_ELEMENT, compat_mptctl_ioctl);
20112 -       if (++where && err) goto out_fail;
20113 -       err = register_ioctl32_conversion(CC_CSMI_SAS_SET_RAID_OPERATION, compat_mptctl_ioctl);
20114 -       if (++where && err) goto out_fail;
20115         err = register_ioctl32_conversion(CC_CSMI_SAS_SET_PHY_INFO, compat_mptctl_ioctl);
20116         if (++where && err) goto out_fail;
20117         err = register_ioctl32_conversion(CC_CSMI_SAS_STP_PASSTHRU, compat_mptctl_ioctl);
20118 @@ -4185,10 +3993,6 @@ out_fail:
20119         unregister_ioctl32_conversion(CC_CSMI_SAS_FIRMWARE_DOWNLOAD);
20120         unregister_ioctl32_conversion(CC_CSMI_SAS_GET_RAID_INFO);
20121         unregister_ioctl32_conversion(CC_CSMI_SAS_GET_RAID_CONFIG);
20122 -       unregister_ioctl32_conversion(CC_CSMI_SAS_GET_RAID_FEATURES);
20123 -       unregister_ioctl32_conversion(CC_CSMI_SAS_SET_RAID_CONTROL);
20124 -       unregister_ioctl32_conversion(CC_CSMI_SAS_GET_RAID_ELEMENT);
20125 -       unregister_ioctl32_conversion(CC_CSMI_SAS_SET_RAID_OPERATION);
20126         unregister_ioctl32_conversion(CC_CSMI_SAS_SET_PHY_INFO);
20127         unregister_ioctl32_conversion(CC_CSMI_SAS_STP_PASSTHRU);
20128         unregister_ioctl32_conversion(CC_CSMI_SAS_TASK_MANAGEMENT);
20129 @@ -4260,10 +4064,6 @@ static void mptctl_exit(void)
20130         unregister_ioctl32_conversion(CC_CSMI_SAS_FIRMWARE_DOWNLOAD);
20131         unregister_ioctl32_conversion(CC_CSMI_SAS_GET_RAID_INFO);
20132         unregister_ioctl32_conversion(CC_CSMI_SAS_GET_RAID_CONFIG);
20133 -       unregister_ioctl32_conversion(CC_CSMI_SAS_GET_RAID_FEATURES);
20134 -       unregister_ioctl32_conversion(CC_CSMI_SAS_SET_RAID_CONTROL);
20135 -       unregister_ioctl32_conversion(CC_CSMI_SAS_GET_RAID_ELEMENT);
20136 -       unregister_ioctl32_conversion(CC_CSMI_SAS_SET_RAID_OPERATION);
20137         unregister_ioctl32_conversion(CC_CSMI_SAS_SET_PHY_INFO);
20138         unregister_ioctl32_conversion(CC_CSMI_SAS_STP_PASSTHRU);
20139         unregister_ioctl32_conversion(CC_CSMI_SAS_TASK_MANAGEMENT);
20140 @@ -4277,7 +4077,7 @@ static void mptctl_exit(void)
20141  }
20142  
20143  #if defined(CPQ_CIM)
20144 -#include "csmi/csmisas.c"
20145 +#include "csmisas.c"
20146  #endif // CPQ_CIM
20147  
20148  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
20149 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptctl.h linux-2.6.9-55.0.12/drivers/message/fusion/mptctl.h
20150 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptctl.h  2007-12-21 11:40:54.000000000 +0100
20151 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptctl.h 2007-11-02 09:10:23.000000000 +0100
20152 @@ -5,8 +5,8 @@
20153   *          LSIFC9xx/LSI409xx Fibre Channel
20154   *      running LSI Logic Fusion MPT (Message Passing Technology) firmware.
20155   *
20156 - *  Copyright (c) 1999-2007 LSI Logic Corporation
20157 - *  (mailto:mpt_linux_developer@lsi.com)
20158 + *  Copyright (c) 1999-2005 LSI Logic Corporation
20159 + *  (mailto:mpt_linux_developer@lsil.com)
20160   *
20161   *  $Id: mptctl.h,v 1.14 2003/03/18 22:49:51 Exp $
20162   */
20163 @@ -59,6 +59,7 @@
20164   */
20165  #define MPT_MISCDEV_BASENAME            "mptctl"
20166  #define MPT_MISCDEV_PATHNAME            "/dev/" MPT_MISCDEV_BASENAME
20167 +#define MPT_CSMI_DESCRIPTION           "LSI Logic Corporation: Fusion MPT Driver "MPT_LINUX_VERSION_COMMON
20168  
20169  #define MPT_PRODUCT_LENGTH              12
20170  
20171 @@ -94,16 +95,6 @@
20172  #define MPTDIAGQUERY           _IOWR(MPT_MAGIC_NUMBER,29,mpt_diag_query_t)
20173  #define MPTDIAGREADBUFFER      _IOWR(MPT_MAGIC_NUMBER,30,mpt_diag_read_buffer_t)
20174  
20175 -#ifdef MPT_SUPPORT_FWDLB_IOCTL
20176 -#define MPTHBAPCIINFO          _IOWR(MPT_MAGIC_NUMBER,31,struct mpt_ioctl_hbapciinfo)
20177 -#endif
20178 -
20179 -
20180 -#define INITIALIZE_IOCTL_STATUS(status) \
20181 -       status &= ~( MPT_IOCTL_STATUS_COMMAND_GOOD \
20182 -       | MPT_IOCTL_STATUS_SENSE_VALID \
20183 -       | MPT_IOCTL_STATUS_RF_VALID);
20184 -
20185  /*
20186   * SPARC PLATFORM REMARKS:
20187   * IOCTL data structures that contain pointers
20188 @@ -314,28 +305,6 @@ typedef struct mpt_ioctl_replace_fw {
20189         u8               newImage[1];
20190  } mpt_ioctl_replace_fw_t;
20191  
20192 -#ifdef MPT_SUPPORT_FWDLB_IOCTL
20193 -struct mpt_ioctl_mptpciinfo {
20194 -    U8  iocNumber;
20195 -    U8  iocState;
20196 -    U8  revisionID;
20197 -    U8  reserved1;
20198 -    U16 vendorID;
20199 -    U16 deviceID;
20200 -    U16 subSystemVendorID;
20201 -    U16 subSystemID;
20202 -};
20203 -
20204 -
20205 -struct mpt_ioctl_hbapciinfo {
20206 -       mpt_ioctl_header     hdr;
20207 -    U8                   totalIOC;
20208 -    U8                   reserved[3];
20209 -    struct mpt_ioctl_mptpciinfo hbapciinfo[18];
20210 -};
20211 -#endif
20212 -
20213 -
20214  /* General MPT Pass through data strucutre
20215   *
20216   * iocnum
20217 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptfc.c linux-2.6.9-55.0.12/drivers/message/fusion/mptfc.c
20218 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptfc.c   2007-12-21 11:40:54.000000000 +0100
20219 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptfc.c  2007-11-02 09:10:23.000000000 +0100
20220 @@ -3,8 +3,8 @@
20221   *      For use with LSI Logic PCI chip/adapter(s)
20222   *      running LSI Logic Fusion MPT (Message Passing Technology) firmware.
20223   *
20224 - *  Copyright (c) 1999-2007 LSI Logic Corporation
20225 - *  (mailto:mpt_linux_developer@lsi.com)
20226 + *  Copyright (c) 1999-2005 LSI Logic Corporation
20227 + *  (mailto:mpt_linux_developer@lsil.com)
20228   *
20229   */
20230  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
20231 @@ -74,7 +74,6 @@
20232  MODULE_AUTHOR(MODULEAUTHOR);
20233  MODULE_DESCRIPTION(my_NAME);
20234  MODULE_LICENSE("GPL");
20235 -MODULE_VERSION(my_VERSION);
20236  
20237  /* Command line args */
20238  static int mpt_pq_filter = 0;
20239 @@ -131,7 +130,7 @@ static struct scsi_host_template mptfc_d
20240         .bios_param                     = mptscsih_bios_param,
20241         .can_queue                      = MPT_FC_CAN_QUEUE,
20242         .this_id                        = -1,
20243 -       .sg_tablesize                   = CONFIG_FUSION_MAX_SGE,
20244 +       .sg_tablesize                   = MPT_SCSI_SG_DEPTH,
20245         .max_sectors                    = 8192,
20246         .cmd_per_lun                    = 7,
20247         .use_clustering                 = ENABLE_CLUSTERING,
20248 @@ -161,8 +160,6 @@ static struct pci_device_id mptfc_pci_ta
20249                 PCI_ANY_ID, PCI_ANY_ID },
20250         { PCI_VENDOR_ID_LSI_LOGIC, MPI_MANUFACTPAGE_DEVICEID_FC949E,
20251                 PCI_ANY_ID, PCI_ANY_ID },
20252 -        { 0x1657, MPI_MANUFACTPAGE_DEVICEID_FC949E,
20253 -                PCI_ANY_ID, PCI_ANY_ID },
20254         {0}     /* Terminating entry */
20255  };
20256  MODULE_DEVICE_TABLE(pci, mptfc_pci_table);
20257 @@ -184,6 +181,8 @@ mptfc_probe(struct pci_dev *pdev, const 
20258         MPT_ADAPTER             *ioc;
20259         unsigned long            flags;
20260         int                      sz, ii;
20261 +       int                      numSGE = 0;
20262 +       int                      scale;
20263         int                      ioc_cap;
20264         u8                      *mem;
20265         int                     error=0;
20266 @@ -262,16 +261,46 @@ mptfc_probe(struct pci_dev *pdev, const 
20267                 ioc->name, mpt_can_queue, ioc->req_depth,
20268                 sh->can_queue));
20269  
20270 -       sh->max_id = ioc->DevicesPerBus;
20271 +       sh->max_id = MPT_MAX_FC_DEVICES<256 ? MPT_MAX_FC_DEVICES : 255;
20272  
20273         sh->max_lun = MPT_LAST_LUN + 1;
20274 -       sh->max_channel = ioc->NumberOfBuses - 1;
20275 +       sh->max_channel = 0;
20276         sh->this_id = ioc->pfacts[0].PortSCSIID;
20277  
20278 +
20279         /* Required entry.
20280          */
20281         sh->unique_id = ioc->id;
20282 -       sh->sg_tablesize = ioc->sg_tablesize;
20283 +
20284 +       /* Verify that we won't exceed the maximum
20285 +        * number of chain buffers
20286 +        * We can optimize:  ZZ = req_sz/sizeof(SGE)
20287 +        * For 32bit SGE's:
20288 +        *  numSGE = 1 + (ZZ-1)*(maxChain -1) + ZZ
20289 +        *               + (req_sz - 64)/sizeof(SGE)
20290 +        * A slightly different algorithm is required for
20291 +        * 64bit SGEs.
20292 +        */
20293 +       scale = ioc->req_sz/(sizeof(dma_addr_t) + sizeof(u32));
20294 +       if (sizeof(dma_addr_t) == sizeof(u64)) {
20295 +               numSGE = (scale - 1) *
20296 +                 (ioc->facts.MaxChainDepth-1) + scale +
20297 +                 (ioc->req_sz - 60) / (sizeof(dma_addr_t) +
20298 +                 sizeof(u32));
20299 +       } else {
20300 +               numSGE = 1 + (scale - 1) *
20301 +                 (ioc->facts.MaxChainDepth-1) + scale +
20302 +                 (ioc->req_sz - 64) / (sizeof(dma_addr_t) +
20303 +                 sizeof(u32));
20304 +       }
20305 +
20306 +       if (numSGE < sh->sg_tablesize) {
20307 +               /* Reset this value */
20308 +               dprintk((MYIOC_s_INFO_FMT
20309 +                 "Resetting sg_tablesize to %d from %d\n",
20310 +                 ioc->name, numSGE, sh->sg_tablesize));
20311 +               sh->sg_tablesize = numSGE;
20312 +       }
20313  
20314  #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,13))
20315         /* Set the pci device pointer in Scsi_Host structure.
20316 @@ -300,24 +329,23 @@ mptfc_probe(struct pci_dev *pdev, const 
20317         dprintk((MYIOC_s_INFO_FMT "ScsiLookup @ %p, sz=%d\n",
20318                  ioc->name, hd->ScsiLookup, sz));
20319  
20320 -       for (ii=0; ii < ioc->NumberOfBuses; ii++) {
20321 -               /* Allocate memory for the device structures.
20322 -                * A non-Null pointer at an offset
20323 -                * indicates a device exists.
20324 -                */
20325 -               sz = ioc->DevicesPerBus * sizeof(void *);
20326 -               mem = kmalloc(sz, GFP_ATOMIC);
20327 -               if (mem == NULL) {
20328 -                       error = -ENOMEM;
20329 -                       goto out_mptfc_probe;
20330 -               }
20331 +       /* Allocate memory for the device structures.
20332 +        * A non-Null pointer at an offset
20333 +        * indicates a device exists.
20334 +        * max_id = 1 + maximum id (hosts.h)
20335 +        */
20336 +       sz = sh->max_id * sizeof(void *);
20337 +       mem = kmalloc(sz, GFP_ATOMIC);
20338 +       if (mem == NULL) {
20339 +               error = -ENOMEM;
20340 +               goto out_mptfc_probe;
20341 +       }
20342  
20343 -               memset(mem, 0, sz);
20344 -               ioc->Target_List[ii] = (struct _MPT_DEVICE *) mem;
20345 +       memset(mem, 0, sz);
20346 +       hd->Targets = (VirtDevice **) mem;
20347  
20348 -               dinitprintk((KERN_INFO
20349 -                 " For Bus=%d, Target_List=%p sz=%d\n", ii, mem, sz));
20350 -       }
20351 +       dprintk((KERN_INFO
20352 +         "  Targets @ %p, sz=%d\n", hd->Targets, sz));
20353  
20354         /* Clear the TM flags
20355          */
20356 @@ -333,17 +361,13 @@ mptfc_probe(struct pci_dev *pdev, const 
20357          */
20358         hd->cmdPtr = NULL;
20359  
20360 -       /* Initialize this IOC's timers
20361 +       /* Initialize this SCSI Hosts' timers
20362          * To use, set the timer expires field
20363 -        * and add_timer. Used for internally
20364 -         * generated commands.
20365 +        * and add_timer
20366          */
20367 -        init_timer(&hd->InternalCmdTimer);
20368 -       hd->InternalCmdTimer.data = (unsigned long) hd;
20369 -       hd->InternalCmdTimer.function = mptscsih_InternalCmdTimer_expired;
20370 -        init_timer(&ioc->TMtimer);
20371 -       ioc->TMtimer.data = (unsigned long) ioc;
20372 -       ioc->TMtimer.function = mptscsih_TM_timeout;
20373 +       init_timer(&hd->timer);
20374 +       hd->timer.data = (unsigned long) hd;
20375 +       hd->timer.function = mptscsih_timer_expired;
20376  
20377         hd->mpt_pq_filter = mpt_pq_filter;
20378  
20379 @@ -356,9 +380,6 @@ mptfc_probe(struct pci_dev *pdev, const 
20380         hd->scandv_wait_done = 0;
20381         hd->last_queue_full = 0;
20382  
20383 -        init_waitqueue_head(&hd->TM_waitq);
20384 -        hd->TM_wait_done = 0;
20385 -
20386         error = scsi_add_host (sh, &ioc->pcidev->dev);
20387         if(error) {
20388                 dprintk((KERN_ERR MYNAM
20389 @@ -394,60 +415,6 @@ static struct pci_driver mptfc_driver = 
20390  };
20391  
20392  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
20393 -int
20394 -mptfc_event_process(MPT_ADAPTER *ioc, EventNotificationReply_t *pEvReply)
20395 -{
20396 -       MPT_SCSI_HOST *hd;
20397 -       u8 event = le32_to_cpu(pEvReply->Event) & 0xFF;
20398 -
20399 -       devtprintk((MYIOC_s_INFO_FMT "MPT event (=%02Xh) routed to FC host driver!\n",
20400 -                       ioc->name, event));
20401 -
20402 -       if (ioc->sh == NULL ||
20403 -               ((hd = (MPT_SCSI_HOST *)ioc->sh->hostdata) == NULL))
20404 -               return 1;
20405 -
20406 -       switch (event) {
20407 -       case MPI_EVENT_UNIT_ATTENTION:                  /* 03 */
20408 -               /* FIXME! */
20409 -               break;
20410 -       case MPI_EVENT_IOC_BUS_RESET:                   /* 04 */
20411 -       case MPI_EVENT_EXT_BUS_RESET:                   /* 05 */
20412 -               if (hd && (ioc->bus_type == SPI) && (hd->soft_resets < -1))
20413 -                       hd->soft_resets++;
20414 -               break;
20415 -       case MPI_EVENT_LOGOUT:                          /* 09 */
20416 -               /* FIXME! */
20417 -               break;
20418 -
20419 -               /*
20420 -                *  CHECKME! Don't think we need to do
20421 -                *  anything for these, but...
20422 -                */
20423 -       case MPI_EVENT_RESCAN:                          /* 06 */
20424 -       case MPI_EVENT_LINK_STATUS_CHANGE:              /* 07 */
20425 -       case MPI_EVENT_LOOP_STATE_CHANGE:               /* 08 */
20426 -               /*
20427 -                *  CHECKME!  Falling thru...
20428 -                */
20429 -               break;
20430 -
20431 -       case MPI_EVENT_NONE:                            /* 00 */
20432 -       case MPI_EVENT_LOG_DATA:                        /* 01 */
20433 -       case MPI_EVENT_STATE_CHANGE:                    /* 02 */
20434 -       case MPI_EVENT_EVENT_CHANGE:                    /* 0A */
20435 -       case MPI_EVENT_INTEGRATED_RAID:                 /* 0B */
20436 -       default:
20437 -               devtprintk((KERN_INFO "%s:  Ignoring event (=%02Xh)\n",
20438 -                       __FUNCTION__, event));
20439 -               break;
20440 -       }
20441 -
20442 -       return 1;               /* currently means nothing really */
20443 -}
20444 -
20445 -
20446 -/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
20447  /**
20448   *     mptfc_init - Register MPT adapter(s) as SCSI host(s) with
20449   *     linux scsi mid-layer.
20450 @@ -464,9 +431,9 @@ mptfc_init(void)
20451         mptfcTaskCtx = mpt_register(mptscsih_taskmgmt_complete, MPTFC_DRIVER);
20452         mptfcInternalCtx = mpt_register(mptscsih_scandv_complete, MPTFC_DRIVER);
20453  
20454 -        if (mpt_event_register(mptfcDoneCtx, mptfc_event_process) == 0) {
20455 +       if (mpt_event_register(mptfcDoneCtx, mptscsih_event_process) == 0) {
20456                 devtprintk((KERN_INFO MYNAM
20457 -                  ": mptfc_event_process Registered for IOC event notifications\n"));
20458 +                 ": Registered for IOC event notifications\n"));
20459         }
20460  
20461         if (mpt_reset_register(mptfcDoneCtx, mptscsih_ioc_reset) == 0) {
20462 @@ -488,7 +455,6 @@ mptfc_exit(void)
20463  {
20464         pci_unregister_driver(&mptfc_driver);
20465  
20466 -
20467         mpt_reset_deregister(mptfcDoneCtx);
20468         dprintk((KERN_INFO MYNAM
20469           ": Deregistered for IOC reset notifications\n"));
20470 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptlan.c linux-2.6.9-55.0.12/drivers/message/fusion/mptlan.c
20471 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptlan.c  2007-12-21 11:40:54.000000000 +0100
20472 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptlan.c 2007-11-02 09:10:23.000000000 +0100
20473 @@ -4,7 +4,7 @@
20474   *      For use with LSI Logic Fibre Channel PCI chip/adapters
20475   *      running LSI Logic Fusion MPT (Message Passing Technology) firmware.
20476   *
20477 - *  Copyright (c) 2000-2007 LSI Logic Corporation
20478 + *  Copyright (c) 2000-2005 LSI Logic Corporation
20479   *
20480   *  $Id: mptlan.c,v 1.55 2003/05/07 14:08:32 Exp $
20481   */
20482 @@ -57,11 +57,9 @@
20483  #include <linux/module.h>
20484  #include <linux/fs.h>
20485  
20486 -#define my_VERSION     MPT_LINUX_VERSION_COMMON
20487  #define MYNAM          "mptlan"
20488  
20489  MODULE_LICENSE("GPL");
20490 -MODULE_VERSION(my_VERSION);
20491  
20492  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
20493  /*
20494 @@ -185,16 +183,16 @@ lan_reply (MPT_ADAPTER *ioc, MPT_FRAME_H
20495         struct net_device *dev = ioc->netdev;
20496         int FreeReqFrame = 0;
20497  
20498 -       dlioprintk((KERN_INFO MYNAM ": %s/%s: Got reply.\n",
20499 +       dioprintk((KERN_INFO MYNAM ": %s/%s: Got reply.\n",
20500                   IOC_AND_NETDEV_NAMES_s_s(dev)));
20501  
20502 -//     dlioprintk((KERN_INFO MYNAM "@lan_reply: mf = %p, reply = %p\n",
20503 +//     dioprintk((KERN_INFO MYNAM "@lan_reply: mf = %p, reply = %p\n",
20504  //                     mf, reply));
20505  
20506         if (mf == NULL) {
20507                 u32 tmsg = CAST_PTR_TO_U32(reply);
20508  
20509 -               dlioprintk((KERN_INFO MYNAM ": %s/%s: @lan_reply, tmsg %08x\n",
20510 +               dioprintk((KERN_INFO MYNAM ": %s/%s: @lan_reply, tmsg %08x\n",
20511                                 IOC_AND_NETDEV_NAMES_s_s(dev),
20512                                 tmsg));
20513  
20514 @@ -204,14 +202,14 @@ lan_reply (MPT_ADAPTER *ioc, MPT_FRAME_H
20515                 //  mptbase.c::mpt_interrupt() routine and callcack here
20516  #if 0
20517                 case LAN_REPLY_FORM_MESSAGE_CONTEXT:
20518 -//                     dlioprintk((KERN_INFO MYNAM "/lan_reply: "
20519 +//                     dioprintk((KERN_INFO MYNAM "/lan_reply: "
20520  //                               "MessageContext turbo reply received\n"));
20521                         FreeReqFrame = 1;
20522                         break;
20523  #endif
20524  
20525                 case LAN_REPLY_FORM_SEND_SINGLE:
20526 -//                     dlioprintk((MYNAM "/lan_reply: "
20527 +//                     dioprintk((MYNAM "/lan_reply: "
20528  //                               "calling mpt_lan_send_reply (turbo)\n"));
20529  
20530                         //      FreeReqFrame = mpt_lan_send_turbo(dev, tmsg);
20531 @@ -230,7 +228,7 @@ lan_reply (MPT_ADAPTER *ioc, MPT_FRAME_H
20532                         break;
20533  
20534                 case LAN_REPLY_FORM_RECEIVE_SINGLE:
20535 -//                     dlioprintk((KERN_INFO MYNAM "@lan_reply: "
20536 +//                     dioprintk((KERN_INFO MYNAM "@lan_reply: "
20537  //                               "rcv-Turbo = %08x\n", tmsg));
20538                         mpt_lan_receive_post_turbo(dev, tmsg);
20539                         break;
20540 @@ -248,10 +246,10 @@ lan_reply (MPT_ADAPTER *ioc, MPT_FRAME_H
20541         }
20542  
20543  //     msg = (u32 *) reply;
20544 -//     dlioprintk((KERN_INFO MYNAM "@lan_reply: msg = %08x %08x %08x %08x\n",
20545 +//     dioprintk((KERN_INFO MYNAM "@lan_reply: msg = %08x %08x %08x %08x\n",
20546  //               le32_to_cpu(msg[0]), le32_to_cpu(msg[1]),
20547  //               le32_to_cpu(msg[2]), le32_to_cpu(msg[3])));
20548 -//     dlioprintk((KERN_INFO MYNAM "@lan_reply: Function = %02xh\n",
20549 +//     dioprintk((KERN_INFO MYNAM "@lan_reply: Function = %02xh\n",
20550  //               reply->u.hdr.Function));
20551  
20552         switch (reply->u.hdr.Function) {
20553 @@ -275,7 +273,7 @@ lan_reply (MPT_ADAPTER *ioc, MPT_FRAME_H
20554                         if (!(pRecvRep->MsgFlags & MPI_MSGFLAGS_CONTINUATION_REPLY))
20555                                 FreeReqFrame = 1;
20556                 } else
20557 -                       dlioprintk((KERN_INFO MYNAM "@lan_reply: zero context "
20558 +                       dioprintk((KERN_INFO MYNAM "@lan_reply: zero context "
20559                                   "ReceivePostReply received.\n"));
20560                 break;
20561         }
20562 @@ -617,7 +615,7 @@ mpt_lan_send_turbo(struct net_device *de
20563         priv->stats.tx_packets++;
20564         priv->stats.tx_bytes += sent->len;
20565  
20566 -       dlioprintk((KERN_INFO MYNAM ": %s/%s: @%s, skb %p sent.\n",
20567 +       dioprintk((KERN_INFO MYNAM ": %s/%s: @%s, skb %p sent.\n",
20568                         IOC_AND_NETDEV_NAMES_s_s(dev),
20569                         __FUNCTION__, sent));
20570  
20571 @@ -649,7 +647,7 @@ mpt_lan_send_reply(struct net_device *de
20572  
20573         count = pSendRep->NumberOfContexts;
20574  
20575 -       dlioprintk((KERN_INFO MYNAM ": send_reply: IOCStatus: %04x\n",
20576 +       dioprintk((KERN_INFO MYNAM ": send_reply: IOCStatus: %04x\n",
20577                  le16_to_cpu(pSendRep->IOCStatus)));
20578  
20579         /* Add check for Loginfo Flag in IOCStatus */
20580 @@ -683,7 +681,7 @@ mpt_lan_send_reply(struct net_device *de
20581                 sent = priv->SendCtl[ctx].skb;
20582                 priv->stats.tx_bytes += sent->len;
20583  
20584 -               dlioprintk((KERN_INFO MYNAM ": %s/%s: @%s, skb %p sent.\n",
20585 +               dioprintk((KERN_INFO MYNAM ": %s/%s: @%s, skb %p sent.\n",
20586                                 IOC_AND_NETDEV_NAMES_s_s(dev),
20587                                 __FUNCTION__, sent));
20588  
20589 @@ -722,7 +720,7 @@ mpt_lan_sdu_send (struct sk_buff *skb, s
20590         int ctx;
20591         u16 cur_naa = 0x1000;
20592  
20593 -       dlioprintk((KERN_INFO MYNAM ": %s called, skb_addr = %p\n",
20594 +       dioprintk((KERN_INFO MYNAM ": %s called, skb_addr = %p\n",
20595                         __FUNCTION__, skb));
20596  
20597         spin_lock_irqsave(&priv->txfidx_lock, flags);
20598 @@ -748,7 +746,7 @@ mpt_lan_sdu_send (struct sk_buff *skb, s
20599         ctx = priv->mpt_txfidx[priv->mpt_txfidx_tail--];
20600         spin_unlock_irqrestore(&priv->txfidx_lock, flags);
20601  
20602 -//     dlioprintk((KERN_INFO MYNAM ": %s/%s: Creating new msg frame (send).\n",
20603 +//     dioprintk((KERN_INFO MYNAM ": %s/%s: Creating new msg frame (send).\n",
20604  //                     IOC_AND_NETDEV_NAMES_s_s(dev)));
20605  
20606         pSendReq = (LANSendRequest_t *) mf;
20607 @@ -783,7 +781,7 @@ mpt_lan_sdu_send (struct sk_buff *skb, s
20608         pTrans->Flags         = 0;
20609         pTrans->TransactionContext[0] = cpu_to_le32(ctx);
20610  
20611 -//     dlioprintk((KERN_INFO MYNAM ": %s/%s: BC = %08x, skb = %p, buff = %p\n",
20612 +//     dioprintk((KERN_INFO MYNAM ": %s/%s: BC = %08x, skb = %p, buff = %p\n",
20613  //                     IOC_AND_NETDEV_NAMES_s_s(dev),
20614  //                     ctx, skb, skb->data));
20615  
20616 @@ -843,7 +841,7 @@ mpt_lan_sdu_send (struct sk_buff *skb, s
20617         mpt_put_msg_frame (LanCtx, mpt_dev, mf);
20618         dev->trans_start = jiffies;
20619  
20620 -       dlioprintk((KERN_INFO MYNAM ": %s/%s: Sending packet. FlagsLength = %08x.\n",
20621 +       dioprintk((KERN_INFO MYNAM ": %s/%s: Sending packet. FlagsLength = %08x.\n",
20622                         IOC_AND_NETDEV_NAMES_s_s(dev),
20623                         le32_to_cpu(pSimple->FlagsLength)));
20624  
20625 @@ -864,10 +862,10 @@ mpt_lan_wake_post_buckets_task(struct ne
20626                         schedule_work(&priv->post_buckets_task);
20627                 } else {
20628                         schedule_delayed_work(&priv->post_buckets_task, 1);
20629 -                       dlioprintk((KERN_INFO MYNAM ": post_buckets queued on "
20630 +                       dioprintk((KERN_INFO MYNAM ": post_buckets queued on "
20631                                    "timer.\n"));
20632                 }
20633 -               dlioprintk((KERN_INFO MYNAM ": %s/%s: Queued post_buckets task.\n",
20634 +               dioprintk((KERN_INFO MYNAM ": %s/%s: Queued post_buckets task.\n",
20635                            IOC_AND_NETDEV_NAMES_s_s(dev) ));
20636         }
20637  }
20638 @@ -880,7 +878,7 @@ mpt_lan_receive_skb(struct net_device *d
20639  
20640         skb->protocol = mpt_lan_type_trans(skb, dev);
20641  
20642 -       dlioprintk((KERN_INFO MYNAM ": %s/%s: Incoming packet (%d bytes) "
20643 +       dioprintk((KERN_INFO MYNAM ": %s/%s: Incoming packet (%d bytes) "
20644                  "delivered to upper level.\n",
20645                         IOC_AND_NETDEV_NAMES_s_s(dev), skb->len));
20646  
20647 @@ -890,13 +888,13 @@ mpt_lan_receive_skb(struct net_device *d
20648         skb->dev = dev;
20649         netif_rx(skb);
20650  
20651 -       dlioprintk((MYNAM "/receive_skb: %d buckets remaining\n",
20652 +       dioprintk((MYNAM "/receive_skb: %d buckets remaining\n",
20653                  atomic_read(&priv->buckets_out)));
20654  
20655         if (atomic_read(&priv->buckets_out) < priv->bucketthresh)
20656                 mpt_lan_wake_post_buckets_task(dev, 1);
20657  
20658 -       dlioprintk((KERN_INFO MYNAM "/receive_post_reply: %d buckets "
20659 +       dioprintk((KERN_INFO MYNAM "/receive_post_reply: %d buckets "
20660                   "remaining, %d received back since sod\n",
20661                   atomic_read(&priv->buckets_out), priv->total_received));
20662  
20663 @@ -1027,8 +1025,8 @@ mpt_lan_receive_post_reply(struct net_de
20664         int count;
20665         int i, l;
20666  
20667 -       dlioprintk((KERN_INFO MYNAM ": mpt_lan_receive_post_reply called\n"));
20668 -       dlioprintk((KERN_INFO MYNAM ": receive_post_reply: IOCStatus: %04x\n",
20669 +       dioprintk((KERN_INFO MYNAM ": mpt_lan_receive_post_reply called\n"));
20670 +       dioprintk((KERN_INFO MYNAM ": receive_post_reply: IOCStatus: %04x\n",
20671                  le16_to_cpu(pRecvRep->IOCStatus)));
20672  
20673         if ((le16_to_cpu(pRecvRep->IOCStatus) & MPI_IOCSTATUS_MASK) ==
20674 @@ -1057,14 +1055,14 @@ mpt_lan_receive_post_reply(struct net_de
20675  //                             offset);
20676  //     }
20677  
20678 -       dlioprintk((KERN_INFO MYNAM ": %s/%s: @rpr, offset = %d, len = %d\n",
20679 +       dioprintk((KERN_INFO MYNAM ": %s/%s: @rpr, offset = %d, len = %d\n",
20680                         IOC_AND_NETDEV_NAMES_s_s(dev),
20681                         offset, len));
20682  
20683         if (count > 1) {
20684                 int szrem = len;
20685  
20686 -//             dlioprintk((KERN_INFO MYNAM ": %s/%s: Multiple buckets returned "
20687 +//             dioprintk((KERN_INFO MYNAM ": %s/%s: Multiple buckets returned "
20688  //                     "for single packet, concatenating...\n",
20689  //                             IOC_AND_NETDEV_NAMES_s_s(dev)));
20690  
20691 @@ -1086,7 +1084,7 @@ mpt_lan_receive_post_reply(struct net_de
20692                         if (szrem < l)
20693                                 l = szrem;
20694  
20695 -//                     dlioprintk((KERN_INFO MYNAM ": %s/%s: Buckets = %d, len = %u\n",
20696 +//                     dioprintk((KERN_INFO MYNAM ": %s/%s: Buckets = %d, len = %u\n",
20697  //                                     IOC_AND_NETDEV_NAMES_s_s(dev),
20698  //                                     i, l));
20699  
20700 @@ -1214,7 +1212,7 @@ mpt_lan_post_receive_buckets(void *dev_i
20701         curr = atomic_read(&priv->buckets_out);
20702         buckets = (priv->max_buckets_out - curr);
20703  
20704 -       dlioprintk((KERN_INFO MYNAM ": %s/%s: @%s, Start_buckets = %u, buckets_out = %u\n",
20705 +       dioprintk((KERN_INFO MYNAM ": %s/%s: @%s, Start_buckets = %u, buckets_out = %u\n",
20706                         IOC_AND_NETDEV_NAMES_s_s(dev),
20707                         __FUNCTION__, buckets, curr));
20708  
20709 @@ -1226,7 +1224,7 @@ mpt_lan_post_receive_buckets(void *dev_i
20710                 if (mf == NULL) {
20711                         printk (KERN_ERR "%s: Unable to alloc request frame\n",
20712                                 __FUNCTION__);
20713 -                       dlioprintk((KERN_ERR "%s: %u buckets remaining\n",
20714 +                       dioprintk((KERN_ERR "%s: %u buckets remaining\n",
20715                                  __FUNCTION__, buckets));
20716                         goto out;
20717                 }
20718 @@ -1337,9 +1335,9 @@ mpt_lan_post_receive_buckets(void *dev_i
20719         }
20720  
20721  out:
20722 -       dlioprintk((KERN_INFO MYNAM "/%s: End_buckets = %u, priv->buckets_out = %u\n",
20723 +       dioprintk((KERN_INFO MYNAM "/%s: End_buckets = %u, priv->buckets_out = %u\n",
20724                   __FUNCTION__, buckets, atomic_read(&priv->buckets_out)));
20725 -       dlioprintk((KERN_INFO MYNAM "/%s: Posted %u buckets and received %u back\n",
20726 +       dioprintk((KERN_INFO MYNAM "/%s: Posted %u buckets and received %u back\n",
20727         __FUNCTION__, priv->total_posted, priv->total_received));
20728  
20729         clear_bit(0, &priv->post_buckets_active);
20730 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptlan.h linux-2.6.9-55.0.12/drivers/message/fusion/mptlan.h
20731 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptlan.h  2007-12-21 11:40:54.000000000 +0100
20732 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptlan.h 2007-11-02 09:10:23.000000000 +0100
20733 @@ -65,9 +65,9 @@ MODULE_DESCRIPTION(LANAME);
20734  
20735  /*****************************************************************************/
20736  #ifdef MPT_LAN_IO_DEBUG
20737 -#define dlioprintk(x)  printk x
20738 +#define dioprintk(x)  printk x
20739  #else
20740 -#define dlioprintk(x)
20741 +#define dioprintk(x)
20742  #endif
20743  
20744  #ifdef MPT_LAN_DEBUG
20745 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptsas.c linux-2.6.9-55.0.12/drivers/message/fusion/mptsas.c
20746 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptsas.c  2007-12-21 11:40:54.000000000 +0100
20747 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptsas.c 2007-11-02 09:10:23.000000000 +0100
20748 @@ -3,8 +3,8 @@
20749   *      For use with LSI Logic PCI chip/adapter(s)
20750   *      running LSI Logic Fusion MPT (Message Passing Technology) firmware.
20751   *
20752 - *  Copyright (c) 1999-2007 LSI Logic Corporation
20753 - *  (mailto:mpt_linux_developer@lsi.com)
20754 + *  Copyright (c) 1999-2005 LSI Logic Corporation
20755 + *  (mailto:mpt_linux_developer@lsil.com)
20756   *
20757   */
20758  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
20759 @@ -64,7 +64,6 @@
20760  
20761  #include "mptbase.h"
20762  #include "mptscsih.h"
20763 -#include "mptsas.h"
20764  
20765  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
20766  #define my_NAME                "Fusion MPT SAS Host driver"
20767 @@ -74,10 +73,8 @@
20768  MODULE_AUTHOR(MODULEAUTHOR);
20769  MODULE_DESCRIPTION(my_NAME);
20770  MODULE_LICENSE("GPL");
20771 -MODULE_VERSION(my_VERSION);
20772  
20773  /* Command line args */
20774 -
20775  static int mpt_pq_filter = 0;
20776  module_param(mpt_pq_filter, int, 0);
20777  MODULE_PARM_DESC(mpt_pq_filter, " Enable peripheral qualifier filter: enable=1  (default=0)");
20778 @@ -90,627 +87,40 @@ static int mpt_sas_hot_plug_enable = 1;
20779  module_param(mpt_sas_hot_plug_enable, int, 0);
20780  MODULE_PARM_DESC(mpt_sas_hot_plug_enable, " Enable SAS Hot Plug Support: enable=1 (default=1)");
20781  
20782 -static int mpt_cmd_retry_count = 144;
20783 -module_param(mpt_cmd_retry_count, int, 0);
20784 -MODULE_PARM_DESC(mpt_cmd_retry_count, " Device discovery TUR command retry count: default=144");
20785 -
20786 -extern int mpt_enable_deadioc_detect;
20787 -
20788 -extern int     mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8 type, u8 bus, u8 id, u8 lun, int ctx2abort, ulong timeout);
20789 +extern int     mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8 type, u8 channel, u8 target, u8 lun, int ctx2abort, ulong timeout);
20790  static int     mptsasDoneCtx = -1;
20791  static int     mptsasTaskCtx = -1;
20792  static int     mptsasInternalCtx = -1; /* Used only for internal commands */
20793  
20794 -static void mptsas_hotplug_work(void *arg);
20795 -
20796 -#if defined(CPQ_CIM)
20797 -/**
20798 - * mptsas_sas_io_unit_pg0
20799 - *
20800 - * obtaining SAS_IO_UNIT page 0
20801 - *
20802 - * @ioc
20803 - * @port_info
20804 - *
20805 - **/
20806 -static int
20807 -mptsas_sas_io_unit_pg0(MPT_ADAPTER *ioc, struct mptsas_portinfo *port_info)
20808 -{
20809 -       ConfigExtendedPageHeader_t hdr;
20810 -       CONFIGPARMS cfg;
20811 -       SasIOUnitPage0_t *buffer;
20812 -       dma_addr_t dma_handle;
20813 -       int error, i;
20814 -
20815 -       hdr.PageVersion = MPI_SASIOUNITPAGE0_PAGEVERSION;
20816 -       hdr.ExtPageLength = 0;
20817 -       hdr.PageNumber = 0;
20818 -       hdr.Reserved1 = 0;
20819 -       hdr.Reserved2 = 0;
20820 -       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
20821 -       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_IO_UNIT;
20822 -
20823 -       cfg.cfghdr.ehdr = &hdr;
20824 -       cfg.physAddr = -1;
20825 -       cfg.pageAddr = 0;
20826 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
20827 -       cfg.dir = 0;    /* read */
20828 -       cfg.timeout = 10;
20829 -
20830 -       error = mpt_config(ioc, &cfg);
20831 -       if (error)
20832 -               goto out;
20833 -       if (!hdr.ExtPageLength) {
20834 -               error = -ENXIO;
20835 -               goto out;
20836 -       }
20837 -
20838 -       buffer = pci_alloc_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
20839 -                                           &dma_handle);
20840 -       if (!buffer) {
20841 -               error = -ENOMEM;
20842 -               goto out;
20843 -       }
20844 -
20845 -       cfg.physAddr = dma_handle;
20846 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
20847 -
20848 -       error = mpt_config(ioc, &cfg);
20849 -       if (error)
20850 -               goto out_free_consistent;
20851 -
20852 -       port_info->num_phys = buffer->NumPhys;
20853 -       port_info->phy_info = kmalloc(port_info->num_phys *
20854 -               sizeof(*port_info->phy_info),GFP_KERNEL);
20855 -       if (!port_info->phy_info) {
20856 -               error = -ENOMEM;
20857 -               goto out_free_consistent;
20858 -       }
20859 -
20860 -       if (port_info->num_phys)
20861 -               port_info->handle =
20862 -                   le16_to_cpu(buffer->PhyData[0].ControllerDevHandle);
20863 -       for (i = 0; i < port_info->num_phys; i++) {
20864 -               port_info->phy_info[i].phy_id = i;
20865 -               port_info->phy_info[i].port_id =
20866 -                   buffer->PhyData[i].Port;
20867 -               port_info->phy_info[i].negotiated_link_rate =
20868 -                   buffer->PhyData[i].NegotiatedLinkRate;
20869 -               port_info->phy_info[i].portinfo = port_info;
20870 -               port_info->phy_info[i].port_flags =
20871 -                   buffer->PhyData[i].PortFlags;
20872 -       }
20873 -
20874 - out_free_consistent:
20875 -       pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
20876 -                           buffer, dma_handle);
20877 - out:
20878 -       return error;
20879 -}
20880 -
20881 -/**
20882 - * mptsas_sas_device_pg0
20883 - *
20884 - * obtaining SAS_DEVICE page 0
20885 - *
20886 - * @ioc
20887 - * device_info
20888 - *
20889 - **/
20890 -static int
20891 -mptsas_sas_device_pg0(MPT_ADAPTER *ioc, struct mptsas_devinfo *device_info,
20892 -               u32 form, u32 form_specific)
20893 -{
20894 -       ConfigExtendedPageHeader_t hdr;
20895 -       CONFIGPARMS cfg;
20896 -       SasDevicePage0_t *buffer;
20897 -       dma_addr_t dma_handle;
20898 -       u64 sas_address;
20899 -       int error=0;
20900 -
20901 -       hdr.PageVersion = MPI_SASDEVICE0_PAGEVERSION;
20902 -       hdr.ExtPageLength = 0;
20903 -       hdr.PageNumber = 0;
20904 -       hdr.Reserved1 = 0;
20905 -       hdr.Reserved2 = 0;
20906 -       hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
20907 -       hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_DEVICE;
20908 -
20909 -       cfg.cfghdr.ehdr = &hdr;
20910 -       cfg.pageAddr = form + form_specific;
20911 -       cfg.physAddr = -1;
20912 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
20913 -       cfg.dir = 0;    /* read */
20914 -       cfg.timeout = 10;
20915 -
20916 -       memset(device_info, 0, sizeof(struct mptsas_devinfo));
20917 -       error = mpt_config(ioc, &cfg);
20918 -       if (error)
20919 -               goto out;
20920 -       if (!hdr.ExtPageLength) {
20921 -               error = -ENXIO;
20922 -               goto out;
20923 -       }
20924 -
20925 -       buffer = pci_alloc_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
20926 -                                     &dma_handle);
20927 -       if (!buffer) {
20928 -               error = -ENOMEM;
20929 -               goto out;
20930 -       }
20931 -
20932 -       cfg.physAddr = dma_handle;
20933 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
20934 -
20935 -       error = mpt_config(ioc, &cfg);
20936 -       if (error)
20937 -               goto out_free_consistent;
20938 -
20939 -       device_info->handle = le16_to_cpu(buffer->DevHandle);
20940 -       device_info->handle_parent = le16_to_cpu(buffer->ParentDevHandle);
20941 -       device_info->handle_enclosure =
20942 -           le16_to_cpu(buffer->EnclosureHandle);
20943 -       device_info->slot = le16_to_cpu(buffer->Slot);
20944 -       device_info->phy_id = buffer->PhyNum;
20945 -       device_info->port_id = buffer->PhysicalPort;
20946 -       device_info->id = buffer->TargetID;
20947 -       device_info->channel = buffer->Bus;
20948 -       memcpy(&sas_address, &buffer->SASAddress, sizeof(u64));
20949 -       device_info->sas_address = le64_to_cpu(sas_address);
20950 -       device_info->device_info =
20951 -           le32_to_cpu(buffer->DeviceInfo);
20952 -
20953 - out_free_consistent:
20954 -       pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
20955 -                           buffer, dma_handle);
20956 - out:
20957 -       return error;
20958 -}
20959 -
20960 -/**
20961 - *     mptsas_get_number_hotspares - returns num hot spares in this ioc
20962 - *     @ioc: Pointer to MPT_ADAPTER structure
20963 - *
20964 - *     Return: number of hotspares
20965 - *
20966 - **/
20967 -static int
20968 -mptsas_get_number_hotspares(MPT_ADAPTER *ioc)
20969 -{
20970 -       ConfigPageHeader_t       hdr;
20971 -       CONFIGPARMS              cfg;
20972 -       IOCPage5_t               *buffer = NULL;
20973 -       dma_addr_t               dma_handle;
20974 -       int                      data_sz=0;
20975 -       int                      rc;
20976 -
20977 -       memset(&hdr, 0, sizeof(ConfigPageHeader_t));
20978 -       memset(&cfg, 0, sizeof(CONFIGPARMS));
20979 -
20980 -       rc = 0;
20981 -       hdr.PageNumber = 5;
20982 -       hdr.PageType = MPI_CONFIG_PAGETYPE_IOC;
20983 -       cfg.cfghdr.hdr = &hdr;
20984 -       cfg.physAddr = -1;
20985 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
20986 -       cfg.timeout = 10;
20987 -
20988 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
20989 -               goto get_ioc_pg5;
20990 -
20991 -       if (hdr.PageLength == 0)
20992 -               goto get_ioc_pg5;
20993 -
20994 -       data_sz = hdr.PageLength * 4;
20995 -       buffer = (IOCPage5_t *) pci_alloc_consistent(ioc->pcidev,
20996 -               data_sz, &dma_handle);
20997 -       if (!buffer)
20998 -               goto get_ioc_pg5;
20999 -
21000 -       memset((u8 *)buffer, 0, data_sz);
21001 -       cfg.physAddr = dma_handle;
21002 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
21003 -
21004 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
21005 -               goto get_ioc_pg5;
21006 -
21007 -       rc = buffer->NumHotSpares;
21008 -
21009 - get_ioc_pg5:
21010 -
21011 -       if (buffer)
21012 -               pci_free_consistent(ioc->pcidev, data_sz,
21013 -                   (u8 *) buffer, dma_handle);
21014 -
21015 -       return rc;
21016 -}
21017 -
21018 -/**
21019 - *     mptsas_get_ioc_pg5 - ioc Page 5 hot spares
21020 - *     @ioc: Pointer to MPT_ADAPTER structure
21021 - *     @pIocPage5: ioc page 5
21022 - *
21023 - *     Return: 0 for success
21024 - *     -ENOMEM if no memory available
21025 - *             -EPERM if not allowed due to ISR context
21026 - *             -EAGAIN if no msg frames currently available
21027 - *             -EFAULT for non-successful reply or no reply (timeout)
21028 - **/
21029 -static int
21030 -mptsas_get_ioc_pg5(MPT_ADAPTER *ioc, IOCPage5_t *iocPage5)
21031 -{
21032 -       ConfigPageHeader_t       hdr;
21033 -       CONFIGPARMS              cfg;
21034 -       IOCPage5_t               *buffer = NULL;
21035 -       dma_addr_t               dma_handle;
21036 -       int                      data_sz=0;
21037 -       int                      rc;
21038 -
21039 -       memset(&hdr, 0, sizeof(ConfigPageHeader_t));
21040 -       memset(&cfg, 0, sizeof(CONFIGPARMS));
21041 -
21042 -       rc = 0;
21043 -       hdr.PageNumber = 5;
21044 -       hdr.PageType = MPI_CONFIG_PAGETYPE_IOC;
21045 -       cfg.cfghdr.hdr = &hdr;
21046 -       cfg.physAddr = -1;
21047 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
21048 -       cfg.timeout = 10;
21049 -
21050 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
21051 -               goto get_ioc_pg5;
21052 -
21053 -       if (hdr.PageLength == 0) {
21054 -               rc = -EFAULT;
21055 -               goto get_ioc_pg5;
21056 -       }
21057 -
21058 -       data_sz = hdr.PageLength * 4;
21059 -       buffer = (IOCPage5_t *) pci_alloc_consistent(ioc->pcidev,
21060 -               data_sz, &dma_handle);
21061 -       if (!buffer) {
21062 -               rc = -ENOMEM;
21063 -               goto get_ioc_pg5;
21064 -       }
21065 -
21066 -       memset((u8 *)buffer, 0, data_sz);
21067 -       cfg.physAddr = dma_handle;
21068 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
21069 -
21070 -       if ((rc = mpt_config(ioc, &cfg)) != 0)
21071 -               goto get_ioc_pg5;
21072 -
21073 -       memcpy(iocPage5, buffer, sizeof(*iocPage5));
21074 -
21075 - get_ioc_pg5:
21076 -
21077 -       if (buffer)
21078 -               pci_free_consistent(ioc->pcidev, data_sz,
21079 -                   (u8 *) buffer, dma_handle);
21080 -
21081 -       return rc;
21082 -}
21083 -
21084 -/**
21085 - * mptsas_add_device_component
21086 - *
21087 - * @ioc
21088 - * @channel - fw mapped id's
21089 - * @id
21090 - * @sas_address
21091 - * @device_info
21092 - *
21093 - **/
21094 -static void
21095 -mptsas_add_device_component(MPT_ADAPTER *ioc, u8 channel, u8 id,
21096 -       u64 sas_address, u32 device_info)
21097 -{
21098 -       struct sas_device_info  *sas_info, *next;
21099 -
21100 -       down(&ioc->sas_device_info_mutex);
21101 -
21102 -       /*
21103 -        * Delete all matching sas_address's out of tree
21104 -        */
21105 -       list_for_each_entry_safe(sas_info, next, &ioc->sas_device_info_list, list) {
21106 -               if (sas_info->sas_address != sas_address)
21107 -                       continue;
21108 -               list_del(&sas_info->list);
21109 -               kfree(sas_info);
21110 -       }
21111 -
21112 -       /*
21113 -        * If there is a matching channel/id, then swap out with new target info
21114 -        */
21115 -       list_for_each_entry(sas_info, &ioc->sas_device_info_list, list) {
21116 -               if (sas_info->fw.channel == channel && sas_info->fw.id == id)
21117 -                       goto initialize_data;
21118 -       }
21119 -
21120 -       if (!(sas_info = kmalloc(sizeof(*sas_info), GFP_KERNEL)))
21121 -               goto out;
21122 -       memset(sas_info, 0, sizeof(*sas_info));
21123 -
21124 -       /*
21125 -        * mapping - is for compatibility with drivers supporting sas transport layer
21126 -        */
21127 -       sas_info->fw.id = id;
21128 -       sas_info->fw.channel = channel;
21129 -       sas_info->os.id = id;
21130 -       sas_info->os.channel = channel;
21131 -       list_add_tail(&sas_info->list, &ioc->sas_device_info_list);
21132 -
21133 - initialize_data:
21134 -
21135 -       sas_info->sas_address = sas_address;
21136 -       sas_info->device_info = device_info;
21137 -       sas_info->is_cached = 0;
21138 -       sas_info->is_logical_volume = 0;
21139 -       devtprintk((KERN_INFO "%s: adding channel=%d id=%d "
21140 -           "sas_address=0x%llX\n", __FUNCTION__, channel, id, sas_address));
21141 -
21142 - out:
21143 -       up(&ioc->sas_device_info_mutex);
21144 -       return;
21145 -}
21146 -
21147 -/**
21148 - * mptsas_add_device_component_single
21149 - *
21150 - * @ioc
21151 - * @channel
21152 - * @id
21153 - *
21154 - **/
21155 -static void
21156 -mptsas_add_device_component_single(MPT_ADAPTER *ioc, u8 channel, u8 id)
21157 -{
21158 -       struct mptsas_devinfo sas_device;
21159 -       int rc;
21160 -
21161 -       rc = mptsas_sas_device_pg0(ioc, &sas_device,
21162 -           (MPI_SAS_DEVICE_PGAD_FORM_BUS_TARGET_ID <<
21163 -            MPI_SAS_DEVICE_PGAD_FORM_SHIFT),
21164 -           (channel << 8) + id);
21165 -       if (rc)
21166 -               return;
21167 -
21168 -       mptsas_add_device_component(ioc, sas_device.channel,
21169 -           sas_device.id, sas_device.sas_address, sas_device.device_info);
21170 -}
21171 -
21172 -/**
21173 - * mptsas_add_device_component_hotspare
21174 - *
21175 - * Handle adding hotspares into the list
21176 - *
21177 - * @ioc
21178 - *
21179 - **/
21180 -static void
21181 -mptsas_add_device_component_hotspare(MPT_ADAPTER *ioc)
21182 -{
21183 -       int             num_hotspares;
21184 -       IOCPage5_t      *iocPage5;
21185 -       RaidPhysDiskPage0_t     phys_disk;
21186 -       int             i;
21187 -
21188 -       iocPage5 = NULL;
21189 -       num_hotspares = mptsas_get_number_hotspares(ioc);
21190 -       if (!num_hotspares)
21191 -               goto out;
21192 -
21193 -       iocPage5 = kmalloc(offsetof(IOCPage5_t,HotSpare) +
21194 -           num_hotspares * sizeof(IOC_5_HOT_SPARE), GFP_KERNEL);
21195 -       if (!iocPage5)
21196 -               goto out;
21197 -       memset(iocPage5, 0, sizeof(*iocPage5));
21198 -       if (mptsas_get_ioc_pg5(ioc, iocPage5) != 0)
21199 -               goto out;
21200 -       for(i = 0; i < num_hotspares; i++) {
21201 -               mpt_raid_phys_disk_pg0(ioc,
21202 -                   iocPage5->HotSpare[i].PhysDiskNum, &phys_disk );
21203 -               mptsas_add_device_component_single(ioc,
21204 -                   phys_disk.PhysDiskBus, phys_disk.PhysDiskID);
21205 -       }
21206 - out:
21207 -       kfree(iocPage5);
21208 -
21209 -}
21210 -
21211 -/**
21212 - * mptsas_add_device_component_ir
21213 - *
21214 - * Handle Integrated RAID, adding each individual device to list
21215 - *
21216 - * @ioc
21217 - * @channel
21218 - * @id
21219 - *
21220 - **/
21221 -static void
21222 -mptsas_add_device_component_ir(MPT_ADAPTER *ioc, u8 channel, u8 id)
21223 -{
21224 -       CONFIGPARMS                     cfg;
21225 -       ConfigPageHeader_t              hdr;
21226 -       dma_addr_t                      dma_handle;
21227 -       pRaidVolumePage0_t              buffer = NULL;
21228 -       int                             i;
21229 -       RaidPhysDiskPage0_t             phys_disk;
21230 -       struct sas_device_info          *sas_info;
21231 -
21232 -       memset(&cfg, 0 , sizeof(CONFIGPARMS));
21233 -       memset(&hdr, 0 , sizeof(ConfigPageHeader_t));
21234 -       hdr.PageType = MPI_CONFIG_PAGETYPE_RAID_VOLUME;
21235 -       cfg.pageAddr = (channel << 8) + id;
21236 -       cfg.cfghdr.hdr = &hdr;
21237 -       cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
21238 -
21239 -       if (mpt_config(ioc, &cfg) != 0)
21240 -               goto out;
21241 -
21242 -       if (!hdr.PageLength)
21243 -               goto out;
21244 -
21245 -       buffer = pci_alloc_consistent(ioc->pcidev, hdr.PageLength * 4,
21246 -           &dma_handle);
21247 -
21248 -       if (!buffer)
21249 -               goto out;
21250 -
21251 -       cfg.physAddr = dma_handle;
21252 -       cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
21253 -
21254 -       if (mpt_config(ioc, &cfg) != 0)
21255 -               goto out;
21256 -
21257 -       if (!buffer->NumPhysDisks)
21258 -               goto out;
21259 -
21260 -       /*
21261 -        * Adding entry for hidden components
21262 -        */
21263 -       for (i = 0; i < buffer->NumPhysDisks; i++) {
21264 -
21265 -               if(mpt_raid_phys_disk_pg0(ioc,
21266 -                   buffer->PhysDisk[i].PhysDiskNum, &phys_disk) != 0)
21267 -                       continue;
21268  
21269 -               mptsas_add_device_component_single(ioc, phys_disk.PhysDiskBus,
21270 -                   phys_disk.PhysDiskID);
21271 -       }
21272 -
21273 -       /*
21274 -        * Adding entry for logical volume in list
21275 -        */
21276 -       list_for_each_entry(sas_info, &ioc->sas_device_info_list, list) {
21277 -               if (sas_info->fw.channel == channel && sas_info->fw.id ==  id)
21278 -                       goto initialize_data;
21279 -       }
21280 -
21281 -       if (!(sas_info = kmalloc(sizeof(*sas_info), GFP_KERNEL)))
21282 -               goto out;
21283 -       memset(sas_info, 0, sizeof(*sas_info));
21284 -
21285 -       sas_info->fw.id = id;
21286 -       sas_info->fw.channel = channel; /* channel zero */
21287 -       down(&ioc->sas_device_info_mutex);
21288 -       list_add_tail(&sas_info->list, &ioc->sas_device_info_list);
21289 -       up(&ioc->sas_device_info_mutex);
21290 -
21291 - initialize_data:
21292 -
21293 -       sas_info->os.id = id;
21294 -       sas_info->os.channel = channel;
21295 -       sas_info->sas_address = 0;
21296 -       sas_info->device_info = 0;
21297 -       sas_info->is_logical_volume = 1;
21298 -       sas_info->is_cached = 0;
21299 -
21300 -       devtprintk((KERN_INFO "%s: adding volume at channel=%d id=%d\n",
21301 -           __FUNCTION__, channel, id));
21302 -
21303 -       mptsas_add_device_component_hotspare(ioc);
21304 - out:
21305 -       if (buffer)
21306 -               pci_free_consistent(ioc->pcidev, hdr.PageLength * 4, buffer,
21307 -                   dma_handle);
21308 -}
21309 -
21310 -
21311 -/**
21312 - * mptsas_del_device_component
21313 - *
21314 - * Once a device has been removed, we mark the
21315 - * entry in the list as being cached
21316 - *
21317 - * @ioc
21318 - * @channel - os mapped id's
21319 - * @id
21320 - *
21321 - **/
21322 -static void
21323 -mptsas_del_device_component(MPT_ADAPTER *ioc, u8 channel, u8 id)
21324 -{
21325 -       struct sas_device_info  *sas_info, *next;
21326 -
21327 -       /*
21328 -        * Set is_cached flag
21329 -        */
21330 -       list_for_each_entry_safe(sas_info, next, &ioc->sas_device_info_list, list) {
21331 -               if (sas_info->os.channel == channel && sas_info->os.id == id) {
21332 -                       sas_info->is_cached = 1;
21333 -                       devtprintk((KERN_INFO
21334 -                           "%s: deleting channel=%d id=%d "
21335 -                           "sas_address=0x%llX\n", __FUNCTION__, channel, id,
21336 -                           sas_info->sas_address));
21337 -               }
21338 -       }
21339 -}
21340 -
21341 -/**
21342 - * mptsas_del_device_components
21343 - *
21344 - * Cleaning the list
21345 - *
21346 - * @ioc
21347 - *
21348 - **/
21349 -static void
21350 -mptsas_del_device_components(MPT_ADAPTER *ioc)
21351 -{
21352 -       struct sas_device_info  *sas_info, *next;
21353 -
21354 -       down(&ioc->sas_device_info_mutex);
21355 -       list_for_each_entry_safe(sas_info, next, &ioc->sas_device_info_list, list) {
21356 -               list_del(&sas_info->list);
21357 -               kfree(sas_info);
21358 -       }
21359 -       up(&ioc->sas_device_info_mutex);
21360 -}
21361 -#endif
21362 -
21363 -/**
21364 - * mptsas_find_vdevice
21365 - *
21366 - * @ioc
21367 - * @channel
21368 - * @id
21369 - *
21370 - **/
21371 -static VirtDevice *
21372 -mptsas_find_vdevice(MPT_ADAPTER *ioc, u8 channel, u8 id)
21373 -{
21374 -       struct _MPT_DEVICE *pMptTarget;
21375 -
21376 -       if (id >= ioc->DevicesPerBus || channel >= ioc->NumberOfBuses)
21377 -               return NULL;
21378 +enum mptsas_hotplug_action {
21379 +       MPTSAS_ADD_DEVICE,
21380 +       MPTSAS_DEL_DEVICE,
21381 +};
21382  
21383 -       pMptTarget = ioc->Target_List[channel];
21384 -       return pMptTarget->Target[id];
21385 -}
21386 +struct mptsas_hotplug_event {
21387 +       struct work_struct      work;
21388 +       MPT_ADAPTER             *ioc;
21389 +       enum mptsas_hotplug_action event_type;
21390 +       u64                     sas_address;
21391 +       u32                     channel;
21392 +       u32                     id;
21393 +       u32                     device_info;
21394 +       u16                     handle;
21395 +       u16                     parent_handle;
21396 +       u8                      phy_id;
21397 +       u8                      isRaid;
21398 +};
21399  
21400 -/**
21401 - * mptsas_qcmd
21402 - *
21403 - * receiving a scsi_cmnd from upper layers
21404 - *
21405 - * @SCpnt
21406 - * @done
21407 - *
21408 - **/
21409  static int
21410  mptsas_qcmd(struct scsi_cmnd *SCpnt, void (*done)(struct scsi_cmnd *))
21411  {
21412         MPT_SCSI_HOST *hd = (MPT_SCSI_HOST *) SCpnt->device->host->hostdata;
21413 -       MPT_ADAPTER *ioc = hd->ioc;
21414 -       static VirtDevice *pTarget;
21415 -       int id = SCpnt->device->id;
21416 -       int channel = SCpnt->device->channel;
21417 -
21418 -       /* If Device has been removed, inhibit any more IO */
21419 -       pTarget = mptsas_find_vdevice(ioc, channel, id);
21420 -       if (pTarget && (pTarget->tflags & MPT_TARGET_FLAGS_DELETED)) {
21421 +       int      id = SCpnt->device->id;
21422 +
21423 +       /* Device has been removed, so inhibit any more IO */
21424 +       if (hd->Targets[id] &&
21425 +           hd->Targets[id]->tflags & MPT_TARGET_FLAGS_DELETED) {
21426                 SCpnt->result = DID_NO_CONNECT << 16;
21427                 done(SCpnt);
21428                 return 0;
21429 @@ -719,32 +129,6 @@ mptsas_qcmd(struct scsi_cmnd *SCpnt, voi
21430         return mptscsih_qcmd(SCpnt,done);
21431  }
21432  
21433 -/**
21434 - * mptsas_slave_configure
21435 - *
21436 - *
21437 - * @sdev
21438 - *
21439 - **/
21440 -static int
21441 -mptsas_slave_configure(struct scsi_device *sdev)
21442 -{
21443 -#if defined(CPQ_CIM)
21444 -       MPT_SCSI_HOST   *hd = (MPT_SCSI_HOST *)sdev->host->hostdata;
21445 -       MPT_ADAPTER *ioc = hd->ioc;
21446 -       int             channel;
21447 -       int             id;
21448 -
21449 -       channel = sdev->channel;
21450 -       id = sdev->id;
21451 -
21452 -       if ((ioc->raid_data.isRaid & (1 << id)) == 0)
21453 -               mptsas_add_device_component_single(ioc, channel, id);
21454 -#endif
21455 -       return mptscsih_slave_configure(sdev);
21456 -}
21457 -
21458 -
21459  /* Show the ioc state for this card */
21460  static ssize_t
21461  mptsas_show_iocstate(struct class_device *class_dev, char *buf)
21462 @@ -778,300 +162,49 @@ static struct scsi_host_template mptsas_
21463         .info                           = mptscsih_info,
21464         .queuecommand                   = mptsas_qcmd,
21465         .slave_alloc                    = mptscsih_slave_alloc,
21466 -       .slave_configure                = mptsas_slave_configure,
21467 -       .slave_destroy                  = mptscsih_slave_destroy,
21468 -#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,11))
21469 -       .change_queue_depth             = mptscsih_change_queue_depth,
21470 -#endif
21471 -       .eh_abort_handler               = mptscsih_abort,
21472 -       .eh_device_reset_handler        = mptscsih_dev_reset,
21473 -       .eh_bus_reset_handler           = mptscsih_bus_reset,
21474 -       .eh_host_reset_handler          = mptscsih_host_reset,
21475 -       .bios_param                     = mptscsih_bios_param,
21476 -       .can_queue                      = MPT_FC_CAN_QUEUE,
21477 -       .this_id                        = -1,
21478 -       .sg_tablesize                   = CONFIG_FUSION_MAX_SGE,
21479 -       .max_sectors                    = 8192,
21480 -       .cmd_per_lun                    = 7,
21481 -       .use_clustering                 = ENABLE_CLUSTERING,
21482 -       .shost_attrs                    = mptsas_host_attrs,
21483 -       .dump_sanity_check              = mptscsih_sanity_check,
21484 -       .dump_poll                      = mptscsih_poll,
21485 -};
21486 -
21487 -/**
21488 - * mptsas_remove
21489 - *
21490 - *
21491 - * @pdev
21492 - *
21493 - **/
21494 -static void __devexit mptsas_remove(struct pci_dev *pdev)
21495 -{
21496 -#if defined(CPQ_CIM)
21497 -       MPT_ADAPTER *ioc = pci_get_drvdata(pdev);
21498 -  if(ioc->sh != NULL)
21499 -       mptsas_del_device_components(ioc);
21500 -#endif
21501 -
21502 -       flush_scheduled_work();
21503 -       mptscsih_remove(pdev);
21504 -}
21505 -
21506 -/**
21507 - * mptsas_target_reset
21508 - *
21509 - * Issues TARGET_RESET to end device using handshaking method
21510 - *
21511 - * @ioc
21512 - * @channel
21513 - * @id
21514 - *
21515 - * Returns (1) success
21516 - *         (0) failure
21517 - *
21518 - **/
21519 -static int
21520 -mptsas_target_reset(MPT_ADAPTER *ioc, u8 channel, u8 id)
21521 -{
21522 -       MPT_FRAME_HDR   *mf;
21523 -       SCSITaskMgmt_t  *pScsiTm;
21524 -
21525 -       if ((mf = mpt_get_msg_frame(ioc->TaskCtx, ioc)) == NULL) {
21526 -               dfailprintk((MYIOC_s_WARN_FMT "%s, no msg frames @%d!!\n",
21527 -                   ioc->name,__FUNCTION__, __LINE__));
21528 -               return 0;
21529 -       }
21530 -
21531 -       /* Format the Request
21532 -        */
21533 -       pScsiTm = (SCSITaskMgmt_t *) mf;
21534 -       memset (pScsiTm, 0, sizeof(SCSITaskMgmt_t));
21535 -       pScsiTm->TargetID = id;
21536 -       pScsiTm->Bus = channel;
21537 -       pScsiTm->Function = MPI_FUNCTION_SCSI_TASK_MGMT;
21538 -       pScsiTm->TaskType = MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET;
21539 -       pScsiTm->MsgFlags = MPI_SCSITASKMGMT_MSGFLAGS_LIPRESET_RESET_OPTION;
21540 -
21541 -// EDM printk("tm target reset : issue : channel=%d id=%d\n", channel, id);
21542 -       DBG_DUMP_TM_REQUEST_FRAME(mf);
21543 -
21544 -       if (mpt_send_handshake_request(ioc->TaskCtx, ioc,
21545 -           sizeof(SCSITaskMgmt_t), (u32 *)mf, 10,NO_SLEEP)) {
21546 -               mpt_free_msg_frame(ioc, mf);
21547 -               dfailprintk((MYIOC_s_WARN_FMT "%s, tm handshake failed @%d!!\n",
21548 -                   ioc->name,__FUNCTION__, __LINE__));
21549 -               return 0;
21550 -       }
21551 -
21552 -       return 1;
21553 -}
21554 -
21555 -/**
21556 - * mptsas_target_reset_queue
21557 - *
21558 - * Receive request for TARGET_RESET after recieving an firmware
21559 - * event NOT_RESPONDING_EVENT, then put command in link list
21560 - * and queue if task_queue already in use.
21561 - *
21562 - * @ioc
21563 - * @sas_event_data
21564 - *
21565 - **/
21566 -static void
21567 -mptsas_target_reset_queue(MPT_ADAPTER *ioc,
21568 -    EVENT_DATA_SAS_DEVICE_STATUS_CHANGE *sas_event_data)
21569 -{
21570 -       MPT_SCSI_HOST   *hd = (MPT_SCSI_HOST *)ioc->sh->hostdata;
21571 -       VirtDevice *vdevice = NULL;
21572 -       struct mptscsih_target_reset    *target_reset_list;
21573 -       u8              id, channel;
21574 -
21575 -       id = sas_event_data->TargetID;
21576 -       channel = sas_event_data->Bus;
21577 -
21578 -       if (!(vdevice = mptsas_find_vdevice(ioc, channel, id)))
21579 -               return;
21580 -
21581 -       vdevice->tflags |= MPT_TARGET_FLAGS_DELETED;
21582 -
21583 -       target_reset_list = kmalloc(sizeof(*target_reset_list),
21584 -           GFP_ATOMIC);
21585 -       if (!target_reset_list) {
21586 -               dfailprintk((MYIOC_s_WARN_FMT
21587 -                       "%s, failed to allocate mem @%d..!!\n",
21588 -                   ioc->name,__FUNCTION__, __LINE__));
21589 -               return;
21590 -       }
21591 -
21592 -       memset(target_reset_list, 0, sizeof(*target_reset_list));
21593 -// EDM printk("tm target reset : queue : channel=%d id=%d\n", channel, id);
21594 -
21595 -       memcpy(&target_reset_list->sas_event_data, sas_event_data,
21596 -               sizeof(*sas_event_data));
21597 -       list_add_tail(&target_reset_list->list, &hd->target_reset_list);
21598 -
21599 -       if (hd->resetPending)
21600 -               return;
21601 -
21602 -       if (mptsas_target_reset(ioc, channel, id)) {
21603 -               target_reset_list->target_reset_issued = 1;
21604 -               hd->resetPending = 1;
21605 -       }
21606 -}
21607 -
21608 -/**
21609 - * mptsas_dev_reset_complete
21610 - *
21611 - * Completion for TARGET_RESET after NOT_RESPONDING_EVENT,
21612 - * enable work queue to finish off removing device from upper layers.
21613 - * then send next TARGET_RESET in the queue.
21614 - *
21615 - * @ioc
21616 - *
21617 - **/
21618 -static void
21619 -mptsas_dev_reset_complete(MPT_ADAPTER *ioc)
21620 -{
21621 -       MPT_SCSI_HOST   *hd = (MPT_SCSI_HOST *)ioc->sh->hostdata;
21622 -        struct list_head *head = &hd->target_reset_list;
21623 -       struct mptscsih_target_reset    *target_reset_list;
21624 -       struct mptsas_hotplug_event *ev;
21625 -       EVENT_DATA_SAS_DEVICE_STATUS_CHANGE *sas_event_data;
21626 -       u8              id, channel;
21627 -       u64             sas_address;
21628 -
21629 -       if (list_empty(head))
21630 -               return;
21631 -
21632 -       target_reset_list = list_entry(head->next,
21633 -           struct mptscsih_target_reset, list);
21634 -
21635 -       sas_event_data = &target_reset_list->sas_event_data;
21636 -       id = sas_event_data->TargetID;
21637 -       channel = sas_event_data->Bus;
21638 -       hd->resetPending = 0;
21639 -
21640 -       /*
21641 -        * retry target reset
21642 -        */
21643 -       if (!target_reset_list->target_reset_issued) {
21644 -               if (mptsas_target_reset(ioc, channel, id)) {
21645 -                       target_reset_list->target_reset_issued = 1;
21646 -                       hd->resetPending = 1;
21647 -               }
21648 -               return;
21649 -       }
21650 -
21651 -// EDM printk("tm target reset : complete : channel=%d id=%d\n", channel, id);
21652 -
21653 -       /*
21654 -        * enable work queue to remove device from upper layers
21655 -        */
21656 -       list_del(&target_reset_list->list);
21657 -
21658 -       ev = kmalloc(sizeof(*ev), GFP_ATOMIC);
21659 -       if (!ev) {
21660 -               dfailprintk((MYIOC_s_WARN_FMT
21661 -                   "%s, failed to allocate mem @%d..!!\n",
21662 -                   ioc->name,__FUNCTION__, __LINE__));
21663 -               return;
21664 -       }
21665 -
21666 -       memset(ev, 0, sizeof(*ev));
21667 -       INIT_WORK(&ev->work, mptsas_hotplug_work, ev);
21668 -       ev->ioc = ioc;
21669 -       ev->handle = le16_to_cpu(sas_event_data->DevHandle);
21670 -       ev->parent_handle = le16_to_cpu(sas_event_data->ParentDevHandle);
21671 -       ev->channel = channel;
21672 -       ev->id = id;
21673 -       ev->phy_id = sas_event_data->PhyNum;
21674 -       memcpy(&sas_address, &sas_event_data->SASAddress, sizeof(u64));
21675 -       ev->sas_address = le64_to_cpu(sas_address);
21676 -       ev->device_info = le32_to_cpu(sas_event_data->DeviceInfo);
21677 -       ev->event_type = MPTSAS_DEL_DEVICE;
21678 -       schedule_work(&ev->work);
21679 -       kfree(target_reset_list);
21680 -
21681 -       /*
21682 -        * issue target reset to next device in the queue
21683 -        */
21684 -
21685 -       head = &hd->target_reset_list;
21686 -       if (list_empty(head))
21687 -               return;
21688 -
21689 -       target_reset_list = list_entry(head->next, struct mptscsih_target_reset,
21690 -           list);
21691 -
21692 -       sas_event_data = &target_reset_list->sas_event_data;
21693 -       id = sas_event_data->TargetID;
21694 -       channel = sas_event_data->Bus;
21695 -
21696 -       if (mptsas_target_reset(ioc, channel, id)) {
21697 -               target_reset_list->target_reset_issued = 1;
21698 -               hd->resetPending = 1;
21699 -       }
21700 -}
21701 +       .slave_configure                = mptscsih_slave_configure,
21702 +       .slave_destroy                  = mptscsih_slave_destroy,
21703 +#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,11))
21704 +       .change_queue_depth             = mptscsih_change_queue_depth,
21705 +#endif
21706 +       .eh_abort_handler               = mptscsih_abort,
21707 +       .eh_device_reset_handler        = mptscsih_dev_reset,
21708 +       .eh_bus_reset_handler           = mptscsih_bus_reset,
21709 +       .eh_host_reset_handler          = mptscsih_host_reset,
21710 +       .bios_param                     = mptscsih_bios_param,
21711 +       .can_queue                      = MPT_FC_CAN_QUEUE,
21712 +       .this_id                        = -1,
21713 +       .sg_tablesize                   = MPT_SCSI_SG_DEPTH,
21714 +       .max_sectors                    = 8192,
21715 +       .cmd_per_lun                    = 7,
21716 +       .use_clustering                 = ENABLE_CLUSTERING,
21717 +       .shost_attrs                    = mptsas_host_attrs,
21718 +       .dump_sanity_check              = mptscsih_sanity_check,
21719 +       .dump_poll                      = mptscsih_poll,
21720 +};
21721  
21722 -/**
21723 - * mptsas_taskmgmt_complete
21724 - *
21725 - * @ioc
21726 - * @mf
21727 - * @mr
21728 - *
21729 - **/
21730 -static int
21731 -mptsas_taskmgmt_complete(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, MPT_FRAME_HDR *mr)
21732 +static void __devexit mptsas_remove(struct pci_dev *pdev)
21733  {
21734 -       mptsas_dev_reset_complete(ioc);
21735 -       return mptscsih_taskmgmt_complete(ioc, mf, mr);
21736 +       flush_scheduled_work();
21737 +       mptscsih_remove(pdev);
21738  }
21739  
21740 -/**
21741 - * mptscsih_ioc_reset
21742 - *
21743 - * @ioc
21744 - * @reset_phase
21745 - *
21746 - **/
21747 -static int
21748 -mptsas_ioc_reset(MPT_ADAPTER *ioc, int reset_phase)
21749 +static void
21750 +mptsas_target_reset(MPT_ADAPTER *ioc, VirtDevice * vdevice)
21751  {
21752 -        MPT_SCSI_HOST   *hd =NULL;
21753 -       struct mptscsih_target_reset    *target_reset_list, *n;
21754 -       int rc;
21755 -
21756 -        if ((ioc->sh != NULL) && (ioc->sh->hostdata != NULL))
21757 -              hd = (MPT_SCSI_HOST *)ioc->sh->hostdata;
21758 -
21759 -       rc = mptscsih_ioc_reset(ioc, reset_phase);
21760 +       MPT_SCSI_HOST           *hd = (MPT_SCSI_HOST *)ioc->sh->hostdata;
21761  
21762 -       if (reset_phase != MPT_IOC_POST_RESET)
21763 -               goto out;
21764 -
21765 -       if (ioc->bus_type != SAS)
21766 -               goto out;
21767 -       if(hd == NULL)
21768 -               goto out;
21769 -
21770 -
21771 -       if (list_empty(&hd->target_reset_list))
21772 -               goto out;
21773 -
21774 -       /* flush the target_reset_list */
21775 -       list_for_each_entry_safe(target_reset_list, n,
21776 -           &hd->target_reset_list, list) {
21777 -               list_del(&target_reset_list->list);
21778 -               kfree(target_reset_list);
21779 +       if (mptscsih_TMHandler(hd,
21780 +            MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET,
21781 +            vdevice->bus_id, vdevice->target_id, 0, 0, 5) < 0) {
21782 +               hd->tmPending = 0;
21783 +               hd->tmState = TM_STATE_NONE;
21784 +               printk(MYIOC_s_WARN_FMT
21785 +              "Error processing TaskMgmt id=%d TARGET_RESET\n",
21786 +                       ioc->name, vdevice->target_id);
21787         }
21788 -
21789 - out:
21790 -       return rc;
21791  }
21792  
21793 -
21794  /****************************************************************************
21795   * Supported hardware
21796   */
21797 @@ -1092,13 +225,6 @@ static struct pci_device_id mptsas_pci_t
21798  MODULE_DEVICE_TABLE(pci, mptsas_pci_table);
21799  
21800  
21801 -/**
21802 - * mptscsih_sas_persist_clear_table
21803 - *
21804 - *
21805 - * @ioc
21806 - *
21807 - **/
21808  static void
21809  mptscsih_sas_persist_clear_table(void * arg)
21810  {
21811 @@ -1107,52 +233,76 @@ mptscsih_sas_persist_clear_table(void * 
21812         mptbase_sas_persist_operation(ioc, MPI_SAS_OP_CLEAR_NOT_PRESENT);
21813  }
21814  
21815 -/**
21816 - * mptsas_hotplug_print
21817 - *
21818 - *
21819 - * @ioc
21820 - * @hot_plug_info
21821 - * @msg_string
21822 - *
21823 - **/
21824 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
21825 +/* mptbase_sas_update_device_list -
21826 + * This is called from the work queue.
21827 + * Purpose is to called when a logical volume has been created, deleted,
21828 + * or status change.
21829 + * Since in SAS the phydisk can be moved to different location, we will need
21830 + * to refresh the device list by recreating it.
21831 + */
21832 +static void
21833 +mptscsih_sas_update_device_list(MPT_ADAPTER *ioc )
21834 +{
21835 +       sas_device_info_t *sasDevice, *pNext;
21836 +
21837 +       /*
21838 +        * Kill everything in the device list, then rediscover
21839 +        */
21840 +       list_for_each_entry_safe(sasDevice, pNext, &ioc->sasDeviceList, list) {
21841 +               list_del(&sasDevice->list);
21842 +               kfree(sasDevice);
21843 +               ioc->alloc_total -= sizeof (sas_device_info_t);
21844 +       }
21845 +
21846 +       if (ioc->sasPhyInfo != NULL) {
21847 +               kfree(ioc->sasPhyInfo);
21848 +               ioc->sasPhyInfo = NULL;
21849 +               ioc->alloc_total -=
21850 +                   ioc->numPhys * sizeof (sas_phy_info_t);
21851 +       }
21852 +       ioc->numPhys = 0;
21853 +
21854 +       /*
21855 +        *  Rescsan list
21856 +        */
21857 +       mpt_sas_get_info(ioc);
21858 +}
21859 +
21860  static void
21861  mptsas_hotplug_print(MPT_ADAPTER *ioc, struct mptsas_hotplug_event *hot_plug_info,  u32 lun, u8 * msg_string)
21862  {
21863 -       char *ds;
21864 +       char *ds = NULL;
21865         u32     id = hot_plug_info->id;
21866 -       u32     channel = hot_plug_info->channel;
21867  
21868 -       if ( id >= ioc->DevicesPerBus ) {
21869 -               printk(MYIOC_s_WARN_FMT "%s: Invalid id=%d, DevicesPerBus=%d\n",
21870 -                   ioc->name, __FUNCTION__, id, ioc->DevicesPerBus);
21871 +       if ( id > ioc->pfacts->MaxDevices ) {
21872 +               printk(MYIOC_s_WARN_FMT "%s: Invalid id=%d, MaxDevices=%d\n",
21873 +                   ioc->name, __FUNCTION__, id, ioc->pfacts->MaxDevices);
21874                 return;
21875         }
21876  
21877 -       if ( channel >= ioc->NumberOfBuses ) {
21878 -               printk(MYIOC_s_WARN_FMT
21879 -                   "%s: Invalid channel=%d, NumberOfBuses=%d\n",
21880 -                   ioc->name, __FUNCTION__, channel, ioc->NumberOfBuses);
21881 -               return;
21882 +       if (hot_plug_info->isRaid) {
21883 +               printk(MYIOC_s_INFO_FMT
21884 +                   "%s device, channel %d, id %d, lun %d\n",
21885 +                       ioc->name, msg_string,
21886 +                       hot_plug_info->channel,
21887 +                       id, lun);
21888 +       } else {
21889 +               if (hot_plug_info->device_info &
21890 +                   MPI_SAS_DEVICE_INFO_SSP_TARGET)
21891 +                       ds = "sas";
21892 +               if (hot_plug_info->device_info &
21893 +                   MPI_SAS_DEVICE_INFO_STP_TARGET)
21894 +                       ds = "stp";
21895 +               if (hot_plug_info->device_info &
21896 +                   MPI_SAS_DEVICE_INFO_SATA_DEVICE)
21897 +                       ds = "sata";
21898 +               printk(MYIOC_s_INFO_FMT
21899 +                   "%s %s device, channel %d, id %d, lun %d,"
21900 +                   "  phy %d\n", ioc->name, msg_string, ds,
21901 +                   hot_plug_info->channel, id, lun,
21902 +                   hot_plug_info->phy_id);
21903         }
21904 -
21905 -       if (hot_plug_info->device_info &
21906 -           MPI_SAS_DEVICE_INFO_SSP_TARGET)
21907 -               ds = "sas ";
21908 -       else if (hot_plug_info->device_info &
21909 -           MPI_SAS_DEVICE_INFO_STP_TARGET)
21910 -               ds = "stp ";
21911 -       else if (hot_plug_info->device_info &
21912 -           MPI_SAS_DEVICE_INFO_SATA_DEVICE)
21913 -               ds = "sata ";
21914 -       else
21915 -               ds = "";
21916 -
21917 -       printk(MYIOC_s_INFO_FMT
21918 -           "%s %sdevice, channel %d, id %d, lun %d,"
21919 -           "  phy %d\n", ioc->name, msg_string, ds,
21920 -           channel, id, lun,
21921 -           hot_plug_info->phy_id);
21922  }
21923  
21924  /*
21925 @@ -1167,32 +317,20 @@ mptsas_remove_target(MPT_ADAPTER *ioc, s
21926         struct Scsi_Host *shost = ioc->sh;
21927         unsigned long flags;
21928         struct scsi_device *sdev;
21929 -       static VirtDevice *pTarget;
21930         u32 channel, id;
21931 +       MPT_SCSI_HOST   *hd = (MPT_SCSI_HOST *)ioc->sh->hostdata;
21932  
21933         id = hot_plug_info->id;
21934 -       channel = hot_plug_info->channel;
21935 -
21936 -       if ( id >= ioc->DevicesPerBus ) {
21937 -               printk(MYIOC_s_WARN_FMT "%s: Invalid id=%d, DevicesPerBus=%d\n",
21938 -                   ioc->name, __FUNCTION__, id, ioc->DevicesPerBus);
21939 -               return;
21940 -       }
21941  
21942 -       if ( channel >= ioc->NumberOfBuses ) {
21943 -               printk(MYIOC_s_WARN_FMT
21944 -                   "%s: Invalid channel=%d, NumberOfBuses=%d\n",
21945 -                   ioc->name, __FUNCTION__, channel, ioc->NumberOfBuses);
21946 +       if ( id > ioc->pfacts->MaxDevices ) {
21947 +               printk(MYIOC_s_WARN_FMT "%s: Invalid id=%d, MaxDevices=%d\n",
21948 +                   ioc->name, __FUNCTION__, id, ioc->pfacts->MaxDevices);
21949                 return;
21950         }
21951  
21952 -       pTarget = mptsas_find_vdevice(ioc, channel, id);
21953 -       if (!pTarget)
21954 -               return;
21955 -
21956 -       pTarget->tflags &= ~MPT_TARGET_FLAGS_TLR_DONE;
21957 -
21958 +       mptsas_target_reset(ioc, hd->Targets[id]);
21959  
21960 +       channel = hot_plug_info->channel;
21961         spin_lock_irqsave(shost->host_lock, flags);
21962   restart:
21963         list_for_each_entry(sdev, &shost->__devices, siblings) {
21964 @@ -1208,46 +346,26 @@ mptsas_remove_target(MPT_ADAPTER *ioc, s
21965         spin_unlock_irqrestore(shost->host_lock, flags);
21966  }
21967  
21968 -/**
21969 - * mptsas_add_device
21970 - *
21971 - *
21972 - * @ioc
21973 - * @hot_plug_info
21974 - *
21975 - **/
21976  static void
21977  mptsas_add_device(MPT_ADAPTER *ioc, struct mptsas_hotplug_event *hot_plug_info,
21978      u32 lun)
21979  {
21980         u32     channel, id;
21981 +#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,14))
21982         struct scsi_device *sdev;
21983 +#else
21984 +        int    error;
21985 +#endif
21986  
21987         id = hot_plug_info->id;
21988  
21989 -       if ( id >= ioc->DevicesPerBus ) {
21990 -               printk(MYIOC_s_WARN_FMT "%s: Invalid id=%d, DevicesPerBus=%d\n",
21991 -                   ioc->name, __FUNCTION__, id, ioc->DevicesPerBus);
21992 +       if ( id > ioc->pfacts->MaxDevices ) {
21993 +               printk(MYIOC_s_WARN_FMT "%s: Invalid id=%d, MaxDevices=%d\n",
21994 +                   ioc->name, __FUNCTION__, id, ioc->pfacts->MaxDevices);
21995                 return;
21996         }
21997  
21998         channel = hot_plug_info->channel;
21999 -       if ( channel >= ioc->NumberOfBuses ) {
22000 -               printk(MYIOC_s_WARN_FMT
22001 -                   "%s: Invalid channel=%d, NumberOfBuses=%d\n",
22002 -                   ioc->name, __FUNCTION__, channel, ioc->NumberOfBuses);
22003 -               return;
22004 -       }
22005 -
22006 -       /*
22007 -        * avoid adding a device that is already present
22008 -        */
22009 -       sdev = scsi_device_lookup(ioc->sh, channel, id, lun);
22010 -       if (sdev) {
22011 -               scsi_device_put(sdev);
22012 -               return;
22013 -       }
22014 -
22015  #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,14))
22016         sdev = scsi_add_device(ioc->sh, channel, id, lun);
22017         if (!IS_ERR(sdev))
22018 @@ -1261,13 +379,6 @@ mptsas_add_device(MPT_ADAPTER *ioc, stru
22019  #endif
22020  }
22021  
22022 -/**
22023 - * scsilun_to_int
22024 - *
22025 - *
22026 - * @scsilun
22027 - *
22028 - **/
22029  static int scsilun_to_int(struct scsi_lun *scsilun)
22030  {
22031         int i;
22032 @@ -1298,170 +409,56 @@ mptsas_scan_target(MPT_ADAPTER *ioc, str
22033         u32             length, channel, id, lun, num_luns;
22034         u8              *data;
22035         u32             retries;
22036 -       int             rc;
22037 +       int             completion_code;
22038  
22039         id = hot_plug_info->id;
22040 -       channel = hot_plug_info->channel;
22041  
22042 -       if ( id > ioc->DevicesPerBus ) {
22043 -               printk(MYIOC_s_WARN_FMT "%s: Invalid id=%d, DevicesPerBus=%d\n",
22044 -                   ioc->name, __FUNCTION__, id, ioc->DevicesPerBus);
22045 -               return;
22046 -       }
22047 -
22048 -       if ( channel >= ioc->NumberOfBuses ) {
22049 -               printk(MYIOC_s_WARN_FMT
22050 -                   "%s: Invalid channel=%d, NumberOfBuses=%d\n",
22051 -                   ioc->name, __FUNCTION__, channel, ioc->NumberOfBuses);
22052 -               return;
22053 -       }
22054 -
22055 -       /*
22056 -        * Integrated RAID doesn't support REPORT_LUNS, it will timeout
22057 -        */
22058 -       if (ioc->raid_data.isRaid & (1 << id)) {
22059 -               mptsas_add_device(ioc, hot_plug_info, 0);
22060 +       if ( id > ioc->pfacts->MaxDevices ) {
22061 +               printk(MYIOC_s_WARN_FMT "%s: Invalid id=%d, MaxDevices=%d\n",
22062 +                   ioc->name, __FUNCTION__, id, ioc->pfacts->MaxDevices);
22063                 return;
22064         }
22065  
22066 -       /* initialize REPORT_LUN params */
22067 +       channel = hot_plug_info->channel;
22068         lun = 0;
22069 -       lun_data_len = 0;
22070 -       lun_data = NULL;
22071 -       lunp = NULL;
22072  
22073         /*
22074 -        * Test Unit Ready
22075 +        * Integrated RAID doesn't support luns greater than 0
22076          */
22077 -       iocmd.cmd = TEST_UNIT_READY;
22078 -       iocmd.bus = channel;
22079 -       iocmd.id = id;
22080 -       iocmd.lun = lun;
22081 -       iocmd.flags = 0;
22082 -       iocmd.data_dma = -1;
22083 -       iocmd.data = NULL;
22084 -       iocmd.size = 0;
22085 -       dinitprintk((MYIOC_s_INFO_FMT "Sending TURs to channel=%d id=%d \n",
22086 -               ioc->name, channel, id));
22087 -       for (retries = 0; retries < mpt_cmd_retry_count; retries++) {
22088 -               if (mptscsih_do_cmd(hd, &iocmd) < 0) {
22089 -                       dinitprintk((MYIOC_s_INFO_FMT
22090 -                           "TUR: mptscsih_do_cmd failed\n",
22091 -                           ioc->name));
22092 -                       goto tur_done;
22093 -               }
22094 -
22095 -               if (hd->pLocal == NULL) {
22096 -                       dinitprintk((MYIOC_s_INFO_FMT "TUR: no pLocal\n",
22097 -                           ioc->name));
22098 -                       goto tur_done;
22099 -               }
22100 -
22101 -               rc = hd->pLocal->completion;
22102 -               if (rc == MPT_SCANDV_GOOD) {
22103 -                       dinitprintk((MYIOC_s_INFO_FMT "TUR: succeeded\n",
22104 -                           ioc->name));
22105 -                       goto tur_done;
22106 -               } else if (rc == MPT_SCANDV_BUSY) {
22107 -                       dinitprintk((MYIOC_s_INFO_FMT "TUR: BUSY\n",
22108 -                               ioc->name));
22109 -                        msleep(1000);  /* sleep 1 second */
22110 -                       continue;
22111 -               } else if (rc == MPT_SCANDV_SENSE) {
22112 -                       u8 skey = hd->pLocal->sense[2] & 0x0F;
22113 -                       u8 asc = hd->pLocal->sense[12];
22114 -                       u8 ascq = hd->pLocal->sense[13];
22115 -                       dinitprintk((MYIOC_s_INFO_FMT
22116 -                           "SenseKey:ASC:ASCQ = (%x:%02x:%02x)\n",
22117 -                           ioc->name, skey, asc, ascq));
22118 -
22119 -                       if (skey == UNIT_ATTENTION) {
22120 -                               dinitprintk((MYIOC_s_INFO_FMT
22121 -                                   "TUR: UNIT ATTENTION\n",
22122 -                                   ioc->name));
22123 -                               continue;
22124 -                       } else if ((skey == NOT_READY) &&
22125 -                           (asc == 0x04)&&(ascq == 0x01)) {
22126 -                               dinitprintk((MYIOC_s_INFO_FMT
22127 -                                   "TUR: Becoming Ready\n",
22128 -                                   ioc->name));
22129 -                                    msleep(1000);  /* sleep 1 second */
22130 -                               continue;
22131 -                       }
22132 -               }
22133 +       if (hot_plug_info->isRaid) {
22134 +               mptsas_add_device(ioc, hot_plug_info, lun);
22135 +               return;
22136         }
22137  
22138 - tur_done:
22139 -
22140         lun_data_len = (MPT_LAST_LUN + 1) * sizeof(struct scsi_lun);
22141         lun_data = pci_alloc_consistent(ioc->pcidev, lun_data_len,
22142             &lun_data_dma);
22143         if (!lun_data)
22144 -               goto report_luns_done;
22145 +               goto out;
22146  
22147 -       /*
22148 -        * Report Luns
22149 -        */
22150         iocmd.cmd = REPORT_LUNS;
22151         iocmd.data_dma = lun_data_dma;
22152         iocmd.data = (u8 *)lun_data;
22153         iocmd.size = lun_data_len;
22154 +       iocmd.bus = channel;
22155 +       iocmd.id = id;
22156 +       iocmd.lun = lun;
22157         iocmd.flags = 0;
22158  
22159         /*
22160 -        * While loop for 10 sec retrying REPORT_LUNS, this is done
22161 +        * While loop for 3 sec retrying REPORT_LUNS, this is done
22162          * because some devices return MPI_SCSI_STATUS_BUSY for several
22163          * seconds.
22164          */
22165 -       dinitprintk((MYIOC_s_INFO_FMT
22166 -          "Sending REPORT_LUNS to channel=%d id=%d \n",
22167 -           ioc->name, channel, id));
22168 +//     for (retries = 0; retries < 3; retries++) {  /* EDM - TRY 10 */
22169         for (retries = 0; retries < 10; retries++) {
22170                 memset(lun_data, 0, lun_data_len);
22171 -               if (mptscsih_do_cmd(hd, &iocmd) < 0) {
22172 -                       dinitprintk((MYIOC_s_INFO_FMT
22173 -                           "RL: mptscsih_do_cmd failed\n", ioc->name));
22174 -                       goto report_luns_done;
22175 -               }
22176 -
22177 -               if (hd->pLocal == NULL) {
22178 -                       dinitprintk((MYIOC_s_INFO_FMT "RL: no pLocal\n",
22179 -                           ioc->name));
22180 -                       goto report_luns_done;
22181 -               }
22182 -
22183 -               rc = hd->pLocal->completion;
22184 -               if (rc == MPT_SCANDV_GOOD) {
22185 -                       dinitprintk((MYIOC_s_INFO_FMT "RL: succeeded\n",
22186 -                           ioc->name));
22187 -                       goto report_luns_done;
22188 -               } else if (rc == MPT_SCANDV_BUSY) {
22189 -                       dinitprintk((MYIOC_s_INFO_FMT "RL: BUSY\n", ioc->name));
22190 -                       msleep(1000);
22191 -                       continue;
22192 -               } else if (rc == MPT_SCANDV_SENSE) {
22193 -                       u8 skey = hd->pLocal->sense[2] & 0x0F;
22194 -                       u8 asc = hd->pLocal->sense[12];
22195 -                       u8 ascq = hd->pLocal->sense[13];
22196 -                       dinitprintk((MYIOC_s_INFO_FMT
22197 -                           "SenseKey:ASC:ASCQ = (%x:%02x:%02x)\n", ioc->name,
22198 -                           skey, asc, ascq));
22199 -
22200 -                       if (skey == UNIT_ATTENTION) {
22201 -                               dinitprintk((MYIOC_s_INFO_FMT
22202 -                                  "RL: UNIT ATTENTION\n", ioc->name));
22203 -                               continue;
22204 -                       } else if ((skey == NOT_READY) &&
22205 -                           (asc == 0x04)&&(ascq == 0x01)) {
22206 -                               dinitprintk((MYIOC_s_INFO_FMT
22207 -                                   "RL: Becoming Ready\n", ioc->name));
22208 -                                    msleep(1000);
22209 -                                     continue;
22210 -                       }
22211 -               }
22212 +               completion_code = mptscsih_do_cmd(hd, &iocmd);
22213 +               if (!completion_code)
22214 +                       break;
22215 +               msleep(1000);
22216         }
22217  
22218 - report_luns_done:
22219         /*
22220          * Attaching lun=0
22221          */
22222 @@ -1470,8 +467,6 @@ mptsas_scan_target(MPT_ADAPTER *ioc, str
22223         /*
22224          * Get the length from the first four bytes of lun_data.
22225          */
22226 -       if (!lun_data)
22227 -               goto out;
22228         data = (u8 *)lun_data;
22229         length = ((data[0] << 24) | (data[1] << 16) |
22230             (data[2] << 8) | (data[3] << 0));
22231 @@ -1501,91 +496,93 @@ mptsas_scan_target(MPT_ADAPTER *ioc, str
22232                     lun_data_dma);
22233  }
22234  
22235 -/**
22236 - * mptsas_hotplug_work
22237 - *
22238 - *
22239 - * @hot_plug_info
22240 - *
22241 - **/
22242  static void
22243  mptsas_hotplug_work(void *arg)
22244  {
22245         struct mptsas_hotplug_event *hot_plug_info = arg;
22246         MPT_ADAPTER             *ioc = hot_plug_info->ioc;
22247 -       u32                     id, channel;
22248 +       MPT_SCSI_HOST           *hd = (MPT_SCSI_HOST *)ioc->sh->hostdata;
22249 +       VirtDevice              *pTarget;
22250 +       u32                     id = hot_plug_info->id;
22251  
22252 -       id = hot_plug_info->id;
22253 -       channel = hot_plug_info->channel;
22254  
22255         dhotpprintk((MYIOC_s_WARN_FMT "Entering %s for channel=%d id=%d\n",
22256 -               ioc->name,__FUNCTION__, channel, id));
22257 +               ioc->name,__FUNCTION__, 
22258 +               hot_plug_info->channel, id));
22259 +
22260 +
22261 +       if ( id > ioc->pfacts->MaxDevices ) {
22262 +               printk(MYIOC_s_WARN_FMT "%s: Invalid id=%d, MaxDevices=%d\n",
22263 +                   ioc->name, __FUNCTION__, id, ioc->pfacts->MaxDevices);
22264 +               return;
22265 +       }
22266  
22267         down(&ioc->hot_plug_semaphore);
22268  
22269 -       /* If there has been a change to raid, then we need to
22270 -        * refresh the config raid data
22271 -        */
22272 -       if (hot_plug_info->refresh_raid_config_pages)
22273 -               mpt_findImVolumes(ioc);
22274 +       pTarget = hd->Targets[id];
22275 +       dhotpprintk((MYIOC_s_WARN_FMT "hot_plug_info=%p ioc=%p hd=%p pTarget=%p\n",
22276 +                   ioc->name, hot_plug_info, ioc, hd, pTarget));
22277  
22278         switch  (hot_plug_info->event_type) {
22279         case MPTSAS_DEL_DEVICE:
22280 -#if defined(CPQ_CIM)
22281 -               mptsas_del_device_component(ioc, channel, id);
22282 -               if (hot_plug_info->refresh_raid_config_pages)
22283 -                       mptsas_add_device_component_hotspare(ioc);
22284 -#endif
22285                 dhotpprintk((MYIOC_s_WARN_FMT
22286                     "MPTSAS_DEL_DEVICE: channel=%d id=%d\n",
22287 -                   ioc->name, channel, id));
22288 +                       ioc->name,
22289 +                       hot_plug_info->channel,
22290 +                       id));
22291 +               if (pTarget == NULL) {
22292 +                       dhotpprintk((MYIOC_s_WARN_FMT
22293 +                           "hot_plug id=%d not found in Targets array",
22294 +                               ioc->name,
22295 +                               id));
22296 +                       goto out;
22297 +               }
22298 +               pTarget->tflags &= ~MPT_TARGET_FLAGS_TLR_DONE;
22299 +               pTarget->tflags |= MPT_TARGET_FLAGS_DELETED;
22300                 mptsas_remove_target(ioc, hot_plug_info);
22301                 break;
22302  
22303         case MPTSAS_ADD_DEVICE:
22304 -#if defined(CPQ_CIM)
22305 -               if (ioc->raid_data.isRaid & (1 << id))
22306 -                       mptsas_add_device_component_ir(ioc, channel, id);
22307 -#endif
22308                 dhotpprintk((MYIOC_s_WARN_FMT
22309                     "MPTSAS_ADD_DEVICE: channel=%d id=%d\n",
22310 -                   ioc->name, channel, id));
22311 +                       ioc->name,
22312 +                       hot_plug_info->channel,
22313 +                       id));
22314 +               if (pTarget) {
22315 +                       dhotpprintk((MYIOC_s_WARN_FMT
22316 +                           "hot_plug id=%d already in Targets array",
22317 +                               ioc->name,
22318 +                               id));
22319 +                       goto out;
22320 +               }
22321                 mptsas_scan_target(ioc, hot_plug_info);
22322                 break;
22323 -#if defined(CPQ_CIM)
22324 -       case MPTSAS_ADD_INACTIVE_VOLUME:
22325 -               dhotpprintk((MYIOC_s_WARN_FMT
22326 -                   "MPTSAS_ADD_INACTIVE_VOLUME: channel=%d id=%d\n",
22327 -                   ioc->name, channel, id));
22328 -               mptsas_add_device_component_ir(ioc, channel, id);
22329 -               break;
22330 -       case MPTSAS_PHYSDISK_ADD:
22331 -               mptsas_add_device_component_single(ioc, channel, id);
22332 -               break;
22333 -#endif
22334         default:
22335                 dhotpprintk((MYIOC_s_WARN_FMT
22336 -                   "Unknown hot_plug event_type=%x: channel=%d id=%d "
22337 -                   " skipping\n", ioc->name, hot_plug_info->event_type,
22338 -                   channel, id));
22339 -               goto out;
22340 +                   "Unknown hot_plug event_type=%x: channel=%d id=%d\n",
22341 +                       ioc->name,
22342 +                       hot_plug_info->event_type,
22343 +                       hot_plug_info->channel,
22344 +                       id));
22345 +               break;
22346 +       }
22347 +
22348 +       /* If there has been a change to raid, then we need to
22349 +        * refresh the config raid data, and sas device link list
22350 +        */
22351 +       if (hot_plug_info->isRaid) {
22352 +               mpt_findImVolumes(ioc);
22353 +               mptscsih_sas_update_device_list(ioc);
22354         }
22355  
22356   out:
22357         dhotpprintk((MYIOC_s_WARN_FMT "%s: kfree hot_plug_info=%p\n",
22358 -           ioc->name,__FUNCTION__, hot_plug_info));
22359 +                   ioc->name,__FUNCTION__, hot_plug_info));
22360         kfree(hot_plug_info);
22361         up(&ioc->hot_plug_semaphore);
22362  }
22363  
22364 -/**
22365 - * mptsas_send_sas_event
22366 - *
22367 - *
22368 - * @ioc
22369 - * @sas_event_data
22370 - *
22371 - **/
22372 +
22373  static void
22374  mptsas_send_sas_event(MPT_ADAPTER *ioc,
22375                 EVENT_DATA_SAS_DEVICE_STATUS_CHANGE *sas_event_data)
22376 @@ -1610,11 +607,8 @@ mptsas_send_sas_event(MPT_ADAPTER *ioc,
22377         }
22378  
22379         switch (sas_event_data->ReasonCode) {
22380 -       case MPI_EVENT_SAS_DEV_STAT_RC_NOT_RESPONDING:
22381 -               mptsas_target_reset_queue(ioc, sas_event_data);
22382 -               break;
22383 -
22384         case MPI_EVENT_SAS_DEV_STAT_RC_ADDED:
22385 +       case MPI_EVENT_SAS_DEV_STAT_RC_NOT_RESPONDING:
22386                 ev = kmalloc(sizeof(*ev), GFP_ATOMIC);
22387                 if (!ev) {
22388                         printk(KERN_WARNING "mptsas: lost hotplug event\n");
22389 @@ -1642,7 +636,6 @@ mptsas_send_sas_event(MPT_ADAPTER *ioc,
22390                         ev->event_type = MPTSAS_DEL_DEVICE;
22391                 schedule_work(&ev->work);
22392                 break;
22393 -
22394         case MPI_EVENT_SAS_DEV_STAT_RC_NO_PERSIST_ADDED:
22395         /*
22396          * Persistent table is full.
22397 @@ -1652,7 +645,6 @@ mptsas_send_sas_event(MPT_ADAPTER *ioc,
22398                     (void *)ioc);
22399                 schedule_work(&ioc->mptscsih_persistTask);
22400                 break;
22401 -
22402         case MPI_EVENT_SAS_DEV_STAT_RC_SMART_DATA:
22403         /* TODO */
22404         case MPI_EVENT_SAS_DEV_STAT_RC_INTERNAL_DEVICE_RESET:
22405 @@ -1662,21 +654,12 @@ mptsas_send_sas_event(MPT_ADAPTER *ioc,
22406         }
22407  }
22408  
22409 -/**
22410 - * mptsas_send_raid_event
22411 - *
22412 - *
22413 - * @ioc
22414 - * @raid_event_data
22415 - *
22416 - **/
22417  static void
22418  mptsas_send_raid_event(MPT_ADAPTER *ioc,
22419                 EVENT_DATA_RAID *raid_event_data)
22420  {
22421         struct mptsas_hotplug_event *ev;
22422 -       int status = le32_to_cpu(raid_event_data->SettingsStatus);
22423 -       int state = (status >> 8) & 0xff;
22424 +       RAID_VOL0_STATUS * volumeStatus;
22425  
22426         if (ioc->bus_type != SAS)
22427                 return;
22428 @@ -1688,13 +671,11 @@ mptsas_send_raid_event(MPT_ADAPTER *ioc,
22429         }
22430  
22431         memset(ev,0,sizeof(struct mptsas_hotplug_event));
22432 +       INIT_WORK(&ev->work, mptsas_hotplug_work, ev);
22433         ev->ioc = ioc;
22434         ev->id = raid_event_data->VolumeID;
22435 -       ev->channel = raid_event_data->VolumeBus;
22436 -       ev->refresh_raid_config_pages = 1;
22437 +       ev->isRaid=1;
22438  
22439 -       devtprintk((KERN_INFO MYNAM ": VolumeID=%d Reason=%x received\n",
22440 -           ev->id, raid_event_data->ReasonCode));
22441         switch (raid_event_data->ReasonCode) {
22442         case MPI_EVENT_RAID_RC_PHYSDISK_DELETED:
22443                 ev->event_type = MPTSAS_ADD_DEVICE;
22444 @@ -1702,24 +683,6 @@ mptsas_send_raid_event(MPT_ADAPTER *ioc,
22445         case MPI_EVENT_RAID_RC_PHYSDISK_CREATED:
22446                 ev->event_type = MPTSAS_DEL_DEVICE;
22447                 break;
22448 -       case MPI_EVENT_RAID_RC_PHYSDISK_STATUS_CHANGED:
22449 -               switch (state) {
22450 -               case MPI_PD_STATE_ONLINE:
22451 -               case MPI_PD_STATE_NOT_COMPATIBLE:
22452 -                       ev->event_type = MPTSAS_PHYSDISK_ADD;
22453 -                       break;
22454 -               case MPI_PD_STATE_MISSING:
22455 -               case MPI_PD_STATE_OFFLINE_AT_HOST_REQUEST:
22456 -               case MPI_PD_STATE_FAILED_AT_HOST_REQUEST:
22457 -               case MPI_PD_STATE_OFFLINE_FOR_ANOTHER_REASON:
22458 -                       ev->event_type = MPTSAS_DEL_DEVICE;
22459 -                       break;
22460 -               default:
22461 -                       devtprintk((KERN_INFO MYNAM
22462 -                           ": ignoring this event! %d\n", __LINE__));
22463 -                       return;
22464 -               }
22465 -               break;
22466         case MPI_EVENT_RAID_RC_VOLUME_DELETED:
22467                 ev->event_type = MPTSAS_DEL_DEVICE;
22468                 break;
22469 @@ -1727,68 +690,18 @@ mptsas_send_raid_event(MPT_ADAPTER *ioc,
22470                 ev->event_type = MPTSAS_ADD_DEVICE;
22471                 break;
22472         case MPI_EVENT_RAID_RC_VOLUME_STATUS_CHANGED:
22473 -               switch (state) {
22474 -               case MPI_RAIDVOL0_STATUS_STATE_FAILED:
22475 -               case MPI_RAIDVOL0_STATUS_STATE_MISSING:
22476 -                       ev->event_type = MPTSAS_DEL_DEVICE;
22477 -                       break;
22478 -               case MPI_RAIDVOL0_STATUS_STATE_OPTIMAL:
22479 -               case MPI_RAIDVOL0_STATUS_STATE_DEGRADED:
22480 -                       ev->event_type = MPTSAS_ADD_DEVICE;
22481 -                       break;
22482 -               default:
22483 -                       devtprintk((KERN_INFO MYNAM
22484 -                           ": ignoring this event! %d\n", __LINE__));
22485 -                       return;
22486 -               }
22487 +               volumeStatus = (RAID_VOL0_STATUS *) &
22488 +                   raid_event_data->SettingsStatus;
22489 +               ev->event_type = (volumeStatus->State ==
22490 +                   MPI_RAIDVOL0_STATUS_STATE_FAILED) ?
22491 +                   MPTSAS_DEL_DEVICE : MPTSAS_ADD_DEVICE;
22492                 break;
22493         default:
22494 -               devtprintk((KERN_INFO MYNAM
22495 -                   ": ignoring this event! %d\n", __LINE__));
22496 -               return;
22497 +               break;
22498         }
22499 -       INIT_WORK(&ev->work, mptsas_hotplug_work, ev);
22500         schedule_work(&ev->work);
22501  }
22502  
22503 -#if defined(CPQ_CIM)
22504 -/*
22505 - * mptsas_send_ir2_event
22506 - *
22507 - * This handle exposing hidden disk when an inactive raid volume is added
22508 - */
22509 -static void
22510 -mptsas_send_ir2_event(MPT_ADAPTER *ioc, PTR_MPI_EVENT_DATA_IR2 ir2_data)
22511 -{
22512 -       struct mptsas_hotplug_event *ev;
22513 -
22514 -       if (ir2_data->ReasonCode !=
22515 -           MPI_EVENT_IR2_RC_FOREIGN_CFG_DETECTED)
22516 -               return;
22517 -
22518 -       ev = kmalloc(sizeof(*ev), GFP_ATOMIC);
22519 -       if (!ev)
22520 -               return;
22521 -       memset(ev, 0, sizeof(*ev));
22522 -       ev->ioc = ioc;
22523 -       ev->id = ir2_data->TargetID;
22524 -       ev->channel = ir2_data->Bus;
22525 -       ev->refresh_raid_config_pages = 1;
22526 -       ev->event_type = MPTSAS_ADD_INACTIVE_VOLUME;
22527 -
22528 -       INIT_WORK(&ev->work, mptsas_hotplug_work, ev);
22529 -       schedule_work(&ev->work);
22530 -};
22531 -#endif
22532 -
22533 -/**
22534 - * mptsas_event_process
22535 - *
22536 - *
22537 - * @ioc
22538 - * @reply
22539 - *
22540 - **/
22541  static int
22542  mptsas_event_process(MPT_ADAPTER *ioc, EventNotificationReply_t *reply)
22543  {
22544 @@ -1803,16 +716,10 @@ mptsas_event_process(MPT_ADAPTER *ioc, E
22545  
22546         switch (event) {
22547         case MPI_EVENT_SAS_DEVICE_STATUS_CHANGE:
22548 -#if defined(CPQ_CIM)
22549 -               ioc->csmi_change_count++;
22550 -#endif
22551                 mptsas_send_sas_event(ioc,
22552                         (EVENT_DATA_SAS_DEVICE_STATUS_CHANGE *)reply->Data);
22553                 break;
22554         case MPI_EVENT_INTEGRATED_RAID:
22555 -#if defined(CPQ_CIM)
22556 -               ioc->csmi_change_count++;
22557 -#endif
22558                 mptsas_send_raid_event(ioc,
22559                         (EVENT_DATA_RAID *)reply->Data);
22560                 break;
22561 @@ -1822,13 +729,6 @@ mptsas_event_process(MPT_ADAPTER *ioc, E
22562                     (void *)ioc);
22563                 schedule_work(&ioc->mptscsih_persistTask);
22564                 break;
22565 -#if defined(CPQ_CIM)
22566 -       case MPI_EVENT_IR2:
22567 -               ioc->csmi_change_count++;
22568 -               mptsas_send_ir2_event(ioc,
22569 -                   (PTR_MPI_EVENT_DATA_IR2)reply->Data);
22570 -               break;
22571 -#endif
22572         default:
22573                 rc = mptscsih_event_process(ioc, reply);
22574                 break;
22575 @@ -1855,13 +755,12 @@ mptsas_probe(struct pci_dev *pdev, const
22576         MPT_ADAPTER             *ioc;
22577         unsigned long            flags;
22578         int                      sz, ii;
22579 +       int                      numSGE = 0;
22580 +       int                      scale;
22581         int                      ioc_cap;
22582         u8                      *mem;
22583         int                     error=0;
22584         int                     r;
22585 -#if defined(CPQ_CIM)
22586 -       struct mptsas_portinfo  *port_info;
22587 -#endif
22588  
22589         if ((r = mpt_attach(pdev,id)) != 0)
22590                 return r;
22591 @@ -1874,27 +773,19 @@ mptsas_probe(struct pci_dev *pdev, const
22592         /*  Added sanity check on readiness of the MPT adapter.
22593          */
22594         if (ioc->last_state != MPI_IOC_STATE_OPERATIONAL) {
22595 -                 if(mpt_enable_deadioc_detect)
22596 -                    return 0;
22597 -                 else {
22598 -                  printk(MYIOC_s_WARN_FMT
22599 -                         "Skipping because it's not operational!\n", ioc->name);
22600 -                      error = -ENODEV;
22601 -               goto out_mptsas_probe;
22602 -                 }
22603 +               printk(MYIOC_s_WARN_FMT
22604 +                 "Skipping because it's not operational!\n",
22605 +                 ioc->name);
22606 +               error = -ENODEV;
22607 +               goto out_mptsas_probe;
22608         }
22609  
22610         if (!ioc->active) {
22611 -             if(mpt_enable_deadioc_detect)
22612 -                      return 0;
22613 -               else {
22614 -
22615 -              printk(MYIOC_s_WARN_FMT "Skipping because it's disabled!\n",
22616 +               printk(MYIOC_s_WARN_FMT "Skipping because it's disabled!\n",
22617                   ioc->name);
22618                 error = -ENODEV;
22619                 goto out_mptsas_probe;
22620         }
22621 -     }
22622  
22623         /*  Sanity check - ensure at least 1 port is INITIATOR capable
22624          */
22625 @@ -1906,8 +797,9 @@ mptsas_probe(struct pci_dev *pdev, const
22626         }
22627  
22628         if (!ioc_cap) {
22629 -               printk(MYIOC_s_WARN_FMT "Skipping ioc=%p because SCSI "
22630 -                   "Initiator mode is NOT enabled!\n", ioc->name, ioc);
22631 +               printk(MYIOC_s_WARN_FMT
22632 +                       "Skipping ioc=%p because SCSI Initiator mode is NOT enabled!\n",
22633 +                       ioc->name, ioc);
22634                 return 0;
22635         }
22636  
22637 @@ -1915,8 +807,8 @@ mptsas_probe(struct pci_dev *pdev, const
22638  
22639         if (!sh) {
22640                 printk(MYIOC_s_WARN_FMT
22641 -                   "Unable to register controller with SCSI subsystem\n",
22642 -                   ioc->name);
22643 +                       "Unable to register controller with SCSI subsystem\n",
22644 +                       ioc->name);
22645                 error = -1;
22646                 goto out_mptsas_probe;
22647          }
22648 @@ -1939,19 +831,49 @@ mptsas_probe(struct pci_dev *pdev, const
22649         else
22650                 sh->can_queue = ioc->req_depth;
22651         dinitprintk((MYIOC_s_INFO_FMT
22652 -           "mpt_can_queue=%d req_depth=%d can_queue=%d\n",
22653 -           ioc->name, mpt_can_queue, ioc->req_depth, sh->can_queue));
22654 +               "mpt_can_queue=%d req_depth=%d can_queue=%d\n",
22655 +               ioc->name, mpt_can_queue, ioc->req_depth,
22656 +               sh->can_queue));
22657  
22658 -       sh->max_id = ioc->DevicesPerBus;
22659 +       sh->max_id = ioc->pfacts->MaxDevices + 1;
22660  
22661         sh->max_lun = MPT_LAST_LUN + 1;
22662 -       sh->max_channel = ioc->NumberOfBuses - 1;
22663 +       sh->max_channel = 0;
22664         sh->this_id = ioc->pfacts[0].PortSCSIID;
22665  
22666         /* Required entry.
22667          */
22668         sh->unique_id = ioc->id;
22669 -       sh->sg_tablesize = ioc->sg_tablesize;
22670 +
22671 +       /* Verify that we won't exceed the maximum
22672 +        * number of chain buffers
22673 +        * We can optimize:  ZZ = req_sz/sizeof(SGE)
22674 +        * For 32bit SGE's:
22675 +        *  numSGE = 1 + (ZZ-1)*(maxChain -1) + ZZ
22676 +        *               + (req_sz - 64)/sizeof(SGE)
22677 +        * A slightly different algorithm is required for
22678 +        * 64bit SGEs.
22679 +        */
22680 +       scale = ioc->req_sz/(sizeof(dma_addr_t) + sizeof(u32));
22681 +       if (sizeof(dma_addr_t) == sizeof(u64)) {
22682 +               numSGE = (scale - 1) *
22683 +                 (ioc->facts.MaxChainDepth-1) + scale +
22684 +                 (ioc->req_sz - 60) / (sizeof(dma_addr_t) +
22685 +                 sizeof(u32));
22686 +       } else {
22687 +               numSGE = 1 + (scale - 1) *
22688 +                 (ioc->facts.MaxChainDepth-1) + scale +
22689 +                 (ioc->req_sz - 64) / (sizeof(dma_addr_t) +
22690 +                 sizeof(u32));
22691 +       }
22692 +
22693 +       if (numSGE < sh->sg_tablesize) {
22694 +               /* Reset this value */
22695 +               dprintk((MYIOC_s_INFO_FMT
22696 +                 "Resetting sg_tablesize to %d from %d\n",
22697 +                 ioc->name, numSGE, sh->sg_tablesize));
22698 +               sh->sg_tablesize = numSGE;
22699 +       }
22700  
22701  #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,13))
22702         /* Set the pci device pointer in Scsi_Host structure.
22703 @@ -1968,7 +890,7 @@ mptsas_probe(struct pci_dev *pdev, const
22704          * (with size equal to req_depth*PtrSz!)
22705          */
22706         sz = ioc->req_depth * sizeof(void *);
22707 -       mem = kmalloc(sz, GFP_KERNEL);
22708 +       mem = kmalloc(sz, GFP_ATOMIC);
22709         if (mem == NULL) {
22710                 error = -ENOMEM;
22711                 goto out_mptsas_probe;
22712 @@ -1978,26 +900,25 @@ mptsas_probe(struct pci_dev *pdev, const
22713         hd->ScsiLookup = (struct scsi_cmnd **) mem;
22714  
22715         dprintk((MYIOC_s_INFO_FMT "ScsiLookup @ %p, sz=%d\n",
22716 -           ioc->name, hd->ScsiLookup, sz));
22717 +                ioc->name, hd->ScsiLookup, sz));
22718  
22719 -       for (ii=0; ii < ioc->NumberOfBuses; ii++) {
22720 -               /* Allocate memory for the device structures.
22721 -                * A non-Null pointer at an offset
22722 -                * indicates a device exists.
22723 -                */
22724 -               sz = ioc->DevicesPerBus * sizeof(void *);
22725 -               mem = kmalloc(sz, GFP_KERNEL);
22726 -               if (mem == NULL) {
22727 -                       error = -ENOMEM;
22728 -                       goto out_mptsas_probe;
22729 -               }
22730 +       /* Allocate memory for the device structures.
22731 +        * A non-Null pointer at an offset
22732 +        * indicates a device exists.
22733 +        * max_id = 1 + maximum id (hosts.h)
22734 +        */
22735 +       sz = sh->max_id * sizeof(void *);
22736 +       mem = kmalloc(sz, GFP_ATOMIC);
22737 +       if (mem == NULL) {
22738 +               error = -ENOMEM;
22739 +               goto out_mptsas_probe;
22740 +       }
22741  
22742 -               memset(mem, 0, sz);
22743 -               ioc->Target_List[ii] = (struct _MPT_DEVICE *) mem;
22744 +       memset(mem, 0, sz);
22745 +       hd->Targets = (VirtDevice **) mem;
22746  
22747 -               dinitprintk((KERN_INFO " For Bus=%d, Target_List=%p sz=%d\n",
22748 -                   ii, mem, sz));
22749 -       }
22750 +       dprintk((KERN_INFO
22751 +         "  Targets @ %p, sz=%d\n", hd->Targets, sz));
22752  
22753         /* Clear the TM flags
22754          */
22755 @@ -2013,18 +934,13 @@ mptsas_probe(struct pci_dev *pdev, const
22756          */
22757         hd->cmdPtr = NULL;
22758  
22759 -       /* Initialize this IOC's  timers
22760 +       /* Initialize this SCSI Hosts' timers
22761          * To use, set the timer expires field
22762 -        * and add_timer. Used for internally
22763 -         * generated commands.
22764 +        * and add_timer
22765          */
22766 -       init_timer(&hd->InternalCmdTimer);
22767 -       hd->InternalCmdTimer.data = (unsigned long) hd;
22768 -       hd->InternalCmdTimer.function = mptscsih_InternalCmdTimer_expired;
22769 -
22770 -       init_timer(&ioc->TMtimer);
22771 -       ioc->TMtimer.data = (unsigned long) ioc;
22772 -       ioc->TMtimer.function = mptscsih_TM_timeout;
22773 +       init_timer(&hd->timer);
22774 +       hd->timer.data = (unsigned long) hd;
22775 +       hd->timer.function = mptscsih_timer_expired;
22776  
22777         init_MUTEX(&ioc->hot_plug_semaphore);
22778  
22779 @@ -2038,50 +954,24 @@ mptsas_probe(struct pci_dev *pdev, const
22780                     ioc, MPI_SAS_OP_CLEAR_ALL_PERSISTENT);
22781         }
22782  
22783 -       ddvprintk((MYIOC_s_INFO_FMT "mpt_pq_filter %x mpt_pq_filter %x\n",
22784 -           ioc->name, mpt_pq_filter, mpt_pq_filter));
22785 +       ddvprintk((MYIOC_s_INFO_FMT
22786 +               "mpt_pq_filter %x mpt_pq_filter %x\n",
22787 +               ioc->name,
22788 +               mpt_pq_filter,
22789 +               mpt_pq_filter));
22790  
22791         init_waitqueue_head(&hd->scandv_waitq);
22792         hd->scandv_wait_done = 0;
22793         hd->last_queue_full = 0;
22794  
22795 -        init_waitqueue_head(&hd->TM_waitq);
22796 -        hd->TM_wait_done = 0;
22797 -
22798 -       INIT_LIST_HEAD(&hd->target_reset_list);
22799 -
22800 -#if defined(CPQ_CIM)
22801 -       INIT_LIST_HEAD(&ioc->sas_device_info_list);
22802 -       init_MUTEX(&ioc->sas_device_info_mutex);
22803 -       port_info = kmalloc(sizeof(*port_info), GFP_KERNEL);
22804 -       if (port_info && !mptsas_sas_io_unit_pg0(ioc, port_info))
22805 -               ioc->num_ports = port_info->num_phys;
22806 -       kfree(port_info);
22807 -#endif
22808 -
22809         error = scsi_add_host (sh, &ioc->pcidev->dev);
22810         if(error) {
22811 -               dprintk((KERN_ERR MYNAM "scsi_add_host failed\n"));
22812 +               dprintk((KERN_ERR MYNAM
22813 +                 "scsi_add_host failed\n"));
22814                 goto out_mptsas_probe;
22815         }
22816  
22817         scsi_scan_host(sh);
22818 -
22819 -#if defined(CPQ_CIM)
22820 -       /*
22821 -        * Handling Inactive Volumes
22822 -        */
22823 -       if (!ioc->ir_firmware ||
22824 -           !ioc->raid_data.pIocPg2 ||
22825 -           !ioc->raid_data.pIocPg2->NumActiveVolumes)
22826 -       return 0;
22827 -
22828 -       for (ii = 0; ii < ioc->raid_data.pIocPg2->NumActiveVolumes; ii++)
22829 -               mptsas_add_device_component_ir(ioc,
22830 -                   ioc->raid_data.pIocPg2->RaidVolume[ii].VolumeBus,
22831 -                   ioc->raid_data.pIocPg2->RaidVolume[ii].VolumeID);
22832 -#endif
22833 -
22834         return 0;
22835  
22836  out_mptsas_probe:
22837 @@ -2122,17 +1012,17 @@ mptsas_init(void)
22838         show_mptmod_ver(my_NAME, my_VERSION);
22839  
22840         mptsasDoneCtx = mpt_register(mptscsih_io_done, MPTSAS_DRIVER);
22841 -       mptsasTaskCtx = mpt_register(mptsas_taskmgmt_complete, MPTSAS_DRIVER);
22842 +       mptsasTaskCtx = mpt_register(mptscsih_taskmgmt_complete, MPTSAS_DRIVER);
22843         mptsasInternalCtx = mpt_register(mptscsih_scandv_complete, MPTSAS_DRIVER);
22844  
22845         if (mpt_event_register(mptsasDoneCtx, mptsas_event_process) == 0) {
22846                 devtprintk((KERN_INFO MYNAM
22847 -                   ": Registered for sas IOC event notifications\n"));
22848 +                 ": Registered for sas IOC event notifications\n"));
22849         }
22850  
22851 -       if (mpt_reset_register(mptsasDoneCtx, mptsas_ioc_reset) == 0) {
22852 +       if (mpt_reset_register(mptsasDoneCtx, mptscsih_ioc_reset) == 0) {
22853                 dprintk((KERN_INFO MYNAM
22854 -                   ": Registered for IOC reset notifications\n"));
22855 +                 ": Registered for IOC reset notifications\n"));
22856         }
22857  
22858         return pci_register_driver(&mptsas_driver);
22859 @@ -2151,11 +1041,11 @@ mptsas_exit(void)
22860  
22861         mpt_reset_deregister(mptsasDoneCtx);
22862         dprintk((KERN_INFO MYNAM
22863 -           ": Deregistered for IOC reset notifications\n"));
22864 +         ": Deregistered for IOC reset notifications\n"));
22865  
22866         mpt_event_deregister(mptsasDoneCtx);
22867         dprintk((KERN_INFO MYNAM
22868 -           ": Deregistered for IOC event notifications\n"));
22869 +         ": Deregistered for IOC event notifications\n"));
22870  
22871         mpt_deregister(mptsasInternalCtx);
22872         mpt_deregister(mptsasTaskCtx);
22873 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptsas.h linux-2.6.9-55.0.12/drivers/message/fusion/mptsas.h
22874 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptsas.h  2007-12-21 11:40:54.000000000 +0100
22875 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptsas.h 1970-01-01 01:00:00.000000000 +0100
22876 @@ -1,166 +0,0 @@
22877 -/*
22878 - *  linux/drivers/message/fusion/mptsas.h
22879 - *      High performance SCSI + LAN / Fibre Channel device drivers.
22880 - *      For use with PCI chip/adapter(s):
22881 - *          LSIFC9xx/LSI409xx Fibre Channel
22882 - *      running LSI Logic Fusion MPT (Message Passing Technology) firmware.
22883 - *
22884 - *  Copyright (c) 1999-2007 LSI Logic Corporation
22885 - *  (mailto:mpt_linux_developer@lsi.com)
22886 - *
22887 - */
22888 -/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
22889 -/*
22890 -    This program is free software; you can redistribute it and/or modify
22891 -    it under the terms of the GNU General Public License as published by
22892 -    the Free Software Foundation; version 2 of the License.
22893 -
22894 -    This program is distributed in the hope that it will be useful,
22895 -    but WITHOUT ANY WARRANTY; without even the implied warranty of
22896 -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
22897 -    GNU General Public License for more details.
22898 -
22899 -    NO WARRANTY
22900 -    THE PROGRAM IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OR
22901 -    CONDITIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED INCLUDING, WITHOUT
22902 -    LIMITATION, ANY WARRANTIES OR CONDITIONS OF TITLE, NON-INFRINGEMENT,
22903 -    MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. Each Recipient is
22904 -    solely responsible for determining the appropriateness of using and
22905 -    distributing the Program and assumes all risks associated with its
22906 -    exercise of rights under this Agreement, including but not limited to
22907 -    the risks and costs of program errors, damage to or loss of data,
22908 -    programs or equipment, and unavailability or interruption of operations.
22909 -
22910 -    DISCLAIMER OF LIABILITY
22911 -    NEITHER RECIPIENT NOR ANY CONTRIBUTORS SHALL HAVE ANY LIABILITY FOR ANY
22912 -    DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22913 -    DAMAGES (INCLUDING WITHOUT LIMITATION LOST PROFITS), HOWEVER CAUSED AND
22914 -    ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
22915 -    TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
22916 -    USE OR DISTRIBUTION OF THE PROGRAM OR THE EXERCISE OF ANY RIGHTS GRANTED
22917 -    HEREUNDER, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGES
22918 -
22919 -    You should have received a copy of the GNU General Public License
22920 -    along with this program; if not, write to the Free Software
22921 -    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
22922 -*/
22923 -
22924 -#ifndef MPTSAS_H_INCLUDED
22925 -#define MPTSAS_H_INCLUDED
22926 -/*{-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
22927 -
22928 -struct mptscsih_target_reset {
22929 -       struct list_head        list;
22930 -       EVENT_DATA_SAS_DEVICE_STATUS_CHANGE sas_event_data;
22931 -       u8      target_reset_issued;
22932 -};
22933 -
22934 -enum mptsas_hotplug_action {
22935 -       MPTSAS_ADD_DEVICE,
22936 -       MPTSAS_DEL_DEVICE,
22937 -       MPTSAS_ADD_INACTIVE_VOLUME,
22938 -       MPTSAS_PHYSDISK_ADD,
22939 -};
22940 -
22941 -struct mptsas_hotplug_event {
22942 -       struct work_struct      work;
22943 -       MPT_ADAPTER             *ioc;
22944 -       enum mptsas_hotplug_action event_type;
22945 -       u64                     sas_address;
22946 -       u32                     channel;
22947 -       u32                     id;
22948 -       u32                     device_info;
22949 -       u16                     handle;
22950 -       u16                     parent_handle;
22951 -       u8                      phy_id;
22952 -       u8                      refresh_raid_config_pages;
22953 -};
22954 -
22955 -/*
22956 - * SAS topology structures
22957 - *
22958 - * The MPT Fusion firmware interface spreads information about the
22959 - * SAS topology over many manufacture pages, thus we need some data
22960 - * structure to collect it and process it for the SAS transport class.
22961 - */
22962 -
22963 -struct mptsas_devinfo {
22964 -       u16     handle;         /* unique id to address this device */
22965 -       u16     handle_parent;  /* unique id to address parent device */
22966 -       u16     handle_enclosure; /* enclosure identifier of the enclosure */
22967 -       u16     slot;           /* physical slot in enclosure */
22968 -       u8      phy_id;         /* phy number of parent device */
22969 -       u8      port_id;        /* sas physical port this device
22970 -                                  is assoc'd with */
22971 -       u8      id;             /* logical target id of this device */
22972 -       u32     phys_disk_num;  /* phys disk id, for csmi-ioctls */
22973 -       u8      channel;        /* logical bus number of this device */
22974 -       u64     sas_address;    /* WWN of this device,
22975 -                                  SATA is assigned by HBA,expander */
22976 -       u32     device_info;    /* bitfield detailed info about this device */
22977 -#if !defined(MPT_WIDE_PORT_API)
22978 -       u8      wide_port_enable;       /* when set, this is part of wide port*/
22979 -#endif
22980 -};
22981 -
22982 -/*
22983 - * Specific details on ports, wide/narrow
22984 - */
22985 -struct mptsas_portinfo_details{
22986 -#if !defined(MPT_WIDE_PORT_API)
22987 -       u8      port_id;        /* port number provided to transport */
22988 -       u8      rphy_id;        /* phy index used for reporting end device*/
22989 -       u32     device_info;    /* bitfield detailed info about this device */
22990 -#endif
22991 -       u16     num_phys;       /* number of phys beloing to this port */
22992 -       u64     phy_bitmask;    /* this needs extending to support 128 phys */
22993 -       struct sas_rphy *rphy; /* rphy for end devices */
22994 -#if defined(MPT_WIDE_PORT_API)
22995 -       struct sas_port *port;  /* transport layer port object */
22996 -#endif
22997 -       struct scsi_target *starget;
22998 -       struct mptsas_portinfo *port_info;
22999 -};
23000 -
23001 -struct mptsas_phyinfo {
23002 -       u8      phy_id;                 /* phy index */
23003 -       u8      port_id;                /* port number this phy is part of */
23004 -       u8      negotiated_link_rate;   /* nego'd link rate for this phy */
23005 -       u8      hw_link_rate;           /* hardware max/min phys link rate */
23006 -       u8      programmed_link_rate;   /* programmed max/min phy link rate */
23007 -#if defined(MPT_WIDE_PORT_API)
23008 -       u8      sas_port_add_phy;       /* flag to request sas_port_add_phy*/
23009 -#endif
23010 -#if defined(CPQ_CIM)
23011 -       u8      change_count;           /* change count of the phy */
23012 -       u8      port_flags;             /* info wrt host sas ports */
23013 -#endif
23014 -       u32     phy_info;               /* various info wrt the phy */
23015 -       struct mptsas_devinfo identify; /* point to phy device info */
23016 -       struct mptsas_devinfo attached; /* point to attached device info */
23017 -       struct sas_phy *phy;
23018 -       struct mptsas_portinfo *portinfo;
23019 -       struct mptsas_portinfo_details * port_details;
23020 -};
23021 -
23022 -struct mptsas_portinfo {
23023 -       struct list_head list;
23024 -       u16             handle;         /* unique id to address this */
23025 -       u16             num_phys;       /* number of phys */
23026 -       struct mptsas_phyinfo *phy_info;
23027 -};
23028 -
23029 -struct mptsas_enclosure {
23030 -       u64     enclosure_logical_id;   /* The WWN for the enclosure */
23031 -       u16     enclosure_handle;       /* unique id to address this */
23032 -       u16     flags;                  /* details enclosure management */
23033 -       u16     num_slot;               /* num slots */
23034 -       u16     start_slot;             /* first slot */
23035 -       u8      start_id;               /* starting logical target id */
23036 -       u8      start_channel;          /* starting logical channel id */
23037 -       u8      sep_id;                 /* SEP device logical target id */
23038 -       u8      sep_channel;            /* SEP channel logical channel id */
23039 -};
23040 -
23041 -/*}-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
23042 -#endif
23043 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptscsi.c linux-2.6.9-55.0.12/drivers/message/fusion/mptscsi.c
23044 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptscsi.c 2007-12-21 11:40:54.000000000 +0100
23045 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptscsi.c        2007-11-02 09:10:23.000000000 +0100
23046 @@ -3,8 +3,8 @@
23047   *      For use with LSI Logic PCI chip/adapter(s)
23048   *      running LSI Logic Fusion MPT (Message Passing Technology) firmware.
23049   *
23050 - *  Copyright (c) 1999-2007 LSI Logic Corporation
23051 - *  (mailto:mpt_linux_developer@lsi.com)
23052 + *  Copyright (c) 1999-2005 LSI Logic Corporation
23053 + *  (mailto:mpt_linux_developer@lsil.com)
23054   *
23055   *  $Id: mptscsih.c,v 1.1.2.4 2003/05/07 14:08:34 Exp $
23056   */
23057 @@ -74,7 +74,6 @@
23058  MODULE_AUTHOR(MODULEAUTHOR);
23059  MODULE_DESCRIPTION(my_NAME);
23060  MODULE_LICENSE("GPL");
23061 -MODULE_VERSION(my_VERSION);
23062  
23063  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
23064  
23065 @@ -83,6 +82,13 @@ typedef struct _BIG_SENSE_BUF {
23066  } BIG_SENSE_BUF;
23067  
23068  #define OEM_TLR_COMMAND                        0xC2
23069 +#define MPT_SCANDV_GOOD                        (0x00000000) /* must be 0 */
23070 +#define MPT_SCANDV_DID_RESET           (0x00000001)
23071 +#define MPT_SCANDV_SENSE               (0x00000002)
23072 +#define MPT_SCANDV_SOME_ERROR          (0x00000004)
23073 +#define MPT_SCANDV_SELECTION_TIMEOUT   (0x00000008)
23074 +#define MPT_SCANDV_ISSUE_SENSE         (0x00000010)
23075 +#define MPT_SCANDV_FALLBACK            (0x00000020)
23076  
23077  #define MPT_SCANDV_MAX_RETRIES         (10)
23078  
23079 @@ -116,37 +122,44 @@ typedef struct _dv_parameters {
23080  int            mptscsih_io_done(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, MPT_FRAME_HDR *r);
23081  static void    mptscsih_report_queue_full(struct scsi_cmnd *sc, SCSIIOReply_t *pScsiReply, SCSIIORequest_t *pScsiReq);
23082  int            mptscsih_taskmgmt_complete(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, MPT_FRAME_HDR *r);
23083 +
23084  static int     mptscsih_AddSGE(MPT_ADAPTER *ioc, struct scsi_cmnd *SCpnt,
23085                                  SCSIIORequest_t *pReq, int req_idx);
23086  static void    mptscsih_freeChainBuffers(MPT_ADAPTER *ioc, int req_idx);
23087  static void    mptscsih_copy_sense_data(struct scsi_cmnd *sc, MPT_SCSI_HOST *hd, MPT_FRAME_HDR *mf, SCSIIOReply_t *pScsiReply);
23088  static int     mptscsih_tm_pending_wait(MPT_SCSI_HOST * hd);
23089 -static int     SCPNT_TO_LOOKUP_IDX(struct scsi_cmnd *sc);
23090 -int            mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8 type, u8 channel, u8 id, u8 lun, int ctx2abort, ulong timeout);
23091 -static int     mptscsih_IssueTaskMgmt(MPT_SCSI_HOST *hd, u8 type, u8 channel, u8 id, u8 lun, int ctx2abort, ulong timeout);
23092 +static int     mptscsih_tm_wait_for_completion(MPT_SCSI_HOST * hd, ulong timeout );
23093 +static u32     SCPNT_TO_LOOKUP_IDX(struct scsi_cmnd *sc);
23094 +
23095 +int            mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8 type, u8 channel, u8 target, u8 lun, int ctx2abort, ulong timeout);
23096 +static int     mptscsih_IssueTaskMgmt(MPT_SCSI_HOST *hd, u8 type, u8 channel, u8 target, u8 lun, int ctx2abort, ulong timeout);
23097  
23098  int            mptscsih_ioc_reset(MPT_ADAPTER *ioc, int post_reset);
23099  int            mptscsih_event_process(MPT_ADAPTER *ioc, EventNotificationReply_t *pEvReply);
23100 -static void    mptscsih_initTarget(MPT_SCSI_HOST *hd, int bus, int id, u8 lun, char *data, int dlen);
23101 -static void    mptscsih_setTargetNegoParms(MPT_SCSI_HOST *hd, VirtDevice *pTarget, char byte56);
23102 -static void    mptscsih_no_negotiate(MPT_SCSI_HOST *hd, int id);
23103 -static int     mptscsih_writeIOCPage4(MPT_SCSI_HOST *hd, int id, int bus);
23104 +
23105 +static void    mptscsih_initTarget(MPT_SCSI_HOST *hd, int bus_id, int target_id, u8 lun, char *data, int dlen);
23106 +static void    mptscsih_setTargetNegoParms(MPT_SCSI_HOST *hd, VirtDevice *target, char byte56);
23107 +static void    mptscsih_set_dvflags(MPT_SCSI_HOST *hd, SCSIIORequest_t *pReq);
23108 +static void    mptscsih_setDevicePage1Flags (u8 width, u8 factor, u8 offset, int *requestedPtr, int *configurationPtr, u8 flags);
23109 +static void    mptscsih_no_negotiate(MPT_SCSI_HOST *hd, int target_id);
23110 +static int     mptscsih_writeSDP1(MPT_SCSI_HOST *hd, int portnum, int target, int flags);
23111 +static int     mptscsih_writeIOCPage4(MPT_SCSI_HOST *hd, int target_id, int bus);
23112  int            mptscsih_scandv_complete(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, MPT_FRAME_HDR *r);
23113 -void           mptscsih_InternalCmdTimer_expired(unsigned long data);
23114 +void           mptscsih_timer_expired(unsigned long data);
23115  static int     mptscsih_synchronize_cache(MPT_SCSI_HOST *hd, int portnum);
23116  
23117  #ifdef MPTSCSIH_ENABLE_DOMAIN_VALIDATION
23118  static int     mptscsih_do_raid(MPT_SCSI_HOST *hd, u8 action, INTERNAL_CMD *io);
23119  static void    mptscsih_domainValidation(void *hd);
23120 -static int     mptscsih_is_phys_disk(MPT_ADAPTER *ioc, int channel, int id);
23121 +static int     mptscsih_is_phys_disk(MPT_ADAPTER *ioc, int id);
23122  static void    mptscsih_qas_check(MPT_SCSI_HOST *hd, int id);
23123 -static int     mptscsih_doDv(MPT_SCSI_HOST *hd, int channel, int id);
23124 -static void    mptscsih_post_PendingMF_command(MPT_ADAPTER *ioc);
23125 +static int     mptscsih_doDv(MPT_SCSI_HOST *hd, int channel, int target);
23126  static void    mptscsih_dv_parms(MPT_SCSI_HOST *hd, DVPARAMETERS *dv,void *pPage);
23127 -static MPT_FRAME_HDR * mptscsih_search_PendingMF(MPT_ADAPTER *ioc, struct scsi_cmnd * sc);
23128  static void    mptscsih_fillbuf(char *buffer, int size, int index, int width);
23129 +static void    mptscsih_set_dvflags_raid(MPT_SCSI_HOST *hd, int id);
23130  #endif
23131 -static void    mpt_IssueTLR(MPT_SCSI_HOST *hd, VirtDevice *pTarget);
23132 +static void
23133 +mpt_IssueTLR(MPT_SCSI_HOST *hd, VirtDevice *pTarget);
23134  
23135  void           mptscsih_remove(struct pci_dev *);
23136  // This was changed in the 2.6.13 kernel
23137 @@ -169,6 +182,8 @@ int mptscsih_resume(struct pci_dev *pdev
23138   */
23139  static spinlock_t dvtaskQ_lock = SPIN_LOCK_UNLOCKED;
23140  static int dvtaskQ_active = 0;
23141 +static int dvtaskQ_release = 0;
23142 +static struct work_struct      dvTaskQ_task;
23143  #endif
23144  
23145  
23146 @@ -560,7 +575,6 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23147         }
23148  
23149         sc = hd->ScsiLookup[req_idx];
23150 -       hd->ScsiLookup[req_idx] = NULL;
23151         if (sc == NULL) {
23152                 MPIHeader_t *hdr = (MPIHeader_t *)mf;
23153  
23154 @@ -575,10 +589,6 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23155                 mptscsih_freeChainBuffers(ioc, req_idx);
23156                 return 1;
23157         }
23158 -       if ((unsigned char *)mf != sc->host_scribble) {
23159 -               mptscsih_freeChainBuffers(ioc, req_idx);
23160 -               return 1;
23161 -       }
23162  
23163         sc->result = DID_OK << 16;              /* Set default reply as OK */
23164         pScsiReq = (SCSIIORequest_t *) mf;
23165 @@ -601,12 +611,8 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23166                 u32      xfer_cnt;
23167                 u16      ioc_status;
23168                 u8       scsi_state, scsi_status;
23169 -#ifdef MPT_DEBUG_ERROR
23170 -               u8       ii, skey, asc, ascq;
23171 -#endif
23172 -               struct _MPT_DEVICE      *pMptTarget;
23173 -               VirtDevice      *pTarget;
23174 -               int      bus, id;
23175 +               VirtDevice              *pTarget;
23176 +               int      target;
23177  
23178                 ioc_status = le16_to_cpu(pScsiReply->IOCStatus) & MPI_IOCSTATUS_MASK;
23179                 scsi_state = pScsiReply->SCSIState;
23180 @@ -627,35 +633,18 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23181                         ioc_status = MPI_IOCSTATUS_SUCCESS;
23182                 }
23183  
23184 -#ifdef MPT_DEBUG_ERR
23185 -               if (ioc_status != MPI_IOCSTATUS_SCSI_DEVICE_NOT_THERE) {        /* 0x0043 */
23186 -                       derrprintk((KERN_NOTICE "Reply ha=%d id=%d lun=%d:\n"
23187 -                               "IOCStatus=%04x SCSIState=%02x SCSIStatus=%02x\n"
23188 -                               "resid=%d bufflen=%d xfer_cnt=%d\n",
23189 -                               ioc->id, pScsiReq->TargetID, pScsiReq->LUN[1],
23190 -                               ioc_status, scsi_state, scsi_status, sc->resid,
23191 -                               sc->request_bufflen, xfer_cnt));
23192 -               }
23193 -#endif
23194 +               dreplyprintk((KERN_NOTICE "Reply ha=%d id=%d lun=%d:\n"
23195 +                       "IOCStatus=%04xh SCSIState=%02xh SCSIStatus=%02xh\n"
23196 +                       "resid=%d bufflen=%d xfer_cnt=%d\n",
23197 +                       ioc->id, pScsiReq->TargetID, pScsiReq->LUN[1],
23198 +                       ioc_status, scsi_state, scsi_status, sc->resid,
23199 +                       sc->request_bufflen, xfer_cnt));
23200  
23201 -               if (scsi_state & MPI_SCSI_STATE_AUTOSENSE_VALID){
23202 +               if (scsi_state & MPI_SCSI_STATE_AUTOSENSE_VALID)
23203                         mptscsih_copy_sense_data(sc, hd, mf, pScsiReply);
23204  
23205 -#ifdef MPT_DEBUG_ERROR
23206 -                       skey = sc->sense_buffer[2];
23207 -                       asc  = sc->sense_buffer[12];
23208 -                       ascq = sc->sense_buffer[13];
23209 -                       derrprintk((MYIOC_s_WARN_FMT
23210 -                               "id=%d SenseKey:ASC:ASCQ = (%x:%02x:%02x) CDB:\n",
23211 -                               ioc->name, pScsiReq->TargetID,
23212 -                               skey, asc, ascq));
23213 -
23214 -                       for (ii=0; ii<pScsiReq->CDBLength; ii++) {
23215 -                               printk("%02x ", pScsiReq->CDB[ii]);
23216 -                       }
23217 -                       printk("\n");
23218 -#endif
23219 -  } else if (scsi_state & MPI_SCSI_STATE_RESPONSE_INFO_VALID && pScsiReply->ResponseInfo) {
23220 +               if (scsi_state & MPI_SCSI_STATE_RESPONSE_INFO_VALID &&
23221 +                   pScsiReply->ResponseInfo) {
23222                         printk(KERN_NOTICE "ha=%d id=%d lun=%d: "
23223                         "FCP_ResponseInfo=%08xh\n",
23224                         ioc->id, pScsiReq->TargetID, pScsiReq->LUN[1],
23225 @@ -670,13 +659,6 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23226                          * killing interrupt handler:-(
23227                          */
23228                         sc->result = SAM_STAT_BUSY;
23229 -#ifdef MPT_DEBUG_FAIL
23230 -                       derrprintk((MYIOC_s_ERR_FMT
23231 -                               "id=%d MPI_IOCSTATUS_BUSY\n",
23232 -                               ioc->name, pScsiReq->TargetID));
23233 -//                     panic ("IOCSTATUS_BUSY!!!!!\n");
23234 -#endif
23235 -
23236                         break;
23237  
23238                 case MPI_IOCSTATUS_SCSI_INVALID_BUS:            /* 0x0041 */
23239 @@ -688,15 +670,11 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23240                         /* Spoof to SCSI Selection Timeout! */
23241                         sc->result = DID_NO_CONNECT << 16;
23242  
23243 -                       bus = pScsiReq->Bus;
23244 -                       id = pScsiReq->TargetID;
23245 -                       if ( ioc->bus_type == SPI ) {
23246 -                               if (hd->sel_timeout[id] < 0xFFFF)
23247 -                                       hd->sel_timeout[pScsiReq->TargetID]++;
23248 -                       }
23249 +                       target = pScsiReq->TargetID;
23250 +                       if (hd->sel_timeout[target] < 0xFFFF)
23251 +                               hd->sel_timeout[pScsiReq->TargetID]++;
23252  
23253 -                       pMptTarget = ioc->Target_List[bus];
23254 -                       pTarget = (VirtDevice *)pMptTarget->Target[id];
23255 +                       pTarget = hd->Targets[target];
23256  
23257                         if ( pTarget ) {
23258                                 if (pTarget->tflags & MPT_TARGET_FLAGS_LED_ON) {
23259 @@ -710,8 +688,8 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23260                                         } else {
23261                                                 SEPMsg = (SEPRequest_t *)mf;
23262                                                 SEPMsg->Function = MPI_FUNCTION_SCSI_ENCLOSURE_PROCESSOR;
23263 -                                               SEPMsg->Bus = pTarget->bus;
23264 -                                               SEPMsg->TargetID = pTarget->id;
23265 +                                               SEPMsg->Bus = pTarget->bus_id;
23266 +                                               SEPMsg->TargetID = pTarget->target_id;
23267                                                 SEPMsg->Action = MPI_SEP_REQ_ACTION_WRITE_STATUS;
23268                                                 SEPMsg->SlotStatus = MPI_SEP_REQ_SLOTSTATUS_UNCONFIGURED;
23269                                                 pTarget->tflags &= ~MPT_TARGET_FLAGS_LED_ON;
23270 @@ -726,24 +704,24 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23271                 case MPI_IOCSTATUS_SCSI_IOC_TERMINATED:         /* 0x004B */
23272                         if ( ioc->bus_type == SAS ) {
23273                                 u16      status = le16_to_cpu(pScsiReply->IOCStatus);
23274 -                               u32      log_info = le32_to_cpu(mr->u.reply.IOCLogInfo);
23275 -//                             sc->result = DID_RESET << 16;
23276 -                               sc->result = DID_SOFT_ERROR << 16;
23277                                 if (status & MPI_IOCSTATUS_FLAG_LOG_INFO_AVAILABLE) {
23278 -                                       if ((log_info & 0xFFFF0000) ==
23279 -                                               SAS_LOGINFO_NEXUS_LOSS) {
23280 +                                       u32      log_info = le32_to_cpu(mr->u.reply.IOCLogInfo);
23281 +                                       log_info &= 0xFFFF0000;  /* mask subcodes */
23282 +                                       dreplyprintk((KERN_NOTICE "IOC_TERMINATED: ha=%d id=%d lun=%d:\n"
23283 +                       "IOCStatus=%04xh SCSIState=%02xh SCSIStatus=%02xh "
23284 +                       "loginfo=%08x\n"
23285 +                       ioc->id, pScsiReq->TargetID, pScsiReq->LUN[1],
23286 +                       status, scsi_state, scsi_status, log_info));
23287 +                                       if (log_info == SAS_LOGINFO_NEXUS_LOSS) {
23288                                                 sc->result = (DID_BUS_BUSY << 16);
23289 +                                               break;
23290                                         }
23291 +                               } else {
23292 +                                       dreplyprintk((KERN_NOTICE "IOC_TERMINATED: ha=%d id=%d lun=%d:\n"
23293 +                       "IOCStatus=%04xh SCSIState=%02xh SCSIStatus=%02xh\n",
23294 +                       ioc->id, pScsiReq->TargetID, pScsiReq->LUN[1],
23295 +                       status, scsi_state, scsi_status));
23296                                 }
23297 -                               derrprintk((KERN_NOTICE "IOC_TERMINATED: "
23298 -                                       "ha=%d id=%d lun=%d "
23299 -                                       "IOCStatus=%04x SCSIState=%02x\n"
23300 -                                       "SCSIStatus=%02x LogInfo=%08x "
23301 -                                       "sc->result=%08x sc=%p\n",
23302 -                                       ioc->id, pScsiReq->TargetID,
23303 -                                       pScsiReq->LUN[1], status, scsi_state,
23304 -                                       scsi_status, log_info, sc->result, sc));
23305 -                               break;
23306                         }  /* allow non-SAS & non-NEXUS_LOSS to drop into below code */
23307  
23308                 case MPI_IOCSTATUS_SCSI_TASK_TERMINATED:        /* 0x0048 */
23309 @@ -775,7 +753,7 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23310                         } else {
23311                                 sc->result = DID_SOFT_ERROR << 16;
23312                         }
23313 -//                     derrprintk((KERN_NOTICE "RESIDUAL_MISMATCH: result=%x on id=%d\n", sc->result, sc->target));
23314 +//                     dreplyprintk((KERN_NOTICE "RESIDUAL_MISMATCH: result=%x on id=%d\n", sc->result, sc->target));
23315                         printk("RESIDUAL_MISMATCH: result=%x on id=%d\n", sc->result, sc->device->id);
23316                         break;
23317  #else
23318 @@ -784,7 +762,7 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23319                                 sc->result=DID_SOFT_ERROR << 16;
23320                         else /* Sufficient data transfer occurred */
23321                                 sc->result = (DID_OK << 16) | scsi_status;
23322 -                       derrprintk((KERN_NOTICE
23323 +                       dreplyprintk((KERN_NOTICE 
23324                             "RESIDUAL_MISMATCH: result=%x on id=%d\n", sc->result, sc->device->id));
23325                         break;
23326  #endif
23327 @@ -804,9 +782,7 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23328                                                 sc->result = SAM_STAT_BUSY;
23329                                         else
23330                                                 sc->result = DID_SOFT_ERROR << 16;
23331 - derrprintk((KERN_NOTICE " xfer_cnt=%d < sc->underflow=%d result=%08x\n",xfer_cnt, sc->underflow, sc->result));
23332 -
23333 -                                 }
23334 +                               }
23335                                 if (scsi_state & (MPI_SCSI_STATE_AUTOSENSE_FAILED | MPI_SCSI_STATE_NO_SCSI_STATUS)) {
23336                                         /* What to do?
23337                                         */
23338 @@ -818,6 +794,9 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23339                                 }
23340                         }
23341  
23342 +                       dreplyprintk((KERN_NOTICE "  sc->underflow={report ERR if < %02xh bytes xfer'd}\n",
23343 +                                       sc->underflow));
23344 +                       dreplyprintk((KERN_NOTICE "  ActBytesXferd=%02xh\n", xfer_cnt));
23345                         /* Report Queue Full
23346                          */
23347                         if (scsi_status == MPI_SCSI_STATUS_TASK_SET_FULL)
23348 @@ -896,18 +875,9 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23349                         break;
23350  
23351                 }       /* switch(ioc_status) */
23352 -               if (ioc_status != MPI_IOCSTATUS_SCSI_DATA_UNDERRUN) {
23353 -                       derrprintk((KERN_NOTICE "ha=%d id=%d lun=%d "
23354 -                               "IOCStatus=%04x SCSIState=%02x\n"
23355 -                               "SCSIStatus=%02x "
23356 -                               "sc->result=%08x sc=%p\n",
23357 -                               ioc->id, pScsiReq->TargetID,
23358 -                               pScsiReq->LUN[1], ioc_status,
23359 -                               scsi_state, scsi_status, sc->result,
23360 -                               sc));
23361 -               }
23362  
23363 -              } /* end of address reply case */
23364 +               dreplyprintk((KERN_NOTICE "  sc->result is %08xh\n", sc->result));
23365 +       } /* end of address reply case */
23366  
23367         /* Unmap the DMA buffers, if any. */
23368         if (sc->use_sg) {
23369 @@ -918,7 +888,8 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_F
23370                                 sc->request_bufflen, sc->sc_data_direction);
23371         }
23372  
23373 -       sc->host_scribble = NULL;
23374 +       hd->ScsiLookup[req_idx] = NULL;
23375 +
23376         sc->scsi_done(sc);              /* Issue the command callback */
23377  
23378         /* Free Chain buffers */
23379 @@ -945,9 +916,7 @@ mptscsih_flush_running_cmds(MPT_SCSI_HOS
23380         int              ii;
23381         int              max = ioc->req_depth;
23382  
23383 -
23384 -drsprintk((MYIOC_s_WARN_FMT ": %s entered\n",ioc->name, __FUNCTION__));
23385 -
23386 +       dprintk((KERN_INFO MYNAM ": flush_ScsiLookup called\n"));
23387         for (ii= 0; ii < max; ii++) {
23388                 if ((SCpnt = hd->ScsiLookup[ii]) != NULL) {
23389  
23390 @@ -959,24 +928,8 @@ drsprintk((MYIOC_s_WARN_FMT ": %s entere
23391                         hd->ScsiLookup[ii] = NULL;
23392  
23393                         mf = MPT_INDEX_2_MFPTR(ioc, ii);
23394 -
23395 -/*                     drsprintk((MYIOC_s_WARN_FMT "flush mf=%p sc=%p\n",
23396 -                               ioc->name, mf, SCpnt));
23397 -                       DBG_DUMP_RESET_REQUEST_FRAME(ioc, mf) */
23398 -
23399 -
23400 -                       /* Free Chain buffers */
23401 -                       mptscsih_freeChainBuffers(ioc, ii);
23402 -
23403 -                       /* Free Message frames */
23404 -                       mpt_free_msg_frame(ioc, mf);
23405 -
23406 -                       if ((unsigned char *)mf != SCpnt->host_scribble) {
23407 -                     drsprintk(( "%s Skipping scsi_done mf=%p host_scribble=%p\n",
23408 -                         __FUNCTION__, mf, SCpnt->host_scribble));
23409 -
23410 -                               continue;
23411 -                       }
23412 +                       dmfprintk(( "flush: ScsiDone (mf=%p,sc=%p)\n",
23413 +                                       mf, SCpnt));
23414  
23415                         /* Set status, free OS resources (SG DMA buffers)
23416                          * Do OS callback
23417 @@ -993,14 +946,20 @@ drsprintk((MYIOC_s_WARN_FMT ": %s entere
23418                                         SCpnt->request_bufflen,
23419                                         SCpnt->sc_data_direction);
23420                         }
23421 -                        SCpnt->result = (DID_BUS_BUSY << 16);
23422 +                       SCpnt->result = DID_RESET << 16;
23423                         SCpnt->host_scribble = NULL;
23424 +
23425 +                       /* Free Chain buffers */
23426 +                       mptscsih_freeChainBuffers(ioc, ii);
23427 +
23428 +                       /* Free Message frames */
23429 +                       mpt_free_msg_frame(ioc, mf);
23430 +
23431                         SCpnt->scsi_done(SCpnt);        /* Issue the command callback */
23432                 }
23433         }
23434  
23435 -drsprintk((MYIOC_s_WARN_FMT ": %s exiting\n", ioc->name, __FUNCTION__));
23436 -
23437 +       return;
23438  }
23439  
23440  /*
23441 @@ -1010,7 +969,7 @@ drsprintk((MYIOC_s_WARN_FMT ": %s exitin
23442   *             Do NOT access the referenced scsi_cmnd structure or
23443   *             members. Will cause either a paging or NULL ptr error.
23444   *     @hd: Pointer to a SCSI HOST structure
23445 - *     @id: target id
23446 + *     @target: target id
23447   *     @lun: lun
23448   *
23449   *     Returns: None.
23450 @@ -1018,47 +977,43 @@ drsprintk((MYIOC_s_WARN_FMT ": %s exitin
23451   *     Called from slave_destroy.
23452   */
23453  static void
23454 -mptscsih_search_running_cmds(MPT_SCSI_HOST *hd, uint id, uint lun)
23455 +mptscsih_search_running_cmds(MPT_SCSI_HOST *hd, uint target, uint lun)
23456  {
23457 -       MPT_ADAPTER             *ioc = hd->ioc;
23458         SCSIIORequest_t *mf = NULL;
23459         int              ii;
23460 -       int              max = ioc->req_depth;
23461 +       int              max = hd->ioc->req_depth;
23462         struct scsi_cmnd *sc;
23463  
23464 -       dsprintk((KERN_INFO MYNAM ": search_running id %d lun %d max %d\n",
23465 -                       id, lun, max));
23466 +       dsprintk((KERN_INFO MYNAM ": search_running target %d lun %d max %d\n",
23467 +                       target, lun, max));
23468  
23469         for (ii=0; ii < max; ii++) {
23470                 if ((sc = hd->ScsiLookup[ii]) != NULL) {
23471  
23472 -                       mf = (SCSIIORequest_t *)MPT_INDEX_2_MFPTR(ioc, ii);
23473 +                       mf = (SCSIIORequest_t *)MPT_INDEX_2_MFPTR(hd->ioc, ii);
23474  
23475                         dsprintk(( "search_running: found (sc=%p, mf = %p)\n",
23476                                         hd->ScsiLookup[ii], mf));
23477                         if (mf == NULL)
23478                                 continue;
23479 -                       dsprintk(( "search_running: found (sc=%p, mf = %p) id %d, lun %d \n",
23480 +                       dsprintk(( "search_running: found (sc=%p, mf = %p) target %d, lun %d \n",
23481                                         hd->ScsiLookup[ii], mf, mf->TargetID, mf->LUN[1]));
23482  
23483 -                       if ((mf->TargetID != ((u8)id)) || (mf->LUN[1] != ((u8) lun)))
23484 +                       if ((mf->TargetID != ((u8)target)) || (mf->LUN[1] != ((u8) lun)))
23485                                 continue;
23486  
23487                         /* Cleanup
23488                          */
23489                         hd->ScsiLookup[ii] = NULL;
23490 -                       mptscsih_freeChainBuffers(ioc, ii);
23491 -                       mpt_free_msg_frame(ioc, (MPT_FRAME_HDR *)mf);
23492 -                       if ((unsigned char *)mf != sc->host_scribble) {
23493 -                               continue;
23494 -                       }
23495 +                       mptscsih_freeChainBuffers(hd->ioc, ii);
23496 +                       mpt_free_msg_frame(hd->ioc, (MPT_FRAME_HDR *)mf);
23497                         if (sc->use_sg) {
23498 -                               pci_unmap_sg(ioc->pcidev,
23499 +                               pci_unmap_sg(hd->ioc->pcidev,
23500                                 (struct scatterlist *) sc->request_buffer,
23501                                         sc->use_sg,
23502                                         sc->sc_data_direction);
23503                         } else if (sc->request_bufflen) {
23504 -                               pci_unmap_single(ioc->pcidev,
23505 +                               pci_unmap_single(hd->ioc->pcidev,
23506                                         sc->SCp.dma_handle,
23507                                         sc->request_bufflen,
23508                                         sc->sc_data_direction);
23509 @@ -1068,8 +1023,8 @@ mptscsih_search_running_cmds(MPT_SCSI_HO
23510                         sc->scsi_done(sc);
23511                 }
23512         }
23513 -       dsprintk((KERN_INFO MYNAM ": search_running id %d lun %d completed\n",
23514 -                       id, lun));
23515 +       dsprintk((KERN_INFO MYNAM ": search_running target %d lun %d completed\n",
23516 +                       target, lun));
23517         return;
23518  }
23519  
23520 @@ -1169,66 +1124,9 @@ mptscsih_sendIOCInit(MPT_SCSI_HOST *hd)
23521  }
23522  
23523  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
23524 -/*     mptscsih_TM_timeout - Call back for timeout on a
23525 - *     task management request.
23526 - *     @data: Pointer to MPT_ADAPTER recast as an unsigned long
23527 - *
23528 - */
23529 -void mptscsih_TM_timeout(unsigned long data)
23530 -{
23531 -       MPT_ADAPTER     *ioc=(MPT_ADAPTER *)data;
23532 -       MPT_SCSI_HOST   *hd =(MPT_SCSI_HOST *)ioc->sh->hostdata;
23533 -       int              retval;
23534 -       u32              ioc_state;
23535 -
23536 -       dtmprintk((KERN_INFO MYNAM ": %s: mptscsih_TM_timeout: "
23537 -                  "TM request timed out!\n", ioc->name));
23538 -
23539 -       /* Delete the timer that triggered this callback.
23540 -        * Remark: DEL_TIMER checks to make sure timer is active
23541 -        * before deleting.
23542 -        */
23543 -       del_timer(&ioc->TMtimer);
23544 -
23545 -       mpt_free_msg_frame(ioc, ioc->tmPtr);
23546 -
23547 -       ioc->tmPtr = NULL;
23548 -
23549 -       dtmprintk((MYIOC_s_WARN_FMT "%s: Calling mpt_SendIocReset MUR!\n",
23550 -               ioc->name, __FUNCTION__));
23551 -       if ((retval = mpt_SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, NO_SLEEP)) != 0) {
23552 -               ioc_state = mpt_GetIocState(ioc, 0);
23553 -               dfailprintk((MYIOC_s_WARN_FMT "%s: IOC MUR failed! ioc_state=%08x\n",
23554 -                       ioc->name, __FUNCTION__, ioc_state));
23555 -//             panic ("IOC MUR Failed");
23556 -               ioc->IOCResetInProgress = 0;
23557 -
23558 -               if ((retval = mpt_HardResetHandler(ioc, NO_SLEEP)) < 0){
23559 -                       printk(KERN_WARNING "%s: %s: HardResetHandler FAILED!!\n",
23560 -                               ioc->name, __FUNCTION__);
23561 -               } else {
23562 -                       dtmprintk((MYIOC_s_WARN_FMT "%s: HardResetHandler succeeded!!\n",
23563 -                               ioc->name, __FUNCTION__));
23564 -               }
23565 -       } else {
23566 -               dtmprintk((MYIOC_s_WARN_FMT "IOC MUR succeeded\n", ioc->name));
23567 -               mptscsih_flush_running_cmds(hd);
23568 -               dtmprintk((MYIOC_s_WARN_FMT "Calling do_ioc_recovery! \n", ioc->name));
23569 -               if ((retval = mpt_do_ioc_recovery(ioc, MPT_HOSTEVENT_IOC_RECOVER, NO_SLEEP)) != 0) {
23570 -                       dfailprintk((MYIOC_s_ERR_FMT "%s: (%d) ioc_recovery failed\n", ioc->name, __FUNCTION__, retval));
23571 -               } else {
23572 -                       dtmprintk((MYIOC_s_WARN_FMT "%s:Successful do_ioc_recovery! \n", ioc->name, __FUNCTION__));
23573 -               }
23574 -       }
23575 -       hd->TM_wait_done = 1;
23576 -       wake_up(&hd->TM_waitq);
23577 -}
23578 -
23579 -/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
23580  /*     mptscsih_writeFCPortPage3  - write FC Port Page 3
23581   *     @hd: Pointer to a SCSI Host Structure
23582 - *     @bus: write FC Port Page 3 for this bus
23583 - *     @id: write FC Port Page 3 for this target ID
23584 + *     @target_id: write FC Port Page 3 for this target ID
23585   *
23586   *     Return: -EAGAIN if unable to obtain a Message Frame
23587   *             or 0 if success.
23588 @@ -1236,7 +1134,7 @@ void mptscsih_TM_timeout(unsigned long d
23589   *     Remark: We do not wait for a return, write pages sequentially.
23590   */
23591  static int
23592 -mptscsih_writeFCPortPage3(MPT_SCSI_HOST *hd, int bus, int id)
23593 +mptscsih_writeFCPortPage3(MPT_SCSI_HOST *hd, int target_id)
23594  {
23595         MPT_ADAPTER             *ioc = hd->ioc;
23596         Config_t                *pReq;
23597 @@ -1247,7 +1145,6 @@ mptscsih_writeFCPortPage3(MPT_SCSI_HOST 
23598         u32                      frameOffset;
23599         u32                      flagsLength;
23600         int                      ii;
23601 -       struct _MPT_DEVICE      *pMptTarget;
23602         VirtDevice              *pTarget;
23603  
23604         /* Get a MF for this command.
23605 @@ -1287,10 +1184,9 @@ mptscsih_writeFCPortPage3(MPT_SCSI_HOST 
23606                 pReq->Header.PageType = MPI_CONFIG_PAGETYPE_FC_PORT |
23607                                 MPI_CONFIG_PAGEATTR_PERSISTENT;
23608         pReq->PageAddress = cpu_to_le32(MPI_FC_PORT_PGAD_FORM_INDEX |
23609 -                                       id);
23610 +                                       target_id);
23611  
23612 -       pMptTarget = ioc->Target_List[bus];
23613 -       pTarget = pMptTarget->Target[id];
23614 +       pTarget = hd->Targets[target_id];
23615  
23616         FCPort3->Header.PageVersion = MPI_FCPORTPAGE3_PAGEVERSION;
23617         FCPort3->Header.PageLength = sizeof(FCPortPage3_t) / 4;
23618 @@ -1299,8 +1195,8 @@ mptscsih_writeFCPortPage3(MPT_SCSI_HOST 
23619                                    MPI_CONFIG_PAGEATTR_PERSISTENT;
23620                 FCPort3->Entry[0].PhysicalIdentifier.WWN.WWPN = pTarget->WWPN;
23621                 FCPort3->Entry[0].PhysicalIdentifier.WWN.WWNN = pTarget->WWNN;
23622 -       FCPort3->Entry[0].TargetID = id;
23623 -       FCPort3->Entry[0].Bus = bus;
23624 +               FCPort3->Entry[0].TargetID = pTarget->target_id;
23625 +               FCPort3->Entry[0].Bus = pTarget->bus_id;
23626         FCPort3->Entry[0].Flags = cpu_to_le16(MPI_PERSISTENT_FLAGS_ENTRY_VALID);
23627  
23628         /* Add a SGE to the config request.
23629 @@ -1308,7 +1204,7 @@ mptscsih_writeFCPortPage3(MPT_SCSI_HOST 
23630         flagsLength = MPT_SGE_FLAGS_SSIMPLE_READ | sizeof(FCPortPage3_t);
23631         mpt_add_sge((char *)&pReq->PageBufferSGE, flagsLength, dataDma);
23632  
23633 -       drsprintk((MYIOC_s_INFO_FMT "writeFCPortPage3: bus=%d id=%d\n", ioc->name, , bus, id));
23634 +       drsprintk((MYIOC_s_INFO_FMT "writeFCPortPage3: target=%d\n", ioc->name, target_id));
23635  
23636         mpt_put_msg_frame(ioc->DoneCtx, ioc, mf);
23637  
23638 @@ -1320,7 +1216,7 @@ mptscsih_writeFCPortPage3(MPT_SCSI_HOST 
23639   *     mptscsih_readFCDevicePage0 - returns FC Device Page 0 data
23640   *     @ioc: Pointer to MPT_ADAPTER structure
23641   *     @bus: bus id
23642 - *     @id: target id
23643 + *     @targetId: target id
23644   *     @fcDevicePage: FC Device Page 0 data
23645   *
23646   *     Returns count of number bytes copied into @fcDevicePage
23647 @@ -1328,7 +1224,7 @@ mptscsih_writeFCPortPage3(MPT_SCSI_HOST 
23648   */
23649  
23650  int
23651 -mptscsih_readFCDevicePage0(MPT_ADAPTER *ioc, u8 bus, u8 id, pFCDevicePage0_t fcDevicePage)
23652 +mptscsih_readFCDevicePage0(MPT_ADAPTER *ioc, u8 bus, u8 targetId, pFCDevicePage0_t fcDevicePage)
23653  {
23654         ConfigPageHeader_t       hdr;
23655         CONFIGPARMS              cfg;
23656 @@ -1348,7 +1244,7 @@ mptscsih_readFCDevicePage0(MPT_ADAPTER *
23657         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
23658         cfg.dir = 0;
23659  
23660 -       cfg.pageAddr = (bus << 8) + id + MPI_FC_DEVICE_PGAD_FORM_BUS_TID;
23661 +       cfg.pageAddr = (bus << 8) + targetId + MPI_FC_DEVICE_PGAD_FORM_BUS_TID;
23662         cfg.timeout = 0;
23663  
23664         if ((rc = mpt_config(ioc, &cfg)) != 0)
23665 @@ -1436,16 +1332,15 @@ mptscsih_remove(struct pci_dev *pdev)
23666                 spin_unlock_irqrestore(&dvtaskQ_lock, flags);
23667         }
23668         if (!count)
23669 -   printk(KERN_ERR MYNAM ": %s: ERROR - DV thread still active!\n",
23670 -            ioc->name);
23671 -#ifdef MPT_DEBUG_DV
23672 +               printk(KERN_ERR MYNAM ": ERROR - DV thread still active!\n");
23673 +#if defined(MPT_DEBUG_DV) || defined(MPT_DEBUG_DV_TINY)
23674         else
23675 -               printk(KERN_ERR MYNAM ": DV thread orig %d, count %d\n", ioc->name,10 * HZ, count);
23676 +               printk(KERN_ERR MYNAM ": DV thread orig %d, count %d\n", 10 * HZ, count);
23677  #endif
23678  #endif
23679  
23680 -       dexitprintk((KERN_INFO MYNAM ": %s ioc=%p hd=%p MaxDevices=%d\n",
23681 -               ioc->name, ioc, hd, ioc->facts.MaxDevices));
23682 +       dexitprintk((KERN_INFO MYNAM ": %s ioc=%p hd=%p Targets=%p MaxDevices=%d\n", 
23683 +               ioc->name, ioc, hd, hd->Targets, ioc->facts.MaxDevices));
23684  // This was changed in the 2.6.13 kernel
23685  #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,13))
23686         mptscsih_shutdown(&pdev->dev);
23687 @@ -1453,19 +1348,19 @@ mptscsih_remove(struct pci_dev *pdev)
23688         mptscsih_shutdown(pdev);
23689  #endif
23690  
23691 -       dexitprintk((KERN_INFO MYNAM ": %s: calling scsi_remove_host ioc=%p host=%p\n",
23692 +       dexitprintk((KERN_INFO MYNAM ": %s: calling scsi_remove_host ioc=%p host=%p\n", 
23693                 ioc->name, ioc, host));
23694  
23695         scsi_remove_host(host);
23696         dexitprintk((KERN_INFO MYNAM ": %s: scsi_remove_host completed\n", ioc->name));
23697  
23698         if (hd->ScsiLookup != NULL) {
23699 -               sz1 = ioc->req_depth * sizeof(void *);
23700 +               sz1 = hd->ioc->req_depth * sizeof(void *);
23701                 kfree(hd->ScsiLookup);
23702                 hd->ScsiLookup = NULL;
23703                 dprintk((MYIOC_s_INFO_FMT
23704                         "Free'd ScsiLookup (%d) memory\n",
23705 -                       ioc->name, sz1));
23706 +                       hd->ioc->name, sz1));
23707         }
23708  
23709         if (hd->info_kbuf != NULL)
23710 @@ -1473,7 +1368,7 @@ mptscsih_remove(struct pci_dev *pdev)
23711  
23712         /* NULL the Scsi_Host pointer
23713          */
23714 -       ioc->sh = NULL;
23715 +       hd->ioc->sh = NULL;
23716  
23717         scsi_host_put(host);
23718  
23719 @@ -1498,36 +1393,25 @@ mptscsih_shutdown(struct pci_dev *pdev)
23720  {
23721         MPT_ADAPTER             *ioc = pci_get_drvdata(pdev);
23722  #endif
23723 -       struct Scsi_Host        *host;
23724 +       struct Scsi_Host        *host = ioc->sh;
23725         MPT_SCSI_HOST           *hd;
23726  
23727 -       host = ioc->sh;
23728 -
23729         if(!host)
23730                 return;
23731  
23732         hd = (MPT_SCSI_HOST *)host->hostdata;
23733  
23734 -       dexitprintk((KERN_INFO MYNAM ": %s: ioc=%p hd=%p\n",
23735 -               __FUNCTION__, ioc, hd));
23736 -
23737         /* Flush the cache of this adapter
23738          */
23739 -       if(hd != NULL) {
23740 -               dexitprintk((KERN_INFO MYNAM ": Calling mptscsih_synchronize_cache for %s\n",
23741 -                       ioc->name));
23742 +       if(hd != NULL)
23743                 mptscsih_synchronize_cache(hd, 0);
23744 -               dexitprintk((KERN_INFO MYNAM ": mptscsih_synchronize_cache for %s completed\n",
23745 -                       ioc->name));
23746 -       }
23747 -       dexitprintk((KERN_INFO MYNAM ": %s done: ioc=%p hd=%p\n",
23748 -               __FUNCTION__, ioc, hd));
23749 +
23750  }
23751  
23752  #ifdef CONFIG_PM
23753  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
23754  /*
23755 - *     mptscsih_suspend - Fusion MPT scsi driver suspend routine.
23756 + *     mptscsih_suspend - Fusion MPT scsie driver suspend routine.
23757   *
23758   *
23759   */
23760 @@ -1566,7 +1450,7 @@ mptscsih_resume(struct pci_dev *pdev)
23761                 return 0;
23762  
23763  #ifdef MPTSCSIH_ENABLE_DOMAIN_VALIDATION
23764 -/*     {
23765 +       {
23766         unsigned long lflags;
23767         spin_lock_irqsave(&dvtaskQ_lock, lflags);
23768         if (!dvtaskQ_active) {
23769 @@ -1578,7 +1462,7 @@ mptscsih_resume(struct pci_dev *pdev)
23770         } else {
23771                 spin_unlock_irqrestore(&dvtaskQ_lock, lflags);
23772         }
23773 -       } */
23774 +       }
23775  #endif
23776         return 0;
23777  }
23778 @@ -1732,13 +1616,10 @@ int
23779  mptscsih_qcmd(struct scsi_cmnd *SCpnt, void (*done)(struct scsi_cmnd *))
23780  {
23781         MPT_SCSI_HOST           *hd;
23782 -       MPT_ADAPTER             *ioc;
23783         MPT_FRAME_HDR           *mf;
23784         SCSIIORequest_t         *pScsiReq;
23785 -       struct _MPT_DEVICE      *pMptTarget;
23786         VirtDevice              *pTarget;
23787 -        unsigned long           flags;
23788 -        int     bus, id;
23789 +       int      target;
23790         int      lun;
23791         u32      datalen;
23792         u32      scsictl;
23793 @@ -1746,34 +1627,18 @@ mptscsih_qcmd(struct scsi_cmnd *SCpnt, v
23794         int      my_idx;
23795         int      ii;
23796  
23797 -       /* EDM Debug */
23798 -//     mptscsih_scsi_print_command(SCpnt);
23799 -
23800         hd = (MPT_SCSI_HOST *) SCpnt->device->host->hostdata;
23801 -       ioc = hd->ioc;
23802 -       bus = SCpnt->device->channel;
23803 -       id = SCpnt->device->id;
23804 +       target = SCpnt->device->id;
23805         lun = SCpnt->device->lun;
23806         SCpnt->scsi_done = done;
23807  
23808 -       spin_lock_irqsave(&ioc->diagLock, flags);
23809 -       if (ioc->IOCResetInProgress) {
23810 -               dfailprintk((MYIOC_s_WARN_FMT "qcmd, SCpnt=%p IOCResetInProgress!!\n",
23811 -                            ioc->name, SCpnt));
23812 -               spin_unlock_irqrestore(&ioc->diagLock, flags);
23813 -               goto fail;
23814 -       }
23815 -       spin_unlock_irqrestore(&ioc->diagLock, flags);
23816 -
23817 -
23818 -       pMptTarget = ioc->Target_List[bus];
23819 -       pTarget = pMptTarget->Target[id];
23820 +       pTarget = hd->Targets[target];
23821  
23822         if ( pTarget ) {
23823                 if ( lun > pTarget->last_lun ) {
23824                         dsprintk((MYIOC_s_INFO_FMT
23825                                 "qcmd: lun=%d > last_lun=%d on id=%d\n",
23826 -                               ioc->name, lun, pTarget->last_lun, id));
23827 +                               hd->ioc->name, lun, pTarget->last_lun, target));
23828                         SCpnt->result = DID_BAD_TARGET << 16;
23829                         SCpnt->scsi_done(SCpnt);
23830                         return 0;
23831 @@ -1782,31 +1647,32 @@ mptscsih_qcmd(struct scsi_cmnd *SCpnt, v
23832                  * allocated, use the Inquiry data to determine if device 
23833                  * supports tagged.
23834                 */
23835 -               if ( pTarget->tflags & MPT_TARGET_FLAGS_Q_YES)
23836 +               if ( (pTarget->tflags & MPT_TARGET_FLAGS_Q_YES)
23837 +                   && (SCpnt->device->tagged_supported)) {
23838                         scsictl = MPI_SCSIIO_CONTROL_SIMPLEQ;
23839 -                else
23840 +               } else {
23841                         scsictl = MPI_SCSIIO_CONTROL_UNTAGGED;
23842 +               }
23843  
23844 -       } else {
23845 +       } else
23846                 scsictl = MPI_SCSIIO_CONTROL_UNTAGGED;
23847 -dioprintk((MYIOC_s_WARN_FMT "qcmd: CDB=%02x id=%d lun=%d Null pTarget, sending Untagged\n",
23848 -                       ioc->name, SCpnt->cmnd[0], id, lun));
23849 -               if (ioc->bus_type == SPI) {
23850 -                       dnegoprintk(("writeSDP1: id=%d Async/Narrow\n",
23851 -                               id));
23852 -                       mpt_writeSDP1(ioc, 0, id, 0);
23853 -               }
23854 +       dmfprintk((MYIOC_s_INFO_FMT "qcmd: SCpnt=%p, done()=%p\n",
23855 +                       (hd && hd->ioc) ? hd->ioc->name : "ioc?", SCpnt, done));
23856  
23857 - }
23858 +       if (hd->resetPending) {
23859 +               dfailprintk((MYIOC_s_INFO_FMT "QueueCmd, SCpnt=%p resetPending!!\n",
23860 +                               hd->ioc->name, SCpnt));
23861 +               return SCSI_MLQUEUE_HOST_BUSY;
23862 +       }
23863  
23864         /*
23865          *  Put together a MPT SCSI request...
23866          */
23867 -       if ((mf = mpt_get_msg_frame(ioc->DoneCtx, ioc)) == NULL) {
23868 +       if ((mf = mpt_get_msg_frame(hd->ioc->DoneCtx, hd->ioc)) == NULL) {
23869                 dfailprintk((MYIOC_s_WARN_FMT "%s, no msg frames!!\n",
23870 -                   ioc->name,__FUNCTION__));
23871 -                   goto fail;
23872 -               }
23873 +                   hd->ioc->name,__FUNCTION__));
23874 +               return SCSI_MLQUEUE_HOST_BUSY;
23875 +       }
23876  
23877         pScsiReq = (SCSIIORequest_t *) mf;
23878  
23879 @@ -1831,8 +1697,8 @@ dioprintk((MYIOC_s_WARN_FMT "qcmd: CDB=%
23880  
23881         /* Use the above information to set up the message frame
23882          */
23883 -       pScsiReq->TargetID = (u8) id;
23884 -       pScsiReq->Bus = (u8) bus;
23885 +       pScsiReq->TargetID = (u8) target;
23886 +       pScsiReq->Bus = (u8) SCpnt->device->channel;
23887         pScsiReq->ChainOffset = 0;
23888         pScsiReq->Function = MPI_FUNCTION_SCSI_IO_REQUEST;
23889         pScsiReq->CDBLength = SCpnt->cmd_len;
23890 @@ -1863,7 +1729,7 @@ dioprintk((MYIOC_s_WARN_FMT "qcmd: CDB=%
23891         pScsiReq->DataLength = cpu_to_le32(datalen);
23892  
23893         /* SenseBuffer low address */
23894 -       pScsiReq->SenseBufferLowAddr = cpu_to_le32(ioc->sense_buf_low_dma
23895 +       pScsiReq->SenseBufferLowAddr = cpu_to_le32(hd->ioc->sense_buf_low_dma
23896                                            + (my_idx * MPT_SENSE_BUFFER_ALLOC));
23897  
23898         /* Now add the SG list
23899 @@ -1875,39 +1741,67 @@ dioprintk((MYIOC_s_WARN_FMT "qcmd: CDB=%
23900                         (dma_addr_t) -1);
23901         } else {
23902                 /* Add a 32 or 64 bit SGE */
23903 -               if (mptscsih_AddSGE(ioc, SCpnt, pScsiReq, my_idx) != SUCCESS){
23904 -                    mptscsih_freeChainBuffers(ioc, my_idx);
23905 -                    mpt_free_msg_frame(ioc, mf);
23906 +               if (mptscsih_AddSGE(hd->ioc, SCpnt, pScsiReq, my_idx) != SUCCESS)
23907                         goto fail;
23908 -                   }
23909         }
23910  
23911 -       SCpnt->host_scribble = (unsigned char *)mf;
23912 -
23913 -       if (ioc->bus_type == SPI &&
23914 -               ioc->spi_data.dvStatus[id] & MPT_SCSICFG_DV_IN_PROGRESS) {
23915 -               spin_lock_irqsave(&ioc->PendingMFlock, flags);
23916 -               ioc->PendingMF = mf;
23917 -               ioc->PendingSCpnt = SCpnt;
23918 -               spin_unlock_irqrestore(&ioc->PendingMFlock, flags);
23919 -               dpendprintk((KERN_INFO " qcmd: %s: DV In Progress id=%d mf=%p sc=%p into PendingMF\n",
23920 -                       ioc->name, id, mf, SCpnt));
23921 -               DBG_DUMP_REQUEST_FRAME(ioc, mf)
23922 -//             mod_timer(&SCpnt->eh_timeout, jiffies + 40 * HZ);
23923 -               return 0;
23924 -}
23925         hd->ScsiLookup[my_idx] = SCpnt;
23926 +       SCpnt->host_scribble = NULL;
23927  
23928 -       mpt_put_msg_frame(ioc->DoneCtx, ioc, mf);
23929 +#ifdef MPTSCSIH_ENABLE_DOMAIN_VALIDATION
23930 +       if (hd->ioc->bus_type == SPI) {
23931 +               int dvStatus = hd->ioc->spi_data.dvStatus[target];
23932 +               int issueCmd = 1;
23933 +
23934 +               if (dvStatus || hd->ioc->spi_data.forceDv) {
23935 +
23936 +                       if ((dvStatus & MPT_SCSICFG_NEED_DV) ||
23937 +                               (hd->ioc->spi_data.forceDv & MPT_SCSICFG_NEED_DV)) {
23938 +                               unsigned long lflags;
23939 +                               /* Schedule DV if necessary */
23940 +                               spin_lock_irqsave(&dvtaskQ_lock, lflags);
23941 +                               if (!dvtaskQ_active) {
23942 +                                       dvtaskQ_active = 1;
23943 +                                       spin_unlock_irqrestore(&dvtaskQ_lock, lflags);
23944 +                                       INIT_WORK(&dvTaskQ_task, mptscsih_domainValidation, (void *) hd);
23945 +
23946 +                                       schedule_work(&dvTaskQ_task);
23947 +                               } else {
23948 +                                       spin_unlock_irqrestore(&dvtaskQ_lock, lflags);
23949 +                               }
23950 +                               hd->ioc->spi_data.forceDv &= ~MPT_SCSICFG_NEED_DV;
23951 +                       }
23952 +
23953 +                       /* Trying to do DV to this target, extend timeout.
23954 +                        * Wait to issue until flag is clear
23955 +                        */
23956 +                       if (dvStatus & MPT_SCSICFG_DV_PENDING) {
23957 +                               mod_timer(&SCpnt->eh_timeout, jiffies + 40 * HZ);
23958 +                               issueCmd = 0;
23959 +                       }
23960 +
23961 +                       /* Set the DV flags.
23962 +                        */
23963 +                       if (dvStatus & MPT_SCSICFG_DV_NOT_DONE)
23964 +                               mptscsih_set_dvflags(hd, pScsiReq);
23965 +
23966 +                       if (!issueCmd)
23967 +                               goto fail;
23968 +               }
23969 +       }
23970 +#endif
23971 +
23972 +       mpt_put_msg_frame(hd->ioc->DoneCtx, hd->ioc, mf);
23973         dmfprintk((MYIOC_s_INFO_FMT "Issued SCSI cmd (%p) mf=%p idx=%d\n",
23974 -                       ioc->name, SCpnt, mf, my_idx));
23975 -       DBG_DUMP_REQUEST_FRAME(ioc,mf)
23976 +                       hd->ioc->name, SCpnt, mf, my_idx));
23977 +       DBG_DUMP_REQUEST_FRAME(mf)
23978         return 0;
23979  
23980   fail:
23981 -       SCpnt->result = DID_BUS_BUSY << 16;
23982 -       SCpnt->scsi_done(SCpnt);
23983 -       return 0;
23984 +       hd->ScsiLookup[my_idx] = NULL;
23985 +       mptscsih_freeChainBuffers(hd->ioc, my_idx);
23986 +       mpt_free_msg_frame(hd->ioc, mf);
23987 +       return SCSI_MLQUEUE_HOST_BUSY;
23988  }
23989  
23990  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
23991 @@ -1972,8 +1866,7 @@ mptscsih_freeChainBuffers(MPT_ADAPTER *i
23992   *
23993   *     @ioc: Pointer to MPT_ADAPTER structure
23994   *     @type: Task Management type
23995 - *     @bus: Logical Bus for reset (if appropriate)
23996 - *     @id: Logical Target ID for reset (if appropriate)
23997 + *     @target: Logical Target ID for reset (if appropriate)
23998   *     @lun: Logical Unit for reset (if appropriate)
23999   *     @ctx2abort: Context for the task to be aborted (if appropriate)
24000   *
24001 @@ -1982,10 +1875,10 @@ mptscsih_freeChainBuffers(MPT_ADAPTER *i
24002   *     Remark: With old EH code, at most 1 SCSI TaskMgmt function per IOC
24003   *     will be active.
24004   *
24005 - *     Returns 0 for SUCCESS.
24006 + *     Returns 0 for SUCCESS or -1 if FAILED.
24007   */
24008  int
24009 -mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8 type, u8 bus, u8 id, u8 lun, int ctx2abort, ulong timeout)
24010 +mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8 type, u8 channel, u8 target, u8 lun, int ctx2abort, ulong timeout)
24011  {
24012         MPT_ADAPTER     *ioc;
24013         int              rc = -1;
24014 @@ -2000,15 +1893,16 @@ mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8
24015                 return 0;
24016  
24017         ioc = hd->ioc;
24018 -
24019 +       if (ioc == NULL) {
24020 +               printk(KERN_ERR MYNAM " TMHandler" " NULL ioc!\n");
24021 +               return FAILED;
24022 +       }
24023         dtmprintk((MYIOC_s_INFO_FMT "TMHandler Entered!\n", ioc->name));
24024  
24025         // SJR - CHECKME - Can we avoid this here?
24026         // (mpt_HardResetHandler has this check...)
24027         spin_lock_irqsave(&ioc->diagLock, flags);
24028 - if (ioc->IOCResetInProgress) {
24029 -     dtmprintk((KERN_INFO MYNAM ": %s: TMHandler failing: "
24030 -                "IOCResetInProgress\n", ioc->name));
24031 +       if ((ioc->diagPending) || (ioc->alt_ioc && ioc->alt_ioc->diagPending)) {
24032                 spin_unlock_irqrestore(&ioc->diagLock, flags);
24033                 return FAILED;
24034         }
24035 @@ -2023,54 +1917,52 @@ mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8
24036                 if (type == MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK) {
24037                         dtmprintk((KERN_INFO MYNAM ": %s: TMHandler abort: "
24038                            "Timed out waiting for last TM (%d) to complete! \n",
24039 -                          ioc->name, hd->tmPending));
24040 +                          hd->ioc->name, hd->tmPending));
24041                         return FAILED;
24042                 } else if (type == MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET) {
24043                         dtmprintk((KERN_INFO MYNAM ": %s: TMHandler target reset: "
24044                            "Timed out waiting for last TM (%d) to complete! \n",
24045 -                          ioc->name, hd->tmPending));
24046 +                          hd->ioc->name, hd->tmPending));
24047                         return FAILED;
24048                 } else if (type == MPI_SCSITASKMGMT_TASKTYPE_RESET_BUS) {
24049                         dtmprintk((KERN_INFO MYNAM ": %s: TMHandler bus reset: "
24050                            "Timed out waiting for last TM (%d) to complete! \n",
24051 -                          ioc->name, hd->tmPending));
24052 +                          hd->ioc->name, hd->tmPending));
24053                         if (hd->tmPending & (1 << MPI_SCSITASKMGMT_TASKTYPE_RESET_BUS))
24054                                 return FAILED;
24055  
24056                         doTask = 0;
24057                 }
24058         } else {
24059 -               spin_lock_irqsave(&ioc->FreeQlock, flags);
24060 +               spin_lock_irqsave(&hd->ioc->FreeQlock, flags);
24061                 hd->tmPending |=  (1 << type);
24062 -               spin_unlock_irqrestore(&ioc->FreeQlock, flags);
24063 +               spin_unlock_irqrestore(&hd->ioc->FreeQlock, flags);
24064         }
24065  
24066         /* Is operational?
24067          */
24068 -       ioc_raw_state = mpt_GetIocState(ioc, 0);
24069 +       ioc_raw_state = mpt_GetIocState(hd->ioc, 0);
24070  
24071  #ifdef MPT_DEBUG_RESET
24072         if ((ioc_raw_state & MPI_IOC_STATE_MASK) != MPI_IOC_STATE_OPERATIONAL) {
24073                 printk(MYIOC_s_WARN_FMT
24074                         "TM Handler: IOC Not operational(0x%x)!\n",
24075 -                ioc->name, ioc_raw_state);
24076 -               return FAILED;
24077 -//             panic ( "TMHandler: IOC Not operational!");
24078 +                       hd->ioc->name, ioc_raw_state);
24079         }
24080  #endif
24081  
24082         if (doTask && ((ioc_raw_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_OPERATIONAL)
24083                                 && !(ioc_raw_state & MPI_DOORBELL_ACTIVE)) {
24084  
24085 -               /* Issue the Task Mgmt request.
24086 +               /* Isse the Task Mgmt request.
24087                  */
24088                 if (hd->hard_resets < -1)
24089                         hd->hard_resets++;
24090 -               rc = mptscsih_IssueTaskMgmt(hd, type, bus, id, lun, ctx2abort, timeout);
24091 +               rc = mptscsih_IssueTaskMgmt(hd, type, channel, target, lun, ctx2abort, timeout);
24092                 if (rc) {
24093 -                       printk(MYIOC_s_INFO_FMT "Issue of TaskMgmt failed!\n", ioc->name);
24094 +                       printk(MYIOC_s_INFO_FMT "Issue of TaskMgmt failed!\n", hd->ioc->name);
24095                 } else {
24096 -                       dtmprintk((MYIOC_s_INFO_FMT "Issue of TaskMgmt Successful!\n", ioc->name));
24097 +                       dtmprintk((MYIOC_s_INFO_FMT "Issue of TaskMgmt Successful!\n", hd->ioc->name));
24098                 }
24099         }
24100  
24101 @@ -2079,21 +1971,11 @@ mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8
24102         if ((type == MPI_SCSITASKMGMT_TASKTYPE_RESET_BUS) && (rc ||
24103                 ioc->reload_fw || (ioc->alt_ioc && ioc->alt_ioc->reload_fw))) {
24104                 dtmprintk((MYIOC_s_INFO_FMT "Calling HardReset! \n",
24105 -                        ioc->name));
24106 -               rc = mpt_HardResetHandler(ioc, CAN_SLEEP);
24107 +                        hd->ioc->name));
24108 +               rc = mpt_HardResetHandler(hd->ioc, CAN_SLEEP);
24109         }
24110  
24111 -    /*
24112 -     * Check IOCStatus from TM reply message
24113 -     */
24114 -       if (hd->tm_iocstatus == MPI_IOCSTATUS_SUCCESS ||
24115 -          hd->tm_iocstatus == MPI_IOCSTATUS_SCSI_TASK_TERMINATED ||
24116 -          hd->tm_iocstatus == MPI_IOCSTATUS_SCSI_IOC_TERMINATED)
24117 -               rc = 0;
24118 -       else
24119 -               rc = FAILED;
24120 -
24121 -       dtmprintk((MYIOC_s_INFO_FMT "TMHandler rc = %d!\n", ioc->name, rc));
24122 +       dtmprintk((MYIOC_s_INFO_FMT "TMHandler rc = %d!\n", hd->ioc->name, rc));
24123  
24124         return rc;
24125  }
24126 @@ -2104,7 +1986,7 @@ mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8
24127   *     mptscsih_IssueTaskMgmt - Generic send Task Management function.
24128   *     @hd: Pointer to MPT_SCSI_HOST structure
24129   *     @type: Task Management type
24130 - *     @id: Logical Target ID for reset (if appropriate)
24131 + *     @target: Logical Target ID for reset (if appropriate)
24132   *     @lun: Logical Unit for reset (if appropriate)
24133   *     @ctx2abort: Context for the task to be aborted (if appropriate)
24134   *
24135 @@ -2117,31 +1999,28 @@ mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8
24136   *     else other non-zero value returned.
24137   */
24138  static int
24139 -mptscsih_IssueTaskMgmt(MPT_SCSI_HOST *hd, u8 type, u8 bus, u8 id, u8 lun, int ctx2abort, ulong timeout)
24140 +mptscsih_IssueTaskMgmt(MPT_SCSI_HOST *hd, u8 type, u8 channel, u8 target, u8 lun, int ctx2abort, ulong timeout)
24141  {
24142 -       MPT_ADAPTER             *ioc = hd->ioc;
24143         MPT_FRAME_HDR   *mf;
24144         SCSITaskMgmt_t  *pScsiTm;
24145         int              ii;
24146         int              retval;
24147 -       u32              ioc_state;
24148 -       unsigned long    flags;
24149  
24150         /* Return Fail to calling function if no message frames available.
24151          */
24152 -       if ((mf = mpt_get_msg_frame(ioc->TaskCtx, ioc)) == NULL) {
24153 +       if ((mf = mpt_get_msg_frame(hd->ioc->TaskCtx, hd->ioc)) == NULL) {
24154                 dfailprintk((MYIOC_s_WARN_FMT "%s, no msg frames!!\n",
24155 -                   ioc->name,__FUNCTION__));
24156 +                   hd->ioc->name,__FUNCTION__));
24157                 return FAILED;
24158         }
24159 -       dtmprintk((MYIOC_s_WARN_FMT "IssueTaskMgmt request @ %p\n",
24160 -                       ioc->name, mf));
24161 +       dtmprintk((MYIOC_s_INFO_FMT "IssueTaskMgmt request @ %p\n",
24162 +                       hd->ioc->name, mf));
24163  
24164         /* Format the Request
24165          */
24166         pScsiTm = (SCSITaskMgmt_t *) mf;
24167 -       pScsiTm->TargetID = id;
24168 -       pScsiTm->Bus = bus;
24169 +       pScsiTm->TargetID = target;
24170 +       pScsiTm->Bus = channel;
24171         pScsiTm->ChainOffset = 0;
24172         pScsiTm->Function = MPI_FUNCTION_SCSI_TASK_MGMT;
24173  
24174 @@ -2161,52 +2040,31 @@ mptscsih_IssueTaskMgmt(MPT_SCSI_HOST *hd
24175  
24176         pScsiTm->TaskMsgContext = ctx2abort;
24177  
24178 -       dtmprintk((MYIOC_s_WARN_FMT "IssueTaskMgmt: ctx2abort (0x%08x) type=%d\n",
24179 -                       ioc->name, ctx2abort, type));
24180 +       dtmprintk((MYIOC_s_INFO_FMT "IssueTaskMgmt: ctx2abort (0x%08x) type=%d\n",
24181 +                       hd->ioc->name, ctx2abort, type));
24182  
24183         DBG_DUMP_TM_REQUEST_FRAME((u32 *)pScsiTm);
24184  
24185 -       hd->TM_wait_done = 0;
24186 -       if ((retval = mpt_send_handshake_request(ioc->TaskCtx, ioc,
24187 -               sizeof(SCSITaskMgmt_t), (u32*)pScsiTm, timeout, CAN_SLEEP)) != 0) {
24188 -               dfailprintk((MYIOC_s_WARN_FMT "%s: send_handshake FAILED!\n",
24189 -                       ioc->name, __FUNCTION__));
24190 -               mpt_free_msg_frame(ioc, mf);
24191 -
24192 -               dtmprintk((MYIOC_s_WARN_FMT "Calling mpt_SendIocReset MUR!\n",
24193 -                       ioc->name));
24194 -               if ((retval = mpt_SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, CAN_SLEEP)) != 0) {
24195 -                       ioc_state = mpt_GetIocState(ioc, 0);
24196 -                       dfailprintk((MYIOC_s_WARN_FMT "IOC MUR failed! ioc_state=%08x\n", ioc->name, ioc_state));
24197 -//                     panic ("IOC MUR Failed");
24198 -                       ioc->IOCResetInProgress = 0;
24199 +       if ((retval = mpt_send_handshake_request(hd->ioc->TaskCtx, hd->ioc,
24200 +               sizeof(SCSITaskMgmt_t), (u32*)pScsiTm,
24201 +               CAN_SLEEP)) != 0) {
24202 +               dfailprintk((MYIOC_s_ERR_FMT "_send_handshake FAILED!"
24203 +                       " (hd %p, ioc %p, mf %p) \n", hd->ioc->name, hd,
24204 +                       hd->ioc, mf));
24205 +               mpt_free_msg_frame(hd->ioc, mf);
24206 +               return retval;
24207 +       }
24208  
24209 -                       if ((retval = mpt_HardResetHandler(ioc, CAN_SLEEP)) < 0){
24210 -                               printk((KERN_WARNING " HardResetHandler FAILED!!\n"));                  }
24211 -                       else {
24212 -                               dtmprintk((MYIOC_s_WARN_FMT " HardResetHandler succeeded!!\n", ioc->name));
24213 -                       }
24214 -               } else {
24215 -                       dtmprintk((MYIOC_s_WARN_FMT "IOC MUR succeeded\n", ioc->name));
24216 -                       mptscsih_flush_running_cmds(hd);
24217 -                       dtmprintk((MYIOC_s_WARN_FMT "Calling do_ioc_recovery! \n", ioc->name));
24218 -                       if ((retval = mpt_do_ioc_recovery(ioc, MPT_HOSTEVENT_IOC_RECOVER, CAN_SLEEP)) != 0) {
24219 -                               dfailprintk((MYIOC_s_ERR_FMT "- (%d) ioc_recovery failed\n", ioc->name, retval));
24220 -                       } else {
24221 -                               dtmprintk((MYIOC_s_WARN_FMT "Successful do_ioc_recovery! \n", ioc->name));
24222 -                       }
24223 -               }
24224 -       } else {
24225 -               dtmprintk((MYIOC_s_WARN_FMT "%s: send_handshake SUCCESS!\n",
24226 -                       ioc->name, __FUNCTION__));
24227 -               if (hd->TM_wait_done == 0) {
24228 -                       wait_event(hd->TM_waitq, hd->TM_wait_done);
24229 -               }
24230 +       if(mptscsih_tm_wait_for_completion(hd, timeout) == FAILED) {
24231 +               dfailprintk((MYIOC_s_ERR_FMT "_wait_for_completion FAILED!"
24232 +                       " (hd %p, ioc %p, mf %p) \n", hd->ioc->name, hd,
24233 +                       hd->ioc, mf));
24234 +               mpt_free_msg_frame(hd->ioc, mf);
24235 +               dtmprintk((MYIOC_s_INFO_FMT "Calling HardReset! \n",
24236 +                        hd->ioc->name));
24237 +               retval = mpt_HardResetHandler(hd->ioc, CAN_SLEEP);
24238         }
24239 -       spin_lock_irqsave(&ioc->FreeQlock, flags);
24240 -       hd->tmPending = 0;
24241 -       hd->tmState = TM_STATE_NONE;
24242 -       spin_unlock_irqrestore(&ioc->FreeQlock, flags);
24243 +
24244         return retval;
24245  }
24246  
24247 @@ -2229,8 +2087,6 @@ mptscsih_abort(struct scsi_cmnd * SCpnt)
24248         int              scpnt_idx;
24249         int              retval;
24250         int              tm_timeout;
24251 -        unsigned long    flags;
24252 -       unsigned long    sn = SCpnt->serial_number;
24253  
24254  /* From the 2.6.13 kernels, they have removed calling
24255   *     eh_threads with the host_lock in locked state
24256 @@ -2251,57 +2107,30 @@ mptscsih_abort(struct scsi_cmnd * SCpnt)
24257         }
24258  
24259         ioc = hd->ioc;
24260 -       spin_lock_irqsave(&ioc->diagLock, flags);
24261 -       if (ioc->IOCResetInProgress) {
24262 -               dtmprintk((KERN_INFO ": %s: abort: "
24263 -                          "IOCResetInProgress (sc=%p)\n",
24264 -                          ioc->name, SCpnt));
24265 -               spin_unlock_irqrestore(&ioc->diagLock, flags);
24266 -
24267 -
24268 +       if (hd->resetPending) {
24269                 return FAILED;
24270         }
24271  
24272 -spin_unlock_irqrestore(&ioc->diagLock, flags);
24273 -
24274         if (hd->timeouts < -1)
24275 -
24276                 hd->timeouts++;
24277  
24278 -       printk(KERN_WARNING MYNAM ": %s: attempting task abort! (sc=%p)\n",
24279 -              ioc->name, SCpnt);
24280 -             scsi_print_command(SCpnt);
24281 -
24282 -//     printk(KERN_WARNING MYNAM ": %s: Delaying 30 seconds\n", ioc->name);
24283 -//     mdelay (30000);
24284 -       /* If this command is pended, then timeout/hang occurred
24285 -        * during DV. Post command and flush pending Q
24286 -        * and then following up with the reset request.
24287 -        */
24288 -       if ( (mf = mptscsih_search_PendingMF(ioc, SCpnt)) != NULL) {
24289 -               /* Cmd was in PendingMF.
24290 -                */
24291 -               dpendprintk((KERN_INFO MYNAM ": %s: mptscsih_abort: "
24292 -                          "Command was in PendingMF! (sc=%p)\n",
24293 -                          ioc->name, SCpnt));
24294 -               return SUCCESS;
24295 -       }
24296 -
24297 -
24298 -
24299         /* Find this command
24300          */
24301         if ((scpnt_idx = SCPNT_TO_LOOKUP_IDX(SCpnt)) < 0) {
24302                 /* Cmd not found in ScsiLookup.
24303                  * Do OS callback.
24304                  */
24305 -//             SCpnt->result = DID_RESET << 16;
24306 +               SCpnt->result = DID_RESET << 16;
24307                 dtmprintk((KERN_INFO MYNAM ": %s: mptscsih_abort: "
24308                            "Command not in the active list! (sc=%p)\n",
24309 -                          ioc->name, SCpnt));
24310 +                          hd->ioc->name, SCpnt));
24311                 return SUCCESS;
24312         }
24313  
24314 +       printk(KERN_WARNING MYNAM ": %s: attempting task abort! (sc=%p)\n",
24315 +              hd->ioc->name, SCpnt);
24316 +       scsi_print_command(SCpnt);
24317 +
24318         /* Most important!  Set TaskMsgContext to SCpnt's MsgContext!
24319          * (the IO to be ABORT'd)
24320          *
24321 @@ -2309,7 +2138,7 @@ spin_unlock_irqrestore(&ioc->diagLock, f
24322          *       swap it here either.  It is an opaque cookie to
24323          *       the controller, so it does not matter. -DaveM
24324          */
24325 -       mf = MPT_INDEX_2_MFPTR(ioc, scpnt_idx);
24326 +       mf = MPT_INDEX_2_MFPTR(hd->ioc, scpnt_idx);
24327         ctx2abort = mf->u.frame.hwhdr.msgctxu.MsgContext;
24328  
24329         hd->abortSCpnt = SCpnt;
24330 @@ -2318,7 +2147,7 @@ spin_unlock_irqrestore(&ioc->diagLock, f
24331         spin_unlock_irq(host_lock);
24332  #endif
24333         /* set timeout in seconds */
24334 -       switch (ioc->bus_type) {
24335 +       switch (hd->ioc->bus_type) {
24336         case FC:
24337                 tm_timeout=40;
24338                 break;
24339 @@ -2327,7 +2156,7 @@ spin_unlock_irqrestore(&ioc->diagLock, f
24340                 break;
24341         case SPI:
24342         default:
24343 -               tm_timeout=10;
24344 +               tm_timeout=2;
24345                 break;
24346         }
24347         retval = mptscsih_TMHandler(hd, MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK,
24348 @@ -2337,30 +2166,17 @@ spin_unlock_irqrestore(&ioc->diagLock, f
24349         spin_lock_irq(host_lock);
24350  #endif
24351  
24352 -if (ioc->bus_type == FC) {
24353 -       if (SCPNT_TO_LOOKUP_IDX(SCpnt) == scpnt_idx &&
24354 -           SCpnt->serial_number == sn) {
24355 -               dtmprintk((KERN_INFO MYNAM ": %s: mptscsih_abort: "
24356 -                          "scpnt_idx=%08x sn=%lx (sc=%p)\n",
24357 -                          ioc->name, scpnt_idx, sn, SCpnt));
24358 -               retval = FAILED;
24359 -       }
24360 -}
24361 -
24362         printk (KERN_WARNING MYNAM ": %s: task abort: %s (sc=%p)\n",
24363 -               ioc->name,
24364 +               hd->ioc->name,
24365                 ((retval == 0) ? "SUCCESS" : "FAILED" ), SCpnt);
24366 -       hd->ScsiLookup[scpnt_idx] = NULL;
24367 -//panic ("Task Abort completed");
24368 -       spin_lock_irqsave(&hd->ioc->FreeQlock, flags);
24369 -       hd->tmPending = 0;
24370 -       hd->tmState = TM_STATE_NONE;
24371 -       spin_unlock_irqrestore(&hd->ioc->FreeQlock, flags);
24372 -
24373  
24374         if (retval == 0)
24375                 return SUCCESS;
24376  
24377 +       if(retval != FAILED ) {
24378 +               hd->tmPending = 0;
24379 +               hd->tmState = TM_STATE_NONE;
24380 +       }
24381         return FAILED;
24382  }
24383  
24384 @@ -2377,10 +2193,8 @@ int
24385  mptscsih_dev_reset(struct scsi_cmnd * SCpnt)
24386  {
24387         MPT_SCSI_HOST   *hd;
24388 -       MPT_ADAPTER     *ioc;
24389 -       int             id,retval;
24390 +       int              retval;
24391         int              tm_timeout;
24392 -        unsigned long    flags;
24393  
24394  /* From the 2.6.13 kernels, they have removed calling
24395   *     eh_threads with the host_lock in locked state
24396 @@ -2398,27 +2212,17 @@ mptscsih_dev_reset(struct scsi_cmnd * SC
24397                 return FAILED;
24398         }
24399  
24400 -       ioc = hd->ioc;
24401 -       id = SCpnt->device->id;
24402 -       spin_lock_irqsave(&ioc->diagLock, flags);
24403 -       if (ioc->IOCResetInProgress) {
24404 -               dtmprintk((KERN_INFO ": %s: target reset: "
24405 -                          "IOCResetInProgress (sc=%p)\n",
24406 -                          ioc->name, SCpnt));
24407 -               spin_unlock_irqrestore(&ioc->diagLock, flags);
24408 -
24409 -            return FAILED;
24410 -}
24411 -spin_unlock_irqrestore(&ioc->diagLock, flags);
24412 +       if (hd->resetPending)
24413 +               return FAILED;
24414  
24415         printk(KERN_WARNING MYNAM ": %s: attempting target reset! (sc=%p)\n",
24416 -              ioc->name, SCpnt);
24417 +              hd->ioc->name, SCpnt);
24418         scsi_print_command(SCpnt);
24419  
24420  #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,13))
24421         spin_unlock_irq(host_lock);
24422  #endif
24423 -       switch (ioc->bus_type) {
24424 +       switch (hd->ioc->bus_type) {
24425         case FC:
24426                 tm_timeout=40;
24427                 break;
24428 @@ -2427,29 +2231,25 @@ spin_unlock_irqrestore(&ioc->diagLock, f
24429                 break;
24430         case SPI:
24431         default:
24432 -               tm_timeout=10;
24433 +               tm_timeout=5;
24434                 break;
24435         }
24436         retval = mptscsih_TMHandler(hd, MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET,
24437 -       SCpnt->device->channel, id, 0, 0, tm_timeout);
24438 +               SCpnt->device->channel, SCpnt->device->id,
24439 +               0, 0, tm_timeout);
24440  #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,13))
24441         spin_lock_irq(host_lock);
24442  #endif
24443         printk (KERN_WARNING MYNAM ": %s: target reset: %s (sc=%p)\n",
24444 -               ioc->name,
24445 +               hd->ioc->name,
24446                 ((retval == 0) ? "SUCCESS" : "FAILED" ), SCpnt);
24447 -       spin_lock_irqsave(&hd->ioc->FreeQlock, flags);
24448 -       hd->tmPending = 0;
24449 -       hd->tmState = TM_STATE_NONE;
24450 -       spin_unlock_irqrestore(&hd->ioc->FreeQlock, flags);
24451 -
24452 -       if (retval == 0) {
24453 -               if (ioc->bus_type == SPI) {
24454 -                       dnegoprintk(("writeSDP1: id=%d USE_NVRAM\n",
24455 -                               id));
24456 -                       mpt_writeSDP1(ioc, 0, id, MPT_SCSICFG_USE_NVRAM);
24457 -               }
24458 -              return SUCCESS;
24459 +
24460 +       if (retval == 0)
24461 +               return SUCCESS;
24462 +
24463 +       if(retval != FAILED ) {
24464 +               hd->tmPending = 0;
24465 +               hd->tmState = TM_STATE_NONE;
24466         }
24467         return FAILED;
24468  }
24469 @@ -2467,10 +2267,8 @@ int
24470  mptscsih_bus_reset(struct scsi_cmnd * SCpnt)
24471  {
24472         MPT_SCSI_HOST   *hd;
24473 -       MPT_ADAPTER     *ioc;
24474         int              retval;
24475         int              tm_timeout;
24476 -        unsigned long    flags;
24477  
24478  /* From the 2.6.13 kernels, they have removed calling
24479   *     eh_threads with the host_lock in locked state
24480 @@ -2488,9 +2286,8 @@ mptscsih_bus_reset(struct scsi_cmnd * SC
24481                 return FAILED;
24482         }
24483  
24484 -       ioc = hd->ioc;
24485         printk(KERN_WARNING MYNAM ": %s: attempting bus reset! (sc=%p)\n",
24486 -              ioc->name, SCpnt);
24487 +              hd->ioc->name, SCpnt);
24488         scsi_print_command(SCpnt);
24489  
24490         if (hd->timeouts < -1)
24491 @@ -2500,7 +2297,7 @@ mptscsih_bus_reset(struct scsi_cmnd * SC
24492  #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,13))
24493         spin_unlock_irq(host_lock);
24494  #endif
24495 -       switch (ioc->bus_type) {
24496 +       switch (hd->ioc->bus_type) {
24497         case FC:
24498                 tm_timeout=40;
24499                 break;
24500 @@ -2509,7 +2306,7 @@ mptscsih_bus_reset(struct scsi_cmnd * SC
24501                 break;
24502         case SPI:
24503         default:
24504 -               tm_timeout=10;
24505 +               tm_timeout=5;
24506                 break;
24507         }
24508         retval = mptscsih_TMHandler(hd, MPI_SCSITASKMGMT_TASKTYPE_RESET_BUS,
24509 @@ -2519,20 +2316,17 @@ mptscsih_bus_reset(struct scsi_cmnd * SC
24510  #endif
24511  
24512         printk (KERN_WARNING MYNAM ": %s: bus reset: %s (sc=%p)\n",
24513 -               ioc->name,
24514 +               hd->ioc->name,
24515                 ((retval == 0) ? "SUCCESS" : "FAILED" ), SCpnt);
24516  
24517 -       spin_lock_irqsave(&hd->ioc->FreeQlock, flags);
24518 -       hd->tmPending = 0;
24519 -       hd->tmState = TM_STATE_NONE;
24520 -       spin_unlock_irqrestore(&hd->ioc->FreeQlock, flags);
24521 -
24522 -
24523 -
24524         if (retval == 0)
24525                 return SUCCESS;
24526  
24527 -        return FAILED;
24528 +       if(retval != FAILED ) {
24529 +               hd->tmPending = 0;
24530 +               hd->tmState = TM_STATE_NONE;
24531 +       }
24532 +       return FAILED;
24533  }
24534  
24535  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
24536 @@ -2549,10 +2343,8 @@ int
24537  mptscsih_host_reset(struct scsi_cmnd *SCpnt)
24538  {
24539         MPT_SCSI_HOST *  hd;
24540 -       MPT_ADAPTER     *ioc;
24541         int              status = SUCCESS;
24542 -        unsigned long    flags;
24543 -
24544 +       int              can_sleep;
24545  /* From the 2.6.13 kernels, they have removed calling
24546   *     eh_threads with the host_lock in locked state
24547   */
24548 @@ -2560,6 +2352,8 @@ mptscsih_host_reset(struct scsi_cmnd *SC
24549         spinlock_t      *host_lock = SCpnt->device->host->host_lock;
24550  #endif
24551  
24552 +       can_sleep = crashdump_mode() ? NO_SLEEP : CAN_SLEEP;
24553 +
24554         /*  If we can't locate the host to reset, then we failed. */
24555         if ((hd = (MPT_SCSI_HOST *) SCpnt->device->host->hostdata) == NULL){
24556                 dtmprintk( ( KERN_INFO MYNAM ": mptscsih_host_reset: "
24557 @@ -2568,9 +2362,8 @@ mptscsih_host_reset(struct scsi_cmnd *SC
24558                 return FAILED;
24559         }
24560  
24561 -       ioc = hd->ioc;
24562         printk(KERN_WARNING MYNAM ": %s: Attempting host reset! (sc=%p)\n",
24563 -              ioc->name, SCpnt);
24564 +              hd->ioc->name, SCpnt);
24565  
24566         /*  If our attempts to reset the host failed, then return a failed
24567          *  status.  The host will be taken off line by the SCSI mid-layer.
24568 @@ -2578,78 +2371,26 @@ mptscsih_host_reset(struct scsi_cmnd *SC
24569  #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,13))
24570         MPT_HOST_UNLOCK(host_lock);
24571  #endif
24572 -       if (mpt_HardResetHandler(ioc,
24573 -           crashdump_mode() ? NO_SLEEP : CAN_SLEEP) < 0) {
24574 -dfailprintk((MYIOC_s_ERR_FMT "host reset: HardResetHandler failed\n", ioc->name));
24575 -
24576 +       if (mpt_HardResetHandler(hd->ioc, can_sleep) < 0){
24577                 status = FAILED;
24578         } else {
24579 -
24580 -dtmprintk((MYIOC_s_ERR_FMT "host reset: HardResetHandler succeeded\n", ioc->name));
24581 -        status = SUCCESS;
24582 -
24583 +               /*  Make sure TM pending is cleared and TM state is set to
24584 +                *  NONE.
24585 +                */
24586 +               hd->tmPending = 0;
24587 +               hd->tmState = TM_STATE_NONE;
24588         }
24589 -
24590  #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,13))
24591         MPT_HOST_LOCK(host_lock);
24592  #endif
24593 -       spin_lock_irqsave(&hd->ioc->FreeQlock, flags);
24594 -       hd->tmPending = 0;
24595 -       hd->tmState = TM_STATE_NONE;
24596 -       spin_unlock_irqrestore(&hd->ioc->FreeQlock, flags);
24597 -
24598 -       return status;
24599 -}
24600 -
24601 -/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
24602 -/* Search the pendingMF for a command with specific index.
24603 - * If found, delete and return mf pointer
24604 - * If not found, return NULL
24605 - */
24606 -static MPT_FRAME_HDR *
24607 -mptscsih_search_PendingMF(MPT_ADAPTER *ioc, struct scsi_cmnd * sc)
24608 -{
24609 -       MPT_SCSI_HOST   *hd=(MPT_SCSI_HOST *) ioc->sh->hostdata;
24610 -       MPT_FRAME_HDR   *mf;
24611 -       unsigned long    flags;
24612 -       u16              req_idx;
24613  
24614 -       dpendprintk((MYIOC_s_WARN_FMT "%s entered\n",
24615 -               ioc->name, __FUNCTION__));
24616 -
24617 -       spin_lock_irqsave(&ioc->PendingMFlock, flags);
24618 -       if ((mf=ioc->PendingMF) == NULL) {
24619 -               spin_unlock_irqrestore(&ioc->PendingMFlock, flags);
24620 -               return NULL;
24621 -       }
24622 +       dtmprintk( ( KERN_INFO MYNAM ": mptscsih_host_reset: "
24623 +                    "Status = %s\n",
24624 +                    (status == SUCCESS) ? "SUCCESS" : "FAILED" ) );
24625  
24626 -       req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
24627 -       if (sc == hd->ScsiLookup[req_idx]) {
24628 -               ioc->PendingMF = NULL;
24629 -               spin_unlock_irqrestore(&ioc->PendingMFlock, flags);
24630 -
24631 -               dpendprintk((MYIOC_s_WARN_FMT "%s: found mf=%p\n",
24632 -                       ioc->name, __FUNCTION__, mf));
24633 -               DBG_DUMP_PENDING_REQUEST_FRAME(ioc, mf)
24634 -               /* Free Chain buffers */
24635 -               mptscsih_freeChainBuffers(ioc, req_idx);
24636 -               /* Free Message frames */
24637 -               mpt_free_msg_frame(ioc, mf);
24638 -               hd->ScsiLookup[req_idx] = NULL;
24639 -               sc->result = (DID_RESET << 16);
24640 -               sc->host_scribble = NULL;
24641 -               sc->scsi_done(sc);      /* Issue the command callback */
24642 -               dpendprintk(( "%s Executed scsi_done mf=%p sc=%p\n",
24643 -                       __FUNCTION__, mf, sc));
24644 -               return mf;
24645 -       }
24646 -       spin_unlock_irqrestore(&ioc->PendingMFlock, flags);
24647 -       dpendprintk((MYIOC_s_WARN_FMT "%s exiting mf=%p not in ScsiLookup\n",
24648 -               ioc->name, __FUNCTION__, mf));
24649 -       return NULL;
24650 +       return status;
24651  }
24652  
24653 -
24654  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
24655  /**
24656   *     mptscsih_tm_pending_wait - wait for pending task management request to
24657 @@ -2661,21 +2402,20 @@ mptscsih_search_PendingMF(MPT_ADAPTER *i
24658  static int
24659  mptscsih_tm_pending_wait(MPT_SCSI_HOST * hd)
24660  {
24661 -       MPT_ADAPTER     *ioc = hd->ioc;
24662         unsigned long  flags;
24663         int            loop_count = 4 * 10;  /* Wait 10 seconds */
24664         int            status = FAILED;
24665  
24666         do {
24667 -               spin_lock_irqsave(&ioc->FreeQlock, flags);
24668 +               spin_lock_irqsave(&hd->ioc->FreeQlock, flags);
24669                 if (hd->tmState == TM_STATE_NONE) {
24670                         hd->tmState = TM_STATE_IN_PROGRESS;
24671                         hd->tmPending = 1;
24672 -                       spin_unlock_irqrestore(&ioc->FreeQlock, flags);
24673 +                       spin_unlock_irqrestore(&hd->ioc->FreeQlock, flags);
24674                         status = SUCCESS;
24675                         break;
24676                 }
24677 -               spin_unlock_irqrestore(&ioc->FreeQlock, flags);
24678 +               spin_unlock_irqrestore(&hd->ioc->FreeQlock, flags);
24679                 msleep(250);
24680         } while (--loop_count);
24681  
24682 @@ -2683,6 +2423,34 @@ mptscsih_tm_pending_wait(MPT_SCSI_HOST *
24683  }
24684  
24685  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
24686 +/**
24687 + *     mptscsih_tm_wait_for_completion - wait for completion of TM task
24688 + *     @hd: Pointer to MPT host structure.
24689 + *
24690 + *     Returns {SUCCESS,FAILED}.
24691 + */
24692 +static int
24693 +mptscsih_tm_wait_for_completion(MPT_SCSI_HOST * hd, ulong timeout )
24694 +{
24695 +       unsigned long  flags;
24696 +       int            loop_count = 4 * timeout;
24697 +       int            status = FAILED;
24698 +
24699 +       do {
24700 +               spin_lock_irqsave(&hd->ioc->FreeQlock, flags);
24701 +               if(hd->tmPending == 0) {
24702 +                       status = SUCCESS;
24703 +                       spin_unlock_irqrestore(&hd->ioc->FreeQlock, flags);
24704 +                       break;
24705 +               }
24706 +               spin_unlock_irqrestore(&hd->ioc->FreeQlock, flags);
24707 +               msleep_interruptible(250);
24708 +       } while (--loop_count);
24709 +
24710 +       return status;
24711 +}
24712 +
24713 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
24714  static void
24715  mptscsih_taskmgmt_response_code(MPT_ADAPTER *ioc, u8 response_code)
24716  {
24717 @@ -2720,17 +2488,17 @@ mptscsih_taskmgmt_response_code(MPT_ADAP
24718  
24719  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
24720  /**
24721 - *      mptscsih_taskmgmt_complete - Registered with Fusion MPT base driver
24722 - *      @ioc: Pointer to MPT_ADAPTER structure
24723 - *      @mf: Pointer to SCSI task mgmt request frame
24724 - *      @mr: Pointer to SCSI task mgmt reply frame
24725 - *
24726 - *      This routine is called from mptbase.c::mpt_interrupt() at the completion
24727 - *      of any SCSI task management request.
24728 - *      This routine is registered with the MPT (base) driver at driver
24729 - *      load/init time via the mpt_register() API call.
24730 + *     mptscsih_taskmgmt_complete - Registered with Fusion MPT base driver
24731 + *     @ioc: Pointer to MPT_ADAPTER structure
24732 + *     @mf: Pointer to SCSI task mgmt request frame
24733 + *     @mr: Pointer to SCSI task mgmt reply frame
24734   *
24735 - *      Returns 1 indicating alloc'd request frame ptr should be freed.
24736 + *     This routine is called from mptbase.c::mpt_interrupt() at the completion
24737 + *     of any SCSI task management request.
24738 + *     This routine is registered with the MPT (base) driver at driver
24739 + *     load/init time via the mpt_register() API call.
24740 + *
24741 + *     Returns 1 indicating alloc'd request frame ptr should be freed.
24742   */
24743  int
24744  mptscsih_taskmgmt_complete(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, MPT_FRAME_HDR *mr)
24745 @@ -2739,26 +2507,27 @@ mptscsih_taskmgmt_complete(MPT_ADAPTER *
24746         SCSITaskMgmt_t          *pScsiTmReq;
24747         MPT_SCSI_HOST           *hd;
24748         unsigned long            flags;
24749 -       u16                      iocstatus = MPI_IOCSTATUS_SUCCESS;
24750 +       u16                      iocstatus;
24751         u8                       tmType;
24752 -       u32                      termination_count;
24753  
24754         dtmprintk((MYIOC_s_WARN_FMT "TaskMgmt completed (mf=%p,mr=%p)\n",
24755                         ioc->name, mf, mr));
24756 +       if (ioc->sh) {
24757                 /* Depending on the thread, a timer is activated for
24758                  * the TM request.  Delete this timer on completion of TM.
24759                  * Decrement count of outstanding TM requests.
24760                  */
24761 -       hd = (MPT_SCSI_HOST *)ioc->sh->hostdata;
24762 -       if (ioc->tmPtr) {
24763 -               del_timer(&ioc->TMtimer);
24764 -               mpt_free_msg_frame(ioc, ioc->tmPtr);
24765 -               ioc->tmPtr = NULL;
24766 +               hd = (MPT_SCSI_HOST *)ioc->sh->hostdata;
24767 +       } else {
24768 +               dtmprintk((MYIOC_s_WARN_FMT "TaskMgmt Complete: NULL Scsi Host Ptr\n",
24769 +                       ioc->name));
24770 +               return 1;
24771         }
24772  
24773         if (mr == NULL) {
24774 -               dtmprintk((MYIOC_s_WARN_FMT "ERROR! TaskMgmt Turbo Reply: Request %p\n",
24775 +               dtmprintk((MYIOC_s_WARN_FMT "ERROR! TaskMgmt Reply: NULL Request %p\n",
24776                         ioc->name, mf));
24777 +               return 1;
24778         } else {
24779                 pScsiTmReply = (SCSITaskMgmtReply_t*)mr;
24780                 pScsiTmReq = (SCSITaskMgmt_t*)mf;
24781 @@ -2771,40 +2540,31 @@ mptscsih_taskmgmt_complete(MPT_ADAPTER *
24782                         mptscsih_taskmgmt_response_code(ioc,
24783                             pScsiTmReply->ResponseCode);
24784  
24785 -               termination_count = le32_to_cpu(pScsiTmReply->TerminationCount);
24786 -
24787 -               iocstatus = le16_to_cpu(pScsiTmReply->IOCStatus) & MPI_IOCSTATUS_MASK;
24788 -               dtmprintk((MYIOC_s_WARN_FMT "  SCSI TaskMgmt (%d) IOCStatus=%04x IOCLogInfo=%08x TerminationCount=%d\n",
24789 -                       ioc->name, tmType, iocstatus, le32_to_cpu(pScsiTmReply->IOCLogInfo), termination_count));
24790 +               dtmprintk((MYIOC_s_WARN_FMT "  TaskType = %d, TerminationCount=%d\n",
24791 +                               ioc->name, tmType, le32_to_cpu(pScsiTmReply->TerminationCount)));
24792                 DBG_DUMP_TM_REPLY_FRAME((u32 *)pScsiTmReply);
24793  
24794 +               iocstatus = le16_to_cpu(pScsiTmReply->IOCStatus) & MPI_IOCSTATUS_MASK;
24795 +               dtmprintk((MYIOC_s_WARN_FMT "  SCSI TaskMgmt (%d) IOCStatus=%04x IOCLogInfo=%08x\n",
24796 +                       ioc->name, tmType, iocstatus, le32_to_cpu(pScsiTmReply->IOCLogInfo)));
24797                 /* Error?  (anything non-zero?) */
24798                 if (iocstatus) {
24799  
24800                         /* clear flags and continue.
24801                          */
24802 -                       if (tmType == MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK) {
24803 -                               if (termination_count == 1) {
24804 -                                       iocstatus = MPI_IOCSTATUS_SCSI_TASK_TERMINATED;
24805 -                                       dtmprintk((MYIOC_s_WARN_FMT "  SCSI Abort Task IOCStatus is now %04x\n",
24806 -                                               ioc->name, iocstatus));
24807 -                               }
24808 +                       if (tmType == MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK)
24809                                 hd->abortSCpnt = NULL;
24810 -                       }
24811  
24812                         /* If an internal command is present
24813                          * or the TM failed - reload the FW.
24814                          * FC FW may respond FAILED to an ABORT
24815                          */
24816 -                       else if (tmType == MPI_SCSITASKMGMT_TASKTYPE_RESET_BUS) {
24817 +                       if (tmType == MPI_SCSITASKMGMT_TASKTYPE_RESET_BUS) {
24818                                 if ((hd->cmdPtr) ||
24819                                     (iocstatus == MPI_IOCSTATUS_SCSI_TASK_MGMT_FAILED)) {
24820                                         if (mpt_HardResetHandler(ioc, NO_SLEEP) < 0) {
24821                                                 printk((KERN_WARNING
24822                                                         " Firmware Reload FAILED!!\n"));
24823 -                                               dfailprintk((MYIOC_s_ERR_FMT "taskmgmt_complete: HardReset failed\n", ioc->name));
24824 -                                       } else {
24825 -                                               dtmprintk((MYIOC_s_ERR_FMT "taskmgmt_complete: HardReset succeeded\n", ioc->name));
24826                                         }
24827                                 }
24828                         }
24829 @@ -2818,16 +2578,12 @@ mptscsih_taskmgmt_complete(MPT_ADAPTER *
24830  
24831         spin_lock_irqsave(&ioc->FreeQlock, flags);
24832         hd->tmPending = 0;
24833 -       hd->tm_iocstatus = iocstatus;
24834 -       hd->tmState = TM_STATE_NONE;
24835         spin_unlock_irqrestore(&ioc->FreeQlock, flags);
24836 +       hd->tmState = TM_STATE_NONE;
24837  
24838 -       hd->TM_wait_done = 1;
24839 -       wake_up(&hd->TM_waitq);
24840         return 1;
24841  }
24842  
24843 -
24844  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
24845  /*
24846   *     This is anyones guess quite frankly.
24847 @@ -2884,48 +2640,38 @@ mptscsih_slave_alloc(struct scsi_device 
24848  {
24849         struct Scsi_Host        *host = device->host;
24850         MPT_SCSI_HOST           *hd = (MPT_SCSI_HOST *)host->hostdata;
24851 -       MPT_ADAPTER             *ioc = hd->ioc;
24852 -       struct _MPT_DEVICE      *pMptTarget;
24853         VirtDevice              *pTarget;
24854 -       SpiCfgData             *pSpi;
24855 -        uint                   bus=device->channel, id=device->id, lun=device->lun;
24856 +       uint                    target = device->id, lun = device->lun;
24857         int                     indexed_lun, lun_index;
24858  
24859 +       if (hd == NULL)
24860 +               return -ENODEV;
24861  
24862 -       pMptTarget = ioc->Target_List[bus];
24863 -       pTarget = pMptTarget->Target[id];
24864 -       dinitprintk((MYIOC_s_INFO_FMT "mptscsih_slave_alloc: bus=%d id=%d lun=%d hd=%p pMptTarget=%p pTarget=%p\n",
24865 -               ioc->name, bus, id, lun, hd, pMptTarget, pTarget));
24866 -
24867 -       if (pTarget) {
24868 -               dinitprintk((MYIOC_s_ERR_FMT "slave_alloc: pTarget=%p already allocated!\n",
24869 -                       ioc->name, pTarget));
24870 +       if ((pTarget = hd->Targets[target]))
24871                 goto out;
24872 -       }
24873  
24874         pTarget = kmalloc(sizeof(VirtDevice), GFP_KERNEL);
24875         if (!pTarget) {
24876                 printk(MYIOC_s_ERR_FMT "slave_alloc kmalloc(%zd) FAILED!\n",
24877 -                       ioc->name, sizeof(VirtDevice));
24878 +                               hd->ioc->name, sizeof(VirtDevice));
24879                 return -ENOMEM;
24880         }
24881  
24882 +       dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_alloc target=%d lun=%d pTarget=%p\n",
24883 +                       hd->ioc->name, target, lun, pTarget));
24884         memset(pTarget, 0, sizeof(VirtDevice));
24885 -if (ioc->bus_type != SPI)
24886 -        pTarget->tflags = MPT_TARGET_FLAGS_Q_YES;
24887 -        pTarget->ioc = ioc;
24888 -        pTarget->id = id;
24889 -       pTarget->bus = bus;
24890 +       pTarget->tflags = MPT_TARGET_FLAGS_Q_YES;
24891 +       pTarget->ioc_id = hd->ioc->id;
24892 +       pTarget->target_id = device->id;
24893 +       pTarget->bus_id = device->channel;
24894         pTarget->last_lun = MPT_LAST_LUN;
24895 -       pMptTarget->Target[id] = pTarget;
24896 -       if (ioc->bus_type == SPI) {
24897 -                pSpi = &ioc->spi_data;
24898 -                 pSpi->dvStatus[id] |= (MPT_SCSICFG_NEED_DV |
24899 -                                         MPT_SCSICFG_DV_NOT_DONE);
24900 -
24901 -               if (ioc->raid_data.isRaid & (1 << device->id)) {
24902 +       pTarget->raidVolume = 0;
24903 +       pTarget->device = device;
24904 +       hd->Targets[target] = pTarget;
24905 +       if (hd->ioc->bus_type == SPI) {
24906 +               if (hd->ioc->raid_data.isRaid & (1 << device->id)) {
24907                         pTarget->raidVolume = 1;
24908 -                       ddvprintk((KERN_INFO
24909 +                       ddvtprintk((KERN_INFO
24910                             "RAID Volume @ id %d\n", device->id));
24911                 }
24912         }
24913 @@ -2937,8 +2683,8 @@ out:
24914         indexed_lun = (lun % 32);
24915         pTarget->luns[lun_index] |= (1 << indexed_lun);
24916  
24917 -       dinitprintk((MYIOC_s_WARN_FMT "mptscsih_slave_alloc: bus=%d id=%d lun=%d pTarget=%p num_luns=%d\n",
24918 -                       ioc->name, bus, id, lun, pTarget, pTarget->num_luns));
24919 +       dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_alloc target=%d lun=%d pTarget=%p num_luns=%d\n",
24920 +                       hd->ioc->name, target, lun, pTarget, pTarget->num_luns));
24921         return 0;
24922  }
24923  
24924 @@ -2951,24 +2697,20 @@ mptscsih_slave_destroy(struct scsi_devic
24925  {
24926         struct Scsi_Host        *host = device->host;
24927         MPT_SCSI_HOST           *hd = (MPT_SCSI_HOST *)host->hostdata;
24928 -       MPT_ADAPTER             *ioc = hd->ioc;
24929 -       struct _MPT_DEVICE      *pMptTarget;
24930         VirtDevice              *pTarget;
24931 -       uint                    bus=device->channel, id=device->id, lun=device->lun;
24932 +       uint                    target = device->id, lun = device->lun;
24933         int                     indexed_lun, lun_index;
24934  
24935 -       pMptTarget = ioc->Target_List[bus];
24936 -       pTarget = pMptTarget->Target[id];
24937 -       if (pTarget == NULL) {
24938 -               printk(MYIOC_s_WARN_FMT " mptscsih_slave_destroy bus=%d id=%d lun=%d pTarget=%p is NULL\n",
24939 -                       ioc->name, bus, id, lun, pTarget);
24940 +       if ((pTarget = hd->Targets[target]) == NULL) {
24941 +               printk(MYIOC_s_WARN_FMT " mptscsih_slave_destroy target=%d lun=%d pTarget=%p is NULL\n",
24942 +                       hd->ioc->name, target, lun, pTarget);
24943                 return;
24944         }
24945 -       dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_destroy bus=%d id=%d lun=%d type=%x pTarget=%p\n",
24946 -                       ioc->name, bus, id, lun, pTarget->inq_data[0], pTarget));
24947 +       dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_destroy target=%d lun=%d type=%x pTarget=%p\n",
24948 +                       hd->ioc->name, target, lun, pTarget->inq_data[0], pTarget));
24949  
24950 -       if((ioc->bus_type == SPI) &&
24951 -               mptscsih_is_phys_disk(ioc, bus, id)) {
24952 +       if((hd->ioc->bus_type == SPI) &&
24953 +               mptscsih_is_phys_disk(hd->ioc, target)) {
24954         ; /* this target reset shouldn't be issued to hidden
24955            * phys disk in a raid volume.  The result would
24956            * kill domain validation on that disk; e.g. disk
24957 @@ -2984,41 +2726,38 @@ mptscsih_slave_destroy(struct scsi_devic
24958              */
24959         }
24960  
24961 -       mptscsih_search_running_cmds(hd, id, lun);
24962 +       mptscsih_search_running_cmds(hd, target, lun);
24963  
24964         lun_index = (lun >> 5);  /* 32 luns per lun_index */
24965         indexed_lun = (lun % 32);
24966         pTarget->luns[lun_index] &= ~(1 << indexed_lun);
24967  
24968         if (--pTarget->num_luns) {
24969 -               dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_destroy bus=%d id=%d lun=%d pTarget=%p num_luns=%d luns[0]=%x returning\n",
24970 -                       ioc->name, bus, id, lun, pTarget, pTarget->num_luns, pTarget->luns[0]));
24971 +               dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_destroy target=%d lun=%d pTarget=%p num_luns=%d luns[0]=%x returning\n",
24972 +                       hd->ioc->name, target, lun, pTarget, pTarget->num_luns, pTarget->luns[0]));
24973                 return;
24974         }
24975  
24976 -       dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_destroy bus=%d id=%d lun=%d freeing pTarget=%p\n",
24977 -                       ioc->name, bus, id, lun, pTarget));
24978 -
24979 -       if (ioc->bus_type == SPI) {
24980 -               if (mptscsih_is_phys_disk(ioc, bus, id)) {
24981 -                       ioc->spi_data.forceDv |= MPT_SCSICFG_RELOAD_IOC_PG3;
24982 -    dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_destroy PhysDisk bus=%d id=% d lun=%d pTarget=%p retained\n",ioc->name, bus, id, lun, pTarget));
24983 -
24984 -
24985 +       dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_destroy target=%d lun=%d freeing pTarget=%p\n",
24986 +                       hd->ioc->name, target, lun, pTarget));
24987 +       kfree(pTarget);
24988 +       hd->Targets[target] = NULL;
24989 +
24990 +       if (hd->ioc->bus_type == SPI) {
24991 +               if (mptscsih_is_phys_disk(hd->ioc, target)) {
24992 +                       hd->ioc->spi_data.forceDv |= MPT_SCSICFG_RELOAD_IOC_PG3;
24993                 } else {
24994 -                       ioc->spi_data.dvStatus[id] =
24995 -                (MPT_SCSICFG_NEGOTIATE | MPT_SCSICFG_DV_NOT_DONE);
24996 -                kfree(pTarget);
24997 -                pMptTarget->Target[id] = NULL;
24998 -                dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_destroy bus=%d id=%d lun=%d pTarget=%p completed\n",ioc->name, bus, id, lun, pTarget));
24999 +                       hd->ioc->spi_data.dvStatus[target] =
25000 +                               MPT_SCSICFG_NEGOTIATE;
25001  
25002 +                       if (!hd->negoNvram) {
25003 +                               hd->ioc->spi_data.dvStatus[target] |=
25004 +                                       MPT_SCSICFG_DV_NOT_DONE;
25005 +                       }
25006                 }
25007 -}else {
25008 -kfree(pTarget);
25009 -pMptTarget->Target[id] = NULL;
25010 -dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_destroy bus=%d id=%d lun=%d pTarget=%p completed\n",
25011 -ioc->name, bus, id, lun, pTarget));
25012 -      }
25013 +       }
25014 +       dsprintk((MYIOC_s_INFO_FMT " mptscsih_slave_destroy target=%d lun=%d pTarget=%p completed\n",
25015 +                       hd->ioc->name, target, lun, pTarget));
25016  }
25017  
25018  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
25019 @@ -3033,34 +2772,29 @@ int
25020  mptscsih_change_queue_depth(struct scsi_device *sdev, int qdepth)
25021  {
25022         MPT_SCSI_HOST   *hd = (MPT_SCSI_HOST *)sdev->host->hostdata;
25023 -       MPT_ADAPTER     *ioc = hd->ioc;
25024 -       struct _MPT_DEVICE      *pMptTarget;
25025         VirtDevice *pTarget;
25026         int     max_depth;
25027         int     tagged;
25028  
25029 -       pMptTarget = ioc->Target_List[sdev->channel];
25030 -       pTarget = pMptTarget->Target[sdev->id];
25031 -       if (pTarget == NULL)
25032 +       if (!(pTarget = hd->Targets[sdev->id]))
25033                 return 0;
25034  
25035 -
25036 -       if (pTarget->tflags & MPT_TARGET_FLAGS_VALID_INQUIRY) {
25037 -               if (!(pTarget->tflags & MPT_TARGET_FLAGS_Q_YES))
25038 -                       max_depth = 1;
25039 -               else if (ioc->bus_type == SPI) {
25040 -                       if (((pTarget->inq_data[0] & 0x1f) == 0x00) &&
25041 -                                (pTarget->minSyncFactor <= MPT_ULTRA160 ))
25042 +       if (hd->ioc->bus_type == SPI) {
25043 +               if (pTarget->tflags & MPT_TARGET_FLAGS_VALID_INQUIRY) {
25044 +                       if (!(pTarget->tflags & MPT_TARGET_FLAGS_Q_YES))
25045 +                               max_depth = 1;
25046 +                       else if (((pTarget->inq_data[0] & 0x1f) == 0x00) &&
25047 +                                (pTarget->minSyncFactor <= MPT_ULTRA160 ))
25048                                 max_depth = MPT_SCSI_CMD_PER_DEV_HIGH;
25049                         else
25050 -                       max_depth = MPT_SCSI_CMD_PER_DEV_LOW;
25051 +                               max_depth = MPT_SCSI_CMD_PER_DEV_LOW;
25052 +               } else {
25053 +                       /* error case - No Inq. Data */
25054 +                       max_depth = 1;
25055 +               }
25056 +       } else
25057 +               max_depth = MPT_SCSI_CMD_PER_DEV_HIGH;
25058  
25059 -               } else
25060 -                       max_depth = MPT_SCSI_CMD_PER_DEV_HIGH;
25061 -       } else {
25062 -               /* error case - No Inq. Data */
25063 -               max_depth = 1;
25064 -       }
25065         if (qdepth > max_depth)
25066                 qdepth = max_depth;
25067         if (qdepth == 1)
25068 @@ -3082,29 +2816,25 @@ int
25069  mptscsih_slave_configure(struct scsi_device *device)
25070  {
25071         struct Scsi_Host        *sh = device->host;
25072 -       struct _MPT_DEVICE      *pMptTarget;
25073         VirtDevice              *pTarget;
25074         MPT_SCSI_HOST           *hd = (MPT_SCSI_HOST *)sh->hostdata;
25075 -       MPT_ADAPTER             *ioc = hd->ioc;
25076         int                     rc;
25077  
25078 -       dinitprintk((MYIOC_s_INFO_FMT
25079 -               "%s: device @ %p, id=%d, LUN=%d, channel=%d\n",
25080 -               ioc->name, __FUNCTION__, device, device->id, device->lun,
25081 -               device->channel));
25082 -       dinitprintk((MYIOC_s_INFO_FMT
25083 -                "sdtr %d wdtr %d ppr %d inq length=%d\n",
25084 -               ioc->name, device->sdtr, device->wdtr,
25085 +       dsprintk((MYIOC_s_INFO_FMT
25086 +               "device @ %p, id=%d, LUN=%d, channel=%d\n",
25087 +               hd->ioc->name, device, device->id, device->lun, device->channel));
25088 +       dsprintk((MYIOC_s_INFO_FMT
25089 +               "sdtr %d wdtr %d ppr %d inq length=%d\n",
25090 +               hd->ioc->name, device->sdtr, device->wdtr,
25091                 device->ppr, device->inquiry_len));
25092  
25093 -       if (device->id >= ioc->DevicesPerBus) {
25094 +       if (device->id > sh->max_id) {
25095                 /* error case, should never happen */
25096                 scsi_adjust_queue_depth(device, 0, 1);
25097                 goto slave_configure_exit;
25098         }
25099  
25100 -       pMptTarget = ioc->Target_List[device->channel];
25101 -       pTarget = pMptTarget->Target[device->id];
25102 +       pTarget = hd->Targets[device->id];
25103  
25104         if (pTarget == NULL) {
25105                 /* Driver doesn't know about this device.
25106 @@ -3122,19 +2852,19 @@ mptscsih_slave_configure(struct scsi_dev
25107                 pTarget->configured_lun=1;
25108  
25109         /* LUN persistancy support */
25110 -       if (ioc->bus_type == FC) {
25111 +       if (hd->ioc->bus_type == FC) {
25112                 FCDevicePage0_t fcDevicePage;
25113  
25114 -               rc = mptscsih_readFCDevicePage0(ioc,
25115 -                   pTarget->bus, pTarget->id, &fcDevicePage);
25116 +               rc = mptscsih_readFCDevicePage0(hd->ioc,
25117 +                   pTarget->bus_id, pTarget->target_id, &fcDevicePage);
25118  
25119                 if (rc > offsetof(FCDevicePage0_t,PortIdentifier)) {
25120                         pTarget->WWPN = fcDevicePage.WWPN;
25121                         pTarget->WWNN = fcDevicePage.WWNN;
25122  
25123                         dsprintk((MYIOC_s_INFO_FMT
25124 -                       "  bus=%d id=%d is WWPN = %08x%08x, WWNN = %08x%08x\n",
25125 -                               ioc->name, pTarget->bus, pTarget->id,
25126 +                       "  target %d is WWPN = %08x%08x, WWNN = %08x%08x\n",
25127 +                               hd->ioc->name, pTarget->target_id,
25128                                 le32_to_cpu(fcDevicePage.WWPN.High),
25129                                 le32_to_cpu(fcDevicePage.WWPN.Low),
25130                                 le32_to_cpu(fcDevicePage.WWNN.High),
25131 @@ -3147,19 +2877,19 @@ mptscsih_slave_configure(struct scsi_dev
25132                 device->inquiry, device->inquiry_len );
25133         mptscsih_change_queue_depth(device, MPT_SCSI_CMD_PER_DEV_HIGH);
25134  
25135 -       dinitprintk((MYIOC_s_INFO_FMT
25136 +       dsprintk((MYIOC_s_INFO_FMT
25137                 "Queue depth=%d, tflags=%x\n",
25138 -               ioc->name, device->queue_depth, pTarget->tflags));
25139 +               hd->ioc->name, device->queue_depth, pTarget->tflags));
25140  
25141 -       dinitprintk((MYIOC_s_INFO_FMT
25142 +       dsprintk((MYIOC_s_INFO_FMT
25143                 "negoFlags=%x, maxOffset=%x, SyncFactor=%x\n",
25144 -               ioc->name, pTarget->negoFlags, pTarget->maxOffset, pTarget->minSyncFactor));
25145 +               hd->ioc->name, pTarget->negoFlags, pTarget->maxOffset, pTarget->minSyncFactor));
25146  
25147  slave_configure_exit:
25148  
25149 -       dinitprintk((MYIOC_s_INFO_FMT
25150 +       dsprintk((MYIOC_s_INFO_FMT
25151                 "tagged %d, simple %d, ordered %d\n",
25152 -               ioc->name,device->tagged_supported, device->simple_tags,
25153 +               hd->ioc->name,device->tagged_supported, device->simple_tags,
25154                 device->ordered_tags));
25155  
25156         return 0;
25157 @@ -3220,20 +2950,16 @@ mptscsih_poll(struct scsi_device *sdev)
25158  static void
25159  mptscsih_copy_sense_data(struct scsi_cmnd *sc, MPT_SCSI_HOST *hd, MPT_FRAME_HDR *mf, SCSIIOReply_t *pScsiReply)
25160  {
25161 -       MPT_ADAPTER     *ioc = hd->ioc;
25162 -       struct _MPT_DEVICE      *pMptTarget;
25163         VirtDevice      *pTarget;
25164         SCSIIORequest_t *pReq;
25165         u32              sense_count = le32_to_cpu(pScsiReply->SenseCount);
25166 -       int              bus, id;
25167 +       int              target;
25168  
25169         /* Get target structure
25170          */
25171         pReq = (SCSIIORequest_t *) mf;
25172 -       bus = (int) pReq->Bus;
25173 -       id = (int) pReq->TargetID;
25174 -       pMptTarget = ioc->Target_List[bus];
25175 -       pTarget = pMptTarget->Target[id];
25176 +       target = (int) pReq->TargetID;
25177 +       pTarget = hd->Targets[target];
25178  
25179         if (sense_count) {
25180                 u8 *sense_data;
25181 @@ -3241,15 +2967,15 @@ mptscsih_copy_sense_data(struct scsi_cmn
25182  
25183                 /* Copy the sense received into the scsi command block. */
25184                 req_index = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
25185 -               sense_data = ((u8 *)ioc->sense_buf_pool + (req_index * MPT_SENSE_BUFFER_ALLOC));
25186 +               sense_data = ((u8 *)hd->ioc->sense_buf_pool + (req_index * MPT_SENSE_BUFFER_ALLOC));
25187                 memcpy(sc->sense_buffer, sense_data, SNS_LEN(sc));
25188 -               DBG_DUMP_SENSE_DATA(sense_data);
25189  
25190                 /* Log SMART data (asc = 0x5D, non-IM case only) if required.
25191                  */
25192 -               if ((ioc->events) && (ioc->eventTypes & (1 << MPI_EVENT_SCSI_DEVICE_STATUS_CHANGE))) {
25193 +               if ((hd->ioc->events) && (hd->ioc->eventTypes & (1 << MPI_EVENT_SCSI_DEVICE_STATUS_CHANGE))) {
25194                         if ((sense_data[12] == 0x5D) && (pTarget->raidVolume == 0)) {
25195                                 int idx;
25196 +                               MPT_ADAPTER *ioc = hd->ioc;
25197  
25198                                 idx = ioc->eventContext % MPTCTL_EVENT_LOG_SIZE;
25199                                 ioc->events[idx].event = MPI_EVENT_SCSI_DEVICE_STATUS_CHANGE;
25200 @@ -3287,21 +3013,19 @@ mptscsih_copy_sense_data(struct scsi_cmn
25201                 }
25202         } else {
25203                 dprintk((MYIOC_s_INFO_FMT "Hmmm... SenseData len=0! (?)\n",
25204 -                               ioc->name));
25205 +                               hd->ioc->name));
25206         }
25207  }
25208  
25209 -static int
25210 +static u32
25211  SCPNT_TO_LOOKUP_IDX(struct scsi_cmnd *sc)
25212  {
25213         MPT_SCSI_HOST *hd;
25214 -       MPT_ADAPTER     *ioc;
25215         int i;
25216  
25217         hd = (MPT_SCSI_HOST *) sc->device->host->hostdata;
25218  
25219 -       ioc = hd->ioc;
25220 -       for (i = 0; i < ioc->req_depth; i++) {
25221 +       for (i = 0; i < hd->ioc->req_depth; i++) {
25222                 if (hd->ScsiLookup[i] == sc) {
25223                         return i;
25224                 }
25225 @@ -3315,10 +3039,8 @@ int
25226  mptscsih_ioc_reset(MPT_ADAPTER *ioc, int reset_phase)
25227  {
25228         MPT_SCSI_HOST   *hd;
25229 -       struct _MPT_DEVICE      *pMptTarget;
25230 -       VirtDevice      *pTarget;
25231         unsigned long    flags;
25232 -       int             bus, id, ii;
25233 +       int             ii;
25234         int             n;
25235  
25236         dtmprintk((KERN_INFO MYNAM
25237 @@ -3338,8 +3060,11 @@ mptscsih_ioc_reset(MPT_ADAPTER *ioc, int
25238         if (reset_phase == MPT_IOC_SETUP_RESET) {
25239                 dtmprintk((MYIOC_s_WARN_FMT "Setup-Diag Reset\n", ioc->name));
25240  
25241 -                mptscsih_flush_running_cmds(hd);
25242 -                dtmprintk((MYIOC_s_WARN_FMT "Setup-Diag Complete\n", ioc->name));
25243 +               /* Clean Up:
25244 +                * 1. Set Hard Reset Pending Flag
25245 +                * All new commands go to doneQ
25246 +                */
25247 +               hd->resetPending = 1;
25248  
25249         } else if (reset_phase == MPT_IOC_PRE_RESET) {
25250                 dtmprintk((MYIOC_s_WARN_FMT "Pre-Diag Reset\n", ioc->name));
25251 @@ -3358,41 +3083,28 @@ mptscsih_ioc_reset(MPT_ADAPTER *ioc, int
25252                  * free these resources.
25253                  */
25254                 if (hd->cmdPtr) {
25255 -                       del_timer(&hd->InternalCmdTimer);
25256 +                       del_timer(&hd->timer);
25257                         mpt_free_msg_frame(ioc, hd->cmdPtr);
25258 -                        hd->cmdPtr = NULL;
25259                 }
25260 -               /* 2d. If a task management has not completed,
25261 -                * free resources associated with this request.
25262 -                */
25263 -               if (ioc->tmPtr) {
25264 -                       del_timer(&ioc->TMtimer);
25265 -                       mpt_free_msg_frame(ioc, ioc->tmPtr);
25266 -                       ioc->tmPtr = NULL;
25267 -               }
25268  
25269 -               dtmprintk((MYIOC_s_WARN_FMT "Pre-Reset complete.\n", ioc->name));
25270 +               dtmprintk((MYIOC_s_WARN_FMT "Pre-Reset complete.\n", ioc->name));
25271  
25272         } else {
25273                 dtmprintk((MYIOC_s_WARN_FMT "Post-Diag Reset\n", ioc->name));
25274  
25275                 if (ioc->bus_type == FC) {
25276                         n = 0;
25277 -                       for (bus = 0; bus < ioc->NumberOfBuses; bus++) {
25278 -                               pMptTarget = ioc->Target_List[bus];
25279 -                               for (id=0; id < ioc->DevicesPerBus; id++) {
25280 -                                       pTarget = pMptTarget->Target[id];
25281 -                                       if (pTarget) {
25282 -                                               dsprintk((MYIOC_s_INFO_FMT
25283 -                                                       "bus=%d id=%d is known to be WWPN %08x%08x, WWNN %08x%08x\n",
25284 -                                                       ioc->name, bus, id,
25285 -                                                       le32_to_cpu(pTarget->WWPN.High),
25286 -                                                       le32_to_cpu(pTarget->WWPN.Low),
25287 -                                                       le32_to_cpu(pTarget->WWNN.High),
25288 -                                                       le32_to_cpu(pTarget->WWNN.Low)));
25289 -                                               mptscsih_writeFCPortPage3(hd, bus, id);
25290 -                                               n++;
25291 -                                       }
25292 +                       for (ii=0; ii < ioc->sh->max_id; ii++) {
25293 +                               if (hd->Targets && hd->Targets[ii]) {
25294 +                                       dsprintk((MYIOC_s_INFO_FMT
25295 +                                               "target %d is known to be WWPN %08x%08x, WWNN %08x%08x\n",
25296 +                                               ioc->name, ii,
25297 +                                               le32_to_cpu(hd->Targets[ii]->WWPN.High),
25298 +                                               le32_to_cpu(hd->Targets[ii]->WWPN.Low),
25299 +                                               le32_to_cpu(hd->Targets[ii]->WWNN.High),
25300 +                                               le32_to_cpu(hd->Targets[ii]->WWNN.Low)));
25301 +                                       mptscsih_writeFCPortPage3(hd, ii);
25302 +                                       n++;
25303                                 }
25304                         }
25305  
25306 @@ -3408,7 +3120,7 @@ mptscsih_ioc_reset(MPT_ADAPTER *ioc, int
25307  
25308                 /* ScsiLookup initialization
25309                  */
25310 -               for (ii=0; ii < ioc->req_depth; ii++)
25311 +               for (ii=0; ii < hd->ioc->req_depth; ii++)
25312                         hd->ScsiLookup[ii] = NULL;
25313  
25314                 /* 2. Chain Buffer initialization
25315 @@ -3417,19 +3129,17 @@ mptscsih_ioc_reset(MPT_ADAPTER *ioc, int
25316                 /* 4. Renegotiate to all devices, if SPI
25317                  */
25318                 if (ioc->bus_type == SPI) {
25319 -                       dnegoprintk((MYIOC_s_WARN_FMT "%s: writeSDP1: ALL_IDS USE_NVRAM\n",
25320 -                               ioc->name, __FUNCTION__));
25321 -                       mpt_writeSDP1(ioc, 0, 0, (MPT_SCSICFG_ALL_IDS | MPT_SCSICFG_USE_NVRAM));
25322 -
25323 +                       dnegoprintk(("writeSDP1: ALL_IDS USE_NVRAM\n"));
25324 +                       mptscsih_writeSDP1(hd, 0, 0, MPT_SCSICFG_ALL_IDS | MPT_SCSICFG_USE_NVRAM);
25325                 }
25326  
25327                 /* 5. Enable new commands to be posted
25328                  */
25329                 spin_lock_irqsave(&ioc->FreeQlock, flags);
25330                 hd->tmPending = 0;
25331 +               spin_unlock_irqrestore(&ioc->FreeQlock, flags);
25332 +               hd->resetPending = 0;
25333                 hd->tmState = TM_STATE_NONE;
25334 -                spin_unlock_irqrestore(&ioc->FreeQlock, flags);
25335 -
25336  
25337                 /* 6. If there was an internal command,
25338                  * wake this process up.
25339 @@ -3448,9 +3158,8 @@ mptscsih_ioc_reset(MPT_ADAPTER *ioc, int
25340                 /* 7. Set flag to force DV and re-read IOC Page 3
25341                  */
25342                 if (ioc->bus_type == SPI) {
25343 -ioc->spi_data.forceDv = MPT_SCSICFG_RELOAD_IOC_PG3;
25344 -ddvprintk(("Set reload IOC Pg3 Flag\n"));
25345 -
25346 +                       ioc->spi_data.forceDv = MPT_SCSICFG_NEED_DV | MPT_SCSICFG_RELOAD_IOC_PG3;
25347 +                       ddvtprintk(("Set reload IOC Pg3 Flag\n"));
25348                 }
25349  
25350                 dtmprintk((MYIOC_s_WARN_FMT "Post-Reset complete.\n", ioc->name));
25351 @@ -3468,13 +3177,9 @@ mptscsih_event_process(MPT_ADAPTER *ioc,
25352  {
25353         MPT_SCSI_HOST *hd;
25354         u8 event = le32_to_cpu(pEvReply->Event) & 0xFF;
25355 -       struct _MPT_DEVICE      *pMptTarget;
25356 -       VirtDevice              *pTarget;
25357 -       int      physDiskNum, bus, id;
25358 -
25359 -       devtprintk((MYIOC_s_WARN_FMT "MPT event (=%02Xh) routed to SCSI host driver!\n",
25360 -                       ioc->name, event));
25361  
25362 +       devtprintk((MYIOC_s_INFO_FMT "MPT event (=%02Xh) routed to SCSI host driver!\n",
25363 +                       ioc->name, event));
25364  
25365         if (ioc->sh == NULL ||
25366                 ((hd = (MPT_SCSI_HOST *)ioc->sh->hostdata) == NULL))
25367 @@ -3508,53 +3213,16 @@ mptscsih_event_process(MPT_ADAPTER *ioc,
25368  #ifdef MPTSCSIH_ENABLE_DOMAIN_VALIDATION
25369         case MPI_EVENT_INTEGRATED_RAID:                 /* 0B */
25370         {
25371 +               pMpiEventDataRaid_t pRaidEventData =
25372 +                   (pMpiEventDataRaid_t) pEvReply->Data;
25373  
25374 -#ifdef MPTSCSIH_ENABLE_DOMAIN_VALIDATION
25375 -                pMpiEventDataRaid_t pRaidEventData =
25376 -                (pMpiEventDataRaid_t) &pEvReply->Data;
25377 -
25378 -/* Domain Validation Needed */
25379 +               /* Domain Validation Needed */
25380                 if (ioc->bus_type == SPI &&
25381                         pRaidEventData->ReasonCode ==
25382                         MPI_EVENT_RAID_RC_DOMAIN_VAL_NEEDED) {
25383 -                         SpiCfgData      *pSpi;
25384 -                       physDiskNum = pRaidEventData->PhysDiskNum;
25385 -                       if (ioc->raid_data.pIocPg3) {
25386 -                               id = ioc->raid_data.pIocPg3->PhysDisk[physDiskNum].PhysDiskID;
25387 -                               bus = ioc->raid_data.pIocPg3->PhysDisk[physDiskNum].PhysDiskBus;
25388 -                               pMptTarget = ioc->Target_List[bus];
25389 -                               pTarget = (VirtDevice *)pMptTarget->Target[id];
25390 -                               ddvprintk((KERN_WARNING "%s: Raid Event: DV Requested for PhysDiskNum=%d bus=%d id=%d pTarget=%p\n",
25391 -                                       ioc->name, physDiskNum, bus, id, pTarget));
25392 -                       } else {
25393 -                               ddvprintk((KERN_WARNING "%s: Raid Event: DV Requested for PhysDiskNum=%d but raid_data.pIocPg3 is NULL\n",
25394 -                                       ioc->name, physDiskNum));
25395 -                               break;
25396 -                       }
25397 -                       pSpi = &ioc->spi_data;
25398 -                       pSpi->dvStatus[id] |= (MPT_SCSICFG_PHYSDISK_DV_ONLY |
25399 -                                             MPT_SCSICFG_NEED_DV |
25400 -                                             MPT_SCSICFG_DV_NOT_DONE);
25401 -
25402 -                       if (pTarget == NULL) {
25403 - ddvprintk((KERN_WARNING " Raid Event: DV Requested for PhysDiskNum=%d bus=%d id=%d but pTarget is NULL\n",
25404 -                                       physDiskNum, bus, id));
25405 -                               mptscsih_initTarget(hd, bus, id, 0,
25406 -                                       NULL, 0 );
25407 -                               pTarget = (VirtDevice *)pMptTarget->Target[id];
25408 - ddvprintk((KERN_WARNING "%s: Raid Event: DV Requested for PhysDiskNum=%d bus=%d id=%d pTarget%p now\n",
25409 -                                       ioc->name, physDiskNum, bus, id, pTarget));
25410 -                       }
25411 -                       pSpi->forceDv |= MPT_SCSICFG_RELOAD_IOC_PG3;
25412 - ddvprintk((KERN_WARNING "%s: Raid Event: Scheduling DV for PhysDiskNum=%d bus=%d id=%d pTarget=%p\n",
25413 -                               ioc->name, physDiskNum, bus, id, pTarget));
25414 - INIT_WORK(&pTarget->dvTask, mptscsih_domainValidation, (void *) pTarget);
25415 -                       schedule_work(&pTarget->dvTask);
25416 - ddvprintk((KERN_WARNING "%s: Raid Event: DV Scheduled for PhysDiskNum=%d bus=%d id=%d pTarget=%p\n",
25417 -                               ioc->name, physDiskNum, bus, id, pTarget));
25418 -#endif
25419  
25420 -       }
25421 +                       mptscsih_set_dvflags_raid(hd, pRaidEventData->PhysDiskNum);
25422 +               }
25423                 break;
25424         }
25425  #endif
25426 @@ -3575,8 +3243,8 @@ mptscsih_event_process(MPT_ADAPTER *ioc,
25427  /*
25428   *     mptscsih_initTarget - Target, LUN alloc/free functionality.
25429   *     @hd: Pointer to MPT_SCSI_HOST structure
25430 - *     @bus: Bus number (?)
25431 - *     @id: SCSI target id
25432 + *     @bus_id: Bus number (?)
25433 + *     @target_id: SCSI target id
25434   *     @lun: SCSI LUN id
25435   *     @data: Pointer to data
25436   *     @dlen: Number of INQUIRY bytes
25437 @@ -3589,17 +3257,16 @@ mptscsih_event_process(MPT_ADAPTER *ioc,
25438   *
25439   */
25440  static void
25441 -mptscsih_initTarget(MPT_SCSI_HOST *hd, int bus, int id, u8 lun, char *data, int dlen)
25442 +mptscsih_initTarget(MPT_SCSI_HOST *hd, int bus_id, int target_id, u8 lun, char *data, int dlen)
25443  {
25444         int             indexed_lun, lun_index;
25445         MPT_ADAPTER     *ioc = hd->ioc;
25446 -       struct _MPT_DEVICE      *pMptTarget;
25447         VirtDevice      *pTarget;
25448         SpiCfgData      *pSpi;
25449         char            data_56;
25450  
25451 -       dinitprintk((MYIOC_s_WARN_FMT "initTarget bus=%d id=%d lun=%d hd=%p\n",
25452 -                       ioc->name, bus, id, lun, hd));
25453 +       dinitprintk((MYIOC_s_INFO_FMT "initTarget bus=%d id=%d lun=%d hd=%p\n",
25454 +                       ioc->name, bus_id, target_id, lun, hd));
25455  
25456         /*
25457          * If the peripheral qualifier filter is enabled then if the target reports a 0x1
25458 @@ -3610,71 +3277,29 @@ mptscsih_initTarget(MPT_SCSI_HOST *hd, i
25459          * around a bug in th emid-layer in some distributions in which the mid-layer will
25460          * continue to try to communicate to the LUN and evntually create a dummy LUN.
25461         */
25462 -       if (hd->mpt_pq_filter && dlen && (data[0] & 0x20))
25463 +       if (hd->mpt_pq_filter && dlen && (data[0] & 0xE0))
25464                 data[0] |= 0x40;
25465  
25466         /* Is LUN supported? If so, upper 2 bits will be 0
25467         * in first byte of inquiry data.
25468         */
25469 +       if (data[0] & 0xe0)
25470 +               return;
25471  
25472 -        if (dlen && (data[0] & 0xe0))
25473 -       return;
25474 -
25475 -       pMptTarget = ioc->Target_List[bus];
25476 -       pTarget = pMptTarget->Target[id];
25477 -       if (pTarget == NULL) {
25478 -               dinitprintk((MYIOC_s_INFO_FMT "initTarget bus=%d id=%d lun=%d pTarget is NULL\n"
25479 -,
25480 -                       ioc->name, bus, id, lun));
25481 -               pTarget = kmalloc(sizeof(VirtDevice), GFP_KERNEL);
25482 -               if (!pTarget) {
25483 -                       printk(MYIOC_s_ERR_FMT "initTarget kmalloc(%zd) FAILED!\n",
25484 -                               ioc->name, sizeof(VirtDevice));
25485 -                       return;
25486 -               }
25487 -
25488 -               memset(pTarget, 0, sizeof(VirtDevice));
25489 -               if (ioc->bus_type != SPI)
25490 -                       pTarget->tflags = MPT_TARGET_FLAGS_Q_YES;
25491 -               pTarget->ioc = ioc;
25492 -               pTarget->id = id;
25493 -               pTarget->bus = bus;
25494 -               pTarget->last_lun = MPT_LAST_LUN;
25495 -               pTarget->raidVolume = 0;
25496 -               pMptTarget->Target[id] = pTarget;
25497 -               if (ioc->bus_type == SPI) {
25498 -                       if (ioc->raid_data.isRaid & (1 << id)) {
25499 -                               pTarget->raidVolume = 1;
25500 -                               ddvprintk((KERN_INFO
25501 -                                   "RAID Volume @ id %d\n", id));
25502 -                       }
25503 -               }
25504 -
25505 +       if ((pTarget = hd->Targets[target_id]) == NULL) {
25506                 return;
25507 -}
25508 -       dinitprintk((MYIOC_s_WARN_FMT "initTarget bus=%d id=%d lun=%d pTarget=%p\n",
25509 -                       ioc->name, bus, id, lun, pTarget));
25510 -       pSpi = &ioc->spi_data;
25511 -       pTarget->ioc = ioc;
25512 -       pTarget->tflags &= ~MPT_TARGET_FLAGS_DELETED;
25513 +       }
25514  
25515         lun_index = (lun >> 5);  /* 32 luns per lun_index */
25516         indexed_lun = (lun % 32);
25517         pTarget->luns[lun_index] |= (1 << indexed_lun);
25518  
25519 -       if (!(pTarget->tflags & MPT_TARGET_FLAGS_VALID_INQUIRY)) {
25520 -               if ( dlen > 8 ) {
25521 -                       memcpy (pTarget->inq_data, data, 8);
25522 -               } else {
25523 -                       memcpy (pTarget->inq_data, data, dlen);
25524 -               }
25525 -       }
25526         if (ioc->bus_type == SPI) {
25527                 if ((data[0] == TYPE_PROCESSOR) && (ioc->spi_data.Saf_Te)) {
25528                         /* Treat all Processors as SAF-TE if
25529                          * command line option is set */
25530                         pTarget->tflags |= MPT_TARGET_FLAGS_SAF_TE_ISSUED;
25531 -                       mptscsih_writeIOCPage4(hd, id, bus);
25532 +                       mptscsih_writeIOCPage4(hd, target_id, bus_id);
25533                 }else if ((data[0] == TYPE_PROCESSOR) &&
25534                         !(pTarget->tflags & MPT_TARGET_FLAGS_SAF_TE_ISSUED )) {
25535                         if ( dlen > 49 ) {
25536 @@ -3686,17 +3311,29 @@ mptscsih_initTarget(MPT_SCSI_HOST *hd, i
25537                                      data[48] == 'T' &&
25538                                      data[49] == 'E' ) {
25539                                         pTarget->tflags |= MPT_TARGET_FLAGS_SAF_TE_ISSUED;
25540 -                                       mptscsih_writeIOCPage4(hd, id, bus);
25541 +                                       mptscsih_writeIOCPage4(hd, target_id, bus_id);
25542                                 }
25543                         }
25544                 }
25545 -data_56 = 0x00;  /* Default to no Ultra 160 or 320 capabilities if Inq data length is < 57 */
25546 -
25547 -
25548                 if (!(pTarget->tflags & MPT_TARGET_FLAGS_VALID_INQUIRY)) {
25549 +                       if ( dlen > 8 ) {
25550 +                               memcpy (pTarget->inq_data, data, 8);
25551 +                       } else {
25552 +                               memcpy (pTarget->inq_data, data, dlen);
25553 +                       }
25554 +
25555 +                       /* If have not done DV, set the DV flag.
25556 +                        */
25557 +                       pSpi = &ioc->spi_data;
25558 +                       if ((data[0] == TYPE_TAPE) || (data[0] == TYPE_PROCESSOR)) {
25559 +                               if (pSpi->dvStatus[target_id] & MPT_SCSICFG_DV_NOT_DONE)
25560 +                                       pSpi->dvStatus[target_id] |= MPT_SCSICFG_NEED_DV;
25561 +                       }
25562  
25563                         pTarget->tflags |= MPT_TARGET_FLAGS_VALID_INQUIRY;
25564  
25565 +
25566 +                       data_56 = 0x00;  /* Default to no Ultra 160 or 320 capabilities if Inq data length is < 57 */
25567                         if (dlen > 56) {
25568                                 if ( (!(pTarget->tflags & MPT_TARGET_FLAGS_VALID_56))) {
25569                                 /* Update the target capabilities
25570 @@ -3705,6 +3342,7 @@ data_56 = 0x00;  /* Default to no Ultra 
25571                                         pTarget->tflags |= MPT_TARGET_FLAGS_VALID_56;
25572                                 }
25573                         }
25574 +                       mptscsih_setTargetNegoParms(hd, pTarget, data_56);
25575                 } else {
25576                         /* Initial Inquiry may not request enough data bytes to
25577                          * obtain byte 57.  DV will; if target doesn't return
25578 @@ -3715,40 +3353,25 @@ data_56 = 0x00;  /* Default to no Ultra 
25579                                  */
25580                                         data_56 = data[56];
25581                                         pTarget->tflags |= MPT_TARGET_FLAGS_VALID_56;
25582 +                                       mptscsih_setTargetNegoParms(hd, pTarget, data_56);
25583                                 }
25584                         }
25585                 }
25586 -
25587 -mptscsih_setTargetNegoParms(hd, pTarget, data_56);
25588 -if (pSpi->dvStatus[id] & MPT_SCSICFG_NEED_DV) {
25589 -       ddvprintk((MYIOC_s_WARN_FMT "%s: DV Scheduled for non-PhysDisk id %d\n",
25590 -                 ioc->name, __FUNCTION__, id));
25591 -INIT_WORK(&pTarget->dvTask, mptscsih_domainValidation, (void *) pTarget);
25592 -schedule_work(&pTarget->dvTask);
25593 -       }
25594 -       } else {
25595 -         pTarget->tflags |= MPT_TARGET_FLAGS_VALID_INQUIRY;
25596 -         if (ioc->bus_type == SAS) {
25597 -            if ( (pTarget->inq_data[7] & 0x02) == 0) {
25598 -                 pTarget->tflags &= ~MPT_TARGET_FLAGS_Q_YES;
25599 -                     }
25600 -            if ((data[0] == TYPE_TAPE)) {
25601 -                      if (ioc->facts.IOCCapabilities &
25602 -                               MPI_IOCFACTS_CAPABILITY_TLR ) {
25603 -                      if ((pTarget->tflags & MPT_TARGET_FLAGS_TLR_DONE) == 0){
25604 -                                               if ( data[8]  == 'H' &&
25605 -                                                    data[9]  == 'P' &&
25606 -                                                    data[10] == ' ' &&
25607 -                                                    data[11] == ' ' &&
25608 -                                                    data[12] == ' ' &&
25609 -                                                    data[13] == ' ' &&
25610 -                                                    data[14] == ' ' &&
25611 -                                                    data[15] == ' ' ) {
25612 -                                                       mpt_IssueTLR(hd, pTarget);
25613 -                                                  pTarget->tflags |= MPT_TARGET_FLAGS_TLR_DONE;
25614 -
25615 -                                                }
25616 -
25617 +       } else if (ioc->bus_type == SAS) {
25618 +               if ((data[0] == TYPE_TAPE)) {
25619 +                       if (ioc->facts.IOCCapabilities & 
25620 +                               MPI_IOCFACTS_CAPABILITY_TLR ) {
25621 +                               if ((pTarget->tflags & MPT_TARGET_FLAGS_TLR_DONE) == 0) {
25622 +                                       if ( data[8]  == 'H' &&
25623 +                                            data[9]  == 'P' &&
25624 +                                            data[10] == ' ' &&
25625 +                                            data[11] == ' ' &&
25626 +                                            data[12] == ' ' &&
25627 +                                            data[13] == ' ' &&
25628 +                                            data[14] == ' ' &&
25629 +                                            data[15] == ' ' ) {
25630 +                                               mpt_IssueTLR(hd, pTarget);
25631 +                                               pTarget->tflags |= MPT_TARGET_FLAGS_TLR_DONE;
25632                                         }
25633                                 }
25634                         }
25635 @@ -3760,12 +3383,11 @@ schedule_work(&pTarget->dvTask);
25636  static void
25637  mpt_IssueTLR(MPT_SCSI_HOST *hd, VirtDevice *pTarget)
25638  {
25639 -       MPT_ADAPTER             *ioc = hd->ioc;
25640         INTERNAL_CMD             iocmd;
25641         int                      lun, indexed_lun, lun_index;
25642  
25643 -       iocmd.id = pTarget->id;
25644 -       iocmd.bus = pTarget->bus;
25645 +       iocmd.id = pTarget->target_id;
25646 +       iocmd.bus = pTarget->bus_id;
25647         for (lun=0; lun <= MPT_LAST_LUN; lun++) {
25648                 /* If LUN present, issue the command
25649                  */
25650 @@ -3777,7 +3399,7 @@ mpt_IssueTLR(MPT_SCSI_HOST *hd, VirtDevi
25651                 }
25652         }
25653         printk(MYIOC_s_INFO_FMT "mpt_IssueTLR: Unable find a lun on id=%d\n",
25654 -               ioc->name, iocmd.id);
25655 +               hd->ioc->name, iocmd.id);
25656         return;
25657  issueTLR:
25658         iocmd.flags = 0;
25659 @@ -3790,7 +3412,7 @@ issueTLR:
25660         if (mptscsih_do_cmd(hd, &iocmd) < 0) {
25661                 if (mptscsih_do_cmd(hd, &iocmd) < 0) {
25662                         printk(MYIOC_s_INFO_FMT "Unable to set TLR on id=%d\n",
25663 -                               ioc->name, iocmd.id);
25664 +                               hd->ioc->name, iocmd.id);
25665                 }
25666         }
25667  }
25668 @@ -3802,14 +3424,12 @@ issueTLR:
25669   *
25670   */
25671  static void
25672 -mptscsih_setTargetNegoParms(MPT_SCSI_HOST *hd, VirtDevice *pTarget, char byte56)
25673 +mptscsih_setTargetNegoParms(MPT_SCSI_HOST *hd, VirtDevice *target, char byte56)
25674  {
25675 -       MPT_ADAPTER     *ioc = hd->ioc;
25676 -       SpiCfgData *pspi_data = &ioc->spi_data;
25677 -       int  id = (int) pTarget->id;
25678 +       SpiCfgData *pspi_data = &hd->ioc->spi_data;
25679 +       int  id = (int) target->target_id;
25680         int  nvram;
25681 -       struct _MPT_DEVICE      *pMptTarget;
25682 -       VirtDevice      *loop_pTarget;
25683 +       VirtDevice      *pTarget;
25684         int ii;
25685         u8 width = MPT_NARROW;
25686         u8 factor = MPT_ASYNC;
25687 @@ -3817,36 +3437,31 @@ mptscsih_setTargetNegoParms(MPT_SCSI_HOS
25688         u8 version, nfactor;
25689         u8 noQas = 1;
25690  
25691 -       pTarget->negoFlags = pspi_data->noQas;
25692 -ddvprintk((KERN_INFO "Command-line QAS setting sets noQas=%02x on id=%d!\n",
25693 -               pspi_data->noQas, id));
25694 +       target->negoFlags = pspi_data->noQas;
25695  
25696 -/* noQas == 0 => device supports QAS. Need byte 56 of Inq to determine
25697 +       ddvtprintk((KERN_INFO "Command-line QAS setting sets noQas=%02x on id=%d!\n", 
25698 +               pspi_data->noQas, id));
25699 +       /* noQas == 0 => device supports QAS. Need byte 56 of Inq to determine
25700          * support. If available, default QAS to off and allow enabling.
25701          * If not available, default QAS to on, turn off for non-disks.
25702          */
25703  
25704         /* Set flags based on Inquiry data
25705          */
25706 -       version = pTarget->inq_data[2] & 0x07;
25707 +       version = target->inq_data[2] & 0x07;
25708         if (version < 2) {
25709                 width = 0;
25710                 factor = MPT_ULTRA2;
25711                 offset = pspi_data->maxSyncOffset;
25712 -               pTarget->tflags &= ~MPT_TARGET_FLAGS_Q_YES;
25713 +               target->tflags &= ~MPT_TARGET_FLAGS_Q_YES;
25714         } else {
25715 -               if (pTarget->inq_data[7] & 0x20) {
25716 +               if (target->inq_data[7] & 0x20) {
25717                         width = 1;
25718                 }
25719  
25720 -               if (pTarget->inq_data[7] & 0x02)
25721 -                       pTarget->tflags |= MPT_TARGET_FLAGS_Q_YES;
25722 -               else
25723 -                       pTarget->tflags &= ~MPT_TARGET_FLAGS_Q_YES;
25724 -
25725 -               if (pTarget->inq_data[7] & 0x10) {
25726 +               if (target->inq_data[7] & 0x10) {
25727                         factor = pspi_data->minSyncFactor;
25728 -                       if (pTarget->tflags & MPT_TARGET_FLAGS_VALID_56) {
25729 +                       if (target->tflags & MPT_TARGET_FLAGS_VALID_56) {
25730                                 /* bits 2 & 3 show Clocking support */
25731                                 if ((byte56 & 0x0C) == 0)
25732                                         factor = MPT_ULTRA2;
25733 @@ -3857,17 +3472,17 @@ ddvprintk((KERN_INFO "Command-line QAS s
25734                                                 factor = MPT_ULTRA320;
25735                                                 if (byte56 & 0x02)
25736                                                 {
25737 -                                                   ddvprintk((KERN_INFO "Enabling QAS due to byte56=%02x on id=%d!\n", byte56, id));
25738 +                                                       ddvtprintk((KERN_INFO "Enabling QAS due to byte56=%02x on id=%d!\n", byte56, id));
25739                                                         noQas = 0;
25740                                                 }
25741 -                                               if (pTarget->inq_data[0] == TYPE_TAPE) {
25742 +                                               if (target->inq_data[0] == TYPE_TAPE) {
25743                                                         if (byte56 & 0x01)
25744 -                                                               pTarget->negoFlags |= MPT_TAPE_NEGO_IDP;
25745 +                                                               target->negoFlags |= MPT_TAPE_NEGO_IDP;
25746                                                 }
25747                                         }
25748                                 }
25749                         } else {
25750 -                               ddvprintk((KERN_INFO "Ultra 80 on id=%d due to ~TARGET_FLAGS_VALID_56!\n", id));
25751 +                               ddvtprintk((KERN_INFO "Ultra 80 on id=%d due to ~TARGET_FLAGS_VALID_56!\n", id));
25752                                 factor = MPT_ULTRA2;
25753                         }
25754  
25755 @@ -3879,7 +3494,7 @@ ddvprintk((KERN_INFO "Command-line QAS s
25756                          * bit 1 QAS support, non-raid only
25757                          * bit 0 IU support
25758                          */
25759 -                       if (pTarget->raidVolume == 1) {
25760 +                       if (target->raidVolume == 1) {
25761                                 noQas = 0;
25762                         }
25763                 } else {
25764 @@ -3888,6 +3503,9 @@ ddvprintk((KERN_INFO "Command-line QAS s
25765                 }
25766         }
25767  
25768 +       if ( (target->inq_data[7] & 0x02) == 0) {
25769 +               target->tflags &= ~MPT_TARGET_FLAGS_Q_YES;
25770 +       }
25771  
25772         /* Update tflags based on NVRAM settings. (SCSI only)
25773          */
25774 @@ -3926,43 +3544,41 @@ ddvprintk((KERN_INFO "Command-line QAS s
25775  
25776         /* Save the data to the target structure.
25777          */
25778 -       pTarget->minSyncFactor = factor;
25779 -       pTarget->maxOffset = offset;
25780 -       pTarget->maxWidth = width;
25781 +       target->minSyncFactor = factor;
25782 +       target->maxOffset = offset;
25783 +       target->maxWidth = width;
25784  
25785 -       pTarget->tflags |= MPT_TARGET_FLAGS_VALID_NEGO;
25786 +       target->tflags |= MPT_TARGET_FLAGS_VALID_NEGO;
25787  
25788         /* Disable unused features.
25789          */
25790         if (!width)
25791 -               pTarget->negoFlags |= MPT_TARGET_NO_NEGO_WIDE;
25792 +               target->negoFlags |= MPT_TARGET_NO_NEGO_WIDE;
25793  
25794         if (!offset)
25795 -               pTarget->negoFlags |= MPT_TARGET_NO_NEGO_SYNC;
25796 +               target->negoFlags |= MPT_TARGET_NO_NEGO_SYNC;
25797  
25798         if ( factor > MPT_ULTRA320 )
25799                 noQas = 0;
25800  
25801         /* GEM, processor WORKAROUND
25802          */
25803 -       if ((pTarget->inq_data[0] == TYPE_PROCESSOR) || (pTarget->inq_data[0] > 0x08)) {
25804 -               pTarget->negoFlags |= (MPT_TARGET_NO_NEGO_WIDE | MPT_TARGET_NO_NEGO_SYNC);
25805 +       if ((target->inq_data[0] == TYPE_PROCESSOR) || (target->inq_data[0] > 0x08)) {
25806 +               target->negoFlags |= (MPT_TARGET_NO_NEGO_WIDE | MPT_TARGET_NO_NEGO_SYNC);
25807                 pspi_data->dvStatus[id] |= MPT_SCSICFG_BLK_NEGO;
25808         } else {
25809                 if (noQas && (pspi_data->noQas == 0)) {
25810                         pspi_data->noQas |= MPT_TARGET_NO_NEGO_QAS;
25811 -                       pTarget->negoFlags |= MPT_TARGET_NO_NEGO_QAS;
25812 +                       target->negoFlags |= MPT_TARGET_NO_NEGO_QAS;
25813  
25814                         /* Disable QAS in a mixed configuration case
25815                         */
25816 -ddvprintk((KERN_INFO "Disabling QAS due to noQas=%02x on id=%d!\n", noQas, id));
25817  
25818 -                pMptTarget = ioc->Target_List[0];
25819 +                       ddvtprintk((KERN_INFO "Disabling QAS due to noQas=%02x on id=%d!\n", noQas, id));
25820                         for (ii = 0; ii < id; ii++) {
25821 -                               loop_pTarget = pMptTarget->Target[id];
25822 -                               if ((loop_pTarget)) {
25823 -                                       loop_pTarget->negoFlags |= MPT_TARGET_NO_NEGO_QAS;
25824 -                                        mpt_writeSDP1(ioc, 0, ii, loop_pTarget->negoFlags);
25825 +                               if ( (pTarget = hd->Targets[ii]) ) {
25826 +                                       pTarget->negoFlags |= MPT_TARGET_NO_NEGO_QAS;
25827 +                                       mptscsih_writeSDP1(hd, 0, ii, pTarget->negoFlags);
25828                                 }
25829                         }
25830                 }
25831 @@ -3970,33 +3586,115 @@ ddvprintk((KERN_INFO "Disabling QAS due 
25832  
25833         /* Write SDP1 on this I/O to this target */
25834         if (pspi_data->dvStatus[id] & MPT_SCSICFG_NEGOTIATE) {
25835 -               dnegoprintk((KERN_INFO "MPT_SCSICFG_NEGOTIATE on id=%d!\n", id));
25836 -                /* First IO to this device; NEED_DV will cause async/narrow */
25837 -                mpt_writeSDP1(ioc, 0, id, 0);
25838 +               ddvtprintk((KERN_INFO "MPT_SCSICFG_NEGOTIATE on id=%d!\n", id));
25839 +               mptscsih_writeSDP1(hd, 0, id, hd->negoNvram);
25840                 pspi_data->dvStatus[id] &= ~MPT_SCSICFG_NEGOTIATE;
25841         } else if (pspi_data->dvStatus[id] & MPT_SCSICFG_BLK_NEGO) {
25842 -               dnegoprintk((KERN_INFO "MPT_SCSICFG_BLK_NEGO on id=%d!\n", id));
25843 -               mpt_writeSDP1(ioc, 0, id, MPT_SCSICFG_BLK_NEGO);
25844 +               ddvtprintk((KERN_INFO "MPT_SCSICFG_BLK_NEGO on id=%d!\n", id));
25845 +               mptscsih_writeSDP1(hd, 0, id, MPT_SCSICFG_BLK_NEGO);
25846                 pspi_data->dvStatus[id] &= ~MPT_SCSICFG_BLK_NEGO;
25847         }
25848  }
25849  
25850  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
25851 +/* If DV disabled (negoNvram set to USE_NVARM) or if not LUN 0, return.
25852 + * Else set the NEED_DV flag after Read Capacity Issued (disks)
25853 + * or Mode Sense (cdroms).
25854 + *
25855 + * Tapes, initTarget will set this flag on completion of Inquiry command.
25856 + * Called only if DV_NOT_DONE flag is set
25857 + */
25858 +static void
25859 +mptscsih_set_dvflags(MPT_SCSI_HOST *hd, SCSIIORequest_t *pReq)
25860 +{
25861 +       MPT_ADAPTER     *ioc = hd->ioc;
25862 +       u8 cmd;
25863 +       SpiCfgData      *pSpi;
25864 +
25865 +       ddvtprintk((MYIOC_s_NOTE_FMT
25866 +               " set_dvflags: id=%d lun=%d negoNvram=%x cmd=%x\n",
25867 +               hd->ioc->name, pReq->TargetID, pReq->LUN[1], hd->negoNvram, pReq->CDB[0]));
25868 +
25869 +       if ((pReq->LUN[1] != 0) || (hd->negoNvram != 0))
25870 +               return;
25871 +
25872 +       cmd = pReq->CDB[0];
25873 +
25874 +       if ((cmd == READ_CAPACITY) || (cmd == MODE_SENSE)) {
25875 +               pSpi = &ioc->spi_data;
25876 +               if ((ioc->raid_data.isRaid & (1 << pReq->TargetID)) && ioc->raid_data.pIocPg3) {
25877 +                       /* Set NEED_DV for all hidden disks
25878 +                        */
25879 +                       Ioc3PhysDisk_t *pPDisk =  ioc->raid_data.pIocPg3->PhysDisk;
25880 +                       int             numPDisk = ioc->raid_data.pIocPg3->NumPhysDisks;
25881 +
25882 +                       while (numPDisk) {
25883 +                               pSpi->dvStatus[pPDisk->PhysDiskID] |= MPT_SCSICFG_NEED_DV;
25884 +                               ddvtprintk(("NEED_DV set for phys disk id %d\n", pPDisk->PhysDiskID));
25885 +                               pPDisk++;
25886 +                               numPDisk--;
25887 +                       }
25888 +               }
25889 +               pSpi->dvStatus[pReq->TargetID] |= MPT_SCSICFG_NEED_DV;
25890 +               ddvtprintk(("NEED_DV set for visible disk id %d\n", pReq->TargetID));
25891 +       }
25892 +}
25893 +
25894 +/* mptscsih_raid_set_dv_flags()
25895 + *
25896 + * New or replaced disk. Set DV flag and schedule DV.
25897 + */
25898 +static void
25899 +mptscsih_set_dvflags_raid(MPT_SCSI_HOST *hd, int id)
25900 +{
25901 +       MPT_ADAPTER     *ioc = hd->ioc;
25902 +       SpiCfgData      *pSpi = &ioc->spi_data;
25903 +       Ioc3PhysDisk_t  *pPDisk;
25904 +       int              numPDisk;
25905 +
25906 +       if (hd->negoNvram != 0)
25907 +               return;
25908 +
25909 +       ddvtprintk(("DV requested for phys disk id %d\n", id));
25910 +       if (ioc->raid_data.pIocPg3) {
25911 +               pPDisk =  ioc->raid_data.pIocPg3->PhysDisk;
25912 +               numPDisk = ioc->raid_data.pIocPg3->NumPhysDisks;
25913 +               while (numPDisk) {
25914 +                       if (id == pPDisk->PhysDiskNum) {
25915 +                               pSpi->dvStatus[pPDisk->PhysDiskID] =
25916 +                                   (MPT_SCSICFG_NEED_DV | MPT_SCSICFG_DV_NOT_DONE);
25917 +                               pSpi->forceDv = MPT_SCSICFG_NEED_DV;
25918 +                               ddvtprintk(("NEED_DV set for phys disk id %d\n",
25919 +                                   pPDisk->PhysDiskID));
25920 +                               break;
25921 +                       }
25922 +                       pPDisk++;
25923 +                       numPDisk--;
25924 +               }
25925 +
25926 +               if (numPDisk == 0) {
25927 +                       /* The physical disk that needs DV was not found
25928 +                        * in the stored IOC Page 3. The driver must reload
25929 +                        * this page. DV routine will set the NEED_DV flag for
25930 +                        * all phys disks that have DV_NOT_DONE set.
25931 +                        */
25932 +                       pSpi->forceDv = MPT_SCSICFG_NEED_DV | MPT_SCSICFG_RELOAD_IOC_PG3;
25933 +                       ddvtprintk(("phys disk %d not found. Setting reload IOC Pg3 Flag\n",id));
25934 +               }
25935 +       }
25936 +}
25937 +
25938 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
25939  /*
25940   * If no Target, bus reset on 1st I/O. Set the flag to
25941   * prevent any future negotiations to this device.
25942   */
25943  static void
25944 -mptscsih_no_negotiate(MPT_SCSI_HOST *hd, int id)
25945 +mptscsih_no_negotiate(MPT_SCSI_HOST *hd, int target_id)
25946  {
25947 -       MPT_ADAPTER     *ioc = hd->ioc;
25948 -       struct _MPT_DEVICE      *pMptTarget;
25949 -       VirtDevice      *pTarget;
25950  
25951 -       pMptTarget = ioc->Target_List[0];
25952 -       pTarget = pMptTarget->Target[id];
25953 -       if (pTarget == NULL)
25954 -               ioc->spi_data.dvStatus[id] |= MPT_SCSICFG_BLK_NEGO;
25955 +       if (hd->Targets[target_id] == NULL)
25956 +               hd->ioc->spi_data.dvStatus[target_id] |= MPT_SCSICFG_BLK_NEGO;
25957  
25958         return;
25959  }
25960 @@ -4006,9 +3704,266 @@ mptscsih_no_negotiate(MPT_SCSI_HOST *hd,
25961   *  SCSI Config Page functionality ...
25962   */
25963  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
25964 +/*     mptscsih_setDevicePage1Flags  - add Requested and Configuration fields flags
25965 + *     based on width, factor and offset parameters.
25966 + *     @width: bus width
25967 + *     @factor: sync factor
25968 + *     @offset: sync offset
25969 + *     @requestedPtr: pointer to requested values (updated)
25970 + *     @configurationPtr: pointer to configuration values (updated)
25971 + *     @flags: flags to block WDTR or SDTR negotiation
25972 + *
25973 + *     Return: None.
25974 + *
25975 + *     Remark: Called by writeSDP1 and _dv_params
25976 + */
25977 +static void
25978 +mptscsih_setDevicePage1Flags (u8 width, u8 factor, u8 offset, int *requestedPtr, int *configurationPtr, u8 flags)
25979 +{
25980 +       u8 nowide = flags & MPT_TARGET_NO_NEGO_WIDE;
25981 +       u8 nosync = flags & MPT_TARGET_NO_NEGO_SYNC;
25982 +
25983 +       *configurationPtr = 0;
25984 +       *requestedPtr = width ? MPI_SCSIDEVPAGE1_RP_WIDE : 0;
25985 +       *requestedPtr |= (offset << 16) | (factor << 8);
25986 +
25987 +       if (width && offset && !nowide && !nosync) {
25988 +               if (factor < MPT_ULTRA160) {
25989 +                       *requestedPtr |= (MPI_SCSIDEVPAGE1_RP_IU + MPI_SCSIDEVPAGE1_RP_DT);
25990 +                       if ((flags & MPT_TARGET_NO_NEGO_QAS) == 0)
25991 +                               *requestedPtr |= MPI_SCSIDEVPAGE1_RP_QAS;
25992 +                       if (flags & MPT_TAPE_NEGO_IDP)
25993 +                               *requestedPtr |= 0x08000000;
25994 +               } else if (factor < MPT_ULTRA2) {
25995 +                       *requestedPtr |= MPI_SCSIDEVPAGE1_RP_DT;
25996 +               }
25997 +       }
25998 +
25999 +       if (nowide)
26000 +               *configurationPtr |= MPI_SCSIDEVPAGE1_CONF_WDTR_DISALLOWED;
26001 +
26002 +       if (nosync)
26003 +               *configurationPtr |= MPI_SCSIDEVPAGE1_CONF_SDTR_DISALLOWED;
26004 +
26005 +       return;
26006 +}
26007 +
26008 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
26009 +/*     mptscsih_writeSDP1  - write SCSI Device Page 1
26010 + *     @hd: Pointer to a SCSI Host Strucutre
26011 + *     @portnum: IOC port number
26012 + *     @target_id: writeSDP1 for single ID
26013 + *     @flags: MPT_SCSICFG_ALL_IDS, MPT_SCSICFG_USE_NVRAM, MPT_SCSICFG_BLK_NEGO
26014 + *
26015 + *     Return: -EFAULT if read of config page header fails
26016 + *             or 0 if success.
26017 + *
26018 + *     Remark: If a target has been found, the settings from the
26019 + *             target structure are used, else the device is set
26020 + *             to async/narrow.
26021 + *
26022 + *     Remark: Called during init and after a FW reload.
26023 + *     Remark: We do not wait for a return, write pages sequentially.
26024 + */
26025 +static int
26026 +mptscsih_writeSDP1(MPT_SCSI_HOST *hd, int portnum, int target_id, int flags)
26027 +{
26028 +       MPT_ADAPTER             *ioc = hd->ioc;
26029 +       Config_t                *pReq;
26030 +       SCSIDevicePage1_t       *pData;
26031 +       VirtDevice              *pTarget;
26032 +       MPT_FRAME_HDR           *mf;
26033 +       dma_addr_t               dataDma;
26034 +       u16                      req_idx;
26035 +       u32                      frameOffset;
26036 +       u32                      requested, configuration, flagsLength;
26037 +       int                      ii, nvram;
26038 +       int                      id = 0, maxid = 0;
26039 +       u8                       width;
26040 +       u8                       factor;
26041 +       u8                       offset;
26042 +       u8                       bus = 0;
26043 +       u8                       negoFlags;
26044 +       u8                       maxwidth, maxoffset, maxfactor;
26045 +
26046 +       if (ioc->spi_data.sdp1length == 0)
26047 +               return 0;
26048 +
26049 +       if (flags & MPT_SCSICFG_ALL_IDS) {
26050 +               id = 0;
26051 +               maxid = ioc->sh->max_id - 1;
26052 +       } else if (ioc->sh) {
26053 +               id = target_id;
26054 +               maxid = min_t(int, id, ioc->sh->max_id - 1);
26055 +       }
26056 +
26057 +       for (; id <= maxid; id++) {
26058 +
26059 +               if (id == ioc->pfacts[portnum].PortSCSIID)
26060 +                       continue;
26061 +
26062 +               /* Use NVRAM to get adapter and target maximums
26063 +                * Data over-riden by target structure information, if present
26064 +                */
26065 +               maxwidth = ioc->spi_data.maxBusWidth;
26066 +               maxoffset = ioc->spi_data.maxSyncOffset;
26067 +               maxfactor = ioc->spi_data.minSyncFactor;
26068 +               if (ioc->spi_data.nvram && (ioc->spi_data.nvram[id] != MPT_HOST_NVRAM_INVALID)) {
26069 +                       nvram = ioc->spi_data.nvram[id];
26070 +
26071 +                       if (maxwidth)
26072 +                               maxwidth = nvram & MPT_NVRAM_WIDE_DISABLE ? 0 : 1;
26073 +
26074 +                       if (maxoffset > 0) {
26075 +                               maxfactor = (nvram & MPT_NVRAM_SYNC_MASK) >> 8;
26076 +                               if (maxfactor == 0) {
26077 +                                       /* Key for async */
26078 +                                       maxfactor = MPT_ASYNC;
26079 +                                       maxoffset = 0;
26080 +                               } else if (maxfactor < ioc->spi_data.minSyncFactor) {
26081 +                                       maxfactor = ioc->spi_data.minSyncFactor;
26082 +                               }
26083 +                       } else
26084 +                               maxfactor = MPT_ASYNC;
26085 +               }
26086 +
26087 +               /* Set the negotiation flags.
26088 +                */
26089 +               negoFlags = ioc->spi_data.noQas;
26090 +               if (!maxwidth)
26091 +                       negoFlags |= MPT_TARGET_NO_NEGO_WIDE;
26092 +
26093 +               if (!maxoffset)
26094 +                       negoFlags |= MPT_TARGET_NO_NEGO_SYNC;
26095 +
26096 +               if (flags & MPT_SCSICFG_USE_NVRAM) {
26097 +                       width = maxwidth;
26098 +                       factor = maxfactor;
26099 +                       offset = maxoffset;
26100 +               } else {
26101 +                       width = 0;
26102 +                       factor = MPT_ASYNC;
26103 +                       offset = 0;
26104 +                       //negoFlags = 0;
26105 +                       //negoFlags = MPT_TARGET_NO_NEGO_SYNC;
26106 +               }
26107 +
26108 +               /* If id is not a raid volume, get the updated
26109 +                * transmission settings from the target structure.
26110 +                */
26111 +               if ( (pTarget = hd->Targets[id]) && !pTarget->raidVolume) {
26112 +                       width = pTarget->maxWidth;
26113 +                       factor = pTarget->minSyncFactor;
26114 +                       offset = pTarget->maxOffset;
26115 +                       negoFlags |= pTarget->negoFlags;
26116 +               }
26117 +
26118 +#ifdef MPTSCSIH_ENABLE_DOMAIN_VALIDATION
26119 +               /* Force to async and narrow if DV has not been executed
26120 +                * for this ID
26121 +                */
26122 +               if ((hd->ioc->spi_data.dvStatus[id] & MPT_SCSICFG_DV_NOT_DONE) != 0) {
26123 +                       width = 0;
26124 +                       factor = MPT_ASYNC;
26125 +                       offset = 0;
26126 +               }
26127 +#endif
26128 +
26129 +               if (flags & MPT_SCSICFG_BLK_NEGO)
26130 +                       negoFlags |= MPT_TARGET_NO_NEGO_WIDE | MPT_TARGET_NO_NEGO_SYNC;
26131 +
26132 +               mptscsih_setDevicePage1Flags(width, factor, offset,
26133 +                                       &requested, &configuration, negoFlags);
26134 +               dnegoprintk(("writeSDP1: id=%d width=%d factor=%x offset=%x negoFlags=%x request=%x config=%x\n",
26135 +                       target_id, width, factor, offset, negoFlags, requested, configuration));
26136 +
26137 +               /* Get a MF for this command.
26138 +                */
26139 +               if ((mf = mpt_get_msg_frame(ioc->DoneCtx, ioc)) == NULL) {
26140 +                       dfailprintk((MYIOC_s_WARN_FMT "%s, no msg frames!!\n",
26141 +                           ioc->name,__FUNCTION__));
26142 +                       return -EAGAIN;
26143 +               }
26144 +
26145 +               ddvprintk((MYIOC_s_INFO_FMT "WriteSDP1 (mf=%p, id=%d, req=0x%x, cfg=0x%x)\n",
26146 +                       hd->ioc->name, mf, id, requested, configuration));
26147 +
26148 +
26149 +               /* Set the request and the data pointers.
26150 +                * Request takes: 36 bytes (32 bit SGE)
26151 +                * SCSI Device Page 1 requires 16 bytes
26152 +                * 40 + 16 <= size of SCSI IO Request = 56 bytes
26153 +                * and MF size >= 64 bytes.
26154 +                * Place data at end of MF.
26155 +                */
26156 +               pReq = (Config_t *)mf;
26157 +
26158 +               req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
26159 +               frameOffset = ioc->req_sz - sizeof(SCSIDevicePage1_t);
26160 +
26161 +               pData = (SCSIDevicePage1_t *)((u8 *) mf + frameOffset);
26162 +               dataDma = ioc->req_frames_dma + (req_idx * ioc->req_sz) + frameOffset;
26163 +
26164 +               /* Complete the request frame (same for all requests).
26165 +                */
26166 +               pReq->Action = MPI_CONFIG_ACTION_PAGE_WRITE_CURRENT;
26167 +               pReq->Reserved = 0;
26168 +               pReq->ChainOffset = 0;
26169 +               pReq->Function = MPI_FUNCTION_CONFIG;
26170 +               pReq->ExtPageLength = 0;
26171 +               pReq->ExtPageType = 0;
26172 +               pReq->MsgFlags = 0;
26173 +               for (ii=0; ii < 8; ii++) {
26174 +                       pReq->Reserved2[ii] = 0;
26175 +               }
26176 +               pReq->Header.PageVersion = ioc->spi_data.sdp1version;
26177 +               pReq->Header.PageLength = ioc->spi_data.sdp1length;
26178 +               pReq->Header.PageNumber = 1;
26179 +               pReq->Header.PageType = MPI_CONFIG_PAGETYPE_SCSI_DEVICE;
26180 +               pReq->PageAddress = cpu_to_le32(id | (bus << 8 ));
26181 +
26182 +               /* Add a SGE to the config request.
26183 +                */
26184 +               flagsLength = MPT_SGE_FLAGS_SSIMPLE_WRITE | ioc->spi_data.sdp1length * 4;
26185 +
26186 +               mpt_add_sge((char *)&pReq->PageBufferSGE, flagsLength, dataDma);
26187 +
26188 +               /* Set up the common data portion
26189 +                */
26190 +               pData->Header.PageVersion = pReq->Header.PageVersion;
26191 +               pData->Header.PageLength = pReq->Header.PageLength;
26192 +               pData->Header.PageNumber = pReq->Header.PageNumber;
26193 +               pData->Header.PageType = pReq->Header.PageType;
26194 +               pData->RequestedParameters = cpu_to_le32(requested);
26195 +               pData->Reserved = 0;
26196 +               pData->Configuration = cpu_to_le32(configuration);
26197 +
26198 +               if ( pTarget ) {
26199 +                       if ( requested & MPI_SCSIDEVPAGE1_RP_IU ) {
26200 +                               pTarget->last_lun = MPT_LAST_LUN;
26201 +                       } else {
26202 +                               pTarget->last_lun = MPT_NON_IU_LAST_LUN;
26203 +                       }
26204 +                       dsprintk((MYIOC_s_INFO_FMT
26205 +                               "writeSDP1: last_lun=%d on id=%d\n",
26206 +                               ioc->name, pTarget->last_lun, id));
26207 +               }
26208 +
26209 +               dprintk((MYIOC_s_INFO_FMT
26210 +                       "write SDP1: id %d pgaddr 0x%x req 0x%x config 0x%x\n",
26211 +                               ioc->name, id, (id | (bus<<8)),
26212 +                               requested, configuration));
26213 +
26214 +               mpt_put_msg_frame(ioc->DoneCtx, ioc, mf);
26215 +       }
26216 +
26217 +       return 0;
26218 +}
26219 +
26220 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
26221  /*     mptscsih_writeIOCPage4  - write IOC Page 4
26222   *     @hd: Pointer to a SCSI Host Structure
26223 - *     @id: write IOC Page4 for this ID & Bus
26224 + *     @target_id: write IOC Page4 for this ID & Bus
26225   *
26226   *     Return: -EAGAIN if unable to obtain a Message Frame
26227   *             or 0 if success.
26228 @@ -4016,7 +3971,7 @@ mptscsih_no_negotiate(MPT_SCSI_HOST *hd,
26229   *     Remark: We do not wait for a return, write pages sequentially.
26230   */
26231  static int
26232 -mptscsih_writeIOCPage4(MPT_SCSI_HOST *hd, int id, int bus)
26233 +mptscsih_writeIOCPage4(MPT_SCSI_HOST *hd, int target_id, int bus)
26234  {
26235         MPT_ADAPTER             *ioc = hd->ioc;
26236         Config_t                *pReq;
26237 @@ -4060,10 +4015,10 @@ mptscsih_writeIOCPage4(MPT_SCSI_HOST *hd
26238                 IOCPage4Ptr = ioc->spi_data.pIocPg4;
26239                 dataDma = ioc->spi_data.IocPg4_dma;
26240                 ii = IOCPage4Ptr->ActiveSEP++;
26241 -       IOCPage4Ptr->SEP[ii].SEPTargetID = id;
26242 +               IOCPage4Ptr->SEP[ii].SEPTargetID = target_id;
26243                 IOCPage4Ptr->SEP[ii].SEPBus = bus;
26244                 pReq->Header = IOCPage4Ptr->Header;
26245 -       pReq->PageAddress = cpu_to_le32(id | (bus << 8 ));
26246 +       pReq->PageAddress = cpu_to_le32(target_id | (bus << 8 ));
26247  
26248         /* Add a SGE to the config request.
26249          */
26250 @@ -4074,7 +4029,7 @@ mptscsih_writeIOCPage4(MPT_SCSI_HOST *hd
26251  
26252         dinitprintk((MYIOC_s_INFO_FMT
26253                 "writeIOCPage4: MaxSEP=%d ActiveSEP=%d id=%d bus=%d\n",
26254 -                       ioc->name, IOCPage4Ptr->MaxSEP, IOCPage4Ptr->ActiveSEP, id, bus));
26255 +                       ioc->name, IOCPage4Ptr->MaxSEP, IOCPage4Ptr->ActiveSEP, target_id, bus));
26256  
26257         mpt_put_msg_frame(ioc->DoneCtx, ioc, mf);
26258  
26259 @@ -4116,9 +4071,6 @@ mptscsih_scandv_complete(MPT_ADAPTER *io
26260  
26261         hd = (MPT_SCSI_HOST *) ioc->sh->hostdata;
26262  
26263 -        del_timer(&hd->InternalCmdTimer);
26264 -
26265 -
26266         if ((mf == NULL) ||
26267             (mf >= MPT_INDEX_2_MFPTR(ioc, ioc->req_depth))) {
26268                 printk(MYIOC_s_ERR_FMT
26269 @@ -4127,18 +4079,19 @@ mptscsih_scandv_complete(MPT_ADAPTER *io
26270                 goto wakeup;
26271         }
26272  
26273 +       del_timer(&hd->timer);
26274         req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
26275         hd->ScsiLookup[req_idx] = NULL;
26276         pReq = (SCSIIORequest_t *) mf;
26277  
26278         if (mf != hd->cmdPtr) {
26279 -               printk(MYIOC_s_WARN_FMT "ScanDvComplete (mf=%p,!= cmdPtr=%p, idx=%d)\n",
26280 -                               ioc->name, (void *)mf, (void *) hd->cmdPtr, req_idx);
26281 +               printk(MYIOC_s_WARN_FMT "ScanDvComplete (mf=%p, cmdPtr=%p, idx=%d)\n",
26282 +                               hd->ioc->name, (void *)mf, (void *) hd->cmdPtr, req_idx);
26283         }
26284         hd->cmdPtr = NULL;
26285  
26286 -       ddvprintk((MYIOC_s_WARN_FMT "ScanDvComplete mf=%p,mr=%p,idx=%d\n",
26287 -                       ioc->name, mf, mr, req_idx));
26288 +       ddvprintk((MYIOC_s_INFO_FMT "ScanDvComplete (mf=%p,mr=%p,idx=%d)\n",
26289 +                       hd->ioc->name, mf, mr, req_idx));
26290  
26291         hd->pLocal = &hd->localReply;
26292         hd->pLocal->scsiStatus = 0;
26293 @@ -4156,9 +4109,10 @@ mptscsih_scandv_complete(MPT_ADAPTER *io
26294  
26295                 status = le16_to_cpu(pReply->IOCStatus) & MPI_IOCSTATUS_MASK;
26296                 scsi_status = pReply->SCSIStatus;
26297 - ddvprintk((MYIOC_s_WARN_FMT "%s: IOCStatus=%04xh SCSIState=%02xh SCSIStatus=%02xh IOCLogInfo=%08xh\n",
26298 -                     ioc->name, __FUNCTION__, status, pReply->SCSIState, scsi_status,
26299 -                     le32_to_cpu(pReply->IOCLogInfo)));
26300 +
26301 +               ddvtprintk((KERN_NOTICE "  IOCStatus=%04xh, SCSIState=%02xh, SCSIStatus=%02xh, IOCLogInfo=%08xh\n",
26302 +                            status, pReply->SCSIState, scsi_status,
26303 +                            le32_to_cpu(pReply->IOCLogInfo)));
26304  
26305                 switch(status) {
26306  
26307 @@ -4203,14 +4157,13 @@ mptscsih_scandv_complete(MPT_ADAPTER *io
26308                                  */
26309                                 completionCode = MPT_SCANDV_SENSE;
26310                                 hd->pLocal->scsiStatus = scsi_status;
26311 -                               sense_data = ((u8 *)ioc->sense_buf_pool +
26312 +                               sense_data = ((u8 *)hd->ioc->sense_buf_pool +
26313                                         (req_idx * MPT_SENSE_BUFFER_ALLOC));
26314  
26315                                 sz = min_t(int, pReq->SenseBufferLength,
26316                                                         SCSI_STD_SENSE_BYTES);
26317                                 memcpy(hd->pLocal->sense, sense_data, sz);
26318  
26319 -                               DBG_DUMP_SENSE_DATA(sense_data);
26320                                 ddvprintk((KERN_NOTICE "  Check Condition, sense ptr %p\n",
26321                                                 sense_data));
26322                         } else if (pReply->SCSIState & MPI_SCSI_STATE_AUTOSENSE_FAILED) {
26323 @@ -4224,7 +4177,7 @@ mptscsih_scandv_complete(MPT_ADAPTER *io
26324                         else if (pReply->SCSIState & MPI_SCSI_STATE_TERMINATED)
26325                                 completionCode = MPT_SCANDV_DID_RESET;
26326                         else if (scsi_status == MPI_SCSI_STATUS_BUSY)
26327 -                               completionCode = MPT_SCANDV_BUSY;
26328 +                               completionCode = MPT_SCANDV_SOME_ERROR;
26329                         else {
26330                                 completionCode = MPT_SCANDV_GOOD;
26331                                 hd->pLocal->scsiStatus = scsi_status;
26332 @@ -4243,9 +4196,9 @@ mptscsih_scandv_complete(MPT_ADAPTER *io
26333                         break;
26334  
26335                 }       /* switch(status) */
26336 -               ddvprintk((MYIOC_s_WARN_FMT ": completionCode=%08xh\n",
26337 -                       ioc->name, completionCode));
26338  
26339 +               ddvtprintk((KERN_NOTICE "  completionCode set to %08xh\n",
26340 +                               completionCode));
26341         } /* end of address reply case */
26342  
26343         hd->pLocal->completion = completionCode;
26344 @@ -4266,53 +4219,48 @@ wakeup:
26345  }
26346  
26347  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
26348 -/*     mptscsih_InternalCmdTimer_expired - Call back for DV timer process.
26349 +/*     mptscsih_timer_expired - Call back for timer process.
26350   *     Used only for dv functionality.
26351   *     @data: Pointer to MPT_SCSI_HOST recast as an unsigned long
26352   *
26353   */
26354 -void mptscsih_InternalCmdTimer_expired(unsigned long data)
26355 +void
26356 +mptscsih_timer_expired(unsigned long data)
26357  {
26358         MPT_SCSI_HOST *hd = (MPT_SCSI_HOST *) data;
26359 -       MPT_ADAPTER     *ioc=hd->ioc;
26360 -       MPIHeader_t *cmd = (MPIHeader_t *)hd->cmdPtr;
26361  
26362 -       ddvprintk((MYIOC_s_WARN_FMT "InternalCmdTimer_expired! cmdPtr=%p\n",
26363 -               ioc->name, cmd));
26364 +       ddvprintk((MYIOC_s_WARN_FMT "Timer Expired! Cmd %p\n", hd->ioc->name, hd->cmdPtr));
26365  
26366 -       hd->cmdPtr = NULL;
26367 -       if (cmd->Function == MPI_FUNCTION_SCSI_IO_REQUEST) {
26368 -#ifdef MPT_DEBUG_DV
26369 -               SCSIIORequest_t *pScsiReq = (SCSIIORequest_t *) cmd;
26370 -               int      id = pScsiReq->TargetID;
26371 -
26372 -               /* Desire to issue a task management request here.
26373 -                * TM requests MUST be single threaded.
26374 -                * If old eh code and no TM current, issue request.
26375 -                * If new eh code, do nothing. Wait for OS cmd timeout
26376 -                *      for bus reset.
26377 -                */
26378 -               ddvprintk((MYIOC_s_WARN_FMT "DV Cmd Timeout: id=%d CDB=%02x\n",
26379 -                       ioc->name, id, pScsiReq->CDB[0]));
26380 -#endif
26381 +       if (hd->cmdPtr) {
26382 +               MPIHeader_t *cmd = (MPIHeader_t *)hd->cmdPtr;
26383  
26384 -               /*
26385 -                * Wake up the original calling thread
26386 -                */
26387 -               hd->pLocal = &hd->localReply;
26388 -               hd->pLocal->completion = MPT_SCANDV_FALLBACK;
26389 -               hd->scandv_wait_done = 1;
26390 -               wake_up(&hd->scandv_waitq);
26391 -       } else {
26392 -               /* Perform a FW reload */
26393 -               if (mpt_HardResetHandler(ioc, NO_SLEEP) < 0) {
26394 -                       printk(MYIOC_s_WARN_FMT "InternalCmdTimer_expired: HardReset FAILED!\n", ioc->name);
26395 -                       dfailprintk((MYIOC_s_ERR_FMT "InternalCmdTimer_expired: HardReset failed\n", ioc->name));
26396 +               if (cmd->Function == MPI_FUNCTION_SCSI_IO_REQUEST) {
26397 +                       /* Desire to issue a task management request here.
26398 +                        * TM requests MUST be single threaded.
26399 +                        * If old eh code and no TM current, issue request.
26400 +                        * If new eh code, do nothing. Wait for OS cmd timeout
26401 +                        *      for bus reset.
26402 +                        */
26403 +                       ddvtprintk((MYIOC_s_NOTE_FMT "DV Cmd Timeout: NoOp\n", hd->ioc->name));
26404                 } else {
26405 -                       ddvprintk((MYIOC_s_ERR_FMT "InternalCmdTimer_expired: HardReset succeeded\n", ioc->name));
26406 +                       /* Perform a FW reload */
26407 +                       if (mpt_HardResetHandler(hd->ioc, NO_SLEEP) < 0) {
26408 +                               printk(MYIOC_s_WARN_FMT "Firmware Reload FAILED!\n", hd->ioc->name);
26409 +                       }
26410                 }
26411 +       } else {
26412 +               /* This should NEVER happen */
26413 +               printk(MYIOC_s_WARN_FMT "Null cmdPtr!!!!\n", hd->ioc->name);
26414         }
26415 -       ddvprintk((MYIOC_s_WARN_FMT "InternalCmdTimer_expired Complete!\n", ioc->name));
26416 +
26417 +       /* No more processing.
26418 +        * TM call will generate an interrupt for SCSI TM Management.
26419 +        * The FW will reply to all outstanding commands, callback will finish cleanup.
26420 +        * Hard reset clean-up will free all resources.
26421 +        */
26422 +       ddvprintk((MYIOC_s_WARN_FMT "Timer Expired Complete!\n", hd->ioc->name));
26423 +
26424 +       return;
26425  }
26426  
26427  #ifdef MPTSCSIH_ENABLE_DOMAIN_VALIDATION
26428 @@ -4331,23 +4279,22 @@ void mptscsih_InternalCmdTimer_expired(u
26429  static int
26430  mptscsih_do_raid(MPT_SCSI_HOST *hd, u8 action, INTERNAL_CMD *io)
26431  {
26432 -       MPT_ADAPTER             *ioc = hd->ioc;
26433         MpiRaidActionRequest_t  *pReq;
26434         MPT_FRAME_HDR           *mf;
26435         int                     in_isr;
26436  
26437         in_isr = in_interrupt();
26438         if (in_isr) {
26439 -               dfailprintk((MYIOC_s_WARN_FMT "Internal raid request not allowed in ISR context!\n",
26440 -                               ioc->name));
26441 +               dprintk((MYIOC_s_WARN_FMT "Internal raid request not allowed in ISR context!\n",
26442 +                                       hd->ioc->name));
26443                 return -EPERM;
26444         }
26445  
26446         /* Get and Populate a free Frame
26447          */
26448 -       if ((mf = mpt_get_msg_frame(ioc->InternalCtx, ioc)) == NULL) {
26449 +       if ((mf = mpt_get_msg_frame(hd->ioc->InternalCtx, hd->ioc)) == NULL) {
26450                 dfailprintk((MYIOC_s_WARN_FMT "%s, no msg frames!!\n",
26451 -                   ioc->name,__FUNCTION__));
26452 +                   hd->ioc->name,__FUNCTION__));
26453                 return -EAGAIN;
26454         }
26455         pReq = (MpiRaidActionRequest_t *)mf;
26456 @@ -4367,11 +4314,10 @@ mptscsih_do_raid(MPT_SCSI_HOST *hd, u8 a
26457                 MPT_SGE_FLAGS_SSIMPLE_READ | 0, (dma_addr_t) -1);
26458  
26459         ddvprintk((MYIOC_s_INFO_FMT "RAID Volume action %x id %d\n",
26460 -                       ioc->name, action, io->id));
26461 +                       hd->ioc->name, action, io->id));
26462  
26463         hd->pLocal = NULL;
26464 -       hd->InternalCmdTimer.data = (unsigned long) hd;
26465 -        hd->InternalCmdTimer.expires = jiffies + HZ*10; /* 10 second timeout */
26466 +       hd->timer.expires = jiffies + HZ*10; /* 10 second timeout */
26467         hd->scandv_wait_done = 0;
26468  
26469         /* Save cmd pointer, for resource free if timeout or
26470 @@ -4379,8 +4325,8 @@ mptscsih_do_raid(MPT_SCSI_HOST *hd, u8 a
26471          */
26472         hd->cmdPtr = mf;
26473  
26474 -       add_timer(&hd->InternalCmdTimer);
26475 -        mpt_put_msg_frame(ioc->InternalCtx, ioc, mf);
26476 +       add_timer(&hd->timer);
26477 +       mpt_put_msg_frame(hd->ioc->InternalCtx, hd->ioc, mf);
26478         wait_event(hd->scandv_waitq, hd->scandv_wait_done);
26479  
26480         if ((hd->pLocal == NULL) || (hd->pLocal->completion != MPT_SCANDV_GOOD))
26481 @@ -4413,7 +4359,6 @@ mptscsih_do_raid(MPT_SCSI_HOST *hd, u8 a
26482  int
26483  mptscsih_do_cmd(MPT_SCSI_HOST *hd, INTERNAL_CMD *io)
26484  {
26485 -       MPT_ADAPTER     *ioc = hd->ioc;
26486         MPT_FRAME_HDR   *mf;
26487         SCSIIORequest_t *pScsiReq;
26488         SCSIIORequest_t  ReqCopy;
26489 @@ -4426,8 +4371,8 @@ mptscsih_do_cmd(MPT_SCSI_HOST *hd, INTER
26490  
26491         in_isr = in_interrupt();
26492         if (in_isr) {
26493 -               dfailprintk((MYIOC_s_WARN_FMT "Internal SCSI IO request not allowed in ISR context!\n",
26494 -                               ioc->name));
26495 +               dprintk((MYIOC_s_WARN_FMT "Internal SCSI IO request not allowed in ISR context!\n",
26496 +                                       hd->ioc->name));
26497                 return -EPERM;
26498         }
26499  
26500 @@ -4542,16 +4487,14 @@ mptscsih_do_cmd(MPT_SCSI_HOST *hd, INTER
26501  
26502         default:
26503                 /* Error Case */
26504 -               dfailprintk((MYIOC_s_WARN_FMT "%s,Unknown cmd=%02x!!\n",
26505 -                   ioc->name,__FUNCTION__, cmd));
26506                 return -EFAULT;
26507         }
26508  
26509         /* Get and Populate a free Frame
26510          */
26511 -       if ((mf = mpt_get_msg_frame(ioc->InternalCtx, ioc)) == NULL) {
26512 +       if ((mf = mpt_get_msg_frame(hd->ioc->InternalCtx, hd->ioc)) == NULL) {
26513                 dfailprintk((MYIOC_s_WARN_FMT "%s, no msg frames!!\n",
26514 -                   ioc->name,__FUNCTION__));
26515 +                   hd->ioc->name,__FUNCTION__));
26516                 return -EBUSY;
26517         }
26518  
26519 @@ -4593,18 +4536,18 @@ mptscsih_do_cmd(MPT_SCSI_HOST *hd, INTER
26520         if (cmd == REQUEST_SENSE) {
26521                 pScsiReq->Control = cpu_to_le32(dir | MPI_SCSIIO_CONTROL_UNTAGGED);
26522                 ddvprintk((MYIOC_s_INFO_FMT "Untagged! 0x%2x\n",
26523 -                       ioc->name, cmd));
26524 +                       hd->ioc->name, cmd));
26525         }
26526  
26527         for (ii=0; ii < 16; ii++)
26528                 pScsiReq->CDB[ii] = CDB[ii];
26529  
26530         pScsiReq->DataLength = cpu_to_le32(io->size);
26531 -       pScsiReq->SenseBufferLowAddr = cpu_to_le32(ioc->sense_buf_low_dma
26532 +       pScsiReq->SenseBufferLowAddr = cpu_to_le32(hd->ioc->sense_buf_low_dma
26533                                            + (my_idx * MPT_SENSE_BUFFER_ALLOC));
26534  
26535 -       ddvprintk((MYIOC_s_INFO_FMT "Sending Command 0x%x for (%d:%d:%d) mf=%p\n",
26536 -                       ioc->name, cmd, io->bus, io->id, io->lun, pScsiReq));
26537 +       ddvprintk((MYIOC_s_INFO_FMT "Sending Command 0x%x for (%d:%d:%d)\n",
26538 +                       hd->ioc->name, cmd, io->bus, io->id, io->lun));
26539  
26540         if (dir == MPI_SCSIIO_CONTROL_READ) {
26541                 mpt_add_sge((char *) &pScsiReq->SGL,
26542 @@ -4630,8 +4573,7 @@ mptscsih_do_cmd(MPT_SCSI_HOST *hd, INTER
26543          *      set scandv_wait_done and call wake_up
26544          */
26545         hd->pLocal = NULL;
26546 -        hd->InternalCmdTimer.data = (unsigned long) hd;
26547 -        hd->InternalCmdTimer.expires = jiffies + HZ*cmdTimeout;
26548 +       hd->timer.expires = jiffies + HZ*cmdTimeout;
26549         hd->scandv_wait_done = 0;
26550  
26551         /* Save cmd pointer, for resource free if timeout or
26552 @@ -4639,8 +4581,8 @@ mptscsih_do_cmd(MPT_SCSI_HOST *hd, INTER
26553          */
26554         hd->cmdPtr = mf;
26555  
26556 -        add_timer(&hd->InternalCmdTimer);
26557 -       mpt_put_msg_frame(ioc->InternalCtx, ioc, mf);
26558 +       add_timer(&hd->timer);
26559 +       mpt_put_msg_frame(hd->ioc->InternalCtx, hd->ioc, mf);
26560         wait_event(hd->scandv_waitq, hd->scandv_wait_done);
26561  
26562         if (hd->pLocal) {
26563 @@ -4657,7 +4599,7 @@ mptscsih_do_cmd(MPT_SCSI_HOST *hd, INTER
26564                 rc = -EFAULT;
26565                 /* This should never happen. */
26566                 ddvprintk((MYIOC_s_INFO_FMT "_do_cmd: Null pLocal!!!\n",
26567 -                               ioc->name));
26568 +                               hd->ioc->name));
26569         }
26570  
26571         return rc;
26572 @@ -4678,7 +4620,6 @@ static int
26573  mptscsih_synchronize_cache(MPT_SCSI_HOST *hd, int portnum)
26574  {
26575         MPT_ADAPTER             *ioc= hd->ioc;
26576 -       struct _MPT_DEVICE      *pMptTarget;
26577         VirtDevice              *pTarget;
26578         SCSIDevicePage1_t       *pcfg1Data = NULL;
26579         INTERNAL_CMD             iocmd;
26580 @@ -4690,6 +4631,7 @@ mptscsih_synchronize_cache(MPT_SCSI_HOST
26581         int                      lun;
26582         int                      indexed_lun, lun_index;
26583         int                      hostId = ioc->pfacts[portnum].PortSCSIID;
26584 +       int                      max_id;
26585         int                      requested, configuration, data;
26586         int                      doConfig = 0;
26587         u8                       flags, factor;
26588 @@ -4697,6 +4639,8 @@ mptscsih_synchronize_cache(MPT_SCSI_HOST
26589         dexitprintk((KERN_INFO MYNAM ": %s called\n",
26590                 __FUNCTION__));
26591  
26592 +       max_id = ioc->sh->max_id - 1;
26593 +
26594         /* Following parameters will not change
26595          * in this routine.
26596          */
26597 @@ -4733,11 +4677,10 @@ mptscsih_synchronize_cache(MPT_SCSI_HOST
26598  
26599         /* loop through all devices on this port
26600          */
26601 -       while (bus < ioc->NumberOfBuses) {
26602 +       while (bus < MPT_MAX_BUS) {
26603                 iocmd.bus = bus;
26604                 iocmd.id = id;
26605 -               pMptTarget = ioc->Target_List[bus];
26606 -               pTarget = pMptTarget->Target[id];
26607 +               pTarget = hd->Targets[(int)id];
26608  
26609                 if (doConfig) {
26610  
26611 @@ -4745,9 +4688,9 @@ mptscsih_synchronize_cache(MPT_SCSI_HOST
26612                         if (pTarget && !pTarget->raidVolume) {
26613                                 flags = pTarget->negoFlags;
26614                         } else {
26615 -                               flags = ioc->spi_data.noQas;
26616 -                               if (ioc->spi_data.nvram && (ioc->spi_data.nvram[id] != MPT_HOST_NVRAM_INVALID)) {
26617 -                                       data = ioc->spi_data.nvram[id];
26618 +                               flags = hd->ioc->spi_data.noQas;
26619 +                               if (hd->ioc->spi_data.nvram && (hd->ioc->spi_data.nvram[id] != MPT_HOST_NVRAM_INVALID)) {
26620 +                                       data = hd->ioc->spi_data.nvram[id];
26621  
26622                                         if (data & MPT_NVRAM_WIDE_DISABLE)
26623                                                 flags |= MPT_TARGET_NO_NEGO_WIDE;
26624 @@ -4759,16 +4702,16 @@ mptscsih_synchronize_cache(MPT_SCSI_HOST
26625                         }
26626  
26627                         /* Force to async, narrow */
26628 -                       mpt_setSDP1parameters(0, MPT_ASYNC, 0, flags,
26629 -                               &requested, &configuration);
26630 -                       dnegoprintk(("%s: syncronize cache: id=%d width=0 factor=MPT_ASYNC "
26631 -                                "offset=0 negoFlags=%x requested=%x configuration=%x\n",
26632 -                                ioc->name, id, flags, requested, configuration));
26633 +                       mptscsih_setDevicePage1Flags(0, MPT_ASYNC, 0, &requested,
26634 +                                       &configuration, flags);
26635 +                       dnegoprintk(("syncronize cache: id=%d width=0 factor=MPT_ASYNC "
26636 +                               "offset=0 negoFlags=%x request=%x config=%x\n",
26637 +                               id, flags, requested, configuration));
26638                         pcfg1Data->RequestedParameters = cpu_to_le32(requested);
26639                         pcfg1Data->Reserved = 0;
26640                         pcfg1Data->Configuration = cpu_to_le32(configuration);
26641                         cfg.pageAddr = (bus<<8) | id;
26642 -                       mpt_config(ioc, &cfg);
26643 +                       mpt_config(hd->ioc, &cfg);
26644                 }
26645  
26646                 /* If target Ptr NULL or if this target is NOT a disk, skip.
26647 @@ -4780,9 +4723,6 @@ mptscsih_synchronize_cache(MPT_SCSI_HOST
26648                                 lun_index = (lun >> 5);  /* 32 luns per lun_index */
26649                                 indexed_lun = (lun % 32);
26650                                 if (pTarget->luns[lun_index] & (1<<indexed_lun)) {
26651 -                                       dexitprintk((KERN_INFO MYNAM ": %s: synchronize_cache for bus=%d id=%d lun=%d\n",
26652 -                                               ioc->name, bus, id, lun));
26653 -
26654                                         iocmd.lun = lun;
26655                                         (void) mptscsih_do_cmd(hd, &iocmd);
26656                                 }
26657 @@ -4795,27 +4735,21 @@ mptscsih_synchronize_cache(MPT_SCSI_HOST
26658                 if (id == hostId)
26659                         id++;
26660  
26661 -               if (id >= ioc->DevicesPerBus) {
26662 +               if (id > max_id) {
26663                         id = 0;
26664                         bus++;
26665                 }
26666         }
26667  
26668 -       dexitprintk((KERN_INFO MYNAM ": %s: synchronize_cache commands done\n",
26669 -               ioc->name));
26670 -
26671         if (pcfg1Data) {
26672 -               dexitprintk((KERN_INFO MYNAM ": %s: free pcfg1Data=%p\n",
26673 -                       ioc->name, pcfg1Data));
26674                 pci_free_consistent(ioc->pcidev, header1.PageLength * 4, pcfg1Data, cfg1_dma_addr);
26675         }
26676  
26677 -       dexitprintk((KERN_INFO MYNAM ": %s: synchronize_cache done\n",
26678 -               ioc->name));
26679         return 0;
26680  }
26681  
26682  #ifdef MPTSCSIH_ENABLE_DOMAIN_VALIDATION
26683 +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
26684  /**
26685   *     mptscsih_domainValidation - Top level handler for domain validation.
26686   *     @hd: Pointer to MPT_SCSI_HOST structure.
26687 @@ -4829,209 +4763,163 @@ mptscsih_synchronize_cache(MPT_SCSI_HOST
26688  static void
26689  mptscsih_domainValidation(void *arg)
26690  {
26691 -       VirtDevice      *pTarget=(VirtDevice *)arg;
26692 -       MPT_SCSI_HOST   *hd;
26693 -       MPT_ADAPTER     *ioc;
26694 -       unsigned long    flags;
26695 -       int              id, dvStatus;
26696 -       int              ii;
26697 +       MPT_SCSI_HOST           *hd;
26698 +       MPT_ADAPTER             *ioc;
26699 +       unsigned long            flags;
26700 +       int                      id, maxid, dvStatus, did;
26701 +       int                      ii, isPhysDisk;
26702  
26703         spin_lock_irqsave(&dvtaskQ_lock, flags);
26704         dvtaskQ_active = 1;
26705 +       if (dvtaskQ_release) {
26706 +               dvtaskQ_active = 0;
26707 +               spin_unlock_irqrestore(&dvtaskQ_lock, flags);
26708 +               return;
26709 +       }
26710         spin_unlock_irqrestore(&dvtaskQ_lock, flags);
26711  
26712 -       if (pTarget == NULL) {
26713 -               ddvprintk((KERN_WARNING "domainValidation called with NULL pTarget\n"));
26714 -               goto mptscsih_domainValidation_exit;
26715 -       }
26716 -       id = pTarget->id;
26717 -       ioc = pTarget->ioc;
26718 -       if (ioc == NULL) {
26719 -               ddvprintk((KERN_WARNING "domainValidation called with NULL pTarget->ioc id=%d\n", id));
26720 -               goto mptscsih_domainValidation_exit;
26721 -       }
26722 -//     set_current_state(TASK_INTERRUPTIBLE);
26723 -//     schedule_timeout(MPT_HZ/4);
26724 +       if (crashdump_mode())
26725 +               return;
26726  
26727 -       hd = (MPT_SCSI_HOST *) ioc->sh->hostdata;
26728 +       /* For this ioc, loop through all devices and do dv to each device.
26729 +        * When complete with this ioc, search through the ioc list, and
26730 +        * for each scsi ioc found, do dv for all devices. Exit when no
26731 +        * device needs dv.
26732 +        */
26733 +       did = 1;
26734 +       while (did) {
26735 +               did = 0;
26736 +               list_for_each_entry(ioc, &ioc_list, list) {
26737 +                       spin_lock_irqsave(&dvtaskQ_lock, flags);
26738 +                       if (dvtaskQ_release) {
26739 +                               dvtaskQ_active = 0;
26740 +                               spin_unlock_irqrestore(&dvtaskQ_lock, flags);
26741 +                               return;
26742 +                       }
26743 +                       spin_unlock_irqrestore(&dvtaskQ_lock, flags);
26744  
26745 -       ddvprintk((KERN_WARNING "domainValidation pTarget=%p ioc=%p hd=%p id=%d\n",
26746 -               pTarget, ioc, hd, id));
26747 -       if (hd == NULL) {
26748 -               ddvprintk((KERN_WARNING "domainValidation called with NULL hd id=%d\n", id));
26749 -               goto mptscsih_domainValidation_exit;
26750 -       }
26751 +                       msleep(250);
26752  
26753 -       if ((ioc->spi_data.forceDv & MPT_SCSICFG_RELOAD_IOC_PG3) != 0) {
26754 -               mpt_read_ioc_pg_3(ioc);
26755 -               if (ioc->spi_data.dvStatus[id] & MPT_SCSICFG_PHYSDISK_DV_ONLY) {
26756 -                       ddvprintk((KERN_WARNING "PHYSDISK_DV_ONLY id=%d\n", id));
26757 -                       ioc->spi_data.dvStatus[id] &=
26758 -                               ~MPT_SCSICFG_PHYSDISK_DV_ONLY;
26759 -                       if (mptscsih_doDv(hd, 0, id) == 1) {
26760 -                               /* Untagged device was busy, try again
26761 -                                */
26762 -                               ioc->spi_data.dvStatus[id] |= MPT_SCSICFG_NEED_DV;
26763 -                       } else {
26764 -                               /* DV is complete. Clear flags.
26765 -                                */
26766 -                               ioc->spi_data.dvStatus[id] &= ~MPT_SCSICFG_DV_NOT_DONE;
26767 -                       }
26768 -                       goto mptscsih_domainValidation_exit;
26769 -               }
26770 +                       /* DV only to SPI adapters */
26771 +                       if (ioc->bus_type != SPI)
26772 +                               continue;
26773  
26774 -               if (ioc->raid_data.pIocPg3) {
26775 -                       Ioc3PhysDisk_t *pPDisk = ioc->raid_data.pIocPg3->PhysDisk;
26776 -                       int     numPDisk = ioc->raid_data.pIocPg3->NumPhysDisks;
26777 +                       /* Make sure everything looks ok */
26778 +                       if (ioc->sh == NULL)
26779 +                               continue;
26780  
26781 -                       while (numPDisk) {
26782 -                               if (ioc->spi_data.dvStatus[pPDisk->PhysDiskID] & MPT_SCSICFG_DV_NOT_DONE)
26783 -                                       ioc->spi_data.dvStatus[pPDisk->PhysDiskID] |= MPT_SCSICFG_NEED_DV;
26784 +                       hd = (MPT_SCSI_HOST *) ioc->sh->hostdata;
26785 +                       if (hd == NULL)
26786 +                               continue;
26787  
26788 -                               pPDisk++;
26789 -                               numPDisk--;
26790 +                       if ((ioc->spi_data.forceDv & MPT_SCSICFG_RELOAD_IOC_PG3) != 0) {
26791 +                               mpt_read_ioc_pg_3(ioc);
26792 +                               if (ioc->raid_data.pIocPg3) {
26793 +                                       Ioc3PhysDisk_t *pPDisk = ioc->raid_data.pIocPg3->PhysDisk;
26794 +                                       int             numPDisk = ioc->raid_data.pIocPg3->NumPhysDisks;
26795 +
26796 +                                       while (numPDisk) {
26797 +                                               if (ioc->spi_data.dvStatus[pPDisk->PhysDiskID] & MPT_SCSICFG_DV_NOT_DONE)
26798 +                                                       ioc->spi_data.dvStatus[pPDisk->PhysDiskID] |= MPT_SCSICFG_NEED_DV;
26799 +
26800 +                                               pPDisk++;
26801 +                                               numPDisk--;
26802 +                                       }
26803 +                               }
26804 +                               ioc->spi_data.forceDv &= ~MPT_SCSICFG_RELOAD_IOC_PG3;
26805                         }
26806 -               }
26807 -               ioc->spi_data.forceDv &= ~MPT_SCSICFG_RELOAD_IOC_PG3;
26808 -       }
26809  
26810 -       dvStatus = ioc->spi_data.dvStatus[id];
26811 +                       maxid = min_t(int, ioc->sh->max_id, MPT_MAX_SCSI_DEVICES);
26812  
26813 -       if (dvStatus & MPT_SCSICFG_NEED_DV) {
26814 -               ioc->spi_data.dvStatus[id] |= MPT_SCSICFG_DV_IN_PROGRESS;
26815 -               ioc->spi_data.dvStatus[id] &= ~MPT_SCSICFG_NEED_DV;
26816 +                       for (id = 0; id < maxid; id++) {
26817 +                               spin_lock_irqsave(&dvtaskQ_lock, flags);
26818 +                               if (dvtaskQ_release) {
26819 +                                       dvtaskQ_active = 0;
26820 +                                       spin_unlock_irqrestore(&dvtaskQ_lock, flags);
26821 +                                       return;
26822 +                               }
26823 +                               spin_unlock_irqrestore(&dvtaskQ_lock, flags);
26824 +                               dvStatus = hd->ioc->spi_data.dvStatus[id];
26825  
26826 -//             set_current_state(TASK_INTERRUPTIBLE);
26827 -//             schedule_timeout(MPT_HZ/4);
26828 +                               if (dvStatus & MPT_SCSICFG_NEED_DV) {
26829 +                                       did++;
26830 +                                       hd->ioc->spi_data.dvStatus[id] |= MPT_SCSICFG_DV_PENDING;
26831 +                                       hd->ioc->spi_data.dvStatus[id] &= ~MPT_SCSICFG_NEED_DV;
26832 +
26833 +                                       msleep(250);
26834 +
26835 +                                       /* If hidden phys disk, block IO's to all
26836 +                                        *      raid volumes
26837 +                                        * else, process normally
26838 +                                        */
26839 +                                       isPhysDisk = mptscsih_is_phys_disk(hd->ioc, id);
26840 +                                       if (isPhysDisk) {
26841 +                                               for (ii=0; ii < MPT_MAX_SCSI_DEVICES; ii++) {
26842 +                                                       if (hd->ioc->raid_data.isRaid & (1 << ii)) {
26843 +                                                               hd->ioc->spi_data.dvStatus[ii] |= MPT_SCSICFG_DV_PENDING;
26844 +                                                       }
26845 +                                               }
26846 +                                       }
26847  
26848 -               /* If hidden phys disk, block IO's to all
26849 -                *      raid volumes
26850 -                * else, process normally
26851 -                */
26852 -               if (ioc->raid_data.isRaid & (1 << id)) {
26853 -                       Ioc3PhysDisk_t *pPDisk =  ioc->raid_data.pIocPg3->PhysDisk;
26854 -                       int numPDisk = ioc->raid_data.pIocPg3->NumPhysDisks;
26855 -                       while (numPDisk) {
26856 -                               ii = pPDisk->PhysDiskID;
26857 -                               if ( ioc->spi_data.dvStatus[ii] & MPT_SCSICFG_DV_NOT_DONE) {
26858 -                                       ddvprintk((KERN_WARNING "doDv for PhysDiskNum=%d PhysDiskID=%d numPDisk=%d\n",
26859 -                                               pPDisk->PhysDiskNum, ii, numPDisk));
26860 -                                       if (mptscsih_doDv(hd, 0, ii) == 1) {
26861 +                                       if(mpt_alt_ioc_wait(hd->ioc)!=0) {
26862 +                                               ddvprintk((MYIOC_s_WARN_FMT "alt_ioc busy!\n",
26863 +                                                   hd->ioc->name));
26864 +                                               continue;
26865 +                                       }
26866 +
26867 +                                       if (mptscsih_doDv(hd, 0, id) == 1) {
26868                                                 /* Untagged device was busy, try again
26869                                                  */
26870 -                                               ioc->spi_data.dvStatus[ii] |= MPT_SCSICFG_NEED_DV;
26871 +                                               hd->ioc->spi_data.dvStatus[id] |= MPT_SCSICFG_NEED_DV;
26872 +                                               hd->ioc->spi_data.dvStatus[id] &= ~MPT_SCSICFG_DV_PENDING;
26873                                         } else {
26874 -                                               ddvprintk((KERN_WARNING "doDv successful for PhysDiskNum=%d PhysDiskID=%d\n",
26875 -                                                       pPDisk->PhysDiskNum, ii));
26876                                                 /* DV is complete. Clear flags.
26877                                                  */
26878 -                                               ioc->spi_data.dvStatus[ii] &= ~MPT_SCSICFG_DV_NOT_DONE;
26879 +                                               hd->ioc->spi_data.dvStatus[id] &= ~(MPT_SCSICFG_DV_NOT_DONE | MPT_SCSICFG_DV_PENDING);
26880 +                                       }
26881 +
26882 +                                       spin_lock(&hd->ioc->initializing_hba_lock);
26883 +                                       hd->ioc->initializing_hba_lock_flag=0;
26884 +                                       spin_unlock(&hd->ioc->initializing_hba_lock);
26885 +
26886 +                                       if (isPhysDisk) {
26887 +                                               for (ii=0; ii < MPT_MAX_SCSI_DEVICES; ii++) {
26888 +                                                       if (hd->ioc->raid_data.isRaid & (1 << ii)) {
26889 +                                                               hd->ioc->spi_data.dvStatus[ii] &= ~MPT_SCSICFG_DV_PENDING;
26890 +                                                       }
26891 +                                               }
26892                                         }
26893 +
26894 +                                       if (hd->ioc->spi_data.noQas)
26895 +                                               mptscsih_qas_check(hd, id);
26896                                 }
26897 -                               pPDisk++;
26898 -                               numPDisk--;
26899 -                       }
26900 -               } else {
26901 -                       ddvprintk((KERN_WARNING "doDv for id=%d\n",
26902 -                               id));
26903 -                       if (mptscsih_doDv(hd, 0, id) == 1) {
26904 -                               /* Untagged device was busy, try again
26905 -                                */
26906 -                               ioc->spi_data.dvStatus[id] |= MPT_SCSICFG_NEED_DV;
26907 -                       } else {
26908 -                               ddvprintk((KERN_WARNING "doDv successful for id=%d\n",
26909 -                                       id));
26910 -                               /* DV is complete. Clear flags.
26911 -                                */
26912 -                               ioc->spi_data.dvStatus[id] &= ~MPT_SCSICFG_DV_NOT_DONE;
26913                         }
26914                 }
26915 -
26916 -               if (ioc->spi_data.noQas)
26917 -                       mptscsih_qas_check(hd, id);
26918 -       } else {
26919 -               ddvprintk((KERN_INFO "~NEED_DV dvStatus=%x for id %d\n",
26920 -                       dvStatus, id));
26921 -//             panic( "~NEED_DV");
26922         }
26923 -mptscsih_domainValidation_exit:
26924 +
26925         spin_lock_irqsave(&dvtaskQ_lock, flags);
26926         dvtaskQ_active = 0;
26927         spin_unlock_irqrestore(&dvtaskQ_lock, flags);
26928 -}
26929 -
26930  
26931 -/* Post command on the PendingMF to the FW.
26932 - */
26933 -void
26934 -mptscsih_post_PendingMF_command(MPT_ADAPTER *ioc)
26935 -{
26936 -       MPT_SCSI_HOST   *hd;
26937 -       MPT_FRAME_HDR   *mf;
26938 -       struct scsi_cmnd *SCpnt;
26939 -       unsigned long    flags;
26940 -       u16              req_idx;
26941 -
26942 -       spin_lock_irqsave(&ioc->PendingMFlock, flags);
26943 -       if ((mf=ioc->PendingMF) == NULL) {
26944 -               spin_unlock_irqrestore(&ioc->PendingMFlock, flags);
26945 -               dpendprintk((MYIOC_s_INFO_FMT "%s: PendingMF is empty\n",
26946 -                       ioc->name, __FUNCTION__));
26947 -               return;
26948 -       }
26949 -
26950 -       mf = ioc->PendingMF;
26951 -       SCpnt = ioc->PendingSCpnt;
26952 -       ioc->PendingMF = NULL;
26953 -       spin_unlock_irqrestore(&ioc->PendingMFlock, flags);
26954 -
26955 -       dpendprintk((MYIOC_s_INFO_FMT "mptscsih_post_PendingMF_command: mf=%p\n",
26956 -               ioc->name, mf));
26957 -       DBG_DUMP_PENDING_REQUEST_FRAME(ioc, mf)
26958 -
26959 -       hd = (MPT_SCSI_HOST *) ioc->sh->hostdata;
26960 -       req_idx = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx);
26961 -       hd->ScsiLookup[req_idx] = SCpnt;
26962 -       mpt_put_msg_frame(ioc->DoneCtx, ioc, mf);
26963 +       return;
26964  }
26965  
26966 -
26967  /* Search IOC page 3 to determine if this is hidden physical disk
26968   */
26969  static int
26970 -mptscsih_is_phys_disk(MPT_ADAPTER *ioc, int channel, int id)
26971 +mptscsih_is_phys_disk(MPT_ADAPTER *ioc, int id)
26972  {
26973 -       struct inactive_raid_component_info *component_info;
26974         int i;
26975 -       int rc = 0;
26976 -
26977 -       if (!ioc->raid_data.pIocPg3)
26978 -               goto out;
26979 -       for (i = 0; i < ioc->raid_data.pIocPg3->NumPhysDisks; i++) {
26980 -               if ((id == ioc->raid_data.pIocPg3->PhysDisk[i].PhysDiskID) &&
26981 -                   (channel == ioc->raid_data.pIocPg3->PhysDisk[i].PhysDiskBus)) {
26982 -                       rc = 1;
26983 -                       goto out;
26984 -               }
26985 -       }
26986  
26987 -       /*
26988 -        * Check inactive list for matching phys disks
26989 -        */
26990 -       if (list_empty(&ioc->raid_data.inactive_list))
26991 -               goto out;
26992 +       if (!ioc->raid_data.isRaid || !ioc->raid_data.pIocPg3)
26993 +               return 0;
26994  
26995 -       down(&ioc->raid_data.inactive_list_mutex);
26996 -       list_for_each_entry(component_info,
26997 -           &ioc->raid_data.inactive_list, list) {
26998 -               if ((component_info->d.PhysDiskID == id) &&
26999 -                   (component_info->d.PhysDiskBus == channel))
27000 -                       rc = 1;
27001 +       for (i = 0; i < ioc->raid_data.pIocPg3->NumPhysDisks; i++) {
27002 +               if (id == ioc->raid_data.pIocPg3->PhysDisk[i].PhysDiskID)
27003 +                       return 1;
27004         }
27005 -       up(&ioc->raid_data.inactive_list_mutex);
27006  
27007 - out:
27008 -       return rc;
27009 +       return 0;
27010  }
27011  
27012  /* Write SDP1 if no QAS has been enabled
27013 @@ -5039,37 +4927,32 @@ mptscsih_is_phys_disk(MPT_ADAPTER *ioc, 
27014  static void
27015  mptscsih_qas_check(MPT_SCSI_HOST *hd, int id)
27016  {
27017 -       MPT_ADAPTER     *ioc = hd->ioc;
27018 -       struct _MPT_DEVICE      *pMptTarget;
27019         VirtDevice *pTarget;
27020         int ii;
27021  
27022 -       pMptTarget = ioc->Target_List[0];
27023         for (ii=0; ii < MPT_MAX_SCSI_DEVICES; ii++) {
27024                 if (ii == id)
27025                         continue;
27026  
27027 -               if ((ioc->spi_data.dvStatus[ii] & MPT_SCSICFG_DV_NOT_DONE) != 0)
27028 +               if ((hd->ioc->spi_data.dvStatus[ii] & MPT_SCSICFG_DV_NOT_DONE) != 0)
27029                         continue;
27030  
27031 -               pTarget = pMptTarget->Target[ii];
27032 -
27033 -               if (pTarget) {
27034 -                       if (!pTarget->raidVolume) {
27035 -                               if ((pTarget->negoFlags & ioc->spi_data.noQas) == 0) {
27036 -                                       pTarget->negoFlags |= ioc->spi_data.noQas;
27037 -                                       dnegoprintk(("mptscsih_qas_check: writeSDP1: id=%d negoFlags=%d\n", ii, pTarget->negoFlags));
27038 -                     mpt_writeSDP1(ioc, 0, ii, MPT_SCSICFG_USE_NVRAM);
27039 -                                               }
27040 -                       } else {
27041 -                               if (mptscsih_is_phys_disk(ioc, 0, ii) == 1) {
27042 -                                       dnegoprintk(("mptscsih_qas_check: is_phys_disk writeSDP1: id=%d SCSICFG_USE_NVRAM\n", ii));
27043 -                                     mpt_writeSDP1(ioc, 0, ii, MPT_SCSICFG_USE_NVRAM);
27044 +               pTarget = hd->Targets[ii];
27045  
27046 -                               }
27047 +               if (pTarget && (!pTarget->raidVolume)) {
27048 +                       if ((pTarget->negoFlags & hd->ioc->spi_data.noQas) == 0) {
27049 +                               pTarget->negoFlags |= hd->ioc->spi_data.noQas;
27050 +                               dnegoprintk(("writeSDP1: id=%d negoFlags=%d\n", id, pTarget->negoFlags));
27051 +                               mptscsih_writeSDP1(hd, 0, ii, 0);
27052 +                       }
27053 +               } else {
27054 +                       if (mptscsih_is_phys_disk(hd->ioc, ii) == 1) {
27055 +                               dnegoprintk(("writeSDP1: id=%d SCSICFG_USE_NVRAM\n", id));
27056 +                               mptscsih_writeSDP1(hd, 0, ii, MPT_SCSICFG_USE_NVRAM);
27057                         }
27058                 }
27059         }
27060 +       return;
27061  }
27062  
27063  
27064 @@ -5094,16 +4977,15 @@ mptscsih_qas_check(MPT_SCSI_HOST *hd, in
27065   *     Return: None.
27066   */
27067  static int
27068 -mptscsih_doDv(MPT_SCSI_HOST *hd, int bus, int id)
27069 +mptscsih_doDv(MPT_SCSI_HOST *hd, int bus_number, int id)
27070  {
27071         MPT_ADAPTER             *ioc = hd->ioc;
27072 -       struct _MPT_DEVICE      *pMptTarget;
27073         VirtDevice              *pTarget;
27074         SCSIDevicePage1_t       *pcfg1Data;
27075         SCSIDevicePage0_t       *pcfg0Data;
27076         u8                      *pbuf1;
27077         u8                      *pbuf2;
27078 -       u8                      *pDvBuf=NULL;
27079 +       u8                      *pDvBuf;
27080         dma_addr_t               dvbuf_dma = -1;
27081         dma_addr_t               buf1_dma = -1;
27082         dma_addr_t               buf2_dma = -1;
27083 @@ -5127,7 +5009,7 @@ mptscsih_doDv(MPT_SCSI_HOST *hd, int bus
27084         char                     firstPass = 1;
27085         char                     doFallback = 0;
27086         char                     readPage0;
27087 -       char                     lun;
27088 +       char                     bus, lun;
27089         char                     inq0 = 0;
27090  
27091         if (ioc->spi_data.sdp1length == 0)
27092 @@ -5141,10 +5023,12 @@ mptscsih_doDv(MPT_SCSI_HOST *hd, int bus
27093          */
27094         if (id == ioc->pfacts[0].PortSCSIID)
27095                 return 0;
27096 -ioc->spi_data.dvStatus[id] |= MPT_SCSICFG_DV_IN_PROGRESS;
27097  
27098         lun = 0;
27099 -       ddvprintk((MYIOC_s_INFO_FMT "DV Started: bus=%d id=%d dv @ %p\n",ioc->name, bus, id, &dv));
27100 +       bus = (u8) bus_number;
27101 +       ddvtprintk((MYIOC_s_NOTE_FMT
27102 +                       "DV Started: bus=%d id=%d dv @ %p\n",
27103 +                       ioc->name, bus, id, &dv));
27104  
27105         /* Prep DV structure
27106          */
27107 @@ -5167,8 +5051,7 @@ ioc->spi_data.dvStatus[id] |= MPT_SCSICF
27108         iocmd.physDiskNum = -1;
27109         iocmd.rsvd = iocmd.rsvd2 = 0;
27110  
27111 -       pMptTarget = ioc->Target_List[bus];
27112 -       pTarget = pMptTarget->Target[id];
27113 +       pTarget = hd->Targets[id];
27114  
27115         /* Use tagged commands if possible.
27116          */
27117 @@ -5176,12 +5059,12 @@ ioc->spi_data.dvStatus[id] |= MPT_SCSICF
27118                 if (pTarget->tflags & MPT_TARGET_FLAGS_Q_YES)
27119                         iocmd.flags |= MPT_ICFLAG_TAGGED_CMD;
27120                 else {
27121 -                       if (ioc->facts.FWVersion.Word < 0x01000600)
27122 -                                 goto doDv_done;
27123 +                       if (hd->ioc->facts.FWVersion.Word < 0x01000600)
27124 +                               return 0;
27125  
27126 -                       if ((ioc->facts.FWVersion.Word >= 0x01010000) &&
27127 -                               (ioc->facts.FWVersion.Word < 0x01010B00))
27128 -                                goto doDv_done;
27129 +                       if ((hd->ioc->facts.FWVersion.Word >= 0x01010000) &&
27130 +                               (hd->ioc->facts.FWVersion.Word < 0x01010B00))
27131 +                               return 0;
27132                 }
27133         }
27134  
27135 @@ -5211,7 +5094,7 @@ ioc->spi_data.dvStatus[id] |= MPT_SCSICF
27136  
27137         pDvBuf = pci_alloc_consistent(ioc->pcidev, dv_alloc, &dvbuf_dma);
27138         if (pDvBuf == NULL)
27139 -                goto doDv_done;
27140 +               return 0;
27141  
27142         sz = 0;
27143         pbuf1 = (u8 *)pDvBuf;
27144 @@ -5237,7 +5120,7 @@ ioc->spi_data.dvStatus[id] |= MPT_SCSICF
27145         /* Skip this ID? Set cfg.cfghdr.hdr to force config page write
27146          */
27147         {
27148 -               SpiCfgData *pspi_data = &ioc->spi_data;
27149 +               SpiCfgData *pspi_data = &hd->ioc->spi_data;
27150                 if (pspi_data->nvram && (pspi_data->nvram[id] != MPT_HOST_NVRAM_INVALID)) {
27151                         /* Set the factor from nvram */
27152                         nfactor = (pspi_data->nvram[id] & MPT_NVRAM_SYNC_MASK) >> 8;
27153 @@ -5247,7 +5130,7 @@ ioc->spi_data.dvStatus[id] |= MPT_SCSICF
27154                         if (!(pspi_data->nvram[id] & MPT_NVRAM_ID_SCAN_ENABLE) ||
27155                                 (pspi_data->PortFlags == MPI_SCSIPORTPAGE2_PORT_FLAGS_OFF_DV) ) {
27156  
27157 -                               ddvprintk((MYIOC_s_INFO_FMT "DV Skipped: bus, id, lun (%d, %d, %d)\n",
27158 +                               ddvprintk((MYIOC_s_NOTE_FMT "DV Skipped: bus, id, lun (%d, %d, %d)\n",
27159                                         ioc->name, bus, id, lun));
27160  
27161                                 dv.cmd = MPT_SET_MAX;
27162 @@ -5260,7 +5143,7 @@ ioc->spi_data.dvStatus[id] |= MPT_SCSICF
27163                                 cfg.physAddr = cfg1_dma_addr;
27164                                 cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_CURRENT;
27165                                 cfg.dir = 1;
27166 -                               mpt_config(ioc, &cfg);
27167 +                               mpt_config(hd->ioc, &cfg);
27168                                 goto target_done;
27169                         }
27170                 }
27171 @@ -5295,7 +5178,7 @@ ioc->spi_data.dvStatus[id] |= MPT_SCSICF
27172         /* RAID Volume ID's may double for a physical device. If RAID but
27173          * not a physical ID as well, skip DV.
27174          */
27175 -       if ((ioc->raid_data.isRaid & (1 << id)) && !(iocmd.flags & MPT_ICFLAG_PHYS_DISK))
27176 +       if ((hd->ioc->raid_data.isRaid & (1 << id)) && !(iocmd.flags & MPT_ICFLAG_PHYS_DISK))
27177                 goto target_done;
27178  
27179  
27180 @@ -5312,10 +5195,8 @@ ioc->spi_data.dvStatus[id] |= MPT_SCSICF
27181         readPage0 = 0;
27182         sz = SCSI_MAX_INQUIRY_BYTES;
27183         rc = MPT_SCANDV_GOOD;
27184 -
27185 -start_DV:
27186         while (1) {
27187 -               ddvprintk((MYIOC_s_INFO_FMT "DV: Start Basic test on id=%d\n", ioc->name, id));
27188 +               ddvprintk((MYIOC_s_NOTE_FMT "DV: Start Basic test on id=%d\n", ioc->name, id));
27189                 retcode = 0;
27190                 dv.cmd = MPT_SET_MIN;
27191                 mptscsih_dv_parms(hd, &dv, (void *)pcfg1Data);
27192 @@ -5324,7 +5205,7 @@ start_DV:
27193                 cfg.physAddr = cfg1_dma_addr;
27194                 cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_CURRENT;
27195                 cfg.dir = 1;
27196 -               if (mpt_config(ioc, &cfg) != 0)
27197 +               if (mpt_config(hd->ioc, &cfg) != 0)
27198                         goto target_done;
27199  
27200                 /* Wide - narrow - wide workaround case
27201 @@ -5333,9 +5214,9 @@ start_DV:
27202                         /* Send an untagged command to reset disk Qs corrupted
27203                          * when a parity error occurs on a Request Sense.
27204                          */
27205 -                       if ((ioc->facts.FWVersion.Word >= 0x01000600) ||
27206 -                               ((ioc->facts.FWVersion.Word >= 0x01010000) &&
27207 -                               (ioc->facts.FWVersion.Word < 0x01010B00)) ) {
27208 +                       if ((hd->ioc->facts.FWVersion.Word >= 0x01000600) ||
27209 +                               ((hd->ioc->facts.FWVersion.Word >= 0x01010000) &&
27210 +                               (hd->ioc->facts.FWVersion.Word < 0x01010B00)) ) {
27211  
27212                                 iocmd.cmd = REQUEST_SENSE;
27213                                 iocmd.data_dma = buf1_dma;
27214 @@ -5400,6 +5281,12 @@ start_DV:
27215                  * if PROCESSOR, quit DV.
27216                  */
27217                 if (inq0 == TYPE_PROCESSOR) {
27218 +                       mptscsih_initTarget(hd,
27219 +                               bus,
27220 +                               id,
27221 +                               lun,
27222 +                               pbuf1,
27223 +                               sz);
27224                         goto target_done;
27225                 }
27226  
27227 @@ -5426,8 +5313,8 @@ start_DV:
27228  
27229                                 if ((pbuf1[56] & 0x02) == 0) {
27230                                         pTarget->negoFlags |= MPT_TARGET_NO_NEGO_QAS;
27231 -                                       ioc->spi_data.noQas = MPT_TARGET_NO_NEGO_QAS;
27232 -                                       ddvprintk((MYIOC_s_INFO_FMT
27233 +                                       hd->ioc->spi_data.noQas = MPT_TARGET_NO_NEGO_QAS;
27234 +                                       ddvprintk((MYIOC_s_NOTE_FMT 
27235                                             "DV: Start Basic noQas on id=%d due to pbuf1[56]=%x\n", 
27236                                             ioc->name, id, pbuf1[56]));
27237                                 }
27238 @@ -5440,7 +5327,7 @@ start_DV:
27239                         dv.cmd = MPT_SET_MAX;
27240  
27241                 mptscsih_dv_parms(hd, &dv, (void *)pcfg1Data);
27242 -               if (mpt_config(ioc, &cfg) != 0)
27243 +               if (mpt_config(hd->ioc, &cfg) != 0)
27244                         goto target_done;
27245  
27246                 if ((!dv.now.width) && (!dv.now.offset))
27247 @@ -5473,7 +5360,7 @@ start_DV:
27248                                         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
27249                                         cfg.dir = 0;
27250  
27251 -                                       if (mpt_config(ioc, &cfg) != 0)
27252 +                                       if (mpt_config(hd->ioc, &cfg) != 0)
27253                                                 goto target_done;
27254  
27255                                         sdp0_info = le32_to_cpu(pcfg0Data->Information) & 0x0E;
27256 @@ -5504,7 +5391,15 @@ start_DV:
27257                                                 if (!firstPass)
27258                                                         doFallback = 1;
27259                                         } else {
27260 -
27261 +                                               ddvprintk((MYIOC_s_NOTE_FMT
27262 +                                                   "DV:Inquiry compared id=%d, calling initTarget\n", ioc->name, id));
27263 +                                               hd->ioc->spi_data.dvStatus[id] &= ~MPT_SCSICFG_DV_NOT_DONE;
27264 +                                               mptscsih_initTarget(hd,
27265 +                                                       bus,
27266 +                                                       id,
27267 +                                                       lun,
27268 +                                                       pbuf1,
27269 +                                                       sz);
27270                                                 break;  /* test complete */
27271                                         }
27272                                 }
27273 @@ -5522,7 +5417,7 @@ start_DV:
27274                         firstPass = 0;
27275                 }
27276         }
27277 -       ddvprintk((MYIOC_s_INFO_FMT "DV: Basic test on id=%d completed OK.\n", ioc->name, id));
27278 +       ddvprintk((MYIOC_s_NOTE_FMT "DV: Basic test on id=%d completed OK.\n", ioc->name, id));
27279  
27280         if (ioc->spi_data.mpt_dv == 0)
27281                 goto target_done;
27282 @@ -5534,10 +5429,10 @@ start_DV:
27283         if (inq0 != 0)
27284                 goto target_done;
27285  
27286 -       ddvprintk((MYIOC_s_INFO_FMT "DV: bus, id, lun (%d, %d, %d) PortFlags=%x\n",
27287 +       ddvprintk((MYIOC_s_NOTE_FMT "DV: bus, id, lun (%d, %d, %d) PortFlags=%x\n",
27288                         ioc->name, bus, id, lun, ioc->spi_data.PortFlags));
27289         if ( ioc->spi_data.PortFlags == MPI_SCSIPORTPAGE2_PORT_FLAGS_BASIC_DV_ONLY ) {
27290 -               ddvprintk((MYIOC_s_INFO_FMT "DV Basic Only: bus, id, lun (%d, %d, %d) PortFlags=%x\n",
27291 +               ddvprintk((MYIOC_s_NOTE_FMT "DV Basic Only: bus, id, lun (%d, %d, %d) PortFlags=%x\n",
27292                         ioc->name, bus, id, lun, ioc->spi_data.PortFlags));
27293                 goto target_done;
27294         }
27295 @@ -5574,7 +5469,7 @@ start_DV:
27296                         u8 skey = hd->pLocal->sense[2] & 0x0F;
27297                         u8 asc = hd->pLocal->sense[12];
27298                         u8 ascq = hd->pLocal->sense[13];
27299 -                       ddvprintk((MYIOC_s_WARN_FMT
27300 +                       ddvprintk((MYIOC_s_INFO_FMT
27301                                 "SenseKey:ASC:ASCQ = (%x:%02x:%02x)\n",
27302                                 ioc->name, skey, asc, ascq));
27303  
27304 @@ -5646,7 +5541,7 @@ start_DV:
27305                                         u8 skey = hd->pLocal->sense[2] & 0x0F;
27306                                         u8 asc = hd->pLocal->sense[12];
27307                                         u8 ascq = hd->pLocal->sense[13];
27308 -                                       ddvprintk((MYIOC_s_WARN_FMT
27309 +                                       ddvprintk((MYIOC_s_INFO_FMT
27310                                                 "SenseKey:ASC:ASCQ = (%x:%02x:%02x)\n",
27311                                                 ioc->name, skey, asc, ascq));
27312                                         if (skey == ILLEGAL_REQUEST) {
27313 @@ -5665,11 +5560,6 @@ start_DV:
27314                                                         ioc->name));
27315                                                 goto target_done;
27316                                         }
27317 -                               } else if (rc == MPT_SCANDV_FALLBACK) {
27318 -                                       doFallback = 1; /* set fallback flag */
27319 -                                       notDone++;
27320 -                                       goto start_DV;
27321 -
27322                                 } else {
27323                                         /* All other errors are fatal
27324                                          */
27325 @@ -5812,7 +5702,7 @@ skip_Reserve:
27326                                         dv.cmd = MPT_FALLBACK;
27327                                         mptscsih_dv_parms(hd, &dv, (void *)pcfg1Data);
27328  
27329 -                                       if (mpt_config(ioc, &cfg) != 0)
27330 +                                       if (mpt_config(hd->ioc, &cfg) != 0)
27331                                                 goto target_done;
27332  
27333                                         if ((!dv.now.width) && (!dv.now.offset))
27334 @@ -5826,7 +5716,7 @@ skip_Reserve:
27335                                 /* Restart data test if UA, else quit.
27336                                  */
27337                                 u8 skey = hd->pLocal->sense[2] & 0x0F;
27338 -                               ddvprintk((MYIOC_s_WARN_FMT
27339 +                               ddvprintk((MYIOC_s_INFO_FMT
27340                                         "SenseKey:ASC:ASCQ = (%x:%02x:%02x)\n", ioc->name, skey,
27341                                         hd->pLocal->sense[12], hd->pLocal->sense[13]));
27342                                 if (skey == UNIT_ATTENTION) {
27343 @@ -5891,7 +5781,7 @@ skip_Reserve:
27344                                                 dv.cmd = MPT_FALLBACK;
27345                                                 mptscsih_dv_parms(hd, &dv, (void *)pcfg1Data);
27346  
27347 -                                               if (mpt_config(ioc, &cfg) != 0)
27348 +                                               if (mpt_config(hd->ioc, &cfg) != 0)
27349                                                         goto target_done;
27350  
27351                                                 if ((!dv.now.width) && (!dv.now.offset))
27352 @@ -5909,7 +5799,7 @@ skip_Reserve:
27353                                 dv.cmd = MPT_FALLBACK;
27354                                 mptscsih_dv_parms(hd, &dv, (void *)pcfg1Data);
27355  
27356 -                               if (mpt_config(ioc, &cfg) != 0)
27357 +                               if (mpt_config(hd->ioc, &cfg) != 0)
27358                                          goto target_done;
27359  
27360                                 if ((!dv.now.width) && (!dv.now.offset))
27361 @@ -5922,7 +5812,7 @@ skip_Reserve:
27362                                 /* Restart data test if UA, else quit.
27363                                  */
27364                                 u8 skey = hd->pLocal->sense[2] & 0x0F;
27365 -                               ddvprintk((MYIOC_s_WARN_FMT
27366 +                               ddvprintk((MYIOC_s_INFO_FMT
27367                                         "SenseKey:ASC:ASCQ = (%x:%02x:%02x)\n", ioc->name, skey,
27368                                         hd->pLocal->sense[12], hd->pLocal->sense[13]));
27369                                 if (skey == UNIT_ATTENTION) {
27370 @@ -5964,8 +5854,8 @@ target_done:
27371                 /* If disk, not U320, disable QAS
27372                  */
27373                 if ((inq0 == 0) && (dv.now.factor > MPT_ULTRA320)) {
27374 -                       ioc->spi_data.noQas = MPT_TARGET_NO_NEGO_QAS;
27375 -                       ddvprintk((MYIOC_s_INFO_FMT
27376 +                       hd->ioc->spi_data.noQas = MPT_TARGET_NO_NEGO_QAS;
27377 +                       ddvprintk((MYIOC_s_NOTE_FMT
27378                             "noQas set due to id=%d has factor=%x\n", ioc->name, id, dv.now.factor));
27379                 }
27380  
27381 @@ -5980,7 +5870,7 @@ target_done:
27382                 cfg.physAddr = cfg1_dma_addr;
27383                 cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_CURRENT;
27384                 cfg.dir = 1;
27385 -               mpt_config(ioc, &cfg);
27386 +               mpt_config(hd->ioc, &cfg);
27387                  */
27388         }
27389  
27390 @@ -5991,18 +5881,13 @@ target_done:
27391                         ddvprintk((MYIOC_s_ERR_FMT "RAID Enable FAILED!\n", ioc->name));
27392         }
27393  
27394 -doDv_done:
27395         /* Done with the DV scan of the current target
27396          */
27397         if (pDvBuf)
27398                 pci_free_consistent(ioc->pcidev, dv_alloc, pDvBuf, dvbuf_dma);
27399  
27400 -       ddvprintk((MYIOC_s_WARN_FMT "DV Done id=%d\n",ioc->name, id));
27401 -       ioc->spi_data.dvStatus[id] &= ~(MPT_SCSICFG_DV_NOT_DONE | MPT_SCSICFG_DV_IN_PROGRESS);
27402 -       /* Post an IO that was pended while
27403 -        * DV was running.
27404 -        */
27405 -       mptscsih_post_PendingMF_command(ioc);
27406 +       ddvtprintk((MYIOC_s_INFO_FMT "DV Done id=%d\n",
27407 +                       ioc->name, id));
27408  
27409         return retcode;
27410  }
27411 @@ -6017,8 +5902,6 @@ doDv_done:
27412  static void
27413  mptscsih_dv_parms(MPT_SCSI_HOST *hd, DVPARAMETERS *dv,void *pPage)
27414  {
27415 -       MPT_ADAPTER             *ioc = hd->ioc;
27416 -       struct _MPT_DEVICE      *pMptTarget;
27417         VirtDevice              *pTarget;
27418         SCSIDevicePage0_t       *pPage0;
27419         SCSIDevicePage1_t       *pPage1;
27420 @@ -6032,48 +5915,49 @@ mptscsih_dv_parms(MPT_SCSI_HOST *hd, DVP
27421  
27422         switch (cmd) {
27423         case MPT_GET_NVRAM_VALS:
27424 -               ddvprintk((MYIOC_s_INFO_FMT "Getting NVRAM: ",
27425 -                       ioc->name));
27426 +               ddvprintk((MYIOC_s_NOTE_FMT "Getting NVRAM: ",
27427 +                                                        hd->ioc->name));
27428                 /* Get the NVRAM values and save in tmax
27429                  * If not an LVD bus, the adapter minSyncFactor has been
27430                  * already throttled back.
27431                  */
27432 -               negoFlags = ioc->spi_data.noQas;
27433 -               pMptTarget = ioc->Target_List[0];
27434 -               pTarget = pMptTarget->Target[id];
27435 -               if (ioc->spi_data.nvram && (ioc->spi_data.nvram[id] != MPT_HOST_NVRAM_INVALID)) {
27436 -                       data = ioc->spi_data.nvram[id];
27437 -                       width = data & MPT_NVRAM_WIDE_DISABLE ? 0 : 1;
27438 -                       if ((offset = ioc->spi_data.maxSyncOffset) == 0)
27439 -                               factor = MPT_ASYNC;
27440 -                       else {
27441 -                               factor = (data & MPT_NVRAM_SYNC_MASK) >> MPT_NVRAM_SYNC_SHIFT;
27442 -                               if ((factor == 0) || (factor == MPT_ASYNC)){
27443 +               negoFlags = hd->ioc->spi_data.noQas;
27444 +               if ((pTarget = hd->Targets[(int)id]) && !pTarget->raidVolume) {
27445 +                       width = pTarget->maxWidth;
27446 +                       offset = pTarget->maxOffset;
27447 +                       factor = pTarget->minSyncFactor;
27448 +                       negoFlags |= pTarget->negoFlags;
27449 +               } else {
27450 +                       if (hd->ioc->spi_data.nvram && (hd->ioc->spi_data.nvram[id] != MPT_HOST_NVRAM_INVALID)) {
27451 +                               data = hd->ioc->spi_data.nvram[id];
27452 +                               width = data & MPT_NVRAM_WIDE_DISABLE ? 0 : 1;
27453 +                               if ((offset = hd->ioc->spi_data.maxSyncOffset) == 0)
27454                                         factor = MPT_ASYNC;
27455 -                                       offset = 0;
27456 +                               else {
27457 +                                       factor = (data & MPT_NVRAM_SYNC_MASK) >> MPT_NVRAM_SYNC_SHIFT;
27458 +                                       if ((factor == 0) || (factor == MPT_ASYNC)){
27459 +                                               factor = MPT_ASYNC;
27460 +                                               offset = 0;
27461 +                                       }
27462                                 }
27463 -                       ddvprintk(("NVRAM id=%d width=%d factor=%x offset=%x negoFlags=%x\n",
27464 -                               id, width, factor, offset, negoFlags));
27465 +                       } else {
27466 +                               width = MPT_NARROW;
27467 +                               offset = 0;
27468 +                               factor = MPT_ASYNC;
27469                         }
27470 -               } else {
27471 -                       width = MPT_NARROW;
27472 -                       offset = 0;
27473 -                       factor = MPT_ASYNC;
27474 -                       ddvprintk(("NVRAM_INVALID id=%d width=%d factor=%x offset=%x negoFlags=%x\n",
27475 -                               id, width, factor, offset, negoFlags));
27476 -               }
27477  
27478 -               /* Set the negotiation flags */
27479 -               if (!width)
27480 -                       negoFlags |= MPT_TARGET_NO_NEGO_WIDE;
27481 +                       /* Set the negotiation flags */
27482 +                       if (!width)
27483 +                               negoFlags |= MPT_TARGET_NO_NEGO_WIDE;
27484  
27485 -               if (!offset)
27486 -                       negoFlags |= MPT_TARGET_NO_NEGO_SYNC;
27487 +                       if (!offset)
27488 +                               negoFlags |= MPT_TARGET_NO_NEGO_SYNC;
27489 +               }
27490  
27491                 /* limit by adapter capabilities */
27492 -               width = min(width, ioc->spi_data.maxBusWidth);
27493 -               offset = min(offset, ioc->spi_data.maxSyncOffset);
27494 -               factor = max(factor, ioc->spi_data.minSyncFactor);
27495 +               width = min(width, hd->ioc->spi_data.maxBusWidth);
27496 +               offset = min(offset, hd->ioc->spi_data.maxSyncOffset);
27497 +               factor = max(factor, hd->ioc->spi_data.minSyncFactor);
27498  
27499                 /* Check Consistency */
27500                 if (offset && (factor < MPT_ULTRA2) && !width)
27501 @@ -6083,13 +5967,13 @@ mptscsih_dv_parms(MPT_SCSI_HOST *hd, DVP
27502                 dv->max.offset = offset;
27503                 dv->max.factor = factor;
27504                 dv->max.flags = negoFlags;
27505 -               ddvprintk(("id=%d width=%d factor=%x offset=%x negoFlags=%x\n",
27506 +               ddvprintk((" id=%d width=%d factor=%x offset=%x negoFlags=%x\n",
27507                                 id, width, factor, offset, negoFlags));
27508                 break;
27509  
27510         case MPT_UPDATE_MAX:
27511 -               ddvprintk((MYIOC_s_INFO_FMT
27512 -                       "Updating with SDP0 Data: ", ioc->name));
27513 +               ddvprintk((MYIOC_s_NOTE_FMT
27514 +                       "Updating with SDP0 Data: ", hd->ioc->name));
27515                 /* Update tmax values with those from Device Page 0.*/
27516                 pPage0 = (SCSIDevicePage0_t *) pPage;
27517                 if (pPage0) {
27518 @@ -6103,10 +5987,12 @@ mptscsih_dv_parms(MPT_SCSI_HOST *hd, DVP
27519                 dv->now.offset = dv->max.offset;
27520                 dv->now.factor = dv->max.factor;
27521                 ddvprintk(("id=%d width=%d factor=%x offset=%x negoFlags=%x\n",
27522 -                       id, dv->now.width, dv->now.factor, dv->now.offset, dv->now.flags));
27523 +                               id, dv->now.width, dv->now.factor, dv->now.offset, dv->now.flags));
27524                 break;
27525  
27526         case MPT_SET_MAX:
27527 +               ddvprintk((MYIOC_s_NOTE_FMT "Setting Max: ",
27528 +                                                               hd->ioc->name));
27529                 /* Set current to the max values. Update the config page.*/
27530                 dv->now.width = dv->max.width;
27531                 dv->now.offset = dv->max.offset;
27532 @@ -6115,18 +6001,22 @@ mptscsih_dv_parms(MPT_SCSI_HOST *hd, DVP
27533  
27534                 pPage1 = (SCSIDevicePage1_t *)pPage;
27535                 if (pPage1) {
27536 -                       mpt_setSDP1parameters (dv->now.width, dv->now.factor, dv->now.offset, dv->now.flags,
27537 -                               &val, &configuration);
27538 +                       mptscsih_setDevicePage1Flags (dv->now.width, dv->now.factor,
27539 +                               dv->now.offset, &val, &configuration, dv->now.flags);
27540 +                       dnegoprintk(("Setting Max: id=%d width=%d factor=%x offset=%x negoFlags=%x request=%x config=%x\n",
27541 +                               id, dv->now.width, dv->now.factor, dv->now.offset, dv->now.flags, val, configuration));
27542                         pPage1->RequestedParameters = cpu_to_le32(val);
27543                         pPage1->Reserved = 0;
27544                         pPage1->Configuration = cpu_to_le32(configuration);
27545                 }
27546  
27547 -               dnegoprintk(("%s: Setting Max: id=%d width=%d factor=%x offset=%x negoFlags=%x requested=%08x configuration=%08x\n",
27548 -                               ioc->name, id, dv->now.width, dv->now.factor, dv->now.offset, dv->now.flags, val, configuration));
27549 +               ddvprintk(("id=%d width=%d factor=%x offset=%x negoFlags=%x request=%x configuration=%x\n",
27550 +                               id, dv->now.width, dv->now.factor, dv->now.offset, dv->now.flags, val, configuration));
27551                 break;
27552  
27553         case MPT_SET_MIN:
27554 +               ddvprintk((MYIOC_s_NOTE_FMT "Setting Min: ",
27555 +                                                               hd->ioc->name));
27556                 /* Set page to asynchronous and narrow
27557                  * Do not update now, breaks fallback routine. */
27558                 width = MPT_NARROW;
27559 @@ -6136,20 +6026,22 @@ mptscsih_dv_parms(MPT_SCSI_HOST *hd, DVP
27560  
27561                 pPage1 = (SCSIDevicePage1_t *)pPage;
27562                 if (pPage1) {
27563 -                       mpt_setSDP1parameters (width, factor, offset, negoFlags,
27564 -                               &val, &configuration);
27565 +                       mptscsih_setDevicePage1Flags (width, factor,
27566 +                               offset, &val, &configuration, negoFlags);
27567 +                       dnegoprintk(("Setting Min: id=%d width=%d factor=%x offset=%x negoFlags=%x request=%x config=%x\n",
27568 +                               id, width, factor, offset, negoFlags, val, configuration));
27569                         pPage1->RequestedParameters = cpu_to_le32(val);
27570                         pPage1->Reserved = 0;
27571                         pPage1->Configuration = cpu_to_le32(configuration);
27572                 }
27573 -               dnegoprintk(("%s: Setting Min: id=%d width=%d factor=%x offset=%x negoFlags=%x requested=%08x configuration=%08x\n",
27574 -                               ioc->name, id, width, factor, offset, negoFlags, val, configuration));
27575 +               ddvprintk(("id=%d width=%d factor=%x offset=%x request=%x config=%x negoFlags=%x\n",
27576 +                               id, width, factor, offset, val, configuration, negoFlags));
27577                 break;
27578  
27579         case MPT_FALLBACK:
27580 -               ddvprintk((MYIOC_s_INFO_FMT
27581 +               ddvprintk((MYIOC_s_NOTE_FMT
27582                         "Fallback: Start: offset %d, factor %x, width %d \n",
27583 -                               ioc->name, dv->now.offset,
27584 +                               hd->ioc->name, dv->now.offset,
27585                                 dv->now.factor, dv->now.width));
27586                 width = dv->now.width;
27587                 offset = dv->now.offset;
27588 @@ -6212,32 +6104,31 @@ mptscsih_dv_parms(MPT_SCSI_HOST *hd, DVP
27589  
27590                 pPage1 = (SCSIDevicePage1_t *)pPage;
27591                 if (pPage1) {
27592 -                       mpt_setSDP1parameters (width, factor, offset, dv->now.flags,
27593 -                               &val, &configuration);
27594 +                       mptscsih_setDevicePage1Flags (width, factor, offset, &val,
27595 +                                               &configuration, dv->now.flags);
27596 +                       dnegoprintk(("Finish: id=%d width=%d offset=%d factor=%x negoFlags=%x request=%x config=%x\n",
27597 +                            id, width, offset, factor, dv->now.flags, val, configuration));
27598  
27599                         pPage1->RequestedParameters = cpu_to_le32(val);
27600                         pPage1->Reserved = 0;
27601                         pPage1->Configuration = cpu_to_le32(configuration);
27602                 }
27603  
27604 -               ddvprintk(("%s: Finish: id=%d width=%d offset=%d factor=%x negoFlags=%x requested=%08x configuration=%08x\n",
27605 -                            ioc->name, id, width, offset, factor, dv->now.flags, val, configuration));
27606 +               ddvprintk(("Finish: id=%d offset=%d factor=%x width=%d request=%x config=%x\n",
27607 +                            id, dv->now.offset, dv->now.factor, dv->now.width, val, configuration));
27608                 break;
27609  
27610         case MPT_SAVE:
27611 -               ddvprintk((MYIOC_s_INFO_FMT
27612 -                       "Saving to pTarget: "
27613 -                       "id=%d width=%x factor=%x offset=%d negoFlags=%x\n",
27614 -                               ioc->name, id, dv->now.width, dv->now.factor,
27615 -                               dv->now.offset, dv->now.flags));
27616 +               ddvprintk((MYIOC_s_NOTE_FMT
27617 +                       "Saving to Target structure: ", hd->ioc->name));
27618 +               ddvprintk(("id=%d width=%x factor=%x offset=%d negoFlags=%x\n",
27619 +                            id, dv->now.width, dv->now.factor, dv->now.offset, dv->now.flags));
27620  
27621                 /* Save these values to target structures
27622                  * or overwrite nvram (phys disks only).
27623                  */
27624  
27625 -               pMptTarget = ioc->Target_List[0];
27626 -               pTarget = pMptTarget->Target[id];
27627 -               if (pTarget && !pTarget->raidVolume ) {
27628 +               if ((pTarget = hd->Targets[(int)id]) && !pTarget->raidVolume ) {
27629                         pTarget->maxWidth = dv->now.width;
27630                         pTarget->maxOffset = dv->now.offset;
27631                         pTarget->minSyncFactor = dv->now.factor;
27632 @@ -6246,8 +6137,8 @@ mptscsih_dv_parms(MPT_SCSI_HOST *hd, DVP
27633                         /* Preserv all flags, use
27634                          * read-modify-write algorithm
27635                          */
27636 -                       if (ioc->spi_data.nvram) {
27637 -                               data = ioc->spi_data.nvram[id];
27638 +                       if (hd->ioc->spi_data.nvram) {
27639 +                               data = hd->ioc->spi_data.nvram[id];
27640  
27641                                 if (dv->now.width)
27642                                         data &= ~MPT_NVRAM_WIDE_DISABLE;
27643 @@ -6260,14 +6151,13 @@ mptscsih_dv_parms(MPT_SCSI_HOST *hd, DVP
27644                                 data &= ~MPT_NVRAM_SYNC_MASK;
27645                                 data |= (dv->now.factor << MPT_NVRAM_SYNC_SHIFT) & MPT_NVRAM_SYNC_MASK;
27646  
27647 -                               ioc->spi_data.nvram[id] = data;
27648 +                               hd->ioc->spi_data.nvram[id] = data;
27649                         }
27650                 }
27651                 break;
27652         }
27653  }
27654  
27655 -
27656  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
27657  /*     mptscsih_fillbuf - fill a buffer with a special data pattern
27658   *             cleanup. For bus scan only.
27659 @@ -6422,11 +6312,10 @@ EXPORT_SYMBOL(mptscsih_taskmgmt_complete
27660  EXPORT_SYMBOL(mptscsih_scandv_complete);
27661  EXPORT_SYMBOL(mptscsih_event_process);
27662  EXPORT_SYMBOL(mptscsih_ioc_reset);
27663 -EXPORT_SYMBOL(mptscsih_InternalCmdTimer_expired);
27664 +EXPORT_SYMBOL(mptscsih_timer_expired);
27665  EXPORT_SYMBOL(mptscsih_readFCDevicePage0);
27666  EXPORT_SYMBOL(mptscsih_change_queue_depth);
27667  EXPORT_SYMBOL(mptscsih_TMHandler);
27668 -EXPORT_SYMBOL(mptscsih_TM_timeout);
27669  EXPORT_SYMBOL(mptscsih_sanity_check);
27670  EXPORT_SYMBOL(mptscsih_poll);
27671  EXPORT_SYMBOL(mptscsih_do_cmd);
27672 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptscsih.h linux-2.6.9-55.0.12/drivers/message/fusion/mptscsih.h
27673 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptscsih.h        2007-12-21 11:40:54.000000000 +0100
27674 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptscsih.h       2007-11-02 09:10:23.000000000 +0100
27675 @@ -5,8 +5,8 @@
27676   *          LSIFC9xx/LSI409xx Fibre Channel
27677   *      running LSI Logic Fusion MPT (Message Passing Technology) firmware.
27678   *
27679 - *  Copyright (c) 1999-2007 LSI Logic Corporation
27680 - *  (mailto:mpt_linux_developer@lsi.com)
27681 + *  Copyright (c) 1999-2005 LSI Logic Corporation
27682 + *  (mailto:mpt_linux_developer@lsil.com)
27683   *
27684   *  $Id: mptscsih.h,v 1.1.2.2 2003/05/07 14:08:35 Exp $
27685   */
27686 @@ -54,17 +54,7 @@
27687   *     SCSI Public stuff...
27688   */
27689  
27690 -#define MPT_SCANDV_GOOD                        (0x00000000) /* must be 0 */
27691 -#define MPT_SCANDV_DID_RESET           (0x00000001)
27692 -#define MPT_SCANDV_SENSE               (0x00000002)
27693 -#define MPT_SCANDV_SOME_ERROR          (0x00000004)
27694 -#define MPT_SCANDV_SELECTION_TIMEOUT   (0x00000008)
27695 -#define MPT_SCANDV_ISSUE_SENSE         (0x00000010)
27696 -#define MPT_SCANDV_FALLBACK            (0x00000020)
27697 -#define MPT_SCANDV_BUSY                        (0x00000040)
27698 -
27699 -//#define MPT_SCSI_CMD_PER_DEV_HIGH    64
27700 -#define MPT_SCSI_CMD_PER_DEV_HIGH      48
27701 +#define MPT_SCSI_CMD_PER_DEV_HIGH      64
27702  #define MPT_SCSI_CMD_PER_DEV_LOW       32
27703  
27704  #define MPT_SCSI_CMD_PER_LUN           7
27705 @@ -133,7 +123,7 @@ extern int mptscsih_taskmgmt_complete(MP
27706  extern int mptscsih_scandv_complete(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, MPT_FRAME_HDR *r);
27707  extern int mptscsih_event_process(MPT_ADAPTER *ioc, EventNotificationReply_t *pEvReply);
27708  extern int mptscsih_ioc_reset(MPT_ADAPTER *ioc, int post_reset);
27709 -extern void mptscsih_InternalCmdTimer_expired(unsigned long data);
27710 +extern void mptscsih_timer_expired(unsigned long data);
27711  extern int mptscsih_readFCDevicePage0(MPT_ADAPTER *ioc, u8 bus, u8 targetId, pFCDevicePage0_t fcDevicePage);
27712  extern void mptscsih_hot_plug_worker_thread(void * arg);
27713  extern int mptscsih_TMHandler(MPT_SCSI_HOST *hd, u8 type, u8 channel, u8 target, u8 lun, int ctx2abort, ulong timeout);
27714 @@ -141,4 +131,4 @@ extern int mptscsih_change_queue_depth(s
27715  extern int mptscsih_do_cmd(MPT_SCSI_HOST *hd, INTERNAL_CMD *iocmd);
27716  extern int mptscsih_sanity_check(struct scsi_device *sdev);
27717  extern void mptscsih_poll(struct scsi_device *sdev);
27718 -extern void scsi_print_command(struct scsi_cmnd *cmd);
27719 +extern void scsi_print_command(struct scsi_cmnd *cmd);
27720 \ Pas de fin de ligne Ã  la fin du fichier.
27721 diff -Nrup linux-2.6.9-67.0.1/drivers/message/fusion/mptspi.c linux-2.6.9-55.0.12/drivers/message/fusion/mptspi.c
27722 --- linux-2.6.9-67.0.1/drivers/message/fusion/mptspi.c  2007-12-21 11:40:54.000000000 +0100
27723 +++ linux-2.6.9-55.0.12/drivers/message/fusion/mptspi.c 2007-11-02 09:10:23.000000000 +0100
27724 @@ -3,8 +3,8 @@
27725   *      For use with LSI Logic PCI chip/adapter(s)
27726   *      running LSI Logic Fusion MPT (Message Passing Technology) firmware.
27727   *
27728 - *  Copyright (c) 1999-2007 LSI Logic Corporation
27729 - *  (mailto:mpt_linux_developer@lsi.com)
27730 + *  Copyright (c) 1999-2005 LSI Logic Corporation
27731 + *  (mailto:mpt_linux_developer@lsil.com)
27732   *
27733   */
27734  /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
27735 @@ -73,7 +73,6 @@
27736  MODULE_AUTHOR(MODULEAUTHOR);
27737  MODULE_DESCRIPTION(my_NAME);
27738  MODULE_LICENSE("GPL");
27739 -MODULE_VERSION(my_VERSION);
27740  
27741  /* Command line args */
27742  #ifdef MPTSCSIH_ENABLE_DOMAIN_VALIDATION
27743 @@ -146,13 +145,12 @@ static struct scsi_host_template mptspi_
27744         .change_queue_depth             = mptscsih_change_queue_depth,
27745  #endif
27746         .eh_abort_handler               = mptscsih_abort,
27747 -        .eh_device_reset_handler        = mptscsih_dev_reset,
27748         .eh_bus_reset_handler           = mptscsih_bus_reset,
27749         .eh_host_reset_handler          = mptscsih_host_reset,
27750         .bios_param                     = mptscsih_bios_param,
27751         .can_queue                      = MPT_SCSI_CAN_QUEUE,
27752         .this_id                        = -1,
27753 -       .sg_tablesize                   = CONFIG_FUSION_MAX_SGE,
27754 +       .sg_tablesize                   = MPT_SCSI_SG_DEPTH,
27755         .max_sectors                    = 8192,
27756         .cmd_per_lun                    = 7,
27757         .use_clustering                 = ENABLE_CLUSTERING,
27758 @@ -191,6 +189,8 @@ mptspi_probe(struct pci_dev *pdev, const
27759         MPT_ADAPTER             *ioc;
27760         unsigned long            flags;
27761         int                      sz, ii;
27762 +       int                      numSGE = 0;
27763 +       int                      scale;
27764         int                      ioc_cap;
27765         u8                      *mem;
27766         int                     error=0;
27767 @@ -269,7 +269,7 @@ mptspi_probe(struct pci_dev *pdev, const
27768                 ioc->name, mpt_can_queue, ioc->req_depth,
27769                 sh->can_queue));
27770  
27771 -       sh->max_id = ioc->DevicesPerBus;
27772 +       sh->max_id = MPT_MAX_SCSI_DEVICES;
27773  
27774         sh->max_lun = MPT_LAST_LUN + 1;
27775         sh->max_channel = 0;
27776 @@ -278,7 +278,36 @@ mptspi_probe(struct pci_dev *pdev, const
27777         /* Required entry.
27778          */
27779         sh->unique_id = ioc->id;
27780 -       sh->sg_tablesize = ioc->sg_tablesize;
27781 +
27782 +       /* Verify that we won't exceed the maximum
27783 +        * number of chain buffers
27784 +        * We can optimize:  ZZ = req_sz/sizeof(SGE)
27785 +        * For 32bit SGE's:
27786 +        *  numSGE = 1 + (ZZ-1)*(maxChain -1) + ZZ
27787 +        *               + (req_sz - 64)/sizeof(SGE)
27788 +        * A slightly different algorithm is required for
27789 +        * 64bit SGEs.
27790 +        */
27791 +       scale = ioc->req_sz/(sizeof(dma_addr_t) + sizeof(u32));
27792 +       if (sizeof(dma_addr_t) == sizeof(u64)) {
27793 +               numSGE = (scale - 1) *
27794 +                 (ioc->facts.MaxChainDepth-1) + scale +
27795 +                 (ioc->req_sz - 60) / (sizeof(dma_addr_t) +
27796 +                 sizeof(u32));
27797 +       } else {
27798 +               numSGE = 1 + (scale - 1) *
27799 +                 (ioc->facts.MaxChainDepth-1) + scale +
27800 +                 (ioc->req_sz - 64) / (sizeof(dma_addr_t) +
27801 +                 sizeof(u32));
27802 +       }
27803 +
27804 +       if (numSGE < sh->sg_tablesize) {
27805 +               /* Reset this value */
27806 +               dprintk((MYIOC_s_INFO_FMT
27807 +                 "Resetting sg_tablesize to %d from %d\n",
27808 +                 ioc->name, numSGE, sh->sg_tablesize));
27809 +               sh->sg_tablesize = numSGE;
27810 +       }
27811  
27812  #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,13))
27813         /* Set the pci device pointer in Scsi_Host structure.
27814 @@ -307,29 +336,29 @@ mptspi_probe(struct pci_dev *pdev, const
27815         dprintk((MYIOC_s_INFO_FMT "ScsiLookup @ %p, sz=%d\n",
27816                  ioc->name, hd->ScsiLookup, sz));
27817  
27818 -       for (ii=0; ii < ioc->NumberOfBuses; ii++) {
27819 -               /* Allocate memory for the device structures.
27820 -                * A non-Null pointer at an offset
27821 -                * indicates a device exists.
27822 -                */
27823 -               sz = ioc->DevicesPerBus * sizeof(void *);
27824 -               mem = kmalloc(sz, GFP_ATOMIC);
27825 -               if (mem == NULL) {
27826 -                       error = -ENOMEM;
27827 -                       goto out_mptspi_probe;
27828 -               }
27829 +       /* Allocate memory for the device structures.
27830 +        * A non-Null pointer at an offset
27831 +        * indicates a device exists.
27832 +        * max_id = 1 + maximum id (hosts.h)
27833 +        */
27834 +       sz = sh->max_id * sizeof(void *);
27835 +       mem = kmalloc(sz, GFP_ATOMIC);
27836 +       if (mem == NULL) {
27837 +               error = -ENOMEM;
27838 +               goto out_mptspi_probe;
27839 +       }
27840  
27841 -               memset(mem, 0, sz);
27842 -               ioc->Target_List[ii] = (struct _MPT_DEVICE *) mem;
27843 +       memset(mem, 0, sz);
27844 +       hd->Targets = (VirtDevice **) mem;
27845  
27846 -               dinitprintk((KERN_INFO
27847 -                 " For Bus=%d, Target_List=%p sz=%d\n", ii, mem, sz));
27848 -       }
27849 +       dprintk((KERN_INFO
27850 +         "  Targets @ %p, sz=%d\n", hd->Targets, sz));
27851  
27852         /* Clear the TM flags
27853          */
27854         hd->tmPending = 0;
27855         hd->tmState = TM_STATE_NONE;
27856 +       hd->resetPending = 0;
27857         hd->abortSCpnt = NULL;
27858  
27859         /* Clear the pointer used to store
27860 @@ -339,21 +368,16 @@ mptspi_probe(struct pci_dev *pdev, const
27861          */
27862         hd->cmdPtr = NULL;
27863  
27864 -       /* Initialize this IOC's  timers
27865 +       /* Initialize this SCSI Hosts' timers
27866          * To use, set the timer expires field
27867 -        * and add_timer.Used for internally
27868 -         * generated commands.
27869 +        * and add_timer
27870          */
27871 -       init_timer(&hd->InternalCmdTimer);
27872 -       hd->InternalCmdTimer.data = (unsigned long) hd;
27873 -       hd->InternalCmdTimer.function = mptscsih_InternalCmdTimer_expired;
27874 -
27875 -       init_timer(&ioc->TMtimer);
27876 -       ioc->TMtimer.data = (unsigned long) ioc;
27877 -       ioc->TMtimer.function = mptscsih_TM_timeout;
27878 +       init_timer(&hd->timer);
27879 +       hd->timer.data = (unsigned long) hd;
27880 +       hd->timer.function = mptscsih_timer_expired;
27881  
27882 -       ioc->spi_data.Saf_Te = mpt_saf_te;
27883 -       hd->mpt_pq_filter = mpt_pq_filter;
27884 +       ioc->spi_data.Saf_Te = mpt_saf_te;
27885 +       hd->mpt_pq_filter = mpt_pq_filter;
27886  
27887  #ifdef MPTSCSIH_ENABLE_DOMAIN_VALIDATION
27888         if (ioc->spi_data.maxBusWidth > mpt_width)
27889 @@ -364,6 +388,7 @@ mptspi_probe(struct pci_dev *pdev, const
27890                 ioc->spi_data.maxSyncOffset = 0;
27891         }
27892         ioc->spi_data.mpt_dv = mpt_dv;
27893 +       hd->negoNvram = 0;
27894  
27895         ddvprintk((MYIOC_s_INFO_FMT
27896                 "dv %x width %x factor %x saf_te %x mpt_pq_filter %x\n",
27897 @@ -374,7 +399,7 @@ mptspi_probe(struct pci_dev *pdev, const
27898                 mpt_saf_te,
27899                 mpt_pq_filter));
27900  #else
27901 -
27902 +       hd->negoNvram = MPT_SCSICFG_USE_NVRAM;
27903         ddvprintk((MYIOC_s_INFO_FMT
27904                 "saf_te %x mpt_pq_filter %x\n",
27905                 ioc->name,
27906 @@ -387,18 +412,18 @@ mptspi_probe(struct pci_dev *pdev, const
27907                 ioc->spi_data.noQas |= MPT_TARGET_NO_NEGO_QAS;
27908         else
27909                 ioc->spi_data.noQas = 0;
27910 -/* enable domain validation flags */
27911  
27912         for (ii=0; ii < MPT_MAX_SCSI_DEVICES; ii++)
27913 -ioc->spi_data.dvStatus[ii] =
27914 +               ioc->spi_data.dvStatus[ii] =
27915 +                 MPT_SCSICFG_NEGOTIATE;
27916  
27917 -(MPT_SCSICFG_NEGOTIATE | MPT_SCSICFG_DV_NOT_DONE);
27918 +       for (ii=0; ii < MPT_MAX_SCSI_DEVICES; ii++)
27919 +               ioc->spi_data.dvStatus[ii] |=
27920 +                 MPT_SCSICFG_DV_NOT_DONE;
27921  
27922         init_waitqueue_head(&hd->scandv_waitq);
27923         hd->scandv_wait_done = 0;
27924         hd->last_queue_full = 0;
27925 -        init_waitqueue_head(&hd->TM_waitq);
27926 -        hd->TM_wait_done = 0;
27927  
27928         error = scsi_add_host (sh, &ioc->pcidev->dev);
27929         if(error) {
27930 @@ -414,10 +439,6 @@ ioc->spi_data.dvStatus[ii] =
27931                     0, 0, 0, 0, 5 /* 5 second timeout */);
27932         }
27933  
27934 -       dnegoprintk((MYIOC_s_WARN_FMT "%s: writeSDP1: ALL_IDS\n",
27935 -               ioc->name, __FUNCTION__));
27936 -       mpt_writeSDP1(ioc, 0, 0, MPT_SCSICFG_ALL_IDS);
27937 -
27938         scsi_scan_host(sh);
27939         return 0;
27940  
27941 @@ -464,7 +485,7 @@ mptspi_init(void)
27942  
27943         if (mpt_event_register(mptspiDoneCtx, mptscsih_event_process) == 0) {
27944                 devtprintk((KERN_INFO MYNAM
27945 -        ": Registered for IOC event notifications mptspiDoneCtx=%08x\n", mptspiDoneCtx));
27946 +                 ": Registered for IOC event notifications\n"));
27947         }
27948  
27949         if (mpt_reset_register(mptspiDoneCtx, mptscsih_ioc_reset) == 0) {