summaryrefslogtreecommitdiffstats
path: root/src/kernel
diff options
context:
space:
mode:
authorPatrick Williams <iawillia@us.ibm.com>2013-04-17 16:53:18 -0500
committerA. Patrick Williams III <iawillia@us.ibm.com>2013-04-18 10:34:59 -0500
commit01b01010e8076b9fa048a370f85c696d8a25ed9f (patch)
tree6e85035c5344802ed0d5d68b4be39d782154cfc7 /src/kernel
parentbb42935e42d82c247d81ea03c4242ceccc41b487 (diff)
downloadtalos-hostboot-01b01010e8076b9fa048a370f85c696d8a25ed9f.tar.gz
talos-hostboot-01b01010e8076b9fa048a370f85c696d8a25ed9f.zip
Add thread-safety to kernel interrupt handler.
The interrupt handling was originally written with the intent that only a single thread would receive interrupts. We purposefully program the Interrupt Presenter hardware to route all interrupts to a single core. IPIs (Inter-processor Interrupts) are not routable by the ICP and end up being delivered to the targeted thread. When we trigger a winkle-wakeup of a thread, that thread gets the IPI interrupt. Since we broadcast the IPI to all threads on a core there is potential for multiple threads to be using the interrupt object at once. Hence, we added a spinlock to protect it. Change-Id: I736de774496b13cc9f344d389b9f249bbabeb036 Tested-by: Jenkins Server Reviewed-by: Dean Sanner <dsanner@us.ibm.com> Reviewed-by: Daniel M. Crowell <dcrowell@us.ibm.com> Reviewed-by: A. Patrick Williams III <iawillia@us.ibm.com>
Diffstat (limited to 'src/kernel')
-rw-r--r--src/kernel/intmsghandler.C4
1 files changed, 4 insertions, 0 deletions
diff --git a/src/kernel/intmsghandler.C b/src/kernel/intmsghandler.C
index 0a6e87b0d..8bf68950c 100644
--- a/src/kernel/intmsghandler.C
+++ b/src/kernel/intmsghandler.C
@@ -99,11 +99,13 @@ void InterruptMsgHdlr::handleInterrupt()
if(cv_instance)
{
+ cv_instance->iv_lock.lock();
cv_instance->sendMessage(MSG_INTR_EXTERN,
reinterpret_cast<void*>(pir),
reinterpret_cast<void*>(
static_cast<uint64_t>(xirr)),
NULL);
+ cv_instance->iv_lock.unlock();
}
}
@@ -140,8 +142,10 @@ void InterruptMsgHdlr::addCpuCore(uint64_t i_pir)
// for the message to be an invalid PIR.
uint64_t pir_key = i_pir | 0x8000000000000000ul;
+ cv_instance->iv_lock.lock();
cv_instance->sendMessage(MSG_INTR_ADD_CPU,
(void*)pir_key,(void *)i_pir,t);
+ cv_instance->iv_lock.unlock();
}
}
OpenPOWER on IntegriCloud