Statistics
| Branch: | Revision:

root / qemu-coroutine.h @ 4d5b97da

History | View | Annotate | Download (5.6 kB)

1
/*
2
 * QEMU coroutine implementation
3
 *
4
 * Copyright IBM, Corp. 2011
5
 *
6
 * Authors:
7
 *  Stefan Hajnoczi    <stefanha@linux.vnet.ibm.com>
8
 *  Kevin Wolf         <kwolf@redhat.com>
9
 *
10
 * This work is licensed under the terms of the GNU LGPL, version 2 or later.
11
 * See the COPYING.LIB file in the top-level directory.
12
 *
13
 */
14

    
15
#ifndef QEMU_COROUTINE_H
16
#define QEMU_COROUTINE_H
17

    
18
#include <stdbool.h>
19
#include "qemu-queue.h"
20
#include "qemu-timer.h"
21

    
22
/**
23
 * Coroutines are a mechanism for stack switching and can be used for
24
 * cooperative userspace threading.  These functions provide a simple but
25
 * useful flavor of coroutines that is suitable for writing sequential code,
26
 * rather than callbacks, for operations that need to give up control while
27
 * waiting for events to complete.
28
 *
29
 * These functions are re-entrant and may be used outside the global mutex.
30
 */
31

    
32
/**
33
 * Mark a function that executes in coroutine context
34
 *
35
 * Functions that execute in coroutine context cannot be called directly from
36
 * normal functions.  In the future it would be nice to enable compiler or
37
 * static checker support for catching such errors.  This annotation might make
38
 * it possible and in the meantime it serves as documentation.
39
 *
40
 * For example:
41
 *
42
 *   static void coroutine_fn foo(void) {
43
 *       ....
44
 *   }
45
 */
46
#define coroutine_fn
47

    
48
typedef struct Coroutine Coroutine;
49

    
50
/**
51
 * Coroutine entry point
52
 *
53
 * When the coroutine is entered for the first time, opaque is passed in as an
54
 * argument.
55
 *
56
 * When this function returns, the coroutine is destroyed automatically and
57
 * execution continues in the caller who last entered the coroutine.
58
 */
59
typedef void coroutine_fn CoroutineEntry(void *opaque);
60

    
61
/**
62
 * Create a new coroutine
63
 *
64
 * Use qemu_coroutine_enter() to actually transfer control to the coroutine.
65
 */
66
Coroutine *qemu_coroutine_create(CoroutineEntry *entry);
67

    
68
/**
69
 * Transfer control to a coroutine
70
 *
71
 * The opaque argument is passed as the argument to the entry point when
72
 * entering the coroutine for the first time.  It is subsequently ignored.
73
 */
74
void qemu_coroutine_enter(Coroutine *coroutine, void *opaque);
75

    
76
/**
77
 * Transfer control back to a coroutine's caller
78
 *
79
 * This function does not return until the coroutine is re-entered using
80
 * qemu_coroutine_enter().
81
 */
82
void coroutine_fn qemu_coroutine_yield(void);
83

    
84
/**
85
 * Get the currently executing coroutine
86
 */
87
Coroutine *coroutine_fn qemu_coroutine_self(void);
88

    
89
/**
90
 * Return whether or not currently inside a coroutine
91
 *
92
 * This can be used to write functions that work both when in coroutine context
93
 * and when not in coroutine context.  Note that such functions cannot use the
94
 * coroutine_fn annotation since they work outside coroutine context.
95
 */
96
bool qemu_in_coroutine(void);
97

    
98

    
99

    
100
/**
101
 * CoQueues are a mechanism to queue coroutines in order to continue executing
102
 * them later. They provide the fundamental primitives on which coroutine locks
103
 * are built.
104
 */
105
typedef struct CoQueue {
106
    QTAILQ_HEAD(, Coroutine) entries;
107
} CoQueue;
108

    
109
/**
110
 * Initialise a CoQueue. This must be called before any other operation is used
111
 * on the CoQueue.
112
 */
113
void qemu_co_queue_init(CoQueue *queue);
114

    
115
/**
116
 * Adds the current coroutine to the CoQueue and transfers control to the
117
 * caller of the coroutine.
118
 */
119
void coroutine_fn qemu_co_queue_wait(CoQueue *queue);
120

    
121
/**
122
 * Adds the current coroutine to the head of the CoQueue and transfers control to the
123
 * caller of the coroutine.
124
 */
125
void coroutine_fn qemu_co_queue_wait_insert_head(CoQueue *queue);
126

    
127
/**
128
 * Restarts the next coroutine in the CoQueue and removes it from the queue.
129
 *
130
 * Returns true if a coroutine was restarted, false if the queue is empty.
131
 */
132
bool qemu_co_queue_next(CoQueue *queue);
133

    
134
/**
135
 * Restarts all coroutines in the CoQueue and leaves the queue empty.
136
 */
137
void qemu_co_queue_restart_all(CoQueue *queue);
138

    
139
/**
140
 * Checks if the CoQueue is empty.
141
 */
142
bool qemu_co_queue_empty(CoQueue *queue);
143

    
144

    
145
/**
146
 * Provides a mutex that can be used to synchronise coroutines
147
 */
148
typedef struct CoMutex {
149
    bool locked;
150
    CoQueue queue;
151
} CoMutex;
152

    
153
/**
154
 * Initialises a CoMutex. This must be called before any other operation is used
155
 * on the CoMutex.
156
 */
157
void qemu_co_mutex_init(CoMutex *mutex);
158

    
159
/**
160
 * Locks the mutex. If the lock cannot be taken immediately, control is
161
 * transferred to the caller of the current coroutine.
162
 */
163
void coroutine_fn qemu_co_mutex_lock(CoMutex *mutex);
164

    
165
/**
166
 * Unlocks the mutex and schedules the next coroutine that was waiting for this
167
 * lock to be run.
168
 */
169
void coroutine_fn qemu_co_mutex_unlock(CoMutex *mutex);
170

    
171
typedef struct CoRwlock {
172
    bool writer;
173
    int reader;
174
    CoQueue queue;
175
} CoRwlock;
176

    
177
/**
178
 * Initialises a CoRwlock. This must be called before any other operation
179
 * is used on the CoRwlock
180
 */
181
void qemu_co_rwlock_init(CoRwlock *lock);
182

    
183
/**
184
 * Read locks the CoRwlock. If the lock cannot be taken immediately because
185
 * of a parallel writer, control is transferred to the caller of the current
186
 * coroutine.
187
 */
188
void qemu_co_rwlock_rdlock(CoRwlock *lock);
189

    
190
/**
191
 * Write Locks the mutex. If the lock cannot be taken immediately because
192
 * of a parallel reader, control is transferred to the caller of the current
193
 * coroutine.
194
 */
195
void qemu_co_rwlock_wrlock(CoRwlock *lock);
196

    
197
/**
198
 * Unlocks the read/write lock and schedules the next coroutine that was
199
 * waiting for this lock to be run.
200
 */
201
void qemu_co_rwlock_unlock(CoRwlock *lock);
202

    
203
/**
204
 * Yield the coroutine for a given duration
205
 *
206
 * Note this function uses timers and hence only works when a main loop is in
207
 * use.  See main-loop.h and do not use from qemu-tool programs.
208
 */
209
void coroutine_fn co_sleep_ns(QEMUClock *clock, int64_t ns);
210

    
211
#endif /* QEMU_COROUTINE_H */