summaryrefslogtreecommitdiffstats
path: root/drivers/iommu/arm-smmu.c
diff options
context:
space:
mode:
authorRobin Murphy <robin.murphy@arm.com>2016-11-07 18:25:09 +0000
committerJoerg Roedel <jroedel@suse.de>2016-11-08 14:52:41 +0100
commit8c82d6ec5abcf9691d37f329bf5f42f6868405db (patch)
tree2f7cfe5ecec2af776e9514340a4f3e4746ad185a /drivers/iommu/arm-smmu.c
parent3c117b543528b0d25801bd75444037dd0fcd2b8d (diff)
downloadlinux-8c82d6ec5abcf9691d37f329bf5f42f6868405db.tar.gz
linux-8c82d6ec5abcf9691d37f329bf5f42f6868405db.tar.bz2
linux-8c82d6ec5abcf9691d37f329bf5f42f6868405db.zip
iommu/arm-smmu: Fix out-of-bounds dereference
When we iterate a master's config entries, what we generally care about is the entry's stream map index, rather than the entry index itself, so it's nice to have the iterator automatically assign the former from the latter. Unfortunately, booting with KASAN reveals the oversight that using a simple comma operator results in the entry index being dereferenced before being checked for validity, so we always access one element past the end of the fwspec array. Flip things around so that the check always happens before the index may be dereferenced. Fixes: adfec2e709d2 ("iommu/arm-smmu: Convert to iommu_fwspec") Reported-by: Mark Rutland <mark.rutland@arm.com> Signed-off-by: Robin Murphy <robin.murphy@arm.com> Acked-by: Will Deacon <will.deacon@arm.com> Signed-off-by: Joerg Roedel <jroedel@suse.de>
Diffstat (limited to 'drivers/iommu/arm-smmu.c')
-rw-r--r--drivers/iommu/arm-smmu.c4
1 files changed, 3 insertions, 1 deletions
diff --git a/drivers/iommu/arm-smmu.c b/drivers/iommu/arm-smmu.c
index d388629ab990..8f7281444551 100644
--- a/drivers/iommu/arm-smmu.c
+++ b/drivers/iommu/arm-smmu.c
@@ -324,8 +324,10 @@ struct arm_smmu_master_cfg {
#define INVALID_SMENDX -1
#define __fwspec_cfg(fw) ((struct arm_smmu_master_cfg *)fw->iommu_priv)
#define fwspec_smmu(fw) (__fwspec_cfg(fw)->smmu)
+#define fwspec_smendx(fw, i) \
+ (i >= fw->num_ids ? INVALID_SMENDX : __fwspec_cfg(fw)->smendx[i])
#define for_each_cfg_sme(fw, i, idx) \
- for (i = 0; idx = __fwspec_cfg(fw)->smendx[i], i < fw->num_ids; ++i)
+ for (i = 0; idx = fwspec_smendx(fw, i), i < fw->num_ids; ++i)
struct arm_smmu_device {
struct device *dev;