LCOV - code coverage report
Current view: directory - xpcom/io - SpecialSystemDirectory.cpp (source / functions) Found Hit Coverage
Test: app.info Lines: 128 44 34.4 %
Date: 2012-06-02 Functions: 5 5 100.0 %

       1                 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2                 : /* ***** BEGIN LICENSE BLOCK *****
       3                 :  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
       4                 :  *
       5                 :  * The contents of this file are subject to the Mozilla Public License Version
       6                 :  * 1.1 (the "License"); you may not use this file except in compliance with
       7                 :  * the License. You may obtain a copy of the License at
       8                 :  * http://www.mozilla.org/MPL/
       9                 :  *
      10                 :  * Software distributed under the License is distributed on an "AS IS" basis,
      11                 :  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
      12                 :  * for the specific language governing rights and limitations under the
      13                 :  * License.
      14                 :  *
      15                 :  * The Original Code is Mozilla Communicator client code, released
      16                 :  * March 31, 1998.
      17                 :  *
      18                 :  * The Initial Developer of the Original Code is
      19                 :  * Netscape Communications Corporation.
      20                 :  * Portions created by the Initial Developer are Copyright (C) 1998
      21                 :  * the Initial Developer. All Rights Reserved.
      22                 :  *
      23                 :  * Contributor(s):
      24                 :  *   Doug Turner <dougt@netscape.com>
      25                 :  *   IBM Corp.
      26                 :  *   Fredrik Holmqvist <thesuckiestemail@yahoo.se>
      27                 :  *   Jungshik Shin <jshin@i18nl10n.com>
      28                 :  *
      29                 :  * Alternatively, the contents of this file may be used under the terms of
      30                 :  * either of the GNU General Public License Version 2 or later (the "GPL"),
      31                 :  * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
      32                 :  * in which case the provisions of the GPL or the LGPL are applicable instead
      33                 :  * of those above. If you wish to allow use of your version of this file only
      34                 :  * under the terms of either the GPL or the LGPL, and not to allow others to
      35                 :  * use your version of this file under the terms of the MPL, indicate your
      36                 :  * decision by deleting the provisions above and replace them with the notice
      37                 :  * and other provisions required by the GPL or the LGPL. If you do not delete
      38                 :  * the provisions above, a recipient may use your version of this file under
      39                 :  * the terms of any one of the MPL, the GPL or the LGPL.
      40                 :  *
      41                 :  * ***** END LICENSE BLOCK ***** */
      42                 : 
      43                 : #include "SpecialSystemDirectory.h"
      44                 : #include "nsString.h"
      45                 : #include "nsDependentString.h"
      46                 : 
      47                 : #if defined(XP_WIN)
      48                 : 
      49                 : #include <windows.h>
      50                 : #include <shlobj.h>
      51                 : #include <stdlib.h>
      52                 : #include <stdio.h>
      53                 : #include <string.h>
      54                 : #include <direct.h>
      55                 : 
      56                 : #elif defined(XP_OS2)
      57                 : 
      58                 : #define MAX_PATH _MAX_PATH
      59                 : #define INCL_WINWORKPLACE
      60                 : #define INCL_DOSMISC
      61                 : #define INCL_DOSMODULEMGR
      62                 : #define INCL_DOSPROCESS
      63                 : #define INCL_WINSHELLDATA
      64                 : #include <os2.h>
      65                 : #include <stdlib.h>
      66                 : #include <stdio.h>
      67                 : #include "prenv.h"
      68                 : 
      69                 : #elif defined(XP_UNIX)
      70                 : 
      71                 : #include <limits.h>
      72                 : #include <unistd.h>
      73                 : #include <stdlib.h>
      74                 : #include <sys/param.h>
      75                 : #include "prenv.h"
      76                 : 
      77                 : #endif
      78                 : 
      79                 : #if defined(VMS)
      80                 : #include <unixlib.h>
      81                 : #endif
      82                 : 
      83                 : #ifndef MAXPATHLEN
      84                 : #ifdef PATH_MAX
      85                 : #define MAXPATHLEN PATH_MAX
      86                 : #elif defined(MAX_PATH)
      87                 : #define MAXPATHLEN MAX_PATH
      88                 : #elif defined(_MAX_PATH)
      89                 : #define MAXPATHLEN _MAX_PATH
      90                 : #elif defined(CCHMAXPATH)
      91                 : #define MAXPATHLEN CCHMAXPATH
      92                 : #else
      93                 : #define MAXPATHLEN 1024
      94                 : #endif
      95                 : #endif
      96                 : 
      97                 : #ifdef XP_WIN
      98                 : typedef HRESULT (WINAPI* nsGetKnownFolderPath)(GUID& rfid,
      99                 :                                                DWORD dwFlags,
     100                 :                                                HANDLE hToken,
     101                 :                                                PWSTR *ppszPath);
     102                 : 
     103                 : static nsGetKnownFolderPath gGetKnownFolderPath = NULL;
     104                 : #endif
     105                 : 
     106            1419 : void StartupSpecialSystemDirectory()
     107                 : {
     108                 : #if defined (XP_WIN)
     109                 :     // SHGetKnownFolderPath is only available on Windows Vista
     110                 :     // so that we need to use GetProcAddress to get the pointer.
     111                 :     HMODULE hShell32DLLInst = GetModuleHandleW(L"shell32.dll");
     112                 :     if(hShell32DLLInst)
     113                 :     {
     114                 :         gGetKnownFolderPath = (nsGetKnownFolderPath)
     115                 :             GetProcAddress(hShell32DLLInst, "SHGetKnownFolderPath");
     116                 :     }
     117                 : #endif
     118            1419 : }
     119                 : 
     120                 : #if defined (XP_WIN)
     121                 : 
     122                 : static nsresult GetKnownFolder(GUID* guid, nsILocalFile** aFile)
     123                 : {
     124                 :     if (!guid || !gGetKnownFolderPath)
     125                 :         return NS_ERROR_FAILURE;
     126                 : 
     127                 :     PWSTR path = NULL;
     128                 :     gGetKnownFolderPath(*guid, 0, NULL, &path);
     129                 : 
     130                 :     if (!path)
     131                 :         return NS_ERROR_FAILURE;
     132                 : 
     133                 :     nsresult rv = NS_NewLocalFile(nsDependentString(path),
     134                 :                                   true,
     135                 :                                   aFile);
     136                 : 
     137                 :     CoTaskMemFree(path);
     138                 :     return rv;
     139                 : }
     140                 : 
     141                 : //----------------------------------------------------------------------------------------
     142                 : static nsresult GetWindowsFolder(int folder, nsILocalFile** aFile)
     143                 : //----------------------------------------------------------------------------------------
     144                 : {
     145                 :     WCHAR path_orig[MAX_PATH + 3];
     146                 :     WCHAR *path = path_orig+1;
     147                 :     HRESULT result = SHGetSpecialFolderPathW(NULL, path, folder, true);
     148                 : 
     149                 :     if (!SUCCEEDED(result))
     150                 :         return NS_ERROR_FAILURE;
     151                 : 
     152                 :     // Append the trailing slash
     153                 :     int len = wcslen(path);
     154                 :     if (len > 1 && path[len - 1] != L'\\')
     155                 :     {
     156                 :         path[len]   = L'\\';
     157                 :         path[++len] = L'\0';
     158                 :     }
     159                 : 
     160                 :     return NS_NewLocalFile(nsDependentString(path, len), true, aFile);
     161                 : }
     162                 : 
     163                 : /**
     164                 :  * Provides a fallback for getting the path to APPDATA or LOCALAPPDATA by
     165                 :  * querying the registry when the call to SHGetSpecialFolderPathW is unable to
     166                 :  * provide these paths (Bug 513958).
     167                 :  */
     168                 : static nsresult GetRegWindowsAppDataFolder(bool aLocal, nsILocalFile** aFile)
     169                 : {
     170                 :     HKEY key;
     171                 :     NS_NAMED_LITERAL_STRING(keyName,
     172                 :     "Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\Shell Folders");
     173                 :     DWORD res = ::RegOpenKeyExW(HKEY_CURRENT_USER, keyName.get(), 0, KEY_READ,
     174                 :                                 &key);
     175                 :     if (res != ERROR_SUCCESS)
     176                 :         return NS_ERROR_FAILURE;
     177                 : 
     178                 :     WCHAR path[MAX_PATH + 2];
     179                 :     DWORD type, size;
     180                 :     res = RegQueryValueExW(key, (aLocal ? L"Local AppData" : L"AppData"), NULL,
     181                 :                            &type, (LPBYTE)&path, &size);
     182                 :     ::RegCloseKey(key);
     183                 :     // The call to RegQueryValueExW must succeed, the type must be REG_SZ, the
     184                 :     // buffer size must not equal 0, and the buffer size be a multiple of 2.
     185                 :     if (res != ERROR_SUCCESS || type != REG_SZ || size == 0 || size % 2 != 0)
     186                 :         return NS_ERROR_FAILURE;
     187                 : 
     188                 :     // Append the trailing slash
     189                 :     int len = wcslen(path);
     190                 :     if (len > 1 && path[len - 1] != L'\\')
     191                 :     {
     192                 :         path[len]   = L'\\';
     193                 :         path[++len] = L'\0';
     194                 :     }
     195                 : 
     196                 :     return NS_NewLocalFile(nsDependentString(path, len), true, aFile);
     197                 : }
     198                 : 
     199                 : #endif // XP_WIN
     200                 : 
     201                 : #if defined(XP_UNIX)
     202                 : static nsresult
     203              31 : GetUnixHomeDir(nsILocalFile** aFile)
     204                 : {
     205                 : #ifdef VMS
     206                 :     char *pHome;
     207                 :     pHome = getenv("HOME");
     208                 :     if (*pHome == '/') {
     209                 :         return NS_NewNativeLocalFile(nsDependentCString(pHome),
     210                 :                                      true,
     211                 :                                      aFile);
     212                 :     } else {
     213                 :         return NS_NewNativeLocalFile(nsDependentCString(decc$translate_vms(pHome)),
     214                 :                                      true,
     215                 :                                      aFile);
     216                 :     }
     217                 : #elif defined(ANDROID)
     218                 :     // XXX no home dir on android; maybe we should return the sdcard if present?
     219                 :     return NS_ERROR_FAILURE;
     220                 : #else
     221              62 :     return NS_NewNativeLocalFile(nsDependentCString(PR_GetEnv("HOME")),
     222              31 :                                  true, aFile);
     223                 : #endif
     224                 : }
     225                 : 
     226                 : /*
     227                 :   The following license applies to the xdg_user_dir_lookup function:
     228                 : 
     229                 :   Copyright (c) 2007 Red Hat, Inc.
     230                 : 
     231                 :   Permission is hereby granted, free of charge, to any person
     232                 :   obtaining a copy of this software and associated documentation files
     233                 :   (the "Software"), to deal in the Software without restriction,
     234                 :   including without limitation the rights to use, copy, modify, merge,
     235                 :   publish, distribute, sublicense, and/or sell copies of the Software,
     236                 :   and to permit persons to whom the Software is furnished to do so,
     237                 :   subject to the following conditions:
     238                 : 
     239                 :   The above copyright notice and this permission notice shall be
     240                 :   included in all copies or substantial portions of the Software.
     241                 : 
     242                 :   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
     243                 :   EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
     244                 :   MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
     245                 :   NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
     246                 :   BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
     247                 :   ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
     248                 :   CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
     249                 :   SOFTWARE.
     250                 : */
     251                 : 
     252                 : static char *
     253               9 : xdg_user_dir_lookup (const char *type)
     254                 : {
     255                 :   FILE *file;
     256                 :   char *home_dir, *config_home, *config_file;
     257                 :   char buffer[512];
     258                 :   char *user_dir;
     259                 :   char *p, *d;
     260                 :   int len;
     261                 :   int relative;
     262                 : 
     263               9 :   home_dir = getenv ("HOME");
     264                 : 
     265               9 :   if (home_dir == NULL)
     266               0 :     goto error;
     267                 : 
     268               9 :   config_home = getenv ("XDG_CONFIG_HOME");
     269               9 :   if (config_home == NULL || config_home[0] == 0)
     270                 :     {
     271               9 :       config_file = (char*) malloc (strlen (home_dir) + strlen ("/.config/user-dirs.dirs") + 1);
     272               9 :       if (config_file == NULL)
     273               0 :         goto error;
     274                 : 
     275               9 :       strcpy (config_file, home_dir);
     276               9 :       strcat (config_file, "/.config/user-dirs.dirs");
     277                 :     }
     278                 :   else
     279                 :     {
     280               0 :       config_file = (char*) malloc (strlen (config_home) + strlen ("/user-dirs.dirs") + 1);
     281               0 :       if (config_file == NULL)
     282               0 :         goto error;
     283                 : 
     284               0 :       strcpy (config_file, config_home);
     285               0 :       strcat (config_file, "/user-dirs.dirs");
     286                 :     }
     287                 : 
     288               9 :   file = fopen (config_file, "r");
     289               9 :   free (config_file);
     290               9 :   if (file == NULL)
     291               9 :     goto error;
     292                 : 
     293               0 :   user_dir = NULL;
     294               0 :   while (fgets (buffer, sizeof (buffer), file))
     295                 :     {
     296                 :       /* Remove newline at end */
     297               0 :       len = strlen (buffer);
     298               0 :       if (len > 0 && buffer[len-1] == '\n')
     299               0 :         buffer[len-1] = 0;
     300                 : 
     301               0 :       p = buffer;
     302               0 :       while (*p == ' ' || *p == '\t')
     303               0 :         p++;
     304                 : 
     305               0 :       if (strncmp (p, "XDG_", 4) != 0)
     306               0 :         continue;
     307               0 :       p += 4;
     308               0 :       if (strncmp (p, type, strlen (type)) != 0)
     309               0 :         continue;
     310               0 :       p += strlen (type);
     311               0 :       if (strncmp (p, "_DIR", 4) != 0)
     312               0 :         continue;
     313               0 :       p += 4;
     314                 : 
     315               0 :       while (*p == ' ' || *p == '\t')
     316               0 :         p++;
     317                 : 
     318               0 :       if (*p != '=')
     319               0 :         continue;
     320               0 :       p++;
     321                 : 
     322               0 :       while (*p == ' ' || *p == '\t')
     323               0 :         p++;
     324                 : 
     325               0 :       if (*p != '"')
     326               0 :         continue;
     327               0 :       p++;
     328                 : 
     329               0 :       relative = 0;
     330               0 :       if (strncmp (p, "$HOME/", 6) == 0)
     331                 :         {
     332               0 :           p += 6;
     333               0 :           relative = 1;
     334                 :         }
     335               0 :       else if (*p != '/')
     336               0 :         continue;
     337                 : 
     338               0 :       if (relative)
     339                 :         {
     340               0 :           user_dir = (char*) malloc (strlen (home_dir) + 1 + strlen (p) + 1);
     341               0 :           if (user_dir == NULL)
     342               0 :             goto error2;
     343                 : 
     344               0 :           strcpy (user_dir, home_dir);
     345               0 :           strcat (user_dir, "/");
     346                 :         }
     347                 :       else
     348                 :         {
     349               0 :           user_dir = (char*) malloc (strlen (p) + 1);
     350               0 :           if (user_dir == NULL)
     351               0 :             goto error2;
     352                 : 
     353               0 :           *user_dir = 0;
     354                 :         }
     355                 : 
     356               0 :       d = user_dir + strlen (user_dir);
     357               0 :       while (*p && *p != '"')
     358                 :         {
     359               0 :           if ((*p == '\\') && (*(p+1) != 0))
     360               0 :             p++;
     361               0 :           *d++ = *p++;
     362                 :         }
     363               0 :       *d = 0;
     364                 :     }
     365                 : error2:
     366               0 :   fclose (file);
     367                 : 
     368               0 :   if (user_dir)
     369               0 :     return user_dir;
     370                 : 
     371                 :  error:
     372               9 :   return NULL;
     373                 : }
     374                 : 
     375                 : static const char xdg_user_dirs[] =
     376                 :     "DESKTOP\0"
     377                 :     "DOCUMENTS\0"
     378                 :     "DOWNLOAD\0"
     379                 :     "MUSIC\0"
     380                 :     "PICTURES\0"
     381                 :     "PUBLICSHARE\0"
     382                 :     "TEMPLATES\0"
     383                 :     "VIDEOS";
     384                 : 
     385                 : static const PRUint8 xdg_user_dir_offsets[] = {
     386                 :     0,
     387                 :     8,
     388                 :     18,
     389                 :     27,
     390                 :     33,
     391                 :     42,
     392                 :     54,
     393                 :     64
     394                 : };
     395                 : 
     396                 : static nsresult
     397               9 : GetUnixXDGUserDirectory(SystemDirectories aSystemDirectory,
     398                 :                         nsILocalFile** aFile)
     399                 : {
     400                 :     char *dir = xdg_user_dir_lookup
     401                 :                     (xdg_user_dirs + xdg_user_dir_offsets[aSystemDirectory -
     402               9 :                                                          Unix_XDG_Desktop]);
     403                 : 
     404                 :     nsresult rv;
     405              18 :     nsCOMPtr<nsILocalFile> file;
     406               9 :     if (dir) {
     407               0 :         rv = NS_NewNativeLocalFile(nsDependentCString(dir), true,
     408               0 :                                    getter_AddRefs(file));
     409               0 :         free(dir);
     410               9 :     } else if (Unix_XDG_Desktop == aSystemDirectory) {
     411                 :         // for the XDG desktop dir, fall back to HOME/Desktop
     412                 :         // (for historical compatibility)
     413               0 :         rv = GetUnixHomeDir(getter_AddRefs(file));
     414               0 :         if (NS_FAILED(rv))
     415               0 :             return rv;
     416                 : 
     417               0 :         rv = file->AppendNative(NS_LITERAL_CSTRING("Desktop"));
     418                 :     }
     419                 : #if defined(MOZ_PLATFORM_MAEMO)
     420                 :     // "MYDOCSDIR" is exported to point to "/home/user/MyDocs" in maemo.
     421                 :     else if (Unix_XDG_Documents == aSystemDirectory) {
     422                 : 
     423                 :         char *myDocs = PR_GetEnv("MYDOCSDIR");
     424                 :         if (!myDocs || !*myDocs)
     425                 :             return NS_ERROR_FAILURE;
     426                 : 
     427                 :         rv = NS_NewNativeLocalFile(nsDependentCString(myDocs), true,
     428                 :                                    getter_AddRefs(file));
     429                 :         if (NS_FAILED(rv))
     430                 :             return rv;
     431                 : 
     432                 :         rv = file->AppendNative(NS_LITERAL_CSTRING(".documents"));
     433                 :     }
     434                 : #endif
     435                 :     else {
     436                 :       // no fallback for the other XDG dirs
     437               9 :       rv = NS_ERROR_FAILURE;
     438                 :     }
     439                 : 
     440               9 :     if (NS_FAILED(rv))
     441               9 :         return rv;
     442                 : 
     443                 :     bool exists;
     444               0 :     rv = file->Exists(&exists);
     445               0 :     if (NS_FAILED(rv))
     446               0 :         return rv;
     447               0 :     if (!exists) {
     448               0 :         rv = file->Create(nsIFile::DIRECTORY_TYPE, 0755);
     449               0 :         if (NS_FAILED(rv))
     450               0 :             return rv;
     451                 :     }
     452                 : 
     453               0 :     *aFile = nsnull;
     454               0 :     file.swap(*aFile);
     455                 : 
     456               0 :     return NS_OK;
     457                 : }
     458                 : #endif
     459                 : 
     460                 : nsresult
     461            1492 : GetSpecialSystemDirectory(SystemDirectories aSystemSystemDirectory,
     462                 :                           nsILocalFile** aFile)
     463                 : {
     464                 : #if defined(XP_WIN)
     465                 :     WCHAR path[MAX_PATH];
     466                 : #else
     467                 :     char path[MAXPATHLEN];
     468                 : #endif
     469                 : 
     470            1492 :     switch (aSystemSystemDirectory)
     471                 :     {
     472                 :         case OS_CurrentWorkingDirectory:
     473                 : #if defined(XP_WIN)
     474                 :             if (!_wgetcwd(path, MAX_PATH))
     475                 :                 return NS_ERROR_FAILURE;
     476                 :             return NS_NewLocalFile(nsDependentString(path),
     477                 :                                    true,
     478                 :                                    aFile);
     479                 : #elif defined(XP_OS2)
     480                 :             if (DosQueryPathInfo( ".", FIL_QUERYFULLNAME, path, MAXPATHLEN))
     481                 :                 return NS_ERROR_FAILURE;
     482                 : #else
     483            1386 :             if(!getcwd(path, MAXPATHLEN))
     484               0 :                 return NS_ERROR_FAILURE;
     485                 : #endif
     486                 : 
     487                 : #if !defined(XP_WIN)
     488            1386 :             return NS_NewNativeLocalFile(nsDependentCString(path),
     489                 :                                          true,
     490            1386 :                                          aFile);
     491                 : #endif
     492                 : 
     493                 :         case OS_DriveDirectory:
     494                 : #if defined (XP_WIN)
     495                 :         {
     496                 :             PRInt32 len = ::GetWindowsDirectoryW(path, MAX_PATH);
     497                 :             if (len == 0)
     498                 :                 break;
     499                 :             if (path[1] == PRUnichar(':') && path[2] == PRUnichar('\\'))
     500                 :                 path[3] = 0;
     501                 : 
     502                 :             return NS_NewLocalFile(nsDependentString(path),
     503                 :                                    true,
     504                 :                                    aFile);
     505                 :         }
     506                 : #elif defined(XP_OS2)
     507                 :         {
     508                 :             ULONG ulBootDrive = 0;
     509                 :             char  buffer[] = " :\\OS2\\";
     510                 :             DosQuerySysInfo( QSV_BOOT_DRIVE, QSV_BOOT_DRIVE,
     511                 :                              &ulBootDrive, sizeof ulBootDrive);
     512                 :             buffer[0] = 'A' - 1 + ulBootDrive; // duh, 1-based index...
     513                 : 
     514                 :             return NS_NewNativeLocalFile(nsDependentCString(buffer),
     515                 :                                          true,
     516                 :                                          aFile);
     517                 :         }
     518                 : #else
     519               0 :         return NS_NewNativeLocalFile(nsDependentCString("/"),
     520                 :                                      true,
     521               0 :                                      aFile);
     522                 : 
     523                 : #endif
     524                 : 
     525                 :         case OS_TemporaryDirectory:
     526                 : #if defined (XP_WIN)
     527                 :             {
     528                 :             DWORD len = ::GetTempPathW(MAX_PATH, path);
     529                 :             if (len == 0)
     530                 :                 break;
     531                 :             return NS_NewLocalFile(nsDependentString(path, len),
     532                 :                                    true,
     533                 :                                    aFile);
     534                 :         }
     535                 : #elif defined(XP_OS2)
     536                 :         {
     537                 :             char *tPath = PR_GetEnv("TMP");
     538                 :             if (!tPath || !*tPath) {
     539                 :                 tPath = PR_GetEnv("TEMP");
     540                 :                 if (!tPath || !*tPath) {
     541                 :                     // if an OS/2 system has neither TMP nor TEMP defined
     542                 :                     // then it is severely broken, so this will never happen.
     543                 :                     return NS_ERROR_UNEXPECTED;
     544                 :                 }
     545                 :             }
     546                 :             nsCString tString = nsDependentCString(tPath);
     547                 :             if (tString.Find("/", false, 0, -1)) {
     548                 :                 tString.ReplaceChar('/','\\');
     549                 :             }
     550                 :             return NS_NewNativeLocalFile(tString, true, aFile);
     551                 :         }
     552                 : #elif defined(MOZ_WIDGET_COCOA)
     553                 :         {
     554                 :             return GetOSXFolderType(kUserDomain, kTemporaryFolderType, aFile);
     555                 :         }
     556                 : 
     557                 : #elif defined(XP_UNIX)
     558                 :         {
     559                 :             static const char *tPath = nsnull;
     560              66 :             if (!tPath) {
     561              66 :                 tPath = PR_GetEnv("TMPDIR");
     562              66 :                 if (!tPath || !*tPath) {
     563              66 :                     tPath = PR_GetEnv("TMP");
     564              66 :                     if (!tPath || !*tPath) {
     565              66 :                         tPath = PR_GetEnv("TEMP");
     566              66 :                         if (!tPath || !*tPath) {
     567              66 :                             tPath = "/tmp/";
     568                 :                         }
     569                 :                     }
     570                 :                 }
     571                 :             }
     572              66 :             return NS_NewNativeLocalFile(nsDependentCString(tPath),
     573                 :                                          true,
     574              66 :                                          aFile);
     575                 :         }
     576                 : #else
     577                 :         break;
     578                 : #endif
     579                 : #if defined (XP_WIN)
     580                 :         case Win_SystemDirectory:
     581                 :         {
     582                 :             PRInt32 len = ::GetSystemDirectoryW(path, MAX_PATH);
     583                 : 
     584                 :             // Need enough space to add the trailing backslash
     585                 :             if (!len || len > MAX_PATH - 2)
     586                 :                 break;
     587                 :             path[len]   = L'\\';
     588                 :             path[++len] = L'\0';
     589                 : 
     590                 :             return NS_NewLocalFile(nsDependentString(path, len),
     591                 :                                    true,
     592                 :                                    aFile);
     593                 :         }
     594                 : 
     595                 :         case Win_WindowsDirectory:
     596                 :         {
     597                 :             PRInt32 len = ::GetWindowsDirectoryW(path, MAX_PATH);
     598                 : 
     599                 :             // Need enough space to add the trailing backslash
     600                 :             if (!len || len > MAX_PATH - 2)
     601                 :                 break;
     602                 : 
     603                 :             path[len]   = L'\\';
     604                 :             path[++len] = L'\0';
     605                 : 
     606                 :             return NS_NewLocalFile(nsDependentString(path, len),
     607                 :                                    true,
     608                 :                                    aFile);
     609                 :         }
     610                 : 
     611                 :         case Win_ProgramFiles:
     612                 :         {
     613                 :             return GetWindowsFolder(CSIDL_PROGRAM_FILES, aFile);
     614                 :         }
     615                 : 
     616                 :         case Win_HomeDirectory:
     617                 :         {
     618                 :             nsresult rv = GetWindowsFolder(CSIDL_PROFILE, aFile);
     619                 :             if (NS_SUCCEEDED(rv))
     620                 :                 return rv;
     621                 : 
     622                 :             PRInt32 len;
     623                 :             if ((len = ::GetEnvironmentVariableW(L"HOME", path, MAX_PATH)) > 0)
     624                 :             {
     625                 :                 // Need enough space to add the trailing backslash
     626                 :                 if (len > MAX_PATH - 2)
     627                 :                     break;
     628                 : 
     629                 :                 path[len]   = L'\\';
     630                 :                 path[++len] = L'\0';
     631                 : 
     632                 :                 rv = NS_NewLocalFile(nsDependentString(path, len),
     633                 :                                      true,
     634                 :                                      aFile);
     635                 :                 if (NS_SUCCEEDED(rv))
     636                 :                     return rv;
     637                 :             }
     638                 : 
     639                 :             len = ::GetEnvironmentVariableW(L"HOMEDRIVE", path, MAX_PATH);
     640                 :             if (0 < len && len < MAX_PATH)
     641                 :             {
     642                 :                 WCHAR temp[MAX_PATH];
     643                 :                 DWORD len2 = ::GetEnvironmentVariableW(L"HOMEPATH", temp, MAX_PATH);
     644                 :                 if (0 < len2 && len + len2 < MAX_PATH)
     645                 :                     wcsncat(path, temp, len2);
     646                 : 
     647                 :                 len = wcslen(path);
     648                 : 
     649                 :                 // Need enough space to add the trailing backslash
     650                 :                 if (len > MAX_PATH - 2)
     651                 :                     break;
     652                 : 
     653                 :                 path[len]   = L'\\';
     654                 :                 path[++len] = L'\0';
     655                 : 
     656                 :                 return NS_NewLocalFile(nsDependentString(path, len),
     657                 :                                        true,
     658                 :                                        aFile);
     659                 :             }
     660                 :         }
     661                 :         case Win_Desktop:
     662                 :         {
     663                 :             return GetWindowsFolder(CSIDL_DESKTOP, aFile);
     664                 :         }
     665                 :         case Win_Programs:
     666                 :         {
     667                 :             return GetWindowsFolder(CSIDL_PROGRAMS, aFile);
     668                 :         }
     669                 : 
     670                 :         case Win_Downloads:
     671                 :         {
     672                 :             // Defined in KnownFolders.h.
     673                 :             GUID folderid_downloads = {0x374de290, 0x123f, 0x4565, {0x91, 0x64,
     674                 :                                        0x39, 0xc4, 0x92, 0x5e, 0x46, 0x7b}};
     675                 :             nsresult rv = GetKnownFolder(&folderid_downloads, aFile);
     676                 :             // On WinXP, there is no downloads folder, default
     677                 :             // to 'Desktop'.
     678                 :             if(NS_ERROR_FAILURE == rv)
     679                 :             {
     680                 :               rv = GetWindowsFolder(CSIDL_DESKTOP, aFile);
     681                 :             }
     682                 :             return rv;
     683                 :         }
     684                 : 
     685                 :         case Win_Controls:
     686                 :         {
     687                 :             return GetWindowsFolder(CSIDL_CONTROLS, aFile);
     688                 :         }
     689                 :         case Win_Printers:
     690                 :         {
     691                 :             return GetWindowsFolder(CSIDL_PRINTERS, aFile);
     692                 :         }
     693                 :         case Win_Personal:
     694                 :         {
     695                 :             return GetWindowsFolder(CSIDL_PERSONAL, aFile);
     696                 :         }
     697                 :         case Win_Favorites:
     698                 :         {
     699                 :             return GetWindowsFolder(CSIDL_FAVORITES, aFile);
     700                 :         }
     701                 :         case Win_Startup:
     702                 :         {
     703                 :             return GetWindowsFolder(CSIDL_STARTUP, aFile);
     704                 :         }
     705                 :         case Win_Recent:
     706                 :         {
     707                 :             return GetWindowsFolder(CSIDL_RECENT, aFile);
     708                 :         }
     709                 :         case Win_Sendto:
     710                 :         {
     711                 :             return GetWindowsFolder(CSIDL_SENDTO, aFile);
     712                 :         }
     713                 :         case Win_Bitbucket:
     714                 :         {
     715                 :             return GetWindowsFolder(CSIDL_BITBUCKET, aFile);
     716                 :         }
     717                 :         case Win_Startmenu:
     718                 :         {
     719                 :             return GetWindowsFolder(CSIDL_STARTMENU, aFile);
     720                 :         }
     721                 :         case Win_Desktopdirectory:
     722                 :         {
     723                 :             return GetWindowsFolder(CSIDL_DESKTOPDIRECTORY, aFile);
     724                 :         }
     725                 :         case Win_Drives:
     726                 :         {
     727                 :             return GetWindowsFolder(CSIDL_DRIVES, aFile);
     728                 :         }
     729                 :         case Win_Network:
     730                 :         {
     731                 :             return GetWindowsFolder(CSIDL_NETWORK, aFile);
     732                 :         }
     733                 :         case Win_Nethood:
     734                 :         {
     735                 :             return GetWindowsFolder(CSIDL_NETHOOD, aFile);
     736                 :         }
     737                 :         case Win_Fonts:
     738                 :         {
     739                 :             return GetWindowsFolder(CSIDL_FONTS, aFile);
     740                 :         }
     741                 :         case Win_Templates:
     742                 :         {
     743                 :             return GetWindowsFolder(CSIDL_TEMPLATES, aFile);
     744                 :         }
     745                 :         case Win_Common_Startmenu:
     746                 :         {
     747                 :             return GetWindowsFolder(CSIDL_COMMON_STARTMENU, aFile);
     748                 :         }
     749                 :         case Win_Common_Programs:
     750                 :         {
     751                 :             return GetWindowsFolder(CSIDL_COMMON_PROGRAMS, aFile);
     752                 :         }
     753                 :         case Win_Common_Startup:
     754                 :         {
     755                 :             return GetWindowsFolder(CSIDL_COMMON_STARTUP, aFile);
     756                 :         }
     757                 :         case Win_Common_Desktopdirectory:
     758                 :         {
     759                 :             return GetWindowsFolder(CSIDL_COMMON_DESKTOPDIRECTORY, aFile);
     760                 :         }
     761                 :         case Win_Common_AppData:
     762                 :         {
     763                 :             return GetWindowsFolder(CSIDL_COMMON_APPDATA, aFile);
     764                 :         }
     765                 :         case Win_Printhood:
     766                 :         {
     767                 :             return GetWindowsFolder(CSIDL_PRINTHOOD, aFile);
     768                 :         }
     769                 :         case Win_Cookies:
     770                 :         {
     771                 :             return GetWindowsFolder(CSIDL_COOKIES, aFile);
     772                 :         }
     773                 :         case Win_Appdata:
     774                 :         {
     775                 :             nsresult rv = GetWindowsFolder(CSIDL_APPDATA, aFile);
     776                 :             if (NS_FAILED(rv))
     777                 :                 rv = GetRegWindowsAppDataFolder(false, aFile);
     778                 :             return rv;
     779                 :         }
     780                 :         case Win_LocalAppdata:
     781                 :         {
     782                 :             nsresult rv = GetWindowsFolder(CSIDL_LOCAL_APPDATA, aFile);
     783                 :             if (NS_FAILED(rv))
     784                 :                 rv = GetRegWindowsAppDataFolder(true, aFile);
     785                 :             return rv;
     786                 :         }
     787                 : #endif  // XP_WIN
     788                 : 
     789                 : #if defined(XP_UNIX)
     790                 :         case Unix_LocalDirectory:
     791               0 :             return NS_NewNativeLocalFile(nsDependentCString("/usr/local/netscape/"),
     792                 :                                          true,
     793               0 :                                          aFile);
     794                 :         case Unix_LibDirectory:
     795               0 :             return NS_NewNativeLocalFile(nsDependentCString("/usr/local/lib/netscape/"),
     796                 :                                          true,
     797               0 :                                          aFile);
     798                 : 
     799                 :         case Unix_HomeDirectory:
     800              31 :             return GetUnixHomeDir(aFile);
     801                 : 
     802                 :         case Unix_XDG_Desktop:
     803                 :         case Unix_XDG_Documents:
     804                 :         case Unix_XDG_Download:
     805                 :         case Unix_XDG_Music:
     806                 :         case Unix_XDG_Pictures:
     807                 :         case Unix_XDG_PublicShare:
     808                 :         case Unix_XDG_Templates:
     809                 :         case Unix_XDG_Videos:
     810               9 :             return GetUnixXDGUserDirectory(aSystemSystemDirectory, aFile);
     811                 : #endif
     812                 : 
     813                 : #ifdef XP_OS2
     814                 :         case OS2_SystemDirectory:
     815                 :         {
     816                 :             ULONG ulBootDrive = 0;
     817                 :             char  buffer[] = " :\\OS2\\System\\";
     818                 :             DosQuerySysInfo( QSV_BOOT_DRIVE, QSV_BOOT_DRIVE,
     819                 :                              &ulBootDrive, sizeof ulBootDrive);
     820                 :             buffer[0] = 'A' - 1 + ulBootDrive; // duh, 1-based index...
     821                 : 
     822                 :             return NS_NewNativeLocalFile(nsDependentCString(buffer),
     823                 :                                          true,
     824                 :                                          aFile);
     825                 :         }
     826                 : 
     827                 :      case OS2_OS2Directory:
     828                 :         {
     829                 :             ULONG ulBootDrive = 0;
     830                 :             char  buffer[] = " :\\OS2\\";
     831                 :             DosQuerySysInfo( QSV_BOOT_DRIVE, QSV_BOOT_DRIVE,
     832                 :                              &ulBootDrive, sizeof ulBootDrive);
     833                 :             buffer[0] = 'A' - 1 + ulBootDrive; // duh, 1-based index...
     834                 : 
     835                 :             return NS_NewNativeLocalFile(nsDependentCString(buffer),
     836                 :                                          true,
     837                 :                                          aFile);
     838                 :         }
     839                 : 
     840                 :      case OS2_HomeDirectory:
     841                 :         {
     842                 :             nsresult rv;
     843                 :             char *tPath = PR_GetEnv("MOZILLA_HOME");
     844                 :             char buffer[CCHMAXPATH];
     845                 :             /* If MOZILLA_HOME is not set, use GetCurrentProcessDirectory */
     846                 :             /* To ensure we get a long filename system */
     847                 :             if (!tPath || !*tPath) {
     848                 :                 PPIB ppib;
     849                 :                 PTIB ptib;
     850                 :                 DosGetInfoBlocks( &ptib, &ppib);
     851                 :                 DosQueryModuleName( ppib->pib_hmte, CCHMAXPATH, buffer);
     852                 :                 *strrchr( buffer, '\\') = '\0'; // XXX DBCS misery
     853                 :                 tPath = buffer;
     854                 :             }
     855                 :             rv = NS_NewNativeLocalFile(nsDependentCString(tPath),
     856                 :                                        true,
     857                 :                                        aFile);
     858                 : 
     859                 :             PrfWriteProfileString(HINI_USERPROFILE, "Mozilla", "Home", tPath);
     860                 :             return rv;
     861                 :         }
     862                 : 
     863                 :         case OS2_DesktopDirectory:
     864                 :         {
     865                 :             char szPath[CCHMAXPATH + 1];
     866                 :             BOOL fSuccess;
     867                 :             fSuccess = WinQueryActiveDesktopPathname (szPath, sizeof(szPath));
     868                 :             if (!fSuccess) {
     869                 :                 // this could happen if we are running without the WPS, return
     870                 :                 // the Home directory instead
     871                 :                 return GetSpecialSystemDirectory(OS2_HomeDirectory, aFile);
     872                 :             }
     873                 :             int len = strlen (szPath);
     874                 :             if (len > CCHMAXPATH -1)
     875                 :                 break;
     876                 :             szPath[len] = '\\';
     877                 :             szPath[len + 1] = '\0';
     878                 : 
     879                 :             return NS_NewNativeLocalFile(nsDependentCString(szPath),
     880                 :                                          true,
     881                 :                                          aFile);
     882                 :         }
     883                 : #endif
     884                 :         default:
     885                 :             break;
     886                 :     }
     887               0 :     return NS_ERROR_NOT_AVAILABLE;
     888                 : }
     889                 : 
     890                 : #if defined (MOZ_WIDGET_COCOA)
     891                 : nsresult
     892                 : GetOSXFolderType(short aDomain, OSType aFolderType, nsILocalFile **localFile)
     893                 : {
     894                 :     OSErr err;
     895                 :     FSRef fsRef;
     896                 :     nsresult rv = NS_ERROR_FAILURE;
     897                 : 
     898                 :     err = ::FSFindFolder(aDomain, aFolderType, kCreateFolder, &fsRef);
     899                 :     if (err == noErr)
     900                 :     {
     901                 :         NS_NewLocalFile(EmptyString(), true, localFile);
     902                 :         nsCOMPtr<nsILocalFileMac> localMacFile(do_QueryInterface(*localFile));
     903                 :         if (localMacFile)
     904                 :             rv = localMacFile->InitWithFSRef(&fsRef);
     905                 :     }
     906                 :     return rv;
     907                 : }
     908                 : #endif
     909                 : 

Generated by: LCOV version 1.7