Loading Documentation/devicetree/bindings/gpu/adreno-pwrlevels.txt +4 −0 Original line number Diff line number Diff line Loading @@ -17,6 +17,10 @@ Properties: - qcom,gpu-pwrlevel: A single powerlevel - qcom,ca-target-pwrlevel: This value indicates which qcom,gpu-pwrlevel to jump on in case of context aware power level jump. Properties: - reg: Index of the powerlevel (0 = highest perf) - qcom,gpu-freq GPU frequency for the powerlevel (in Hz) Loading Documentation/devicetree/bindings/gpu/adreno.txt +19 −0 Original line number Diff line number Diff line Loading @@ -167,6 +167,15 @@ Optional Properties: Specify the size of snapshot in bytes. This will override snapshot size defined in the driver code. - qcom,enable-ca-jump: Boolean. Enables use of context aware DCVS - qcom,ca-busy-penalty: This property represents the time in microseconds required to initiate context aware power level jump. - qcom,ca-target-pwrlevel: This value indicates which qcom,gpu-pwrlevel to jump on in case of context aware power level jump. - qcom,gpu-qdss-stm: <baseAddr size> baseAddr - base address of the gpu channels in the qdss stm memory region Loading Loading @@ -323,6 +332,15 @@ Example of A330 GPU in MSM8916: coresight-child-list = <&funnel_in0>; coresight-child-ports = <5>; /* Enable context aware freq. scaling */ qcom,enable-ca-jump; /* Context aware jump busy penalty in us */ qcom,ca-busy-penalty = <12000>; /* Context aware jump target power level */ qcom,ca-target-pwrlevel = <1>; qcom,soc-hw-revisions { #address-cells = <1>; #size-cells = <0>; Loading Loading @@ -389,6 +407,7 @@ Example of A330 GPU in MSM8916: #size-cells = <0>; qcom,speed-bin = <0>; qcom,ca-target-pwrlevel = <1>; qcom,gpu-pwrlevel@0 { reg = <0>; Loading drivers/gpu/msm/adreno.c +55 −0 Original line number Diff line number Diff line Loading @@ -849,6 +849,58 @@ static const struct of_device_id adreno_match_table[] = { {} }; static void adreno_of_get_ca_target_pwrlevel(struct adreno_device *adreno_dev, struct device_node *node) { struct kgsl_device *device = KGSL_DEVICE(adreno_dev); unsigned int ca_target_pwrlevel = 1; of_property_read_u32(node, "qcom,ca-target-pwrlevel", &ca_target_pwrlevel); if (ca_target_pwrlevel > device->pwrctrl.num_pwrlevels - 2) ca_target_pwrlevel = 1; device->pwrscale.ctxt_aware_target_pwrlevel = ca_target_pwrlevel; } static void adreno_of_get_ca_aware_properties(struct adreno_device *adreno_dev, struct device_node *parent) { struct kgsl_device *device = KGSL_DEVICE(adreno_dev); struct kgsl_pwrscale *pwrscale = &device->pwrscale; struct device_node *node, *child; unsigned int bin = 0; pwrscale->ctxt_aware_enable = of_property_read_bool(parent, "qcom,enable-ca-jump"); if (pwrscale->ctxt_aware_enable) { if (of_property_read_u32(parent, "qcom,ca-busy-penalty", &pwrscale->ctxt_aware_busy_penalty)) pwrscale->ctxt_aware_busy_penalty = 12000; node = of_find_node_by_name(parent, "qcom,gpu-pwrlevel-bins"); if (node == NULL) { adreno_of_get_ca_target_pwrlevel(adreno_dev, parent); return; } for_each_child_of_node(node, child) { if (of_property_read_u32(child, "qcom,speed-bin", &bin)) continue; if (bin == adreno_dev->speed_bin) { adreno_of_get_ca_target_pwrlevel(adreno_dev, child); return; } } pwrscale->ctxt_aware_target_pwrlevel = 1; } } static int adreno_of_parse_pwrlevels(struct adreno_device *adreno_dev, struct device_node *node) { Loading Loading @@ -1018,6 +1070,9 @@ static int adreno_of_get_power(struct adreno_device *adreno_dev, if (adreno_of_get_pwrlevels(adreno_dev, node)) return -EINVAL; /* Get context aware DCVS properties */ adreno_of_get_ca_aware_properties(adreno_dev, node); /* get pm-qos-active-latency, set it to default if not found */ if (of_property_read_u32(node, "qcom,pm-qos-active-latency", &device->pwrctrl.pm_qos_active_latency)) Loading drivers/gpu/msm/kgsl_pwrscale.c +6 −18 Original line number Diff line number Diff line Loading @@ -985,24 +985,12 @@ int kgsl_pwrscale_init(struct device *dev, const char *governor) data->disable_busy_time_burst = of_property_read_bool( device->pdev->dev.of_node, "qcom,disable-busy-time-burst"); data->ctxt_aware_enable = of_property_read_bool(device->pdev->dev.of_node, "qcom,enable-ca-jump"); if (data->ctxt_aware_enable) { if (of_property_read_u32(device->pdev->dev.of_node, "qcom,ca-target-pwrlevel", &data->bin.ctxt_aware_target_pwrlevel)) data->bin.ctxt_aware_target_pwrlevel = 1; if ((data->bin.ctxt_aware_target_pwrlevel > pwr->num_pwrlevels)) data->bin.ctxt_aware_target_pwrlevel = 1; if (of_property_read_u32(device->pdev->dev.of_node, "qcom,ca-busy-penalty", &data->bin.ctxt_aware_busy_penalty)) data->bin.ctxt_aware_busy_penalty = 12000; if (pwrscale->ctxt_aware_enable) { data->ctxt_aware_enable = pwrscale->ctxt_aware_enable; data->bin.ctxt_aware_target_pwrlevel = pwrscale->ctxt_aware_target_pwrlevel; data->bin.ctxt_aware_busy_penalty = pwrscale->ctxt_aware_busy_penalty; } if (of_property_read_bool(device->pdev->dev.of_node, Loading drivers/gpu/msm/kgsl_pwrscale.h +8 −0 Original line number Diff line number Diff line Loading @@ -91,6 +91,11 @@ struct kgsl_pwr_history { * @popp_level - Current level of POPP mitigation * @popp_state - Control state for POPP, on/off, recently pushed, etc * @cooling_dev - Thermal cooling device handle * @ctxt_aware_enable - Whether or not ctxt aware DCVS feature is enabled * @ctxt_aware_busy_penalty - The time in microseconds required to trigger * ctxt aware power level jump * @ctxt_aware_target_pwrlevel - pwrlevel to jump on in case of ctxt aware * power level jump */ struct kgsl_pwrscale { struct devfreq *devfreqptr; Loading @@ -113,6 +118,9 @@ struct kgsl_pwrscale { int popp_level; unsigned long popp_state; struct thermal_cooling_device *cooling_dev; bool ctxt_aware_enable; unsigned int ctxt_aware_target_pwrlevel; unsigned int ctxt_aware_busy_penalty; }; int kgsl_pwrscale_init(struct device *dev, const char *governor); Loading Loading
Documentation/devicetree/bindings/gpu/adreno-pwrlevels.txt +4 −0 Original line number Diff line number Diff line Loading @@ -17,6 +17,10 @@ Properties: - qcom,gpu-pwrlevel: A single powerlevel - qcom,ca-target-pwrlevel: This value indicates which qcom,gpu-pwrlevel to jump on in case of context aware power level jump. Properties: - reg: Index of the powerlevel (0 = highest perf) - qcom,gpu-freq GPU frequency for the powerlevel (in Hz) Loading
Documentation/devicetree/bindings/gpu/adreno.txt +19 −0 Original line number Diff line number Diff line Loading @@ -167,6 +167,15 @@ Optional Properties: Specify the size of snapshot in bytes. This will override snapshot size defined in the driver code. - qcom,enable-ca-jump: Boolean. Enables use of context aware DCVS - qcom,ca-busy-penalty: This property represents the time in microseconds required to initiate context aware power level jump. - qcom,ca-target-pwrlevel: This value indicates which qcom,gpu-pwrlevel to jump on in case of context aware power level jump. - qcom,gpu-qdss-stm: <baseAddr size> baseAddr - base address of the gpu channels in the qdss stm memory region Loading Loading @@ -323,6 +332,15 @@ Example of A330 GPU in MSM8916: coresight-child-list = <&funnel_in0>; coresight-child-ports = <5>; /* Enable context aware freq. scaling */ qcom,enable-ca-jump; /* Context aware jump busy penalty in us */ qcom,ca-busy-penalty = <12000>; /* Context aware jump target power level */ qcom,ca-target-pwrlevel = <1>; qcom,soc-hw-revisions { #address-cells = <1>; #size-cells = <0>; Loading Loading @@ -389,6 +407,7 @@ Example of A330 GPU in MSM8916: #size-cells = <0>; qcom,speed-bin = <0>; qcom,ca-target-pwrlevel = <1>; qcom,gpu-pwrlevel@0 { reg = <0>; Loading
drivers/gpu/msm/adreno.c +55 −0 Original line number Diff line number Diff line Loading @@ -849,6 +849,58 @@ static const struct of_device_id adreno_match_table[] = { {} }; static void adreno_of_get_ca_target_pwrlevel(struct adreno_device *adreno_dev, struct device_node *node) { struct kgsl_device *device = KGSL_DEVICE(adreno_dev); unsigned int ca_target_pwrlevel = 1; of_property_read_u32(node, "qcom,ca-target-pwrlevel", &ca_target_pwrlevel); if (ca_target_pwrlevel > device->pwrctrl.num_pwrlevels - 2) ca_target_pwrlevel = 1; device->pwrscale.ctxt_aware_target_pwrlevel = ca_target_pwrlevel; } static void adreno_of_get_ca_aware_properties(struct adreno_device *adreno_dev, struct device_node *parent) { struct kgsl_device *device = KGSL_DEVICE(adreno_dev); struct kgsl_pwrscale *pwrscale = &device->pwrscale; struct device_node *node, *child; unsigned int bin = 0; pwrscale->ctxt_aware_enable = of_property_read_bool(parent, "qcom,enable-ca-jump"); if (pwrscale->ctxt_aware_enable) { if (of_property_read_u32(parent, "qcom,ca-busy-penalty", &pwrscale->ctxt_aware_busy_penalty)) pwrscale->ctxt_aware_busy_penalty = 12000; node = of_find_node_by_name(parent, "qcom,gpu-pwrlevel-bins"); if (node == NULL) { adreno_of_get_ca_target_pwrlevel(adreno_dev, parent); return; } for_each_child_of_node(node, child) { if (of_property_read_u32(child, "qcom,speed-bin", &bin)) continue; if (bin == adreno_dev->speed_bin) { adreno_of_get_ca_target_pwrlevel(adreno_dev, child); return; } } pwrscale->ctxt_aware_target_pwrlevel = 1; } } static int adreno_of_parse_pwrlevels(struct adreno_device *adreno_dev, struct device_node *node) { Loading Loading @@ -1018,6 +1070,9 @@ static int adreno_of_get_power(struct adreno_device *adreno_dev, if (adreno_of_get_pwrlevels(adreno_dev, node)) return -EINVAL; /* Get context aware DCVS properties */ adreno_of_get_ca_aware_properties(adreno_dev, node); /* get pm-qos-active-latency, set it to default if not found */ if (of_property_read_u32(node, "qcom,pm-qos-active-latency", &device->pwrctrl.pm_qos_active_latency)) Loading
drivers/gpu/msm/kgsl_pwrscale.c +6 −18 Original line number Diff line number Diff line Loading @@ -985,24 +985,12 @@ int kgsl_pwrscale_init(struct device *dev, const char *governor) data->disable_busy_time_burst = of_property_read_bool( device->pdev->dev.of_node, "qcom,disable-busy-time-burst"); data->ctxt_aware_enable = of_property_read_bool(device->pdev->dev.of_node, "qcom,enable-ca-jump"); if (data->ctxt_aware_enable) { if (of_property_read_u32(device->pdev->dev.of_node, "qcom,ca-target-pwrlevel", &data->bin.ctxt_aware_target_pwrlevel)) data->bin.ctxt_aware_target_pwrlevel = 1; if ((data->bin.ctxt_aware_target_pwrlevel > pwr->num_pwrlevels)) data->bin.ctxt_aware_target_pwrlevel = 1; if (of_property_read_u32(device->pdev->dev.of_node, "qcom,ca-busy-penalty", &data->bin.ctxt_aware_busy_penalty)) data->bin.ctxt_aware_busy_penalty = 12000; if (pwrscale->ctxt_aware_enable) { data->ctxt_aware_enable = pwrscale->ctxt_aware_enable; data->bin.ctxt_aware_target_pwrlevel = pwrscale->ctxt_aware_target_pwrlevel; data->bin.ctxt_aware_busy_penalty = pwrscale->ctxt_aware_busy_penalty; } if (of_property_read_bool(device->pdev->dev.of_node, Loading
drivers/gpu/msm/kgsl_pwrscale.h +8 −0 Original line number Diff line number Diff line Loading @@ -91,6 +91,11 @@ struct kgsl_pwr_history { * @popp_level - Current level of POPP mitigation * @popp_state - Control state for POPP, on/off, recently pushed, etc * @cooling_dev - Thermal cooling device handle * @ctxt_aware_enable - Whether or not ctxt aware DCVS feature is enabled * @ctxt_aware_busy_penalty - The time in microseconds required to trigger * ctxt aware power level jump * @ctxt_aware_target_pwrlevel - pwrlevel to jump on in case of ctxt aware * power level jump */ struct kgsl_pwrscale { struct devfreq *devfreqptr; Loading @@ -113,6 +118,9 @@ struct kgsl_pwrscale { int popp_level; unsigned long popp_state; struct thermal_cooling_device *cooling_dev; bool ctxt_aware_enable; unsigned int ctxt_aware_target_pwrlevel; unsigned int ctxt_aware_busy_penalty; }; int kgsl_pwrscale_init(struct device *dev, const char *governor); Loading