Skip to content

Commit 54ba74b

Browse files
Add more Cygwin support (#9686)
* GNUMakefile: add support for cygwin * uucore: add more cygwin support * chroot, id, nohup, stdbuf, stty: add support for cygwin * uucore, chroot, id, nohup, stdbuf: format * chore: format * chore: fix spelling * GNUMakefile: fix inverted check
1 parent 949f038 commit 54ba74b

File tree

10 files changed

+165
-18
lines changed

10 files changed

+165
-18
lines changed

GNUmakefile

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -62,15 +62,15 @@ TOYBOX_SRC := $(TOYBOX_ROOT)/toybox-$(TOYBOX_VER)
6262

6363
#------------------------------------------------------------------------
6464
# Detect the host system.
65-
# On Windows the environment already sets OS = Windows_NT.
65+
# On Windows uname -s might return MINGW_NT-* or CYGWIN_NT-*.
6666
# Otherwise let it default to the kernel name returned by uname -s
6767
# (Linux, Darwin, FreeBSD, …).
6868
#------------------------------------------------------------------------
69-
OS ?= $(shell uname -s)
69+
OS := $(shell uname -s)
7070

7171
# Windows does not allow symlink by default.
7272
# Allow to override LN for AppArmor.
73-
ifeq ($(OS),Windows_NT)
73+
ifneq (,$(findstring _NT,$(OS)))
7474
LN ?= ln -f
7575
endif
7676
LN ?= ln -sf
@@ -195,7 +195,7 @@ HASHSUM_PROGS := \
195195

196196
$(info Detected OS = $(OS))
197197

198-
ifneq ($(OS),Windows_NT)
198+
ifeq (,$(findstring MINGW,$(OS)))
199199
PROGS += $(UNIX_PROGS)
200200
endif
201201
ifeq ($(SELINUX_ENABLED),1)
@@ -450,8 +450,12 @@ install: build install-manpages install-completions install-locales
450450
mkdir -p $(INSTALLDIR_BIN)
451451
ifneq (,$(and $(findstring stdbuf,$(UTILS)),$(findstring feat_external_libstdbuf,$(CARGOFLAGS))))
452452
mkdir -p $(DESTDIR)$(LIBSTDBUF_DIR)
453+
ifneq (,$(findstring CYGWIN,$(OS)))
454+
$(INSTALL) -m 755 $(BUILDDIR)/deps/stdbuf.dll $(DESTDIR)$(LIBSTDBUF_DIR)/libstdbuf.dll
455+
else
453456
$(INSTALL) -m 755 $(BUILDDIR)/deps/libstdbuf.* $(DESTDIR)$(LIBSTDBUF_DIR)/
454457
endif
458+
endif
455459
ifeq (${MULTICALL}, y)
456460
$(INSTALL) -m 755 $(BUILDDIR)/coreutils $(INSTALLDIR_BIN)/$(PROG_PREFIX)coreutils
457461
$(foreach prog, $(filter-out coreutils, $(INSTALLEES)), \
@@ -472,7 +476,7 @@ else
472476
endif
473477

474478
uninstall:
475-
ifneq ($(OS),Windows_NT)
479+
ifeq (,$(findstring MINGW,$(OS)))
476480
rm -f $(DESTDIR)$(LIBSTDBUF_DIR)/libstdbuf.*
477481
-rm -d $(DESTDIR)$(LIBSTDBUF_DIR) 2>/dev/null || true
478482
endif

src/uu/chroot/src/chroot.rs

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -319,7 +319,12 @@ fn supplemental_gids(uid: libc::uid_t) -> Vec<libc::gid_t> {
319319

320320
/// Set the supplemental group IDs for this process.
321321
fn set_supplemental_gids(gids: &[libc::gid_t]) -> std::io::Result<()> {
322-
#[cfg(any(target_vendor = "apple", target_os = "freebsd", target_os = "openbsd"))]
322+
#[cfg(any(
323+
target_vendor = "apple",
324+
target_os = "freebsd",
325+
target_os = "openbsd",
326+
target_os = "cygwin"
327+
))]
323328
let n = gids.len() as libc::c_int;
324329
#[cfg(any(target_os = "linux", target_os = "android"))]
325330
let n = gids.len() as libc::size_t;

src/uu/id/src/id.rs

Lines changed: 18 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -535,7 +535,12 @@ fn pline(possible_uid: Option<uid_t>) {
535535
);
536536
}
537537

