// SPDX-License-Identifier: GPL-2.0
/*
 * Intel Speed Select -- Enumerate and control features for TPMI Interface
 * Copyright (c) 2022 Intel Corporation.
 */

#include <linux/isst_if.h>
#include "isst.h"

int tpmi_process_ioctl(int ioctl_no, void *info)
{
	const char *pathname = "/dev/isst_interface";
	int fd;

	if (is_debug_enabled()) {
		debug_printf("Issue IOCTL: ");
		switch (ioctl_no) {
		case ISST_IF_CORE_POWER_STATE:
			debug_printf("ISST_IF_CORE_POWER_STATE\n");
			break;
		case ISST_IF_CLOS_PARAM:
			debug_printf("ISST_IF_CLOS_PARAM\n");
			break;
		case ISST_IF_CLOS_ASSOC:
			debug_printf("ISST_IF_CLOS_ASSOC\n");
			break;
		case ISST_IF_PERF_LEVELS:
			debug_printf("ISST_IF_PERF_LEVELS\n");
			break;
		case ISST_IF_PERF_SET_LEVEL:
			debug_printf("ISST_IF_PERF_SET_LEVEL\n");
			break;
		case ISST_IF_PERF_SET_FEATURE:
			debug_printf("ISST_IF_PERF_SET_FEATURE\n");
			break;
		case ISST_IF_GET_PERF_LEVEL_INFO:
			debug_printf("ISST_IF_GET_PERF_LEVEL_INFO\n");
			break;
		case ISST_IF_GET_PERF_LEVEL_CPU_MASK:
			debug_printf("ISST_IF_GET_PERF_LEVEL_CPU_MASK\n");
			break;
		case ISST_IF_GET_BASE_FREQ_INFO:
			debug_printf("ISST_IF_GET_BASE_FREQ_INFO\n");
			break;
		case ISST_IF_GET_BASE_FREQ_CPU_MASK:
			debug_printf("ISST_IF_GET_BASE_FREQ_CPU_MASK\n");
			break;
		case ISST_IF_GET_TURBO_FREQ_INFO:
			debug_printf("ISST_IF_GET_TURBO_FREQ_INFO\n");
			break;
		case ISST_IF_COUNT_TPMI_INSTANCES:
			debug_printf("ISST_IF_COUNT_TPMI_INSTANCES\n");
			break;
		default:
			debug_printf("%d\n", ioctl_no);
			break;
		}
	}

	fd = open(pathname, O_RDWR);
	if (fd < 0)
		return -1;

	if (ioctl(fd, ioctl_no, info) == -1) {
		debug_printf("IOCTL %d Failed\n", ioctl_no);
		close(fd);
		return -1;
	}

	close(fd);

	return 0;
}

static int tpmi_get_disp_freq_multiplier(void)
{
	return 1;
}

static int tpmi_get_trl_max_levels(void)
{
	return TRL_MAX_LEVELS;
}

static char *tpmi_get_trl_level_name(int level)
{
	switch (level) {
	case 0:
		return "level-0";
	case 1:
		return "level-1";
	case 2:
		return "level-2";
	case 3:
		return "level-3";
	case 4:
		return "level-4";
	case 5:
		return "level-5";
	case 6:
		return "level-6";
	case 7:
		return "level-7";
	default:
		return NULL;
	}
}


static void tpmi_update_platform_param(enum isst_platform_param param, int value)
{
	/* No params need to be updated for now */
}

static int tpmi_is_punit_valid(struct isst_id *id)
{
	struct isst_tpmi_instance_count info;
	int ret;

	if (id->punit < 0)
		return 0;

	info.socket_id = id->pkg;
	ret = tpmi_process_ioctl(ISST_IF_COUNT_TPMI_INSTANCES, &info);
	if (ret == -1)
		return 0;

	if (info.valid_mask & BIT(id->punit))
		return 1;

	return 0;
}

static int tpmi_read_pm_config(struct isst_id *id, int *cp_state, int *cp_cap)
{
	struct isst_core_power info;
	int ret;

	info.get_set = 0;
	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	ret = tpmi_process_ioctl(ISST_IF_CORE_POWER_STATE, &info);
	if (ret == -1)
		return ret;

	*cp_state = info.enable;
	*cp_cap = info.supported;

	return 0;
}

