blob: 299f9509683643640ad12c4e299de40586d030a1 [file] [log] [blame]
Angel Pons80d92382020-04-05 15:47:00 +02001/* SPDX-License-Identifier: GPL-2.0-only */
Mariusz Szafranskia4041332017-08-02 17:28:17 +02002
3#include <stdint.h>
4#include <string.h>
Kyösti Mälkki13f66502019-03-03 08:01:05 +02005#include <device/mmio.h>
Mariusz Szafranskia4041332017-08-02 17:28:17 +02006#include <console/console.h>
7#include <device/device.h>
8#include <device/pci.h>
9
10#include <soc/iomap.h>
11#include <soc/pcr.h>
12#include <soc/soc_util.h>
Julien Viard de Galbert7ebb6b02018-03-01 16:03:31 +010013#include <soc/gpio_dnv.h>
Mariusz Szafranskia4041332017-08-02 17:28:17 +020014
15// Community PadOwnOffset HostOwnOffset
16// GpiIsOffset
17// GpiIeOffset GpiGpeStsOffset GpiGpeEnOffset
18// SmiStsOffset
19// SmiEnOffset NmiStsOffset NmiEnOffset
20// PadCfgLockOffset
21// PadCfgLockTxOffset PadCfgOffset PadPerGroup
22static const struct GPIO_GROUP_INFO mGpioGroupInfo[] = {
23 {PID_GPIOCOM0, R_PCH_PCR_GPIO_NC_PAD_OWN, R_PCH_PCR_GPIO_NC_HOSTSW_OWN,
24 R_PCH_PCR_GPIO_NC_GPI_IS, R_PCH_PCR_GPIO_NC_GPI_IE,
25 R_PCH_PCR_GPIO_NC_GPI_GPE_STS, R_PCH_PCR_GPIO_NC_GPI_GPE_EN,
26 R_PCH_PCR_GPIO_NC_SMI_STS, R_PCH_PCR_GPIO_NC_SMI_EN,
27 R_PCH_PCR_GPIO_NC_NMI_STS, R_PCH_PCR_GPIO_NC_NMI_EN,
28 R_PCH_PCR_GPIO_NC_PADCFGLOCK, R_PCH_PCR_GPIO_NC_PADCFGLOCKTX,
29 R_PCH_PCR_GPIO_NC_PADCFG_OFFSET,
30 V_PCH_GPIO_NC_PAD_MAX}, // DNV NORTH_ALL
31 {PID_GPIOCOM1, R_PCH_PCR_GPIO_SC_DFX_PAD_OWN,
32 R_PCH_PCR_GPIO_SC_DFX_HOSTSW_OWN, R_PCH_PCR_GPIO_SC_DFX_GPI_IS,
33 R_PCH_PCR_GPIO_SC_DFX_GPI_IE, R_PCH_PCR_GPIO_SC_DFX_GPI_GPE_STS,
34 R_PCH_PCR_GPIO_SC_DFX_GPI_GPE_EN, NO_REGISTER_FOR_PROPERTY,
35 NO_REGISTER_FOR_PROPERTY, NO_REGISTER_FOR_PROPERTY,
36 NO_REGISTER_FOR_PROPERTY, R_PCH_PCR_GPIO_SC_DFX_PADCFGLOCK,
37 R_PCH_PCR_GPIO_SC_DFX_PADCFGLOCKTX,
38 R_PCH_PCR_GPIO_SC_DFX_PADCFG_OFFSET,
39 V_PCH_GPIO_SC_DFX_PAD_MAX}, // DNV SOUTH_DFX
40 {PID_GPIOCOM1, R_PCH_PCR_GPIO_SC0_PAD_OWN,
41 R_PCH_PCR_GPIO_SC0_HOSTSW_OWN, R_PCH_PCR_GPIO_SC0_GPI_IS,
42 R_PCH_PCR_GPIO_SC0_GPI_IE, R_PCH_PCR_GPIO_SC0_GPI_GPE_STS,
43 R_PCH_PCR_GPIO_SC0_GPI_GPE_EN, R_PCH_PCR_GPIO_SC0_SMI_STS,
44 R_PCH_PCR_GPIO_SC0_SMI_EN, R_PCH_PCR_GPIO_SC0_NMI_STS,
45 R_PCH_PCR_GPIO_SC0_NMI_EN, R_PCH_PCR_GPIO_SC0_PADCFGLOCK,
46 R_PCH_PCR_GPIO_SC0_PADCFGLOCKTX, R_PCH_PCR_GPIO_SC0_PADCFG_OFFSET,
47 V_PCH_GPIO_SC0_PAD_MAX}, // DNV South Community 0
48 {PID_GPIOCOM1, R_PCH_PCR_GPIO_SC1_PAD_OWN,
49 R_PCH_PCR_GPIO_SC1_HOSTSW_OWN, R_PCH_PCR_GPIO_SC1_GPI_IS,
50 R_PCH_PCR_GPIO_SC1_GPI_IE, R_PCH_PCR_GPIO_SC1_GPI_GPE_STS,
51 R_PCH_PCR_GPIO_SC1_GPI_GPE_EN, R_PCH_PCR_GPIO_SC1_SMI_STS,
52 R_PCH_PCR_GPIO_SC1_SMI_EN, R_PCH_PCR_GPIO_SC1_NMI_STS,
53 R_PCH_PCR_GPIO_SC1_NMI_EN, R_PCH_PCR_GPIO_SC1_PADCFGLOCK,
54 R_PCH_PCR_GPIO_SC1_PADCFGLOCKTX, R_PCH_PCR_GPIO_SC1_PADCFG_OFFSET,
55 V_PCH_GPIO_SC1_PAD_MAX}, // DNV South Community 1
56};
57
58/* Retrieve address and length of GPIO info table */
59static struct GPIO_GROUP_INFO *
60GpioGetGroupInfoTable(uint32_t *GpioGroupInfoTableLength)
61{
Patrick Georgi6b688f52021-02-12 13:49:11 +010062 *GpioGroupInfoTableLength = ARRAY_SIZE(mGpioGroupInfo);
Mariusz Szafranskia4041332017-08-02 17:28:17 +020063 return (struct GPIO_GROUP_INFO *)mGpioGroupInfo;
64}
65
66/* Get Gpio Pad Ownership */
67static void GpioGetPadOwnership(GPIO_PAD GpioPad, GPIO_PAD_OWN *PadOwnVal)
68{
69 uint32_t Mask;
70 uint32_t RegOffset;
71 uint32_t GroupIndex;
72 uint32_t PadNumber;
73 struct GPIO_GROUP_INFO *GpioGroupInfo;
74 uint32_t GpioGroupInfoLength;
75 uint32_t PadOwnRegValue;
76
77 GroupIndex = GPIO_GET_GROUP_INDEX_FROM_PAD(GpioPad);
78 PadNumber = GPIO_GET_PAD_NUMBER(GpioPad);
79
80 GpioGroupInfo = GpioGetGroupInfoTable(&GpioGroupInfoLength);
81
82 //
83 // Check if group argument exceeds GPIO GROUP INFO array
84 //
85 if ((uint32_t)GroupIndex >= GpioGroupInfoLength) {
86 printk(BIOS_ERR, "GPIO ERROR: Group argument (%d) exceeds GPIO "
87 "group range\n",
88 GroupIndex);
89 return;
90 }
91
92 //
93 // Check if legal pin number
94 //
95 if (PadNumber >= GpioGroupInfo[GroupIndex].PadPerGroup) {
96 printk(BIOS_ERR, "GPIO ERROR: Pin number (%d) exceeds possible "
97 "range for this group\n",
98 PadNumber);
99 return;
100 }
101 //
102 // Calculate RegOffset using Pad Ownership offset and GPIO Pad number.
103 // One DWord register contains information for 8 pads.
104 //
105 RegOffset =
106 GpioGroupInfo[GroupIndex].PadOwnOffset + (PadNumber >> 3) * 0x4;
107
108 //
109 // Calculate pad bit position within DWord register
110 //
111 PadNumber %= 8;
112 Mask = ((1 << 1) | (1 << 0)) << (PadNumber * 4);
113
114 PadOwnRegValue = read32((void *)PCH_PCR_ADDRESS(
115 GpioGroupInfo[GroupIndex].Community, RegOffset));
116
117 *PadOwnVal = (GPIO_PAD_OWN)((PadOwnRegValue & Mask) >> (PadNumber * 4));
118}
119
Julien Viard de Galbert7ebb6b02018-03-01 16:03:31 +0100120void gpio_configure_dnv_pads(const struct dnv_pad_config *gpio, size_t num)
Mariusz Szafranskia4041332017-08-02 17:28:17 +0200121{
122 /* Return if gpio not valid */
123 if ((gpio == NULL) || (num == 0))
124 return;
125
126 uint32_t Index;
127 uint32_t Dw0Reg;
128 uint32_t Dw0RegMask;
129 uint32_t Dw1Reg;
130 uint32_t Dw1RegMask;
131 uint32_t PadCfgReg;
132 uint64_t HostSoftOwnReg[V_PCH_GPIO_GROUP_MAX];
133 uint64_t HostSoftOwnRegMask[V_PCH_GPIO_GROUP_MAX];
134 uint64_t GpiGpeEnReg[V_PCH_GPIO_GROUP_MAX];
135 uint64_t GpiGpeEnRegMask[V_PCH_GPIO_GROUP_MAX];
136 struct GPIO_GROUP_INFO *GpioGroupInfo;
137 uint32_t GpioGroupInfoLength;
138 GPIO_PAD GpioGroupOffset;
139 uint32_t NumberOfGroups;
140 GPIO_PAD_OWN PadOwnVal;
Julien Viard de Galbert7ebb6b02018-03-01 16:03:31 +0100141 struct dnv_pad_config *GpioData;
Mariusz Szafranskia4041332017-08-02 17:28:17 +0200142 GPIO_PAD Group;
143 uint32_t GroupIndex;
144 uint32_t PadNumber;
145 uint32_t FinalValue;
146 uint32_t Data32;
147 uint32_t PadMode1, PadMode2;
148
149 PadOwnVal = GpioPadOwnHost;
150
151 memset(HostSoftOwnReg, 0, sizeof(HostSoftOwnReg));
152 memset(HostSoftOwnRegMask, 0, sizeof(HostSoftOwnRegMask));
153 memset(GpiGpeEnReg, 0, sizeof(GpiGpeEnReg));
154 memset(GpiGpeEnRegMask, 0, sizeof(GpiGpeEnRegMask));
155
156 GpioGroupInfo = GpioGetGroupInfoTable(&GpioGroupInfoLength);
157
158 GpioGroupOffset = GPIO_DNV_GROUP_MIN;
159 NumberOfGroups = V_PCH_GPIO_GROUP_MAX;
160
161 for (Index = 0; Index < (uint32_t)num; Index++) {
162
163 Dw0RegMask = 0;
164 Dw0Reg = 0;
165 Dw1RegMask = 0;
166 Dw1Reg = 0;
167
Julien Viard de Galbert7ebb6b02018-03-01 16:03:31 +0100168 GpioData = (struct dnv_pad_config *)&(gpio[Index]);
Mariusz Szafranskia4041332017-08-02 17:28:17 +0200169
170 Group = GPIO_GET_GROUP_FROM_PAD(GpioData->GpioPad);
171 GroupIndex = GPIO_GET_GROUP_INDEX_FROM_PAD(GpioData->GpioPad);
172 PadNumber = GPIO_GET_PAD_NUMBER(GpioData->GpioPad);
173
174 //
175 // Check if group index argument exceeds GPIO group index range
176 //
177 if (GroupIndex >= V_PCH_GPIO_GROUP_MAX) {
178 printk(BIOS_ERR, "GPIO ERROR: Invalid Group Index "
179 "(GroupIndex=%d, Pad=%d)!\n",
180 GroupIndex, PadNumber);
181 continue;
182 }
183
184 //
185 // Check if group argument exceeds GPIO group range
186 //
187 if ((Group < GpioGroupOffset) ||
188 (Group >= NumberOfGroups + GpioGroupOffset)) {
189 printk(BIOS_ERR,
190 "GPIO ERROR: Invalid Group (Group=%d)!\n",
191 Group);
192 return;
193 }
194
195 //
196 // Check if legal pin number
197 //
198 if (PadNumber >= GpioGroupInfo[GroupIndex].PadPerGroup) {
199 printk(BIOS_ERR, "GPIO ERROR: Invalid PadNumber "
200 "(PadNumber=%d)!\n",
201 PadNumber);
202 return;
203 }
204
205 //
206 // Check if selected GPIO Pad is not owned by CSME/ISH
207 //
208 GpioGetPadOwnership(GpioData->GpioPad, &PadOwnVal);
209
210 if (PadOwnVal != GpioPadOwnHost) {
211 printk(BIOS_ERR, "GPIO WARNING: Accessing pad not "
212 "owned by host (Group=%d, Pad=%d)!",
213 GroupIndex, PadNumber);
214 if (PadOwnVal == GpioPadOwnCsme)
215 printk(BIOS_ERR, "The owner is CSME\n");
216 else if (PadOwnVal == GpioPadOwnIsh)
217 printk(BIOS_ERR, "The owner is ISH\n");
218 printk(BIOS_ERR, "** Please make sure the GPIO usage "
219 "in sync between CSME/ISH and Host IA "
220 "FW configuration.\n");
221 printk(BIOS_ERR, "** All the GPIO occupied by CSME/ISH "
222 "should not do any configuration by "
223 "Host IA FW.\n");
224 continue;
225 }
226
227 //
228 // Configure Reset Type (PadRstCfg)
229 //
230 Dw0RegMask |=
231 ((((GpioData->GpioConfig.PowerConfig &
232 GPIO_CONF_RESET_MASK) >>
233 GPIO_CONF_RESET_BIT_POS) == GpioHardwareDefault)
234 ? 0x0
235 : B_PCH_GPIO_RST_CONF);
236 Dw0Reg |= (((GpioData->GpioConfig.PowerConfig &
237 GPIO_CONF_RESET_MASK) >>
238 (GPIO_CONF_RESET_BIT_POS + 1))
239 << N_PCH_GPIO_RST_CONF);
240
241 //
242 // Configure how interrupt is triggered (RxEvCfg)
243 //
244 Dw0RegMask |=
245 ((((GpioData->GpioConfig.InterruptConfig &
246 GPIO_CONF_INT_TRIG_MASK) >>
247 GPIO_CONF_INT_TRIG_BIT_POS) == GpioHardwareDefault)
248 ? 0x0
249 : B_PCH_GPIO_RX_LVL_EDG);
250 Dw0Reg |= (((GpioData->GpioConfig.InterruptConfig &
251 GPIO_CONF_INT_TRIG_MASK) >>
252 (GPIO_CONF_INT_TRIG_BIT_POS + 1))
253 << N_PCH_GPIO_RX_LVL_EDG);
254
255 //
256 // Configure interrupt generation (GPIRoutIOxAPIC/SCI/SMI/NMI)
257 //
258 Dw0RegMask |=
259 ((((GpioData->GpioConfig.InterruptConfig &
260 GPIO_CONF_INT_ROUTE_MASK) >>
261 GPIO_CONF_INT_ROUTE_BIT_POS) == GpioHardwareDefault)
262 ? 0x0
263 : (B_PCH_GPIO_RX_NMI_ROUTE |
264 B_PCH_GPIO_RX_SCI_ROUTE |
265 B_PCH_GPIO_RX_SMI_ROUTE |
266 B_PCH_GPIO_RX_APIC_ROUTE));
267 Dw0Reg |= (((GpioData->GpioConfig.InterruptConfig &
268 GPIO_CONF_INT_ROUTE_MASK) >>
269 (GPIO_CONF_INT_ROUTE_BIT_POS + 1))
270 << N_PCH_GPIO_RX_NMI_ROUTE);
271
Jonathan Neuschäfer5268b762018-02-12 12:24:25 +0100272 // If CFIO is not Working as GPIO mode, Don't move TxDisable and
Mariusz Szafranskia4041332017-08-02 17:28:17 +0200273 // RxDisable
274 if (GpioData->GpioConfig.PadMode == GpioPadModeGpio) {
275 //
276 // Configure GPIO direction (GPIORxDis and GPIOTxDis)
277 //
278 Dw0RegMask |= ((((GpioData->GpioConfig.Direction &
279 GPIO_CONF_DIR_MASK) >>
280 GPIO_CONF_DIR_BIT_POS) ==
281 GpioHardwareDefault)
282 ? 0x0
283 : (B_PCH_GPIO_RXDIS |
284 B_PCH_GPIO_TXDIS));
285 Dw0Reg |= (((GpioData->GpioConfig.Direction &
286 GPIO_CONF_DIR_MASK) >>
287 (GPIO_CONF_DIR_BIT_POS + 1))
288 << N_PCH_GPIO_TXDIS);
289 }
290
291 //
292 // Configure GPIO input inversion (RXINV)
293 //
294 Dw0RegMask |= ((((GpioData->GpioConfig.Direction &
295 GPIO_CONF_INV_MASK) >>
296 GPIO_CONF_INV_BIT_POS) == GpioHardwareDefault)
297 ? 0x0
298 : B_PCH_GPIO_RXINV);
299 Dw0Reg |= (((GpioData->GpioConfig.Direction &
300 GPIO_CONF_INV_MASK) >>
301 (GPIO_CONF_INV_BIT_POS + 1))
302 << N_PCH_GPIO_RXINV);
303
304 //
305 // Configure GPIO output state (GPIOTxState)
306 //
307 Dw0RegMask |=
308 ((((GpioData->GpioConfig.OutputState &
309 GPIO_CONF_OUTPUT_MASK) >>
310 GPIO_CONF_OUTPUT_BIT_POS) == GpioHardwareDefault)
311 ? 0x0
312 : B_PCH_GPIO_TX_STATE);
313 Dw0Reg |= (((GpioData->GpioConfig.OutputState &
314 GPIO_CONF_OUTPUT_MASK) >>
315 (GPIO_CONF_OUTPUT_BIT_POS + 1))
316 << N_PCH_GPIO_TX_STATE);
317
318 //
319 // Configure GPIO RX raw override to '1' (RXRAW1)
320 //
321 Dw0RegMask |=
322 ((((GpioData->GpioConfig.OtherSettings &
323 GPIO_CONF_RXRAW_MASK) >>
324 GPIO_CONF_RXRAW_BIT_POS) == GpioHardwareDefault)
325 ? 0x0
326 : B_PCH_GPIO_RX_RAW1);
327 Dw0Reg |= (((GpioData->GpioConfig.OtherSettings &
328 GPIO_CONF_RXRAW_MASK) >>
329 (GPIO_CONF_RXRAW_BIT_POS + 1))
330 << N_PCH_GPIO_RX_RAW1);
331
332 //
333 // Configure GPIO Pad Mode (PMode)
334 //
335 Dw0RegMask |=
336 ((((GpioData->GpioConfig.PadMode &
337 GPIO_CONF_PAD_MODE_MASK) >>
338 GPIO_CONF_PAD_MODE_BIT_POS) == GpioHardwareDefault)
339 ? 0x0
340 : B_PCH_GPIO_PAD_MODE);
341 Dw0Reg |= (((GpioData->GpioConfig.PadMode &
342 GPIO_CONF_PAD_MODE_MASK) >>
343 (GPIO_CONF_PAD_MODE_BIT_POS + 1))
344 << N_PCH_GPIO_PAD_MODE);
345
346 //
347 // Configure GPIO termination (Term)
348 //
349 Dw1RegMask |= ((((GpioData->GpioConfig.ElectricalConfig &
350 GPIO_CONF_TERM_MASK) >>
351 GPIO_CONF_TERM_BIT_POS) == GpioHardwareDefault)
352 ? 0x0
353 : B_PCH_GPIO_TERM);
354 Dw1Reg |= (((GpioData->GpioConfig.ElectricalConfig &
355 GPIO_CONF_TERM_MASK) >>
356 (GPIO_CONF_TERM_BIT_POS + 1))
357 << N_PCH_GPIO_TERM);
358
359 //
360 // Configure GPIO pad tolerance (padtol)
361 //
362 Dw1RegMask |=
363 ((((GpioData->GpioConfig.ElectricalConfig &
364 GPIO_CONF_PADTOL_MASK) >>
365 GPIO_CONF_PADTOL_BIT_POS) == GpioHardwareDefault)
366 ? 0x0
367 : B_PCH_GPIO_PADTOL);
368 Dw1Reg |= (((GpioData->GpioConfig.ElectricalConfig &
369 GPIO_CONF_PADTOL_MASK) >>
370 (GPIO_CONF_PADTOL_BIT_POS + 1))
371 << N_PCH_GPIO_PADTOL);
372
373 //
374 // Check for additional requirements on setting PADCFG register
375 //
376
377 //
378 // Create PADCFG register offset using group and pad number
379 //
380 PadCfgReg = 0x8 * PadNumber +
381 GpioGroupInfo[GroupIndex].PadCfgOffset;
382 Data32 = read32((void *)PCH_PCR_ADDRESS(
383 GpioGroupInfo[GroupIndex].Community, PadCfgReg));
384
385 FinalValue = ((Data32 & (~Dw0RegMask)) | Dw0Reg);
386
387 PadMode1 =
388 (Data32 & B_PCH_GPIO_PAD_MODE) >> N_PCH_GPIO_PAD_MODE;
389 PadMode2 =
390 (Dw0Reg & B_PCH_GPIO_PAD_MODE) >> N_PCH_GPIO_PAD_MODE;
391
392 if (((Data32 & B_PCH_GPIO_PAD_MODE) !=
393 (FinalValue & B_PCH_GPIO_PAD_MODE)) ||
394 (PadMode2 == 0)) {
395 printk(BIOS_DEBUG, "Changing GpioPad PID: %x Offset: "
396 "0x%x PadModeP1: %d P2: %d ",
397 GpioGroupInfo[GroupIndex].Community, PadCfgReg,
398 PadMode1, PadMode2);
399 printk(BIOS_DEBUG, "R: 0x%08x Fx%08x !\n", Data32,
400 FinalValue);
401 //
402 // Write PADCFG DW0 register``
403 //
404 mmio_andthenor32(
405 (void *)(uint32_t)PCH_PCR_ADDRESS(
406 GpioGroupInfo[GroupIndex].Community,
407 PadCfgReg),
408 ~(uint32_t)Dw0RegMask, (uint32_t)Dw0Reg);
409 }
410
411 Data32 = read32((void *)PCH_PCR_ADDRESS(
412 GpioGroupInfo[GroupIndex].Community, PadCfgReg + 0x4));
413 FinalValue = ((Data32 & (~Dw1RegMask)) | Dw1Reg);
414 if (Data32 != FinalValue) {
415 //
416 // Write PADCFG DW1 register
417 //
418 mmio_andthenor32(
419 (void *)(uint32_t)PCH_PCR_ADDRESS(
420 GpioGroupInfo[GroupIndex].Community,
421 PadCfgReg + 0x4),
422 ~(uint32_t)Dw1RegMask, (uint32_t)Dw1Reg);
423 }
424
425 //
426 // Update value to be programmed in HOSTSW_OWN register
427 //
Patrick Rudolphdcf30e82022-03-22 09:02:16 +0100428 HostSoftOwnRegMask[GroupIndex] |=
429 ((uint64_t)GpioData->GpioConfig.HostSoftPadOwn & 0x1) << PadNumber;
430 HostSoftOwnReg[GroupIndex] |=
431 ((uint64_t)GpioData->GpioConfig.HostSoftPadOwn >> 0x1) << PadNumber;
Mariusz Szafranskia4041332017-08-02 17:28:17 +0200432
433 //
434 // Update value to be programmed in GPI_GPE_EN register
435 //
Patrick Rudolphdcf30e82022-03-22 09:02:16 +0100436 GpiGpeEnRegMask[GroupIndex] |=
437 ((uint64_t)GpioData->GpioConfig.InterruptConfig & 0x1) << PadNumber;
438 GpiGpeEnReg[GroupIndex] |=
439 (((uint64_t)GpioData->GpioConfig.InterruptConfig & GpioIntSci) >> 3)
440 << PadNumber;
Mariusz Szafranskia4041332017-08-02 17:28:17 +0200441 }
442
443 for (Index = 0; Index < NumberOfGroups; Index++) {
444 //
445 // Write HOSTSW_OWN registers
446 //
447 if (GpioGroupInfo[Index].HostOwnOffset !=
448 NO_REGISTER_FOR_PROPERTY) {
449 mmio_andthenor32(
450 (void *)PCH_PCR_ADDRESS(
451 GpioGroupInfo[Index].Community,
452 GpioGroupInfo[Index].HostOwnOffset),
453 ~(uint32_t)(HostSoftOwnRegMask[Index] &
454 0xFFFFFFFF),
455 (uint32_t)(HostSoftOwnReg[Index] & 0xFFFFFFFF));
456 mmio_andthenor32(
457 (void *)PCH_PCR_ADDRESS(
458 GpioGroupInfo[Index].Community,
459 GpioGroupInfo[Index].HostOwnOffset +
460 0x4),
Patrick Rudolphdcf30e82022-03-22 09:02:16 +0100461 ~(uint32_t)(HostSoftOwnRegMask[Index] >> 32),
462 (uint32_t)(HostSoftOwnReg[Index] >> 32));
Mariusz Szafranskia4041332017-08-02 17:28:17 +0200463 }
464
465 //
466 // Write GPI_GPE_EN registers
467 //
468 if (GpioGroupInfo[Index].GpiGpeEnOffset !=
469 NO_REGISTER_FOR_PROPERTY) {
470 mmio_andthenor32(
471 (void *)PCH_PCR_ADDRESS(
472 GpioGroupInfo[Index].Community,
473 GpioGroupInfo[Index].GpiGpeEnOffset),
474 ~(uint32_t)(GpiGpeEnRegMask[Index] &
475 0xFFFFFFFF),
476 (uint32_t)(GpiGpeEnReg[Index] & 0xFFFFFFFF));
477 mmio_andthenor32(
478 (void *)PCH_PCR_ADDRESS(
479 GpioGroupInfo[Index].Community,
480 GpioGroupInfo[Index].GpiGpeEnOffset +
481 0x4),
Patrick Rudolphdcf30e82022-03-22 09:02:16 +0100482 ~(uint32_t)(GpiGpeEnRegMask[Index] >> 32),
483 (uint32_t)(GpiGpeEnReg[Index] >> 32));
Mariusz Szafranskia4041332017-08-02 17:28:17 +0200484 }
485 }
486}