asymmetric-32bit.rst 6.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155
  1. ======================
  2. Asymmetric 32-bit SoCs
  3. ======================
  4. Author: Will Deacon <[email protected]>
  5. This document describes the impact of asymmetric 32-bit SoCs on the
  6. execution of 32-bit (``AArch32``) applications.
  7. Date: 2021-05-17
  8. Introduction
  9. ============
  10. Some Armv9 SoCs suffer from a big.LITTLE misfeature where only a subset
  11. of the CPUs are capable of executing 32-bit user applications. On such
  12. a system, Linux by default treats the asymmetry as a "mismatch" and
  13. disables support for both the ``PER_LINUX32`` personality and
  14. ``execve(2)`` of 32-bit ELF binaries, with the latter returning
  15. ``-ENOEXEC``. If the mismatch is detected during late onlining of a
  16. 64-bit-only CPU, then the onlining operation fails and the new CPU is
  17. unavailable for scheduling.
  18. Surprisingly, these SoCs have been produced with the intention of
  19. running legacy 32-bit binaries. Unsurprisingly, that doesn't work very
  20. well with the default behaviour of Linux.
  21. It seems inevitable that future SoCs will drop 32-bit support
  22. altogether, so if you're stuck in the unenviable position of needing to
  23. run 32-bit code on one of these transitionary platforms then you would
  24. be wise to consider alternatives such as recompilation, emulation or
  25. retirement. If neither of those options are practical, then read on.
  26. Enabling kernel support
  27. =======================
  28. Since the kernel support is not completely transparent to userspace,
  29. allowing 32-bit tasks to run on an asymmetric 32-bit system requires an
  30. explicit "opt-in" and can be enabled by passing the
  31. ``allow_mismatched_32bit_el0`` parameter on the kernel command-line.
  32. For the remainder of this document we will refer to an *asymmetric
  33. system* to mean an asymmetric 32-bit SoC running Linux with this kernel
  34. command-line option enabled.
  35. Userspace impact
  36. ================
  37. 32-bit tasks running on an asymmetric system behave in mostly the same
  38. way as on a homogeneous system, with a few key differences relating to
  39. CPU affinity.
  40. sysfs
  41. -----
  42. The subset of CPUs capable of running 32-bit tasks is described in
  43. ``/sys/devices/system/cpu/aarch32_el0`` and is documented further in
  44. ``Documentation/ABI/testing/sysfs-devices-system-cpu``.
  45. **Note:** CPUs are advertised by this file as they are detected and so
  46. late-onlining of 32-bit-capable CPUs can result in the file contents
  47. being modified by the kernel at runtime. Once advertised, CPUs are never
  48. removed from the file.
  49. ``execve(2)``
  50. -------------
  51. On a homogeneous system, the CPU affinity of a task is preserved across
  52. ``execve(2)``. This is not always possible on an asymmetric system,
  53. specifically when the new program being executed is 32-bit yet the
  54. affinity mask contains 64-bit-only CPUs. In this situation, the kernel
  55. determines the new affinity mask as follows:
  56. 1. If the 32-bit-capable subset of the affinity mask is not empty,
  57. then the affinity is restricted to that subset and the old affinity
  58. mask is saved. This saved mask is inherited over ``fork(2)`` and
  59. preserved across ``execve(2)`` of 32-bit programs.
  60. **Note:** This step does not apply to ``SCHED_DEADLINE`` tasks.
  61. See `SCHED_DEADLINE`_.
  62. 2. Otherwise, the cpuset hierarchy of the task is walked until an
  63. ancestor is found containing at least one 32-bit-capable CPU. The
  64. affinity of the task is then changed to match the 32-bit-capable
  65. subset of the cpuset determined by the walk.
  66. 3. On failure (i.e. out of memory), the affinity is changed to the set
  67. of all 32-bit-capable CPUs of which the kernel is aware.
  68. A subsequent ``execve(2)`` of a 64-bit program by the 32-bit task will
  69. invalidate the affinity mask saved in (1) and attempt to restore the CPU
  70. affinity of the task using the saved mask if it was previously valid.
  71. This restoration may fail due to intervening changes to the deadline
  72. policy or cpuset hierarchy, in which case the ``execve(2)`` continues
  73. with the affinity unchanged.
  74. Calls to ``sched_setaffinity(2)`` for a 32-bit task will consider only
  75. the 32-bit-capable CPUs of the requested affinity mask. On success, the
  76. affinity for the task is updated and any saved mask from a prior
  77. ``execve(2)`` is invalidated.
  78. ``SCHED_DEADLINE``
  79. ------------------
  80. Explicit admission of a 32-bit deadline task to the default root domain
  81. (e.g. by calling ``sched_setattr(2)``) is rejected on an asymmetric
  82. 32-bit system unless admission control is disabled by writing -1 to
  83. ``/proc/sys/kernel/sched_rt_runtime_us``.
  84. ``execve(2)`` of a 32-bit program from a 64-bit deadline task will
  85. return ``-ENOEXEC`` if the root domain for the task contains any
  86. 64-bit-only CPUs and admission control is enabled. Concurrent offlining
  87. of 32-bit-capable CPUs may still necessitate the procedure described in
  88. `execve(2)`_, in which case step (1) is skipped and a warning is
  89. emitted on the console.
  90. **Note:** It is recommended that a set of 32-bit-capable CPUs are placed
  91. into a separate root domain if ``SCHED_DEADLINE`` is to be used with
  92. 32-bit tasks on an asymmetric system. Failure to do so is likely to
  93. result in missed deadlines.
  94. Cpusets
  95. -------
  96. The affinity of a 32-bit task on an asymmetric system may include CPUs
  97. that are not explicitly allowed by the cpuset to which it is attached.
  98. This can occur as a result of the following two situations:
  99. - A 64-bit task attached to a cpuset which allows only 64-bit CPUs
  100. executes a 32-bit program.
  101. - All of the 32-bit-capable CPUs allowed by a cpuset containing a
  102. 32-bit task are offlined.
  103. In both of these cases, the new affinity is calculated according to step
  104. (2) of the process described in `execve(2)`_ and the cpuset hierarchy is
  105. unchanged irrespective of the cgroup version.
  106. CPU hotplug
  107. -----------
  108. On an asymmetric system, the first detected 32-bit-capable CPU is
  109. prevented from being offlined by userspace and any such attempt will
  110. return ``-EPERM``. Note that suspend is still permitted even if the
  111. primary CPU (i.e. CPU 0) is 64-bit-only.
  112. KVM
  113. ---
  114. Although KVM will not advertise 32-bit EL0 support to any vCPUs on an
  115. asymmetric system, a broken guest at EL1 could still attempt to execute
  116. 32-bit code at EL0. In this case, an exit from a vCPU thread in 32-bit
  117. mode will return to host userspace with an ``exit_reason`` of
  118. ``KVM_EXIT_FAIL_ENTRY`` and will remain non-runnable until successfully
  119. re-initialised by a subsequent ``KVM_ARM_VCPU_INIT`` operation.