[coreboot-gerrit] Patch set updated for coreboot: device/dram/ddr2: Add function to select common CAS en freq

Arthur Heymans (arthur@aheymans.xyz) gerrit at coreboot.org
Fri Mar 10 14:53:34 CET 2017


Arthur Heymans (arthur at aheymans.xyz) just uploaded a new patch set to gerrit, which you can find at https://review.coreboot.org/18320

-gerrit

commit 19237ab9669520c44af733688507a84448e7f768
Author: Arthur Heymans <arthur at aheymans.xyz>
Date:   Wed Mar 1 20:10:55 2017 +0100

    device/dram/ddr2: Add function to select common CAS en freq
    
    This function finds highest common CAS and selects tCLK while
    accounting for the minimal tCLK the memory controller needs.
    
    Change-Id: I3ab39d38a243edddfde8f70ebd23f79ff774e90e
    Signed-off-by: Arthur Heymans <arthur at aheymans.xyz>
---
 src/device/dram/ddr2.c         | 60 ++++++++++++++++++++++++++++++++++++++++++
 src/include/device/dram/ddr2.h |  3 ++-
 2 files changed, 62 insertions(+), 1 deletion(-)

diff --git a/src/device/dram/ddr2.c b/src/device/dram/ddr2.c
index 1471ed5..5f9bdfc 100644
--- a/src/device/dram/ddr2.c
+++ b/src/device/dram/ddr2.c
@@ -2,6 +2,7 @@
  * This file is part of the coreboot project.
  *
  * Copyright (C) 2017 Patrick Rudolph <siro at das-labor.org>
+ * Copyright (C) 2017 Arthur Heymans <arthur at aheymans.xyz>
  *
  * This program is free software: you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
@@ -628,3 +629,62 @@ void dram_print_spd_ddr2(const struct dimm_attr_st *dimm)
 	print_us("  tPLL              : ", dimm->tPLL);
 	print_us("  tRR               : ", dimm->tRR);
 }
+
+u32 get_common_freq_cas(u8 cas_mask, const struct dimm_attr_st *dimm,
+			int num_dimms, u8 *selected_cas, u32 mimimum_ctrl_tclk)
+{
+	int i, j, high_common_cas;
+	u32 tCLK = 0;
+	u32 common_min_tclk[i] = { };
+
+	for (i = 0; i < num_dimms; i++) {
+		if (dimm[i].dimm_type == SPD_DIMM_TYPE_UNDEFINED)
+			continue;
+		cas_mask &= dimm[i].cas_supported;
+	}
+
+	if (!cas_mask) {
+		printk(BIOS_DEBUG, "No common supported CAS\n");
+		return 0;
+	}
+
+	high_common_cas = spd_get_msbs(cas_mask);
+	for (i = high_common_cas; cas_mask & (1 << i); i--) {
+		for (j = 0; j < num_dimms; i++) {
+			if (dimm[i].dimm_type == SPD_DIMM_TYPE_UNDEFINED)
+				continue;
+			common_min_tclk[i] = MAX(common_min_tclk[i],
+						dimm[j].cycle_time[i]);
+		}
+	}
+
+	while (common_min_tclk[high_common_cas] < mimimum_ctrl_tclk) {
+		high_common_cas--;
+		if (high_common_cas < 3)
+			break;
+	}
+
+	tCLK = common_min_tclk[high_common_cas];
+
+	if (tCLK <= TCK_800MHZ) {
+		tCLK = TCK_800MHZ;
+	} else if (tCLK <= TCK_666MHZ) {
+		tCLK = TCK_666MHZ;
+	} else if (tCLK <= TCK_533MHZ) {
+		tCLK = TCK_533MHZ;
+	} else if (tCLK <= TCK_400MHZ) {
+		tCLK = TCK_400MHZ;
+	} else if (tCLK <= TCK_333MHZ) {
+		tCLK = TCK_333MHZ;
+	} else if (tCLK <= TCK_266MHZ) {
+		tCLK = TCK_266MHZ;
+	} else if (tCLK <= TCK_200MHZ) {
+		tCLK = TCK_200MHZ;
+	} else {
+		printk(BIOS_DEBUG, "Too slow common tCLK found\n");
+		return 0;
+	}
+
+	*selected_cas = high_common_cas;
+	return tCLK;
+}
diff --git a/src/include/device/dram/ddr2.h b/src/include/device/dram/ddr2.h
index 7f59a7a..b1a3d44 100644
--- a/src/include/device/dram/ddr2.h
+++ b/src/include/device/dram/ddr2.h
@@ -213,6 +213,7 @@ u32 spd_decode_spd_size_ddr2(u8 byte0);
 u32 spd_decode_eeprom_size_ddr2(u8 byte1);
 int spd_decode_ddr2(struct dimm_attr_st *dimm, u8 spd[SPD_SIZE_MAX_DDR2]);
 void dram_print_spd_ddr2(const struct dimm_attr_st *dimm);
-
+u32 get_common_freq_cas(u8 cas_mask, const struct dimm_attr_st *dimm, int num_dimms,
+			u8 *selected_cas, u32 mimimum_ctrl_tclk);
 
 #endif /* DEVICE_DRAM_DDR2L_H */



More information about the coreboot-gerrit mailing list