mirror of
git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2025-08-05 16:54:27 +00:00

The function name is ambiguous because it returns an intermediate value for calculating maximum frequency rather than the CPPC 'Highest Perf' register. Rename the function to clarify its use and allow the function to return errors. Adjust the consumer in acpi-cpufreq to catch errors. Reviewed-by: Gautham R. Shenoy <gautham.shenoy@amd.com> Signed-off-by: Mario Limonciello <mario.limonciello@amd.com>
242 lines
5.8 KiB
C
242 lines
5.8 KiB
C
/* SPDX-License-Identifier: GPL-2.0-only */
|
|
/*
|
|
* CPPC (Collaborative Processor Performance Control) methods used
|
|
* by CPUfreq drivers.
|
|
*
|
|
* (C) Copyright 2014, 2015 Linaro Ltd.
|
|
* Author: Ashwin Chaugule <ashwin.chaugule@linaro.org>
|
|
*/
|
|
|
|
#ifndef _CPPC_ACPI_H
|
|
#define _CPPC_ACPI_H
|
|
|
|
#include <linux/acpi.h>
|
|
#include <linux/cpufreq.h>
|
|
#include <linux/types.h>
|
|
|
|
#include <acpi/pcc.h>
|
|
#include <acpi/processor.h>
|
|
|
|
/* CPPCv2 and CPPCv3 support */
|
|
#define CPPC_V2_REV 2
|
|
#define CPPC_V3_REV 3
|
|
#define CPPC_V2_NUM_ENT 21
|
|
#define CPPC_V3_NUM_ENT 23
|
|
|
|
#define PCC_CMD_COMPLETE_MASK (1 << 0)
|
|
#define PCC_ERROR_MASK (1 << 2)
|
|
|
|
#define MAX_CPC_REG_ENT 21
|
|
|
|
/* CPPC specific PCC commands. */
|
|
#define CMD_READ 0
|
|
#define CMD_WRITE 1
|
|
|
|
/* Each register has the folowing format. */
|
|
struct cpc_reg {
|
|
u8 descriptor;
|
|
u16 length;
|
|
u8 space_id;
|
|
u8 bit_width;
|
|
u8 bit_offset;
|
|
u8 access_width;
|
|
u64 address;
|
|
} __packed;
|
|
|
|
/*
|
|
* Each entry in the CPC table is either
|
|
* of type ACPI_TYPE_BUFFER or
|
|
* ACPI_TYPE_INTEGER.
|
|
*/
|
|
struct cpc_register_resource {
|
|
acpi_object_type type;
|
|
u64 __iomem *sys_mem_vaddr;
|
|
union {
|
|
struct cpc_reg reg;
|
|
u64 int_value;
|
|
} cpc_entry;
|
|
};
|
|
|
|
/* Container to hold the CPC details for each CPU */
|
|
struct cpc_desc {
|
|
int num_entries;
|
|
int version;
|
|
int cpu_id;
|
|
int write_cmd_status;
|
|
int write_cmd_id;
|
|
struct cpc_register_resource cpc_regs[MAX_CPC_REG_ENT];
|
|
struct acpi_psd_package domain_info;
|
|
struct kobject kobj;
|
|
};
|
|
|
|
/* These are indexes into the per-cpu cpc_regs[]. Order is important. */
|
|
enum cppc_regs {
|
|
HIGHEST_PERF,
|
|
NOMINAL_PERF,
|
|
LOW_NON_LINEAR_PERF,
|
|
LOWEST_PERF,
|
|
GUARANTEED_PERF,
|
|
DESIRED_PERF,
|
|
MIN_PERF,
|
|
MAX_PERF,
|
|
PERF_REDUC_TOLERANCE,
|
|
TIME_WINDOW,
|
|
CTR_WRAP_TIME,
|
|
REFERENCE_CTR,
|
|
DELIVERED_CTR,
|
|
PERF_LIMITED,
|
|
ENABLE,
|
|
AUTO_SEL_ENABLE,
|
|
AUTO_ACT_WINDOW,
|
|
ENERGY_PERF,
|
|
REFERENCE_PERF,
|
|
LOWEST_FREQ,
|
|
NOMINAL_FREQ,
|
|
};
|
|
|
|
/*
|
|
* Categorization of registers as described
|
|
* in the ACPI v.5.1 spec.
|
|
* XXX: Only filling up ones which are used by governors
|
|
* today.
|
|
*/
|
|
struct cppc_perf_caps {
|
|
u32 guaranteed_perf;
|
|
u32 highest_perf;
|
|
u32 nominal_perf;
|
|
u32 lowest_perf;
|
|
u32 lowest_nonlinear_perf;
|
|
u32 lowest_freq;
|
|
u32 nominal_freq;
|
|
u32 energy_perf;
|
|
bool auto_sel;
|
|
};
|
|
|
|
struct cppc_perf_ctrls {
|
|
u32 max_perf;
|
|
u32 min_perf;
|
|
u32 desired_perf;
|
|
u32 energy_perf;
|
|
};
|
|
|
|
struct cppc_perf_fb_ctrs {
|
|
u64 reference;
|
|
u64 delivered;
|
|
u64 reference_perf;
|
|
u64 wraparound_time;
|
|
};
|
|
|
|
/* Per CPU container for runtime CPPC management. */
|
|
struct cppc_cpudata {
|
|
struct list_head node;
|
|
struct cppc_perf_caps perf_caps;
|
|
struct cppc_perf_ctrls perf_ctrls;
|
|
struct cppc_perf_fb_ctrs perf_fb_ctrs;
|
|
unsigned int shared_type;
|
|
cpumask_var_t shared_cpu_map;
|
|
};
|
|
|
|
#ifdef CONFIG_ACPI_CPPC_LIB
|
|
extern int cppc_get_desired_perf(int cpunum, u64 *desired_perf);
|
|
extern int cppc_get_nominal_perf(int cpunum, u64 *nominal_perf);
|
|
extern int cppc_get_highest_perf(int cpunum, u64 *highest_perf);
|
|
extern int cppc_get_perf_ctrs(int cpu, struct cppc_perf_fb_ctrs *perf_fb_ctrs);
|
|
extern int cppc_set_perf(int cpu, struct cppc_perf_ctrls *perf_ctrls);
|
|
extern int cppc_set_enable(int cpu, bool enable);
|
|
extern int cppc_get_perf_caps(int cpu, struct cppc_perf_caps *caps);
|
|
extern bool cppc_perf_ctrs_in_pcc(void);
|
|
extern unsigned int cppc_perf_to_khz(struct cppc_perf_caps *caps, unsigned int perf);
|
|
extern unsigned int cppc_khz_to_perf(struct cppc_perf_caps *caps, unsigned int freq);
|
|
extern bool acpi_cpc_valid(void);
|
|
extern bool cppc_allow_fast_switch(void);
|
|
extern int acpi_get_psd_map(unsigned int cpu, struct cppc_cpudata *cpu_data);
|
|
extern unsigned int cppc_get_transition_latency(int cpu);
|
|
extern bool cpc_ffh_supported(void);
|
|
extern bool cpc_supported_by_cpu(void);
|
|
extern int cpc_read_ffh(int cpunum, struct cpc_reg *reg, u64 *val);
|
|
extern int cpc_write_ffh(int cpunum, struct cpc_reg *reg, u64 val);
|
|
extern int cppc_get_epp_perf(int cpunum, u64 *epp_perf);
|
|
extern int cppc_set_epp_perf(int cpu, struct cppc_perf_ctrls *perf_ctrls, bool enable);
|
|
extern int cppc_get_auto_sel_caps(int cpunum, struct cppc_perf_caps *perf_caps);
|
|
extern int cppc_set_auto_sel(int cpu, bool enable);
|
|
extern int amd_get_boost_ratio_numerator(unsigned int cpu, u64 *numerator);
|
|
#else /* !CONFIG_ACPI_CPPC_LIB */
|
|
static inline int cppc_get_desired_perf(int cpunum, u64 *desired_perf)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int cppc_get_nominal_perf(int cpunum, u64 *nominal_perf)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int cppc_get_highest_perf(int cpunum, u64 *highest_perf)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int cppc_get_perf_ctrs(int cpu, struct cppc_perf_fb_ctrs *perf_fb_ctrs)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int cppc_set_perf(int cpu, struct cppc_perf_ctrls *perf_ctrls)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int cppc_set_enable(int cpu, bool enable)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int cppc_get_perf_caps(int cpu, struct cppc_perf_caps *caps)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline bool cppc_perf_ctrs_in_pcc(void)
|
|
{
|
|
return false;
|
|
}
|
|
static inline bool acpi_cpc_valid(void)
|
|
{
|
|
return false;
|
|
}
|
|
static inline bool cppc_allow_fast_switch(void)
|
|
{
|
|
return false;
|
|
}
|
|
static inline unsigned int cppc_get_transition_latency(int cpu)
|
|
{
|
|
return CPUFREQ_ETERNAL;
|
|
}
|
|
static inline bool cpc_ffh_supported(void)
|
|
{
|
|
return false;
|
|
}
|
|
static inline int cpc_read_ffh(int cpunum, struct cpc_reg *reg, u64 *val)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int cpc_write_ffh(int cpunum, struct cpc_reg *reg, u64 val)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int cppc_set_epp_perf(int cpu, struct cppc_perf_ctrls *perf_ctrls, bool enable)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int cppc_get_epp_perf(int cpunum, u64 *epp_perf)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int cppc_set_auto_sel(int cpu, bool enable)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int cppc_get_auto_sel_caps(int cpunum, struct cppc_perf_caps *perf_caps)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
static inline int amd_get_boost_ratio_numerator(unsigned int cpu, u64 *numerator)
|
|
{
|
|
return -EOPNOTSUPP;
|
|
}
|
|
#endif /* !CONFIG_ACPI_CPPC_LIB */
|
|
|
|
#endif /* _CPPC_ACPI_H*/
|