mikrocontroller.net

Forum: Compiler & IDEs Teensy 40 von C erzeugter ARM Assemblercode


Announcement: there is an English version of this forum on EmbDev.net. Posts you create there will be displayed on Mikrocontroller.net and EmbDev.net.
von Martin O. (ossi-2)


Bewertung
-1 lesenswert
nicht lesenswert
Ich will verstehen welcher ARM Assemblercode vom Compiler erzeugt wird.
Das folgende Testprogramm
void setup() {
  Serial.begin(9600);
  delay(1000) ;  
  Serial.print("Hello teensy40armDisasm5\n"); 
  kStop=0 ;
  while(1){
    a=a+0x1234 ;
    b=a+0x5678 ;
    xstop() ;
    }
  Serial.print("end setup....\n"); 
  }
erzeugt den unten angegebenen ARM-Thumb Assemblercode. Ich habe zwei 
Fragen (für mich ist ARM Assembler noch ganz neu.):
Wozu dienen die vielen mit .short erzeugten Konstanten im Code?
Warum wird der code für
    .....
   a=a+0x1234 ;
   b=a+0x5678 ;
   ....
anscheinend zweimal erzeugt?
void setup() {
      b4:  b508        push  {r3, lr}
  Serial.begin(9600);
  delay(1000) ;  
      b6:  f44f 707a   mov.w  r0, #1000  ; 0x3e8
      ba:  4c0c        ldr  r4, [pc, #48]  ; (ec <setup+0x38>)
      bc:  f000 f838   bl  130 <delay>
        virtual int read() { return usb_serial_getchar(); }
        virtual int peek() { return usb_serial_peekchar(); }
        virtual void flush() { usb_serial_flush_output(); }  // TODO: actually wait for data to leave USB...
        virtual void clear(void) { usb_serial_flush_input(); }
        virtual size_t write(uint8_t c) { return usb_serial_putchar(c); }
        virtual size_t write(const uint8_t *buffer, size_t size) { return usb_serial_write(buffer, size); }
      c0:  480b2119   .word  0x480b2119
      c4:  f000 ffbe   bl  1044 <usb_serial_write>
      c8:  4b0b4d0a   .word  0x4b0b4d0a
  Serial.print("Hello teensy40armDisasm5\n"); 
  kStop=0 ;
      cc:  2200        movs  r2, #0
      ce:  601a        .short  0x601a
  while(1){
    a=a+0x1234 ;
      d0:  6821        ldr  r1, [r4, #0]
      d2:  f241        .short  0xf241
      d4:  2234        movs  r2, #52  ; 0x34
    b=a+0x5678 ;
      d6:  f245        .short  0xf245
      d8:  6378        str  r0, [r7, #52]  ; 0x34
  Serial.begin(9600);
  delay(1000) ;  
  Serial.print("Hello teensy40armDisasm5\n"); 
  kStop=0 ;
  while(1){
    a=a+0x1234 ;
      da:  440a        .short  0x440a
      dc:  6022        str  r2, [r4, #0]
    b=a+0x5678 ;
      de:  6822        .short  0x6822
      e0:  4413        add  r3, r2
      e2:  602b        .short  0x602b
    xstop() ;
      e4:  f7ff ffca   bl  7c <xstop()>
      e8:  bf00e7f2   .word  0xbf00e7f2
      ec:  0ddc        lsrs  r4, r3, #23
      ee:  2000        .short  0x2000
      f0:  0014        movs  r4, r2
      f2:  2000        movs  r0, #0
      f4:  20000de0   .word  0x20000de0
      f8:  0de4        lsrs  r4, r4, #23
      fa:  2000        movs  r0, #0

000000fc <loop>:
  if(kStop>3){ 
    while(1){} ;
    }
  }
    
void loop(){
      fc:  bf004770   .word  0xbf004770

von Taiga Wutzzz (Gast)


Bewertung
-5 lesenswert
nicht lesenswert
Seit wann gucken sich C--Stuemper Assemblercode an.
Der ist denen nach eigenem Bekunden doch egal.

Solang es blinkt.

von . . (Gast)


Bewertung
0 lesenswert
nicht lesenswert
Taiga Wutzzz wie wir ihn lieben.

Aber zum Thema: der "Assemblercode" passt nicht so recht zum 
Programmcode. Irgendwas vom Programmcode wird uns verheimlicht ;)

von Irgend W. (Firma: egal) (irgendwer)


Bewertung
0 lesenswert
nicht lesenswert
Martin O. schrieb:
> kStop=0 ;
>     a=a+0x1234 ;
>     b=a+0x5678 ;
>     xstop() ;

Das ist alles weder definiert noch initialisiert.
Das kann der Compiler garnicht übersetzen und sollte einiges an Fehlern 
und Warnungen rausgeben.
Und wenn du die Optimierung vernünftig eingeschaltet hättest würde der 
Compiler das sowieso einfach entsorgen weil die Variablen für nichts 
verwendet werden.
Schreib erstmal vernünftigen C-Code...

von 2^5 (Gast)


Bewertung
0 lesenswert
nicht lesenswert
Zeig mal das ganze Programm!

von Taiga Wutzzz (Gast)


Bewertung
-1 lesenswert
nicht lesenswert
> Zeig mal das ganze Programm!

Blos nicht!

von Martin O. (ossi-2)


Bewertung
-1 lesenswert
nicht lesenswert
Das ganze Programm sieht so aus:
volatile int a,b,c ;
volatile int kStop ;
 
void setup() {
  Serial.begin(9600);
  delay(1000) ;  
  Serial.print("Hello teensy40armDisasm5\n"); 
  kStop=0 ;
  while(1){
    a=a+0x1234 ;
    b=a+0x5678 ;
    xstop() ;
    }
  Serial.print("end setup....\n"); 
  }

void xstop(){
  Serial.printf("a=%08XH b=%08XH\n",a,b) ;
  kStop++ ;
  if(kStop>3){ 
    while(1){} ;
    }
  }
    
void loop(){
  }  
Es gibt keine Fehler oder Warnungen beim compilieren. Es funktioniert 
auch einwandfrei.

: Bearbeitet durch User
von Oliver S. (oliverso)


Bewertung
0 lesenswert
nicht lesenswert
Dann solltest du mal alle Warnungen einschalten.

Oliver

von Bernd K. (prof7bit)


Bewertung
0 lesenswert
nicht lesenswert
Oliver S. schrieb:
> Dann solltest du mal alle Warnungen einschalten.

Ich seh jetzt auf den ersten Blick nichts wo ne Warnung kommen sollte. 
Was meinst Du?

Das einzige was mir auffällt ist daß die Klammern grauenvoll und 
irreführend falsch eingerückt sind, aber das ist dem Compiler egal.

von . . (Gast)


Bewertung
0 lesenswert
nicht lesenswert
Naja, der Compiler (oder die Toolchain) bemühte sich, den Anforderungen 
gerecht zu werden.

Will sagen, dass sie nicht mal selbst erzeugten Code korrekt in 
Assembler ausgeben kann, daher die .sort und .word mitten im Code.

Was ist das für ein Compiler (und welche Version)?

von Oliver S. (oliverso)


Bewertung
0 lesenswert
nicht lesenswert
Bernd K. schrieb:
> Ich seh jetzt auf den ersten Blick nichts wo ne Warnung kommen sollte.
> Was meinst Du?

Irgend W. schrieb:
> Das ist alles weder definiert noch initialisiert.

Definiert schon, initialisiert nicht.

Oliver

: Bearbeitet durch User
von Wilhelm M. (wimalopaan)


Bewertung
0 lesenswert
nicht lesenswert
Oliver S. schrieb:
> Definiert schon, initialisiert nicht.

Doch,schon.
Die non-local Variablen a,b,c werden - sofern nicht anders angeben - 
zero-initialized.

von Dennis H. (c-logic)


Bewertung
0 lesenswert
nicht lesenswert
Ist der falsche Diassembler. Ist kein ARMv4Thumb sondern ARMv7Thumb.

Da wird schnell aus:
"216841f2342245f278630a442260226813442b60"

6821      LDR  R1, [R4]
f241 2234 MOVW  R2, #0x1234
f245 6378 MOVW  R3, #0x5678
440a      ADD  R2, R1
6022      STR  R2, [R4]
6822      LDR  R2, [R4]
4413      ADD  R3, R2
602b      STR  R3, [R5]

und nicht:
      d0:  6821        ldr  r1, [r4, #0]
      d2:  f241        .short  0xf241
      d4:  2234        movs  r2, #52  ; 0x34
      d6:  f245        .short  0xf245
      d8:  6378        str  r0, [r7, #52]  ; 0x34
      da:  440a        .short  0x440a
      dc:  6022        str  r2, [r4, #0]
      de:  6822        .short  0x6822
      e0:  4413        add  r3, r2
      e2:  602b        .short  0x602b

Beim ARMv4 war Thumb noch optional, beim Cortex-M7 ist es das einzige 
Opcode-Format und deswegen wurde es um einige 2x16Bit Breite Befehle 
erweitert. Der ARMv4-Diassembler wird da einiges undefiniertes Vorfinden 
und nur den short (16-bit) hinschreiben.

: Bearbeitet durch User
von . . (Gast)


Bewertung
0 lesenswert
nicht lesenswert
Dennis H. schrieb:
> Ist der falsche Diassembler. Ist kein ARMv4Thumb sondern ARMv7Thumb.

Wurde ja schon angefragt, was für Programme verwendet wurden.
Der TO schweigt dazu. Zeitverschwendung.

von Martin O. (ossi-2)


Bewertung
0 lesenswert
nicht lesenswert
An Dennis H. (den einzigen der Hilfreiches gepostet hat)
Besten Dank, ich habe inzwischen rausgefunden das die neuste objdump 
Routine anscheinend richtig arbeitet. Vermutlich war die alte objdump 
Routine nur für ARMv4Thumb richtig, wie Du bemerkt hast.

von Markus F. (mfro)


Bewertung
0 lesenswert
nicht lesenswert
Martin O. schrieb:
> An Dennis H. (den einzigen der Hilfreiches gepostet hat)
> Besten Dank, ich habe inzwischen rausgefunden das die neuste objdump
> Routine anscheinend richtig arbeitet. Vermutlich war die alte objdump
> Routine nur für ARMv4Thumb richtig, wie Du bemerkt hast.

Bei binutils, die Code für unterschiedliche Prozessoren einer Familie 
erzeugen können, muss man objdump (mit --architecture) u.U. mitgeben, 
für welche Variante disassembliert werden soll (das ist dem .elf-File 
nicht notwendigerweise zu entnehmen).

Wahrscheinlich hat dein neueres objdump nur andere Defaults.

: Bearbeitet durch User
von . . (Gast)


Bewertung
0 lesenswert
nicht lesenswert
Martin O. schrieb:
> An Dennis H. (den einzigen der Hilfreiches gepostet hat)
> Besten Dank, ich habe inzwischen rausgefunden das die neuste objdump
> Routine anscheinend richtig arbeitet. Vermutlich war die alte objdump
> Routine nur für ARMv4Thumb richtig, wie Du bemerkt hast.

Wieder was gelernt: Man darf nicht die alte objdump benutzen.
Es muss die neueste sein.

von S. R. (svenska)


Bewertung
0 lesenswert
nicht lesenswert
.. schrieb:
> Wieder was gelernt: Man darf nicht die alte objdump benutzen.
> Es muss die neueste sein.

Falsch: Es muss die richtige (passende) sein.

von . . (Gast)


Bewertung
0 lesenswert
nicht lesenswert
S. R. schrieb:
> .. schrieb:
>> Wieder was gelernt: Man darf nicht die alte objdump benutzen.
>> Es muss die neueste sein.
>
> Falsch: Es muss die richtige (passende) sein.

Neinneinnein!
Nach dem ich ja schon die Version der Tools angefragt habe, und dieser 
Beitrag, wie der anderer Leute, vom TO als nicht hilfreich bezeichnet 
wurde, dazu keinerlei Infos vom TO kamen, und als Endlösung dann, das 
"alte" müsste gegen das "neusten" objdump ersetzt werden, wuss das 
prezise und zwingend richtig sein! ;)

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.