View previous topic :: View next topic |
Author |
Message |
njepsen
Joined: 13 Aug 2007 Posts: 469
|
Posted: Fri Nov 20, 2015 1:47 am Post subject: RTC loses its way |
|
|
I have a problem with a RTC which from time to time, (no pun intended) suddenly loses 6 moths if I run a particular subroutine.
Here is the code snippets which works OK, and has been reliable for a year or more.
Code: |
'*******************************************************************************
$regfile = "m1284pdef.dat" 'my processor
$crystal = 9830400 'system crystal
$framesize = 800 ' Located at top of 16k of SRAM
$hwstack = 250 '
$swstack = 250 '
$frameprotect = 1
'various dim statements are here
'we want to set up counter 1 to toggle 1x per sec
Dim Timer1preset As Long 'therefor prescale = 65536 - 39062.5 = 26473
Config Timer1 = timer , Prescale = 1024 'counts 9830400/1024 = 9600 per sec
'timer preset = 65536 - 9600 = 55936
Config Clock = User
Config Date = Dmy , Separator = /
Timer1preset = 55936
$baud = 9600
Open "com1:" For Binary As #3
Config Serialin = Buffered , Size = 200 , Cts = Pind.4 , Rts = Pind.7 , Threshold_full = 30 , Threshold_empty = 30
Config Serialout = Buffered , Size = 250
'*************************************************************
'main loop is here
do
code
call housekeeping() ' this gets called often
code
code
loop
'*************************************************************
sub housekeeping()
'This sub increments the local RTC
'No interrupts are used
'The 'A compare' is set to zero and the compare flag tifr1.OCF1A
'goes high when counter1 = 0, which happens every 1 sec
'Sub takes about 5uSec
ocr1aH = 0 'set compare hi byte to 0
ocr1al = 0 'set compare lo byte to 0
if tifr1.OCF1A = 1 then 'Timer Int Flag Register. Compare with 0 is true
timer1 = 55936
tifr1.OCF1A = 1 'reset bit 1. see pg140 of atmega 1284 data sheet
if mytimeoutb_sec > 0 then Decr mytimeoutb_sec '1 sec used in timer loops
incr local_sec
time$ = time(local_sec) 'calculate time & update RTC This could be moved also
' date$ = date(local_sec) 'calculate date & update RTC moved to main loop
end if
end sub
'*******************************************************************
|
This next piece of code looks for 32 numbers from a noise meter, which is on a ser port #3. If the loop runs once,
then there is no problem.
BUT if the loop runs 5 times because the noise meter is turned off for example,
then during this loop, the date$ and time$ values go back to February 2015.
Code: |
#If enable_thirds = 1
Retries = 0
msg_id = 99
do
incr retries
call timedelay_ms(100)
Print #3 , "XC1;" 'meter preset
call timedelay_ms(100)
Print #3 , "XW2;" 'meter preset
call timedelay_ms(100)
Print #3 , "BL8 , 32;" 'ask meter for 32 1/3rd octave values
call receive_meter_RS232(32)
Loop Until Retries > 5 Or Msg_id = 0
#endif
'*******************************************************************************
|
here are the two subs that are called from the problem sub. Code: |
'***********************************************
Sub Timedelay_ms(byval Mydelay As Integer)
'delay in ms
'does not need timer1
local dly as integer
dly = 0
While dly < Mydelay
call housekeeping()
waitms 1
Incr dly
Reset Watchdog
Wend
End Sub
'******************************************************************************
'*******************************************************************************
sub Receive_meter_RS232(byval targetcommacountint as integer)
Mytimeoutb_sec = 20 '20 secs
Msg_id = 99
Commacounti = 0
charcount = Temph 'restore pointer
do
rxbyte = inkey(#3)
If Rxbyte = 32 Then Rxbyte = 0
If Rxbyte = 10 Then Rxbyte = 0
If Rxbyte = 13 Then
Rxbyte = 44
Incr Commacounti
End If
If Rxbyte <> 0 Then
Incr Charcount 'used when writing to sd card
Bigbuffer(charcount) = Rxbyte 'store my data in buffer
End If
Reset Watchdog
call housekeeping()
If Commacounti = Targetcommacountint Then
Msg_id = 0
Print #1 , ""
Print #1 , ">> expected " ; Targetcommacountint ; ",got " ; Commacounti 'print target & actual
clearmeter
exit sub 'this is the normal exit from this sub
end if
Loop Until Mytimeoutb_sec = 0
tempstr1 = ">> wrong comma count.Target = " + str(Targetcommacountint) + ",got " + str(Commacounti)
print #1 , tempstr1
'back up the pointer
while charcount > temph
decr Charcount
wend
'
end sub
'****************************************************************************** |
(BASCOM-AVR version : 2.0.7.7 , Latest : 2.0.7.8 ) _________________ Neil |
|
Back to top |
|
|
enniom
Joined: 20 Oct 2009 Posts: 537
|
Posted: Fri Nov 20, 2015 3:48 am Post subject: |
|
|
1. Can you be sure that Charcount is always within the dimensioned value of Bigbuffer?
2. What is clearmeter? |
|
Back to top |
|
|
njepsen
Joined: 13 Aug 2007 Posts: 469
|
Posted: Fri Nov 20, 2015 4:02 am Post subject: |
|
|
Bigbuffer is dimensioned to 10,000 bytes and elsewhere in the code, its size is checked
& the pointer reset to 1. (this has never happened )
here is clearmeter
Code: |
'******************************************************************************
sub clearmeter() 'clear out meter tx buffer
'clear meter serial port buffer
mytimeoutb_sec = 3
Do
Rxbyte = Inkey(#3)
Print #1 , "W" ;
Reset Watchdog
call timedelay_ms(2)
Loop Until Ischarwaiting(#3) = 0 or mytimeoutb_sec = 0
end sub
'****************************************************************************** |
_________________ Neil |
|
Back to top |
|
|
enniom
Joined: 20 Oct 2009 Posts: 537
|
Posted: Fri Nov 20, 2015 4:39 am Post subject: |
|
|
Only other thought.
Code: | while charcount > temph
decr Charcount
wend |
Is it possible that this can assign a value of 0 or roll-under to 65535 (I assume Charcount is a Word to accommodate the 10,000-byte buffer size)? |
|
Back to top |
|
|
MWS
Joined: 22 Aug 2009 Posts: 2262
|
Posted: Fri Nov 20, 2015 7:17 am Post subject: |
|
|
enniom wrote: | Code: | while charcount > temph
decr Charcount
wend |
Is it possible that this can assign a value of 0 or roll-under to 65535 (I assume Charcount is a Word to accommodate the 10,000-byte buffer size)? |
That's only an odd and cycle-intensive way of writing:
|
|
Back to top |
|
|
enniom
Joined: 20 Oct 2009 Posts: 537
|
Posted: Fri Nov 20, 2015 1:02 pm Post subject: |
|
|
Hi Neil,
You use $Frameprotect.
Are you passing variables in subroutines used in ISRs?
If so, could these be overrunning the $Framesize? |
|
Back to top |
|
|
njepsen
Joined: 13 Aug 2007 Posts: 469
|
Posted: Wed Nov 25, 2015 3:39 am Post subject: |
|
|
Hi enniom,
Thanks for taking time to look at this. I think You mean - am I passing variables in subs that are also used in ISRs?
The answer is no.
I only have 3 IRSs. Timer rollover for T0,T1 and T3, and the serial ports. I have included the timer ISRs below.
T0 simply flashes a LED, T2 is the RTC, and T3 calls a sub that checks a flag.
The problem with this bug is I can wallpaper over it so it doesnt happen, but I dont know what is causing it.
Code: |
'*****************************************************************************
sub timer3overflow()
'T3 rolls over every 5 seconds
'ttrn is checked every 30 seconds
timer3 = 17536 '65536 - 9600x5
call check TTRN ' time to read noise
end sub
'***********************************************
sub Timer0overflow()
'called 37 x per second
'flashes LED once per sec
$asm
push r24 ;save r24
in r24, sreg ;r24<-sreg
push r24 ;save status register to stack
lds r24, {btimer0} ;load direct
inc r24
cpi r24,37 ;compare
brlo timer0overflo ;br if r24 < 37
clr r24 ;clear r24
sbi heartbeat_pin,heartbeat_bit ; write 1 to pin = toggle led
timer0overflo:
sts {btimer0},r24 ;store btimer0 <- r24
pop r24
out sreg , r24 'get Sregister back
pop r24
$end asm
end sub
'********************************************************************************
'*****************************************************************************
sub Check_ttrn()
'is it TTRN (time to read noise).
'This sub called once every 5 sec under interrupt of timer3
'Dn5 lets it happen only once per 15 min
'TTRN is latched in this sub and unlatched when data is sent
'dn5 = a semiphore bit called 'done5'
if dn5 = 0 then
If _min = 0 Or _min = 15 Or _min = 30 Or _min = 45 Then
Dn5 = 1
Ttrn = 1 'time to read noise
Print #1 , ">> time to read noise"
End If
else
If _min <> 0 and _min <> 15 and _min <> 30 and _min <> 45 and ttrn = 0 Then
Dn5 = 0
end if
end if
end sub
'*****************************************************************************
* |
_________________ Neil |
|
Back to top |
|
|
|
|
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 You cannot attach files in this forum You cannot download files in this forum
|
|