Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-or-later
0002 /*
0003  * AMD SoC Power Management Controller Driver
0004  *
0005  * Copyright (c) 2020, Advanced Micro Devices, Inc.
0006  * All Rights Reserved.
0007  *
0008  * Author: Shyam Sundar S K <Shyam-sundar.S-k@amd.com>
0009  */
0010 
0011 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
0012 
0013 #include <linux/acpi.h>
0014 #include <linux/bitfield.h>
0015 #include <linux/bits.h>
0016 #include <linux/debugfs.h>
0017 #include <linux/delay.h>
0018 #include <linux/io.h>
0019 #include <linux/iopoll.h>
0020 #include <linux/limits.h>
0021 #include <linux/module.h>
0022 #include <linux/pci.h>
0023 #include <linux/platform_device.h>
0024 #include <linux/rtc.h>
0025 #include <linux/suspend.h>
0026 #include <linux/seq_file.h>
0027 #include <linux/uaccess.h>
0028 
0029 /* SMU communication registers */
0030 #define AMD_PMC_REGISTER_MESSAGE    0x538
0031 #define AMD_PMC_REGISTER_RESPONSE   0x980
0032 #define AMD_PMC_REGISTER_ARGUMENT   0x9BC
0033 
0034 /* PMC Scratch Registers */
0035 #define AMD_PMC_SCRATCH_REG_CZN     0x94
0036 #define AMD_PMC_SCRATCH_REG_YC      0xD14
0037 
0038 /* STB Registers */
0039 #define AMD_PMC_STB_INDEX_ADDRESS   0xF8
0040 #define AMD_PMC_STB_INDEX_DATA      0xFC
0041 #define AMD_PMC_STB_PMI_0       0x03E30600
0042 #define AMD_PMC_STB_PREDEF      0xC6000001
0043 
0044 /* STB S2D(Spill to DRAM) has different message port offset */
0045 #define STB_SPILL_TO_DRAM       0xBE
0046 #define AMD_S2D_REGISTER_MESSAGE    0xA20
0047 #define AMD_S2D_REGISTER_RESPONSE   0xA80
0048 #define AMD_S2D_REGISTER_ARGUMENT   0xA88
0049 
0050 /* STB Spill to DRAM Parameters */
0051 #define S2D_TELEMETRY_BYTES_MAX     0x100000
0052 #define S2D_TELEMETRY_DRAMBYTES_MAX 0x1000000
0053 
0054 /* Base address of SMU for mapping physical address to virtual address */
0055 #define AMD_PMC_SMU_INDEX_ADDRESS   0xB8
0056 #define AMD_PMC_SMU_INDEX_DATA      0xBC
0057 #define AMD_PMC_MAPPING_SIZE        0x01000
0058 #define AMD_PMC_BASE_ADDR_OFFSET    0x10000
0059 #define AMD_PMC_BASE_ADDR_LO        0x13B102E8
0060 #define AMD_PMC_BASE_ADDR_HI        0x13B102EC
0061 #define AMD_PMC_BASE_ADDR_LO_MASK   GENMASK(15, 0)
0062 #define AMD_PMC_BASE_ADDR_HI_MASK   GENMASK(31, 20)
0063 
0064 /* SMU Response Codes */
0065 #define AMD_PMC_RESULT_OK                    0x01
0066 #define AMD_PMC_RESULT_CMD_REJECT_BUSY       0xFC
0067 #define AMD_PMC_RESULT_CMD_REJECT_PREREQ     0xFD
0068 #define AMD_PMC_RESULT_CMD_UNKNOWN           0xFE
0069 #define AMD_PMC_RESULT_FAILED                0xFF
0070 
0071 /* FCH SSC Registers */
0072 #define FCH_S0I3_ENTRY_TIME_L_OFFSET    0x30
0073 #define FCH_S0I3_ENTRY_TIME_H_OFFSET    0x34
0074 #define FCH_S0I3_EXIT_TIME_L_OFFSET 0x38
0075 #define FCH_S0I3_EXIT_TIME_H_OFFSET 0x3C
0076 #define FCH_SSC_MAPPING_SIZE        0x800
0077 #define FCH_BASE_PHY_ADDR_LOW       0xFED81100
0078 #define FCH_BASE_PHY_ADDR_HIGH      0x00000000
0079 
0080 /* SMU Message Definations */
0081 #define SMU_MSG_GETSMUVERSION       0x02
0082 #define SMU_MSG_LOG_GETDRAM_ADDR_HI 0x04
0083 #define SMU_MSG_LOG_GETDRAM_ADDR_LO 0x05
0084 #define SMU_MSG_LOG_START       0x06
0085 #define SMU_MSG_LOG_RESET       0x07
0086 #define SMU_MSG_LOG_DUMP_DATA       0x08
0087 #define SMU_MSG_GET_SUP_CONSTRAINTS 0x09
0088 /* List of supported CPU ids */
0089 #define AMD_CPU_ID_RV           0x15D0
0090 #define AMD_CPU_ID_RN           0x1630
0091 #define AMD_CPU_ID_PCO          AMD_CPU_ID_RV
0092 #define AMD_CPU_ID_CZN          AMD_CPU_ID_RN
0093 #define AMD_CPU_ID_YC           0x14B5
0094 #define AMD_CPU_ID_CB           0x14D8
0095 #define AMD_CPU_ID_PS           0x14E8
0096 
0097 #define PMC_MSG_DELAY_MIN_US        50
0098 #define RESPONSE_REGISTER_LOOP_MAX  20000
0099 
0100 #define SOC_SUBSYSTEM_IP_MAX    12
0101 #define DELAY_MIN_US        2000
0102 #define DELAY_MAX_US        3000
0103 #define FIFO_SIZE       4096
0104 enum amd_pmc_def {
0105     MSG_TEST = 0x01,
0106     MSG_OS_HINT_PCO,
0107     MSG_OS_HINT_RN,
0108 };
0109 
0110 enum s2d_arg {
0111     S2D_TELEMETRY_SIZE = 0x01,
0112     S2D_PHYS_ADDR_LOW,
0113     S2D_PHYS_ADDR_HIGH,
0114 };
0115 
0116 struct amd_pmc_bit_map {
0117     const char *name;
0118     u32 bit_mask;
0119 };
0120 
0121 static const struct amd_pmc_bit_map soc15_ip_blk[] = {
0122     {"DISPLAY", BIT(0)},
0123     {"CPU",     BIT(1)},
0124     {"GFX",     BIT(2)},
0125     {"VDD",     BIT(3)},
0126     {"ACP",     BIT(4)},
0127     {"VCN",     BIT(5)},
0128     {"ISP",     BIT(6)},
0129     {"NBIO",    BIT(7)},
0130     {"DF",      BIT(8)},
0131     {"USB0",    BIT(9)},
0132     {"USB1",    BIT(10)},
0133     {"LAPIC",   BIT(11)},
0134     {}
0135 };
0136 
0137 struct amd_pmc_dev {
0138     void __iomem *regbase;
0139     void __iomem *smu_virt_addr;
0140     void __iomem *stb_virt_addr;
0141     void __iomem *fch_virt_addr;
0142     bool msg_port;
0143     u32 base_addr;
0144     u32 cpu_id;
0145     u32 active_ips;
0146 /* SMU version information */
0147     u8 smu_program;
0148     u8 major;
0149     u8 minor;
0150     u8 rev;
0151     struct device *dev;
0152     struct pci_dev *rdev;
0153     struct mutex lock; /* generic mutex lock */
0154 #if IS_ENABLED(CONFIG_DEBUG_FS)
0155     struct dentry *dbgfs_dir;
0156 #endif /* CONFIG_DEBUG_FS */
0157 };
0158 
0159 static bool enable_stb;
0160 module_param(enable_stb, bool, 0644);
0161 MODULE_PARM_DESC(enable_stb, "Enable the STB debug mechanism");
0162 
0163 static struct amd_pmc_dev pmc;
0164 static int amd_pmc_send_cmd(struct amd_pmc_dev *dev, u32 arg, u32 *data, u8 msg, bool ret);
0165 static int amd_pmc_read_stb(struct amd_pmc_dev *dev, u32 *buf);
0166 #ifdef CONFIG_SUSPEND
0167 static int amd_pmc_write_stb(struct amd_pmc_dev *dev, u32 data);
0168 #endif
0169 
0170 static inline u32 amd_pmc_reg_read(struct amd_pmc_dev *dev, int reg_offset)
0171 {
0172     return ioread32(dev->regbase + reg_offset);
0173 }
0174 
0175 static inline void amd_pmc_reg_write(struct amd_pmc_dev *dev, int reg_offset, u32 val)
0176 {
0177     iowrite32(val, dev->regbase + reg_offset);
0178 }
0179 
0180 struct smu_metrics {
0181     u32 table_version;
0182     u32 hint_count;
0183     u32 s0i3_last_entry_status;
0184     u32 timein_s0i2;
0185     u64 timeentering_s0i3_lastcapture;
0186     u64 timeentering_s0i3_totaltime;
0187     u64 timeto_resume_to_os_lastcapture;
0188     u64 timeto_resume_to_os_totaltime;
0189     u64 timein_s0i3_lastcapture;
0190     u64 timein_s0i3_totaltime;
0191     u64 timein_swdrips_lastcapture;
0192     u64 timein_swdrips_totaltime;
0193     u64 timecondition_notmet_lastcapture[SOC_SUBSYSTEM_IP_MAX];
0194     u64 timecondition_notmet_totaltime[SOC_SUBSYSTEM_IP_MAX];
0195 } __packed;
0196 
0197 static int amd_pmc_stb_debugfs_open(struct inode *inode, struct file *filp)
0198 {
0199     struct amd_pmc_dev *dev = filp->f_inode->i_private;
0200     u32 size = FIFO_SIZE * sizeof(u32);
0201     u32 *buf;
0202     int rc;
0203 
0204     buf = kzalloc(size, GFP_KERNEL);
0205     if (!buf)
0206         return -ENOMEM;
0207 
0208     rc = amd_pmc_read_stb(dev, buf);
0209     if (rc) {
0210         kfree(buf);
0211         return rc;
0212     }
0213 
0214     filp->private_data = buf;
0215     return rc;
0216 }
0217 
0218 static ssize_t amd_pmc_stb_debugfs_read(struct file *filp, char __user *buf, size_t size,
0219                     loff_t *pos)
0220 {
0221     if (!filp->private_data)
0222         return -EINVAL;
0223 
0224     return simple_read_from_buffer(buf, size, pos, filp->private_data,
0225                        FIFO_SIZE * sizeof(u32));
0226 }
0227 
0228 static int amd_pmc_stb_debugfs_release(struct inode *inode, struct file *filp)
0229 {
0230     kfree(filp->private_data);
0231     return 0;
0232 }
0233 
0234 static const struct file_operations amd_pmc_stb_debugfs_fops = {
0235     .owner = THIS_MODULE,
0236     .open = amd_pmc_stb_debugfs_open,
0237     .read = amd_pmc_stb_debugfs_read,
0238     .release = amd_pmc_stb_debugfs_release,
0239 };
0240 
0241 static int amd_pmc_stb_debugfs_open_v2(struct inode *inode, struct file *filp)
0242 {
0243     struct amd_pmc_dev *dev = filp->f_inode->i_private;
0244     u32 *buf;
0245 
0246     buf = kzalloc(S2D_TELEMETRY_BYTES_MAX, GFP_KERNEL);
0247     if (!buf)
0248         return -ENOMEM;
0249 
0250     memcpy_fromio(buf, dev->stb_virt_addr, S2D_TELEMETRY_BYTES_MAX);
0251     filp->private_data = buf;
0252 
0253     return 0;
0254 }
0255 
0256 static ssize_t amd_pmc_stb_debugfs_read_v2(struct file *filp, char __user *buf, size_t size,
0257                        loff_t *pos)
0258 {
0259     if (!filp->private_data)
0260         return -EINVAL;
0261 
0262     return simple_read_from_buffer(buf, size, pos, filp->private_data,
0263                     S2D_TELEMETRY_BYTES_MAX);
0264 }
0265 
0266 static int amd_pmc_stb_debugfs_release_v2(struct inode *inode, struct file *filp)
0267 {
0268     kfree(filp->private_data);
0269     return 0;
0270 }
0271 
0272 static const struct file_operations amd_pmc_stb_debugfs_fops_v2 = {
0273     .owner = THIS_MODULE,
0274     .open = amd_pmc_stb_debugfs_open_v2,
0275     .read = amd_pmc_stb_debugfs_read_v2,
0276     .release = amd_pmc_stb_debugfs_release_v2,
0277 };
0278 
0279 #if defined(CONFIG_SUSPEND) || defined(CONFIG_DEBUG_FS)
0280 static int amd_pmc_setup_smu_logging(struct amd_pmc_dev *dev)
0281 {
0282     if (dev->cpu_id == AMD_CPU_ID_PCO) {
0283         dev_warn_once(dev->dev, "SMU debugging info not supported on this platform\n");
0284         return -EINVAL;
0285     }
0286 
0287     /* Get Active devices list from SMU */
0288     if (!dev->active_ips)
0289         amd_pmc_send_cmd(dev, 0, &dev->active_ips, SMU_MSG_GET_SUP_CONSTRAINTS, 1);
0290 
0291     /* Get dram address */
0292     if (!dev->smu_virt_addr) {
0293         u32 phys_addr_low, phys_addr_hi;
0294         u64 smu_phys_addr;
0295 
0296         amd_pmc_send_cmd(dev, 0, &phys_addr_low, SMU_MSG_LOG_GETDRAM_ADDR_LO, 1);
0297         amd_pmc_send_cmd(dev, 0, &phys_addr_hi, SMU_MSG_LOG_GETDRAM_ADDR_HI, 1);
0298         smu_phys_addr = ((u64)phys_addr_hi << 32 | phys_addr_low);
0299 
0300         dev->smu_virt_addr = devm_ioremap(dev->dev, smu_phys_addr,
0301                           sizeof(struct smu_metrics));
0302         if (!dev->smu_virt_addr)
0303             return -ENOMEM;
0304     }
0305 
0306     /* Start the logging */
0307     amd_pmc_send_cmd(dev, 0, NULL, SMU_MSG_LOG_RESET, 0);
0308     amd_pmc_send_cmd(dev, 0, NULL, SMU_MSG_LOG_START, 0);
0309 
0310     return 0;
0311 }
0312 
0313 static int amd_pmc_idlemask_read(struct amd_pmc_dev *pdev, struct device *dev,
0314                  struct seq_file *s)
0315 {
0316     u32 val;
0317 
0318     switch (pdev->cpu_id) {
0319     case AMD_CPU_ID_CZN:
0320         val = amd_pmc_reg_read(pdev, AMD_PMC_SCRATCH_REG_CZN);
0321         break;
0322     case AMD_CPU_ID_YC:
0323     case AMD_CPU_ID_CB:
0324     case AMD_CPU_ID_PS:
0325         val = amd_pmc_reg_read(pdev, AMD_PMC_SCRATCH_REG_YC);
0326         break;
0327     default:
0328         return -EINVAL;
0329     }
0330 
0331     if (dev)
0332         dev_dbg(pdev->dev, "SMU idlemask s0i3: 0x%x\n", val);
0333 
0334     if (s)
0335         seq_printf(s, "SMU idlemask : 0x%x\n", val);
0336 
0337     return 0;
0338 }
0339 
0340 static int get_metrics_table(struct amd_pmc_dev *pdev, struct smu_metrics *table)
0341 {
0342     if (!pdev->smu_virt_addr) {
0343         int ret = amd_pmc_setup_smu_logging(pdev);
0344 
0345         if (ret)
0346             return ret;
0347     }
0348 
0349     if (pdev->cpu_id == AMD_CPU_ID_PCO)
0350         return -ENODEV;
0351     memcpy_fromio(table, pdev->smu_virt_addr, sizeof(struct smu_metrics));
0352     return 0;
0353 }
0354 #endif /* CONFIG_SUSPEND || CONFIG_DEBUG_FS */
0355 
0356 #ifdef CONFIG_SUSPEND
0357 static void amd_pmc_validate_deepest(struct amd_pmc_dev *pdev)
0358 {
0359     struct smu_metrics table;
0360 
0361     if (get_metrics_table(pdev, &table))
0362         return;
0363 
0364     if (!table.s0i3_last_entry_status)
0365         dev_warn(pdev->dev, "Last suspend didn't reach deepest state\n");
0366     else
0367         dev_dbg(pdev->dev, "Last suspend in deepest state for %lluus\n",
0368              table.timein_s0i3_lastcapture);
0369 }
0370 #endif
0371 
0372 #ifdef CONFIG_DEBUG_FS
0373 static int smu_fw_info_show(struct seq_file *s, void *unused)
0374 {
0375     struct amd_pmc_dev *dev = s->private;
0376     struct smu_metrics table;
0377     int idx;
0378 
0379     if (get_metrics_table(dev, &table))
0380         return -EINVAL;
0381 
0382     seq_puts(s, "\n=== SMU Statistics ===\n");
0383     seq_printf(s, "Table Version: %d\n", table.table_version);
0384     seq_printf(s, "Hint Count: %d\n", table.hint_count);
0385     seq_printf(s, "Last S0i3 Status: %s\n", table.s0i3_last_entry_status ? "Success" :
0386            "Unknown/Fail");
0387     seq_printf(s, "Time (in us) to S0i3: %lld\n", table.timeentering_s0i3_lastcapture);
0388     seq_printf(s, "Time (in us) in S0i3: %lld\n", table.timein_s0i3_lastcapture);
0389     seq_printf(s, "Time (in us) to resume from S0i3: %lld\n",
0390            table.timeto_resume_to_os_lastcapture);
0391 
0392     seq_puts(s, "\n=== Active time (in us) ===\n");
0393     for (idx = 0 ; idx < SOC_SUBSYSTEM_IP_MAX ; idx++) {
0394         if (soc15_ip_blk[idx].bit_mask & dev->active_ips)
0395             seq_printf(s, "%-8s : %lld\n", soc15_ip_blk[idx].name,
0396                    table.timecondition_notmet_lastcapture[idx]);
0397     }
0398 
0399     return 0;
0400 }
0401 DEFINE_SHOW_ATTRIBUTE(smu_fw_info);
0402 
0403 static int s0ix_stats_show(struct seq_file *s, void *unused)
0404 {
0405     struct amd_pmc_dev *dev = s->private;
0406     u64 entry_time, exit_time, residency;
0407 
0408     /* Use FCH registers to get the S0ix stats */
0409     if (!dev->fch_virt_addr) {
0410         u32 base_addr_lo = FCH_BASE_PHY_ADDR_LOW;
0411         u32 base_addr_hi = FCH_BASE_PHY_ADDR_HIGH;
0412         u64 fch_phys_addr = ((u64)base_addr_hi << 32 | base_addr_lo);
0413 
0414         dev->fch_virt_addr = devm_ioremap(dev->dev, fch_phys_addr, FCH_SSC_MAPPING_SIZE);
0415         if (!dev->fch_virt_addr)
0416             return -ENOMEM;
0417     }
0418 
0419     entry_time = ioread32(dev->fch_virt_addr + FCH_S0I3_ENTRY_TIME_H_OFFSET);
0420     entry_time = entry_time << 32 | ioread32(dev->fch_virt_addr + FCH_S0I3_ENTRY_TIME_L_OFFSET);
0421 
0422     exit_time = ioread32(dev->fch_virt_addr + FCH_S0I3_EXIT_TIME_H_OFFSET);
0423     exit_time = exit_time << 32 | ioread32(dev->fch_virt_addr + FCH_S0I3_EXIT_TIME_L_OFFSET);
0424 
0425     /* It's in 48MHz. We need to convert it */
0426     residency = exit_time - entry_time;
0427     do_div(residency, 48);
0428 
0429     seq_puts(s, "=== S0ix statistics ===\n");
0430     seq_printf(s, "S0ix Entry Time: %lld\n", entry_time);
0431     seq_printf(s, "S0ix Exit Time: %lld\n", exit_time);
0432     seq_printf(s, "Residency Time: %lld\n", residency);
0433 
0434     return 0;
0435 }
0436 DEFINE_SHOW_ATTRIBUTE(s0ix_stats);
0437 
0438 static int amd_pmc_get_smu_version(struct amd_pmc_dev *dev)
0439 {
0440     int rc;
0441     u32 val;
0442 
0443     rc = amd_pmc_send_cmd(dev, 0, &val, SMU_MSG_GETSMUVERSION, 1);
0444     if (rc)
0445         return rc;
0446 
0447     dev->smu_program = (val >> 24) & GENMASK(7, 0);
0448     dev->major = (val >> 16) & GENMASK(7, 0);
0449     dev->minor = (val >> 8) & GENMASK(7, 0);
0450     dev->rev = (val >> 0) & GENMASK(7, 0);
0451 
0452     dev_dbg(dev->dev, "SMU program %u version is %u.%u.%u\n",
0453         dev->smu_program, dev->major, dev->minor, dev->rev);
0454 
0455     return 0;
0456 }
0457 
0458 static int amd_pmc_idlemask_show(struct seq_file *s, void *unused)
0459 {
0460     struct amd_pmc_dev *dev = s->private;
0461     int rc;
0462 
0463     /* we haven't yet read SMU version */
0464     if (!dev->major) {
0465         rc = amd_pmc_get_smu_version(dev);
0466         if (rc)
0467             return rc;
0468     }
0469 
0470     if (dev->major > 56 || (dev->major >= 55 && dev->minor >= 37)) {
0471         rc = amd_pmc_idlemask_read(dev, NULL, s);
0472         if (rc)
0473             return rc;
0474     } else {
0475         seq_puts(s, "Unsupported SMU version for Idlemask\n");
0476     }
0477 
0478     return 0;
0479 }
0480 DEFINE_SHOW_ATTRIBUTE(amd_pmc_idlemask);
0481 
0482 static void amd_pmc_dbgfs_unregister(struct amd_pmc_dev *dev)
0483 {
0484     debugfs_remove_recursive(dev->dbgfs_dir);
0485 }
0486 
0487 static void amd_pmc_dbgfs_register(struct amd_pmc_dev *dev)
0488 {
0489     dev->dbgfs_dir = debugfs_create_dir("amd_pmc", NULL);
0490     debugfs_create_file("smu_fw_info", 0644, dev->dbgfs_dir, dev,
0491                 &smu_fw_info_fops);
0492     debugfs_create_file("s0ix_stats", 0644, dev->dbgfs_dir, dev,
0493                 &s0ix_stats_fops);
0494     debugfs_create_file("amd_pmc_idlemask", 0644, dev->dbgfs_dir, dev,
0495                 &amd_pmc_idlemask_fops);
0496     /* Enable STB only when the module_param is set */
0497     if (enable_stb) {
0498         if (dev->cpu_id == AMD_CPU_ID_YC || dev->cpu_id == AMD_CPU_ID_CB ||
0499             dev->cpu_id == AMD_CPU_ID_PS)
0500             debugfs_create_file("stb_read", 0644, dev->dbgfs_dir, dev,
0501                         &amd_pmc_stb_debugfs_fops_v2);
0502         else
0503             debugfs_create_file("stb_read", 0644, dev->dbgfs_dir, dev,
0504                         &amd_pmc_stb_debugfs_fops);
0505     }
0506 }
0507 #else
0508 static inline void amd_pmc_dbgfs_register(struct amd_pmc_dev *dev)
0509 {
0510 }
0511 
0512 static inline void amd_pmc_dbgfs_unregister(struct amd_pmc_dev *dev)
0513 {
0514 }
0515 #endif /* CONFIG_DEBUG_FS */
0516 
0517 static void amd_pmc_dump_registers(struct amd_pmc_dev *dev)
0518 {
0519     u32 value, message, argument, response;
0520 
0521     if (dev->msg_port) {
0522         message = AMD_S2D_REGISTER_MESSAGE;
0523         argument = AMD_S2D_REGISTER_ARGUMENT;
0524         response = AMD_S2D_REGISTER_RESPONSE;
0525     } else {
0526         message = AMD_PMC_REGISTER_MESSAGE;
0527         argument = AMD_PMC_REGISTER_ARGUMENT;
0528         response = AMD_PMC_REGISTER_RESPONSE;
0529     }
0530 
0531     value = amd_pmc_reg_read(dev, response);
0532     dev_dbg(dev->dev, "AMD_PMC_REGISTER_RESPONSE:%x\n", value);
0533 
0534     value = amd_pmc_reg_read(dev, argument);
0535     dev_dbg(dev->dev, "AMD_PMC_REGISTER_ARGUMENT:%x\n", value);
0536 
0537     value = amd_pmc_reg_read(dev, message);
0538     dev_dbg(dev->dev, "AMD_PMC_REGISTER_MESSAGE:%x\n", value);
0539 }
0540 
0541 static int amd_pmc_send_cmd(struct amd_pmc_dev *dev, u32 arg, u32 *data, u8 msg, bool ret)
0542 {
0543     int rc;
0544     u32 val, message, argument, response;
0545 
0546     mutex_lock(&dev->lock);
0547 
0548     if (dev->msg_port) {
0549         message = AMD_S2D_REGISTER_MESSAGE;
0550         argument = AMD_S2D_REGISTER_ARGUMENT;
0551         response = AMD_S2D_REGISTER_RESPONSE;
0552     } else {
0553         message = AMD_PMC_REGISTER_MESSAGE;
0554         argument = AMD_PMC_REGISTER_ARGUMENT;
0555         response = AMD_PMC_REGISTER_RESPONSE;
0556     }
0557 
0558     /* Wait until we get a valid response */
0559     rc = readx_poll_timeout(ioread32, dev->regbase + response,
0560                 val, val != 0, PMC_MSG_DELAY_MIN_US,
0561                 PMC_MSG_DELAY_MIN_US * RESPONSE_REGISTER_LOOP_MAX);
0562     if (rc) {
0563         dev_err(dev->dev, "failed to talk to SMU\n");
0564         goto out_unlock;
0565     }
0566 
0567     /* Write zero to response register */
0568     amd_pmc_reg_write(dev, response, 0);
0569 
0570     /* Write argument into response register */
0571     amd_pmc_reg_write(dev, argument, arg);
0572 
0573     /* Write message ID to message ID register */
0574     amd_pmc_reg_write(dev, message, msg);
0575 
0576     /* Wait until we get a valid response */
0577     rc = readx_poll_timeout(ioread32, dev->regbase + response,
0578                 val, val != 0, PMC_MSG_DELAY_MIN_US,
0579                 PMC_MSG_DELAY_MIN_US * RESPONSE_REGISTER_LOOP_MAX);
0580     if (rc) {
0581         dev_err(dev->dev, "SMU response timed out\n");
0582         goto out_unlock;
0583     }
0584 
0585     switch (val) {
0586     case AMD_PMC_RESULT_OK:
0587         if (ret) {
0588             /* PMFW may take longer time to return back the data */
0589             usleep_range(DELAY_MIN_US, 10 * DELAY_MAX_US);
0590             *data = amd_pmc_reg_read(dev, argument);
0591         }
0592         break;
0593     case AMD_PMC_RESULT_CMD_REJECT_BUSY:
0594         dev_err(dev->dev, "SMU not ready. err: 0x%x\n", val);
0595         rc = -EBUSY;
0596         goto out_unlock;
0597     case AMD_PMC_RESULT_CMD_UNKNOWN:
0598         dev_err(dev->dev, "SMU cmd unknown. err: 0x%x\n", val);
0599         rc = -EINVAL;
0600         goto out_unlock;
0601     case AMD_PMC_RESULT_CMD_REJECT_PREREQ:
0602     case AMD_PMC_RESULT_FAILED:
0603     default:
0604         dev_err(dev->dev, "SMU cmd failed. err: 0x%x\n", val);
0605         rc = -EIO;
0606         goto out_unlock;
0607     }
0608 
0609 out_unlock:
0610     mutex_unlock(&dev->lock);
0611     amd_pmc_dump_registers(dev);
0612     return rc;
0613 }
0614 
0615 #ifdef CONFIG_SUSPEND
0616 static int amd_pmc_get_os_hint(struct amd_pmc_dev *dev)
0617 {
0618     switch (dev->cpu_id) {
0619     case AMD_CPU_ID_PCO:
0620         return MSG_OS_HINT_PCO;
0621     case AMD_CPU_ID_RN:
0622     case AMD_CPU_ID_YC:
0623     case AMD_CPU_ID_CB:
0624     case AMD_CPU_ID_PS:
0625         return MSG_OS_HINT_RN;
0626     }
0627     return -EINVAL;
0628 }
0629 
0630 static int amd_pmc_verify_czn_rtc(struct amd_pmc_dev *pdev, u32 *arg)
0631 {
0632     struct rtc_device *rtc_device;
0633     time64_t then, now, duration;
0634     struct rtc_wkalrm alarm;
0635     struct rtc_time tm;
0636     int rc;
0637 
0638     if (pdev->major < 64 || (pdev->major == 64 && pdev->minor < 53))
0639         return 0;
0640 
0641     rtc_device = rtc_class_open("rtc0");
0642     if (!rtc_device)
0643         return 0;
0644     rc = rtc_read_alarm(rtc_device, &alarm);
0645     if (rc)
0646         return rc;
0647     if (!alarm.enabled) {
0648         dev_dbg(pdev->dev, "alarm not enabled\n");
0649         return 0;
0650     }
0651     rc = rtc_read_time(rtc_device, &tm);
0652     if (rc)
0653         return rc;
0654     then = rtc_tm_to_time64(&alarm.time);
0655     now = rtc_tm_to_time64(&tm);
0656     duration = then-now;
0657 
0658     /* in the past */
0659     if (then < now)
0660         return 0;
0661 
0662     /* will be stored in upper 16 bits of s0i3 hint argument,
0663      * so timer wakeup from s0i3 is limited to ~18 hours or less
0664      */
0665     if (duration <= 4 || duration > U16_MAX)
0666         return -EINVAL;
0667 
0668     *arg |= (duration << 16);
0669     rc = rtc_alarm_irq_enable(rtc_device, 0);
0670     dev_dbg(pdev->dev, "wakeup timer programmed for %lld seconds\n", duration);
0671 
0672     return rc;
0673 }
0674 
0675 static void amd_pmc_s2idle_prepare(void)
0676 {
0677     struct amd_pmc_dev *pdev = &pmc;
0678     int rc;
0679     u8 msg;
0680     u32 arg = 1;
0681 
0682     /* Reset and Start SMU logging - to monitor the s0i3 stats */
0683     amd_pmc_setup_smu_logging(pdev);
0684 
0685     /* Activate CZN specific RTC functionality */
0686     if (pdev->cpu_id == AMD_CPU_ID_CZN) {
0687         rc = amd_pmc_verify_czn_rtc(pdev, &arg);
0688         if (rc) {
0689             dev_err(pdev->dev, "failed to set RTC: %d\n", rc);
0690             return;
0691         }
0692     }
0693 
0694     /* Dump the IdleMask before we send hint to SMU */
0695     amd_pmc_idlemask_read(pdev, pdev->dev, NULL);
0696     msg = amd_pmc_get_os_hint(pdev);
0697     rc = amd_pmc_send_cmd(pdev, arg, NULL, msg, 0);
0698     if (rc) {
0699         dev_err(pdev->dev, "suspend failed: %d\n", rc);
0700         return;
0701     }
0702 
0703     if (enable_stb) {
0704         rc = amd_pmc_write_stb(pdev, AMD_PMC_STB_PREDEF);
0705         if (rc)
0706             dev_err(pdev->dev, "error writing to STB: %d\n", rc);
0707     }
0708 }
0709 
0710 static void amd_pmc_s2idle_restore(void)
0711 {
0712     struct amd_pmc_dev *pdev = &pmc;
0713     int rc;
0714     u8 msg;
0715 
0716     msg = amd_pmc_get_os_hint(pdev);
0717     rc = amd_pmc_send_cmd(pdev, 0, NULL, msg, 0);
0718     if (rc)
0719         dev_err(pdev->dev, "resume failed: %d\n", rc);
0720 
0721     /* Let SMU know that we are looking for stats */
0722     amd_pmc_send_cmd(pdev, 0, NULL, SMU_MSG_LOG_DUMP_DATA, 0);
0723 
0724     /* Dump the IdleMask to see the blockers */
0725     amd_pmc_idlemask_read(pdev, pdev->dev, NULL);
0726 
0727     /* Write data incremented by 1 to distinguish in stb_read */
0728     if (enable_stb) {
0729         rc = amd_pmc_write_stb(pdev, AMD_PMC_STB_PREDEF + 1);
0730         if (rc)
0731             dev_err(pdev->dev, "error writing to STB: %d\n", rc);
0732     }
0733 
0734     /* Notify on failed entry */
0735     amd_pmc_validate_deepest(pdev);
0736 }
0737 
0738 static struct acpi_s2idle_dev_ops amd_pmc_s2idle_dev_ops = {
0739     .prepare = amd_pmc_s2idle_prepare,
0740     .restore = amd_pmc_s2idle_restore,
0741 };
0742 #endif
0743 
0744 static const struct pci_device_id pmc_pci_ids[] = {
0745     { PCI_DEVICE(PCI_VENDOR_ID_AMD, AMD_CPU_ID_PS) },
0746     { PCI_DEVICE(PCI_VENDOR_ID_AMD, AMD_CPU_ID_CB) },
0747     { PCI_DEVICE(PCI_VENDOR_ID_AMD, AMD_CPU_ID_YC) },
0748     { PCI_DEVICE(PCI_VENDOR_ID_AMD, AMD_CPU_ID_CZN) },
0749     { PCI_DEVICE(PCI_VENDOR_ID_AMD, AMD_CPU_ID_RN) },
0750     { PCI_DEVICE(PCI_VENDOR_ID_AMD, AMD_CPU_ID_PCO) },
0751     { PCI_DEVICE(PCI_VENDOR_ID_AMD, AMD_CPU_ID_RV) },
0752     { }
0753 };
0754 
0755 static int amd_pmc_s2d_init(struct amd_pmc_dev *dev)
0756 {
0757     u32 phys_addr_low, phys_addr_hi;
0758     u64 stb_phys_addr;
0759     u32 size = 0;
0760 
0761     /* Spill to DRAM feature uses separate SMU message port */
0762     dev->msg_port = 1;
0763 
0764     amd_pmc_send_cmd(dev, S2D_TELEMETRY_SIZE, &size, STB_SPILL_TO_DRAM, 1);
0765     if (size != S2D_TELEMETRY_BYTES_MAX)
0766         return -EIO;
0767 
0768     /* Get STB DRAM address */
0769     amd_pmc_send_cmd(dev, S2D_PHYS_ADDR_LOW, &phys_addr_low, STB_SPILL_TO_DRAM, 1);
0770     amd_pmc_send_cmd(dev, S2D_PHYS_ADDR_HIGH, &phys_addr_hi, STB_SPILL_TO_DRAM, 1);
0771 
0772     stb_phys_addr = ((u64)phys_addr_hi << 32 | phys_addr_low);
0773 
0774     /* Clear msg_port for other SMU operation */
0775     dev->msg_port = 0;
0776 
0777     dev->stb_virt_addr = devm_ioremap(dev->dev, stb_phys_addr, S2D_TELEMETRY_DRAMBYTES_MAX);
0778     if (!dev->stb_virt_addr)
0779         return -ENOMEM;
0780 
0781     return 0;
0782 }
0783 
0784 #ifdef CONFIG_SUSPEND
0785 static int amd_pmc_write_stb(struct amd_pmc_dev *dev, u32 data)
0786 {
0787     int err;
0788 
0789     err = pci_write_config_dword(dev->rdev, AMD_PMC_STB_INDEX_ADDRESS, AMD_PMC_STB_PMI_0);
0790     if (err) {
0791         dev_err(dev->dev, "failed to write addr in stb: 0x%X\n",
0792             AMD_PMC_STB_INDEX_ADDRESS);
0793         return pcibios_err_to_errno(err);
0794     }
0795 
0796     err = pci_write_config_dword(dev->rdev, AMD_PMC_STB_INDEX_DATA, data);
0797     if (err) {
0798         dev_err(dev->dev, "failed to write data in stb: 0x%X\n",
0799             AMD_PMC_STB_INDEX_DATA);
0800         return pcibios_err_to_errno(err);
0801     }
0802 
0803     return 0;
0804 }
0805 #endif
0806 
0807 static int amd_pmc_read_stb(struct amd_pmc_dev *dev, u32 *buf)
0808 {
0809     int i, err;
0810 
0811     err = pci_write_config_dword(dev->rdev, AMD_PMC_STB_INDEX_ADDRESS, AMD_PMC_STB_PMI_0);
0812     if (err) {
0813         dev_err(dev->dev, "error writing addr to stb: 0x%X\n",
0814             AMD_PMC_STB_INDEX_ADDRESS);
0815         return pcibios_err_to_errno(err);
0816     }
0817 
0818     for (i = 0; i < FIFO_SIZE; i++) {
0819         err = pci_read_config_dword(dev->rdev, AMD_PMC_STB_INDEX_DATA, buf++);
0820         if (err) {
0821             dev_err(dev->dev, "error reading data from stb: 0x%X\n",
0822                 AMD_PMC_STB_INDEX_DATA);
0823             return pcibios_err_to_errno(err);
0824         }
0825     }
0826 
0827     return 0;
0828 }
0829 
0830 static int amd_pmc_probe(struct platform_device *pdev)
0831 {
0832     struct amd_pmc_dev *dev = &pmc;
0833     struct pci_dev *rdev;
0834     u32 base_addr_lo, base_addr_hi;
0835     u64 base_addr;
0836     int err;
0837     u32 val;
0838 
0839     dev->dev = &pdev->dev;
0840 
0841     rdev = pci_get_domain_bus_and_slot(0, 0, PCI_DEVFN(0, 0));
0842     if (!rdev || !pci_match_id(pmc_pci_ids, rdev)) {
0843         err = -ENODEV;
0844         goto err_pci_dev_put;
0845     }
0846 
0847     dev->cpu_id = rdev->device;
0848     dev->rdev = rdev;
0849     err = pci_write_config_dword(rdev, AMD_PMC_SMU_INDEX_ADDRESS, AMD_PMC_BASE_ADDR_LO);
0850     if (err) {
0851         dev_err(dev->dev, "error writing to 0x%x\n", AMD_PMC_SMU_INDEX_ADDRESS);
0852         err = pcibios_err_to_errno(err);
0853         goto err_pci_dev_put;
0854     }
0855 
0856     err = pci_read_config_dword(rdev, AMD_PMC_SMU_INDEX_DATA, &val);
0857     if (err) {
0858         err = pcibios_err_to_errno(err);
0859         goto err_pci_dev_put;
0860     }
0861 
0862     base_addr_lo = val & AMD_PMC_BASE_ADDR_HI_MASK;
0863 
0864     err = pci_write_config_dword(rdev, AMD_PMC_SMU_INDEX_ADDRESS, AMD_PMC_BASE_ADDR_HI);
0865     if (err) {
0866         dev_err(dev->dev, "error writing to 0x%x\n", AMD_PMC_SMU_INDEX_ADDRESS);
0867         err = pcibios_err_to_errno(err);
0868         goto err_pci_dev_put;
0869     }
0870 
0871     err = pci_read_config_dword(rdev, AMD_PMC_SMU_INDEX_DATA, &val);
0872     if (err) {
0873         err = pcibios_err_to_errno(err);
0874         goto err_pci_dev_put;
0875     }
0876 
0877     base_addr_hi = val & AMD_PMC_BASE_ADDR_LO_MASK;
0878     base_addr = ((u64)base_addr_hi << 32 | base_addr_lo);
0879 
0880     dev->regbase = devm_ioremap(dev->dev, base_addr + AMD_PMC_BASE_ADDR_OFFSET,
0881                     AMD_PMC_MAPPING_SIZE);
0882     if (!dev->regbase) {
0883         err = -ENOMEM;
0884         goto err_pci_dev_put;
0885     }
0886 
0887     mutex_init(&dev->lock);
0888 
0889     if (enable_stb && (dev->cpu_id == AMD_CPU_ID_YC || dev->cpu_id == AMD_CPU_ID_CB)) {
0890         err = amd_pmc_s2d_init(dev);
0891         if (err)
0892             return err;
0893     }
0894 
0895     platform_set_drvdata(pdev, dev);
0896 #ifdef CONFIG_SUSPEND
0897     err = acpi_register_lps0_dev(&amd_pmc_s2idle_dev_ops);
0898     if (err)
0899         dev_warn(dev->dev, "failed to register LPS0 sleep handler, expect increased power consumption\n");
0900 #endif
0901 
0902     amd_pmc_dbgfs_register(dev);
0903     return 0;
0904 
0905 err_pci_dev_put:
0906     pci_dev_put(rdev);
0907     return err;
0908 }
0909 
0910 static int amd_pmc_remove(struct platform_device *pdev)
0911 {
0912     struct amd_pmc_dev *dev = platform_get_drvdata(pdev);
0913 
0914 #ifdef CONFIG_SUSPEND
0915     acpi_unregister_lps0_dev(&amd_pmc_s2idle_dev_ops);
0916 #endif
0917     amd_pmc_dbgfs_unregister(dev);
0918     pci_dev_put(dev->rdev);
0919     mutex_destroy(&dev->lock);
0920     return 0;
0921 }
0922 
0923 static const struct acpi_device_id amd_pmc_acpi_ids[] = {
0924     {"AMDI0005", 0},
0925     {"AMDI0006", 0},
0926     {"AMDI0007", 0},
0927     {"AMDI0008", 0},
0928     {"AMD0004", 0},
0929     {"AMD0005", 0},
0930     { }
0931 };
0932 MODULE_DEVICE_TABLE(acpi, amd_pmc_acpi_ids);
0933 
0934 static struct platform_driver amd_pmc_driver = {
0935     .driver = {
0936         .name = "amd_pmc",
0937         .acpi_match_table = amd_pmc_acpi_ids,
0938     },
0939     .probe = amd_pmc_probe,
0940     .remove = amd_pmc_remove,
0941 };
0942 module_platform_driver(amd_pmc_driver);
0943 
0944 MODULE_LICENSE("GPL v2");
0945 MODULE_DESCRIPTION("AMD PMC Driver");