147 lines
3.3 KiB
NASM
147 lines
3.3 KiB
NASM
|
|
|
|
|
|
; Utils_WaitNanoSecs waittime_in_ns , cyles_already_used , waitcount_register
|
|
;
|
|
; cycles already used will be subtracted from the delay
|
|
; the waittime resolution is 1 cycle (delay from exact to +1 cycle)
|
|
; the maximum delay at 20MHz (50ns/clock) is 38350ns
|
|
; waitcount register must specify an immediate register
|
|
; taken from https://www.mikrocontroller.net/articles/AVR_Assembler_Makros#Verz%C3%B6gerung_um_X_Nanosekunden
|
|
;
|
|
.set Osc_Hz = clock ; 1 MHz
|
|
.set cycle_time_ns = (1000000000 / Osc_Hz) ; clock duration
|
|
.macro Utils_WaitNanoSecs
|
|
.set cycles = ((@0 + cycle_time_ns - 1) / cycle_time_ns - @1)
|
|
.if (cycles > (255 * 3 + 2))
|
|
.error "MACRO Utils_WaitNanoSecs - too many cycles to burn"
|
|
.else
|
|
.if (cycles > 6)
|
|
.set loop_cycles = (cycles / 3)
|
|
ldi @2,loop_cycles
|
|
dec @2
|
|
brne pc-1
|
|
.set cycles = (cycles - (loop_cycles * 3))
|
|
.endif
|
|
.if (cycles > 0)
|
|
.if (cycles & 4)
|
|
rjmp pc+1
|
|
rjmp pc+1
|
|
.endif
|
|
.if (cycles & 2)
|
|
rjmp pc+1
|
|
.endif
|
|
.if (cycles & 1)
|
|
nop
|
|
.endif
|
|
.endif
|
|
.endif
|
|
.endmacro
|
|
|
|
|
|
|
|
|
|
|
|
; ***************************************************************************
|
|
; Utils_FillSram
|
|
;
|
|
; IN:
|
|
; - x: pointer to SRAM to fill
|
|
; - r16: value to fill the SRAM with
|
|
; - r17: size of area to fill
|
|
; OUT:
|
|
; - nothing
|
|
; MODIFIED REGISTERS: r17, x
|
|
|
|
Utils_FillSram:
|
|
tst r17
|
|
breq Utils_FillSram_end
|
|
|
|
Utils_FillSram_loop:
|
|
st x+, r16
|
|
dec r17
|
|
brne Utils_FillSram_loop
|
|
Utils_FillSram_end:
|
|
ret
|
|
|
|
|
|
|
|
; ***************************************************************************
|
|
; Increment a 32 bit counter at the address given by X.
|
|
; IN:
|
|
; - X: Address of the 4 byte counter (1. byte is LSB)
|
|
; OUT:
|
|
; - nothing
|
|
; MODIFIED REGISTERS: r18, r19, r20, r21, 22
|
|
|
|
Utils_IncrementCounter32:
|
|
ld r18, x+
|
|
ld r19, x+
|
|
ld r20, x+
|
|
ld r21, x
|
|
clr r22
|
|
inc r18
|
|
adc r19, r22
|
|
adc r20, r22
|
|
adc r21, r22
|
|
st x, r21
|
|
st -x, r20
|
|
st -x, r19
|
|
st -x, r18
|
|
ret
|
|
|
|
|
|
|
|
|
|
; ***************************************************************************
|
|
; Utils_ReadEeprom
|
|
;
|
|
; Read a byte from EEPROM (see example in ATtiny24/44/84 manual p.19).
|
|
;
|
|
; IN:
|
|
; - X: EEPROM Address to read from
|
|
; OUT:
|
|
; - R16: byte read
|
|
; MODIFIED REGISTERS: R16
|
|
|
|
Utils_ReadEeprom:
|
|
sbic EECR, EEPE ; wait for previous write to complete (if any)
|
|
rjmp Utils_ReadEeprom
|
|
out EEARH, xh ; set EEPROM address
|
|
out EEARL, xl
|
|
sbi EECR, EERE ; start EEPROM read by writing EERE
|
|
in r16, EEDR ; read data from data register
|
|
ret
|
|
|
|
|
|
|
|
; ***************************************************************************
|
|
; Utils_WriteEeprom
|
|
;
|
|
; Write a byte to EEPROM (see example in ATtiny24/44/84 manual p.18).
|
|
;
|
|
; IN:
|
|
; - R16: byte to write
|
|
; - X: EEPROM Address to read from
|
|
; OUT:
|
|
; - nothing
|
|
; MODIFIED REGISTERS: R17
|
|
|
|
Utils_WriteEeprom:
|
|
sbic EECR, EEPE ; wait for previous write to complete (if any)
|
|
rjmp Utils_WriteEeprom
|
|
ldi r17, (0<<EEPM1) | (0<<EEPM0) ; set programming mode
|
|
out EECR, r17
|
|
out EEARH, xh ; set EEPROM address
|
|
out EEARL, xl
|
|
out EEDR, r16 ; write data to data register
|
|
sbi EECR, EEMPE ; write logical one to EEMPE
|
|
sbi EECR, EEPE ; start EEPROM write by setting EEPE
|
|
ret
|
|
|
|
|
|
|
|
|
|
|
|
|