int tpmi_get_config_levels(struct isst_id *id, struct isst_pkg_ctdp *pkg_dev)
{
	struct isst_perf_level_info info;
	int ret;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;

	ret = tpmi_process_ioctl(ISST_IF_PERF_LEVELS, &info);
	if (ret == -1)
		return ret;

	pkg_dev->version = info.feature_rev;
	pkg_dev->levels = info.max_level;
	pkg_dev->locked = info.locked;
	pkg_dev->current_level = info.current_level;
	pkg_dev->locked = info.locked;
	pkg_dev->enabled = info.enabled;

	return 0;
}

static int tpmi_get_ctdp_control(struct isst_id *id, int config_index,
				 struct isst_pkg_ctdp_level_info *ctdp_level)
{
	struct isst_core_power core_power_info;
	struct isst_perf_level_info info;
	int level_mask;
	int ret;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;

	ret = tpmi_process_ioctl(ISST_IF_PERF_LEVELS, &info);
	if (ret == -1)
		return -1;

	if (config_index != 0xff)
		level_mask = 1 << config_index;
	else
		level_mask = config_index;

	if (!(info.level_mask & level_mask))
		return -1;

	ctdp_level->fact_support = info.sst_tf_support;
	ctdp_level->pbf_support = info.sst_bf_support;
	ctdp_level->fact_enabled = !!(info.feature_state & BIT(1));
	ctdp_level->pbf_enabled = !!(info.feature_state & BIT(0));

	core_power_info.get_set = 0;
	core_power_info.socket_id = id->pkg;
	core_power_info.power_domain_id = id->punit;

	ret = tpmi_process_ioctl(ISST_IF_CORE_POWER_STATE, &core_power_info);
	if (ret == -1)
		return ret;

	ctdp_level->sst_cp_support = core_power_info.supported;
	ctdp_level->sst_cp_enabled = core_power_info.enable;

	debug_printf
	    ("cpu:%d CONFIG_TDP_GET_TDP_CONTROL fact_support:%d pbf_support: %d fact_enabled:%d pbf_enabled:%d\n",
	     id->cpu, ctdp_level->fact_support, ctdp_level->pbf_support,
	     ctdp_level->fact_enabled, ctdp_level->pbf_enabled);

	return 0;
}

static int tpmi_get_tdp_info(struct isst_id *id, int config_index,
			     struct isst_pkg_ctdp_level_info *ctdp_level)
{
	struct isst_perf_level_data_info info;
	int ret;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.level = config_index;

	ret = tpmi_process_ioctl(ISST_IF_GET_PERF_LEVEL_INFO, &info);
	if (ret == -1)
		return ret;

	ctdp_level->pkg_tdp = info.thermal_design_power_w;
	ctdp_level->tdp_ratio = info.tdp_ratio;
	ctdp_level->sse_p1 = info.base_freq_mhz;
	ctdp_level->avx2_p1 = info.base_freq_avx2_mhz;
	ctdp_level->avx512_p1 = info.base_freq_avx512_mhz;
	ctdp_level->amx_p1 = info.base_freq_amx_mhz;

	ctdp_level->t_proc_hot = info.tjunction_max_c;
	ctdp_level->mem_freq = info.max_memory_freq_mhz;
	ctdp_level->cooling_type = info.cooling_type;

	ctdp_level->uncore_p0 = info.p0_fabric_freq_mhz;
	ctdp_level->uncore_p1 = info.p1_fabric_freq_mhz;
	ctdp_level->uncore_pm = info.pm_fabric_freq_mhz;

	debug_printf
	    ("cpu:%d ctdp:%d CONFIG_TDP_GET_TDP_INFO tdp_ratio:%d pkg_tdp:%d ctdp_level->t_proc_hot:%d\n",
	     id->cpu, config_index, ctdp_level->tdp_ratio, ctdp_level->pkg_tdp,
	     ctdp_level->t_proc_hot);

	return 0;
}

static int tpmi_get_pwr_info(struct isst_id *id, int config_index,
			     struct isst_pkg_ctdp_level_info *ctdp_level)
{
	/* TBD */
	ctdp_level->pkg_max_power = 0;
	ctdp_level->pkg_min_power = 0;

