summaryrefslogtreecommitdiff
path: root/drivers/char/ipmi/ipmi_ssif.c
diff options
context:
space:
mode:
authorCorey Minyard <cminyard@mvista.com>2018-08-22 20:08:13 +0300
committerCorey Minyard <cminyard@mvista.com>2018-08-31 16:42:29 +0300
commit2512e40e48d21d8bac09f7e91d2c3ceb2d3b50b2 (patch)
treed3f88ae5767b53c41a4a9d8c4089dc98ac956dd7 /drivers/char/ipmi/ipmi_ssif.c
parentcd2315d471f45a36cb1329722920d89cd6d3d11f (diff)
downloadlinux-2512e40e48d21d8bac09f7e91d2c3ceb2d3b50b2.tar.xz
ipmi: Rework SMI registration failure
There were certain situations where ipmi_register_smi() would return a failure, but the interface would still be registered and would need to be unregistered. This is obviously a bad design and resulted in an oops in certain failure cases. If the interface is started up in ipmi_register_smi(), then an error occurs, shut down the interface there so the cleanup can be done properly. Fix the various smi users, too. Signed-off-by: Corey Minyard <cminyard@mvista.com> Reported-by: Justin Ernst <justin.ernst@hpe.com> Tested-by: Justin Ernst <justin.ernst@hpe.com> Cc: Andrew Banman <abanman@hpe.com> Cc: Russ Anderson <russ.anderson@hpe.com> Cc: <stable@vger.kernel.org> # 4.18.x
Diffstat (limited to 'drivers/char/ipmi/ipmi_ssif.c')
-rw-r--r--drivers/char/ipmi/ipmi_ssif.c13
1 files changed, 3 insertions, 10 deletions
diff --git a/drivers/char/ipmi/ipmi_ssif.c b/drivers/char/ipmi/ipmi_ssif.c
index 18e4650c233b..c12edc8e91df 100644
--- a/drivers/char/ipmi/ipmi_ssif.c
+++ b/drivers/char/ipmi/ipmi_ssif.c
@@ -1214,18 +1214,11 @@ static void shutdown_ssif(void *send_info)
complete(&ssif_info->wake_thread);
kthread_stop(ssif_info->thread);
}
-
- /*
- * No message can be outstanding now, we have removed the
- * upper layer and it permitted us to do so.
- */
- kfree(ssif_info);
}
static int ssif_remove(struct i2c_client *client)
{
struct ssif_info *ssif_info = i2c_get_clientdata(client);
- struct ipmi_smi *intf;
struct ssif_addr_info *addr_info;
if (!ssif_info)
@@ -1235,9 +1228,7 @@ static int ssif_remove(struct i2c_client *client)
* After this point, we won't deliver anything asychronously
* to the message handler. We can unregister ourself.
*/
- intf = ssif_info->intf;
- ssif_info->intf = NULL;
- ipmi_unregister_smi(intf);
+ ipmi_unregister_smi(ssif_info->intf);
list_for_each_entry(addr_info, &ssif_infos, link) {
if (addr_info->client == client) {
@@ -1246,6 +1237,8 @@ static int ssif_remove(struct i2c_client *client)
}
}
+ kfree(ssif_info);
+
return 0;
}