dahdi: Prevent memory corruption on device unload.
The channels now have embedded 'struct devices' that contain a device_private pointer in which to store the device private data. When a device is unregistered in the system the device privata data is freed by the device core, even though the chan_release function doesn't free the memory associated with the device, So when dev_set_drvdata() is called, it's writing into freed memory. We also need zero out the embedded struct device before registration, since we do not have any guarantee that it points to valid memory (or, if a channel was unregisterd with sysfs, and then reregistered without being cleared out). Otherwise the core could try to use the previously freed private data again. Signed-off-by: Shaun Ruffell <sruffell@digium.com> Signed-off-by: Russ Meyerriecks <rmeyerriecks@digium.com>
This commit is contained in:
committed by
Russ Meyerriecks
parent
4641d5b396
commit
bb5eeccef3
@@ -240,6 +240,7 @@ int chan_sysfs_create(struct dahdi_chan *chan)
|
||||
span = chan->span;
|
||||
devt = MKDEV(MAJOR(dahdi_channels_devt), chan->channo);
|
||||
dev = &chan->chan_device;
|
||||
memset(dev, 0, sizeof(*dev));
|
||||
dev->devt = devt;
|
||||
dev->bus = &chan_bus_type;
|
||||
dev->parent = span->span_device;
|
||||
@@ -253,7 +254,7 @@ int chan_sysfs_create(struct dahdi_chan *chan)
|
||||
if (res) {
|
||||
chan_err(chan, "%s: device_register failed: %d\n",
|
||||
__func__, res);
|
||||
dev_set_drvdata(dev, NULL);
|
||||
put_device(dev);
|
||||
return res;
|
||||
}
|
||||
set_bit(DAHDI_FLAGBIT_DEVFILE, &chan->flags);
|
||||
@@ -272,7 +273,6 @@ void chan_sysfs_remove(struct dahdi_chan *chan)
|
||||
dev = &chan->chan_device;
|
||||
BUG_ON(dev_get_drvdata(dev) != chan);
|
||||
device_unregister(dev);
|
||||
dev_set_drvdata(dev, NULL);
|
||||
/* FIXME: should have been done earlier in dahdi_chan_unreg */
|
||||
chan->channo = -1;
|
||||
clear_bit(DAHDI_FLAGBIT_DEVFILE, &chan->flags);
|
||||
|
||||
Reference in New Issue
Block a user