Sunday, June 5, 2011

GetSpecialFolderPath in Powershell

To complete "Enumerate your own enum in Powershell" post, I give you this below script to use GetSpecialFolderPath
(Download it)
You can remove # comment in this script if you need to see some examples of array or hashtable use


#
#
# GetSpecialFolderPath
#
# by F.Richard 2011-05
#
#

#Requires -Version 2.0


# CSIDL
# http://msdn.microsoft.com/en-us/library/bb762494%28v=vs.85%29.aspx
# for windows XP and later OS
# KNOWNFOLDERID
# http://msdn.microsoft.com/en-us/library/dd378457%28v=vs.85%29.aspx
# for Vista and later OS
# Recognized Environment Variables
# http://technet.microsoft.com/en-us/library/cc749104%28WS.10%29.aspx

# DllImport
$signature = @"
[DllImport("Shell32.dll")]
public static extern int SHGetSpecialFolderPath(UIntPtr hwndOwner, System.Text.StringBuilder lpszPath, CSIDL iCsidl, int fCreate);


public enum CSIDL : int {
CSIDL_DESKTOP = 0x0000,
CSIDL_INTERNET = 0x0001,
CSIDL_PROGRAMS = 0x0002,
CSIDL_CONTROLS = 0x0003,
CSIDL_PRINTERS = 0x0004,
CSIDL_PERSONAL = 0x0005,
CSIDL_FAVORITES = 0x0006,
CSIDL_STARTUP = 0x0007,
CSIDL_RECENT = 0x0008,
CSIDL_SENDTO = 0x0009,
CSIDL_BITBUCKET = 0x000a,
CSIDL_STARTMENU = 0x000b,
CSIDL_MYDOCUMENTS = CSIDL_PERSONAL,
CSIDL_MYMUSIC = 0x000d,
CSIDL_MYVIDEO = 0x000e,
CSIDL_DESKTOPDIRECTORY = 0x0010,
CSIDL_DRIVES = 0x0011,
CSIDL_NETWORK = 0x0012,
CSIDL_NETHOOD = 0x0013,
CSIDL_FONTS = 0x0014,
CSIDL_TEMPLATES = 0x0015,
CSIDL_COMMON_STARTMENU = 0x0016,
CSIDL_COMMON_PROGRAMS = 0x0017,
CSIDL_COMMON_STARTUP = 0x0018,
CSIDL_COMMON_DESKTOPDIRECTORY = 0x0019,
CSIDL_APPDATA = 0x001a,
CSIDL_PRINTHOOD = 0x001b,
CSIDL_LOCAL_APPDATA = 0x001c,
CSIDL_ALTSTARTUP = 0x001d,
CSIDL_COMMON_ALTSTARTUP = 0x001e,
CSIDL_COMMON_FAVORITES = 0x001f,
CSIDL_INTERNET_CACHE = 0x0020,
CSIDL_COOKIES = 0x0021,
CSIDL_HISTORY = 0x0022,
CSIDL_COMMON_APPDATA = 0x0023,
CSIDL_WINDOWS = 0x0024,
CSIDL_SYSTEM = 0x0025,
CSIDL_PROGRAM_FILES = 0x0026,
CSIDL_MYPICTURES = 0x0027,
CSIDL_PROFILE = 0x0028,
CSIDL_SYSTEMX86 = 0x0029,
CSIDL_PROGRAM_FILESX86 = 0x002a,
CSIDL_PROGRAM_FILES_COMMON = 0x002b,
CSIDL_PROGRAM_FILES_COMMONX86 = 0x002c,
CSIDL_COMMON_TEMPLATES = 0x002d,
CSIDL_COMMON_DOCUMENTS = 0x002e,
CSIDL_COMMON_ADMINTOOLS = 0x002f,
CSIDL_ADMINTOOLS = 0x0030,
CSIDL_CONNECTIONS = 0x0031,
CSIDL_COMMON_MUSIC = 0x0035,
CSIDL_COMMON_PICTURES = 0x0036,
CSIDL_COMMON_VIDEO = 0x0037,
CSIDL_RESOURCES = 0x0038,
CSIDL_RESOURCES_LOCALIZED = 0x0039,
CSIDL_COMMON_OEM_LINKS = 0x003a,
CSIDL_CDBURN_AREA = 0x003b,
CSIDL_COMPUTERSNEARME = 0x003d,
CSIDL_FLAG_CREATE = 0x8000,
CSIDL_FLAG_DONT_VERIFY = 0x4000,
CSIDL_FLAG_DONT_UNEXPAND = 0x2000,
CSIDL_FLAG_NO_ALIAS = 0x1000,
CSIDL_FLAG_PER_USER_INIT = 0x0800
}
"@



