|
|
View previous topic :: View next topic |
Author |
Message |
jubilee Guest
|
Ex_pulse using timer 1? |
Posted: Thu Oct 16, 2003 8:50 pm |
|
|
hey all
i have problems using timer1 to time a pulse of aorund 10 to 11 HZ freq.
Questions is how long could timer 1 time?
isnt it: 65535 cycles before overflows
each cycle is : fosc/4
=20M/4 =5Mhz which is 200 n seconds
#include <16F872.h>
#fuses HS,NOWDT,NOPROTECT
#use delay(clock=20000000)
#use rs232(baud=9600, xmit=PIN_C6, rcv=PIN_C7) // Jumpers: 8 to 11, 7 to 12
void wait_for_low_to_high() {
while(input(PIN_B1)) ; /* if it's high, wait for a low */
delay_us(3); /* account for fall time */
while(!input(PIN_B1)); /* wait for signal to go high */
}
void wait_for_low() {
delay_us(3); /* account for rise time */
while(input(PIN_B1)); /* wait for signal to go high */
}
main() {
long time;
float newtime;
setup_timer_1(T1_INTERNAL); // Start timer 1
setup_counters( RTCC_INTERNAL, RTCC_DIV_256);
while (TRUE)
{
printf("\n\rWaiting...\n\r");
wait_for_low_to_high();
set_timer1(0);
wait_for_low();
wait_for_low_to_high();
time = get_timer1();
delay_ms(100);
newtime = time *0.0000512 ;
printf(" counter : %8lu\n\n\r", time);
// printf("period : %4x\n\n\r", newtime);
printf("time in us : %8f\n\n\r", newtime);
}
out put i get at hypoerterminal is rubbish , why?
Quote: |
Waiting...
‹23437500000000000000��000000000000000.0000€
Waiting...
time in us : -67790�time in us : -67790� counter : 000 |
|
|
|
wedilo
Joined: 16 Sep 2003 Posts: 71 Location: Moers, Germany
|
Re: Ex_pulse using timer 1? |
Posted: Fri Oct 17, 2003 1:51 am |
|
|
Hello,
you need an isr that should be called every 100ms or so?
No problem,
The timer will increment every 1.6us at 20MHz
An instruction (here one increment) need 4 machine cycles
So calculate: 20e6 / 4 / T1_DIV_BY_8 = 625000 increments a second
You need only 625000 / 10 = 62500 increments
So then initialize the timer1 as follows:
Code: |
setup_timer1(T1_INTERNAL | T1_DIV_BY_8)
long lTemp=65536-62500 // Important, because timer always counts UP !!
set_timer1(lTemp)
enable_interups(INT_TIMER1)
#INT_TIMER1
isr_Test {
// Will be called very 100ms
}
|
I hope the calculation is correct and the code will work. Please, try it out...
73 Sven |
|
|
jubilee Guest
|
Thanks wedilo |
Posted: Mon Oct 20, 2003 5:02 am |
|
|
try that timer 1 thing .
but varies it .. as in not using an interrupt to time 1 sec.
instead using timer1 to time a period . |
|
|
Ttelmah Guest
|
Re: Thanks wedilo |
Posted: Mon Oct 20, 2003 10:34 am |
|
|
jubilee wrote: | try that timer 1 thing .
but varies it .. as in not using an interrupt to time 1 sec.
instead using timer1 to time a period . |
Try something like this:
1) setup Timer1, as:
setup_timer_1(T1_INTERNAL ! T1_DIV_BY_8); // Start timer 1
2) Poll for the rising edge.
while(input(PIN_B1));
while(!input(PIN_B1));
//Remember you only want to clear this _on_ the edge.
set_timer1(0L);
Now the timer will start on the rising edge. You should not really need to add a delay, since there will be one involved in setting the registers, and also the 'low' transition, will allready be at quite a low level (depending on the nature of the input).
Note also, that if you immediately just poll for low, the test will fall straight through, if the signal is allready low. I suspect this is the first reason why your current code is giving unexpected results.
The second reason, is that the timer, may well be wrapping. The count interval is 5MHz, with the /1 prescaler, and if you are timing a pulse that is 0.1 seconds wide, the count will then reach 500000, involving the timer in having wrapped over seven times. The /8 prescaler, should (just) handle a pulse width up to 0.1048 seconds.
Now you talk about the 'frequency' of a pulse. Inherently, a pulse does not have a 'frequency', but only a period. If you want the frequency (how often the pulse repeats), you will need to wait for the next rising edge. If however you just want the pulse width, then you should wait for the falling edge. I will assume the latter.
while(input(PIN_B1);
time=get_timer1();
printf(" counter : %lu\r\n",time);
printf("time in us : %6.1f\r\n",(float)time*0.625);
Beware, that depending what emulation mode you are in, HyperTerminal, may ignore 'newline' codes, unless they are preceeded by a carriage return.
Best Wishes |
|
|
|
|
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
|