-
Notifications
You must be signed in to change notification settings - Fork 1
Expand file tree
/
Copy pathbuild.sh
More file actions
executable file
·151 lines (127 loc) · 5.12 KB
/
Copy pathbuild.sh
File metadata and controls
executable file
·151 lines (127 loc) · 5.12 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
#!/bin/bash
# build.sh — Build PerspectiveCLI
#
# Usage:
# ./build.sh Build debug (default)
# ./build.sh release Build release (optimized)
# ./build.sh clean Clean build artifacts and rebuild debug
# ./build.sh dist Build release + create distributable .tar.gz
#
# This script handles both Swift compilation and Metal shader compilation,
# which swift build cannot do on its own.
set -euo pipefail
CONFIG="debug"
CLEAN=false
DIST=false
case "${1:-}" in
release) CONFIG="release" ;;
clean) CLEAN=true ;;
dist) CONFIG="release"; DIST=true ;;
esac
PROJECT_DIR="$(cd "$(dirname "$0")" && pwd)"
cd "$PROJECT_DIR"
# ── Clean ──────────────────────────────────────────────────────────────
if $CLEAN; then
echo "Cleaning build artifacts..."
swift package clean
echo ""
fi
# ── Swift Build ────────────────────────────────────────────────────────
echo "Building PerspectiveCLI ($CONFIG)..."
if [ "$CONFIG" = "release" ]; then
swift build -c release
else
swift build
fi
BIN_DIR=$(swift build ${CONFIG:+-c $CONFIG} --show-bin-path 2>/dev/null)
echo "Binary: $BIN_DIR/PerspectiveCLI"
echo ""
# ── Metal Shaders ──────────────────────────────────────────────────────
# SwiftPM doesn't compile .metal files in C/C++ targets.
# We compile them manually and place mlx.metallib next to the binary.
METAL_DIR=".build/checkouts/mlx-swift/Source/Cmlx/mlx-generated/metal"
if [ ! -d "$METAL_DIR" ]; then
echo "Warning: Metal shader directory not found, skipping metallib build."
echo "MLX backend will not work without it."
exit 0
fi
# Skip if metallib is already newer than all .metal sources
METALLIB="$BIN_DIR/mlx.metallib"
if [ -f "$METALLIB" ]; then
NEEDS_REBUILD=false
while IFS= read -r f; do
if [ "$f" -nt "$METALLIB" ]; then
NEEDS_REBUILD=true
break
fi
done < <(find "$METAL_DIR" -name "*.metal")
if ! $NEEDS_REBUILD; then
echo "mlx.metallib is up to date, skipping."
SKIP_METAL=true
fi
fi
if [ "${SKIP_METAL:-false}" = false ]; then
WORK=$(mktemp -d)
trap 'rm -rf "$WORK"' EXIT
echo "Compiling Metal shaders..."
for f in $(find "$METAL_DIR" -name "*.metal"); do
name=$(basename "$f" .metal)
echo " $name"
xcrun metal -c \
-I "$METAL_DIR" \
-I "$METAL_DIR/steel" \
-I "$METAL_DIR/steel/gemm" \
-I "$METAL_DIR/steel/conv" \
-I "$METAL_DIR/steel/attn" \
-I "$METAL_DIR/steel/attn/kernels" \
-o "$WORK/$name.air" "$f"
done
echo "Linking mlx.metallib..."
xcrun metallib -o "$WORK/mlx.metallib" "$WORK"/*.air
cp "$WORK/mlx.metallib" "$METALLIB"
fi
echo ""
# ── Dist ──────────────────────────────────────────────────────────────
if $DIST; then
VERSION=$(git describe --tags 2>/dev/null || echo "dev")
DIST_DIR="$PROJECT_DIR/dist"
STAGE="$DIST_DIR/perspective-cli-${VERSION}"
ARCHIVE="$DIST_DIR/perspective-cli-${VERSION}-macos-arm64.tar.gz"
rm -rf "$STAGE"
mkdir -p "$STAGE"
cp "$BIN_DIR/PerspectiveCLI" "$STAGE/perspective"
cp "$METALLIB" "$STAGE/mlx.metallib"
cp "$PROJECT_DIR/install.sh" "$STAGE/"
cp "$PROJECT_DIR/LICENSE" "$STAGE/" 2>/dev/null || true
cp "$PROJECT_DIR/README.md" "$STAGE/"
tar -czf "$ARCHIVE" -C "$DIST_DIR" "perspective-cli-${VERSION}"
rm -rf "$STAGE"
SHA=$(shasum -a 256 "$ARCHIVE" | cut -d' ' -f1)
echo "Distribution archive created:"
echo " $ARCHIVE"
echo " SHA-256: $SHA"
echo ""
echo "To install:"
echo " tar xzf $(basename "$ARCHIVE")"
echo " cd perspective-cli-${VERSION}"
echo " ./install.sh"
echo ""
echo "Or one-liner (after publishing the release):"
echo " curl -fsSL https://raw.githubusercontent.com/techopolis/PerspectiveCLI/main/scripts/remote-install.sh | bash"
# ── Update Homebrew formula ───────────────────────────────────────
FORMULA="$PROJECT_DIR/Formula/perspective.rb"
if [ -f "$FORMULA" ]; then
sed -i '' "s|url \".*\"|url \"https://github.com/techopolis/PerspectiveCLI/releases/download/${VERSION}/perspective-cli-${VERSION}-macos-arm64.tar.gz\"|" "$FORMULA"
sed -i '' "s|version \".*\"|version \"${VERSION}\"|" "$FORMULA"
sed -i '' "s|sha256 \".*\"|sha256 \"${SHA}\"|" "$FORMULA"
echo ""
echo "Homebrew formula updated:"
echo " $FORMULA"
echo " version: $VERSION"
echo " sha256: $SHA"
echo ""
echo "Copy to your homebrew-tap repo:"
echo " cp $FORMULA /path/to/homebrew-tap/Formula/"
fi
fi
echo "Build complete."