diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/Charset.java b/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/Charset.java new file mode 100644 index 000000000..a2963e13a --- /dev/null +++ b/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/Charset.java @@ -0,0 +1,13 @@ +package org.teavm.classlib.impl.charset; + +/** + * + * @author Alexey Andreev + */ +public abstract class Charset { + public abstract int encode(int[] buffer, int offset, int length, byte[] dest, int destOffset, int destLength); + + public abstract int decode(byte[] buffer, int offset, int length, int[] dest, int destOffset, int destLength); + + public static native Charset get(String name); +} diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/CharsetName.java b/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/CharsetName.java new file mode 100644 index 000000000..e8b488cd3 --- /dev/null +++ b/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/CharsetName.java @@ -0,0 +1,16 @@ +package org.teavm.classlib.impl.charset; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +/** + * + * @author Alexey Andreev + */ +@Retention(RetentionPolicy.CLASS) +@Target(ElementType.TYPE) +public @interface CharsetName { + String value(); +} diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/UTF16Charset.java b/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/UTF16Charset.java new file mode 100644 index 000000000..8bf3d0d44 --- /dev/null +++ b/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/UTF16Charset.java @@ -0,0 +1,10 @@ +package org.teavm.classlib.impl.charset; + +/** + * + * @author Alexey Andreev + */ +@CharsetName("UTF-16") +public class UTF16Charset { + +} diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/UTF8Charset.java b/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/UTF8Charset.java new file mode 100644 index 000000000..59b866e69 --- /dev/null +++ b/teavm-classlib/src/main/java/org/teavm/classlib/impl/charset/UTF8Charset.java @@ -0,0 +1,18 @@ +package org.teavm.classlib.impl.charset; + +/** + * + * @author Alexey Andreev + */ +@CharsetName("UTF-8") +public class UTF8Charset extends Charset { + @Override + public int encode(int[] buffer, int offset, int length, byte[] dest, int destOffset, int destLength) { + return 0; + } + + @Override + public int decode(byte[] buffer, int offset, int length, int[] dest, int destOffset, int destLength) { + return 0; + } +} diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/TAbstractStringBuilder.java b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/TAbstractStringBuilder.java index 2a6246d03..a8e143a4d 100644 --- a/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/TAbstractStringBuilder.java +++ b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/TAbstractStringBuilder.java @@ -351,4 +351,17 @@ class TAbstractStringBuilder extends TObject implements TSerializable, TCharSequ // TODO: implement throw new TUnsupportedOperationException(); } + + public void getChars(int srcBegin, int srcEnd, char[] dst, int dstBegin) { + if (srcBegin > srcEnd) { + throw new TIndexOutOfBoundsException(TString.wrap("Index out of bounds")); + } + while (srcBegin < srcEnd) { + dst[dstBegin++] = buffer[srcBegin++]; + } + } + + public void setLength(int newLength) { + length = 0; + } } diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/TAutoCloseable.java b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/TAutoCloseable.java new file mode 100644 index 000000000..7606f9ae5 --- /dev/null +++ b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/TAutoCloseable.java @@ -0,0 +1,9 @@ +package org.teavm.classlib.java.lang; + +/** + * + * @author Alexey Andreev + */ +public interface TAutoCloseable { + void close() throws TException; +} diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TCloseable.java b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TCloseable.java new file mode 100644 index 000000000..1bc55c48b --- /dev/null +++ b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TCloseable.java @@ -0,0 +1,12 @@ +package org.teavm.classlib.java.lang.io; + +import org.teavm.classlib.java.lang.TAutoCloseable; + +/** + * + * @author Alexey Andreev + */ +public interface TCloseable extends TAutoCloseable { + @Override + void close() throws TIOException; +} diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TFilterOutputStream.java b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TFilterOutputStream.java new file mode 100644 index 000000000..d396f2e20 --- /dev/null +++ b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TFilterOutputStream.java @@ -0,0 +1,33 @@ +package org.teavm.classlib.java.lang.io; + +/** + * + * @author Alexey Andreev + */ +public class TFilterOutputStream extends TOutputStream { + protected TOutputStream out; + + public TFilterOutputStream(TOutputStream out) { + this.out = out; + } + + @Override + public void write(int b) throws TIOException { + out.write(b); + } + + @Override + public void close() throws TIOException { + try { + out.flush(); + } catch (TIOException e) { + // do nothing + } + close(); + } + + @Override + public void flush() throws TIOException { + out.flush(); + } +} diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TFlushable.java b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TFlushable.java new file mode 100644 index 000000000..a5e8c0a23 --- /dev/null +++ b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TFlushable.java @@ -0,0 +1,9 @@ +package org.teavm.classlib.java.lang.io; + +/** + * + * @author Alexey Andreev + */ +public interface TFlushable { + void flush() throws TIOException; +} diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TIOException.java b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TIOException.java new file mode 100644 index 000000000..e212c3fe0 --- /dev/null +++ b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TIOException.java @@ -0,0 +1,29 @@ +package org.teavm.classlib.java.lang.io; + +import org.teavm.classlib.java.lang.TException; +import org.teavm.classlib.java.lang.TString; +import org.teavm.classlib.java.lang.TThrowable; + +/** + * + * @author Alexey Andreev + */ +public class TIOException extends TException { + private static final long serialVersionUID = 3626109154700059455L; + + public TIOException() { + super(); + } + + public TIOException(TString message, TThrowable cause) { + super(message, cause); + } + + public TIOException(TString message) { + super(message); + } + + public TIOException(TThrowable cause) { + super(cause); + } +} diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TOutputStream.java b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TOutputStream.java new file mode 100644 index 000000000..5de5e3a57 --- /dev/null +++ b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TOutputStream.java @@ -0,0 +1,29 @@ +package org.teavm.classlib.java.lang.io; + +import org.teavm.classlib.java.lang.TObject; + +/** + * + * @author Alexey Andreev + */ +public abstract class TOutputStream extends TObject implements TCloseable, TFlushable { + public abstract void write(int b) throws TIOException; + + public void write(byte[] b) throws TIOException { + write(b, 0, b.length); + } + + public void write(byte[] b, int off, int len) throws TIOException { + for (int i = 0; i < len; ++i) { + write(b[off++]); + } + } + + @Override + public void close() throws TIOException { + } + + @Override + public void flush() throws TIOException { + } +} diff --git a/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TPrintStream.java b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TPrintStream.java new file mode 100644 index 000000000..69ad1feb7 --- /dev/null +++ b/teavm-classlib/src/main/java/org/teavm/classlib/java/lang/io/TPrintStream.java @@ -0,0 +1,112 @@ +package org.teavm.classlib.java.lang.io; + +import org.teavm.classlib.java.lang.TStringBuilder; + +/** + * + * @author Alexey Andreev + */ +public class TPrintStream extends TFilterOutputStream { + private boolean autoFlush; + private boolean errorState; + private TStringBuilder sb = new TStringBuilder(); + private char[] buffer = new char[32]; + + public TPrintStream(TOutputStream out, boolean autoFlush) { + super(out); + this.autoFlush = autoFlush; + } + + public TPrintStream(TOutputStream out) { + this(out, false); + } + + public boolean checkError() { + flush(); + return errorState; + } + + protected void setError() { + errorState = true; + } + + protected void clearError() { + errorState = false; + } + + @Override + public void write(int b) { + if (!check()) { + return; + } + try { + out.write(b); + } catch (TIOException e) { + errorState = true; + } + if (autoFlush && !errorState) { + flush(); + } + } + + @Override + public void write(byte[] b, int off, int len) { + if (!check()) { + return; + } + try { + out.write(b, off, len); + } catch (TIOException e) { + errorState = true; + } + } + + @Override + public void close() throws TIOException { + if (!checkError()) { + return; + } + try { + out.close(); + } catch (TIOException e) { + errorState = true; + } finally { + out = null; + } + } + + @Override + public void flush() throws TIOException { + if (!check()) { + return; + } + try { + out.flush(); + } catch (TIOException e) { + errorState = true; + } + } + + private boolean check() { + if (out == null) { + errorState = true; + } + return !errorState; + } + + public void print(char[] s) { + + } + + public void print(int i) { + sb.append(i); + printSB(); + } + + private void printSB() { + char[] buffer = sb.length() > this.buffer.length ? new char[sb.length()] : this.buffer; + sb.getChars(0, sb.length(), buffer, 0); + print(buffer); + sb.setLength(0); + } +} diff --git a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ClassTests.java b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ClassTest.java similarity index 97% rename from teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ClassTests.java rename to teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ClassTest.java index 75b79c960..d1c11e141 100644 --- a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ClassTests.java +++ b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ClassTest.java @@ -7,7 +7,7 @@ import org.junit.Test; * * @author Alexey Andreev */ -public class ClassTests { +public class ClassTest { @Test public void classNameEvaluated() { assertEquals("java.lang.Object", Object.class.getName()); diff --git a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ObjectTests.java b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ObjectTest.java similarity index 97% rename from teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ObjectTests.java rename to teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ObjectTest.java index b099399f3..c419c4936 100644 --- a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ObjectTests.java +++ b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/ObjectTest.java @@ -7,7 +7,7 @@ import org.junit.Test; * * @author Alexey Andreev */ -public class ObjectTests { +public class ObjectTest { @Test public void objectCreated() { Object a = new Object(); diff --git a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringBuilderTests.java b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringBuilderTest.java similarity index 99% rename from teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringBuilderTests.java rename to teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringBuilderTest.java index 7397ee384..3737ff41d 100644 --- a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringBuilderTests.java +++ b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringBuilderTest.java @@ -7,7 +7,7 @@ import org.junit.Test; * * @author Alexey Andreev */ -public class StringBuilderTests { +public class StringBuilderTest { @Test public void integerAppended() { StringBuilder sb = new StringBuilder(); diff --git a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringTests.java b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringTest.java similarity index 99% rename from teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringTests.java rename to teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringTest.java index 04e1bd06c..21572dd0b 100644 --- a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringTests.java +++ b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/StringTest.java @@ -7,7 +7,7 @@ import org.junit.Test; * * @author Alexey Andreev */ -public class StringTests { +public class StringTest { @Test public void charsExtracted() { String str = "123"; diff --git a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/SystemTests.java b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/SystemTest.java similarity index 97% rename from teavm-classlib/src/test/java/org/teavm/classlib/java/lang/SystemTests.java rename to teavm-classlib/src/test/java/org/teavm/classlib/java/lang/SystemTest.java index 33c4d9c3c..3b617bece 100644 --- a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/SystemTests.java +++ b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/SystemTest.java @@ -7,7 +7,7 @@ import org.junit.Test; * * @author Alexey Andreev */ -public class SystemTests { +public class SystemTest { @Test public void copiesArray() { Object a = new Object(); diff --git a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/VMTests.java b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/VMTest.java similarity index 97% rename from teavm-classlib/src/test/java/org/teavm/classlib/java/lang/VMTests.java rename to teavm-classlib/src/test/java/org/teavm/classlib/java/lang/VMTest.java index 9b7ea6632..762876f9c 100644 --- a/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/VMTests.java +++ b/teavm-classlib/src/test/java/org/teavm/classlib/java/lang/VMTest.java @@ -7,7 +7,7 @@ import org.junit.Test; * * @author Alexey Andreev */ -public class VMTests { +public class VMTest { @Test public void multiArrayCreated() { int[][] array = new int[2][3]; diff --git a/teavm-maven-plugin/src/main/java/org/teavm/maven/BuildJavascriptJUnitMojo.java b/teavm-maven-plugin/src/main/java/org/teavm/maven/BuildJavascriptJUnitMojo.java index 93a6a89a4..0780cbe0e 100644 --- a/teavm-maven-plugin/src/main/java/org/teavm/maven/BuildJavascriptJUnitMojo.java +++ b/teavm-maven-plugin/src/main/java/org/teavm/maven/BuildJavascriptJUnitMojo.java @@ -129,10 +129,14 @@ public class BuildJavascriptJUnitMojo extends AbstractMojo { } allTestsWriter.write("], function() {}); }"); } + int methodsGenerated = 0; + log.info("Generating test files"); for (MethodReference method : testMethods) { - log.info("Building test for " + method); + log.debug("Building test for " + method); decompileClassesForTest(classLoader, method, fileNames.get(method)); + ++methodsGenerated; } + log.info("Test files successfully generated for " + methodsGenerated + " method(s)"); } catch (IOException e) { throw new MojoFailureException("IO error occured generating JavaScript files", e); } diff --git a/teavm-maven-plugin/src/main/java/org/teavm/maven/BuildJavascriptMojo.java b/teavm-maven-plugin/src/main/java/org/teavm/maven/BuildJavascriptMojo.java index 045ac37b7..85e5ae69b 100644 --- a/teavm-maven-plugin/src/main/java/org/teavm/maven/BuildJavascriptMojo.java +++ b/teavm-maven-plugin/src/main/java/org/teavm/maven/BuildJavascriptMojo.java @@ -14,6 +14,9 @@ import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.Parameter; import org.apache.maven.project.MavenProject; import org.teavm.javascript.JavascriptBuilder; +import org.teavm.model.MethodDescriptor; +import org.teavm.model.MethodReference; +import org.teavm.model.ValueType; /** * @@ -36,6 +39,9 @@ public class BuildJavascriptMojo extends AbstractMojo { @Parameter private boolean minifiying = true; + @Parameter + private String mainClass; + public void setProject(MavenProject project) { this.project = project; } @@ -60,6 +66,10 @@ public class BuildJavascriptMojo extends AbstractMojo { log.info("Building JavaScript file"); JavascriptBuilder builder = new JavascriptBuilder(classLoader); builder.setMinifying(minifiying); + MethodDescriptor mainMethodDesc = new MethodDescriptor("main", ValueType.arrayOf( + ValueType.object("java.lang.String")), ValueType.VOID); + builder.entryPoint("main", new MethodReference(mainClass, mainMethodDesc)) + .withValue(1, "java.lang.String"); builder.build(targetFile); log.info("JavaScript file successfully built"); } catch (RuntimeException e) { diff --git a/teavm-maven-plugin/src/test/java/.gitignore b/teavm-maven-plugin/src/test/java/.gitignore new file mode 100644 index 000000000..e69de29bb diff --git a/teavm-maven-plugin/src/test/resources/.gitignore b/teavm-maven-plugin/src/test/resources/.gitignore new file mode 100644 index 000000000..e69de29bb