1*2744d7eeSmsaitoh /* $NetBSD: spdmemvar.h,v 1.16 2020/03/24 04:12:13 msaitoh Exp $ */ 2d41a3cefSpgoyette 3d41a3cefSpgoyette /* 4d41a3cefSpgoyette * Copyright (c) 2007 Paul Goyette 5d41a3cefSpgoyette * Copyright (c) 2007 Tobias Nygren 6d41a3cefSpgoyette * All rights reserved. 7d41a3cefSpgoyette * 8d41a3cefSpgoyette * Redistribution and use in source and binary forms, with or without 9d41a3cefSpgoyette * modification, are permitted provided that the following conditions 10d41a3cefSpgoyette * are met: 11d41a3cefSpgoyette * 1. Redistributions of source code must retain the above copyright 12d41a3cefSpgoyette * notice, this list of conditions and the following disclaimer. 13d41a3cefSpgoyette * 2. Redistributions in binary form must reproduce the above copyright 14d41a3cefSpgoyette * notice, this list of conditions and the following disclaimer in the 15d41a3cefSpgoyette * documentation and/or other materials provided with the distribution. 16d41a3cefSpgoyette * 3. The name of the author may not be used to endorse or promote products 17d41a3cefSpgoyette * derived from this software without specific prior written permission. 18d41a3cefSpgoyette * 19d41a3cefSpgoyette * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS 20d41a3cefSpgoyette * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 21d41a3cefSpgoyette * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 22d41a3cefSpgoyette * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 23d41a3cefSpgoyette * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24d41a3cefSpgoyette * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25d41a3cefSpgoyette * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26d41a3cefSpgoyette * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27d41a3cefSpgoyette * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28d41a3cefSpgoyette * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29d41a3cefSpgoyette * POSSIBILITY OF SUCH DAMAGE. 30d41a3cefSpgoyette */ 31d41a3cefSpgoyette 32d41a3cefSpgoyette /* 33d41a3cefSpgoyette * This information is extracted from JEDEC standard SPD4_01 (www.jedec.org) 34d41a3cefSpgoyette */ 35d41a3cefSpgoyette 36d41a3cefSpgoyette #if BYTE_ORDER == BIG_ENDIAN 37d41a3cefSpgoyette #define SPD_BITFIELD(a, b, c, d) d; c; b; a 38d41a3cefSpgoyette #else 39d41a3cefSpgoyette #define SPD_BITFIELD(a, b, c, d) a; b; c; d 40d41a3cefSpgoyette #endif 41d41a3cefSpgoyette 4250d1d96aSpgoyette /* 4350d1d96aSpgoyette * NOTE 4450d1d96aSpgoyette * 4550d1d96aSpgoyette * Fields with "offsets" are field widths, measured in bits, 4650d1d96aSpgoyette * with "offset" additional bits. Thus, a field with value 4750d1d96aSpgoyette * of 2 with an offset of 14 defines a field with total width 4850d1d96aSpgoyette * of 16 bits. 4950d1d96aSpgoyette */ 5050d1d96aSpgoyette 51d41a3cefSpgoyette struct spdmem_fpm { /* FPM and EDO DIMMS */ 5250d1d96aSpgoyette uint8_t fpm_len; 5350d1d96aSpgoyette uint8_t fpm_size; 5450d1d96aSpgoyette uint8_t fpm_type; 55d41a3cefSpgoyette uint8_t fpm_rows; 56d41a3cefSpgoyette uint8_t fpm_cols; 57d41a3cefSpgoyette uint8_t fpm_banks; 58d41a3cefSpgoyette uint16_t fpm_datawidth; /* endian-sensitive */ 59d41a3cefSpgoyette uint8_t fpm_voltage; 60d41a3cefSpgoyette uint8_t fpm_tRAC; 61d41a3cefSpgoyette uint8_t fpm_tCAC; 62d41a3cefSpgoyette uint8_t fpm_config; 63d41a3cefSpgoyette SPD_BITFIELD( \ 64d41a3cefSpgoyette uint8_t fpm_refresh:7, \ 65d41a3cefSpgoyette uint8_t fpm_selfrefresh:1, , \ 66d41a3cefSpgoyette ); 67d41a3cefSpgoyette uint8_t fpm_dram_dramwidth; 68d41a3cefSpgoyette uint8_t fpm_dram_eccwidth; 69d41a3cefSpgoyette uint8_t fpm_unused2[17]; 70d41a3cefSpgoyette uint8_t fpm_superset; 71d41a3cefSpgoyette uint8_t fpm_unused3[30]; 72d41a3cefSpgoyette uint8_t fpm_cksum; 73d41a3cefSpgoyette } __packed; 74d41a3cefSpgoyette 75d41a3cefSpgoyette struct spdmem_sdram { /* PC66/PC100/PC133 SDRAM */ 7650d1d96aSpgoyette uint8_t sdr_len; 7750d1d96aSpgoyette uint8_t sdr_size; 7850d1d96aSpgoyette uint8_t sdr_type; 79d41a3cefSpgoyette SPD_BITFIELD( \ 80d41a3cefSpgoyette uint8_t sdr_rows:4, \ 81d41a3cefSpgoyette uint8_t sdr_rows2:4, , \ 82d41a3cefSpgoyette ); 83d41a3cefSpgoyette SPD_BITFIELD( \ 84d41a3cefSpgoyette uint8_t sdr_cols:4, \ 85d41a3cefSpgoyette uint8_t sdr_cols2:4, , \ 86d41a3cefSpgoyette ); 87d41a3cefSpgoyette uint8_t sdr_banks; 88d41a3cefSpgoyette uint16_t sdr_datawidth; /* endian-sensitive */ 89d41a3cefSpgoyette uint8_t sdr_voltage; 90d41a3cefSpgoyette SPD_BITFIELD( \ 91d41a3cefSpgoyette uint8_t sdr_cycle_tenths:4, \ 92d41a3cefSpgoyette uint8_t sdr_cycle_whole:4, , \ 93d41a3cefSpgoyette ); 94d41a3cefSpgoyette SPD_BITFIELD( 95d41a3cefSpgoyette uint8_t sdr_tAC_tenths:4, \ 96d41a3cefSpgoyette uint8_t sdr_tAC_whole:4, , \ 97d41a3cefSpgoyette ); 98d41a3cefSpgoyette uint8_t sdr_config; 99d41a3cefSpgoyette SPD_BITFIELD( \ 100d41a3cefSpgoyette uint8_t sdr_refresh:7, \ 101d41a3cefSpgoyette uint8_t sdr_selfrefresh:1, , \ 102d41a3cefSpgoyette ); 103d41a3cefSpgoyette SPD_BITFIELD( \ 104d41a3cefSpgoyette uint8_t sdr_dramwidth:7, \ 105d41a3cefSpgoyette uint8_t sdr_dram_asym_bank2:1, ,\ 106d41a3cefSpgoyette ); 107d41a3cefSpgoyette SPD_BITFIELD( \ 108d41a3cefSpgoyette uint8_t sdr_eccwidth:7, \ 109d41a3cefSpgoyette uint8_t sdr_ecc_asym_bank2:1, , \ 110d41a3cefSpgoyette ); 111d41a3cefSpgoyette uint8_t sdr_min_clk_delay; 112d41a3cefSpgoyette SPD_BITFIELD( \ 113d41a3cefSpgoyette uint8_t sdr_burstlengths:4, \ 114d41a3cefSpgoyette uint8_t sdr_unused1:4, , \ 115d41a3cefSpgoyette ); 116d41a3cefSpgoyette uint8_t sdr_banks_per_chip; 117d41a3cefSpgoyette uint8_t sdr_tCAS; 118d41a3cefSpgoyette uint8_t sdr_tCS; 119d41a3cefSpgoyette uint8_t sdr_tWE; 120d41a3cefSpgoyette uint8_t sdr_mod_attrs; 121d41a3cefSpgoyette uint8_t sdr_dev_attrs; 122d41a3cefSpgoyette uint8_t sdr_min_cc_1; 123d41a3cefSpgoyette uint8_t sdr_max_tAC_1; 124d41a3cefSpgoyette uint8_t sdr_min_cc_2; 125d41a3cefSpgoyette uint8_t sdr_max_tAC_2; 126d41a3cefSpgoyette uint8_t sdr_tRP; 127d41a3cefSpgoyette uint8_t sdr_tRRD; 128d41a3cefSpgoyette uint8_t sdr_tRCD; 129d41a3cefSpgoyette uint8_t sdr_tRAS; 130d41a3cefSpgoyette uint8_t sdr_module_rank_density; 131d41a3cefSpgoyette uint8_t sdr_tIS; 132d41a3cefSpgoyette #define sdr_superset sdr_tIS 133d41a3cefSpgoyette uint8_t sdr_tIH; 134d41a3cefSpgoyette uint8_t sdr_tDS; 135d41a3cefSpgoyette uint8_t sdr_tDH; 136d41a3cefSpgoyette uint8_t sdr_unused2[5]; 137d41a3cefSpgoyette uint8_t sdr_tRC; 138d41a3cefSpgoyette uint8_t sdr_unused3[18]; 139d41a3cefSpgoyette uint8_t sdr_esdram; 140d41a3cefSpgoyette uint8_t sdr_super_tech; 141d41a3cefSpgoyette uint8_t sdr_spdrev; 142d41a3cefSpgoyette uint8_t sdr_cksum; 143d41a3cefSpgoyette } __packed; 144d41a3cefSpgoyette 145d41a3cefSpgoyette struct spdmem_rom { 14650d1d96aSpgoyette uint8_t rom_len; 14750d1d96aSpgoyette uint8_t rom_size; 14850d1d96aSpgoyette uint8_t rom_type; 149d41a3cefSpgoyette uint8_t rom_rows; 150d41a3cefSpgoyette uint8_t rom_cols; 151d41a3cefSpgoyette uint8_t rom_banks; 152d41a3cefSpgoyette uint16_t rom_datawidth; /* endian-sensitive */ 153d41a3cefSpgoyette uint8_t rom_voltage; 154d41a3cefSpgoyette uint16_t rom_tAA; /* endian-sensitive */ 155d41a3cefSpgoyette uint8_t rom_config; 156d41a3cefSpgoyette uint8_t rom_unused1; 157d41a3cefSpgoyette uint8_t rom_tPA; 158d41a3cefSpgoyette uint8_t rom_tOE; 159d41a3cefSpgoyette uint16_t rom_tCE; /* endian-sensitive */ 160d41a3cefSpgoyette uint8_t rom_burstlength; 161d41a3cefSpgoyette uint8_t rom_unused2[14]; 162d41a3cefSpgoyette uint8_t rom_superset[31]; 163d41a3cefSpgoyette uint8_t rom_cksum; 164d41a3cefSpgoyette } __packed; 165d41a3cefSpgoyette 166d41a3cefSpgoyette 167d41a3cefSpgoyette struct spdmem_ddr { /* Dual Data Rate SDRAM */ 16850d1d96aSpgoyette uint8_t ddr_len; 16950d1d96aSpgoyette uint8_t ddr_size; 17050d1d96aSpgoyette uint8_t ddr_type; 171d41a3cefSpgoyette SPD_BITFIELD( \ 172d41a3cefSpgoyette uint8_t ddr_rows:4, \ 173d41a3cefSpgoyette uint8_t ddr_rows2:4, , \ 174d41a3cefSpgoyette ); 175d41a3cefSpgoyette SPD_BITFIELD( \ 176d41a3cefSpgoyette uint8_t ddr_cols:4, \ 177d41a3cefSpgoyette uint8_t ddr_cols2:4, , \ 178d41a3cefSpgoyette ); 179d41a3cefSpgoyette uint8_t ddr_ranks; 180d41a3cefSpgoyette uint16_t ddr_datawidth; /* endian-sensitive */ 181d41a3cefSpgoyette uint8_t ddr_voltage; 182d41a3cefSpgoyette SPD_BITFIELD( \ 183d41a3cefSpgoyette uint8_t ddr_cycle_tenths:4, \ 184d41a3cefSpgoyette uint8_t ddr_cycle_whole:4, , \ 185d41a3cefSpgoyette ); 186d41a3cefSpgoyette SPD_BITFIELD( \ 187d41a3cefSpgoyette uint8_t ddr_tAC_hundredths:4, \ 188d41a3cefSpgoyette uint8_t ddr_tAC_tenths:4, , \ 189d41a3cefSpgoyette ); 190d41a3cefSpgoyette uint8_t ddr_config; 191d41a3cefSpgoyette SPD_BITFIELD( \ 192d41a3cefSpgoyette uint8_t ddr_refresh:7, \ 193d41a3cefSpgoyette uint8_t ddr_selfrefresh:1, , \ 194d41a3cefSpgoyette ); 195d41a3cefSpgoyette SPD_BITFIELD( \ 196d41a3cefSpgoyette uint8_t ddr_dramwidth:7, \ 197d41a3cefSpgoyette uint8_t ddr_dram_asym_bank2:1, ,\ 198d41a3cefSpgoyette ); 199d41a3cefSpgoyette SPD_BITFIELD( \ 200d41a3cefSpgoyette uint8_t ddr_eccwidth:7, \ 201d41a3cefSpgoyette uint8_t ddr_ecc_asym_bank2:1, , \ 202d41a3cefSpgoyette ); 203d41a3cefSpgoyette uint8_t ddr_min_clk_delay; 204d41a3cefSpgoyette SPD_BITFIELD( \ 205d41a3cefSpgoyette uint8_t ddr_burstlengths:4, \ 206d41a3cefSpgoyette uint8_t ddr_unused1:4, , \ 207d41a3cefSpgoyette ); 208d41a3cefSpgoyette uint8_t ddr_banks_per_chip; 209d41a3cefSpgoyette uint8_t ddr_tCAS; 210d41a3cefSpgoyette uint8_t ddr_tCS; 211d41a3cefSpgoyette uint8_t ddr_tWE; 212d41a3cefSpgoyette uint8_t ddr_mod_attrs; 213d41a3cefSpgoyette uint8_t ddr_dev_attrs; 214d41a3cefSpgoyette uint8_t ddr_min_cc_05; 215d41a3cefSpgoyette uint8_t ddr_max_tAC_05; 216d41a3cefSpgoyette uint8_t ddr_min_cc_1; 217d41a3cefSpgoyette uint8_t ddr_max_tAC_1; 218d41a3cefSpgoyette uint8_t ddr_tRP; 219d41a3cefSpgoyette uint8_t ddr_tRRD; 220d41a3cefSpgoyette uint8_t ddr_tRCD; 221d41a3cefSpgoyette uint8_t ddr_tRAS; 222d41a3cefSpgoyette uint8_t ddr_module_rank_density; 223d41a3cefSpgoyette uint8_t ddr_tIS; 224d41a3cefSpgoyette #define ddr_superset ddr_tIS 225d41a3cefSpgoyette uint8_t ddr_tIH; 226d41a3cefSpgoyette uint8_t ddr_tDS; 227d41a3cefSpgoyette uint8_t ddr_tDH; 228d41a3cefSpgoyette uint8_t ddr_unused2[5]; 229d41a3cefSpgoyette uint8_t ddr_tRC; 230d41a3cefSpgoyette uint8_t ddr_tRFC; 231d41a3cefSpgoyette uint8_t ddr_tCK; 232d41a3cefSpgoyette uint8_t ddr_tDQSQ; 233d41a3cefSpgoyette uint8_t ddr_tQHS; 234d41a3cefSpgoyette uint8_t ddr_unused3; 235d41a3cefSpgoyette uint8_t ddr_height; 236d41a3cefSpgoyette uint8_t ddr_unused4[15]; 237d41a3cefSpgoyette uint8_t ddr_cksum; 238d41a3cefSpgoyette } __packed; 239d41a3cefSpgoyette 240d41a3cefSpgoyette struct spdmem_ddr2 { /* Dual Data Rate 2 SDRAM */ 24150d1d96aSpgoyette uint8_t ddr2_len; 24250d1d96aSpgoyette uint8_t ddr2_size; 24350d1d96aSpgoyette uint8_t ddr2_type; 244d41a3cefSpgoyette SPD_BITFIELD( \ 245d41a3cefSpgoyette uint8_t ddr2_rows:5, \ 246d41a3cefSpgoyette uint8_t ddr2_unused1:3, , \ 247d41a3cefSpgoyette ); 248d41a3cefSpgoyette SPD_BITFIELD( \ 249d41a3cefSpgoyette uint8_t ddr2_cols:4, \ 250d41a3cefSpgoyette uint8_t ddr2_unused2:4, , \ 251d41a3cefSpgoyette ); 252d41a3cefSpgoyette SPD_BITFIELD( \ 253d41a3cefSpgoyette uint8_t ddr2_ranks:3, 254d41a3cefSpgoyette uint8_t ddr2_cardoncard:1, \ 255d41a3cefSpgoyette uint8_t ddr2_package:1, \ 256d41a3cefSpgoyette uint8_t ddr2_height:3 \ 257d41a3cefSpgoyette ); 258d41a3cefSpgoyette uint8_t ddr2_datawidth; 259d41a3cefSpgoyette uint8_t ddr2_unused3; 260d41a3cefSpgoyette uint8_t ddr2_voltage; 261d41a3cefSpgoyette SPD_BITFIELD( \ 262d41a3cefSpgoyette uint8_t ddr2_cycle_frac:4, \ 263d41a3cefSpgoyette uint8_t ddr2_cycle_whole:4, , \ 264d41a3cefSpgoyette ); 265d41a3cefSpgoyette SPD_BITFIELD( \ 266d41a3cefSpgoyette uint8_t ddr2_tAC_hundredths:4, \ 267d41a3cefSpgoyette uint8_t ddr2_tAC_tenths:4, , \ 268d41a3cefSpgoyette ); 269d41a3cefSpgoyette uint8_t ddr2_config; 270d41a3cefSpgoyette SPD_BITFIELD( \ 271d41a3cefSpgoyette uint8_t ddr2_refresh:7, \ 272d41a3cefSpgoyette uint8_t ddr2_selfrefresh:1, , \ 273d41a3cefSpgoyette ); 274d41a3cefSpgoyette uint8_t ddr2_dramwidth; 275d41a3cefSpgoyette uint8_t ddr2_eccwidth; 276d41a3cefSpgoyette uint8_t ddr2_unused4; 277d41a3cefSpgoyette SPD_BITFIELD( \ 278d41a3cefSpgoyette uint8_t ddr2_burstlengths:4, \ 279d41a3cefSpgoyette uint8_t ddr2_unused5:4, , \ 280d41a3cefSpgoyette ); 281d41a3cefSpgoyette uint8_t ddr2_banks_per_chip; 282d41a3cefSpgoyette uint8_t ddr2_tCAS; 283d41a3cefSpgoyette uint8_t ddr2_mechanical; 284d41a3cefSpgoyette uint8_t ddr2_dimm_type; 285d41a3cefSpgoyette uint8_t ddr2_mod_attrs; 286d41a3cefSpgoyette uint8_t ddr2_dev_attrs; 287d41a3cefSpgoyette uint8_t ddr2_min_cc_1; 288d41a3cefSpgoyette uint8_t ddr2_max_tAC_1; 289d41a3cefSpgoyette uint8_t ddr2_min_cc_2; 290d41a3cefSpgoyette uint8_t ddr2_max_tAC_2; 291d41a3cefSpgoyette uint8_t ddr2_tRP; 292d41a3cefSpgoyette uint8_t ddr2_tRRD; 293d41a3cefSpgoyette uint8_t ddr2_tRCD; 294d41a3cefSpgoyette uint8_t ddr2_tRAS; 295d41a3cefSpgoyette uint8_t ddr2_module_rank_density; 296d41a3cefSpgoyette uint8_t ddr2_tIS; 297d41a3cefSpgoyette uint8_t ddr2_tIH; 298d41a3cefSpgoyette uint8_t ddr2_tDS; 299d41a3cefSpgoyette uint8_t ddr2_tDH; 300d41a3cefSpgoyette uint8_t ddr2_tWR; 301d41a3cefSpgoyette uint8_t ddr2_tWTR; 302d41a3cefSpgoyette uint8_t ddr2_tRTP; 303d41a3cefSpgoyette uint8_t ddr2_probe; 304d41a3cefSpgoyette uint8_t ddr2_extensions; 305d41a3cefSpgoyette uint8_t ddr2_tRC; 306d41a3cefSpgoyette uint8_t ddr2_tRFC; 307d41a3cefSpgoyette uint8_t ddr2_tCK; 308d41a3cefSpgoyette uint8_t ddr2_tDQSQ; 309d41a3cefSpgoyette uint8_t ddr2_tQHS; 310d41a3cefSpgoyette uint8_t ddr2_pll_relock; 311d41a3cefSpgoyette uint8_t ddr2_Tcasemax; 312d41a3cefSpgoyette uint8_t ddr2_Psi_TA_DRAM; 313d41a3cefSpgoyette uint8_t ddr2_dt0; 314d41a3cefSpgoyette uint8_t ddr2_dt2NQ; 315d41a3cefSpgoyette uint8_t ddr2_dr2P; 316d41a3cefSpgoyette uint8_t ddr2_dt3N; 317d41a3cefSpgoyette uint8_t ddr2_dt3Pfast; 318d41a3cefSpgoyette uint8_t ddr2_dt3Pslow; 319d41a3cefSpgoyette uint8_t ddr2_dt4R_4R4W_mode; 320d41a3cefSpgoyette uint8_t ddr2_dt5B; 321d41a3cefSpgoyette uint8_t ddr2_dt7; 322d41a3cefSpgoyette uint8_t ddr2_Psi_TA_PLL; 323d41a3cefSpgoyette uint8_t ddr2_Psi_TA_Reg; 324d41a3cefSpgoyette uint8_t ddr2_dt_PLL_Active; 325d41a3cefSpgoyette uint8_t ddr2_dt_Reg_Active; 326d41a3cefSpgoyette uint8_t ddr2_spdrev; 327d41a3cefSpgoyette uint8_t ddr2_cksum; 328d41a3cefSpgoyette } __packed; 329d41a3cefSpgoyette 330d41a3cefSpgoyette struct spdmem_fbdimm { /* Fully-buffered DIMM */ 33150d1d96aSpgoyette uint8_t fbdimm_len; 33250d1d96aSpgoyette uint8_t fbdimm_size; 33350d1d96aSpgoyette uint8_t fbdimm_type; 334d41a3cefSpgoyette SPD_BITFIELD( \ 335d41a3cefSpgoyette uint8_t fbdimm_ps1_voltage:4, \ 336d41a3cefSpgoyette uint8_t fbdimm_ps2_voltage:4, , \ 337d41a3cefSpgoyette ); 338d41a3cefSpgoyette SPD_BITFIELD( \ 339d41a3cefSpgoyette uint8_t fbdimm_banks:2, \ 340d41a3cefSpgoyette uint8_t fbdimm_cols:3, \ 341d41a3cefSpgoyette uint8_t fbdimm_rows:3, \ 342d41a3cefSpgoyette ); 343d41a3cefSpgoyette SPD_BITFIELD( \ 344d41a3cefSpgoyette uint8_t fbdimm_thick:3, \ 345d41a3cefSpgoyette uint8_t fbdimm_height:3, \ 346d41a3cefSpgoyette uint8_t fbdimm_unused1:2, \ 347d41a3cefSpgoyette ); 348d41a3cefSpgoyette uint8_t fbdimm_mod_type; 349d41a3cefSpgoyette SPD_BITFIELD( \ 350d41a3cefSpgoyette uint8_t fbdimm_dev_width:3, \ 351d41a3cefSpgoyette uint8_t fbdimm_ranks:3, \ 352d41a3cefSpgoyette uint8_t fbdimm_unused2:2, \ 353d41a3cefSpgoyette ); 354d41a3cefSpgoyette SPD_BITFIELD( \ 355d41a3cefSpgoyette uint8_t fbdimm_ftb_divisor:4, \ 35617c75893Smsaitoh uint8_t fbdimm_ftb_dividend:4, ,\ 357d41a3cefSpgoyette ); 358d41a3cefSpgoyette uint8_t fbdimm_mtb_dividend; 359d41a3cefSpgoyette uint8_t fbdimm_mtb_divisor; 360d41a3cefSpgoyette uint8_t fbdimm_tCKmin; 361d41a3cefSpgoyette uint8_t fbdimm_tCKmax; 362d41a3cefSpgoyette uint8_t fbdimm_tCAS; 363d41a3cefSpgoyette uint8_t fbdimm_tAAmin; 364d41a3cefSpgoyette SPD_BITFIELD( \ 365d41a3cefSpgoyette uint8_t fbdimm_tWR_min:4, \ 366d41a3cefSpgoyette uint8_t fbdimm_WR_range:4, , \ 367d41a3cefSpgoyette ); 368d41a3cefSpgoyette uint8_t fbdimm_tWR; 369d41a3cefSpgoyette SPD_BITFIELD( \ 370d41a3cefSpgoyette uint8_t fbdimm_tWL_min:4, \ 371d41a3cefSpgoyette uint8_t fbdimm_tWL_range:4, , \ 372d41a3cefSpgoyette ); 373d41a3cefSpgoyette SPD_BITFIELD( \ 374d41a3cefSpgoyette uint8_t fbdimm_tAL_min:4, \ 375d41a3cefSpgoyette uint8_t fbdimm_tAL_range:4, , \ 376d41a3cefSpgoyette ); 377d41a3cefSpgoyette uint8_t fbdimm_tRCDmin; 378d41a3cefSpgoyette uint8_t fbdimm_tRRDmin; 379d41a3cefSpgoyette uint8_t fbdimm_tRPmin; 380d41a3cefSpgoyette SPD_BITFIELD( \ 381d41a3cefSpgoyette uint8_t fbdimm_tRAS_msb:4, \ 382d41a3cefSpgoyette uint8_t fbdimm_tRC_msb:4, , \ 383d41a3cefSpgoyette ); 384d41a3cefSpgoyette uint8_t fbdimm_tRAS_lsb; 385d41a3cefSpgoyette uint8_t fbdimm_tRC_lsb; 386d41a3cefSpgoyette uint16_t fbdimm_tRFC; /* endian-sensitive */ 387d41a3cefSpgoyette uint8_t fbdimm_tWTR; 388d41a3cefSpgoyette uint8_t fbdimm_tRTP; 389d41a3cefSpgoyette SPD_BITFIELD( \ 390d41a3cefSpgoyette uint8_t fbdimm_burst_4:1, \ 391d41a3cefSpgoyette uint8_t fbdimm_burst_8:1, \ 392d41a3cefSpgoyette uint8_t fbdimm_unused3:6, \ 393d41a3cefSpgoyette ); 394d41a3cefSpgoyette uint8_t fbdimm_terms; 395d41a3cefSpgoyette uint8_t fbdimm_drivers; 396d41a3cefSpgoyette uint8_t fbdimm_tREFI; 397d41a3cefSpgoyette uint8_t fbdimm_Tcasemax; 398d41a3cefSpgoyette uint8_t fbdimm_Psi_TA_SDRAM; 399d41a3cefSpgoyette uint8_t fbdimm_DT0; 400d41a3cefSpgoyette uint8_t fbdimm_DT2N_DT2Q; 401d41a3cefSpgoyette uint8_t fbdimm_DT2P; 402d41a3cefSpgoyette uint8_t fbdimm_DT3N; 403d41a3cefSpgoyette uint8_t fbdimm_DT4R_DT4R4W; 404d41a3cefSpgoyette uint8_t fbdimm_DT5B; 405d41a3cefSpgoyette uint8_t fbdimm_DT7; 406d41a3cefSpgoyette uint8_t fbdimm_unused4[84]; 407d41a3cefSpgoyette uint16_t fbdimm_crc; 408d41a3cefSpgoyette } __packed; 409d41a3cefSpgoyette 410d41a3cefSpgoyette struct spdmem_rambus { /* Direct Rambus DRAM */ 41150d1d96aSpgoyette uint8_t rdr_len; 41250d1d96aSpgoyette uint8_t rdr_size; 41350d1d96aSpgoyette uint8_t rdr_type; 414d41a3cefSpgoyette SPD_BITFIELD( \ 415d41a3cefSpgoyette uint8_t rdr_rows:4, \ 416d41a3cefSpgoyette uint8_t rdr_cols:4, , \ 417d41a3cefSpgoyette ); 418d41a3cefSpgoyette } __packed; 419d41a3cefSpgoyette 420d41a3cefSpgoyette struct spdmem_ddr3 { /* Dual Data Rate 3 SDRAM */ 4215e0f0bcdSmsaitoh SPD_BITFIELD( \ 4225e0f0bcdSmsaitoh uint8_t ddr3_ROM_used:4, \ 4235e0f0bcdSmsaitoh uint8_t ddr3_ROM_size:3, \ 4245e0f0bcdSmsaitoh uint8_t ddr3_crccover:1, \ 4255e0f0bcdSmsaitoh ); 4265e0f0bcdSmsaitoh uint8_t ddr3_romrev; 42750d1d96aSpgoyette uint8_t ddr3_type; 428d41a3cefSpgoyette uint8_t ddr3_mod_type; 429d41a3cefSpgoyette SPD_BITFIELD( \ 430d41a3cefSpgoyette /* chipsize is offset by 28: 0 = 256M, 1 = 512M, ... */ \ 431d41a3cefSpgoyette uint8_t ddr3_chipsize:4, \ 432d41a3cefSpgoyette /* logbanks is offset by 3 */ \ 433d41a3cefSpgoyette uint8_t ddr3_logbanks:3, \ 434d41a3cefSpgoyette uint8_t ddr3_unused1:1, \ 435d41a3cefSpgoyette ); 436d41a3cefSpgoyette /* cols is offset by 9, rows offset by 12 */ 437d41a3cefSpgoyette SPD_BITFIELD( \ 438d41a3cefSpgoyette uint8_t ddr3_cols:3, \ 439d41a3cefSpgoyette uint8_t ddr3_rows:5, , \ 440d41a3cefSpgoyette ); 441d41a3cefSpgoyette SPD_BITFIELD( \ 442d41a3cefSpgoyette uint8_t ddr3_NOT15V:1, \ 443d41a3cefSpgoyette uint8_t ddr3_135V:1, \ 444d35fd4d2Smsaitoh uint8_t ddr3_125V:1, \ 445d41a3cefSpgoyette uint8_t ddr3_unused2:5 \ 446d41a3cefSpgoyette ); 447d41a3cefSpgoyette /* chipwidth in bits offset by 2: 0 = X4, 1 = X8, 2 = X16 */ 448d41a3cefSpgoyette /* physbanks is offset by 1 */ 449d41a3cefSpgoyette SPD_BITFIELD( \ 450d41a3cefSpgoyette uint8_t ddr3_chipwidth:3, \ 451d41a3cefSpgoyette uint8_t ddr3_physbanks:5, , \ 452d41a3cefSpgoyette ); 453d41a3cefSpgoyette /* datawidth in bits offset by 3: 1 = 16b, 2 = 32b, 3 = 64b */ 454d41a3cefSpgoyette SPD_BITFIELD( \ 455d41a3cefSpgoyette uint8_t ddr3_datawidth:3, \ 456d41a3cefSpgoyette uint8_t ddr3_hasECC:2, \ 457d41a3cefSpgoyette uint8_t ddr3_unused2a:3 , \ 458d41a3cefSpgoyette ); 459d41a3cefSpgoyette /* Fine time base, in pico-seconds */ 460d41a3cefSpgoyette SPD_BITFIELD( \ 461d41a3cefSpgoyette uint8_t ddr3_ftb_divisor:4, \ 462d41a3cefSpgoyette uint8_t ddr3_ftb_dividend:4, , \ 463d41a3cefSpgoyette ); 464d41a3cefSpgoyette uint8_t ddr3_mtb_dividend; /* 0x0108 = 0.1250ns */ 465d41a3cefSpgoyette uint8_t ddr3_mtb_divisor; /* 0x010f = 0.0625ns */ 466f2e2af51Smsaitoh uint8_t ddr3_tCKmin_mtb; 467d41a3cefSpgoyette uint8_t ddr3_unused3; 468d41a3cefSpgoyette uint16_t ddr3_CAS_sup; /* Bit 0 ==> CAS 4 cycles */ 469f2e2af51Smsaitoh uint8_t ddr3_tAAmin_mtb; 470d41a3cefSpgoyette uint8_t ddr3_tWRmin; 471f2e2af51Smsaitoh uint8_t ddr3_tRCDmin_mtb; 472d41a3cefSpgoyette uint8_t ddr3_tRRDmin; 473f2e2af51Smsaitoh uint8_t ddr3_tRPmin_mtb; 474d41a3cefSpgoyette SPD_BITFIELD( \ 475d41a3cefSpgoyette uint8_t ddr3_tRAS_msb:4, \ 476f2e2af51Smsaitoh uint8_t ddr3_tRCmin_mtb_msb:4, , \ 477d41a3cefSpgoyette ); 478d41a3cefSpgoyette uint8_t ddr3_tRAS_lsb; 479f2e2af51Smsaitoh uint8_t ddr3_tRCmin_mtb_lsb; 480d41a3cefSpgoyette uint8_t ddr3_tRFCmin_lsb; 481d41a3cefSpgoyette uint8_t ddr3_tRFCmin_msb; 482d41a3cefSpgoyette uint8_t ddr3_tWTRmin; 483d41a3cefSpgoyette uint8_t ddr3_tRTPmin; 484d41a3cefSpgoyette SPD_BITFIELD( \ 485d41a3cefSpgoyette uint8_t ddr3_tFAW_msb:4, , , \ 486d41a3cefSpgoyette ); 487d41a3cefSpgoyette uint8_t ddr3_tFAW_lsb; 488d41a3cefSpgoyette uint8_t ddr3_output_drvrs; 489d41a3cefSpgoyette SPD_BITFIELD( \ 490d41a3cefSpgoyette uint8_t ddr3_ext_temp_range:1, \ 491d41a3cefSpgoyette uint8_t ddr3_ext_temp_2x_refresh:1, \ 492d41a3cefSpgoyette uint8_t ddr3_asr_refresh:1, \ 493d41a3cefSpgoyette /* Bit 4 indicates on-die thermal sensor */ 494d41a3cefSpgoyette /* Bit 7 indicates Partial-Array Self-Refresh (PASR) */ 495d41a3cefSpgoyette uint8_t ddr3_unused7:5 \ 496d41a3cefSpgoyette ); 497d41a3cefSpgoyette SPD_BITFIELD( \ 498d41a3cefSpgoyette uint8_t ddr3_therm_sensor_acc:7,\ 499d41a3cefSpgoyette uint8_t ddr3_has_therm_sensor:1, , \ 500d41a3cefSpgoyette ); 501d41a3cefSpgoyette SPD_BITFIELD( \ 502d41a3cefSpgoyette uint8_t ddr3_non_std_devtype:7, \ 503d41a3cefSpgoyette uint8_t ddr3_std_device:1, , \ 504d41a3cefSpgoyette ); 505f2e2af51Smsaitoh uint8_t ddr3_tCKmin_ftb; 506f2e2af51Smsaitoh uint8_t ddr3_tAAmin_ftb; 507f2e2af51Smsaitoh uint8_t ddr3_tRCDmin_ftb; 508f2e2af51Smsaitoh uint8_t ddr3_tRPmin_ftb; 509f2e2af51Smsaitoh uint8_t ddr3_tRCmin_ftb; 510f2e2af51Smsaitoh uint8_t ddr3_unused4[2]; 511f2e2af51Smsaitoh uint8_t ddr3_MAC; 512*2744d7eeSmsaitoh uint8_t ddr3_unused4a[18]; 513d41a3cefSpgoyette uint8_t ddr3_mod_height; 514d41a3cefSpgoyette uint8_t ddr3_mod_thickness; 515d41a3cefSpgoyette uint8_t ddr3_ref_card; 516d41a3cefSpgoyette uint8_t ddr3_mapping; 517d41a3cefSpgoyette uint8_t ddr3_unused5[53]; 518d41a3cefSpgoyette uint8_t ddr3_mfgID_lsb; 519d41a3cefSpgoyette uint8_t ddr3_mfgID_msb; 520d41a3cefSpgoyette uint8_t ddr3_mfgloc; 521d41a3cefSpgoyette uint8_t ddr3_mfg_year; 522d41a3cefSpgoyette uint8_t ddr3_mfg_week; 523d41a3cefSpgoyette uint8_t ddr3_serial[4]; 524d41a3cefSpgoyette uint16_t ddr3_crc; 5254da9f6ddSsoren uint8_t ddr3_part[18]; 5264da9f6ddSsoren uint8_t ddr3_rev[2]; 5274da9f6ddSsoren uint8_t ddr3_dram_mfgID_lsb; 5284da9f6ddSsoren uint8_t ddr3_dram_mfgID_msb; 5294da9f6ddSsoren uint8_t ddr3_vendor[26]; 530d41a3cefSpgoyette } __packed; 531d41a3cefSpgoyette 53250d1d96aSpgoyette /* DDR4 info from JEDEC Standard No. 21-C, Annex L - 4.1.2.12 */ 53350d1d96aSpgoyette 53450d1d96aSpgoyette /* Module-type specific bytes - bytes 0x080 thru 0x0ff */ 53550d1d96aSpgoyette 53650d1d96aSpgoyette struct spdmem_ddr4_mod_unbuffered { 53750d1d96aSpgoyette SPD_BITFIELD( \ 53850d1d96aSpgoyette uint8_t ddr4_unbuf_mod_height:4, \ 53950d1d96aSpgoyette uint8_t ddr4_unbuf_card_ext:4, , \ 54050d1d96aSpgoyette ); 54150d1d96aSpgoyette SPD_BITFIELD( \ 54250d1d96aSpgoyette uint8_t ddr4_unbuf_max_thick_front:4, \ 54350d1d96aSpgoyette uint8_t ddr4_unbuf_max_thick_back:4, , \ 54450d1d96aSpgoyette ); 54550d1d96aSpgoyette SPD_BITFIELD( \ 54650d1d96aSpgoyette uint8_t ddr4_unbuf_refcard:5, \ 54750d1d96aSpgoyette uint8_t ddr4_unbuf_refcard_rev:2, \ 54850d1d96aSpgoyette uint8_t ddr4_unbuf_refcard_ext:1, \ 54950d1d96aSpgoyette ); 55050d1d96aSpgoyette SPD_BITFIELD( \ 55150d1d96aSpgoyette uint8_t ddr4_unbuf_mirror_mapping:1, \ 55250d1d96aSpgoyette uint8_t ddr4_unbuf_unused1:7, , \ 55350d1d96aSpgoyette ); 55450d1d96aSpgoyette uint8_t ddr4_unbuf_unused2[122]; 55550d1d96aSpgoyette uint8_t ddr4_unbuf_crc[2]; 55650d1d96aSpgoyette } __packed; 55750d1d96aSpgoyette 55850d1d96aSpgoyette struct spdmem_ddr4_mod_registered { 55950d1d96aSpgoyette SPD_BITFIELD( \ 56050d1d96aSpgoyette uint8_t ddr4_reg_mod_height:4, \ 56150d1d96aSpgoyette uint8_t ddr4_reg_card_ext:4, , \ 56250d1d96aSpgoyette ); 56350d1d96aSpgoyette SPD_BITFIELD( \ 56450d1d96aSpgoyette uint8_t ddr4_reg_max_thick_front:4, \ 56550d1d96aSpgoyette uint8_t ddr4_reg_max_thick_back:4, , \ 56650d1d96aSpgoyette ); 56750d1d96aSpgoyette SPD_BITFIELD( \ 56850d1d96aSpgoyette uint8_t ddr4_reg_refcard:5, \ 56950d1d96aSpgoyette uint8_t ddr4_reg_refcard_rev:2, \ 57050d1d96aSpgoyette uint8_t ddr4_reg_refcard_ext:1, \ 57150d1d96aSpgoyette ); 57250d1d96aSpgoyette SPD_BITFIELD( \ 57350d1d96aSpgoyette uint8_t ddr4_reg_regcnt:2, \ 57450d1d96aSpgoyette uint8_t ddr4_reg_dram_rows:2, \ 57550d1d96aSpgoyette uint8_t ddr4_reg_unused1:4, \ 57650d1d96aSpgoyette ); 57750d1d96aSpgoyette SPD_BITFIELD( \ 57850d1d96aSpgoyette uint8_t ddr4_reg_heat_spread_char:7, \ 57950d1d96aSpgoyette uint8_t ddr4_reg_heat_spread_exist:1, , \ 58050d1d96aSpgoyette ); 58150d1d96aSpgoyette uint8_t ddr4_reg_mfg_id_lsb; 58250d1d96aSpgoyette uint8_t ddr4_reg_mfg_id_msb; 58350d1d96aSpgoyette uint8_t ddr4_reg_revision; 58450d1d96aSpgoyette SPD_BITFIELD( \ 58550d1d96aSpgoyette uint8_t ddr4_reg_mirror_mapping:1, \ 58650d1d96aSpgoyette uint8_t ddr4_reg_unused2:7, , \ 58750d1d96aSpgoyette ); 58850d1d96aSpgoyette SPD_BITFIELD( \ 58950d1d96aSpgoyette uint8_t ddr4_reg_output_drive_CKE:2, \ 59050d1d96aSpgoyette uint8_t ddr4_reg_output_drive_ODT:2, \ 59150d1d96aSpgoyette uint8_t ddr4_reg_output_drive_CmdAddr:2,\ 59250d1d96aSpgoyette uint8_t ddr4_reg_output_drive_chipsel:2 \ 59350d1d96aSpgoyette ); 59450d1d96aSpgoyette SPD_BITFIELD( \ 59550d1d96aSpgoyette uint8_t ddr4_reg_output_drive_CK_Y0Y2:2,\ 59650d1d96aSpgoyette uint8_t ddr4_reg_output_drive_CK_Y1Y3:2,\ 59750d1d96aSpgoyette uint8_t ddr4_reg_unused3:4, \ 59850d1d96aSpgoyette ); 59950d1d96aSpgoyette uint8_t ddr4_reg_unused4[115]; 60050d1d96aSpgoyette uint8_t ddr4_reg_crc[2]; 60150d1d96aSpgoyette } __packed; 60250d1d96aSpgoyette 60350d1d96aSpgoyette struct spdmem_ddr4_mod_reduced_load { 60450d1d96aSpgoyette SPD_BITFIELD( \ 60550d1d96aSpgoyette uint8_t ddr4_rload_mod_height:4, \ 60650d1d96aSpgoyette uint8_t ddr4_rload_card_ext:4, , \ 60750d1d96aSpgoyette ); 60850d1d96aSpgoyette SPD_BITFIELD( \ 60950d1d96aSpgoyette uint8_t ddr4_rload_max_thick_front:4, \ 61050d1d96aSpgoyette uint8_t ddr4_rload_max_thick_back:4, , \ 61150d1d96aSpgoyette ); 61250d1d96aSpgoyette SPD_BITFIELD( \ 61350d1d96aSpgoyette uint8_t ddr4_rload_refcard:5, \ 61450d1d96aSpgoyette uint8_t ddr4_rload_refcard_rev:2, \ 61550d1d96aSpgoyette uint8_t ddr4_rload_refcard_ext:1, \ 61650d1d96aSpgoyette ); 61750d1d96aSpgoyette SPD_BITFIELD( \ 61850d1d96aSpgoyette uint8_t ddr4_rload_regcnt:2, \ 61950d1d96aSpgoyette uint8_t ddr4_rload_dram_rows:2, \ 62050d1d96aSpgoyette uint8_t ddr4_rload_unused1:4, \ 62150d1d96aSpgoyette ); 62250d1d96aSpgoyette SPD_BITFIELD( \ 62350d1d96aSpgoyette uint8_t ddr4_rload_unused2:7, \ 62450d1d96aSpgoyette uint8_t ddr4_rload_heat_spread_exist:1, , \ 62550d1d96aSpgoyette ); 62650d1d96aSpgoyette uint8_t ddr4_rload_reg_mfg_id_lsb; 62750d1d96aSpgoyette uint8_t ddr4_rload_reg_mfg_id_msb; 62850d1d96aSpgoyette uint8_t ddr4_rload_reg_revision; 62950d1d96aSpgoyette SPD_BITFIELD( \ 63050d1d96aSpgoyette uint8_t ddr4_rload_reg_mirror_mapping:1,\ 63150d1d96aSpgoyette uint8_t ddr4_rload_unused3:7, , \ 63250d1d96aSpgoyette ); 63350d1d96aSpgoyette SPD_BITFIELD( \ 63450d1d96aSpgoyette uint8_t ddr4_rload_output_drive_CKE:2, \ 63550d1d96aSpgoyette uint8_t ddr4_rload_output_drive_ODT:2, \ 63650d1d96aSpgoyette uint8_t ddr4_rload_output_drive_CmdAddr:2, \ 63750d1d96aSpgoyette uint8_t ddr4_rload_output_drive_chipsel:2 \ 63850d1d96aSpgoyette ); 63950d1d96aSpgoyette SPD_BITFIELD( \ 64050d1d96aSpgoyette uint8_t ddr4_rload_output_drive_CK_Y0Y2:2, \ 64150d1d96aSpgoyette uint8_t ddr4_rload_output_drive_CK_Y1Y3:2, \ 64250d1d96aSpgoyette uint8_t ddr4_rload_unused4:4, \ 64350d1d96aSpgoyette ); 64450d1d96aSpgoyette uint8_t ddr4_rload_dbuff_revision; 64550d1d96aSpgoyette SPD_BITFIELD( \ 64650d1d96aSpgoyette uint8_t ddr4_rload_VrefDQ_0:6, \ 64750d1d96aSpgoyette uint8_t ddr4_rload_unused5:2, , \ 64850d1d96aSpgoyette ); 64950d1d96aSpgoyette SPD_BITFIELD( \ 65050d1d96aSpgoyette uint8_t ddr4_rload_VrefDQ_1:6, \ 65150d1d96aSpgoyette uint8_t ddr4_rload_unused6:2, , \ 65250d1d96aSpgoyette ); 65350d1d96aSpgoyette SPD_BITFIELD( \ 65450d1d96aSpgoyette uint8_t ddr4_rload_VrefDQ_2:6, \ 65550d1d96aSpgoyette uint8_t ddr4_rload_unused7:2, , \ 65650d1d96aSpgoyette ); 65750d1d96aSpgoyette SPD_BITFIELD( \ 65850d1d96aSpgoyette uint8_t ddr4_rload_VrefDQ_3:6, \ 65950d1d96aSpgoyette uint8_t ddr4_rload_unused8:2, , \ 66050d1d96aSpgoyette ); 66150d1d96aSpgoyette SPD_BITFIELD( \ 66250d1d96aSpgoyette uint8_t ddr4_rload_VrefDQ_buffer:6, \ 66350d1d96aSpgoyette uint8_t ddr4_rload_unused9:2, , \ 66450d1d96aSpgoyette ); 66550d1d96aSpgoyette SPD_BITFIELD( \ 66650d1d96aSpgoyette uint8_t ddr4_rload_MDQ_Read_Term_Str_1866:3, \ 66750d1d96aSpgoyette uint8_t ddr4_rload_unused10:1, \ 66850d1d96aSpgoyette uint8_t ddr4_rload_MDQ_Drive_Str_1866:3, \ 66950d1d96aSpgoyette uint8_t ddr4_rload_unused11:1 \ 67050d1d96aSpgoyette ); 67150d1d96aSpgoyette SPD_BITFIELD( \ 67250d1d96aSpgoyette uint8_t ddr4_rload_MDQ_Read_Term_Str_2400:3, \ 67350d1d96aSpgoyette uint8_t ddr4_rload_unused12:1, \ 67450d1d96aSpgoyette uint8_t ddr4_rload_MDQ_Drive_Str_2400:3, \ 67550d1d96aSpgoyette uint8_t ddr4_rload_unused13:1 \ 67650d1d96aSpgoyette ); 67750d1d96aSpgoyette SPD_BITFIELD( \ 67850d1d96aSpgoyette uint8_t ddr4_rload_MDQ_Read_Term_Str_3200:3, \ 67950d1d96aSpgoyette uint8_t ddr4_rload_unused14:1, \ 68050d1d96aSpgoyette uint8_t ddr4_rload_MDQ_Drive_Str_3200:3, \ 68150d1d96aSpgoyette uint8_t ddr4_rload_unused15:1 \ 68250d1d96aSpgoyette ); 68350d1d96aSpgoyette SPD_BITFIELD( \ 68450d1d96aSpgoyette uint8_t ddr4_rload_DRAM_Drive_Str_1866:2, \ 68550d1d96aSpgoyette uint8_t ddr4_rload_DRAM_Drive_Str_2400:2, \ 68650d1d96aSpgoyette uint8_t ddr4_rload_DRAM_Drive_Str_3200:2, \ 68750d1d96aSpgoyette uint8_t ddr4_rload_unused16:2 \ 68850d1d96aSpgoyette ); 68950d1d96aSpgoyette SPD_BITFIELD( \ 69050d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_NOM_1866:3, \ 69150d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_WR_1866:3, \ 69250d1d96aSpgoyette uint8_t ddr4_rload_unused17:2, \ 69350d1d96aSpgoyette ); 69450d1d96aSpgoyette SPD_BITFIELD( \ 69550d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_NOM_2400:3, \ 69650d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_WR_2400:3, \ 69750d1d96aSpgoyette uint8_t ddr4_rload_unused18:2, \ 69850d1d96aSpgoyette ); 69950d1d96aSpgoyette SPD_BITFIELD( \ 70050d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_NOM_3200:3, \ 70150d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_WR_3200:3, \ 70250d1d96aSpgoyette uint8_t ddr4_rload_unused19:2, \ 70350d1d96aSpgoyette ); 70450d1d96aSpgoyette SPD_BITFIELD( \ 70550d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_PARK_01_1866:3, \ 70650d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_PARK_23_1866:3, \ 70750d1d96aSpgoyette uint8_t ddr4_rload_unused20:2, \ 70850d1d96aSpgoyette ); 70950d1d96aSpgoyette SPD_BITFIELD( \ 71050d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_PARK_01_2400:3, \ 71150d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_PARK_23_2400:3, \ 71250d1d96aSpgoyette uint8_t ddr4_rload_unused21:2, \ 71350d1d96aSpgoyette ); 71450d1d96aSpgoyette SPD_BITFIELD( \ 71550d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_PARK_01_3200:3, \ 71650d1d96aSpgoyette uint8_t ddr4_rload_DRAM_ODT_RTT_PARK_23_3200:3, \ 71750d1d96aSpgoyette uint8_t ddr4_rload_unused22:2, \ 71850d1d96aSpgoyette ); 71950d1d96aSpgoyette uint8_t ddr4_rload_unused23[99]; 72050d1d96aSpgoyette uint8_t ddr4_rload_crc[2]; 72150d1d96aSpgoyette } __packed; 72250d1d96aSpgoyette 72350d1d96aSpgoyette struct spdmem_ddr4 { /* Dual Data Rate 4 SDRAM */ 72450d1d96aSpgoyette SPD_BITFIELD( \ 72550d1d96aSpgoyette uint8_t ddr4_ROM_used:4, \ 72650d1d96aSpgoyette uint8_t ddr4_ROM_size:3, \ 72750d1d96aSpgoyette uint8_t ddr4_unused0:1, \ 72850d1d96aSpgoyette ); 72950d1d96aSpgoyette uint8_t ddr4_romrev; 73050d1d96aSpgoyette uint8_t ddr4_type; 73150d1d96aSpgoyette SPD_BITFIELD( \ 73250d1d96aSpgoyette uint8_t ddr4_mod_type:4, \ 73319d53e8dSmsaitoh uint8_t ddr4_hybrid_media:3, \ 73419d53e8dSmsaitoh uint8_t ddr4_hybrid:1, \ 73550d1d96aSpgoyette ); 73650d1d96aSpgoyette SPD_BITFIELD( \ 73750d1d96aSpgoyette /* capacity is offset by 28: 0 = 256M, 1 = 512M, ... */ \ 73850d1d96aSpgoyette uint8_t ddr4_capacity:4, \ 73950d1d96aSpgoyette /* logbanks is offset by 2 */ \ 74050d1d96aSpgoyette uint8_t ddr4_logbanks:2, \ 74150d1d96aSpgoyette /* bankgroups is offset by 0 */ 74250d1d96aSpgoyette uint8_t ddr4_bankgroups:2, \ 74350d1d96aSpgoyette ); 74450d1d96aSpgoyette /* cols is offset by 9, rows offset by 12 */ 74550d1d96aSpgoyette SPD_BITFIELD( \ 74650d1d96aSpgoyette uint8_t ddr4_cols:3, \ 74750d1d96aSpgoyette uint8_t ddr4_rows:3, \ 74850d1d96aSpgoyette uint8_t ddr4_unused2:2, \ 74950d1d96aSpgoyette ); 75050d1d96aSpgoyette SPD_BITFIELD( \ 75150d1d96aSpgoyette uint8_t ddr4_signal_loading:2, \ 75250d1d96aSpgoyette uint8_t ddr4_unused3:2, \ 75350d1d96aSpgoyette uint8_t ddr4_diecount:3, \ 75450d1d96aSpgoyette uint8_t ddr4_non_monolithic:1 \ 75550d1d96aSpgoyette ); 75650d1d96aSpgoyette SPD_BITFIELD( \ 75750d1d96aSpgoyette uint8_t ddr4_max_activate_count:4, \ 75850d1d96aSpgoyette uint8_t ddr4_max_activate_window:2, \ 75950d1d96aSpgoyette uint8_t ddr4_unused4:2, \ 76050d1d96aSpgoyette ); 76150d1d96aSpgoyette uint8_t ddr4_unused5; /* SDRAM Thermal & Refresh Options */ 76250d1d96aSpgoyette SPD_BITFIELD( \ 76350d1d96aSpgoyette uint8_t ddr4_unused6:6, \ 76450d1d96aSpgoyette uint8_t ddr4_ppr_support:2, , /* post package repair */ \ 76550d1d96aSpgoyette ); 76650d1d96aSpgoyette uint8_t ddr4_unused7; 76750d1d96aSpgoyette SPD_BITFIELD( \ 76850d1d96aSpgoyette uint8_t ddr4_dram_vdd_12:2, \ 76950d1d96aSpgoyette uint8_t ddr4_dram_vdd_tbd1:2, \ 77050d1d96aSpgoyette uint8_t ddr4_dram_vdd_tbd2:2, \ 77150d1d96aSpgoyette uint8_t ddr4_unused8:2 \ 77250d1d96aSpgoyette ); 77350d1d96aSpgoyette SPD_BITFIELD( \ 77450d1d96aSpgoyette /* device width is 0=4, 1=8, 2=16, or 4=32 bits */ \ 77550d1d96aSpgoyette uint8_t ddr4_device_width:3, \ 77650d1d96aSpgoyette /* number of package ranks is field value plus 1 */ \ 77750d1d96aSpgoyette uint8_t ddr4_package_ranks:3, \ 778e95ac17fSmsaitoh uint8_t ddr4_rank_mix:1, \ 779e95ac17fSmsaitoh uint8_t ddr4_unused9:1 \ 78050d1d96aSpgoyette ); 78150d1d96aSpgoyette SPD_BITFIELD( \ 78250d1d96aSpgoyette /* primary width is offset by 3, extension is offset by 2 */ \ 78350d1d96aSpgoyette uint8_t ddr4_primary_bus_width:3, \ 78450d1d96aSpgoyette uint8_t ddr4_bus_width_extension:2, \ 78550d1d96aSpgoyette uint8_t ddr4_unused10:3, \ 78650d1d96aSpgoyette ); 78750d1d96aSpgoyette SPD_BITFIELD( \ 78850d1d96aSpgoyette uint8_t ddr4_unused11:7, \ 78950d1d96aSpgoyette uint8_t ddr4_has_therm_sensor:1, , \ 79050d1d96aSpgoyette ); 79150d1d96aSpgoyette SPD_BITFIELD( \ 79250d1d96aSpgoyette uint8_t ddr4_ext_mod_type:4, \ 79350d1d96aSpgoyette uint8_t ddr4_unused12:4, , \ 79450d1d96aSpgoyette ); 79550d1d96aSpgoyette uint8_t ddr4_unused13; 79650d1d96aSpgoyette SPD_BITFIELD( \ 79750d1d96aSpgoyette /* units = 1ps (10**-12sec) */ \ 79850d1d96aSpgoyette uint8_t ddr4_fine_timebase:2, \ 79950d1d96aSpgoyette /* units = 125ps */ \ 80050d1d96aSpgoyette uint8_t ddr4_medium_timebase:2, , \ 80150d1d96aSpgoyette ); 80250d1d96aSpgoyette uint8_t ddr4_tCKAVGmin_mtb; 80350d1d96aSpgoyette uint8_t ddr4_tCKAVGmax_mtb; 80450d1d96aSpgoyette /* Bit 0 of CAS_supported[0 corresponds to CL=7 */ 80550d1d96aSpgoyette uint8_t ddr4_CAS_supported[4]; 80650d1d96aSpgoyette uint8_t ddr4_tAAmin_mtb; 80750d1d96aSpgoyette uint8_t ddr4_tRCDmin_mtb; 80850d1d96aSpgoyette uint8_t ddr4_tRPmin_mtb; 80950d1d96aSpgoyette SPD_BITFIELD( \ 81050d1d96aSpgoyette uint8_t ddr4_tRASmin_msb:4, \ 81150d1d96aSpgoyette uint8_t ddr4_tRCmin_mtb_msb:4, , \ 81250d1d96aSpgoyette ); 81350d1d96aSpgoyette uint8_t ddr4_tRASmin_lsb; 81450d1d96aSpgoyette uint8_t ddr4_tRCmin_mtb_lsb; 81550d1d96aSpgoyette uint8_t ddr4_tRFC1min_lsb; 81650d1d96aSpgoyette uint8_t ddr4_tRFC1min_msb; 81750d1d96aSpgoyette uint8_t ddr4_tRFC2min_lsb; 81850d1d96aSpgoyette uint8_t ddr4_tRFC2min_msb; 81950d1d96aSpgoyette uint8_t ddr4_tRFC4min_lsb; 82050d1d96aSpgoyette uint8_t ddr4_tRFC4min_msb; 82150d1d96aSpgoyette SPD_BITFIELD( \ 822c52f0d42Smsaitoh uint8_t ddr4_tFAW_mtb_msb:4, \ 823c52f0d42Smsaitoh uint8_t ddr4_unused14:4, , \ 82450d1d96aSpgoyette ); 82550d1d96aSpgoyette uint8_t ddr4_tFAWmin_mtb_lsb; 82650d1d96aSpgoyette uint8_t ddr4_tRRD_Smin_mtb; 82750d1d96aSpgoyette uint8_t ddr4_tRRD_Lmin_mtb; 82850d1d96aSpgoyette uint8_t ddr4_tCCD_Lmin_mtb; 82919d53e8dSmsaitoh uint8_t ddr4_tWR_min_msb; 83019d53e8dSmsaitoh uint8_t ddr4_tWR_min_mtb; 83119d53e8dSmsaitoh uint8_t ddr4_tWTR_min; 83219d53e8dSmsaitoh uint8_t ddr4_tWTR_Smin_mtb; 83319d53e8dSmsaitoh uint8_t ddr4_tWTR_Lmin_mtb; 83419d53e8dSmsaitoh uint8_t ddr4_unused15[14]; 83550d1d96aSpgoyette uint8_t ddr4_connector_map[18]; 83650d1d96aSpgoyette uint8_t ddr4_unused16[39]; 83750d1d96aSpgoyette uint8_t ddr4_tCCD_Lmin_ftb; 83850d1d96aSpgoyette uint8_t ddr4_tRRD_Lmin_ftb; 83950d1d96aSpgoyette uint8_t ddr4_tRRD_Smin_ftb; 84050d1d96aSpgoyette uint8_t ddr4_tRCmin_ftb; 84150d1d96aSpgoyette uint8_t ddr4_tRPmin_ftb; 84250d1d96aSpgoyette uint8_t ddr4_tRCDmin_ftb; 84350d1d96aSpgoyette uint8_t ddr4_tAAmin_ftb; 84450d1d96aSpgoyette uint8_t ddr4_tCKAVGmax_ftb; 84550d1d96aSpgoyette uint8_t ddr4_tCKAVGmin_ftb; 84650d1d96aSpgoyette uint16_t ddr4_crc; 84750d1d96aSpgoyette union { 84850d1d96aSpgoyette struct spdmem_ddr4_mod_unbuffered u2_unbuf; 84950d1d96aSpgoyette struct spdmem_ddr4_mod_registered u2_reg; 85050d1d96aSpgoyette struct spdmem_ddr4_mod_reduced_load u2_red_load; 85150d1d96aSpgoyette } ddr4_u2; 85250d1d96aSpgoyette uint8_t ddr4_unused17[64]; 85350d1d96aSpgoyette uint8_t ddr4_module_mfg_lsb; 85450d1d96aSpgoyette uint8_t ddr4_module_mfg_msb; 85550d1d96aSpgoyette uint8_t ddr4_module_mfg_loc; 85650d1d96aSpgoyette uint8_t ddr4_module_mfg_year; 85750d1d96aSpgoyette uint8_t ddr4_module_mfg_week; 85850d1d96aSpgoyette uint8_t ddr4_serial_number[4]; 85950d1d96aSpgoyette uint8_t ddr4_part_number[20]; 86050d1d96aSpgoyette uint8_t ddr4_revision_code; 86150d1d96aSpgoyette uint8_t ddr4_dram_mfgID_lsb; 86250d1d96aSpgoyette uint8_t ddr4_dram_mfgID_msb; 86350d1d96aSpgoyette uint8_t ddr4_dram_stepping; 86450d1d96aSpgoyette uint8_t ddr4_mfg_specific_data[29]; 86550d1d96aSpgoyette uint8_t ddr4_unused18[2]; 866aead28a1Sozaki-r uint8_t ddr4_user_data[128]; 86750d1d96aSpgoyette } __packed; 86850d1d96aSpgoyette 869d41a3cefSpgoyette struct spdmem { 870d41a3cefSpgoyette union { 871d41a3cefSpgoyette struct spdmem_fbdimm u1_fbd; 872d41a3cefSpgoyette struct spdmem_fpm u1_fpm; 873d41a3cefSpgoyette struct spdmem_ddr u1_ddr; 874d41a3cefSpgoyette struct spdmem_ddr2 u1_ddr2; 875d41a3cefSpgoyette struct spdmem_sdram u1_sdr; 876d41a3cefSpgoyette struct spdmem_rambus u1_rdr; 877d41a3cefSpgoyette struct spdmem_rom u1_rom; 878d41a3cefSpgoyette struct spdmem_ddr3 u1_ddr3; 87950d1d96aSpgoyette struct spdmem_ddr4 u1_ddr4; 880d41a3cefSpgoyette } sm_u1; 881d41a3cefSpgoyette } __packed; 882d41a3cefSpgoyette #define sm_fbd sm_u1.u1_fbd 883d41a3cefSpgoyette #define sm_fpm sm_u1.u1_fpm 884d41a3cefSpgoyette #define sm_ddr sm_u1.u1_ddr 885d41a3cefSpgoyette #define sm_ddr2 sm_u1.u1_ddr2 886d41a3cefSpgoyette #define sm_rdr sm_u1.u1_rdr 887d41a3cefSpgoyette #define sm_rom sm_u1.u1_rom 888d41a3cefSpgoyette #define sm_ddr3 sm_u1.u1_ddr3 889d41a3cefSpgoyette #define sm_sdr sm_u1.u1_sdr 89050d1d96aSpgoyette #define sm_ddr4 sm_u1.u1_ddr4 891d41a3cefSpgoyette 892d41a3cefSpgoyette /* some fields are in the same place for all memory types */ 893d41a3cefSpgoyette 89450d1d96aSpgoyette #define sm_len sm_fpm.fpm_len 89550d1d96aSpgoyette #define sm_size sm_fpm.fpm_size 89650d1d96aSpgoyette #define sm_type sm_fpm.fpm_type 897d41a3cefSpgoyette #define sm_cksum sm_fpm.fpm_cksum 898d41a3cefSpgoyette #define sm_config sm_fpm.fpm_config 899d41a3cefSpgoyette #define sm_voltage sm_fpm.fpm_voltage 900d41a3cefSpgoyette #define sm_refresh sm_fpm.fpm_refresh 901d41a3cefSpgoyette #define sm_selfrefresh sm_fpm.fpm_selfrefresh 902d41a3cefSpgoyette 90319d53e8dSmsaitoh #define SPDMEM_TYPE_MAXLEN 40 904d41a3cefSpgoyette 905d41a3cefSpgoyette struct spdmem_softc { 906be9c8c17Smsaitoh int (*sc_read)(struct spdmem_softc *, uint16_t, uint8_t *); 907d41a3cefSpgoyette struct spdmem sc_spd_data; 908e3bc45f1Spgoyette struct sysctllog *sc_sysctl_log; 909d41a3cefSpgoyette char sc_type[SPDMEM_TYPE_MAXLEN]; 910d41a3cefSpgoyette }; 911d41a3cefSpgoyette 912d41a3cefSpgoyette int spdmem_common_probe(struct spdmem_softc *); 913d41a3cefSpgoyette void spdmem_common_attach(struct spdmem_softc *, device_t); 914e3bc45f1Spgoyette int spdmem_common_detach(struct spdmem_softc *, device_t); 915