Forum: Compiler & IDEs Disasembliertes Hex-File in C nachprogrammieren


von Olli (Gast)


Lesenswert?

Beim Aufräumen der Garage haben meine Kinder ein altes 
Metalldetektorprojekt
aus meiner Ausbildungszeit hervorgezaubert. Dieses soll nun aufgefrischt 
werden. Leider ist der Sourcecode nach Umzügen und neuer Hardware nicht 
mehr
vorhanden. Aber das Auslesen des Hex-Files aus dem Atmega8 hat 
funktioniert.
Es gibt einen Abschnitt der ISR(TIMER2_COMP_vect) im Disassembling den 
ich
nicht richtig verstehe.
1
cbi ADMUX, MUX0;  0000048C;  Lösche Bit MUX0 im PortRegister ADMUX
2
cbi PORTC, PORTC2;  0000048E;  Lösche Bit PORTC2 im PortRegister PORTC
3
cbi PORTC, PORTC5;  00000490;  Lösche Bit PORTC5 im PortRegister PORTC
4
lds r17, OnInterval;  00000492    10 91
5
rjmp Label_049C;  00000496;  Springe zu Label_049C
6
Label_0498:
7
rjmp Label_049A;  00000498;  Springe zu Label_049A
8
Label_049A:
9
rjmp Label_049C;  0000049A;  Springe zu Label_049C
10
Label_049C:
11
mov r16, r17;    0000049C;  Kopiere Inhalt von R17 in R16
12
dec r17;      0000049E;  R17 = R17 - 1, verringere R17 um 1
13
and r16, r16;            000004A0    00 23
14
brne Label_0498;            000004A2    D1 F7
15
sbi PORTC, PORTC5;  000004A4;  Setze Bit PORTC5 im PortRegister PORTC
Was passiert in den Zeilen 492 - 4A2 ?
Das kann doch nur eine Zeitschleife sein ?
Aber der Footprint eines _delays_us() sieht in Assembler anders aus.
In C sollte das doch so aussehen, oder ?
1
ADMUX &= ~(1<<MUX0);
2
PORTC &= ~(1<<PC2);
3
PORTC &= ~(1<<PC5);
4
while (OnInterval > 0) {
5
    OnInterval = OnInterval - 1;
6
}
7
PORTC |= (1<<PC5);
Habt Ihr eine Idee dazu ?

von Theobald (Gast)


Lesenswert?

Olli schrieb:
> Was passiert in den Zeilen 492 - 4A2 ?

Welche sind das? Dein Assemblerlisting zeigt nur Zeilen 1 bis 15.

von Olli (Gast)


Lesenswert?

Es sind die Zeilen 4 - 14, die richtige Nummerieung steht weiter rechts 
in
den Zeilen (00000492 - 000004A4).

von Ingo W. (uebrig) Benutzerseite


Lesenswert?

Du hast aber nur die ersten 14 Zeilen der Disassemblerausgabe in den 
Beitrag eingefügt. Besser die gesamte Datei als Anhang!

von MWS (Gast)


Lesenswert?

Olli schrieb:
> Das kann doch nur eine Zeitschleife sein ?

Unvorteilhafte Darstellung.
Der einzige Sinn der rjmps jeweils auf ein darauf folgendes Label ist 
Zeit zu verbrauchen, z.B. um für die Laufzeit pro Schleifendurchlauf zu 
kompensieren.

von c-hater (Gast)


Lesenswert?

Olli schrieb:

> Das kann doch nur eine Zeitschleife sein ?

Ja. Offensichtlich hat da ein dezimalsystemfixierter Assembler-Novize 
(ganz vorsichtig: Im Kontext eines Compilers) sein ganz persönliches 
Busy-Wait programmiert.

Ziel der Sache war wohl, ein (zur Laufzeit setzbares) Vielfaches von 
zehn MCU-Takten zu warten.

Wozu auch immer das gut gewesen sein soll. Warten ist fast niemals gut 
und wenn man schon ein busy wait baut, dann doch wenigstens eins, 
welches den Systemtakt kennt und die Takte entsprechend der Wartezeit 
berechnet, sprich (wenn man schonmal einen Compiler hat): _delay_us(). 
Kannte der Mann wohl noch nicht...

von MaWin (Gast)


Lesenswert?

c-hater schrieb:
> Wozu auch immer das gut gewesen sein soll. Warten ist fast niemals gut
> und wenn man schon ein busy wait baut, dann doch wenigstens eins,
> welches den Systemtakt kennt und die Takte entsprechend der Wartezeit
> berechnet, sprich (wenn man schonmal einen Compiler hat): _delay_us().
> Kannte der Mann wohl noch nicht...

Leute, es geht nicht darum das Programm zu optimieren, sondern darum ein 
bestehendes Hex wieder in entsprechenden gleichen C-Code 
zurückzuwandeln.

von Nikolaus S. (Firma: Golden Delicious Computers) (hns)


Lesenswert?

Olli schrieb:
> In C sollte das doch so aussehen, oder ?
>
1
> ADMUX &= ~(1<<MUX0);
2
> PORTC &= ~(1<<PC2);
3
> PORTC &= ~(1<<PC5);
4
> while (OnInterval > 0) {
5
>     OnInterval = OnInterval - 1;
6
> }
7
> PORTC |= (1<<PC5);
8
>
> Habt Ihr eine Idee dazu ?

Welchen Code erzeugt denn der C-Compiler daraus und wie ähnlich ist das 
Ergebnis zum vorgefundenen (Dis)Assemblerlisting?

von Jörg W. (dl8dtl) (Moderator) Benutzerseite


Lesenswert?

Weißt du denn noch, was für ein Compiler es mal war?

Ich würde das für etwas wie _delay_us(irgendwas) halten, allerdings 
erzeugt AVR-GCC dafür normalerweise einfach nur eine Schleife. Lediglich 
wenn man nach der Schleife noch "Finetuning" braucht, baut er noch so 
einen "rjmp ." Konstrukt rein, aber nicht in die Schleife.
1
#define F_CPU 1E6
2
#include <util/delay.h>
3
#include <avr/io.h>
4
5
void adcop(void) {
6
7
  ADMUX &= ~(1<<MUX0);
8
  PORTC &= ~(1<<PC2);
9
  PORTC &= ~(1<<PC5);
10
11
  _delay_us(13.3);
12
13
  PORTC |= (1<<PC5);
14
}
bringt, für einen ATmega8 compiliert:
1
  cbi 0x7,0
2
  cbi 0x15,2
3
  cbi 0x15,5
4
  ldi r24,lo8(4)
5
1:  dec r24
6
  brne 1b
7
  rjmp .
8
  sbi 0x15,5
9
  ret

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.