| ... | ... | @@ -167,45 +167,6 @@ test "openat smoke test" { |
| 167 | 167 | } |
| 168 | 168 | } |
| 169 | 169 | |
| 170 | | test "symlink with relative paths" { |
| 171 | | if (native_os == .wasi) return error.SkipZigTest; // Can symlink, but can't change into tmpDir |
| 172 | | |
| 173 | | var tmp = tmpDir(.{}); |
| 174 | | defer tmp.cleanup(); |
| 175 | | |
| 176 | | const target_name = "symlink-target"; |
| 177 | | const symlink_name = "symlinker"; |
| 178 | | |
| 179 | | // Restore default CWD at end of test. |
| 180 | | const orig_cwd = try fs.cwd().openDir(".", .{}); |
| 181 | | defer orig_cwd.setAsCwd() catch unreachable; |
| 182 | | |
| 183 | | // Create the target file |
| 184 | | try tmp.dir.writeFile(.{ .sub_path = target_name, .data = "nonsense" }); |
| 185 | | |
| 186 | | // Want to test relative paths, so cd into the tmpdir for this test |
| 187 | | try tmp.dir.setAsCwd(); |
| 188 | | |
| 189 | | if (native_os == .windows) { |
| 190 | | const wtarget_name = try std.unicode.wtf8ToWtf16LeAllocZ(a, target_name); |
| 191 | | const wsymlink_name = try std.unicode.wtf8ToWtf16LeAllocZ(a, symlink_name); |
| 192 | | defer a.free(wtarget_name); |
| 193 | | defer a.free(wsymlink_name); |
| 194 | | |
| 195 | | std.os.windows.CreateSymbolicLink(tmp.dir.fd, wsymlink_name, wtarget_name, false) catch |err| switch (err) { |
| 196 | | // Symlink requires admin privileges on windows, so this test can legitimately fail. |
| 197 | | error.AccessDenied => return error.SkipZigTest, |
| 198 | | else => return err, |
| 199 | | }; |
| 200 | | } else { |
| 201 | | try posix.symlink(target_name, symlink_name); |
| 202 | | } |
| 203 | | |
| 204 | | var buffer: [fs.max_path_bytes]u8 = undefined; |
| 205 | | const given = try posix.readlink(symlink_name, buffer[0..]); |
| 206 | | try expect(mem.eql(u8, target_name, given)); |
| 207 | | } |
| 208 | | |
| 209 | 170 | test "readlink on Windows" { |
| 210 | 171 | if (native_os != .windows) return error.SkipZigTest; |
| 211 | 172 | |
| ... | ... | @@ -220,55 +181,6 @@ fn testReadlink(target_path: []const u8, symlink_path: []const u8) !void { |
| 220 | 181 | try expect(mem.eql(u8, target_path, given)); |
| 221 | 182 | } |
| 222 | 183 | |
| 223 | | test "link with relative paths" { |
| 224 | | if (native_os == .wasi) return error.SkipZigTest; // Can link, but can't change into tmpDir |
| 225 | | if ((builtin.cpu.arch == .riscv32 or builtin.cpu.arch.isLoongArch()) and builtin.os.tag == .linux and !builtin.link_libc) return error.SkipZigTest; // No `fstat()`. |
| 226 | | if (builtin.cpu.arch.isMIPS64()) return error.SkipZigTest; // `nstat.nlink` assertion is failing with LLVM 20+ for unclear reasons. |
| 227 | | |
| 228 | | switch (native_os) { |
| 229 | | .wasi, .linux, .solaris, .illumos => {}, |
| 230 | | else => return error.SkipZigTest, |
| 231 | | } |
| 232 | | |
| 233 | | var tmp = tmpDir(.{}); |
| 234 | | defer tmp.cleanup(); |
| 235 | | |
| 236 | | // Restore default CWD at end of test. |
| 237 | | const orig_cwd = try fs.cwd().openDir(".", .{}); |
| 238 | | defer orig_cwd.setAsCwd() catch unreachable; |
| 239 | | |
| 240 | | const target_name = "link-target"; |
| 241 | | const link_name = "newlink"; |
| 242 | | |
| 243 | | try tmp.dir.writeFile(.{ .sub_path = target_name, .data = "example" }); |
| 244 | | |
| 245 | | // Test 1: create the relative link from inside tmp |
| 246 | | try tmp.dir.setAsCwd(); |
| 247 | | try posix.link(target_name, link_name); |
| 248 | | |
| 249 | | // Verify |
| 250 | | const efd = try tmp.dir.openFile(target_name, .{}); |
| 251 | | defer efd.close(); |
| 252 | | |
| 253 | | const nfd = try tmp.dir.openFile(link_name, .{}); |
| 254 | | defer nfd.close(); |
| 255 | | |
| 256 | | { |
| 257 | | const estat = try posix.fstat(efd.handle); |
| 258 | | const nstat = try posix.fstat(nfd.handle); |
| 259 | | try testing.expectEqual(estat.ino, nstat.ino); |
| 260 | | try testing.expectEqual(@as(@TypeOf(nstat.nlink), 2), nstat.nlink); |
| 261 | | } |
| 262 | | |
| 263 | | // Test 2: Remove the link and see the stats update |
| 264 | | try posix.unlink(link_name); |
| 265 | | |
| 266 | | { |
| 267 | | const estat = try posix.fstat(efd.handle); |
| 268 | | try testing.expectEqual(@as(@TypeOf(estat.nlink), 1), estat.nlink); |
| 269 | | } |
| 270 | | } |
| 271 | | |
| 272 | 184 | test "linkat with different directories" { |
| 273 | 185 | if ((builtin.cpu.arch == .riscv32 or builtin.cpu.arch.isLoongArch()) and builtin.os.tag == .linux and !builtin.link_libc) return error.SkipZigTest; // No `fstatat()`. |
| 274 | 186 | if (builtin.cpu.arch.isMIPS64()) return error.SkipZigTest; // `nstat.nlink` assertion is failing with LLVM 20+ for unclear reasons. |