]> git.proxmox.com Git - mirror_edk2.git/blobdiff - BaseTools/Source/Python/UPT/InstallPkg.py
BaseTools: Remove equality operator with None
[mirror_edk2.git] / BaseTools / Source / Python / UPT / InstallPkg.py
index 776196e8ea8b44a684c64f265ce6c8f043995343..c0d56b55aacde53df33d0ea1c6add11317aac3a2 100644 (file)
@@ -1,7 +1,7 @@
 ## @file\r
 # Install distribution package.\r
 #\r
-# Copyright (c) 2011, Intel Corporation. All rights reserved.<BR>\r
+# Copyright (c) 2011 - 2017, Intel Corporation. All rights reserved.<BR>\r
 #\r
 # This program and the accompanying materials are licensed and made available \r
 # under the terms and conditions of the BSD License which accompanies this \r
@@ -17,12 +17,14 @@ Install a distribution package
 ##\r
 # Import Modules\r
 #\r
+from Core.FileHook import __FileHookOpen__\r
 import os.path\r
 from os import chmod\r
 from os import SEEK_SET\r
 from os import SEEK_END\r
 import stat\r
 import md5\r
+import copy\r
 from sys import stdin\r
 from sys import platform\r
 from shutil import rmtree\r
@@ -42,7 +44,6 @@ from Logger.ToolError import FORMAT_INVALID
 from Logger.ToolError import FILE_TYPE_MISMATCH\r
 import Logger.Log as Logger\r
 \r
-from Library.Misc import CheckEnvVariable\r
 from Library.Misc import Sdict\r
 from Library.Misc import ConvertPath\r
 from Library.ParserValidate import IsValidInstallPath\r
@@ -83,7 +84,6 @@ def InstallNewPackage(WorkspaceDir, Path, CustomPath = False):
     Input = Input.replace('\r', '').replace('\n', '')\r
     return InstallNewPackage(WorkspaceDir, Input, False)\r
 \r
-\r
 ## InstallNewModule\r
 #\r
 # @param WorkspaceDir:   Workspace Directory\r
@@ -91,7 +91,7 @@ def InstallNewPackage(WorkspaceDir, Path, CustomPath = False):
 # @param PathList:       The already installed standalone module Path list\r
 #\r
 def InstallNewModule(WorkspaceDir, Path, PathList = None):\r
-    if PathList == None:\r
+    if PathList is None:\r
         PathList = []\r
     Path = ConvertPath(Path)\r
     Path = os.path.normpath(Path)\r
@@ -133,17 +133,16 @@ def InstallNewFile(WorkspaceDir, File):
 #\r
 # UnZipDp\r
 #\r
-def UnZipDp(WorkspaceDir, Options, DataBase):\r
+def UnZipDp(WorkspaceDir, DpPkgFileName, Index=1):\r
     ContentZipFile = None\r
     Logger.Quiet(ST.MSG_UZIP_PARSE_XML)\r
-    DpPkgFileName = Options.PackageFile\r
     DistFile = PackageFile(DpPkgFileName)\r
     \r
     DpDescFileName, ContentFileName = GetDPFile(DistFile.GetZipFile())\r
     \r
-    GlobalData.gUNPACK_DIR = os.path.normpath(os.path.join(WorkspaceDir, ".tmp"))\r
-    DistPkgFile = DistFile.UnpackFile(DpDescFileName,\r
-        os.path.normpath(os.path.join(GlobalData.gUNPACK_DIR, DpDescFileName)))\r
+    TempDir = os.path.normpath(os.path.join(WorkspaceDir, "Conf/.tmp%s" % str(Index)))\r
+    GlobalData.gUNPACK_DIR.append(TempDir)\r
+    DistPkgFile = DistFile.UnpackFile(DpDescFileName, os.path.normpath(os.path.join(TempDir, DpDescFileName)))\r
     if not DistPkgFile:\r
         Logger.Error("InstallPkg", FILE_NOT_FOUND, ST.ERR_FILE_BROKEN %DpDescFileName)\r
     \r
@@ -156,46 +155,19 @@ def UnZipDp(WorkspaceDir, Options, DataBase):
         DistPkg.Header.RePackage = False\r
     if DistPkg.Header.ReadOnly == '':\r
         DistPkg.Header.ReadOnly = False\r
