buildframework/helium/sf/java/imaker/src/com/nokia/helium/imaker/ant/engines/EmakeEngine.java
changeset 628 7c4a911dc066
parent 587 85df38eb4012
equal deleted inserted replaced
588:c7c26511138f 628:7c4a911dc066
     1 /*
     1 /*
     2 * Copyright (c) 2007-2008 Nokia Corporation and/or its subsidiary(-ies).
     2  * Copyright (c) 2007-2008 Nokia Corporation and/or its subsidiary(-ies).
     3 * All rights reserved.
     3  * All rights reserved.
     4 * This component and the accompanying materials are made available
     4  * This component and the accompanying materials are made available
     5 * under the terms of the License "Eclipse Public License v1.0"
     5  * under the terms of the License "Eclipse Public License v1.0"
     6 * which accompanies this distribution, and is available
     6  * which accompanies this distribution, and is available
     7 * at the URL "http://www.eclipse.org/legal/epl-v10.html".
     7  * at the URL "http://www.eclipse.org/legal/epl-v10.html".
     8 *
     8  *
     9 * Initial Contributors:
     9  * Initial Contributors:
    10 * Nokia Corporation - initial contribution.
    10  * Nokia Corporation - initial contribution.
    11 *
    11  *
    12 * Contributors:
    12  * Contributors:
    13 *
    13  *
    14 * Description:  
    14  * Description:  
    15 *
    15  *
    16 */
    16  */
    17 package com.nokia.helium.imaker.ant.engines;
    17 package com.nokia.helium.imaker.ant.engines;
    18 
    18 
    19 import java.io.File;
    19 import java.io.File;
       
    20 import java.io.FileNotFoundException;
    20 import java.io.FileOutputStream;
    21 import java.io.FileOutputStream;
    21 import java.io.IOException;
    22 import java.io.IOException;
    22 import java.io.FileNotFoundException;
       
    23 import java.io.OutputStreamWriter;
    23 import java.io.OutputStreamWriter;
    24 import java.io.StringWriter;
    24 import java.io.StringWriter;
    25 import java.net.MalformedURLException;
    25 import java.net.MalformedURLException;
    26 import java.net.URL;
    26 import java.net.URL;
    27 import java.util.ArrayList;
    27 import java.util.ArrayList;
    45 import freemarker.template.Configuration;
    45 import freemarker.template.Configuration;
    46 import freemarker.template.Template;
    46 import freemarker.template.Template;
    47 import freemarker.template.TemplateException;
    47 import freemarker.template.TemplateException;
    48 
    48 
    49 /**
    49 /**
    50  *
    50  * 
    51  * Simplest possible definition of the type, e.g:
    51  * Simplest possible definition of the type, e.g:
       
    52  * 
    52  * <pre>
    53  * <pre>
    53  * &lt;emakeEngine id="imaker.ec" /&gt;
    54  * &lt;emakeEngine id="imaker.ec" /&gt;
    54  * </pre>
    55  * </pre>
    55  * 
    56  * 
    56  * Emake engine with some custom configuration.
    57  * Emake engine with some custom configuration.
    57  * <pre> 
    58  * 
       
    59  * <pre>
    58  * &lt;emakeEngine id="imaker.ec" &gt;
    60  * &lt;emakeEngine id="imaker.ec" &gt;
    59  *     &lt;arg value="--emake-annofile=imaker.anno.xml" /&gt;
    61  *     &lt;arg value="--emake-annofile=imaker.anno.xml" /&gt;
    60  * &lt;/emakeEngine&gt;
    62  * &lt;/emakeEngine&gt;
    61  * </pre>
    63  * </pre>
    62  * 
    64  * 
    63  * @ant.type name=emakeEngine category="imaker"
    65  * @ant.type name=emakeEngine category="imaker"
    64  */
    66  */
    65 public class EmakeEngine extends DataType implements Engine {
    67 public class EmakeEngine extends DataType implements Engine {
    66     private Logger log = Logger.getLogger(getClass());
    68     private Logger log = Logger.getLogger(getClass());
    67     private IMakerTask task;
    69     private IMakerTask task;
    68     private List<Arg> customArgs = new ArrayList<Arg>(); 
    70     private List<Arg> customArgs = new ArrayList<Arg>();
    69     private File template;
    71     private File template;
    70     
    72 
    71     /**
    73     /**
    72      * Holder for emake custom args. 
    74      * Holder for emake custom args.
    73      */
    75      */
    74     public class Arg {
    76     public class Arg {
    75         private String value;
    77         private String value;
    76 
    78 
    77         /**
    79         /**
    78          * Get the value of the argument.
    80          * Get the value of the argument.
       
    81          * 
    79          * @return the argument
    82          * @return the argument
    80          */
    83          */
    81         public String getValue() {
    84         public String getValue() {
    82             return value;
    85             return value;
    83         }
    86         }
    84 
    87 
    85         /**
    88         /**
    86          * Define the additional command line parameter you want to add to emake
    89          * Define the additional command line parameter you want to add to emake invocation.
    87          * invocation.
    90          * 
    88          * @param value the additional command line parameter
    91          * @param value the additional command line parameter
    89          * @ant.required
    92          * @ant.required
    90          */
    93          */
    91         public void setValue(String value) {
    94         public void setValue(String value) {
    92             this.value = value;
    95             this.value = value;
    99     public void build(List<List<Command>> cmdSet) throws IMakerException {
   102     public void build(List<List<Command>> cmdSet) throws IMakerException {
   100         File makefile = null;
   103         File makefile = null;
   101         try {
   104         try {
   102             // Writing the makefile.
   105             // Writing the makefile.
   103             makefile = writeMakefile(cmdSet);
   106             makefile = writeMakefile(cmdSet);
   104             
   107 
   105             // Running Emake
   108             // Running Emake
   106             runEmake(makefile);
   109             runEmake(makefile);
   107         } finally {
   110         }
       
   111         finally {
   108             if (makefile != null) {
   112             if (makefile != null) {
   109                 makefile.delete();
   113                 makefile.delete();
   110             }
   114             }
   111         }
   115         }
   112     }
   116     }
   113 
   117 
   114     /**
   118     /**
   115      * Returns the jar file name containing this class
   119      * Returns the jar file name containing this class
       
   120      * 
   116      * @return a File object or null if not found.
   121      * @return a File object or null if not found.
   117      * @throws IMakerException
   122      * @throws IMakerException
   118      */
   123      */
   119     protected File getJarFile() throws IMakerException {
   124     protected File getJarFile() throws IMakerException {
   120         URL url = this.getClass().getClassLoader().getResource(this.getClass().getName().replace('.', '/') + ".class");
   125         URL url = this.getClass().getClassLoader().getResource(this.getClass().getName().replace('.', '/')
       
   126             + ".class");
   121         if (url.getProtocol().equals("jar") && url.getPath().contains("!/")) {
   127         if (url.getProtocol().equals("jar") && url.getPath().contains("!/")) {
   122             String fileUrl = url.getPath().split("!/")[0];
   128             String fileUrl = url.getPath().split("!/")[0];
   123             try {
   129             try {
   124                 return new File(new URL(fileUrl).getPath());
   130                 return new File(new URL(fileUrl).getPath());
   125             } catch (MalformedURLException e) {
   131             }
       
   132             catch (MalformedURLException e) {
   126                 throw new IMakerException("Error determining the jar file where "
   133                 throw new IMakerException("Error determining the jar file where "
   127                         + this.getClass().getName() + " is located.", e);
   134                     + this.getClass().getName() + " is located.", e);
   128             }
   135             }
   129         }
   136         }
   130         return null;
   137         return null;
   131     }
   138     }
       
   139 
   132     /**
   140     /**
   133      * Run emake using defined makefile.
   141      * Run emake using defined makefile.
       
   142      * 
   134      * @param makefile the makefile to build
   143      * @param makefile the makefile to build
   135      * @throws IMakerException
   144      * @throws IMakerException
   136      */
   145      */
   137     private void runEmake(File makefile) throws IMakerException {
   146     private void runEmake(File makefile) throws IMakerException {
   138         FileStreamConsumer output = null;
   147         FileStreamConsumer output = null;
   139         if (task.getOutput() != null) {
   148         if (task.getOutput() != null) {
   140             try {
   149             try {
   141                 output = new FileStreamConsumer(task.getOutput());
   150                 output = new FileStreamConsumer(task.getOutput());
   142             } catch (FileNotFoundException e) {
   151             }
       
   152             catch (FileNotFoundException e) {
   143                 throw new IMakerException("Error creating the stream recorder: " + e.getMessage(), e);
   153                 throw new IMakerException("Error creating the stream recorder: " + e.getMessage(), e);
   144             }
   154             }
   145         }
   155         }
   146         try {
   156         try {
   147             Emake emake = new Emake();
   157             Emake emake = new Emake();
   162             if (output != null) {
   172             if (output != null) {
   163                 emake.addOutputLineHandler(output);
   173                 emake.addOutputLineHandler(output);
   164                 emake.addErrorLineHandler(output);
   174                 emake.addErrorLineHandler(output);
   165             }
   175             }
   166             emake.execute(args.toArray(new String[args.size()]));
   176             emake.execute(args.toArray(new String[args.size()]));
   167         } catch (IMakerException e) {
   177         }
       
   178         catch (IMakerException e) {
   168             throw new IMakerException("Error executing emake: " + e.getMessage(), e);
   179             throw new IMakerException("Error executing emake: " + e.getMessage(), e);
   169         } finally {
   180         }
       
   181         finally {
   170             if (output != null) {
   182             if (output != null) {
   171                 output.close();
   183                 output.close();
   172             }
   184             }
   173         }
   185         }
   174     }
   186     }
   175     
   187 
   176     /**
   188     /**
   177      * Create the Makefile based on the cmdSet build sequence. 
   189      * Create the Makefile based on the cmdSet build sequence.
       
   190      * 
   178      * @param cmdSet
   191      * @param cmdSet
   179      * @return
   192      * @return
   180      * @throws IMakerException 
   193      * @throws IMakerException
   181      * @throws IOException
   194      * @throws IOException
   182      */
   195      */
   183     private File writeMakefile(List<List<Command>> cmdSet) throws IMakerException {
   196     private File writeMakefile(List<List<Command>> cmdSet) throws IMakerException {
   184         try {
   197         try {
   185             Configuration cfg = new Configuration();
   198             Configuration cfg = new Configuration();
   186             Template template = null;
   199             Template template = null;
   187             if (this.template != null) {
   200             if (this.template != null) {
   188                 if (!this.template.exists()) {
   201                 if (!this.template.exists()) {
   189                     throw new IMakerException("Could not find template file: " + this.template.getAbsolutePath());
   202                     throw new IMakerException("Could not find template file: "
       
   203                         + this.template.getAbsolutePath());
   190                 }
   204                 }
   191                 task.log("Loading template: " + this.template.getAbsolutePath());
   205                 task.log("Loading template: " + this.template.getAbsolutePath());
   192                 cfg.setTemplateLoader(new FileTemplateLoader(this.template.getParentFile()));
   206                 cfg.setTemplateLoader(new FileTemplateLoader(this.template.getParentFile()));
   193                 template = cfg.getTemplate(this.template.getName());
   207                 template = cfg.getTemplate(this.template.getName());
   194             } else {
   208             }
       
   209             else {
   195                 cfg.setTemplateLoader(new ClassTemplateLoader(this.getClass(), ""));
   210                 cfg.setTemplateLoader(new ClassTemplateLoader(this.getClass(), ""));
   196                 template = cfg.getTemplate("build_imaker_roms_signing.mk.ftl");
   211                 template = cfg.getTemplate("build_imaker_roms_signing.mk.ftl");
   197             }
   212             }
   198             File makefile = File.createTempFile("helium-imaker", ".mk", task.getEpocroot());
   213             File makefile = File.createTempFile("helium-imaker", ".mk", task.getEpocroot());
   199             makefile.deleteOnExit();
   214             makefile.deleteOnExit();
   202             data.put("cmdSets", cmdSet);
   217             data.put("cmdSets", cmdSet);
   203             data.put("makefile", makefile.getAbsoluteFile());
   218             data.put("makefile", makefile.getAbsoluteFile());
   204             data.put("java_home", System.getProperty("java.home"));
   219             data.put("java_home", System.getProperty("java.home"));
   205             File jar = getJarFile();
   220             File jar = getJarFile();
   206             if (jar != null) {
   221             if (jar != null) {
   207                 task.log("Using " + jar + " as the utility container, make sure the file is available under an emake root.");
   222                 task.log("Using "
       
   223                     + jar
       
   224                     + " as the utility container, make sure the file is available under an emake root.");
   208                 data.put("java_utils_classpath", jar.getAbsolutePath());
   225                 data.put("java_utils_classpath", jar.getAbsolutePath());
   209             }
   226             }
   210             template.process(data, out);
   227             template.process(data, out);
   211             log.debug(out.getBuffer().toString());
   228             log.debug(out.getBuffer().toString());
   212         
   229 
   213             OutputStreamWriter output = new OutputStreamWriter(new FileOutputStream(makefile));
   230             OutputStreamWriter output = new OutputStreamWriter(new FileOutputStream(makefile));
   214             output.append(out.getBuffer().toString());
   231             output.append(out.getBuffer().toString());
   215             output.close();
   232             output.close();
   216             return makefile;
   233             return makefile;
   217         } catch (IOException e) {
   234         }
   218            throw new IMakerException("Error generating the makefile: " + e.getMessage(), e);
   235         catch (IOException e) {
   219         } catch (TemplateException e) {
   236             throw new IMakerException("Error generating the makefile: " + e.getMessage(), e);
   220             throw new IMakerException("Error while rendering the makefile template: " + e.getMessage(), e);
   237         }
   221         }
   238         catch (TemplateException e) {
   222     }
   239             throw new IMakerException("Error while rendering the makefile template: "
   223     
   240                 + e.getMessage(), e);
       
   241         }
       
   242     }
       
   243 
   224     /**
   244     /**
   225      * Add custom parameters for the emake invocation.
   245      * Add custom parameters for the emake invocation.
       
   246      * 
   226      * @return a new Arg object.
   247      * @return a new Arg object.
   227      */
   248      */
   228     public Arg createArg() {
   249     public Arg createArg() {
   229         Arg arg = new Arg();
   250         Arg arg = new Arg();
   230         customArgs.add(arg);
   251         customArgs.add(arg);
   231         return arg;
   252         return arg;
   232     }
   253     }
   233     
   254 
   234     
       
   235     /**
   255     /**
   236      * {@inheritDoc}
   256      * {@inheritDoc}
   237      */
   257      */
   238     @Override
   258     @Override
   239     public void setTask(IMakerTask task) {
   259     public void setTask(IMakerTask task) {
   240         this.task = task;
   260         this.task = task;
   241     }
   261     }
   242     
   262 
   243     /**
   263     /**
   244      * Defines an alternate template to use to generate the build sequence for emake.
   264      * Defines an alternate template to use to generate the build sequence for emake.
       
   265      * 
   245      * @ant.not-required
   266      * @ant.not-required
   246      */
   267      */
   247     public void setTemplate(File template) {
   268     public void setTemplate(File template) {
   248         this.template = template;
   269         this.template = template;
   249     }
   270     }