Watch, Follow, &
Connect with Us

For forums, blogs and more please visit our
Developer Tools Community.


Welcome, Guest
Guest Settings
Help

Thread: Unable to Resolve Shell Links



Permlink Replies: 2 - Last Post: Jan 9, 2016 5:12 PM Last Post By: Ian Branch
Ray Konopka

Posts: 32
Registered: 10/11/99
Unable to Resolve Shell Links
Click to report abuse...   Click to reply to this thread Reply
  Posted: Jan 9, 2016 2:44 PM
Hi Everyone,

I would appreciate your help. The following is a standard block of code that is commonly used to resolve shell links. The file name of the link file is passed to the function and a IShellLinkW reference is created and from that an IPersistFile reference. The IPersistFile reference is then use to load the link file. Then the shell information can be extracted from the file. For example, the path to the target specified in the link file.

Well, the reason I need your help is that this code no longer seems to work on any machine I've tested. Actually, the problem was brought to my attention by another developers). Anyway, the problem is that the PersisteFile.Load call always fails with an exception that the specified file does not exist. This is why I added the TFile.Exists() call in the function. This function also reports that the file does not exist. However, the file does indeed exists at the directory listed. In my original test, I used an Open Dialog to pick the file.

From what I can tell the GetFileAttributes Windows API function that is called when calling TFile.Exists is returning INVALID_FILE_ATTRIBUTES and the test fails. I suspect something similar is happening when calling PersistFile.Load.

What I am interested is if other people have the same problem with this code. I would also be interested to hear if this code works for anyone. I did my testing on Windows 7. Still have to test under Windows 10.

Thanks for your help.

Ray

uses
  IOUtils,
  ComObj,
  ActiveX,
  ShlObj;
 
function ResolveShellLink( const AShellLinkFile: string ): string;
var
  ShellLink: IShellLinkW;
  PersistFile: IPersistFile;
  tmpsz: array[ 0..MAX_PATH ] of Char;
  FindData: TWin32FindData;
begin
  Result := AShellLinkFile;
 
  OleCheck( CoCreateInstance( CLSID_ShellLink, nil, CLSCTX_INPROC_SERVER, IShellLinkW, ShellLink ) );
  try
    OleCheck( ShellLink.QueryInterface( IPersistFile, PersistFile ) );
    try
      if TFile.Exists( AShellLinkFile ) then
        ShowMessage( 'Exists' );
 
      OleCheck( PersistFile.Load( PWideChar( AShellLinkFile ), STGM_READ ) );
 
      OleCheck( ShellLink.Resolve( 0, SLR_ANY_MATCH or SLR_NO_UI ) );
 
      OleCheck( ShellLink.GetPath( tmpsz, MAX_PATH, FindData, SLGP_SHORTPATH ) );
 
      Result := tmpsz;
    finally
      PersistFile := nil;
    end;
  finally
    ShellLink := nil;
  end;
end;
 
 
procedure TForm7.RzButton1Click(Sender: TObject);
var
  S: string;
begin
  S := 'C:\Users\rkonopka\Documents\Embarcadero\Studio\Projects\Win32\Debug\Unit4.pas - Shortcut';
  ShowMessage( ResolveShellLink( S ) );
end;
Ian Branch

Posts: 442
Registered: 9/23/99
Re: Unable to Resolve Shell Links
Click to report abuse...   Click to reply to this thread Reply
  Posted: Jan 9, 2016 4:56 PM   in response to: Ray Konopka in response to: Ray Konopka
Hi Ray,

Raize rules.

Ummm, I'm no expert but shouldn't the line be...

	  S :=
'C:\Users\rkonopka\Documents\Embarcadero\Studio\Projects\Win32\Debug\Uni
t4.pas - Shortcut.lnk';
	


Note the .lnk after shortcut.

This works for me...;-) Delphi 10S - Win 10.

Regards,
Ian
Ian Branch

Posts: 442
Registered: 9/23/99
Re: Unable to Resolve Shell Links
Click to report abuse...   Click to reply to this thread Reply
  Posted: Jan 9, 2016 5:12 PM   in response to: Ian Branch in response to: Ian Branch
Just figured out I am an expert...

Ex - As in has been.
Spurt - As in drip under pressure.

;-)
Legend
Helpful Answer (5 pts)
Correct Answer (10 pts)

Server Response from: ETNAJIVE02