diff options
Diffstat (limited to 'drivers/gpu/drm/msm/msm_kms.c')
-rw-r--r-- | drivers/gpu/drm/msm/msm_kms.c | 19 |
1 files changed, 18 insertions, 1 deletions
diff --git a/drivers/gpu/drm/msm/msm_kms.c b/drivers/gpu/drm/msm/msm_kms.c index 38965e12a6bf..35d5397e73b4 100644 --- a/drivers/gpu/drm/msm/msm_kms.c +++ b/drivers/gpu/drm/msm/msm_kms.c @@ -164,12 +164,26 @@ void msm_crtc_disable_vblank(struct drm_crtc *crtc) vblank_ctrl_queue_work(priv, crtc, false); } +static int msm_kms_fault_handler(void *arg, unsigned long iova, int flags, void *data) +{ + struct msm_kms *kms = arg; + + if (atomic_read(&kms->fault_snapshot_capture) == 0) { + msm_disp_snapshot_state(kms->dev); + atomic_inc(&kms->fault_snapshot_capture); + } + + return -ENOSYS; +} + struct msm_gem_address_space *msm_kms_init_aspace(struct drm_device *dev) { struct msm_gem_address_space *aspace; struct msm_mmu *mmu; struct device *mdp_dev = dev->dev; struct device *mdss_dev = mdp_dev->parent; + struct msm_drm_private *priv = dev->dev_private; + struct msm_kms *kms = priv->kms; struct device *iommu_dev; /* @@ -181,7 +195,7 @@ struct msm_gem_address_space *msm_kms_init_aspace(struct drm_device *dev) else iommu_dev = mdss_dev; - mmu = msm_iommu_new(iommu_dev, 0); + mmu = msm_iommu_disp_new(iommu_dev, 0); if (IS_ERR(mmu)) return ERR_CAST(mmu); @@ -195,8 +209,11 @@ struct msm_gem_address_space *msm_kms_init_aspace(struct drm_device *dev) if (IS_ERR(aspace)) { dev_err(mdp_dev, "aspace create, error %pe\n", aspace); mmu->funcs->destroy(mmu); + return aspace; } + msm_mmu_set_fault_handler(aspace->mmu, kms, msm_kms_fault_handler); + return aspace; } |