1/* 2 * Copyright (c) 2004-2005 HighPoint Technologies, Inc. 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 14 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 15 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 17 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 18 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 19 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 20 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 21 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 22 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 23 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 24 * SUCH DAMAGE. 25 * 26 * $FreeBSD$ 27 */ 28 29#ifndef _VDEVICE_H_ 30#define _VDEVICE_H_ 31 32/*************************************************************************** 33 * Description: virtual device header 34 ***************************************************************************/ 35 36typedef struct _VDevice 37{ 38 UCHAR VDeviceType; 39 UCHAR vf_bootmark: 1; /* is boot device? */ 40 UCHAR vf_bootable: 1; /* has active partition */ 41 UCHAR vf_online: 1; /* is usable? */ 42 UCHAR vf_cache_disk: 1; /* Cache enabled */ 43 UCHAR vf_format_v2: 1; /* old array block */ 44 UCHAR vf_freed: 1; /* memory free */ 45 UCHAR reserve1; 46 UCHAR bSerialNumber; /* valid if pParent!=0 */ 47 48 PVDevice pParent; /* parent array */ 49 PVBus pVBus; /* vbus this device located. Must not be NULL. */ 50 51 LBA_T VDeviceCapacity; /* number of blocks */ 52 53 LBA_T LockedLba; 54 USHORT LockedSectors; 55 USHORT ActiveRequests; 56 PCommand LockWaitList; 57 void (* HPTLIBAPI QuiesceAction)(_VBUS_ARG void *arg); 58 void *QuiesceArg; 59 void (* HPTLIBAPI flush_callback)(_VBUS_ARG void *arg); 60 void *flush_callback_arg; 61 62 63#if defined(_RAID5N_) 64 struct stripe **CacheEntry; 65 struct range_lock *range_lock; 66#endif 67 68 void (* HPTLIBAPI pfnSendCommand)(_VBUS_ARG PCommand pCmd); /* call this to send a command to a VDevice */ 69 void (* HPTLIBAPI pfnDeviceFailed)(_VBUS_ARG PVDevice pVDev); /* call this when a VDevice failed */ 70 71 union { 72#ifdef SUPPORT_ARRAY 73 RaidArray array; 74#endif 75 Device disk; 76 } u; 77 78} VDevice; 79 80#define ARRAY_VDEV_SIZE ((UINT)(ULONG_PTR)&((PVDevice)0)->u+sizeof(RaidArray)) 81#define DISK_VDEV_SIZE ((UINT)(ULONG_PTR)&((PVDevice)0)->u+sizeof(Device)) 82 83#define Map2pVDevice(pDev) ((PVDevice)((UINT_PTR)pDev - (UINT)(UINT_PTR)&((PVDevice)0)->u.disk)) 84 85/* 86 * bUserDeviceMode 87 */ 88#define MEMBER_NOT_SET_MODE 0x5F 89 90/* 91 * arrayType 92 */ 93#define VD_SPARE 0 94#define VD_REMOVABLE 1 95#define VD_ATAPI 2 96#define VD_SINGLE_DISK 3 97 98#define VD_JBOD 4 /* JBOD */ 99#define VD_RAID_0 5 /* RAID 0 stripe */ 100#define VD_RAID_1 6 /* RAID 1 mirror */ 101#define VD_RAID_3 7 /* RAID 3 */ 102#define VD_RAID_5 8 /* RAID 5 */ 103#define VD_MAX_TYPE 8 104 105#ifdef SUPPORT_ARRAY 106#define mIsArray(pVDev) (pVDev->VDeviceType>VD_SINGLE_DISK) 107#else 108#define mIsArray(pVDev) 0 109#endif 110 111extern void (* HPTLIBAPI pfnSendCommand[])(_VBUS_ARG PCommand pCmd); 112extern void (* HPTLIBAPI pfnDeviceFailed[])(_VBUS_ARG PVDevice pVDev); 113void HPTLIBAPI fOsDiskFailed(_VBUS_ARG PVDevice pVDev); 114void HPTLIBAPI fDeviceSendCommand(_VBUS_ARG PCommand pCmd); 115void HPTLIBAPI fSingleDiskFailed(_VBUS_ARG PVDevice pVDev); 116 117/*************************************************************************** 118 * Description: RAID Adapter 119 ***************************************************************************/ 120 121typedef struct _VBus { 122 /* pVDevice[] may be non-continuous */ 123 PVDevice pVDevice[MAX_VDEVICE_PER_VBUS]; 124 125 UINT nInstances; 126 PChipInstance pChipInstance[MAX_CHIP_IN_VBUS]; 127 128 void * OsExt; /* for OS private use */ 129 130 131 int serial_mode; 132 int next_active; 133 int working_devs; 134 135 136 137 PCommand pFreeCommands; 138 DPC_ROUTINE PendingRoutines[MAX_PENDING_ROUTINES]; 139 int PendingRoutinesFirst, PendingRoutinesLast; 140 DPC_ROUTINE IdleRoutines[MAX_IDLE_ROUTINES]; 141 int IdleRoutinesFirst, IdleRoutinesLast; 142 143#ifdef SUPPORT_ARRAY 144 PVDevice pFreeArrayLink; 145 BYTE _ArrayTables[MAX_ARRAY_PER_VBUS * ARRAY_VDEV_SIZE]; 146#endif 147 148 149#ifdef _RAID5N_ 150 struct r5_global_data r5; 151#endif 152 153} VBus; 154 155/* 156 * Array members must be on same VBus. 157 * The platform dependent part shall select one of the following strategy. 158 */ 159#ifdef SET_VBUS_FOR_EACH_IRQ 160#define CHIP_ON_SAME_VBUS(pChip1, pChip2) ((pChip1)->bChipIntrNum==(pChip2)->bChipIntrNum) 161#elif defined(SET_VBUS_FOR_EACH_CONTROLLER) 162#define CHIP_ON_SAME_VBUS(pChip1, pChip2) \ 163 ((pChip1)->pci_bus==(pChip2)->pci_bus && (pChip1)->pci_dev==(pChip2)->pci_dev) 164#elif defined(SET_VBUS_FOR_EACH_FUNCTION) 165#define CHIP_ON_SAME_VBUS(pChip1, pChip2) \ 166 ((pChip1)->pci_bus==(pChip2)->pci_bus && (pChip1)->pci_dev==(pChip2)->pci_dev && (pChip1)->pci_func==(pChip2)->pci_func) 167#else 168#error You must set one vbus setting 169#endif 170 171#define FOR_EACH_CHANNEL_ON_VBUS(_pVBus, _pChan) \ 172 for (_pChan=pChanStart; _pChan<pChanEnd; _pChan++) \ 173 if (_pChan->pChipInstance->pVBus!=_pVBus) ; else 174 175#define FOR_EACH_DEV_ON_VBUS(pVBus, pVDev, i) \ 176 for(i = 0; i < MAX_VDEVICE_PER_VBUS; i++) \ 177 if ((pVDev=pVBus->pVDevice[i])==0) continue; else 178 179 180#define FOR_EACH_VBUS(pVBus) \ 181 for(pVBus = gVBus; pVBus < &gVBus[MAX_VBUS]; pVBus++) \ 182 183#define FOR_EACH_ARRAY_ON_ALL_VBUS(pVBus, pArray, i) \ 184 for(pVBus = gVBus; pVBus < &gVBus[MAX_VBUS]; pVBus++) \ 185 for(i = 0; i < MAX_ARRAY_PER_VBUS; i++) \ 186 if ((pArray=((PVDevice)&pVBus->_ArrayTables[i*ARRAY_VDEV_SIZE]))->u.array.dArStamp==0) continue; else 187 188#define FOR_EACH_DEV_ON_ALL_VBUS(pVBus, pVDev, i) \ 189 FOR_EACH_VBUS(pVBus) \ 190 for(i = 0; i < MAX_VDEVICE_PER_VBUS; i++) \ 191 if ((pVDev=pVBus->pVDevice[i])==0) continue; else 192 193/*************************************************************************** 194 * Description: the functions called by IDE layer 195 ***************************************************************************/ 196#ifdef SUPPORT_ARRAY 197#define IdeRegisterDevice fCheckArray 198#else 199void HPTLIBAPI IdeRegisterDevice(PDevice pDev); 200#endif 201 202/*************************************************************************** 203 * Description: the functions OS must provided 204 ***************************************************************************/ 205 206void HPTLIBAPI OsSetDeviceTable(PDevice pDevice, PIDENTIFY_DATA pIdentify); 207 208/* 209 * allocate and free data structure 210 */ 211PChannel fGetChannelTable(void); 212PDevice fGetDeviceTable(void); 213#define OsGetChannelTable(x, y) fGetChannelTable() 214#define OsGetDeviceTable(x, y) fGetDeviceTable() 215void OsReturnTable(PDevice pDevice); 216/*************************************************************************** 217 * Description: the functions Prototype 218 ***************************************************************************/ 219/* 220 * vdevice.c 221 */ 222int Initialize(void); 223int InitializeAllChips(void); 224void InitializeVBus(PVBus pVBus); 225void fRegisterChip(PChipInstance pChip); 226void __fRegisterVDevices(PVBus pVBus); 227void fRegisterVDevices(void); 228void HPTLIBAPI UnregisterVDevice(PVDevice); 229void HPTLIBAPI fCheckBootable(PVDevice pVDev); 230void HPTLIBAPI fFlushVDev(PVDevice pVDev); 231void HPTLIBAPI fFlushVDevAsync(PVDevice pVDev, DPC_PROC done, void *arg); 232void HPTLIBAPI fShutdownVDev(PVDevice pVDev); 233void HPTLIBAPI fResetVBus(_VBUS_ARG0); 234void HPTLIBAPI fCompleteAllCommandsSynchronously(PVBus _vbus_p); 235 236#define RegisterVDevice(pVDev) 237#define OsRegisterDevice(pVDev) 238#define OsUnregisterDevice(pVDev) 239 240#ifdef SUPPORT_VBUS_CONFIG 241void VBus_Config(PVBus pVBus, char *str); 242#else 243#define VBus_Config(pVBus, str) 244#endif 245 246#pragma pack(1) 247struct fdisk_partition_table 248{ 249 UCHAR bootid; /* bootable? 0=no, 128=yes */ 250 UCHAR beghead; /* beginning head number */ 251 UCHAR begsect; /* beginning sector number */ 252 UCHAR begcyl; /* 10 bit nmbr, with high 2 bits put in begsect */ 253 UCHAR systid; /* Operating System type indicator code */ 254 UCHAR endhead; /* ending head number */ 255 UCHAR endsect; /* ending sector number */ 256 UCHAR endcyl; /* also a 10 bit nmbr, with same high 2 bit trick */ 257 ULONG relsect; /* first sector relative to start of disk */ 258 ULONG numsect; /* number of sectors in partition */ 259}; 260 261typedef struct _Master_Boot_Record 262{ 263 UCHAR bootinst[446]; /* space to hold actual boot code */ 264 struct fdisk_partition_table parts[4]; 265 USHORT signature; /* set to 0xAA55 to indicate PC MBR format */ 266} 267Master_Boot_Record, *PMaster_Boot_Record; 268 269#ifndef SUPPORT_ARRAY 270/* TODO: move it later */ 271#ifdef __BIG_ENDIAN_BITFIELD 272typedef DWORD TIME_RECORD; 273#else 274typedef struct _TIME_RECORD { 275 UINT seconds:6; /* 0 - 59 */ 276 UINT minutes:6; /* 0 - 59 */ 277 UINT month:4; /* 1 - 12 */ 278 UINT hours:6; /* 0 - 59 */ 279 UINT day:5; /* 1 - 31 */ 280 UINT year:5; /* 0=2000, 31=2031 */ 281} TIME_RECORD; 282#endif 283#endif 284 285#pragma pack() 286#endif 287