3 Copyright (c) 2004-2012 Alexandr A. Telyatnikov (Alter)
9 This is the chip-specific init module for ATA/ATAPI IDE controllers
10 with Busmaster DMA and Serial ATA support
13 Alexander A. Telyatnikov (Alter)
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.
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
39 added support for non-standard layout of registers
48 UniataChipDetectChannels(
49 IN PVOID HwDeviceExtension
,
50 IN PPCI_COMMON_CONFIG pciData
, // optional
51 IN ULONG DeviceNumber
,
52 IN PPORT_CONFIGURATION_INFORMATION ConfigInfo
55 PHW_DEVICE_EXTENSION deviceExtension
= (PHW_DEVICE_EXTENSION
)HwDeviceExtension
;
56 //ULONG slotNumber = deviceExtension->slotNumber;
57 //ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber;
58 ULONG VendorID
= deviceExtension
->DevID
& 0xffff;
59 //ULONG DeviceID = (deviceExtension->DevID >> 16) & 0xffff;
60 //ULONG RevID = deviceExtension->RevID;
61 ULONG ChipType
= deviceExtension
->HwFlags
& CHIPTYPE_MASK
;
62 ULONG ChipFlags
= deviceExtension
->HwFlags
& CHIPFLAG_MASK
;
64 KdPrint2((PRINT_PREFIX
"UniataChipDetectChannels:\n" ));
66 if(ChipFlags
& (UNIATA_SATA
| UNIATA_AHCI
)) {
67 if(!deviceExtension
->NumberChannels
) {
68 KdPrint2((PRINT_PREFIX
"uninitialized SATA/AHCI port number -> 1\n"));
69 deviceExtension
->NumberChannels
= 1;
71 if(AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"IgnoreAhciPM", 1 /* DEBUG */)) {
72 KdPrint2((PRINT_PREFIX
"SATA/AHCI w/o PM, max luns 1 or 2\n"));
73 deviceExtension
->NumberLuns
= 2; // we may be in Legacy mode
74 //chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE;
76 KdPrint2((PRINT_PREFIX
"SATA/AHCI -> possible PM, max luns %d\n", SATA_MAX_PM_UNITS
));
77 deviceExtension
->NumberLuns
= SATA_MAX_PM_UNITS
;
78 //deviceExtension->NumberLuns = 1;
81 if(deviceExtension
->MasterDev
) {
82 KdPrint2((PRINT_PREFIX
"MasterDev -> 1 chan\n"));
83 deviceExtension
->NumberChannels
= 1;
87 case ATA_ACER_LABS_ID
:
88 switch(deviceExtension
->DevID
) {
91 deviceExtension
->NumberChannels
= 4;
92 KdPrint2((PRINT_PREFIX
"Acer 4 chan\n"));
97 if(ChipType
!= PRMIO
) {
100 deviceExtension
->NumberChannels
= 4;
101 KdPrint2((PRINT_PREFIX
"Promise 4 chan\n"));
104 KdPrint2((PRINT_PREFIX
"Marvell\n"));
105 switch(deviceExtension
->DevID
) {
107 /* 88SX6101 only have 1 PATA channel */
108 if(BMList
[deviceExtension
->DevIndex
].channel
) {
109 KdPrint2((PRINT_PREFIX
"88SX6101 has no 2nd PATA chan\n"));
112 deviceExtension
->NumberChannels
= 1;
113 KdPrint2((PRINT_PREFIX
"88SX6101 PATA 1 chan\n"));
118 KdPrint2((PRINT_PREFIX
"ATI\n"));
119 switch(deviceExtension
->DevID
) {
122 /* IXP600 & IXP700 only have 1 PATA channel */
123 if(BMList
[deviceExtension
->DevIndex
].channel
) {
124 KdPrint2((PRINT_PREFIX
"New ATI no 2nd PATA chan\n"));
127 deviceExtension
->NumberChannels
= 1;
128 KdPrint2((PRINT_PREFIX
"New ATI PATA 1 chan\n"));
132 case ATA_SILICON_IMAGE_ID
:
134 if(ChipFlags
& SIIBUG
) {
135 /* work around errata in early chips */
136 deviceExtension
->DmaSegmentLength
= 15 * DEV_BSIZE
;
137 deviceExtension
->DmaSegmentAlignmentMask
= 8192-1;
139 if(ChipType
!= SIIMIO
) {
146 if(VendorID
== ATA_SILICON_IMAGE_ID
) {
147 KdPrint2((PRINT_PREFIX
"New SII\n"));
149 KdPrint2((PRINT_PREFIX
"ATI SATA\n"));
151 if(deviceExtension
->HwFlags
& SII4CH
) {
152 deviceExtension
->NumberChannels
= 4;
153 KdPrint2((PRINT_PREFIX
"4 chan\n"));
157 if(/*(deviceExtension->DevID == 0x32491106) &&
158 ScsiPortConvertPhysicalAddressToUlong((*ConfigInfo->AccessRanges)[5].RangeStart)*/
159 deviceExtension
->HwFlags
& VIABAR
) {
160 deviceExtension
->NumberChannels
= 3;
161 KdPrint2((PRINT_PREFIX
"VIA 3 chan\n"));
163 if(ChipFlags
& VIASATA
) {
164 /* 2 SATA without SATA registers on first channel + 1 PATA on second */
165 // do nothing, generic PATA INIT
166 KdPrint2((PRINT_PREFIX
"VIA SATA without SATA regs -> no PM\n"));
167 deviceExtension
->NumberLuns
= 1;
171 /* ITE ATA133 controller */
172 if(deviceExtension
->DevID
== 0x82131283) {
173 if(BMList
[deviceExtension
->DevIndex
].channel
) {
174 KdPrint2((PRINT_PREFIX
"New ITE has no 2nd PATA chan\n"));
177 deviceExtension
->NumberChannels
= 1;
178 KdPrint2((PRINT_PREFIX
"New ITE PATA 1 chan\n"));
183 /* New Intel PATA controllers */
184 if(g_opt_VirtualMachine
!= VM_VBOX
&&
185 /*deviceExtension->DevID == 0x27df8086 ||
186 deviceExtension->DevID == 0x269e8086 ||
187 deviceExtension->DevID == ATA_I82801HBM*/
189 if(BMList
[deviceExtension
->DevIndex
].channel
) {
190 KdPrint2((PRINT_PREFIX
"New Intel PATA has no 2nd chan\n"));
193 deviceExtension
->NumberChannels
= 1;
194 KdPrint2((PRINT_PREFIX
"New Intel PATA 1 chan\n"));
197 #endif // this code is removed from newer FreeBSD
199 /* New JMicron PATA controllers */
200 if(deviceExtension
->DevID
== ATA_JMB361
||
201 deviceExtension
->DevID
== ATA_JMB363
||
202 deviceExtension
->DevID
== ATA_JMB368
) {
203 if(BMList
[deviceExtension
->DevIndex
].channel
) {
204 KdPrint2((PRINT_PREFIX
"New JMicron has no 2nd chan\n"));
207 deviceExtension
->NumberChannels
= 1;
208 KdPrint2((PRINT_PREFIX
"New JMicron PATA 1 chan\n"));
211 } // end switch(VendorID)
214 } // end UniataChipDetectChannels()
219 IN PVOID HwDeviceExtension
,
220 IN PPCI_COMMON_CONFIG pciData
, // optional
221 IN ULONG DeviceNumber
,
222 IN OUT PPORT_CONFIGURATION_INFORMATION ConfigInfo
,
223 IN BOOLEAN
* simplexOnly
226 PHW_DEVICE_EXTENSION deviceExtension
= (PHW_DEVICE_EXTENSION
)HwDeviceExtension
;
227 ULONG slotNumber
= deviceExtension
->slotNumber
;
228 ULONG SystemIoBusNumber
= deviceExtension
->SystemIoBusNumber
;
229 ULONG VendorID
= deviceExtension
->DevID
& 0xffff;
230 ULONG DeviceID
= (deviceExtension
->DevID
>> 16) & 0xffff;
231 ULONG RevID
= deviceExtension
->RevID
;
233 BUSMASTER_CONTROLLER_INFORMATION
* DevTypeInfo
;
239 ULONG BaseMemAddress
;
240 ULONG BaseIoAddress1
;
241 ULONG BaseIoAddress2
;
242 ULONG BaseIoAddressBM
;
243 BOOLEAN MemIo
= FALSE
;
245 KdPrint2((PRINT_PREFIX
"UniataChipDetect:\n" ));
246 KdPrint2((PRINT_PREFIX
"HwFlags: %#x\n", deviceExtension
->HwFlags
));
248 i
= Ata_is_dev_listed((PBUSMASTER_CONTROLLER_INFORMATION
)&BusMasterAdapters
[0], VendorID
, 0xffff, 0, NUM_BUSMASTER_ADAPTERS
);
250 c
= AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"ForceSimplex", 0);
256 BaseIoAddressBM
= pciData
->u
.type0
.BaseAddresses
[4] & ~0x07;
257 deviceExtension
->MaxTransferMode
= BaseIoAddressBM
? ATA_DMA
: ATA_PIO4
;
258 ConfigInfo
->MaximumTransferLength
= DEV_BSIZE
*256;
259 deviceExtension
->MaximumDmaTransferLength
= ConfigInfo
->MaximumTransferLength
;
260 //deviceExtension->NumberOfPhysicalBreaks = min(deviceExtension->MaximumDmaTransferLength/PAGE_SIZE+1, ATA_DMA_ENTRIES);
261 deviceExtension
->DmaSegmentLength
= 0x10000;
262 deviceExtension
->DmaSegmentAlignmentMask
= 0xffff;
264 KdPrint2((PRINT_PREFIX
"i: %#x\n", i
));
265 if(i
!= BMLIST_TERMINATOR
) {
266 DevTypeInfo
= (PBUSMASTER_CONTROLLER_INFORMATION
)&BusMasterAdapters
[i
];
269 if(Ata_is_ahci_dev(pciData
)) {
270 KdPrint2((PRINT_PREFIX
" AHCI candidate"));
272 deviceExtension
->NumberChannels
= 0;
273 if(!UniataAhciDetect(HwDeviceExtension
, pciData
, ConfigInfo
)) {
274 KdPrint2((PRINT_PREFIX
" AHCI init failed - not detected\n"));
275 return STATUS_UNSUCCESSFUL
;
277 KdPrint2((PRINT_PREFIX
" unknown AHCI dev, addr %#x ", deviceExtension
->BaseIoAHCI_0
.Addr
));
279 KdPrint2((PRINT_PREFIX
" unknown dev, BM addr %#x ", BaseIoAddressBM
));
281 KdPrint2((PRINT_PREFIX
" MaxTransferMode %#x\n", deviceExtension
->MaxTransferMode
));
283 if(!UniataChipDetectChannels(HwDeviceExtension
, pciData
, DeviceNumber
, ConfigInfo
)) {
284 return STATUS_UNSUCCESSFUL
;
286 if(!UniataAllocateLunExt(deviceExtension
, UNIATA_ALLOCATE_NEW_LUNS
)) {
287 return STATUS_UNSUCCESSFUL
;
289 // DEBUG, we shall return success when AHCI is completly supported
290 //return STATUS_NOT_FOUND;
291 return STATUS_SUCCESS
;
294 static BUSMASTER_CONTROLLER_INFORMATION
const SiSAdapters
[] = {
295 PCI_DEV_HW_SPEC_BM( 0182, 1039, 0x00, ATA_SA150
, "SiS 182" , SISSATA
| UNIATA_SATA
),
296 PCI_DEV_HW_SPEC_BM( 0181, 1039, 0x00, ATA_SA150
, "SiS 181" , SISSATA
| UNIATA_SATA
),
297 PCI_DEV_HW_SPEC_BM( 0180, 1039, 0x00, ATA_SA150
, "SiS 180" , SISSATA
| UNIATA_SATA
),
298 PCI_DEV_HW_SPEC_BM( 0965, 1039, 0x00, ATA_UDMA6
, "SiS 965" , SIS133NEW
),
299 PCI_DEV_HW_SPEC_BM( 0964, 1039, 0x00, ATA_UDMA6
, "SiS 964" , SIS133NEW
),
300 PCI_DEV_HW_SPEC_BM( 0963, 1039, 0x00, ATA_UDMA6
, "SiS 963" , SIS133NEW
),
301 PCI_DEV_HW_SPEC_BM( 0962, 1039, 0x00, ATA_UDMA6
, "SiS 962" , SIS133NEW
),
303 PCI_DEV_HW_SPEC_BM( 0745, 1039, 0x00, ATA_UDMA5
, "SiS 745" , SIS100NEW
),
304 PCI_DEV_HW_SPEC_BM( 0735, 1039, 0x00, ATA_UDMA5
, "SiS 735" , SIS100NEW
),
305 PCI_DEV_HW_SPEC_BM( 0733, 1039, 0x00, ATA_UDMA5
, "SiS 733" , SIS100NEW
),
306 PCI_DEV_HW_SPEC_BM( 0730, 1039, 0x00, ATA_UDMA5
, "SiS 730" , SIS100OLD
),
308 PCI_DEV_HW_SPEC_BM( 0646, 1039, 0x00, ATA_UDMA6
, "SiS 645DX", SIS133NEW
),
309 /* PCI_DEV_HW_SPEC_BM( 0645, 1039, 0x00, ATA_UDMA6, "SiS 645" , SIS133NEW ),*/
310 /* PCI_DEV_HW_SPEC_BM( 0640, 1039, 0x00, ATA_UDMA4, "SiS 640" , SIS_SOUTH ),*/
311 PCI_DEV_HW_SPEC_BM( 0635, 1039, 0x00, ATA_UDMA5
, "SiS 635" , SIS100NEW
),
312 PCI_DEV_HW_SPEC_BM( 0633, 1039, 0x00, ATA_UDMA5
, "SiS 633" , SIS100NEW
),
313 PCI_DEV_HW_SPEC_BM( 0630, 1039, 0x00, ATA_UDMA5
, "SiS 630S" , SIS100OLD
),
314 PCI_DEV_HW_SPEC_BM( 0630, 1039, 0x00, ATA_UDMA4
, "SiS 630" , SIS66
),
315 PCI_DEV_HW_SPEC_BM( 0620, 1039, 0x00, ATA_UDMA4
, "SiS 620" , SIS66
),
317 PCI_DEV_HW_SPEC_BM( 0550, 1039, 0x00, ATA_UDMA5
, "SiS 550" , SIS66
),
318 PCI_DEV_HW_SPEC_BM( 0540, 1039, 0x00, ATA_UDMA4
, "SiS 540" , SIS66
),
319 PCI_DEV_HW_SPEC_BM( 0530, 1039, 0x00, ATA_UDMA4
, "SiS 530" , SIS66
),
321 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x04, ATA_UDMA6, "SiS 962L" , SIS133OLD ), // ???
322 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x00, ATA_UDMA6, "SiS 961" , SIS133OLD ),
324 PCI_DEV_HW_SPEC_BM( 5517, 1039, 0x00, ATA_UDMA5
, "SiS 961" , SIS100NEW
| SIS_BASE
),
325 PCI_DEV_HW_SPEC_BM( 5518, 1039, 0x00, ATA_UDMA6
, "SiS 962/3", SIS133NEW
| SIS_BASE
),
326 PCI_DEV_HW_SPEC_BM( 5513, 1039, 0xc2, ATA_UDMA2
, "SiS 5513" , SIS33
| SIS_BASE
),
327 PCI_DEV_HW_SPEC_BM( 5513, 1039, 0x00, ATA_WDMA2
, "SiS 5513" , SIS33
| SIS_BASE
),
328 PCI_DEV_HW_SPEC_BM( 0601, 1039, 0x00, ATA_UDMA2
, "SiS 5513" , SIS33
| SIS_BASE
),
329 PCI_DEV_HW_SPEC_BM( ffff
, ffff
, 0xff, BMLIST_TERMINATOR
, NULL
, BMLIST_TERMINATOR
)
332 static BUSMASTER_CONTROLLER_INFORMATION
const ViaAdapters
[] = {
333 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x41, ATA_UDMA2
, "VIA 82C586B", VIA33
| 0x00 ),
334 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x40, ATA_UDMA2
, "VIA 82C586B", VIA33
| VIAPRQ
),
335 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x02, ATA_UDMA2
, "VIA 82C586B", VIA33
| 0x00 ),
336 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x00, ATA_WDMA2
, "VIA 82C586" , VIA33
| 0x00 ),
337 PCI_DEV_HW_SPEC_BM( 0596, 1106, 0x12, ATA_UDMA4
, "VIA 82C596B", VIA66
| VIACLK
),
338 PCI_DEV_HW_SPEC_BM( 0596, 1106, 0x00, ATA_UDMA2
, "VIA 82C596" , VIA33
| 0x00 ),
339 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x40, ATA_UDMA5
, "VIA 82C686B", VIA100
| VIABUG
),
340 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x10, ATA_UDMA4
, "VIA 82C686A", VIA66
| VIACLK
),
341 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x00, ATA_UDMA2
, "VIA 82C686" , VIA33
| 0x00 ),
342 PCI_DEV_HW_SPEC_BM( 8231, 1106, 0x00, ATA_UDMA5
, "VIA 8231" , VIA100
| VIABUG
),
343 PCI_DEV_HW_SPEC_BM( 3074, 1106, 0x00, ATA_UDMA5
, "VIA 8233" , VIA100
| 0x00 ),
344 PCI_DEV_HW_SPEC_BM( 3109, 1106, 0x00, ATA_UDMA5
, "VIA 8233C" , VIA100
| 0x00 ),
345 PCI_DEV_HW_SPEC_BM( 3147, 1106, 0x00, ATA_UDMA6
, "VIA 8233A" , VIA133
| 0x00 ),
346 PCI_DEV_HW_SPEC_BM( 3177, 1106, 0x00, ATA_UDMA6
, "VIA 8235" , VIA133
| 0x00 ),
347 PCI_DEV_HW_SPEC_BM( 3227, 1106, 0x00, ATA_UDMA6
, "VIA 8237" , VIA133
| 0x00 ),
348 PCI_DEV_HW_SPEC_BM( 0591, 1106, 0x00, ATA_UDMA6
, "VIA 8237A" , VIA133
| 0x00 ),
349 // presence of AHCI controller means something about isa-mapped part
350 PCI_DEV_HW_SPEC_BM( 5337, 1106, 0x00, ATA_UDMA6
, "VIA 8237S" , VIA133
| 0x00 ),
351 PCI_DEV_HW_SPEC_BM( 5372, 1106, 0x00, ATA_UDMA6
, "VIA 8237" , VIA133
| 0x00 ),
352 PCI_DEV_HW_SPEC_BM( 7372, 1106, 0x00, ATA_UDMA6
, "VIA 8237" , VIA133
| 0x00 ),
353 PCI_DEV_HW_SPEC_BM( 3349, 1106, 0x00, ATA_UDMA6
, "VIA 8251" , VIA133
| 0x00 ),
354 PCI_DEV_HW_SPEC_BM( 8324, 1106, 0x00, ATA_SA150
, "VIA CX700" , VIA133
| VIASATA
),
355 PCI_DEV_HW_SPEC_BM( 8353, 1106, 0x00, ATA_SA150
, "VIA VX800" , VIA133
| VIASATA
),
356 PCI_DEV_HW_SPEC_BM( 8409, 1106, 0x00, ATA_UDMA6
, "VIA VX855" , VIA133
| 0x00 ),
357 PCI_DEV_HW_SPEC_BM( 8410, 1106, 0x00, ATA_SA300
, "VIA VX900" , VIA133
| VIASATA
),
358 PCI_DEV_HW_SPEC_BM( ffff
, ffff
, 0xff, BMLIST_TERMINATOR
, NULL
, BMLIST_TERMINATOR
)
361 static BUSMASTER_CONTROLLER_INFORMATION
const ViaSouthAdapters
[] = {
362 PCI_DEV_HW_SPEC_BM( 3112, 1106, 0x00, ATA_MODE_NOT_SPEC
, "VIA 8361", VIASOUTH
),
363 PCI_DEV_HW_SPEC_BM( 0305, 1106, 0x00, ATA_MODE_NOT_SPEC
, "VIA 8363", VIASOUTH
),
364 PCI_DEV_HW_SPEC_BM( 0391, 1106, 0x00, ATA_MODE_NOT_SPEC
, "VIA 8371", VIASOUTH
),
365 PCI_DEV_HW_SPEC_BM( 3102, 1106, 0x00, ATA_MODE_NOT_SPEC
, "VIA 8662", VIASOUTH
),
366 PCI_DEV_HW_SPEC_BM( ffff
, ffff
, 0xff, BMLIST_TERMINATOR
, NULL
, BMLIST_TERMINATOR
)
369 KdPrint2((PRINT_PREFIX
"VendorID/DeviceID/Rev %#x/%#x/%#x\n", VendorID
, DeviceID
, RevID
));
374 KdPrint2((PRINT_PREFIX
"ATA_SIS_ID\n"));
375 DevTypeInfo
= (BUSMASTER_CONTROLLER_INFORMATION
*)&SiSAdapters
[0];
376 i
= AtapiFindListedDev(DevTypeInfo
, -1, HwDeviceExtension
, SystemIoBusNumber
, PCISLOTNUM_NOT_SPECIFIED
, NULL
);
377 if(i
!= BMLIST_TERMINATOR
) {
378 deviceExtension
->FullDevName
= SiSAdapters
[i
].FullDevName
;
383 KdPrint2((PRINT_PREFIX
"ATA_VIA_ID\n"));
384 // New chips have own DeviceId
385 if(deviceExtension
->DevID
!= ATA_VIA82C571
&&
386 deviceExtension
->DevID
!= ATA_VIACX700IDE
&&
387 deviceExtension
->DevID
!= ATA_VIASATAIDE
&&
388 deviceExtension
->DevID
!= ATA_VIASATAIDE2
&&
389 deviceExtension
->DevID
!= ATA_VIASATAIDE3
) {
390 KdPrint2((PRINT_PREFIX
"Via new\n"));
393 KdPrint2((PRINT_PREFIX
"Via-old-style %x\n", deviceExtension
->DevID
));
394 // Traditionally, chips have same DeviceId, we can distinguish between them
395 // only by ISA Bridge DeviceId
396 DevTypeInfo
= (BUSMASTER_CONTROLLER_INFORMATION
*)&ViaSouthAdapters
[0];
397 i
= AtapiFindListedDev(DevTypeInfo
, -1, HwDeviceExtension
, SystemIoBusNumber
,
398 PCISLOTNUM_NOT_SPECIFIED
/*slotNumber*/, NULL
);
399 /* if(i == BMLIST_TERMINATOR) {
400 i = AtapiFindListedDev(DevTypeInfo, -1, HwDeviceExtension, SystemIoBusNumber, PCISLOTNUM_NOT_SPECIFIED, NULL);
402 if(i
!= BMLIST_TERMINATOR
) {
403 KdPrint2((PRINT_PREFIX
"VIASOUTH\n"));
404 deviceExtension
->HwFlags
|= VIASOUTH
;
406 DevTypeInfo
= (BUSMASTER_CONTROLLER_INFORMATION
*)&ViaAdapters
[0];
407 i
= AtapiFindListedDev(DevTypeInfo
, -1, HwDeviceExtension
, SystemIoBusNumber
,
408 PCISLOTNUM_NOT_SPECIFIED
/*slotNumber*/, NULL
);
409 if(i
!= BMLIST_TERMINATOR
) {
410 deviceExtension
->FullDevName
= ViaAdapters
[i
].FullDevName
;
420 KdPrint2((PRINT_PREFIX
"Default\n"));
422 deviceExtension
->MaxTransferMode
= deviceExtension
->BaseIoAddressBM_0
? ATA_DMA
: ATA_PIO4
;
423 /* do extra chipset specific setups */
424 switch(deviceExtension
->DevID
) {
426 //case ATA_CYPRESS_ID:
427 case 0xc6931080: /* 82c693 ATA controller */
428 deviceExtension
->MaxTransferMode
= ATA_WDMA2
;
431 case 0x000116ca: /* Cenatek Rocket Drive controller */
432 deviceExtension
->MaxTransferMode
= ATA_WDMA2
;
435 /* case ATA_CYRIX_ID:
436 DevTypeInfo = &CyrixAdapters[0];
438 case 0x01021078: /* Cyrix 5530 ATA33 controller */
439 deviceExtension
->MaxTransferMode
= ATA_UDMA2
;
442 case 0x06401039: /* CMD 640 known bad, no DMA */
448 case 0x10001042: /* RZ 100x known bad, no DMA */
451 if(deviceExtension
->BaseIoAddressBM_0
)
452 ScsiPortFreeDeviceBase(HwDeviceExtension
,
453 deviceExtension
->BaseIoAddressBM_0
);
455 deviceExtension
->BaseIoAddressBM_0
= 0;
456 deviceExtension
->BusMaster
= DMA_MODE_NONE
;
457 deviceExtension
->MaxTransferMode
= ATA_PIO4
;
460 case 0x81721283: /* IT8172 IDE controller */
461 deviceExtension
->MaxTransferMode
= ATA_UDMA2
;
466 return STATUS_NOT_FOUND
;
468 return STATUS_SUCCESS
;
472 i
= Ata_is_dev_listed(DevTypeInfo
, VendorID
, DeviceID
, RevID
, -1);
474 KdPrint2((PRINT_PREFIX
"i: %#x\n", i
));
475 if(i
== BMLIST_TERMINATOR
) {
477 //return STATUS_NOT_FOUND;
479 deviceExtension
->MaxTransferMode
= DevTypeInfo
[i
].MaxTransferMode
;
480 deviceExtension
->HwFlags
|= DevTypeInfo
[i
].RaidFlags
;
482 KdPrint2((PRINT_PREFIX
"HwFlags: %#x\n", deviceExtension
->HwFlags
));
484 tmp32
= AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"HwFlagsOverride", deviceExtension
->HwFlags
);
485 KdPrint2((PRINT_PREFIX
"HwFlagsOverride: %#x\n", tmp32
));
486 deviceExtension
->HwFlags
= tmp32
;
488 tmp32
= AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"HwFlagsAdd", 0);
489 KdPrint2((PRINT_PREFIX
"HwFlagsAdd: %#x\n", tmp32
));
490 deviceExtension
->HwFlags
|= tmp32
;
492 KdPrint2((PRINT_PREFIX
"HwFlags (final): %#x\n", deviceExtension
->HwFlags
));
493 if(deviceExtension
->HwFlags
& UNIATA_SIMPLEX_ONLY
) {
494 KdPrint2((PRINT_PREFIX
"UNIATA_SIMPLEX_ONLY\n" ));
498 KdPrint2((PRINT_PREFIX
"MaxTransferMode: %#x\n", deviceExtension
->MaxTransferMode
));
499 tmp32
= AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"MaxTransferMode", deviceExtension
->MaxTransferMode
);
500 if(tmp32
!= 0xffffffff) {
501 KdPrint2((PRINT_PREFIX
"MaxTransferMode (overriden): %#x\n", deviceExtension
->MaxTransferMode
));
502 deviceExtension
->MaxTransferMode
= tmp32
;
505 if(deviceExtension
->MaxTransferMode
>= ATA_SA150
) {
506 deviceExtension
->HwFlags
|= UNIATA_SATA
;
509 ConfigInfo->MaximumTransferLength = DEV_BSIZE*256;
510 deviceExtension->MaximumDmaTransferLength = ConfigInfo->MaximumTransferLength;
512 ChipType
= deviceExtension
->HwFlags
& CHIPTYPE_MASK
;
513 ChipFlags
= deviceExtension
->HwFlags
& CHIPFLAG_MASK
;
515 if(ChipFlags
& UNIATA_AHCI
) {
516 deviceExtension
->NumberChannels
= 0;
517 if(!UniataAhciDetect(HwDeviceExtension
, pciData
, ConfigInfo
)) {
518 KdPrint2((PRINT_PREFIX
" AHCI detect failed\n"));
519 return STATUS_UNSUCCESSFUL
;
522 if(!UniataChipDetectChannels(HwDeviceExtension
, pciData
, DeviceNumber
, ConfigInfo
)) {
523 return STATUS_UNSUCCESSFUL
;
525 // UniataAhciDetect() sets proper number of channels
526 if(!UniataAllocateLunExt(deviceExtension
, UNIATA_ALLOCATE_NEW_LUNS
)) {
527 return STATUS_UNSUCCESSFUL
;
530 if(ChipFlags
& UNIATA_AHCI
) {
534 case ATA_ACER_LABS_ID
:
535 if(ChipFlags
& UNIATA_SATA
) {
536 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
537 BaseIoAddress1
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
539 BaseIoAddress2
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
541 BaseIoAddressBM
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
542 4, 0, deviceExtension
->NumberChannels
*sizeof(IDE_BUSMASTER_REGISTERS
));
543 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
544 //ULONG unit01 = (c & 1);
545 ULONG unit10
= (c
& 2);
546 chan
= &deviceExtension
->chan
[c
];
548 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
549 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseIoAddress1
+ i
+ (unit10
? 8 : 0);
551 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseIoAddress2
+ 2 + (unit10
? 4 : 0);
552 UniataInitSyncBaseIO(chan
);
554 for (i
=0; i
<=IDX_BM_IO_SZ
; i
++) {
555 chan
->RegTranslation
[IDX_BM_IO
+i
].Addr
= BaseIoAddressBM
+ i
+ (c
* sizeof(IDE_BUSMASTER_REGISTERS
));
558 // SATA not supported yet
560 //chan->RegTranslation[IDX_BM_Command] = BaseMemAddress + 0x260 + offs7;
561 //chan->RegTranslation[IDX_BM_PRD_Table] = BaseMemAddress + 0x244 + offs7;
562 //chan->RegTranslation[IDX_BM_DeviceSpecific0] = BaseMemAddress + (c << 2);
564 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
569 if(ChipFlags
& UNIATA_SATA
) {
570 KdPrint2((PRINT_PREFIX
"NVIDIA SATA\n"));
571 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
572 5, 0, ((ChipFlags
& NV4OFF
) ? 0x400 : 0) + 0x40*2);
573 KdPrint2((PRINT_PREFIX
"BaseMemAddress %x\n", BaseMemAddress
));
574 if((*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
575 KdPrint2((PRINT_PREFIX
"MemIo\n"));
578 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
579 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
580 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
581 chan
= &deviceExtension
->chan
[c
];
583 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ (c
<< 6);
584 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
585 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ 4 + (c
<< 6);
586 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
587 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ 8 + (c
<< 6);
588 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
590 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
596 if(ChipType
!= PRMIO
) {
602 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
603 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
605 KdPrint2((PRINT_PREFIX
"BaseMemAddress %x\n", BaseMemAddress
));
606 if((*ConfigInfo
->AccessRanges
)[4].RangeInMemory
) {
607 KdPrint2((PRINT_PREFIX
"MemIo\n"));
610 deviceExtension
->BaseIoAddressBM_0
.Addr
= BaseMemAddress
;
611 deviceExtension
->BaseIoAddressBM_0
.MemIo
= MemIo
;
612 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
616 chan
= &deviceExtension
->chan
[c
];
621 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
622 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseMemAddress
+ 0x200 + (i
<< 2) + offs12
;
623 chan
->RegTranslation
[IDX_IO1
+i
].MemIo
= MemIo
;
625 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseMemAddress
+ 0x238 + offs7
;
626 chan
->RegTranslation
[IDX_IO2_AltStatus
].MemIo
= MemIo
;
628 UniataInitSyncBaseIO(chan
);
630 chan
->RegTranslation
[IDX_BM_Command
].Addr
= BaseMemAddress
+ 0x260 + offs7
;
631 chan
->RegTranslation
[IDX_BM_Command
].MemIo
= MemIo
;
632 chan
->RegTranslation
[IDX_BM_PRD_Table
].Addr
= BaseMemAddress
+ 0x244 + offs7
;
633 chan
->RegTranslation
[IDX_BM_PRD_Table
].MemIo
= MemIo
;
634 chan
->RegTranslation
[IDX_BM_DeviceSpecific0
].Addr
= BaseMemAddress
+ (c
<< 2);
635 chan
->RegTranslation
[IDX_BM_DeviceSpecific0
].MemIo
= MemIo
;
640 KdPrint2((PRINT_PREFIX
"ATI\n"));
642 case ATA_SILICON_IMAGE_ID
: {
644 if(ChipFlags
& SIIBUG
) {
646 if(ChipType
!= SIIMIO
) {
653 if(VendorID
== ATA_SILICON_IMAGE_ID
) {
654 KdPrint2((PRINT_PREFIX
"New SII\n"));
656 KdPrint2((PRINT_PREFIX
"ATI SATA\n"));
658 //if(deviceExtension->HwFlags & SII4CH) {
659 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
661 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
663 KdPrint2((PRINT_PREFIX
"BaseMemAddress %x\n", BaseMemAddress
));
664 if((*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
665 KdPrint2((PRINT_PREFIX
"MemIo\n"));
668 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
669 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
671 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
672 ULONG unit01
= (c
& 1);
673 ULONG unit10
= (c
& 2);
675 chan
= &deviceExtension
->chan
[c
];
677 if(deviceExtension
->AltRegMap
) {
678 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
679 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseMemAddress
+ 0x80 + i
+ (unit01
<< 6) + (unit10
<< 8);
680 chan
->RegTranslation
[IDX_IO1
+i
].MemIo
= MemIo
;
682 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseMemAddress
+ 0x8a + (unit01
<< 6) + (unit10
<< 8);
683 chan
->RegTranslation
[IDX_IO2_AltStatus
].MemIo
= MemIo
;
684 UniataInitSyncBaseIO(chan
);
686 chan
->RegTranslation
[IDX_BM_Command
].Addr
= BaseMemAddress
+ 0x00 + (unit01
<< 3) + (unit10
<< 8);
687 chan
->RegTranslation
[IDX_BM_Command
].MemIo
= MemIo
;
688 chan
->RegTranslation
[IDX_BM_Status
].Addr
= BaseMemAddress
+ 0x02 + (unit01
<< 3) + (unit10
<< 8);
689 chan
->RegTranslation
[IDX_BM_Status
].MemIo
= MemIo
;
690 chan
->RegTranslation
[IDX_BM_PRD_Table
].Addr
= BaseMemAddress
+ 0x04 + (unit01
<< 3) + (unit10
<< 8);
691 chan
->RegTranslation
[IDX_BM_PRD_Table
].MemIo
= MemIo
;
692 //chan->RegTranslation[IDX_BM_DeviceSpecific0].Addr = BaseMemAddress + 0xa1 + (unit01 << 6) + (unit10 << 8);
693 //chan->RegTranslation[IDX_BM_DeviceSpecific0].MemIo = MemIo;
694 chan
->RegTranslation
[IDX_BM_DeviceSpecific0
].Addr
= BaseMemAddress
+ 0x10 + (unit01
<< 3) + (unit10
<< 8);
695 chan
->RegTranslation
[IDX_BM_DeviceSpecific0
].MemIo
= MemIo
;
696 chan
->RegTranslation
[IDX_BM_DeviceSpecific1
].Addr
= BaseMemAddress
+ 0x40 + (unit01
<< 2) + (unit10
<< 8);
697 chan
->RegTranslation
[IDX_BM_DeviceSpecific1
].MemIo
= MemIo
;
700 if(ChipFlags
& UNIATA_SATA
) {
701 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ 0x104 + (unit01
<< 7) + (unit10
<< 8);
702 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
703 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ 0x108 + (unit01
<< 7) + (unit10
<< 8);
704 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
705 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ 0x100 + (unit01
<< 7) + (unit10
<< 8);
706 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
708 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
713 case ATA_SERVERWORKS_ID
: {
715 if(ChipType
!= SWKSMIO
) {
722 KdPrint2((PRINT_PREFIX
"ServerWorks\n"));
724 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
725 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
727 KdPrint2((PRINT_PREFIX
"BaseMemAddress %x\n", BaseMemAddress
));
728 if((*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
729 KdPrint2((PRINT_PREFIX
"MemIo\n"));
732 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
733 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
735 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
736 ULONG offs
= c
*0x100;
738 chan
= &deviceExtension
->chan
[c
];
739 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
740 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseMemAddress
+ offs
+ i
*4;
741 chan
->RegTranslation
[IDX_IO1
+i
].MemIo
= MemIo
;
743 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseMemAddress
+ offs
+ 0x20;
744 chan
->RegTranslation
[IDX_IO2_AltStatus
].MemIo
= MemIo
;
745 UniataInitSyncBaseIO(chan
);
747 chan
->RegTranslation
[IDX_BM_Command
].Addr
= BaseMemAddress
+ offs
+ 0x30;
748 chan
->RegTranslation
[IDX_BM_Command
].MemIo
= MemIo
;
749 chan
->RegTranslation
[IDX_BM_Status
].Addr
= BaseMemAddress
+ offs
+ 0x32;
750 chan
->RegTranslation
[IDX_BM_Status
].MemIo
= MemIo
;
751 chan
->RegTranslation
[IDX_BM_PRD_Table
].Addr
= BaseMemAddress
+ offs
+ 0x34;
752 chan
->RegTranslation
[IDX_BM_PRD_Table
].MemIo
= MemIo
;
754 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ offs
+ 0x40;
755 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
756 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ offs
+ 0x44;
757 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
758 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ offs
+ 0x48;
759 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
761 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
766 //if(ChipType != SIS_SOUTH) {}
767 BOOLEAN SIS_182
=FALSE
;
769 if(!(ChipFlags
& SIS_BASE
)) {
770 KdPrint2((PRINT_PREFIX
"Found SIS_SOUTH\n"));
771 //PrintNtConsole("Found SIS_SOUTH\n");
774 // Make some additional checks
775 KdPrint2((PRINT_PREFIX
"ChipType == SIS_BASE\n"));
776 ChangePciConfig1(0x57, (a
& 0x7f));
777 GetPciConfig4(0x00, tmp32
);
778 if(tmp32
== ATA_SIS5518
) {
779 ChipType
= SIS133NEW
;
780 deviceExtension
->HwFlags
= (deviceExtension
->HwFlags
& ~CHIPTYPE_MASK
) | SIS133NEW
;
781 deviceExtension
->MaxTransferMode
= ATA_UDMA6
;
782 KdPrint2((PRINT_PREFIX
"UniataChipDetect: SiS 962/963 DMA %#x controller\n", deviceExtension
->MaxTransferMode
));
783 //PrintNtConsole("UniataChipDetect: SiS 962/963 DMA %#x controller\n", deviceExtension->MaxTransferMode);
785 ChangePciConfig1(0x57, (a
| 0x80));
787 static BUSMASTER_CONTROLLER_INFORMATION
const SiSSouthAdapters
[] = {
788 PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x10, ATA_MODE_NOT_SPEC
, "SiS 961", 0 ),
789 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x00, ATA_MODE_NOT_SPEC, "SiS 961", 0 ),
790 PCI_DEV_HW_SPEC_BM( ffff
, ffff
, 0xff, ATA_MODE_NOT_SPEC
, NULL
, -1 )
793 GetPciConfig1(0x4a, tmp8
);
794 ChangePciConfig1(0x4a, (a
| 0x10));
795 if(tmp32
== ATA_SIS5513
||
796 tmp32
== ATA_SIS5517
) {
797 i
= AtapiFindListedDev((BUSMASTER_CONTROLLER_INFORMATION
*)&SiSSouthAdapters
[0],
798 -1, HwDeviceExtension
, SystemIoBusNumber
, PCISLOTNUM_NOT_SPECIFIED
, NULL
);
799 if(i
!= BMLIST_TERMINATOR
) {
800 deviceExtension
->HwFlags
= (deviceExtension
->HwFlags
& ~CHIPTYPE_MASK
) | SIS133OLD
;
801 deviceExtension
->MaxTransferMode
= ATA_UDMA6
;
802 //deviceExtension->MaxTransferMode = SiSSouthAdapters[i].MaxTransferMode;
803 if(SiSSouthAdapters
[i
].RaidFlags
& UNIATA_SATA
) {
804 deviceExtension
->HwFlags
|= UNIATA_SATA
;
805 if(SiSSouthAdapters
[i
].nDeviceId
== 0x1182) {
810 // SiS-South not found
811 if(tmp32
== ATA_SIS5517
) {
812 deviceExtension
->HwFlags
= (deviceExtension
->HwFlags
& ~CHIPTYPE_MASK
) | SIS100NEW
;
813 deviceExtension
->MaxTransferMode
= ATA_UDMA5
;
816 KdPrint2((PRINT_PREFIX
"Generic SiS DMA\n"));
821 SetPciConfig1(0x4a, tmp8
);
822 KdPrint2((PRINT_PREFIX
"UniataChipDetect: SiS 961 DMA %#x controller\n", deviceExtension
->MaxTransferMode
));
823 //PrintNtConsole("UniataChipDetect: SiS 961 DMA %#x controller\n", deviceExtension->MaxTransferMode);
824 if(deviceExtension
->HwFlags
& UNIATA_SATA
) {
825 KdPrint2((PRINT_PREFIX
"SiS SATA\n"));
827 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
829 KdPrint2((PRINT_PREFIX
"BaseMemAddress %x\n", BaseMemAddress
));
830 if((*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
831 KdPrint2((PRINT_PREFIX
"MemIo\n"));
834 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
835 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
837 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
838 ULONG offs
= c
<< (SIS_182
? 5 : 6);
840 chan
= &deviceExtension
->chan
[c
];
841 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ 0 + offs
;
842 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
843 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ 4 + offs
;
844 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
845 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ 8 + offs
;
846 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
848 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
852 //ChangePciConfig1(0x57, (a | 0x80));
857 if(ChipFlags
& VIASATA
) {
858 /* 2 SATA without SATA registers on first channel + 1 PATA on second */
859 // do nothing, generic PATA INIT
860 KdPrint2((PRINT_PREFIX
"VIA SATA without SATA regs\n"));
863 if(ChipFlags
& UNIATA_SATA
) {
866 ULONG BaseMemAddress
= 0;
869 case 0x3149: // VIA 6420
870 KdPrint2((PRINT_PREFIX
"VIA 6420\n"));
873 case 0x3249: // VIA 6421
874 KdPrint2((PRINT_PREFIX
"VIA 6421\n"));
879 KdPrint2((PRINT_PREFIX
"IoSize %x\n", IoSize
));
880 /*deviceExtension->*/BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
881 5, 0, IoSize
* deviceExtension
->NumberChannels
);
882 if(BaseMemAddress
&& (*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
883 KdPrint2((PRINT_PREFIX
"MemIo\n"));
886 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
887 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
889 if(/*deviceExtension->*/BaseMemAddress
) {
890 KdPrint2((PRINT_PREFIX
"UniataChipDetect: BAR5 %x\n", /*deviceExtension->*/BaseMemAddress
));
891 if(ChipFlags
& VIABAR
) {
893 ULONG BaseIoAddressBM_0
;
896 KdPrint2((PRINT_PREFIX
"UniataChipDetect: VIABAR\n"));
897 /*deviceExtension->*/BaseIoAddressBM_0
= /*(PIDE_BUSMASTER_REGISTERS)*/
898 AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
, 4, 0,
899 sizeof(IDE_BUSMASTER_REGISTERS
)*deviceExtension
->NumberChannels
);
900 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
901 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
903 chan
= &deviceExtension
->chan
[c
];
905 BaseIo
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
, c
, 0, /*0x80*/ sizeof(IDE_REGISTERS_1
) + sizeof(IDE_REGISTERS_2
)*2);
907 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
908 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseIo
+ i
;
910 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseIo
+ sizeof(IDE_REGISTERS_1
) + 2;
911 UniataInitSyncBaseIO(chan
);
913 for (i
=0; i
<=IDX_BM_IO_SZ
; i
++) {
914 chan
->RegTranslation
[IDX_BM_IO
+i
].Addr
= BaseIoAddressBM_0
+ sizeof(IDE_BUSMASTER_REGISTERS
)*c
+ i
;
919 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
920 chan
= &deviceExtension
->chan
[c
];
921 if((ChipFlags
& VIABAR
) && (c
==2)) {
922 // Do not setup SATA registers for PATA part
923 for (i
=0; i
<=IDX_SATA_IO_SZ
; i
++) {
924 chan
->RegTranslation
[IDX_SATA_IO
+i
].Addr
= 0;
925 chan
->RegTranslation
[IDX_SATA_IO
+i
].MemIo
= 0;
929 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ (c
* IoSize
);
930 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
931 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ 4 + (c
* IoSize
);
932 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
933 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ 8 + (c
* IoSize
);
934 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
936 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
945 if(!(ChipFlags
& UNIATA_SATA
)) {
949 /* the intel 31244 needs special care if in DPA mode */
950 if(DeviceID
== 3200 && // Intel 31244
951 pciData
->SubClass
!= PCI_DEV_SUBCLASS_IDE
) {
953 KdPrint2((PRINT_PREFIX
"UniataChipDetect: Intel 31244, DPA mode\n"));
954 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
956 if((*ConfigInfo
->AccessRanges
)[0].RangeInMemory
) {
957 KdPrint2((PRINT_PREFIX
"MemIo\n"));
960 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
961 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
962 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
964 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
965 ULONG offs
= 0x200 + c
*0x200;
967 chan
= &deviceExtension
->chan
[c
];
968 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
969 chan
->RegTranslation
[IDX_IO1
+i
].MemIo
= MemIo
;
970 chan
->RegTranslation
[IDX_IO1_o
+i
].MemIo
= MemIo
;
973 chan
->RegTranslation
[IDX_IO1_i_Data
].Addr
= BaseMemAddress
+ 0x00 + offs
;
974 chan
->RegTranslation
[IDX_IO1_i_Error
].Addr
= BaseMemAddress
+ 0x04 + offs
;
975 chan
->RegTranslation
[IDX_IO1_i_BlockCount
].Addr
= BaseMemAddress
+ 0x08 + offs
;
976 chan
->RegTranslation
[IDX_IO1_i_BlockNumber
].Addr
= BaseMemAddress
+ 0x0c + offs
;
977 chan
->RegTranslation
[IDX_IO1_i_CylinderLow
].Addr
= BaseMemAddress
+ 0x10 + offs
;
978 chan
->RegTranslation
[IDX_IO1_i_CylinderHigh
].Addr
= BaseMemAddress
+ 0x14 + offs
;
979 chan
->RegTranslation
[IDX_IO1_i_DriveSelect
].Addr
= BaseMemAddress
+ 0x18 + offs
;
980 chan
->RegTranslation
[IDX_IO1_i_Status
].Addr
= BaseMemAddress
+ 0x1c + offs
;
982 UniataInitSyncBaseIO(chan
);
984 chan
->RegTranslation
[IDX_IO1_o_Command
].Addr
= BaseMemAddress
+ 0x1d + offs
;
985 chan
->RegTranslation
[IDX_IO1_o_Feature
].Addr
= BaseMemAddress
+ 0x06 + offs
;
986 chan
->RegTranslation
[IDX_IO2_o_Control
].Addr
= BaseMemAddress
+ 0x29 + offs
;
988 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseMemAddress
+ 0x28 + offs
;
989 chan
->RegTranslation
[IDX_IO2_AltStatus
].MemIo
= MemIo
;
991 chan
->RegTranslation
[IDX_BM_Command
].Addr
= BaseMemAddress
+ offs
+ 0x70;
992 chan
->RegTranslation
[IDX_BM_Command
].MemIo
= MemIo
;
993 chan
->RegTranslation
[IDX_BM_Status
].Addr
= BaseMemAddress
+ offs
+ 0x72;
994 chan
->RegTranslation
[IDX_BM_Status
].MemIo
= MemIo
;
995 chan
->RegTranslation
[IDX_BM_PRD_Table
].Addr
= BaseMemAddress
+ offs
+ 0x74;
996 chan
->RegTranslation
[IDX_BM_PRD_Table
].MemIo
= MemIo
;
998 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ 0x100 + offs
;
999 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
1000 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ 0x104 + offs
;
1001 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
1002 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ 0x108 + offs
;
1003 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
1005 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1010 if(deviceExtension
->MaxTransferMode
>= ATA_SA150
) {
1011 GetPciConfig1(0x90, tmp8
);
1012 KdPrint2((PRINT_PREFIX
"Intel chip config: %x\n", tmp8
));
1013 /* SATA parts can be either compat or AHCI */
1014 if(ChipFlags
& UNIATA_AHCI
) {
1017 //KdPrint2((PRINT_PREFIX "AHCI not supported yet\n"));
1019 KdPrint2((PRINT_PREFIX
"try run AHCI\n"));
1022 KdPrint2((PRINT_PREFIX
"Compatible mode\n"));
1024 deviceExtension
->HwFlags
&= ~UNIATA_AHCI
;
1026 /* if BAR(5) is IO it should point to SATA interface registers */
1027 if(deviceExtension
->DevID
== 0x28288086 &&
1028 pciData
->u
.type0
.SubVendorID
== 0x106b) {
1029 /* Skip BAR(5) on ICH8M Apples, system locks up on access. */
1030 KdPrint2((PRINT_PREFIX
"Ignore BAR5 on ICH8M Apples\n"));
1033 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
1035 if(BaseMemAddress
&& (*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
1036 KdPrint2((PRINT_PREFIX
"MemIo\n"));
1040 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
1041 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
1043 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
1044 chan
= &deviceExtension
->chan
[c
];
1046 if(ChipFlags
& ICH5
) {
1047 KdPrint2((PRINT_PREFIX
"ICH5\n"));
1048 if ((tmp8
& 0x04) == 0) {
1049 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1050 } else if ((tmp8
& 0x02) == 0) {
1053 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA;
1055 } else if ((tmp8
& 0x02) != 0) {
1058 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA;
1062 if(ChipFlags
& I6CH2
) {
1063 KdPrint2((PRINT_PREFIX
"I6CH2\n"));
1064 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1066 KdPrint2((PRINT_PREFIX
"other Intel\n"));
1067 switch(tmp8
& 0x03) {
1084 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA5
);
1085 KdPrint2((PRINT_PREFIX
"PATA part\n"));
1088 if(!(ChipFlags
& ICH7
) && BaseMemAddress
) {
1089 KdPrint2((PRINT_PREFIX
"BaseMemAddress[5] -> indexed\n"));
1090 chan
->RegTranslation
[IDX_INDEXED_ADDR
].Addr
= BaseMemAddress
+ 0;
1091 chan
->RegTranslation
[IDX_INDEXED_ADDR
].MemIo
= MemIo
;
1092 chan
->RegTranslation
[IDX_INDEXED_DATA
].Addr
= BaseMemAddress
+ 4;
1093 chan
->RegTranslation
[IDX_INDEXED_DATA
].MemIo
= MemIo
;
1095 if((ChipFlags
& ICH5
) || BaseMemAddress
) {
1097 KdPrint2((PRINT_PREFIX
"io proc()\n"));
1098 // Rather interesting way of register access...
1099 ChipType
= INTEL_IDX
;
1100 deviceExtension
->HwFlags
&= ~CHIPTYPE_MASK
;
1101 deviceExtension
->HwFlags
|= ChipType
;
1103 if(ChipFlags
& ICH7
) {
1104 KdPrint2((PRINT_PREFIX
"ICH7 way\n"));
1106 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= 0x200*c
+ 0; // this is fake non-zero value
1107 chan
->RegTranslation
[IDX_SATA_SStatus
].Proc
= 1;
1108 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= 0x200*c
+ 2; // this is fake non-zero value
1109 chan
->RegTranslation
[IDX_SATA_SError
].Proc
= 1;
1110 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= 0x200*c
+ 1; // this is fake non-zero value
1111 chan
->RegTranslation
[IDX_SATA_SControl
].Proc
= 1;
1117 // rest of INIT staff is in AtapiChipInit()
1122 /* Cyrix 5530 ATA33 controller */
1123 if(deviceExtension
->DevID
== 0x01021078) {
1124 ConfigInfo
->AlignmentMask
= 0x0f;
1125 deviceExtension
->MaximumDmaTransferLength
= 63*1024;
1128 case ATA_JMICRON_ID
:
1129 /* New JMicron PATA controllers */
1130 GetPciConfig1(0xdf, tmp8
);
1132 KdPrint((" Check JMicron AHCI\n"));
1133 if(Ata_is_ahci_dev(pciData
)) {
1134 ChipFlags
|= UNIATA_AHCI
;
1135 deviceExtension
->HwFlags
|= UNIATA_AHCI
;
1137 KdPrint((" JMicron PATA\n"));
1140 /* set controller configuration to a combined setup we support */
1141 SetPciConfig4(0x40, 0x80c0a131);
1142 SetPciConfig4(0x80, 0x01200000);
1143 //KdPrint((" JMicron Combined (not supported yet)\n"));
1144 //return STATUS_NOT_FOUND;
1149 return STATUS_SUCCESS
;
1151 } // end UniataChipDetect()
1155 Do some 'magic staff' for VIA SouthBridge
1156 This will prevent data losses
1160 AtapiViaSouthBridgeFixup(
1161 IN PVOID HwDeviceExtension
,
1162 IN BUS_DATA_TYPE BusDataType
,
1163 IN ULONG SystemIoBusNumber
,
1167 PHW_DEVICE_EXTENSION deviceExtension
= (PHW_DEVICE_EXTENSION
)HwDeviceExtension
;
1168 PCI_COMMON_CONFIG pciData
;
1174 PCI_SLOT_NUMBER slotData
;
1176 BOOLEAN found
= FALSE
;
1178 slotData
.u
.AsULONG
= slotNumber
;
1179 for(funcNumber
= 0; funcNumber
< PCI_MAX_FUNCTION
; funcNumber
++) {
1181 slotData
.u
.bits
.FunctionNumber
= funcNumber
;
1183 busDataRead
= ScsiPortGetBusData(HwDeviceExtension
,
1188 PCI_COMMON_HDR_LENGTH
);
1190 if (busDataRead
< (ULONG
)PCI_COMMON_HDR_LENGTH
) {
1194 VendorID
= pciData
.VendorID
;
1195 DeviceID
= pciData
.DeviceID
;
1196 dev_id
= (VendorID
| (DeviceID
<< 16));
1198 if (dev_id
== 0x03051106 || /* VIA VT8363 */
1199 dev_id
== 0x03911106 || /* VIA VT8371 */
1200 dev_id
== 0x31021106 || /* VIA VT8662 */
1201 dev_id
== 0x31121106) { /* VIA VT8361 */
1204 GetPciConfig1(0x76, reg76
);
1206 if ((reg76
& 0xf0) != 0xd0) {
1207 SetPciConfig1(0x75, 0x80);
1208 SetPciConfig1(0x76, (reg76
& 0x0f) | 0xd0);
1215 deviceExtension
->HwFlags
&= ~VIABUG
;
1217 } // end AtapiViaSouthBridgeFixup()
1220 Do some 'magic staff' for ROSB SouthBridge
1221 This will prevent data losses
1225 AtapiRosbSouthBridgeFixup(
1226 IN PVOID HwDeviceExtension
,
1227 IN BUS_DATA_TYPE BusDataType
,
1228 IN ULONG SystemIoBusNumber
,
1232 //PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension;
1233 PCI_COMMON_CONFIG pciData
;
1239 PCI_SLOT_NUMBER slotData
;
1241 // BOOLEAN found = FALSE;
1243 /* locate the ISA part in the southbridge and enable UDMA33 */
1244 slotData
.u
.AsULONG
= slotNumber
;
1245 for(funcNumber
= 0; funcNumber
< PCI_MAX_FUNCTION
; funcNumber
++) {
1247 slotData
.u
.bits
.FunctionNumber
= funcNumber
;
1249 busDataRead
= ScsiPortGetBusData(HwDeviceExtension
,
1254 PCI_COMMON_HDR_LENGTH
);
1256 if (busDataRead
< (ULONG
)PCI_COMMON_HDR_LENGTH
) {
1260 VendorID
= pciData
.VendorID
;
1261 DeviceID
= pciData
.DeviceID
;
1262 dev_id
= (VendorID
| (DeviceID
<< 16));
1264 if (dev_id
== ATA_ROSB4_ISA
) { /* */
1265 ChangePciConfig4(0x64, ((a
& ~0x00002000) | 0x00004000));
1269 } // end AtapiRosbSouthBridgeFixup()
1272 Do some 'magic staff' for ROSB SouthBridge
1273 This will prevent data losses
1277 AtapiAliSouthBridgeFixup(
1278 IN PVOID HwDeviceExtension
,
1279 IN BUS_DATA_TYPE BusDataType
,
1280 IN ULONG SystemIoBusNumber
,
1281 IN ULONG slotNumber
,
1285 //PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension;
1286 PCI_COMMON_CONFIG pciData
;
1292 PCI_SLOT_NUMBER slotData
;
1294 // BOOLEAN found = FALSE;
1296 /* workaround for datacorruption bug found on at least SUN Blade-100
1297 * find the ISA function on the southbridge and disable then enable
1298 * the ATA channel tristate buffer */
1299 slotData
.u
.AsULONG
= slotNumber
;
1300 for(funcNumber
= 0; funcNumber
< PCI_MAX_FUNCTION
; funcNumber
++) {
1302 slotData
.u
.bits
.FunctionNumber
= funcNumber
;
1304 busDataRead
= ScsiPortGetBusData(HwDeviceExtension
,
1309 PCI_COMMON_HDR_LENGTH
);
1311 if (busDataRead
< (ULONG
)PCI_COMMON_HDR_LENGTH
) {
1315 VendorID
= pciData
.VendorID
;
1316 DeviceID
= pciData
.DeviceID
;
1317 dev_id
= (VendorID
| (DeviceID
<< 16));
1319 if (dev_id
== ATA_ALI_1533
) { /* SOUTH */
1320 ChangePciConfig1(0x58, (a
& ~(0x04 << c
)));
1321 ChangePciConfig1(0x58, (a
| (0x04 << c
)));
1325 } // end AtapiRosbSouthBridgeFixup()
1330 IN PHW_DEVICE_EXTENSION deviceExtension
,
1331 IN ULONG channel
// physical channel number (0-1)
1334 PVOID HwDeviceExtension
= (PVOID
)deviceExtension
;
1335 ULONG slotNumber
= deviceExtension
->slotNumber
;
1336 ULONG SystemIoBusNumber
= deviceExtension
->SystemIoBusNumber
;
1338 ULONG ChipType
= deviceExtension
->HwFlags
& CHIPTYPE_MASK
;
1340 UCHAR reg
, val
, res
;
1341 PCI_SLOT_NUMBER slotData
;
1343 slotData
.u
.AsULONG
= deviceExtension
->slotNumber
;
1345 if(ChipType
== HPT374
&& slotData
.u
.bits
.FunctionNumber
== 1) {
1346 reg
= channel
? 0x57 : 0x53;
1347 GetPciConfig1(reg
, val
);
1348 SetPciConfig1(reg
, val
| 0x80);
1352 GetPciConfig1(reg
, val
);
1353 SetPciConfig1(reg
, val
& 0xfe);
1355 GetPciConfig1(0x5a, res
);
1356 res
= res
& (channel
? 0x01 : 0x02);
1357 SetPciConfig1(reg
, val
);
1358 KdPrint2((PRINT_PREFIX
"hpt_cable80(%d) = %d\n", channel
, !res
));
1360 } // end hpt_cable80()
1366 IN PHW_DEVICE_EXTENSION deviceExtension,
1367 IN ULONG channel // physical channel number (0-1)
1370 PVOID HwDeviceExtension = (PVOID)deviceExtension;
1371 ULONG slotNumber = deviceExtension->slotNumber;
1372 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber;
1374 ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK;
1381 GetPciConfig1(0x50, reg50);
1398 for (j=0; j>=2; i -= 8) {
1399 i = (3-(channel*2+j))*8;
1400 if (((reg50 >> (i & 0x10)) & 8) &&
1401 ((reg50 >> i) & 0x20) &&
1402 (((reg50 >> i) & 7) < a)) {
1404 res |= TRUE; //(1 << (1 - (i >> 4)));
1407 KdPrint2((PRINT_PREFIX "via_cable80(%d) = %d\n", channel, res));
1410 } // end via_cable80()
1416 IN PHW_DEVICE_EXTENSION deviceExtension
,
1417 IN ULONG channel
, // physical channel number (0-1)
1422 PVOID HwDeviceExtension
= (PVOID
)deviceExtension
;
1423 ULONG slotNumber
= deviceExtension
->slotNumber
;
1424 ULONG SystemIoBusNumber
= deviceExtension
->SystemIoBusNumber
;
1426 if(deviceExtension
->MaxTransferMode
<= ATA_UDMA2
) {
1427 KdPrint2((PRINT_PREFIX
"generic_cable80(%d, %#x, %d) <= UDMA2\n", channel
, pci_reg
, bit_offs
));
1431 //ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK;
1433 ULONG c
; // logical channel (for Compatible Mode controllers)
1436 c
= channel
- deviceExtension
->Channel
; // logical channel (for Compatible Mode controllers)
1437 chan
= &deviceExtension
->chan
[c
];
1439 GetPciConfig1(pci_reg
, tmp8
);
1440 if(!(tmp8
& (1 << (channel
<< bit_offs
)))) {
1441 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
1442 KdPrint2((PRINT_PREFIX
"generic_cable80(%d, %#x, %d) = 0\n", channel
, pci_reg
, bit_offs
));
1446 KdPrint2((PRINT_PREFIX
"generic_cable80(%d, %#x, %d) = 1\n", channel
, pci_reg
, bit_offs
));
1448 } // end generic_cable80()
1452 UniAtaReadLunConfig(
1453 IN PHW_DEVICE_EXTENSION deviceExtension
,
1454 IN ULONG channel
, // physical channel
1455 IN ULONG DeviceNumber
1460 PHW_LU_EXTENSION LunExt
;
1463 c
= channel
- deviceExtension
->Channel
; // logical channel
1465 chan
= &deviceExtension
->chan
[c
];
1466 DeviceNumber
= (DeviceNumber
% deviceExtension
->NumberLuns
);
1467 LunExt
= chan
->lun
[DeviceNumber
];
1469 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"ReadCacheEnable", 1);
1470 LunExt
->opt_ReadCacheEnable
= tmp32
? TRUE
: FALSE
;
1472 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"WriteCacheEnable", 1);
1473 LunExt
->opt_WriteCacheEnable
= tmp32
? TRUE
: FALSE
;
1475 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"MaxTransferMode", chan
->MaxTransferMode
);
1476 LunExt
->opt_MaxTransferMode
= tmp32
;
1478 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"PreferedTransferMode", 0xffffffff);
1479 LunExt
->opt_PreferedTransferMode
= tmp32
;
1481 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"AdvancedPowerMode", ATA_C_F_APM_CNT_MIN_NO_STANDBY
);
1483 tmp32
= 0xfe; // max. performance
1485 LunExt
->opt_AdvPowerMode
= (UCHAR
)tmp32
;
1487 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"AcousticMgmt", ATA_C_F_AAM_CNT_MAX_POWER_SAVE
);
1489 tmp32
= 0xfe; // max. performance
1492 tmp32
= 0x0; // disable feature
1494 LunExt
->opt_AcousticMode
= (UCHAR
)tmp32
;
1496 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"StandbyTimer", 0);
1500 LunExt
->opt_StandbyTimer
= (UCHAR
)tmp32
;
1502 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"ReadOnly", 0);
1504 LunExt
->opt_ReadOnly
= (UCHAR
)tmp32
;
1507 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"GeomType", 0xffffffff);
1508 if(tmp32
> GEOM_MANUAL
) {
1511 LunExt
->opt_GeomType
= tmp32
;
1512 if(tmp32
== GEOM_MANUAL
) {
1513 LunExt
->DeviceFlags
|= DFLAGS_MANUAL_CHS
;
1514 LunExt
->opt_GeomType
= GEOM_ORIG
;
1515 // assume IdentifyData is already zero-filled
1516 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"C", 0);
1517 LunExt
->IdentifyData
.NumberOfCurrentCylinders
=
1518 LunExt
->IdentifyData
.NumberOfCylinders
= (USHORT
)tmp32
;
1519 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"H", 0);
1520 LunExt
->IdentifyData
.NumberOfCurrentHeads
=
1521 LunExt
->IdentifyData
.NumberOfHeads
= (USHORT
)tmp32
;
1522 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"S", 0);
1523 LunExt
->IdentifyData
.CurrentSectorsPerTrack
=
1524 LunExt
->IdentifyData
.SectorsPerTrack
= (USHORT
)tmp32
;
1525 memcpy(LunExt
->IdentifyData
.ModelNumber
, "SEIDH DD", 8); // ESDI HDD
1526 memcpy(LunExt
->IdentifyData
.SerialNumber
, ".10", 4);
1527 memcpy(LunExt
->IdentifyData
.FirmwareRevision
, ".10", 4);
1528 if(!LunExt
->IdentifyData
.SectorsPerTrack
||
1529 !LunExt
->IdentifyData
.NumberOfCylinders
||
1530 !LunExt
->IdentifyData
.SectorsPerTrack
) {
1532 KdPrint2((PRINT_PREFIX
"Wrong CHS\n"));
1533 LunExt
->opt_GeomType
= GEOM_AUTO
;
1535 LunExt
->DeviceFlags
|= DFLAGS_MANUAL_CHS
;
1536 LunExt
->opt_GeomType
= GEOM_ORIG
;
1540 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"Hidden", 0);
1542 LunExt
->DeviceFlags
|= DFLAGS_HIDDEN
;
1547 } // end UniAtaReadLunConfig()
1551 AtapiReadChipConfig(
1552 IN PVOID HwDeviceExtension
,
1553 IN ULONG DeviceNumber
,
1554 IN ULONG channel
// physical channel
1557 PHW_DEVICE_EXTENSION deviceExtension
= (PHW_DEVICE_EXTENSION
)HwDeviceExtension
;
1560 ULONG c
; // logical channel (for Compatible Mode controllers)
1563 KdPrint2((PRINT_PREFIX
"AtapiReadChipConfig: devExt %#x\n", deviceExtension
));
1564 ASSERT(deviceExtension
);
1566 if(channel
!= CHAN_NOT_SPECIFIED
) {
1567 c
= channel
- deviceExtension
->Channel
; // logical channel (for Compatible Mode controllers)
1569 c
= CHAN_NOT_SPECIFIED
;
1572 KdPrint2((PRINT_PREFIX
"AtapiReadChipConfig: dev %#x, ph chan %d\n", DeviceNumber
, channel
));
1574 if(channel
== CHAN_NOT_SPECIFIED
) {
1575 if(AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"ForceSimplex", FALSE
)) {
1576 deviceExtension
->simplexOnly
= TRUE
;
1578 deviceExtension
->opt_AtapiDmaZeroTransfer
= FALSE
;
1579 deviceExtension
->opt_AtapiDmaControlCmd
= FALSE
;
1580 deviceExtension
->opt_AtapiDmaRawRead
= g_opt_AtapiDmaRawRead
;
1581 deviceExtension
->opt_AtapiDmaReadWrite
= TRUE
;
1584 if(c
== CHAN_NOT_SPECIFIED
) {
1585 KdPrint2((PRINT_PREFIX
"MaxTransferMode (base): %#x\n", deviceExtension
->MaxTransferMode
));
1586 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
1587 chan
= &deviceExtension
->chan
[c
];
1588 chan
->MaxTransferMode
= deviceExtension
->MaxTransferMode
;
1589 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DEVNUM_NOT_SPECIFIED
, L
"MaxTransferMode", chan
->MaxTransferMode
);
1590 if(tmp32
!= 0xffffffff) {
1591 KdPrint2((PRINT_PREFIX
"MaxTransferMode (overriden): %#x\n", chan
->MaxTransferMode
));
1592 chan
->MaxTransferMode
= tmp32
;
1594 //UniAtaReadLunConfig(deviceExtension, c, 0);
1595 //UniAtaReadLunConfig(deviceExtension, c, 1);
1598 deviceExtension
->opt_AtapiDmaZeroTransfer
=
1599 AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"AtapiDmaZeroTransfer", deviceExtension
->opt_AtapiDmaZeroTransfer
) ?
1602 deviceExtension
->opt_AtapiDmaControlCmd
=
1603 AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"AtapiDmaControlCmd", deviceExtension
->opt_AtapiDmaControlCmd
) ?
1606 deviceExtension
->opt_AtapiDmaRawRead
=
1607 AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"AtapiDmaRawRead", deviceExtension
->opt_AtapiDmaRawRead
) ?
1610 deviceExtension
->opt_AtapiDmaReadWrite
=
1611 AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"AtapiDmaReadWrite", deviceExtension
->opt_AtapiDmaReadWrite
) ?
1615 chan
= &deviceExtension
->chan
[c
];
1616 chan
->MaxTransferMode
= deviceExtension
->MaxTransferMode
;
1617 tmp32
= AtapiRegCheckDevValue(deviceExtension
, c
, DEVNUM_NOT_SPECIFIED
, L
"MaxTransferMode", chan
->MaxTransferMode
);
1618 if(tmp32
!= 0xffffffff) {
1619 KdPrint2((PRINT_PREFIX
"MaxTransferMode (overriden): %#x\n", chan
->MaxTransferMode
));
1620 chan
->MaxTransferMode
= tmp32
;
1622 tmp32
= AtapiRegCheckDevValue(deviceExtension
, c
, DEVNUM_NOT_SPECIFIED
, L
"ReorderEnable", TRUE
);
1623 chan
->UseReorder
= tmp32
? TRUE
: FALSE
;
1625 for(i
=0; i
<deviceExtension
->NumberLuns
; i
++) {
1626 UniAtaReadLunConfig(deviceExtension
, channel
, i
);
1631 } // end AtapiReadChipConfig()
1636 IN PVOID HwDeviceExtension
,
1637 IN ULONG DeviceNumber
,
1638 IN ULONG channel
// logical channel
1641 PHW_DEVICE_EXTENSION deviceExtension
= (PHW_DEVICE_EXTENSION
)HwDeviceExtension
;
1642 ULONG slotNumber
= deviceExtension
->slotNumber
;
1643 ULONG SystemIoBusNumber
= deviceExtension
->SystemIoBusNumber
;
1644 ULONG VendorID
= deviceExtension
->DevID
& 0xffff;
1645 ULONG DeviceID
= (deviceExtension
->DevID
>> 16) & 0xffff;
1646 ULONG RevID
= deviceExtension
->RevID
;
1648 // BUSMASTER_CONTROLLER_INFORMATION* DevTypeInfo;
1649 ULONG ChipType
= deviceExtension
->HwFlags
& CHIPTYPE_MASK
;
1650 ULONG ChipFlags
= deviceExtension
->HwFlags
& CHIPFLAG_MASK
;
1655 ULONG c
; // logical channel (for Compatible Mode controllers)
1656 BOOLEAN CheckCable
= FALSE
;
1657 BOOLEAN GlobalInit
= FALSE
;
1658 //ULONG BaseIoAddress;
1661 case CHAN_NOT_SPECIFIED_CHECK_CABLE
:
1664 case CHAN_NOT_SPECIFIED
:
1665 c
= CHAN_NOT_SPECIFIED
;
1669 //c = channel - deviceExtension->Channel; // logical channel (for Compatible Mode controllers)
1671 channel
+= deviceExtension
->Channel
;
1674 KdPrint2((PRINT_PREFIX
"AtapiChipInit: dev %#x, ph chan %d, c %d\n", DeviceNumber
, channel
, c
));
1676 KdPrint2((PRINT_PREFIX
"HwFlags: %#x\n", deviceExtension
->HwFlags
));
1677 KdPrint2((PRINT_PREFIX
"VendorID/DeviceID/Rev %#x/%#x/%#x\n", VendorID
, DeviceID
, RevID
));
1679 if(deviceExtension
->UnknownDev
) {
1680 KdPrint2((PRINT_PREFIX
" Unknown chip\n" ));
1682 VendorID
= 0xffffffff;
1686 if(ChipFlags
& UNIATA_AHCI
) {
1687 /* if BAR(5) is IO it should point to SATA interface registers */
1688 if(!deviceExtension
->BaseIoAHCI_0
.Addr
) {
1689 KdPrint2((PRINT_PREFIX
" !BaseIoAHCI_0, exiting\n" ));
1692 if(c
== CHAN_NOT_SPECIFIED
) {
1693 return UniataAhciInit(HwDeviceExtension
);
1695 if(c
<deviceExtension
->NumberChannels
) {
1696 KdPrint2((PRINT_PREFIX
" AHCI single channel init\n" ));
1697 UniataAhciReset(HwDeviceExtension
, c
);
1700 KdPrint2((PRINT_PREFIX
" AHCI non-existent channel\n" ));
1705 if((WinVer_Id() > WinVer_NT
) &&
1707 deviceExtension
->MasterDev
) {
1708 PCI_COMMON_CONFIG pciData
;
1711 KdPrint2((PRINT_PREFIX
" re-enable IO resources of MasterDev\n" ));
1713 busDataRead
= HalGetBusData
1714 //ScsiPortGetBusData
1716 //HwDeviceExtension,
1717 PCIConfiguration
, SystemIoBusNumber
, slotNumber
,
1718 &pciData
, PCI_COMMON_HDR_LENGTH
);
1719 if(busDataRead
== PCI_COMMON_HDR_LENGTH
) {
1720 UniataEnableIoPCI(SystemIoBusNumber
, slotNumber
, &pciData
);
1722 KdPrint2((PRINT_PREFIX
" re-enable IO resources of MasterDev FAILED\n" ));
1727 // case ATA_ACARD_ID:
1729 case ATA_ACER_LABS_ID
:
1730 if(ChipFlags
& UNIATA_SATA
) {
1731 if(c
== CHAN_NOT_SPECIFIED
) {
1732 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
1733 chan
= &deviceExtension
->chan
[c
];
1734 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1735 /* the southbridge might need the data corruption fix */
1736 if(RevID
== 0xc2 || RevID
== 0xc3) {
1737 AtapiAliSouthBridgeFixup(HwDeviceExtension
, PCIConfiguration
,
1738 SystemIoBusNumber
, slotNumber
, c
);
1741 /* enable PCI interrupt */
1742 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG
, Command
), (a
& ~0x0400));
1745 if(ChipFlags
& ALINEW
) {
1746 if(c
== CHAN_NOT_SPECIFIED
) {
1747 /* use device interrupt as byte count end */
1748 ChangePciConfig1(0x4a, (a
| 0x20));
1749 /* enable cable detection and UDMA support on newer chips, rev < 0xc7 */
1751 ChangePciConfig1(0x4b, (a
| 0x09));
1754 /* enable ATAPI UDMA mode */
1755 ChangePciConfig1(0x53, (a
| (RevID
>= 0xc7 ? 0x03 : 0x01)));
1758 // check 80-pin cable
1759 generic_cable80(deviceExtension
, channel
, 0x4a, 0);
1762 if(c
== CHAN_NOT_SPECIFIED
) {
1763 /* deactivate the ATAPI FIFO and enable ATAPI UDMA */
1764 ChangePciConfig1(0x53, (a
| 0x03));
1767 deviceExtension
->chan
[c
].ChannelCtrlFlags
|= CTRFLAGS_DMA_RO
;
1772 if(c
== CHAN_NOT_SPECIFIED
) {
1773 /* set prefetch, postwrite */
1774 if(ChipFlags
& AMDBUG
) {
1775 ChangePciConfig1(0x41, (a
& 0x0f));
1777 ChangePciConfig1(0x41, (a
| 0xf0));
1780 if(deviceExtension
->MaxTransferMode
< ATA_UDMA2
)
1782 // check 80-pin cable
1783 if(!(ChipFlags
& UNIATA_NO80CHK
)) {
1784 if(c
== CHAN_NOT_SPECIFIED
) {
1787 generic_cable80(deviceExtension
, channel
, 0x42, 0);
1791 case ATA_HIGHPOINT_ID
:
1793 if(c
== CHAN_NOT_SPECIFIED
) {
1795 if(ChipFlags
& HPTOLD
) {
1796 /* turn off interrupt prediction */
1797 ChangePciConfig1(0x51, (a
& ~0x80));
1799 /* turn off interrupt prediction */
1800 ChangePciConfig1(0x51, (a
& ~0x03));
1801 ChangePciConfig1(0x55, (a
& ~0x03));
1802 /* turn on interrupts */
1803 ChangePciConfig1(0x5a, (a
& ~0x10));
1804 /* set clocks etc */
1805 if(ChipType
< HPT372
) {
1806 SetPciConfig1(0x5b, 0x22);
1808 ChangePciConfig1(0x5b, ((a
& 0x01) | 0x20));
1813 // check 80-pin cable
1814 chan
= &deviceExtension
->chan
[c
];
1815 if(!hpt_cable80(deviceExtension
, channel
)) {
1816 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
1820 case ATA_INTEL_ID
: {
1824 if(ChipFlags
& UNIATA_SATA
) {
1826 KdPrint2((PRINT_PREFIX
"Intel SATA\n"));
1827 if(ChipFlags
& UNIATA_AHCI
) {
1828 KdPrint2((PRINT_PREFIX
"Do nothing for AHCI\n"));
1831 if(c
== CHAN_NOT_SPECIFIED
) {
1832 KdPrint2((PRINT_PREFIX
"Base init\n"));
1833 /* force all ports active "the legacy way" */
1834 ChangePciConfig2(0x92, (a
| 0x0f));
1836 if(deviceExtension
->BaseIoAddressSATA_0
.Addr
&& (ChipFlags
& ICH7
)) {
1837 /* Set SCRAE bit to enable registers access. */
1838 ChangePciConfig4(0x94, (a
| (1 << 9)));
1839 /* Set Ports Implemented register bits. */
1840 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
), 0x0c,
1841 AtapiReadPortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
), 0x0c) | 0x0f);
1843 /* enable PCI interrupt */
1844 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG
, Command
), (a
& ~0x0400));
1848 KdPrint2((PRINT_PREFIX
"channel init\n"));
1850 GetPciConfig1(0x90, tmp8
);
1851 KdPrint2((PRINT_PREFIX
"reg 90: %x, init lun map\n", tmp8
));
1853 KdPrint2((PRINT_PREFIX
"chan %d\n", c
));
1854 chan
= &deviceExtension
->chan
[c
];
1856 if(ChipFlags
& ICH5
) {
1857 KdPrint2((PRINT_PREFIX
"ICH5\n"));
1858 if ((tmp8
& 0x04) == 0) {
1859 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1860 chan
->lun
[0]->SATA_lun_map
= (tmp8
& 0x01) ^ c
;
1861 chan
->lun
[1]->SATA_lun_map
= 0;
1862 } else if ((tmp8
& 0x02) == 0) {
1864 chan
->lun
[0]->SATA_lun_map
= (tmp8
& 0x01) ? 1 : 0;
1865 chan
->lun
[1]->SATA_lun_map
= (tmp8
& 0x01) ? 0 : 1;
1868 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA;
1870 } else if ((tmp8
& 0x02) != 0) {
1872 chan
->lun
[0]->SATA_lun_map
= (tmp8
& 0x01) ? 1 : 0;
1873 chan
->lun
[1]->SATA_lun_map
= (tmp8
& 0x01) ? 0 : 1;
1876 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA;
1880 if(ChipFlags
& I6CH2
) {
1881 KdPrint2((PRINT_PREFIX
"I6CH2\n"));
1882 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1883 chan
->lun
[0]->SATA_lun_map
= c
? 0 : 1;
1884 chan
->lun
[1]->SATA_lun_map
= 0;
1886 KdPrint2((PRINT_PREFIX
"other Intel\n"));
1887 switch(tmp8
& 0x03) {
1889 KdPrint2((PRINT_PREFIX
"0 -> %d/%d\n", 0+c
, 2+c
));
1890 chan
->lun
[0]->SATA_lun_map
= 0+c
;
1891 chan
->lun
[1]->SATA_lun_map
= 2+c
;
1895 KdPrint2((PRINT_PREFIX
"2 -> %d/%d\n", 0, 2));
1896 chan
->lun
[0]->SATA_lun_map
= 0;
1897 chan
->lun
[1]->SATA_lun_map
= 2;
1900 KdPrint2((PRINT_PREFIX
"PATA\n"));
1906 KdPrint2((PRINT_PREFIX
"2 -> %d/%d\n", 1, 3));
1907 chan
->lun
[0]->SATA_lun_map
= 1;
1908 chan
->lun
[1]->SATA_lun_map
= 3;
1911 KdPrint2((PRINT_PREFIX
"PATA\n"));
1919 KdPrint2((PRINT_PREFIX
"PATA part\n"));
1920 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA5
);
1923 if(ChipType
== INTEL_IDX
) {
1924 KdPrint2((PRINT_PREFIX
"io indexed\n"));
1925 //for(c=0; c<deviceExtension->NumberChannels; c++) {
1926 chan
= &deviceExtension
->chan
[c
];
1927 UniataSataWritePort4(chan
, IDX_SATA_SError
, 0xffffffff, 0);
1928 if(!(chan
->ChannelCtrlFlags
& CTRFLAGS_NO_SLAVE
)) {
1929 UniataSataWritePort4(chan
, IDX_SATA_SError
, 0xffffffff, 1);
1937 if(deviceExtension
->MaxTransferMode
<= ATA_UDMA2
)
1939 // check 80-pin cable
1940 if(c
== CHAN_NOT_SPECIFIED
) {
1943 chan
= &deviceExtension
->chan
[c
];
1944 GetPciConfig2(0x54, reg54
);
1945 KdPrint2((PRINT_PREFIX
" intel 80-pin check (reg54=%x)\n", reg54
));
1946 if(reg54
== 0x0000 || reg54
== 0xffff) {
1947 KdPrint2((PRINT_PREFIX
" check failed (not supported)\n"));
1949 if( ((reg54
>> (channel
*2)) & 30) == 0) {
1950 KdPrint2((PRINT_PREFIX
" intel 40-pin\n"));
1951 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
1955 case ATA_NVIDIA_ID
: {
1956 if(ChipFlags
& UNIATA_SATA
) {
1957 if(c
== CHAN_NOT_SPECIFIED
) {
1958 ULONG offs
= (ChipFlags
& NV4OFF
) ? 0x0440 : 0x0010;
1959 /* enable control access */
1960 ChangePciConfig1(0x50, (a
| 0x04));
1961 /* MCP55 seems to need some time to allow r_res2 read. */
1962 AtapiStallExecution(10);
1963 KdPrint2((PRINT_PREFIX
"BaseIoAddressSATA_0=%x\n", deviceExtension
->BaseIoAddressSATA_0
.Addr
));
1964 if(ChipFlags
& NVQ
) {
1965 /* clear interrupt status */
1966 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),offs
, 0x00ff00ff);
1967 /* enable device and PHY state change interrupts */
1968 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),offs
+4, 0x000d000d);
1969 /* disable NCQ support */
1970 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x0400,
1971 AtapiReadPortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x0400) & 0xfffffff9);
1973 /* clear interrupt status */
1974 AtapiWritePortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),offs
, 0xff);
1975 /* enable device and PHY state change interrupts */
1976 AtapiWritePortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),offs
+1, 0xdd);
1978 /* enable PCI interrupt */
1979 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG
, Command
), (a
& ~0x0400));
1981 //UniataSataPhyEnable(HwDeviceExtension, c);
1986 if(c
== CHAN_NOT_SPECIFIED
) {
1987 /* set prefetch, postwrite */
1988 ChangePciConfig1(0x51, (a
& 0x0f));
1990 // check 80-pin cable
1991 generic_cable80(deviceExtension
, channel
, 0x52, 1);
1992 /* chan = &deviceExtension->chan[c];
1993 GetPciConfig1(0x52, reg52);
1994 if( !((reg52 >> (channel*2)) & 0x01)) {
1995 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
2000 case ATA_PROMISE_ID
: {
2005 if(c
== CHAN_NOT_SPECIFIED
) {
2006 // ATA_OUTB(ctlr->r_res1, 0x11, ATA_INB(ctlr->r_res1, 0x11) | 0x0a);
2007 AtapiWritePortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressBM_0
),0x11,
2008 AtapiReadPortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressBM_0
),0x11) | 0x0a );
2012 /* enable burst mode */
2013 // ATA_OUTB(ctlr->r_res1, 0x1f, ATA_INB(ctlr->r_res1, 0x1f) | 0x01);
2014 if(c
== CHAN_NOT_SPECIFIED
) {
2015 AtapiWritePortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressBM_0
),0x1f,
2016 AtapiReadPortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressBM_0
),0x1f) | 0x01 );
2018 // check 80-pin cable
2019 chan
= &deviceExtension
->chan
[c
];
2020 GetPciConfig2(0x50, Reg50
);
2021 if(Reg50
& (1 << (channel
+10))) {
2022 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
2027 if(c
== CHAN_NOT_SPECIFIED
) {
2030 // check 80-pin cable
2031 chan
= &deviceExtension
->chan
[c
];
2032 AtapiWritePort1(chan
, IDX_BM_DeviceSpecific0
, 0x0b);
2033 if(AtapiReadPort1(chan
, IDX_BM_DeviceSpecific1
) & 0x04) {
2034 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
2039 if(c
== CHAN_NOT_SPECIFIED
) {
2040 if(ChipFlags
& PRSATA
) {
2041 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressBM_0
),0x6c, 0x000000ff);
2044 chan
= &deviceExtension
->chan
[c
];
2045 AtapiWritePort4(chan
, IDX_BM_Command
,
2046 (AtapiReadPort4(chan
, IDX_BM_Command
) & ~0x00000f8f) | channel
);
2047 AtapiWritePort4(chan
, IDX_BM_DeviceSpecific0
, 0x00000001);
2048 // check 80-pin cable
2049 if(chan
->MaxTransferMode
< ATA_SA150
&&
2050 (AtapiReadPort4(chan
, IDX_BM_Command
) & 0x01000000)) {
2051 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
2057 case ATA_SERVERWORKS_ID
:
2058 if(c
== CHAN_NOT_SPECIFIED
) {
2059 if(ChipType
== SWKS33
) {
2060 AtapiRosbSouthBridgeFixup(HwDeviceExtension
, PCIConfiguration
,
2061 SystemIoBusNumber
, slotNumber
);
2063 ChangePciConfig1(0x5a, ((a
& ~0x40) | ((ChipType
== SWKS100
) ? 0x03 : 0x02)));
2068 if(ChipType
== SIIMIO
) {
2069 KdPrint2((PRINT_PREFIX
"ATI New\n"));
2072 KdPrint2((PRINT_PREFIX
"ATI\n"));
2075 case ATA_SILICON_IMAGE_ID
:
2076 /* if(ChipFlags & SIIENINTR) {
2077 SetPciConfig1(0x71, 0x01);
2082 KdPrint2((PRINT_PREFIX
"SII\n"));
2085 if(c
== CHAN_NOT_SPECIFIED
) {
2086 if(ChipFlags
& SIISETCLK
) {
2087 KdPrint2((PRINT_PREFIX
"SIISETCLK\n"));
2088 GetPciConfig1(0x8a, tmp8
);
2089 if ((tmp8
& 0x30) != 0x10)
2090 ChangePciConfig1(0x8a, (a
& 0xcf) | 0x10);
2091 GetPciConfig1(0x8a, tmp8
);
2092 if ((tmp8
& 0x30) != 0x10) {
2093 KdPrint2((PRINT_PREFIX
"Sil 0680 could not set ATA133 clock\n"));
2094 deviceExtension
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA5
);
2098 if(deviceExtension
->MaxTransferMode
< ATA_SA150
) {
2099 // check 80-pin cable
2100 if(c
== CHAN_NOT_SPECIFIED
) {
2103 KdPrint2((PRINT_PREFIX
"Check UDMA66 cable\n"));
2104 chan
= &deviceExtension
->chan
[c
];
2105 GetPciConfig2(0x79, Reg79
);
2106 if(Reg79
& (channel
? 0x02 : 0x01)) {
2107 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
2111 ULONG unit01
= (c
& 1);
2112 ULONG unit10
= (c
& 2);
2113 /* enable/disable PHY state change interrupt */
2114 if(c
== CHAN_NOT_SPECIFIED
) {
2115 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
2118 if(ChipFlags
& SIINOSATAIRQ
) {
2119 KdPrint2((PRINT_PREFIX
"Disable broken SATA intr on c=%x\n", c
));
2120 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
), 0x148 + (unit01
<< 7) + (unit10
<< 8),0);
2124 if(ChipFlags
& SIINOSATAIRQ
) {
2125 KdPrint2((PRINT_PREFIX
"Disable broken SATA intr on c=%x\n", c
));
2126 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
), 0x148 + (unit01
<< 7) + (unit10
<< 8),0);
2128 KdPrint2((PRINT_PREFIX
"Enable SATA intr on c=%x\n", c
));
2129 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
), 0x148 + (unit01
<< 7) + (unit10
<< 8),(1 << 16));
2133 if(c
== CHAN_NOT_SPECIFIED
) {
2134 /* enable interrupt as BIOS might not */
2135 ChangePciConfig1(0x8a, (a
& 0x3f));
2136 // Enable 3rd and 4th channels
2137 if (ChipFlags
& SII4CH
) {
2138 KdPrint2((PRINT_PREFIX
"SII4CH\n"));
2139 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x0200, 0x00000002);
2142 chan
= &deviceExtension
->chan
[c
];
2143 /* dont block interrupts */
2144 //ChangePciConfig4(0x48, (a & ~0x03c00000));
2145 /*tmp32 =*/ AtapiReadPortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x48);
2146 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x48, (1 << 22) << c
);
2148 /*tmp32 =*/ AtapiReadPortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x48);
2150 /* Initialize FIFO PCI bus arbitration */
2151 GetPciConfig1(offsetof(PCI_COMMON_CONFIG
, CacheLineSize
), tmp8
);
2153 KdPrint2((PRINT_PREFIX
"SII: CacheLine=%d\n", tmp8
));
2155 AtapiWritePort2(chan
, IDX_BM_DeviceSpecific1
, ((USHORT
)tmp8
) << 8 | tmp8
);
2157 KdPrint2((PRINT_PREFIX
"SII: CacheLine=0 !!!\n"));
2164 KdPrint2((PRINT_PREFIX
"SII_CMD\n"));
2165 if(c
== CHAN_NOT_SPECIFIED
) {
2166 /* Setup interrupts. */
2167 SetPciConfig1(0x71, 0x01);
2169 /* GetPciConfig1(0x8a, tmp8);
2171 SetPciConfig1(0x71, tmp8);*/
2173 /* Use MEMORY READ LINE for reads.
2174 * NOTE: Although not mentioned in the PCI0646U specs,
2175 * these bits are write only and won't be read
2176 * back as set or not. The PCI0646U2 specs clarify
2180 SetPciConfig1(0x71, tmp8);
2182 /* Set reasonable active/recovery/address-setup values. */
2183 SetPciConfig1(0x53, 0x40);
2184 SetPciConfig1(0x54, 0x3f);
2185 SetPciConfig1(0x55, 0x40);
2186 SetPciConfig1(0x56, 0x3f);
2187 SetPciConfig1(0x57, 0x1c);
2188 SetPciConfig1(0x58, 0x3f);
2189 SetPciConfig1(0x5b, 0x3f);
2196 if(c
== CHAN_NOT_SPECIFIED
) {
2202 ChangePciConfig1(0x52, (a
& ~0x04));
2206 ChangePciConfig1(0x49, (a
& ~0x01));
2209 ChangePciConfig2(0x50, (a
| 0x0008));
2210 ChangePciConfig2(0x52, (a
| 0x0008));
2213 ChangePciConfig2(0x04, (a
& ~0x0400));
2216 if(ChipType
== SIS133NEW
) {
2218 // check 80-pin cable
2219 if(c
== CHAN_NOT_SPECIFIED
) {
2222 chan
= &deviceExtension
->chan
[c
];
2223 GetPciConfig2(channel
? 0x52 : 0x50, tmp16
);
2224 if(tmp16
& 0x8000) {
2225 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
2229 // check 80-pin cable
2230 if(c
== CHAN_NOT_SPECIFIED
) {
2233 chan
= &deviceExtension
->chan
[c
];
2234 GetPciConfig1(48, tmp8
);
2235 if(tmp8
& (0x10 << channel
)) {
2236 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
2243 /* if(ChipFlags & (UNIATA_SATA | UNIATA_AHCI | VIASATA) {
2246 if(c
== CHAN_NOT_SPECIFIED
) {
2247 /* prepare for ATA-66 on the 82C686a and 82C596b */
2248 if(ChipFlags
& VIACLK
) {
2249 ChangePciConfig4(0x50, (a
| 0x030b030b));
2252 if(ChipFlags
& (UNIATA_SATA
| VIASATA
)) {
2253 /* enable PCI interrupt */
2254 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG
, Command
), (a
& ~0x0400));
2257 * vt6420/1 has problems talking to some drives. The following
2258 * is based on the fix from Joseph Chan <JosephChan@via.com.tw>.
2260 * When host issues HOLD, device may send up to 20DW of data
2261 * before acknowledging it with HOLDA and the host should be
2262 * able to buffer them in FIFO. Unfortunately, some WD drives
2263 * send upto 40DW before acknowledging HOLD and, in the
2264 * default configuration, this ends up overflowing vt6421's
2265 * FIFO, making the controller abort the transaction with
2268 * Rx52[2] is the internal 128DW FIFO Flow control watermark
2269 * adjusting mechanism enable bit and the default value 0
2270 * means host will issue HOLD to device when the left FIFO
2271 * size goes below 32DW. Setting it to 1 makes the watermark
2274 * http://www.reactos.org/bugzilla/show_bug.cgi?id=6500
2277 if(DeviceID
== 0x3149 || DeviceID
== 0x3249) { //vt6420 or vt6421
2278 KdPrint2((PRINT_PREFIX
"VIA 642x FIFO\n"));
2279 ChangePciConfig1(0x52, a
| (1 << 2));
2285 /* the southbridge might need the data corruption fix */
2286 if(ChipFlags
& VIABUG
) {
2287 AtapiViaSouthBridgeFixup(HwDeviceExtension
, PCIConfiguration
,
2288 SystemIoBusNumber
, slotNumber
);
2290 /* set prefetch, postwrite */
2291 if(ChipType
!= VIA133
) {
2292 ChangePciConfig1(0x41, (a
| 0xf0));
2295 /* set fifo configuration half'n'half */
2296 ChangePciConfig1(0x43, ((a
& ((ChipFlags
& VIAPRQ
) ? 0x80 : 0x90)) | 0x2a));
2298 /* set status register read retry */
2299 ChangePciConfig1(0x44, (a
| 0x08));
2301 /* set DMA read & end-of-sector fifo flush */
2302 ChangePciConfig1(0x46, ((a
& 0x0c) | 0xf0));
2304 /* set sector size */
2305 SetPciConfig2(0x60, DEV_BSIZE
);
2306 SetPciConfig2(0x68, DEV_BSIZE
);
2309 chan
= &deviceExtension
->chan
[c
];
2311 if(ChipFlags
& (UNIATA_SATA
| VIASATA
)) {
2312 if((ChipFlags
& VIABAR
) && (c
>= 2)) {
2313 // this is PATA channel
2314 chan
->MaxTransferMode
= ATA_UDMA5
;
2317 UniataSataWritePort4(chan
, IDX_SATA_SError
, 0xffffffff, 0);
2321 // check 80-pin cable
2322 if(!via_cable80(deviceExtension, channel)) {
2323 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
2331 if(ChipType
== ITE_33
|| ChipType
== ITE_133_NEW
) {
2334 if(ChipType
== ITE_133
) {
2335 if(c
== CHAN_NOT_SPECIFIED
) {
2336 /* set PCI mode and 66Mhz reference clock */
2337 ChangePciConfig1(0x50, a
& ~0x83);
2339 /* set default active & recover timings */
2340 SetPciConfig1(0x54, 0x31);
2341 SetPciConfig1(0x56, 0x31);
2343 // check 80-pin cable
2344 GetPciConfig2(0x40, tmp16
);
2345 chan
= &deviceExtension
->chan
[c
];
2346 if(!(tmp16
& (channel
? 0x08 : 0x04))) {
2347 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
2351 if(ChipType
== ITE_133_NEW
) {
2355 if(c
!= CHAN_NOT_SPECIFIED
) {
2356 // We don't know how to check for 80-pin cable on unknown controllers.
2357 // Later we shall check bit in IDENTIFY structure, but it is not reliable way.
2358 // So, leave this flag to use as hint in error recovery procedures
2359 KdPrint2((PRINT_PREFIX
"UNIATA_NO80CHK\n"));
2360 deviceExtension
->HwFlags
|= UNIATA_NO80CHK
;
2365 // In all places separate channels are inited after common controller init
2366 // The only exception is probe. But there we may need info about 40/80 pin and MaxTransferRate
2367 if(CheckCable
&& !(ChipFlags
& (UNIATA_NO80CHK
| UNIATA_SATA
))) {
2368 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
2369 AtapiChipInit(HwDeviceExtension
, DeviceNumber
, c
);
2374 } // end AtapiChipInit()
2379 IN PHW_DEVICE_EXTENSION deviceExtension
,
2380 IN PIDE_BUSMASTER_REGISTERS BaseIoAddressBM_0
,
2388 if(!BaseIoAddressBM_0
) {
2391 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
2392 chan
= &deviceExtension
->chan
[c
];
2393 for (i
=0; i
<IDX_BM_IO_SZ
; i
++) {
2394 chan
->RegTranslation
[IDX_BM_IO
+i
].Addr
= BaseIoAddressBM_0
? ((ULONGIO_PTR
)BaseIoAddressBM_0
+ i
) : 0;
2395 chan
->RegTranslation
[IDX_BM_IO
+i
].MemIo
= MemIo
;
2397 if(BaseIoAddressBM_0
) {
2398 BaseIoAddressBM_0
++;
2402 } // end UniataInitMapBM()
2407 IN PHW_CHANNEL chan
,
2408 IN PIDE_REGISTERS_1 BaseIoAddress1
,
2409 IN PIDE_REGISTERS_2 BaseIoAddress2
2414 for (i
=0; i
<IDX_IO1_SZ
; i
++) {
2415 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseIoAddress1
? ((ULONGIO_PTR
)BaseIoAddress1
+ i
) : 0;
2416 chan
->RegTranslation
[IDX_IO1
+i
].MemIo
= FALSE
;
2418 for (i
=0; i
<IDX_IO2_SZ
; i
++) {
2419 chan
->RegTranslation
[IDX_IO2
+i
].Addr
= BaseIoAddress2
? ((ULONGIO_PTR
)BaseIoAddress2
+ i
) : 0;
2420 chan
->RegTranslation
[IDX_IO2
+i
].MemIo
= FALSE
;
2422 UniataInitSyncBaseIO(chan
);
2424 } // end UniataInitMapBase()
2428 UniataInitSyncBaseIO(
2432 RtlCopyMemory(&chan
->RegTranslation
[IDX_IO1_o
], &chan
->RegTranslation
[IDX_IO1
], IDX_IO1_SZ
*sizeof(chan
->RegTranslation
[0]));
2433 RtlCopyMemory(&chan
->RegTranslation
[IDX_IO2_o
], &chan
->RegTranslation
[IDX_IO2
], IDX_IO2_SZ
*sizeof(chan
->RegTranslation
[0]));
2435 } // end UniataInitSyncBaseIO()
2440 IN PHW_CHANNEL chan
,
2441 IN PHW_DEVICE_EXTENSION deviceExtension
,
2447 KdPrint2((PRINT_PREFIX
"AtapiSetupLunPtrs for channel %d of %d, %d luns \n", c
, deviceExtension
->NumberChannels
, deviceExtension
->NumberLuns
));
2449 if(!deviceExtension
->NumberLuns
) {
2450 KdPrint2((PRINT_PREFIX
"Achtung !deviceExtension->NumberLuns \n"));
2451 deviceExtension
->NumberLuns
= IDE_MAX_LUN_PER_CHAN
;
2453 KdPrint2((PRINT_PREFIX
" Chan %#x\n", chan
));
2454 chan
->DeviceExtension
= deviceExtension
;
2456 chan
->NumberLuns
= deviceExtension
->NumberLuns
;
2457 for(i
=0; i
<deviceExtension
->NumberLuns
; i
++) {
2458 chan
->lun
[i
] = &(deviceExtension
->lun
[c
*deviceExtension
->NumberLuns
+i
]);
2459 KdPrint2((PRINT_PREFIX
" Lun %#x\n", i
));
2460 KdPrint2((PRINT_PREFIX
" Lun ptr %#x\n", chan
->lun
[i
]));
2462 chan
->AltRegMap
= deviceExtension
->AltRegMap
;
2463 chan
->NextDpcChan
= -1;
2464 for(i
=0; i
<deviceExtension
->NumberLuns
; i
++) {
2465 chan
->lun
[i
]->DeviceExtension
= deviceExtension
;
2466 chan
->lun
[i
]->chan
= chan
;
2467 chan
->lun
[i
]->Lun
= i
;
2469 if((deviceExtension
->HwFlags
& UNIATA_AHCI
) &&
2470 deviceExtension
->AhciInternalAtaReq0
&&
2471 deviceExtension
->AhciInternalSrb0
) {
2472 chan
->AhciInternalAtaReq
= &(deviceExtension
->AhciInternalAtaReq0
[c
]);
2473 chan
->AhciInternalSrb
= &(deviceExtension
->AhciInternalSrb0
[c
]);
2474 UniataAhciSetupCmdPtr(chan
->AhciInternalAtaReq
);
2475 chan
->AhciInternalSrb
->SrbExtension
= chan
->AhciInternalAtaReq
;
2476 chan
->AhciInternalAtaReq
->Srb
= chan
->AhciInternalSrb
;
2479 } // end AtapiSetupLunPtrs()
2483 UniataAllocateLunExt(
2484 PHW_DEVICE_EXTENSION deviceExtension
,
2485 ULONG NewNumberChannels
2488 PHW_LU_EXTENSION old_luns
= NULL
;
2489 PHW_CHANNEL old_chans
= NULL
;
2491 KdPrint2((PRINT_PREFIX
"allocate %d Luns for %d channels\n", deviceExtension
->NumberLuns
, deviceExtension
->NumberChannels
));
2493 old_luns
= deviceExtension
->lun
;
2494 old_chans
= deviceExtension
->chan
;
2496 if(old_luns
|| old_chans
) {
2497 if(NewNumberChannels
== UNIATA_ALLOCATE_NEW_LUNS
) {
2498 KdPrint2((PRINT_PREFIX
"already allocated!\n"));
2503 if(!deviceExtension
->NumberLuns
) {
2504 KdPrint2((PRINT_PREFIX
"default NumberLuns=2\n"));
2505 deviceExtension
->NumberLuns
= 2;
2508 if(deviceExtension
->HwFlags
& UNIATA_AHCI
) {
2509 if(!deviceExtension
->AhciInternalAtaReq0
) {
2510 deviceExtension
->AhciInternalAtaReq0
= (PATA_REQ
)ExAllocatePool(NonPagedPool
, sizeof(ATA_REQ
)*deviceExtension
->NumberChannels
);
2511 if (!deviceExtension
->AhciInternalAtaReq0
) {
2512 KdPrint2((PRINT_PREFIX
"!deviceExtension->AhciInternalAtaReq0 => SP_RETURN_ERROR\n"));
2515 RtlZeroMemory(deviceExtension
->AhciInternalAtaReq0
, sizeof(ATA_REQ
)*deviceExtension
->NumberChannels
);
2517 if(!deviceExtension
->AhciInternalSrb0
) {
2518 deviceExtension
->AhciInternalSrb0
= (PSCSI_REQUEST_BLOCK
)ExAllocatePool(NonPagedPool
, sizeof(SCSI_REQUEST_BLOCK
)*deviceExtension
->NumberChannels
);
2519 if (!deviceExtension
->AhciInternalSrb0
) {
2520 KdPrint2((PRINT_PREFIX
"!deviceExtension->AhciInternalSrb0 => SP_RETURN_ERROR\n"));
2521 UniataFreeLunExt(deviceExtension
);
2524 RtlZeroMemory(deviceExtension
->AhciInternalSrb0
, sizeof(SCSI_REQUEST_BLOCK
)*deviceExtension
->NumberChannels
);
2528 deviceExtension
->lun
= (PHW_LU_EXTENSION
)ExAllocatePool(NonPagedPool
, sizeof(HW_LU_EXTENSION
) * (deviceExtension
->NumberChannels
+1) * deviceExtension
->NumberLuns
);
2529 if (!deviceExtension
->lun
) {
2530 KdPrint2((PRINT_PREFIX
"!deviceExtension->lun => SP_RETURN_ERROR\n"));
2531 UniataFreeLunExt(deviceExtension
);
2534 RtlZeroMemory(deviceExtension
->lun
, sizeof(HW_LU_EXTENSION
) * (deviceExtension
->NumberChannels
+1) * deviceExtension
->NumberLuns
);
2536 deviceExtension
->chan
= (PHW_CHANNEL
)ExAllocatePool(NonPagedPool
, sizeof(HW_CHANNEL
) * (deviceExtension
->NumberChannels
+1));
2537 if (!deviceExtension
->chan
) {
2538 UniataFreeLunExt(deviceExtension
);
2539 KdPrint2((PRINT_PREFIX
"!deviceExtension->chan => SP_RETURN_ERROR\n"));
2542 RtlZeroMemory(deviceExtension
->chan
, sizeof(HW_CHANNEL
) * (deviceExtension
->NumberChannels
+1));
2544 } // end UniataAllocateLunExt()
2549 PHW_DEVICE_EXTENSION deviceExtension
2552 if (deviceExtension
->lun
) {
2553 ExFreePool(deviceExtension
->lun
);
2554 deviceExtension
->lun
= NULL
;
2556 if (deviceExtension
->chan
) {
2557 ExFreePool(deviceExtension
->chan
);
2558 deviceExtension
->chan
= NULL
;
2560 if(deviceExtension
->AhciInternalAtaReq0
) {
2561 ExFreePool(deviceExtension
->AhciInternalAtaReq0
);
2562 deviceExtension
->AhciInternalAtaReq0
= NULL
;
2564 if(deviceExtension
->AhciInternalSrb0
) {
2565 ExFreePool(deviceExtension
->AhciInternalSrb0
);
2566 deviceExtension
->AhciInternalSrb0
= NULL
;
2570 } // end UniataFreeLunExt()