• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /** @file
2   This PEIM will parse the hoblist from fsp and report them into pei core.
3   This file contains the main entrypoint of the PEIM.
4 
5   Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>
6   This program and the accompanying materials
7   are licensed and made available under the terms and conditions of the BSD License
8   which accompanies this distribution.  The full text of the license may be found at
9   http://opensource.org/licenses/bsd-license.php.
10 
11   THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12   WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
13 
14 **/
15 
16 
17 #include <PiPei.h>
18 #include <Library/IoLib.h>
19 #include <Library/SerialPortLib.h>
20 
21 #define PCI_IDX        0xCF8
22 #define PCI_DAT        0xCFC
23 
24 #define PCI_LPC_BASE    (0x8000F800)
25 #define PCI_LPC_REG(x)  (PCI_LPC_BASE + (x))
26 
27 #define PMC_BASE_ADDRESS                  0xFED03000    // PMC Memory Base Address
28 #define R_PCH_LPC_PMC_BASE                        0x44  // PBASE, 32bit, 512 Bytes
29 #define B_PCH_LPC_PMC_BASE_EN                     BIT1  // Enable Bit
30 #define R_PCH_PMC_GEN_PMCON_1                     0x20  // General PM Configuration 1
31 #define B_PCH_PMC_GEN_PMCON_SUS_PWR_FLR           BIT14 // SUS Well Power Failure
32 #define B_PCH_PMC_GEN_PMCON_PWROK_FLR             BIT16 // PWROK Failure
33 
34 #define R_PCH_LPC_UART_CTRL                       0x80  // UART Control
35 #define B_PCH_LPC_UART_CTRL_COM1_EN               BIT0  // COM1 Enable
36 
37 #define ILB_BASE_ADDRESS                  0xFED08000    // ILB Memory Base Address
38 #define R_PCH_ILB_IRQE                            0x88  // IRQ Enable Control
39 
40 #define IO_BASE_ADDRESS                   0xFED0C000    // IO Memory Base Address
41 
42 #define V_PCH_ILB_IRQE_UARTIRQEN_IRQ3             BIT3  // UART IRQ3 Enable
43 #define V_PCH_ILB_IRQE_UARTIRQEN_IRQ4             BIT4  // UART IRQ4 Enable
44 #define PCIEX_BASE_ADDRESS                        0xE0000000
45 #define PCI_EXPRESS_BASE_ADDRESS                  PCIEX_BASE_ADDRESS
46 #define PciD31F0RegBase                           PCIEX_BASE_ADDRESS + (UINT32) (31 << 15)
47 #define SB_RCBA                                   0xfed1c000
48 
49 typedef enum {
50   PchA0         = 0,
51   PchA1         = 1,
52   PchB0         = 2,
53   PchB1         = 3,
54   PchB2         = 4,
55   PchB3         = 5,
56   PchC0         = 6,
57   PchSteppingMax
58 } PCH_STEPPING;
59 
60 #define MmPciAddress( Segment, Bus, Device, Function, Register ) \
61   ( (UINTN)PCI_EXPRESS_BASE_ADDRESS + \
62     (UINTN)(Bus << 20) + \
63     (UINTN)(Device << 15) + \
64     (UINTN)(Function << 12) + \
65     (UINTN)(Register) \
66   )
67 
68 #define DEFAULT_PCI_BUS_NUMBER_PCH  0
69 #define PCI_DEVICE_NUMBER_PCH_LPC                 31
70 #define PCI_FUNCTION_NUMBER_PCH_LPC               0
71 
72 #define R_PCH_LPC_RID_CC                          0x08  // Revision ID & Class Code
73 
74 #define V_PCH_LPC_RID_0                           0x01  // A0 Stepping (17 x 17)
75 #define V_PCH_LPC_RID_1                           0x02  // A0 Stepping (25 x 27)
76 #define V_PCH_LPC_RID_2                           0x03  // A1 Stepping (17 x 17)
77 #define V_PCH_LPC_RID_3                           0x04  // A1 Stepping (25 x 27)
78 #define V_PCH_LPC_RID_4                           0x05  // B0 Stepping (17 x 17)
79 #define V_PCH_LPC_RID_5                           0x06  // B0 Stepping (25 x 27)
80 #define V_PCH_LPC_RID_6                           0x07  // B1 Stepping (17 x 17)
81 #define V_PCH_LPC_RID_7                           0x08  // B1 Stepping (25 x 27)
82 #define V_PCH_LPC_RID_8                           0x09  // B2 Stepping (17 x 17)
83 #define V_PCH_LPC_RID_9                           0x0A  // B2 Stepping (25 x 27)
84 #define V_PCH_LPC_RID_A                           0x0B  // B3 Stepping (17 x 17)
85 #define V_PCH_LPC_RID_B                           0x0C  // B3 Stepping (25 x 27)
86 #define V_PCH_LPC_RID_C                           0x0D  // C0 Stepping (17 x 17)
87 #define V_PCH_LPC_RID_D                           0x0E  // C0 Stepping (25 x 27)
88 
89 /**
90   Return Pch stepping type
91 
92   @param[in] None
93 
94   @retval PCH_STEPPING            Pch stepping type
95 
96 **/
97 PCH_STEPPING
98 EFIAPI
PchStepping(VOID)99 PchStepping (
100   VOID
101   )
102 {
103   UINT8 RevId;
104 
105   RevId = MmioRead8 (
106           MmPciAddress (0,
107             DEFAULT_PCI_BUS_NUMBER_PCH,
108             PCI_DEVICE_NUMBER_PCH_LPC,
109             PCI_FUNCTION_NUMBER_PCH_LPC,
110             R_PCH_LPC_RID_CC)
111           );
112 
113   switch (RevId) {
114     case V_PCH_LPC_RID_0:
115     case V_PCH_LPC_RID_1:
116       return PchA0;
117       break;
118 
119     case V_PCH_LPC_RID_2:
120     case V_PCH_LPC_RID_3:
121       return PchA1;
122       break;
123 
124     case V_PCH_LPC_RID_4:
125     case V_PCH_LPC_RID_5:
126       return PchB0;
127       break;
128 
129     case V_PCH_LPC_RID_6:
130     case V_PCH_LPC_RID_7:
131       return PchB1;
132       break;
133 
134     case V_PCH_LPC_RID_8:
135     case V_PCH_LPC_RID_9:
136       return PchB2;
137       break;
138 
139     case V_PCH_LPC_RID_A:
140     case V_PCH_LPC_RID_B:
141       return PchB3;
142       break;
143 
144     case V_PCH_LPC_RID_C:
145     case V_PCH_LPC_RID_D:
146       return PchC0;
147       break;
148 
149     default:
150       return PchSteppingMax;
151       break;
152 
153   }
154 }
155 
156 /**
157   Enable legacy decoding on ICH6
158 
159  @param[in] none
160 
161  @retval EFI_SUCCESS     Always returns success.
162 
163 **/
164 VOID
EnableInternalUart(VOID)165 EnableInternalUart(
166   VOID
167   )
168 {
169 
170   //
171   // Program and enable PMC Base.
172   //
173   IoWrite32 (PCI_IDX,  PCI_LPC_REG(R_PCH_LPC_PMC_BASE));
174   IoWrite32 (PCI_DAT,  (PMC_BASE_ADDRESS | B_PCH_LPC_PMC_BASE_EN));
175 
176   //
177   // Enable COM1 for debug message output.
178   //
179   MmioAndThenOr32 (PMC_BASE_ADDRESS + R_PCH_PMC_GEN_PMCON_1, (UINT32) (~(B_PCH_PMC_GEN_PMCON_SUS_PWR_FLR + B_PCH_PMC_GEN_PMCON_PWROK_FLR)), BIT24);
180 
181   //
182   // Silicon Steppings
183   //
184   if (PchStepping()>= PchB0)
185     MmioOr8 (ILB_BASE_ADDRESS + R_PCH_ILB_IRQE, (UINT8) V_PCH_ILB_IRQE_UARTIRQEN_IRQ4);
186   else
187     MmioOr8 (ILB_BASE_ADDRESS + R_PCH_ILB_IRQE, (UINT8) V_PCH_ILB_IRQE_UARTIRQEN_IRQ3);
188   MmioAnd32(IO_BASE_ADDRESS + 0x0520, (UINT32)~(0x00000187));
189   MmioOr32 (IO_BASE_ADDRESS + 0x0520, (UINT32)0x81); // UART3_RXD-L
190   MmioAnd32(IO_BASE_ADDRESS + 0x0530, (UINT32)~(0x00000007));
191   MmioOr32 (IO_BASE_ADDRESS + 0x0530, (UINT32)0x1); // UART3_RXD-L
192   MmioOr8 (PciD31F0RegBase + R_PCH_LPC_UART_CTRL, (UINT8) B_PCH_LPC_UART_CTRL_COM1_EN);
193 
194   SerialPortInitialize ();
195   SerialPortWrite ((UINT8 *)"EnableInternalUart!\r\n", sizeof("EnableInternalUart!\r\n") - 1);
196 
197   return  ;
198 }
199