Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/lupyuen/zig-pinephone-mach
(Experimental) Mach Zig Game Engine on PinePhone
https://github.com/lupyuen/zig-pinephone-mach
gamedev graphics-engine mach opengles pinephone webgpu zig
Last synced: 28 days ago
JSON representation
(Experimental) Mach Zig Game Engine on PinePhone
- Host: GitHub
- URL: https://github.com/lupyuen/zig-pinephone-mach
- Owner: lupyuen
- License: apache-2.0
- Created: 2022-07-24T06:04:29.000Z (over 2 years ago)
- Default Branch: main
- Last Pushed: 2022-07-25T10:29:41.000Z (over 2 years ago)
- Last Synced: 2024-11-14T18:29:18.738Z (3 months ago)
- Topics: gamedev, graphics-engine, mach, opengles, pinephone, webgpu, zig
- Homepage:
- Size: 74.2 KB
- Stars: 1
- Watchers: 2
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- Funding: .github/FUNDING.yml
- License: LICENSE
Awesome Lists containing this project
README
# (Experimental) Mach Zig Game Engine on PinePhone
Can we run the Mach Game Engine (in Zig) on PinePhone?
https://machengine.org/
https://github.com/hexops/mach
Let's find out! (With Manjaro Phosh)
```text
██████████████████ ████████ manjaro@manjaro-arm
██████████████████ ████████ -------------------
██████████████████ ████████ OS: Manjaro ARM Linux aarch64
██████████████████ ████████ Host: Pine64 PinePhone (1.2)
████████ ████████ Kernel: 5.18.3-1-MANJARO-ARM
████████ ████████ ████████ Uptime: 1 hour, 48 mins
████████ ████████ ████████ Packages: 806 (pacman)
████████ ████████ ████████ Shell: bash 5.1.16
████████ ████████ ████████ Resolution: 720x1440
████████ ████████ ████████ Terminal: node
████████ ████████ ████████ CPU: (4) @ 1.152GHz
████████ ████████ ████████ Memory: 507MiB / 1991MiB
████████ ████████ ████████
████████ ████████ ████████
```# Build Mach
Follow these steps to download Zig, download Mach and build Mach on PinePhone...
```bash
$ curl -O -L https://ziglang.org/builds/zig-linux-aarch64-0.10.0-dev.3080+eb1b2f5c5.tar.xz
$ tar xf zig-linux-aarch64-0.10.0-dev.3080+eb1b2f5c5.tar.xz
$ export PATH="$HOME/zig-linux-aarch64-0.10.0-dev.3080+eb1b2f5c5:$PATH"
$ git clone https://github.com/hexops/mach
$ cd mach
$ zig build example-rotating-cube -Ddawn-from-source=true
```[(See the complete log)](https://gist.github.com/lupyuen/ff77c494b0589371b44b6c96f8491e31)
Be patient, it takes roughly 1.5 hours for the first build. Subsequent builds will complete in seconds.
# Missing Arm64 Atomics
Mach fails to build on PinePhone due to Missing Arm64 Atomics...
```bash
$ zig build example-rotating-cube -Ddawn-from-source=true
LLD Link...
ld.lld: error: undefined symbol: __aarch64_ldadd8_relax
ld.lld: error: undefined symbol: __aarch64_ldadd8_acq
ld.lld: error: undefined symbol: __aarch64_ldadd8_rel
ld.lld: error: undefined symbol: __aarch64_ldadd8_acq_rel
ld.lld: error: undefined symbol: __aarch64_ldadd4_relax
ld.lld: error: undefined symbol: __aarch64_ldadd4_acq
ld.lld: error: undefined symbol: __aarch64_ldadd4_rel
ld.lld: error: undefined symbol: __aarch64_ldadd4_acq_rel
ld.lld: error: undefined symbol: __aarch64_swp8_acq_rel
ld.lld: error: undefined symbol: __aarch64_cas8_acq_rel
```[(See the complete log)](https://gist.github.com/lupyuen/ff77c494b0589371b44b6c96f8491e31)
This is caused by Zig's incomplete support for LLVM and Atomics...
https://github.com/ziglang/zig/issues/10086
So we copy the Arm64 Atomics from this Rust Implementation...
https://github.com/suptalentdev/mustang/blob/master/c-scape/aarch64_outline_atomics/aarch64_outline_atomics/src/lib.rs
https://docs.rs/atomic/latest/atomic/struct.Atomic.html
# Fix Missing Arm64 Atomics
To build Mach correctly on PinePhone, apply this fix for the Missing Arm64 Atomics...
```zig
//// TODO: To fix the Missing Atomics for Mach Zig Game Engine on PinePhone Manjaro Phosh,
//// Insert these lines at the bottom of mach/examples/rotating-cube/main.zig
////
//// Here are the Linker Errors for the Missing Atomics:
//// https://gist.github.com/lupyuen/ff77c494b0589371b44b6c96f8491e31
////
//// Refer to this issue: https://github.com/ziglang/zig/issues/10086
//// Rust Implementation: https://github.com/suptalentdev/mustang/blob/master/c-scape/aarch64_outline_atomics/aarch64_outline_atomics/src/lib.rs
//// Rust Atomic Struct: https://docs.rs/atomic/latest/atomic/struct.Atomic.htmlpub export fn __aarch64_ldadd4_relax() c_int { _ = puts("TODO: __aarch64_ldadd4_relax"); return 0; }
pub export fn __aarch64_ldadd4_acq() c_int { _ = puts("TODO: __aarch64_ldadd4_acq"); return 0; }
pub export fn __aarch64_ldadd4_rel() c_int { _ = puts("TODO: __aarch64_ldadd4_rel"); return 0; }pub export fn __aarch64_ldadd4_acq_rel(x: u32, p: [*c]u32) u32 {
// (*p).fetch_add(x, AcqRel)
// Add to the current value, returning the previous value.
// AcqRel: For loads it uses Acquire ordering. For stores it uses the Release ordering.
const ret = p.*;
_ = printf("__aarch64_ldadd4_acq_rel: x=%d, p=%p, ret=%d\n", x, p, ret);
p.* +%= x;
return ret;
}pub export fn __aarch64_ldadd8_relax(x: u32, p: [*c]u32) u32 {
// (*p).fetch_add(x, Relaxed)
// Add to the current value, returning the previous value.
// Relaxed: No ordering constraints, only atomic operation
const ret = p.*;
_ = printf("__aarch64_ldadd8_relax: x=%d, p=%p, ret=%d\n", x, p, ret);
p.* +%= x;
return ret;
}pub export fn __aarch64_ldadd8_acq() c_int { _ = puts("TODO: __aarch64_ldadd8_acq"); return 0; }
pub export fn __aarch64_ldadd8_rel(x: u64, p: [*c]u64) u64 {
// (*p).fetch_add(x, AcqRel)
// Add to the current value, returning the previous value.
const ret = p.*;
_ = printf("__aarch64_ldadd8_rel: x=%d, p=%p, ret=%d\n", x, p, ret);
p.* +%= x;
return ret;
}pub export fn __aarch64_ldadd8_acq_rel(x: u64, p: [*c]u64) u64 {
// (*p).fetch_add(x, AcqRel)
// Add to the current value, returning the previous value.
// AcqRel: For loads it uses Acquire ordering. For stores it uses the Release ordering.
const ret = p.*;
_ = printf("__aarch64_ldadd8_acq_rel: x=%d, p=%p, ret=%d\n", x, p, ret);
p.* +%= x;
return ret;
}pub export fn __aarch64_swp8_acq_rel() c_int { _ = puts("TODO: __aarch64_swp8_acq_rel"); return 0; }
pub export fn __aarch64_cas8_acq_rel() c_int { _ = puts("TODO: __aarch64_cas8_acq_rel"); return 0; }extern fn printf(format: [*:0]const u8, ...) c_int;
extern fn puts(str: [*:0]const u8) c_int;
```After fixing, Mach builds OK on PinePhone...
```bash
$ zig build example-rotating-cube -Ddawn-from-source=true
```# GLFW Error
When we run Mach on PinePhone, it fails with a GLFW Error...
```bash
$ zig build example-rotating-cube -Ddawn-from-source=true$ export GPU_BACKEND=opengl
$ zig-out/bin/example-rotating-cube
glfw: error.VersionUnavailable: GLX: Failed to create context: GLXBadFBConfig$ export GPU_BACKEND=opengles
$ zig-out/bin/example-rotating-cube
glfw: error.VersionUnavailable: EGL: Failed to create context: An EGLConfig argument does not name a valid EGL frame buffer configuration
```[(See complete log)](https://gist.github.com/lupyuen/700efb3b25463bc042ce9e23169efb18)
Which might be caused by the OpenGL Version on PinePhone...
# OpenGL Version
PinePhone supports OpenGL version 2.1, which might be too old for Mach...
```text
$ glxinfo | grep "OpenGL version"
OpenGL version string: 2.1 Mesa 22.1.3
```When we set `MESA_GL_VERSION_OVERRIDE`, Mach fails with a GLSL Error ...
```bash
$ zig build example-rotating-cube -Ddawn-from-source=true
$ export GPU_BACKEND=opengl
$ export MESA_GL_VERSION_OVERRIDE=4.5$ glxinfo | grep 'OpenGL version'
OpenGL version string: 4.5 (Compatibility Profile) Mesa 22.1.3$ zig-out/bin/example-rotating-cube
mach: found OpenGL backend on Unknown adapter: Mali400, OpenGL version 4.5 (Core Profile) Mesa 22.1.3
gpu: validation error: #version 450
Program compilation failed:
0:1(10): error: GLSL 4.50 is not supported. Supported versions are: 1.10, 1.20, and 1.00 ES
- While calling [Device].CreateRenderPipeline([RenderPipelineDescriptor]).
```[(See the complete log)](https://gist.github.com/lupyuen/9d3aca0d10cc6dfee0a7d3e50f14e191)
This says that Mach failed to create the GPU Render Pipeline...
```zig
const vs_module = core.device.createShaderModule(&.{
.label = "my vertex shader",
.code = .{ .wgsl = @embedFile("vert.wgsl") },
});const pipeline_descriptor = gpu.RenderPipeline.Descriptor{
.fragment = &fragment,
.layout = pipeline_layout,
.depth_stencil = null,
.vertex = .{
.module = vs_module,
.entry_point = "main",
.buffers = &.{vertex_buffer_layout},
```[(Source)](https://github.com/hexops/mach/blob/main/examples/rotating-cube/main.zig#L87-L107)
Because PinePhone failed to load the [OpenGL Shading Language](https://www.khronos.org/opengl/wiki/OpenGL_Shading_Language) (GLSL) file [vert.wgsl](https://github.com/hexops/mach/blob/main/examples/rotating-cube/vert.wgsl).
This GLSL Error appears when we set `MESA_GL_VERSION_OVERRIDE` to 4.4 or above.
The GLFW Error appears when we set `MESA_GL_VERSION_OVERRIDE` to 4.3 or below.
So it seems Mach only works with OpenGL / GLSL version 4.4 and above. Which isn't supported on PinePhone.
Perhaps PinePhone Pro (with Vulkan) will support Mach.
# Pinebook Pro
Will Mach run on Pinebook Pro?
```text
██████████████████ ████████ luppy@pinebook
██████████████████ ████████ --------------
██████████████████ ████████ OS: Manjaro ARM Linux aarch64
██████████████████ ████████ Host: Pine64 Pinebook Pro
████████ ████████ Kernel: 5.18.5-1-MANJARO-ARM
████████ ████████ ████████ Uptime: 53 mins
████████ ████████ ████████ Packages: 1006 (pacman)
████████ ████████ ████████ Shell: bash 5.1.16
████████ ████████ ████████ Resolution: 1920x1080
████████ ████████ ████████ Terminal: node
████████ ████████ ████████ CPU: (6) @ 1.416GHz
████████ ████████ ████████ Memory: 914MiB / 3868MiB
████████ ████████ ████████
████████ ████████ ████████
```We run the same steps to build Mach on Pinebook Pro (Manjaro Xfce)...
https://github.com/lupyuen/zig-pinephone-mach#build-mach
And apply the fix for Missing Arm64 Atomics...
https://github.com/lupyuen/zig-pinephone-mach#missing-arm64-atomics
[(See the build log)](https://gist.github.com/lupyuen/1aaca1615848d86844a4d2873a847439)
(Mach builds on Pinebook Pro in roughly half an hour)
Mach fails with the same GLFW Error on Pinebook Pro even though it supports OpenGL 3.1...
```bash
$ zig build example-rotating-cube -Ddawn-from-source=true
$ export GPU_BACKEND=opengl$ glxinfo | grep 'OpenGL version'
OpenGL version string: 3.1 Mesa 22.1.3$ zig-out/bin/example-rotating-cube
glfw: error.VersionUnavailable: GLX: Failed to create context: GLXBadFBConfig
```[(See the complete log)](https://gist.github.com/lupyuen/46d5e398fad09ec498d8c9c93d82e03a)
When we set `MESA_GL_VERSION_OVERRIDE`, Mach fails with the same GLSL Error...
```bash
$ zig build example-rotating-cube -Ddawn-from-source=true
$ export GPU_BACKEND=opengl
$ export MESA_GL_VERSION_OVERRIDE=4.5$ glxinfo | grep 'OpenGL version'
OpenGL version string: 4.5 (Compatibility Profile) Mesa 22.1.3$ zig-out/bin/example-rotating-cube
mach: found OpenGL backend on Unknown adapter: Mali-T860 (Panfrost), OpenGL version 4.5 (Core Profile) Mesa 22.1.3
gpu: validation error: #version 450
Program compilation failed:
0:1(10): error: GLSL 4.50 is not supported. Supported versions are: 1.10, 1.20, 1.30, 1.40, 1.00 ES, and 3.00 ES
- While calling [Device].CreateRenderPipeline([RenderPipelineDescriptor]).
```[(See the complete log)](https://gist.github.com/lupyuen/849491f0aef2b8ad67e8ab1ce250f067)
So it seems Mach won't run on Pinebook Pro because it doesn't support OpenGL / GLSL version 4.4 or later.