Since CPU and device are not one-to-one correspondence, need to build a map to show which device is the best choice when requests sent from a certain cpu.
Signed-off-by: Yang Shen shenyang39@huawei.com --- wd_sched.c | 68 +++++++++++++++++++++++++++++++++++------------------- 1 file changed, 44 insertions(+), 24 deletions(-)
diff --git a/wd_sched.c b/wd_sched.c index bef5f74..65569e0 100644 --- a/wd_sched.c +++ b/wd_sched.c @@ -70,13 +70,15 @@ struct wd_sched_info { * @numa_num: the max numa numbers of the scheduler. * @type_num: the max operation types of the scheduler. * @poll_func: the task's poll operation function. - * @sched_info: the context of the scheduler + * @numamap: a map of cpus to devices. + * @sched_info: the context of the scheduler. */ struct wd_sched_ctx { __u32 policy; __u32 type_num; __u16 numa_num; user_poll_func poll_func; + int numamap[NUMA_NUM_NODES]; struct wd_sched_info sched_info[0]; };
@@ -174,32 +176,12 @@ static __u32 session_sched_init_ctx(handle_t h_sched_ctx, void *sched_key, const return sched_get_next_pos_rr(region, NULL); }
-static int get_nearby_numa_id(handle_t h_sched_ctx) +static handle_t session_sched_init_rr(handle_t h_sched_ctx, void *sched_param) { -#define MAX_NUMA_DISTANCE 1024 struct wd_sched_ctx *sched_ctx = (struct wd_sched_ctx *)h_sched_ctx; - struct wd_sched_info *sched_info = sched_ctx->sched_info; + struct sched_params *param = (struct sched_params *)sched_param; int cpu = sched_getcpu(); int node = numa_node_of_cpu(cpu); - int dis = MAX_NUMA_DISTANCE; - int i, tmp, valid_id = -1; - - for (i = 0; i < sched_ctx->numa_num; i++) { - if (sched_info[i].valid) { - tmp = numa_distance(node, i); - if (dis > tmp) { - valid_id = i; - dis = tmp; - } - } - } - - return valid_id; -} - -static handle_t session_sched_init_rr(handle_t h_sched_ctx, void *sched_param) -{ - struct sched_params *param = (struct sched_params *)sched_param; struct sched_key *skey;
skey = malloc(sizeof(struct sched_key)); @@ -210,7 +192,7 @@ static handle_t session_sched_init_rr(handle_t h_sched_ctx, void *sched_param)
if (!param || param->numa_id < 0) { memset(skey, 0, sizeof(struct sched_key)); - skey->numa_id = get_nearby_numa_id(h_sched_ctx); + skey->numa_id = sched_ctx->numamap[node]; if (skey->numa_id < 0) { WD_ERR("failed to get valid sched numa region!\n"); free(skey); @@ -375,6 +357,42 @@ static struct wd_sched sched_table[SCHED_POLICY_BUTT] = { }, };
+static int wd_sched_get_nearby_numa_id(struct wd_sched_info *sched_info, int node, int numa_num) +{ + int dis = INT32_MAX; + int valid_id = -1; + int i, tmp; + + for (i = 0; i < numa_num; i++) { + if (sched_info[i].valid) { + tmp = numa_distance(node, i); + if (dis > tmp) { + valid_id = i; + dis = tmp; + } + } + } + + return valid_id; +} + +static void wd_sched_map_cpus_to_dev(struct wd_sched_ctx *sched_ctx) +{ + struct wd_sched_info *sched_info = sched_ctx->sched_info; + int *numamap = sched_ctx->numamap; + int i; + + memset(numamap, -1, sizeof(*numamap) * NUMA_NUM_NODES); + + for (i = 0; i < sched_ctx->numa_num; i++) { + if (sched_info[i].valid) + numamap[i] = i; + else + numamap[i] = wd_sched_get_nearby_numa_id(sched_info, i, + sched_ctx->numa_num); + } +} + int wd_sched_rr_instance(const struct wd_sched *sched, struct sched_params *param) { struct wd_sched_info *sched_info = NULL; @@ -429,6 +447,8 @@ int wd_sched_rr_instance(const struct wd_sched *sched, struct sched_params *para sched_info[numa_id].ctx_region[mode][type].valid = true; sched_info[numa_id].valid = true;
+ wd_sched_map_cpus_to_dev(sched_ctx); + pthread_mutex_init(&sched_info[numa_id].ctx_region[mode][type].lock, NULL);
-- 2.24.0