/**
  **********************************************************************************
  * @file    cache_drv.c
  * @author  Product application department
  * @version V1.0
  * @date    2020.02.25
  * @brief   cache驱动.
  * @note 这个文件提供了drv层cache接口:
  *     - cache初始化接口.
  *     - 获取cache状态接口.
  *     - cache清除接口.
  *
  @verbatim
  ===================================================================================
                                  ##### 更新 #####
  ===================================================================================
  [..] 更新时间:
  [..] 更新人:
  [..] 更新内容:
        1. nothing.
  @endverbatim
 */

#include "cache_drv.h"

/*** 全局变量定义 ***************************************************************/
/*** volatile **********/

/*** @ static **********/

/*** 常量定义 *******************************************************************/

/*** 函数定义 *******************************************************************/

/**
 * @brief ICACHE初始化
 * @param[in] rom: The attributes of rom memory regions；
*                          取值cacheThrough, cacheBack or cacheOff
 *			 boot：The attributes of boot memory regions
 *                   	取值cacheThrough, cacheBack or cacheOff
 *			 spim1： The attributes of spim1 memory regions
 *				取值cacheThrough, cacheBack or cacheOff
 *			 eflash： The attributes of eflash memory regions
 *				取值cacheThrough, cacheBack or cacheOff
 * @note 上电后执行一次，请勿重复执行
 * @retval NONE
*/
void DRV_ICACHE_Init(CACHE_ComTypeDef spim1,CACHE_ComTypeDef spim2,CACHE_ComTypeDef sdram, CACHE_ComTypeDef eflash, CACHE_ComTypeDef rom, CACHE_ComTypeDef boot)
{
	/*    spim1 cache configuration    */
	if (CACHE_Off == spim1)
	{
		IPCCRGS_H &= SPIM1_CACHEOFF;
	}
	
	else if (CACHE_Through == spim1)
	{
		IPCCRGS_H &= SPIM1_CACHEOFF;
		IPCCRGS_H |= (WRITE_THROUGH << SPIM1_CACHE_SHIFT);
	}
	else if (CACHE_Back == spim1)
	{
		IPCCRGS_H &= SPIM1_CACHEOFF;
		IPCCRGS_H |= (WRITE_BACK << SPIM1_CACHE_SHIFT);
	}
	/*    spim2 cache configuration    */
	if (CACHE_Off == spim2)
	{
		IPCCRGS_H &= SPIM2_CACHEOFF;
	}
	else if (CACHE_Through == spim2)
	{
		IPCCRGS_H &= SPIM2_CACHEOFF;
		IPCCRGS_H |= (WRITE_THROUGH << SPIM2_CACHE_SHIFT);
	}
	else if (CACHE_Back == spim2)
	{
		IPCCRGS_H &= SPIM2_CACHEOFF;
		IPCCRGS_H |= (WRITE_BACK << SPIM2_CACHE_SHIFT);
	}
	/*sdram cache configuration*/
	
	if (CACHE_Off == sdram)
	{
		IPCCRGS_H &= SDRAM_CACHEOFF;
	}
	else if (CACHE_Through == sdram)
	{
		IPCCRGS_H &= SDRAM_CACHEOFF;
		IPCCRGS_H |= (WRITE_THROUGH << SDRAM_CACHE_SHIFT);
	}
	else if (CACHE_Back == sdram)
	{
		IPCCRGS_H &= SDRAM_CACHEOFF;
		IPCCRGS_H |= (WRITE_BACK << SDRAM_CACHE_SHIFT);
	}	
	
	
	/*    rom cache configuration    */
	if (CACHE_Off == rom)
	{
		IPCCRGS &= ROM_CACHEOFF;
	}
	else if (CACHE_Through == rom)
	{
		IPCCRGS &= ROM_CACHEOFF;
		IPCCRGS |= (0x02 << ROM_CACHE_SHIFT);
	}
	else if (CACHE_Back == rom)
	{
		IPCCRGS &= ROM_CACHEOFF;
		IPCCRGS |= (0x03 << ROM_CACHE_SHIFT);
	}
		
	/*    boot cache configuration    */
	if (CACHE_Off == boot)
	{
		IPCCRGS_H &= BOOT_CACHEOFF;
	}
	else if (CACHE_Through == boot)
	{
		IPCCRGS_H &= BOOT_CACHEOFF;
		IPCCRGS_H |= (WRITE_THROUGH << BOOT_CACHE_SHIFT);
	}
	else if (CACHE_Back == boot)
	{
		IPCCRGS_H &= BOOT_CACHEOFF;
		IPCCRGS_H |= (WRITE_BACK << BOOT_CACHE_SHIFT);
	}
	
	/*    eflash cache configuration    */
	if (CACHE_Off == eflash)
	{
		IPCCRGS &= EFLASH_CACHEOFF;
	}
	else if (CACHE_Through == eflash)
	{
		//IR2HIGHADDR = 0x1fffff;
		IPCCRGS &= EFLASH_CACHEOFF;
		IPCCRGS |= (EFLASH_WRITE_THROUGH << EFLASH_CACHE_SHIFT);
	}
	else if (CACHE_Back == eflash)
	{
		//IR2HIGHADDR = 0x1fffff;
		IPCCRGS &= EFLASH_CACHEOFF;
		IPCCRGS |= (EFLASH_WRITE_BACK << EFLASH_CACHE_SHIFT );
	}
	
	ICACHE->CACHE_CCR |= (GO|INVW1|INVW0);
	while( ((ICACHE->CACHE_CCR)&(GO)) == GO );
	ICACHE->CACHE_CCR |= ENCACHE;
}

