Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 11 additions & 10 deletions .github/workflows/validate.yml
Original file line number Diff line number Diff line change
Expand Up @@ -53,12 +53,12 @@ jobs:
uses: actions/cache@v4
with:
path: ~/.mcpp/registry
key: mcpp-registry-${{ runner.os }}-0.0.45-${{ hashFiles('pkgs/**/*.lua', 'tests/*.sh', '.github/workflows/validate.yml') }}
key: mcpp-registry-${{ runner.os }}-0.0.46-${{ hashFiles('pkgs/**/*.lua', 'tests/*.sh', '.github/workflows/validate.yml') }}
restore-keys: |
mcpp-registry-${{ runner.os }}-0.0.45-
mcpp-registry-${{ runner.os }}-0.0.46-
- name: Download mcpp
env:
MCPP_VERSION: "0.0.45"
MCPP_VERSION: "0.0.46"
run: |
curl -L -fsS -o mcpp.tar.gz \
"https://github.com/mcpp-community/mcpp/releases/download/v${MCPP_VERSION}/mcpp-${MCPP_VERSION}-linux-x86_64.tar.gz"
Expand All @@ -72,6 +72,7 @@ jobs:
- name: Run compat smoke tests
env:
MCPP_INDEX_SMOKE_MCPP_HOME: ${{ runner.temp }}/mcpp-smoke-home
MCPP_INDEX_SMOKE_CACHE_DIR: ${{ runner.temp }}/mcpp-smoke-cache
run: |
mkdir -p "$MCPP_INDEX_SMOKE_MCPP_HOME"
"$MCPP" --version
Expand All @@ -91,14 +92,14 @@ jobs:
include:
- platform: macos
os: macos-15
archive: mcpp-0.0.45-macosx-arm64.tar.gz
root: mcpp-0.0.45-macosx-arm64
archive: mcpp-0.0.46-macosx-arm64.tar.gz
root: mcpp-0.0.46-macosx-arm64
mcpp: bin/mcpp
xlings: registry/bin/xlings
- platform: windows
os: windows-latest
archive: mcpp-0.0.45-windows-x86_64.zip
root: mcpp-0.0.45-windows-x86_64
archive: mcpp-0.0.46-windows-x86_64.zip
root: mcpp-0.0.46-windows-x86_64
mcpp: bin/mcpp.exe
xlings: registry/bin/xlings.exe
steps:
Expand All @@ -107,13 +108,13 @@ jobs:
uses: actions/cache@v4
with:
path: ~/.mcpp/registry
key: mcpp-registry-${{ runner.os }}-0.0.45-${{ hashFiles('pkgs/**/*.lua', 'tests/*.sh', '.github/workflows/validate.yml') }}
key: mcpp-registry-${{ runner.os }}-0.0.46-${{ hashFiles('pkgs/**/*.lua', 'tests/*.sh', '.github/workflows/validate.yml') }}
restore-keys: |
mcpp-registry-${{ runner.os }}-0.0.45-
mcpp-registry-${{ runner.os }}-0.0.46-
- name: Download mcpp
shell: bash
env:
MCPP_VERSION: "0.0.45"
MCPP_VERSION: "0.0.46"
MCPP_ARCHIVE: ${{ matrix.archive }}
MCPP_ROOT: ${{ matrix.root }}
run: |
Expand Down
16 changes: 12 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ mcpp build # 自动拉取源码 + 构建
| `gtest` | 1.15.2 | Google Test 测试框架 |
| `imgui` | 1.92.8 | Dear ImGui immediate-mode GUI 核心源码 |
| `opengl` | 2026.05.31 | Khronos OpenGL API 头文件 |
| `glx-runtime` | 2026.06.03 | Linux host GLVND/GLX/OpenGL runtime adapter |
| `khrplatform` | 2026.05.31 | Khronos KHR platform 头文件 |
| `xorgproto` | 2025.1 | X.Org protocol 头文件 |
| `xtrans` | 1.6.0 | X.Org transport support headers/source snippets |
Expand Down Expand Up @@ -77,7 +78,10 @@ mcpplibs.xpkg
imgui
├── compat.imgui
├── compat.glfw
│ └── compat.opengl
│ ├── compat.opengl
│ └── compat.glx-runtime
│ └── compat.xext → compat.x11
│ ← Linux GLX/OpenGL driver runtime provider
└── compat.opengl ← 消费者只需要 import imgui.* 模块

