On 11.07.2022 01:06, Sam Protsenko wrote: > SysMMU v7 can have Virtual Machine registers, which implement multiple > translation domains. The driver should know if it's true or not, as VM > registers shouldn't be accessed if not present. Read corresponding > capabilities register to obtain that info, and store it in driver data. > > Signed-off-by: Sam Protsenko <semen.protsenko@xxxxxxxxxx> I would merge this with the next one. Imho this change doesn't make much sense on it's own. > --- > Changes in v2: > - Removed the 'const' qualifier for local non-pointer variables > > drivers/iommu/exynos-iommu.c | 26 ++++++++++++++++++++++++++ > 1 file changed, 26 insertions(+) > > diff --git a/drivers/iommu/exynos-iommu.c b/drivers/iommu/exynos-iommu.c > index 0cb1ce10db51..48681189ccf8 100644 > --- a/drivers/iommu/exynos-iommu.c > +++ b/drivers/iommu/exynos-iommu.c > @@ -135,6 +135,9 @@ static u32 lv2ent_offset(sysmmu_iova_t iova) > #define CFG_SYSSEL (1 << 22) /* System MMU 3.2 only */ > #define CFG_FLPDCACHE (1 << 20) /* System MMU 3.2+ only */ > > +#define CAPA0_CAPA1_EXIST BIT(11) > +#define CAPA1_VCR_ENABLED BIT(14) > + > /* common registers */ > #define REG_MMU_VERSION 0x034 > > @@ -154,6 +157,10 @@ static u32 lv2ent_offset(sysmmu_iova_t iova) > #define REG_V5_FAULT_AR_VA 0x070 > #define REG_V5_FAULT_AW_VA 0x080 > > +/* v7.x registers */ > +#define REG_V7_CAPA0 0x870 > +#define REG_V7_CAPA1 0x874 > + > #define has_sysmmu(dev) (dev_iommu_priv_get(dev) != NULL) > > enum { > @@ -298,6 +305,9 @@ struct sysmmu_drvdata { > > struct iommu_device iommu; /* IOMMU core handle */ > const unsigned int *regs; /* register set */ > + > + /* v7 fields */ > + bool has_vcr; /* virtual machine control register */ > }; > > static struct exynos_iommu_domain *to_exynos_domain(struct iommu_domain *dom) > @@ -411,11 +421,27 @@ static void __sysmmu_get_version(struct sysmmu_drvdata *data) > MMU_MAJ_VER(data->version), MMU_MIN_VER(data->version)); > } > > +static bool __sysmmu_has_capa1(struct sysmmu_drvdata *data) > +{ > + u32 capa0 = readl(data->sfrbase + REG_V7_CAPA0); > + > + return capa0 & CAPA0_CAPA1_EXIST; > +} > + > +static void __sysmmu_get_vcr(struct sysmmu_drvdata *data) > +{ > + u32 capa1 = readl(data->sfrbase + REG_V7_CAPA1); > + > + data->has_vcr = capa1 & CAPA1_VCR_ENABLED; > +} > + > static void sysmmu_get_hw_info(struct sysmmu_drvdata *data) > { > __sysmmu_enable_clocks(data); > > __sysmmu_get_version(data); > + if (MMU_MAJ_VER(data->version) >= 7 && __sysmmu_has_capa1(data)) > + __sysmmu_get_vcr(data); > if (MMU_MAJ_VER(data->version) < 5) > data->regs = sysmmu_regs[REG_SET_V1]; > else Best regards -- Marek Szyprowski, PhD Samsung R&D Institute Poland