/**
 * \file
 *
 * \brief BPM driver
 *
 * Copyright (c) 2012 - 2013 Atmel Corporation. All rights reserved.
 *
 * \asf_license_start
 *
 * \page License
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are met:
 *
 * 1. Redistributions of source code must retain the above copyright notice,
 *    this list of conditions and the following disclaimer.
 *
 * 2. Redistributions in binary form must reproduce the above copyright notice,
 *    this list of conditions and the following disclaimer in the documentation
 *    and/or other materials provided with the distribution.
 *
 * 3. The name of Atmel may not be used to endorse or promote products derived
 *    from this software without specific prior written permission.
 *
 * 4. This software may only be redistributed and used in connection with an
 *    Atmel microcontroller product.
 *
 * THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR IMPLIED
 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE
 * EXPRESSLY AND SPECIFICALLY DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR
 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 * POSSIBILITY OF SUCH DAMAGE.
 *
 * \asf_license_stop
 *
 */

#include "compiler.h"
#include "bpm.h"

RAMFUNC bool bpm_ps_no_halt_exec(Bpm *bpm, uint32_t pmcon);
/**
 * \brief Execute Power Scaling No Halt with a delay loop
 *
 * \note SysTick is used to check timeout.
 *
 * \param bpm BPM register base
 * \param pmcon BPM_PMCON value to write
 *
 * \return PSOK status, true if set.
 */
RAMFUNC bool bpm_ps_no_halt_exec(Bpm *bpm, uint32_t pmcon)
{
	bool b_psok = false;
	bool b_timeout = false;
	BPM_UNLOCK(PMCON);
	bpm->BPM_PMCON = pmcon;
	do {
		b_psok = (BPM->BPM_SR & BPM_SR_PSOK);
		b_timeout = (SysTick->CTRL & SysTick_CTRL_COUNTFLAG_Msk);
	} while (!b_psok && !b_timeout);
	return b_psok;
}


bool bpm_power_scaling_cpu_failsafe(Bpm *bpm, uint32_t ps_value,
	uint32_t timeout)
{
	uint32_t pmcon = 0;

	/* Read last PM_CON value */
	pmcon = bpm->BPM_PMCON;

	/* Clear last PS Value & Write new one */
	pmcon &= ~BPM_PMCON_PS_Msk;
	pmcon |= BPM_PMCON_PS(ps_value);

	/* Set PSCM Value: PS change no halt */
	pmcon |= BPM_PMCON_PSCM;

	/* Power Scaling Change Request */
	pmcon |= BPM_PMCON_PSCREQ;

	/* Execute power scaling no halt in RAM */
	irqflags_t flags;
	bool b_psok;
	uint32_t ctrl, load, val;
	/* Avoid interrupt while flash halt */
	flags = cpu_irq_save();

	/* Save SysTick */
	val = SysTick->VAL;
	ctrl = SysTick->CTRL;
	load = SysTick->LOAD;
	/* Setup SysTick & start counting */
	SysTick->LOAD = timeout;
	SysTick->CTRL = SysTick_CTRL_CLKSOURCE_Msk | SysTick_CTRL_ENABLE_Msk;

	b_psok = bpm_ps_no_halt_exec(bpm, pmcon);

	/* Restore SysTick */
	SysTick->CTRL = 0;
	SysTick->LOAD = load;
	SysTick->VAL = val;
	SysTick->CTRL = ctrl;

	cpu_irq_restore(flags);
	return b_psok;
}

void bpm_power_scaling_cpu(Bpm *bpm, uint32_t ps_value)
{
	uint32_t pmcon = 0;
	/* Read last PM_CON value */
	pmcon = bpm->BPM_PMCON;
	/* Clear last PS Value */
	pmcon &= ~BPM_PMCON_PS_Msk;
	/* Write new PS Value */
	pmcon |= BPM_PMCON_PS(ps_value);
	/* PSCM: without CPU halt */
	pmcon |= BPM_PMCON_PSCM;
	/* Power Scaling Change Request */
	pmcon |= BPM_PMCON_PSCREQ;
	/* Unlock PMCON register */
	BPM_UNLOCK(PMCON);
	/* Write back PM_CON value */
	bpm->BPM_PMCON = pmcon;
}

void bpm_enable_fast_wakeup(Bpm *bpm)
{
	uint32_t pmcon = bpm->BPM_PMCON | BPM_PMCON_FASTWKUP;
	BPM_UNLOCK(PMCON);
	bpm->BPM_PMCON = pmcon;
}

void bpm_disable_fast_wakeup(Bpm *bpm)
{
	uint32_t pmcon = bpm->BPM_PMCON & (~BPM_PMCON_FASTWKUP);
	BPM_UNLOCK(PMCON);
	bpm->BPM_PMCON = pmcon;
}

void bpm_set_clk32_source(Bpm *bpm, uint32_t source)
{
	uint32_t pmcon;

	/* Read PMCON first */
	pmcon = bpm->BPM_PMCON;
	if (source == BPM_CLK32_SOURCE_OSC32K) {
		/* Clear CK32S for OSC32K */
		pmcon &= ~BPM_PMCON_CK32S;
	} else {
		/* Set CK32S for RC32K */
		pmcon |= BPM_PMCON_CK32S;
	}

	/* Unlock PMCON register */
	BPM_UNLOCK(PMCON);
	bpm->BPM_PMCON = pmcon;
}

