Add missing windows conditions variable
Those are used by generic RW lock implementation. https://bugs.freedesktop.org/show_bug.cgi?id=96754
This commit is contained in:
parent
db2f422578
commit
6ad2f51e9e
@ -2,6 +2,7 @@ noinst_LTLIBRARIES = libsystem_wrappers.la
|
|||||||
|
|
||||||
noinst_HEADERS = include/aligned_array.h \
|
noinst_HEADERS = include/aligned_array.h \
|
||||||
include/asm_defines.h \
|
include/asm_defines.h \
|
||||||
|
include/condition_variable_wrapper.h \
|
||||||
include/compile_assert_c.h \
|
include/compile_assert_c.h \
|
||||||
include/event_wrapper.h \
|
include/event_wrapper.h \
|
||||||
include/scoped_vector.h \
|
include/scoped_vector.h \
|
||||||
@ -42,27 +43,49 @@ libsystem_wrappers_la_SOURCES = include/aligned_malloc.h \
|
|||||||
source/trace_impl.h \
|
source/trace_impl.h \
|
||||||
source/trace_posix.h \
|
source/trace_posix.h \
|
||||||
source/trace_win.h
|
source/trace_win.h
|
||||||
|
|
||||||
|
EXTRA_DIST = BUILD.gn
|
||||||
|
|
||||||
if HAVE_POSIX
|
if HAVE_POSIX
|
||||||
libsystem_wrappers_la_SOURCES += source/critical_section_posix.cc \
|
libsystem_wrappers_la_SOURCES += source/critical_section_posix.cc \
|
||||||
source/event_timer_posix.cc \
|
source/event_timer_posix.cc \
|
||||||
source/rw_lock_posix.cc \
|
source/rw_lock_posix.cc \
|
||||||
source/thread_posix.cc \
|
source/thread_posix.cc \
|
||||||
source/trace_posix.cc
|
source/trace_posix.cc
|
||||||
|
else
|
||||||
|
EXTRA_DIST += source/critical_section_posix.cc \
|
||||||
|
source/event_timer_posix.cc \
|
||||||
|
source/rw_lock_posix.cc \
|
||||||
|
source/thread_posix.cc \
|
||||||
|
source/trace_posix.cc
|
||||||
endif
|
endif
|
||||||
|
|
||||||
if HAVE_WIN
|
if HAVE_WIN
|
||||||
libsystem_wrappers_la_SOURCES += source/critical_section_win.cc \
|
libsystem_wrappers_la_SOURCES += include/fix_interlocked_exchange_pointer_win.h \
|
||||||
|
source/critical_section_win.cc \
|
||||||
|
source/condition_variable.cc \
|
||||||
|
source/condition_variable_event_win.cc \
|
||||||
|
source/condition_variable_event_win.h \
|
||||||
|
source/condition_variable_native_win.cc \
|
||||||
|
source/condition_variable_native_win.h \
|
||||||
source/event_timer_win.cc \
|
source/event_timer_win.cc \
|
||||||
source/rw_lock_win.cc \
|
source/rw_lock_win.cc \
|
||||||
source/rw_lock_generic.cc \
|
source/rw_lock_generic.cc \
|
||||||
source/thread_win.cc \
|
source/thread_win.cc \
|
||||||
source/trace_win.cc
|
source/trace_win.cc
|
||||||
|
else
|
||||||
|
EXTRA_DIST += include/fix_interlocked_exchange_pointer_win.h \
|
||||||
|
source/critical_section_win.cc \
|
||||||
|
source/condition_variable.cc \
|
||||||
|
source/condition_variable_event_win.cc \
|
||||||
|
source/condition_variable_event_win.h \
|
||||||
|
source/condition_variable_native_win.cc \
|
||||||
|
source/condition_variable_native_win.h \
|
||||||
|
source/event_timer_win.cc \
|
||||||
|
source/rw_lock_generic.cc \
|
||||||
|
source/rw_lock_win.cc \
|
||||||
|
source/thread_win.cc \
|
||||||
|
source/trace_win.cc
|
||||||
endif
|
endif
|
||||||
libsystem_wrappers_la_CXXFLAGS = $(AM_CXXFLAGS) $(COMMON_CXXFLAGS)
|
|
||||||
|
|
||||||
EXTRA_DIST = BUILD.gn \
|
libsystem_wrappers_la_CXXFLAGS = $(AM_CXXFLAGS) $(COMMON_CXXFLAGS)
|
||||||
source/critical_section_win.cc \
|
|
||||||
source/event_timer_win.cc \
|
|
||||||
source/rw_lock_generic.cc \
|
|
||||||
source/rw_lock_win.cc \
|
|
||||||
source/thread_win.cc \
|
|
||||||
source/trace_win.cc
|
|
||||||
|
42
webrtc/system_wrappers/include/condition_variable_wrapper.h
Normal file
42
webrtc/system_wrappers/include/condition_variable_wrapper.h
Normal file
@ -0,0 +1,42 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2011 The WebRTC project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef WEBRTC_SYSTEM_WRAPPERS_INCLUDE_CONDITION_VARIABLE_WRAPPER_H_
|
||||||
|
#define WEBRTC_SYSTEM_WRAPPERS_INCLUDE_CONDITION_VARIABLE_WRAPPER_H_
|
||||||
|
|
||||||
|
namespace webrtc {
|
||||||
|
|
||||||
|
class CriticalSectionWrapper;
|
||||||
|
|
||||||
|
class ConditionVariableWrapper {
|
||||||
|
public:
|
||||||
|
// Factory method, constructor disabled.
|
||||||
|
static ConditionVariableWrapper* CreateConditionVariable();
|
||||||
|
|
||||||
|
virtual ~ConditionVariableWrapper() {}
|
||||||
|
|
||||||
|
// Calling thread will atomically release crit_sect and wait until next
|
||||||
|
// some other thread calls Wake() or WakeAll().
|
||||||
|
virtual void SleepCS(CriticalSectionWrapper& crit_sect) = 0;
|
||||||
|
|
||||||
|
// Same as above but with a timeout.
|
||||||
|
virtual bool SleepCS(CriticalSectionWrapper& crit_sect,
|
||||||
|
unsigned long max_time_in_ms) = 0;
|
||||||
|
|
||||||
|
// Wakes one thread calling SleepCS().
|
||||||
|
virtual void Wake() = 0;
|
||||||
|
|
||||||
|
// Wakes all threads calling SleepCS().
|
||||||
|
virtual void WakeAll() = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace webrtc
|
||||||
|
|
||||||
|
#endif // WEBRTC_SYSTEM_WRAPPERS_INCLUDE_CONDITION_VARIABLE_WRAPPER_H_
|
41
webrtc/system_wrappers/source/condition_variable.cc
Normal file
41
webrtc/system_wrappers/source/condition_variable.cc
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2011 The WebRTC project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "webrtc/system_wrappers/include/condition_variable_wrapper.h"
|
||||||
|
|
||||||
|
#if defined(_WIN32)
|
||||||
|
#include <windows.h>
|
||||||
|
#include "webrtc/system_wrappers/source/condition_variable_event_win.h"
|
||||||
|
#include "webrtc/system_wrappers/source/condition_variable_native_win.h"
|
||||||
|
#elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC)
|
||||||
|
#include <pthread.h>
|
||||||
|
#include "webrtc/system_wrappers/source/condition_variable_posix.h"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
namespace webrtc {
|
||||||
|
|
||||||
|
ConditionVariableWrapper* ConditionVariableWrapper::CreateConditionVariable() {
|
||||||
|
#if defined(_WIN32)
|
||||||
|
// Try to create native condition variable implementation.
|
||||||
|
ConditionVariableWrapper* ret_val = ConditionVariableNativeWin::Create();
|
||||||
|
if (!ret_val) {
|
||||||
|
// Native condition variable implementation does not exist. Create generic
|
||||||
|
// condition variable based on events.
|
||||||
|
ret_val = new ConditionVariableEventWin();
|
||||||
|
}
|
||||||
|
return ret_val;
|
||||||
|
#elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC)
|
||||||
|
return ConditionVariablePosix::Create();
|
||||||
|
#else
|
||||||
|
return NULL;
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace webrtc
|
195
webrtc/system_wrappers/source/condition_variable_event_win.cc
Normal file
195
webrtc/system_wrappers/source/condition_variable_event_win.cc
Normal file
@ -0,0 +1,195 @@
|
|||||||
|
/*
|
||||||
|
Source:
|
||||||
|
http://www1.cse.wustl.edu/~schmidt/ACE-copying.html
|
||||||
|
|
||||||
|
License:
|
||||||
|
Copyright and Licensing Information for ACE(TM), TAO(TM), CIAO(TM), DAnCE(TM),
|
||||||
|
and CoSMIC(TM)
|
||||||
|
|
||||||
|
ACE(TM), TAO(TM), CIAO(TM), DAnCE>(TM), and CoSMIC(TM) (henceforth referred to
|
||||||
|
as "DOC software") are copyrighted by Douglas C. Schmidt and his research
|
||||||
|
group at Washington University, University of California, Irvine, and
|
||||||
|
Vanderbilt University, Copyright (c) 1993-2009, all rights reserved. Since DOC
|
||||||
|
software is open-source, freely available software, you are free to use,
|
||||||
|
modify, copy, and distribute--perpetually and irrevocably--the DOC software
|
||||||
|
source code and object code produced from the source, as well as copy and
|
||||||
|
distribute modified versions of this software. You must, however, include this
|
||||||
|
copyright statement along with any code built using DOC software that you
|
||||||
|
release. No copyright statement needs to be provided if you just ship binary
|
||||||
|
executables of your software products.
|
||||||
|
You can use DOC software in commercial and/or binary software releases and are
|
||||||
|
under no obligation to redistribute any of your source code that is built
|
||||||
|
using DOC software. Note, however, that you may not misappropriate the DOC
|
||||||
|
software code, such as copyrighting it yourself or claiming authorship of the
|
||||||
|
DOC software code, in a way that will prevent DOC software from being
|
||||||
|
distributed freely using an open-source development model. You needn't inform
|
||||||
|
anyone that you're using DOC software in your software, though we encourage
|
||||||
|
you to let us know so we can promote your project in the DOC software success
|
||||||
|
stories.
|
||||||
|
|
||||||
|
The ACE, TAO, CIAO, DAnCE, and CoSMIC web sites are maintained by the DOC
|
||||||
|
Group at the Institute for Software Integrated Systems (ISIS) and the Center
|
||||||
|
for Distributed Object Computing of Washington University, St. Louis for the
|
||||||
|
development of open-source software as part of the open-source software
|
||||||
|
community. Submissions are provided by the submitter ``as is'' with no
|
||||||
|
warranties whatsoever, including any warranty of merchantability,
|
||||||
|
noninfringement of third party intellectual property, or fitness for any
|
||||||
|
particular purpose. In no event shall the submitter be liable for any direct,
|
||||||
|
indirect, special, exemplary, punitive, or consequential damages, including
|
||||||
|
without limitation, lost profits, even if advised of the possibility of such
|
||||||
|
damages. Likewise, DOC software is provided as is with no warranties of any
|
||||||
|
kind, including the warranties of design, merchantability, and fitness for a
|
||||||
|
particular purpose, noninfringement, or arising from a course of dealing,
|
||||||
|
usage or trade practice. Washington University, UC Irvine, Vanderbilt
|
||||||
|
University, their employees, and students shall have no liability with respect
|
||||||
|
to the infringement of copyrights, trade secrets or any patents by DOC
|
||||||
|
software or any part thereof. Moreover, in no event will Washington
|
||||||
|
University, UC Irvine, or Vanderbilt University, their employees, or students
|
||||||
|
be liable for any lost revenue or profits or other special, indirect and
|
||||||
|
consequential damages.
|
||||||
|
|
||||||
|
DOC software is provided with no support and without any obligation on the
|
||||||
|
part of Washington University, UC Irvine, Vanderbilt University, their
|
||||||
|
employees, or students to assist in its use, correction, modification, or
|
||||||
|
enhancement. A number of companies around the world provide commercial support
|
||||||
|
for DOC software, however. DOC software is Y2K-compliant, as long as the
|
||||||
|
underlying OS platform is Y2K-compliant. Likewise, DOC software is compliant
|
||||||
|
with the new US daylight savings rule passed by Congress as "The Energy Policy
|
||||||
|
Act of 2005," which established new daylight savings times (DST) rules for the
|
||||||
|
United States that expand DST as of March 2007. Since DOC software obtains
|
||||||
|
time/date and calendaring information from operating systems users will not be
|
||||||
|
affected by the new DST rules as long as they upgrade their operating systems
|
||||||
|
accordingly.
|
||||||
|
|
||||||
|
The names ACE(TM), TAO(TM), CIAO(TM), DAnCE(TM), CoSMIC(TM), Washington
|
||||||
|
University, UC Irvine, and Vanderbilt University, may not be used to endorse
|
||||||
|
or promote products or services derived from this source without express
|
||||||
|
written permission from Washington University, UC Irvine, or Vanderbilt
|
||||||
|
University. This license grants no permission to call products or services
|
||||||
|
derived from this source ACE(TM), TAO(TM), CIAO(TM), DAnCE(TM), or CoSMIC(TM),
|
||||||
|
nor does it grant permission for the name Washington University, UC Irvine, or
|
||||||
|
Vanderbilt University to appear in their names.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This source code contain modifications to the original source code
|
||||||
|
* which can be found here:
|
||||||
|
* http://www.cs.wustl.edu/~schmidt/win32-cv-1.html (section 3.2).
|
||||||
|
* Modifications:
|
||||||
|
* 1) Dynamic detection of native support for condition variables.
|
||||||
|
* 2) Use of WebRTC defined types and classes. Renaming of some functions.
|
||||||
|
* 3) Introduction of a second event for wake all functionality. This prevents
|
||||||
|
* a thread from spinning on the same condition variable, preventing other
|
||||||
|
* threads from waking up.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "webrtc/system_wrappers/source/condition_variable_event_win.h"
|
||||||
|
#include "webrtc/system_wrappers/source/critical_section_win.h"
|
||||||
|
|
||||||
|
namespace webrtc {
|
||||||
|
|
||||||
|
ConditionVariableEventWin::ConditionVariableEventWin() : eventID_(WAKEALL_0) {
|
||||||
|
memset(&num_waiters_[0], 0, sizeof(num_waiters_));
|
||||||
|
|
||||||
|
InitializeCriticalSection(&num_waiters_crit_sect_);
|
||||||
|
|
||||||
|
events_[WAKEALL_0] = CreateEvent(NULL, // no security attributes
|
||||||
|
TRUE, // manual-reset, sticky event
|
||||||
|
FALSE, // initial state non-signaled
|
||||||
|
NULL); // no name for event
|
||||||
|
|
||||||
|
events_[WAKEALL_1] = CreateEvent(NULL, // no security attributes
|
||||||
|
TRUE, // manual-reset, sticky event
|
||||||
|
FALSE, // initial state non-signaled
|
||||||
|
NULL); // no name for event
|
||||||
|
|
||||||
|
events_[WAKE] = CreateEvent(NULL, // no security attributes
|
||||||
|
FALSE, // auto-reset, sticky event
|
||||||
|
FALSE, // initial state non-signaled
|
||||||
|
NULL); // no name for event
|
||||||
|
}
|
||||||
|
|
||||||
|
ConditionVariableEventWin::~ConditionVariableEventWin() {
|
||||||
|
CloseHandle(events_[WAKE]);
|
||||||
|
CloseHandle(events_[WAKEALL_1]);
|
||||||
|
CloseHandle(events_[WAKEALL_0]);
|
||||||
|
|
||||||
|
DeleteCriticalSection(&num_waiters_crit_sect_);
|
||||||
|
}
|
||||||
|
|
||||||
|
void ConditionVariableEventWin::SleepCS(CriticalSectionWrapper& crit_sect) {
|
||||||
|
SleepCS(crit_sect, INFINITE);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool ConditionVariableEventWin::SleepCS(CriticalSectionWrapper& crit_sect,
|
||||||
|
unsigned long max_time_in_ms) {
|
||||||
|
EnterCriticalSection(&num_waiters_crit_sect_);
|
||||||
|
|
||||||
|
// Get the eventID for the event that will be triggered by next
|
||||||
|
// WakeAll() call and start waiting for it.
|
||||||
|
const EventWakeUpType eventID =
|
||||||
|
(WAKEALL_0 == eventID_) ? WAKEALL_1 : WAKEALL_0;
|
||||||
|
|
||||||
|
++(num_waiters_[eventID]);
|
||||||
|
LeaveCriticalSection(&num_waiters_crit_sect_);
|
||||||
|
|
||||||
|
CriticalSectionWindows* cs =
|
||||||
|
static_cast<CriticalSectionWindows*>(&crit_sect);
|
||||||
|
LeaveCriticalSection(&cs->crit);
|
||||||
|
HANDLE events[2];
|
||||||
|
events[0] = events_[WAKE];
|
||||||
|
events[1] = events_[eventID];
|
||||||
|
const DWORD result = WaitForMultipleObjects(2, // Wait on 2 events.
|
||||||
|
events,
|
||||||
|
FALSE, // Wait for either.
|
||||||
|
max_time_in_ms);
|
||||||
|
|
||||||
|
const bool ret_val = (result != WAIT_TIMEOUT);
|
||||||
|
|
||||||
|
EnterCriticalSection(&num_waiters_crit_sect_);
|
||||||
|
--(num_waiters_[eventID]);
|
||||||
|
|
||||||
|
// Last waiter should only be true for WakeAll(). WakeAll() correspond
|
||||||
|
// to position 1 in events[] -> (result == WAIT_OBJECT_0 + 1)
|
||||||
|
const bool last_waiter = (result == WAIT_OBJECT_0 + 1) &&
|
||||||
|
(num_waiters_[eventID] == 0);
|
||||||
|
LeaveCriticalSection(&num_waiters_crit_sect_);
|
||||||
|
|
||||||
|
if (last_waiter) {
|
||||||
|
// Reset/unset the WakeAll() event since all threads have been
|
||||||
|
// released.
|
||||||
|
ResetEvent(events_[eventID]);
|
||||||
|
}
|
||||||
|
|
||||||
|
EnterCriticalSection(&cs->crit);
|
||||||
|
return ret_val;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ConditionVariableEventWin::Wake() {
|
||||||
|
EnterCriticalSection(&num_waiters_crit_sect_);
|
||||||
|
const bool have_waiters = (num_waiters_[WAKEALL_0] > 0) ||
|
||||||
|
(num_waiters_[WAKEALL_1] > 0);
|
||||||
|
LeaveCriticalSection(&num_waiters_crit_sect_);
|
||||||
|
|
||||||
|
if (have_waiters) {
|
||||||
|
SetEvent(events_[WAKE]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void ConditionVariableEventWin::WakeAll() {
|
||||||
|
EnterCriticalSection(&num_waiters_crit_sect_);
|
||||||
|
|
||||||
|
// Update current WakeAll() event
|
||||||
|
eventID_ = (WAKEALL_0 == eventID_) ? WAKEALL_1 : WAKEALL_0;
|
||||||
|
|
||||||
|
// Trigger current event
|
||||||
|
const EventWakeUpType eventID = eventID_;
|
||||||
|
const bool have_waiters = num_waiters_[eventID] > 0;
|
||||||
|
LeaveCriticalSection(&num_waiters_crit_sect_);
|
||||||
|
|
||||||
|
if (have_waiters) {
|
||||||
|
SetEvent(events_[eventID]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace webrtc
|
46
webrtc/system_wrappers/source/condition_variable_event_win.h
Normal file
46
webrtc/system_wrappers/source/condition_variable_event_win.h
Normal file
@ -0,0 +1,46 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef WEBRTC_SYSTEM_WRAPPERS_SOURCE_CONDITION_VARIABLE_EVENT_WIN_H_
|
||||||
|
#define WEBRTC_SYSTEM_WRAPPERS_SOURCE_CONDITION_VARIABLE_EVENT_WIN_H_
|
||||||
|
|
||||||
|
#include <windows.h>
|
||||||
|
|
||||||
|
#include "webrtc/system_wrappers/include/condition_variable_wrapper.h"
|
||||||
|
|
||||||
|
namespace webrtc {
|
||||||
|
|
||||||
|
class ConditionVariableEventWin : public ConditionVariableWrapper {
|
||||||
|
public:
|
||||||
|
ConditionVariableEventWin();
|
||||||
|
virtual ~ConditionVariableEventWin();
|
||||||
|
|
||||||
|
void SleepCS(CriticalSectionWrapper& crit_sect);
|
||||||
|
bool SleepCS(CriticalSectionWrapper& crit_sect, unsigned long max_time_inMS);
|
||||||
|
void Wake();
|
||||||
|
void WakeAll();
|
||||||
|
|
||||||
|
private:
|
||||||
|
enum EventWakeUpType {
|
||||||
|
WAKEALL_0 = 0,
|
||||||
|
WAKEALL_1 = 1,
|
||||||
|
WAKE = 2,
|
||||||
|
EVENT_COUNT = 3
|
||||||
|
};
|
||||||
|
|
||||||
|
unsigned int num_waiters_[2];
|
||||||
|
EventWakeUpType eventID_;
|
||||||
|
CRITICAL_SECTION num_waiters_crit_sect_;
|
||||||
|
HANDLE events_[EVENT_COUNT];
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace webrtc
|
||||||
|
|
||||||
|
#endif // WEBRTC_SYSTEM_WRAPPERS_SOURCE_CONDITION_VARIABLE_EVENT_WIN_H_
|
104
webrtc/system_wrappers/source/condition_variable_native_win.cc
Normal file
104
webrtc/system_wrappers/source/condition_variable_native_win.cc
Normal file
@ -0,0 +1,104 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "webrtc/system_wrappers/include/trace.h"
|
||||||
|
#include "webrtc/system_wrappers/source/condition_variable_native_win.h"
|
||||||
|
#include "webrtc/system_wrappers/source/critical_section_win.h"
|
||||||
|
|
||||||
|
namespace webrtc {
|
||||||
|
|
||||||
|
static HMODULE library = NULL;
|
||||||
|
static bool win_support_condition_variables_primitive = false;
|
||||||
|
|
||||||
|
PInitializeConditionVariable PInitializeConditionVariable_;
|
||||||
|
PSleepConditionVariableCS PSleepConditionVariableCS_;
|
||||||
|
PWakeConditionVariable PWakeConditionVariable_;
|
||||||
|
PWakeAllConditionVariable PWakeAllConditionVariable_;
|
||||||
|
|
||||||
|
typedef void (WINAPI *PInitializeConditionVariable)(PCONDITION_VARIABLE);
|
||||||
|
typedef BOOL (WINAPI *PSleepConditionVariableCS)(PCONDITION_VARIABLE,
|
||||||
|
PCRITICAL_SECTION, DWORD);
|
||||||
|
typedef void (WINAPI *PWakeConditionVariable)(PCONDITION_VARIABLE);
|
||||||
|
typedef void (WINAPI *PWakeAllConditionVariable)(PCONDITION_VARIABLE);
|
||||||
|
|
||||||
|
ConditionVariableNativeWin::ConditionVariableNativeWin() {
|
||||||
|
}
|
||||||
|
|
||||||
|
ConditionVariableNativeWin::~ConditionVariableNativeWin() {
|
||||||
|
}
|
||||||
|
|
||||||
|
ConditionVariableWrapper* ConditionVariableNativeWin::Create() {
|
||||||
|
ConditionVariableNativeWin* ret_val = new ConditionVariableNativeWin();
|
||||||
|
if (!ret_val->Init()) {
|
||||||
|
delete ret_val;
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
return ret_val;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool ConditionVariableNativeWin::Init() {
|
||||||
|
if (!library) {
|
||||||
|
// Native implementation is supported on Vista+.
|
||||||
|
library = LoadLibrary(TEXT("Kernel32.dll"));
|
||||||
|
// TODO(henrike): this code results in an attempt to load the above dll
|
||||||
|
// every time the previous attempt failed. Only try to load once.
|
||||||
|
if (library) {
|
||||||
|
// TODO(henrike): not thread safe as reading and writing to library is not
|
||||||
|
// serialized. Fix.
|
||||||
|
WEBRTC_TRACE(kTraceStateInfo, kTraceUtility, -1, "Loaded Kernel.dll");
|
||||||
|
|
||||||
|
PInitializeConditionVariable_ =
|
||||||
|
(PInitializeConditionVariable) GetProcAddress(
|
||||||
|
library, "InitializeConditionVariable");
|
||||||
|
PSleepConditionVariableCS_ = (PSleepConditionVariableCS) GetProcAddress(
|
||||||
|
library, "SleepConditionVariableCS");
|
||||||
|
PWakeConditionVariable_ = (PWakeConditionVariable) GetProcAddress(
|
||||||
|
library, "WakeConditionVariable");
|
||||||
|
PWakeAllConditionVariable_ = (PWakeAllConditionVariable) GetProcAddress(
|
||||||
|
library, "WakeAllConditionVariable");
|
||||||
|
|
||||||
|
if (PInitializeConditionVariable_ && PSleepConditionVariableCS_
|
||||||
|
&& PWakeConditionVariable_ && PWakeAllConditionVariable_) {
|
||||||
|
WEBRTC_TRACE(
|
||||||
|
kTraceStateInfo, kTraceUtility, -1,
|
||||||
|
"Loaded native condition variables");
|
||||||
|
win_support_condition_variables_primitive = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!win_support_condition_variables_primitive) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
PInitializeConditionVariable_(&condition_variable_);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ConditionVariableNativeWin::SleepCS(CriticalSectionWrapper& crit_sect) {
|
||||||
|
SleepCS(crit_sect, INFINITE);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool ConditionVariableNativeWin::SleepCS(CriticalSectionWrapper& crit_sect,
|
||||||
|
unsigned long max_time_in_ms) {
|
||||||
|
CriticalSectionWindows* cs =
|
||||||
|
static_cast<CriticalSectionWindows*>(&crit_sect);
|
||||||
|
BOOL ret_val = PSleepConditionVariableCS_(&condition_variable_,
|
||||||
|
&(cs->crit), max_time_in_ms);
|
||||||
|
return ret_val != 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ConditionVariableNativeWin::Wake() {
|
||||||
|
PWakeConditionVariable_(&condition_variable_);
|
||||||
|
}
|
||||||
|
|
||||||
|
void ConditionVariableNativeWin::WakeAll() {
|
||||||
|
PWakeAllConditionVariable_(&condition_variable_);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace webrtc
|
@ -0,0 +1,54 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef WEBRTC_SYSTEM_WRAPPERS_SOURCE_CONDITION_VARIABLE_NATIVE_WIN_H_
|
||||||
|
#define WEBRTC_SYSTEM_WRAPPERS_SOURCE_CONDITION_VARIABLE_NATIVE_WIN_H_
|
||||||
|
|
||||||
|
#include <windows.h>
|
||||||
|
|
||||||
|
#include "webrtc/system_wrappers/include/condition_variable_wrapper.h"
|
||||||
|
|
||||||
|
namespace webrtc {
|
||||||
|
|
||||||
|
#if !defined CONDITION_VARIABLE_INIT
|
||||||
|
typedef struct RTL_CONDITION_VARIABLE_ {
|
||||||
|
void* Ptr;
|
||||||
|
} RTL_CONDITION_VARIABLE, *PRTL_CONDITION_VARIABLE;
|
||||||
|
|
||||||
|
typedef RTL_CONDITION_VARIABLE CONDITION_VARIABLE, *PCONDITION_VARIABLE;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
typedef void (WINAPI* PInitializeConditionVariable)(PCONDITION_VARIABLE);
|
||||||
|
typedef BOOL (WINAPI* PSleepConditionVariableCS)(PCONDITION_VARIABLE,
|
||||||
|
PCRITICAL_SECTION, DWORD);
|
||||||
|
typedef void (WINAPI* PWakeConditionVariable)(PCONDITION_VARIABLE);
|
||||||
|
typedef void (WINAPI* PWakeAllConditionVariable)(PCONDITION_VARIABLE);
|
||||||
|
|
||||||
|
class ConditionVariableNativeWin : public ConditionVariableWrapper {
|
||||||
|
public:
|
||||||
|
static ConditionVariableWrapper* Create();
|
||||||
|
virtual ~ConditionVariableNativeWin();
|
||||||
|
|
||||||
|
void SleepCS(CriticalSectionWrapper& crit_sect);
|
||||||
|
bool SleepCS(CriticalSectionWrapper& crit_sect, unsigned long max_time_inMS);
|
||||||
|
void Wake();
|
||||||
|
void WakeAll();
|
||||||
|
|
||||||
|
private:
|
||||||
|
ConditionVariableNativeWin();
|
||||||
|
|
||||||
|
bool Init();
|
||||||
|
|
||||||
|
CONDITION_VARIABLE condition_variable_;
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace webrtc
|
||||||
|
|
||||||
|
#endif // WEBRTC_SYSTEM_WRAPPERS_SOURCE_CONDITION_VARIABLE_NATIVE_WIN_H_
|
Loading…
x
Reference in New Issue
Block a user