libarchive
Expand All @@ -90,6 +94,8 @@ libarchive
glfw
├── opengl
│ └── khrplatform ← GLFW/glfw3.h 所需 OpenGL/KHR 头文件
├── glx-runtime
│ └── xext → x11 ← GLFW GLX dlopen 所需 host GLVND/driver runtime
└── x11 / xcursor / xext / xfixes / xi
/ xinerama / xorgproto / xrandr / xrender
← GLFW Linux X11 后端所需 runtime/header 闭包
Expand All @@ -111,9 +117,11 @@ x11
mcpp 0.0.3+ 的 transitive walker 自动沿链路传播头文件和依赖,消费者只需声明直接依赖。

> 当前 X11/XCB/Xau/Xdmcp 以及 GLFW 需要的 Xcursor/Xext/Xfixes/Xi/Xinerama/
> Xrandr/Xrender 都已按上游源码提供 runtime `.so`。`compat.glfw` 仍沿用
> GLFW 上游的 GLX/OpenGL 动态加载行为,包描述会声明需要 `dlopen` 的
> `libGLX.so.0`/`libGL.so.1`/`libGL.so` 以及 `opengl.glx.driver` 能力。
> Xrandr/Xrender 都已按上游源码提供 runtime `.so`,并声明标准 ELF SONAME
> (如 `libX11.so.6`、`libxcb.so.1`)。`compat.glx-runtime` 是 Linux host
> GLVND/GLX/OpenGL driver runtime adapter,提供 GLFW 上游 `dlopen` 需要的
> `libGLX.so.0`/`libGL.so.1`/`libGL.so` runtime 目录,并通过 `compat.xext`
> 带入 host GLX 库常见的 X11/Xext ABI 依赖闭包。
> 窗口运行时仍需要宿主环境提供可用的 X server/GLX/OpenGL 驱动。

