-
Notifications
You must be signed in to change notification settings - Fork 20
/
Copy pathpico_osal_pthread.c
119 lines (102 loc) · 2.55 KB
/
pico_osal_pthread.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
/* Pthread osal implementation, for testing purposes */
#include <pthread.h>
#include "pico_defines.h"
#include "pico_stack.h"
#include "pico_osal.h"
#include <semaphore.h>
#include <time.h>
#define BILLION 1000000000
void * pico_mutex_init(void) {
pthread_mutex_t *mutex = pico_zalloc(sizeof(pthread_mutex_t));
if (!mutex)
return NULL;
if (pthread_mutex_init(mutex, NULL) == 0 )
return mutex;
pico_free(mutex);
return NULL;
}
void pico_mutex_deinit(void * mutex)
{
pthread_mutex_destroy((pthread_mutex_t *)mutex);
pico_free(mutex);
}
void pico_mutex_lock(void * mutex)
{
pthread_mutex_lock((pthread_mutex_t *)mutex);
}
int pico_mutex_lock_timeout(void *mutex, int timeout)
{
if (timeout < 0) {
return pthread_mutex_lock((pthread_mutex_t *)mutex);
} else {
struct timespec ts = { timeout / 1000, (timeout % 1000) * 1000000 };
return pthread_mutex_timedlock((pthread_mutex_t *)mutex, &ts);
}
}
void pico_mutex_unlock(void * mutex)
{
pthread_mutex_unlock((pthread_mutex_t *)mutex);
}
void * pico_signal_init(void)
{
sem_t *sem = pico_zalloc(sizeof(pthread_mutex_t));
if (!sem)
return NULL;
if (sem_init(sem, 0, 0) == 0)
return sem;
pico_free(sem);
return NULL;
}
void pico_signal_deinit(void * signal)
{
sem_destroy((sem_t *) signal);
}
void pico_signal_wait(void * signal)
{
sem_wait((sem_t *) signal);
}
int pico_signal_wait_timeout(void * signal, int timeout)
{
if (timeout < 0) {
return sem_wait((sem_t *) signal);
} else {
struct timespec ts;
clock_gettime(CLOCK_REALTIME, &ts);
ts.tv_sec += (timeout / 1000);
ts.tv_nsec += ((timeout % 1000) * 1000000);
if (ts.tv_nsec >= BILLION) {
ts.tv_nsec -= BILLION;
ts.tv_sec++;
}
return sem_timedwait((sem_t *) signal, &ts);
}
}
void pico_signal_send(void * signal)
{
sem_post((sem_t *) signal);
}
pico_thread_t pico_thread_create(pico_thread_fn thread, void *arg, int stack_size, int prio)
{
pico_thread_t t = PICO_ZALLOC(sizeof(pthread_t));
if (!t)
return NULL;
(void)stack_size;
(void)prio;
pthread_create((pthread_t *)t, NULL, thread, arg);
pthread_detach(*((pthread_t *)t));
}
void pico_thread_destroy(pico_thread_t t)
{
pthread_cancel(*((pthread_t *)t));
PICO_FREE(t);
}
void pico_msleep(int ms)
{
struct timespec ts = { ms / 1000, (ms % 1000) * 1000000 };
nanosleep(&ts, NULL);
}
void pico_threads_schedule(void)
{
while (1 < 2)
pico_msleep(1000);
}