-    \r
-    #\r
-    # prepare check dependency\r
-    #\r
-    Dep = DependencyRules(DataBase)\r
-    #\r
-    # Check distribution package installed or not\r
-    #\r
-    if Dep.CheckDpExists(DistPkg.Header.GetGuid(),\r
-        DistPkg.Header.GetVersion()):\r
-        Logger.Error("InstallPkg", UPT_ALREADY_INSTALLED_ERROR,\r
-            ST.WRN_DIST_PKG_INSTALLED)\r
-    #\r
-    # Check distribution dependency (all module dependency should be\r
-    # satisfied)\r
-    #\r
-    if not Dep.CheckDpDepexSatisfied(DistPkg):\r
-        Logger.Error("InstallPkg", UNKNOWN_ERROR,\r
-            ST.ERR_PACKAGE_NOT_MATCH_DEPENDENCY,\r
-            ExtraData=DistPkg.Header.Name)\r
+\r
     #\r
     # unzip contents.zip file\r
     #\r
-    ContentFile = DistFile.UnpackFile(ContentFileName,\r
-        os.path.normpath(os.path.join(GlobalData.gUNPACK_DIR, ContentFileName)))\r
+    ContentFile = DistFile.UnpackFile(ContentFileName, os.path.normpath(os.path.join(TempDir, ContentFileName)))\r
     if not ContentFile:\r
         Logger.Error("InstallPkg", FILE_NOT_FOUND,\r
             ST.ERR_FILE_BROKEN % ContentFileName)\r
 \r
-    FilePointer = open(ContentFile, "rb")\r
-    #\r
-    # Assume no archive comment.\r
-    #\r
-    FilePointer.seek(0, SEEK_SET)\r
-    FilePointer.seek(0, SEEK_END)\r
     #\r
     # Get file size\r
     #                \r
-    FileSize = FilePointer.tell()\r
-    FilePointer.close()\r
+    FileSize = os.path.getsize(ContentFile)\r
                \r
     if FileSize != 0:        \r
         ContentZipFile = PackageFile(ContentFile)\r
@@ -204,13 +176,13 @@ def UnZipDp(WorkspaceDir, Options, DataBase):
     # verify MD5 signature when existed\r
     #\r
     if DistPkg.Header.Signature != '':\r
-        Md5Sigature = md5.new(open(ContentFile, 'rb').read())\r
+        Md5Sigature = md5.new(__FileHookOpen__(ContentFile, 'rb').read())\r
         if DistPkg.Header.Signature != Md5Sigature.hexdigest():\r
             ContentZipFile.Close()\r
             Logger.Error("InstallPkg", FILE_CHECKSUM_FAILURE,\r
                 ExtraData=ContentFile)\r
 \r
-    return DistPkg, Dep, ContentZipFile, DpPkgFileName\r
+    return DistPkg, ContentZipFile, DpPkgFileName, DistFile\r
 \r
 ## GetPackageList\r
 #\r
