Skip to content
Snippets Groups Projects
Commit 43d99d5f authored by Vaibhav Gupta's avatar Vaibhav Gupta
Browse files

fmc-eeprom: Maintain the reference count of the device.


With nvmem framework, the reference counter of the nvmem device is
increased when we ask the device from the kernel via helper functions
like "nvmem_device_find()", "nvmem_device_get()", etc. If reference
count is zero, the driver can be unloaded (rmmod) during ongoing
operations.

Thus, the reference count should be incremented during add, and
decremented during delete.

Reported-by: default avatarFederico Vaga <federico.vaga@cern.ch>
Signed-off-by: default avatarVaibhav Gupta <vaibhav.gupta@cern.ch>
parent 37a8cf39
Branches
Tags
No related merge requests found
......@@ -115,29 +115,7 @@ ssize_t fmc_slot_eeprom_read(struct fmc_slot *slot,
{
int err = 0;
#if KERNEL_VERSION(4, 6, 0) <= LINUX_VERSION_CODE
size_t len;
struct nvmem_device *nvmem;
char *nvmem_parent_name;
len = strlen(dev_name(&slot->eeprom->dev)) + 1;
nvmem_parent_name = kzalloc(len, GFP_KERNEL);
if (nvmem_parent_name) {
snprintf(nvmem_parent_name, len, "%s",
dev_name(&slot->eeprom->dev));
nvmem = nvmem_device_find(nvmem_parent_name,
fmc_nvmem_device_find_match);
if (!IS_ERR_OR_NULL(nvmem)) {
err = nvmem_device_read(nvmem, offset, count, buf);
#if KERNEL_VERSION(5, 1, 0) <= LINUX_VERSION_CODE
nvmem_device_put(nvmem);
#endif
}
else {
err = PTR_ERR(nvmem);
}
kfree(nvmem_parent_name);
}
err = nvmem_device_read(slot->nvmem, offset, count, buf);
#else
/*
* TODO if we export this function, do we have to lock it when we
......@@ -198,6 +176,20 @@ static int __fmc_slot_eeprom_add(struct fmc_slot *slot,
dev_err(&slot->dev, "Failed to create eeprom symlink to %s\n",
dev_name(&slot->eeprom->dev));
#if KERNEL_VERSION(4, 6, 0) <= LINUX_VERSION_CODE
slot->nvmem_parent_name = kzalloc(strlen(dev_name(&slot->eeprom->dev)) + 1,
GFP_KERNEL);
if (!slot->nvmem_parent_name)
return -ENOMEM;
snprintf(slot->nvmem_parent_name, strlen(dev_name(&slot->eeprom->dev)),
"%s", dev_name(&slot->eeprom->dev));
slot->nvmem = nvmem_device_find(slot->nvmem_parent_name,
fmc_nvmem_device_find_match);
if (IS_ERR_OR_NULL(slot->nvmem))
return PTR_ERR(slot->nvmem);
#endif
return 0;
}
......@@ -226,6 +218,11 @@ int fmc_slot_eeprom_add(struct fmc_slot *slot)
*/
void fmc_slot_eeprom_del(struct fmc_slot *slot)
{
#if KERNEL_VERSION(5, 1, 0) <= LINUX_VERSION_CODE
nvmem_device_put(slot->nvmem);
#endif
kfree(slot->nvmem_parent_name);
if (!slot || !slot->eeprom)
return;
......
......@@ -89,6 +89,8 @@ struct fmc_slot {
#if KERNEL_VERSION(4, 6, 0) <= LINUX_VERSION_CODE
#define AT24_NUM_PROPERTIES 4
struct property_entry at24_data[AT24_NUM_PROPERTIES];
struct nvmem_device *nvmem;
char *nvmem_parent_name;
#else
struct memory_accessor *macc;
struct at24_platform_data at24_data;
......
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment