What makes a valid Windows file name?

A common question for people starting to program on Windows is, “What makes a valid Windows file name?” You want to use this information to make simplifying assumptions in your code: that names can be no longer than MAX_PATH, that two names won't differ only by case, etc. Unfortunately, the answer to what makes a valid file name in Windows is not simple.

Due to the layering of Windows architecture, the definition of a "legal" file name may vary depending upon the component of the operating system you are dealing with.

· NTFS and the Posix subsystem have the most permissive definition of a "legal" name. The name may be up to 32,768 Unicode characters long. The name can contain trailing periods, trailing spaces, and two files may have names that differ only in case (e.g., README.TXT and readme.txt).

· The Win32 subsystem enforces additional constraints on legal file names. The name can be at most MAX_PATH characters long (defined in windef.h as 260 characters), may not have trailing dots or spaces, and file names are case preserving, not case sensitive — if two files exists with names that differ only in case, you will only be able to manipulate one of them through Win32 APIs.

· DOS and 16-bit Windows applications are still limited to "8.3" names.

See Inside Windows 2000, pages 729ff, for more information on the different constraints on file names.

These differences have practical consequences for any code that attempts to manage files that could be created by another program. If your management code uses DOS (heaven forbid!) or Win32 APIs to manipulate files, it is possible for the untrusted program to create files that your program cannot open or manipulate. For example, a user connected to Posix-based FTP server could create files with file names longer than MAX_PATH. If the administrator uses a Win32-based program to manage the FTP upload directory, then he will not be able to open, delete, or otherwise manipulate the files with long file names.

If you are writing a Win32-based program that manages arbitrary files, consider prepending " \\?\ " to the start of file names before you call CreateFile( ), DeleteFile( ), RenameFile( ), etc. This escape sequence at the start of a file name instructs the Win32 subsystem to bypass its normal name checking functions, and you will be able to use any valid NTFS name from your Win32 program.