//*****************************************************************************
//
// ADCdriver.c - Knihovna pro ovladani A/D prevodnikuDriver for the Analog to Digital Convertor (ADC)
// 
//*****************************************************************************


#include <hw_memmap.h>
#include <hw_types.h>
#include <hw_gpio.h>
#include <hw_ints.h>
#include <hw_sysctl.h>
#include <sysctl.h>
#include <systick.h>
#include <gpio.h>
#include <debug.h>
#include <intrinsics.h>
#include <interrupt.h>

#include <ADCdriver.h>
#include <SPIdriver.h>
#include <LEDdriver.h>



//Definice konstant
#define PORTD_PIN2 GPIO_PORTD_AHB_BASE + GPIO_O_DATA + (GPIO_PIN_2 << 2)        //Rizeni spinace pro vybiti kondenzatoru, na kterem se provadi integrace
#define PORTE_PIN0 GPIO_PORTE_AHB_BASE + GPIO_O_DATA + (GPIO_PIN_0 << 2)        //Pro pristup k pinu pri 50MHz / spusteni prevodu - signal CONV
#define PORTE_PIN1 GPIO_PORTE_AHB_BASE + GPIO_O_DATA + (GPIO_PIN_1 << 2)        //Pro pristup k pinu pri 50MHz / spusteni prevodu - signal CONV
#define PORTE_PIN2 GPIO_PORTE_AHB_BASE + GPIO_O_DATA + (GPIO_PIN_2 << 2)        //Pro pristup k pinu pri 50MHz / spusteni prevodu - signal CONV
#define PORTE_PIN3 GPIO_PORTE_AHB_BASE + GPIO_O_DATA + (GPIO_PIN_3 << 2)        //Pro pristup k pinu pri 50MHz / spusteni prevodu - signal CONV
//#define PORTE_PINX(x) (GPIO_PORTE_AHB_BASE + GPIO_O_DATA + ((GPIO_PIN_0 << x) << 2))    //pro rychly pristup k pinu x na portu E

//Definice funkci***************************************************************
//Inicializace pinu pro rizeni A/D prevodu-------------------------------------
void ADCInit(void)
{
    SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOE);                                //Konfigurace pinu 0 na portu E jako vystupni / signal CONV
    SysCtlGPIOAHBEnable(SYSCTL_PERIPH_GPIOE);
    GPIOPinTypeGPIOOutput(GPIO_PORTE_AHB_BASE, MEASURE_PINS);                   //pin pro vybijeni mer.kondenzatoru take nastaven jako vystupni
    HWREG(0x4005C010) = GPIO_PIN_2;                                             //Po inicializaci pinu je ve vychozim stavu kondenzator vybijen pres spinac do zeme
}

//Vygenerovani pulzu LD, zmereni a navraceni hodnoty z A/D---------------------- 
unsigned short ADCGetValue(unsigned char channel)                               //Paramtr channel rika, ze ktereho A/D prevodniku se bude cist / nastaveni CS
{
    unsigned short result;
    
    SPI_SetCS(channel);                                                         //Pro dany A/D prevodnik nastavi signal CS / vyber A/D prevodniku
    IntMasterDisable();                                                         //Zakazani preruseni procesoru / stejna doba integrace
    
    //HWREG(GPIO_PORTE_AHB_BASE + GPIO_O_DATA + (GPIO_PIN_2 << 2)) = GPIO_PIN_2;  // Vybijeni
    
    HWREG(PORTD_PIN2) = 0;                                                      //Rozepnuti spinace pro vybijeni kondenzatoru / spusteni integrace
    
    LEDPulse(1);                                                                //Vygenerovani pulzu laserovou diodou
    
    //HWREG(PORTE_PIN0) = GPIO_PIN_0;                                             //Spusteni prevodu na zvolenem A/D  / signalem CONV

    switch(channel%4)
    {
      case 0:
      {
        HWREG(PORTE_PIN0) = GPIO_PIN_0;
        break;
      }
      case 1:
      {
        //HWREG(PORTE_PIN1) = GPIO_PIN_1;
        break;
      }
      case 2:
      {
        HWREG(PORTE_PIN2) = GPIO_PIN_2;
        break;
      }
      case 3:
      {
       // HWREG(PORTE_PIN3) = GPIO_PIN_3;
        break;
      }
    }
    
    //SysCtlDelay(1);                                                           // The loop takes 3 cycles/loop.
    HWREG(PORTD_PIN2) = GPIO_PIN_2;                                             //Merena hodnota je jiz zapamatovana na A/D prevodniku, vybiti kondenzatoru pro integraci
    
    SysCtlDelay(11);                                                            //Odzkousene zpozdeni pro dokonceni prevodu A/D prevodniku (za 1 cyklus 3 instrukce)
    
    IntMasterEnable();                                                          //Povoleni preruseni / jiz je domereno
    result = SPI_Read16b();                                                     //Vycteni dat z A/D prevodniku
    SPI_SetCS(SPI_CS_OFF);                                                      //Deaktivace vybraneho A/D prevodniku pomoci signalu CS
    
   // HWREG(PORTE_PIN0) = 0;                                                      //Deaktivace signalu CONV
    switch(channel%4)
    {
      case 0:
      {
        HWREG(PORTE_PIN0) = 0;
        break;
      }
      case 1:
      {
        //HWREG(PORTE_PIN1) = 0;
        break;
      }
      case 2:
      {
        HWREG(PORTE_PIN2) = 0;
        break;
      }
      case 3:
      {
       // HWREG(PORTE_PIN3) = 0;
        break;
      }
    }
    SysCtlDelay(100);
    
    return result;                                                              //Funkce vraci hodnotu vyctenou z A/D prevodniku
}

//Funkce pro vycteni hodnot ze vsech A/D prevodniku-----------------------------
void ADCGetAllValues()
{  
   //unsigned short value;
    
    //value=ADCGetValue(0);
}
