summaryrefslogtreecommitdiffstats
path: root/include
diff options
context:
space:
mode:
authorDave Jiang <dave.jiang@intel.com>2020-04-13 10:40:12 -0700
committerVinod Koul <vkoul@kernel.org>2020-04-27 21:26:23 +0530
commit0821009445a8261ac4d32a6df4b83938e007c765 (patch)
treed59ad9425d0c1860538d3ce6173ab4ba2d570d49 /include
parent0c89446379218698189a47871336cb30286a7197 (diff)
downloadlinux-0821009445a8261ac4d32a6df4b83938e007c765.tar.bz2
dmaengine: fix channel index enumeration
When the channel register code was changed to allow hotplug operations, dynamic indexing wasn't taken into account. When channels are randomly plugged and unplugged out of order, the serial indexing breaks. Convert channel indexing to using IDA tracking in order to allow dynamic assignment. The previous code does not cause any regression bug for existing channel allocation besides idxd driver since the hotplug usage case is only used by idxd at this point. With this change, the chan->idr_ref is also not needed any longer. We can have a device with no channels registered due to hot plug. The channel device release code no longer should attempt to free the dma device id on the last channel release. Fixes: e81274cd6b52 ("dmaengine: add support to dynamic register/unregister of channels") Reported-by: Yixin Zhang <yixin.zhang@intel.com> Signed-off-by: Dave Jiang <dave.jiang@intel.com> Tested-by: Yixin Zhang <yixin.zhang@intel.com> Link: https://lore.kernel.org/r/158679961260.7674.8485924270472851852.stgit@djiang5-desk3.ch.intel.com Signed-off-by: Vinod Koul <vkoul@kernel.org>
Diffstat (limited to 'include')
-rw-r--r--include/linux/dmaengine.h4
1 files changed, 2 insertions, 2 deletions
diff --git a/include/linux/dmaengine.h b/include/linux/dmaengine.h
index 31e58ec9f741..e1c03339918f 100644
--- a/include/linux/dmaengine.h
+++ b/include/linux/dmaengine.h
@@ -341,13 +341,11 @@ struct dma_chan {
* @chan: driver channel device
* @device: sysfs device
* @dev_id: parent dma_device dev_id
- * @idr_ref: reference count to gate release of dma_device dev_id
*/
struct dma_chan_dev {
struct dma_chan *chan;
struct device device;
int dev_id;
- atomic_t *idr_ref;
};
/**
@@ -835,6 +833,8 @@ struct dma_device {
int dev_id;
struct device *dev;
struct module *owner;
+ struct ida chan_ida;
+ struct mutex chan_mutex; /* to protect chan_ida */
u32 src_addr_widths;
u32 dst_addr_widths;