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