aboutsummaryrefslogtreecommitdiff
path: root/lib/std
diff options
context:
space:
mode:
authorAndrew Kelley <andrew@ziglang.org>2025-12-11 22:35:55 -0800
committerAndrew Kelley <andrew@ziglang.org>2025-12-23 22:15:09 -0800
commite1cf753db72425fd944f6fe9f2a991fb1de3f942 (patch)
tree4b9c33aa2cd4e0da5ad7e5fec9f0de45c6747507 /lib/std
parent68621afd2e203d82b6f53bf4ede951827fa98db8 (diff)
downloadzig-e1cf753db72425fd944f6fe9f2a991fb1de3f942.tar.gz
zig-e1cf753db72425fd944f6fe9f2a991fb1de3f942.zip
std: update fchmodat tests
Diffstat (limited to 'lib/std')
-rw-r--r--lib/std/Build.zig2
-rw-r--r--lib/std/Io/Dir.zig2
-rw-r--r--lib/std/Io/Kqueue.zig4
-rw-r--r--lib/std/fs/test.zig487
-rw-r--r--lib/std/posix/test.zig61
5 files changed, 243 insertions, 313 deletions
diff --git a/lib/std/Build.zig b/lib/std/Build.zig
index 085254fdde..b7300cb5df 100644
--- a/lib/std/Build.zig
+++ b/lib/std/Build.zig
@@ -1698,7 +1698,7 @@ pub fn addCheckFile(
return Step.CheckFile.create(b, file_source, options);
}
-pub fn truncateFile(b: *Build, dest_path: []const u8) (Io.Dir.MakeError || Io.Dir.StatPathError)!void {
+pub fn truncateFile(b: *Build, dest_path: []const u8) (Io.Dir.MakeError || Io.Dir.StatFileError)!void {
const io = b.graph.io;
if (b.verbose) log.info("truncate {s}", .{dest_path});
const cwd = Io.Dir.cwd();
diff --git a/lib/std/Io/Dir.zig b/lib/std/Io/Dir.zig
index 0bc3982a61..be82b8b8b2 100644
--- a/lib/std/Io/Dir.zig
+++ b/lib/std/Io/Dir.zig
@@ -1710,7 +1710,7 @@ pub const SetFilePermissionsOptions = struct {
follow_symlinks: bool = true,
};
-/// Also known as "chmodat".
+/// Also known as "fchmodat".
pub fn setFilePermissions(
dir: Dir,
io: Io,
diff --git a/lib/std/Io/Kqueue.zig b/lib/std/Io/Kqueue.zig
index e34c862ae9..9f9403d5ad 100644
--- a/lib/std/Io/Kqueue.zig
+++ b/lib/std/Io/Kqueue.zig
@@ -873,7 +873,7 @@ pub fn io(k: *Kqueue) Io {
.dirMakePath = dirMakePath,
.dirMakeOpenPath = dirMakeOpenPath,
.dirStat = dirStat,
- .dirStatPath = dirStatPath,
+ .dirStatFile = dirStatFile,
.fileStat = fileStat,
.dirAccess = dirAccess,
@@ -1144,7 +1144,7 @@ fn dirStat(userdata: ?*anyopaque, dir: Dir) Dir.StatError!Dir.Stat {
_ = dir;
@panic("TODO");
}
-fn dirStatPath(userdata: ?*anyopaque, dir: Dir, sub_path: []const u8, options: Dir.StatPathOptions) Dir.StatPathError!File.Stat {
+fn dirStatFile(userdata: ?*anyopaque, dir: Dir, sub_path: []const u8, options: Dir.StatPathOptions) Dir.StatFileError!File.Stat {
const k: *Kqueue = @ptrCast(@alignCast(userdata));
_ = k;
_ = dir;
diff --git a/lib/std/fs/test.zig b/lib/std/fs/test.zig
index dd9b21d77b..5205e8eacf 100644
--- a/lib/std/fs/test.zig
+++ b/lib/std/fs/test.zig
@@ -3,19 +3,23 @@ const native_os = builtin.os.tag;
const std = @import("../std.zig");
const Io = std.Io;
-const testing = std.testing;
-const expect = std.testing.expect;
const fs = std.fs;
const mem = std.mem;
const wasi = std.os.wasi;
const windows = std.os.windows;
-const posix = std.posix;
const ArenaAllocator = std.heap.ArenaAllocator;
const Dir = std.Io.Dir;
const File = std.Io.File;
-const tmpDir = std.testing.tmpDir;
const SymLinkFlags = std.Io.Dir.SymLinkFlags;
+const testing = std.testing;
+const expect = std.testing.expect;
+const expectError = std.testing.expectError;
+const expectEqual = std.testing.expectEqual;
+const tmpDir = std.testing.tmpDir;
+const expectEqualStrings = std.testing.expectEqualStrings;
+const expectEqualSlices = std.testing.expectEqualSlices;
+
const PathType = enum {
relative,
absolute,
@@ -29,7 +33,7 @@ const PathType = enum {
};
}
- pub const TransformError = posix.RealPathError || error{OutOfMemory};
+ pub const TransformError = Io.Dir.RealPathError || error{OutOfMemory};
pub const TransformFn = fn (allocator: mem.Allocator, dir: Dir, relative_path: [:0]const u8) TransformError![:0]const u8;
pub fn getTransformFn(comptime path_type: PathType) TransformFn {
@@ -249,7 +253,7 @@ test "Dir.readLink on non-symlinks" {
fn testReadLink(io: Io, dir: Dir, target_path: []const u8, symlink_path: []const u8) !void {
var buffer: [fs.max_path_bytes]u8 = undefined;
const actual = try dir.readLink(io, symlink_path, &buffer);
- try testing.expectEqualStrings(target_path, actual);
+ try expectEqualStrings(target_path, actual);
}
fn testReadLinkW(allocator: mem.Allocator, dir: Dir, target_path: []const u8, symlink_path: []const u8) !void {
@@ -260,13 +264,13 @@ fn testReadLinkW(allocator: mem.Allocator, dir: Dir, target_path: []const u8, sy
const wtf16_buffer = try allocator.alloc(u16, target_path_w.len);
defer allocator.free(wtf16_buffer);
const actual = try dir.readLinkW(symlink_path_w.span(), wtf16_buffer);
- try testing.expectEqualSlices(u16, target_path_w, actual);
+ try expectEqualSlices(u16, target_path_w, actual);
}
fn testReadLinkAbsolute(target_path: []const u8, symlink_path: []const u8) !void {
var buffer: [fs.max_path_bytes]u8 = undefined;
const given = try fs.readLinkAbsolute(symlink_path, buffer[0..]);
- try testing.expectEqualStrings(target_path, given);
+ try expectEqualStrings(target_path, given);
}
test "File.stat on a File that is a symlink returns Kind.sym_link" {
@@ -286,72 +290,11 @@ test "File.stat on a File that is a symlink returns Kind.sym_link" {
try setupSymlink(io, ctx.dir, dir_target_path, "symlink", .{ .is_directory = true });
- var symlink: Dir = switch (builtin.target.os.tag) {
- .windows => windows_symlink: {
- const sub_path_w = try windows.cStrToPrefixedFileW(ctx.dir.handle, "symlink");
-
- var result: Dir = .{
- .handle = undefined,
- };
-
- const path_len_bytes = @as(u16, @intCast(sub_path_w.span().len * 2));
- var nt_name = windows.UNICODE_STRING{
- .Length = path_len_bytes,
- .MaximumLength = path_len_bytes,
- .Buffer = @constCast(&sub_path_w.data),
- };
- var attr: windows.OBJECT_ATTRIBUTES = .{
- .Length = @sizeOf(windows.OBJECT_ATTRIBUTES),
- .RootDirectory = if (fs.path.isAbsoluteWindowsW(sub_path_w.span())) null else ctx.dir.handle,
- .Attributes = 0,
- .ObjectName = &nt_name,
- .SecurityDescriptor = null,
- .SecurityQualityOfService = null,
- };
- var io_status_block: windows.IO_STATUS_BLOCK = undefined;
- const rc = windows.ntdll.NtCreateFile(
- &result.handle,
- windows.STANDARD_RIGHTS_READ | windows.FILE_READ_ATTRIBUTES | windows.FILE_READ_EA | windows.SYNCHRONIZE | windows.FILE_TRAVERSE,
- &attr,
- &io_status_block,
- null,
- .{ .NORMAL = true },
- .VALID_FLAGS,
- .OPEN,
- .{
- .DIRECTORY_FILE = true,
- .IO = .SYNCHRONOUS_NONALERT,
- .OPEN_FOR_BACKUP_INTENT = true,
- .OPEN_REPARSE_POINT = true, // the important thing here
- },
- null,
- 0,
- );
-
- switch (rc) {
- .SUCCESS => break :windows_symlink .{ .fd = result.handle },
- else => return windows.unexpectedStatus(rc),
- }
- },
- .linux => linux_symlink: {
- const sub_path_c = try posix.toPosixPath("symlink");
- // the O_NOFOLLOW | O_PATH combination can obtain a fd to a symlink
- // note that if O_DIRECTORY is set, then this will error with ENOTDIR
- const flags: posix.O = .{
- .NOFOLLOW = true,
- .PATH = true,
- .ACCMODE = .RDONLY,
- .CLOEXEC = true,
- };
- const fd = try posix.openatZ(ctx.dir.handle, &sub_path_c, flags, 0);
- break :linux_symlink .{ .handle = fd };
- },
- else => unreachable,
- };
+ var symlink: Dir = try ctx.dir.openDir("symlink", .{ .follow_symlinks = false });
defer symlink.close(io);
const stat = try symlink.stat(io);
- try testing.expectEqual(File.Kind.sym_link, stat.kind);
+ try expectEqual(File.Kind.sym_link, stat.kind);
}
}.impl);
}
@@ -417,7 +360,7 @@ test "openDirAbsolute" {
defer dir.close(io);
const ino = (try dir.stat(io)).inode;
- try testing.expectEqual(tmp_ino, ino);
+ try expectEqual(tmp_ino, ino);
}
{
@@ -429,7 +372,7 @@ test "openDirAbsolute" {
defer dir.close(io);
const ino = (try dir.stat(io)).inode;
- try testing.expectEqual(sub_ino, ino);
+ try expectEqual(sub_ino, ino);
}
{
@@ -441,7 +384,7 @@ test "openDirAbsolute" {
defer dir.close(io);
const ino = (try dir.stat(io)).inode;
- try testing.expectEqual(tmp_ino, ino);
+ try expectEqual(tmp_ino, ino);
}
}
@@ -480,7 +423,7 @@ test "openDir non-cwd parent '..'" {
const actual_path = try dir.realpathAlloc(testing.allocator, ".");
defer testing.allocator.free(actual_path);
- try testing.expectEqualStrings(expected_path, actual_path);
+ try expectEqualStrings(expected_path, actual_path);
}
test "readLinkAbsolute" {
@@ -548,7 +491,7 @@ test "Dir.Iterator" {
try entries.append(Dir.Entry{ .name = name, .kind = entry.kind });
}
- try testing.expectEqual(@as(usize, 2), entries.items.len); // note that the Iterator skips '.' and '..'
+ try expectEqual(@as(usize, 2), entries.items.len); // note that the Iterator skips '.' and '..'
try testing.expect(contains(&entries, .{ .name = "some_file", .kind = .file }));
try testing.expect(contains(&entries, .{ .name = "some_dir", .kind = .directory }));
}
@@ -619,7 +562,7 @@ test "Dir.Iterator twice" {
try entries.append(Dir.Entry{ .name = name, .kind = entry.kind });
}
- try testing.expectEqual(@as(usize, 2), entries.items.len); // note that the Iterator skips '.' and '..'
+ try expectEqual(@as(usize, 2), entries.items.len); // note that the Iterator skips '.' and '..'
try testing.expect(contains(&entries, .{ .name = "some_file", .kind = .file }));
try testing.expect(contains(&entries, .{ .name = "some_dir", .kind = .directory }));
}
@@ -655,7 +598,7 @@ test "Dir.Iterator reset" {
try entries.append(.{ .name = name, .kind = entry.kind });
}
- try testing.expectEqual(@as(usize, 2), entries.items.len); // note that the Iterator skips '.' and '..'
+ try expectEqual(@as(usize, 2), entries.items.len); // note that the Iterator skips '.' and '..'
try testing.expect(contains(&entries, .{ .name = "some_file", .kind = .file }));
try testing.expect(contains(&entries, .{ .name = "some_dir", .kind = .directory }));
@@ -690,7 +633,7 @@ test "Dir.Iterator but dir is deleted during iteration" {
// On Linux, we can opt-in to receiving a more specific error by calling `nextLinux`
if (native_os == .linux) {
- try std.testing.expectError(error.DirNotFound, iterator.nextLinux());
+ try expectError(error.DirNotFound, iterator.nextLinux());
}
}
@@ -717,10 +660,10 @@ test "Dir.realpath smoke test" {
var buf: [fs.max_path_bytes]u8 = undefined;
// FileNotFound if the path doesn't exist
- try testing.expectError(error.FileNotFound, ctx.dir.realpathAlloc(allocator, test_file_path));
- try testing.expectError(error.FileNotFound, ctx.dir.realpath(test_file_path, &buf));
- try testing.expectError(error.FileNotFound, ctx.dir.realpathAlloc(allocator, test_dir_path));
- try testing.expectError(error.FileNotFound, ctx.dir.realpath(test_dir_path, &buf));
+ try expectError(error.FileNotFound, ctx.dir.realpathAlloc(allocator, test_file_path));
+ try expectError(error.FileNotFound, ctx.dir.realpath(test_file_path, &buf));
+ try expectError(error.FileNotFound, ctx.dir.realpathAlloc(allocator, test_dir_path));
+ try expectError(error.FileNotFound, ctx.dir.realpath(test_dir_path, &buf));
// Now create the file and dir
try ctx.dir.writeFile(io, .{ .sub_path = test_file_path, .data = "" });
@@ -740,19 +683,19 @@ test "Dir.realpath smoke test" {
// First, test non-alloc version
{
const file_path = try ctx.dir.realpath(test_file_path, &buf);
- try testing.expectEqualStrings(expected_file_path, file_path);
+ try expectEqualStrings(expected_file_path, file_path);
const dir_path = try ctx.dir.realpath(test_dir_path, &buf);
- try testing.expectEqualStrings(expected_dir_path, dir_path);
+ try expectEqualStrings(expected_dir_path, dir_path);
}
// Next, test alloc version
{
const file_path = try ctx.dir.realpathAlloc(allocator, test_file_path);
- try testing.expectEqualStrings(expected_file_path, file_path);
+ try expectEqualStrings(expected_file_path, file_path);
const dir_path = try ctx.dir.realpathAlloc(allocator, test_dir_path);
- try testing.expectEqualStrings(expected_dir_path, dir_path);
+ try expectEqualStrings(expected_dir_path, dir_path);
}
}
}.impl);
@@ -769,7 +712,7 @@ test "readFileAlloc" {
const buf1 = try tmp_dir.dir.readFileAlloc(io, "test_file", testing.allocator, .limited(1024));
defer testing.allocator.free(buf1);
- try testing.expectEqualStrings("", buf1);
+ try expectEqualStrings("", buf1);
const write_buf: []const u8 = "this is a test.\nthis is a test.\nthis is a test.\nthis is a test.\n";
try file.writeAll(write_buf);
@@ -778,12 +721,12 @@ test "readFileAlloc" {
// max_bytes > file_size
const buf2 = try tmp_dir.dir.readFileAlloc(io, "test_file", testing.allocator, .limited(1024));
defer testing.allocator.free(buf2);
- try testing.expectEqualStrings(write_buf, buf2);
+ try expectEqualStrings(write_buf, buf2);
}
{
// max_bytes == file_size
- try testing.expectError(
+ try expectError(
error.StreamTooLong,
tmp_dir.dir.readFileAlloc(io, "test_file", testing.allocator, .limited(write_buf.len)),
);
@@ -793,11 +736,11 @@ test "readFileAlloc" {
// max_bytes == file_size + 1
const buf2 = try tmp_dir.dir.readFileAlloc(io, "test_file", testing.allocator, .limited(write_buf.len + 1));
defer testing.allocator.free(buf2);
- try testing.expectEqualStrings(write_buf, buf2);
+ try expectEqualStrings(write_buf, buf2);
}
// max_bytes < file_size
- try testing.expectError(
+ try expectError(
error.StreamTooLong,
tmp_dir.dir.readFileAlloc(io, "test_file", testing.allocator, .limited(write_buf.len - 1)),
);
@@ -809,12 +752,12 @@ test "Dir.statFile" {
const io = ctx.io;
const test_file_name = try ctx.transformPath("test_file");
- try testing.expectError(error.FileNotFound, ctx.dir.statFile(io, test_file_name, .{}));
+ try expectError(error.FileNotFound, ctx.dir.statFile(io, test_file_name, .{}));
try ctx.dir.writeFile(io, .{ .sub_path = test_file_name, .data = "" });
const stat = try ctx.dir.statFile(io, test_file_name, .{});
- try testing.expectEqual(File.Kind.file, stat.kind);
+ try expectEqual(File.Kind.file, stat.kind);
}
}.impl);
}
@@ -828,7 +771,7 @@ test "statFile on dangling symlink" {
try setupSymlink(io, ctx.dir, symlink_target, symlink_name, .{});
- try std.testing.expectError(error.FileNotFound, ctx.dir.statFile(io, symlink_name, .{}));
+ try expectError(error.FileNotFound, ctx.dir.statFile(io, symlink_name, .{}));
}
}.impl);
}
@@ -843,19 +786,19 @@ test "directory operations on files" {
var file = try ctx.dir.createFile(io, test_file_name, .{ .read = true });
file.close(io);
- try testing.expectError(error.PathAlreadyExists, ctx.dir.makeDir(io, test_file_name, .default_dir));
- try testing.expectError(error.NotDir, ctx.dir.openDir(io, test_file_name, .{}));
- try testing.expectError(error.NotDir, ctx.dir.deleteDir(io, test_file_name));
+ try expectError(error.PathAlreadyExists, ctx.dir.makeDir(io, test_file_name, .default_dir));
+ try expectError(error.NotDir, ctx.dir.openDir(io, test_file_name, .{}));
+ try expectError(error.NotDir, ctx.dir.deleteDir(io, test_file_name));
if (ctx.path_type == .absolute and comptime PathType.absolute.isSupported(builtin.os)) {
- try testing.expectError(error.PathAlreadyExists, fs.makeDirAbsolute(test_file_name));
- try testing.expectError(error.NotDir, fs.deleteDirAbsolute(test_file_name));
+ try expectError(error.PathAlreadyExists, fs.makeDirAbsolute(test_file_name));
+ try expectError(error.NotDir, fs.deleteDirAbsolute(test_file_name));
}
// ensure the file still exists and is a file as a sanity check
file = try ctx.dir.openFile(io, test_file_name, .{});
const stat = try file.stat(io);
- try testing.expectEqual(File.Kind.file, stat.kind);
+ try expectEqual(File.Kind.file, stat.kind);
file.close(io);
}
}.impl);
@@ -873,8 +816,8 @@ test "file operations on directories" {
try ctx.dir.makeDir(io, test_dir_name, .default_dir);
- try testing.expectError(error.IsDir, ctx.dir.createFile(io, test_dir_name, .{}));
- try testing.expectError(error.IsDir, ctx.dir.deleteFile(io, test_dir_name));
+ try expectError(error.IsDir, ctx.dir.createFile(io, test_dir_name, .{}));
+ try expectError(error.IsDir, ctx.dir.deleteFile(io, test_dir_name));
switch (native_os) {
.dragonfly, .netbsd => {
// no error when reading a directory. See https://github.com/ziglang/zig/issues/5732
@@ -884,10 +827,10 @@ test "file operations on directories" {
.wasi => {
// WASI return EBADF, which gets mapped to NotOpenForReading.
// See https://github.com/bytecodealliance/wasmtime/issues/1935
- try testing.expectError(error.NotOpenForReading, ctx.dir.readFileAlloc(io, test_dir_name, testing.allocator, .unlimited));
+ try expectError(error.NotOpenForReading, ctx.dir.readFileAlloc(io, test_dir_name, testing.allocator, .unlimited));
},
else => {
- try testing.expectError(error.IsDir, ctx.dir.readFileAlloc(io, test_dir_name, testing.allocator, .unlimited));
+ try expectError(error.IsDir, ctx.dir.readFileAlloc(io, test_dir_name, testing.allocator, .unlimited));
},
}
@@ -898,12 +841,12 @@ test "file operations on directories" {
} else {
// Note: The `.mode = .read_write` is necessary to ensure the error occurs on all platforms.
// TODO: Add a read-only test as well, see https://github.com/ziglang/zig/issues/5732
- try testing.expectError(error.IsDir, ctx.dir.openFile(io, test_dir_name, .{ .mode = .read_write }));
+ try expectError(error.IsDir, ctx.dir.openFile(io, test_dir_name, .{ .mode = .read_write }));
}
if (ctx.path_type == .absolute and comptime PathType.absolute.isSupported(builtin.os)) {
- try testing.expectError(error.IsDir, fs.createFileAbsolute(test_dir_name, .{}));
- try testing.expectError(error.IsDir, fs.deleteFileAbsolute(test_dir_name));
+ try expectError(error.IsDir, fs.createFileAbsolute(test_dir_name, .{}));
+ try expectError(error.IsDir, fs.deleteFileAbsolute(test_dir_name));
}
// ensure the directory still exists as a sanity check
@@ -935,12 +878,12 @@ test "deleteDir" {
const test_file_path = try ctx.transformPath("test_dir" ++ fs.path.sep_str ++ "test_file");
// deleting a non-existent directory
- try testing.expectError(error.FileNotFound, ctx.dir.deleteDir(io, test_dir_path));
+ try expectError(error.FileNotFound, ctx.dir.deleteDir(io, test_dir_path));
// deleting a non-empty directory
try ctx.dir.makeDir(io, test_dir_path, .default_dir);
try ctx.dir.writeFile(io, .{ .sub_path = test_file_path, .data = "" });
- try testing.expectError(error.DirNotEmpty, ctx.dir.deleteDir(io, test_dir_path));
+ try expectError(error.DirNotEmpty, ctx.dir.deleteDir(io, test_dir_path));
// deleting an empty directory
try ctx.dir.deleteFile(io, test_file_path);
@@ -962,7 +905,7 @@ test "Dir.rename files" {
const missing_file_path = try ctx.transformPath("missing_file_name");
const something_else_path = try ctx.transformPath("something_else");
- try testing.expectError(error.FileNotFound, ctx.dir.rename(missing_file_path, ctx.dir, something_else_path, io));
+ try expectError(error.FileNotFound, ctx.dir.rename(missing_file_path, ctx.dir, something_else_path, io));
// Renaming files
const test_file_name = try ctx.transformPath("test_file");
@@ -972,7 +915,7 @@ test "Dir.rename files" {
try ctx.dir.rename(test_file_name, ctx.dir, renamed_test_file_name, io);
// Ensure the file was renamed
- try testing.expectError(error.FileNotFound, ctx.dir.openFile(io, test_file_name, .{}));
+ try expectError(error.FileNotFound, ctx.dir.openFile(io, test_file_name, .{}));
file = try ctx.dir.openFile(io, renamed_test_file_name, .{});
file.close(io);
@@ -985,7 +928,7 @@ test "Dir.rename files" {
existing_file.close(io);
try ctx.dir.rename(renamed_test_file_name, ctx.dir, existing_file_path, io);
- try testing.expectError(error.FileNotFound, ctx.dir.openFile(io, renamed_test_file_name, .{}));
+ try expectError(error.FileNotFound, ctx.dir.openFile(io, renamed_test_file_name, .{}));
file = try ctx.dir.openFile(io, existing_file_path, .{});
file.close(io);
}
@@ -1011,7 +954,7 @@ test "Dir.rename directories" {
try ctx.dir.rename(test_dir_path, ctx.dir, test_dir_renamed_path, io);
// Ensure the directory was renamed
- try testing.expectError(error.FileNotFound, ctx.dir.openDir(io, test_dir_path, .{}));
+ try expectError(error.FileNotFound, ctx.dir.openDir(io, test_dir_path, .{}));
var dir = try ctx.dir.openDir(io, test_dir_renamed_path, .{});
// Put a file in the directory
@@ -1023,7 +966,7 @@ test "Dir.rename directories" {
try ctx.dir.rename(test_dir_renamed_path, ctx.dir, test_dir_renamed_again_path, io);
// Ensure the directory was renamed and the file still exists in it
- try testing.expectError(error.FileNotFound, ctx.dir.openDir(io, test_dir_renamed_path, .{}));
+ try expectError(error.FileNotFound, ctx.dir.openDir(io, test_dir_renamed_path, .{}));
dir = try ctx.dir.openDir(io, test_dir_renamed_again_path, .{});
file = try dir.openFile(io, "test_file", .{});
file.close(io);
@@ -1048,7 +991,7 @@ test "Dir.rename directory onto empty dir" {
try ctx.dir.rename(test_dir_path, ctx.dir, target_dir_path, io);
// Ensure the directory was renamed
- try testing.expectError(error.FileNotFound, ctx.dir.openDir(io, test_dir_path, .{}));
+ try expectError(error.FileNotFound, ctx.dir.openDir(io, test_dir_path, .{}));
var dir = try ctx.dir.openDir(io, target_dir_path, .{});
dir.close(io);
}
@@ -1073,7 +1016,7 @@ test "Dir.rename directory onto non-empty dir" {
target_dir.close(io);
// Rename should fail with PathAlreadyExists if target_dir is non-empty
- try testing.expectError(error.PathAlreadyExists, ctx.dir.rename(test_dir_path, ctx.dir, target_dir_path, io));
+ try expectError(error.PathAlreadyExists, ctx.dir.rename(test_dir_path, ctx.dir, target_dir_path, io));
// Ensure the directory was not renamed
var dir = try ctx.dir.openDir(io, test_dir_path, .{});
@@ -1095,8 +1038,8 @@ test "Dir.rename file <-> dir" {
var file = try ctx.dir.createFile(io, test_file_path, .{ .read = true });
file.close(io);
try ctx.dir.makeDir(io, test_dir_path, .default_dir);
- try testing.expectError(error.IsDir, ctx.dir.rename(test_file_path, ctx.dir, test_dir_path, io));
- try testing.expectError(error.NotDir, ctx.dir.rename(test_dir_path, ctx.dir, test_file_path, io));
+ try expectError(error.IsDir, ctx.dir.rename(test_file_path, ctx.dir, test_dir_path, io));
+ try expectError(error.NotDir, ctx.dir.rename(test_dir_path, ctx.dir, test_file_path, io));
}
}.impl);
}
@@ -1118,7 +1061,7 @@ test "rename" {
try Dir.rename(tmp_dir1.dir, test_file_name, tmp_dir2.dir, renamed_test_file_name, io);
// ensure the file was renamed
- try testing.expectError(error.FileNotFound, tmp_dir1.dir.openFile(io, test_file_name, .{}));
+ try expectError(error.FileNotFound, tmp_dir1.dir.openFile(io, test_file_name, .{}));
file = try tmp_dir2.dir.openFile(io, renamed_test_file_name, .{});
file.close(io);
}
@@ -1139,7 +1082,7 @@ test "renameAbsolute" {
const base_path = try tmp_dir.dir.realpathAlloc(allocator, ".");
- try testing.expectError(error.FileNotFound, fs.renameAbsolute(
+ try expectError(error.FileNotFound, fs.renameAbsolute(
try fs.path.join(allocator, &.{ base_path, "missing_file_name" }),
try fs.path.join(allocator, &.{ base_path, "something_else" }),
));
@@ -1155,10 +1098,10 @@ test "renameAbsolute" {
);
// ensure the file was renamed
- try testing.expectError(error.FileNotFound, tmp_dir.dir.openFile(io, test_file_name, .{}));
+ try expectError(error.FileNotFound, tmp_dir.dir.openFile(io, test_file_name, .{}));
file = try tmp_dir.dir.openFile(io, renamed_test_file_name, .{});
const stat = try file.stat(io);
- try testing.expectEqual(File.Kind.file, stat.kind);
+ try expectEqual(File.Kind.file, stat.kind);
file.close(io);
// Renaming directories
@@ -1171,7 +1114,7 @@ test "renameAbsolute" {
);
// ensure the directory was renamed
- try testing.expectError(error.FileNotFound, tmp_dir.dir.openDir(io, test_dir_name, .{}));
+ try expectError(error.FileNotFound, tmp_dir.dir.openDir(io, test_dir_name, .{}));
var dir = try tmp_dir.dir.openDir(io, renamed_test_dir_name, .{});
dir.close(io);
}
@@ -1193,7 +1136,7 @@ test "executablePath" {
const buf_self_exe_path = try std.process.executablePath(io, &buf);
const alloc_self_exe_path = try std.process.executablePathAlloc(io, testing.allocator);
defer testing.allocator.free(alloc_self_exe_path);
- try testing.expectEqualSlices(u8, buf_self_exe_path, alloc_self_exe_path);
+ try expectEqualSlices(u8, buf_self_exe_path, alloc_self_exe_path);
}
test "deleteTree does not follow symlinks" {
@@ -1212,7 +1155,7 @@ test "deleteTree does not follow symlinks" {
try tmp.dir.deleteTree(io, "a");
- try testing.expectError(error.FileNotFound, tmp.dir.access(io, "a", .{}));
+ try expectError(error.FileNotFound, tmp.dir.access(io, "a", .{}));
try tmp.dir.access(io, "b", .{});
}
@@ -1227,7 +1170,7 @@ test "deleteTree on a symlink" {
try setupSymlink(io, tmp.dir, "file", "filelink", .{});
try tmp.dir.deleteTree(io, "filelink");
- try testing.expectError(error.FileNotFound, tmp.dir.access(io, "filelink", .{}));
+ try expectError(error.FileNotFound, tmp.dir.access(io, "filelink", .{}));
try tmp.dir.access(io, "file", .{});
// Symlink to a directory
@@ -1235,7 +1178,7 @@ test "deleteTree on a symlink" {
try setupSymlink(io, tmp.dir, "dir", "dirlink", .{ .is_directory = true });
try tmp.dir.deleteTree(io, "dirlink");
- try testing.expectError(error.FileNotFound, tmp.dir.access(io, "dirlink", .{}));
+ try expectError(error.FileNotFound, tmp.dir.access(io, "dirlink", .{}));
try tmp.dir.access(io, "dir", .{});
}
@@ -1257,7 +1200,7 @@ test "makePath, put some files in it, deleteTree" {
});
try ctx.dir.deleteTree(io, dir_path);
- try testing.expectError(error.FileNotFound, ctx.dir.openDir(io, dir_path, .{}));
+ try expectError(error.FileNotFound, ctx.dir.openDir(io, dir_path, .{}));
}
}.impl);
}
@@ -1280,7 +1223,7 @@ test "makePath, put some files in it, deleteTreeMinStackSize" {
});
try ctx.dir.deleteTreeMinStackSize(dir_path);
- try testing.expectError(error.FileNotFound, ctx.dir.openDir(io, dir_path, .{}));
+ try expectError(error.FileNotFound, ctx.dir.openDir(io, dir_path, .{}));
}
}.impl);
}
@@ -1294,7 +1237,7 @@ test "makePath in a directory that no longer exists" {
defer tmp.cleanup();
try tmp.parent_dir.deleteTree(io, &tmp.sub_path);
- try testing.expectError(error.FileNotFound, tmp.dir.makePath(io, "sub-path"));
+ try expectError(error.FileNotFound, tmp.dir.makePath(io, "sub-path"));
}
test "makePath but sub_path contains pre-existing file" {
@@ -1306,7 +1249,7 @@ test "makePath but sub_path contains pre-existing file" {
try tmp.dir.makeDir(io, "foo", .default_dir);
try tmp.dir.writeFile(io, .{ .sub_path = "foo/bar", .data = "" });
- try testing.expectError(error.NotDir, tmp.dir.makePath(io, "foo/bar/baz"));
+ try expectError(error.NotDir, tmp.dir.makePath(io, "foo/bar/baz"));
}
fn expectDir(io: Io, dir: Dir, path: []const u8) !void {
@@ -1364,8 +1307,8 @@ test "makepath relative walks" {
// On Windows, .. is resolved before passing the path to NtCreateFile,
// meaning everything except `first/C` drops out.
try expectDir(io, tmp.dir, "first" ++ fs.path.sep_str ++ "C");
- try testing.expectError(error.FileNotFound, tmp.dir.access(io, "second", .{}));
- try testing.expectError(error.FileNotFound, tmp.dir.access(io, "third", .{}));
+ try expectError(error.FileNotFound, tmp.dir.access(io, "second", .{}));
+ try expectError(error.FileNotFound, tmp.dir.access(io, "third", .{}));
},
else => {
try expectDir(io, tmp.dir, "first" ++ fs.path.sep_str ++ "A");
@@ -1413,10 +1356,10 @@ fn testFilenameLimits(io: Io, iterable_dir: Dir, maxed_filename: []const u8) !vo
var count: usize = 0;
while (try walker.next()) |entry| {
- try testing.expectEqualStrings(maxed_filename, entry.basename);
+ try expectEqualStrings(maxed_filename, entry.basename);
count += 1;
}
- try testing.expectEqual(@as(usize, 2), count);
+ try expectEqual(@as(usize, 2), count);
}
// ensure that we can delete the tree
@@ -1467,14 +1410,14 @@ test "writev, readv" {
try writer.interface.writeVecAll(&write_vecs);
try writer.interface.flush();
- try testing.expectEqual(@as(u64, line1.len + line2.len), try src_file.length(io));
+ try expectEqual(@as(u64, line1.len + line2.len), try src_file.length(io));
var reader = writer.moveToReader(io);
try reader.seekTo(0);
try reader.interface.readVecAll(&read_vecs);
- try testing.expectEqualStrings(&buf1, "line2\n");
- try testing.expectEqualStrings(&buf2, "line1\n");
- try testing.expectError(error.EndOfStream, reader.interface.readSliceAll(&buf1));
+ try expectEqualStrings(&buf1, "line2\n");
+ try expectEqualStrings(&buf2, "line1\n");
+ try expectError(error.EndOfStream, reader.interface.readSliceAll(&buf1));
}
test "pwritev, preadv" {
@@ -1498,14 +1441,14 @@ test "pwritev, preadv" {
try writer.seekTo(16);
try writer.interface.writeVecAll(&lines);
try writer.interface.flush();
- try testing.expectEqual(@as(u64, 16 + line1.len + line2.len), try src_file.length(io));
+ try expectEqual(@as(u64, 16 + line1.len + line2.len), try src_file.length(io));
var reader = writer.moveToReader(io);
try reader.seekTo(16);
try reader.interface.readVecAll(&read_vecs);
- try testing.expectEqualStrings(&buf1, "line2\n");
- try testing.expectEqualStrings(&buf2, "line1\n");
- try testing.expectError(error.EndOfStream, reader.interface.readSliceAll(&buf1));
+ try expectEqualStrings(&buf1, "line2\n");
+ try expectEqualStrings(&buf2, "line1\n");
+ try expectError(error.EndOfStream, reader.interface.readSliceAll(&buf1));
}
test "setEndPos" {
@@ -1529,34 +1472,34 @@ test "setEndPos" {
{
try f.setEndPos(initial_size);
- try testing.expectEqual(initial_size, try f.length(io));
+ try expectEqual(initial_size, try f.length(io));
try reader.seekTo(0);
- try testing.expectEqual(initial_size, try reader.interface.readSliceShort(&buffer));
- try testing.expectEqualStrings("ninebytes", buffer[0..@intCast(initial_size)]);
+ try expectEqual(initial_size, try reader.interface.readSliceShort(&buffer));
+ try expectEqualStrings("ninebytes", buffer[0..@intCast(initial_size)]);
}
{
const larger = initial_size + 4;
try f.setEndPos(larger);
- try testing.expectEqual(larger, try f.length(io));
+ try expectEqual(larger, try f.length(io));
try reader.seekTo(0);
- try testing.expectEqual(larger, try reader.interface.readSliceShort(&buffer));
- try testing.expectEqualStrings("ninebytes\x00\x00\x00\x00", buffer[0..@intCast(larger)]);
+ try expectEqual(larger, try reader.interface.readSliceShort(&buffer));
+ try expectEqualStrings("ninebytes\x00\x00\x00\x00", buffer[0..@intCast(larger)]);
}
{
const smaller = initial_size - 5;
try f.setEndPos(smaller);
- try testing.expectEqual(smaller, try f.length(io));
+ try expectEqual(smaller, try f.length(io));
try reader.seekTo(0);
- try testing.expectEqual(smaller, try reader.interface.readSliceShort(&buffer));
- try testing.expectEqualStrings("nine", buffer[0..@intCast(smaller)]);
+ try expectEqual(smaller, try reader.interface.readSliceShort(&buffer));
+ try expectEqualStrings("nine", buffer[0..@intCast(smaller)]);
}
try f.setEndPos(0);
- try testing.expectEqual(0, try f.length(io));
+ try expectEqual(0, try f.length(io));
try reader.seekTo(0);
- try testing.expectEqual(0, try reader.interface.readSliceShort(&buffer));
+ try expectEqual(0, try reader.interface.readSliceShort(&buffer));
}
test "access file" {
@@ -1567,7 +1510,7 @@ test "access file" {
const file_path = try ctx.transformPath("os_test_tmp" ++ fs.path.sep_str ++ "file.txt");
try ctx.dir.makePath(io, dir_path);
- try testing.expectError(error.FileNotFound, ctx.dir.access(io, file_path, .{}));
+ try expectError(error.FileNotFound, ctx.dir.access(io, file_path, .{}));
try ctx.dir.writeFile(io, .{ .sub_path = file_path, .data = "" });
try ctx.dir.access(io, file_path, .{});
@@ -1614,13 +1557,13 @@ test "sendfile" {
var file_writer = dest_file.writer(io, &fallback_buffer);
try file_writer.interface.writeVecAll(&headers);
try file_reader.seekTo(1);
- try testing.expectEqual(10, try file_writer.interface.sendFileAll(&file_reader, .limited(10)));
+ try expectEqual(10, try file_writer.interface.sendFileAll(&file_reader, .limited(10)));
try file_writer.interface.writeVecAll(&trailers);
try file_writer.interface.flush();
var fr = file_writer.moveToReader(io);
try fr.seekTo(0);
const amt = try fr.interface.readSliceShort(&written_buf);
- try testing.expectEqualStrings("header1\nsecond header\nine1\nsecontrailer1\nsecond trailer\n", written_buf[0..amt]);
+ try expectEqualStrings("header1\nsecond header\nine1\nsecontrailer1\nsecond trailer\n", written_buf[0..amt]);
}
test "sendfile with buffered data" {
@@ -1651,15 +1594,15 @@ test "sendfile with buffered data" {
var fallback_buffer: [32]u8 = undefined;
var file_writer = dest_file.writer(io, &fallback_buffer);
- try std.testing.expectEqual(4, try file_writer.interface.sendFileAll(&file_reader, .limited(4)));
+ try expectEqual(4, try file_writer.interface.sendFileAll(&file_reader, .limited(4)));
var written_buf: [8]u8 = undefined;
var fr = file_writer.moveToReader(io);
try fr.seekTo(0);
const amt = try fr.interface.readSliceShort(&written_buf);
- try std.testing.expectEqual(4, amt);
- try std.testing.expectEqualSlices(u8, "AAAA", written_buf[0..amt]);
+ try expectEqual(4, amt);
+ try expectEqualSlices(u8, "AAAA", written_buf[0..amt]);
}
test "copyFile" {
@@ -1690,7 +1633,7 @@ fn expectFileContents(io: Io, dir: Dir, file_path: []const u8, data: []const u8)
const contents = try dir.readFileAlloc(io, file_path, testing.allocator, .limited(1000));
defer testing.allocator.free(contents);
- try testing.expectEqualSlices(u8, data, contents);
+ try expectEqualSlices(u8, data, contents);
}
test "AtomicFile" {
@@ -1712,7 +1655,7 @@ test "AtomicFile" {
try af.finish();
}
const content = try ctx.dir.readFileAlloc(io, test_out_file, allocator, .limited(9999));
- try testing.expectEqualStrings(test_content, content);
+ try expectEqualStrings(test_content, content);
try ctx.dir.deleteFile(io, test_out_file);
}
@@ -1731,7 +1674,7 @@ test "open file with exclusive nonblocking lock twice" {
defer file1.close(io);
const file2 = ctx.dir.createFile(io, filename, .{ .lock = .exclusive, .lock_nonblocking = true });
- try testing.expectError(error.WouldBlock, file2);
+ try expectError(error.WouldBlock, file2);
}
}.impl);
}
@@ -1748,7 +1691,7 @@ test "open file with shared and exclusive nonblocking lock" {
defer file1.close(io);
const file2 = ctx.dir.createFile(io, filename, .{ .lock = .exclusive, .lock_nonblocking = true });
- try testing.expectError(error.WouldBlock, file2);
+ try expectError(error.WouldBlock, file2);
}
}.impl);
}
@@ -1765,7 +1708,7 @@ test "open file with exclusive and shared nonblocking lock" {
defer file1.close(io);
const file2 = ctx.dir.createFile(io, filename, .{ .lock = .shared, .lock_nonblocking = true });
- try testing.expectError(error.WouldBlock, file2);
+ try expectError(error.WouldBlock, file2);
}
}.impl);
}
@@ -1805,7 +1748,7 @@ test "open file with exclusive lock twice, make sure second lock waits" {
// Wait for the spawned thread to start trying to acquire the exclusive file lock.
// Then wait a bit to make sure that can't acquire it since we currently hold the file lock.
started.wait();
- try testing.expectError(error.Timeout, locked.timedWait(10 * std.time.ns_per_ms));
+ try expectError(error.Timeout, locked.timedWait(10 * std.time.ns_per_ms));
// Release the file lock which should unlock the thread to lock it and set the locked event.
file.close(io);
@@ -1846,7 +1789,7 @@ test "open file with exclusive nonblocking lock twice (absolute paths)" {
.lock_nonblocking = true,
});
file1.close(io);
- try testing.expectError(error.WouldBlock, file2);
+ try expectError(error.WouldBlock, file2);
}
test "read from locked file" {
@@ -1871,9 +1814,9 @@ test "read from locked file" {
defer f2.close(io);
var buffer: [1]u8 = undefined;
if (builtin.os.tag == .windows) {
- try std.testing.expectError(error.LockViolation, f2.read(&buffer));
+ try expectError(error.LockViolation, f2.read(&buffer));
} else {
- try std.testing.expectEqual(0, f2.read(&buffer));
+ try expectEqual(0, f2.read(&buffer));
}
}
}
@@ -1925,7 +1868,7 @@ test "walker" {
std.debug.print("found unexpected path: {f}\n", .{std.ascii.hexEscape(entry.path, .lower)});
return err;
};
- testing.expectEqual(expected_paths.get(entry.path).?, entry.depth()) catch |err| {
+ expectEqual(expected_paths.get(entry.path).?, entry.depth()) catch |err| {
std.debug.print("path reported unexpected depth: {f}\n", .{std.ascii.hexEscape(entry.path, .lower)});
return err;
};
@@ -1934,7 +1877,7 @@ test "walker" {
defer entry_dir.close(io);
num_walked += 1;
}
- try testing.expectEqual(expected_paths.kvs.len, num_walked);
+ try expectEqual(expected_paths.kvs.len, num_walked);
}
test "selective walker, skip entries that start with ." {
@@ -1992,7 +1935,7 @@ test "selective walker, skip entries that start with ." {
std.debug.print("found unexpected path: {f}\n", .{std.ascii.hexEscape(entry.path, .lower)});
return err;
};
- testing.expectEqual(expected_paths.get(entry.path).?, entry.depth()) catch |err| {
+ expectEqual(expected_paths.get(entry.path).?, entry.depth()) catch |err| {
std.debug.print("path reported unexpected depth: {f}\n", .{std.ascii.hexEscape(entry.path, .lower)});
return err;
};
@@ -2002,7 +1945,7 @@ test "selective walker, skip entries that start with ." {
defer entry_dir.close(io);
num_walked += 1;
}
- try testing.expectEqual(expected_paths.kvs.len, num_walked);
+ try expectEqual(expected_paths.kvs.len, num_walked);
}
test "walker without fully iterating" {
@@ -2025,7 +1968,7 @@ test "walker without fully iterating" {
num_walked += 1;
break;
}
- try testing.expectEqual(@as(usize, 1), num_walked);
+ try expectEqual(@as(usize, 1), num_walked);
}
test "'.' and '..' in Io.Dir functions" {
@@ -2061,7 +2004,7 @@ test "'.' and '..' in Io.Dir functions" {
try ctx.dir.writeFile(io, .{ .sub_path = update_path, .data = "something" });
var dir = ctx.dir;
const prev_status = try dir.updateFile(io, file_path, dir, update_path, .{});
- try testing.expectEqual(Io.Dir.PrevStatus.stale, prev_status);
+ try expectEqual(Io.Dir.PrevStatus.stale, prev_status);
try ctx.dir.deleteDir(io, subdir_path);
}
@@ -2106,8 +2049,7 @@ test "'.' and '..' in absolute functions" {
}
test "chmod" {
- if (native_os == .windows or native_os == .wasi)
- return error.SkipZigTest;
+ if (native_os == .windows or native_os == .wasi) return;
const io = testing.io;
@@ -2116,17 +2058,17 @@ test "chmod" {
const file = try tmp.dir.createFile(io, "test_file", .{ .permissions = .fromMode(0o600) });
defer file.close(io);
- try testing.expectEqual(@as(posix.mode_t, 0o600), (try file.stat(io)).permissions.toMode() & 0o7777);
+ try expectEqual(0o600, (try file.stat(io)).permissions.toMode() & 0o7777);
try file.setPermissions(io, .fromMode(0o644));
- try testing.expectEqual(@as(posix.mode_t, 0o644), (try file.stat(io)).permissions.toMode() & 0o7777);
+ try expectEqual(0o644, (try file.stat(io)).permissions.toMode() & 0o7777);
try tmp.dir.makeDir(io, "test_dir", .default_dir);
var dir = try tmp.dir.openDir(io, "test_dir", .{ .iterate = true });
defer dir.close(io);
try dir.setPermissions(io, .fromMode(0o700));
- try testing.expectEqual(@as(posix.mode_t, 0o700), (try dir.stat(io)).permissions.toMode() & 0o7777);
+ try expectEqual(0o700, (try dir.stat(io)).permissions.toMode() & 0o7777);
}
test "chown" {
@@ -2162,70 +2104,70 @@ test "invalid UTF-8/WTF-8 paths" {
// This is both invalid UTF-8 and WTF-8, since \xFF is an invalid start byte
const invalid_path = try ctx.transformPath("\xFF");
- try testing.expectError(expected_err, ctx.dir.openFile(invalid_path, .{}));
+ try expectError(expected_err, ctx.dir.openFile(invalid_path, .{}));
- try testing.expectError(expected_err, ctx.dir.createFile(invalid_path, .{}));
+ try expectError(expected_err, ctx.dir.createFile(invalid_path, .{}));
- try testing.expectError(expected_err, ctx.dir.makeDir(invalid_path, .default_dir));
+ try expectError(expected_err, ctx.dir.makeDir(invalid_path, .default_dir));
- try testing.expectError(expected_err, ctx.dir.makePath(invalid_path));
- try testing.expectError(expected_err, ctx.dir.makeOpenPath(invalid_path, .{}));
+ try expectError(expected_err, ctx.dir.makePath(invalid_path));
+ try expectError(expected_err, ctx.dir.makeOpenPath(invalid_path, .{}));
- try testing.expectError(expected_err, ctx.dir.openDir(invalid_path, .{}));
+ try expectError(expected_err, ctx.dir.openDir(invalid_path, .{}));
- try testing.expectError(expected_err, ctx.dir.deleteFile(invalid_path));
+ try expectError(expected_err, ctx.dir.deleteFile(invalid_path));
- try testing.expectError(expected_err, ctx.dir.deleteDir(io, invalid_path));
+ try expectError(expected_err, ctx.dir.deleteDir(io, invalid_path));
- try testing.expectError(expected_err, ctx.dir.rename(invalid_path, ctx.dir, invalid_path, io));
+ try expectError(expected_err, ctx.dir.rename(invalid_path, ctx.dir, invalid_path, io));
- try testing.expectError(expected_err, ctx.dir.symLink(io, invalid_path, invalid_path, .{}));
+ try expectError(expected_err, ctx.dir.symLink(io, invalid_path, invalid_path, .{}));
if (native_os == .wasi) {
- try testing.expectError(expected_err, ctx.dir.symLinkWasi(invalid_path, invalid_path, .{}));
+ try expectError(expected_err, ctx.dir.symLinkWasi(invalid_path, invalid_path, .{}));
}
- try testing.expectError(expected_err, ctx.dir.readLink(io, invalid_path, &[_]u8{}));
+ try expectError(expected_err, ctx.dir.readLink(io, invalid_path, &[_]u8{}));
if (native_os == .wasi) {
- try testing.expectError(expected_err, ctx.dir.readLinkWasi(invalid_path, &[_]u8{}));
+ try expectError(expected_err, ctx.dir.readLinkWasi(invalid_path, &[_]u8{}));
}
- try testing.expectError(expected_err, ctx.dir.readFile(invalid_path, &[_]u8{}));
- try testing.expectError(expected_err, ctx.dir.readFileAlloc(invalid_path, testing.allocator, .limited(0)));
+ try expectError(expected_err, ctx.dir.readFile(invalid_path, &[_]u8{}));
+ try expectError(expected_err, ctx.dir.readFileAlloc(invalid_path, testing.allocator, .limited(0)));
- try testing.expectError(expected_err, ctx.dir.deleteTree(io, invalid_path));
- try testing.expectError(expected_err, ctx.dir.deleteTreeMinStackSize(invalid_path));
+ try expectError(expected_err, ctx.dir.deleteTree(io, invalid_path));
+ try expectError(expected_err, ctx.dir.deleteTreeMinStackSize(invalid_path));
- try testing.expectError(expected_err, ctx.dir.writeFile(io, .{ .sub_path = invalid_path, .data = "" }));
+ try expectError(expected_err, ctx.dir.writeFile(io, .{ .sub_path = invalid_path, .data = "" }));
- try testing.expectError(expected_err, ctx.dir.access(invalid_path, .{}));
+ try expectError(expected_err, ctx.dir.access(invalid_path, .{}));
var dir = ctx.dir;
- try testing.expectError(expected_err, dir.updateFile(io, invalid_path, dir, invalid_path, .{}));
- try testing.expectError(expected_err, ctx.dir.copyFile(invalid_path, ctx.dir, invalid_path, .{}));
+ try expectError(expected_err, dir.updateFile(io, invalid_path, dir, invalid_path, .{}));
+ try expectError(expected_err, ctx.dir.copyFile(invalid_path, ctx.dir, invalid_path, .{}));
- try testing.expectError(expected_err, ctx.dir.statFile(invalid_path));
+ try expectError(expected_err, ctx.dir.statFile(invalid_path));
if (native_os != .wasi) {
- try testing.expectError(expected_err, ctx.dir.realpath(invalid_path, &[_]u8{}));
- try testing.expectError(expected_err, ctx.dir.realpathAlloc(testing.allocator, invalid_path));
+ try expectError(expected_err, ctx.dir.realpath(invalid_path, &[_]u8{}));
+ try expectError(expected_err, ctx.dir.realpathAlloc(testing.allocator, invalid_path));
}
- try testing.expectError(expected_err, Dir.rename(ctx.dir, invalid_path, ctx.dir, invalid_path, io));
+ try expectError(expected_err, Dir.rename(ctx.dir, invalid_path, ctx.dir, invalid_path, io));
if (native_os != .wasi and ctx.path_type != .relative) {
- try testing.expectError(expected_err, Dir.copyFileAbsolute(invalid_path, invalid_path, .{}));
- try testing.expectError(expected_err, Dir.makeDirAbsolute(invalid_path));
- try testing.expectError(expected_err, Dir.deleteDirAbsolute(invalid_path));
- try testing.expectError(expected_err, Dir.renameAbsolute(invalid_path, invalid_path));
- try testing.expectError(expected_err, Dir.openDirAbsolute(invalid_path, .{}));
- try testing.expectError(expected_err, Dir.openFileAbsolute(invalid_path, .{}));
- try testing.expectError(expected_err, Dir.accessAbsolute(invalid_path, .{}));
- try testing.expectError(expected_err, Dir.createFileAbsolute(invalid_path, .{}));
- try testing.expectError(expected_err, Dir.deleteFileAbsolute(invalid_path));
+ try expectError(expected_err, Dir.copyFileAbsolute(invalid_path, invalid_path, .{}));
+ try expectError(expected_err, Dir.makeDirAbsolute(invalid_path));
+ try expectError(expected_err, Dir.deleteDirAbsolute(invalid_path));
+ try expectError(expected_err, Dir.renameAbsolute(invalid_path, invalid_path));
+ try expectError(expected_err, Dir.openDirAbsolute(invalid_path, .{}));
+ try expectError(expected_err, Dir.openFileAbsolute(invalid_path, .{}));
+ try expectError(expected_err, Dir.accessAbsolute(invalid_path, .{}));
+ try expectError(expected_err, Dir.createFileAbsolute(invalid_path, .{}));
+ try expectError(expected_err, Dir.deleteFileAbsolute(invalid_path));
var readlink_buf: [Dir.max_path_bytes]u8 = undefined;
- try testing.expectError(expected_err, Dir.readLinkAbsolute(invalid_path, &readlink_buf));
- try testing.expectError(expected_err, Dir.symLinkAbsolute(invalid_path, invalid_path, .{}));
- try testing.expectError(expected_err, Dir.realpathAlloc(testing.allocator, invalid_path));
+ try expectError(expected_err, Dir.readLinkAbsolute(invalid_path, &readlink_buf));
+ try expectError(expected_err, Dir.symLinkAbsolute(invalid_path, invalid_path, .{}));
+ try expectError(expected_err, Dir.realpathAlloc(testing.allocator, invalid_path));
}
}
}.impl);
@@ -2259,8 +2201,8 @@ test "read file non vectored" {
else => |e| return e,
};
}
- try testing.expectEqualStrings(contents, w.buffered());
- try testing.expectEqual(contents.len, i);
+ try expectEqualStrings(contents, w.buffered());
+ try expectEqual(contents.len, i);
}
test "seek keeping partial buffer" {
@@ -2282,7 +2224,7 @@ test "seek keeping partial buffer" {
var read_buffer: [3]u8 = undefined;
var file_reader: Io.File.Reader = .init(file, io, &read_buffer);
- try testing.expectEqual(0, file_reader.logicalPos());
+ try expectEqual(0, file_reader.logicalPos());
var buf: [4]u8 = undefined;
try file_reader.interface.readSliceAll(&buf);
@@ -2292,18 +2234,18 @@ test "seek keeping partial buffer" {
return;
}
- try testing.expectEqual(4, file_reader.logicalPos());
- try testing.expectEqual(7, file_reader.pos);
+ try expectEqual(4, file_reader.logicalPos());
+ try expectEqual(7, file_reader.pos);
try file_reader.seekTo(6);
- try testing.expectEqual(6, file_reader.logicalPos());
- try testing.expectEqual(7, file_reader.pos);
+ try expectEqual(6, file_reader.logicalPos());
+ try expectEqual(7, file_reader.pos);
- try testing.expectEqualStrings("0123", &buf);
+ try expectEqualStrings("0123", &buf);
const n = try file_reader.interface.readSliceShort(&buf);
- try testing.expectEqual(4, n);
+ try expectEqual(4, n);
- try testing.expectEqualStrings("6789", &buf);
+ try expectEqualStrings("6789", &buf);
}
test "seekBy" {
@@ -2320,8 +2262,8 @@ test "seekBy" {
var buffer: [20]u8 = undefined;
const n = try reader.interface.readSliceShort(&buffer);
- try testing.expectEqual(15, n);
- try testing.expectEqualStrings("t's test seekBy", buffer[0..15]);
+ try expectEqual(15, n);
+ try expectEqualStrings("t's test seekBy", buffer[0..15]);
}
test "seekTo flushes buffered data" {
@@ -2348,7 +2290,7 @@ test "seekTo flushes buffered data" {
var buf: [4]u8 = undefined;
try file_reader.interface.readSliceAll(&buf);
- try std.testing.expectEqualStrings(contents, &buf);
+ try expectEqualStrings(contents, &buf);
}
test "File.Writer sendfile with buffered contents" {
@@ -2372,7 +2314,7 @@ test "File.Writer sendfile with buffered contents" {
var out_buf: [1]u8 = undefined;
var out_w = out.writerStreaming(&out_buf);
try out_w.interface.writeByte('a');
- try testing.expectEqual(3, try out_w.interface.sendFileAll(&in_r, .unlimited));
+ try expectEqual(3, try out_w.interface.sendFileAll(&in_r, .unlimited));
try out_w.interface.flush();
}
@@ -2380,8 +2322,8 @@ test "File.Writer sendfile with buffered contents" {
defer check.close(io);
var check_buf: [4]u8 = undefined;
var check_r = check.reader(io, &check_buf);
- try testing.expectEqualStrings("abcd", try check_r.interface.take(4));
- try testing.expectError(error.EndOfStream, check_r.interface.takeByte());
+ try expectEqualStrings("abcd", try check_r.interface.take(4));
+ try expectError(error.EndOfStream, check_r.interface.takeByte());
}
test "readlink on Windows" {
@@ -2410,23 +2352,72 @@ test "readlinkat" {
try tmp.dir.writeFile(io, .{ .sub_path = "file.txt", .data = "nonsense" });
// create a symbolic link
- if (native_os == .windows) {
- std.os.windows.CreateSymbolicLink(
- tmp.dir.handle,
- &[_]u16{ 'l', 'i', 'n', 'k' },
- &[_:0]u16{ 'f', 'i', 'l', 'e', '.', 't', 'x', 't' },
- false,
- ) catch |err| switch (err) {
+ tmp.dir.symLink("file.txt", "link", .{}) catch |err| switch (err) {
+ error.AccessDenied => {
// Symlink requires admin privileges on windows, so this test can legitimately fail.
- error.AccessDenied => return error.SkipZigTest,
- else => return err,
- };
- } else {
- try posix.symlinkat("file.txt", tmp.dir.handle, "link");
- }
+ if (native_os == .windows) return error.SkipZigTest;
+ },
+ };
// read the link
var buffer: [fs.max_path_bytes]u8 = undefined;
const read_link = try tmp.dir.readLink(io, "link", &buffer);
- try expect(mem.eql(u8, "file.txt", read_link));
+ try expectEqualStrings("file.txt", read_link);
+}
+
+test "fchmodat smoke test" {
+ if (!Io.File.Permissions.has_executable_bit) return error.SkipZigTest;
+
+ if (builtin.cpu.arch.isMIPS64() and (builtin.abi == .gnuabin32 or builtin.abi == .muslabin32)) {
+ // https://github.com/ziglang/zig/issues/23808
+ return error.SkipZigTest;
+ }
+
+ const io = testing.io;
+
+ var tmp = tmpDir(.{});
+ defer tmp.cleanup();
+
+ try expectError(error.FileNotFound, tmp.dir.setPermissions(io, "regfile", 0o666, .{}));
+ const file = try tmp.dir.createFile(io, "regfile", .{
+ .exclusive = true,
+ .permissions = .fromMode(0o644),
+ });
+ file.close(io);
+
+ if ((builtin.cpu.arch == .riscv32 or builtin.cpu.arch.isLoongArch()) and
+ builtin.os.tag == .linux and !builtin.link_libc)
+ {
+ return error.SkipZigTest; // No `fstatat()`.
+ }
+
+ try tmp.dir.symLink(io, "regfile", "symlink", .{});
+ const sym_mode = blk: {
+ const st = try tmp.dir.statFile(io, "symlink", .{ .follow_symlinks = false });
+ break :blk st.permissions.toMode() & 0b111_111_111;
+ };
+
+ try tmp.dir.setFilePermissions(io, "regfile", .fromMode(0o640), .{});
+ try expectMode(io, tmp.dir, "regfile", .fromMode(0o640));
+ try tmp.dir.setFilePermissions(io, "regfile", .fromMode(0o600), .{ .follow_symlinks = false });
+ try expectMode(io, tmp.dir, "regfile", .fromMode(0o600));
+
+ try tmp.dir.setFilePermissions(io, "symlink", .fromMode(0o640), .{});
+ try expectMode(io, tmp.dir, "regfile", .fromMode(0o640));
+ try expectMode(io, tmp.dir, "symlink", .fromMode(sym_mode));
+
+ var test_link = true;
+ tmp.dir.setFilePermissions(io, "symlink", .fromMode(0o600), .{ .follow_symlinks = false }) catch |err| switch (err) {
+ error.OperationNotSupported => test_link = false,
+ else => |e| return e,
+ };
+ if (test_link)
+ try expectMode(tmp.dir.handle, "symlink", 0o600);
+ try expectMode(tmp.dir.handle, "regfile", 0o640);
+}
+
+fn expectMode(io: Io, dir: Dir, file: []const u8, permissions: File.Permissions) !void {
+ const mode = permissions.toMode();
+ const st = try dir.statFile(io, file, .{ .follow_symlinks = false });
+ try expectEqual(mode, st.mode & 0b111_111_111);
}
diff --git a/lib/std/posix/test.zig b/lib/std/posix/test.zig
index 1764d7ad35..87361a5038 100644
--- a/lib/std/posix/test.zig
+++ b/lib/std/posix/test.zig
@@ -870,67 +870,6 @@ test "pwrite with empty buffer" {
try expectEqual(rc, 0);
}
-fn getFileMode(dir: posix.fd_t, path: []const u8) !posix.mode_t {
- const path_z = try posix.toPosixPath(path);
- const mode: posix.mode_t = if (native_os == .linux) blk: {
- const stx = try linux.wrapped.statx(
- dir,
- &path_z,
- posix.AT.SYMLINK_NOFOLLOW,
- .{ .MODE = true },
- );
- std.debug.assert(stx.mask.MODE);
- break :blk stx.mode;
- } else blk: {
- const st = try posix.fstatatZ(dir, &path_z, posix.AT.SYMLINK_NOFOLLOW);
- break :blk st.mode;
- };
-
- return mode & 0b111_111_111;
-}
-
-fn expectMode(dir: posix.fd_t, file: []const u8, mode: posix.mode_t) !void {
- const actual = try getFileMode(dir, file);
- try expectEqual(mode, actual & 0b111_111_111);
-}
-
-test "fchmodat smoke test" {
- if (!Io.File.Permissions.has_executable_bit) return error.SkipZigTest;
-
- var tmp = tmpDir(.{});
- defer tmp.cleanup();
-
- try expectError(error.FileNotFound, posix.fchmodat(tmp.dir.handle, "regfile", 0o666, 0));
- const fd = try posix.openat(
- tmp.dir.handle,
- "regfile",
- .{ .ACCMODE = .WRONLY, .CREAT = true, .EXCL = true, .TRUNC = true },
- 0o644,
- );
- posix.close(fd);
-
- try posix.symlinkat("regfile", tmp.dir.handle, "symlink");
- const sym_mode = try getFileMode(tmp.dir.handle, "symlink");
-
- try posix.fchmodat(tmp.dir.handle, "regfile", 0o640, 0);
- try expectMode(tmp.dir.handle, "regfile", 0o640);
- try posix.fchmodat(tmp.dir.handle, "regfile", 0o600, posix.AT.SYMLINK_NOFOLLOW);
- try expectMode(tmp.dir.handle, "regfile", 0o600);
-
- try posix.fchmodat(tmp.dir.handle, "symlink", 0o640, 0);
- try expectMode(tmp.dir.handle, "regfile", 0o640);
- try expectMode(tmp.dir.handle, "symlink", sym_mode);
-
- var test_link = true;
- posix.fchmodat(tmp.dir.handle, "symlink", 0o600, posix.AT.SYMLINK_NOFOLLOW) catch |err| switch (err) {
- error.OperationNotSupported => test_link = false,
- else => |e| return e,
- };
- if (test_link)
- try expectMode(tmp.dir.handle, "symlink", 0o600);
- try expectMode(tmp.dir.handle, "regfile", 0o640);
-}
-
const CommonOpenFlags = packed struct {
ACCMODE: posix.ACCMODE = .RDONLY,
CREAT: bool = false,