• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * ProGuard -- shrinking, optimization, obfuscation, and preverification
3  *             of Java bytecode.
4  *
5  * Copyright (c) 2002-2009 Eric Lafortune (eric@graphics.cornell.edu)
6  *
7  * This program is free software; you can redistribute it and/or modify it
8  * under the terms of the GNU General Public License as published by the Free
9  * Software Foundation; either version 2 of the License, or (at your option)
10  * any later version.
11  *
12  * This program is distributed in the hope that it will be useful, but WITHOUT
13  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
14  * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
15  * more details.
16  *
17  * You should have received a copy of the GNU General Public License along
18  * with this program; if not, write to the Free Software Foundation, Inc.,
19  * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20  */
21 package proguard.ant;
22 
23 import org.apache.tools.ant.BuildException;
24 import proguard.*;
25 import proguard.classfile.util.ClassUtil;
26 
27 import java.io.*;
28 import java.util.ArrayList;
29 
30 /**
31  * This Task allows to configure and run ProGuard from Ant.
32  *
33  * @author Eric Lafortune
34  */
35 public class ProGuardTask extends ConfigurationTask
36 {
37     // Ant task attributes.
38 
setConfiguration(File configurationFile)39     public void setConfiguration(File configurationFile) throws BuildException
40     {
41         try
42         {
43             ConfigurationParser parser = new ConfigurationParser(configurationFile);
44 
45             try
46             {
47                 parser.parse(configuration);
48             }
49             catch (ParseException ex)
50             {
51                 throw new BuildException(ex.getMessage());
52             }
53             finally
54             {
55                 parser.close();
56             }
57         }
58         catch (IOException ex)
59         {
60             throw new BuildException(ex.getMessage());
61         }
62     }
63 
64 
65     /**
66      * @deprecated Use the nested outjar element instead.
67      */
setOutjar(String parameters)68     public void setOutjar(String parameters)
69     {
70         throw new BuildException("Use the <outjar> nested element instead of the 'outjar' attribute");
71     }
72 
73 
setSkipnonpubliclibraryclasses(boolean skipNonPublicLibraryClasses)74     public void setSkipnonpubliclibraryclasses(boolean skipNonPublicLibraryClasses)
75     {
76         configuration.skipNonPublicLibraryClasses = skipNonPublicLibraryClasses;
77     }
78 
79 
setSkipnonpubliclibraryclassmembers(boolean skipNonPublicLibraryClassMembers)80     public void setSkipnonpubliclibraryclassmembers(boolean skipNonPublicLibraryClassMembers)
81     {
82         configuration.skipNonPublicLibraryClassMembers = skipNonPublicLibraryClassMembers;
83     }
84 
85 
setTarget(String target)86     public void setTarget(String target)
87     {
88         configuration.targetClassVersion = ClassUtil.internalClassVersion(target);
89         if (configuration.targetClassVersion == 0)
90         {
91             throw new BuildException("Unsupported target '"+target+"'");
92         }
93     }
94 
95 
setForceprocessing(boolean forceProcessing)96     public void setForceprocessing(boolean forceProcessing)
97     {
98         configuration.lastModified = forceProcessing ? Long.MAX_VALUE : 0;
99     }
100 
101 
setPrintseeds(File printSeeds)102     public void setPrintseeds(File printSeeds)
103     {
104         configuration.printSeeds = optionalFile(printSeeds);
105     }
106 
107 
setShrink(boolean shrink)108     public void setShrink(boolean shrink)
109     {
110         configuration.shrink = shrink;
111     }
112 
113 
setPrintusage(File printUsage)114     public void setPrintusage(File printUsage)
115     {
116         configuration.printUsage = optionalFile(printUsage);
117     }
118 
119 
setOptimize(boolean optimize)120     public void setOptimize(boolean optimize)
121     {
122         configuration.optimize = optimize;
123     }
124 
125 
setOptimizationpasses(int optimizationPasses)126     public void setOptimizationpasses(int optimizationPasses)
127     {
128         configuration.optimizationPasses = optimizationPasses;
129     }
130 
131 
setAllowaccessmodification(boolean allowAccessModification)132     public void setAllowaccessmodification(boolean allowAccessModification)
133     {
134         configuration.allowAccessModification = allowAccessModification;
135     }
136 
137 
setMergeinterfacesaggressively(boolean mergeinterfacesaggressively)138     public void setMergeinterfacesaggressively(boolean mergeinterfacesaggressively)
139     {
140         configuration.mergeInterfacesAggressively = mergeinterfacesaggressively;
141     }
142 
143 
setObfuscate(boolean obfuscate)144     public void setObfuscate(boolean obfuscate)
145     {
146         configuration.obfuscate = obfuscate;
147     }
148 
149 
setPrintmapping(File printMapping)150     public void setPrintmapping(File printMapping)
151     {
152         configuration.printMapping = optionalFile(printMapping);
153     }
154 
155 
setApplymapping(File applyMapping)156     public void setApplymapping(File applyMapping)
157     {
158         configuration.applyMapping = resolvedFile(applyMapping);
159     }
160 
161 
setObfuscationdictionary(File obfuscationDictionary)162     public void setObfuscationdictionary(File obfuscationDictionary)
163     {
164         configuration.obfuscationDictionary = resolvedFile(obfuscationDictionary);
165     }
166 
167 
setClassobfuscationdictionary(File classObfuscationDictionary)168     public void setClassobfuscationdictionary(File classObfuscationDictionary)
169     {
170         configuration.classObfuscationDictionary = resolvedFile(classObfuscationDictionary);
171     }
172 
173 
setPackageobfuscationdictionary(File packageObfuscationDictionary)174     public void setPackageobfuscationdictionary(File packageObfuscationDictionary)
175     {
176         configuration.packageObfuscationDictionary = resolvedFile(packageObfuscationDictionary);
177     }
178 
179 
setOverloadaggressively(boolean overloadAggressively)180     public void setOverloadaggressively(boolean overloadAggressively)
181     {
182         configuration.overloadAggressively = overloadAggressively;
183     }
184 
185 
setUseuniqueclassmembernames(boolean useUniqueClassMemberNames)186     public void setUseuniqueclassmembernames(boolean useUniqueClassMemberNames)
187     {
188         configuration.useUniqueClassMemberNames = useUniqueClassMemberNames;
189     }
190 
191 
setUsemixedcaseclassnames(boolean useMixedCaseClassNames)192     public void setUsemixedcaseclassnames(boolean useMixedCaseClassNames)
193     {
194         configuration.useMixedCaseClassNames = useMixedCaseClassNames;
195     }
196 
197 
setFlattenpackagehierarchy(String flattenPackageHierarchy)198     public void setFlattenpackagehierarchy(String flattenPackageHierarchy)
199     {
200         configuration.flattenPackageHierarchy = ClassUtil.internalClassName(flattenPackageHierarchy);
201     }
202 
203 
setRepackageclasses(String repackageClasses)204     public void setRepackageclasses(String repackageClasses)
205     {
206         configuration.repackageClasses = ClassUtil.internalClassName(repackageClasses);
207     }
208 
209     /**
210      * @deprecated Use the repackageclasses attribute instead.
211      */
setDefaultpackage(String defaultPackage)212     public void setDefaultpackage(String defaultPackage)
213     {
214         configuration.repackageClasses = ClassUtil.internalClassName(defaultPackage);
215     }
216 
217 
setRenamesourcefileattribute(String newSourceFileAttribute)218     public void setRenamesourcefileattribute(String newSourceFileAttribute)
219     {
220         configuration.newSourceFileAttribute = newSourceFileAttribute;
221     }
222 
223 
setPreverify(boolean preverify)224     public void setPreverify(boolean preverify)
225     {
226         configuration.preverify = preverify;
227     }
228 
229 
setMicroedition(boolean microEdition)230     public void setMicroedition(boolean microEdition)
231     {
232         configuration.microEdition = microEdition;
233     }
234 
235 
setVerbose(boolean verbose)236     public void setVerbose(boolean verbose)
237     {
238         configuration.verbose = verbose;
239     }
240 
241 
setNote(boolean note)242     public void setNote(boolean note)
243     {
244         configuration.note = note ? null : new ArrayList();
245     }
246 
247 
setWarn(boolean warn)248     public void setWarn(boolean warn)
249     {
250         configuration.warn = warn ? null : new ArrayList();
251     }
252 
253 
setIgnorewarnings(boolean ignoreWarnings)254     public void setIgnorewarnings(boolean ignoreWarnings)
255     {
256         configuration.ignoreWarnings = ignoreWarnings;
257     }
258 
259 
setPrintconfiguration(File printConfiguration)260     public void setPrintconfiguration(File printConfiguration)
261     {
262         configuration.printConfiguration = optionalFile(printConfiguration);
263     }
264 
265 
setDump(File dump)266     public void setDump(File dump)
267     {
268         configuration.dump = optionalFile(dump);
269     }
270 
271 
272     // Implementations for Task.
273 
execute()274     public void execute() throws BuildException
275     {
276         try
277         {
278             ProGuard proGuard = new ProGuard(configuration);
279             proGuard.execute();
280         }
281         catch (IOException ex)
282         {
283             throw new BuildException(ex.getMessage());
284         }
285     }
286 
287 
288     // Small utility methods.
289 
290     /**
291      * Returns a file that is properly resolved with respect to the project
292      * directory, or <code>null</code> or empty if its name is actually a
293      * boolean flag.
294      */
optionalFile(File file)295     private File optionalFile(File file)
296     {
297         String fileName = file.getName();
298 
299         return
300             fileName.equalsIgnoreCase("false") ||
301             fileName.equalsIgnoreCase("no")    ||
302             fileName.equalsIgnoreCase("off")    ? null :
303             fileName.equalsIgnoreCase("true")  ||
304             fileName.equalsIgnoreCase("yes")   ||
305             fileName.equalsIgnoreCase("on")     ? new File("")   :
306                                                   resolvedFile(file);
307     }
308 
309 
310     /**
311      * Returns a file that is properly resolved with respect to the project
312      * directory.
313      */
resolvedFile(File file)314     private File resolvedFile(File file)
315     {
316         return file.isAbsolute() ? file :
317                                    new File(getProject().getBaseDir(),
318                                             file.getName());
319     }
320 }
321