Even if you open a file with GUID, you can still get its name, or at least one of its names

Raymond Chen

Some time ago, I showed how you could eschew file names entirely and use GUIDs to open your files. But even if you choose to open the file with a GUID, you can still get its name.

Take the second program from that earlier article and make these changes:

#define UNICODE
#define _UNICODE
#include <windows.h>
#include <stdio.h>
#include <tchar.h>
#include <ole2.h>

int __cdecl _tmain(int argc, PTSTR *argv)
{
 HANDLE hRoot = CreateFile(_T("C:\\"), 0,
                 FILE_SHARE_READ | FILE_SHARE_WRITE |
                 FILE_SHARE_DELETE, NULL,
                 OPEN_EXISTING,
                 FILE_FLAG_BACKUP_SEMANTICS, NULL);
 if (hRoot != INVALID_HANDLE_VALUE) {
  FILE_ID_DESCRIPTOR desc;
  desc.dwSize = sizeof(desc);
  desc.Type = ObjectIdType;
  if (SUCCEEDED(CLSIDFromString(argv[1], &desc.ObjectId))) {
   HANDLE h = OpenFileById(hRoot, &desc, GENERIC_READ,
                 FILE_SHARE_READ | FILE_SHARE_WRITE |
                 FILE_SHARE_DELETE, NULL, 0);
   if (h != INVALID_HANDLE_VALUE) {
    TCHAR buffer[MAX_PATH];
    DWORD result = GetFinalPathNameByHandle(h,
                                buffer, ARRAYSIZE(buffer));
    if (result > 0 && result < ARRAYSIZE(buffer)) {
     _tprintf(_T("Final path is %s\n"), buffer);
    }
    CloseHandle(h);
   }
  }
  CloseHandle(hRoot);
 }
 return 0;
}

There’s a catch: If the file has multiple names (say, due to hard links), then only one of the names is returned, and you don’t get to pick which one. The system will pick one arbitrarily.

You can get the other names with the FindFirstFileName function, which I discussed some time ago.

7 comments

Discussion is closed. Login to edit/delete existing comments.

    • Theodore Dubois 0

      Can you update the link on the linked article please, Raymond?

  • Harold H 0

    It seems that the process of transferring old articles over to the new system has changed the formatting, resulting in a sort of Raymond Haiku.
    https://devblogs.microsoft.com/oldnewthing/?p=10103
    A customer asked,“Given a hardlink name,is it possible to get the original file name usedto create it in the first place?”

  • Stuart Dunkeld 0

    > The system will pick one arbitrarily.
    “Arbitrariness is the quality of being ‘determined by chance, whim, or impulse, and not by necessity, reason, or principle'”
    So it will pick one at random chance, or by some kind of ‘code whim’? I’m hoping not ‘by impulse’ as that would indicate a little more consciousness than I like to see in operating systems..

    • Kenny O Biel 0

      Arbitrary in that it is an implementation detail that might change in the future. From our perspective it is abitrary because MS’s “necessity, reason, or principle” might change, but if they let us know what those reasons are people will come rely on it making it impossible to change even if necessary.

    • MNGoldenEagle 0

      This is the problem with dictionaries, they provide definitions that are very generic and seldom useful in context.
      The technical definition of “arbitrary” from a developer’s standpoint is, “left up to implementation and transparent to the consumer.”  You care about the contract, but not with the contents.  For example, the result of a pseudo-random number generator is arbitrary: the result of the generator is always deterministic according to its state and implementation, but from our perspective we don’t care about how the number is generated, we just want a number.
      Another example: hash algorithms.  The result of a hash algorithm is arbitrary because we don’t care about what the actual hash is, we just care that it obeys the contract.  The implementation doesn’t matter, all that matters is that we get a hash.

  • Jo M 0

    I wonder why do you insist on showing code for 128 bit GUID instead of 64 bit fileID ? Assume that the scope is NTFS volume in our server. Inside that volume are many files and we want to shortcut the text path into reliable 64 bit number. Assume there are long term files over there. They are never moved and if they would move, that would be inside their volume.
    can you see the usefulness ? 
    I would expect GetFileByID to work on these 64 bit numbers.
    i did try the code with 128 bits and I get error 87. Checked the parameters many times. Does this have to do with admin rights ? I would not think so.
    Tons of verbiage all over the net about fileID but nobody talks about the usefulness of 64 bit access numbers instead of text pathes on the server.
    If you address me here, please share similar technique for use on Unix, hence Mac and Linux. Mac wants me to use bookmarks which is self defeating the usefulness. The good news is that Mac is not my first choice for server.

Feedback usabilla icon