diff --git a/drivers/accel/rocket/rocket_drv.c b/drivers/accel/rocket/rocket_drv.c index d08aa04b71475bdd5a707e15a2854b5dd5d09130..f0ca0417c96a1fb3242c5d6757322c4298c7ab6e 100644 --- a/drivers/accel/rocket/rocket_drv.c +++ b/drivers/accel/rocket/rocket_drv.c @@ -12,6 +12,7 @@ #include <linux/module.h> #include <linux/platform_device.h> #include <linux/pm_runtime.h> +#include <linux/iommu.h> #include <drm/drm_drv.h> #include <drm/drm_ioctl.h> #include <drm/drm_accel.h> @@ -327,6 +328,10 @@ static int rocket_device_runtime_resume(struct device *dev) for (unsigned int core = 0; core < rdev->num_cores; core++) { printk("*** %s: %d core %d\n", __func__, 2, core); + + struct iommu_domain *domain = iommu_get_domain_for_dev(rdev->cores[core].dev); + iommu_attach_device(domain, rdev->cores[core].dev); + clk_prepare_enable(rdev->cores[core].a_clk); clk_prepare_enable(rdev->cores[core].h_clk); } @@ -350,6 +355,9 @@ static int rocket_device_runtime_suspend(struct device *dev) clk_disable_unprepare(rdev->cores[core].a_clk); clk_disable_unprepare(rdev->cores[core].h_clk); + + struct iommu_domain *domain = iommu_get_domain_for_dev(rdev->cores[core].dev); + iommu_detach_device(domain, rdev->cores[core].dev); } clk_disable_unprepare(rdev->pclk); diff --git a/drivers/accel/rocket/rocket_gem.c b/drivers/accel/rocket/rocket_gem.c index afacdf91491e5314a31ff861ae194944f8d68416..41a94206bd5d008e0840af3d9e22e96f7e208420 100644 --- a/drivers/accel/rocket/rocket_gem.c +++ b/drivers/accel/rocket/rocket_gem.c @@ -7,6 +7,7 @@ #include <linux/dma-mapping.h> #include "rocket_gem.h" +#include "rocket_device.h" /** * rocket_gem_create_object - Implementation of driver->gem_create_object. @@ -30,12 +31,15 @@ struct drm_gem_object *rocket_gem_create_object(struct drm_device *dev, size_t s int rocket_ioctl_create_bo(struct drm_device *dev, void *data, struct drm_file *file) { struct drm_rocket_create_bo *args = data; + struct rocket_device *rdev = dev->dev_private; struct drm_gem_shmem_object *shmem_obj; struct rocket_gem_object *rkt_obj; struct drm_gem_object *gem_obj; struct sg_table *sgt; int ret; + printk("*** %s: %d\n", __func__, 1); + shmem_obj = drm_gem_shmem_create(dev, args->size); if (IS_ERR(shmem_obj)) return PTR_ERR(shmem_obj); @@ -52,15 +56,22 @@ int rocket_ioctl_create_bo(struct drm_device *dev, void *data, struct drm_file * if (ret) goto err; + printk("*** %s: %d before drm_gem_shmem_get_pages_sgt\n", __func__, 1); sgt = drm_gem_shmem_get_pages_sgt(shmem_obj); if (IS_ERR(sgt)) { ret = PTR_ERR(sgt); goto err; } + ret = dma_map_sgtable(rdev->cores[1].dev, sgt, DMA_BIDIRECTIONAL, 0); + ret = dma_map_sgtable(rdev->cores[2].dev, sgt, DMA_BIDIRECTIONAL, 0); + printk("*** %s: %d after drm_gem_shmem_get_pages_sgt\n", __func__, 1); + args->offset = drm_vma_node_offset_addr(&gem_obj->vma_node); args->dma_address = sg_dma_address(shmem_obj->sgt->sgl); + printk("*** %s: %d\n", __func__, 99); + return 0; err: @@ -83,11 +94,14 @@ int rocket_ioctl_prep_bo(struct drm_device *dev, void *data, struct drm_file *fi { struct drm_rocket_prep_bo *args = data; unsigned long timeout = drm_timeout_abs_to_jiffies(args->timeout_ns); + struct rocket_device *rdev = dev->dev_private; struct drm_gem_object *gem_obj; struct drm_gem_shmem_object *shmem_obj; bool write = !!(args->op & ROCKET_PREP_WRITE); long ret = 0; + printk("*** %s: %d\n", __func__, 1); + if (args->op & ~(ROCKET_PREP_READ | ROCKET_PREP_WRITE)) return -EINVAL; @@ -102,11 +116,16 @@ int rocket_ioctl_prep_bo(struct drm_device *dev, void *data, struct drm_file *fi shmem_obj = &to_rocket_bo(gem_obj)->base; - dma_sync_sgtable_for_cpu(dev->dev, shmem_obj->sgt, rocket_op_to_dma_dir(args->op)); + dma_sync_sgtable_for_cpu(rdev->cores[0].dev, shmem_obj->sgt, rocket_op_to_dma_dir(args->op)); + dma_sync_sgtable_for_cpu(rdev->cores[1].dev, shmem_obj->sgt, rocket_op_to_dma_dir(args->op)); + dma_sync_sgtable_for_cpu(rdev->cores[2].dev, shmem_obj->sgt, rocket_op_to_dma_dir(args->op)); + to_rocket_bo(gem_obj)->last_cpu_prep_op = args->op; drm_gem_object_put(gem_obj); + printk("*** %s: %d\n", __func__, 99); + return ret; } @@ -116,6 +135,9 @@ int rocket_ioctl_fini_bo(struct drm_device *dev, void *data, struct drm_file *fi struct drm_gem_object *gem_obj; struct rocket_gem_object *rkt_obj; struct drm_gem_shmem_object *shmem_obj; + struct rocket_device *rdev = dev->dev_private; + + printk("*** %s: %d\n", __func__, 1); gem_obj = drm_gem_object_lookup(file, args->handle); if (!gem_obj) @@ -126,11 +148,18 @@ int rocket_ioctl_fini_bo(struct drm_device *dev, void *data, struct drm_file *fi WARN_ON(rkt_obj->last_cpu_prep_op == 0); - dma_sync_sgtable_for_device(dev->dev, shmem_obj->sgt, + dma_sync_sgtable_for_device(rdev->cores[0].dev, shmem_obj->sgt, + rocket_op_to_dma_dir(rkt_obj->last_cpu_prep_op)); + dma_sync_sgtable_for_device(rdev->cores[1].dev, shmem_obj->sgt, + rocket_op_to_dma_dir(rkt_obj->last_cpu_prep_op)); + dma_sync_sgtable_for_device(rdev->cores[2].dev, shmem_obj->sgt, rocket_op_to_dma_dir(rkt_obj->last_cpu_prep_op)); + rkt_obj->last_cpu_prep_op = 0; drm_gem_object_put(gem_obj); + printk("*** %s: %d\n", __func__, 99); + return 0; } diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c index ed6c5cb60c5aeecff72490e037a70d9fba0553ce..6d28fae79e0e48e1cc4980ea634cabc06b698144 100644 --- a/drivers/iommu/iommu.c +++ b/drivers/iommu/iommu.c @@ -2106,6 +2106,8 @@ int iommu_attach_device(struct iommu_domain *domain, struct device *dev) struct iommu_group *group = dev->iommu_group; int ret; + printk("*** %s: %d %s domain %px\n", __func__, 1, dev_name(dev), domain); + if (!group) return -ENODEV; @@ -2122,6 +2124,8 @@ int iommu_attach_device(struct iommu_domain *domain, struct device *dev) out_unlock: mutex_unlock(&group->mutex); + + printk("*** %s: %d %s domain %px\n", __func__, 99, dev_name(dev), domain); return ret; } EXPORT_SYMBOL_GPL(iommu_attach_device); diff --git a/drivers/iommu/rockchip-iommu.c b/drivers/iommu/rockchip-iommu.c index 673b0ebb62628db0207d3ccd122927dc9fd7d9c7..0f1c68271d38d645d80046521adfcf46ad41bacb 100644 --- a/drivers/iommu/rockchip-iommu.c +++ b/drivers/iommu/rockchip-iommu.c @@ -504,6 +504,8 @@ static int rk_iommu_force_reset(struct rk_iommu *iommu) u32 dte_addr; bool val; + printk("*** %s: %s\n", __func__, dev_name(iommu->dev)); + if (iommu->reset_disabled) return 0; @@ -831,6 +833,8 @@ static int rk_iommu_map(struct iommu_domain *domain, unsigned long _iova, u32 dte_index, pte_index; int ret; + printk("*** %s: domain %px\n", __func__, domain); + spin_lock_irqsave(&rk_domain->dt_lock, flags); /* @@ -872,6 +876,8 @@ static size_t rk_iommu_unmap(struct iommu_domain *domain, unsigned long _iova, u32 *pte_addr; size_t unmap_size; + printk("*** %s: domain %px\n", __func__, domain); + spin_lock_irqsave(&rk_domain->dt_lock, flags); /* @@ -913,6 +919,8 @@ static void rk_iommu_disable(struct rk_iommu *iommu) { int i; + printk("*** %s: %s\n", __func__, dev_name(iommu->dev)); + /* Ignore error while disabling, just keep going */ WARN_ON(clk_bulk_enable(iommu->num_clocks, iommu->clocks)); rk_iommu_enable_stall(iommu); @@ -932,6 +940,9 @@ static int rk_iommu_enable(struct rk_iommu *iommu) struct rk_iommu_domain *rk_domain = to_rk_domain(domain); int ret, i; + printk("*** %s: %s\n", __func__, dev_name(iommu->dev)); + //WARN(1, ""); + ret = clk_bulk_enable(iommu->num_clocks, iommu->clocks); if (ret) return ret; @@ -973,6 +984,8 @@ static int rk_iommu_identity_attach(struct iommu_domain *identity_domain, if (!iommu) return -ENODEV; + printk("*** %s: dev %s domain %px iommu %s\n", __func__, dev_name(dev), identity_domain, dev_name(iommu->dev)); + rk_domain = to_rk_domain(iommu->domain); dev_dbg(dev, "Detaching from iommu domain\n"); @@ -1021,6 +1034,8 @@ static int rk_iommu_attach_device(struct iommu_domain *domain, if (!iommu) return 0; + printk("*** %s: dev %s domain %px iommu %s\n", __func__, dev_name(dev), domain, dev_name(iommu->dev)); + dev_dbg(dev, "Attaching to iommu domain\n"); /* iommu already attached */ @@ -1061,6 +1076,8 @@ static struct iommu_domain *rk_iommu_domain_alloc_paging(struct device *dev) if (!rk_domain) return NULL; + printk("*** %s: dev %s &rk_domain->domain %px\n", __func__, dev_name(dev), &rk_domain->domain); + /* * rk32xx iommus use a 2 level pagetable. * Each level1 (dt) and level2 (pt) table has 1024 4-byte entries.