/*
* drivers/misc/tegra-profiler/power_clk.c
*
- * Copyright (c) 2015, NVIDIA CORPORATION. All rights reserved.
+ * Copyright (c) 2013-2015, NVIDIA CORPORATION. All rights reserved.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
int nr;
struct power_clk_data data[POWER_CLK_MAX_VALUES];
- unsigned long long counter;
atomic_t active;
-
struct mutex lock;
};
{
mutex_lock(&s->lock);
- if (!is_data_changed(s)) {
- mutex_unlock(&s->lock);
- return;
- }
+ if (!is_data_changed(s))
+ goto out_unlock;
pr_debug("cpu: %lu/%lu/%lu/%lu\n",
power_ctx.cpu.data[0].value,
mutex_unlock(&s->lock);
make_sample();
+ return;
+
+out_unlock:
+ mutex_unlock(&s->lock);
}
static void
default:
pr_err_once("error: invalid power_clk type\n");
- return;
+ break;
}
- s->counter++;
mutex_unlock(&s->lock);
}
mutex_lock(&s->lock);
- if (!atomic_read(&s->active)) {
- mutex_unlock(&s->lock);
- return;
- }
+ if (!atomic_read(&s->active))
+ goto out_unlock;
cpu = freq->cpu;
cpufreq = freq->new;
- if (cpu >= POWER_CLK_MAX_VALUES) {
+ pr_debug("cpu: %d, cpufreq: %d\n", cpu, cpufreq);
+
+ if (cpu >= s->nr) {
pr_err_once("error: cpu id: %d\n", cpu);
- mutex_unlock(&s->lock);
- return;
+ goto out_unlock;
}
s->data[cpu].value = cpufreq;
cpu, freq->old, cpufreq);
mutex_unlock(&s->lock);
-
check_source(s);
+ return;
+
+out_unlock:
+ mutex_unlock(&s->lock);
}
static int
if (!atomic_read(&s->active))
return 0;
+ pr_debug("action: %lu\n", action);
+
if (action == CPUFREQ_POSTCHANGE ||
action == CPUFREQ_RESUMECHANGE) {
freq = hcpu;
s->data[i].value = 0;
s->data[i].prev = 0;
}
- atomic_set(s, 0);
mutex_unlock(&s->lock);
}
s->type = type;
s->nb.notifier_call = notifier;
s->nr = min_t(int, nr_values, POWER_CLK_MAX_VALUES);
-
+ atomic_set(&s->active, 0);
mutex_init(&s->lock);
+
reset_data(s);
}
add_timer(timer);
}
+static void
+read_all_sources_work_func(struct work_struct *work)
+{
+ int cpu_id;
+
+ for_each_possible_cpu(cpu_id)
+ read_source(&power_ctx.cpu, cpu_id);
+
+ read_source(&power_ctx.gpu, -1);
+ read_source(&power_ctx.emc, -1);
+
+ check_clks();
+}
+
+static DECLARE_WORK(read_all_sources_work, read_all_sources_work_func);
+
int quadd_power_clk_start(void)
{
struct power_clk_source *s;
add_timer(timer);
}
+ schedule_work(&read_all_sources_work);
+
return 0;
}
mutex_unlock(&s->lock);
s = &power_ctx.cpu;
- mutex_unlock(&s->lock);
- atomic_set(&s->active, 0);
mutex_lock(&s->lock);
+ atomic_set(&s->active, 0);
+ mutex_unlock(&s->lock);
pr_info("power_clk: stop\n");
}