	debug_printf
	    ("cpu:%d ctdp:%d CONFIG_TDP_GET_PWR_INFO pkg_max_power:%d pkg_min_power:%d\n",
	     id->cpu, config_index, ctdp_level->pkg_max_power,
	     ctdp_level->pkg_min_power);

	return 0;
}

int tpmi_get_coremask_info(struct isst_id *id, int config_index,
			   struct isst_pkg_ctdp_level_info *ctdp_level)
{
	struct isst_perf_level_cpu_mask info;
	int ret, cpu_count;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.level = config_index;
	info.punit_cpu_map = 1;

	ret = tpmi_process_ioctl(ISST_IF_GET_PERF_LEVEL_CPU_MASK, &info);
	if (ret == -1)
		return ret;

	set_cpu_mask_from_punit_coremask(id, info.mask,
					 ctdp_level->core_cpumask_size,
					 ctdp_level->core_cpumask, &cpu_count);
	ctdp_level->cpu_count = cpu_count;

	debug_printf("cpu:%d ctdp:%d core_mask ino cpu count:%d\n",
		     id->cpu, config_index, ctdp_level->cpu_count);

	return 0;
}

static int tpmi_get_get_trls(struct isst_id *id, int config_index,
			     struct isst_pkg_ctdp_level_info *ctdp_level)
{
	struct isst_perf_level_data_info info;
	int ret, i, j;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.level = config_index;

	ret = tpmi_process_ioctl(ISST_IF_GET_PERF_LEVEL_INFO, &info);
	if (ret == -1)
		return ret;

	if (info.max_buckets > TRL_MAX_BUCKETS)
		info.max_buckets = TRL_MAX_BUCKETS;

	if (info.max_trl_levels > TRL_MAX_LEVELS)
		info.max_trl_levels = TRL_MAX_LEVELS;

	for (i = 0; i < info.max_trl_levels; ++i)
		for (j = 0; j < info.max_buckets; ++j)
			ctdp_level->trl_ratios[i][j] = info.trl_freq_mhz[i][j];

	return 0;
}

static int tpmi_get_get_trl(struct isst_id *id, int level, int config_index,
			    int *trl)
{
	struct isst_pkg_ctdp_level_info ctdp_level;
	int ret, i;

	ret = tpmi_get_get_trls(id, config_index, &ctdp_level);
	if (ret)
		return ret;

	/* FIX ME: Just return for level 0 */
	for (i = 0; i < 8; ++i)
		trl[i] = ctdp_level.trl_ratios[0][i];

	return 0;
}

static int tpmi_get_trl_bucket_info(struct isst_id *id, int config_index,
				    unsigned long long *buckets_info)
{
	struct isst_perf_level_data_info info;
	unsigned char *mask = (unsigned char *)buckets_info;
	int ret, i;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.level = config_index;

	ret = tpmi_process_ioctl(ISST_IF_GET_PERF_LEVEL_INFO, &info);
	if (ret == -1)
		return ret;

	if (info.max_buckets > TRL_MAX_BUCKETS)
		info.max_buckets = TRL_MAX_BUCKETS;

	for (i = 0; i < info.max_buckets; ++i)
		mask[i] = info.bucket_core_counts[i];

	debug_printf("cpu:%d TRL bucket info: 0x%llx\n", id->cpu,
		     *buckets_info);

	return 0;
}

static int tpmi_set_tdp_level(struct isst_id *id, int tdp_level)
{
	struct isst_perf_level_control info;
	int ret;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.level = tdp_level;

	ret = tpmi_process_ioctl(ISST_IF_PERF_SET_LEVEL, &info);
	if (ret == -1)
		return ret;

	return 0;
}

static int _pbf_get_coremask_info(struct isst_id *id, int config_index,
				  struct isst_pbf_info *pbf_info)
{
	struct isst_perf_level_cpu_mask info;
	int ret, cpu_count;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.level = config_index;
	info.punit_cpu_map = 1;

	ret = tpmi_process_ioctl(ISST_IF_GET_BASE_FREQ_CPU_MASK, &info);
	if (ret == -1)
		return ret;

	set_cpu_mask_from_punit_coremask(id, info.mask,
					 pbf_info->core_cpumask_size,
					 pbf_info->core_cpumask, &cpu_count);

	debug_printf("cpu:%d ctdp:%d pbf core_mask info cpu count:%d\n",
		     id->cpu, config_index, cpu_count);

	return 0;
}

