Message ID | 1418036853-2889-1-git-send-email-julian@jusst.de (mailing list archive) |
---|---|
State | Not Applicable |
Headers | show |
Am 08.12.2014 um 12:07 schrieb Julian Scheel: > As dma_get_any_slave_channel is used to request a channel which will later on > be released through dma_release_channel it needs to maintain the privatecnt > just as __dma_request_channel does. Do this by refactoring the privatenct > handling into a helper function which is used from __dma_request_channel as > well as dma_get_any_slave_channel. > > Signed-off-by: Julian Scheel <julian@jusst.de> > --- > drivers/dma/dmaengine.c | 30 +++++++++++++++++++++--------- > 1 file changed, 21 insertions(+), 9 deletions(-) > > diff --git a/drivers/dma/dmaengine.c b/drivers/dma/dmaengine.c > index 24bfaf0..0215db4 100644 > --- a/drivers/dma/dmaengine.c > +++ b/drivers/dma/dmaengine.c > @@ -535,6 +535,24 @@ struct dma_chan *dma_get_slave_channel(struct dma_chan *chan) > } > EXPORT_SYMBOL_GPL(dma_get_slave_channel); > > + > +static int dma_get_channel_private(struct dma_device *device, struct dma_chan *chan) > +{ > + int err; > + > + /* We first set DMA_PRIVATE to disable > + * balance_ref_count as this channel will not be > + * published in the general-purpose allocator > + */ > + dma_cap_set(DMA_PRIVATE, device->cap_mask); > + device->privatecnt++; > + > + err = dma_chan_get(chan); > + if (err && --device->privatecnt == 0) > + dma_cap_clear(DMA_PRIVATE, device->cap_mask); > + return err; > +} > + > struct dma_chan *dma_get_any_slave_channel(struct dma_device *device) > { > dma_cap_mask_t mask; > @@ -549,7 +567,7 @@ struct dma_chan *dma_get_any_slave_channel(struct dma_device *device) > > chan = private_candidate(&mask, device, NULL, NULL); > if (chan) { > - err = dma_chan_get(chan); > + err = dma_get_channel_private(device, chan); > if (err) { > pr_debug("%s: failed to get %s: (%d)\n", > __func__, dma_chan_name(chan), err); > @@ -584,13 +602,9 @@ struct dma_chan *__dma_request_channel(const dma_cap_mask_t *mask, > chan = private_candidate(mask, device, fn, fn_param); > if (chan) { > /* Found a suitable channel, try to grab, prep, and > - * return it. We first set DMA_PRIVATE to disable > - * balance_ref_count as this channel will not be > - * published in the general-purpose allocator > + * return it. > */ > - dma_cap_set(DMA_PRIVATE, device->cap_mask); > - device->privatecnt++; > - err = dma_chan_get(chan); > + err = dma_get_channel_private(device, chan); > > if (err == -ENODEV) { > pr_debug("%s: %s module removed\n", > @@ -601,8 +615,6 @@ struct dma_chan *__dma_request_channel(const dma_cap_mask_t *mask, > __func__, dma_chan_name(chan), err); > else > break; > - if (--device->privatecnt == 0) > - dma_cap_clear(DMA_PRIVATE, device->cap_mask); > chan = NULL; > } > } > Any objections on this patch? -Julian -- To unsubscribe from this list: send the line "unsubscribe dmaengine" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
diff --git a/drivers/dma/dmaengine.c b/drivers/dma/dmaengine.c index 24bfaf0..0215db4 100644 --- a/drivers/dma/dmaengine.c +++ b/drivers/dma/dmaengine.c @@ -535,6 +535,24 @@ struct dma_chan *dma_get_slave_channel(struct dma_chan *chan) } EXPORT_SYMBOL_GPL(dma_get_slave_channel); + +static int dma_get_channel_private(struct dma_device *device, struct dma_chan *chan) +{ + int err; + + /* We first set DMA_PRIVATE to disable + * balance_ref_count as this channel will not be + * published in the general-purpose allocator + */ + dma_cap_set(DMA_PRIVATE, device->cap_mask); + device->privatecnt++; + + err = dma_chan_get(chan); + if (err && --device->privatecnt == 0) + dma_cap_clear(DMA_PRIVATE, device->cap_mask); + return err; +} + struct dma_chan *dma_get_any_slave_channel(struct dma_device *device) { dma_cap_mask_t mask; @@ -549,7 +567,7 @@ struct dma_chan *dma_get_any_slave_channel(struct dma_device *device) chan = private_candidate(&mask, device, NULL, NULL); if (chan) { - err = dma_chan_get(chan); + err = dma_get_channel_private(device, chan); if (err) { pr_debug("%s: failed to get %s: (%d)\n", __func__, dma_chan_name(chan), err); @@ -584,13 +602,9 @@ struct dma_chan *__dma_request_channel(const dma_cap_mask_t *mask, chan = private_candidate(mask, device, fn, fn_param); if (chan) { /* Found a suitable channel, try to grab, prep, and - * return it. We first set DMA_PRIVATE to disable - * balance_ref_count as this channel will not be - * published in the general-purpose allocator + * return it. */ - dma_cap_set(DMA_PRIVATE, device->cap_mask); - device->privatecnt++; - err = dma_chan_get(chan); + err = dma_get_channel_private(device, chan); if (err == -ENODEV) { pr_debug("%s: %s module removed\n", @@ -601,8 +615,6 @@ struct dma_chan *__dma_request_channel(const dma_cap_mask_t *mask, __func__, dma_chan_name(chan), err); else break; - if (--device->privatecnt == 0) - dma_cap_clear(DMA_PRIVATE, device->cap_mask); chan = NULL; } }
As dma_get_any_slave_channel is used to request a channel which will later on be released through dma_release_channel it needs to maintain the privatecnt just as __dma_request_channel does. Do this by refactoring the privatenct handling into a helper function which is used from __dma_request_channel as well as dma_get_any_slave_channel. Signed-off-by: Julian Scheel <julian@jusst.de> --- drivers/dma/dmaengine.c | 30 +++++++++++++++++++++--------- 1 file changed, 21 insertions(+), 9 deletions(-)