Forum: Mikrocontroller und Digitale Elektronik Komisches Verhalten des Optimierers


von Martin (Gast)


Lesenswert?

Hallo, ich habe mir ein Board mit einem Cortex M3 gebaut, auch externes 
RAM angeschlossen.

Jetzt habe ich zwei Funktionen geschrieben, welche den Speicher 
beschreiben und auslesen.
In der Hauptschleife rufe ich diese nun auf.
1
i = 0;
2
3
  /* Infinite loop */
4
  while (1)
5
  {
6
    ExtRam_SetByte(i, 0x13);
7
    check = ExtRam_GetByte(i);
8
    
9
    i++;
10
  
11
    if(i >= 0x80000)
12
      i = 0x00000;
13
14
  }
15
}

Der Optimierer macht allerdings voll den Kack daraus, hier mal ein 
Assemblerlisting:
1
/* Infinite loop */
2
  while (1)
3
  {
4
    ExtRam_SetByte(i, 0x13);
5
     2113       movs r1, #0x13
6
     2000       movs r0, #0x00
7
     F7FFFFB2   bl 0x08000684 <ExtRam_SetByte>
8
    check = ExtRam_GetByte(i);
9
     2000       movs r0, #0x00
10
     F7FFFF87   bl 0x08000634 <ExtRam_GetByte>
11
    ExtRam_SetByte(i, 0x13);
12
     2113       movs r1, #0x13
13
     2001       movs r0, #0x01
14
     F7FFFFAB   bl 0x08000684 <ExtRam_SetByte>
15
    check = ExtRam_GetByte(i);
16
     2001       movs r0, #0x01
17
     F7FFFF80   bl 0x08000634 <ExtRam_GetByte>
18
    ExtRam_SetByte(i, 0x13);
19
     2002       movs r0, #0x02
20
     2113       movs r1, #0x13
21
     F7FFFFA4   bl 0x08000684 <ExtRam_SetByte>
22
    check = ExtRam_GetByte(i);
23
     2002       movs r0, #0x02
24
     F7FFFF79   bl 0x08000634 <ExtRam_GetByte>
25
    
26
    i++;
27
     2303       movs r3, #0x03
28
     E00B       b 0x0800075E
29
    ExtRam_SetByte(i, 0x13);
30
     4620       mov r0, r4
31
     2113       movs r1, #0x13
32
     F7FFFF9B   bl 0x08000684 <ExtRam_SetByte>
33
    check = ExtRam_GetByte(i);
34
     4620       mov r0, r4
35
     F7FFFF70   bl 0x08000634 <ExtRam_GetByte>
36
    
37
    i++;
38
     1C63       adds r3, r4, #0x1
39
     2400       movs r4, #0x00
40
  
41
    if(i >= 0x80000)
42
     F5B32F00   cmp.w r3, #0x00080000
43
     D2F3       bcs 0x08000746
44
     461C       mov r4, r3
45
     E7F1       b 0x08000746

er ruft erst dreimal die Funktionen direkt auf und setzt dann 'i' auf 3. 
Irgenwie blöd, oda?

Ich arbeite mit Rowley Crossworks und die Optimierung ist auf Size 
gestellt.

Kann ich da was ändern?

Gruß, Martin

von Johann L. (gjlayde) Benutzerseite


Lesenswert?

Martin wrote:
>
> er ruft erst dreimal die Funktionen direkt auf und setzt dann 'i' auf 3.
> Irgenwie blöd, oda?

Zumindest korrekt... schon mal nicht unwichtig :o)

> Ich arbeite mit Rowley Crossworks und die Optimierung ist auf Size
> gestellt.

Rowley basiert wohl auf GCC? Ich hatte ähnlichen Ärger mit neuen gcc 
4.3.x für AVR: Schleifen wurden aufgerollt trotz -Os, -fno-unroll-loops 
et. al. blieben erfolglos. Sind wohl noch Zicken der neuesten GCC 
Versionen. Die Mainline ist hauptsächlich auf SPeed getrimmt, nicht auf 
Schlankheit.

> Kann ich da was ändern?
Ja. Du hast ja die Quellen :o)
Evtl. ist's für die Mainline (i386) nachvollziehbar daß aufgerollt wird 
trotz -Os. Dann ist die Wahrscheinlichkeit größer, daß das Problem bald 
gefixt wird. Hier wäre dann

   http://gcc.gnu.org/ml/gcc-help

die richtige Anlaufstelle. Das Anrollen der Schleife passiert 
wahrscheinlich im Target-unabhängigen Teil. Wo genau, siehst du mit 
Ausgaben per -fdump-tree-all. Falls der böse Pass verschaltert ist, kann 
angetestet werden, ob dessen Deaktivierung Abhilfe schafft.

Johann

von Martin (Gast)


Lesenswert?

Danke erstmal.

Bin vorrübergehend auf IAR umgestiegen, hab da zwar nut 32k Code, aber 
das wird schon erstmal reichen.
Das tolle ist auch, dass bei Crossworks beim Speicherlesen und 
-schreiben Fehler kommen und bei IAR nicht. (kann auch mein Fehler sein, 
aber ist gleicher Code)

Gruß, Martin

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.