[BACK]Return to aacvar.h CVS log [TXT][DIR] Up to [local] / sys / dev / ic

Annotation of sys/dev/ic/aacvar.h, Revision 1.1.1.1

1.1       nbrk        1: /*     $OpenBSD: aacvar.h,v 1.7 2006/05/07 20:12:41 tedu Exp $ */
                      2:
                      3: /*-
                      4:  * Copyright (c) 2000 Michael Smith
                      5:  * Copyright (c) 2000 BSDi
                      6:  * Copyright (c) 2000 Niklas Hallqvist
                      7:  * All rights reserved.
                      8:  *
                      9:  * Redistribution and use in source and binary forms, with or without
                     10:  * modification, are permitted provided that the following conditions
                     11:  * are met:
                     12:  * 1. Redistributions of source code must retain the above copyright
                     13:  *    notice, this list of conditions and the following disclaimer.
                     14:  * 2. Redistributions in binary form must reproduce the above copyright
                     15:  *    notice, this list of conditions and the following disclaimer in the
                     16:  *    documentation and/or other materials provided with the distribution.
                     17:  *
                     18:  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
                     19:  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
                     20:  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
                     21:  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
                     22:  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
                     23:  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
                     24:  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
                     25:  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
                     26:  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
                     27:  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
                     28:  * SUCH DAMAGE.
                     29:  *
                     30:  *     $FreeBSD: /c/ncvs/src/sys/dev/aac/aacvar.h,v 1.1 2000/09/13 03:20:34 msmith Exp $
                     31:  */
                     32:
                     33: /*
                     34:  * This driver would not have rewritten for OpenBSD if it was not for the
                     35:  * hardware donation from Nocom.  I want to thank them for their support.
                     36:  * Of course, credit should go to Mike Smith for the original work he did
                     37:  * in the FreeBSD driver where I found lots of inspiration.
                     38:  * - Niklas Hallqvist
                     39:  */
                     40:
                     41: /* compatability */
                     42: #define time_second (mono_time.tv_sec)
                     43:
                     44: /* Debugging */
                     45: // #define AAC_DEBUG 0x0
                     46:
                     47: #ifdef AAC_DEBUG
                     48: #define AAC_DPRINTF(mask, args) if (aac_debug & (mask)) printf args
                     49: #define AAC_D_INTR     0x001
                     50: #define AAC_D_MISC     0x002
                     51: #define AAC_D_CMD      0x004
                     52: #define AAC_D_QUEUE    0x008
                     53: #define AAC_D_IO       0x010
                     54: #define AAC_D_IOCTL    0x020
                     55: #define AAC_D_LOCK     0x040
                     56: #define AAC_D_THREAD   0x080
                     57: #define AAC_D_FIB      0x100
                     58: extern int aac_debug;
                     59:
                     60: #define AAC_PRINT_FIB(sc, fib)  do { \
                     61:        if (aac_debug & AAC_D_FIB) \
                     62:                aac_print_fib((sc), (fib), __func__); \
                     63: } while (0)
                     64: #else
                     65: #define AAC_DPRINTF(mask, args)
                     66: #define AAC_PRINT_FIB(sc, fib)
                     67: #endif
                     68:
                     69: struct aac_code_lookup {
                     70:        char    *string;
                     71:        u_int32_t code;
                     72: };
                     73:
                     74: struct aac_softc;
                     75:
                     76: /*
                     77:  * We allocate a small set of FIBs for the adapter to use to send us messages.
                     78:  */
                     79: #define AAC_ADAPTER_FIBS       8
                     80:
                     81: /*
                     82:  * FIBs are allocated in page-size chunks and can grow up to the 512
                     83:  * limit imposed by the hardware.
                     84:  */
                     85: #define AAC_FIB_COUNT          (PAGE_SIZE/sizeof(struct aac_fib))
                     86: #define AAC_MAX_FIBS           512
                     87: #define AAC_FIBMAP_SIZE                (PAGE_SIZE)
                     88:
                     89: /*
                     90:  * The controller reports status events in AIFs.  We hang on to a number of
                     91:  * these in order to pass them out to user-space management tools.
                     92:  */
                     93: #define AAC_AIFQ_LENGTH                64
                     94:
                     95: /*
                     96:  * Firmware messages are passed in the printf buffer.
                     97:  */
                     98: #define AAC_PRINTF_BUFSIZE     256
                     99:
                    100: /*
                    101:  * We wait this many seconds for the adapter to come ready if it is still
                    102:  * booting.
                    103:  */
                    104: #define AAC_BOOT_TIMEOUT       (3 * 60)
                    105:
                    106: /*
                    107:  * Timeout for immediate commands.
                    108:  */
                    109: #define AAC_IMMEDIATE_TIMEOUT  30
                    110:
                    111: /*
                    112:  * Timeout for normal commands
                    113:  */
                    114: #define AAC_CMD_TIMEOUT                30              /* seconds */
                    115:
                    116: /*
                    117:  * Rate at which we periodically check for timed out commands and kick the
                    118:  * controller.
                    119:  */
                    120: #define AAC_PERIODIC_INTERVAL  20              /* seconds */
                    121:
                    122: /*
                    123:  * Wait this long for a lost interrupt to get detected.
                    124:  */
                    125: #define AAC_WATCH_TIMEOUT      10000           /* 10000 * 1ms = 10s */
                    126:
                    127: /*
                    128:  * Delay 20ms after the qnotify in sync operations.  Experimentally deduced.
                    129:  */
                    130: #define AAC_SYNC_DELAY 20000
                    131:
                    132: /*
                    133:  * The firmware interface allows for a 16-bit s/g list length.  We limit
                    134:  * ourselves to a reasonable maximum and ensure alignment.
                    135:  */
                    136: #define AAC_MAXSGENTRIES       64      /* max S/G entries, limit 65535 */
                    137:
                    138: /*
                    139:  * We gather a number of adapter-visible items into a single structure.
                    140:  *
                    141:  * The ordering of this structure may be important; we copy the Linux driver:
                    142:  *
                    143:  * Adapter FIBs
                    144:  * Init struct
                    145:  * Queue headers (Comm Area)
                    146:  * Printf buffer
                    147:  *
                    148:  * In addition, we add:
                    149:  * Sync Fib
                    150:  */
                    151: struct aac_common {
                    152:        /* fibs for the controller to send us messages */
                    153:        struct aac_fib ac_fibs[AAC_ADAPTER_FIBS];
                    154:
                    155:        /* the init structure */
                    156:        struct aac_adapter_init ac_init;
                    157:
                    158:        /* arena within which the queue structures are kept */
                    159:        u_int8_t ac_qbuf[sizeof(struct aac_queue_table) + AAC_QUEUE_ALIGN];
                    160:
                    161:        /* buffer for text messages from the controller */
                    162:        char    ac_printf[AAC_PRINTF_BUFSIZE];
                    163:
                    164:        /* fib for synchronous commands */
                    165:        struct aac_fib ac_sync_fib;
                    166: };
                    167: #define AAC_COMMON_ALLOCSIZE (8192 + sizeof(struct aac_common))
                    168:
                    169: /*
                    170:  * Interface operations
                    171:  */
                    172: struct aac_interface {
                    173:        int     (*aif_get_fwstatus)(struct aac_softc *);
                    174:        void    (*aif_qnotify)(struct aac_softc *, int);
                    175:        int     (*aif_get_istatus)(struct aac_softc *);
                    176:        void    (*aif_set_istatus)(struct aac_softc *, int);
                    177:        void    (*aif_set_mailbox)(struct aac_softc *, u_int32_t,
                    178:            u_int32_t, u_int32_t, u_int32_t, u_int32_t);
                    179:        int     (*aif_get_mailbox)(struct aac_softc *, int mb);
                    180:        void    (*aif_set_interrupts)(struct aac_softc *, int);
                    181: };
                    182: extern struct aac_interface aac_fa_interface;
                    183: extern struct aac_interface aac_sa_interface;
                    184: extern struct aac_interface aac_rx_interface;
                    185: extern struct aac_interface aac_rkt_interface;
                    186:
                    187: #define AAC_GET_FWSTATUS(sc)           ((sc)->aac_if.aif_get_fwstatus(sc))
                    188: #define AAC_QNOTIFY(sc, qbit) \
                    189:        ((sc)->aac_if.aif_qnotify((sc), (qbit)))
                    190: #define AAC_GET_ISTATUS(sc)            ((sc)->aac_if.aif_get_istatus(sc))
                    191: #define AAC_CLEAR_ISTATUS(sc, mask) \
                    192:        ((sc)->aac_if.aif_set_istatus((sc), (mask)))
                    193: #define AAC_SET_MAILBOX(sc, command, arg0, arg1, arg2, arg3) \
                    194:        do {                                                            \
                    195:                ((sc)->aac_if.aif_set_mailbox((sc), (command), (arg0),  \
                    196:                    (arg1), (arg2), (arg3)));                           \
                    197:        } while(0)
                    198: #define AAC_GET_MAILBOX(sc, mb) \
                    199:        ((sc)->aac_if.aif_get_mailbox(sc, (mb)))
                    200: #define        AAC_MASK_INTERRUPTS(sc) \
                    201:        ((sc)->aac_if.aif_set_interrupts((sc), 0))
                    202: #define AAC_UNMASK_INTERRUPTS(sc) \
                    203:        ((sc)->aac_if.aif_set_interrupts((sc), 1))
                    204:
                    205: #define AAC_SETREG4(sc, reg, val) \
                    206:        bus_space_write_4((sc)->aac_memt, (sc)->aac_memh, (reg), (val))
                    207: #define AAC_GETREG4(sc, reg) \
                    208:        bus_space_read_4((sc)->aac_memt, (sc)->aac_memh, (reg))
                    209: #define AAC_SETREG2(sc, reg, val) \
                    210:        bus_space_write_2((sc)->aac_memt, (sc)->aac_memh, (reg), (val))
                    211: #define AAC_GETREG2(sc, reg) \
                    212:        bus_space_read_2((sc)->aac_memt, (sc)->aac_memh, (reg))
                    213: #define AAC_SETREG1(sc, reg, val) \
                    214:        bus_space_write_1((sc)->aac_memt, (sc)->aac_memh, (reg), (val))
                    215: #define AAC_GETREG1(sc, reg) \
                    216:        bus_space_read_1((sc)->aac_memt, (sc)->aac_memh, (reg))
                    217:
                    218: /* Define the OS version specific locks */
                    219: typedef struct rwlock aac_lock_t;
                    220: #define AAC_LOCK_INIT(l, s)    do { \
                    221:     rw_init((l), "aaclock"); \
                    222:     AAC_DPRINTF(AAC_D_LOCK, ("%s: init lock @%s: %d\n", \
                    223:                sc->aac_dev.dv_xname, __FUNCTION__, __LINE__)); \
                    224: } while (0)
                    225:
                    226: #define AAC_LOCK_ACQUIRE(l) do { \
                    227:     AAC_DPRINTF(AAC_D_LOCK, ("%s: lock @%s: %d\n", \
                    228:                sc->aac_dev.dv_xname, __FUNCTION__, __LINE__)); \
                    229:     rw_enter_write((l)); \
                    230: } while (0)
                    231:
                    232: #define AAC_LOCK_RELEASE(l) do { \
                    233:     rw_exit_write((l)); \
                    234:     AAC_DPRINTF(AAC_D_LOCK, ("%s: unlock @%s: %d\n", \
                    235:                sc->aac_dev.dv_xname, __FUNCTION__, __LINE__)); \
                    236: } while (0)
                    237:
                    238: /*
                    239:  * Per-container data structure
                    240:  */
                    241: struct aac_container
                    242: {
                    243:        struct aac_mntobj co_mntobj;
                    244:        int                             co_found;
                    245:        TAILQ_ENTRY(aac_container)      co_link;
                    246: };
                    247:
                    248: /*
                    249:  * A command contol block, one for each corresponding command index of the
                    250:  * controller.
                    251:  */
                    252: struct aac_command
                    253: {
                    254:        TAILQ_ENTRY(aac_command) cm_link;       /* list linkage */
                    255:
                    256:        struct aac_softc        *cm_sc;         /* controller that owns us */
                    257:
                    258:        struct aac_fib          *cm_fib;        /* FIB for this command */
                    259:        bus_addr_t              cm_fibphys;     /* bus address of the FIB */
                    260:        void                    *cm_data;
                    261:        size_t                  cm_datalen;
                    262:        bus_dmamap_t            cm_datamap;
                    263:        struct aac_sg_table     *cm_sgtable;    /* pointer to s/g table */
                    264:
                    265:        u_int                   cm_flags;
                    266: #define AAC_CMD_MAPPED         (1<<0)  /* command has had its data mapped */
                    267: #define AAC_CMD_DATAIN         (1<<1)  /* command involves data moving
                    268:                                         * from controller to host */
                    269: #define AAC_CMD_DATAOUT                (1<<2)  /* command involves data moving
                    270:                                         * from host to controller */
                    271: #define AAC_CMD_COMPLETED      (1<<3)  /* command has been completed */
                    272: #define AAC_CMD_TIMEDOUT       (1<<4)  /* command taken too long */
                    273: #define AAC_ON_AACQ_FREE       (1<<5)
                    274: #define AAC_ON_AACQ_READY      (1<<6)
                    275: #define AAC_ON_AACQ_BUSY       (1<<7)
                    276: #define AAC_ON_AACQ_BIO                (1<<8)
                    277: #define AAC_ON_AACQ_MASK       ((1<<5)|(1<<6)|(1<<7)|(1<<8))
                    278: #define AAC_QUEUE_FRZN         (1<<9)  /* Freeze the processing of
                    279:                                         * commands on the queue. */
                    280: #define AAC_ACF_WATCHDOG       (1<<10)
                    281:
                    282:        void                    (*cm_complete)(struct aac_command *);
                    283:        void                    *cm_private;
                    284:        u_int32_t               cm_blkno;
                    285:        u_int32_t               cm_bcount;
                    286:        time_t                  cm_timestamp;   /* command creation time */
                    287:        int                     cm_queue;
                    288:        int                     cm_index;
                    289: };
                    290:
                    291: struct aac_fibmap {
                    292:        TAILQ_ENTRY(aac_fibmap) fm_link;        /* list linkage */
                    293:        struct aac_fib          *aac_fibs;
                    294:        bus_dmamap_t            aac_fibmap;
                    295:        bus_dma_segment_t       aac_seg;
                    296:        int                     aac_nsegs;
                    297:        struct aac_command      *aac_commands;
                    298: };
                    299:
                    300: /*
                    301:  * Command queue statistics
                    302:  */
                    303: #define AACQ_FREE       0
                    304: #define AACQ_BIO        1
                    305: #define AACQ_READY      2
                    306: #define AACQ_BUSY       3
                    307: #define AACQ_COUNT      4       /* total number of queues */
                    308:
                    309: struct aac_qstat {
                    310:         u_int32_t       q_length;
                    311:         u_int32_t       q_max;
                    312: };
                    313:
                    314: /*
                    315:  * Per-controller structure.
                    316:  */
                    317: struct aac_softc
                    318: {
                    319:        struct device aac_dev;
                    320:        void   *aac_ih;
                    321:        struct  scsi_link aac_link;     /* Virtual SCSI bus for cache devs */
                    322:
                    323:        bus_space_tag_t aac_memt;
                    324:        bus_space_handle_t aac_memh;
                    325:        bus_dma_tag_t aac_dmat;         /* parent DMA tag */
                    326:
                    327:        /* controller features, limits and status */
                    328:        int     aac_state;
                    329: #define AAC_STATE_SUSPEND      (1<<0)
                    330: #define        AAC_STATE_OPEN          (1<<1)
                    331: #define AAC_STATE_INTERRUPTS_ON        (1<<2)
                    332: #define AAC_STATE_AIF_SLEEPER  (1<<3)
                    333:        struct FsaRevision aac_revision;
                    334:
                    335:        int     aac_hwif;       /* controller hardware interface */
                    336: #define AAC_HWIF_I960RX                0
                    337: #define AAC_HWIF_STRONGARM     1
                    338: #define AAC_HWIF_FALCON                2
                    339: #define AAC_HWIF_RKT           3
                    340: #define AAC_HWIF_UNKNOWN       -1
                    341:
                    342:        struct aac_common *aac_common;
                    343:        bus_dmamap_t            aac_common_map;
                    344:        u_int32_t aac_common_busaddr;
                    345:        struct aac_interface aac_if;
                    346:
                    347:        /* command/fib resources */
                    348:        TAILQ_HEAD(,aac_fibmap) aac_fibmap_tqh;
                    349:        u_int                   total_fibs;
                    350:        struct aac_command      *aac_commands;
                    351:
                    352:        /* command management */
                    353:        TAILQ_HEAD(,aac_command) aac_free;      /* command structures
                    354:                                                 * available for reuse */
                    355:        TAILQ_HEAD(,aac_command) aac_ready;     /* commands on hold for
                    356:                                                 * controller resources */
                    357:        TAILQ_HEAD(,aac_command) aac_busy;
                    358:        TAILQ_HEAD(,aac_command) aac_bio;
                    359:
                    360:        /* command management */
                    361:        struct aac_queue_table *aac_queues;
                    362:        struct aac_queue_entry *aac_qentries[AAC_QUEUE_COUNT];
                    363:
                    364:        struct aac_qstat        aac_qstat[AACQ_COUNT];  /* queue statistics */
                    365:
                    366:        /* connected containters */
                    367:        TAILQ_HEAD(,aac_container)      aac_container_tqh;
                    368:        aac_lock_t              aac_container_lock;
                    369:
                    370:        /* Protect the sync fib */
                    371: #define AAC_SYNC_LOCK_FORCE    (1 << 0)
                    372:        aac_lock_t              aac_sync_lock;
                    373:
                    374:        aac_lock_t              aac_io_lock;
                    375:
                    376:        struct {
                    377:                u_int8_t hd_present;
                    378:                u_int8_t hd_is_logdrv;
                    379:                u_int8_t hd_is_arraydrv;
                    380:                u_int8_t hd_is_master;
                    381:                u_int8_t hd_is_parity;
                    382:                u_int8_t hd_is_hotfix;
                    383:                u_int8_t hd_master_no;
                    384:                u_int8_t hd_lock;
                    385:                u_int8_t hd_heads;
                    386:                u_int8_t hd_secs;
                    387:                u_int16_t hd_devtype;
                    388:                u_int32_t hd_size;
                    389:                u_int8_t hd_ldr_no;
                    390:                u_int8_t hd_rw_attribs;
                    391:                u_int32_t hd_start_sec;
                    392:        } aac_hdr[AAC_MAX_CONTAINERS];
                    393:        int                     aac_container_count;
                    394:
                    395:        /* management interface */
                    396:        aac_lock_t              aac_aifq_lock;
                    397:        struct aac_aif_command  aac_aifq[AAC_AIFQ_LENGTH];
                    398:        int                     aac_aifq_head;
                    399:        int                     aac_aifq_tail;
                    400:        struct selinfo          aac_select;
                    401:        struct proc             *aifthread;
                    402:        int                     aifflags;
                    403: #define AAC_AIFFLAGS_RUNNING   (1 << 0)
                    404: #define AAC_AIFFLAGS_AIF       (1 << 1)
                    405: #define        AAC_AIFFLAGS_EXIT       (1 << 2)
                    406: #define AAC_AIFFLAGS_EXITED    (1 << 3)
                    407: #define        AAC_AIFFLAGS_COMPLETE   (1 << 4)
                    408: #define AAC_AIFFLAGS_PRINTF    (1 << 5)
                    409: #define AAC_AIFFLAGS_PENDING   (AAC_AIFFLAGS_AIF | AAC_AIFFLAGS_COMPLETE | \
                    410:                                 AAC_AIFFLAGS_PRINTF)
                    411:
                    412:        u_int32_t               flags;
                    413: #define AAC_FLAGS_PERC2QC      (1 << 0)
                    414: #define        AAC_FLAGS_ENABLE_CAM    (1 << 1)        /* No SCSI passthrough */
                    415: #define        AAC_FLAGS_CAM_NORESET   (1 << 2)        /* Fake SCSI resets */
                    416: #define        AAC_FLAGS_CAM_PASSONLY  (1 << 3)        /* Only create pass devices */
                    417: #define        AAC_FLAGS_SG_64BIT      (1 << 4)        /* Use 64-bit S/G addresses */
                    418: #define        AAC_FLAGS_4GB_WINDOW    (1 << 5)        /* Device can access host mem
                    419:                                                 * 2GB-4GB range */
                    420: #define        AAC_FLAGS_NO4GB         (1 << 6)        /* Can't access host mem >2GB*/
                    421: #define        AAC_FLAGS_256FIBS       (1 << 7)        /* Can only do 256 commands */
                    422: #define        AAC_FLAGS_BROKEN_MEMMAP (1 << 8)        /* Broken HostPhysMemPages */
                    423:
                    424:        u_int32_t               supported_options;
                    425:        int                     aac_max_fibs;
                    426:        void                    *aac_sdh;
                    427: };
                    428:
                    429: /*
                    430:  * Public functions
                    431:  */
                    432: extern int     aac_wait_command(struct aac_command *, int);
                    433: extern int     aac_alloc_command(struct aac_softc *, struct aac_command **);
                    434: extern void    aac_release_command(struct aac_command *);
                    435: extern int     aac_alloc_sync_fib(struct aac_softc *, struct aac_fib **, int);
                    436: extern void    aac_release_sync_fib(struct aac_softc *);
                    437: extern int     aac_sync_fib(struct aac_softc *, u_int32_t, u_int32_t,
                    438:                             struct aac_fib *, u_int16_t);
                    439:
                    440: void   aacminphys(struct buf *);
                    441: int    aac_attach(struct aac_softc *);
                    442: int    aac_intr(void *);
                    443:
                    444: /* These all require correctly aligned buffers */
                    445: static __inline__ void aac_enc16(u_int8_t *, u_int16_t);
                    446: static __inline__ void aac_enc32(u_int8_t *, u_int32_t);
                    447: static __inline__ u_int16_t aac_dec16(u_int8_t *);
                    448: static __inline__ u_int32_t aac_dec32(u_int8_t *);
                    449:
                    450: static __inline__ void
                    451: aac_enc16(addr, value)
                    452:        u_int8_t *addr;
                    453:        u_int16_t value;
                    454: {
                    455:        *(u_int16_t *)addr = htole16(value);
                    456: }
                    457:
                    458: static __inline__ void
                    459: aac_enc32(addr, value)
                    460:        u_int8_t *addr;
                    461:        u_int32_t value;
                    462: {
                    463:        *(u_int32_t *)addr = htole32(value);
                    464: }
                    465:
                    466: static __inline__ u_int16_t
                    467: aac_dec16(addr)
                    468:        u_int8_t *addr;
                    469: {
                    470:        return letoh16(*(u_int16_t *)addr);
                    471: }
                    472:
                    473: static __inline__ u_int32_t
                    474: aac_dec32(addr)
                    475:        u_int8_t *addr;
                    476: {
                    477:        return letoh32(*(u_int32_t *)addr);
                    478: }
                    479:
                    480: /* Declarations copied from aac.c */
                    481: #ifdef AAC_DEBUG
                    482: void aac_print_fib(struct aac_softc *, struct aac_fib *, const char *);
                    483: void aac_print_aif(struct aac_softc *, struct aac_aif_command *);
                    484: #endif
                    485: void aac_handle_aif(struct aac_softc *, struct aac_fib *);
                    486:
                    487:
                    488:
                    489:
                    490:
                    491: /*
                    492:  * Queue primitives for driver queues.
                    493:  */
                    494: #define AACQ_ADD(sc, qname)                                    \
                    495:        do {                                                    \
                    496:                struct aac_qstat *qs;                           \
                    497:                                                                \
                    498:                qs = &(sc)->aac_qstat[qname];                   \
                    499:                                                                \
                    500:                qs->q_length++;                                 \
                    501:                if (qs->q_length > qs->q_max)                   \
                    502:                        qs->q_max = qs->q_length;               \
                    503:        } while (0)
                    504:
                    505: #define AACQ_REMOVE(sc, qname)    (sc)->aac_qstat[qname].q_length--
                    506: #define AACQ_INIT(sc, qname)                           \
                    507:        do {                                            \
                    508:                sc->aac_qstat[qname].q_length = 0;      \
                    509:                sc->aac_qstat[qname].q_max = 0;         \
                    510:        } while (0)
                    511:
                    512:
                    513: #define AACQ_COMMAND_QUEUE(name, index)                                        \
                    514: static __inline void                                                   \
                    515: aac_initq_ ## name (struct aac_softc *sc)                              \
                    516: {                                                                      \
                    517:        TAILQ_INIT(&sc->aac_ ## name);                                  \
                    518:        AACQ_INIT(sc, index);                                           \
                    519: }                                                                      \
                    520: static __inline void                                                   \
                    521: aac_enqueue_ ## name (struct aac_command *cm)                          \
                    522: {                                                                      \
                    523:        AAC_DPRINTF(AAC_D_CMD, (": enqueue " #name));                   \
                    524:        if ((cm->cm_flags & AAC_ON_AACQ_MASK) != 0) {                   \
                    525:                printf("command %p is on another queue, flags = %#x\n", \
                    526:                       cm, cm->cm_flags);                               \
                    527:                panic("command is on another queue");                   \
                    528:        }                                                               \
                    529:        TAILQ_INSERT_TAIL(&cm->cm_sc->aac_ ## name, cm, cm_link);       \
                    530:        cm->cm_flags |= AAC_ON_ ## index;                               \
                    531:        AACQ_ADD(cm->cm_sc, index);                                     \
                    532: }                                                                      \
                    533: static __inline void                                                   \
                    534: aac_requeue_ ## name (struct aac_command *cm)                          \
                    535: {                                                                      \
                    536:        AAC_DPRINTF(AAC_D_CMD, (": requeue " #name));                   \
                    537:        if ((cm->cm_flags & AAC_ON_AACQ_MASK) != 0) {                   \
                    538:                printf("command %p is on another queue, flags = %#x\n", \
                    539:                       cm, cm->cm_flags);                               \
                    540:                panic("command is on another queue");                   \
                    541:        }                                                               \
                    542:        TAILQ_INSERT_HEAD(&cm->cm_sc->aac_ ## name, cm, cm_link);       \
                    543:        cm->cm_flags |= AAC_ON_ ## index;                               \
                    544:        AACQ_ADD(cm->cm_sc, index);                                     \
                    545: }                                                                      \
                    546: static __inline struct aac_command *                                   \
                    547: aac_dequeue_ ## name (struct aac_softc *sc)                            \
                    548: {                                                                      \
                    549:        struct aac_command *cm;                                         \
                    550:                                                                        \
                    551:        if ((cm = TAILQ_FIRST(&sc->aac_ ## name)) != NULL) {            \
                    552:                AAC_DPRINTF(AAC_D_CMD, (": dequeue " #name));           \
                    553:                if ((cm->cm_flags & AAC_ON_ ## index) == 0) {           \
                    554:                        printf("dequeue - command %p not in queue, flags = %#x, "       \
                    555:                               "bit = %#x\n", cm, cm->cm_flags,         \
                    556:                               AAC_ON_ ## index);                       \
                    557:                        panic("command not in queue");                  \
                    558:                }                                                       \
                    559:                TAILQ_REMOVE(&sc->aac_ ## name, cm, cm_link);           \
                    560:                cm->cm_flags &= ~AAC_ON_ ## index;                      \
                    561:                AACQ_REMOVE(sc, index);                                 \
                    562:        }                                                               \
                    563:        return(cm);                                                     \
                    564: }                                                                      \
                    565: static __inline void                                                   \
                    566: aac_remove_ ## name (struct aac_command *cm)                           \
                    567: {                                                                      \
                    568:        AAC_DPRINTF(AAC_D_CMD, (": remove " #name));                    \
                    569:        if ((cm->cm_flags & AAC_ON_ ## index) == 0) {                   \
                    570:                printf("remove - command %p not in queue, flags = %#x, "                \
                    571:                       "bit = %#x\n", cm, cm->cm_flags,                 \
                    572:                       AAC_ON_ ## index);                               \
                    573:                panic("command not in queue");                          \
                    574:        }                                                               \
                    575:        TAILQ_REMOVE(&cm->cm_sc->aac_ ## name, cm, cm_link);            \
                    576:        cm->cm_flags &= ~AAC_ON_ ## index;                              \
                    577:        AACQ_REMOVE(cm->cm_sc, index);                                  \
                    578: }                                                                      \
                    579: struct hack
                    580:
                    581: AACQ_COMMAND_QUEUE(free, AACQ_FREE);
                    582: AACQ_COMMAND_QUEUE(ready, AACQ_READY);
                    583: AACQ_COMMAND_QUEUE(busy, AACQ_BUSY);
                    584: AACQ_COMMAND_QUEUE(bio, AACQ_BIO);
                    585:
                    586: static __inline void
                    587: aac_print_printf(struct aac_softc *sc)
                    588: {
                    589:        /*
                    590:         * XXX We have the ability to read the length of the printf string
                    591:         * from out of the mailboxes.
                    592:         */
                    593:        printf("** %s: %.*s", sc->aac_dev.dv_xname, AAC_PRINTF_BUFSIZE,
                    594:               sc->aac_common->ac_printf);
                    595:        sc->aac_common->ac_printf[0] = 0;
                    596:        AAC_QNOTIFY(sc, AAC_DB_PRINTF);
                    597: }

CVSweb