Home | History | Annotate | Line # | Download | only in ic
spdmem.c revision 1.38
      1  1.38  nakayama /* $NetBSD: spdmem.c,v 1.38 2022/02/02 22:43:14 nakayama Exp $ */
      2   1.1  pgoyette 
      3   1.1  pgoyette /*
      4   1.1  pgoyette  * Copyright (c) 2007 Nicolas Joly
      5   1.1  pgoyette  * Copyright (c) 2007 Paul Goyette
      6   1.1  pgoyette  * Copyright (c) 2007 Tobias Nygren
      7   1.1  pgoyette  * All rights reserved.
      8   1.1  pgoyette  *
      9   1.1  pgoyette  * Redistribution and use in source and binary forms, with or without
     10   1.1  pgoyette  * modification, are permitted provided that the following conditions
     11   1.1  pgoyette  * are met:
     12   1.1  pgoyette  * 1. Redistributions of source code must retain the above copyright
     13   1.1  pgoyette  *    notice, this list of conditions and the following disclaimer.
     14   1.1  pgoyette  * 2. Redistributions in binary form must reproduce the above copyright
     15   1.1  pgoyette  *    notice, this list of conditions and the following disclaimer in the
     16   1.1  pgoyette  *    documentation and/or other materials provided with the distribution.
     17   1.1  pgoyette  * 3. The name of the author may not be used to endorse or promote products
     18   1.1  pgoyette  *    derived from this software without specific prior written permission.
     19   1.1  pgoyette  *
     20   1.1  pgoyette  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS
     21   1.1  pgoyette  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
     22   1.1  pgoyette  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
     23   1.1  pgoyette  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
     24   1.1  pgoyette  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
     25   1.1  pgoyette  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
     26   1.1  pgoyette  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
     27   1.1  pgoyette  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
     28   1.1  pgoyette  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
     29   1.1  pgoyette  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
     30   1.1  pgoyette  * POSSIBILITY OF SUCH DAMAGE.
     31   1.1  pgoyette  */
     32   1.1  pgoyette 
     33   1.1  pgoyette /*
     34   1.1  pgoyette  * Serial Presence Detect (SPD) memory identification
     35   1.1  pgoyette  */
     36   1.1  pgoyette 
     37   1.1  pgoyette #include <sys/cdefs.h>
     38  1.38  nakayama __KERNEL_RCSID(0, "$NetBSD: spdmem.c,v 1.38 2022/02/02 22:43:14 nakayama Exp $");
     39   1.1  pgoyette 
     40   1.1  pgoyette #include <sys/param.h>
     41   1.1  pgoyette #include <sys/device.h>
     42   1.1  pgoyette #include <sys/endian.h>
     43   1.1  pgoyette #include <sys/sysctl.h>
     44   1.1  pgoyette #include <machine/bswap.h>
     45   1.1  pgoyette 
     46   1.1  pgoyette #include <dev/i2c/i2cvar.h>
     47   1.1  pgoyette #include <dev/ic/spdmemreg.h>
     48   1.1  pgoyette #include <dev/ic/spdmemvar.h>
     49   1.1  pgoyette 
     50   1.1  pgoyette /* Routines for decoding spd data */
     51   1.1  pgoyette static void decode_edofpm(const struct sysctlnode *, device_t, struct spdmem *);
     52   1.1  pgoyette static void decode_rom(const struct sysctlnode *, device_t, struct spdmem *);
     53   1.1  pgoyette static void decode_sdram(const struct sysctlnode *, device_t, struct spdmem *,
     54   1.1  pgoyette 	int);
     55   1.1  pgoyette static void decode_ddr(const struct sysctlnode *, device_t, struct spdmem *);
     56   1.1  pgoyette static void decode_ddr2(const struct sysctlnode *, device_t, struct spdmem *);
     57   1.1  pgoyette static void decode_ddr3(const struct sysctlnode *, device_t, struct spdmem *);
     58  1.13  pgoyette static void decode_ddr4(const struct sysctlnode *, device_t, struct spdmem *);
     59   1.1  pgoyette static void decode_fbdimm(const struct sysctlnode *, device_t, struct spdmem *);
     60   1.1  pgoyette 
     61   1.3  pgoyette static void decode_size_speed(device_t, const struct sysctlnode *,
     62   1.3  pgoyette 			      int, int, int, int, bool, const char *, int);
     63   1.1  pgoyette static void decode_voltage_refresh(device_t, struct spdmem *);
     64   1.1  pgoyette 
     65   1.1  pgoyette #define IS_RAMBUS_TYPE (s->sm_len < 4)
     66   1.1  pgoyette 
     67  1.12      matt static const char* const spdmem_basic_types[] = {
     68   1.1  pgoyette 	"unknown",
     69   1.1  pgoyette 	"FPM",
     70   1.1  pgoyette 	"EDO",
     71   1.1  pgoyette 	"Pipelined Nibble",
     72   1.1  pgoyette 	"SDRAM",
     73   1.1  pgoyette 	"ROM",
     74   1.1  pgoyette 	"DDR SGRAM",
     75   1.1  pgoyette 	"DDR SDRAM",
     76   1.1  pgoyette 	"DDR2 SDRAM",
     77   1.1  pgoyette 	"DDR2 SDRAM FB",
     78   1.1  pgoyette 	"DDR2 SDRAM FB Probe",
     79  1.12      matt 	"DDR3 SDRAM",
     80  1.20   msaitoh 	"DDR4 SDRAM",
     81  1.20   msaitoh 	"unknown",
     82  1.20   msaitoh 	"DDR4E SDRAM",
     83  1.20   msaitoh 	"LPDDR3 SDRAM",
     84  1.38  nakayama 	"LPDDR4 SDRAM",
     85  1.36   msaitoh 	"LPDDR4X SDRAM",
     86  1.38  nakayama 	"DDR5 SDRAM"
     87   1.1  pgoyette };
     88   1.1  pgoyette 
     89  1.13  pgoyette static const char* const spdmem_ddr4_module_types[] = {
     90  1.13  pgoyette 	"DDR4 Extended",
     91  1.13  pgoyette 	"DDR4 RDIMM",
     92  1.13  pgoyette 	"DDR4 UDIMM",
     93  1.13  pgoyette 	"DDR4 SO-DIMM",
     94  1.13  pgoyette 	"DDR4 Load-Reduced DIMM",
     95  1.13  pgoyette 	"DDR4 Mini-RDIMM",
     96  1.13  pgoyette 	"DDR4 Mini-UDIMM",
     97  1.13  pgoyette 	"DDR4 Reserved",
     98  1.13  pgoyette 	"DDR4 72Bit SO-RDIMM",
     99  1.13  pgoyette 	"DDR4 72Bit SO-UDIMM",
    100  1.13  pgoyette 	"DDR4 Undefined",
    101  1.13  pgoyette 	"DDR4 Reserved",
    102  1.13  pgoyette 	"DDR4 16Bit SO-DIMM",
    103  1.13  pgoyette 	"DDR4 32Bit SO-DIMM",
    104  1.13  pgoyette 	"DDR4 Reserved",
    105  1.13  pgoyette 	"DDR4 Undefined"
    106  1.13  pgoyette };
    107  1.13  pgoyette 
    108  1.12      matt static const char* const spdmem_superset_types[] = {
    109   1.1  pgoyette 	"unknown",
    110   1.1  pgoyette 	"ESDRAM",
    111   1.1  pgoyette 	"DDR ESDRAM",
    112   1.1  pgoyette 	"PEM EDO",
    113   1.1  pgoyette 	"PEM SDRAM"
    114   1.1  pgoyette };
    115   1.1  pgoyette 
    116  1.12      matt static const char* const spdmem_voltage_types[] = {
    117   1.1  pgoyette 	"TTL (5V tolerant)",
    118   1.1  pgoyette 	"LvTTL (not 5V tolerant)",
    119   1.1  pgoyette 	"HSTL 1.5V",
    120   1.1  pgoyette 	"SSTL 3.3V",
    121   1.1  pgoyette 	"SSTL 2.5V",
    122   1.1  pgoyette 	"SSTL 1.8V"
    123   1.1  pgoyette };
    124   1.1  pgoyette 
    125  1.12      matt static const char* const spdmem_refresh_types[] = {
    126   1.1  pgoyette 	"15.625us",
    127   1.1  pgoyette 	"3.9us",
    128   1.1  pgoyette 	"7.8us",
    129   1.1  pgoyette 	"31.3us",
    130   1.1  pgoyette 	"62.5us",
    131   1.1  pgoyette 	"125us"
    132   1.1  pgoyette };
    133   1.1  pgoyette 
    134  1.12      matt static const char* const spdmem_parity_types[] = {
    135   1.1  pgoyette 	"no parity or ECC",
    136   1.1  pgoyette 	"data parity",
    137   1.1  pgoyette 	"data ECC",
    138   1.1  pgoyette 	"data parity and ECC",
    139   1.1  pgoyette 	"cmd/addr parity",
    140   1.1  pgoyette 	"cmd/addr/data parity",
    141   1.1  pgoyette 	"cmd/addr parity, data ECC",
    142   1.1  pgoyette 	"cmd/addr/data parity, data ECC"
    143   1.1  pgoyette };
    144   1.1  pgoyette 
    145  1.13  pgoyette int spd_rom_sizes[] = { 0, 128, 256, 384, 512 };
    146  1.13  pgoyette 
    147  1.13  pgoyette 
    148   1.1  pgoyette /* Cycle time fractional values (units of .001 ns) for DDR2 SDRAM */
    149   1.1  pgoyette static const uint16_t spdmem_cycle_frac[] = {
    150   1.1  pgoyette 	0, 100, 200, 300, 400, 500, 600, 700, 800, 900,
    151   1.1  pgoyette 	250, 333, 667, 750, 999, 999
    152   1.1  pgoyette };
    153   1.1  pgoyette 
    154   1.1  pgoyette /* Format string for timing info */
    155   1.5       wiz #define	LATENCY	"tAA-tRCD-tRP-tRAS: %d-%d-%d-%d\n"
    156   1.1  pgoyette 
    157   1.1  pgoyette /* CRC functions used for certain memory types */
    158   1.1  pgoyette 
    159  1.21   msaitoh static uint16_t
    160  1.21   msaitoh spdcrc16(struct spdmem_softc *sc, int count)
    161   1.1  pgoyette {
    162   1.1  pgoyette 	uint16_t crc;
    163   1.1  pgoyette 	int i, j;
    164   1.1  pgoyette 	uint8_t val;
    165   1.1  pgoyette 	crc = 0;
    166   1.1  pgoyette 	for (j = 0; j <= count; j++) {
    167  1.21   msaitoh 		(sc->sc_read)(sc, j, &val);
    168   1.1  pgoyette 		crc = crc ^ val << 8;
    169   1.1  pgoyette 		for (i = 0; i < 8; ++i)
    170   1.1  pgoyette 			if (crc & 0x8000)
    171   1.1  pgoyette 				crc = crc << 1 ^ 0x1021;
    172   1.1  pgoyette 			else
    173   1.1  pgoyette 				crc = crc << 1;
    174   1.1  pgoyette 	}
    175   1.1  pgoyette 	return (crc & 0xFFFF);
    176   1.1  pgoyette }
    177   1.1  pgoyette 
    178   1.1  pgoyette int
    179   1.1  pgoyette spdmem_common_probe(struct spdmem_softc *sc)
    180   1.1  pgoyette {
    181   1.1  pgoyette 	int cksum = 0;
    182   1.1  pgoyette 	uint8_t i, val, spd_type;
    183   1.1  pgoyette 	int spd_len, spd_crc_cover;
    184   1.1  pgoyette 	uint16_t crc_calc, crc_spd;
    185   1.1  pgoyette 
    186  1.21   msaitoh 	/* Read failed means a device doesn't exist */
    187  1.21   msaitoh 	if ((sc->sc_read)(sc, 2, &spd_type) != 0)
    188  1.21   msaitoh 		return 0;
    189   1.1  pgoyette 
    190  1.22   msaitoh 	/* Memory type should not be 0 */
    191  1.22   msaitoh 	if (spd_type == 0x00)
    192  1.22   msaitoh 		return 0;
    193  1.22   msaitoh 
    194   1.1  pgoyette 	/* For older memory types, validate the checksum over 1st 63 bytes */
    195   1.1  pgoyette 	if (spd_type <= SPDMEM_MEMTYPE_DDR2SDRAM) {
    196  1.21   msaitoh 		for (i = 0; i < 63; i++) {
    197  1.21   msaitoh 			(sc->sc_read)(sc, i, &val);
    198  1.21   msaitoh 			cksum += val;
    199  1.21   msaitoh 		}
    200   1.1  pgoyette 
    201  1.21   msaitoh 		(sc->sc_read)(sc, 63, &val);
    202   1.1  pgoyette 
    203  1.21   msaitoh 		if ((cksum & 0xff) != val) {
    204   1.1  pgoyette 			aprint_debug("spd checksum failed, calc = 0x%02x, "
    205   1.1  pgoyette 				     "spd = 0x%02x\n", cksum, val);
    206   1.1  pgoyette 			return 0;
    207   1.1  pgoyette 		} else
    208   1.1  pgoyette 			return 1;
    209   1.1  pgoyette 	}
    210   1.1  pgoyette 
    211   1.1  pgoyette 	/* For DDR3 and FBDIMM, verify the CRC */
    212   1.1  pgoyette 	else if (spd_type <= SPDMEM_MEMTYPE_DDR3SDRAM) {
    213  1.21   msaitoh 		(sc->sc_read)(sc, 0, &val);
    214  1.21   msaitoh 		spd_len = val;
    215   1.2  pgoyette 		if (spd_len & SPDMEM_SPDCRC_116)
    216   1.1  pgoyette 			spd_crc_cover = 116;
    217   1.1  pgoyette 		else
    218   1.1  pgoyette 			spd_crc_cover = 125;
    219   1.1  pgoyette 		switch (spd_len & SPDMEM_SPDLEN_MASK) {
    220   1.1  pgoyette 		case SPDMEM_SPDLEN_128:
    221   1.1  pgoyette 			spd_len = 128;
    222   1.1  pgoyette 			break;
    223   1.1  pgoyette 		case SPDMEM_SPDLEN_176:
    224   1.1  pgoyette 			spd_len = 176;
    225   1.1  pgoyette 			break;
    226   1.1  pgoyette 		case SPDMEM_SPDLEN_256:
    227   1.1  pgoyette 			spd_len = 256;
    228   1.1  pgoyette 			break;
    229   1.1  pgoyette 		default:
    230   1.1  pgoyette 			return 0;
    231   1.1  pgoyette 		}
    232   1.1  pgoyette 		if (spd_crc_cover > spd_len)
    233   1.1  pgoyette 			return 0;
    234   1.1  pgoyette 		crc_calc = spdcrc16(sc, spd_crc_cover);
    235  1.21   msaitoh 		(sc->sc_read)(sc, 127, &val);
    236  1.21   msaitoh 		crc_spd = val << 8;
    237  1.21   msaitoh 		(sc->sc_read)(sc, 126, &val);
    238  1.21   msaitoh 		crc_spd |= val;
    239   1.1  pgoyette 		if (crc_calc != crc_spd) {
    240   1.1  pgoyette 			aprint_debug("crc16 failed, covers %d bytes, "
    241   1.1  pgoyette 				     "calc = 0x%04x, spd = 0x%04x\n",
    242   1.1  pgoyette 				     spd_crc_cover, crc_calc, crc_spd);
    243   1.1  pgoyette 			return 0;
    244   1.1  pgoyette 		}
    245   1.1  pgoyette 		return 1;
    246  1.13  pgoyette 	} else if (spd_type == SPDMEM_MEMTYPE_DDR4SDRAM) {
    247  1.21   msaitoh 		(sc->sc_read)(sc, 0, &val);
    248  1.21   msaitoh 		spd_len = val & 0x0f;
    249  1.23      maya 		if ((unsigned int)spd_len >= __arraycount(spd_rom_sizes))
    250  1.13  pgoyette 			return 0;
    251  1.13  pgoyette 		spd_len = spd_rom_sizes[spd_len];
    252  1.17   msaitoh 		spd_crc_cover = 125; /* For byte 0 to 125 */
    253  1.13  pgoyette 		if (spd_crc_cover > spd_len)
    254  1.13  pgoyette 			return 0;
    255  1.13  pgoyette 		crc_calc = spdcrc16(sc, spd_crc_cover);
    256  1.21   msaitoh 		(sc->sc_read)(sc, 127, &val);
    257  1.21   msaitoh 		crc_spd = val << 8;
    258  1.21   msaitoh 		(sc->sc_read)(sc, 126, &val);
    259  1.21   msaitoh 		crc_spd |= val;
    260  1.13  pgoyette 		if (crc_calc != crc_spd) {
    261  1.13  pgoyette 			aprint_debug("crc16 failed, covers %d bytes, "
    262  1.13  pgoyette 				     "calc = 0x%04x, spd = 0x%04x\n",
    263  1.13  pgoyette 				     spd_crc_cover, crc_calc, crc_spd);
    264  1.13  pgoyette 			return 0;
    265  1.13  pgoyette 		}
    266  1.13  pgoyette 		/*
    267  1.13  pgoyette 		 * We probably could also verify the CRC for the other
    268  1.13  pgoyette 		 * "pages" of SPD data in blocks 1 and 2, but we'll do
    269  1.13  pgoyette 		 * it some other time.
    270  1.13  pgoyette 		 */
    271  1.13  pgoyette 		return 1;
    272  1.37   msaitoh 	} else if (spd_type == SPDMEM_MEMTYPE_DDR5SDRAM) {
    273  1.37   msaitoh 		/* XXX Need Datasheet. */
    274  1.37   msaitoh 		(sc->sc_read)(sc, 0, &val);
    275  1.37   msaitoh 		spd_len = val & 0x0f;
    276  1.37   msaitoh 		if ((unsigned int)spd_len >= __arraycount(spd_rom_sizes))
    277  1.37   msaitoh 			return 0;
    278  1.37   msaitoh 		aprint_verbose("DDR5 SPD ROM?\n");
    279  1.37   msaitoh 		return 0;
    280  1.22   msaitoh 	}
    281   1.1  pgoyette 
    282   1.1  pgoyette 	/* For unrecognized memory types, don't match at all */
    283   1.1  pgoyette 	return 0;
    284   1.1  pgoyette }
    285   1.1  pgoyette 
    286   1.1  pgoyette void
    287   1.1  pgoyette spdmem_common_attach(struct spdmem_softc *sc, device_t self)
    288   1.1  pgoyette {
    289   1.1  pgoyette 	struct spdmem *s = &(sc->sc_spd_data);
    290   1.1  pgoyette 	const char *type;
    291   1.1  pgoyette 	const char *rambus_rev = "Reserved";
    292   1.1  pgoyette 	int dimm_size;
    293   1.3  pgoyette 	unsigned int i, spd_len, spd_size;
    294   1.1  pgoyette 	const struct sysctlnode *node = NULL;
    295   1.1  pgoyette 
    296  1.21   msaitoh 	(sc->sc_read)(sc, 0, &s->sm_len);
    297  1.21   msaitoh 	(sc->sc_read)(sc, 1, &s->sm_size);
    298  1.21   msaitoh 	(sc->sc_read)(sc, 2, &s->sm_type);
    299   1.1  pgoyette 
    300  1.13  pgoyette 	if (s->sm_type == SPDMEM_MEMTYPE_DDR4SDRAM) {
    301  1.13  pgoyette 		/*
    302  1.13  pgoyette 		 * An even newer encoding with one byte holding both
    303  1.13  pgoyette 		 * the used-size and capacity values
    304  1.13  pgoyette 		 */
    305  1.13  pgoyette 		spd_len = s->sm_len & 0x0f;
    306  1.13  pgoyette 		spd_size = (s->sm_len >> 4) & 0x07;
    307  1.13  pgoyette 
    308  1.13  pgoyette 		spd_len = spd_rom_sizes[spd_len];
    309  1.13  pgoyette 		spd_size *= 512;
    310  1.13  pgoyette 
    311  1.13  pgoyette 	} else if (s->sm_type >= SPDMEM_MEMTYPE_FBDIMM) {
    312  1.13  pgoyette 		/*
    313  1.13  pgoyette 		 * FBDIMM and DDR3 (and probably all newer) have a different
    314  1.13  pgoyette 		 * encoding of the SPD EEPROM used/total sizes
    315  1.13  pgoyette 		 */
    316   1.1  pgoyette 		spd_size = 64 << (s->sm_len & SPDMEM_SPDSIZE_MASK);
    317   1.1  pgoyette 		switch (s->sm_len & SPDMEM_SPDLEN_MASK) {
    318   1.1  pgoyette 		case SPDMEM_SPDLEN_128:
    319   1.1  pgoyette 			spd_len = 128;
    320   1.1  pgoyette 			break;
    321   1.1  pgoyette 		case SPDMEM_SPDLEN_176:
    322   1.1  pgoyette 			spd_len = 176;
    323   1.1  pgoyette 			break;
    324   1.1  pgoyette 		case SPDMEM_SPDLEN_256:
    325   1.1  pgoyette 			spd_len = 256;
    326   1.1  pgoyette 			break;
    327   1.1  pgoyette 		default:
    328   1.1  pgoyette 			spd_len = 64;
    329   1.1  pgoyette 			break;
    330   1.1  pgoyette 		}
    331   1.1  pgoyette 	} else {
    332   1.1  pgoyette 		spd_size = 1 << s->sm_size;
    333   1.1  pgoyette 		spd_len = s->sm_len;
    334   1.1  pgoyette 		if (spd_len < 64)
    335   1.1  pgoyette 			spd_len = 64;
    336   1.1  pgoyette 	}
    337   1.1  pgoyette 	if (spd_len > spd_size)
    338   1.1  pgoyette 		spd_len = spd_size;
    339   1.1  pgoyette 	if (spd_len > sizeof(struct spdmem))
    340   1.1  pgoyette 		spd_len = sizeof(struct spdmem);
    341   1.1  pgoyette 	for (i = 3; i < spd_len; i++)
    342  1.21   msaitoh 		(sc->sc_read)(sc, i, &((uint8_t *)s)[i]);
    343   1.1  pgoyette 
    344   1.1  pgoyette 	/*
    345   1.1  pgoyette 	 * Setup our sysctl subtree, hw.spdmemN
    346   1.1  pgoyette 	 */
    347   1.3  pgoyette 	sc->sc_sysctl_log = NULL;
    348   1.9     pooka 	sysctl_createv(&sc->sc_sysctl_log, 0, NULL, &node,
    349   1.9     pooka 	    0, CTLTYPE_NODE,
    350   1.9     pooka 	    device_xname(self), NULL, NULL, 0, NULL, 0,
    351   1.9     pooka 	    CTL_HW, CTL_CREATE, CTL_EOL);
    352   1.1  pgoyette 	if (node != NULL && spd_len != 0)
    353  1.33   msaitoh 		sysctl_createv(&sc->sc_sysctl_log, 0, NULL, NULL,
    354  1.33   msaitoh 		    0,
    355  1.33   msaitoh 		    CTLTYPE_STRUCT, "spd_data",
    356   1.1  pgoyette 		    SYSCTL_DESCR("raw spd data"), NULL,
    357  1.33   msaitoh 		    0, s, spd_len,
    358  1.33   msaitoh 		    CTL_HW, node->sysctl_num, CTL_CREATE, CTL_EOL);
    359   1.1  pgoyette 
    360   1.1  pgoyette 	/*
    361   1.1  pgoyette 	 * Decode and print key SPD contents
    362   1.1  pgoyette 	 */
    363   1.1  pgoyette 	if (IS_RAMBUS_TYPE) {
    364   1.1  pgoyette 		if (s->sm_type == SPDMEM_MEMTYPE_RAMBUS)
    365   1.1  pgoyette 			type = "Rambus";
    366   1.1  pgoyette 		else if (s->sm_type == SPDMEM_MEMTYPE_DIRECTRAMBUS)
    367   1.1  pgoyette 			type = "Direct Rambus";
    368   1.1  pgoyette 		else
    369   1.1  pgoyette 			type = "Rambus (unknown)";
    370   1.1  pgoyette 
    371   1.1  pgoyette 		switch (s->sm_len) {
    372   1.1  pgoyette 		case 0:
    373   1.1  pgoyette 			rambus_rev = "Invalid";
    374   1.1  pgoyette 			break;
    375   1.1  pgoyette 		case 1:
    376   1.1  pgoyette 			rambus_rev = "0.7";
    377   1.1  pgoyette 			break;
    378   1.1  pgoyette 		case 2:
    379   1.1  pgoyette 			rambus_rev = "1.0";
    380   1.1  pgoyette 			break;
    381   1.1  pgoyette 		default:
    382   1.1  pgoyette 			rambus_rev = "Reserved";
    383   1.1  pgoyette 			break;
    384   1.1  pgoyette 		}
    385   1.1  pgoyette 	} else {
    386   1.1  pgoyette 		if (s->sm_type < __arraycount(spdmem_basic_types))
    387   1.1  pgoyette 			type = spdmem_basic_types[s->sm_type];
    388   1.1  pgoyette 		else
    389   1.1  pgoyette 			type = "unknown memory type";
    390   1.1  pgoyette 
    391   1.1  pgoyette 		if (s->sm_type == SPDMEM_MEMTYPE_EDO &&
    392   1.1  pgoyette 		    s->sm_fpm.fpm_superset == SPDMEM_SUPERSET_EDO_PEM)
    393   1.1  pgoyette 			type = spdmem_superset_types[SPDMEM_SUPERSET_EDO_PEM];
    394   1.1  pgoyette 		if (s->sm_type == SPDMEM_MEMTYPE_SDRAM &&
    395   1.1  pgoyette 		    s->sm_sdr.sdr_superset == SPDMEM_SUPERSET_SDRAM_PEM)
    396   1.1  pgoyette 			type = spdmem_superset_types[SPDMEM_SUPERSET_SDRAM_PEM];
    397   1.1  pgoyette 		if (s->sm_type == SPDMEM_MEMTYPE_DDRSDRAM &&
    398   1.1  pgoyette 		    s->sm_ddr.ddr_superset == SPDMEM_SUPERSET_DDR_ESDRAM)
    399   1.1  pgoyette 			type =
    400   1.1  pgoyette 			    spdmem_superset_types[SPDMEM_SUPERSET_DDR_ESDRAM];
    401   1.1  pgoyette 		if (s->sm_type == SPDMEM_MEMTYPE_SDRAM &&
    402   1.1  pgoyette 		    s->sm_sdr.sdr_superset == SPDMEM_SUPERSET_ESDRAM) {
    403   1.1  pgoyette 			type = spdmem_superset_types[SPDMEM_SUPERSET_ESDRAM];
    404   1.1  pgoyette 		}
    405  1.13  pgoyette 		if (s->sm_type == SPDMEM_MEMTYPE_DDR4SDRAM &&
    406  1.13  pgoyette 		    s->sm_ddr4.ddr4_mod_type <
    407  1.13  pgoyette 				__arraycount(spdmem_ddr4_module_types)) {
    408  1.13  pgoyette 			type = spdmem_ddr4_module_types[s->sm_ddr4.ddr4_mod_type];
    409  1.13  pgoyette 		}
    410   1.1  pgoyette 	}
    411   1.1  pgoyette 
    412   1.1  pgoyette 	strlcpy(sc->sc_type, type, SPDMEM_TYPE_MAXLEN);
    413  1.20   msaitoh 
    414  1.20   msaitoh 	if (s->sm_type == SPDMEM_MEMTYPE_DDR4SDRAM) {
    415  1.20   msaitoh 		/*
    416  1.20   msaitoh 		 * The latest spec (DDR4 SPD Document Release 3) defines
    417  1.20   msaitoh 		 * NVDIMM Hybrid only.
    418  1.20   msaitoh 		 */
    419  1.20   msaitoh 		if ((s->sm_ddr4.ddr4_hybrid)
    420  1.20   msaitoh 		    && (s->sm_ddr4.ddr4_hybrid_media == 1))
    421  1.20   msaitoh 			strlcat(sc->sc_type, " NVDIMM hybrid",
    422  1.20   msaitoh 			    SPDMEM_TYPE_MAXLEN);
    423  1.20   msaitoh 	}
    424  1.33   msaitoh 
    425   1.1  pgoyette 	if (node != NULL)
    426   1.3  pgoyette 		sysctl_createv(&sc->sc_sysctl_log, 0, NULL, NULL,
    427   1.1  pgoyette 		    0,
    428   1.1  pgoyette 		    CTLTYPE_STRING, "mem_type",
    429   1.1  pgoyette 		    SYSCTL_DESCR("memory module type"), NULL,
    430   1.1  pgoyette 		    0, sc->sc_type, 0,
    431   1.1  pgoyette 		    CTL_HW, node->sysctl_num, CTL_CREATE, CTL_EOL);
    432   1.1  pgoyette 
    433   1.1  pgoyette 	if (IS_RAMBUS_TYPE) {
    434   1.8     soren 		aprint_naive("\n");
    435   1.8     soren 		aprint_normal("\n");
    436   1.8     soren 		aprint_normal_dev(self, "%s, SPD Revision %s", type, rambus_rev);
    437   1.1  pgoyette 		dimm_size = 1 << (s->sm_rdr.rdr_rows + s->sm_rdr.rdr_cols - 13);
    438   1.1  pgoyette 		if (dimm_size >= 1024)
    439   1.1  pgoyette 			aprint_normal(", %dGB\n", dimm_size / 1024);
    440   1.1  pgoyette 		else
    441   1.1  pgoyette 			aprint_normal(", %dMB\n", dimm_size);
    442   1.1  pgoyette 
    443   1.1  pgoyette 		/* No further decode for RAMBUS memory */
    444   1.1  pgoyette 		return;
    445   1.1  pgoyette 	}
    446   1.1  pgoyette 	switch (s->sm_type) {
    447   1.1  pgoyette 	case SPDMEM_MEMTYPE_EDO:
    448   1.1  pgoyette 	case SPDMEM_MEMTYPE_FPM:
    449   1.1  pgoyette 		decode_edofpm(node, self, s);
    450   1.1  pgoyette 		break;
    451   1.1  pgoyette 	case SPDMEM_MEMTYPE_ROM:
    452   1.1  pgoyette 		decode_rom(node, self, s);
    453   1.1  pgoyette 		break;
    454   1.1  pgoyette 	case SPDMEM_MEMTYPE_SDRAM:
    455   1.1  pgoyette 		decode_sdram(node, self, s, spd_len);
    456   1.1  pgoyette 		break;
    457   1.1  pgoyette 	case SPDMEM_MEMTYPE_DDRSDRAM:
    458   1.1  pgoyette 		decode_ddr(node, self, s);
    459   1.1  pgoyette 		break;
    460   1.1  pgoyette 	case SPDMEM_MEMTYPE_DDR2SDRAM:
    461   1.1  pgoyette 		decode_ddr2(node, self, s);
    462   1.1  pgoyette 		break;
    463   1.1  pgoyette 	case SPDMEM_MEMTYPE_DDR3SDRAM:
    464   1.1  pgoyette 		decode_ddr3(node, self, s);
    465   1.1  pgoyette 		break;
    466   1.1  pgoyette 	case SPDMEM_MEMTYPE_FBDIMM:
    467   1.1  pgoyette 	case SPDMEM_MEMTYPE_FBDIMM_PROBE:
    468   1.1  pgoyette 		decode_fbdimm(node, self, s);
    469   1.1  pgoyette 		break;
    470  1.13  pgoyette 	case SPDMEM_MEMTYPE_DDR4SDRAM:
    471  1.13  pgoyette 		decode_ddr4(node, self, s);
    472  1.13  pgoyette 		break;
    473   1.1  pgoyette 	}
    474   1.8     soren 
    475   1.8     soren 	/* Dump SPD */
    476   1.8     soren 	for (i = 0; i < spd_len;  i += 16) {
    477   1.8     soren 		unsigned int j, k;
    478   1.8     soren 		aprint_debug_dev(self, "0x%02x:", i);
    479   1.8     soren 		k = (spd_len > (i + 16)) ? i + 16 : spd_len;
    480   1.8     soren 		for (j = i; j < k; j++)
    481   1.8     soren 			aprint_debug(" %02x", ((uint8_t *)s)[j]);
    482   1.8     soren 		aprint_debug("\n");
    483   1.8     soren 	}
    484   1.1  pgoyette }
    485   1.1  pgoyette 
    486   1.3  pgoyette int
    487   1.3  pgoyette spdmem_common_detach(struct spdmem_softc *sc, device_t self)
    488   1.3  pgoyette {
    489   1.3  pgoyette 	sysctl_teardown(&sc->sc_sysctl_log);
    490   1.3  pgoyette 
    491   1.3  pgoyette 	return 0;
    492   1.3  pgoyette }
    493   1.3  pgoyette 
    494   1.1  pgoyette static void
    495   1.3  pgoyette decode_size_speed(device_t self, const struct sysctlnode *node,
    496   1.3  pgoyette 		  int dimm_size, int cycle_time, int d_clk, int bits,
    497   1.3  pgoyette 		  bool round, const char *ddr_type_string, int speed)
    498   1.1  pgoyette {
    499   1.1  pgoyette 	int p_clk;
    500   1.7       chs 	struct spdmem_softc *sc = device_private(self);
    501   1.1  pgoyette 
    502   1.1  pgoyette 	if (dimm_size < 1024)
    503   1.1  pgoyette 		aprint_normal("%dMB", dimm_size);
    504   1.1  pgoyette 	else
    505   1.1  pgoyette 		aprint_normal("%dGB", dimm_size / 1024);
    506   1.1  pgoyette 	if (node != NULL)
    507   1.3  pgoyette 		sysctl_createv(&sc->sc_sysctl_log, 0, NULL, NULL,
    508   1.1  pgoyette 		    CTLFLAG_IMMEDIATE,
    509   1.1  pgoyette 		    CTLTYPE_INT, "size",
    510   1.1  pgoyette 		    SYSCTL_DESCR("module size in MB"), NULL,
    511   1.1  pgoyette 		    dimm_size, NULL, 0,
    512   1.1  pgoyette 		    CTL_HW, node->sysctl_num, CTL_CREATE, CTL_EOL);
    513   1.1  pgoyette 
    514   1.1  pgoyette 	if (cycle_time == 0) {
    515   1.1  pgoyette 		aprint_normal("\n");
    516   1.1  pgoyette 		return;
    517   1.1  pgoyette 	}
    518   1.1  pgoyette 
    519   1.1  pgoyette 	/*
    520   1.1  pgoyette 	 * Calculate p_clk first, since for DDR3 we need maximum significance.
    521   1.1  pgoyette 	 * DDR3 rating is not rounded to a multiple of 100.  This results in
    522   1.1  pgoyette 	 * cycle_time of 1.5ns displayed as PC3-10666.
    523   1.1  pgoyette 	 *
    524   1.1  pgoyette 	 * For SDRAM, the speed is provided by the caller so we use it.
    525   1.1  pgoyette 	 */
    526   1.1  pgoyette 	d_clk *= 1000 * 1000;
    527   1.1  pgoyette 	if (speed)
    528   1.1  pgoyette 		p_clk = speed;
    529   1.1  pgoyette 	else
    530   1.1  pgoyette 		p_clk = (d_clk * bits) / 8 / cycle_time;
    531   1.1  pgoyette 	d_clk = ((d_clk + cycle_time / 2) ) / cycle_time;
    532   1.1  pgoyette 	if (round) {
    533   1.1  pgoyette 		if ((p_clk % 100) >= 50)
    534   1.1  pgoyette 			p_clk += 50;
    535   1.1  pgoyette 		p_clk -= p_clk % 100;
    536   1.1  pgoyette 	}
    537   1.1  pgoyette 	aprint_normal(", %dMHz (%s-%d)\n",
    538   1.1  pgoyette 		      d_clk, ddr_type_string, p_clk);
    539   1.1  pgoyette 	if (node != NULL)
    540   1.3  pgoyette 		sysctl_createv(&sc->sc_sysctl_log, 0, NULL, NULL,
    541   1.1  pgoyette 			       CTLFLAG_IMMEDIATE,
    542   1.1  pgoyette 			       CTLTYPE_INT, "speed",
    543   1.1  pgoyette 			       SYSCTL_DESCR("memory speed in MHz"),
    544   1.1  pgoyette 			       NULL, d_clk, NULL, 0,
    545   1.1  pgoyette 			       CTL_HW, node->sysctl_num, CTL_CREATE, CTL_EOL);
    546   1.1  pgoyette }
    547   1.1  pgoyette 
    548   1.1  pgoyette static void
    549   1.1  pgoyette decode_voltage_refresh(device_t self, struct spdmem *s)
    550   1.1  pgoyette {
    551   1.1  pgoyette 	const char *voltage, *refresh;
    552   1.1  pgoyette 
    553   1.1  pgoyette 	if (s->sm_voltage < __arraycount(spdmem_voltage_types))
    554   1.1  pgoyette 		voltage = spdmem_voltage_types[s->sm_voltage];
    555   1.1  pgoyette 	else
    556   1.1  pgoyette 		voltage = "unknown";
    557   1.1  pgoyette 
    558   1.1  pgoyette 	if (s->sm_refresh < __arraycount(spdmem_refresh_types))
    559   1.1  pgoyette 		refresh = spdmem_refresh_types[s->sm_refresh];
    560   1.1  pgoyette 	else
    561   1.1  pgoyette 		refresh = "unknown";
    562   1.1  pgoyette 
    563   1.1  pgoyette 	aprint_verbose_dev(self, "voltage %s, refresh time %s%s\n",
    564   1.1  pgoyette 			voltage, refresh,
    565   1.1  pgoyette 			s->sm_selfrefresh?" (self-refreshing)":"");
    566   1.1  pgoyette }
    567   1.1  pgoyette 
    568   1.1  pgoyette static void
    569  1.18   msaitoh decode_edofpm(const struct sysctlnode *node, device_t self, struct spdmem *s)
    570  1.18   msaitoh {
    571  1.18   msaitoh 
    572   1.8     soren 	aprint_naive("\n");
    573   1.8     soren 	aprint_normal("\n");
    574   1.8     soren 	aprint_normal_dev(self, "%s", spdmem_basic_types[s->sm_type]);
    575   1.8     soren 
    576   1.1  pgoyette 	aprint_normal("\n");
    577   1.1  pgoyette 	aprint_verbose_dev(self,
    578   1.1  pgoyette 	    "%d rows, %d cols, %d banks, %dns tRAC, %dns tCAC\n",
    579   1.1  pgoyette 	    s->sm_fpm.fpm_rows, s->sm_fpm.fpm_cols, s->sm_fpm.fpm_banks,
    580   1.1  pgoyette 	    s->sm_fpm.fpm_tRAC, s->sm_fpm.fpm_tCAC);
    581   1.1  pgoyette }
    582   1.1  pgoyette 
    583   1.1  pgoyette static void
    584  1.18   msaitoh decode_rom(const struct sysctlnode *node, device_t self, struct spdmem *s)
    585  1.18   msaitoh {
    586  1.18   msaitoh 
    587   1.8     soren 	aprint_naive("\n");
    588   1.8     soren 	aprint_normal("\n");
    589   1.8     soren 	aprint_normal_dev(self, "%s", spdmem_basic_types[s->sm_type]);
    590   1.8     soren 
    591   1.1  pgoyette 	aprint_normal("\n");
    592   1.1  pgoyette 	aprint_verbose_dev(self, "%d rows, %d cols, %d banks\n",
    593   1.1  pgoyette 	    s->sm_rom.rom_rows, s->sm_rom.rom_cols, s->sm_rom.rom_banks);
    594   1.1  pgoyette }
    595   1.1  pgoyette 
    596   1.1  pgoyette static void
    597   1.1  pgoyette decode_sdram(const struct sysctlnode *node, device_t self, struct spdmem *s,
    598  1.18   msaitoh 	     int spd_len)
    599  1.18   msaitoh {
    600   1.1  pgoyette 	int dimm_size, cycle_time, bits, tAA, i, speed, freq;
    601   1.1  pgoyette 
    602   1.8     soren 	aprint_naive("\n");
    603   1.8     soren 	aprint_normal("\n");
    604   1.8     soren 	aprint_normal_dev(self, "%s", spdmem_basic_types[s->sm_type]);
    605   1.8     soren 
    606   1.1  pgoyette 	aprint_normal("%s, %s, ",
    607   1.1  pgoyette 		(s->sm_sdr.sdr_mod_attrs & SPDMEM_SDR_MASK_REG)?
    608   1.1  pgoyette 			" (registered)":"",
    609   1.1  pgoyette 		(s->sm_config < __arraycount(spdmem_parity_types))?
    610   1.1  pgoyette 			spdmem_parity_types[s->sm_config]:"invalid parity");
    611   1.1  pgoyette 
    612   1.1  pgoyette 	dimm_size = 1 << (s->sm_sdr.sdr_rows + s->sm_sdr.sdr_cols - 17);
    613   1.1  pgoyette 	dimm_size *= s->sm_sdr.sdr_banks * s->sm_sdr.sdr_banks_per_chip;
    614   1.1  pgoyette 
    615   1.1  pgoyette 	cycle_time = s->sm_sdr.sdr_cycle_whole * 1000 +
    616   1.1  pgoyette 		     s->sm_sdr.sdr_cycle_tenths * 100;
    617   1.1  pgoyette 	bits = le16toh(s->sm_sdr.sdr_datawidth);
    618   1.1  pgoyette 	if (s->sm_config == 1 || s->sm_config == 2)
    619   1.1  pgoyette 		bits -= 8;
    620   1.1  pgoyette 
    621   1.1  pgoyette 	/* Calculate speed here - from OpenBSD */
    622   1.1  pgoyette 	if (spd_len >= 128)
    623   1.1  pgoyette 		freq = ((uint8_t *)s)[126];
    624   1.1  pgoyette 	else
    625   1.1  pgoyette 		freq = 0;
    626   1.1  pgoyette 	switch (freq) {
    627   1.1  pgoyette 		/*
    628  1.33   msaitoh 		 * Must check cycle time since some PC-133 DIMMs
    629   1.1  pgoyette 		 * actually report PC-100
    630   1.1  pgoyette 		 */
    631   1.1  pgoyette 	    case 100:
    632   1.1  pgoyette 	    case 133:
    633   1.1  pgoyette 		if (cycle_time < 8000)
    634   1.1  pgoyette 			speed = 133;
    635   1.1  pgoyette 		else
    636   1.1  pgoyette 			speed = 100;
    637   1.1  pgoyette 		break;
    638   1.1  pgoyette 	    case 0x66:		/* Legacy DIMMs use _hex_ 66! */
    639   1.1  pgoyette 	    default:
    640   1.1  pgoyette 		speed = 66;
    641   1.1  pgoyette 	}
    642   1.3  pgoyette 	decode_size_speed(self, node, dimm_size, cycle_time, 1, bits, FALSE,
    643   1.3  pgoyette 			  "PC", speed);
    644   1.1  pgoyette 
    645   1.1  pgoyette 	aprint_verbose_dev(self,
    646   1.1  pgoyette 	    "%d rows, %d cols, %d banks, %d banks/chip, %d.%dns cycle time\n",
    647   1.1  pgoyette 	    s->sm_sdr.sdr_rows, s->sm_sdr.sdr_cols, s->sm_sdr.sdr_banks,
    648   1.1  pgoyette 	    s->sm_sdr.sdr_banks_per_chip, cycle_time/1000,
    649   1.1  pgoyette 	    (cycle_time % 1000) / 100);
    650   1.1  pgoyette 
    651   1.1  pgoyette 	tAA  = 0;
    652   1.1  pgoyette 	for (i = 0; i < 8; i++)
    653   1.1  pgoyette 		if (s->sm_sdr.sdr_tCAS & (1 << i))
    654   1.1  pgoyette 			tAA = i;
    655   1.1  pgoyette 	tAA++;
    656   1.4  christos 	aprint_verbose_dev(self, LATENCY, tAA, s->sm_sdr.sdr_tRCD,
    657   1.1  pgoyette 	    s->sm_sdr.sdr_tRP, s->sm_sdr.sdr_tRAS);
    658   1.1  pgoyette 
    659   1.1  pgoyette 	decode_voltage_refresh(self, s);
    660   1.1  pgoyette }
    661   1.1  pgoyette 
    662   1.1  pgoyette static void
    663  1.18   msaitoh decode_ddr(const struct sysctlnode *node, device_t self, struct spdmem *s)
    664  1.18   msaitoh {
    665   1.1  pgoyette 	int dimm_size, cycle_time, bits, tAA, i;
    666   1.1  pgoyette 
    667   1.8     soren 	aprint_naive("\n");
    668   1.8     soren 	aprint_normal("\n");
    669   1.8     soren 	aprint_normal_dev(self, "%s", spdmem_basic_types[s->sm_type]);
    670   1.8     soren 
    671   1.1  pgoyette 	aprint_normal("%s, %s, ",
    672   1.1  pgoyette 		(s->sm_ddr.ddr_mod_attrs & SPDMEM_DDR_MASK_REG)?
    673   1.1  pgoyette 			" (registered)":"",
    674   1.1  pgoyette 		(s->sm_config < __arraycount(spdmem_parity_types))?
    675   1.1  pgoyette 			spdmem_parity_types[s->sm_config]:"invalid parity");
    676   1.1  pgoyette 
    677   1.1  pgoyette 	dimm_size = 1 << (s->sm_ddr.ddr_rows + s->sm_ddr.ddr_cols - 17);
    678   1.1  pgoyette 	dimm_size *= s->sm_ddr.ddr_ranks * s->sm_ddr.ddr_banks_per_chip;
    679   1.1  pgoyette 
    680   1.1  pgoyette 	cycle_time = s->sm_ddr.ddr_cycle_whole * 1000 +
    681   1.1  pgoyette 		  spdmem_cycle_frac[s->sm_ddr.ddr_cycle_tenths];
    682   1.1  pgoyette 	bits = le16toh(s->sm_ddr.ddr_datawidth);
    683   1.1  pgoyette 	if (s->sm_config == 1 || s->sm_config == 2)
    684   1.1  pgoyette 		bits -= 8;
    685   1.3  pgoyette 	decode_size_speed(self, node, dimm_size, cycle_time, 2, bits, TRUE,
    686   1.3  pgoyette 			  "PC", 0);
    687   1.1  pgoyette 
    688   1.1  pgoyette 	aprint_verbose_dev(self,
    689   1.1  pgoyette 	    "%d rows, %d cols, %d ranks, %d banks/chip, %d.%dns cycle time\n",
    690   1.1  pgoyette 	    s->sm_ddr.ddr_rows, s->sm_ddr.ddr_cols, s->sm_ddr.ddr_ranks,
    691   1.1  pgoyette 	    s->sm_ddr.ddr_banks_per_chip, cycle_time/1000,
    692   1.1  pgoyette 	    (cycle_time % 1000 + 50) / 100);
    693   1.1  pgoyette 
    694   1.1  pgoyette 	tAA  = 0;
    695   1.1  pgoyette 	for (i = 2; i < 8; i++)
    696   1.1  pgoyette 		if (s->sm_ddr.ddr_tCAS & (1 << i))
    697   1.1  pgoyette 			tAA = i;
    698   1.1  pgoyette 	tAA /= 2;
    699   1.1  pgoyette 
    700   1.1  pgoyette #define __DDR_ROUND(scale, field)	\
    701   1.1  pgoyette 		((scale * s->sm_ddr.field + cycle_time - 1) / cycle_time)
    702   1.1  pgoyette 
    703   1.4  christos 	aprint_verbose_dev(self, LATENCY, tAA, __DDR_ROUND(250, ddr_tRCD),
    704   1.1  pgoyette 		__DDR_ROUND(250, ddr_tRP), __DDR_ROUND(1000, ddr_tRAS));
    705   1.1  pgoyette 
    706   1.1  pgoyette #undef	__DDR_ROUND
    707   1.1  pgoyette 
    708   1.1  pgoyette 	decode_voltage_refresh(self, s);
    709   1.1  pgoyette }
    710   1.1  pgoyette 
    711   1.1  pgoyette static void
    712  1.18   msaitoh decode_ddr2(const struct sysctlnode *node, device_t self, struct spdmem *s)
    713  1.18   msaitoh {
    714   1.1  pgoyette 	int dimm_size, cycle_time, bits, tAA, i;
    715   1.1  pgoyette 
    716   1.8     soren 	aprint_naive("\n");
    717   1.8     soren 	aprint_normal("\n");
    718   1.8     soren 	aprint_normal_dev(self, "%s", spdmem_basic_types[s->sm_type]);
    719   1.8     soren 
    720   1.1  pgoyette 	aprint_normal("%s, %s, ",
    721   1.1  pgoyette 		(s->sm_ddr2.ddr2_mod_attrs & SPDMEM_DDR2_MASK_REG)?
    722   1.1  pgoyette 			" (registered)":"",
    723   1.1  pgoyette 		(s->sm_config < __arraycount(spdmem_parity_types))?
    724   1.1  pgoyette 			spdmem_parity_types[s->sm_config]:"invalid parity");
    725   1.1  pgoyette 
    726   1.1  pgoyette 	dimm_size = 1 << (s->sm_ddr2.ddr2_rows + s->sm_ddr2.ddr2_cols - 17);
    727   1.1  pgoyette 	dimm_size *= (s->sm_ddr2.ddr2_ranks + 1) *
    728   1.1  pgoyette 		     s->sm_ddr2.ddr2_banks_per_chip;
    729   1.1  pgoyette 
    730   1.1  pgoyette 	cycle_time = s->sm_ddr2.ddr2_cycle_whole * 1000 +
    731   1.1  pgoyette 		 spdmem_cycle_frac[s->sm_ddr2.ddr2_cycle_frac];
    732   1.1  pgoyette 	bits = s->sm_ddr2.ddr2_datawidth;
    733   1.1  pgoyette 	if ((s->sm_config & 0x03) != 0)
    734   1.1  pgoyette 		bits -= 8;
    735   1.3  pgoyette 	decode_size_speed(self, node, dimm_size, cycle_time, 2, bits, TRUE,
    736   1.3  pgoyette 			  "PC2", 0);
    737   1.1  pgoyette 
    738   1.1  pgoyette 	aprint_verbose_dev(self,
    739   1.1  pgoyette 	    "%d rows, %d cols, %d ranks, %d banks/chip, %d.%02dns cycle time\n",
    740   1.1  pgoyette 	    s->sm_ddr2.ddr2_rows, s->sm_ddr2.ddr2_cols,
    741   1.1  pgoyette 	    s->sm_ddr2.ddr2_ranks + 1, s->sm_ddr2.ddr2_banks_per_chip,
    742   1.1  pgoyette 	    cycle_time / 1000, (cycle_time % 1000 + 5) /10 );
    743   1.1  pgoyette 
    744   1.1  pgoyette 	tAA  = 0;
    745   1.1  pgoyette 	for (i = 2; i < 8; i++)
    746   1.1  pgoyette 		if (s->sm_ddr2.ddr2_tCAS & (1 << i))
    747   1.1  pgoyette 			tAA = i;
    748   1.1  pgoyette 
    749   1.1  pgoyette #define __DDR2_ROUND(scale, field)	\
    750   1.1  pgoyette 		((scale * s->sm_ddr2.field + cycle_time - 1) / cycle_time)
    751   1.1  pgoyette 
    752   1.4  christos 	aprint_verbose_dev(self, LATENCY, tAA, __DDR2_ROUND(250, ddr2_tRCD),
    753   1.1  pgoyette 		__DDR2_ROUND(250, ddr2_tRP), __DDR2_ROUND(1000, ddr2_tRAS));
    754   1.1  pgoyette 
    755   1.1  pgoyette #undef	__DDR_ROUND
    756   1.1  pgoyette 
    757   1.1  pgoyette 	decode_voltage_refresh(self, s);
    758   1.1  pgoyette }
    759   1.1  pgoyette 
    760   1.1  pgoyette static void
    761  1.26  christos print_part(const char *part, size_t pnsize)
    762  1.18   msaitoh {
    763  1.27  christos 	const char *p = memchr(part, ' ', pnsize);
    764  1.27  christos 	if (p == NULL)
    765  1.27  christos 		p = part + pnsize;
    766  1.27  christos 	aprint_normal(": %.*s\n", (int)(p - part), part);
    767  1.26  christos }
    768  1.26  christos 
    769  1.34   msaitoh static u_int
    770  1.34   msaitoh ddr3_value_pico(struct spdmem *s, uint8_t txx_mtb, uint8_t txx_ftb)
    771  1.34   msaitoh {
    772  1.34   msaitoh 	u_int mtb, ftb; /* in picoseconds */
    773  1.34   msaitoh 	intmax_t signed_txx_ftb;
    774  1.34   msaitoh 	u_int val;
    775  1.34   msaitoh 
    776  1.34   msaitoh 	mtb = (u_int)s->sm_ddr3.ddr3_mtb_dividend * 1000 /
    777  1.34   msaitoh 	    s->sm_ddr3.ddr3_mtb_divisor;
    778  1.34   msaitoh 	ftb = (u_int)s->sm_ddr3.ddr3_ftb_dividend * 1000 /
    779  1.34   msaitoh 	    s->sm_ddr3.ddr3_ftb_divisor;
    780  1.34   msaitoh 
    781  1.34   msaitoh 	/* tXX_ftb is signed value */
    782  1.34   msaitoh 	signed_txx_ftb = (int8_t)txx_ftb;
    783  1.34   msaitoh 	val = txx_mtb * mtb +
    784  1.34   msaitoh 	    ((txx_ftb > 127) ? signed_txx_ftb : txx_ftb) * ftb / 1000;
    785  1.34   msaitoh 
    786  1.34   msaitoh 	return val;
    787  1.34   msaitoh }
    788  1.34   msaitoh 
    789  1.34   msaitoh #define __DDR3_VALUE_PICO(s, field)				\
    790  1.34   msaitoh 	ddr3_value_pico(s, s->sm_ddr3.ddr3_##field##_mtb,	\
    791  1.34   msaitoh 	    s->sm_ddr3.ddr3_##field##_ftb)
    792  1.34   msaitoh 
    793  1.26  christos static void
    794  1.26  christos decode_ddr3(const struct sysctlnode *node, device_t self, struct spdmem *s)
    795  1.26  christos {
    796  1.26  christos 	int dimm_size, cycle_time, bits;
    797  1.26  christos 
    798   1.8     soren 	aprint_naive("\n");
    799  1.26  christos 	print_part(s->sm_ddr3.ddr3_part, sizeof(s->sm_ddr3.ddr3_part));
    800   1.8     soren 	aprint_normal_dev(self, "%s", spdmem_basic_types[s->sm_type]);
    801   1.8     soren 
    802   1.1  pgoyette 	if (s->sm_ddr3.ddr3_mod_type ==
    803   1.1  pgoyette 		SPDMEM_DDR3_TYPE_MINI_RDIMM ||
    804   1.1  pgoyette 	    s->sm_ddr3.ddr3_mod_type == SPDMEM_DDR3_TYPE_RDIMM)
    805   1.1  pgoyette 		aprint_normal(" (registered)");
    806   1.1  pgoyette 	aprint_normal(", %sECC, %stemp-sensor, ",
    807   1.1  pgoyette 		(s->sm_ddr3.ddr3_hasECC)?"":"no ",
    808   1.1  pgoyette 		(s->sm_ddr3.ddr3_has_therm_sensor)?"":"no ");
    809   1.1  pgoyette 
    810   1.1  pgoyette 	/*
    811   1.1  pgoyette 	 * DDR3 size specification is quite different from others
    812   1.1  pgoyette 	 *
    813   1.1  pgoyette 	 * Module capacity is defined as
    814   1.1  pgoyette 	 *	Chip_Capacity_in_bits / 8bits-per-byte *
    815   1.1  pgoyette 	 *	external_bus_width / internal_bus_width
    816   1.1  pgoyette 	 * We further divide by 2**20 to get our answer in MB
    817   1.1  pgoyette 	 */
    818   1.1  pgoyette 	dimm_size = (s->sm_ddr3.ddr3_chipsize + 28 - 20) - 3 +
    819   1.1  pgoyette 		    (s->sm_ddr3.ddr3_datawidth + 3) -
    820   1.1  pgoyette 		    (s->sm_ddr3.ddr3_chipwidth + 2);
    821   1.1  pgoyette 	dimm_size = (1 << dimm_size) * (s->sm_ddr3.ddr3_physbanks + 1);
    822   1.1  pgoyette 
    823  1.34   msaitoh 	cycle_time = __DDR3_VALUE_PICO(s, tCKmin);
    824   1.1  pgoyette 	bits = 1 << (s->sm_ddr3.ddr3_datawidth + 3);
    825   1.3  pgoyette 	decode_size_speed(self, node, dimm_size, cycle_time, 2, bits, FALSE,
    826   1.3  pgoyette 			  "PC3", 0);
    827   1.1  pgoyette 
    828   1.1  pgoyette 	aprint_verbose_dev(self,
    829   1.1  pgoyette 	    "%d rows, %d cols, %d log. banks, %d phys. banks, "
    830   1.1  pgoyette 	    "%d.%03dns cycle time\n",
    831  1.32   msaitoh 	    s->sm_ddr3.ddr3_rows + 12, s->sm_ddr3.ddr3_cols + 9,
    832   1.1  pgoyette 	    1 << (s->sm_ddr3.ddr3_logbanks + 3),
    833   1.1  pgoyette 	    s->sm_ddr3.ddr3_physbanks + 1,
    834   1.1  pgoyette 	    cycle_time/1000, cycle_time % 1000);
    835   1.1  pgoyette 
    836  1.34   msaitoh #define	__DDR3_CYCLES(val)						\
    837  1.34   msaitoh 	((val / cycle_time) + ((val % cycle_time) ? 1 : 0))
    838   1.1  pgoyette 
    839  1.34   msaitoh 	aprint_verbose_dev(self, LATENCY,
    840  1.34   msaitoh 	    __DDR3_CYCLES(__DDR3_VALUE_PICO(s, tAAmin)),
    841  1.34   msaitoh 	    __DDR3_CYCLES(__DDR3_VALUE_PICO(s, tRCDmin)),
    842  1.34   msaitoh 	    __DDR3_CYCLES(__DDR3_VALUE_PICO(s, tRPmin)),
    843  1.35   msaitoh 	    __DDR3_CYCLES((s->sm_ddr3.ddr3_tRAS_msb * 256
    844  1.35   msaitoh 		+ s->sm_ddr3.ddr3_tRAS_lsb) * s->sm_ddr3.ddr3_mtb_dividend
    845  1.35   msaitoh 		/ s->sm_ddr3.ddr3_mtb_divisor * 1000));
    846   1.1  pgoyette 
    847   1.1  pgoyette #undef	__DDR3_CYCLES
    848  1.14   msaitoh 
    849  1.14   msaitoh 	/* For DDR3, Voltage is written in another area */
    850  1.14   msaitoh 	if (!s->sm_ddr3.ddr3_NOT15V || s->sm_ddr3.ddr3_135V
    851  1.14   msaitoh 	    || s->sm_ddr3.ddr3_125V) {
    852  1.14   msaitoh 		aprint_verbose("%s:", device_xname(self));
    853  1.14   msaitoh 		if (!s->sm_ddr3.ddr3_NOT15V)
    854  1.14   msaitoh 			aprint_verbose(" 1.5V");
    855  1.14   msaitoh 		if (s->sm_ddr3.ddr3_135V)
    856  1.14   msaitoh 			aprint_verbose(" 1.35V");
    857  1.14   msaitoh 		if (s->sm_ddr3.ddr3_125V)
    858  1.14   msaitoh 			aprint_verbose(" 1.25V");
    859  1.14   msaitoh 		aprint_verbose(" operable\n");
    860  1.14   msaitoh 	}
    861   1.1  pgoyette }
    862   1.1  pgoyette 
    863   1.1  pgoyette static void
    864  1.18   msaitoh decode_fbdimm(const struct sysctlnode *node, device_t self, struct spdmem *s)
    865  1.18   msaitoh {
    866   1.1  pgoyette 	int dimm_size, cycle_time, bits;
    867   1.1  pgoyette 
    868   1.8     soren 	aprint_naive("\n");
    869   1.8     soren 	aprint_normal("\n");
    870   1.8     soren 	aprint_normal_dev(self, "%s", spdmem_basic_types[s->sm_type]);
    871   1.8     soren 
    872   1.1  pgoyette 	/*
    873   1.1  pgoyette 	 * FB-DIMM module size calculation is very much like DDR3
    874   1.1  pgoyette 	 */
    875   1.1  pgoyette 	dimm_size = s->sm_fbd.fbdimm_rows + 12 +
    876   1.1  pgoyette 		    s->sm_fbd.fbdimm_cols +  9 - 20 - 3;
    877   1.1  pgoyette 	dimm_size = (1 << dimm_size) * (1 << (s->sm_fbd.fbdimm_banks + 2));
    878   1.1  pgoyette 
    879   1.1  pgoyette 	cycle_time = (1000 * s->sm_fbd.fbdimm_mtb_dividend +
    880   1.1  pgoyette 			    (s->sm_fbd.fbdimm_mtb_divisor / 2)) /
    881   1.1  pgoyette 		     s->sm_fbd.fbdimm_mtb_divisor;
    882   1.1  pgoyette 	bits = 1 << (s->sm_fbd.fbdimm_dev_width + 2);
    883   1.3  pgoyette 	decode_size_speed(self, node, dimm_size, cycle_time, 2, bits, TRUE,
    884   1.3  pgoyette 			  "PC2", 0);
    885   1.1  pgoyette 
    886   1.1  pgoyette 	aprint_verbose_dev(self,
    887   1.1  pgoyette 	    "%d rows, %d cols, %d banks, %d.%02dns cycle time\n",
    888   1.1  pgoyette 	    s->sm_fbd.fbdimm_rows, s->sm_fbd.fbdimm_cols,
    889   1.1  pgoyette 	    1 << (s->sm_fbd.fbdimm_banks + 2),
    890   1.1  pgoyette 	    cycle_time / 1000, (cycle_time % 1000 + 5) /10 );
    891   1.1  pgoyette 
    892   1.1  pgoyette #define	__FBDIMM_CYCLES(field) (s->sm_fbd.field / s->sm_fbd.fbdimm_tCKmin)
    893   1.1  pgoyette 
    894   1.4  christos 	aprint_verbose_dev(self, LATENCY, __FBDIMM_CYCLES(fbdimm_tAAmin),
    895  1.33   msaitoh 	    __FBDIMM_CYCLES(fbdimm_tRCDmin), __FBDIMM_CYCLES(fbdimm_tRPmin),
    896  1.33   msaitoh 	    (s->sm_fbd.fbdimm_tRAS_msb * 256 + s->sm_fbd.fbdimm_tRAS_lsb) /
    897  1.33   msaitoh 	    s->sm_fbd.fbdimm_tCKmin);
    898   1.1  pgoyette 
    899   1.1  pgoyette #undef	__FBDIMM_CYCLES
    900   1.1  pgoyette 
    901   1.1  pgoyette 	decode_voltage_refresh(self, s);
    902   1.1  pgoyette }
    903  1.13  pgoyette 
    904  1.13  pgoyette static void
    905  1.18   msaitoh decode_ddr4(const struct sysctlnode *node, device_t self, struct spdmem *s)
    906  1.18   msaitoh {
    907  1.30   msaitoh 	int dimm_size, cycle_time, ranks;
    908  1.33   msaitoh 	int tAA_clocks, tRCD_clocks, tRP_clocks, tRAS_clocks;
    909  1.13  pgoyette 
    910  1.13  pgoyette 	aprint_naive("\n");
    911  1.26  christos 	print_part(s->sm_ddr4.ddr4_part_number,
    912  1.26  christos 	    sizeof(s->sm_ddr4.ddr4_part_number));
    913  1.13  pgoyette 	aprint_normal_dev(self, "%s", spdmem_basic_types[s->sm_type]);
    914  1.13  pgoyette 	if (s->sm_ddr4.ddr4_mod_type < __arraycount(spdmem_ddr4_module_types))
    915  1.33   msaitoh 		aprint_normal(" (%s)",
    916  1.13  pgoyette 		    spdmem_ddr4_module_types[s->sm_ddr4.ddr4_mod_type]);
    917  1.28   msaitoh 	aprint_normal(", %sECC, %stemp-sensor, ",
    918  1.28   msaitoh 		(s->sm_ddr4.ddr4_bus_width_extension) ? "" : "no ",
    919  1.28   msaitoh 		(s->sm_ddr4.ddr4_has_therm_sensor) ? "" : "no ");
    920  1.13  pgoyette 
    921  1.13  pgoyette 	/*
    922  1.13  pgoyette 	 * DDR4 size calculation from JEDEC spec
    923  1.13  pgoyette 	 *
    924  1.13  pgoyette 	 * Module capacity in bytes is defined as
    925  1.13  pgoyette 	 *	Chip_Capacity_in_bits / 8bits-per-byte *
    926  1.13  pgoyette 	 *	primary_bus_width / DRAM_width *
    927  1.13  pgoyette 	 *	logical_ranks_per_DIMM
    928  1.13  pgoyette 	 *
    929  1.13  pgoyette 	 * logical_ranks_per DIMM equals package_ranks, but multiply
    930  1.13  pgoyette 	 * by diecount for 3DS packages
    931  1.13  pgoyette 	 *
    932  1.13  pgoyette 	 * We further divide by 2**20 to get our answer in MB
    933  1.13  pgoyette 	 */
    934  1.13  pgoyette 	dimm_size = (s->sm_ddr4.ddr4_capacity + 28)	/* chip_capacity */
    935  1.13  pgoyette 		     - 20				/* convert to MB */
    936  1.13  pgoyette 		     - 3				/* bits --> bytes */
    937  1.13  pgoyette 		     + (s->sm_ddr4.ddr4_primary_bus_width + 3); /* bus width */
    938  1.13  pgoyette 	switch (s->sm_ddr4.ddr4_device_width) {		/* DRAM width */
    939  1.13  pgoyette 	case 0:	dimm_size -= 2;
    940  1.13  pgoyette 		break;
    941  1.13  pgoyette 	case 1: dimm_size -= 3;
    942  1.13  pgoyette 		break;
    943  1.13  pgoyette 	case 2:	dimm_size -= 4;
    944  1.13  pgoyette 		break;
    945  1.13  pgoyette 	case 4: dimm_size -= 5;
    946  1.13  pgoyette 		break;
    947  1.13  pgoyette 	default:
    948  1.13  pgoyette 		dimm_size = -1;		/* flag invalid value */
    949  1.13  pgoyette 	}
    950  1.33   msaitoh 	if (dimm_size >= 0) {
    951  1.13  pgoyette 		dimm_size = (1 << dimm_size) *
    952  1.13  pgoyette 		    (s->sm_ddr4.ddr4_package_ranks + 1); /* log.ranks/DIMM */
    953  1.13  pgoyette 		if (s->sm_ddr4.ddr4_signal_loading == 2) {
    954  1.19  pgoyette 			dimm_size *= (s->sm_ddr4.ddr4_diecount + 1);
    955  1.13  pgoyette 		}
    956  1.13  pgoyette 	}
    957  1.13  pgoyette 
    958  1.24   msaitoh /*
    959  1.24   msaitoh  * Note that the ddr4_xxx_ftb fields are actually signed offsets from
    960  1.24   msaitoh  * the corresponding mtb value, so we might have to subtract 256!
    961  1.24   msaitoh  */
    962  1.18   msaitoh #define	__DDR4_VALUE(field) ((s->sm_ddr4.ddr4_##field##_mtb * 125 +	\
    963  1.18   msaitoh 			     s->sm_ddr4.ddr4_##field##_ftb) - 		\
    964  1.18   msaitoh 			    ((s->sm_ddr4.ddr4_##field##_ftb > 127)?256:0))
    965  1.13  pgoyette 	/*
    966  1.33   msaitoh 	 * For now, the only value for mtb is 0 = 125ps, and ftb = 1ps
    967  1.13  pgoyette 	 * so we don't need to figure out the time-base units - just
    968  1.13  pgoyette 	 * hard-code them for now.
    969  1.13  pgoyette 	 */
    970  1.18   msaitoh 	cycle_time = __DDR4_VALUE(tCKAVGmin);
    971  1.13  pgoyette 	decode_size_speed(self, node, dimm_size, cycle_time, 2,
    972  1.19  pgoyette 			  1 << (s->sm_ddr4.ddr4_primary_bus_width + 3),
    973  1.13  pgoyette 			  TRUE, "PC4", 0);
    974  1.13  pgoyette 
    975  1.30   msaitoh 	ranks = s->sm_ddr4.ddr4_package_ranks + 1;
    976  1.13  pgoyette 	aprint_verbose_dev(self,
    977  1.30   msaitoh 	    "%d rows, %d cols, %d ranks%s, %d banks/group, %d bank groups\n",
    978  1.29   msaitoh 	    s->sm_ddr4.ddr4_rows + 12, s->sm_ddr4.ddr4_cols + 9,
    979  1.30   msaitoh 	    ranks, (ranks > 1) ? ((s->sm_ddr4.ddr4_rank_mix == 1)
    980  1.31  pgoyette 		? " (asymmetric)" : " (symmetric)") : "",
    981  1.13  pgoyette 	    1 << (2 + s->sm_ddr4.ddr4_logbanks),
    982  1.30   msaitoh 	    1 << s->sm_ddr4.ddr4_bankgroups);
    983  1.30   msaitoh 
    984  1.30   msaitoh 	aprint_verbose_dev(self, "%d.%03dns cycle time\n",
    985  1.20   msaitoh 	    cycle_time / 1000, cycle_time % 1000);
    986  1.13  pgoyette 
    987  1.18   msaitoh 	tAA_clocks =  __DDR4_VALUE(tAAmin)  * 1000 / cycle_time;
    988  1.18   msaitoh 	tRCD_clocks = __DDR4_VALUE(tRCDmin) * 1000 / cycle_time;
    989  1.18   msaitoh 	tRP_clocks =  __DDR4_VALUE(tRPmin)  * 1000 / cycle_time;
    990  1.13  pgoyette 	tRAS_clocks = (s->sm_ddr4.ddr4_tRASmin_msb * 256 +
    991  1.13  pgoyette 		       s->sm_ddr4.ddr4_tRASmin_lsb) * 125 * 1000 / cycle_time;
    992  1.13  pgoyette 
    993  1.13  pgoyette /*
    994  1.13  pgoyette  * Per JEDEC spec, rounding is done by taking the time value, dividing
    995  1.13  pgoyette  * by the cycle time, subtracting .010 from the result, and then
    996  1.13  pgoyette  * rounded up to the nearest integer.  Unfortunately, none of their
    997  1.13  pgoyette  * examples say what to do when the result of the subtraction is already
    998  1.13  pgoyette  * an integer.  For now, assume that we still round up (so an interval
    999  1.13  pgoyette  * of exactly 12.010 clock cycles will be printed as 13).
   1000  1.13  pgoyette  */
   1001  1.13  pgoyette #define	__DDR4_ROUND(value) ((value - 10) / 1000 + 1)
   1002  1.13  pgoyette 
   1003  1.13  pgoyette 	aprint_verbose_dev(self, LATENCY, __DDR4_ROUND(tAA_clocks),
   1004  1.18   msaitoh 			   __DDR4_ROUND(tRCD_clocks),
   1005  1.13  pgoyette 			   __DDR4_ROUND(tRP_clocks),
   1006  1.13  pgoyette 			   __DDR4_ROUND(tRAS_clocks));
   1007  1.13  pgoyette 
   1008  1.13  pgoyette #undef	__DDR4_VALUE
   1009  1.13  pgoyette #undef	__DDR4_ROUND
   1010  1.13  pgoyette }
   1011