aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorLaurent Bercot <ska-skaware@skarnet.org>2025-12-09 05:46:14 +0000
committerLaurent Bercot <ska-skaware@skarnet.org>2025-12-09 05:46:14 +0000
commit420d8cef5cb8eed461a1b17dcd17de270571baf9 (patch)
tree65ff04a3a64ef12bc3553b90b1b0c33887f4fb2d /src
parentb1903e7ebc0f017c4f630ed9bc5a3ba823e0be86 (diff)
downloads6-rc-420d8cef5cb8eed461a1b17dcd17de270571baf9.tar.gz
Next batch of fixes
Diffstat (limited to 'src')
-rw-r--r--src/include/s6-rc/repo.h4
-rw-r--r--src/repo/deps-lib/s6rcrepo3
-rw-r--r--src/repo/s6-rc-set-change.c19
-rw-r--r--src/repo/s6-rc-set-commit.c4
-rw-r--r--src/repo/s6-rc-set-copy.c5
-rw-r--r--src/repo/s6-rc-set-delete.c10
-rw-r--r--src/repo/s6-rc-set-install.c3
-rw-r--r--src/repo/s6-rc-set-new.c10
-rw-r--r--src/repo/s6-rc-set-status.c36
-rw-r--r--src/repo/s6rc_repo_flattenservices.c7
-rw-r--r--src/repo/s6rc_repo_listcontents.c5
-rw-r--r--src/repo/s6rc_repo_listdeps_internal.c3
-rw-r--r--src/repo/s6rc_repo_removeinternals.c17
-rw-r--r--src/repo/s6rc_repo_sanitize_setname.c15
-rw-r--r--src/repo/s6rc_repo_sanitize_svname.c19
15 files changed, 103 insertions, 57 deletions
diff --git a/src/include/s6-rc/repo.h b/src/include/s6-rc/repo.h
index 17b7047..2dacf42 100644
--- a/src/include/s6-rc/repo.h
+++ b/src/include/s6-rc/repo.h
@@ -29,6 +29,9 @@ extern int s6rc_repo_makestores (char const *, char const *const *, uint16_t, ch
extern int s6rc_repo_fillset (char const *, char const *, char const *const *, uint32_t) ;
+extern void s6rc_repo_sanitize_setname (char const *) ;
+extern void s6rc_repo_sanitize_svname (char const *) ;
+
extern int s6rc_repo_cleanup (char const *) ;
extern int s6rc_repo_sync (char const *, unsigned int, char const *) ;
extern int s6rc_repo_syncset (char const *, char const *, unsigned int) ;
@@ -60,6 +63,7 @@ extern int s6rc_repo_makesvlist (char const *, char const *, stralloc *, genallo
extern int s6rc_repo_makesvlist_byname (char const *, char const *, stralloc *, genalloc *) ;
extern int s6rc_repo_badsub (char const *, char const *, char const **, uint32_t, uint8_t, uint8_t, s6rc_repo_sv const *, uint32_t, stralloc *, genalloc *) ;
extern int s6rc_repo_moveservices (char const *, char const *, s6rc_repo_sv const *, uint32_t, uint8_t, char const *, unsigned int) ;
+extern void s6rc_repo_removeinternals (genalloc *, unsigned int, char const *) ;
extern int s6rc_repo_fixset (char const *, char const *, uint32_t, unsigned int, stralloc *, genalloc *, genalloc *) ;
extern int s6rc_repo_fix (char const *, uint32_t, unsigned int) ;
diff --git a/src/repo/deps-lib/s6rcrepo b/src/repo/deps-lib/s6rcrepo
index 7014ea1..c9d90f2 100644
--- a/src/repo/deps-lib/s6rcrepo
+++ b/src/repo/deps-lib/s6rcrepo
@@ -20,6 +20,9 @@ s6rc_repo_makestores.o
s6rc_repo_makesvlist.o
s6rc_repo_makesvlist_byname.o
s6rc_repo_moveservices.o
+s6rc_repo_removeinternals.o
+s6rc_repo_sanitize_setname.o
+s6rc_repo_sanitize_svname.o
s6rc_repo_setcompile.o
s6rc_repo_setuptodate.o
s6rc_repo_subnames.o
diff --git a/src/repo/s6-rc-set-change.c b/src/repo/s6-rc-set-change.c
index 5d5bd80..8d6d27f 100644
--- a/src/repo/s6-rc-set-change.c
+++ b/src/repo/s6-rc-set-change.c
@@ -122,21 +122,12 @@ int main (int argc, char const *const *argv)
forcelevel = p->sub ;
}
if (argc < 3) dieusage() ;
- if (strchr(argv[0], '/') || strchr(argv[0], '\n'))
- strerr_dief1x(100, "set names cannot contain / or newlines") ;
-
+ s6rc_repo_sanitize_setname(argv[0]) ;
newsub = bsearch(argv[1], accepted_subs, sizeof(accepted_subs)/sizeof(struct subname_s), sizeof(struct subname_s), &subname_cmp) ;
if (!newsub) strerr_dief2x(100, "unrecognized state change directive:", argv[1]) ;
if (newsub->sub == 3 && !(wgolb & GOLB_FORCE_ESSENTIAL))
- strerr_diefu1x(10, " artificially mark a service as essential without --force-essential") ;
-
- for (unsigned int i = 2 ; i < argc ; i++)
- {
- if (argv[i][0] == '.')
- strerr_dief2x(100, "service names cannot ", "start with a dot") ;
- if (strchr(argv[i], '/') || strchr(argv[i], '\n'))
- strerr_dief2x(100, "service names cannot ", "contain / or newlines") ;
- }
+ strerr_diefu1x(100, " artificially mark a service as essential without --force-essential") ;
+ for (unsigned int i = 2 ; i < argc ; i++) s6rc_repo_sanitize_svname(argv[i]) ;
tain_now_g() ;
fdlock = s6rc_repo_lock(wgola[GOLA_REPODIR], 1) ;
@@ -146,8 +137,8 @@ int main (int argc, char const *const *argv)
listn = genalloc_len(s6rc_repo_sv, &svlist) ;
sabase = storage.len ;
{
- int r = s6rc_repo_flattenservices(wgola[GOLA_REPODIR], argv + 2, argc - 2, &storage, &indices) ;
- if (r) _exit(r) ;
+ int e = s6rc_repo_flattenservices(wgola[GOLA_REPODIR], argv + 2, argc - 2, &storage, &indices) ;
+ if (e) _exit(e) ;
}
n = genalloc_len(size_t, &indices) ;
if (!n) strerr_dief1x(101, "can't happen: 0 services in flattened list!") ;
diff --git a/src/repo/s6-rc-set-commit.c b/src/repo/s6-rc-set-commit.c
index c4c7967..e5a3619 100644
--- a/src/repo/s6-rc-set-commit.c
+++ b/src/repo/s6-rc-set-commit.c
@@ -70,8 +70,8 @@ int main (int argc, char const *const *argv)
if (wgola[GOLA_VERBOSITY] && !uint0_scan(wgola[GOLA_VERBOSITY], &verbosity))
strerr_dief1x(100, "verbosity needs to be an unsigned integer") ;
if (!argc) dieusage() ;
- if (strchr(argv[0], '/') || strchr(argv[0], '\n'))
- strerr_dief1x(100, "set names cannot contain / or newlines") ;
+ s6rc_repo_sanitize_setname(argv[0]) ;
+
tain_now_g() ;
fdlock = s6rc_repo_lock(wgola[GOLA_REPODIR], 1) ;
if (fdlock == -1) strerr_diefu2sys(111, "lock ", wgola[GOLA_REPODIR]) ;
diff --git a/src/repo/s6-rc-set-copy.c b/src/repo/s6-rc-set-copy.c
index 637093d..8a5992e 100644
--- a/src/repo/s6-rc-set-copy.c
+++ b/src/repo/s6-rc-set-copy.c
@@ -119,9 +119,8 @@ int main (int argc, char const *const *argv)
if (wgola[GOLA_VERBOSITY] && !uint0_scan(wgola[GOLA_VERBOSITY], &verbosity))
strerr_dief1x(100, "verbosity needs to be an unsigned integer") ;
if (argc < 2) dieusage() ;
- for (unsigned int i = 0 ; i < 2 ; i++)
- if (strchr(argv[i], '/') || strchr(argv[i], '\n'))
- strerr_dief1x(100, "set names cannot contain / or newlines") ;
+ s6rc_repo_sanitize_setname(argv[0]) ;
+ s6rc_repo_sanitize_setname(argv[1]) ;
tain_now_g() ;
fdlock = s6rc_repo_lock(wgola[GOLA_REPODIR], 1) ;
diff --git a/src/repo/s6-rc-set-delete.c b/src/repo/s6-rc-set-delete.c
index 95f4216..2987033 100644
--- a/src/repo/s6-rc-set-delete.c
+++ b/src/repo/s6-rc-set-delete.c
@@ -98,15 +98,7 @@ int main (int argc, char const *const *argv)
if (wgola[GOLA_VERBOSITY] && !uint0_scan(wgola[GOLA_VERBOSITY], &verbosity))
strerr_dief1x(100, "verbosity needs to be an unsigned integer") ;
if (!argc) dieusage() ;
- for (unsigned int i = 0 ; i < argc ; i++)
- {
- if (!argv[i][0])
- strerr_dief2x(100, "set names cannot ", "be empty") ;
- if (argv[i][0] == '.')
- strerr_dief2x(100, "set names cannot ", "start with a dot") ;
- if (strchr(argv[i], '/') || strchr(argv[i], '\n'))
- strerr_dief2x(100, "set names cannot ", "contain / or newlines") ;
- }
+ for (unsigned int i = 0 ; i < argc ; i++) s6rc_repo_sanitize_setname(argv[i]) ;
tain_now_g() ;
fdlock = s6rc_repo_lock(wgola[GOLA_REPODIR], 1) ;
diff --git a/src/repo/s6-rc-set-install.c b/src/repo/s6-rc-set-install.c
index e4f754f..a3a82df 100644
--- a/src/repo/s6-rc-set-install.c
+++ b/src/repo/s6-rc-set-install.c
@@ -79,8 +79,7 @@ int main (int argc, char const *const *argv)
if (wgola[GOLA_VERBOSITY] && !uint0_scan(wgola[GOLA_VERBOSITY], &verbosity))
strerr_dief1x(100, "verbosity needs to be an unsigned integer") ;
if (!argc) dieusage() ;
- if (strchr(argv[0], '/') || strchr(argv[0], '\n'))
- strerr_dief1x(100, "set names cannot contain / or newlines") ;
+ s6rc_repo_sanitize_setname(argv[0]) ;
tain_now_g() ;
fdlock = s6rc_repo_lock(wgola[GOLA_REPODIR], 0) ;
diff --git a/src/repo/s6-rc-set-new.c b/src/repo/s6-rc-set-new.c
index d40d29e..a685aa6 100644
--- a/src/repo/s6-rc-set-new.c
+++ b/src/repo/s6-rc-set-new.c
@@ -115,15 +115,7 @@ int main (int argc, char const *const *argv)
if (wgola[GOLA_VERBOSITY] && !uint0_scan(wgola[GOLA_VERBOSITY], &verbosity))
strerr_dief1x(100, "verbosity needs to be an unsigned integer") ;
if (!argc) dieusage() ;
- for (unsigned int i = 0 ; i < argc ; i++)
- {
- if (!argv[i][0])
- strerr_dief2x(100, "set names cannot ", "be empty") ;
- if (argv[i][0] == '.')
- strerr_dief2x(100, "set names cannot ", "start with a dot") ;
- if (strchr(argv[i], '/') || strchr(argv[i], '\n'))
- strerr_dief2x(100, "set names cannot ", "contain / or newlines") ;
- }
+ for (unsigned int i = 0 ; i < argc ; i++) s6rc_repo_sanitize_setname(argv[i]) ;
tain_now_g() ;
fdlock = s6rc_repo_lock(wgola[GOLA_REPODIR], 1) ;
diff --git a/src/repo/s6-rc-set-status.c b/src/repo/s6-rc-set-status.c
index 7c07e9d..f6b6e5f 100644
--- a/src/repo/s6-rc-set-status.c
+++ b/src/repo/s6-rc-set-status.c
@@ -12,11 +12,13 @@
#include <skalibs/direntry.h>
#include <skalibs/buffer.h>
#include <skalibs/tai.h>
+#include <skalibs/stralloc.h>
+#include <skalibs/genalloc.h>
#include <s6-rc/config.h>
#include <s6-rc/repo.h>
-#define USAGE "s6-rc-set-status [ -v verbosity ] [ -r repo ] [ -E | -e ] set services..."
+#define USAGE "s6-rc-set-status [ -v verbosity ] [ -r repo ] [ -E | -e ] [ -L ] set services..."
#define dieusage() strerr_dieusage(100, USAGE)
#define dieout() strerr_diefu1sys(111, "write to stdout")
@@ -46,6 +48,8 @@ int main (int argc, char const **argv)
{ .so = 'v', .lo = "verbosity", .i = GOLA_VERBOSITY },
{ .so = 'r', .lo = "repodir", .i = GOLA_REPODIR }
} ;
+ stralloc sa = STRALLOC_ZERO ;
+ genalloc ga = GENALLOC_ZERO ; /* size_t */
int fdlock ;
unsigned int verbosity = 1 ;
uint64_t wgolb = 0 ;
@@ -59,19 +63,12 @@ int main (int argc, char const **argv)
golc = GOL_main(argc, argv, rgolb, rgola, &wgolb, wgola) ;
argc -= golc ; argv += golc ;
- if (argc < 2) dieusage() ;
+ if (!argc) dieusage() ;
setname = *argv++ ; argc-- ;
if (wgola[GOLA_VERBOSITY] && !uint0_scan(wgola[GOLA_VERBOSITY], &verbosity))
strerr_dief1x(100, "verbosity needs to be an unsigned integer") ;
- if (strchr(setname, '/') || strchr(setname, '\n'))
- strerr_dief2x(100, "set", " names cannot contain / or newlines") ;
- for (unsigned int i = 0 ; i < argc ; i++)
- {
- if (argv[i][0] == '.')
- strerr_dief2x(100, "service", " names cannot start with a dot") ;
- if (strchr(argv[i], '/') || strchr(argv[i], '\n'))
- strerr_dief2x(100, "service", " names cannot contain / or newlines") ;
- }
+ s6rc_repo_sanitize_setname(setname) ;
+ for (unsigned int i = 0 ; i < argc ; i++) s6rc_repo_sanitize_svname(argv[i]) ;
tain_now_g() ;
fdlock = s6rc_repo_lock(wgola[GOLA_REPODIR], 1) ;
@@ -82,7 +79,20 @@ int main (int argc, char const **argv)
if (e) _exit(e) ;
}
- qsort(argv, argc, sizeof(char const *), &str_cmp) ;
+ if (argc)
+ {
+ int e = s6rc_repo_flattenservices(wgola[GOLA_REPODIR], argv, argc, &sa, &ga) ;
+ if (e) _exit(e) ;
+ argc = genalloc_len(size_t, &ga) ;
+ }
+ char const *flatargv[argc ? argc : 1] ;
+ if (argc)
+ {
+ for (unsigned int i = 0 ; i < argc ; i++)
+ flatargv[i] = sa.s + genalloc_s(size_t, &ga)[i] ;
+ qsort(flatargv, argc, sizeof(char const *), &str_cmp) ;
+ genalloc_free(size_t, &ga) ;
+ }
size_t repolen = strlen(wgola[GOLA_REPODIR]) ;
size_t setlen = strlen(setname) ;
@@ -105,7 +115,7 @@ int main (int argc, char const **argv)
d = readdir(dir) ;
if (!d) break ;
if (d->d_name[0] == '.') continue ;
- if (argc && !bsearch(d->d_name, argv, argc, sizeof(char const *), &str_bcmp)) continue ;
+ if (argc && !bsearch(d->d_name, flatargv, argc, sizeof(char const *), &str_bcmp)) continue ;
if (buffer_puts(buffer_1, d->d_name) < 0) dieout() ;
if (!(wgolb & GOLB_NOSUB))
if (buffer_put(buffer_1, "/", 1) < 0
diff --git a/src/repo/s6rc_repo_flattenservices.c b/src/repo/s6rc_repo_flattenservices.c
index cf3dc55..36a0aad 100644
--- a/src/repo/s6rc_repo_flattenservices.c
+++ b/src/repo/s6rc_repo_flattenservices.c
@@ -22,7 +22,7 @@ int s6rc_repo_flattenservices (char const *repo, char const *const *services, ui
int swasnull = !storage->s ;
int gwasnull = !indices->s ;
size_t sabase = storage->len ;
- size_t gabase = genalloc_len(size_t, indices) ;
+ uint32_t gabase = genalloc_len(size_t, indices) ;
{
size_t m = 0 ;
@@ -61,9 +61,12 @@ int s6rc_repo_flattenservices (char const *repo, char const *const *services, ui
if (WEXITSTATUS(wstat)) return WEXITSTATUS(wstat) ;
}
- if (!string_index(storage->s + sabase, sabase, storage->len, '\n', indices)) goto err ;
+ if (!string_index(storage->s, sabase, storage->len - sabase, '\n', indices)) goto err2 ;
+ s6rc_repo_removeinternals(indices, gabase, storage->s) ;
return 0 ;
+ err2:
+ strerr_warnfu1sys("index services") ;
err:
if (gwasnull) genalloc_free(size_t, indices) ;
else genalloc_setlen(size_t, indices, gabase) ;
diff --git a/src/repo/s6rc_repo_listcontents.c b/src/repo/s6rc_repo_listcontents.c
index bcfc946..bb9a99b 100644
--- a/src/repo/s6rc_repo_listcontents.c
+++ b/src/repo/s6rc_repo_listcontents.c
@@ -56,8 +56,9 @@ int s6rc_repo_listcontents (char const *repo, char const *bundle, stralloc *stor
return (WEXITSTATUS(wstat) < 99) - 1 ;
}
- if (!string_index(storage->s + sabase, sabase, storage->len, '\n', indices)) goto err ;
- return 1 ;
+ if (!string_index(storage->s, sabase, storage->len - sabase, '\n', indices)) goto err ;
+ s6rc_repo_removeinternals(indices, gabase, storage->s) ;
+ return 1 ;
err:
if (gwasnull) genalloc_free(size_t, indices) ;
diff --git a/src/repo/s6rc_repo_listdeps_internal.c b/src/repo/s6rc_repo_listdeps_internal.c
index 5af879a..78c7ca1 100644
--- a/src/repo/s6rc_repo_listdeps_internal.c
+++ b/src/repo/s6rc_repo_listdeps_internal.c
@@ -62,7 +62,8 @@ int s6rc_repo_listdeps_internal (char const *repo, char const *const *services,
if (WEXITSTATUS(wstat)) return wait_estatus(wstat) ;
}
- if (!string_index(storage->s + sabase, sabase, storage->len, '\n', indices)) goto err ;
+ if (!string_index(storage->s, sabase, storage->len - sabase, '\n', indices)) goto err ;
+ s6rc_repo_removeinternals(indices, gabase, storage->s) ;
return 0 ;
err:
diff --git a/src/repo/s6rc_repo_removeinternals.c b/src/repo/s6rc_repo_removeinternals.c
new file mode 100644
index 0000000..8c3da8c
--- /dev/null
+++ b/src/repo/s6rc_repo_removeinternals.c
@@ -0,0 +1,17 @@
+/* ISC license. */
+
+#include <string.h>
+
+#include <skalibs/genalloc.h>
+
+#include <s6-rc/repo.h>
+
+void s6rc_repo_removeinternals (genalloc *ga, unsigned int start, char const *s)
+{
+ size_t *indices = genalloc_s(size_t, ga) ;
+ unsigned int n = genalloc_len(size_t, ga) ;
+ for (unsigned int i = start ; i < n ; i++)
+ if (!strncmp(s + indices[i], "s6rc-", 5) || !strncmp(s + indices[i], "s6-rc-", 6))
+ indices[i--] = indices[--n] ;
+ genalloc_setlen(size_t, ga, n) ;
+}
diff --git a/src/repo/s6rc_repo_sanitize_setname.c b/src/repo/s6rc_repo_sanitize_setname.c
new file mode 100644
index 0000000..07edc44
--- /dev/null
+++ b/src/repo/s6rc_repo_sanitize_setname.c
@@ -0,0 +1,15 @@
+/* ISC license. */
+
+#include <string.h>
+
+#include <skalibs/strerr.h>
+
+#include <s6-rc/repo.h>
+
+void s6rc_repo_sanitize_setname (char const *set)
+{
+ if (!set[0])
+ strerr_dief2x(100, "set names cannot ", "be empty") ;
+ if (strchr(set, '/') || strchr(set, '\n'))
+ strerr_dief2x(100, "set names cannot ", "contain / or newlines") ;
+}
diff --git a/src/repo/s6rc_repo_sanitize_svname.c b/src/repo/s6rc_repo_sanitize_svname.c
new file mode 100644
index 0000000..2d0fdb3
--- /dev/null
+++ b/src/repo/s6rc_repo_sanitize_svname.c
@@ -0,0 +1,19 @@
+/* ISC license. */
+
+#include <string.h>
+
+#include <skalibs/strerr.h>
+
+#include <s6-rc/repo.h>
+
+void s6rc_repo_sanitize_svname (char const *sv)
+{
+ if (!sv[0])
+ strerr_dief2x(100, "service names cannot ", "be empty") ;
+ if (sv[0] == '.')
+ strerr_dief3x(100, "service names cannot ", "start with ", "a dot") ;
+ if (strchr(sv, '/') || strchr(sv, '\n'))
+ strerr_dief2x(100, "service names cannot ", "contain / or newlines") ;
+ if (!strncmp(sv, "s6rc-", 5) || !strncmp(sv, "s6-rc-", 6))
+ strerr_dief3x(100, "service names cannot ", "start with ", "reserved prefixes") ;
+}