In diesem Paket ist eine provisorische Umgehung dieses Problems enthalten: rolfslcdtreiber.tar.gz
(die aufgeteilten Blöcke der hex-Datei werden noch mit falschen Adressen modifiziert um avrdude zu überlisten)
Versucht man eine hex-Datei von mehr als 64KB zu speichern erhält man einen Fehler. Wenn man jetzt die grosse hex-Datei auf mehrere jeweils maximal 64KB grosse Teile aufteilt und diese einzeln brennt (wobei man nur bei der 1. den Flash zuvor löscht), dann scheint es korrekt zu funktionieren. Aber das stimmt nicht! Denn beim zurücklesen passiert der selbe Fehler nochmals. Offenbar wird der zweite und vierte 64KB Block innerhalb des Flash-Speichers jeweils vertauscht geschrieben. Und beim zurücklesen wird ebenfalls der zweite und vierte Block vertauscht.
Man muss also innerhalb des Microkontroller-Programms überprüfen ob die Daten an der richtigen Stelle gespeichert wurden.
Hier ein entsprechendes einfaches Assemblerprogramm:
;; flashcheck.asm
;; checking flash memory
;; Hardware: mk3 board with myAVRstamp256 (Atmega2560)
;; connected LEDs at PORTL and PORTB
.include "m2560def.inc"
main: ldi r16, low(RAMEND)
ldi r17, high(RAMEND)
out SPL, r16
out SPH, r17
ldi r16, 0xFF
sts DDRL, r16 ;whole PORTL as output
out DDRB, r16 ;whole PORTB as output
mainloop:
; ldi r16, 1
ldi r16, 0x06 ;Number "1" for 7 segment display on MK3 board
out PORTB, r16 ;Number 1 at PORTB
call subroutine1
sts PORTL, r16 ;Result of subroutine1 at PORTL
rcall wait ;wait about 1 sec
; ldi r16, 2
ldi r16, 0x5B ;Number "2" for 7 segment display on MK3 board
out PORTB, r16 ;Number 2 at PORTB
call subroutine2
sts PORTL, r16 ;Result of subroutine2 at PORTL
rcall wait ;wait about 1 sec
; ldi r16, 3
ldi r16, 0x4F ;Number "3" for 7 segment display on MK3 board
out PORTB, r16 ;Number 3 at PORTB
call subroutine3
sts PORTL, r16 ;Result of subroutine3 at PORTL
rcall wait ;wait about 1 sec
; ldi r16, 4
ldi r16, 0x66 ;Number "4" for 7 segment display on MK3 board
out PORTB, r16 ;Number 4 at PORTB
call subroutine4
sts PORTL, r16 ;Result of subroutine4 at PORTL
rcall wait
rcall wait
rcall wait ;wait about 3 sec
rjmp mainloop
wait: ; waiting subroutine
push r24 ; save registers on stack
push r25
push r16
ldi r16, 150 ; counter for outer loop
w1: ldi r24, low(-32000) ; r25:r24 as 16 bit counter for inner loop
ldi r25, high(-32000)
w2: adiw r24, 1 ; r25:r24 incrementing
brne w2 ; branch if not zero
dec r16
brne w1 ; outer loop
pop r16 ; restore registers from stack
pop r25
pop r24
ret
subroutine1: ;first subroutine at low flash address
ldi r16, 0x11
ret
.org 0x8000
subroutine2: ;2. subroutine above 64KB
ldi r16, 0x22
ret
.org 0x10000
subroutine3: ;3. subroutine above 128KB
ldi r16, 0x33
ret
.org 0x18000
subroutine4: ;4. subroutine above 192KB
ldi r16, 0x44
ret
Wenn man die ".org" Befehle weglässt, dann funktioniert es korrekt.
Es werden der Reihe nach die Zahlen 1 bis 4 auf dem 7-Segment-Display angezeigt und gleichzeitig der entsprechende Rückgabewert
von der jeweiligen Subroutine auf den PORTL-LEDs angezeigt.