/**
 * @brief DCACHE初始化
 * @param[in] rom: The attributes of rom memory regions；
*                          取值cacheThrough, cacheBack or cacheOff
*                   boot：The attributes of boot memory regions
*                          取值cacheThrough, cacheBack or cacheOff
*                   spim1： The attributes of spim1 memory regions
*                          取值cacheThrough, cacheBack or cacheOff
*                   eflash： The attributes of eflash memory regions
*                          取值cacheThrough, cacheBack or cacheOff
 * @note 上电后执行一次，请勿重复执行
 * @retval NONE
*/
void DRV_DCACHE_Init(CACHE_ComTypeDef spim1,CACHE_ComTypeDef spim2,CACHE_ComTypeDef sdram, CACHE_ComTypeDef eflash, CACHE_ComTypeDef rom, CACHE_ComTypeDef boot)
{
	/*    spim1 cache configuration    */
	if (CACHE_Off == spim1)
	{
		DPCCRGS_H &= SPIM1_CACHEOFF;
	}
	else if (CACHE_Through == spim1)
	{
		DPCCRGS_H &= SPIM1_CACHEOFF;
		DPCCRGS_H |= (WRITE_THROUGH << SPIM1_CACHE_SHIFT);
	}
	else if (CACHE_Back == spim1)
	{
		DPCCRGS_H &= SPIM1_CACHEOFF;
		DPCCRGS_H |= (WRITE_BACK << SPIM1_CACHE_SHIFT);
	}
	/*    spim2 cache configuration    */
	if (CACHE_Off == spim2)
	{
		DPCCRGS_H &= SPIM2_CACHEOFF;
	}
	else if (CACHE_Through == spim2)
	{
		DPCCRGS_H &= SPIM2_CACHEOFF;
		DPCCRGS_H |= (WRITE_THROUGH << SPIM2_CACHE_SHIFT);
	}
	else if (CACHE_Back == spim2)
	{
		DPCCRGS_H &= SPIM2_CACHEOFF;
		DPCCRGS_H |= (WRITE_BACK << SPIM2_CACHE_SHIFT);
	}
	/*    sdram cache configuration    */	
	
	if (CACHE_Off == sdram)
	{
		DPCCRGS_H &= SDRAM_CACHEOFF;
	}
	else if (CACHE_Through == sdram)
	{
		DPCCRGS_H &= SDRAM_CACHEOFF;
		DPCCRGS_H |= (WRITE_THROUGH << SDRAM_CACHE_SHIFT);
	}
	else if (CACHE_Back == sdram)
	{
		DPCCRGS_H &= SDRAM_CACHEOFF;
		DPCCRGS_H |= (WRITE_BACK << SDRAM_CACHE_SHIFT);
	}	
	
	
	/*    rom cache configuration    */
	if (CACHE_Off == rom)
	{
		DPCCRGS &= ROM_CACHEOFF;
	}
	else if (CACHE_Through == rom)
	{
		DPCCRGS &= ROM_CACHEOFF;
		DPCCRGS |= (0x02 << ROM_CACHE_SHIFT);
	}
	else if (CACHE_Back == rom)
	{
		DPCCRGS &= ROM_CACHEOFF;
		DPCCRGS |= (0x03 << ROM_CACHE_SHIFT);
	}
		
	/*    boot cache configuration    */
	if (CACHE_Off == boot)
	{
		DPCCRGS_H &= BOOT_CACHEOFF;
	}
	else if (CACHE_Through == boot)
	{
		DPCCRGS_H &= BOOT_CACHEOFF;
		DPCCRGS_H |= (WRITE_THROUGH << BOOT_CACHE_SHIFT);
	}
	else if (CACHE_Back == boot)
	{
		DPCCRGS_H &= BOOT_CACHEOFF;
		DPCCRGS_H |= (WRITE_BACK << BOOT_CACHE_SHIFT);
	}
	
	/*    eflash cache configuration   */
	if (CACHE_Off == eflash)
	{
		DPCCRGS &= EFLASH_CACHEOFF;
	}
	else if (CACHE_Through == eflash)
	{
		//DR2HIGHADDR = 0x1fffff;
		DPCCRGS &= EFLASH_CACHEOFF;
		DPCCRGS |= (EFLASH_WRITE_THROUGH << EFLASH_CACHE_SHIFT);
	}
	else if (CACHE_Back == eflash)
	{
		//DR2HIGHADDR = 0x1fffff;
		DPCCRGS &= EFLASH_CACHEOFF;
		DPCCRGS |= (EFLASH_WRITE_BACK << EFLASH_CACHE_SHIFT);
	}
	
	DCACHE->CACHE_CCR |= (GO|INVW1|INVW0);
	while( ((DCACHE->CACHE_CCR)&(GO)) == GO );
	DCACHE->CACHE_CCR |= ENCACHE;	
}

void DRV_ICACHE_Syn(void)
{
	DCACHE->CACHE_CCR |= (GO|PUSHW0|PUSHW1);
	while( ((DCACHE->CACHE_CCR)&(GO)) == GO );
}

void DRV_DCACHE_Syn(void)
{
	ICACHE->CACHE_CCR |= (GO|INVW0|INVW1);
	while( ((ICACHE->CACHE_CCR)&(GO)) == GO );
}


