/*
 * Copyright (c) 2018, Arm Limited. All rights reserved.
 *
 * SPDX-License-Identifier: BSD-3-Clause
 */

#include <arch_helpers.h>
#include <lib/spinlock.h>
#include <lib/utils_def.h>
#include <platform_def.h>

/*******************************************************************************
 * Secure Service response global array. All the responses to the requests done
 * to the Secure Partition are stored here. They are removed from the array as
 * soon as their value is read.
 ******************************************************************************/
struct sprt_response {
	int is_valid;
	uint32_t token;
	uint16_t client_id, handle;
	u_register_t x1, x2, x3;
};

static struct sprt_response responses[PLAT_SPM_RESPONSES_MAX];

static spinlock_t responses_lock;

/* Add response to the global response buffer. Returns 0 on success else -1. */
int spm_response_add(uint16_t client_id, uint16_t handle, uint32_t token,
		     u_register_t x1, u_register_t x2, u_register_t x3)
{
	spin_lock(&responses_lock);

	/* Make sure that there isn't any other response with the same token. */
	for (unsigned int i = 0U; i < ARRAY_SIZE(responses); i++) {
		struct sprt_response *resp = &(responses[i]);

		if ((resp->is_valid == 1) && (resp->token == token)) {
			return -1;
		}
	}

	for (int i = 0; i < ARRAY_SIZE(responses); i++) {
		struct sprt_response *resp = &(responses[i]);

		if (resp->is_valid == 0) {
			resp->token = token;
			resp->client_id = client_id;
			resp->handle = handle;
			resp->x1 = x1;
			resp->x2 = x2;
			resp->x3 = x3;

			dmbish();

			resp->is_valid = 1;

			spin_unlock(&responses_lock);

			return 0;
		}
	}

	spin_unlock(&responses_lock);

	return -1;
}

/*
 * Returns a response from the requests array and removes it from it. Returns 0
 * on success, -1 if it wasn't found.
 */
int spm_response_get(uint16_t client_id, uint16_t handle, uint32_t token,
		     u_register_t *x1, u_register_t *x2, u_register_t *x3)
{
	spin_lock(&responses_lock);

	for (unsigned int i = 0U; i < ARRAY_SIZE(responses); i++) {
		struct sprt_response *resp = &(responses[i]);

		/* Ignore invalid entries */
		if (resp->is_valid == 0) {
			continue;
		}

		/* Make sure that all the information matches the stored one */
		if ((resp->token != token) || (resp->client_id != client_id) ||
		    (resp->handle != handle)) {
			continue;
		}

		*x1 = resp->x1;
		*x2 = resp->x2;
		*x3 = resp->x3;

		dmbish();

		resp->is_valid = 0;

		spin_unlock(&responses_lock);

		return 0;
	}

	spin_unlock(&responses_lock);

	return -1;
}
