]> git.proxmox.com Git - mirror_edk2.git/blame_incremental - BaseTools/Source/Python/UPT/UPT.py
BaseTools/UPT: Use a simple way to get package path
[mirror_edk2.git] / BaseTools / Source / Python / UPT / UPT.py
... / ...
CommitLineData
1## @file\r
2#\r
3# This file is the main entry for UPT \r
4#\r
5# Copyright (c) 2011 - 2017, Intel Corporation. All rights reserved.<BR>\r
6#\r
7# This program and the accompanying materials are licensed and made available \r
8# under the terms and conditions of the BSD License which accompanies this \r
9# distribution. The full text of the license may be found at \r
10# http://opensource.org/licenses/bsd-license.php\r
11#\r
12# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
13# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
14#\r
15\r
16'''\r
17UPT\r
18'''\r
19\r
20## import modules\r
21#\r
22from Core import FileHook\r
23import sys\r
24import os.path\r
25from sys import platform\r
26import platform as pf\r
27from optparse import OptionParser\r
28from traceback import format_exc\r
29from platform import python_version\r
30\r
31from Logger import StringTable as ST\r
32import Logger.Log as Logger\r
33from Logger.StringTable import MSG_VERSION\r
34from Logger.StringTable import MSG_DESCRIPTION\r
35from Logger.StringTable import MSG_USAGE\r
36from Logger.ToolError import FILE_NOT_FOUND\r
37from Logger.ToolError import OPTION_MISSING\r
38from Logger.ToolError import FILE_TYPE_MISMATCH\r
39from Logger.ToolError import OPTION_CONFLICT\r
40from Logger.ToolError import FatalError\r
41from Logger.ToolError import UPT_ALREADY_INSTALLED_ERROR\r
42from Common.MultipleWorkspace import MultipleWorkspace as mws\r
43\r
44import MkPkg\r
45import InstallPkg\r
46import RmPkg\r
47import InventoryWs\r
48import ReplacePkg\r
49import TestInstall\r
50from Library.Misc import GetWorkspace\r
51from Library import GlobalData\r
52from Core.IpiDb import IpiDatabase\r
53from BuildVersion import gBUILD_VERSION\r
54\r
55## CheckConflictOption\r
56#\r
57# CheckConflictOption\r
58#\r
59def CheckConflictOption(Opt):\r
60 if (Opt.PackFileToCreate or Opt.PackFileToInstall or Opt.PackFileToRemove or Opt.PackFileToReplace) \\r
61 and Opt.InventoryWs:\r
62 Logger.Error("UPT", OPTION_CONFLICT, ExtraData=ST.ERR_L_OA_EXCLUSIVE)\r
63 elif Opt.PackFileToReplace and (Opt.PackFileToCreate or Opt.PackFileToInstall or Opt.PackFileToRemove):\r
64 Logger.Error("UPT", OPTION_CONFLICT, ExtraData=ST.ERR_U_ICR_EXCLUSIVE)\r
65 elif (Opt.PackFileToCreate and Opt.PackFileToInstall and Opt.PackFileToRemove):\r
66 Logger.Error("UPT", OPTION_CONFLICT, ExtraData=ST.ERR_REQUIRE_I_C_R_OPTION)\r
67 elif Opt.PackFileToCreate and Opt.PackFileToInstall:\r
68 Logger.Error("UPT", OPTION_CONFLICT, ExtraData=ST.ERR_I_C_EXCLUSIVE)\r
69 elif Opt.PackFileToInstall and Opt.PackFileToRemove:\r
70 Logger.Error("UPT", OPTION_CONFLICT, ExtraData=ST.ERR_I_R_EXCLUSIVE)\r
71 elif Opt.PackFileToCreate and Opt.PackFileToRemove:\r
72 Logger.Error("UPT", OPTION_CONFLICT, ExtraData=ST.ERR_C_R_EXCLUSIVE)\r
73 elif Opt.TestDistFiles and (Opt.PackFileToCreate or Opt.PackFileToInstall \\r
74 or Opt.PackFileToRemove or Opt.PackFileToReplace):\r
75 Logger.Error("UPT", OPTION_CONFLICT, ExtraData=ST.ERR_C_R_EXCLUSIVE)\r
76\r
77 if Opt.CustomPath and Opt.UseGuidedPkgPath:\r
78 Logger.Warn("UPT", ST.WARN_CUSTOMPATH_OVERRIDE_USEGUIDEDPATH)\r
79 Opt.UseGuidedPkgPath = False\r
80\r
81## SetLogLevel\r
82#\r
83def SetLogLevel(Opt):\r
84 if Opt.opt_verbose:\r
85 Logger.SetLevel(Logger.VERBOSE)\r
86 elif Opt.opt_quiet:\r
87 Logger.SetLevel(Logger.QUIET + 1)\r
88 elif Opt.debug_level != None:\r
89 if Opt.debug_level < 0 or Opt.debug_level > 9:\r
90 Logger.Warn("UPT", ST.ERR_DEBUG_LEVEL)\r
91 Logger.SetLevel(Logger.INFO)\r
92 else:\r
93 Logger.SetLevel(Opt.debug_level + 1)\r
94 elif Opt.opt_slient:\r
95 Logger.SetLevel(Logger.SILENT)\r
96 else:\r
97 Logger.SetLevel(Logger.INFO)\r
98\r
99## Main\r
100#\r
101# Main\r
102#\r
103def Main():\r
104 Logger.Initialize()\r
105\r
106 Parser = OptionParser(version=(MSG_VERSION + ' Build ' + gBUILD_VERSION), description=MSG_DESCRIPTION,\r
107 prog="UPT.exe", usage=MSG_USAGE)\r
108\r
109 Parser.add_option("-d", "--debug", action="store", type="int", dest="debug_level", help=ST.HLP_PRINT_DEBUG_INFO)\r
110\r
111 Parser.add_option("-v", "--verbose", action="store_true", dest="opt_verbose",\r
112 help=ST.HLP_PRINT_INFORMATIONAL_STATEMENT)\r
113\r
114 Parser.add_option("-s", "--silent", action="store_true", dest="opt_slient", help=ST.HLP_RETURN_NO_DISPLAY)\r
115\r
116 Parser.add_option("-q", "--quiet", action="store_true", dest="opt_quiet", help=ST.HLP_RETURN_AND_DISPLAY)\r
117\r
118 Parser.add_option("-i", "--install", action="store", type="string", dest="Install_Distribution_Package_File",\r
119 help=ST.HLP_SPECIFY_PACKAGE_NAME_INSTALL)\r
120\r
121 Parser.add_option("-c", "--create", action="store", type="string", dest="Create_Distribution_Package_File",\r
122 help=ST.HLP_SPECIFY_PACKAGE_NAME_CREATE)\r
123\r
124 Parser.add_option("-r", "--remove", action="store", type="string", dest="Remove_Distribution_Package_File",\r
125 help=ST.HLP_SPECIFY_PACKAGE_NAME_REMOVE)\r
126\r
127 Parser.add_option("-t", "--template", action="store", type="string", dest="Package_Information_Data_File",\r
128 help=ST.HLP_SPECIFY_TEMPLATE_NAME_CREATE)\r
129\r
130 Parser.add_option("-p", "--dec-filename", action="append", type="string", dest="EDK2_DEC_Filename",\r
131 help=ST.HLP_SPECIFY_DEC_NAME_CREATE)\r
132\r
133 Parser.add_option("-m", "--inf-filename", action="append", type="string", dest="EDK2_INF_Filename",\r
134 help=ST.HLP_SPECIFY_INF_NAME_CREATE)\r
135\r
136 Parser.add_option("-l", "--list", action="store_true", dest="List_Dist_Installed",\r
137 help=ST.HLP_LIST_DIST_INSTALLED)\r
138\r
139 Parser.add_option("-f", "--force", action="store_true", dest="Yes", help=ST.HLP_DISABLE_PROMPT)\r
140\r
141 Parser.add_option("-n", "--custom-path", action="store_true", dest="CustomPath", help=ST.HLP_CUSTOM_PATH_PROMPT)\r
142\r
143 Parser.add_option("-x", "--free-lock", action="store_true", dest="SkipLock", help=ST.HLP_SKIP_LOCK_CHECK)\r
144\r
145 Parser.add_option("-u", "--replace", action="store", type="string", dest="Replace_Distribution_Package_File",\r
146 help=ST.HLP_SPECIFY_PACKAGE_NAME_REPLACE)\r
147\r
148 Parser.add_option("-o", "--original", action="store", type="string", dest="Original_Distribution_Package_File",\r
149 help=ST.HLP_SPECIFY_PACKAGE_NAME_TO_BE_REPLACED)\r
150\r
151 Parser.add_option("--use-guided-paths", action="store_true", dest="Use_Guided_Paths", help=ST.HLP_USE_GUIDED_PATHS)\r
152\r
153 Parser.add_option("-j", "--test-install", action="append", type="string",\r
154 dest="Test_Install_Distribution_Package_Files", help=ST.HLP_TEST_INSTALL)\r
155\r
156 Opt = Parser.parse_args()[0]\r
157\r
158 Var2Var = [\r
159 ("PackageInformationDataFile", Opt.Package_Information_Data_File),\r
160 ("PackFileToInstall", Opt.Install_Distribution_Package_File),\r
161 ("PackFileToCreate", Opt.Create_Distribution_Package_File),\r
162 ("PackFileToRemove", Opt.Remove_Distribution_Package_File),\r
163 ("PackageFileList", Opt.EDK2_DEC_Filename),\r
164 ("ModuleFileList", Opt.EDK2_INF_Filename),\r
165 ("InventoryWs", Opt.List_Dist_Installed),\r
166 ("PackFileToReplace", Opt.Replace_Distribution_Package_File),\r
167 ("PackFileToBeReplaced", Opt.Original_Distribution_Package_File),\r
168 ("UseGuidedPkgPath", Opt.Use_Guided_Paths),\r
169 ("TestDistFiles", Opt.Test_Install_Distribution_Package_Files)\r
170 ]\r
171\r
172 for Var in Var2Var:\r
173 setattr(Opt, Var[0], Var[1])\r
174\r
175 try:\r
176 GlobalData.gWORKSPACE, GlobalData.gPACKAGE_PATH = GetWorkspace()\r
177 except FatalError, XExcept:\r
178 if Logger.GetLevel() <= Logger.DEBUG_9:\r
179 Logger.Quiet(ST.MSG_PYTHON_ON % (python_version(), platform) + format_exc())\r
180 return XExcept.args[0]\r
181\r
182 # Support WORKSPACE is a long path\r
183 # Only works for windows system\r
184 if pf.system() == 'Windows':\r
185 Vol = 'B:'\r
186 for Index in range(90, 65, -1):\r
187 Vol = chr(Index) + ':'\r
188 if not os.path.isdir(Vol):\r
189 os.system('subst %s "%s"' % (Vol, GlobalData.gWORKSPACE))\r
190 break\r
191 GlobalData.gWORKSPACE = '%s\\' % Vol\r
192\r
193 WorkspaceDir = GlobalData.gWORKSPACE\r
194\r
195 SetLogLevel(Opt)\r
196\r
197 Mgr = FileHook.RecoverMgr(WorkspaceDir)\r
198 FileHook.SetRecoverMgr(Mgr)\r
199\r
200 GlobalData.gDB = IpiDatabase(os.path.normpath(os.path.join(WorkspaceDir, \\r
201 "Conf/DistributionPackageDatabase.db")), WorkspaceDir)\r
202 GlobalData.gDB.InitDatabase(Opt.SkipLock)\r
203\r
204 #\r
205 # Make sure the Db will get closed correctly\r
206 #\r
207 try:\r
208 ReturnCode = 0\r
209 CheckConflictOption(Opt)\r
210\r
211 RunModule = None\r
212 if Opt.PackFileToCreate:\r
213 if Opt.PackageInformationDataFile:\r
214 if not os.path.exists(Opt.PackageInformationDataFile):\r
215 if not os.path.exists(os.path.join(WorkspaceDir, Opt.PackageInformationDataFile)):\r
216 Logger.Error("\nUPT", FILE_NOT_FOUND, ST.ERR_NO_TEMPLATE_FILE % Opt.PackageInformationDataFile)\r
217 else:\r
218 Opt.PackageInformationDataFile = os.path.join(WorkspaceDir, Opt.PackageInformationDataFile)\r
219 else:\r
220 Logger.Error("UPT", OPTION_MISSING, ExtraData=ST.ERR_REQUIRE_T_OPTION)\r
221 if not Opt.PackFileToCreate.endswith('.dist'):\r
222 Logger.Error("CreatePkg", FILE_TYPE_MISMATCH, ExtraData=ST.ERR_DIST_EXT_ERROR % Opt.PackFileToCreate)\r
223 RunModule = MkPkg.Main\r
224\r
225 elif Opt.PackFileToInstall:\r
226 if not Opt.PackFileToInstall.endswith('.dist'):\r
227 Logger.Error("InstallPkg", FILE_TYPE_MISMATCH, ExtraData=ST.ERR_DIST_EXT_ERROR % Opt.PackFileToInstall)\r
228\r
229 AbsPath = GetFullPathDist(Opt.PackFileToInstall, WorkspaceDir)\r
230 if not AbsPath:\r
231 Logger.Error("InstallPkg", FILE_NOT_FOUND, ST.ERR_INSTALL_DIST_NOT_FOUND % Opt.PackFileToInstall)\r
232\r
233 Opt.PackFileToInstall = AbsPath\r
234 setattr(Opt, 'PackageFile', Opt.PackFileToInstall)\r
235 RunModule = InstallPkg.Main\r
236\r
237 elif Opt.PackFileToRemove:\r
238 if not Opt.PackFileToRemove.endswith('.dist'):\r
239 Logger.Error("RemovePkg", FILE_TYPE_MISMATCH, ExtraData=ST.ERR_DIST_EXT_ERROR % Opt.PackFileToRemove)\r
240 head, tail = os.path.split(Opt.PackFileToRemove)\r
241 if head or not tail:\r
242 Logger.Error("RemovePkg",\r
243 FILE_TYPE_MISMATCH,\r
244 ExtraData=ST.ERR_DIST_FILENAME_ONLY_FOR_REMOVE % Opt.PackFileToRemove)\r
245\r
246 setattr(Opt, 'DistributionFile', Opt.PackFileToRemove)\r
247 RunModule = RmPkg.Main\r
248 elif Opt.InventoryWs:\r
249 RunModule = InventoryWs.Main\r
250\r
251 elif Opt.PackFileToBeReplaced and not Opt.PackFileToReplace:\r
252 Logger.Error("ReplacePkg", OPTION_MISSING, ExtraData=ST.ERR_REQUIRE_U_OPTION)\r
253\r
254 elif Opt.PackFileToReplace:\r
255 if not Opt.PackFileToReplace.endswith('.dist'):\r
256 Logger.Error("ReplacePkg", FILE_TYPE_MISMATCH, ExtraData=ST.ERR_DIST_EXT_ERROR % Opt.PackFileToReplace)\r
257 if not Opt.PackFileToBeReplaced:\r
258 Logger.Error("ReplacePkg", OPTION_MISSING, ExtraData=ST.ERR_REQUIRE_O_OPTION)\r
259 if not Opt.PackFileToBeReplaced.endswith('.dist'):\r
260 Logger.Error("ReplacePkg",\r
261 FILE_TYPE_MISMATCH,\r
262 ExtraData=ST.ERR_DIST_EXT_ERROR % Opt.PackFileToBeReplaced)\r
263\r
264 head, tail = os.path.split(Opt.PackFileToBeReplaced)\r
265 if head or not tail:\r
266 Logger.Error("ReplacePkg",\r
267 FILE_TYPE_MISMATCH,\r
268 ExtraData=ST.ERR_DIST_FILENAME_ONLY_FOR_REPLACE_ORIG % Opt.PackFileToBeReplaced)\r
269\r
270 AbsPath = GetFullPathDist(Opt.PackFileToReplace, WorkspaceDir)\r
271 if not AbsPath:\r
272 Logger.Error("ReplacePkg", FILE_NOT_FOUND, ST.ERR_REPLACE_DIST_NOT_FOUND % Opt.PackFileToReplace)\r
273\r
274 Opt.PackFileToReplace = AbsPath\r
275 RunModule = ReplacePkg.Main\r
276\r
277 elif Opt.Test_Install_Distribution_Package_Files:\r
278 for Dist in Opt.Test_Install_Distribution_Package_Files:\r
279 if not Dist.endswith('.dist'):\r
280 Logger.Error("TestInstall", FILE_TYPE_MISMATCH, ExtraData=ST.ERR_DIST_EXT_ERROR % Dist)\r
281\r
282 setattr(Opt, 'DistFiles', Opt.Test_Install_Distribution_Package_Files)\r
283 RunModule = TestInstall.Main\r
284\r
285 else:\r
286 Parser.print_usage()\r
287 return OPTION_MISSING\r
288\r
289 ReturnCode = RunModule(Opt)\r
290 except FatalError, XExcept:\r
291 ReturnCode = XExcept.args[0]\r
292 if Logger.GetLevel() <= Logger.DEBUG_9:\r
293 Logger.Quiet(ST.MSG_PYTHON_ON % (python_version(), platform) + \\r
294 format_exc())\r
295 finally:\r
296 try:\r
297 if ReturnCode != 0 and ReturnCode != UPT_ALREADY_INSTALLED_ERROR:\r
298 Logger.Quiet(ST.MSG_RECOVER_START)\r
299 GlobalData.gDB.RollBack()\r
300 Mgr.rollback()\r
301 Logger.Quiet(ST.MSG_RECOVER_DONE)\r
302 else:\r
303 GlobalData.gDB.Commit()\r
304 Mgr.commit()\r
305 except StandardError:\r
306 Logger.Quiet(ST.MSG_RECOVER_FAIL)\r
307 GlobalData.gDB.CloseDb()\r
308\r
309 if pf.system() == 'Windows':\r
310 os.system('subst %s /D' % GlobalData.gWORKSPACE.replace('\\',''))\r
311\r
312 return ReturnCode\r
313\r
314## GetFullPathDist\r
315#\r
316# This function will check DistFile existence, if not absolute path, then try current working directory,\r
317# then $(WORKSPACE),and return the AbsPath. If file doesn't find, then return None\r
318#\r
319# @param DistFile: The distribution file in either relative path or absolute path\r
320# @param WorkspaceDir: Workspace Directory\r
321# @return AbsPath: The Absolute path of the distribution file if existed, None else\r
322#\r
323def GetFullPathDist(DistFile, WorkspaceDir):\r
324 if os.path.isabs(DistFile):\r
325 if not (os.path.exists(DistFile) and os.path.isfile(DistFile)):\r
326 return None\r
327 else:\r
328 return DistFile\r
329 else:\r
330 AbsPath = os.path.normpath(os.path.join(os.getcwd(), DistFile))\r
331 if not (os.path.exists(AbsPath) and os.path.isfile(AbsPath)):\r
332 AbsPath = os.path.normpath(os.path.join(WorkspaceDir, DistFile))\r
333 if not (os.path.exists(AbsPath) and os.path.isfile(AbsPath)):\r
334 return None\r
335\r
336 return AbsPath\r
337\r
338if __name__ == '__main__':\r
339 RETVAL = Main()\r
340 #\r
341 # 0-127 is a safe return range, and 1 is a standard default error\r
342 #\r
343 if RETVAL < 0 or RETVAL > 127:\r
344 RETVAL = 1\r
345 sys.exit(RETVAL)\r