3 Copyright (c) 2006, Intel Corporation
4 All rights reserved. This program and the accompanying materials
5 are licensed and made available under the terms and conditions of the BSD License
6 which accompanies this distribution. The full text of the license may be found at
7 http://opensource.org/licenses/bsd-license.php
9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
12 package org
.tianocore
.build
.fpd
;
15 import java
.util
.HashMap
;
16 import java
.util
.Iterator
;
20 import javax
.xml
.parsers
.DocumentBuilder
;
21 import javax
.xml
.parsers
.DocumentBuilderFactory
;
22 import javax
.xml
.transform
.OutputKeys
;
23 import javax
.xml
.transform
.Result
;
24 import javax
.xml
.transform
.Source
;
25 import javax
.xml
.transform
.Transformer
;
26 import javax
.xml
.transform
.TransformerFactory
;
27 import javax
.xml
.transform
.dom
.DOMSource
;
28 import javax
.xml
.transform
.stream
.StreamResult
;
30 import org
.apache
.tools
.ant
.BuildException
;
31 import org
.apache
.tools
.ant
.Project
;
32 import org
.tianocore
.build
.global
.GlobalData
;
33 import org
.tianocore
.build
.global
.SurfaceAreaQuery
;
34 import org
.tianocore
.build
.id
.FpdModuleIdentification
;
35 import org
.tianocore
.build
.id
.ModuleIdentification
;
36 import org
.w3c
.dom
.Comment
;
37 import org
.w3c
.dom
.Document
;
38 import org
.w3c
.dom
.Element
;
39 import org
.w3c
.dom
.NamedNodeMap
;
40 import org
.w3c
.dom
.Node
;
41 import org
.w3c
.dom
.NodeList
;
44 class PlatformBuildFileGenerator is used to generate ${PLATFORM}_build.xml file.
48 public class PlatformBuildFileGenerator
{
50 private String platformName
;
53 /// Mapping from modules identification to out put file name
55 private Map
<FpdModuleIdentification
, String
> outfiles
;
58 /// Mapping from FV name to its modules
60 private Map
<String
, Set
<FpdModuleIdentification
>> fvs
= new HashMap
<String
, Set
<FpdModuleIdentification
>>();
63 private boolean isUnified
= true;
65 private Project project
;
67 private String info
= "DO NOT EDIT \n"
68 + "This file is auto-generated by the build utility\n"
71 + "Auto-generated ANT build file for building EFI Modules and Platforms\n";
73 public PlatformBuildFileGenerator(Project project
, Map
<FpdModuleIdentification
, String
> outfiles
, Map
<String
, Set
<FpdModuleIdentification
>> fvs
, boolean isUnified
){
74 this.project
= project
;
75 this.outfiles
= outfiles
;
76 this.isUnified
= isUnified
;
78 this.platformName
= project
.getProperty("PLATFORM");
82 Generate build.out.xml file.
84 @throws BuildException
85 build.out.xml XML document create error
87 public void genBuildFile() throws BuildException
{
88 DocumentBuilderFactory domfac
= DocumentBuilderFactory
.newInstance();
90 DocumentBuilder dombuilder
= domfac
.newDocumentBuilder();
91 Document document
= dombuilder
.newDocument();
92 Comment rootComment
= document
.createComment(info
);
94 // create root element and its attributes
96 Element root
= document
.createElement("project");
97 root
.setAttribute("name", project
.getProperty("PLATFORM"));
98 root
.setAttribute("default", "all");
99 root
.setAttribute("basedir", ".");
102 // element for External ANT tasks
104 root
.appendChild(document
.createComment("Apply external ANT tasks"));
105 Element ele
= document
.createElement("taskdef");
106 ele
.setAttribute("resource", "GenBuild.tasks");
107 root
.appendChild(ele
);
109 ele
= document
.createElement("taskdef");
110 ele
.setAttribute("resource", "frameworktasks.tasks");
111 root
.appendChild(ele
);
113 ele
= document
.createElement("taskdef");
114 ele
.setAttribute("resource", "net/sf/antcontrib/antlib.xml");
115 root
.appendChild(ele
);
117 ele
= document
.createElement("property");
118 ele
.setAttribute("environment", "env");
119 root
.appendChild(ele
);
124 root
.appendChild(document
.createComment("Default target"));
125 ele
= document
.createElement("target");
126 ele
.setAttribute("name", "all");
127 ele
.setAttribute("depends", "prebuild, modules, fvs, postbuild");
128 root
.appendChild(ele
);
131 // Modules and Fvs Target
133 applyModules(document
, root
);
135 applyFvs(document
, root
);
140 applyClean(document
, root
);
145 applyCleanall(document
, root
);
148 // User Extension pre build
150 applyUserExtensionsPreBuild(document
, root
);
153 // User Extension Post build
155 applyUserExtensionsPostBuild(document
, root
);
157 document
.appendChild(rootComment
);
158 document
.appendChild(root
);
160 // Prepare the DOM document for writing
162 Source source
= new DOMSource(document
);
164 // Prepare the output file
166 File file
= new File(project
.getProperty("PLATFORM_DIR") + File
.separatorChar
+ platformName
+ "_build.xml");
168 // generate all directory path
170 (new File(file
.getParent())).mkdirs();
171 Result result
= new StreamResult(file
);
173 // Write the DOM document to the file
175 Transformer xformer
= TransformerFactory
.newInstance().newTransformer();
176 xformer
.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "2");
177 xformer
.setOutputProperty(OutputKeys
.INDENT
, "yes");
178 xformer
.transform(source
, result
);
179 } catch (Exception ex
) {
180 throw new BuildException("Generation of the " + platformName
+ "_build.xml failed!\n" + ex
.getMessage());
185 1. Get All valid Fv Image Names in sequence
186 2. For each FV, get modules by sequences
189 @param document XML document
192 private void applyModules(Document document
, Node root
) {
193 root
.appendChild(document
.createComment("Modules target"));
194 Element ele
= document
.createElement("target");
195 ele
.setAttribute("name", "modules");
198 // Get all valid FV name
200 String
[] validFv
= SurfaceAreaQuery
.getFpdValidImageNames();
203 // For each valid FV, get all modules in sequence
205 for (int i
= 0; i
< validFv
.length
; i
++) {
206 if (fvs
.containsKey(validFv
[i
])) {
207 Set
<FpdModuleIdentification
> set
= fvs
.get(validFv
[i
]);
208 Iterator
<FpdModuleIdentification
> iter
= set
.iterator();
209 while (iter
.hasNext()) {
210 FpdModuleIdentification fpdModuleId
= iter
.next();
211 applySingleModule(document
, ele
, fpdModuleId
);
217 // Get all other modules
219 Iterator
<String
> fvsNameIter
= fvs
.keySet().iterator();
221 while (fvsNameIter
.hasNext()) {
222 String fvName
= fvsNameIter
.next();
223 if (!isContain(validFv
, fvName
)) {
224 Set
<FpdModuleIdentification
> set
= fvs
.get(fvName
);
225 Iterator iter
= set
.iterator();
226 while (iter
.hasNext()) {
227 FpdModuleIdentification fpdModuleId
= (FpdModuleIdentification
) iter
.next();
228 applySingleModule(document
, ele
, fpdModuleId
);
233 root
.appendChild(ele
);
236 private void applySingleModule(Document document
, Node root
, FpdModuleIdentification fpdModuleId
) {
237 ModuleIdentification moduleId
= fpdModuleId
.getModule();
238 Element moduleEle
= document
.createElement("GenBuild");
239 moduleEle
.setAttribute("type", "build");
241 // Inherit Properties.
242 //{"ARCH", "PACKAGE", "PACKAGE_GUID", "PACKAGE_VERSION", "MODULE_DIR"}
248 Element property
= document
.createElement("property");
249 property
.setAttribute("name", "ARCH");
250 property
.setAttribute("value", fpdModuleId
.getArch());
251 moduleEle
.appendChild(property
);
256 property
= document
.createElement("property");
257 property
.setAttribute("name", "MODULE_GUID");
258 property
.setAttribute("value", moduleId
.getGuid());
259 moduleEle
.appendChild(property
);
264 property
= document
.createElement("property");
265 property
.setAttribute("name", "MODULE_VERSION");
266 property
.setAttribute("value", moduleId
.getVersion());
267 moduleEle
.appendChild(property
);
272 property
= document
.createElement("property");
273 property
.setAttribute("name", "PACKAGE_GUID");
274 property
.setAttribute("value", moduleId
.getPackage().getGuid());
275 moduleEle
.appendChild(property
);
280 property
= document
.createElement("property");
281 property
.setAttribute("name", "PACKAGE_VERSION");
282 property
.setAttribute("value", moduleId
.getPackage().getVersion());
283 moduleEle
.appendChild(property
);
285 root
.appendChild(moduleEle
);
288 private boolean isContain(String
[] list
, String item
) {
289 for (int i
= 0; i
< list
.length
; i
++) {
290 if (list
[i
].equalsIgnoreCase(item
)) {
297 private void applyFvs(Document document
, Node root
) {
301 root
.appendChild(document
.createComment("FVs target"));
302 Element ele
= document
.createElement("target");
303 ele
.setAttribute("name", "fvs");
306 // For every Target and ToolChain
308 String
[] targetList
= GlobalData
.getToolChainInfo().getTargets();
309 for (int i
= 0; i
< targetList
.length
; i
++){
310 String
[] toolchainList
= GlobalData
.getToolChainInfo().getTagnames();
311 for(int j
= 0; j
< toolchainList
.length
; j
++){
312 String fvOutputDir
= project
.getProperty("BUILD_DIR") + File
.separatorChar
313 + targetList
[i
] + "_"
314 + toolchainList
[j
] + File
.separatorChar
+ "FV";
315 String
[] validFv
= SurfaceAreaQuery
.getFpdValidImageNames();
316 for (int k
= 0; k
< validFv
.length
; k
++) {
317 String inputFile
= fvOutputDir
+ "" + File
.separatorChar
+ validFv
[k
].toUpperCase() + ".inf";
318 Element fvEle
= document
.createElement("genfvimage");
319 fvEle
.setAttribute("infFile", inputFile
);
320 fvEle
.setAttribute("outputDir", fvOutputDir
);
321 ele
.appendChild(fvEle
);
325 root
.appendChild(ele
);
328 private void applyClean(Document document
, Node root
) {
332 root
.appendChild(document
.createComment("Clean target"));
333 Element ele
= document
.createElement("target");
334 ele
.setAttribute("name", "clean");
337 Element cleanEle
= document
.createElement("delete");
338 cleanEle
.setAttribute("includeemptydirs", "true");
339 Element filesetEle
= document
.createElement("fileset");
340 filesetEle
.setAttribute("dir", project
.getProperty("BUILD_DIR"));
341 filesetEle
.setAttribute("includes", "**\\OUTPUT\\**");
342 cleanEle
.appendChild(filesetEle
);
343 ele
.appendChild(cleanEle
);
345 Set set
= outfiles
.keySet();
346 Iterator iter
= set
.iterator();
347 while (iter
.hasNext()) {
348 FpdModuleIdentification fpdModuleId
= (FpdModuleIdentification
) iter
.next();
349 ModuleIdentification moduleId
= fpdModuleId
.getModule();
351 Element ifEle
= document
.createElement("if");
352 Element availableEle
= document
.createElement("available");
353 availableEle
.setAttribute("file", moduleId
.getMsaFile().getParent() + File
.separatorChar
355 ifEle
.appendChild(availableEle
);
356 Element elseEle
= document
.createElement("then");
358 Element moduleEle
= document
.createElement("ant");
359 moduleEle
.setAttribute("antfile", moduleId
.getMsaFile().getParent() + File
.separatorChar
361 moduleEle
.setAttribute("target", "clean");
363 // Inherit Properties.
364 //{"ARCH", "PACKAGE", "PACKAGE_GUID", "PACKAGE_VERSION", "MODULE_DIR"}
370 Element property
= document
.createElement("property");
371 property
.setAttribute("name", "ARCH");
372 property
.setAttribute("value", fpdModuleId
.getArch());
373 moduleEle
.appendChild(property
);
378 property
= document
.createElement("property");
379 property
.setAttribute("name", "PACKAGE");
380 property
.setAttribute("value", moduleId
.getPackage().getName());
381 moduleEle
.appendChild(property
);
386 property
= document
.createElement("property");
387 property
.setAttribute("name", "PACKAGE_GUID");
388 property
.setAttribute("value", moduleId
.getPackage().getGuid());
389 moduleEle
.appendChild(property
);
394 property
= document
.createElement("property");
395 property
.setAttribute("name", "PACKAGE_VERSION");
396 property
.setAttribute("value", moduleId
.getPackage().getVersion());
397 moduleEle
.appendChild(property
);
402 property
= document
.createElement("property");
403 property
.setAttribute("name", "MODULE_DIR");
404 property
.setAttribute("value", moduleId
.getMsaFile().getParent());
405 moduleEle
.appendChild(property
);
406 elseEle
.appendChild(moduleEle
);
407 ifEle
.appendChild(elseEle
);
408 ele
.appendChild(ifEle
);
411 root
.appendChild(ele
);
414 private void applyCleanall(Document document
, Node root
) {
418 root
.appendChild(document
.createComment("Target: cleanall"));
419 Element ele
= document
.createElement("target");
420 ele
.setAttribute("name", "cleanall");
423 String
[] targetList
= GlobalData
.getToolChainInfo().getTargets();
424 for (int i
= 0; i
< targetList
.length
; ++i
) {
425 String
[] toolchainList
= GlobalData
.getToolChainInfo().getTagnames();
426 for(int j
= 0; j
< toolchainList
.length
; j
++) {
427 Element cleanAllEle
= document
.createElement("delete");
428 cleanAllEle
.setAttribute("dir", project
.getProperty("BUILD_DIR") + File
.separatorChar
+ targetList
[i
] + "_" + toolchainList
[j
]);
429 ele
.appendChild(cleanAllEle
);
433 Set set
= outfiles
.keySet();
434 Iterator iter
= set
.iterator();
435 while (iter
.hasNext()) {
436 FpdModuleIdentification fpdModuleId
= (FpdModuleIdentification
) iter
.next();
437 ModuleIdentification moduleId
= fpdModuleId
.getModule();
439 Element ifEle
= document
.createElement("if");
440 Element availableEle
= document
.createElement("available");
441 availableEle
.setAttribute("file", moduleId
.getMsaFile().getParent() + File
.separatorChar
443 ifEle
.appendChild(availableEle
);
444 Element elseEle
= document
.createElement("then");
446 Element moduleEle
= document
.createElement("ant");
447 moduleEle
.setAttribute("antfile", moduleId
.getMsaFile().getParent() + File
.separatorChar
449 moduleEle
.setAttribute("target", "cleanall");
451 // Inherit Properties.
452 //{"ARCH", "PACKAGE", "PACKAGE_GUID", "PACKAGE_VERSION", "MODULE_DIR"}
458 Element property
= document
.createElement("property");
459 property
.setAttribute("name", "ARCH");
460 property
.setAttribute("value", fpdModuleId
.getArch());
461 moduleEle
.appendChild(property
);
466 property
= document
.createElement("property");
467 property
.setAttribute("name", "PACKAGE");
468 property
.setAttribute("value", moduleId
.getPackage().getName());
469 moduleEle
.appendChild(property
);
474 property
= document
.createElement("property");
475 property
.setAttribute("name", "PACKAGE_GUID");
476 property
.setAttribute("value", moduleId
.getPackage().getGuid());
477 moduleEle
.appendChild(property
);
482 property
= document
.createElement("property");
483 property
.setAttribute("name", "PACKAGE_VERSION");
484 property
.setAttribute("value", moduleId
.getPackage().getVersion());
485 moduleEle
.appendChild(property
);
490 property
= document
.createElement("property");
491 property
.setAttribute("name", "MODULE_DIR");
492 property
.setAttribute("value", moduleId
.getMsaFile().getParent());
493 moduleEle
.appendChild(property
);
494 elseEle
.appendChild(moduleEle
);
495 ifEle
.appendChild(elseEle
);
496 ele
.appendChild(ifEle
);
499 root
.appendChild(ele
);
502 private void applyUserExtensionsPreBuild(Document document
, Node root
) {
506 root
.appendChild(document
.createComment("Pre-Build Processing"));
507 Element ele
= document
.createElement("target");
508 ele
.setAttribute("name", "prebuild");
510 Node node
= SurfaceAreaQuery
.getFpdUserExtensionPreBuild();
513 // For every Target and ToolChain
515 String
[] targetList
= GlobalData
.getToolChainInfo().getTargets();
516 for (int i
= 0; i
< targetList
.length
; i
++){
517 String
[] toolchainList
= GlobalData
.getToolChainInfo().getTagnames();
518 for(int j
= 0; j
< toolchainList
.length
; j
++){
522 String ffsCommonDir
= project
.getProperty("BUILD_DIR") + File
.separatorChar
523 + targetList
[i
] + "_"
525 File fvDir
= new File(ffsCommonDir
+ File
.separatorChar
+ "FV");
526 Element fvEle
= document
.createElement("var");
527 fvEle
.setAttribute("name", "FV_DIR");
528 fvEle
.setAttribute("value", fvDir
.getPath().replaceAll("(\\\\)", "/"));
529 ele
.appendChild(fvEle
);
531 NodeList childNodes
= node
.getChildNodes();
532 for (int k
= 0; k
< childNodes
.getLength(); k
++) {
533 Node childItem
= childNodes
.item(k
);
534 if (childItem
.getNodeType() == Node
.ELEMENT_NODE
) {
535 ele
.appendChild(recursiveNode(childItem
, document
));
543 root
.appendChild(ele
);
546 private void applyUserExtensionsPostBuild(Document document
, Node root
) {
550 root
.appendChild(document
.createComment("Post-Build Processing"));
551 Element ele
= document
.createElement("target");
552 ele
.setAttribute("name", "postbuild");
554 Node node
= SurfaceAreaQuery
.getFpdUserExtensionPostBuild();
557 // For every Target and ToolChain
559 String
[] targetList
= GlobalData
.getToolChainInfo().getTargets();
560 for (int i
= 0; i
< targetList
.length
; i
++){
561 String
[] toolchainList
= GlobalData
.getToolChainInfo().getTagnames();
562 for(int j
= 0; j
< toolchainList
.length
; j
++){
566 String ffsCommonDir
= project
.getProperty("BUILD_DIR") + File
.separatorChar
567 + targetList
[i
] + "_"
569 File fvDir
= new File(ffsCommonDir
+ File
.separatorChar
+ "FV");
570 Element fvEle
= document
.createElement("var");
571 fvEle
.setAttribute("name", "FV_DIR");
572 fvEle
.setAttribute("value", fvDir
.getPath().replaceAll("(\\\\)", "/"));
573 ele
.appendChild(fvEle
);
575 NodeList childNodes
= node
.getChildNodes();
576 for (int k
= 0; k
< childNodes
.getLength(); k
++) {
577 Node childItem
= childNodes
.item(k
);
578 if (childItem
.getNodeType() == Node
.ELEMENT_NODE
) {
579 ele
.appendChild(recursiveNode(childItem
, document
));
587 root
.appendChild(ele
);
590 private Element
recursiveNode(Node node
, Document document
) {
591 Element root
= document
.createElement(node
.getNodeName());
592 NamedNodeMap attr
= node
.getAttributes();
593 for (int i
= 0; i
< attr
.getLength(); i
++) {
594 Node attrItem
= attr
.item(i
);
595 root
.setAttribute(attrItem
.getNodeName(), attrItem
.getNodeValue());
597 NodeList childNodes
= node
.getChildNodes();
598 for (int i
= 0; i
< childNodes
.getLength(); i
++) {
599 Node childItem
= childNodes
.item(i
);
600 if (childItem
.getNodeType() == Node
.ELEMENT_NODE
) {
601 root
.appendChild(recursiveNode(childItem
, document
));
603 else if (childItem
.getNodeType() == Node
.TEXT_NODE
){
604 if ( ! childItem
.getNodeValue().trim().equalsIgnoreCase("")) {
605 root
.setTextContent(childItem
.getNodeValue());