Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit a919a018 authored by Suravee Suthikulpanit's avatar Suravee Suthikulpanit Committed by Joerg Roedel
Browse files

iommu/amd: Fix logic to determine and checking max PASID



In reality, the spec can only support 16-bit PASID since
INVALIDATE_IOTLB_PAGES and COMPLETE_PPR_REQUEST commands only allow 16-bit
PASID. So, we updated the PASID_MASK accordingly and invoke BUG_ON
if the hardware is reporting PASmax more than 16-bit.

Besides, max PASID is defined as ((2^(PASmax+1)) - 1). The current does not
determine this correctly.

Signed-off-by: default avatarSuravee Suthikulpanit <suravee.suthikulpanit@amd.com>
Tested-by: default avatarJay Cornwall <Jay.Cornwall@amd.com>
Signed-off-by: default avatarJoerg Roedel <joro@8bytes.org>
parent e8d2d82d
Loading
Loading
Loading
Loading
+2 −2
Original line number Diff line number Diff line
@@ -963,7 +963,7 @@ static void build_inv_iommu_pasid(struct iommu_cmd *cmd, u16 domid, int pasid,

	address &= ~(0xfffULL);

	cmd->data[0]  = pasid & PASID_MASK;
	cmd->data[0]  = pasid;
	cmd->data[1]  = domid;
	cmd->data[2]  = lower_32_bits(address);
	cmd->data[3]  = upper_32_bits(address);
@@ -1001,7 +1001,7 @@ static void build_complete_ppr(struct iommu_cmd *cmd, u16 devid, int pasid,

	cmd->data[0]  = devid;
	if (gn) {
		cmd->data[1]  = pasid & PASID_MASK;
		cmd->data[1]  = pasid;
		cmd->data[2]  = CMD_INV_IOMMU_PAGES_GN_MASK;
	}
	cmd->data[3]  = tag & 0x1ff;
+9 −7
Original line number Diff line number Diff line
@@ -150,7 +150,7 @@ int amd_iommus_present;
bool amd_iommu_np_cache __read_mostly;
bool amd_iommu_iotlb_sup __read_mostly = true;

u32 amd_iommu_max_pasids __read_mostly = ~0;
u32 amd_iommu_max_pasid __read_mostly = ~0;

bool amd_iommu_v2_present __read_mostly;
bool amd_iommu_pc_present __read_mostly;
@@ -1231,14 +1231,16 @@ static int iommu_init_pci(struct amd_iommu *iommu)

	if (iommu_feature(iommu, FEATURE_GT)) {
		int glxval;
		u32 pasids;
		u64 shift;
		u32 max_pasid;
		u64 pasmax;

		shift   = iommu->features & FEATURE_PASID_MASK;
		shift >>= FEATURE_PASID_SHIFT;
		pasids  = (1 << shift);
		pasmax = iommu->features & FEATURE_PASID_MASK;
		pasmax >>= FEATURE_PASID_SHIFT;
		max_pasid  = (1 << (pasmax + 1)) - 1;

		amd_iommu_max_pasids = min(amd_iommu_max_pasids, pasids);
		amd_iommu_max_pasid = min(amd_iommu_max_pasid, max_pasid);

		BUG_ON(amd_iommu_max_pasid & ~PASID_MASK);

		glxval   = iommu->features & FEATURE_GLXVAL_MASK;
		glxval >>= FEATURE_GLXVAL_SHIFT;
+8 −3
Original line number Diff line number Diff line
@@ -98,7 +98,12 @@
#define FEATURE_GLXVAL_SHIFT	14
#define FEATURE_GLXVAL_MASK	(0x03ULL << FEATURE_GLXVAL_SHIFT)

#define PASID_MASK		0x000fffff
/* Note:
 * The current driver only support 16-bit PASID.
 * Currently, hardware only implement upto 16-bit PASID
 * even though the spec says it could have upto 20 bits.
 */
#define PASID_MASK		0x0000ffff

/* MMIO status bits */
#define MMIO_STATUS_EVT_INT_MASK	(1 << 1)
@@ -696,8 +701,8 @@ extern unsigned long *amd_iommu_pd_alloc_bitmap;
 */
extern u32 amd_iommu_unmap_flush;

/* Smallest number of PASIDs supported by any IOMMU in the system */
extern u32 amd_iommu_max_pasids;
/* Smallest max PASID supported by any IOMMU in the system */
extern u32 amd_iommu_max_pasid;

extern bool amd_iommu_v2_present;