CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to support@ccsinfo.com

ADC Basics

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
Jan



Joined: 30 Aug 2016
Posts: 5

View user's profile Send private message

ADC Basics
PostPosted: Tue Sep 13, 2016 2:38 am     Reply with quote

Hi guys,

I have a problem reading my ADC channels. One of the first things I do in my Main function is to call a InitHardware-function where I do the following:

Code:

setup_oscillator(OSC_16MHZ);
   
setup_vref(VREF_ON | VREF_ADC_1v024);
setup_adc_ports(sAN0);   
setup_adc_ports(sAN2 | VSS_FVR);
setup_adc_ports(sAN3 | VSS_FVR);
SETUP_ADC(ADC_CLOCK_DIV_16);


After the InitHardware-function there is a while(1) loop where I read the different ADC channels. I do this as follows:

Code:

set_adc_channel(ADCchannel);
delay_us(10);
ADCval = read_adc();


The problem is that it seems that sAN2 and sAN3 don't use fixed voltage reference. Instead they use VDD as voltage reference.
As you can see I don't call setup_adc_ports() or SETUP_ADC() in while(1) anymore. I only set the channel, wait a bit and then read the ADC. Is this procedure incorrect?

I have a PIC12F1840 and am using PCM Version 4.132.

Thanks for your help!

Regards,
Jan
RF_Developer



Joined: 07 Feb 2011
Posts: 839

View user's profile Send private message

PostPosted: Tue Sep 13, 2016 4:22 am     Reply with quote

There should only be one setup_adc_ports(). In your code, only the last one is being used, and as it is wrong, the wrong reference is being used.

You cannot easily use different references with different channels. Select one reference and use it for all channels. You need to OR the channels together in setup_adc_ports(), and put the vref as a second parameter:

Code:

   setup_vref(VREF_ON | VREF_ADC_1v024);
   setup_adc_ports(sAN0 | sAN2 | sAN3, VSS_FVR);
   setup_adc(ADC_CLOCK_DIV_16);


Your ADC conversion code, in the while loop, looks fine. For most applications you could reduce the delay to about 5us. It doesn't have to be a delay: if there's something else the processor could be usefully doing, such as processing a previous ADC reading, then that's fine, as long as it takes long enough.
Jan



Joined: 30 Aug 2016
Posts: 5

View user's profile Send private message

PostPosted: Tue Sep 13, 2016 4:59 am     Reply with quote

Hi RF-Developer,

thanks a lot for your fast support. You said there is no easy way to use different references with different channels. Is there a hard way? And if yes, how do I have to implement it?

Thank you!
Ttelmah



Joined: 11 Mar 2010
Posts: 19369

View user's profile Send private message

PostPosted: Tue Sep 13, 2016 7:23 am     Reply with quote

Beware, that what you are trying to do, is not legal.....

Table 30-8 of the data sheet
"PIC12(L)F1840 A/D CONVERTER (ADC) CHARACTERISTICS:"

Line AD06 - minimum Reference voltage 1.8v

Note 5 below the table:

"5: FVR voltage selected must be 2.048V or 4.096V."

The ADC does not support operating off 1.024v.

In your post, you only use one reference.
Code:

setup_oscillator(OSC_16MHZ);
   
setup_vref(VREF_ON | VREF_ADC_2v048); //minimum allowed
setup_adc_ports(sAN0 | sAN2 | sAN3 | VSS_FVR);   
//sets up the ADC to use the 2.048v reference, and support channels
//0, 2 & 3.
SETUP_ADC(ADC_CLOCK_DIV_16);
set_adc_channel(0);

//etc...


The 1.024 output, is for other peripherals like the DAC, not the ADC.
Jan



Joined: 30 Aug 2016
Posts: 5

View user's profile Send private message

PostPosted: Wed Sep 14, 2016 12:21 am     Reply with quote

Thanks for the hint. I immediately changed it. But is there a way to use different voltage references with different channels?
Ttelmah



Joined: 11 Mar 2010
Posts: 19369

View user's profile Send private message

PostPosted: Wed Sep 14, 2016 12:55 am     Reply with quote

You have to reprogram the ADC to the new settings. Allow time for it to settle (this takes longer than just the Tacq, and will depend on the impedance of your Vref source).

Beware though. If (for instance) you have a (say) 2v reference selected, then the ADC inputs are not allowed to go significantly above this. If you have other channels that you are going to sample with (for example) a 3v reference, you may run into problems from this.

Honestly seems very complex. The normal best way is to choose a reference that is just above the highest voltage you want to use with the ADC, get it as accurate and stable as you can (bandgap reference), and work from this.
temtronic



Joined: 01 Jul 2010
Posts: 9174
Location: Greensville,Ontario

View user's profile Send private message

PostPosted: Wed Sep 14, 2016 5:35 am     Reply with quote

Mr T's last statement sums it up. Old school is to have a 'signal conditioning' board between the sensors and the computer. This allows every sensor to be 'conditioned' to send the ADC the best range for it.
If you set the ADC up for say 5 volts max, and a pressure sensor only maxes out at .1 volt ,then the signal conditioning board would amplify that .1 to become 5.
As well , the board typically provides protection as well as stabile power to the sensors.

Jay
Ttelmah



Joined: 11 Mar 2010
Posts: 19369

View user's profile Send private message

PostPosted: Wed Sep 14, 2016 6:27 am     Reply with quote

A very important point. A lot of people forget 'signal pre-processing', and this can be vital.

Have one system here where the full scale of the sensor is just on 60mV, and the impedance is very high. This is being read by a PIC using a 2.5v reference, and some good quality instrumentation op-amps provide the buffering, offset and gain needed.
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group