summaryrefslogtreecommitdiff
path: root/src/lib/libc/include/cancel.h
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/libc/include/cancel.h')
-rw-r--r--src/lib/libc/include/cancel.h75
1 files changed, 75 insertions, 0 deletions
diff --git a/src/lib/libc/include/cancel.h b/src/lib/libc/include/cancel.h
new file mode 100644
index 0000000000..4f4add471b
--- /dev/null
+++ b/src/lib/libc/include/cancel.h
@@ -0,0 +1,75 @@
1/* $OpenBSD: cancel.h,v 1.1 2016/05/07 19:05:22 guenther Exp $ */
2/*
3 * Copyright (c) 2015 Philip Guenther <guenther@openbsd.org>
4 *
5 * Permission to use, copy, modify, and distribute this software for any
6 * purpose with or without fee is hereby granted, provided that the above
7 * copyright notice and this permission notice appear in all copies.
8 *
9 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16 */
17
18#ifndef _CANCEL_H_
19#define _CANCEL_H_
20
21#include <tib.h>
22#include "thread_private.h"
23
24__BEGIN_HIDDEN_DECLS
25/* process a cancel request at a cancel point */
26__dead void _thread_canceled(void);
27__END_HIDDEN_DECLS
28
29#ifdef LIBC
30/*
31 * Redirect macros that would use the syscall to instead use our callback
32 */
33#define __get_tcb() _thread_cb.tc_tcb()
34#endif
35
36#define PREP_CANCEL_POINT(tib) \
37 int _cantcancel = (tib)->tib_cantcancel
38
39#define ENTER_CANCEL_POINT_INNER(tib, can_cancel, delay) \
40 if (_cantcancel == 0) { \
41 (tib)->tib_cancel_point = (delay) ? \
42 CANCEL_POINT_DELAYED : CANCEL_POINT; \
43 if (can_cancel) { \
44 __asm volatile("":::"memory"); \
45 if (__predict_false((tib)->tib_canceled)) \
46 _thread_canceled(); \
47 } \
48 }
49
50#define LEAVE_CANCEL_POINT_INNER(tib, can_cancel) \
51 if (_cantcancel == 0) { \
52 (tib)->tib_cancel_point = 0; \
53 if (can_cancel) { \
54 __asm volatile("":::"memory"); \
55 if (__predict_false((tib)->tib_canceled)) \
56 _thread_canceled(); \
57 } \
58 }
59
60/*
61 * Enter or leave a cancelation point, optionally processing pending
62 * cancelation requests. Note that ENTER_CANCEL_POINT opens a block
63 * and LEAVE_CANCEL_POINT must close that same block.
64 */
65#define ENTER_CANCEL_POINT(can_cancel) \
66 { \
67 struct tib *_tib = TIB_GET(); \
68 PREP_CANCEL_POINT(_tib); \
69 ENTER_CANCEL_POINT_INNER(_tib, can_cancel, 0)
70
71#define LEAVE_CANCEL_POINT(can_cancel) \
72 LEAVE_CANCEL_POINT_INNER(_tib, can_cancel); \
73 }
74
75#endif /* _CANCEL_H_ */