scmi_protocol.h 9.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286
  1. // SPDX-License-Identifier: GPL-2.0
  2. /*
  3. * SCMI Message Protocol driver header
  4. *
  5. * Copyright (C) 2018 ARM Ltd.
  6. */
  7. #include <linux/device.h>
  8. #include <linux/types.h>
  9. #define SCMI_MAX_STR_SIZE 16
  10. #define SCMI_MAX_NUM_RATES 16
  11. /**
  12. * struct scmi_revision_info - version information structure
  13. *
  14. * @major_ver: Major ABI version. Change here implies risk of backward
  15. * compatibility break.
  16. * @minor_ver: Minor ABI version. Change here implies new feature addition,
  17. * or compatible change in ABI.
  18. * @num_protocols: Number of protocols that are implemented, excluding the
  19. * base protocol.
  20. * @num_agents: Number of agents in the system.
  21. * @impl_ver: A vendor-specific implementation version.
  22. * @vendor_id: A vendor identifier(Null terminated ASCII string)
  23. * @sub_vendor_id: A sub-vendor identifier(Null terminated ASCII string)
  24. */
  25. struct scmi_revision_info {
  26. u16 major_ver;
  27. u16 minor_ver;
  28. u8 num_protocols;
  29. u8 num_agents;
  30. u32 impl_ver;
  31. char vendor_id[SCMI_MAX_STR_SIZE];
  32. char sub_vendor_id[SCMI_MAX_STR_SIZE];
  33. };
  34. struct scmi_clock_info {
  35. char name[SCMI_MAX_STR_SIZE];
  36. bool rate_discrete;
  37. union {
  38. struct {
  39. int num_rates;
  40. u64 rates[SCMI_MAX_NUM_RATES];
  41. } list;
  42. struct {
  43. u64 min_rate;
  44. u64 max_rate;
  45. u64 step_size;
  46. } range;
  47. };
  48. };
  49. struct scmi_handle;
  50. /**
  51. * struct scmi_clk_ops - represents the various operations provided
  52. * by SCMI Clock Protocol
  53. *
  54. * @count_get: get the count of clocks provided by SCMI
  55. * @info_get: get the information of the specified clock
  56. * @rate_get: request the current clock rate of a clock
  57. * @rate_set: set the clock rate of a clock
  58. * @enable: enables the specified clock
  59. * @disable: disables the specified clock
  60. */
  61. struct scmi_clk_ops {
  62. int (*count_get)(const struct scmi_handle *handle);
  63. const struct scmi_clock_info *(*info_get)
  64. (const struct scmi_handle *handle, u32 clk_id);
  65. int (*rate_get)(const struct scmi_handle *handle, u32 clk_id,
  66. u64 *rate);
  67. int (*rate_set)(const struct scmi_handle *handle, u32 clk_id,
  68. u32 config, u64 rate);
  69. int (*enable)(const struct scmi_handle *handle, u32 clk_id);
  70. int (*disable)(const struct scmi_handle *handle, u32 clk_id);
  71. };
  72. /**
  73. * struct scmi_perf_ops - represents the various operations provided
  74. * by SCMI Performance Protocol
  75. *
  76. * @limits_set: sets limits on the performance level of a domain
  77. * @limits_get: gets limits on the performance level of a domain
  78. * @level_set: sets the performance level of a domain
  79. * @level_get: gets the performance level of a domain
  80. * @device_domain_id: gets the scmi domain id for a given device
  81. * @transition_latency_get: gets the DVFS transition latency for a given device
  82. * @device_opps_add: adds all the OPPs for a given device
  83. * @freq_set: sets the frequency for a given device using sustained frequency
  84. * to sustained performance level mapping
  85. * @freq_get: gets the frequency for a given device using sustained frequency
  86. * to sustained performance level mapping
  87. */
  88. struct scmi_perf_ops {
  89. int (*limits_set)(const struct scmi_handle *handle, u32 domain,
  90. u32 max_perf, u32 min_perf);
  91. int (*limits_get)(const struct scmi_handle *handle, u32 domain,
  92. u32 *max_perf, u32 *min_perf);
  93. int (*level_set)(const struct scmi_handle *handle, u32 domain,
  94. u32 level, bool poll);
  95. int (*level_get)(const struct scmi_handle *handle, u32 domain,
  96. u32 *level, bool poll);
  97. int (*device_domain_id)(struct device *dev);
  98. int (*transition_latency_get)(const struct scmi_handle *handle,
  99. struct device *dev);
  100. int (*device_opps_add)(const struct scmi_handle *handle,
  101. struct device *dev);
  102. int (*freq_set)(const struct scmi_handle *handle, u32 domain,
  103. unsigned long rate, bool poll);
  104. int (*freq_get)(const struct scmi_handle *handle, u32 domain,
  105. unsigned long *rate, bool poll);
  106. };
  107. /**
  108. * struct scmi_power_ops - represents the various operations provided
  109. * by SCMI Power Protocol
  110. *
  111. * @num_domains_get: get the count of power domains provided by SCMI
  112. * @name_get: gets the name of a power domain
  113. * @state_set: sets the power state of a power domain
  114. * @state_get: gets the power state of a power domain
  115. */
  116. struct scmi_power_ops {
  117. int (*num_domains_get)(const struct scmi_handle *handle);
  118. char *(*name_get)(const struct scmi_handle *handle, u32 domain);
  119. #define SCMI_POWER_STATE_TYPE_SHIFT 30
  120. #define SCMI_POWER_STATE_ID_MASK (BIT(28) - 1)
  121. #define SCMI_POWER_STATE_PARAM(type, id) \
  122. ((((type) & BIT(0)) << SCMI_POWER_STATE_TYPE_SHIFT) | \
  123. ((id) & SCMI_POWER_STATE_ID_MASK))
  124. #define SCMI_POWER_STATE_GENERIC_ON SCMI_POWER_STATE_PARAM(0, 0)
  125. #define SCMI_POWER_STATE_GENERIC_OFF SCMI_POWER_STATE_PARAM(1, 0)
  126. int (*state_set)(const struct scmi_handle *handle, u32 domain,
  127. u32 state);
  128. int (*state_get)(const struct scmi_handle *handle, u32 domain,
  129. u32 *state);
  130. };
  131. struct scmi_sensor_info {
  132. u32 id;
  133. u8 type;
  134. char name[SCMI_MAX_STR_SIZE];
  135. };
  136. /*
  137. * Partial list from Distributed Management Task Force (DMTF) specification:
  138. * DSP0249 (Platform Level Data Model specification)
  139. */
  140. enum scmi_sensor_class {
  141. NONE = 0x0,
  142. TEMPERATURE_C = 0x2,
  143. VOLTAGE = 0x5,
  144. CURRENT = 0x6,
  145. POWER = 0x7,
  146. ENERGY = 0x8,
  147. };
  148. /**
  149. * struct scmi_sensor_ops - represents the various operations provided
  150. * by SCMI Sensor Protocol
  151. *
  152. * @count_get: get the count of sensors provided by SCMI
  153. * @info_get: get the information of the specified sensor
  154. * @configuration_set: control notifications on cross-over events for
  155. * the trip-points
  156. * @trip_point_set: selects and configures a trip-point of interest
  157. * @reading_get: gets the current value of the sensor
  158. */
  159. struct scmi_sensor_ops {
  160. int (*count_get)(const struct scmi_handle *handle);
  161. const struct scmi_sensor_info *(*info_get)
  162. (const struct scmi_handle *handle, u32 sensor_id);
  163. int (*configuration_set)(const struct scmi_handle *handle,
  164. u32 sensor_id);
  165. int (*trip_point_set)(const struct scmi_handle *handle, u32 sensor_id,
  166. u8 trip_id, u64 trip_value);
  167. int (*reading_get)(const struct scmi_handle *handle, u32 sensor_id,
  168. bool async, u64 *value);
  169. };
  170. /**
  171. * struct scmi_handle - Handle returned to ARM SCMI clients for usage.
  172. *
  173. * @dev: pointer to the SCMI device
  174. * @version: pointer to the structure containing SCMI version information
  175. * @power_ops: pointer to set of power protocol operations
  176. * @perf_ops: pointer to set of performance protocol operations
  177. * @clk_ops: pointer to set of clock protocol operations
  178. * @sensor_ops: pointer to set of sensor protocol operations
  179. * @perf_priv: pointer to private data structure specific to performance
  180. * protocol(for internal use only)
  181. * @clk_priv: pointer to private data structure specific to clock
  182. * protocol(for internal use only)
  183. * @power_priv: pointer to private data structure specific to power
  184. * protocol(for internal use only)
  185. * @sensor_priv: pointer to private data structure specific to sensors
  186. * protocol(for internal use only)
  187. */
  188. struct scmi_handle {
  189. struct device *dev;
  190. struct scmi_revision_info *version;
  191. struct scmi_perf_ops *perf_ops;
  192. struct scmi_clk_ops *clk_ops;
  193. struct scmi_power_ops *power_ops;
  194. struct scmi_sensor_ops *sensor_ops;
  195. /* for protocol internal use */
  196. void *perf_priv;
  197. void *clk_priv;
  198. void *power_priv;
  199. void *sensor_priv;
  200. };
  201. enum scmi_std_protocol {
  202. SCMI_PROTOCOL_BASE = 0x10,
  203. SCMI_PROTOCOL_POWER = 0x11,
  204. SCMI_PROTOCOL_SYSTEM = 0x12,
  205. SCMI_PROTOCOL_PERF = 0x13,
  206. SCMI_PROTOCOL_CLOCK = 0x14,
  207. SCMI_PROTOCOL_SENSOR = 0x15,
  208. };
  209. struct scmi_device {
  210. u32 id;
  211. u8 protocol_id;
  212. struct device dev;
  213. struct scmi_handle *handle;
  214. };
  215. #define to_scmi_dev(d) container_of(d, struct scmi_device, dev)
  216. struct scmi_device *
  217. scmi_device_create(struct device_node *np, struct device *parent, int protocol);
  218. void scmi_device_destroy(struct scmi_device *scmi_dev);
  219. struct scmi_device_id {
  220. u8 protocol_id;
  221. };
  222. struct scmi_driver {
  223. const char *name;
  224. int (*probe)(struct scmi_device *sdev);
  225. void (*remove)(struct scmi_device *sdev);
  226. const struct scmi_device_id *id_table;
  227. struct device_driver driver;
  228. };
  229. #define to_scmi_driver(d) container_of(d, struct scmi_driver, driver)
  230. #ifdef CONFIG_ARM_SCMI_PROTOCOL
  231. int scmi_driver_register(struct scmi_driver *driver,
  232. struct module *owner, const char *mod_name);
  233. void scmi_driver_unregister(struct scmi_driver *driver);
  234. #else
  235. static inline int
  236. scmi_driver_register(struct scmi_driver *driver, struct module *owner,
  237. const char *mod_name)
  238. {
  239. return -EINVAL;
  240. }
  241. static inline void scmi_driver_unregister(struct scmi_driver *driver) {}
  242. #endif /* CONFIG_ARM_SCMI_PROTOCOL */
  243. #define scmi_register(driver) \
  244. scmi_driver_register(driver, THIS_MODULE, KBUILD_MODNAME)
  245. #define scmi_unregister(driver) \
  246. scmi_driver_unregister(driver)
  247. /**
  248. * module_scmi_driver() - Helper macro for registering a scmi driver
  249. * @__scmi_driver: scmi_driver structure
  250. *
  251. * Helper macro for scmi drivers to set up proper module init / exit
  252. * functions. Replaces module_init() and module_exit() and keeps people from
  253. * printing pointless things to the kernel log when their driver is loaded.
  254. */
  255. #define module_scmi_driver(__scmi_driver) \
  256. module_driver(__scmi_driver, scmi_register, scmi_unregister)
  257. typedef int (*scmi_prot_init_fn_t)(struct scmi_handle *);
  258. int scmi_protocol_register(int protocol_id, scmi_prot_init_fn_t fn);
  259. void scmi_protocol_unregister(int protocol_id);