Line data Source code
1 : #include "uhallibs/ipc/RobustMutex.hpp"
2 :
3 : #include "uhal/log/log.hpp"
4 : #include <cstring>
5 :
6 : namespace uhallibs {
7 : namespace ipc {
8 :
9 0 : RobustMutex::RobustMutex()
10 0 : : mCount(0)
11 0 : , mSessionActive(false)
12 : {
13 0 : pthread_mutexattr_t lAttr;
14 :
15 0 : int s = pthread_mutexattr_init(&lAttr);
16 0 : if (s != 0) {
17 0 : exception::MutexError lExc;
18 0 : log(lExc, "Error code ", uhal::Integer(s), " (", strerror(s), ") returned in mutex attr initialisation");
19 0 : throw lExc;
20 0 : }
21 :
22 0 : s = pthread_mutexattr_setpshared(&lAttr, PTHREAD_PROCESS_SHARED);
23 0 : if (s != 0) {
24 0 : exception::MutexError lExc;
25 0 : log(lExc, "Error code ", uhal::Integer(s), " (", strerror(s), ") returned by pthread_mutexattr_setpshared");
26 0 : throw lExc;
27 0 : }
28 :
29 0 : s = pthread_mutexattr_setrobust(&lAttr, PTHREAD_MUTEX_ROBUST);
30 0 : if (s != 0) {
31 0 : exception::MutexError lExc;
32 0 : log(lExc, "Error code ", uhal::Integer(s), " (", strerror(s), ") returned by pthread_mutexattr_setrobust");
33 0 : throw lExc;
34 0 : }
35 :
36 0 : s = pthread_mutex_init(&mMutex, &lAttr);
37 0 : if (s != 0) {
38 0 : exception::MutexError lExc;
39 0 : log(lExc, "Error code ", uhal::Integer(s), " (", strerror(s), ") returned in mutex initialisation");
40 0 : throw lExc;
41 0 : }
42 0 : }
43 :
44 0 : RobustMutex::~RobustMutex() {}
45 :
46 : void
47 0 : RobustMutex::lock()
48 : {
49 0 : int s = pthread_mutex_lock(&mMutex);
50 0 : bool lLastOwnerDied = (s == EOWNERDEAD);
51 0 : if (lLastOwnerDied)
52 0 : s = pthread_mutex_consistent(&mMutex);
53 :
54 0 : if (s != 0) {
55 0 : exception::MutexError lExc;
56 0 : log(lExc,
57 : "Error code ",
58 0 : uhal::Integer(s),
59 : " (",
60 0 : strerror(s),
61 : ") returned when ",
62 0 : lLastOwnerDied ? "making mutex state consistent" : "locking mutex");
63 0 : throw lExc;
64 0 : }
65 0 : }
66 :
67 : void
68 0 : RobustMutex::unlock()
69 : {
70 0 : int s = pthread_mutex_unlock(&mMutex);
71 0 : if (s != 0)
72 0 : log(uhal::Error(), "Error code ", uhal::Integer(s), " (", strerror(s), ") returned when unlocking mutex");
73 0 : }
74 :
75 : uint64_t
76 0 : RobustMutex::getCounter() const
77 : {
78 0 : return mCount;
79 : }
80 :
81 : bool
82 0 : RobustMutex::isActive() const
83 : {
84 0 : return mSessionActive;
85 : }
86 :
87 : void
88 0 : RobustMutex::startSession()
89 : {
90 0 : mCount++;
91 0 : mSessionActive = true;
92 0 : }
93 :
94 : void
95 0 : RobustMutex::endSession()
96 : {
97 0 : mSessionActive = false;
98 0 : }
99 :
100 : } // namespace ipc
101 : } // namespace uhal
|