# Register shell32 functions
If (-not ("Shell32.Tools" -as [Type])) {
$type = Add-Type -MemberDefinition $signature -Name Tools -Namespace Shell32 -Using System.Text -PassThru
} else {
If ($debug) { Write-Host "Shell32.Tools already Registered" }
}
# Get Common Desktop Directory
$hwnd = New-Object UIntPtr
$lpData = New-Object System.Text.StringBuilder(260) # MAX_PATH = 256
$CSIDL = "CSIDL_COMMON_DESKTOPDIRECTORY"
if([Shell32.Tools]::SHGetSpecialFolderPath($hwnd, $lpData, $CSIDL, 0)) {
Write-Host $CSIDL "=" $lpData
}


# Enum To Array
$arrEnum=[Enum]::GetNames([Shell32.Tools+CSIDL])
# Remove remark to display name and value
#foreach ($name in $arrEnum) {
# Write-Host "Name:$name Value:"([Shell32.Tools+CSIDL]::$name).value__
#}


# Enum To Hash
$hashEnum = @{ }
[Enum]::GetValues([Shell32.Tools+CSIDL])| % {$hashEnum["$_"] = $_.value__ }
# Remove remark to display name and value
#foreach ($name in $hashEnum.keys) {
# Write-Host "Name:$name Value:"$hashEnum["$name"]
#}


foreach ($CSIDL in $arrEnum) {
if ([Shell32.Tools]::SHGetSpecialFolderPath($hwnd, $lpData, $CSIDL, 0)) {
Write-Host $CSIDL "=" $lpData
}
}


Windows 2003 english example results with myuser user


