See PIC16F87/88 Data Sheet:
TIMER1 MODULE /Timer1 Counter Operation
Circuit to extract the 60Hz clock from the power line:
http://www.maxim-ic.com/appnotes.cfm...te_number/1994
Luciano
See PIC16F87/88 Data Sheet:
TIMER1 MODULE /Timer1 Counter Operation
Circuit to extract the 60Hz clock from the power line:
http://www.maxim-ic.com/appnotes.cfm...te_number/1994
Luciano
If I'm reading correctly what I'm seeing, tmr1 counts backwards?
tmr1 starts at $FFFF (65535) and overflows at $0000 (0) So if I need to set a flag every 21600 pulses, I need to preload the counter, or start the counter, at $AB9F (43935) and count down to 0 from there?
No, the Timer Count UP from $0000 to $FFFF and then sets a flag (or interrupt) as it rolls from $FFFF (maximum count) and starts again from $0000.
Have a look at this thread for presetting a 10mS example.
http://www.picbasic.co.uk/forum/showthread.php?t=632
SetTimer:
T1CON.0=0 ' Stop the Clock
TMR1RunOn.Highbyte=TMR1H ' Load the Run-On (Over-Run) value (if any)
TMR1RunOn.Lowbyte=TMR1L
TMR1RunOn=TMR1Preset+TMR1RunOn ' Calculate the New (adjusted) value for TMR1
If TMR1CalAR=0 then ' Calibration ADVANCE (add) or RETARD (subtract)
TMR1RunOn=TMR1RunOn+TMR1Cal
else
TMR1RunOn=TMR1RunOn-TMR1Cal
endif
TMR1H=TMR1RunOn.Highbyte ' Save new values to TMR1
TMR1L=TMR1RunOn.Lowbyte
T1CON.0=1 ' Restart the Clock
PIR1.0=0 ' Reset TMR1's Interupt Flag
Return
Ok, code killing aside.... forgive my noobness.
If I strip out the calibration aspect as I dont think i need it. (1sec/60hz = 1 pulse every 16.667ms) should be enough time.....
SetTimer:
T1CON.0=0 ' Stop the Clock
TMR1.Highbyte=TMR1H ' Load the high timer start point
TMR1.Lowbyte=TMR1L ' Load the low timer start point
TMR1.Highbyte= $AB ' Save new values to TMR1 (65535 - 21600 = 43935 = AB9F)
TMR1.Lowbyte= $9F
T1CON.0=1 ' Restart the Clock
PIR1.0=0 ' Reset TMR1's Interupt Flag
Return
This should reset the timer everytime with 43935 as a starting point, leaving 21600 pulses until a rollover and the interupt flag is set, upon which the program needs to increment a counter by 1, store the result in eeprom and reset the counter to start again. Oh, and increment the display aswell ;-)
Last edited by jmgelba; - 12th April 2005 at 21:08.
Hmmm... don't quite understand your figures...
1/60=16667uS = $411B based on 1uS tick time (4MHz clock)
$0000-$411B=$BEE5
Use Microsofts Calculator in Scientific mode... you cant do 0-411B in hex directly, so instead do FFFF-411B and just add 1 to your answer.
Setting the clock for a 16667uS count would be...
T1CON.0=0 ' Stop the Clock
TMR1H=$BE ' Set Timer Highbyte
TMR1L=$E5 ' Set Timer Lowbyte
T1CON.1=1 ' Restart the Clock
PIR1.0=0 ' Reset TMR1's Interrupt Flag
If you're returning from an Interrupt then use RESUME otherwise if it's from a subroutine use RETURN.
You may have to adjust the $E5 value slightly to trim your time accurately to account for instruction cycle time in setting the clock etc.
Melanie,
I think we have our wires crossed a little.
Are you setting up the timer to count internal pulses? I am trying to count a 60hz 50% duty cycle pulse from the mains supply. When I've counted 21600 of them, I want the counter to reset, send a increment to a counter, and start again.
Therefore, I dont understand why we need to measure 16.67ms. This is the period between highs at the i/p. Time really has nothing to do with it, we just need to get to 21600 and say, ok, im done, reset me please :-)
So thats why I have the numbers in there that I do. Start the counter at 43935, when we've counted 21600 pulses we should be at 65535. The next pulse will set the interupt, and we start again. Well, start the timer at 43936 I guess.
65535 = $FFFF
43935 = $AB9F
21600 = $5460
65535 - 21600 = 43935
According to Microsoft's calculator.
Thanks for the tidbit on the resume command.
Disclaimer:- I know you're not stupid, so the natural conclusion is that I must be LOL. Thanks for your help Mel.
No, it's my fault... not reading the thread properly from the beginning...
What I told you was valid for the timer keeping it's own time...
But, nevertheless if you want the Timer to count 21600 (or however many) pulses from an external source then yes, it's 65536-21600=43936, or $ABA0 that needs to be preset into TMR1H & TMR1L. Note I'm subtracting from 65536 ($0000 or zero) and not from 65535 ($FFFF), because the interrupt is on the roll from 65535 ($FFFF) to 65536 ($0000).
Look at the T1CON Register for your PIC... you will also have to set TMR1CS for EXTERNAL input and provide your 60Hz pulses on the appropriate T1CKI pin for your PIC.
Bookmarks