static int tpmi_get_pbf_info(struct isst_id *id, int level,
			     struct isst_pbf_info *pbf_info)
{
	struct isst_base_freq_info info;
	int ret;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.level = level;

	ret = tpmi_process_ioctl(ISST_IF_GET_BASE_FREQ_INFO, &info);
	if (ret == -1)
		return ret;

	pbf_info->p1_low = info.low_base_freq_mhz;
	pbf_info->p1_high = info.high_base_freq_mhz;
	pbf_info->tdp = info.thermal_design_power_w;
	pbf_info->t_prochot = info.tjunction_max_c;

	debug_printf("cpu:%d ctdp:%d pbf info:%d:%d:%d:%d\n",
		     id->cpu, level, pbf_info->p1_low, pbf_info->p1_high,
		     pbf_info->tdp, pbf_info->t_prochot);

	return _pbf_get_coremask_info(id, level, pbf_info);
}

static int tpmi_set_pbf_fact_status(struct isst_id *id, int pbf, int enable)
{
	struct isst_pkg_ctdp pkg_dev;
	struct isst_pkg_ctdp_level_info ctdp_level;
	int current_level;
	struct isst_perf_feature_control info;
	int ret;

	ret = isst_get_ctdp_levels(id, &pkg_dev);
	if (ret)
		debug_printf("cpu:%d No support for dynamic ISST\n", id->cpu);

	current_level = pkg_dev.current_level;

	ret = isst_get_ctdp_control(id, current_level, &ctdp_level);
	if (ret)
		return ret;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;

	info.feature = 0;

	if (pbf) {
		if (ctdp_level.fact_enabled)
			info.feature |= BIT(1);

		if (enable)
			info.feature |= BIT(0);
		else
			info.feature &= ~BIT(0);
	} else {

		if (enable && !ctdp_level.sst_cp_enabled)
			isst_display_error_info_message(0,
							"Make sure to execute before: core-power enable",
							0, 0);

		if (ctdp_level.pbf_enabled)
			info.feature |= BIT(0);

		if (enable)
			info.feature |= BIT(1);
		else
			info.feature &= ~BIT(1);
	}

	ret = tpmi_process_ioctl(ISST_IF_PERF_SET_FEATURE, &info);
	if (ret == -1)
		return ret;

	return 0;
}

static int tpmi_get_fact_info(struct isst_id *id, int level, int fact_bucket,
			      struct isst_fact_info *fact_info)
{
	struct isst_turbo_freq_info info;
	int i, j;
	int ret;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.level = level;

	ret = tpmi_process_ioctl(ISST_IF_GET_TURBO_FREQ_INFO, &info);
	if (ret == -1)
		return ret;

	for (i = 0; i < info.max_clip_freqs; ++i)
		fact_info->lp_ratios[i] = info.lp_clip_freq_mhz[i];

	if (info.max_buckets > TRL_MAX_BUCKETS)
		info.max_buckets = TRL_MAX_BUCKETS;

	if (info.max_trl_levels > TRL_MAX_LEVELS)
		info.max_trl_levels = TRL_MAX_LEVELS;

	for (i = 0; i < info.max_trl_levels; ++i) {
		for (j = 0; j < info.max_buckets; ++j)
			fact_info->bucket_info[j].hp_ratios[i] =
			    info.trl_freq_mhz[i][j];
	}

	for (i = 0; i < info.max_buckets; ++i)
		fact_info->bucket_info[i].hp_cores = info.bucket_core_counts[i];

	return 0;
}

