1 /*++ 2 3 Copyright (c) 2004-2016 Alexandr A. Telyatnikov (Alter) 4 5 Module Name: 6 id_init.cpp 7 8 Abstract: 9 This is the chip-specific init module for ATA/ATAPI IDE controllers 10 with Busmaster DMA and Serial ATA support 11 12 Author: 13 Alexander A. Telyatnikov (Alter) 14 15 Environment: 16 kernel mode only 17 18 Notes: 19 20 THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 21 IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 22 OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 23 IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 24 INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 25 NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 26 DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 27 THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 28 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 29 THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 30 31 Revision History: 32 33 Some parts of code were taken from FreeBSD 5.1-6.1 ATA driver by 34 S�ren Schmidt, Copyright (c) 1998-2007 35 added IT8172 IDE controller support from Linux 36 added VIA 8233/8235 fix from Linux 37 added 80-pin cable detection from Linux for 38 VIA, nVidia 39 added support for non-standard layout of registers 40 added SATA support 41 added AHCI support 42 43 Licence: 44 GPLv2 45 46 --*/ 47 48 #include "stdafx.h" 49 50 static BUSMASTER_CONTROLLER_INFORMATION_BASE const AtiSouthAdapters[] = { 51 PCI_DEV_HW_SPEC_BM( 4385, 1002, 0x00, ATA_MODE_NOT_SPEC, "ATI South", 0 ), 52 PCI_DEV_HW_SPEC_BM( ffff, ffff, 0xff, BMLIST_TERMINATOR, NULL , BMLIST_TERMINATOR ) 53 }; 54 55 56 BOOLEAN 57 NTAPI 58 UniataChipDetectChannels( 59 IN PVOID HwDeviceExtension, 60 IN PPCI_COMMON_CONFIG pciData, // optional 61 IN ULONG DeviceNumber, 62 IN PPORT_CONFIGURATION_INFORMATION ConfigInfo 63 ) 64 { 65 PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension; 66 //ULONG slotNumber = deviceExtension->slotNumber; 67 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber; 68 ULONG VendorID = deviceExtension->DevID & 0xffff; 69 //ULONG DeviceID = (deviceExtension->DevID >> 16) & 0xffff; 70 //ULONG RevID = deviceExtension->RevID; 71 ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK; 72 ULONG ChipFlags= deviceExtension->HwFlags & CHIPFLAG_MASK; 73 ULONG i,n; 74 75 KdPrint2((PRINT_PREFIX "UniataChipDetectChannels:\n" )); 76 77 deviceExtension->AHCI_PI_mask = 0; 78 79 if(ChipFlags & (UNIATA_SATA | UNIATA_AHCI)) { 80 if(!deviceExtension->NumberChannels) { 81 KdPrint2((PRINT_PREFIX "uninitialized SATA/AHCI port number -> 1\n")); 82 deviceExtension->NumberChannels = 1; 83 } 84 if(AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"IgnoreAhciPM", 1 /* DEBUG */)) { 85 KdPrint2((PRINT_PREFIX "SATA/AHCI w/o PM, max luns 1 or 2\n")); 86 deviceExtension->NumberLuns = 2; // we may be in Legacy mode 87 //chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 88 } else { 89 KdPrint2((PRINT_PREFIX "SATA/AHCI -> possible PM, max luns %d\n", SATA_MAX_PM_UNITS)); 90 deviceExtension->NumberLuns = SATA_MAX_PM_UNITS; 91 //deviceExtension->NumberLuns = 1; 92 } 93 } 94 if(deviceExtension->MasterDev) { 95 KdPrint2((PRINT_PREFIX "MasterDev -> 1 chan\n")); 96 deviceExtension->NumberChannels = 1; 97 } 98 for(n=0; n<deviceExtension->NumberChannels; n++) { 99 if(AtapiRegCheckDevValue(deviceExtension, n, DEVNUM_NOT_SPECIFIED, L"Exclude", 0)) { 100 KdPrint2((PRINT_PREFIX "Channel %d excluded\n", n)); 101 deviceExtension->AHCI_PI_mask &= ~((ULONG)1 << n); 102 } else { 103 deviceExtension->AHCI_PI_mask |= ((ULONG)1 << n); 104 } 105 } 106 KdPrint2((PRINT_PREFIX "PortMask %#x\n", deviceExtension->AHCI_PI_mask)); 107 deviceExtension->AHCI_PI_mask = 108 AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"PortMask", (ULONG)0xffffffff >> (32-deviceExtension->NumberChannels) ); 109 KdPrint2((PRINT_PREFIX "Force PortMask %#x\n", deviceExtension->AHCI_PI_mask)); 110 111 for(i=deviceExtension->AHCI_PI_mask, n=0; i; n++, i=i>>1); 112 KdPrint2((PRINT_PREFIX "mask -> %d chans\n", n)); 113 114 switch(VendorID) { 115 case ATA_ACER_LABS_ID: 116 switch(deviceExtension->DevID) { 117 case 0x528710b9: 118 case 0x528810b9: 119 deviceExtension->NumberChannels = 4; 120 KdPrint2((PRINT_PREFIX "Acer 4 chan\n")); 121 } 122 break; 123 case ATA_PROMISE_ID: 124 125 if(ChipType != PRMIO) { 126 break; 127 } 128 if(!(ChipFlags & UNIATA_SATA)) { 129 deviceExtension->NumberChannels = 4; 130 KdPrint2((PRINT_PREFIX "Promise up to 4 chan\n")); 131 } else 132 if(ChipFlags & PRCMBO) { 133 deviceExtension->NumberChannels = 3; 134 KdPrint2((PRINT_PREFIX "Promise 3 chan\n")); 135 } else { 136 deviceExtension->NumberChannels = 4; 137 KdPrint2((PRINT_PREFIX "Promise 4 chan\n")); 138 } 139 break; 140 case ATA_MARVELL_ID: 141 KdPrint2((PRINT_PREFIX "Marvell\n")); 142 /* AHCI part has own DevID-based workaround */ 143 switch(deviceExtension->DevID) { 144 case 0x610111ab: 145 /* 88SX6101 only have 1 PATA channel */ 146 if(BMList[deviceExtension->DevIndex].channel) { 147 KdPrint2((PRINT_PREFIX "88SX6101/11 has no 2nd PATA chan\n")); 148 return FALSE; 149 } 150 deviceExtension->NumberChannels = 1; 151 KdPrint2((PRINT_PREFIX "88SX6101 PATA 1 chan\n")); 152 break; 153 } 154 break; 155 case ATA_ATI_ID: 156 KdPrint2((PRINT_PREFIX "ATI\n")); 157 switch(deviceExtension->DevID) { 158 case ATA_ATI_IXP600: 159 KdPrint2((PRINT_PREFIX " IXP600\n")); 160 /* IXP600 only have 1 PATA channel */ 161 if(BMList[deviceExtension->DevIndex].channel) { 162 KdPrint2((PRINT_PREFIX "New ATI no 2nd PATA chan\n")); 163 return FALSE; 164 } 165 deviceExtension->NumberChannels = 1; 166 KdPrint2((PRINT_PREFIX "New ATI PATA 1 chan\n")); 167 break; 168 169 case ATA_ATI_IXP700: { 170 UCHAR satacfg = 0; 171 PCI_SLOT_NUMBER slotData; 172 ULONG j, slotNumber; 173 174 KdPrint2((PRINT_PREFIX " IXP700\n")); 175 /* 176 * When "combined mode" is enabled, an additional PATA channel is 177 * emulated with two SATA ports and appears on this device. 178 * This mode can only be detected via SMB controller. 179 */ 180 j = AtapiFindListedDev((BUSMASTER_CONTROLLER_INFORMATION_BASE*)&AtiSouthAdapters[0], -1, HwDeviceExtension, SystemIoBusNumber, PCISLOTNUM_NOT_SPECIFIED, &slotData); 181 if(j != BMLIST_TERMINATOR) { 182 slotNumber = slotData.u.AsULONG; 183 184 GetPciConfig1(0xad, satacfg); 185 KdPrint(("SATA controller %s (%s%s channel)\n", 186 (satacfg & 0x01) == 0 ? "disabled" : "enabled", 187 (satacfg & 0x08) == 0 ? "" : "combined mode, ", 188 (satacfg & 0x10) == 0 ? "primary" : "secondary")); 189 /* 190 * If SATA controller is enabled but combined mode is disabled, 191 * we have only one PATA channel. Ignore a non-existent channel. 192 */ 193 if ((satacfg & 0x09) == 0x01) { 194 if(BMList[deviceExtension->DevIndex].channel) { 195 KdPrint2((PRINT_PREFIX "New ATI no 2nd PATA chan\n")); 196 return FALSE; 197 } 198 deviceExtension->NumberChannels = 1; 199 KdPrint2((PRINT_PREFIX "New ATI PATA 1 chan\n")); 200 break; 201 } else { 202 KdPrint2((PRINT_PREFIX "New ATI 2 chan\n")); 203 deviceExtension->NumberChannels = 2; 204 /* 205 if (BMList[deviceExtension->DevIndex].channel != ((satacfg & 0x10) >> 4)) { 206 ; 207 } 208 */ 209 210 } 211 } 212 213 break; } 214 } 215 /* FALLTHROUGH */ 216 case ATA_SILICON_IMAGE_ID: 217 218 if(ChipFlags & SIIBUG) { 219 /* work around errata in early chips */ 220 deviceExtension->DmaSegmentLength = 15 * DEV_BSIZE; 221 deviceExtension->DmaSegmentAlignmentMask = 8192-1; 222 } 223 if(ChipType != SIIMIO) { 224 break; 225 } 226 if(!pciData) { 227 break; 228 } 229 230 if(VendorID == ATA_SILICON_IMAGE_ID) { 231 KdPrint2((PRINT_PREFIX "New SII\n")); 232 } else { 233 KdPrint2((PRINT_PREFIX "ATI SATA\n")); 234 } 235 if(deviceExtension->HwFlags & SII4CH) { 236 deviceExtension->NumberChannels = 4; 237 KdPrint2((PRINT_PREFIX "4 chan\n")); 238 } 239 break; 240 case ATA_VIA_ID: 241 if(/*(deviceExtension->DevID == 0x32491106) && 242 ScsiPortConvertPhysicalAddressToUlong((*ConfigInfo->AccessRanges)[5].RangeStart)*/ 243 deviceExtension->HwFlags & VIABAR) { 244 deviceExtension->NumberChannels = 3; 245 KdPrint2((PRINT_PREFIX "VIA 3 chan\n")); 246 } 247 if(ChipFlags & VIASATA) { 248 /* 2 SATA without SATA registers on first channel + 1 PATA on second */ 249 // do nothing, generic PATA INIT 250 KdPrint2((PRINT_PREFIX "VIA SATA without SATA regs -> no PM\n")); 251 deviceExtension->NumberLuns = 1; 252 } 253 break; 254 case ATA_ITE_ID: 255 /* ITE ATA133 controller */ 256 if(deviceExtension->DevID == 0x82131283) { 257 if(BMList[deviceExtension->DevIndex].channel) { 258 KdPrint2((PRINT_PREFIX "New ITE has no 2nd PATA chan\n")); 259 return FALSE; 260 } 261 deviceExtension->NumberChannels = 1; 262 KdPrint2((PRINT_PREFIX "New ITE PATA 1 chan\n")); 263 } 264 break; 265 #if 0 266 case ATA_INTEL_ID: 267 /* New Intel PATA controllers */ 268 if(g_opt_VirtualMachine != VM_VBOX && 269 /*deviceExtension->DevID == 0x27df8086 || 270 deviceExtension->DevID == 0x269e8086 || 271 deviceExtension->DevID == ATA_I82801HBM*/ 272 ChipFlags & I1CH) { 273 if(BMList[deviceExtension->DevIndex].channel) { 274 KdPrint2((PRINT_PREFIX "New Intel PATA has no 2nd chan\n")); 275 return FALSE; 276 } 277 deviceExtension->NumberChannels = 1; 278 KdPrint2((PRINT_PREFIX "New Intel PATA 1 chan\n")); 279 } 280 break; 281 #endif // this code is removed from newer FreeBSD 282 case ATA_JMICRON_ID: 283 /* New JMicron PATA controllers */ 284 if(deviceExtension->DevID == ATA_JMB361 || 285 deviceExtension->DevID == ATA_JMB363 || 286 deviceExtension->DevID == ATA_JMB368) { 287 if(BMList[deviceExtension->DevIndex].channel) { 288 KdPrint2((PRINT_PREFIX "New JMicron has no 2nd chan\n")); 289 return FALSE; 290 } 291 deviceExtension->NumberChannels = 1; 292 KdPrint2((PRINT_PREFIX "New JMicron PATA 1 chan\n")); 293 } 294 break; 295 case ATA_CYRIX_ID: 296 if(ChipType == CYRIX_OLD) { 297 UCHAR tmp8; 298 ULONG slotNumber; 299 slotNumber = deviceExtension->slotNumber; 300 KdPrint2((PRINT_PREFIX "Cyrix slot %#x\n", slotNumber)); 301 GetPciConfig1(0x60, tmp8); 302 if(tmp8 & (1 << BMList[deviceExtension->DevIndex].channel)) { 303 KdPrint2((PRINT_PREFIX "Old Cyrix chan %d ok\n", BMList[deviceExtension->DevIndex].channel)); 304 } else { 305 KdPrint2((PRINT_PREFIX "Old Cyrix no chan %d\n", BMList[deviceExtension->DevIndex].channel)); 306 return FALSE; 307 } 308 } 309 break; 310 } // end switch(VendorID) 311 312 i = AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"NumberChannels", n); 313 if(!i) { 314 i = n; 315 } 316 KdPrint2((PRINT_PREFIX "reg -> %d chans\n", n)); 317 318 deviceExtension->NumberChannels = min(i, deviceExtension->NumberChannels); 319 if(!deviceExtension->NumberChannels) { 320 KdPrint2((PRINT_PREFIX "all channels blocked\n", n)); 321 return FALSE; 322 } 323 deviceExtension->AHCI_PI_mask &= (ULONG)0xffffffff >> (32-deviceExtension->NumberChannels); 324 KdPrint2((PRINT_PREFIX "Final PortMask %#x\n", deviceExtension->AHCI_PI_mask)); 325 326 return TRUE; 327 328 } // end UniataChipDetectChannels() 329 330 NTSTATUS 331 NTAPI 332 UniataChipDetect( 333 IN PVOID HwDeviceExtension, 334 IN PPCI_COMMON_CONFIG pciData, // optional 335 IN ULONG DeviceNumber, 336 IN OUT PPORT_CONFIGURATION_INFORMATION ConfigInfo, 337 IN BOOLEAN* simplexOnly 338 ) 339 { 340 PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension; 341 ULONG slotNumber = deviceExtension->slotNumber; 342 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber; 343 ULONG VendorID = deviceExtension->DevID & 0xffff; 344 ULONG DeviceID = (deviceExtension->DevID >> 16) & 0xffff; 345 ULONG RevID = deviceExtension->RevID; 346 ULONG i, c; 347 BUSMASTER_CONTROLLER_INFORMATION_BASE* DevTypeInfo; 348 PHW_CHANNEL chan; 349 ULONG ChipType; 350 ULONG ChipFlags; 351 ULONG tmp32; 352 UCHAR tmp8; 353 ULONG BaseMemAddress; 354 ULONG BaseIoAddress1; 355 ULONG BaseIoAddress2; 356 ULONG BaseIoAddressBM; 357 BOOLEAN MemIo = FALSE; 358 BOOLEAN IsPata = FALSE; 359 360 KdPrint2((PRINT_PREFIX "UniataChipDetect:\n" )); 361 KdPrint2((PRINT_PREFIX "HwFlags: %#x\n", deviceExtension->HwFlags)); 362 363 i = Ata_is_dev_listed((PBUSMASTER_CONTROLLER_INFORMATION_BASE)&BusMasterAdapters[0], VendorID, 0xffff, 0, NUM_BUSMASTER_ADAPTERS); 364 365 c = AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"ForceSimplex", 0); 366 if(c) { 367 *simplexOnly = TRUE; 368 } 369 370 // defaults 371 BaseIoAddressBM = pciData->u.type0.BaseAddresses[4] & ~0x07; 372 deviceExtension->MaxTransferMode = BaseIoAddressBM ? ATA_DMA : ATA_PIO4; 373 ConfigInfo->MaximumTransferLength = DEV_BSIZE*256; 374 deviceExtension->MaximumDmaTransferLength = ConfigInfo->MaximumTransferLength; 375 //deviceExtension->NumberOfPhysicalBreaks = min(deviceExtension->MaximumDmaTransferLength/PAGE_SIZE+1, ATA_DMA_ENTRIES); 376 deviceExtension->DmaSegmentLength = 0x10000; 377 deviceExtension->DmaSegmentAlignmentMask = 0xffff; 378 379 KdPrint2((PRINT_PREFIX "i: %#x\n", i)); 380 if(i != BMLIST_TERMINATOR) { 381 DevTypeInfo = (PBUSMASTER_CONTROLLER_INFORMATION_BASE)&BusMasterAdapters[i]; 382 } else { 383 unknown_dev: 384 if(Ata_is_ahci_dev(pciData)) { 385 KdPrint2((PRINT_PREFIX " AHCI candidate")); 386 387 deviceExtension->NumberChannels = 0; 388 if(!UniataAhciDetect(HwDeviceExtension, pciData, ConfigInfo)) { 389 KdPrint2((PRINT_PREFIX " AHCI init failed - not detected\n")); 390 return STATUS_UNSUCCESSFUL; 391 } 392 KdPrint2((PRINT_PREFIX " unknown AHCI dev, addr %#x ", deviceExtension->BaseIoAHCI_0.Addr)); 393 } 394 KdPrint2((PRINT_PREFIX " unknown dev, BM addr %#x ", BaseIoAddressBM)); 395 DevTypeInfo = NULL; 396 KdPrint2((PRINT_PREFIX " MaxTransferMode %#x\n", deviceExtension->MaxTransferMode)); 397 398 if(!UniataChipDetectChannels(HwDeviceExtension, pciData, DeviceNumber, ConfigInfo)) { 399 return STATUS_UNSUCCESSFUL; 400 } 401 if(!UniataAllocateLunExt(deviceExtension, UNIATA_ALLOCATE_NEW_LUNS)) { 402 return STATUS_UNSUCCESSFUL; 403 } 404 return STATUS_SUCCESS; 405 } 406 407 static BUSMASTER_CONTROLLER_INFORMATION_BASE const SiSAdapters[] = { 408 PCI_DEV_HW_SPEC_BM( 1183, 1039, 0x00, ATA_SA150, "SiS 1183 IDE" , SIS133NEW), 409 PCI_DEV_HW_SPEC_BM( 1182, 1039, 0x00, ATA_SA150, "SiS 1182" , SISSATA | UNIATA_SATA), 410 PCI_DEV_HW_SPEC_BM( 0183, 1039, 0x00, ATA_SA150, "SiS 183 RAID" , SISSATA | UNIATA_SATA), 411 PCI_DEV_HW_SPEC_BM( 0182, 1039, 0x00, ATA_SA150, "SiS 182" , SISSATA | UNIATA_SATA), 412 PCI_DEV_HW_SPEC_BM( 0181, 1039, 0x00, ATA_SA150, "SiS 181" , SISSATA | UNIATA_SATA), 413 PCI_DEV_HW_SPEC_BM( 0180, 1039, 0x00, ATA_SA150, "SiS 180" , SISSATA | UNIATA_SATA), 414 PCI_DEV_HW_SPEC_BM( 0965, 1039, 0x00, ATA_UDMA6, "SiS 965" , SIS133NEW ), 415 PCI_DEV_HW_SPEC_BM( 0964, 1039, 0x00, ATA_UDMA6, "SiS 964" , SIS133NEW ), 416 PCI_DEV_HW_SPEC_BM( 0963, 1039, 0x00, ATA_UDMA6, "SiS 963" , SIS133NEW ), 417 PCI_DEV_HW_SPEC_BM( 0962, 1039, 0x00, ATA_UDMA6, "SiS 962" , SIS133NEW ), 418 419 PCI_DEV_HW_SPEC_BM( 0745, 1039, 0x00, ATA_UDMA5, "SiS 745" , SIS100NEW ), 420 PCI_DEV_HW_SPEC_BM( 0735, 1039, 0x00, ATA_UDMA5, "SiS 735" , SIS100NEW ), 421 PCI_DEV_HW_SPEC_BM( 0733, 1039, 0x00, ATA_UDMA5, "SiS 733" , SIS100NEW ), 422 PCI_DEV_HW_SPEC_BM( 0730, 1039, 0x00, ATA_UDMA5, "SiS 730" , SIS100OLD ), 423 424 PCI_DEV_HW_SPEC_BM( 0646, 1039, 0x00, ATA_UDMA6, "SiS 645DX", SIS133NEW ), 425 /* PCI_DEV_HW_SPEC_BM( 0645, 1039, 0x00, ATA_UDMA6, "SiS 645" , SIS133NEW ),*/ 426 /* PCI_DEV_HW_SPEC_BM( 0640, 1039, 0x00, ATA_UDMA4, "SiS 640" , SIS_SOUTH ),*/ 427 PCI_DEV_HW_SPEC_BM( 0635, 1039, 0x00, ATA_UDMA5, "SiS 635" , SIS100NEW ), 428 PCI_DEV_HW_SPEC_BM( 0633, 1039, 0x00, ATA_UDMA5, "SiS 633" , SIS100NEW ), 429 PCI_DEV_HW_SPEC_BM( 0630, 1039, 0x30, ATA_UDMA5, "SiS 630S" , SIS100OLD ), 430 PCI_DEV_HW_SPEC_BM( 0630, 1039, 0x00, ATA_UDMA4, "SiS 630" , SIS66 ), 431 PCI_DEV_HW_SPEC_BM( 0620, 1039, 0x00, ATA_UDMA4, "SiS 620" , SIS66 ), 432 433 PCI_DEV_HW_SPEC_BM( 0550, 1039, 0x00, ATA_UDMA5, "SiS 550" , SIS66 ), 434 PCI_DEV_HW_SPEC_BM( 0540, 1039, 0x00, ATA_UDMA4, "SiS 540" , SIS66 ), 435 PCI_DEV_HW_SPEC_BM( 0530, 1039, 0x00, ATA_UDMA4, "SiS 530" , SIS66 ), 436 437 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x04, ATA_UDMA6, "SiS 962L" , SIS133OLD ), // ??? 438 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x00, ATA_UDMA6, "SiS 961" , SIS133OLD ), 439 440 PCI_DEV_HW_SPEC_BM( 5517, 1039, 0x00, ATA_UDMA5, "SiS 961" , SIS100NEW | SIS_BASE ), 441 PCI_DEV_HW_SPEC_BM( 5518, 1039, 0x00, ATA_UDMA6, "SiS 962/3", SIS133NEW | SIS_BASE ), 442 PCI_DEV_HW_SPEC_BM( 5513, 1039, 0xc2, ATA_UDMA2, "SiS 5513" , SIS33 | SIS_BASE ), 443 PCI_DEV_HW_SPEC_BM( 5513, 1039, 0x00, ATA_WDMA2, "SiS 5513" , SIS33 | SIS_BASE ), 444 PCI_DEV_HW_SPEC_BM( 0601, 1039, 0x00, ATA_UDMA2, "SiS 5513" , SIS33 | SIS_BASE ), 445 PCI_DEV_HW_SPEC_BM( ffff, ffff, 0xff, BMLIST_TERMINATOR , NULL , BMLIST_TERMINATOR ) 446 }; 447 448 static BUSMASTER_CONTROLLER_INFORMATION_BASE const ViaAdapters[] = { 449 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x41, ATA_UDMA2, "VIA 82C586B", VIA33 | 0x00 ), 450 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x40, ATA_UDMA2, "VIA 82C586B", VIA33 | VIAPRQ ), 451 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x02, ATA_UDMA2, "VIA 82C586B", VIA33 | 0x00 ), 452 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x00, ATA_WDMA2, "VIA 82C586" , VIA33 | 0x00 ), 453 PCI_DEV_HW_SPEC_BM( 0596, 1106, 0x12, ATA_UDMA4, "VIA 82C596B", VIA66 | VIACLK ), 454 PCI_DEV_HW_SPEC_BM( 0596, 1106, 0x00, ATA_UDMA2, "VIA 82C596" , VIA33 | 0x00 ), 455 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x40, ATA_UDMA5, "VIA 82C686B", VIA100 | VIABUG ), 456 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x10, ATA_UDMA4, "VIA 82C686A", VIA66 | VIACLK ), 457 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x00, ATA_UDMA2, "VIA 82C686" , VIA33 | 0x00 ), 458 PCI_DEV_HW_SPEC_BM( 8231, 1106, 0x00, ATA_UDMA5, "VIA 8231" , VIA100 | VIABUG ), 459 PCI_DEV_HW_SPEC_BM( 3074, 1106, 0x00, ATA_UDMA5, "VIA 8233" , VIA100 | 0x00 ), 460 PCI_DEV_HW_SPEC_BM( 3109, 1106, 0x00, ATA_UDMA5, "VIA 8233C" , VIA100 | 0x00 ), 461 PCI_DEV_HW_SPEC_BM( 3147, 1106, 0x00, ATA_UDMA6, "VIA 8233A" , VIA133 | 0x00 ), 462 PCI_DEV_HW_SPEC_BM( 3177, 1106, 0x00, ATA_UDMA6, "VIA 8235" , VIA133 | 0x00 ), 463 PCI_DEV_HW_SPEC_BM( 3227, 1106, 0x00, ATA_UDMA6, "VIA 8237" , VIA133 | 0x00 ), 464 PCI_DEV_HW_SPEC_BM( 0591, 1106, 0x00, ATA_UDMA6, "VIA 8237A" , VIA133 | 0x00 ), 465 // presence of AHCI controller means something about isa-mapped part 466 PCI_DEV_HW_SPEC_BM( 5337, 1106, 0x00, ATA_UDMA6, "VIA 8237S" , VIA133 | 0x00 ), 467 PCI_DEV_HW_SPEC_BM( 5372, 1106, 0x00, ATA_UDMA6, "VIA 8237" , VIA133 | 0x00 ), 468 PCI_DEV_HW_SPEC_BM( 7372, 1106, 0x00, ATA_UDMA6, "VIA 8237" , VIA133 | 0x00 ), 469 PCI_DEV_HW_SPEC_BM( 3349, 1106, 0x00, ATA_UDMA6, "VIA 8251" , VIA133 | 0x00 ), 470 PCI_DEV_HW_SPEC_BM( 8324, 1106, 0x00, ATA_SA150, "VIA CX700" , VIANEW | VIASATA), 471 PCI_DEV_HW_SPEC_BM( 8353, 1106, 0x00, ATA_SA150, "VIA VX800" , VIANEW | VIASATA), 472 PCI_DEV_HW_SPEC_BM( 8409, 1106, 0x00, ATA_UDMA6, "VIA VX855" , VIA133 | 0x00 ), 473 PCI_DEV_HW_SPEC_BM( 8410, 1106, 0x00, ATA_SA300, "VIA VX900" , VIANEW | VIASATA), 474 PCI_DEV_HW_SPEC_BM( ffff, ffff, 0xff, BMLIST_TERMINATOR , NULL , BMLIST_TERMINATOR ) 475 }; 476 477 static BUSMASTER_CONTROLLER_INFORMATION_BASE const ViaSouthAdapters[] = { 478 PCI_DEV_HW_SPEC_BM( 3112, 1106, 0x00, ATA_MODE_NOT_SPEC, "VIA 8361", VIASOUTH ), 479 PCI_DEV_HW_SPEC_BM( 0305, 1106, 0x00, ATA_MODE_NOT_SPEC, "VIA 8363", VIASOUTH ), 480 PCI_DEV_HW_SPEC_BM( 0391, 1106, 0x00, ATA_MODE_NOT_SPEC, "VIA 8371", VIASOUTH ), 481 PCI_DEV_HW_SPEC_BM( 3102, 1106, 0x00, ATA_MODE_NOT_SPEC, "VIA 8662", VIASOUTH ), 482 PCI_DEV_HW_SPEC_BM( ffff, ffff, 0xff, BMLIST_TERMINATOR, NULL , BMLIST_TERMINATOR ) 483 }; 484 485 KdPrint2((PRINT_PREFIX "VendorID/DeviceID/Rev %#x/%#x/%#x\n", VendorID, DeviceID, RevID)); 486 487 switch(VendorID) { 488 489 case ATA_SIS_ID: 490 /* 491 We shall get here for all SIS controllers, even unlisted. 492 Then perform bus scan to find SIS bridge and decide what to do with controller 493 */ 494 KdPrint2((PRINT_PREFIX "ATA_SIS_ID\n")); 495 DevTypeInfo = (BUSMASTER_CONTROLLER_INFORMATION_BASE*)&SiSAdapters[0]; 496 i = AtapiFindListedDev(DevTypeInfo, -1, HwDeviceExtension, SystemIoBusNumber, PCISLOTNUM_NOT_SPECIFIED, NULL); 497 if(i != BMLIST_TERMINATOR) { 498 deviceExtension->FullDevName = SiSAdapters[i].FullDevName; 499 } 500 goto for_ugly_chips; 501 502 case ATA_VIA_ID: 503 KdPrint2((PRINT_PREFIX "ATA_VIA_ID\n")); 504 // New chips have own DeviceId 505 if(deviceExtension->DevID != ATA_VIA82C571 && 506 deviceExtension->DevID != ATA_VIACX700IDE && 507 deviceExtension->DevID != ATA_VIASATAIDE && 508 deviceExtension->DevID != ATA_VIASATAIDE2 && 509 deviceExtension->DevID != ATA_VIASATAIDE3) { 510 KdPrint2((PRINT_PREFIX "Via new\n")); 511 break; 512 } 513 KdPrint2((PRINT_PREFIX "Via-old-style %x\n", deviceExtension->DevID)); 514 // Traditionally, chips have same DeviceId, we can distinguish between them 515 // only by ISA Bridge DeviceId 516 DevTypeInfo = (BUSMASTER_CONTROLLER_INFORMATION_BASE*)&ViaSouthAdapters[0]; 517 i = AtapiFindListedDev(DevTypeInfo, -1, HwDeviceExtension, SystemIoBusNumber, 518 PCISLOTNUM_NOT_SPECIFIED/*slotNumber*/, NULL); 519 /* if(i == BMLIST_TERMINATOR) { 520 i = AtapiFindListedDev(DevTypeInfo, -1, HwDeviceExtension, SystemIoBusNumber, PCISLOTNUM_NOT_SPECIFIED, NULL); 521 }*/ 522 if(i != BMLIST_TERMINATOR) { 523 KdPrint2((PRINT_PREFIX "VIASOUTH\n")); 524 deviceExtension->HwFlags |= VIASOUTH; 525 } 526 DevTypeInfo = (BUSMASTER_CONTROLLER_INFORMATION_BASE*)&ViaAdapters[0]; 527 i = AtapiFindListedDev(DevTypeInfo, -1, HwDeviceExtension, SystemIoBusNumber, 528 PCISLOTNUM_NOT_SPECIFIED/*slotNumber*/, NULL); 529 if(i != BMLIST_TERMINATOR) { 530 deviceExtension->FullDevName = ViaAdapters[i].FullDevName; 531 } 532 goto for_ugly_chips; 533 534 default: 535 536 // do nothing 537 break; 538 539 #if 0 540 KdPrint2((PRINT_PREFIX "Default\n")); 541 542 deviceExtension->MaxTransferMode = deviceExtension->BaseIoAddressBM_0 ? ATA_DMA : ATA_PIO4; 543 /* do extra chipset specific setups */ 544 switch(deviceExtension->DevID) { 545 546 //case ATA_CYPRESS_ID: 547 case 0xc6931080: /* 82c693 ATA controller */ 548 deviceExtension->MaxTransferMode = ATA_WDMA2; 549 break; 550 551 case 0x000116ca: /* Cenatek Rocket Drive controller */ 552 deviceExtension->MaxTransferMode = ATA_WDMA2; 553 break; 554 555 /* case ATA_CYRIX_ID: 556 DevTypeInfo = &CyrixAdapters[0]; 557 break;*/ 558 case 0x01021078: /* Cyrix 5530 ATA33 controller */ 559 deviceExtension->MaxTransferMode = ATA_UDMA2; 560 break; 561 562 case 0x06401039: /* CMD 640 known bad, no DMA */ 563 case 0x06011039: 564 *simplexOnly = TRUE; 565 566 /* FALLTHROUGH */ 567 568 case 0x10001042: /* RZ 100x known bad, no DMA */ 569 case 0x10011042: 570 571 if(deviceExtension->BaseIoAddressBM_0) 572 ScsiPortFreeDeviceBase(HwDeviceExtension, 573 deviceExtension->BaseIoAddressBM_0); 574 575 UniataInitIoResEx(&deviceExtension->BaseIoAddressBM_0, 0, FALSE, FALSE); 576 deviceExtension->BusMaster = DMA_MODE_NONE; 577 deviceExtension->MaxTransferMode = ATA_PIO4; 578 break; 579 580 case 0x81721283: /* IT8172 IDE controller */ 581 deviceExtension->MaxTransferMode = ATA_UDMA2; 582 *simplexOnly = TRUE; 583 break; 584 585 default: 586 return STATUS_NOT_FOUND; 587 } 588 return STATUS_SUCCESS; 589 #endif 590 } 591 592 i = Ata_is_dev_listed(DevTypeInfo, VendorID, DeviceID, RevID, -1); 593 for_ugly_chips: 594 KdPrint2((PRINT_PREFIX "i: %#x\n", i)); 595 if(i == BMLIST_TERMINATOR) { 596 goto unknown_dev; 597 //return STATUS_NOT_FOUND; 598 } 599 deviceExtension->MaxTransferMode = DevTypeInfo[i].MaxTransferMode; 600 deviceExtension->HwFlags |= DevTypeInfo[i].RaidFlags; 601 602 KdPrint2((PRINT_PREFIX "HwFlags: %#x\n", deviceExtension->HwFlags)); 603 604 tmp32 = AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"HwFlagsOverride", deviceExtension->HwFlags); 605 KdPrint2((PRINT_PREFIX "HwFlagsOverride: %#x\n", tmp32)); 606 deviceExtension->HwFlags = tmp32; 607 608 tmp32 = AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"HwFlagsAdd", 0); 609 KdPrint2((PRINT_PREFIX "HwFlagsAdd: %#x\n", tmp32)); 610 deviceExtension->HwFlags |= tmp32; 611 612 KdPrint2((PRINT_PREFIX "HwFlags (final): %#x\n", deviceExtension->HwFlags)); 613 if(deviceExtension->HwFlags & UNIATA_SIMPLEX_ONLY) { 614 KdPrint2((PRINT_PREFIX "UNIATA_SIMPLEX_ONLY\n" )); 615 *simplexOnly = TRUE; 616 } 617 618 KdPrint2((PRINT_PREFIX "MaxTransferMode: %#x\n", deviceExtension->MaxTransferMode)); 619 tmp32 = AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"MaxTransferMode", deviceExtension->MaxTransferMode); 620 if(tmp32 != 0xffffffff) { 621 KdPrint2((PRINT_PREFIX "MaxTransferMode (overriden): %#x\n", deviceExtension->MaxTransferMode)); 622 deviceExtension->MaxTransferMode = tmp32; 623 } 624 625 if(deviceExtension->MaxTransferMode >= ATA_SA150) { 626 KdPrint2((PRINT_PREFIX "setting UNIATA_SATA flag\n")); 627 deviceExtension->HwFlags |= UNIATA_SATA; 628 } 629 630 /* 631 ConfigInfo->MaximumTransferLength = DEV_BSIZE*256; 632 deviceExtension->MaximumDmaTransferLength = ConfigInfo->MaximumTransferLength; 633 */ 634 ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK; 635 ChipFlags = deviceExtension->HwFlags & CHIPFLAG_MASK; 636 637 /* for even more ugly AHCI-capable chips */ 638 if(ChipFlags & UNIATA_AHCI) { 639 /* 640 Seems, some chips may have inoperable/alternative BAR5 in SATA mode 641 This can be detected via PCI SubClass 642 */ 643 switch(VendorID) { 644 case ATA_NVIDIA_ID: 645 case ATA_ATI_ID: 646 KdPrint2((PRINT_PREFIX "ATA_xxx_ID check AHCI subclass\n")); 647 if((pciData)->SubClass == PCI_DEV_SUBCLASS_IDE) { 648 KdPrint2((PRINT_PREFIX "Non-AHCI mode\n")); 649 ChipFlags &= ~UNIATA_AHCI; 650 deviceExtension->HwFlags &= ~UNIATA_AHCI; 651 } 652 break; 653 default: 654 if(!ScsiPortConvertPhysicalAddressToUlong((*ConfigInfo->AccessRanges)[5].RangeStart)) { 655 KdPrint2((PRINT_PREFIX "No BAR5, try BM\n")); 656 ChipFlags &= ~UNIATA_AHCI; 657 deviceExtension->HwFlags &= ~UNIATA_AHCI; 658 } 659 break; 660 } 661 } 662 663 if(ChipFlags & UNIATA_AHCI) { 664 665 deviceExtension->NumberChannels = 0; 666 if(!UniataAhciDetect(HwDeviceExtension, pciData, ConfigInfo)) { 667 KdPrint2((PRINT_PREFIX " AHCI detect failed\n")); 668 return STATUS_UNSUCCESSFUL; 669 } 670 671 } else 672 if(!UniataChipDetectChannels(HwDeviceExtension, pciData, DeviceNumber, ConfigInfo)) { 673 return STATUS_UNSUCCESSFUL; 674 } 675 // UniataAhciDetect() sets proper number of channels 676 if(!UniataAllocateLunExt(deviceExtension, UNIATA_ALLOCATE_NEW_LUNS)) { 677 return STATUS_UNSUCCESSFUL; 678 } 679 680 switch(VendorID) { 681 case ATA_ACER_LABS_ID: 682 if(ChipFlags & UNIATA_SATA) { 683 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator 684 BaseIoAddress1 = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 685 0, 0, 0x10); 686 BaseIoAddress2 = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 687 1, 0, 0x10); 688 BaseIoAddressBM = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 689 4, 0, deviceExtension->NumberChannels*sizeof(IDE_BUSMASTER_REGISTERS)); 690 for(c=0; c<deviceExtension->NumberChannels; c++) { 691 //ULONG unit01 = (c & 1); 692 ULONG unit10 = (c & 2); 693 chan = &deviceExtension->chan[c]; 694 695 for (i=0; i<=IDX_IO1_SZ; i++) { 696 UniataInitIoRes(chan, IDX_IO1+i, BaseIoAddress1 + i + (unit10 ? 8 : 0), FALSE, FALSE); 697 } 698 UniataInitIoRes(chan, IDX_IO2_AltStatus, BaseIoAddress2 + 2 + (unit10 ? 4 : 0), FALSE, FALSE); 699 UniataInitSyncBaseIO(chan); 700 701 for (i=0; i<=IDX_BM_IO_SZ; i++) { 702 UniataInitIoRes(chan, IDX_BM_IO+i, BaseIoAddressBM + i + (c * sizeof(IDE_BUSMASTER_REGISTERS)), FALSE, FALSE); 703 } 704 705 // SATA not supported yet 706 707 //chan->RegTranslation[IDX_BM_Command] = BaseMemAddress + 0x260 + offs7; 708 //chan->RegTranslation[IDX_BM_PRD_Table] = BaseMemAddress + 0x244 + offs7; 709 //chan->RegTranslation[IDX_BM_DeviceSpecific0] = BaseMemAddress + (c << 2); 710 711 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 712 } 713 } 714 break; 715 case ATA_NVIDIA_ID: 716 if(ChipFlags & UNIATA_SATA) { 717 KdPrint2((PRINT_PREFIX "NVIDIA SATA\n")); 718 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 719 5, 0, ((ChipFlags & NV4OFF) ? 0x400 : 0) + 0x40*2); 720 KdPrint2((PRINT_PREFIX "BaseMemAddress %x\n", BaseMemAddress)); 721 if(!BaseMemAddress) { 722 return STATUS_UNSUCCESSFUL; 723 } 724 if((*ConfigInfo->AccessRanges)[5].RangeInMemory) { 725 KdPrint2((PRINT_PREFIX "MemIo\n")); 726 MemIo = TRUE; 727 } 728 UniataInitIoResEx(&deviceExtension->BaseIoAddressSATA_0, BaseMemAddress, MemIo, FALSE); 729 for(c=0; c<deviceExtension->NumberChannels; c++) { 730 chan = &deviceExtension->chan[c]; 731 732 UniataInitIoRes(chan, IDX_SATA_SStatus, BaseMemAddress + (c << 6), MemIo, FALSE); 733 UniataInitIoRes(chan, IDX_SATA_SError, BaseMemAddress + 4 + (c << 6), MemIo, FALSE); 734 UniataInitIoRes(chan, IDX_SATA_SControl, BaseMemAddress + 8 + (c << 6), MemIo, FALSE); 735 736 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 737 } 738 } 739 break; 740 case ATA_PROMISE_ID: 741 742 if(ChipType != PRMIO) { 743 break; 744 } 745 if(!pciData) { 746 break; 747 } 748 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator 749 750 /* BAR4 -> res1 */ 751 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 752 4, 0, 0x4000); 753 KdPrint2((PRINT_PREFIX "BaseMemAddress[4] %x\n", BaseMemAddress)); 754 if(!BaseMemAddress) { 755 return STATUS_UNSUCCESSFUL; 756 } 757 if((*ConfigInfo->AccessRanges)[4].RangeInMemory) { 758 KdPrint2((PRINT_PREFIX "MemIo\n")); 759 MemIo = TRUE; 760 } 761 UniataInitIoResEx(&deviceExtension->BaseIoAddressSATA_0, BaseMemAddress, MemIo, FALSE); 762 763 /* BAR3 -> res2 */ 764 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 765 3, 0, 0xd0000); 766 KdPrint2((PRINT_PREFIX "BaseMemAddress[3] %x\n", BaseMemAddress)); 767 if(!BaseMemAddress) { 768 return STATUS_UNSUCCESSFUL; 769 } 770 if((*ConfigInfo->AccessRanges)[3].RangeInMemory) { 771 KdPrint2((PRINT_PREFIX "MemIo\n")); 772 MemIo = TRUE; 773 } 774 UniataInitIoResEx(&deviceExtension->BaseIoAddressBM_0, BaseMemAddress, MemIo, FALSE); 775 776 if(!(ChipFlags & UNIATA_SATA)) { 777 UCHAR reg48; 778 779 reg48 = AtapiReadPortEx1(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),0x48); 780 deviceExtension->NumberChannels = ((reg48 & 0x01) ? 1 : 0) + 781 ((reg48 & 0x02) ? 1 : 0) + 782 2; 783 KdPrint2((PRINT_PREFIX "Channels -> %d\n", deviceExtension->NumberChannels)); 784 } 785 786 for(c=0; c<deviceExtension->NumberChannels; c++) { 787 788 /* res2-based */ 789 ULONG offs8, offs7; 790 791 chan = &deviceExtension->chan[c]; 792 793 offs8 = c << 8; 794 offs7 = c << 7; 795 796 for (i=0; i<=IDX_IO1_SZ; i++) { 797 UniataInitIoRes(chan, IDX_IO1+i, BaseMemAddress + 0x200 + (i << 2) + offs8, MemIo, FALSE); 798 } 799 UniataInitIoRes(chan, IDX_IO2_AltStatus, BaseMemAddress + 0x238 + offs7, MemIo, FALSE); 800 801 UniataInitSyncBaseIO(chan); 802 803 UniataInitIoRes(chan, IDX_BM_Command, BaseMemAddress + 0x260 + offs7, MemIo, FALSE); 804 UniataInitIoRes(chan, IDX_BM_PRD_Table, BaseMemAddress + 0x244 + offs7, MemIo, FALSE); 805 UniataInitIoRes(chan, IDX_BM_DeviceSpecific0, BaseMemAddress + (c << 2), MemIo, FALSE); 806 807 if((ChipFlags & PRSATA) || 808 ((ChipFlags & PRCMBO) && c<2)) { 809 KdPrint2((PRINT_PREFIX "Promise SATA\n")); 810 811 UniataInitIoRes(chan, IDX_SATA_SStatus, BaseMemAddress + 0x400 + offs7, MemIo, FALSE); 812 UniataInitIoRes(chan, IDX_SATA_SError, BaseMemAddress + 0x404 + offs7, MemIo, FALSE); 813 UniataInitIoRes(chan, IDX_SATA_SControl, BaseMemAddress + 0x408 + offs7, MemIo, FALSE); 814 815 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 816 } else { 817 KdPrint2((PRINT_PREFIX "Promise PATA\n")); 818 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA6); 819 } 820 } 821 break; 822 823 case ATA_ATI_ID: 824 KdPrint2((PRINT_PREFIX "ATI\n")); 825 if(ChipType == ATI700) { 826 KdPrint2((PRINT_PREFIX "ATI700\n")); 827 if(!(ChipFlags & UNIATA_AHCI)) { 828 KdPrint2((PRINT_PREFIX "IXP700 PATA\n")); 829 chan = &deviceExtension->chan[0]; 830 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA5); 831 } 832 break; 833 } 834 /* FALLTHROUGH */ 835 case ATA_SILICON_IMAGE_ID: { 836 837 if(ChipFlags & SIIBUG) { 838 } 839 if(ChipType != SIIMIO) { 840 break; 841 } 842 if(!pciData) { 843 break; 844 } 845 846 if(VendorID == ATA_SILICON_IMAGE_ID) { 847 KdPrint2((PRINT_PREFIX "New SII\n")); 848 } else { 849 KdPrint2((PRINT_PREFIX "ATI SATA\n")); 850 } 851 //if(deviceExtension->HwFlags & SII4CH) { 852 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator 853 //} 854 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 855 5, 0, 0x800); 856 KdPrint2((PRINT_PREFIX "BaseMemAddress %x\n", BaseMemAddress)); 857 if(!BaseMemAddress) { 858 return STATUS_UNSUCCESSFUL; 859 } 860 if((*ConfigInfo->AccessRanges)[5].RangeInMemory) { 861 KdPrint2((PRINT_PREFIX "MemIo\n")); 862 MemIo = TRUE; 863 } 864 UniataInitIoResEx(&deviceExtension->BaseIoAddressSATA_0, BaseMemAddress, MemIo, FALSE); 865 866 for(c=0; c<deviceExtension->NumberChannels; c++) { 867 ULONG unit01 = (c & 1); 868 ULONG unit10 = (c & 2); 869 870 chan = &deviceExtension->chan[c]; 871 872 if(deviceExtension->AltRegMap) { 873 for (i=0; i<=IDX_IO1_SZ; i++) { 874 UniataInitIoRes(chan, IDX_IO1+i, BaseMemAddress + 0x80 + i + (unit01 << 6) + (unit10 << 8), MemIo, FALSE); 875 } 876 UniataInitIoRes(chan, IDX_IO2_AltStatus, BaseMemAddress + 0x8a + (unit01 << 6) + (unit10 << 8), MemIo, FALSE); 877 UniataInitSyncBaseIO(chan); 878 879 UniataInitIoRes(chan, IDX_BM_Command, BaseMemAddress + 0x00 + (unit01 << 3) + (unit10 << 8), MemIo, FALSE); 880 UniataInitIoRes(chan, IDX_BM_Status, BaseMemAddress + 0x02 + (unit01 << 3) + (unit10 << 8), MemIo, FALSE); 881 UniataInitIoRes(chan, IDX_BM_PRD_Table, BaseMemAddress + 0x04 + (unit01 << 3) + (unit10 << 8), MemIo, FALSE); 882 UniataInitIoRes(chan, IDX_BM_DeviceSpecific0, BaseMemAddress + 0x10 + (unit01 << 3) + (unit10 << 8), MemIo, FALSE); 883 UniataInitIoRes(chan, IDX_BM_DeviceSpecific1, BaseMemAddress + 0x40 + (unit01 << 2) + (unit10 << 8), MemIo, FALSE); 884 } 885 886 if(chan->MaxTransferMode < ATA_SA150) { 887 // do nothing for PATA part 888 KdPrint2((PRINT_PREFIX "No SATA regs for PATA part\n")); 889 } else 890 if(ChipFlags & UNIATA_SATA) { 891 UniataInitIoRes(chan, IDX_SATA_SStatus, BaseMemAddress + 0x104 + (unit01 << 7) + (unit10 << 8), MemIo, FALSE); 892 UniataInitIoRes(chan, IDX_SATA_SError, BaseMemAddress + 0x108 + (unit01 << 2) + (unit10 << 8), MemIo, FALSE); 893 UniataInitIoRes(chan, IDX_SATA_SControl, BaseMemAddress + 0x100 + (unit01 << 2) + (unit10 << 8), MemIo, FALSE); 894 895 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 896 } 897 } 898 break; } 899 900 case ATA_SERVERWORKS_ID: { 901 902 if(ChipType != SWKSMIO) { 903 break; 904 } 905 if(!pciData) { 906 break; 907 } 908 909 KdPrint2((PRINT_PREFIX "ServerWorks\n")); 910 911 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator 912 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 913 5, 0, 0x400); 914 KdPrint2((PRINT_PREFIX "BaseMemAddress %x\n", BaseMemAddress)); 915 if(!BaseMemAddress) { 916 return STATUS_UNSUCCESSFUL; 917 } 918 if((*ConfigInfo->AccessRanges)[5].RangeInMemory) { 919 KdPrint2((PRINT_PREFIX "MemIo\n")); 920 MemIo = TRUE; 921 } 922 UniataInitIoResEx(&deviceExtension->BaseIoAddressSATA_0, BaseMemAddress, MemIo, FALSE); 923 924 for(c=0; c<deviceExtension->NumberChannels; c++) { 925 ULONG offs = c*0x100; 926 927 chan = &deviceExtension->chan[c]; 928 for (i=0; i<=IDX_IO1_SZ; i++) { 929 UniataInitIoRes(chan, IDX_IO1+i, BaseMemAddress + offs + i*4, MemIo, FALSE); 930 } 931 UniataInitIoRes(chan, IDX_IO2_AltStatus, BaseMemAddress + offs + 0x20, MemIo, FALSE); 932 UniataInitSyncBaseIO(chan); 933 934 UniataInitIoRes(chan, IDX_BM_Command, BaseMemAddress + offs + 0x30, MemIo, FALSE); 935 UniataInitIoRes(chan, IDX_BM_Status, BaseMemAddress + offs + 0x32, MemIo, FALSE); 936 UniataInitIoRes(chan, IDX_BM_PRD_Table, BaseMemAddress + offs + 0x34, MemIo, FALSE); 937 938 UniataInitIoRes(chan, IDX_SATA_SStatus, BaseMemAddress + offs + 0x40, MemIo, FALSE); 939 UniataInitIoRes(chan, IDX_SATA_SError, BaseMemAddress + offs + 0x44, MemIo, FALSE); 940 UniataInitIoRes(chan, IDX_SATA_SControl, BaseMemAddress + offs + 0x48, MemIo, FALSE); 941 942 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 943 } 944 break; } 945 946 case ATA_SIS_ID: { 947 //if(ChipType != SIS_SOUTH) {} 948 BOOLEAN SIS_182=FALSE; 949 950 if(!(ChipFlags & SIS_BASE)) { 951 KdPrint2((PRINT_PREFIX "Found SIS_SOUTH\n")); 952 //PrintNtConsole("Found SIS_SOUTH\n"); 953 break; 954 } 955 // Make some additional checks 956 KdPrint2((PRINT_PREFIX "ChipType == SIS_BASE\n")); 957 ChangePciConfig1(0x57, (a & 0x7f)); 958 GetPciConfig4(0x00, tmp32); 959 if(tmp32 == ATA_SIS5518) { 960 ChipType = SIS133NEW; 961 deviceExtension->HwFlags = (deviceExtension->HwFlags & ~CHIPTYPE_MASK) | SIS133NEW; 962 deviceExtension->MaxTransferMode = ATA_UDMA6; 963 KdPrint2((PRINT_PREFIX "UniataChipDetect: SiS 962/963 DMA %#x controller\n", deviceExtension->MaxTransferMode)); 964 //PrintNtConsole("UniataChipDetect: SiS 962/963 DMA %#x controller\n", deviceExtension->MaxTransferMode); 965 // Restore device ID 966 ChangePciConfig1(0x57, (a | 0x80)); 967 } else { 968 static BUSMASTER_CONTROLLER_INFORMATION_BASE const SiSSouthAdapters[] = { 969 PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x10, ATA_MODE_NOT_SPEC, "SiS 961", 0 ), 970 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x00, ATA_MODE_NOT_SPEC, "SiS 961", 0 ), 971 PCI_DEV_HW_SPEC_BM( ffff, ffff, 0xff, ATA_MODE_NOT_SPEC, NULL , -1 ) 972 }; 973 // Save settings 974 GetPciConfig1(0x4a, tmp8); 975 ChangePciConfig1(0x4a, (a | 0x10)); 976 if(tmp32 == ATA_SIS5513 || 977 tmp32 == ATA_SIS5517) { 978 i = AtapiFindListedDev((BUSMASTER_CONTROLLER_INFORMATION_BASE*)&SiSSouthAdapters[0], 979 -1, HwDeviceExtension, SystemIoBusNumber, PCISLOTNUM_NOT_SPECIFIED, NULL); 980 if(i != BMLIST_TERMINATOR) { 981 KdPrint2((PRINT_PREFIX "SIS South\n")); 982 deviceExtension->HwFlags = (deviceExtension->HwFlags & ~CHIPTYPE_MASK) | SIS133OLD; 983 deviceExtension->MaxTransferMode = ATA_UDMA6; 984 //deviceExtension->MaxTransferMode = SiSSouthAdapters[i].MaxTransferMode; 985 if(SiSSouthAdapters[i].RaidFlags & UNIATA_SATA) { 986 KdPrint2((PRINT_PREFIX "SIS South SATA\n")); 987 deviceExtension->HwFlags |= UNIATA_SATA; 988 if(SiSSouthAdapters[i].nDeviceId == 0x1182 || 989 SiSSouthAdapters[i].nDeviceId == 0x1183) { 990 KdPrint2((PRINT_PREFIX "SIS_182\n")); 991 SIS_182 = TRUE; 992 } 993 } 994 } else { 995 // SiS-South not found 996 if(tmp32 == ATA_SIS5517) { 997 deviceExtension->HwFlags = (deviceExtension->HwFlags & ~CHIPTYPE_MASK) | SIS100NEW; 998 deviceExtension->MaxTransferMode = ATA_UDMA5; 999 } else { 1000 // generic SiS33 1001 KdPrint2((PRINT_PREFIX "Generic SiS DMA\n")); 1002 } 1003 } 1004 } 1005 // Restore settings 1006 SetPciConfig1(0x4a, tmp8); 1007 KdPrint2((PRINT_PREFIX "UniataChipDetect: SiS 961 DMA %#x controller\n", deviceExtension->MaxTransferMode)); 1008 //PrintNtConsole("UniataChipDetect: SiS 961 DMA %#x controller\n", deviceExtension->MaxTransferMode); 1009 if(deviceExtension->HwFlags & UNIATA_SATA) { 1010 KdPrint2((PRINT_PREFIX "SiS SATA\n")); 1011 1012 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 1013 5, 0, 0x400); 1014 KdPrint2((PRINT_PREFIX "BaseMemAddress %x\n", BaseMemAddress)); 1015 if(BaseMemAddress) { 1016 if((*ConfigInfo->AccessRanges)[5].RangeInMemory) { 1017 KdPrint2((PRINT_PREFIX "MemIo\n")); 1018 MemIo = TRUE; 1019 } 1020 UniataInitIoResEx(&deviceExtension->BaseIoAddressSATA_0, BaseMemAddress, MemIo, FALSE); 1021 1022 for(c=0; c<deviceExtension->NumberChannels; c++) { 1023 ULONG offs = c << (SIS_182 ? 5 : 6); 1024 1025 chan = &deviceExtension->chan[c]; 1026 UniataInitIoRes(chan, IDX_SATA_SStatus, BaseMemAddress + 0 + offs, MemIo, FALSE); 1027 UniataInitIoRes(chan, IDX_SATA_SError, BaseMemAddress + 4 + offs, MemIo, FALSE); 1028 UniataInitIoRes(chan, IDX_SATA_SControl, BaseMemAddress + 8 + offs, MemIo, FALSE); 1029 1030 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 1031 } 1032 } 1033 } 1034 } 1035 //ChangePciConfig1(0x57, (a | 0x80)); 1036 break; } 1037 1038 case ATA_VIA_ID: { 1039 1040 if(ChipFlags & VIASATA) { 1041 /* 2 SATA without SATA registers on first channel + 1 PATA on second */ 1042 // do nothing, generic PATA INIT 1043 KdPrint2((PRINT_PREFIX "VIA SATA without SATA regs\n")); 1044 break; 1045 } 1046 if(ChipFlags & UNIATA_SATA) { 1047 1048 ULONG IoSize = 0; 1049 BaseMemAddress = 0; 1050 1051 switch(DeviceID) { 1052 case 0x3149: // VIA 6420 1053 KdPrint2((PRINT_PREFIX "VIA 6420\n")); 1054 IoSize = 0x80; 1055 break; 1056 case 0x3249: // VIA 6421 1057 KdPrint2((PRINT_PREFIX "VIA 6421\n")); 1058 IoSize = 0x40; 1059 break; 1060 } 1061 if(IoSize) { 1062 KdPrint2((PRINT_PREFIX "IoSize %x\n", IoSize)); 1063 /*deviceExtension->*/BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 1064 5, 0, IoSize * deviceExtension->NumberChannels); 1065 if(BaseMemAddress && (*ConfigInfo->AccessRanges)[5].RangeInMemory) { 1066 KdPrint2((PRINT_PREFIX "MemIo\n")); 1067 MemIo = TRUE; 1068 } 1069 UniataInitIoResEx(&deviceExtension->BaseIoAddressSATA_0, BaseMemAddress, MemIo, FALSE); 1070 } 1071 if(/*deviceExtension->*/BaseMemAddress) { 1072 KdPrint2((PRINT_PREFIX "UniataChipDetect: BAR5 %x\n", /*deviceExtension->*/BaseMemAddress)); 1073 if(ChipFlags & VIABAR) { 1074 1075 ULONG BaseIoAddressBM_0; 1076 ULONG BaseIo; 1077 1078 KdPrint2((PRINT_PREFIX "UniataChipDetect: VIABAR\n")); 1079 /*deviceExtension->*/BaseIoAddressBM_0 = /*(PIDE_BUSMASTER_REGISTERS)*/ 1080 AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 4, 0, 1081 sizeof(IDE_BUSMASTER_REGISTERS)*deviceExtension->NumberChannels); 1082 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator 1083 for(c=0; c<deviceExtension->NumberChannels; c++) { 1084 1085 chan = &deviceExtension->chan[c]; 1086 1087 BaseIo = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, c, 0, /*0x80*/ sizeof(IDE_REGISTERS_1) + sizeof(IDE_REGISTERS_2)*2); 1088 1089 for (i=0; i<=IDX_IO1_SZ; i++) { 1090 UniataInitIoRes(chan, IDX_IO1+i, BaseIo + i, FALSE, FALSE); 1091 } 1092 UniataInitIoRes(chan, IDX_IO2_AltStatus, BaseIo + sizeof(IDE_REGISTERS_1) + 2, FALSE, FALSE); 1093 UniataInitSyncBaseIO(chan); 1094 1095 for (i=0; i<=IDX_BM_IO_SZ; i++) { 1096 UniataInitIoRes(chan, IDX_BM_IO+i, BaseIoAddressBM_0 + sizeof(IDE_BUSMASTER_REGISTERS)*c + i, FALSE, FALSE); 1097 } 1098 1099 } 1100 } 1101 for(c=0; c<deviceExtension->NumberChannels; c++) { 1102 chan = &deviceExtension->chan[c]; 1103 if((ChipFlags & VIABAR) && (c==2)) { 1104 // Do not setup SATA registers for PATA part 1105 for (i=0; i<=IDX_SATA_IO_SZ; i++) { 1106 UniataInitIoRes(chan, IDX_SATA_IO+i, 0, FALSE, FALSE); 1107 } 1108 break; 1109 } 1110 UniataInitIoRes(chan, IDX_SATA_SStatus, BaseMemAddress + (c * IoSize), MemIo, FALSE); 1111 UniataInitIoRes(chan, IDX_SATA_SError, BaseMemAddress + 4 + (c * IoSize), MemIo, FALSE); 1112 UniataInitIoRes(chan, IDX_SATA_SControl, BaseMemAddress + 8 + (c * IoSize), MemIo, FALSE); 1113 1114 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 1115 } 1116 1117 } 1118 } 1119 break; } 1120 case ATA_INTEL_ID: { 1121 1122 if(!(ChipFlags & UNIATA_SATA)) { 1123 break; 1124 } 1125 1126 /* the intel 31244 needs special care if in DPA mode */ 1127 if(DeviceID == 3200 && // Intel 31244 1128 pciData->SubClass != PCI_DEV_SUBCLASS_IDE) { 1129 1130 KdPrint2((PRINT_PREFIX "UniataChipDetect: Intel 31244, DPA mode\n")); 1131 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 1132 0, 0, 0x0c00); 1133 if(!BaseMemAddress) { 1134 return STATUS_UNSUCCESSFUL; 1135 } 1136 if((*ConfigInfo->AccessRanges)[0].RangeInMemory) { 1137 KdPrint2((PRINT_PREFIX "MemIo\n")); 1138 MemIo = TRUE; 1139 } 1140 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator 1141 UniataInitIoResEx(&deviceExtension->BaseIoAddressSATA_0, BaseMemAddress, MemIo, FALSE); 1142 1143 for(c=0; c<deviceExtension->NumberChannels; c++) { 1144 ULONG offs = 0x200 + c*0x200; 1145 1146 chan = &deviceExtension->chan[c]; 1147 for (i=0; i<=IDX_IO1_SZ; i++) { 1148 UniataInitIoRes(chan, IDX_BM_IO+i, BaseMemAddress + i*4 + offs, MemIo, FALSE); 1149 } 1150 1151 UniataInitSyncBaseIO(chan); 1152 1153 UniataInitIoRes(chan, IDX_IO1_o_Command, BaseMemAddress + 0x1d + offs, MemIo, FALSE); 1154 UniataInitIoRes(chan, IDX_IO1_o_Feature, BaseMemAddress + 0x06 + offs, MemIo, FALSE); 1155 UniataInitIoRes(chan, IDX_IO2_o_Control, BaseMemAddress + 0x29 + offs, MemIo, FALSE); 1156 1157 UniataInitIoRes(chan, IDX_IO2_AltStatus, BaseMemAddress + 0x28 + offs, MemIo, FALSE); 1158 1159 UniataInitIoRes(chan, IDX_BM_Command, BaseMemAddress + 0x70 + offs, MemIo, FALSE); 1160 UniataInitIoRes(chan, IDX_BM_Status, BaseMemAddress + 0x72 + offs, MemIo, FALSE); 1161 UniataInitIoRes(chan, IDX_BM_PRD_Table, BaseMemAddress + 0x74 + offs, MemIo, FALSE); 1162 1163 UniataInitIoRes(chan, IDX_SATA_SStatus, BaseMemAddress + 0x100 + offs, MemIo, FALSE); 1164 UniataInitIoRes(chan, IDX_SATA_SError, BaseMemAddress + 0x104 + offs, MemIo, FALSE); 1165 UniataInitIoRes(chan, IDX_SATA_SControl, BaseMemAddress + 0x108 + offs, MemIo, FALSE); 1166 1167 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 1168 } 1169 1170 break; 1171 } 1172 if(deviceExtension->MaxTransferMode >= ATA_SA150) { 1173 1174 BOOLEAN OrigAHCI = FALSE; 1175 1176 GetPciConfig1(0x90, tmp8); 1177 KdPrint2((PRINT_PREFIX "Intel chip config: %x\n", tmp8)); 1178 /* SATA parts can be either compat or AHCI */ 1179 MemIo = FALSE; 1180 if(ChipFlags & UNIATA_AHCI) { 1181 OrigAHCI = TRUE; 1182 if(tmp8 & 0xc0) { 1183 //KdPrint2((PRINT_PREFIX "AHCI not supported yet\n")); 1184 //return FALSE; 1185 KdPrint2((PRINT_PREFIX "try run AHCI\n")); 1186 if(ScsiPortConvertPhysicalAddressToUlong((*ConfigInfo->AccessRanges)[5].RangeStart)) { 1187 break; 1188 } 1189 KdPrint2((PRINT_PREFIX "No BAR5, try BM\n")); 1190 deviceExtension->HwFlags &= ~UNIATA_AHCI; 1191 } 1192 BaseIoAddressBM = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 1193 4, 0, sizeof(IDE_BUSMASTER_REGISTERS)); 1194 if(BaseIoAddressBM) { 1195 KdPrint2((PRINT_PREFIX "Intel BM check at %x\n", BaseIoAddressBM)); 1196 /* check if we really have valid BM registers */ 1197 if((*ConfigInfo->AccessRanges)[4].RangeInMemory) { 1198 KdPrint2((PRINT_PREFIX "MemIo[4]\n")); 1199 MemIo = TRUE; 1200 } 1201 UniataInitIoResEx(&deviceExtension->BaseIoAddressBM_0, BaseIoAddressBM, MemIo, FALSE); 1202 1203 tmp8 = AtapiReadPortEx1(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressBM_0),IDX_BM_Status); 1204 KdPrint2((PRINT_PREFIX "BM status: %x\n", tmp8)); 1205 /* cleanup */ 1206 ScsiPortFreeDeviceBase(HwDeviceExtension, (PCHAR)BaseIoAddressBM); 1207 UniataInitIoResEx(&deviceExtension->BaseIoAddressBM_0, 0, 0, FALSE); 1208 1209 if(tmp8 == 0xff) { 1210 KdPrint2((PRINT_PREFIX "invalid BM status, keep AHCI mode\n")); 1211 break; 1212 } 1213 } 1214 KdPrint2((PRINT_PREFIX "Compatible mode, reallocate LUNs\n")); 1215 deviceExtension->NumberLuns = 2; // we may be in Legacy mode 1216 if(!UniataAllocateLunExt(deviceExtension, 2)) { 1217 KdPrint2((PRINT_PREFIX "can't re-allocate Luns\n")); 1218 return STATUS_UNSUCCESSFUL; 1219 } 1220 } 1221 deviceExtension->HwFlags &= ~UNIATA_AHCI; 1222 1223 MemIo = FALSE; 1224 /* if BAR(5) is IO it should point to SATA interface registers */ 1225 if(OrigAHCI) { 1226 /* Skip BAR(5) in compatible mode */ 1227 KdPrint2((PRINT_PREFIX "Ignore BAR5 on compatible\n")); 1228 BaseMemAddress = 0; 1229 } else 1230 if(deviceExtension->DevID == 0x28288086 && 1231 pciData->u.type0.SubVendorID == 0x106b) { 1232 /* Skip BAR(5) on ICH8M Apples, system locks up on access. */ 1233 KdPrint2((PRINT_PREFIX "Ignore BAR5 on ICH8M Apples\n")); 1234 BaseMemAddress = 0; 1235 } else { 1236 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 1237 5, 0, 0x10); 1238 if(BaseMemAddress && (*ConfigInfo->AccessRanges)[5].RangeInMemory) { 1239 KdPrint2((PRINT_PREFIX "MemIo[5]\n")); 1240 MemIo = TRUE; 1241 } 1242 } 1243 UniataInitIoResEx(&deviceExtension->BaseIoAddressSATA_0, BaseMemAddress, MemIo, FALSE); 1244 1245 for(c=0; c<deviceExtension->NumberChannels; c++) { 1246 chan = &deviceExtension->chan[c]; 1247 IsPata = FALSE; 1248 if(ChipFlags & ICH5) { 1249 KdPrint2((PRINT_PREFIX "ICH5\n")); 1250 if ((tmp8 & 0x04) == 0) { 1251 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 1252 } else if ((tmp8 & 0x02) == 0) { 1253 if(c != 0) { 1254 IsPata = TRUE; 1255 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA; 1256 } 1257 } else if ((tmp8 & 0x02) != 0) { 1258 if(c != 1) { 1259 IsPata = TRUE; 1260 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA; 1261 } 1262 } 1263 } else 1264 if(ChipFlags & I6CH2) { 1265 KdPrint2((PRINT_PREFIX "I6CH2\n")); 1266 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 1267 } else { 1268 KdPrint2((PRINT_PREFIX "other Intel\n")); 1269 switch(tmp8 & 0x03) { 1270 case 2: 1271 if(c!=0) { 1272 // PATA 1273 IsPata = TRUE; 1274 } 1275 break; 1276 case 1: 1277 if(c!=1) { 1278 // PATA 1279 IsPata = TRUE; 1280 } 1281 break; 1282 } 1283 } 1284 1285 if(IsPata) { 1286 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA5); 1287 KdPrint2((PRINT_PREFIX "PATA part\n")); 1288 } else { 1289 1290 if(!(ChipFlags & ICH7) && BaseMemAddress) { 1291 KdPrint2((PRINT_PREFIX "BaseMemAddress[5] -> indexed\n")); 1292 UniataInitIoRes(chan, IDX_INDEXED_ADDR, BaseMemAddress + 0, MemIo, FALSE); 1293 UniataInitIoRes(chan, IDX_INDEXED_DATA, BaseMemAddress + 4, MemIo, FALSE); 1294 } 1295 if((ChipFlags & ICH5) || BaseMemAddress) { 1296 1297 KdPrint2((PRINT_PREFIX "io proc()\n")); 1298 // Rather interesting way of register access... 1299 ChipType = INTEL_IDX; 1300 deviceExtension->HwFlags &= ~CHIPTYPE_MASK; 1301 deviceExtension->HwFlags |= ChipType; 1302 1303 if(ChipFlags & ICH7) { 1304 KdPrint2((PRINT_PREFIX "ICH7 way\n")); 1305 } 1306 UniataInitIoRes(chan, IDX_SATA_SStatus, 0x200*c + 0, FALSE, TRUE); // this is fake non-zero value 1307 UniataInitIoRes(chan, IDX_SATA_SError, 0x200*c + 2, FALSE, TRUE); 1308 UniataInitIoRes(chan, IDX_SATA_SControl, 0x200*c + 1, FALSE, TRUE); 1309 } 1310 } 1311 1312 } // end for() 1313 1314 // rest of INIT staff is in AtapiChipInit() 1315 1316 } // ATA_SA150 1317 break; } 1318 case ATA_CYRIX_ID: 1319 /* Cyrix 5530 ATA33 controller */ 1320 if(deviceExtension->DevID == 0x01021078) { 1321 ConfigInfo->AlignmentMask = 0x0f; 1322 deviceExtension->MaximumDmaTransferLength = 63*1024; 1323 } 1324 break; 1325 case ATA_JMICRON_ID: 1326 /* New JMicron PATA controllers */ 1327 GetPciConfig1(0xdf, tmp8); 1328 if(tmp8 & 0x40) { 1329 KdPrint((" Check JMicron AHCI\n")); 1330 if(Ata_is_ahci_dev(pciData)) { 1331 ChipFlags |= UNIATA_AHCI; 1332 deviceExtension->HwFlags |= UNIATA_AHCI; 1333 } else { 1334 KdPrint((" JMicron PATA\n")); 1335 } 1336 } else { 1337 /* set controller configuration to a combined setup we support */ 1338 SetPciConfig4(0x40, 0x80c0a131); 1339 SetPciConfig4(0x80, 0x01200000); 1340 //KdPrint((" JMicron Combined (not supported yet)\n")); 1341 //return STATUS_NOT_FOUND; 1342 } 1343 break; 1344 } 1345 1346 return STATUS_SUCCESS; 1347 1348 } // end UniataChipDetect() 1349 1350 1351 /* 1352 Do some 'magic staff' for VIA SouthBridge 1353 This will prevent data losses 1354 */ 1355 VOID 1356 NTAPI 1357 AtapiViaSouthBridgeFixup( 1358 IN PVOID HwDeviceExtension, 1359 IN BUS_DATA_TYPE BusDataType, 1360 IN ULONG SystemIoBusNumber, 1361 IN ULONG slotNumber 1362 ) 1363 { 1364 PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension; 1365 PCI_COMMON_CONFIG pciData; 1366 ULONG funcNumber; 1367 ULONG busDataRead; 1368 1369 ULONG VendorID; 1370 ULONG DeviceID; 1371 PCI_SLOT_NUMBER slotData; 1372 ULONG dev_id; 1373 BOOLEAN found = FALSE; 1374 1375 slotData.u.AsULONG = slotNumber; 1376 for(funcNumber = 0; funcNumber < PCI_MAX_FUNCTION; funcNumber++) { 1377 1378 slotData.u.bits.FunctionNumber = funcNumber; 1379 1380 busDataRead = ScsiPortGetBusData(HwDeviceExtension, 1381 PCIConfiguration, 1382 SystemIoBusNumber, 1383 slotData.u.AsULONG, 1384 &pciData, 1385 PCI_COMMON_HDR_LENGTH); 1386 1387 if (busDataRead < (ULONG)PCI_COMMON_HDR_LENGTH) { 1388 continue; 1389 } 1390 1391 VendorID = pciData.VendorID; 1392 DeviceID = pciData.DeviceID; 1393 dev_id = (VendorID | (DeviceID << 16)); 1394 1395 if (dev_id == 0x03051106 || /* VIA VT8363 */ 1396 dev_id == 0x03911106 || /* VIA VT8371 */ 1397 dev_id == 0x31021106 || /* VIA VT8662 */ 1398 dev_id == 0x31121106) { /* VIA VT8361 */ 1399 UCHAR reg76; 1400 1401 GetPciConfig1(0x76, reg76); 1402 1403 if ((reg76 & 0xf0) != 0xd0) { 1404 SetPciConfig1(0x75, 0x80); 1405 SetPciConfig1(0x76, (reg76 & 0x0f) | 0xd0); 1406 } 1407 found = TRUE; 1408 break; 1409 } 1410 } 1411 if(!found) { 1412 deviceExtension->HwFlags &= ~VIABUG; 1413 } 1414 } // end AtapiViaSouthBridgeFixup() 1415 1416 /* 1417 Do some 'magic staff' for ROSB SouthBridge 1418 This will prevent data losses 1419 */ 1420 VOID 1421 NTAPI 1422 AtapiRosbSouthBridgeFixup( 1423 IN PVOID HwDeviceExtension, 1424 IN BUS_DATA_TYPE BusDataType, 1425 IN ULONG SystemIoBusNumber, 1426 IN ULONG slotNumber 1427 ) 1428 { 1429 //PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension; 1430 PCI_COMMON_CONFIG pciData; 1431 ULONG funcNumber; 1432 ULONG busDataRead; 1433 1434 ULONG VendorID; 1435 ULONG DeviceID; 1436 PCI_SLOT_NUMBER slotData; 1437 ULONG dev_id; 1438 // BOOLEAN found = FALSE; 1439 1440 /* locate the ISA part in the southbridge and enable UDMA33 */ 1441 slotData.u.AsULONG = slotNumber; 1442 for(funcNumber = 0; funcNumber < PCI_MAX_FUNCTION; funcNumber++) { 1443 1444 slotData.u.bits.FunctionNumber = funcNumber; 1445 1446 busDataRead = ScsiPortGetBusData(HwDeviceExtension, 1447 PCIConfiguration, 1448 SystemIoBusNumber, 1449 slotData.u.AsULONG, 1450 &pciData, 1451 PCI_COMMON_HDR_LENGTH); 1452 1453 if (busDataRead < (ULONG)PCI_COMMON_HDR_LENGTH) { 1454 continue; 1455 } 1456 1457 VendorID = pciData.VendorID; 1458 DeviceID = pciData.DeviceID; 1459 dev_id = (VendorID | (DeviceID << 16)); 1460 1461 if (dev_id == ATA_ROSB4_ISA) { /* */ 1462 ChangePciConfig4(0x64, ((a & ~0x00002000) | 0x00004000)); 1463 break; 1464 } 1465 } 1466 } // end AtapiRosbSouthBridgeFixup() 1467 1468 /* 1469 Do some 'magic staff' for ROSB SouthBridge 1470 This will prevent data losses 1471 */ 1472 VOID 1473 NTAPI 1474 AtapiAliSouthBridgeFixup( 1475 IN PVOID HwDeviceExtension, 1476 IN BUS_DATA_TYPE BusDataType, 1477 IN ULONG SystemIoBusNumber, 1478 IN ULONG slotNumber, 1479 IN ULONG c 1480 ) 1481 { 1482 //PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension; 1483 PCI_COMMON_CONFIG pciData; 1484 ULONG funcNumber; 1485 ULONG busDataRead; 1486 1487 ULONG VendorID; 1488 ULONG DeviceID; 1489 PCI_SLOT_NUMBER slotData; 1490 ULONG dev_id; 1491 // BOOLEAN found = FALSE; 1492 1493 /* workaround for datacorruption bug found on at least SUN Blade-100 1494 * find the ISA function on the southbridge and disable then enable 1495 * the ATA channel tristate buffer */ 1496 slotData.u.AsULONG = slotNumber; 1497 for(funcNumber = 0; funcNumber < PCI_MAX_FUNCTION; funcNumber++) { 1498 1499 slotData.u.bits.FunctionNumber = funcNumber; 1500 1501 busDataRead = ScsiPortGetBusData(HwDeviceExtension, 1502 PCIConfiguration, 1503 SystemIoBusNumber, 1504 slotData.u.AsULONG, 1505 &pciData, 1506 PCI_COMMON_HDR_LENGTH); 1507 1508 if (busDataRead < (ULONG)PCI_COMMON_HDR_LENGTH) { 1509 continue; 1510 } 1511 1512 VendorID = pciData.VendorID; 1513 DeviceID = pciData.DeviceID; 1514 dev_id = (VendorID | (DeviceID << 16)); 1515 1516 if (dev_id == ATA_ALI_1533) { /* SOUTH */ 1517 ChangePciConfig1(0x58, (a & ~(0x04 << c))); 1518 ChangePciConfig1(0x58, (a | (0x04 << c))); 1519 break; 1520 } 1521 } 1522 } // end AtapiRosbSouthBridgeFixup() 1523 1524 ULONG 1525 NTAPI 1526 hpt_cable80( 1527 IN PHW_DEVICE_EXTENSION deviceExtension, 1528 IN ULONG channel // physical channel number (0-1) 1529 ) 1530 { 1531 PVOID HwDeviceExtension = (PVOID)deviceExtension; 1532 ULONG slotNumber = deviceExtension->slotNumber; 1533 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber; 1534 1535 ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK; 1536 1537 UCHAR reg, val, res; 1538 PCI_SLOT_NUMBER slotData; 1539 1540 PHW_CHANNEL chan; 1541 ULONG c; // logical channel (for Compatible Mode controllers) 1542 1543 c = channel - deviceExtension->Channel; // logical channel (for Compatible Mode controllers) 1544 chan = &deviceExtension->chan[c]; 1545 1546 slotData.u.AsULONG = deviceExtension->slotNumber; 1547 1548 if(deviceExtension->HwFlags & UNIATA_NO80CHK) { 1549 KdPrint2((PRINT_PREFIX "UNIATA_NO80CHK\n")); 1550 return TRUE; 1551 } 1552 1553 if(ChipType == HPT374 && slotData.u.bits.FunctionNumber == 1) { 1554 reg = channel ? 0x57 : 0x53; 1555 GetPciConfig1(reg, val); 1556 SetPciConfig1(reg, val | 0x80); 1557 } 1558 else { 1559 reg = 0x5b; 1560 GetPciConfig1(reg, val); 1561 SetPciConfig1(reg, val & 0xfe); 1562 } 1563 GetPciConfig1(0x5a, res); 1564 res = res & (channel ? 0x01 : 0x02); 1565 SetPciConfig1(reg, val); 1566 if(chan->Force80pin) { 1567 KdPrint2((PRINT_PREFIX "Force80pin\n")); 1568 res = 0; 1569 } 1570 KdPrint2((PRINT_PREFIX "hpt_cable80(%d) = %d\n", channel, !res)); 1571 return !res; 1572 } // end hpt_cable80() 1573 1574 /* 1575 ULONG 1576 NTAPI 1577 via_cable80( 1578 IN PHW_DEVICE_EXTENSION deviceExtension, 1579 IN ULONG channel // physical channel number (0-1) 1580 ) 1581 { 1582 PVOID HwDeviceExtension = (PVOID)deviceExtension; 1583 ULONG slotNumber = deviceExtension->slotNumber; 1584 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber; 1585 1586 ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK; 1587 1588 ULONG reg50; 1589 ULONG a; 1590 ULONG i, j; 1591 BOOLEAN res; 1592 1593 GetPciConfig1(0x50, reg50); 1594 1595 switch(ChipType) { 1596 case VIA133: 1597 a = 8; 1598 break; 1599 case VIA100: 1600 a = 4; 1601 break; 1602 case VIA66: 1603 a = 2; 1604 break; 1605 default: 1606 return false; 1607 } 1608 1609 res = FALSE; 1610 for (j=0; j>=2; i -= 8) { 1611 i = (3-(channel*2+j))*8; 1612 if (((reg50 >> (i & 0x10)) & 8) && 1613 ((reg50 >> i) & 0x20) && 1614 (((reg50 >> i) & 7) < a)) { 1615 1616 res |= TRUE; //(1 << (1 - (i >> 4))); 1617 } 1618 } 1619 KdPrint2((PRINT_PREFIX "via_cable80(%d) = %d\n", channel, res)); 1620 return res; 1621 1622 } // end via_cable80() 1623 */ 1624 1625 BOOLEAN 1626 NTAPI 1627 generic_cable80( 1628 IN PHW_DEVICE_EXTENSION deviceExtension, 1629 IN ULONG channel, // physical channel number (0-1) 1630 IN ULONG pci_reg, 1631 IN ULONG bit_offs 1632 ) 1633 { 1634 PVOID HwDeviceExtension = (PVOID)deviceExtension; 1635 ULONG slotNumber = deviceExtension->slotNumber; 1636 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber; 1637 1638 if(deviceExtension->MaxTransferMode <= ATA_UDMA2) { 1639 KdPrint2((PRINT_PREFIX "generic_cable80(%d, %#x, %d) <= UDMA2\n", channel, pci_reg, bit_offs)); 1640 return FALSE; 1641 } 1642 1643 //ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK; 1644 PHW_CHANNEL chan; 1645 ULONG c; // logical channel (for Compatible Mode controllers) 1646 UCHAR tmp8; 1647 1648 c = channel - deviceExtension->Channel; // logical channel (for Compatible Mode controllers) 1649 chan = &deviceExtension->chan[c]; 1650 1651 if(chan->Force80pin) { 1652 KdPrint2((PRINT_PREFIX "Force80pin\n")); 1653 return TRUE; 1654 } 1655 1656 GetPciConfig1(pci_reg, tmp8); 1657 if(!(tmp8 & (1 << (channel << bit_offs)))) { 1658 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 1659 KdPrint2((PRINT_PREFIX "generic_cable80(%d, %#x, %d) = 0\n", channel, pci_reg, bit_offs)); 1660 return FALSE; 1661 } 1662 1663 KdPrint2((PRINT_PREFIX "generic_cable80(%d, %#x, %d) = 1\n", channel, pci_reg, bit_offs)); 1664 return TRUE; 1665 } // end generic_cable80() 1666 1667 VOID 1668 NTAPI 1669 UniAtaReadLunConfig( 1670 IN PHW_DEVICE_EXTENSION deviceExtension, 1671 IN ULONG channel, // physical channel 1672 IN ULONG DeviceNumber 1673 ) 1674 { 1675 ULONG tmp32; 1676 PHW_CHANNEL chan; 1677 PHW_LU_EXTENSION LunExt; 1678 ULONG c; 1679 1680 c = channel - deviceExtension->Channel; // logical channel 1681 1682 chan = &deviceExtension->chan[c]; 1683 DeviceNumber = (DeviceNumber % deviceExtension->NumberLuns); 1684 LunExt = chan->lun[DeviceNumber]; 1685 1686 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"ReadCacheEnable", 1); 1687 LunExt->opt_ReadCacheEnable = tmp32 ? TRUE : FALSE; 1688 1689 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"WriteCacheEnable", 1); 1690 LunExt->opt_WriteCacheEnable = tmp32 ? TRUE : FALSE; 1691 1692 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"MaxTransferMode", chan->MaxTransferMode); 1693 LunExt->opt_MaxTransferMode = tmp32; 1694 1695 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"PreferedTransferMode", 0xffffffff); 1696 LunExt->opt_PreferedTransferMode = tmp32; 1697 1698 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"AdvancedPowerMode", ATA_C_F_APM_CNT_MIN_NO_STANDBY); 1699 if(tmp32 > 0xfe) { 1700 tmp32 = 0xfe; // max. performance 1701 } 1702 LunExt->opt_AdvPowerMode = (UCHAR)tmp32; 1703 1704 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"AcousticMgmt", ATA_C_F_AAM_CNT_MAX_POWER_SAVE); 1705 if(tmp32 > 0xfe) { 1706 tmp32 = 0xfe; // max. performance 1707 } else 1708 if(tmp32 < 0x80) { 1709 tmp32 = 0x0; // disable feature 1710 } 1711 LunExt->opt_AcousticMode = (UCHAR)tmp32; 1712 1713 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"StandbyTimer", 0); 1714 if(tmp32 == 0xfe) { 1715 tmp32 = 0xff; 1716 } 1717 LunExt->opt_StandbyTimer = (UCHAR)tmp32; 1718 1719 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"ReadOnly", 0); 1720 if(tmp32 <= 2) { 1721 LunExt->opt_ReadOnly = (UCHAR)tmp32; 1722 } 1723 1724 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"GeomType", 0xffffffff); 1725 if(tmp32 > GEOM_MANUAL) { 1726 tmp32 = 0xffffffff; 1727 } 1728 LunExt->opt_GeomType = tmp32; 1729 if(tmp32 == GEOM_MANUAL) { 1730 LunExt->DeviceFlags |= DFLAGS_MANUAL_CHS; 1731 LunExt->opt_GeomType = GEOM_ORIG; 1732 // assume IdentifyData is already zero-filled 1733 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"C", 0); 1734 LunExt->IdentifyData.NumberOfCurrentCylinders = 1735 LunExt->IdentifyData.NumberOfCylinders = (USHORT)tmp32; 1736 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"H", 0); 1737 LunExt->IdentifyData.NumberOfCurrentHeads = 1738 LunExt->IdentifyData.NumberOfHeads = (USHORT)tmp32; 1739 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"S", 0); 1740 LunExt->IdentifyData.CurrentSectorsPerTrack = 1741 LunExt->IdentifyData.SectorsPerTrack = (USHORT)tmp32; 1742 memcpy(LunExt->IdentifyData.ModelNumber, "SEIDH DD", 8); // ESDI HDD 1743 memcpy(LunExt->IdentifyData.SerialNumber, ".10", 4); 1744 memcpy(LunExt->IdentifyData.FirmwareRevision, ".10", 4); 1745 if(!LunExt->IdentifyData.SectorsPerTrack || 1746 !LunExt->IdentifyData.NumberOfCylinders || 1747 !LunExt->IdentifyData.NumberOfHeads) { 1748 // ERROR 1749 KdPrint2((PRINT_PREFIX "Wrong CHS\n")); 1750 LunExt->opt_GeomType = GEOM_AUTO; 1751 } else { 1752 LunExt->DeviceFlags |= DFLAGS_MANUAL_CHS; 1753 LunExt->opt_GeomType = GEOM_ORIG; 1754 } 1755 } 1756 1757 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"Hidden", 0); 1758 if(tmp32) { 1759 LunExt->DeviceFlags |= DFLAGS_HIDDEN; 1760 } 1761 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DeviceNumber, L"Exclude", 0); 1762 if(tmp32) { 1763 LunExt->DeviceFlags |= DFLAGS_HIDDEN; 1764 } 1765 1766 return; 1767 } // end UniAtaReadLunConfig() 1768 1769 BOOLEAN 1770 NTAPI 1771 AtapiReadChipConfig( 1772 IN PVOID HwDeviceExtension, 1773 IN ULONG DeviceNumber, 1774 IN ULONG channel // physical channel 1775 ) 1776 { 1777 PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension; 1778 PHW_CHANNEL chan; 1779 ULONG tmp32; 1780 ULONG c; // logical channel (for Compatible Mode controllers) 1781 ULONG i; 1782 1783 KdPrint2((PRINT_PREFIX "AtapiReadChipConfig: devExt %#x\n", deviceExtension )); 1784 ASSERT(deviceExtension); 1785 1786 if(channel != CHAN_NOT_SPECIFIED) { 1787 c = channel - deviceExtension->Channel; // logical channel (for Compatible Mode controllers) 1788 } else { 1789 c = CHAN_NOT_SPECIFIED; 1790 } 1791 1792 KdPrint2((PRINT_PREFIX "AtapiReadChipConfig: dev %#x, ph chan %d\n", DeviceNumber, channel )); 1793 1794 if(channel == CHAN_NOT_SPECIFIED) { 1795 if(AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"ForceSimplex", FALSE)) { 1796 deviceExtension->simplexOnly = TRUE; 1797 } 1798 deviceExtension->opt_AtapiDmaZeroTransfer = FALSE; 1799 deviceExtension->opt_AtapiDmaControlCmd = FALSE; 1800 deviceExtension->opt_AtapiDmaRawRead = g_opt_AtapiDmaRawRead; 1801 deviceExtension->opt_AtapiDmaReadWrite = TRUE; 1802 } 1803 1804 if(c == CHAN_NOT_SPECIFIED) { 1805 KdPrint2((PRINT_PREFIX "MaxTransferMode (base): %#x\n", deviceExtension->MaxTransferMode)); 1806 for(c=0; c<deviceExtension->NumberChannels; c++) { 1807 chan = &deviceExtension->chan[c]; 1808 chan->MaxTransferMode = deviceExtension->MaxTransferMode; 1809 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DEVNUM_NOT_SPECIFIED, L"MaxTransferMode", chan->MaxTransferMode); 1810 if(tmp32 != 0xffffffff) { 1811 KdPrint2((PRINT_PREFIX "MaxTransferMode (overriden): %#x\n", chan->MaxTransferMode)); 1812 chan->MaxTransferMode = tmp32; 1813 } 1814 tmp32 = AtapiRegCheckDevValue(deviceExtension, c, DEVNUM_NOT_SPECIFIED, L"Force80pin", FALSE); 1815 chan->Force80pin = tmp32 ? TRUE : FALSE; 1816 if(chan->Force80pin) { 1817 KdPrint2((PRINT_PREFIX "Force80pin on chip\n")); 1818 deviceExtension->HwFlags |= UNIATA_NO80CHK; 1819 } 1820 1821 //UniAtaReadLunConfig(deviceExtension, c, 0); 1822 //UniAtaReadLunConfig(deviceExtension, c, 1); 1823 } 1824 1825 deviceExtension->opt_AtapiDmaZeroTransfer = 1826 AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"AtapiDmaZeroTransfer", deviceExtension->opt_AtapiDmaZeroTransfer) ? 1827 TRUE : FALSE; 1828 1829 deviceExtension->opt_AtapiDmaControlCmd = 1830 AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"AtapiDmaControlCmd", deviceExtension->opt_AtapiDmaControlCmd) ? 1831 TRUE : FALSE; 1832 1833 deviceExtension->opt_AtapiDmaRawRead = 1834 AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"AtapiDmaRawRead", deviceExtension->opt_AtapiDmaRawRead) ? 1835 TRUE : FALSE; 1836 1837 deviceExtension->opt_AtapiDmaReadWrite = 1838 AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"AtapiDmaReadWrite", deviceExtension->opt_AtapiDmaReadWrite) ? 1839 TRUE : FALSE; 1840 1841 } else { 1842 chan = &deviceExtension->chan[c]; 1843 chan->MaxTransferMode = deviceExtension->MaxTransferMode; 1844 tmp32 = AtapiRegCheckDevValue(deviceExtension, c, DEVNUM_NOT_SPECIFIED, L"MaxTransferMode", chan->MaxTransferMode); 1845 if(tmp32 != 0xffffffff) { 1846 KdPrint2((PRINT_PREFIX "MaxTransferMode (overriden): %#x\n", chan->MaxTransferMode)); 1847 chan->MaxTransferMode = tmp32; 1848 } 1849 tmp32 = AtapiRegCheckDevValue(deviceExtension, c, DEVNUM_NOT_SPECIFIED, L"ReorderEnable", TRUE); 1850 chan->UseReorder = tmp32 ? TRUE : FALSE; 1851 1852 tmp32 = AtapiRegCheckDevValue(deviceExtension, c, DEVNUM_NOT_SPECIFIED, L"Force80pin", FALSE); 1853 chan->Force80pin = tmp32 ? TRUE : FALSE; 1854 if(chan->Force80pin) { 1855 KdPrint2((PRINT_PREFIX "Force80pin on channel\n")); 1856 } 1857 1858 for(i=0; i<deviceExtension->NumberLuns; i++) { 1859 UniAtaReadLunConfig(deviceExtension, channel, i); 1860 } 1861 } 1862 1863 return TRUE; 1864 } // end AtapiReadChipConfig() 1865 1866 BOOLEAN 1867 NTAPI 1868 AtapiChipInit( 1869 IN PVOID HwDeviceExtension, 1870 IN ULONG DeviceNumber, 1871 IN ULONG channel // logical channel 1872 ) 1873 { 1874 PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension; 1875 ULONG slotNumber = deviceExtension->slotNumber; 1876 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber; 1877 ULONG VendorID = deviceExtension->DevID & 0xffff; 1878 ULONG DeviceID = (deviceExtension->DevID >> 16) & 0xffff; 1879 ULONG RevID = deviceExtension->RevID; 1880 // ULONG i; 1881 // BUSMASTER_CONTROLLER_INFORMATION_BASE* DevTypeInfo; 1882 ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK; 1883 ULONG ChipFlags = deviceExtension->HwFlags & CHIPFLAG_MASK; 1884 PHW_CHANNEL chan; 1885 UCHAR tmp8; 1886 USHORT tmp16; 1887 ULONG tmp32; 1888 ULONG c; // logical channel (for Compatible Mode controllers) 1889 BOOLEAN CheckCable = FALSE; 1890 BOOLEAN GlobalInit = FALSE; 1891 //ULONG BaseIoAddress; 1892 1893 switch(channel) { 1894 case CHAN_NOT_SPECIFIED_CHECK_CABLE: 1895 CheckCable = TRUE; 1896 /* FALLTHROUGH */ 1897 case CHAN_NOT_SPECIFIED: 1898 c = CHAN_NOT_SPECIFIED; 1899 GlobalInit = TRUE; 1900 break; 1901 default: 1902 //c = channel - deviceExtension->Channel; // logical channel (for Compatible Mode controllers) 1903 c = channel; 1904 channel += deviceExtension->Channel; 1905 } 1906 1907 KdPrint2((PRINT_PREFIX "AtapiChipInit: dev %#x, ph chan %d, c %d\n", DeviceNumber, channel, c)); 1908 1909 KdPrint2((PRINT_PREFIX "HwFlags: %#x\n", deviceExtension->HwFlags)); 1910 KdPrint2((PRINT_PREFIX "VendorID/DeviceID/Rev %#x/%#x/%#x\n", VendorID, DeviceID, RevID)); 1911 1912 if(deviceExtension->UnknownDev) { 1913 KdPrint2((PRINT_PREFIX " Unknown chip\n" )); 1914 //return TRUE; 1915 VendorID = 0xffffffff; 1916 } 1917 1918 1919 if(ChipFlags & UNIATA_AHCI) { 1920 /* if BAR(5) is IO it should point to SATA interface registers */ 1921 if(!deviceExtension->BaseIoAHCI_0.Addr) { 1922 KdPrint2((PRINT_PREFIX " !BaseIoAHCI_0, exiting\n" )); 1923 return FALSE; 1924 } 1925 if(c == CHAN_NOT_SPECIFIED) { 1926 return UniataAhciInit(HwDeviceExtension); 1927 } else 1928 if(c<deviceExtension->NumberChannels) { 1929 KdPrint2((PRINT_PREFIX " AHCI single channel init\n" )); 1930 UniataAhciReset(HwDeviceExtension, c); 1931 return TRUE; 1932 } else { 1933 KdPrint2((PRINT_PREFIX " AHCI non-existent channel\n" )); 1934 return FALSE; 1935 } 1936 } 1937 1938 if((WinVer_Id() > WinVer_NT) && 1939 GlobalInit && 1940 deviceExtension->MasterDev) { 1941 PCI_COMMON_CONFIG pciData; 1942 ULONG busDataRead; 1943 1944 KdPrint2((PRINT_PREFIX " re-enable IO resources of MasterDev\n" )); 1945 1946 busDataRead = HalGetBusData 1947 //ScsiPortGetBusData 1948 ( 1949 //HwDeviceExtension, 1950 PCIConfiguration, SystemIoBusNumber, slotNumber, 1951 &pciData, PCI_COMMON_HDR_LENGTH); 1952 if(busDataRead == PCI_COMMON_HDR_LENGTH) { 1953 UniataEnableIoPCI(SystemIoBusNumber, slotNumber, &pciData); 1954 } else { 1955 KdPrint2((PRINT_PREFIX " re-enable IO resources of MasterDev FAILED\n" )); 1956 } 1957 } 1958 1959 switch(VendorID) { 1960 // case ATA_ACARD_ID: 1961 // break; 1962 case ATA_ACER_LABS_ID: 1963 if(ChipFlags & UNIATA_SATA) { 1964 if(c == CHAN_NOT_SPECIFIED) { 1965 for(c=0; c<deviceExtension->NumberChannels; c++) { 1966 chan = &deviceExtension->chan[c]; 1967 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 1968 /* the southbridge might need the data corruption fix */ 1969 if(RevID == 0xc2 || RevID == 0xc3) { 1970 AtapiAliSouthBridgeFixup(HwDeviceExtension, PCIConfiguration, 1971 SystemIoBusNumber, slotNumber, c); 1972 } 1973 } 1974 /* enable PCI interrupt */ 1975 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG, Command), (a & ~0x0400)); 1976 } 1977 } else 1978 if(ChipFlags & ALINEW) { 1979 if(c == CHAN_NOT_SPECIFIED) { 1980 /* use device interrupt as byte count end */ 1981 ChangePciConfig1(0x4a, (a | 0x20)); 1982 /* enable cable detection and UDMA support on newer chips, rev < 0xc7 */ 1983 if(RevID < 0xc7) { 1984 ChangePciConfig1(0x4b, (a | 0x09)); 1985 } 1986 1987 /* enable ATAPI UDMA mode */ 1988 ChangePciConfig1(0x53, (a | (RevID >= 0xc7 ? 0x03 : 0x01))); 1989 1990 } else { 1991 // check 80-pin cable 1992 generic_cable80(deviceExtension, channel, 0x4a, 0); 1993 } 1994 } else { 1995 if(c == CHAN_NOT_SPECIFIED) { 1996 /* deactivate the ATAPI FIFO and enable ATAPI UDMA */ 1997 ChangePciConfig1(0x53, (a | 0x03)); 1998 } else { 1999 // ATAPI DMA R/O 2000 deviceExtension->chan[c].ChannelCtrlFlags |= CTRFLAGS_DMA_RO; 2001 } 2002 } 2003 break; 2004 case ATA_AMD_ID: 2005 if(c == CHAN_NOT_SPECIFIED) { 2006 /* set prefetch, postwrite */ 2007 if(ChipFlags & AMDBUG) { 2008 ChangePciConfig1(0x41, (a & 0x0f)); 2009 } else { 2010 ChangePciConfig1(0x41, (a | 0xf0)); 2011 } 2012 } 2013 if(deviceExtension->MaxTransferMode < ATA_UDMA2) 2014 break; 2015 // check 80-pin cable 2016 if(!(ChipFlags & UNIATA_NO80CHK)) { 2017 if(c == CHAN_NOT_SPECIFIED) { 2018 // do nothing 2019 } else { 2020 generic_cable80(deviceExtension, channel, 0x42, 0); 2021 } 2022 } 2023 break; 2024 case ATA_HIGHPOINT_ID: 2025 2026 if(c == CHAN_NOT_SPECIFIED) { 2027 2028 if(ChipFlags & HPTOLD) { 2029 /* turn off interrupt prediction */ 2030 ChangePciConfig1(0x51, (a & ~0x80)); 2031 } else { 2032 /* turn off interrupt prediction */ 2033 ChangePciConfig1(0x51, (a & ~0x03)); 2034 ChangePciConfig1(0x55, (a & ~0x03)); 2035 /* turn on interrupts */ 2036 ChangePciConfig1(0x5a, (a & ~0x10)); 2037 /* set clocks etc */ 2038 if(ChipType < HPT372) { 2039 SetPciConfig1(0x5b, 0x22); 2040 } else { 2041 ChangePciConfig1(0x5b, ((a & 0x01) | 0x20)); 2042 } 2043 } 2044 2045 } else { 2046 // check 80-pin cable 2047 chan = &deviceExtension->chan[c]; 2048 if(!hpt_cable80(deviceExtension, channel)) { 2049 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 2050 } 2051 } 2052 break; 2053 case ATA_INTEL_ID: { 2054 BOOLEAN IsPata; 2055 USHORT reg54; 2056 if(ChipFlags & UNIATA_SATA) { 2057 2058 KdPrint2((PRINT_PREFIX "Intel SATA\n")); 2059 if(ChipFlags & UNIATA_AHCI) { 2060 KdPrint2((PRINT_PREFIX "Do nothing for AHCI\n")); 2061 /* enable PCI interrupt */ 2062 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG, Command), (a & ~0x0400)); 2063 break; 2064 } 2065 if(c == CHAN_NOT_SPECIFIED) { 2066 KdPrint2((PRINT_PREFIX "Base init\n")); 2067 /* force all ports active "the legacy way" */ 2068 ChangePciConfig2(0x92, (a | 0x0f)); 2069 2070 if(deviceExtension->BaseIoAddressSATA_0.Addr && (ChipFlags & ICH7)) { 2071 /* Set SCRAE bit to enable registers access. */ 2072 ChangePciConfig4(0x94, (a | (1 << 9))); 2073 /* Set Ports Implemented register bits. */ 2074 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0), 0x0c, 2075 AtapiReadPortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0), 0x0c) | 0x0f); 2076 } 2077 /* enable PCI interrupt */ 2078 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG, Command), (a & ~0x0400)); 2079 2080 } else { 2081 2082 KdPrint2((PRINT_PREFIX "channel init\n")); 2083 2084 GetPciConfig1(0x90, tmp8); 2085 KdPrint2((PRINT_PREFIX "reg 90: %x, init lun map\n", tmp8)); 2086 2087 KdPrint2((PRINT_PREFIX "chan %d\n", c)); 2088 chan = &deviceExtension->chan[c]; 2089 IsPata = FALSE; 2090 if(ChipFlags & ICH5) { 2091 KdPrint2((PRINT_PREFIX "ICH5\n")); 2092 if ((tmp8 & 0x04) == 0) { 2093 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 2094 chan->lun[0]->SATA_lun_map = (tmp8 & 0x01) ^ c; 2095 chan->lun[1]->SATA_lun_map = 0; 2096 } else if ((tmp8 & 0x02) == 0) { 2097 if(c == 0) { 2098 chan->lun[0]->SATA_lun_map = (tmp8 & 0x01) ? 1 : 0; 2099 chan->lun[1]->SATA_lun_map = (tmp8 & 0x01) ? 0 : 1; 2100 } else { 2101 IsPata = TRUE; 2102 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA; 2103 } 2104 } else if ((tmp8 & 0x02) != 0) { 2105 if(c == 1) { 2106 chan->lun[0]->SATA_lun_map = (tmp8 & 0x01) ? 1 : 0; 2107 chan->lun[1]->SATA_lun_map = (tmp8 & 0x01) ? 0 : 1; 2108 } else { 2109 IsPata = TRUE; 2110 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA; 2111 } 2112 } 2113 } else 2114 if(ChipFlags & I6CH2) { 2115 KdPrint2((PRINT_PREFIX "I6CH2\n")); 2116 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE; 2117 chan->lun[0]->SATA_lun_map = c ? 0 : 1; 2118 chan->lun[1]->SATA_lun_map = 0; 2119 } else { 2120 KdPrint2((PRINT_PREFIX "other Intel\n")); 2121 switch(tmp8 & 0x03) { 2122 case 0: 2123 KdPrint2((PRINT_PREFIX "0 -> %d/%d\n", 0+c, 2+c)); 2124 chan->lun[0]->SATA_lun_map = 0+c; 2125 chan->lun[1]->SATA_lun_map = 2+c; 2126 break; 2127 case 2: 2128 if(c==0) { 2129 KdPrint2((PRINT_PREFIX "2 -> %d/%d\n", 0, 2)); 2130 chan->lun[0]->SATA_lun_map = 0; 2131 chan->lun[1]->SATA_lun_map = 2; 2132 } else { 2133 // PATA 2134 KdPrint2((PRINT_PREFIX "PATA\n")); 2135 IsPata = TRUE; 2136 } 2137 break; 2138 case 1: 2139 if(c==1) { 2140 KdPrint2((PRINT_PREFIX "2 -> %d/%d\n", 1, 3)); 2141 chan->lun[0]->SATA_lun_map = 1; 2142 chan->lun[1]->SATA_lun_map = 3; 2143 } else { 2144 // PATA 2145 KdPrint2((PRINT_PREFIX "PATA\n")); 2146 IsPata = TRUE; 2147 } 2148 break; 2149 } 2150 } 2151 2152 if(IsPata) { 2153 KdPrint2((PRINT_PREFIX "PATA part\n")); 2154 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA5); 2155 } 2156 2157 if(ChipType == INTEL_IDX) { 2158 KdPrint2((PRINT_PREFIX "io indexed\n")); 2159 //for(c=0; c<deviceExtension->NumberChannels; c++) { 2160 chan = &deviceExtension->chan[c]; 2161 UniataSataWritePort4(chan, IDX_SATA_SError, 0xffffffff, 0); 2162 if(!(chan->ChannelCtrlFlags & CTRFLAGS_NO_SLAVE)) { 2163 UniataSataWritePort4(chan, IDX_SATA_SError, 0xffffffff, 1); 2164 } 2165 //} 2166 } 2167 } 2168 2169 break; 2170 } 2171 if(deviceExtension->MaxTransferMode <= ATA_UDMA2) 2172 break; 2173 // check 80-pin cable 2174 if(c == CHAN_NOT_SPECIFIED) { 2175 // do nothing 2176 } else { 2177 chan = &deviceExtension->chan[c]; 2178 GetPciConfig2(0x54, reg54); 2179 KdPrint2((PRINT_PREFIX " intel 80-pin check (reg54=%x)\n", reg54)); 2180 if(deviceExtension->HwFlags & UNIATA_NO80CHK) { 2181 KdPrint2((PRINT_PREFIX " No check (administrative)\n")); 2182 if(chan->Force80pin) { 2183 KdPrint2((PRINT_PREFIX "Force80pin\n")); 2184 } 2185 } else 2186 if(reg54 == 0x0000 || reg54 == 0xffff) { 2187 KdPrint2((PRINT_PREFIX " check failed (not supported)\n")); 2188 } else 2189 if( ((reg54 >> (channel*2)) & 30) == 0) { 2190 KdPrint2((PRINT_PREFIX " intel 40-pin\n")); 2191 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 2192 } 2193 } 2194 break; } 2195 case ATA_NVIDIA_ID: { 2196 if(ChipFlags & UNIATA_SATA) { 2197 if(c == CHAN_NOT_SPECIFIED) { 2198 ULONG offs = (ChipFlags & NV4OFF) ? 0x0440 : 0x0010; 2199 /* enable control access */ 2200 ChangePciConfig1(0x50, (a | 0x04)); 2201 /* MCP55 seems to need some time to allow r_res2 read. */ 2202 AtapiStallExecution(10); 2203 KdPrint2((PRINT_PREFIX "BaseIoAddressSATA_0=%x\n", deviceExtension->BaseIoAddressSATA_0.Addr)); 2204 if(ChipFlags & NVQ) { 2205 KdPrint2((PRINT_PREFIX "Disable NCQ\n")); 2206 tmp32 = AtapiReadPortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),0x0400); 2207 KdPrint2((PRINT_PREFIX "MODE=%#x\n", tmp32)); 2208 if(tmp32 & ~0xfffffff9) { 2209 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),0x0400, 2210 tmp32 & 0xfffffff9); 2211 } 2212 ChipFlags &= ~NVQ; 2213 deviceExtension->HwFlags = ChipFlags; 2214 } 2215 if(ChipFlags & NVQ) { 2216 /* disable ECO 398 */ 2217 ChangePciConfig1(0x7f, (a & ~(1 << 7))); 2218 2219 KdPrint2((PRINT_PREFIX "Enable NCQ\n")); 2220 /* enable NCQ support */ 2221 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),0x0400, 2222 tmp32 | ~0x00000006); 2223 2224 /* clear interrupt status */ 2225 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),offs, 0x00ff00ff); 2226 /* enable device and PHY state change interrupts */ 2227 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),offs+4, 0x000d000d); 2228 } else { 2229 /* clear interrupt status */ 2230 AtapiWritePortEx1(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),offs, 0xff); 2231 /* enable device and PHY state change interrupts */ 2232 AtapiWritePortEx1(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),offs+1, 0xdd); 2233 } 2234 /* enable PCI interrupt */ 2235 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG, Command), (a & ~0x0400)); 2236 } else { 2237 //UniataSataPhyEnable(HwDeviceExtension, c); 2238 } 2239 } else { 2240 //UCHAR reg52; 2241 2242 if(c == CHAN_NOT_SPECIFIED) { 2243 /* set prefetch, postwrite */ 2244 ChangePciConfig1(0x51, (a & 0x0f)); 2245 } else { 2246 // check 80-pin cable 2247 generic_cable80(deviceExtension, channel, 0x52, 1); 2248 /* chan = &deviceExtension->chan[c]; 2249 GetPciConfig1(0x52, reg52); 2250 if( !((reg52 >> (channel*2)) & 0x01)) { 2251 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 2252 }*/ 2253 } 2254 } 2255 break; } 2256 case ATA_PROMISE_ID: { 2257 USHORT Reg50; 2258 switch(ChipType) { 2259 case PRNEW: 2260 /* setup clocks */ 2261 if(c == CHAN_NOT_SPECIFIED) { 2262 // ATA_OUTB(ctlr->r_res1, 0x11, ATA_INB(ctlr->r_res1, 0x11) | 0x0a); 2263 AtapiWritePortEx1(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressBM_0),0x11, 2264 AtapiReadPortEx1(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressBM_0),0x11) | 0x0a ); 2265 } 2266 /* FALLTHROUGH */ 2267 case PROLD: 2268 /* enable burst mode */ 2269 // ATA_OUTB(ctlr->r_res1, 0x1f, ATA_INB(ctlr->r_res1, 0x1f) | 0x01); 2270 if(c == CHAN_NOT_SPECIFIED) { 2271 AtapiWritePortEx1(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressBM_0),0x1f, 2272 AtapiReadPortEx1(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressBM_0),0x1f) | 0x01 ); 2273 } else { 2274 // check 80-pin cable 2275 chan = &deviceExtension->chan[c]; 2276 GetPciConfig2(0x50, Reg50); 2277 if(Reg50 & (1 << (channel+10))) { 2278 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 2279 } 2280 } 2281 break; 2282 case PRTX: 2283 if(c == CHAN_NOT_SPECIFIED) { 2284 // do nothing 2285 } else { 2286 // check 80-pin cable 2287 chan = &deviceExtension->chan[c]; 2288 AtapiWritePort1(chan, IDX_BM_DeviceSpecific0, 0x0b); 2289 if(AtapiReadPort1(chan, IDX_BM_DeviceSpecific1) & 0x04) { 2290 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 2291 } 2292 } 2293 break; 2294 case PRMIO: 2295 if(c == CHAN_NOT_SPECIFIED) { 2296 /* clear SATA status and unmask interrupts */ 2297 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressBM_0), 2298 (ChipFlags & PRG2) ? 0x60 : 0x6c, 0x000000ff); 2299 if(ChipFlags & UNIATA_SATA) { 2300 /* enable "long burst length" on gen2 chips */ 2301 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressBM_0), 0x44, 2302 AtapiReadPortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressBM_0), 0x44) | 0x2000); 2303 } 2304 } else { 2305 chan = &deviceExtension->chan[c]; 2306 AtapiWritePort4(chan, IDX_BM_Command, 2307 (AtapiReadPort4(chan, IDX_BM_Command) & ~0x00000f8f) | channel ); 2308 AtapiWritePort4(chan, IDX_BM_DeviceSpecific0, 0x00000001); 2309 // check 80-pin cable 2310 if(chan->MaxTransferMode < ATA_SA150 && 2311 (AtapiReadPort4(chan, IDX_BM_Command) & 0x01000000)) { 2312 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 2313 } 2314 } 2315 break; 2316 } 2317 break; } 2318 case ATA_SERVERWORKS_ID: 2319 if(c == CHAN_NOT_SPECIFIED) { 2320 if(ChipType == SWKS33) { 2321 AtapiRosbSouthBridgeFixup(HwDeviceExtension, PCIConfiguration, 2322 SystemIoBusNumber, slotNumber); 2323 } else { 2324 ChangePciConfig1(0x5a, ((a & ~0x40) | ((ChipType == SWKS100) ? 0x03 : 0x02))); 2325 } 2326 } 2327 break; 2328 case ATA_ATI_ID: 2329 if(ChipType == SIIMIO) { 2330 KdPrint2((PRINT_PREFIX "ATI New\n")); 2331 // fall to SiI 2332 } else { 2333 KdPrint2((PRINT_PREFIX "ATI\n")); 2334 break; 2335 } 2336 /* FALLTHROUGH */ 2337 case ATA_SILICON_IMAGE_ID: 2338 /* if(ChipFlags & SIIENINTR) { 2339 SetPciConfig1(0x71, 0x01); 2340 }*/ 2341 switch(ChipType) { 2342 case SIIMIO: { 2343 2344 KdPrint2((PRINT_PREFIX "SII\n")); 2345 USHORT Reg79; 2346 2347 if(c == CHAN_NOT_SPECIFIED) { 2348 if(ChipFlags & SIISETCLK) { 2349 KdPrint2((PRINT_PREFIX "SIISETCLK\n")); 2350 GetPciConfig1(0x8a, tmp8); 2351 if ((tmp8 & 0x30) != 0x10) 2352 ChangePciConfig1(0x8a, (a & 0xcf) | 0x10); 2353 GetPciConfig1(0x8a, tmp8); 2354 if ((tmp8 & 0x30) != 0x10) { 2355 KdPrint2((PRINT_PREFIX "Sil 0680 could not set ATA133 clock\n")); 2356 deviceExtension->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA5); 2357 } 2358 } 2359 } 2360 if(deviceExtension->MaxTransferMode < ATA_SA150) { 2361 // check 80-pin cable 2362 if(c == CHAN_NOT_SPECIFIED) { 2363 // do nothing 2364 } else { 2365 KdPrint2((PRINT_PREFIX "Check UDMA66 cable\n")); 2366 chan = &deviceExtension->chan[c]; 2367 GetPciConfig2(0x79, Reg79); 2368 if(Reg79 & (channel ? 0x02 : 0x01)) { 2369 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 2370 } 2371 } 2372 } else { 2373 ULONG unit01 = (c & 1); 2374 ULONG unit10 = (c & 2); 2375 /* enable/disable PHY state change interrupt */ 2376 if(c == CHAN_NOT_SPECIFIED) { 2377 for(c=0; c<deviceExtension->NumberChannels; c++) { 2378 unit01 = (c & 1); 2379 unit10 = (c & 2); 2380 if(ChipFlags & SIINOSATAIRQ) { 2381 KdPrint2((PRINT_PREFIX "Disable broken SATA intr on c=%x\n", c)); 2382 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0), 0x148 + (unit01 << 7) + (unit10 << 8),0); 2383 } 2384 } 2385 } else { 2386 if(ChipFlags & SIINOSATAIRQ) { 2387 KdPrint2((PRINT_PREFIX "Disable broken SATA intr on c=%x\n", c)); 2388 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0), 0x148 + (unit01 << 7) + (unit10 << 8),0); 2389 } else { 2390 KdPrint2((PRINT_PREFIX "Enable SATA intr on c=%x\n", c)); 2391 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0), 0x148 + (unit01 << 7) + (unit10 << 8),(1 << 16)); 2392 } 2393 } 2394 } 2395 if(c == CHAN_NOT_SPECIFIED) { 2396 /* enable interrupt as BIOS might not */ 2397 ChangePciConfig1(0x8a, (a & 0x3f)); 2398 // Enable 3rd and 4th channels 2399 if (ChipFlags & SII4CH) { 2400 KdPrint2((PRINT_PREFIX "SII4CH\n")); 2401 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),0x0200, 0x00000002); 2402 } 2403 } else { 2404 chan = &deviceExtension->chan[c]; 2405 /* dont block interrupts */ 2406 //ChangePciConfig4(0x48, (a & ~0x03c00000)); 2407 /*tmp32 =*/ AtapiReadPortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),0x48); 2408 AtapiWritePortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),0x48, (1 << 22) << c); 2409 // flush 2410 /*tmp32 =*/ AtapiReadPortEx4(NULL, (ULONGIO_PTR)(&deviceExtension->BaseIoAddressSATA_0),0x48); 2411 2412 /* Initialize FIFO PCI bus arbitration */ 2413 GetPciConfig1(offsetof(PCI_COMMON_CONFIG, CacheLineSize), tmp8); 2414 if(tmp8) { 2415 KdPrint2((PRINT_PREFIX "SII: CacheLine=%d\n", tmp8)); 2416 tmp8 = (tmp8/8)+1; 2417 AtapiWritePort2(chan, IDX_BM_DeviceSpecific1, ((USHORT)tmp8) << 8 | tmp8); 2418 } else { 2419 KdPrint2((PRINT_PREFIX "SII: CacheLine=0 !!!\n")); 2420 } 2421 } 2422 break; } 2423 2424 case SIICMD: { 2425 2426 KdPrint2((PRINT_PREFIX "SII_CMD\n")); 2427 if(c == CHAN_NOT_SPECIFIED) { 2428 /* Setup interrupts. */ 2429 SetPciConfig1(0x71, 0x01); 2430 2431 /* GetPciConfig1(0x8a, tmp8); 2432 tmp8 &= ~(0x30); 2433 SetPciConfig1(0x71, tmp8);*/ 2434 2435 /* Use MEMORY READ LINE for reads. 2436 * NOTE: Although not mentioned in the PCI0646U specs, 2437 * these bits are write only and won't be read 2438 * back as set or not. The PCI0646U2 specs clarify 2439 * this point. 2440 */ 2441 /* tmp8 |= 0x02; 2442 SetPciConfig1(0x71, tmp8); 2443 */ 2444 /* Set reasonable active/recovery/address-setup values. */ 2445 SetPciConfig1(0x53, 0x40); 2446 SetPciConfig1(0x54, 0x3f); 2447 SetPciConfig1(0x55, 0x40); 2448 SetPciConfig1(0x56, 0x3f); 2449 SetPciConfig1(0x57, 0x1c); 2450 SetPciConfig1(0x58, 0x3f); 2451 SetPciConfig1(0x5b, 0x3f); 2452 } 2453 2454 break; } 2455 case ATI700: 2456 KdPrint2((PRINT_PREFIX "ATI700\n")); 2457 if(c == 0 && !(ChipFlags & UNIATA_AHCI)) { 2458 KdPrint2((PRINT_PREFIX "IXP700 PATA\n")); 2459 chan = &deviceExtension->chan[c]; 2460 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA5); 2461 } 2462 break; 2463 } /* switch(ChipType) */ 2464 break; 2465 case ATA_SIS_ID: 2466 if(c == CHAN_NOT_SPECIFIED) { 2467 switch(ChipType) { 2468 case SIS33: 2469 break; 2470 case SIS66: 2471 case SIS100OLD: 2472 ChangePciConfig1(0x52, (a & ~0x04)); 2473 break; 2474 case SIS100NEW: 2475 case SIS133OLD: 2476 ChangePciConfig1(0x49, (a & ~0x01)); 2477 break; 2478 case SIS133NEW: 2479 ChangePciConfig2(0x50, (a | 0x0008)); 2480 ChangePciConfig2(0x52, (a | 0x0008)); 2481 break; 2482 case SISSATA: 2483 ChangePciConfig2(0x04, (a & ~0x0400)); 2484 break; 2485 } 2486 } 2487 if(deviceExtension->HwFlags & UNIATA_SATA) { 2488 // do nothing for SATA 2489 } else 2490 if(ChipType == SIS133NEW) { 2491 // check 80-pin cable 2492 if(c == CHAN_NOT_SPECIFIED) { 2493 // do nothing 2494 } else { 2495 chan = &deviceExtension->chan[c]; 2496 GetPciConfig2(channel ? 0x52 : 0x50, tmp16); 2497 if(tmp16 & 0x8000) { 2498 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 2499 } 2500 } 2501 } else { 2502 // check 80-pin cable 2503 if(c == CHAN_NOT_SPECIFIED) { 2504 // do nothing 2505 } else { 2506 chan = &deviceExtension->chan[c]; 2507 GetPciConfig1(48, tmp8); 2508 if(tmp8 & (0x10 << channel)) { 2509 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 2510 } 2511 } 2512 } 2513 break; 2514 case ATA_VIA_ID: 2515 2516 /* if(ChipFlags & (UNIATA_SATA | UNIATA_AHCI | VIASATA) { 2517 break; 2518 }*/ 2519 if(c == CHAN_NOT_SPECIFIED) { 2520 /* prepare for ATA-66 on the 82C686a and 82C596b */ 2521 if(ChipFlags & VIACLK) { 2522 ChangePciConfig4(0x50, (a | 0x030b030b)); 2523 } 2524 // no init for SATA 2525 if(ChipFlags & (UNIATA_SATA | VIASATA)) { 2526 /* enable PCI interrupt */ 2527 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG, Command), (a & ~0x0400)); 2528 2529 /* 2530 * vt6420/1 has problems talking to some drives. The following 2531 * is based on the fix from Joseph Chan <JosephChan@via.com.tw>. 2532 * 2533 * When host issues HOLD, device may send up to 20DW of data 2534 * before acknowledging it with HOLDA and the host should be 2535 * able to buffer them in FIFO. Unfortunately, some WD drives 2536 * send upto 40DW before acknowledging HOLD and, in the 2537 * default configuration, this ends up overflowing vt6421's 2538 * FIFO, making the controller abort the transaction with 2539 * R_ERR. 2540 * 2541 * Rx52[2] is the internal 128DW FIFO Flow control watermark 2542 * adjusting mechanism enable bit and the default value 0 2543 * means host will issue HOLD to device when the left FIFO 2544 * size goes below 32DW. Setting it to 1 makes the watermark 2545 * 64DW. 2546 * 2547 * http://www.reactos.org/bugzilla/show_bug.cgi?id=6500 2548 */ 2549 2550 if(DeviceID == 0x3149 || DeviceID == 0x3249) { //vt6420 or vt6421 2551 KdPrint2((PRINT_PREFIX "VIA 642x FIFO\n")); 2552 ChangePciConfig1(0x52, a | (1 << 2)); 2553 } 2554 2555 break; 2556 } 2557 2558 /* the southbridge might need the data corruption fix */ 2559 if(ChipFlags & VIABUG) { 2560 AtapiViaSouthBridgeFixup(HwDeviceExtension, PCIConfiguration, 2561 SystemIoBusNumber, slotNumber); 2562 } 2563 /* set prefetch, postwrite */ 2564 if(ChipType != VIA133) { 2565 ChangePciConfig1(0x41, (a | 0xf0)); 2566 } 2567 2568 /* set fifo configuration half'n'half */ 2569 ChangePciConfig1(0x43, ((a & ((ChipFlags & VIAPRQ) ? 0x80 : 0x90)) | 0x2a)); 2570 2571 /* set status register read retry */ 2572 ChangePciConfig1(0x44, (a | 0x08)); 2573 2574 /* set DMA read & end-of-sector fifo flush */ 2575 ChangePciConfig1(0x46, ((a & 0x0c) | 0xf0)); 2576 2577 /* set sector size */ 2578 SetPciConfig2(0x60, DEV_BSIZE); 2579 SetPciConfig2(0x68, DEV_BSIZE); 2580 } else { 2581 2582 chan = &deviceExtension->chan[c]; 2583 // no init for SATA 2584 if(ChipFlags & (UNIATA_SATA | VIASATA)) { 2585 if((ChipFlags & VIABAR) && (c >= 2)) { 2586 // this is PATA channel 2587 chan->MaxTransferMode = ATA_UDMA5; 2588 break; 2589 } 2590 UniataSataWritePort4(chan, IDX_SATA_SError, 0xffffffff, 0); 2591 break; 2592 } 2593 /* 2594 // check 80-pin cable 2595 if(!via_cable80(deviceExtension, channel)) { 2596 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 2597 } 2598 */ 2599 } 2600 2601 break; 2602 2603 case ATA_ITE_ID: 2604 if(ChipType == ITE_33 || ChipType == ITE_133_NEW) { 2605 break; 2606 } 2607 if(ChipType == ITE_133) { 2608 if(c == CHAN_NOT_SPECIFIED) { 2609 /* set PCI mode and 66Mhz reference clock */ 2610 ChangePciConfig1(0x50, a & ~0x83); 2611 2612 /* set default active & recover timings */ 2613 SetPciConfig1(0x54, 0x31); 2614 SetPciConfig1(0x56, 0x31); 2615 } else { 2616 // check 80-pin cable 2617 GetPciConfig2(0x40, tmp16); 2618 chan = &deviceExtension->chan[c]; 2619 if(!(tmp16 & (channel ? 0x08 : 0x04))) { 2620 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2); 2621 } 2622 } 2623 } else 2624 if(ChipType == ITE_133_NEW) { 2625 } 2626 break; 2627 case ATA_CYRIX_ID: 2628 KdPrint2((PRINT_PREFIX "Cyrix\n")); 2629 if(ChipType == CYRIX_OLD) { 2630 if(c == CHAN_NOT_SPECIFIED) { 2631 GetPciConfig1(0x60, tmp8); 2632 if(!(tmp8 & 0x40)) { 2633 KdPrint2((PRINT_PREFIX "Enable DMA\n")); 2634 tmp8 |= 0x40; 2635 SetPciConfig1(0x60, tmp8); 2636 } 2637 } 2638 } 2639 break; 2640 default: 2641 if(c != CHAN_NOT_SPECIFIED) { 2642 // We don't know how to check for 80-pin cable on unknown controllers. 2643 // Later we shall check bit in IDENTIFY structure, but it is not reliable way. 2644 // So, leave this flag to use as hint in error recovery procedures 2645 KdPrint2((PRINT_PREFIX "UNIATA_NO80CHK\n")); 2646 deviceExtension->HwFlags |= UNIATA_NO80CHK; 2647 } 2648 break; 2649 } 2650 2651 // In all places separate channels are inited after common controller init 2652 // The only exception is probe. But there we may need info about 40/80 pin and MaxTransferRate 2653 if(CheckCable && !(ChipFlags & (UNIATA_NO80CHK | UNIATA_SATA))) { 2654 for(c=0; c<deviceExtension->NumberChannels; c++) { 2655 AtapiChipInit(HwDeviceExtension, DeviceNumber, c); 2656 } 2657 } 2658 2659 return TRUE; 2660 } // end AtapiChipInit() 2661 2662 VOID 2663 NTAPI 2664 UniataInitMapBM( 2665 IN PHW_DEVICE_EXTENSION deviceExtension, 2666 IN PIDE_BUSMASTER_REGISTERS BaseIoAddressBM_0, 2667 IN BOOLEAN MemIo 2668 ) 2669 { 2670 PHW_CHANNEL chan; 2671 ULONG c; 2672 ULONG i; 2673 2674 if(!BaseIoAddressBM_0) { 2675 MemIo = FALSE; 2676 } 2677 for(c=0; c<deviceExtension->NumberChannels; c++) { 2678 chan = &deviceExtension->chan[c]; 2679 for (i=0; i<IDX_BM_IO_SZ; i++) { 2680 UniataInitIoRes(chan, IDX_BM_IO+i, BaseIoAddressBM_0 ? ((ULONGIO_PTR)BaseIoAddressBM_0 + i) : 0, MemIo, FALSE); 2681 } 2682 if(BaseIoAddressBM_0) { 2683 BaseIoAddressBM_0++; 2684 } 2685 } 2686 return; 2687 } // end UniataInitMapBM() 2688 2689 VOID 2690 NTAPI 2691 UniataInitMapBase( 2692 IN PHW_CHANNEL chan, 2693 IN PIDE_REGISTERS_1 BaseIoAddress1, 2694 IN PIDE_REGISTERS_2 BaseIoAddress2 2695 ) 2696 { 2697 ULONG i; 2698 2699 for (i=0; i<IDX_IO1_SZ; i++) { 2700 UniataInitIoRes(chan, IDX_IO1+i, BaseIoAddress1 ? ((ULONGIO_PTR)BaseIoAddress1 + i) : 0, FALSE, FALSE); 2701 } 2702 for (i=0; i<IDX_IO2_SZ; i++) { 2703 UniataInitIoRes(chan, IDX_IO2+i, BaseIoAddress2 ? ((ULONGIO_PTR)BaseIoAddress2 + i) : 0, FALSE, FALSE); 2704 } 2705 UniataInitSyncBaseIO(chan); 2706 return; 2707 } // end UniataInitMapBase() 2708 2709 VOID 2710 NTAPI 2711 UniataInitSyncBaseIO( 2712 IN PHW_CHANNEL chan 2713 ) 2714 { 2715 RtlCopyMemory(&chan->RegTranslation[IDX_IO1_o], &chan->RegTranslation[IDX_IO1], IDX_IO1_SZ*sizeof(chan->RegTranslation[0])); 2716 RtlCopyMemory(&chan->RegTranslation[IDX_IO2_o], &chan->RegTranslation[IDX_IO2], IDX_IO2_SZ*sizeof(chan->RegTranslation[0])); 2717 return; 2718 } // end UniataInitSyncBaseIO() 2719 2720 VOID 2721 UniataInitIoRes( 2722 IN PHW_CHANNEL chan, 2723 IN ULONG idx, 2724 IN ULONG addr, 2725 IN BOOLEAN MemIo, 2726 IN BOOLEAN Proc 2727 ) 2728 { 2729 if(!addr) { 2730 MemIo = Proc = FALSE; 2731 } 2732 chan->RegTranslation[idx].Addr = addr; 2733 chan->RegTranslation[idx].MemIo = MemIo; 2734 chan->RegTranslation[idx].Proc = Proc; 2735 } // end UniataInitIoRes() 2736 2737 VOID 2738 UniataInitIoResEx( 2739 IN PIORES IoRes, 2740 IN ULONG addr, 2741 IN BOOLEAN MemIo, 2742 IN BOOLEAN Proc 2743 ) 2744 { 2745 if(!addr) { 2746 MemIo = Proc = FALSE; 2747 } 2748 IoRes->Addr = addr; 2749 IoRes->MemIo = MemIo; 2750 IoRes->Proc = Proc; 2751 } // end UniataInitIoResEx() 2752 2753 VOID 2754 NTAPI 2755 AtapiSetupLunPtrs( 2756 IN PHW_CHANNEL chan, 2757 IN PHW_DEVICE_EXTENSION deviceExtension, 2758 IN ULONG c 2759 ) 2760 { 2761 ULONG i; 2762 2763 KdPrint2((PRINT_PREFIX "AtapiSetupLunPtrs for channel %d of %d, %d luns \n", c, deviceExtension->NumberChannels, deviceExtension->NumberLuns)); 2764 2765 if(!deviceExtension->NumberLuns) { 2766 KdPrint2((PRINT_PREFIX "Achtung !deviceExtension->NumberLuns \n")); 2767 deviceExtension->NumberLuns = IDE_MAX_LUN_PER_CHAN; 2768 } 2769 KdPrint2((PRINT_PREFIX " Chan %#x\n", chan)); 2770 chan->DeviceExtension = deviceExtension; 2771 chan->lChannel = c; 2772 chan->NumberLuns = deviceExtension->NumberLuns; 2773 for(i=0; i<deviceExtension->NumberLuns; i++) { 2774 chan->lun[i] = &(deviceExtension->lun[c*deviceExtension->NumberLuns+i]); 2775 KdPrint2((PRINT_PREFIX " Lun %#x\n", i)); 2776 KdPrint2((PRINT_PREFIX " Lun ptr %#x\n", chan->lun[i])); 2777 } 2778 chan->AltRegMap = deviceExtension->AltRegMap; 2779 chan->NextDpcChan = -1; 2780 chan->last_devsel = -1; 2781 for(i=0; i<deviceExtension->NumberLuns; i++) { 2782 chan->lun[i]->DeviceExtension = deviceExtension; 2783 chan->lun[i]->chan = chan; 2784 chan->lun[i]->Lun = i; 2785 } 2786 if((deviceExtension->HwFlags & UNIATA_AHCI) && 2787 deviceExtension->AhciInternalAtaReq0 && 2788 deviceExtension->AhciInternalSrb0) { 2789 chan->AhciInternalAtaReq = &(deviceExtension->AhciInternalAtaReq0[c]); 2790 chan->AhciInternalSrb = &(deviceExtension->AhciInternalSrb0[c]); 2791 UniataAhciSetupCmdPtr(chan->AhciInternalAtaReq); 2792 chan->AhciInternalSrb->SrbExtension = chan->AhciInternalAtaReq; 2793 chan->AhciInternalAtaReq->Srb = chan->AhciInternalSrb; 2794 } 2795 return; 2796 } // end AtapiSetupLunPtrs() 2797 2798 BOOLEAN 2799 NTAPI 2800 UniataAllocateLunExt( 2801 PHW_DEVICE_EXTENSION deviceExtension, 2802 ULONG NewNumberChannels 2803 ) 2804 { 2805 PHW_LU_EXTENSION old_luns = NULL; 2806 PHW_CHANNEL old_chans = NULL; 2807 2808 KdPrint2((PRINT_PREFIX "allocate %d Luns for %d channels\n", deviceExtension->NumberLuns, deviceExtension->NumberChannels)); 2809 2810 old_luns = deviceExtension->lun; 2811 old_chans = deviceExtension->chan; 2812 2813 if(old_luns || old_chans) { 2814 if(NewNumberChannels == UNIATA_ALLOCATE_NEW_LUNS) { 2815 KdPrint2((PRINT_PREFIX "already allocated!\n")); 2816 return FALSE; 2817 } 2818 } 2819 2820 if(!deviceExtension->NumberLuns) { 2821 KdPrint2((PRINT_PREFIX "default NumberLuns=2\n")); 2822 deviceExtension->NumberLuns = 2; 2823 } 2824 2825 if(deviceExtension->HwFlags & UNIATA_AHCI) { 2826 if(!deviceExtension->AhciInternalAtaReq0) { 2827 deviceExtension->AhciInternalAtaReq0 = (PATA_REQ)ExAllocatePool(NonPagedPool, sizeof(ATA_REQ)*deviceExtension->NumberChannels); 2828 if (!deviceExtension->AhciInternalAtaReq0) { 2829 KdPrint2((PRINT_PREFIX "!deviceExtension->AhciInternalAtaReq0 => SP_RETURN_ERROR\n")); 2830 return FALSE; 2831 } 2832 RtlZeroMemory(deviceExtension->AhciInternalAtaReq0, sizeof(ATA_REQ)*deviceExtension->NumberChannels); 2833 } 2834 if(!deviceExtension->AhciInternalSrb0) { 2835 deviceExtension->AhciInternalSrb0 = (PSCSI_REQUEST_BLOCK)ExAllocatePool(NonPagedPool, sizeof(SCSI_REQUEST_BLOCK)*deviceExtension->NumberChannels); 2836 if (!deviceExtension->AhciInternalSrb0) { 2837 KdPrint2((PRINT_PREFIX "!deviceExtension->AhciInternalSrb0 => SP_RETURN_ERROR\n")); 2838 UniataFreeLunExt(deviceExtension); 2839 return FALSE; 2840 } 2841 RtlZeroMemory(deviceExtension->AhciInternalSrb0, sizeof(SCSI_REQUEST_BLOCK)*deviceExtension->NumberChannels); 2842 } 2843 } 2844 2845 deviceExtension->lun = (PHW_LU_EXTENSION)ExAllocatePool(NonPagedPool, sizeof(HW_LU_EXTENSION) * (deviceExtension->NumberChannels+1) * deviceExtension->NumberLuns); 2846 if (!deviceExtension->lun) { 2847 KdPrint2((PRINT_PREFIX "!deviceExtension->lun => SP_RETURN_ERROR\n")); 2848 UniataFreeLunExt(deviceExtension); 2849 return FALSE; 2850 } 2851 RtlZeroMemory(deviceExtension->lun, sizeof(HW_LU_EXTENSION) * (deviceExtension->NumberChannels+1) * deviceExtension->NumberLuns); 2852 2853 deviceExtension->chan = (PHW_CHANNEL)ExAllocatePool(NonPagedPool, sizeof(HW_CHANNEL) * (deviceExtension->NumberChannels+1)); 2854 if (!deviceExtension->chan) { 2855 UniataFreeLunExt(deviceExtension); 2856 KdPrint2((PRINT_PREFIX "!deviceExtension->chan => SP_RETURN_ERROR\n")); 2857 return FALSE; 2858 } 2859 RtlZeroMemory(deviceExtension->chan, sizeof(HW_CHANNEL) * (deviceExtension->NumberChannels+1)); 2860 return TRUE; 2861 } // end UniataAllocateLunExt() 2862 2863 VOID 2864 NTAPI 2865 UniataFreeLunExt( 2866 PHW_DEVICE_EXTENSION deviceExtension 2867 ) 2868 { 2869 if (deviceExtension->lun) { 2870 ExFreePool(deviceExtension->lun); 2871 deviceExtension->lun = NULL; 2872 } 2873 if (deviceExtension->chan) { 2874 ExFreePool(deviceExtension->chan); 2875 deviceExtension->chan = NULL; 2876 } 2877 if(deviceExtension->AhciInternalAtaReq0) { 2878 ExFreePool(deviceExtension->AhciInternalAtaReq0); 2879 deviceExtension->AhciInternalAtaReq0 = NULL; 2880 } 2881 if(deviceExtension->AhciInternalSrb0) { 2882 ExFreePool(deviceExtension->AhciInternalSrb0); 2883 deviceExtension->AhciInternalSrb0 = NULL; 2884 } 2885 2886 return; 2887 } // end UniataFreeLunExt() 2888 2889