Problem mit "extern" und "multiple definition"

Hallo!

Ich habe folgendes Projekt das ziemlich Probleme macht, ich will eine Zentrale "Datenbank" als struct, habe das offizielle "struct" auch als extern deklariert, da es von diversen CPPs geändert/gelesen werden soll, leider klappt das nicht:

database.h

#pragma once
#ifndef DATABASE_H
#define DATABASE_H

#include <Arduino.h>

typedef struct module{
    String moduleName;
    int moduleChannels;
    int moduleExtensions;
    String moduleAddress;
    String moduleIP;
    String moduleVersion;
    float module_battery;
    int module_rssi;
} module;

typedef struct moduleDatabase{
    module _module;
    String moduleAddress;
    int online;
    unsigned long last_ping;
} moduleDatabase;

extern moduleDatabase database[24] = {};

#endif

main.cpp

#include <Arduino.h>
#include "main.h"
#include "database.h"

void parseMod(module mod)
{
}

void setup() {
// put your setup code here, to run once:
}

void loop() {
// put your main code here, to run repeatedly:
}

test.cpp:

#include "test.h"

Test::Test(void)
{}

void Test::addModule(module mod)
{
}

test.h:

#ifndef TEST_H
#define TEST_H
#include "database.h"
class Test
{
    Test(void);
    void addModule(module mod);
};

#endif

Mein Compiler wirft mir folgende Fehlermeldung aus:

In file included from src/main.cpp:3:0:
src/database.h:26:34: warning: 'database' initialized and declared 'extern'
 extern moduleDatabase database[24] = {};
                                  ^
In file included from src/test.h:3:0,
                 from src/test.cpp:1:
src/database.h:26:34: warning: 'database' initialized and declared 'extern'
 extern moduleDatabase database[24] = {};
                                  ^
Linking .pio/build/esp32dev/firmware.elf
.pio/build/esp32dev/src/test.cpp.o:(.bss.database+0x0): multiple definition of `database'
.pio/build/esp32dev/src/main.cpp.o:(.bss.database+0x0): first defined here
collect2: error: ld returned 1 exit status
*** [.pio/build/esp32dev/firmware.elf] Error 1

entferne ich das "include" aus der "test.h" wird mein struct "module" in der Class nicht mehr erkannt.

Ich will aber über die Main und über die Test.cpp auf die "database" zugreifen, das geht ja nur wenn ich die "database.h" entsprechend include, aber darf das laut compiler nicht?

Vielleicht kann mir ja jemand helfen.... :slight_smile:

Grüße,
Daniel

Hier solltest du dich für einen Include Guard entscheiden, nicht beide verwenden.

Das ist alter C Stil, das typedef ist da nicht nötig.

Entscheide dich!
Entweder eine extern Deklaration, oder eine Definition, ohne extern.

Du musst Definition und Deklaration unterscheiden. Extern deklariert eine Variable die schon mal an anderer Stelle definiert wurde.

Generell ändere mal das:

typedef struct module{
...
} module;

typedef struct moduleDatabase{
...
} moduleDatabase;

Zu:

struct Module{
...
};

struct ModuleDatabase{
...
};

Typedef struct ist eher eine C Sache. Braucht man in C++ normalerweise nicht, da das implizit schon gemacht wird

Und Strukturen/Klassen fängt man normal mit Großbuchstaben an. Geht aber so oder so

Moin!

vielen Dank für die Infos, habe ich jetzt korrigiert, man sollte eventuell mal den Warnings des Compilers folgen... :wink:

In der Tat funktioniert es ohne Initialisierung deutlich besser! :wink:

extern struct moduleDatabase database[24];

vielen Dank!

Vergiss doch bitte den alten C Stil, wenn du dich in der C++ Welt bewegst.

Sorry, ich versuche mich daran zu gewöhnen :wink: programmiere hauptsächlich in der C Welt...

extern ModuleDatabase database[24];

Wäre natürlich korrekt! :wink:

This topic was automatically closed 120 days after the last reply. New replies are no longer allowed.