⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 aic7xxx.c

📁 基于组件方式开发操作系统的OSKIT源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
#define CFRESETB        0x0040  /* reset SCSI bus at boot */#define CFBPRIMARY      0x0100  /* Channel B primary on 7895 chipsets */#define CFSEAUTOTERM    0x0400  /* aic7890 Perform SE Auto Term */#define CFLVDSTERM      0x0800  /* aic7890 LVD Termination *//* UNUSED                0xF280 */  unsigned short adapter_control;        /* word 17 *//* * Bus Release, Host Adapter ID */#define CFSCSIID        0x000F                /* host adapter SCSI ID *//* UNUSED                0x00F0 */#define CFBRTIME        0xFF00                /* bus release time */  unsigned short brtime_id;                /* word 18 *//* * Maximum targets */#define CFMAXTARG        0x00FF        /* maximum targets *//* UNUSED                0xFF00 */  unsigned short max_targets;                /* word 19 */  unsigned short res_1[11];                /* words 20-30 */  unsigned short checksum;                /* word 31 */};#define SELBUS_MASK                0x0a#define         SELNARROW        0x00#define         SELBUSB                0x08#define SINGLE_BUS                0x00#define SCB_TARGET(scb)         \       (((scb)->hscb->target_channel_lun & TID) >> 4)#define SCB_LUN(scb)            \       ((scb)->hscb->target_channel_lun & LID)#define SCB_IS_SCSIBUS_B(scb)   \       (((scb)->hscb->target_channel_lun & SELBUSB) != 0)/* * If an error occurs during a data transfer phase, run the command * to completion - it's easier that way - making a note of the error * condition in this location. This then will modify a DID_OK status * into an appropriate error for the higher-level SCSI code. */#define aic7xxx_error(cmd)        ((cmd)->SCp.Status)/* * Keep track of the targets returned status. */#define aic7xxx_status(cmd)        ((cmd)->SCp.sent_command)/* * The position of the SCSI commands scb within the scb array. */#define aic7xxx_position(cmd)        ((cmd)->SCp.have_data_in)/* * So we can keep track of our host structs */static struct aic7xxx_host *first_aic7xxx = NULL;/* * As of Linux 2.1, the mid-level SCSI code uses virtual addresses * in the scatter-gather lists.  We need to convert the virtual * addresses to physical addresses. */struct hw_scatterlist {  unsigned int address;  unsigned int length;};/* * Maximum number of SG segments these cards can support. */#define        AIC7XXX_MAX_SG 128/* * The maximum number of SCBs we could have for ANY type * of card. DON'T FORGET TO CHANGE THE SCB MASK IN THE * SEQUENCER CODE IF THIS IS MODIFIED! */#define AIC7XXX_MAXSCB        255struct aic7xxx_hwscb {/* ------------    Begin hardware supported fields    ---------------- *//* 0*/  unsigned char control;/* 1*/  unsigned char target_channel_lun;       /* 4/1/3 bits *//* 2*/  unsigned char target_status;/* 3*/  unsigned char SG_segment_count;/* 4*/  unsigned int  SG_list_pointer;/* 8*/  unsigned char residual_SG_segment_count;/* 9*/  unsigned char residual_data_count[3];/*12*/  unsigned int  data_pointer;/*16*/  unsigned int  data_count;/*20*/  unsigned int  SCSI_cmd_pointer;/*24*/  unsigned char SCSI_cmd_length;/*25*/  unsigned char tag;          /* Index into our kernel SCB array.                                     * Also used as the tag for tagged I/O                                     */#define SCB_PIO_TRANSFER_SIZE  26   /* amount we need to upload/download                                     * via PIO to initialize a transaction.                                     *//*26*/  unsigned char next;         /* Used to thread SCBs awaiting selection                                     * or disconnected down in the sequencer.                                     *//*27*/  unsigned char prev;/*28*/  unsigned int pad;           /*                                     * Unused by the kernel, but we require                                     * the padding so that the array of                                     * hardware SCBs is alligned on 32 byte                                     * boundaries so the sequencer can index                                     */};typedef enum {        SCB_FREE                = 0x0000,        SCB_WAITINGQ            = 0x0002,        SCB_ACTIVE              = 0x0004,        SCB_SENSE               = 0x0008,        SCB_ABORT               = 0x0010,        SCB_DEVICE_RESET        = 0x0020,        SCB_RESET               = 0x0040,        SCB_RECOVERY_SCB        = 0x0080,        SCB_MSGOUT_PPR          = 0x0100,        SCB_MSGOUT_SENT         = 0x0200,        SCB_MSGOUT_SDTR         = 0x0400,        SCB_MSGOUT_WDTR         = 0x0800,        SCB_MSGOUT_BITS         = SCB_MSGOUT_PPR |                                  SCB_MSGOUT_SENT |                                   SCB_MSGOUT_SDTR |                                  SCB_MSGOUT_WDTR,        SCB_QUEUED_ABORT        = 0x1000,        SCB_QUEUED_FOR_DONE     = 0x2000,        SCB_WAS_BUSY            = 0x4000} scb_flag_type;typedef enum {        AHC_FNONE                 = 0x00000000,        AHC_PAGESCBS              = 0x00000001,        AHC_CHANNEL_B_PRIMARY     = 0x00000002,        AHC_USEDEFAULTS           = 0x00000004,        AHC_INDIRECT_PAGING       = 0x00000008,        AHC_CHNLB                 = 0x00000020,        AHC_CHNLC                 = 0x00000040,        AHC_EXTEND_TRANS_A        = 0x00000100,        AHC_EXTEND_TRANS_B        = 0x00000200,        AHC_TERM_ENB_A            = 0x00000400,        AHC_TERM_ENB_SE_LOW       = 0x00000400,        AHC_TERM_ENB_B            = 0x00000800,        AHC_TERM_ENB_SE_HIGH      = 0x00000800,        AHC_HANDLING_REQINITS     = 0x00001000,        AHC_TARGETMODE            = 0x00002000,        AHC_NEWEEPROM_FMT         = 0x00004000, /*  *  Here ends the FreeBSD defined flags and here begins the linux defined  *  flags.  NOTE: I did not preserve the old flag name during this change  *  specifically to force me to evaluate what flags were being used properly  *  and what flags weren't.  This way, I could clean up the flag usage on  *  a use by use basis.  Doug Ledford  */        AHC_RESET_DELAY           = 0x00080000,        AHC_A_SCANNED             = 0x00100000,        AHC_B_SCANNED             = 0x00200000,        AHC_MULTI_CHANNEL         = 0x00400000,        AHC_BIOS_ENABLED          = 0x00800000,        AHC_SEEPROM_FOUND         = 0x01000000,        AHC_TERM_ENB_LVD          = 0x02000000,        AHC_ABORT_PENDING         = 0x04000000,        AHC_RESET_PENDING         = 0x08000000,#define AHC_IN_ISR_BIT              28        AHC_IN_ISR                = 0x10000000,        AHC_IN_ABORT              = 0x20000000,        AHC_IN_RESET              = 0x40000000,        AHC_EXTERNAL_SRAM         = 0x80000000} ahc_flag_type;typedef enum {  AHC_NONE             = 0x0000,  AHC_CHIPID_MASK      = 0x00ff,  AHC_AIC7770          = 0x0001,  AHC_AIC7850          = 0x0002,  AHC_AIC7860          = 0x0003,  AHC_AIC7870          = 0x0004,  AHC_AIC7880          = 0x0005,  AHC_AIC7890          = 0x0006,  AHC_AIC7895          = 0x0007,  AHC_AIC7896          = 0x0008,  AHC_AIC7892          = 0x0009,  AHC_AIC7899          = 0x000a,  AHC_VL               = 0x0100,  AHC_EISA             = 0x0200,  AHC_PCI              = 0x0400,} ahc_chip;typedef enum {  AHC_FENONE           = 0x0000,  AHC_ULTRA            = 0x0001,  AHC_ULTRA2           = 0x0002,  AHC_WIDE             = 0x0004,  AHC_TWIN             = 0x0008,  AHC_MORE_SRAM        = 0x0010,  AHC_CMD_CHAN         = 0x0020,  AHC_QUEUE_REGS       = 0x0040,  AHC_SG_PRELOAD       = 0x0080,  AHC_SPIOCAP          = 0x0100,  AHC_ULTRA3           = 0x0200,  AHC_AIC7770_FE       = AHC_FENONE,  AHC_AIC7850_FE       = AHC_SPIOCAP,  AHC_AIC7860_FE       = AHC_ULTRA|AHC_SPIOCAP,  AHC_AIC7870_FE       = AHC_FENONE,  AHC_AIC7880_FE       = AHC_ULTRA,  AHC_AIC7890_FE       = AHC_MORE_SRAM|AHC_CMD_CHAN|AHC_ULTRA2|                         AHC_QUEUE_REGS|AHC_SG_PRELOAD,  AHC_AIC7895_FE       = AHC_MORE_SRAM|AHC_CMD_CHAN|AHC_ULTRA,  AHC_AIC7896_FE       = AHC_AIC7890_FE,  AHC_AIC7892_FE       = AHC_AIC7890_FE|AHC_ULTRA3,  AHC_AIC7899_FE       = AHC_AIC7890_FE|AHC_ULTRA3,} ahc_feature;struct aic7xxx_scb {        struct aic7xxx_hwscb  *hscb;          /* corresponding hardware scb */        Scsi_Cmnd             *cmd;              /* Scsi_Cmnd for this scb */        struct aic7xxx_scb    *q_next;        /* next scb in queue */        volatile scb_flag_type flags;         /* current state of scb */        struct hw_scatterlist *sg_list;       /* SG list in adapter format */        unsigned char          tag_action;        unsigned char          sg_count;        unsigned char          sense_cmd[6];  /*                                               * Allocate 6 characters for                                               * sense command.                                               */        unsigned int           sg_length; /* We init this during buildscb so we                                           * don't have to calculate anything                                           * during underflow/overflow/stat code                                           */        void                  *kmalloc_ptr;};/* * Define a linked list of SCBs. */typedef struct {  struct aic7xxx_scb *head;  struct aic7xxx_scb *tail;} scb_queue_type;static struct {  unsigned char errno;  const char *errmesg;} hard_error[] = {  { ILLHADDR,  "Illegal Host Access" },  { ILLSADDR,  "Illegal Sequencer Address referenced" },  { ILLOPCODE, "Illegal Opcode in sequencer program" },  { SQPARERR,  "Sequencer Ram Parity Error" },  { DPARERR,   "Data-Path Ram Parity Error" },  { MPARERR,   "Scratch Ram/SCB Array Ram Parity Error" },  { PCIERRSTAT,"PCI Error detected" },  { CIOPARERR, "CIOBUS Parity Error" }};static unsigned chargeneric_sense[] = { REQUEST_SENSE, 0, 0, 0, 255, 0 };typedef struct {  scb_queue_type free_scbs;        /*                                    * SCBs assigned to free slot on                                    * card (no paging required)                                    */  struct aic7xxx_scb   *scb_array[AIC7XXX_MAXSCB];  struct aic7xxx_hwscb *hscbs;  unsigned char  numscbs;          /* current number of scbs */  unsigned char  maxhscbs;         /* hardware scbs */  unsigned char  maxscbs;          /* max scbs including pageable scbs */  void          *hscb_kmalloc_ptr;} scb_data_type;struct target_cmd {  unsigned char mesg_bytes[4];  unsigned char command[28];};#define AHC_TRANS_CUR    0x0001#define AHC_TRANS_ACTIVE 0x0002#define AHC_TRANS_GOAL   0x0004#define AHC_TRANS_USER   0x0008#define AHC_TRANS_QUITE  0x0010typedef struct {  unsigned char cur_width;  unsigned char goal_width;  unsigned char cur_period;  unsigned char goal_period;  unsigned char cur_offset;  unsigned char goal_offset;  unsigned char cur_options;  unsigned char goal_options;  unsigned char user_width;  unsigned char user_period;  unsigned char user_offset;  unsigned char user_options;} transinfo_type;/* * Define a structure used for each host adapter.  Note, in order to avoid * problems with architectures I can't test on (because I don't have one, * such as the Alpha based systems) which happen to give faults for * non-aligned memory accesses, care was taken to align this structure * in a way that gauranteed all accesses larger than 8 bits were aligned * on the appropriate boundary.  It's also organized to try and be more * cache line efficient.  Be careful when changing this lest you might hurt * overall performance and bring down the wrath of the masses. */struct aic7xxx_host {  /*   *  This is the first 64 bytes in the host struct   */  /*   * We are grouping things here....first, items that get either read or   * written with nearly every interrupt   */  volatile ahc_flag_type   flags;  ahc_feature              features;         /* chip features */  unsigned long            base;             /* card base address */  volatile unsigned char  *maddr;            /* memory mapped address */  unsigned long            isr_count;        /* Interrupt count */  unsigned long            spurious_int;  scb_data_type           *scb_data;  volatile unsigned short  needdv;  volatile unsigned short  needppr;  volatile unsigned short  needsdtr;  volatile unsigned short  needwdtr;  volatile unsigned short  dtr_pending;  struct aic7xxx_cmd_queue {    Scsi_Cmnd *head;    Scsi_Cmnd *tail;  } completeq;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -