[RFC] etnaviv: missing dma_mask

Guido Günther agx at sigxcpu.org
Fri Aug 24 12:04:36 UTC 2018


Hi,
(shortened the cc: list a bit)

On Thu, Aug 23, 2018 at 10:54:16AM +0200, Lucas Stach wrote:
> Am Freitag, den 17.08.2018, 08:42 +0200 schrieb Christoph Hellwig:
> > On Tue, Aug 14, 2018 at 05:12:25PM +0300, Eugeniy Paltsev wrote:
> > > Hi Lucas, Christoph,
> > > 
> > > After switching ARC to generic dma_noncoherent cache ops 
> > > etnaviv driver start failing on dma maping functions because of
> > > dma_mask lack.
> > > 
> > > So I'm wondering is it valid case to have device which is
> > > DMA capable and doesn't have dma_mask set?
> > > 
> > > If not, then I guess something like that should work
> > > (at least it works for ARC):
> > 
> > This looks ok is a minimal fix:
> > 
> > Reviewed-by: Christoph Hellwig <hch at lst.de>
> > 
> > But why doesn't this device have a dma-range property in DT?
> 
> Because the etnaviv device is a virtual device not represented in DT,
> as it is only used to expose the DRM device, which may cover multiple
> GPU core devices. The GPU core devices are properly configured from DT,
> but unfortunately many of the dma related operations happen through the
> DRM device. We could fix this by replacing many of the DRM helpers with
> etnaviv specific functions handling dma per GPU core, but it isn't a
> clear win right now, as generally on SoCs with multiple GPU cores, the
> devices are on the same bus and have the same dma requirements.

I ended up with dummy_dma_ops on arm64 recently since we don't configure
dma via DT. I'm currently using

index 540b59fb4103..5506c833aa3f 100644
--- a/drivers/gpu/drm/etnaviv/etnaviv_drv.c
+++ b/drivers/gpu/drm/etnaviv/etnaviv_drv.c
@@ -592,8 +592,19 @@ static int etnaviv_pdev_probe(struct platform_device *pdev)
 {
 	struct device *dev = &pdev->dev;
 	struct component_match *match = NULL;
+	int ret;
+
+	ret = of_dma_configure(dev, NULL, true);
+	if (ret) {
+		dev_err(&pdev->dev, "Setting up dma ops failed\n");
+		return ret;
+	};
 
-	dma_set_coherent_mask(&pdev->dev, DMA_BIT_MASK(32));
+	ret = dma_coerce_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(32));
+	if (ret) {
+		dev_err(&pdev->dev, "dma_coerce_mask_and_coherent failed\n");
+		return ret;
+	};
 
 	if (!dev->platform_data) {
 		struct device_node *core_node;

but I wonder what the correct fix would be?
Cheers,
 -- Guido


More information about the etnaviv mailing list