示例#1
0
static void nvhost_scale_notify(struct platform_device *pdev, bool busy)
{
	struct nvhost_device_data *pdata = platform_get_drvdata(pdev);
	struct nvhost_device_profile *profile = pdata->power_profile;
	struct devfreq *devfreq = pdata->power_manager;

	/* Is the device profile initialised? */
	if (!profile)
		return;

	/* inform edp about new constraint */
	if (pdata->gpu_edp_device) {
		u32 avg = 0;
		actmon_op().read_avg_norm(profile->actmon, &avg);
		BUG();
		/* the next line passes a bogus frequency */
		tegra_edp_notify_gpu_load(avg, 0);
	}

	/* If defreq is disabled, set the freq to max or min */
	if (!devfreq) {
		unsigned long freq = busy ? UINT_MAX : 0;
		nvhost_scale_target(&pdev->dev, &freq, 0);
		return;
	}

	mutex_lock(&devfreq->lock);
	if (!profile->actmon)
		update_load_estimate(profile, busy);
	profile->dev_stat.busy = busy;
	update_devfreq(devfreq);
	mutex_unlock(&devfreq->lock);
}
示例#2
0
void nvhost_scale3d_callback(struct nvhost_device_profile *profile,
			     unsigned long freq)
{
	struct nvhost_gr3d_params *gr3d_params = profile->private_data;
	struct nvhost_device_data *pdata = platform_get_drvdata(profile->pdev);
	struct nvhost_emc_params *emc_params = &gr3d_params->emc_params;
	long hz;
	long after;

	/* Set EMC clockrate */
	after = (long) clk_get_rate(clk(profile, gr3d_params->clk_3d));
	hz = nvhost_scale3d_get_emc_rate(emc_params, after);
	nvhost_module_set_devfreq_rate(profile->pdev, gr3d_params->clk_3d_emc,
				       hz);

	if (pdata->gpu_edp_device) {
		u32 avg = 0;
		actmon_op().read_avg_norm(profile->actmon, &avg);
		tegra_edp_notify_gpu_load(avg);
	}
}
static int nvhost_scale3d_get_dev_status(struct device *d,
		      struct devfreq_dev_status *stat)
{
	struct platform_device *dev = to_platform_device(d);
	struct nvhost_master *host_master = nvhost_get_host(dev);
	struct nvhost_devfreq_ext_stat *ext_stat =
		power_profile.dev_stat->private_data;
	u32 avg = 0;
	ktime_t t;

	/* Make sure there are correct values for the current frequency */
	power_profile.dev_stat->current_frequency =
		clk_get_rate(power_profile.clk_3d);

	/* Copy the contents of the current device status */
	ext_stat->busy = power_profile.last_event_type;
	*stat = *power_profile.dev_stat;

	/* Read and scale AVG. AVG is scaled to interval 0-dt, where dt
	 * is the last time it was read. (this is really clumsy, but the
	 * governor uses internally time differences) */
	actmon_op().read_avg_norm(host_master, &avg);
	t = ktime_get();
	stat->total_time = ktime_us_delta(t, power_profile.last_request_time);
	stat->busy_time = (avg * stat->total_time) / 1000;
	power_profile.last_request_time = t;

	/* Finally, clear out the local values */
	power_profile.dev_stat->total_time = 0;
	power_profile.dev_stat->busy_time = 0;
	power_profile.last_event_type = DEVICE_UNKNOWN;

	tegra_edp_notify_gpu_load(avg);

	return 0;
}