From dccbccbbd6f73ff9384b2342a66fb73f9c84d1cd Mon Sep 17 00:00:00 2001 From: Stefan Lankes Date: Tue, 5 Jan 2016 23:17:27 +0100 Subject: [PATCH] on a shutdown request, we shutdown the network und flush the cache --- hermit/arch/x86/kernel/apic.c | 24 ++++++++++++++++++++---- hermit/include/hermit/tasks.h | 6 +++++- hermit/kernel/main.c | 7 ++++++- hermit/kernel/tasks.c | 2 +- 4 files changed, 32 insertions(+), 7 deletions(-) diff --git a/hermit/arch/x86/kernel/apic.c b/hermit/arch/x86/kernel/apic.c index d3bf4d979..c3ce0fd48 100644 --- a/hermit/arch/x86/kernel/apic.c +++ b/hermit/arch/x86/kernel/apic.c @@ -62,6 +62,7 @@ typedef struct { static const apic_processor_entry_t* apic_processors[MAX_APIC_CORES] = {[0 ... MAX_APIC_CORES-1] = NULL}; extern int32_t boot_processor; extern uint32_t cpu_freq; +extern atomic_int32_t cpu_online; apic_mp_t* apic_mp __attribute__ ((section (".data"))) = NULL; static apic_config_table_t* apic_config = NULL; static size_t lapic = 0; @@ -736,17 +737,32 @@ static void apic_err_handler(struct state *s) static void apic_shutdown(struct state *s) { - kprintf("Receive an IPI to shutdown HermitCore\n"); + int if_bootprocessor = (apic_processors[boot_processor]->id == apic_cpu_id()); + + if (if_bootprocessor) { + kprintf("Receive an IPI to shutdown HermitCore\n"); + + while(atomic_int32_read(&cpu_online) != 1) + PAUSE; + + network_shutdown(); + + kprintf("Diable APIC timer\n"); + } - kprintf("Diable APIC timer\n"); apic_disable_timer(); - kprintf("Disable APIC\n"); + if (if_bootprocessor) + kprintf("Disable APIC\n"); + lapic_write(APIC_LVT_TSR, 0x10000); // disable thermal sensor interrupt lapic_write(APIC_LVT_PMC, 0x10000); // disable performance counter interrupt lapic_write(APIC_SVR, 0x00); // disable the apic - kprintf("System goes down...\n"); + if (if_bootprocessor) + kprintf("System goes down...\n"); + flush_cache(); + atomic_int32_dec(&cpu_online); HALT; kprintf("Ups, we should never reach this point!\n"); diff --git a/hermit/include/hermit/tasks.h b/hermit/include/hermit/tasks.h index 55c3148d7..088a254ef 100644 --- a/hermit/include/hermit/tasks.h +++ b/hermit/include/hermit/tasks.h @@ -206,9 +206,13 @@ void NORETURN do_abort(void); void NORETURN leave_kernel_task(void); /** @brief if a task exists with higher priority, HermitCore switch to it. - * */ + */ void check_scheduling(void); +/** @brief This function shutdowns the (ip) network + */ +int network_shutdown(void); + #ifdef DYNAMIC_TICKS /** @brief check, if the tick counter has to be updated * */ diff --git a/hermit/kernel/main.c b/hermit/kernel/main.c index 48109d371..f3c53646c 100644 --- a/hermit/kernel/main.c +++ b/hermit/kernel/main.c @@ -188,8 +188,13 @@ static int init_netifs(void) return 0; } -static int network_shutdown(void) +int network_shutdown(void) { + kputs("Shutdown LwIP\n"); + + if (libc_sd > 0) + closesocket(libc_sd); + mmnif_shutdown(); netifapi_netif_set_down(&mmnif_netif); diff --git a/hermit/kernel/tasks.c b/hermit/kernel/tasks.c index 0d69123aa..9b02ced30 100644 --- a/hermit/kernel/tasks.c +++ b/hermit/kernel/tasks.c @@ -460,7 +460,7 @@ int create_task(tid_t* id, entry_point_t ep, void* arg, uint8_t prio, uint32_t c } if (!ret) - kprintf("start new thread %d on core %d with stack address %p\n", i, core_id, stack); + kprintf("start new task %d on core %d with stack address %p\n", i, core_id, stack); out: spinlock_irqsave_unlock(&table_lock);