/*
 * Copyright (C) 2019 Marvell International Ltd.
 *
 * SPDX-License-Identifier:     BSD-3-Clause
 * https://spdx.org/licenses
 */

#include <a8k_plat_def.h>
#include <arch_helpers.h>
#include <common/debug.h>
#include <lib/mmio.h>
#include <mss_scp_bl2_format.h>

/* CONFI REGISTERS */
#define MG_CM3_CONFI_BASE(CP)		(MVEBU_CP_REGS_BASE(CP) + 0x100000)
#define MG_CM3_SRAM_BASE(CP)		MG_CM3_CONFI_BASE(CP)
#define MG_CM3_CONFI_GLOB_CFG_REG(CP)	(MG_CM3_CONFI_BASE(CP) + 0x2B500)
#define CM3_CPU_EN_BIT			BIT(28)
#define MG_CM3_MG_INT_MFX_REG(CP)	(MG_CM3_CONFI_BASE(CP) + 0x2B054)
#define CM3_SYS_RESET_BIT		BIT(0)

#define MG_CM3_SHARED_MEM_BASE(CP)	(MG_CM3_SRAM_BASE(CP) + 0x1FC00ULL)

#define MG_SRAM_SIZE	0x20000 /* 128KB */

#define MG_ACK_TIMEOUT 10

/**
 * struct ap_sharedmem_ctrl - used to pass information between the HOST and CM3
 * @init_done:	Set by CM3 when ap_proces initialzied. Host check if CM3 set
 *		this flag to confirm that the process is running
 * @lane_nr:	Set by Host to mark which comphy lane should be configure. E.g.:
 *		- A8K development board uses comphy lane 2 for eth0
 *		- CN913x development board uses comphy lane 4 for eth0
 */
struct ap_sharedmem_ctrl {
	uint32_t init_done;
	uint32_t lane_nr;
};

int mg_image_load(uintptr_t src_addr, uint32_t size, int cp_index)
{
	uintptr_t mg_regs = MG_CM3_SRAM_BASE(cp_index);

	if (size > MG_SRAM_SIZE) {
		ERROR("image is too big to fit into MG CM3 memory\n");
		return 1;
	}

	NOTICE("Loading MG image from address 0x%lx Size 0x%x to MG at 0x%lx\n",
	       src_addr, size, mg_regs);

	/* Copy image to MG CM3 SRAM */
	memcpy((void *)mg_regs, (void *)src_addr, size);

	/* Don't release MG CM3 from reset - it will be done by next step
	 * bootloader (e.g. U-Boot), when appriopriate device-tree setup (which
	 * has enabeld 802.3. auto-neg) will be chosen.
	 */

	return 0;
}

void mg_start_ap_fw(int cp_nr, uint8_t comphy_index)
{
	volatile struct ap_sharedmem_ctrl *ap_shared_ctrl =
					(void *)MG_CM3_SHARED_MEM_BASE(cp_nr);
	int timeout = MG_ACK_TIMEOUT;

	if (mmio_read_32(MG_CM3_CONFI_GLOB_CFG_REG(cp_nr)) & CM3_CPU_EN_BIT) {
		VERBOSE("cm3 already running\n");
		return;  /* cm3 already running */
	}

	/*
	 * Mark which comphy lane should be used - it will be read via shared
	 * mem by ap process
	 */
	ap_shared_ctrl->lane_nr = comphy_index;
	/* Make sure it took place before enabling cm3 */
	dmbst();

	mmio_setbits_32(MG_CM3_CONFI_GLOB_CFG_REG(cp_nr), CM3_CPU_EN_BIT);
	mmio_setbits_32(MG_CM3_MG_INT_MFX_REG(cp_nr), CM3_SYS_RESET_BIT);

	/* Check for ap process initialization by fw */
	while (ap_shared_ctrl->init_done != 1 && timeout--)
		VERBOSE("Waiting for ap process ack, timeout %d\n", timeout);

	if (timeout == 0) {
		ERROR("AP process failed, disabling cm3\n");
		mmio_clrbits_32(MG_CM3_MG_INT_MFX_REG(cp_nr),
				CM3_SYS_RESET_BIT);
		mmio_clrbits_32(MG_CM3_CONFI_GLOB_CFG_REG(cp_nr),
				CM3_CPU_EN_BIT);
	}
}
