mirror of
https://github.com/memtest86plus/memtest86plus.git
synced 2025-02-25 18:55:23 -06:00
Replace SPD SKU reading code repeated multiple times across all the parse_spd_* functions with a dedicated read_sku function. Convert spd_infos.sku from len+data into classic NULL-terminated C-string. Takes the same space, but simplifies handling. Also, use char instead of uint8_t so no conversion is needed when printing. Change the way how the end of part number is handled. Stop on the first non-ASCII character and then trim all trailing spaces. This allows SKUs with two (or more) spaces inside the name to be handled properly. Finally, fix incorrect / inconsistent part number length handling, with the following end result: - parse_spd_sdram: 18 [73-90] (no change) - parse_spd_rdram: 18 [73-90] (no change) - parse_spd_ddr: 18 [73-90] (no change) - parse_spd_ddr2: 18 [73-90] (no change) - parse_spd_ddr3: 20+1=21 -> 18 [128-145] - parse_spd_ddr4: 20+1=21 -> 20 [329-348] - parse_spd_ddr5: 29+1=30 -> 30 [521-550] (technicaly no change) Before: text data bss total filename 13143 3795 18 16956 build32/system/smbus.o 11735 4359 18 16112 build64/system/smbus.o 81705 51133 13088 145926 build32/memtest_shared 79686 58109 294432 432227 build64/memtest_shared After: text data bss total filename 10784 3887 18 14689 build32/system/smbus.o 10486 4399 18 14903 build64/system/smbus.o 79353 51101 13088 143542 build32/memtest_shared 78438 58077 294432 430947 build64/memtest_shared gcc-11.3.0.
143 lines
3.4 KiB
C
143 lines
3.4 KiB
C
#ifndef _SMBUS_H_
|
|
#define _SMBUS_H_
|
|
/**
|
|
* SPDX-License-Identifier: GPL-2.0
|
|
*
|
|
* \file
|
|
*
|
|
* Provides functions for reading SPD via SMBUS
|
|
*
|
|
* Copyright (C) 2004-2022 Samuel Demeulemeester.
|
|
*/
|
|
|
|
/* Vendor IDs */
|
|
#define VID_ATI 0x1002
|
|
#define VID_AMD 0x1022
|
|
#define VID_SIS 0x1039
|
|
#define VID_NVIDIA 0x10DE
|
|
#define VID_VIA 0x1106
|
|
#define VID_SERVERWORKS 0x1166
|
|
#define VID_HYGON 0x1D94
|
|
#define VID_INTEL 0x8086
|
|
|
|
#define I2C_WRITE 0
|
|
#define I2C_READ 1
|
|
|
|
#define SPD5_MR11 11
|
|
|
|
/* i801 Hosts Addresses */
|
|
#define SMBHSTSTS smbusbase
|
|
#define SMBHSTCNT smbusbase + 2
|
|
#define SMBHSTCMD smbusbase + 3
|
|
#define SMBHSTADD smbusbase + 4
|
|
#define SMBHSTDAT0 smbusbase + 5
|
|
#define SMBHSTDAT1 smbusbase + 6
|
|
#define SMBBLKDAT smbusbase + 7
|
|
#define SMBPEC smbusbase + 8
|
|
#define SMBAUXSTS smbusbase + 12
|
|
#define SMBAUXCTL smbusbase + 13
|
|
|
|
/* i801 Hosts Status register bits */
|
|
#define SMBHSTSTS_BYTE_DONE 0x80
|
|
#define SMBHSTSTS_INUSE_STS 0x40
|
|
#define SMBHSTSTS_SMBALERT_STS 0x20
|
|
#define SMBHSTSTS_FAILED 0x10
|
|
#define SMBHSTSTS_BUS_ERR 0x08
|
|
#define SMBHSTSTS_DEV_ERR 0x04
|
|
#define SMBHSTSTS_INTR 0x02
|
|
#define SMBHSTSTS_HOST_BUSY 0x01
|
|
|
|
#define SMBHSTCNT_QUICK 0x00
|
|
#define SMBHSTCNT_BYTE 0x04
|
|
#define SMBHSTCNT_BYTE_DATA 0x08
|
|
#define SMBHSTCNT_WORD_DATA 0x0C
|
|
#define SMBHSTCNT_BLOCK_DATA 0x14
|
|
#define SMBHSTCNT_I2C_BLOCK_DATA 0x18
|
|
#define SMBHSTCNT_LAST_BYTE 0x20
|
|
#define SMBHSTCNT_START 0x40
|
|
|
|
/* AMD-Specific constants */
|
|
#define AMD_INDEX_IO_PORT 0xCD6
|
|
#define AMD_DATA_IO_PORT 0xCD7
|
|
#define AMD_SMBUS_BASE_REG 0x2C
|
|
#define AMD_PM_INDEX 0x00
|
|
|
|
/* nVidia-Specific constants */
|
|
#define NV_SMBUS_ADR_REG 0x20
|
|
#define NV_OLD_SMBUS_ADR_REG 0x50
|
|
|
|
#define NVSMBCNT smbusbase + 0
|
|
#define NVSMBSTS smbusbase + 1
|
|
#define NVSMBADD smbusbase + 2
|
|
#define NVSMBCMD smbusbase + 3
|
|
#define NVSMBDAT(x) (smbusbase + 4 + (x))
|
|
|
|
#define NVSMBCNT_WRITE 0x00
|
|
#define NVSMBCNT_READ 0x01
|
|
#define NVSMBCNT_QUICK 0x02
|
|
#define NVSMBCNT_BYTE 0x04
|
|
#define NVSMBCNT_BYTE_DATA 0x06
|
|
#define NVSMBCNT_WORD_DATA 0x08
|
|
|
|
#define NVSMBSTS_DONE 0x80
|
|
#define NVSMBSTS_ALRM 0x40
|
|
#define NVSMBSTS_RES 0x20
|
|
#define NVSMBSTS_STATUS 0x1f
|
|
|
|
/** Rounding factors for timing computation
|
|
*
|
|
* These factors are used as a configurable CEIL() function
|
|
* to get the upper int from a float past a specific decimal point.
|
|
*/
|
|
|
|
#define DDR5_ROUNDING_FACTOR 30
|
|
#define ROUNDING_FACTOR 0.9f
|
|
|
|
#define SPD_SKU_LEN 32
|
|
|
|
struct pci_smbus_controller {
|
|
unsigned vendor;
|
|
unsigned device;
|
|
void (*get_adr)(void);
|
|
};
|
|
|
|
typedef struct spd_infos {
|
|
bool isValid;
|
|
uint8_t slot_num;
|
|
uint16_t jedec_code;
|
|
uint32_t module_size;
|
|
char *type;
|
|
char sku[SPD_SKU_LEN + 1];
|
|
uint8_t XMP;
|
|
uint16_t freq;
|
|
bool hasECC;
|
|
uint8_t fab_year;
|
|
uint8_t fab_week;
|
|
uint16_t tCL;
|
|
uint8_t tCL_dec;
|
|
uint16_t tRCD;
|
|
uint16_t tRP;
|
|
uint16_t tRAS;
|
|
uint16_t tRC;
|
|
} spd_info;
|
|
|
|
typedef struct ram_infos {
|
|
uint16_t freq;
|
|
uint16_t tCL;
|
|
uint8_t tCL_dec;
|
|
uint16_t tRCD;
|
|
uint16_t tRP;
|
|
uint16_t tRAS;
|
|
char *type;
|
|
} ram_info;
|
|
|
|
extern ram_info ram;
|
|
|
|
/**
|
|
* Print SMBUS Info
|
|
*/
|
|
|
|
void print_smbus_startup_info(void);
|
|
|
|
#endif // SMBUS_H
|