Posts: 81
Threads: 37
Joined: Jun 2008
GetShortcutInfoEx does not work for directory symbolic links or junctions. Any idea how to get info about them, like what their targets are?
Posts: 12,073
Threads: 140
Joined: Dec 2002
Function
MountVolume
;/
function ~vol ~mountpoint
;Mounts volume vol to mountpoint.
;Error if fails.
;vol - volume name, eg "D:\".
;mountpoint - folder that will be mount point of vol. Can exist or not, as mount point or empty folder.
if(!vol.len or !mountpoint.len) end ES_BADARG
if(!vol.end("\")) vol+"\"
mountpoint.expandpath
mountpoint.rtrim("\")
if(dir(mountpoint 2)) UnmountVolume mountpoint
mkdir mountpoint; err end _error
mountpoint+"\"
;Vista bug: incorrect icon on desktop if the folder did not exist.
;To fix it, here could be inserted some delay.
;However (another Windows bug?) with 1 s delay, the folder becomes not as shortcut,
;and when you try to delete it, deletes all files in the volume. With eg
;5 s delay works well. Or maybe randomly, I did not test enough.
;Tried SHChangeNotify.
if(!GetVolumeNameForVolumeMountPoint(vol _s.all(100) 100) or !SetVolumeMountPointW(@mountpoint @_s.lpstr)) end _s.dllerror
Function
UnmountVolume
;/
function ~mountpoint
;Unmounts mountpoint and deletes the empty folder.
;Error if fails.
mountpoint.expandpath
if(!mountpoint.end("\")) mountpoint+"\"
if(!DeleteVolumeMountPointW(@mountpoint)) end _s.dllerror
del mountpoint.rtrim("\"); err end _error
Member function
str.GetMountPointTarget
;/
function $mountpoint
;Gets mount point target.
;Error if fails.
;The target is volume name in form "\\?\Volume\{GUID}\". With many functions it can be used instead of drive letter eg "D:\".
__HFile hf.Create(mountpoint OPEN_EXISTING GENERIC_READ 0 FILE_FLAG_OPEN_REPARSE_POINT|FILE_FLAG_BACKUP_SEMANTICS)
this.all(2000 2 0)
int n
if(!DeviceIoControl(hf FSCTL_GET_REPARSE_POINT 0 0 this this.len &n 0)) end _s.dllerror
if(n<=22) end ES_FAILED
this.get(this 20 n-20)
this.ansi
this.fix; this-"\\"
err+ end _error
Function
CreateSymLink
;/
function $symlink $target
;Creates symbolic link.
;Error if fails.
;If symlink exists and is not folder, deletes.
;Symbolic links are supported on Vista and later.
dll- kernel32 !CreateSymbolicLinkW @*lpSymlinkFileName @*lpTargetFileName dwFlags
str s1.expandpath(symlink)
if(dir(symlink)) del symlink; err
str s2.expandpath(target)
if(!CreateSymbolicLinkW(@s1 @s2 0)) end _s.dllerror
SHChangeNotify SHCNE_CREATE SHCNF_PATHW +@s1 0
Member function
str.GetSymLinkTarget
;/
function $symlink
;Gets symbolic link target.
;Error if fails.
;Symbolic links are supported on Vista and later.
;
__HFile hf.Create(symlink OPEN_EXISTING GENERIC_READ 0 FILE_FLAG_OPEN_REPARSE_POINT)
this.all(2000 2 0)
int n
if(!DeviceIoControl(hf FSCTL_GET_REPARSE_POINT 0 0 this this.len &n 0)) end _s.dllerror
if(n<=22) end ES_FAILED
this.get(this 20 n-20)
this.ansi
n=find(this "\??"); if(n<0) end ES_FAILED
this.fix(n)
err+ end _error
test
Macro
MountVolume("D:" "$desktop$\D")
;
str s.GetMountPointTarget("$desktop$\D")
out s
;5
;UnmountVolume "$desktop$\D"
;CreateSymLink "$desktop$\test_sl.txt" "$desktop$\test.txt"
;
;str s.GetSymLinkTarget("$desktop$\test_sl.txt")
;out s
;;5
;;del "$desktop$\test_sl.txt"