/*
 * myapp.c
 *
 *  Created on: 20. 4. 2022
 *      Author: cosi
 */
#include "main.h"
#include "myapp.h"
#include "X2C.h"


rawADCData_typedef rawADCData;
int32_t Th_MCU;
extern char Btn_PB5,Btn_PB8;
int16_t updateCntr, updateCntMax = 10;

//inicializacni funkce
void MyInit(void){
		// Spusteni a povoleni kanalu TIM1
		LL_TIM_EnableCounter(TIM1);
		LL_TIM_CC_EnableChannel(TIM1,LL_TIM_CHANNEL_CH1
									|LL_TIM_CHANNEL_CH1N
									|LL_TIM_CHANNEL_CH2
									|LL_TIM_CHANNEL_CH2N
									|LL_TIM_CHANNEL_CH3
									|LL_TIM_CHANNEL_CH3N
									);
		LL_TIM_EnableAllOutputs(TIM1);

		//Spusteni TIM3
		LL_TIM_EnableCounter(TIM3);
		LL_TIM_CC_EnableChannel(TIM3,LL_TIM_CHANNEL_CH3);
		LL_TIM_EnableAllOutputs(TIM3);

		//Spusteni TIM16
		LL_TIM_EnableCounter(TIM16);
		LL_TIM_CC_EnableChannel(TIM16,LL_TIM_CHANNEL_CH1);
		LL_TIM_EnableAllOutputs(TIM16);

		//Reset digitálních izolátorů
		LL_TIM_OC_SetCompareCH1(TIM1, TIM1ARR/2);
		LL_TIM_OC_SetCompareCH2(TIM1, TIM1ARR/2);
		LL_TIM_OC_SetCompareCH3(TIM1, TIM1ARR/2);
		LL_TIM_OC_SetCompareCH3(TIM3, TIM3ARR/2);
		LL_TIM_OC_SetCompareCH1(TIM16, TIM16ARR/2);

		//zakazani PWM pro PFC a RB
		PFCSTOP();
		RBSTOP();
		IRAMYSTOP();

		// Nastaveni a povoleni DMA
		LL_DMA_ConfigAddresses(DMA1, LL_DMA_CHANNEL_1,
						(uint32_t) &(*ADC12_COMMON).CDR,
						(uint32_t) rawADCData.usData,
						LL_DMA_DIRECTION_PERIPH_TO_MEMORY);
		LL_DMA_SetDataLength(DMA1, LL_DMA_CHANNEL_1, ADCsmpNum); // Nastaveni delky dat - ADCsmpNum - pocet prenosu

		// Nastaveni preruseni DMA
		LL_DMA_ClearFlag_TC1(DMA1);
		LL_DMA_EnableIT_TC(DMA1, LL_DMA_CHANNEL_1);
		// Povoleni DMA kanalu
		LL_DMA_EnableChannel(DMA1, LL_DMA_CHANNEL_1);

		ADC12_COMMON->CCR |= ADC_CCR_TSEN | ADC_CCR_VREFEN;

		 uint32_t wait_loop_index;
		  wait_loop_index = ((LL_ADC_DELAY_INTERNAL_REGUL_STAB_US * (SystemCoreClock / (100000 * 2))) / 10);
		  while(wait_loop_index != 0)
		  {
		    wait_loop_index--;
		  }
		// Povoleni a spusteni ADC
		// Kalibrace
		LL_ADC_StartCalibration(ADC1, LL_ADC_SINGLE_ENDED);
		while (LL_ADC_IsCalibrationOnGoing(ADC1))
				;
		LL_ADC_StartCalibration(ADC2, LL_ADC_SINGLE_ENDED);
		while (LL_ADC_IsCalibrationOnGoing(ADC2))
				;
		LL_ADC_StartCalibration(ADC2, LL_ADC_DIFFERENTIAL_ENDED);
		while (LL_ADC_IsCalibrationOnGoing(ADC2))
				;
		// Povoleni interniho regulatoru a cekani na stabilizaci napeti
		LL_ADC_EnableInternalRegulator(ADC1);
		uint32_t delayCycles = 72000;
		while (--delayCycles)
				;
		// Povoleni ADC
		LL_ADC_Enable(ADC1);
		LL_ADC_Enable(ADC2);
		// Spusteni konverze
		LL_ADC_REG_StartConversion(ADC1);
		LL_ADC_REG_StartConversion(ADC2);

		//Reset uživatelských LED
		CLEAR_BIT(GPIOC->ODR,GPIO_ODR_11);
		CLEAR_BIT(GPIOC->ODR,GPIO_ODR_10);
		CLEAR_BIT(GPIOC->ODR,GPIO_ODR_6);
		CLEAR_BIT(GPIOB->ODR,GPIO_ODR_7);
}

