This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

timer triggering adc

using Tiva launchpad, TM4C123GH6PM

Still learning. Hoping somebody can spot what's wrong. I'm trying to setup a timer to trigger ADC. ADC returns incorrect values.

#define PART_TM4C123GH6PM

#include <stdint.h>
#include <stdbool.h>
#include "stdlib.h"
#include "inc/hw_ints.h"
#include "inc/hw_memmap.h"
#include "inc/hw_uart.h"
#include "inc/hw_timer.h"
#include "inc/hw_gpio.h"
#include "inc/hw_pwm.h"
#include "inc/hw_types.h"
#include "driverlib/adc.h"
#include "driverlib/timer.h"
#include "driverlib/gpio.h"
#include "driverlib/timer.h"
#include "driverlib/interrupt.h"
#include "driverlib/pin_map.h"
#include "driverlib/rom.h"
#include "driverlib/rom_map.h"
#include "driverlib/sysctl.h"
#include "driverlib/uart.h"
#include "driverlib/udma.h"
#include "driverlib/pwm.h"
#include "driverlib/ssi.h"
#include "driverlib/systick.h"
#include "driverlib/adc.h"
#include "utils/uartstdio.h"
#include "utils/uartstdio.c"
#include <string.h>

uint32_t _adc;
uint32_t TempValueC;

void ADCInit(void)
{
    // ADC
    SysCtlPeripheralEnable(SYSCTL_PERIPH_ADC0);
    SysCtlDelay(3);
    //  GPIO (ADC Pins)
    //SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOD);
    ADCSequenceConfigure(ADC0_BASE, 1, ADC_TRIGGER_TIMER, 0);
    ADCSequenceStepConfigure(ADC0_BASE, 1, 0, ADC_CTL_TS| ADC_CTL_IE | ADC_CTL_END);
    //ADCHardwareOversampleConfigure(ADC0_BASE, 64);

    ADCSequenceEnable(ADC0_BASE, 1);
    ADCIntEnable(ADC0_BASE, 1);

    //  Timer (ADC Trigger)
    SysCtlPeripheralEnable(SYSCTL_PERIPH_TIMER0);
     TimerConfigure(TIMER0_BASE, TIMER_CFG_A_PERIODIC);
     TimerLoadSet(TIMER0_BASE, TIMER_A, SysCtlClockGet() / 10000); // 10KHz
     TimerControlTrigger(TIMER0_BASE, TIMER_A, true);
     TimerEnable(TIMER0_BASE, TIMER_A);

     IntEnable(INT_TIMER0A);

    IntEnable(INT_ADC0SS1);

}

void ADC0SS1IntHandler(void)
{
	TimerDisable(TIMER0_BASE, TIMER_A);
    // Ack Interrupt
    ADCIntClear(ADC0_BASE, 1);
    // Read ADC Data
    ADCSequenceDataGet(ADC0_BASE, 1, _adc);
    TempValueC = (uint32_t)(147.5 - ((75.0*3.3 *(float)_adc)) / 4096.0);
    UARTprintf("Temperature = %3d*C: ", TempValueC);
   TimerEnable(TIMER0_BASE, TIMER_A);

}

void InitConsole(void)
{

    SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOA);

    GPIOPinConfigure(GPIO_PA0_U0RX);
    GPIOPinConfigure(GPIO_PA1_U0TX);

    SysCtlPeripheralEnable(SYSCTL_PERIPH_UART0);

    //
    // Use the internal 16MHz oscillator as the UART clock source.
    //
    UARTClockSourceSet(UART0_BASE, UART_CLOCK_PIOSC);

    GPIOPinTypeUART(GPIO_PORTA_BASE, GPIO_PIN_0 | GPIO_PIN_1);

    UARTStdioConfig(0, 9600, 16000000);

}


