diff --git a/hypervisor/arch/x86/guest/vcpu.c b/hypervisor/arch/x86/guest/vcpu.c index a65d9ac5a..bc48c4d95 100755 --- a/hypervisor/arch/x86/guest/vcpu.c +++ b/hypervisor/arch/x86/guest/vcpu.c @@ -986,8 +986,7 @@ int32_t prepare_vcpu(struct acrn_vm *vm, uint16_t pcpu_id) vcpu->thread_obj.host_sp = build_stack_frame(vcpu); vcpu->thread_obj.switch_out = context_switch_out; vcpu->thread_obj.switch_in = context_switch_in; - vcpu->thread_obj.priority = get_vm_config(vm->vm_id)->vm_prio; - init_thread_data(&vcpu->thread_obj); + init_thread_data(&vcpu->thread_obj, &get_vm_config(vm->vm_id)->sched_params); for (i = 0; i < VCPU_EVENT_NUM; i++) { init_event(&vcpu->events[i]); } diff --git a/hypervisor/common/hv_main.c b/hypervisor/common/hv_main.c index 3f8b2c949..380175451 100644 --- a/hypervisor/common/hv_main.c +++ b/hypervisor/common/hv_main.c @@ -95,6 +95,7 @@ void run_idle_thread(void) { uint16_t pcpu_id = get_pcpu_id(); struct thread_object *idle = &per_cpu(idle, pcpu_id); + struct sched_params idle_params = {0}; char idle_name[16]; snprintf(idle_name, 16U, "idle%hu", pcpu_id); @@ -103,7 +104,8 @@ void run_idle_thread(void) idle->thread_entry = default_idle; idle->switch_out = NULL; idle->switch_in = NULL; - idle->priority = PRIO_IDLE; + idle_params.prio = PRIO_IDLE; + init_thread_data(idle, &idle_params); run_thread(idle); diff --git a/hypervisor/common/sched_bvt.c b/hypervisor/common/sched_bvt.c index 26a363da4..783730079 100644 --- a/hypervisor/common/sched_bvt.c +++ b/hypervisor/common/sched_bvt.c @@ -168,7 +168,7 @@ static void sched_bvt_deinit(struct sched_control *ctl) del_timer(&bvt_ctl->tick_timer); } -static void sched_bvt_init_data(struct thread_object *obj) +static void sched_bvt_init_data(struct thread_object *obj, __unused struct sched_params * params) { struct sched_bvt_data *data; diff --git a/hypervisor/common/sched_iorr.c b/hypervisor/common/sched_iorr.c index 929e59fad..039c47a92 100644 --- a/hypervisor/common/sched_iorr.c +++ b/hypervisor/common/sched_iorr.c @@ -132,7 +132,7 @@ void sched_iorr_deinit(struct sched_control *ctl) del_timer(&iorr_ctl->tick_timer); } -void sched_iorr_init_data(struct thread_object *obj) +void sched_iorr_init_data(struct thread_object *obj, __unused struct sched_params * params) { struct sched_iorr_data *data; diff --git a/hypervisor/common/sched_prio.c b/hypervisor/common/sched_prio.c index 8d16b452f..2ca517c93 100644 --- a/hypervisor/common/sched_prio.c +++ b/hypervisor/common/sched_prio.c @@ -11,6 +11,7 @@ struct sched_prio_data { /* keep list as the first item */ struct list_head list; + int priority; }; static int sched_prio_init(struct sched_control *ctl) @@ -25,12 +26,13 @@ static int sched_prio_init(struct sched_control *ctl) return 0; } -static void sched_prio_init_data(struct thread_object *obj) +static void sched_prio_init_data(struct thread_object *obj, struct sched_params *params) { struct sched_prio_data *data; data = (struct sched_prio_data *)obj->data; INIT_LIST_HEAD(&data->list); + data->priority = params->priority; } static struct thread_object *sched_prio_pick_next(struct sched_control *ctl) @@ -52,15 +54,15 @@ static void prio_queue_add(struct thread_object *obj) struct sched_prio_control *prio_ctl = (struct sched_prio_control *)obj->sched_ctl->priv; struct sched_prio_data *data = (struct sched_prio_data *)obj->data; - struct thread_object *iter_obj; + struct sched_prio_data *iter_data; struct list_head *pos; if (list_empty(&prio_ctl->prio_queue)) { list_add(&data->list, &prio_ctl->prio_queue); } else { list_for_each(pos, &prio_ctl->prio_queue) { - iter_obj = container_of(pos, struct thread_object, data); - if (iter_obj->priority < obj->priority) { + iter_data = container_of(pos, struct sched_prio_data, list); + if (iter_data->priority < data->priority) { list_add_node(&data->list, pos->prev, pos); break; } diff --git a/hypervisor/common/schedule.c b/hypervisor/common/schedule.c index 32cadd7b6..ce05b9a45 100644 --- a/hypervisor/common/schedule.c +++ b/hypervisor/common/schedule.c @@ -98,14 +98,14 @@ void deinit_sched(uint16_t pcpu_id) } } -void init_thread_data(struct thread_object *obj) +void init_thread_data(struct thread_object *obj, struct sched_params *params) { struct acrn_scheduler *scheduler = get_scheduler(obj->pcpu_id); uint64_t rflag; obtain_schedule_lock(obj->pcpu_id, &rflag); if (scheduler->init_data != NULL) { - scheduler->init_data(obj); + scheduler->init_data(obj, params); } /* initial as BLOCKED status, so we can wake it up to run */ set_thread_status(obj, THREAD_STS_BLOCKED); @@ -241,7 +241,6 @@ void run_thread(struct thread_object *obj) { uint64_t rflag; - init_thread_data(obj); obtain_schedule_lock(obj->pcpu_id, &rflag); get_cpu_var(sched_ctl).curr_obj = obj; set_thread_status(obj, THREAD_STS_RUNNING); diff --git a/hypervisor/include/arch/x86/asm/vm_config.h b/hypervisor/include/arch/x86/asm/vm_config.h index a489ab348..14311652b 100644 --- a/hypervisor/include/arch/x86/asm/vm_config.h +++ b/hypervisor/include/arch/x86/asm/vm_config.h @@ -15,6 +15,7 @@ #include #include #include +#include #define AFFINITY_CPU(n) (1UL << (n)) #define MAX_VCPUS_PER_VM MAX_PCPU_NUM @@ -170,7 +171,7 @@ struct acrn_vm_config { * GUEST_FLAG_LAPIC_PASSTHROUGH * We could add more guest flags in future; */ - uint32_t vm_prio; /* The priority for VM vCPU scheduling */ + struct sched_params sched_params; /* Scheduler params for vCPUs of this VM */ uint16_t companion_vm_id; /* The companion VM id for this VM */ struct acrn_vm_mem_config memory; /* memory configuration of VM */ struct epc_section epc; /* EPC memory configuration of VM */ diff --git a/hypervisor/include/common/schedule.h b/hypervisor/include/common/schedule.h index fa2a6e44f..b7131385f 100644 --- a/hypervisor/include/common/schedule.h +++ b/hypervisor/include/common/schedule.h @@ -34,6 +34,16 @@ enum thread_priority { PRIO_MAX }; +/* + * For now, we just have several parameters for all the schedulers. So we + * put them together here for simplicity. TODO When this structure grows big + * enough, we need to replace it with a union of parameters of different + * schedulers. + */ +struct sched_params { + uint32_t prio; /* The priority of a thread */ +}; + struct thread_object; typedef void (*thread_entry_t)(struct thread_object *obj); typedef void (*switch_t)(struct thread_object *obj); @@ -49,8 +59,6 @@ struct thread_object { switch_t switch_out; switch_t switch_in; - int priority; - uint8_t data[THREAD_DATA_SIZE]; }; @@ -70,7 +78,7 @@ struct acrn_scheduler { /* init scheduler */ int32_t (*init)(struct sched_control *ctl); /* init private data of scheduler */ - void (*init_data)(struct thread_object *obj); + void (*init_data)(struct thread_object *obj, struct sched_params *params); /* pick the next thread object */ struct thread_object* (*pick_next)(struct sched_control *ctl); /* put thread object into sleep */ @@ -120,7 +128,7 @@ void deinit_sched(uint16_t pcpu_id); void obtain_schedule_lock(uint16_t pcpu_id, uint64_t *rflag); void release_schedule_lock(uint16_t pcpu_id, uint64_t rflag); -void init_thread_data(struct thread_object *obj); +void init_thread_data(struct thread_object *obj, struct sched_params *params); void deinit_thread_data(struct thread_object *obj); void make_reschedule_request(uint16_t pcpu_id); diff --git a/misc/config_tools/data/generic_board/generic_code/hybrid/vm_configurations.c b/misc/config_tools/data/generic_board/generic_code/hybrid/vm_configurations.c index a9f983026..61edd6a02 100644 --- a/misc/config_tools/data/generic_board/generic_code/hybrid/vm_configurations.c +++ b/misc/config_tools/data/generic_board/generic_code/hybrid/vm_configurations.c @@ -22,7 +22,10 @@ struct acrn_vm_config /* Static configured VM0 */ CONFIG_PRE_STD_VM, .name = "SAFETY_VM0", - .vm_prio = PRIO_LOW, + .sched_params = + { + .prio = PRIO_LOW, + }, .companion_vm_id = 65535U, .guest_flags = (GUEST_FLAG_STATIC_VM), .cpu_affinity = VM0_CONFIG_CPU_AFFINITY, @@ -106,7 +109,10 @@ struct acrn_vm_config CONFIG_SERVICE_VM, .name = "ACRN_Service_VM", /* Allow Service VM to reboot the system since it is the highest priority VM. */ - .vm_prio = PRIO_LOW, + .sched_params = + { + .prio = PRIO_LOW, + }, .companion_vm_id = 65535U, .guest_flags = (GUEST_FLAG_STATIC_VM), .cpu_affinity = SERVICE_VM_CONFIG_CPU_AFFINITY, @@ -163,7 +169,10 @@ struct acrn_vm_config /* Static configured VM2 */ CONFIG_POST_STD_VM, .name = "POST_STD_VM1", - .vm_prio = PRIO_LOW, + .sched_params = + { + .prio = PRIO_LOW, + }, .companion_vm_id = 65535U, .guest_flags = (GUEST_FLAG_STATIC_VM), .cpu_affinity = VM2_CONFIG_CPU_AFFINITY, @@ -186,7 +195,10 @@ struct acrn_vm_config /* Static configured VM3 */ CONFIG_POST_STD_VM, .name = "POST_STD_VM2", - .vm_prio = PRIO_LOW, + .sched_params = + { + .prio = PRIO_LOW, + }, .companion_vm_id = 65535U, .guest_flags = (GUEST_FLAG_STATIC_VM), .cpu_affinity = VM3_CONFIG_CPU_AFFINITY, diff --git a/misc/config_tools/data/generic_board/generic_code/partitioned/vm_configurations.c b/misc/config_tools/data/generic_board/generic_code/partitioned/vm_configurations.c index 8bb214158..e39639eb1 100644 --- a/misc/config_tools/data/generic_board/generic_code/partitioned/vm_configurations.c +++ b/misc/config_tools/data/generic_board/generic_code/partitioned/vm_configurations.c @@ -25,7 +25,10 @@ struct acrn_vm_config vm_configs[CONFIG_MAX_VM_NUM] = { /* Static configured VM0 */ CONFIG_PRE_STD_VM, .name = "PRE_STD_VM0", - .vm_prio = PRIO_LOW, + .sched_params = + { + .prio = PRIO_LOW, + }, .companion_vm_id = 65535U, .guest_flags = (GUEST_FLAG_STATIC_VM), .cpu_affinity = VM0_CONFIG_CPU_AFFINITY, @@ -102,7 +105,10 @@ struct acrn_vm_config vm_configs[CONFIG_MAX_VM_NUM] = { /* Static configured VM1 */ CONFIG_PRE_STD_VM, .name = "PRE_STD_VM1", - .vm_prio = PRIO_LOW, + .sched_params = + { + .prio = PRIO_LOW, + }, .companion_vm_id = 65535U, .guest_flags = (GUEST_FLAG_STATIC_VM), .cpu_affinity = VM1_CONFIG_CPU_AFFINITY, diff --git a/misc/config_tools/data/generic_board/generic_code/shared/vm_configurations.c b/misc/config_tools/data/generic_board/generic_code/shared/vm_configurations.c index 10bf375fb..e2c3cfb30 100644 --- a/misc/config_tools/data/generic_board/generic_code/shared/vm_configurations.c +++ b/misc/config_tools/data/generic_board/generic_code/shared/vm_configurations.c @@ -17,7 +17,10 @@ struct acrn_vm_config vm_configs[CONFIG_MAX_VM_NUM] = { CONFIG_SERVICE_VM, .name = "ACRN_Service_VM", /* Allow Service VM to reboot the system since it is the highest priority VM. */ - .vm_prio = PRIO_LOW, + .sched_params = + { + .prio = PRIO_LOW, + }, .companion_vm_id = 65535U, .guest_flags = (GUEST_FLAG_STATIC_VM), .cpu_affinity = SERVICE_VM_CONFIG_CPU_AFFINITY, @@ -74,7 +77,10 @@ struct acrn_vm_config vm_configs[CONFIG_MAX_VM_NUM] = { /* Static configured VM1 */ CONFIG_POST_STD_VM, .name = "POST_STD_VM1", - .vm_prio = PRIO_LOW, + .sched_params = + { + .prio = PRIO_LOW, + }, .companion_vm_id = 65535U, .guest_flags = (GUEST_FLAG_STATIC_VM), .cpu_affinity = VM1_CONFIG_CPU_AFFINITY, @@ -105,7 +111,10 @@ struct acrn_vm_config vm_configs[CONFIG_MAX_VM_NUM] = { /* Static configured VM2 */ CONFIG_POST_RT_VM, .name = "POST_RT_VM1", - .vm_prio = PRIO_LOW, + .sched_params = + { + .prio = PRIO_LOW, + }, .companion_vm_id = 65535U, .guest_flags = (GUEST_FLAG_LAPIC_PASSTHROUGH | GUEST_FLAG_RT | GUEST_FLAG_STATIC_VM), .cpu_affinity = VM2_CONFIG_CPU_AFFINITY, diff --git a/misc/config_tools/xforms/vm_configurations.c.xsl b/misc/config_tools/xforms/vm_configurations.c.xsl index 64dce14d9..a2ef700cc 100644 --- a/misc/config_tools/xforms/vm_configurations.c.xsl +++ b/misc/config_tools/xforms/vm_configurations.c.xsl @@ -110,7 +110,10 @@ - + + + }, +