@@ -329,6 +329,14 @@ static int notify_starting(unsigned int cpu)
329
329
return 0 ;
330
330
}
331
331
332
+ static int bringup_wait_for_ap (unsigned int cpu )
333
+ {
334
+ struct cpuhp_cpu_state * st = per_cpu_ptr (& cpuhp_state , cpu );
335
+
336
+ wait_for_completion (& st -> done );
337
+ return st -> result ;
338
+ }
339
+
332
340
static int bringup_cpu (unsigned int cpu )
333
341
{
334
342
struct task_struct * idle = idle_thread_get (cpu );
@@ -340,8 +348,9 @@ static int bringup_cpu(unsigned int cpu)
340
348
cpu_notify (CPU_UP_CANCELED , cpu );
341
349
return ret ;
342
350
}
351
+ ret = bringup_wait_for_ap (cpu );
343
352
BUG_ON (!cpu_online (cpu ));
344
- return 0 ;
353
+ return ret ;
345
354
}
346
355
347
356
/*
@@ -470,7 +479,7 @@ static void cpuhp_thread_fun(unsigned int cpu)
470
479
}
471
480
} else {
472
481
/* Cannot happen .... */
473
- BUG_ON (st -> state < CPUHP_KICK_AP_THREAD );
482
+ BUG_ON (st -> state < CPUHP_AP_ONLINE_IDLE );
474
483
475
484
/* Regular hotplug work */
476
485
if (st -> state < st -> target )
@@ -780,7 +789,7 @@ static int __ref _cpu_down(unsigned int cpu, int tasks_frozen,
780
789
* If the current CPU state is in the range of the AP hotplug thread,
781
790
* then we need to kick the thread.
782
791
*/
783
- if (st -> state >= CPUHP_KICK_AP_THREAD ) {
792
+ if (st -> state > CPUHP_TEARDOWN_CPU ) {
784
793
ret = cpuhp_kick_ap_work (cpu );
785
794
/*
786
795
* The AP side has done the error rollback already. Just
@@ -793,11 +802,11 @@ static int __ref _cpu_down(unsigned int cpu, int tasks_frozen,
793
802
* We might have stopped still in the range of the AP hotplug
794
803
* thread. Nothing to do anymore.
795
804
*/
796
- if (st -> state >= CPUHP_KICK_AP_THREAD )
805
+ if (st -> state > CPUHP_TEARDOWN_CPU )
797
806
goto out ;
798
807
}
799
808
/*
800
- * The AP brought itself down below CPUHP_KICK_AP_THREAD . So we need
809
+ * The AP brought itself down to CPUHP_TEARDOWN_CPU . So we need
801
810
* to do the further cleanups.
802
811
*/
803
812
ret = cpuhp_down_callbacks (cpu , st , cpuhp_bp_states , target );
@@ -859,18 +868,32 @@ void notify_cpu_starting(unsigned int cpu)
859
868
860
869
/*
861
870
* Called from the idle task. We need to set active here, so we can kick off
862
- * the stopper thread.
871
+ * the stopper thread and unpark the smpboot threads. If the target state is
872
+ * beyond CPUHP_AP_ONLINE_IDLE we kick cpuhp thread and let it bring up the
873
+ * cpu further.
863
874
*/
864
- static int cpuhp_set_cpu_active ( unsigned int cpu )
875
+ void cpuhp_online_idle ( enum cpuhp_state state )
865
876
{
866
- struct cpuhp_cpu_state * st = per_cpu_ptr (& cpuhp_state , cpu );
877
+ struct cpuhp_cpu_state * st = this_cpu_ptr (& cpuhp_state );
878
+ unsigned int cpu = smp_processor_id ();
879
+
880
+ /* Happens for the boot cpu */
881
+ if (state != CPUHP_AP_ONLINE_IDLE )
882
+ return ;
883
+
884
+ st -> state = CPUHP_AP_ONLINE_IDLE ;
867
885
868
886
/* The cpu is marked online, set it active now */
869
887
set_cpu_active (cpu , true);
870
- /* Unpark the stopper thread and the hotplug thread */
888
+ /* Unpark the stopper thread and the hotplug thread of this cpu */
871
889
stop_machine_unpark (cpu );
872
890
kthread_unpark (st -> thread );
873
- return 0 ;
891
+
892
+ /* Should we go further up ? */
893
+ if (st -> target > CPUHP_AP_ONLINE_IDLE )
894
+ __cpuhp_kick_ap_work (st );
895
+ else
896
+ complete (& st -> done );
874
897
}
875
898
876
899
/* Requires cpu_add_remove_lock to be held */
@@ -910,7 +933,7 @@ static int _cpu_up(unsigned int cpu, int tasks_frozen, enum cpuhp_state target)
910
933
* If the current CPU state is in the range of the AP hotplug thread,
911
934
* then we need to kick the thread once more.
912
935
*/
913
- if (st -> state >= CPUHP_KICK_AP_THREAD ) {
936
+ if (st -> state > CPUHP_BRINGUP_CPU ) {
914
937
ret = cpuhp_kick_ap_work (cpu );
915
938
/*
916
939
* The AP side has done the error rollback already. Just
@@ -922,10 +945,10 @@ static int _cpu_up(unsigned int cpu, int tasks_frozen, enum cpuhp_state target)
922
945
923
946
/*
924
947
* Try to reach the target state. We max out on the BP at
925
- * CPUHP_KICK_AP_THREAD . After that the AP hotplug thread is
948
+ * CPUHP_BRINGUP_CPU . After that the AP hotplug thread is
926
949
* responsible for bringing it up to the target state.
927
950
*/
928
- target = min ((int )target , CPUHP_KICK_AP_THREAD );
951
+ target = min ((int )target , CPUHP_BRINGUP_CPU );
929
952
ret = cpuhp_up_callbacks (cpu , st , cpuhp_bp_states , target );
930
953
out :
931
954
cpu_hotplug_done ();
@@ -1146,22 +1169,7 @@ static struct cpuhp_step cpuhp_bp_states[] = {
1146
1169
.teardown = takedown_cpu ,
1147
1170
.cant_stop = true,
1148
1171
},
1149
- [CPUHP_CPU_SET_ACTIVE ] = {
1150
- .name = "cpu:active" ,
1151
- .startup = cpuhp_set_cpu_active ,
1152
- .teardown = NULL ,
1153
- },
1154
- [CPUHP_KICK_AP_THREAD ] = {
1155
- .name = "cpuhp:kickthread" ,
1156
- .startup = cpuhp_kick_ap_work ,
1157
- .teardown = cpuhp_kick_ap_work ,
1158
- },
1159
1172
#endif
1160
- [CPUHP_BP_ONLINE ] = {
1161
- .name = "online" ,
1162
- .startup = NULL ,
1163
- .teardown = NULL ,
1164
- },
1165
1173
};
1166
1174
1167
1175
/* Application processor state steps */
@@ -1204,7 +1212,7 @@ static bool cpuhp_is_ap_state(enum cpuhp_state state)
1204
1212
{
1205
1213
if (state >= CPUHP_AP_OFFLINE && state <= CPUHP_AP_ONLINE )
1206
1214
return true;
1207
- return state > CPUHP_BP_ONLINE ;
1215
+ return state > CPUHP_BRINGUP_CPU ;
1208
1216
}
1209
1217
1210
1218
static struct cpuhp_step * cpuhp_get_step (enum cpuhp_state state )
0 commit comments