Clover coverage report - Ant Coverage
Coverage timestamp: Tue Apr 8 2003 20:43:55 EST
file stats: LOC: 692   Methods: 31
NCLOC: 405   Classes: 2
 
 Source file Conditionals Statements Methods TOTAL
Path.java 81.7% 84.9% 93.5% 84.6%
 1   
 /*
 2   
  * The Apache Software License, Version 1.1
 3   
  *
 4   
  * Copyright (c) 2000-2003 The Apache Software Foundation.  All rights
 5   
  * reserved.
 6   
  *
 7   
  * Redistribution and use in source and binary forms, with or without
 8   
  * modification, are permitted provided that the following conditions
 9   
  * are met:
 10   
  *
 11   
  * 1. Redistributions of source code must retain the above copyright
 12   
  *    notice, this list of conditions and the following disclaimer.
 13   
  *
 14   
  * 2. Redistributions in binary form must reproduce the above copyright
 15   
  *    notice, this list of conditions and the following disclaimer in
 16   
  *    the documentation and/or other materials provided with the
 17   
  *    distribution.
 18   
  *
 19   
  * 3. The end-user documentation included with the redistribution, if
 20   
  *    any, must include the following acknowlegement:
 21   
  *       "This product includes software developed by the
 22   
  *        Apache Software Foundation (http://www.apache.org/)."
 23   
  *    Alternately, this acknowlegement may appear in the software itself,
 24   
  *    if and wherever such third-party acknowlegements normally appear.
 25   
  *
 26   
  * 4. The names "Ant" and "Apache Software
 27   
  *    Foundation" must not be used to endorse or promote products derived
 28   
  *    from this software without prior written permission. For written
 29   
  *    permission, please contact apache@apache.org.
 30   
  *
 31   
  * 5. Products derived from this software may not be called "Apache"
 32   
  *    nor may "Apache" appear in their names without prior written
 33   
  *    permission of the Apache Group.
 34   
  *
 35   
  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
 36   
  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
 37   
  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
 38   
  * DISCLAIMED.  IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
 39   
  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 40   
  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
 41   
  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
 42   
  * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
 43   
  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
 44   
  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
 45   
  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 46   
  * SUCH DAMAGE.
 47   
  * ====================================================================
 48   
  *
 49   
  * This software consists of voluntary contributions made by many
 50   
  * individuals on behalf of the Apache Software Foundation.  For more
 51   
  * information on the Apache Software Foundation, please see
 52   
  * <http://www.apache.org/>.
 53   
  */
 54   
 
 55   
 package org.apache.tools.ant.types;
 56   
 
 57   
 import java.io.File;
 58   
 import java.util.Enumeration;
 59   
 import java.util.Locale;
 60   
 import java.util.Stack;
 61   
 import java.util.Vector;
 62   
 import org.apache.tools.ant.BuildException;
 63   
 import org.apache.tools.ant.DirectoryScanner;
 64   
 import org.apache.tools.ant.PathTokenizer;
 65   
 import org.apache.tools.ant.Project;
 66   
 import org.apache.tools.ant.util.JavaEnvUtils;
 67   
 
 68   
 
 69   
 
 70   
 /**
 71   
  * This object represents a path as used by CLASSPATH or PATH
 72   
  * environment variable.
 73   
  * <p>
 74   
  * <code>
 75   
  * &lt;sometask&gt;<br>
 76   
  * &nbsp;&nbsp;&lt;somepath&gt;<br>
 77   
  * &nbsp;&nbsp;&nbsp;&nbsp;&lt;pathelement location="/path/to/file.jar" /&gt;<br>
 78   
  * &nbsp;&nbsp;&nbsp;&nbsp;&lt;pathelement path="/path/to/file2.jar:/path/to/class2;/path/to/class3" /&gt;<br>
 79   
  * &nbsp;&nbsp;&nbsp;&nbsp;&lt;pathelement location="/path/to/file3.jar" /&gt;<br>
 80   
  * &nbsp;&nbsp;&nbsp;&nbsp;&lt;pathelement location="/path/to/file4.jar" /&gt;<br>
 81   
  * &nbsp;&nbsp;&lt;/somepath&gt;<br>
 82   
  * &lt;/sometask&gt;<br>
 83   
  * </code>
 84   
  * <p>
 85   
  * The object implemention <code>sometask</code> must provide a method called
 86   
  * <code>createSomepath</code> which returns an instance of <code>Path</code>.
 87   
  * Nested path definitions are handled by the Path object and must be labeled
 88   
  * <code>pathelement</code>.<p>
 89   
  *
 90   
  * The path element takes a parameter <code>path</code> which will be parsed
 91   
  * and split into single elements. It will usually be used
 92   
  * to define a path from an environment variable.
 93   
  *
 94   
  * @author Thomas.Haas@softwired-inc.com
 95   
  * @author Stefan Bodewig
 96   
  */
 97   
 
 98   
 public class Path extends DataType implements Cloneable {
 99   
 
 100   
     private Vector elements;
 101   
 
 102   
     /** The system classspath as a Path object */
 103   
     public static Path systemClasspath = 
 104   
         new Path(null, System.getProperty("java.class.path"));
 105   
 
 106   
 
 107   
     /**
 108   
      * Helper class, holds the nested <code>&lt;pathelement&gt;</code> values.
 109   
      */
 110   
     public class PathElement {
 111   
         private String[] parts;
 112   
 
 113  8651
         public void setLocation(File loc) {
 114  8651
             parts = new String[] {translateFile(loc.getAbsolutePath())};
 115   
         }
 116   
 
 117  211
         public void setPath(String path) {
 118  211
             parts = Path.translatePath(getProject(), path);
 119   
         }
 120   
 
 121  11644
         public String[] getParts() {
 122  11644
             return parts;
 123   
         }
 124   
     }
 125   
 
 126   
     /**
 127   
      * Invoked by IntrospectionHelper for <code>setXXX(Path p)</code>
 128   
      * attribute setters.  
 129   
      */
 130  128
     public Path(Project p, String path) {
 131  128
         this(p);
 132  128
         createPathElement().setPath(path);
 133   
     }
 134   
 
 135  1076
     public Path(Project project) {
 136  1076
         setProject(project);
 137  1076
         elements = new Vector();
 138   
     }
 139   
 
 140   
     /**
 141   
      * Adds a element definition to the path.
 142   
      * @param location the location of the element to add (must not be
 143   
      * <code>null</code> nor empty.
 144   
      */
 145  8605
     public void setLocation(File location) throws BuildException {
 146  8605
         if (isReference()) {
 147  1
             throw tooManyAttributes();
 148   
         }
 149  8604
         createPathElement().setLocation(location);
 150   
     }
 151   
 
 152   
 
 153   
     /**
 154   
      * Parses a path definition and creates single PathElements.
 155   
      * @param path the path definition.
 156   
      */
 157  25
     public void setPath(String path) throws BuildException {
 158  25
         if (isReference()) {
 159  1
             throw tooManyAttributes();
 160   
         }
 161  24
         createPathElement().setPath(path);
 162   
     }
 163   
 
 164   
     /**
 165   
      * Makes this instance in effect a reference to another Path instance.
 166   
      *
 167   
      * <p>You must not set another attribute or nest elements inside
 168   
      * this element if you make it a reference.</p>
 169   
      */
 170  71
     public void setRefid(Reference r) throws BuildException {
 171  71
         if (!elements.isEmpty()) {
 172  2
             throw tooManyAttributes();
 173   
         }
 174  69
         elements.addElement(r);
 175  69
         super.setRefid(r);
 176   
     }
 177   
 
 178   
     /**
 179   
      * Creates the nested <code>&lt;pathelement&gt;</code> element.
 180   
      */
 181  8863
     public PathElement createPathElement() throws BuildException {
 182  8863
         if (isReference()) {
 183  1
             throw noChildrenAllowed();
 184   
         }
 185  8862
         PathElement pe = new PathElement();
 186  8862
         elements.addElement(pe);
 187  8862
         return pe;
 188   
     }
 189   
 
 190   
     /**
 191   
      * Adds a nested <code>&lt;fileset&gt;</code> element.
 192   
      */
 193  5
     public void addFileset(FileSet fs) throws BuildException {
 194  5
         if (isReference()) {
 195  1
             throw noChildrenAllowed();
 196   
         }
 197  4
         elements.addElement(fs);
 198  4
         setChecked( false );
 199   
     }
 200   
 
 201   
     /**
 202   
      * Adds a nested <code>&lt;filelist&gt;</code> element.
 203   
      */
 204  2
     public void addFilelist(FileList fl) throws BuildException {
 205  2
         if (isReference()) {
 206  1
             throw noChildrenAllowed();
 207   
         }
 208  1
         elements.addElement(fl);
 209  1
         setChecked( false );
 210   
     }
 211   
 
 212   
     /**
 213   
      * Adds a nested <code>&lt;dirset&gt;</code> element.
 214   
      */
 215  2
     public void addDirset(DirSet dset) throws BuildException {
 216  2
         if (isReference()) {
 217  1
             throw noChildrenAllowed();
 218   
         }
 219  1
         elements.addElement(dset);
 220  1
         setChecked( false );
 221   
     }
 222   
 
 223   
     /**
 224   
      * Creates a nested <code>&lt;path&gt;</code> element.
 225   
      */
 226  129
     public Path createPath() throws BuildException {
 227  129
         if (isReference()) {
 228  1
             throw noChildrenAllowed();
 229   
         }
 230  128
         Path p = new Path(getProject());
 231  128
         elements.addElement(p);
 232  128
         setChecked( false );
 233  128
         return p;
 234   
     }
 235   
 
 236   
     /**
 237   
      * Append the contents of the other Path instance to this.
 238   
      */
 239  369
     public void append(Path other) {
 240  369
         if (other == null) {
 241  11
             return;
 242   
         }
 243  358
         String[] l = other.list();
 244  358
         for (int i = 0; i < l.length; i++) {
 245  2224
             if (elements.indexOf(l[i]) == -1) {
 246  2224
                 elements.addElement(l[i]);
 247   
             }
 248   
         }
 249   
     }
 250   
 
 251   
      /**
 252   
      * Adds the components on the given path which exist to this
 253   
      * Path. Components that don't exist, aren't added.
 254   
      *
 255   
      * @param source - source path whose components are examined for existence
 256   
      */
 257  355
      public void addExisting(Path source) {
 258  355
          addExisting(source, false );
 259   
      }
 260   
 
 261   
     /** Same as addExisting, but support classpath behavior if tryUserDir
 262   
      * is true. Classpaths are relative to user dir, not the project base.
 263   
      * That used to break jspc test
 264   
      *
 265   
      * @param source
 266   
      * @param tryUserDir
 267   
      */
 268  378
     public void addExisting(Path source, boolean tryUserDir) {
 269  378
         String[] list = source.list();
 270  378
         File userDir=(tryUserDir) ? new File(System.getProperty( "user.dir"))
 271   
                 : null;
 272   
 
 273  378
         for (int i = 0; i < list.length; i++) {
 274  8608
             File f = null;
 275  8608
             if (getProject() != null) {
 276  8582
                 f = getProject().resolveFile(list[i]);
 277   
             } else {
 278  26
                 f = new File(list[i]);
 279   
             }
 280   
             // probably not the best choice, but it solves the problem of
 281   
             // relative paths in CLASSPATH
 282  8608
             if( tryUserDir && ! f.exists()) {
 283  0
                 f=new File( userDir, list[i]);
 284   
             }
 285  8608
             if (f.exists()) {
 286  8577
                 setLocation(f);
 287   
             } else {
 288  31
                 log("dropping " + f + " from path as it doesn't exist",
 289   
                     Project.MSG_VERBOSE);
 290   
             }
 291   
         }
 292   
     }
 293   
 
 294   
     /**
 295   
      * Returns all path elements defined by this and nested path objects.
 296   
      * @return list of path elements.
 297   
      */
 298  3515
     public String[] list() {
 299  3515
         if (!isChecked()) {
 300   
             // make sure we don't have a circular reference here
 301  117
             Stack stk = new Stack();
 302  117
             stk.push(this);
 303  117
             dieOnCircularReference(stk, getProject());
 304   
         }
 305   
 
 306  3513
         Vector result = new Vector(2 * elements.size());
 307  3513
         for (int i = 0; i < elements.size(); i++) {
 308  17205
             Object o = elements.elementAt(i);
 309  17205
             if (o instanceof Reference) {
 310  491
                 Reference r = (Reference) o;
 311  491
                 o = r.getReferencedObject(getProject());
 312   
                 // we only support references to paths right now
 313  491
                 if (!(o instanceof Path)) {
 314  0
                     String msg = r.getRefId() + " doesn\'t denote a path " + o;
 315  0
                     throw new BuildException(msg);
 316   
                 }
 317   
             }
 318   
             
 319  17205
             if (o instanceof String) {
 320   
                 // obtained via append
 321  3531
                 addUnlessPresent(result, (String) o);
 322  13674
             } else if (o instanceof PathElement) {
 323  11644
                 String[] parts = ((PathElement) o).getParts();
 324  11644
                 if (parts == null) {
 325  0
                     throw new BuildException("You must either set location or" 
 326   
                         + " path on <pathelement>");
 327   
                 }
 328  11644
                 for (int j = 0; j < parts.length; j++) {
 329  23426
                     addUnlessPresent(result, parts[j]);
 330   
                 }
 331  2030
             } else if (o instanceof Path) {
 332  1888
                 Path p = (Path) o;
 333  1888
                 if (p.getProject() == null) {
 334  0
                     p.setProject(getProject());
 335   
                 }
 336  1888
                 String[] parts = p.list();
 337  1888
                 for (int j = 0; j < parts.length; j++) {
 338  9030
                     addUnlessPresent(result, parts[j]);
 339   
                 }
 340  142
             } else if (o instanceof DirSet) {
 341  1
                 DirSet dset = (DirSet) o;
 342  1
                 DirectoryScanner ds = dset.getDirectoryScanner(getProject());
 343  1
                 String[] s = ds.getIncludedDirectories();
 344  1
                 File dir = dset.getDir(getProject());
 345  1
                 addUnlessPresent(result, dir, s);
 346  141
             } else if (o instanceof FileSet) {
 347  140
                 FileSet fs = (FileSet) o;
 348  140
                 DirectoryScanner ds = fs.getDirectoryScanner(getProject());
 349  140
                 String[] s = ds.getIncludedFiles();
 350  140
                 File dir = fs.getDir(getProject());
 351  140
                 addUnlessPresent(result, dir, s);
 352  1
             } else if (o instanceof FileList) {
 353  1
                 FileList fl = (FileList) o;
 354  1
                 String[] s = fl.getFiles(getProject());
 355  1
                 File dir = fl.getDir(getProject());
 356  1
                 addUnlessPresent(result, dir, s);
 357   
             }
 358   
         }
 359  3513
         String[] res = new String[result.size()];
 360  3513
         result.copyInto(res);
 361  3513
         return res;
 362   
     }
 363   
 
 364   
 
 365   
     /**
 366   
      * Returns a textual representation of the path, which can be used as
 367   
      * CLASSPATH or PATH environment variable definition.
 368   
      * @return a textual representation of the path.
 369   
      */
 370  391
     public String toString() {
 371  391
         final String[] list = list();
 372   
 
 373   
         // empty path return empty string
 374  391
         if (list.length == 0) {
 375  32
             return "";
 376   
         }
 377   
 
 378   
         // path containing one or more elements
 379  359
         final StringBuffer result = new StringBuffer(list[0].toString());
 380  359
         for (int i = 1; i < list.length; i++) {
 381  9873
             result.append(File.pathSeparatorChar);
 382  9873
             result.append(list[i]);
 383   
         }
 384   
 
 385  359
         return result.toString();
 386   
     }
 387   
 
 388   
     /**
 389   
      * Splits a PATH (with : or ; as separators) into its parts.
 390   
      */
 391  211
     public static String[] translatePath(Project project, String source) {
 392  211
         final Vector result = new Vector();
 393  211
         if (source == null) {
 394  0
           return new String[0];
 395   
         }
 396   
 
 397  211
         PathTokenizer tok = new PathTokenizer(source);
 398  211
         StringBuffer element = new StringBuffer();
 399  211
         while (tok.hasMoreTokens()) {
 400  3827
             String pathElement = tok.nextToken();
 401  3827
             try {
 402  3827
                 element.append(resolveFile(project, pathElement));
 403   
             } catch (BuildException e) {
 404  0
                 project.log("Dropping path element " + pathElement 
 405   
                     + " as it is not valid relative to the project", 
 406   
                     Project.MSG_VERBOSE);
 407   
             }
 408  3827
             for (int i = 0; i < element.length(); i++) {
 409  132262
                 translateFileSep(element, i);
 410   
             }
 411  3827
             result.addElement(element.toString());
 412  3827
             element = new StringBuffer();
 413   
         }
 414  211
         String[] res = new String[result.size()];
 415  211
         result.copyInto(res);
 416  211
         return res;
 417   
     }
 418   
 
 419   
     /**
 420   
      * Returns its argument with all file separator characters
 421   
      * replaced so that they match the local OS conventions.  
 422   
      */
 423  8656
     public static String translateFile(String source) {
 424  8656
         if (source == null) {
 425  0
           return "";
 426   
         }
 427   
 
 428  8656
         final StringBuffer result = new StringBuffer(source);
 429  8656
         for (int i = 0; i < result.length(); i++) {
 430  303479
             translateFileSep(result, i);
 431   
         }
 432   
 
 433  8656
         return result.toString();
 434   
     }
 435   
 
 436   
     /**
 437   
      * Translates all occurrences of / or \ to correct separator of the
 438   
      * current platform and returns whether it had to do any
 439   
      * replacements.  
 440   
      */
 441  435741
     protected static boolean translateFileSep(StringBuffer buffer, int pos) {
 442  435741
         if (buffer.charAt(pos) == '/' || buffer.charAt(pos) == '\\') {
 443  64605
             buffer.setCharAt(pos, File.separatorChar);
 444  64605
             return true;
 445   
         }
 446  371136
         return false;
 447   
     }
 448   
 
 449   
     /**
 450   
      * How many parts does this Path instance consist of.
 451   
      */
 452  36
     public int size() {
 453  36
         return list().length;
 454   
     }
 455   
 
 456   
     /**
 457   
      * Return a Path that holds the same elements as this instance.
 458   
      */
 459  149
     public Object clone() {
 460  149
         Path p = new Path(getProject());
 461  149
         p.append(this);
 462  149
         return p;
 463   
     }
 464   
 
 465   
     /**
 466   
      * Overrides the version of DataType to recurse on all DataType
 467   
      * child elements that may have been added.  
 468   
      */
 469  296
     protected void dieOnCircularReference(Stack stk, Project p) 
 470   
         throws BuildException {
 471   
 
 472  296
         if (isChecked()) {
 473  112
             return;
 474   
         }
 475   
 
 476  184
         Enumeration enum = elements.elements();
 477  184
         while (enum.hasMoreElements()) {
 478  202
             Object o = enum.nextElement();
 479  202
             if (o instanceof Reference) {
 480  64
                 o = ((Reference) o).getReferencedObject(p);
 481   
             }
 482   
 
 483  202
             if (o instanceof DataType) {
 484  187
                 if (stk.contains(o)) {
 485  2
                     throw circularReference();
 486   
                 } else {
 487  185
                     stk.push(o);
 488  185
                     ((DataType) o).dieOnCircularReference(stk, p);
 489  183
                     stk.pop();
 490   
                 }
 491   
             }
 492   
         }
 493  180
         setChecked( true );
 494   
     }
 495   
 
 496   
     /**
 497   
      * Resolve a filename with Project's help - if we know one that is.
 498   
      *
 499   
      * <p>Assume the filename is absolute if project is null.</p>
 500   
      */
 501  3827
     private static String resolveFile(Project project, String relativeName) {
 502  3827
         if (project != null) {
 503  3730
             File f = project.resolveFile(relativeName);
 504  3730
             return f.getAbsolutePath();
 505   
         }
 506  97
         return relativeName;
 507   
     }
 508   
 
 509   
     /**
 510   
      * Adds a String to the Vector if it isn't already included.
 511   
      */
 512  35992
     private static void addUnlessPresent(Vector v, String s) {
 513  35992
         if (v.indexOf(s) == -1) {
 514  35969
             v.addElement(s);
 515   
         }
 516   
     }
 517   
 
 518   
     /**
 519   
      * Adds absolute path names of listed files in the given directory
 520   
      * to the Vector if they are not already included.
 521   
      */
 522  142
     private static void addUnlessPresent(Vector v, File dir, String[] s) {
 523  142
         for (int j = 0; j < s.length; j++) {
 524  5
             File d = new File(dir, s[j]);
 525  5
             String absolutePath = d.getAbsolutePath();
 526  5
             addUnlessPresent(v, translateFile(absolutePath));
 527   
         } 
 528   
     }
 529   
 
 530   
     /**
 531   
      * Concatenates the system class path in the order specified by
 532   
      * the ${build.sysclasspath} property - using &quot;last&quot; as
 533   
      * default value.
 534   
      */
 535  0
     public Path concatSystemClasspath() {
 536  0
         return concatSystemClasspath("last");
 537   
     }
 538   
 
 539   
     /**
 540   
      * Concatenates the system class path in the order specified by
 541   
      * the ${build.sysclasspath} property - using the supplied value
 542   
      * if ${build.sysclasspath} has not been set.
 543   
      */
 544  318
     public Path concatSystemClasspath(String defValue) {
 545   
 
 546  318
         Path result = new Path(getProject());
 547   
 
 548  318
         String order = defValue;
 549  318
         if (getProject() != null) {
 550  318
             String o = getProject().getProperty("build.sysclasspath");
 551  318
             if (o != null) {
 552  2
                 order = o;
 553   
             }
 554   
         }
 555   
         
 556  318
         if (order.equals("only")) {
 557   
             // only: the developer knows what (s)he is doing
 558  6
             result.addExisting(Path.systemClasspath, true);
 559   
         
 560  312
         } else if (order.equals("first")) {
 561   
             // first: developer could use a little help
 562  0
             result.addExisting(Path.systemClasspath, true);
 563  0
             result.addExisting(this);
 564   
 
 565  312
         } else if (order.equals("ignore")) {
 566   
             // ignore: don't trust anyone
 567  295
             result.addExisting(this);
 568   
 
 569   
         } else {
 570   
             // last: don't trust the developer
 571  17
             if (!order.equals("last")) {
 572  0
                 log("invalid value for build.sysclasspath: " + order, 
 573   
                     Project.MSG_WARN);
 574   
             }
 575   
 
 576  17
             result.addExisting(this);
 577  17
             result.addExisting(Path.systemClasspath, true);
 578   
         }
 579   
         
 580   
 
 581  318
         return result;
 582   
 
 583   
     }
 584   
 
 585   
     /**
 586   
      * Add the Java Runtime classes to this Path instance.
 587   
      */
 588  2
     public void addJavaRuntime() {
 589  2
         if (System.getProperty("java.vendor").toLowerCase(Locale.US).indexOf("microsoft") >= 0) {
 590   
             // Pull in *.zip from packages directory
 591  0
             FileSet msZipFiles = new FileSet();
 592  0
             msZipFiles.setDir(new File(System.getProperty("java.home") 
 593   
                 + File.separator + "Packages"));
 594  0
             msZipFiles.setIncludes("*.ZIP");
 595  0
             addFileset(msZipFiles);
 596  2
         } else if ("Kaffe".equals(System.getProperty("java.vm.name"))) {
 597  0
             FileSet kaffeJarFiles = new FileSet();
 598  0
             kaffeJarFiles.setDir(new File(System.getProperty("java.home") 
 599   
                                           + File.separator + "share"
 600   
                                           + File.separator + "kaffe"));
 601   
             
 602  0
             kaffeJarFiles.setIncludes("*.jar");
 603  0
             addFileset(kaffeJarFiles);
 604  2
         } else if (JavaEnvUtils.isJavaVersion(JavaEnvUtils.JAVA_1_1)) {
 605  0
             addExisting(new Path(null,
 606   
                                  System.getProperty("java.home")
 607   
                                  + File.separator + "lib"
 608   
                                  + File.separator
 609   
                                  + "classes.zip"));
 610   
         } else {
 611   
             // JDK > 1.1 seems to set java.home to the JRE directory.
 612  2
             addExisting(new Path(null,
 613   
                                  System.getProperty("java.home")
 614   
                                  + File.separator + "lib"
 615   
                                  + File.separator + "rt.jar"));
 616   
             // Just keep the old version as well and let addExisting
 617   
             // sort it out.
 618  2
             addExisting(new Path(null,
 619   
                                  System.getProperty("java.home")
 620   
                                  + File.separator + "jre"
 621   
                                  + File.separator + "lib"
 622   
                                  + File.separator + "rt.jar"));
 623   
 
 624   
             // Sun's and Apple's 1.4 have JCE and JSSE in separate jars.
 625  2
             String[] secJars = { "jce", "jsse" };
 626  2
             for (int i = 0; i < secJars.length; i++) {
 627  4
                 addExisting(new Path(null,
 628   
                                      System.getProperty("java.home")
 629   
                                      + File.separator + "lib"
 630   
                                      + File.separator + secJars[i] + ".jar"));
 631  4
                 addExisting(new Path(null,
 632   
                                      System.getProperty("java.home")
 633   
                                      + File.separator + ".."
 634   
                                      + File.separator + "Classes"
 635   
                                      + File.separator + secJars[i] + ".jar"));
 636   
             }
 637   
 
 638   
             // IBM's 1.4 has rt.jar split into 4 smaller jars and a combined
 639   
             // JCE/JSSE in security.jar.
 640  2
             String[] ibmJars =
 641   
                 { "core", "graphics", "security", "server", "xml" };
 642  2
             for (int i = 0; i < ibmJars.length; i++) {
 643  10
                 addExisting(new Path(null,
 644   
                                      System.getProperty("java.home")
 645   
                                      + File.separator + "lib"
 646   
                                      + File.separator + ibmJars[i] + ".jar"));
 647   
             }
 648   
 
 649   
             // Added for MacOS X
 650  2
             addExisting(new Path(null,
 651   
                                  System.getProperty("java.home")
 652   
                                  + File.separator + ".."
 653   
                                  + File.separator + "Classes"
 654   
                                  + File.separator + "classes.jar"));
 655  2
             addExisting(new Path(null,
 656   
                                  System.getProperty("java.home")
 657   
                                  + File.separator + ".."
 658   
                                  + File.separator + "Classes"
 659   
                                  + File.separator + "ui.jar"));
 660   
         }
 661   
     }
 662   
 
 663   
     /**
 664   
      * Emulation of extdirs feature in java >= 1.2.
 665   
      * This method adds all files in the given
 666   
      * directories (but not in sub-directories!) to the classpath,
 667   
      * so that you don't have to specify them all one by one.
 668   
      * @param extdirs - Path to append files to
 669   
      */
 670  0
     public void addExtdirs(Path extdirs) {
 671  0
         if (extdirs == null) {
 672  0
             String extProp = System.getProperty("java.ext.dirs");
 673  0
             if (extProp != null) {
 674  0
                 extdirs = new Path(getProject(), extProp);
 675   
             } else {
 676  0
                 return;
 677   
             }
 678   
         }
 679   
 
 680  0
         String[] dirs = extdirs.list();
 681  0
         for (int i = 0; i < dirs.length; i++) {
 682  0
             File dir = getProject().resolveFile(dirs[i]);
 683  0
             if (dir.exists() && dir.isDirectory()) {
 684  0
                 FileSet fs = new FileSet();
 685  0
                 fs.setDir(dir);
 686  0
                 fs.setIncludes("*");
 687  0
                 addFileset(fs);
 688   
             }
 689   
         }
 690   
     }
 691   
 }
 692