diff options
Diffstat (limited to 'kernel/cpu.c')
| -rw-r--r-- | kernel/cpu.c | 28 | 
1 files changed, 14 insertions, 14 deletions
diff --git a/kernel/cpu.c b/kernel/cpu.c index f7c063239fa5..37b223e4fc05 100644 --- a/kernel/cpu.c +++ b/kernel/cpu.c @@ -1335,26 +1335,21 @@ static int cpuhp_store_callbacks(enum cpuhp_state state, const char *name,  	struct cpuhp_step *sp;  	int ret = 0; -	mutex_lock(&cpuhp_state_mutex); -  	if (state == CPUHP_AP_ONLINE_DYN || state == CPUHP_BP_PREPARE_DYN) {  		ret = cpuhp_reserve_state(state);  		if (ret < 0) -			goto out; +			return ret;  		state = ret;  	}  	sp = cpuhp_get_step(state); -	if (name && sp->name) { -		ret = -EBUSY; -		goto out; -	} +	if (name && sp->name) +		return -EBUSY; +  	sp->startup.single = startup;  	sp->teardown.single = teardown;  	sp->name = name;  	sp->multi_instance = multi_instance;  	INIT_HLIST_HEAD(&sp->list); -out: -	mutex_unlock(&cpuhp_state_mutex);  	return ret;  } @@ -1428,6 +1423,7 @@ int __cpuhp_state_add_instance(enum cpuhp_state state, struct hlist_node *node,  		return -EINVAL;  	get_online_cpus(); +	mutex_lock(&cpuhp_state_mutex);  	if (!invoke || !sp->startup.multi)  		goto add_node; @@ -1447,16 +1443,14 @@ int __cpuhp_state_add_instance(enum cpuhp_state state, struct hlist_node *node,  		if (ret) {  			if (sp->teardown.multi)  				cpuhp_rollback_install(cpu, state, node); -			goto err; +			goto unlock;  		}  	}  add_node:  	ret = 0; -	mutex_lock(&cpuhp_state_mutex);  	hlist_add_head(node, &sp->list); +unlock:  	mutex_unlock(&cpuhp_state_mutex); - -err:  	put_online_cpus();  	return ret;  } @@ -1491,6 +1485,7 @@ int __cpuhp_setup_state(enum cpuhp_state state,  		return -EINVAL;  	get_online_cpus(); +	mutex_lock(&cpuhp_state_mutex);  	ret = cpuhp_store_callbacks(state, name, startup, teardown,  				    multi_instance); @@ -1524,6 +1519,7 @@ int __cpuhp_setup_state(enum cpuhp_state state,  		}  	}  out: +	mutex_unlock(&cpuhp_state_mutex);  	put_online_cpus();  	/*  	 * If the requested state is CPUHP_AP_ONLINE_DYN, return the @@ -1547,6 +1543,8 @@ int __cpuhp_state_remove_instance(enum cpuhp_state state,  		return -EINVAL;  	get_online_cpus(); +	mutex_lock(&cpuhp_state_mutex); +  	if (!invoke || !cpuhp_get_teardown_cb(state))  		goto remove;  	/* @@ -1563,7 +1561,6 @@ int __cpuhp_state_remove_instance(enum cpuhp_state state,  	}  remove: -	mutex_lock(&cpuhp_state_mutex);  	hlist_del(node);  	mutex_unlock(&cpuhp_state_mutex);  	put_online_cpus(); @@ -1571,6 +1568,7 @@ remove:  	return 0;  }  EXPORT_SYMBOL_GPL(__cpuhp_state_remove_instance); +  /**   * __cpuhp_remove_state - Remove the callbacks for an hotplug machine state   * @state:	The state to remove @@ -1589,6 +1587,7 @@ void __cpuhp_remove_state(enum cpuhp_state state, bool invoke)  	get_online_cpus(); +	mutex_lock(&cpuhp_state_mutex);  	if (sp->multi_instance) {  		WARN(!hlist_empty(&sp->list),  		     "Error: Removing state %d which has instances left.\n", @@ -1613,6 +1612,7 @@ void __cpuhp_remove_state(enum cpuhp_state state, bool invoke)  	}  remove:  	cpuhp_store_callbacks(state, NULL, NULL, NULL, false); +	mutex_unlock(&cpuhp_state_mutex);  	put_online_cpus();  }  EXPORT_SYMBOL(__cpuhp_remove_state);  |