The \\?\ (pronounced “extended-length path” or “verbatim path”) syntax is a Windows path prefix that tells the system to treat the path literally and bypass normal Windows path processing (path normalization, MAX_PATH length limit, and some path parsing rules). Key points:
Purpose
- Allows paths longer than MAX_PATH (260 characters).
- Prevents the system from interpreting backslashes, relative segments (., ..), or expanding device names; the path is taken verbatim.
Syntax
- For local paths: start with \\?\ followed immediately by a drive letter and a colon, e.g.: \\?\C:\very\long\path...
- For UNC/network paths: use the \\?\UNC\ form instead of \\server\share, e.g.: \\?\UNC\server\share\path...
- Do not mix forward slashes; use backslashes.
Limits and behavior
- Removes the MAX_PATH ~260-character limit for most APIs that accept Win32 file paths when used with wide-char (UTF-16) APIs.
- Some Win32 APIs, shells, and libraries do not accept \\?\ paths; some higher-level frameworks (older .NET, Windows Explorer) may not handle them.
- Certain parse rules are disabled: the path is not normalized (so trailing dots/spaces are preserved) and long relative components won’t be collapsed.
- You must use absolute paths; relative paths with \\?\ are not supported.
- For device paths (NT namespace) a different prefix \\?\GLOBALROOT\ or \\.\ may be used for special device access.
Unicode
- Typically used with wide-character (W) Win32 APIs (UTF-16). Passing UTF-8/ANSI APIs can be problematic.
Examples
- Long local path: \\?\C:\very\long\directory... ( > 260 chars )
- Long UNC path: \\?\UNC\myserver\myshare\folder\file.txt
Common pitfalls
- Some Windows APIs (including many shell APIs) reject \\?\ paths.
- Don’t use trailing backslash immediately after \\?, e.g., \\?\C:\ is fine but be careful with extra slashes.
- When interop with libraries/frameworks, strip or add the prefix only at the last moment when calling Win32 functions.
C# example — using the \\?\ (verbatim/extended-length) path prefix
using System;
using System.IO;
using System.Text;
class Program
{
// Helper: convert a normal absolute path to an extended-length path for local drive or UNC
static string ToExtendedLengthPath(string path)
{
if (string.IsNullOrWhiteSpace(path))
throw new ArgumentException(nameof(path));
// Normalize separators
path = Path.GetFullPath(path);
// If UNC path (\\server\share\...), convert to \\?\UNC\server\share\...
if (path.StartsWith(@"\\"))
{
return @"\\?\UNC\" + path.Substring(2);
}
// Otherwise (drive letter) prefix with \\?\
return @"\\?\" + path;
}
static void Main()
{
// Example long folder path (ensure this exists or create it)
string longFolder = @"C:\example\very\long\path\that\..."; // replace with real long path
string extended = ToExtendedLengthPath(longFolder);
Console.WriteLine("Extended path: " + extended);
// Create directory using extended path
Directory.CreateDirectory(extended);
Console.WriteLine("Directory created.");
// Create a file inside that directory
string file = Path.Combine(extended, "test.txt");
using (var fs = new FileStream(file, FileMode.Create, FileAccess.Write, FileShare.None))
using (var sw = new StreamWriter(fs, Encoding.UTF8))
{
sw.WriteLine("Hello from extended-length path!");
}
Console.WriteLine("File written.");
// Read the file back
using (var sr = new StreamReader(new FileStream(file, FileMode.Open, FileAccess.Read, FileShare.Read), Encoding.UTF8))
{
Console.WriteLine("File contents:");
Console.WriteLine(sr.ReadToEnd());
}
}
}
Notes:
- Use Path.GetFullPath to ensure an absolute path before adding the prefix.
- For UNC paths (start with \\), convert to \\?\UNC... as shown.
- Many .NET APIs work with \\?\ paths on modern runtimes, but some higher-level APIs or components (older frameworks, Windows shell) may not.
No comments:
Post a Comment