1 /*
2 * Copyright (C) 2015-2017 Alibaba Group Holding Limited
3 */
4
5 #ifndef _BLE_OS_PORT_H
6 #define _BLE_OS_PORT_H
7
8 #ifndef ASSERT
9 #define ASSERT __ASSERT
10 #endif
11 #include <k_api.h>
12 #include <misc/dlist.h>
13 #include <misc/slist.h>
14
15 #define _STRINGIFY(x) #x
16
17 #define ___in_section(a, b, c) \
18 __attribute__((section("." _STRINGIFY(a) \
19 "." _STRINGIFY(b) \
20 "." _STRINGIFY(c))))
21
22 //#define __in_section(a, b, c) ___in_section(a, b, c)
23 #define __in_section(a, b, c)
24
25 #define __in_section_unique(seg) ___in_section(seg, _FILE_PATH_HASH, \
26 __COUNTER__)
27
28 #define __in_btstack_section() __in_section(btstack, static, func)
29
30 #ifndef ARG_UNUSED
31 #define ARG_UNUSED(x) (void)(x)
32 #endif
33
34 #ifndef __packed
35 #define __packed __attribute__((__packed__))
36 #endif
37
38 #ifndef __printf_like
39 #define __printf_like(f, a) __attribute__((format (printf, f, a)))
40 #endif
41 #define STACK_ALIGN 4
42 #define __stack __aligned(STACK_ALIGN)
43
44 #define K_FOREVER -1
45 #define K_NO_WAIT 0
46
47 /* Unaligned access */
48 #define UNALIGNED_GET(p) \
49 __extension__ ({ \
50 struct __attribute__((__packed__)) { \
51 __typeof__(*(p)) __v; \
52 } *__p = (__typeof__(__p)) (p); \
53 __p->__v; \
54 })
55
56 #ifndef UNUSED
57 #define UNUSED(x) (void)x
58 #endif
59
60 enum _poll_types_bits {
61 _POLL_TYPE_IGNORE,
62 _POLL_TYPE_SIGNAL,
63 _POLL_TYPE_SEM_AVAILABLE,
64 _POLL_TYPE_DATA_AVAILABLE,
65 _POLL_NUM_TYPES
66 };
67
68 #define _POLL_TYPE_BIT(type) (1 << ((type)-1))
69
70 enum _poll_states_bits {
71 _POLL_STATE_NOT_READY,
72 _POLL_STATE_SIGNALED,
73 _POLL_STATE_SEM_AVAILABLE,
74 _POLL_STATE_DATA_AVAILABLE,
75 _POLL_NUM_STATES
76 };
77
78 #define _POLL_STATE_BIT(state) (1 << ((state)-1))
79
80 #define _POLL_EVENT_NUM_UNUSED_BITS \
81 (32 - (0 + 8 /* tag */ \
82 + _POLL_NUM_TYPES + _POLL_NUM_STATES + 1 /* modes */ \
83 ))
84
85 #define K_POLL_SIGNAL_INITIALIZER(obj) \
86 { \
87 .poll_events = SYS_DLIST_STATIC_INIT(&obj.poll_events), .signaled = 0, \
88 .result = 0, \
89 }
90
91 struct k_poll_event {
92 sys_dnode_t _node;
93 struct _poller *poller;
94 uint32_t tag : 8;
95 uint32_t type :
96 _POLL_NUM_TYPES;
97 uint32_t state :
98 _POLL_NUM_STATES;
99 uint32_t mode : 1;
100 uint32_t unused :
101 _POLL_EVENT_NUM_UNUSED_BITS;
102 union {
103 void *obj;
104 struct k_poll_signal *signal;
105 struct k_sem *sem;
106 struct kfifo *fifo;
107 struct k_queue *queue;
108 };
109 };
110
111 struct k_poll_signal {
112 sys_dlist_t poll_events;
113 unsigned int signaled;
114 int result;
115 };
116
117 #define K_POLL_STATE_NOT_READY 0
118 #define K_POLL_STATE_EADDRINUSE 1
119 #define K_POLL_STATE_SIGNALED 2
120 #define K_POLL_STATE_SEM_AVAILABLE 3
121 #define K_POLL_STATE_DATA_AVAILABLE 4
122 #define K_POLL_STATE_FIFO_DATA_AVAILABLE K_POLL_STATE_DATA_AVAILABLE
123 #define K_POLL_STATE_DATA_RECV 5
124 #define K_POLL_STATE_TX_SYNC_DONE 6
125
126
127 #define K_POLL_TYPE_IGNORE 0
128 #define K_POLL_TYPE_SIGNAL 1
129 #define K_POLL_TYPE_SEM_AVAILABLE 2
130 #define K_POLL_TYPE_DATA_AVAILABLE 3
131 #define K_POLL_TYPE_FIFO_DATA_AVAILABLE K_POLL_TYPE_DATA_AVAILABLE
132 #define K_POLL_TYPE_DATA_RECV 5
133 #define K_POLL_TYPE_EARLIER_WORK 6
134
135 #define K_POLL_EVENT_STATIC_INITIALIZER(event_type, event_mode, event_obj, \
136 event_tag) \
137 { \
138 .type = event_type, .tag = event_tag, .state = K_POLL_STATE_NOT_READY, \
139 .mode = event_mode, .unused = 0, { .obj = event_obj }, \
140 }
141
142 extern void k_poll_signal_raise(struct k_poll_signal *signal, int result);
143
144 #if 0 //YULONG
145 extern int k_poll(struct k_poll_event *events, int num_events,
146 int32_t timeout);
147 extern void k_poll_event_init(struct k_poll_event *event, uint32_t type,
148 int mode, void *obj);
149 extern void _handle_obj_poll_events(sys_dlist_t *events, uint32_t state);
150 #endif
151
152 /* public - polling modes */
153 enum k_poll_modes {
154 /* polling thread does not take ownership of objects when available */
155 K_POLL_MODE_NOTIFY_ONLY = 0,
156
157 K_POLL_NUM_MODES
158 };
159
160 #define BT_STACK(name, size) \
161 k_thread_stack_t name[(size) / sizeof(k_thread_stack_t)];
162
163 #define BT_STACK_NOINIT(name, size) \
164 k_thread_stack_t name[(size) / sizeof(k_thread_stack_t)];
165
k_call_stacks_analyze()166 static inline void k_call_stacks_analyze()
167 {
168 return;
169 }
170
K_THREAD_STACK_BUFFER(uint32_t * sym)171 static inline char *K_THREAD_STACK_BUFFER(uint32_t *sym)
172 {
173 return NULL;
174 }
175
176 #define k_oops() while(1)
177
178 void *k_current_get(void);
179 uint32_t k_get_tick(void);
180 uint32_t k_tick2ms(uint32_t tick);
181 void k_sleep(int32_t ms);
182
183 uint32_t k_uptime_get_32();
184
185
186 #define _DO_CONCAT(x, y) x ## y
187 #define _CONCAT(x, y) _DO_CONCAT(x, y)
188
189 #ifndef BUILD_ASSERT
190 /* compile-time assertion that makes the build fail */
191 #define BUILD_ASSERT(EXPR) \
192 enum _CONCAT(__build_assert_enum, __COUNTER__) { \
193 _CONCAT(__build_assert, __COUNTER__) = 1 / !!(EXPR) \
194 }
195 #endif
196 #ifndef BUILD_ASSERT_MSG
197 /* build assertion with message -- common implementation swallows message. */
198 #define BUILD_ASSERT_MSG(EXPR, MSG) BUILD_ASSERT(EXPR)
199 #endif
200
201 #ifndef MSEC_PER_SEC
202 #define MSEC_PER_SEC 1000
203 #endif
204 /**
205 * @brief Generate timeout delay from milliseconds.
206 *
207 * This macro generates a timeout delay that that instructs a kernel API
208 * to wait up to @a ms milliseconds to perform the requested operation.
209 *
210 * @param ms Duration in milliseconds.
211 *
212 * @return Timeout delay value.
213 */
214 #define K_MSEC(ms) (ms)
215
216 /**
217 * @brief Generate timeout delay from seconds.
218 *
219 * This macro generates a timeout delay that that instructs a kernel API
220 * to wait up to @a s seconds to perform the requested operation.
221 *
222 * @param s Duration in seconds.
223 *
224 * @return Timeout delay value.
225 */
226 #define K_SECONDS(s) K_MSEC((s) * MSEC_PER_SEC)
227
228 /**
229 * @brief Generate timeout delay from minutes.
230 *
231 * This macro generates a timeout delay that that instructs a kernel API
232 * to wait up to @a m minutes to perform the requested operation.
233 *
234 * @param m Duration in minutes.
235 *
236 * @return Timeout delay value.
237 */
238 #define K_MINUTES(m) K_SECONDS((m) * 60)
239
240 /**
241 * @brief Generate timeout delay from hours.
242 *
243 * This macro generates a timeout delay that that instructs a kernel API
244 * to wait up to @a h hours to perform the requested operation.
245 *
246 * @param h Duration in hours.
247 *
248 * @return Timeout delay value.
249 */
250 #define K_HOURS(h) K_MINUTES((h) * 60)
251
252 #define popcount(x) __builtin_popcount(x)
253
find_msb_set(uint32_t op)254 static inline unsigned int find_msb_set(uint32_t op)
255 {
256 if (op == 0) {
257 return 0;
258 }
259
260 return 32 - __builtin_clz(op);
261 }
262
find_lsb_set(uint32_t op)263 static inline unsigned int find_lsb_set(uint32_t op)
264 {
265 return __builtin_ffs(op);
266 }
267
268 #define k_thread_foreach(...)
269
270 #define k_free free
271
272 #define snprintk snprintf
273
274 #ifndef __aligned
275 #define __aligned(x) __attribute__((__aligned__(x)))
276 #endif
277
278 #ifndef BIT
279 #define BIT(nr) (1UL << (nr))
280 #endif
281
282 #define __noinit
283
284 #ifndef ARRAY_SIZE
285 #define ARRAY_SIZE(array) \
286 ((unsigned long) (sizeof(array) / sizeof((array)[0])))
287 #endif
288
289 typedef kbuf_queue_t _queue_t;
290 typedef ksem_t _sem_t;
291 typedef ktask_t _task_t;
292 typedef cpu_stack_t _stack_element_t;
293 typedef kmutex_t _mutex_t;
294
295 /* Log define*/
296 enum {
297 LOG_LEVEL_NONE = 0,
298 LOG_LEVEL_FATAL,
299 LOG_LEVEL_ERROR,
300 LOG_LEVEL_WARN,
301 LOG_LEVEL_INFO,
302 LOG_LEVEL_DEBUG,
303 LOG_LEVEL_MAX_BIT
304 };
305
306 #define BT_TAG "AOSBT"
307
308 #define BT_LOG_DBG 1
309 #if BT_LOG_DBG
310 #define SYS_LOG_DBG(fmt,...) LOGD(BT_TAG, "%s:"fmt, __FUNCTION__, ##__VA_ARGS__)
311 #define SYS_LOG_INF(fmt,...) LOGI(BT_TAG, "%s:"fmt, __FUNCTION__, ##__VA_ARGS__)
312 #define SYS_LOG_WRN(fmt,...) LOGW(BT_TAG, "%s:"fmt, __FUNCTION__, ##__VA_ARGS__)
313 #define SYS_LOG_ERR(fmt,...) LOGE(BT_TAG, "%s:"fmt, __FUNCTION__, ##__VA_ARGS__)
314 #else
315 #define SYS_LOG_DBG(fmt,...) LOGD(BT_TAG, fmt, ##__VA_ARGS__)
316 #define SYS_LOG_INF(fmt,...) LOGI(BT_TAG, fmt, ##__VA_ARGS__)
317 #define SYS_LOG_WRN(fmt,...) LOGW(BT_TAG, fmt, ##__VA_ARGS__)
318 #define SYS_LOG_ERR(fmt,...) LOGE(BT_TAG, fmt, ##__VA_ARGS__)
319 #endif
320
321 struct k_queue {
322 _sem_t sem;
323 sys_slist_t queue_list;
324 sys_dlist_t poll_events;
325 };
326
327 extern void k_queue_init(struct k_queue *queue);
328 extern void k_queue_uninit(struct k_queue *queue);
329 extern void k_queue_cancel_wait(struct k_queue *queue);
330 extern void k_queue_append(struct k_queue *queue, void *data);
331 extern void k_queue_prepend(struct k_queue *queue, void *data);
332 extern void k_queue_insert(struct k_queue *queue, void *prev, void *data);
333 extern void k_queue_append_list(struct k_queue *queue, void *head, void *tail);
334 extern void *k_queue_get(struct k_queue *queue, int32_t timeout);
335 extern int k_queue_is_empty(struct k_queue *queue);
336 extern int k_queue_count(struct k_queue *queue);
337
k_queue_remove(struct k_queue * queue,void * data)338 static inline bool k_queue_remove(struct k_queue *queue, void *data)
339 {
340 return sys_slist_find_and_remove(&queue->queue_list, (sys_snode_t *)data);
341 }
342
k_queue_first_entry(struct k_queue * queue)343 static inline void *k_queue_first_entry(struct k_queue *queue)
344 {
345 return sys_slist_peek_head(&queue->queue_list);
346 }
347
348 /* lifo define*/
349 struct k_lifo {
350 struct k_queue _queue;
351 };
352
353 #define k_lifo_init(lifo) k_queue_init((struct k_queue *)lifo)
354
355 #define k_lifo_put(lifo, data) k_queue_prepend((struct k_queue *)lifo, data)
356
357 #define k_lifo_get(lifo, timeout) k_queue_get((struct k_queue *)lifo, timeout)
358
359 #define k_lifo_num_get(lifo) k_queue_count((struct k_queue *)lifo)
360
361 struct kfifo {
362 struct k_queue _queue;
363 };
364
365 #define k_fifo_init(fifo) k_queue_init((struct k_queue *)fifo)
366
367 #define k_fifo_cancel_wait(fifo) k_queue_cancel_wait((struct k_queue *)fifo)
368
369 #define k_fifo_put(fifo, data) k_queue_append((struct k_queue *)fifo, data)
370
371 #define k_fifo_put_list(fifo, head, tail) \
372 k_queue_append_list((struct k_queue *)fifo, head, tail)
373
374 #define k_fifo_get(fifo, timeout) k_queue_get((struct k_queue *)fifo, timeout)
375 #define k_fifo_num_get(fifo) k_queue_count((struct k_queue *)fifo)
376
377 /* sem define*/
378 struct k_sem {
379 _sem_t sem;
380 sys_dlist_t poll_events;
381 };
382
383 /**
384 * @brief Initialize a semaphore.
385 *
386 * This routine initializes a semaphore object, prior to its first use.
387 *
388 * @param sem Address of the semaphore.
389 * @param initial_count Initial semaphore count.
390 * @param limit Maximum permitted semaphore count.
391 *
392 * @return 0 Creat a semaphore succcess
393 */
394 int k_sem_init(struct k_sem *sem, unsigned int initial_count,
395 unsigned int limit);
396
397 /**
398 * @brief Take a semaphore.
399 *
400 * This routine takes @a sem.
401 *
402 * @note Can be called by ISRs, but @a timeout must be set to K_NO_WAIT.
403 *
404 * @param sem Address of the semaphore.
405 * @param timeout Waiting period to take the semaphore (in milliseconds),
406 * or one of the special values K_NO_WAIT and K_FOREVER.
407 *
408 * @note When porting code from the nanokernel legacy API to the new API, be
409 * careful with the return value of this function. The return value is the
410 * reverse of the one of nano_sem_take family of APIs: 0 means success, and
411 * non-zero means failure, while the nano_sem_take family returns 1 for success
412 * and 0 for failure.
413 *
414 * @retval 0 Semaphore taken.
415 * @retval -EBUSY Returned without waiting.
416 * @retval -EAGAIN Waiting period timed out.
417 */
418 int k_sem_take(struct k_sem *sem, uint32_t timeout);
419
420 /**
421 * @brief Give a semaphore.
422 *
423 * This routine gives @a sem, unless the semaphore is already at its maximum
424 * permitted count.
425 *
426 * @note Can be called by ISRs.
427 *
428 * @param sem Address of the semaphore.
429 *
430 * @return 0 Give semaphore success
431 */
432 int k_sem_give(struct k_sem *sem);
433
434 /**
435 * @brief Delete a semaphore.
436 *
437 * This routine delete @a sem,
438 *
439 * @note Can be called by ISRs.
440 *
441 * @param sem Address of the semaphore.
442 *
443 * @return 0 delete semaphore success
444 */
445 int k_sem_delete(struct k_sem *sem);
446
447 /**
448 * @brief Get a semaphore's count.
449 *
450 * This routine returns the current count of @a sem.
451 *
452 * @param sem Address of the semaphore.
453 *
454 * @return Current semaphore count.
455 */
456 unsigned int k_sem_count_get(struct k_sem *sem);
457
458 /* mutex define*/
459 struct k_mutex {
460 _mutex_t mutex;
461 sys_dlist_t poll_events;
462 };
463
464 typedef void (*k_timer_handler_t)(void *timer, void *args);
465 typedef struct k_timer {
466 ktimer_t timer;
467 k_timer_handler_t handler;
468 void *args;
469 uint32_t timeout;
470 uint32_t start_ms;
471 } k_timer_t;
472
473 /**
474 * @brief Initialize a timer.
475 *
476 * This routine initializes a timer, prior to its first use.
477 *
478 * @param timer Address of timer.
479 * @param handle Function to invoke each time the timer expires.
480 * @param args Arguments sent to handle.
481 *
482 * @return N/A
483 */
484 void k_timer_init(k_timer_t *timer, k_timer_handler_t handle, void *args);
485
486 /**
487 * @brief Start a timer.
488 *
489 * @param timer Address of timer.
490 * @param timeout time before timeout happen(in milliseconds).
491 *
492 * @return N/A
493 */
494 void k_timer_start(k_timer_t *timer, uint32_t timeout);
495
496 /**
497 * @brief Stop a timer.
498 *
499 * @param timer Address of timer.
500 *
501 * @return N/A
502 */
503 void k_timer_stop(k_timer_t *timer);
504
505 /**
506 * @brief Get time now.
507 *
508 * @return time(in milliseconds)
509 */
510 int64_t k_uptime_get(void);
511
512 /**
513 * @brief Get time now.
514 *
515 * @return time(in milliseconds)
516 */
517 uint32_t k_uptime_get_32(void);
518
519 /**
520 * @brief Judge if a timer started.
521 *
522 * @param timer Address of timer.
523 *
524 * @return N/A
525 */
526 bool k_timer_is_started(k_timer_t *timer);
527
528 void k_sleep(int32_t duration);
529
530 void k_mutex_init(struct k_mutex *mutex);
531 int k_mutex_lock(struct k_mutex *mutex, bt_s32_t timeout);
532 void k_mutex_unlock(struct k_mutex *mutex);
533
534 const char *log_strdup(const char *str);
535
536 #define __DEPRECATED_MACRO
537
538 #endif /* KPORT_H */
539