### 本地 smoke 验证
Expand Down
21 changes: 1 addition & 20 deletions pkgs/c/compat.glfw.lua
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ package = {
"src/posix_module.c",
},
deps = {
["compat.glx-runtime"] = "2026.06.03",
["compat.x11"] = "1.8.13",
["compat.xcursor"] = "1.2.3",
["compat.xext"] = "1.3.7",
Expand Down Expand Up @@ -119,25 +120,6 @@ package = {

import("xim.libxpkg.pkginfo")

local function patch_x11_loader_names(root)
local file = path.join(root, "src", "x11_init.c")
local data = io.readfile(file)
local replacements = {
['"libX11.so.6"'] = '"libX11.so"',
['"libXi.so.6"'] = '"libXi.so"',
['"libXrandr.so.2"'] = '"libXrandr.so"',
['"libXcursor.so.1"'] = '"libXcursor.so"',
['"libXinerama.so.1"'] = '"libXinerama.so"',
['"libX11-xcb.so.1"'] = '"libX11-xcb.so"',
['"libXrender.so.1"'] = '"libXrender.so"',
['"libXext.so.6"'] = '"libXext.so"',
}
for from, to in pairs(replacements) do
data = data:gsub(from, to)
end
io.writefile(file, data)
end

function install()
local srcdir = pkginfo.install_file():replace(".tar.gz", "")
if not os.isdir(srcdir) then
Expand All @@ -146,6 +128,5 @@ function install()

os.tryrm(pkginfo.install_dir())
os.mv(srcdir, pkginfo.install_dir())
patch_x11_loader_names(pkginfo.install_dir())
return true
end
135 changes: 135 additions & 0 deletions pkgs/c/compat.glx-runtime.lua
Original file line number Diff line number Diff line change
@@ -0,0 +1,135 @@
package = {
spec = "1",
namespace = "compat",
name = "compat.glx-runtime",
description = "Host GLVND/GLX/OpenGL runtime adapter for mcpp Linux window applications",
licenses = {"MIT"},
repo = "https://github.com/KhronosGroup/OpenGL-Registry",
type = "package",

xpm = {
linux = {
["2026.06.03"] = {
url = "https://raw.githubusercontent.com/KhronosGroup/OpenGL-Registry/a30033d3e812c9bf10094f1010374a6b15e192eb/README.adoc",
sha256 = "ea68efce197e68413ebb62c51ab4bccfb2309a2fca776d31b49d972f59f3640e",
},
},
},

mcpp = {
language = "c++23",
import_std = false,
c_standard = "c11",
generated_files = {
["mcpp_generated/glx_runtime_empty.c"] = "int mcpp_compat_glx_runtime_anchor(void) { return 0; }\n",
},
sources = {"mcpp_generated/glx_runtime_empty.c"},
targets = { ["glx_runtime"] = { kind = "lib" } },
runtime = {
library_dirs = { "mcpp_generated/glx_runtime/lib" },
dlopen_libs = { "libGLX.so.0", "libGL.so.1", "libGL.so" },
capabilities = { "x11.display", "opengl.glx.driver" },
},
deps = {
["compat.xext"] = "1.3.7",
},
},
}

import("xim.libxpkg.pkginfo")
import("xim.libxpkg.log")

local function sh_quote(value)
return "'" .. tostring(value):gsub("'", "'\\''") .. "'"
end

local function split_paths(value)
local out = {}
if not value or value == "" then
return out
end
for item in tostring(value):gmatch("[^:]+") do
if item ~= "" then
table.insert(out, item)
end
end
return out
end

local function candidate_dirs()
local out = {}
local seen = {}
local function add(dir)
if dir and dir ~= "" and not seen[dir] and os.isdir(dir) then
seen[dir] = true
table.insert(out, dir)
end
end

for _, dir in ipairs(split_paths(os.getenv("MCPP_HOST_GL_LIBRARY_PATH"))) do
add(dir)
end
add("/lib/x86_64-linux-gnu")
add("/usr/lib/x86_64-linux-gnu")
add("/lib64")
add("/usr/lib64")
add("/usr/lib")
return out
end

local host_gl_patterns = {
"libGL.so*",
"libGLX.so*",
"libGLX_*.so*",
"libGLdispatch.so*",
"libOpenGL.so*",
"libEGL.so*",
"libEGL_*.so*",
"libGLES*.so*",
"libnvidia*.so*",
"libglapi.so*",
"libdrm*.so*",
"libexpat.so*",
"libxshmfence.so*",
"libbsd.so*",
"libmd.so*",
}

local required = {
["libGLX.so.0"] = false,
["libGL.so.1"] = false,
}

local function link_runtime_libs(outdir)
os.mkdir(outdir)
for _, dir in ipairs(candidate_dirs()) do
for _, pattern in ipairs(host_gl_patterns) do
os.exec(
"for lib in " .. sh_quote(dir) .. "/" .. pattern ..
"; do [ -e \"$lib\" ] || continue; " ..
"ln -sf \"$lib\" " .. sh_quote(outdir) .. "/\"$(basename \"$lib\")\"; " ..
"done"
)
end
end

for name, _ in pairs(required) do
if not os.isfile(path.join(outdir, name)) then
log.error("required host GL runtime library not found: %s", name)
return false
end
end
return true
end

function install()
os.tryrm(pkginfo.install_dir())
os.mkdir(pkginfo.install_dir())

local generated = path.join(pkginfo.install_dir(), "mcpp_generated")
os.mkdir(generated)
io.writefile(path.join(generated, "glx_runtime_empty.c"),
"int mcpp_compat_glx_runtime_anchor(void) { return 0; }\n")

return link_runtime_libs(path.join(generated, "glx_runtime", "lib"))
end
2 changes: 1 addition & 1 deletion pkgs/c/compat.x11.lua
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@ package = {
"modules/lc/Utf8/*.c",
"modules/om/generic/*.c",
},
targets = { ["X11"] = { kind = "shared" } },
targets = { ["X11"] = { kind = "shared", soname = "libX11.so.6" } },
deps = {
["compat.xcb"] = "1.17.0",
["compat.xorgproto"] = "2025.1",
Expand Down
2 changes: 1 addition & 1 deletion pkgs/c/compat.xau.lua
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ package = {
"*/AuUnlock.c",
"*/AuWrite.c",
},
targets = { ["Xau"] = { kind = "shared" } },
targets = { ["Xau"] = { kind = "shared", soname = "libXau.so.6" } },
deps = {
["compat.xorgproto"] = "2025.1",
},
Expand Down
2 changes: 1 addition & 1 deletion pkgs/c/compat.xcb.lua
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ package = {
"src/bigreq.c",
"src/xc_misc.c",
},
targets = { ["xcb"] = { kind = "shared" } },
targets = { ["xcb"] = { kind = "shared", soname = "libxcb.so.1" } },
deps = {
["compat.xau"] = "1.0.12",
["compat.xcb-proto"] = "1.17.0",
Expand Down
2 changes: 1 addition & 1 deletion pkgs/c/compat.xcursor.lua
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ package = {
cflags = {"-D_GNU_SOURCE", "-D_DEFAULT_SOURCE", "-DHAVE_XFIXES=1"},
include_dirs = {"*/include", "*/include/X11/Xcursor", "*/include/X11/extensions", "*/src"},
sources = {"*/src/*.c"},
targets = { ["Xcursor"] = { kind = "shared" } },
targets = { ["Xcursor"] = { kind = "shared", soname = "libXcursor.so.1" } },
deps = {
["compat.x11"] = "1.8.13",
["compat.xfixes"] = "6.0.2",
Expand Down
2 changes: 1 addition & 1 deletion pkgs/c/compat.xdmcp.lua
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ package = {
"*/Wrap.c",
"*/Write.c",
},
targets = { ["Xdmcp"] = { kind = "shared" } },
targets = { ["Xdmcp"] = { kind = "shared", soname = "libXdmcp.so.6" } },
deps = {
["compat.xorgproto"] = "2025.1",
},
Expand Down
2 changes: 1 addition & 1 deletion pkgs/c/compat.xext.lua
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ package = {
cflags = {"-D_GNU_SOURCE", "-D_DEFAULT_SOURCE"},
include_dirs = {"*/include", "*/include/X11/extensions", "*/src"},
sources = {"*/src/*.c"},
targets = { ["Xext"] = { kind = "shared" } },
targets = { ["Xext"] = { kind = "shared", soname = "libXext.so.6" } },
deps = {
["compat.x11"] = "1.8.13",
["compat.xorgproto"] = "2025.1",
Expand Down
2 changes: 1 addition & 1 deletion pkgs/c/compat.xfixes.lua
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ package = {
cflags = {"-D_GNU_SOURCE", "-D_DEFAULT_SOURCE"},
include_dirs = {"*/include", "*/include/X11/extensions", "*/src"},
sources = {"*/src/*.c"},
targets = { ["Xfixes"] = { kind = "shared" } },
targets = { ["Xfixes"] = { kind = "shared", soname = "libXfixes.so.3" } },
deps = {
["compat.x11"] = "1.8.13",
["compat.xext"] = "1.3.7",
Expand Down
2 changes: 1 addition & 1 deletion pkgs/c/compat.xi.lua
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ package = {
"*/src/*.c",
"!*/src/XFreeLst.c",
},
targets = { ["Xi"] = { kind = "shared" } },
targets = { ["Xi"] = { kind = "shared", soname = "libXi.so.6" } },
deps = {
["compat.x11"] = "1.8.13",
["compat.xext"] = "1.3.7",
Expand Down
2 changes: 1 addition & 1 deletion pkgs/c/compat.xinerama.lua
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ package = {
cflags = {"-D_GNU_SOURCE", "-D_DEFAULT_SOURCE"},
include_dirs = {"*/include", "*/include/X11/extensions", "*/src"},
sources = {"*/src/*.c"},
targets = { ["Xinerama"] = { kind = "shared" } },
targets = { ["Xinerama"] = { kind = "shared", soname = "libXinerama.so.1" } },
deps = {
["compat.x11"] = "1.8.13",
["compat.xext"] = "1.3.7",
Expand Down
2 changes: 1 addition & 1 deletion pkgs/c/compat.xrandr.lua
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ package = {
cflags = {"-D_GNU_SOURCE", "-D_DEFAULT_SOURCE"},
include_dirs = {"*/include", "*/include/X11/extensions", "*/src"},
sources = {"*/src/*.c"},
targets = { ["Xrandr"] = { kind = "shared" } },
targets = { ["Xrandr"] = { kind = "shared", soname = "libXrandr.so.2" } },
deps = {
["compat.x11"] = "1.8.13",
["compat.xext"] = "1.3.7",
Expand Down
2 changes: 1 addition & 1 deletion pkgs/c/compat.xrender.lua
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ package = {
cflags = {"-D_GNU_SOURCE", "-D_DEFAULT_SOURCE"},
include_dirs = {"*/include", "*/include/X11/extensions", "*/src"},
sources = {"*/src/*.c"},
targets = { ["Xrender"] = { kind = "shared" } },
targets = { ["Xrender"] = { kind = "shared", soname = "libXrender.so.1" } },
deps = {
["compat.x11"] = "1.8.13",
["compat.xorgproto"] = "2025.1",
Expand Down
Loading
Loading