Commit 3e2a590a authored by Linus Torvalds's avatar Linus Torvalds
Browse files
Pull iommu fixes from Will Deacon:
 "This is mainly all Intel VT-D stuff, but there are some fixes for AMD
  and ARM as well.

  We've also got the revert I promised during the merge window, which
  removes a temporary hack to accomodate i915 while we transitioned the
  Intel IOMMU driver over to the common DMA-IOMMU API.

  Finally, there are still a couple of other VT-D fixes floating around,
  so I expect to send you another batch of fixes next week.

  Summary:

   - Fix VT-D TLB invalidation for subdevices

   - Fix VT-D use-after-free on subdevice detach

   - Fix VT-D locking so that IRQs are disabled during SVA bind/unbind

   - Fix VT-D address alignment when flushing IOTLB

   - Fix memory leak in VT-D IRQ remapping failure path

   - Revert temporary i915 sglist hack now that it is no longer required

   - Fix sporadic boot failure with Arm SMMU on Qualcomm SM8150

   - Fix NULL dereference in AMD IRQ remapping code with remapping disabled

   - Fix accidental enabling of irqs on AMD resume-from-suspend path

   - Fix some typos in comments"

* tag 'iommu-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/arm64/linux:
  iommu/vt-d: Fix ineffective devTLB invalidation for subdevices
  iommu/vt-d: Fix general protection fault in aux_detach_device()
  iommu/vt-d: Move intel_iommu info from struct intel_svm to struct intel_svm_dev
  iommu/arm-smmu-qcom: Initialize SCTLR of the bypass context
  iommu/vt-d: Fix lockdep splat in sva bind()/unbind()
  Revert "iommu: Add quirk for Intel graphic devices in map_sg"
  iommu/vt-d: Fix misuse of ALIGN in qi_flush_piotlb()
  iommu/amd: Stop irq_remapping_select() matching when remapping is disabled
  iommu/amd: Set iommu->int_enabled consistently when interrupts are set up
  iommu/intel: Fix memleak in intel_irq_remapping_alloc
  iommu/iova: fix 'domain' typos
parents 95f05058 7c29ada5
Loading
Loading
Loading
Loading
+1 −2
Original line number Diff line number Diff line
@@ -1973,8 +1973,6 @@ static int iommu_setup_msi(struct amd_iommu *iommu)
		return r;
	}

	iommu->int_enabled = true;

	return 0;
}

@@ -2169,6 +2167,7 @@ static int iommu_init_irq(struct amd_iommu *iommu)
	if (ret)
		return ret;

	iommu->int_enabled = true;
enable_faults:
	iommu_feature_enable(iommu, CONTROL_EVT_INT_EN);

+3 −0
Original line number Diff line number Diff line
@@ -3854,6 +3854,9 @@ static int irq_remapping_select(struct irq_domain *d, struct irq_fwspec *fwspec,
	struct amd_iommu *iommu;
	int devid = -1;

	if (!amd_iommu_irq_remap)
		return 0;

	if (x86_fwspec_is_ioapic(fwspec))
		devid = get_ioapic_devid(fwspec->param[0]);
	else if (x86_fwspec_is_hpet(fwspec))
+2 −0
Original line number Diff line number Diff line
@@ -196,6 +196,8 @@ static int qcom_smmu_cfg_probe(struct arm_smmu_device *smmu)

		set_bit(qsmmu->bypass_cbndx, smmu->context_map);

		arm_smmu_cb_write(smmu, qsmmu->bypass_cbndx, ARM_SMMU_CB_SCTLR, 0);

		reg = FIELD_PREP(ARM_SMMU_CBAR_TYPE, CBAR_TYPE_S1_TRANS_S2_BYPASS);
		arm_smmu_gr1_write(smmu, ARM_SMMU_GR1_CBAR(qsmmu->bypass_cbndx), reg);
	}
+0 −27
Original line number Diff line number Diff line
@@ -863,33 +863,6 @@ static int __finalise_sg(struct device *dev, struct scatterlist *sg, int nents,
	unsigned int cur_len = 0, max_len = dma_get_max_seg_size(dev);
	int i, count = 0;

	/*
	 * The Intel graphic driver is used to assume that the returned
	 * sg list is not combound. This blocks the efforts of converting
	 * Intel IOMMU driver to dma-iommu api's. Add this quirk to make the
	 * device driver work and should be removed once it's fixed in i915
	 * driver.
	 */
	if (IS_ENABLED(CONFIG_DRM_I915) && dev_is_pci(dev) &&
	    to_pci_dev(dev)->vendor == PCI_VENDOR_ID_INTEL &&
	    (to_pci_dev(dev)->class >> 16) == PCI_BASE_CLASS_DISPLAY) {
		for_each_sg(sg, s, nents, i) {
			unsigned int s_iova_off = sg_dma_address(s);
			unsigned int s_length = sg_dma_len(s);
			unsigned int s_iova_len = s->length;

			s->offset += s_iova_off;
			s->length = s_length;
			sg_dma_address(s) = dma_addr + s_iova_off;
			sg_dma_len(s) = s_length;
			dma_addr += s_iova_len;

			pr_info_once("sg combining disabled due to i915 driver\n");
		}

		return nents;
	}

	for_each_sg(sg, s, nents, i) {
		/* Restore this segment's original unaligned fields first */
		unsigned int s_iova_off = sg_dma_address(s);
+2 −2
Original line number Diff line number Diff line
@@ -1461,8 +1461,8 @@ void qi_flush_piotlb(struct intel_iommu *iommu, u16 did, u32 pasid, u64 addr,
		int mask = ilog2(__roundup_pow_of_two(npages));
		unsigned long align = (1ULL << (VTD_PAGE_SHIFT + mask));

		if (WARN_ON_ONCE(!ALIGN(addr, align)))
			addr &= ~(align - 1);
		if (WARN_ON_ONCE(!IS_ALIGNED(addr, align)))
			addr = ALIGN_DOWN(addr, align);

		desc.qw0 = QI_EIOTLB_PASID(pasid) |
				QI_EIOTLB_DID(did) |
Loading