Compare commits
16 Commits
138044e52f
...
0.14.5
| Author | SHA1 | Date | |
|---|---|---|---|
|
0e9127d417
|
|||
|
e6f747d635
|
|||
|
9b699d7298
|
|||
|
941f931f8b
|
|||
|
f0eac562b3
|
|||
|
008c0624f6
|
|||
|
f4bd4de2e4
|
|||
|
6d7173e438
|
|||
|
958f08bd9e
|
|||
|
02b5edae05
|
|||
|
0819eeb75d
|
|||
|
0f12dcc552
|
|||
|
b9c4b49603
|
|||
|
2c4349872c
|
|||
|
59fa3ed3d2
|
|||
|
71655a8559
|
21
Makefile
21
Makefile
@@ -1,4 +1,4 @@
|
|||||||
# Copyright (c) 2023–2024 Emma Tebibyte <emma@tebibyte.media>
|
# Copyright (c) 2023–2025 Emma Tebibyte <emma@tebibyte.media>
|
||||||
# Copyright (c) 2023–2024 DTB <trinity@trinity.moe>
|
# Copyright (c) 2023–2024 DTB <trinity@trinity.moe>
|
||||||
# Copyright (c) 2023 Sasha Koshka <sashakoshka@tebibyte.media>
|
# Copyright (c) 2023 Sasha Koshka <sashakoshka@tebibyte.media>
|
||||||
# Copyright (c) 2024 Aaditya Aryal <aryalaadi123@gmail.com>
|
# Copyright (c) 2024 Aaditya Aryal <aryalaadi123@gmail.com>
|
||||||
@@ -42,7 +42,7 @@ BIN = build/bin
|
|||||||
default: all test
|
default: all test
|
||||||
|
|
||||||
.PHONY: all
|
.PHONY: all
|
||||||
all: dj false fop hru intcmp mm npc peek rpn scrut str strcmp swab true
|
all: dj false fileis fop hru intcmp mm npc peek rpn str strcmp swab true
|
||||||
|
|
||||||
# keep build/include until bindgen(1) has stdin support
|
# keep build/include until bindgen(1) has stdin support
|
||||||
# https://github.com/rust-lang/rust-bindgen/issues/2703
|
# https://github.com/rust-lang/rust-bindgen/issues/2703
|
||||||
@@ -62,7 +62,12 @@ dist: all docs
|
|||||||
install: dist
|
install: dist
|
||||||
cp -r $(DESTDIR)/* /
|
cp -r $(DESTDIR)/* /
|
||||||
|
|
||||||
include tests/tests.mk
|
TESTFILES != for file in tests/*.mk; do printf '%s ' "$$file"; done
|
||||||
|
|
||||||
|
TESTS != printf '%s\n' "$(TESTFILES)" | xargs -n1 basename \
|
||||||
|
| sed 's/\.mk/_tests/g'
|
||||||
|
|
||||||
|
include $(TESTFILES)
|
||||||
|
|
||||||
.PHONY: test
|
.PHONY: test
|
||||||
test: all $(TESTS) /tmp/getopt
|
test: all $(TESTS) /tmp/getopt
|
||||||
@@ -112,6 +117,11 @@ false: build/bin/false
|
|||||||
build/bin/false: src/false.c build
|
build/bin/false: src/false.c build
|
||||||
$(CC) $(CFLAGS) -o $@ src/false.c
|
$(CC) $(CFLAGS) -o $@ src/false.c
|
||||||
|
|
||||||
|
.PHONY: fileis
|
||||||
|
fileis: build/bin/fileis
|
||||||
|
build/bin/fileis: src/fileis.rs build rustlibs
|
||||||
|
$(RUSTC) $(RUSTFLAGS) $(RUSTLIBS) -o $@ src/fileis.rs
|
||||||
|
|
||||||
.PHONY: fop
|
.PHONY: fop
|
||||||
fop: build/bin/fop
|
fop: build/bin/fop
|
||||||
build/bin/fop: src/fop.rs build rustlibs
|
build/bin/fop: src/fop.rs build rustlibs
|
||||||
@@ -147,11 +157,6 @@ rpn: build/bin/rpn
|
|||||||
build/bin/rpn: src/rpn.rs build rustlibs
|
build/bin/rpn: src/rpn.rs build rustlibs
|
||||||
$(RUSTC) $(RUSTFLAGS) -o $@ src/rpn.rs
|
$(RUSTC) $(RUSTFLAGS) -o $@ src/rpn.rs
|
||||||
|
|
||||||
.PHONY: scrut
|
|
||||||
scrut: build/bin/scrut
|
|
||||||
build/bin/scrut: src/scrut.c build
|
|
||||||
$(CC) $(CFLAGS) -o $@ src/scrut.c
|
|
||||||
|
|
||||||
.PHONY: str
|
.PHONY: str
|
||||||
str: build/bin/str
|
str: build/bin/str
|
||||||
build/bin/str: src/str.c build
|
build/bin/str: src/str.c build
|
||||||
|
|||||||
@@ -1,15 +1,15 @@
|
|||||||
.\" Copyright (c) 2024 DTB <trinity@trinity.moe>
|
.\" Copyright (c) 2024 DTB <trinity@trinity.moe>
|
||||||
.\" Copyright (c) 2024 Emma Tebibyte <emma@tebibyte.media>
|
.\" Copyright (c) 2024–2025 Emma Tebibyte <emma@tebibyte.media>
|
||||||
.\"
|
.\"
|
||||||
.\" This work is licensed under CC BY-SA 4.0. To see a copy of this license,
|
.\" This work is licensed under CC BY-SA 4.0. To see a copy of this license,
|
||||||
.\" visit <http://creativecommons.org/licenses/by-sa/4.0/>.
|
.\" visit <http://creativecommons.org/licenses/by-sa/4.0/>.
|
||||||
.\"
|
.\"
|
||||||
.TH SCRUT 1 2024-06-06 "Harakit X.X.X"
|
.TH FILEIS 1 2025-02-24 "Harakit X.X.X"
|
||||||
.SH NAME
|
.SH NAME
|
||||||
scrut \(en scrutinize file properties
|
fileis \(en scrutinize file properties
|
||||||
.SH SYNOPSIS
|
.SH SYNOPSIS
|
||||||
|
|
||||||
scrut
|
fileis
|
||||||
.RB [ -LSbcdefgkprsuwx ]
|
.RB [ -LSbcdefgkprsuwx ]
|
||||||
.B file...
|
.B file...
|
||||||
.\"
|
.\"
|
||||||
@@ -82,5 +82,6 @@ Copyright \(co 2024 DTB. License AGPLv3+: GNU AGPL version 3 or later
|
|||||||
.\"
|
.\"
|
||||||
.SH SEE ALSO
|
.SH SEE ALSO
|
||||||
.BR access (3p),
|
.BR access (3p),
|
||||||
|
.BR chown (1p),
|
||||||
.BR lstat (3p),
|
.BR lstat (3p),
|
||||||
.BR test (1p)
|
.BR test (1p)
|
||||||
91
src/fileis.rs
Normal file
91
src/fileis.rs
Normal file
@@ -0,0 +1,91 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2024 DTB <trinity@trinity.moe>
|
||||||
|
* Copyright (c) 2024 Emma Tebibyte <emma@tebibyte.media>
|
||||||
|
* SPDX-License-Identifier: AGPL-3.0-or-later
|
||||||
|
*
|
||||||
|
* This program is free software: you can redistribute it and/or modify it under
|
||||||
|
* the terms of the GNU Affero General Public License as published by the Free
|
||||||
|
* Software Foundation, either version 3 of the License, or (at your option) any
|
||||||
|
* later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||||
|
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
|
||||||
|
* FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more
|
||||||
|
* details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU Affero General Public License
|
||||||
|
* along with this program. If not, see https://www.gnu.org/licenses/.
|
||||||
|
*/
|
||||||
|
|
||||||
|
use std::{
|
||||||
|
env::args,
|
||||||
|
fs::metadata,
|
||||||
|
os::unix::fs::{ FileTypeExt, MetadataExt },
|
||||||
|
process::ExitCode,
|
||||||
|
};
|
||||||
|
|
||||||
|
extern crate getopt;
|
||||||
|
extern crate strerror;
|
||||||
|
extern crate sysexits;
|
||||||
|
|
||||||
|
use getopt::GetOpt;
|
||||||
|
use strerror::StrError;
|
||||||
|
use sysexits::EX_USAGE;
|
||||||
|
|
||||||
|
const OPTS: &str = "bcdefgkprsuwxLS";
|
||||||
|
|
||||||
|
fn usage(argv0: &str) -> ExitCode {
|
||||||
|
eprintln!("Usage: {} [-{}] file...", argv0, OPTS);
|
||||||
|
ExitCode::from(EX_USAGE)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main() -> ExitCode {
|
||||||
|
let argv = args().collect::<Vec<_>>();
|
||||||
|
|
||||||
|
let mut sel = String::with_capacity(OPTS.len()); // selected options
|
||||||
|
let mut optind: usize = 1; // argv[0]
|
||||||
|
|
||||||
|
while let Some(opt) = argv.getopt(OPTS) {
|
||||||
|
if let Ok(optchr) = opt.opt() { sel.push_str(optchr); }
|
||||||
|
else { return usage(&argv[0]); }
|
||||||
|
|
||||||
|
optind = opt.ind();
|
||||||
|
}
|
||||||
|
|
||||||
|
if optind == argv.len() { return usage(&argv[0]); }
|
||||||
|
|
||||||
|
for arg in argv.iter().skip(optind) {
|
||||||
|
let fmeta = match metadata(arg) {
|
||||||
|
Ok(m) => m,
|
||||||
|
Err(e) => { // no perms or nonexistent
|
||||||
|
eprintln!("{}: {}: {}", argv[0], arg, e.strerror());
|
||||||
|
return ExitCode::FAILURE;
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
let fmode = fmeta.mode();
|
||||||
|
let ftype = fmeta.file_type();
|
||||||
|
|
||||||
|
for selection in sel.chars() { // run all selected tests
|
||||||
|
match selection {
|
||||||
|
'b' if ftype.is_block_device() => (),
|
||||||
|
'c' if ftype.is_char_device() => (),
|
||||||
|
'e' => (), // exists or metadata would have errored
|
||||||
|
'd' if fmeta.is_dir() => (),
|
||||||
|
'f' if fmeta.is_file() => (),
|
||||||
|
'g' if fmode & 0o2000 /* S_ISGID */ != 0 => (), // setgid
|
||||||
|
'k' if fmode & 0o1000 /* S_ISVTX */ != 0 => (), // setvtx
|
||||||
|
'p' if ftype.is_fifo() => (),
|
||||||
|
'r' if fmode & 0o0400 /* S_IRUSR */ != 0 => (), // read access
|
||||||
|
'u' if fmode & 0o4000 /* S_ISUID */ != 0 => (), // setuid
|
||||||
|
'w' if fmode & 0o0200 /* S_IWUSR */ != 0 => (), // write access
|
||||||
|
'x' if fmode & 0o0100 /* S_IXUSR */ != 0 => (), // exec access
|
||||||
|
'L' if fmeta.is_symlink() => (),
|
||||||
|
'S' if ftype.is_socket() => (),
|
||||||
|
_ => { return ExitCode::FAILURE; }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ExitCode::SUCCESS
|
||||||
|
}
|
||||||
31
tests/README
31
tests/README
@@ -1,24 +1,13 @@
|
|||||||
The testing suite contains two trees: the Bonsai tree and the POSIX tree:
|
Tests
|
||||||
|
=====
|
||||||
|
|
||||||
.
|
The Harakit testing suite verifies the functionality of Harakit utilities
|
||||||
├── README
|
and checks for regressions and other issues relating to compliance to our
|
||||||
├── bonsai/
|
standards of practice.
|
||||||
│ ├── dj.mk
|
|
||||||
│ ├── false.mk
|
|
||||||
│ ├── fop.mk
|
|
||||||
│ └── ...
|
|
||||||
├── posix/
|
|
||||||
└── tests.mk
|
|
||||||
|
|
||||||
The Bonsai tree tests the functionality of Harakit utilities for regressions and
|
Tests inherit the environment set by the top-level Makefile, which sets the BIN
|
||||||
other issues relating to compliance to our standards of practice.
|
variable to the build/bin directory at the root of the project; therefore, each
|
||||||
|
binary is located at $(BIN)/tool for idiomatic access.
|
||||||
The POSIX tests are currently a work-in-progress. Their status in this
|
|
||||||
repository is uncertain.
|
|
||||||
|
|
||||||
Both sets of tests also inherit the environment set by the top-level Makefile,
|
|
||||||
which sets the BIN variable to the build/bin directory at the root of the
|
|
||||||
project; therefore, each binary is located at $(BIN)/tool for idiomatic access.
|
|
||||||
|
|
||||||
Each test contains a set of PHONY targets which are prefixed with the name of
|
Each test contains a set of PHONY targets which are prefixed with the name of
|
||||||
the tool being tested and an underscore. The first target is tests, which
|
the tool being tested and an underscore. The first target is tests, which
|
||||||
@@ -27,10 +16,10 @@ included in the top Makefile, so they can be called from the root of the
|
|||||||
repository. This also means that BIN can be set manually so that tests can be
|
repository. This also means that BIN can be set manually so that tests can be
|
||||||
run using make(1) inside of the tests directory:
|
run using make(1) inside of the tests directory:
|
||||||
|
|
||||||
$ make -f tests.mk BIN=../build/bin dj_tests
|
$ make -f dj.mk BIN=../build/bin dj_tests
|
||||||
|
|
||||||
--
|
--
|
||||||
Copyright © 2024 Emma Tebibyte <emma@tebibyte.media>
|
Copyright © 2024–2025 Emma Tebibyte <emma@tebibyte.media>
|
||||||
|
|
||||||
This work is licensed under CC BY-SA 4.0. To view a copy of this license, visit
|
This work is licensed under CC BY-SA 4.0. To view a copy of this license, visit
|
||||||
<http://creativecommons.org/licenses/by-sa/4.0/>.
|
<http://creativecommons.org/licenses/by-sa/4.0/>.
|
||||||
|
|||||||
@@ -8,20 +8,20 @@
|
|||||||
|
|
||||||
.PRAGMA: command_comment
|
.PRAGMA: command_comment
|
||||||
|
|
||||||
.PHONY: scrut_tests
|
.PHONY: fileis_tests
|
||||||
scrut_tests: scrut_help scrut_options
|
fileis_tests: fileis_help fileis_options
|
||||||
|
|
||||||
.PHONY: scrut_help
|
.PHONY: fileis_help
|
||||||
scrut_help: $(BIN)/scrut
|
fileis_help: $(BIN)/fileis
|
||||||
! $(BIN)/scrut -h
|
! $(BIN)/fileis -h
|
||||||
|
|
||||||
.PHONY: scrut_options
|
.PHONY: fileis_options
|
||||||
# scrut tests file attributes, but files of a certain attribute aren't
|
# fileis tests file attributes, but files of a certain attribute aren't
|
||||||
# guaranteed to be present on a system. This test checks all of the files in
|
# guaranteed to be present on a system. This test checks all of the files in
|
||||||
# harakit and, if test(1p) says a file matches a certain attribute, then checks
|
# harakit and, if test(1p) says a file matches a certain attribute, then checks
|
||||||
# scrut.
|
# fileis.
|
||||||
# opts are space-delimited (for command splitting), sel is not
|
# opts are space-delimited (for command splitting), sel is not
|
||||||
scrut_options: $(BIN)/scrut
|
fileis_options: $(BIN)/fileis
|
||||||
set -e; \
|
set -e; \
|
||||||
opts="b c d e f g k p r s u w x L S"; \
|
opts="b c d e f g k p r s u w x L S"; \
|
||||||
sel=; \
|
sel=; \
|
||||||
@@ -30,12 +30,12 @@ scrut_options: $(BIN)/scrut
|
|||||||
for opt in $$opts; \
|
for opt in $$opts; \
|
||||||
do if ! printf "%s\n" $$sel | grep $$opt >/dev/null; then \
|
do if ! printf "%s\n" $$sel | grep $$opt >/dev/null; then \
|
||||||
if test -$$opt "$$f"; then \
|
if test -$$opt "$$f"; then \
|
||||||
if ! $(BIN)/scrut -$$opt "$$f"; \
|
if ! $(BIN)/fileis -$$opt "$$f"; \
|
||||||
then printf "[!!] scrut -%s failed on %s.\n" \
|
then printf "[!!] fileis -%s failed on %s.\n" \
|
||||||
$$opt "$$f"; \
|
$$opt "$$f"; \
|
||||||
fi; \
|
fi; \
|
||||||
sel="$$sel$$opt"; \
|
sel="$$sel$$opt"; \
|
||||||
printf "[OK] Tested scrut -%s using %s\n" \
|
printf "[OK] Tested fileis -%s using %s\n" \
|
||||||
$$opt "$$f"; \
|
$$opt "$$f"; \
|
||||||
fi; \
|
fi; \
|
||||||
fi; \
|
fi; \
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
#!/bin/sh
|
#!/bin/sh
|
||||||
# Copyright (c) 2024 DTB <trinity@trinity.moe>
|
# Copyright (c) 2024 DTB <trinity@trinity.moe>
|
||||||
# Copyright (c) 2024 Emma Tebibyte <emma@tebibyte.media>
|
# Copyright (c) 2024–2025 Emma Tebibyte <emma@tebibyte.media>
|
||||||
# SPDX-License-Identifier: FSFAP
|
# SPDX-License-Identifier: FSFAP
|
||||||
#
|
#
|
||||||
# Copying and distribution of this file, with or without modification, are
|
# Copying and distribution of this file, with or without modification, are
|
||||||
@@ -26,7 +26,7 @@ npc_args:
|
|||||||
|
|
||||||
.PHONY: npc_ascii
|
.PHONY: npc_ascii
|
||||||
# Test 0x00 to 0x7f in input; in other words, the full 7b ASCII range.
|
# Test 0x00 to 0x7f in input; in other words, the full 7b ASCII range.
|
||||||
npc_ascii: npc_ascii_controls npc_ascii_symbols npc_ascii_uppers # \
|
npc_ascii: npc_ascii_controls npc_ascii_uppers # npc_ascii_symbols \
|
||||||
# npc_ascii_lowers
|
# npc_ascii_lowers
|
||||||
|
|
||||||
.PHONY: npc_ascii_controls
|
.PHONY: npc_ascii_controls
|
||||||
@@ -63,14 +63,18 @@ npc_ascii_controls:
|
|||||||
| tail -n 1 \
|
| tail -n 1 \
|
||||||
| xargs -I out test "^K^L^M^N^O^P^Q^R^S^T^U^V^W^X^Y^Z^[^\^]^^^_"
|
| xargs -I out test "^K^L^M^N^O^P^Q^R^S^T^U^V^W^X^Y^Z^[^\^]^^^_"
|
||||||
|
|
||||||
.PHONY: npc_ascii_symbols
|
# This test is broken on Linux and will need closer inspection along with GNU
|
||||||
# ASCII 0x1f to 0x3f (^_ and symbols)
|
# xargs(1).
|
||||||
npc_ascii_symbols:
|
# .PHONY: npc_ascii_symbols
|
||||||
# shell quoting olympics
|
# # ASCII 0x1f to 0x3f (^_ and symbols)
|
||||||
awk 'BEGIN{ for (i = 31; i < 64; ++i) printf("%c", i); print }' \
|
# npc_ascii_symbols:
|
||||||
| $(BIN)/npc \
|
# # shell quoting olympics
|
||||||
| sed -e s"/\'/\\\'/g" -e 's/"/\\"/g' \
|
# c="$(awk 'BEGIN{ for (i = 31; i < 64; ++i) printf("%c", i); print }')"
|
||||||
| xargs -I out test "^_ !\"#$$%&'()*+,-./0123456789:;<=>?" = out
|
#
|
||||||
|
# printf '%s\n' "$c" | $(BIN)/npc \
|
||||||
|
# | sed -e s"/\'/\\\'/g" -e 's/"/\\"/g' \
|
||||||
|
# | tr -d '\n' \
|
||||||
|
# | xargs -I out test "^_ !\"#$$%&\'()*+,-./0123456789:;<=>?" = out
|
||||||
|
|
||||||
.PHONY: npc_ascii_uppers
|
.PHONY: npc_ascii_uppers
|
||||||
# ASCII 0x40 to 0x5f (uppercases)
|
# ASCII 0x40 to 0x5f (uppercases)
|
||||||
@@ -1,22 +0,0 @@
|
|||||||
#!/bin/sh
|
|
||||||
# Copyright (c) 2024 Emma Tebibyte <emma@tebibyte.media>
|
|
||||||
# SPDX-License-Identifier: FSFAP
|
|
||||||
#
|
|
||||||
# Copying and distribution of this file, with or without modification, are
|
|
||||||
# permitted in any medium without royalty provided the copyright notice and this
|
|
||||||
# notice are preserved. This file is offered as-is, without any warranty.
|
|
||||||
|
|
||||||
# Strictly POSIX-compliant cat(1) implementation. See cat(1p)
|
|
||||||
|
|
||||||
for arg in "$@"; do
|
|
||||||
case "$arg" in
|
|
||||||
-u) args="$(printf '%s %s\n' "$args" "$arg")" ;;
|
|
||||||
*) args="$(printf -- '%s -i %s\n' "$args" "$arg")" ;;
|
|
||||||
esac
|
|
||||||
done
|
|
||||||
|
|
||||||
# See IEEE Std 1003.1-2017 3.282
|
|
||||||
# https://pubs.opengroup.org/onlinepubs/9699919799/basedefs/V1_chap03.html#tag_03_282
|
|
||||||
IFS=' '
|
|
||||||
|
|
||||||
mm $args
|
|
||||||
@@ -1,12 +0,0 @@
|
|||||||
#!/bin/sh
|
|
||||||
# Copyright (c) 2024 DTB <trinity@trinity.moe>
|
|
||||||
# Copyright (c) 2024 Emma Tebibyte <emma@tebibyte.media>
|
|
||||||
# SPDX-License-Identifier: FSFAP
|
|
||||||
#
|
|
||||||
# Copying and distribution of this file, with or without modification, are
|
|
||||||
# permitted in any medium without royalty provided the copyright notice and this
|
|
||||||
# notice are preserved. This file is offered as-is, without any warranty.
|
|
||||||
|
|
||||||
# Strictly POSIX-compliant false(1) implementation. See false(1p)
|
|
||||||
|
|
||||||
false "$@"
|
|
||||||
@@ -1,11 +0,0 @@
|
|||||||
#!/bin/sh
|
|
||||||
# Copyright (c) 2024 DTB <trinity@trinity.moe>
|
|
||||||
# Copyright (c) 2024 Emma Tebibyte <emma@tebibyte.media>
|
|
||||||
# SPDX-License-Identifier: FSFAP
|
|
||||||
#
|
|
||||||
# Copying and distribution of this file, with or without modification, are
|
|
||||||
# permitted in any medium without royalty provided the copyright notice and this
|
|
||||||
# notice are preserved. This file is offered as-is, without any warranty.
|
|
||||||
|
|
||||||
# Strictly POSIX-compliant true(1) implementation. See true(1p)
|
|
||||||
true "$@"
|
|
||||||
@@ -1,5 +0,0 @@
|
|||||||
#!/bin/sh
|
|
||||||
|
|
||||||
set -ex
|
|
||||||
|
|
||||||
PATH="$PWD/bin:$PATH"
|
|
||||||
@@ -1,15 +0,0 @@
|
|||||||
# Copyright (c) 2024 Emma Tebibyte <emma@tebibyte.media>
|
|
||||||
# SPDX-License-Identifier: FSFAP
|
|
||||||
#
|
|
||||||
# Copying and distribution of this file, with or without modification, are
|
|
||||||
# permitted in any medium without royalty provided the copyright notice and this
|
|
||||||
# notice are preserved. This file is offered as-is, without any warranty.
|
|
||||||
|
|
||||||
|
|
||||||
#TESTFILES != for file in tests/bonsai/*.mk tests/posix/*.mk; do printf '%s ' "$$file"; done;
|
|
||||||
TESTFILES != for file in tests/bonsai/*.mk; do printf '%s ' "$$file"; done;
|
|
||||||
|
|
||||||
TESTS != printf '%s\n' "$(TESTFILES)" | xargs -n1 basename \
|
|
||||||
| sed 's/\.mk/_tests/g'
|
|
||||||
|
|
||||||
include $(TESTFILES)
|
|
||||||
Reference in New Issue
Block a user