summaryrefslogtreecommitdiffstats
path: root/drivers/gpu/nvgpu/gp10b
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/gpu/nvgpu/gp10b')
-rw-r--r--drivers/gpu/nvgpu/gp10b/platform_gp10b_tegra.c47
1 files changed, 34 insertions, 13 deletions
diff --git a/drivers/gpu/nvgpu/gp10b/platform_gp10b_tegra.c b/drivers/gpu/nvgpu/gp10b/platform_gp10b_tegra.c
index 8cf6d5e8..5e5c7703 100644
--- a/drivers/gpu/nvgpu/gp10b/platform_gp10b_tegra.c
+++ b/drivers/gpu/nvgpu/gp10b/platform_gp10b_tegra.c
@@ -1,7 +1,7 @@
1/* 1/*
2 * GP10B Tegra Platform Interface 2 * GP10B Tegra Platform Interface
3 * 3 *
4 * Copyright (c) 2014-2016, NVIDIA CORPORATION. All rights reserved. 4 * Copyright (c) 2014-2017, NVIDIA CORPORATION. All rights reserved.
5 * 5 *
6 * This program is free software; you can redistribute it and/or modify it 6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms and conditions of the GNU General Public License, 7 * under the terms and conditions of the GNU General Public License,
@@ -35,8 +35,12 @@
35#include "gp10b_sysfs.h" 35#include "gp10b_sysfs.h"
36#include <linux/platform/tegra/emc_bwmgr.h> 36#include <linux/platform/tegra/emc_bwmgr.h>
37 37
38#define GP10B_MAX_SUPPORTED_FREQS 11 38/* Select every GP10B_FREQ_SELECT_STEP'th frequency from h/w table */
39static unsigned long gp10b_freq_table[GP10B_MAX_SUPPORTED_FREQS]; 39#define GP10B_FREQ_SELECT_STEP 8
40/* Max number of freq supported in h/w */
41#define GP10B_MAX_SUPPORTED_FREQS 120
42static unsigned long
43gp10b_freq_table[GP10B_MAX_SUPPORTED_FREQS / GP10B_FREQ_SELECT_STEP];
40 44
41#define TEGRA_GP10B_BW_PER_FREQ 64 45#define TEGRA_GP10B_BW_PER_FREQ 64
42#define TEGRA_DDR4_BW_PER_FREQ 16 46#define TEGRA_DDR4_BW_PER_FREQ 16
@@ -340,22 +344,39 @@ static int gp10b_clk_get_freqs(struct device *dev,
340 unsigned long **freqs, int *num_freqs) 344 unsigned long **freqs, int *num_freqs)
341{ 345{
342 struct gk20a_platform *platform = gk20a_get_platform(dev); 346 struct gk20a_platform *platform = gk20a_get_platform(dev);
343 unsigned long min_rate, max_rate, freq_step, rate; 347 unsigned long max_rate;
344 int i; 348 unsigned long new_rate = 0, prev_rate = 0;
349 int i = 0, freq_counter = 0;
345 350
346 min_rate = clk_round_rate(platform->clk[0], 0);
347 max_rate = clk_round_rate(platform->clk[0], (UINT_MAX - 1)); 351 max_rate = clk_round_rate(platform->clk[0], (UINT_MAX - 1));
348 freq_step = (max_rate - min_rate)/(GP10B_MAX_SUPPORTED_FREQS - 1);
349 gk20a_dbg_info("min rate: %ld max rate: %ld freq step %ld\n",
350 min_rate, max_rate, freq_step);
351 352
352 for (i = 0; i < GP10B_MAX_SUPPORTED_FREQS; i++) { 353 /*
353 rate = min_rate + i * freq_step; 354 * Walk the h/w frequency table and only select
354 gp10b_freq_table[i] = clk_round_rate(platform->clk[0], rate); 355 * GP10B_FREQ_SELECT_STEP'th frequencies and
356 * add MAX freq to last
357 */
358 for (; i < GP10B_MAX_SUPPORTED_FREQS; ++i) {
359 prev_rate = new_rate;
360 new_rate = clk_round_rate(platform->clk[0], prev_rate + 1);
361
362 if (i % GP10B_FREQ_SELECT_STEP == 0 ||
363 new_rate == max_rate) {
364 gp10b_freq_table[freq_counter++] = new_rate;
365
366 if (new_rate == max_rate)
367 break;
368 }
355 } 369 }
370
371 WARN_ON(i == GP10B_MAX_SUPPORTED_FREQS);
372
356 /* Fill freq table */ 373 /* Fill freq table */
357 *freqs = gp10b_freq_table; 374 *freqs = gp10b_freq_table;
358 *num_freqs = GP10B_MAX_SUPPORTED_FREQS; 375 *num_freqs = freq_counter;
376
377 gk20a_dbg_info("min rate: %ld max rate: %ld num_of_freq %d\n",
378 gp10b_freq_table[0], max_rate, *num_freqs);
379
359 return 0; 380 return 0;
360} 381}
361 382