ubuntuusers.de

GCC

Dieser Artikel wurde für die folgenden Ubuntu-Versionen getestet:


Du möchtest den Artikel für eine weitere Ubuntu-Version testen? Mitarbeit im Wiki ist immer willkommen! Dazu sind die Hinweise zum Testen von Artikeln zu beachten.

Die Gnu Compiler Collection, kurz GCC, ist eine Sammlung von Compilern und bietet eine einheitliche Schnittstelle zur Erstellung von Programmen in C, C++, Objective-C, Fortran, Ada, Assembler und Go an. Die Sprachen D (gdc), Eiffel (smarteiffel), Lisp (gcl), Pascal (gpc) und Prolog (gprolog) sind nicht Teil der GCC, sondern sind eigenständige Programme des GNU-Projekts.

Die ursprüngliche Bedeutung von GCC war GNU C Compiler, aber weil seither noch eine Reihe weiterer Sprachen hinzugefügt wurde, hat sich die Bedeutung nach GNU Compiler Collection gewandelt. Heute wird der C-Compiler kleinbuchstabig als gcc bezeichnet, um eine Unterscheidung vom Ganzen zu ermöglichen.

Dieser Artikel soll helfen, Programme mithilfe der GCC unter Ubuntu zu kompilieren. Er hat nicht die Absicht, eine Einführung in die von ihr unterstützen Sprachen zu geben. Hierzu sollte man die entsprechenden Webseiten, Online-Tutorien oder auch ein gutes Buch lesen.

Benötigte Werkzeuge und Programme

Wer Pakete irgendwelcher Art schon einmal selbst erstellt hat, der wird sich das Paket build-essential schon installiert haben. Es enthält neben je einem Compiler für C und C++ auch noch zahlreiche hilfreiche Werkzeuge, die unter den Entwicklern so regen Gebrauch finden (z.Bsp. Makefiles), dass sie unter jedem System, das etwas kompilieren möchte, als gegeben vorausgesetzt werden können. [1]

  • build-essential

Befehl zum Installieren der Pakete:

sudo apt-get install build-essential 

Oder mit apturl installieren, Link: apt://build-essential

Für andere Sprachen als C und C++ sind folgende Pakete notwendig [1]:

  • gobjc (Objective-C)

  • gfortran (Fortran)

  • gnat (universe, Ada)

Befehl zum Installieren der Pakete:

sudo apt-get install gobjc gfortran gnat 

Oder mit apturl installieren, Link: apt://gobjc,gfortran,gnat

Der Erstellungsprozess

Die grobe Struktur, wie mithilfe der GCC Projekte verschiedener Sprachen erstellt werden, gleicht derjenigen anderer Compiler. Erst wird die Quelldatei vorkompiliert, was dabei genau passiert, ist sprachabhängig. Meist läuft das Ganze so ab, dass zuerst ein Präprozessor aufgerufen wird, der unter anderem weitere Dateien einbindet, Makros ersetzt und Kommentare entfernt, also die Vorarbeit leistet. Danach wird die eigentliche Sprache angeschaut, optimiert und in Assemblerbefehle umgewandelt, die danach meist in Form von Objektdateien vorliegen.

Schlussendlich werden diese zusammengefasst, wobei man zumindest die Wahl zwischen einer grösseren Objektdatei, einer statischen Bibliothek, einer Programmbibliothek oder natürlich einem ausführbaren Programm selber.

Programme kompilieren

Hello World (nur Assembler, C, C++ und Ada)

Folgende Dateien [2] geben, nachdem sie kompiliert wurden [3], "Hello World" aus:

C++ (main.cc) C (main.c) Assembler (main.S) Ada (main.adb)
1
2
3
4
5
6
#include <iostream>

int main()
{
    std::cout << "Hello World\n";
}
1
2
3
4
5
6
#include <stdio.h>

