Back to index

lightning-sunbird  0.9+nobinonly
nsInstallFileOpItem.cpp
Go to the documentation of this file.
00001 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
00002 /* ***** BEGIN LICENSE BLOCK *****
00003  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
00004  *
00005  * The contents of this file are subject to the Mozilla Public License Version
00006  * 1.1 (the "License"); you may not use this file except in compliance with
00007  * the License. You may obtain a copy of the License at
00008  * http://www.mozilla.org/MPL/
00009  *
00010  * Software distributed under the License is distributed on an "AS IS" basis,
00011  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
00012  * for the specific language governing rights and limitations under the
00013  * License.
00014  *
00015  * The Original Code is mozilla.org code.
00016  *
00017  * The Initial Developer of the Original Code is
00018  * Netscape Communications Corporation.
00019  * Portions created by the Initial Developer are Copyright (C) 1998
00020  * the Initial Developer. All Rights Reserved.
00021  *
00022  * Contributor(s):
00023  *
00024  * Alternatively, the contents of this file may be used under the terms of
00025  * either of the GNU General Public License Version 2 or later (the "GPL"),
00026  * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
00027  * in which case the provisions of the GPL or the LGPL are applicable instead
00028  * of those above. If you wish to allow use of your version of this file only
00029  * under the terms of either the GPL or the LGPL, and not to allow others to
00030  * use your version of this file under the terms of the MPL, indicate your
00031  * decision by deleting the provisions above and replace them with the notice
00032  * and other provisions required by the GPL or the LGPL. If you do not delete
00033  * the provisions above, a recipient may use your version of this file under
00034  * the terms of any one of the MPL, the GPL or the LGPL.
00035  *
00036  * ***** END LICENSE BLOCK ***** */
00037 
00038 #include "nspr.h"
00039 #include "nsInstall.h"
00040 #include "nsInstallFileOpEnums.h"
00041 #include "nsInstallFileOpItem.h"
00042 #include "ScheduledTasks.h"
00043 #include "nsProcess.h"
00044 #include "nsNativeCharsetUtils.h"
00045 #include "nsReadableUtils.h"
00046 #include "nsInstallExecute.h"
00047 
00048 #ifdef _WINDOWS
00049 #include <windows.h>
00050 #include "nsWinShortcut.h"
00051 #endif
00052 
00053 #if defined(XP_MAC) || defined(XP_MACOSX)
00054 #include <Aliases.h>
00055 #include <Gestalt.h>
00056 #include <Resources.h>
00057 #include <TextUtils.h>
00058 #include "MoreFilesX.h"
00059 #include "nsILocalFileMac.h"
00060 #endif
00061 
00062 static NS_DEFINE_CID(kIProcessCID, NS_PROCESS_CID); 
00063 
00064 /* Public Methods */
00065 
00066 MOZ_DECL_CTOR_COUNTER(nsInstallFileOpItem)
00067 
00068 nsInstallFileOpItem::nsInstallFileOpItem(nsInstall*     aInstallObj,
00069                                          PRInt32        aCommand,
00070                                          nsIFile*       aTarget,
00071                                          PRInt32        aFlags,
00072                                          PRInt32*       aReturn)
00073 :nsInstallObject(aInstallObj),
00074  mTarget(aTarget)
00075 {
00076     MOZ_COUNT_CTOR(nsInstallFileOpItem);
00077 
00078     *aReturn      = nsInstall::SUCCESS;
00079     mIObj         = aInstallObj;
00080     mCommand      = aCommand;
00081     mFlags        = aFlags;
00082     mSrc          = nsnull;
00083     mStrTarget    = nsnull;
00084     mShortcutPath = nsnull;
00085     mWorkingPath  = nsnull;
00086     mIcon         = nsnull;
00087 }
00088 
00089 nsInstallFileOpItem::nsInstallFileOpItem(nsInstall*     aInstallObj,
00090                                          PRInt32        aCommand,
00091                                          nsIFile*       aSrc,
00092                                          nsIFile*       aTarget,
00093                                          PRInt32*       aReturn)
00094 :nsInstallObject(aInstallObj),
00095  mSrc(aSrc),
00096  mTarget(aTarget)
00097 {
00098   MOZ_COUNT_CTOR(nsInstallFileOpItem);
00099 
00100   *aReturn    = nsInstall::SUCCESS;
00101   mIObj       = aInstallObj;
00102   mCommand    = aCommand;
00103   mFlags      = 0;
00104   mStrTarget  = nsnull;
00105   mAction     = ACTION_NONE;
00106   mShortcutPath = nsnull;
00107   mWorkingPath  = nsnull;
00108   mIcon         = nsnull;
00109 }
00110 
00111 nsInstallFileOpItem::nsInstallFileOpItem(nsInstall*     aInstallObj,
00112                                          PRInt32        aCommand,
00113                                          nsIFile*       aTarget,
00114                                          PRInt32*       aReturn)
00115 :nsInstallObject(aInstallObj),
00116  mTarget(aTarget)
00117 {
00118   MOZ_COUNT_CTOR(nsInstallFileOpItem);
00119 
00120   *aReturn    = nsInstall::SUCCESS;
00121   mIObj       = aInstallObj;
00122        mCommand    = aCommand;
00123        mFlags      = 0;
00124        mSrc        = nsnull;
00125        mStrTarget  = nsnull;
00126   mAction     = ACTION_NONE;
00127   mShortcutPath = nsnull;
00128   mWorkingPath  = nsnull;
00129   mIcon         = nsnull;
00130 }
00131 
00132 nsInstallFileOpItem::nsInstallFileOpItem(nsInstall*     aInstallObj,
00133                                          PRInt32        aCommand,
00134                                          nsIFile*       a1,
00135                                          nsString&      a2,
00136                                          PRBool         aBlocking,
00137                                          PRInt32*       aReturn)
00138 :nsInstallObject(aInstallObj)
00139 {
00140     MOZ_COUNT_CTOR(nsInstallFileOpItem);
00141 
00142     *aReturn      = nsInstall::SUCCESS;
00143     mIObj         = aInstallObj;
00144     mCommand      = aCommand;
00145     mFlags        = 0;
00146     mAction       = ACTION_NONE;
00147     mShortcutPath = nsnull;
00148     mWorkingPath  = nsnull;
00149     mIcon         = nsnull;
00150 
00151     switch(mCommand)
00152     {
00153         case NS_FOP_DIR_RENAME:
00154         case NS_FOP_FILE_RENAME:
00155             mSrc = a1;
00156             mTarget     = nsnull;
00157             mStrTarget  = new nsString(a2);
00158 
00159             if (mSrc == nsnull || mStrTarget == nsnull)
00160                 *aReturn = nsInstall::OUT_OF_MEMORY;
00161 
00162             break;
00163 
00164         case NS_FOP_FILE_EXECUTE:
00165             mBlocking = aBlocking;
00166         default:
00167             mSrc        = nsnull;
00168             mTarget     = a1;
00169             mParams     = a2;
00170             mStrTarget  = nsnull;
00171 
00172     }
00173 }
00174 
00175 nsInstallFileOpItem::nsInstallFileOpItem(nsInstall*     aInstallObj,
00176                                          PRInt32        aCommand,
00177                                          nsIFile*       aTarget,
00178                                          nsIFile*       aShortcutPath,
00179                                          nsString&      aDescription,
00180                                          nsIFile*       aWorkingPath,
00181                                          nsString&      aParams,
00182                                          nsIFile*       aIcon,
00183                                          PRInt32        aIconId,
00184                                          PRInt32*       aReturn)
00185 :nsInstallObject(aInstallObj),
00186  mTarget(aTarget),
00187  mShortcutPath(aShortcutPath),
00188  mWorkingPath(aWorkingPath),
00189  mIcon(aIcon),
00190  mDescription(aDescription),
00191  mParams(aParams)
00192 {
00193     MOZ_COUNT_CTOR(nsInstallFileOpItem);
00194 
00195   *aReturn    = nsInstall::SUCCESS;
00196   mIObj       = aInstallObj;
00197   mCommand    = aCommand;
00198   mIconId     = aIconId;
00199   mFlags      = 0;
00200   mSrc        = nsnull;
00201   mStrTarget  = nsnull;
00202   mAction     = ACTION_NONE;
00203 }
00204 
00205 nsInstallFileOpItem::~nsInstallFileOpItem()
00206 {
00207   //if(mSrc)
00208   //  delete mSrc;
00209   //if(mTarget)
00210   //  delete mTarget;
00211   if(mStrTarget)
00212     delete mStrTarget;
00213   //if(mParams)
00214   //  delete mParams;
00215   //if(mShortcutPath)
00216   //  delete mShortcutPath;
00217   //if(mDescription)
00218   //  delete mDescription;
00219   //if(mWorkingPath)
00220   //  delete mWorkingPath;
00221   //if(mIcon)
00222   //  delete mIcon;
00223 
00224   MOZ_COUNT_DTOR(nsInstallFileOpItem);
00225 }
00226 
00227 #ifdef XP_MAC
00228 #pragma mark -
00229 #endif
00230 
00231 PRInt32 nsInstallFileOpItem::Complete()
00232 {
00233   PRInt32 ret = nsInstall::SUCCESS;
00234 
00235   switch(mCommand)
00236   {
00237     case NS_FOP_FILE_COPY:
00238       ret = NativeFileOpFileCopyComplete();
00239       break;
00240     case NS_FOP_FILE_DELETE:
00241       ret = NativeFileOpFileDeleteComplete(mTarget);
00242       break;
00243     case NS_FOP_FILE_EXECUTE:
00244       ret = NativeFileOpFileExecuteComplete();
00245       break;
00246     case NS_FOP_FILE_MOVE:
00247       ret = NativeFileOpFileMoveComplete();
00248       break;
00249     case NS_FOP_FILE_RENAME:
00250       ret = NativeFileOpFileRenameComplete();
00251       break;
00252     case NS_FOP_DIR_CREATE:
00253       // operation is done in the prepare phase
00254       break;
00255     case NS_FOP_DIR_REMOVE:
00256       ret = NativeFileOpDirRemoveComplete();
00257       break;
00258     case NS_FOP_DIR_RENAME:
00259       ret = NativeFileOpDirRenameComplete();
00260       break;
00261     case NS_FOP_WIN_SHORTCUT:
00262       ret = NativeFileOpWindowsShortcutComplete();
00263       break;
00264     case NS_FOP_MAC_ALIAS:
00265       ret = NativeFileOpMacAliasComplete();
00266       break;
00267     case NS_FOP_UNIX_LINK:
00268       ret = NativeFileOpUnixLink();
00269       break;
00270     case NS_FOP_WIN_REGISTER_SERVER:
00271       ret = NativeFileOpWindowsRegisterServerComplete();
00272       break;
00273   }
00274 
00275   if ( (ret != nsInstall::SUCCESS) && (ret < nsInstall::GESTALT_INVALID_ARGUMENT || ret > nsInstall::REBOOT_NEEDED) )
00276     ret = nsInstall::UNEXPECTED_ERROR; /* translate to XPInstall error */
00277        
00278   return ret;
00279 }
00280   
00281 #define RESBUFSIZE 4096
00282 char* nsInstallFileOpItem::toString()
00283 {
00284   nsString result;
00285   char*    resultCString = new char[RESBUFSIZE];
00286   char*    rsrcVal = nsnull;
00287   nsCAutoString temp;
00288   nsCAutoString srcPath;
00289   nsCAutoString dstPath;
00290 
00291     // STRING USE WARNING: perhaps |result| should be an |nsCAutoString| to avoid all this double converting
00292   *resultCString = nsnull;
00293   switch(mCommand)
00294   {
00295     case NS_FOP_FILE_COPY:
00296       if((mSrc == nsnull) || (mTarget == nsnull))
00297         break;
00298 
00299       mSrc->GetNativePath(srcPath);
00300       mTarget->GetNativePath(dstPath);
00301       rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("CopyFile"));
00302       if(rsrcVal != nsnull)
00303         PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, srcPath.get(), dstPath.get() );
00304       break;
00305 
00306     case NS_FOP_FILE_DELETE:
00307       if(mTarget == nsnull)
00308         break;
00309 
00310       mTarget->GetNativePath(dstPath);
00311       rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("DeleteFile"));
00312       if(rsrcVal != nsnull)
00313         PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, dstPath.get() );
00314       break;
00315 
00316     case NS_FOP_FILE_EXECUTE:
00317       if(mTarget == nsnull)
00318         break;
00319 
00320       mTarget->GetNativePath(dstPath);
00321 
00322       NS_CopyUnicodeToNative(mParams, temp);
00323       if(!temp.IsEmpty())
00324       {
00325         rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("ExecuteWithArgs"));
00326         if(rsrcVal != nsnull)
00327           PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, dstPath.get(), temp.get());
00328       }
00329       else
00330       {
00331         rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("Execute"));
00332         if(rsrcVal != nsnull)
00333           PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, dstPath.get());
00334       }
00335       break;
00336 
00337     case NS_FOP_FILE_MOVE:
00338       if((mSrc == nsnull) || (mTarget == nsnull))
00339         break;
00340 
00341       mSrc->GetNativePath(srcPath);
00342       mTarget->GetNativePath(dstPath);
00343       rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("MoveFile"));
00344       if(rsrcVal != nsnull)
00345         PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, srcPath.get(), dstPath.get());
00346       break;
00347 
00348     case NS_FOP_FILE_RENAME:
00349       if((mSrc == nsnull) || (mTarget == nsnull))
00350         break;
00351 
00352       mSrc->GetNativePath(srcPath);
00353       mTarget->GetNativePath(dstPath);
00354       rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("RenameFile"));
00355       if(rsrcVal != nsnull)
00356         PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, srcPath.get(), dstPath.get());
00357       break;
00358 
00359     case NS_FOP_DIR_CREATE:
00360       if(mTarget == nsnull)
00361         break;
00362 
00363       mTarget->GetNativePath(dstPath);
00364       rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("CreateFolder"));
00365       if(rsrcVal != nsnull)
00366         PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, dstPath.get());
00367       break;
00368 
00369     case NS_FOP_DIR_REMOVE:
00370       if(mTarget == nsnull)
00371         break;
00372 
00373       mTarget->GetNativePath(dstPath);
00374       rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("RemoveFolder"));
00375       if(rsrcVal != nsnull)
00376         PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, dstPath.get());
00377       break;
00378 
00379     case NS_FOP_DIR_RENAME:
00380       if((mSrc == nsnull) || (mTarget == nsnull))
00381         break;
00382 
00383       mSrc->GetNativePath(srcPath);
00384       mTarget->GetNativePath(dstPath);
00385       rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("RenameFolder"));
00386       if(rsrcVal != nsnull)
00387         PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, srcPath.get(), dstPath.get());
00388       break;
00389 
00390     case NS_FOP_WIN_SHORTCUT:
00391       rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("WindowsShortcut"));
00392       if(rsrcVal && mShortcutPath)
00393       {
00394         nsCAutoString description;
00395 
00396         NS_CopyUnicodeToNative(mDescription, description);
00397         mShortcutPath->GetNativePath(temp);
00398         temp.Append(NS_LITERAL_CSTRING("\\") + description);
00399         PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, temp.get());
00400       }
00401       break;
00402 
00403     case NS_FOP_MAC_ALIAS:
00404       if(mTarget == nsnull)
00405         break;
00406 
00407       mTarget->GetNativePath(dstPath);
00408       rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("MacAlias"));
00409       if(rsrcVal != nsnull)
00410         PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, dstPath.get());
00411       break;
00412 
00413     case NS_FOP_UNIX_LINK:
00414       break;
00415 
00416     case NS_FOP_WIN_REGISTER_SERVER:
00417       if(mTarget == nsnull)
00418         break;
00419 
00420       mTarget->GetNativePath(dstPath);
00421       rsrcVal = mInstall->GetResourcedString(NS_LITERAL_STRING("WindowsRegisterServer"));
00422       if(rsrcVal != nsnull)
00423         PR_snprintf(resultCString, RESBUFSIZE, rsrcVal, dstPath.get());
00424       break;
00425 
00426     default:
00427       if(rsrcVal != nsnull)
00428         resultCString = mInstall->GetResourcedString(NS_LITERAL_STRING("UnknownFileOpCommand"));
00429       break;
00430   }
00431 
00432   if(rsrcVal)
00433     Recycle(rsrcVal);
00434 
00435   return resultCString;
00436 }
00437 
00438 PRInt32 nsInstallFileOpItem::Prepare()
00439 {
00440   PRInt32 ret = nsInstall::SUCCESS;
00441 
00442   switch(mCommand)
00443   {
00444     case NS_FOP_FILE_COPY:
00445       ret = NativeFileOpFileCopyPrepare();
00446       break;
00447     case NS_FOP_FILE_DELETE:
00448       ret = NativeFileOpFileDeletePrepare();
00449       break;
00450     case NS_FOP_FILE_EXECUTE:
00451       ret = NativeFileOpFileExecutePrepare();
00452       break;
00453     case NS_FOP_FILE_MOVE:
00454       ret = NativeFileOpFileMovePrepare();
00455       break;
00456     case NS_FOP_FILE_RENAME:
00457       ret = NativeFileOpFileRenamePrepare();
00458       break;
00459     case NS_FOP_DIR_CREATE:
00460       ret = NativeFileOpDirCreatePrepare();
00461       break;
00462     case NS_FOP_DIR_REMOVE:
00463       ret = NativeFileOpDirRemovePrepare();
00464       break;
00465     case NS_FOP_DIR_RENAME:
00466       ret = NativeFileOpDirRenamePrepare();
00467       break;
00468     case NS_FOP_WIN_SHORTCUT:
00469       ret = NativeFileOpWindowsShortcutPrepare();
00470       break;
00471     case NS_FOP_MAC_ALIAS:
00472       ret = NativeFileOpMacAliasPrepare();
00473       break;
00474     case NS_FOP_UNIX_LINK:
00475       break;
00476     case NS_FOP_WIN_REGISTER_SERVER:
00477       ret = NativeFileOpWindowsRegisterServerPrepare();
00478       break;
00479     default:
00480       break;
00481   }
00482 
00483   if ( (ret != nsInstall::SUCCESS) && (ret < nsInstall::GESTALT_INVALID_ARGUMENT || ret > nsInstall::REBOOT_NEEDED) )
00484     ret = nsInstall::UNEXPECTED_ERROR; /* translate to XPInstall error */
00485 
00486   return(ret);
00487 }
00488 
00489 void nsInstallFileOpItem::Abort()
00490 {
00491   switch(mCommand)
00492   {
00493     case NS_FOP_FILE_COPY:
00494       NativeFileOpFileCopyAbort();
00495       break;
00496     case NS_FOP_FILE_DELETE:
00497       // does nothing
00498       break;
00499     case NS_FOP_FILE_EXECUTE:
00500       // does nothing
00501       break;
00502     case NS_FOP_FILE_MOVE:
00503       NativeFileOpFileMoveAbort();
00504       break;
00505     case NS_FOP_FILE_RENAME:
00506       NativeFileOpFileRenameAbort();
00507       break;
00508     case NS_FOP_DIR_CREATE:
00509       NativeFileOpDirCreateAbort();
00510       break;
00511     case NS_FOP_DIR_REMOVE:
00512       break;
00513     case NS_FOP_DIR_RENAME:
00514       NativeFileOpDirRenameAbort();
00515       break;
00516     case NS_FOP_WIN_SHORTCUT:
00517       NativeFileOpWindowsShortcutAbort();
00518       break;
00519     case NS_FOP_MAC_ALIAS:
00520       NativeFileOpMacAliasAbort();
00521       break;
00522     case NS_FOP_UNIX_LINK:
00523       break;
00524     case NS_FOP_WIN_REGISTER_SERVER:
00525       NativeFileOpWindowsRegisterServerAbort();
00526       break;
00527   }
00528 }
00529 
00530 /* Private Methods */
00531 
00532 /* CanUninstall
00533 * InstallFileOpItem() does not install any files which can be uninstalled,
00534 * hence this function returns false. 
00535 */
00536 PRBool
00537 nsInstallFileOpItem::CanUninstall()
00538 {
00539     return PR_FALSE;
00540 }
00541 
00542 /* RegisterPackageNode
00543 * InstallFileOpItem() does notinstall files which need to be registered,
00544 * hence this function returns false.
00545 */
00546 PRBool
00547 nsInstallFileOpItem::RegisterPackageNode()
00548 {
00549     return PR_FALSE;
00550 }
00551 
00552 #ifdef XP_MAC
00553 #pragma mark -
00554 #endif
00555 
00556 //
00557 // File operation functions begin here
00558 //
00559 PRInt32
00560 nsInstallFileOpItem::NativeFileOpDirCreatePrepare()
00561 {
00562   PRInt32  ret = nsInstall::UNEXPECTED_ERROR;
00563   PRBool   flagExists;
00564   PRBool   flagIsFile;
00565   nsresult rv;
00566 
00567   mAction = nsInstallFileOpItem::ACTION_FAILED;
00568 
00569   rv = mTarget->Exists(&flagExists);
00570   if (NS_SUCCEEDED(rv))
00571   {
00572     if (!flagExists)
00573     {
00574       rv = mTarget->Create(1, 0755);
00575       if (NS_SUCCEEDED(rv))
00576       {
00577         mAction = nsInstallFileOpItem::ACTION_SUCCESS;
00578         ret = nsInstall::SUCCESS;
00579       }
00580     }
00581     else
00582     {
00583       rv = mTarget->IsFile(&flagIsFile);
00584       if (NS_SUCCEEDED(rv))
00585       {
00586         if (flagIsFile)
00587           ret = nsInstall::IS_FILE;
00588         else
00589         {
00590           mAction = nsInstallFileOpItem::ACTION_SUCCESS;
00591           ret = nsInstall::SUCCESS;
00592         }
00593       }
00594     }
00595   }
00596 
00597   return ret;
00598 }
00599 
00600 PRInt32
00601 nsInstallFileOpItem::NativeFileOpDirCreateAbort()
00602 {
00603   if(nsInstallFileOpItem::ACTION_SUCCESS == mAction)
00604     mTarget->Remove(PR_FALSE);
00605 
00606   return nsInstall::SUCCESS;
00607 }
00608 
00609 PRInt32
00610 nsInstallFileOpItem::NativeFileOpDirRemovePrepare()
00611 {
00612   PRBool flagExists, flagIsFile;
00613 
00614   mTarget->Exists(&flagExists);
00615 
00616   if(flagExists)
00617   {
00618     mTarget->IsFile(&flagIsFile);
00619     if(!flagIsFile)
00620       return nsInstall::SUCCESS;
00621     else
00622       return nsInstall::IS_FILE;
00623   }
00624     
00625   return nsInstall::DOES_NOT_EXIST;
00626 }
00627 
00628 PRInt32
00629 nsInstallFileOpItem::NativeFileOpDirRemoveComplete()
00630 {
00631   mTarget->Remove(mFlags);
00632   return nsInstall::SUCCESS;
00633 }
00634 
00635 PRInt32
00636 nsInstallFileOpItem::NativeFileOpFileRenamePrepare()
00637 {
00638   PRBool flagExists, flagIsFile;
00639 
00640   // XXX needs to check file attributes to make sure
00641   // user has proper permissions to delete file.
00642   // Waiting on dougt's fix to nsFileSpec().
00643   // In the meantime, check as much as possible.
00644   mSrc->Exists(&flagExists);
00645   if(flagExists)
00646   {
00647     mSrc->IsFile(&flagIsFile);
00648     if(flagIsFile)
00649     {
00650       nsIFile* target;
00651 
00652       mSrc->GetParent(&target);
00653       nsresult rv =
00654           target->Append(*mStrTarget);
00655       //90% of the failures during Append will be because the target wasn't in string form
00656       // which it must be.
00657       if (NS_FAILED(rv)) return nsInstall::INVALID_ARGUMENTS;
00658 
00659       target->Exists(&flagExists);
00660       if(flagExists)
00661         return nsInstall::ALREADY_EXISTS;
00662       else
00663         return nsInstall::SUCCESS;
00664     }
00665     else
00666       return nsInstall::SOURCE_IS_DIRECTORY;
00667   }
00668     
00669   return nsInstall::SOURCE_DOES_NOT_EXIST;
00670 }
00671 
00672 PRInt32
00673 nsInstallFileOpItem::NativeFileOpFileRenameComplete()
00674 {
00675   PRInt32 ret = nsInstall::SUCCESS;
00676   PRBool flagExists, flagIsFile;
00677   
00678   mSrc->Exists(&flagExists);
00679   if(flagExists)
00680   {
00681     mSrc->IsFile(&flagIsFile);
00682     if(flagIsFile)
00683     {
00684         nsCOMPtr<nsIFile> parent;
00685         nsCOMPtr<nsIFile> target;
00686 
00687         mSrc->GetParent(getter_AddRefs(parent)); //need parent seprated for use in MoveTo method
00688         if(parent)
00689         {
00690             mSrc->GetParent(getter_AddRefs(target)); //need target for path assembly to check if the file already exists
00691 
00692             if (target)
00693             {
00694                 target->Append(*mStrTarget);
00695             }
00696             else
00697                 return nsInstall::UNEXPECTED_ERROR;
00698 
00699             target->Exists(&flagExists);
00700             if(!flagExists)
00701             {
00702                 mSrc->MoveTo(parent, *mStrTarget);
00703             }
00704             else
00705                 return nsInstall::ALREADY_EXISTS;
00706         }
00707         else
00708             return nsInstall::UNEXPECTED_ERROR;
00709     }
00710     else
00711       ret = nsInstall::SOURCE_IS_DIRECTORY;
00712   }
00713   else  
00714     ret = nsInstall::SOURCE_DOES_NOT_EXIST;
00715 
00716   return ret;
00717 }
00718 
00719 PRInt32
00720 nsInstallFileOpItem::NativeFileOpFileRenameAbort()
00721 {
00722   PRInt32   ret  = nsInstall::SUCCESS;
00723   PRBool    flagExists;
00724   nsAutoString leafName;
00725   nsCOMPtr<nsIFile>  newFilename;
00726   nsCOMPtr<nsIFile>  parent;
00727 
00728   mSrc->Exists(&flagExists);
00729   if(!flagExists)
00730   {
00731     mSrc->GetParent(getter_AddRefs(newFilename));
00732     if(newFilename)
00733     {
00734       mSrc->GetParent(getter_AddRefs(parent));
00735       if(parent)
00736       {
00737         mSrc->GetLeafName(leafName);
00738 
00739         newFilename->Append(*mStrTarget);
00740         newFilename->MoveTo(parent, leafName);
00741       }
00742       else
00743         return nsInstall::UNEXPECTED_ERROR;
00744     }
00745     else
00746       return nsInstall::UNEXPECTED_ERROR;
00747   }
00748 
00749   return ret;
00750 }
00751 
00752 PRInt32
00753 nsInstallFileOpItem::NativeFileOpFileCopyPrepare()
00754 {
00755   PRBool flagExists, flagIsFile, flagIsWritable;
00756   nsAutoString leafName;
00757   nsresult rv;
00758   nsCOMPtr<nsIFile> tempVar;
00759   nsCOMPtr<nsIFile> targetParent;
00760 
00761   // XXX needs to check file attributes to make sure
00762   // user has proper permissions to delete file.
00763   // Waiting on dougt's fix to nsFileSpec().
00764   // In the meantime, check as much as possible.
00765   
00766   mSrc->Exists(&flagExists);
00767   if(flagExists)
00768   {
00769     mSrc->IsFile(&flagIsFile);
00770     if(flagIsFile)
00771     {
00772       mTarget->Exists(&flagExists);
00773       if(!flagExists)
00774       {
00775         //Assume mTarget is a file
00776         //Make sure mTarget's parent exists otherwise, error.
00777         rv = mTarget->GetParent(getter_AddRefs(targetParent));
00778         if(NS_FAILED(rv)) return rv;
00779         rv = targetParent->Exists(&flagExists);
00780         if(NS_FAILED(rv)) return rv;
00781         if(!flagExists)
00782           return nsInstall::DOES_NOT_EXIST;
00783       }
00784       else
00785       {
00786         mTarget->IsFile(&flagIsFile);
00787         if(flagIsFile)
00788         {
00789           mTarget->IsWritable(&flagIsWritable);
00790           if (!flagIsWritable)
00791             return nsInstall::ACCESS_DENIED;
00792         }
00793         else
00794         {
00795           mTarget->Clone(getter_AddRefs(tempVar));
00796           mSrc->GetLeafName(leafName);
00797           tempVar->Append(leafName);
00798           tempVar->Exists(&flagExists);
00799           if(flagExists)
00800           {
00801             tempVar->IsWritable(&flagIsWritable);
00802             if (!flagIsWritable)
00803               return nsInstall::ACCESS_DENIED;
00804           }
00805         }
00806 
00807       }
00808 
00809       return nsInstall::SUCCESS;
00810     }
00811     else
00812       return nsInstall::SOURCE_IS_DIRECTORY;
00813   }
00814     
00815   return nsInstall::SOURCE_DOES_NOT_EXIST;
00816 }
00817 
00818 PRInt32
00819 nsInstallFileOpItem::NativeFileOpFileCopyComplete()
00820 {
00821   PRInt32 rv = NS_OK;
00822   PRBool flagIsFile, flagExists;
00823   nsAutoString leafName;
00824   nsCOMPtr<nsIFile> parent;
00825   nsCOMPtr<nsIFile> tempTarget;
00826 
00827   mAction = nsInstallFileOpItem::ACTION_FAILED;
00828 
00829   mTarget->Exists(&flagExists);
00830   if(flagExists)
00831   {
00832     mTarget->IsFile(&flagIsFile); //Target is file that is already on the system
00833     if (flagIsFile)
00834     {
00835       rv = mTarget->Remove(PR_FALSE);
00836       if (NS_FAILED(rv)) return rv;
00837       rv = mTarget->GetParent(getter_AddRefs(parent));
00838       if (NS_FAILED(rv)) return rv;
00839       rv = mTarget->GetLeafName(leafName);
00840       if (NS_FAILED(rv)) return rv;
00841       rv = mSrc->CopyTo(parent, leafName);
00842     }
00843     else //Target is a directory
00844     {
00845       rv = mSrc->GetLeafName(leafName);
00846       if (NS_FAILED(rv)) return rv;
00847       rv = mTarget->Clone(getter_AddRefs(tempTarget));
00848       if (NS_FAILED(rv)) return rv;
00849       rv = tempTarget->Append(leafName);
00850       if (NS_FAILED(rv)) return rv;
00851       tempTarget->Exists(&flagExists);
00852       if (flagExists)
00853         tempTarget->Remove(PR_FALSE);
00854 
00855       rv = mSrc->CopyTo(mTarget, leafName);
00856     }
00857   }
00858   else //Target is a file but isn't on the system
00859   {
00860     mTarget->GetParent(getter_AddRefs(parent));
00861     if (NS_FAILED(rv)) return rv;
00862     mTarget->GetLeafName(leafName);
00863     if (NS_FAILED(rv)) return rv;
00864     rv = mSrc->CopyTo(parent, leafName);
00865   }
00866 
00867   if(nsInstall::SUCCESS == rv)
00868     mAction = nsInstallFileOpItem::ACTION_SUCCESS;
00869 
00870   return rv;
00871 }
00872 
00873 PRInt32
00874 nsInstallFileOpItem::NativeFileOpFileCopyAbort()
00875 {
00876   nsCOMPtr<nsIFile> fullTarget;
00877   PRInt32 ret = nsInstall::SUCCESS;
00878 
00879   mTarget->Clone(getter_AddRefs(fullTarget));
00880   if(nsInstallFileOpItem::ACTION_SUCCESS == mAction)
00881   {
00882     nsAutoString leafName;
00883     mSrc->GetLeafName(leafName);
00884     fullTarget->Append(leafName);
00885     fullTarget->Remove(PR_FALSE);
00886   }
00887 
00888   return ret;
00889 }
00890 
00891 PRInt32
00892 nsInstallFileOpItem::NativeFileOpFileDeletePrepare()
00893 {
00894   PRBool flagExists, flagIsFile;
00895 
00896   // XXX needs to check file attributes to make sure
00897   // user has proper permissions to delete file.
00898   // Waiting on dougt's fix to nsFileSpec().
00899   // In the meantime, check as much as possible.
00900   
00901   mTarget->Exists(&flagExists);
00902   if(flagExists)
00903   {
00904     mTarget->IsFile(&flagIsFile);
00905     if(flagIsFile)
00906       return nsInstall::SUCCESS;
00907     else
00908       return nsInstall::IS_DIRECTORY;
00909   }
00910     
00911   return nsInstall::DOES_NOT_EXIST;
00912 }
00913 
00914 PRInt32
00915 nsInstallFileOpItem::NativeFileOpFileDeleteComplete(nsIFile *aTarget)
00916 {
00917   PRBool flagExists, flagIsFile;
00918 
00919   aTarget->Exists(&flagExists);
00920   if(flagExists)
00921   {
00922     aTarget->IsFile(&flagIsFile);
00923     if(flagIsFile)
00924       return DeleteFileNowOrSchedule(aTarget);
00925     else
00926       return nsInstall::IS_DIRECTORY;
00927   }
00928     
00929   // file went away on its own, not a problem
00930   return nsInstall::SUCCESS;
00931 }
00932 
00933 PRInt32
00934 nsInstallFileOpItem::NativeFileOpFileExecutePrepare()
00935 {
00936   PRBool flagExists, flagIsFile;
00937   // XXX needs to check file attributes to make sure
00938   // user has proper permissions to delete file.
00939   // Waiting on dougt's fix to nsFileSpec().
00940   // In the meantime, check as much as possible.
00941   // Also, an absolute path (with filename) must be
00942   // used.  Xpinstall does not assume files are on the path.
00943   mTarget->Exists(&flagExists);
00944   if(flagExists)
00945   {
00946     mTarget->IsFile(&flagIsFile);
00947     if(flagIsFile)
00948       return nsInstall::SUCCESS;
00949     else
00950       return nsInstall::IS_DIRECTORY;
00951   }
00952     
00953   return nsInstall::DOES_NOT_EXIST;
00954 }
00955 
00956 PRInt32
00957 nsInstallFileOpItem::NativeFileOpFileExecuteComplete()
00958 {
00959   #define ARG_SLOTS 256
00960 
00961   char *cParams[ARG_SLOTS];
00962   int   argcount = 0;
00963 
00964   nsresult rv;
00965   PRInt32  result = NS_OK; // assume success
00966 
00967   cParams[0] = nsnull;
00968 
00969   if (mTarget == nsnull)
00970     return nsInstall::INVALID_ARGUMENTS;
00971 
00972   nsCOMPtr<nsIProcess> process = do_CreateInstance(kIProcessCID);
00973   
00974   if (!mParams.IsEmpty())
00975   {
00976     nsCAutoString temp;
00977 
00978     NS_CopyUnicodeToNative(mParams, temp);
00979     argcount = xpi_PrepareProcessArguments(temp.get(), cParams, ARG_SLOTS);
00980   }
00981   if (argcount >= 0)
00982   {
00983     rv = process->Init(mTarget);
00984     if (NS_SUCCEEDED(rv))
00985     {
00986       rv = process->Run(mBlocking, (const char **)&cParams, argcount, nsnull);
00987       if (NS_SUCCEEDED(rv))
00988       {
00989         if (mBlocking)
00990         {
00991           // check the return value for errors
00992           PRInt32 value;
00993           rv = process->GetExitValue(&value);
00994           if (NS_FAILED(rv) || value != 0)
00995             result = nsInstall::EXECUTION_ERROR;
00996         }
00997       }
00998       else
00999         result = nsInstall::EXECUTION_ERROR;
01000     }
01001     else
01002       result = nsInstall::EXECUTION_ERROR;
01003   }
01004   else
01005     result = nsInstall::UNEXPECTED_ERROR;
01006 
01007   return result;
01008 }
01009 
01010 PRInt32
01011 nsInstallFileOpItem::NativeFileOpFileMovePrepare()
01012 {
01013   PRBool flagExists, flagIsFile, flagIsWritable;
01014   nsresult rv = NS_OK;
01015 
01016   mSrc->Exists(&flagExists);
01017   if(flagExists)
01018   {
01019     mTarget->Exists(&flagExists);
01020     if(!flagExists)
01021     {
01022       //Assume mTarget is a file
01023       //Make sure mTarget's parent exists otherwise, error.
01024       nsCOMPtr<nsIFile> targetParent;
01025 
01026       rv = mTarget->GetParent(getter_AddRefs(targetParent));
01027       if(NS_FAILED(rv)) return rv;
01028       rv = targetParent->Exists(&flagExists);
01029       if(NS_FAILED(rv)) return rv;
01030       if(!flagExists)
01031         return nsInstall::DOES_NOT_EXIST;
01032       else
01033         return NativeFileOpFileCopyPrepare();
01034     } 
01035     else
01036     {
01037       mTarget->IsFile(&flagIsFile);
01038       if(flagIsFile)
01039       {
01040         mTarget->IsWritable(&flagIsWritable);
01041         if (!flagIsWritable)
01042           return nsInstall::ACCESS_DENIED;
01043       }
01044       else
01045       {
01046         nsCOMPtr<nsIFile> tempVar;
01047         nsAutoString leaf;
01048 
01049         mTarget->Clone(getter_AddRefs(tempVar));
01050         mSrc->GetLeafName(leaf);
01051         tempVar->Append(leaf);
01052 
01053         tempVar->Exists(&flagExists);
01054         if(flagExists)
01055         {
01056           tempVar->IsWritable(&flagIsWritable);
01057           if (!flagIsWritable)
01058             return nsInstall::ACCESS_DENIED;
01059         }
01060       }
01061       return NativeFileOpFileCopyPrepare();
01062     }
01063   }
01064 
01065   return nsInstall::SOURCE_DOES_NOT_EXIST;
01066 }
01067 
01068 PRInt32
01069 nsInstallFileOpItem::NativeFileOpFileMoveComplete()
01070 {
01071   PRBool flagExists;
01072   PRInt32 ret = nsInstall::SUCCESS;
01073 
01074   mAction = nsInstallFileOpItem::ACTION_FAILED;
01075   mSrc->Exists(&flagExists);
01076   if(flagExists)
01077   {
01078       PRInt32 ret2 = nsInstall::SUCCESS;
01079 
01080       ret = NativeFileOpFileCopyComplete();
01081       if(nsInstall::SUCCESS == ret)
01082       {
01083         mAction = nsInstallFileOpItem::ACTION_SUCCESS;
01084         ret2    = NativeFileOpFileDeleteComplete(mSrc);
01085 
01086         // We don't care if the value of ret2 is other than
01087         // REBOOT_NEEDED.  ret takes precedence otherwise.
01088         if(nsInstall::REBOOT_NEEDED == ret2)
01089           ret = ret2;
01090       }
01091   }
01092   else
01093     ret = nsInstall::SOURCE_DOES_NOT_EXIST;
01094 
01095   return ret;
01096 }
01097 
01098 PRInt32
01099 nsInstallFileOpItem::NativeFileOpFileMoveAbort()
01100 {
01101   PRBool flagExists;
01102   PRInt32 ret = nsInstall::SUCCESS;
01103 
01104   if(nsInstallFileOpItem::ACTION_SUCCESS == mAction)
01105   {
01106     mSrc->Exists(&flagExists);
01107     if(flagExists)
01108       ret = NativeFileOpFileDeleteComplete(mTarget);
01109     else
01110     {
01111       mTarget->Exists(&flagExists);
01112       if(flagExists)
01113       {
01114         nsCOMPtr<nsIFile> tempVar;
01115         PRInt32    ret2 = nsInstall::SUCCESS;
01116 
01117         // switch the values of mSrc and mTarget
01118         // so the original state can be restored.
01119         // NativeFileOpFileCopyComplete() copies from
01120         // mSrc to mTarget by default.
01121         mTarget->Clone(getter_AddRefs(tempVar));
01122         mSrc->Clone(getter_AddRefs(mTarget));
01123         tempVar->Clone(getter_AddRefs(mSrc));
01124 
01125         ret = NativeFileOpFileCopyComplete();
01126         if(nsInstall::SUCCESS == ret)
01127         {
01128           ret2 = NativeFileOpFileDeleteComplete(mSrc);
01129 
01130           // We don't care if the value of ret2 is other than
01131           // REBOOT_NEEDED.  ret takes precedence otherwise.
01132           if(nsInstall::REBOOT_NEEDED == ret2)
01133             ret = ret2;
01134         }
01135       }
01136       else
01137         ret = nsInstall::DOES_NOT_EXIST;
01138     }
01139   }
01140 
01141   return ret;
01142 }
01143 
01144 PRInt32
01145 nsInstallFileOpItem::NativeFileOpDirRenamePrepare()
01146 {
01147   PRBool flagExists, flagIsFile;
01148   // XXX needs to check file attributes to make sure
01149   // user has proper permissions to delete file.
01150   // Waiting on dougt's fix to nsFileSpec().
01151   // In the meantime, check as much as possible.
01152   mSrc->Exists(&flagExists);
01153   if(flagExists)
01154   {
01155     mSrc->IsFile(&flagIsFile);
01156     if(!flagIsFile)
01157     {
01158       nsCOMPtr<nsIFile> target;
01159 
01160       mSrc->GetParent(getter_AddRefs(target));
01161       target->Append(*mStrTarget);
01162 
01163       target->Exists(&flagExists);
01164       if(flagExists)
01165         return nsInstall::ALREADY_EXISTS;
01166       else
01167         return nsInstall::SUCCESS;
01168     }
01169     else
01170       return nsInstall::IS_FILE;
01171   }
01172     
01173   return nsInstall::SOURCE_DOES_NOT_EXIST;
01174 }
01175 
01176 PRInt32
01177 nsInstallFileOpItem::NativeFileOpDirRenameComplete()
01178 {
01179   PRBool flagExists, flagIsFile;
01180   PRInt32 ret = nsInstall::SUCCESS;
01181 
01182   mSrc->Exists(&flagExists);
01183   if(flagExists)
01184   {
01185     mSrc->IsFile(&flagIsFile);
01186     if(!flagIsFile)
01187     {
01188       nsCOMPtr<nsIFile> target;
01189 
01190       mSrc->GetParent(getter_AddRefs(target));
01191       target->Append(*mStrTarget);
01192 
01193       target->Exists(&flagExists);
01194       if(!flagExists)
01195       {
01196         nsCOMPtr<nsIFile> parent;
01197         mSrc->GetParent(getter_AddRefs(parent));
01198         ret = mSrc->MoveTo(parent, *mStrTarget);
01199       }
01200       else
01201         return nsInstall::ALREADY_EXISTS;
01202     }
01203     else
01204       ret = nsInstall::SOURCE_IS_FILE;
01205   }
01206   else  
01207     ret = nsInstall::SOURCE_DOES_NOT_EXIST;
01208 
01209   return ret;
01210 }
01211 
01212 PRInt32
01213 nsInstallFileOpItem::NativeFileOpDirRenameAbort()
01214 {
01215   PRBool     flagExists;
01216   PRInt32    ret = nsInstall::SUCCESS;
01217   nsAutoString leafName;
01218   nsCOMPtr<nsIFile> newDirName;
01219   nsCOMPtr<nsIFile> parent;
01220 
01221   mSrc->Exists(&flagExists);
01222   if(!flagExists)
01223   {
01224     mSrc->GetLeafName(leafName);
01225     mSrc->GetParent(getter_AddRefs(newDirName));
01226     newDirName->Append(*mStrTarget);
01227     mSrc->GetParent(getter_AddRefs(parent));
01228     ret = newDirName->MoveTo(parent, leafName);
01229   }
01230 
01231   return ret;
01232 }
01233 
01234 PRInt32
01235 nsInstallFileOpItem::NativeFileOpWindowsShortcutPrepare()
01236 {
01237   PRInt32 ret = nsInstall::SUCCESS;
01238 
01239 #ifdef _WINDOWS
01240   nsCOMPtr<nsIFile> tempVar;
01241   PRBool            flagExists;
01242 
01243   if(mShortcutPath)
01244   {
01245     mShortcutPath->Clone(getter_AddRefs(tempVar));
01246     tempVar->Exists(&flagExists);
01247     if(!flagExists)
01248     {
01249       tempVar->Create(1, 0755);
01250       tempVar->Exists(&flagExists);
01251       if(!flagExists)
01252         ret = nsInstall::ACCESS_DENIED;
01253     }
01254     else
01255     {
01256       tempVar->AppendNative(NS_LITERAL_CSTRING("NSTestDir"));
01257       tempVar->Create(1, 0755);
01258       tempVar->Exists(&flagExists);
01259       if(!flagExists)
01260         ret = nsInstall::ACCESS_DENIED;
01261       else
01262         tempVar->Remove(0);
01263     }
01264   }
01265 
01266   if(nsInstall::SUCCESS == ret)
01267     mAction = nsInstallFileOpItem::ACTION_SUCCESS;
01268 
01269 #endif
01270 
01271   return ret;
01272 }
01273 
01274 PRInt32
01275 nsInstallFileOpItem::NativeFileOpWindowsShortcutComplete()
01276 {
01277   PRInt32 ret = nsInstall::SUCCESS;
01278 
01279 #ifdef _WINDOWS
01280   nsresult      rv1, rv2;
01281   nsCAutoString description;
01282   nsCAutoString params;
01283   nsCAutoString targetNativePathStr;
01284   nsCAutoString shortcutNativePathStr;
01285   nsCAutoString workingpathNativePathStr;
01286   nsCAutoString iconNativePathStr;
01287 
01288   rv1 = NS_CopyUnicodeToNative(mDescription, description);
01289   rv2 = NS_CopyUnicodeToNative(mParams, params);
01290 
01291   if(NS_FAILED(rv1) || NS_FAILED(rv2))
01292     ret = nsInstall::UNEXPECTED_ERROR;
01293   else
01294   {
01295     if(mTarget)
01296       mTarget->GetNativePath(targetNativePathStr);
01297     if(mShortcutPath)
01298       mShortcutPath->GetNativePath(shortcutNativePathStr);
01299     if(mWorkingPath)
01300       mWorkingPath->GetNativePath(workingpathNativePathStr);
01301     if(mIcon)
01302       mIcon->GetNativePath(iconNativePathStr);
01303 
01304     CreateALink(targetNativePathStr.get(),
01305                       shortcutNativePathStr.get(),
01306                       description.get(),
01307                       workingpathNativePathStr.get(),
01308                       params.get(),
01309                       iconNativePathStr.get(),
01310                       mIconId);
01311 
01312     mAction = nsInstallFileOpItem::ACTION_SUCCESS;
01313   }
01314 #endif
01315 
01316   return ret;
01317 }
01318 
01319 PRInt32
01320 nsInstallFileOpItem::NativeFileOpWindowsShortcutAbort()
01321 {
01322 #ifdef _WINDOWS
01323   if(mShortcutPath)
01324   {
01325     nsCOMPtr<nsIFile> shortcutTarget;
01326     nsAutoString shortcutDescription(mDescription + NS_LITERAL_STRING(".lnk"));
01327 
01328     mShortcutPath->Clone(getter_AddRefs(shortcutTarget));
01329     shortcutTarget->Append(shortcutDescription);
01330 
01331     NativeFileOpFileDeleteComplete(shortcutTarget);
01332   }
01333 #endif
01334 
01335   return nsInstall::SUCCESS;
01336 }
01337 
01338 PRInt32
01339 nsInstallFileOpItem::NativeFileOpMacAliasPrepare()
01340 {
01341 
01342 #if defined(XP_MAC) || defined(XP_MACOSX)
01343   nsCOMPtr<nsILocalFileMac> targetFile = do_QueryInterface(mTarget);
01344   nsCOMPtr<nsILocalFileMac> sourceFile = do_QueryInterface(mSrc);
01345 
01346   nsresult      rv;
01347   PRBool        exists;  
01348    
01349   // check if source file exists
01350   rv = sourceFile->Exists(&exists);
01351   if (NS_FAILED(rv) || !exists)
01352     return nsInstall::SOURCE_DOES_NOT_EXIST;
01353 
01354   // check if alias file already exists at target
01355   targetFile->SetFollowLinks(PR_FALSE);
01356   rv = targetFile->Exists(&exists);
01357   if (NS_FAILED(rv))
01358     return nsInstall::INVALID_PATH_ERR;
01359   
01360   // if file already exists: delete it before creating an updated alias
01361   if (exists) {
01362     rv = targetFile->Remove(PR_TRUE);
01363     if (NS_FAILED(rv))
01364         return nsInstall::FILENAME_ALREADY_USED;
01365   }    
01366 #endif /* XP_MAC || XP_MACOSX */
01367 
01368     return nsInstall::SUCCESS;
01369 }
01370 
01371 PRInt32
01372 nsInstallFileOpItem::NativeFileOpMacAliasComplete()
01373 {
01374 
01375 #if defined(XP_MAC) || defined(XP_MACOSX)
01376   // XXX gestalt to see if alias manager is around
01377   
01378   nsCOMPtr<nsILocalFileMac> localFileMacTarget = do_QueryInterface(mTarget);
01379   nsCOMPtr<nsILocalFileMac> localFileMacSrc = do_QueryInterface(mSrc);
01380   
01381   FSRef         sourceRef, aliasRef, aliasParentRef;
01382   HFSUniStr255  aliasName;
01383   PRBool        exists;
01384   AliasHandle   aliasH;
01385   OSErr         err = noErr;
01386   nsresult      rv = NS_OK;
01387   
01388   // check if source file exists
01389   rv = localFileMacSrc->Exists(&exists);
01390   if (NS_FAILED(rv) || !exists)
01391     return nsInstall::SOURCE_DOES_NOT_EXIST;
01392       
01393   // check if file/folder already exists at target
01394   localFileMacTarget->SetFollowLinks(PR_FALSE);
01395   rv = localFileMacTarget->Exists(&exists);
01396   if (NS_FAILED(rv))
01397     return nsInstall::INVALID_PATH_ERR;
01398   
01399   // if file already exists: delete it before creating an updated alias
01400   if (exists) {
01401     rv = localFileMacTarget->Remove(PR_TRUE);
01402     if (NS_FAILED(rv))
01403         return nsInstall::FILENAME_ALREADY_USED;
01404   }    
01405 
01406   rv = localFileMacSrc->GetFSRef(&sourceRef);
01407   if (NS_FAILED(rv)) return rv;
01408 
01409   // get alias parent
01410   nsCOMPtr<nsIFile> aliasParentIFile;
01411   rv = localFileMacTarget->GetParent(getter_AddRefs(aliasParentIFile)); 
01412   if (NS_FAILED(rv)) return rv;
01413   nsCOMPtr<nsILocalFileMac> macDaddy(do_QueryInterface(aliasParentIFile));
01414   rv = macDaddy->GetFSRef(&aliasParentRef); 
01415   if (NS_FAILED(rv)) return rv;
01416 
01417   // get alias leaf name
01418   nsAutoString leafName;
01419   rv = localFileMacTarget->GetLeafName(leafName);
01420   if (NS_FAILED(rv)) return rv;
01421   aliasName.length = leafName.Length();
01422   CopyUnicodeTo(leafName, 0, aliasName.unicode, aliasName.length);
01423 
01424   err = FSNewAliasMinimal( &sourceRef, &aliasH );
01425   if (err != noErr)  // bubble up Alias Manager error
01426        return err;
01427        
01428   // create the alias file
01429   FSCatalogInfo catInfo;
01430   FSGetCatalogInfo(&sourceRef, kFSCatInfoFinderInfo, &catInfo, 
01431     NULL, NULL, NULL);
01432   // mark newly created file as an alias file
01433   FInfo *fInfo = (FInfo *) catInfo.finderInfo;
01434   fInfo->fdFlags |= kIsAlias;
01435   FSCreateResFile(&aliasParentRef, aliasName.length, aliasName.unicode, 
01436     kFSCatInfoFinderInfo, &catInfo, &aliasRef, NULL);
01437 
01438   SInt16 refNum = FSOpenResFile(&aliasRef, fsRdWrPerm);
01439   if (refNum != -1)
01440   {
01441     UseResFile(refNum);
01442     AddResource((Handle)aliasH, rAliasType, 0, "\pAlias");
01443     ReleaseResource((Handle)aliasH);
01444     UpdateResFile(refNum);
01445     CloseResFile(refNum);
01446   }
01447   else
01448     return nsInstall::SUCCESS;  // non-fatal so prevent internal abort
01449   
01450 #endif /* XP_MAC || XP_MACOSX */
01451 
01452   return nsInstall::SUCCESS;
01453 }
01454 
01455 PRInt32
01456 nsInstallFileOpItem::NativeFileOpMacAliasAbort()
01457 {  
01458 #if defined(XP_MAC) || defined(XP_MACOSX)
01459   NativeFileOpFileDeleteComplete(mTarget);
01460 #endif 
01461 
01462   return nsInstall::SUCCESS;
01463 }
01464 
01465 PRInt32
01466 nsInstallFileOpItem::NativeFileOpUnixLink()
01467 {
01468   return nsInstall::SUCCESS;
01469 }
01470 
01471 PRInt32
01472 nsInstallFileOpItem::NativeFileOpWindowsRegisterServerPrepare()
01473 {
01474   PRInt32 rv = nsInstall::SUCCESS;
01475 
01476 #ifdef _WINDOWS
01477   nsCAutoString file;
01478   FARPROC   DllReg;
01479   HINSTANCE hLib;
01480 
01481   mTarget->GetNativePath(file);
01482   if(!file.IsEmpty())
01483   {
01484     if((hLib = LoadLibraryEx(file.get(), NULL, LOAD_WITH_ALTERED_SEARCH_PATH)) != NULL)
01485     {
01486       if((DllReg = GetProcAddress(hLib, "DllRegisterServer")) == NULL)
01487         rv = nsInstall::UNABLE_TO_LOCATE_LIB_FUNCTION;
01488 
01489       FreeLibrary(hLib);
01490     }
01491     else
01492       rv = nsInstall::UNABLE_TO_LOAD_LIBRARY;
01493   }
01494   else
01495     rv = nsInstall::UNEXPECTED_ERROR;
01496 #endif
01497 
01498   return(rv);
01499 }
01500 
01501 PRInt32
01502 nsInstallFileOpItem::NativeFileOpWindowsRegisterServerComplete()
01503 {
01504   PRInt32 rv = nsInstall::SUCCESS;
01505 
01506 #ifdef _WINDOWS
01507   nsCAutoString file;
01508   FARPROC   DllReg;
01509   HINSTANCE hLib;
01510 
01511   mTarget->GetNativePath(file);
01512   if(!file.IsEmpty())
01513   {
01514     if((hLib = LoadLibraryEx(file.get(), NULL, LOAD_WITH_ALTERED_SEARCH_PATH)) != NULL)
01515     {
01516       if((DllReg = GetProcAddress(hLib, "DllRegisterServer")) != NULL)
01517         DllReg();
01518       else
01519         rv = nsInstall::UNABLE_TO_LOCATE_LIB_FUNCTION;
01520 
01521       FreeLibrary(hLib);
01522     }
01523     else
01524       rv = nsInstall::UNABLE_TO_LOAD_LIBRARY;
01525   }
01526   else
01527     rv = nsInstall::UNEXPECTED_ERROR;
01528 #endif
01529 
01530   return(rv);
01531 }
01532 
01533 PRInt32
01534 nsInstallFileOpItem::NativeFileOpWindowsRegisterServerAbort()
01535 {
01536   PRInt32 rv = nsInstall::SUCCESS;
01537 
01538 #ifdef _WINDOWS
01539   nsCAutoString file;
01540   FARPROC   DllUnReg;
01541   HINSTANCE hLib;
01542 
01543   mTarget->GetNativePath(file);
01544   if(!file.IsEmpty())
01545   {
01546     if((hLib = LoadLibraryEx(file.get(), NULL, LOAD_WITH_ALTERED_SEARCH_PATH)) != NULL)
01547     {
01548       if((DllUnReg = GetProcAddress(hLib, "DllUnregisterServer")) != NULL)
01549         DllUnReg();
01550       else
01551         rv = nsInstall::UNABLE_TO_LOCATE_LIB_FUNCTION;
01552 
01553       FreeLibrary(hLib);
01554     }
01555     else
01556       rv = nsInstall::UNABLE_TO_LOAD_LIBRARY;
01557   }
01558   else
01559     rv = nsInstall::UNEXPECTED_ERROR;
01560 #endif
01561 
01562   return(rv);
01563 }
01564