diff options
Diffstat (limited to 'src/Platform/Posix/Tss.c')
| -rw-r--r-- | src/Platform/Posix/Tss.c | 97 |
1 files changed, 97 insertions, 0 deletions
diff --git a/src/Platform/Posix/Tss.c b/src/Platform/Posix/Tss.c new file mode 100644 index 0000000..a16d653 --- /dev/null +++ b/src/Platform/Posix/Tss.c @@ -0,0 +1,97 @@ +#include "Thread.h" + +#include <BH/Thread.h> +#include <stdlib.h> +#include <string.h> + + +static int tssCleanupLock = 0; +static int tssCleanupSize = 0; +static BH_GenericCallback tssCleanupData[BH_MAX_TSS]; + +static int tssLock = 0; +static int tssReady = 0; +static pthread_key_t tssKey; + + +static void BH_TssKeyCleanup(void *data) +{ + int i; + + /* Lock cleanup table and call cleanups */ + BH_SpinlockLock(&tssCleanupLock); + for (i = 0; i < tssCleanupSize; i++) + tssCleanupData[i](((void **)data)[i]); + BH_SpinlockUnlock(&tssCleanupLock); + + free(data); +} + + +static void **BH_TssDataFetch(void) +{ + void **result; + + /* Get or setup TSS data */ + BH_SpinlockLock(&tssLock); + if (!tssReady) + { + if (pthread_key_create(&tssKey, BH_TssKeyCleanup)) + abort(); + tssReady = 1; + } + BH_SpinlockUnlock(&tssLock); + + /* Get or setup TSS data */ + result = pthread_getspecific(tssKey); + if (!result) + { + result = malloc(sizeof(void *) * BH_MAX_TSS); + if (!result) + abort(); + + memset(result, 0, sizeof(sizeof(void *) * BH_MAX_TSS)); + if (pthread_setspecific(tssKey, result)) + abort(); + } + + return result; +} + + +void BH_TssCleanup(void) +{ + BH_TssKeyCleanup(BH_TssDataFetch()); +} + + +int BH_TssCreate(BH_GenericCallback callback) +{ + int result; + + /* Lock info and set up cleanup function */ + BH_SpinlockLock(&tssCleanupLock); + if (tssCleanupSize < BH_MAX_TSS) + { + tssCleanupData[tssCleanupSize] = callback; + result = tssCleanupSize++; + } + else + result = BH_ERROR; + BH_SpinlockUnlock(&tssCleanupLock); + + return result; +} + + +void *BH_TssRead(int index) +{ + return BH_TssDataFetch()[index]; +} + + +void BH_TssWrite(int index, + void *value) +{ + BH_TssDataFetch()[index] = value; +} |