538-
#[cfg(any(target_os = "linux", target_os = "android", target_os = "openbsd"))]
538+
#[cfg(any(
539+
target_os = "linux",
540+
target_os = "android",
541+
target_os = "openbsd",
542+
target_os = "cygwin"
543+
))]
539544
fn pline(possible_uid: Option<uid_t>) {
540545
let uid = possible_uid.unwrap_or_else(getuid);
541546
let pw = Passwd::locate(uid).unwrap();
@@ -552,10 +557,20 @@ fn pline(possible_uid: Option<uid_t>) {
552557
);
553558
}
554559

555-
#[cfg(any(target_os = "linux", target_os = "android", target_os = "openbsd"))]
560+
#[cfg(any(
561+
target_os = "linux",
562+
target_os = "android",
563+
target_os = "openbsd",
564+
target_os = "cygwin"
565+
))]
556566
fn auditid() {}
557567

558-
#[cfg(not(any(target_os = "linux", target_os = "android", target_os = "openbsd")))]
568+
#[cfg(not(any(
569+
target_os = "linux",
570+
target_os = "android",
571+
target_os = "openbsd",
572+
target_os = "cygwin"
573+
)))]
559574
fn auditid() {
560575
use std::mem::MaybeUninit;
561576

src/uu/nohup/src/nohup.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -185,7 +185,8 @@ unsafe extern "C" {
185185
target_os = "linux",
186186
target_os = "android",
187187
target_os = "freebsd",
188-
target_os = "openbsd"
188+
target_os = "openbsd",
189+
target_os = "cygwin"
189190
))]
190191
/// # Safety
191192
/// This function is unsafe because it dereferences a raw pointer.

src/uu/stdbuf/build.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,11 @@ mod platform {
2626
pub const DYLIB_EXT: &str = ".dylib";
2727
}
2828

