2017-12-08 2 views
1

Ich beginne mit der Programmierung in Assembly in x86 und ich befolge eine Anleitung dafür. Ich verwende Gas, um auf einer virtuellen Linux-Maschine zu kompilieren.x86 Assembly mit Gas auf Linux: mehrere Definitionen von 'Haupt'

Ich versuche, ein einfaches leeres Programm auszuführen, in dem die Hauptroutine das Programm sofort beendet. Das ist die erste Aufgabe in dem Handbuch, dem ich folge. Mein Code wird in einer Datei gespeichert hello.s und es sieht wie folgt aus:

.global main 

main: 
    movq %rsp, %rbp 
    mov $0, %rdi 
    call exit 

Im Anschluss I in das Verzeichnis der Datei navigieren und versuchen, es wie folgt auszuführen:

gcc -o hello.o hello.s -no-pie ./hello.s 

I Fehlermeldung:

/tmp/cc62hr1F.o: In function 'main': 
(.text+0x0): multiple definition of 'main' 
/tmp/ccwMutY1.o(.text+0x0): first defined here 
collect2: error: ld returned 1 exit status 

Was bedeutet dieser Fehler und wie kann er behoben werden? Vielen Dank im Voraus.

+0

Nun, ich bin kein Fan dieser Syntax, so dass ich kein Gas und bin nicht ganz auf dem neuesten Stand, aber Sie haben möglicherweise 2 Hauptetiketten dort ... Was passiert, wenn Sie den einen oder anderen entfernen? –

+3

Ihr Problem besteht darin, dass Sie "hello.s" zweimal an den Compiler übergeben, sodass es zweimal zusammengesetzt wird und zweimal versucht, eine Binärdatei zu generieren, was zu dem doppelten Symbolfehler führt, den Sie beobachten. – fuz

Antwort

1

BEARBEITEN/LÖSUNG: Ich habe herausgefunden, was los war. Im Terminal sollte ich es so laufen lassen:

gcc -o hello.o hello.s -no-pie 
./hello.o 

Dies sind zwei separate Befehle. Ich habe sie in einer Zeile geschrieben. Und die Datei zu laufen muss die Erweiterungen .o nicht haben.

+3

Beachten Sie, dass ausführbare Dateien unter Linux/UNIX normalerweise keine Dateierweiterung haben. Also 'gcc -o hallo -no-pie hallo.s' (auch beachten Sie, Optionen kommen vor Operanden) wäre richtiger. Dateien mit dem Zusatz '.o' sind * Objektdateien *, die verknüpft werden müssen, bevor sie ausgeführt werden können. – fuz

+0

Es gibt sicherlich eine Option, um .o-Datei von .s zu erhalten ('-c' ist für C-Quelle, zu faul, um zu überprüfen, dass es auch für .s funktioniert), aber solange der gesamte Code in einer einzigen .s-Datei ist kann das 'gcc' veranlassen, die Binärdatei direkt zu erstellen, genau wie du es getan hast. Verwenden Sie einfach '.o' nicht für den Binärnamen. Der binäre Standardname ist 'a.out', es sei denn, Sie geben Ihre eigene an, indem Sie die Option -o ' verwenden. – Ped7g