Skip to content

Commit 6b7ad72

Browse files
committed
Add __await__ method to Task class.
1 parent 0929353 commit 6b7ad72

File tree

1 file changed

+39
-33
lines changed

1 file changed

+39
-33
lines changed

extmod/moduasyncio.c

Lines changed: 39 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -29,11 +29,8 @@
2929
#include "py/pairheap.h"
3030
#include "py/mphal.h"
3131

32-
#if 0 // causes error for unix build
33-
#include "shared-bindings/supervisor/__init__.h"
34-
#else
32+
// Unix build does not have shared-bindings/supervisor/__init__.h
3533
extern mp_obj_t supervisor_ticks_ms(void);
36-
#endif
3734

3835
#if MICROPY_PY_UASYNCIO
3936

@@ -232,6 +229,40 @@ STATIC mp_obj_t task_cancel(mp_obj_t self_in) {
232229
}
233230
STATIC MP_DEFINE_CONST_FUN_OBJ_1(task_cancel_obj, task_cancel);
234231

232+
STATIC mp_obj_t task_getiter(mp_obj_t self_in, mp_obj_iter_buf_t *iter_buf) {
233+
(void)iter_buf;
234+
mp_obj_task_t *self = MP_OBJ_TO_PTR(self_in);
235+
if (TASK_IS_DONE(self)) {
236+
// Signal that the completed-task has been await'ed on.
237+
self->state = TASK_STATE_DONE_WAS_WAITED_ON;
238+
} else if (self->state == TASK_STATE_RUNNING_NOT_WAITED_ON) {
239+
// Allocate the waiting queue.
240+
self->state = task_queue_make_new(&task_queue_type, 0, 0, NULL);
241+
}
242+
return self_in;
243+
}
244+
245+
STATIC mp_obj_t task_iternext(mp_obj_t self_in) {
246+
mp_obj_task_t *self = MP_OBJ_TO_PTR(self_in);
247+
if (TASK_IS_DONE(self)) {
248+
// Task finished, raise return value to caller so it can continue.
249+
nlr_raise(self->data);
250+
} else {
251+
// Put calling task on waiting queue.
252+
mp_obj_t cur_task = mp_obj_dict_get(uasyncio_context, MP_OBJ_NEW_QSTR(MP_QSTR_cur_task));
253+
mp_obj_t args[2] = { self->state, cur_task };
254+
task_queue_push_sorted(2, args);
255+
// Set calling task's data to this task that it waits on, to double-link it.
256+
((mp_obj_task_t *)MP_OBJ_TO_PTR(cur_task))->data = self_in;
257+
}
258+
return mp_const_none;
259+
}
260+
261+
STATIC mp_obj_t task_await(mp_obj_t self_in) {
262+
return task_getiter(self_in, NULL);
263+
}
264+
STATIC MP_DEFINE_CONST_FUN_OBJ_1(task_await_obj, task_await);
265+
235266
STATIC void task_attr(mp_obj_t self_in, qstr attr, mp_obj_t *dest) {
236267
mp_obj_task_t *self = MP_OBJ_TO_PTR(self_in);
237268
if (dest[0] == MP_OBJ_NULL) {
@@ -250,7 +281,11 @@ STATIC void task_attr(mp_obj_t self_in, qstr attr, mp_obj_t *dest) {
250281
dest[1] = self_in;
251282
} else if (attr == MP_QSTR_ph_key) {
252283
dest[0] = self->ph_key;
284+
} else if (attr == MP_QSTR___await__) {
285+
dest[0] = MP_OBJ_FROM_PTR(&task_await_obj);
286+
dest[1] = self_in;
253287
}
288+
254289
} else if (dest[1] != MP_OBJ_NULL) {
255290
// Store
256291
if (attr == MP_QSTR_data) {
@@ -263,35 +298,6 @@ STATIC void task_attr(mp_obj_t self_in, qstr attr, mp_obj_t *dest) {
263298
}
264299
}
265300

266-
STATIC mp_obj_t task_getiter(mp_obj_t self_in, mp_obj_iter_buf_t *iter_buf) {
267-
(void)iter_buf;
268-
mp_obj_task_t *self = MP_OBJ_TO_PTR(self_in);
269-
if (TASK_IS_DONE(self)) {
270-
// Signal that the completed-task has been await'ed on.
271-
self->state = TASK_STATE_DONE_WAS_WAITED_ON;
272-
} else if (self->state == TASK_STATE_RUNNING_NOT_WAITED_ON) {
273-
// Allocate the waiting queue.
274-
self->state = task_queue_make_new(&task_queue_type, 0, 0, NULL);
275-
}
276-
return self_in;
277-
}
278-
279-
STATIC mp_obj_t task_iternext(mp_obj_t self_in) {
280-
mp_obj_task_t *self = MP_OBJ_TO_PTR(self_in);
281-
if (TASK_IS_DONE(self)) {
282-
// Task finished, raise return value to caller so it can continue.
283-
nlr_raise(self->data);
284-
} else {
285-
// Put calling task on waiting queue.
286-
mp_obj_t cur_task = mp_obj_dict_get(uasyncio_context, MP_OBJ_NEW_QSTR(MP_QSTR_cur_task));
287-
mp_obj_t args[2] = { self->state, cur_task };
288-
task_queue_push_sorted(2, args);
289-
// Set calling task's data to this task that it waits on, to double-link it.
290-
((mp_obj_task_t *)MP_OBJ_TO_PTR(cur_task))->data = self_in;
291-
}
292-
return mp_const_none;
293-
}
294-
295301
STATIC const mp_obj_type_t task_type = {
296302
{ &mp_type_type },
297303
.flags = MP_TYPE_FLAG_EXTENDED,

0 commit comments

Comments
 (0)