Skip to content
This repository was archived by the owner on Dec 15, 2025. It is now read-only.

Commit 0533984

Browse files
committed
...
1 parent e2e60a9 commit 0533984

File tree

3 files changed

+79
-6
lines changed

3 files changed

+79
-6
lines changed

Makefile

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,3 +14,17 @@ release-aarch64-musl: prepare-aarch64-musl
1414

1515
prepare-aarch64-musl:
1616
rustup target add aarch64-unknown-linux-musl
17+
18+
# Build for macOS (both Intel and Apple Silicon)
19+
release-macos:
20+
cargo build --release
21+
22+
# Install to ~/hero/bin (if it exists)
23+
install-macos: release-macos
24+
@if [ -d ~/hero/bin ]; then \
25+
cp target/release/zinit ~/hero/bin; \
26+
echo "Installed zinit to ~/hero/bin"; \
27+
else \
28+
echo "~/hero/bin directory not found. Please create it or specify a different installation path."; \
29+
exit 1; \
30+
fi

docs/osx_cross_compile.md

Lines changed: 24 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,28 @@
1-
# macOS Installation Guide for Cross-Compilation to aarch64-unknown-linux-musl
1+
# macOS Guide for Zinit
22

3-
This guide outlines the steps to set up your macOS environment for cross-compiling Rust projects to the `aarch64-unknown-linux-musl` target. This is particularly useful for building binaries that can run on ARM-based Linux systems (e.g., Raspberry Pi, AWS Graviton) using musl libc.
3+
This guide covers both building Zinit natively on macOS and cross-compiling from macOS to Linux targets.
4+
5+
## Building Zinit Natively on macOS
6+
7+
Zinit can now be built and run directly on macOS. The code has been updated to handle platform-specific differences between Linux and macOS.
8+
9+
### Building for macOS
10+
11+
```bash
12+
# Build a release version for macOS
13+
make release-macos
14+
15+
# Install to ~/hero/bin (if it exists)
16+
make install-macos
17+
```
18+
19+
The native macOS build provides most of Zinit's functionality, with the following limitations:
20+
- System reboot and shutdown operations are not supported (they will exit the process instead)
21+
- Some Linux-specific features are disabled
22+
23+
## Cross-Compilation from macOS to Linux
24+
25+
This section outlines the steps to set up your macOS environment for cross-compiling Rust projects to the `aarch64-unknown-linux-musl` target. This is particularly useful for building binaries that can run on ARM-based Linux systems (e.g., Raspberry Pi, AWS Graviton) using musl libc.
426

527
## Prerequisites
628

src/zinit/lifecycle.rs

Lines changed: 41 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,13 @@
11
use crate::manager::{Log, Logs, Process, ProcessManager};
22
use crate::zinit::config;
33
use crate::zinit::errors::ZInitError;
4+
#[cfg(target_os = "linux")]
45
use crate::zinit::ord::{service_dependency_order, ProcessDAG, DUMMY_ROOT};
56
use crate::zinit::service::ZInitService;
67
use crate::zinit::state::{State, Target};
7-
use crate::zinit::types::{ServiceTable, Watcher};
8+
use crate::zinit::types::ServiceTable;
9+
#[cfg(target_os = "linux")]
10+
use crate::zinit::types::Watcher;
811

912
// Define a local extension trait for WaitStatus
1013
trait WaitStatusExt {
@@ -17,16 +20,22 @@ impl WaitStatusExt for WaitStatus {
1720
}
1821
}
1922
use anyhow::Result;
23+
#[cfg(target_os = "linux")]
2024
use nix::sys::reboot::RebootMode;
2125
use nix::sys::signal;
2226
use nix::sys::wait::WaitStatus;
2327
use nix::unistd::Pid;
28+
#[cfg(target_os = "linux")]
2429
use std::collections::HashMap;
2530
use std::str::FromStr;
2631
use std::sync::Arc;
27-
use tokio::sync::{mpsc, Notify, RwLock};
32+
#[cfg(target_os = "linux")]
33+
use tokio::sync::mpsc;
34+
use tokio::sync::{Notify, RwLock};
2835
use tokio::time;
36+
#[cfg(target_os = "linux")]
2937
use tokio::time::timeout;
38+
#[cfg(target_os = "linux")]
3039
use tokio_stream::StreamExt;
3140

3241
/// Manages the lifecycle of services
@@ -208,16 +217,41 @@ impl LifecycleManager {
208217
/// Shutdown the system
209218
pub async fn shutdown(&self) -> Result<()> {
210219
info!("shutting down");
211-
self.power(RebootMode::RB_POWER_OFF).await
220+
#[cfg(target_os = "linux")]
221+
return self.power(RebootMode::RB_POWER_OFF).await;
222+
223+
#[cfg(not(target_os = "linux"))]
224+
{
225+
*self.shutdown.write().await = true;
226+
if self.container {
227+
std::process::exit(0);
228+
} else {
229+
info!("System shutdown not supported on this platform");
230+
std::process::exit(0);
231+
}
232+
}
212233
}
213234

214235
/// Reboot the system
215236
pub async fn reboot(&self) -> Result<()> {
216237
info!("rebooting");
217-
self.power(RebootMode::RB_AUTOBOOT).await
238+
#[cfg(target_os = "linux")]
239+
return self.power(RebootMode::RB_AUTOBOOT).await;
240+
241+
#[cfg(not(target_os = "linux"))]
242+
{
243+
*self.shutdown.write().await = true;
244+
if self.container {
245+
std::process::exit(0);
246+
} else {
247+
info!("System reboot not supported on this platform");
248+
std::process::exit(0);
249+
}
250+
}
218251
}
219252

220253
/// Power off or reboot the system
254+
#[cfg(target_os = "linux")]
221255
async fn power(&self, mode: RebootMode) -> Result<()> {
222256
*self.shutdown.write().await = true;
223257

@@ -239,6 +273,7 @@ impl LifecycleManager {
239273
self.kill_process_tree(dag, state_channels, shutdown_timeouts)
240274
.await?;
241275

276+
// On Linux, we can use sync and reboot
242277
nix::unistd::sync();
243278
if self.container {
244279
std::process::exit(0);
@@ -250,6 +285,7 @@ impl LifecycleManager {
250285
}
251286

252287
/// Kill processes in dependency order
288+
#[cfg(target_os = "linux")]
253289
async fn kill_process_tree(
254290
&self,
255291
mut dag: ProcessDAG,
@@ -305,6 +341,7 @@ impl LifecycleManager {
305341
}
306342

307343
/// Wait for a service to be killed
344+
#[cfg(target_os = "linux")]
308345
async fn kill_wait(
309346
self,
310347
name: String,

0 commit comments

Comments
 (0)