diff options
author | Patrick Williams <iawillia@us.ibm.com> | 2012-09-13 17:26:13 -0500 |
---|---|---|
committer | Daniel M. Crowell <dcrowell@us.ibm.com> | 2012-09-21 14:27:08 -0500 |
commit | f754a2a6f0079f3424e2368ae3c3635ac8440612 (patch) | |
tree | db7821f2e34e36f40fae69277e0cefb93573adaf /src/kernel | |
parent | 337654733b5bb5ba1a33b41c0fecf78c36185b13 (diff) | |
download | talos-hostboot-f754a2a6f0079f3424e2368ae3c3635ac8440612.tar.gz talos-hostboot-f754a2a6f0079f3424e2368ae3c3635ac8440612.zip |
Fixes for winkle state.
The memory profiling tools sometimes encountered a condition where
the kernel stack was becoming corrupted. I tracked it down to the
winkle code storing the winkle-save state at the wrong end of the
stack. Moving the winkle-save area to the bottom of the stack,
which is where I originally intended it to go.
Also noticed that the task issuing the winkle was in "running"
state while waiting for the cores to come out of winkle. Ensure
that the kernel updates the task state with a non-running status
while we are waiting for winkle to complete.
Change-Id: I07a56ea6f24cbc09362f9227d81915da5bc9f148
Reviewed-on: http://gfw160.austin.ibm.com:8080/gerrit/1737
Tested-by: Jenkins Server
Reviewed-by: Douglas R. Gilbert <dgilbert@us.ibm.com>
Reviewed-by: Daniel M. Crowell <dcrowell@us.ibm.com>
Diffstat (limited to 'src/kernel')
-rw-r--r-- | src/kernel/cpumgr.C | 11 | ||||
-rw-r--r-- | src/kernel/misc.C | 3 | ||||
-rw-r--r-- | src/kernel/start.S | 2 | ||||
-rw-r--r-- | src/kernel/syscall.C | 5 |
4 files changed, 16 insertions, 5 deletions
diff --git a/src/kernel/cpumgr.C b/src/kernel/cpumgr.C index 791d14703..db79a15bf 100644 --- a/src/kernel/cpumgr.C +++ b/src/kernel/cpumgr.C @@ -177,8 +177,15 @@ void CpuManager::startCPU(ssize_t i) } cpu->scheduler = &Singleton<Scheduler>::instance(); cpu->scheduler_extra = NULL; - cpu->kernel_stack = - (void*) (((uint64_t)PageManager::allocatePage(4)) + 16320); + + const size_t kernel_page_count = 4; + const size_t kernel_page_offset = kernel_page_count * PAGESIZE - + 8 * sizeof(uint64_t); + cpu->kernel_stack_bottom = PageManager::allocatePage(kernel_page_count); + cpu->kernel_stack = reinterpret_cast<void*>( + reinterpret_cast<uintptr_t>(cpu->kernel_stack_bottom) + + kernel_page_offset); + cpu->xscom_mutex = (mutex_t)MUTEX_INITIALIZER; // Create idle task. diff --git a/src/kernel/misc.C b/src/kernel/misc.C index 3754003d0..9b2872f04 100644 --- a/src/kernel/misc.C +++ b/src/kernel/misc.C @@ -162,7 +162,7 @@ namespace KernelMisc task_t* saveArea = new task_t; memset(saveArea, '\0', sizeof(task_t)); saveArea->context.msr_mask = 0xC030; // EE, PR, IR, DR. - *(reinterpret_cast<task_t**>(cpu->kernel_stack)) = saveArea; + *(reinterpret_cast<task_t**>(cpu->kernel_stack_bottom)) = saveArea; // Execute winkle. kernel_execute_winkle(saveArea); @@ -190,6 +190,7 @@ namespace KernelMisc setTB(iv_timebase); // Restore caller of cpu_master_winkle(). + iv_caller->state = TASK_STATE_RUNNING; TaskManager::setCurrentTask(iv_caller); } diff --git a/src/kernel/start.S b/src/kernel/start.S index 048c2411e..252014e6a 100644 --- a/src/kernel/start.S +++ b/src/kernel/start.S @@ -618,7 +618,7 @@ intvect_system_reset_inactive: beq+ _start ;// Now we are a winkled processor that is awoken. - ld r1, CPU_KERNEL_STACK(r2) + ld r1, CPU_KERNEL_STACK_BOTTOM(r2) ld r1, 0(r1) mtsprg3 r1 b kernel_dispatch_task diff --git a/src/kernel/syscall.C b/src/kernel/syscall.C index a38f08b78..4eb3b4fa8 100644 --- a/src/kernel/syscall.C +++ b/src/kernel/syscall.C @@ -701,7 +701,10 @@ namespace Systemcalls else { TASK_SETRTN(t, 0); - DeferredQueue::insert(new KernelMisc::WinkleCore(t)); + KernelMisc::WinkleCore* deferred = new KernelMisc::WinkleCore(t); + t->state = TASK_STATE_BLOCK_USRSPACE; + t->state_info = deferred; + DeferredQueue::insert(deferred); TaskManager::setCurrentTask(cpu->idle_task); DeferredQueue::execute(); } |