static void _set_uncore_min_max(struct isst_id *id, int max, int freq)
{
	DIR *dir;
	FILE *filep;
	struct dirent *entry;
	char buffer[512];
	unsigned int tmp_id;
	int ret;

	dir = opendir("/sys/devices/system/cpu/intel_uncore_frequency/");
	if (!dir)
		return;

	while ((entry = readdir(dir)) != NULL ) {
		/* Check domain_id */
		snprintf(buffer, sizeof(buffer),
			 "/sys/devices/system/cpu/intel_uncore_frequency/%s/domain_id", entry->d_name);

		filep = fopen(buffer, "r");
		if (!filep)
			goto end;

		ret = fscanf(filep, "%u", &tmp_id);
		fclose(filep);
		if (ret != 1)
			goto end;

		if (tmp_id != id->punit)
			continue;

		/* Check package_id */
		snprintf(buffer, sizeof(buffer),
			 "/sys/devices/system/cpu/intel_uncore_frequency/%s/package_id", entry->d_name);

		filep = fopen(buffer, "r");
		if (!filep)
			goto end;

		ret = fscanf(filep, "%u", &tmp_id);
		fclose(filep);

		if (ret != 1)
			goto end;

		if (tmp_id != id->pkg)
			continue;

		/* Found the right sysfs path, adjust and quit */
		if (max)
			snprintf(buffer, sizeof(buffer),
				 "/sys/devices/system/cpu/intel_uncore_frequency/%s/max_freq_khz", entry->d_name);
		 else
			snprintf(buffer, sizeof(buffer),
				 "/sys/devices/system/cpu/intel_uncore_frequency/%s/min_freq_khz", entry->d_name);

		filep = fopen(buffer, "w");
		if (!filep)
			goto end;

		fprintf(filep, "%d\n", freq);
		fclose(filep);
		break;
	}

end:
	closedir(dir);
}

static void tpmi_adjust_uncore_freq(struct isst_id *id, int config_index,
				struct isst_pkg_ctdp_level_info *ctdp_level)
{
	struct isst_perf_level_data_info info;
	int ret;

	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.level = config_index;

	ret = tpmi_process_ioctl(ISST_IF_GET_PERF_LEVEL_INFO, &info);
	if (ret == -1)
		return;

	ctdp_level->uncore_p0 = info.p0_fabric_freq_mhz;
	ctdp_level->uncore_p1 = info.p1_fabric_freq_mhz;
	ctdp_level->uncore_pm = info.pm_fabric_freq_mhz;

	if (ctdp_level->uncore_pm)
		_set_uncore_min_max(id, 0, ctdp_level->uncore_pm * 100000);

	if (ctdp_level->uncore_p0)
		_set_uncore_min_max(id, 1, ctdp_level->uncore_p0 * 100000);

	return;
}

static int tpmi_get_clos_information(struct isst_id *id, int *enable, int *type)
{
	struct isst_core_power info;
	int ret;

	info.get_set = 0;
	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	ret = tpmi_process_ioctl(ISST_IF_CORE_POWER_STATE, &info);
	if (ret == -1)
		return ret;

	*enable = info.enable;
	*type = info.priority_type;

	return 0;
}

static int tpmi_pm_qos_config(struct isst_id *id, int enable_clos,
			      int priority_type)
{
	struct isst_core_power info;
	int i, ret, saved_punit;

	info.get_set = 1;
	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.enable = enable_clos;
	info.priority_type = priority_type;

	saved_punit = id->punit;

	/* Set for all other dies also. This is per package setting */
	for (i = 0; i < MAX_PUNIT_PER_DIE; i++) {
		id->punit = i;
		if (isst_is_punit_valid(id)) {
			info.power_domain_id = i;
			ret = tpmi_process_ioctl(ISST_IF_CORE_POWER_STATE, &info);
			if (ret == -1) {
				id->punit = saved_punit;
				return ret;
			}
		}
	}

	id->punit = saved_punit;

	return 0;
}

int tpmi_pm_get_clos(struct isst_id *id, int clos,
		     struct isst_clos_config *clos_config)
{
	struct isst_clos_param info;
	int ret;

	info.get_set = 0;
	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.clos = clos;

	ret = tpmi_process_ioctl(ISST_IF_CLOS_PARAM, &info);
	if (ret == -1)
		return ret;

	clos_config->epp = 0;
	clos_config->clos_prop_prio = info.prop_prio;
	clos_config->clos_min = info.min_freq_mhz;
	clos_config->clos_max = info.max_freq_mhz;
	clos_config->clos_desired = 0;

	debug_printf("cpu:%d clos:%d min:%d max:%d\n", id->cpu, clos,
		     clos_config->clos_min, clos_config->clos_max);

	return 0;
}

int tpmi_set_clos(struct isst_id *id, int clos,
		  struct isst_clos_config *clos_config)
{
	struct isst_clos_param info;
	int i, ret, saved_punit;

	info.get_set = 1;
	info.socket_id = id->pkg;
	info.power_domain_id = id->punit;
	info.clos = clos;
	info.prop_prio = clos_config->clos_prop_prio;