int main ()
{
        printf ("Hello World\n");
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
.section .data
hello: .ascii "Hello World!\n"
.section .text
.globl _start
_start:
    mov $4, %eax
    mov $1, %ebx
    mov $hello, %ecx
    mov $13, %edx
    int $0x80
    mov $1, %eax
    mov $0, %ebx
    int $0x80
1
2
3
4
5
6
7
with Ada.Text_IO;
use  Ada.Text_IO;

procedure main is
begin
	Put_Line("Hallo World!");
end main;
g++ main.cc gcc main.c gcc main.S gcc -c main.adb (-c ist Voraussetzung)

Wird nichts anderes angegeben, versucht der Compiler ein ausführbares Programm zu erstellen, das standardmäßig a.out heißt. Führt man dieses im Terminal [3] aus [4], so wird wie erwartet "Hello World" ausgegeben.

Hinweis:

Es fällt auf, dass das "Hello World" von C++ nicht mit dem gcc, sondern mit dem g++ kompiliert wird. Der gcc erkennt zwar die Eingabesprache anhand der Endung (.cpp, .cc und .cxx wären alle korrekt), aber er verzichtet darauf, die Standardbibliothek von C++ zu verlinken. Der g++ macht dies automatisch und erspart so einiges an Aufwand.

Eine Erwähnung wert ist, dass diese drei Sprachen oder deren Objektdateien beliebig zusammengelinkt werden können. Es ist sogar möglich, dies alles in einem Befehl zu tun. Man muss nur an alle Standardbibliotheken denken.

Empfohlene Parameter

Es wird allgemein empfohlen, Programme ausschließlich mit folgenden Parametern zu erstellen (Erklärung weiter unten):

gcc -g -Wall -Wextra -pedantic-errors foo.c -o foo 

Oft kommt noch entweder -O0 -ggdb3 für das Debugging oder -march=native -O3 für eine schnelle Ausführung hinzu.

Einige wichtige Parameter

Es gibt aber auch noch viele andere nützliche Parameter, die wichtigsten sind hier in der Tabelle zusammengefasst:

Parameter Erklärung
-o Bestimmt den Namen der Ausgabedatei (Standard: „a.out“)
-c Der Quellcode wird nur kompiliert, aber noch nicht gelinkt (neue Endung oft „.o“)
-OX Optimiert den Quellcode; der Grad der Optimierung (Platzhalter X) kann 0 (nichts), 1 (Größe und Geschwindigkeit), 2 (Geschwindigkeit), 3 (Geschwindigkeit, aggressiv) oder s (Größe) sein)
-march=nativ Optimiert speziell für den vorhandenen Prozessor und wird auf anderen Architekturen nicht laufen.
-lXXX Bindet weitere Bibliotheken ein (z.B. -lncurses für libncurses)
-std=XXX Legt den Sprachstandard fest (XXX kann z.B. c99, c1x, c11, gnu++98, c++98, c++0x oder c++11 sein)
-ansi Erlaubt nur ANSI-C-konforme Konstrukte
-Wall Aktiviert sinnvolle Warnungen, die vom gcc-Compiler unterstützt werden.
-Wextra Aktiviert noch mehr Warnungen, die vom gcc-Compiler unterstützt werden.
-pedantic Weist auf nicht ISO-konforme Konstrukte mit einer Warnung hin (-pedantic-errors erzwingt Fehler)
-v Gibt die Kommandos und Schritte aus, die der Compiler gerade ausführt (Präprozessor, Compiler, Assembler, Linker...)
-g Fügt Debugging-Symbole in die Binärdatei ein
-ggdb Fügt weitere Debugging-Symbole für den GDB hinzu. Mit -ggdb3 wird alles mögliche unterstützt.

Interaktion mit Buildsystemen

So wichtig die Kenntnis der Kommandozeilenoptionen auch ist, um Programme zu kompilieren, gibt niemand den ganzen GCC-Aufruf in einer Shell ein – dafür sind Buildsysteme da. Wer etwas auf der Basis von Makefiles benutzt, der unterscheidet zwischen Optionen, die den Quelltext betreffen (CFLAGS bzw. CCFLAGS), und solchen, die das Linken betreffen (LDFLAGS). Von den in der Tabelle aufgelisteten Optionen gehört nur -l nicht in CFLAGS.

Es kann vorkommen, dass es zu Fehlern kommt, wenn der "-l"-Parameter vor der Angabe der Quelldatei angegeben wird, daher hilft es, diesen Parameter zum Schluss anzugeben.

Diese Revision wurde am 15. Dezember 2020 20:41 von schollsky erstellt.
Die folgenden Schlagworte wurden dem Artikel zugewiesen: Programmierung