#rem TERMINAL OUTPUT:
Mode= 1 Overhead= +3573 us
Test1:Maths Algorithm= +5775 us
Test2:EEPROM Table= +3365 us
Test3 Direct BITS= +7077 us
Check= +5 us
PRODUCED BY CODE SNIPPET :
#endrem
; Program to Estimate the Execution speed of most M2 PICaxe Instructions
; AllyCat, 2012, Updated August 2019
#picaxe 08m2 ; Or any other M2 but *CANNOT USE THE SIMULATOR*
#terminal 4800 ; 4800 baud at setfreq m4 (*Also X2s require SFR changes*)
; *Select MODE here* ; MODE 1 = Number of PIC Instruction cycles (= time in us)
symbol MODE = 1 ; MODE 2 = Measure times with Setfreq M16 (up to 64,000 us)
; MODE 3 = Calculate 4MHz execution times up to 255.99ms
symbol TMR1L = $16 ; Timer 1 Low byte SFR address
symbol TMR1H = $17 ; Timer 1 High byte SFR address
symbol T1CON = $18 ; Control Register: Prescaler = %--nn---- (PS = 2^nn)
symbol tempb = b23 ; or s_w4 Temporary byte for MODE3, etc.
symbol exec = w12 ; or s_w5 16-bit execution cycles or time
symbol nul = w13 ; or s_w6 Overhead for Call/Return,etc.with no instructions
main:
do
nul = 0
sertxd(cr,lf,"Mode= ",#MODE)
sertxd(" Overhead=")
gosub start ; Start the NUL measurement
gosub measure ; Shows and Returns timer value in us or ms
nul = exec ; Store for subsequent calculations
gosub runtests ;* Update any of the target code as required *
sertxd(cr,lf,"Check=") ; Re-measure the NUL (or another) value
gosub start
gosub measure
if exec > 50 then
sertxd(" ***") ; Mark inaccurate nul result
endif
sertxd(cr,lf)
pause 5000
loop
end
runtests:
sertxd(cr,lf,"Test1:Maths Algorithm=") ; Report the second test, etc.
w0 = %01101001
gosub start
w0 = b0 * 16 | b0 & $0F0F
w0 = w0 * 4 | w0 & $3333
w0 = w0 * 2 | w0 & $5555
w0 = w0 * 2 | w0 ; = 30 bytes
gosub measure
sertxd(cr,lf,"Test2:EEPROM Table=")
w0 = %01101001
symbol base = 10
data base,(0,3,$0C,$0F,$30,$33,$3C,$3F,$C0,$C3,$CC,$CF,$F0,$F3,$FC,$FF)
gosub start
b1 = b0 ** 4096 + base ; Maybe faster than / 16
b0 = b0 and 15 + base
read b0,b0
read b1,b1 ; = 14 bytes
gosub measure
sertxd(cr,lf,"Test3 Direct BITS=")
w0 = %01101001
gosub start
bit15 = bit7 : bit14 = bit7
bit13 = bit6 : bit12 = bit6
bit11 = bit5 : bit10 = bit5
bit9 = bit4 : bit8 = bit4
bit7 = bit3 : bit6 = bit3
bit5 = bit2 : bit4 = bit2
bit3 = bit1 : bit2 = bit1
bit1 = bit0 ; = 35 bytes
gosub measure
return
; REQUIRED SUBROUTINES
start: ; Setup the Mode and Reset Timer 0
tempb = MODE ; At least one variable is needed in IF.THEN
if tempb > 1 then
setfreq m16 ; For modes 2 and 3
pause 100 ;* 25 ms to allow 20 ms timer to update *
endif
peeksfr T1CON,tempb
pokesfr T1CON,0 ; Stop the timer
pokesfr TMR1H,0 ; Clear High byte
pokesfr TMR1L,0
pokesfr T1CON,tempb ; Restore the timer (1 / 33 at 4 / 16 MHz)
return
measure: ; Reads Timer 0, calculates and displays timed delay
pokesfr T1CON,0 ; Stop the timer to read both bytes
peeksfr TMR1L,tempb ; Read Low byte (S_W variables only words)
peeksfr TMR1H,exec ; Read High byte
pokesfr T1CON,1 ; Restart timer (can ignore frequency)
exec = exec * 256 + tempb ; Allows use of S_W variable
exec = exec - nul ; Estimate execution time of target code
setfreq m4 ; Ensure serial comms are at default again
if exec > 64000 then ; Correctly display negative values (near zero)
sertxd(" -")
exec = - exec
else
sertxd(" +")
endif
tempb = MODE
if tempb < 3 then ; Check the MODE
sertxd (#exec," us ")
else ; Display in ms to 2 decimal places
tempb = exec ** 26214 / 100 ; *4/10 = 26214 / 65536 then /100
sertxd(#tempb,".") ; Units of ms
tempb = exec ** 26214 // 100 / 10
sertxd(#tempb) ; Tenths of ms
tempb = exec ** 26214 // 10
sertxd(#tempb," ms") ; Hundredths of ms
endif
return