diff --git a/drivers/gpu/nvgpu/os/linux/ioctl_ctrl.c b/drivers/gpu/nvgpu/os/linux/ioctl_ctrl.c index 2c9c51373..9549a4195 100644 --- a/drivers/gpu/nvgpu/os/linux/ioctl_ctrl.c +++ b/drivers/gpu/nvgpu/os/linux/ioctl_ctrl.c @@ -1943,7 +1943,6 @@ int gk20a_ctrl_dev_mmap(struct file *filp, struct vm_area_struct *vma) struct gk20a_ctrl_priv *priv = filp->private_data; struct gk20a *g = priv->g; struct nvgpu_os_linux *l = nvgpu_os_linux_from_gk20a(g); - u64 addr; int err; if (g->ops.fifo.usermode_base == NULL) @@ -1958,8 +1957,6 @@ int gk20a_ctrl_dev_mmap(struct file *filp, struct vm_area_struct *vma) if (vma->vm_pgoff != 0UL) return -EINVAL; - addr = l->regs_bus_addr + g->ops.fifo.usermode_base(g); - /* Sync with poweron/poweroff, and require valid regs */ err = gk20a_busy(g); if (err) { @@ -1973,7 +1970,8 @@ int gk20a_ctrl_dev_mmap(struct file *filp, struct vm_area_struct *vma) vma->vm_ops = &usermode_vma_ops; vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot); - err = io_remap_pfn_range(vma, vma->vm_start, addr >> PAGE_SHIFT, + err = io_remap_pfn_range(vma, vma->vm_start, + l->usermode_regs_bus_addr >> PAGE_SHIFT, vma->vm_end - vma->vm_start, vma->vm_page_prot); if (!err) { priv->usermode_vma.vma = vma; @@ -1993,7 +1991,6 @@ static void alter_usermode_mapping(struct gk20a *g, { struct nvgpu_os_linux *l = nvgpu_os_linux_from_gk20a(g); struct vm_area_struct *vma = priv->usermode_vma.vma; - u64 addr; int err; if (!vma) { @@ -2001,8 +1998,6 @@ static void alter_usermode_mapping(struct gk20a *g, return; } - addr = l->regs_bus_addr + g->ops.fifo.usermode_base(g); - down_write(&vma->vm_mm->mmap_sem); if (poweroff) { @@ -2015,7 +2010,7 @@ static void alter_usermode_mapping(struct gk20a *g, } else { vma->vm_flags = priv->usermode_vma.flags; err = io_remap_pfn_range(vma, vma->vm_start, - addr >> PAGE_SHIFT, + l->usermode_regs_bus_addr >> PAGE_SHIFT, SZ_4K, vma->vm_page_prot); if (err != 0) { nvgpu_err(g, "can't restore usermode mapping"); diff --git a/drivers/gpu/nvgpu/os/linux/module.c b/drivers/gpu/nvgpu/os/linux/module.c index 1054819fc..823f92cc6 100644 --- a/drivers/gpu/nvgpu/os/linux/module.c +++ b/drivers/gpu/nvgpu/os/linux/module.c @@ -286,6 +286,16 @@ int gk20a_pm_finalize_poweron(struct device *dev) if (err) goto done; + if (g->ops.fifo.usermode_base != NULL) { + /* + * Native has regs_bus_addr set but not this one yet. Virtual + * gets usermode_regs_bus_addr directly from chip-specific + * probe, and regs_bus_addr stays unset. + */ + l->usermode_regs_bus_addr = l->regs_bus_addr + + g->ops.fifo.usermode_base(g); + } + err = nvgpu_finalize_poweron_linux(l); if (err) goto done; diff --git a/drivers/gpu/nvgpu/os/linux/os_linux.h b/drivers/gpu/nvgpu/os/linux/os_linux.h index 5880384a0..393180327 100644 --- a/drivers/gpu/nvgpu/os/linux/os_linux.h +++ b/drivers/gpu/nvgpu/os/linux/os_linux.h @@ -124,6 +124,7 @@ struct nvgpu_os_linux { struct resource *reg_mem; void __iomem *regs; void __iomem *regs_saved; + u64 regs_bus_addr; struct resource *bar1_mem; void __iomem *bar1; @@ -131,8 +132,7 @@ struct nvgpu_os_linux { void __iomem *usermode_regs; void __iomem *usermode_regs_saved; - - u64 regs_bus_addr; + u64 usermode_regs_bus_addr; struct nvgpu_os_linux_ops ops; diff --git a/drivers/gpu/nvgpu/os/linux/vgpu/gv11b/platform_gv11b_vgpu_tegra.c b/drivers/gpu/nvgpu/os/linux/vgpu/gv11b/platform_gv11b_vgpu_tegra.c index fa060847d..252ab4876 100644 --- a/drivers/gpu/nvgpu/os/linux/vgpu/gv11b/platform_gv11b_vgpu_tegra.c +++ b/drivers/gpu/nvgpu/os/linux/vgpu/gv11b/platform_gv11b_vgpu_tegra.c @@ -49,6 +49,8 @@ static int gv11b_vgpu_probe(struct device *dev) } l->usermode_regs = regs; + l->usermode_regs_bus_addr = r->start; + #ifdef CONFIG_TEGRA_GK20A_NVHOST ret = nvgpu_get_nvhost_dev(g); if (ret) {