Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-or-later
0002 /*
0003  *  Copyright (C) 2002,2003 Intrinsyc Software
0004  *
0005  * History:
0006  *   31-Jul-2002 : Initial version [FB]
0007  *   29-Jan-2003 : added PXA255 support [FB]
0008  *   20-Apr-2003 : ported to v2.5 (Dustin McIntire, Sensoria Corp.)
0009  *
0010  * Note:
0011  *   This driver may change the memory bus clock rate, but will not do any
0012  *   platform specific access timing changes... for example if you have flash
0013  *   memory connected to CS0, you will need to register a platform specific
0014  *   notifier which will adjust the memory access strobes to maintain a
0015  *   minimum strobe width.
0016  */
0017 
0018 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
0019 
0020 #include <linux/kernel.h>
0021 #include <linux/module.h>
0022 #include <linux/sched.h>
0023 #include <linux/init.h>
0024 #include <linux/cpufreq.h>
0025 #include <linux/err.h>
0026 #include <linux/regulator/consumer.h>
0027 #include <linux/soc/pxa/cpu.h>
0028 #include <linux/io.h>
0029 
0030 #ifdef DEBUG
0031 static unsigned int freq_debug;
0032 module_param(freq_debug, uint, 0);
0033 MODULE_PARM_DESC(freq_debug, "Set the debug messages to on=1/off=0");
0034 #else
0035 #define freq_debug  0
0036 #endif
0037 
0038 static struct regulator *vcc_core;
0039 
0040 static unsigned int pxa27x_maxfreq;
0041 module_param(pxa27x_maxfreq, uint, 0);
0042 MODULE_PARM_DESC(pxa27x_maxfreq, "Set the pxa27x maxfreq in MHz"
0043          "(typically 624=>pxa270, 416=>pxa271, 520=>pxa272)");
0044 
0045 struct pxa_cpufreq_data {
0046     struct clk *clk_core;
0047 };
0048 static struct pxa_cpufreq_data  pxa_cpufreq_data;
0049 
0050 struct pxa_freqs {
0051     unsigned int khz;
0052     int vmin;
0053     int vmax;
0054 };
0055 
0056 /*
0057  * PXA255 definitions
0058  */
0059 static const struct pxa_freqs pxa255_run_freqs[] =
0060 {
0061     /* CPU   MEMBUS        run  turbo PXbus SDRAM */
0062     { 99500, -1, -1},   /*  99,   99,   50,   50  */
0063     {132700, -1, -1},   /* 133,  133,   66,   66  */
0064     {199100, -1, -1},   /* 199,  199,   99,   99  */
0065     {265400, -1, -1},   /* 265,  265,  133,   66  */
0066     {331800, -1, -1},   /* 331,  331,  166,   83  */
0067     {398100, -1, -1},   /* 398,  398,  196,   99  */
0068 };
0069 
0070 /* Use the turbo mode frequencies for the CPUFREQ_POLICY_POWERSAVE policy */
0071 static const struct pxa_freqs pxa255_turbo_freqs[] =
0072 {
0073     /* CPU             run  turbo PXbus SDRAM */
0074     { 99500, -1, -1},   /*  99,   99,   50,   50  */
0075     {199100, -1, -1},   /*  99,  199,   50,   99  */
0076     {298500, -1, -1},   /*  99,  287,   50,   99  */
0077     {298600, -1, -1},   /* 199,  287,   99,   99  */
0078     {398100, -1, -1},   /* 199,  398,   99,   99  */
0079 };
0080 
0081 #define NUM_PXA25x_RUN_FREQS ARRAY_SIZE(pxa255_run_freqs)
0082 #define NUM_PXA25x_TURBO_FREQS ARRAY_SIZE(pxa255_turbo_freqs)
0083 
0084 static struct cpufreq_frequency_table
0085     pxa255_run_freq_table[NUM_PXA25x_RUN_FREQS+1];
0086 static struct cpufreq_frequency_table
0087     pxa255_turbo_freq_table[NUM_PXA25x_TURBO_FREQS+1];
0088 
0089 static unsigned int pxa255_turbo_table;
0090 module_param(pxa255_turbo_table, uint, 0);
0091 MODULE_PARM_DESC(pxa255_turbo_table, "Selects the frequency table (0 = run table, !0 = turbo table)");
0092 
0093 static struct pxa_freqs pxa27x_freqs[] = {
0094     {104000,  900000, 1705000 },
0095     {156000, 1000000, 1705000 },
0096     {208000, 1180000, 1705000 },
0097     {312000, 1250000, 1705000 },
0098     {416000, 1350000, 1705000 },
0099     {520000, 1450000, 1705000 },
0100     {624000, 1550000, 1705000 }
0101 };
0102 
0103 #define NUM_PXA27x_FREQS ARRAY_SIZE(pxa27x_freqs)
0104 static struct cpufreq_frequency_table
0105     pxa27x_freq_table[NUM_PXA27x_FREQS+1];
0106 
0107 #ifdef CONFIG_REGULATOR
0108 
0109 static int pxa_cpufreq_change_voltage(const struct pxa_freqs *pxa_freq)
0110 {
0111     int ret = 0;
0112     int vmin, vmax;
0113 
0114     if (!cpu_is_pxa27x())
0115         return 0;
0116 
0117     vmin = pxa_freq->vmin;
0118     vmax = pxa_freq->vmax;
0119     if ((vmin == -1) || (vmax == -1))
0120         return 0;
0121 
0122     ret = regulator_set_voltage(vcc_core, vmin, vmax);
0123     if (ret)
0124         pr_err("Failed to set vcc_core in [%dmV..%dmV]\n", vmin, vmax);
0125     return ret;
0126 }
0127 
0128 static void pxa_cpufreq_init_voltages(void)
0129 {
0130     vcc_core = regulator_get(NULL, "vcc_core");
0131     if (IS_ERR(vcc_core)) {
0132         pr_info("Didn't find vcc_core regulator\n");
0133         vcc_core = NULL;
0134     } else {
0135         pr_info("Found vcc_core regulator\n");
0136     }
0137 }
0138 #else
0139 static int pxa_cpufreq_change_voltage(const struct pxa_freqs *pxa_freq)
0140 {
0141     return 0;
0142 }
0143 
0144 static void pxa_cpufreq_init_voltages(void) { }
0145 #endif
0146 
0147 static void find_freq_tables(struct cpufreq_frequency_table **freq_table,
0148                  const struct pxa_freqs **pxa_freqs)
0149 {
0150     if (cpu_is_pxa25x()) {
0151         if (!pxa255_turbo_table) {
0152             *pxa_freqs = pxa255_run_freqs;
0153             *freq_table = pxa255_run_freq_table;
0154         } else {
0155             *pxa_freqs = pxa255_turbo_freqs;
0156             *freq_table = pxa255_turbo_freq_table;
0157         }
0158     } else if (cpu_is_pxa27x()) {
0159         *pxa_freqs = pxa27x_freqs;
0160         *freq_table = pxa27x_freq_table;
0161     } else {
0162         BUG();
0163     }
0164 }
0165 
0166 static void pxa27x_guess_max_freq(void)
0167 {
0168     if (!pxa27x_maxfreq) {
0169         pxa27x_maxfreq = 416000;
0170         pr_info("PXA CPU 27x max frequency not defined (pxa27x_maxfreq), assuming pxa271 with %dkHz maxfreq\n",
0171             pxa27x_maxfreq);
0172     } else {
0173         pxa27x_maxfreq *= 1000;
0174     }
0175 }
0176 
0177 static unsigned int pxa_cpufreq_get(unsigned int cpu)
0178 {
0179     struct pxa_cpufreq_data *data = cpufreq_get_driver_data();
0180 
0181     return (unsigned int) clk_get_rate(data->clk_core) / 1000;
0182 }
0183 
0184 static int pxa_set_target(struct cpufreq_policy *policy, unsigned int idx)
0185 {
0186     struct cpufreq_frequency_table *pxa_freqs_table;
0187     const struct pxa_freqs *pxa_freq_settings;
0188     struct pxa_cpufreq_data *data = cpufreq_get_driver_data();
0189     unsigned int new_freq_cpu;
0190     int ret = 0;
0191 
0192     /* Get the current policy */
0193     find_freq_tables(&pxa_freqs_table, &pxa_freq_settings);
0194 
0195     new_freq_cpu = pxa_freq_settings[idx].khz;
0196 
0197     if (freq_debug)
0198         pr_debug("Changing CPU frequency from %d Mhz to %d Mhz\n",
0199              policy->cur / 1000,  new_freq_cpu / 1000);
0200 
0201     if (vcc_core && new_freq_cpu > policy->cur) {
0202         ret = pxa_cpufreq_change_voltage(&pxa_freq_settings[idx]);
0203         if (ret)
0204             return ret;
0205     }
0206 
0207     clk_set_rate(data->clk_core, new_freq_cpu * 1000);
0208 
0209     /*
0210      * Even if voltage setting fails, we don't report it, as the frequency
0211      * change succeeded. The voltage reduction is not a critical failure,
0212      * only power savings will suffer from this.
0213      *
0214      * Note: if the voltage change fails, and a return value is returned, a
0215      * bug is triggered (seems a deadlock). Should anybody find out where,
0216      * the "return 0" should become a "return ret".
0217      */
0218     if (vcc_core && new_freq_cpu < policy->cur)
0219         ret = pxa_cpufreq_change_voltage(&pxa_freq_settings[idx]);
0220 
0221     return 0;
0222 }
0223 
0224 static int pxa_cpufreq_init(struct cpufreq_policy *policy)
0225 {
0226     int i;
0227     unsigned int freq;
0228     struct cpufreq_frequency_table *pxa255_freq_table;
0229     const struct pxa_freqs *pxa255_freqs;
0230 
0231     /* try to guess pxa27x cpu */
0232     if (cpu_is_pxa27x())
0233         pxa27x_guess_max_freq();
0234 
0235     pxa_cpufreq_init_voltages();
0236 
0237     /* set default policy and cpuinfo */
0238     policy->cpuinfo.transition_latency = 1000; /* FIXME: 1 ms, assumed */
0239 
0240     /* Generate pxa25x the run cpufreq_frequency_table struct */
0241     for (i = 0; i < NUM_PXA25x_RUN_FREQS; i++) {
0242         pxa255_run_freq_table[i].frequency = pxa255_run_freqs[i].khz;
0243         pxa255_run_freq_table[i].driver_data = i;
0244     }
0245     pxa255_run_freq_table[i].frequency = CPUFREQ_TABLE_END;
0246 
0247     /* Generate pxa25x the turbo cpufreq_frequency_table struct */
0248     for (i = 0; i < NUM_PXA25x_TURBO_FREQS; i++) {
0249         pxa255_turbo_freq_table[i].frequency =
0250             pxa255_turbo_freqs[i].khz;
0251         pxa255_turbo_freq_table[i].driver_data = i;
0252     }
0253     pxa255_turbo_freq_table[i].frequency = CPUFREQ_TABLE_END;
0254 
0255     pxa255_turbo_table = !!pxa255_turbo_table;
0256 
0257     /* Generate the pxa27x cpufreq_frequency_table struct */
0258     for (i = 0; i < NUM_PXA27x_FREQS; i++) {
0259         freq = pxa27x_freqs[i].khz;
0260         if (freq > pxa27x_maxfreq)
0261             break;
0262         pxa27x_freq_table[i].frequency = freq;
0263         pxa27x_freq_table[i].driver_data = i;
0264     }
0265     pxa27x_freq_table[i].driver_data = i;
0266     pxa27x_freq_table[i].frequency = CPUFREQ_TABLE_END;
0267 
0268     /*
0269      * Set the policy's minimum and maximum frequencies from the tables
0270      * just constructed.  This sets cpuinfo.mxx_freq, min and max.
0271      */
0272     if (cpu_is_pxa25x()) {
0273         find_freq_tables(&pxa255_freq_table, &pxa255_freqs);
0274         pr_info("using %s frequency table\n",
0275             pxa255_turbo_table ? "turbo" : "run");
0276 
0277         policy->freq_table = pxa255_freq_table;
0278     }
0279     else if (cpu_is_pxa27x()) {
0280         policy->freq_table = pxa27x_freq_table;
0281     }
0282 
0283     pr_info("frequency change support initialized\n");
0284 
0285     return 0;
0286 }
0287 
0288 static struct cpufreq_driver pxa_cpufreq_driver = {
0289     .flags  = CPUFREQ_NEED_INITIAL_FREQ_CHECK,
0290     .verify = cpufreq_generic_frequency_table_verify,
0291     .target_index = pxa_set_target,
0292     .init   = pxa_cpufreq_init,
0293     .get    = pxa_cpufreq_get,
0294     .name   = "PXA2xx",
0295     .driver_data = &pxa_cpufreq_data,
0296 };
0297 
0298 static int __init pxa_cpu_init(void)
0299 {
0300     int ret = -ENODEV;
0301 
0302     pxa_cpufreq_data.clk_core = clk_get_sys(NULL, "core");
0303     if (IS_ERR(pxa_cpufreq_data.clk_core))
0304         return PTR_ERR(pxa_cpufreq_data.clk_core);
0305 
0306     if (cpu_is_pxa25x() || cpu_is_pxa27x())
0307         ret = cpufreq_register_driver(&pxa_cpufreq_driver);
0308     return ret;
0309 }
0310 
0311 static void __exit pxa_cpu_exit(void)
0312 {
0313     cpufreq_unregister_driver(&pxa_cpufreq_driver);
0314 }
0315 
0316 
0317 MODULE_AUTHOR("Intrinsyc Software Inc.");
0318 MODULE_DESCRIPTION("CPU frequency changing driver for the PXA architecture");
0319 MODULE_LICENSE("GPL");
0320 module_init(pxa_cpu_init);
0321 module_exit(pxa_cpu_exit);