diff options
author | Georgi Djakov <georgi.djakov@linaro.org> | 2019-08-09 08:13:23 -0400 |
---|---|---|
committer | Georgi Djakov <georgi.djakov@linaro.org> | 2019-08-13 16:02:44 -0400 |
commit | 127ab2cc5f19692efe422935267b9db0845b2b04 (patch) | |
tree | 104e5154b6166e0c87251ab2ad9948154b809e38 | |
parent | d45331b00ddb179e291766617259261c112db872 (diff) |
interconnect: Add support for path tags
Consumers may have use cases with different bandwidth requirements based
on the system or driver state. The consumer driver can append a specific
tag to the path and pass this information to the interconnect platform
driver to do the aggregation based on this state.
Introduce icc_set_tag() function that will allow the consumers to append
an optional tag to each path. The aggregation of these tagged paths is
platform specific.
Reviewed-by: Evan Green <evgreen@chromium.org>
Signed-off-by: Georgi Djakov <georgi.djakov@linaro.org>
-rw-r--r-- | drivers/interconnect/core.c | 24 | ||||
-rw-r--r-- | drivers/interconnect/qcom/sdm845.c | 2 | ||||
-rw-r--r-- | include/linux/interconnect-provider.h | 4 | ||||
-rw-r--r-- | include/linux/interconnect.h | 5 |
4 files changed, 31 insertions, 4 deletions
diff --git a/drivers/interconnect/core.c b/drivers/interconnect/core.c index 871eb4bc4efc..251354bb7fdc 100644 --- a/drivers/interconnect/core.c +++ b/drivers/interconnect/core.c | |||
@@ -29,6 +29,7 @@ static struct dentry *icc_debugfs_dir; | |||
29 | * @req_node: entry in list of requests for the particular @node | 29 | * @req_node: entry in list of requests for the particular @node |
30 | * @node: the interconnect node to which this constraint applies | 30 | * @node: the interconnect node to which this constraint applies |
31 | * @dev: reference to the device that sets the constraints | 31 | * @dev: reference to the device that sets the constraints |
32 | * @tag: path tag (optional) | ||
32 | * @avg_bw: an integer describing the average bandwidth in kBps | 33 | * @avg_bw: an integer describing the average bandwidth in kBps |
33 | * @peak_bw: an integer describing the peak bandwidth in kBps | 34 | * @peak_bw: an integer describing the peak bandwidth in kBps |
34 | */ | 35 | */ |
@@ -36,6 +37,7 @@ struct icc_req { | |||
36 | struct hlist_node req_node; | 37 | struct hlist_node req_node; |
37 | struct icc_node *node; | 38 | struct icc_node *node; |
38 | struct device *dev; | 39 | struct device *dev; |
40 | u32 tag; | ||
39 | u32 avg_bw; | 41 | u32 avg_bw; |
40 | u32 peak_bw; | 42 | u32 peak_bw; |
41 | }; | 43 | }; |
@@ -204,7 +206,7 @@ static int aggregate_requests(struct icc_node *node) | |||
204 | node->peak_bw = 0; | 206 | node->peak_bw = 0; |
205 | 207 | ||
206 | hlist_for_each_entry(r, &node->req_list, req_node) | 208 | hlist_for_each_entry(r, &node->req_list, req_node) |
207 | p->aggregate(node, r->avg_bw, r->peak_bw, | 209 | p->aggregate(node, r->tag, r->avg_bw, r->peak_bw, |
208 | &node->avg_bw, &node->peak_bw); | 210 | &node->avg_bw, &node->peak_bw); |
209 | 211 | ||
210 | return 0; | 212 | return 0; |
@@ -386,6 +388,26 @@ struct icc_path *of_icc_get(struct device *dev, const char *name) | |||
386 | EXPORT_SYMBOL_GPL(of_icc_get); | 388 | EXPORT_SYMBOL_GPL(of_icc_get); |
387 | 389 | ||
388 | /** | 390 | /** |
391 | * icc_set_tag() - set an optional tag on a path | ||
392 | * @path: the path we want to tag | ||
393 | * @tag: the tag value | ||
394 | * | ||
395 | * This function allows consumers to append a tag to the requests associated | ||
396 | * with a path, so that a different aggregation could be done based on this tag. | ||
397 | */ | ||
398 | void icc_set_tag(struct icc_path *path, u32 tag) | ||
399 | { | ||
400 | int i; | ||
401 | |||
402 | if (!path) | ||
403 | return; | ||
404 | |||
405 | for (i = 0; i < path->num_nodes; i++) | ||
406 | path->reqs[i].tag = tag; | ||
407 | } | ||
408 | EXPORT_SYMBOL_GPL(icc_set_tag); | ||
409 | |||
410 | /** | ||
389 | * icc_set_bw() - set bandwidth constraints on an interconnect path | 411 | * icc_set_bw() - set bandwidth constraints on an interconnect path |
390 | * @path: reference to the path returned by icc_get() | 412 | * @path: reference to the path returned by icc_get() |
391 | * @avg_bw: average bandwidth in kilobytes per second | 413 | * @avg_bw: average bandwidth in kilobytes per second |
diff --git a/drivers/interconnect/qcom/sdm845.c b/drivers/interconnect/qcom/sdm845.c index 4915b78da673..fb526004c82e 100644 --- a/drivers/interconnect/qcom/sdm845.c +++ b/drivers/interconnect/qcom/sdm845.c | |||
@@ -626,7 +626,7 @@ static void bcm_aggregate(struct qcom_icc_bcm *bcm) | |||
626 | bcm->dirty = false; | 626 | bcm->dirty = false; |
627 | } | 627 | } |
628 | 628 | ||
629 | static int qcom_icc_aggregate(struct icc_node *node, u32 avg_bw, | 629 | static int qcom_icc_aggregate(struct icc_node *node, u32 tag, u32 avg_bw, |
630 | u32 peak_bw, u32 *agg_avg, u32 *agg_peak) | 630 | u32 peak_bw, u32 *agg_avg, u32 *agg_peak) |
631 | { | 631 | { |
632 | size_t i; | 632 | size_t i; |
diff --git a/include/linux/interconnect-provider.h b/include/linux/interconnect-provider.h index 63caccadc2db..4ee19fd41568 100644 --- a/include/linux/interconnect-provider.h +++ b/include/linux/interconnect-provider.h | |||
@@ -45,8 +45,8 @@ struct icc_provider { | |||
45 | struct list_head provider_list; | 45 | struct list_head provider_list; |
46 | struct list_head nodes; | 46 | struct list_head nodes; |
47 | int (*set)(struct icc_node *src, struct icc_node *dst); | 47 | int (*set)(struct icc_node *src, struct icc_node *dst); |
48 | int (*aggregate)(struct icc_node *node, u32 avg_bw, u32 peak_bw, | 48 | int (*aggregate)(struct icc_node *node, u32 tag, u32 avg_bw, |
49 | u32 *agg_avg, u32 *agg_peak); | 49 | u32 peak_bw, u32 *agg_avg, u32 *agg_peak); |
50 | struct icc_node* (*xlate)(struct of_phandle_args *spec, void *data); | 50 | struct icc_node* (*xlate)(struct of_phandle_args *spec, void *data); |
51 | struct device *dev; | 51 | struct device *dev; |
52 | int users; | 52 | int users; |
diff --git a/include/linux/interconnect.h b/include/linux/interconnect.h index dc25864755ba..d70a914cba11 100644 --- a/include/linux/interconnect.h +++ b/include/linux/interconnect.h | |||
@@ -30,6 +30,7 @@ struct icc_path *icc_get(struct device *dev, const int src_id, | |||
30 | struct icc_path *of_icc_get(struct device *dev, const char *name); | 30 | struct icc_path *of_icc_get(struct device *dev, const char *name); |
31 | void icc_put(struct icc_path *path); | 31 | void icc_put(struct icc_path *path); |
32 | int icc_set_bw(struct icc_path *path, u32 avg_bw, u32 peak_bw); | 32 | int icc_set_bw(struct icc_path *path, u32 avg_bw, u32 peak_bw); |
33 | void icc_set_tag(struct icc_path *path, u32 tag); | ||
33 | 34 | ||
34 | #else | 35 | #else |
35 | 36 | ||
@@ -54,6 +55,10 @@ static inline int icc_set_bw(struct icc_path *path, u32 avg_bw, u32 peak_bw) | |||
54 | return 0; | 55 | return 0; |
55 | } | 56 | } |
56 | 57 | ||
58 | static inline void icc_set_tag(struct icc_path *path, u32 tag) | ||
59 | { | ||
60 | } | ||
61 | |||
57 | #endif /* CONFIG_INTERCONNECT */ | 62 | #endif /* CONFIG_INTERCONNECT */ |
58 | 63 | ||
59 | #endif /* __LINUX_INTERCONNECT_H */ | 64 | #endif /* __LINUX_INTERCONNECT_H */ |