linux/drivers/powercap/arm_scmi_powercap.c

// SPDX-License-Identifier: GPL-2.0
/*
 * SCMI Powercap support.
 *
 * Copyright (C) 2022 ARM Ltd.
 */

#include <linux/device.h>
#include <linux/math.h>
#include <linux/limits.h>
#include <linux/list.h>
#include <linux/module.h>
#include <linux/powercap.h>
#include <linux/scmi_protocol.h>
#include <linux/slab.h>

#define to_scmi_powercap_zone(z)

static const struct scmi_powercap_proto_ops *powercap_ops;

struct scmi_powercap_zone {};

struct scmi_powercap_root {};

static struct powercap_control_type *scmi_top_pcntrl;

static int scmi_powercap_zone_release(struct powercap_zone *pz)
{}

static int scmi_powercap_get_max_power_range_uw(struct powercap_zone *pz,
						u64 *max_power_range_uw)
{}

static int scmi_powercap_get_power_uw(struct powercap_zone *pz,
				      u64 *power_uw)
{}

static int scmi_powercap_zone_enable_set(struct powercap_zone *pz, bool mode)
{}

static int scmi_powercap_zone_enable_get(struct powercap_zone *pz, bool *mode)
{}

static const struct powercap_zone_ops zone_ops =;

static void scmi_powercap_normalize_cap(const struct scmi_powercap_zone *spz,
					u64 power_limit_uw, u32 *norm)
{}

static int scmi_powercap_set_power_limit_uw(struct powercap_zone *pz, int cid,
					    u64 power_uw)
{}

static int scmi_powercap_get_power_limit_uw(struct powercap_zone *pz, int cid,
					    u64 *power_limit_uw)
{}

static void scmi_powercap_normalize_time(const struct scmi_powercap_zone *spz,
					 u64 time_us, u32 *norm)
{}

static int scmi_powercap_set_time_window_us(struct powercap_zone *pz, int cid,
					    u64 time_window_us)
{}

static int scmi_powercap_get_time_window_us(struct powercap_zone *pz, int cid,
					    u64 *time_window_us)
{}

static int scmi_powercap_get_max_power_uw(struct powercap_zone *pz, int cid,
					  u64 *max_power_uw)
{}

static int scmi_powercap_get_min_power_uw(struct powercap_zone *pz, int cid,
					  u64 *min_power_uw)
{}

static int scmi_powercap_get_max_time_window_us(struct powercap_zone *pz,
						int cid, u64 *time_window_us)
{}

static int scmi_powercap_get_min_time_window_us(struct powercap_zone *pz,
						int cid, u64 *time_window_us)
{}

static const char *scmi_powercap_get_name(struct powercap_zone *pz, int cid)
{}

static const struct powercap_zone_constraint_ops constraint_ops  =;

static void scmi_powercap_unregister_all_zones(struct scmi_powercap_root *pr)
{}

static inline unsigned int
scmi_powercap_get_zone_height(struct scmi_powercap_zone *spz)
{}

static inline struct scmi_powercap_zone *
scmi_powercap_get_parent_zone(struct scmi_powercap_zone *spz)
{}

static int scmi_powercap_register_zone(struct scmi_powercap_root *pr,
				       struct scmi_powercap_zone *spz,
				       struct scmi_powercap_zone *parent)
{}

/**
 * scmi_zones_register- Register SCMI powercap zones starting from parent zones
 *
 * @dev: A reference to the SCMI device
 * @pr: A reference to the root powercap zones descriptors
 *
 * When registering SCMI powercap zones with the powercap framework we should
 * take care to always register zones starting from the root ones and to
 * deregister starting from the leaves.
 *
 * Unfortunately we cannot assume that the array of available SCMI powercap
 * zones provided by the SCMI platform firmware is built to comply with such
 * requirement.
 *
 * This function, given the set of SCMI powercap zones to register, takes care
 * to walk the SCMI powercap zones trees up to the root registering any
 * unregistered parent zone before registering the child zones; at the same
 * time each registered-zone height in such a tree is accounted for and each
 * zone, once registered, is stored in the @registered_zones array that is
 * indexed by zone height: this way will be trivial, at unregister time, to walk
 * the @registered_zones array backward and unregister all the zones starting
 * from the leaves, removing children zones before parents.
 *
 * While doing this, we prune away any zone marked as invalid (like the ones
 * sporting an SCMI abstract power scale) as long as they are positioned as
 * leaves in the SCMI powercap zones hierarchy: any non-leaf invalid zone causes
 * the entire process to fail since we cannot assume the correctness of an SCMI
 * powercap zones hierarchy if some of the internal nodes are missing.
 *
 * Note that the array of SCMI powercap zones as returned by the SCMI platform
 * is known to be sane, i.e. zones relationships have been validated at the
 * protocol layer.
 *
 * Return: 0 on Success
 */
static int scmi_zones_register(struct device *dev,
			       struct scmi_powercap_root *pr)
{}

static int scmi_powercap_probe(struct scmi_device *sdev)
{}

static void scmi_powercap_remove(struct scmi_device *sdev)
{}

static const struct scmi_device_id scmi_id_table[] =;
MODULE_DEVICE_TABLE(scmi, scmi_id_table);

static struct scmi_driver scmi_powercap_driver =;

static int __init scmi_powercap_init(void)
{}
module_init();

static void __exit scmi_powercap_exit(void)
{}
module_exit(scmi_powercap_exit);

MODULE_AUTHOR();
MODULE_DESCRIPTION();
MODULE_LICENSE();