perf: Key the interpreter symbol cache by Name rather than FastString
[ghc.git] / rts / TopHandler.c
blobbeea07e8e3c2281338c41f46b7a9bf9aa14cbfdb
1 #include "Rts.h"
2 #include "StablePtr.h"
3 #include "TopHandler.h"
5 #if defined(THREADED_RTS)
6 static Mutex m; // Protects the operations on topHandlerPtr,
7 // which aren't atomic
8 #endif
9 static StgStablePtr topHandlerPtr;
11 void rts_setMainThread(StgWeak *weak) {
12 ACQUIRE_LOCK(&m);
13 if (topHandlerPtr != NULL) {
14 freeStablePtr(topHandlerPtr); // OK to do under the lock
16 topHandlerPtr = getStablePtr((StgPtr)weak);
17 // referent is a Weak#
18 ASSERT(weak->header.info == &stg_WEAK_info);
20 // See Note [rts_setMainThread has an unsound type] in
21 // libraries/base/GHC/TopHandler.hs.
22 ASSERT(weak->key->header.info == &stg_TSO_info);
24 RELEASE_LOCK(&m);
27 StgTSO *getTopHandlerThread(void) {
28 ACQUIRE_LOCK(&m);
29 StgWeak *weak = (StgWeak*)deRefStablePtr(topHandlerPtr);
30 RELEASE_LOCK(&m);
31 if (weak == NULL) {
32 // topHandlerPtr was never initialised
33 return NULL;
35 const StgInfoTable *info = ACQUIRE_LOAD(&weak->header.info);
36 if (info == &stg_WEAK_info) {
37 StgClosure *key = ((StgWeak*)weak)->key;
39 // See Note [rts_setMainThread has an unsound type] in
40 // libraries/base/GHC/TopHandler.hs.
41 ASSERT(key->header.info == &stg_TSO_info);
43 return (StgTSO *)key;
44 } else if (info == &stg_DEAD_WEAK_info) {
45 return NULL;
46 } else {
47 barf("getTopHandlerThread: neither a WEAK nor a DEAD_WEAK: %p %p %d",
48 weak, info, info->type);
49 return NULL;
53 void initTopHandler(void) {
54 #if defined(THREADED_RTS)
55 initMutex(&m);
56 #endif
57 topHandlerPtr = NULL;
60 void exitTopHandler(void) {
61 freeStablePtr(topHandlerPtr);
62 topHandlerPtr = NULL;
63 #if defined(THREADED_RTS)
64 closeMutex(&m);
65 #endif