diff --git a/litex/soc/integration/soc.py b/litex/soc/integration/soc.py index a7f005245..6c3f6ef37 100644 --- a/litex/soc/integration/soc.py +++ b/litex/soc/integration/soc.py @@ -1045,6 +1045,26 @@ class LiteXSoC(SoC): **kwargs) self.csr.add("sdram") + # Save SPD data to be able to verify it at runtime + if hasattr(module, "_spd_data"): + # pack the data into words of bus width + bytes_per_word = self.bus.data_width // 8 + mem = [0] * ceil(len(module._spd_data) / bytes_per_word) + for i in range(len(mem)): + for offset in range(bytes_per_word): + mem[i] <<= 8 + if self.cpu.endianness == "little": + offset = bytes_per_word - 1 - offset + spd_byte = i * bytes_per_word + offset + if spd_byte < len(module._spd_data): + mem[i] |= module._spd_data[spd_byte] + self.add_rom( + name="spd", + origin=self.mem_map.get("spd", None), + size=len(module._spd_data), + contents=mem, + ) + if not with_soc_interconnect: return # Compute/Check SDRAM size diff --git a/litex/soc/software/bios/cmds/cmd_litedram.c b/litex/soc/software/bios/cmds/cmd_litedram.c index 8c81017fc..4c14d98b6 100644 --- a/litex/soc/software/bios/cmds/cmd_litedram.c +++ b/litex/soc/software/bios/cmds/cmd_litedram.c @@ -3,8 +3,10 @@ #include #include #include +#include #include +#include #include #include @@ -272,6 +274,19 @@ static void spdread_handler(int nb_params, char **params) } dump_bytes((unsigned int *) buf, len, 0); + +#ifdef SPD_BASE + { + int cmp_result; + cmp_result = memcmp(buf, (void *) SPD_BASE, SPD_SIZE); + if (cmp_result == 0) { + printf("Memory conents matches the data used for gateware generation\n"); + } else { + printf("\nWARNING: memory differs from the data used during gateware generation:\n"); + dump_bytes((void *) SPD_BASE, SPD_SIZE, 0); + } + } +#endif } define_command(spdread, spdread_handler, "Read SPD EEPROM", LITEDRAM_CMDS); #endif