4 * Copyright 1998, 1999, 2000 Juergen Schmied
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
22 * Many of these functions are in SHLWAPI.DLL also
27 #include "wine/port.h"
31 #include "wine/debug.h"
37 #include "shell32_main.h"
38 #include "undocshell.h"
39 #include "wine/unicode.h"
42 WINE_DEFAULT_DEBUG_CHANNEL(shell
);
45 ########## Combining and Constructing paths ##########
48 /*************************************************************************
49 * PathAppend [SHELL32.36]
51 BOOL WINAPI
PathAppendAW(
55 if (SHELL_OsIsUnicode())
56 return PathAppendW(lpszPath1
, lpszPath2
);
57 return PathAppendA(lpszPath1
, lpszPath2
);
60 /*************************************************************************
61 * PathCombine [SHELL32.37]
63 LPVOID WINAPI
PathCombineAW(
68 if (SHELL_OsIsUnicode())
69 return PathCombineW( szDest
, lpszDir
, lpszFile
);
70 return PathCombineA( szDest
, lpszDir
, lpszFile
);
73 /*************************************************************************
74 * PathAddBackslash [SHELL32.32]
76 LPVOID WINAPI
PathAddBackslashAW(LPVOID lpszPath
)
78 if(SHELL_OsIsUnicode())
79 return PathAddBackslashW(lpszPath
);
80 return PathAddBackslashA(lpszPath
);
83 /*************************************************************************
84 * PathBuildRoot [SHELL32.30]
86 LPVOID WINAPI
PathBuildRootAW(LPVOID lpszPath
, int drive
)
88 if(SHELL_OsIsUnicode())
89 return PathBuildRootW(lpszPath
, drive
);
90 return PathBuildRootA(lpszPath
, drive
);
94 Extracting Component Parts
97 /*************************************************************************
98 * PathFindFileName [SHELL32.34]
100 LPVOID WINAPI
PathFindFileNameAW(LPCVOID lpszPath
)
102 if(SHELL_OsIsUnicode())
103 return PathFindFileNameW(lpszPath
);
104 return PathFindFileNameA(lpszPath
);
107 /*************************************************************************
108 * PathFindExtension [SHELL32.31]
110 LPVOID WINAPI
PathFindExtensionAW(LPCVOID lpszPath
)
112 if (SHELL_OsIsUnicode())
113 return PathFindExtensionW(lpszPath
);
114 return PathFindExtensionA(lpszPath
);
118 /*************************************************************************
119 * PathGetExtensionA [internal]
122 * exported by ordinal
123 * return value points to the first char after the dot
125 static LPSTR
PathGetExtensionA(LPCSTR lpszPath
)
127 TRACE("(%s)\n",lpszPath
);
129 lpszPath
= PathFindExtensionA(lpszPath
);
130 return (LPSTR
)(*lpszPath
?(lpszPath
+1):lpszPath
);
133 /*************************************************************************
134 * PathGetExtensionW [internal]
136 static LPWSTR
PathGetExtensionW(LPCWSTR lpszPath
)
138 TRACE("(%s)\n",debugstr_w(lpszPath
));
140 lpszPath
= PathFindExtensionW(lpszPath
);
141 return (LPWSTR
)(*lpszPath
?(lpszPath
+1):lpszPath
);
144 /*************************************************************************
145 * PathGetExtension [SHELL32.158]
147 LPVOID WINAPI
PathGetExtensionAW(LPCVOID lpszPath
,DWORD void1
, DWORD void2
)
149 if (SHELL_OsIsUnicode())
150 return PathGetExtensionW(lpszPath
);
151 return PathGetExtensionA(lpszPath
);
154 /*************************************************************************
155 * PathGetArgs [SHELL32.52]
157 LPVOID WINAPI
PathGetArgsAW(LPVOID lpszPath
)
159 if (SHELL_OsIsUnicode())
160 return PathGetArgsW(lpszPath
);
161 return PathGetArgsA(lpszPath
);
164 /*************************************************************************
165 * PathGetDriveNumber [SHELL32.57]
167 int WINAPI
PathGetDriveNumberAW(LPVOID lpszPath
)
169 if (SHELL_OsIsUnicode())
170 return PathGetDriveNumberW(lpszPath
);
171 return PathGetDriveNumberA(lpszPath
);
174 /*************************************************************************
175 * PathRemoveFileSpec [SHELL32.35]
177 BOOL WINAPI
PathRemoveFileSpecAW(LPVOID lpszPath
)
179 if (SHELL_OsIsUnicode())
180 return PathRemoveFileSpecW(lpszPath
);
181 return PathRemoveFileSpecA(lpszPath
);
184 /*************************************************************************
185 * PathStripPath [SHELL32.38]
187 void WINAPI
PathStripPathAW(LPVOID lpszPath
)
189 if (SHELL_OsIsUnicode())
190 PathStripPathW(lpszPath
);
192 PathStripPathA(lpszPath
);
195 /*************************************************************************
196 * PathStripToRoot [SHELL32.50]
198 BOOL WINAPI
PathStripToRootAW(LPVOID lpszPath
)
200 if (SHELL_OsIsUnicode())
201 return PathStripToRootW(lpszPath
);
202 return PathStripToRootA(lpszPath
);
205 /*************************************************************************
206 * PathRemoveArgs [SHELL32.251]
208 void WINAPI
PathRemoveArgsAW(LPVOID lpszPath
)
210 if (SHELL_OsIsUnicode())
211 PathRemoveArgsW(lpszPath
);
213 PathRemoveArgsA(lpszPath
);
216 /*************************************************************************
217 * PathRemoveExtension [SHELL32.250]
219 void WINAPI
PathRemoveExtensionAW(LPVOID lpszPath
)
221 if (SHELL_OsIsUnicode())
222 PathRemoveExtensionW(lpszPath
);
224 PathRemoveExtensionA(lpszPath
);
232 /*************************************************************************
233 * PathGetShortPathA [internal]
235 LPSTR WINAPI
PathGetShortPathA(LPSTR lpszPath
)
237 FIXME("%s stub\n", lpszPath
);
241 /*************************************************************************
242 * PathGetShortPathW [internal]
244 LPWSTR WINAPI
PathGetShortPathW(LPWSTR lpszPath
)
246 FIXME("%s stub\n", debugstr_w(lpszPath
));
250 /*************************************************************************
251 * PathGetShortPath [SHELL32.92]
253 LPVOID WINAPI
PathGetShortPathAW(LPVOID lpszPath
)
255 if(SHELL_OsIsUnicode())
256 return PathGetShortPathW(lpszPath
);
257 return PathGetShortPathA(lpszPath
);
260 /*************************************************************************
261 * PathRemoveBlanks [SHELL32.33]
263 void WINAPI
PathRemoveBlanksAW(LPVOID str
)
265 if(SHELL_OsIsUnicode())
266 PathRemoveBlanksW(str
);
268 PathRemoveBlanksA(str
);
271 /*************************************************************************
272 * PathQuoteSpaces [SHELL32.55]
274 VOID WINAPI
PathQuoteSpacesAW (LPVOID lpszPath
)
276 if(SHELL_OsIsUnicode())
277 PathQuoteSpacesW(lpszPath
);
279 PathQuoteSpacesA(lpszPath
);
282 /*************************************************************************
283 * PathUnquoteSpaces [SHELL32.56]
285 VOID WINAPI
PathUnquoteSpacesAW(LPVOID str
)
287 if(SHELL_OsIsUnicode())
288 PathUnquoteSpacesW(str
);
290 PathUnquoteSpacesA(str
);
293 /*************************************************************************
294 * PathParseIconLocation [SHELL32.249]
296 int WINAPI
PathParseIconLocationAW (LPVOID lpszPath
)
298 if(SHELL_OsIsUnicode())
299 return PathParseIconLocationW(lpszPath
);
300 return PathParseIconLocationA(lpszPath
);
304 ########## Path Testing ##########
306 /*************************************************************************
307 * PathIsUNC [SHELL32.39]
309 BOOL WINAPI
PathIsUNCAW (LPCVOID lpszPath
)
311 if (SHELL_OsIsUnicode())
312 return PathIsUNCW( lpszPath
);
313 return PathIsUNCA( lpszPath
);
316 /*************************************************************************
317 * PathIsRelative [SHELL32.40]
319 BOOL WINAPI
PathIsRelativeAW (LPCVOID lpszPath
)
321 if (SHELL_OsIsUnicode())
322 return PathIsRelativeW( lpszPath
);
323 return PathIsRelativeA( lpszPath
);
326 /*************************************************************************
327 * PathIsRoot [SHELL32.29]
329 BOOL WINAPI
PathIsRootAW(LPCVOID lpszPath
)
331 if (SHELL_OsIsUnicode())
332 return PathIsRootW(lpszPath
);
333 return PathIsRootA(lpszPath
);
336 /*************************************************************************
337 * PathIsExeA [internal]
339 static BOOL
PathIsExeA (LPCSTR lpszPath
)
341 LPCSTR lpszExtension
= PathGetExtensionA(lpszPath
);
343 static const char * const lpszExtensions
[] =
344 {"exe", "com", "pif", "cmd", "bat", "scf", "scr", NULL
};
346 TRACE("path=%s\n",lpszPath
);
348 for(i
=0; lpszExtensions
[i
]; i
++)
349 if (!strcasecmp(lpszExtension
,lpszExtensions
[i
])) return TRUE
;
354 /*************************************************************************
355 * PathIsExeW [internal]
357 static BOOL
PathIsExeW (LPCWSTR lpszPath
)
359 LPCWSTR lpszExtension
= PathGetExtensionW(lpszPath
);
361 static const WCHAR lpszExtensions
[][4] =
362 {{'e','x','e','\0'}, {'c','o','m','\0'}, {'p','i','f','\0'},
363 {'c','m','d','\0'}, {'b','a','t','\0'}, {'s','c','f','\0'},
364 {'s','c','r','\0'}, {'\0'} };
366 TRACE("path=%s\n",debugstr_w(lpszPath
));
368 for(i
=0; lpszExtensions
[i
][0]; i
++)
369 if (!strcmpiW(lpszExtension
,lpszExtensions
[i
])) return TRUE
;
374 /*************************************************************************
375 * PathIsExe [SHELL32.43]
377 BOOL WINAPI
PathIsExeAW (LPCVOID path
)
379 if (SHELL_OsIsUnicode())
380 return PathIsExeW (path
);
381 return PathIsExeA(path
);
384 /*************************************************************************
385 * PathIsDirectory [SHELL32.159]
387 BOOL WINAPI
PathIsDirectoryAW (LPCVOID lpszPath
)
389 if (SHELL_OsIsUnicode())
390 return PathIsDirectoryW (lpszPath
);
391 return PathIsDirectoryA (lpszPath
);
394 /*************************************************************************
395 * PathFileExists [SHELL32.45]
397 BOOL WINAPI
PathFileExistsAW (LPCVOID lpszPath
)
399 if (SHELL_OsIsUnicode())
400 return PathFileExistsW (lpszPath
);
401 return PathFileExistsA (lpszPath
);
404 /*************************************************************************
405 * PathMatchSpec [SHELL32.46]
407 BOOL WINAPI
PathMatchSpecAW(LPVOID name
, LPVOID mask
)
409 if (SHELL_OsIsUnicode())
410 return PathMatchSpecW( name
, mask
);
411 return PathMatchSpecA( name
, mask
);
414 /*************************************************************************
415 * PathIsSameRoot [SHELL32.650]
417 BOOL WINAPI
PathIsSameRootAW(LPCVOID lpszPath1
, LPCVOID lpszPath2
)
419 if (SHELL_OsIsUnicode())
420 return PathIsSameRootW(lpszPath1
, lpszPath2
);
421 return PathIsSameRootA(lpszPath1
, lpszPath2
);
424 /*************************************************************************
425 * IsLFNDrive [SHELL32.119]
428 * exported by ordinal Name
430 BOOL WINAPI
IsLFNDriveA(LPCSTR lpszPath
)
434 if (!GetVolumeInformationA(lpszPath
,NULL
,0,NULL
,&fnlen
,NULL
,NULL
,0))
440 ########## Creating Something Unique ##########
442 /*************************************************************************
443 * PathMakeUniqueNameA [internal]
445 BOOL WINAPI
PathMakeUniqueNameA(
448 LPCSTR lpszShortName
,
452 FIXME("%p %lu %s %s %s stub\n",
453 lpszBuffer
, dwBuffSize
, debugstr_a(lpszShortName
),
454 debugstr_a(lpszLongName
), debugstr_a(lpszPathName
));
458 /*************************************************************************
459 * PathMakeUniqueNameW [internal]
461 BOOL WINAPI
PathMakeUniqueNameW(
464 LPCWSTR lpszShortName
,
465 LPCWSTR lpszLongName
,
466 LPCWSTR lpszPathName
)
468 FIXME("%p %lu %s %s %s stub\n",
469 lpszBuffer
, dwBuffSize
, debugstr_w(lpszShortName
),
470 debugstr_w(lpszLongName
), debugstr_w(lpszPathName
));
474 /*************************************************************************
475 * PathMakeUniqueName [SHELL32.47]
477 BOOL WINAPI
PathMakeUniqueNameAW(
480 LPCVOID lpszShortName
,
481 LPCVOID lpszLongName
,
482 LPCVOID lpszPathName
)
484 if (SHELL_OsIsUnicode())
485 return PathMakeUniqueNameW(lpszBuffer
,dwBuffSize
, lpszShortName
,lpszLongName
,lpszPathName
);
486 return PathMakeUniqueNameA(lpszBuffer
,dwBuffSize
, lpszShortName
,lpszLongName
,lpszPathName
);
489 /*************************************************************************
490 * PathYetAnotherMakeUniqueName [SHELL32.75]
493 * exported by ordinal
495 BOOL WINAPI
PathYetAnotherMakeUniqueNameA(
498 LPCSTR lpszShortName
,
501 FIXME("(%p,%p, %p ,%p):stub.\n",
502 lpszBuffer
, lpszPathName
, lpszShortName
, lpszLongName
);
508 ########## cleaning and resolving paths ##########
511 /*************************************************************************
512 * PathFindOnPath [SHELL32.145]
514 BOOL WINAPI
PathFindOnPathAW(LPVOID sFile
, LPCVOID sOtherDirs
)
516 if (SHELL_OsIsUnicode())
517 return PathFindOnPathW(sFile
, (LPCWSTR
*)sOtherDirs
);
518 return PathFindOnPathA(sFile
, (LPCSTR
*)sOtherDirs
);
521 /*************************************************************************
522 * PathCleanupSpec [SHELL32.171]
524 DWORD WINAPI
PathCleanupSpecAW (LPCVOID x
, LPVOID y
)
526 FIXME("(%p, %p) stub\n",x
,y
);
530 /*************************************************************************
531 * PathQualifyA [SHELL32]
533 BOOL WINAPI
PathQualifyA(LPCSTR pszPath
)
535 FIXME("%s\n",pszPath
);
539 /*************************************************************************
540 * PathQualifyW [SHELL32]
542 BOOL WINAPI
PathQualifyW(LPCWSTR pszPath
)
544 FIXME("%s\n",debugstr_w(pszPath
));
548 /*************************************************************************
549 * PathQualify [SHELL32.49]
551 BOOL WINAPI
PathQualifyAW(LPCVOID pszPath
)
553 if (SHELL_OsIsUnicode())
554 return PathQualifyW(pszPath
);
555 return PathQualifyA(pszPath
);
558 /*************************************************************************
559 * PathResolveA [SHELL32.51]
561 BOOL WINAPI
PathResolveA(
566 FIXME("(%s,%p,0x%08lx),stub!\n",
567 lpszPath
, *alpszPaths
, dwFlags
);
571 /*************************************************************************
572 * PathResolveW [SHELL32]
574 BOOL WINAPI
PathResolveW(
579 FIXME("(%s,%p,0x%08lx),stub!\n",
580 debugstr_w(lpszPath
), debugstr_w(*alpszPaths
), dwFlags
);
584 /*************************************************************************
585 * PathResolve [SHELL32.51]
587 BOOL WINAPI
PathResolveAW(
592 if (SHELL_OsIsUnicode())
593 return PathResolveW(lpszPath
, (LPCWSTR
*)alpszPaths
, dwFlags
);
594 return PathResolveA(lpszPath
, (LPCSTR
*)alpszPaths
, dwFlags
);
597 /*************************************************************************
598 * PathProcessCommandA [SHELL32.653]
600 HRESULT WINAPI
PathProcessCommandA (
606 FIXME("%s %p 0x%04lx 0x%04lx stub\n",
607 lpszPath
, lpszBuff
, dwBuffSize
, dwFlags
);
608 strcpy(lpszBuff
, lpszPath
);
612 /*************************************************************************
613 * PathProcessCommandW
615 HRESULT WINAPI
PathProcessCommandW (
621 FIXME("(%s, %p, 0x%04lx, 0x%04lx) stub\n",
622 debugstr_w(lpszPath
), lpszBuff
, dwBuffSize
, dwFlags
);
623 strcpyW(lpszBuff
, lpszPath
);
627 /*************************************************************************
628 * PathProcessCommand (SHELL32.653)
630 HRESULT WINAPI
PathProcessCommandAW (
636 if (SHELL_OsIsUnicode())
637 return PathProcessCommandW(lpszPath
, lpszBuff
, dwBuffSize
, dwFlags
);
638 return PathProcessCommandA(lpszPath
, lpszBuff
, dwBuffSize
, dwFlags
);
642 ########## special ##########
645 /*************************************************************************
646 * PathSetDlgItemPath (SHELL32.48)
648 VOID WINAPI
PathSetDlgItemPathAW(HWND hDlg
, int id
, LPCVOID pszPath
)
650 if (SHELL_OsIsUnicode())
651 PathSetDlgItemPathW(hDlg
, id
, pszPath
);
653 PathSetDlgItemPathA(hDlg
, id
, pszPath
);
657 /*************************************************************************
658 * SHGetSpecialFolderPathA [SHELL32.@]
660 * converts csidl to path
663 static const char * const szSHFolders
= "Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\Shell Folders";
664 static const char * const szSHUserFolders
= "Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\User Shell Folders";
665 static const char * const szSetup
= "Software\\Microsoft\\Windows\\CurrentVersion\\Setup";
666 static const char * const szCurrentVersion
= "Software\\Microsoft\\Windows\\CurrentVersion";
668 static const char * const szEnvUserProfile
= "%USERPROFILE%";
669 static const char * const szEnvSystemRoot
= "%SYSTEMROOT%";
677 LPCSTR szDefaultPath
; /* fallback string; sub dir of windows directory */
680 #define CSIDL_MYFLAG_SHFOLDER 1
681 #define CSIDL_MYFLAG_SETUP 2
682 #define CSIDL_MYFLAG_CURRVER 4
683 #define CSIDL_MYFLAG_RELATIVE 8
685 #define HKLM HKEY_LOCAL_MACHINE
686 #define HKCU HKEY_CURRENT_USER
687 static const CSIDL_DATA CSIDL_Data
[] =
689 { /* CSIDL_DESKTOP */
694 { /* CSIDL_INTERNET */
695 0, (HKEY
)1, /* FIXME */
699 { /* CSIDL_PROGRAMS */
702 "Start Menu\\Programs"
704 { /* CSIDL_CONTROLS (.CPL files) */
709 { /* CSIDL_PRINTERS */
714 { /* CSIDL_PERSONAL */
719 { /* CSIDL_FAVORITES */
724 { /* CSIDL_STARTUP */
727 "Start Menu\\Programs\\StartUp"
739 { /* CSIDL_BITBUCKET (is this c:\recycled ?) */
740 0, (HKEY
)1, /* FIXME */
744 { /* CSIDL_STARTMENU */
749 { /* CSIDL_MYDOCUMENTS */
750 0, (HKEY
)1, /* FIXME */
754 { /* CSIDL_MYMUSIC */
755 0, (HKEY
)1, /* FIXME */
759 { /* CSIDL_MYVIDEO */
760 0, (HKEY
)1, /* FIXME */
769 { /* CSIDL_DESKTOPDIRECTORY */
775 0, (HKEY
)1, /* FIXME */
779 { /* CSIDL_NETWORK */
780 0, (HKEY
)1, /* FIXME */
782 "Network Neighborhood"
784 { /* CSIDL_NETHOOD */
794 { /* CSIDL_TEMPLATES */
799 { /* CSIDL_COMMON_STARTMENU */
804 { /* CSIDL_COMMON_PROGRAMS */
809 { /* CSIDL_COMMON_STARTUP */
812 "All Users\\Start Menu\\Programs\\StartUp"
814 { /* CSIDL_COMMON_DESKTOPDIRECTORY */
819 { /* CSIDL_APPDATA */
824 { /* CSIDL_PRINTHOOD */
829 { /* CSIDL_LOCAL_APPDATA (win2k only/undocumented) */
832 "Local Settings\\Application Data",
834 { /* CSIDL_ALTSTARTUP */
835 0, (HKEY
)1, /* FIXME */
839 { /* CSIDL_COMMON_ALTSTARTUP */
840 0, (HKEY
)1, /* FIXME */
844 { /* CSIDL_COMMON_FAVORITES */
849 { /* CSIDL_INTERNET_CACHE */
852 "Temporary Internet Files"
854 { /* CSIDL_COOKIES */
859 { /* CSIDL_HISTORY */
864 { /* CSIDL_COMMON_APPDATA */
867 "All Users\\Application Data"
869 { /* CSIDL_WINDOWS */
879 { /* CSIDL_PROGRAM_FILES */
884 { /* CSIDL_MYPICTURES */
887 "My Documents\\My Pictures"
889 { /* CSIDL_PROFILE */
891 "WinDir", /* correct ? */
894 { /* CSIDL_SYSTEMX86 */
899 { /* CSIDL_PROGRAM_FILESX86 */
904 { /* CSIDL_PROGRAM_FILES_COMMON */
907 "Program Files\\Common Files" /* ? */
909 { /* CSIDL_PROGRAM_FILES_COMMONX86 */
912 "Program Files\\Common Files" /* ? */
914 { /* CSIDL_COMMON_TEMPLATES */
915 0, (HKEY
)1, /* FIXME */
919 { /* CSIDL_COMMON_DOCUMENTS */
920 0, (HKEY
)1, /* FIXME */
924 { /* CSIDL_COMMON_ADMINTOOLS */
925 0, (HKEY
)1, /* FIXME */
929 { /* CSIDL_ADMINTOOLS */
931 "Administrative Tools",
932 "Start Menu\\Programs\\Administrative Tools"
934 { /* CSIDL_CONNECTIONS */
935 0, (HKEY
)1, /* FIXME */
954 { /* CSIDL_COMMON_MUSIC */
959 { /* CSIDL_COMMON_PICTURES */
964 { /* CSIDL_COMMON_VIDEO */
969 { /* CSIDL_RESOURCES */
974 { /* CSIDL_RESOURCES_LOCALIZED */
979 { /* CSIDL_COMMON_OEM_LINKS */
984 { /* CSIDL_CDBURN_AREA */
989 { /* unassigned 3C */
994 { /* CSIDL_COMPUTERSNEARME */
999 { /* CSIDL_PROFILES */
1008 /**********************************************************************/
1010 BOOL WINAPI
SHGetSpecialFolderPathA (
1016 CHAR szValueName
[MAX_PATH
], szDefaultPath
[MAX_PATH
], szBuildPath
[MAX_PATH
];
1017 HKEY hRootKey
, hKey
;
1019 DWORD dwType
, dwDisp
, dwPathLen
= MAX_PATH
;
1020 DWORD folder
= csidl
& CSIDL_FOLDER_MASK
;
1023 TRACE("%p,%p,csidl=%lu,0x%04x\n", hwndOwner
,szPath
,csidl
,bCreate
);
1025 if ((folder
>= sizeof(CSIDL_Data
) / sizeof(CSIDL_Data
[0])) ||
1026 (CSIDL_Data
[folder
].hRootKey
== 0))
1028 ERR("folder 0x%04lx unknown or not allowed\n", folder
);
1031 if (CSIDL_Data
[folder
].hRootKey
== (HKEY
)1)
1033 FIXME("folder 0x%04lx unknown, please add.\n", folder
);
1037 dwFlags
= CSIDL_Data
[folder
].dwFlags
;
1038 hRootKey
= CSIDL_Data
[folder
].hRootKey
;
1039 strcpy(szValueName
, CSIDL_Data
[folder
].szValueName
);
1040 strcpy(szDefaultPath
, CSIDL_Data
[folder
].szDefaultPath
);
1042 if (dwFlags
& CSIDL_MYFLAG_SHFOLDER
)
1044 /* user shell folders */
1045 if (RegCreateKeyExA(hRootKey
,szSHUserFolders
,0,NULL
,0,KEY_ALL_ACCESS
,NULL
,&hKey
,&dwDisp
)) return FALSE
;
1047 if (RegQueryValueExA(hKey
,szValueName
,NULL
,&dwType
,(LPBYTE
)szPath
,&dwPathLen
))
1052 if (RegCreateKeyExA(hRootKey
,szSHFolders
,0,NULL
,0,KEY_ALL_ACCESS
,NULL
,&hKey
,&dwDisp
)) return FALSE
;
1054 if (RegQueryValueExA(hKey
,szValueName
,NULL
,&dwType
,(LPBYTE
)szPath
,&dwPathLen
))
1057 /* value not existing */
1058 if (dwFlags
& CSIDL_MYFLAG_RELATIVE
)
1060 GetWindowsDirectoryA(szPath
, MAX_PATH
);
1061 PathAddBackslashA(szPath
);
1062 strcat(szPath
, szDefaultPath
);
1066 strcpy(szPath
, "C:\\"); /* FIXME ??? */
1067 strcat(szPath
, szDefaultPath
);
1069 RegSetValueExA(hKey
,szValueName
,0,REG_SZ
,(LPBYTE
)szPath
,strlen(szPath
)+1);
1078 if (dwFlags
& CSIDL_MYFLAG_SETUP
)
1081 if (dwFlags
& CSIDL_MYFLAG_CURRVER
)
1082 pRegPath
= szCurrentVersion
;
1085 ERR("folder settings broken, please correct !\n");
1089 if (RegCreateKeyExA(hRootKey
,pRegPath
,0,NULL
,0,KEY_ALL_ACCESS
,NULL
,&hKey
,&dwDisp
)) return FALSE
;
1091 if (RegQueryValueExA(hKey
,szValueName
,NULL
,&dwType
,(LPBYTE
)szPath
,&dwPathLen
))
1093 /* value not existing */
1094 if (dwFlags
& CSIDL_MYFLAG_RELATIVE
)
1096 GetWindowsDirectoryA(szPath
, MAX_PATH
);
1097 PathAddBackslashA(szPath
);
1098 strcat(szPath
, szDefaultPath
);
1102 strcpy(szPath
, "C:\\"); /* FIXME ??? */
1103 strcat(szPath
, szDefaultPath
);
1105 RegSetValueExA(hKey
,szValueName
,0,REG_SZ
,(LPBYTE
)szPath
,strlen(szPath
)+1);
1110 /* expand paths like %USERPROFILE% */
1111 if (dwType
== REG_EXPAND_SZ
)
1113 ExpandEnvironmentStringsA(szPath
, szDefaultPath
, MAX_PATH
);
1114 strcpy(szPath
, szDefaultPath
);
1117 /* if we don't care about existing directories we are ready */
1118 if(csidl
& CSIDL_FLAG_DONT_VERIFY
) return TRUE
;
1120 if (PathFileExistsA(szPath
)) return TRUE
;
1122 /* not existing but we are not allowed to create it */
1123 if (!bCreate
) return FALSE
;
1125 /* create directory/directories */
1126 strcpy(szBuildPath
, szPath
);
1127 p
= strchr(szBuildPath
, '\\');
1131 if (!PathFileExistsA(szBuildPath
))
1133 if (!CreateDirectoryA(szBuildPath
,NULL
))
1135 ERR("Failed to create directory '%s'.\n", szPath
);
1140 p
= strchr(p
+1, '\\');
1142 /* last component must be created too. */
1143 if (!PathFileExistsA(szBuildPath
))
1145 if (!CreateDirectoryA(szBuildPath
,NULL
))
1147 ERR("Failed to create directory '%s'.\n", szPath
);
1152 MESSAGE("Created not existing system directory '%s'\n", szPath
);
1156 /*************************************************************************
1157 * SHGetSpecialFolderPathW
1159 BOOL WINAPI
SHGetSpecialFolderPathW (
1165 char szTemp
[MAX_PATH
];
1167 if (SHGetSpecialFolderPathA(hwndOwner
, szTemp
, csidl
, bCreate
))
1169 if (!MultiByteToWideChar( CP_ACP
, 0, szTemp
, -1, szPath
, MAX_PATH
))
1170 szPath
[MAX_PATH
-1] = 0;
1173 TRACE("%p,%p,csidl=%lu,0x%04x\n", hwndOwner
,szPath
,csidl
,bCreate
);
1178 /*************************************************************************
1179 * SHGetSpecialFolderPath (SHELL32.175)
1181 BOOL WINAPI
SHGetSpecialFolderPathAW (
1188 if (SHELL_OsIsUnicode())
1189 return SHGetSpecialFolderPathW (hwndOwner
, szPath
, csidl
, bCreate
);
1190 return SHGetSpecialFolderPathA (hwndOwner
, szPath
, csidl
, bCreate
);
1193 /*************************************************************************
1194 * SHGetFolderPathA [SHELL32.@]
1196 HRESULT WINAPI
SHGetFolderPathA(
1199 HANDLE hToken
, /* [in] FIXME: get paths for specific user */
1200 DWORD dwFlags
, /* [in] FIXME: SHGFP_TYPE_CURRENT|SHGFP_TYPE_DEFAULT */
1203 return (SHGetSpecialFolderPathA(
1206 CSIDL_FOLDER_MASK
& nFolder
,
1207 CSIDL_FLAG_CREATE
& nFolder
)) ? S_OK
: E_FAIL
;
1210 /*************************************************************************
1211 * SHGetFolderPathW [SHELL32.@]
1213 HRESULT WINAPI
SHGetFolderPathW(
1220 return (SHGetSpecialFolderPathW(
1223 CSIDL_FOLDER_MASK
& nFolder
,
1224 CSIDL_FLAG_CREATE
& nFolder
)) ? S_OK
: E_FAIL
;