mirror of
https://github.com/torvalds/linux.git
synced 2026-07-28 18:21:24 +02:00
platform/x86/intel/pmc: Enable PkgC LTR blocking counter
Enable the Package C-state LTR blocking counter in the PMT telemetry region. This counter records how many times any Package C-state entry is blocked for the specified reasons. Add pmc_core_pkgc_counters_show() as a common helper to display package C-state blocking counters from the telemetry region. Signed-off-by: Xi Pardee <xi.pardee@linux.intel.com> Link: https://patch.msgid.link/20260505043342.2573556-3-xi.pardee@linux.intel.com Reviewed-by: Ilpo Järvinen <ilpo.jarvinen@linux.intel.com> Signed-off-by: Ilpo Järvinen <ilpo.jarvinen@linux.intel.com>
This commit is contained in:
parent
dfe614f82e
commit
38c79dd63b
|
|
@ -1071,6 +1071,34 @@ static int pmc_core_die_c6_us_show(struct seq_file *s, void *unused)
|
|||
}
|
||||
DEFINE_SHOW_ATTRIBUTE(pmc_core_die_c6_us);
|
||||
|
||||
static int pmc_core_pkgc_counters_show(struct seq_file *s,
|
||||
struct telem_endpoint *ep,
|
||||
u32 offset, const char **counters)
|
||||
{
|
||||
unsigned int i;
|
||||
u32 counter;
|
||||
int ret;
|
||||
|
||||
for (i = 0; counters[i]; i++) {
|
||||
ret = pmt_telem_read32(ep, offset + i, &counter, 1);
|
||||
if (ret)
|
||||
return ret;
|
||||
seq_printf(s, "%-30s %-30u\n", counters[i], counter);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int pmc_core_pkgc_ltr_blocker_show(struct seq_file *s, void *unused)
|
||||
{
|
||||
struct pmc_dev *pmcdev = s->private;
|
||||
|
||||
return pmc_core_pkgc_counters_show(s, pmcdev->pc_ep,
|
||||
pmcdev->pkgc_ltr_blocker_offset,
|
||||
pmcdev->pkgc_ltr_blocker_counters);
|
||||
}
|
||||
DEFINE_SHOW_ATTRIBUTE(pmc_core_pkgc_ltr_blocker);
|
||||
|
||||
static int pmc_core_lpm_latch_mode_show(struct seq_file *s, void *unused)
|
||||
{
|
||||
struct pmc_dev *pmcdev = s->private;
|
||||
|
|
@ -1322,7 +1350,7 @@ static struct telem_endpoint *pmc_core_register_endpoint(struct pci_dev *pcidev,
|
|||
return ERR_PTR(-ENODEV);
|
||||
}
|
||||
|
||||
void pmc_core_punit_pmt_init(struct pmc_dev *pmcdev, u32 *guids)
|
||||
void pmc_core_punit_pmt_init(struct pmc_dev *pmcdev, struct pmc_dev_info *pmc_dev_info)
|
||||
{
|
||||
struct telem_endpoint *ep;
|
||||
|
||||
|
|
@ -1333,16 +1361,32 @@ void pmc_core_punit_pmt_init(struct pmc_dev *pmcdev, u32 *guids)
|
|||
return;
|
||||
}
|
||||
|
||||
ep = pmc_core_register_endpoint(pcidev, guids);
|
||||
if (IS_ERR(ep)) {
|
||||
dev_err(&pmcdev->pdev->dev,
|
||||
"pmc_core: couldn't get DMU telem endpoint %ld",
|
||||
PTR_ERR(ep));
|
||||
return;
|
||||
if (pmc_dev_info->dmu_guids) {
|
||||
ep = pmc_core_register_endpoint(pcidev, pmc_dev_info->dmu_guids);
|
||||
if (IS_ERR(ep)) {
|
||||
dev_err(&pmcdev->pdev->dev,
|
||||
"pmc_core: couldn't get DMU telem endpoint %ld",
|
||||
PTR_ERR(ep));
|
||||
return;
|
||||
}
|
||||
|
||||
pmcdev->punit_ep = ep;
|
||||
pmcdev->die_c6_offset = MTL_PMT_DMU_DIE_C6_OFFSET;
|
||||
}
|
||||
|
||||
pmcdev->punit_ep = ep;
|
||||
pmcdev->die_c6_offset = MTL_PMT_DMU_DIE_C6_OFFSET;
|
||||
if (pmc_dev_info->pc_guid) {
|
||||
ep = pmt_telem_find_and_register_endpoint(&pcidev->dev, pmc_dev_info->pc_guid, 0);
|
||||
if (IS_ERR(ep)) {
|
||||
dev_err(&pmcdev->pdev->dev,
|
||||
"pmc_core: couldn't get Package C-state telem endpoint %ld",
|
||||
PTR_ERR(ep));
|
||||
return;
|
||||
}
|
||||
|
||||
pmcdev->pc_ep = ep;
|
||||
pmcdev->pkgc_ltr_blocker_counters = pmc_dev_info->pkgc_ltr_blocker_counters;
|
||||
pmcdev->pkgc_ltr_blocker_offset = pmc_dev_info->pkgc_ltr_blocker_offset;
|
||||
}
|
||||
}
|
||||
|
||||
void pmc_core_set_device_d3(unsigned int device)
|
||||
|
|
@ -1466,6 +1510,13 @@ static void pmc_core_dbgfs_register(struct pmc_dev *pmcdev, struct pmc_dev_info
|
|||
pmcdev->dbgfs_dir, pmcdev,
|
||||
&pmc_core_die_c6_us_fops);
|
||||
}
|
||||
|
||||
if (pmcdev->pc_ep) {
|
||||
debugfs_create_file("pkgc_ltr_blocker_show", 0444,
|
||||
pmcdev->dbgfs_dir, pmcdev,
|
||||
&pmc_core_pkgc_ltr_blocker_fops);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
@ -1716,8 +1767,8 @@ int generic_core_init(struct pmc_dev *pmcdev, struct pmc_dev_info *pmc_dev_info)
|
|||
}
|
||||
|
||||
pmc_core_get_low_power_modes(pmcdev);
|
||||
if (pmc_dev_info->dmu_guids)
|
||||
pmc_core_punit_pmt_init(pmcdev, pmc_dev_info->dmu_guids);
|
||||
if (pmc_dev_info->dmu_guids || pmc_dev_info->pc_guid)
|
||||
pmc_core_punit_pmt_init(pmcdev, pmc_dev_info);
|
||||
|
||||
if (ssram) {
|
||||
ret = pmc_core_get_telem_info(pmcdev, pmc_dev_info);
|
||||
|
|
@ -1738,6 +1789,9 @@ int generic_core_init(struct pmc_dev *pmcdev, struct pmc_dev_info *pmc_dev_info)
|
|||
if (pmcdev->punit_ep)
|
||||
pmt_telem_unregister_endpoint(pmcdev->punit_ep);
|
||||
|
||||
if (pmcdev->pc_ep)
|
||||
pmt_telem_unregister_endpoint(pmcdev->pc_ep);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
|
@ -1834,6 +1888,9 @@ static void pmc_core_clean_structure(struct platform_device *pdev)
|
|||
if (pmcdev->punit_ep)
|
||||
pmt_telem_unregister_endpoint(pmcdev->punit_ep);
|
||||
|
||||
if (pmcdev->pc_ep)
|
||||
pmt_telem_unregister_endpoint(pmcdev->pc_ep);
|
||||
|
||||
platform_set_drvdata(pdev, NULL);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -453,6 +453,9 @@ struct pmc {
|
|||
* @suspend: Function to perform platform specific suspend
|
||||
* @resume: Function to perform platform specific resume
|
||||
*
|
||||
* @pkgc_ltr_blocker_counters: Array of PKGC LTR blocker counters
|
||||
* @pkgc_ltr_blocker_offset: Offset to PKGC LTR blockers in telemetry region
|
||||
*
|
||||
* pmc_dev contains info about power management controller device.
|
||||
*/
|
||||
struct pmc_dev {
|
||||
|
|
@ -471,8 +474,12 @@ struct pmc_dev {
|
|||
u8 num_of_pkgc;
|
||||
|
||||
u32 die_c6_offset;
|
||||
struct telem_endpoint *pc_ep;
|
||||
struct telem_endpoint *punit_ep;
|
||||
struct pmc_info *regmap_list;
|
||||
|
||||
const char **pkgc_ltr_blocker_counters;
|
||||
u32 pkgc_ltr_blocker_offset;
|
||||
};
|
||||
|
||||
enum pmc_index {
|
||||
|
|
@ -486,12 +493,15 @@ enum pmc_index {
|
|||
* struct pmc_dev_info - Structure to keep PMC device info
|
||||
* @pci_func: Function number of the primary PMC
|
||||
* @dmu_guids: List of Die Management Unit GUID
|
||||
* @pc_guid: GUID for telemetry region to read PKGC blocker info
|
||||
* @pkgc_ltr_blocker_offset: Offset to PKGC LTR blockers in telemetry region
|
||||
* @regmap_list: Pointer to a list of pmc_info structure that could be
|
||||
* available for the platform. When set, this field implies
|
||||
* SSRAM support.
|
||||
* @map: Pointer to a pmc_reg_map struct that contains platform
|
||||
* specific attributes of the primary PMC
|
||||
* @sub_req_show: File operations to show substate requirements
|
||||
* @pkgc_ltr_blocker_counters: Array of PKGC LTR blocker counters
|
||||
* @suspend: Function to perform platform specific suspend
|
||||
* @resume: Function to perform platform specific resume
|
||||
* @init: Function to perform platform specific init action
|
||||
|
|
@ -500,9 +510,12 @@ enum pmc_index {
|
|||
struct pmc_dev_info {
|
||||
u8 pci_func;
|
||||
u32 *dmu_guids;
|
||||
u32 pc_guid;
|
||||
u32 pkgc_ltr_blocker_offset;
|
||||
struct pmc_info *regmap_list;
|
||||
const struct pmc_reg_map *map;
|
||||
const struct file_operations *sub_req_show;
|
||||
const char **pkgc_ltr_blocker_counters;
|
||||
void (*suspend)(struct pmc_dev *pmcdev);
|
||||
int (*resume)(struct pmc_dev *pmcdev);
|
||||
int (*init)(struct pmc_dev *pmcdev, struct pmc_dev_info *pmc_dev_info);
|
||||
|
|
@ -535,7 +548,7 @@ int pmc_core_send_ltr_ignore(struct pmc_dev *pmcdev, u32 value, int ignore);
|
|||
|
||||
int pmc_core_resume_common(struct pmc_dev *pmcdev);
|
||||
int get_primary_reg_base(struct pmc *pmc);
|
||||
void pmc_core_punit_pmt_init(struct pmc_dev *pmcdev, u32 *guids);
|
||||
void pmc_core_punit_pmt_init(struct pmc_dev *pmcdev, struct pmc_dev_info *pmc_dev_info);
|
||||
void pmc_core_set_device_d3(unsigned int device);
|
||||
|
||||
int generic_core_init(struct pmc_dev *pmcdev, struct pmc_dev_info *pmc_dev_info);
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user