Release onexit/events with any missed zfsdev_state
Linux and FreeBSD will most likely never see this issue. On macOS when kext is unloaded, but zed is still connected, zed will be issued ENODEV. As the cdevsw is released, the kernel will not have zfsdev_release() called to release minor/onexit/events, and it "leaks". This ensures it is cleaned up before unload. Changed the for loop from zsprev, to zsnext style, for less code duplication. Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov> Signed-off-by: Jorgen Lundman <lundman@lundman.net> Closes #10700
This commit is contained in:
parent
f67f5832ec
commit
faa296c73c
|
@ -201,6 +201,8 @@ zfsdev_close(void *data)
|
|||
zfs_onexit_destroy(zs->zs_onexit);
|
||||
zfs_zevent_destroy(zs->zs_zevent);
|
||||
mutex_exit(&zfsdev_state_lock);
|
||||
zs->zs_onexit = NULL;
|
||||
zs->zs_zevent = NULL;
|
||||
}
|
||||
|
||||
static int
|
||||
|
|
|
@ -148,6 +148,8 @@ zfsdev_state_destroy(struct file *filp)
|
|||
zs->zs_minor = -1;
|
||||
zfs_onexit_destroy(zs->zs_onexit);
|
||||
zfs_zevent_destroy(zs->zs_zevent);
|
||||
zs->zs_onexit = NULL;
|
||||
zs->zs_zevent = NULL;
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
|
|
@ -7609,19 +7609,20 @@ out:
|
|||
void
|
||||
zfs_kmod_fini(void)
|
||||
{
|
||||
zfsdev_state_t *zs, *zsprev = NULL;
|
||||
zfsdev_state_t *zs, *zsnext = NULL;
|
||||
|
||||
zfsdev_detach();
|
||||
|
||||
mutex_destroy(&zfsdev_state_lock);
|
||||
|
||||
for (zs = zfsdev_state_list; zs != NULL; zs = zs->zs_next) {
|
||||
if (zsprev)
|
||||
kmem_free(zsprev, sizeof (zfsdev_state_t));
|
||||
zsprev = zs;
|
||||
for (zs = zfsdev_state_list; zs != NULL; zs = zsnext) {
|
||||
zsnext = zs->zs_next;
|
||||
if (zs->zs_onexit)
|
||||
zfs_onexit_destroy(zs->zs_onexit);
|
||||
if (zs->zs_zevent)
|
||||
zfs_zevent_destroy(zs->zs_zevent);
|
||||
kmem_free(zs, sizeof (zfsdev_state_t));
|
||||
}
|
||||
if (zsprev)
|
||||
kmem_free(zsprev, sizeof (zfsdev_state_t));
|
||||
|
||||
zfs_fini();
|
||||
spa_fini();
|
||||
|
|
Loading…
Reference in New Issue