1 /*
2  * %CopyrightBegin%
3  *
4  * Copyright Ericsson AB 2009-2016. All Rights Reserved.
5  *
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  *     http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  *
18  * %CopyrightEnd%
19  */
20 
21 /*
22  * Author: Rickard Green
23  */
24 
25 #define ETHR_EVENT_OFF_WAITER__		((ethr_sint32_t) -1)
26 #define ETHR_EVENT_OFF__		((ethr_sint32_t) 1)
27 #define ETHR_EVENT_ON__ 		((ethr_sint32_t) 0)
28 
29 typedef struct {
30     ethr_atomic32_t state;
31     HANDLE handle;
32 } ethr_event;
33 
34 #if defined(ETHR_TRY_INLINE_FUNCS) || defined(ETHR_EVENT_IMPL__)
35 
36 #pragma intrinsic(_InterlockedExchange)
37 
38 static ETHR_INLINE void
ETHR_INLINE_FUNC_NAME_(ethr_event_set)39 ETHR_INLINE_FUNC_NAME_(ethr_event_set)(ethr_event *e)
40 {
41     /* _InterlockedExchange() imply a full memory barrier which is important */
42     ethr_sint32_t state = ethr_atomic32_xchg_wb(&e->state, ETHR_EVENT_ON__);
43     if (state == ETHR_EVENT_OFF_WAITER__) {
44 	if (!SetEvent(e->handle))
45 	    ETHR_FATAL_ERROR__(ethr_win_get_errno__());
46     }
47 }
48 
49 static ETHR_INLINE void
ETHR_INLINE_FUNC_NAME_(ethr_event_reset)50 ETHR_INLINE_FUNC_NAME_(ethr_event_reset)(ethr_event *e)
51 {
52     ethr_atomic32_set(&e->state, ETHR_EVENT_OFF__);
53     ETHR_MEMORY_BARRIER;
54 }
55 
56 #endif
57 
58 int ethr_event_init(ethr_event *e);
59 int ethr_event_prepare_timed(ethr_event *e);
60 int ethr_event_destroy(ethr_event *e);
61 int ethr_event_wait(ethr_event *e);
62 int ethr_event_swait(ethr_event *e, int spincount);
63 int ethr_event_twait(ethr_event *e, ethr_sint64_t timeout);
64 int ethr_event_stwait(ethr_event *e, int spincount, ethr_sint64_t timeout);
65 #if !defined(ETHR_TRY_INLINE_FUNCS) || defined(ETHR_EVENT_IMPL__)
66 void ethr_event_set(ethr_event *e);
67 void ethr_event_reset(ethr_event *e);
68 #endif
69