authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2020-03-18 14:45:01-04:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2020-03-18 16:10:57-04:00
log27affde592653ac7f92489cec404b4bf3e0d1b29
treed563a351e3cf7656471f50cd5112b790d2c6233e
parentc45fe2759fdb882efb4caf89a35136b8b205ee7c
signaturelock-open Commit is signed but in an unrecognized format.

(breaking) clarify openDir API

* remove deprecated `std.fs.Dir` APIs * `std.fs.Dir.openDir` now takes a options struct with bool fields for `access_sub_paths` and `iterate`. It's now much more clear how opening directories works. * fixed the std lib and various zig code calling the wrong openDir function. * the runtime safety check for dir flags is removed in favor of the cheaper option of putting a comment on the same line as handling EBADF / ACCESS_DENIED, since that will show up in stack traces.

9 files changed, 61 insertions(+), 135 deletions(-)

lib/std/build.zig+2-2
...@@ -2156,10 +2156,10 @@ pub const LibExeObjStep = struct {...@@ -2156,10 +2156,10 @@ pub const LibExeObjStep = struct {
2156 const build_output_dir = mem.trimRight(u8, output_dir_nl, "\r\n");2156 const build_output_dir = mem.trimRight(u8, output_dir_nl, "\r\n");
21572157
2158 if (self.output_dir) |output_dir| {2158 if (self.output_dir) |output_dir| {
2159 var src_dir = try std.fs.cwd().openDirList(build_output_dir);2159 var src_dir = try std.fs.cwd().openDir(build_output_dir, .{ .iterate = true });
2160 defer src_dir.close();2160 defer src_dir.close();
21612161
2162 var dest_dir = try std.fs.cwd().openDirTraverse(output_dir);2162 var dest_dir = try std.fs.cwd().openDir(output_dir, .{});
2163 defer dest_dir.close();2163 defer dest_dir.close();
21642164
2165 var it = src_dir.iterate();2165 var it = src_dir.iterate();
lib/std/build/write_file.zig+1-1
...@@ -78,7 +78,7 @@ pub const WriteFileStep = struct {...@@ -78,7 +78,7 @@ pub const WriteFileStep = struct {
78 warn("unable to make path {}: {}\n", .{ self.output_dir, @errorName(err) });78 warn("unable to make path {}: {}\n", .{ self.output_dir, @errorName(err) });
79 return err;79 return err;
80 };80 };
81 var dir = try fs.cwd().openDirTraverse(self.output_dir);81 var dir = try fs.cwd().openDir(self.output_dir, .{});
82 defer dir.close();82 defer dir.close();
83 for (self.files.toSliceConst()) |file| {83 for (self.files.toSliceConst()) |file| {
84 dir.writeFile(file.basename, file.bytes) catch |err| {84 dir.writeFile(file.basename, file.bytes) catch |err| {
lib/std/fs.zig+43-118
...@@ -274,7 +274,7 @@ pub fn deleteTree(full_path: []const u8) !void {...@@ -274,7 +274,7 @@ pub fn deleteTree(full_path: []const u8) !void {
274 CannotDeleteRootDirectory,274 CannotDeleteRootDirectory,
275 }.CannotDeleteRootDirectory;275 }.CannotDeleteRootDirectory;
276276
277 var dir = try cwd().openDirList(dirname);277 var dir = try cwd().openDir(dirname, .{});
278 defer dir.close();278 defer dir.close();
279279
280 return dir.deleteTree(path.basename(full_path));280 return dir.deleteTree(path.basename(full_path));
...@@ -339,7 +339,7 @@ pub const Dir = struct {...@@ -339,7 +339,7 @@ pub const Dir = struct {
339 if (rc == 0) return null;339 if (rc == 0) return null;
340 if (rc < 0) {340 if (rc < 0) {
341 switch (os.errno(rc)) {341 switch (os.errno(rc)) {
342 os.EBADF => unreachable,342 os.EBADF => unreachable, // Dir is invalid or was opened without iteration ability
343 os.EFAULT => unreachable,343 os.EFAULT => unreachable,
344 os.ENOTDIR => unreachable,344 os.ENOTDIR => unreachable,
345 os.EINVAL => unreachable,345 os.EINVAL => unreachable,
...@@ -388,7 +388,7 @@ pub const Dir = struct {...@@ -388,7 +388,7 @@ pub const Dir = struct {
388 );388 );
389 switch (os.errno(rc)) {389 switch (os.errno(rc)) {
390 0 => {},390 0 => {},
391 os.EBADF => unreachable,391 os.EBADF => unreachable, // Dir is invalid or was opened without iteration ability
392 os.EFAULT => unreachable,392 os.EFAULT => unreachable,
393 os.ENOTDIR => unreachable,393 os.ENOTDIR => unreachable,
394 os.EINVAL => unreachable,394 os.EINVAL => unreachable,
...@@ -444,7 +444,7 @@ pub const Dir = struct {...@@ -444,7 +444,7 @@ pub const Dir = struct {
444 const rc = os.linux.getdents64(self.dir.fd, &self.buf, self.buf.len);444 const rc = os.linux.getdents64(self.dir.fd, &self.buf, self.buf.len);
445 switch (os.linux.getErrno(rc)) {445 switch (os.linux.getErrno(rc)) {
446 0 => {},446 0 => {},
447 os.EBADF => unreachable,447 os.EBADF => unreachable, // Dir is invalid or was opened without iteration ability
448 os.EFAULT => unreachable,448 os.EFAULT => unreachable,
449 os.ENOTDIR => unreachable,449 os.ENOTDIR => unreachable,
450 os.EINVAL => unreachable,450 os.EINVAL => unreachable,
...@@ -555,36 +555,6 @@ pub const Dir = struct {...@@ -555,36 +555,6 @@ pub const Dir = struct {
555 };555 };
556556
557 pub fn iterate(self: Dir) Iterator {557 pub fn iterate(self: Dir) Iterator {
558 // Make sure the directory was not open with openDirTraverse
559 if (std.debug.runtime_safety) {
560 var ok = true;
561
562 if (builtin.os.tag == .windows) {
563 const w = os.windows;
564
565 var io_status_block: w.IO_STATUS_BLOCK = undefined;
566 var info: w.FILE_ACCESS_INFORMATION = undefined;
567
568 const rc = w.ntdll.NtQueryInformationFile(
569 self.fd,
570 &io_status_block,
571 &info,
572 @sizeOf(w.FILE_ACCESS_INFORMATION),
573 .FileAccessInformation,
574 );
575 assert(rc == .SUCCESS);
576
577 ok = (info.AccessFlags & w.FILE_LIST_DIRECTORY) != 0;
578 } else if (@hasDecl(os, "O_PATH")) {
579 const f = os.fcntl(self.fd, os.F_GETFL, 0) catch unreachable;
580 ok = (f & os.O_PATH) == 0;
581 }
582
583 if (!ok) {
584 std.debug.panic("iterate() called on Dir open with openDirTraverse", .{});
585 }
586 }
587
588 switch (builtin.os.tag) {558 switch (builtin.os.tag) {
589 .macosx, .ios, .freebsd, .netbsd, .dragonfly => return Iterator{559 .macosx, .ios, .freebsd, .netbsd, .dragonfly => return Iterator{
590 .dir = self,560 .dir = self,
...@@ -626,16 +596,6 @@ pub const Dir = struct {...@@ -626,16 +596,6 @@ pub const Dir = struct {
626 DeviceBusy,596 DeviceBusy,
627 } || os.UnexpectedError;597 } || os.UnexpectedError;
628598
629 /// Deprecated; call `cwd().openDirList` directly.
630 pub fn open(dir_path: []const u8) OpenError!Dir {
631 return cwd().openDirList(dir_path);
632 }
633
634 /// Deprecated; call `cwd().openDirListC` directly.
635 pub fn openC(dir_path_c: [*:0]const u8) OpenError!Dir {
636 return cwd().openDirListC(dir_path_c);
637 }
638
639 pub fn close(self: *Dir) void {599 pub fn close(self: *Dir) void {
640 if (need_async_thread) {600 if (need_async_thread) {
641 std.event.Loop.instance.?.close(self.fd);601 std.event.Loop.instance.?.close(self.fd);
...@@ -822,79 +782,61 @@ pub const Dir = struct {...@@ -822,79 +782,61 @@ pub const Dir = struct {
822 try os.fchdir(self.fd);782 try os.fchdir(self.fd);
823 }783 }
824784
825 /// Deprecated; call `openDirList` directly.785 pub const OpenDirOptions = struct {
826 pub fn openDir(self: Dir, sub_path: []const u8) OpenError!Dir {786 /// `true` means the opened directory can be used as the `Dir` parameter
827 return self.openDirList(sub_path);787 /// for functions which operate based on an open directory handle. When `false`,
828 }788 /// such operations are Illegal Behavior.
789 access_sub_paths: bool = true,
829790
830 /// Deprecated; call `openDirListC` directly.791 /// `true` means the opened directory can be scanned for the files and sub-directories
831 pub fn openDirC(self: Dir, sub_path_c: [*:0]const u8) OpenError!Dir {792 /// of the result. It means the `iterate` function can be called.
832 return self.openDirListC(sub_path_c);793 iterate: bool = false,
833 }794 };
834795
835 /// Opens a directory at the given path with the ability to access subpaths796 /// Opens a directory at the given path. The directory is a system resource that remains
836 /// of the result. Calling `iterate` on the result is illegal behavior; to797 /// open until `close` is called on the result.
837 /// list the contents of a directory, open it with `openDirList`.
838 ///
839 /// Call `close` on the result when done.
840 ///798 ///
841 /// Asserts that the path parameter has no null bytes.799 /// Asserts that the path parameter has no null bytes.
842 /// TODO collapse this and `openDirList` into one function with an options parameter800 pub fn openDir(self: Dir, sub_path: []const u8, args: OpenDirOptions) OpenError!Dir {
843 pub fn openDirTraverse(self: Dir, sub_path: []const u8) OpenError!Dir {
844 if (builtin.os.tag == .windows) {801 if (builtin.os.tag == .windows) {
845 const sub_path_w = try os.windows.sliceToPrefixedFileW(sub_path);802 const sub_path_w = try os.windows.sliceToPrefixedFileW(sub_path);
846 return self.openDirTraverseW(&sub_path_w);803 return self.openDirW(&sub_path_w, args);
847 }804 } else {
848805 const sub_path_c = try os.toPosixPath(sub_path);
849 const sub_path_c = try os.toPosixPath(sub_path);806 return self.openDirC(&sub_path_c, args);
850 return self.openDirTraverseC(&sub_path_c);
851 }
852
853 /// Opens a directory at the given path with the ability to access subpaths and list contents
854 /// of the result. If the ability to list contents is unneeded, `openDirTraverse` acts the
855 /// same and may be more efficient.
856 ///
857 /// Call `close` on the result when done.
858 ///
859 /// Asserts that the path parameter has no null bytes.
860 /// TODO collapse this and `openDirTraverse` into one function with an options parameter
861 pub fn openDirList(self: Dir, sub_path: []const u8) OpenError!Dir {
862 if (builtin.os.tag == .windows) {
863 const sub_path_w = try os.windows.sliceToPrefixedFileW(sub_path);
864 return self.openDirListW(&sub_path_w);
865 }807 }
866
867 const sub_path_c = try os.toPosixPath(sub_path);
868 return self.openDirListC(&sub_path_c);
869 }808 }
870809
871 /// Same as `openDirTraverse` except the parameter is null-terminated.810 /// Same as `openDir` except the parameter is null-terminated.
872 pub fn openDirTraverseC(self: Dir, sub_path_c: [*:0]const u8) OpenError!Dir {811 pub fn openDirC(self: Dir, sub_path_c: [*:0]const u8, args: OpenDirOptions) OpenError!Dir {
873 if (builtin.os.tag == .windows) {812 if (builtin.os.tag == .windows) {
874 const sub_path_w = try os.windows.cStrToPrefixedFileW(sub_path_c);813 const sub_path_w = try os.windows.cStrToPrefixedFileW(sub_path_c);
875 return self.openDirTraverseW(&sub_path_w);814 return self.openDirW(&sub_path_w, args);
876 } else {815 } else if (!args.iterate) {
877 const O_PATH = if (@hasDecl(os, "O_PATH")) os.O_PATH else 0;816 const O_PATH = if (@hasDecl(os, "O_PATH")) os.O_PATH else 0;
878 return self.openDirFlagsC(sub_path_c, os.O_RDONLY | os.O_CLOEXEC | O_PATH);817 return self.openDirFlagsC(sub_path_c, os.O_DIRECTORY | os.O_RDONLY | os.O_CLOEXEC | O_PATH);
818 } else {
819 return self.openDirFlagsC(sub_path_c, os.O_DIRECTORY | os.O_RDONLY | os.O_CLOEXEC);
879 }820 }
880 }821 }
881822
882 /// Same as `openDirList` except the parameter is null-terminated.823 /// Same as `openDir` except the path parameter is WTF-16 encoded, NT-prefixed.
883 pub fn openDirListC(self: Dir, sub_path_c: [*:0]const u8) OpenError!Dir {824 /// This function asserts the target OS is Windows.
884 if (builtin.os.tag == .windows) {825 pub fn openDirW(self: Dir, sub_path_w: [*:0]const u16, args: OpenDirOptions) OpenError!Dir {
885 const sub_path_w = try os.windows.cStrToPrefixedFileW(sub_path_c);826 const w = os.windows;
886 return self.openDirListW(&sub_path_w);827 // TODO remove some of these flags if args.access_sub_paths is false
887 } else {828 const base_flags = w.STANDARD_RIGHTS_READ | w.FILE_READ_ATTRIBUTES | w.FILE_READ_EA |
888 return self.openDirFlagsC(sub_path_c, os.O_RDONLY | os.O_CLOEXEC);829 w.SYNCHRONIZE | w.FILE_TRAVERSE;
889 }830 const flags: u32 = if (args.iterate) base_flags else base_flags | w.FILE_LIST_DIRECTORY;
831 return self.openDirAccessMaskW(sub_path_w, flags);
890 }832 }
891833
834 /// `flags` must contain `os.O_DIRECTORY`.
892 fn openDirFlagsC(self: Dir, sub_path_c: [*:0]const u8, flags: u32) OpenError!Dir {835 fn openDirFlagsC(self: Dir, sub_path_c: [*:0]const u8, flags: u32) OpenError!Dir {
893 const os_flags = flags | os.O_DIRECTORY;
894 const result = if (need_async_thread)836 const result = if (need_async_thread)
895 std.event.Loop.instance.?.openatZ(self.fd, sub_path_c, os_flags, 0)837 std.event.Loop.instance.?.openatZ(self.fd, sub_path_c, flags, 0)
896 else838 else
897 os.openatC(self.fd, sub_path_c, os_flags, 0);839 os.openatC(self.fd, sub_path_c, flags, 0);
898 const fd = result catch |err| switch (err) {840 const fd = result catch |err| switch (err) {
899 error.FileTooBig => unreachable, // can't happen for directories841 error.FileTooBig => unreachable, // can't happen for directories
900 error.IsDir => unreachable, // we're providing O_DIRECTORY842 error.IsDir => unreachable, // we're providing O_DIRECTORY
...@@ -905,22 +847,6 @@ pub const Dir = struct {...@@ -905,22 +847,6 @@ pub const Dir = struct {
905 return Dir{ .fd = fd };847 return Dir{ .fd = fd };
906 }848 }
907849
908 /// Same as `openDirTraverse` except the path parameter is UTF16LE, NT-prefixed.
909 /// This function is Windows-only.
910 pub fn openDirTraverseW(self: Dir, sub_path_w: [*:0]const u16) OpenError!Dir {
911 const w = os.windows;
912
913 return self.openDirAccessMaskW(sub_path_w, w.STANDARD_RIGHTS_READ | w.FILE_READ_ATTRIBUTES | w.FILE_READ_EA | w.SYNCHRONIZE | w.FILE_TRAVERSE);
914 }
915
916 /// Same as `openDirList` except the path parameter is UTF16LE, NT-prefixed.
917 /// This function is Windows-only.
918 pub fn openDirListW(self: Dir, sub_path_w: [*:0]const u16) OpenError!Dir {
919 const w = os.windows;
920
921 return self.openDirAccessMaskW(sub_path_w, w.STANDARD_RIGHTS_READ | w.FILE_READ_ATTRIBUTES | w.FILE_READ_EA | w.SYNCHRONIZE | w.FILE_TRAVERSE | w.FILE_LIST_DIRECTORY);
922 }
923
924 fn openDirAccessMaskW(self: Dir, sub_path_w: [*:0]const u16, access_mask: u32) OpenError!Dir {850 fn openDirAccessMaskW(self: Dir, sub_path_w: [*:0]const u16, access_mask: u32) OpenError!Dir {
925 const w = os.windows;851 const w = os.windows;
926852
...@@ -1141,7 +1067,7 @@ pub const Dir = struct {...@@ -1141,7 +1067,7 @@ pub const Dir = struct {
1141 error.Unexpected,1067 error.Unexpected,
1142 => |e| return e,1068 => |e| return e,
1143 }1069 }
1144 var dir = self.openDirList(sub_path) catch |err| switch (err) {1070 var dir = self.openDir(sub_path, .{ .iterate = true }) catch |err| switch (err) {
1145 error.NotDir => {1071 error.NotDir => {
1146 if (got_access_denied) {1072 if (got_access_denied) {
1147 return error.AccessDenied;1073 return error.AccessDenied;
...@@ -1174,7 +1100,6 @@ pub const Dir = struct {...@@ -1174,7 +1100,6 @@ pub const Dir = struct {
11741100
1175 var dir_name_buf: [MAX_PATH_BYTES]u8 = undefined;1101 var dir_name_buf: [MAX_PATH_BYTES]u8 = undefined;
1176 var dir_name: []const u8 = sub_path;1102 var dir_name: []const u8 = sub_path;
1177 var parent_dir = self;
11781103
1179 // Here we must avoid recursion, in order to provide O(1) memory guarantee of this function.1104 // Here we must avoid recursion, in order to provide O(1) memory guarantee of this function.
1180 // Go through each entry and if it is not a directory, delete it. If it is a directory,1105 // Go through each entry and if it is not a directory, delete it. If it is a directory,
...@@ -1206,7 +1131,7 @@ pub const Dir = struct {...@@ -1206,7 +1131,7 @@ pub const Dir = struct {
1206 => |e| return e,1131 => |e| return e,
1207 }1132 }
12081133
1209 const new_dir = dir.openDirList(entry.name) catch |err| switch (err) {1134 const new_dir = dir.openDir(entry.name, .{ .iterate = true }) catch |err| switch (err) {
1210 error.NotDir => {1135 error.NotDir => {
1211 if (got_access_denied) {1136 if (got_access_denied) {
1212 return error.AccessDenied;1137 return error.AccessDenied;
...@@ -1491,7 +1416,7 @@ pub const Walker = struct {...@@ -1491,7 +1416,7 @@ pub const Walker = struct {
1491 try self.name_buffer.appendByte(path.sep);1416 try self.name_buffer.appendByte(path.sep);
1492 try self.name_buffer.append(base.name);1417 try self.name_buffer.append(base.name);
1493 if (base.kind == .Directory) {1418 if (base.kind == .Directory) {
1494 var new_dir = top.dir_it.dir.openDirList(base.name) catch |err| switch (err) {1419 var new_dir = top.dir_it.dir.openDir(base.name, .{ .iterate = true }) catch |err| switch (err) {
1495 error.NameTooLong => unreachable, // no path sep in base.name1420 error.NameTooLong => unreachable, // no path sep in base.name
1496 else => |e| return e,1421 else => |e| return e,
1497 };1422 };
...@@ -1529,7 +1454,7 @@ pub const Walker = struct {...@@ -1529,7 +1454,7 @@ pub const Walker = struct {
1529pub fn walkPath(allocator: *Allocator, dir_path: []const u8) !Walker {1454pub fn walkPath(allocator: *Allocator, dir_path: []const u8) !Walker {
1530 assert(!mem.endsWith(u8, dir_path, path.sep_str));1455 assert(!mem.endsWith(u8, dir_path, path.sep_str));
15311456
1532 var dir = try cwd().openDirList(dir_path);1457 var dir = try cwd().openDir(dir_path, .{ .iterate = true });
1533 errdefer dir.close();1458 errdefer dir.close();
15341459
1535 var name_buffer = try std.Buffer.init(allocator, dir_path);1460 var name_buffer = try std.Buffer.init(allocator, dir_path);
lib/std/os/test.zig+6-5
...@@ -21,7 +21,7 @@ test "makePath, put some files in it, deleteTree" {...@@ -21,7 +21,7 @@ test "makePath, put some files in it, deleteTree" {
21 try io.writeFile("os_test_tmp" ++ fs.path.sep_str ++ "b" ++ fs.path.sep_str ++ "c" ++ fs.path.sep_str ++ "file.txt", "nonsense");21 try io.writeFile("os_test_tmp" ++ fs.path.sep_str ++ "b" ++ fs.path.sep_str ++ "c" ++ fs.path.sep_str ++ "file.txt", "nonsense");
22 try io.writeFile("os_test_tmp" ++ fs.path.sep_str ++ "b" ++ fs.path.sep_str ++ "file2.txt", "blah");22 try io.writeFile("os_test_tmp" ++ fs.path.sep_str ++ "b" ++ fs.path.sep_str ++ "file2.txt", "blah");
23 try fs.deleteTree("os_test_tmp");23 try fs.deleteTree("os_test_tmp");
24 if (fs.cwd().openDirTraverse("os_test_tmp")) |dir| {24 if (fs.cwd().openDir("os_test_tmp", .{})) |dir| {
25 @panic("expected error");25 @panic("expected error");
26 } else |err| {26 } else |err| {
27 expect(err == error.FileNotFound);27 expect(err == error.FileNotFound);
...@@ -49,7 +49,7 @@ test "sendfile" {...@@ -49,7 +49,7 @@ test "sendfile" {
49 try fs.cwd().makePath("os_test_tmp");49 try fs.cwd().makePath("os_test_tmp");
50 defer fs.deleteTree("os_test_tmp") catch {};50 defer fs.deleteTree("os_test_tmp") catch {};
5151
52 var dir = try fs.cwd().openDirList("os_test_tmp");52 var dir = try fs.cwd().openDir("os_test_tmp", .{});
53 defer dir.close();53 defer dir.close();
5454
55 const line1 = "line1\n";55 const line1 = "line1\n";
...@@ -455,7 +455,10 @@ test "fcntl" {...@@ -455,7 +455,10 @@ test "fcntl" {
455 const test_out_file = "os_tmp_test";455 const test_out_file = "os_tmp_test";
456456
457 const file = try fs.cwd().createFile(test_out_file, .{});457 const file = try fs.cwd().createFile(test_out_file, .{});
458 defer file.close();458 defer {
459 file.close();
460 fs.cwd().deleteFile(test_out_file) catch {};
461 }
459462
460 // Note: The test assumes createFile opens the file with O_CLOEXEC463 // Note: The test assumes createFile opens the file with O_CLOEXEC
461 {464 {
...@@ -472,6 +475,4 @@ test "fcntl" {...@@ -472,6 +475,4 @@ test "fcntl" {
472 const flags = try os.fcntl(file.handle, os.F_GETFD, 0);475 const flags = try os.fcntl(file.handle, os.F_GETFD, 0);
473 expect((flags & os.FD_CLOEXEC) != 0);476 expect((flags & os.FD_CLOEXEC) != 0);
474 }477 }
475
476 try fs.cwd().deleteFile(test_out_file);
477}478}
lib/std/zig/system.zig+1-1
...@@ -754,7 +754,7 @@ pub const NativeTargetInfo = struct {...@@ -754,7 +754,7 @@ pub const NativeTargetInfo = struct {
754 const rpath_list = mem.toSliceConst(u8, @ptrCast([*:0]u8, strtab[rpoff..].ptr));754 const rpath_list = mem.toSliceConst(u8, @ptrCast([*:0]u8, strtab[rpoff..].ptr));
755 var it = mem.tokenize(rpath_list, ":");755 var it = mem.tokenize(rpath_list, ":");
756 while (it.next()) |rpath| {756 while (it.next()) |rpath| {
757 var dir = fs.cwd().openDirList(rpath) catch |err| switch (err) {757 var dir = fs.cwd().openDir(rpath, .{}) catch |err| switch (err) {
758 error.NameTooLong => unreachable,758 error.NameTooLong => unreachable,
759 error.InvalidUtf8 => unreachable,759 error.InvalidUtf8 => unreachable,
760 error.BadPathName => unreachable,760 error.BadPathName => unreachable,
src-self-hosted/libc_installation.zig+5-5
...@@ -280,7 +280,7 @@ pub const LibCInstallation = struct {...@@ -280,7 +280,7 @@ pub const LibCInstallation = struct {
280 // search in reverse order280 // search in reverse order
281 const search_path_untrimmed = search_paths.at(search_paths.len - path_i - 1);281 const search_path_untrimmed = search_paths.at(search_paths.len - path_i - 1);
282 const search_path = std.mem.trimLeft(u8, search_path_untrimmed, " ");282 const search_path = std.mem.trimLeft(u8, search_path_untrimmed, " ");
283 var search_dir = fs.cwd().openDirList(search_path) catch |err| switch (err) {283 var search_dir = fs.cwd().openDir(search_path, .{}) catch |err| switch (err) {
284 error.FileNotFound,284 error.FileNotFound,
285 error.NotDir,285 error.NotDir,
286 error.NoDevice,286 error.NoDevice,
...@@ -335,7 +335,7 @@ pub const LibCInstallation = struct {...@@ -335,7 +335,7 @@ pub const LibCInstallation = struct {
335 const stream = result_buf.outStream();335 const stream = result_buf.outStream();
336 try stream.print("{}\\Include\\{}\\ucrt", .{ search.path, search.version });336 try stream.print("{}\\Include\\{}\\ucrt", .{ search.path, search.version });
337337
338 var dir = fs.cwd().openDirList(result_buf.toSliceConst()) catch |err| switch (err) {338 var dir = fs.cwd().openDir(result_buf.toSliceConst(), .{}) catch |err| switch (err) {
339 error.FileNotFound,339 error.FileNotFound,
340 error.NotDir,340 error.NotDir,
341 error.NoDevice,341 error.NoDevice,
...@@ -382,7 +382,7 @@ pub const LibCInstallation = struct {...@@ -382,7 +382,7 @@ pub const LibCInstallation = struct {
382 const stream = result_buf.outStream();382 const stream = result_buf.outStream();
383 try stream.print("{}\\Lib\\{}\\ucrt\\{}", .{ search.path, search.version, arch_sub_dir });383 try stream.print("{}\\Lib\\{}\\ucrt\\{}", .{ search.path, search.version, arch_sub_dir });
384384
385 var dir = fs.cwd().openDirList(result_buf.toSliceConst()) catch |err| switch (err) {385 var dir = fs.cwd().openDir(result_buf.toSliceConst(), .{}) catch |err| switch (err) {
386 error.FileNotFound,386 error.FileNotFound,
387 error.NotDir,387 error.NotDir,
388 error.NoDevice,388 error.NoDevice,
...@@ -437,7 +437,7 @@ pub const LibCInstallation = struct {...@@ -437,7 +437,7 @@ pub const LibCInstallation = struct {
437 const stream = result_buf.outStream();437 const stream = result_buf.outStream();
438 try stream.print("{}\\Lib\\{}\\um\\{}", .{ search.path, search.version, arch_sub_dir });438 try stream.print("{}\\Lib\\{}\\um\\{}", .{ search.path, search.version, arch_sub_dir });
439439
440 var dir = fs.cwd().openDirList(result_buf.toSliceConst()) catch |err| switch (err) {440 var dir = fs.cwd().openDir(result_buf.toSliceConst(), .{}) catch |err| switch (err) {
441 error.FileNotFound,441 error.FileNotFound,
442 error.NotDir,442 error.NotDir,
443 error.NoDevice,443 error.NoDevice,
...@@ -475,7 +475,7 @@ pub const LibCInstallation = struct {...@@ -475,7 +475,7 @@ pub const LibCInstallation = struct {
475475
476 try result_buf.append("\\include");476 try result_buf.append("\\include");
477477
478 var dir = fs.cwd().openDirList(result_buf.toSliceConst()) catch |err| switch (err) {478 var dir = fs.cwd().openDir(result_buf.toSliceConst(), .{}) catch |err| switch (err) {
479 error.FileNotFound,479 error.FileNotFound,
480 error.NotDir,480 error.NotDir,
481 error.NoDevice,481 error.NoDevice,
src-self-hosted/main.zig+1-1
...@@ -734,7 +734,7 @@ async fn fmtPath(fmt: *Fmt, file_path_ref: []const u8, check_mode: bool) FmtErro...@@ -734,7 +734,7 @@ async fn fmtPath(fmt: *Fmt, file_path_ref: []const u8, check_mode: bool) FmtErro
734 max_src_size,734 max_src_size,
735 ) catch |err| switch (err) {735 ) catch |err| switch (err) {
736 error.IsDir, error.AccessDenied => {736 error.IsDir, error.AccessDenied => {
737 var dir = try fs.cwd().openDirList(file_path);737 var dir = try fs.cwd().openDir(file_path, .{ .iterate = true });
738 defer dir.close();738 defer dir.close();
739739
740 var group = event.Group(FmtError!void).init(fmt.allocator);740 var group = event.Group(FmtError!void).init(fmt.allocator);
src-self-hosted/print_targets.zig+1-1
...@@ -72,7 +72,7 @@ pub fn cmdTargets(...@@ -72,7 +72,7 @@ pub fn cmdTargets(
72 };72 };
73 defer allocator.free(zig_lib_dir);73 defer allocator.free(zig_lib_dir);
7474
75 var dir = try std.fs.cwd().openDirList(zig_lib_dir);75 var dir = try std.fs.cwd().openDir(zig_lib_dir, .{});
76 defer dir.close();76 defer dir.close();
7777
78 const vers_txt = try dir.readFileAlloc(allocator, "libc/glibc/vers.txt", 10 * 1024);78 const vers_txt = try dir.readFileAlloc(allocator, "libc/glibc/vers.txt", 10 * 1024);
src-self-hosted/stage2.zig+1-1
...@@ -319,7 +319,7 @@ fn fmtPath(fmt: *Fmt, file_path: []const u8, check_mode: bool) FmtError!void {...@@ -319,7 +319,7 @@ fn fmtPath(fmt: *Fmt, file_path: []const u8, check_mode: bool) FmtError!void {
319 const source_code = io.readFileAlloc(fmt.allocator, file_path) catch |err| switch (err) {319 const source_code = io.readFileAlloc(fmt.allocator, file_path) catch |err| switch (err) {
320 error.IsDir, error.AccessDenied => {320 error.IsDir, error.AccessDenied => {
321 // TODO make event based (and dir.next())321 // TODO make event based (and dir.next())
322 var dir = try fs.cwd().openDirList(file_path);322 var dir = try fs.cwd().openDir(file_path, .{ .iterate = true });
323 defer dir.close();323 defer dir.close();
324324
325 var dir_it = dir.iterate();325 var dir_it = dir.iterate();