Der Abschnitt über Makefiles im AVR C Tutorial ist für mich unverständlich. Mit diesem minimal Makefile bekommt man die ersten Projekte kompiliert. Mit den unten beschriebenden Änderungen reicht ein make im Verzeichnis in dem sich Makefile und Code befinden und das ganze zu kompilieren. Im optionalen Teil kann man die entsprechenden avrdude Parameter angeben um mit "make install" den Chip zu flashen. #AVR-GCC Makefile PROJECT=tutorial_1 SOURCES=main.c #anpassen CC=avr-gcc OBJCOPY=avr-objcopy #angabe des ziels für avr-libc MMCU=atmega8 #anpassen CFLAGS=-mmcu=$(MMCU) -Wall $(PROJECT).hex: $(PROJECT).out $(OBJCOPY) -j .text -O ihex $(PROJECT).out $(PROJECT).hex $(PROJECT).out: $(SOURCES) $(CC) $(CFLAGS) -I./ -o $(PROJECT).out $(SOURCES) ########################optional############################### install: $(PROJECT).hex avrdude -p m8 -P /dev/ttyUSB0 -b 115200 -c avr910 -U flash:w:$(PROJECT).hex clean: rm -f $(PROJECT).out rm -f $(PROJECT).hex Zu ersetzen: 1. SOURCES=main.c Hier kommt eure Quelldatei hin 2.MMCU=atmega8 atmega8 durch den verwendeten Atmega ersetzen 3. optional avrdude einstellungen zum flashen des Chips, mit "make install"
Hi, danke fuer das Makefile Beispiel. Ich finds schade das die Jungs im GCC Howto vergessen haben ein Makefile Beispiel zu schreiben. Wollte mal das LCD Beispiel compilen, und bekomme folgenden Fehler: main.c:(.text+0x8): undefined reference to `lcd_init' main.c:(.text+0xc): undefined reference to `lcd_data' main.c:(.text+0x10): undefined reference to `lcd_data' main.c:(.text+0x14): undefined reference to `lcd_data' main.c:(.text+0x18): undefined reference to `lcd_data' main.c:(.text+0x1e): undefined reference to `set_cursor' main.c:(.text+0x24): undefined reference to `lcd_string'
Hallo. Ich möchte mir floating-point-Werte auf dem UART ausgeben lassen. Dazu habe ich gelesen, dass dies über die sprintf()-Funktion geht, wo ich vorher noch die entsprechenden Einstellungen im Makefile vornehmen muss. Im "Exkurs Makefile" des Tutorials habe ich schon einiges gelesen,allerdings zeigt es mir auf dem HyperTerminal, den ich zur Ausgabe nutze, immer nur ein "?" an!!! Laut dem Tutorial und der WinAVR-libc Doku benötige ich: PRINTF_LIB_FLOAT = -Wl,-u,vfprintf -lprintf_flt MATH_LIB = -lm LDFLAGS += lprintf_flt bei LIBDIRS habe ich den Pfad der printf-Bibliothek mit dem Befehle LIBDIRS = -L$C:/WinAVR-20080610/avr/lib eingebunden. Da ich bisher noch nicht viel mit Makefiles gemacht habe weiss ich halt nicht woran es liegt,dass es mir nur ein "?" ausgibt. Zum testen habe ich mir einen Dezimalwert in der Variable x in float berechnen lassen.Im Watch-Window steht der auch korrekt drin. ... x = (double)x_wert * 0.0039; length = sprintf((char *)str,"%3.3f",x); sendDataToUart(str,length); Am Programm dürfte es nicht liegen,da ich Dezimalwerte auch problemlos ausgeben kann.
Lösungsmöglichkeit 1: Wirklich lernen wie (gnu) make funktioniert Lösungsmöglichkeit 2: mfile nehmen, printf-Option anklicken und gut ist
Lösungsmöglichkeit2 fällt weg,da ich in meinem Makefile Funkeinstellungen mit drin habe,die von meiner genutzten Software und dem dazugehörigen Stack gegeben sind. Ich denke,dass es bei mir ein Problem der Platzierung der benötigten Printf-Einstellungen innerhalb des Makefiles ist.Das heißt, in welcher "ifeq"-Bedingung ich die Parameter für Printf setze. Kann das möglich sein?
>Ich denke,dass es bei mir ein Problem der Platzierung der benötigten >Printf-Einstellungen innerhalb des Makefiles ist.Das heißt, in welcher >"ifeq"-Bedingung ich die Parameter für Printf setze. >Kann das möglich sein? Nein. PRINTF_LIB_FLOAT = -Wl,-u,vfprintf -lprintf_flt definiert im makefile eine Variable Namens PRINTF_LIB_FLOAT. Mehr nicht. Die muß auch in den Linkeraufruf, sonst hat die keine Wirkung. Daher: >Lösungsmöglichkeit 1: Wirklich lernen wie (gnu) make funktioniert >Lösungsmöglichkeit 2: mfile nehmen, printf-Option anklicken und gut ist Lösungsmöglichkeit 3: Lösungsmöglichkeit 2 nehmen, im erzeugten makefile nachschauen, wie es richtig geht. Oliver
> Lösungsmöglichkeit2 fällt weg,da ich in meinem Makefile > Funkeinstellungen mit drin habe,die von meiner genutzten Software und > dem dazugehörigen Stack gegeben sind. Bleibt immer noch die NR. 1: Lernen wie make funktioniert.
Oliver wrote: >PRINTF_LIB_FLOAT = -Wl,-u,vfprintf -lprintf_flt >definiert im makefile eine Variable Namens PRINTF_LIB_FLOAT. Mehr nicht. >Die muß auch in den Linkeraufruf, sonst hat die keine Wirkung. Danke für den Tipp.Jetzt funktioniert es.Die Werte kommen als float auf dem HyperTerminal an. Allerdings gibt es noch ein Problem,wenn ich den float-Wert (bei mir in Variable "x") mit der Gleichung: x = (double)x_wert*0.0039; // den Wert gibt es i HyperTerminal aus winkelx = asin(x)/PI*180; in einen Winkel umrechnen will!Ich habe aber wie in der libc-Bibliothek beschrieben,nach dem PRINT_LIB_FLOAT gleich MATH_LIB = -lm stehen?! Nach dem Build stehen folgende Warnungen: c:/winavr-20080610/bin/../lib/gcc/avr/4.3.0/../../../../avr/lib/avr51\li bc.a(fp_powsodd.o): In function `__fp_powsodd': (.text.fplib+0x10): relocation truncated to fit: R_AVR_13_PCREL against symbol `__mulsf3' defined in .text section in c:/winavr-20080610/bin/../lib/gcc/avr/4.3.0/avr51\libgcc.a(_mul_sf.o) Jemand eine Idee? c:/winavr-20080610/bin/../lib/gcc/avr/4.3.0/../../../../avr/lib/avr51\li bc.a(fp_powsodd.o): In function `__fp_powsodd': (.text.fplib+0x20): relocation truncated to fit: R_AVR_13_PCREL against symbol `__mulsf3' defined in .text section in c:/winavr-20080610/bin/../lib/gcc/avr/4.3.0/avr51\libgcc.a(_mul_sf.o) make: *** [link] Error 1 Build succeeded with 6 Warnings...
Selber Fehler... Das -lm bzw, MATH_LIB muß in den Linkeraufruf, die Fehlermeldung lässt vermuten, daß es da fehlt. >Lösungsmöglichkeit 3: Lösungsmöglichkeit 2 nehmen, im erzeugten makefile >nachschauen, wie es richtig geht. Oliver
hier ist mein entsprechender Code im Makefile: # Linking --------------------------------------------- ifeq ($(COMPILER_TYPE), GCC) # It's easier to use indirect ld call via gcc instead of direct ld call. LD = $(CC) LINKER_FLAGS = -Xlinker -Map=$(PROJNAME).map -Wl,--gc-sections ifeq ($(HAL), ATMEGA1281) objects = $(COMPONENTS_PATH)/../lib/WdtInitatmega1281.o LINKER_FLAGS += $(filter -mmcu%,$(CFLAGS)) #LDFLAGS += -lprintf_flt PRINTF_LIB_FLOAT = -Wl,-u,vfprintf -lprintf_flt MATH_LIB = -lm endif ifeq ($(DEBUG), ON) LINKER_FLAGS += -g -Wl -u vfprintf -lprintf_flt -lm //das war Tipp v. dir endif endif und wo soll da MATH_LIB hin? Wo ich es oben stehen habe,hat es nichts bewirkt!?
Das ist ja alles nur Vorgeplänkel. Entscheidend ist der eigentliche Aufruf des linkers. Zeig nochmal das komplette makefile (als Anhang) Oliver
also ich hab mich jetz im Forum belesen und sämtliche Dinge ausprobiert,aber das will einfach nicht.
Ersetz mal die Zeile
>$(LD) $(LIBDIRS) $(LINKER_FLAGS) $(objects) $(LIBS) -o $(PROJNAME).elf
durch
$(LD) $(LIBDIRS) $(LINKER_FLAGS) $(objects) $(LIBS) -lm -o
$(PROJNAME).elf
Oliver
Nachtrag: Das ist jetzt die brute-force-methode. Und alles in eine Zeile. Im Sinne des makefile-Autors wäre das -lm (oder ein vorher definiertes MATH_LIB) vermutlich in der letzten Zeile dieses Blocks richtig ifeq ($(COMPILER_TYPE), GCC) LIBDIRS = \ -L$(COMPONENTS_PATH)/../lib \ -L$(BSP_PATH)/lib \ -L$(CS_PATH)/lib \ -L$(PDS_PATH)/lib \ -L$C:/WinAVR-20080610/avr/lib LIBS = -l$(STACK_LIB) -l$(PDS_LIB) -l$(BSP_LIB) -l$(STACK_LIB) Oliver
Vielen Dank Oliver!Jetzt funktioniert es. Aber wenn die "i$(MATH_LIB)" allein schon in die LIBS mit inkludiert hätte,hätte des doch auch klappen müssen,oder? Vorausgesetzt, ich habe "MATH_LIB = -lm" bei den Makros im Teil "Linking" hinzugefügt. Jedenfalls habe ich das auch schon probiert,jedoch ohne Erfolg. Naja,sei es drum...
Na ja, ob das alles bei den vielen ifeq an der richtigen Stelle stand, ist fraglich. Oliver
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.