Home | History | Annotate | Line # | Download | only in ic
spdmem.c revision 1.2.2.2
      1  1.2.2.2  yamt /* $NetBSD: spdmem.c,v 1.2.2.2 2010/08/11 22:53:32 yamt Exp $ */
      2  1.2.2.2  yamt 
      3  1.2.2.2  yamt /*
      4  1.2.2.2  yamt  * Copyright (c) 2007 Nicolas Joly
      5  1.2.2.2  yamt  * Copyright (c) 2007 Paul Goyette
      6  1.2.2.2  yamt  * Copyright (c) 2007 Tobias Nygren
      7  1.2.2.2  yamt  * All rights reserved.
      8  1.2.2.2  yamt  *
      9  1.2.2.2  yamt  * Redistribution and use in source and binary forms, with or without
     10  1.2.2.2  yamt  * modification, are permitted provided that the following conditions
     11  1.2.2.2  yamt  * are met:
     12  1.2.2.2  yamt  * 1. Redistributions of source code must retain the above copyright
     13  1.2.2.2  yamt  *    notice, this list of conditions and the following disclaimer.
     14  1.2.2.2  yamt  * 2. Redistributions in binary form must reproduce the above copyright
     15  1.2.2.2  yamt  *    notice, this list of conditions and the following disclaimer in the
     16  1.2.2.2  yamt  *    documentation and/or other materials provided with the distribution.
     17  1.2.2.2  yamt  * 3. The name of the author may not be used to endorse or promote products
     18  1.2.2.2  yamt  *    derived from this software without specific prior written permission.
     19  1.2.2.2  yamt  *
     20  1.2.2.2  yamt  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS
     21  1.2.2.2  yamt  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
     22  1.2.2.2  yamt  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
     23  1.2.2.2  yamt  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
     24  1.2.2.2  yamt  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
     25  1.2.2.2  yamt  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
     26  1.2.2.2  yamt  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
     27  1.2.2.2  yamt  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
     28  1.2.2.2  yamt  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
     29  1.2.2.2  yamt  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
     30  1.2.2.2  yamt  * POSSIBILITY OF SUCH DAMAGE.
     31  1.2.2.2  yamt  */
     32  1.2.2.2  yamt 
     33  1.2.2.2  yamt /*
     34  1.2.2.2  yamt  * Serial Presence Detect (SPD) memory identification
     35  1.2.2.2  yamt  */
     36  1.2.2.2  yamt 
     37  1.2.2.2  yamt #include <sys/cdefs.h>
     38  1.2.2.2  yamt __KERNEL_RCSID(0, "$NetBSD: spdmem.c,v 1.2.2.2 2010/08/11 22:53:32 yamt Exp $");
     39  1.2.2.2  yamt 
     40  1.2.2.2  yamt #include <sys/param.h>
     41  1.2.2.2  yamt #include <sys/device.h>
     42  1.2.2.2  yamt #include <sys/endian.h>
     43  1.2.2.2  yamt #include <sys/sysctl.h>
     44  1.2.2.2  yamt #include <machine/bswap.h>
     45  1.2.2.2  yamt 
     46  1.2.2.2  yamt #include <dev/i2c/i2cvar.h>
     47  1.2.2.2  yamt #include <dev/ic/spdmemreg.h>
     48  1.2.2.2  yamt #include <dev/ic/spdmemvar.h>
     49  1.2.2.2  yamt 
     50  1.2.2.2  yamt SYSCTL_SETUP_PROTO(sysctl_spdmem_setup);
     51  1.2.2.2  yamt 
     52  1.2.2.2  yamt /* Routines for decoding spd data */
     53  1.2.2.2  yamt static void decode_edofpm(const struct sysctlnode *, device_t, struct spdmem *);
     54  1.2.2.2  yamt static void decode_rom(const struct sysctlnode *, device_t, struct spdmem *);
     55  1.2.2.2  yamt static void decode_sdram(const struct sysctlnode *, device_t, struct spdmem *,
     56  1.2.2.2  yamt 	int);
     57  1.2.2.2  yamt static void decode_ddr(const struct sysctlnode *, device_t, struct spdmem *);
     58  1.2.2.2  yamt static void decode_ddr2(const struct sysctlnode *, device_t, struct spdmem *);
     59  1.2.2.2  yamt static void decode_ddr3(const struct sysctlnode *, device_t, struct spdmem *);
     60  1.2.2.2  yamt static void decode_fbdimm(const struct sysctlnode *, device_t, struct spdmem *);
     61  1.2.2.2  yamt 
     62  1.2.2.2  yamt static void decode_size_speed(const struct sysctlnode *, int, int, int, int,
     63  1.2.2.2  yamt 			      bool, const char *, int);
     64  1.2.2.2  yamt static void decode_voltage_refresh(device_t, struct spdmem *);
     65  1.2.2.2  yamt 
     66  1.2.2.2  yamt #define IS_RAMBUS_TYPE (s->sm_len < 4)
     67  1.2.2.2  yamt 
     68  1.2.2.2  yamt static const char* spdmem_basic_types[] = {
     69  1.2.2.2  yamt 	"unknown",
     70  1.2.2.2  yamt 	"FPM",
     71  1.2.2.2  yamt 	"EDO",
     72  1.2.2.2  yamt 	"Pipelined Nibble",
     73  1.2.2.2  yamt 	"SDRAM",
     74  1.2.2.2  yamt 	"ROM",
     75  1.2.2.2  yamt 	"DDR SGRAM",
     76  1.2.2.2  yamt 	"DDR SDRAM",
     77  1.2.2.2  yamt 	"DDR2 SDRAM",
     78  1.2.2.2  yamt 	"DDR2 SDRAM FB",
     79  1.2.2.2  yamt 	"DDR2 SDRAM FB Probe",
     80  1.2.2.2  yamt 	"DDR3 SDRAM"
     81  1.2.2.2  yamt };
     82  1.2.2.2  yamt 
     83  1.2.2.2  yamt static const char* spdmem_superset_types[] = {
     84  1.2.2.2  yamt 	"unknown",
     85  1.2.2.2  yamt 	"ESDRAM",
     86  1.2.2.2  yamt 	"DDR ESDRAM",
     87  1.2.2.2  yamt 	"PEM EDO",
     88  1.2.2.2  yamt 	"PEM SDRAM"
     89  1.2.2.2  yamt };
     90  1.2.2.2  yamt 
     91  1.2.2.2  yamt static const char* spdmem_voltage_types[] = {
     92  1.2.2.2  yamt 	"TTL (5V tolerant)",
     93  1.2.2.2  yamt 	"LvTTL (not 5V tolerant)",
     94  1.2.2.2  yamt 	"HSTL 1.5V",
     95  1.2.2.2  yamt 	"SSTL 3.3V",
     96  1.2.2.2  yamt 	"SSTL 2.5V",
     97  1.2.2.2  yamt 	"SSTL 1.8V"
     98  1.2.2.2  yamt };
     99  1.2.2.2  yamt 
    100  1.2.2.2  yamt static const char* spdmem_refresh_types[] = {
    101  1.2.2.2  yamt 	"15.625us",
    102  1.2.2.2  yamt 	"3.9us",
    103  1.2.2.2  yamt 	"7.8us",
    104  1.2.2.2  yamt 	"31.3us",
    105  1.2.2.2  yamt 	"62.5us",
    106  1.2.2.2  yamt 	"125us"
    107  1.2.2.2  yamt };
    108  1.2.2.2  yamt 
    109  1.2.2.2  yamt static const char* spdmem_parity_types[] = {
    110  1.2.2.2  yamt 	"no parity or ECC",
    111  1.2.2.2  yamt 	"data parity",
    112  1.2.2.2  yamt 	"data ECC",
    113  1.2.2.2  yamt 	"data parity and ECC",
    114  1.2.2.2  yamt 	"cmd/addr parity",
    115  1.2.2.2  yamt 	"cmd/addr/data parity",
    116  1.2.2.2  yamt 	"cmd/addr parity, data ECC",
    117  1.2.2.2  yamt 	"cmd/addr/data parity, data ECC"
    118  1.2.2.2  yamt };
    119  1.2.2.2  yamt 
    120  1.2.2.2  yamt /* Cycle time fractional values (units of .001 ns) for DDR2 SDRAM */
    121  1.2.2.2  yamt static const uint16_t spdmem_cycle_frac[] = {
    122  1.2.2.2  yamt 	0, 100, 200, 300, 400, 500, 600, 700, 800, 900,
    123  1.2.2.2  yamt 	250, 333, 667, 750, 999, 999
    124  1.2.2.2  yamt };
    125  1.2.2.2  yamt 
    126  1.2.2.2  yamt /* Format string for timing info */
    127  1.2.2.2  yamt static const char* latency="tAA-tRCD-tRP-tRAS: %d-%d-%d-%d\n";
    128  1.2.2.2  yamt 
    129  1.2.2.2  yamt /* sysctl stuff */
    130  1.2.2.2  yamt static int hw_node = CTL_EOL;
    131  1.2.2.2  yamt 
    132  1.2.2.2  yamt /* CRC functions used for certain memory types */
    133  1.2.2.2  yamt 
    134  1.2.2.2  yamt static uint16_t spdcrc16 (struct spdmem_softc *sc, int count)
    135  1.2.2.2  yamt {
    136  1.2.2.2  yamt 	uint16_t crc;
    137  1.2.2.2  yamt 	int i, j;
    138  1.2.2.2  yamt 	uint8_t val;
    139  1.2.2.2  yamt 	crc = 0;
    140  1.2.2.2  yamt 	for (j = 0; j <= count; j++) {
    141  1.2.2.2  yamt 		val = (sc->sc_read)(sc, j);
    142  1.2.2.2  yamt 		crc = crc ^ val << 8;
    143  1.2.2.2  yamt 		for (i = 0; i < 8; ++i)
    144  1.2.2.2  yamt 			if (crc & 0x8000)
    145  1.2.2.2  yamt 				crc = crc << 1 ^ 0x1021;
    146  1.2.2.2  yamt 			else
    147  1.2.2.2  yamt 				crc = crc << 1;
    148  1.2.2.2  yamt 	}
    149  1.2.2.2  yamt 	return (crc & 0xFFFF);
    150  1.2.2.2  yamt }
    151  1.2.2.2  yamt 
    152  1.2.2.2  yamt int
    153  1.2.2.2  yamt spdmem_common_probe(struct spdmem_softc *sc)
    154  1.2.2.2  yamt {
    155  1.2.2.2  yamt 	int cksum = 0;
    156  1.2.2.2  yamt 	uint8_t i, val, spd_type;
    157  1.2.2.2  yamt 	int spd_len, spd_crc_cover;
    158  1.2.2.2  yamt 	uint16_t crc_calc, crc_spd;
    159  1.2.2.2  yamt 
    160  1.2.2.2  yamt 	spd_type = (sc->sc_read)(sc, 2);
    161  1.2.2.2  yamt 
    162  1.2.2.2  yamt 	/* For older memory types, validate the checksum over 1st 63 bytes */
    163  1.2.2.2  yamt 	if (spd_type <= SPDMEM_MEMTYPE_DDR2SDRAM) {
    164  1.2.2.2  yamt 		for (i = 0; i < 63; i++)
    165  1.2.2.2  yamt 			cksum += (sc->sc_read)(sc, i);
    166  1.2.2.2  yamt 
    167  1.2.2.2  yamt 		val = (sc->sc_read)(sc, 63);
    168  1.2.2.2  yamt 
    169  1.2.2.2  yamt 		if (cksum == 0 || (cksum & 0xff) != val) {
    170  1.2.2.2  yamt 			aprint_debug("spd checksum failed, calc = 0x%02x, "
    171  1.2.2.2  yamt 				     "spd = 0x%02x\n", cksum, val);
    172  1.2.2.2  yamt 			return 0;
    173  1.2.2.2  yamt 		} else
    174  1.2.2.2  yamt 			return 1;
    175  1.2.2.2  yamt 	}
    176  1.2.2.2  yamt 
    177  1.2.2.2  yamt 	/* For DDR3 and FBDIMM, verify the CRC */
    178  1.2.2.2  yamt 	else if (spd_type <= SPDMEM_MEMTYPE_DDR3SDRAM) {
    179  1.2.2.2  yamt 		spd_len = (sc->sc_read)(sc, 0);
    180  1.2.2.2  yamt 		if (spd_len & SPDMEM_SPDCRC_116)
    181  1.2.2.2  yamt 			spd_crc_cover = 116;
    182  1.2.2.2  yamt 		else
    183  1.2.2.2  yamt 			spd_crc_cover = 125;
    184  1.2.2.2  yamt 		switch (spd_len & SPDMEM_SPDLEN_MASK) {
    185  1.2.2.2  yamt 		case SPDMEM_SPDLEN_128:
    186  1.2.2.2  yamt 			spd_len = 128;
    187  1.2.2.2  yamt 			break;
    188  1.2.2.2  yamt 		case SPDMEM_SPDLEN_176:
    189  1.2.2.2  yamt 			spd_len = 176;
    190  1.2.2.2  yamt 			break;
    191  1.2.2.2  yamt 		case SPDMEM_SPDLEN_256:
    192  1.2.2.2  yamt 			spd_len = 256;
    193  1.2.2.2  yamt 			break;
    194  1.2.2.2  yamt 		default:
    195  1.2.2.2  yamt 			return 0;
    196  1.2.2.2  yamt 		}
    197  1.2.2.2  yamt 		if (spd_crc_cover > spd_len)
    198  1.2.2.2  yamt 			return 0;
    199  1.2.2.2  yamt 		crc_calc = spdcrc16(sc, spd_crc_cover);
    200  1.2.2.2  yamt 		crc_spd = (sc->sc_read)(sc, 127) << 8;
    201  1.2.2.2  yamt 		crc_spd |= (sc->sc_read)(sc, 126);
    202  1.2.2.2  yamt 		if (crc_calc != crc_spd) {
    203  1.2.2.2  yamt 			aprint_debug("crc16 failed, covers %d bytes, "
    204  1.2.2.2  yamt 				     "calc = 0x%04x, spd = 0x%04x\n",
    205  1.2.2.2  yamt 				     spd_crc_cover, crc_calc, crc_spd);
    206  1.2.2.2  yamt 			return 0;
    207  1.2.2.2  yamt 		}
    208  1.2.2.2  yamt 		return 1;
    209  1.2.2.2  yamt 	}
    210  1.2.2.2  yamt 
    211  1.2.2.2  yamt 	/* For unrecognized memory types, don't match at all */
    212  1.2.2.2  yamt 	return 0;
    213  1.2.2.2  yamt }
    214  1.2.2.2  yamt 
    215  1.2.2.2  yamt void
    216  1.2.2.2  yamt spdmem_common_attach(struct spdmem_softc *sc, device_t self)
    217  1.2.2.2  yamt {
    218  1.2.2.2  yamt 	struct spdmem *s = &(sc->sc_spd_data);
    219  1.2.2.2  yamt 	const char *type;
    220  1.2.2.2  yamt 	const char *rambus_rev = "Reserved";
    221  1.2.2.2  yamt 	int dimm_size;
    222  1.2.2.2  yamt 	int i;
    223  1.2.2.2  yamt 	unsigned int spd_len, spd_size;
    224  1.2.2.2  yamt 	const struct sysctlnode *node = NULL;
    225  1.2.2.2  yamt 
    226  1.2.2.2  yamt 	/*
    227  1.2.2.2  yamt 	 * FBDIMM and DDR3 (and probably all newer) have a different
    228  1.2.2.2  yamt 	 * encoding of the SPD EEPROM used/total sizes
    229  1.2.2.2  yamt 	 */
    230  1.2.2.2  yamt 	s->sm_len = (sc->sc_read)(sc, 0);
    231  1.2.2.2  yamt 	s->sm_size = (sc->sc_read)(sc, 1);
    232  1.2.2.2  yamt 	s->sm_type = (sc->sc_read)(sc, 2);
    233  1.2.2.2  yamt 
    234  1.2.2.2  yamt 	if (s->sm_type >= SPDMEM_MEMTYPE_FBDIMM) {
    235  1.2.2.2  yamt 		spd_size = 64 << (s->sm_len & SPDMEM_SPDSIZE_MASK);
    236  1.2.2.2  yamt 		switch (s->sm_len & SPDMEM_SPDLEN_MASK) {
    237  1.2.2.2  yamt 		case SPDMEM_SPDLEN_128:
    238  1.2.2.2  yamt 			spd_len = 128;
    239  1.2.2.2  yamt 			break;
    240  1.2.2.2  yamt 		case SPDMEM_SPDLEN_176:
    241  1.2.2.2  yamt 			spd_len = 176;
    242  1.2.2.2  yamt 			break;
    243  1.2.2.2  yamt 		case SPDMEM_SPDLEN_256:
    244  1.2.2.2  yamt 			spd_len = 256;
    245  1.2.2.2  yamt 			break;
    246  1.2.2.2  yamt 		default:
    247  1.2.2.2  yamt 			spd_len = 64;
    248  1.2.2.2  yamt 			break;
    249  1.2.2.2  yamt 		}
    250  1.2.2.2  yamt 	} else {
    251  1.2.2.2  yamt 		spd_size = 1 << s->sm_size;
    252  1.2.2.2  yamt 		spd_len = s->sm_len;
    253  1.2.2.2  yamt 		if (spd_len < 64)
    254  1.2.2.2  yamt 			spd_len = 64;
    255  1.2.2.2  yamt 	}
    256  1.2.2.2  yamt 	if (spd_len > spd_size)
    257  1.2.2.2  yamt 		spd_len = spd_size;
    258  1.2.2.2  yamt 	if (spd_len > sizeof(struct spdmem))
    259  1.2.2.2  yamt 		spd_len = sizeof(struct spdmem);
    260  1.2.2.2  yamt 	for (i = 3; i < spd_len; i++)
    261  1.2.2.2  yamt 		((uint8_t *)s)[i] = (sc->sc_read)(sc, i);
    262  1.2.2.2  yamt 
    263  1.2.2.2  yamt #ifdef DEBUG
    264  1.2.2.2  yamt 	for (i = 0; i < spd_len;  i += 16) {
    265  1.2.2.2  yamt 		int j, k;
    266  1.2.2.2  yamt 		aprint_debug("\n");
    267  1.2.2.2  yamt 		aprint_debug_dev(self, "0x%02x:", i);
    268  1.2.2.2  yamt 		k = (spd_len > i + 16) ? spd_len : i + 16;
    269  1.2.2.2  yamt 		for (j = i; j < k; j++)
    270  1.2.2.2  yamt 			aprint_debug(" %02x", ((uint8_t *)s)[j]);
    271  1.2.2.2  yamt 	}
    272  1.2.2.2  yamt 	aprint_debug("\n");
    273  1.2.2.2  yamt 	aprint_debug_dev(self, "");
    274  1.2.2.2  yamt #endif
    275  1.2.2.2  yamt 
    276  1.2.2.2  yamt 	/*
    277  1.2.2.2  yamt 	 * Setup our sysctl subtree, hw.spdmemN
    278  1.2.2.2  yamt 	 */
    279  1.2.2.2  yamt 	if (hw_node != CTL_EOL)
    280  1.2.2.2  yamt 		sysctl_createv(NULL, 0, NULL, &node,
    281  1.2.2.2  yamt 		    0, CTLTYPE_NODE,
    282  1.2.2.2  yamt 		    device_xname(self), NULL, NULL, 0, NULL, 0,
    283  1.2.2.2  yamt 		    CTL_HW, CTL_CREATE, CTL_EOL);
    284  1.2.2.2  yamt 	if (node != NULL && spd_len != 0)
    285  1.2.2.2  yamt                 sysctl_createv(NULL, 0, NULL, NULL,
    286  1.2.2.2  yamt                     0,
    287  1.2.2.2  yamt                     CTLTYPE_STRUCT, "spd_data",
    288  1.2.2.2  yamt 		    SYSCTL_DESCR("raw spd data"), NULL,
    289  1.2.2.2  yamt                     0, s, spd_len,
    290  1.2.2.2  yamt                     CTL_HW, node->sysctl_num, CTL_CREATE, CTL_EOL);
    291  1.2.2.2  yamt 
    292  1.2.2.2  yamt 	/*
    293  1.2.2.2  yamt 	 * Decode and print key SPD contents
    294  1.2.2.2  yamt 	 */
    295  1.2.2.2  yamt 	if (IS_RAMBUS_TYPE) {
    296  1.2.2.2  yamt 		if (s->sm_type == SPDMEM_MEMTYPE_RAMBUS)
    297  1.2.2.2  yamt 			type = "Rambus";
    298  1.2.2.2  yamt 		else if (s->sm_type == SPDMEM_MEMTYPE_DIRECTRAMBUS)
    299  1.2.2.2  yamt 			type = "Direct Rambus";
    300  1.2.2.2  yamt 		else
    301  1.2.2.2  yamt 			type = "Rambus (unknown)";
    302  1.2.2.2  yamt 
    303  1.2.2.2  yamt 		switch (s->sm_len) {
    304  1.2.2.2  yamt 		case 0:
    305  1.2.2.2  yamt 			rambus_rev = "Invalid";
    306  1.2.2.2  yamt 			break;
    307  1.2.2.2  yamt 		case 1:
    308  1.2.2.2  yamt 			rambus_rev = "0.7";
    309  1.2.2.2  yamt 			break;
    310  1.2.2.2  yamt 		case 2:
    311  1.2.2.2  yamt 			rambus_rev = "1.0";
    312  1.2.2.2  yamt 			break;
    313  1.2.2.2  yamt 		default:
    314  1.2.2.2  yamt 			rambus_rev = "Reserved";
    315  1.2.2.2  yamt 			break;
    316  1.2.2.2  yamt 		}
    317  1.2.2.2  yamt 	} else {
    318  1.2.2.2  yamt 		if (s->sm_type < __arraycount(spdmem_basic_types))
    319  1.2.2.2  yamt 			type = spdmem_basic_types[s->sm_type];
    320  1.2.2.2  yamt 		else
    321  1.2.2.2  yamt 			type = "unknown memory type";
    322  1.2.2.2  yamt 
    323  1.2.2.2  yamt 		if (s->sm_type == SPDMEM_MEMTYPE_EDO &&
    324  1.2.2.2  yamt 		    s->sm_fpm.fpm_superset == SPDMEM_SUPERSET_EDO_PEM)
    325  1.2.2.2  yamt 			type = spdmem_superset_types[SPDMEM_SUPERSET_EDO_PEM];
    326  1.2.2.2  yamt 		if (s->sm_type == SPDMEM_MEMTYPE_SDRAM &&
    327  1.2.2.2  yamt 		    s->sm_sdr.sdr_superset == SPDMEM_SUPERSET_SDRAM_PEM)
    328  1.2.2.2  yamt 			type = spdmem_superset_types[SPDMEM_SUPERSET_SDRAM_PEM];
    329  1.2.2.2  yamt 		if (s->sm_type == SPDMEM_MEMTYPE_DDRSDRAM &&
    330  1.2.2.2  yamt 		    s->sm_ddr.ddr_superset == SPDMEM_SUPERSET_DDR_ESDRAM)
    331  1.2.2.2  yamt 			type =
    332  1.2.2.2  yamt 			    spdmem_superset_types[SPDMEM_SUPERSET_DDR_ESDRAM];
    333  1.2.2.2  yamt 		if (s->sm_type == SPDMEM_MEMTYPE_SDRAM &&
    334  1.2.2.2  yamt 		    s->sm_sdr.sdr_superset == SPDMEM_SUPERSET_ESDRAM) {
    335  1.2.2.2  yamt 			type = spdmem_superset_types[SPDMEM_SUPERSET_ESDRAM];
    336  1.2.2.2  yamt 		}
    337  1.2.2.2  yamt 	}
    338  1.2.2.2  yamt 
    339  1.2.2.2  yamt 	aprint_naive("\n");
    340  1.2.2.2  yamt 	aprint_normal("\n");
    341  1.2.2.2  yamt 	aprint_normal_dev(self, "%s", type);
    342  1.2.2.2  yamt 	strlcpy(sc->sc_type, type, SPDMEM_TYPE_MAXLEN);
    343  1.2.2.2  yamt 	if (node != NULL)
    344  1.2.2.2  yamt 		sysctl_createv(NULL, 0, NULL, NULL,
    345  1.2.2.2  yamt 		    0,
    346  1.2.2.2  yamt 		    CTLTYPE_STRING, "mem_type",
    347  1.2.2.2  yamt 		    SYSCTL_DESCR("memory module type"), NULL,
    348  1.2.2.2  yamt 		    0, sc->sc_type, 0,
    349  1.2.2.2  yamt 		    CTL_HW, node->sysctl_num, CTL_CREATE, CTL_EOL);
    350  1.2.2.2  yamt 
    351  1.2.2.2  yamt 	if (IS_RAMBUS_TYPE) {
    352  1.2.2.2  yamt 		aprint_normal(", SPD Revision %s", rambus_rev);
    353  1.2.2.2  yamt 		dimm_size = 1 << (s->sm_rdr.rdr_rows + s->sm_rdr.rdr_cols - 13);
    354  1.2.2.2  yamt 		if (dimm_size >= 1024)
    355  1.2.2.2  yamt 			aprint_normal(", %dGB\n", dimm_size / 1024);
    356  1.2.2.2  yamt 		else
    357  1.2.2.2  yamt 			aprint_normal(", %dMB\n", dimm_size);
    358  1.2.2.2  yamt 
    359  1.2.2.2  yamt 		/* No further decode for RAMBUS memory */
    360  1.2.2.2  yamt 		return;
    361  1.2.2.2  yamt 	}
    362  1.2.2.2  yamt 	switch (s->sm_type) {
    363  1.2.2.2  yamt 	case SPDMEM_MEMTYPE_EDO:
    364  1.2.2.2  yamt 	case SPDMEM_MEMTYPE_FPM:
    365  1.2.2.2  yamt 		decode_edofpm(node, self, s);
    366  1.2.2.2  yamt 		break;
    367  1.2.2.2  yamt 	case SPDMEM_MEMTYPE_ROM:
    368  1.2.2.2  yamt 		decode_rom(node, self, s);
    369  1.2.2.2  yamt 		break;
    370  1.2.2.2  yamt 	case SPDMEM_MEMTYPE_SDRAM:
    371  1.2.2.2  yamt 		decode_sdram(node, self, s, spd_len);
    372  1.2.2.2  yamt 		break;
    373  1.2.2.2  yamt 	case SPDMEM_MEMTYPE_DDRSDRAM:
    374  1.2.2.2  yamt 		decode_ddr(node, self, s);
    375  1.2.2.2  yamt 		break;
    376  1.2.2.2  yamt 	case SPDMEM_MEMTYPE_DDR2SDRAM:
    377  1.2.2.2  yamt 		decode_ddr2(node, self, s);
    378  1.2.2.2  yamt 		break;
    379  1.2.2.2  yamt 	case SPDMEM_MEMTYPE_DDR3SDRAM:
    380  1.2.2.2  yamt 		decode_ddr3(node, self, s);
    381  1.2.2.2  yamt 		break;
    382  1.2.2.2  yamt 	case SPDMEM_MEMTYPE_FBDIMM:
    383  1.2.2.2  yamt 	case SPDMEM_MEMTYPE_FBDIMM_PROBE:
    384  1.2.2.2  yamt 		decode_fbdimm(node, self, s);
    385  1.2.2.2  yamt 		break;
    386  1.2.2.2  yamt 	}
    387  1.2.2.2  yamt }
    388  1.2.2.2  yamt 
    389  1.2.2.2  yamt SYSCTL_SETUP(sysctl_spdmem_setup, "sysctl hw.spdmem subtree setup")
    390  1.2.2.2  yamt {
    391  1.2.2.2  yamt 	const struct sysctlnode *node;
    392  1.2.2.2  yamt 
    393  1.2.2.2  yamt 	if (sysctl_createv(clog, 0, NULL, &node,
    394  1.2.2.2  yamt 	    CTLFLAG_PERMANENT,
    395  1.2.2.2  yamt 	    CTLTYPE_NODE, "hw", NULL,
    396  1.2.2.2  yamt 	    NULL, 0, NULL, 0,
    397  1.2.2.2  yamt 	    CTL_HW, CTL_EOL) != 0)
    398  1.2.2.2  yamt 		return;
    399  1.2.2.2  yamt 
    400  1.2.2.2  yamt 	hw_node = node->sysctl_num;
    401  1.2.2.2  yamt }
    402  1.2.2.2  yamt 
    403  1.2.2.2  yamt static void
    404  1.2.2.2  yamt decode_size_speed(const struct sysctlnode *node, int dimm_size, int cycle_time,
    405  1.2.2.2  yamt 		  int d_clk, int bits, bool round, const char *ddr_type_string,
    406  1.2.2.2  yamt 		  int speed)
    407  1.2.2.2  yamt {
    408  1.2.2.2  yamt 	int p_clk;
    409  1.2.2.2  yamt 
    410  1.2.2.2  yamt 	if (dimm_size < 1024)
    411  1.2.2.2  yamt 		aprint_normal("%dMB", dimm_size);
    412  1.2.2.2  yamt 	else
    413  1.2.2.2  yamt 		aprint_normal("%dGB", dimm_size / 1024);
    414  1.2.2.2  yamt 	if (node != NULL)
    415  1.2.2.2  yamt 		sysctl_createv(NULL, 0, NULL, NULL,
    416  1.2.2.2  yamt 		    CTLFLAG_IMMEDIATE,
    417  1.2.2.2  yamt 		    CTLTYPE_INT, "size",
    418  1.2.2.2  yamt 		    SYSCTL_DESCR("module size in MB"), NULL,
    419  1.2.2.2  yamt 		    dimm_size, NULL, 0,
    420  1.2.2.2  yamt 		    CTL_HW, node->sysctl_num, CTL_CREATE, CTL_EOL);
    421  1.2.2.2  yamt 
    422  1.2.2.2  yamt 	if (cycle_time == 0) {
    423  1.2.2.2  yamt 		aprint_normal("\n");
    424  1.2.2.2  yamt 		return;
    425  1.2.2.2  yamt 	}
    426  1.2.2.2  yamt 
    427  1.2.2.2  yamt 	/*
    428  1.2.2.2  yamt 	 * Calculate p_clk first, since for DDR3 we need maximum significance.
    429  1.2.2.2  yamt 	 * DDR3 rating is not rounded to a multiple of 100.  This results in
    430  1.2.2.2  yamt 	 * cycle_time of 1.5ns displayed as PC3-10666.
    431  1.2.2.2  yamt 	 *
    432  1.2.2.2  yamt 	 * For SDRAM, the speed is provided by the caller so we use it.
    433  1.2.2.2  yamt 	 */
    434  1.2.2.2  yamt 	d_clk *= 1000 * 1000;
    435  1.2.2.2  yamt 	if (speed)
    436  1.2.2.2  yamt 		p_clk = speed;
    437  1.2.2.2  yamt 	else
    438  1.2.2.2  yamt 		p_clk = (d_clk * bits) / 8 / cycle_time;
    439  1.2.2.2  yamt 	d_clk = ((d_clk + cycle_time / 2) ) / cycle_time;
    440  1.2.2.2  yamt 	if (round) {
    441  1.2.2.2  yamt 		if ((p_clk % 100) >= 50)
    442  1.2.2.2  yamt 			p_clk += 50;
    443  1.2.2.2  yamt 		p_clk -= p_clk % 100;
    444  1.2.2.2  yamt 	}
    445  1.2.2.2  yamt 	aprint_normal(", %dMHz (%s-%d)\n",
    446  1.2.2.2  yamt 		      d_clk, ddr_type_string, p_clk);
    447  1.2.2.2  yamt 	if (node != NULL)
    448  1.2.2.2  yamt 		sysctl_createv(NULL, 0, NULL, NULL,
    449  1.2.2.2  yamt 			       CTLFLAG_IMMEDIATE,
    450  1.2.2.2  yamt 			       CTLTYPE_INT, "speed",
    451  1.2.2.2  yamt 			       SYSCTL_DESCR("memory speed in MHz"),
    452  1.2.2.2  yamt 			       NULL, d_clk, NULL, 0,
    453  1.2.2.2  yamt 			       CTL_HW, node->sysctl_num, CTL_CREATE, CTL_EOL);
    454  1.2.2.2  yamt }
    455  1.2.2.2  yamt 
    456  1.2.2.2  yamt static void
    457  1.2.2.2  yamt decode_voltage_refresh(device_t self, struct spdmem *s)
    458  1.2.2.2  yamt {
    459  1.2.2.2  yamt 	const char *voltage, *refresh;
    460  1.2.2.2  yamt 
    461  1.2.2.2  yamt 	if (s->sm_voltage < __arraycount(spdmem_voltage_types))
    462  1.2.2.2  yamt 		voltage = spdmem_voltage_types[s->sm_voltage];
    463  1.2.2.2  yamt 	else
    464  1.2.2.2  yamt 		voltage = "unknown";
    465  1.2.2.2  yamt 
    466  1.2.2.2  yamt 	if (s->sm_refresh < __arraycount(spdmem_refresh_types))
    467  1.2.2.2  yamt 		refresh = spdmem_refresh_types[s->sm_refresh];
    468  1.2.2.2  yamt 	else
    469  1.2.2.2  yamt 		refresh = "unknown";
    470  1.2.2.2  yamt 
    471  1.2.2.2  yamt 	aprint_verbose_dev(self, "voltage %s, refresh time %s%s\n",
    472  1.2.2.2  yamt 			voltage, refresh,
    473  1.2.2.2  yamt 			s->sm_selfrefresh?" (self-refreshing)":"");
    474  1.2.2.2  yamt }
    475  1.2.2.2  yamt 
    476  1.2.2.2  yamt static void
    477  1.2.2.2  yamt decode_edofpm(const struct sysctlnode *node, device_t self, struct spdmem *s) {
    478  1.2.2.2  yamt 	aprint_normal("\n");
    479  1.2.2.2  yamt 	aprint_verbose_dev(self,
    480  1.2.2.2  yamt 	    "%d rows, %d cols, %d banks, %dns tRAC, %dns tCAC\n",
    481  1.2.2.2  yamt 	    s->sm_fpm.fpm_rows, s->sm_fpm.fpm_cols, s->sm_fpm.fpm_banks,
    482  1.2.2.2  yamt 	    s->sm_fpm.fpm_tRAC, s->sm_fpm.fpm_tCAC);
    483  1.2.2.2  yamt }
    484  1.2.2.2  yamt 
    485  1.2.2.2  yamt static void
    486  1.2.2.2  yamt decode_rom(const struct sysctlnode *node, device_t self, struct spdmem *s) {
    487  1.2.2.2  yamt 	aprint_normal("\n");
    488  1.2.2.2  yamt 	aprint_verbose_dev(self, "%d rows, %d cols, %d banks\n",
    489  1.2.2.2  yamt 	    s->sm_rom.rom_rows, s->sm_rom.rom_cols, s->sm_rom.rom_banks);
    490  1.2.2.2  yamt }
    491  1.2.2.2  yamt 
    492  1.2.2.2  yamt static void
    493  1.2.2.2  yamt decode_sdram(const struct sysctlnode *node, device_t self, struct spdmem *s,
    494  1.2.2.2  yamt 	     int spd_len) {
    495  1.2.2.2  yamt 	int dimm_size, cycle_time, bits, tAA, i, speed, freq;
    496  1.2.2.2  yamt 
    497  1.2.2.2  yamt 	aprint_normal("%s, %s, ",
    498  1.2.2.2  yamt 		(s->sm_sdr.sdr_mod_attrs & SPDMEM_SDR_MASK_REG)?
    499  1.2.2.2  yamt 			" (registered)":"",
    500  1.2.2.2  yamt 		(s->sm_config < __arraycount(spdmem_parity_types))?
    501  1.2.2.2  yamt 			spdmem_parity_types[s->sm_config]:"invalid parity");
    502  1.2.2.2  yamt 
    503  1.2.2.2  yamt 	dimm_size = 1 << (s->sm_sdr.sdr_rows + s->sm_sdr.sdr_cols - 17);
    504  1.2.2.2  yamt 	dimm_size *= s->sm_sdr.sdr_banks * s->sm_sdr.sdr_banks_per_chip;
    505  1.2.2.2  yamt 
    506  1.2.2.2  yamt 	cycle_time = s->sm_sdr.sdr_cycle_whole * 1000 +
    507  1.2.2.2  yamt 		     s->sm_sdr.sdr_cycle_tenths * 100;
    508  1.2.2.2  yamt 	bits = le16toh(s->sm_sdr.sdr_datawidth);
    509  1.2.2.2  yamt 	if (s->sm_config == 1 || s->sm_config == 2)
    510  1.2.2.2  yamt 		bits -= 8;
    511  1.2.2.2  yamt 
    512  1.2.2.2  yamt 	/* Calculate speed here - from OpenBSD */
    513  1.2.2.2  yamt 	if (spd_len >= 128)
    514  1.2.2.2  yamt 		freq = ((uint8_t *)s)[126];
    515  1.2.2.2  yamt 	else
    516  1.2.2.2  yamt 		freq = 0;
    517  1.2.2.2  yamt 	switch (freq) {
    518  1.2.2.2  yamt 		/*
    519  1.2.2.2  yamt 		 * Must check cycle time since some PC-133 DIMMs
    520  1.2.2.2  yamt 		 * actually report PC-100
    521  1.2.2.2  yamt 		 */
    522  1.2.2.2  yamt 	    case 100:
    523  1.2.2.2  yamt 	    case 133:
    524  1.2.2.2  yamt 		if (cycle_time < 8000)
    525  1.2.2.2  yamt 			speed = 133;
    526  1.2.2.2  yamt 		else
    527  1.2.2.2  yamt 			speed = 100;
    528  1.2.2.2  yamt 		break;
    529  1.2.2.2  yamt 	    case 0x66:		/* Legacy DIMMs use _hex_ 66! */
    530  1.2.2.2  yamt 	    default:
    531  1.2.2.2  yamt 		speed = 66;
    532  1.2.2.2  yamt 	}
    533  1.2.2.2  yamt 	decode_size_speed(node, dimm_size, cycle_time, 1, bits, FALSE, "PC",
    534  1.2.2.2  yamt 			  speed);
    535  1.2.2.2  yamt 
    536  1.2.2.2  yamt 	aprint_verbose_dev(self,
    537  1.2.2.2  yamt 	    "%d rows, %d cols, %d banks, %d banks/chip, %d.%dns cycle time\n",
    538  1.2.2.2  yamt 	    s->sm_sdr.sdr_rows, s->sm_sdr.sdr_cols, s->sm_sdr.sdr_banks,
    539  1.2.2.2  yamt 	    s->sm_sdr.sdr_banks_per_chip, cycle_time/1000,
    540  1.2.2.2  yamt 	    (cycle_time % 1000) / 100);
    541  1.2.2.2  yamt 
    542  1.2.2.2  yamt 	tAA  = 0;
    543  1.2.2.2  yamt 	for (i = 0; i < 8; i++)
    544  1.2.2.2  yamt 		if (s->sm_sdr.sdr_tCAS & (1 << i))
    545  1.2.2.2  yamt 			tAA = i;
    546  1.2.2.2  yamt 	tAA++;
    547  1.2.2.2  yamt 	aprint_verbose_dev(self, latency, tAA, s->sm_sdr.sdr_tRCD,
    548  1.2.2.2  yamt 	    s->sm_sdr.sdr_tRP, s->sm_sdr.sdr_tRAS);
    549  1.2.2.2  yamt 
    550  1.2.2.2  yamt 	decode_voltage_refresh(self, s);
    551  1.2.2.2  yamt }
    552  1.2.2.2  yamt 
    553  1.2.2.2  yamt static void
    554  1.2.2.2  yamt decode_ddr(const struct sysctlnode *node, device_t self, struct spdmem *s) {
    555  1.2.2.2  yamt 	int dimm_size, cycle_time, bits, tAA, i;
    556  1.2.2.2  yamt 
    557  1.2.2.2  yamt 	aprint_normal("%s, %s, ",
    558  1.2.2.2  yamt 		(s->sm_ddr.ddr_mod_attrs & SPDMEM_DDR_MASK_REG)?
    559  1.2.2.2  yamt 			" (registered)":"",
    560  1.2.2.2  yamt 		(s->sm_config < __arraycount(spdmem_parity_types))?
    561  1.2.2.2  yamt 			spdmem_parity_types[s->sm_config]:"invalid parity");
    562  1.2.2.2  yamt 
    563  1.2.2.2  yamt 	dimm_size = 1 << (s->sm_ddr.ddr_rows + s->sm_ddr.ddr_cols - 17);
    564  1.2.2.2  yamt 	dimm_size *= s->sm_ddr.ddr_ranks * s->sm_ddr.ddr_banks_per_chip;
    565  1.2.2.2  yamt 
    566  1.2.2.2  yamt 	cycle_time = s->sm_ddr.ddr_cycle_whole * 1000 +
    567  1.2.2.2  yamt 		  spdmem_cycle_frac[s->sm_ddr.ddr_cycle_tenths];
    568  1.2.2.2  yamt 	bits = le16toh(s->sm_ddr.ddr_datawidth);
    569  1.2.2.2  yamt 	if (s->sm_config == 1 || s->sm_config == 2)
    570  1.2.2.2  yamt 		bits -= 8;
    571  1.2.2.2  yamt 	decode_size_speed(node, dimm_size, cycle_time, 2, bits, TRUE, "PC", 0);
    572  1.2.2.2  yamt 
    573  1.2.2.2  yamt 	aprint_verbose_dev(self,
    574  1.2.2.2  yamt 	    "%d rows, %d cols, %d ranks, %d banks/chip, %d.%dns cycle time\n",
    575  1.2.2.2  yamt 	    s->sm_ddr.ddr_rows, s->sm_ddr.ddr_cols, s->sm_ddr.ddr_ranks,
    576  1.2.2.2  yamt 	    s->sm_ddr.ddr_banks_per_chip, cycle_time/1000,
    577  1.2.2.2  yamt 	    (cycle_time % 1000 + 50) / 100);
    578  1.2.2.2  yamt 
    579  1.2.2.2  yamt 	tAA  = 0;
    580  1.2.2.2  yamt 	for (i = 2; i < 8; i++)
    581  1.2.2.2  yamt 		if (s->sm_ddr.ddr_tCAS & (1 << i))
    582  1.2.2.2  yamt 			tAA = i;
    583  1.2.2.2  yamt 	tAA /= 2;
    584  1.2.2.2  yamt 
    585  1.2.2.2  yamt #define __DDR_ROUND(scale, field)	\
    586  1.2.2.2  yamt 		((scale * s->sm_ddr.field + cycle_time - 1) / cycle_time)
    587  1.2.2.2  yamt 
    588  1.2.2.2  yamt 	aprint_verbose_dev(self, latency, tAA, __DDR_ROUND(250, ddr_tRCD),
    589  1.2.2.2  yamt 		__DDR_ROUND(250, ddr_tRP), __DDR_ROUND(1000, ddr_tRAS));
    590  1.2.2.2  yamt 
    591  1.2.2.2  yamt #undef	__DDR_ROUND
    592  1.2.2.2  yamt 
    593  1.2.2.2  yamt 	decode_voltage_refresh(self, s);
    594  1.2.2.2  yamt }
    595  1.2.2.2  yamt 
    596  1.2.2.2  yamt static void
    597  1.2.2.2  yamt decode_ddr2(const struct sysctlnode *node, device_t self, struct spdmem *s) {
    598  1.2.2.2  yamt 	int dimm_size, cycle_time, bits, tAA, i;
    599  1.2.2.2  yamt 
    600  1.2.2.2  yamt 	aprint_normal("%s, %s, ",
    601  1.2.2.2  yamt 		(s->sm_ddr2.ddr2_mod_attrs & SPDMEM_DDR2_MASK_REG)?
    602  1.2.2.2  yamt 			" (registered)":"",
    603  1.2.2.2  yamt 		(s->sm_config < __arraycount(spdmem_parity_types))?
    604  1.2.2.2  yamt 			spdmem_parity_types[s->sm_config]:"invalid parity");
    605  1.2.2.2  yamt 
    606  1.2.2.2  yamt 	dimm_size = 1 << (s->sm_ddr2.ddr2_rows + s->sm_ddr2.ddr2_cols - 17);
    607  1.2.2.2  yamt 	dimm_size *= (s->sm_ddr2.ddr2_ranks + 1) *
    608  1.2.2.2  yamt 		     s->sm_ddr2.ddr2_banks_per_chip;
    609  1.2.2.2  yamt 
    610  1.2.2.2  yamt 	cycle_time = s->sm_ddr2.ddr2_cycle_whole * 1000 +
    611  1.2.2.2  yamt 		 spdmem_cycle_frac[s->sm_ddr2.ddr2_cycle_frac];
    612  1.2.2.2  yamt 	bits = s->sm_ddr2.ddr2_datawidth;
    613  1.2.2.2  yamt 	if ((s->sm_config & 0x03) != 0)
    614  1.2.2.2  yamt 		bits -= 8;
    615  1.2.2.2  yamt 	decode_size_speed(node, dimm_size, cycle_time, 2, bits, TRUE, "PC2", 0);
    616  1.2.2.2  yamt 
    617  1.2.2.2  yamt 	aprint_verbose_dev(self,
    618  1.2.2.2  yamt 	    "%d rows, %d cols, %d ranks, %d banks/chip, %d.%02dns cycle time\n",
    619  1.2.2.2  yamt 	    s->sm_ddr2.ddr2_rows, s->sm_ddr2.ddr2_cols,
    620  1.2.2.2  yamt 	    s->sm_ddr2.ddr2_ranks + 1, s->sm_ddr2.ddr2_banks_per_chip,
    621  1.2.2.2  yamt 	    cycle_time / 1000, (cycle_time % 1000 + 5) /10 );
    622  1.2.2.2  yamt 
    623  1.2.2.2  yamt 	tAA  = 0;
    624  1.2.2.2  yamt 	for (i = 2; i < 8; i++)
    625  1.2.2.2  yamt 		if (s->sm_ddr2.ddr2_tCAS & (1 << i))
    626  1.2.2.2  yamt 			tAA = i;
    627  1.2.2.2  yamt 
    628  1.2.2.2  yamt #define __DDR2_ROUND(scale, field)	\
    629  1.2.2.2  yamt 		((scale * s->sm_ddr2.field + cycle_time - 1) / cycle_time)
    630  1.2.2.2  yamt 
    631  1.2.2.2  yamt 	aprint_verbose_dev(self, latency, tAA, __DDR2_ROUND(250, ddr2_tRCD),
    632  1.2.2.2  yamt 		__DDR2_ROUND(250, ddr2_tRP), __DDR2_ROUND(1000, ddr2_tRAS));
    633  1.2.2.2  yamt 
    634  1.2.2.2  yamt #undef	__DDR_ROUND
    635  1.2.2.2  yamt 
    636  1.2.2.2  yamt 	decode_voltage_refresh(self, s);
    637  1.2.2.2  yamt }
    638  1.2.2.2  yamt 
    639  1.2.2.2  yamt static void
    640  1.2.2.2  yamt decode_ddr3(const struct sysctlnode *node, device_t self, struct spdmem *s) {
    641  1.2.2.2  yamt 	int dimm_size, cycle_time, bits;
    642  1.2.2.2  yamt 
    643  1.2.2.2  yamt 	if (s->sm_ddr3.ddr3_mod_type ==
    644  1.2.2.2  yamt 		SPDMEM_DDR3_TYPE_MINI_RDIMM ||
    645  1.2.2.2  yamt 	    s->sm_ddr3.ddr3_mod_type == SPDMEM_DDR3_TYPE_RDIMM)
    646  1.2.2.2  yamt 		aprint_normal(" (registered)");
    647  1.2.2.2  yamt 	aprint_normal(", %sECC, %stemp-sensor, ",
    648  1.2.2.2  yamt 		(s->sm_ddr3.ddr3_hasECC)?"":"no ",
    649  1.2.2.2  yamt 		(s->sm_ddr3.ddr3_has_therm_sensor)?"":"no ");
    650  1.2.2.2  yamt 
    651  1.2.2.2  yamt 	/*
    652  1.2.2.2  yamt 	 * DDR3 size specification is quite different from others
    653  1.2.2.2  yamt 	 *
    654  1.2.2.2  yamt 	 * Module capacity is defined as
    655  1.2.2.2  yamt 	 *	Chip_Capacity_in_bits / 8bits-per-byte *
    656  1.2.2.2  yamt 	 *	external_bus_width / internal_bus_width
    657  1.2.2.2  yamt 	 * We further divide by 2**20 to get our answer in MB
    658  1.2.2.2  yamt 	 */
    659  1.2.2.2  yamt 	dimm_size = (s->sm_ddr3.ddr3_chipsize + 28 - 20) - 3 +
    660  1.2.2.2  yamt 		    (s->sm_ddr3.ddr3_datawidth + 3) -
    661  1.2.2.2  yamt 		    (s->sm_ddr3.ddr3_chipwidth + 2);
    662  1.2.2.2  yamt 	dimm_size = (1 << dimm_size) * (s->sm_ddr3.ddr3_physbanks + 1);
    663  1.2.2.2  yamt 
    664  1.2.2.2  yamt 	cycle_time = (1000 * s->sm_ddr3.ddr3_mtb_dividend +
    665  1.2.2.2  yamt 			    (s->sm_ddr3.ddr3_mtb_divisor / 2)) /
    666  1.2.2.2  yamt 		     s->sm_ddr3.ddr3_mtb_divisor;
    667  1.2.2.2  yamt 	cycle_time *= s->sm_ddr3.ddr3_tCKmin;
    668  1.2.2.2  yamt 	bits = 1 << (s->sm_ddr3.ddr3_datawidth + 3);
    669  1.2.2.2  yamt 	decode_size_speed(node, dimm_size, cycle_time, 2, bits, FALSE, "PC3", 0);
    670  1.2.2.2  yamt 
    671  1.2.2.2  yamt 	aprint_verbose_dev(self,
    672  1.2.2.2  yamt 	    "%d rows, %d cols, %d log. banks, %d phys. banks, "
    673  1.2.2.2  yamt 	    "%d.%03dns cycle time\n",
    674  1.2.2.2  yamt 	    s->sm_ddr3.ddr3_rows + 9, s->sm_ddr3.ddr3_cols + 12,
    675  1.2.2.2  yamt 	    1 << (s->sm_ddr3.ddr3_logbanks + 3),
    676  1.2.2.2  yamt 	    s->sm_ddr3.ddr3_physbanks + 1,
    677  1.2.2.2  yamt 	    cycle_time/1000, cycle_time % 1000);
    678  1.2.2.2  yamt 
    679  1.2.2.2  yamt #define	__DDR3_CYCLES(field) (s->sm_ddr3.field / s->sm_ddr3.ddr3_tCKmin)
    680  1.2.2.2  yamt 
    681  1.2.2.2  yamt 	aprint_verbose_dev(self, latency, __DDR3_CYCLES(ddr3_tAAmin),
    682  1.2.2.2  yamt 		__DDR3_CYCLES(ddr3_tRCDmin), __DDR3_CYCLES(ddr3_tRPmin),
    683  1.2.2.2  yamt 		(s->sm_ddr3.ddr3_tRAS_msb * 256 + s->sm_ddr3.ddr3_tRAS_lsb) /
    684  1.2.2.2  yamt 		    s->sm_ddr3.ddr3_tCKmin);
    685  1.2.2.2  yamt 
    686  1.2.2.2  yamt #undef	__DDR3_CYCLES
    687  1.2.2.2  yamt }
    688  1.2.2.2  yamt 
    689  1.2.2.2  yamt static void
    690  1.2.2.2  yamt decode_fbdimm(const struct sysctlnode *node, device_t self, struct spdmem *s) {
    691  1.2.2.2  yamt 	int dimm_size, cycle_time, bits;
    692  1.2.2.2  yamt 
    693  1.2.2.2  yamt 	/*
    694  1.2.2.2  yamt 	 * FB-DIMM module size calculation is very much like DDR3
    695  1.2.2.2  yamt 	 */
    696  1.2.2.2  yamt 	dimm_size = s->sm_fbd.fbdimm_rows + 12 +
    697  1.2.2.2  yamt 		    s->sm_fbd.fbdimm_cols +  9 - 20 - 3;
    698  1.2.2.2  yamt 	dimm_size = (1 << dimm_size) * (1 << (s->sm_fbd.fbdimm_banks + 2));
    699  1.2.2.2  yamt 
    700  1.2.2.2  yamt 	cycle_time = (1000 * s->sm_fbd.fbdimm_mtb_dividend +
    701  1.2.2.2  yamt 			    (s->sm_fbd.fbdimm_mtb_divisor / 2)) /
    702  1.2.2.2  yamt 		     s->sm_fbd.fbdimm_mtb_divisor;
    703  1.2.2.2  yamt 	bits = 1 << (s->sm_fbd.fbdimm_dev_width + 2);
    704  1.2.2.2  yamt 	decode_size_speed(node, dimm_size, cycle_time, 2, bits, TRUE, "PC2", 0);
    705  1.2.2.2  yamt 
    706  1.2.2.2  yamt 	aprint_verbose_dev(self,
    707  1.2.2.2  yamt 	    "%d rows, %d cols, %d banks, %d.%02dns cycle time\n",
    708  1.2.2.2  yamt 	    s->sm_fbd.fbdimm_rows, s->sm_fbd.fbdimm_cols,
    709  1.2.2.2  yamt 	    1 << (s->sm_fbd.fbdimm_banks + 2),
    710  1.2.2.2  yamt 	    cycle_time / 1000, (cycle_time % 1000 + 5) /10 );
    711  1.2.2.2  yamt 
    712  1.2.2.2  yamt #define	__FBDIMM_CYCLES(field) (s->sm_fbd.field / s->sm_fbd.fbdimm_tCKmin)
    713  1.2.2.2  yamt 
    714  1.2.2.2  yamt 	aprint_verbose_dev(self, latency, __FBDIMM_CYCLES(fbdimm_tAAmin),
    715  1.2.2.2  yamt 		__FBDIMM_CYCLES(fbdimm_tRCDmin), __FBDIMM_CYCLES(fbdimm_tRPmin),
    716  1.2.2.2  yamt 		(s->sm_fbd.fbdimm_tRAS_msb * 256 +
    717  1.2.2.2  yamt 			s->sm_fbd.fbdimm_tRAS_lsb) /
    718  1.2.2.2  yamt 		    s->sm_fbd.fbdimm_tCKmin);
    719  1.2.2.2  yamt 
    720  1.2.2.2  yamt #undef	__FBDIMM_CYCLES
    721  1.2.2.2  yamt 
    722  1.2.2.2  yamt 	decode_voltage_refresh(self, s);
    723  1.2.2.2  yamt }
    724