У меня есть сокет, разделенный между 4 потоками, и я хотел использовать принцип RAII для получения и освобождения мьютекса.
Основные реалии
- Я использую библиотеку pthread.
- Я не могу использовать Boost.
- Я не могу использовать ничего новее, чем C ++ 03.
- Я не могу использовать исключения.
Фон
Вместо того, чтобы блокировать мьютекс для сокета каждый раз перед его использованием, а затем разблокировать мьютекс сразу после этого, я подумал, что мог бы написать scoped_lock()
, который блокировал бымьютекс, и как только он выходит из области видимости, он автоматически разблокирует мьютекс.
Итак, я просто делаю блокировку в конструкторе и разблокировку в деструкторе, как показано здесь.
ScopedLock::ScopedLock(pthread_mutex_t& mutex, int& errorCode)
: m_Mutex(mutex)
{
errorCode = m_lock();
}
ScopedLock::~ScopedLock()
{
errorCode = m_unlock();
}
, где m_lock()
и m_unlock()
- это просто две функции-обертки вокруг функций pthread_mutex_lock()
и pthread_mutex_unlock()
, соответственно, с некоторыми дополнительными tracelines / logging.
Таким образом, яне нужно было бы писать как минимум два оператора разблокировки, одно для хорошего случая и одно для плохого (по крайней мере, в некоторых ситуациях может быть больше неверных путей).
Проблема
Проблема, с которой я столкнулсяЯ столкнулся с тем, что мне не нравится в этой схеме - деструктор.
Я старательно сделал для каждой функции обработку ошибок, но от деструктора этого ScopedLock()
я не могу сообщитьвызывающая сторона о любых ошибках, которые могут быть возвращены моим m_unlock()
.