Emscripten compilation issues
I'm getting this error when compiling with Emscripten:
solver.c:32:2: error: call to undeclared function '_mm_pause'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
Tried to add this to CMakeLists.txt:
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wno-implicit-function-declaration")
And I got this error:
wasm-ld: error: engine/libs/box2d/libbox2d.a(solver.c.o): undefined symbol: _mm_pause
So, I modified solver.c with code similar to miniaudio lib:
Instead of:
#if defined(B2_CPU_ARM)
static inline void b2Pause (void)
{
__asm__ __volatile__("isb\n");
}
#else
#include <immintrin.h>
static inline void b2Pause(void)
{
_mm_pause();
}
#endif
I changed to:
#if !defined(B2_CPU_ARM)
#include <immintrin.h>
#endif
static inline void b2Pause(void)
{
#if defined(__i386) || defined(_M_IX86) || defined(__x86_64__) || defined(_M_X64)
/* x86/x64 */
#if (defined(_MSC_VER) || defined(__WATCOMC__) || defined(__DMC__)) && !defined(__clang__)
#if _MSC_VER >= 1400
_mm_pause();
#else
#if defined(__DMC__)
/* Digital Mars does not recognize the PAUSE opcode. Fall back to NOP. */
__asm nop;
#else
__asm pause;
#endif
#endif
#else
__asm__ __volatile__ ("pause");
#endif
#elif (defined(__arm__) && defined(__ARM_ARCH) && __ARM_ARCH >= 7) || defined(_M_ARM64) || (defined(_M_ARM) && _M_ARM >= 7) || defined(__ARM_ARCH_6K__) || defined(__ARM_ARCH_6T2__)
/* ARM */
#if defined(_MSC_VER)
/* Apparently there is a __yield() intrinsic that's compatible with ARM, but I cannot find documentation for it nor can I find where it's declared. */
__yield();
#else
__asm__ __volatile__ ("yield"); /* ARMv6K/ARMv6T2 and above. */
#endif
#else
/* Unknown or unsupported architecture. No-op. */
#endif
}
And works now!
This page suggests a way to handle _mm_pause in WASM. https://emscripten.org/docs/porting/simd.html
This page suggests a way to handle _mm_pause in WASM. https://emscripten.org/docs/porting/simd.html
It says _mm_pause is "No-op.".
But anyway, the code from miniaudio that I am using is working.
The miniaudio solution has a lot of stuff. I'll be trying to build on Emscripten soon and will investigate.
@eduardodoria Your approach to those errors wasn't really correct.
In file included from /tmp/box2d/src/contact_solver.c:482:
/home/peter/.emscripten_cache/sysroot/include/compat/emmintrin.h:11:2: error: "SSE2 instruction set not enabled"
11 | #error "SSE2 instruction set not enabled"
| ^
The issue with the intrinsics is that -msse2 needs to be a compile option in order for that to compile.
Emscripten also wants -msimd128.
emcc: error: passing any of -msse, -msse2, -msse3, -mssse3, -msse4.1, -msse4.2, -msse4, -mavx, -mfpu=neon flags also requires passing -msimd128 (or -mrelaxed-simd)!
elseif (EMSCRIPTEN)
message(STATUS "Box2D on Emscripten")
+ target_compile_options(box2d PRIVATE -msimd128 -msse2)
elseif (UNIX)
This patch fixes that specific compiler error. -mavx2 seems to be unsupported.
The next error I see is:
/tmp/box2d/src/timer.c:192:8: error: use of undeclared identifier 'size_t'; did you mean 'sizeof'?
192 | for ( size_t i = 0; i < count; i++ )
| ^~~~~~
| sizeof
/tmp/box2d/src/timer.c:192:17: error: expression is not assignable
192 | for ( size_t i = 0; i < count; i++ )
| ~~~~~~~~ ^
But this is just a normal problem with depending on a transitive include, including stddef.h in timer.c solved it for me.
Also, for emscripten, building the samples doesn't currently work, because of FetchContent_MakeAvailable(glfw). This fails likeso:
-- Checking for modules 'wayland-client>=0.2.7;wayland-cursor>=0.2.7;wayland-egl>=0.2.7;xkbcommon>=0.5.0'
-- Package 'wayland-client', required by 'virtual:world', not found
-- Package 'wayland-cursor', required by 'virtual:world', not found
-- Package 'wayland-egl', required by 'virtual:world', not found
-- Package 'xkbcommon', required by 'virtual:world', not found
CMake Error at /usr/share/cmake/Modules/FindPkgConfig.cmake:645 (message):
The following required packages were not found:
- wayland-client>=0.2.7
- wayland-cursor>=0.2.7
- wayland-egl>=0.2.7
- xkbcommon>=0.5.0
Call Stack (most recent call first):
/usr/share/cmake/Modules/FindPkgConfig.cmake:873 (_pkg_check_modules_internal)
build/_deps/glfw-src/src/CMakeLists.txt:164 (pkg_check_modules)
https://emscripten.org/docs/compiling/Contrib-Ports.html
For raylib, we are using the javascript glfw implementation mentioned here, link with -sUSE_GLFW=3 instead of downloading and building glfw for that circumstance.
@Peter0x44 you are correct.
Just added target_compile_options(box2d PRIVATE -msimd128 -msse2) and include stddef.h fixed.
Also, for emscripten, building the samples doesn't currently work, because of FetchContent_MakeAvailable(glfw). This fails likeso:
This is just where the problems begin. The shaders need porting to gles2, along with some changes/removal of glad. But I think that's better discussed in a different issue.
I think I addressed these issues in #787. However, I haven't tested Emscripten with this yet.