uint32_t bpm_get_backup_wakeup_cause(Bpm *bpm)
{
	return bpm->BPM_BKUPWCAUSE;
}

void bpm_enable_wakeup_source(Bpm *bpm, uint32_t sources)
{
	/* Write BKUPWEN value */
	bpm->BPM_BKUPWEN |= sources;
}

void bpm_disable_wakeup_source(Bpm *bpm, uint32_t sources)
{
	/* Write BKUPWEN value */
	bpm->BPM_BKUPWEN &= ~sources;
}

void bpm_enable_backup_pin(Bpm *bpm, uint32_t backup_pins)
{
	/* Write back BKUPPMUX value */
	bpm->BPM_BKUPPMUX |= backup_pins;
}

void bpm_disable_backup_pin(Bpm *bpm, uint32_t backup_pins)
{
	/* Write back BKUPPMUX value */
	bpm->BPM_BKUPPMUX &= ~backup_pins;
}

void bpm_enable_io_retention(Bpm *bpm)
{
	bpm->BPM_IORET |= BPM_IORET_RET;
}

void bpm_disable_io_retention(Bpm *bpm)
{
	bpm->BPM_IORET &= ~BPM_IORET_RET;
}

void bpm_enable_interrupt(Bpm *bpm, uint32_t sources)
{
	bpm->BPM_IER = sources;
}

void bpm_disable_interrupt(Bpm *bpm, uint32_t sources)
{
	bpm->BPM_IDR = sources;
}

uint32_t bpm_get_interrupt_mask(Bpm *bpm)
{
	return bpm->BPM_IMR;
}

uint32_t bpm_get_interrupt_status(Bpm *bpm)
{
	return bpm->BPM_ISR;
}

void bpm_clear_interrupt(Bpm *bpm, uint32_t sources)
{
	bpm->BPM_ICR = sources;
}

uint32_t bpm_get_status(Bpm *bpm)
{
	return bpm->BPM_SR;
}

uint32_t bpm_get_version(Bpm *bpm)
{
	return bpm->BPM_VERSION;
}

void bpm_sleep(Bpm *bpm, uint32_t sleep_mode)
{
	uint32_t pmcon;

	/* Read PMCON register */
	pmcon = bpm->BPM_PMCON;
	pmcon &= ~BPM_PMCON_BKUP;
	pmcon &= ~BPM_PMCON_RET;
	pmcon &= ~BPM_PMCON_SLEEP_Msk;

	/* Unlock PMCON register */
	BPM_UNLOCK(PMCON);

	if (sleep_mode == BPM_SM_SLEEP_0) {
		pmcon |= BPM_PMCON_SLEEP(0);
		bpm->BPM_PMCON = pmcon;
		SCB->SCR &= ~SCB_SCR_SLEEPDEEP_Msk;
	} else if (sleep_mode == BPM_SM_SLEEP_1) {
		pmcon |= BPM_PMCON_SLEEP(1);
		bpm->BPM_PMCON = pmcon;
		SCB->SCR &= ~SCB_SCR_SLEEPDEEP_Msk;
	} else if (sleep_mode == BPM_SM_SLEEP_2) {
		pmcon |= BPM_PMCON_SLEEP(2);
		bpm->BPM_PMCON = pmcon;
		SCB->SCR &= ~SCB_SCR_SLEEPDEEP_Msk;
	} else if (sleep_mode == BPM_SM_SLEEP_3) {
		pmcon |= BPM_PMCON_SLEEP(3);
		bpm->BPM_PMCON = pmcon;
		SCB->SCR &= ~SCB_SCR_SLEEPDEEP_Msk;
	} else if (sleep_mode == BPM_SM_WAIT) {
		bpm->BPM_PMCON = pmcon;
		SCB->SCR |= SCB_SCR_SLEEPDEEP_Msk;
	} else if (sleep_mode == BPM_SM_RET) {
		pmcon |= BPM_PMCON_RET;
		bpm->BPM_PMCON = pmcon;
		SCB->SCR |= SCB_SCR_SLEEPDEEP_Msk;
	} else { /* if (sleep_mode == BPM_SM_BACKUP) */
		pmcon |= BPM_PMCON_BKUP;
		bpm->BPM_PMCON = pmcon;
		SCB->SCR |= SCB_SCR_SLEEPDEEP_Msk;
	}

	/* Wait until vreg is ok. */
	while(!(BSCIF->BSCIF_PCLKSR & BSCIF_PCLKSR_VREGOK));
	asm volatile ("wfi");
	/* ensure sleep request propagation to flash. */
	asm volatile ("nop");

	/* The interrupts wake-up from the previous wfi, but there are still
	 * masked since we are in the critical section thanks to the previous
	 * set_pri_mask(1). Thus, we need to leave the critical section.
	 * Please note that we should probably use something like
	 * cpu_leave_critical(), using set_pri_mask(0)
	 */
	/* In this demo interrupts are managed by the FreeRTOS kernel and must not
	be altered here so the following line has been removed _RB_
	cpu_irq_enable(); */
}
