problem mit include

OP #1190296
Lesenswert?

hallo

ich binde die datei test.c mit #include "test.c" ein. nun wenn ich in 
dieser datei irgendein c code schreibe ausser #define dann gibt der 
compiler fehler aus.
ein beispiel:
    uint8_t var_1;

../test.c:1: error: expected '=', ',', ';', 'asm' or '__attribute__' 
before 'var_1'


ich vermute dass bei compiler zusätzlich was eingestellt werden muss 
dass die include datei "ganz normal" eingegunden wird.

meine prog. umgebung: xp, avrstudio 4.16, winavr 20081205

gruss
Gast #1190298
Lesenswert?

Weil der Compiler uint8_t nicht als Datentyp kennt, denkt er Du möchtest 
einen Wert zuweisen. Vermutlich hast Du einfach das #include <..> für 
das .h-File vergessen, in dem der Typ uint8_t definiert ist.

Du solltest übrigens keine *.c Files per Include einbinden. Include ist 
für *.h Files. Wenn Du mehrere *.c Files brauchst, dann kannst Du die 
einzeln kompilieren und dann beim Linken alle *.o Files angeben oder Du 
gibst dem Compiler gleich eine Liste der *.c Files die er zu einem 
Executable machen soll. Schau Dir einfach mal ein x-beliebiges Makefile 
an, da kann man sehen wie das gemacht wird.
Gast #1190324
Lesenswert?

Man kann mit #include alles includen. Egal ob .h, .c, .txt, .schnitzel 
oder sonstwas. Der Praeprozessor fuegt den Teil einfach ein, basta - nur 
syntaktisch korrekt muss das Resultat sein.

Um Rolfs Problem zu loesen, muesste er schon ein wenig mehr zeigen. 
Mindestens das File das den include macht und das komplette test.c.
OP #1190339
Lesenswert?

Man kann mit #include alles includen. Egal ob .h, .c, .txt, .schnitzel
oder sonstwas. Der Praeprozessor fuegt den Teil einfach ein, basta - nur
syntaktisch korrekt muss das Resultat sein.

@ Peter Stegemann

das habe ich auch gemeint. mehr möchte ich auch nicht. in meiner 
referenz steht auch "Der Präprozessor entfernt die #include-Zeile und 
ersetzt sie durch den gesamten Quelltext der Include-Datei. Die 
Quelltextdatei selbst wird nicht physisch verändert, der Compiler erhält 
jedoch den modifizierten Text zur Übersetzung. "

dem scheint es aber nicht so zu sein...

hier ist gleich makefile

######################################################################## 
#######
# Makefile for the project projekt_1
######################################################################## 
#######

## General Flags
PROJECT = projekt_1
MCU = atmega644p
TARGET = projekt_1.elf
CC = avr-gcc

## Options common to compile, link and assembly rules
COMMON = -mmcu=$(MCU)

## Compile options common for all C compilation units.
CFLAGS = $(COMMON)
CFLAGS += -Wall -gdwarf-2 -Os -std=gnu99 -funsigned-char 
-funsigned-bitfields -fpack-struct -fshort-enums
CFLAGS += -MD -MP -MT $(*F).o -MF dep/$(@F).d

## Assembly specific flags
ASMFLAGS = $(COMMON)
ASMFLAGS += $(CFLAGS)
ASMFLAGS += -x assembler-with-cpp -Wa,-gdwarf2

## Linker flags
LDFLAGS = $(COMMON)
LDFLAGS +=  -SRC=$(TARGET).c-globals.c  -Wl,-Map=projekt_1.map


## Intel Hex file production flags
HEX_FLASH_FLAGS = -R .eeprom -R .fuse -R .lock -R .signature

HEX_EEPROM_FLAGS = -j .eeprom
HEX_EEPROM_FLAGS += --set-section-flags=.eeprom="alloc,load"
HEX_EEPROM_FLAGS += --change-section-lma .eeprom=0 --no-change-warnings


## Objects that must be built in order to link
OBJECTS = projekt_1.o globals.o

## Objects explicitly added by the user
LINKONLYOBJECTS =

## Build
all: $(TARGET) projekt_1.hex projekt_1.eep projekt_1.lss size

## Compile
projekt_1.o: ../projekt_1.c
  $(CC) $(INCLUDES) $(CFLAGS) -c  $<

globals.o: ../globals.c
  $(CC) $(INCLUDES) $(CFLAGS) -c  $<

##Link
$(TARGET): $(OBJECTS)
   $(CC) $(LDFLAGS) $(OBJECTS) $(LINKONLYOBJECTS) $(LIBDIRS) $(LIBS) -o 
$(TARGET)

%.hex: $(TARGET)
  avr-objcopy -O ihex $(HEX_FLASH_FLAGS)  $< $@

%.eep: $(TARGET)
  -avr-objcopy $(HEX_EEPROM_FLAGS) -O ihex $< $@ || exit 0

%.lss: $(TARGET)
  avr-objdump -h -S $< > $@

size: ${TARGET}
  @echo
  @avr-size -C --mcu=${MCU} ${TARGET}

