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 CCS Technical Support

PIC18LF45K80 ADC problem

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



Joined: 19 May 2010
Posts: 13

View user's profile Send private message

PIC18LF45K80 ADC problem
PostPosted: Fri Feb 22, 2013 3:36 pm     Reply with quote

I need help with the ADC of a PIC18LF45K80, which Microchip has created an errata related to it.
The problem is that the results of the conversion do not match the input voltage and overall the behavior is not consistent (or linear) with changes in the input signal.

Code:

/****************************************************************************************************/
/*  ADC configuration                                                                               */
/*  Channels 0, 1, & 2 for sensor IC #1                                                    */
/*  Channels 5, 6, & 7 for sensor IC #2                                                    */
/*  Reference voltage Vref+ set from channel 3 at +3.3V; Vref- set to AVss                          */
/*  Analog Negative channel is 00 (AVss)                                                            */
/*  AD result is right justified                                                                    */
/*  AD acquisition time set to 20 TAD; AD conversion clock set at Fosc/64                           */
/****************************************************************************************************/
#byte           ADCON0      =   0xfc2           // AD Converter Control Register 0
#byte           ADCON1      =   0xfc1           // AD Converter Control Register 1
#byte           ADCON2      =   0xfc0           // AD Converter Control Register 2
#byte           ANCON0      =   0xf5d           // AD Converter Port Configuration Register 0
#byte           ANCON1      =   0xf5c           // AD Converter Port Configuration Register 1
#byte           ADRESH      =   0xfc4           // AD Converter Result High Byte Register
#byte           ADRESL      =   0xfc3           // AD Converter Result Low Byte Register
#define         ADCSET1         0x00            // ADC Setup for ADCON0
#define         ADCSET2         0x10            // ADC Setup for ADCON1
#define         ADCSET3         0xbe            // ADC Setup for ADCON2
#define         ADCSET4_1       0x0f            // ADC Setup for ANCON0 with 3 channels active
#define         ADCSET4_2       0xef            // ADC Setup for ANCON0 with 6 channels active
#define         ADCSET5         0x00            // ADC Setup for ANCON1
#bit            ADON        =   ADCON0.0        // ADC on/off bit
#bit            ADGO        =   ADCON0.1        // ADC start conversion bit; conversion flag
#bit            CHS0        =   ADCON0.2        // ADC channel selection bits for conversion
#bit            CHS1        =   ADCON0.3
#bit            CHS2        =   ADCON0.4
#bit            CHS3        =   ADCON0.5
#bit            CHS4        =   ADCON0.6
#bit            VCFG0       =   ADCON1.4        // ADC Vref+ selection bits for conversion
#bit            VCFG1       =   ADCON1.5

void device_config(void){

    SCS0    =   0;                                      // Setup primary oscillator
    SCS1    =   0;

    TXSTA1  =   TXCOM1;                                 // Setup UART1
    RCSTA1  =   RXCOM1;
    SPBRG1  =   BRCOM1;
    BAUDCON1 =  BRSCOM1;

    set_tris_a(0x2f);                                   // RA6, RA7 OSC; rest inputs
    set_tris_b(0xc0);                                   // High address port, inputs; rest outputs
    port_b_pullups(TRUE);                               // Enable pull-ups for high address port
    set_tris_c(0x81);                                   // xBEE_TX, SOSC0 inputs; rest outputs
    set_tris_d(0xFF);                                   // All inputs
    port_d_pullups(TRUE);                               // Enable pull-ups for Address port
    #ifdef USES_MAG2
        set_tris_e(0x0F);                               // ADC inputs for second magnetic IC
    #else
        set_tris_e(0x08);
    #endif
//lastRXchar = RCREG1;

    ANCON0  =   ADCSET4_1;                              // Setup of ADC
    #ifdef USES_MAG2
    ANCON0  =   ADCSET4_2;
    #endif
    ANCON1  =   ADCSET5;
    ADCON0  =   ADCSET1;
    ADCON1  =   ADCSET2;
    ADCON2  =   ADCSET3;
   
    T1CON   =   TMR1SET;                                // Setup Timer1
    set_timer1(TMR1VAL_5SEC);                           // Start Timer1
}

