Print this page
XXXX cpudrv attach error handling is leaky
XXXX cpudrv attach is racy

@@ -275,12 +275,20 @@
                         ddi_soft_state_free(cpudrv_state, instance);
                         cpudrv_enabled = B_FALSE;
                         return (DDI_FAILURE);
                 }
 
+                if (!cpudrv_is_enabled(cpudsp)) {
+                        cmn_err(CE_WARN, "cpudrv_attach: instance %d: "
+                            "not supported or it got disabled on us",
+                            instance);
+                        cpudrv_enabled = B_FALSE;
+                        ddi_soft_state_free(cpudrv_state, instance);
+                        return (DDI_FAILURE);
+                }
+
                 mutex_init(&cpudsp->lock, NULL, MUTEX_DRIVER, NULL);
-                if (cpudrv_is_enabled(cpudsp)) {
                         if (cpudrv_init(cpudsp) != DDI_SUCCESS) {
                                 cpudrv_enabled = B_FALSE;
                                 cpudrv_free(cpudsp);
                                 ddi_soft_state_free(cpudrv_state, instance);
                                 return (DDI_FAILURE);

@@ -304,10 +312,16 @@
                          * activities.
                          */
                         cpudsp->cpudrv_pm.tq = ddi_taskq_create(dip,
                             "cpudrv_monitor", CPUDRV_TASKQ_THREADS,
                             TASKQ_DEFAULTPRI, 0);
+                if (cpudsp->cpudrv_pm.tq == NULL) {
+                        cpudrv_enabled = B_FALSE;
+                        cpudrv_free(cpudsp);
+                        ddi_soft_state_free(cpudrv_state, instance);
+                        return (DDI_FAILURE);
+                }
 
                         mutex_init(&cpudsp->cpudrv_pm.timeout_lock, NULL,
                             MUTEX_DRIVER, NULL);
                         cv_init(&cpudsp->cpudrv_pm.timeout_cv, NULL,
                             CV_DEFAULT, NULL);

@@ -334,16 +348,15 @@
                          * has been initialized.
                          */
                         CPUDRV_MONITOR_INIT(cpudsp);
                         mutex_exit(&cpudsp->lock);
 
-                }
-
                 if (!cpudrv_mach_init(cpudsp)) {
                         cmn_err(CE_WARN, "cpudrv_attach: instance %d: "
                             "cpudrv_mach_init failed", instance);
                         cpudrv_enabled = B_FALSE;
+                        ddi_taskq_destroy(cpudsp->cpudrv_pm.tq);
                         cpudrv_free(cpudsp);
                         ddi_soft_state_free(cpudrv_state, instance);
                         return (DDI_FAILURE);
                 }