@@ -222,9 +194,13 @@ def GetPackageList(DistPkg, Dep, WorkspaceDir, Options, ContentZipFile, ModuleLi
         PackagePath = Path\r
         Package = DistPkg.PackageSurfaceArea[Guid, Version, Path]\r
         Logger.Info(ST.MSG_INSTALL_PACKAGE % Package.GetName())\r
-        if Dep.CheckPackageExists(Guid, Version):\r
-            Logger.Info(ST.WRN_PACKAGE_EXISTED %(Guid, Version))\r
-        NewPackagePath = InstallNewPackage(WorkspaceDir, PackagePath, Options.CustomPath)\r
+#         if Dep.CheckPackageExists(Guid, Version):\r
+#             Logger.Info(ST.WRN_PACKAGE_EXISTED %(Guid, Version))\r
+        if Options.UseGuidedPkgPath:\r
+            GuidedPkgPath = "%s_%s_%s" % (Package.GetName(), Guid, Version)\r
+            NewPackagePath = InstallNewPackage(WorkspaceDir, GuidedPkgPath, Options.CustomPath)\r
+        else:\r
+            NewPackagePath = InstallNewPackage(WorkspaceDir, PackagePath, Options.CustomPath)\r
         InstallPackageContent(PackagePath, NewPackagePath, Package, ContentZipFile, Dep, WorkspaceDir, ModuleList, \r
                               DistPkg.Header.ReadOnly)\r
         PackageList.append(Package)\r
@@ -238,8 +214,8 @@ def GetPackageList(DistPkg, Dep, WorkspaceDir, Options, ContentZipFile, ModuleLi
     # dependency (Hard to get the location of the newly installed package)\r
     #\r
     for Package in PackageList:\r
-        FilePath = PackageToDec(Package)\r
-        Md5Sigature = md5.new(open(str(FilePath), 'rb').read())\r
+        FilePath = PackageToDec(Package, DistPkg.Header)\r
+        Md5Sigature = md5.new(__FileHookOpen__(str(FilePath), 'rb').read())\r
         Md5Sum = Md5Sigature.hexdigest()\r
         if (FilePath, Md5Sum) not in Package.FileList:\r
             Package.FileList.append((FilePath, Md5Sum))\r
@@ -258,7 +234,7 @@ def GetModuleList(DistPkg, Dep, WorkspaceDir, ContentZipFile, ModuleList):
     # install them directly. If not, we will try to create a new directory \r
     # for it.\r
     #\r
-    ModulePathList = []   \r
+    ModulePathList = []\r
     \r
     #\r
     # Check module exist and install\r
@@ -297,8 +273,9 @@ def GetModuleList(DistPkg, Dep, WorkspaceDir, ContentZipFile, ModuleList):
     # generate all inf for modules\r
     #\r
     for (Module, Package) in ModuleList:\r
-        FilePath = ModuleToInf(Module)\r
-        Md5Sigature = md5.new(open(str(FilePath), 'rb').read())\r
+        CheckCNameInModuleRedefined(Module, DistPkg)\r
+        FilePath = ModuleToInf(Module, Package, DistPkg.Header)\r
+        Md5Sigature = md5.new(__FileHookOpen__(str(FilePath), 'rb').read())\r
         Md5Sum = Md5Sigature.hexdigest()\r
         if Package:\r
             if (FilePath, Md5Sum) not in Package.FileList:\r
@@ -306,9 +283,167 @@ def GetModuleList(DistPkg, Dep, WorkspaceDir, ContentZipFile, ModuleList):
         else:\r
             if (FilePath, Md5Sum) not in Module.FileList:\r
                 Module.FileList.append((FilePath, Md5Sum))\r
+        #\r
+        # append the module unicode files to Package FileList\r
+        #\r
+        for (FilePath, Md5Sum) in Module.FileList:\r
+            if str(FilePath).endswith('.uni') and Package and (FilePath, Md5Sum) not in Package.FileList:\r
+                Package.FileList.append((FilePath, Md5Sum))\r
     \r
     return NewDict\r
 \r
+##\r
+# Get all protocol/ppi/guid CNames and pcd name from all dependent DEC file\r
+#\r
+def GetDepProtocolPpiGuidPcdNames(DePackageObjList):\r
+    #\r
+    # [[Dec1Protocol1, Dec1Protocol2...], [Dec2Protocols...],...]\r
+    #\r
+    DependentProtocolCNames = []\r
+    DependentPpiCNames = []\r
+    DependentGuidCNames = []\r
+    DependentPcdNames = []\r
+    \r
+    for PackageObj in DePackageObjList:\r
+        #\r
+        # Get protocol CName list from all dependent DEC file\r
+        #\r
+        ProtocolCNames = []\r
+        for Protocol in PackageObj.GetProtocolList():\r
+            if Protocol.GetCName() not in ProtocolCNames:\r
+                ProtocolCNames.append(Protocol.GetCName())\r
+  \r
+        DependentProtocolCNames.append(ProtocolCNames)\r
+            \r
+        #\r
+        # Get Ppi CName list from all dependent DEC file\r
+        #            \r
+        PpiCNames = []\r
+        for Ppi in PackageObj.GetPpiList():\r
+            if Ppi.GetCName() not in PpiCNames:\r
+                PpiCNames.append(Ppi.GetCName())\r
+\r
+        DependentPpiCNames.append(PpiCNames)\r
+            \r
+        #\r
+        # Get Guid CName list from all dependent DEC file\r
+        #      \r
+        GuidCNames = []\r
+        for Guid in PackageObj.GetGuidList():\r
+            if Guid.GetCName() not in GuidCNames:\r
+                GuidCNames.append(Guid.GetCName())\r
+        \r
+        DependentGuidCNames.append(GuidCNames)\r
+        \r
+        #\r
+        # Get PcdName list from all dependent DEC file\r
+        #\r
+        PcdNames = []\r
+        for Pcd in PackageObj.GetPcdList():\r
+            PcdName = '.'.join([Pcd.GetTokenSpaceGuidCName(), Pcd.GetCName()])\r
+            if PcdName not in PcdNames:\r
+                PcdNames.append(PcdName)\r
+        \r
+        DependentPcdNames.append(PcdNames)\r
+                \r
+            \r
+    return DependentProtocolCNames, DependentPpiCNames, DependentGuidCNames, DependentPcdNames\r
+\r
+##\r
+# Check if protocol CName is redefined\r
+#\r
+def CheckProtoclCNameRedefined(Module, DependentProtocolCNames):\r
+    for ProtocolInModule in Module.GetProtocolList():\r
+        IsCNameDefined = False\r
+        for PackageProtocolCNames in DependentProtocolCNames:\r
+            if ProtocolInModule.GetCName() in PackageProtocolCNames:\r
+                if IsCNameDefined:\r
+                    Logger.Error("\nUPT", FORMAT_INVALID, \r
+                                 File = Module.GetFullPath(), \r
+                                 ExtraData = \\r
+                                 ST.ERR_INF_PARSER_ITEM_DUPLICATE_IN_DEC % ProtocolInModule.GetCName())\r
+                else:\r
+                    IsCNameDefined = True\r
+\r
+##\r
+# Check if Ppi CName is redefined\r
+#\r
+def CheckPpiCNameRedefined(Module, DependentPpiCNames):\r
+    for PpiInModule in Module.GetPpiList():\r
+        IsCNameDefined = False\r
+        for PackagePpiCNames in DependentPpiCNames:\r
+            if PpiInModule.GetCName() in PackagePpiCNames:\r
+                if IsCNameDefined:\r
+                    Logger.Error("\nUPT", FORMAT_INVALID, \r
+                                 File = Module.GetFullPath(), \r
+                                 ExtraData = ST.ERR_INF_PARSER_ITEM_DUPLICATE_IN_DEC % PpiInModule.GetCName())\r
+                else:\r
+                    IsCNameDefined = True    \r
+\r
+##\r
+# Check if Guid CName is redefined\r
+#\r
+def CheckGuidCNameRedefined(Module, DependentGuidCNames):\r
+    for GuidInModule in Module.GetGuidList():\r
+        IsCNameDefined = False\r
+        for PackageGuidCNames in DependentGuidCNames:\r
+            if GuidInModule.GetCName() in PackageGuidCNames:\r
+                if IsCNameDefined:\r
+                    Logger.Error("\nUPT", FORMAT_INVALID, \r
+                                 File = Module.GetFullPath(), \r
+                                 ExtraData = \\r
+                                 ST.ERR_INF_PARSER_ITEM_DUPLICATE_IN_DEC % GuidInModule.GetCName())\r
+                else:\r
+                    IsCNameDefined = True\r
+\r
+##\r
+# Check if PcdName is redefined\r
+#\r
+def CheckPcdNameRedefined(Module, DependentPcdNames):\r
+    PcdObjs = []\r
+    if not Module.GetBinaryFileList():\r
+        PcdObjs += Module.GetPcdList()\r
+    else:\r
+        Binary = Module.GetBinaryFileList()[0]\r
+        for AsBuild in Binary.GetAsBuiltList():\r
+            PcdObjs += AsBuild.GetPatchPcdList() + AsBuild.GetPcdExList()\r
+\r
+    for PcdObj in PcdObjs:\r
+        PcdName = '.'.join([PcdObj.GetTokenSpaceGuidCName(), PcdObj.GetCName()])\r
+        IsPcdNameDefined = False\r
+        for PcdNames in DependentPcdNames:\r
+            if PcdName in PcdNames:\r
+                if IsPcdNameDefined:\r
+                    Logger.Error("\nUPT", FORMAT_INVALID, \r
+                                 File = Module.GetFullPath(), \r
+                                 ExtraData = ST.ERR_INF_PARSER_ITEM_DUPLICATE_IN_DEC % PcdName)\r
+                else:\r
+                    IsPcdNameDefined = True\r
+\r
+##\r
+# Check if any Protocol/Ppi/Guid and Pcd name is redefined in its dependent DEC files\r
+#\r
+def CheckCNameInModuleRedefined(Module, DistPkg):\r
+    DePackageObjList = []\r
+    #\r
+    # Get all dependent package objects\r
+    # \r
+    for Obj in Module.GetPackageDependencyList():\r
+        Guid = Obj.GetGuid()\r
+        Version = Obj.GetVersion()\r
+        for Key in DistPkg.PackageSurfaceArea:\r
+            if Key[0] == Guid and Key[1] == Version:\r
+                if DistPkg.PackageSurfaceArea[Key] not in DePackageObjList:\r
+                    DePackageObjList.append(DistPkg.PackageSurfaceArea[Key])\r
+    \r
+    DependentProtocolCNames, DependentPpiCNames, DependentGuidCNames, DependentPcdNames = \\r
+    GetDepProtocolPpiGuidPcdNames(DePackageObjList)\r
+\r
+    CheckProtoclCNameRedefined(Module, DependentProtocolCNames)\r
+    CheckPpiCNameRedefined(Module, DependentPpiCNames)\r
+    CheckGuidCNameRedefined(Module, DependentGuidCNames)\r
+    CheckPcdNameRedefined(Module, DependentPcdNames)\r
+\r
 ## GenToolMisc\r
 #\r
 # GenToolMisc\r
@@ -366,75 +501,52 @@ def GenToolMisc(DistPkg, WorkspaceDir, ContentZipFile):
 # @param  Options: command Options\r
 #\r
 def Main(Options = None):\r
-    ContentZipFile, DistFile = None, None\r
-\r
     try:\r
-        DataBase = GlobalData.gDB        \r
-        CheckEnvVariable()\r
+        DataBase = GlobalData.gDB\r
         WorkspaceDir = GlobalData.gWORKSPACE\r
         if not Options.PackageFile:\r
             Logger.Error("InstallPkg", OPTION_MISSING, ExtraData=ST.ERR_SPECIFY_PACKAGE)\r
         \r
-        #\r
-        # unzip dist.pkg file\r
-        #\r
-        DistPkg, Dep, ContentZipFile, DpPkgFileName = UnZipDp(WorkspaceDir, Options, DataBase)\r
+        # Get all Dist Info\r
+        DistInfoList = []\r
+        DistPkgList = []\r
+        Index = 1\r
+        for ToBeInstalledDist in Options.PackageFile:\r
+            #\r
+            # unzip dist.pkg file\r
+            #\r
+            DistInfoList.append(UnZipDp(WorkspaceDir, ToBeInstalledDist, Index))\r
+            DistPkgList.append(DistInfoList[-1][0])\r
+            Index += 1\r
 \r
-        #\r
-        # PackageList, ModuleList record the information for the meta-data\r
-        # files that need to be generated later\r
-        #\r
-        PackageList = []\r
-        ModuleList = []\r
-        DistPkg.PackageSurfaceArea = GetPackageList(DistPkg, Dep, WorkspaceDir, Options, \r
-                                                    ContentZipFile, ModuleList, PackageList)\r
+            #\r
+            # Add dist\r
+            #\r
+            GlobalData.gTO_BE_INSTALLED_DIST_LIST.append(DistInfoList[-1][0])\r
 \r
-        DistPkg.ModuleSurfaceArea = GetModuleList(DistPkg, Dep, WorkspaceDir, ContentZipFile, ModuleList)       \r
-        \r
-        \r
-        GenToolMisc(DistPkg, WorkspaceDir, ContentZipFile)\r
-        \r
-        #\r
-        # copy "Distribution File" to directory $(WORKSPACE)/conf/upt\r
-        #\r
-        DistFileName = os.path.split(DpPkgFileName)[1]\r
-        DestDir = os.path.normpath(os.path.join(WorkspaceDir, GlobalData.gUPT_DIR))\r
-        CreateDirectory(DestDir)\r
-        DestFile = os.path.normpath(os.path.join(DestDir, DistFileName))\r
-        if os.path.exists(DestFile):\r
-            FileName, Ext = os.path.splitext(DistFileName)\r
-            NewFileName = FileName + '_' + DistPkg.Header.GetGuid() + '_' + DistPkg.Header.GetVersion() + Ext\r
-            DestFile = os.path.normpath(os.path.join(DestDir, NewFileName))\r
-            if os.path.exists(DestFile):\r
-                #\r
-                # ask for user input the new file name\r
-                #\r
-                Logger.Info( ST.MSG_NEW_FILE_NAME_FOR_DIST)\r
-                Input = stdin.readline()\r
-                Input = Input.replace('\r', '').replace('\n', '')\r
-                DestFile = os.path.normpath(os.path.join(DestDir, Input))\r
-        copyfile(DpPkgFileName, DestFile)\r
-        NewDpPkgFileName = DestFile[DestFile.find(DestDir) + len(DestDir) + 1:]\r
+        # Check for dependency\r
+        Dep = DependencyRules(DataBase, DistPkgList)\r
 \r
-        #\r
-        # update database\r
-        #\r
-        Logger.Quiet(ST.MSG_UPDATE_PACKAGE_DATABASE)\r
-        DataBase.AddDPObject(DistPkg, NewDpPkgFileName, DistFileName, \r
-                       DistPkg.Header.RePackage)\r
-        \r
+        for ToBeInstalledDist in DistInfoList:\r
+            CheckInstallDpx(Dep, ToBeInstalledDist[0], ToBeInstalledDist[2])\r
+\r
+            #\r
+            # Install distribution\r
+            #\r
+            InstallDp(ToBeInstalledDist[0], ToBeInstalledDist[2], ToBeInstalledDist[1],\r
+                      Options, Dep, WorkspaceDir, DataBase)\r
         ReturnCode = 0\r
         \r
     except FatalError, XExcept:\r
         ReturnCode = XExcept.args[0]\r
         if Logger.GetLevel() <= Logger.DEBUG_9:\r
-            Logger.Quiet(ST.MSG_PYTHON_ON % (python_version(),\r
-                platform) + format_exc())\r
+            Logger.Quiet(ST.MSG_PYTHON_ON % (python_version(), platform) + format_exc())\r
+            \r
     except KeyboardInterrupt:\r
         ReturnCode = ABORT_ERROR\r
         if Logger.GetLevel() <= Logger.DEBUG_9:\r
-            Logger.Quiet(ST.MSG_PYTHON_ON % (python_version(),\r
-                platform) + format_exc())\r
+            Logger.Quiet(ST.MSG_PYTHON_ON % (python_version(), platform) + format_exc())\r
+            \r
     except:\r
         ReturnCode = CODE_ERROR\r
         Logger.Error(\r
@@ -446,23 +558,78 @@ def Main(Options = None):
                     )\r
         Logger.Quiet(ST.MSG_PYTHON_ON % (python_version(),\r
             platform) + format_exc())\r
-\r
     finally:\r
         Logger.Quiet(ST.MSG_REMOVE_TEMP_FILE_STARTED)\r
-        if DistFile:\r
-            DistFile.Close()\r
-        if ContentZipFile:\r
-            ContentZipFile.Close()\r
-        if GlobalData.gUNPACK_DIR:\r
-            rmtree(GlobalData.gUNPACK_DIR)\r
-            GlobalData.gUNPACK_DIR = None\r
+        for ToBeInstalledDist in DistInfoList:\r
+            if ToBeInstalledDist[3]:\r
+                ToBeInstalledDist[3].Close()\r
+            if ToBeInstalledDist[1]:\r
+                ToBeInstalledDist[1].Close()\r
+        for TempDir in GlobalData.gUNPACK_DIR:\r
+            rmtree(TempDir)\r
+        GlobalData.gUNPACK_DIR = []\r
         Logger.Quiet(ST.MSG_REMOVE_TEMP_FILE_DONE)\r
-\r
     if ReturnCode == 0:\r
         Logger.Quiet(ST.MSG_FINISH)\r
-    \r
     return ReturnCode\r
 \r
+# BackupDist method\r
+#  \r
+# This method will backup the Distribution file into the $(WORKSPACE)/conf/upt, and rename it \r
+# if there is already a same-named distribution existed.\r
+#\r
+# @param DpPkgFileName: The distribution path\r
+# @param Guid:          The distribution Guid\r
+# @param Version:       The distribution Version\r
+# @param WorkspaceDir:  The workspace directory\r
+# @retval NewDpPkgFileName: The exact backup file name\r
+#\r
+def BackupDist(DpPkgFileName, Guid, Version, WorkspaceDir):\r
+    DistFileName = os.path.split(DpPkgFileName)[1]\r
+    DestDir = os.path.normpath(os.path.join(WorkspaceDir, GlobalData.gUPT_DIR))\r
+    CreateDirectory(DestDir)\r
+    DestFile = os.path.normpath(os.path.join(DestDir, DistFileName))\r
+    if os.path.exists(DestFile):\r
+        FileName, Ext = os.path.splitext(DistFileName)\r
+        NewFileName = FileName + '_' + Guid + '_' + Version + Ext\r
+        DestFile = os.path.normpath(os.path.join(DestDir, NewFileName))\r
+        if os.path.exists(DestFile):\r
+            #\r
+            # ask for user input the new file name\r
+            #\r
+            Logger.Info( ST.MSG_NEW_FILE_NAME_FOR_DIST)\r
+            Input = stdin.readline()\r
+            Input = Input.replace('\r', '').replace('\n', '')\r
+            DestFile = os.path.normpath(os.path.join(DestDir, Input))\r
+    copyfile(DpPkgFileName, DestFile)\r
+    NewDpPkgFileName = DestFile[DestFile.find(DestDir) + len(DestDir) + 1:]\r
+    return NewDpPkgFileName\r
+\r
+## CheckInstallDpx method\r
+#\r
+#  check whether distribution could be installed\r
+#\r
+#   @param  Dep: the DependencyRules instance that used to check dependency\r
+#   @param  DistPkg: the distribution object\r
+#\r
+def CheckInstallDpx(Dep, DistPkg, DistPkgFileName):\r
+    #\r
+    # Check distribution package installed or not\r
+    #\r
+    if Dep.CheckDpExists(DistPkg.Header.GetGuid(),\r
+        DistPkg.Header.GetVersion()):\r
+        Logger.Error("InstallPkg",\r
+                     UPT_ALREADY_INSTALLED_ERROR,\r
+                     ST.WRN_DIST_PKG_INSTALLED % os.path.basename(DistPkgFileName))\r
+    #\r
+    # Check distribution dependency (all module dependency should be\r
+    # satisfied)\r
+    #\r
+    if not Dep.CheckInstallDpDepexSatisfied(DistPkg):\r
+        Logger.Error("InstallPkg", UNKNOWN_ERROR,\r
+            ST.ERR_PACKAGE_NOT_MATCH_DEPENDENCY,\r
+            ExtraData=DistPkg.Header.Name)\r
+\r
 ## InstallModuleContent method\r
 #\r
 # If this is standalone module, then Package should be none,\r
@@ -501,7 +668,7 @@ def InstallModuleContent(FromPath, NewPath, ModulePath, Module, ContentZipFile,
             \r
             if not IsValidInstallPath(File):\r
                 Logger.Error("UPT", FORMAT_INVALID, ST.ERR_FILE_NAME_INVALIDE%File)\r
-                      \r
+\r
             FromFile = os.path.join(FromPath, ModulePath, File)\r
             Executable = Item.GetExecutable()            \r
             ToFile = os.path.normpath(os.path.join(NewModuleFullPath, ConvertPath(File)))\r
@@ -575,7 +742,7 @@ def InstallModuleContentZipFile(ContentZipFile, FromPath, ModulePath, WorkspaceD
                 FromFile = FileName\r
                 ToFile = os.path.normpath(os.path.join(WorkspaceDir, \r
                         ConvertPath(FileName.replace(FromPath, NewPath, 1))))\r
-                CheckList = Module.FileList\r
+                CheckList = copy.copy(Module.FileList)\r
                 if Package:\r
                     CheckList += Package.FileList\r
                 for Item in CheckList:\r
@@ -619,23 +786,28 @@ def FileUnderPath(FileName, CheckPath):
 # @return:  True or False  \r
 #\r
 def InstallFile(ContentZipFile, FromFile, ToFile, ReadOnly, Executable=False):\r
-    if not ContentZipFile or not ContentZipFile.UnpackFile(FromFile, ToFile):\r
-        Logger.Error("UPT", FILE_NOT_FOUND, ST.ERR_INSTALL_FILE_FROM_EMPTY_CONTENT%FromFile)\r
+    if os.path.exists(os.path.normpath(ToFile)):\r
+        pass\r
+    else:\r
+        if not ContentZipFile or not ContentZipFile.UnpackFile(FromFile, ToFile):\r
+            Logger.Error("UPT", FILE_NOT_FOUND, ST.ERR_INSTALL_FILE_FROM_EMPTY_CONTENT % FromFile)\r
 \r
-    if ReadOnly:\r
-        if not Executable:\r
-            chmod(ToFile, stat.S_IREAD)\r
+        if ReadOnly:\r
+            if not Executable:\r
+                chmod(ToFile, stat.S_IRUSR | stat.S_IRGRP | stat.S_IROTH)\r
+            else:\r
+                chmod(ToFile, stat.S_IRUSR | stat.S_IRGRP | stat.S_IROTH | stat.S_IEXEC | stat.S_IXGRP | stat.S_IXOTH)\r
+        elif Executable:\r
+            chmod(ToFile, stat.S_IRUSR | stat.S_IRGRP | stat.S_IROTH | stat.S_IWUSR | stat.S_IWGRP |\r
+                  stat.S_IWOTH | stat.S_IEXEC | stat.S_IXGRP | stat.S_IXOTH)\r
         else:\r
-            chmod(ToFile, stat.S_IREAD|stat.S_IEXEC)\r
-    elif Executable:\r
-        chmod(ToFile, stat.S_IREAD|stat.S_IWRITE|stat.S_IEXEC)\r
-    else:\r
-        chmod(ToFile, stat.S_IREAD|stat.S_IWRITE)\r
+            chmod(ToFile, stat.S_IRUSR | stat.S_IRGRP | stat.S_IROTH | stat.S_IWUSR | stat.S_IWGRP | stat.S_IWOTH)\r
                 \r
-    Md5Sigature = md5.new(open(str(ToFile), 'rb').read())\r
+    Md5Sigature = md5.new(__FileHookOpen__(str(ToFile), 'rb').read())\r
     Md5Sum = Md5Sigature.hexdigest()\r
+\r
     return Md5Sum\r
-        \r
+\r
 ## InstallPackageContent method\r
 #\r
 #   @param  FromPath: FromPath\r
@@ -701,10 +873,10 @@ def InstallPackageContent(FromPath, ToPath, Package, ContentZipFile, Dep,
             CreateDirectory(ToFile)\r
             continue\r
         if ReadOnly:\r
-            chmod(ToFile, stat.S_IREAD)\r
+            chmod(ToFile, stat.S_IRUSR|stat.S_IRGRP|stat.S_IROTH)\r
         else:\r
-            chmod(ToFile, stat.S_IREAD|stat.S_IWRITE)            \r
-        Md5Sigature = md5.new(open(str(ToFile), 'rb').read())\r
+            chmod(ToFile, stat.S_IRUSR|stat.S_IRGRP|stat.S_IROTH|stat.S_IWUSR|stat.S_IWGRP|stat.S_IWOTH)            \r
+        Md5Sigature = md5.new(__FileHookOpen__(str(ToFile), 'rb').read())\r
         Md5Sum = Md5Sigature.hexdigest()\r
         if (ToFile, Md5Sum) not in Package.FileList:\r
             Package.FileList.append((ToFile, Md5Sum))\r
@@ -768,3 +940,34 @@ def GetDPFile(ZipFile):
             ExtraData=ST.ERR_DIST_FILE_TOOFEW)\r
     return DescFile, ContentFile\r
 \r
+## InstallDp method\r
+#\r
+#   Install the distribution to current workspace\r
+#\r
+def InstallDp(DistPkg, DpPkgFileName, ContentZipFile, Options, Dep, WorkspaceDir, DataBase):\r
+    #\r
+    # PackageList, ModuleList record the information for the meta-data\r
+    # files that need to be generated later\r
+    #\r
+    PackageList = []\r
+    ModuleList = []\r
+    DistPkg.PackageSurfaceArea = GetPackageList(DistPkg, Dep, WorkspaceDir, Options, \r
+                                                ContentZipFile, ModuleList, PackageList)\r
+\r
+    DistPkg.ModuleSurfaceArea = GetModuleList(DistPkg, Dep, WorkspaceDir, ContentZipFile, ModuleList)\r
+    \r
+    GenToolMisc(DistPkg, WorkspaceDir, ContentZipFile)\r
+    \r
+    #\r
+    # copy "Distribution File" to directory $(WORKSPACE)/conf/upt\r
+    #\r
+    DistFileName = os.path.split(DpPkgFileName)[1]\r
+    NewDpPkgFileName = BackupDist(DpPkgFileName, DistPkg.Header.GetGuid(), DistPkg.Header.GetVersion(), WorkspaceDir)\r
+\r
+    #\r
+    # update database\r
+    #\r
+    Logger.Quiet(ST.MSG_UPDATE_PACKAGE_DATABASE)\r
+    DataBase.AddDPObject(DistPkg, NewDpPkgFileName, DistFileName, \r
+                   DistPkg.Header.RePackage)\r
+\r