1 /*******************************************************************************
2 * Copyright (C) 2018 Cadence Design Systems, Inc.
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining
5 * a copy of this software and associated documentation files (the
6 * "Software"), to use this Software with Cadence processor cores only and
7 * not with any other processors and platforms, subject to
8 * the following conditions:
9 *
10 * The above copyright notice and this permission notice shall be included
11 * in all copies or substantial portions of the Software.
12 *
13 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
14 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
15 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
16 * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
17 * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
18 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
19 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
20
21 ******************************************************************************/
22
23 #ifndef __XF_H
24 #error "xf-osal.h mustn't be included directly"
25 #endif
26
27 /*******************************************************************************
28 * Includes
29 ******************************************************************************/
30 #include "xos.h"
31
32 /*******************************************************************************
33 * Tracing primitive
34 ******************************************************************************/
35
36 #define __xf_puts(str) \
37 puts((str))
38
39 /*******************************************************************************
40 * Lock operation
41 ******************************************************************************/
42
43 /* ...lock definition */
44 typedef XosMutex xf_lock_t;
45
46 /* ...lock initialization */
__xf_lock_init(xf_lock_t * lock)47 static inline void __xf_lock_init(xf_lock_t *lock)
48 {
49 xos_mutex_create(lock, XOS_MUTEX_WAIT_PRIORITY, 0);
50 }
51
52 /* ...lock acquisition */
__xf_lock(xf_lock_t * lock)53 static inline void __xf_lock(xf_lock_t *lock)
54 {
55 xos_mutex_lock(lock);
56 }
57
58 /* ...lock release */
__xf_unlock(xf_lock_t * lock)59 static inline void __xf_unlock(xf_lock_t *lock)
60 {
61 xos_mutex_unlock(lock);
62 }
63
64 /*******************************************************************************
65 * Waiting object
66 ******************************************************************************/
67
68 #if 0
69 /* ...waiting object handle */
70 typedef struct __xf_wait
71 {
72 /* ...conditional variable */
73 pthread_cond_t wait;
74
75 /* ...waiting mutex */
76 pthread_mutex_t mutex;
77
78 } xf_wait_t;
79
80 /* ...initialize waiting object */
81 static inline void __xf_wait_init(xf_wait_t *w)
82 {
83 pthread_cond_init(&w->wait, NULL);
84 pthread_mutex_init(&w->mutex, NULL);
85 }
86
87 /* ...prepare to waiting */
88 static inline void __xf_wait_prepare(xf_wait_t *w)
89 {
90 pthread_mutex_lock(&w->mutex);
91 }
92
93 #define __xf_wait_prepare(w) \
94 ({ \
95 TRACE(1, _x("prepare-wait")); \
96 (__xf_wait_prepare)(w); \
97 })
98
99 /* ...wait until event is signalled */
100 static inline int __xf_wait(xf_wait_t *w, u32 timeout)
101 {
102 struct timespec ts;
103 struct timeval tv;
104 int r;
105
106 /* ...wait with or without timeout (communication mutex is taken) */
107 if (!timeout)
108 {
109 r = -pthread_cond_wait(&w->wait, &w->mutex);
110 }
111 else
112 {
113 /* ...get current time */
114 gettimeofday(&tv, NULL);
115
116 /* ...set absolute timeout */
117 ts.tv_sec = tv.tv_sec + timeout / 1000;
118 ts.tv_nsec = tv.tv_usec * 1000 + (timeout % 1000) * 1000000;
119 (ts.tv_nsec >= 1000000000 ? ts.tv_sec++, ts.tv_nsec -= 1000000000 : 0);
120
121 /* ...wait conditionally with absolute timeout*/
122 r = -pthread_cond_timedwait(&w->wait, &w->mutex, &ts);
123 }
124
125 /* ...leave with communication mutex taken */
126 return r;
127 }
128
129 #define __xf_wait(w, timeout) \
130 ({ \
131 int __r; \
132 TRACE(1, _x("wait")); \
133 __r = (__xf_wait)(w, timeout); \
134 TRACE(1, _x("resume")); \
135 __r; \
136 })
137
138 /* ...wake up waiting handle */
139 static inline void __xf_wakeup(xf_wait_t *w)
140 {
141 /* ...take communication mutex before signaling */
142 pthread_mutex_lock(&w->mutex);
143
144 /* ...signalling will resume waiting thread */
145 pthread_cond_signal(&w->wait);
146
147 /* ...assure that waiting task will not resume until we say this - is that really needed? - tbd */
148 pthread_mutex_unlock(&w->mutex);
149 }
150
151 #define __xf_wakeup(w) \
152 ({ \
153 TRACE(1, _x("wakeup")); \
154 (__xf_wakeup)(w); \
155 })
156
157 /* ...complete waiting operation */
158 static inline void __xf_wait_complete(xf_wait_t *w)
159 {
160 pthread_mutex_unlock(&w->mutex);
161 }
162
163 #define __xf_wait_complete(w) \
164 ({ \
165 TRACE(1, _x("wait-complete")); \
166 (__xf_wait_complete)(w); \
167 })
168 #endif
169
170 /*******************************************************************************
171 * Thread support
172 ******************************************************************************/
173
174 /* ...thread handle definition */
175 typedef XosThread xf_thread_t;
176 typedef XosThreadFunc xf_entry_t;
177
178 /* ...thread creation */
__xf_thread_create(xf_thread_t * thread,xf_entry_t * f,void * arg,const char * name,void * stack,unsigned int stack_size,int priority)179 static inline int __xf_thread_create(xf_thread_t *thread, xf_entry_t *f,
180 void *arg, const char *name, void * stack,
181 unsigned int stack_size, int priority)
182 {
183 int r;
184
185 /* ...create proxy asynchronous thread managing SHMEM */
186 r = xos_thread_create(thread, 0, f, arg, name, stack, stack_size, priority, 0, 0);
187
188 return r;
189 }
190
191 /* ...terminate thread operation */
__xf_thread_destroy(xf_thread_t * thread)192 static inline int __xf_thread_destroy(xf_thread_t *thread)
193 {
194 int r;
195
196 /* ...wait until thread terminates */
197 /* v-tbd - avoid infinite wait for join */
198 //xos_thread_join(thread, &r);
199
200 /* ...delete thread, free up TCB, stack */
201 r = xos_thread_delete(thread);
202
203 /* ...return final status */
204 return r;
205 }
206
207