void measure_voltage(void){

    unsigned int16  ADCresult, ADCdata;
    unsigned int8   i;

    ADON    =   ON;                                     // Enable ADC
    CHS0 = 0;                                           // Vdd core as ADC input
    CHS1 = 0;
    CHS2 = 0;
    CHS3 = 0;
    CHS4 = 0;
    ADCdata = 0;
    for( i = 0; i < 4; i++){
        delay_us(50);
        ADGO    =   ON;                                 // Start sampling
        while(ADGO);                                    // Wait until conversion is finish   
        ADCresult = ADRESH << 8;
        ADCresult += ADRESL;
        ADCdata += ADCresult;
    }
    ADON    =   OFF;                                    // Disable ADC
    sensor_state.voltage = (ADCdata >> 2);              // Average 4 samples

}


Before I change microcontroller I want to review if anything can be done to get the ADC working correctly.
Thank you.
gpsmikey



Joined: 16 Nov 2010
Posts: 588
Location: Kirkland, WA

View user's profile Send private message

PostPosted: Sat Feb 23, 2013 1:41 am     Reply with quote

I have not used that one, but often times, strange readings show up when either there is noise on the input or the input impedance is too high. Make sure the input impedance is low enough compared to the data sheet for that chip. One quick test for noise is - do you get the same (wrong) readings each time for a given input voltage or does it wander around for a given input voltage (which would tend to indicate noise problems) ?
_________________
mikey
-- you can't have too many gadgets or too much disk space !
old engineering saying: 1+1 = 3 for sufficiently large values of 1 or small values of 3
Ttelmah



Joined: 11 Mar 2010
Posts: 19496

View user's profile Send private message

PostPosted: Sat Feb 23, 2013 2:28 am     Reply with quote

1) Use the CCS functions.
2) The problems with the ADC on this chip, mean that it works 'OK' if you accept it as a 10bit ADC, but with a bit of offset (this comes down to applying a calibration). No point in fiddling round with the ADC code, just divide the results by 4, and store an offset calibration value for the chip (take a reading of a known voltage, and store this, then use this to give the offset required).
3) If you do have to go 'DIY', then use the compiler functions to help. Make16, is several instructions more efficient than rotating and adding, to form a 16bit value. etc..
4) As a comment, looking at the code, you are selecting an external Vref. Have you got this connected?.

Best Wishes
FCP



Joined: 19 May 2010
Posts: 13

View user's profile Send private message

PostPosted: Mon Feb 25, 2013 9:10 am     Reply with quote

Hi,

Thank you for your comments.
I do have the reference voltage present and is constant, it comes form a +3.3V charge pump IC. Which I will use for the base value to get the offset voltage for adjusting the reading.
As for having a 10-bit data, we selected this particular device because of the 12-bit ADC, so I either make it "work" or change the device and add an external ADC.
Ttelmah



Joined: 11 Mar 2010
Posts: 19496

View user's profile Send private message

PostPosted: Mon Feb 25, 2013 10:03 am     Reply with quote

As it stands it won't give a reliable 12bit ADC. Lesson is to read the errata when selecting a part.
Talk to Microchip. Ask explicitly how long it will be before a fixed version is available. You may well find they have engineering samples already, since this is a 'major' failure on the chip.
There are other chips like the 67J93, which have a fully working 12bit ADC. It has a couple of minor issues with the MSSP, but otherwise is 99% 'bug free'. You might see if this has the other features you want.

Best Wishes
FCP



Joined: 19 May 2010
Posts: 13

View user's profile Send private message

PostPosted: Mon Feb 25, 2013 3:30 pm     Reply with quote

Hi,

On the IC selection side, I had no input, right now I am trying to fix the issues that the design has.
So far, I have been able to correct the issues with the data conversion up to satisfactory levels.
Nevertheless, I still need to get the actual supply voltage to the IC to judge when the voltage coming into the system is no longer having the adequate level.
Thank you.
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