On Mon, 25 Jun 2012, Arnd Bergmann wrote:

[snip]

> The channel data in the device tree is still in a format
> that is specific to that dmaengine driver and interpreted
> by it. Using the regular dma_filter_fn prototype is not
> necessary, but it would be convenient because the dmaengine
> code already knows how to deal with it. If we don't use this
> method, how about adding another callback to struct dma_device
> like
> 
> bool (*device_match)(struct dma_chan *chan, struct property *req);

I like this idea, but why don't we extend it to also cover the non-DT 
case? I.e., why don't we add the above callback (call it "match" or 
"filter" or anything else) to dmaengine operations and inside (the 
extended) dma_request_channel(), instead of calling the filter function, 
passed as a parameter, we loop over all registered DMAC devices and call 
their filter callbacks, until one of them returns true? In fact, it goes 
back to my earlier proposal from 
http://thread.gmane.org/gmane.linux.kernel/1246957
which I, possibly, failed to explain properly. So, the transformation 
chain from today's API would be (all code is approximate):

(today)

<client driver>
        dma_request_channel(mask, filter, filter_arg);

<dmaengine_core>
        for_each_channel() {
                ret = (*filter)(chan, filter_arg);
                if (ret) {
                        ret = chan->device->device_alloc_chan_resources(chan);
                        if (!ret)
                                return chan;
                        else
                                return NULL;
                }
        }

(can be transformed to)

<client driver>
        dma_request_channel(mask, filter_arg);

<dmaengine_core>
        for_each_channel() {
                ret = chan->device->filter(chan, filter_arg);
                if (ret) {
                        <same as above>
                }
        }

(which further could be simplified to)

<client driver>
        dma_request_channel(mask, filter_arg);

<dmaengine_core>
        for_each_channel() {
                ret = chan->device->device_alloc_chan_resources(chan, 
filter_arg);
                if (!ret)
                        return chan;
                else if (ret != -ENODEV)
                        return ret;
                /* -ENODEV - try the next channel */
        }

Which is quite similar to my above mentioned proposal. Wouldn't this both 
improve the present API and prepare it for DT?

Thanks
Guennadi
---
Guennadi Liakhovetski, Ph.D.
Freelance Open-Source Software Developer
http://www.open-technology.de/
--
To unsubscribe from this list: send the line "unsubscribe linux-omap" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Reply via email to