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

Convert Volts of LM35 with PIC16F877 and MAX187

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







Convert Volts of LM35 with PIC16F877 and MAX187
PostPosted: Thu Apr 06, 2006 3:11 pm     Reply with quote

Hello, I am using a PIC16F877 and I make the conversion to 12 bits by means of a MAX187. By means of a LM35, receipt the tension in mV, later to show it by display. The problem this in which to the entrance of the ADC I have the correct value, but in display this value oscillates much, and it does not give a correct value. This it is my code:



#include "C:\Program Files C\20060403_spi.h"
#include <max187.c>
#include <lcd.c>
#use fast_io (A)
#use fast_io (B)
#use fast_io (C)
#use fast_io (D)
#use fast_io (E)
#byte port_a=0X05
#byte port_b=0X06
#byte port_c=0X07
#byte port_d=0X08
#byte port_e=0X09

#ifndef MAX4534_EN

#define MAX4534_A0 PIN_A0
#define MAX4534_A1 PIN_A1
#define MAX4534_EN PIN_A2

#endif



void main()
{
float temperatura;
setup_adc_ports(NO_ANALOGS);
setup_adc(ADC_OFF);
setup_psp(PSP_DISABLED);
setup_spi(FALSE);
setup_timer_0(RTCC_INTERNAL|RTCC_DIV_1);
setup_timer_1(T1_DISABLED);
setup_timer_2(T2_DISABLED,0,1);
set_tris_a(0x00); //Port A as exit
set_tris_b(0x00); //Port B as exit
set_tris_c(0b11010111); //Port C as coming and goings
set_tris_d(0xFF); //RD0...RD7 exit
set_tris_e(0x00); //RE0...RE2 gate
port_b=0;

/*Init mux 4:1 MAX4534 */

port_a=0;
delay_ms(5);
output_high(MAX4534_EN);
output_high(MAX4534_A1);
output_low(MAX4534_A0);

/*Init A/D MAX187*/

init_ext_adc();
lcd_init(); //Init LCD
lcd_putc(" Digital\n"); //Extract text
lcd_putc(" Termometer"); //Extract text
delay_ms(3000);
lcd_putc("\f"); //Clean screen
lcd_putc("Temperatura\n"); //Extract text
lcd_putc("actual"); //Extract text
delay_ms(1000);
lcd_gotoxy(14,2); //Arranged cursor LCD
lcd_putc("oC");

while(1)
{
init_ext_adc();
lcd_gotoxy(8,2); //Arranged cursor LCD
lcd_putc(" "); //Clean this sector of screen
lcd_gotoxy(8,2); //Arranged cursor LCD
temperatura = read_ext_adc();
printf(lcd_putc,"%03.1f",temperatura); //xxx.x °C
delay_ms (1000);
temperatura=0;
}
}

And the code off <max187.c>, it's the same off drivers ADS8320.c CCS Compiler

//////////////// Driver for MAX187 A/D Converter ///////////////////////
//// ////
//// init_ext_adc() Call after power up ////
//// ////
//// value = read_ext_adc() Converts to digital number ////
//// and sends to MCU ////
//// ////
/////////////////////////////////////////////////////////////////////////
//// (C) Copyright 1996,2003 Custom Computer Services ////
//// This source code may only be used by licensed users of the CCS ////
//// C compiler. This source code may only be distributed to other ////
//// licensed users of the CCS C compiler. No other use, ////
//// reproduction or distribution is permitted without written ////
//// permission. Derivative programs created using this software ////
//// in object code form are not restricted in any way. ////
/////////////////////////////////////////////////////////////////////////


#ifndef MAX187_CS

#define MAX187_DOUT PIN_C4
#define MAX187_SCLK PIN_C3
#define MAX187_CS PIN_C2

#endif


void init_ext_adc() {
output_high(MAX187_CS);
output_high(MAX187_SCLK);
}


long read_ext_adc() {
int i;
long data;

data=0;
output_low(MAX187_CS);
for(i=0;i<=5;i++) // take sample and send start bit
{
output_low(MAX187_SCLK);
delay_us(1);
output_high(MAX187_SCLK);
delay_us(1);
}
for(i=0;i<8;++i) { // send sample over spi
output_low(MAX187_SCLK);
delay_us(1);
shift_left(&data,2,input(MAX187_DOUT));
output_high(MAX187_SCLK);
delay_us(1);
}

output_high(MAX187_CS);
return(data);
}

float convert_to_volts(long data) {
return ((float)data*2.5/0xffff);
}

Sorry for my basic english

Thank you,

Regards
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Thu Apr 06, 2006 3:47 pm     Reply with quote

What you have done is to take the CCS driver for the ADS8320
and then edit it to make it look as if CCS has a MAX187 driver
and then post it. That's not going to work. The two chips are
not compatible. You have to make a real driver for the MAX187.

--------
Just a notice to anyone reading this thread from Google.
The code posted above is not a valid driver for the MAX187.
It's made to look as if CCS has a driver for it. They do not.
Do not use the code posted above. It will not work.
O_R_E
Guest







MAX187
PostPosted: Wed Apr 12, 2006 9:47 am     Reply with quote

Hello,

I have modified driver of the MAX187, but what I obtain is the value multiplied by two, that is to say, the double. As I can solve it? Thanks This is the code of driver MAX187:

#ifndef MAX187_CS

#define MAX187_DOUT PIN_C4
#define MAX187_SCLK PIN_C3
#define MAX187_CS PIN_C2

#endif

void init_ext_adc() {
output_low(MAX187_CS);
output_low(MAX187_SCLK);
}

