Skip to content

Commit 11e67f1

Browse files
fyin1wenlingz
authored andcommitted
softirq: move softirq from hv_main to interrupt context
softirq shouldn't be bounded to vcpu thread. One issue for this is shell (based on timer) can't work if we don't start any guest. This change also is trying best to make softirq handler running with irq enabled. Also update the irq disable/enabel in vmexit handler to align with the usage in vcpu_thread. Tracked-On: #3387 Signed-off-by: Yin Fengwei <fengwei.yin@intel.com> Acked-by: Anthony Xu <anthony.xu@intel.com>
1 parent cb9866b commit 11e67f1

File tree

5 files changed

+31
-8
lines changed

5 files changed

+31
-8
lines changed

hypervisor/arch/x86/guest/vmexit.c

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -224,9 +224,15 @@ int32_t vmexit_handler(struct acrn_vcpu *vcpu)
224224
/* exit dispatch handling */
225225
if (basic_exit_reason == VMX_EXIT_REASON_EXTERNAL_INTERRUPT) {
226226
/* Handling external_interrupt should disable intr */
227-
CPU_IRQ_DISABLE();
227+
if (!is_lapic_pt_enabled(vcpu)) {
228+
CPU_IRQ_DISABLE();
229+
}
230+
228231
ret = dispatch->handler(vcpu);
229-
CPU_IRQ_ENABLE();
232+
233+
if (!is_lapic_pt_enabled(vcpu)) {
234+
CPU_IRQ_ENABLE();
235+
}
230236
} else {
231237
ret = dispatch->handler(vcpu);
232238
}

hypervisor/arch/x86/irq.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -361,6 +361,8 @@ void dispatch_interrupt(const struct intr_excp_ctx *ctx)
361361
} else {
362362
handle_spurious_interrupt(vr);
363363
}
364+
365+
do_softirq();
364366
}
365367

366368
void dispatch_exception(struct intr_excp_ctx *ctx)

hypervisor/common/hv_main.c

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -28,11 +28,7 @@ void vcpu_thread(struct sched_object *obj)
2828
}
2929

3030
if (!is_lapic_pt_enabled(vcpu)) {
31-
/* handle pending softirq when irq enable*/
32-
do_softirq();
3331
CPU_IRQ_DISABLE();
34-
/* handle risk softirq when disabling irq*/
35-
do_softirq();
3632
}
3733

3834
/* Don't open interrupt window between here and vmentry */

hypervisor/common/softirq.c

Lines changed: 20 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -32,9 +32,8 @@ void fire_softirq(uint16_t nr)
3232
bitmap_set_lock(nr, &per_cpu(softirq_pending, get_pcpu_id()));
3333
}
3434

35-
void do_softirq(void)
35+
static void do_softirq_internal(uint16_t cpu_id)
3636
{
37-
uint16_t cpu_id = get_pcpu_id();
3837
volatile uint64_t *softirq_pending_bitmap =
3938
&per_cpu(softirq_pending, cpu_id);
4039
uint16_t nr = ffs64(*softirq_pending_bitmap);
@@ -45,3 +44,22 @@ void do_softirq(void)
4544
nr = ffs64(*softirq_pending_bitmap);
4645
}
4746
}
47+
48+
/*
49+
* @pre: this function will only be called with irq disabled
50+
*/
51+
void do_softirq(void)
52+
{
53+
uint16_t cpu_id = get_pcpu_id();
54+
55+
if (per_cpu(softirq_servicing, cpu_id) == 0U) {
56+
per_cpu(softirq_servicing, cpu_id) = 1U;
57+
58+
CPU_IRQ_ENABLE();
59+
do_softirq_internal(cpu_id);
60+
CPU_IRQ_DISABLE();
61+
62+
do_softirq_internal(cpu_id);
63+
per_cpu(softirq_servicing, cpu_id) = 0U;
64+
}
65+
}

hypervisor/include/arch/x86/per_cpu.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,7 @@ struct per_cpu_region {
4848
uint8_t stack[CONFIG_STACK_SIZE] __aligned(16);
4949
uint32_t lapic_id;
5050
uint32_t lapic_ldr;
51+
uint32_t softirq_servicing;
5152
struct smp_call_info_data smp_call_info;
5253
#ifdef PROFILING_ON
5354
struct profiling_info_wrapper profiling_info;

0 commit comments

Comments
 (0)