mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Probleme mit Linker in WIN AVR


Autor: Raphael (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo zusammen,

ich habe ein Programm, dass aus mehreren C Dateien und einer 
Assemblerdatei besteht. Anscheinend hat der Linker ein Problem die 
Dateien zusammen zufügen. Dateien liegen alle im gleichen Ordner, 
makefile auch. Was kann das sein?

-------- begin --------
avr-gcc (GCC) 4.2.2 (WinAVR 20071221)
Copyright (C) 2007 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is 
NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR 
PURPOSE.


Compiling C: main.c
avr-gcc -c -mmcu=atmega128 -I. -gdwarf-2 -DF_CPU=8000000UL -Os 
-funsigned-char -funsigned-bitfields -fpack-struct -fshort-enums -Wall 
-Wstrict-prototypes -Wa,-adhlns=./main.lst  -std=gnu99 -Wundef -MMD -MP 
-MF .dep/main.o.d main.c -o main.o

Linking: main.elf
avr-gcc -mmcu=atmega128 -I. -gdwarf-2 -DF_CPU=8000000UL -Os 
-funsigned-char -funsigned-bitfields -fpack-struct -fshort-enums -Wall 
-Wstrict-prototypes -Wa,-adhlns=main.o  -std=gnu99 -Wundef -MMD -MP -MF 
.dep/main.elf.d main.o --output main.elf -Wl,-Map=main.map,--cref 
-lm
main.o: In function `main':
C:\Dokumente und Einstellungen\Raphael\Eigene Dateien\test/main.c:24: 
undefined reference to `lcd_init'
C:\Dokumente und Einstellungen\Raphael\Eigene Dateien\test/main.c:25: 
undefined reference to `backcolor'
C:\Dokumente und Einstellungen\Raphael\Eigene Dateien\test/main.c:25: 
undefined reference to `backcolor'
C:\Dokumente und Einstellungen\Raphael\Eigene Dateien\test/main.c:26: 
undefined reference to `textcolor'
C:\Dokumente und Einstellungen\Raphael\Eigene Dateien\test/main.c:26: 
undefined reference to `textcolor'
C:\Dokumente und Einstellungen\Raphael\Eigene Dateien\test/main.c:27: 
undefined reference to `fill_screen'
C:\Dokumente und Einstellungen\Raphael\Eigene Dateien\test/main.c:34: 
undefined reference to `put_char'
make.exe: *** [main.elf] Error 1

> Process Exit Code: 2
> Time Taken: 00:01

Autor: Johann L. (gjlayde) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Du verwendest Funktinen/Objekte aus anderen Modulen, ohne sie zu 
deklarieren.

Um eine Funktion/Objekt in einem anderen Modul zu verwenden, muss sie 
dort bekannt sein. Das wird in C üblicherweise über Headern erledigt.

Es fehlt in main also
#include "lcd-zeugs.h"
#include "farben-zeugs.h"
#include "put-zeugs.h"
...

Du könntest auch auf Warnungen des Compilers schauen, gib dazu mal an -W 
-Wall beim gcc-Aufruf

Johann

Autor: Johann L. (gjlayde) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Äh..Stop.-)

Wo sind denn die anderen Objekte (*.o)? Wie soll der Linker das sonst 
linken? Du gibst nur die main.o an, da sind natürlich externe Referenzen 
drinne, die der Linker nicht auflösen kann, wenn die Module fehlen, in 
denen diese definiert werden. Daher meckert er.

Ist eher ein Problem deines Linker-Aufrufs, also deines Makefiles,  als
eines des Linkers.

Johann

Autor: ... (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@Johann:
Das ist zwar absolut richtig, würde aber auch noch nichts nützen. Wo 
sollen denn die *.o herkommen? Dazu müßte er erstmal (Zitat:)"mehreren C 
Dateien" kompilieren :)
Da fehlt also im Makefile noch mehr.

Autor: Peter Diener (pdiener) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
So wie das aussieht, hast du ja die Funktionen, die als undefined 
reference ausgeworfen werden, selbst geschrieben.

lcd_init
backcolor
textcolor
fill_screen
put_char

Undefined reference bedeutet, dass die Funktion an einer Stelle 
aufgerufen wird, wo sie noch nicht bekannt ist. Das kann im C-Code z.B. 
passieren, wenn man keine Prototypen angibt und Funktionen, die im 
Quelltext weiter unten definiert sind in einer Funktion, die darüber ist 
(niedrigere Zeilennummer) aufruft.

Normal macht man das dann so (Beispiel, ich kenne deine Funktionen 
nicht):
//define prototypes
void lcd_init();
void backcolor(int color);
void fill_screen(int color);
//usw...


void lcd_init()
{
  //Funktionsquelltext
}

void backcolor(int color)
{
  //Funktionsquelltext
}

void fill_screen(int color)
{
  //Funktionsquelltext
}


Damit darf dann auch beispielsweise innerhalb von backcolor fill_screen 
aufgerufen werden.
Wenn man das sauber machen will, packt man die ganzen Prototypen noch in 
ein Headerfile und bindet das mit #include in das main.c am Anfang ein.

Über dieses Headerfile können die Funktionen aus main.c auch anderen 
Dateien bekannt gemacht werden.

Grüße,

Peter

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.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

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