logo

最近遇到一个core dump,初步分析是double checked locking问题
双重检查目的避免对象创建后,避免不必要的锁。然而由于编译器优化,会产生问题。
e.g. 一般是这样实现的:

Singleton* Singleton::getInstance() {
    if (m_instance == NULL) { // 1st test
        Lock lock;
        if (m_instance == NULL) { // 2nd test
        m_instance = new Singleton;
        }
    }
return m_instance;
}

c++11中可以采用memory fence来保证顺序。

std::atomic<Singleton*> Singleton::m_instance;
std::mutex Singleton::m_mutex;

Singleton* Singleton::getInstance() {
    Singleton* tmp = m_instance.load(std::memory_order_relaxed);
    std::atomic_thread_fence(std::memory_order_acquire);
    if (tmp == nullptr) {
        std::lock_guard<std::mutex> lock(m_mutex);
        tmp = m_instance.load(std::memory_order_relaxed);
        if (tmp == nullptr) {
            tmp = new Singleton;
            std::atomic_thread_fence(std::memory_order_release);
            m_instance.store(tmp, std::memory_order_relaxed);
        }
    }
    return tmp;
}

more:http://preshing.com/20130930/double-checked-locking-is-fixed-in-cpp11/

0 回复
需要 登录 后方可回复, 如果你还没有账号你可以 注册 一个帐号。