as assume i have the following:
DateCalc.h
#ifndef E4345519_327E_4EF6_9F7F_17FC0BA48B93
#define E4345519_327E_4EF6_9F7F_17FC0BA48B93
#include <stdint.h>
#include <time.h>
int isLeapYear(int year)
{
year = year <= 1900 ? year + 1900 : year;
return ((year % 4) == 0) && (((year % 100) != 0) || ((year % 400) == 0));
}
int numDayInMonth(const int year, const int month)
{
const int leap_year = isLeapYear(year) ? 1 : 0;
int num_of_days = 0;
const int num_day_in_month[12] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
if (month == 2)
{
num_of_days = num_day_in_month[1] + leap_year;
}
else
{
num_of_days = num_day_in_month[month - 1];
}
return num_of_days;
}
int dayOfWeek(int year, int month, int day)
{
year = year <= 1900 ? year + 1900 : year;
const static int t[] = {0, 3, 2, 5, 0, 3, 5, 1, 4, 6, 2, 4};
year -= month < 3;
return (year + year / 4 - year / 100 + year / 400 + t[month - 1] + day) % 7;
}
int16_t dayOfYear(int16_t year, int16_t month, int16_t day)
{
// Add the days in the previous months
while (month-- > 0)
{
day = day + numDayInMonth(year, month); // num_day_in_month[month - 1];
}
return day - 1;
}
int bounds(const int v, const int minVal, const int maxVal, const int dir)
{
const int value = v + dir;
if (dir > 0)
{
return value > maxVal ? minVal : value;
}
else
{
return value < minVal ? maxVal : value;
}
}
tm complete_tm(const tm dtv)
{
tm ltm = dtv;
ltm.tm_wday = dayOfWeek(ltm.tm_year, ltm.tm_mon, ltm.tm_mday);
ltm.tm_yday = dayOfYear(ltm.tm_year, ltm.tm_mon, ltm.tm_mday);
ltm.tm_isdst = 0;
return ltm;
}
tm changeYear(const tm dtv, const int dir)
{
tm ltm = dtv;
ltm.tm_year = bounds(ltm.tm_year, 0, 999, dir);
ltm = complete_tm(ltm);
return ltm;
}
tm changeMonth(const tm dtv, const int dir)
{
tm ltm = dtv;
ltm.tm_mon = bounds(dtv.tm_mon, 0, 11, dir);
ltm = complete_tm(ltm);
return ltm;
}
tm changeDay(const tm dtv, const int dir)
{
tm ltm = dtv;
const int maxDays = numDayInMonth(dtv.tm_year, dtv.tm_mon);
ltm.tm_mday = bounds(dtv.tm_mday, 1, maxDays, dir);
ltm = complete_tm(ltm);
return ltm;
}
tm changeHour(const tm dtv, const int dir)
{
tm ltm = dtv;
ltm.tm_hour = bounds(dtv.tm_hour, 0, 23, dir);
ltm = complete_tm(ltm);
return ltm;
}
tm changeMinute(const tm dtv, const int dir)
{
tm ltm = dtv;
ltm.tm_min = bounds(dtv.tm_min, 0, 59, dir);
ltm = complete_tm(ltm);
return ltm;
}
tm changeSecond(const tm dtv, const int dir)
{
tm ltm = dtv;
ltm.tm_sec = 0;
ltm = complete_tm(ltm);
return ltm;
}
char *toString(const tm dtv, char *buffer, size_t sz)
{
tm ltm = dtv;
strftime(buffer, sz, "%d/%m/%y %H:%M:%S", <m);
return buffer;
}
long differenceInSeconds(const tm start, const tm end)
{
tm f_ltm = start;
tm t_ltm = end;
const time_t from = mktime(&f_ltm);
const time_t to = mktime(&t_ltm);
const double diff = difftime(to, from);
return (long)diff;
}
#endif /* E4345519_327E_4EF6_9F7F_17FC0BA48B93 */
TMWrapper.h
#ifndef C82E444B_1CB6_45C6_B8FD_DD8BC278857C
#define C82E444B_1CB6_45C6_B8FD_DD8BC278857C
#include <DateCalc.h>
class TMWrapper
{
public:
TMWrapper(const int year, const int month, const int day, const int hour = 0, const int minute = 0, const int second = 0, const bool isDst = false) : _tm{.tm_sec = second, .tm_min = minute, .tm_hour = hour, .tm_mday = day, .tm_mon = month, .tm_year = year, .tm_wday = 0, .tm_yday = 0, .tm_isdst = 0}
{
_tm = complete_tm(_tm);
}
explicit TMWrapper(const tm tm) : _tm(tm)
{
_tm = complete_tm(_tm);
}
void modifyYear(const int delta)
{
_tm = changeYear(_tm, delta);
}
void modifyMonth(const int delta)
{
_tm = changeMonth(_tm, delta);
}
void modifyDay(const int delta)
{
_tm = changeDay(_tm, delta);
}
void modifyHour(const int delta)
{
_tm = changeHour(_tm, delta);
}
void modifyMinute(const int delta)
{
_tm = changeMinute(_tm, delta);
}
void modifySecond(const int delta)
{
_tm = changeSecond(_tm, delta);
}
int year()
{
return _tm.tm_year + 1900;
}
int month()
{
return _tm.tm_mon + 1;
}
int day()
{
return _tm.tm_mday;
}
int hour()
{
return _tm.tm_mday;
}
int minute()
{
return _tm.tm_min;
}
int second()
{
return _tm.tm_sec;
}
char *toDateTimeString(char *buffer, const size_t sz)
{
return toString(_tm, buffer, sz);
}
long diff(TMWrapper tm)
{
return differenceInSeconds(_tm, tm._tm);
}
tm get_tm()
{
return _tm;
}
private:
tm _tm;
};
#endif /* C82E444B_1CB6_45C6_B8FD_DD8BC278857C */
RTCLibWrapper
#include <RTCLibWrapper.h>
void RTCLibWrapper::init()
{
if (!_rtcCtrl.begin())
{
while (1)
delay(10);
}
if (_rtcCtrl.lostPower())
{
_rtcCtrl.adjust(DateTime(F(__DATE__), F(__TIME__)));
}
}
DateTime fromDateTimeValue(TMWrapper dtv)
{
DateTime dt = DateTime(dtv.year(), dtv.month(), dtv.day(), dtv.hour(), dtv.minute(), dtv.second());
return dt;
}
TMWrapper toDateTimeValue(DateTime dt)
{
TMWrapper tm(dt.year(), dt.month(), dt.day(), dt.hour(), dt.minute(), dt.second(), false);
return tm;
}
TMWrapper RTCLibWrapper::now()
{
DateTime dt = _rtcCtrl.now();
return toDateTimeValue(dt);
}
void RTCLibWrapper::changeTime(TMWrapper dtv)
{
DateTime dt = fromDateTimeValue(dtv);
_rtcCtrl.adjust(dt);
}
RTCLibWrapper.h
#ifndef RTCLibWrapper_h
#define RTCLibWrapper_h
#include <IRTCLibWrapper.h>
#include <Wire.h>
#include <RTClib.h>
class RTCLibWrapper : public IRTCLibWrapper
{
public:
void init() override;
TMWrapper now() override;
void changeTime(TMWrapper dtv) override;
private:
RTC_DS3231 _rtcCtrl;
};
#endif
IRTCLibWrapper
#ifndef IRTCLibWrapper_h
#define IRTCLibWrapper_h
#include <TMWrapper.h>
class IRTCLibWrapper
{
public:
virtual void init() = 0;
virtual TMWrapper now() = 0;
virtual void changeTime(TMWrapper dtv) = 0;
};
#endif
and finally the main
#include <Arduino.h>
#include <Wire.h>
#include <RTCLibWrapper.h>
IRTCLibWrapper *_rtc = new RTCLibWrapper();
void setup()
{
}
void loop()
{
delay(200);
}
why whould i get multiple definition errors on main, originating on DateCalc?
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `isLeapYear(int)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:8: multiple definition of `isLeapYear(int)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:8: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `numDayInMonth(int, int)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:14: multiple definition of `numDayInMonth(int, int)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:14: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `dayOfWeek(int, int, int)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:30: multiple definition of `dayOfWeek(int, int, int)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:30: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `dayOfYear(short, short, short)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:38: multiple definition of `dayOfYear(short, short, short)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:38: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `bounds(int, int, int, int)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:48: multiple definition of `bounds(int, int, int, int)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:48: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `complete_tm(tm)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:61: multiple definition of `complete_tm(tm)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:61: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `changeYear(tm, int)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:70: multiple definition of `changeYear(tm, int)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:70: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `changeMonth(tm, int)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:78: multiple definition of `changeMonth(tm, int)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:78: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `changeDay(tm, int)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:86: multiple definition of `changeDay(tm, int)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:86: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `changeHour(tm, int)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:95: multiple definition of `changeHour(tm, int)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:95: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `changeMinute(tm, int)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:103: multiple definition of `changeMinute(tm, int)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:103: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `changeSecond(tm, int)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:110: multiple definition of `changeSecond(tm, int)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:110: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `toString(tm, char*, unsigned int)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:118: multiple definition of `toString(tm, char*, unsigned int)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:118: first defined here
c:/users/user/.platformio/packages/toolchain-xtensa-esp32@8.4.0+2021r2-patch5/bin/../lib/gcc/xtensa-esp32-elf/8.4.0/../../../../xtensa-esp32-elf/bin/ld.exe: .pio\build\debug\lib933\libRTCLibWrapper.a(RTCLibWrapper.cpp.o): in function `differenceInSeconds(tm, tm)':
C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:125: multiple definition of `differenceInSeconds(tm, tm)'; .pio\build\debug\src\main-debug.cpp.o:C:\Users\User\Documents\PlatformIO\Projects\JewishClock\HClock/lib/DateCalc/DateCalc.h:125: first defined here