Thread Safety in C

前端 未结 9 1956
余生分开走
余生分开走 2021-02-02 01:01

imagine I write a library in C. Further, imagine this library to be used from a multi-threaded environment. How do I make it thread-safe? More specific: How do

9条回答
  •  醉话见心
    2021-02-02 01:22

    You can create wrappers with #ifdef. It's really the best you can do. (Or you can use a third party library to do this).

    I'll show how I did it as an example for windows and linux. It's in C++ and not C but again it's just an example:

    #ifdef WIN32
    typedef HANDLE thread_t;
    typedef unsigned ThreadEntryFunction;
    #define thread __declspec(thread)
    
    class Mutex : NoCopyAssign
    {
    public:
        Mutex() { InitializeCriticalSection(&mActual); }
        ~Mutex() { DeleteCriticalSection(&mActual); }
        void Lock() { EnterCriticalSection(&mActual); }
        void Unlock() { LeaveCriticalSection(&mActual); }
    private:
        CRITICAL_SECTION mActual;
    };
    
    class ThreadEvent : NoCopyAssign
    {
    public:
        ThreadEvent() { Actual = CreateEvent(NULL, false, false, NULL); }
        ~ThreadEvent() { CloseHandle(Actual); }
        void Send() { SetEvent(Actual); }
    
        HANDLE Actual;
    };
    #else
    typedef pthread_t thread_t;
    typedef void *ThreadEntryFunction;
    #define thread __thread
    extern pthread_mutexattr_t MutexAttributeRecursive;
    
    class Mutex : NoCopyAssign
    {
    public:
        Mutex() { pthread_mutex_init(&mActual, &MutexAttributeRecursive); }
        ~Mutex() { pthread_mutex_destroy(&mActual); }
        void Lock() { pthread_mutex_lock(&mActual); }
        void Unlock() { pthread_mutex_unlock(&mActual); }
    private:
        pthread_mutex_t mActual;
    };
    
    class ThreadEvent : NoCopyAssign
    {
    public:
        ThreadEvent() { pthread_cond_init(&mActual, NULL); }
        ~ThreadEvent() { pthread_cond_destroy(&mActual); }
    
        void Send() { pthread_cond_signal(&mActual); }
    private:
        pthread_cond_t mActual;
    };
    
    inline thread_t GetCurrentThread() { return pthread_self(); }
    #endif
    
    /* Allows for easy mutex locking */
    class MutexLock : NoAssign
    {
    public:
        MutexLock(Mutex &m) : mMutex(m) { mMutex.Lock(); }
        ~MutexLock() { mMutex.Unlock(); }
    private:
        Mutex &mMutex;
    };
    

提交回复
热议问题