#include "t1001.h"
#include "stdint.h"
#include "omw_sdma.h"


TASK_STRUCT SDMA_Task_Struct;
int SDMA_TaskTable[32];

void omw_sdma_init(void)
{
    for(int i=0;i<32;i++)
	    SDMA_TaskTable[i]	 = (uint32_t)(SDMA_Task_Struct.task0 + i*SDMA_TASK_SIZE);
    SYS_CTRL->SDMA_TASK_TABLE_ADDR = (uint32_t)SDMA_TaskTable;
}

void omw_sdma_cmd(FunctionalState NewState)
{
	assert_param(IS_FUNCTIONAL_STATE(NewState));
	SYS_CTRL->SDMA_EN = NewState;
}


void omw_sdma_action(uint8_t dma_action)
{
	assert_param(IS_SDMA_ACTION(dma_action));
	
	SYS_CTRL->SDMA_ACTION = dma_action;
	SYS_CTRL->SDMA_ACTION = 0;
}

void omw_sdma_task_init(SDMA_TASK_InitTypeDef *sdma_task_ptr ,uint32_t * Sdma_taskX)
{
	
	//cfg0
	uint32_t t = 0;
	if(sdma_task_ptr->dma_word_en == SDMA_TASK_TRANSACTION_WORD)
	sdma_task_ptr->num_bytes = (sdma_task_ptr->num_bytes << 2);
	
	t = (sdma_task_ptr->int_en) + (sdma_task_ptr->dma_word_en) + (sdma_task_ptr->task_format) + (sdma_task_ptr->cmd_war) + (sdma_task_ptr->cmd_pre_en) \
	    + (sdma_task_ptr->trigger_index << 20) + (sdma_task_ptr->src_add_inc_en)+(sdma_task_ptr->dst_add_inc_en)+(sdma_task_ptr->src_begin_upd_en)+(sdma_task_ptr->dst_begin_upd_en) + (sdma_task_ptr->num_bytes);
	*(volatile uint32_t*)(Sdma_taskX + 0) = t;
	
	//cfg1
	*(volatile uint32_t*)(Sdma_taskX + 1) = sdma_task_ptr->src_addr;
	
	//cfg2
	*(volatile uint32_t*)(Sdma_taskX + 2) = sdma_task_ptr->dst_addr;
	
	//cfg3
	t = 0;
	if(sdma_task_ptr->task_format == SDMA_TASK_MODE_FIFO) 
	{  
		t = t + ((sdma_task_ptr->fifo_mode_dst) << 0) + ((sdma_task_ptr->fifo_mode_src) << 1);
		t = t + ((sdma_task_ptr->fifo_size) << 4);
    }
	else if(sdma_task_ptr->task_format == SDMA_TASK_MODE_COMMAND)
	{
		t = (sdma_task_ptr->cmd_addr);
	}
    *(volatile uint32_t*)(Sdma_taskX + 3) = t;
	
	//cfg4
	if(sdma_task_ptr->task_format == SDMA_TASK_MODE_COMMAND)
		*(volatile uint32_t*)(Sdma_taskX + 4) = sdma_task_ptr -> cmd_wdata;
	else
	    *(volatile uint32_t*)(Sdma_taskX + 4) = 0;
	//cfg5
	if(sdma_task_ptr->task_format == SDMA_TASK_MODE_COMMAND)
	    *(volatile uint32_t*)(Sdma_taskX + 5) = sdma_task_ptr -> cmd_mask;
    else
	    *(volatile uint32_t*)(Sdma_taskX + 4) = 0;
}




void omw_sdma_task_struct_init(SDMA_TASK_InitTypeDef *sdma_task_ptr)
{
	sdma_task_ptr ->int_en = SDMA_TASK_INTR_DISABLE;
	sdma_task_ptr ->dma_word_en = SDMA_TASK_TRANSACTION_BYTE;
	sdma_task_ptr ->task_format = SDMA_TASK_MODE_NORMAL;
	sdma_task_ptr ->cmd_war = SDMA_TASK_CMD_WAR_DISABLE;
	sdma_task_ptr ->cmd_pre_en = SDMA_TASK_CMD_PRE_DISABLE;
	
	
	sdma_task_ptr ->trigger_index = 31;
    sdma_task_ptr ->src_add_inc_en = SDMA_TASK_SRC_ADD_INCRE_DISABLE;
    sdma_task_ptr ->dst_add_inc_en = SDMA_TASK_DST_ADD_INCRE_DISABLE;
    sdma_task_ptr ->src_begin_upd_en = SDMA_TASK_SRC_BEGIN_UDT_DISABLE;
    sdma_task_ptr ->dst_begin_upd_en = SDMA_TASK_DST_BEGIN_UDT_DISABLE;
	sdma_task_ptr ->num_bytes = 0;
	sdma_task_ptr ->src_addr = 0;
	sdma_task_ptr ->dst_addr = 0;
	sdma_task_ptr ->cmd_addr = 0;
	sdma_task_ptr ->cmd_wdata = 0;
	sdma_task_ptr ->cmd_mask = 0;
	sdma_task_ptr ->fifo_size = 0;
	sdma_task_ptr ->fifo_mode_src = 0;
	sdma_task_ptr ->fifo_mode_dst = 0;
}


void omw_sdma_value_set(uint32_t SDMAx,FlagStatus NewStatus)
{
	
	if(NewStatus == SET)
		SYS_CTRL->SDMA_TASK_VAL |= SDMAx;
	else
		SYS_CTRL->SDMA_TASK_VAL &= ~(SDMAx);
}


uint32_t omw_sdma_status(void)
{
	return SYS_CTRL->SDMA_TASK_STATUS;
}



uint8_t omw_sdma_status_bit(uint32_t SDMAx)
{
	uint8_t flag;
	if ((SDMAx & (SYS_CTRL->SDMA_TASK_STATUS)) != 0)
	  flag = SET;
	else
		flag = RESET;
	return flag;
}



uint32_t omw_sdma_get_it_status(void)
{
	return SYS_CTRL->SDMA_INT_STATUS;
}



uint8_t omw_sdma_get_it_status_bit(uint32_t SDMAx)
{
	uint8_t flag;
	if ((SDMAx & (SYS_CTRL->SDMA_INT_STATUS)) != 0)
	  flag = SET;
	else
		flag = RESET;
	return flag;
}


void omw_sdma_intr_clr(uint32_t SDMAx)
{
	SYS_CTRL->SDMA_INT_CLEAR = SDMAx;
}