// SPDX-License-Identifier: LGPL-3.0-or-later
// Copyright © 2020 Florian Schmaus
#include <stdlib.h>

#include "emper-common.h"
#include "emper.h"

#define FIBER_COUNT 10

static cps* sem;
static int counter;

static void fiber_fun(void) {
	__sync_fetch_and_add(&counter, 1);
	signal_and_exit_cps(sem);
}

static void check_fun(void) {
	wait_cps(sem);

	if (counter != FIBER_COUNT) {
		exit(EXIT_FAILURE);
	}

	exit(EXIT_SUCCESS);
}

static void alpha_fun(void) {
	sem = new_counting_sem_with(FIBER_COUNT);

	fiber* fibers[FIBER_COUNT];

	for (unsigned int i = 0; i < FIBER_COUNT; i++) {
		fibers[i] = fiber_from0(fiber_fun);
	}

	for (unsigned int i = 0; i < FIBER_COUNT; i++) {
		schedule(fibers[i]);
	}

	fiber* check_fiber = fiber_from0(check_fun);
	schedule(check_fiber);
}

int main(UNUSED_ARG int argc, UNUSED_ARG char* argv[]) {
	init_runtime();

	fiber* alpha_fiber = fiber_from0(alpha_fun);
	schedule_from_anywhere(alpha_fiber);

	wait_until_runtime_finished();

	return EXIT_FAILURE;
}