summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSamuele Panzeri <samuele.panzeri@gmail.com>2023-05-05 02:12:55 +0200
committerRĂ©mi Verschelde <rverschelde@gmail.com>2023-05-12 12:31:22 +0200
commitcf0bd389cc7294c7e8bc6dbc57a88880cfd8372e (patch)
treeb5a79093923fca0f67ad6f1bb6bfd8ba56575fc9
parenta37f79124fb9d04eb7ecb9b0e23be34a0638d0b5 (diff)
Support long path in file access on windows
Changed windows file access file to check for path length and use the \\?\ long format when needed (cherry picked from commit 59f04e16b87ed5ce013c4ed184fdac796d814dc8)
-rw-r--r--core/io/dir_access.h2
-rw-r--r--core/io/file_access.h2
-rw-r--r--drivers/windows/dir_access_windows.cpp15
-rw-r--r--drivers/windows/dir_access_windows.h3
-rw-r--r--drivers/windows/file_access_windows.cpp8
-rw-r--r--drivers/windows/file_access_windows.h1
6 files changed, 23 insertions, 8 deletions
diff --git a/core/io/dir_access.h b/core/io/dir_access.h
index 51eb68eaea..52ed688deb 100644
--- a/core/io/dir_access.h
+++ b/core/io/dir_access.h
@@ -68,7 +68,7 @@ protected:
virtual String _get_root_string() const;
AccessType get_access_type() const;
- String fix_path(String p_path) const;
+ virtual String fix_path(String p_path) const;
template <class T>
static Ref<DirAccess> _create_builtin() {
diff --git a/core/io/file_access.h b/core/io/file_access.h
index 47770cad87..3374dca7a1 100644
--- a/core/io/file_access.h
+++ b/core/io/file_access.h
@@ -80,7 +80,7 @@ protected:
static void _bind_methods();
AccessType get_access_type() const;
- String fix_path(const String &p_path) const;
+ virtual String fix_path(const String &p_path) const;
virtual Error open_internal(const String &p_path, int p_mode_flags) = 0; ///< open a file
virtual uint64_t _get_modified_time(const String &p_file) = 0;
virtual void _set_access_type(AccessType p_access);
diff --git a/drivers/windows/dir_access_windows.cpp b/drivers/windows/dir_access_windows.cpp
index 7b88bd8a95..88eb89656a 100644
--- a/drivers/windows/dir_access_windows.cpp
+++ b/drivers/windows/dir_access_windows.cpp
@@ -59,6 +59,14 @@ struct DirAccessWindowsPrivate {
WIN32_FIND_DATAW fu; //unicode version
};
+String DirAccessWindows::fix_path(String p_path) const {
+ String r_path = DirAccess::fix_path(p_path);
+ if (r_path.is_absolute_path() && !r_path.is_network_share_path() && r_path.length() > MAX_PATH) {
+ r_path = "\\\\?\\" + r_path.replace("/", "\\");
+ }
+ return r_path;
+}
+
// CreateFolderAsync
Error DirAccessWindows::list_dir_begin() {
@@ -158,6 +166,7 @@ Error DirAccessWindows::make_dir(String p_dir) {
p_dir = fix_path(p_dir);
if (p_dir.is_relative_path()) {
p_dir = current_dir.path_join(p_dir);
+ p_dir = fix_path(p_dir);
}
p_dir = p_dir.simplify_path().replace("/", "\\");
@@ -165,12 +174,6 @@ Error DirAccessWindows::make_dir(String p_dir) {
bool success;
int err;
- if (!p_dir.is_network_share_path()) {
- p_dir = "\\\\?\\" + p_dir;
- // Add "\\?\" to the path to extend max. path length past 248, if it's not a network share UNC path.
- // See https://msdn.microsoft.com/en-us/library/windows/desktop/aa363855(v=vs.85).aspx
- }
-
success = CreateDirectoryW((LPCWSTR)(p_dir.utf16().get_data()), nullptr);
err = GetLastError();
diff --git a/drivers/windows/dir_access_windows.h b/drivers/windows/dir_access_windows.h
index 9d91c22f7e..1e55917756 100644
--- a/drivers/windows/dir_access_windows.h
+++ b/drivers/windows/dir_access_windows.h
@@ -53,6 +53,9 @@ class DirAccessWindows : public DirAccess {
bool _cisdir = false;
bool _cishidden = false;
+protected:
+ virtual String fix_path(String p_path) const override;
+
public:
virtual Error list_dir_begin() override; ///< This starts dir listing
virtual String get_next() override;
diff --git a/drivers/windows/file_access_windows.cpp b/drivers/windows/file_access_windows.cpp
index 0e51586b5a..03930626a5 100644
--- a/drivers/windows/file_access_windows.cpp
+++ b/drivers/windows/file_access_windows.cpp
@@ -68,6 +68,14 @@ bool FileAccessWindows::is_path_invalid(const String &p_path) {
return invalid_files.has(fname);
}
+String FileAccessWindows::fix_path(const String &p_path) const {
+ String r_path = FileAccess::fix_path(p_path);
+ if (r_path.is_absolute_path() && !r_path.is_network_share_path() && r_path.length() > MAX_PATH) {
+ r_path = "\\\\?\\" + r_path.replace("/", "\\");
+ }
+ return r_path;
+}
+
Error FileAccessWindows::open_internal(const String &p_path, int p_mode_flags) {
if (is_path_invalid(p_path)) {
#ifdef DEBUG_ENABLED
diff --git a/drivers/windows/file_access_windows.h b/drivers/windows/file_access_windows.h
index 453f8d3b5f..13c881e562 100644
--- a/drivers/windows/file_access_windows.h
+++ b/drivers/windows/file_access_windows.h
@@ -54,6 +54,7 @@ class FileAccessWindows : public FileAccess {
static HashSet<String> invalid_files;
public:
+ virtual String fix_path(const String &p_path) const override;
virtual Error open_internal(const String &p_path, int p_mode_flags) override; ///< open a file
virtual bool is_open() const override; ///< true when file is open