Skip to main content
Visitor II
June 27, 2012
Question

Problem with STM8S103 ADC

  • June 27, 2012
  • 2 replies
  • 736 views
Posted on June 27, 2012 at 05:08

I am using STM8S103 to measure three channels of voltage signals named vs12, vs5 and vs3 respectively. Timer 4 is enabled to generate interrupt every 10ms and three voltage signals are measured alternately. That is, in the 1st 10ms interrupt, vs12 is measured. In the 2nd 10ms interrupt, vs5 is measured. In the 3rd 10ms interrupt, vs3 is measured, and so on. During each measurement, mcu makes 16 captures for further average processing. The measurement result will be displayed in HyperTerminal via UART.

The problem is that when only 1 channel (vs12, vs5, or vs3) is enabled, the measurement is correct. But when two channels are enabled, both channels' measurements are wrong. Could anyone have a look at the following code and give me some suggestions?

The C code is described as follows.

main()

{

      ADC1->CR1 |= (ADC1_CR1_SPSEL & (0x02<<4)); //fADC = 4 MHz

      ADC1->CR2 |= ADC1_CR2_ALIGN; //right aligment

     

     while(1){

           // select the ADC channel

           if (vs_sel==0){

ADC1->CSR |= (ADC1_CSR_CH & CH_VS12);

} else if (vs_sel==1){

ADC1->CSR |= (ADC1_CSR_CH & CH_VS5);

}

    }

}

Timer 4 Interrupt:

@far @interrupt void irq_system_tim4_ovf (void)

{

 // If MAX NO OF SAMPLES are taken then voltage

// values will not be recorded in array vs12_arr

no_of_sample_vals = 0;

while( no_of_sample_vals < MAX_NO_SAMPLE_VAL )

{                                            

//start ADC

ADC1->CR1 |= ADC1_CR1_ADON; //ADC powered up

ADC1->CR1 |= ADC1_CR1_ADON; //begin conversion

//check for the EOC

while (!(ADC1->CSR & ADC1_CSR_EOC)){}; 

//must read LSBs first

if (vs_sel==0){

vs12_arr[no_of_sample_vals] = ADC1->DRL;

vs12_arr[no_of_sample_vals] |= ADC1->DRH << 8;

} else if (vs_sel==1){

vs5_arr[no_of_sample_vals] = ADC1->DRL;

vs5_arr[no_of_sample_vals] |= ADC1->DRH << 8;

}

//ADC powered down

ADC1->CR1 |= ~ADC1_CR1_ADON;

no_of_sample_vals++;

}

// Update the time counter

flag_10ms = 1;

if (t_10ms==100){  /* 1 sec is completed */

 flag_1sec = 1;

t_10ms = 0;

}

t_10ms++;

vs_sel++;

if (vs_sel==3) vs_sel = 0;

// Clear the flag

    TIM4->SR1 &=~(0x01);

    return;

}

    This topic has been closed for replies.

    2 replies

    tangsgAuthor
    Visitor II
    June 27, 2012
    Posted on June 27, 2012 at 06:04

    Solved. Can anyone find the root cause? hah

    Visitor II
    June 27, 2012
    Posted on June 27, 2012 at 21:59

    So what was the problem then? :)