diff --git a/cmake/Modules/Generate.cmake b/cmake/Modules/Generate.cmake index 6a54baf631..d27de33310 100644 --- a/cmake/Modules/Generate.cmake +++ b/cmake/Modules/Generate.cmake @@ -25,6 +25,12 @@ function(IDLC_GENERATE) endif() set(_idlc_depends CycloneDDS::libidlc) else() + if (CMAKE_HOST_SYSTEM_NAME STREQUAL "Linux" AND NOT ".so" IN_LIST CMAKE_FIND_LIBRARY_SUFFIXES) + # When cross-compiling, find_library looks for libraries using naming onventions of the target, + # But here we're trying to find the idlc backend library to run on the host. + # For now, building for a Windows target on a Linux host with w64-mingw is supported by this workaround. + list(APPEND CMAKE_FIND_LIBRARY_SUFFIXES ".so") + endif() find_library(_idlc_backend "cycloneddsidlc" NO_CMAKE_FIND_ROOT_PATH) if (_idlc_backend) if (NOT DEFINED _idlc_generate_skipreport) diff --git a/examples/roundtrip/ping.c b/examples/roundtrip/ping.c index 244c4470df..f96c25d13f 100644 --- a/examples/roundtrip/ping.c +++ b/examples/roundtrip/ping.c @@ -108,7 +108,7 @@ static dds_time_t exampleGet99PercentileFromTimeStats (ExampleTimeStats *stats) static dds_entity_t waitSet; #ifdef _WIN32 -#include +#include static bool CtrlHandler (DWORD fdwCtrlType) { (void)fdwCtrlType; diff --git a/examples/roundtrip/pong.c b/examples/roundtrip/pong.c index 8ad28350e0..169118492c 100644 --- a/examples/roundtrip/pong.c +++ b/examples/roundtrip/pong.c @@ -15,7 +15,7 @@ static dds_entity_t prepare_dds(dds_entity_t *writer, dds_entity_t *reader, dds_ static void finalize_dds(dds_entity_t participant, RoundTripModule_DataType data[MAX_SAMPLES]); #ifdef _WIN32 -#include +#include static bool CtrlHandler (DWORD fdwCtrlType) { (void)fdwCtrlType; diff --git a/ports/mingw-w64/Dockerfile b/ports/mingw-w64/Dockerfile new file mode 100644 index 0000000000..6fddc8a62f --- /dev/null +++ b/ports/mingw-w64/Dockerfile @@ -0,0 +1,42 @@ +ARG ARCH=x86_64 + +FROM ubuntu:24.04 AS build +# supports x86_64 or i686 +ARG ARCH + +RUN apt-get update && DEBIAN_FRONTEND=noninteractive apt-get install -y -q\ + build-essential \ + cmake \ + mingw-w64 + +WORKDIR /project +COPY --link . src + +# Host build, only for idlc (+ libidlc) but building individual targets doesn't really work... +RUN cmake -S src -B host-build +RUN cmake --build host-build --parallel +RUN cmake --install host-build --prefix /project/install + +# Cross build with mingw-w64 toolchain +RUN cmake -S src -B build \ + -DBUILD_EXAMPLES=1 \ + -DCMAKE_TOOLCHAIN_FILE=/project/src/ports/mingw-w64/mingw-w64-${ARCH}.cmake \ + -DCMAKE_PREFIX_PATH=/project/install +RUN cmake --build build --parallel +RUN cmake --install build + +FROM ubuntu:24.04 +ARG ARCH + +RUN if [ "${ARCH}" = "i686" ]; then \ + dpkg --add-architecture i386; \ + apt-get update && DEBIAN_FRONTEND=noninteractive apt-get install -y -q mingw-w64 wine wine32:i386; \ + echo "export WINEARCH=win32" >> /etc/bash.bashrc; \ + else \ + apt-get update && DEBIAN_FRONTEND=noninteractive apt-get install -y -q mingw-w64 wine; \ + fi + +COPY --from=build /usr/local/bin /usr/local/bin +COPY --from=build /usr/local/lib /usr/local/lib +COPY --from=build /usr/local/include /usr/local/include +COPY --from=build /project/build/bin /usr/local/bin diff --git a/ports/mingw-w64/mingw-w64-i686.cmake b/ports/mingw-w64/mingw-w64-i686.cmake new file mode 100644 index 0000000000..5c2d670ddb --- /dev/null +++ b/ports/mingw-w64/mingw-w64-i686.cmake @@ -0,0 +1,13 @@ +set(CMAKE_SYSTEM_NAME Windows) +set(CMAKE_SYSTEM_PROCESSOR i686) + +set(TOOLCHAIN_PREFIX i686-w64-mingw32) + +set(CMAKE_C_COMPILER ${TOOLCHAIN_PREFIX}-gcc) +set(CMAKE_CXX_COMPILER ${TOOLCHAIN_PREFIX}-g++) + +set(CMAKE_FIND_ROOT_PATH /usr/${TOOLCHAIN_PREFIX}) + +set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) +set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) +set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) diff --git a/ports/mingw-w64/mingw-w64-x86_64.cmake b/ports/mingw-w64/mingw-w64-x86_64.cmake new file mode 100644 index 0000000000..af65043769 --- /dev/null +++ b/ports/mingw-w64/mingw-w64-x86_64.cmake @@ -0,0 +1,13 @@ +set(CMAKE_SYSTEM_NAME Windows) +set(CMAKE_SYSTEM_PROCESSOR x86_64) + +set(TOOLCHAIN_PREFIX x86_64-w64-mingw32) + +set(CMAKE_C_COMPILER ${TOOLCHAIN_PREFIX}-gcc) +set(CMAKE_CXX_COMPILER ${TOOLCHAIN_PREFIX}-g++) + +set(CMAKE_FIND_ROOT_PATH /usr/${TOOLCHAIN_PREFIX}) + +set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) +set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) +set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) diff --git a/src/ddsrt/include/dds/ddsrt/types/windows.h b/src/ddsrt/include/dds/ddsrt/types/windows.h index 2752a55249..b8f4b465ba 100644 --- a/src/ddsrt/include/dds/ddsrt/types/windows.h +++ b/src/ddsrt/include/dds/ddsrt/types/windows.h @@ -20,11 +20,13 @@ #endif #include -#include +#include #include #include #include +#ifdef _MSC_VER typedef SSIZE_T ssize_t; +#endif #endif /* DDSRT_TYPES_WINDOWS_H */ diff --git a/src/ddsrt/src/netstat/windows/netstat.c b/src/ddsrt/src/netstat/windows/netstat.c index 967988f359..511357c52a 100644 --- a/src/ddsrt/src/netstat/windows/netstat.c +++ b/src/ddsrt/src/netstat/windows/netstat.c @@ -6,7 +6,7 @@ #ifndef WIN32_LEAN_AND_MEAN #define WIN32_LEAN_AND_MEAN #endif -#include +#include #include #include diff --git a/src/ddsrt/src/sockets/windows/socket.c b/src/ddsrt/src/sockets/windows/socket.c index 0458374168..e771527536 100644 --- a/src/ddsrt/src/sockets/windows/socket.c +++ b/src/ddsrt/src/sockets/windows/socket.c @@ -20,7 +20,7 @@ #include "dds/ddsrt/time.h" // Has to be included after most of windows has been included, it seems -#include +#include #ifdef ddsrt_select #undef ddsrt_select /* See sockets.h for details. */ diff --git a/src/tools/idlc/src/idlc/generator.c b/src/tools/idlc/src/idlc/generator.c index c70d4776c2..865b312fb0 100644 --- a/src/tools/idlc/src/idlc/generator.c +++ b/src/tools/idlc/src/idlc/generator.c @@ -16,7 +16,7 @@ #include #if WIN32 -#include +#include static const char sep[] = "/\\"; static const char lib[] = "cyclonedds"; static const char ext[] = "dll";