602abcdb4634169f6e01a6f735541ec02a329ca8
[reactos.git] / reactos / drivers / storage / ide / uniata / id_init.cpp
1 /*++
2
3 Copyright (c) 2004-2008 Alexandr A. Telyatnikov (Alter)
4
5 Module Name:
6 id_init.cpp
7
8 Abstract:
9 This is the chip-specific init module for ATA/ATAPI IDE controllers
10 with Busmaster DMA and Serial ATA support
11
12 Author:
13 Alexander A. Telyatnikov (Alter)
14
15 Environment:
16 kernel mode only
17
18 Notes:
19
20 THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
21 IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
22 OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
23 IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
24 INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
25 NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
29 THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30
31 Revision History:
32
33 Some parts of code were taken from FreeBSD 5.1-6.1 ATA driver by
34 Søren Schmidt, Copyright (c) 1998-2007
35 added IT8172 IDE controller support from Linux
36 added VIA 8233/8235 fix from Linux
37 added 80-pin cable detection from Linux for
38 VIA, nVidia
39 added support for non-standard layout of registers
40 added SATA support
41
42 --*/
43
44 #include "stdafx.h"
45
46 BOOLEAN
47 NTAPI
48 UniataChipDetectChannels(
49 IN PVOID HwDeviceExtension,
50 IN PPCI_COMMON_CONFIG pciData, // optional
51 IN ULONG DeviceNumber,
52 IN PPORT_CONFIGURATION_INFORMATION ConfigInfo
53 )
54 {
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;
63
64 KdPrint2((PRINT_PREFIX "UniataChipDetectChannels:\n" ));
65 switch(VendorID) {
66 case ATA_ACER_LABS_ID:
67 switch(deviceExtension->DevID) {
68 case 0x528710b9:
69 case 0x528810b9:
70 deviceExtension->NumberChannels = 4;
71 KdPrint2((PRINT_PREFIX "Acer 4 chan\n"));
72 }
73 break;
74 case ATA_PROMISE_ID:
75
76 if(ChipType != PRMIO) {
77 break;
78 }
79 deviceExtension->NumberChannels = 4;
80 KdPrint2((PRINT_PREFIX "Promise 4 chan\n"));
81 break;
82 case ATA_MARVELL_ID:
83 KdPrint2((PRINT_PREFIX "Marvell\n"));
84 switch(deviceExtension->DevID) {
85 case 0x610111ab:
86 /* 88SX6101 only have 1 PATA channel */
87 if(BMList[deviceExtension->DevIndex].channel) {
88 KdPrint2((PRINT_PREFIX "88SX6101 has no 2nd PATA chan\n"));
89 return FALSE;
90 }
91 deviceExtension->NumberChannels = 1;
92 KdPrint2((PRINT_PREFIX "88SX6101 PATA 1 chan\n"));
93 break;
94 }
95 break;
96 case ATA_ATI_ID:
97 KdPrint2((PRINT_PREFIX "ATI\n"));
98 switch(deviceExtension->DevID) {
99 case 0x438c1002:
100 case 0x439c1002:
101 /* IXP600 & IXP700 only have 1 PATA channel */
102 if(BMList[deviceExtension->DevIndex].channel) {
103 KdPrint2((PRINT_PREFIX "New ATI no 2nd PATA chan\n"));
104 return FALSE;
105 }
106 deviceExtension->NumberChannels = 1;
107 KdPrint2((PRINT_PREFIX "New ATI PATA 1 chan\n"));
108 break;
109 }
110 case ATA_SILICON_IMAGE_ID:
111
112 if(ChipFlags & SIIBUG) {
113 }
114 if(ChipType != SIIMIO) {
115 break;
116 }
117 if(!pciData) {
118 break;
119 }
120
121 if(VendorID == ATA_SILICON_IMAGE_ID) {
122 KdPrint2((PRINT_PREFIX "New SII\n"));
123 } else {
124 KdPrint2((PRINT_PREFIX "ATI SATA\n"));
125 }
126 if(deviceExtension->HwFlags & SII4CH) {
127 deviceExtension->NumberChannels = 4;
128 KdPrint2((PRINT_PREFIX "4 chan\n"));
129 }
130 break;
131 case ATA_VIA_ID:
132 if((deviceExtension->DevID == 0x32491106) &&
133 ScsiPortConvertPhysicalAddressToUlong((*ConfigInfo->AccessRanges)[5].RangeStart)) {
134 deviceExtension->NumberChannels = 3;
135 KdPrint2((PRINT_PREFIX "VIA 3 chan\n"));
136 }
137 break;
138 } // end switch(VendorID)
139 return TRUE;
140
141 } // end UniataChipDetectChannels()
142
143 BOOLEAN
144 NTAPI
145 UniataChipDetect(
146 IN PVOID HwDeviceExtension,
147 IN PPCI_COMMON_CONFIG pciData, // optional
148 IN ULONG DeviceNumber,
149 IN OUT PPORT_CONFIGURATION_INFORMATION ConfigInfo,
150 IN BOOLEAN* simplexOnly
151 )
152 {
153 PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension;
154 ULONG slotNumber = deviceExtension->slotNumber;
155 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber;
156 ULONG VendorID = deviceExtension->DevID & 0xffff;
157 ULONG DeviceID = (deviceExtension->DevID >> 16) & 0xffff;
158 ULONG RevID = deviceExtension->RevID;
159 ULONG i, c;
160 BUSMASTER_CONTROLLER_INFORMATION* DevTypeInfo;
161 PHW_CHANNEL chan;
162 ULONG ChipType;
163 ULONG ChipFlags;
164 ULONG tmp32;
165 UCHAR tmp8;
166 ULONG BaseMemAddress;
167 ULONG BaseIoAddress1;
168 ULONG BaseIoAddress2;
169 ULONG BaseIoAddressBM;
170 BOOLEAN MemIo = FALSE;
171
172 KdPrint2((PRINT_PREFIX "UniataChipDetect:\n" ));
173 KdPrint2((PRINT_PREFIX "HwFlags: %#x\n", deviceExtension->HwFlags));
174
175 i = Ata_is_dev_listed((PBUSMASTER_CONTROLLER_INFORMATION)&BusMasterAdapters[0], VendorID, 0xffff, 0, NUM_BUSMASTER_ADAPTERS);
176
177 c = AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"ForceSimplex", 0);
178 if(c) {
179 *simplexOnly = TRUE;
180 }
181
182 // defaults
183 BaseIoAddressBM = pciData->u.type0.BaseAddresses[4] & ~0x07;
184 deviceExtension->MaxTransferMode = BaseIoAddressBM ? ATA_DMA : ATA_PIO4;
185 ConfigInfo->MaximumTransferLength = DEV_BSIZE*256;
186 deviceExtension->MaximumDmaTransferLength = ConfigInfo->MaximumTransferLength;
187
188 KdPrint2((PRINT_PREFIX "i: %#x\n", i));
189 if(i != BMLIST_TERMINATOR) {
190 DevTypeInfo = (PBUSMASTER_CONTROLLER_INFORMATION)&BusMasterAdapters[i];
191 } else {
192 KdPrint2((PRINT_PREFIX " unknown dev, BM addr %#x", BaseIoAddressBM));
193 DevTypeInfo = NULL;
194 KdPrint2((PRINT_PREFIX " MaxTransferMode %#x\n", deviceExtension->MaxTransferMode));
195
196 if(!UniataChipDetectChannels(HwDeviceExtension, pciData, DeviceNumber, ConfigInfo)) {
197 return FALSE;
198 }
199 if(!UniataAllocateLunExt(deviceExtension, UNIATA_ALLOCATE_NEW_LUNS)) {
200 return FALSE;
201 }
202
203 return FALSE;
204 }
205
206 static BUSMASTER_CONTROLLER_INFORMATION const SiSAdapters[] = {
207 PCI_DEV_HW_SPEC_BM( 0182, 1039, 0x00, ATA_SA150, "SiS 182" , SISSATA | UNIATA_SATA),
208 PCI_DEV_HW_SPEC_BM( 0181, 1039, 0x00, ATA_SA150, "SiS 181" , SISSATA | UNIATA_SATA),
209 PCI_DEV_HW_SPEC_BM( 0180, 1039, 0x00, ATA_SA150, "SiS 180" , SISSATA | UNIATA_SATA),
210 PCI_DEV_HW_SPEC_BM( 0965, 1039, 0x00, ATA_UDMA6, "SiS 965" , SIS133NEW ),
211 PCI_DEV_HW_SPEC_BM( 0964, 1039, 0x00, ATA_UDMA6, "SiS 964" , SIS133NEW ),
212 PCI_DEV_HW_SPEC_BM( 0963, 1039, 0x00, ATA_UDMA6, "SiS 963" , SIS133NEW ),
213 PCI_DEV_HW_SPEC_BM( 0962, 1039, 0x00, ATA_UDMA6, "SiS 962" , SIS133NEW ),
214
215 PCI_DEV_HW_SPEC_BM( 0745, 1039, 0x00, ATA_UDMA5, "SiS 745" , SIS100NEW ),
216 PCI_DEV_HW_SPEC_BM( 0735, 1039, 0x00, ATA_UDMA5, "SiS 735" , SIS100NEW ),
217 PCI_DEV_HW_SPEC_BM( 0733, 1039, 0x00, ATA_UDMA5, "SiS 733" , SIS100NEW ),
218 PCI_DEV_HW_SPEC_BM( 0730, 1039, 0x00, ATA_UDMA5, "SiS 730" , SIS100OLD ),
219
220 PCI_DEV_HW_SPEC_BM( 0646, 1039, 0x00, ATA_UDMA6, "SiS 645DX", SIS133NEW ),
221 /* PCI_DEV_HW_SPEC_BM( 0645, 1039, 0x00, ATA_UDMA6, "SiS 645" , SIS133NEW ),*/
222 /* PCI_DEV_HW_SPEC_BM( 0640, 1039, 0x00, ATA_UDMA4, "SiS 640" , SIS_SOUTH ),*/
223 PCI_DEV_HW_SPEC_BM( 0635, 1039, 0x00, ATA_UDMA5, "SiS 635" , SIS100NEW ),
224 PCI_DEV_HW_SPEC_BM( 0633, 1039, 0x00, ATA_UDMA5, "SiS 633" , SIS100NEW ),
225 PCI_DEV_HW_SPEC_BM( 0630, 1039, 0x00, ATA_UDMA5, "SiS 630S" , SIS100OLD ),
226 PCI_DEV_HW_SPEC_BM( 0630, 1039, 0x00, ATA_UDMA4, "SiS 630" , SIS66 ),
227 PCI_DEV_HW_SPEC_BM( 0620, 1039, 0x00, ATA_UDMA4, "SiS 620" , SIS66 ),
228
229 PCI_DEV_HW_SPEC_BM( 0550, 1039, 0x00, ATA_UDMA5, "SiS 550" , SIS66 ),
230 PCI_DEV_HW_SPEC_BM( 0540, 1039, 0x00, ATA_UDMA4, "SiS 540" , SIS66 ),
231 PCI_DEV_HW_SPEC_BM( 0530, 1039, 0x00, ATA_UDMA4, "SiS 530" , SIS66 ),
232
233 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x04, ATA_UDMA6, "SiS 962L" , SIS133OLD ), // ???
234 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x00, ATA_UDMA6, "SiS 961" , SIS133OLD ),
235
236 PCI_DEV_HW_SPEC_BM( 5517, 1039, 0x00, ATA_UDMA5, "SiS 961" , SIS100NEW | SIS_BASE ),
237 PCI_DEV_HW_SPEC_BM( 5518, 1039, 0x00, ATA_UDMA6, "SiS 962/3", SIS133NEW | SIS_BASE ),
238 PCI_DEV_HW_SPEC_BM( 5513, 1039, 0xc2, ATA_UDMA2, "SiS 5513" , SIS33 | SIS_BASE ),
239 PCI_DEV_HW_SPEC_BM( 5513, 1039, 0x00, ATA_WDMA2, "SiS 5513" , SIS33 | SIS_BASE ),
240 PCI_DEV_HW_SPEC_BM( 0601, 1039, 0x00, ATA_UDMA2, "SiS 5513" , SIS33 | SIS_BASE ),
241 PCI_DEV_HW_SPEC_BM( ffff, ffff, 0xff, BMLIST_TERMINATOR , NULL , BMLIST_TERMINATOR )
242 };
243
244 static BUSMASTER_CONTROLLER_INFORMATION const ViaAdapters[] = {
245 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x41, ATA_UDMA2, "VIA 82C586B", VIA33 | 0x00 ),
246 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x40, ATA_UDMA2, "VIA 82C586B", VIA33 | VIAPRQ ),
247 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x02, ATA_UDMA2, "VIA 82C586B", VIA33 | 0x00 ),
248 PCI_DEV_HW_SPEC_BM( 0586, 1106, 0x00, ATA_WDMA2, "VIA 82C586" , VIA33 | 0x00 ),
249 PCI_DEV_HW_SPEC_BM( 0596, 1106, 0x12, ATA_UDMA4, "VIA 82C596B", VIA66 | VIACLK ),
250 PCI_DEV_HW_SPEC_BM( 0596, 1106, 0x00, ATA_UDMA2, "VIA 82C596" , VIA33 | 0x00 ),
251 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x40, ATA_UDMA5, "VIA 82C686B", VIA100 | VIABUG ),
252 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x10, ATA_UDMA4, "VIA 82C686A", VIA66 | VIACLK ),
253 PCI_DEV_HW_SPEC_BM( 0686, 1106, 0x00, ATA_UDMA2, "VIA 82C686" , VIA33 | 0x00 ),
254 PCI_DEV_HW_SPEC_BM( 8231, 1106, 0x00, ATA_UDMA5, "VIA 8231" , VIA100 | VIABUG ),
255 PCI_DEV_HW_SPEC_BM( 3074, 1106, 0x00, ATA_UDMA5, "VIA 8233" , VIA100 | 0x00 ),
256 PCI_DEV_HW_SPEC_BM( 3109, 1106, 0x00, ATA_UDMA5, "VIA 8233C" , VIA100 | 0x00 ),
257 PCI_DEV_HW_SPEC_BM( 3147, 1106, 0x00, ATA_UDMA6, "VIA 8233A" , VIA133 | VIAAST ),
258 PCI_DEV_HW_SPEC_BM( 3177, 1106, 0x00, ATA_UDMA6, "VIA 8235" , VIA133 | VIAAST ),
259 PCI_DEV_HW_SPEC_BM( 3227, 1106, 0x00, ATA_UDMA6, "VIA 8237" , VIA133 | VIAAST ),
260 PCI_DEV_HW_SPEC_BM( 0591, 1106, 0x00, ATA_UDMA6, "VIA 8237A" , VIA133 | VIAAST ),
261 PCI_DEV_HW_SPEC_BM( 3349, 1106, 0x00, ATA_UDMA6, "VIA 8251" , VIA133 | VIAAST ),
262 PCI_DEV_HW_SPEC_BM( ffff, ffff, 0xff, BMLIST_TERMINATOR , NULL , BMLIST_TERMINATOR )
263 };
264
265 static BUSMASTER_CONTROLLER_INFORMATION const ViaSouthAdapters[] = {
266 PCI_DEV_HW_SPEC_BM( 3112, 1106, 0x00, -1, "VIA 8361", VIASOUTH ),
267 PCI_DEV_HW_SPEC_BM( 0305, 1106, 0x00, -1, "VIA 8363", VIASOUTH ),
268 PCI_DEV_HW_SPEC_BM( 0391, 1106, 0x00, -1, "VIA 8371", VIASOUTH ),
269 PCI_DEV_HW_SPEC_BM( 3102, 1106, 0x00, -1, "VIA 8662", VIASOUTH ),
270 PCI_DEV_HW_SPEC_BM( ffff, ffff, 0xff, BMLIST_TERMINATOR, NULL , BMLIST_TERMINATOR )
271 };
272
273 KdPrint2((PRINT_PREFIX "VendorID/DeviceID/Rev %#x/%#x/%#x\n", VendorID, DeviceID, RevID));
274
275 switch(VendorID) {
276
277 case ATA_SIS_ID:
278 KdPrint2((PRINT_PREFIX "ATA_SIS_ID\n"));
279 DevTypeInfo = (BUSMASTER_CONTROLLER_INFORMATION*)&SiSAdapters[0];
280 i = AtapiFindListedDev(DevTypeInfo, -1, HwDeviceExtension, SystemIoBusNumber, PCISLOTNUM_NOT_SPECIFIED, NULL);
281 if(i != BMLIST_TERMINATOR) {
282 deviceExtension->FullDevName = SiSAdapters[i].FullDevName;
283 }
284 goto for_ugly_chips;
285
286 case ATA_VIA_ID:
287 KdPrint2((PRINT_PREFIX "ATA_VIA_ID\n"));
288 // New chips have own DeviceId
289 if(deviceExtension->DevID != ATA_VIA82C571)
290 break;
291 // Old chips have same DeviceId, we can distinguish between them
292 // only by SouthBridge DeviceId
293 DevTypeInfo = (BUSMASTER_CONTROLLER_INFORMATION*)&ViaSouthAdapters[0];
294 i = AtapiFindListedDev(DevTypeInfo, -1, HwDeviceExtension, SystemIoBusNumber, slotNumber, NULL);
295 if(i != BMLIST_TERMINATOR) {
296 KdPrint2((PRINT_PREFIX "VIASOUTH\n"));
297 deviceExtension->HwFlags |= VIASOUTH;
298 }
299 DevTypeInfo = (BUSMASTER_CONTROLLER_INFORMATION*)&ViaAdapters[0];
300 i = AtapiFindListedDev(DevTypeInfo, -1, HwDeviceExtension, SystemIoBusNumber, slotNumber, NULL);
301 if(i != BMLIST_TERMINATOR) {
302 deviceExtension->FullDevName = SiSAdapters[i].FullDevName;
303 }
304 goto for_ugly_chips;
305
306 default:
307
308 // do nothing
309 break;
310
311 #if 0
312 KdPrint2((PRINT_PREFIX "Default\n"));
313
314 deviceExtension->MaxTransferMode = deviceExtension->BaseIoAddressBM_0 ? ATA_DMA : ATA_PIO4;
315 /* do extra chipset specific setups */
316 switch(deviceExtension->DevID) {
317
318 //case ATA_CYPRESS_ID:
319 case 0xc6931080: /* 82c693 ATA controller */
320 deviceExtension->MaxTransferMode = ATA_WDMA2;
321 break;
322
323 case 0x000116ca: /* Cenatek Rocket Drive controller */
324 deviceExtension->MaxTransferMode = ATA_WDMA2;
325 break;
326
327 /* case ATA_CYRIX_ID:
328 DevTypeInfo = &CyrixAdapters[0];
329 break;*/
330 case 0x01021078: /* Cyrix 5530 ATA33 controller */
331 deviceExtension->MaxTransferMode = ATA_UDMA2;
332 break;
333
334 case 0x06401039: /* CMD 640 known bad, no DMA */
335 case 0x06011039:
336 *simplexOnly = TRUE;
337
338 /* FALLTHROUGH */
339
340 case 0x10001042: /* RZ 100x known bad, no DMA */
341 case 0x10011042:
342
343 if(deviceExtension->BaseIoAddressBM_0)
344 ScsiPortFreeDeviceBase(HwDeviceExtension,
345 deviceExtension->BaseIoAddressBM_0);
346
347 deviceExtension->BaseIoAddressBM_0 = 0;
348 deviceExtension->BusMaster = FALSE;
349 deviceExtension->MaxTransferMode = ATA_PIO4;
350 break;
351
352 case 0x81721283: /* IT8172 IDE controller */
353 deviceExtension->MaxTransferMode = ATA_UDMA2;
354 *simplexOnly = TRUE;
355 break;
356
357 default:
358 return FALSE;
359 }
360 return TRUE;
361 #endif
362 }
363
364 i = Ata_is_dev_listed(DevTypeInfo, VendorID, DeviceID, RevID, -1);
365 for_ugly_chips:
366 KdPrint2((PRINT_PREFIX "i: %#x\n", i));
367 if(i == BMLIST_TERMINATOR) {
368 return FALSE;
369 }
370 deviceExtension->MaxTransferMode = DevTypeInfo[i].MaxTransferMode;
371 deviceExtension->HwFlags |= DevTypeInfo[i].RaidFlags;
372
373 KdPrint2((PRINT_PREFIX "HwFlags: %#x\n", deviceExtension->HwFlags));
374
375 tmp32 = AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"HwFlagsOverride", deviceExtension->HwFlags);
376 KdPrint2((PRINT_PREFIX "HwFlagsOverride: %#x\n", tmp32));
377 deviceExtension->HwFlags = tmp32;
378
379 tmp32 = AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"HwFlagsAdd", 0);
380 KdPrint2((PRINT_PREFIX "HwFlagsAdd: %#x\n", tmp32));
381 deviceExtension->HwFlags |= tmp32;
382
383 KdPrint2((PRINT_PREFIX "HwFlags (final): %#x\n", deviceExtension->HwFlags));
384 if(deviceExtension->HwFlags & UNIATA_SIMPLEX_ONLY) {
385 KdPrint2((PRINT_PREFIX "UNIATA_SIMPLEX_ONLY\n" ));
386 *simplexOnly = TRUE;
387 }
388
389 KdPrint2((PRINT_PREFIX "MaxTransferMode: %#x\n", deviceExtension->MaxTransferMode));
390 tmp32 = AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"MaxTransferMode", deviceExtension->MaxTransferMode);
391 if(tmp32 != 0xffffffff) {
392 KdPrint2((PRINT_PREFIX "MaxTransferMode (overriden): %#x\n", deviceExtension->MaxTransferMode));
393 deviceExtension->MaxTransferMode = tmp32;
394 }
395
396 if(deviceExtension->MaxTransferMode >= ATA_SA150) {
397 deviceExtension->HwFlags |= UNIATA_SATA;
398 }
399 /*
400 ConfigInfo->MaximumTransferLength = DEV_BSIZE*256;
401 deviceExtension->MaximumDmaTransferLength = ConfigInfo->MaximumTransferLength;
402 */
403 ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK;
404 ChipFlags = deviceExtension->HwFlags & CHIPFLAG_MASK;
405
406 if(!UniataChipDetectChannels(HwDeviceExtension, pciData, DeviceNumber, ConfigInfo)) {
407 return FALSE;
408 }
409 if(!UniataAllocateLunExt(deviceExtension, UNIATA_ALLOCATE_NEW_LUNS)) {
410 return FALSE;
411 }
412
413 switch(VendorID) {
414 case ATA_ACER_LABS_ID:
415 if(ChipFlags & UNIATA_SATA) {
416 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator
417 BaseIoAddress1 = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber,
418 0, 0, 0x10);
419 BaseIoAddress2 = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber,
420 1, 0, 0x10);
421 BaseIoAddressBM = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber,
422 4, 0, deviceExtension->NumberChannels*sizeof(IDE_BUSMASTER_REGISTERS));
423 for(c=0; c<deviceExtension->NumberChannels; c++) {
424 //ULONG unit01 = (c & 1);
425 ULONG unit10 = (c & 2);
426 chan = &deviceExtension->chan[c];
427
428 for (i=0; i<=IDX_IO1_SZ; i++) {
429 chan->RegTranslation[IDX_IO1+i].Addr = BaseIoAddress1 + i + (unit10 ? 8 : 0);
430 }
431 chan->RegTranslation[IDX_IO2_AltStatus].Addr = BaseIoAddress2 + 2 + (unit10 ? 4 : 0);
432 UniataInitSyncBaseIO(chan);
433
434 for (i=0; i<=IDX_BM_IO_SZ; i++) {
435 chan->RegTranslation[IDX_BM_IO+i].Addr = BaseIoAddressBM + i + (c * sizeof(IDE_BUSMASTER_REGISTERS));
436 }
437
438 // SATA not supported yet
439
440 //chan->RegTranslation[IDX_BM_Command] = BaseMemAddress + 0x260 + offs7;
441 //chan->RegTranslation[IDX_BM_PRD_Table] = BaseMemAddress + 0x244 + offs7;
442 //chan->RegTranslation[IDX_BM_DeviceSpecific0] = BaseMemAddress + (c << 2);
443
444 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE;
445 }
446 }
447 break;
448 case ATA_NVIDIA_ID:
449 if(ChipFlags & UNIATA_SATA) {
450 KdPrint2((PRINT_PREFIX "NVIDIA SATA\n"));
451 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber,
452 5, 0, ((ChipFlags & NV4OFF) ? 0x400 : 0) + 0x40*2);
453 KdPrint2((PRINT_PREFIX "BaseMemAddress %x\n", BaseMemAddress));
454 if((*ConfigInfo->AccessRanges)[5].RangeInMemory) {
455 KdPrint2((PRINT_PREFIX "MemIo\n"));
456 MemIo = TRUE;
457 }
458 deviceExtension->BaseIoAddressSATA_0.Addr = BaseMemAddress;
459 deviceExtension->BaseIoAddressSATA_0.MemIo = MemIo;
460 for(c=0; c<deviceExtension->NumberChannels; c++) {
461 chan = &deviceExtension->chan[c];
462
463 chan->RegTranslation[IDX_SATA_SStatus].Addr = BaseMemAddress + (c << 6);
464 chan->RegTranslation[IDX_SATA_SStatus].MemIo = MemIo;
465 chan->RegTranslation[IDX_SATA_SError].Addr = BaseMemAddress + 4 + (c << 6);
466 chan->RegTranslation[IDX_SATA_SError].MemIo = MemIo;
467 chan->RegTranslation[IDX_SATA_SControl].Addr = BaseMemAddress + 8 + (c << 6);
468 chan->RegTranslation[IDX_SATA_SControl].MemIo = MemIo;
469
470 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE;
471 }
472 }
473 break;
474 case ATA_PROMISE_ID:
475
476 if(ChipType != PRMIO) {
477 break;
478 }
479 if(!pciData) {
480 break;
481 }
482 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator
483 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber,
484 4, 0, 0x4000);
485 KdPrint2((PRINT_PREFIX "BaseMemAddress %x\n", BaseMemAddress));
486 if((*ConfigInfo->AccessRanges)[4].RangeInMemory) {
487 KdPrint2((PRINT_PREFIX "MemIo\n"));
488 MemIo = TRUE;
489 }
490 deviceExtension->BaseIoAddressBM_0.Addr = BaseMemAddress;
491 deviceExtension->BaseIoAddressBM_0.MemIo = MemIo;
492 for(c=0; c<deviceExtension->NumberChannels; c++) {
493
494 ULONG offs12, offs7;
495
496 chan = &deviceExtension->chan[c];
497
498 offs12 = c << 12;
499 offs7 = c << 7;
500
501 for (i=0; i<=IDX_IO1_SZ; i++) {
502 chan->RegTranslation[IDX_IO1+i].Addr = BaseMemAddress + 0x200 + (i << 2) + offs12;
503 chan->RegTranslation[IDX_IO1+i].MemIo = MemIo;
504 }
505 chan->RegTranslation[IDX_IO2_AltStatus].Addr = BaseMemAddress + 0x238 + offs7;
506 chan->RegTranslation[IDX_IO2_AltStatus].MemIo = MemIo;
507
508 UniataInitSyncBaseIO(chan);
509
510 chan->RegTranslation[IDX_BM_Command].Addr = BaseMemAddress + 0x260 + offs7;
511 chan->RegTranslation[IDX_BM_Command].MemIo = MemIo;
512 chan->RegTranslation[IDX_BM_PRD_Table].Addr = BaseMemAddress + 0x244 + offs7;
513 chan->RegTranslation[IDX_BM_PRD_Table].MemIo = MemIo;
514 chan->RegTranslation[IDX_BM_DeviceSpecific0].Addr = BaseMemAddress + (c << 2);
515 chan->RegTranslation[IDX_BM_DeviceSpecific0].MemIo = MemIo;
516 }
517 break;
518
519 case ATA_ATI_ID:
520 KdPrint2((PRINT_PREFIX "ATI\n"));
521 case ATA_SILICON_IMAGE_ID: {
522
523 if(ChipFlags & SIIBUG) {
524 }
525 if(ChipType != SIIMIO) {
526 break;
527 }
528 if(!pciData) {
529 break;
530 }
531
532 if(VendorID == ATA_SILICON_IMAGE_ID) {
533 KdPrint2((PRINT_PREFIX "New SII\n"));
534 } else {
535 KdPrint2((PRINT_PREFIX "ATI SATA\n"));
536 }
537 //if(deviceExtension->HwFlags & SII4CH) {
538 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator
539 //}
540 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber,
541 5, 0, 0x800);
542 KdPrint2((PRINT_PREFIX "BaseMemAddress %x\n", BaseMemAddress));
543 if((*ConfigInfo->AccessRanges)[5].RangeInMemory) {
544 KdPrint2((PRINT_PREFIX "MemIo\n"));
545 MemIo = TRUE;
546 }
547 deviceExtension->BaseIoAddressSATA_0.Addr = BaseMemAddress;
548 deviceExtension->BaseIoAddressSATA_0.MemIo = MemIo;
549
550 for(c=0; c<deviceExtension->NumberChannels; c++) {
551 ULONG unit01 = (c & 1);
552 ULONG unit10 = (c & 2);
553
554 chan = &deviceExtension->chan[c];
555
556 if(deviceExtension->AltRegMap) {
557 for (i=0; i<=IDX_IO1_SZ; i++) {
558 chan->RegTranslation[IDX_IO1+i].Addr = BaseMemAddress + 0x80 + i + (unit01 << 6) + (unit10 << 8);
559 chan->RegTranslation[IDX_IO1+i].MemIo = MemIo;
560 }
561 chan->RegTranslation[IDX_IO2_AltStatus].Addr = BaseMemAddress + 0x8a + (unit01 << 6) + (unit10 << 8);
562 chan->RegTranslation[IDX_IO2_AltStatus].MemIo = MemIo;
563 UniataInitSyncBaseIO(chan);
564
565 chan->RegTranslation[IDX_BM_Command].Addr = BaseMemAddress + 0x00 + (unit01 << 3) + (unit10 << 8);
566 chan->RegTranslation[IDX_BM_Command].MemIo = MemIo;
567 chan->RegTranslation[IDX_BM_Status].Addr = BaseMemAddress + 0x02 + (unit01 << 3) + (unit10 << 8);
568 chan->RegTranslation[IDX_BM_Status].MemIo = MemIo;
569 chan->RegTranslation[IDX_BM_PRD_Table].Addr = BaseMemAddress + 0x04 + (unit01 << 3) + (unit10 << 8);
570 chan->RegTranslation[IDX_BM_PRD_Table].MemIo = MemIo;
571 //chan->RegTranslation[IDX_BM_DeviceSpecific0].Addr = BaseMemAddress + 0xa1 + (unit01 << 6) + (unit10 << 8);
572 //chan->RegTranslation[IDX_BM_DeviceSpecific0].MemIo = MemIo;
573 chan->RegTranslation[IDX_BM_DeviceSpecific0].Addr = BaseMemAddress + 0x10 + (unit01 << 3) + (unit10 << 8);
574 chan->RegTranslation[IDX_BM_DeviceSpecific0].MemIo = MemIo;
575 chan->RegTranslation[IDX_BM_DeviceSpecific1].Addr = BaseMemAddress + 0x40 + (unit01 << 2) + (unit10 << 8);
576 chan->RegTranslation[IDX_BM_DeviceSpecific1].MemIo = MemIo;
577 }
578
579 if(ChipFlags & UNIATA_SATA) {
580 chan->RegTranslation[IDX_SATA_SStatus].Addr = BaseMemAddress + 0x104 + (unit01 << 7) + (unit10 << 8);
581 chan->RegTranslation[IDX_SATA_SStatus].MemIo = MemIo;
582 chan->RegTranslation[IDX_SATA_SError].Addr = BaseMemAddress + 0x108 + (unit01 << 7) + (unit10 << 8);
583 chan->RegTranslation[IDX_SATA_SError].MemIo = MemIo;
584 chan->RegTranslation[IDX_SATA_SControl].Addr = BaseMemAddress + 0x100 + (unit01 << 7) + (unit10 << 8);
585 chan->RegTranslation[IDX_SATA_SControl].MemIo = MemIo;
586
587 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE;
588 }
589 }
590 break; }
591
592 case ATA_SERVERWORKS_ID: {
593
594 if(ChipType != SWKSMIO) {
595 break;
596 }
597 if(!pciData) {
598 break;
599 }
600
601 KdPrint2((PRINT_PREFIX "ServerWorks\n"));
602
603 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator
604 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber,
605 5, 0, 0x400);
606 KdPrint2((PRINT_PREFIX "BaseMemAddress %x\n", BaseMemAddress));
607 if((*ConfigInfo->AccessRanges)[5].RangeInMemory) {
608 KdPrint2((PRINT_PREFIX "MemIo\n"));
609 MemIo = TRUE;
610 }
611 deviceExtension->BaseIoAddressSATA_0.Addr = BaseMemAddress;
612 deviceExtension->BaseIoAddressSATA_0.MemIo = MemIo;
613
614 for(c=0; c<deviceExtension->NumberChannels; c++) {
615 ULONG offs = c*0x100;
616
617 chan = &deviceExtension->chan[c];
618 for (i=0; i<=IDX_IO1_SZ; i++) {
619 chan->RegTranslation[IDX_IO1+i].Addr = BaseMemAddress + offs + i*4;
620 chan->RegTranslation[IDX_IO1+i].MemIo = MemIo;
621 }
622 chan->RegTranslation[IDX_IO2_AltStatus].Addr = BaseMemAddress + offs + 0x20;
623 chan->RegTranslation[IDX_IO2_AltStatus].MemIo = MemIo;
624 UniataInitSyncBaseIO(chan);
625
626 chan->RegTranslation[IDX_BM_Command].Addr = BaseMemAddress + offs + 0x30;
627 chan->RegTranslation[IDX_BM_Command].MemIo = MemIo;
628 chan->RegTranslation[IDX_BM_Status].Addr = BaseMemAddress + offs + 0x32;
629 chan->RegTranslation[IDX_BM_Status].MemIo = MemIo;
630 chan->RegTranslation[IDX_BM_PRD_Table].Addr = BaseMemAddress + offs + 0x34;
631 chan->RegTranslation[IDX_BM_PRD_Table].MemIo = MemIo;
632
633 chan->RegTranslation[IDX_SATA_SStatus].Addr = BaseMemAddress + offs + 0x40;
634 chan->RegTranslation[IDX_SATA_SStatus].MemIo = MemIo;
635 chan->RegTranslation[IDX_SATA_SError].Addr = BaseMemAddress + offs + 0x44;
636 chan->RegTranslation[IDX_SATA_SError].MemIo = MemIo;
637 chan->RegTranslation[IDX_SATA_SControl].Addr = BaseMemAddress + offs + 0x48;
638 chan->RegTranslation[IDX_SATA_SControl].MemIo = MemIo;
639
640 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE;
641 }
642 break; }
643
644 case ATA_SIS_ID: {
645 //if(ChipType != SIS_SOUTH) {
646 BOOLEAN SIS_182=FALSE;
647
648 if(!(ChipFlags & SIS_BASE)) {
649 KdPrint2((PRINT_PREFIX "Found SIS_SOUTH\n"));
650 //PrintNtConsole("Found SIS_SOUTH\n");
651 break;
652 }
653 // Make some additional checks
654 KdPrint2((PRINT_PREFIX "ChipType == SIS_BASE\n"));
655 ChangePciConfig1(0x57, (a & 0x7f));
656 GetPciConfig4(0x00, tmp32);
657 if(tmp32 == ATA_SIS5518) {
658 ChipType = SIS133NEW;
659 deviceExtension->HwFlags = (deviceExtension->HwFlags & ~CHIPTYPE_MASK) | SIS133NEW;
660 deviceExtension->MaxTransferMode = ATA_UDMA6;
661 KdPrint2((PRINT_PREFIX "UniataChipDetect: SiS 962/963 DMA %#x controller\n", deviceExtension->MaxTransferMode));
662 //PrintNtConsole("UniataChipDetect: SiS 962/963 DMA %#x controller\n", deviceExtension->MaxTransferMode);
663 // Restore device ID
664 ChangePciConfig1(0x57, (a | 0x80));
665 } else {
666 static BUSMASTER_CONTROLLER_INFORMATION const SiSSouthAdapters[] = {
667 PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x10, -1, "SiS 961", 0 ),
668 // PCI_DEV_HW_SPEC_BM( 0008, 1039, 0x00, -1, "SiS 961", 0 ),
669 PCI_DEV_HW_SPEC_BM( ffff, ffff, 0xff, -1, NULL , -1 )
670 };
671 // Save settings
672 GetPciConfig1(0x4a, tmp8);
673 ChangePciConfig1(0x4a, (a | 0x10));
674 if(tmp32 == ATA_SIS5513 ||
675 tmp32 == ATA_SIS5517) {
676 i = AtapiFindListedDev((BUSMASTER_CONTROLLER_INFORMATION*)&SiSSouthAdapters[0],
677 -1, HwDeviceExtension, SystemIoBusNumber, PCISLOTNUM_NOT_SPECIFIED, NULL);
678 if(i != BMLIST_TERMINATOR) {
679 deviceExtension->HwFlags = (deviceExtension->HwFlags & ~CHIPTYPE_MASK) | SIS133OLD;
680 //deviceExtension->MaxTransferMode = ATA_UDMA6;
681 deviceExtension->MaxTransferMode = SiSSouthAdapters[i].MaxTransferMode;
682 if(SiSSouthAdapters[i].RaidFlags & UNIATA_SATA) {
683 deviceExtension->HwFlags |= UNIATA_SATA;
684 if(SiSSouthAdapters[i].nDeviceId == 0x1182) {
685 SIS_182 = TRUE;
686 }
687 }
688 } else {
689 // SiS-South not found
690 if(tmp32 == ATA_SIS5517) {
691 deviceExtension->HwFlags = (deviceExtension->HwFlags & ~CHIPTYPE_MASK) | SIS100NEW;
692 deviceExtension->MaxTransferMode = ATA_UDMA5;
693 } else {
694 // generic SiS33
695 KdPrint2((PRINT_PREFIX "Generic SiS DMA\n"));
696 }
697 }
698 }
699 // Restore settings
700 SetPciConfig1(0x4a, tmp8);
701 KdPrint2((PRINT_PREFIX "UniataChipDetect: SiS 961 DMA %#x controller\n", deviceExtension->MaxTransferMode));
702 //PrintNtConsole("UniataChipDetect: SiS 961 DMA %#x controller\n", deviceExtension->MaxTransferMode);
703 if(deviceExtension->HwFlags & UNIATA_SATA) {
704 KdPrint2((PRINT_PREFIX "SiS SATA\n"));
705
706 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber,
707 5, 0, 0x400);
708 KdPrint2((PRINT_PREFIX "BaseMemAddress %x\n", BaseMemAddress));
709 if((*ConfigInfo->AccessRanges)[5].RangeInMemory) {
710 KdPrint2((PRINT_PREFIX "MemIo\n"));
711 MemIo = TRUE;
712 }
713 deviceExtension->BaseIoAddressSATA_0.Addr = BaseMemAddress;
714 deviceExtension->BaseIoAddressSATA_0.MemIo = MemIo;
715
716 for(c=0; c<deviceExtension->NumberChannels; c++) {
717 ULONG offs = c << (SIS_182 ? 5 : 6);
718
719 chan = &deviceExtension->chan[c];
720 chan->RegTranslation[IDX_SATA_SStatus].Addr = BaseMemAddress + 0 + offs;
721 chan->RegTranslation[IDX_SATA_SStatus].MemIo = MemIo;
722 chan->RegTranslation[IDX_SATA_SError].Addr = BaseMemAddress + 4 + offs;
723 chan->RegTranslation[IDX_SATA_SError].MemIo = MemIo;
724 chan->RegTranslation[IDX_SATA_SControl].Addr = BaseMemAddress + 8 + offs;
725 chan->RegTranslation[IDX_SATA_SControl].MemIo = MemIo;
726
727 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE;
728 }
729 }
730 }
731 //ChangePciConfig1(0x57, (a | 0x80));
732 break; }
733
734 case ATA_VIA_ID: {
735
736 if(ChipFlags & UNIATA_SATA) {
737
738 ULONG IoSize = 0;
739 ULONG BaseMemAddress = 0;
740
741 switch(DeviceID) {
742 case 0x3149: // VIA 6420
743 KdPrint2((PRINT_PREFIX "VIA 6420\n"));
744 IoSize = 0x80;
745 break;
746 case 0x3249: // VIA 6421
747 KdPrint2((PRINT_PREFIX "VIA 6421\n"));
748 IoSize = 0x40;
749 break;
750 }
751 if(IoSize) {
752 KdPrint2((PRINT_PREFIX "IoSize %x\n", IoSize));
753 /*deviceExtension->*/BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber,
754 5, 0, IoSize * deviceExtension->NumberChannels);
755 if((*ConfigInfo->AccessRanges)[5].RangeInMemory) {
756 KdPrint2((PRINT_PREFIX "MemIo\n"));
757 MemIo = TRUE;
758 }
759 deviceExtension->BaseIoAddressSATA_0.Addr = BaseMemAddress;
760 deviceExtension->BaseIoAddressSATA_0.MemIo = MemIo;
761 }
762 if(/*deviceExtension->*/BaseMemAddress) {
763 KdPrint2((PRINT_PREFIX "UniataChipDetect: BAR5 %x\n", /*deviceExtension->*/BaseMemAddress));
764 if(ChipFlags & VIABAR) {
765
766 ULONG BaseIoAddressBM_0;
767 ULONG BaseIo;
768
769 KdPrint2((PRINT_PREFIX "UniataChipDetect: VIABAR\n"));
770 /*deviceExtension->*/BaseIoAddressBM_0 = /*(PIDE_BUSMASTER_REGISTERS)*/
771 AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, 4, 0,
772 sizeof(IDE_BUSMASTER_REGISTERS)*deviceExtension->NumberChannels);
773 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator
774 for(c=0; c<deviceExtension->NumberChannels; c++) {
775
776 chan = &deviceExtension->chan[c];
777
778 BaseIo = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber, c, 0, 0x80);
779
780 for (i=0; i<=IDX_IO1_SZ; i++) {
781 chan->RegTranslation[IDX_IO1+i].Addr = BaseIo + i;
782 }
783 chan->RegTranslation[IDX_IO2_AltStatus].Addr = BaseIo + sizeof(IDE_REGISTERS_1) + 2 + FIELD_OFFSET(IDE_REGISTERS_2, AltStatus );
784 UniataInitSyncBaseIO(chan);
785
786 for (i=0; i<=IDX_BM_IO_SZ; i++) {
787 chan->RegTranslation[IDX_BM_IO+i].Addr = BaseIoAddressBM_0 + sizeof(IDE_BUSMASTER_REGISTERS)*c + i;
788 }
789 if(c < 2) {
790 // Do not setup SATA registers for PATA part
791 chan->RegTranslation[IDX_SATA_SStatus].Addr = BaseMemAddress + (c * IoSize);
792 chan->RegTranslation[IDX_SATA_SStatus].MemIo = MemIo;
793 chan->RegTranslation[IDX_SATA_SError].Addr = BaseMemAddress + 4 + (c * IoSize);
794 chan->RegTranslation[IDX_SATA_SError].MemIo = MemIo;
795 chan->RegTranslation[IDX_SATA_SControl].Addr = BaseMemAddress + 8 + (c * IoSize);
796 chan->RegTranslation[IDX_SATA_SControl].MemIo = MemIo;
797
798 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE;
799 }
800
801 }
802 }
803 }
804 }
805 break; }
806 case ATA_INTEL_ID: {
807
808 if(!(ChipFlags & UNIATA_SATA)) {
809 break;
810 }
811
812 /* the intel 31244 needs special care if in DPA mode */
813 if(DeviceID == 3200 && // Intel 31244
814 pciData->SubClass != PCI_DEV_SUBCLASS_IDE) {
815
816 KdPrint2((PRINT_PREFIX "UniataChipDetect: Intel 31244, DPA mode\n"));
817 BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber,
818 0, 0, 0x0c00);
819 if((*ConfigInfo->AccessRanges)[0].RangeInMemory) {
820 KdPrint2((PRINT_PREFIX "MemIo\n"));
821 MemIo = TRUE;
822 }
823 deviceExtension->AltRegMap = TRUE; // inform generic resource allocator
824 deviceExtension->BaseIoAddressSATA_0.Addr = BaseMemAddress;
825 deviceExtension->BaseIoAddressSATA_0.MemIo = MemIo;
826
827 for(c=0; c<deviceExtension->NumberChannels; c++) {
828 ULONG offs = 0x200 + c*0x200;
829
830 chan = &deviceExtension->chan[c];
831 for (i=0; i<=IDX_IO1_SZ; i++) {
832 chan->RegTranslation[IDX_IO1+i].MemIo = MemIo;
833 chan->RegTranslation[IDX_IO1_o+i].MemIo = MemIo;
834 }
835
836 chan->RegTranslation[IDX_IO1_i_Data ].Addr = BaseMemAddress + 0x00 + offs;
837 chan->RegTranslation[IDX_IO1_i_Error ].Addr = BaseMemAddress + 0x04 + offs;
838 chan->RegTranslation[IDX_IO1_i_BlockCount ].Addr = BaseMemAddress + 0x08 + offs;
839 chan->RegTranslation[IDX_IO1_i_BlockNumber ].Addr = BaseMemAddress + 0x0c + offs;
840 chan->RegTranslation[IDX_IO1_i_CylinderLow ].Addr = BaseMemAddress + 0x10 + offs;
841 chan->RegTranslation[IDX_IO1_i_CylinderHigh].Addr = BaseMemAddress + 0x14 + offs;
842 chan->RegTranslation[IDX_IO1_i_DriveSelect ].Addr = BaseMemAddress + 0x18 + offs;
843 chan->RegTranslation[IDX_IO1_i_Status ].Addr = BaseMemAddress + 0x1c + offs;
844
845 UniataInitSyncBaseIO(chan);
846
847 chan->RegTranslation[IDX_IO1_o_Command ].Addr = BaseMemAddress + 0x1d + offs;
848 chan->RegTranslation[IDX_IO1_o_Feature ].Addr = BaseMemAddress + 0x06 + offs;
849 chan->RegTranslation[IDX_IO2_o_Control ].Addr = BaseMemAddress + 0x29 + offs;
850
851 chan->RegTranslation[IDX_IO2_AltStatus].Addr = BaseMemAddress + 0x28 + offs;
852 chan->RegTranslation[IDX_IO2_AltStatus].MemIo = MemIo;
853
854 chan->RegTranslation[IDX_BM_Command].Addr = BaseMemAddress + offs + 0x70;
855 chan->RegTranslation[IDX_BM_Command].MemIo = MemIo;
856 chan->RegTranslation[IDX_BM_Status].Addr = BaseMemAddress + offs + 0x72;
857 chan->RegTranslation[IDX_BM_Status].MemIo = MemIo;
858 chan->RegTranslation[IDX_BM_PRD_Table].Addr = BaseMemAddress + offs + 0x74;
859 chan->RegTranslation[IDX_BM_PRD_Table].MemIo = MemIo;
860
861 chan->RegTranslation[IDX_SATA_SStatus].Addr = BaseMemAddress + 0x100 + offs;
862 chan->RegTranslation[IDX_SATA_SStatus].MemIo = MemIo;
863 chan->RegTranslation[IDX_SATA_SError].Addr = BaseMemAddress + 0x104 + offs;
864 chan->RegTranslation[IDX_SATA_SError].MemIo = MemIo;
865 chan->RegTranslation[IDX_SATA_SControl].Addr = BaseMemAddress + 0x108 + offs;
866 chan->RegTranslation[IDX_SATA_SControl].MemIo = MemIo;
867
868 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE;
869 }
870
871 break;
872 }
873 /* SATA parts can be either compat or AHCI */
874 if(ChipFlags & UNIATA_AHCI) {
875
876 GetPciConfig1(0x90, tmp8);
877 if(tmp8 & 0xc0) {
878 KdPrint2((PRINT_PREFIX "AHCI not supported yet\n"));
879 return FALSE;
880 }
881 deviceExtension->HwFlags &= ~UNIATA_AHCI;
882 }
883 #if 0
884 if(ChipFlags & UNIATA_SATA) {
885 //BaseMemAddress = AtapiGetIoRange(HwDeviceExtension, ConfigInfo, pciData, SystemIoBusNumber,
886 // 0, 0, 0x0c00);
887 BaseMemAddress = NULL; // HACK-HACK
888 if(!BaseMemAddress) {
889 KdPrint2((PRINT_PREFIX "Intel: no SATA I/O space, operate in PATA Compatible mode\n"));
890 deviceExtension->HwFlags &= ~UNIATA_SATA;
891 break;
892 }
893 if((*ConfigInfo->AccessRanges)[0].RangeInMemory) {
894 KdPrint2((PRINT_PREFIX "MemIo\n"));
895 MemIo = TRUE;
896 }
897 deviceExtension->BaseIoAddressSATA_0.Addr = BaseMemAddress;
898 deviceExtension->BaseIoAddressSATA_0.MemIo = MemIo;
899 }
900 #endif
901 break; }
902 case 0x1078:
903 /* Cyrix 5530 ATA33 controller */
904 if(deviceExtension->DevID == 0x01021078) {
905 ConfigInfo->AlignmentMask = 0x0f;
906 deviceExtension->MaximumDmaTransferLength = 63*1024;
907 }
908 break;
909 }
910
911 return TRUE;
912
913 } // end UniataChipDetect()
914
915
916 /*
917 Do some 'magic staff' for VIA SouthBridge
918 This will prevent data losses
919 */
920 VOID
921 NTAPI
922 AtapiViaSouthBridgeFixup(
923 IN PVOID HwDeviceExtension,
924 IN BUS_DATA_TYPE BusDataType,
925 IN ULONG SystemIoBusNumber,
926 IN ULONG slotNumber
927 )
928 {
929 PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension;
930 PCI_COMMON_CONFIG pciData;
931 ULONG funcNumber;
932 ULONG busDataRead;
933
934 ULONG VendorID;
935 ULONG DeviceID;
936 PCI_SLOT_NUMBER slotData;
937 ULONG dev_id;
938 BOOLEAN found = FALSE;
939
940 slotData.u.AsULONG = slotNumber;
941 for(funcNumber = 0; funcNumber < PCI_MAX_FUNCTION; funcNumber++) {
942
943 slotData.u.bits.FunctionNumber = funcNumber;
944
945 busDataRead = ScsiPortGetBusData(HwDeviceExtension,
946 PCIConfiguration,
947 SystemIoBusNumber,
948 slotData.u.AsULONG,
949 &pciData,
950 PCI_COMMON_HDR_LENGTH);
951
952 if (busDataRead < (ULONG)PCI_COMMON_HDR_LENGTH) {
953 continue;
954 }
955
956 VendorID = pciData.VendorID;
957 DeviceID = pciData.DeviceID;
958 dev_id = (VendorID | (DeviceID << 16));
959
960 if (dev_id == 0x03051106 || /* VIA VT8363 */
961 dev_id == 0x03911106 || /* VIA VT8371 */
962 dev_id == 0x31021106 || /* VIA VT8662 */
963 dev_id == 0x31121106) { /* VIA VT8361 */
964 UCHAR reg76;
965
966 GetPciConfig1(0x76, reg76);
967
968 if ((reg76 & 0xf0) != 0xd0) {
969 SetPciConfig1(0x75, 0x80);
970 SetPciConfig1(0x76, (reg76 & 0x0f) | 0xd0);
971 }
972 found = TRUE;
973 break;
974 }
975 }
976 if(!found) {
977 deviceExtension->HwFlags &= ~VIABUG;
978 }
979 } // end AtapiViaSouthBridgeFixup()
980
981 /*
982 Do some 'magic staff' for ROSB SouthBridge
983 This will prevent data losses
984 */
985 VOID
986 NTAPI
987 AtapiRosbSouthBridgeFixup(
988 IN PVOID HwDeviceExtension,
989 IN BUS_DATA_TYPE BusDataType,
990 IN ULONG SystemIoBusNumber,
991 IN ULONG slotNumber
992 )
993 {
994 //PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension;
995 PCI_COMMON_CONFIG pciData;
996 ULONG funcNumber;
997 ULONG busDataRead;
998
999 ULONG VendorID;
1000 ULONG DeviceID;
1001 PCI_SLOT_NUMBER slotData;
1002 ULONG dev_id;
1003 // BOOLEAN found = FALSE;
1004
1005 /* locate the ISA part in the southbridge and enable UDMA33 */
1006 slotData.u.AsULONG = slotNumber;
1007 for(funcNumber = 0; funcNumber < PCI_MAX_FUNCTION; funcNumber++) {
1008
1009 slotData.u.bits.FunctionNumber = funcNumber;
1010
1011 busDataRead = ScsiPortGetBusData(HwDeviceExtension,
1012 PCIConfiguration,
1013 SystemIoBusNumber,
1014 slotData.u.AsULONG,
1015 &pciData,
1016 PCI_COMMON_HDR_LENGTH);
1017
1018 if (busDataRead < (ULONG)PCI_COMMON_HDR_LENGTH) {
1019 continue;
1020 }
1021
1022 VendorID = pciData.VendorID;
1023 DeviceID = pciData.DeviceID;
1024 dev_id = (VendorID | (DeviceID << 16));
1025
1026 if (dev_id == ATA_ROSB4_ISA) { /* VIA VT8361 */
1027 ChangePciConfig4(0x64, ((a & ~0x00002000) | 0x00004000));
1028 break;
1029 }
1030 }
1031 } // end AtapiRosbSouthBridgeFixup()
1032
1033 /*
1034 Do some 'magic staff' for ROSB SouthBridge
1035 This will prevent data losses
1036 */
1037 VOID
1038 NTAPI
1039 AtapiAliSouthBridgeFixup(
1040 IN PVOID HwDeviceExtension,
1041 IN BUS_DATA_TYPE BusDataType,
1042 IN ULONG SystemIoBusNumber,
1043 IN ULONG slotNumber,
1044 IN ULONG c
1045 )
1046 {
1047 //PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension;
1048 PCI_COMMON_CONFIG pciData;
1049 ULONG funcNumber;
1050 ULONG busDataRead;
1051
1052 ULONG VendorID;
1053 ULONG DeviceID;
1054 PCI_SLOT_NUMBER slotData;
1055 ULONG dev_id;
1056 // BOOLEAN found = FALSE;
1057
1058 /* workaround for datacorruption bug found on at least SUN Blade-100
1059 * find the ISA function on the southbridge and disable then enable
1060 * the ATA channel tristate buffer */
1061 slotData.u.AsULONG = slotNumber;
1062 for(funcNumber = 0; funcNumber < PCI_MAX_FUNCTION; funcNumber++) {
1063
1064 slotData.u.bits.FunctionNumber = funcNumber;
1065
1066 busDataRead = ScsiPortGetBusData(HwDeviceExtension,
1067 PCIConfiguration,
1068 SystemIoBusNumber,
1069 slotData.u.AsULONG,
1070 &pciData,
1071 PCI_COMMON_HDR_LENGTH);
1072
1073 if (busDataRead < (ULONG)PCI_COMMON_HDR_LENGTH) {
1074 continue;
1075 }
1076
1077 VendorID = pciData.VendorID;
1078 DeviceID = pciData.DeviceID;
1079 dev_id = (VendorID | (DeviceID << 16));
1080
1081 if (dev_id == ATA_ALI_1533) { /* SOUTH */
1082 ChangePciConfig1(0x58, (a & ~(0x04 << c)));
1083 ChangePciConfig1(0x58, (a | (0x04 << c)));
1084 break;
1085 }
1086 }
1087 } // end AtapiRosbSouthBridgeFixup()
1088
1089 ULONG
1090 NTAPI
1091 hpt_cable80(
1092 IN PHW_DEVICE_EXTENSION deviceExtension,
1093 IN ULONG channel // physical channel number (0-1)
1094 )
1095 {
1096 PVOID HwDeviceExtension = (PVOID)deviceExtension;
1097 ULONG slotNumber = deviceExtension->slotNumber;
1098 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber;
1099
1100 ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK;
1101
1102 UCHAR reg, val, res;
1103 PCI_SLOT_NUMBER slotData;
1104
1105 slotData.u.AsULONG = deviceExtension->slotNumber;
1106
1107 if(ChipType == HPT374 && slotData.u.bits.FunctionNumber == 1) {
1108 reg = channel ? 0x57 : 0x53;
1109 GetPciConfig1(reg, val);
1110 SetPciConfig1(reg, val | 0x80);
1111 }
1112 else {
1113 reg = 0x5b;
1114 GetPciConfig1(reg, val);
1115 SetPciConfig1(reg, val & 0xfe);
1116 }
1117 GetPciConfig1(0x5a, res);
1118 res = res & (channel ? 0x01 : 0x02);
1119 SetPciConfig1(reg, val);
1120 return !res;
1121 } // end hpt_cable80()
1122
1123
1124 ULONG
1125 NTAPI
1126 via_cable80(
1127 IN PHW_DEVICE_EXTENSION deviceExtension,
1128 IN ULONG channel // physical channel number (0-1)
1129 )
1130 {
1131 PVOID HwDeviceExtension = (PVOID)deviceExtension;
1132 ULONG slotNumber = deviceExtension->slotNumber;
1133 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber;
1134
1135 ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK;
1136
1137 ULONG reg50;
1138 ULONG a;
1139 ULONG i, j;
1140 BOOLEAN res;
1141
1142 GetPciConfig1(0x50, reg50);
1143
1144 switch(ChipType) {
1145 case VIA133:
1146 a = 8;
1147 break;
1148 case VIA100:
1149 a = 4;
1150 break;
1151 case VIA66:
1152 a = 2;
1153 break;
1154 default:
1155 return false;
1156 }
1157
1158 res = FALSE;
1159 for (j=0; j>=2; i -= 8) {
1160 i = (3-(channel*2+j))*8;
1161 if (((reg50 >> (i & 0x10)) & 8) &&
1162 ((reg50 >> i) & 0x20) &&
1163 (((reg50 >> i) & 7) < a)) {
1164
1165 res |= TRUE; //(1 << (1 - (i >> 4)));
1166 }
1167 }
1168 return res;
1169
1170 } // end via_cable80()
1171
1172 BOOLEAN
1173 NTAPI
1174 generic_cable80(
1175 IN PHW_DEVICE_EXTENSION deviceExtension,
1176 IN ULONG channel, // physical channel number (0-1)
1177 IN ULONG pci_reg,
1178 IN ULONG bit_offs
1179 )
1180 {
1181 PVOID HwDeviceExtension = (PVOID)deviceExtension;
1182 ULONG slotNumber = deviceExtension->slotNumber;
1183 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber;
1184
1185 //ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK;
1186 PHW_CHANNEL chan;
1187 ULONG c; // logical channel (for Compatible Mode controllers)
1188 UCHAR tmp8;
1189
1190 c = channel - deviceExtension->Channel; // logical channel (for Compatible Mode controllers)
1191 chan = &deviceExtension->chan[c];
1192
1193 GetPciConfig1(pci_reg, tmp8);
1194 if(!(tmp8 & (1 << (channel << bit_offs)))) {
1195 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1196 return FALSE;
1197 }
1198
1199 return TRUE;
1200 } // end generic_cable80()
1201
1202 VOID
1203 NTAPI
1204 UniAtaReadLunConfig(
1205 IN PHW_DEVICE_EXTENSION deviceExtension,
1206 IN ULONG channel, // physical channel
1207 IN ULONG ldev
1208 )
1209 {
1210 ULONG tmp32;
1211 PHW_CHANNEL chan;
1212 PHW_LU_EXTENSION LunExt;
1213 ULONG c;
1214
1215 c = channel - deviceExtension->Channel; // logical channel
1216
1217 chan = &deviceExtension->chan[c];
1218 ldev &= 0x01;
1219 LunExt = &(deviceExtension->lun[c*2+ldev]);
1220
1221 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, ldev, L"ReadCacheEnable", 1);
1222 LunExt->opt_ReadCacheEnable = tmp32 ? TRUE : FALSE;
1223
1224 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, ldev, L"WriteCacheEnable", 1);
1225 LunExt->opt_WriteCacheEnable = tmp32 ? TRUE : FALSE;
1226
1227 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, ldev, L"MaxTransferMode", chan->MaxTransferMode);
1228 LunExt->opt_MaxTransferMode = tmp32;
1229
1230 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, ldev, L"PreferedTransferMode", 0xffffffff);
1231 LunExt->opt_PreferedTransferMode = tmp32;
1232
1233 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, ldev, L"ReadOnly", 0);
1234 if(tmp32 <= 2) {
1235 LunExt->opt_ReadOnly = (UCHAR)tmp32;
1236 }
1237
1238 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, ldev, L"GeomType", 0xffffffff);
1239 if(tmp32 > 2) {
1240 tmp32 = 0xffffffff;
1241 }
1242 LunExt->opt_GeomType = tmp32;
1243
1244 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, ldev, L"Hidden", 0);
1245 if(tmp32) {
1246 LunExt->DeviceFlags |= DFLAGS_HIDDEN;
1247 }
1248
1249 return;
1250 } // end UniAtaReadLunConfig()
1251
1252 BOOLEAN
1253 NTAPI
1254 AtapiReadChipConfig(
1255 IN PVOID HwDeviceExtension,
1256 IN ULONG DeviceNumber,
1257 IN ULONG channel // physical channel
1258 )
1259 {
1260 PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension;
1261 PHW_CHANNEL chan;
1262 ULONG tmp32;
1263 ULONG c; // logical channel (for Compatible Mode controllers)
1264
1265 KdPrint2((PRINT_PREFIX "AtapiReadChipConfig: devExt %#x\n", deviceExtension ));
1266 ASSERT(deviceExtension);
1267
1268 if(channel != CHAN_NOT_SPECIFIED) {
1269 c = channel - deviceExtension->Channel; // logical channel (for Compatible Mode controllers)
1270 } else {
1271 c = CHAN_NOT_SPECIFIED;
1272 }
1273
1274 KdPrint2((PRINT_PREFIX "AtapiReadChipConfig: dev %#x, ph chan %d\n", DeviceNumber, channel ));
1275
1276 if(channel == CHAN_NOT_SPECIFIED) {
1277 if(AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"ForceSimplex", FALSE)) {
1278 deviceExtension->simplexOnly = TRUE;
1279 }
1280 deviceExtension->opt_AtapiDmaZeroTransfer = FALSE;
1281 deviceExtension->opt_AtapiDmaControlCmd = FALSE;
1282 deviceExtension->opt_AtapiDmaRawRead = FALSE;//TRUE; // Disabling that for VirtualBox
1283 deviceExtension->opt_AtapiDmaReadWrite = TRUE;
1284 }
1285
1286 if(c == CHAN_NOT_SPECIFIED) {
1287 KdPrint2((PRINT_PREFIX "MaxTransferMode (base): %#x\n", deviceExtension->MaxTransferMode));
1288 for(c=0; c<deviceExtension->NumberChannels; c++) {
1289 chan = &deviceExtension->chan[c];
1290 chan->MaxTransferMode = deviceExtension->MaxTransferMode;
1291 tmp32 = AtapiRegCheckDevValue(deviceExtension, channel, DEVNUM_NOT_SPECIFIED, L"MaxTransferMode", chan->MaxTransferMode);
1292 if(tmp32 != 0xffffffff) {
1293 KdPrint2((PRINT_PREFIX "MaxTransferMode (overriden): %#x\n", chan->MaxTransferMode));
1294 chan->MaxTransferMode = tmp32;
1295 }
1296 //UniAtaReadLunConfig(deviceExtension, c, 0);
1297 //UniAtaReadLunConfig(deviceExtension, c, 1);
1298 }
1299
1300 deviceExtension->opt_AtapiDmaZeroTransfer =
1301 AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"AtapiDmaZeroTransfer", deviceExtension->opt_AtapiDmaZeroTransfer) ?
1302 TRUE : FALSE;
1303
1304 deviceExtension->opt_AtapiDmaControlCmd =
1305 AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"AtapiDmaControlCmd", deviceExtension->opt_AtapiDmaControlCmd) ?
1306 TRUE : FALSE;
1307
1308 deviceExtension->opt_AtapiDmaRawRead =
1309 AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"AtapiDmaRawRead", deviceExtension->opt_AtapiDmaRawRead) ?
1310 TRUE : FALSE;
1311
1312 deviceExtension->opt_AtapiDmaReadWrite =
1313 AtapiRegCheckDevValue(deviceExtension, CHAN_NOT_SPECIFIED, DEVNUM_NOT_SPECIFIED, L"AtapiDmaReadWrite", deviceExtension->opt_AtapiDmaReadWrite) ?
1314 TRUE : FALSE;
1315
1316 } else {
1317 chan = &deviceExtension->chan[c];
1318 chan->MaxTransferMode = deviceExtension->MaxTransferMode;
1319 tmp32 = AtapiRegCheckDevValue(deviceExtension, c, DEVNUM_NOT_SPECIFIED, L"MaxTransferMode", chan->MaxTransferMode);
1320 if(tmp32 != 0xffffffff) {
1321 KdPrint2((PRINT_PREFIX "MaxTransferMode (overriden): %#x\n", chan->MaxTransferMode));
1322 chan->MaxTransferMode = tmp32;
1323 }
1324 tmp32 = AtapiRegCheckDevValue(deviceExtension, c, DEVNUM_NOT_SPECIFIED, L"ReorderEnable", TRUE);
1325 chan->UseReorder = tmp32 ? TRUE : FALSE;
1326
1327 UniAtaReadLunConfig(deviceExtension, channel, 0);
1328 UniAtaReadLunConfig(deviceExtension, channel, 1);
1329 }
1330
1331 return TRUE;
1332 } // end AtapiReadChipConfig()
1333
1334 BOOLEAN
1335 NTAPI
1336 AtapiChipInit(
1337 IN PVOID HwDeviceExtension,
1338 IN ULONG DeviceNumber,
1339 IN ULONG channel // physical channel
1340 )
1341 {
1342 PHW_DEVICE_EXTENSION deviceExtension = (PHW_DEVICE_EXTENSION)HwDeviceExtension;
1343 ULONG slotNumber = deviceExtension->slotNumber;
1344 ULONG SystemIoBusNumber = deviceExtension->SystemIoBusNumber;
1345 ULONG VendorID = deviceExtension->DevID & 0xffff;
1346 #ifdef _DEBUG
1347 ULONG DeviceID = (deviceExtension->DevID >> 16) & 0xffff;
1348 #endif
1349 ULONG RevID = deviceExtension->RevID;
1350 // ULONG i;
1351 // BUSMASTER_CONTROLLER_INFORMATION* DevTypeInfo;
1352 ULONG ChipType = deviceExtension->HwFlags & CHIPTYPE_MASK;
1353 ULONG ChipFlags = deviceExtension->HwFlags & CHIPFLAG_MASK;
1354 PHW_CHANNEL chan;
1355 UCHAR tmp8;
1356 USHORT tmp16;
1357 ULONG tmp32;
1358 ULONG c; // logical channel (for Compatible Mode controllers)
1359 BOOLEAN CheckCable = FALSE;
1360 //ULONG BaseIoAddress;
1361
1362 switch(channel) {
1363 case CHAN_NOT_SPECIFIED_CHECK_CABLE:
1364 CheckCable = TRUE;
1365 /* FALLTHROUGH */
1366 case CHAN_NOT_SPECIFIED:
1367 c = CHAN_NOT_SPECIFIED;
1368 break;
1369 default:
1370 c = channel - deviceExtension->Channel; // logical channel (for Compatible Mode controllers)
1371 }
1372
1373 KdPrint2((PRINT_PREFIX "AtapiChipInit: dev %#x, ph chan %d\n", DeviceNumber, channel ));
1374
1375 KdPrint2((PRINT_PREFIX "HwFlags: %#x\n", deviceExtension->HwFlags));
1376 KdPrint2((PRINT_PREFIX "VendorID/DeviceID/Rev %#x/%#x/%#x\n", VendorID, DeviceID, RevID));
1377
1378 if(deviceExtension->UnknownDev) {
1379 KdPrint2((PRINT_PREFIX " Unknown chip, exiting\n" ));
1380 //return TRUE;
1381 VendorID = 0xffffffff;
1382 }
1383
1384 switch(VendorID) {
1385 // case ATA_ACARD_ID:
1386 // break;
1387 case ATA_ACER_LABS_ID:
1388 if(ChipFlags & UNIATA_SATA) {
1389 if(c == CHAN_NOT_SPECIFIED) {
1390 for(c=0; c<deviceExtension->NumberChannels; c++) {
1391 chan = &deviceExtension->chan[c];
1392 chan->ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE;
1393 /* the southbridge might need the data corruption fix */
1394 if(RevID == 0xc2 || RevID == 0xc3) {
1395 AtapiAliSouthBridgeFixup(HwDeviceExtension, PCIConfiguration,
1396 SystemIoBusNumber, slotNumber, c);
1397 }
1398 }
1399 /* enable PCI interrupt */
1400 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG, Command), (a & ~0x0400));
1401 }
1402 } else
1403 if(ChipFlags & ALINEW) {
1404 if(c == CHAN_NOT_SPECIFIED) {
1405 /* use device interrupt as byte count end */
1406 ChangePciConfig1(0x4a, (a | 0x20));
1407 /* enable cable detection and UDMA support on newer chips */
1408 ChangePciConfig1(0x4b, (a | 0x09));
1409
1410 /* enable ATAPI UDMA mode */
1411 ChangePciConfig1(0x53, (a | 0x01));
1412
1413 } else {
1414 // check 80-pin cable
1415 generic_cable80(deviceExtension, channel, 0x4a, 0);
1416 }
1417 } else {
1418 if(c == CHAN_NOT_SPECIFIED) {
1419 /* deactivate the ATAPI FIFO and enable ATAPI UDMA */
1420 ChangePciConfig1(0x53, (a | 0x03));
1421 } else {
1422 // ATAPI DMA R/O
1423 deviceExtension->chan[c].ChannelCtrlFlags |= CTRFLAGS_DMA_RO;
1424 }
1425 }
1426 break;
1427 case ATA_AMD_ID:
1428 if(c == CHAN_NOT_SPECIFIED) {
1429 /* set prefetch, postwrite */
1430 if(ChipFlags & AMDBUG) {
1431 ChangePciConfig1(0x41, (a & 0x0f));
1432 } else {
1433 ChangePciConfig1(0x41, (a | 0xf0));
1434 }
1435 }
1436 if(deviceExtension->MaxTransferMode < ATA_UDMA2)
1437 break;
1438 // check 80-pin cable
1439 if(!(ChipFlags & UNIATA_NO80CHK)) {
1440 if(c == CHAN_NOT_SPECIFIED) {
1441 // do nothing
1442 } else {
1443 generic_cable80(deviceExtension, channel, 0x42, 0);
1444 }
1445 }
1446 break;
1447 case ATA_HIGHPOINT_ID:
1448
1449 if(c == CHAN_NOT_SPECIFIED) {
1450
1451 if(ChipFlags & HPTOLD) {
1452 /* turn off interrupt prediction */
1453 ChangePciConfig1(0x51, (a & ~0x80));
1454 } else {
1455 /* turn off interrupt prediction */
1456 ChangePciConfig1(0x51, (a & ~0x03));
1457 ChangePciConfig1(0x55, (a & ~0x03));
1458 /* turn on interrupts */
1459 ChangePciConfig1(0x5a, (a & ~0x10));
1460 /* set clocks etc */
1461 if(ChipType < HPT372) {
1462 SetPciConfig1(0x5b, 0x22);
1463 } else {
1464 ChangePciConfig1(0x5b, ((a & 0x01) | 0x20));
1465 }
1466 }
1467
1468 } else {
1469 // check 80-pin cable
1470 chan = &deviceExtension->chan[c];
1471 if(!hpt_cable80(deviceExtension, channel)) {
1472 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1473 }
1474 }
1475 break;
1476 case ATA_INTEL_ID: {
1477 USHORT reg54;
1478 if(ChipFlags & UNIATA_SATA) {
1479 if(c != CHAN_NOT_SPECIFIED)
1480 break;
1481 #if 0
1482 /* force all ports active "the legacy way" */
1483 ChangePciConfig2(0x92, (a | 0x0f));
1484 /* enable PCI interrupt */
1485 ChangePciConfig2(/*PCIR_COMMAND*/0x04, (a & ~0x0400));
1486
1487 if(!(ChipFlags & UNIATA_AHCI)) {
1488 /* ICH5 in compat mode has SATA ports as master/slave on 1 channel */
1489 GetPciConfig1(0x90, tmp8);
1490 if(!(tmp8 & 0x04)) {
1491 /* XXX SOS should be in intel_allocate if we grow it */
1492 if(c == CHAN_NOT_SPECIFIED) {
1493 for(c=0; c<deviceExtension->NumberChannels; c++) {
1494 deviceExtension->chan[c].ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE;
1495 }
1496 } else {
1497 deviceExtension->chan[c].ChannelCtrlFlags |= CTRFLAGS_NO_SLAVE;
1498 }
1499 }
1500 }
1501 #else
1502 /* enable PCI interrupt */
1503 ChangePciConfig2(/*PCIR_COMMAND*/0x04, (a & ~0x0400));
1504 #endif
1505 break;
1506 }
1507 if(deviceExtension->MaxTransferMode < ATA_UDMA2)
1508 break;
1509 // check 80-pin cable
1510 if(c == CHAN_NOT_SPECIFIED) {
1511 // do nothing
1512 } else {
1513 chan = &deviceExtension->chan[c];
1514 GetPciConfig2(0x54, reg54);
1515 if( ((reg54 >> (channel*2)) & 30) != 30) {
1516 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1517 }
1518 }
1519 break; }
1520 case ATA_NVIDIA_ID: {
1521 if(ChipFlags & UNIATA_SATA) {
1522 if(c == CHAN_NOT_SPECIFIED) {
1523 ULONG offs = (ChipFlags & NV4OFF) ? 0x0440 : 0x0010;
1524 /* enable control access */
1525 ChangePciConfig1(0x50, (a | 0x04));
1526 KdPrint2((PRINT_PREFIX "BaseIoAddressSATA_0=%x\n", deviceExtension->BaseIoAddressSATA_0.Addr));
1527 if(ChipFlags & NVQ) {
1528 /* clear interrupt status */
1529 AtapiWritePortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0),offs, 0x00ff00ff);
1530 /* enable device and PHY state change interrupts */
1531 AtapiWritePortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0),offs+4, 0x000d000d);
1532 /* disable NCQ support */
1533 AtapiWritePortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0),0x0400,
1534 AtapiReadPortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0),0x0400) & 0xfffffff9);
1535 } else {
1536 /* clear interrupt status */
1537 AtapiWritePortEx1(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0),offs, 0xff);
1538 /* enable device and PHY state change interrupts */
1539 AtapiWritePortEx1(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0),offs+1, 0xdd);
1540 }
1541 /* enable PCI interrupt */
1542 ChangePciConfig2(offsetof(PCI_COMMON_CONFIG, Command), (a & ~0x0400));
1543 } else {
1544 //UniataSataPhyEnable(HwDeviceExtension, c);
1545 }
1546 } else {
1547 //UCHAR reg52;
1548
1549 if(c == CHAN_NOT_SPECIFIED) {
1550 /* set prefetch, postwrite */
1551 ChangePciConfig1(0x51, (a & 0x0f));
1552 } else {
1553 // check 80-pin cable
1554 generic_cable80(deviceExtension, channel, 0x52, 1);
1555 /* chan = &deviceExtension->chan[c];
1556 GetPciConfig1(0x52, reg52);
1557 if( !((reg52 >> (channel*2)) & 0x01)) {
1558 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1559 }*/
1560 }
1561 }
1562 break; }
1563 case ATA_PROMISE_ID: {
1564 USHORT Reg50;
1565 switch(ChipType) {
1566 case PRNEW:
1567 /* setup clocks */
1568 if(c == CHAN_NOT_SPECIFIED) {
1569 // ATA_OUTB(ctlr->r_res1, 0x11, ATA_INB(ctlr->r_res1, 0x11) | 0x0a);
1570 AtapiWritePortEx1(NULL, (ULONG)(&deviceExtension->BaseIoAddressBM_0),0x11,
1571 AtapiReadPortEx1(NULL, (ULONG)(&deviceExtension->BaseIoAddressBM_0),0x11) | 0x0a );
1572 }
1573 /* FALLTHROUGH */
1574 case PROLD:
1575 /* enable burst mode */
1576 // ATA_OUTB(ctlr->r_res1, 0x1f, ATA_INB(ctlr->r_res1, 0x1f) | 0x01);
1577 if(c == CHAN_NOT_SPECIFIED) {
1578 AtapiWritePortEx1(NULL, (ULONG)(&deviceExtension->BaseIoAddressBM_0),0x1f,
1579 AtapiReadPortEx1(NULL, (ULONG)(&deviceExtension->BaseIoAddressBM_0),0x1f) | 0x01 );
1580 } else {
1581 // check 80-pin cable
1582 chan = &deviceExtension->chan[c];
1583 GetPciConfig2(0x50, Reg50);
1584 if(Reg50 & (1 << (channel+10))) {
1585 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1586 }
1587 }
1588 break;
1589 case PRTX:
1590 if(c == CHAN_NOT_SPECIFIED) {
1591 // do nothing
1592 } else {
1593 // check 80-pin cable
1594 chan = &deviceExtension->chan[c];
1595 AtapiWritePort1(chan, IDX_BM_DeviceSpecific0, 0x0b);
1596 if(AtapiReadPort1(chan, IDX_BM_DeviceSpecific1) & 0x04) {
1597 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1598 }
1599 }
1600 break;
1601 case PRMIO:
1602 if(c == CHAN_NOT_SPECIFIED) {
1603 if(ChipFlags & PRSATA) {
1604 AtapiWritePortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressBM_0),0x6c, 0x000000ff);
1605 }
1606 } else {
1607 chan = &deviceExtension->chan[c];
1608 AtapiWritePort4(chan, IDX_BM_Command,
1609 (AtapiReadPort4(chan, IDX_BM_Command) & ~0x00000f8f) | channel );
1610 AtapiWritePort4(chan, IDX_BM_DeviceSpecific0, 0x00000001);
1611 // check 80-pin cable
1612 if(chan->MaxTransferMode < ATA_SA150 &&
1613 (AtapiReadPort4(chan, IDX_BM_Command) & 0x01000000)) {
1614 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1615 }
1616 }
1617 break;
1618 }
1619 break; }
1620 case ATA_SERVERWORKS_ID:
1621 if(c == CHAN_NOT_SPECIFIED) {
1622 if(ChipType == SWKS33) {
1623 AtapiRosbSouthBridgeFixup(HwDeviceExtension, PCIConfiguration,
1624 SystemIoBusNumber, slotNumber);
1625 } else {
1626 ChangePciConfig1(0x5a, ((a & ~0x40) | ((ChipType == SWKS100) ? 0x03 : 0x02)));
1627 }
1628 }
1629 break;
1630 case ATA_ATI_ID:
1631 if(ChipType == SIIMIO) {
1632 KdPrint2((PRINT_PREFIX "ATI New\n"));
1633 // fall to SiI
1634 } else {
1635 KdPrint2((PRINT_PREFIX "ATI\n"));
1636 break;
1637 }
1638 case ATA_SILICON_IMAGE_ID:
1639 /* if(ChipFlags & SIIENINTR) {
1640 SetPciConfig1(0x71, 0x01);
1641 }*/
1642 switch(ChipType) {
1643 case SIIMIO: {
1644
1645 KdPrint2((PRINT_PREFIX "SII\n"));
1646 USHORT Reg79;
1647
1648 if(c == CHAN_NOT_SPECIFIED) {
1649 if(ChipFlags & SIISETCLK) {
1650 KdPrint2((PRINT_PREFIX "SIISETCLK\n"));
1651 GetPciConfig1(0x8a, tmp8);
1652 if ((tmp8 & 0x30) != 0x10)
1653 ChangePciConfig1(0x8a, (a & 0xcf) | 0x10);
1654 GetPciConfig1(0x8a, tmp8);
1655 if ((tmp8 & 0x30) != 0x10) {
1656 KdPrint2((PRINT_PREFIX "Sil 0680 could not set ATA133 clock\n"));
1657 deviceExtension->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA5);
1658 }
1659 }
1660 }
1661 if(deviceExtension->MaxTransferMode < ATA_SA150) {
1662 // check 80-pin cable
1663 if(c == CHAN_NOT_SPECIFIED) {
1664 // do nothing
1665 } else {
1666 KdPrint2((PRINT_PREFIX "Check UDMA66 cable\n"));
1667 chan = &deviceExtension->chan[c];
1668 GetPciConfig2(0x79, Reg79);
1669 if(Reg79 & (channel ? 0x02 : 0x01)) {
1670 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1671 }
1672 }
1673 } else {
1674 ULONG unit01 = (c & 1);
1675 ULONG unit10 = (c & 2);
1676 /* enable/disable PHY state change interrupt */
1677 if(c == CHAN_NOT_SPECIFIED) {
1678 for(c=0; c<deviceExtension->NumberChannels; c++) {
1679 unit01 = (c & 1);
1680 unit10 = (c & 2);
1681 if(ChipFlags & SIINOSATAIRQ) {
1682 KdPrint2((PRINT_PREFIX "Disable broken SATA intr on c=%x\n", c));
1683 AtapiWritePortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0), 0x148 + (unit01 << 7) + (unit10 << 8),0);
1684 }
1685 }
1686 } else {
1687 if(ChipFlags & SIINOSATAIRQ) {
1688 KdPrint2((PRINT_PREFIX "Disable broken SATA intr on c=%x\n", c));
1689 AtapiWritePortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0), 0x148 + (unit01 << 7) + (unit10 << 8),0);
1690 } else {
1691 KdPrint2((PRINT_PREFIX "Enable SATA intr on c=%x\n", c));
1692 AtapiWritePortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0), 0x148 + (unit01 << 7) + (unit10 << 8),(1 << 16));
1693 }
1694 }
1695 }
1696 if(c == CHAN_NOT_SPECIFIED) {
1697 /* enable interrupt as BIOS might not */
1698 ChangePciConfig1(0x8a, (a & 0x3f));
1699 // Enable 3rd and 4th channels
1700 if (ChipFlags & SII4CH) {
1701 KdPrint2((PRINT_PREFIX "SII4CH\n"));
1702 AtapiWritePortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0),0x0200, 0x00000002);
1703 }
1704 } else {
1705 chan = &deviceExtension->chan[c];
1706 /* dont block interrupts */
1707 //ChangePciConfig4(0x48, (a & ~0x03c00000));
1708 tmp32 = AtapiReadPortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0),0x48);
1709 AtapiWritePortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0),0x48, (1 << 22) << c);
1710 // flush
1711 tmp32 = AtapiReadPortEx4(NULL, (ULONG)(&deviceExtension->BaseIoAddressSATA_0),0x48);
1712
1713 /* Initialize FIFO PCI bus arbitration */
1714 GetPciConfig1(offsetof(PCI_COMMON_CONFIG, CacheLineSize), tmp8);
1715 if(tmp8) {
1716 KdPrint2((PRINT_PREFIX "SII: CacheLine=%d\n", tmp32));
1717 tmp8 = (tmp8/8)+1;
1718 AtapiWritePort2(chan, IDX_BM_DeviceSpecific1, ((USHORT)tmp8) << 8 | tmp8);
1719 } else {
1720 KdPrint2((PRINT_PREFIX "SII: CacheLine=0 !!!\n"));
1721 }
1722 }
1723 break; }
1724
1725 case SIICMD: {
1726
1727 KdPrint2((PRINT_PREFIX "SII_CMD\n"));
1728 if(c == CHAN_NOT_SPECIFIED) {
1729 /* Setup interrupts. */
1730 SetPciConfig1(0x71, 0x01);
1731
1732 /* GetPciConfig1(0x8a, tmp8);
1733 tmp8 &= ~(0x30);
1734 SetPciConfig1(0x71, tmp8);*/
1735
1736 /* Use MEMORY READ LINE for reads.
1737 * NOTE: Although not mentioned in the PCI0646U specs,
1738 * these bits are write only and won't be read
1739 * back as set or not. The PCI0646U2 specs clarify
1740 * this point.
1741 */
1742 /* tmp8 |= 0x02;
1743 SetPciConfig1(0x71, tmp8);
1744 */
1745 /* Set reasonable active/recovery/address-setup values. */
1746 SetPciConfig1(0x53, 0x40);
1747 SetPciConfig1(0x54, 0x3f);
1748 SetPciConfig1(0x55, 0x40);
1749 SetPciConfig1(0x56, 0x3f);
1750 SetPciConfig1(0x57, 0x1c);
1751 SetPciConfig1(0x58, 0x3f);
1752 SetPciConfig1(0x5b, 0x3f);
1753 }
1754
1755 break; }
1756 }
1757 break;
1758 case ATA_SIS_ID:
1759 if(c == CHAN_NOT_SPECIFIED) {
1760 switch(ChipType) {
1761 case SIS33:
1762 break;
1763 case SIS66:
1764 case SIS100OLD:
1765 ChangePciConfig1(0x52, (a & ~0x04));
1766 break;
1767 case SIS100NEW:
1768 case SIS133OLD:
1769 ChangePciConfig1(0x49, (a & ~0x01));
1770 break;
1771 case SIS133NEW:
1772 ChangePciConfig2(0x50, (a | 0x0008));
1773 ChangePciConfig2(0x52, (a | 0x0008));
1774 break;
1775 case SISSATA:
1776 ChangePciConfig2(0x04, (a & ~0x0400));
1777 }
1778 }
1779 if(ChipType == SIS133NEW) {
1780 USHORT tmp16;
1781 // check 80-pin cable
1782 if(c == CHAN_NOT_SPECIFIED) {
1783 // do nothing
1784 } else {
1785 chan = &deviceExtension->chan[c];
1786 GetPciConfig2(channel ? 0x52 : 0x50, tmp16);
1787 if(tmp16 & 0x8000) {
1788 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1789 }
1790 }
1791 } else {
1792 // check 80-pin cable
1793 if(c == CHAN_NOT_SPECIFIED) {
1794 // do nothing
1795 } else {
1796 chan = &deviceExtension->chan[c];
1797 GetPciConfig1(48, tmp8);
1798 if(tmp8 & (0x10 << channel)) {
1799 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1800 }
1801 }
1802 }
1803 break;
1804 case ATA_VIA_ID:
1805
1806 if(c == CHAN_NOT_SPECIFIED) {
1807 /* prepare for ATA-66 on the 82C686a and 82C596b */
1808 if(ChipFlags & VIACLK) {
1809 ChangePciConfig4(0x50, (a | 0x030b030b));
1810 }
1811 // no init for SATA
1812 if(ChipFlags & UNIATA_SATA) {
1813 /* enable PCI interrupt */
1814 ChangePciConfig2(/*PCIR_COMMAND*/0x04, (a & ~0x0400));
1815 break;
1816 }
1817
1818 /* the southbridge might need the data corruption fix */
1819 if(ChipFlags & VIABUG) {
1820 AtapiViaSouthBridgeFixup(HwDeviceExtension, PCIConfiguration,
1821 SystemIoBusNumber, slotNumber);
1822 }
1823 /* set prefetch, postwrite */
1824 if(ChipType != VIA133) {
1825 ChangePciConfig1(0x41, (a | 0xf0));
1826 }
1827
1828 /* set fifo configuration half'n'half */
1829 ChangePciConfig1(0x43, ((a & ((ChipFlags & VIAPRQ) ? 0x80 : 0x90)) | 0x2a));
1830
1831 /* set status register read retry */
1832 ChangePciConfig1(0x44, (a | 0x08));
1833
1834 /* set DMA read & end-of-sector fifo flush */
1835 ChangePciConfig1(0x46, ((a & 0x0c) | 0xf0));
1836
1837 /* set sector size */
1838 SetPciConfig2(0x60, DEV_BSIZE);
1839 SetPciConfig2(0x68, DEV_BSIZE);
1840 } else {
1841 // check 80-pin cable
1842 chan = &deviceExtension->chan[c];
1843 if(!via_cable80(deviceExtension, channel)) {
1844 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1845 }
1846 }
1847
1848 break;
1849
1850 case ATA_ITE_ID:
1851 // Old chip
1852 if(ChipType == ITE_33)
1853 break;
1854 if(c == CHAN_NOT_SPECIFIED) {
1855 /* set PCI mode and 66Mhz reference clock */
1856 ChangePciConfig1(0x50, a & ~0x83);
1857
1858 /* set default active & recover timings */
1859 SetPciConfig1(0x54, 0x31);
1860 SetPciConfig1(0x56, 0x31);
1861 } else {
1862 // check 80-pin cable
1863 GetPciConfig2(0x40, tmp16);
1864 chan = &deviceExtension->chan[c];
1865 if(!(tmp16 & (channel ? 0x08 : 0x04))) {
1866 chan->MaxTransferMode = min(deviceExtension->MaxTransferMode, ATA_UDMA2);
1867 }
1868 }
1869
1870 break;
1871 default:
1872 if(c != CHAN_NOT_SPECIFIED) {
1873 // We don't know how to check for 80-pin cable on unknown controllers.
1874 // Later we shall check bit in IDENTIFY structure, but it is not reliable way.
1875 // So, leave this flag to use as hint in error recovery procedures
1876 KdPrint2((PRINT_PREFIX "UNIATA_NO80CHK\n"));
1877 deviceExtension->HwFlags |= UNIATA_NO80CHK;
1878 }
1879 break;
1880 }
1881
1882 // In all places separate channels are inited after common controller init
1883 // The only exception is probe. But there we may need info about 40/80 pin and MaxTransferRate
1884 if(CheckCable && !(ChipFlags & (UNIATA_NO80CHK | UNIATA_SATA))) {
1885 for(c=0; c<deviceExtension->NumberChannels; c++) {
1886 AtapiChipInit(HwDeviceExtension, DeviceNumber, c);
1887 }
1888 }
1889
1890 return TRUE;
1891 } // end AtapiChipInit()
1892
1893 VOID
1894 NTAPI
1895 UniataInitMapBM(
1896 IN PHW_DEVICE_EXTENSION deviceExtension,
1897 IN PIDE_BUSMASTER_REGISTERS BaseIoAddressBM_0,
1898 IN BOOLEAN MemIo
1899 )
1900 {
1901 PHW_CHANNEL chan;
1902 ULONG c;
1903 ULONG i;
1904
1905 if(!BaseIoAddressBM_0) {
1906 MemIo = FALSE;
1907 }
1908 for(c=0; c<deviceExtension->NumberChannels; c++) {
1909 chan = &deviceExtension->chan[c];
1910 for (i=0; i<IDX_BM_IO_SZ; i++) {
1911 chan->RegTranslation[IDX_BM_IO+i].Addr = BaseIoAddressBM_0 ? ((ULONG)BaseIoAddressBM_0 + i) : 0;
1912 chan->RegTranslation[IDX_BM_IO+i].MemIo = MemIo;
1913 }
1914 if(BaseIoAddressBM_0) {
1915 BaseIoAddressBM_0++;
1916 }
1917 }
1918 } // end UniataInitMapBM()
1919
1920 VOID
1921 NTAPI
1922 UniataInitMapBase(
1923 IN PHW_CHANNEL chan,
1924 IN PIDE_REGISTERS_1 BaseIoAddress1,
1925 IN PIDE_REGISTERS_2 BaseIoAddress2
1926 )
1927 {
1928 ULONG i;
1929
1930 for (i=0; i<IDX_IO1_SZ; i++) {
1931 chan->RegTranslation[IDX_IO1+i].Addr = BaseIoAddress1 ? ((ULONG)BaseIoAddress1 + i) : 0;
1932 chan->RegTranslation[IDX_IO1+i].MemIo = FALSE;
1933 }
1934 for (i=0; i<IDX_IO2_SZ; i++) {
1935 chan->RegTranslation[IDX_IO2+i].Addr = BaseIoAddress2 ? ((ULONG)BaseIoAddress2 + i) : 0;
1936 chan->RegTranslation[IDX_IO2+i].MemIo = FALSE;
1937 }
1938 UniataInitSyncBaseIO(chan);
1939 } // end UniataInitMapBase()
1940
1941 VOID
1942 NTAPI
1943 UniataInitSyncBaseIO(
1944 IN PHW_CHANNEL chan
1945 )
1946 {
1947 RtlCopyMemory(&chan->RegTranslation[IDX_IO1_o], &chan->RegTranslation[IDX_IO1], IDX_IO1_SZ*sizeof(chan->RegTranslation[0]));
1948 RtlCopyMemory(&chan->RegTranslation[IDX_IO2_o], &chan->RegTranslation[IDX_IO2], IDX_IO2_SZ*sizeof(chan->RegTranslation[0]));
1949 } // end UniataInitSyncBaseIO()