//Funkce pro prepocet hodnot z ADC prevodniku na realne hodnoty
void MyUpdate(void){
	SET_BIT(GPIOA->ODR, GPIO_ODR_5);
	x2cModel.inports.bInIRAMYOverCurrent = readOverCurrent();
	x2cModel.inports.bInIRAMYOverTemp = readOverTemp();



	x2cModel.inports.bInIph1 = ADC2Current(rawADCData.RawADC.Iph1);
	x2cModel.inports.bInIph3 = ADC2Current(rawADCData.RawADC.Iph3);
	x2cModel.inports.bInPot = ADC2Vpot(rawADCData.RawADC.Vpot);
	x2cModel.inports.bInVdc = ADC2Vdc(rawADCData.RawADC.Vd);
	x2cModel.inports.bInVL1 = ADC2VL1(rawADCData.RawADC.VL1);
	//x2cModel.inports.bInThH = ADC2Th(rawADCData.RawADC.Th_H);

	CLEAR_BIT(GPIOA->ODR, GPIO_ODR_5);
	X2C_Update_1();
	SET_BIT(GPIOA->ODR, GPIO_ODR_5);



	TIM1->CCR1 = (uint32_t) (dutylimit((*x2cModel.outports.bOutDuty1)*0.5f+0.5f) * (float)TIM1ARR);
	TIM1->CCR2 = (uint32_t) (dutylimit((*x2cModel.outports.bOutDuty2)*0.5f+0.5f) * (float)TIM1ARR);
	TIM1->CCR3 = (uint32_t) (dutylimit((*x2cModel.outports.bOutDuty3)*0.5f+0.5f) * (float)TIM1ARR);


	CLEAR_BIT(GPIOA->ODR, GPIO_ODR_5);
}

void MyUpdate1kHz(void){
	if(++updateCntr == updateCntMax){
		updateCntr = 0;
		MyUpdate100Hz();

	}
}

void MyUpdate100Hz(void){

	x2cModel.inports.bInIPB8 = readGPIOB8();
	x2cModel.inports.bInIPB9 = readGPIOB9();
	x2cModel.inports.bInIPB4 = readGPIOB4();
	x2cModel.inports.bInIPB5 = readGPIOB5();

	X2C_Update_100();

	x2cModel.inports.bInDir = *x2cModel.outports.bOutDir;

	IRAMYCheck(*x2cModel.outports.bOutIRAMYEnable);
	PFCCheck(*x2cModel.outports.bOutPFCEnable&&x2cModel.inports.bInIPB5);
	RBCheck(*x2cModel.outports.bOutRBEnable);

	writeGPIOB7(*x2cModel.outports.bOutPB7_Green);
	writeGPIOC6(*x2cModel.outports.bOutPC6_Red);
	//writeGPIOC10(*x2cModel.outports.bOutThH>80);
	writeGPIOC11(*x2cModel.outports.bOutPC11_Green);
	Th_MCU = __LL_ADC_CALC_TEMPERATURE(__LL_ADC_CALC_VREFANALOG_VOLTAGE(rawADCData.RawADC.Vref,LL_ADC_RESOLUTION_12B),rawADCData.RawADC.Th_MCU,LL_ADC_RESOLUTION_12B);
}
