|
|
View previous topic :: View next topic |
Author |
Message |
Nathan Meyer Guest
|
PIC12F675 with timer0 and 32.7Khz cyrstal |
Posted: Tue Feb 04, 2003 2:21 pm |
|
|
I am using a PIC12F675 part in a battery pack, so I want it to comsume as little power as possible. So I am trying to run it using a 32.7Khz cyrstal and run it in LP mode. I am using the timer0 to toggle an output pin that will vary in duty cycle as the program runs. With the LP mode and the crystal and the timer0 set up in my program, the output will not function correctly, it will either turn the pin high or low and stay there. I have tried changing the program so that the timer0 is not used and I just manually toggle the output pin and this works fine. I have also, changed the code to have INTRC instead of LP with the timer0 and that will run fine. Here is the code, any suggestions? I am using ver. 3.129
#include "12f675.h"
#use delay(clock=32700)
#fuses LP,PUT,BROWNOUT,WDT,NOMCLR
#use fast_io(A)
#define vbat PIN_A0
#define isns PIN_A1
#define soc PIN_A2
#define on PIN_A3
#define caplo 0
#define caphi 1
#define mult 120
#define multd 129
long on_time,capacity=0,sum,prod,design_cap=3200,percent,crnt,voltage;
char loop,count;
#int_timer0
timer0_isr()
{
restart_wdt();
percent=((capacity*11)/design_cap);
on_time=percent*233;
count=count+1;
if(!loop)
{
if(on_time==0)
{
loop=0;
count=count+1;
}
else
{
output_high(soc);
set_timer0((2560-on_time)/10);
loop=1;
}
}
else
{
if(on_time>=2500)
loop=1;
else
{
output_low(soc);
set_timer0(on_time/10);
loop=0;
}
}
}
////////////////////////////////////////////////////////
void main()
{
setup_adc_ports(AN0_ANALOG && AN1_ANALOG);
setup_adc(ADC_CLOCK_DIV_2);
setup_vref(false);
set_timer0(0);
port_b_pullups(false);
setup_counters(RTCC_INTERNAL,WDT_2304MS);
//setup_timer_0(RTCC_DIV_2);
setup_timer_1(T1_DISABLED);
setup_comparator(FALSE);
enable_interrupts(INT_TIMER0);
enable_interrupts(global);
set_tris_a(0b00101011);
loop=0;
count=0;
sum=0;
prod=0;
capacity=600;
while (true)
{
set_adc_channel(0);
delay_us(100);
restart_wdt();
voltage=read_adc();
set_adc_channel(1);
delay_us(100);
restart_wdt();
crnt=read_adc();
//if(voltage<=174&&crnt<=4)
//capacity=0;
if (voltage>=210&&crnt<=4&&capacity<=875)
capacity=875;
while(input(on))
{
if(count>=55)
{
count=0;
delay_us(100);
restart_wdt();
voltage=read_adc();
set_adc_channel(1);
delay_us(100);
restart_wdt();
crnt=read_adc();
delay_us(100);
restart_wdt();
sum=crnt*mult;
prod=sum+prod;
if (prod>=36000)
{
prod=prod-36000;
capacity=capacity+1;
if(capacity>=3200)
capacity=3200;
}
if(voltage>=233&&(9>=crnt>=4))
capacity=3200;
}
restart_wdt();
//write_eeprom(caplo,0x00);
//write_eeprom(caphi,0x00);
}
while(!input(on)&&crnt>4)
{
restart_wdt();
if(count>=55)
{
count=0;
set_adc_channel(0);
delay_us(100);
restart_wdt();
voltage=read_adc();
set_adc_channel(1);
delay_us(100);
restart_wdt();
crnt=read_adc();
sum=crnt*multd;
prod=sum+prod;
if(prod>=36000)
{
prod=prod-36000;
capacity=capacity-1;
if(capacity==0 || capacity>=3205)
capacity=0;
}
if(voltage<=170)
capacity=0;
}
}
}
}
___________________________
This message was ported from CCS's old forum
Original Post ID: 11278 |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
Re: PIC12F675 with timer0 and 32.7Khz cyrstal |
Posted: Tue Feb 04, 2003 6:44 pm |
|
|
:=I am using a PIC12F675 part in a battery pack, so I want it to comsume as little power as possible. So I am trying to run it using a 32.7Khz cyrstal and run it in LP mode.
:=
--------------------------------------------------------
I didn't try to solve your design problems. I just went
through your code below, and noted anything that I thought
looked wrong. There may be things that I missed.
Also, the CCS compiler may have problems with A/D and
comparator initialization. In the following post,
I said that they were apparently working OK with vs. 3.127.
The init functions may or may not still be working OK with
vs. 3.129. Just keep that in mind. To be really safe,
you should look closely at the generated code (in the .LST
file) and consult the data sheet.
<a href="http://www.pic-c.com/forum/general/posts/9522.html" TARGET="_blank">http://www.pic-c.com/forum/general/posts/9522.html</a>
:=#include "12f675.h"
:=#use delay(clock=32700)
Shouldn't this clock value really be 32768 ?
:=#fuses LP,PUT,BROWNOUT,WDT,NOMCLR
I wouldn't turn on the watchdog timer during initial
development. Do it later, after you have all the
code working. You don't want to be chasing WDT
problems while you're debugging your code.
:=
:=#use fast_io(A)
:=#define vbat PIN_A0
:=#define isns PIN_A1
:=#define soc PIN_A2
:=#define on PIN_A3
:=
:=#define caplo 0
:=#define caphi 1
:=#define mult 120
:=#define multd 129
:=
:=long on_time,capacity=0,sum,prod,design_cap=3200,percent,crnt,voltage;
If you're going to initialize variables when you declare them,
I would put them on separate lines. It's a lot easier to see
what you're doing.
:=char loop,count;
:=
:=#int_timer0
:=timer0_isr()
:={
:=
:= restart_wdt();
:= percent=((capacity*11)/design_cap);
:= on_time=percent*233;
:= count=count+1;
:= if(!loop)
:= {
:= if(on_time==0)
:= {
:= loop=0;
:= count=count+1;
:= }
:= else
:= {
:= output_high(soc);
:= set_timer0((2560-on_time)/10);
:= loop=1;
:= }
:= }
:= else
:= {
:= if(on_time>=2500)
:= loop=1;
:= else
:= {
:= output_low(soc);
:= set_timer0(on_time/10);
:= loop=0;
:= }
:= }
:=}
:=
:=////////////////////////////////////////////////////////
:=void main()
:={
:=
:= setup_adc_ports(AN0_ANALOG && AN1_ANALOG);
This declaration is not correct. The 12F675.H file
says the values must be OR'ed together (with a bitwise OR).
You're doing a logical AND.
:= setup_adc(ADC_CLOCK_DIV_2);
:= setup_vref(false);
:= set_timer0(0);
:= port_b_pullups(false);
:= setup_counters(RTCC_INTERNAL,WDT_2304MS);
:= //setup_timer_0(RTCC_DIV_2);
:= setup_timer_1(T1_DISABLED);
:= setup_comparator(FALSE);
:= enable_interrupts(INT_TIMER0);
:= enable_interrupts(global);
:=
:= set_tris_a(0b00101011);
I would do all my initialization, such as this TRIS statement,
BEFORE I enabled interrupts.
:=
:= loop=0;
:= count=0;
:= sum=0;
:= prod=0;
:= capacity=600;
:=
:=while (true)
:={
:= set_adc_channel(0);
:= delay_us(100);
:= restart_wdt();
:= voltage=read_adc();
:= set_adc_channel(1);
:= delay_us(100);
:= restart_wdt();
:= crnt=read_adc();
:= //if(voltage<=174&&crnt<=4)
:= //capacity=0;
:= if (voltage>=210&&crnt<=4&&capacity<=875)
:= capacity=875;
:= while(input(on))
:= {
:= if(count>=55)
:= {
:= count=0;
:= delay_us(100);
:= restart_wdt();
:= voltage=read_adc();
:= set_adc_channel(1);
:= delay_us(100);
:= restart_wdt();
:= crnt=read_adc();
:= delay_us(100);
:= restart_wdt();
:= sum=crnt*mult;
:= prod=sum+prod;
:= if (prod>=36000)
:= {
:= prod=prod-36000;
:= capacity=capacity+1;
:= if(capacity>=3200)
:= capacity=3200;
:= }
:= if(voltage>=233&&(9>=crnt>=4))
Is the line above using correct syntax ?
:= capacity=3200;
:= }
:= restart_wdt();
:= //write_eeprom(caplo,0x00);
:= //write_eeprom(caphi,0x00);
:= }
:= while(!input(on)&&crnt>4)
:= {
:= restart_wdt();
:= if(count>=55)
:= {
:= count=0;
:= set_adc_channel(0);
:= delay_us(100);
:= restart_wdt();
:= voltage=read_adc();
:= set_adc_channel(1);
:= delay_us(100);
:= restart_wdt();
:= crnt=read_adc();
:= sum=crnt*multd;
:= prod=sum+prod;
:= if(prod>=36000)
:= {
:= prod=prod-36000;
:= capacity=capacity-1;
:= if(capacity==0 || capacity>=3205)
:= capacity=0;
:= }
:= if(voltage<=170)
:= capacity=0;
:= }
:= }
:=
:=}
:=}
___________________________
This message was ported from CCS's old forum
Original Post ID: 11282 |
|
|
|
|
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
|