feature. See also
. The project being documented here (as the example) is the Zig library itself.
Threaded.fileLock
fn fileLock(userdata: ?*anyopaque, file: File, lock: File.Lock) File.LockError!void
File
Code
fn fileLock(userdata: ?*anyopaque, file: File, lock: File.Lock) File.LockError!void {
if (native_os == .wasi) return error.FileLocksUnsupported;
const t: *Threaded = @ptrCast(@alignCast(userdata));
_ = t;
if (is_windows) {
const exclusive = switch (lock) {
.none => {
var io_status_block: windows.IO_STATUS_BLOCK = undefined;
while (true) switch (windows.ntdll.NtUnlockFile(
file.handle,
&io_status_block,
&windows_lock_range_off,
&windows_lock_range_len,
0,
)) {
.SUCCESS => return,
.CANCELLED => continue,
.RANGE_NOT_LOCKED => return,
.ACCESS_VIOLATION => |err| return windows.statusBug(err),
else => |status| return windows.unexpectedStatus(status),
};
},
.shared => false,
.exclusive => true,
};
var io_status_block: windows.IO_STATUS_BLOCK = undefined;
const syscall: Syscall = try .start();
while (true) switch (windows.ntdll.NtLockFile(
file.handle,
null,
null,
null,
&io_status_block,
&windows_lock_range_off,
&windows_lock_range_len,
null,
.FALSE,
.fromBool(exclusive),
)) {
.SUCCESS => return syscall.finish(),
.CANCELLED => {
try syscall.checkCancel();
continue;
},
.INSUFFICIENT_RESOURCES => return syscall.fail(error.SystemResources),
.LOCK_NOT_GRANTED => |err| return syscall.ntstatusBug(err),
.ACCESS_VIOLATION => |err| return syscall.ntstatusBug(err),
else => |status| return syscall.unexpectedNtstatus(status),
};
}
const operation: i32 = switch (lock) {
.none => posix.LOCK.UN,
.shared => posix.LOCK.SH,
.exclusive => posix.LOCK.EX,
};
const syscall: Syscall = try .start();
while (true) {
switch (posix.errno(posix.system.flock(file.handle, operation))) {
.SUCCESS => return syscall.finish(),
.INTR => {
try syscall.checkCancel();
continue;
},
else => |e| {
syscall.finish();
switch (e) {
.BADF => |err| return errnoBug(err),
.INVAL => |err| return errnoBug(err),
.NOLCK => return error.SystemResources,
.AGAIN => |err| return errnoBug(err),
.OPNOTSUPP => return error.FileLocksUnsupported,
else => |err| return posix.unexpectedErrno(err),
}
},
}
}
}