I am trying to create a software pwm using 1 or 2 timers.
One timer:
Code: Select all
sub procedure Timer3Int org $22
'When TMR3 matches PR3 this interrupt is executed and TMR3 is cleared
T3CON.15 = 0 'T3 stopped
if LATD.8 = 1 then
'If softscale_duty = softscale_period then LATD.8 remains high for another softscale_period
if softscale_duty <> softscale_period then
LATD.8 = 0
PR3 = softscale_period - softscale_duty 'low period
end if
else
'If softscale_duty = 0 then LATD.8 remains low for another softscale_period
if softscale_duty <> 0 then
LATD.8 = 1
PR3 = softscale_duty 'high period
end if
end if
IFS0.7 = 0 'Clear T3IF
TMR3 = 0
T3CON.15 = 1 'T3 started
end sub
Code: Select all
sub procedure Timer4Int org $3E
'When TMR4 matches PR4 this interrupt is executed and TMR4 is cleared.
'LATD.8 is high when entering this routine.
'If softscale_duty = softscale_period then LATD.8 remains high for another softscale_period
if softscale_duty <> softscale_period then
LATD.8 = 0
T4CON.15 = 0 'T4 stopped
PR5 = softscale_period - softscale_duty 'low period
TMR5 = 0
T5CON.15 = 1 'T5 started
end if
IFS1.5 = 0 'Clear T4IF
end sub
sub procedure Timer5Int org $40
'When TMR5 matches PR5 this interrupt is executed and TMR5 is cleared.
'LATD.8 is low when entering this routine.
'If softscale_duty = 0 then LATD.8 remains low for another softscale_period
if softscale_duty <> 0 then
LATD.8 = 1
T5CON.15 = 0 'T5 stopped
PR4 = softscale_duty 'high period
TMR4 = 0
T4CON.15 = 1 'T4 started
end if
IFS1.6 = 0 'Clear T5IF
end sub
There are of course lost clockcycles due to interrupt latency
and interrupt code.
My goal is to achieve that LATD.8 low period + high period
equals softscale_period+1
Which approach would give the best result?
What is the number of lost cycles (so I can compensate
the PR values to achieve my goal) ?
Any better approach (without using output compare)?
regards peter