Forum: Mikrocontroller und Digitale Elektronik mega64 Bootloader schreibt nur erste Seite.


von Christoph S. (mcseven)


Lesenswert?

Hi*,

habe mir einen BL angepaßt, aber der schreibt nur die erste Seite.
Bei größeren Adressen als 254 werden nur xFFFF Bytes zurückgelesen.
Ich vermute, es liegt am ASM-Teil, aber daran hatte ich nichts geändert.
BL-Größe ist 4k, also keine RWW-Sektion.
Weiß jemand, wo der Fehler liegt?
1
/*
2
register unsigned int Pagedata @2;
3
register unsigned int PageAddress @4;
4
register unsigned int CurrentAddress @6;
5
register unsigned char k @8;
6
register char spmcrval @10;
7
*/
8
9
//rx_buffer[0]-[1] = PageNumber --> PageAdress
10
//rx_buffer[2]-[257] = PageData
11
12
for (i=0;i<256;i+=2) {
13
  Pagedata=rx_buffer1[i+2]+(rx_buffer1[i+3]<<8);
14
  while (SPMCR&1); //wait for spm complete
15
  CurrentAddress=(PageAddress*256)+i; 
16
  spmcrval=1;
17
  #asm 
18
  movw r30, r6;       //move CurrentAddress to Z pointer   
19
  mov r1, r3;         //move Pagedata MSB reg 1
20
  mov r0, r2;         //move Pagedata LSB reg 1  
21
  sts SpmcrAddr, r10; //move spmcrval to SPM control register
22
  spm;                //store program memory
23
  #endasm
24
}    
25
26
while (SPMCR&1);    //wait for spm complete
27
spmcrval=3;         //erase page
28
#asm 
29
movw r30, r4;       //move PageAddress to Z pointer
30
sts SpmcrAddr, r10; //move spmcrval to SPM control register              
31
spm;                //erase page
32
#endasm
33
34
while (SPMCR&1);    //wait for spm complete
35
spmcrval=5;         //write page
36
#asm 
37
movw r30, r4;       //move PageAddress to Z pointer
38
sts SpmcrAddr, r10; //move spmcrval to SPM control register              
39
spm;                //write page
40
#endasm
41
while (SPMCR&1);    // wait for spm complete
42
spmcrval=0x11;      // enableRWW  see mega8 datasheet for explanation
43
                    // P. 212 Section "Prevent reading the RWW section
44
                    // during self-programming
45
#asm 
46
sts SpmcrAddr, r10; //move spmcrval to SPMCR              
47
spm;
48
#endasm
49
50
for (j=0;j<256;j+=2) {
51
  CurrentAddress=(PageAddress*256)+j; 
52
  #asm
53
  movw r30, r6; //move  CurrentAddress to Z pointer  
54
  lpm r2, Z+;   //read LSB
55
  lpm r3, Z;    //read MSB
56
  #endasm    
57
  Checkdata = rx_buffer1[j+2] +(rx_buffer1[j+3]<<8);
58
  // PAGEDATA HAS BEEN FILLED BY ASM PART ABOVE!
59
  // Verify schlägt ab PageNumber 1 / CurrentAddress=256 fehl,
60
  // es werden immer 0xFFFF zurückgelesen.
61
  if (Pagedata != Checkdata) { 
62
    //ERROR
63
  }
64
}

Danke,
Christoph

von 2921 (Gast)


Lesenswert?

Wie ich mich erinnere, muss man nach dem Schreiben die Seite jeweils 
wieder freigeben.

von Christoph S. (mcseven)


Lesenswert?

Hi,

danke für Deine Antwort, aber das Problem war simpel:
AVR Bootloading geht vereinfacht so:
1. Seite in den Flash füttern
2. Adresse eingeben, wo diese Seite hinsoll
3. Diese seite löschen
4. Den Speichervorgang anstoßen
5. Optional RWW aktivieren, bei 4k BL aber sowieso irrelevant

Da der Z-Pointer nur ein Byte groß ist, kann ich auch nur 256 Seiten 
speichern. Für den Mega64 reicht das, da sinds sogar noch weniger, weil 
ja der BL noch 4k haben will. Ich hatte nur vergessen, aus meiner 
Seitennummer in INT (000-255) ein BYTE zu machen, welches in den 
Z-Pointer kommt. Ich hatte mit obigem Quelltext immer nur das High-Byte 
von PAGENUMBER (immer 0) in den Z-Pointer geschrieben, und deswegen wars 
immer 0.

Man verändere obigen Source wie folgt:
1. Ganz oben einfügen: "PageAddress <<= 8;"
2. 2x ersetzen "PageAddress*256" durch "PageAddress"

Sieheda, es geht ;)

Danke, Christoph

von Wolfgang Horn (Gast)


Lesenswert?

Hi,  Christoph,

freut mich, daß Deion Bootloader läuft.
Aber Deine Beschreibung ist falsch.

AVR Bootloading geht vereinfacht so:
1. Seite in den Flash füttern
2. Adresse eingeben, wo diese Seite hinsoll
3. Diese seite löschen
4. Den Speichervorgang anstoßen
5. Optional RWW aktivieren, bei 4k BL aber sowieso irrelevant

zu 1: nicht in das Flash, sondern in die Bootloader Page.
zu 2: ja.
zu 3: mit boot_page_write (page) bootloader page in flash schreiben, 
dies stößt den Schreibvorgang an.


ciao
Wolfgang Horn

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.