long read_ext_adc() {
int i;
long data;
data=0;
delay_us(86); //Delay 86 us, to init conversion (tCONV)
output_low(MAX187_CS);
for(i=0;i<13;++i) { // send sample over spi
output_low(MAX187_SCLK);
delay_us(1);
shift_left(&data,2,input(MAX187_DOUT));
output_high(MAX187_SCLK);
delay_us(1);

}
delay_us(10);
output_high(MAX187_CS);
return(data);
}

float convert_to_volts(long data) {
return ((float)data*5.0/0xFFFF);
}

And this is the main code:

#include "C:\Program Files C\20060405_spi.h"
#include <max187.c>
#include <lcd.c>
#use fast_io (A)
#use fast_io (B)
#use fast_io (C)
#use fast_io (D)
#use fast_io (E)
#byte port_a=0X05
#byte port_b=0X06
#byte port_c=0X07
#byte port_d=0X08
#byte port_e=0X09

#ifndef MAX4534_EN
#define MAX4534_A0 PIN_A0
#define MAX4534_A1 PIN_A1
#define MAX4534_EN PIN_A2
#endif

void main()
{
float value;
setup_adc_ports(NO_ANALOGS);
setup_adc(ADC_OFF);
setup_psp(PSP_DISABLED);
setup_spi(FALSE);
setup_timer_0(RTCC_INTERNAL|RTCC_DIV_1);
setup_timer_1(T1_DISABLED);
setup_timer_2(T2_DISABLED,0,1);
set_tris_a(0x00);
set_tris_b(0x00);
set_tris_c(0b11010111);
set_tris_d(0xFF);
set_tris_e(0x00);
port_b=0;
port_a=0;


/*Init LCD*/
lcd_init();
lcd_putc(" Digital\n");
lcd_putc(" Reference");
delay_ms(2000);
lcd_putc("\f");
lcd_putc("Value\n");
delay_ms(2000);
lcd_gotoxy(14,2);
lcd_putc("V");

while (1)
{
output_high(MAX4534_EN); //Init multiplexor MAX4534
output_low(MAX4534_A1);
output_high(MAX4534_A0);
init_ext_adc(); //Init MAX187
value = read_ext_adc();
lcd_gotoxy(8,2);
lcd_putc(" ");
lcd_gotoxy(8,2);
printf(lcd_putc,"%03.2f",value); //Tension in [Volts]
delay_ms (2000);
value=0;
}
}

Thank you
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Wed Apr 12, 2006 11:42 am     Reply with quote

Look at some sample drivers on the net. Go to http://www.google.com
and search for: MAX187 int char
That will find you some source code. Here is one of the many
links you will find:
http://www.mikrocontroller.net/attachment.php/206290/GetMAX187.C

Do you notice how their for() loop only does 12 iterations ?

You should then question why you are doing 13 iterations.

You should go to the Maxim web page here, and download the
data sheet:
http://www.maxim-ic.com/quick_view2.cfm/qv_pk/1033
It shows 12 bits.

Their appnote here, in Figure 2, shows 12 bits.
http://www.maxim-ic.com/appnotes.cfm/appnote_number/827

How did I know to look for this ? Whenever a result is "off" by a
power of 2, the most likely cause is a shift problem. Either you
shifted too much, or too little. So when you mentioned your problem
I instantly zoomed in on the loop count.
O_R_E
Guest







Conversion AD con MAX187 y PIC16F877
PostPosted: Thu Apr 13, 2006 4:26 am     Reply with quote

Hello Jdm programer,

This driver off MAX187, it's ok:

//////////////// Driver for MAX187 A/D Converter ///////////////////////
//// ////
//// init_ext_adc() Call after power up ////
//// ////
//// value = read_ext_adc() Converts to digital number ////
//// and sends to MCU ////
//// ////
/////////////////////////////////////////////////////////////////////////
//// (C) Copyright 1996,2003 Custom Computer Services ////
//// This source code may only be used by licensed users of the CCS ////
//// C compiler. This source code may only be distributed to other ////
//// licensed users of the CCS C compiler. No other use, ////
//// reproduction or distribution is permitted without written ////
//// permission. Derivative programs created using this software ////
//// in object code form are not restricted in any way. ////
/////////////////////////////////////////////////////////////////////////

#ifndef MAX187_CS

#define MAX187_DOUT PIN_C4
#define MAX187_SCLK PIN_C3
#define MAX187_CS PIN_C2

#endif

void init_ext_adc() {
output_low(MAX187_CS);
output_low(MAX187_SCLK);
}

long read_ext_adc() {
int i;
long data;
data=0;
delay_us(86); //Espero 86 us, para iniciar la conversion (tCONV)
output_low(MAX187_CS);
for(i=0;i<12;++i) { // send sample over spi
output_low(MAX187_SCLK);
delay_us(1);
shift_left(&data,2,input(MAX187_DOUT));
output_high(MAX187_SCLK);
delay_us(1);

}
delay_us(10);
output_high(MAX187_CS);
return(data);
}

float convert_to_volts(long data) {
return ((float)data*2.5/0xFFFF);
}
The problem was in the curl, that is of 13 clocks. The paragraph of datasheet had confused me that says in page 15:

1. Use a general-purpose I/O line on the CPU to pull CS
low. Keep SCLK low.
2. Wait the for the maximum conversion time specified
before activating SCLK. Alternatively, look for a
DOUT rising edge to determine the end of
conversion.
3. Activate SCLK for a minimum of 13 clock.

Thanks
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