blob: fde8852559e9fff927439c9e2f3de24b8e5b8b82 [file] [log] [blame]
zbao7d94cf92012-07-02 14:19:14 +08001/* $NoKeywords:$ */
2/**
3 * @file
4 *
5 * PCIe utility. Various supporting functions.
6 *
7 *
8 *
9 * @xrefitem bom "File Content Label" "Release Content"
10 * @e project: AGESA
11 * @e sub-project: GNB
12 * @e \$Revision: 63425 $ @e \$Date: 2011-12-22 11:24:10 -0600 (Thu, 22 Dec 2011) $
13 *
14 */
15/*
16*****************************************************************************
17*
Siyuan Wang641f00c2013-06-08 11:50:55 +080018 * Copyright (c) 2008 - 2012, Advanced Micro Devices, Inc.
19 * All rights reserved.
20 *
21 * Redistribution and use in source and binary forms, with or without
22 * modification, are permitted provided that the following conditions are met:
23 * * Redistributions of source code must retain the above copyright
24 * notice, this list of conditions and the following disclaimer.
25 * * Redistributions in binary form must reproduce the above copyright
26 * notice, this list of conditions and the following disclaimer in the
27 * documentation and/or other materials provided with the distribution.
28 * * Neither the name of Advanced Micro Devices, Inc. nor the names of
29 * its contributors may be used to endorse or promote products derived
30 * from this software without specific prior written permission.
31 *
32 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
33 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
34 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
35 * DISCLAIMED. IN NO EVENT SHALL ADVANCED MICRO DEVICES, INC. BE LIABLE FOR ANY
36 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
37 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
38 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
39 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
40 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
41 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
zbao7d94cf92012-07-02 14:19:14 +080042* ***************************************************************************
43*
44*/
45
46/*----------------------------------------------------------------------------------------
47 * M O D U L E S U S E D
48 *----------------------------------------------------------------------------------------
49 */
50#include "AGESA.h"
51#include "Ids.h"
52#include "amdlib.h"
53#include "Gnb.h"
54#include "GnbPcie.h"
55#include "GnbPcieFamServices.h"
56#include "GnbCommonLib.h"
57#include "GnbPcieConfig.h"
58#include "GnbPcieInitLibV1.h"
59#include "GnbRegistersLN.h"
60#include "Filecode.h"
61#define FILECODE PROC_GNB_MODULES_GNBPCIEINITLIBV1_PCIEUTILITYLIB_FILECODE
62/*----------------------------------------------------------------------------------------
63 * D E F I N I T I O N S A N D M A C R O S
64 *----------------------------------------------------------------------------------------
65 */
66/// Lane type
67typedef enum {
68 LaneTypeCore, ///< Core Lane
69 LaneTypePhy, ///< Package Phy Lane
70 LaneTypeNativePhy ///< Native Phy Lane
71} LANE_TYPE;
72
73/// Lane Property
74typedef enum {
75 LanePropertyConfig, ///< Configuration
76 LanePropertyActive, ///< Active
77 LanePropertyAllocated ///< Allocated
78} LANE_PROPERTY;
79
80
81/*----------------------------------------------------------------------------------------
82 * T Y P E D E F S A N D S T R U C T U R E S
83 *----------------------------------------------------------------------------------------
84 */
85typedef struct {
86 UINT32 Flags;
87 PCIE_LINK_SPEED_CAP LinkSpeedCapability;
88} PCIE_GLOBAL_GEN_CAP_WORKSPACE;
89
90/*----------------------------------------------------------------------------------------
91 * P R O T O T Y P E S O F L O C A L F U N C T I O N S
92 *----------------------------------------------------------------------------------------
93 */
94
95/*----------------------------------------------------------------------------------------*/
96/**
97 * Get link state history from HW state machine
98 *
99 *
100 *
101 * @param[in] Engine Pointer to engine config descriptor
102 * @param[out] History Buffer to save history
103 * @param[in] Length Buffer length
104 * @param[in] Pcie Pointer to global PCIe configuration
105 */
106
107VOID
108PcieUtilGetLinkHwStateHistory (
109 IN PCIe_ENGINE_CONFIG *Engine,
110 OUT UINT8 *History,
111 IN UINT8 Length,
112 IN PCIe_PLATFORM_CONFIG *Pcie
113 )
114{
115 UINT8 ReadLength;
116 UINT32 LocalHistory [6];
117 UINT16 Index;
118 ASSERT (Length <= 16);
119 ASSERT (Length > 0);
120 if (Length > 6*4) {
121 Length = 6*4;
122 }
123 ReadLength = (Length + 3) / 4;
124 for (Index = 0; Index < ReadLength; Index++) {
125 LocalHistory[Index] = PciePortRegisterRead (
126 Engine,
127 DxF0xE4_xA5_ADDRESS + Index,
128 Pcie
129 );
130 }
131 LibAmdMemCopy (History, LocalHistory, Length, GnbLibGetHeader (Pcie));
132}
133
134/*----------------------------------------------------------------------------------------*/
135/**
136 * Search array for specific pattern
137 *
138 *
139 * @param[in] Buf1 Pointer to source buffer which will be subject of search
140 * @param[in] Buf1Length Length of the source buffer
141 * @param[in] Buf2 Pointer to pattern buffer
142 * @param[in] Buf2Length Length of the pattern buffer
143 * @retval TRUE Pattern found
144 * @retval TRUE Pattern not found
145 */
146
147BOOLEAN
148PcieUtilSearchArray (
149 IN UINT8 *Buf1,
150 IN UINTN Buf1Length,
Arthur Heymans8d3640d2022-05-16 12:27:36 +0200151 CONST IN UINT8 *Buf2,
zbao7d94cf92012-07-02 14:19:14 +0800152 IN UINTN Buf2Length
153 )
154{
155 UINT8 *CurrentBuf1Ptr;
156 CurrentBuf1Ptr = Buf1;
157 while (CurrentBuf1Ptr < (Buf1 + Buf1Length - Buf2Length)) {
158 UINT8 *SourceBufPtr;
Arthur Heymans8d3640d2022-05-16 12:27:36 +0200159 CONST UINT8 *PatternBufPtr;
zbao7d94cf92012-07-02 14:19:14 +0800160 UINTN PatternBufLength;
161 SourceBufPtr = CurrentBuf1Ptr;
162 PatternBufPtr = Buf2;
163 PatternBufLength = Buf2Length;
164 while ((*SourceBufPtr++ == *PatternBufPtr++) && (PatternBufLength-- != 0));
165 if (PatternBufLength == 0) {
166 return TRUE;
167 }
168 CurrentBuf1Ptr++;
169 }
170 return FALSE;
171}
172
173
174/*----------------------------------------------------------------------------------------*/
175/**
176 * Check if link reversed
177 *
178 *
179 * @param[in] HwLinkState Check for HW auto link reversal
180 * @param[in] Engine Pointer to engine config descriptor
181 * @param[in] Pcie Pointer to PCIe config descriptor
182 * @retval TRUE if link reversed
183 */
184BOOLEAN
185PcieUtilIsLinkReversed (
186 IN BOOLEAN HwLinkState,
187 IN PCIe_ENGINE_CONFIG *Engine,
188 IN PCIe_PLATFORM_CONFIG *Pcie
189 )
190{
191 UINT32 LinkReversal;
192
193 LinkReversal = (Engine->EngineData.StartLane > Engine->EngineData.EndLane) ? 1 : 0;
194 if (HwLinkState) {
195 DxF0xE4_x50_STRUCT DxF0xE4_x50;
196 DxF0xE4_x50.Value = PciePortRegisterRead (
197 Engine,
198 DxF0xE4_x50_ADDRESS,
199 Pcie
200 );
201 LinkReversal ^= DxF0xE4_x50.Field.PortLaneReversal;
202 }
203 return ((LinkReversal & BIT0) != 0) ? TRUE : FALSE;
204}
205
206
207/*----------------------------------------------------------------------------------------*/
208/**
209 * Get link width detected during training
210 *
211 *
212 *
213 * @param[in] Engine Pointer to engine config descriptor
214 * @param[in] Pcie Pointer to global PCIe configuration
215 * @retval Link width
216 */
217UINT8
218PcieUtilGetLinkWidth (
219 IN PCIe_ENGINE_CONFIG *Engine,
220 IN PCIe_PLATFORM_CONFIG *Pcie
221 )
222{
223 UINT8 LinkWidth;
224 DxF0xE4_xA2_STRUCT DxF0xE4_xA2;
225 DxF0xE4_xA2.Value = PciePortRegisterRead (
226 Engine,
227 DxF0xE4_xA2_ADDRESS,
228 Pcie
229 );
230 switch (DxF0xE4_xA2.Field.LcLinkWidthRd) {
231 case 0x6:
232 LinkWidth = 16;
233 break;
234 case 0x5:
235 LinkWidth = 12;
236 break;
237 case 0x4:
238 LinkWidth = 8;
239 break;
240 case 0x3:
241 LinkWidth = 4;
242 break;
243 case 0x2:
244 LinkWidth = 2;
245 break;
246 case 0x1:
247 LinkWidth = 1;
248 break;
249 default:
250 LinkWidth = 0;
251 }
252 return LinkWidth;
253}
254
255/*----------------------------------------------------------------------------------------*/
256/**
257 * Get bitmap of PCIE engine lane of requested type
258 *
259 *
260 * @param[in] LaneType Lane type
261 * @param[in] LaneProperty Lane Property
262 * @param[in] Engine Pointer to engine config descriptor
263 * @retval Lane bitmap
264 */
265
266STATIC UINT32
267PcieUtilGetPcieEngineLaneBitMap (
268 IN LANE_TYPE LaneType,
269 IN LANE_PROPERTY LaneProperty,
270 IN PCIe_ENGINE_CONFIG *Engine
271 )
272{
273 UINT32 LaneBitmap;
274 UINT8 Width;
275 UINT16 Offset;
276 UINT16 LoPhylane;
277 UINT16 HiPhylane;
278 PCIe_PLATFORM_CONFIG *Pcie;
279
280 Width = 0;
281 Offset = 0;
282 LaneBitmap = 0;
283 Pcie = (PCIe_PLATFORM_CONFIG *) PcieConfigGetParent (DESCRIPTOR_PLATFORM, &Engine->Header);
284
285 if (PcieConfigIsPcieEngine (Engine)) {
286 if (LaneType == LaneTypeCore && LaneProperty == LanePropertyConfig) {
287 Width = PcieConfigGetNumberOfCoreLane (Engine);
288 Offset = Engine->Type.Port.StartCoreLane;
289 LaneBitmap = ((1 << Width) - 1) << Offset;
290 } else if (PcieConfigIsEngineAllocated (Engine)) {
291 if (LaneType == LaneTypeNativePhy) {
292 LaneBitmap = PcieUtilGetPcieEngineLaneBitMap (LaneTypePhy, LaneProperty, Engine);
293 LaneBitmap = PcieFmGetNativePhyLaneBitmap (LaneBitmap, Engine);
294 } else {
295 if (LaneType == LaneTypeCore) {
296 if (LaneProperty == LanePropertyActive) {
297 Width = PcieUtilGetLinkWidth (Engine, Pcie);
298 Offset = PcieUtilIsLinkReversed (TRUE, Engine, Pcie) ? (Engine->Type.Port.EndCoreLane - Width + 1) : Engine->Type.Port.StartCoreLane;
299 } else if (LaneProperty == LanePropertyAllocated) {
300 Width = PcieConfigGetNumberOfPhyLane (Engine);
301 Offset = PcieUtilIsLinkReversed (FALSE, Engine, Pcie) ? (Engine->Type.Port.EndCoreLane - Width + 1) : Engine->Type.Port.StartCoreLane;
302 }
303 }
304 if (LaneType == LaneTypePhy) {
305 LoPhylane = PcieLibGetLoPhyLane (Engine);
306 HiPhylane = PcieLibGetHiPhyLane (Engine);
307 if (LaneProperty == LanePropertyActive) {
308 Width = PcieUtilGetLinkWidth (Engine, Pcie);
309 Offset = (PcieUtilIsLinkReversed (TRUE, Engine, Pcie) ? (HiPhylane - Width + 1) : LoPhylane) - PcieConfigGetParentWrapper (Engine)->StartPhyLane;
310 } else if (LaneProperty == LanePropertyAllocated) {
311 Width = PcieConfigGetNumberOfPhyLane (Engine);
312 Offset = LoPhylane - PcieConfigGetParentWrapper (Engine)->StartPhyLane;
313 }
314 }
315 LaneBitmap = ((1 << Width) - 1) << Offset;
316 }
317 }
318 }
319 return LaneBitmap;
320}
321
322/*----------------------------------------------------------------------------------------*/
323/**
324 * Get bitmap of PCIE engine lane of requested type
325 *
326 *
327 * @param[in] LaneType Lane type
328 * @param[in] LaneProperty Lane Property
329 * @param[in] Engine Pointer to engine config descriptor
330 * @retval Lane bitmap
331 */
332
333STATIC UINT32
334PcieUtilGetDdiEngineLaneBitMap (
335 IN LANE_TYPE LaneType,
336 IN LANE_PROPERTY LaneProperty,
337 IN PCIe_ENGINE_CONFIG *Engine
338 )
339{
340 UINT32 LaneBitmap;
341 UINT8 Width;
342 UINT16 Offset;
343 Width = 0;
344 Offset = 0;
345 LaneBitmap = 0;
346 if (PcieConfigIsDdiEngine (Engine)) {
347 if (PcieConfigIsEngineAllocated (Engine)) {
348 if (LaneType == LaneTypePhy && ((LaneProperty == LanePropertyActive && (Engine->InitStatus & INIT_STATUS_DDI_ACTIVE)) || (LaneProperty == LanePropertyAllocated))) {
349 Width = PcieConfigGetNumberOfPhyLane (Engine);
350 Offset = PcieLibGetLoPhyLane (Engine) - PcieConfigGetParentWrapper (Engine)->StartPhyLane;
351 LaneBitmap = ((1 << Width) - 1) << Offset;
352 }
353 if (LaneType == LaneTypeNativePhy) {
354 LaneBitmap = PcieUtilGetDdiEngineLaneBitMap (LaneTypePhy, LaneProperty, Engine);
355 LaneBitmap = PcieFmGetNativePhyLaneBitmap (LaneBitmap, Engine);
356 }
357 }
358 }
359 return LaneBitmap;
360}
361
362
363/*----------------------------------------------------------------------------------------*/
364/**
365 * Get bitmap of engine lane of requested type
366 *
367 *
368 * @param[in] IncludeLaneType Include Lane type
369 * @param[in] ExcludeLaneType Exclude Lane type
370 * @param[in] Engine Pointer to engine config descriptor
371 * @retval Lane bitmap
372 */
373
374UINT32
375PcieUtilGetEngineLaneBitMap (
376 IN UINT32 IncludeLaneType,
377 IN UINT32 ExcludeLaneType,
378 IN PCIe_ENGINE_CONFIG *Engine
379 )
380{
381 UINT32 LaneBitmap;
382 LaneBitmap = 0;
383 if (IncludeLaneType & LANE_TYPE_PCIE_LANES) {
384 if (IncludeLaneType & LANE_TYPE_PCIE_CORE_CONFIG) {
385 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeCore, LanePropertyConfig, Engine);
386 }
387 if (IncludeLaneType & LANE_TYPE_PCIE_CORE_ALLOC) {
388 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeCore, LanePropertyAllocated, Engine);
389 }
390 if (IncludeLaneType & (LANE_TYPE_PCIE_CORE_ACTIVE | LANE_TYPE_PCIE_CORE_ALLOC_ACTIVE)) {
391 if (Engine->Type.Port.PortData.LinkHotplug == HotplugEnhanced || PcieConfigCheckPortStatus (Engine, INIT_STATUS_PCIE_PORT_IN_COMPLIANCE)) {
392 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeCore, LanePropertyAllocated, Engine);
393 } else if (PcieConfigCheckPortStatus (Engine, INIT_STATUS_PCIE_TRAINING_SUCCESS)) {
394 if (IncludeLaneType & LANE_TYPE_PCIE_CORE_ALLOC_ACTIVE) {
395 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeCore, LanePropertyAllocated, Engine);
396 } else {
397 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeCore, LanePropertyActive, Engine);
398 }
399 }
400 }
401 if ((IncludeLaneType & LANE_TYPE_PCIE_SB_CORE_CONFIG) && PcieConfigIsSbPcieEngine (Engine)) {
402 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeCore, LanePropertyConfig, Engine);
403 }
404 if ((IncludeLaneType & LANE_TYPE_PCIE_CORE_HOTPLUG) && (Engine->Type.Port.PortData.LinkHotplug != HotplugDisabled)) {
405 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeCore, LanePropertyAllocated, Engine);
406 }
407 if (IncludeLaneType & LANE_TYPE_PCIE_PHY) {
408 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypePhy, LanePropertyAllocated, Engine);
409 }
410 if (IncludeLaneType & LANE_TYPE_PCIE_PHY_NATIVE) {
411 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeNativePhy, LanePropertyAllocated, Engine);
412 }
413 if (IncludeLaneType & (LANE_TYPE_PCIE_PHY_NATIVE_ACTIVE | LANE_TYPE_PCIE_PHY_NATIVE_ALLOC_ACTIVE)) {
414 if (Engine->Type.Port.PortData.LinkHotplug == HotplugEnhanced || PcieConfigCheckPortStatus (Engine, INIT_STATUS_PCIE_PORT_IN_COMPLIANCE)) {
415 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeNativePhy, LanePropertyAllocated, Engine);
416 } else if (PcieConfigCheckPortStatus (Engine, INIT_STATUS_PCIE_TRAINING_SUCCESS)) {
417 if (IncludeLaneType & LANE_TYPE_PCIE_PHY_NATIVE_ALLOC_ACTIVE) {
418 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeNativePhy, LanePropertyAllocated, Engine);
419 } else {
420 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeNativePhy, LanePropertyActive, Engine);
421 }
422 }
423 }
424 if ((IncludeLaneType & LANE_TYPE_PCIE_PHY_NATIVE_HOTPLUG) && (Engine->Type.Port.PortData.LinkHotplug != HotplugDisabled)) {
425 LaneBitmap |= PcieUtilGetPcieEngineLaneBitMap (LaneTypeNativePhy, LanePropertyAllocated, Engine);
426 }
427 }
428 if (IncludeLaneType & LANE_TYPE_DDI_LANES) {
429 if (IncludeLaneType & LANE_TYPE_DDI_PHY) {
430 LaneBitmap |= PcieUtilGetDdiEngineLaneBitMap (LaneTypePhy, LanePropertyAllocated, Engine);
431 }
432 if (IncludeLaneType & LANE_TYPE_DDI_PHY_NATIVE) {
433 LaneBitmap |= PcieUtilGetDdiEngineLaneBitMap (LaneTypeNativePhy, LanePropertyAllocated, Engine);
434 }
435 if (IncludeLaneType & LANE_TYPE_DDI_PHY_NATIVE_ACTIVE) {
436 LaneBitmap |= PcieUtilGetDdiEngineLaneBitMap (LaneTypeNativePhy, LanePropertyActive, Engine);
437 }
438 }
439 if (ExcludeLaneType != 0) {
440 LaneBitmap &= (~PcieUtilGetEngineLaneBitMap (ExcludeLaneType, 0, Engine));
441 }
442 return LaneBitmap;
443}
444
445/*----------------------------------------------------------------------------------------*/
446/**
447 * Get bitmap of phy lane confugred for master pll
448 *
449 *
450 * @param[in] Wrapper Pointer to wrapper config descriptor
451 * @retval Lane bitmap
452 */
453
454STATIC UINT32
455PcieUtilGetMasterPllLaneBitMap (
456 IN PCIe_WRAPPER_CONFIG *Wrapper
457 )
458{
459 if (Wrapper->MasterPll != 0) {
460 return 0xf << (Wrapper->MasterPll - 0xA) * 4;
461 }
462 return 0;
463}
464
465/*----------------------------------------------------------------------------------------*/
466/**
467 * Get bitmap of Wrapper lane of requested type
468 *
469 *
470 * @param[in] IncludeLaneType Include Lane type
471 * @param[in] ExcludeLaneType Exclude Lane type
472 * @param[in] Wrapper Pointer to wrapper config descriptor
473 * @retval Lane bitmap
474 */
475
476UINT32
477PcieUtilGetWrapperLaneBitMap (
478 IN UINT32 IncludeLaneType,
479 IN UINT32 ExcludeLaneType,
480 IN PCIe_WRAPPER_CONFIG *Wrapper
481 )
482{
483 PCIe_ENGINE_CONFIG *EngineList;
484 UINT32 LaneBitmap;
485 EngineList = PcieConfigGetChildEngine (Wrapper);
486 LaneBitmap = 0;
487 if ((IncludeLaneType | ExcludeLaneType) != 0) {
488 if ((IncludeLaneType & LANE_TYPE_ALL) == LANE_TYPE_ALL) {
489 LaneBitmap = (1 << (Wrapper->NumberOfLanes)) - 1;
490 if (ExcludeLaneType != 0) {
491 LaneBitmap &= (~PcieUtilGetWrapperLaneBitMap (ExcludeLaneType, 0, Wrapper));
492 }
493 } else {
494 while (EngineList != NULL) {
495 LaneBitmap |= PcieUtilGetEngineLaneBitMap (IncludeLaneType, ExcludeLaneType, EngineList);
496 EngineList = PcieLibGetNextDescriptor (EngineList);
497 }
498 if ((IncludeLaneType & LANE_TYPE_PCIE_PHY_NATIVE_MASTER_PLL) != 0) {
499 LaneBitmap |= PcieUtilGetMasterPllLaneBitMap (Wrapper);
500 }
501 if ((ExcludeLaneType & LANE_TYPE_PCIE_PHY_NATIVE_MASTER_PLL) != 0) {
502 LaneBitmap &= (~PcieUtilGetMasterPllLaneBitMap (Wrapper));
503 }
504 }
505 }
506 return LaneBitmap;
507}
508
509/*----------------------------------------------------------------------------------------*/
510/**
511 * Program port register table
512 *
513 *
514 *
515 * @param[in] Table Pointer to table
516 * @param[in] Length number of entries
517 * @param[in] Engine Pointer to engine config descriptor
518 * @param[in] S3Save Save for S3 flag
519 * @param[in] Pcie Pointer to global PCIe configuration
520 *
521 */
522
523VOID
524PciePortProgramRegisterTable (
Arthur Heymans8d3640d2022-05-16 12:27:36 +0200525 CONST IN PCIE_PORT_REGISTER_ENTRY *Table,
zbao7d94cf92012-07-02 14:19:14 +0800526 IN UINTN Length,
527 IN PCIe_ENGINE_CONFIG *Engine,
528 IN BOOLEAN S3Save,
529 IN PCIe_PLATFORM_CONFIG *Pcie
530 )
531{
532 UINTN Index;
533 UINT32 Value;
534 for (Index = 0; Index < Length; Index++) {
535 Value = PciePortRegisterRead (
536 Engine,
537 Table[Index].Reg,
538 Pcie
539 );
540 Value &= (~Table[Index].Mask);
541 Value |= Table[Index].Data;
542 PciePortRegisterWrite (
543 Engine,
544 Table[Index].Reg,
545 Value,
546 S3Save,
547 Pcie
548 );
549 }
550}
551
552
553/*----------------------------------------------------------------------------------------*/
554/**
555 * Lock registers
556 *
557 *
558 * @param[in] Wrapper Pointer to wrapper config descriptor
559 * @param[in] Pcie Pointer to global PCIe configuration
560 */
561
562VOID
563PcieLockRegisters (
564 IN PCIe_WRAPPER_CONFIG *Wrapper,
565 IN PCIe_PLATFORM_CONFIG *Pcie
566 )
567{
568 UINT8 CoreId;
569 IDS_HDT_CONSOLE (GNB_TRACE, "PcieLockRegisters Enter\n");
570 if (PcieLibIsPcieWrapper (Wrapper)) {
571 for (CoreId = Wrapper->StartPcieCoreId; CoreId <= Wrapper->EndPcieCoreId; CoreId++) {
572 PcieRegisterWriteField (
573 Wrapper,
574 CORE_SPACE (CoreId, D0F0xE4_CORE_0010_ADDRESS),
575 D0F0xE4_CORE_0010_HwInitWrLock_OFFSET,
576 D0F0xE4_CORE_0010_HwInitWrLock_WIDTH,
577 0x1,
578 TRUE,
579 Pcie
580 );
581 }
582 }
583 IDS_HDT_CONSOLE (GNB_TRACE, "PcieLockRegisters Exit\n");
584}
585
586
587/*----------------------------------------------------------------------------------------*/
588/**
589 * Training state handling
590 *
591 *
592 *
593 * @param[in] Engine Pointer to engine config descriptor
594 * @param[in, out] Buffer Indicate if engine in non final state
595 * @param[in] Pcie Pointer to global PCIe configuration
596 *
597 */
598
599VOID
600STATIC
601PcieUtilGlobalGenCapabilityCallback (
602 IN PCIe_ENGINE_CONFIG *Engine,
603 IN OUT VOID *Buffer,
604 IN PCIe_PLATFORM_CONFIG *Pcie
605 )
606{
607 PCIE_GLOBAL_GEN_CAP_WORKSPACE *GlobalGenCapability;
608 PCIE_LINK_SPEED_CAP LinkSpeedCapability;
609 PCIE_HOTPLUG_TYPE HotPlugType;
610 UINT32 Flags;
611
612 Flags = PCIE_GLOBAL_GEN_CAP_ALL_PORTS;
613 GlobalGenCapability = (PCIE_GLOBAL_GEN_CAP_WORKSPACE*) Buffer;
614 LinkSpeedCapability = PcieGen1;
615 if (PcieConfigCheckPortStatus (Engine, INIT_STATUS_PCIE_TRAINING_SUCCESS)) {
616 Flags |= PCIE_GLOBAL_GEN_CAP_TRAINED_PORTS;
617 }
618 HotPlugType = Engine->Type.Port.PortData.LinkHotplug;
619 if ((HotPlugType == HotplugBasic) || (HotPlugType == HotplugServer) || (HotPlugType == HotplugEnhanced)) {
620 Flags |= PCIE_GLOBAL_GEN_CAP_HOTPLUG_PORTS;
621 }
622 if ((GlobalGenCapability->Flags & Flags) != 0) {
623 ASSERT ((GlobalGenCapability->Flags & (PCIE_PORT_GEN_CAP_MAX | PCIE_PORT_GEN_CAP_BOOT)) != 0);
624 LinkSpeedCapability = PcieFmGetLinkSpeedCap (GlobalGenCapability->Flags, Engine);
625 if (GlobalGenCapability->LinkSpeedCapability < LinkSpeedCapability) {
626 GlobalGenCapability->LinkSpeedCapability = LinkSpeedCapability;
627 }
628 }
629}
630
631/*----------------------------------------------------------------------------------------*/
632/**
633 * Determine global GEN capability
634 *
635 *
636 * @param[in] Flags global GEN capability flags
637 * @param[in] Pcie Pointer to global PCIe configuration
638 *
639 */
640PCIE_LINK_SPEED_CAP
641PcieUtilGlobalGenCapability (
642 IN UINT32 Flags,
643 IN PCIe_PLATFORM_CONFIG *Pcie
644 )
645{
646 PCIE_LINK_SPEED_CAP GlobalCapability;
647 PCIE_GLOBAL_GEN_CAP_WORKSPACE GlobalGenCap;
648
649 GlobalGenCap.LinkSpeedCapability = PcieGen1;
650 GlobalGenCap.Flags = Flags;
651 PcieConfigRunProcForAllEngines (
652 DESCRIPTOR_ALLOCATED | DESCRIPTOR_PCIE_ENGINE,
653 PcieUtilGlobalGenCapabilityCallback,
654 &GlobalGenCap,
655 Pcie
656 );
657
658 GlobalCapability = GlobalGenCap.LinkSpeedCapability;
659
660 return GlobalCapability;
661}