cesanta / mongoose

Embedded Web Server
https://mongoose.ws
Other
11.16k stars 2.73k forks source link

Can't compile 7.5 with MinGW since gmtime_r and localtime_r definitions #1435

Closed marcelwirtz closed 2 years ago

marcelwirtz commented 2 years ago

I tried to upgrade from Mongoose Version 7.3 to 7.5 but every time i try to compile i get the compile error below.

C:\PROJECTS\CPP\libmgwebserver\src\server\mongoose.h:454: In file included from ..\src\server\mongoose.h:454, In file included from ..\src\server\mongoose.h:454, from ..\src\server\mongoose.c:18: C:/Qt/Tools/mingw810_32/i686-w64-mingw32/include/time.h:312:34: note: previous definition of 'gmtime_r' was here forceinline struct tm *cdecl gmtime_r(const time_t _Time, struct tm _Tm) {

Is there sth. i can do? 7.3 worked like a charm but used normal gmtime and localtime which should be thread safe already on Windows if i got this right.

I wish you happy holidays and a happy new year.

Kind regards, Marcel

cpq commented 2 years ago

The make mingw target runs a unit test using mingw compiler, and it works fine. Which mingw version do you use? I think I'll ban people who ignore issue questions, which ask about the compiler. Why did you ignore it and force me to spend my time on this round-trip?

marcelwirtz commented 2 years ago

To be honest it wasn't on purpose to ignore it. I copy and pasted the error message which also deleted the questions, got distracted by a phone call and forgot about it because i had to do other stuff first. So sorry about that!

Hope thats all things you need to know besides the error message above.

What i already tested yesterday:

if i put

#ifdef _POSIX_THREAD_SAFE_FUNCTIONS
    #warning "With POSIX"
#else
    #warning "Without POSIX"
#endif

right before the implementations in mongoose.h, to see if the POSIX functions from time.h to be used. I am getting the output in the screenshot which i can't explain why the first time POSIX isn't used and then it is a few times.

warnings

Kind regards and again sorry for the inconvenience, Marcel

cpq commented 2 years ago

In Mongoose's make mingw the GCC 9.3.0 is used:

$ docker run --rm -e Tmp=. -e WINEDEBUG=-all -v /home/cpq/src/mongoose:/home/cpq/src/mongoose -w /home/cpq/src/mongoose mdashnet/mingw i686-w64-mingw32-gcc -v
Target: i686-w64-mingw32
...
gcc version 9.3.0 (GCC) 

The make mingwtriggers the following command:

$ make mingw
docker run --rm -e Tmp=. -e WINEDEBUG=-all -v /home/cpq/src/mongoose:/home/cpq/src/mongoose -w /home/cpq/src/mongoose mdashnet/mingw i686-w64-mingw32-gcc mongoose.c test/unit_test.c test/packed_fs.c -W -Wall -Werror -I. -DMG_MAX_HTTP_HEADERS=7 -DMG_ENABLE_LINES -DMG_ENABLE_PACKED_FS=1 -lwsock32 -o test.exe

So my guess is that on your system, some build options enable _r functions, hence you get a conflict. The right way to fix that would be to guard the appropriate block in src/arch_win32.h. If you can find which preprocessor definition switches on those _r functions, that'll be great.

nnieddu commented 2 years ago

Hello @marcelwirtz,

Just try compiling with clang and without the "-D_POSIX_C_SOURCE=200000L" :

clang ../../mongoose.c main.c -I../.. -W -Wall -DMG_ENABLE_LINES=1 -lws2_32 -o mongoose.exe (you can use gcc, it's working too but produce some warning for me).

Tested today with last mongoose(7.5) release and GCC 11.2.0 + LLVM/Clang/LLD/LLDB 13.0.0 + MinGW-w64 9.0.0 . Everything seems working well (i don't try with Openssl but can confirm with Mbedtls it's working). (just download winlib archive "extract where you want/mingw64/bin/" and add the pathto this folder to your PATH env variable).

marcelwirtz commented 2 years ago

Hey guys, thanks for helping out. Since I can't get rid of POSIX definitions as they come from the Qt framework that we use and the functions come from time.h where they are enabled with _POSIX_THREAD_SAFE_FUNCTIONS define, i guarded the definitions in mongoose.h with this, whats seems to work for me.

#ifndef _POSIX_THREAD_SAFE_FUNCTIONS
// https://lgtm.com/rules/2154840805/ -gmtime, localtime, ctime and asctime
static __inline struct tm *gmtime_r(time_t *t, struct tm *tm) {
  (void) tm;
  return gmtime(t);
}

static __inline struct tm *localtime_r(time_t *t, struct tm *tm) {
  (void) tm;
  return localtime(t);
}
#endif

I don't know if it's possible to do that by default but anyway thanks for pointing that out.

Kind regards and merry christmas to you, Marcel

bing2008 commented 2 years ago

Hey @marcelwirtz ,this is my bad. I was just test the version in my env (mingw32) , that's make the issue. see: https://github.com/cesanta/mongoose/discussions/1408#discussioncomment-1812139