предварительная обработка для TaskScheduler-Library не работает - ошибка множественного определения - PullRequest
0 голосов
/ 11 мая 2018

У меня проблемы с получением нескольких определений errors для всей библиотеки.Как только я включаю библиотеку TaskScheduler в другую header-file (кроме .ino), я получаю error.

Для пояснения: ниже не приведен мой фактический код, который яхочу быть исправленным!Я уменьшил его до минимума, который все еще имеет error (проверено в Eclipse sloeber и Arduino IDE ):

Project.ino:

#include <TaskScheduler.h>
#include "WifiHelper.h"

void setup(){}
void loop(){}

WifiHelper.h:

#ifndef WIFIHELPER_H_
#define WIFIHELPER_H_

#include <TaskScheduler.h>

#endif /* WIFIHELPER_H_ */

WifiHelper.cpp:

#include "Wifihelper.h"

Вы можете скачать проект здесь .

Так зачем мне сюда дважды включать TaskScheduler.h?Ну, класс WifiHelper.h получает указатель типа Scheduler и инициирует Task с ним в файле WifiHelper.cpp в его конструкторе WifiHelper::WifiHelper(std::shared_prt<Scheduler> scheduler){...}.

TaskScheduler.h имеет препроцессорзаявление, и я действительно не понимаю, почему я сталкиваюсь с этой проблемой здесь.В моем первоначальном проекте я использую несколько других библиотек, как указано выше, и все работает отлично.В заключение мне интересно, если это проблема с библиотекой ...

Заранее спасибо:)

Часть errormessage:

'Starting combiner'
"C:/Users/Mimi/Documents/Arduino/hardware/espressif/esp32/tools/xtensa/esp32-elf/bin/xtensa-esp32-elf-gcc" -nostdlib "-LC:/Users/Mimi/Documents/Arduino/hardware/espressif/esp32/tools/sdk/lib" "-LC:/Users/Mimi/Documents/Arduino/hardware/espressif/esp32/tools/sdk/ld" -T esp32_out.ld -T esp32.common.ld -T esp32.rom.ld -T esp32.peripherals.ld -T esp32.rom.spiram_incompatible_fns.ld -u ld_include_panic_highint_hdl -u call_user_start_cpu0 -Wl,--gc-sections -Wl,-static -Wl,- undefined=uxTopUsedPriority -u __cxa_guard_dummy -u __cxx_fatal_exception -Wl,--start-group    .\WifiHelper.cpp.o .\sloeber.ino.cpp.o   "C:/Users/Mimi/eclipse-workspaces/esp32/Project2/Release/arduino.ar" -lgcc -lopenssl -lbtdm_app -lfatfs -lwps -lcoexist -lwear_levelling -lhal -lnewlib -ldriver -lbootloader_support -lpp -lmesh -lsmartconfig -ljsmn -lwpa -lethernet -lphy -lapp_trace -lconsole -lulp -lwpa_supplicant -lfreertos -lbt -lmicro-ecc -lcxx -lxtensa-debug-module -lmdns -lvfs -lsoc -lcore -lsdmmc -lcoap -ltcpip_adapter -lc_nano -lrtc -lspi_flash -lwpa2 -lesp32 -lapp_update -lnghttp -lspiffs -lespnow -lnvs_flash -lesp_adc_cal -llog -lexpat -lm -lc -lheap -lmbedtls -llwip -lnet80211 -lpthread -ljson -lstdc++ -Wl,--end-group -Wl,-EL -o "C:/Users/Mimi/eclipse-workspaces/esp32/Project2/Release/Project2.elf" C:/Users/Mimi/eclipse-workspaces/esp32/Project2/Release/arduino.ar
.\sloeber.ino.cpp.o: In function `Task::isEnabled()':
C:\Users\Mimi\Documents\Arduino\libraries\TaskScheduler\src/TaskScheduler.h:312: multiple definition of `Task::isEnabled()'
.\WifiHelper.cpp.o:C:\Users\Mimi\Documents\Arduino\libraries\TaskScheduler\src/TaskScheduler.h:312: first defined here
.\sloeber.ino.cpp.o: In function `Task::getInterval()':
sloeber.ino.cpp:(.text._ZN4Task11getIntervalEv+0x0): multiple definition of `Task::getInterval()'
.\WifiHelper.cpp.o:WifiHelper.cpp:(.text._ZN4Task11getIntervalEv+0x0): first defined here
.\sloeber.ino.cpp.o: In function `Task::getIterations()':

и так далее, и так далее - если вы хотите увидеть полное сообщение, нажмите здесь ... в конце концов, не запутайтесь в Project2.ino.Я просто попробовал это в другом проекте с теми же файлами.

1 Ответ

0 голосов
/ 11 мая 2018

В C / C ++, если вы определяете функцию внутри 2 отдельных «модулей перевода» (т.е. файлов «.cpp»), вы получите эту ошибку, потому что компоновщик не знает, какой из них использовать для конечной программы.

Ваш Project.ino, похоже, компилируется как собственный модуль перевода - «sloeber.ino.cpp», поэтому, если у вас есть одинаковое определение функции, включенное в WifiHelper.cpp и sloeber.ino.cpp, вы получите эту ошибку.

Сначала убедитесь, что вы не включили материал дважды. Чтобы быть абсолютно уверенным, вы можете добавить охрану вокруг вашего #include:

#ifndef TASK_SCHEDULER_H_INCLUDED
#define TASK_SCHEDULER_H_INCLUDED
#include <TaskScheduler.h>
#endif // TASK_SCHEDULER_H_INCLUDED

Глядя на исходный код здесь - https://github.com/arkhipenko/TaskScheduler/blob/master/src/TaskScheduler.h

это явно не предполагалось включать дважды.

Но там есть еще один файл - TaskSchedulerDeclarations.h , который может быть включен несколько раз, поэтому, возможно, попробуйте использовать этот файл в других ваших файлах.

Если это не помогает, есть другие обходные пути:

  1. перемещает определения библиотечных функций из файла .h в файлы .cpp и хранит объявления функций только в файлах .h (хотя это может быть большой работой)
  2. или добавьте «static» перед определениями функций, которые будут отображать их как локальные для модуля перевода (один файл cpp), в этом случае не является ошибкой иметь несколько из них во всей программе.
...