diff options
Diffstat (limited to 'drivers/gpu/drm/tegra')
| -rw-r--r-- | drivers/gpu/drm/tegra/dpaux.c | 39 | ||||
| -rw-r--r-- | drivers/gpu/drm/tegra/drm.c | 13 | ||||
| -rw-r--r-- | drivers/gpu/drm/tegra/gem.c | 25 | 
3 files changed, 36 insertions, 41 deletions
| diff --git a/drivers/gpu/drm/tegra/dpaux.c b/drivers/gpu/drm/tegra/dpaux.c index d6b55e3e3716..07b26972f487 100644 --- a/drivers/gpu/drm/tegra/dpaux.c +++ b/drivers/gpu/drm/tegra/dpaux.c @@ -56,15 +56,14 @@ static inline struct tegra_dpaux *work_to_dpaux(struct work_struct *work)  	return container_of(work, struct tegra_dpaux, work);  } -static inline unsigned long tegra_dpaux_readl(struct tegra_dpaux *dpaux, -					      unsigned long offset) +static inline u32 tegra_dpaux_readl(struct tegra_dpaux *dpaux, +				    unsigned long offset)  {  	return readl(dpaux->regs + (offset << 2));  }  static inline void tegra_dpaux_writel(struct tegra_dpaux *dpaux, -				      unsigned long value, -				      unsigned long offset) +				      u32 value, unsigned long offset)  {  	writel(value, dpaux->regs + (offset << 2));  } @@ -72,34 +71,32 @@ static inline void tegra_dpaux_writel(struct tegra_dpaux *dpaux,  static void tegra_dpaux_write_fifo(struct tegra_dpaux *dpaux, const u8 *buffer,  				   size_t size)  { -	unsigned long offset = DPAUX_DP_AUXDATA_WRITE(0);  	size_t i, j; -	for (i = 0; i < size; i += 4) { -		size_t num = min_t(size_t, size - i, 4); -		unsigned long value = 0; +	for (i = 0; i < DIV_ROUND_UP(size, 4); i++) { +		size_t num = min_t(size_t, size - i * 4, 4); +		u32 value = 0;  		for (j = 0; j < num; j++) -			value |= buffer[i + j] << (j * 8); +			value |= buffer[i * 4 + j] << (j * 8); -		tegra_dpaux_writel(dpaux, value, offset++); +		tegra_dpaux_writel(dpaux, value, DPAUX_DP_AUXDATA_WRITE(i));  	}  }  static void tegra_dpaux_read_fifo(struct tegra_dpaux *dpaux, u8 *buffer,  				  size_t size)  { -	unsigned long offset = DPAUX_DP_AUXDATA_READ(0);  	size_t i, j; -	for (i = 0; i < size; i += 4) { -		size_t num = min_t(size_t, size - i, 4); -		unsigned long value; +	for (i = 0; i < DIV_ROUND_UP(size, 4); i++) { +		size_t num = min_t(size_t, size - i * 4, 4); +		u32 value; -		value = tegra_dpaux_readl(dpaux, offset++); +		value = tegra_dpaux_readl(dpaux, DPAUX_DP_AUXDATA_READ(i));  		for (j = 0; j < num; j++) -			buffer[i + j] = value >> (j * 8); +			buffer[i * 4 + j] = value >> (j * 8);  	}  } @@ -250,7 +247,7 @@ static irqreturn_t tegra_dpaux_irq(int irq, void *data)  {  	struct tegra_dpaux *dpaux = data;  	irqreturn_t ret = IRQ_HANDLED; -	unsigned long value; +	u32 value;  	/* clear interrupts */  	value = tegra_dpaux_readl(dpaux, DPAUX_INTR_AUX); @@ -273,7 +270,7 @@ static int tegra_dpaux_probe(struct platform_device *pdev)  {  	struct tegra_dpaux *dpaux;  	struct resource *regs; -	unsigned long value; +	u32 value;  	int err;  	dpaux = devm_kzalloc(&pdev->dev, sizeof(*dpaux), GFP_KERNEL); @@ -465,7 +462,7 @@ int tegra_dpaux_detach(struct tegra_dpaux *dpaux)  enum drm_connector_status tegra_dpaux_detect(struct tegra_dpaux *dpaux)  { -	unsigned long value; +	u32 value;  	value = tegra_dpaux_readl(dpaux, DPAUX_DP_AUXSTAT); @@ -477,7 +474,7 @@ enum drm_connector_status tegra_dpaux_detect(struct tegra_dpaux *dpaux)  int tegra_dpaux_enable(struct tegra_dpaux *dpaux)  { -	unsigned long value; +	u32 value;  	value = DPAUX_HYBRID_PADCTL_AUX_CMH(2) |  		DPAUX_HYBRID_PADCTL_AUX_DRVZ(4) | @@ -495,7 +492,7 @@ int tegra_dpaux_enable(struct tegra_dpaux *dpaux)  int tegra_dpaux_disable(struct tegra_dpaux *dpaux)  { -	unsigned long value; +	u32 value;  	value = tegra_dpaux_readl(dpaux, DPAUX_HYBRID_SPARE);  	value |= DPAUX_HYBRID_SPARE_PAD_POWER_DOWN; diff --git a/drivers/gpu/drm/tegra/drm.c b/drivers/gpu/drm/tegra/drm.c index 1833abd7d3aa..427f50c6803c 100644 --- a/drivers/gpu/drm/tegra/drm.c +++ b/drivers/gpu/drm/tegra/drm.c @@ -124,14 +124,22 @@ static int tegra_drm_load(struct drm_device *drm, unsigned long flags)  		return -ENOMEM;  	if (iommu_present(&platform_bus_type)) { +		struct iommu_domain_geometry *geometry; +		u64 start, end; +  		tegra->domain = iommu_domain_alloc(&platform_bus_type);  		if (!tegra->domain) {  			err = -ENOMEM;  			goto free;  		} -		DRM_DEBUG("IOMMU context initialized\n"); -		drm_mm_init(&tegra->mm, 0, SZ_2G); +		geometry = &tegra->domain->geometry; +		start = geometry->aperture_start; +		end = geometry->aperture_end; + +		DRM_DEBUG("IOMMU context initialized (aperture: %#llx-%#llx)\n", +			  start, end); +		drm_mm_init(&tegra->mm, start, end - start + 1);  	}  	mutex_init(&tegra->clients_lock); @@ -173,7 +181,6 @@ static int tegra_drm_load(struct drm_device *drm, unsigned long flags)  	drm->irq_enabled = true;  	/* syncpoints are used for full 32-bit hardware VBLANK counters */ -	drm->vblank_disable_immediate = true;  	drm->max_vblank_count = 0xffffffff;  	err = drm_vblank_init(drm, drm->mode_config.num_crtc); diff --git a/drivers/gpu/drm/tegra/gem.c b/drivers/gpu/drm/tegra/gem.c index 1217272a51f2..01e16e146bfe 100644 --- a/drivers/gpu/drm/tegra/gem.c +++ b/drivers/gpu/drm/tegra/gem.c @@ -189,7 +189,6 @@ static void tegra_bo_free(struct drm_device *drm, struct tegra_bo *bo)  static int tegra_bo_get_pages(struct drm_device *drm, struct tegra_bo *bo)  {  	struct scatterlist *s; -	struct sg_table *sgt;  	unsigned int i;  	bo->pages = drm_gem_get_pages(&bo->gem); @@ -198,36 +197,28 @@ static int tegra_bo_get_pages(struct drm_device *drm, struct tegra_bo *bo)  	bo->num_pages = bo->gem.size >> PAGE_SHIFT; -	sgt = drm_prime_pages_to_sg(bo->pages, bo->num_pages); -	if (IS_ERR(sgt)) +	bo->sgt = drm_prime_pages_to_sg(bo->pages, bo->num_pages); +	if (IS_ERR(bo->sgt))  		goto put_pages;  	/* -	 * Fake up the SG table so that dma_map_sg() can be used to flush the -	 * pages associated with it. Note that this relies on the fact that -	 * the DMA API doesn't hook into IOMMU on Tegra, therefore mapping is -	 * only cache maintenance. +	 * Fake up the SG table so that dma_sync_sg_for_device() can be used +	 * to flush the pages associated with it.  	 *  	 * TODO: Replace this by drm_clflash_sg() once it can be implemented  	 * without relying on symbols that are not exported.  	 */ -	for_each_sg(sgt->sgl, s, sgt->nents, i) +	for_each_sg(bo->sgt->sgl, s, bo->sgt->nents, i)  		sg_dma_address(s) = sg_phys(s); -	if (dma_map_sg(drm->dev, sgt->sgl, sgt->nents, DMA_TO_DEVICE) == 0) -		goto release_sgt; - -	bo->sgt = sgt; +	dma_sync_sg_for_device(drm->dev, bo->sgt->sgl, bo->sgt->nents, +			       DMA_TO_DEVICE);  	return 0; -release_sgt: -	sg_free_table(sgt); -	kfree(sgt); -	sgt = ERR_PTR(-ENOMEM);  put_pages:  	drm_gem_put_pages(&bo->gem, bo->pages, false, false); -	return PTR_ERR(sgt); +	return PTR_ERR(bo->sgt);  }  static int tegra_bo_alloc(struct drm_device *drm, struct tegra_bo *bo) | 
