]> git.proxmox.com Git - mirror_edk2.git/blame - Tools/Java/Source/FrameworkTasks/org/tianocore/framework/tasks/GenFvImageTask.java
Restructuring for better separation of Tool packages.
[mirror_edk2.git] / Tools / Java / Source / FrameworkTasks / org / tianocore / framework / tasks / GenFvImageTask.java
CommitLineData
878ddf1f 1/** @file\r
2 GenFvImageTask class.\r
3\r
4 GenFvImageTask is to call GenFvImage.exe to generate FvImage.\r
5 \r
6 Copyright (c) 2006, Intel Corporation\r
7 All rights reserved. This program and the accompanying materials\r
8 are licensed and made available under the terms and conditions of the BSD License\r
9 which accompanies this 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
16package org.tianocore.framework.tasks;\r
878ddf1f 17\r
18import org.apache.tools.ant.BuildException;\r
19import org.apache.tools.ant.Project;\r
20import org.apache.tools.ant.Task;\r
93f5dd0a 21import org.apache.tools.ant.taskdefs.Execute;\r
22import org.apache.tools.ant.taskdefs.LogStreamHandler;\r
23import org.apache.tools.ant.types.Commandline;\r
878ddf1f 24\r
a236f1a1 25import java.io.File;\r
d946661a 26import java.util.LinkedList;\r
27import java.util.regex.Matcher;\r
28import java.util.regex.Pattern;\r
29import java.util.List;\r
d946661a 30import java.util.Iterator;\r
31import java.io.BufferedReader;\r
32import java.io.FileReader;\r
a236f1a1 33\r
93f5dd0a 34import org.tianocore.common.logger.EdkLog;\r
35\r
878ddf1f 36/**\r
37 GenFvImageTask\r
38 \r
39 GenFvImageTask is to call GenFvImage.exe to generate the FvImage.\r
40 \r
41**/\r
42public class GenFvImageTask extends Task implements EfiDefine{\r
93f5dd0a 43 //\r
44 // tool name\r
45 //\r
a236f1a1 46 static final private String toolName = "GenFvImage";\r
93f5dd0a 47 //\r
d946661a 48 // Pattern to match the section header (e.g. [options], [files])\r
49 // \r
50 static final private Pattern sectionHeader = Pattern.compile("\\[([^\\[\\]]+)\\]");\r
51 //\r
93f5dd0a 52 // The name of input inf file\r
53 //\r
54 private FileArg infFile = new FileArg();\r
55 //\r
56 // Output directory\r
57 //\r
a236f1a1 58 private String outputDir = ".";\r
a236f1a1 59\r
878ddf1f 60 /**\r
61 execute\r
62 \r
63 GenFvImageTask execute is to assemble tool command line & execute tool\r
64 command line.\r
65 **/\r
66 public void execute() throws BuildException {\r
67 Project project = this.getOwningTarget().getProject();\r
2da8968b 68 String path = project.getProperty("env.FRAMEWORK_TOOLS_PATH");\r
a236f1a1 69\r
d946661a 70 if (isUptodate()) {\r
71 EdkLog.log(this, EdkLog.EDK_VERBOSE, infFile.toFileList() + " is uptodate!");\r
72 return;\r
73 }\r
74\r
93f5dd0a 75 String command;\r
a236f1a1 76 if (path == null) {\r
93f5dd0a 77 command = toolName;\r
a236f1a1 78 } else {\r
93f5dd0a 79 command = path + File.separator + toolName;\r
878ddf1f 80 }\r
8742c000 81\r
93f5dd0a 82 String argument = "" + infFile;\r
83 //\r
84 // lauch the program\r
85 //\r
a236f1a1 86 int exitCode = 0;\r
878ddf1f 87 try {\r
93f5dd0a 88 Commandline cmdline = new Commandline();\r
89 cmdline.setExecutable(command);\r
90 cmdline.createArgument().setLine(argument);\r
91\r
92 LogStreamHandler streamHandler = new LogStreamHandler(this,\r
93 Project.MSG_INFO, Project.MSG_WARN);\r
94 Execute runner = new Execute(streamHandler, null);\r
a236f1a1 95\r
93f5dd0a 96 runner.setAntRun(project);\r
97 runner.setCommandline(cmdline.getCommandline());\r
98 runner.setWorkingDirectory(new File(outputDir)); \r
99 //\r
100 // log command line string.\r
101 //\r
102 EdkLog.log(this, EdkLog.EDK_VERBOSE, Commandline.toString(cmdline.getCommandline()));\r
103 EdkLog.log(this, infFile.toFileList());\r
104\r
105 exitCode = runner.execute();\r
a236f1a1 106 if (exitCode != 0) {\r
93f5dd0a 107 EdkLog.log(this, "ERROR = " + Integer.toHexString(exitCode));\r
878ddf1f 108 } else {\r
93f5dd0a 109 EdkLog.log(this, EdkLog.EDK_VERBOSE, "GenFvImage succeeded!");\r
878ddf1f 110 }\r
878ddf1f 111 } catch (Exception e) {\r
a236f1a1 112 throw new BuildException(e.getMessage());\r
113 } finally {\r
114 if (exitCode != 0) {\r
c59963f5 115 throw new BuildException("GenFvImage: failed to generate FV file!");\r
a236f1a1 116 }\r
117 }\r
878ddf1f 118 }\r
119 /**\r
120 getInfFile\r
121 \r
122 This function is to get class member of infFile\r
123 @return String name of infFile\r
124 **/\r
125 public String getInfFile() {\r
93f5dd0a 126 return infFile.getValue();\r
878ddf1f 127 }\r
128 \r
129 /**\r
130 setInfFile\r
131 \r
132 This function is to set class member of infFile.\r
133 \r
134 @param infFile name of infFile\r
135 **/\r
136 public void setInfFile(String infFile) {\r
93f5dd0a 137 this.infFile.setArg(" -I ", infFile);\r
878ddf1f 138 }\r
139 \r
a236f1a1 140 /**\r
141 getOutputDir\r
142 \r
143 This function is to get output directory.\r
144 \r
145 @return Path of output directory.\r
146 **/\r
147 public String getOutputDir() {\r
148 return outputDir;\r
149 }\r
150\r
151 /**\r
152 setOutputDir\r
153 \r
154 This function is to set output directory.\r
155 \r
156 @param outputDir The output direcotry.\r
157 **/\r
158 public void setOutputDir(String outputDir) {\r
159 this.outputDir = outputDir;\r
160 }\r
d946661a 161\r
162 //\r
163 // dependency check\r
164 // \r
165 private boolean isUptodate() {\r
166 String infName = this.infFile.getValue();\r
167 String fvName = "";\r
168 List<String> ffsFiles = new LinkedList<String>();\r
169 File inf = new File(infName);\r
170\r
171 try {\r
172 FileReader reader = new FileReader(inf);\r
173 BufferedReader in = new BufferedReader(reader);\r
174 String str;\r
175\r
176 //\r
177 // Read the inf file line by line\r
178 // \r
179 boolean inFiles = false;\r
180 boolean inOptions = false;\r
181 while ((str = in.readLine()) != null) {\r
182 str = str.trim();\r
183 if (str.length() == 0) {\r
184 continue;\r
185 }\r
186\r
187 Matcher matcher = sectionHeader.matcher(str);\r
188 if (matcher.find()) {\r
189 //\r
190 // We take care of only "options" and "files" section\r
191 // \r
192 String sectionName = str.substring(matcher.start(1), matcher.end(1));\r
193 if (sectionName.equalsIgnoreCase("options")) {\r
194 inOptions = true;\r
195 inFiles = false;\r
196 } else if (sectionName.equalsIgnoreCase("files")) {\r
197 inFiles = true;\r
198 inOptions = false;\r
199 } else {\r
200 inFiles = false;\r
201 inOptions = false;\r
202 }\r
203 continue;\r
204 }\r
205\r
206 //\r
207 // skip invalid line\r
208 // \r
209 int equalMarkPos = str.indexOf("=");\r
210 if (equalMarkPos < 0) {\r
211 continue;\r
212 }\r
213\r
214 //\r
215 // we have only interest in EFI_FILE_NAME\r
216 // \r
217 String fileNameFlag = str.substring(0, equalMarkPos).trim();\r
218 String fileName = str.substring(equalMarkPos + 1).trim();\r
219 if (!fileNameFlag.equalsIgnoreCase("EFI_FILE_NAME")\r
220 || fileName.length() == 0) {\r
221 continue;\r
222 }\r
223\r
224 if (inFiles) {\r
225 //\r
226 // files specified beneath the [files] section are source files\r
227 // \r
228 ffsFiles.add(fileName);\r
229 } else if (inOptions) {\r
230 //\r
231 // file specified beneath the [options] section is the target file\r
232 // \r
233 fvName = outputDir + File.separator + fileName;\r
234 }\r
235 }\r
236 } catch (Exception ex) {\r
237 throw new BuildException(ex.getMessage());\r
238 }\r
239\r
240 //\r
241 // if destionation file doesn't exist, we need to generate it.\r
242 // \r
243 File fvFile = new File(fvName);\r
244 if (!fvFile.exists()) {\r
245 EdkLog.log(this, EdkLog.EDK_VERBOSE, fvName + " doesn't exist!");\r
246 return false;\r
247 }\r
248\r
249 //\r
250 // the inf file itself will be taken as source file, check its timestamp\r
251 // against the target file\r
252 // \r
253 long fvFileTimeStamp = fvFile.lastModified();\r
254 if (inf.lastModified() > fvFileTimeStamp) {\r
255 EdkLog.log(this, EdkLog.EDK_VERBOSE, infName + " has been changed since last build!");\r
256 return false;\r
257 }\r
258\r
259 //\r
260 // no change in the inf file, we need to check each source files in it\r
261 // against the target file\r
262 // \r
263 for (Iterator it = ffsFiles.iterator(); it.hasNext(); ) {\r
264 String fileName = (String)it.next();\r
265 File file = new File(fileName);\r
266 if (file.lastModified() > fvFileTimeStamp) {\r
267 EdkLog.log(this, EdkLog.EDK_VERBOSE, fileName + " has been changed since last build!");\r
268 return false;\r
269 }\r
270 }\r
271\r
272 return true;\r
273 }\r
8742c000 274}\r