godotengine / godotengine/godot

On Linux EditorPlugin opening file by `FileAccess::create_temp` with ModeFlag WRITE will have absolute path with mktemp characters.

Open
#116,018 2 comments 0 reactions 0 assignees View on GitHub
needs testing platform:linuxbsd topic:core topic:platforms
Dominant language
C++
Stars
117k
Forks
26.8k
PR merge metrics
PR metrics pending

Description

### Tested versions

Godot v4.7.dev (a0f49be5f)
Forgot to grap put also exist pre 4.6 release commit.

### System information

Godot v4.7.dev (a0f49be5f) - Arch Linux #1 SMP PREEMPT_DYNAMIC on Wayland - X11 display driver - Vulkan (Forward+)

### Issue description

I have custom resource file to load world data from.
I'm making editor plugin for tools to edit this file. I made a button to remake whole file because of certain edits.

Procedure for this is:
1. Use `FileAccess::create_temp` get **write only** temporary file. Call it `newfile`.
2. To the copy on relevent parts to `newfile`.
3. Close old resource `FileAccess`.
4. Rename old resource file to have ".bak" ending using `DirAccess::rename_absolute`.
5. Get `newfile` filename by `FileAccess::get_path_absolute`. Call it `tmpfile`
6. Close `newfile` `FileAccess`.
7. Rename `newfile` to be resource file using `DirAccess::rename_absolute` using `tmpfile`.
8. Reopen the resource file (which should be now "newfile" in content).

Procedure fails on step 7.

Reason for this is that in `FileAccessUnix::open_internal` backup save enabling gets triggered and mkstemp "adds" characters to the end. These characters are visible in `FileAccess::get_path_absolute` but not in `FileAccess::get_path`. This then causes an issue where on close mkstemp's characters are removed and then `tmppath` does not exist for step 6 since I used absolute path.

If I used `FileAccess::get_path` things would have worked out but Godot's API is not clear enough that I should use `FileAccess::get_path` in this case (maybe on some system get_path is relative with temporary files).

I think this backup save feature should disable on temporary files. Kinda, pointless for them but I want more opinions before commit to a fix.

There are also other problems backup save feature causes. FileAccess::create_temp opens the file twice to avoid problems on read only (this might not be problem on Unix) however this backup save feature makes first open pointless as mkstemp makes sure file names differ on both openings.

### Steps to reproduce

On Linux (or other system where ) using godot-cpp run:
```C++
Ref newfile=FileAccess::create_temp(FileAccess::ModeFlags::READ_WRITE, String(), String(), true);
const String tmpfile=newfile->get_path_absolute();
newfile->close();
if (DirAccess::rename_absolute(tmpfile,"/tmp/1234.abc") != Error::OK) {
print_line("ERROR");
}
```

### Minimal reproduction project (MRP)

N/A

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.