diff options
| author | Vincent Rischmann <vincent@rischmann.fr> | 2021-02-27 23:30:43 +0100 |
|---|---|---|
| committer | Veikka Tuominen <git@vexu.eu> | 2021-06-09 18:15:50 +0300 |
| commit | c71e8a30cdf050e45c2ca2dc81e93b10cf00dc5f (patch) | |
| tree | 3641124b53b25db7d628b28d47b423cabb35488b /lib/std | |
| parent | 7f32c799a95dd8a54ca7f984f41524021ceee2ce (diff) | |
| download | zig-c71e8a30cdf050e45c2ca2dc81e93b10cf00dc5f.tar.gz zig-c71e8a30cdf050e45c2ca2dc81e93b10cf00dc5f.zip | |
os/linux: add fadvise
Diffstat (limited to 'lib/std')
| -rw-r--r-- | lib/std/os/linux.zig | 59 | ||||
| -rw-r--r-- | lib/std/os/linux/test.zig | 20 |
2 files changed, 79 insertions, 0 deletions
diff --git a/lib/std/os/linux.zig b/lib/std/os/linux.zig index 9e7b38fe90..85916004d1 100644 --- a/lib/std/os/linux.zig +++ b/lib/std/os/linux.zig @@ -1454,6 +1454,65 @@ pub fn process_vm_writev(pid: pid_t, local: [*]const iovec, local_count: usize, ); } +pub fn fadvise(fd: fd_t, offset: i64, len: i64, advice: usize) usize { + if (comptime std.Target.current.cpu.arch.isMIPS()) { + // MIPS requires a 7 argument syscall + + const offset_halves = splitValue64(offset); + const length_halves = splitValue64(len); + + return syscall7( + .fadvise64, + @bitCast(usize, @as(isize, fd)), + 0, + offset_halves[0], + offset_halves[1], + length_halves[0], + length_halves[1], + advice, + ); + } else if (comptime std.Target.current.cpu.arch.isARM()) { + // ARM reorders the arguments + + const offset_halves = splitValue64(offset); + const length_halves = splitValue64(len); + + return syscall6( + .fadvise64_64, + @bitCast(usize, @as(isize, fd)), + advice, + offset_halves[0], + offset_halves[1], + length_halves[0], + length_halves[1], + ); + } else if (@hasField(SYS, "fadvise64_64") and usize_bits != 64) { + // The extra usize check is needed to avoid SPARC64 because it provides both + // fadvise64 and fadvise64_64 but the latter behaves differently than other platforms. + + const offset_halves = splitValue64(offset); + const length_halves = splitValue64(len); + + return syscall6( + .fadvise64_64, + @bitCast(usize, @as(isize, fd)), + offset_halves[0], + offset_halves[1], + length_halves[0], + length_halves[1], + advice, + ); + } else { + return syscall4( + .fadvise64, + @bitCast(usize, @as(isize, fd)), + @bitCast(usize, offset), + @bitCast(usize, len), + advice, + ); + } +} + test { if (std.Target.current.os.tag == .linux) { _ = @import("linux/test.zig"); diff --git a/lib/std/os/linux/test.zig b/lib/std/os/linux/test.zig index c4a00c48ec..2e98fe359d 100644 --- a/lib/std/os/linux/test.zig +++ b/lib/std/os/linux/test.zig @@ -108,3 +108,23 @@ test "user and group ids" { try expectEqual(linux.getauxval(elf.AT_EUID), linux.geteuid()); try expectEqual(linux.getauxval(elf.AT_EGID), linux.getegid()); } + +test "fadvise" { + const tmp_file_name = "temp_posix_fadvise.txt"; + var file = try fs.cwd().createFile(tmp_file_name, .{}); + defer { + file.close(); + fs.cwd().deleteFile(tmp_file_name) catch {}; + } + + var buf: [2048]u8 = undefined; + try file.writeAll(&buf); + + const ret = linux.fadvise( + file.handle, + 0, + 0, + linux.POSIX_FADV_SEQUENTIAL, + ); + try expectEqual(@as(usize, 0), ret); +} |
