1 /** @file
2
3 Copyright (c) 2004 - 2014, Intel Corporation. All rights reserved.<BR>
4
5
6 This program and the accompanying materials are licensed and made available under
7
8 the terms and conditions of the BSD License that accompanies this distribution.
9
10 The full text of the license may be found at
11
12 http://opensource.org/licenses/bsd-license.php.
13
14
15
16 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
17
18 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
19
20
21
22
23
24 Module Name:
25
26 PchInitPeim.c
27
28 Abstract:
29
30 Do Early PCH platform initialization.
31
32
33 --*/
34
35 #include "PlatformEarlyInit.h"
36 #include "Ppi/PchPlatformPolicy.h"
37 #include "PchRegs.h"
38 #include <Ppi/PchUsbPolicy.h>
39 #include "Ppi/PchInit.h"
40 #include <Library/PcdLib.h>
41
42 EFI_GUID gPchPlatformPolicyPpiGuid = PCH_PLATFORM_POLICY_PPI_GUID;
43
44 #define MC_PMSTS_OFFSET 0xC
45
46 #define DEFAULT_BUS_INFO 0x2020
47
48
49 #define PCI_LPC_BASE (0x8000F800)
50 #define PCI_LPC_REG(x) (PCI_LPC_BASE + (x))
51 #define PCIEX_BASE_ADDRESS 0xE0000000
52 #define PciD31F0RegBase PCIEX_BASE_ADDRESS + (UINT32) (31 << 15)
53
54 VOID
55 PchPolicySetupInit (
56 IN CONST EFI_PEI_SERVICES **PeiServices,
57 IN SYSTEM_CONFIGURATION *SystemConfiguration
58 );
59
60 VOID
61 PchInitInterrupt (
62 IN SYSTEM_CONFIGURATION *SystemConfiguration
63 );
64
65 EFI_STATUS
66 InstallPeiPchUsbPolicy (
67 IN CONST EFI_PEI_SERVICES **PeiServices
ReadCmosBank1Byte(IN UINT8 Address)68 );
69
70 #ifndef __GNUC__
71 #pragma warning (push)
72 #pragma warning (disable : 4245)
73 #pragma warning (pop)
74 #endif
75
76 UINT8
77 ReadCmosBank1Byte (
78 IN UINT8 Address
79 )
WriteCmosBank1Byte(IN UINT8 Address,IN UINT8 Data)80 {
81 UINT8 Data;
82
83 IoWrite8(R_PCH_RTC_EXT_INDEX, Address);
84 Data = IoRead8 (R_PCH_RTC_EXT_TARGET);
85 return Data;
86 }
87
88 VOID
89 WriteCmosBank1Byte (
90 IN UINT8 Address,
91 IN UINT8 Data
92 )
93 {
94 IoWrite8(R_PCH_RTC_EXT_INDEX, Address);
95 IoWrite8(R_PCH_RTC_EXT_TARGET, Data);
96 }
97
98 /**
CheckPowerOffNow(VOID)99 Turn off system if needed.
100
101 @param PeiServices Pointer to PEI Services
102 @param CpuIo Pointer to CPU I/O Protocol
103
104 @retval None.
105
106 **/
107 VOID
108 CheckPowerOffNow (
109 VOID
110 )
111 {
112 UINT16 Pm1Sts;
113
114 //
115 // Read and check the ACPI registers
116 //
117 Pm1Sts = IoRead16 (ACPI_BASE_ADDRESS + R_PCH_ACPI_PM1_STS);
118 if ((Pm1Sts & B_PCH_ACPI_PM1_STS_PWRBTN) == B_PCH_ACPI_PM1_STS_PWRBTN) {
119 IoWrite16 (ACPI_BASE_ADDRESS + R_PCH_ACPI_PM1_STS, B_PCH_ACPI_PM1_STS_PWRBTN);
120 IoWrite16 (ACPI_BASE_ADDRESS + R_PCH_ACPI_PM1_CNT, V_PCH_ACPI_PM1_CNT_S5);
121 IoWrite16 (ACPI_BASE_ADDRESS + R_PCH_ACPI_PM1_CNT, V_PCH_ACPI_PM1_CNT_S5 + B_PCH_ACPI_PM1_CNT_SLP_EN);
122
123 //
124 // Should not return
125 //
126 CpuDeadLoop();
127 }
128 }
129
130 VOID
131 ClearPowerState (
132 IN SYSTEM_CONFIGURATION *SystemConfiguration
133 )
134 {
135 UINT8 Data8;
136 UINT16 Data16;
137 UINT32 Data32;
138
139 //
140 // Check for PowerState option for AC power loss and program the chipset
141 //
142
143 //
144 // Clear PWROK (Set to Clear)
145 //
146 MmioOr32 (PMC_BASE_ADDRESS + R_PCH_PMC_GEN_PMCON_1, B_PCH_PMC_GEN_PMCON_PWROK_FLR);
147
148 //
149 // Clear Power Failure Bit (Set to Clear)
150 //
151 // TODO: Check if it is OK to clear here
152 //
153
154 MmioOr32 (PMC_BASE_ADDRESS + R_PCH_PMC_GEN_PMCON_1, B_PCH_PMC_GEN_PMCON_SUS_PWR_FLR);
155
156 //
157 // Clear the GPE and PM enable
158 //
159 IoWrite16 (ACPI_BASE_ADDRESS + R_PCH_ACPI_PM1_EN, (UINT16) 0x00);
160 IoWrite32 (ACPI_BASE_ADDRESS + R_PCH_ACPI_GPE0a_EN, (UINT32) 0x00);
161
162 //
163 // Halt the TCO timer
164 //
165 Data16 = IoRead16 (ACPI_BASE_ADDRESS + R_PCH_TCO_CNT);
166 Data16 |= B_PCH_TCO_CNT_TMR_HLT;
167 IoWrite16 (ACPI_BASE_ADDRESS + R_PCH_TCO_CNT, Data16);
168
169 //
170 // if NMI_NOW_STS is set
171 // NMI NOW bit is "Write '1' to clear"
172 //
173 Data8 = MmioRead8(ILB_BASE_ADDRESS + R_PCH_ILB_GNMI);
174 if ((Data8 & B_PCH_ILB_GNMI_NMINS) == B_PCH_ILB_GNMI_NMINS) {
175 MmioOr8 (ILB_BASE_ADDRESS + R_PCH_ILB_GNMI, B_PCH_ILB_GNMI_NMIN);
176 }
177
178 //
179 // Before we clear the TO status bit here we need to save the results in a CMOS bit for later use.
180 //
181 Data32 = IoRead32 (ACPI_BASE_ADDRESS + R_PCH_TCO_STS);
182 if ((Data32 & B_PCH_TCO_STS_SECOND_TO) == B_PCH_TCO_STS_SECOND_TO)
183 {
184 #if (defined(HW_WATCHDOG_TIMER_SUPPORT) && (HW_WATCHDOG_TIMER_SUPPORT != 0))
185 WriteCmosBank1Byte (
186 EFI_CMOS_PERFORMANCE_FLAGS,
187 ReadCmosBank1Byte (EFI_CMOS_PERFORMANCE_FLAGS) | B_CMOS_TCO_WDT_RESET
188 );
189 #endif
ClearSmiAndWake(VOID)190 }
191 }
192
193 /*++
194
195 Clear any SMI status or wake status left over from boot.
196
197 **/
198 VOID
199 ClearSmiAndWake (
200 VOID
201 )
202 {
203 UINT16 Pm1Sts;
204 UINT32 Gpe0Sts;
205 UINT32 SmiSts;
206
207 //
208 // Read the ACPI registers
209 //
210 Pm1Sts = IoRead16 (ACPI_BASE_ADDRESS + R_PCH_ACPI_PM1_STS);
211 Gpe0Sts = IoRead32 (ACPI_BASE_ADDRESS + R_PCH_ACPI_GPE0a_STS);
212 SmiSts = IoRead32 (ACPI_BASE_ADDRESS + R_PCH_SMI_STS);
213
214 //
215 // Register Wake up reason for S4. This information is used to notify
216 // WinXp of wake up reason because S4 wake up path doesn't keep SCI.
217 // This is important for Viiv(Quick resume) platform.
218 //
219
220 //
221 // First Clear CMOS S4 Wake up flag.
222 //
223 WriteCmosBank1Byte(CMOS_S4_WAKEUP_FLAG_ADDRESS, 0);
224
225 //
226 // Check wake up reason and set CMOS accordingly. Currently checks
227 // Power button, USB, PS/2.
228 // Note : PS/2 wake up is using GPI13 (IO_PME). This must be changed depending
229 // on board design.
230 //
231 if ((Pm1Sts & B_PCH_ACPI_PM1_STS_PWRBTN) || (Gpe0Sts & (B_PCH_ACPI_GPE0a_STS_CORE_GPIO | B_PCH_ACPI_GPE0a_STS_SUS_GPIO))) {
232 WriteCmosBank1Byte(CMOS_S4_WAKEUP_FLAG_ADDRESS, 1);
233 }
234
235 //
236 // Clear any SMI or wake state from the boot
237 //
238 Pm1Sts = (B_PCH_ACPI_PM1_STS_PRBTNOR | B_PCH_ACPI_PM1_STS_PWRBTN);
239
240 Gpe0Sts |=
241 (
242 B_PCH_ACPI_GPE0a_STS_CORE_GPIO |
243 B_PCH_ACPI_GPE0a_STS_SUS_GPIO |
244 B_PCH_ACPI_GPE0a_STS_PME_B0 |
245 B_PCH_ACPI_GPE0a_STS_BATLOW |
246 B_PCH_ACPI_GPE0a_STS_PCI_EXP |
247 B_PCH_ACPI_GPE0a_STS_GUNIT_SCI |
248 B_PCH_ACPI_GPE0a_STS_PUNIT_SCI |
249 B_PCH_ACPI_GPE0a_STS_SWGPE |
250 B_PCH_ACPI_GPE0a_STS_HOT_PLUG
251 );
252
253 SmiSts |=
254 (
255 B_PCH_SMI_STS_SMBUS |
256 B_PCH_SMI_STS_PERIODIC |
257 B_PCH_SMI_STS_TCO |
258 B_PCH_SMI_STS_SWSMI_TMR |
259 B_PCH_SMI_STS_APM |
260 B_PCH_SMI_STS_ON_SLP_EN |
261 B_PCH_SMI_STS_BIOS
262 );
263
264 //
265 // Write them back
266 //
267 IoWrite16 (ACPI_BASE_ADDRESS + R_PCH_ACPI_PM1_STS, Pm1Sts);
268 IoWrite32 (ACPI_BASE_ADDRESS + R_PCH_ACPI_GPE0a_STS, Gpe0Sts);
269 IoWrite32 (ACPI_BASE_ADDRESS + R_PCH_SMI_STS, SmiSts);
270 }
271
272 /**
273 Issue PCI-E Secondary Bus Reset
PcieSecondaryBusReset(IN CONST EFI_PEI_SERVICES ** PeiServices,IN UINT8 Bus,IN UINT8 Dev,IN UINT8 Fun)274
275 @param Bus Bus number of the bridge
276 @param Dev Devices number of the bridge
277 @param Fun Function number of the bridge
278
279 @retval EFI_SUCCESS
280
281 **/
282 EFI_STATUS
283 PcieSecondaryBusReset (
284 IN CONST EFI_PEI_SERVICES **PeiServices,
285 IN UINT8 Bus,
286 IN UINT8 Dev,
287 IN UINT8 Fun
288 )
289 {
290 EFI_PEI_STALL_PPI *PeiStall;
291 EFI_STATUS Status;
292
293 Status = (**PeiServices).LocatePpi (
294 PeiServices,
295 &gEfiPeiStallPpiGuid,
296 0,
297 NULL,
298 (void **)&PeiStall
299 );
300 ASSERT_EFI_ERROR (Status);
301
302 //
303 // Issue secondary bus reset
304 //
305 MmPci16Or(0, Bus, Dev, Fun, PCI_BRIDGE_CONTROL_REGISTER_OFFSET, EFI_PCI_BRIDGE_CONTROL_RESET_SECONDARY_BUS);
306
307 //
308 // Wait 1ms
309 //
310 PeiStall->Stall (PeiServices, PeiStall, 1000);
311
312
313 //
314 // Clear the reset bit
315 // Note: The PCIe spec suggests 100ms delay between clearing this bit and accessing
316 // the device's config space. Since we will not access the config space until we enter DXE
317 // we don't put delay expressly here.
318 //
319 MmPci16And(0, Bus, Dev, Fun, PCI_BRIDGE_CONTROL_REGISTER_OFFSET, ~(EFI_PCI_BRIDGE_CONTROL_RESET_SECONDARY_BUS));
320
321 return EFI_SUCCESS;
322 }
323
324 /**
325 Provide hard reset PPI service.
326 To generate full hard reset, write 0x0E to ICH RESET_GENERATOR_PORT (0xCF9).
IchReset(IN CONST EFI_PEI_SERVICES ** PeiServices)327
328 @param PeiServices General purpose services available to every PEIM.
329
330 @retval Not return System reset occured.
331 @retval EFI_DEVICE_ERROR Device error, could not reset the system.
332
333 **/
334 EFI_STATUS
335 EFIAPI
336 IchReset (
337 IN CONST EFI_PEI_SERVICES **PeiServices
338 )
339 {
340 IoWrite8 (
341 R_PCH_RST_CNT,
342 V_PCH_RST_CNT_HARDSTARTSTATE
343 );
344
345 IoWrite8 (
346 R_PCH_RST_CNT,
347 V_PCH_RST_CNT_HARDRESET
348 );
349
350 //
351 // System reset occured, should never reach at this line.
352 //
353 ASSERT_EFI_ERROR (EFI_DEVICE_ERROR);
354 CpuDeadLoop();
355
356 return EFI_DEVICE_ERROR;
357 }
358
359 VOID
360 PchPlatformLpcInit (
361 IN CONST EFI_PEI_SERVICES **PeiServices,
362 IN SYSTEM_CONFIGURATION *SystemConfiguration
363 )
364 {
365 EFI_BOOT_MODE BootMode;
366 UINT8 Data8;
367 UINT16 Data16;
368
369 (*PeiServices)->GetBootMode(PeiServices, &BootMode);
370
371 if ((BootMode != BOOT_ON_S3_RESUME)) {
372
373 //
374 // Clear all pending SMI. On S3 clear power button enable so it wll not generate an SMI
375 //
376 ClearSmiAndWake ();
377 }
378
379 ClearPowerState (SystemConfiguration);
380
381 //
382 // Need to set and clear SET bit (RTC_REGB Bit 7) as requested by the ICH EDS
383 // early in POST after each power up directly after coin-cell battery insertion.
384 // This is to avoid the UIP bit (RTC_REGA Bit 7) from stuck at "1".
385 // The UIP bit status may be polled by software (i.e ME FW) during POST.
386 //
387 if (MmioRead8 (PMC_BASE_ADDRESS + R_PCH_PMC_GEN_PMCON_1) & B_PCH_PMC_GEN_PMCON_RTC_PWR_STS) {
388 //
389 // Set and clear SET bit in RTC_REGB
390 //
391 IoWrite8(R_PCH_RTC_INDEX, R_PCH_RTC_REGISTERB);
392 Data8 = IoRead8(R_PCH_RTC_TARGET);
393 Data8 |= B_PCH_RTC_REGISTERB_SET;
394 IoWrite8(R_PCH_RTC_TARGET, Data8);
395
396 IoWrite8(R_PCH_RTC_INDEX, R_PCH_RTC_REGISTERB);
397 Data8 &= (~B_PCH_RTC_REGISTERB_SET);
398 IoWrite8(R_PCH_RTC_TARGET, Data8);
399
400 //
401 // Clear the UIP bit in RTC_REGA
402 //
403 IoWrite8(R_PCH_RTC_INDEX, R_PCH_RTC_REGISTERA);
404 IoWrite8(R_PCH_RTC_TARGET, 0x00);
405 }
406
407 //
408 // Disable SERR NMI and IOCHK# NMI in port 61
409 //
410 Data8 = IoRead8 (R_PCH_NMI_SC);
411 IoWrite8(R_PCH_NMI_SC, (UINT8) (Data8 | B_PCH_NMI_SC_PCI_SERR_EN | B_PCH_NMI_SC_IOCHK_NMI_EN));
412
413 //
414 // Enable Bus Master, I/O, Mem, and SERR on LPC bridge
415 //
416 Data16 = PchLpcPciCfg16 (R_PCH_LPC_COMMAND);
417 MmioWrite16 (
418 MmPciAddress (0,
419 DEFAULT_PCI_BUS_NUMBER_PCH,
420 PCI_DEVICE_NUMBER_PCH_LPC,
421 PCI_FUNCTION_NUMBER_PCH_LPC,
422 R_PCH_LPC_COMMAND
423 ),
424 (Data16 |
425 B_PCH_LPC_COMMAND_IOSE |
426 B_PCH_LPC_COMMAND_MSE |
427 B_PCH_LPC_COMMAND_BME |
428 B_PCH_LPC_COMMAND_SERR_EN)
429 );
430
431 //
432 // Set Stretch S4 to 1-2s per marketing request.
433 // Note: This register is powered by RTC well.
434 //
435 MmioAndThenOr8 (
436 PMC_BASE_ADDRESS + R_PCH_PMC_GEN_PMCON_1 ,
UARTInit(IN SYSTEM_CONFIGURATION * SystemConfiguration)437 (UINT8) (~B_PCH_PMC_GEN_PMCON_SLP_S4_MAW),
438 (UINT8) (B_PCH_PMC_GEN_PMCON_SLP_S4_ASE | V_PCH_PMC_GEN_PMCON_SLP_S4_MAW_4S)
439 );
440
441 }
442
443 #define V_PCH_ILB_IRQE_UARTIRQEN_IRQ3 BIT3 // UART IRQ3 Enable
444
445 VOID
446 UARTInit (
447 IN SYSTEM_CONFIGURATION *SystemConfiguration
448 )
449 {
450 if (0) { // for fix cr4 issue
451 //
452 // Program and enable PMC Base.
453 //
454 IoWrite32 (0xCF8, PCI_LPC_REG(R_PCH_LPC_PMC_BASE));
455 IoWrite32 (0xCFC, (PMC_BASE_ADDRESS | B_PCH_LPC_PMC_BASE_EN));
456
457 if( (SystemConfiguration->PcuUart1 == 1) &&
458 (SystemConfiguration->LpssHsuart0Enabled == 0)){
459 //
460 // Enable COM1 for debug message output.
461 //
462 MmioOr32 (PMC_BASE_ADDRESS + R_PCH_PMC_GEN_PMCON_1, BIT24);
463
464 //
465 //Enable internal UART3 port(COM1)
466 //
467 MmioOr8 (ILB_BASE_ADDRESS + R_PCH_ILB_IRQE, (UINT8) V_PCH_ILB_IRQE_UARTIRQEN_IRQ3);
468 MmioOr32 (IO_BASE_ADDRESS + 0x0520, 0x01); // UART3_RXD-L
469 MmioOr32 (IO_BASE_ADDRESS + 0x0530, 0x01); // UART3_TXD-0
470 MmioOr8 (PciD31F0RegBase + R_PCH_LPC_UART_CTRL, (UINT8) B_PCH_LPC_UART_CTRL_COM1_EN);
471 } else {
472 //
473 //Disable UART3(COM1)
474 //
475 MmioAnd8 (ILB_BASE_ADDRESS + R_PCH_ILB_IRQE, (UINT8) ~V_PCH_ILB_IRQE_UARTIRQEN_IRQ3);
476 MmioAnd32 (IO_BASE_ADDRESS + 0x0520, ~(UINT32)0x07);
477 MmioAnd32 (IO_BASE_ADDRESS + 0x0530, ~(UINT32)0x07);
478 MmioAnd8 (PciD31F0RegBase + R_PCH_LPC_UART_CTRL, (UINT8) ~B_PCH_LPC_UART_CTRL_COM1_EN);
479
480
481 if (SystemConfiguration->LpssHsuart0Enabled == 1){
482 //
483 //Valleyview BIOS Specification Vol2,17.2
484 //LPSS_UART1 �C set each pad PAD_CONF0.Func_Pin_Mux to function 1:
485 //
486 MmioAnd8 (IO_BASE_ADDRESS + 0x0090, (UINT8)~0x07);
487 MmioOr8 (IO_BASE_ADDRESS + 0x0090, 0x01);
488 MmioAnd8 (IO_BASE_ADDRESS + 0x00D0, (UINT8)~0x07);
489 MmioOr8 (IO_BASE_ADDRESS + 0x00D0, 0x01);
490
491 }
492 }
493
494
495 DEBUG ((EFI_D_ERROR, "EnableInternalUart\n"));
496 } else {
497 //
498 // If SIO UART interface selected
499 //Disable internal UART port(COM1)
500 //
501 if (0) {; // For fix CR4 issue
502 MmioAnd8 (ILB_BASE_ADDRESS + R_PCH_ILB_IRQE, (UINT8) ~V_PCH_ILB_IRQE_UARTIRQEN_IRQ3);
IchRcrbInit(IN CONST EFI_PEI_SERVICES ** PeiServices,IN SYSTEM_CONFIGURATION * SystemConfiguration)503 MmioAnd8 (IO_BASE_ADDRESS + 0x0090, (UINT8)~0x07);
504 MmioAnd8 (IO_BASE_ADDRESS + 0x00D0, (UINT8)~0x07);
505 MmioAnd8 (PciD31F0RegBase + R_PCH_LPC_UART_CTRL, (UINT8) ~B_PCH_LPC_UART_CTRL_COM1_EN);
506
507 }
508 }
509 }
510
511 VOID
512 IchRcrbInit (
513 IN CONST EFI_PEI_SERVICES **PeiServices,
514 IN SYSTEM_CONFIGURATION *SystemConfiguration
515 )
516 {
517 EFI_BOOT_MODE BootMode;
518
519 (*PeiServices)->GetBootMode(PeiServices, &BootMode);
520
521 //
522 // If not recovery or flash update boot path. set the BIOS interface lock down bit.
523 // It locks the top swap bit and BIOS boot strap bits from being changed.
524 //
525 if ((BootMode != BOOT_IN_RECOVERY_MODE) && (BootMode != BOOT_ON_FLASH_UPDATE)) {
526 MmioOr8 (RCBA_BASE_ADDRESS + R_PCH_RCRB_GCS, B_PCH_RCRB_GCS_BILD);
527 }
528
529 //
530 // Disable the Watchdog timer expiration from causing a system reset
531 //
532 MmioOr8 (PMC_BASE_ADDRESS + R_PCH_PMC_PM_CFG, B_PCH_PMC_PM_CFG_NO_REBOOT);
533
534 //
535 // Initial RCBA according to the PeiRCBA table
536 //
537 if ((BootMode == BOOT_ON_S3_RESUME)) {
538 //
539 // We are resuming from S3
540 // Enable HPET if enabled in Setup
541 // ICH Config register Offset 0x3404 bit 7 (Enable) = 1,
542 // Bit 1:0 (Mem I/O address) = 0 (0xFED00000)
PlatformPchInit(IN SYSTEM_CONFIGURATION * SystemConfiguration,IN CONST EFI_PEI_SERVICES ** PeiServices,IN UINT16 PlatformType)543 //
544 MmioOr8 (R_PCH_PCH_HPET + R_PCH_PCH_HPET_GCFG, B_PCH_PCH_HPET_GCFG_EN);
545
546 }
547
548 }
549
550
551 EFI_STATUS
552 PlatformPchInit (
553 IN SYSTEM_CONFIGURATION *SystemConfiguration,
554 IN CONST EFI_PEI_SERVICES **PeiServices,
555 IN UINT16 PlatformType
556 )
557 {
558 EFI_STATUS Status;
559 EFI_BOOT_MODE BootMode;
560
561 Status = PeiServicesGetBootMode (&BootMode);
562 ASSERT_EFI_ERROR (Status);
563
564 IchRcrbInit (PeiServices, SystemConfiguration);
565
566 if (BootMode == BOOT_IN_RECOVERY_MODE) {
567 InstallPeiPchUsbPolicy(PeiServices);
568 }
569
570 //
571 // PCH Policy Initialization based on Setup variable.
572 //
573 PchPolicySetupInit (PeiServices, SystemConfiguration);
574
575 UARTInit(SystemConfiguration);
576
577 PchPlatformLpcInit (PeiServices, SystemConfiguration);
578
579 return EFI_SUCCESS;
580 }
581
IsA16Inverted()582 /**
583
584 Returns the state of A16 inversion
585
586 @retval TRUE A16 is inverted
587 @retval FALSE A16 is not inverted
588
589 **/
590 BOOLEAN
591 IsA16Inverted (
592 )
593 {
594 UINT8 Data;
595 Data = MmioRead8 (RCBA_BASE_ADDRESS + R_PCH_RCRB_GCS);
596 return (Data & B_PCH_RCRB_GCS_TS) ? TRUE : FALSE;
597 }
598
599 VOID
600 PchPolicySetupInit (
601 IN CONST EFI_PEI_SERVICES **PeiServices,
602 IN SYSTEM_CONFIGURATION *SystemConfiguration
603 )
604 {
605 EFI_STATUS Status;
606 EFI_PEI_PPI_DESCRIPTOR *PchPlatformPolicyPpiDesc;
607 PCH_PLATFORM_POLICY_PPI *PchPlatformPolicyPpi;
608 PCH_HPET_CONFIG *HpetConfig;
609 PCH_PCIE_CONFIG *PcieConfig;
610 UINT8 Index;
611 PCH_IOAPIC_CONFIG *IoApicConfig;
612 PCH_LPSS_CONFIG *LpssConfig;
613 UINT32 SpiHsfsReg;
614 UINT32 SpiFdodReg;
615
616 //
617 // Disable codec ALC-262
618 //
619 UINT32 IoBase;
620
621 //
622 // Install Pch Platform Policy PPI. As we depend on Pch Init PPI so we are executed after
623 // PchInit PEIM. Thus we can insure PCH Initialization is performed when we install the Pch Platform Policy PPI,
624 // as PchInit PEIM registered a notification function on our policy PPI.
625 //
626 // --cr-- For better code structure / modularity, we should use a notification function on Pch Init PPI to perform
627 // actions that depend on PchInit PEIM's initialization.
628 //
629 //Todo: confirm if we need update to PCH_PLATFORM_POLICY_PPI_REVISION_5
630 //
631 DEBUG ((EFI_D_ERROR, "PchPolicySetupInit() - Start\n"));
632
633 Status = (*PeiServices)->AllocatePool (PeiServices, sizeof (EFI_PEI_PPI_DESCRIPTOR), (void **)&PchPlatformPolicyPpiDesc);
634 ASSERT_EFI_ERROR (Status);
635
636 Status = (*PeiServices)->AllocatePool (PeiServices, sizeof (PCH_PLATFORM_POLICY_PPI), (void **)&PchPlatformPolicyPpi);
637 ASSERT_EFI_ERROR (Status);
638
639 Status = (*PeiServices)->AllocatePool (PeiServices, sizeof (PCH_HPET_CONFIG), (void **)&HpetConfig);
640 ASSERT_EFI_ERROR (Status);
641
642 Status = (*PeiServices)->AllocatePool (PeiServices, sizeof (PCH_PCIE_CONFIG), (void **)&PcieConfig);
643 ASSERT_EFI_ERROR (Status);
644
645 Status = (*PeiServices)->AllocatePool (PeiServices, sizeof (PCH_IOAPIC_CONFIG), (void **)&IoApicConfig);
646 ASSERT_EFI_ERROR (Status);
647
648 Status = (*PeiServices)->AllocatePool (PeiServices, sizeof (PCH_LPSS_CONFIG), (void **)&LpssConfig);
649 ASSERT_EFI_ERROR (Status);
650
651 PchPlatformPolicyPpi->Revision = PCH_PLATFORM_POLICY_PPI_REVISION_1;
652 PchPlatformPolicyPpi->BusNumber = DEFAULT_PCI_BUS_NUMBER_PCH;
653 PchPlatformPolicyPpi->SpiBase = SPI_BASE_ADDRESS;
654 PchPlatformPolicyPpi->PmcBase = PMC_BASE_ADDRESS;
655 PchPlatformPolicyPpi->IoBase = IO_BASE_ADDRESS;
656 PchPlatformPolicyPpi->IlbBase = ILB_BASE_ADDRESS;
657 PchPlatformPolicyPpi->PUnitBase = PUNIT_BASE_ADDRESS;
658 PchPlatformPolicyPpi->MphyBase = MPHY_BASE_ADDRESS;
659 PchPlatformPolicyPpi->Rcba = RCBA_BASE_ADDRESS;
660 PchPlatformPolicyPpi->AcpiBase = ACPI_BASE_ADDRESS;
661 PchPlatformPolicyPpi->GpioBase = GPIO_BASE_ADDRESS;
662 PchPlatformPolicyPpi->SataMode = SystemConfiguration->SataType;
663 PchPlatformPolicyPpi->EnableRmh = SystemConfiguration->PchUsbRmh;
664
665 PchPlatformPolicyPpi->EhciPllCfgEnable = SystemConfiguration->EhciPllCfgEnable;
666
667
668 PchPlatformPolicyPpi->HpetConfig = HpetConfig;
669 PchPlatformPolicyPpi->PcieConfig = PcieConfig;
670 PchPlatformPolicyPpi->IoApicConfig = IoApicConfig;
671
672 PchPlatformPolicyPpi->HpetConfig->Enable = SystemConfiguration->Hpet;
673 PchPlatformPolicyPpi->HpetConfig->Base = HPET_BASE_ADDRESS;
674 PchPlatformPolicyPpi->IoApicConfig->IoApicId = 0x01;
675
676 //
677 // Set LPSS configuration according to setup value.
678 //
679 PchPlatformPolicyPpi->LpssConfig->LpssPciModeEnabled = SystemConfiguration->LpssPciModeEnabled;
680
681 PchPlatformPolicyPpi->LpssConfig->Dma1Enabled = SystemConfiguration->LpssDma1Enabled;
682 PchPlatformPolicyPpi->LpssConfig->I2C0Enabled = SystemConfiguration->LpssI2C0Enabled;
683 PchPlatformPolicyPpi->LpssConfig->I2C1Enabled = SystemConfiguration->LpssI2C1Enabled;
684 PchPlatformPolicyPpi->LpssConfig->I2C2Enabled = SystemConfiguration->LpssI2C2Enabled;
685 PchPlatformPolicyPpi->LpssConfig->I2C3Enabled = SystemConfiguration->LpssI2C3Enabled;
686 PchPlatformPolicyPpi->LpssConfig->I2C4Enabled = SystemConfiguration->LpssI2C4Enabled;
687 PchPlatformPolicyPpi->LpssConfig->I2C5Enabled = SystemConfiguration->LpssI2C5Enabled;
688 PchPlatformPolicyPpi->LpssConfig->I2C6Enabled = SystemConfiguration->LpssI2C6Enabled;
689
690 PchPlatformPolicyPpi->LpssConfig->Dma0Enabled = SystemConfiguration->LpssDma0Enabled;;
691 PchPlatformPolicyPpi->LpssConfig->Pwm0Enabled = SystemConfiguration->LpssPwm0Enabled;
692 PchPlatformPolicyPpi->LpssConfig->Pwm1Enabled = SystemConfiguration->LpssPwm1Enabled;
693 PchPlatformPolicyPpi->LpssConfig->Hsuart0Enabled = SystemConfiguration->LpssHsuart0Enabled;
694 PchPlatformPolicyPpi->LpssConfig->Hsuart1Enabled = SystemConfiguration->LpssHsuart1Enabled;
695 PchPlatformPolicyPpi->LpssConfig->SpiEnabled = SystemConfiguration->LpssSpiEnabled;
696
697
698 for (Index = 0; Index < PCH_PCIE_MAX_ROOT_PORTS; Index++) {
699 PchPlatformPolicyPpi->PcieConfig->PcieSpeed[Index] = SystemConfiguration->PcieRootPortSpeed[Index];
700 }
701
702 SpiHsfsReg = MmioRead32 (SPI_BASE_ADDRESS + R_PCH_SPI_HSFS);
703 if ((SpiHsfsReg & B_PCH_SPI_HSFS_FDV) == B_PCH_SPI_HSFS_FDV) {
704 MmioWrite32 (SPI_BASE_ADDRESS + R_PCH_SPI_FDOC, V_PCH_SPI_FDOC_FDSS_FSDM);
705 SpiFdodReg = MmioRead32 (SPI_BASE_ADDRESS + R_PCH_SPI_FDOD);
706 if (SpiFdodReg == V_PCH_SPI_FDBAR_FLVALSIG) {
707 }
708 //
709 // Disable codec ALC-262
710 //
711 if (SystemConfiguration->DisableCodec262 == 1) {
712 IoBase = MmioRead32 (MmPciAddress (0,
713 PchPlatformPolicyPpi->BusNumber,
714 PCI_DEVICE_NUMBER_PCH_LPC,
715 PCI_FUNCTION_NUMBER_PCH_LPC,
716 0
717 ) + R_PCH_LPC_IO_BASE) & B_PCH_LPC_IO_BASE_BAR;
718 MmioAnd32 ((UINTN) (IoBase + 0x270), (UINT32) (~0x07));
719 }
720 }
721
722 PchPlatformPolicyPpiDesc->Flags = EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST;
723 PchPlatformPolicyPpiDesc->Guid = &gPchPlatformPolicyPpiGuid;
724 PchPlatformPolicyPpiDesc->Ppi = PchPlatformPolicyPpi;
725
726 //
727 // Install PCH Platform Policy PPI
728 //
729 Status = (**PeiServices).InstallPpi (
InstallPeiPchUsbPolicy(IN CONST EFI_PEI_SERVICES ** PeiServices)730 PeiServices,
731 PchPlatformPolicyPpiDesc
732 );
733 ASSERT_EFI_ERROR (Status);
734
735 DEBUG ((EFI_D_ERROR, "PchPolicySetupInit() - End\n"));
736 }
737
738 EFI_STATUS
739 InstallPeiPchUsbPolicy (
740 IN CONST EFI_PEI_SERVICES **PeiServices
741 )
742 {
743 EFI_STATUS Status = EFI_SUCCESS;
744
745 EFI_PEI_PPI_DESCRIPTOR *PeiPchUsbPolicyPpiDesc;
746 PCH_USB_POLICY_PPI *PeiPchUsbPolicyPpi;
747 PCH_USB_CONFIG *UsbConfig;
748
749 DEBUG ((EFI_D_INFO, "InstallPeiPchUsbPolicy...\n"));
750
751 //
752 // Allocate descriptor and PPI structures. Since these are dynamically updated
753 // we cannot do a global variable PPI.
754 //
755 Status = (*PeiServices)->AllocatePool (PeiServices, sizeof (EFI_PEI_PPI_DESCRIPTOR), (void **)&PeiPchUsbPolicyPpiDesc);
756
757
758 Status = (*PeiServices)->AllocatePool (PeiServices, sizeof (PCH_USB_POLICY_PPI), (void **)&PeiPchUsbPolicyPpi);
759
760
761
762 Status = (*PeiServices)->AllocatePool (PeiServices, sizeof (PCH_USB_CONFIG), (void **)&UsbConfig);
763
764
765 //
766 // Initiate PCH USB policy.
767 //
768 PeiPchUsbPolicyPpi->Revision = PCH_USB_POLICY_PPI_REVISION_1;
769 UsbConfig->Usb20Settings[0].Enable = PCH_DEVICE_ENABLE;
770 UsbConfig->UsbPerPortCtl = PCH_DEVICE_DISABLE;
771 UsbConfig->Ehci1Usbr = PCH_DEVICE_DISABLE;
772
773 UsbConfig->Usb20OverCurrentPins[0] = PchUsbOverCurrentPin0;
774
775 UsbConfig->Usb20OverCurrentPins[1] = PchUsbOverCurrentPin0;
776
777 UsbConfig->Usb20OverCurrentPins[2] = PchUsbOverCurrentPin1;
778
779 UsbConfig->Usb20OverCurrentPins[3] = PchUsbOverCurrentPin1;
780
781
782 //
783 // Enable USB Topology control and program the topology setting for every USB port
784 // See Platform Design Guide for description of topologies
785 //
786 //
787 // Port 0: ~10.9", Port 1: ~10.1", Port 2: ~11.2", Port 3: ~11.5", Port 4: ~3.7", Port 5: ~2.7", Port 6: ~4.1"
788 // Port 7: ~4.5", Port 8: ~10.7", Port 9: ~10.5", Port 10: ~4.2", Port 11: ~4.3", Port 12: ~3.1", Port 13: ~2.9"
789 //
790
791 //
792 // Port 0: ~3.5", Port 1: ~4.1", Port 2: ~4.6", Port 3: ~4.6", Port 4: ~12.5", Port 5: ~12", Port 6: ~5.1"
793 // Port 7: ~5.1", Port 8: ~4.1", Port 9: ~4.1", Port 10: ~14.5", Port 11: ~12.8", Port 12: ~12.9", Port 13: ~14.6"
794 //
795 UsbConfig->Usb20PortLength[0] = 0x53;
796 UsbConfig->Usb20PortLength[1] = 0x49;
797 UsbConfig->Usb20PortLength[2] = 0x47;
798 UsbConfig->Usb20PortLength[3] = 0x80;
799
800 PeiPchUsbPolicyPpi->Mode = EHCI_MODE;
801
802 PeiPchUsbPolicyPpi->EhciMemBaseAddr = PcdGet32(PcdPeiIchEhciControllerMemoryBaseAddress);
803
804 PeiPchUsbPolicyPpi->EhciMemLength = (UINT32) 0x400 * PchEhciControllerMax;
805
806 PeiPchUsbPolicyPpi->XhciMemBaseAddr = 0;
807
808 PeiPchUsbPolicyPpi->UsbConfig = UsbConfig;
809
810 PeiPchUsbPolicyPpiDesc->Flags = EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST;
811
812 PeiPchUsbPolicyPpiDesc->Guid = &gPchUsbPolicyPpiGuid;
813
814 PeiPchUsbPolicyPpiDesc->Ppi = PeiPchUsbPolicyPpi;
815
816 //
817 // Install PCH USB Policy PPI
818 //
819 Status = (**PeiServices).InstallPpi (PeiServices, PeiPchUsbPolicyPpiDesc);
820
821 return Status;
822 }
823