1b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org/* 2b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. 3b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * 4b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * Use of this source code is governed by a BSD-style license 5b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * that can be found in the LICENSE file in the root of the source 6b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * tree. An additional intellectual property rights grant can be found 7b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * in the file PATENTS. All contributing project authors may 8b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org * be found in the AUTHORS file in the root of the source tree. 9b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org */ 10b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 11ba41365cf8e326bff31b693ddef75ba1c38c23a0phoglund@webrtc.org#include "webrtc/system_wrappers/source/rw_lock_generic.h" 12b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 13ba41365cf8e326bff31b693ddef75ba1c38c23a0phoglund@webrtc.org#include "webrtc/system_wrappers/interface/condition_variable_wrapper.h" 14ba41365cf8e326bff31b693ddef75ba1c38c23a0phoglund@webrtc.org#include "webrtc/system_wrappers/interface/critical_section_wrapper.h" 15b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 16b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgnamespace webrtc { 17b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 18b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgRWLockGeneric::RWLockGeneric() 19b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org : readers_active_(0), 20b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org writer_active_(false), 21b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org readers_waiting_(0), 22b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org writers_waiting_(0) { 23b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org critical_section_ = CriticalSectionWrapper::CreateCriticalSection(); 24b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org read_condition_ = ConditionVariableWrapper::CreateConditionVariable(); 25b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org write_condition_ = ConditionVariableWrapper::CreateConditionVariable(); 26b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 27b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 28b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgRWLockGeneric::~RWLockGeneric() { 29b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org delete write_condition_; 30b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org delete read_condition_; 31b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org delete critical_section_; 32b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 33b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 34b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgvoid RWLockGeneric::AcquireLockExclusive() { 35b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org CriticalSectionScoped cs(critical_section_); 36b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (writer_active_ || readers_active_ > 0) { 37b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org ++writers_waiting_; 38b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org while (writer_active_ || readers_active_ > 0) { 39b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org write_condition_->SleepCS(*critical_section_); 40b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 41b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org --writers_waiting_; 42b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 43b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org writer_active_ = true; 44b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 45b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 46b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgvoid RWLockGeneric::ReleaseLockExclusive() { 47b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org CriticalSectionScoped cs(critical_section_); 48b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org writer_active_ = false; 49b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (writers_waiting_ > 0) { 50b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org write_condition_->Wake(); 51b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } else if (readers_waiting_ > 0) { 52b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org read_condition_->WakeAll(); 53b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 54b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 55b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 56b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgvoid RWLockGeneric::AcquireLockShared() { 57b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org CriticalSectionScoped cs(critical_section_); 58b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (writer_active_ || writers_waiting_ > 0) { 59b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org ++readers_waiting_; 60b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 61b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org while (writer_active_ || writers_waiting_ > 0) { 62b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org read_condition_->SleepCS(*critical_section_); 63b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 64b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org --readers_waiting_; 65b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 66b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org ++readers_active_; 67b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 68b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 69b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.orgvoid RWLockGeneric::ReleaseLockShared() { 70b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org CriticalSectionScoped cs(critical_section_); 71b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org --readers_active_; 72b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org if (readers_active_ == 0 && writers_waiting_ > 0) { 73b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org write_condition_->Wake(); 74b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org } 75b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} 76b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org 77b015cbede88899f67a53fbbe581b02ce8e32794andrew@webrtc.org} // namespace webrtc 78