	info.min_freq_mhz = clos_config->clos_min;
	info.max_freq_mhz = clos_config->clos_max;

	if (info.min_freq_mhz <= 0xff)
		info.min_freq_mhz *= 100;
	if (info.max_freq_mhz <= 0xff)
		info.max_freq_mhz *= 100;

	saved_punit = id->punit;

	/* Set for all other dies also. This is per package setting */
	for (i = 0; i < MAX_PUNIT_PER_DIE; i++) {
		id->punit = i;
		if (isst_is_punit_valid(id)) {
			info.power_domain_id = i;
			ret = tpmi_process_ioctl(ISST_IF_CLOS_PARAM, &info);
			if (ret == -1) {
				id->punit = saved_punit;
				return ret;
			}
		}
	}

	id->punit = saved_punit;

	debug_printf("set cpu:%d clos:%d min:%d max:%d\n", id->cpu, clos,
		     clos_config->clos_min, clos_config->clos_max);

	return 0;
}

static int tpmi_clos_get_assoc_status(struct isst_id *id, int *clos_id)
{
	struct isst_if_clos_assoc_cmds assoc_cmds;
	int ret;

	assoc_cmds.cmd_count = 1;
	assoc_cmds.get_set = 0;
	assoc_cmds.punit_cpu_map = 1;
	assoc_cmds.assoc_info[0].logical_cpu = find_phy_core_num(id->cpu);
	assoc_cmds.assoc_info[0].socket_id = id->pkg;
	assoc_cmds.assoc_info[0].power_domain_id = id->punit;

	ret = tpmi_process_ioctl(ISST_IF_CLOS_ASSOC, &assoc_cmds);
	if (ret == -1)
		return ret;

	*clos_id = assoc_cmds.assoc_info[0].clos;

	return 0;
}

static int tpmi_clos_associate(struct isst_id *id, int clos_id)
{
	struct isst_if_clos_assoc_cmds assoc_cmds;
	int ret;

	assoc_cmds.cmd_count = 1;
	assoc_cmds.get_set = 1;
	assoc_cmds.punit_cpu_map = 1;
	assoc_cmds.assoc_info[0].logical_cpu = find_phy_core_num(id->cpu);
	assoc_cmds.assoc_info[0].clos = clos_id;
	assoc_cmds.assoc_info[0].socket_id = id->pkg;
	assoc_cmds.assoc_info[0].power_domain_id = id->punit;

	ret = tpmi_process_ioctl(ISST_IF_CLOS_ASSOC, &assoc_cmds);
	if (ret == -1)
		return ret;

	return 0;
}

static struct isst_platform_ops tpmi_ops = {
	.get_disp_freq_multiplier = tpmi_get_disp_freq_multiplier,
	.get_trl_max_levels = tpmi_get_trl_max_levels,
	.get_trl_level_name = tpmi_get_trl_level_name,
	.update_platform_param = tpmi_update_platform_param,
	.is_punit_valid = tpmi_is_punit_valid,
	.read_pm_config = tpmi_read_pm_config,
	.get_config_levels = tpmi_get_config_levels,
	.get_ctdp_control = tpmi_get_ctdp_control,
	.get_tdp_info = tpmi_get_tdp_info,
	.get_pwr_info = tpmi_get_pwr_info,
	.get_coremask_info = tpmi_get_coremask_info,
	.get_get_trl = tpmi_get_get_trl,
	.get_get_trls = tpmi_get_get_trls,
	.get_trl_bucket_info = tpmi_get_trl_bucket_info,
	.set_tdp_level = tpmi_set_tdp_level,
	.get_pbf_info = tpmi_get_pbf_info,
	.set_pbf_fact_status = tpmi_set_pbf_fact_status,
	.get_fact_info = tpmi_get_fact_info,
	.adjust_uncore_freq = tpmi_adjust_uncore_freq,
	.get_clos_information = tpmi_get_clos_information,
	.pm_qos_config = tpmi_pm_qos_config,
	.pm_get_clos = tpmi_pm_get_clos,
	.set_clos = tpmi_set_clos,
	.clos_get_assoc_status = tpmi_clos_get_assoc_status,
	.clos_associate = tpmi_clos_associate,
};

struct isst_platform_ops *tpmi_get_platform_ops(void)
{
	return &tpmi_ops;
}
