As Jack pointed out in his answer, the short name is assigned when the file is created (or renamed, or moved). The value is dependent both on the long file name, as well as what other short names already exist.
The exact short name assignment algorithm is undocumented, and there is no guarantee that the algorithm remains constant between Windows versions, or even between different storage system formats. You should not write code that is dependent on any particular short name assignment algorithm.
There are both design limitations and bugs that arise from short file names. An example of a design limitation is del *.txt
can delete a file named something.txt2
because the extension of the short name will probably be .txt
, and source masks look at both long and short names. See the section titled "BUG - Short 8.3 filenames can break the /D and /S options
" at What are the undocumented features and limitations of the Windows FINDSTR command? for an example of a bug arising from short names.
NTFS volumes can have short file names disabled (short names that existed prior to disabling them will remain). Many people (organizations) disable short names on their system because of the problems they can cause.
Update
Here is a definitive argument for why it is a waste of time trying to establish the algorithm for how short file names are generated - FSUTIL allows you to specify any short name you want for a file, as long as it does not already exist in that folder.
Here is the relevant FSUTIL help documentation
C:\test>fsutil file
---- FILE Commands Supported ----
findbysid Find a file by security identifier
queryallocranges Query the allocated ranges for a file
setshortname Set the short name for a file
setvaliddata Set the valid data length for a file
setzerodata Set the zero data for a file
createnew Creates a new file of a specified size
queryfileid Queries the file ID of the specified file
queryfilenamebyid Displays a random link name for the file ID
C:\test>fsutil file setshortname /?
Usage : fsutil file setshortname <filename> <shortname>
Eg : fsutil file setshortname C:\testfile.txt testfile