00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011 #ifndef _SK_RT_LOCK_H_
00012 #define _SK_RT_LOCK_H_
00013
00014 #include <sk/util/Object.h>
00015
00016 namespace sk {
00017 namespace rt {
00018 class Lock
00019 : public virtual sk::util::Object
00020 {
00021 public:
00022 virtual void lock() = 0;
00023 virtual bool tryLock() = 0;
00024 virtual void unlock() = 0;
00025 virtual bool isLocked() const = 0;
00026
00027 template<typename R, typename T, typename TMF>
00028 R synchronize(T& target, TMF method);
00029
00030 template<typename T, typename TMF>
00031 void synchronize(T& target, TMF method);
00032
00033 template<typename T, typename TMF, typename P>
00034 void synchronize(T& target, TMF method, P& param);
00035
00036 template<typename T>
00037 void synchronize(T& target);
00038
00039 template<typename T>
00040 void synchronize(const T& target);
00041
00042 template<typename T, typename TMF, typename P>
00043 struct MemberFunctionWithParamInvocator;
00044 };
00045
00046 typedef void (function_t)();
00047 template<> void Lock::synchronize<function_t>(function_t& function);
00048 }
00049 }
00050
00051 template<typename R, typename T, typename TMF>
00052 R
00053 sk::rt::Lock::
00054 synchronize(T& target, TMF method)
00055 {
00056 lock();
00057
00058 try {
00059 R result = (target.*method)();
00060 unlock();
00061 return result;
00062 }
00063 catch(...) {
00064 unlock();
00065 throw;
00066 }
00067 }
00068
00069 template<typename T, typename TMF>
00070 void
00071 sk::rt::Lock::
00072 synchronize(T& target, TMF method)
00073 {
00074 lock();
00075
00076 try {
00077 (target.*method)();
00078 }
00079 catch(...) {
00080 unlock();
00081 throw;
00082 }
00083 unlock();
00084 }
00085
00086
00087
00088
00089
00090
00091
00092 template<typename T, typename TMF, typename P>
00093 void
00094 sk::rt::Lock::
00095 synchronize(T& target, TMF method, P& param)
00096 {
00097 lock();
00098
00099 try {
00100 (target.*method)(param);
00101 }
00102 catch(...) {
00103 unlock();
00104 throw;
00105 }
00106 unlock();
00107 }
00108
00109 #if 0
00110
00111 template<typename T, typename TMF, typename P>
00112 struct sk::rt::Lock::MemberFunctionWithParamInvocator {
00113 MemberFunctionWithParamInvocator(T& target, TMF method, P& param)
00114 : _target(target), _method(method), _param(param) {}
00115
00116 void invoke() {
00117 (_target.*_method)(_param);
00118 }
00119 T& _target;
00120 TMF _method;
00121 P& _param;
00122 };
00123
00124 template<typename T, typename TMF, typename P>
00125 void
00126 sk::rt::Lock::
00127 synchronize(T& target, TMF method, P& param)
00128 {
00129 MemberFunctionWithParamInvocator<T, TMF, P> invocator(target, method, param);
00130 synchronize(invocator, &MemberFunctionWithParamInvocator<T, TMF, P>::invoke);
00131 }
00132
00133 #endif
00134
00135 template<typename T>
00136 void
00137 sk::rt::Lock::
00138 synchronize(T& target)
00139 {
00140 synchronize(target, &T::operator());
00141 }
00142
00143 template<typename T>
00144 void
00145 sk::rt::Lock::
00146 synchronize(const T& target)
00147 {
00148 synchronize(target, &T::operator());
00149 }
00150
00151 #endif