| ... | @@ -16238,6 +16238,8 @@ fn createFileMap( | ... | @@ -16238,6 +16238,8 @@ fn createFileMap( |
| 16238 | try Thread.checkCancel(); | 16238 | try Thread.checkCancel(); |
| 16239 | | 16239 | |
| 16240 | var section = windows.INVALID_HANDLE_VALUE; | 16240 | var section = windows.INVALID_HANDLE_VALUE; |
| | 16241 | const section_size: windows.LARGE_INTEGER = @intCast(len); |
| | 16242 | const page = windows.PAGE.fromProtection(protection) orelse return error.AccessDenied; |
| 16241 | switch (windows.ntdll.NtCreateSection( | 16243 | switch (windows.ntdll.NtCreateSection( |
| 16242 | &section, | 16244 | &section, |
| 16243 | .{ | 16245 | .{ |
| ... | @@ -16251,8 +16253,8 @@ fn createFileMap( | ... | @@ -16251,8 +16253,8 @@ fn createFileMap( |
| 16251 | .STANDARD = .{ .RIGHTS = .REQUIRED }, | 16253 | .STANDARD = .{ .RIGHTS = .REQUIRED }, |
| 16252 | }, | 16254 | }, |
| 16253 | null, | 16255 | null, |
| 16254 | @constCast(&@as(i64, @intCast(len))), | 16256 | &section_size, |
| 16255 | .{ .READWRITE = true }, | 16257 | page, |
| 16256 | .{ .COMMIT = populate }, | 16258 | .{ .COMMIT = populate }, |
| 16257 | file.handle, | 16259 | file.handle, |
| 16258 | )) { | 16260 | )) { |
| ... | @@ -16260,6 +16262,7 @@ fn createFileMap( | ... | @@ -16260,6 +16262,7 @@ fn createFileMap( |
| 16260 | .FILE_LOCK_CONFLICT => return error.FileLockConflict, | 16262 | .FILE_LOCK_CONFLICT => return error.FileLockConflict, |
| 16261 | .INVALID_FILE_FOR_SECTION => return error.OperationUnsupported, | 16263 | .INVALID_FILE_FOR_SECTION => return error.OperationUnsupported, |
| 16262 | .ACCESS_DENIED => return error.AccessDenied, | 16264 | .ACCESS_DENIED => return error.AccessDenied, |
| | 16265 | .SECTION_TOO_BIG => return error.SectionOversize, |
| 16263 | else => |status| return windows.unexpectedStatus(status), | 16266 | else => |status| return windows.unexpectedStatus(status), |
| 16264 | } | 16267 | } |
| 16265 | var contents_ptr: ?[*]align(std.heap.page_size_min) u8 = null; | 16268 | var contents_ptr: ?[*]align(std.heap.page_size_min) u8 = null; |
| ... | @@ -16274,7 +16277,7 @@ fn createFileMap( | ... | @@ -16274,7 +16277,7 @@ fn createFileMap( |
| 16274 | &contents_len, | 16277 | &contents_len, |
| 16275 | .Unmap, | 16278 | .Unmap, |
| 16276 | .{}, | 16279 | .{}, |
| 16277 | .{ .READWRITE = true }, | 16280 | page, |
| 16278 | )) { | 16281 | )) { |
| 16279 | .SUCCESS => {}, | 16282 | .SUCCESS => {}, |
| 16280 | .CONFLICTING_ADDRESSES => return error.MappingAlreadyExists, | 16283 | .CONFLICTING_ADDRESSES => return error.MappingAlreadyExists, |
| ... | @@ -16363,16 +16366,20 @@ fn fileMemoryMapDestroy(userdata: ?*anyopaque, mm: *File.MemoryMap) void { | ... | @@ -16363,16 +16366,20 @@ fn fileMemoryMapDestroy(userdata: ?*anyopaque, mm: *File.MemoryMap) void { |
| 16363 | const memory = mm.memory; | 16366 | const memory = mm.memory; |
| 16364 | if (mm.section) |section| switch (native_os) { | 16367 | if (mm.section) |section| switch (native_os) { |
| 16365 | .windows => { | 16368 | .windows => { |
| | 16369 | if (section == windows.INVALID_HANDLE_VALUE) return; |
| 16366 | _ = windows.ntdll.NtUnmapViewOfSection(windows.current_process, memory.ptr); | 16370 | _ = windows.ntdll.NtUnmapViewOfSection(windows.current_process, memory.ptr); |
| 16367 | windows.CloseHandle(section); | 16371 | windows.CloseHandle(section); |
| 16368 | }, | 16372 | }, |
| 16369 | .wasi => unreachable, | 16373 | .wasi => unreachable, |
| 16370 | else => switch (posix.errno(posix.system.munmap(memory.ptr, memory.len))) { | 16374 | else => { |
| 16371 | .SUCCESS => {}, | 16375 | if (memory.len == 0) return; |
| 16372 | else => |e| { | 16376 | switch (posix.errno(posix.system.munmap(memory.ptr, memory.len))) { |
| 16373 | if (builtin.mode == .Debug) | 16377 | .SUCCESS => {}, |
| 16374 | std.log.err("failed to unmap {d} bytes at {*}: {t}", .{ memory.len, memory.ptr, e }); | 16378 | else => |e| { |
| 16375 | }, | 16379 | if (builtin.mode == .Debug) |
| | 16380 | std.log.err("failed to unmap {d} bytes at {*}: {t}", .{ memory.len, memory.ptr, e }); |
| | 16381 | }, |
| | 16382 | } |
| 16376 | }, | 16383 | }, |
| 16377 | } else { | 16384 | } else { |
| 16378 | const gpa = t.allocator; | 16385 | const gpa = t.allocator; |
| ... | @@ -16394,47 +16401,16 @@ fn fileMemoryMapSetLength( | ... | @@ -16394,47 +16401,16 @@ fn fileMemoryMapSetLength( |
| 16394 | const new_len = options.len; | 16401 | const new_len = options.len; |
| 16395 | | 16402 | |
| 16396 | if (mm.section) |section| { | 16403 | if (mm.section) |section| { |
| 16397 | const aligned_old_len = alignment.forward(old_memory.len); | 16404 | if (alignment.forward(new_len) == alignment.forward(old_memory.len)) { |
| 16398 | const aligned_new_len = alignment.forward(new_len); | | |
| 16399 | if (aligned_new_len == aligned_old_len) { | | |
| 16400 | mm.memory.len = new_len; | 16405 | mm.memory.len = new_len; |
| 16401 | return; | 16406 | return; |
| 16402 | } | 16407 | } |
| 16403 | switch (native_os) { | 16408 | switch (native_os) { |
| 16404 | .windows => { | 16409 | .windows => { |
| 16405 | if (aligned_new_len > aligned_old_len) { | 16410 | _ = windows.ntdll.NtUnmapViewOfSection(windows.current_process, old_memory.ptr); |
| 16406 | var new_section_size: windows.LARGE_INTEGER = @intCast(aligned_new_len); | 16411 | windows.CloseHandle(section); |
| 16407 | switch (windows.ntdll.NtExtendSection(section, &new_section_size)) { | 16412 | mm.section = windows.INVALID_HANDLE_VALUE; |
| 16408 | .SUCCESS => {}, | 16413 | mm.memory = &.{}; |
| 16409 | else => |status| return windows.unexpectedStatus(status), | | |
| 16410 | } | | |
| 16411 | assert(new_section_size == aligned_new_len); | | |
| 16412 | mm.memory.len = new_len; | | |
| 16413 | } else { | | |
| 16414 | _ = windows.ntdll.NtUnmapViewOfSection(windows.current_process, old_memory.ptr); | | |
| 16415 | windows.CloseHandle(section); | | |
| 16416 | var contents_len = aligned_new_len; | | |
| 16417 | var contents_ptr: ?[*]align(std.heap.page_size_min) u8 = null; | | |
| 16418 | switch (windows.ntdll.NtMapViewOfSection( | | |
| 16419 | section, | | |
| 16420 | windows.current_process, | | |
| 16421 | @ptrCast(&contents_ptr), | | |
| 16422 | null, | | |
| 16423 | 0, | | |
| 16424 | null, | | |
| 16425 | &contents_len, | | |
| 16426 | .Unmap, | | |
| 16427 | .{}, | | |
| 16428 | .{ .READWRITE = true }, | | |
| 16429 | )) { | | |
| 16430 | .SUCCESS => {}, | | |
| 16431 | .SECTION_PROTECTION => return error.PermissionDenied, | | |
| 16432 | .INVALID_VIEW_SIZE => |status| return windows.statusBug(status), | | |
| 16433 | else => |status| return windows.unexpectedStatus(status), | | |
| 16434 | } | | |
| 16435 | assert(contents_len == aligned_new_len); | | |
| 16436 | mm.memory = contents_ptr.?[0..new_len]; | | |
| 16437 | } | | |
| 16438 | }, | 16414 | }, |
| 16439 | .wasi => unreachable, | 16415 | .wasi => unreachable, |
| 16440 | .linux => { | 16416 | .linux => { |
| ... | @@ -16463,6 +16439,7 @@ fn fileMemoryMapSetLength( | ... | @@ -16463,6 +16439,7 @@ fn fileMemoryMapSetLength( |
| 16463 | } | 16439 | } |
| 16464 | }; | 16440 | }; |
| 16465 | mm.memory = new_memory; | 16441 | mm.memory = new_memory; |
| | 16442 | return; |
| 16466 | }, | 16443 | }, |
| 16467 | else => { | 16444 | else => { |
| 16468 | switch (posix.errno(posix.system.munmap(old_memory.ptr, old_memory.len))) { | 16445 | switch (posix.errno(posix.system.munmap(old_memory.ptr, old_memory.len))) { |
| ... | @@ -16475,20 +16452,21 @@ fn fileMemoryMapSetLength( | ... | @@ -16475,20 +16452,21 @@ fn fileMemoryMapSetLength( |
| 16475 | return error.Unexpected; | 16452 | return error.Unexpected; |
| 16476 | }, | 16453 | }, |
| 16477 | } | 16454 | } |
| 16478 | if (createFileMap(mm.file, options.protection, mm.offset, options.populate, new_len)) |result| { | 16455 | mm.memory = &.{}; |
| 16479 | mm.* = result; | | |
| 16480 | return; | | |
| 16481 | } else |err| switch (err) { | | |
| 16482 | error.OperationUnsupported, | | |
| 16483 | error.Unseekable, | | |
| 16484 | error.SectionOversize, | | |
| 16485 | error.MappingAlreadyExists, | | |
| 16486 | error.FileLockConflict, | | |
| 16487 | => return error.Unexpected, // It worked before on the same open file. | | |
| 16488 | else => |e| return e, | | |
| 16489 | } | | |
| 16490 | }, | 16456 | }, |
| 16491 | } | 16457 | } |
| | 16458 | if (createFileMap(mm.file, options.protection, mm.offset, options.populate, new_len)) |result| { |
| | 16459 | mm.* = result; |
| | 16460 | return; |
| | 16461 | } else |err| switch (err) { |
| | 16462 | error.OperationUnsupported, |
| | 16463 | error.Unseekable, |
| | 16464 | error.SectionOversize, |
| | 16465 | error.MappingAlreadyExists, |
| | 16466 | error.FileLockConflict, |
| | 16467 | => return error.Unexpected, // It worked before on the same open file. |
| | 16468 | else => |e| return e, |
| | 16469 | } |
| 16492 | } else { | 16470 | } else { |
| 16493 | const gpa = t.allocator; | 16471 | const gpa = t.allocator; |
| 16494 | if (gpa.rawRemap(old_memory, alignment, new_len, @returnAddress())) |new_ptr| { | 16472 | if (gpa.rawRemap(old_memory, alignment, new_len, @returnAddress())) |new_ptr| { |