smp.c 6.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288
  1. // SPDX-License-Identifier: GPL-2.0-or-later
  2. /*
  3. * SMP support for pSeries machines.
  4. *
  5. * Dave Engebretsen, Peter Bergner, and
  6. * Mike Corrigan {engebret|bergner|mikec}@us.ibm.com
  7. *
  8. * Plus various changes from other IBM teams...
  9. */
  10. #include <linux/kernel.h>
  11. #include <linux/sched.h>
  12. #include <linux/smp.h>
  13. #include <linux/interrupt.h>
  14. #include <linux/delay.h>
  15. #include <linux/init.h>
  16. #include <linux/spinlock.h>
  17. #include <linux/cache.h>
  18. #include <linux/err.h>
  19. #include <linux/device.h>
  20. #include <linux/cpu.h>
  21. #include <linux/pgtable.h>
  22. #include <asm/ptrace.h>
  23. #include <linux/atomic.h>
  24. #include <asm/irq.h>
  25. #include <asm/page.h>
  26. #include <asm/io.h>
  27. #include <asm/smp.h>
  28. #include <asm/paca.h>
  29. #include <asm/machdep.h>
  30. #include <asm/cputable.h>
  31. #include <asm/firmware.h>
  32. #include <asm/rtas.h>
  33. #include <asm/vdso_datapage.h>
  34. #include <asm/cputhreads.h>
  35. #include <asm/xics.h>
  36. #include <asm/xive.h>
  37. #include <asm/dbell.h>
  38. #include <asm/plpar_wrappers.h>
  39. #include <asm/code-patching.h>
  40. #include <asm/svm.h>
  41. #include <asm/kvm_guest.h>
  42. #include "pseries.h"
  43. /*
  44. * The Primary thread of each non-boot processor was started from the OF client
  45. * interface by prom_hold_cpus and is spinning on secondary_hold_spinloop.
  46. */
  47. static cpumask_var_t of_spin_mask;
  48. /* Query where a cpu is now. Return codes #defined in plpar_wrappers.h */
  49. int smp_query_cpu_stopped(unsigned int pcpu)
  50. {
  51. int cpu_status, status;
  52. int qcss_tok = rtas_token("query-cpu-stopped-state");
  53. if (qcss_tok == RTAS_UNKNOWN_SERVICE) {
  54. printk_once(KERN_INFO
  55. "Firmware doesn't support query-cpu-stopped-state\n");
  56. return QCSS_HARDWARE_ERROR;
  57. }
  58. status = rtas_call(qcss_tok, 1, 2, &cpu_status, pcpu);
  59. if (status != 0) {
  60. printk(KERN_ERR
  61. "RTAS query-cpu-stopped-state failed: %i\n", status);
  62. return status;
  63. }
  64. return cpu_status;
  65. }
  66. /**
  67. * smp_startup_cpu() - start the given cpu
  68. *
  69. * At boot time, there is nothing to do for primary threads which were
  70. * started from Open Firmware. For anything else, call RTAS with the
  71. * appropriate start location.
  72. *
  73. * Returns:
  74. * 0 - failure
  75. * 1 - success
  76. */
  77. static inline int smp_startup_cpu(unsigned int lcpu)
  78. {
  79. int status;
  80. unsigned long start_here =
  81. __pa(ppc_function_entry(generic_secondary_smp_init));
  82. unsigned int pcpu;
  83. int start_cpu;
  84. if (cpumask_test_cpu(lcpu, of_spin_mask))
  85. /* Already started by OF and sitting in spin loop */
  86. return 1;
  87. pcpu = get_hard_smp_processor_id(lcpu);
  88. /* Check to see if the CPU out of FW already for kexec */
  89. if (smp_query_cpu_stopped(pcpu) == QCSS_NOT_STOPPED){
  90. cpumask_set_cpu(lcpu, of_spin_mask);
  91. return 1;
  92. }
  93. /*
  94. * If the RTAS start-cpu token does not exist then presume the
  95. * cpu is already spinning.
  96. */
  97. start_cpu = rtas_token("start-cpu");
  98. if (start_cpu == RTAS_UNKNOWN_SERVICE)
  99. return 1;
  100. status = rtas_call(start_cpu, 3, 1, NULL, pcpu, start_here, pcpu);
  101. if (status != 0) {
  102. printk(KERN_ERR "start-cpu failed: %i\n", status);
  103. return 0;
  104. }
  105. return 1;
  106. }
  107. static void smp_setup_cpu(int cpu)
  108. {
  109. if (xive_enabled())
  110. xive_smp_setup_cpu();
  111. else if (cpu != boot_cpuid)
  112. xics_setup_cpu();
  113. if (firmware_has_feature(FW_FEATURE_SPLPAR))
  114. vpa_init(cpu);
  115. cpumask_clear_cpu(cpu, of_spin_mask);
  116. }
  117. static int smp_pSeries_kick_cpu(int nr)
  118. {
  119. if (nr < 0 || nr >= nr_cpu_ids)
  120. return -EINVAL;
  121. if (!smp_startup_cpu(nr))
  122. return -ENOENT;
  123. /*
  124. * The processor is currently spinning, waiting for the
  125. * cpu_start field to become non-zero After we set cpu_start,
  126. * the processor will continue on to secondary_start
  127. */
  128. paca_ptrs[nr]->cpu_start = 1;
  129. return 0;
  130. }
  131. static int pseries_smp_prepare_cpu(int cpu)
  132. {
  133. if (xive_enabled())
  134. return xive_smp_prepare_cpu(cpu);
  135. return 0;
  136. }
  137. /* Cause IPI as setup by the interrupt controller (xics or xive) */
  138. static void (*ic_cause_ipi)(int cpu) __ro_after_init;
  139. /* Use msgsndp doorbells target is a sibling, else use interrupt controller */
  140. static void dbell_or_ic_cause_ipi(int cpu)
  141. {
  142. if (doorbell_try_core_ipi(cpu))
  143. return;
  144. ic_cause_ipi(cpu);
  145. }
  146. static int pseries_cause_nmi_ipi(int cpu)
  147. {
  148. int hwcpu;
  149. if (cpu == NMI_IPI_ALL_OTHERS) {
  150. hwcpu = H_SIGNAL_SYS_RESET_ALL_OTHERS;
  151. } else {
  152. if (cpu < 0) {
  153. WARN_ONCE(true, "incorrect cpu parameter %d", cpu);
  154. return 0;
  155. }
  156. hwcpu = get_hard_smp_processor_id(cpu);
  157. }
  158. if (plpar_signal_sys_reset(hwcpu) == H_SUCCESS)
  159. return 1;
  160. return 0;
  161. }
  162. static __init void pSeries_smp_probe(void)
  163. {
  164. if (xive_enabled())
  165. xive_smp_probe();
  166. else
  167. xics_smp_probe();
  168. /* No doorbell facility, must use the interrupt controller for IPIs */
  169. if (!cpu_has_feature(CPU_FTR_DBELL))
  170. return;
  171. /* Doorbells can only be used for IPIs between SMT siblings */
  172. if (!cpu_has_feature(CPU_FTR_SMT))
  173. return;
  174. check_kvm_guest();
  175. if (is_kvm_guest()) {
  176. /*
  177. * KVM emulates doorbells by disabling FSCR[MSGP] so msgsndp
  178. * faults to the hypervisor which then reads the instruction
  179. * from guest memory, which tends to be slower than using XIVE.
  180. */
  181. if (xive_enabled())
  182. return;
  183. /*
  184. * XICS hcalls aren't as fast, so we can use msgsndp (which
  185. * also helps exercise KVM emulation), however KVM can't
  186. * emulate secure guests because it can't read the instruction
  187. * out of their memory.
  188. */
  189. if (is_secure_guest())
  190. return;
  191. }
  192. /*
  193. * Under PowerVM, FSCR[MSGP] is enabled as guest vCPU siblings are
  194. * gang scheduled on the same physical core, so doorbells are always
  195. * faster than the interrupt controller, and they can be used by
  196. * secure guests.
  197. */
  198. ic_cause_ipi = smp_ops->cause_ipi;
  199. smp_ops->cause_ipi = dbell_or_ic_cause_ipi;
  200. }
  201. static struct smp_ops_t pseries_smp_ops = {
  202. .message_pass = NULL, /* Use smp_muxed_ipi_message_pass */
  203. .cause_ipi = NULL, /* Filled at runtime by pSeries_smp_probe() */
  204. .cause_nmi_ipi = pseries_cause_nmi_ipi,
  205. .probe = pSeries_smp_probe,
  206. .prepare_cpu = pseries_smp_prepare_cpu,
  207. .kick_cpu = smp_pSeries_kick_cpu,
  208. .setup_cpu = smp_setup_cpu,
  209. .cpu_bootable = smp_generic_cpu_bootable,
  210. };
  211. /* This is called very early */
  212. void __init smp_init_pseries(void)
  213. {
  214. int i;
  215. pr_debug(" -> smp_init_pSeries()\n");
  216. smp_ops = &pseries_smp_ops;
  217. alloc_bootmem_cpumask_var(&of_spin_mask);
  218. /*
  219. * Mark threads which are still spinning in hold loops
  220. *
  221. * We know prom_init will not have started them if RTAS supports
  222. * query-cpu-stopped-state.
  223. */
  224. if (rtas_token("query-cpu-stopped-state") == RTAS_UNKNOWN_SERVICE) {
  225. if (cpu_has_feature(CPU_FTR_SMT)) {
  226. for_each_present_cpu(i) {
  227. if (cpu_thread_in_core(i) == 0)
  228. cpumask_set_cpu(i, of_spin_mask);
  229. }
  230. } else
  231. cpumask_copy(of_spin_mask, cpu_present_mask);
  232. cpumask_clear_cpu(boot_cpuid, of_spin_mask);
  233. }
  234. /* Non-lpar has additional take/give timebase */
  235. if (rtas_token("freeze-time-base") != RTAS_UNKNOWN_SERVICE) {
  236. smp_ops->give_timebase = rtas_give_timebase;
  237. smp_ops->take_timebase = rtas_take_timebase;
  238. }
  239. pr_debug(" <- smp_init_pSeries()\n");
  240. }