File: | home/coreboot/node-root/workspace/coreboot_scanbuild/3rdparty/stm/Stm/StmPkg/Core/Runtime/PeApicHandler.c |
Warning: | line 100, column 3 Value stored to 'high' is never read |
Press '?' to see keyboard shortcuts
Keyboard shortcuts:
1 | /** @file |
2 | |
3 | APIC Handler |
4 | |
5 | This program and the accompanying materials |
6 | are licensed and made available under the terms and conditions of the BSD License |
7 | which accompanies this distribution. The full text of the license may be found at |
8 | http://opensource.org/licenses/bsd-license.php. |
9 | |
10 | THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, |
11 | WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. |
12 | |
13 | **/ |
14 | |
15 | #include "StmRuntime.h" |
16 | #include "PeStm.h" |
17 | |
18 | extern PE_SMI_CONTROL PeSmiControl; |
19 | |
20 | |
21 | // function to signal to the PE VM that it needs to handle a SMI |
22 | |
23 | #define ICR_LOW0x300 0x300 |
24 | #define ICR_HIGH0x310 0x310 |
25 | #define APIC_REG(offset)(*(UINTN *)(apicAddress + offset)) (*(UINTN *)(apicAddress + offset)) |
26 | |
27 | static UINTN apicAddress; |
28 | |
29 | #define APIC_EN1 << 11 1 << 11 |
30 | #define APIC_EXTD1 << 10 1 << 10 |
31 | |
32 | #define LOCAL_APIC_DISABLED0 0 |
33 | #define APIC_INVALID1 << 10 APIC_EXTD1 << 10 |
34 | |
35 | // apic modes |
36 | #define xAPIC_MODE1 << 11 APIC_EN1 << 11 |
37 | #define x2APIC_MODE1 << 11|1 << 10 APIC_EN1 << 11|APIC_EXTD1 << 10 |
38 | |
39 | #ifndef __writemsr |
40 | static __inline__ __attribute__((always_inline)) void __writemsr (UINT32 msr, UINT64 Value) |
41 | { |
42 | __asm__ __volatile__ ( |
43 | "wrmsr" |
44 | : |
45 | : "c" (msr), "A" (Value) |
46 | ); |
47 | } |
48 | #endif |
49 | |
50 | // from LocalApic.h |
51 | |
52 | // lower half of Interrupt Command Register (ICR) |
53 | |
54 | typedef union |
55 | { |
56 | struct |
57 | { |
58 | UINT32 Vector:8; // the vector number of the interrupt being sent |
59 | UINT32 DeliveryMode:3; // Specifies the type of IPI being sent |
60 | UINT32 DestinationMode:1; // 0: physical destination mode, 1: logical destination mode |
61 | UINT32 DeliveryStatus:1; // Indicates the IPI delivery status. Reserved in x2APIC mode |
62 | UINT32 Reserved0:1; // Reserved |
63 | UINT32 Level:1; // 0 for the INIT level de-assert delivery mode. Otherwise 1 |
64 | UINT32 TriggerMode:1; // 0: edge, 1: level when using the INIT level de-assert delivery mode |
65 | UINT32 Reserved1:2; // Reserved |
66 | UINT32 DestinationShorthand:2; // A shorthand notation to specify the destination of the message |
67 | UINT32 Reserved2:12; // Reserved |
68 | } Bits; |
69 | UINT32 Uint32; |
70 | } LOCAL_APIC_ICR_LOW; |
71 | |
72 | #define LOCAL_APIC_DELIVERY_MODE_SMI2 2 |
73 | #define LOCAL_APIC_DESTINATION_SHORTHAND_ALL_EXCLUDING_SELF3 3 |
74 | |
75 | void SignalPeVm(UINT32 CpuIndex) |
76 | { |
77 | UINT32 low, high; |
78 | UINT64 ApicMsr; |
79 | // UINT32 mine = 0; |
80 | |
81 | #ifdef SHOWSMI |
82 | if(CpuIndex == 0) |
83 | { |
84 | UINT16 pmbase = get_pmbase(); |
85 | DEBUG((EFI_D_DEBUG,do { if (DebugPrintEnabled ()) { DebugPrint (EFI_D_DEBUG, " %ld SignalPeVm ****SMI*** smi_en: %x smi_sts: %x\n" , CpuIndex, IoRead32(pmbase + SMI_EN), IoRead32(pmbase + SMI_STS )); } } while (((BOOLEAN)(0==1))) |
86 | " %ld SignalPeVm ****SMI*** smi_en: %x smi_sts: %x\n",do { if (DebugPrintEnabled ()) { DebugPrint (EFI_D_DEBUG, " %ld SignalPeVm ****SMI*** smi_en: %x smi_sts: %x\n" , CpuIndex, IoRead32(pmbase + SMI_EN), IoRead32(pmbase + SMI_STS )); } } while (((BOOLEAN)(0==1))) |
87 | CpuIndex,do { if (DebugPrintEnabled ()) { DebugPrint (EFI_D_DEBUG, " %ld SignalPeVm ****SMI*** smi_en: %x smi_sts: %x\n" , CpuIndex, IoRead32(pmbase + SMI_EN), IoRead32(pmbase + SMI_STS )); } } while (((BOOLEAN)(0==1))) |
88 | IoRead32(pmbase + SMI_EN),do { if (DebugPrintEnabled ()) { DebugPrint (EFI_D_DEBUG, " %ld SignalPeVm ****SMI*** smi_en: %x smi_sts: %x\n" , CpuIndex, IoRead32(pmbase + SMI_EN), IoRead32(pmbase + SMI_STS )); } } while (((BOOLEAN)(0==1))) |
89 | IoRead32(pmbase + SMI_STS)))do { if (DebugPrintEnabled ()) { DebugPrint (EFI_D_DEBUG, " %ld SignalPeVm ****SMI*** smi_en: %x smi_sts: %x\n" , CpuIndex, IoRead32(pmbase + SMI_EN), IoRead32(pmbase + SMI_STS )); } } while (((BOOLEAN)(0==1))); |
90 | } |
91 | #endif |
92 | |
93 | if((PeSmiControl.PeExec == 1) && (InterlockedCompareExchange32(&PeSmiControl.PeNmiBreak, 0, 1) == 0)) |
94 | { |
95 | ApicMsr = AsmReadMsr64 (IA32_APIC_BASE_MSR_INDEX0x1B); |
96 | |
97 | apicAddress = (UINTN)(ApicMsr & 0xffffff000); // assume the default for now |
98 | |
99 | low = APIC_REG(ICR_LOW)(*(UINTN *)(apicAddress + 0x300)) & 0xFFF32000; |
100 | high = APIC_REG(ICR_HIGH)(*(UINTN *)(apicAddress + 0x310)) & 0x00FFFFFF; |
Value stored to 'high' is never read | |
101 | |
102 | //high |= (PE_APIC_ID << 24); // put the destination apic ID into the upper eight bits |
103 | high = PeSmiControl.PeApicId << 24; |
104 | //low |= 0x4400; // bits: (8-10) NMI, (14) asset trigger mode |
105 | low = 0x400; |
106 | |
107 | switch (ApicMsr & (APIC_EN1 << 11|APIC_EXTD1 << 10)) |
108 | { |
109 | case xAPIC_MODE1 << 11: |
110 | APIC_REG(ICR_HIGH)(*(UINTN *)(apicAddress + 0x310)) = high; // write high before low |
111 | APIC_REG(ICR_LOW)(*(UINTN *)(apicAddress + 0x300)) = low; // because writing to low triggers the IPI |
112 | break; |
113 | |
114 | case x2APIC_MODE1 << 11|1 << 10: |
115 | // x2APIC uses MSR's |
116 | __writemsr(0x800 + 0x30, low |((UINT64)PeSmiControl.PeApicId << 32)); |
117 | break; |
118 | |
119 | default: |
120 | DEBUG((EFI_D_ERROR, " %ld SignalPeVm - APIC mode invalid or APIC disabled\n", CpuIndex))do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, " %ld SignalPeVm - APIC mode invalid or APIC disabled\n" , CpuIndex); } } while (((BOOLEAN)(0==1))); |
121 | } |
122 | DEBUG((EFI_D_ERROR, "%ld SignalPeVm - Sent NMI to ApicId: %ld CpuIndex: %ld command: high: %08lx low: %08lx APIC_MSR: %p\n",do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, "%ld SignalPeVm - Sent NMI to ApicId: %ld CpuIndex: %ld command: high: %08lx low: %08lx APIC_MSR: %p\n" , CpuIndex, PeSmiControl.PeApicId, PeSmiControl.PeCpuIndex, high , low, ApicMsr); } } while (((BOOLEAN)(0==1))) |
123 | CpuIndex,do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, "%ld SignalPeVm - Sent NMI to ApicId: %ld CpuIndex: %ld command: high: %08lx low: %08lx APIC_MSR: %p\n" , CpuIndex, PeSmiControl.PeApicId, PeSmiControl.PeCpuIndex, high , low, ApicMsr); } } while (((BOOLEAN)(0==1))) |
124 | PeSmiControl.PeApicId,do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, "%ld SignalPeVm - Sent NMI to ApicId: %ld CpuIndex: %ld command: high: %08lx low: %08lx APIC_MSR: %p\n" , CpuIndex, PeSmiControl.PeApicId, PeSmiControl.PeCpuIndex, high , low, ApicMsr); } } while (((BOOLEAN)(0==1))) |
125 | PeSmiControl.PeCpuIndex,do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, "%ld SignalPeVm - Sent NMI to ApicId: %ld CpuIndex: %ld command: high: %08lx low: %08lx APIC_MSR: %p\n" , CpuIndex, PeSmiControl.PeApicId, PeSmiControl.PeCpuIndex, high , low, ApicMsr); } } while (((BOOLEAN)(0==1))) |
126 | high,do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, "%ld SignalPeVm - Sent NMI to ApicId: %ld CpuIndex: %ld command: high: %08lx low: %08lx APIC_MSR: %p\n" , CpuIndex, PeSmiControl.PeApicId, PeSmiControl.PeCpuIndex, high , low, ApicMsr); } } while (((BOOLEAN)(0==1))) |
127 | low,do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, "%ld SignalPeVm - Sent NMI to ApicId: %ld CpuIndex: %ld command: high: %08lx low: %08lx APIC_MSR: %p\n" , CpuIndex, PeSmiControl.PeApicId, PeSmiControl.PeCpuIndex, high , low, ApicMsr); } } while (((BOOLEAN)(0==1))) |
128 | ApicMsr))do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, "%ld SignalPeVm - Sent NMI to ApicId: %ld CpuIndex: %ld command: high: %08lx low: %08lx APIC_MSR: %p\n" , CpuIndex, PeSmiControl.PeApicId, PeSmiControl.PeCpuIndex, high , low, ApicMsr); } } while (((BOOLEAN)(0==1))); |
129 | } |
130 | #ifdef SMIVMPE |
131 | else |
132 | { |
133 | if(PeSmiControl.PeExec == 1) |
134 | { |
135 | DEBUG((EFI_D_ERROR, " %ld - ***+++*** SMI present with PE/VM active\n", CpuIndex))do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, " %ld - ***+++*** SMI present with PE/VM active\n" , CpuIndex); } } while (((BOOLEAN)(0==1))); |
136 | } |
137 | } |
138 | #endif |
139 | |
140 | } |
141 | |
142 | void SendSmiToOtherProcessors(UINT32 CpuIndex) |
143 | { |
144 | LOCAL_APIC_ICR_LOW low; |
145 | UINT32 high; |
146 | UINTN highSave; |
147 | UINT64 ApicMsr; |
148 | |
149 | ApicMsr = AsmReadMsr64 (IA32_APIC_BASE_MSR_INDEX0x1B); |
150 | |
151 | apicAddress = (UINTN)(ApicMsr & 0xffffff000); // assume the default for now |
152 | |
153 | highSave = APIC_REG(ICR_HIGH)(*(UINTN *)(apicAddress + 0x310)); |
154 | low.Uint32 = 0; |
155 | low.Bits.DeliveryMode = LOCAL_APIC_DELIVERY_MODE_SMI2; |
156 | low.Bits.Level = 1; |
157 | low.Bits.DestinationShorthand = LOCAL_APIC_DESTINATION_SHORTHAND_ALL_EXCLUDING_SELF3; |
158 | |
159 | high = 0; // nonspecific |
160 | |
161 | switch (ApicMsr & (APIC_EN1 << 11|APIC_EXTD1 << 10)) |
162 | { |
163 | case xAPIC_MODE1 << 11: |
164 | APIC_REG(ICR_HIGH)(*(UINTN *)(apicAddress + 0x310)) = high; // write high before lows |
165 | APIC_REG(ICR_LOW)(*(UINTN *)(apicAddress + 0x300)) = low.Uint32; // because writing to low triggers the IPI |
166 | break; |
167 | |
168 | case x2APIC_MODE1 << 11|1 << 10: |
169 | // x2APIC uses MSR's |
170 | __writemsr(0x800 + 0x30, low.Uint32 |((UINT64)high << 32)); |
171 | break; |
172 | |
173 | default: |
174 | DEBUG((EFI_D_ERROR,do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, "%ld SendSmiToOtherProcessors - APIC mode invalid or APIC disabled\n" , CpuIndex); } } while (((BOOLEAN)(0==1))) |
175 | "%ld SendSmiToOtherProcessors - APIC mode invalid or APIC disabled\n",do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, "%ld SendSmiToOtherProcessors - APIC mode invalid or APIC disabled\n" , CpuIndex); } } while (((BOOLEAN)(0==1))) |
176 | CpuIndex))do { if (DebugPrintEnabled ()) { DebugPrint (0x80000000, "%ld SendSmiToOtherProcessors - APIC mode invalid or APIC disabled\n" , CpuIndex); } } while (((BOOLEAN)(0==1))); |
177 | } |
178 | |
179 | APIC_REG(ICR_HIGH)(*(UINTN *)(apicAddress + 0x310)) = highSave; //restore high |
180 | |
181 | DEBUG((EFI_D_INFO,do { if (DebugPrintEnabled ()) { DebugPrint (0x00000040, "%ld SendSmiToOtherProcessors - Sent SMI to other processors command: high: 0x%08lx low: 0x%08lx APIC_MSR: 0x%p\n" , CpuIndex, high, low, ApicMsr); } } while (((BOOLEAN)(0==1)) ) |
182 | "%ld SendSmiToOtherProcessors - Sent SMI to other processors command: high: 0x%08lx low: 0x%08lx APIC_MSR: 0x%p\n",do { if (DebugPrintEnabled ()) { DebugPrint (0x00000040, "%ld SendSmiToOtherProcessors - Sent SMI to other processors command: high: 0x%08lx low: 0x%08lx APIC_MSR: 0x%p\n" , CpuIndex, high, low, ApicMsr); } } while (((BOOLEAN)(0==1)) ) |
183 | CpuIndex,do { if (DebugPrintEnabled ()) { DebugPrint (0x00000040, "%ld SendSmiToOtherProcessors - Sent SMI to other processors command: high: 0x%08lx low: 0x%08lx APIC_MSR: 0x%p\n" , CpuIndex, high, low, ApicMsr); } } while (((BOOLEAN)(0==1)) ) |
184 | high,do { if (DebugPrintEnabled ()) { DebugPrint (0x00000040, "%ld SendSmiToOtherProcessors - Sent SMI to other processors command: high: 0x%08lx low: 0x%08lx APIC_MSR: 0x%p\n" , CpuIndex, high, low, ApicMsr); } } while (((BOOLEAN)(0==1)) ) |
185 | low,do { if (DebugPrintEnabled ()) { DebugPrint (0x00000040, "%ld SendSmiToOtherProcessors - Sent SMI to other processors command: high: 0x%08lx low: 0x%08lx APIC_MSR: 0x%p\n" , CpuIndex, high, low, ApicMsr); } } while (((BOOLEAN)(0==1)) ) |
186 | ApicMsr))do { if (DebugPrintEnabled ()) { DebugPrint (0x00000040, "%ld SendSmiToOtherProcessors - Sent SMI to other processors command: high: 0x%08lx low: 0x%08lx APIC_MSR: 0x%p\n" , CpuIndex, high, low, ApicMsr); } } while (((BOOLEAN)(0==1)) ); |
187 | } |