View previous topic :: View next topic |
Author |
Message |
hemnath
Joined: 03 Oct 2012 Posts: 242 Location: chennai
|
problem with timer |
Posted: Wed Nov 21, 2012 4:40 am |
|
|
I'm using 18F2520 and internal oscillator 4MHz. i'm displaying the count in LCD for every 1ms. But it is not working with 1ms interrupt. Please help Code: | #include "18F2520.h"
#include <f2520_regs.h>
#fuses INTRC_IO
#use delay(clock=4000000)
#define RS PIN_A2
#define EN PIN_A1
void lcd_cmd(unsigned char);
void lcd_data(unsigned char);
void T0_init();
void lcd_init();
unsigned int16 temp=0;
void main()
{
TRISA = 0x00;
LATA = 0x00;
TRISB = 0x00;
LATB = 0x00;
T0CON = 0x01; // Prescaler= 1:4, 16-bit mode, Internal Clock
lcd_init();
while(1)
{
T0_init();
lcd_cmd(0x80);
printf(lcd_data,"%LU",temp);
}
}
void T0_init()
{
TMR0H = 0xF6; // Values calculated for 1 millisecond delay with 4MHz crystal
TMR0L = 0x3B;
TMR0ON = 1; // Timer0 On
while(TMR0IF == 0); // Wait until TMR0IF gets flagged
temp++;
TMR0ON = 0; // Timer0 Off
TMR0IF = 0; // Clear Timer0 interrupt flag
}
void lcd_init()
{
lcd_cmd(0x30); // Configure the LCD in 8-bit mode, 1 line and 5x7 font
lcd_cmd(0x0C); // Display On and Cursor Off
lcd_cmd(0x01); // Clear display screen
lcd_cmd(0x06); // Increment cursor
lcd_cmd(0x80); // Set cursor position to 1st line, 1st column
}
void lcd_cmd(unsigned char c)
{
output_b (c);
output_low(RS);
output_high (EN);
delay_ms (10);
output_low (EN);
}
void lcd_data(unsigned char z)
{
output_b(z);
output_high(RS);
output_high(EN);
delay_ms(10);
output_low(EN);
}
|
|
|
|
Mike Walne
Joined: 19 Feb 2004 Posts: 1785 Location: Boston Spa UK
|
|
Posted: Wed Nov 21, 2012 5:13 am |
|
|
Quote: | But it is not working with 1ms interrupt. Please help |
Please be more specific.
What's not working?
What are you expecting to happen?
Explain what is wrong.
Mike |
|
|
hemnath
Joined: 03 Oct 2012 Posts: 242 Location: chennai
|
|
Posted: Wed Nov 21, 2012 5:32 am |
|
|
I'm trying to increment a variable "temp" for every 1ms. But it's not happening. For one second, temp should be incremented upto 1000 counts. Is it correct? |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9221 Location: Greensville,Ontario
|
|
Posted: Wed Nov 21, 2012 6:39 am |
|
|
One problem that no one here can answer is 'What is the refresh rate of your LCD module ?' Can it really update at a 1ms rate ?
The easy test is to get rid or your T0_init() function and replace it with the CCS equal delay_ms(1).Far simpler code and it works for what you want..a simple inline delay within your main loop.You're not using ISRs..at least not in the normal way...
Also you should use the CCS supplied functions.We know they work and are easy to see what 'configuration' you are trying to achieve.Directly setting ports and registers is usually done in assembler and again CCS has done a LOT of work to make your life easier!
hth
jay |
|
|
Mike Walne
Joined: 19 Feb 2004 Posts: 1785 Location: Boston Spa UK
|
|
Posted: Wed Nov 21, 2012 7:43 am |
|
|
Quote: | For one second, temp should be incremented upto 1000 counts. Is it correct? | Yes, of course it is.
But most LCD displays can't update at ms rates.
Do as temtronic suggests.
Cut your code to the minimum, find out haw fast you can update, then you may have starting point.
Mike |
|
|
hemnath
Joined: 03 Oct 2012 Posts: 242 Location: chennai
|
|
Posted: Wed Nov 21, 2012 8:00 am |
|
|
I have cut the code and it is very simple..Increments variable i and display for every 1 ms . it increments as 0,1,2,3.....etc as normally. But it increments only 10 counts for a second.
i'm using 4 MHZ internal oscillator.
Code: | void main()
{
lcd_init();
while(1)
{
for(i=0;i<=1000;i++)
{
lcd_cmd(0x80);
delay_ms(1);
printf(lcd_data,"%5LU",i);
}
}
} |
|
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19499
|
|
Posted: Wed Nov 21, 2012 8:11 am |
|
|
Seriously, 'of course'.
Typically LCD's take perhaps 40mSec to 'clear', and at least 20uSec to accept a character (though this will not be seen, most update the actual display at less than 10*/second). Printing 5 digits from a counter, will involve four divisions by 10 (320uSec each), and four subtractions (4uSec each), plus outputting each character to the LCD.
There is no problem at all in having your chip count mSec, but there is ' no way' of displaying these on an LCD as they count, or seeing them (how fast can you 'see' something - think about the fact that movies only typically update at 24* per second). Also though you need to be using a hardware timer to count in mSec. Using a delay in a loop is never going to work. The loop also takes time....
Study a digital stopwatch. Even the ones that show only 1/100th second counts, don't show these as they count, but just a blurred digit. The actual 'value' only shows when you stop the watch.
Best Wsihes |
|
|
|