C:\> .\GetSpecialFolderPath.ps1
CSIDL_COMMON_DESKTOPDIRECTORY = C:\Documents and Settings\All Users\Desktop
CSIDL_DESKTOP = C:\Documents and Settings\myuser\Desktop
CSIDL_PROGRAMS = C:\Documents and Settings\myuser\Start Menu\Programs
CSIDL_PERSONAL = C:\Documents and Settings\myuser\My Documents
CSIDL_MYDOCUMENTS = C:\Documents and Settings\myuser\My Documents
CSIDL_FAVORITES = C:\Documents and Settings\myuser\Favorites
CSIDL_STARTUP = C:\Documents and Settings\myuser\Start Menu\Programs\Startup
CSIDL_RECENT = C:\Documents and Settings\myuser\Recent
CSIDL_SENDTO = C:\Documents and Settings\myuser\SendTo
CSIDL_STARTMENU = C:\Documents and Settings\myuser\Start Menu
CSIDL_DESKTOPDIRECTORY = C:\Documents and Settings\myuser\Desktop
CSIDL_NETHOOD = C:\Documents and Settings\myuser\NetHood
CSIDL_FONTS = C:\WINDOWS\Fonts
CSIDL_TEMPLATES = C:\Documents and Settings\myuser\Templates
CSIDL_COMMON_STARTMENU = C:\Documents and Settings\All Users\Start Menu
CSIDL_COMMON_PROGRAMS = C:\Documents and Settings\All Users\Start Menu\Programs
CSIDL_COMMON_STARTUP = C:\Documents and Settings\All Users\Start Menu\Programs\Startup
CSIDL_COMMON_DESKTOPDIRECTORY = C:\Documents and Settings\All Users\Desktop
CSIDL_APPDATA = C:\Documents and Settings\myuser\Application Data
CSIDL_PRINTHOOD = C:\Documents and Settings\myuser\PrintHood
CSIDL_LOCAL_APPDATA = C:\Documents and Settings\myuser\Local Settings\Application Data
CSIDL_COMMON_FAVORITES = C:\Documents and Settings\All Users\Favorites
CSIDL_INTERNET_CACHE = C:\Documents and Settings\myuser\Local Settings\Temporary Internet Files
CSIDL_COOKIES = C:\Documents and Settings\myuser\Cookies
CSIDL_HISTORY = C:\Documents and Settings\myuser\Local Settings\History
CSIDL_COMMON_APPDATA = C:\Documents and Settings\All Users\Application Data
CSIDL_WINDOWS = C:\WINDOWS
CSIDL_SYSTEM = C:\WINDOWS\system32
CSIDL_PROGRAM_FILES = C:\Program Files
CSIDL_PROFILE = C:\Documents and Settings\myuser
CSIDL_SYSTEMX86 = C:\WINDOWS\system32
CSIDL_PROGRAM_FILES_COMMON = C:\Program Files\Common Files
CSIDL_COMMON_TEMPLATES = C:\Documents and Settings\All Users\Templates
CSIDL_COMMON_DOCUMENTS = C:\Documents and Settings\All Users\Documents
CSIDL_COMMON_ADMINTOOLS = C:\Documents and Settings\All Users\Start Menu\Programs\Administrative Tools
CSIDL_ADMINTOOLS = C:\Documents and Settings\myuser\Start Menu\Programs\Administrative Tools
CSIDL_COMMON_MUSIC = C:\Documents and Settings\All Users\Documents\My Music
CSIDL_COMMON_VIDEO = C:\Documents and Settings\All Users\Documents\My Videos
CSIDL_RESOURCES = C:\WINDOWS\resources
CSIDL_CDBURN_AREA = C:\Documents and Settings\myuser\Local Settings\Application Data\Microsoft\CD Burning
CSIDL_FLAG_PER_USER_INIT = C:\Documents and Settings\myuser\Desktop
CSIDL_FLAG_NO_ALIAS = C:\Documents and Settings\myuser\Desktop
CSIDL_FLAG_DONT_UNEXPAND = C:\Documents and Settings\myuser\Desktop
CSIDL_FLAG_DONT_VERIFY = C:\Documents and Settings\myuser\Desktop
CSIDL_FLAG_CREATE = C:\Documents and Settings\myuser\Desktop



Windows XP french example results with myuser user


