Robert Schuster writes: > Hi guys, > today I tripped on some weird incompatibility between ecj (3.3.1 as > found in Debian Lenny) and gjar 0.95: > > gjar creates jars which need zip version 2.0 to extract, while e.g. > fastjar creates files which are readable by version 1.0. > > This is what 'file' says: > > src1-fastjar.jar: Zip archive data, at least v1.0 to extract > src1-gjar.jar: Zip archive data, at least v2.0 to extract > > The problem comes when you want to compile something with ecj and put > such a jar (the gjar-created one) in the classpath or bootclasspath. > > It simply does not find the files! > > ecj -cp ../src1-gjar.jar use/Test.java Now, this is very odd. It really shouldn't happen unless the runtime libraries used by ecj and by jar are different. > ---------- > 1. ERROR in use/Test.java (at line 3) > import base.Base; > ^^^^ > The import base cannot be resolved > ---------- > 2. ERROR in use/Test.java (at line 9) > Base b = new Base("Test"); > ^^^^ > Base cannot be resolved to a type > ---------- > 3. ERROR in use/Test.java (at line 9) > Base b = new Base("Test"); > ^^^^ > Base cannot be resolved to a type > ---------- > 3 problems (3 errors)rob@linkist:~/tmp/jartest/src2$ > > Looking at the jar's content reveals that a class is there: > gjar -tf src1-gjar.jar > > META-INF/MANIFEST.MF > ./base/Base.class > > Who is the one to blame? Is ecj unable to process version 2.0 zip files > or does gjar create unsuitable files? Is this a known issue? Sun's jar also sometimes creates zip v2.0 files. Try this: touch file.file {jdk}/bin/jar cf x.jar file.file x.jar: Zip archive data, at least v2.0 to extract ecj uses the runtime library's java.util.zip.*, so it can't simply be the zip version that's causing the problem? I wonder: is it simply that some files are compressed? The DEFLATE algorithm is probably why unzip version 2.0 is needed. The difference is that some files are compressed. unzip -lv ../src1-gjar.jar Archive: ../src1-gjar.jar Length Method Size Ratio Date Time CRC-32 Name -------- ------ ------- ----- ---- ---- ------ ---- 25 Defl:N 27 -8% 12-03-07 15:30 ee027fb2 META-INF/MANIFEST.MF 354 Stored 354 0% 12-03-07 15:30 0bee6f8e ./base/Base.class -------- ------- --- ------- 379 381 -1% 2 files unzip -lv ../src1-fastjar.jar Archive: ../src1-fastjar.jar Length Method Size Ratio Date Time CRC-32 Name -------- ------ ------- ----- ---- ---- ------ ---- 0 Stored 0 0% 12-03-07 15:28 00000000 META-INF/ 44 Stored 44 0% 12-03-07 15:28 616d2db8 META-INF/MANIFEST.MF 354 Stored 354 0% 11-29-07 23:42 0bee6f8e base/Base.class -------- ------- --- ------- 398 398 0% 3 files unzip -lv ../src1-jar.jar Archive: ../src1-jar.jar Length Method Size Ratio Date Time CRC-32 Name -------- ------ ------- ----- ---- ---- ------ ---- 0 Stored 0 0% 12-03-07 15:33 00000000 META-INF/ 71 Stored 71 0% 12-03-07 15:33 8f35f6c2 META-INF/MANIFEST.MF 354 Stored 354 0% 11-29-07 23:42 0bee6f8e base/Base.class -------- ------- --- ------- 425 425 0% 3 files OK, I'm going to do an experiment. Let's try this: $ gjar cvf ../src1-gjar.jar ./base/Base.class adding: ./base/Base.class (in=354) (out=354) (stored 26%) $ jar cvf ../src1-gjar.jar ./base/Base.class added manifest adding: base/Base.class(in = 354) (out= 265)(deflated 25%) Note that gjar adds "./" to the start of the path, and jar does not. That's the bug: gjar needs to strip "./" from the start of the path. $ gjar cvf ../src1-gjar.jar base/Base.class adding: base/Base.class (in=354) (out=354) (stored 26%) $ cd ../src2/ $ ./compile-gjar ---------- 1. WARNING in use/Test.java (at line 9) Base b = new Base("Test"); ^ The local variable b is never read ---------- 1 problem (1 warning) Andrew. -- Red Hat UK Ltd, Amberley Place, 107-111 Peascod Street, Windsor, Berkshire, SL4 1TE, UK Registered in England and Wales No. 3798903