spd/lp5: Add Hynix memory part
[coreboot2.git] / src / lib / dimm_info_util.c
blobd16cb46d0a0ccbcdeec4cf7a299966142671a5db
1 /* SPDX-License-Identifier: GPL-2.0-only */
3 #include <device/dram/spd.h>
4 #include <dimm_info_util.h>
5 #include <smbios.h>
6 #include <spd.h>
7 #include <console/console.h>
9 uint8_t smbios_bus_width_to_spd_width(uint8_t ddr_type, uint16_t total_width,
10 uint16_t data_width)
12 uint8_t out;
14 /* Lookup table as defined in the JEDEC Standard. */
15 switch (data_width) {
16 case 64:
17 out = MEMORY_BUS_WIDTH_64;
18 break;
19 case 32:
20 out = MEMORY_BUS_WIDTH_32;
21 break;
22 case 16:
23 out = MEMORY_BUS_WIDTH_16;
24 break;
25 case 8:
26 out = MEMORY_BUS_WIDTH_8;
27 break;
28 default:
29 printk(BIOS_NOTICE, "Unknown memory size %hu\n", data_width);
31 * The SMBIOS spec says we should set 0xFFFF on an unknown
32 * value, but we don't have a way of passing that signal via SPD
33 * encoded values.
35 out = MEMORY_BUS_WIDTH_8;
36 break;
39 uint16_t extension_bits = total_width - data_width;
41 switch (extension_bits) {
42 case 8:
43 if (ddr_type == MEMORY_TYPE_DDR5 || ddr_type == MEMORY_TYPE_LPDDR5)
44 out |= SPD_ECC_8BIT_LP5_DDR5;
45 else
46 out |= SPD_ECC_8BIT;
47 break;
48 case 0:
49 /* No extension bits */
50 break;
51 default:
52 printk(BIOS_NOTICE, "Unknown number of extension bits %hu\n",
53 extension_bits);
54 break;
57 return out;
60 uint32_t smbios_memory_size_to_mib(uint16_t memory_size, uint32_t extended_size)
62 /* Memory size is unknown */
63 if (memory_size == 0xFFFF)
64 return 0;
65 /* (32 GiB - 1 MiB) or greater is expressed in the extended size. */
66 else if (memory_size == 0x7FFF)
67 return extended_size;
68 /* When the MSB is flipped, the value is specified in kilobytes */
69 else if (memory_size & 0x8000)
70 return (memory_size ^ 0x8000) / KiB;
71 /* Value contains MiB */
72 else
73 return memory_size;
76 uint8_t smbios_form_factor_to_spd_mod_type(smbios_memory_type memory_type,
77 smbios_memory_form_factor form_factor)
79 return convert_form_factor_to_module_type(memory_type, form_factor);