diff --git a/drivers/nvdimm/pmem.c b/drivers/nvdimm/pmem.c index 34189a145ac6..4a9cffc14512 100644 --- a/drivers/nvdimm/pmem.c +++ b/drivers/nvdimm/pmem.c @@ -382,10 +382,8 @@ static int pmem_attach_disk(struct device *dev, pmem->bb_state = sysfs_get_dirent(disk_to_dev(disk)->kobj.sd, "badblocks"); - if (pmem->bb_state) - sysfs_put(pmem->bb_state); - else - dev_warn(dev, "sysfs_get_dirent 'badblocks' failed\n"); + if (!pmem->bb_state) + dev_warn(dev, "'badblocks' notification disabled\n"); return 0; } @@ -418,8 +416,18 @@ static int nd_pmem_probe(struct device *dev) static int nd_pmem_remove(struct device *dev) { + struct pmem_device *pmem = dev_get_drvdata(dev); + if (is_nd_btt(dev)) nvdimm_namespace_detach_btt(to_nd_btt(dev)); + else { + /* + * Note, this assumes device_lock() context to not race + * nd_pmem_notify() + */ + sysfs_put(pmem->bb_state); + pmem->bb_state = NULL; + } nvdimm_flush(to_nd_region(dev->parent)); return 0; diff --git a/drivers/nvdimm/region.c b/drivers/nvdimm/region.c index ca94029d20b3..034f0a07d627 100644 --- a/drivers/nvdimm/region.c +++ b/drivers/nvdimm/region.c @@ -60,11 +60,9 @@ static int nd_region_probe(struct device *dev) return -ENODEV; nd_region->bb_state = sysfs_get_dirent(nd_region->dev.kobj.sd, "badblocks"); - if (nd_region->bb_state) - sysfs_put(nd_region->bb_state); - else + if (!nd_region->bb_state) dev_warn(&nd_region->dev, - "sysfs_get_dirent 'badblocks' failed\n"); + "'badblocks' notification disabled\n"); ndr_res.start = nd_region->ndr_start; ndr_res.end = nd_region->ndr_start + nd_region->ndr_size - 1; nvdimm_badblocks_populate(nd_region, &nd_region->bb, &ndr_res); @@ -111,6 +109,13 @@ static int nd_region_remove(struct device *dev) dev_set_drvdata(dev, NULL); nvdimm_bus_unlock(dev); + /* + * Note, this assumes device_lock() context to not race + * nd_region_notify() + */ + sysfs_put(nd_region->bb_state); + nd_region->bb_state = NULL; + return 0; }