Skip to content

Commit 0e9a471

Browse files
committed
Fix Windows build: add zip pkg, portable embed (od replaces xxd)
1. Add zip to MSYS2 build packages (both dry-run and release). 2. embed-frontend.sh: replace xxd with od+sed for hex dump — xxd requires vim which isn't in MSYS2 CLANG64 by default. 3. embed-frontend.sh: flip IS_MACOS→IS_LINUX — Linux gets ld -r -b binary (ELF-only), everything else (macOS, Windows) gets the portable C-array approach via od. 4. release.yml: same Windows archive fix (msys2 shell + .exe detect).
1 parent 89dd3bb commit 0e9a471

3 files changed

Lines changed: 23 additions & 23 deletions

File tree

.github/workflows/dry-run.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -191,6 +191,7 @@ jobs:
191191
mingw-w64-clang-x86_64-clang
192192
mingw-w64-clang-x86_64-zlib
193193
make
194+
zip
194195
195196
- uses: actions/setup-node@v4
196197
with:
@@ -204,7 +205,6 @@ jobs:
204205
shell: msys2 {0}
205206
run: |
206207
BIN=build/c/codebase-memory-mcp
207-
# MSYS2 Clang produces .exe extension
208208
[ -f "${BIN}.exe" ] && BIN="${BIN}.exe"
209209
cp "$BIN" codebase-memory-mcp.exe
210210
zip codebase-memory-mcp-windows-amd64.zip codebase-memory-mcp.exe

.github/workflows/release.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -187,6 +187,7 @@ jobs:
187187
mingw-w64-clang-x86_64-clang
188188
mingw-w64-clang-x86_64-zlib
189189
make
190+
zip
190191
191192
- uses: actions/setup-node@v4
192193
with:

scripts/embed-frontend.sh

Lines changed: 21 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -19,10 +19,10 @@ OUTPUT_DIR="${2:?Usage: embed-frontend.sh <dist_dir> <output_dir>}"
1919
rm -rf "$OUTPUT_DIR"
2020
mkdir -p "$OUTPUT_DIR"
2121

22-
# Detect platform
23-
IS_MACOS=false
24-
if [[ "$(uname -s)" == "Darwin" ]]; then
25-
IS_MACOS=true
22+
# Detect platform — Linux uses ld -r -b binary, everything else uses xxd+cc
23+
IS_LINUX=false
24+
if [[ "$(uname -s)" == "Linux" ]] && ! [[ "$(uname -s)" =~ MINGW|MSYS ]]; then
25+
IS_LINUX=true
2626
fi
2727

2828
# Content-type detection
@@ -68,25 +68,24 @@ for file in "${FILES[@]}"; do
6868
mangled=$(mangle "$rel")
6969
obj="$OUTPUT_DIR/embed_${mangled}.o"
7070

71-
if $IS_MACOS; then
72-
# macOS: use custom section + assembly approach
73-
# ld -r -b binary not available on macOS default ld
74-
# Instead, use xxd to create a C array (for macOS compatibility)
71+
if $IS_LINUX; then
72+
# Linux: ld -r -b binary (zero bloat, ELF only)
73+
abs_obj="$(cd "$(dirname "$0")/.." && pwd)/$obj"
74+
(cd "$DIST_DIR" && ld -r -b binary -o "$abs_obj" "$rel")
75+
else
76+
# macOS/Windows/MSYS2: generate C byte array + cc (no xxd dependency)
7577
local_c="$OUTPUT_DIR/embed_${mangled}.c"
7678
local_sym="_binary_${mangled}"
7779

7880
echo "/* Generated from $rel */" > "$local_c"
7981
echo "const unsigned char ${local_sym}_data[] = {" >> "$local_c"
80-
xxd -i < "$file" >> "$local_c"
82+
# Use od (POSIX) to generate hex bytes — works everywhere without xxd/vim
83+
od -An -tx1 -v < "$file" | tr -s ' ' '\n' | grep -v '^$' | sed 's/^/0x/; s/$/,/' | paste -sd' ' - | fold -s -w 76 | sed 's/^/ /' >> "$local_c"
8184
echo "};" >> "$local_c"
8285
echo "const unsigned int ${local_sym}_size = sizeof(${local_sym}_data);" >> "$local_c"
8386

