1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright(c) 2010-2014 Intel Corporation 3 */ 4 5 #include <errno.h> 6 #include <stdint.h> 7 #include <stdio.h> 8 #include <sys/queue.h> 9 10 #include <rte_launch.h> 11 #include <rte_memory.h> 12 #include <rte_eal.h> 13 #include <rte_atomic.h> 14 #include <rte_pause.h> 15 #include <rte_per_lcore.h> 16 #include <rte_lcore.h> 17 18 #include "eal_private.h" 19 20 /* 21 * Wait until a lcore finished its job. 22 */ 23 int 24 rte_eal_wait_lcore(unsigned worker_id) 25 { 26 while (__atomic_load_n(&lcore_config[worker_id].state, 27 __ATOMIC_ACQUIRE) != WAIT) 28 rte_pause(); 29 30 return lcore_config[worker_id].ret; 31 } 32 33 /* 34 * Check that every WORKER lcores are in WAIT state, then call 35 * rte_eal_remote_launch() for all of them. If call_main is true 36 * (set to CALL_MAIN), also call the function on the main lcore. 37 */ 38 int 39 rte_eal_mp_remote_launch(int (*f)(void *), void *arg, 40 enum rte_rmt_call_main_t call_main) 41 { 42 int lcore_id; 43 int main_lcore = rte_get_main_lcore(); 44 45 /* check state of lcores */ 46 RTE_LCORE_FOREACH_WORKER(lcore_id) { 47 if (lcore_config[lcore_id].state != WAIT) 48 return -EBUSY; 49 } 50 51 /* send messages to cores */ 52 RTE_LCORE_FOREACH_WORKER(lcore_id) { 53 rte_eal_remote_launch(f, arg, lcore_id); 54 } 55 56 if (call_main == CALL_MAIN) { 57 lcore_config[main_lcore].ret = f(arg); 58 lcore_config[main_lcore].state = WAIT; 59 } 60 61 return 0; 62 } 63 64 /* 65 * Return the state of the lcore identified by worker_id. 66 */ 67 enum rte_lcore_state_t 68 rte_eal_get_lcore_state(unsigned lcore_id) 69 { 70 return lcore_config[lcore_id].state; 71 } 72 73 /* 74 * Do a rte_eal_wait_lcore() for every lcore. The return values are 75 * ignored. 76 */ 77 void 78 rte_eal_mp_wait_lcore(void) 79 { 80 unsigned lcore_id; 81 82 RTE_LCORE_FOREACH_WORKER(lcore_id) { 83 rte_eal_wait_lcore(lcore_id); 84 } 85 } 86