Пример #1
0
/*
 * This function invokes the start function of the coroutine when the
 * coroutine is first called. If it was called from coro_new, then it sets
 * up the stack and initializes the saved context.
 */
void _coro_enter(coro c)
{
	if (setjmp(c->ctxt))
	{	/* start the coroutine; stack is empty at this point. */
		cvalue _return;
		_return.p = _cur;
		_cur->start(_value);
		/* return the exited coroutine to the exit handler */
		coro_call(&_on_exit, _return);
	}
	/* this code executes when _coro_enter is called from coro_new */
INIT_CTXT:
	{
		/* local and new stack pointers at identical relative positions on the stack */
		intptr_t local_sp = (intptr_t)&local_sp;
		/* I don't know what the addition "- sizeof(void *)" is for when
		   the stack grows downards */
		intptr_t new_sp = c->stack_base +
			(_stack_grows_up
				? _frame_offset
				: c->stack_size - _frame_offset - sizeof(void *));

		/* copy local stack frame to the new stack */
		_coro_cpframe(local_sp, new_sp);

		/* reset any locals in the saved state to point to the new stack */
		_coro_rebase(c, local_sp, new_sp);
	}
}
Пример #2
0
void Luagame::Luagame::run() {
	std::vector<coro_call> coroutines;
	for (auto& box : boxes) {
		coroutines.push_back(coro_call(
					[&](coro_yield& yield) {
						cur_yield = &yield;
						box.run();
					}));
	}

	bool one_run;
	do {
		one_run = false;
		for (auto& coro : coroutines) {
			if (coro) {
				one_run = true;
				coro();
			}
		}
	} while (one_run);
}
Пример #3
0
void coro_run(coro *next) {
	coro *caller = coro_new(NULL, NULL);
	coro_call(caller, next);
	coro_release(caller);
}