libutil: remote unsafeLockFileSingleThreaded

while this does require spawning a thread for every contended lock now
we don't expect performance to be impacted. only build-remote used the
synchronous method, and it only used it to serialize uploads to remote
builders. these uploads are expensive enough to dwarf the thread cost.

Change-Id: Iad0aa0cd738bc96fd06a90d655803dadffa09c47
This commit is contained in:
eldritch horrors
2025-07-14 17:02:30 +00:00
parent df45583c7a
commit 280772583f
3 changed files with 6 additions and 30 deletions
+6 -1
View File
@@ -5,6 +5,7 @@
#include <chrono>
#include <cstring>
#include <future>
#include <kj/time.h>
#include <set>
#include <memory>
#include <string>
@@ -413,8 +414,12 @@ static int main_build_remote(AsyncIoRoot & aio, std::string programName, Strings
{
Activity act(*logger, lvlTalkative, actUnknown, fmt("waiting for the upload lock to '%s'", storeUri));
if (!unsafeLockFileSingleThreaded(uploadLock.get(), ltWrite, std::chrono::minutes(15)))
auto result = aio.blockOn(
AIO().timeoutAfter(15 * kj::MINUTES, lockFileAsync(uploadLock.get(), ltWrite))
);
if (!result) {
printError("somebody is hogging the upload lock for '%s', continuing...");
}
}
auto substitute = settings.buildersUseSubstitutes ? Substitute : NoSubstitute;
-22
View File
@@ -87,28 +87,6 @@ try {
return {result::current_exception()};
}
bool unsafeLockFileSingleThreaded(int fd, LockType lockType, std::chrono::seconds timeout)
{
int type = convertLockType(lockType);
auto old = signal(SIGALRM, [](int) {});
alarm(timeout.count());
KJ_DEFER({
alarm(0);
signal(SIGALRM, old);
});
while (flock(fd, type) != 0) {
checkInterrupt();
if (errno != EINTR)
throw SysError("acquiring lock");
else
return false;
}
return true;
}
bool tryLockFile(int fd, LockType lockType)
{
int type = convertLockType(lockType);
-7
View File
@@ -22,13 +22,6 @@ enum LockType { ltRead, ltWrite };
void lockFile(int fd, LockType lockType, NeverAsync = {});
kj::Promise<Result<void>> lockFileAsync(int fd, LockType lockType);
/**
* Same as `lockFile`, but with a timeout. This timeout uses the POSIX `alarm`
* facility and a `SIGALRM` handler. Using this function from multiple threads
* in the same process is not safe: all `SIGALRM` handlers set previously will
* be overwritten while this function is executing and are restored on return.
*/
bool unsafeLockFileSingleThreaded(int fd, LockType lockType, std::chrono::seconds timeout);
bool tryLockFile(int fd, LockType lockType);
void unlockFile(int fd);