coresight: cti: Increase reference count when enabling cti
authorTingwei Zhang <tingwei@codeaurora.org>
Mon, 28 Sep 2020 16:35:08 +0000 (10:35 -0600)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 28 Sep 2020 17:47:41 +0000 (19:47 +0200)
CTI device is enabled when associated coresight device is enabled.
Increase the module and device reference count for CTI device
when it's enabled. This can prevent CTI device be removed or
module be unloaded when CTI device is enabled by an active trace
session.

Signed-off-by: Mike Leach <mike.leach@linaro.org>
Signed-off-by: Tingwei Zhang <tingwei@codeaurora.org>
Signed-off-by: Mathieu Poirier <mathieu.poirier@linaro.org>
Link: https://lore.kernel.org/r/20200928163513.70169-21-mathieu.poirier@linaro.org
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
drivers/hwtracing/coresight/coresight.c

index 711beb92166aa90dffa85bbe9b08aa954aa39a75..546c97045afed1baab7e3fe8cdbb0dbb5bb90594 100644 (file)
@@ -241,19 +241,30 @@ coresight_control_assoc_ectdev(struct coresight_device *csdev, bool enable)
 {
        int ect_ret = 0;
        struct coresight_device *ect_csdev = csdev->ect_dev;
+       struct module *mod;
 
        if (!ect_csdev)
                return 0;
        if ((!ect_ops(ect_csdev)->enable) || (!ect_ops(ect_csdev)->disable))
                return 0;
 
+       mod = ect_csdev->dev.parent->driver->owner;
        if (enable) {
-               ect_ret = ect_ops(ect_csdev)->enable(ect_csdev);
-               if (!ect_ret)
-                       csdev->ect_enabled = true;
+               if (try_module_get(mod)) {
+                       ect_ret = ect_ops(ect_csdev)->enable(ect_csdev);
+                       if (ect_ret) {
+                               module_put(mod);
+                       } else {
+                               get_device(ect_csdev->dev.parent);
+                               csdev->ect_enabled = true;
+                       }
+               } else
+                       ect_ret = -ENODEV;
        } else {
                if (csdev->ect_enabled) {
                        ect_ret = ect_ops(ect_csdev)->disable(ect_csdev);
+                       put_device(ect_csdev->dev.parent);
+                       module_put(mod);
                        csdev->ect_enabled = false;
                }
        }