c:\> .\GetSpecialFolderPath.ps1
CSIDL_COMMON_DESKTOPDIRECTORY = C:\Documents and Settings\All Users\Bureau
CSIDL_DESKTOP = C:\Documents and Settings\myuser\Bureau
CSIDL_PROGRAMS = C:\Documents and Settings\myuser\Menu Démarrer\Programmes
CSIDL_PERSONAL = D:\DONNEES
CSIDL_MYDOCUMENTS = D:\DONNEES
CSIDL_FAVORITES = C:\Documents and Settings\myuser\Favoris
CSIDL_STARTUP = C:\Documents and Settings\myuser\Menu Démarrer\Programmes\Démarrage
CSIDL_RECENT = C:\Documents and Settings\myuser\Recent
CSIDL_SENDTO = C:\Documents and Settings\myuser\SendTo
CSIDL_STARTMENU = C:\Documents and Settings\myuser\Menu Démarrer
CSIDL_MYMUSIC = D:\DONNEES\Ma musique
CSIDL_MYVIDEO = D:\DONNEES\Mes vidéos
CSIDL_DESKTOPDIRECTORY = C:\Documents and Settings\myuser\Bureau
CSIDL_NETHOOD = C:\Documents and Settings\myuser\Voisinage réseau
CSIDL_FONTS = C:\WINDOWS\Fonts
CSIDL_TEMPLATES = C:\Documents and Settings\myuser\Modèles
CSIDL_COMMON_STARTMENU = C:\Documents and Settings\All Users\Menu Démarrer
CSIDL_COMMON_PROGRAMS = C:\Documents and Settings\All Users\Menu Démarrer\Programmes
CSIDL_COMMON_STARTUP = C:\Documents and Settings\All Users\Menu Démarrer\Programmes\Démarrage
CSIDL_COMMON_DESKTOPDIRECTORY = C:\Documents and Settings\All Users\Bureau
CSIDL_APPDATA = C:\Documents and Settings\myuser\Application Data
CSIDL_PRINTHOOD = C:\Documents and Settings\myuser\Voisinage d'impression
CSIDL_LOCAL_APPDATA = C:\Documents and Settings\myuser\Local Settings\Application Data
CSIDL_COMMON_FAVORITES = C:\Documents and Settings\All Users\Favoris
CSIDL_INTERNET_CACHE = C:\Documents and Settings\myuser\Local Settings\Temporary Internet Files
CSIDL_COOKIES = C:\Documents and Settings\myuser\Cookies
CSIDL_HISTORY = C:\Documents and Settings\myuser\Local Settings\Historique
CSIDL_COMMON_APPDATA = C:\Documents and Settings\All Users\Application Data
CSIDL_WINDOWS = C:\WINDOWS
CSIDL_SYSTEM = C:\WINDOWS\system32
CSIDL_PROGRAM_FILES = C:\Program Files
CSIDL_MYPICTURES = D:\DONNEES
CSIDL_PROFILE = C:\Documents and Settings\myuser
CSIDL_SYSTEMX86 = C:\WINDOWS\system32
CSIDL_PROGRAM_FILES_COMMON = C:\Program Files\Fichiers communs
CSIDL_COMMON_TEMPLATES = C:\Documents and Settings\All Users\Modèles
CSIDL_COMMON_DOCUMENTS = C:\Documents and Settings\All Users\Documents
CSIDL_COMMON_ADMINTOOLS = C:\Documents and Settings\All Users\Menu Démarrer\Programmes\Outils d'administration
CSIDL_ADMINTOOLS = C:\Documents and Settings\myuser\Menu Démarrer\Programmes\Outils d'administration
CSIDL_COMMON_MUSIC = C:\Documents and Settings\All Users\Documents\Ma musique
CSIDL_COMMON_PICTURES = C:\Documents and Settings\All Users\Documents\Mes images
CSIDL_COMMON_VIDEO = C:\Documents and Settings\All Users\Documents\Mes vidéos
CSIDL_RESOURCES = C:\WINDOWS\resources
CSIDL_CDBURN_AREA = C:\Documents and Settings\myuser\Local Settings\Application Data\Microsoft\CD Burning
CSIDL_FLAG_PER_USER_INIT = C:\Documents and Settings\myuser\Bureau
CSIDL_FLAG_NO_ALIAS = C:\Documents and Settings\myuser\Bureau
CSIDL_FLAG_DONT_UNEXPAND = C:\Documents and Settings\myuser\Bureau
CSIDL_FLAG_DONT_VERIFY = C:\Documents and Settings\myuser\Bureau
CSIDL_FLAG_CREATE = C:\Documents and Settings\myuser\Bureau

2 comments:

Michael said...

Awesome! Exactly what I needed, thank you for the script. 5 Stars!

Anonymous said...

Thanks Franck, this gave me exactly what I wanted, a list of CSIDL values :-)