29+
#[cfg(target_os = "cygwin")]
30+
mod platform {
31+
pub const DYLIB_EXT: &str = ".dll";
32+
}
33+
2934
fn main() {
3035
println!("cargo:rerun-if-changed=build.rs");
3136
println!("cargo:rerun-if-changed=src/libstdbuf/src/libstdbuf.rs");
@@ -103,6 +108,9 @@ fn main() {
103108
assert!(status.success(), "Failed to build libstdbuf");
104109

105110
// Copy the built library to OUT_DIR for include_bytes! to find
111+
#[cfg(target_os = "cygwin")]
112+
let lib_name = format!("stdbuf{}", platform::DYLIB_EXT);
113+
#[cfg(not(target_os = "cygwin"))]
106114
let lib_name = format!("libstdbuf{}", platform::DYLIB_EXT);
107115
let dest_path = Path::new(&out_dir).join(format!("libstdbuf{}", platform::DYLIB_EXT));
108116

src/uu/stdbuf/src/libstdbuf/build.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,8 @@ fn main() {
1111
println!("cargo:rustc-link-arg=-fPIC");
1212

1313
let target = env::var("TARGET").unwrap_or_else(|_| "unknown".to_string());
14-
// Ensure the library doesn't have any undefined symbols (-z flag not supported on macOS)
15-
if !target.contains("apple-darwin") {
14+
// Ensure the library doesn't have any undefined symbols (-z flag not supported on macOS and Cygwin)
15+
if !target.contains("apple-darwin") && !target.contains("cygwin") {
1616
println!("cargo:rustc-link-arg=-z");
1717
println!("cargo:rustc-link-arg=defs");
1818
}

src/uu/stdbuf/src/libstdbuf/src/libstdbuf.rs

Lines changed: 88 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
//
33
// For the full copyright and license information, please view the LICENSE
44
// file that was distributed with this source code.
5-
// spell-checker:ignore (ToDO) IOFBF IOLBF IONBF setvbuf stderrp stdinp stdoutp
5+
// spell-checker:ignore (ToDO) getreent reent IOFBF IOLBF IONBF setvbuf stderrp stdinp stdoutp
66

77
use ctor::ctor;
88
use libc::{_IOFBF, _IOLBF, _IONBF, FILE, c_char, c_int, fileno, size_t};
@@ -35,7 +35,35 @@ pub unsafe extern "C" fn __stdbuf_get_stdin() -> *mut FILE {
3535
unsafe { __stdin }
3636
}
3737

38-
#[cfg(not(any(target_os = "macos", target_os = "freebsd", target_os = "openbsd")))]
38+
#[cfg(target_os = "cygwin")]
39+
{
40+
// _getreent()->_std{in,out,err}
41+
// see:
42+
// echo '#include <stdio.h>\nstd{in,out,err}' | gcc -E -xc - -std=c23 | tail -n1
43+
// echo '#include <stdio.h>' | grep -E -xc - -std=c23 | grep 'struct _reent' -A91 | grep 580 -A91 | tail -n+2
44+
45+
#[repr(C)]
46+
struct _reent {
47+
_errno: c_int,
48+
_stdin: *mut FILE,
49+
_stdout: *mut FILE,
50+
_stderr: *mut FILE,
51+
// other stuff
52+
}
53+
54+
unsafe extern "C" {
55+
fn __getreent() -> *mut _reent;
56+
}
57+
58+
unsafe { (*__getreent())._stdin }
59+
}
60+
61+
#[cfg(not(any(
62+
target_os = "macos",
63+
target_os = "freebsd",
64+
target_os = "openbsd",
65+
target_os = "cygwin"
66+
)))]
3967
{
4068
unsafe extern "C" {
4169
static mut stdin: *mut FILE;
@@ -64,7 +92,35 @@ pub unsafe extern "C" fn __stdbuf_get_stdout() -> *mut FILE {
6492
unsafe { __stdout }
6593
}
6694

67-
#[cfg(not(any(target_os = "macos", target_os = "freebsd", target_os = "openbsd")))]
95+
#[cfg(target_os = "cygwin")]
96+
{
97+
// _getreent()->_std{in,out,err}
98+
// see:
99+
// echo '#include <stdio.h>\nstd{in,out,err}' | gcc -E -xc - -std=c23 | tail -n1
100+
// echo '#include <stdio.h>' | grep -E -xc - -std=c23 | grep 'struct _reent' -A91 | grep 580 -A91 | tail -n+2
101+
102+
#[repr(C)]
103+
struct _reent {
104+
_errno: c_int,
105+
_stdin: *mut FILE,
106+
_stdout: *mut FILE,
107+
_stderr: *mut FILE,
108+
// other stuff
109+
}
110+
111+
unsafe extern "C" {
112+
fn __getreent() -> *mut _reent;
113+
}
114+
115+
unsafe { (*__getreent())._stdout }
116+
}
117+
118+
#[cfg(not(any(
119+
target_os = "macos",
120+
target_os = "freebsd",
121+
target_os = "openbsd",
122+
target_os = "cygwin"
123+
)))]
68124
{
69125
unsafe extern "C" {
70126
static mut stdout: *mut FILE;
@@ -93,7 +149,35 @@ pub unsafe extern "C" fn __stdbuf_get_stderr() -> *mut FILE {
93149
unsafe { __stderr }
94150
}
95151

96-
#[cfg(not(any(target_os = "macos", target_os = "freebsd", target_os = "openbsd")))]
152+
#[cfg(target_os = "cygwin")]
153+
{
154+
// _getreent()->_std{in,out,err}
155+
// see:
156+
// echo '#include <stdio.h>\nstd{in,out,err}' | gcc -E -xc - -std=c23 | tail -n1
157+
// echo '#include <stdio.h>' | grep -E -xc - -std=c23 | grep 'struct _reent' -A91 | grep 580 -A91 | tail -n+2
158+
159+
#[repr(C)]
160+
struct _reent {
161+
_errno: c_int,
162+
_stdin: *mut FILE,
163+
_stdout: *mut FILE,
164+
_stderr: *mut FILE,
165+
// other stuff
166+
}
167+
168+
unsafe extern "C" {
169+
fn __getreent() -> *mut _reent;
170+
}
171+
172+
unsafe { (*__getreent())._stdin }
173+
}
174+
175+
#[cfg(not(any(
176+
target_os = "macos",
177+
target_os = "freebsd",
178+
target_os = "openbsd",
179+
target_os = "cygwin"
180+
)))]
97181
{
98182
unsafe extern "C" {
99183
static mut stderr: *mut FILE;

src/uu/stdbuf/src/stdbuf.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,9 @@ const STDBUF_INJECT: &[u8] = include_bytes!(concat!(env!("OUT_DIR"), "/libstdbuf
4343
#[cfg(all(not(feature = "feat_external_libstdbuf"), target_vendor = "apple"))]
4444
const STDBUF_INJECT: &[u8] = include_bytes!(concat!(env!("OUT_DIR"), "/libstdbuf.dylib"));
4545

46+
#[cfg(all(not(feature = "feat_external_libstdbuf"), target_os = "cygwin"))]
47+
const STDBUF_INJECT: &[u8] = include_bytes!(concat!(env!("OUT_DIR"), "/libstdbuf.dll"));
48+
4649
enum BufferType {
4750
Default,
4851
Line,

src/uu/stty/src/flags.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -256,13 +256,16 @@ pub const LOCAL_FLAGS: &[Flag<L>] = &[
256256
// Not supported by nix
257257
// Flag::new("xcase", L::XCASE),
258258
Flag::new("tostop", L::TOSTOP),
259+
#[cfg(not(target_os = "cygwin"))]
259260
Flag::new("echoprt", L::ECHOPRT),
261+
#[cfg(not(target_os = "cygwin"))]
260262
Flag::new("prterase", L::ECHOPRT).hidden(),
261263
Flag::new("echoctl", L::ECHOCTL).sane(),
262264
Flag::new("ctlecho", L::ECHOCTL).sane().hidden(),
263265
Flag::new("echoke", L::ECHOKE).sane(),
264266
Flag::new("crtkill", L::ECHOKE).sane().hidden(),
265267
Flag::new("flusho", L::FLUSHO),
268+
#[cfg(not(target_os = "cygwin"))]
266269
Flag::new("extproc", L::EXTPROC),
267270
];
268271

src/uucore/src/lib/features/utmpx.rs

Lines changed: 26 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
// For the full copyright and license information, please view the LICENSE
44
// file that was distributed with this source code.
55
//
6-
// spell-checker:ignore logind
6+
// spell-checker:ignore IDLEN logind
77

88
//! Aims to provide platform-independent methods to obtain login records
99
//!
@@ -56,7 +56,12 @@ pub use libc::getutxent;
5656
#[cfg_attr(target_env = "musl", allow(deprecated))]
5757
pub use libc::setutxent;
5858
use libc::utmpx;
59-
#[cfg(any(target_vendor = "apple", target_os = "linux", target_os = "netbsd"))]
59+
#[cfg(any(
60+
target_vendor = "apple",
61+
target_os = "linux",
62+
target_os = "netbsd",
63+
target_os = "cygwin"
64+
))]
6065
#[cfg_attr(target_env = "musl", allow(deprecated))]
6166
pub use libc::utmpxname;
6267

@@ -179,6 +184,25 @@ mod ut {
179184
pub use libc::USER_PROCESS;
180185
}
181186

187+
#[cfg(target_os = "cygwin")]
188+
mod ut {
189+
pub static DEFAULT_FILE: &str = "";
190+
191+
pub use libc::UT_HOSTSIZE;
192+
pub use libc::UT_IDLEN;
193+
pub use libc::UT_LINESIZE;
194+
pub use libc::UT_NAMESIZE;
195+
196+
pub use libc::BOOT_TIME;
197+
pub use libc::DEAD_PROCESS;
198+
pub use libc::INIT_PROCESS;
199+
pub use libc::LOGIN_PROCESS;
200+
pub use libc::NEW_TIME;
201+
pub use libc::OLD_TIME;
202+
pub use libc::RUN_LVL;
203+
pub use libc::USER_PROCESS;
204+
}
205+
182206
/// A login record
183207
pub struct Utmpx {
184208
inner: utmpx,

0 commit comments

Comments
 (0)