Between the header and the definitions, there's no line gap, and in a
couple of places a double line gap for no semantic reason, which makes
the output look a little odd.
Fix this so blocks are consistently separated with a single line gap:
* Add a newline after the "Generated file" comment line, so this is
clearly split from whatever the first definition in the file is.
* At the start of a SysregFields block there's no need for a newline as
we haven't output any sysreg encoding details prior to this.
* At the end of a Sysreg block there's no need for a newline if we
have no RES0 or RES1 fields, as there will be a line gap after the
previous element (e.g. a Fields line).
There should be no functional change as a result of this patch.
Signed-off-by: Mark Rutland <mark.rutland@arm.com>
Cc: Mark Brown <broonie@kernel.org>
Cc: Will Deacon <will@kernel.org>
Link: https://lore.kernel.org/r/20220513174118.266966-3-mark.rutland@arm.com
Signed-off-by: Catalin Marinas <catalin.marinas@arm.com>
Currently for registers without fields we create a comment pointing at
the common definitions, e.g.
| #define REG_TTBR0_EL1 S3_0_C2_C0_0
| #define SYS_TTBR0_EL1 sys_reg(3, 0, 2, 0, 0)
| #define SYS_TTBR0_EL1_Op0 3
| #define SYS_TTBR0_EL1_Op1 0
| #define SYS_TTBR0_EL1_CRn 2
| #define SYS_TTBR0_EL1_CRm 0
| #define SYS_TTBR0_EL1_Op2 0
|
| /* See TTBRx_EL1 */
It would be slightly nicer if the comment said what we should be looking
for, e.g.
| #define REG_TTBR0_EL1 S3_0_C2_C0_0
| #define SYS_TTBR0_EL1 sys_reg(3, 0, 2, 0, 0)
| #define SYS_TTBR0_EL1_Op0 3
| #define SYS_TTBR0_EL1_Op1 0
| #define SYS_TTBR0_EL1_CRn 2
| #define SYS_TTBR0_EL1_CRm 0
| #define SYS_TTBR0_EL1_Op2 0
|
| /* For TTBR0_EL1 fields see TTBRx_EL1 */
Update the comment generation accordingly.
Signed-off-by: Mark Rutland <mark.rutland@arm.com>
Cc: Mark Brown <broonie@kernel.org>
Cc: Will Deacon <will@kernel.org>
Link: https://lore.kernel.org/r/20220513174118.266966-2-mark.rutland@arm.com
Signed-off-by: Catalin Marinas <catalin.marinas@arm.com>
The arm64 kernel requires some metadata for each system register it may
need to access. Currently we have:
* A SYS_<regname> definition which sorresponds to a sys_reg() macro.
This is used both to look up a sysreg by encoding (e.g. in KVM), and
also to generate code to access a sysreg where the assembler is
unaware of the specific sysreg encoding.
Where assemblers support the S3_<op1>_C<crn>_C<crm>_<op2> syntax for
system registers, we could use this rather than manually assembling
the instructions. However, we don't have consistent definitions for
these and we currently still need to handle toolchains that lack this
feature.
* A set of <regname>_<fieldname>_SHIFT and <regname>_<fieldname>_MASK
definitions, which can be used to extract fields from the register, or
to construct a register from a set of fields.
These do not follow the convention used by <linux/bitfield.h>, and the
masks are not shifted into place, preventing their use in FIELD_PREP()
and FIELD_GET(). We require the SHIFT definitions for inline assembly
(and WIDTH definitions would be helpful for UBFX/SBFX), so we cannot
only define a shifted MASK. Defining a SHIFT, WIDTH, shifted MASK and
unshifted MASK is tedious and error-prone and life is much easier when
they can be relied up to exist when writing code.
* A set of <regname>_<fieldname>_<valname> definitions for each
enumerated value a field may hold. These are used when identifying the
presence of features.
Atop of this, other code has to build up metadata at runtime (e.g. the
sets of RES0/RES1 bits in a register).
This patch adds scripting so that we can have an easier-to-manage
canonical representation of this metadata, from which we can generate
all the definitions necessary for various use-cases, e.g.
| #define REG_ID_AA64ISAR0_EL1 S3_0_C0_C6_0
| #define SYS_ID_AA64ISAR0_EL1 sys_reg(3, 0, 0, 6, 0)
| #define SYS_ID_AA64ISAR0_EL1_Op0 3
| #define SYS_ID_AA64ISAR0_EL1_Op1 0
| #define SYS_ID_AA64ISAR0_EL1_CRn 0
| #define SYS_ID_AA64ISAR0_EL1_CRm 6
| #define SYS_ID_AA64ISAR0_EL1_Op2 0
| #define ID_AA64ISAR0_EL1_RNDR GENMASK(63, 60)
| #define ID_AA64ISAR0_EL1_RNDR_MASK GENMASK(63, 60)
| #define ID_AA64ISAR0_EL1_RNDR_SHIFT 60
| #define ID_AA64ISAR0_EL1_RNDR_WIDTH 4
| #define ID_AA64ISAR0_EL1_RNDR_NI UL(0b0000)
| #define ID_AA64ISAR0_EL1_RNDR_IMP UL(0b0001)
The script requires that all bits in the register be specified and that
there be no overlapping fields. This helps the script spot errors in the
input but means that the few registers which change layout at runtime
depending on things like virtualisation settings will need some manual
handling. No actual register conversions are done here but a header for
the register data with some documention of the format is provided.
For cases where multiple registers share a layout (eg, when identical
controls are provided at multiple ELs) the register fields can be
defined once and referenced from the actual registers, currently we do
not generate actual defines for the individual registers.
At the moment this is only intended to express metadata from the
architecture, and does not handle policy imposed by the kernel, such as
values exposed to userspace or VMs. In future this could be extended to
express such information.
This script was mostly written by Mark Rutland but has been extended by
Mark Brown to improve validation of input and better integrate with the
kernel.
Signed-off-by: Mark Rutland <mark.rutland@arm.com>
Co-Developed-by: Mark Brown <broonie@kernel.org>
Signed-off-by: Mark Brown <broonie@kernel.org>
Link: https://lore.kernel.org/r/20220503170233.507788-9-broonie@kernel.org
Signed-off-by: Catalin Marinas <catalin.marinas@arm.com>