commit: 47fdc92256b2437431ceb5fbbdc1a1e75635357c Author: Michał Górny <mgorny <AT> gentoo <DOT> org> AuthorDate: Thu Nov 27 19:54:01 2025 +0000 Commit: Michał Górny <mgorny <AT> gentoo <DOT> org> CommitDate: Thu Nov 27 19:54:01 2025 +0000 URL: https://gitweb.gentoo.org/proj/steve.git/commit/?id=47fdc922
Add a hack for `nasm-rs` pre-releasing tokens `nasm-rs` is releasing a token that it did not acquire itself in order to account for the extra token acquired for the parent process (make's "implicit slot"). While this is invalid, let's add a workaround to permit the process to hold -1 tokens in order to unbreak builds while packages go through Cargo's insanely broken update model. Bug: https://github.com/medek/nasm-rs/issues/44 Signed-off-by: Michał Górny <mgorny <AT> gentoo.org> steve.cxx | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/steve.cxx b/steve.cxx index 8b61368..a6ed034 100644 --- a/steve.cxx +++ b/steve.cxx @@ -56,7 +56,7 @@ struct steve_poll_waiter { struct steve_process { int pid_fd{-1}; - size_t tokens_held{0}; + ssize_t tokens_held{0}; std::unique_ptr<struct event, std::function<void(struct event*)>> event; ~steve_process() { @@ -283,11 +283,24 @@ static void steve_write( fuse_reply_err(req, EIO); return; } + if (size > SSIZE_MAX) { + std::print(stderr, "Warning: process {} tried to return more than SSIZE_MAX tokens\n", + fi->fh); + fuse_reply_err(req, EFBIG); + return; + } - if (state->processes[fi->fh].tokens_held < size) { + /* workaround for https://github.com/medek/nasm-rs/issues/44 */ + if (state->processes[fi->fh].tokens_held == 0 && size == 1) { + std::print(stderr, "Warning: process {} pre-released an unacquired token, please report a bug upstream\n", + fi->fh); + } else if (state->processes[fi->fh].tokens_held < static_cast<ssize_t>(size)) { std::print(stderr, "Warning: process {} tried to return {} tokens while holding only {} tokens, capping\n", fi->fh, size, state->processes[fi->fh].tokens_held); - size = state->processes[fi->fh].tokens_held; + if (state->processes[fi->fh].tokens_held < 0) + size = 0; + else + size = state->processes[fi->fh].tokens_held; } if (size == 0) { fuse_reply_err(req, ENOSPC);
