3 Copyright (c) 2004-2011 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\n"));
73 deviceExtension
->NumberLuns
= 2;
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
) {
136 if(ChipType
!= SIIMIO
) {
143 if(VendorID
== ATA_SILICON_IMAGE_ID
) {
144 KdPrint2((PRINT_PREFIX
"New SII\n"));
146 KdPrint2((PRINT_PREFIX
"ATI SATA\n"));
148 if(deviceExtension
->HwFlags
& SII4CH
) {
149 deviceExtension
->NumberChannels
= 4;
150 KdPrint2((PRINT_PREFIX
"4 chan\n"));
154 if(/*(deviceExtension->DevID == 0x32491106) &&
155 ScsiPortConvertPhysicalAddressToUlong((*ConfigInfo->AccessRanges)[5].RangeStart)*/
156 deviceExtension
->HwFlags
& VIABAR
) {
157 deviceExtension
->NumberChannels
= 3;
158 KdPrint2((PRINT_PREFIX
"VIA 3 chan\n"));
160 if(ChipFlags
& VIASATA
) {
161 /* 2 SATA without SATA registers on first channel + 1 PATA on second */
162 // do nothing, generic PATA INIT
163 KdPrint2((PRINT_PREFIX
"VIA SATA without SATA regs -> no PM\n"));
164 deviceExtension
->NumberLuns
= 1;
168 /* ITE ATA133 controller */
169 if(deviceExtension
->DevID
== 0x82131283) {
170 if(BMList
[deviceExtension
->DevIndex
].channel
) {
171 KdPrint2((PRINT_PREFIX
"New ITE has no 2nd PATA chan\n"));
174 deviceExtension
->NumberChannels
= 1;
175 KdPrint2((PRINT_PREFIX
"New ITE PATA 1 chan\n"));
179 /* New Intel PATA controllers */
180 if(/*deviceExtension->DevID == 0x27df8086 ||
181 deviceExtension->DevID == 0x269e8086 ||
182 deviceExtension->DevID == ATA_I82801HBM*/
184 if(BMList
[deviceExtension
->DevIndex
].channel
) {
185 KdPrint2((PRINT_PREFIX
"New Intel PATA has no 2nd chan\n"));
188 deviceExtension
->NumberChannels
= 1;
189 KdPrint2((PRINT_PREFIX
"New Intel PATA 1 chan\n"));
193 /* New JMicron PATA controllers */
194 if(deviceExtension
->DevID
== ATA_JMB361
||
195 deviceExtension
->DevID
== ATA_JMB363
||
196 deviceExtension
->DevID
== ATA_JMB368
) {
197 if(BMList
[deviceExtension
->DevIndex
].channel
) {
198 KdPrint2((PRINT_PREFIX
"New JMicron has no 2nd chan\n"));
201 deviceExtension
->NumberChannels
= 1;
202 KdPrint2((PRINT_PREFIX
"New JMicron PATA 1 chan\n"));
205 } // end switch(VendorID)
208 } // end UniataChipDetectChannels()
213 IN PVOID HwDeviceExtension
,
214 IN PPCI_COMMON_CONFIG pciData
, // optional
215 IN ULONG DeviceNumber
,
216 IN OUT PPORT_CONFIGURATION_INFORMATION ConfigInfo
,
217 IN BOOLEAN
* simplexOnly
220 PHW_DEVICE_EXTENSION deviceExtension
= (PHW_DEVICE_EXTENSION
)HwDeviceExtension
;
221 ULONG slotNumber
= deviceExtension
->slotNumber
;
222 ULONG SystemIoBusNumber
= deviceExtension
->SystemIoBusNumber
;
223 ULONG VendorID
= deviceExtension
->DevID
& 0xffff;
224 ULONG DeviceID
= (deviceExtension
->DevID
>> 16) & 0xffff;
225 ULONG RevID
= deviceExtension
->RevID
;
227 BUSMASTER_CONTROLLER_INFORMATION
* DevTypeInfo
;
233 ULONG BaseMemAddress
;
234 ULONG BaseIoAddress1
;
235 ULONG BaseIoAddress2
;
236 ULONG BaseIoAddressBM
;
237 BOOLEAN MemIo
= FALSE
;
239 KdPrint2((PRINT_PREFIX
"UniataChipDetect:\n" ));
240 KdPrint2((PRINT_PREFIX
"HwFlags: %#x\n", deviceExtension
->HwFlags
));
242 i
= Ata_is_dev_listed((PBUSMASTER_CONTROLLER_INFORMATION
)&BusMasterAdapters
[0], VendorID
, 0xffff, 0, NUM_BUSMASTER_ADAPTERS
);
244 c
= AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"ForceSimplex", 0);
250 BaseIoAddressBM
= pciData
->u
.type0
.BaseAddresses
[4] & ~0x07;
251 deviceExtension
->MaxTransferMode
= BaseIoAddressBM
? ATA_DMA
: ATA_PIO4
;
252 ConfigInfo
->MaximumTransferLength
= DEV_BSIZE
*256;
253 deviceExtension
->MaximumDmaTransferLength
= ConfigInfo
->MaximumTransferLength
;
255 KdPrint2((PRINT_PREFIX
"i: %#x\n", i
));
256 if(i
!= BMLIST_TERMINATOR
) {
257 DevTypeInfo
= (PBUSMASTER_CONTROLLER_INFORMATION
)&BusMasterAdapters
[i
];
259 if(Ata_is_ahci_dev(pciData
)) {
260 KdPrint2((PRINT_PREFIX
" AHCI candidate"));
262 deviceExtension
->NumberChannels
= 0;
263 if(!UniataAhciDetect(HwDeviceExtension
, pciData
, ConfigInfo
)) {
264 KdPrint2((PRINT_PREFIX
" AHCI init failed - not detected\n"));
265 return STATUS_UNSUCCESSFUL
;
267 KdPrint2((PRINT_PREFIX
" unknown AHCI dev, addr %#x", deviceExtension
->BaseIoAHCI_0
.Addr
));
270 KdPrint2((PRINT_PREFIX
" unknown dev, BM addr %#I64x", BaseIoAddressBM
));
272 KdPrint2((PRINT_PREFIX
" MaxTransferMode %#x\n", deviceExtension
->MaxTransferMode
));
274 if(!UniataChipDetectChannels(HwDeviceExtension
, pciData
, DeviceNumber
, ConfigInfo
)) {
275 return STATUS_UNSUCCESSFUL
;
277 if(!UniataAllocateLunExt(deviceExtension
, UNIATA_ALLOCATE_NEW_LUNS
)) {
278 return STATUS_UNSUCCESSFUL
;
281 return STATUS_NOT_FOUND
;
284 static BUSMASTER_CONTROLLER_INFORMATION
const SiSAdapters
[] = {
285 PCI_DEV_HW_SPEC_BM( 0182, 1039, 0x00, ATA_SA150
, "SiS 182" , SISSATA
| UNIATA_SATA
),
286 PCI_DEV_HW_SPEC_BM( 0181, 1039, 0x00, ATA_SA150
, "SiS 181" , SISSATA
| UNIATA_SATA
),
287 PCI_DEV_HW_SPEC_BM( 0180, 1039, 0x00, ATA_SA150
, "SiS 180" , SISSATA
| UNIATA_SATA
),
288 PCI_DEV_HW_SPEC_BM( 0965, 1039, 0x00, ATA_UDMA6
, "SiS 965" , SIS133NEW
),
289 PCI_DEV_HW_SPEC_BM( 0964, 1039, 0x00, ATA_UDMA6
, "SiS 964" , SIS133NEW
),
290 PCI_DEV_HW_SPEC_BM( 0963, 1039, 0x00, ATA_UDMA6
, "SiS 963" , SIS133NEW
),
291 PCI_DEV_HW_SPEC_BM( 0962, 1039, 0x00, ATA_UDMA6
, "SiS 962" , SIS133NEW
),
293 PCI_DEV_HW_SPEC_BM( 0745, 1039, 0x00, ATA_UDMA5
, "SiS 745" , SIS100NEW
),
294 PCI_DEV_HW_SPEC_BM( 0735, 1039, 0x00, ATA_UDMA5
, "SiS 735" , SIS100NEW
),
295 PCI_DEV_HW_SPEC_BM( 0733, 1039, 0x00, ATA_UDMA5
, "SiS 733" , SIS100NEW
),
296 PCI_DEV_HW_SPEC_BM( 0730, 1039, 0x00, ATA_UDMA5
, "SiS 730" , SIS100OLD
),
298 PCI_DEV_HW_SPEC_BM( 0646, 1039, 0x00, ATA_UDMA6
, "SiS 645DX", SIS133NEW
),
299 /* PCI_DEV_HW_SPEC_BM( 0645, 1039, 0x00, ATA_UDMA6, "SiS 645" , SIS133NEW ),*/
300 /* PCI_DEV_HW_SPEC_BM( 0640, 1039, 0x00, ATA_UDMA4, "SiS 640" , SIS_SOUTH ),*/
301 PCI_DEV_HW_SPEC_BM( 0635, 1039, 0x00, ATA_UDMA5
, "SiS 635" , SIS100NEW
),
302 PCI_DEV_HW_SPEC_BM( 0633, 1039, 0x00, ATA_UDMA5
, "SiS 633" , SIS100NEW
),
303 PCI_DEV_HW_SPEC_BM( 0630, 1039, 0x00, ATA_UDMA5
, "SiS 630S" , SIS100OLD
),
304 PCI_DEV_HW_SPEC_BM( 0630, 1039, 0x00, ATA_UDMA4
, "SiS 630" , SIS66
),
305 PCI_DEV_HW_SPEC_BM( 0620, 1039, 0x00, ATA_UDMA4
, "SiS 620" , SIS66
),
307 PCI_DEV_HW_SPEC_BM( 0550, 1039, 0x00, ATA_UDMA5
, "SiS 550" , SIS66
),
308 PCI_DEV_HW_SPEC_BM( 0540, 1039, 0x00, ATA_UDMA4
, "SiS 540" , SIS66
),
309 PCI_DEV_HW_SPEC_BM( 0530, 1039, 0x00, ATA_UDMA4
, "SiS 530" , SIS66
),
311 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x04, ATA_UDMA6, "SiS 962L" , SIS133OLD ), // ???
312 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x00, ATA_UDMA6, "SiS 961" , SIS133OLD ),
314 PCI_DEV_HW_SPEC_BM( 5517, 1039, 0x00, ATA_UDMA5
, "SiS 961" , SIS100NEW
| SIS_BASE
),
315 PCI_DEV_HW_SPEC_BM( 5518, 1039, 0x00, ATA_UDMA6
, "SiS 962/3", SIS133NEW
| SIS_BASE
),
316 PCI_DEV_HW_SPEC_BM( 5513, 1039, 0xc2, ATA_UDMA2
, "SiS 5513" , SIS33
| SIS_BASE
),
317 PCI_DEV_HW_SPEC_BM( 5513, 1039, 0x00, ATA_WDMA2
, "SiS 5513" , SIS33
| SIS_BASE
),
318 PCI_DEV_HW_SPEC_BM( 0601, 1039, 0x00, ATA_UDMA2
, "SiS 5513" , SIS33
| SIS_BASE
),
319 PCI_DEV_HW_SPEC_BM( ffff
, ffff
, 0xff, BMLIST_TERMINATOR
, NULL
, BMLIST_TERMINATOR
)
322 static BUSMASTER_CONTROLLER_INFORMATION
const ViaAdapters
[] = {
323 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x41, ATA_UDMA2
, "VIA 82C586B", VIA33
| 0x00 ),
324 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x40, ATA_UDMA2
, "VIA 82C586B", VIA33
| VIAPRQ
),
325 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x02, ATA_UDMA2
, "VIA 82C586B", VIA33
| 0x00 ),
326 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x00, ATA_WDMA2
, "VIA 82C586" , VIA33
| 0x00 ),
327 PCI_DEV_HW_SPEC_BM( 0596, 1106, 0x12, ATA_UDMA4
, "VIA 82C596B", VIA66
| VIACLK
),
328 PCI_DEV_HW_SPEC_BM( 0596, 1106, 0x00, ATA_UDMA2
, "VIA 82C596" , VIA33
| 0x00 ),
329 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x40, ATA_UDMA5
, "VIA 82C686B", VIA100
| VIABUG
),
330 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x10, ATA_UDMA4
, "VIA 82C686A", VIA66
| VIACLK
),
331 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x00, ATA_UDMA2
, "VIA 82C686" , VIA33
| 0x00 ),
332 PCI_DEV_HW_SPEC_BM( 8231, 1106, 0x00, ATA_UDMA5
, "VIA 8231" , VIA100
| VIABUG
),
333 PCI_DEV_HW_SPEC_BM( 3074, 1106, 0x00, ATA_UDMA5
, "VIA 8233" , VIA100
| 0x00 ),
334 PCI_DEV_HW_SPEC_BM( 3109, 1106, 0x00, ATA_UDMA5
, "VIA 8233C" , VIA100
| 0x00 ),
335 PCI_DEV_HW_SPEC_BM( 3147, 1106, 0x00, ATA_UDMA6
, "VIA 8233A" , VIA133
| 0x00 ),
336 PCI_DEV_HW_SPEC_BM( 3177, 1106, 0x00, ATA_UDMA6
, "VIA 8235" , VIA133
| 0x00 ),
337 PCI_DEV_HW_SPEC_BM( 3227, 1106, 0x00, ATA_UDMA6
, "VIA 8237" , VIA133
| 0x00 ),
338 PCI_DEV_HW_SPEC_BM( 0591, 1106, 0x00, ATA_UDMA6
, "VIA 8237A" , VIA133
| 0x00 ),
339 // presence of AHCI controller means something about isa-mapped part
340 PCI_DEV_HW_SPEC_BM( 5337, 1106, 0x00, ATA_UDMA6
, "VIA 8237S" , VIA133
| 0x00 ),
341 PCI_DEV_HW_SPEC_BM( 5372, 1106, 0x00, ATA_UDMA6
, "VIA 8237" , VIA133
| 0x00 ),
342 PCI_DEV_HW_SPEC_BM( 7372, 1106, 0x00, ATA_UDMA6
, "VIA 8237" , VIA133
| 0x00 ),
343 PCI_DEV_HW_SPEC_BM( 3349, 1106, 0x00, ATA_UDMA6
, "VIA 8251" , VIA133
| 0x00 ),
344 PCI_DEV_HW_SPEC_BM( 8324, 1106, 0x00, ATA_SA150
, "VIA CX700" , VIA133
| VIASATA
),
345 PCI_DEV_HW_SPEC_BM( 8353, 1106, 0x00, ATA_SA150
, "VIA VX800" , VIA133
| VIASATA
),
346 PCI_DEV_HW_SPEC_BM( 8409, 1106, 0x00, ATA_UDMA6
, "VIA VX855" , VIA133
| 0x00 ),
347 PCI_DEV_HW_SPEC_BM( 8410, 1106, 0x00, ATA_SA300
, "VIA VX900" , VIA133
| VIASATA
),
348 PCI_DEV_HW_SPEC_BM( ffff
, ffff
, 0xff, BMLIST_TERMINATOR
, NULL
, BMLIST_TERMINATOR
)
351 static BUSMASTER_CONTROLLER_INFORMATION
const ViaSouthAdapters
[] = {
352 PCI_DEV_HW_SPEC_BM( 3112, 1106, 0x00, -1, "VIA 8361", VIASOUTH
),
353 PCI_DEV_HW_SPEC_BM( 0305, 1106, 0x00, -1, "VIA 8363", VIASOUTH
),
354 PCI_DEV_HW_SPEC_BM( 0391, 1106, 0x00, -1, "VIA 8371", VIASOUTH
),
355 PCI_DEV_HW_SPEC_BM( 3102, 1106, 0x00, -1, "VIA 8662", VIASOUTH
),
356 PCI_DEV_HW_SPEC_BM( ffff
, ffff
, 0xff, BMLIST_TERMINATOR
, NULL
, BMLIST_TERMINATOR
)
359 KdPrint2((PRINT_PREFIX
"VendorID/DeviceID/Rev %#x/%#x/%#x\n", VendorID
, DeviceID
, RevID
));
364 KdPrint2((PRINT_PREFIX
"ATA_SIS_ID\n"));
365 DevTypeInfo
= (BUSMASTER_CONTROLLER_INFORMATION
*)&SiSAdapters
[0];
366 i
= AtapiFindListedDev(DevTypeInfo
, -1, HwDeviceExtension
, SystemIoBusNumber
, PCISLOTNUM_NOT_SPECIFIED
, NULL
);
367 if(i
!= BMLIST_TERMINATOR
) {
368 deviceExtension
->FullDevName
= SiSAdapters
[i
].FullDevName
;
373 KdPrint2((PRINT_PREFIX
"ATA_VIA_ID\n"));
374 // New chips have own DeviceId
375 if(deviceExtension
->DevID
!= ATA_VIA82C571
&&
376 deviceExtension
->DevID
!= ATA_VIACX700IDE
&&
377 deviceExtension
->DevID
!= ATA_VIASATAIDE
&&
378 deviceExtension
->DevID
!= ATA_VIASATAIDE2
&&
379 deviceExtension
->DevID
!= ATA_VIASATAIDE3
) {
380 KdPrint2((PRINT_PREFIX
"Via new\n"));
383 KdPrint2((PRINT_PREFIX
"Via-old-style %x\n", deviceExtension
->DevID
));
384 // Traditionally, chips have same DeviceId, we can distinguish between them
385 // only by ISA Bridge DeviceId
386 DevTypeInfo
= (BUSMASTER_CONTROLLER_INFORMATION
*)&ViaSouthAdapters
[0];
387 i
= AtapiFindListedDev(DevTypeInfo
, -1, HwDeviceExtension
, SystemIoBusNumber
,
388 PCISLOTNUM_NOT_SPECIFIED
/*slotNumber*/, NULL
);
389 /* if(i == BMLIST_TERMINATOR) {
390 i = AtapiFindListedDev(DevTypeInfo, -1, HwDeviceExtension, SystemIoBusNumber, PCISLOTNUM_NOT_SPECIFIED, NULL);
392 if(i
!= BMLIST_TERMINATOR
) {
393 KdPrint2((PRINT_PREFIX
"VIASOUTH\n"));
394 deviceExtension
->HwFlags
|= VIASOUTH
;
396 DevTypeInfo
= (BUSMASTER_CONTROLLER_INFORMATION
*)&ViaAdapters
[0];
397 i
= AtapiFindListedDev(DevTypeInfo
, -1, HwDeviceExtension
, SystemIoBusNumber
,
398 PCISLOTNUM_NOT_SPECIFIED
/*slotNumber*/, NULL
);
399 if(i
!= BMLIST_TERMINATOR
) {
400 deviceExtension
->FullDevName
= ViaAdapters
[i
].FullDevName
;
410 KdPrint2((PRINT_PREFIX
"Default\n"));
412 deviceExtension
->MaxTransferMode
= deviceExtension
->BaseIoAddressBM_0
? ATA_DMA
: ATA_PIO4
;
413 /* do extra chipset specific setups */
414 switch(deviceExtension
->DevID
) {
416 //case ATA_CYPRESS_ID:
417 case 0xc6931080: /* 82c693 ATA controller */
418 deviceExtension
->MaxTransferMode
= ATA_WDMA2
;
421 case 0x000116ca: /* Cenatek Rocket Drive controller */
422 deviceExtension
->MaxTransferMode
= ATA_WDMA2
;
425 /* case ATA_CYRIX_ID:
426 DevTypeInfo = &CyrixAdapters[0];
428 case 0x01021078: /* Cyrix 5530 ATA33 controller */
429 deviceExtension
->MaxTransferMode
= ATA_UDMA2
;
432 case 0x06401039: /* CMD 640 known bad, no DMA */
438 case 0x10001042: /* RZ 100x known bad, no DMA */
441 if(deviceExtension
->BaseIoAddressBM_0
)
442 ScsiPortFreeDeviceBase(HwDeviceExtension
,
443 deviceExtension
->BaseIoAddressBM_0
);
445 deviceExtension
->BaseIoAddressBM_0
= 0;
446 deviceExtension
->BusMaster
= FALSE
;
447 deviceExtension
->MaxTransferMode
= ATA_PIO4
;
450 case 0x81721283: /* IT8172 IDE controller */
451 deviceExtension
->MaxTransferMode
= ATA_UDMA2
;
456 return STATUS_NOT_FOUND
;
458 return STATUS_SUCCESS
;
462 i
= Ata_is_dev_listed(DevTypeInfo
, VendorID
, DeviceID
, RevID
, -1);
464 KdPrint2((PRINT_PREFIX
"i: %#x\n", i
));
465 if(i
== BMLIST_TERMINATOR
) {
467 //return STATUS_NOT_FOUND;
469 deviceExtension
->MaxTransferMode
= DevTypeInfo
[i
].MaxTransferMode
;
470 deviceExtension
->HwFlags
|= DevTypeInfo
[i
].RaidFlags
;
472 KdPrint2((PRINT_PREFIX
"HwFlags: %#x\n", deviceExtension
->HwFlags
));
474 tmp32
= AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"HwFlagsOverride", deviceExtension
->HwFlags
);
475 KdPrint2((PRINT_PREFIX
"HwFlagsOverride: %#x\n", tmp32
));
476 deviceExtension
->HwFlags
= tmp32
;
478 tmp32
= AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"HwFlagsAdd", 0);
479 KdPrint2((PRINT_PREFIX
"HwFlagsAdd: %#x\n", tmp32
));
480 deviceExtension
->HwFlags
|= tmp32
;
482 KdPrint2((PRINT_PREFIX
"HwFlags (final): %#x\n", deviceExtension
->HwFlags
));
483 if(deviceExtension
->HwFlags
& UNIATA_SIMPLEX_ONLY
) {
484 KdPrint2((PRINT_PREFIX
"UNIATA_SIMPLEX_ONLY\n" ));
488 KdPrint2((PRINT_PREFIX
"MaxTransferMode: %#x\n", deviceExtension
->MaxTransferMode
));
489 tmp32
= AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"MaxTransferMode", deviceExtension
->MaxTransferMode
);
490 if(tmp32
!= 0xffffffff) {
491 KdPrint2((PRINT_PREFIX
"MaxTransferMode (overriden): %#x\n", deviceExtension
->MaxTransferMode
));
492 deviceExtension
->MaxTransferMode
= tmp32
;
495 if(deviceExtension
->MaxTransferMode
>= ATA_SA150
) {
496 deviceExtension
->HwFlags
|= UNIATA_SATA
;
499 ConfigInfo->MaximumTransferLength = DEV_BSIZE*256;
500 deviceExtension->MaximumDmaTransferLength = ConfigInfo->MaximumTransferLength;
502 ChipType
= deviceExtension
->HwFlags
& CHIPTYPE_MASK
;
503 ChipFlags
= deviceExtension
->HwFlags
& CHIPFLAG_MASK
;
505 if(ChipFlags
& UNIATA_AHCI
) {
506 deviceExtension
->NumberChannels
= 0;
507 if(!UniataAhciDetect(HwDeviceExtension
, pciData
, ConfigInfo
)) {
508 KdPrint2((PRINT_PREFIX
" AHCI detect failed\n"));
509 return STATUS_UNSUCCESSFUL
;
512 if(!UniataChipDetectChannels(HwDeviceExtension
, pciData
, DeviceNumber
, ConfigInfo
)) {
513 return STATUS_UNSUCCESSFUL
;
515 // UniataAhciDetect() sets proper number of channels
516 if(!UniataAllocateLunExt(deviceExtension
, UNIATA_ALLOCATE_NEW_LUNS
)) {
517 return STATUS_UNSUCCESSFUL
;
520 if(ChipFlags
& UNIATA_AHCI
) {
524 case ATA_ACER_LABS_ID
:
525 if(ChipFlags
& UNIATA_SATA
) {
526 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
527 BaseIoAddress1
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
529 BaseIoAddress2
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
531 BaseIoAddressBM
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
532 4, 0, deviceExtension
->NumberChannels
*sizeof(IDE_BUSMASTER_REGISTERS
));
533 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
534 //ULONG unit01 = (c & 1);
535 ULONG unit10
= (c
& 2);
536 chan
= &deviceExtension
->chan
[c
];
538 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
539 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseIoAddress1
+ i
+ (unit10
? 8 : 0);
541 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseIoAddress2
+ 2 + (unit10
? 4 : 0);
542 UniataInitSyncBaseIO(chan
);
544 for (i
=0; i
<=IDX_BM_IO_SZ
; i
++) {
545 chan
->RegTranslation
[IDX_BM_IO
+i
].Addr
= BaseIoAddressBM
+ i
+ (c
* sizeof(IDE_BUSMASTER_REGISTERS
));
548 // SATA not supported yet
550 //chan->RegTranslation[IDX_BM_Command] = BaseMemAddress + 0x260 + offs7;
551 //chan->RegTranslation[IDX_BM_PRD_Table] = BaseMemAddress + 0x244 + offs7;
552 //chan->RegTranslation[IDX_BM_DeviceSpecific0] = BaseMemAddress + (c << 2);
554 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
559 if(ChipFlags
& UNIATA_SATA
) {
560 KdPrint2((PRINT_PREFIX
"NVIDIA SATA\n"));
561 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
562 5, 0, ((ChipFlags
& NV4OFF
) ? 0x400 : 0) + 0x40*2);
563 KdPrint2((PRINT_PREFIX
"BaseMemAddress %x\n", BaseMemAddress
));
564 if((*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
565 KdPrint2((PRINT_PREFIX
"MemIo\n"));
568 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
569 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
570 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
571 chan
= &deviceExtension
->chan
[c
];
573 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ (c
<< 6);
574 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
575 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ 4 + (c
<< 6);
576 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
577 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ 8 + (c
<< 6);
578 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
580 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
586 if(ChipType
!= PRMIO
) {
592 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
593 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
595 KdPrint2((PRINT_PREFIX
"BaseMemAddress %x\n", BaseMemAddress
));
596 if((*ConfigInfo
->AccessRanges
)[4].RangeInMemory
) {
597 KdPrint2((PRINT_PREFIX
"MemIo\n"));
600 deviceExtension
->BaseIoAddressBM_0
.Addr
= BaseMemAddress
;
601 deviceExtension
->BaseIoAddressBM_0
.MemIo
= MemIo
;
602 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
606 chan
= &deviceExtension
->chan
[c
];
611 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
612 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseMemAddress
+ 0x200 + (i
<< 2) + offs12
;
613 chan
->RegTranslation
[IDX_IO1
+i
].MemIo
= MemIo
;
615 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseMemAddress
+ 0x238 + offs7
;
616 chan
->RegTranslation
[IDX_IO2_AltStatus
].MemIo
= MemIo
;
618 UniataInitSyncBaseIO(chan
);
620 chan
->RegTranslation
[IDX_BM_Command
].Addr
= BaseMemAddress
+ 0x260 + offs7
;
621 chan
->RegTranslation
[IDX_BM_Command
].MemIo
= MemIo
;
622 chan
->RegTranslation
[IDX_BM_PRD_Table
].Addr
= BaseMemAddress
+ 0x244 + offs7
;
623 chan
->RegTranslation
[IDX_BM_PRD_Table
].MemIo
= MemIo
;
624 chan
->RegTranslation
[IDX_BM_DeviceSpecific0
].Addr
= BaseMemAddress
+ (c
<< 2);
625 chan
->RegTranslation
[IDX_BM_DeviceSpecific0
].MemIo
= MemIo
;
630 KdPrint2((PRINT_PREFIX
"ATI\n"));
632 case ATA_SILICON_IMAGE_ID
: {
634 if(ChipFlags
& SIIBUG
) {
636 if(ChipType
!= SIIMIO
) {
643 if(VendorID
== ATA_SILICON_IMAGE_ID
) {
644 KdPrint2((PRINT_PREFIX
"New SII\n"));
646 KdPrint2((PRINT_PREFIX
"ATI SATA\n"));
648 //if(deviceExtension->HwFlags & SII4CH) {
649 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
651 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
653 KdPrint2((PRINT_PREFIX
"BaseMemAddress %x\n", BaseMemAddress
));
654 if((*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
655 KdPrint2((PRINT_PREFIX
"MemIo\n"));
658 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
659 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
661 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
662 ULONG unit01
= (c
& 1);
663 ULONG unit10
= (c
& 2);
665 chan
= &deviceExtension
->chan
[c
];
667 if(deviceExtension
->AltRegMap
) {
668 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
669 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseMemAddress
+ 0x80 + i
+ (unit01
<< 6) + (unit10
<< 8);
670 chan
->RegTranslation
[IDX_IO1
+i
].MemIo
= MemIo
;
672 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseMemAddress
+ 0x8a + (unit01
<< 6) + (unit10
<< 8);
673 chan
->RegTranslation
[IDX_IO2_AltStatus
].MemIo
= MemIo
;
674 UniataInitSyncBaseIO(chan
);
676 chan
->RegTranslation
[IDX_BM_Command
].Addr
= BaseMemAddress
+ 0x00 + (unit01
<< 3) + (unit10
<< 8);
677 chan
->RegTranslation
[IDX_BM_Command
].MemIo
= MemIo
;
678 chan
->RegTranslation
[IDX_BM_Status
].Addr
= BaseMemAddress
+ 0x02 + (unit01
<< 3) + (unit10
<< 8);
679 chan
->RegTranslation
[IDX_BM_Status
].MemIo
= MemIo
;
680 chan
->RegTranslation
[IDX_BM_PRD_Table
].Addr
= BaseMemAddress
+ 0x04 + (unit01
<< 3) + (unit10
<< 8);
681 chan
->RegTranslation
[IDX_BM_PRD_Table
].MemIo
= MemIo
;
682 //chan->RegTranslation[IDX_BM_DeviceSpecific0].Addr = BaseMemAddress + 0xa1 + (unit01 << 6) + (unit10 << 8);
683 //chan->RegTranslation[IDX_BM_DeviceSpecific0].MemIo = MemIo;
684 chan
->RegTranslation
[IDX_BM_DeviceSpecific0
].Addr
= BaseMemAddress
+ 0x10 + (unit01
<< 3) + (unit10
<< 8);
685 chan
->RegTranslation
[IDX_BM_DeviceSpecific0
].MemIo
= MemIo
;
686 chan
->RegTranslation
[IDX_BM_DeviceSpecific1
].Addr
= BaseMemAddress
+ 0x40 + (unit01
<< 2) + (unit10
<< 8);
687 chan
->RegTranslation
[IDX_BM_DeviceSpecific1
].MemIo
= MemIo
;
690 if(ChipFlags
& UNIATA_SATA
) {
691 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ 0x104 + (unit01
<< 7) + (unit10
<< 8);
692 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
693 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ 0x108 + (unit01
<< 7) + (unit10
<< 8);
694 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
695 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ 0x100 + (unit01
<< 7) + (unit10
<< 8);
696 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
698 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
703 case ATA_SERVERWORKS_ID
: {
705 if(ChipType
!= SWKSMIO
) {
712 KdPrint2((PRINT_PREFIX
"ServerWorks\n"));
714 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
715 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
717 KdPrint2((PRINT_PREFIX
"BaseMemAddress %x\n", BaseMemAddress
));
718 if((*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
719 KdPrint2((PRINT_PREFIX
"MemIo\n"));
722 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
723 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
725 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
726 ULONG offs
= c
*0x100;
728 chan
= &deviceExtension
->chan
[c
];
729 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
730 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseMemAddress
+ offs
+ i
*4;
731 chan
->RegTranslation
[IDX_IO1
+i
].MemIo
= MemIo
;
733 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseMemAddress
+ offs
+ 0x20;
734 chan
->RegTranslation
[IDX_IO2_AltStatus
].MemIo
= MemIo
;
735 UniataInitSyncBaseIO(chan
);
737 chan
->RegTranslation
[IDX_BM_Command
].Addr
= BaseMemAddress
+ offs
+ 0x30;
738 chan
->RegTranslation
[IDX_BM_Command
].MemIo
= MemIo
;
739 chan
->RegTranslation
[IDX_BM_Status
].Addr
= BaseMemAddress
+ offs
+ 0x32;
740 chan
->RegTranslation
[IDX_BM_Status
].MemIo
= MemIo
;
741 chan
->RegTranslation
[IDX_BM_PRD_Table
].Addr
= BaseMemAddress
+ offs
+ 0x34;
742 chan
->RegTranslation
[IDX_BM_PRD_Table
].MemIo
= MemIo
;
744 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ offs
+ 0x40;
745 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
746 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ offs
+ 0x44;
747 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
748 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ offs
+ 0x48;
749 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
751 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
756 //if(ChipType != SIS_SOUTH) {}
757 BOOLEAN SIS_182
=FALSE
;
759 if(!(ChipFlags
& SIS_BASE
)) {
760 KdPrint2((PRINT_PREFIX
"Found SIS_SOUTH\n"));
761 //PrintNtConsole("Found SIS_SOUTH\n");
764 // Make some additional checks
765 KdPrint2((PRINT_PREFIX
"ChipType == SIS_BASE\n"));
766 ChangePciConfig1(0x57, (a
& 0x7f));
767 GetPciConfig4(0x00, tmp32
);
768 if(tmp32
== ATA_SIS5518
) {
769 ChipType
= SIS133NEW
;
770 deviceExtension
->HwFlags
= (deviceExtension
->HwFlags
& ~CHIPTYPE_MASK
) | SIS133NEW
;
771 deviceExtension
->MaxTransferMode
= ATA_UDMA6
;
772 KdPrint2((PRINT_PREFIX
"UniataChipDetect: SiS 962/963 DMA %#x controller\n", deviceExtension
->MaxTransferMode
));
773 //PrintNtConsole("UniataChipDetect: SiS 962/963 DMA %#x controller\n", deviceExtension->MaxTransferMode);
775 ChangePciConfig1(0x57, (a
| 0x80));
777 static BUSMASTER_CONTROLLER_INFORMATION
const SiSSouthAdapters
[] = {
778 PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x10, -1, "SiS 961", 0 ),
779 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x00, -1, "SiS 961", 0 ),
780 PCI_DEV_HW_SPEC_BM( ffff
, ffff
, 0xff, -1, NULL
, -1 )
783 GetPciConfig1(0x4a, tmp8
);
784 ChangePciConfig1(0x4a, (a
| 0x10));
785 if(tmp32
== ATA_SIS5513
||
786 tmp32
== ATA_SIS5517
) {
787 i
= AtapiFindListedDev((BUSMASTER_CONTROLLER_INFORMATION
*)&SiSSouthAdapters
[0],
788 -1, HwDeviceExtension
, SystemIoBusNumber
, PCISLOTNUM_NOT_SPECIFIED
, NULL
);
789 if(i
!= BMLIST_TERMINATOR
) {
790 deviceExtension
->HwFlags
= (deviceExtension
->HwFlags
& ~CHIPTYPE_MASK
) | SIS133OLD
;
791 //deviceExtension->MaxTransferMode = ATA_UDMA6;
792 deviceExtension
->MaxTransferMode
= SiSSouthAdapters
[i
].MaxTransferMode
;
793 if(SiSSouthAdapters
[i
].RaidFlags
& UNIATA_SATA
) {
794 deviceExtension
->HwFlags
|= UNIATA_SATA
;
795 if(SiSSouthAdapters
[i
].nDeviceId
== 0x1182) {
800 // SiS-South not found
801 if(tmp32
== ATA_SIS5517
) {
802 deviceExtension
->HwFlags
= (deviceExtension
->HwFlags
& ~CHIPTYPE_MASK
) | SIS100NEW
;
803 deviceExtension
->MaxTransferMode
= ATA_UDMA5
;
806 KdPrint2((PRINT_PREFIX
"Generic SiS DMA\n"));
811 SetPciConfig1(0x4a, tmp8
);
812 KdPrint2((PRINT_PREFIX
"UniataChipDetect: SiS 961 DMA %#x controller\n", deviceExtension
->MaxTransferMode
));
813 //PrintNtConsole("UniataChipDetect: SiS 961 DMA %#x controller\n", deviceExtension->MaxTransferMode);
814 if(deviceExtension
->HwFlags
& UNIATA_SATA
) {
815 KdPrint2((PRINT_PREFIX
"SiS SATA\n"));
817 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
819 KdPrint2((PRINT_PREFIX
"BaseMemAddress %x\n", BaseMemAddress
));
820 if((*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
821 KdPrint2((PRINT_PREFIX
"MemIo\n"));
824 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
825 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
827 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
828 ULONG offs
= c
<< (SIS_182
? 5 : 6);
830 chan
= &deviceExtension
->chan
[c
];
831 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ 0 + offs
;
832 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
833 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ 4 + offs
;
834 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
835 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ 8 + offs
;
836 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
838 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
842 //ChangePciConfig1(0x57, (a | 0x80));
847 if(ChipFlags
& VIASATA
) {
848 /* 2 SATA without SATA registers on first channel + 1 PATA on second */
849 // do nothing, generic PATA INIT
850 KdPrint2((PRINT_PREFIX
"VIA SATA without SATA regs\n"));
853 if(ChipFlags
& UNIATA_SATA
) {
856 ULONG BaseMemAddress
= 0;
859 case 0x3149: // VIA 6420
860 KdPrint2((PRINT_PREFIX
"VIA 6420\n"));
863 case 0x3249: // VIA 6421
864 KdPrint2((PRINT_PREFIX
"VIA 6421\n"));
869 KdPrint2((PRINT_PREFIX
"IoSize %x\n", IoSize
));
870 /*deviceExtension->*/BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
871 5, 0, IoSize
* deviceExtension
->NumberChannels
);
872 if(BaseMemAddress
&& (*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
873 KdPrint2((PRINT_PREFIX
"MemIo\n"));
876 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
877 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
879 if(/*deviceExtension->*/BaseMemAddress
) {
880 KdPrint2((PRINT_PREFIX
"UniataChipDetect: BAR5 %x\n", /*deviceExtension->*/BaseMemAddress
));
881 if(ChipFlags
& VIABAR
) {
883 ULONG BaseIoAddressBM_0
;
886 KdPrint2((PRINT_PREFIX
"UniataChipDetect: VIABAR\n"));
887 /*deviceExtension->*/BaseIoAddressBM_0
= /*(PIDE_BUSMASTER_REGISTERS)*/
888 AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
, 4, 0,
889 sizeof(IDE_BUSMASTER_REGISTERS
)*deviceExtension
->NumberChannels
);
890 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
891 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
893 chan
= &deviceExtension
->chan
[c
];
895 BaseIo
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
, c
, 0, /*0x80*/ sizeof(IDE_REGISTERS_1
) + sizeof(IDE_REGISTERS_2
)*2);
897 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
898 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseIo
+ i
;
900 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseIo
+ sizeof(IDE_REGISTERS_1
) + 2;
901 UniataInitSyncBaseIO(chan
);
903 for (i
=0; i
<=IDX_BM_IO_SZ
; i
++) {
904 chan
->RegTranslation
[IDX_BM_IO
+i
].Addr
= BaseIoAddressBM_0
+ sizeof(IDE_BUSMASTER_REGISTERS
)*c
+ i
;
909 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
910 chan
= &deviceExtension
->chan
[c
];
911 if((ChipFlags
& VIABAR
) && (c
==2)) {
912 // Do not setup SATA registers for PATA part
913 for (i
=0; i
<=IDX_SATA_IO_SZ
; i
++) {
914 chan
->RegTranslation
[IDX_SATA_IO
+i
].Addr
= 0;
915 chan
->RegTranslation
[IDX_SATA_IO
+i
].MemIo
= 0;
919 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ (c
* IoSize
);
920 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
921 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ 4 + (c
* IoSize
);
922 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
923 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ 8 + (c
* IoSize
);
924 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
926 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
935 if(!(ChipFlags
& UNIATA_SATA
)) {
939 /* the intel 31244 needs special care if in DPA mode */
940 if(DeviceID
== 3200 && // Intel 31244
941 pciData
->SubClass
!= PCI_DEV_SUBCLASS_IDE
) {
943 KdPrint2((PRINT_PREFIX
"UniataChipDetect: Intel 31244, DPA mode\n"));
944 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
946 if((*ConfigInfo
->AccessRanges
)[0].RangeInMemory
) {
947 KdPrint2((PRINT_PREFIX
"MemIo\n"));
950 deviceExtension
->AltRegMap
= TRUE
; // inform generic resource allocator
951 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
952 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
954 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
955 ULONG offs
= 0x200 + c
*0x200;
957 chan
= &deviceExtension
->chan
[c
];
958 for (i
=0; i
<=IDX_IO1_SZ
; i
++) {
959 chan
->RegTranslation
[IDX_IO1
+i
].MemIo
= MemIo
;
960 chan
->RegTranslation
[IDX_IO1_o
+i
].MemIo
= MemIo
;
963 chan
->RegTranslation
[IDX_IO1_i_Data
].Addr
= BaseMemAddress
+ 0x00 + offs
;
964 chan
->RegTranslation
[IDX_IO1_i_Error
].Addr
= BaseMemAddress
+ 0x04 + offs
;
965 chan
->RegTranslation
[IDX_IO1_i_BlockCount
].Addr
= BaseMemAddress
+ 0x08 + offs
;
966 chan
->RegTranslation
[IDX_IO1_i_BlockNumber
].Addr
= BaseMemAddress
+ 0x0c + offs
;
967 chan
->RegTranslation
[IDX_IO1_i_CylinderLow
].Addr
= BaseMemAddress
+ 0x10 + offs
;
968 chan
->RegTranslation
[IDX_IO1_i_CylinderHigh
].Addr
= BaseMemAddress
+ 0x14 + offs
;
969 chan
->RegTranslation
[IDX_IO1_i_DriveSelect
].Addr
= BaseMemAddress
+ 0x18 + offs
;
970 chan
->RegTranslation
[IDX_IO1_i_Status
].Addr
= BaseMemAddress
+ 0x1c + offs
;
972 UniataInitSyncBaseIO(chan
);
974 chan
->RegTranslation
[IDX_IO1_o_Command
].Addr
= BaseMemAddress
+ 0x1d + offs
;
975 chan
->RegTranslation
[IDX_IO1_o_Feature
].Addr
= BaseMemAddress
+ 0x06 + offs
;
976 chan
->RegTranslation
[IDX_IO2_o_Control
].Addr
= BaseMemAddress
+ 0x29 + offs
;
978 chan
->RegTranslation
[IDX_IO2_AltStatus
].Addr
= BaseMemAddress
+ 0x28 + offs
;
979 chan
->RegTranslation
[IDX_IO2_AltStatus
].MemIo
= MemIo
;
981 chan
->RegTranslation
[IDX_BM_Command
].Addr
= BaseMemAddress
+ offs
+ 0x70;
982 chan
->RegTranslation
[IDX_BM_Command
].MemIo
= MemIo
;
983 chan
->RegTranslation
[IDX_BM_Status
].Addr
= BaseMemAddress
+ offs
+ 0x72;
984 chan
->RegTranslation
[IDX_BM_Status
].MemIo
= MemIo
;
985 chan
->RegTranslation
[IDX_BM_PRD_Table
].Addr
= BaseMemAddress
+ offs
+ 0x74;
986 chan
->RegTranslation
[IDX_BM_PRD_Table
].MemIo
= MemIo
;
988 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= BaseMemAddress
+ 0x100 + offs
;
989 chan
->RegTranslation
[IDX_SATA_SStatus
].MemIo
= MemIo
;
990 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= BaseMemAddress
+ 0x104 + offs
;
991 chan
->RegTranslation
[IDX_SATA_SError
].MemIo
= MemIo
;
992 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= BaseMemAddress
+ 0x108 + offs
;
993 chan
->RegTranslation
[IDX_SATA_SControl
].MemIo
= MemIo
;
995 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1000 if(deviceExtension
->MaxTransferMode
>= ATA_SA150
) {
1001 GetPciConfig1(0x90, tmp8
);
1002 KdPrint2((PRINT_PREFIX
"Intel chip config: %x\n", tmp8
));
1003 /* SATA parts can be either compat or AHCI */
1004 if(ChipFlags
& UNIATA_AHCI
) {
1007 //KdPrint2((PRINT_PREFIX "AHCI not supported yet\n"));
1009 KdPrint2((PRINT_PREFIX
"try run AHCI\n"));
1012 KdPrint2((PRINT_PREFIX
"Compatible mode\n"));
1014 deviceExtension
->HwFlags
&= ~UNIATA_AHCI
;
1016 /* if BAR(5) is IO it should point to SATA interface registers */
1017 BaseMemAddress
= AtapiGetIoRange(HwDeviceExtension
, ConfigInfo
, pciData
, SystemIoBusNumber
,
1019 if(BaseMemAddress
&& (*ConfigInfo
->AccessRanges
)[5].RangeInMemory
) {
1020 KdPrint2((PRINT_PREFIX
"MemIo\n"));
1023 deviceExtension
->BaseIoAddressSATA_0
.Addr
= BaseMemAddress
;
1024 deviceExtension
->BaseIoAddressSATA_0
.MemIo
= MemIo
;
1026 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
1027 chan
= &deviceExtension
->chan
[c
];
1029 if(ChipFlags
& ICH5
) {
1030 KdPrint2((PRINT_PREFIX
"ICH5\n"));
1031 if ((tmp8
& 0x04) == 0) {
1032 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1033 } else if ((tmp8
& 0x02) == 0) {
1036 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA;
1038 } else if ((tmp8
& 0x02) != 0) {
1041 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA;
1045 if(ChipFlags
& I6CH2
) {
1046 KdPrint2((PRINT_PREFIX
"I6CH2\n"));
1047 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1049 KdPrint2((PRINT_PREFIX
"other Intel\n"));
1050 switch(tmp8
& 0x03) {
1067 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA5
);
1068 KdPrint2((PRINT_PREFIX
"PATA part\n"));
1071 if(/*(ChipFlags & ICH5) &&*/ BaseMemAddress
) {
1072 KdPrint2((PRINT_PREFIX
"BaseMemAddress[5] -> indexed\n"));
1073 chan
->RegTranslation
[IDX_INDEXED_ADDR
].Addr
= BaseMemAddress
+ 0;
1074 chan
->RegTranslation
[IDX_INDEXED_ADDR
].MemIo
= MemIo
;
1075 chan
->RegTranslation
[IDX_INDEXED_DATA
].Addr
= BaseMemAddress
+ 4;
1076 chan
->RegTranslation
[IDX_INDEXED_DATA
].MemIo
= MemIo
;
1078 if((ChipFlags
& ICH5
) || BaseMemAddress
) {
1080 KdPrint2((PRINT_PREFIX
"io indexed\n"));
1081 // Rather interesting way of register access...
1082 ChipType
= INTEL_IDX
;
1083 deviceExtension
->HwFlags
&= ~CHIPTYPE_MASK
;
1084 deviceExtension
->HwFlags
|= ChipType
;
1086 chan
->RegTranslation
[IDX_SATA_SStatus
].Addr
= 0x200*c
+ 0;
1087 chan
->RegTranslation
[IDX_SATA_SStatus
].Proc
= 1;
1088 chan
->RegTranslation
[IDX_SATA_SError
].Addr
= 0x200*c
+ 2;
1089 chan
->RegTranslation
[IDX_SATA_SError
].Proc
= 1;
1090 chan
->RegTranslation
[IDX_SATA_SControl
].Addr
= 0x200*c
+ 1;
1091 chan
->RegTranslation
[IDX_SATA_SControl
].Proc
= 1;
1097 // rest of INIT staff is in AtapiChipInit()
1102 /* Cyrix 5530 ATA33 controller */
1103 if(deviceExtension
->DevID
== 0x01021078) {
1104 ConfigInfo
->AlignmentMask
= 0x0f;
1105 deviceExtension
->MaximumDmaTransferLength
= 63*1024;
1108 case ATA_JMICRON_ID
:
1109 /* New JMicron PATA controllers */
1110 GetPciConfig1(0xdf, tmp8
);
1112 KdPrint((" Check JMicron AHCI\n"));
1113 if(Ata_is_ahci_dev(pciData
)) {
1114 ChipFlags
|= UNIATA_AHCI
;
1115 deviceExtension
->HwFlags
|= UNIATA_AHCI
;
1117 KdPrint((" JMicron PATA\n"));
1120 /* set controller configuration to a combined setup we support */
1121 SetPciConfig4(0x40, 0x80c0a131);
1122 SetPciConfig4(0x80, 0x01200000);
1123 //KdPrint((" JMicron Combined (not supported yet)\n"));
1124 //return STATUS_NOT_FOUND;
1129 return STATUS_SUCCESS
;
1131 } // end UniataChipDetect()
1135 Do some 'magic staff' for VIA SouthBridge
1136 This will prevent data losses
1140 AtapiViaSouthBridgeFixup(
1141 IN PVOID HwDeviceExtension
,
1142 IN BUS_DATA_TYPE BusDataType
,
1143 IN ULONG SystemIoBusNumber
,
1147 PHW_DEVICE_EXTENSION deviceExtension
= (PHW_DEVICE_EXTENSION
)HwDeviceExtension
;
1148 PCI_COMMON_CONFIG pciData
;
1154 PCI_SLOT_NUMBER slotData
;
1156 BOOLEAN found
= FALSE
;
1158 slotData
.u
.AsULONG
= slotNumber
;
1159 for(funcNumber
= 0; funcNumber
< PCI_MAX_FUNCTION
; funcNumber
++) {
1161 slotData
.u
.bits
.FunctionNumber
= funcNumber
;
1163 busDataRead
= ScsiPortGetBusData(HwDeviceExtension
,
1168 PCI_COMMON_HDR_LENGTH
);
1170 if (busDataRead
< (ULONG
)PCI_COMMON_HDR_LENGTH
) {
1174 VendorID
= pciData
.VendorID
;
1175 DeviceID
= pciData
.DeviceID
;
1176 dev_id
= (VendorID
| (DeviceID
<< 16));
1178 if (dev_id
== 0x03051106 || /* VIA VT8363 */
1179 dev_id
== 0x03911106 || /* VIA VT8371 */
1180 dev_id
== 0x31021106 || /* VIA VT8662 */
1181 dev_id
== 0x31121106) { /* VIA VT8361 */
1184 GetPciConfig1(0x76, reg76
);
1186 if ((reg76
& 0xf0) != 0xd0) {
1187 SetPciConfig1(0x75, 0x80);
1188 SetPciConfig1(0x76, (reg76
& 0x0f) | 0xd0);
1195 deviceExtension
->HwFlags
&= ~VIABUG
;
1197 } // end AtapiViaSouthBridgeFixup()
1200 Do some 'magic staff' for ROSB SouthBridge
1201 This will prevent data losses
1205 AtapiRosbSouthBridgeFixup(
1206 IN PVOID HwDeviceExtension
,
1207 IN BUS_DATA_TYPE BusDataType
,
1208 IN ULONG SystemIoBusNumber
,
1212 //PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension;
1213 PCI_COMMON_CONFIG pciData
;
1219 PCI_SLOT_NUMBER slotData
;
1221 // BOOLEAN found = FALSE;
1223 /* locate the ISA part in the southbridge and enable UDMA33 */
1224 slotData
.u
.AsULONG
= slotNumber
;
1225 for(funcNumber
= 0; funcNumber
< PCI_MAX_FUNCTION
; funcNumber
++) {
1227 slotData
.u
.bits
.FunctionNumber
= funcNumber
;
1229 busDataRead
= ScsiPortGetBusData(HwDeviceExtension
,
1234 PCI_COMMON_HDR_LENGTH
);
1236 if (busDataRead
< (ULONG
)PCI_COMMON_HDR_LENGTH
) {
1240 VendorID
= pciData
.VendorID
;
1241 DeviceID
= pciData
.DeviceID
;
1242 dev_id
= (VendorID
| (DeviceID
<< 16));
1244 if (dev_id
== ATA_ROSB4_ISA
) { /* */
1245 ChangePciConfig4(0x64, ((a
& ~0x00002000) | 0x00004000));
1249 } // end AtapiRosbSouthBridgeFixup()
1252 Do some 'magic staff' for ROSB SouthBridge
1253 This will prevent data losses
1257 AtapiAliSouthBridgeFixup(
1258 IN PVOID HwDeviceExtension
,
1259 IN BUS_DATA_TYPE BusDataType
,
1260 IN ULONG SystemIoBusNumber
,
1261 IN ULONG slotNumber
,
1265 //PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension;
1266 PCI_COMMON_CONFIG pciData
;
1272 PCI_SLOT_NUMBER slotData
;
1274 // BOOLEAN found = FALSE;
1276 /* workaround for datacorruption bug found on at least SUN Blade-100
1277 * find the ISA function on the southbridge and disable then enable
1278 * the ATA channel tristate buffer */
1279 slotData
.u
.AsULONG
= slotNumber
;
1280 for(funcNumber
= 0; funcNumber
< PCI_MAX_FUNCTION
; funcNumber
++) {
1282 slotData
.u
.bits
.FunctionNumber
= funcNumber
;
1284 busDataRead
= ScsiPortGetBusData(HwDeviceExtension
,
1289 PCI_COMMON_HDR_LENGTH
);
1291 if (busDataRead
< (ULONG
)PCI_COMMON_HDR_LENGTH
) {
1295 VendorID
= pciData
.VendorID
;
1296 DeviceID
= pciData
.DeviceID
;
1297 dev_id
= (VendorID
| (DeviceID
<< 16));
1299 if (dev_id
== ATA_ALI_1533
) { /* SOUTH */
1300 ChangePciConfig1(0x58, (a
& ~(0x04 << c
)));
1301 ChangePciConfig1(0x58, (a
| (0x04 << c
)));
1305 } // end AtapiRosbSouthBridgeFixup()
1310 IN PHW_DEVICE_EXTENSION deviceExtension
,
1311 IN ULONG channel
// physical channel number (0-1)
1314 PVOID HwDeviceExtension
= (PVOID
)deviceExtension
;
1315 ULONG slotNumber
= deviceExtension
->slotNumber
;
1316 ULONG SystemIoBusNumber
= deviceExtension
->SystemIoBusNumber
;
1318 ULONG ChipType
= deviceExtension
->HwFlags
& CHIPTYPE_MASK
;
1320 UCHAR reg
, val
, res
;
1321 PCI_SLOT_NUMBER slotData
;
1323 slotData
.u
.AsULONG
= deviceExtension
->slotNumber
;
1325 if(ChipType
== HPT374
&& slotData
.u
.bits
.FunctionNumber
== 1) {
1326 reg
= channel
? 0x57 : 0x53;
1327 GetPciConfig1(reg
, val
);
1328 SetPciConfig1(reg
, val
| 0x80);
1332 GetPciConfig1(reg
, val
);
1333 SetPciConfig1(reg
, val
& 0xfe);
1335 GetPciConfig1(0x5a, res
);
1336 res
= res
& (channel
? 0x01 : 0x02);
1337 SetPciConfig1(reg
, val
);
1339 } // end hpt_cable80()
1345 IN PHW_DEVICE_EXTENSION deviceExtension
,
1346 IN ULONG channel
// physical channel number (0-1)
1349 PVOID HwDeviceExtension
= (PVOID
)deviceExtension
;
1350 ULONG slotNumber
= deviceExtension
->slotNumber
;
1351 ULONG SystemIoBusNumber
= deviceExtension
->SystemIoBusNumber
;
1353 ULONG ChipType
= deviceExtension
->HwFlags
& CHIPTYPE_MASK
;
1360 GetPciConfig1(0x50, reg50
);
1377 for (j
=0; j
>=2; i
-= 8) {
1378 i
= (3-(channel
*2+j
))*8;
1379 if (((reg50
>> (i
& 0x10)) & 8) &&
1380 ((reg50
>> i
) & 0x20) &&
1381 (((reg50
>> i
) & 7) < a
)) {
1383 res
|= TRUE
; //(1 << (1 - (i >> 4)));
1388 } // end via_cable80()
1393 IN PHW_DEVICE_EXTENSION deviceExtension
,
1394 IN ULONG channel
, // physical channel number (0-1)
1399 PVOID HwDeviceExtension
= (PVOID
)deviceExtension
;
1400 ULONG slotNumber
= deviceExtension
->slotNumber
;
1401 ULONG SystemIoBusNumber
= deviceExtension
->SystemIoBusNumber
;
1403 //ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK;
1405 ULONG c
; // logical channel (for Compatible Mode controllers)
1408 c
= channel
- deviceExtension
->Channel
; // logical channel (for Compatible Mode controllers)
1409 chan
= &deviceExtension
->chan
[c
];
1411 GetPciConfig1(pci_reg
, tmp8
);
1412 if(!(tmp8
& (1 << (channel
<< bit_offs
)))) {
1413 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
1418 } // end generic_cable80()
1422 UniAtaReadLunConfig(
1423 IN PHW_DEVICE_EXTENSION deviceExtension
,
1424 IN ULONG channel
, // physical channel
1425 IN ULONG DeviceNumber
1430 PHW_LU_EXTENSION LunExt
;
1433 c
= channel
- deviceExtension
->Channel
; // logical channel
1435 chan
= &deviceExtension
->chan
[c
];
1436 DeviceNumber
= (DeviceNumber
% deviceExtension
->NumberLuns
);
1437 LunExt
= chan
->lun
[DeviceNumber
];
1439 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"ReadCacheEnable", 1);
1440 LunExt
->opt_ReadCacheEnable
= tmp32
? TRUE
: FALSE
;
1442 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"WriteCacheEnable", 1);
1443 LunExt
->opt_WriteCacheEnable
= tmp32
? TRUE
: FALSE
;
1445 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"MaxTransferMode", chan
->MaxTransferMode
);
1446 LunExt
->opt_MaxTransferMode
= tmp32
;
1448 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"PreferedTransferMode", 0xffffffff);
1449 LunExt
->opt_PreferedTransferMode
= tmp32
;
1451 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"ReadOnly", 0);
1453 LunExt
->opt_ReadOnly
= (UCHAR
)tmp32
;
1456 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"GeomType", 0xffffffff);
1460 LunExt
->opt_GeomType
= tmp32
;
1462 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DeviceNumber
, L
"Hidden", 0);
1464 LunExt
->DeviceFlags
|= DFLAGS_HIDDEN
;
1468 } // end UniAtaReadLunConfig()
1472 AtapiReadChipConfig(
1473 IN PVOID HwDeviceExtension
,
1474 IN ULONG DeviceNumber
,
1475 IN ULONG channel
// physical channel
1478 PHW_DEVICE_EXTENSION deviceExtension
= (PHW_DEVICE_EXTENSION
)HwDeviceExtension
;
1481 ULONG c
; // logical channel (for Compatible Mode controllers)
1484 KdPrint2((PRINT_PREFIX
"AtapiReadChipConfig: devExt %#x\n", deviceExtension
));
1485 ASSERT(deviceExtension
);
1487 if(channel
!= CHAN_NOT_SPECIFIED
) {
1488 c
= channel
- deviceExtension
->Channel
; // logical channel (for Compatible Mode controllers)
1490 c
= CHAN_NOT_SPECIFIED
;
1493 KdPrint2((PRINT_PREFIX
"AtapiReadChipConfig: dev %#x, ph chan %d\n", DeviceNumber
, channel
));
1495 if(channel
== CHAN_NOT_SPECIFIED
) {
1496 if(AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"ForceSimplex", FALSE
)) {
1497 deviceExtension
->simplexOnly
= TRUE
;
1499 deviceExtension
->opt_AtapiDmaZeroTransfer
= FALSE
;
1500 deviceExtension
->opt_AtapiDmaControlCmd
= FALSE
;
1501 deviceExtension
->opt_AtapiDmaRawRead
= g_opt_AtapiDmaRawRead
;
1502 deviceExtension
->opt_AtapiDmaReadWrite
= TRUE
;
1505 if(c
== CHAN_NOT_SPECIFIED
) {
1506 KdPrint2((PRINT_PREFIX
"MaxTransferMode (base): %#x\n", deviceExtension
->MaxTransferMode
));
1507 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
1508 chan
= &deviceExtension
->chan
[c
];
1509 chan
->MaxTransferMode
= deviceExtension
->MaxTransferMode
;
1510 tmp32
= AtapiRegCheckDevValue(deviceExtension
, channel
, DEVNUM_NOT_SPECIFIED
, L
"MaxTransferMode", chan
->MaxTransferMode
);
1511 if(tmp32
!= 0xffffffff) {
1512 KdPrint2((PRINT_PREFIX
"MaxTransferMode (overriden): %#x\n", chan
->MaxTransferMode
));
1513 chan
->MaxTransferMode
= tmp32
;
1515 //UniAtaReadLunConfig(deviceExtension, c, 0);
1516 //UniAtaReadLunConfig(deviceExtension, c, 1);
1519 deviceExtension
->opt_AtapiDmaZeroTransfer
=
1520 AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"AtapiDmaZeroTransfer", deviceExtension
->opt_AtapiDmaZeroTransfer
) ?
1523 deviceExtension
->opt_AtapiDmaControlCmd
=
1524 AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"AtapiDmaControlCmd", deviceExtension
->opt_AtapiDmaControlCmd
) ?
1527 deviceExtension
->opt_AtapiDmaRawRead
=
1528 AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"AtapiDmaRawRead", deviceExtension
->opt_AtapiDmaRawRead
) ?
1531 deviceExtension
->opt_AtapiDmaReadWrite
=
1532 AtapiRegCheckDevValue(deviceExtension
, CHAN_NOT_SPECIFIED
, DEVNUM_NOT_SPECIFIED
, L
"AtapiDmaReadWrite", deviceExtension
->opt_AtapiDmaReadWrite
) ?
1536 chan
= &deviceExtension
->chan
[c
];
1537 chan
->MaxTransferMode
= deviceExtension
->MaxTransferMode
;
1538 tmp32
= AtapiRegCheckDevValue(deviceExtension
, c
, DEVNUM_NOT_SPECIFIED
, L
"MaxTransferMode", chan
->MaxTransferMode
);
1539 if(tmp32
!= 0xffffffff) {
1540 KdPrint2((PRINT_PREFIX
"MaxTransferMode (overriden): %#x\n", chan
->MaxTransferMode
));
1541 chan
->MaxTransferMode
= tmp32
;
1543 tmp32
= AtapiRegCheckDevValue(deviceExtension
, c
, DEVNUM_NOT_SPECIFIED
, L
"ReorderEnable", TRUE
);
1544 chan
->UseReorder
= tmp32
? TRUE
: FALSE
;
1546 for(i
=0; i
<deviceExtension
->NumberLuns
; i
++) {
1547 UniAtaReadLunConfig(deviceExtension
, channel
, i
);
1552 } // end AtapiReadChipConfig()
1557 IN PVOID HwDeviceExtension
,
1558 IN ULONG DeviceNumber
,
1559 IN ULONG channel
// physical channel
1562 PHW_DEVICE_EXTENSION deviceExtension
= (PHW_DEVICE_EXTENSION
)HwDeviceExtension
;
1563 ULONG slotNumber
= deviceExtension
->slotNumber
;
1564 ULONG SystemIoBusNumber
= deviceExtension
->SystemIoBusNumber
;
1565 ULONG VendorID
= deviceExtension
->DevID
& 0xffff;
1567 ULONG DeviceID
= (deviceExtension
->DevID
>> 16) & 0xffff;
1569 ULONG RevID
= deviceExtension
->RevID
;
1571 // BUSMASTER_CONTROLLER_INFORMATION* DevTypeInfo;
1572 ULONG ChipType
= deviceExtension
->HwFlags
& CHIPTYPE_MASK
;
1573 ULONG ChipFlags
= deviceExtension
->HwFlags
& CHIPFLAG_MASK
;
1578 ULONG c
; // logical channel (for Compatible Mode controllers)
1579 BOOLEAN CheckCable
= FALSE
;
1580 //ULONG BaseIoAddress;
1583 case CHAN_NOT_SPECIFIED_CHECK_CABLE
:
1586 case CHAN_NOT_SPECIFIED
:
1587 c
= CHAN_NOT_SPECIFIED
;
1590 c
= channel
- deviceExtension
->Channel
; // logical channel (for Compatible Mode controllers)
1593 KdPrint2((PRINT_PREFIX
"AtapiChipInit: dev %#x, ph chan %d\n", DeviceNumber
, channel
));
1595 KdPrint2((PRINT_PREFIX
"HwFlags: %#x\n", deviceExtension
->HwFlags
));
1596 KdPrint2((PRINT_PREFIX
"VendorID/DeviceID/Rev %#x/%#x/%#x\n", VendorID
, DeviceID
, RevID
));
1598 if(deviceExtension
->UnknownDev
) {
1599 KdPrint2((PRINT_PREFIX
" Unknown chip\n" ));
1601 VendorID
= 0xffffffff;
1605 if(ChipFlags
& UNIATA_AHCI
) {
1606 /* if BAR(5) is IO it should point to SATA interface registers */
1607 if(!deviceExtension
->BaseIoAHCI_0
.Addr
) {
1608 KdPrint2((PRINT_PREFIX
" !BaseIoAHCI_0, exiting\n" ));
1611 if(c
== CHAN_NOT_SPECIFIED
) {
1612 return UniataAhciInit(HwDeviceExtension
);
1614 if(c
<deviceExtension
->NumberChannels
) {
1615 KdPrint2((PRINT_PREFIX
" AHCI single channel init\n" ));
1616 UniataAhciReset(HwDeviceExtension
, c
);
1619 KdPrint2((PRINT_PREFIX
" AHCI non-existent channel\n" ));
1625 // case ATA_ACARD_ID:
1627 case ATA_ACER_LABS_ID
:
1628 if(ChipFlags
& UNIATA_SATA
) {
1629 if(c
== CHAN_NOT_SPECIFIED
) {
1630 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
1631 chan
= &deviceExtension
->chan
[c
];
1632 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1633 /* the southbridge might need the data corruption fix */
1634 if(RevID
== 0xc2 || RevID
== 0xc3) {
1635 AtapiAliSouthBridgeFixup(HwDeviceExtension
, PCIConfiguration
,
1636 SystemIoBusNumber
, slotNumber
, c
);
1639 /* enable PCI interrupt */
1640 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG
, Command
), (a
& ~0x0400));
1643 if(ChipFlags
& ALINEW
) {
1644 if(c
== CHAN_NOT_SPECIFIED
) {
1645 /* use device interrupt as byte count end */
1646 ChangePciConfig1(0x4a, (a
| 0x20));
1647 /* enable cable detection and UDMA support on newer chips, rev < 0xc7 */
1649 ChangePciConfig1(0x4b, (a
| 0x09));
1652 /* enable ATAPI UDMA mode */
1653 ChangePciConfig1(0x53, (a
| (RevID
>= 0xc7 ? 0x03 : 0x01)));
1656 // check 80-pin cable
1657 generic_cable80(deviceExtension
, channel
, 0x4a, 0);
1660 if(c
== CHAN_NOT_SPECIFIED
) {
1661 /* deactivate the ATAPI FIFO and enable ATAPI UDMA */
1662 ChangePciConfig1(0x53, (a
| 0x03));
1665 deviceExtension
->chan
[c
].ChannelCtrlFlags
|= CTRFLAGS_DMA_RO
;
1670 if(c
== CHAN_NOT_SPECIFIED
) {
1671 /* set prefetch, postwrite */
1672 if(ChipFlags
& AMDBUG
) {
1673 ChangePciConfig1(0x41, (a
& 0x0f));
1675 ChangePciConfig1(0x41, (a
| 0xf0));
1678 if(deviceExtension
->MaxTransferMode
< ATA_UDMA2
)
1680 // check 80-pin cable
1681 if(!(ChipFlags
& UNIATA_NO80CHK
)) {
1682 if(c
== CHAN_NOT_SPECIFIED
) {
1685 generic_cable80(deviceExtension
, channel
, 0x42, 0);
1689 case ATA_HIGHPOINT_ID
:
1691 if(c
== CHAN_NOT_SPECIFIED
) {
1693 if(ChipFlags
& HPTOLD
) {
1694 /* turn off interrupt prediction */
1695 ChangePciConfig1(0x51, (a
& ~0x80));
1697 /* turn off interrupt prediction */
1698 ChangePciConfig1(0x51, (a
& ~0x03));
1699 ChangePciConfig1(0x55, (a
& ~0x03));
1700 /* turn on interrupts */
1701 ChangePciConfig1(0x5a, (a
& ~0x10));
1702 /* set clocks etc */
1703 if(ChipType
< HPT372
) {
1704 SetPciConfig1(0x5b, 0x22);
1706 ChangePciConfig1(0x5b, ((a
& 0x01) | 0x20));
1711 // check 80-pin cable
1712 chan
= &deviceExtension
->chan
[c
];
1713 if(!hpt_cable80(deviceExtension
, channel
)) {
1714 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
1718 case ATA_INTEL_ID
: {
1722 if(ChipFlags
& UNIATA_SATA
) {
1724 KdPrint2((PRINT_PREFIX
"Intel SATA\n"));
1725 if(ChipFlags
& UNIATA_AHCI
) {
1726 KdPrint2((PRINT_PREFIX
"Do nothing for AHCI\n"));
1729 if(c
== CHAN_NOT_SPECIFIED
) {
1730 KdPrint2((PRINT_PREFIX
"Base init\n"));
1731 /* force all ports active "the legacy way" */
1732 ChangePciConfig2(0x92, (a
| 0x0f));
1733 /* enable PCI interrupt */
1734 ChangePciConfig2(/*PCIR_COMMAND*/0x04, (a
& ~0x0400));
1738 KdPrint2((PRINT_PREFIX
"channel init\n"));
1740 GetPciConfig1(0x90, tmp8
);
1741 KdPrint2((PRINT_PREFIX
"reg 90: %x, init lun map\n", tmp8
));
1743 KdPrint2((PRINT_PREFIX
"chan %d\n", c
));
1744 chan
= &deviceExtension
->chan
[c
];
1746 if(ChipFlags
& ICH5
) {
1747 KdPrint2((PRINT_PREFIX
"ICH5\n"));
1748 if ((tmp8
& 0x04) == 0) {
1749 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1750 chan
->lun
[0]->SATA_lun_map
= (tmp8
& 0x01) ^ c
;
1751 chan
->lun
[1]->SATA_lun_map
= 0;
1752 } else if ((tmp8
& 0x02) == 0) {
1754 chan
->lun
[0]->SATA_lun_map
= (tmp8
& 0x01) ? 1 : 0;
1755 chan
->lun
[1]->SATA_lun_map
= (tmp8
& 0x01) ? 0 : 1;
1758 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA;
1760 } else if ((tmp8
& 0x02) != 0) {
1762 chan
->lun
[0]->SATA_lun_map
= (tmp8
& 0x01) ? 1 : 0;
1763 chan
->lun
[1]->SATA_lun_map
= (tmp8
& 0x01) ? 0 : 1;
1766 //chan->ChannelCtrlFlags |= CTRFLAGS_PATA;
1770 if(ChipFlags
& I6CH2
) {
1771 KdPrint2((PRINT_PREFIX
"I6CH2\n"));
1772 chan
->ChannelCtrlFlags
|= CTRFLAGS_NO_SLAVE
;
1773 chan
->lun
[0]->SATA_lun_map
= c
? 4 : 5;
1774 chan
->lun
[1]->SATA_lun_map
= 0;
1776 KdPrint2((PRINT_PREFIX
"other Intel\n"));
1777 switch(tmp8
& 0x03) {
1779 chan
->lun
[0]->SATA_lun_map
= 0+c
;
1780 chan
->lun
[1]->SATA_lun_map
= 2+c
;
1784 chan
->lun
[0]->SATA_lun_map
= 0;
1785 chan
->lun
[1]->SATA_lun_map
= 2;
1793 chan
->lun
[0]->SATA_lun_map
= 1;
1794 chan
->lun
[1]->SATA_lun_map
= 3;
1804 KdPrint2((PRINT_PREFIX
"PATA part\n"));
1805 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA5
);
1808 if(ChipType
== INTEL_IDX
) {
1809 KdPrint2((PRINT_PREFIX
"io indexed\n"));
1810 //for(c=0; c<deviceExtension->NumberChannels; c++) {
1811 chan
= &deviceExtension
->chan
[c
];
1812 UniataSataWritePort4(chan
, IDX_SATA_SError
, 0xffffffff, 0);
1813 if(!(chan
->ChannelCtrlFlags
& CTRFLAGS_NO_SLAVE
)) {
1814 UniataSataWritePort4(chan
, IDX_SATA_SError
, 0xffffffff, 1);
1822 if(deviceExtension
->MaxTransferMode
< ATA_UDMA2
)
1824 // check 80-pin cable
1825 if(c
== CHAN_NOT_SPECIFIED
) {
1828 chan
= &deviceExtension
->chan
[c
];
1829 GetPciConfig2(0x54, reg54
);
1830 if( ((reg54
>> (channel
*2)) & 30) != 30) {
1831 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
1835 case ATA_NVIDIA_ID
: {
1836 if(ChipFlags
& UNIATA_SATA
) {
1837 if(c
== CHAN_NOT_SPECIFIED
) {
1838 ULONG offs
= (ChipFlags
& NV4OFF
) ? 0x0440 : 0x0010;
1839 /* enable control access */
1840 ChangePciConfig1(0x50, (a
| 0x04));
1841 /* MCP55 seems to need some time to allow r_res2 read. */
1842 AtapiStallExecution(10);
1843 KdPrint2((PRINT_PREFIX
"BaseIoAddressSATA_0=%x\n", deviceExtension
->BaseIoAddressSATA_0
.Addr
));
1844 if(ChipFlags
& NVQ
) {
1845 /* clear interrupt status */
1846 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),offs
, 0x00ff00ff);
1847 /* enable device and PHY state change interrupts */
1848 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),offs
+4, 0x000d000d);
1849 /* disable NCQ support */
1850 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x0400,
1851 AtapiReadPortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x0400) & 0xfffffff9);
1853 /* clear interrupt status */
1854 AtapiWritePortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),offs
, 0xff);
1855 /* enable device and PHY state change interrupts */
1856 AtapiWritePortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),offs
+1, 0xdd);
1858 /* enable PCI interrupt */
1859 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG
, Command
), (a
& ~0x0400));
1861 //UniataSataPhyEnable(HwDeviceExtension, c);
1866 if(c
== CHAN_NOT_SPECIFIED
) {
1867 /* set prefetch, postwrite */
1868 ChangePciConfig1(0x51, (a
& 0x0f));
1870 // check 80-pin cable
1871 generic_cable80(deviceExtension
, channel
, 0x52, 1);
1872 /* chan = &deviceExtension->chan[c];
1873 GetPciConfig1(0x52, reg52);
1874 if( !((reg52 >> (channel*2)) & 0x01)) {
1875 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1880 case ATA_PROMISE_ID
: {
1885 if(c
== CHAN_NOT_SPECIFIED
) {
1886 // ATA_OUTB(ctlr->r_res1, 0x11, ATA_INB(ctlr->r_res1, 0x11) | 0x0a);
1887 AtapiWritePortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressBM_0
),0x11,
1888 AtapiReadPortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressBM_0
),0x11) | 0x0a );
1892 /* enable burst mode */
1893 // ATA_OUTB(ctlr->r_res1, 0x1f, ATA_INB(ctlr->r_res1, 0x1f) | 0x01);
1894 if(c
== CHAN_NOT_SPECIFIED
) {
1895 AtapiWritePortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressBM_0
),0x1f,
1896 AtapiReadPortEx1(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressBM_0
),0x1f) | 0x01 );
1898 // check 80-pin cable
1899 chan
= &deviceExtension
->chan
[c
];
1900 GetPciConfig2(0x50, Reg50
);
1901 if(Reg50
& (1 << (channel
+10))) {
1902 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
1907 if(c
== CHAN_NOT_SPECIFIED
) {
1910 // check 80-pin cable
1911 chan
= &deviceExtension
->chan
[c
];
1912 AtapiWritePort1(chan
, IDX_BM_DeviceSpecific0
, 0x0b);
1913 if(AtapiReadPort1(chan
, IDX_BM_DeviceSpecific1
) & 0x04) {
1914 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
1919 if(c
== CHAN_NOT_SPECIFIED
) {
1920 if(ChipFlags
& PRSATA
) {
1921 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressBM_0
),0x6c, 0x000000ff);
1924 chan
= &deviceExtension
->chan
[c
];
1925 AtapiWritePort4(chan
, IDX_BM_Command
,
1926 (AtapiReadPort4(chan
, IDX_BM_Command
) & ~0x00000f8f) | channel
);
1927 AtapiWritePort4(chan
, IDX_BM_DeviceSpecific0
, 0x00000001);
1928 // check 80-pin cable
1929 if(chan
->MaxTransferMode
< ATA_SA150
&&
1930 (AtapiReadPort4(chan
, IDX_BM_Command
) & 0x01000000)) {
1931 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
1937 case ATA_SERVERWORKS_ID
:
1938 if(c
== CHAN_NOT_SPECIFIED
) {
1939 if(ChipType
== SWKS33
) {
1940 AtapiRosbSouthBridgeFixup(HwDeviceExtension
, PCIConfiguration
,
1941 SystemIoBusNumber
, slotNumber
);
1943 ChangePciConfig1(0x5a, ((a
& ~0x40) | ((ChipType
== SWKS100
) ? 0x03 : 0x02)));
1948 if(ChipType
== SIIMIO
) {
1949 KdPrint2((PRINT_PREFIX
"ATI New\n"));
1952 KdPrint2((PRINT_PREFIX
"ATI\n"));
1955 case ATA_SILICON_IMAGE_ID
:
1956 /* if(ChipFlags & SIIENINTR) {
1957 SetPciConfig1(0x71, 0x01);
1962 KdPrint2((PRINT_PREFIX
"SII\n"));
1965 if(c
== CHAN_NOT_SPECIFIED
) {
1966 if(ChipFlags
& SIISETCLK
) {
1967 KdPrint2((PRINT_PREFIX
"SIISETCLK\n"));
1968 GetPciConfig1(0x8a, tmp8
);
1969 if ((tmp8
& 0x30) != 0x10)
1970 ChangePciConfig1(0x8a, (a
& 0xcf) | 0x10);
1971 GetPciConfig1(0x8a, tmp8
);
1972 if ((tmp8
& 0x30) != 0x10) {
1973 KdPrint2((PRINT_PREFIX
"Sil 0680 could not set ATA133 clock\n"));
1974 deviceExtension
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA5
);
1978 if(deviceExtension
->MaxTransferMode
< ATA_SA150
) {
1979 // check 80-pin cable
1980 if(c
== CHAN_NOT_SPECIFIED
) {
1983 KdPrint2((PRINT_PREFIX
"Check UDMA66 cable\n"));
1984 chan
= &deviceExtension
->chan
[c
];
1985 GetPciConfig2(0x79, Reg79
);
1986 if(Reg79
& (channel
? 0x02 : 0x01)) {
1987 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
1991 ULONG unit01
= (c
& 1);
1992 ULONG unit10
= (c
& 2);
1993 /* enable/disable PHY state change interrupt */
1994 if(c
== CHAN_NOT_SPECIFIED
) {
1995 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
1998 if(ChipFlags
& SIINOSATAIRQ
) {
1999 KdPrint2((PRINT_PREFIX
"Disable broken SATA intr on c=%x\n", c
));
2000 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
), 0x148 + (unit01
<< 7) + (unit10
<< 8),0);
2004 if(ChipFlags
& SIINOSATAIRQ
) {
2005 KdPrint2((PRINT_PREFIX
"Disable broken SATA intr on c=%x\n", c
));
2006 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
), 0x148 + (unit01
<< 7) + (unit10
<< 8),0);
2008 KdPrint2((PRINT_PREFIX
"Enable SATA intr on c=%x\n", c
));
2009 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
), 0x148 + (unit01
<< 7) + (unit10
<< 8),(1 << 16));
2013 if(c
== CHAN_NOT_SPECIFIED
) {
2014 /* enable interrupt as BIOS might not */
2015 ChangePciConfig1(0x8a, (a
& 0x3f));
2016 // Enable 3rd and 4th channels
2017 if (ChipFlags
& SII4CH
) {
2018 KdPrint2((PRINT_PREFIX
"SII4CH\n"));
2019 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x0200, 0x00000002);
2022 chan
= &deviceExtension
->chan
[c
];
2023 /* dont block interrupts */
2024 //ChangePciConfig4(0x48, (a & ~0x03c00000));
2025 tmp32
= AtapiReadPortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x48);
2026 AtapiWritePortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x48, (1 << 22) << c
);
2028 tmp32
= AtapiReadPortEx4(NULL
, (ULONGIO_PTR
)(&deviceExtension
->BaseIoAddressSATA_0
),0x48);
2030 /* Initialize FIFO PCI bus arbitration */
2031 GetPciConfig1(offsetof(PCI_COMMON_CONFIG
, CacheLineSize
), tmp8
);
2033 KdPrint2((PRINT_PREFIX
"SII: CacheLine=%d\n", tmp32
));
2035 AtapiWritePort2(chan
, IDX_BM_DeviceSpecific1
, ((USHORT
)tmp8
) << 8 | tmp8
);
2037 KdPrint2((PRINT_PREFIX
"SII: CacheLine=0 !!!\n"));
2044 KdPrint2((PRINT_PREFIX
"SII_CMD\n"));
2045 if(c
== CHAN_NOT_SPECIFIED
) {
2046 /* Setup interrupts. */
2047 SetPciConfig1(0x71, 0x01);
2049 /* GetPciConfig1(0x8a, tmp8);
2051 SetPciConfig1(0x71, tmp8);*/
2053 /* Use MEMORY READ LINE for reads.
2054 * NOTE: Although not mentioned in the PCI0646U specs,
2055 * these bits are write only and won't be read
2056 * back as set or not. The PCI0646U2 specs clarify
2060 SetPciConfig1(0x71, tmp8);
2062 /* Set reasonable active/recovery/address-setup values. */
2063 SetPciConfig1(0x53, 0x40);
2064 SetPciConfig1(0x54, 0x3f);
2065 SetPciConfig1(0x55, 0x40);
2066 SetPciConfig1(0x56, 0x3f);
2067 SetPciConfig1(0x57, 0x1c);
2068 SetPciConfig1(0x58, 0x3f);
2069 SetPciConfig1(0x5b, 0x3f);
2076 if(c
== CHAN_NOT_SPECIFIED
) {
2082 ChangePciConfig1(0x52, (a
& ~0x04));
2086 ChangePciConfig1(0x49, (a
& ~0x01));
2089 ChangePciConfig2(0x50, (a
| 0x0008));
2090 ChangePciConfig2(0x52, (a
| 0x0008));
2093 ChangePciConfig2(0x04, (a
& ~0x0400));
2096 if(ChipType
== SIS133NEW
) {
2098 // check 80-pin cable
2099 if(c
== CHAN_NOT_SPECIFIED
) {
2102 chan
= &deviceExtension
->chan
[c
];
2103 GetPciConfig2(channel
? 0x52 : 0x50, tmp16
);
2104 if(tmp16
& 0x8000) {
2105 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
2109 // check 80-pin cable
2110 if(c
== CHAN_NOT_SPECIFIED
) {
2113 chan
= &deviceExtension
->chan
[c
];
2114 GetPciConfig1(48, tmp8
);
2115 if(tmp8
& (0x10 << channel
)) {
2116 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
2123 /* if(ChipFlags & (UNIATA_SATA | UNIATA_AHCI | VIASATA) {
2126 if(c
== CHAN_NOT_SPECIFIED
) {
2127 /* prepare for ATA-66 on the 82C686a and 82C596b */
2128 if(ChipFlags
& VIACLK
) {
2129 ChangePciConfig4(0x50, (a
| 0x030b030b));
2132 if(ChipFlags
& (UNIATA_SATA
| VIASATA
)) {
2133 /* enable PCI interrupt */
2134 ChangePciConfig2(/*PCIR_COMMAND*/0x04, (a
& ~0x0400));
2138 /* the southbridge might need the data corruption fix */
2139 if(ChipFlags
& VIABUG
) {
2140 AtapiViaSouthBridgeFixup(HwDeviceExtension
, PCIConfiguration
,
2141 SystemIoBusNumber
, slotNumber
);
2143 /* set prefetch, postwrite */
2144 if(ChipType
!= VIA133
) {
2145 ChangePciConfig1(0x41, (a
| 0xf0));
2148 /* set fifo configuration half'n'half */
2149 ChangePciConfig1(0x43, ((a
& ((ChipFlags
& VIAPRQ
) ? 0x80 : 0x90)) | 0x2a));
2151 /* set status register read retry */
2152 ChangePciConfig1(0x44, (a
| 0x08));
2154 /* set DMA read & end-of-sector fifo flush */
2155 ChangePciConfig1(0x46, ((a
& 0x0c) | 0xf0));
2157 /* set sector size */
2158 SetPciConfig2(0x60, DEV_BSIZE
);
2159 SetPciConfig2(0x68, DEV_BSIZE
);
2162 chan
= &deviceExtension
->chan
[c
];
2164 if(ChipFlags
& (UNIATA_SATA
| VIASATA
)) {
2165 if((ChipFlags
& VIABAR
) && (c
>= 2)) {
2168 UniataSataWritePort4(chan
, IDX_SATA_SError
, 0xffffffff, 0);
2172 // check 80-pin cable
2173 if(!via_cable80(deviceExtension
, channel
)) {
2174 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
2181 if(ChipType
== ITE_33
|| ChipType
== ITE_133_NEW
) {
2184 if(ChipType
== ITE_133
) {
2185 if(c
== CHAN_NOT_SPECIFIED
) {
2186 /* set PCI mode and 66Mhz reference clock */
2187 ChangePciConfig1(0x50, a
& ~0x83);
2189 /* set default active & recover timings */
2190 SetPciConfig1(0x54, 0x31);
2191 SetPciConfig1(0x56, 0x31);
2193 // check 80-pin cable
2194 GetPciConfig2(0x40, tmp16
);
2195 chan
= &deviceExtension
->chan
[c
];
2196 if(!(tmp16
& (channel
? 0x08 : 0x04))) {
2197 chan
->MaxTransferMode
= min(deviceExtension
->MaxTransferMode
, ATA_UDMA2
);
2201 if(ChipType
== ITE_133_NEW
) {
2205 if(c
!= CHAN_NOT_SPECIFIED
) {
2206 // We don't know how to check for 80-pin cable on unknown controllers.
2207 // Later we shall check bit in IDENTIFY structure, but it is not reliable way.
2208 // So, leave this flag to use as hint in error recovery procedures
2209 KdPrint2((PRINT_PREFIX
"UNIATA_NO80CHK\n"));
2210 deviceExtension
->HwFlags
|= UNIATA_NO80CHK
;
2215 // In all places separate channels are inited after common controller init
2216 // The only exception is probe. But there we may need info about 40/80 pin and MaxTransferRate
2217 if(CheckCable
&& !(ChipFlags
& (UNIATA_NO80CHK
| UNIATA_SATA
))) {
2218 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
2219 AtapiChipInit(HwDeviceExtension
, DeviceNumber
, c
);
2224 } // end AtapiChipInit()
2229 IN PHW_DEVICE_EXTENSION deviceExtension
,
2230 IN PIDE_BUSMASTER_REGISTERS BaseIoAddressBM_0
,
2238 if(!BaseIoAddressBM_0
) {
2241 for(c
=0; c
<deviceExtension
->NumberChannels
; c
++) {
2242 chan
= &deviceExtension
->chan
[c
];
2243 for (i
=0; i
<IDX_BM_IO_SZ
; i
++) {
2244 chan
->RegTranslation
[IDX_BM_IO
+i
].Addr
= BaseIoAddressBM_0
? ((ULONGIO_PTR
)BaseIoAddressBM_0
+ i
) : 0;
2245 chan
->RegTranslation
[IDX_BM_IO
+i
].MemIo
= MemIo
;
2247 if(BaseIoAddressBM_0
) {
2248 BaseIoAddressBM_0
++;
2251 } // end UniataInitMapBM()
2256 IN PHW_CHANNEL chan
,
2257 IN PIDE_REGISTERS_1 BaseIoAddress1
,
2258 IN PIDE_REGISTERS_2 BaseIoAddress2
2263 for (i
=0; i
<IDX_IO1_SZ
; i
++) {
2264 chan
->RegTranslation
[IDX_IO1
+i
].Addr
= BaseIoAddress1
? ((ULONGIO_PTR
)BaseIoAddress1
+ i
) : 0;
2265 chan
->RegTranslation
[IDX_IO1
+i
].MemIo
= FALSE
;
2267 for (i
=0; i
<IDX_IO2_SZ
; i
++) {
2268 chan
->RegTranslation
[IDX_IO2
+i
].Addr
= BaseIoAddress2
? ((ULONGIO_PTR
)BaseIoAddress2
+ i
) : 0;
2269 chan
->RegTranslation
[IDX_IO2
+i
].MemIo
= FALSE
;
2271 UniataInitSyncBaseIO(chan
);
2272 } // end UniataInitMapBase()
2276 UniataInitSyncBaseIO(
2280 RtlCopyMemory(&chan
->RegTranslation
[IDX_IO1_o
], &chan
->RegTranslation
[IDX_IO1
], IDX_IO1_SZ
*sizeof(chan
->RegTranslation
[0]));
2281 RtlCopyMemory(&chan
->RegTranslation
[IDX_IO2_o
], &chan
->RegTranslation
[IDX_IO2
], IDX_IO2_SZ
*sizeof(chan
->RegTranslation
[0]));
2282 } // end UniataInitSyncBaseIO()
2287 IN PHW_CHANNEL chan
,
2288 IN PHW_DEVICE_EXTENSION deviceExtension
,
2294 if(!deviceExtension
->NumberLuns
) {
2295 deviceExtension
->NumberLuns
= IDE_MAX_LUN_PER_CHAN
;
2297 chan
->DeviceExtension
= deviceExtension
;
2299 chan
->NumberLuns
= deviceExtension
->NumberLuns
;
2300 for(i
=0; i
<deviceExtension
->NumberLuns
; i
++) {
2301 chan
->lun
[i
] = &(deviceExtension
->lun
[c
*deviceExtension
->NumberLuns
+i
]);
2303 chan
->AltRegMap
= deviceExtension
->AltRegMap
;
2304 chan
->NextDpcChan
= -1;
2305 for(i
=0; i
<deviceExtension
->NumberLuns
; i
++) {
2306 chan
->lun
[i
]->DeviceExtension
= deviceExtension
;
2307 chan
->lun
[i
]->chan
= chan
;
2308 chan
->lun
[i
]->Lun
= i
;
2310 } // end AtapiSetupLunPtrs()