84-
cc -c -O2 -o "$obj" "$local_c"
87+
${CC:-cc} -c -O2 -o "$obj" "$local_c"
8588
rm -f "$local_c"
86-
else
87-
# Linux: ld -r -b binary (zero bloat)
88-
abs_obj="$(cd "$(dirname "$0")/.." && pwd)/$obj"
89-
(cd "$DIST_DIR" && ld -r -b binary -o "$abs_obj" "$rel")
9089
fi
9190

9291
OBJ_FILES+=("$obj")
@@ -111,7 +110,7 @@ for file in "${FILES[@]}"; do
111110
mangled=$(mangle "$rel")
112111
sym="_binary_${mangled}"
113112

114-
if $IS_MACOS; then
113+
if ! $IS_LINUX; then
115114
echo "extern const unsigned char ${sym}_data[];" >> "$ASSETS_C"
116115
echo "extern const unsigned int ${sym}_size;" >> "$ASSETS_C"
117116
else
@@ -132,7 +131,7 @@ for file in "${FILES[@]}"; do
132131
# URL path: /index.html for root, /assets/... for assets
133132
url_path="/$rel"
134133

135-
if $IS_MACOS; then
134+
if ! $IS_LINUX; then
136135
echo " {\"$url_path\", ${sym}_data, 0, \"$ct\"}," >> "$ASSETS_C"
137136
else
138137
echo " {\"$url_path\", ${sym}_start, 0, \"$ct\"}," >> "$ASSETS_C"
@@ -142,11 +141,11 @@ done
142141
echo "};" >> "$ASSETS_C"
143142
echo "const int CBM_EMBEDDED_FILE_COUNT = ${#FILES[@]};" >> "$ASSETS_C"
144143

145-
# Generate size fixup (for macOS where we have explicit size vars)
146-
if $IS_MACOS; then
144+
# Generate size fixup
145+
if $IS_LINUX; then
146+
# Linux: compute size from start/end pointers (ld -r -b binary symbols)
147147
cat >> "$ASSETS_C" <<'SIZEINIT'
148148
149-
/* Initialize sizes — called once or we use the _size vars directly */
150149
static void __attribute__((constructor)) init_embedded_sizes(void) {
151150
cbm_embedded_file_t *files = CBM_EMBEDDED_FILES;
152151
SIZEINIT
@@ -155,12 +154,12 @@ SIZEINIT
155154
rel="${FILES[$i]#$DIST_DIR/}"
156155
mangled=$(mangle "$rel")
157156
sym="_binary_${mangled}"
158-
echo " files[$i].size = ${sym}_size;" >> "$ASSETS_C"
157+
echo " files[$i].size = (unsigned int)(${sym}_end - ${sym}_start);" >> "$ASSETS_C"
159158
done
160159

161160
echo "}" >> "$ASSETS_C"
162161
else
163-
# Linux: compute size from start/end pointers
162+
# macOS/Windows: use explicit _size vars from xxd-generated C arrays
164163
cat >> "$ASSETS_C" <<'SIZEINIT'
165164
166165
static void __attribute__((constructor)) init_embedded_sizes(void) {
@@ -171,7 +170,7 @@ SIZEINIT
171170
rel="${FILES[$i]#$DIST_DIR/}"
172171
mangled=$(mangle "$rel")
173172
sym="_binary_${mangled}"
174-
echo " files[$i].size = (unsigned int)(${sym}_end - ${sym}_start);" >> "$ASSETS_C"
173+
echo " files[$i].size = ${sym}_size;" >> "$ASSETS_C"
175174
done
176175

177176
echo "}" >> "$ASSETS_C"

0 commit comments

Comments
 (0)