]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - sys/dev/arcmsr/arcmsr.c
Import lib9p 9d5aee77bcc1bf0e79b0a3bfefff5fdf2146283c.
[FreeBSD/FreeBSD.git] / sys / dev / arcmsr / arcmsr.c
1 /*
2 ********************************************************************************
3 **        OS    : FreeBSD
4 **   FILE NAME  : arcmsr.c
5 **        BY    : Erich Chen, Ching Huang
6 **   Description: SCSI RAID Device Driver for 
7 **                ARECA (ARC11XX/ARC12XX/ARC13XX/ARC16XX/ARC188x)
8 **                SATA/SAS RAID HOST Adapter
9 ********************************************************************************
10 ********************************************************************************
11 **
12 ** SPDX-License-Identifier: BSD-3-Clause
13 **
14 ** Copyright (C) 2002 - 2012, Areca Technology Corporation All rights reserved.
15 **
16 ** Redistribution and use in source and binary forms, with or without
17 ** modification, are permitted provided that the following conditions
18 ** are met:
19 ** 1. Redistributions of source code must retain the above copyright
20 **    notice, this list of conditions and the following disclaimer.
21 ** 2. Redistributions in binary form must reproduce the above copyright
22 **    notice, this list of conditions and the following disclaimer in the
23 **    documentation and/or other materials provided with the distribution.
24 ** 3. The name of the author may not be used to endorse or promote products
25 **    derived from this software without specific prior written permission.
26 **
27 ** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
28 ** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
29 ** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
30 ** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 
31 ** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES(INCLUDING, BUT
32 ** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 
33 ** DATA, OR PROFITS; OR BUSINESS INTERRUPTION)HOWEVER CAUSED AND ON ANY
34 ** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
35 **(INCLUDING NEGLIGENCE OR OTHERWISE)ARISING IN ANY WAY OUT OF THE USE OF
36 ** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
37 ********************************************************************************
38 ** History
39 **
40 **    REV#         DATE         NAME        DESCRIPTION
41 ** 1.00.00.00   03/31/2004  Erich Chen      First release
42 ** 1.20.00.02   11/29/2004  Erich Chen      bug fix with arcmsr_bus_reset when PHY error
43 ** 1.20.00.03   04/19/2005  Erich Chen      add SATA 24 Ports adapter type support
44 **                                          clean unused function
45 ** 1.20.00.12   09/12/2005  Erich Chen      bug fix with abort command handling, 
46 **                                          firmware version check 
47 **                                          and firmware update notify for hardware bug fix
48 **                                          handling if none zero high part physical address 
49 **                                          of srb resource 
50 ** 1.20.00.13   08/18/2006  Erich Chen      remove pending srb and report busy
51 **                                          add iop message xfer 
52 **                                          with scsi pass-through command
53 **                                          add new device id of sas raid adapters 
54 **                                          code fit for SPARC64 & PPC 
55 ** 1.20.00.14   02/05/2007  Erich Chen      bug fix for incorrect ccb_h.status report
56 **                                          and cause g_vfs_done() read write error
57 ** 1.20.00.15   10/10/2007  Erich Chen      support new RAID adapter type ARC120x
58 ** 1.20.00.16   10/10/2009  Erich Chen      Bug fix for RAID adapter type ARC120x
59 **                                          bus_dmamem_alloc() with BUS_DMA_ZERO
60 ** 1.20.00.17   07/15/2010  Ching Huang     Added support ARC1880
61 **                                          report CAM_DEV_NOT_THERE instead of CAM_SEL_TIMEOUT when device failed,
62 **                                          prevent cam_periph_error removing all LUN devices of one Target id
63 **                                          for any one LUN device failed
64 ** 1.20.00.18   10/14/2010  Ching Huang     Fixed "inquiry data fails comparion at DV1 step"
65 **              10/25/2010  Ching Huang     Fixed bad range input in bus_alloc_resource for ADAPTER_TYPE_B
66 ** 1.20.00.19   11/11/2010  Ching Huang     Fixed arcmsr driver prevent arcsas support for Areca SAS HBA ARC13x0
67 ** 1.20.00.20   12/08/2010  Ching Huang     Avoid calling atomic_set_int function
68 ** 1.20.00.21   02/08/2011  Ching Huang     Implement I/O request timeout
69 **              02/14/2011  Ching Huang     Modified pktRequestCount
70 ** 1.20.00.21   03/03/2011  Ching Huang     if a command timeout, then wait its ccb back before free it
71 ** 1.20.00.22   07/04/2011  Ching Huang     Fixed multiple MTX panic
72 ** 1.20.00.23   10/28/2011  Ching Huang     Added TIMEOUT_DELAY in case of too many HDDs need to start 
73 ** 1.20.00.23   11/08/2011  Ching Huang     Added report device transfer speed 
74 ** 1.20.00.23   01/30/2012  Ching Huang     Fixed Request requeued and Retrying command
75 ** 1.20.00.24   06/11/2012  Ching Huang     Fixed return sense data condition
76 ** 1.20.00.25   08/17/2012  Ching Huang     Fixed hotplug device no function on type A adapter
77 ** 1.20.00.26   12/14/2012  Ching Huang     Added support ARC1214,1224,1264,1284
78 ** 1.20.00.27   05/06/2013  Ching Huang     Fixed out standing cmd full on ARC-12x4
79 ** 1.20.00.28   09/13/2013  Ching Huang     Removed recursive mutex in arcmsr_abort_dr_ccbs
80 ** 1.20.00.29   12/18/2013  Ching Huang     Change simq allocation number, support ARC1883
81 ** 1.30.00.00   11/30/2015  Ching Huang     Added support ARC1203
82 ** 1.40.00.00   07/11/2017  Ching Huang     Added support ARC1884
83 ** 1.40.00.01   10/30/2017  Ching Huang     Fixed release memory resource
84 ******************************************************************************************
85 */
86
87 #include <sys/cdefs.h>
88 __FBSDID("$FreeBSD$");
89
90 #if 0
91 #define ARCMSR_DEBUG1                   1
92 #endif
93 #include <sys/param.h>
94 #include <sys/systm.h>
95 #include <sys/malloc.h>
96 #include <sys/kernel.h>
97 #include <sys/bus.h>
98 #include <sys/queue.h>
99 #include <sys/stat.h>
100 #include <sys/devicestat.h>
101 #include <sys/kthread.h>
102 #include <sys/module.h>
103 #include <sys/proc.h>
104 #include <sys/lock.h>
105 #include <sys/sysctl.h>
106 #include <sys/poll.h>
107 #include <sys/ioccom.h>
108 #include <vm/vm.h>
109 #include <vm/vm_param.h>
110 #include <vm/pmap.h>
111
112 #include <isa/rtc.h>
113
114 #include <machine/bus.h>
115 #include <machine/resource.h>
116 #include <machine/atomic.h>
117 #include <sys/conf.h>
118 #include <sys/rman.h>
119
120 #include <cam/cam.h>
121 #include <cam/cam_ccb.h>
122 #include <cam/cam_sim.h>
123 #include <cam/cam_periph.h>
124 #include <cam/cam_xpt_periph.h>
125 #include <cam/cam_xpt_sim.h>
126 #include <cam/cam_debug.h>
127 #include <cam/scsi/scsi_all.h>
128 #include <cam/scsi/scsi_message.h>
129 /*
130 **************************************************************************
131 **************************************************************************
132 */
133 #include <sys/selinfo.h>
134 #include <sys/mutex.h>
135 #include <sys/endian.h>
136 #include <dev/pci/pcivar.h>
137 #include <dev/pci/pcireg.h>
138
139 #define arcmsr_callout_init(a)  callout_init(a, /*mpsafe*/1);
140
141 #define ARCMSR_DRIVER_VERSION   "arcmsr version 1.40.00.01 2017-10-30"
142 #include <dev/arcmsr/arcmsr.h>
143 /*
144 **************************************************************************
145 **************************************************************************
146 */
147 static void arcmsr_free_srb(struct CommandControlBlock *srb);
148 static struct CommandControlBlock *arcmsr_get_freesrb(struct AdapterControlBlock *acb);
149 static u_int8_t arcmsr_seek_cmd2abort(union ccb *abortccb);
150 static int arcmsr_probe(device_t dev);
151 static int arcmsr_attach(device_t dev);
152 static int arcmsr_detach(device_t dev);
153 static u_int32_t arcmsr_iop_ioctlcmd(struct AdapterControlBlock *acb, u_int32_t ioctl_cmd, caddr_t arg);
154 static void arcmsr_iop_parking(struct AdapterControlBlock *acb);
155 static int arcmsr_shutdown(device_t dev);
156 static void arcmsr_interrupt(struct AdapterControlBlock *acb);
157 static void arcmsr_polling_srbdone(struct AdapterControlBlock *acb, struct CommandControlBlock *poll_srb);
158 static void arcmsr_free_resource(struct AdapterControlBlock *acb);
159 static void arcmsr_bus_reset(struct AdapterControlBlock *acb);
160 static void arcmsr_stop_adapter_bgrb(struct AdapterControlBlock *acb);
161 static void arcmsr_start_adapter_bgrb(struct AdapterControlBlock *acb);
162 static void arcmsr_iop_init(struct AdapterControlBlock *acb);
163 static void arcmsr_flush_adapter_cache(struct AdapterControlBlock *acb);
164 static u_int32_t arcmsr_Read_iop_rqbuffer_data(struct AdapterControlBlock *acb, struct QBUFFER *prbuffer);
165 static void arcmsr_Write_data_2iop_wqbuffer(struct AdapterControlBlock *acb);
166 static void arcmsr_abort_allcmd(struct AdapterControlBlock *acb);
167 static void arcmsr_srb_complete(struct CommandControlBlock *srb, int stand_flag);
168 static void arcmsr_iop_reset(struct AdapterControlBlock *acb);
169 static void arcmsr_report_sense_info(struct CommandControlBlock *srb);
170 static void arcmsr_build_srb(struct CommandControlBlock *srb, bus_dma_segment_t *dm_segs, u_int32_t nseg);
171 static int arcmsr_iop_message_xfer(struct AdapterControlBlock *acb, union ccb *pccb);
172 static int arcmsr_resume(device_t dev);
173 static int arcmsr_suspend(device_t dev);
174 static void arcmsr_rescanLun_cb(struct cam_periph *periph, union ccb *ccb);
175 static void arcmsr_polling_devmap(void *arg);
176 static void arcmsr_srb_timeout(void *arg);
177 static void arcmsr_hbd_postqueue_isr(struct AdapterControlBlock *acb);
178 static void arcmsr_hbe_postqueue_isr(struct AdapterControlBlock *acb);
179 static void arcmsr_teardown_intr(device_t dev, struct AdapterControlBlock *acb);
180 #ifdef ARCMSR_DEBUG1
181 static void arcmsr_dump_data(struct AdapterControlBlock *acb);
182 #endif
183 /*
184 **************************************************************************
185 **************************************************************************
186 */
187 static void UDELAY(u_int32_t us) { DELAY(us); }
188 /*
189 **************************************************************************
190 **************************************************************************
191 */
192 static bus_dmamap_callback_t arcmsr_map_free_srb;
193 static bus_dmamap_callback_t arcmsr_execute_srb;
194 /*
195 **************************************************************************
196 **************************************************************************
197 */
198 static d_open_t arcmsr_open;
199 static d_close_t arcmsr_close;
200 static d_ioctl_t arcmsr_ioctl;
201
202 static device_method_t arcmsr_methods[]={
203         DEVMETHOD(device_probe,         arcmsr_probe),
204         DEVMETHOD(device_attach,        arcmsr_attach),
205         DEVMETHOD(device_detach,        arcmsr_detach),
206         DEVMETHOD(device_shutdown,      arcmsr_shutdown),
207         DEVMETHOD(device_suspend,       arcmsr_suspend),
208         DEVMETHOD(device_resume,        arcmsr_resume),
209         DEVMETHOD_END
210 };
211
212 static driver_t arcmsr_driver={
213         "arcmsr", arcmsr_methods, sizeof(struct AdapterControlBlock)
214 };
215
216 static devclass_t arcmsr_devclass;
217 DRIVER_MODULE(arcmsr, pci, arcmsr_driver, arcmsr_devclass, 0, 0);
218 MODULE_DEPEND(arcmsr, pci, 1, 1, 1);
219 MODULE_DEPEND(arcmsr, cam, 1, 1, 1);
220 #ifndef BUS_DMA_COHERENT                
221         #define BUS_DMA_COHERENT        0x04    /* hint: map memory in a coherent way */
222 #endif
223 static struct cdevsw arcmsr_cdevsw={
224                 .d_version = D_VERSION, 
225                 .d_open    = arcmsr_open,       /* open     */
226                 .d_close   = arcmsr_close,      /* close    */
227                 .d_ioctl   = arcmsr_ioctl,      /* ioctl    */
228                 .d_name    = "arcmsr",          /* name     */
229         };
230 /*
231 **************************************************************************
232 **************************************************************************
233 */
234 static int arcmsr_open(struct cdev *dev, int flags, int fmt, struct thread *proc)
235 {
236         int     unit = dev2unit(dev);
237         struct AdapterControlBlock *acb = devclass_get_softc(arcmsr_devclass, unit);
238
239         if (acb == NULL) {
240                 return ENXIO;
241         }
242         return (0);
243 }
244 /*
245 **************************************************************************
246 **************************************************************************
247 */
248 static int arcmsr_close(struct cdev *dev, int flags, int fmt, struct thread *proc)
249 {
250         int     unit = dev2unit(dev);
251         struct AdapterControlBlock *acb = devclass_get_softc(arcmsr_devclass, unit);
252
253         if (acb == NULL) {
254                 return ENXIO;
255         }
256         return 0;
257 }
258 /*
259 **************************************************************************
260 **************************************************************************
261 */
262 static int arcmsr_ioctl(struct cdev *dev, u_long ioctl_cmd, caddr_t arg, int flags, struct thread *proc)
263 {
264         int     unit = dev2unit(dev);
265         struct AdapterControlBlock *acb = devclass_get_softc(arcmsr_devclass, unit);
266
267         if (acb == NULL) {
268                 return ENXIO;
269         }
270         return (arcmsr_iop_ioctlcmd(acb, ioctl_cmd, arg));
271 }
272 /*
273 **********************************************************************
274 **********************************************************************
275 */
276 static u_int32_t arcmsr_disable_allintr( struct AdapterControlBlock *acb)
277 {
278         u_int32_t intmask_org = 0;
279
280         switch (acb->adapter_type) {
281         case ACB_ADAPTER_TYPE_A: {
282                         /* disable all outbound interrupt */
283                         intmask_org = CHIP_REG_READ32(HBA_MessageUnit, 0, outbound_intmask); /* disable outbound message0 int */
284                         CHIP_REG_WRITE32(HBA_MessageUnit, 0, outbound_intmask, intmask_org|ARCMSR_MU_OUTBOUND_ALL_INTMASKENABLE);
285                 }
286                 break;
287         case ACB_ADAPTER_TYPE_B: {
288                         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
289                         /* disable all outbound interrupt */
290                         intmask_org = READ_CHIP_REG32(0, phbbmu->iop2drv_doorbell_mask)
291                                                 & (~ARCMSR_IOP2DRV_MESSAGE_CMD_DONE); /* disable outbound message0 int */
292                         WRITE_CHIP_REG32(0, phbbmu->iop2drv_doorbell_mask, 0); /* disable all interrupt */
293                 }
294                 break;
295         case ACB_ADAPTER_TYPE_C: {
296                         /* disable all outbound interrupt */
297                         intmask_org = CHIP_REG_READ32(HBC_MessageUnit, 0, host_int_mask)        ; /* disable outbound message0 int */
298                         CHIP_REG_WRITE32(HBC_MessageUnit, 0, host_int_mask, intmask_org|ARCMSR_HBCMU_ALL_INTMASKENABLE);
299                 }
300                 break;
301         case ACB_ADAPTER_TYPE_D: {
302                         /* disable all outbound interrupt */
303                         intmask_org = CHIP_REG_READ32(HBD_MessageUnit, 0, pcief0_int_enable)    ; /* disable outbound message0 int */
304                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, pcief0_int_enable, ARCMSR_HBDMU_ALL_INT_DISABLE);
305                 }
306                 break;
307         case ACB_ADAPTER_TYPE_E: {
308                         /* disable all outbound interrupt */
309                         intmask_org = CHIP_REG_READ32(HBC_MessageUnit, 0, host_int_mask)        ; /* disable outbound message0 int */
310                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, host_int_mask, intmask_org | ARCMSR_HBEMU_ALL_INTMASKENABLE);
311                 }
312                 break;
313         }
314         return (intmask_org);
315 }
316 /*
317 **********************************************************************
318 **********************************************************************
319 */
320 static void arcmsr_enable_allintr( struct AdapterControlBlock *acb, u_int32_t intmask_org)
321 {
322         u_int32_t mask;
323
324         switch (acb->adapter_type) {
325         case ACB_ADAPTER_TYPE_A: {
326                         /* enable outbound Post Queue, outbound doorbell Interrupt */
327                         mask = ~(ARCMSR_MU_OUTBOUND_POSTQUEUE_INTMASKENABLE|ARCMSR_MU_OUTBOUND_DOORBELL_INTMASKENABLE|ARCMSR_MU_OUTBOUND_MESSAGE0_INTMASKENABLE);
328                         CHIP_REG_WRITE32(HBA_MessageUnit, 0, outbound_intmask, intmask_org & mask);
329                         acb->outbound_int_enable = ~(intmask_org & mask) & 0x000000ff;
330                 }
331                 break;
332         case ACB_ADAPTER_TYPE_B: {
333                         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
334                         /* enable ARCMSR_IOP2DRV_MESSAGE_CMD_DONE */
335                         mask = (ARCMSR_IOP2DRV_DATA_WRITE_OK|ARCMSR_IOP2DRV_DATA_READ_OK|ARCMSR_IOP2DRV_CDB_DONE|ARCMSR_IOP2DRV_MESSAGE_CMD_DONE);
336                         WRITE_CHIP_REG32(0, phbbmu->iop2drv_doorbell_mask, intmask_org | mask); /*1=interrupt enable, 0=interrupt disable*/
337                         acb->outbound_int_enable = (intmask_org | mask) & 0x0000000f;
338                 }
339                 break;
340         case ACB_ADAPTER_TYPE_C: {
341                         /* enable outbound Post Queue, outbound doorbell Interrupt */
342                         mask = ~(ARCMSR_HBCMU_UTILITY_A_ISR_MASK | ARCMSR_HBCMU_OUTBOUND_DOORBELL_ISR_MASK | ARCMSR_HBCMU_OUTBOUND_POSTQUEUE_ISR_MASK);
343                         CHIP_REG_WRITE32(HBC_MessageUnit, 0, host_int_mask, intmask_org & mask);
344                         acb->outbound_int_enable = ~(intmask_org & mask) & 0x0000000f;
345                 }
346                 break;
347         case ACB_ADAPTER_TYPE_D: {
348                         /* enable outbound Post Queue, outbound doorbell Interrupt */
349                         mask = ARCMSR_HBDMU_ALL_INT_ENABLE;
350                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, pcief0_int_enable, intmask_org | mask);
351                         CHIP_REG_READ32(HBD_MessageUnit, 0, pcief0_int_enable);
352                         acb->outbound_int_enable = mask;
353                 }
354                 break;
355         case ACB_ADAPTER_TYPE_E: {
356                         /* enable outbound Post Queue, outbound doorbell Interrupt */
357                         mask = ~(ARCMSR_HBEMU_OUTBOUND_DOORBELL_ISR | ARCMSR_HBEMU_OUTBOUND_POSTQUEUE_ISR);
358                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, host_int_mask, intmask_org & mask);
359                         acb->outbound_int_enable = ~(intmask_org & mask) & 0x0000000f;
360                 }
361                 break;
362         }
363 }
364 /*
365 **********************************************************************
366 **********************************************************************
367 */
368 static u_int8_t arcmsr_hba_wait_msgint_ready(struct AdapterControlBlock *acb)
369 {
370         u_int32_t Index;
371         u_int8_t Retries = 0x00;
372
373         do {
374                 for(Index=0; Index < 100; Index++) {
375                         if(CHIP_REG_READ32(HBA_MessageUnit, 0, outbound_intstatus) & ARCMSR_MU_OUTBOUND_MESSAGE0_INT) {
376                                 CHIP_REG_WRITE32(HBA_MessageUnit, 0, outbound_intstatus, ARCMSR_MU_OUTBOUND_MESSAGE0_INT);/*clear interrupt*/
377                                 return TRUE;
378                         }
379                         UDELAY(10000);
380                 }/*max 1 seconds*/
381         }while(Retries++ < 20);/*max 20 sec*/
382         return (FALSE);
383 }
384 /*
385 **********************************************************************
386 **********************************************************************
387 */
388 static u_int8_t arcmsr_hbb_wait_msgint_ready(struct AdapterControlBlock *acb)
389 {
390         u_int32_t Index;
391         u_int8_t Retries = 0x00;
392         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
393
394         do {
395                 for(Index=0; Index < 100; Index++) {
396                         if(READ_CHIP_REG32(0, phbbmu->iop2drv_doorbell) & ARCMSR_IOP2DRV_MESSAGE_CMD_DONE) {
397                                 WRITE_CHIP_REG32(0, phbbmu->iop2drv_doorbell, ARCMSR_MESSAGE_INT_CLEAR_PATTERN);/*clear interrupt*/
398                                 WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_DRV2IOP_END_OF_INTERRUPT);
399                                 return TRUE;
400                         }
401                         UDELAY(10000);
402                 }/*max 1 seconds*/
403         }while(Retries++ < 20);/*max 20 sec*/
404         return (FALSE);
405 }
406 /*
407 **********************************************************************
408 **********************************************************************
409 */
410 static u_int8_t arcmsr_hbc_wait_msgint_ready(struct AdapterControlBlock *acb)
411 {
412         u_int32_t Index;
413         u_int8_t Retries = 0x00;
414
415         do {
416                 for(Index=0; Index < 100; Index++) {
417                         if(CHIP_REG_READ32(HBC_MessageUnit, 0, outbound_doorbell) & ARCMSR_HBCMU_IOP2DRV_MESSAGE_CMD_DONE) {
418                                 CHIP_REG_WRITE32(HBC_MessageUnit, 0, outbound_doorbell_clear, ARCMSR_HBCMU_IOP2DRV_MESSAGE_CMD_DONE_DOORBELL_CLEAR);/*clear interrupt*/
419                                 return TRUE;
420                         }
421                         UDELAY(10000);
422                 }/*max 1 seconds*/
423         }while(Retries++ < 20);/*max 20 sec*/
424         return (FALSE);
425 }
426 /*
427 **********************************************************************
428 **********************************************************************
429 */
430 static u_int8_t arcmsr_hbd_wait_msgint_ready(struct AdapterControlBlock *acb)
431 {
432         u_int32_t Index;
433         u_int8_t Retries = 0x00;
434
435         do {
436                 for(Index=0; Index < 100; Index++) {
437                         if(CHIP_REG_READ32(HBD_MessageUnit, 0, outbound_doorbell) & ARCMSR_HBDMU_IOP2DRV_MESSAGE_CMD_DONE) {
438                                 CHIP_REG_WRITE32(HBD_MessageUnit, 0, outbound_doorbell, ARCMSR_HBDMU_IOP2DRV_MESSAGE_CMD_DONE_CLEAR);/*clear interrupt*/
439                                 return TRUE;
440                         }
441                         UDELAY(10000);
442                 }/*max 1 seconds*/
443         }while(Retries++ < 20);/*max 20 sec*/
444         return (FALSE);
445 }
446 /*
447 **********************************************************************
448 **********************************************************************
449 */
450 static u_int8_t arcmsr_hbe_wait_msgint_ready(struct AdapterControlBlock *acb)
451 {
452         u_int32_t Index, read_doorbell;
453         u_int8_t Retries = 0x00;
454
455         do {
456                 for(Index=0; Index < 100; Index++) {
457                         read_doorbell = CHIP_REG_READ32(HBE_MessageUnit, 0, iobound_doorbell);
458                         if((read_doorbell ^ acb->in_doorbell) & ARCMSR_HBEMU_IOP2DRV_MESSAGE_CMD_DONE) {
459                                 CHIP_REG_WRITE32(HBE_MessageUnit, 0, host_int_status, 0);/*clear interrupt*/
460                                 acb->in_doorbell = read_doorbell;
461                                 return TRUE;
462                         }
463                         UDELAY(10000);
464                 }/*max 1 seconds*/
465         }while(Retries++ < 20);/*max 20 sec*/
466         return (FALSE);
467 }
468 /*
469 ************************************************************************
470 ************************************************************************
471 */
472 static void arcmsr_flush_hba_cache(struct AdapterControlBlock *acb)
473 {
474         int retry_count = 30;/* enlarge wait flush adapter cache time: 10 minute */
475
476         CHIP_REG_WRITE32(HBA_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_FLUSH_CACHE);
477         do {
478                 if(arcmsr_hba_wait_msgint_ready(acb)) {
479                         break;
480                 } else {
481                         retry_count--;
482                 }
483         }while(retry_count != 0);
484 }
485 /*
486 ************************************************************************
487 ************************************************************************
488 */
489 static void arcmsr_flush_hbb_cache(struct AdapterControlBlock *acb)
490 {
491         int retry_count = 30;/* enlarge wait flush adapter cache time: 10 minute */
492         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
493
494         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_MESSAGE_FLUSH_CACHE);
495         do {
496                 if(arcmsr_hbb_wait_msgint_ready(acb)) {
497                         break;
498                 } else {
499                         retry_count--;
500                 }
501         }while(retry_count != 0);
502 }
503 /*
504 ************************************************************************
505 ************************************************************************
506 */
507 static void arcmsr_flush_hbc_cache(struct AdapterControlBlock *acb)
508 {
509         int retry_count = 30;/* enlarge wait flush adapter cache time: 10 minute */
510
511         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_FLUSH_CACHE);
512         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_doorbell, ARCMSR_HBCMU_DRV2IOP_MESSAGE_CMD_DONE);
513         do {
514                 if(arcmsr_hbc_wait_msgint_ready(acb)) {
515                         break;
516                 } else {
517                         retry_count--;
518                 }
519         }while(retry_count != 0);
520 }
521 /*
522 ************************************************************************
523 ************************************************************************
524 */
525 static void arcmsr_flush_hbd_cache(struct AdapterControlBlock *acb)
526 {
527         int retry_count = 30; /* enlarge wait flush adapter cache time: 10 minute */
528
529         CHIP_REG_WRITE32(HBD_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_FLUSH_CACHE);
530         do {
531                 if(arcmsr_hbd_wait_msgint_ready(acb)) {
532                         break;
533                 } else {
534                         retry_count--;
535                 }
536         }while(retry_count != 0);
537 }
538 /*
539 ************************************************************************
540 ************************************************************************
541 */
542 static void arcmsr_flush_hbe_cache(struct AdapterControlBlock *acb)
543 {
544         int retry_count = 30;/* enlarge wait flush adapter cache time: 10 minute */
545
546         CHIP_REG_WRITE32(HBE_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_FLUSH_CACHE);
547         acb->out_doorbell ^= ARCMSR_HBEMU_DRV2IOP_MESSAGE_CMD_DONE;
548         CHIP_REG_WRITE32(HBE_MessageUnit, 0, iobound_doorbell, acb->out_doorbell);
549         do {
550                 if(arcmsr_hbe_wait_msgint_ready(acb)) {
551                         break;
552                 } else {
553                         retry_count--;
554                 }
555         }while(retry_count != 0);
556 }
557 /*
558 ************************************************************************
559 ************************************************************************
560 */
561 static void arcmsr_flush_adapter_cache(struct AdapterControlBlock *acb)
562 {
563         switch (acb->adapter_type) {
564         case ACB_ADAPTER_TYPE_A: {
565                         arcmsr_flush_hba_cache(acb);
566                 }
567                 break;
568         case ACB_ADAPTER_TYPE_B: {
569                         arcmsr_flush_hbb_cache(acb);
570                 }
571                 break;
572         case ACB_ADAPTER_TYPE_C: {
573                         arcmsr_flush_hbc_cache(acb);
574                 }
575                 break;
576         case ACB_ADAPTER_TYPE_D: {
577                         arcmsr_flush_hbd_cache(acb);
578                 }
579                 break;
580         case ACB_ADAPTER_TYPE_E: {
581                         arcmsr_flush_hbe_cache(acb);
582                 }
583                 break;
584         }
585 }
586 /*
587 *******************************************************************************
588 *******************************************************************************
589 */
590 static int arcmsr_suspend(device_t dev)
591 {
592         struct AdapterControlBlock      *acb = device_get_softc(dev);
593
594         /* flush controller */
595         arcmsr_iop_parking(acb);
596         /* disable all outbound interrupt */
597         arcmsr_disable_allintr(acb);
598         return(0);
599 }
600 /*
601 *******************************************************************************
602 *******************************************************************************
603 */
604 static int arcmsr_resume(device_t dev)
605 {
606         struct AdapterControlBlock      *acb = device_get_softc(dev);
607
608         arcmsr_iop_init(acb);
609         return(0);
610 }
611 /*
612 *********************************************************************************
613 *********************************************************************************
614 */
615 static void arcmsr_async(void *cb_arg, u_int32_t code, struct cam_path *path, void *arg)
616 {
617         struct AdapterControlBlock *acb;
618         u_int8_t target_id, target_lun;
619         struct cam_sim *sim;
620
621         sim = (struct cam_sim *) cb_arg;
622         acb =(struct AdapterControlBlock *) cam_sim_softc(sim);
623         switch (code) {
624         case AC_LOST_DEVICE:
625                 target_id = xpt_path_target_id(path);
626                 target_lun = xpt_path_lun_id(path);
627                 if((target_id > ARCMSR_MAX_TARGETID) || (target_lun > ARCMSR_MAX_TARGETLUN)) {
628                         break;
629                 }
630         //      printf("%s:scsi id=%d lun=%d device lost \n", device_get_name(acb->pci_dev), target_id, target_lun);
631                 break;
632         default:
633                 break;
634         }
635 }
636 /*
637 **********************************************************************
638 **********************************************************************
639 */
640 static void arcmsr_report_sense_info(struct CommandControlBlock *srb)
641 {
642         union ccb *pccb = srb->pccb;
643
644         pccb->ccb_h.status |= CAM_SCSI_STATUS_ERROR;
645         pccb->csio.scsi_status = SCSI_STATUS_CHECK_COND;
646         if(pccb->csio.sense_len) {
647                 memset(&pccb->csio.sense_data, 0, sizeof(pccb->csio.sense_data));
648                 memcpy(&pccb->csio.sense_data, srb->arcmsr_cdb.SenseData, 
649                 get_min(sizeof(struct SENSE_DATA), sizeof(pccb->csio.sense_data)));
650                 ((u_int8_t *)&pccb->csio.sense_data)[0] = (0x1 << 7 | 0x70); /* Valid,ErrorCode */
651                 pccb->ccb_h.status |= CAM_AUTOSNS_VALID;
652         }
653 }
654 /*
655 *********************************************************************
656 *********************************************************************
657 */
658 static void arcmsr_abort_hba_allcmd(struct AdapterControlBlock *acb)
659 {
660         CHIP_REG_WRITE32(HBA_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_ABORT_CMD);
661         if(!arcmsr_hba_wait_msgint_ready(acb)) {
662                 printf("arcmsr%d: wait 'abort all outstanding command' timeout \n", acb->pci_unit);
663         }
664 }
665 /*
666 *********************************************************************
667 *********************************************************************
668 */
669 static void arcmsr_abort_hbb_allcmd(struct AdapterControlBlock *acb)
670 {
671         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
672         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_MESSAGE_ABORT_CMD);
673         if(!arcmsr_hbb_wait_msgint_ready(acb)) {
674                 printf("arcmsr%d: wait 'abort all outstanding command' timeout \n", acb->pci_unit);
675         }
676 }
677 /*
678 *********************************************************************
679 *********************************************************************
680 */
681 static void arcmsr_abort_hbc_allcmd(struct AdapterControlBlock *acb)
682 {
683         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_ABORT_CMD);
684         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_doorbell, ARCMSR_HBCMU_DRV2IOP_MESSAGE_CMD_DONE);
685         if(!arcmsr_hbc_wait_msgint_ready(acb)) {
686                 printf("arcmsr%d: wait 'abort all outstanding command' timeout \n", acb->pci_unit);
687         }
688 }
689 /*
690 *********************************************************************
691 *********************************************************************
692 */
693 static void arcmsr_abort_hbd_allcmd(struct AdapterControlBlock *acb)
694 {
695         CHIP_REG_WRITE32(HBD_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_ABORT_CMD);
696         if(!arcmsr_hbd_wait_msgint_ready(acb)) {
697                 printf("arcmsr%d: wait 'abort all outstanding command' timeout \n", acb->pci_unit);
698         }
699 }
700 /*
701 *********************************************************************
702 *********************************************************************
703 */
704 static void arcmsr_abort_hbe_allcmd(struct AdapterControlBlock *acb)
705 {
706         CHIP_REG_WRITE32(HBE_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_ABORT_CMD);
707         acb->out_doorbell ^= ARCMSR_HBEMU_DRV2IOP_MESSAGE_CMD_DONE;
708         CHIP_REG_WRITE32(HBE_MessageUnit, 0, iobound_doorbell, acb->out_doorbell);
709         if(!arcmsr_hbe_wait_msgint_ready(acb)) {
710                 printf("arcmsr%d: wait 'abort all outstanding command' timeout \n", acb->pci_unit);
711         }
712 }
713 /*
714 *********************************************************************
715 *********************************************************************
716 */
717 static void arcmsr_abort_allcmd(struct AdapterControlBlock *acb)
718 {
719         switch (acb->adapter_type) {
720         case ACB_ADAPTER_TYPE_A: {
721                         arcmsr_abort_hba_allcmd(acb);
722                 }
723                 break;
724         case ACB_ADAPTER_TYPE_B: {
725                         arcmsr_abort_hbb_allcmd(acb);
726                 }
727                 break;
728         case ACB_ADAPTER_TYPE_C: {
729                         arcmsr_abort_hbc_allcmd(acb);
730                 }
731                 break;
732         case ACB_ADAPTER_TYPE_D: {
733                         arcmsr_abort_hbd_allcmd(acb);
734                 }
735                 break;
736         case ACB_ADAPTER_TYPE_E: {
737                         arcmsr_abort_hbe_allcmd(acb);
738                 }
739                 break;
740         }
741 }
742 /*
743 **********************************************************************
744 **********************************************************************
745 */
746 static void arcmsr_srb_complete(struct CommandControlBlock *srb, int stand_flag)
747 {
748         struct AdapterControlBlock *acb = srb->acb;
749         union ccb *pccb = srb->pccb;
750
751         if(srb->srb_flags & SRB_FLAG_TIMER_START)
752                 callout_stop(&srb->ccb_callout);
753         if((pccb->ccb_h.flags & CAM_DIR_MASK) != CAM_DIR_NONE) {
754                 bus_dmasync_op_t op;
755
756                 if((pccb->ccb_h.flags & CAM_DIR_MASK) == CAM_DIR_IN) {
757                         op = BUS_DMASYNC_POSTREAD;
758                 } else {
759                         op = BUS_DMASYNC_POSTWRITE;
760                 }
761                 bus_dmamap_sync(acb->dm_segs_dmat, srb->dm_segs_dmamap, op);
762                 bus_dmamap_unload(acb->dm_segs_dmat, srb->dm_segs_dmamap);
763         }
764         if(stand_flag == 1) {
765                 atomic_subtract_int(&acb->srboutstandingcount, 1);
766                 if((acb->acb_flags & ACB_F_CAM_DEV_QFRZN) && (
767                 acb->srboutstandingcount < (acb->maxOutstanding -10))) {
768                         acb->acb_flags &= ~ACB_F_CAM_DEV_QFRZN;
769                         pccb->ccb_h.status |= CAM_RELEASE_SIMQ;
770                 }
771         }
772         if(srb->srb_state != ARCMSR_SRB_TIMEOUT)
773                 arcmsr_free_srb(srb);
774         acb->pktReturnCount++;
775         xpt_done(pccb);
776 }
777 /*
778 **************************************************************************
779 **************************************************************************
780 */
781 static void arcmsr_report_srb_state(struct AdapterControlBlock *acb, struct CommandControlBlock *srb, u_int16_t error)
782 {
783         int target, lun;
784
785         target = srb->pccb->ccb_h.target_id;
786         lun = srb->pccb->ccb_h.target_lun;
787         if(error == FALSE) {
788                 if(acb->devstate[target][lun] == ARECA_RAID_GONE) {
789                         acb->devstate[target][lun] = ARECA_RAID_GOOD;
790                 }
791                 srb->pccb->ccb_h.status |= CAM_REQ_CMP;
792                 arcmsr_srb_complete(srb, 1);
793         } else {
794                 switch(srb->arcmsr_cdb.DeviceStatus) {
795                 case ARCMSR_DEV_SELECT_TIMEOUT: {
796                                 if(acb->devstate[target][lun] == ARECA_RAID_GOOD) {
797                                         printf( "arcmsr%d: Target=%x, Lun=%x, selection timeout, raid volume was lost\n", acb->pci_unit, target, lun);
798                                 }
799                                 acb->devstate[target][lun] = ARECA_RAID_GONE;
800                                 srb->pccb->ccb_h.status |= CAM_DEV_NOT_THERE;
801                                 arcmsr_srb_complete(srb, 1);
802                         }
803                         break;
804                 case ARCMSR_DEV_ABORTED:
805                 case ARCMSR_DEV_INIT_FAIL: {
806                                 acb->devstate[target][lun] = ARECA_RAID_GONE;
807                                 srb->pccb->ccb_h.status |= CAM_DEV_NOT_THERE;
808                                 arcmsr_srb_complete(srb, 1);
809                         }
810                         break;
811                 case SCSISTAT_CHECK_CONDITION: {
812                                 acb->devstate[target][lun] = ARECA_RAID_GOOD;
813                                 arcmsr_report_sense_info(srb);
814                                 arcmsr_srb_complete(srb, 1);
815                         }
816                         break;
817                 default:
818                         printf("arcmsr%d: scsi id=%d lun=%d isr got command error done,but got unknown DeviceStatus=0x%x \n"
819                                         , acb->pci_unit, target, lun ,srb->arcmsr_cdb.DeviceStatus);
820                         acb->devstate[target][lun] = ARECA_RAID_GONE;
821                         srb->pccb->ccb_h.status |= CAM_UNCOR_PARITY;
822                         /*unknown error or crc error just for retry*/
823                         arcmsr_srb_complete(srb, 1);
824                         break;
825                 }
826         }
827 }
828 /*
829 **************************************************************************
830 **************************************************************************
831 */
832 static void arcmsr_drain_donequeue(struct AdapterControlBlock *acb, u_int32_t flag_srb, u_int16_t error)
833 {
834         struct CommandControlBlock *srb;
835
836         /* check if command done with no error*/
837         switch (acb->adapter_type) {
838         case ACB_ADAPTER_TYPE_A:
839         case ACB_ADAPTER_TYPE_B:
840                 srb = (struct CommandControlBlock *)(acb->vir2phy_offset+(flag_srb << 5));/*frame must be 32 bytes aligned*/
841                 break;
842         case ACB_ADAPTER_TYPE_C:
843         case ACB_ADAPTER_TYPE_D:
844                 srb = (struct CommandControlBlock *)(acb->vir2phy_offset+(flag_srb & 0xFFFFFFE0)); /*frame must be 32 bytes aligned*/
845                 break;
846         case ACB_ADAPTER_TYPE_E:
847                 srb = acb->psrb_pool[flag_srb];
848                 break;
849         default:
850                 srb = (struct CommandControlBlock *)(acb->vir2phy_offset+(flag_srb << 5));/*frame must be 32 bytes aligned*/
851                 break;
852         }
853         if((srb->acb != acb) || (srb->srb_state != ARCMSR_SRB_START)) {
854                 if(srb->srb_state == ARCMSR_SRB_TIMEOUT) {
855                         arcmsr_free_srb(srb);
856                         printf("arcmsr%d: srb='%p' return srb has been timeouted\n", acb->pci_unit, srb);
857                         return;
858                 }
859                 printf("arcmsr%d: return srb has been completed\n"
860                         "srb='%p' srb_state=0x%x outstanding srb count=%d \n",
861                         acb->pci_unit, srb, srb->srb_state, acb->srboutstandingcount);
862                 return;
863         }
864         arcmsr_report_srb_state(acb, srb, error);
865 }
866 /*
867 **************************************************************************
868 **************************************************************************
869 */
870 static void     arcmsr_srb_timeout(void *arg)
871 {
872         struct CommandControlBlock *srb = (struct CommandControlBlock *)arg;
873         struct AdapterControlBlock *acb;
874         int target, lun;
875         u_int8_t cmd;
876
877         target = srb->pccb->ccb_h.target_id;
878         lun = srb->pccb->ccb_h.target_lun;
879         acb = srb->acb;
880         ARCMSR_LOCK_ACQUIRE(&acb->isr_lock);
881         if(srb->srb_state == ARCMSR_SRB_START)
882         {
883                 cmd = scsiio_cdb_ptr(&srb->pccb->csio)[0];
884                 srb->srb_state = ARCMSR_SRB_TIMEOUT;
885                 srb->pccb->ccb_h.status |= CAM_CMD_TIMEOUT;
886                 arcmsr_srb_complete(srb, 1);
887                 printf("arcmsr%d: scsi id %d lun %d cmd=0x%x srb='%p' ccb command time out!\n",
888                                  acb->pci_unit, target, lun, cmd, srb);
889         }
890         ARCMSR_LOCK_RELEASE(&acb->isr_lock);
891 #ifdef ARCMSR_DEBUG1
892         arcmsr_dump_data(acb);
893 #endif
894 }
895
896 /*
897 **********************************************************************
898 **********************************************************************
899 */
900 static void arcmsr_done4abort_postqueue(struct AdapterControlBlock *acb)
901 {
902         int i=0;
903         u_int32_t flag_srb;
904         u_int16_t error;
905
906         switch (acb->adapter_type) {
907         case ACB_ADAPTER_TYPE_A: {
908                         u_int32_t outbound_intstatus;
909
910                         /*clear and abort all outbound posted Q*/
911                         outbound_intstatus = CHIP_REG_READ32(HBA_MessageUnit, 0, outbound_intstatus) & acb->outbound_int_enable;
912                         CHIP_REG_WRITE32(HBA_MessageUnit, 0, outbound_intstatus, outbound_intstatus);/*clear interrupt*/
913                         while(((flag_srb=CHIP_REG_READ32(HBA_MessageUnit, 0, outbound_queueport)) != 0xFFFFFFFF) && (i++ < ARCMSR_MAX_OUTSTANDING_CMD)) {
914                                 error = (flag_srb & ARCMSR_SRBREPLY_FLAG_ERROR_MODE0)?TRUE:FALSE;
915                                 arcmsr_drain_donequeue(acb, flag_srb, error);
916                         }
917                 }
918                 break;
919         case ACB_ADAPTER_TYPE_B: {
920                         struct HBB_MessageUnit *phbbmu=(struct HBB_MessageUnit *)acb->pmu;
921
922                         /*clear all outbound posted Q*/
923                         WRITE_CHIP_REG32(0, phbbmu->iop2drv_doorbell, ARCMSR_DOORBELL_INT_CLEAR_PATTERN); /* clear doorbell interrupt */
924                         for(i=0; i < ARCMSR_MAX_HBB_POSTQUEUE; i++) {
925                                 if((flag_srb = phbbmu->done_qbuffer[i]) != 0) {
926                                         phbbmu->done_qbuffer[i] = 0;
927                                         error = (flag_srb & ARCMSR_SRBREPLY_FLAG_ERROR_MODE0)?TRUE:FALSE;
928                                         arcmsr_drain_donequeue(acb, flag_srb, error);
929                                 }
930                                 phbbmu->post_qbuffer[i] = 0;
931                         }/*drain reply FIFO*/
932                         phbbmu->doneq_index = 0;
933                         phbbmu->postq_index = 0;
934                 }
935                 break;
936         case ACB_ADAPTER_TYPE_C: {
937                         while((CHIP_REG_READ32(HBC_MessageUnit, 0, host_int_status) & ARCMSR_HBCMU_OUTBOUND_POSTQUEUE_ISR) && (i++ < ARCMSR_MAX_OUTSTANDING_CMD)) {
938                                 flag_srb = CHIP_REG_READ32(HBC_MessageUnit, 0, outbound_queueport_low);
939                                 error = (flag_srb & ARCMSR_SRBREPLY_FLAG_ERROR_MODE1) ? TRUE : FALSE;
940                                 arcmsr_drain_donequeue(acb, flag_srb, error);
941                         }
942                 }
943                 break;
944         case ACB_ADAPTER_TYPE_D: {
945                         arcmsr_hbd_postqueue_isr(acb);
946                 }
947                 break;
948         case ACB_ADAPTER_TYPE_E: {
949                         arcmsr_hbe_postqueue_isr(acb);
950                 }
951                 break;
952         }
953 }
954 /*
955 ****************************************************************************
956 ****************************************************************************
957 */
958 static void arcmsr_iop_reset(struct AdapterControlBlock *acb)
959 {
960         struct CommandControlBlock *srb;
961         u_int32_t intmask_org;
962         u_int32_t i=0;
963
964         if(acb->srboutstandingcount>0) {
965                 /* disable all outbound interrupt */
966                 intmask_org = arcmsr_disable_allintr(acb);
967                 /*clear and abort all outbound posted Q*/
968                 arcmsr_done4abort_postqueue(acb);
969                 /* talk to iop 331 outstanding command aborted*/
970                 arcmsr_abort_allcmd(acb);
971                 for(i=0; i < ARCMSR_MAX_FREESRB_NUM; i++) {
972                         srb = acb->psrb_pool[i];
973                         if(srb->srb_state == ARCMSR_SRB_START) {
974                                 srb->srb_state = ARCMSR_SRB_ABORTED;
975                                 srb->pccb->ccb_h.status |= CAM_REQ_ABORTED;
976                                 arcmsr_srb_complete(srb, 1);
977                                 printf("arcmsr%d: scsi id=%d lun=%jx srb='%p' aborted\n"
978                                                 , acb->pci_unit, srb->pccb->ccb_h.target_id
979                                                 , (uintmax_t)srb->pccb->ccb_h.target_lun, srb);
980                         }
981                 }
982                 /* enable all outbound interrupt */
983                 arcmsr_enable_allintr(acb, intmask_org);
984         }
985         acb->srboutstandingcount = 0;
986         acb->workingsrb_doneindex = 0;
987         acb->workingsrb_startindex = 0;
988         acb->pktRequestCount = 0;
989         acb->pktReturnCount = 0;
990 }
991 /*
992 **********************************************************************
993 **********************************************************************
994 */
995 static void arcmsr_build_srb(struct CommandControlBlock *srb, 
996                 bus_dma_segment_t *dm_segs, u_int32_t nseg)
997 {
998         struct ARCMSR_CDB *arcmsr_cdb = &srb->arcmsr_cdb;
999         u_int8_t *psge = (u_int8_t *)&arcmsr_cdb->u;
1000         u_int32_t address_lo, address_hi;
1001         union ccb *pccb = srb->pccb;
1002         struct ccb_scsiio *pcsio = &pccb->csio;
1003         u_int32_t arccdbsize = 0x30;
1004
1005         memset(arcmsr_cdb, 0, sizeof(struct ARCMSR_CDB));
1006         arcmsr_cdb->Bus = 0;
1007         arcmsr_cdb->TargetID = pccb->ccb_h.target_id;
1008         arcmsr_cdb->LUN = pccb->ccb_h.target_lun;
1009         arcmsr_cdb->Function = 1;
1010         arcmsr_cdb->CdbLength = (u_int8_t)pcsio->cdb_len;
1011         bcopy(scsiio_cdb_ptr(pcsio), arcmsr_cdb->Cdb, pcsio->cdb_len);
1012         if(nseg != 0) {
1013                 struct AdapterControlBlock *acb = srb->acb;
1014                 bus_dmasync_op_t op;    
1015                 u_int32_t length, i, cdb_sgcount = 0;
1016
1017                 if((pccb->ccb_h.flags & CAM_DIR_MASK) == CAM_DIR_IN) {
1018                         op = BUS_DMASYNC_PREREAD;
1019                 } else {
1020                         op = BUS_DMASYNC_PREWRITE;
1021                         arcmsr_cdb->Flags |= ARCMSR_CDB_FLAG_WRITE;
1022                         srb->srb_flags |= SRB_FLAG_WRITE;
1023                 }
1024                 bus_dmamap_sync(acb->dm_segs_dmat, srb->dm_segs_dmamap, op);
1025                 for(i=0; i < nseg; i++) {
1026                         /* Get the physical address of the current data pointer */
1027                         length = arcmsr_htole32(dm_segs[i].ds_len);
1028                         address_lo = arcmsr_htole32(dma_addr_lo32(dm_segs[i].ds_addr));
1029                         address_hi = arcmsr_htole32(dma_addr_hi32(dm_segs[i].ds_addr));
1030                         if(address_hi == 0) {
1031                                 struct SG32ENTRY *pdma_sg = (struct SG32ENTRY *)psge;
1032                                 pdma_sg->address = address_lo;
1033                                 pdma_sg->length = length;
1034                                 psge += sizeof(struct SG32ENTRY);
1035                                 arccdbsize += sizeof(struct SG32ENTRY);
1036                         } else {
1037                                 u_int32_t sg64s_size = 0, tmplength = length;
1038
1039                                 while(1) {
1040                                         u_int64_t span4G, length0;
1041                                         struct SG64ENTRY *pdma_sg = (struct SG64ENTRY *)psge;
1042
1043                                         span4G = (u_int64_t)address_lo + tmplength;
1044                                         pdma_sg->addresshigh = address_hi;
1045                                         pdma_sg->address = address_lo;
1046                                         if(span4G > 0x100000000) {
1047                                                 /*see if cross 4G boundary*/
1048                                                 length0 = 0x100000000-address_lo;
1049                                                 pdma_sg->length = (u_int32_t)length0 | IS_SG64_ADDR;
1050                                                 address_hi = address_hi+1;
1051                                                 address_lo = 0;
1052                                                 tmplength = tmplength - (u_int32_t)length0;
1053                                                 sg64s_size += sizeof(struct SG64ENTRY);
1054                                                 psge += sizeof(struct SG64ENTRY);
1055                                                 cdb_sgcount++;
1056                                         } else {
1057                                                 pdma_sg->length = tmplength | IS_SG64_ADDR;
1058                                                 sg64s_size += sizeof(struct SG64ENTRY);
1059                                                 psge += sizeof(struct SG64ENTRY);
1060                                                 break;
1061                                         }
1062                                 }
1063                                 arccdbsize += sg64s_size;
1064                         }
1065                         cdb_sgcount++;
1066                 }
1067                 arcmsr_cdb->sgcount = (u_int8_t)cdb_sgcount;
1068                 arcmsr_cdb->DataLength = pcsio->dxfer_len;
1069                 if( arccdbsize > 256) {
1070                         arcmsr_cdb->Flags |= ARCMSR_CDB_FLAG_SGL_BSIZE;
1071                 }
1072         } else {
1073                 arcmsr_cdb->DataLength = 0;
1074         }
1075         srb->arc_cdb_size = arccdbsize;
1076         arcmsr_cdb->msgPages = (arccdbsize/256) + ((arccdbsize % 256) ? 1 : 0);
1077 }
1078 /*
1079 **************************************************************************
1080 **************************************************************************
1081 */ 
1082 static void arcmsr_post_srb(struct AdapterControlBlock *acb, struct CommandControlBlock *srb)
1083 {
1084         u_int32_t cdb_phyaddr_low = (u_int32_t) srb->cdb_phyaddr_low;
1085         struct ARCMSR_CDB *arcmsr_cdb = (struct ARCMSR_CDB *)&srb->arcmsr_cdb;
1086
1087         bus_dmamap_sync(acb->srb_dmat, acb->srb_dmamap, (srb->srb_flags & SRB_FLAG_WRITE) ? BUS_DMASYNC_POSTWRITE:BUS_DMASYNC_POSTREAD);
1088         atomic_add_int(&acb->srboutstandingcount, 1);
1089         srb->srb_state = ARCMSR_SRB_START;
1090
1091         switch (acb->adapter_type) {
1092         case ACB_ADAPTER_TYPE_A: {
1093                         if(arcmsr_cdb->Flags & ARCMSR_CDB_FLAG_SGL_BSIZE) {
1094                                 CHIP_REG_WRITE32(HBA_MessageUnit, 0, inbound_queueport, cdb_phyaddr_low|ARCMSR_SRBPOST_FLAG_SGL_BSIZE);
1095                         } else {
1096                                 CHIP_REG_WRITE32(HBA_MessageUnit, 0, inbound_queueport, cdb_phyaddr_low);
1097                         }
1098                 }
1099                 break;
1100         case ACB_ADAPTER_TYPE_B: {
1101                         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
1102                         int ending_index, index;
1103
1104                         index = phbbmu->postq_index;
1105                         ending_index = ((index+1) % ARCMSR_MAX_HBB_POSTQUEUE);
1106                         phbbmu->post_qbuffer[ending_index] = 0;
1107                         if(arcmsr_cdb->Flags & ARCMSR_CDB_FLAG_SGL_BSIZE) {
1108                                 phbbmu->post_qbuffer[index] = cdb_phyaddr_low | ARCMSR_SRBPOST_FLAG_SGL_BSIZE;
1109                         } else {
1110                                 phbbmu->post_qbuffer[index] = cdb_phyaddr_low;
1111                         }
1112                         index++;
1113                         index %= ARCMSR_MAX_HBB_POSTQUEUE;     /*if last index number set it to 0 */
1114                         phbbmu->postq_index = index;
1115                         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_DRV2IOP_CDB_POSTED);
1116                 }
1117                 break;
1118         case ACB_ADAPTER_TYPE_C: {
1119                         u_int32_t ccb_post_stamp, arc_cdb_size, cdb_phyaddr_hi32;
1120
1121                         arc_cdb_size = (srb->arc_cdb_size > 0x300) ? 0x300 : srb->arc_cdb_size;
1122                         ccb_post_stamp = (cdb_phyaddr_low | ((arc_cdb_size-1) >> 6) | 1);
1123                         cdb_phyaddr_hi32 = acb->srb_phyaddr.B.phyadd_high;
1124                         if(cdb_phyaddr_hi32)
1125                         {
1126                                 CHIP_REG_WRITE32(HBC_MessageUnit,0,inbound_queueport_high, cdb_phyaddr_hi32);
1127                                 CHIP_REG_WRITE32(HBC_MessageUnit,0,inbound_queueport_low, ccb_post_stamp);
1128                         }
1129                         else
1130                         {
1131                                 CHIP_REG_WRITE32(HBC_MessageUnit,0,inbound_queueport_low, ccb_post_stamp);
1132                         }
1133                 }
1134                 break;
1135         case ACB_ADAPTER_TYPE_D: {
1136                         struct HBD_MessageUnit0 *phbdmu = (struct HBD_MessageUnit0 *)acb->pmu;
1137                         u_int16_t index_stripped;
1138                         u_int16_t postq_index;
1139                         struct InBound_SRB *pinbound_srb;
1140
1141                         ARCMSR_LOCK_ACQUIRE(&acb->postDone_lock);
1142                         postq_index = phbdmu->postq_index;
1143                         pinbound_srb = (struct InBound_SRB *)&phbdmu->post_qbuffer[postq_index & 0xFF];
1144                         pinbound_srb->addressHigh = srb->cdb_phyaddr_high;
1145                         pinbound_srb->addressLow = srb->cdb_phyaddr_low;
1146                         pinbound_srb->length = srb->arc_cdb_size >> 2;
1147                         arcmsr_cdb->Context = srb->cdb_phyaddr_low;
1148                         if (postq_index & 0x4000) {
1149                                 index_stripped = postq_index & 0xFF;
1150                                 index_stripped += 1;
1151                                 index_stripped %= ARCMSR_MAX_HBD_POSTQUEUE;
1152                                 phbdmu->postq_index = index_stripped ? (index_stripped | 0x4000) : index_stripped;
1153                         } else {
1154                                 index_stripped = postq_index;
1155                                 index_stripped += 1;
1156                                 index_stripped %= ARCMSR_MAX_HBD_POSTQUEUE;
1157                                 phbdmu->postq_index = index_stripped ? index_stripped : (index_stripped | 0x4000);
1158                         }
1159                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, inboundlist_write_pointer, postq_index);
1160                         ARCMSR_LOCK_RELEASE(&acb->postDone_lock);
1161                 }
1162                 break;
1163         case ACB_ADAPTER_TYPE_E: {
1164                         u_int32_t ccb_post_stamp, arc_cdb_size;
1165
1166                         arc_cdb_size = (srb->arc_cdb_size > 0x300) ? 0x300 : srb->arc_cdb_size;
1167                         ccb_post_stamp = (srb->smid | ((arc_cdb_size-1) >> 6));
1168                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, inbound_queueport_high, 0);
1169                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, inbound_queueport_low, ccb_post_stamp);
1170                 }
1171                 break;
1172         }
1173 }
1174 /*
1175 ************************************************************************
1176 ************************************************************************
1177 */
1178 static struct QBUFFER *arcmsr_get_iop_rqbuffer( struct AdapterControlBlock *acb)
1179 {
1180         struct QBUFFER *qbuffer=NULL;
1181
1182         switch (acb->adapter_type) {
1183         case ACB_ADAPTER_TYPE_A: {
1184                         struct HBA_MessageUnit *phbamu = (struct HBA_MessageUnit *)acb->pmu;
1185
1186                         qbuffer = (struct QBUFFER *)&phbamu->message_rbuffer;
1187                 }
1188                 break;
1189         case ACB_ADAPTER_TYPE_B: {
1190                         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
1191
1192                         qbuffer = (struct QBUFFER *)&phbbmu->hbb_rwbuffer->message_rbuffer;
1193                 }
1194                 break;
1195         case ACB_ADAPTER_TYPE_C: {
1196                         struct HBC_MessageUnit *phbcmu = (struct HBC_MessageUnit *)acb->pmu;
1197
1198                         qbuffer = (struct QBUFFER *)&phbcmu->message_rbuffer;
1199                 }
1200                 break;
1201         case ACB_ADAPTER_TYPE_D: {
1202                         struct HBD_MessageUnit0 *phbdmu = (struct HBD_MessageUnit0 *)acb->pmu;
1203
1204                         qbuffer = (struct QBUFFER *)&phbdmu->phbdmu->message_rbuffer;
1205                 }
1206                 break;
1207         case ACB_ADAPTER_TYPE_E: {
1208                         struct HBE_MessageUnit *phbcmu = (struct HBE_MessageUnit *)acb->pmu;
1209
1210                         qbuffer = (struct QBUFFER *)&phbcmu->message_rbuffer;
1211                 }
1212                 break;
1213         }
1214         return(qbuffer);
1215 }
1216 /*
1217 ************************************************************************
1218 ************************************************************************
1219 */
1220 static struct QBUFFER *arcmsr_get_iop_wqbuffer( struct AdapterControlBlock *acb)
1221 {
1222         struct QBUFFER *qbuffer = NULL;
1223
1224         switch (acb->adapter_type) {
1225         case ACB_ADAPTER_TYPE_A: {
1226                         struct HBA_MessageUnit *phbamu = (struct HBA_MessageUnit *)acb->pmu;
1227
1228                         qbuffer = (struct QBUFFER *)&phbamu->message_wbuffer;
1229                 }
1230                 break;
1231         case ACB_ADAPTER_TYPE_B: {
1232                         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
1233
1234                         qbuffer = (struct QBUFFER *)&phbbmu->hbb_rwbuffer->message_wbuffer;
1235                 }
1236                 break;
1237         case ACB_ADAPTER_TYPE_C: {
1238                         struct HBC_MessageUnit *phbcmu = (struct HBC_MessageUnit *)acb->pmu;
1239
1240                         qbuffer = (struct QBUFFER *)&phbcmu->message_wbuffer;
1241                 }
1242                 break;
1243         case ACB_ADAPTER_TYPE_D: {
1244                         struct HBD_MessageUnit0 *phbdmu = (struct HBD_MessageUnit0 *)acb->pmu;
1245
1246                         qbuffer = (struct QBUFFER *)&phbdmu->phbdmu->message_wbuffer;
1247                 }
1248                 break;
1249         case ACB_ADAPTER_TYPE_E: {
1250                         struct HBE_MessageUnit *phbcmu = (struct HBE_MessageUnit *)acb->pmu;
1251
1252                         qbuffer = (struct QBUFFER *)&phbcmu->message_wbuffer;
1253                 }
1254                 break;
1255         }
1256         return(qbuffer);
1257 }
1258 /*
1259 **************************************************************************
1260 **************************************************************************
1261 */
1262 static void arcmsr_iop_message_read(struct AdapterControlBlock *acb)
1263 {
1264         switch (acb->adapter_type) {
1265         case ACB_ADAPTER_TYPE_A: {
1266                         /* let IOP know data has been read */
1267                         CHIP_REG_WRITE32(HBA_MessageUnit, 0, inbound_doorbell, ARCMSR_INBOUND_DRIVER_DATA_READ_OK);
1268                 }
1269                 break;
1270         case ACB_ADAPTER_TYPE_B: {
1271                         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
1272                         /* let IOP know data has been read */
1273                         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_DRV2IOP_DATA_READ_OK);
1274                 }
1275                 break;
1276         case ACB_ADAPTER_TYPE_C: {
1277                         /* let IOP know data has been read */
1278                         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_doorbell, ARCMSR_HBCMU_DRV2IOP_DATA_READ_OK);
1279                 }
1280                 break;
1281         case ACB_ADAPTER_TYPE_D: {
1282                         /* let IOP know data has been read */
1283                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, inbound_doorbell, ARCMSR_HBDMU_DRV2IOP_DATA_OUT_READ);
1284                 }
1285                 break;
1286         case ACB_ADAPTER_TYPE_E: {
1287                         /* let IOP know data has been read */
1288                         acb->out_doorbell ^= ARCMSR_HBEMU_DRV2IOP_DATA_READ_OK;
1289                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, iobound_doorbell, acb->out_doorbell);
1290                 }
1291                 break;
1292         }
1293 }
1294 /*
1295 **************************************************************************
1296 **************************************************************************
1297 */
1298 static void arcmsr_iop_message_wrote(struct AdapterControlBlock *acb)
1299 {
1300         switch (acb->adapter_type) {
1301         case ACB_ADAPTER_TYPE_A: {
1302                         /*
1303                         ** push inbound doorbell tell iop, driver data write ok 
1304                         ** and wait reply on next hwinterrupt for next Qbuffer post
1305                         */
1306                         CHIP_REG_WRITE32(HBA_MessageUnit, 0, inbound_doorbell, ARCMSR_INBOUND_DRIVER_DATA_WRITE_OK);
1307                 }
1308                 break;
1309         case ACB_ADAPTER_TYPE_B: {
1310                         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
1311                         /*
1312                         ** push inbound doorbell tell iop, driver data write ok 
1313                         ** and wait reply on next hwinterrupt for next Qbuffer post
1314                         */
1315                         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_DRV2IOP_DATA_WRITE_OK);
1316                 }
1317                 break;
1318         case ACB_ADAPTER_TYPE_C: {
1319                         /*
1320                         ** push inbound doorbell tell iop, driver data write ok 
1321                         ** and wait reply on next hwinterrupt for next Qbuffer post
1322                         */
1323                         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_doorbell, ARCMSR_HBCMU_DRV2IOP_DATA_WRITE_OK);
1324                 }
1325                 break;
1326         case ACB_ADAPTER_TYPE_D: {
1327                         /*
1328                         ** push inbound doorbell tell iop, driver data write ok 
1329                         ** and wait reply on next hwinterrupt for next Qbuffer post
1330                         */
1331                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, inbound_doorbell, ARCMSR_HBDMU_DRV2IOP_DATA_IN_READY);
1332                 }
1333                 break;
1334         case ACB_ADAPTER_TYPE_E: {
1335                         /*
1336                         ** push inbound doorbell tell iop, driver data write ok 
1337                         ** and wait reply on next hwinterrupt for next Qbuffer post
1338                         */
1339                         acb->out_doorbell ^= ARCMSR_HBEMU_DRV2IOP_DATA_WRITE_OK;
1340                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, iobound_doorbell, acb->out_doorbell);
1341                 }
1342                 break;
1343         }
1344 }
1345 /*
1346 ************************************************************************
1347 ************************************************************************
1348 */
1349 static void arcmsr_stop_hba_bgrb(struct AdapterControlBlock *acb)
1350 {
1351         acb->acb_flags &= ~ACB_F_MSG_START_BGRB;
1352         CHIP_REG_WRITE32(HBA_MessageUnit, 
1353                 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_STOP_BGRB);
1354         if(!arcmsr_hba_wait_msgint_ready(acb)) {
1355                 printf("arcmsr%d: wait 'stop adapter background rebulid' timeout \n"
1356                         , acb->pci_unit);
1357         }
1358 }
1359 /*
1360 ************************************************************************
1361 ************************************************************************
1362 */
1363 static void arcmsr_stop_hbb_bgrb(struct AdapterControlBlock *acb)
1364 {
1365         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
1366         acb->acb_flags &= ~ACB_F_MSG_START_BGRB;
1367         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_MESSAGE_STOP_BGRB);
1368         if(!arcmsr_hbb_wait_msgint_ready(acb)) {
1369                 printf( "arcmsr%d: wait 'stop adapter background rebulid' timeout \n"
1370                         , acb->pci_unit);
1371         }
1372 }
1373 /*
1374 ************************************************************************
1375 ************************************************************************
1376 */
1377 static void arcmsr_stop_hbc_bgrb(struct AdapterControlBlock *acb)
1378 {
1379         acb->acb_flags &= ~ACB_F_MSG_START_BGRB;
1380         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_STOP_BGRB);
1381         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_doorbell,ARCMSR_HBCMU_DRV2IOP_MESSAGE_CMD_DONE);
1382         if(!arcmsr_hbc_wait_msgint_ready(acb)) {
1383                 printf("arcmsr%d: wait 'stop adapter background rebulid' timeout \n", acb->pci_unit);
1384         }
1385 }
1386 /*
1387 ************************************************************************
1388 ************************************************************************
1389 */
1390 static void arcmsr_stop_hbd_bgrb(struct AdapterControlBlock *acb)
1391 {
1392         acb->acb_flags &= ~ACB_F_MSG_START_BGRB;
1393         CHIP_REG_WRITE32(HBD_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_STOP_BGRB);
1394         if(!arcmsr_hbd_wait_msgint_ready(acb)) {
1395                 printf("arcmsr%d: wait 'stop adapter background rebulid' timeout \n", acb->pci_unit);
1396         }
1397 }
1398 /*
1399 ************************************************************************
1400 ************************************************************************
1401 */
1402 static void arcmsr_stop_hbe_bgrb(struct AdapterControlBlock *acb)
1403 {
1404         acb->acb_flags &= ~ACB_F_MSG_START_BGRB;
1405         CHIP_REG_WRITE32(HBE_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_STOP_BGRB);
1406         acb->out_doorbell ^= ARCMSR_HBEMU_DRV2IOP_MESSAGE_CMD_DONE;
1407         CHIP_REG_WRITE32(HBE_MessageUnit, 0, iobound_doorbell, acb->out_doorbell);
1408         if(!arcmsr_hbe_wait_msgint_ready(acb)) {
1409                 printf("arcmsr%d: wait 'stop adapter background rebulid' timeout \n", acb->pci_unit);
1410         }
1411 }
1412 /*
1413 ************************************************************************
1414 ************************************************************************
1415 */
1416 static void arcmsr_stop_adapter_bgrb(struct AdapterControlBlock *acb)
1417 {
1418         switch (acb->adapter_type) {
1419         case ACB_ADAPTER_TYPE_A: {
1420                         arcmsr_stop_hba_bgrb(acb);
1421                 }
1422                 break;
1423         case ACB_ADAPTER_TYPE_B: {
1424                         arcmsr_stop_hbb_bgrb(acb);
1425                 }
1426                 break;
1427         case ACB_ADAPTER_TYPE_C: {
1428                         arcmsr_stop_hbc_bgrb(acb);
1429                 }
1430                 break;
1431         case ACB_ADAPTER_TYPE_D: {
1432                         arcmsr_stop_hbd_bgrb(acb);
1433                 }
1434                 break;
1435         case ACB_ADAPTER_TYPE_E: {
1436                         arcmsr_stop_hbe_bgrb(acb);
1437                 }
1438                 break;
1439         }
1440 }
1441 /*
1442 ************************************************************************
1443 ************************************************************************
1444 */
1445 static void arcmsr_poll(struct cam_sim *psim)
1446 {
1447         struct AdapterControlBlock *acb;
1448         int     mutex;
1449
1450         acb = (struct AdapterControlBlock *)cam_sim_softc(psim);
1451         mutex = mtx_owned(&acb->isr_lock);
1452         if( mutex == 0 )
1453                 ARCMSR_LOCK_ACQUIRE(&acb->isr_lock);
1454         arcmsr_interrupt(acb);
1455         if( mutex == 0 )
1456                 ARCMSR_LOCK_RELEASE(&acb->isr_lock);
1457 }
1458 /*
1459 **************************************************************************
1460 **************************************************************************
1461 */
1462 static u_int32_t arcmsr_Read_iop_rqbuffer_data_D(struct AdapterControlBlock *acb,
1463         struct QBUFFER *prbuffer) {
1464         u_int8_t *pQbuffer;
1465         u_int8_t *buf1 = NULL;
1466         u_int32_t *iop_data, *buf2 = NULL;
1467         u_int32_t iop_len, data_len;
1468
1469         iop_data = (u_int32_t *)prbuffer->data;
1470         iop_len = (u_int32_t)prbuffer->data_len;
1471         if ( iop_len > 0 )
1472         {
1473                 buf1 = malloc(128, M_DEVBUF, M_NOWAIT | M_ZERO);
1474                 buf2 = (u_int32_t *)buf1;
1475                 if( buf1 == NULL)
1476                         return (0);
1477                 data_len = iop_len;
1478                 while(data_len >= 4)
1479                 {
1480                         *buf2++ = *iop_data++;
1481                         data_len -= 4;
1482                 }
1483                 if(data_len)
1484                         *buf2 = *iop_data;
1485                 buf2 = (u_int32_t *)buf1;
1486         }
1487         while (iop_len > 0) {
1488                 pQbuffer = &acb->rqbuffer[acb->rqbuf_lastindex];
1489                 *pQbuffer = *buf1;
1490                 acb->rqbuf_lastindex++;
1491                 /* if last, index number set it to 0 */
1492                 acb->rqbuf_lastindex %= ARCMSR_MAX_QBUFFER;
1493                 buf1++;
1494                 iop_len--;
1495         }
1496         if(buf2)
1497                 free( (u_int8_t *)buf2, M_DEVBUF);
1498         /* let IOP know data has been read */
1499         arcmsr_iop_message_read(acb);
1500         return (1);
1501 }
1502 /*
1503 **************************************************************************
1504 **************************************************************************
1505 */
1506 static u_int32_t arcmsr_Read_iop_rqbuffer_data(struct AdapterControlBlock *acb,
1507         struct QBUFFER *prbuffer) {
1508         u_int8_t *pQbuffer;
1509         u_int8_t *iop_data;
1510         u_int32_t iop_len;
1511
1512         if(acb->adapter_type >= ACB_ADAPTER_TYPE_B) {
1513                 return(arcmsr_Read_iop_rqbuffer_data_D(acb, prbuffer));
1514         }
1515         iop_data = (u_int8_t *)prbuffer->data;
1516         iop_len = (u_int32_t)prbuffer->data_len;
1517         while (iop_len > 0) {
1518                 pQbuffer = &acb->rqbuffer[acb->rqbuf_lastindex];
1519                 *pQbuffer = *iop_data;
1520                 acb->rqbuf_lastindex++;
1521                 /* if last, index number set it to 0 */
1522                 acb->rqbuf_lastindex %= ARCMSR_MAX_QBUFFER;
1523                 iop_data++;
1524                 iop_len--;
1525         }
1526         /* let IOP know data has been read */
1527         arcmsr_iop_message_read(acb);
1528         return (1);
1529 }
1530 /*
1531 **************************************************************************
1532 **************************************************************************
1533 */
1534 static void arcmsr_iop2drv_data_wrote_handle(struct AdapterControlBlock *acb)
1535 {
1536         struct QBUFFER *prbuffer;
1537         int my_empty_len;
1538
1539         /*check this iop data if overflow my rqbuffer*/
1540         ARCMSR_LOCK_ACQUIRE(&acb->qbuffer_lock);
1541         prbuffer = arcmsr_get_iop_rqbuffer(acb);
1542         my_empty_len = (acb->rqbuf_lastindex - acb->rqbuf_firstindex - 1) &
1543                 (ARCMSR_MAX_QBUFFER-1);
1544         if(my_empty_len >= prbuffer->data_len) {
1545                 if(arcmsr_Read_iop_rqbuffer_data(acb, prbuffer) == 0)
1546                         acb->acb_flags |= ACB_F_IOPDATA_OVERFLOW;
1547         } else {
1548                 acb->acb_flags |= ACB_F_IOPDATA_OVERFLOW;
1549         }
1550         ARCMSR_LOCK_RELEASE(&acb->qbuffer_lock);
1551 }
1552 /*
1553 **********************************************************************
1554 **********************************************************************
1555 */
1556 static void arcmsr_Write_data_2iop_wqbuffer_D(struct AdapterControlBlock *acb)
1557 {
1558         u_int8_t *pQbuffer;
1559         struct QBUFFER *pwbuffer;
1560         u_int8_t *buf1 = NULL;
1561         u_int32_t *iop_data, *buf2 = NULL;
1562         u_int32_t allxfer_len = 0, data_len;
1563
1564         if(acb->acb_flags & ACB_F_MESSAGE_WQBUFFER_READ) {
1565                 buf1 = malloc(128, M_DEVBUF, M_NOWAIT | M_ZERO);
1566                 buf2 = (u_int32_t *)buf1;
1567                 if( buf1 == NULL)
1568                         return;
1569
1570                 acb->acb_flags &= (~ACB_F_MESSAGE_WQBUFFER_READ);
1571                 pwbuffer = arcmsr_get_iop_wqbuffer(acb);
1572                 iop_data = (u_int32_t *)pwbuffer->data;
1573                 while((acb->wqbuf_firstindex != acb->wqbuf_lastindex) 
1574                         && (allxfer_len < 124)) {
1575                         pQbuffer = &acb->wqbuffer[acb->wqbuf_firstindex];
1576                         *buf1 = *pQbuffer;
1577                         acb->wqbuf_firstindex++;
1578                         acb->wqbuf_firstindex %= ARCMSR_MAX_QBUFFER;
1579                         buf1++;
1580                         allxfer_len++;
1581                 }
1582                 pwbuffer->data_len = allxfer_len;
1583                 data_len = allxfer_len;
1584                 buf1 = (u_int8_t *)buf2;
1585                 while(data_len >= 4)
1586                 {
1587                         *iop_data++ = *buf2++;
1588                         data_len -= 4;
1589                 }
1590                 if(data_len)
1591                         *iop_data = *buf2;
1592                 free( buf1, M_DEVBUF);
1593                 arcmsr_iop_message_wrote(acb);
1594         }
1595 }
1596 /*
1597 **********************************************************************
1598 **********************************************************************
1599 */
1600 static void arcmsr_Write_data_2iop_wqbuffer(struct AdapterControlBlock *acb)
1601 {
1602         u_int8_t *pQbuffer;
1603         struct QBUFFER *pwbuffer;
1604         u_int8_t *iop_data;
1605         int32_t allxfer_len=0;
1606
1607         if(acb->adapter_type >= ACB_ADAPTER_TYPE_B) {
1608                 arcmsr_Write_data_2iop_wqbuffer_D(acb);
1609                 return;
1610         }
1611         if(acb->acb_flags & ACB_F_MESSAGE_WQBUFFER_READ) {
1612                 acb->acb_flags &= (~ACB_F_MESSAGE_WQBUFFER_READ);
1613                 pwbuffer = arcmsr_get_iop_wqbuffer(acb);
1614                 iop_data = (u_int8_t *)pwbuffer->data;
1615                 while((acb->wqbuf_firstindex != acb->wqbuf_lastindex) 
1616                         && (allxfer_len < 124)) {
1617                         pQbuffer = &acb->wqbuffer[acb->wqbuf_firstindex];
1618                         *iop_data = *pQbuffer;
1619                         acb->wqbuf_firstindex++;
1620                         acb->wqbuf_firstindex %= ARCMSR_MAX_QBUFFER;
1621                         iop_data++;
1622                         allxfer_len++;
1623                 }
1624                 pwbuffer->data_len = allxfer_len;
1625                 arcmsr_iop_message_wrote(acb);
1626         }
1627 }
1628 /*
1629 **************************************************************************
1630 **************************************************************************
1631 */
1632 static void arcmsr_iop2drv_data_read_handle(struct AdapterControlBlock *acb)
1633 {
1634         ARCMSR_LOCK_ACQUIRE(&acb->qbuffer_lock);
1635         acb->acb_flags |= ACB_F_MESSAGE_WQBUFFER_READ;
1636         /*
1637         *****************************************************************
1638         **   check if there are any mail packages from user space program
1639         **   in my post bag, now is the time to send them into Areca's firmware
1640         *****************************************************************
1641         */
1642         if(acb->wqbuf_firstindex != acb->wqbuf_lastindex) {
1643                 arcmsr_Write_data_2iop_wqbuffer(acb);
1644         }
1645         if(acb->wqbuf_firstindex == acb->wqbuf_lastindex) {
1646                 acb->acb_flags |= ACB_F_MESSAGE_WQBUFFER_CLEARED;
1647         }
1648         ARCMSR_LOCK_RELEASE(&acb->qbuffer_lock);
1649 }
1650 /*
1651 **************************************************************************
1652 **************************************************************************
1653 */
1654 static void arcmsr_rescanLun_cb(struct cam_periph *periph, union ccb *ccb)
1655 {
1656 /*
1657         if (ccb->ccb_h.status != CAM_REQ_CMP)
1658                 printf("arcmsr_rescanLun_cb: Rescan Target=%x, lun=%x,"
1659                         "failure status=%x\n", ccb->ccb_h.target_id,
1660                         ccb->ccb_h.target_lun, ccb->ccb_h.status);
1661         else
1662                 printf("arcmsr_rescanLun_cb: Rescan lun successfully!\n");
1663 */
1664         xpt_free_path(ccb->ccb_h.path);
1665         xpt_free_ccb(ccb);
1666 }
1667
1668 static void     arcmsr_rescan_lun(struct AdapterControlBlock *acb, int target, int lun)
1669 {
1670         struct cam_path     *path;
1671         union ccb           *ccb;
1672
1673         if ((ccb = (union ccb *)xpt_alloc_ccb_nowait()) == NULL)
1674                         return;
1675         if (xpt_create_path(&path, NULL, cam_sim_path(acb->psim), target, lun) != CAM_REQ_CMP)
1676         {
1677                 xpt_free_ccb(ccb);
1678                 return;
1679         }
1680 /*      printf("arcmsr_rescan_lun: Rescan Target=%x, Lun=%x\n", target, lun); */
1681         bzero(ccb, sizeof(union ccb));
1682         xpt_setup_ccb(&ccb->ccb_h, path, 5);
1683         ccb->ccb_h.func_code = XPT_SCAN_LUN;
1684         ccb->ccb_h.cbfcnp = arcmsr_rescanLun_cb;
1685         ccb->crcn.flags = CAM_FLAG_NONE;
1686         xpt_action(ccb);
1687 }
1688
1689 static void arcmsr_abort_dr_ccbs(struct AdapterControlBlock *acb, int target, int lun)
1690 {
1691         struct CommandControlBlock *srb;
1692         u_int32_t intmask_org;
1693         int i;
1694
1695         /* disable all outbound interrupts */
1696         intmask_org = arcmsr_disable_allintr(acb);
1697         for (i = 0; i < ARCMSR_MAX_FREESRB_NUM; i++)
1698         {
1699                 srb = acb->psrb_pool[i];
1700                 if (srb->srb_state == ARCMSR_SRB_START)
1701                 {
1702                         if((target == srb->pccb->ccb_h.target_id) && (lun == srb->pccb->ccb_h.target_lun))
1703                         {
1704                                 srb->srb_state = ARCMSR_SRB_ABORTED;
1705                                 srb->pccb->ccb_h.status |= CAM_REQ_ABORTED;
1706                                 arcmsr_srb_complete(srb, 1);
1707                                 printf("arcmsr%d: abort scsi id %d lun %d srb=%p \n", acb->pci_unit, target, lun, srb);
1708                         }
1709                 }
1710         }
1711         /* enable outbound Post Queue, outbound doorbell Interrupt */
1712         arcmsr_enable_allintr(acb, intmask_org);
1713 }
1714 /*
1715 **************************************************************************
1716 **************************************************************************
1717 */
1718 static void arcmsr_dr_handle(struct AdapterControlBlock *acb) {
1719         u_int32_t       devicemap;
1720         u_int32_t       target, lun;
1721         u_int32_t       deviceMapCurrent[4]={0};
1722         u_int8_t        *pDevMap;
1723
1724         switch (acb->adapter_type) {
1725         case ACB_ADAPTER_TYPE_A:
1726                 devicemap = offsetof(struct HBA_MessageUnit, msgcode_rwbuffer[ARCMSR_FW_DEVMAP_OFFSET]);
1727                 for (target = 0; target < 4; target++) 
1728                 {
1729                         deviceMapCurrent[target]=bus_space_read_4(acb->btag[0], acb->bhandle[0],  devicemap);
1730                         devicemap += 4;
1731                 }
1732                 break;
1733
1734         case ACB_ADAPTER_TYPE_B:
1735                 devicemap = offsetof(struct HBB_RWBUFFER, msgcode_rwbuffer[ARCMSR_FW_DEVMAP_OFFSET]);
1736                 for (target = 0; target < 4; target++) 
1737                 {
1738                         deviceMapCurrent[target]=bus_space_read_4(acb->btag[1], acb->bhandle[1],  devicemap);
1739                         devicemap += 4;
1740                 }
1741                 break;
1742
1743         case ACB_ADAPTER_TYPE_C:
1744                 devicemap = offsetof(struct HBC_MessageUnit, msgcode_rwbuffer[ARCMSR_FW_DEVMAP_OFFSET]);
1745                 for (target = 0; target < 4; target++) 
1746                 {
1747                         deviceMapCurrent[target]=bus_space_read_4(acb->btag[0], acb->bhandle[0],  devicemap);
1748                         devicemap += 4;
1749                 }
1750                 break;
1751         case ACB_ADAPTER_TYPE_D:
1752                 devicemap = offsetof(struct HBD_MessageUnit, msgcode_rwbuffer[ARCMSR_FW_DEVMAP_OFFSET]);
1753                 for (target = 0; target < 4; target++) 
1754                 {
1755                         deviceMapCurrent[target]=bus_space_read_4(acb->btag[0], acb->bhandle[0],  devicemap);
1756                         devicemap += 4;
1757                 }
1758                 break;
1759         case ACB_ADAPTER_TYPE_E:
1760                 devicemap = offsetof(struct HBE_MessageUnit, msgcode_rwbuffer[ARCMSR_FW_DEVMAP_OFFSET]);
1761                 for (target = 0; target < 4; target++) 
1762                 {
1763                         deviceMapCurrent[target]=bus_space_read_4(acb->btag[0], acb->bhandle[0],  devicemap);
1764                         devicemap += 4;
1765                 }
1766                 break;
1767         }
1768
1769         if(acb->acb_flags & ACB_F_BUS_HANG_ON)
1770         {
1771                 acb->acb_flags &= ~ACB_F_BUS_HANG_ON;
1772         }
1773         /* 
1774         ** adapter posted CONFIG message 
1775         ** copy the new map, note if there are differences with the current map
1776         */
1777         pDevMap = (u_int8_t     *)&deviceMapCurrent[0];
1778         for (target = 0; target < ARCMSR_MAX_TARGETID - 1; target++) 
1779         {
1780                 if (*pDevMap != acb->device_map[target])
1781                 {
1782                         u_int8_t difference, bit_check;
1783
1784                         difference = *pDevMap ^ acb->device_map[target];
1785                         for(lun=0; lun < ARCMSR_MAX_TARGETLUN; lun++)
1786                         {
1787                                 bit_check = (1 << lun);         /*check bit from 0....31*/
1788                                 if(difference & bit_check)
1789                                 {
1790                                         if(acb->device_map[target] & bit_check)
1791                                         {/* unit departed */
1792                                                 printf("arcmsr_dr_handle: Target=%x, lun=%x, GONE!!!\n",target,lun);
1793                                                 arcmsr_abort_dr_ccbs(acb, target, lun);
1794                                                 arcmsr_rescan_lun(acb, target, lun);
1795                                                 acb->devstate[target][lun] = ARECA_RAID_GONE;
1796                                         }
1797                                         else
1798                                         {/* unit arrived */
1799                                                 printf("arcmsr_dr_handle: Target=%x, lun=%x, Plug-IN!!!\n",target,lun);
1800                                                 arcmsr_rescan_lun(acb, target, lun);
1801                                                 acb->devstate[target][lun] = ARECA_RAID_GOOD;
1802                                         }
1803                                 }
1804                         }
1805 /*                      printf("arcmsr_dr_handle: acb->device_map[%x]=0x%x, deviceMapCurrent[%x]=%x\n",target,acb->device_map[target],target,*pDevMap); */
1806                         acb->device_map[target] = *pDevMap;
1807                 }
1808                 pDevMap++;
1809         }
1810 }
1811 /*
1812 **************************************************************************
1813 **************************************************************************
1814 */
1815 static void arcmsr_hba_message_isr(struct AdapterControlBlock *acb) {
1816         u_int32_t outbound_message;
1817
1818         CHIP_REG_WRITE32(HBA_MessageUnit, 0, outbound_intstatus, ARCMSR_MU_OUTBOUND_MESSAGE0_INT);
1819         outbound_message = CHIP_REG_READ32(HBA_MessageUnit, 0, msgcode_rwbuffer[0]);
1820         if (outbound_message == ARCMSR_SIGNATURE_GET_CONFIG)
1821                 arcmsr_dr_handle( acb );
1822 }
1823 /*
1824 **************************************************************************
1825 **************************************************************************
1826 */
1827 static void arcmsr_hbb_message_isr(struct AdapterControlBlock *acb) {
1828         u_int32_t outbound_message;
1829         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
1830
1831         /* clear interrupts */
1832         WRITE_CHIP_REG32(0, phbbmu->iop2drv_doorbell, ARCMSR_MESSAGE_INT_CLEAR_PATTERN);
1833         outbound_message = CHIP_REG_READ32(HBB_RWBUFFER, 1, msgcode_rwbuffer[0]);
1834         if (outbound_message == ARCMSR_SIGNATURE_GET_CONFIG)
1835                 arcmsr_dr_handle( acb );
1836 }
1837 /*
1838 **************************************************************************
1839 **************************************************************************
1840 */
1841 static void arcmsr_hbc_message_isr(struct AdapterControlBlock *acb) {
1842         u_int32_t outbound_message;
1843
1844         CHIP_REG_WRITE32(HBC_MessageUnit, 0, outbound_doorbell_clear, ARCMSR_HBCMU_IOP2DRV_MESSAGE_CMD_DONE_DOORBELL_CLEAR);
1845         outbound_message = CHIP_REG_READ32(HBC_MessageUnit, 0, msgcode_rwbuffer[0]);
1846         if (outbound_message == ARCMSR_SIGNATURE_GET_CONFIG)
1847                 arcmsr_dr_handle( acb );
1848 }
1849 /*
1850 **************************************************************************
1851 **************************************************************************
1852 */
1853 static void arcmsr_hbd_message_isr(struct AdapterControlBlock *acb) {
1854         u_int32_t outbound_message;
1855
1856         CHIP_REG_WRITE32(HBD_MessageUnit, 0, outbound_doorbell, ARCMSR_HBDMU_IOP2DRV_MESSAGE_CMD_DONE_CLEAR);
1857         outbound_message = CHIP_REG_READ32(HBD_MessageUnit, 0, msgcode_rwbuffer[0]);
1858         if (outbound_message == ARCMSR_SIGNATURE_GET_CONFIG)
1859                 arcmsr_dr_handle( acb );
1860 }
1861 /*
1862 **************************************************************************
1863 **************************************************************************
1864 */
1865 static void arcmsr_hbe_message_isr(struct AdapterControlBlock *acb) {
1866         u_int32_t outbound_message;
1867
1868         CHIP_REG_WRITE32(HBE_MessageUnit, 0, host_int_status, 0);
1869         outbound_message = CHIP_REG_READ32(HBE_MessageUnit, 0, msgcode_rwbuffer[0]);
1870         if (outbound_message == ARCMSR_SIGNATURE_GET_CONFIG)
1871                 arcmsr_dr_handle( acb );
1872 }
1873 /*
1874 **************************************************************************
1875 **************************************************************************
1876 */
1877 static void arcmsr_hba_doorbell_isr(struct AdapterControlBlock *acb)
1878 {
1879         u_int32_t doorbell_status;
1880
1881         /*
1882         *******************************************************************
1883         **  Maybe here we need to check wrqbuffer_lock is lock or not
1884         **  DOORBELL: din! don! 
1885         **  check if there are any mail need to pack from firmware
1886         *******************************************************************
1887         */
1888         doorbell_status = CHIP_REG_READ32(HBA_MessageUnit, 0, outbound_doorbell);
1889         CHIP_REG_WRITE32(HBA_MessageUnit, 0, outbound_doorbell, doorbell_status); /* clear doorbell interrupt */
1890         if(doorbell_status & ARCMSR_OUTBOUND_IOP331_DATA_WRITE_OK) {
1891                 arcmsr_iop2drv_data_wrote_handle(acb);
1892         }
1893         if(doorbell_status & ARCMSR_OUTBOUND_IOP331_DATA_READ_OK) {
1894                 arcmsr_iop2drv_data_read_handle(acb);
1895         }
1896 }
1897 /*
1898 **************************************************************************
1899 **************************************************************************
1900 */
1901 static void arcmsr_hbc_doorbell_isr(struct AdapterControlBlock *acb)
1902 {
1903         u_int32_t doorbell_status;
1904
1905         /*
1906         *******************************************************************
1907         **  Maybe here we need to check wrqbuffer_lock is lock or not
1908         **  DOORBELL: din! don! 
1909         **  check if there are any mail need to pack from firmware
1910         *******************************************************************
1911         */
1912         doorbell_status = CHIP_REG_READ32(HBC_MessageUnit, 0, outbound_doorbell);
1913         CHIP_REG_WRITE32(HBC_MessageUnit, 0, outbound_doorbell_clear, doorbell_status); /* clear doorbell interrupt */
1914         if(doorbell_status & ARCMSR_HBCMU_IOP2DRV_DATA_WRITE_OK) {
1915                 arcmsr_iop2drv_data_wrote_handle(acb);
1916         }
1917         if(doorbell_status & ARCMSR_HBCMU_IOP2DRV_DATA_READ_OK) {
1918                 arcmsr_iop2drv_data_read_handle(acb);
1919         }
1920         if(doorbell_status & ARCMSR_HBCMU_IOP2DRV_MESSAGE_CMD_DONE) {
1921                 arcmsr_hbc_message_isr(acb);    /* messenger of "driver to iop commands" */
1922         }
1923 }
1924 /*
1925 **************************************************************************
1926 **************************************************************************
1927 */
1928 static void arcmsr_hbd_doorbell_isr(struct AdapterControlBlock *acb)
1929 {
1930         u_int32_t doorbell_status;
1931
1932         /*
1933         *******************************************************************
1934         **  Maybe here we need to check wrqbuffer_lock is lock or not
1935         **  DOORBELL: din! don! 
1936         **  check if there are any mail need to pack from firmware
1937         *******************************************************************
1938         */
1939         doorbell_status = CHIP_REG_READ32(HBD_MessageUnit, 0, outbound_doorbell) & ARCMSR_HBDMU_F0_DOORBELL_CAUSE;
1940         if(doorbell_status)
1941                 CHIP_REG_WRITE32(HBD_MessageUnit, 0, outbound_doorbell, doorbell_status); /* clear doorbell interrupt */
1942         while( doorbell_status & ARCMSR_HBDMU_F0_DOORBELL_CAUSE ) {
1943                 if(doorbell_status & ARCMSR_HBDMU_IOP2DRV_DATA_WRITE_OK) {
1944                         arcmsr_iop2drv_data_wrote_handle(acb);
1945                 }
1946                 if(doorbell_status & ARCMSR_HBDMU_IOP2DRV_DATA_READ_OK) {
1947                         arcmsr_iop2drv_data_read_handle(acb);
1948                 }
1949                 if(doorbell_status & ARCMSR_HBDMU_IOP2DRV_MESSAGE_CMD_DONE) {
1950                         arcmsr_hbd_message_isr(acb);    /* messenger of "driver to iop commands" */
1951                 }
1952                 doorbell_status = CHIP_REG_READ32(HBD_MessageUnit, 0, outbound_doorbell) & ARCMSR_HBDMU_F0_DOORBELL_CAUSE;
1953                 if(doorbell_status)
1954                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, outbound_doorbell, doorbell_status); /* clear doorbell interrupt */
1955         }
1956 }
1957 /*
1958 **************************************************************************
1959 **************************************************************************
1960 */
1961 static void arcmsr_hbe_doorbell_isr(struct AdapterControlBlock *acb)
1962 {
1963         u_int32_t doorbell_status, in_doorbell;
1964
1965         /*
1966         *******************************************************************
1967         **  Maybe here we need to check wrqbuffer_lock is lock or not
1968         **  DOORBELL: din! don! 
1969         **  check if there are any mail need to pack from firmware
1970         *******************************************************************
1971         */
1972         in_doorbell = CHIP_REG_READ32(HBE_MessageUnit, 0, iobound_doorbell);
1973         CHIP_REG_WRITE32(HBE_MessageUnit, 0, host_int_status, 0); /* clear doorbell interrupt */
1974         doorbell_status = in_doorbell ^ acb->in_doorbell;
1975         if(doorbell_status & ARCMSR_HBEMU_IOP2DRV_DATA_WRITE_OK) {
1976                 arcmsr_iop2drv_data_wrote_handle(acb);
1977         }
1978         if(doorbell_status & ARCMSR_HBEMU_IOP2DRV_DATA_READ_OK) {
1979                 arcmsr_iop2drv_data_read_handle(acb);
1980         }
1981         if(doorbell_status & ARCMSR_HBEMU_IOP2DRV_MESSAGE_CMD_DONE) {
1982                 arcmsr_hbe_message_isr(acb);    /* messenger of "driver to iop commands" */
1983         }
1984         acb->in_doorbell = in_doorbell;
1985 }
1986 /*
1987 **************************************************************************
1988 **************************************************************************
1989 */
1990 static void arcmsr_hba_postqueue_isr(struct AdapterControlBlock *acb)
1991 {
1992         u_int32_t flag_srb;
1993         u_int16_t error;
1994
1995         /*
1996         *****************************************************************************
1997         **               areca cdb command done
1998         *****************************************************************************
1999         */
2000         bus_dmamap_sync(acb->srb_dmat, acb->srb_dmamap, 
2001                 BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
2002         while((flag_srb = CHIP_REG_READ32(HBA_MessageUnit, 
2003                 0, outbound_queueport)) != 0xFFFFFFFF) {
2004                 /* check if command done with no error*/
2005         error = (flag_srb & ARCMSR_SRBREPLY_FLAG_ERROR_MODE0) ? TRUE : FALSE;
2006                 arcmsr_drain_donequeue(acb, flag_srb, error);
2007         }       /*drain reply FIFO*/
2008 }
2009 /*
2010 **************************************************************************
2011 **************************************************************************
2012 */
2013 static void arcmsr_hbb_postqueue_isr(struct AdapterControlBlock *acb)
2014 {
2015         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
2016         u_int32_t flag_srb;
2017         int index;
2018         u_int16_t error;
2019
2020         /*
2021         *****************************************************************************
2022         **               areca cdb command done
2023         *****************************************************************************
2024         */
2025         bus_dmamap_sync(acb->srb_dmat, acb->srb_dmamap, 
2026                 BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
2027         index = phbbmu->doneq_index;
2028         while((flag_srb = phbbmu->done_qbuffer[index]) != 0) {
2029                 phbbmu->done_qbuffer[index] = 0;
2030                 index++;
2031                 index %= ARCMSR_MAX_HBB_POSTQUEUE;     /*if last index number set it to 0 */
2032                 phbbmu->doneq_index = index;
2033                 /* check if command done with no error*/
2034         error = (flag_srb & ARCMSR_SRBREPLY_FLAG_ERROR_MODE0)?TRUE:FALSE;
2035                 arcmsr_drain_donequeue(acb, flag_srb, error);
2036         }       /*drain reply FIFO*/
2037 }
2038 /*
2039 **************************************************************************
2040 **************************************************************************
2041 */
2042 static void arcmsr_hbc_postqueue_isr(struct AdapterControlBlock *acb)
2043 {
2044         u_int32_t flag_srb,throttling = 0;
2045         u_int16_t error;
2046
2047         /*
2048         *****************************************************************************
2049         **               areca cdb command done
2050         *****************************************************************************
2051         */
2052         bus_dmamap_sync(acb->srb_dmat, acb->srb_dmamap, BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
2053         do {
2054                 flag_srb = CHIP_REG_READ32(HBC_MessageUnit, 0, outbound_queueport_low);
2055                 if (flag_srb == 0xFFFFFFFF)
2056                         break;
2057                 /* check if command done with no error*/
2058                 error = (flag_srb & ARCMSR_SRBREPLY_FLAG_ERROR_MODE1)?TRUE:FALSE;
2059                 arcmsr_drain_donequeue(acb, flag_srb, error);
2060                 throttling++;
2061                 if(throttling == ARCMSR_HBC_ISR_THROTTLING_LEVEL) {
2062                         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_doorbell,ARCMSR_HBCMU_DRV2IOP_POSTQUEUE_THROTTLING);
2063                         throttling = 0;
2064                 }
2065         } while(CHIP_REG_READ32(HBC_MessageUnit, 0, host_int_status) & ARCMSR_HBCMU_OUTBOUND_POSTQUEUE_ISR);
2066 }
2067 /*
2068 **********************************************************************
2069 ** 
2070 **********************************************************************
2071 */
2072 static uint16_t arcmsr_get_doneq_index(struct HBD_MessageUnit0 *phbdmu)
2073 {
2074         uint16_t doneq_index, index_stripped;
2075
2076         doneq_index = phbdmu->doneq_index;
2077         if (doneq_index & 0x4000) {
2078                 index_stripped = doneq_index & 0xFF;
2079                 index_stripped += 1;
2080                 index_stripped %= ARCMSR_MAX_HBD_POSTQUEUE;
2081                 phbdmu->doneq_index = index_stripped ?
2082                     (index_stripped | 0x4000) : index_stripped;
2083         } else {
2084                 index_stripped = doneq_index;
2085                 index_stripped += 1;
2086                 index_stripped %= ARCMSR_MAX_HBD_POSTQUEUE;
2087                 phbdmu->doneq_index = index_stripped ?
2088                     index_stripped : (index_stripped | 0x4000);
2089         }
2090         return (phbdmu->doneq_index);
2091 }
2092 /*
2093 **************************************************************************
2094 **************************************************************************
2095 */
2096 static void arcmsr_hbd_postqueue_isr(struct AdapterControlBlock *acb)
2097 {
2098         struct HBD_MessageUnit0 *phbdmu = (struct HBD_MessageUnit0 *)acb->pmu;
2099         u_int32_t outbound_write_pointer;
2100         u_int32_t addressLow;
2101         uint16_t doneq_index;
2102         u_int16_t error;
2103         /*
2104         *****************************************************************************
2105         **               areca cdb command done
2106         *****************************************************************************
2107         */
2108         if((CHIP_REG_READ32(HBD_MessageUnit, 0, outboundlist_interrupt_cause) &
2109                 ARCMSR_HBDMU_OUTBOUND_LIST_INTERRUPT) == 0)
2110                 return;
2111         bus_dmamap_sync(acb->srb_dmat, acb->srb_dmamap, 
2112                 BUS_DMASYNC_POSTREAD | BUS_DMASYNC_POSTWRITE);
2113         outbound_write_pointer = phbdmu->done_qbuffer[0].addressLow;
2114         doneq_index = phbdmu->doneq_index;
2115         while ((doneq_index & 0xFF) != (outbound_write_pointer & 0xFF)) {
2116                 doneq_index = arcmsr_get_doneq_index(phbdmu);
2117                 addressLow = phbdmu->done_qbuffer[(doneq_index & 0xFF)+1].addressLow;
2118                 error = (addressLow & ARCMSR_SRBREPLY_FLAG_ERROR_MODE1) ? TRUE : FALSE;
2119                 arcmsr_drain_donequeue(acb, addressLow, error); /*Check if command done with no error */
2120                 CHIP_REG_WRITE32(HBD_MessageUnit, 0, outboundlist_read_pointer, doneq_index);
2121                 outbound_write_pointer = phbdmu->done_qbuffer[0].addressLow;
2122         }
2123         CHIP_REG_WRITE32(HBD_MessageUnit, 0, outboundlist_interrupt_cause, ARCMSR_HBDMU_OUTBOUND_LIST_INTERRUPT_CLEAR);
2124         CHIP_REG_READ32(HBD_MessageUnit, 0, outboundlist_interrupt_cause); /*Dummy ioread32 to force pci flush */
2125 }
2126 /*
2127 **************************************************************************
2128 **************************************************************************
2129 */
2130 static void arcmsr_hbe_postqueue_isr(struct AdapterControlBlock *acb)
2131 {
2132         u_int16_t error;
2133         uint32_t doneq_index;
2134         uint16_t cmdSMID;
2135
2136         /*
2137         *****************************************************************************
2138         **               areca cdb command done
2139         *****************************************************************************
2140         */
2141         bus_dmamap_sync(acb->srb_dmat, acb->srb_dmamap, BUS_DMASYNC_POSTREAD | BUS_DMASYNC_POSTWRITE);
2142         doneq_index = acb->doneq_index;
2143         while ((CHIP_REG_READ32(HBE_MessageUnit, 0, reply_post_producer_index) & 0xFFFF) != doneq_index) {
2144                 cmdSMID = acb->pCompletionQ[doneq_index].cmdSMID;
2145                 error = (acb->pCompletionQ[doneq_index].cmdFlag & ARCMSR_SRBREPLY_FLAG_ERROR_MODE1) ? TRUE : FALSE;
2146                 arcmsr_drain_donequeue(acb, (u_int32_t)cmdSMID, error);
2147                 doneq_index++;
2148                 if (doneq_index >= acb->completionQ_entry)
2149                         doneq_index = 0;
2150         }
2151         acb->doneq_index = doneq_index;
2152         CHIP_REG_WRITE32(HBE_MessageUnit, 0, reply_post_consumer_index, doneq_index);
2153 }
2154 /*
2155 **********************************************************************
2156 **********************************************************************
2157 */
2158 static void arcmsr_handle_hba_isr( struct AdapterControlBlock *acb)
2159 {
2160         u_int32_t outbound_intStatus;
2161         /*
2162         *********************************************
2163         **   check outbound intstatus 
2164         *********************************************
2165         */
2166         outbound_intStatus = CHIP_REG_READ32(HBA_MessageUnit, 0, outbound_intstatus) & acb->outbound_int_enable;
2167         if(!outbound_intStatus) {
2168                 /*it must be share irq*/
2169                 return;
2170         }
2171         CHIP_REG_WRITE32(HBA_MessageUnit, 0, outbound_intstatus, outbound_intStatus); /*clear interrupt*/
2172         /* MU doorbell interrupts*/
2173         if(outbound_intStatus & ARCMSR_MU_OUTBOUND_DOORBELL_INT) {
2174                 arcmsr_hba_doorbell_isr(acb);
2175         }
2176         /* MU post queue interrupts*/
2177         if(outbound_intStatus & ARCMSR_MU_OUTBOUND_POSTQUEUE_INT) {
2178                 arcmsr_hba_postqueue_isr(acb);
2179         }
2180         if(outbound_intStatus & ARCMSR_MU_OUTBOUND_MESSAGE0_INT) {
2181                 arcmsr_hba_message_isr(acb);
2182         }
2183 }
2184 /*
2185 **********************************************************************
2186 **********************************************************************
2187 */
2188 static void arcmsr_handle_hbb_isr( struct AdapterControlBlock *acb)
2189 {
2190         u_int32_t outbound_doorbell;
2191         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
2192         /*
2193         *********************************************
2194         **   check outbound intstatus 
2195         *********************************************
2196         */
2197         outbound_doorbell = READ_CHIP_REG32(0, phbbmu->iop2drv_doorbell) & acb->outbound_int_enable;
2198         if(!outbound_doorbell) {
2199                 /*it must be share irq*/
2200                 return;
2201         }
2202         WRITE_CHIP_REG32(0, phbbmu->iop2drv_doorbell, ~outbound_doorbell); /* clear doorbell interrupt */
2203         READ_CHIP_REG32(0, phbbmu->iop2drv_doorbell);
2204         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_DRV2IOP_END_OF_INTERRUPT);
2205         /* MU ioctl transfer doorbell interrupts*/
2206         if(outbound_doorbell & ARCMSR_IOP2DRV_DATA_WRITE_OK) {
2207                 arcmsr_iop2drv_data_wrote_handle(acb);
2208         }
2209         if(outbound_doorbell & ARCMSR_IOP2DRV_DATA_READ_OK) {
2210                 arcmsr_iop2drv_data_read_handle(acb);
2211         }
2212         /* MU post queue interrupts*/
2213         if(outbound_doorbell & ARCMSR_IOP2DRV_CDB_DONE) {
2214                 arcmsr_hbb_postqueue_isr(acb);
2215         }
2216         if(outbound_doorbell & ARCMSR_IOP2DRV_MESSAGE_CMD_DONE) {
2217                 arcmsr_hbb_message_isr(acb);
2218         }
2219 }
2220 /*
2221 **********************************************************************
2222 **********************************************************************
2223 */
2224 static void arcmsr_handle_hbc_isr( struct AdapterControlBlock *acb)
2225 {
2226         u_int32_t host_interrupt_status;
2227         /*
2228         *********************************************
2229         **   check outbound intstatus 
2230         *********************************************
2231         */
2232         host_interrupt_status = CHIP_REG_READ32(HBC_MessageUnit, 0, host_int_status) &
2233                 (ARCMSR_HBCMU_OUTBOUND_POSTQUEUE_ISR |
2234                 ARCMSR_HBCMU_OUTBOUND_DOORBELL_ISR);
2235         if(!host_interrupt_status) {
2236                 /*it must be share irq*/
2237                 return;
2238         }
2239         do {
2240                 /* MU doorbell interrupts*/
2241                 if(host_interrupt_status & ARCMSR_HBCMU_OUTBOUND_DOORBELL_ISR) {
2242                         arcmsr_hbc_doorbell_isr(acb);
2243                 }
2244                 /* MU post queue interrupts*/
2245                 if(host_interrupt_status & ARCMSR_HBCMU_OUTBOUND_POSTQUEUE_ISR) {
2246                         arcmsr_hbc_postqueue_isr(acb);
2247                 }
2248                 host_interrupt_status = CHIP_REG_READ32(HBC_MessageUnit, 0, host_int_status);
2249         } while (host_interrupt_status & (ARCMSR_HBCMU_OUTBOUND_POSTQUEUE_ISR | ARCMSR_HBCMU_OUTBOUND_DOORBELL_ISR));
2250 }
2251 /*
2252 **********************************************************************
2253 **********************************************************************
2254 */
2255 static void arcmsr_handle_hbd_isr( struct AdapterControlBlock *acb)
2256 {
2257         u_int32_t host_interrupt_status;
2258         u_int32_t intmask_org;
2259         /*
2260         *********************************************
2261         **   check outbound intstatus 
2262         *********************************************
2263         */
2264         host_interrupt_status = CHIP_REG_READ32(HBD_MessageUnit, 0, host_int_status) & acb->outbound_int_enable;
2265         if(!(host_interrupt_status & ARCMSR_HBDMU_OUTBOUND_INT)) {
2266                 /*it must be share irq*/
2267                 return;
2268         }
2269         /* disable outbound interrupt */
2270         intmask_org = CHIP_REG_READ32(HBD_MessageUnit, 0, pcief0_int_enable)    ; /* disable outbound message0 int */
2271         CHIP_REG_WRITE32(HBD_MessageUnit, 0, pcief0_int_enable, ARCMSR_HBDMU_ALL_INT_DISABLE);
2272         /* MU doorbell interrupts*/
2273         if(host_interrupt_status & ARCMSR_HBDMU_OUTBOUND_DOORBELL_INT) {
2274                 arcmsr_hbd_doorbell_isr(acb);
2275         }
2276         /* MU post queue interrupts*/
2277         if(host_interrupt_status & ARCMSR_HBDMU_OUTBOUND_POSTQUEUE_INT) {
2278                 arcmsr_hbd_postqueue_isr(acb);
2279         }
2280         /* enable all outbound interrupt */
2281         CHIP_REG_WRITE32(HBD_MessageUnit, 0, pcief0_int_enable, intmask_org | ARCMSR_HBDMU_ALL_INT_ENABLE);
2282 //      CHIP_REG_READ32(HBD_MessageUnit, 0, pcief0_int_enable);
2283 }
2284 /*
2285 **********************************************************************
2286 **********************************************************************
2287 */
2288 static void arcmsr_handle_hbe_isr( struct AdapterControlBlock *acb)
2289 {
2290         u_int32_t host_interrupt_status;
2291         /*
2292         *********************************************
2293         **   check outbound intstatus 
2294         *********************************************
2295         */
2296         host_interrupt_status = CHIP_REG_READ32(HBE_MessageUnit, 0, host_int_status) &
2297                 (ARCMSR_HBEMU_OUTBOUND_POSTQUEUE_ISR |
2298                 ARCMSR_HBEMU_OUTBOUND_DOORBELL_ISR);
2299         if(!host_interrupt_status) {
2300                 /*it must be share irq*/
2301                 return;
2302         }
2303         do {
2304                 /* MU doorbell interrupts*/
2305                 if(host_interrupt_status & ARCMSR_HBEMU_OUTBOUND_DOORBELL_ISR) {
2306                         arcmsr_hbe_doorbell_isr(acb);
2307                 }
2308                 /* MU post queue interrupts*/
2309                 if(host_interrupt_status & ARCMSR_HBEMU_OUTBOUND_POSTQUEUE_ISR) {
2310                         arcmsr_hbe_postqueue_isr(acb);
2311                 }
2312                 host_interrupt_status = CHIP_REG_READ32(HBE_MessageUnit, 0, host_int_status);
2313         } while (host_interrupt_status & (ARCMSR_HBEMU_OUTBOUND_POSTQUEUE_ISR | ARCMSR_HBEMU_OUTBOUND_DOORBELL_ISR));
2314 }
2315 /*
2316 ******************************************************************************
2317 ******************************************************************************
2318 */
2319 static void arcmsr_interrupt(struct AdapterControlBlock *acb)
2320 {
2321         switch (acb->adapter_type) {
2322         case ACB_ADAPTER_TYPE_A:
2323                 arcmsr_handle_hba_isr(acb);
2324                 break;
2325         case ACB_ADAPTER_TYPE_B:
2326                 arcmsr_handle_hbb_isr(acb);
2327                 break;
2328         case ACB_ADAPTER_TYPE_C:
2329                 arcmsr_handle_hbc_isr(acb);
2330                 break;
2331         case ACB_ADAPTER_TYPE_D:
2332                 arcmsr_handle_hbd_isr(acb);
2333                 break;
2334         case ACB_ADAPTER_TYPE_E:
2335                 arcmsr_handle_hbe_isr(acb);
2336                 break;
2337         default:
2338                 printf("arcmsr%d: interrupt service,"
2339                 " unknown adapter type =%d\n", acb->pci_unit, acb->adapter_type);
2340                 break;
2341         }
2342 }
2343 /*
2344 **********************************************************************
2345 **********************************************************************
2346 */
2347 static void arcmsr_intr_handler(void *arg)
2348 {
2349         struct AdapterControlBlock *acb = (struct AdapterControlBlock *)arg;
2350
2351         ARCMSR_LOCK_ACQUIRE(&acb->isr_lock);
2352         arcmsr_interrupt(acb);
2353         ARCMSR_LOCK_RELEASE(&acb->isr_lock);
2354 }
2355 /*
2356 ******************************************************************************
2357 ******************************************************************************
2358 */
2359 static void     arcmsr_polling_devmap(void *arg)
2360 {
2361         struct AdapterControlBlock *acb = (struct AdapterControlBlock *)arg;
2362         switch (acb->adapter_type) {
2363         case ACB_ADAPTER_TYPE_A:
2364                 CHIP_REG_WRITE32(HBA_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_GET_CONFIG);
2365                 break;
2366
2367         case ACB_ADAPTER_TYPE_B: {
2368                         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
2369                         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_MESSAGE_GET_CONFIG);
2370                 }
2371                 break;
2372
2373         case ACB_ADAPTER_TYPE_C:
2374                 CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_GET_CONFIG);
2375                 CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_doorbell, ARCMSR_HBCMU_DRV2IOP_MESSAGE_CMD_DONE);
2376                 break;
2377
2378         case ACB_ADAPTER_TYPE_D:
2379                 CHIP_REG_WRITE32(HBD_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_GET_CONFIG);
2380                 break;
2381
2382         case ACB_ADAPTER_TYPE_E:
2383                 CHIP_REG_WRITE32(HBE_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_GET_CONFIG);
2384                 acb->out_doorbell ^= ARCMSR_HBEMU_DRV2IOP_MESSAGE_CMD_DONE;
2385                 CHIP_REG_WRITE32(HBE_MessageUnit, 0, iobound_doorbell, acb->out_doorbell);
2386                 break;
2387         }
2388
2389         if((acb->acb_flags & ACB_F_SCSISTOPADAPTER) == 0)
2390         {
2391                 callout_reset(&acb->devmap_callout, 5 * hz, arcmsr_polling_devmap, acb);        /* polling per 5 seconds */
2392         }
2393 }
2394
2395 /*
2396 *******************************************************************************
2397 **
2398 *******************************************************************************
2399 */
2400 static void arcmsr_iop_parking(struct AdapterControlBlock *acb)
2401 {
2402         u_int32_t intmask_org;
2403
2404         if(acb != NULL) {
2405                 /* stop adapter background rebuild */
2406                 if(acb->acb_flags & ACB_F_MSG_START_BGRB) {
2407                         intmask_org = arcmsr_disable_allintr(acb);
2408                         arcmsr_stop_adapter_bgrb(acb);
2409                         arcmsr_flush_adapter_cache(acb);
2410                         arcmsr_enable_allintr(acb, intmask_org);
2411                 }
2412         }
2413 }
2414 /*
2415 ***********************************************************************
2416 **
2417 ************************************************************************
2418 */
2419 static u_int32_t arcmsr_iop_ioctlcmd(struct AdapterControlBlock *acb, u_int32_t ioctl_cmd, caddr_t arg)
2420 {
2421         struct CMD_MESSAGE_FIELD *pcmdmessagefld;
2422         u_int32_t retvalue = EINVAL;
2423
2424         pcmdmessagefld = (struct CMD_MESSAGE_FIELD *) arg;
2425         if(memcmp(pcmdmessagefld->cmdmessage.Signature, "ARCMSR", 6)!=0) {
2426                 return retvalue;
2427         }
2428         ARCMSR_LOCK_ACQUIRE(&acb->qbuffer_lock);
2429         switch(ioctl_cmd) {
2430         case ARCMSR_MESSAGE_READ_RQBUFFER: {
2431                         u_int8_t *pQbuffer;
2432                         u_int8_t *ptmpQbuffer = pcmdmessagefld->messagedatabuffer;                      
2433                         u_int32_t allxfer_len=0;
2434
2435                         while((acb->rqbuf_firstindex != acb->rqbuf_lastindex) 
2436                                 && (allxfer_len < 1031)) {
2437                                 /*copy READ QBUFFER to srb*/
2438                                 pQbuffer = &acb->rqbuffer[acb->rqbuf_firstindex];
2439                                 *ptmpQbuffer = *pQbuffer;
2440                                 acb->rqbuf_firstindex++;
2441                                 acb->rqbuf_firstindex %= ARCMSR_MAX_QBUFFER; 
2442                                 /*if last index number set it to 0 */
2443                                 ptmpQbuffer++;
2444                                 allxfer_len++;
2445                         }
2446                         if(acb->acb_flags & ACB_F_IOPDATA_OVERFLOW) {
2447                                 struct QBUFFER *prbuffer;
2448
2449                                 acb->acb_flags &= ~ACB_F_IOPDATA_OVERFLOW;
2450                                 prbuffer = arcmsr_get_iop_rqbuffer(acb);
2451                                 if(arcmsr_Read_iop_rqbuffer_data(acb, prbuffer) == 0)
2452                                         acb->acb_flags |= ACB_F_IOPDATA_OVERFLOW;
2453                         }
2454                         pcmdmessagefld->cmdmessage.Length = allxfer_len;
2455                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_OK;
2456                         retvalue = ARCMSR_MESSAGE_SUCCESS;
2457                 }
2458                 break;
2459         case ARCMSR_MESSAGE_WRITE_WQBUFFER: {
2460                         u_int32_t my_empty_len, user_len, wqbuf_firstindex, wqbuf_lastindex;
2461                         u_int8_t *pQbuffer;
2462                         u_int8_t *ptmpuserbuffer = pcmdmessagefld->messagedatabuffer;
2463
2464                         user_len = pcmdmessagefld->cmdmessage.Length;
2465                         /*check if data xfer length of this request will overflow my array qbuffer */
2466                         wqbuf_lastindex = acb->wqbuf_lastindex;
2467                         wqbuf_firstindex = acb->wqbuf_firstindex;
2468                         if(wqbuf_lastindex != wqbuf_firstindex) {
2469                                 arcmsr_Write_data_2iop_wqbuffer(acb);
2470                                 pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_ERROR;
2471                         } else {
2472                                 my_empty_len = (wqbuf_firstindex - wqbuf_lastindex - 1) &
2473                                         (ARCMSR_MAX_QBUFFER - 1);
2474                                 if(my_empty_len >= user_len) {
2475                                         while(user_len > 0) {
2476                                                 /*copy srb data to wqbuffer*/
2477                                                 pQbuffer = &acb->wqbuffer[acb->wqbuf_lastindex];
2478                                                 *pQbuffer = *ptmpuserbuffer;
2479                                                 acb->wqbuf_lastindex++;
2480                                                 acb->wqbuf_lastindex %= ARCMSR_MAX_QBUFFER;
2481                                                 /*if last index number set it to 0 */
2482                                                 ptmpuserbuffer++;
2483                                                 user_len--;
2484                                         }
2485                                         /*post fist Qbuffer*/
2486                                         if(acb->acb_flags & ACB_F_MESSAGE_WQBUFFER_CLEARED) {
2487                                                 acb->acb_flags &= ~ACB_F_MESSAGE_WQBUFFER_CLEARED;
2488                                                 arcmsr_Write_data_2iop_wqbuffer(acb);
2489                                         }
2490                                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_OK;
2491                                 } else {
2492                                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_ERROR;
2493                                 }
2494                         }
2495                         retvalue = ARCMSR_MESSAGE_SUCCESS;
2496                 }
2497                 break;
2498         case ARCMSR_MESSAGE_CLEAR_RQBUFFER: {
2499                         u_int8_t *pQbuffer = acb->rqbuffer;
2500
2501                         if(acb->acb_flags & ACB_F_IOPDATA_OVERFLOW) {
2502                                 acb->acb_flags &= ~ACB_F_IOPDATA_OVERFLOW;
2503                                 arcmsr_iop_message_read(acb);
2504                                 /*signature, let IOP know data has been readed */
2505                         }
2506                         acb->acb_flags |= ACB_F_MESSAGE_RQBUFFER_CLEARED;
2507                         acb->rqbuf_firstindex = 0;
2508                         acb->rqbuf_lastindex = 0;
2509                         memset(pQbuffer, 0, ARCMSR_MAX_QBUFFER);
2510                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_OK;
2511                         retvalue = ARCMSR_MESSAGE_SUCCESS;
2512                 }
2513                 break;
2514         case ARCMSR_MESSAGE_CLEAR_WQBUFFER:
2515                 {
2516                         u_int8_t *pQbuffer = acb->wqbuffer;
2517
2518                         if(acb->acb_flags & ACB_F_IOPDATA_OVERFLOW) {
2519                                 acb->acb_flags &= ~ACB_F_IOPDATA_OVERFLOW;
2520                                 arcmsr_iop_message_read(acb);
2521                                 /*signature, let IOP know data has been readed */
2522                         }
2523                         acb->acb_flags |= (ACB_F_MESSAGE_WQBUFFER_CLEARED|ACB_F_MESSAGE_WQBUFFER_READ);
2524                         acb->wqbuf_firstindex = 0;
2525                         acb->wqbuf_lastindex = 0;
2526                         memset(pQbuffer, 0, ARCMSR_MAX_QBUFFER);
2527                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_OK;
2528                         retvalue = ARCMSR_MESSAGE_SUCCESS;
2529                 }
2530                 break;
2531         case ARCMSR_MESSAGE_CLEAR_ALLQBUFFER: {
2532                         u_int8_t *pQbuffer;
2533
2534                         if(acb->acb_flags & ACB_F_IOPDATA_OVERFLOW) {
2535                                 acb->acb_flags &= ~ACB_F_IOPDATA_OVERFLOW;
2536                                 arcmsr_iop_message_read(acb);
2537                                 /*signature, let IOP know data has been readed */
2538                         }
2539                         acb->acb_flags  |= (ACB_F_MESSAGE_WQBUFFER_CLEARED
2540                                         |ACB_F_MESSAGE_RQBUFFER_CLEARED
2541                                         |ACB_F_MESSAGE_WQBUFFER_READ);
2542                         acb->rqbuf_firstindex = 0;
2543                         acb->rqbuf_lastindex = 0;
2544                         acb->wqbuf_firstindex = 0;
2545                         acb->wqbuf_lastindex = 0;
2546                         pQbuffer = acb->rqbuffer;
2547                         memset(pQbuffer, 0, sizeof(struct QBUFFER));
2548                         pQbuffer = acb->wqbuffer;
2549                         memset(pQbuffer, 0, sizeof(struct QBUFFER));
2550                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_OK;
2551                         retvalue = ARCMSR_MESSAGE_SUCCESS;
2552                 }
2553                 break;
2554         case ARCMSR_MESSAGE_REQUEST_RETURNCODE_3F: {
2555                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_3F;
2556                         retvalue = ARCMSR_MESSAGE_SUCCESS;
2557                 }
2558                 break;
2559         case ARCMSR_MESSAGE_SAY_HELLO: {
2560                         u_int8_t *hello_string = "Hello! I am ARCMSR";
2561                         u_int8_t *puserbuffer = (u_int8_t *)pcmdmessagefld->messagedatabuffer;
2562
2563                         if(memcpy(puserbuffer, hello_string, (int16_t)strlen(hello_string))) {
2564                                 pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_ERROR;
2565                                 ARCMSR_LOCK_RELEASE(&acb->qbuffer_lock);
2566                                 return ENOIOCTL;
2567                         }
2568                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_OK;
2569                         retvalue = ARCMSR_MESSAGE_SUCCESS;
2570                 }
2571                 break;
2572         case ARCMSR_MESSAGE_SAY_GOODBYE: {
2573                         arcmsr_iop_parking(acb);
2574                         retvalue = ARCMSR_MESSAGE_SUCCESS;
2575                 }
2576                 break;
2577         case ARCMSR_MESSAGE_FLUSH_ADAPTER_CACHE: {
2578                         arcmsr_flush_adapter_cache(acb);
2579                         retvalue = ARCMSR_MESSAGE_SUCCESS;
2580                 }
2581                 break;
2582         }
2583         ARCMSR_LOCK_RELEASE(&acb->qbuffer_lock);
2584         return (retvalue);
2585 }
2586 /*
2587 **************************************************************************
2588 **************************************************************************
2589 */
2590 static void arcmsr_free_srb(struct CommandControlBlock *srb)
2591 {
2592         struct AdapterControlBlock      *acb;
2593
2594         acb = srb->acb;
2595         ARCMSR_LOCK_ACQUIRE(&acb->srb_lock);
2596         srb->srb_state = ARCMSR_SRB_DONE;
2597         srb->srb_flags = 0;
2598         acb->srbworkingQ[acb->workingsrb_doneindex] = srb;
2599         acb->workingsrb_doneindex++;
2600         acb->workingsrb_doneindex %= ARCMSR_MAX_FREESRB_NUM;
2601         ARCMSR_LOCK_RELEASE(&acb->srb_lock);
2602 }
2603 /*
2604 **************************************************************************
2605 **************************************************************************
2606 */
2607 static struct CommandControlBlock *arcmsr_get_freesrb(struct AdapterControlBlock *acb)
2608 {
2609         struct CommandControlBlock *srb = NULL;
2610         u_int32_t workingsrb_startindex, workingsrb_doneindex;
2611
2612         ARCMSR_LOCK_ACQUIRE(&acb->srb_lock);
2613         workingsrb_doneindex = acb->workingsrb_doneindex;
2614         workingsrb_startindex = acb->workingsrb_startindex;
2615         srb = acb->srbworkingQ[workingsrb_startindex];
2616         workingsrb_startindex++;
2617         workingsrb_startindex %= ARCMSR_MAX_FREESRB_NUM;
2618         if(workingsrb_doneindex != workingsrb_startindex) {
2619                 acb->workingsrb_startindex = workingsrb_startindex;
2620         } else {
2621                 srb = NULL;
2622         }
2623         ARCMSR_LOCK_RELEASE(&acb->srb_lock);
2624         return(srb);
2625 }
2626 /*
2627 **************************************************************************
2628 **************************************************************************
2629 */
2630 static int arcmsr_iop_message_xfer(struct AdapterControlBlock *acb, union ccb *pccb)
2631 {
2632         struct CMD_MESSAGE_FIELD *pcmdmessagefld;
2633         int retvalue = 0, transfer_len = 0;
2634         char *buffer;
2635         uint8_t *ptr = scsiio_cdb_ptr(&pccb->csio);
2636         u_int32_t controlcode = (u_int32_t ) ptr[5] << 24 |
2637                                 (u_int32_t ) ptr[6] << 16 |
2638                                 (u_int32_t ) ptr[7] << 8  |
2639                                 (u_int32_t ) ptr[8];
2640                                         /* 4 bytes: Areca io control code */
2641         if ((pccb->ccb_h.flags & CAM_DATA_MASK) == CAM_DATA_VADDR) {
2642                 buffer = pccb->csio.data_ptr;
2643                 transfer_len = pccb->csio.dxfer_len;
2644         } else {
2645                 retvalue = ARCMSR_MESSAGE_FAIL;
2646                 goto message_out;
2647         }
2648         if (transfer_len > sizeof(struct CMD_MESSAGE_FIELD)) {
2649                 retvalue = ARCMSR_MESSAGE_FAIL;
2650                 goto message_out;
2651         }
2652         pcmdmessagefld = (struct CMD_MESSAGE_FIELD *) buffer;
2653         switch(controlcode) {
2654         case ARCMSR_MESSAGE_READ_RQBUFFER: {
2655                         u_int8_t *pQbuffer;
2656                         u_int8_t *ptmpQbuffer = pcmdmessagefld->messagedatabuffer;
2657                         int32_t allxfer_len = 0;
2658
2659                         ARCMSR_LOCK_ACQUIRE(&acb->qbuffer_lock);
2660                         while ((acb->rqbuf_firstindex != acb->rqbuf_lastindex)
2661                                 && (allxfer_len < 1031)) {
2662                                 pQbuffer = &acb->rqbuffer[acb->rqbuf_firstindex];
2663                                 *ptmpQbuffer = *pQbuffer;
2664                                 acb->rqbuf_firstindex++;
2665                                 acb->rqbuf_firstindex %= ARCMSR_MAX_QBUFFER;
2666                                 ptmpQbuffer++;
2667                                 allxfer_len++;
2668                         }
2669                         if (acb->acb_flags & ACB_F_IOPDATA_OVERFLOW) {
2670                                 struct QBUFFER  *prbuffer;
2671
2672                                 acb->acb_flags &= ~ACB_F_IOPDATA_OVERFLOW;
2673                                 prbuffer = arcmsr_get_iop_rqbuffer(acb);
2674                                 if(arcmsr_Read_iop_rqbuffer_data(acb, prbuffer) == 0)
2675                                         acb->acb_flags |= ACB_F_IOPDATA_OVERFLOW;
2676                         }
2677                         pcmdmessagefld->cmdmessage.Length = allxfer_len;
2678                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_OK;
2679                         retvalue = ARCMSR_MESSAGE_SUCCESS;
2680                         ARCMSR_LOCK_RELEASE(&acb->qbuffer_lock);
2681                 }
2682                 break;
2683         case ARCMSR_MESSAGE_WRITE_WQBUFFER: {
2684                         int32_t my_empty_len, user_len, wqbuf_firstindex, wqbuf_lastindex;
2685                         u_int8_t *pQbuffer;
2686                         u_int8_t *ptmpuserbuffer = pcmdmessagefld->messagedatabuffer;
2687
2688                         user_len = pcmdmessagefld->cmdmessage.Length;
2689                         ARCMSR_LOCK_ACQUIRE(&acb->qbuffer_lock);
2690                         wqbuf_lastindex = acb->wqbuf_lastindex;
2691                         wqbuf_firstindex = acb->wqbuf_firstindex;
2692                         if (wqbuf_lastindex != wqbuf_firstindex) {
2693                                 arcmsr_Write_data_2iop_wqbuffer(acb);
2694                                 /* has error report sensedata */
2695                                 if(pccb->csio.sense_len) {
2696                                 ((u_int8_t *)&pccb->csio.sense_data)[0] = (0x1 << 7 | 0x70); 
2697                                 /* Valid,ErrorCode */
2698                                 ((u_int8_t *)&pccb->csio.sense_data)[2] = 0x05; 
2699                                 /* FileMark,EndOfMedia,IncorrectLength,Reserved,SenseKey */
2700                                 ((u_int8_t *)&pccb->csio.sense_data)[7] = 0x0A; 
2701                                 /* AdditionalSenseLength */
2702                                 ((u_int8_t *)&pccb->csio.sense_data)[12] = 0x20; 
2703                                 /* AdditionalSenseCode */
2704                                 }
2705                                 retvalue = ARCMSR_MESSAGE_FAIL;
2706                         } else {
2707                                 my_empty_len = (wqbuf_firstindex-wqbuf_lastindex - 1)
2708                                                 &(ARCMSR_MAX_QBUFFER - 1);
2709                                 if (my_empty_len >= user_len) {
2710                                         while (user_len > 0) {
2711                                                 pQbuffer = &acb->wqbuffer[acb->wqbuf_lastindex];
2712                                                 *pQbuffer = *ptmpuserbuffer;
2713                                                 acb->wqbuf_lastindex++;
2714                                                 acb->wqbuf_lastindex %= ARCMSR_MAX_QBUFFER;
2715                                                 ptmpuserbuffer++;
2716                                                 user_len--;
2717                                         }
2718                                         if (acb->acb_flags & ACB_F_MESSAGE_WQBUFFER_CLEARED) {
2719                                                 acb->acb_flags &=
2720                                                     ~ACB_F_MESSAGE_WQBUFFER_CLEARED;
2721                                                 arcmsr_Write_data_2iop_wqbuffer(acb);
2722                                         }
2723                                 } else {
2724                                         /* has error report sensedata */
2725                                         if(pccb->csio.sense_len) {
2726                                         ((u_int8_t *)&pccb->csio.sense_data)[0] = (0x1 << 7 | 0x70);
2727                                         /* Valid,ErrorCode */
2728                                         ((u_int8_t *)&pccb->csio.sense_data)[2] = 0x05; 
2729                                         /* FileMark,EndOfMedia,IncorrectLength,Reserved,SenseKey */
2730                                         ((u_int8_t *)&pccb->csio.sense_data)[7] = 0x0A; 
2731                                         /* AdditionalSenseLength */
2732                                         ((u_int8_t *)&pccb->csio.sense_data)[12] = 0x20; 
2733                                         /* AdditionalSenseCode */
2734                                         }
2735                                         retvalue = ARCMSR_MESSAGE_FAIL;
2736                                 }
2737                         }
2738                         ARCMSR_LOCK_RELEASE(&acb->qbuffer_lock);
2739                 }
2740                 break;
2741         case ARCMSR_MESSAGE_CLEAR_RQBUFFER: {
2742                         u_int8_t *pQbuffer = acb->rqbuffer;
2743
2744                         ARCMSR_LOCK_ACQUIRE(&acb->qbuffer_lock);
2745                         if (acb->acb_flags & ACB_F_IOPDATA_OVERFLOW) {
2746                                 acb->acb_flags &= ~ACB_F_IOPDATA_OVERFLOW;
2747                                 arcmsr_iop_message_read(acb);
2748                         }
2749                         acb->acb_flags |= ACB_F_MESSAGE_RQBUFFER_CLEARED;
2750                         acb->rqbuf_firstindex = 0;
2751                         acb->rqbuf_lastindex = 0;
2752                         memset(pQbuffer, 0, ARCMSR_MAX_QBUFFER);
2753                         pcmdmessagefld->cmdmessage.ReturnCode =
2754                             ARCMSR_MESSAGE_RETURNCODE_OK;
2755                         ARCMSR_LOCK_RELEASE(&acb->qbuffer_lock);
2756                 }
2757                 break;
2758         case ARCMSR_MESSAGE_CLEAR_WQBUFFER: {
2759                         u_int8_t *pQbuffer = acb->wqbuffer;
2760
2761                         ARCMSR_LOCK_ACQUIRE(&acb->qbuffer_lock);
2762                         if (acb->acb_flags & ACB_F_IOPDATA_OVERFLOW) {
2763                                 acb->acb_flags &= ~ACB_F_IOPDATA_OVERFLOW;
2764                                 arcmsr_iop_message_read(acb);
2765                         }
2766                         acb->acb_flags |=
2767                                 (ACB_F_MESSAGE_WQBUFFER_CLEARED |
2768                                         ACB_F_MESSAGE_WQBUFFER_READ);
2769                         acb->wqbuf_firstindex = 0;
2770                         acb->wqbuf_lastindex = 0;
2771                         memset(pQbuffer, 0, ARCMSR_MAX_QBUFFER);
2772                         pcmdmessagefld->cmdmessage.ReturnCode =
2773                                 ARCMSR_MESSAGE_RETURNCODE_OK;
2774                         ARCMSR_LOCK_RELEASE(&acb->qbuffer_lock);
2775                 }
2776                 break;
2777         case ARCMSR_MESSAGE_CLEAR_ALLQBUFFER: {
2778                         u_int8_t *pQbuffer;
2779
2780                         ARCMSR_LOCK_ACQUIRE(&acb->qbuffer_lock);
2781                         if (acb->acb_flags & ACB_F_IOPDATA_OVERFLOW) {
2782                                 acb->acb_flags &= ~ACB_F_IOPDATA_OVERFLOW;
2783                                 arcmsr_iop_message_read(acb);
2784                         }
2785                         acb->acb_flags |=
2786                                 (ACB_F_MESSAGE_WQBUFFER_CLEARED
2787                                 | ACB_F_MESSAGE_RQBUFFER_CLEARED
2788                                 | ACB_F_MESSAGE_WQBUFFER_READ);
2789                         acb->rqbuf_firstindex = 0;
2790                         acb->rqbuf_lastindex = 0;
2791                         acb->wqbuf_firstindex = 0;
2792                         acb->wqbuf_lastindex = 0;
2793                         pQbuffer = acb->rqbuffer;
2794                         memset(pQbuffer, 0, sizeof (struct QBUFFER));
2795                         pQbuffer = acb->wqbuffer;
2796                         memset(pQbuffer, 0, sizeof (struct QBUFFER));
2797                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_OK;
2798                         ARCMSR_LOCK_RELEASE(&acb->qbuffer_lock);
2799                 }
2800                 break;
2801         case ARCMSR_MESSAGE_REQUEST_RETURNCODE_3F: {
2802                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_3F;
2803                 }
2804                 break;
2805         case ARCMSR_MESSAGE_SAY_HELLO: {
2806                         int8_t *hello_string = "Hello! I am ARCMSR";
2807
2808                         memcpy(pcmdmessagefld->messagedatabuffer, hello_string
2809                                 , (int16_t)strlen(hello_string));
2810                         pcmdmessagefld->cmdmessage.ReturnCode = ARCMSR_MESSAGE_RETURNCODE_OK;
2811                 }
2812                 break;
2813         case ARCMSR_MESSAGE_SAY_GOODBYE:
2814                 arcmsr_iop_parking(acb);
2815                 break;
2816         case ARCMSR_MESSAGE_FLUSH_ADAPTER_CACHE:
2817                 arcmsr_flush_adapter_cache(acb);
2818                 break;
2819         default:
2820                 retvalue = ARCMSR_MESSAGE_FAIL;
2821         }
2822 message_out:
2823         return (retvalue);
2824 }
2825 /*
2826 *********************************************************************
2827 *********************************************************************
2828 */
2829 static void arcmsr_execute_srb(void *arg, bus_dma_segment_t *dm_segs, int nseg, int error)
2830 {
2831         struct CommandControlBlock *srb = (struct CommandControlBlock *)arg;
2832         struct AdapterControlBlock *acb = (struct AdapterControlBlock *)srb->acb;
2833         union ccb *pccb;
2834         int target, lun; 
2835
2836         pccb = srb->pccb;
2837         target = pccb->ccb_h.target_id;
2838         lun = pccb->ccb_h.target_lun;
2839         acb->pktRequestCount++;
2840         if(error != 0) {
2841                 if(error != EFBIG) {
2842                         printf("arcmsr%d: unexpected error %x"
2843                                 " returned from 'bus_dmamap_load' \n"
2844                                 , acb->pci_unit, error);
2845                 }
2846                 if((pccb->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_INPROG) {
2847                         pccb->ccb_h.status |= CAM_REQ_TOO_BIG;
2848                 }
2849                 arcmsr_srb_complete(srb, 0);
2850                 return;
2851         }
2852         if(nseg > ARCMSR_MAX_SG_ENTRIES) {
2853                 pccb->ccb_h.status |= CAM_REQ_TOO_BIG;
2854                 arcmsr_srb_complete(srb, 0);
2855                 return;
2856         }
2857         if(acb->acb_flags & ACB_F_BUS_RESET) {
2858                 printf("arcmsr%d: bus reset and return busy \n", acb->pci_unit);
2859                 pccb->ccb_h.status |= CAM_SCSI_BUS_RESET;
2860                 arcmsr_srb_complete(srb, 0);
2861                 return;
2862         }
2863         if(acb->devstate[target][lun] == ARECA_RAID_GONE) {
2864                 u_int8_t block_cmd, cmd;
2865
2866                 cmd = scsiio_cdb_ptr(&pccb->csio)[0];
2867                 block_cmd = cmd & 0x0f;
2868                 if(block_cmd == 0x08 || block_cmd == 0x0a) {
2869                         printf("arcmsr%d:block 'read/write' command "
2870                                 "with gone raid volume Cmd=0x%2x, TargetId=%d, Lun=%d \n"
2871                                 , acb->pci_unit, cmd, target, lun);
2872                         pccb->ccb_h.status |= CAM_DEV_NOT_THERE;
2873                         arcmsr_srb_complete(srb, 0);
2874                         return;
2875                 }
2876         }
2877         if((pccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_INPROG) {
2878                 if(nseg != 0) {
2879                         bus_dmamap_unload(acb->dm_segs_dmat, srb->dm_segs_dmamap);
2880                 }
2881                 arcmsr_srb_complete(srb, 0);
2882                 return;
2883         }
2884         if(acb->srboutstandingcount >= acb->maxOutstanding) {
2885                 if((acb->acb_flags & ACB_F_CAM_DEV_QFRZN) == 0)
2886                 {
2887                         xpt_freeze_simq(acb->psim, 1);
2888                         acb->acb_flags |= ACB_F_CAM_DEV_QFRZN;
2889                 }
2890                 pccb->ccb_h.status &= ~CAM_SIM_QUEUED;
2891                 pccb->ccb_h.status |= CAM_REQUEUE_REQ;
2892                 arcmsr_srb_complete(srb, 0);
2893                 return;
2894         }
2895         pccb->ccb_h.status |= CAM_SIM_QUEUED;
2896         arcmsr_build_srb(srb, dm_segs, nseg);
2897         arcmsr_post_srb(acb, srb);
2898         if (pccb->ccb_h.timeout != CAM_TIME_INFINITY)
2899         {
2900                 arcmsr_callout_init(&srb->ccb_callout);
2901                 callout_reset_sbt(&srb->ccb_callout, SBT_1MS *
2902                     (pccb->ccb_h.timeout + (ARCMSR_TIMEOUT_DELAY * 1000)), 0,
2903                     arcmsr_srb_timeout, srb, 0);
2904                 srb->srb_flags |= SRB_FLAG_TIMER_START;
2905         }
2906 }
2907 /*
2908 *****************************************************************************************
2909 *****************************************************************************************
2910 */
2911 static u_int8_t arcmsr_seek_cmd2abort(union ccb *abortccb)
2912 {
2913         struct CommandControlBlock *srb;
2914         struct AdapterControlBlock *acb = (struct AdapterControlBlock *) abortccb->ccb_h.arcmsr_ccbacb_ptr;
2915         u_int32_t intmask_org;
2916         int i = 0;
2917
2918         acb->num_aborts++;
2919         /*
2920         ***************************************************************************
2921         ** It is the upper layer do abort command this lock just prior to calling us.
2922         ** First determine if we currently own this command.
2923         ** Start by searching the device queue. If not found
2924         ** at all, and the system wanted us to just abort the
2925         ** command return success.
2926         ***************************************************************************
2927         */
2928         if(acb->srboutstandingcount != 0) {
2929                 /* disable all outbound interrupt */
2930                 intmask_org = arcmsr_disable_allintr(acb);
2931                 for(i=0; i < ARCMSR_MAX_FREESRB_NUM; i++) {
2932                         srb = acb->psrb_pool[i];
2933                         if(srb->srb_state == ARCMSR_SRB_START) {
2934                                 if(srb->pccb == abortccb) {
2935                                         srb->srb_state = ARCMSR_SRB_ABORTED;
2936                                         printf("arcmsr%d:scsi id=%d lun=%jx abort srb '%p'"
2937                                                 "outstanding command \n"
2938                                                 , acb->pci_unit, abortccb->ccb_h.target_id
2939                                                 , (uintmax_t)abortccb->ccb_h.target_lun, srb);
2940                                         arcmsr_polling_srbdone(acb, srb);
2941                                         /* enable outbound Post Queue, outbound doorbell Interrupt */
2942                                         arcmsr_enable_allintr(acb, intmask_org);
2943                                         return (TRUE);
2944                                 }
2945                         }
2946                 }
2947                 /* enable outbound Post Queue, outbound doorbell Interrupt */
2948                 arcmsr_enable_allintr(acb, intmask_org);
2949         }
2950         return(FALSE);
2951 }
2952 /*
2953 ****************************************************************************
2954 ****************************************************************************
2955 */
2956 static void arcmsr_bus_reset(struct AdapterControlBlock *acb)
2957 {
2958         int retry = 0;
2959
2960         acb->num_resets++;
2961         acb->acb_flags |= ACB_F_BUS_RESET;
2962         while(acb->srboutstandingcount != 0 && retry < 400) {
2963                 arcmsr_interrupt(acb);
2964                 UDELAY(25000);
2965                 retry++;
2966         }
2967         arcmsr_iop_reset(acb);
2968         acb->acb_flags &= ~ACB_F_BUS_RESET;
2969
2970 /*
2971 **************************************************************************
2972 **************************************************************************
2973 */
2974 static void arcmsr_handle_virtual_command(struct AdapterControlBlock *acb,
2975                 union ccb *pccb)
2976 {
2977         if (pccb->ccb_h.target_lun) {
2978                 pccb->ccb_h.status |= CAM_DEV_NOT_THERE;
2979                 xpt_done(pccb);
2980                 return;
2981         }
2982         pccb->ccb_h.status |= CAM_REQ_CMP;
2983         switch (scsiio_cdb_ptr(&pccb->csio)[0]) {
2984         case INQUIRY: {
2985                 unsigned char inqdata[36];
2986                 char *buffer = pccb->csio.data_ptr;
2987
2988                 inqdata[0] = T_PROCESSOR;       /* Periph Qualifier & Periph Dev Type */
2989                 inqdata[1] = 0;                 /* rem media bit & Dev Type Modifier */
2990                 inqdata[2] = 0;                 /* ISO, ECMA, & ANSI versions */
2991                 inqdata[3] = 0;
2992                 inqdata[4] = 31;                /* length of additional data */
2993                 inqdata[5] = 0;
2994                 inqdata[6] = 0;
2995                 inqdata[7] = 0;
2996                 strncpy(&inqdata[8], "Areca   ", 8);    /* Vendor Identification */
2997                 strncpy(&inqdata[16], "RAID controller ", 16);  /* Product Identification */
2998                 strncpy(&inqdata[32], "R001", 4); /* Product Revision */
2999                 memcpy(buffer, inqdata, sizeof(inqdata));
3000                 xpt_done(pccb);
3001         }
3002         break;
3003         case WRITE_BUFFER:
3004         case READ_BUFFER: {
3005                 if (arcmsr_iop_message_xfer(acb, pccb)) {
3006                         pccb->ccb_h.status |= CAM_SCSI_STATUS_ERROR;
3007                         pccb->csio.scsi_status = SCSI_STATUS_CHECK_COND;
3008                 }
3009                 xpt_done(pccb);
3010         }
3011         break;
3012         default:
3013                 xpt_done(pccb);
3014         }
3015 }
3016 /*
3017 *********************************************************************
3018 *********************************************************************
3019 */
3020 static void arcmsr_action(struct cam_sim *psim, union ccb *pccb)
3021 {
3022         struct AdapterControlBlock *acb;
3023
3024         acb = (struct AdapterControlBlock *) cam_sim_softc(psim);
3025         if(acb == NULL) {
3026                 pccb->ccb_h.status |= CAM_REQ_INVALID;
3027                 xpt_done(pccb);
3028                 return;
3029         }
3030         switch (pccb->ccb_h.func_code) {
3031         case XPT_SCSI_IO: {
3032                         struct CommandControlBlock *srb;
3033                         int target = pccb->ccb_h.target_id;
3034                         int error;
3035
3036                         if (pccb->ccb_h.flags & CAM_CDB_PHYS) {
3037                                 pccb->ccb_h.status = CAM_REQ_INVALID;
3038                                 xpt_done(pccb);
3039                                 return;
3040                         }
3041
3042                         if(target == 16) {
3043                                 /* virtual device for iop message transfer */
3044                                 arcmsr_handle_virtual_command(acb, pccb);
3045                                 return;
3046                         }
3047                         if((srb = arcmsr_get_freesrb(acb)) == NULL) {
3048                                 pccb->ccb_h.status |= CAM_RESRC_UNAVAIL;
3049                                 xpt_done(pccb);
3050                                 return;
3051                         }
3052                         pccb->ccb_h.arcmsr_ccbsrb_ptr = srb;
3053                         pccb->ccb_h.arcmsr_ccbacb_ptr = acb;
3054                         srb->pccb = pccb;
3055                         error = bus_dmamap_load_ccb(acb->dm_segs_dmat
3056                                 , srb->dm_segs_dmamap
3057                                 , pccb
3058                                 , arcmsr_execute_srb, srb, /*flags*/0);
3059                         if(error == EINPROGRESS) {
3060                                 xpt_freeze_simq(acb->psim, 1);
3061                                 pccb->ccb_h.status |= CAM_RELEASE_SIMQ;
3062                         }
3063                         break;
3064                 }
3065         case XPT_PATH_INQ: {
3066                         struct ccb_pathinq *cpi = &pccb->cpi;
3067
3068                         cpi->version_num = 1;
3069                         cpi->hba_inquiry = PI_SDTR_ABLE | PI_TAG_ABLE;
3070                         cpi->target_sprt = 0;
3071                         cpi->hba_misc = 0;
3072                         cpi->hba_eng_cnt = 0;
3073                         cpi->max_target = ARCMSR_MAX_TARGETID;        /* 0-16 */
3074                         cpi->max_lun = ARCMSR_MAX_TARGETLUN;        /* 0-7 */
3075                         cpi->initiator_id = ARCMSR_SCSI_INITIATOR_ID; /* 255 */
3076                         cpi->bus_id = cam_sim_bus(psim);
3077                         strlcpy(cpi->sim_vid, "FreeBSD", SIM_IDLEN);
3078                         strlcpy(cpi->hba_vid, "ARCMSR", HBA_IDLEN);
3079                         strlcpy(cpi->dev_name, cam_sim_name(psim), DEV_IDLEN);
3080                         cpi->unit_number = cam_sim_unit(psim);
3081                         if(acb->adapter_bus_speed == ACB_BUS_SPEED_12G)
3082                                 cpi->base_transfer_speed = 1200000;
3083                         else if(acb->adapter_bus_speed == ACB_BUS_SPEED_6G)
3084                                 cpi->base_transfer_speed = 600000;
3085                         else
3086                                 cpi->base_transfer_speed = 300000;
3087                         if((acb->vendor_device_id == PCIDevVenIDARC1880) ||
3088                            (acb->vendor_device_id == PCIDevVenIDARC1884) ||
3089                            (acb->vendor_device_id == PCIDevVenIDARC1680) ||
3090                            (acb->vendor_device_id == PCIDevVenIDARC1214))
3091                         {
3092                                 cpi->transport = XPORT_SAS;
3093                                 cpi->transport_version = 0;
3094                                 cpi->protocol_version = SCSI_REV_SPC2;
3095                         }
3096                         else
3097                         {
3098                                 cpi->transport = XPORT_SPI;
3099                                 cpi->transport_version = 2;
3100                                 cpi->protocol_version = SCSI_REV_2;
3101                         }
3102                         cpi->protocol = PROTO_SCSI;
3103                         cpi->ccb_h.status |= CAM_REQ_CMP;
3104                         xpt_done(pccb);
3105                         break;
3106                 }
3107         case XPT_ABORT: {
3108                         union ccb *pabort_ccb;
3109
3110                         pabort_ccb = pccb->cab.abort_ccb;
3111                         switch (pabort_ccb->ccb_h.func_code) {
3112                         case XPT_ACCEPT_TARGET_IO:
3113                         case XPT_CONT_TARGET_IO:
3114                                 if(arcmsr_seek_cmd2abort(pabort_ccb)==TRUE) {
3115                                         pabort_ccb->ccb_h.status |= CAM_REQ_ABORTED;
3116                                         xpt_done(pabort_ccb);
3117                                         pccb->ccb_h.status |= CAM_REQ_CMP;
3118                                 } else {
3119                                         xpt_print_path(pabort_ccb->ccb_h.path);
3120                                         printf("Not found\n");
3121                                         pccb->ccb_h.status |= CAM_PATH_INVALID;
3122                                 }
3123                                 break;
3124                         case XPT_SCSI_IO:
3125                                 pccb->ccb_h.status |= CAM_UA_ABORT;
3126                                 break;
3127                         default:
3128                                 pccb->ccb_h.status |= CAM_REQ_INVALID;
3129                                 break;
3130                         }
3131                         xpt_done(pccb);
3132                         break;
3133                 }
3134         case XPT_RESET_BUS:
3135         case XPT_RESET_DEV: {
3136                         u_int32_t       i;
3137
3138                         arcmsr_bus_reset(acb);
3139                         for (i=0; i < 500; i++) {
3140                                 DELAY(1000);    
3141                         }
3142                         pccb->ccb_h.status |= CAM_REQ_CMP;
3143                         xpt_done(pccb);
3144                         break;
3145                 }
3146         case XPT_TERM_IO: {
3147                         pccb->ccb_h.status |= CAM_REQ_INVALID;
3148                         xpt_done(pccb);
3149                         break;
3150                 }
3151         case XPT_GET_TRAN_SETTINGS: {
3152                         struct ccb_trans_settings *cts;
3153
3154                         if(pccb->ccb_h.target_id == 16) {
3155                                 pccb->ccb_h.status |= CAM_FUNC_NOTAVAIL;
3156                                 xpt_done(pccb);
3157                                 break;
3158                         }
3159                         cts = &pccb->cts;
3160                         {
3161                                 struct ccb_trans_settings_scsi *scsi;
3162                                 struct ccb_trans_settings_spi *spi;
3163                                 struct ccb_trans_settings_sas *sas;     
3164
3165                                 scsi = &cts->proto_specific.scsi;
3166                                 scsi->flags = CTS_SCSI_FLAGS_TAG_ENB;
3167                                 scsi->valid = CTS_SCSI_VALID_TQ;
3168                                 cts->protocol = PROTO_SCSI;
3169
3170                                 if((acb->vendor_device_id == PCIDevVenIDARC1880) ||
3171                                    (acb->vendor_device_id == PCIDevVenIDARC1884) ||
3172                                    (acb->vendor_device_id == PCIDevVenIDARC1680) ||
3173                                    (acb->vendor_device_id == PCIDevVenIDARC1214))
3174                                 {
3175                                         cts->protocol_version = SCSI_REV_SPC2;
3176                                         cts->transport_version = 0;
3177                                         cts->transport = XPORT_SAS;
3178                                         sas = &cts->xport_specific.sas;
3179                                         sas->valid = CTS_SAS_VALID_SPEED;
3180                                         if (acb->adapter_bus_speed == ACB_BUS_SPEED_12G)
3181                                                 sas->bitrate = 1200000;
3182                                         else if(acb->adapter_bus_speed == ACB_BUS_SPEED_6G)
3183                                                 sas->bitrate = 600000;
3184                                         else if(acb->adapter_bus_speed == ACB_BUS_SPEED_3G)
3185                                                 sas->bitrate = 300000;
3186                                 }
3187                                 else
3188                                 {
3189                                         cts->protocol_version = SCSI_REV_2;
3190                                         cts->transport_version = 2;
3191                                         cts->transport = XPORT_SPI;
3192                                         spi = &cts->xport_specific.spi;
3193                                         spi->flags = CTS_SPI_FLAGS_DISC_ENB;
3194                                         if (acb->adapter_bus_speed == ACB_BUS_SPEED_6G)
3195                                                 spi->sync_period = 1;
3196                                         else
3197                                                 spi->sync_period = 2;
3198                                         spi->sync_offset = 32;
3199                                         spi->bus_width = MSG_EXT_WDTR_BUS_16_BIT;
3200                                         spi->valid = CTS_SPI_VALID_DISC
3201                                                 | CTS_SPI_VALID_SYNC_RATE
3202                                                 | CTS_SPI_VALID_SYNC_OFFSET
3203                                                 | CTS_SPI_VALID_BUS_WIDTH;
3204                                 }
3205                         }
3206                         pccb->ccb_h.status |= CAM_REQ_CMP;
3207                         xpt_done(pccb);
3208                         break;
3209                 }
3210         case XPT_SET_TRAN_SETTINGS: {
3211                         pccb->ccb_h.status |= CAM_FUNC_NOTAVAIL;
3212                         xpt_done(pccb);
3213                         break;
3214                 }
3215         case XPT_CALC_GEOMETRY:
3216                         if(pccb->ccb_h.target_id == 16) {
3217                                 pccb->ccb_h.status |= CAM_FUNC_NOTAVAIL;
3218                                 xpt_done(pccb);
3219                                 break;
3220                         }
3221                         cam_calc_geometry(&pccb->ccg, 1);
3222                         xpt_done(pccb);
3223                         break;
3224         default:
3225                 pccb->ccb_h.status |= CAM_REQ_INVALID;
3226                 xpt_done(pccb);
3227                 break;
3228         }
3229 }
3230 /*
3231 **********************************************************************
3232 **********************************************************************
3233 */
3234 static void arcmsr_start_hba_bgrb(struct AdapterControlBlock *acb)
3235 {
3236         acb->acb_flags |= ACB_F_MSG_START_BGRB;
3237         CHIP_REG_WRITE32(HBA_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_START_BGRB);
3238         if(!arcmsr_hba_wait_msgint_ready(acb)) {
3239                 printf("arcmsr%d: wait 'start adapter background rebulid' timeout \n", acb->pci_unit);
3240         }
3241 }
3242 /*
3243 **********************************************************************
3244 **********************************************************************
3245 */
3246 static void arcmsr_start_hbb_bgrb(struct AdapterControlBlock *acb)
3247 {
3248         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
3249         acb->acb_flags |= ACB_F_MSG_START_BGRB;
3250         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_MESSAGE_START_BGRB);
3251         if(!arcmsr_hbb_wait_msgint_ready(acb)) {
3252                 printf( "arcmsr%d: wait 'start adapter background rebulid' timeout \n", acb->pci_unit);
3253         }
3254 }
3255 /*
3256 **********************************************************************
3257 **********************************************************************
3258 */
3259 static void arcmsr_start_hbc_bgrb(struct AdapterControlBlock *acb)
3260 {
3261         acb->acb_flags |= ACB_F_MSG_START_BGRB;
3262         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_START_BGRB);
3263         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_doorbell, ARCMSR_HBCMU_DRV2IOP_MESSAGE_CMD_DONE);
3264         if(!arcmsr_hbc_wait_msgint_ready(acb)) {
3265                 printf("arcmsr%d: wait 'start adapter background rebulid' timeout \n", acb->pci_unit);
3266         }
3267 }
3268 /*
3269 **********************************************************************
3270 **********************************************************************
3271 */
3272 static void arcmsr_start_hbd_bgrb(struct AdapterControlBlock *acb)
3273 {
3274         acb->acb_flags |= ACB_F_MSG_START_BGRB;
3275         CHIP_REG_WRITE32(HBD_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_START_BGRB);
3276         if(!arcmsr_hbd_wait_msgint_ready(acb)) {
3277                 printf("arcmsr%d: wait 'start adapter background rebulid' timeout \n", acb->pci_unit);
3278         }
3279 }
3280 /*
3281 **********************************************************************
3282 **********************************************************************
3283 */
3284 static void arcmsr_start_hbe_bgrb(struct AdapterControlBlock *acb)
3285 {
3286         acb->acb_flags |= ACB_F_MSG_START_BGRB;
3287         CHIP_REG_WRITE32(HBE_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_START_BGRB);
3288         acb->out_doorbell ^= ARCMSR_HBEMU_DRV2IOP_MESSAGE_CMD_DONE;
3289         CHIP_REG_WRITE32(HBE_MessageUnit, 0, iobound_doorbell, acb->out_doorbell);
3290         if(!arcmsr_hbe_wait_msgint_ready(acb)) {
3291                 printf("arcmsr%d: wait 'start adapter background rebulid' timeout \n", acb->pci_unit);
3292         }
3293 }
3294 /*
3295 **********************************************************************
3296 **********************************************************************
3297 */
3298 static void arcmsr_start_adapter_bgrb(struct AdapterControlBlock *acb)
3299 {
3300         switch (acb->adapter_type) {
3301         case ACB_ADAPTER_TYPE_A:
3302                 arcmsr_start_hba_bgrb(acb);
3303                 break;
3304         case ACB_ADAPTER_TYPE_B:
3305                 arcmsr_start_hbb_bgrb(acb);
3306                 break;
3307         case ACB_ADAPTER_TYPE_C:
3308                 arcmsr_start_hbc_bgrb(acb);
3309                 break;
3310         case ACB_ADAPTER_TYPE_D:
3311                 arcmsr_start_hbd_bgrb(acb);
3312                 break;
3313         case ACB_ADAPTER_TYPE_E:
3314                 arcmsr_start_hbe_bgrb(acb);
3315                 break;
3316         }
3317 }
3318 /*
3319 **********************************************************************
3320 ** 
3321 **********************************************************************
3322 */
3323 static void arcmsr_polling_hba_srbdone(struct AdapterControlBlock *acb, struct CommandControlBlock *poll_srb)
3324 {
3325         struct CommandControlBlock *srb;
3326         u_int32_t flag_srb, outbound_intstatus, poll_srb_done=0, poll_count=0;
3327         u_int16_t       error;
3328
3329 polling_ccb_retry:
3330         poll_count++;
3331         outbound_intstatus=CHIP_REG_READ32(HBA_MessageUnit, 0, outbound_intstatus) & acb->outbound_int_enable;
3332         CHIP_REG_WRITE32(HBA_MessageUnit, 0, outbound_intstatus, outbound_intstatus);   /*clear interrupt*/
3333         bus_dmamap_sync(acb->srb_dmat, acb->srb_dmamap, BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
3334         while(1) {
3335                 if((flag_srb = CHIP_REG_READ32(HBA_MessageUnit, 
3336                         0, outbound_queueport)) == 0xFFFFFFFF) {
3337                         if(poll_srb_done) {
3338                                 break;/*chip FIFO no ccb for completion already*/
3339                         } else {
3340                                 UDELAY(25000);
3341                                 if ((poll_count > 100) && (poll_srb != NULL)) {
3342                                         break;
3343                                 }
3344                                 goto polling_ccb_retry;
3345                         }
3346                 }
3347                 /* check if command done with no error*/
3348                 srb = (struct CommandControlBlock *)
3349                         (acb->vir2phy_offset+(flag_srb << 5));/*frame must be 32 bytes aligned*/
3350                 error = (flag_srb & ARCMSR_SRBREPLY_FLAG_ERROR_MODE0)?TRUE:FALSE;
3351                 poll_srb_done = (srb == poll_srb) ? 1:0;
3352                 if((srb->acb != acb) || (srb->srb_state != ARCMSR_SRB_START)) {
3353                         if(srb->srb_state == ARCMSR_SRB_ABORTED) {
3354                                 printf("arcmsr%d: scsi id=%d lun=%jx srb='%p'"
3355                                         "poll command abort successfully \n"
3356                                         , acb->pci_unit
3357                                         , srb->pccb->ccb_h.target_id
3358                                         , (uintmax_t)srb->pccb->ccb_h.target_lun, srb);
3359                                 srb->pccb->ccb_h.status |= CAM_REQ_ABORTED;
3360                                 arcmsr_srb_complete(srb, 1);
3361                                 continue;
3362                         }
3363                         printf("arcmsr%d: polling get an illegal srb command done srb='%p'"
3364                                 "srboutstandingcount=%d \n"
3365                                 , acb->pci_unit
3366                                 , srb, acb->srboutstandingcount);
3367                         continue;
3368                 }
3369                 arcmsr_report_srb_state(acb, srb, error);
3370         }       /*drain reply FIFO*/
3371 }
3372 /*
3373 **********************************************************************
3374 **
3375 **********************************************************************
3376 */
3377 static void arcmsr_polling_hbb_srbdone(struct AdapterControlBlock *acb, struct CommandControlBlock *poll_srb)
3378 {
3379         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
3380         struct CommandControlBlock *srb;
3381         u_int32_t flag_srb, poll_srb_done=0, poll_count=0;
3382         int index;
3383         u_int16_t       error;
3384
3385 polling_ccb_retry:
3386         poll_count++;
3387         WRITE_CHIP_REG32(0, phbbmu->iop2drv_doorbell, ARCMSR_DOORBELL_INT_CLEAR_PATTERN); /* clear doorbell interrupt */
3388         bus_dmamap_sync(acb->srb_dmat, acb->srb_dmamap, BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
3389         while(1) {
3390                 index = phbbmu->doneq_index;
3391                 if((flag_srb = phbbmu->done_qbuffer[index]) == 0) {
3392                         if(poll_srb_done) {
3393                                 break;/*chip FIFO no ccb for completion already*/
3394                         } else {
3395                                 UDELAY(25000);
3396                                 if ((poll_count > 100) && (poll_srb != NULL)) {
3397                                         break;
3398                                 }
3399                                 goto polling_ccb_retry;
3400                         }
3401                 }
3402                 phbbmu->done_qbuffer[index] = 0;
3403                 index++;
3404                 index %= ARCMSR_MAX_HBB_POSTQUEUE;     /*if last index number set it to 0 */
3405                 phbbmu->doneq_index = index;
3406                 /* check if command done with no error*/
3407                 srb = (struct CommandControlBlock *)
3408                         (acb->vir2phy_offset+(flag_srb << 5));/*frame must be 32 bytes aligned*/
3409                 error = (flag_srb & ARCMSR_SRBREPLY_FLAG_ERROR_MODE0)?TRUE:FALSE;
3410                 poll_srb_done = (srb == poll_srb) ? 1:0;
3411                 if((srb->acb != acb) || (srb->srb_state != ARCMSR_SRB_START)) {
3412                         if(srb->srb_state == ARCMSR_SRB_ABORTED) {
3413                                 printf("arcmsr%d: scsi id=%d lun=%jx srb='%p'"
3414                                         "poll command abort successfully \n"
3415                                         , acb->pci_unit
3416                                         , srb->pccb->ccb_h.target_id
3417                                         , (uintmax_t)srb->pccb->ccb_h.target_lun, srb);
3418                                 srb->pccb->ccb_h.status |= CAM_REQ_ABORTED;
3419                                 arcmsr_srb_complete(srb, 1);            
3420                                 continue;
3421                         }
3422                         printf("arcmsr%d: polling get an illegal srb command done srb='%p'"
3423                                 "srboutstandingcount=%d \n"
3424                                 , acb->pci_unit
3425                                 , srb, acb->srboutstandingcount);
3426                         continue;
3427                 }
3428                 arcmsr_report_srb_state(acb, srb, error);
3429         }       /*drain reply FIFO*/
3430 }
3431 /*
3432 **********************************************************************
3433 ** 
3434 **********************************************************************
3435 */
3436 static void arcmsr_polling_hbc_srbdone(struct AdapterControlBlock *acb, struct CommandControlBlock *poll_srb)
3437 {
3438         struct CommandControlBlock *srb;
3439         u_int32_t flag_srb, poll_srb_done=0, poll_count=0;
3440         u_int16_t       error;
3441
3442 polling_ccb_retry:
3443         poll_count++;
3444         bus_dmamap_sync(acb->srb_dmat, acb->srb_dmamap, BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
3445         while(1) {
3446                 if(!(CHIP_REG_READ32(HBC_MessageUnit, 0, host_int_status) & ARCMSR_HBCMU_OUTBOUND_POSTQUEUE_ISR)) {
3447                         if(poll_srb_done) {
3448                                 break;/*chip FIFO no ccb for completion already*/
3449                         } else {
3450                                 UDELAY(25000);
3451                                 if ((poll_count > 100) && (poll_srb != NULL)) {
3452                                         break;
3453                                 }
3454                                 if (acb->srboutstandingcount == 0) {
3455                                     break;
3456                                 }
3457                                 goto polling_ccb_retry;
3458                         }
3459                 }
3460                 flag_srb = CHIP_REG_READ32(HBC_MessageUnit, 0, outbound_queueport_low);
3461                 /* check if command done with no error*/
3462                 srb = (struct CommandControlBlock *)(acb->vir2phy_offset+(flag_srb & 0xFFFFFFE0));/*frame must be 32 bytes aligned*/
3463                 error = (flag_srb & ARCMSR_SRBREPLY_FLAG_ERROR_MODE1)?TRUE:FALSE;
3464                 if (poll_srb != NULL)
3465                         poll_srb_done = (srb == poll_srb) ? 1:0;
3466                 if((srb->acb != acb) || (srb->srb_state != ARCMSR_SRB_START)) {
3467                         if(srb->srb_state == ARCMSR_SRB_ABORTED) {
3468                                 printf("arcmsr%d: scsi id=%d lun=%jx srb='%p'poll command abort successfully \n"
3469                                                 , acb->pci_unit, srb->pccb->ccb_h.target_id, (uintmax_t)srb->pccb->ccb_h.target_lun, srb);
3470                                 srb->pccb->ccb_h.status |= CAM_REQ_ABORTED;
3471                                 arcmsr_srb_complete(srb, 1);
3472                                 continue;
3473                         }
3474                         printf("arcmsr%d: polling get an illegal srb command done srb='%p'srboutstandingcount=%d \n"
3475                                         , acb->pci_unit, srb, acb->srboutstandingcount);
3476                         continue;
3477                 }
3478                 arcmsr_report_srb_state(acb, srb, error);
3479         }       /*drain reply FIFO*/
3480 }
3481 /*
3482 **********************************************************************
3483 ** 
3484 **********************************************************************
3485 */
3486 static void arcmsr_polling_hbd_srbdone(struct AdapterControlBlock *acb, struct CommandControlBlock *poll_srb)
3487 {
3488         struct HBD_MessageUnit0 *phbdmu = (struct HBD_MessageUnit0 *)acb->pmu;
3489         struct CommandControlBlock *srb;
3490         u_int32_t flag_srb, poll_srb_done=0, poll_count=0;
3491         u_int32_t outbound_write_pointer;
3492         u_int16_t       error, doneq_index;
3493
3494 polling_ccb_retry:
3495         poll_count++;
3496         bus_dmamap_sync(acb->srb_dmat, acb->srb_dmamap, BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
3497         while(1) {
3498                 outbound_write_pointer = phbdmu->done_qbuffer[0].addressLow;
3499                 doneq_index = phbdmu->doneq_index;
3500                 if ((outbound_write_pointer & 0xFF) == (doneq_index & 0xFF)) {
3501                         if(poll_srb_done) {
3502                                 break;/*chip FIFO no ccb for completion already*/
3503                         } else {
3504                                 UDELAY(25000);
3505                                 if ((poll_count > 100) && (poll_srb != NULL)) {
3506                                         break;
3507                                 }
3508                                 if (acb->srboutstandingcount == 0) {
3509                                         break;
3510                                 }
3511                                 goto polling_ccb_retry;
3512                         }
3513                 }
3514                 doneq_index = arcmsr_get_doneq_index(phbdmu);
3515                 flag_srb = phbdmu->done_qbuffer[(doneq_index & 0xFF)+1].addressLow;
3516                 /* check if command done with no error*/
3517                 srb = (struct CommandControlBlock *)(acb->vir2phy_offset+(flag_srb & 0xFFFFFFE0));/*frame must be 32 bytes aligned*/
3518                 error = (flag_srb & ARCMSR_SRBREPLY_FLAG_ERROR_MODE1) ? TRUE : FALSE;
3519                 CHIP_REG_WRITE32(HBD_MessageUnit, 0, outboundlist_read_pointer, doneq_index);
3520                 if (poll_srb != NULL)
3521                         poll_srb_done = (srb == poll_srb) ? 1:0;
3522                 if((srb->acb != acb) || (srb->srb_state != ARCMSR_SRB_START)) {
3523                         if(srb->srb_state == ARCMSR_SRB_ABORTED) {
3524                                 printf("arcmsr%d: scsi id=%d lun=%jx srb='%p'poll command abort successfully \n"
3525                                                 , acb->pci_unit, srb->pccb->ccb_h.target_id, (uintmax_t)srb->pccb->ccb_h.target_lun, srb);
3526                                 srb->pccb->ccb_h.status |= CAM_REQ_ABORTED;
3527                                 arcmsr_srb_complete(srb, 1);
3528                                 continue;
3529                         }
3530                         printf("arcmsr%d: polling get an illegal srb command done srb='%p'srboutstandingcount=%d \n"
3531                                         , acb->pci_unit, srb, acb->srboutstandingcount);
3532                         continue;
3533                 }
3534                 arcmsr_report_srb_state(acb, srb, error);
3535         }       /*drain reply FIFO*/
3536 }
3537 /*
3538 **********************************************************************
3539 ** 
3540 **********************************************************************
3541 */
3542 static void arcmsr_polling_hbe_srbdone(struct AdapterControlBlock *acb, struct CommandControlBlock *poll_srb)
3543 {
3544         struct CommandControlBlock *srb;
3545         u_int32_t poll_srb_done=0, poll_count=0, doneq_index;
3546         u_int16_t       error, cmdSMID;
3547
3548 polling_ccb_retry:
3549         poll_count++;
3550         bus_dmamap_sync(acb->srb_dmat, acb->srb_dmamap, BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
3551         while(1) {
3552                 doneq_index = acb->doneq_index;
3553                 if((CHIP_REG_READ32(HBE_MessageUnit, 0, reply_post_producer_index) & 0xFFFF) == doneq_index) {
3554                         if(poll_srb_done) {
3555                                 break;/*chip FIFO no ccb for completion already*/
3556                         } else {
3557                                 UDELAY(25000);
3558                             if ((poll_count > 100) && (poll_srb != NULL)) {
3559                                         break;
3560                                 }
3561                             if (acb->srboutstandingcount == 0) {
3562                                     break;
3563                             }
3564                                 goto polling_ccb_retry;
3565                         }
3566                 }
3567                 cmdSMID = acb->pCompletionQ[doneq_index].cmdSMID;
3568                 doneq_index++;
3569                 if (doneq_index >= acb->completionQ_entry)
3570                         doneq_index = 0;
3571                 acb->doneq_index = doneq_index;
3572                 srb = acb->psrb_pool[cmdSMID];
3573                 error = (acb->pCompletionQ[doneq_index].cmdFlag & ARCMSR_SRBREPLY_FLAG_ERROR_MODE1) ? TRUE : FALSE;
3574                 if (poll_srb != NULL)
3575                         poll_srb_done = (srb == poll_srb) ? 1:0;
3576                 if((srb->acb != acb) || (srb->srb_state != ARCMSR_SRB_START)) {
3577                         if(srb->srb_state == ARCMSR_SRB_ABORTED) {
3578                                 printf("arcmsr%d: scsi id=%d lun=%jx srb='%p'poll command abort successfully \n"
3579                                                 , acb->pci_unit, srb->pccb->ccb_h.target_id, (uintmax_t)srb->pccb->ccb_h.target_lun, srb);
3580                                 srb->pccb->ccb_h.status |= CAM_REQ_ABORTED;
3581                                 arcmsr_srb_complete(srb, 1);
3582                                 continue;
3583                         }
3584                         printf("arcmsr%d: polling get an illegal srb command done srb='%p'srboutstandingcount=%d \n"
3585                                         , acb->pci_unit, srb, acb->srboutstandingcount);
3586                         continue;
3587                 }
3588                 arcmsr_report_srb_state(acb, srb, error);
3589         }       /*drain reply FIFO*/
3590         CHIP_REG_WRITE32(HBE_MessageUnit, 0, reply_post_producer_index, doneq_index);
3591 }
3592 /*
3593 **********************************************************************
3594 **********************************************************************
3595 */
3596 static void arcmsr_polling_srbdone(struct AdapterControlBlock *acb, struct CommandControlBlock *poll_srb)
3597 {
3598         switch (acb->adapter_type) {
3599         case ACB_ADAPTER_TYPE_A: {
3600                         arcmsr_polling_hba_srbdone(acb, poll_srb);
3601                 }
3602                 break;
3603         case ACB_ADAPTER_TYPE_B: {
3604                         arcmsr_polling_hbb_srbdone(acb, poll_srb);
3605                 }
3606                 break;
3607         case ACB_ADAPTER_TYPE_C: {
3608                         arcmsr_polling_hbc_srbdone(acb, poll_srb);
3609                 }
3610                 break;
3611         case ACB_ADAPTER_TYPE_D: {
3612                         arcmsr_polling_hbd_srbdone(acb, poll_srb);
3613                 }
3614                 break;
3615         case ACB_ADAPTER_TYPE_E: {
3616                         arcmsr_polling_hbe_srbdone(acb, poll_srb);
3617                 }
3618                 break;
3619         }
3620 }
3621 /*
3622 **********************************************************************
3623 **********************************************************************
3624 */
3625 static void arcmsr_get_hba_config(struct AdapterControlBlock *acb)
3626 {
3627         char *acb_firm_model = acb->firm_model;
3628         char *acb_firm_version = acb->firm_version;
3629         char *acb_device_map = acb->device_map;
3630         size_t iop_firm_model = offsetof(struct HBA_MessageUnit,msgcode_rwbuffer[ARCMSR_FW_MODEL_OFFSET]);      /*firm_model,15,60-67*/
3631         size_t iop_firm_version = offsetof(struct HBA_MessageUnit,msgcode_rwbuffer[ARCMSR_FW_VERS_OFFSET]);     /*firm_version,17,68-83*/
3632         size_t iop_device_map = offsetof(struct HBA_MessageUnit,msgcode_rwbuffer[ARCMSR_FW_DEVMAP_OFFSET]);
3633         int i;
3634
3635         CHIP_REG_WRITE32(HBA_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_GET_CONFIG);
3636         if(!arcmsr_hba_wait_msgint_ready(acb)) {
3637                 printf("arcmsr%d: wait 'get adapter firmware miscellaneous data' timeout \n", acb->pci_unit);
3638         }
3639         i = 0;
3640         while(i < 8) {
3641                 *acb_firm_model = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_firm_model+i); 
3642                 /* 8 bytes firm_model, 15, 60-67*/
3643                 acb_firm_model++;
3644                 i++;
3645         }
3646         i=0;
3647         while(i < 16) {
3648                 *acb_firm_version = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_firm_version+i);  
3649                 /* 16 bytes firm_version, 17, 68-83*/
3650                 acb_firm_version++;
3651                 i++;
3652         }
3653         i=0;
3654         while(i < 16) {
3655                 *acb_device_map = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_device_map+i);  
3656                 acb_device_map++;
3657                 i++;
3658         }
3659         printf("Areca RAID adapter%d: %s F/W version %s \n", acb->pci_unit, acb->firm_model, acb->firm_version);
3660         acb->firm_request_len = CHIP_REG_READ32(HBA_MessageUnit, 0, msgcode_rwbuffer[1]);   /*firm_request_len, 1, 04-07*/
3661         acb->firm_numbers_queue = CHIP_REG_READ32(HBA_MessageUnit, 0, msgcode_rwbuffer[2]); /*firm_numbers_queue, 2, 08-11*/
3662         acb->firm_sdram_size = CHIP_REG_READ32(HBA_MessageUnit, 0, msgcode_rwbuffer[3]);    /*firm_sdram_size, 3, 12-15*/
3663         acb->firm_ide_channels = CHIP_REG_READ32(HBA_MessageUnit, 0, msgcode_rwbuffer[4]);  /*firm_ide_channels, 4, 16-19*/
3664         acb->firm_cfg_version = CHIP_REG_READ32(HBA_MessageUnit, 0, msgcode_rwbuffer[ARCMSR_FW_CFGVER_OFFSET]); /*firm_cfg_version,  25,          */
3665         if(acb->firm_numbers_queue > ARCMSR_MAX_OUTSTANDING_CMD)
3666                 acb->maxOutstanding = ARCMSR_MAX_OUTSTANDING_CMD - 1;
3667         else
3668                 acb->maxOutstanding = acb->firm_numbers_queue - 1;
3669 }
3670 /*
3671 **********************************************************************
3672 **********************************************************************
3673 */
3674 static void arcmsr_get_hbb_config(struct AdapterControlBlock *acb)
3675 {
3676         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
3677         char *acb_firm_model = acb->firm_model;
3678         char *acb_firm_version = acb->firm_version;
3679         char *acb_device_map = acb->device_map;
3680         size_t iop_firm_model = offsetof(struct HBB_RWBUFFER, msgcode_rwbuffer[ARCMSR_FW_MODEL_OFFSET]);        /*firm_model,15,60-67*/
3681         size_t iop_firm_version = offsetof(struct HBB_RWBUFFER, msgcode_rwbuffer[ARCMSR_FW_VERS_OFFSET]);       /*firm_version,17,68-83*/
3682         size_t iop_device_map = offsetof(struct HBB_RWBUFFER, msgcode_rwbuffer[ARCMSR_FW_DEVMAP_OFFSET]);
3683         int i;
3684
3685         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_MESSAGE_GET_CONFIG);
3686         if(!arcmsr_hbb_wait_msgint_ready(acb)) {
3687                 printf( "arcmsr%d: wait" "'get adapter firmware miscellaneous data' timeout \n", acb->pci_unit);
3688         }
3689         i = 0;
3690         while(i < 8) {
3691                 *acb_firm_model = bus_space_read_1(acb->btag[1], acb->bhandle[1], iop_firm_model+i);
3692                 /* 8 bytes firm_model, 15, 60-67*/
3693                 acb_firm_model++;
3694                 i++;
3695         }
3696         i = 0;
3697         while(i < 16) {
3698                 *acb_firm_version = bus_space_read_1(acb->btag[1], acb->bhandle[1], iop_firm_version+i);
3699                 /* 16 bytes firm_version, 17, 68-83*/
3700                 acb_firm_version++;
3701                 i++;
3702         }
3703         i = 0;
3704         while(i < 16) {
3705                 *acb_device_map = bus_space_read_1(acb->btag[1], acb->bhandle[1], iop_device_map+i);  
3706                 acb_device_map++;
3707                 i++;
3708         }
3709         printf("Areca RAID adapter%d: %s F/W version %s \n", acb->pci_unit, acb->firm_model, acb->firm_version);
3710         acb->firm_request_len = CHIP_REG_READ32(HBB_RWBUFFER, 1, msgcode_rwbuffer[1]);   /*firm_request_len, 1, 04-07*/
3711         acb->firm_numbers_queue = CHIP_REG_READ32(HBB_RWBUFFER, 1, msgcode_rwbuffer[2]); /*firm_numbers_queue, 2, 08-11*/
3712         acb->firm_sdram_size = CHIP_REG_READ32(HBB_RWBUFFER, 1, msgcode_rwbuffer[3]);    /*firm_sdram_size, 3, 12-15*/
3713         acb->firm_ide_channels = CHIP_REG_READ32(HBB_RWBUFFER, 1, msgcode_rwbuffer[4]);  /*firm_ide_channels, 4, 16-19*/
3714         acb->firm_cfg_version = CHIP_REG_READ32(HBB_RWBUFFER, 1, msgcode_rwbuffer[ARCMSR_FW_CFGVER_OFFSET]);    /*firm_cfg_version,  25,          */
3715         if(acb->firm_numbers_queue > ARCMSR_MAX_HBB_POSTQUEUE)
3716                 acb->maxOutstanding = ARCMSR_MAX_HBB_POSTQUEUE - 1;
3717         else
3718                 acb->maxOutstanding = acb->firm_numbers_queue - 1;
3719 }
3720 /*
3721 **********************************************************************
3722 **********************************************************************
3723 */
3724 static void arcmsr_get_hbc_config(struct AdapterControlBlock *acb)
3725 {
3726         char *acb_firm_model = acb->firm_model;
3727         char *acb_firm_version = acb->firm_version;
3728         char *acb_device_map = acb->device_map;
3729         size_t iop_firm_model = offsetof(struct HBC_MessageUnit,msgcode_rwbuffer[ARCMSR_FW_MODEL_OFFSET]);   /*firm_model,15,60-67*/
3730         size_t iop_firm_version = offsetof(struct HBC_MessageUnit,msgcode_rwbuffer[ARCMSR_FW_VERS_OFFSET]); /*firm_version,17,68-83*/
3731         size_t iop_device_map = offsetof(struct HBC_MessageUnit,msgcode_rwbuffer[ARCMSR_FW_DEVMAP_OFFSET]);
3732         int i;
3733
3734         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_GET_CONFIG);
3735         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_doorbell, ARCMSR_HBCMU_DRV2IOP_MESSAGE_CMD_DONE);
3736         if(!arcmsr_hbc_wait_msgint_ready(acb)) {
3737                 printf("arcmsr%d: wait 'get adapter firmware miscellaneous data' timeout \n", acb->pci_unit);
3738         }
3739         i = 0;
3740         while(i < 8) {
3741                 *acb_firm_model = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_firm_model+i); 
3742                 /* 8 bytes firm_model, 15, 60-67*/
3743                 acb_firm_model++;
3744                 i++;
3745         }
3746         i = 0;
3747         while(i < 16) {
3748                 *acb_firm_version = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_firm_version+i);  
3749                 /* 16 bytes firm_version, 17, 68-83*/
3750                 acb_firm_version++;
3751                 i++;
3752         }
3753         i = 0;
3754         while(i < 16) {
3755                 *acb_device_map = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_device_map+i);  
3756                 acb_device_map++;
3757                 i++;
3758         }
3759         printf("Areca RAID adapter%d: %s F/W version %s \n", acb->pci_unit, acb->firm_model, acb->firm_version);
3760         acb->firm_request_len   = CHIP_REG_READ32(HBC_MessageUnit, 0, msgcode_rwbuffer[1]);     /*firm_request_len,   1, 04-07*/
3761         acb->firm_numbers_queue = CHIP_REG_READ32(HBC_MessageUnit, 0, msgcode_rwbuffer[2]);     /*firm_numbers_queue, 2, 08-11*/
3762         acb->firm_sdram_size    = CHIP_REG_READ32(HBC_MessageUnit, 0, msgcode_rwbuffer[3]);     /*firm_sdram_size,    3, 12-15*/
3763         acb->firm_ide_channels  = CHIP_REG_READ32(HBC_MessageUnit, 0, msgcode_rwbuffer[4]);     /*firm_ide_channels,  4, 16-19*/
3764         acb->firm_cfg_version   = CHIP_REG_READ32(HBC_MessageUnit, 0, msgcode_rwbuffer[ARCMSR_FW_CFGVER_OFFSET]);       /*firm_cfg_version,  25,          */
3765         if(acb->firm_numbers_queue > ARCMSR_MAX_OUTSTANDING_CMD)
3766                 acb->maxOutstanding = ARCMSR_MAX_OUTSTANDING_CMD - 1;
3767         else
3768                 acb->maxOutstanding = acb->firm_numbers_queue - 1;
3769 }
3770 /*
3771 **********************************************************************
3772 **********************************************************************
3773 */
3774 static void arcmsr_get_hbd_config(struct AdapterControlBlock *acb)
3775 {
3776         char *acb_firm_model = acb->firm_model;
3777         char *acb_firm_version = acb->firm_version;
3778         char *acb_device_map = acb->device_map;
3779         size_t iop_firm_model = offsetof(struct HBD_MessageUnit, msgcode_rwbuffer[ARCMSR_FW_MODEL_OFFSET]);   /*firm_model,15,60-67*/
3780         size_t iop_firm_version = offsetof(struct HBD_MessageUnit, msgcode_rwbuffer[ARCMSR_FW_VERS_OFFSET]); /*firm_version,17,68-83*/
3781         size_t iop_device_map = offsetof(struct HBD_MessageUnit, msgcode_rwbuffer[ARCMSR_FW_DEVMAP_OFFSET]);
3782         int i;
3783
3784         if(CHIP_REG_READ32(HBD_MessageUnit, 0, outbound_doorbell) & ARCMSR_HBDMU_IOP2DRV_MESSAGE_CMD_DONE)
3785                 CHIP_REG_WRITE32(HBD_MessageUnit, 0, outbound_doorbell, ARCMSR_HBDMU_IOP2DRV_MESSAGE_CMD_DONE_CLEAR);
3786         CHIP_REG_WRITE32(HBD_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_GET_CONFIG);
3787         if(!arcmsr_hbd_wait_msgint_ready(acb)) {
3788                 printf("arcmsr%d: wait 'get adapter firmware miscellaneous data' timeout \n", acb->pci_unit);
3789         }
3790         i = 0;
3791         while(i < 8) {
3792                 *acb_firm_model = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_firm_model+i); 
3793                 /* 8 bytes firm_model, 15, 60-67*/
3794                 acb_firm_model++;
3795                 i++;
3796         }
3797         i = 0;
3798         while(i < 16) {
3799                 *acb_firm_version = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_firm_version+i);  
3800                 /* 16 bytes firm_version, 17, 68-83*/
3801                 acb_firm_version++;
3802                 i++;
3803         }
3804         i = 0;
3805         while(i < 16) {
3806                 *acb_device_map = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_device_map+i);  
3807                 acb_device_map++;
3808                 i++;
3809         }
3810         printf("Areca RAID adapter%d: %s F/W version %s \n", acb->pci_unit, acb->firm_model, acb->firm_version);
3811         acb->firm_request_len   = CHIP_REG_READ32(HBD_MessageUnit, 0, msgcode_rwbuffer[1]);     /*firm_request_len,   1, 04-07*/
3812         acb->firm_numbers_queue = CHIP_REG_READ32(HBD_MessageUnit, 0, msgcode_rwbuffer[2]);     /*firm_numbers_queue, 2, 08-11*/
3813         acb->firm_sdram_size    = CHIP_REG_READ32(HBD_MessageUnit, 0, msgcode_rwbuffer[3]);     /*firm_sdram_size,    3, 12-15*/
3814         acb->firm_ide_channels  = CHIP_REG_READ32(HBD_MessageUnit, 0, msgcode_rwbuffer[4]);     /*firm_ide_channels,  4, 16-19*/
3815         acb->firm_cfg_version   = CHIP_REG_READ32(HBD_MessageUnit, 0, msgcode_rwbuffer[ARCMSR_FW_CFGVER_OFFSET]);       /*firm_cfg_version,  25,          */
3816         if(acb->firm_numbers_queue > ARCMSR_MAX_HBD_POSTQUEUE)
3817                 acb->maxOutstanding = ARCMSR_MAX_HBD_POSTQUEUE - 1;
3818         else
3819                 acb->maxOutstanding = acb->firm_numbers_queue - 1;
3820 }
3821 /*
3822 **********************************************************************
3823 **********************************************************************
3824 */
3825 static void arcmsr_get_hbe_config(struct AdapterControlBlock *acb)
3826 {
3827         char *acb_firm_model = acb->firm_model;
3828         char *acb_firm_version = acb->firm_version;
3829         char *acb_device_map = acb->device_map;
3830         size_t iop_firm_model = offsetof(struct HBE_MessageUnit,msgcode_rwbuffer[ARCMSR_FW_MODEL_OFFSET]);   /*firm_model,15,60-67*/
3831         size_t iop_firm_version = offsetof(struct HBE_MessageUnit,msgcode_rwbuffer[ARCMSR_FW_VERS_OFFSET]); /*firm_version,17,68-83*/
3832         size_t iop_device_map = offsetof(struct HBE_MessageUnit,msgcode_rwbuffer[ARCMSR_FW_DEVMAP_OFFSET]);
3833         int i;
3834
3835         CHIP_REG_WRITE32(HBE_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_GET_CONFIG);
3836         acb->out_doorbell ^= ARCMSR_HBEMU_DRV2IOP_MESSAGE_CMD_DONE;
3837         CHIP_REG_WRITE32(HBE_MessageUnit, 0, iobound_doorbell, acb->out_doorbell);
3838         if(!arcmsr_hbe_wait_msgint_ready(acb)) {
3839                 printf("arcmsr%d: wait 'get adapter firmware miscellaneous data' timeout \n", acb->pci_unit);
3840         }
3841
3842         i = 0;
3843         while(i < 8) {
3844                 *acb_firm_model = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_firm_model+i); 
3845                 /* 8 bytes firm_model, 15, 60-67*/
3846                 acb_firm_model++;
3847                 i++;
3848         }
3849         i = 0;
3850         while(i < 16) {
3851                 *acb_firm_version = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_firm_version+i);  
3852                 /* 16 bytes firm_version, 17, 68-83*/
3853                 acb_firm_version++;
3854                 i++;
3855         }
3856         i = 0;
3857         while(i < 16) {
3858                 *acb_device_map = bus_space_read_1(acb->btag[0], acb->bhandle[0], iop_device_map+i);  
3859                 acb_device_map++;
3860                 i++;
3861         }
3862         printf("Areca RAID adapter%d: %s F/W version %s \n", acb->pci_unit, acb->firm_model, acb->firm_version);
3863         acb->firm_request_len   = CHIP_REG_READ32(HBE_MessageUnit, 0, msgcode_rwbuffer[1]);     /*firm_request_len,   1, 04-07*/
3864         acb->firm_numbers_queue = CHIP_REG_READ32(HBE_MessageUnit, 0, msgcode_rwbuffer[2]);     /*firm_numbers_queue, 2, 08-11*/
3865         acb->firm_sdram_size    = CHIP_REG_READ32(HBE_MessageUnit, 0, msgcode_rwbuffer[3]);     /*firm_sdram_size,    3, 12-15*/
3866         acb->firm_ide_channels  = CHIP_REG_READ32(HBE_MessageUnit, 0, msgcode_rwbuffer[4]);     /*firm_ide_channels,  4, 16-19*/
3867         acb->firm_cfg_version   = CHIP_REG_READ32(HBE_MessageUnit, 0, msgcode_rwbuffer[ARCMSR_FW_CFGVER_OFFSET]);       /*firm_cfg_version,  25,          */
3868         if(acb->firm_numbers_queue > ARCMSR_MAX_OUTSTANDING_CMD)
3869                 acb->maxOutstanding = ARCMSR_MAX_OUTSTANDING_CMD - 1;
3870         else
3871                 acb->maxOutstanding = acb->firm_numbers_queue - 1;
3872 }
3873 /*
3874 **********************************************************************
3875 **********************************************************************
3876 */
3877 static void arcmsr_get_firmware_spec(struct AdapterControlBlock *acb)
3878 {
3879         switch (acb->adapter_type) {
3880         case ACB_ADAPTER_TYPE_A: {
3881                         arcmsr_get_hba_config(acb);
3882                 }
3883                 break;
3884         case ACB_ADAPTER_TYPE_B: {
3885                         arcmsr_get_hbb_config(acb);
3886                 }
3887                 break;
3888         case ACB_ADAPTER_TYPE_C: {
3889                         arcmsr_get_hbc_config(acb);
3890                 }
3891                 break;
3892         case ACB_ADAPTER_TYPE_D: {
3893                         arcmsr_get_hbd_config(acb);
3894                 }
3895                 break;
3896         case ACB_ADAPTER_TYPE_E: {
3897                         arcmsr_get_hbe_config(acb);
3898                 }
3899                 break;
3900         }
3901 }
3902 /*
3903 **********************************************************************
3904 **********************************************************************
3905 */
3906 static void arcmsr_wait_firmware_ready( struct AdapterControlBlock *acb)
3907 {
3908         int     timeout=0;
3909
3910         switch (acb->adapter_type) {
3911         case ACB_ADAPTER_TYPE_A: {
3912                         while ((CHIP_REG_READ32(HBA_MessageUnit, 0, outbound_msgaddr1) & ARCMSR_OUTBOUND_MESG1_FIRMWARE_OK) == 0)
3913                         {
3914                                 if (timeout++ > 2000) /* (2000*15)/1000 = 30 sec */
3915                                 {
3916                                         printf( "arcmsr%d:timed out waiting for firmware \n", acb->pci_unit);
3917                                         return;
3918                                 }
3919                                 UDELAY(15000); /* wait 15 milli-seconds */
3920                         }
3921                 }
3922                 break;
3923         case ACB_ADAPTER_TYPE_B: {
3924                         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
3925                         while ((READ_CHIP_REG32(0, phbbmu->iop2drv_doorbell) & ARCMSR_MESSAGE_FIRMWARE_OK) == 0)
3926                         {
3927                                 if (timeout++ > 2000) /* (2000*15)/1000 = 30 sec */
3928                                 {
3929                                         printf( "arcmsr%d: timed out waiting for firmware \n", acb->pci_unit);
3930                                         return;
3931                                 }
3932                                 UDELAY(15000); /* wait 15 milli-seconds */
3933                         }
3934                         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_DRV2IOP_END_OF_INTERRUPT);
3935                 }
3936                 break;
3937         case ACB_ADAPTER_TYPE_C: {
3938                         while ((CHIP_REG_READ32(HBC_MessageUnit, 0, outbound_msgaddr1) & ARCMSR_HBCMU_MESSAGE_FIRMWARE_OK) == 0)
3939                         {
3940                                 if (timeout++ > 2000) /* (2000*15)/1000 = 30 sec */
3941                                 {
3942                                         printf( "arcmsr%d:timed out waiting for firmware ready\n", acb->pci_unit);
3943                                         return;
3944                                 }
3945                                 UDELAY(15000); /* wait 15 milli-seconds */
3946                         }
3947                 }
3948                 break;
3949         case ACB_ADAPTER_TYPE_D: {
3950                         while ((CHIP_REG_READ32(HBD_MessageUnit, 0, outbound_msgaddr1) & ARCMSR_HBDMU_MESSAGE_FIRMWARE_OK) == 0)
3951                         {
3952                                 if (timeout++ > 2000) /* (2000*15)/1000 = 30 sec */
3953                                 {
3954                                         printf( "arcmsr%d:timed out waiting for firmware ready\n", acb->pci_unit);
3955                                         return;
3956                                 }
3957                                 UDELAY(15000); /* wait 15 milli-seconds */
3958                         }
3959                 }
3960                 break;
3961         case ACB_ADAPTER_TYPE_E: {
3962                         while ((CHIP_REG_READ32(HBE_MessageUnit, 0, outbound_msgaddr1) & ARCMSR_HBEMU_MESSAGE_FIRMWARE_OK) == 0)
3963                         {
3964                                 if (timeout++ > 4000) /* (4000*15)/1000 = 60 sec */
3965                                 {
3966                                         printf( "arcmsr%d:timed out waiting for firmware ready\n", acb->pci_unit);
3967                                         return;
3968                                 }
3969                                 UDELAY(15000); /* wait 15 milli-seconds */
3970                         }
3971                 }
3972                 break;
3973         }
3974 }
3975 /*
3976 **********************************************************************
3977 **********************************************************************
3978 */
3979 static void arcmsr_clear_doorbell_queue_buffer( struct AdapterControlBlock *acb)
3980 {
3981         u_int32_t outbound_doorbell;
3982
3983         switch (acb->adapter_type) {
3984         case ACB_ADAPTER_TYPE_A: {
3985                         /* empty doorbell Qbuffer if door bell ringed */
3986                         outbound_doorbell = CHIP_REG_READ32(HBA_MessageUnit, 0, outbound_doorbell);
3987                         CHIP_REG_WRITE32(HBA_MessageUnit, 0, outbound_doorbell, outbound_doorbell);     /*clear doorbell interrupt */
3988                         CHIP_REG_WRITE32(HBA_MessageUnit, 0, inbound_doorbell, ARCMSR_INBOUND_DRIVER_DATA_READ_OK);
3989                 }
3990                 break;
3991         case ACB_ADAPTER_TYPE_B: {
3992                         struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
3993                         WRITE_CHIP_REG32(0, phbbmu->iop2drv_doorbell, ARCMSR_DOORBELL_INT_CLEAR_PATTERN);/*clear interrupt and message state*/
3994                         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_DRV2IOP_DATA_READ_OK);
3995                         /* let IOP know data has been read */
3996                 }
3997                 break;
3998         case ACB_ADAPTER_TYPE_C: {
3999                         /* empty doorbell Qbuffer if door bell ringed */
4000                         outbound_doorbell = CHIP_REG_READ32(HBC_MessageUnit, 0, outbound_doorbell);
4001                         CHIP_REG_WRITE32(HBC_MessageUnit, 0, outbound_doorbell_clear, outbound_doorbell);       /*clear doorbell interrupt */
4002                         CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_doorbell, ARCMSR_HBCMU_DRV2IOP_DATA_READ_OK);
4003                         CHIP_REG_READ32(HBC_MessageUnit, 0, outbound_doorbell_clear); /* Dummy read to force pci flush */
4004                         CHIP_REG_READ32(HBC_MessageUnit, 0, inbound_doorbell); /* Dummy read to force pci flush */
4005                 }
4006                 break;
4007         case ACB_ADAPTER_TYPE_D: {
4008                         /* empty doorbell Qbuffer if door bell ringed */
4009                         outbound_doorbell = CHIP_REG_READ32(HBD_MessageUnit, 0, outbound_doorbell);
4010                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, outbound_doorbell, outbound_doorbell);     /*clear doorbell interrupt */
4011                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, inbound_doorbell, ARCMSR_HBDMU_DRV2IOP_DATA_OUT_READ);
4012                 }
4013                 break;
4014         case ACB_ADAPTER_TYPE_E: {
4015                         /* empty doorbell Qbuffer if door bell ringed */
4016                         acb->in_doorbell = CHIP_REG_READ32(HBE_MessageUnit, 0, iobound_doorbell);
4017                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, host_int_status, 0);       /*clear doorbell interrupt */
4018                         acb->out_doorbell ^= ARCMSR_HBEMU_DRV2IOP_DATA_READ_OK;
4019                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, iobound_doorbell, acb->out_doorbell);
4020                 }
4021                 break;
4022         }
4023 }
4024 /*
4025 ************************************************************************
4026 ************************************************************************
4027 */
4028 static u_int32_t arcmsr_iop_confirm(struct AdapterControlBlock *acb)
4029 {
4030         unsigned long srb_phyaddr;
4031         u_int32_t srb_phyaddr_hi32;
4032         u_int32_t srb_phyaddr_lo32;
4033
4034         /*
4035         ********************************************************************
4036         ** here we need to tell iop 331 our freesrb.HighPart 
4037         ** if freesrb.HighPart is not zero
4038         ********************************************************************
4039         */
4040         srb_phyaddr = (unsigned long) acb->srb_phyaddr.phyaddr;
4041         srb_phyaddr_hi32 = acb->srb_phyaddr.B.phyadd_high;
4042         srb_phyaddr_lo32 = acb->srb_phyaddr.B.phyadd_low;
4043         switch (acb->adapter_type) {
4044         case ACB_ADAPTER_TYPE_A: {
4045                         if(srb_phyaddr_hi32 != 0) {
4046                                 CHIP_REG_WRITE32(HBA_MessageUnit, 0, msgcode_rwbuffer[0], ARCMSR_SIGNATURE_SET_CONFIG);
4047                                 CHIP_REG_WRITE32(HBA_MessageUnit, 0, msgcode_rwbuffer[1], srb_phyaddr_hi32);
4048                                 CHIP_REG_WRITE32(HBA_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_SET_CONFIG);
4049                                 if(!arcmsr_hba_wait_msgint_ready(acb)) {
4050                                         printf( "arcmsr%d: 'set srb high part physical address' timeout \n", acb->pci_unit);
4051                                         return FALSE;
4052                                 }
4053                         }
4054                 }
4055                 break;
4056                 /*
4057                 ***********************************************************************
4058                 **    if adapter type B, set window of "post command Q" 
4059                 ***********************************************************************
4060                 */
4061         case ACB_ADAPTER_TYPE_B: {
4062                         u_int32_t post_queue_phyaddr;
4063                         struct HBB_MessageUnit *phbbmu;
4064
4065                         phbbmu = (struct HBB_MessageUnit *)acb->pmu;
4066                         phbbmu->postq_index = 0;
4067                         phbbmu->doneq_index = 0;
4068                         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_MESSAGE_SET_POST_WINDOW);
4069                         if(!arcmsr_hbb_wait_msgint_ready(acb)) {
4070                                 printf( "arcmsr%d: 'set window of post command Q' timeout\n", acb->pci_unit);
4071                                 return FALSE;
4072                         }
4073                         post_queue_phyaddr = srb_phyaddr + ARCMSR_SRBS_POOL_SIZE 
4074                                                                 + offsetof(struct HBB_MessageUnit, post_qbuffer);
4075                         CHIP_REG_WRITE32(HBB_RWBUFFER, 1, msgcode_rwbuffer[0], ARCMSR_SIGNATURE_SET_CONFIG); /* driver "set config" signature */
4076                         CHIP_REG_WRITE32(HBB_RWBUFFER, 1, msgcode_rwbuffer[1], srb_phyaddr_hi32); /* normal should be zero */
4077                         CHIP_REG_WRITE32(HBB_RWBUFFER, 1, msgcode_rwbuffer[2], post_queue_phyaddr); /* postQ size (256+8)*4 */
4078                         CHIP_REG_WRITE32(HBB_RWBUFFER, 1, msgcode_rwbuffer[3], post_queue_phyaddr+1056); /* doneQ size (256+8)*4 */
4079                         CHIP_REG_WRITE32(HBB_RWBUFFER, 1, msgcode_rwbuffer[4], 1056); /* srb maxQ size must be --> [(256+8)*4] */
4080                         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_MESSAGE_SET_CONFIG);
4081                         if(!arcmsr_hbb_wait_msgint_ready(acb)) {
4082                                 printf( "arcmsr%d: 'set command Q window' timeout \n", acb->pci_unit);
4083                                 return FALSE;
4084                         }
4085                         WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_MESSAGE_START_DRIVER_MODE);
4086                         if(!arcmsr_hbb_wait_msgint_ready(acb)) {
4087                                 printf( "arcmsr%d: 'start diver mode' timeout \n", acb->pci_unit);
4088                                 return FALSE;
4089                         }
4090                 }
4091                 break;
4092         case ACB_ADAPTER_TYPE_C: {
4093                         if(srb_phyaddr_hi32 != 0) {
4094                                 CHIP_REG_WRITE32(HBC_MessageUnit, 0, msgcode_rwbuffer[0], ARCMSR_SIGNATURE_SET_CONFIG);
4095                                 CHIP_REG_WRITE32(HBC_MessageUnit, 0, msgcode_rwbuffer[1], srb_phyaddr_hi32);
4096                                 CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_SET_CONFIG);
4097                                 CHIP_REG_WRITE32(HBC_MessageUnit, 0, inbound_doorbell,ARCMSR_HBCMU_DRV2IOP_MESSAGE_CMD_DONE);
4098                                 if(!arcmsr_hbc_wait_msgint_ready(acb)) {
4099                                         printf( "arcmsr%d: 'set srb high part physical address' timeout \n", acb->pci_unit);
4100                                         return FALSE;
4101                                 }
4102                         }
4103                 }
4104                 break;
4105         case ACB_ADAPTER_TYPE_D: {
4106                         u_int32_t post_queue_phyaddr, done_queue_phyaddr;
4107                         struct HBD_MessageUnit0 *phbdmu;
4108
4109                         phbdmu = (struct HBD_MessageUnit0 *)acb->pmu;
4110                         phbdmu->postq_index = 0;
4111                         phbdmu->doneq_index = 0x40FF;
4112                         post_queue_phyaddr = srb_phyaddr_lo32 + ARCMSR_SRBS_POOL_SIZE 
4113                                                                 + offsetof(struct HBD_MessageUnit0, post_qbuffer);
4114                         done_queue_phyaddr = srb_phyaddr_lo32 + ARCMSR_SRBS_POOL_SIZE 
4115                                                                 + offsetof(struct HBD_MessageUnit0, done_qbuffer);
4116                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, msgcode_rwbuffer[0], ARCMSR_SIGNATURE_SET_CONFIG); /* driver "set config" signature */
4117                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, msgcode_rwbuffer[1], srb_phyaddr_hi32);
4118                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, msgcode_rwbuffer[2], post_queue_phyaddr); /* postQ base */
4119                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, msgcode_rwbuffer[3], done_queue_phyaddr); /* doneQ base */
4120                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, msgcode_rwbuffer[4], 0x100);
4121                         CHIP_REG_WRITE32(HBD_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_SET_CONFIG);
4122                         if(!arcmsr_hbd_wait_msgint_ready(acb)) {
4123                                 printf( "arcmsr%d: 'set srb high part physical address' timeout \n", acb->pci_unit);
4124                                 return FALSE;
4125                         }
4126                 }
4127                 break;
4128         case ACB_ADAPTER_TYPE_E: {
4129                         u_int32_t cdb_phyaddr_lo32;
4130                         cdb_phyaddr_lo32 = srb_phyaddr_lo32 + offsetof(struct CommandControlBlock, arcmsr_cdb);
4131                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, msgcode_rwbuffer[0], ARCMSR_SIGNATURE_SET_CONFIG);
4132                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, msgcode_rwbuffer[1], ARCMSR_SIGNATURE_1884);
4133                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, msgcode_rwbuffer[2], cdb_phyaddr_lo32);
4134                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, msgcode_rwbuffer[3], srb_phyaddr_hi32);
4135                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, msgcode_rwbuffer[4], SRB_SIZE);
4136                         cdb_phyaddr_lo32 = srb_phyaddr_lo32 + ARCMSR_SRBS_POOL_SIZE;
4137                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, msgcode_rwbuffer[5], cdb_phyaddr_lo32);
4138                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, msgcode_rwbuffer[6], srb_phyaddr_hi32);
4139                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, msgcode_rwbuffer[7], COMPLETION_Q_POOL_SIZE);
4140                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, inbound_msgaddr0, ARCMSR_INBOUND_MESG0_SET_CONFIG);
4141                         acb->out_doorbell ^= ARCMSR_HBEMU_DRV2IOP_MESSAGE_CMD_DONE;
4142                         CHIP_REG_WRITE32(HBE_MessageUnit, 0, iobound_doorbell, acb->out_doorbell);
4143                         if(!arcmsr_hbe_wait_msgint_ready(acb)) {
4144                                 printf( "arcmsr%d: 'set srb high part physical address' timeout \n", acb->pci_unit);
4145                                 return FALSE;
4146                         }
4147                 }
4148                 break;
4149         }
4150         return (TRUE);
4151 }
4152 /*
4153 ************************************************************************
4154 ************************************************************************
4155 */
4156 static void arcmsr_enable_eoi_mode(struct AdapterControlBlock *acb)
4157 {
4158         if (acb->adapter_type == ACB_ADAPTER_TYPE_B)
4159         {
4160                 struct HBB_MessageUnit *phbbmu = (struct HBB_MessageUnit *)acb->pmu;
4161                 WRITE_CHIP_REG32(0, phbbmu->drv2iop_doorbell, ARCMSR_MESSAGE_ACTIVE_EOI_MODE);
4162                 if(!arcmsr_hbb_wait_msgint_ready(acb)) {
4163                         printf( "arcmsr%d: 'iop enable eoi mode' timeout \n", acb->pci_unit);
4164                         return;
4165                 }
4166         }
4167 }
4168 /*
4169 **********************************************************************
4170 **********************************************************************
4171 */
4172 static void arcmsr_iop_init(struct AdapterControlBlock *acb)
4173 {
4174         u_int32_t intmask_org;
4175
4176         /* disable all outbound interrupt */
4177         intmask_org = arcmsr_disable_allintr(acb);
4178         arcmsr_wait_firmware_ready(acb);
4179         arcmsr_iop_confirm(acb);
4180         arcmsr_get_firmware_spec(acb);
4181         /*start background rebuild*/
4182         arcmsr_start_adapter_bgrb(acb);
4183         /* empty doorbell Qbuffer if door bell ringed */
4184         arcmsr_clear_doorbell_queue_buffer(acb);
4185         arcmsr_enable_eoi_mode(acb);
4186         /* enable outbound Post Queue, outbound doorbell Interrupt */
4187         arcmsr_enable_allintr(acb, intmask_org);
4188         acb->acb_flags |= ACB_F_IOP_INITED;
4189 }
4190 /*
4191 **********************************************************************
4192 **********************************************************************
4193 */
4194 static void arcmsr_map_free_srb(void *arg, bus_dma_segment_t *segs, int nseg, int error)
4195 {
4196         struct AdapterControlBlock *acb = arg;
4197         struct CommandControlBlock *srb_tmp;
4198         u_int32_t i;
4199         unsigned long srb_phyaddr = (unsigned long)segs->ds_addr;
4200
4201         acb->srb_phyaddr.phyaddr = srb_phyaddr; 
4202         srb_tmp = (struct CommandControlBlock *)acb->uncacheptr;
4203         for(i=0; i < ARCMSR_MAX_FREESRB_NUM; i++) {
4204                 if(bus_dmamap_create(acb->dm_segs_dmat,
4205                          /*flags*/0, &srb_tmp->dm_segs_dmamap) != 0) {
4206                         acb->acb_flags |= ACB_F_MAPFREESRB_FAILD;
4207                         printf("arcmsr%d:"
4208                         " srb dmamap bus_dmamap_create error\n", acb->pci_unit);
4209                         return;
4210                 }
4211                 if((acb->adapter_type == ACB_ADAPTER_TYPE_C) || (acb->adapter_type == ACB_ADAPTER_TYPE_D)
4212                          || (acb->adapter_type == ACB_ADAPTER_TYPE_E))
4213                 {
4214                         srb_tmp->cdb_phyaddr_low = srb_phyaddr;
4215                         srb_tmp->cdb_phyaddr_high = (u_int32_t)((srb_phyaddr >> 16) >> 16);
4216                 }
4217                 else
4218                         srb_tmp->cdb_phyaddr_low = srb_phyaddr >> 5;
4219                 srb_tmp->acb = acb;
4220                 srb_tmp->smid = i << 16;
4221                 acb->srbworkingQ[i] = acb->psrb_pool[i] = srb_tmp;
4222                 srb_phyaddr = srb_phyaddr + SRB_SIZE;
4223                 srb_tmp = (struct CommandControlBlock *)((unsigned long)srb_tmp + SRB_SIZE);
4224         }
4225         if (acb->adapter_type == ACB_ADAPTER_TYPE_E)
4226                 acb->pCompletionQ = (pCompletion_Q)srb_tmp;
4227         acb->vir2phy_offset = (unsigned long)srb_tmp - (unsigned long)srb_phyaddr;
4228 }
4229 /*
4230 ************************************************************************
4231 ************************************************************************
4232 */
4233 static void arcmsr_free_resource(struct AdapterControlBlock *acb)
4234 {
4235         /* remove the control device */
4236         if(acb->ioctl_dev != NULL) {
4237                 destroy_dev(acb->ioctl_dev);
4238         }
4239         bus_dmamap_unload(acb->srb_dmat, acb->srb_dmamap);
4240         bus_dmamap_destroy(acb->srb_dmat, acb->srb_dmamap);
4241         bus_dma_tag_destroy(acb->srb_dmat);
4242         bus_dma_tag_destroy(acb->dm_segs_dmat);
4243         bus_dma_tag_destroy(acb->parent_dmat);
4244 }
4245 /*
4246 ************************************************************************
4247 ************************************************************************
4248 */
4249 static void arcmsr_mutex_init(struct AdapterControlBlock *acb)
4250 {
4251         ARCMSR_LOCK_INIT(&acb->isr_lock, "arcmsr isr lock");
4252         ARCMSR_LOCK_INIT(&acb->srb_lock, "arcmsr srb lock");
4253         ARCMSR_LOCK_INIT(&acb->postDone_lock, "arcmsr postQ lock");
4254         ARCMSR_LOCK_INIT(&acb->qbuffer_lock, "arcmsr RW buffer lock");
4255 }
4256 /*
4257 ************************************************************************
4258 ************************************************************************
4259 */
4260 static void arcmsr_mutex_destroy(struct AdapterControlBlock *acb)
4261 {
4262         ARCMSR_LOCK_DESTROY(&acb->qbuffer_lock);
4263         ARCMSR_LOCK_DESTROY(&acb->postDone_lock);
4264         ARCMSR_LOCK_DESTROY(&acb->srb_lock);
4265         ARCMSR_LOCK_DESTROY(&acb->isr_lock);
4266 }
4267 /*
4268 ************************************************************************
4269 ************************************************************************
4270 */
4271 static u_int32_t arcmsr_initialize(device_t dev)
4272 {
4273         struct AdapterControlBlock *acb = device_get_softc(dev);
4274         u_int16_t pci_command;
4275         int i, j,max_coherent_size;
4276         u_int32_t vendor_dev_id;
4277
4278         vendor_dev_id = pci_get_devid(dev);
4279         acb->vendor_device_id = vendor_dev_id;
4280         acb->sub_device_id = pci_read_config(dev, PCIR_SUBDEV_0, 2);
4281         switch (vendor_dev_id) {
4282         case PCIDevVenIDARC1880:
4283         case PCIDevVenIDARC1882:
4284         case PCIDevVenIDARC1213:
4285         case PCIDevVenIDARC1223: {
4286                         acb->adapter_type = ACB_ADAPTER_TYPE_C;
4287                         if ((acb->sub_device_id == ARECA_SUB_DEV_ID_1883) ||
4288                             (acb->sub_device_id == ARECA_SUB_DEV_ID_1216) ||
4289                             (acb->sub_device_id == ARECA_SUB_DEV_ID_1226))
4290                                 acb->adapter_bus_speed = ACB_BUS_SPEED_12G;
4291                         else
4292                                 acb->adapter_bus_speed = ACB_BUS_SPEED_6G;
4293                         max_coherent_size = ARCMSR_SRBS_POOL_SIZE;
4294                 }
4295                 break;
4296         case PCIDevVenIDARC1884:
4297                 acb->adapter_type = ACB_ADAPTER_TYPE_E;
4298                 acb->adapter_bus_speed = ACB_BUS_SPEED_12G;
4299                 max_coherent_size = ARCMSR_SRBS_POOL_SIZE + COMPLETION_Q_POOL_SIZE;
4300                 acb->completionQ_entry = COMPLETION_Q_POOL_SIZE / sizeof(struct deliver_completeQ);
4301                 break;
4302         case PCIDevVenIDARC1214: {
4303                         acb->adapter_type = ACB_ADAPTER_TYPE_D;
4304                         acb->adapter_bus_speed = ACB_BUS_SPEED_6G;
4305                         max_coherent_size = ARCMSR_SRBS_POOL_SIZE + (sizeof(struct HBD_MessageUnit0));
4306                 }
4307                 break;
4308         case PCIDevVenIDARC1200:
4309         case PCIDevVenIDARC1201: {
4310                         acb->adapter_type = ACB_ADAPTER_TYPE_B;
4311                         acb->adapter_bus_speed = ACB_BUS_SPEED_3G;
4312                         max_coherent_size = ARCMSR_SRBS_POOL_SIZE + (sizeof(struct HBB_MessageUnit));
4313                 }
4314                 break;
4315         case PCIDevVenIDARC1203: {
4316                         acb->adapter_type = ACB_ADAPTER_TYPE_B;
4317                         acb->adapter_bus_speed = ACB_BUS_SPEED_6G;
4318                         max_coherent_size = ARCMSR_SRBS_POOL_SIZE + (sizeof(struct HBB_MessageUnit));
4319                 }
4320                 break;
4321         case PCIDevVenIDARC1110:
4322         case PCIDevVenIDARC1120:
4323         case PCIDevVenIDARC1130:
4324         case PCIDevVenIDARC1160:
4325         case PCIDevVenIDARC1170:
4326         case PCIDevVenIDARC1210:
4327         case PCIDevVenIDARC1220:
4328         case PCIDevVenIDARC1230:
4329         case PCIDevVenIDARC1231:
4330         case PCIDevVenIDARC1260:
4331         case PCIDevVenIDARC1261:
4332         case PCIDevVenIDARC1270:
4333         case PCIDevVenIDARC1280:
4334         case PCIDevVenIDARC1212:
4335         case PCIDevVenIDARC1222:
4336         case PCIDevVenIDARC1380:
4337         case PCIDevVenIDARC1381:
4338         case PCIDevVenIDARC1680:
4339         case PCIDevVenIDARC1681: {
4340                         acb->adapter_type = ACB_ADAPTER_TYPE_A;
4341                         acb->adapter_bus_speed = ACB_BUS_SPEED_3G;
4342                         max_coherent_size = ARCMSR_SRBS_POOL_SIZE;
4343                 }
4344                 break;
4345         default: {
4346                         printf("arcmsr%d:"
4347                         " unknown RAID adapter type \n", device_get_unit(dev));
4348                         return ENOMEM;
4349                 }
4350         }
4351         if(bus_dma_tag_create(  /*PCI parent*/          bus_get_dma_tag(dev),
4352                                 /*alignemnt*/           1,
4353                                 /*boundary*/            0,
4354                                 /*lowaddr*/             BUS_SPACE_MAXADDR,
4355                                 /*highaddr*/            BUS_SPACE_MAXADDR,
4356                                 /*filter*/              NULL,
4357                                 /*filterarg*/           NULL,
4358                                 /*maxsize*/             BUS_SPACE_MAXSIZE_32BIT,
4359                                 /*nsegments*/           BUS_SPACE_UNRESTRICTED,
4360                                 /*maxsegsz*/            BUS_SPACE_MAXSIZE_32BIT,
4361                                 /*flags*/               0,
4362                                 /*lockfunc*/            NULL,
4363                                 /*lockarg*/             NULL,
4364                                                         &acb->parent_dmat) != 0)
4365         {
4366                 printf("arcmsr%d: parent_dmat bus_dma_tag_create failure!\n", device_get_unit(dev));
4367                 return ENOMEM;
4368         }
4369
4370         /* Create a single tag describing a region large enough to hold all of the s/g lists we will need. */
4371         if(bus_dma_tag_create(  /*parent_dmat*/         acb->parent_dmat,
4372                                 /*alignment*/           1,
4373                                 /*boundary*/            0,
4374 #ifdef PAE
4375                                 /*lowaddr*/             BUS_SPACE_MAXADDR_32BIT,
4376 #else
4377                                 /*lowaddr*/             BUS_SPACE_MAXADDR,
4378 #endif
4379                                 /*highaddr*/            BUS_SPACE_MAXADDR,
4380                                 /*filter*/              NULL,
4381                                 /*filterarg*/           NULL,
4382                                 /*maxsize*/             ARCMSR_MAX_SG_ENTRIES * PAGE_SIZE * ARCMSR_MAX_FREESRB_NUM,
4383                                 /*nsegments*/           ARCMSR_MAX_SG_ENTRIES,
4384                                 /*maxsegsz*/            BUS_SPACE_MAXSIZE_32BIT,
4385                                 /*flags*/               0,
4386                                 /*lockfunc*/            busdma_lock_mutex,
4387                                 /*lockarg*/             &acb->isr_lock,
4388                                                         &acb->dm_segs_dmat) != 0)
4389         {
4390                 bus_dma_tag_destroy(acb->parent_dmat);
4391                 printf("arcmsr%d: dm_segs_dmat bus_dma_tag_create failure!\n", device_get_unit(dev));
4392                 return ENOMEM;
4393         }
4394
4395         /* DMA tag for our srb structures.... Allocate the freesrb memory */
4396         if(bus_dma_tag_create(  /*parent_dmat*/         acb->parent_dmat,
4397                                 /*alignment*/           0x20,
4398                                 /*boundary*/            0,
4399                                 /*lowaddr*/             BUS_SPACE_MAXADDR_32BIT,
4400                                 /*highaddr*/            BUS_SPACE_MAXADDR,
4401                                 /*filter*/              NULL,
4402                                 /*filterarg*/           NULL,
4403                                 /*maxsize*/             max_coherent_size,
4404                                 /*nsegments*/           1,
4405                                 /*maxsegsz*/            BUS_SPACE_MAXSIZE_32BIT,
4406                                 /*flags*/               0,
4407                                 /*lockfunc*/            NULL,
4408                                 /*lockarg*/             NULL,
4409                                                         &acb->srb_dmat) != 0)
4410         {
4411                 bus_dma_tag_destroy(acb->dm_segs_dmat);
4412                 bus_dma_tag_destroy(acb->parent_dmat);
4413                 printf("arcmsr%d: srb_dmat bus_dma_tag_create failure!\n", device_get_unit(dev));
4414                 return ENXIO;
4415         }
4416         /* Allocation for our srbs */
4417         if(bus_dmamem_alloc(acb->srb_dmat, (void **)&acb->uncacheptr, BUS_DMA_WAITOK | BUS_DMA_COHERENT | BUS_DMA_ZERO, &acb->srb_dmamap) != 0) {
4418                 bus_dma_tag_destroy(acb->srb_dmat);
4419                 bus_dma_tag_destroy(acb->dm_segs_dmat);
4420                 bus_dma_tag_destroy(acb->parent_dmat);
4421                 printf("arcmsr%d: srb_dmat bus_dmamem_alloc failure!\n", device_get_unit(dev));
4422                 return ENXIO;
4423         }
4424         /* And permanently map them */
4425         if(bus_dmamap_load(acb->srb_dmat, acb->srb_dmamap, acb->uncacheptr, max_coherent_size, arcmsr_map_free_srb, acb, /*flags*/0)) {
4426                 bus_dma_tag_destroy(acb->srb_dmat);
4427                 bus_dma_tag_destroy(acb->dm_segs_dmat);
4428                 bus_dma_tag_destroy(acb->parent_dmat);
4429                 printf("arcmsr%d: srb_dmat bus_dmamap_load failure!\n", device_get_unit(dev));
4430                 return ENXIO;
4431         }
4432         pci_command = pci_read_config(dev, PCIR_COMMAND, 2);
4433         pci_command |= PCIM_CMD_BUSMASTEREN;
4434         pci_command |= PCIM_CMD_PERRESPEN;
4435         pci_command |= PCIM_CMD_MWRICEN;
4436         /* Enable Busmaster */
4437         pci_write_config(dev, PCIR_COMMAND, pci_command, 2);
4438         switch(acb->adapter_type) {
4439         case ACB_ADAPTER_TYPE_A: {
4440                 u_int32_t rid0 = PCIR_BAR(0);
4441                 vm_offset_t     mem_base0;
4442
4443                 acb->sys_res_arcmsr[0] = bus_alloc_resource_any(dev,SYS_RES_MEMORY, &rid0, RF_ACTIVE);
4444                 if(acb->sys_res_arcmsr[0] == NULL) {
4445                         arcmsr_free_resource(acb);
4446                         printf("arcmsr%d: bus_alloc_resource failure!\n", device_get_unit(dev));
4447                         return ENOMEM;
4448                 }
4449                 if(rman_get_start(acb->sys_res_arcmsr[0]) <= 0) {
4450                         arcmsr_free_resource(acb);
4451                         printf("arcmsr%d: rman_get_start failure!\n", device_get_unit(dev));
4452                         return ENXIO;
4453                 }
4454                 mem_base0 = (vm_offset_t) rman_get_virtual(acb->sys_res_arcmsr[0]);
4455                 if(mem_base0 == 0) {
4456                         arcmsr_free_resource(acb);
4457                         printf("arcmsr%d: rman_get_virtual failure!\n", device_get_unit(dev));
4458                         return ENXIO;
4459                 }
4460                 acb->btag[0] = rman_get_bustag(acb->sys_res_arcmsr[0]);
4461                 acb->bhandle[0] = rman_get_bushandle(acb->sys_res_arcmsr[0]);
4462                 acb->pmu = (struct MessageUnit_UNION *)mem_base0;
4463                 acb->rid[0] = rid0;
4464                 }
4465                 break;
4466         case ACB_ADAPTER_TYPE_B: {
4467                 struct HBB_MessageUnit *phbbmu;
4468                 struct CommandControlBlock *freesrb;
4469                 u_int32_t rid[]={ PCIR_BAR(0), PCIR_BAR(2) };
4470                 vm_offset_t     mem_base[]={0,0};
4471                 for(i=0; i < 2; i++) {
4472                         acb->sys_res_arcmsr[i] = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid[i], RF_ACTIVE);
4473                         if(acb->sys_res_arcmsr[i] == NULL) {
4474                                 arcmsr_free_resource(acb);
4475                                 printf("arcmsr%d: bus_alloc_resource %d failure!\n", device_get_unit(dev), i);
4476                                 return ENOMEM;
4477                         }
4478                         if(rman_get_start(acb->sys_res_arcmsr[i]) <= 0) {
4479                                 arcmsr_free_resource(acb);
4480                                 printf("arcmsr%d: rman_get_start %d failure!\n", device_get_unit(dev), i);
4481                                 return ENXIO;
4482                         }
4483                         mem_base[i] = (vm_offset_t) rman_get_virtual(acb->sys_res_arcmsr[i]);
4484                         if(mem_base[i] == 0) {
4485                                 arcmsr_free_resource(acb);
4486                                 printf("arcmsr%d: rman_get_virtual %d failure!\n", device_get_unit(dev), i);
4487                                 return ENXIO;
4488                         }
4489                         acb->btag[i] = rman_get_bustag(acb->sys_res_arcmsr[i]);
4490                         acb->bhandle[i] = rman_get_bushandle(acb->sys_res_arcmsr[i]);
4491                 }
4492                 freesrb = (struct CommandControlBlock *)acb->uncacheptr;
4493                 acb->pmu = (struct MessageUnit_UNION *)((unsigned long)freesrb+ARCMSR_SRBS_POOL_SIZE);
4494                 phbbmu = (struct HBB_MessageUnit *)acb->pmu;
4495                 phbbmu->hbb_doorbell = (struct HBB_DOORBELL *)mem_base[0];
4496                 phbbmu->hbb_rwbuffer = (struct HBB_RWBUFFER *)mem_base[1];
4497                 if (vendor_dev_id == PCIDevVenIDARC1203) {
4498                         phbbmu->drv2iop_doorbell = offsetof(struct HBB_DOORBELL_1203, drv2iop_doorbell);
4499                         phbbmu->drv2iop_doorbell_mask = offsetof(struct HBB_DOORBELL_1203, drv2iop_doorbell_mask);
4500                         phbbmu->iop2drv_doorbell = offsetof(struct HBB_DOORBELL_1203, iop2drv_doorbell);
4501                         phbbmu->iop2drv_doorbell_mask = offsetof(struct HBB_DOORBELL_1203, iop2drv_doorbell_mask);
4502                 } else {
4503                         phbbmu->drv2iop_doorbell = offsetof(struct HBB_DOORBELL, drv2iop_doorbell);
4504                         phbbmu->drv2iop_doorbell_mask = offsetof(struct HBB_DOORBELL, drv2iop_doorbell_mask);
4505                         phbbmu->iop2drv_doorbell = offsetof(struct HBB_DOORBELL, iop2drv_doorbell);
4506                         phbbmu->iop2drv_doorbell_mask = offsetof(struct HBB_DOORBELL, iop2drv_doorbell_mask);
4507                 }
4508                 acb->rid[0] = rid[0];
4509                 acb->rid[1] = rid[1];
4510                 }
4511                 break;
4512         case ACB_ADAPTER_TYPE_C: {
4513                 u_int32_t rid0 = PCIR_BAR(1);
4514                 vm_offset_t     mem_base0;
4515
4516                 acb->sys_res_arcmsr[0] = bus_alloc_resource_any(dev,SYS_RES_MEMORY, &rid0, RF_ACTIVE);
4517                 if(acb->sys_res_arcmsr[0] == NULL) {
4518                         arcmsr_free_resource(acb);
4519                         printf("arcmsr%d: bus_alloc_resource failure!\n", device_get_unit(dev));
4520                         return ENOMEM;
4521                 }
4522                 if(rman_get_start(acb->sys_res_arcmsr[0]) <= 0) {
4523                         arcmsr_free_resource(acb);
4524                         printf("arcmsr%d: rman_get_start failure!\n", device_get_unit(dev));
4525                         return ENXIO;
4526                 }
4527                 mem_base0 = (vm_offset_t) rman_get_virtual(acb->sys_res_arcmsr[0]);
4528                 if(mem_base0 == 0) {
4529                         arcmsr_free_resource(acb);
4530                         printf("arcmsr%d: rman_get_virtual failure!\n", device_get_unit(dev));
4531                         return ENXIO;
4532                 }
4533                 acb->btag[0] = rman_get_bustag(acb->sys_res_arcmsr[0]);
4534                 acb->bhandle[0] = rman_get_bushandle(acb->sys_res_arcmsr[0]);
4535                 acb->pmu = (struct MessageUnit_UNION *)mem_base0;
4536                 acb->rid[0] = rid0;
4537                 }
4538                 break;
4539         case ACB_ADAPTER_TYPE_D: {
4540                 struct HBD_MessageUnit0 *phbdmu;
4541                 u_int32_t rid0 = PCIR_BAR(0);
4542                 vm_offset_t     mem_base0;
4543
4544                 acb->sys_res_arcmsr[0] = bus_alloc_resource_any(dev,SYS_RES_MEMORY, &rid0, RF_ACTIVE);
4545                 if(acb->sys_res_arcmsr[0] == NULL) {
4546                         arcmsr_free_resource(acb);
4547                         printf("arcmsr%d: bus_alloc_resource failure!\n", device_get_unit(dev));
4548                         return ENOMEM;
4549                 }
4550                 if(rman_get_start(acb->sys_res_arcmsr[0]) <= 0) {
4551                         arcmsr_free_resource(acb);
4552                         printf("arcmsr%d: rman_get_start failure!\n", device_get_unit(dev));
4553                         return ENXIO;
4554                 }
4555                 mem_base0 = (vm_offset_t) rman_get_virtual(acb->sys_res_arcmsr[0]);
4556                 if(mem_base0 == 0) {
4557                         arcmsr_free_resource(acb);
4558                         printf("arcmsr%d: rman_get_virtual failure!\n", device_get_unit(dev));
4559                         return ENXIO;
4560                 }
4561                 acb->btag[0] = rman_get_bustag(acb->sys_res_arcmsr[0]);
4562                 acb->bhandle[0] = rman_get_bushandle(acb->sys_res_arcmsr[0]);
4563                 acb->pmu = (struct MessageUnit_UNION *)((unsigned long)acb->uncacheptr+ARCMSR_SRBS_POOL_SIZE);
4564                 phbdmu = (struct HBD_MessageUnit0 *)acb->pmu;
4565                 phbdmu->phbdmu = (struct HBD_MessageUnit *)mem_base0;
4566                 acb->rid[0] = rid0;
4567                 }
4568                 break;
4569         case ACB_ADAPTER_TYPE_E: {
4570                 u_int32_t rid0 = PCIR_BAR(1);
4571                 vm_offset_t     mem_base0;
4572
4573                 acb->sys_res_arcmsr[0] = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid0, RF_ACTIVE);
4574                 if(acb->sys_res_arcmsr[0] == NULL) {
4575                         arcmsr_free_resource(acb);
4576                         printf("arcmsr%d: bus_alloc_resource failure!\n", device_get_unit(dev));
4577                         return ENOMEM;
4578                 }
4579                 if(rman_get_start(acb->sys_res_arcmsr[0]) <= 0) {
4580                         arcmsr_free_resource(acb);
4581                         printf("arcmsr%d: rman_get_start failure!\n", device_get_unit(dev));
4582                         return ENXIO;
4583                 }
4584                 mem_base0 = (vm_offset_t) rman_get_virtual(acb->sys_res_arcmsr[0]);
4585                 if(mem_base0 == 0) {
4586                         arcmsr_free_resource(acb);
4587                         printf("arcmsr%d: rman_get_virtual failure!\n", device_get_unit(dev));
4588                         return ENXIO;
4589                 }
4590                 acb->btag[0] = rman_get_bustag(acb->sys_res_arcmsr[0]);
4591                 acb->bhandle[0] = rman_get_bushandle(acb->sys_res_arcmsr[0]);
4592                 acb->pmu = (struct MessageUnit_UNION *)mem_base0;
4593                 acb->doneq_index = 0;
4594                 acb->in_doorbell = 0;
4595                 acb->out_doorbell = 0;
4596                 acb->rid[0] = rid0;
4597                 CHIP_REG_WRITE32(HBE_MessageUnit, 0, host_int_status, 0); /*clear interrupt*/
4598                 CHIP_REG_WRITE32(HBE_MessageUnit, 0, iobound_doorbell, ARCMSR_HBEMU_DOORBELL_SYNC); /* synchronize doorbell to 0 */
4599                 }
4600                 break;
4601         }
4602         if(acb->acb_flags & ACB_F_MAPFREESRB_FAILD) {
4603                 arcmsr_free_resource(acb);
4604                 printf("arcmsr%d: map free srb failure!\n", device_get_unit(dev));
4605                 return ENXIO;
4606         }
4607         acb->acb_flags  |= (ACB_F_MESSAGE_WQBUFFER_CLEARED|ACB_F_MESSAGE_RQBUFFER_CLEARED|ACB_F_MESSAGE_WQBUFFER_READ);
4608         acb->acb_flags &= ~ACB_F_SCSISTOPADAPTER;
4609         /*
4610         ********************************************************************
4611         ** init raid volume state
4612         ********************************************************************
4613         */
4614         for(i=0; i < ARCMSR_MAX_TARGETID; i++) {
4615                 for(j=0; j < ARCMSR_MAX_TARGETLUN; j++) {
4616                         acb->devstate[i][j] = ARECA_RAID_GONE;
4617                 }
4618         }
4619         arcmsr_iop_init(acb);
4620         return(0);
4621 }
4622
4623 static int arcmsr_setup_msix(struct AdapterControlBlock *acb)
4624 {
4625         int i;
4626
4627         for (i = 0; i < acb->msix_vectors; i++) {
4628                 acb->irq_id[i] = 1 + i;
4629                 acb->irqres[i] = bus_alloc_resource_any(acb->pci_dev,
4630                     SYS_RES_IRQ, &acb->irq_id[i], RF_ACTIVE);
4631                 if (acb->irqres[i] == NULL) {
4632                         printf("arcmsr: Can't allocate MSI-X resource\n");
4633                         goto irq_alloc_failed;
4634                 }
4635                 if (bus_setup_intr(acb->pci_dev, acb->irqres[i],
4636                     INTR_MPSAFE | INTR_TYPE_CAM, NULL, arcmsr_intr_handler,
4637                     acb, &acb->ih[i])) {
4638                         printf("arcmsr: Cannot set up MSI-X interrupt handler\n");
4639                         goto irq_alloc_failed;
4640                 }
4641         }
4642         printf("arcmsr: MSI-X INT enabled\n");
4643         acb->acb_flags |= ACB_F_MSIX_ENABLED;
4644         return TRUE;
4645
4646 irq_alloc_failed:
4647         arcmsr_teardown_intr(acb->pci_dev, acb);
4648         return FALSE;
4649 }
4650
4651 /*
4652 ************************************************************************
4653 ************************************************************************
4654 */
4655 static int arcmsr_attach(device_t dev)
4656 {
4657         struct AdapterControlBlock *acb=(struct AdapterControlBlock *)device_get_softc(dev);
4658         u_int32_t unit=device_get_unit(dev);
4659         struct ccb_setasync csa;
4660         struct cam_devq *devq;  /* Device Queue to use for this SIM */
4661         struct resource *irqres;
4662
4663         if(acb == NULL) {
4664                 printf("arcmsr%d: cannot allocate softc\n", unit);
4665                 return (ENOMEM);
4666         }
4667         arcmsr_mutex_init(acb);
4668         acb->pci_dev = dev;
4669         acb->pci_unit = unit;
4670         if(arcmsr_initialize(dev)) {
4671                 printf("arcmsr%d: initialize failure!\n", unit);
4672                 goto initialize_failed;
4673         }
4674         /* After setting up the adapter, map our interrupt */
4675         acb->msix_vectors = ARCMSR_NUM_MSIX_VECTORS;
4676         if (pci_alloc_msix(dev, &acb->msix_vectors) == 0) {
4677                 if (arcmsr_setup_msix(acb) == TRUE)
4678                         goto irqx;
4679         }
4680         acb->irq_id[0] = 0;
4681         irqres = bus_alloc_resource_any(dev, SYS_RES_IRQ, &acb->irq_id[0], RF_SHAREABLE | RF_ACTIVE);
4682         if(irqres == NULL || 
4683                 bus_setup_intr(dev, irqres, INTR_TYPE_CAM|INTR_ENTROPY|INTR_MPSAFE, NULL, arcmsr_intr_handler, acb, &acb->ih[0])) {
4684                 printf("arcmsr%d: unable to register interrupt handler!\n", unit);
4685                 goto setup_intr_failed;
4686         }
4687         acb->irqres[0] = irqres;
4688 irqx:
4689         /*
4690          * Now let the CAM generic SCSI layer find the SCSI devices on
4691          * the bus *  start queue to reset to the idle loop. *
4692          * Create device queue of SIM(s) *  (MAX_START_JOB - 1) :
4693          * max_sim_transactions
4694         */
4695         devq = cam_simq_alloc(acb->maxOutstanding);
4696         if(devq == NULL) {
4697                 printf("arcmsr%d: cam_simq_alloc failure!\n", unit);
4698                 goto simq_alloc_failed;
4699         }
4700         acb->psim = cam_sim_alloc(arcmsr_action, arcmsr_poll, "arcmsr", acb, unit, &acb->isr_lock, 1, ARCMSR_MAX_OUTSTANDING_CMD, devq);
4701         if(acb->psim == NULL) {
4702                 printf("arcmsr%d: cam_sim_alloc failure!\n", unit);
4703                 goto sim_alloc_failed;
4704         }
4705         ARCMSR_LOCK_ACQUIRE(&acb->isr_lock);
4706         if(xpt_bus_register(acb->psim, dev, 0) != CAM_SUCCESS) {
4707                 printf("arcmsr%d: xpt_bus_register failure!\n", unit);
4708                 goto xpt_bus_failed;
4709         }
4710         if(xpt_create_path(&acb->ppath, /* periph */ NULL, cam_sim_path(acb->psim), CAM_TARGET_WILDCARD, CAM_LUN_WILDCARD) != CAM_REQ_CMP) {
4711                 printf("arcmsr%d: xpt_create_path failure!\n", unit);
4712                 goto xpt_path_failed;
4713         }
4714         /*
4715         ****************************************************
4716         */
4717         xpt_setup_ccb(&csa.ccb_h, acb->ppath, /*priority*/5);
4718         csa.ccb_h.func_code = XPT_SASYNC_CB;
4719         csa.event_enable = AC_FOUND_DEVICE|AC_LOST_DEVICE;
4720         csa.callback = arcmsr_async;
4721         csa.callback_arg = acb->psim;
4722         xpt_action((union ccb *)&csa);
4723         ARCMSR_LOCK_RELEASE(&acb->isr_lock);
4724         /* Create the control device.  */
4725         acb->ioctl_dev = make_dev(&arcmsr_cdevsw, unit, UID_ROOT, GID_WHEEL /* GID_OPERATOR */, S_IRUSR | S_IWUSR, "arcmsr%d", unit);
4726                 
4727         (void)make_dev_alias(acb->ioctl_dev, "arc%d", unit);
4728         arcmsr_callout_init(&acb->devmap_callout);
4729         callout_reset(&acb->devmap_callout, 60 * hz, arcmsr_polling_devmap, acb);
4730         return (0);
4731 xpt_path_failed:
4732         xpt_bus_deregister(cam_sim_path(acb->psim));
4733 xpt_bus_failed:
4734         cam_sim_free(acb->psim, /* free_simq */ TRUE);
4735 sim_alloc_failed:
4736         cam_simq_free(devq);
4737 simq_alloc_failed:
4738         arcmsr_teardown_intr(dev, acb);
4739 setup_intr_failed:
4740         arcmsr_free_resource(acb);
4741 initialize_failed:
4742         arcmsr_mutex_destroy(acb);
4743         return ENXIO;
4744 }
4745
4746 /*
4747 ************************************************************************
4748 ************************************************************************
4749 */
4750 static int arcmsr_probe(device_t dev)
4751 {
4752         u_int32_t id;
4753         u_int16_t sub_device_id;
4754         static char buf[256];
4755         char x_type[]={"unknown"};
4756         char *type;
4757         int raid6 = 1;
4758
4759         if (pci_get_vendor(dev) != PCI_VENDOR_ID_ARECA) {
4760                 return (ENXIO);
4761         }
4762         sub_device_id = pci_read_config(dev, PCIR_SUBDEV_0, 2);
4763         switch(id = pci_get_devid(dev)) {
4764         case PCIDevVenIDARC1110:
4765         case PCIDevVenIDARC1200:
4766         case PCIDevVenIDARC1201:
4767         case PCIDevVenIDARC1210:
4768                 raid6 = 0;
4769                 /*FALLTHRU*/
4770         case PCIDevVenIDARC1120:
4771         case PCIDevVenIDARC1130:
4772         case PCIDevVenIDARC1160:
4773         case PCIDevVenIDARC1170:
4774         case PCIDevVenIDARC1220:
4775         case PCIDevVenIDARC1230:
4776         case PCIDevVenIDARC1231:
4777         case PCIDevVenIDARC1260:
4778         case PCIDevVenIDARC1261:
4779         case PCIDevVenIDARC1270:
4780         case PCIDevVenIDARC1280:
4781                 type = "SATA 3G";
4782                 break;
4783         case PCIDevVenIDARC1212:
4784         case PCIDevVenIDARC1222:
4785         case PCIDevVenIDARC1380:
4786         case PCIDevVenIDARC1381:
4787         case PCIDevVenIDARC1680:
4788         case PCIDevVenIDARC1681:
4789                 type = "SAS 3G";
4790                 break;
4791         case PCIDevVenIDARC1880:
4792         case PCIDevVenIDARC1882:
4793         case PCIDevVenIDARC1213:
4794         case PCIDevVenIDARC1223:
4795                 if ((sub_device_id == ARECA_SUB_DEV_ID_1883) ||
4796                     (sub_device_id == ARECA_SUB_DEV_ID_1216) ||
4797                     (sub_device_id == ARECA_SUB_DEV_ID_1226))
4798                         type = "SAS 12G";
4799                 else
4800                         type = "SAS 6G";
4801                 break;
4802         case PCIDevVenIDARC1884:
4803                 type = "SAS 12G";
4804                 break;
4805         case PCIDevVenIDARC1214:
4806         case PCIDevVenIDARC1203:
4807                 type = "SATA 6G";
4808                 break;
4809         default:
4810                 type = x_type;
4811                 raid6 = 0;
4812                 break;
4813         }
4814         if(type == x_type)
4815                 return(ENXIO);
4816         sprintf(buf, "Areca %s Host Adapter RAID Controller %s\n%s\n",
4817                 type, raid6 ? "(RAID6 capable)" : "", ARCMSR_DRIVER_VERSION);
4818         device_set_desc_copy(dev, buf);
4819         return (BUS_PROBE_DEFAULT);
4820 }
4821 /*
4822 ************************************************************************
4823 ************************************************************************
4824 */
4825 static int arcmsr_shutdown(device_t dev)
4826 {
4827         u_int32_t  i;
4828         u_int32_t intmask_org;
4829         struct CommandControlBlock *srb;
4830         struct AdapterControlBlock *acb=(struct AdapterControlBlock *)device_get_softc(dev);
4831
4832         /* stop adapter background rebuild */
4833         ARCMSR_LOCK_ACQUIRE(&acb->isr_lock);
4834         /* disable all outbound interrupt */
4835         intmask_org = arcmsr_disable_allintr(acb);
4836         arcmsr_stop_adapter_bgrb(acb);
4837         arcmsr_flush_adapter_cache(acb);
4838         /* abort all outstanding command */
4839         acb->acb_flags |= ACB_F_SCSISTOPADAPTER;
4840         acb->acb_flags &= ~ACB_F_IOP_INITED;
4841         if(acb->srboutstandingcount != 0) {
4842                 /*clear and abort all outbound posted Q*/
4843                 arcmsr_done4abort_postqueue(acb);
4844                 /* talk to iop 331 outstanding command aborted*/
4845                 arcmsr_abort_allcmd(acb);
4846                 for(i=0; i < ARCMSR_MAX_FREESRB_NUM; i++) {
4847                         srb = acb->psrb_pool[i];
4848                         if(srb->srb_state == ARCMSR_SRB_START) {
4849                                 srb->srb_state = ARCMSR_SRB_ABORTED;
4850                                 srb->pccb->ccb_h.status |= CAM_REQ_ABORTED;
4851                                 arcmsr_srb_complete(srb, 1);
4852                         }
4853                 }
4854         }
4855         acb->srboutstandingcount = 0;
4856         acb->workingsrb_doneindex = 0;
4857         acb->workingsrb_startindex = 0;
4858         acb->pktRequestCount = 0;
4859         acb->pktReturnCount = 0;
4860         ARCMSR_LOCK_RELEASE(&acb->isr_lock);
4861         return (0);
4862 }
4863 /*
4864 ************************************************************************
4865 ************************************************************************
4866 */
4867 static void arcmsr_teardown_intr(device_t dev, struct AdapterControlBlock *acb)
4868 {
4869         int i;
4870
4871         if (acb->acb_flags & ACB_F_MSIX_ENABLED) {
4872                 for (i = 0; i < acb->msix_vectors; i++) {
4873                         if (acb->ih[i])
4874                                 bus_teardown_intr(dev, acb->irqres[i], acb->ih[i]);
4875                         if (acb->irqres[i] != NULL)
4876                                 bus_release_resource(dev, SYS_RES_IRQ,
4877                                     acb->irq_id[i], acb->irqres[i]);
4878
4879                         acb->ih[i] = NULL;
4880                 }
4881                 pci_release_msi(dev);
4882         } else {
4883                 if (acb->ih[0])
4884                         bus_teardown_intr(dev, acb->irqres[0], acb->ih[0]);
4885                 if (acb->irqres[0] != NULL)
4886                         bus_release_resource(dev, SYS_RES_IRQ,
4887                             acb->irq_id[0], acb->irqres[0]);
4888                 acb->ih[0] = NULL;
4889         }
4890
4891 }
4892 /*
4893 ************************************************************************
4894 ************************************************************************
4895 */
4896 static int arcmsr_detach(device_t dev)
4897 {
4898         struct AdapterControlBlock *acb=(struct AdapterControlBlock *)device_get_softc(dev);
4899         int i;
4900
4901         callout_stop(&acb->devmap_callout);
4902         arcmsr_teardown_intr(dev, acb);
4903         arcmsr_shutdown(dev);
4904         arcmsr_free_resource(acb);
4905         for(i=0; (acb->sys_res_arcmsr[i]!=NULL) && (i<2); i++) {
4906                 bus_release_resource(dev, SYS_RES_MEMORY, acb->rid[i], acb->sys_res_arcmsr[i]);
4907         }
4908         ARCMSR_LOCK_ACQUIRE(&acb->isr_lock);
4909         xpt_async(AC_LOST_DEVICE, acb->ppath, NULL);
4910         xpt_free_path(acb->ppath);
4911         xpt_bus_deregister(cam_sim_path(acb->psim));
4912         cam_sim_free(acb->psim, TRUE);
4913         ARCMSR_LOCK_RELEASE(&acb->isr_lock);
4914         arcmsr_mutex_destroy(acb);
4915         return (0);
4916 }
4917
4918 #ifdef ARCMSR_DEBUG1
4919 static void arcmsr_dump_data(struct AdapterControlBlock *acb)
4920 {
4921         if((acb->pktRequestCount - acb->pktReturnCount) == 0)
4922                 return;
4923         printf("Command Request Count   =0x%x\n",acb->pktRequestCount);
4924         printf("Command Return Count    =0x%x\n",acb->pktReturnCount);
4925         printf("Command (Req-Rtn) Count =0x%x\n",(acb->pktRequestCount - acb->pktReturnCount));
4926         printf("Queued Command Count    =0x%x\n",acb->srboutstandingcount);
4927 }
4928 #endif