## Clean target
.PHONY: clean
clean:
  -rm -rf $(OBJECTS) projekt_1.elf dep/* projekt_1.hex projekt_1.eep 
projekt_1.lss projekt_1.map


## Other dependencies
-include $(shell mkdir dep 2>/dev/null) $(wildcard dep/*)
Angehängte Dateien:
#1190341
Lesenswert?

Um es mal zu präzisieren:
Die übliche Vorgehensweise, um syntaktische Probleme zu vermeiden, ist 
das erstellen einer Headerdatei (*.h) zu jeder .c-Datei, in der sich 
ausschließlich Deklarationen (jedoch keine Definitionen ) aller 
Objekte befinden, die in der dazugehörigen .c-Datei definiert sind und 
die für andere Module (andere .c-Dateien) sichtbar sein sollen. Und nur 
die .h-Dateien werden dann mit #include eingebunden.

Außer Variablen-/Funktionsdeklarationen können in Headerdateien auch 
Typdfinitionen (typedef) und Präprozessormakros stehen. Das war es dann 
aber auch schon fast...

Normalerweise bindet man Quelldateien tatsächlich nicht mit #include 
ein. Klar, man kann alles einbinden, aber nur in wenigen Fällen macht 
das Sinn.
Gast #1190351
Lesenswert?

Rolf Riller wrote:

> @ Peter Stegemann

> dem scheint es aber nicht so zu sein...

Doch doch, dein projekt_1.c uebersetzt auch einwandfrei. Nur hast du 
globals.c nochmal separat im Projekt - und das File alleine kann der 
Compiler so nicht uebersetzen. Und selbst wenn er koennte, du haettest 
den Inhalt dann doppelt, was beim Linken wieder krachen duerfte, weil du 
so doppelte Symbole bekommst. Ach das liesse sich loesen, fuehrt aber 
hier wohl zu weit...

Man kann zwar mit #include machen was man moechte, wenn man aber nicht 
genau weiss, was man tut, haelt man sich besser an die von Johannes 
beschriebenen Konventionen ;-)

Ich denke was du willst ist ein globals.c, das selbstaendig uebersetzt 
(also alle noetigen includes machen!) und ein globals.h, dass die 
Variablen extern deklariert und von den anderen Dateien eingebunden 
wird. Wie ....... schon schrieb, muss das mehrfach hier im Forum 
beschrieben sein.
OP #1190449
Lesenswert?

also ich kriegs nicht auf die reihe.

kann mir jemand ein tutoriallink geben wo erklärt wird wie man diese 
problematik bewerkstelligt:

--- hauptfile.c -----
int main()
  {
    var_1 = 1;
    var_2 = 1;
    func_1();
    func_2();
  }

--- module_1.c ------
int var_1;
void func_1()
  {
    var_2 = 1;
    func_2();
  }

--- module_2.c -------
int var_2;
void func_2()
  {
    var_1 = 1;
    func_1();
  }

was ich möchte ist dass man "kreuz und querz" aufrufe tätigen kann, wie 
man das von php oder vb.net kennt. dort includet man das nötige modul 
mit seinen funktionen und variablen und gut ist es. meine hausaufgaben 
habe ich schon gemacht nämlich sämtliche foren durchsucht usw. da wird 
zwar viel geredet aber nichts konkretes.

danke im voraus
Persönliche Seite #1190456
Lesenswert?

Einfach:

--- hauptfile.c -----
#include "module_1.h"
#include "module_2.h"

int main()
  {
    var_1 = 1;
    var_2 = 1;
    func_1();
    func_2();
  }

--- module_1.c ------
#include "module_2.h"

int var_1;
void func_1()
  {
    var_2 = 1;
    func_2();
  }

--- module_2.c -------
#include "module_1.h"

int var_2;
void func_2()
  {
    var_1 = 1;
    func_1();
  }

--- module_1.h ------
extern int var_1;
void func_1();

--- module_2.h -------
extern int var_2;
void func_2();
#1190469
Lesenswert?

zunächst mal überlegst du dir, welche Informationen für module_1.c bzw. 
module_2.c 'nach aussen' sichtbar sein sollen.

Für module_1.c sind das
  * Es gibt eine Variable var_1
  * Es gibt eine Funktion func_1

Für module_2.c sind das
  * Es gibt eine Variable var_2
  * Es gibt eine Funktion func_2

Dann legst du dir für jedes der beiden *.c Files ein entsprechendes 
Header File an. Sinnvollerweise nennt man das Header File gleich wie das 
zugehörige *.c File, nur kriegt es die Endung *.h

In diese Header Files kommen die Deklarationen für alle Dinge, die vom 
*.c File exportiert werden, also von aussen sichtbar sein sollen

In deinem Beispiel sind das

--- module_1.h ------
1
extern int var_1;
2

3
void func_1();

und

--- module_2.h -------
1
extern int var_2;
2
void func_2();

Wie werden sie jetzt verwendet?
Ganz einfach.
Jedes *.c, dass eine Funktionalität aus einem anderen *.c benutzen will, 
includiert das entsprechende Header File. Sinnvollerweise wird das 
definierende C-File auch sein eigenes Header File includieren. Damit 
ermöglicht man dem Compiler eine gewisse Prüfung, ob beides auch 
zusammenstimmt und wenn man eigene Datentypen definiert (Strukture, 
Unions) führt sowieso an diesem Include kein Weg vorbei

Konkret:

--- hauptfile.c -----
1
#include "module_1.h"    // stellt var_1  und func_1  bereit
2
#include "module_2.h"    // stellt var_2  und func_2  bereit
3

4
int main()
5
{
6
  var_1 = 1;
7
  var_2 = 1;
8
  func_1();
9
  func_2();
10
}

--- module_1.c ------
1
#include "module_1.h"
2

3
int var_1;
4
void func_1()
5
{
6
  var_2 = 1;
7
  func_2();
8
}

--- module_2.c -------
1
#include "module_2.h"
2
#include "module_1.h"   // weil ja var_1 und func_1 benutzt werden sollen
3

4
int var_2;
5
void func_2()
6
{
7
  var_1 = 1;
8
  func_1();
9
}

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren