mirror of
https://github.com/torvalds/linux.git
synced 2026-09-23 05:04:02 +02:00
iommu/arm-smmu-v3: Support IDR5.DS and widen the TLBI SCALE field
An SMMU implementing SMMU_IDR5.DS extends the range invalidation commands: the SCALE field grows a 6th bit, raising its maximum value from 31 to 39, and TTL == 0b01 becomes a valid level hint for a 16KB translation granule. Add a new ARM_SMMU_FEAT_DS feature detecting the DS bit, and widen the CMDQ_TLBI_0_SCALE field to its architectural 6 bits. Mask the scale value explicitly in arm_smmu_cmdq_batch_add_range(), so the range invalidation path emits the same commands as before, keeping the pre-existing 5-bit truncation of a scale above 31. Also list DS as a valid IDR5 field in the iommu_hw_info_arm_smmuv3 kdoc: iommufd has always reported the raw IDR5 register, so a VMM may conclude from that bit alone that it can expose DS to its guest. Suggested-by: Jason Gunthorpe <jgg@nvidia.com> Reviewed-by: Jason Gunthorpe <jgg@nvidia.com> Reviewed-by: Pranjal Shrivastava <praan@google.com> Assisted-by: Claude:claude-fable-5 Signed-off-by: Nicolin Chen <nicolinc@nvidia.com> Signed-off-by: Will Deacon <will@kernel.org>
This commit is contained in:
parent
eced8058c8
commit
773f2b9e36
|
|
@ -2511,9 +2511,10 @@ static void arm_smmu_cmdq_batch_add_range(struct arm_smmu_device *smmu,
|
|||
/* Determine how many chunks of 2^scale size we have */
|
||||
num = (num_pages >> scale) & CMDQ_TLBI_RANGE_NUM_MAX;
|
||||
|
||||
/* Keep the pre-DS 5-bit truncation when scale > 31 */
|
||||
cmd->data[0] = orig_data0 |
|
||||
FIELD_PREP(CMDQ_TLBI_0_NUM, num - 1) |
|
||||
FIELD_PREP(CMDQ_TLBI_0_SCALE, scale);
|
||||
FIELD_PREP(CMDQ_TLBI_0_SCALE, scale & 0x1f);
|
||||
|
||||
/* range is num * 2^scale * pgsize */
|
||||
inv_range = num << (scale + tg);
|
||||
|
|
@ -5197,6 +5198,9 @@ static int arm_smmu_device_hw_probe(struct arm_smmu_device *smmu)
|
|||
/* Maximum number of outstanding stalls */
|
||||
smmu->evtq.max_stalls = FIELD_GET(IDR5_STALL_MAX, reg);
|
||||
|
||||
if (reg & IDR5_DS)
|
||||
smmu->features |= ARM_SMMU_FEAT_DS;
|
||||
|
||||
/* Page sizes */
|
||||
if (reg & IDR5_GRAN64K)
|
||||
smmu->pgsize_bitmap |= SZ_64K | SZ_512M;
|
||||
|
|
|
|||
|
|
@ -65,6 +65,7 @@ struct arm_vsmmu;
|
|||
|
||||
#define ARM_SMMU_IDR5 0x14
|
||||
#define IDR5_STALL_MAX GENMASK(31, 16)
|
||||
#define IDR5_DS (1 << 7)
|
||||
#define IDR5_GRAN64K (1 << 6)
|
||||
#define IDR5_GRAN16K (1 << 5)
|
||||
#define IDR5_GRAN4K (1 << 4)
|
||||
|
|
@ -417,7 +418,7 @@ struct arm_smmu_cmd {
|
|||
|
||||
#define CMDQ_TLBI_0_NUM GENMASK_ULL(16, 12)
|
||||
#define CMDQ_TLBI_RANGE_NUM_MAX 31
|
||||
#define CMDQ_TLBI_0_SCALE GENMASK_ULL(24, 20)
|
||||
#define CMDQ_TLBI_0_SCALE GENMASK_ULL(25, 20)
|
||||
#define CMDQ_TLBI_0_VMID GENMASK_ULL(47, 32)
|
||||
#define CMDQ_TLBI_0_ASID GENMASK_ULL(63, 48)
|
||||
#define CMDQ_TLBI_1_LEAF (1UL << 0)
|
||||
|
|
@ -925,6 +926,7 @@ struct arm_smmu_device {
|
|||
#define ARM_SMMU_FEAT_S2FWB (1 << 23)
|
||||
#define ARM_SMMU_FEAT_BBML2 (1 << 24)
|
||||
#define ARM_SMMU_FEAT_HAFT (1 << 25)
|
||||
#define ARM_SMMU_FEAT_DS (1 << 26)
|
||||
u32 features;
|
||||
|
||||
#define ARM_SMMU_OPT_SKIP_PREFETCH (1 << 0)
|
||||
|
|
|
|||
|
|
@ -605,7 +605,7 @@ enum iommu_hw_info_arm_smmuv3_flags {
|
|||
* idr[0]: ST_LEVEL, TERM_MODEL, STALL_MODEL, TTENDIAN , CD2L, ASID16, TTF
|
||||
* idr[1]: SIDSIZE, SSIDSIZE
|
||||
* idr[3]: BBML, RIL
|
||||
* idr[5]: VAX, GRAN64K, GRAN16K, GRAN4K
|
||||
* idr[5]: VAX, GRAN64K, GRAN16K, GRAN4K, DS
|
||||
*
|
||||
* - S1P should be assumed to be true if a NESTED HWPT can be created
|
||||
* - VFIO/iommufd only support platforms with COHACC, it should be assumed to be
|
||||
|
|
@ -613,7 +613,7 @@ enum iommu_hw_info_arm_smmuv3_flags {
|
|||
* - ATS is a per-device property. If the VMM describes any devices as ATS
|
||||
* capable in ACPI/DT it should set the corresponding idr.
|
||||
*
|
||||
* This list may expand in future (eg E0PD, AIE, PBHA, D128, DS etc). It is
|
||||
* This list may expand in future (eg E0PD, AIE, PBHA, D128 etc). It is
|
||||
* important that VMMs do not read bits outside the list to allow for
|
||||
* compatibility with future kernels. Several features in the SMMUv3
|
||||
* architecture are not currently supported by the kernel for nesting: HTTU,
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user