Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   1) // SPDX-License-Identifier: GPL-2.0-or-later
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   3)  * k10temp.c - AMD Family 10h/11h/12h/14h/15h/16h/17h
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   4)  *		processor hardware monitoring
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   5)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   6)  * Copyright (c) 2009 Clemens Ladisch <clemens@ladisch.de>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   7)  * Copyright (c) 2020 Guenter Roeck <linux@roeck-us.net>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   8)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   9)  * Implementation notes:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  10)  * - CCD register address information as well as the calculation to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  11)  *   convert raw register values is from https://github.com/ocerman/zenpower.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  12)  *   The information is not confirmed from chip datasheets, but experiments
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  13)  *   suggest that it provides reasonable temperature values.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  14)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  15) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  16) #include <linux/bitops.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  17) #include <linux/err.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  18) #include <linux/hwmon.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  19) #include <linux/init.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  20) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  21) #include <linux/pci.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  22) #include <linux/pci_ids.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  23) #include <asm/amd_nb.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  24) #include <asm/processor.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  25) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  26) MODULE_DESCRIPTION("AMD Family 10h+ CPU core temperature monitor");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  27) MODULE_AUTHOR("Clemens Ladisch <clemens@ladisch.de>");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  28) MODULE_LICENSE("GPL");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  29) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  30) static bool force;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  31) module_param(force, bool, 0444);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  32) MODULE_PARM_DESC(force, "force loading on processors with erratum 319");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  33) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  34) /* Provide lock for writing to NB_SMU_IND_ADDR */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  35) static DEFINE_MUTEX(nb_smu_ind_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  36) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  37) #ifndef PCI_DEVICE_ID_AMD_15H_M70H_NB_F3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  38) #define PCI_DEVICE_ID_AMD_15H_M70H_NB_F3	0x15b3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  39) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  40) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  41) /* CPUID function 0x80000001, ebx */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  42) #define CPUID_PKGTYPE_MASK	GENMASK(31, 28)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  43) #define CPUID_PKGTYPE_F		0x00000000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  44) #define CPUID_PKGTYPE_AM2R2_AM3	0x10000000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  45) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  46) /* DRAM controller (PCI function 2) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  47) #define REG_DCT0_CONFIG_HIGH		0x094
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  48) #define  DDR3_MODE			BIT(8)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  49) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  50) /* miscellaneous (PCI function 3) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  51) #define REG_HARDWARE_THERMAL_CONTROL	0x64
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  52) #define  HTC_ENABLE			BIT(0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  53) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  54) #define REG_REPORTED_TEMPERATURE	0xa4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  55) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  56) #define REG_NORTHBRIDGE_CAPABILITIES	0xe8
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  57) #define  NB_CAP_HTC			BIT(10)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  58) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  59) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  60)  * For F15h M60h and M70h, REG_HARDWARE_THERMAL_CONTROL
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  61)  * and REG_REPORTED_TEMPERATURE have been moved to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  62)  * D0F0xBC_xD820_0C64 [Hardware Temperature Control]
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  63)  * D0F0xBC_xD820_0CA4 [Reported Temperature Control]
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  64)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  65) #define F15H_M60H_HARDWARE_TEMP_CTRL_OFFSET	0xd8200c64
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  66) #define F15H_M60H_REPORTED_TEMP_CTRL_OFFSET	0xd8200ca4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  67) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  68) /* Common for Zen CPU families (Family 17h and 18h) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  69) #define ZEN_REPORTED_TEMP_CTRL_OFFSET		0x00059800
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  70) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  71) #define ZEN_CCD_TEMP(x)				(0x00059954 + ((x) * 4))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  72) #define ZEN_CCD_TEMP_VALID			BIT(11)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  73) #define ZEN_CCD_TEMP_MASK			GENMASK(10, 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  74) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  75) #define ZEN_CUR_TEMP_SHIFT			21
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  76) #define ZEN_CUR_TEMP_RANGE_SEL_MASK		BIT(19)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  77) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  78) #define ZEN_SVI_BASE				0x0005A000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  79) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  80) /* F17h thermal registers through SMN */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  81) #define F17H_M01H_SVI_TEL_PLANE0		(ZEN_SVI_BASE + 0xc)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  82) #define F17H_M01H_SVI_TEL_PLANE1		(ZEN_SVI_BASE + 0x10)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  83) #define F17H_M31H_SVI_TEL_PLANE0		(ZEN_SVI_BASE + 0x14)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  84) #define F17H_M31H_SVI_TEL_PLANE1		(ZEN_SVI_BASE + 0x10)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  85) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  86) #define F17H_M01H_CFACTOR_ICORE			1000000	/* 1A / LSB	*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  87) #define F17H_M01H_CFACTOR_ISOC			250000	/* 0.25A / LSB	*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  88) #define F17H_M31H_CFACTOR_ICORE			1000000	/* 1A / LSB	*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  89) #define F17H_M31H_CFACTOR_ISOC			310000	/* 0.31A / LSB	*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  90) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  91) /* F19h thermal registers through SMN */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  92) #define F19H_M01_SVI_TEL_PLANE0			(ZEN_SVI_BASE + 0x14)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  93) #define F19H_M01_SVI_TEL_PLANE1			(ZEN_SVI_BASE + 0x10)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  94) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  95) #define F19H_M01H_CFACTOR_ICORE			1000000	/* 1A / LSB	*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  96) #define F19H_M01H_CFACTOR_ISOC			310000	/* 0.31A / LSB	*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  97) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  98) struct k10temp_data {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  99) 	struct pci_dev *pdev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) 	void (*read_htcreg)(struct pci_dev *pdev, u32 *regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) 	void (*read_tempreg)(struct pci_dev *pdev, u32 *regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) 	int temp_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) 	u32 temp_adjust_mask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) 	u32 show_temp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) 	bool is_zen;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) #define TCTL_BIT	0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) #define TDIE_BIT	1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) #define TCCD_BIT(x)	((x) + 2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) #define HAVE_TEMP(d, channel)	((d)->show_temp & BIT(channel))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) #define HAVE_TDIE(d)		HAVE_TEMP(d, TDIE_BIT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) struct tctl_offset {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) 	u8 model;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) 	char const *id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) 	int offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) static const struct tctl_offset tctl_offset_table[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) 	{ 0x17, "AMD Ryzen 5 1600X", 20000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) 	{ 0x17, "AMD Ryzen 7 1700X", 20000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) 	{ 0x17, "AMD Ryzen 7 1800X", 20000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) 	{ 0x17, "AMD Ryzen 7 2700X", 10000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) 	{ 0x17, "AMD Ryzen Threadripper 19", 27000 }, /* 19{00,20,50}X */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) 	{ 0x17, "AMD Ryzen Threadripper 29", 27000 }, /* 29{20,50,70,90}[W]X */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) static void read_htcreg_pci(struct pci_dev *pdev, u32 *regval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) 	pci_read_config_dword(pdev, REG_HARDWARE_THERMAL_CONTROL, regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) static void read_tempreg_pci(struct pci_dev *pdev, u32 *regval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) 	pci_read_config_dword(pdev, REG_REPORTED_TEMPERATURE, regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) static void amd_nb_index_read(struct pci_dev *pdev, unsigned int devfn,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) 			      unsigned int base, int offset, u32 *val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) 	mutex_lock(&nb_smu_ind_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) 	pci_bus_write_config_dword(pdev->bus, devfn,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) 				   base, offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) 	pci_bus_read_config_dword(pdev->bus, devfn,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) 				  base + 4, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) 	mutex_unlock(&nb_smu_ind_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) static void read_htcreg_nb_f15(struct pci_dev *pdev, u32 *regval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) 	amd_nb_index_read(pdev, PCI_DEVFN(0, 0), 0xb8,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) 			  F15H_M60H_HARDWARE_TEMP_CTRL_OFFSET, regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) static void read_tempreg_nb_f15(struct pci_dev *pdev, u32 *regval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) 	amd_nb_index_read(pdev, PCI_DEVFN(0, 0), 0xb8,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) 			  F15H_M60H_REPORTED_TEMP_CTRL_OFFSET, regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) static void read_tempreg_nb_zen(struct pci_dev *pdev, u32 *regval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) 	amd_smn_read(amd_pci_dev_to_node_id(pdev),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) 		     ZEN_REPORTED_TEMP_CTRL_OFFSET, regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) static long get_raw_temp(struct k10temp_data *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) 	u32 regval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) 	long temp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) 	data->read_tempreg(data->pdev, &regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) 	temp = (regval >> ZEN_CUR_TEMP_SHIFT) * 125;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) 	if (regval & data->temp_adjust_mask)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) 		temp -= 49000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) 	return temp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) static const char *k10temp_temp_label[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) 	"Tctl",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) 	"Tdie",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) 	"Tccd1",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) 	"Tccd2",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) 	"Tccd3",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) 	"Tccd4",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) 	"Tccd5",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) 	"Tccd6",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) 	"Tccd7",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) 	"Tccd8",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) static int k10temp_read_labels(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) 			       enum hwmon_sensor_types type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) 			       u32 attr, int channel, const char **str)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) 	switch (type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) 	case hwmon_temp:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) 		*str = k10temp_temp_label[channel];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) 		return -EOPNOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) static int k10temp_read_temp(struct device *dev, u32 attr, int channel,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) 			     long *val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) 	struct k10temp_data *data = dev_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) 	u32 regval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) 	switch (attr) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) 	case hwmon_temp_input:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) 		switch (channel) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) 		case 0:		/* Tctl */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) 			*val = get_raw_temp(data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) 			if (*val < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) 				*val = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) 		case 1:		/* Tdie */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) 			*val = get_raw_temp(data) - data->temp_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) 			if (*val < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) 				*val = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) 		case 2 ... 9:		/* Tccd{1-8} */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) 			amd_smn_read(amd_pci_dev_to_node_id(data->pdev),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) 				     ZEN_CCD_TEMP(channel - 2), &regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) 			*val = (regval & ZEN_CCD_TEMP_MASK) * 125 - 49000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) 		default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) 			return -EOPNOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) 	case hwmon_temp_max:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) 		*val = 70 * 1000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) 	case hwmon_temp_crit:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) 		data->read_htcreg(data->pdev, &regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) 		*val = ((regval >> 16) & 0x7f) * 500 + 52000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) 	case hwmon_temp_crit_hyst:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) 		data->read_htcreg(data->pdev, &regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) 		*val = (((regval >> 16) & 0x7f)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) 			- ((regval >> 24) & 0xf)) * 500 + 52000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) 		return -EOPNOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) static int k10temp_read(struct device *dev, enum hwmon_sensor_types type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) 			u32 attr, int channel, long *val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) 	switch (type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) 	case hwmon_temp:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) 		return k10temp_read_temp(dev, attr, channel, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) 		return -EOPNOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) static umode_t k10temp_is_visible(const void *_data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) 				  enum hwmon_sensor_types type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) 				  u32 attr, int channel)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) 	const struct k10temp_data *data = _data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) 	struct pci_dev *pdev = data->pdev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) 	u32 reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) 	switch (type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) 	case hwmon_temp:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) 		switch (attr) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) 		case hwmon_temp_input:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) 			if (!HAVE_TEMP(data, channel))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) 				return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) 		case hwmon_temp_max:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) 			if (channel || data->is_zen)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) 				return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) 		case hwmon_temp_crit:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) 		case hwmon_temp_crit_hyst:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) 			if (channel || !data->read_htcreg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) 				return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) 			pci_read_config_dword(pdev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) 					      REG_NORTHBRIDGE_CAPABILITIES,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) 					      &reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) 			if (!(reg & NB_CAP_HTC))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) 				return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) 			data->read_htcreg(data->pdev, &reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) 			if (!(reg & HTC_ENABLE))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) 				return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) 		case hwmon_temp_label:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) 			/* Show temperature labels only on Zen CPUs */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) 			if (!data->is_zen || !HAVE_TEMP(data, channel))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) 				return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) 		default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) 			return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) 	return 0444;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) static bool has_erratum_319(struct pci_dev *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) 	u32 pkg_type, reg_dram_cfg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) 	if (boot_cpu_data.x86 != 0x10)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) 		return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) 	 * Erratum 319: The thermal sensor of Socket F/AM2+ processors
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) 	 *              may be unreliable.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) 	pkg_type = cpuid_ebx(0x80000001) & CPUID_PKGTYPE_MASK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) 	if (pkg_type == CPUID_PKGTYPE_F)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) 		return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) 	if (pkg_type != CPUID_PKGTYPE_AM2R2_AM3)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) 		return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) 	/* DDR3 memory implies socket AM3, which is good */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) 	pci_bus_read_config_dword(pdev->bus,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) 				  PCI_DEVFN(PCI_SLOT(pdev->devfn), 2),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) 				  REG_DCT0_CONFIG_HIGH, &reg_dram_cfg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) 	if (reg_dram_cfg & DDR3_MODE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) 		return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) 	 * Unfortunately it is possible to run a socket AM3 CPU with DDR2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) 	 * memory. We blacklist all the cores which do exist in socket AM2+
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) 	 * format. It still isn't perfect, as RB-C2 cores exist in both AM2+
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) 	 * and AM3 formats, but that's the best we can do.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) 	return boot_cpu_data.x86_model < 4 ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) 	       (boot_cpu_data.x86_model == 4 && boot_cpu_data.x86_stepping <= 2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) static const struct hwmon_channel_info *k10temp_info[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) 	HWMON_CHANNEL_INFO(temp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) 			   HWMON_T_INPUT | HWMON_T_MAX |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) 			   HWMON_T_CRIT | HWMON_T_CRIT_HYST |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) 			   HWMON_T_LABEL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) 			   HWMON_T_INPUT | HWMON_T_LABEL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) 			   HWMON_T_INPUT | HWMON_T_LABEL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) 			   HWMON_T_INPUT | HWMON_T_LABEL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) 			   HWMON_T_INPUT | HWMON_T_LABEL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) 			   HWMON_T_INPUT | HWMON_T_LABEL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) 			   HWMON_T_INPUT | HWMON_T_LABEL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) 			   HWMON_T_INPUT | HWMON_T_LABEL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) 			   HWMON_T_INPUT | HWMON_T_LABEL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) 			   HWMON_T_INPUT | HWMON_T_LABEL),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) 	HWMON_CHANNEL_INFO(in,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) 			   HWMON_I_INPUT | HWMON_I_LABEL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) 			   HWMON_I_INPUT | HWMON_I_LABEL),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) 	HWMON_CHANNEL_INFO(curr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) 			   HWMON_C_INPUT | HWMON_C_LABEL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) 			   HWMON_C_INPUT | HWMON_C_LABEL),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) 	NULL
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) static const struct hwmon_ops k10temp_hwmon_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) 	.is_visible = k10temp_is_visible,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) 	.read = k10temp_read,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) 	.read_string = k10temp_read_labels,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) static const struct hwmon_chip_info k10temp_chip_info = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) 	.ops = &k10temp_hwmon_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) 	.info = k10temp_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) static void k10temp_get_ccd_support(struct pci_dev *pdev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) 				    struct k10temp_data *data, int limit)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) 	u32 regval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) 	int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) 	for (i = 0; i < limit; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) 		amd_smn_read(amd_pci_dev_to_node_id(pdev),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) 			     ZEN_CCD_TEMP(i), &regval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) 		if (regval & ZEN_CCD_TEMP_VALID)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) 			data->show_temp |= BIT(TCCD_BIT(i));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) static int k10temp_probe(struct pci_dev *pdev, const struct pci_device_id *id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) 	int unreliable = has_erratum_319(pdev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) 	struct device *dev = &pdev->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) 	struct k10temp_data *data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) 	struct device *hwmon_dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) 	int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) 	if (unreliable) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) 		if (!force) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) 			dev_err(dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) 				"unreliable CPU thermal sensor; monitoring disabled\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) 			return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) 		dev_warn(dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) 			 "unreliable CPU thermal sensor; check erratum 319\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) 	data = devm_kzalloc(dev, sizeof(*data), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) 	if (!data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) 		return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) 	data->pdev = pdev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) 	data->show_temp |= BIT(TCTL_BIT);	/* Always show Tctl */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) 	if (boot_cpu_data.x86 == 0x15 &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) 	    ((boot_cpu_data.x86_model & 0xf0) == 0x60 ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) 	     (boot_cpu_data.x86_model & 0xf0) == 0x70)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) 		data->read_htcreg = read_htcreg_nb_f15;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) 		data->read_tempreg = read_tempreg_nb_f15;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) 	} else if (boot_cpu_data.x86 == 0x17 || boot_cpu_data.x86 == 0x18) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) 		data->temp_adjust_mask = ZEN_CUR_TEMP_RANGE_SEL_MASK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) 		data->read_tempreg = read_tempreg_nb_zen;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) 		data->show_temp |= BIT(TDIE_BIT);	/* show Tdie */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) 		data->is_zen = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) 		switch (boot_cpu_data.x86_model) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) 		case 0x1:	/* Zen */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) 		case 0x8:	/* Zen+ */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) 		case 0x11:	/* Zen APU */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) 		case 0x18:	/* Zen+ APU */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) 			k10temp_get_ccd_support(pdev, data, 4);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) 		case 0x31:	/* Zen2 Threadripper */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) 		case 0x71:	/* Zen2 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) 			k10temp_get_ccd_support(pdev, data, 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) 	} else if (boot_cpu_data.x86 == 0x19) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) 		data->temp_adjust_mask = ZEN_CUR_TEMP_RANGE_SEL_MASK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) 		data->read_tempreg = read_tempreg_nb_zen;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) 		data->show_temp |= BIT(TDIE_BIT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) 		data->is_zen = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) 		switch (boot_cpu_data.x86_model) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) 		case 0x0 ... 0x1:	/* Zen3 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) 			k10temp_get_ccd_support(pdev, data, 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) 		data->read_htcreg = read_htcreg_pci;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) 		data->read_tempreg = read_tempreg_pci;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) 	for (i = 0; i < ARRAY_SIZE(tctl_offset_table); i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) 		const struct tctl_offset *entry = &tctl_offset_table[i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) 		if (boot_cpu_data.x86 == entry->model &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) 		    strstr(boot_cpu_data.x86_model_id, entry->id)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) 			data->temp_offset = entry->offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) 	hwmon_dev = devm_hwmon_device_register_with_info(dev, "k10temp", data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) 							 &k10temp_chip_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) 							 NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) 	return PTR_ERR_OR_ZERO(hwmon_dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) static const struct pci_device_id k10temp_id_table[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_10H_NB_MISC) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_11H_NB_MISC) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_CNB17H_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_15H_NB_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_15H_M10H_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_15H_M30H_NB_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_15H_M60H_NB_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_15H_M70H_NB_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_16H_NB_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_16H_M30H_NB_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_17H_DF_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_17H_M10H_DF_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_17H_M30H_DF_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_17H_M60H_DF_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_17H_M70H_DF_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) 	{ PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_19H_DF_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) 	{ PCI_VDEVICE(HYGON, PCI_DEVICE_ID_AMD_17H_DF_F3) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) 	{}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) MODULE_DEVICE_TABLE(pci, k10temp_id_table);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) static struct pci_driver k10temp_driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) 	.name = "k10temp",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) 	.id_table = k10temp_id_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) 	.probe = k10temp_probe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) module_pci_driver(k10temp_driver);