7 * Common Technology functions for DDR2
9 * @xrefitem bom "File Content Label" "Release Content"
11 * @e sub-project: (Mem/Tech/DDR2)
12 * @e \$Revision: 56279 $ @e \$Date: 2011-07-11 13:11:28 -0600 (Mon, 11 Jul 2011) $
15 /*****************************************************************************
17 * Copyright (C) 2012 Advanced Micro Devices, Inc.
18 * All rights reserved.
20 * Redistribution and use in source and binary forms, with or without
21 * modification, are permitted provided that the following conditions are met:
22 * * Redistributions of source code must retain the above copyright
23 * notice, this list of conditions and the following disclaimer.
24 * * Redistributions in binary form must reproduce the above copyright
25 * notice, this list of conditions and the following disclaimer in the
26 * documentation and/or other materials provided with the distribution.
27 * * Neither the name of Advanced Micro Devices, Inc. nor the names of
28 * its contributors may be used to endorse or promote products derived
29 * from this software without specific prior written permission.
31 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
32 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
33 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
34 * DISCLAIMED. IN NO EVENT SHALL ADVANCED MICRO DEVICES, INC. BE LIABLE FOR ANY
35 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
36 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
37 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
38 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
39 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
40 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
42 * ***************************************************************************
47 *----------------------------------------------------------------------------
50 *----------------------------------------------------------------------------
57 #include "AdvancedApi.h"
65 #include "OptionMemory.h"
66 #include "PlatformMemoryConfiguration.h"
73 #define FILECODE PROC_MEM_TECH_DDR2_MT2_FILECODE
75 /*----------------------------------------------------------------------------
76 * DEFINITIONS AND MACROS
78 *----------------------------------------------------------------------------
81 /*----------------------------------------------------------------------------
82 * TYPEDEFS AND STRUCTURES
84 *----------------------------------------------------------------------------
87 /*----------------------------------------------------------------------------
88 * PROTOTYPES OF LOCAL FUNCTIONS
90 *----------------------------------------------------------------------------
93 /*----------------------------------------------------------------------------
96 *----------------------------------------------------------------------------
98 /* -----------------------------------------------------------------------------*/
101 * This function Constructs the technology block
103 * @param[in,out] *NBPtr - Pointer to the MEM_NB_BLOCK
104 * @param[in,out] *TechPtr - Pointer to the MEM_TECH_BLOCK
109 MemConstructTechBlock2 (
110 IN OUT MEM_TECH_BLOCK *TechPtr,
111 IN OUT MEM_NB_BLOCK *NBPtr
114 TECHNOLOGY_TYPE *TechTypePtr;
120 CH_DEF_STRUCT *ChannelPtr;
123 TechTypePtr = (TECHNOLOGY_TYPE *) FindPSOverrideEntry (NBPtr->RefPtr->PlatformMemoryConfiguration, PSO_MEM_TECH, NBPtr->MCTPtr->SocketId, 0, 0, NULL, NULL);
124 if (TechTypePtr != NULL) {
125 // Ensure the platform override value is valid
126 ASSERT ((*TechTypePtr == DDR3_TECHNOLOGY) || (*TechTypePtr == DDR2_TECHNOLOGY));
127 if (*TechTypePtr != DDR2_TECHNOLOGY) {
133 TechPtr->NBPtr = NBPtr;
134 TechPtr->RefPtr = NBPtr->RefPtr;
135 MCTPtr = NBPtr->MCTPtr;
137 TechPtr->NBPtr = NBPtr;
138 TechPtr->RefPtr = NBPtr->RefPtr;
140 TechPtr->SetDramMode = MemTSetDramMode2;
141 TechPtr->DimmPresence = MemTDIMMPresence2;
142 TechPtr->SpdCalcWidth = MemTSPDCalcWidth2;
143 TechPtr->SpdGetTargetSpeed = MemTSPDGetTargetSpeed2;
144 TechPtr->AutoCycTiming = MemTAutoCycTiming2;
145 TechPtr->SpdSetBanks = MemTSPDSetBanks2;
146 TechPtr->SetDqsEccTmgs = MemTSetDQSEccTmgs;
147 TechPtr->GetCSIntLvAddr = MemTGetCSIntLvAddr2;
148 TechPtr->AdjustTwrwr = MemTAdjustTwrwr2;
149 TechPtr->AdjustTwrrd = MemTAdjustTwrrd2;
150 TechPtr->GetDimmSpdBuffer = MemTGetDimmSpdBuffer2;
151 TechPtr->GetLD = MemTGetLD2;
152 TechPtr->MaxFilterDly = 0;
155 // Map the Logical Dimms on this channel to the SPD that should be used for that logical DIMM.
156 // The pointers to the DIMM SPD information is as follows (2 Dimm/Ch and 3 Dimm/Ch examples).
158 // DIMM Spd Buffer Current Channel DimmSpdPtr[MAX_DIMMS_PER_CHANNEL] array
159 // (Number of dimms varies by platform) (Array size is determined in AGESA.H) Dimm operations loop
160 // on this array only)
161 // 2 DIMMS PER CHANNEL
163 // Socket N Channel N Dimm 0 SR/DR DIMM <--------------DimmSpdPtr[0]
164 // Dimm 1 SR/DR DIMM <--------------DimmSpdPtr[1]
165 // DimmSpdPtr[2]------->NULL
166 // DimmSpdPtr[3]------->NULL
168 // Socket N Channel N Dimm 0 SR/DR DIMM <--------------DimmSpdPtr[0]
169 // Dimm 1 QR DIMM <---------+----DimmSpdPtr[1]
170 // | DimmSpdPtr[2]------->NULL
171 // +----DimmSpdPtr[3]
173 // Socket N Channel N Dimm 0 QR DIMM <-----+--------DimmSpdPtr[0]
174 // Dimm 1 QR DIMM <-----|---+----DimmSpdPtr[1]
175 // +-- | ---DimmSpdPtr[2]
176 // +----DimmSpdPtr[3]
178 // 3 DIMMS PER CHANNEL
180 // Socket N Channel N Dimm 0 SR/DR DIMM <--------------DimmSpdPtr[0]
181 // Dimm 1 SR/DR DIMM <--------------DimmSpdPtr[1]
182 // Dimm 3 SR/DR DIMM <--------------DimmSpdPtr[2]
183 // DimmSpdPtr[3]------->NULL
185 // Socket N Channel N Dimm 0 SR/DR DIMM <--------------DimmSpdPtr[0]
186 // Dimm 1 QR DIMM <---------+----DimmSpdPtr[1]
187 // Dimm 3 SR/DR DIMM <-------- | ---DimmSpdPtr[2]
188 // +----DimmSpdPtr[3]
192 for (Dct = 0; Dct < NBPtr->DctCount; Dct++) {
193 NBPtr->SwitchDCT (NBPtr, Dct);
194 DCTPtr = NBPtr->DCTPtr;
195 for (Channel = 0; Channel < NBPtr->ChannelCount; Channel++) {
196 NBPtr->SwitchChannel (NBPtr, Channel);
197 ChannelPtr = NBPtr->ChannelPtr;
198 ChannelPtr->TechType = DDR2_TECHNOLOGY;
199 ChannelPtr->MCTPtr = MCTPtr;
200 ChannelPtr->DCTPtr = DCTPtr;
202 DimmSlots = GetMaxDimmsPerChannel (NBPtr->RefPtr->PlatformMemoryConfiguration,
204 NBPtr->GetSocketRelativeChannel (NBPtr, Dct, Channel)
207 // Initialize the SPD pointers for each Dimm
209 for (i = 0 ; i < (sizeof (ChannelPtr->DimmSpdPtr) / sizeof (ChannelPtr->DimmSpdPtr[0])) ; i++) {
210 ChannelPtr->DimmSpdPtr[i] = NULL;
212 for (i = 0 ; i < DimmSlots; i++) {
213 ChannelPtr->DimmSpdPtr[i] = &(ChannelPtr->SpdPtr[i]);
214 if ( (i + 2) < (sizeof (ChannelPtr->DimmSpdPtr) / sizeof (ChannelPtr->DimmSpdPtr[0]))) {
215 if (ChannelPtr->DimmSpdPtr[i]->DimmPresent) {
216 if ((((ChannelPtr->DimmSpdPtr[i]->Data[SPD_DM_BANKS] >> 3) & 0x07) + 1) > 2) {
217 ChannelPtr->DimmSpdPtr[i + 2] = &(ChannelPtr->SpdPtr[i]);
227 /*----------------------------------------------------------------------------
230 *----------------------------------------------------------------------------