topology_dts.c 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553
  1. /*
  2. * Copyright (C) 2017 MediaTek Inc.
  3. *
  4. * This program is free software; you can redistribute it and/or modify
  5. * it under the terms of the GNU General Public License version 2 as
  6. * published by the Free Software Foundation.
  7. *
  8. * This program is distributed in the hope that it will be useful,
  9. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  10. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  11. * See http://www.gnu.org/licenses/gpl-2.0.html for more details.
  12. */
  13. #include <linux/list_sort.h>
  14. struct cpu_efficiency {
  15. const char *compatible;
  16. unsigned long efficiency;
  17. };
  18. /*
  19. * Table of relative efficiency of each processors
  20. * The efficiency value must fit in 20bit and the final
  21. * cpu_scale value must be in the range
  22. * 0 < cpu_scale < SCHED_CAPACITY_SCALE.
  23. * Processors that are not defined in the table,
  24. * use the default SCHED_CAPACITY_SCALE value for cpu_scale.
  25. */
  26. static const struct cpu_efficiency table_efficiency[] = {
  27. { "arm,cortex-a73", 3630 },
  28. { "arm,cortex-a72", 4186 },
  29. { "arm,cortex-a57", 3891 },
  30. { "arm,cortex-a53", 2048 },
  31. { "arm,cortex-a35", 1661 },
  32. { NULL, },
  33. };
  34. static void update_siblings_masks(unsigned int cpuid);
  35. static void update_cpu_capacity(unsigned int cpu);
  36. static unsigned long *__cpu_capacity;
  37. #define cpu_capacity(cpu) __cpu_capacity[cpu]
  38. static u64 max_cpu_perf, min_cpu_perf;
  39. static int __init get_cpu_for_node(struct device_node *node)
  40. {
  41. struct device_node *cpu_node;
  42. int cpu;
  43. cpu_node = of_parse_phandle(node, "cpu", 0);
  44. if (!cpu_node)
  45. return -1;
  46. for_each_possible_cpu(cpu) {
  47. if (of_get_cpu_node(cpu, NULL) == cpu_node) {
  48. of_node_put(cpu_node);
  49. return cpu;
  50. }
  51. }
  52. pr_crit("Unable to find CPU node for %s\n", cpu_node->full_name);
  53. of_node_put(cpu_node);
  54. return -1;
  55. }
  56. static int __init parse_core(struct device_node *core, int cluster_id,
  57. int core_id)
  58. {
  59. char name[10];
  60. bool leaf = true;
  61. int i = 0;
  62. int cpu;
  63. struct device_node *t;
  64. do {
  65. snprintf(name, sizeof(name), "thread%d", i);
  66. t = of_get_child_by_name(core, name);
  67. if (t) {
  68. leaf = false;
  69. cpu = get_cpu_for_node(t);
  70. if (cpu >= 0) {
  71. cpu_topology[cpu].socket_id = cluster_id;
  72. cpu_topology[cpu].core_id = core_id;
  73. cpu_topology[cpu].thread_id = i;
  74. } else {
  75. pr_err("%s: Can't get CPU for thread\n",
  76. t->full_name);
  77. of_node_put(t);
  78. return -EINVAL;
  79. }
  80. of_node_put(t);
  81. }
  82. i++;
  83. } while (t);
  84. cpu = get_cpu_for_node(core);
  85. if (cpu >= 0) {
  86. if (!leaf) {
  87. pr_err("%s: Core has both threads and CPU\n",
  88. core->full_name);
  89. return -EINVAL;
  90. }
  91. cpu_topology[cpu].socket_id = cluster_id;
  92. cpu_topology[cpu].core_id = core_id;
  93. } else if (leaf) {
  94. pr_err("%s: Can't get CPU for leaf core\n", core->full_name);
  95. return -EINVAL;
  96. }
  97. return 0;
  98. }
  99. static int __init parse_cluster(struct device_node *cluster, int depth)
  100. {
  101. char name[10];
  102. bool leaf = true;
  103. bool has_cores = false;
  104. struct device_node *c;
  105. static int cluster_id __initdata;
  106. int core_id = 0;
  107. int i, ret;
  108. /*
  109. * First check for child clusters; we currently ignore any
  110. * information about the nesting of clusters and present the
  111. * scheduler with a flat list of them.
  112. */
  113. i = 0;
  114. do {
  115. snprintf(name, sizeof(name), "cluster%d", i);
  116. c = of_get_child_by_name(cluster, name);
  117. if (c) {
  118. leaf = false;
  119. ret = parse_cluster(c, depth + 1);
  120. of_node_put(c);
  121. if (ret != 0)
  122. return ret;
  123. }
  124. i++;
  125. } while (c);
  126. /* Now check for cores */
  127. i = 0;
  128. do {
  129. snprintf(name, sizeof(name), "core%d", i);
  130. c = of_get_child_by_name(cluster, name);
  131. if (c) {
  132. has_cores = true;
  133. if (depth == 0) {
  134. pr_err("%s: cpu-map children should be clusters\n",
  135. c->full_name);
  136. of_node_put(c);
  137. return -EINVAL;
  138. }
  139. if (leaf) {
  140. ret = parse_core(c, cluster_id, core_id++);
  141. } else {
  142. pr_err("%s: Non-leaf cluster with core %s\n",
  143. cluster->full_name, name);
  144. ret = -EINVAL;
  145. }
  146. of_node_put(c);
  147. if (ret != 0)
  148. return ret;
  149. }
  150. i++;
  151. } while (c);
  152. if (leaf && !has_cores)
  153. pr_warn("%s: empty cluster\n", cluster->full_name);
  154. if (leaf)
  155. cluster_id++;
  156. return 0;
  157. }
  158. static int __init parse_dt_topology(void)
  159. {
  160. struct device_node *cn, *map;
  161. int ret = 0;
  162. int cpu;
  163. cn = of_find_node_by_path("/cpus");
  164. if (!cn) {
  165. pr_err("No CPU information found in DT\n");
  166. return 0;
  167. }
  168. /*
  169. * When topology is provided cpu-map is essentially a root
  170. * cluster with restricted subnodes.
  171. */
  172. map = of_get_child_by_name(cn, "cpu-map");
  173. if (!map)
  174. goto out;
  175. ret = parse_cluster(map, 0);
  176. if (ret != 0)
  177. goto out_map;
  178. /*
  179. * Check that all cores are in the topology; the SMP code will
  180. * only mark cores described in the DT as possible.
  181. */
  182. for_each_possible_cpu(cpu)
  183. if (cpu_topology[cpu].socket_id == -1)
  184. ret = -EINVAL;
  185. out_map:
  186. of_node_put(map);
  187. out:
  188. of_node_put(cn);
  189. return ret;
  190. }
  191. static void __init parse_dt_cpu_capacity(void)
  192. {
  193. const struct cpu_efficiency *cpu_eff;
  194. struct device_node *cn = NULL;
  195. int cpu = 0, i = 0;
  196. __cpu_capacity = kcalloc(nr_cpu_ids, sizeof(*__cpu_capacity),
  197. GFP_NOWAIT);
  198. min_cpu_perf = ULONG_MAX;
  199. max_cpu_perf = 0;
  200. min_cpu_perf = ULONG_MAX;
  201. max_cpu_perf = 0;
  202. for_each_possible_cpu(cpu) {
  203. const u32 *rate;
  204. int len;
  205. u64 cpu_perf;
  206. /* too early to use cpu->of_node */
  207. cn = of_get_cpu_node(cpu, NULL);
  208. if (!cn) {
  209. pr_debug("missing device node for CPU %d\n", cpu);
  210. continue;
  211. }
  212. for (cpu_eff = table_efficiency; cpu_eff->compatible; cpu_eff++)
  213. if (of_device_is_compatible(cn, cpu_eff->compatible))
  214. break;
  215. if (cpu_eff->compatible == NULL)
  216. continue;
  217. rate = of_get_property(cn, "clock-frequency", &len);
  218. if (!rate || len != 4) {
  219. pr_debug("%s missing clock-frequency property\n",
  220. cn->full_name);
  221. continue;
  222. }
  223. cpu_perf = ((be32_to_cpup(rate)) >> 20) * cpu_eff->efficiency;
  224. cpu_capacity(cpu) = cpu_perf;
  225. max_cpu_perf = max(max_cpu_perf, cpu_perf);
  226. min_cpu_perf = min(min_cpu_perf, cpu_perf);
  227. i++;
  228. }
  229. if (i < num_possible_cpus()) {
  230. max_cpu_perf = 0;
  231. min_cpu_perf = 0;
  232. }
  233. }
  234. /*
  235. * Scheduler load-tracking scale-invariance
  236. *
  237. * Provides the scheduler with a scale-invariance correction factor that
  238. * compensates for frequency scaling.
  239. */
  240. static DEFINE_PER_CPU(atomic_long_t, cpu_freq_capacity);
  241. static DEFINE_PER_CPU(atomic_long_t, cpu_max_freq);
  242. static DEFINE_PER_CPU(atomic_long_t, cpu_min_freq);
  243. /* cpufreq callback function setting current cpu frequency */
  244. void arch_scale_set_curr_freq(int cpu, unsigned long freq)
  245. {
  246. unsigned long max = atomic_long_read(&per_cpu(cpu_max_freq, cpu));
  247. unsigned long curr;
  248. if (!max)
  249. return;
  250. curr = (freq * SCHED_CAPACITY_SCALE) / max;
  251. atomic_long_set(&per_cpu(cpu_freq_capacity, cpu), curr);
  252. }
  253. /* cpufreq callback function setting max cpu frequency */
  254. void arch_scale_set_max_freq(int cpu, unsigned long freq)
  255. {
  256. atomic_long_set(&per_cpu(cpu_max_freq, cpu), freq);
  257. }
  258. void arch_scale_set_min_freq(int cpu, unsigned long freq)
  259. {
  260. atomic_long_set(&per_cpu(cpu_min_freq, cpu), freq);
  261. }
  262. unsigned long arch_scale_get_max_freq(int cpu)
  263. {
  264. unsigned long max = atomic_long_read(&per_cpu(cpu_max_freq, cpu));
  265. return max;
  266. }
  267. unsigned long arch_scale_get_min_freq(int cpu)
  268. {
  269. unsigned long min = atomic_long_read(&per_cpu(cpu_min_freq, cpu));
  270. return min;
  271. }
  272. unsigned long arch_scale_freq_capacity(struct sched_domain *sd, int cpu)
  273. {
  274. unsigned long curr = atomic_long_read(&per_cpu(cpu_freq_capacity, cpu));
  275. if (!curr)
  276. return SCHED_CAPACITY_SCALE;
  277. return curr;
  278. }
  279. unsigned long arch_get_max_cpu_capacity(int cpu)
  280. {
  281. return per_cpu(cpu_scale, cpu);
  282. }
  283. unsigned long arch_get_cur_cpu_capacity(int cpu)
  284. {
  285. unsigned long scale_freq;
  286. scale_freq = atomic_long_read(&per_cpu(cpu_freq_capacity, cpu));
  287. if (!scale_freq)
  288. scale_freq = SCHED_CAPACITY_SCALE;
  289. return (per_cpu(cpu_scale, cpu) * scale_freq / SCHED_CAPACITY_SCALE);
  290. }
  291. static int cpu_topology_init;
  292. void __init arch_build_cpu_topology_domain(void)
  293. {
  294. int cpuid;
  295. init_cpu_topology();
  296. /* update core and thread sibling masks */
  297. for_each_possible_cpu(cpuid) {
  298. update_siblings_masks(cpuid);
  299. update_cpu_capacity(cpuid);
  300. }
  301. cpu_topology_init = 1;
  302. }
  303. /*
  304. * Extras of CPU & Cluster functions
  305. */
  306. int arch_cpu_is_big(unsigned int cpu)
  307. {
  308. struct cputopo_arm *cpu_topo = &cpu_topology[cpu];
  309. switch (cpu_topo->partno) {
  310. case ARM_CPU_PART_CORTEX_A57:
  311. case ARM_CPU_PART_CORTEX_A72:
  312. return 1;
  313. default:
  314. return 0;
  315. }
  316. }
  317. int arch_cpu_is_little(unsigned int cpu)
  318. {
  319. return !arch_cpu_is_big(cpu);
  320. }
  321. int arch_is_smp(void)
  322. {
  323. static int __arch_smp = -1;
  324. if (__arch_smp != -1)
  325. return __arch_smp;
  326. __arch_smp = (max_cpu_perf != min_cpu_perf) ? 0 : 1;
  327. return __arch_smp;
  328. }
  329. int arch_get_nr_clusters(void)
  330. {
  331. static int __arch_nr_clusters = -1;
  332. int max_id = 0;
  333. unsigned int cpu;
  334. if (__arch_nr_clusters != -1)
  335. return __arch_nr_clusters;
  336. /* assume socket id is monotonic increasing without gap. */
  337. for_each_possible_cpu(cpu) {
  338. struct cputopo_arm *cpu_topo = &cpu_topology[cpu];
  339. if (cpu_topo->socket_id > max_id)
  340. max_id = cpu_topo->socket_id;
  341. }
  342. __arch_nr_clusters = max_id + 1;
  343. return __arch_nr_clusters;
  344. }
  345. int arch_is_multi_cluster(void)
  346. {
  347. return arch_get_nr_clusters() > 1 ? 1 : 0;
  348. }
  349. int arch_get_cluster_id(unsigned int cpu)
  350. {
  351. struct cputopo_arm *cpu_topo = &cpu_topology[cpu];
  352. return cpu_topo->socket_id < 0 ? 0 : cpu_topo->socket_id;
  353. }
  354. void arch_get_cluster_cpus(struct cpumask *cpus, int cluster_id)
  355. {
  356. unsigned int cpu;
  357. cpumask_clear(cpus);
  358. for_each_possible_cpu(cpu) {
  359. struct cputopo_arm *cpu_topo = &cpu_topology[cpu];
  360. if (cpu_topo->socket_id == cluster_id)
  361. cpumask_set_cpu(cpu, cpus);
  362. }
  363. }
  364. int arch_better_capacity(unsigned int cpu)
  365. {
  366. return cpu_capacity(cpu) > min_cpu_perf;
  367. }
  368. /*
  369. * Heterogenous CPU capacity compare function
  370. * Only inspect lowest id of cpus in same domain.
  371. * Assume CPUs in same domain has same capacity.
  372. */
  373. struct cluster_info {
  374. struct hmp_domain *hmpd;
  375. int cpu;
  376. bool is_big;
  377. unsigned long cpu_perf;
  378. };
  379. static inline __init void fillin_cluster(struct cluster_info *cinfo,
  380. struct hmp_domain *hmpd)
  381. {
  382. int cpu;
  383. unsigned long cpu_perf;
  384. cinfo->hmpd = hmpd;
  385. cinfo->cpu = cpumask_any(&cinfo->hmpd->possible_cpus);
  386. cinfo->is_big = arch_cpu_is_big(cinfo->cpu);
  387. for_each_cpu(cpu, &hmpd->possible_cpus) {
  388. cpu_perf = cpu_capacity(cpu);
  389. if (cpu_perf > 0)
  390. break;
  391. }
  392. cinfo->cpu_perf = cpu_perf;
  393. if (cpu_perf == 0)
  394. pr_info("Uninitialized CPU performance (CPU mask: %lx)",
  395. cpumask_bits(&hmpd->possible_cpus)[0]);
  396. }
  397. /*
  398. * Negative, if @a should sort before @b
  399. * Positive, if @a should sort after @b.
  400. * Return 0, if ordering is to be preserved
  401. */
  402. int __init hmp_compare(void *priv, struct list_head *a, struct list_head *b)
  403. {
  404. struct cluster_info ca;
  405. struct cluster_info cb;
  406. fillin_cluster(&ca, list_entry(a, struct hmp_domain, hmp_domains));
  407. fillin_cluster(&cb, list_entry(b, struct hmp_domain, hmp_domains));
  408. /* Handle diff CPU type */
  409. if (ca.is_big != cb.is_big)
  410. return ca.is_big ? -1 : 1;
  411. return (ca.cpu_perf > cb.cpu_perf) ? -1 : 1;
  412. }
  413. void __init arch_init_hmp_domains(void)
  414. {
  415. struct hmp_domain *domain;
  416. struct cpumask cpu_mask;
  417. int id, maxid;
  418. cpumask_clear(&cpu_mask);
  419. maxid = arch_get_nr_clusters();
  420. /*
  421. * Initialize hmp_domains
  422. * Must be ordered with respect to compute capacity.
  423. * Fastest domain at head of list.
  424. */
  425. for (id = 0; id < maxid; id++) {
  426. arch_get_cluster_cpus(&cpu_mask, id);
  427. domain = (struct hmp_domain *)
  428. kmalloc(sizeof(struct hmp_domain), GFP_KERNEL);
  429. if (domain) {
  430. cpumask_copy(&domain->possible_cpus, &cpu_mask);
  431. cpumask_and(&domain->cpus, cpu_online_mask,
  432. &domain->possible_cpus);
  433. list_add(&domain->hmp_domains, &hmp_domains);
  434. }
  435. }
  436. /*
  437. * Sorting HMP domain by CPU capacity
  438. */
  439. list_sort(NULL, &hmp_domains, &hmp_compare);
  440. }
  441. #ifdef CONFIG_MTK_SCHED_RQAVG_KS
  442. /* To add this function for sched_avg.c */
  443. unsigned long get_cpu_orig_capacity(unsigned int cpu)
  444. {
  445. u64 capacity = cpu_capacity(cpu);
  446. if (!capacity || !max_cpu_perf)
  447. return 1024;
  448. capacity *= SCHED_CAPACITY_SCALE;
  449. capacity = div64_u64(capacity, max_cpu_perf);
  450. return capacity;
  451. }
  452. #endif