/*
 * Copyright (c) 2018 Intel Corporation
 *
 * SPDX-License-Identifier: Apache-2.0
 */

#include <kernel.h>
#include <cmsis_os.h>
#include <string.h>

K_MEM_SLAB_DEFINE(cmsis_semaphore_slab, sizeof(struct k_sem),
		CONFIG_CMSIS_SEMAPHORE_MAX_COUNT, 4);

/**
 * @brief Create and Initialize a semaphore object.
 */
osSemaphoreId osSemaphoreCreate(const osSemaphoreDef_t *semaphore_def,
				int32_t count)
{
	struct k_sem *semaphore;

	if (semaphore_def == NULL) {
		return NULL;
	}

	if (k_is_in_isr()) {
		return NULL;
	}

	if (k_mem_slab_alloc(&cmsis_semaphore_slab,
				(void **)&semaphore, K_MSEC(100)) == 0) {
		(void)memset(semaphore, 0, sizeof(struct k_sem));
	} else {
		return NULL;
	}

	k_sem_init(semaphore, count, count);

	return (osSemaphoreId)semaphore;
}

/**
 * @brief Wait until a semaphore becomes available.
 */
int32_t osSemaphoreWait(osSemaphoreId semaphore_id, uint32_t timeout)
{
	struct k_sem *semaphore = (struct k_sem *) semaphore_id;
	int status;

	if (semaphore_id == NULL) {
		return -1;
	}

	if (k_is_in_isr()) {
		return -1;
	}

	if (timeout == osWaitForever) {
		status = k_sem_take(semaphore, K_FOREVER);
	} else if (timeout == 0U) {
		status = k_sem_take(semaphore, K_NO_WAIT);
	} else {
		status = k_sem_take(semaphore, timeout);
	}

	/* If k_sem_take is successful, return the number of available
	 * tokens + 1. +1 is for accounting the currently acquired token.
	 * If it has timed out, return 0 (no tokens available).
	 */
	if (status == 0) {
		return k_sem_count_get(semaphore) + 1;
	} else {
		return 0;
	}
}

/**
 * @brief Release a semaphore that was obtained by osSemaphoreWait.
 */
osStatus osSemaphoreRelease(osSemaphoreId semaphore_id)
{
	struct k_sem *semaphore = (struct k_sem *) semaphore_id;

	if (semaphore_id == NULL) {
		return osErrorParameter;
	}

	/* All tokens have already been released */
	if (k_sem_count_get(semaphore) == semaphore->limit) {
		return osErrorResource;
	}

	k_sem_give(semaphore);

	return osOK;
}

/**
 * @brief Delete a semaphore that was created by osSemaphoreCreate.
 */
osStatus osSemaphoreDelete(osSemaphoreId semaphore_id)
{
	struct k_sem *semaphore = (struct k_sem *) semaphore_id;

	if (semaphore_id == NULL) {
		return osErrorParameter;
	}

	if (k_is_in_isr()) {
		return osErrorISR;
	}

	/* The status code "osErrorResource" (the semaphore object
	 * could not be deleted) is not supported in Zephyr.
	 */

	k_mem_slab_free(&cmsis_semaphore_slab, (void *) &semaphore);

	return osOK;
}
