Chameleon

Chameleon Svn Source Tree

Root/trunk/i386/libsaio/dram_controllers.c

1/*
2 * dram controller access and scan from the pci host controller
3 * Integrated and adapted for chameleon 2.0 RC5 by Rekursor from bs0d work
4 * original source comes from:
5 *
6 * memtest86
7 *
8 * Released under version 2 of the Gnu Public License.
9 * By Chris Brady, cbrady@sgi.com
10 * ----------------------------------------------------
11 * MemTest86+ V4.00 Specific code (GPL V2.0)
12 * By Samuel DEMEULEMEESTER, sdemeule@memtest.org
13 * http://www.canardpc.com - http://www.memtest.org
14 */
15
16#include "libsaio.h"
17#include "bootstruct.h"
18#include "pci.h"
19#include "platform.h"
20#include "dram_controllers.h"
21
22#ifndef DEBUG_DRAM
23#define DEBUG_DRAM 0
24#endif
25
26#if DEBUG_DRAM
27#define DBG(x...) printf(x)
28#else
29#define DBG(x...)
30#endif
31
32/*
33 * Initialise memory controller functions
34 */
35
36// Setup P35 Memory Controller
37static void setup_p35(pci_dt_t *dram_dev)
38{
39uint32_t dev0;
40
41// Activate MMR I/O
42dev0 = pci_config_read32(dram_dev->dev.addr, 0x48);
43if (!(dev0 & 0x1)) {
44pci_config_write8(dram_dev->dev.addr, 0x48, (dev0 | 1));
45}
46}
47
48int nhm_bus = 0x3F;
49
50// Setup Nehalem Integrated Memory Controller
51static void setup_nhm(pci_dt_t *dram_dev)
52{
53static long possible_nhm_bus[] = {0xFF, 0x7F, 0x3F};
54unsigned long did, vid;
55int i;
56
57// Nehalem supports Scrubbing
58// First, locate the PCI bus where the MCH is located
59for(i = 0; i < (sizeof(possible_nhm_bus)/sizeof(possible_nhm_bus[0])); i++) {
60vid = pci_config_read16(PCIADDR(possible_nhm_bus[i], 3, 4), PCI_VENDOR_ID);
61did = pci_config_read16(PCIADDR(possible_nhm_bus[i], 3, 4), PCI_DEVICE_ID);
62vid &= 0xFFFF;
63did &= 0xFF00;
64
65if(vid == 0x8086 && did >= 0x2C00) {
66nhm_bus = possible_nhm_bus[i];
67}
68}
69}
70
71/*
72 * Retrieve memory controller fsb functions
73 */
74
75
76// Get i965 Memory Speed
77static void get_fsb_i965(pci_dt_t *dram_dev)
78{
79uint32_t dev0, mch_ratio, mch_cfg, mch_fsb;
80
81long *ptr;
82
83// Find Ratio
84dev0 = pci_config_read32(dram_dev->dev.addr, 0x48);
85dev0 &= 0xFFFFC000;
86ptr = (long*)(dev0 + 0xC00);
87mch_cfg = *ptr & 0xFFFF;
88
89mch_ratio = 100000;
90
91switch (mch_cfg & 7) {
92case 0: mch_fsb = 1066; break;
93case 1: mch_fsb = 533; break;
94default:
95case 2: mch_fsb = 800; break;
96case 3: mch_fsb = 667; break;
97case 4: mch_fsb = 1333; break;
98case 6: mch_fsb = 1600; break;
99}
100
101DBG("mch_fsb %d\n", mch_fsb);
102
103switch (mch_fsb) {
104case 533:
105switch ((mch_cfg >> 4) & 7) {
106case 1:mch_ratio = 200000; break;
107case 2:mch_ratio = 250000; break;
108case 3:mch_ratio = 300000; break;
109}
110break;
111
112default:
113case 800:
114switch ((mch_cfg >> 4) & 7) {
115case 0:mch_ratio = 100000; break;
116case 1:mch_ratio = 125000; break;
117case 2:mch_ratio = 166667; break; // 1.666666667
118case 3:mch_ratio = 200000; break;
119case 4:mch_ratio = 266667; break; // 2.666666667
120case 5:mch_ratio = 333333; break; // 3.333333333
121}
122break;
123
124case 1066:
125switch ((mch_cfg >> 4) & 7) {
126case 1:mch_ratio = 100000; break;
127case 2:mch_ratio = 125000; break;
128case 3:mch_ratio = 150000; break;
129case 4:mch_ratio = 200000; break;
130case 5:mch_ratio = 250000; break;
131}
132break;
133
134case 1333:
135switch ((mch_cfg >> 4) & 7) {
136case 2:mch_ratio = 100000; break;
137case 3:mch_ratio = 120000; break;
138case 4:mch_ratio = 160000; break;
139case 5:mch_ratio = 200000; break;
140}
141break;
142
143case 1600:
144switch ((mch_cfg >> 4) & 7)
145{
146case 3:mch_ratio = 100000; break;
147case 4:mch_ratio = 133333; break; // 1.333333333
148case 5:mch_ratio = 150000; break;
149case 6:mch_ratio = 200000; break;
150}
151break;
152}
153
154DBG("mch_ratio %d\n", mch_ratio);
155
156// Compute RAM Frequency
157Platform.RAM.Frequency = (Platform.CPU.FSBFrequency * mch_ratio) / 100000;
158
159DBG("ram_fsb %d\n", Platform.RAM.Frequency);
160
161}
162
163// Get i965m Memory Speed
164static void get_fsb_im965(pci_dt_t *dram_dev)
165{
166uint32_t dev0, mch_ratio, mch_cfg, mch_fsb;
167
168long *ptr;
169
170// Find Ratio
171dev0 = pci_config_read32(dram_dev->dev.addr, 0x48);
172dev0 &= 0xFFFFC000;
173ptr = (long*)(dev0 + 0xC00);
174mch_cfg = *ptr & 0xFFFF;
175
176mch_ratio = 100000;
177
178switch (mch_cfg & 7) {
179case 1: mch_fsb = 533; break;
180default:
181case 2:mch_fsb = 800; break;
182case 3:mch_fsb = 667; break;
183case 6:mch_fsb = 1066; break;
184}
185
186switch (mch_fsb) {
187case 533:
188switch ((mch_cfg >> 4) & 7) {
189case 1:mch_ratio = 125000; break;
190case 2:mch_ratio = 150000; break;
191case 3:mch_ratio = 200000; break;
192}
193break;
194
195case 667:
196switch ((mch_cfg >> 4)& 7) {
197case 1:mch_ratio = 100000; break;
198case 2:mch_ratio = 120000; break;
199case 3:mch_ratio = 160000; break;
200case 4:mch_ratio = 200000; break;
201case 5:mch_ratio = 240000; break;
202}
203break;
204
205default:
206case 800:
207switch ((mch_cfg >> 4) & 7) {
208case 1:mch_ratio = 83333; break; // 0.833333333
209case 2:mch_ratio = 100000; break;
210case 3:mch_ratio = 133333; break; // 1.333333333
211case 4:mch_ratio = 166667; break; // 1.666666667
212case 5:mch_ratio = 200000; break;
213}
214break;
215case 1066:
216switch ((mch_cfg >> 4)&7) {
217case 5:mch_ratio = 150000; break;
218case 6:mch_ratio = 200000; break;
219}
220
221}
222
223// Compute RAM Frequency
224Platform.RAM.Frequency = (Platform.CPU.FSBFrequency * mch_ratio) / 100000;
225// DBG("ram_fsb %d\n", Platform.RAM.Frequency);
226}
227
228
229// Get iCore7 Memory Speed
230static void get_fsb_nhm(pci_dt_t *dram_dev)
231{
232uint32_t mch_ratio, mc_dimm_clk_ratio;
233
234// Get the clock ratio
235mc_dimm_clk_ratio = pci_config_read16(PCIADDR(nhm_bus, 3, 4), 0x54 );
236mch_ratio = (mc_dimm_clk_ratio & 0x1F);
237
238// Compute RAM Frequency
239Platform.RAM.Frequency = Platform.CPU.FSBFrequency * mch_ratio / 2;
240// DBG("ram_fsb %d\n", Platform.RAM.Frequency);
241}
242
243/*
244 * Retrieve memory controller info functions
245 */
246
247// Get i965 Memory Timings
248static void get_timings_i965(pci_dt_t *dram_dev)
249{
250// Thanks for CDH optis
251uint32_t dev0, c0ckectrl, c1ckectrl, offset;
252uint32_t ODT_Control_Register, Precharge_Register, ACT_Register, Read_Register, Misc_Register;
253
254long *ptr;
255
256// Read MMR Base Address
257dev0 = pci_config_read32(dram_dev->dev.addr, 0x48);
258dev0 &= 0xFFFFC000;
259
260ptr = (long*)(dev0 + 0x260);
261c0ckectrl = *ptr & 0xFFFFFFFF;
262
263ptr = (long*)(dev0 + 0x660);
264c1ckectrl = *ptr & 0xFFFFFFFF;
265
266// If DIMM 0 not populated, check DIMM 1
267((c0ckectrl) >> 20 & 0xF) ? (offset = 0) : (offset = 0x400);
268
269ptr = (long*)(dev0 + offset + 0x29C);
270ODT_Control_Register = *ptr & 0xFFFFFFFF;
271
272ptr = (long*)(dev0 + offset + 0x250);
273Precharge_Register = *ptr & 0xFFFFFFFF;
274
275ptr = (long*)(dev0 + offset + 0x252);
276ACT_Register = *ptr & 0xFFFFFFFF;
277
278ptr = (long*)(dev0 + offset + 0x258);
279Read_Register = *ptr & 0xFFFFFFFF;
280
281ptr = (long*)(dev0 + offset + 0x244);
282Misc_Register = *ptr & 0xFFFFFFFF;
283
284// 965 Series only support DDR2
285Platform.RAM.Type = SMB_MEM_TYPE_DDR2;
286
287// CAS Latency (tCAS)
288Platform.RAM.CAS = ((ODT_Control_Register >> 17) & 7) + 3;
289
290// RAS-To-CAS (tRCD)
291Platform.RAM.TRC = (Read_Register >> 16) & 0xF;
292
293// RAS Precharge (tRP)
294Platform.RAM.TRP = (ACT_Register >> 13) & 0xF;
295
296// RAS Active to precharge (tRAS)
297Platform.RAM.RAS = (Precharge_Register >> 11) & 0x1F;
298
299if ((c0ckectrl >> 20 & 0xF) && (c1ckectrl >> 20 & 0xF)) {
300Platform.RAM.Channels = SMB_MEM_CHANNEL_DUAL;
301} else {
302Platform.RAM.Channels = SMB_MEM_CHANNEL_SINGLE;
303}
304}
305
306// Get im965 Memory Timings
307static void get_timings_im965(pci_dt_t *dram_dev)
308{
309// Thanks for CDH optis
310uint32_t dev0, c0ckectrl, c1ckectrl, offset, ODT_Control_Register, Precharge_Register;
311long *ptr;
312
313// Read MMR Base Address
314dev0 = pci_config_read32(dram_dev->dev.addr, 0x48);
315dev0 &= 0xFFFFC000;
316
317ptr = (long*)(dev0 + 0x1200);
318c0ckectrl = *ptr & 0xFFFFFFFF;
319
320ptr = (long*)(dev0 + 0x1300);
321c1ckectrl = *ptr & 0xFFFFFFFF;
322
323// If DIMM 0 not populated, check DIMM 1
324((c0ckectrl) >> 20 & 0xF) ? (offset = 0) : (offset = 0x100);
325
326ptr = (long*)(dev0 + offset + 0x121C);
327ODT_Control_Register = *ptr & 0xFFFFFFFF;
328
329ptr = (long*)(dev0 + offset + 0x1214);
330Precharge_Register = *ptr & 0xFFFFFFFF;
331
332// Series only support DDR2
333Platform.RAM.Type = SMB_MEM_TYPE_DDR2;
334
335// CAS Latency (tCAS)
336Platform.RAM.CAS = ((ODT_Control_Register >> 23) & 7) + 3;
337
338// RAS-To-CAS (tRCD)
339Platform.RAM.TRC = ((Precharge_Register >> 5) & 7) + 2;
340
341// RAS Precharge (tRP)
342Platform.RAM.TRP= (Precharge_Register & 7) + 2;
343
344// RAS Active to precharge (tRAS)
345Platform.RAM.RAS = (Precharge_Register >> 21) & 0x1F;
346
347if ((c0ckectrl >> 20 & 0xF) && (c1ckectrl >> 20 & 0xF)) {
348Platform.RAM.Channels = SMB_MEM_CHANNEL_DUAL;
349} else {
350Platform.RAM.Channels = SMB_MEM_CHANNEL_SINGLE;
351}
352}
353
354// Get P35 Memory Timings
355static void get_timings_p35(pci_dt_t *dram_dev)
356{
357// Thanks for CDH optis
358unsigned long dev0, Memory_Check, c0ckectrl, c1ckectrl, offset;
359unsigned long ODT_Control_Register, Precharge_Register, ACT_Register, Read_Register, Misc_Register;
360long *ptr;
361
362//Device_ID = pci_config_read16(dram_dev->dev.addr, 0x02);
363//Device_ID &= 0xFFFF;
364
365// Now, read MMR Base Address
366dev0 = pci_config_read32(dram_dev->dev.addr, 0x48);
367dev0 &= 0xFFFFC000;
368
369ptr = (long*)(dev0 + 0x260);
370c0ckectrl = *ptr & 0xFFFFFFFF;
371
372ptr = (long*)(dev0 + 0x660);
373c1ckectrl = *ptr & 0xFFFFFFFF;
374
375// If DIMM 0 not populated, check DIMM 1
376((c0ckectrl) >> 20 & 0xF) ? (offset = 0) : (offset = 0x400);
377
378ptr = (long*)(dev0 + offset + 0x265);
379ODT_Control_Register = *ptr & 0xFFFFFFFF;
380
381ptr = (long*)(dev0 + offset + 0x25D);
382Precharge_Register = *ptr & 0xFFFFFFFF;
383
384ptr = (long*)(dev0 + offset + 0x252);
385ACT_Register = *ptr & 0xFFFFFFFF;
386
387ptr = (long*)(dev0 + offset + 0x258);
388Read_Register = *ptr & 0xFFFFFFFF;
389
390ptr = (long*)(dev0 + offset + 0x244);
391Misc_Register = *ptr & 0xFFFFFFFF;
392
393ptr = (long*)(dev0 + offset + 0x1E8);
394Memory_Check = *ptr & 0xFFFFFFFF;
395
396// On P45, check 1A8
397if(dram_dev->device_id > 0x2E00) {
398ptr = (long*)(dev0 + offset + 0x1A8);
399Memory_Check = *ptr & 0xFFFFFFFF;
400Memory_Check >>= 2;
401Memory_Check &= 1;
402Memory_Check = !Memory_Check;
403} else {
404ptr = (long*)(dev0 + offset + 0x1E8);
405Memory_Check = *ptr & 0xFFFFFFFF;
406}
407
408// Determine DDR-II or DDR-III
409if (Memory_Check & 1) {
410Platform.RAM.Type = SMB_MEM_TYPE_DDR2;
411} else {
412Platform.RAM.Type = SMB_MEM_TYPE_DDR3;
413}
414
415// CAS Latency (tCAS)
416if(dram_dev->device_id > 0x2E00) {
417Platform.RAM.CAS = ((ODT_Control_Register >> 8) & 0x3F) - 6;
418} else {
419Platform.RAM.CAS = ((ODT_Control_Register >> 8) & 0x3F) - 9;
420}
421
422// RAS-To-CAS (tRCD)
423Platform.RAM.TRC = (Read_Register >> 17) & 0xF;
424
425// RAS Precharge (tRP)
426Platform.RAM.TRP = (ACT_Register >> 13) & 0xF;
427
428// RAS Active to precharge (tRAS)
429Platform.RAM.RAS = Precharge_Register & 0x3F;
430
431// Channel configuration
432if (((c0ckectrl >> 20) & 0xF) && ((c1ckectrl >> 20) & 0xF)) {
433Platform.RAM.Channels = SMB_MEM_CHANNEL_DUAL;
434} else {
435Platform.RAM.Channels = SMB_MEM_CHANNEL_SINGLE;
436}
437}
438
439// Get Nehalem Memory Timings
440static void get_timings_nhm(pci_dt_t *dram_dev)
441{
442unsigned long mc_channel_bank_timing, mc_control, mc_channel_mrs_value;
443int fvc_bn = 4;
444
445// Find which channels are populated
446mc_control = pci_config_read16(PCIADDR(nhm_bus, 3, 0), 0x48);
447mc_control = (mc_control >> 8) & 0x7;
448
449// DDR-III
450Platform.RAM.Type = SMB_MEM_TYPE_DDR3;
451
452// Get the first valid channel
453if(mc_control & 1) {
454fvc_bn = 4;
455} else if(mc_control & 2) {
456fvc_bn = 5;
457} else if(mc_control & 7) {
458fvc_bn = 6;
459}
460
461// Now, detect timings
462mc_channel_bank_timing = pci_config_read32(PCIADDR(nhm_bus, fvc_bn, 0), 0x88);
463mc_channel_mrs_value = pci_config_read32(PCIADDR(nhm_bus, fvc_bn, 0), 0x70);
464
465// CAS Latency (tCAS)
466Platform.RAM.CAS = ((mc_channel_mrs_value >> 4) & 0xF ) + 4;
467
468// RAS-To-CAS (tRCD)
469Platform.RAM.TRC = (mc_channel_bank_timing >> 9) & 0xF;
470
471// RAS Active to precharge (tRAS)
472Platform.RAM.RAS = (mc_channel_bank_timing >> 4) & 0x1F;
473
474// RAS Precharge (tRP)
475Platform.RAM.TRP = mc_channel_bank_timing & 0xF;
476
477// Single , Dual or Triple Channels
478if (mc_control == 1 || mc_control == 2 || mc_control == 4 ) {
479Platform.RAM.Channels = SMB_MEM_CHANNEL_SINGLE;
480} else if (mc_control == 7) {
481Platform.RAM.Channels = SMB_MEM_CHANNEL_TRIPLE;
482} else {
483Platform.RAM.Channels = SMB_MEM_CHANNEL_DUAL;
484}
485}
486
487static struct mem_controller_t dram_controllers[] = {
488
489// Default unknown chipset
490{ 0, 0, "",NULL, NULL, NULL },
491
492// Intel
493//{ 0x8086, 0x0100, "2rd Gen Core processor",NULL, NULL, NULL },
494//{ 0x8086, 0x0104, "2rd Gen Core processor",NULL, NULL, NULL },
495//{ 0x8086, 0x010C, "Xeon E3-1200/2rd Gen Core processor",NULL, NULL, NULL },
496//{ 0x8086, 0x0150, "Xeon E3-1200 v2/3rd Gen Core processor",NULL, NULL, NULL },
497//{ 0x8086, 0x0154, "3rd Gen Core processor",NULL, NULL, NULL },
498//{ 0x8086, 0x0158, "Xeon E3-1200 v2/Ivy Bridge",NULL, NULL, NULL },
499//{ 0x8086, 0x015C, "Xeon E3-1200 v2/3rd Gen Core processor",NULL, NULL, NULL },
500
501//{ 0x8086, 0x0BF0, "Atom Processor D2xxx/N2xxx",NULL, NULL, NULL },
502//{ 0x8086, 0x0BF1, "Atom Processor D2xxx/N2xxx",NULL, NULL, NULL },
503//{ 0x8086, 0x0BF2, "Atom Processor D2xxx/N2xxx",NULL, NULL, NULL },
504//{ 0x8086, 0x0BF3, "Atom Processor D2xxx/N2xxx",NULL, NULL, NULL },
505//{ 0x8086, 0x0BF4, "Atom Processor D2xxx/N2xxx",NULL, NULL, NULL },
506//{ 0x8086, 0x0BF5, "Atom Processor D2xxx/N2xxx",NULL, NULL, NULL },
507//{ 0x8086, 0x0BF6, "Atom Processor D2xxx/N2xxx",NULL, NULL, NULL },
508//{ 0x8086, 0x0BF7, "Atom Processor D2xxx/N2xxx",NULL, NULL, NULL },
509
510//{ 0x8086, 0x0C00, "Haswell",NULL, NULL, NULL },
511//{ 0x8086, 0x0C04, "Haswell",NULL, NULL, NULL },
512//{ 0x8086, 0x0C08, "Haswell",NULL, NULL, NULL },
513
514{ 0x8086, 0x7190, "VMWare",NULL, NULL, NULL },
515
516{ 0x8086, 0x1A30, "82845 845 [Brookdale]",NULL, NULL, NULL },
517
518{ 0x8086, 0x2970, "82946GZ/PL/GL",setup_p35, get_fsb_i965,get_timings_i965},
519{ 0x8086, 0x2990, "82Q963/Q965",setup_p35, get_fsb_i965,get_timings_i965},
520{ 0x8086, 0x29A0, "P965/G965",setup_p35, get_fsb_i965,get_timings_i965},
521
522{ 0x8086, 0x2A00, "GM965/GL960",setup_p35, get_fsb_im965,get_timings_im965},
523{ 0x8086, 0x2A10, "GME965/GLE960",setup_p35, get_fsb_im965,get_timings_im965},
524{ 0x8086, 0x2A40, "PM/GM45/47",setup_p35, get_fsb_im965,get_timings_im965},
525
526{ 0x8086, 0x29B0, "82Q35 Express",setup_p35, get_fsb_i965,get_timings_p35},
527{ 0x8086, 0x29C0, "82G33/G31/P35/P31",setup_p35, get_fsb_i965,get_timings_p35},
528{ 0x8086, 0x29D0, "82Q33 Express",setup_p35, get_fsb_i965,get_timings_p35},
529{ 0x8086, 0x29E0, "82X38/X48 Express",setup_p35, get_fsb_i965,get_timings_p35},
530{ 0x8086, 0x29F0, "3200/3210",setup_p35, get_fsb_i965,get_timings_p35},
531
532{ 0x8086, 0x2E00, "Eaglelake",setup_p35, get_fsb_i965,get_timings_p35},
533{ 0x8086, 0x2E10, "Q45/Q43",setup_p35, get_fsb_i965,get_timings_p35},
534{ 0x8086, 0x2E20, "P45/G45",setup_p35, get_fsb_i965,get_timings_p35},
535{ 0x8086, 0x2E30, "G41",setup_p35, get_fsb_i965,get_timings_p35},
536//{ 0x8086, 0x2E40, "4 Series Chipset",NULL, NULL, NULL },
537//{ 0x8086, 0x2E90, "4 Series Chipset",NULL, NULL, NULL },
538
539{ 0x8086, 0xD131, "NHM IMC",setup_nhm, get_fsb_nhm,get_timings_nhm},
540{ 0x8086, 0xD132, "NHM IMC",setup_nhm, get_fsb_nhm,get_timings_nhm},
541{ 0x8086, 0x3400, "5520/5500/X58",setup_nhm, get_fsb_nhm,get_timings_nhm},
542{ 0x8086, 0x3401, "5520/5500/X58",setup_nhm, get_fsb_nhm,get_timings_nhm},
543{ 0x8086, 0x3402, "5520/5500/X58",setup_nhm, get_fsb_nhm,get_timings_nhm},
544{ 0x8086, 0x3403, "5500",setup_nhm, get_fsb_nhm,get_timings_nhm},
545{ 0x8086, 0x3404, "5520/5500/X58",setup_nhm, get_fsb_nhm,get_timings_nhm},
546{ 0x8086, 0x3405, "5520/5500/X58",setup_nhm, get_fsb_nhm,get_timings_nhm},
547{ 0x8086, 0x3406, "5520",setup_nhm, get_fsb_nhm,get_timings_nhm},
548{ 0x8086, 0x3407, "5520/5500/X58",setup_nhm, get_fsb_nhm,get_timings_nhm},
549};
550
551static const char *memory_channel_types[] =
552{
553"Unknown", "Single", "Dual", "Triple"
554};
555
556void scan_dram_controller(pci_dt_t *dram_dev)
557{
558int i;
559for(i = 1; i < sizeof(dram_controllers) / sizeof(dram_controllers[0]); i++) {
560if ((dram_controllers[i].vendor == dram_dev->vendor_id) && (dram_controllers[i].device == dram_dev->device_id)) {
561verbose("%s%s DRAM Controller [%4x:%4x] at %02x:%02x.%x\n",
562(dram_dev->vendor_id == 0x8086) ? "Intel Corporation " : "" ,
563dram_controllers[i].name, dram_dev->vendor_id, dram_dev->device_id,
564dram_dev->dev.bits.bus, dram_dev->dev.bits.dev, dram_dev->dev.bits.func);
565
566if (dram_controllers[i].initialise != NULL) {
567dram_controllers[i].initialise(dram_dev);
568}
569
570if (dram_controllers[i].poll_timings != NULL) {
571dram_controllers[i].poll_timings(dram_dev);
572}
573
574if (dram_controllers[i].poll_speed != NULL) {
575dram_controllers[i].poll_speed(dram_dev);
576}
577
578verbose("Frequency detected: %d MHz (%d) %s Channel \n\tCAS:%d tRC:%d tRP:%d RAS:%d (%d-%d-%d-%d)\n",
579(uint32_t)Platform.RAM.Frequency / 1000000,
580(uint32_t)Platform.RAM.Frequency / 500000,
581memory_channel_types[Platform.RAM.Channels]
582,Platform.RAM.CAS, Platform.RAM.TRC, Platform.RAM.TRP, Platform.RAM.RAS
583,Platform.RAM.CAS, Platform.RAM.TRC, Platform.RAM.TRP, Platform.RAM.RAS);
584//getchar();
585}
586}
587}
588

Archive Download this file

Revision: 2636