void main(){

	InitConsole();
	ADCInit();
	// Clock (80MHz)
	    SysCtlClockSet(SYSCTL_SYSDIV_2_5| SYSCTL_USE_PLL | SYSCTL_XTAL_16MHZ | SYSCTL_OSC_MAIN);

    IntMasterEnable();

	while(1){

	}
}

  • Hello FL9,

    If there is no Timer Interrupt Handler then why enable the Timer Interrupt in the first place.

    IntEnable(INT_TIMER0A);

    What is the value is the ADC returning?

    Also as it has been shown that putting the UARTprintf in the interrupt handler is not a good idea due to the delay it takes. Also I guess that the string length being sent over UART would exceed the time taken v/s the ADC conversion.

    Regards
    Amit
  • The value in the TempValueC is always 147. I need a timer interrupt or not? i want to operate ADC of this mikrocontroller at 10ksps rate. What i do wrong?

    The Values in the ADC returning:

    #define PART_TM4C123GH6PM
    
    #include <stdint.h>
    #include <stdbool.h>
    #include "stdlib.h"
    #include "inc/hw_ints.h"
    #include "inc/hw_memmap.h"
    #include "inc/hw_uart.h"
    #include "inc/hw_timer.h"
    #include "inc/hw_gpio.h"
    #include "inc/hw_pwm.h"
    #include "inc/hw_types.h"
    #include "driverlib/adc.h"
    #include "driverlib/timer.h"
    #include "driverlib/gpio.h"
    #include "driverlib/timer.h"
    #include "driverlib/interrupt.h"
    #include "driverlib/pin_map.h"
    #include "driverlib/rom.h"
    #include "driverlib/rom_map.h"
    #include "driverlib/sysctl.h"
    #include "driverlib/uart.h"
    #include "driverlib/udma.h"
    #include "driverlib/pwm.h"
    #include "driverlib/ssi.h"
    #include "driverlib/systick.h"
    #include "driverlib/adc.h"
    #include "utils/uartstdio.h"
    #include "utils/uartstdio.c"
    #include <string.h>
    
    uint32_t _adc;
    uint8_t TempValueC;
    
    void ADCInit(void)
    {
        // ADC
        SysCtlPeripheralEnable(SYSCTL_PERIPH_ADC0);
        SysCtlDelay(3);
        //  GPIO (ADC Pins)
        //SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOD);
        ADCSequenceConfigure(ADC0_BASE, 1, ADC_TRIGGER_TIMER, 0);
        ADCSequenceStepConfigure(ADC0_BASE, 1, 0, ADC_CTL_TS| ADC_CTL_IE | ADC_CTL_END);
        //ADCHardwareOversampleConfigure(ADC0_BASE, 64);
    
        ADCSequenceEnable(ADC0_BASE, 1);
        ADCIntEnable(ADC0_BASE, 1);
    
        //  Timer (ADC Trigger)
        SysCtlPeripheralEnable(SYSCTL_PERIPH_TIMER0);
         TimerConfigure(TIMER0_BASE, TIMER_CFG_A_PERIODIC);
         TimerLoadSet(TIMER0_BASE, TIMER_A, SysCtlClockGet() / 10000); // 10KHz
         TimerControlTrigger(TIMER0_BASE, TIMER_A, true);
         TimerEnable(TIMER0_BASE, TIMER_A);
    
        IntEnable(INT_TIMER0A);
    
        IntEnable(INT_ADC0SS1);
        ADCIntEnable(ADC0_BASE, 1);
    
    }
    
    void ADC0SS1IntHandler(void)
    {
    	TimerDisable(TIMER0_BASE, TIMER_A);
        // Ack Interrupt
        ADCIntClear(ADC0_BASE, 1);
        // Read ADC Data
        ADCSequenceDataGet(ADC0_BASE, 1, _adc);
        TempValueC = (uint32_t)(147.5 - ((75.0*3.3 *(float)_adc)) / 4096.0);
    
       TimerEnable(TIMER0_BASE, TIMER_A);
    
    }
    
    void Timer0IntHandler(void)
    {
    
    	TimerIntClear(TIMER0_BASE, TIMER_TIMA_TIMEOUT);
    
    }
    
    void InitConsole(void){
    	 SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOA);
    
    	    GPIOPinConfigure(GPIO_PA0_U0RX);
    	    GPIOPinConfigure(GPIO_PA1_U0TX);
    
    	    SysCtlPeripheralEnable(SYSCTL_PERIPH_UART0);
    
    	    //
    	    // Use the internal 16MHz oscillator as the UART clock source.
    	    //
    	    UARTClockSourceSet(UART0_BASE, UART_CLOCK_PIOSC);
    
    	    GPIOPinTypeUART(GPIO_PORTA_BASE, GPIO_PIN_0 | GPIO_PIN_1);
    
    	    UARTStdioConfig(0, 9600, 16000000);
    
    }
    
    void main(){
    
    	InitConsole();
    	ADCInit();
    	// Clock (80MHz)
    	    SysCtlClockSet(SYSCTL_SYSDIV_2_5| SYSCTL_USE_PLL | SYSCTL_XTAL_16MHZ | SYSCTL_OSC_MAIN);
    
        IntMasterEnable();
    
    	while(1){
    		UARTCharPut(UART0_BASE, TempValueC);
    		//UARTprintf("Temperature = %4d*C: ", TempValueC);
    	}
    }

  • the value in the ADC returning is 0. what is wrong in my code?
  • Hello FL9,

    Can you check the following example code?

    D:\ti\TivaWare_C_Series-2.1.2.111\examples\peripherals\adc\temperature_sensor.c

    This code removes the Timer from the picture and focuses on the Temp Sense

    Regards
    Amit
  • I have tested the following example code.

    D:\ti\TivaWare_C_Series-2.1.2.111\examples\peripherals\adc\temperature_sensor.c

    It works and provides correct values. But I want to operate adc of this microcontroller at (for example) 10ksps rate. I m really confused how to set the sampling rate.

  • Hello FL9

    Your approach of using the Timer is nothing wrong and is valid. However there are a few things you need to understand

    1. The Baud Rate of 9600bps is too low for any valuable data on the Console v/s the 10KSPS.
    2. The timer interrupt enable is not required nor the Disable and Enable of the timer in the interrupt handler. When the timer is enabled to trigger the ADC, it will do so w/o any CPU intervention.

    When doing the debug, if you put a break point in the Interrupt Handler does it halt the CPU?

    Regards
    Amit
  • I have deleted UART and Timer Interrupt Handler from my Code and startup_css.c. I am watching the values in debug mode. The Value in ADC is always 0. I am missing something. I want to understand how to modify the sampling rate. Please help me.

    #include <stdint.h>
    #include <stdbool.h>
    #include <math.h>
    
    #include "inc/tm4c123gh6pm.h"
    #include "inc/hw_memmap.h"
    #include "inc/hw_types.h"
    #include "driverlib/sysctl.h"
    #include "driverlib/interrupt.h"
    #include "driverlib/gpio.h"
    #include "driverlib/timer.h"
    #include "driverlib/adc.h"
    #include "driverlib/fpu.h"
    #include "driverlib/pin_map.h"
    
    uint32_t ui32ADC0Value;
    volatile uint32_t TempValueC;
    
    int main(void)
    {
        //Set processor @ 32 MHz.
        SysCtlClockSet(SYSCTL_SYSDIV_2_5|SYSCTL_USE_PLL|SYSCTL_XTAL_16MHZ|SYSCTL_OSC_MAIN);
    
    //===============================================================================================
    
    
        //ADC pins
    
        SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOD);
    
        //Timer for 10 kHz calc and adc trigger
        SysCtlPeripheralEnable(SYSCTL_PERIPH_TIMER0);
    
        //ADC 0
        SysCtlPeripheralEnable(SYSCTL_PERIPH_ADC0);
    
        SysCtlDelay(10);
    
    //===============================================================================================
        //Peripheral configuration
    
        //Config Timer0: 16 kHz
        TimerConfigure(TIMER0_BASE, TIMER_CFG_PERIODIC);    //32 bit mode
        TimerLoadSet(TIMER0_BASE, TIMER_A, 2000-1);         //load period
        TimerControlTrigger(TIMER0_BASE, TIMER_A, true);    //ADC trigger
    
        //Configure ADC0
        ADCSequenceDisable(ADC0_BASE, 1);
       // GPIOPinTypeADC(GPIO_PORTD_BASE, GPIO_PIN_3);
    
        ADCSequenceConfigure(ADC0_BASE, 1, ADC_TRIGGER_TIMER, 0); //sequencer 1, proccessor trig, priority zero highest
    
        ADCSequenceStepConfigure(ADC0_BASE, 1, 0, ADC_CTL_TS|ADC_CTL_IE|ADC_CTL_END);  //final step: give int, stop
    
        IntEnable(INT_ADC0SS1);
        ADCIntClear(ADC0_BASE, 1);
        ADCIntEnable(ADC0_BASE, 1);
    
    //===============================================================================================
        //Enable the peripherals one by one
    
        //Int master enable
        IntMasterEnable();
    
        //ADC
        ADCSequenceEnable(ADC0_BASE, 1);
    
        //Timer0: Calc & ADC trigger
          TimerEnable(TIMER0_BASE, TIMER_A);
    //===============================================================================================
        while(1)
        {
        	TempValueC = (uint32_t)(147.5 - ((75.0*3.3 *(float)ui32ADC0Value)) / 4096.0);
        	//TempValueC= ((1475 * 1023) - (2250 * ui32ADC0Value)) / 10230;
        }
    }
    //===============================================================================================
    
    //================================================================================================
    void ADC0SS1IntHandler(void)
    {
        ADCIntClear(ADC0_BASE, 1);
        ADCSequenceDataGet(ADC0_BASE, 1, ui32ADC0Value);
    }
    //==================================================================================================