Skip to content

Commit

Permalink
LoongArch support (#1411)
Browse files Browse the repository at this point in the history
* Fixed -Wuninitialized warnings when not using SSE or NEON
  • Loading branch information
jrouwe authored Dec 21, 2024
1 parent 997c67e commit f094082
Show file tree
Hide file tree
Showing 12 changed files with 54 additions and 29 deletions.
30 changes: 30 additions & 0 deletions .github/workflows/determinism_check.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ env:
UBUNTU_GCC_AARCH64_VERSION: aarch64-linux-gnu-g++-12
UBUNTU_GCC_RISCV_VERSION: riscv64-linux-gnu-g++-12
UBUNTU_GCC_POWERPC_VERSION: powerpc64le-linux-gnu-g++-12
UBUNTU_GCC_LOONGARCH_VERSION: loongarch64-linux-gnu-g++-14

on:
push:
Expand Down Expand Up @@ -294,6 +295,35 @@ jobs:
# working-directory: ${{github.workspace}}/Build/Linux_Distribution
# run: qemu-ppc64le -L /usr/powerpc64le-linux-gnu/ ./PerformanceTest -q=LinearCast -t=max -s=Pyramid -validate_hash=${PYRAMID_HASH}

loongarch_gcc:
runs-on: ubuntu-24.04
name: LoongArch GCC Determinism Check
steps:
- name: Checkout Code
uses: actions/checkout@v4
- name: Update index
run: sudo apt-get update
- name: Install Cross Compiler
run: sudo apt-get install g++-14-loongarch64-linux-gnu gcc-12-multilib g++-12-multilib qemu-user -y
- name: Configure CMake
working-directory: ${{github.workspace}}/Build
run: ./cmake_linux_clang_gcc.sh Distribution ${{env.UBUNTU_GCC_LOONGARCH_VERSION}} -DCROSS_COMPILE_ARM=ON -DCROSS_PLATFORM_DETERMINISTIC=ON -DCROSS_COMPILE_ARM_TARGET="" -DTARGET_VIEWER=OFF -DTARGET_SAMPLES=OFF -DTARGET_HELLO_WORLD=OFF -DTARGET_UNIT_TESTS=ON -DTARGET_PERFORMANCE_TEST=ON
- name: Build
run: cmake --build ${{github.workspace}}/Build/Linux_Distribution -j $(nproc)
- name: Unit Tests
working-directory: ${{github.workspace}}/Build/Linux_Distribution
run: qemu-loongarch64 -L /usr/loongarch64-linux-gnu/ ./UnitTests
- name: Test ConvexVsMesh
working-directory: ${{github.workspace}}/Build/Linux_Distribution
run: qemu-loongarch64 -L /usr/loongarch64-linux-gnu/ ./PerformanceTest -q=LinearCast -t=max -s=ConvexVsMesh -validate_hash=${CONVEX_VS_MESH_HASH}
- name: Test Ragdoll
working-directory: ${{github.workspace}}/Build/Linux_Distribution
run: qemu-loongarch64 -L /usr/loongarch64-linux-gnu/ ./PerformanceTest -q=LinearCast -t=max -s=Ragdoll -validate_hash=${RAGDOLL_HASH}
# This is slow so disabled for the moment
# - name: Test Pyramid
# working-directory: ${{github.workspace}}/Build/Linux_Distribution
# run: qemu-loongarch64 -L /usr/loongarch64-linux-gnu/ ./PerformanceTest -q=LinearCast -t=max -s=Pyramid -validate_hash=${PYRAMID_HASH}

emscripten:
runs-on: ubuntu-latest
name: Emscripten Determinism Check
Expand Down
1 change: 1 addition & 0 deletions Docs/Architecture.md
Original file line number Diff line number Diff line change
Expand Up @@ -634,6 +634,7 @@ It is quite difficult to verify cross platform determinism, so this feature is l
* Linux gcc ARM 64-bit with NEON
* Linux gcc RISC-V 64-bit
* Linux gcc PowerPC (Little Endian) 64-bit
* Linux gcc LoongArch 64-bit
* WASM emscripten running in nodejs

The most important things to look out for in your own application:
Expand Down
2 changes: 1 addition & 1 deletion Docs/ReleaseNotes.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ For breaking API changes see [this document](https://github.com/jrouwe/JoltPhysi
* Added `PhysicsSystem::SetSimShapeFilter`. This allows filtering out collisions between sub shapes within a body and can for example be used to have a single body that contains a low detail simulation shape an a high detail collision query shape.
* Added an example of a body that's both a sensor and a rigid body in `ContactListenerTest`.
* Added binary serialization to `SkeletalAnimation`.
* Added support for RISC-V and PowerPC (Little Endian) CPUs.
* Added support for RISC-V, LoongArch and PowerPC (Little Endian) CPUs.

### Bug fixes

Expand Down
2 changes: 2 additions & 0 deletions Jolt/ConfigurationString.h
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@ inline const char *GetConfigurationString()
#else
"(Little Endian) "
#endif
#elif defined(JPH_CPU_LOONGARCH)
"LoongArch "
#elif defined(JPH_CPU_E2K)
"E2K "
#elif defined(JPH_CPU_WASM)
Expand Down
26 changes: 11 additions & 15 deletions Jolt/Core/Core.h
Original file line number Diff line number Diff line change
Expand Up @@ -216,6 +216,16 @@
#endif
#define JPH_VECTOR_ALIGNMENT 16
#define JPH_DVECTOR_ALIGNMENT 8
#elif defined(__loongarch__)
// LoongArch CPU architecture
#define JPH_CPU_LOONGARCH
#if defined(__loongarch64)
#define JPH_CPU_ADDRESS_BITS 64
#else
#define JPH_CPU_ADDRESS_BITS 32
#endif
#define JPH_VECTOR_ALIGNMENT 16
#define JPH_DVECTOR_ALIGNMENT 8
#elif defined(__e2k__)
// E2K CPU architecture (MCST Elbrus 2000)
#define JPH_CPU_E2K
Expand All @@ -231,18 +241,6 @@
#error Unsupported CPU architecture
#endif

// CPU helper macros
#ifdef JPH_CPU_RISCV
#define JPH_IF_RISCV(x) x
#else
#define JPH_IF_RISCV(x)
#endif
#ifdef JPH_CPU_PPC
#define JPH_IF_PPC(x) x
#else
#define JPH_IF_PPC(x)
#endif

// If this define is set, Jolt is compiled as a shared library
#ifdef JPH_SHARED_LIBRARY
#ifdef JPH_BUILD_SHARED_LIBRARY
Expand Down Expand Up @@ -357,8 +355,6 @@
JPH_GCC_SUPPRESS_WARNING("-Wpedantic") \
JPH_GCC_SUPPRESS_WARNING("-Wunused-parameter") \
JPH_GCC_SUPPRESS_WARNING("-Wmaybe-uninitialized") \
JPH_IF_RISCV(JPH_GCC_SUPPRESS_WARNING("-Wuninitialized")) \
JPH_IF_PPC(JPH_GCC_SUPPRESS_WARNING("-Wuninitialized")) \
\
JPH_MSVC_SUPPRESS_WARNING(4619) /* #pragma warning: there is no warning number 'XXXX' */ \
JPH_MSVC_SUPPRESS_WARNING(4514) /* 'X' : unreferenced inline function has been removed */ \
Expand Down Expand Up @@ -397,7 +393,7 @@
#elif defined(JPH_PLATFORM_LINUX) || defined(JPH_PLATFORM_ANDROID) || defined(JPH_PLATFORM_MACOS) || defined(JPH_PLATFORM_IOS) || defined(JPH_PLATFORM_FREEBSD)
#if defined(JPH_CPU_X86)
#define JPH_BREAKPOINT __asm volatile ("int $0x3")
#elif defined(JPH_CPU_ARM) || defined(JPH_CPU_RISCV) || defined(JPH_CPU_E2K) || defined(JPH_CPU_PPC)
#elif defined(JPH_CPU_ARM) || defined(JPH_CPU_RISCV) || defined(JPH_CPU_E2K) || defined(JPH_CPU_PPC) || defined(JPH_CPU_LOONGARCH)
#define JPH_BREAKPOINT __builtin_trap()
#else
#error Unknown CPU architecture
Expand Down
2 changes: 1 addition & 1 deletion Jolt/Core/FPControlWord.h
Original file line number Diff line number Diff line change
Expand Up @@ -130,7 +130,7 @@ class FPControlWord : public NonCopyable

// RISC-V only implements manually checking if exceptions occurred by reading the fcsr register. It doesn't generate exceptions.

#elif defined(JPH_CPU_PPC)
#elif defined(JPH_CPU_PPC) || defined(JPH_CPU_LOONGARCH)

// Not implemented right now

Expand Down
2 changes: 1 addition & 1 deletion Jolt/Core/FPFlushDenormals.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@

JPH_NAMESPACE_BEGIN

#if defined(JPH_CPU_WASM) || defined(JPH_CPU_RISCV) || defined(JPH_CPU_PPC)
#if defined(JPH_CPU_WASM) || defined(JPH_CPU_RISCV) || defined(JPH_CPU_PPC) || defined(JPH_CPU_LOONGARCH)

// Not supported
class FPFlushDenormals { };
Expand Down
2 changes: 1 addition & 1 deletion Jolt/Core/TickCounter.h
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ JPH_INLINE uint64 GetProcessorTickCount()
uint64 val;
asm volatile("mrs %0, cntvct_el0" : "=r" (val));
return val;
#elif defined(JPH_CPU_ARM) || defined(JPH_CPU_RISCV) || defined(JPH_CPU_WASM) || defined(JPH_CPU_PPC)
#elif defined(JPH_CPU_ARM) || defined(JPH_CPU_RISCV) || defined(JPH_CPU_WASM) || defined(JPH_CPU_PPC) || defined(JPH_CPU_LOONGARCH)
return 0; // Not supported
#else
#error Undefined
Expand Down
4 changes: 2 additions & 2 deletions Jolt/Math/Math.h
Original file line number Diff line number Diff line change
Expand Up @@ -120,7 +120,7 @@ inline uint CountTrailingZeros(uint32 inValue)
return 32;
return __builtin_ctz(inValue);
#endif
#elif defined(JPH_CPU_E2K) || defined(JPH_CPU_RISCV) || defined(JPH_CPU_PPC)
#elif defined(JPH_CPU_E2K) || defined(JPH_CPU_RISCV) || defined(JPH_CPU_PPC) || defined(JPH_CPU_LOONGARCH)
return inValue ? __builtin_ctz(inValue) : 32;
#else
#error Undefined
Expand Down Expand Up @@ -150,7 +150,7 @@ inline uint CountLeadingZeros(uint32 inValue)
#else
return __builtin_clz(inValue);
#endif
#elif defined(JPH_CPU_E2K) || defined(JPH_CPU_RISCV) || defined(JPH_CPU_PPC)
#elif defined(JPH_CPU_E2K) || defined(JPH_CPU_RISCV) || defined(JPH_CPU_PPC) || defined(JPH_CPU_LOONGARCH)
return inValue ? __builtin_clz(inValue) : 32;
#else
#error Undefined
Expand Down
8 changes: 2 additions & 6 deletions Jolt/Math/Vec3.inl
Original file line number Diff line number Diff line change
Expand Up @@ -64,9 +64,7 @@ Vec3::Vec3(const Float3 &inV)
mF32[0] = inV[0];
mF32[1] = inV[1];
mF32[2] = inV[2];
#ifdef JPH_FLOATING_POINT_EXCEPTIONS_ENABLED
mF32[3] = inV[2];
#endif
mF32[3] = inV[2]; // Not strictly needed when JPH_FLOATING_POINT_EXCEPTIONS_ENABLED is off but prevents warnings about uninitialized variables
#endif
}

Expand All @@ -82,9 +80,7 @@ Vec3::Vec3(float inX, float inY, float inZ)
mF32[0] = inX;
mF32[1] = inY;
mF32[2] = inZ;
#ifdef JPH_FLOATING_POINT_EXCEPTIONS_ENABLED
mF32[3] = inZ;
#endif
mF32[3] = inZ; // Not strictly needed when JPH_FLOATING_POINT_EXCEPTIONS_ENABLED is off but prevents warnings about uninitialized variables
#endif
}

Expand Down
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,7 @@ Why create yet another physics engine? Firstly, it has been a personal learning
## Supported platforms

* Windows (Desktop or UWP) x86/x64/ARM32/ARM64
* Linux (tested on Ubuntu) x86/x64/ARM32/ARM64/RISC-V64/PowerPC64LE
* Linux (tested on Ubuntu) x86/x64/ARM32/ARM64/RISC-V64/LoongArch64/PowerPC64LE
* FreeBSD
* Android x86/x64/ARM32/ARM64
* Platform Blue (a popular game console) x64
Expand Down
2 changes: 1 addition & 1 deletion UnitTests/Core/FPFlushDenormalsTest.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
#include <Jolt/Core/FPFlushDenormals.h>
#include <atomic>

#if !defined(JPH_CPU_WASM) && !defined(JPH_CPU_RISCV) && !defined(JPH_CPU_PPC)
#if !defined(JPH_CPU_WASM) && !defined(JPH_CPU_RISCV) && !defined(JPH_CPU_PPC) && !defined(JPH_CPU_LOONGARCH)

// Implemented as a global atomic so the compiler can't optimize it to a constant
extern atomic<float> TestFltMin;
Expand Down

0 comments on commit f094082

Please sign in to comment.