From 4dbd404f64be8e46637f0e78821c7c8e6ef05fc8 Mon Sep 17 00:00:00 2001 From: Chris Rankin Date: Tue, 21 Nov 2017 17:06:18 +0000 Subject: [PATCH] Integrate our deterministic OpenJDK fork with Avian (#117) * Remove non-deterministic classes from Avian (wip). * Complete integration between Avian and our local OpenJDK fork. * Revert accidental Avian modification. * Implements a "blacklist filter" for Avian's system classloader. * Remove .DSA, .RSA, .SF and .MF files when creating a fat jar. * Revert more accidental Avian changes. * Fix breakage with dependencies, and retain Kryo instance. * Apply blacklisting per thread rather than globally. * Blacklist java.lang.ClassLoader and all java.lang.Thread* classes. * Add comment explaining class blacklisting. * Fix Avian when building without OpenJDK. * Configure ProGuard to keep more classes for deserialisation. * Retain explicit return type for secure random function. * Add sources of random numbers to the class blacklist. * Blacklist the threading classes more precisely. * Make SystemClassLoader.isForbidden() static. * Prevent ProGuard from removing SerializedLambda.readResolve(). * Remove Avian tests involving direct buffers. --- .../net/corda/core/crypto/CryptoUtils.kt | 2 +- .../net/corda/core/utilities/SgxSupport.kt | 5 +- sgx-jvm/Makefile | 2 +- .../classpath/avian/SystemClassLoader.java | 49 + .../avian/classpath/avian/http/Handler.java | 148 --- sgx-jvm/avian/classpath/java-io.cpp | 80 -- sgx-jvm/avian/classpath/java-lang.cpp | 151 --- sgx-jvm/avian/classpath/java-net.cpp | 145 --- sgx-jvm/avian/classpath/java-nio.cpp | 884 +----------------- sgx-jvm/avian/classpath/java/io/File.java | 93 -- .../classpath/java/io/ObjectInputStream.java | 443 --------- .../classpath/java/io/ObjectOutputStream.java | 337 ------- .../classpath/java/io/RandomAccessFile.java | 51 - sgx-jvm/avian/classpath/java/lang/Math.java | 8 - sgx-jvm/avian/classpath/java/lang/System.java | 10 - sgx-jvm/avian/classpath/java/lang/Thread.java | 46 - .../classpath/java/net/BindException.java | 21 - .../classpath/java/net/DatagramSocket.java | 19 - .../avian/classpath/java/net/InetAddress.java | 54 +- .../classpath/java/net/InetSocketAddress.java | 65 -- .../classpath/java/net/ServerSocket.java | 17 - sgx-jvm/avian/classpath/java/net/Socket.java | 201 ---- .../classpath/java/net/SocketAddress.java | 13 - sgx-jvm/avian/classpath/java/net/URL.java | 4 +- .../nio/channels/ClosedSelectorException.java | 13 - .../java/nio/channels/DatagramChannel.java | 239 ----- .../java/nio/channels/FileChannel.java | 35 - .../java/nio/channels/SelectableChannel.java | 43 - .../java/nio/channels/SelectionKey.java | 83 -- .../classpath/java/nio/channels/Selector.java | 52 -- .../nio/channels/ServerSocketChannel.java | 93 -- .../java/nio/channels/SocketChannel.java | 214 ----- .../java/nio/channels/SocketSelector.java | 133 --- .../avian/classpath/java/util/ArrayList.java | 21 - .../avian/classpath/java/util/Calendar.java | 2 +- .../classpath/java/util/Collections.java | 12 +- sgx-jvm/avian/classpath/java/util/Date.java | 4 - sgx-jvm/avian/classpath/java/util/Random.java | 10 - .../avian/classpath/java/util/TreeMap.java | 24 - sgx-jvm/avian/classpath/java/util/UUID.java | 13 - .../concurrent/ExecutorCompletionService.java | 73 -- .../java/util/concurrent/FutureTask.java | 40 +- .../util/concurrent/LinkedBlockingQueue.java | 302 ------ .../java/util/concurrent/TimeUnit.java | 16 - .../classpath/java/util/zip/ZipEntry.java | 1 - sgx-jvm/avian/classpath/sockets.cpp | 205 ---- sgx-jvm/avian/classpath/sockets.h | 74 -- sgx-jvm/avian/corda.pro | 14 + sgx-jvm/avian/makefile | 6 +- sgx-jvm/avian/openjdk-src.mk | 2 - sgx-jvm/avian/src/avian/machine.h | 3 + sgx-jvm/avian/src/builtin.cpp | 6 + sgx-jvm/avian/src/classpath-avian.cpp | 1 + sgx-jvm/avian/src/classpath-openjdk.cpp | 2 +- sgx-jvm/avian/src/machine.cpp | 46 + sgx-jvm/avian/src/types.def | 1 + .../avian/test/BufferedInputStreamTest.java | 10 - sgx-jvm/avian/test/Buffers.java | 25 +- sgx-jvm/avian/test/CompletionServiceTest.java | 54 -- sgx-jvm/avian/test/FutureTaskTest.java | 72 -- .../avian/test/LinkedBlockingQueueTest.java | 208 ----- sgx-jvm/avian/test/MemoryRamp.java | 6 +- sgx-jvm/avian/test/Misc.java | 2 - sgx-jvm/avian/test/extra/SendFile.java | 73 -- sgx-jvm/avian/test/extra/SendServer.java | 92 -- sgx-jvm/avian/test/extra/Sockets.java | 41 - sgx-jvm/jvm-enclave/enclave/CMakeLists.txt | 5 +- .../jvm-enclave/enclave/create-boot-jar.sh | 11 +- sgx-jvm/jvm-enclave/enclave/enclave.cpp | 11 +- sgx-jvm/jvm-enclave/enclave/enclave.xml | 2 +- sgx-jvm/jvm-enclave/jni/jni_sgx_api.cpp | 4 +- sgx-jvm/linux-sgx/psw/urts/loader.cpp | 2 +- verify-enclave/build.gradle | 9 +- .../com/r3/enclaves/txverify/Enclavelet.kt | 49 +- .../txverify/EnclaveletSerializationScheme.kt | 6 + .../com/r3/enclaves/txverify/NativeSgxApi.kt | 3 +- .../com/r3/enclaves/DummySystemClassLoader.kt | 6 + .../r3/enclaves/txverify/EnclaveletTest.kt | 4 + 78 files changed, 238 insertions(+), 5088 deletions(-) delete mode 100644 sgx-jvm/avian/classpath/avian/http/Handler.java delete mode 100644 sgx-jvm/avian/classpath/java-net.cpp delete mode 100644 sgx-jvm/avian/classpath/java/io/ObjectInputStream.java delete mode 100644 sgx-jvm/avian/classpath/java/io/ObjectOutputStream.java delete mode 100644 sgx-jvm/avian/classpath/java/net/BindException.java delete mode 100644 sgx-jvm/avian/classpath/java/net/DatagramSocket.java delete mode 100644 sgx-jvm/avian/classpath/java/net/InetSocketAddress.java delete mode 100644 sgx-jvm/avian/classpath/java/net/ServerSocket.java delete mode 100644 sgx-jvm/avian/classpath/java/net/Socket.java delete mode 100644 sgx-jvm/avian/classpath/java/net/SocketAddress.java delete mode 100644 sgx-jvm/avian/classpath/java/nio/channels/ClosedSelectorException.java delete mode 100644 sgx-jvm/avian/classpath/java/nio/channels/DatagramChannel.java delete mode 100644 sgx-jvm/avian/classpath/java/nio/channels/FileChannel.java delete mode 100644 sgx-jvm/avian/classpath/java/nio/channels/SelectableChannel.java delete mode 100644 sgx-jvm/avian/classpath/java/nio/channels/SelectionKey.java delete mode 100644 sgx-jvm/avian/classpath/java/nio/channels/Selector.java delete mode 100644 sgx-jvm/avian/classpath/java/nio/channels/ServerSocketChannel.java delete mode 100644 sgx-jvm/avian/classpath/java/nio/channels/SocketChannel.java delete mode 100644 sgx-jvm/avian/classpath/java/nio/channels/SocketSelector.java delete mode 100644 sgx-jvm/avian/classpath/java/util/concurrent/ExecutorCompletionService.java delete mode 100644 sgx-jvm/avian/classpath/java/util/concurrent/LinkedBlockingQueue.java delete mode 100644 sgx-jvm/avian/classpath/sockets.cpp delete mode 100644 sgx-jvm/avian/classpath/sockets.h create mode 100644 sgx-jvm/avian/corda.pro delete mode 100644 sgx-jvm/avian/test/CompletionServiceTest.java delete mode 100644 sgx-jvm/avian/test/LinkedBlockingQueueTest.java delete mode 100644 sgx-jvm/avian/test/extra/SendFile.java delete mode 100644 sgx-jvm/avian/test/extra/SendServer.java delete mode 100644 sgx-jvm/avian/test/extra/Sockets.java create mode 100644 verify-enclave/src/test/kotlin/com/r3/enclaves/DummySystemClassLoader.kt diff --git a/core/src/main/kotlin/net/corda/core/crypto/CryptoUtils.kt b/core/src/main/kotlin/net/corda/core/crypto/CryptoUtils.kt index c02ef10bb6..8549908a25 100644 --- a/core/src/main/kotlin/net/corda/core/crypto/CryptoUtils.kt +++ b/core/src/main/kotlin/net/corda/core/crypto/CryptoUtils.kt @@ -219,7 +219,7 @@ private val _newSecureRandom: () -> SecureRandom by lazy { * which should never happen and suggests an unusual JVM or non-standard Java library. */ @Throws(NoSuchAlgorithmException::class) -fun newSecureRandom() = _newSecureRandom() +fun newSecureRandom(): SecureRandom = _newSecureRandom() /** * Returns a random positive non-zero long generated using a secure RNG. This function sacrifies a bit of entropy in order diff --git a/core/src/main/kotlin/net/corda/core/utilities/SgxSupport.kt b/core/src/main/kotlin/net/corda/core/utilities/SgxSupport.kt index 7e3bd03cfc..b4691cb1e0 100644 --- a/core/src/main/kotlin/net/corda/core/utilities/SgxSupport.kt +++ b/core/src/main/kotlin/net/corda/core/utilities/SgxSupport.kt @@ -1,7 +1,8 @@ package net.corda.core.utilities object SgxSupport { + @JvmStatic val isInsideEnclave: Boolean by lazy { - System.getProperty("os.name") == "Linux" && (System.getProperty("java.vm.name") == "Avian") + (System.getProperty("os.name") == "Linux") && (System.getProperty("java.vm.name") == "Avian (Corda)") } -} \ No newline at end of file +} diff --git a/sgx-jvm/Makefile b/sgx-jvm/Makefile index 2b67d641af..cc297d4481 100644 --- a/sgx-jvm/Makefile +++ b/sgx-jvm/Makefile @@ -11,7 +11,7 @@ all: jvm-enclave/standalone/build/standalone_sgx_verify linux-sgx-driver/isgx.ko # The final binary jvm-enclave/standalone/build/standalone_sgx_verify: avian linux-sgx/build/linux/aesm_service - JAVA_HOME=$(JAVA_HOME) $(MAKE) -C jvm-enclave + JAVA_HOME=$(JAVA_HOME) JDK_IMAGE=$(JDK_IMAGE) $(MAKE) -C jvm-enclave # Avian with SGX support AVIAN_EXTRA_CFLAGS="-I$(ROOT)/usr/include -I$(ROOT)/usr/include/x86_64-linux-gnu" diff --git a/sgx-jvm/avian/classpath/avian/SystemClassLoader.java b/sgx-jvm/avian/classpath/avian/SystemClassLoader.java index 71c3749f60..15ee5e69b9 100644 --- a/sgx-jvm/avian/classpath/avian/SystemClassLoader.java +++ b/sgx-jvm/avian/classpath/avian/SystemClassLoader.java @@ -18,6 +18,9 @@ import java.util.Collections; import java.util.ArrayList; import java.util.Enumeration; import java.util.NoSuchElementException; +import java.util.LinkedHashSet; +import java.util.Set; +import java.util.regex.Pattern; public class SystemClassLoader extends ClassLoader { public static native ClassLoader appLoader(); @@ -25,6 +28,7 @@ public class SystemClassLoader extends ClassLoader { private native VMClass findVMClass(String name) throws ClassNotFoundException; + @Override protected Class findClass(String name) throws ClassNotFoundException { return getClass(findVMClass(name)); } @@ -35,11 +39,54 @@ public class SystemClassLoader extends ClassLoader { private native VMClass findLoadedVMClass(String name); + private static native void startBlacklisting0(); + + public void startBlacklisting() { + if (isForbidden("java/util/regex/Pattern$Test")) { + throw new IllegalStateException("Impossible!"); + } + startBlacklisting0(); + } + + private static final Set BLACKLIST = Collections.unmodifiableSet(setOf( + Pattern.compile("^java/lang/reflect/"), + Pattern.compile("^java/lang/invoke/"), + Pattern.compile("^java/io/File"), + Pattern.compile("^java/net/"), + Pattern.compile("^java/.*Random$"), + Pattern.compile("^java/util/concurrent/"), + Pattern.compile("^java/lang/ClassLoader$"), + Pattern.compile("^java/lang/(Inheritable)?ThreadLocal$"), + Pattern.compile("^java/lang/Thread$"), + Pattern.compile("^com/sun/"), + Pattern.compile("^sun/") + )); + + private static Set setOf(T... items) { + Set set = new LinkedHashSet(); + Collections.addAll(set, items); + return set; + } + + /* + * Invoked via JNI, so uses the specification + * rather than the class name. + */ + private static boolean isForbidden(String spec) { + for (Pattern bad : BLACKLIST) { + if (bad.matcher(spec).find()) { + return true; + } + } + return false; + } + protected Class reallyFindLoadedClass(String name){ VMClass c = findLoadedVMClass(name); return c == null ? null : getClass(c); } + @Override protected Class loadClass(String name, boolean resolve) throws ClassNotFoundException { @@ -83,6 +130,7 @@ public class SystemClassLoader extends ClassLoader { // appropriate for the Avian build, so we override it to ensure we // get the behavior we want. This implementation is the same as // that of Avian's java.lang.ClassLoader.getResource. + @Override public URL getResource(String path) { URL url = null; ClassLoader parent = getParent(); @@ -99,6 +147,7 @@ public class SystemClassLoader extends ClassLoader { // As above, we override this method to avoid inappropriate behavior // in OpenJDK's java.lang.ClassLoader.getResources. + @Override public Enumeration getResources(String name) throws IOException { Collection urls = new ArrayList(5); diff --git a/sgx-jvm/avian/classpath/avian/http/Handler.java b/sgx-jvm/avian/classpath/avian/http/Handler.java deleted file mode 100644 index 03eec5b2c8..0000000000 --- a/sgx-jvm/avian/classpath/avian/http/Handler.java +++ /dev/null @@ -1,148 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package avian.http; - -import java.io.BufferedInputStream; -import java.io.BufferedReader; -import java.io.BufferedWriter; -import java.io.ByteArrayInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.io.InputStreamReader; -import java.io.OutputStream; -import java.io.OutputStreamWriter; -import java.net.Socket; -import java.net.URL; -import java.net.URLConnection; -import java.net.URLStreamHandler; -import java.util.ArrayList; -import java.util.Collections; -import java.util.HashMap; -import java.util.List; -import java.util.Map; - -public class Handler extends URLStreamHandler -{ - public URLConnection openConnection(URL url) throws IOException - { - return new HttpURLConnection(url); - } - - class HttpURLConnection extends URLConnection - { - private static final String HKEY_CONTENT_LENGTH = "content-length"; - - Socket socket; - private BufferedWriter writer; - private InputStream bin; - private Map> header = new HashMap>(); - private int status; - - protected HttpURLConnection(URL url) - { - super(url); - } - - @Override - public void connect() throws IOException - { - if(socket == null) - { - URLConnection con = null; - String host = url.getHost(); - int port =url.getPort(); - if(port < 0) port = 80; - socket = new Socket(host, port); - OutputStream out = socket.getOutputStream(); - writer = new BufferedWriter(new OutputStreamWriter(out)); - writer.write("GET " + url.getPath() + " HTTP/1.1"); - writer.write("\r\nHost: " + host); - writer.write("\r\n\r\n"); - writer.flush(); - bin = new BufferedInputStream(socket.getInputStream()); - readHeader(); -// System.out.println("Status: " + status); -// System.out.println("Headers: " + header); - } - } - - private void readHeader() throws IOException - { - byte[] buf = new byte[8192]; - int b = 0; - int index = 0; - while(b >= 0) - { - if(index >= 4 && buf[index-4] == '\r' && buf[index-3] == '\n' && buf[index-2] == '\r' && buf[index-1] == '\n') - { - break; - } - b = bin.read(); - buf[index] = (byte) b; - index++; - if(index >= buf.length) - { - throw new IOException("Header exceeded maximum size of 8k."); - } - } - BufferedReader reader = new BufferedReader(new InputStreamReader(new ByteArrayInputStream(buf, 0, index))); - String line = reader.readLine(); - int x = line.indexOf(' '); - status = Integer.parseInt(line.substring(x + 1 , line.indexOf(' ', x+1))); - while(line != null) - { - int i = line.indexOf(':'); - if(i > 0) - { - String key = line.substring(0, i).toLowerCase(); - String value = line.substring(i + 1).trim(); - - List valueList = new ArrayList(); - valueList.add(value); - header.put(key, Collections.unmodifiableList(valueList)); - } - line = reader.readLine(); - } - reader.close(); - } - - @Override - public InputStream getInputStream() throws IOException - { - connect(); - return bin; - } - - @Override - public OutputStream getOutputStream() throws IOException - { - throw new UnsupportedOperationException("Can' write to HTTP Connection"); - } - - @Override - public int getContentLength() - { - return getHeaderFieldInt(HKEY_CONTENT_LENGTH, -1); - } - - @Override - public long getContentLengthLong() - { - return getHeaderFieldLong(HKEY_CONTENT_LENGTH, -1l); - } - - @Override - public Map> getHeaderFields() - { - return Collections.unmodifiableMap(header); - } - } -} diff --git a/sgx-jvm/avian/classpath/java-io.cpp b/sgx-jvm/avian/classpath/java-io.cpp index 2ca5ee04d1..2cf264efbd 100644 --- a/sgx-jvm/avian/classpath/java-io.cpp +++ b/sgx-jvm/avian/classpath/java-io.cpp @@ -347,65 +347,6 @@ extern "C" JNIEXPORT jlong JNICALL return 0; } -extern "C" JNIEXPORT void JNICALL - Java_java_io_File_mkdir(JNIEnv* e, jclass, jstring path) -{ - string_t chars = getChars(e, path); - if (chars) { - if (not exists(chars)) { - int r = ::MKDIR(chars, 0777); - if (r != 0) { - throwNewErrno(e, "java/io/IOException"); - } - } - releaseChars(e, path, chars); - } -} - -extern "C" JNIEXPORT jboolean JNICALL - Java_java_io_File_createNewFile(JNIEnv* e, jclass, jstring path) -{ - bool result = false; - string_t chars = getChars(e, path); - if (chars) { - if (not exists(chars)) { - int fd = OPEN(chars, O_CREAT | O_WRONLY | O_EXCL, 0666); - if (fd == -1) { - if (errno != EEXIST) { - throwNewErrno(e, "java/io/IOException"); - } - } else { - result = true; - doClose(e, fd); - } - } - releaseChars(e, path, chars); - } - return result; -} - -extern "C" JNIEXPORT void JNICALL -Java_java_io_File_delete(JNIEnv* e, jclass, jstring path) -{ - string_t chars = getChars(e, path); - int r; - if (chars) { -#ifdef PLATFORM_WINDOWS - if (GetFileAttributes(chars) & FILE_ATTRIBUTE_DIRECTORY) { - r = !RemoveDirectory(chars); - } else { - r = REMOVE(chars); - } -#else - r = REMOVE(chars); -#endif - if (r != 0) { - throwNewErrno(e, "java/io/IOException"); - } - releaseChars(e, path, chars); - } -} - extern "C" JNIEXPORT jboolean JNICALL Java_java_io_File_canRead(JNIEnv* e, jclass, jstring path) { @@ -497,27 +438,6 @@ extern "C" JNIEXPORT jboolean JNICALL #endif -extern "C" JNIEXPORT jboolean JNICALL - Java_java_io_File_rename(JNIEnv* e, jclass, jstring old, jstring new_) -{ - string_t oldChars = getChars(e, old); - string_t newChars = getChars(e, new_); - if (oldChars) { - bool v; - if (newChars) { - v = RENAME(oldChars, newChars) == 0; - - releaseChars(e, new_, newChars); - } else { - v = false; - } - releaseChars(e, old, oldChars); - return v; - } else { - return false; - } -} - extern "C" JNIEXPORT jboolean JNICALL Java_java_io_File_isDirectory(JNIEnv* e, jclass, jstring path) { diff --git a/sgx-jvm/avian/classpath/java-lang.cpp b/sgx-jvm/avian/classpath/java-lang.cpp index 75f89088cd..631b6b1742 100644 --- a/sgx-jvm/avian/classpath/java-lang.cpp +++ b/sgx-jvm/avian/classpath/java-lang.cpp @@ -376,103 +376,6 @@ void copyAndEscape(char** dest, const char* src, size_t length) *dest = destp; } -extern "C" JNIEXPORT void JNICALL - Java_java_lang_Runtime_exec(JNIEnv* e, - jclass, - jobjectArray command, - jlongArray process) -{ -#if !defined(WINAPI_FAMILY) || WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP) - int size = 0; - for (int i = 0; i < e->GetArrayLength(command); ++i) { - jstring element = (jstring)e->GetObjectArrayElement(command, i); - if (element) { - // worst case, assuming every character is '"', and we escape all of them - size += 2 * e->GetStringUTFLength(element) + 3; - } else { - throwNew(e, - "java/lang/NullPointerException", - strdup("null string array element")); - } - } - - RUNTIME_ARRAY(char, line, size); - char* linep = RUNTIME_ARRAY_BODY(line); - for (int i = 0; i < e->GetArrayLength(command); ++i) { - if (i) - *(linep++) = _T(' '); - jstring element = (jstring)e->GetObjectArrayElement(command, i); - const char* s = e->GetStringUTFChars(element, 0); - - copyAndEscape(&linep, s, e->GetStringUTFLength(element)); - - e->ReleaseStringUTFChars(element, s); - } - *(linep++) = _T('\0'); - - HANDLE in[] = {0, 0}; - HANDLE out[] = {0, 0}; - HANDLE err[] = {0, 0}; - - makePipe(e, in); - SetHandleInformation(in[0], HANDLE_FLAG_INHERIT, 0); - jlong inDescriptor = static_cast(descriptor(e, in[0])); - if (e->ExceptionCheck()) - return; - e->SetLongArrayRegion(process, 2, 1, &inDescriptor); - makePipe(e, out); - SetHandleInformation(out[1], HANDLE_FLAG_INHERIT, 0); - jlong outDescriptor = static_cast(descriptor(e, out[1])); - if (e->ExceptionCheck()) - return; - e->SetLongArrayRegion(process, 3, 1, &outDescriptor); - makePipe(e, err); - SetHandleInformation(err[0], HANDLE_FLAG_INHERIT, 0); - jlong errDescriptor = static_cast(descriptor(e, err[0])); - if (e->ExceptionCheck()) - return; - e->SetLongArrayRegion(process, 4, 1, &errDescriptor); - - PROCESS_INFORMATION pi; - ZeroMemory(&pi, sizeof(pi)); - - STARTUPINFO si; - ZeroMemory(&si, sizeof(si)); - si.cb = sizeof(si); - si.dwFlags = STARTF_USESTDHANDLES; - si.hStdOutput = in[1]; - si.hStdInput = out[0]; - si.hStdError = err[1]; - - BOOL success = CreateProcess(0, - (LPSTR)RUNTIME_ARRAY_BODY(line), - 0, - 0, - 1, - CREATE_NO_WINDOW | CREATE_UNICODE_ENVIRONMENT, - 0, - 0, - &si, - &pi); - - CloseHandle(in[1]); - CloseHandle(out[0]); - CloseHandle(err[1]); - - if (not success) { - throwNew(e, "java/io/IOException", getErrorStr(GetLastError())); - return; - } - - jlong pid = reinterpret_cast(pi.hProcess); - e->SetLongArrayRegion(process, 0, 1, &pid); - jlong tid = reinterpret_cast(pi.hThread); - e->SetLongArrayRegion(process, 1, 1, &tid); -#else - throwNew(e, "java/io/Exception", strdup("Not supported on WinRT/WinPhone8")); -#endif -} - extern "C" JNIEXPORT jint JNICALL Java_java_lang_Runtime_waitFor(JNIEnv* e, jclass, jlong pid, jlong tid) { @@ -1003,60 +906,6 @@ extern "C" JNIEXPORT jobjectArray JNICALL return array; } -// System.getEnvironment() implementation -// TODO: For Win32, replace usage of deprecated _environ and add Unicode -// support (neither of which is likely to be of great importance). -#ifdef AVIAN_IOS -namespace { -const char* environ[] = {0}; -} -#elif defined __APPLE__ -#include -#define environ (*_NSGetEnviron()) -#elif defined(WINAPI_FAMILY) \ - && !WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP) -// WinRT/WP8 does not provide alternative for environment variables -char* environ[] = {0}; -#else -extern char** environ; -#endif -extern "C" JNIEXPORT jobjectArray JNICALL - Java_java_lang_System_getEnvironment(JNIEnv* env, jclass) -{ - int length; - for (length = 0; environ[length] != 0; ++length) - ; - - jobjectArray stringArray = env->NewObjectArray( - length, env->FindClass("java/lang/String"), env->NewStringUTF("")); - - for (int i = 0; i < length; i++) { - jobject varString = env->NewStringUTF(environ[i]); - env->SetObjectArrayElement(stringArray, i, varString); - } - - return stringArray; -} - -extern "C" JNIEXPORT jlong JNICALL - Java_java_lang_System_currentTimeMillis(JNIEnv*, jclass) -{ -#ifdef PLATFORM_WINDOWS - // We used to use _ftime here, but that only gives us 1-second - // resolution on Windows 7. _ftime_s might work better, but MinGW - // doesn't have it as of this writing. So we use this mess instead: - FILETIME time; - GetSystemTimeAsFileTime(&time); - return (((static_cast(time.dwHighDateTime) << 32) | time.dwLowDateTime) - / 10000) - 11644473600000LL; -#else - timeval tv = {0, 0}; - gettimeofday(&tv, 0); - return (static_cast(tv.tv_sec) * 1000) - + (static_cast(tv.tv_usec) / 1000); -#endif -} - extern "C" JNIEXPORT jstring JNICALL Java_java_lang_System_doMapLibraryName(JNIEnv* e, jclass, jstring name) { diff --git a/sgx-jvm/avian/classpath/java-net.cpp b/sgx-jvm/avian/classpath/java-net.cpp deleted file mode 100644 index cafb02238a..0000000000 --- a/sgx-jvm/avian/classpath/java-net.cpp +++ /dev/null @@ -1,145 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -#ifndef SGX - -#include "jni.h" -#include "avian/machine.h" -#include "sockets.h" -#include "jni-util.h" - -using namespace avian::classpath::sockets; - -extern "C" JNIEXPORT void JNICALL Java_java_net_Socket_init(JNIEnv* e, jclass) -{ - init(e); -} - -extern "C" JNIEXPORT SOCKET JNICALL - Java_java_net_Socket_create(JNIEnv* e, jclass) -{ - return create(e); -} - -extern "C" JNIEXPORT void JNICALL Java_java_net_Socket_connect(JNIEnv* e, - jclass, - jlong sock, - jlong addr, - jshort port) -{ - connect(e, static_cast(sock), addr, port); -} - -extern "C" JNIEXPORT void JNICALL Java_java_net_Socket_bind(JNIEnv* e, - jclass, - jlong sock, - jlong addr, - jshort port) -{ - bind(e, static_cast(sock), addr, port); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_net_Socket_abort(JNIEnv* e, jclass, jlong sock) -{ - abort(e, static_cast(sock)); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_net_Socket_close(JNIEnv* e, jclass, jlong sock) -{ - close(e, static_cast(sock)); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_net_Socket_closeOutput(JNIEnv* e, jclass, jlong sock) -{ - close_output(e, static_cast(sock)); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_net_Socket_closeInput(JNIEnv* e, jclass, jlong sock) -{ - close_input(e, static_cast(sock)); -} - -extern "C" JNIEXPORT void JNICALL - Avian_java_net_Socket_send(vm::Thread* t, vm::object, uintptr_t* arguments) -{ /* SOCKET s, object buffer_obj, int start_pos, int count */ - SOCKET& s = *(reinterpret_cast(&arguments[0])); - vm::GcByteArray* buffer_obj = vm::cast( - t, reinterpret_cast(arguments[2])); - int32_t& start_pos = *(reinterpret_cast(&arguments[3])); - int32_t& count = *(reinterpret_cast(&arguments[4])); - char* buffer = reinterpret_cast(&buffer_obj->body()[start_pos]); - avian::classpath::sockets::send((JNIEnv*)t, s, buffer, count); -} - -extern "C" JNIEXPORT int64_t JNICALL - Avian_java_net_Socket_recv(vm::Thread* t, vm::object, uintptr_t* arguments) -{ /* SOCKET s, object buffer_obj, int start_pos, int count */ - SOCKET& s = *(reinterpret_cast(&arguments[0])); - vm::GcByteArray* buffer_obj = vm::cast( - t, reinterpret_cast(arguments[2])); - int32_t& start_pos = *(reinterpret_cast(&arguments[3])); - int32_t& count = *(reinterpret_cast(&arguments[4])); - char* buffer = reinterpret_cast(&buffer_obj->body()[start_pos]); - return avian::classpath::sockets::recv((JNIEnv*)t, s, buffer, count); -} - -extern "C" JNIEXPORT jint JNICALL - Java_java_net_InetAddress_ipv4AddressForName(JNIEnv* e, - jclass, - jstring name) -{ - if(!name) { - throwNew(e, "java/lang/NullPointerException", 0); - return 0; - } - - const char* chars = e->GetStringUTFChars(name, 0); - if (chars) { -#ifdef PLATFORM_WINDOWS - hostent* host = gethostbyname(chars); - e->ReleaseStringUTFChars(name, chars); - if (host) { - return ntohl(reinterpret_cast(host->h_addr_list[0])->s_addr); - } else { - throwNew(e, "java/net/UnknownHostException", 0); - return 0; - } -#else - addrinfo hints; - memset(&hints, 0, sizeof(addrinfo)); - hints.ai_family = AF_INET; - hints.ai_socktype = SOCK_STREAM; - - addrinfo* result; - int r = getaddrinfo(chars, 0, &hints, &result); - e->ReleaseStringUTFChars(name, chars); - - if (r != 0) { - throwNew(e, "java/net/UnknownHostException", 0); - return 0; - } else { - int address = ntohl( - reinterpret_cast(result->ai_addr)->sin_addr.s_addr); - - freeaddrinfo(result); - return address; - } -#endif - } else { - throwNew(e, "java/lang/OutOfMemoryError", 0); - return 0; - } -} - -#endif // !SGX \ No newline at end of file diff --git a/sgx-jvm/avian/classpath/java-nio.cpp b/sgx-jvm/avian/classpath/java-nio.cpp index e04adc2d70..a384ea2315 100644 --- a/sgx-jvm/avian/classpath/java-nio.cpp +++ b/sgx-jvm/avian/classpath/java-nio.cpp @@ -85,18 +85,6 @@ inline jbyteArray errorString(JNIEnv* e, int n) #endif } -inline jbyteArray socketErrorString(JNIEnv* e, int n) -{ -#ifdef PLATFORM_WINDOWS - const unsigned size = 64; - char buffer[size]; - snprintf(buffer, size, "wsa code: %d", n); - return charsToArray(e, buffer); -#else - return errorString(e, n); -#endif -} - inline jbyteArray errorString(JNIEnv* e) { #ifdef PLATFORM_WINDOWS @@ -132,37 +120,6 @@ void throwIOException(JNIEnv* e) throwIOException(e, errorString(e)); } -void throwSocketException(JNIEnv* e, const char* s) -{ - throwNew(e, "java/net/SocketException", s); -} - -void throwSocketException(JNIEnv* e, jbyteArray a) -{ - size_t length = e->GetArrayLength(a); - uint8_t* buf = static_cast(allocate(e, length)); - if (buf) { - e->GetByteArrayRegion(a, 0, length, reinterpret_cast(buf)); - throwSocketException(e, reinterpret_cast(buf)); - free(buf); - } else { - return; - } -} - -void throwSocketException(JNIEnv* e) -{ - throwSocketException(e, errorString(e)); -} - -void init(sockaddr_in* address, jint host, jint port) -{ - memset(address, 0, sizeof(sockaddr_in)); - address->sin_family = AF_INET; - address->sin_port = htons(port); - address->sin_addr.s_addr = htonl(host); -} - inline bool einProgress(int error) { #ifdef PLATFORM_WINDOWS @@ -172,26 +129,6 @@ inline bool einProgress(int error) #endif } -inline bool einProgress() -{ -#ifdef PLATFORM_WINDOWS - return WSAGetLastError() == WSAEINPROGRESS - or WSAGetLastError() == WSAEWOULDBLOCK; -#else - return errno == EINPROGRESS; -#endif -} - -inline bool eagain() -{ -#ifdef PLATFORM_WINDOWS - return WSAGetLastError() == WSAEINPROGRESS - or WSAGetLastError() == WSAEWOULDBLOCK; -#else - return errno == EAGAIN; -#endif -} - bool setBlocking(JNIEnv* e, int d, bool blocking) { #ifdef PLATFORM_WINDOWS @@ -214,609 +151,32 @@ bool setBlocking(JNIEnv* e, int d, bool blocking) return true; } -bool setTcpNoDelay(JNIEnv* e, int d, bool on) -{ - int flag = on; - int r = setsockopt( - d, IPPROTO_TCP, TCP_NODELAY, reinterpret_cast(&flag), sizeof(int)); - if (r < 0) { - throwSocketException(e); - return false; - } - return true; -} - -void doBind(JNIEnv* e, int s, sockaddr_in* address) -{ - { - int opt = 1; - int r = ::setsockopt(s, - SOL_SOCKET, - SO_REUSEADDR, - reinterpret_cast(&opt), - sizeof(int)); - if (r != 0) { - throwIOException(e); - return; - } - } - -#ifdef SO_NOSIGPIPE - { - int opt = 1; - int r = ::setsockopt(s, - SOL_SOCKET, - SO_NOSIGPIPE, - reinterpret_cast(&opt), - sizeof(int)); - if (r != 0) { - throwIOException(e); - return; - } - } -#endif - - { - int r - = ::bind(s, reinterpret_cast(address), sizeof(sockaddr_in)); - if (r != 0) { - throwIOException(e); - return; - } - } -} - -void doListen(JNIEnv* e, int s) -{ - int r = ::listen(s, 100); - if (r != 0) { - throwIOException(e); - } -} - -void doFinishConnect(JNIEnv* e, int socket) -{ - int error; - socklen_t size = sizeof(int); - int r = getsockopt( - socket, SOL_SOCKET, SO_ERROR, reinterpret_cast(&error), &size); - - if (r != 0 or size != sizeof(int)) { - throwIOException(e); - } else if (error and not einProgress(error)) { - throwIOException(e, socketErrorString(e, error)); - } -} - -bool doConnect(JNIEnv* e, int s, sockaddr_in* address) -{ - int r - = ::connect(s, reinterpret_cast(address), sizeof(sockaddr_in)); - if (r == 0) { - return true; - } else if (not einProgress()) { - throwIOException(e); - return false; - } else { - return false; - } -} - -int doAccept(JNIEnv* e, int s) -{ - sockaddr address; - socklen_t length = sizeof(address); - int r = ::accept(s, &address, &length); - if (r >= 0) { - return r; - } else if (errno != EINTR) { - throwIOException(e); - } - return -1; -} - -int doRead(int fd, void* buffer, size_t count) +inline bool einProgress() { #ifdef PLATFORM_WINDOWS - return recv(fd, static_cast(buffer), count, 0); + return WSAGetLastError() == WSAEINPROGRESS + or WSAGetLastError() == WSAEWOULDBLOCK; #else - return read(fd, buffer, count); + return errno == EINPROGRESS; #endif } -int doRecv(int fd, void* buffer, size_t count, int32_t* host, int32_t* port) -{ - sockaddr address; - socklen_t length = sizeof(address); - int r = recvfrom(fd, static_cast(buffer), count, 0, &address, &length); - - if (r > 0) { - sockaddr_in a; - memcpy(&a, &address, length); - *host = ntohl(a.sin_addr.s_addr); - *port = ntohs(a.sin_port); - } else { - *host = 0; - *port = 0; - } - - return r; -} - -int doWrite(int fd, const void* buffer, size_t count) +inline bool eagain() { #ifdef PLATFORM_WINDOWS - return send(fd, static_cast(buffer), count, 0); + return WSAGetLastError() == WSAEINPROGRESS + or WSAGetLastError() == WSAEWOULDBLOCK; #else - return write(fd, buffer, count); + return errno == EAGAIN; #endif } -int doSend(int fd, sockaddr_in* address, const void* buffer, size_t count) -{ - return sendto(fd, - static_cast(buffer), - count, - 0, - reinterpret_cast(address), - sizeof(sockaddr_in)); -} - -int makeSocket(JNIEnv* e, int type = SOCK_STREAM, int protocol = IPPROTO_TCP) -{ - int s = ::socket(AF_INET, type, protocol); - if (s < 0) { - throwIOException(e); - return s; - } - - return s; -} - } // namespace -extern "C" JNIEXPORT jint JNICALL - Java_java_nio_channels_ServerSocketChannel_natDoAccept(JNIEnv* e, - jclass, - jint socket) -{ - return ::doAccept(e, socket); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_ServerSocketChannel_natDoListen(JNIEnv* e, - jclass, - jint socket, - jint host, - jint port) -{ - sockaddr_in address; - init(&address, host, port); - - ::doBind(e, socket, &address); - if (e->ExceptionCheck()) - return; - - ::doListen(e, socket); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_SocketChannel_bind(JNIEnv* e, - jclass, - jint socket, - jint host, - jint port) -{ - sockaddr_in address; - init(&address, host, port); - - ::doBind(e, socket, &address); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_DatagramChannel_bind(JNIEnv* e, - jclass c, - jint socket, - jint host, - jint port) -{ - Java_java_nio_channels_SocketChannel_bind(e, c, socket, host, port); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_SocketChannel_configureBlocking(JNIEnv* e, - jclass, - jint socket, - jboolean blocking) -{ - setBlocking(e, socket, blocking); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_DatagramChannel_configureBlocking(JNIEnv* e, - jclass c, - jint socket, - jboolean blocking) -{ - return Java_java_nio_channels_SocketChannel_configureBlocking( - e, c, socket, blocking); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_SocketChannel_natSetTcpNoDelay(JNIEnv* e, - jclass, - jint socket, - jboolean on) -{ - setTcpNoDelay(e, socket, on); -} - -extern "C" JNIEXPORT jboolean JNICALL - Java_java_nio_channels_SocketChannel_natDoConnect(JNIEnv* e, - jclass, - jint socket, - jint host, - jint port) -{ - sockaddr_in address; - init(&address, host, port); - - return ::doConnect(e, socket, &address); -} - -extern "C" JNIEXPORT jint JNICALL - Java_java_nio_channels_SocketChannel_makeSocket(JNIEnv* e, jclass) -{ - return makeSocket(e); -} - -extern "C" JNIEXPORT jint JNICALL - Java_java_nio_channels_DatagramChannel_makeSocket(JNIEnv* e, jclass) -{ - return makeSocket(e, SOCK_DGRAM, IPPROTO_UDP); -} - -extern "C" JNIEXPORT jboolean JNICALL - Java_java_nio_channels_DatagramChannel_connect(JNIEnv* e, - jclass, - jint socket, - jint host, - jint port) -{ - sockaddr_in address; - init(&address, host, port); - - return ::doConnect(e, socket, &address); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_SocketChannel_natFinishConnect(JNIEnv* e, - jclass, - jint socket) -{ - doFinishConnect(e, socket); -} - -extern "C" JNIEXPORT jint JNICALL - Java_java_nio_channels_SocketChannel_natRead(JNIEnv* e, - jclass, - jint socket, - jbyteArray buffer, - jint offset, - jint length, - jboolean blocking) -{ - int r; - if (blocking) { - uint8_t* buf = static_cast(allocate(e, length)); - if (buf) { - r = ::doRead(socket, buf, length); - if (r > 0) { - e->SetByteArrayRegion(buffer, offset, r, reinterpret_cast(buf)); - } - free(buf); - } else { - return 0; - } - } else { - jboolean isCopy; - uint8_t* buf - = static_cast(e->GetPrimitiveArrayCritical(buffer, &isCopy)); - - r = ::doRead(socket, buf + offset, length); - - e->ReleasePrimitiveArrayCritical(buffer, buf, 0); - } - - if (r < 0) { - if (eagain()) { - return 0; - } else { - throwIOException(e); - } - } else if (r == 0) { - return -1; - } - return r; -} - -extern "C" JNIEXPORT jint JNICALL - Java_java_nio_channels_DatagramChannel_receive(JNIEnv* e, - jclass, - jint socket, - jbyteArray buffer, - jint offset, - jint length, - jboolean blocking, - jintArray address) -{ - int r; - int32_t host; - int32_t port; - if (blocking) { - uint8_t* buf = static_cast(allocate(e, length)); - if (buf) { - r = ::doRecv(socket, buf, length, &host, &port); - if (r > 0) { - e->SetByteArrayRegion(buffer, offset, r, reinterpret_cast(buf)); - } - free(buf); - } else { - return 0; - } - } else { - jboolean isCopy; - uint8_t* buf - = static_cast(e->GetPrimitiveArrayCritical(buffer, &isCopy)); - - r = ::doRecv(socket, buf + offset, length, &host, &port); - - e->ReleasePrimitiveArrayCritical(buffer, buf, 0); - } - - if (r < 0) { - if (eagain()) { - return 0; - } else { - throwIOException(e); - } - } else if (r == 0) { - return -1; - } else { - jint jhost = host; - e->SetIntArrayRegion(address, 0, 1, &jhost); - jint jport = port; - e->SetIntArrayRegion(address, 1, 1, &jport); - } - - return r; -} - -extern "C" JNIEXPORT jint JNICALL - Java_java_nio_channels_SocketChannel_natWrite(JNIEnv* e, - jclass, - jint socket, - jbyteArray buffer, - jint offset, - jint length, - jboolean blocking) -{ - int r; - if (blocking) { - uint8_t* buf = static_cast(allocate(e, length)); - if (buf) { - e->GetByteArrayRegion( - buffer, offset, length, reinterpret_cast(buf)); - r = ::doWrite(socket, buf, length); - free(buf); - } else { - return 0; - } - } else { - jboolean isCopy; - uint8_t* buf - = static_cast(e->GetPrimitiveArrayCritical(buffer, &isCopy)); - - r = ::doWrite(socket, buf + offset, length); - - e->ReleasePrimitiveArrayCritical(buffer, buf, 0); - } - - if (r < 0) { - if (eagain()) { - return 0; - } else { - throwIOException(e); - } - } - return r; -} - -extern "C" JNIEXPORT jint JNICALL - Java_java_nio_channels_DatagramChannel_write(JNIEnv* e, - jclass c, - jint socket, - jbyteArray buffer, - jint offset, - jint length, - jboolean blocking) -{ - return Java_java_nio_channels_SocketChannel_natWrite( - e, c, socket, buffer, offset, length, blocking); -} - -extern "C" JNIEXPORT jint JNICALL - Java_java_nio_channels_DatagramChannel_send(JNIEnv* e, - jclass, - jint socket, - jint host, - jint port, - jbyteArray buffer, - jint offset, - jint length, - jboolean blocking) -{ - sockaddr_in address; - init(&address, host, port); - - int r; - if (blocking) { - uint8_t* buf = static_cast(allocate(e, length)); - if (buf) { - e->GetByteArrayRegion( - buffer, offset, length, reinterpret_cast(buf)); - r = ::doSend(socket, &address, buf, length); - free(buf); - } else { - return 0; - } - } else { - jboolean isCopy; - uint8_t* buf - = static_cast(e->GetPrimitiveArrayCritical(buffer, &isCopy)); - - r = ::doSend(socket, &address, buf + offset, length); - - e->ReleasePrimitiveArrayCritical(buffer, buf, 0); - } - - if (r < 0) { - if (eagain()) { - return 0; - } else { - throwIOException(e); - } - } - return r; -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_SocketChannel_natThrowWriteError(JNIEnv* e, - jclass, - jint socket) -{ - int error; - socklen_t size = sizeof(int); - int r = getsockopt( - socket, SOL_SOCKET, SO_ERROR, reinterpret_cast(&error), &size); - if (r != 0 or size != sizeof(int)) { - throwIOException(e); - } else if (error != 0) { - throwIOException(e, socketErrorString(e, error)); - } -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_SocketChannel_natCloseSocket(JNIEnv*, - jclass, - jint socket) -{ - doClose(socket); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_DatagramChannel_close(JNIEnv*, jclass, jint socket) -{ - doClose(socket); -} - namespace { class Pipe { public: -#ifdef PLATFORM_WINDOWS - // The Windows socket API only accepts socket file descriptors, not - // pipe descriptors or others. Thus, to implement - // Selector.wakeup(), we make a socket connection via the loopback - // interface and use it as a pipe. - Pipe(JNIEnv* e) : connected_(false), listener_(-1), reader_(-1), writer_(-1) - { - sockaddr_in address; - address.sin_family = AF_INET; - address.sin_port = 0; - address.sin_addr.s_addr = inet_addr("127.0.0.1"); // INADDR_LOOPBACK; - - listener_ = makeSocket(e); - if (e->ExceptionCheck()) - return; - - setBlocking(e, listener_, false); - - ::doBind(e, listener_, &address); - if (e->ExceptionCheck()) - return; - - ::doListen(e, listener_); - if (e->ExceptionCheck()) - return; - - socklen_t length = sizeof(sockaddr_in); - int r = getsockname( - listener_, reinterpret_cast(&address), &length); - if (r) { - throwIOException(e); - return; - } - - writer_ = makeSocket(e); - if (e->ExceptionCheck()) - return; - - setBlocking(e, writer_, true); - connected_ = ::doConnect(e, writer_, &address); - } - - void dispose() - { - if (listener_ >= 0) - ::doClose(listener_); - if (reader_ >= 0) - ::doClose(reader_); - if (writer_ >= 0) - ::doClose(writer_); - } - - bool connected() - { - return connected_; - } - - void setConnected(bool v) - { - connected_ = v; - } - - int listener() - { - return listener_; - } - - void setListener(int v) - { - listener_ = v; - } - - int reader() - { - return reader_; - } - - void setReader(int v) - { - reader_ = v; - } - - int writer() - { - return writer_; - } - - private: - bool connected_; - int listener_; - int reader_; - int writer_; -#else Pipe(JNIEnv* e) { if (::pipe(pipe) != 0) { @@ -856,236 +216,10 @@ class Pipe { private: int pipe[2]; bool open_; -#endif -}; - -struct SelectorState { - fd_set read; - fd_set write; - fd_set except; - Pipe control; - SelectorState(JNIEnv* e) : control(e) - { - } }; } // namespace -extern "C" JNIEXPORT jlong JNICALL - Java_java_nio_channels_SocketSelector_natInit(JNIEnv* e, jclass) -{ - void* mem = malloc(sizeof(SelectorState)); - if (mem) { - SelectorState* s = new (mem) SelectorState(e); - if (e->ExceptionCheck()) - return 0; - - if (s) { - FD_ZERO(&(s->read)); - FD_ZERO(&(s->write)); - FD_ZERO(&(s->except)); - return reinterpret_cast(s); - } - } - throwNew(e, "java/lang/OutOfMemoryError", 0); - return 0; -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_SocketSelector_natWakeup(JNIEnv* e, - jclass, - jlong state) -{ - SelectorState* s = reinterpret_cast(state); - if (s->control.connected()) { - const char c = 1; - int r = ::doWrite(s->control.writer(), &c, 1); - if (r != 1) { - throwIOException(e); - } - } -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_SocketSelector_natClose(JNIEnv*, jclass, jlong state) -{ - SelectorState* s = reinterpret_cast(state); - s->control.dispose(); - free(s); -} - -extern "C" JNIEXPORT void JNICALL - Java_java_nio_channels_SocketSelector_natSelectClearAll(JNIEnv*, - jclass, - jint socket, - jlong state) -{ - SelectorState* s = reinterpret_cast(state); - FD_CLR(static_cast(socket), &(s->read)); - FD_CLR(static_cast(socket), &(s->write)); - FD_CLR(static_cast(socket), &(s->except)); -} - -extern "C" JNIEXPORT jint JNICALL - Java_java_nio_channels_SocketSelector_natSelectUpdateInterestSet( - JNIEnv*, - jclass, - jint socket, - jint interest, - jlong state, - jint max) -{ - SelectorState* s = reinterpret_cast(state); - if (interest & (java_nio_channels_SelectionKey_OP_READ - | java_nio_channels_SelectionKey_OP_ACCEPT)) { - FD_SET(static_cast(socket), &(s->read)); - if (max < socket) - max = socket; - } else { - FD_CLR(static_cast(socket), &(s->read)); - } - - if (interest & (java_nio_channels_SelectionKey_OP_WRITE - | java_nio_channels_SelectionKey_OP_CONNECT)) { - FD_SET(static_cast(socket), &(s->write)); - FD_SET(static_cast(socket), &(s->except)); - if (max < socket) - max = socket; - } else { - FD_CLR(static_cast(socket), &(s->write)); - } - return max; -} - -extern "C" JNIEXPORT jint JNICALL - Java_java_nio_channels_SocketSelector_natDoSocketSelect(JNIEnv* e, - jclass, - jlong state, - jint max, - jlong interval) -{ - SelectorState* s = reinterpret_cast(state); - if (s->control.reader() >= 0) { - int socket = s->control.reader(); - FD_SET(static_cast(socket), &(s->read)); - if (max < socket) - max = socket; - } - -#ifdef PLATFORM_WINDOWS - if (s->control.listener() >= 0) { - int socket = s->control.listener(); - FD_SET(static_cast(socket), &(s->read)); - if (max < socket) - max = socket; - } - - if (not s->control.connected()) { - int socket = s->control.writer(); - FD_SET(static_cast(socket), &(s->write)); - FD_SET(static_cast(socket), &(s->except)); - if (max < socket) - max = socket; - } -#endif - - timeval time; - if (interval > 0) { - time.tv_sec = interval / 1000; - time.tv_usec = (interval % 1000) * 1000; - } else if (interval < 0) { - time.tv_sec = 0; - time.tv_usec = 0; - } else { - time.tv_sec = 24 * 60 * 60 * 1000; - time.tv_usec = 0; - } - int r = ::select(max + 1, &(s->read), &(s->write), &(s->except), &time); - - if (r < 0) { - if (errno != EINTR) { - throwIOException(e); - return 0; - } - } - -#ifdef PLATFORM_WINDOWS - if (FD_ISSET(s->control.writer(), &(s->write)) - or FD_ISSET(s->control.writer(), &(s->except))) { - int socket = s->control.writer(); - FD_CLR(static_cast(socket), &(s->write)); - FD_CLR(static_cast(socket), &(s->except)); - - int error; - socklen_t size = sizeof(int); - int r = getsockopt( - socket, SOL_SOCKET, SO_ERROR, reinterpret_cast(&error), &size); - if (r != 0 or size != sizeof(int)) { - throwIOException(e); - } else if (error != 0) { - throwIOException(e, socketErrorString(e, error)); - } - s->control.setConnected(true); - } - - if (s->control.listener() >= 0 - and FD_ISSET(s->control.listener(), &(s->read))) { - FD_CLR(static_cast(s->control.listener()), &(s->read)); - - s->control.setReader(::doAccept(e, s->control.listener())); - s->control.setListener(-1); - } -#endif - - if (s->control.reader() >= 0 and FD_ISSET(s->control.reader(), &(s->read))) { - FD_CLR(static_cast(s->control.reader()), &(s->read)); - - char c; - int r = 1; - while (r == 1) { - r = ::doRead(s->control.reader(), &c, 1); - } - if (r < 0 and not eagain()) { - throwIOException(e); - } - } - - return r; -} - -extern "C" JNIEXPORT jint JNICALL - Java_java_nio_channels_SocketSelector_natUpdateReadySet(JNIEnv*, - jclass, - jint socket, - jint interest, - jlong state) -{ - SelectorState* s = reinterpret_cast(state); - jint ready = 0; - - if (FD_ISSET(socket, &(s->read))) { - if (interest & java_nio_channels_SelectionKey_OP_READ) { - ready |= java_nio_channels_SelectionKey_OP_READ; - } - - if (interest & java_nio_channels_SelectionKey_OP_ACCEPT) { - ready |= java_nio_channels_SelectionKey_OP_ACCEPT; - } - } - - if (FD_ISSET(socket, &(s->write)) or FD_ISSET(socket, &(s->except))) { - if (interest & java_nio_channels_SelectionKey_OP_WRITE) { - ready |= java_nio_channels_SelectionKey_OP_WRITE; - } - - if (interest & java_nio_channels_SelectionKey_OP_CONNECT) { - ready |= java_nio_channels_SelectionKey_OP_CONNECT; - } - } - - return ready; -} - extern "C" JNIEXPORT jboolean JNICALL Java_java_nio_ByteOrder_isNativeBigEndian(JNIEnv*, jclass) { @@ -1099,4 +233,4 @@ extern "C" JNIEXPORT jboolean JNICALL return JNI_FALSE; } -#endif // !SGX \ No newline at end of file +#endif // !SGX diff --git a/sgx-jvm/avian/classpath/java/io/File.java b/sgx-jvm/avian/classpath/java/io/File.java index 10c331498f..fe73b433eb 100644 --- a/sgx-jvm/avian/classpath/java/io/File.java +++ b/sgx-jvm/avian/classpath/java/io/File.java @@ -47,43 +47,6 @@ public class File implements Serializable { this(parent.getPath() + FileSeparator + child); } - public static File createTempFile(String prefix, String suffix) - throws IOException - { - return createTempFile(prefix, suffix, null); - } - - public static File createTempFile(String prefix, String suffix, - File directory) - throws IOException - { - if(directory == null) { - directory = new File(System.getProperty("java.io.tmpdir")); - } - if(suffix == null) { - suffix = ".tmp"; - } - File ret; - long state = System.currentTimeMillis(); - - do { - ret = generateFile(directory, prefix, state, suffix); - state *= 7; - state += 3; - } while(ret == null); - ret.createNewFile(); - return ret; - } - - private static File generateFile(File directory, String prefix, long state, String suffix) { - File ret = new File(directory, prefix + state + suffix); - if(ret.exists()) { - return null; - } else { - return ret; - } - } - private static String stripSeparators(String p) { while (p.length() > 1 && p.endsWith(FileSeparator)) { p = p.substring(0, p.length() - 1); @@ -104,12 +67,6 @@ public class File implements Serializable { ("\\".equals(FileSeparator) ? path.replace('/', '\\') : path); } - public static native boolean rename(String old, String new_); - - public boolean renameTo(File newName) { - return rename(path, newName.path); - } - private static native boolean isDirectory(String path); public boolean isDirectory() { @@ -144,16 +101,6 @@ public class File implements Serializable { return canExecute(path); } - private static native boolean setExecutable(String path, boolean executable, boolean ownerOnly); - - public boolean setExecutable(boolean executable) { - return setExecutable(executable, true); - } - - public boolean setExecutable(boolean executable, boolean ownerOnly) { - return setExecutable(path, executable, ownerOnly); - } - public String getName() { int index = path.lastIndexOf(FileSeparator); if (index >= 0) { @@ -219,46 +166,6 @@ public class File implements Serializable { return exists(path); } - private static native void mkdir(String path) throws IOException; - - public boolean mkdir() { - try { - mkdir(path); - return true; - } catch (IOException e) { - return false; - } - } - - private static native boolean createNewFile(String path) throws IOException; - - public boolean createNewFile() throws IOException { - return createNewFile(path); - } - - public static native void delete(String path) throws IOException; - - public boolean delete() { - try { - delete(path); - return true; - } catch (IOException e) { - return false; - } - } - - public boolean mkdirs() { - File parent = getParentFile(); - if (parent != null) { - if (!parent.exists()) { - if (!parent.mkdirs()) { - return false; - } - } - } - return mkdir(); - } - public File[] listFiles() { return listFiles(null); } diff --git a/sgx-jvm/avian/classpath/java/io/ObjectInputStream.java b/sgx-jvm/avian/classpath/java/io/ObjectInputStream.java deleted file mode 100644 index 66677141de..0000000000 --- a/sgx-jvm/avian/classpath/java/io/ObjectInputStream.java +++ /dev/null @@ -1,443 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.io; - -import static java.io.ObjectOutputStream.STREAM_MAGIC; -import static java.io.ObjectOutputStream.STREAM_VERSION; -import static java.io.ObjectOutputStream.TC_NULL; -import static java.io.ObjectOutputStream.TC_REFERENCE; -import static java.io.ObjectOutputStream.TC_CLASSDESC; -import static java.io.ObjectOutputStream.TC_OBJECT; -import static java.io.ObjectOutputStream.TC_STRING; -import static java.io.ObjectOutputStream.TC_ARRAY; -import static java.io.ObjectOutputStream.TC_CLASS; -import static java.io.ObjectOutputStream.TC_BLOCKDATA; -import static java.io.ObjectOutputStream.TC_ENDBLOCKDATA; -import static java.io.ObjectOutputStream.TC_RESET; -import static java.io.ObjectOutputStream.TC_BLOCKDATALONG; -import static java.io.ObjectOutputStream.TC_EXCEPTION; -import static java.io.ObjectOutputStream.TC_LONGSTRING; -import static java.io.ObjectOutputStream.TC_PROXYCLASSDESC; -import static java.io.ObjectOutputStream.TC_ENUM; -import static java.io.ObjectOutputStream.SC_WRITE_METHOD; -import static java.io.ObjectOutputStream.SC_BLOCK_DATA; -import static java.io.ObjectOutputStream.SC_SERIALIZABLE; -import static java.io.ObjectOutputStream.SC_EXTERNALIZABLE; -import static java.io.ObjectOutputStream.SC_ENUM; -import static java.io.ObjectOutputStream.getReadOrWriteMethod; - -import avian.VMClass; - -import java.util.ArrayList; -import java.util.HashMap; -import java.lang.reflect.Array; -import java.lang.reflect.Field; -import java.lang.reflect.Method; -import java.lang.reflect.Modifier; - -public class ObjectInputStream extends InputStream implements DataInput { - private final static int HANDLE_OFFSET = 0x7e0000; - - private final InputStream in; - private final ArrayList references; - - public ObjectInputStream(InputStream in) throws IOException { - this.in = in; - short signature = (short)rawShort(); - if (signature != STREAM_MAGIC) { - throw new IOException("Unrecognized signature: 0x" - + Integer.toHexString(signature)); - } - int version = rawShort(); - if (version != STREAM_VERSION) { - throw new IOException("Unsupported version: " + version); - } - references = new ArrayList(); - } - - public int read() throws IOException { - return in.read(); - } - - private int rawByte() throws IOException { - int c = read(); - if (c < 0) { - throw new EOFException(); - } - return c; - } - - private int rawShort() throws IOException { - return (rawByte() << 8) | rawByte(); - } - - private int rawInt() throws IOException { - return (rawShort() << 16) | rawShort(); - } - - private long rawLong() throws IOException { - return ((rawInt() & 0xffffffffl) << 32) | rawInt(); - } - - private String rawString() throws IOException { - int length = rawShort(); - byte[] array = new byte[length]; - readFully(array); - return new String(array); - } - - public int read(byte[] b, int offset, int length) throws IOException { - return in.read(b, offset, length); - } - - public void readFully(byte[] b) throws IOException { - readFully(b, 0, b.length); - } - - public void readFully(byte[] b, int offset, int length) throws IOException { - while (length > 0) { - int count = read(b, offset, length); - if (count < 0) { - throw new EOFException("Reached EOF " + length + " bytes too early"); - } - offset += count; - length -= count; - } - } - - public String readLine() throws IOException { - int c = read(); - if (c < 0) { - return null; - } else if (c == '\n') { - return ""; - } - StringBuilder builder = new StringBuilder(); - for (;;) { - builder.append((char)c); - c = read(); - if (c < 0 || c == '\n') { - return builder.toString(); - } - } - } - - public void close() throws IOException { - in.close(); - } - - private int remainingBlockData; - - private int rawBlockDataByte() throws IOException { - while (remainingBlockData <= 0) { - int b = rawByte(); - if (b == TC_BLOCKDATA) { - remainingBlockData = rawByte(); - } else { - throw new UnsupportedOperationException("Unknown token: 0x" - + Integer.toHexString(b)); - } - } - --remainingBlockData; - return rawByte(); - } - - private int rawBlockDataShort() throws IOException { - return (rawBlockDataByte() << 8) | rawBlockDataByte(); - } - - private int rawBlockDataInt() throws IOException { - return (rawBlockDataShort() << 16) | rawBlockDataShort(); - } - - private long rawBlockDataLong() throws IOException { - return ((rawBlockDataInt() & 0xffffffffl) << 32) | rawBlockDataInt(); - } - - public boolean readBoolean() throws IOException { - return rawBlockDataByte() != 0; - } - - public byte readByte() throws IOException { - return (byte)rawBlockDataByte(); - } - - public char readChar() throws IOException { - return (char)rawBlockDataShort(); - } - - public short readShort() throws IOException { - return (short)rawBlockDataShort(); - } - - public int readInt() throws IOException { - return rawBlockDataInt(); - } - - public long readLong() throws IOException { - return rawBlockDataLong(); - } - - public float readFloat() throws IOException { - return Float.intBitsToFloat(rawBlockDataInt()); - } - - public double readDouble() throws IOException { - return Double.longBitsToDouble(rawBlockDataLong()); - } - - public int readUnsignedByte() throws IOException { - return rawBlockDataByte(); - } - - public int readUnsignedShort() throws IOException { - return rawBlockDataShort(); - } - - public String readUTF() throws IOException { - int length = rawBlockDataShort(); - if (remainingBlockData < length) { - throw new IOException("Short block data: " - + remainingBlockData + " < " + length); - } - byte[] bytes = new byte[length]; - readFully(bytes); - remainingBlockData -= length; - return new String(bytes, "UTF-8"); - } - - public int skipBytes(int count) throws IOException { - int i = 0; - while (i < count) { - if (read() < 0) { - return i; - } - ++i; - } - return count; - } - - private static Class charToPrimitiveType(int c) { - if (c == 'B') { - return Byte.TYPE; - } else if (c == 'C') { - return Character.TYPE; - } else if (c == 'D') { - return Double.TYPE; - } else if (c == 'F') { - return Float.TYPE; - } else if (c == 'I') { - return Integer.TYPE; - } else if (c == 'J') { - return Long.TYPE; - } else if (c == 'S') { - return Short.TYPE; - } else if (c == 'Z') { - return Boolean.TYPE; - } - throw new RuntimeException("Unhandled char: " + (char)c); - } - - private void expectToken(int token) throws IOException { - int c = rawByte(); - if (c != token) { - throw new UnsupportedOperationException("Unexpected token: 0x" - + Integer.toHexString(c)); - } - } - - private void field(Field field, Object o) - throws IOException, IllegalArgumentException, IllegalAccessException, - ClassNotFoundException - { - Class type = field.getType(); - if (!type.isPrimitive()) { - field.set(o, readObject()); - } else { - if (type == Byte.TYPE) { - field.setByte(o, (byte)rawByte()); - } else if (type == Character.TYPE) { - field.setChar(o, (char)rawShort()); - } else if (type == Double.TYPE) { - field.setDouble(o, Double.longBitsToDouble(rawLong())); - } else if (type == Float.TYPE) { - field.setFloat(o, Float.intBitsToFloat(rawInt())); - } else if (type == Integer.TYPE) { - field.setInt(o, rawInt()); - } else if (type == Long.TYPE) { - field.setLong(o, rawLong()); - } else if (type == Short.TYPE) { - field.setShort(o, (short)rawShort()); - } else if (type == Boolean.TYPE) { - field.setBoolean(o, rawByte() != 0); - } else { - throw new IOException("Unhandled type: " + type); - } - } - } - - public Object readObject() throws IOException, ClassNotFoundException { - int c = rawByte(); - if (c == TC_NULL) { - return null; - } - if (c == TC_STRING) { - int length = rawShort(); - byte[] bytes = new byte[length]; - readFully(bytes); - String s = new String(bytes, "UTF-8"); - references.add(s); - return s; - } - if (c == TC_REFERENCE) { - int handle = rawInt(); - return references.get(handle - HANDLE_OFFSET); - } - if (c != TC_OBJECT) { - throw new IOException("Unexpected token: 0x" - + Integer.toHexString(c)); - } - - // class desc - c = rawByte(); - ClassDesc classDesc; - if (c == TC_REFERENCE) { - int handle = rawInt() - HANDLE_OFFSET; - classDesc = (ClassDesc)references.get(handle); - } else if (c == TC_CLASSDESC) { - classDesc = classDesc(); - } else { - throw new UnsupportedOperationException("Unexpected token: 0x" - + Integer.toHexString(c)); - } - - try { - Object o = makeInstance(classDesc.clazz.vmClass); - references.add(o); - - do { - Object o1 = classDesc.clazz.cast(o); - boolean customized = (classDesc.flags & SC_WRITE_METHOD) != 0; - Method readMethod = customized ? - getReadOrWriteMethod(o, "readObject") : null; - if (readMethod == null) { - if (customized) { - throw new IOException("Could not find required readObject method " - + "in " + classDesc.clazz); - } - defaultReadObject(o, classDesc.fields); - } else { - current = o1; - currentFields = classDesc.fields; - readMethod.invoke(o, this); - current = null; - currentFields = null; - expectToken(TC_ENDBLOCKDATA); - } - } while ((classDesc = classDesc.superClassDesc) != null); - - return o; - } catch (IOException e) { - throw e; - } catch (Exception e) { - throw new IOException(e); - } - } - - private static class ClassDesc { - Class clazz; - int flags; - Field[] fields; - ClassDesc superClassDesc; - } - - private ClassDesc classDesc() throws ClassNotFoundException, IOException { - ClassDesc result = new ClassDesc(); - String className = rawString(); - ClassLoader loader = Thread.currentThread().getContextClassLoader(); - result.clazz = loader.loadClass(className); - long serialVersionUID = rawLong(); - try { - Field field = result.clazz.getField("serialVersionUID"); - long expected = field.getLong(null); - if (expected != serialVersionUID) { - throw new IOException("Incompatible serial version UID: 0x" - + Long.toHexString(serialVersionUID) + " != 0x" - + Long.toHexString(expected)); - } - } catch (Exception ignored) { } - references.add(result); - - result.flags = rawByte(); - if ((result.flags & ~(SC_SERIALIZABLE | SC_WRITE_METHOD)) != 0) { - throw new UnsupportedOperationException("Cannot handle flags: 0x" - + Integer.toHexString(result.flags)); - } - - int fieldCount = rawShort(); - result.fields = new Field[fieldCount]; - for (int i = 0; i < result.fields.length; i++) { - int typeChar = rawByte(); - String fieldName = rawString(); - try { - result.fields[i] = result.clazz.getDeclaredField(fieldName); - } catch (Exception e) { - throw new IOException(e); - } - Class type; - if (typeChar == '[' || typeChar == 'L') { - String typeName = (String)readObject(); - if (typeName.startsWith("L") && typeName.endsWith(";")) { - typeName = typeName.substring(1, typeName.length() - 1) - .replace('/', '.'); - } - type = loader.loadClass(typeName); - } else { - type = charToPrimitiveType(typeChar); - } - if (result.fields[i].getType() != type) { - throw new IOException("Unexpected type of field " + fieldName - + ": expected " + result.fields[i].getType() + " but got " + type); - } - } - expectToken(TC_ENDBLOCKDATA); - int c = rawByte(); - if (c == TC_CLASSDESC) { - result.superClassDesc = classDesc(); - } else if (c != TC_NULL) { - throw new UnsupportedOperationException("Unexpected token: 0x" - + Integer.toHexString(c)); - } - - return result; - } - - private Object current; - private Field[] currentFields; - - public void defaultReadObject() throws IOException { - defaultReadObject(current, currentFields); - } - - private void defaultReadObject(Object o, Field[] fields) throws IOException { - try { - for (Field field : fields) { - field(field, o); - } - } catch (IOException e) { - throw e; - } catch (Exception e) { - throw new IOException(e); - } - } - - private static native Object makeInstance(VMClass c); -} diff --git a/sgx-jvm/avian/classpath/java/io/ObjectOutputStream.java b/sgx-jvm/avian/classpath/java/io/ObjectOutputStream.java deleted file mode 100644 index 0ed12a2b76..0000000000 --- a/sgx-jvm/avian/classpath/java/io/ObjectOutputStream.java +++ /dev/null @@ -1,337 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.io; - -import java.util.ArrayList; -import java.lang.reflect.Array; -import java.lang.reflect.Field; -import java.lang.reflect.Method; -import java.lang.reflect.Modifier; - -public class ObjectOutputStream extends OutputStream implements DataOutput { - final static short STREAM_MAGIC = (short)0xaced; - final static short STREAM_VERSION = 5; - final static byte TC_NULL = (byte)0x70; - final static byte TC_REFERENCE = (byte)0x71; - final static byte TC_CLASSDESC = (byte)0x72; - final static byte TC_OBJECT = (byte)0x73; - final static byte TC_STRING = (byte)0x74; - final static byte TC_ARRAY = (byte)0x75; - final static byte TC_CLASS = (byte)0x76; - final static byte TC_BLOCKDATA = (byte)0x77; - final static byte TC_ENDBLOCKDATA = (byte)0x78; - final static byte TC_RESET = (byte)0x79; - final static byte TC_BLOCKDATALONG = (byte)0x7a; - final static byte TC_EXCEPTION = (byte)0x7b; - final static byte TC_LONGSTRING = (byte)0x7c; - final static byte TC_PROXYCLASSDESC = (byte)0x7d; - final static byte TC_ENUM = (byte)0x7e; - final static byte SC_WRITE_METHOD = 0x01; //if SC_SERIALIZABLE - final static byte SC_BLOCK_DATA = 0x08; //if SC_EXTERNALIZABLE - final static byte SC_SERIALIZABLE = 0x02; - final static byte SC_EXTERNALIZABLE = 0x04; - final static byte SC_ENUM = 0x10; - - private final OutputStream out; - - public ObjectOutputStream(OutputStream out) throws IOException { - this.out = out; - rawShort(STREAM_MAGIC); - rawShort(STREAM_VERSION); - } - - public void write(int c) throws IOException { - out.write(c); - } - - public void write(byte[] b, int offset, int length) throws IOException { - out.write(b, offset, length); - } - - public void flush() throws IOException { - out.flush(); - } - - public void close() throws IOException { - out.close(); - } - - private void rawByte(int v) throws IOException { - out.write((byte)(v & 0xff)); - } - - private void rawShort(int v) throws IOException { - rawByte(v >> 8); - rawByte(v); - } - - private void rawInt(int v) throws IOException { - rawShort(v >> 16); - rawShort(v); - } - - private void rawLong(long v) throws IOException { - rawInt((int)(v >> 32)); - rawInt((int)(v & 0xffffffffl)); - } - - private void blockData(int... bytes) throws IOException { - blockData(bytes, null, null); - } - - private void blockData(int[] bytes, byte[] bytes2, char[] chars) throws IOException { - int count = (bytes == null ? 0 : bytes.length) - + (bytes2 == null ? 0 : bytes2.length) - + (chars == null ? 0 : chars.length * 2); - if (count < 0x100) { - rawByte(TC_BLOCKDATA); - rawByte(count); - } else { - rawByte(TC_BLOCKDATALONG); - rawInt(count); - } - if (bytes != null) { - for (int b : bytes) { - rawByte(b); - } - } - if (bytes2 != null) { - for (byte b : bytes2) { - rawByte(b & 0xff); - } - } - if (chars != null) { - for (char c : chars) { - rawShort((short)c); - } - } - } - - public void writeBoolean(boolean v) throws IOException { - blockData(v ? 1 : 0); - } - - public void writeByte(int v) throws IOException { - blockData(v); - } - - public void writeShort(int v) throws IOException { - blockData(v >> 8, v); - } - - public void writeChar(int v) throws IOException { - blockData(v >> 8, v); - } - - public void writeInt(int v) throws IOException { - blockData(v >> 24, v >> 16, v >> 8, v); - } - - public void writeLong(long v) throws IOException { - int u = (int)(v >> 32), l = (int)(v & 0xffffffff); - blockData(u >> 24, u >> 16, u >> 8, u, l >> 24, l >> 16, l >> 8, l); - } - - public void writeFloat(float v) throws IOException { - writeInt(Float.floatToIntBits(v)); - } - - public void writeDouble(double v) throws IOException { - writeLong(Double.doubleToLongBits(v)); - } - - public void writeBytes(String s) throws IOException { - blockData(null, s.getBytes(), null); - } - - public void writeChars(String s) throws IOException { - blockData(null, null, s.toCharArray()); - } - - public void writeUTF(String s) throws IOException { - byte[] bytes = s.getBytes(); - int length = bytes.length; - blockData(new int[] { length >> 8, length }, bytes, null); - } - - private int classHandle; - - private void string(String s) throws IOException { - int length = s.length(); - rawShort(length); - for (byte b : s.getBytes()) { - rawByte(b); - } - } - - private static char primitiveTypeChar(Class type) { - if (type == Byte.TYPE) { - return 'B'; - } else if (type == Character.TYPE) { - return 'C'; - } else if (type == Double.TYPE) { - return 'D'; - } else if (type == Float.TYPE) { - return 'F'; - } else if (type == Integer.TYPE) { - return 'I'; - } else if (type == Long.TYPE) { - return 'J'; - } else if (type == Short.TYPE) { - return 'S'; - } else if (type == Boolean.TYPE) { - return 'Z'; - } - throw new RuntimeException("Unhandled primitive type: " + type); - } - - private void classDesc(Class clazz, int scFlags) throws IOException { - rawByte(TC_CLASSDESC); - - // class name - string(clazz.getName()); - - // serial version UID - long serialVersionUID = 1l; - try { - Field field = clazz.getField("serialVersionUID"); - serialVersionUID = field.getLong(null); - } catch (Exception ignored) {} - rawLong(serialVersionUID); - - // handle - rawByte(SC_SERIALIZABLE | scFlags); - - Field[] fields = getFields(clazz); - rawShort(fields.length); - for (Field field : fields) { - Class fieldType = field.getType(); - if (fieldType.isPrimitive()) { - rawByte(primitiveTypeChar(fieldType)); - string(field.getName()); - } else { - rawByte(fieldType.isArray() ? '[' : 'L'); - string(field.getName()); - rawByte(TC_STRING); - string("L" + fieldType.getName().replace('.', '/') + ";"); - } - } - rawByte(TC_ENDBLOCKDATA); // TODO: write annotation - rawByte(TC_NULL); // super class desc - } - - private void field(Object o, Field field) throws IOException { - try { - field.setAccessible(true); - Class type = field.getType(); - if (!type.isPrimitive()) { - writeObject(field.get(o)); - } else if (type == Byte.TYPE) { - rawByte(field.getByte(o)); - } else if (type == Character.TYPE) { - char c = field.getChar(o); - rawShort((short)c); - } else if (type == Double.TYPE) { - double d = field.getDouble(o); - rawLong(Double.doubleToLongBits(d)); - } else if (type == Float.TYPE) { - float f = field.getFloat(o); - rawInt(Float.floatToIntBits(f)); - } else if (type == Integer.TYPE) { - int i = field.getInt(o); - rawInt(i); - } else if (type == Long.TYPE) { - long l = field.getLong(o); - rawLong(l); - } else if (type == Short.TYPE) { - short s = field.getShort(o); - rawShort(s); - } else if (type == Boolean.TYPE) { - boolean b = field.getBoolean(o); - rawByte(b ? 1 : 0); - } else { - throw new UnsupportedOperationException("Field '" + field.getName() - + "' has unsupported type: " + type); - } - } catch (IOException e) { - throw e; - } catch (Exception e) { - throw new IOException(e); - } - } - - private static Field[] getFields(Class clazz) { - ArrayList list = new ArrayList(); - Field[] fields = clazz.getDeclaredFields(); - for (Field field : fields) { - if (0 == (field.getModifiers() & - (Modifier.STATIC | Modifier.TRANSIENT))) { - list.add(field); - } - } - return list.toArray(new Field[list.size()]); - } - - public void writeObject(Object o) throws IOException { - if (o == null) { - rawByte(TC_NULL); - return; - } - if (o instanceof String) { - byte[] bytes = ((String)o).getBytes("UTF-8"); - rawByte(TC_STRING); - rawShort(bytes.length); - write(bytes); - return; - } - rawByte(TC_OBJECT); - Method writeObject = getReadOrWriteMethod(o, "writeObject"); - if (writeObject == null) { - classDesc(o.getClass(), 0); - defaultWriteObject(o); - } else try { - classDesc(o.getClass(), SC_WRITE_METHOD); - current = o; - writeObject.invoke(o, this); - current = null; - rawByte(TC_ENDBLOCKDATA); - } catch (Exception e) { - throw new IOException(e); - } - } - - static Method getReadOrWriteMethod(Object o, String methodName) { - try { - Method method = o.getClass().getDeclaredMethod(methodName, - new Class[] { methodName.startsWith("write") ? - ObjectOutputStream.class : ObjectInputStream.class }); - method.setAccessible(true); - int modifiers = method.getModifiers(); - if ((modifiers & Modifier.STATIC) == 0 || - (modifiers & Modifier.PRIVATE) != 0) { - return method; - } - } catch (NoSuchMethodException ignored) { } - return null; - } - - private Object current; - - public void defaultWriteObject() throws IOException { - defaultWriteObject(current); - } - - private void defaultWriteObject(Object o) throws IOException { - for (Field field : getFields(o.getClass())) { - field(o, field); - } - } -} diff --git a/sgx-jvm/avian/classpath/java/io/RandomAccessFile.java b/sgx-jvm/avian/classpath/java/io/RandomAccessFile.java index 4739b9ea78..3669aba4d5 100644 --- a/sgx-jvm/avian/classpath/java/io/RandomAccessFile.java +++ b/sgx-jvm/avian/classpath/java/io/RandomAccessFile.java @@ -12,7 +12,6 @@ package java.io; import java.lang.IllegalArgumentException; import java.nio.ByteBuffer; -import java.nio.channels.FileChannel; public class RandomAccessFile implements DataInput, Closeable { @@ -229,54 +228,4 @@ public class RandomAccessFile implements DataInput, Closeable { } private static native void close(long peer); - - public FileChannel getChannel() { - return new FileChannel() { - public void close() { - if (peer != 0) RandomAccessFile.close(peer); - } - - public boolean isOpen() { - return peer != 0; - } - - public int read(ByteBuffer dst, long position) throws IOException { - if (!dst.hasArray()) throw new IOException("Cannot handle " + dst.getClass()); - // TODO: this needs to be synchronized on the Buffer, no? - byte[] array = dst.array(); - return readBytes(peer, position, array, dst.position(), dst.remaining()); - } - - public int read(ByteBuffer dst) throws IOException { - int count = read(dst, position); - if (count > 0) position += count; - return count; - } - - public int write(ByteBuffer src, long position) throws IOException { - if (!src.hasArray()) throw new IOException("Cannot handle " + src.getClass()); - byte[] array = src.array(); - return writeBytes(peer, position, array, src.position(), src.remaining()); - } - - public int write(ByteBuffer src) throws IOException { - int count = write(src, position); - if (count > 0) position += count; - return count; - } - - public long position() throws IOException { - return getFilePointer(); - } - - public FileChannel position(long position) throws IOException { - seek(position); - return this; - } - - public long size() throws IOException { - return length(); - } - }; - } } diff --git a/sgx-jvm/avian/classpath/java/lang/Math.java b/sgx-jvm/avian/classpath/java/lang/Math.java index c1d1c0bdaf..7c12b47c23 100644 --- a/sgx-jvm/avian/classpath/java/lang/Math.java +++ b/sgx-jvm/avian/classpath/java/lang/Math.java @@ -16,10 +16,6 @@ public final class Math { public static final double E = 2.718281828459045; public static final double PI = 3.141592653589793; - private static class Static { - public static final Random random = new Random(); - } - private Math() { } public static double max(double a, double b) { @@ -86,10 +82,6 @@ public final class Math { return f > 0 ? +1.0f : f < 0 ? -1.0f : 0; } - public static double random() { - return Static.random.nextDouble(); - } - public static native double floor(double v); public static native double ceil(double v); diff --git a/sgx-jvm/avian/classpath/java/lang/System.java b/sgx-jvm/avian/classpath/java/lang/System.java index f6ceabad6b..e7b15b29e1 100644 --- a/sgx-jvm/avian/classpath/java/lang/System.java +++ b/sgx-jvm/avian/classpath/java/lang/System.java @@ -22,10 +22,6 @@ import java.util.Hashtable; import java.util.Properties; public abstract class System { - private static class NanoTime { - public static final long BaseInMillis = currentTimeMillis(); - } - private static class Static { public static Properties properties = makeProperties(); } @@ -91,14 +87,8 @@ public abstract class System { private static native String[] getVMProperties(); - public static native long currentTimeMillis(); - public static native int identityHashCode(Object o); - public static long nanoTime() { - return (currentTimeMillis() - NanoTime.BaseInMillis) * 1000000; - } - public static String mapLibraryName(String name) { if (name != null) { return doMapLibraryName(name); diff --git a/sgx-jvm/avian/classpath/java/lang/Thread.java b/sgx-jvm/avian/classpath/java/lang/Thread.java index 0dea70aae4..f30b3ec0cd 100644 --- a/sgx-jvm/avian/classpath/java/lang/Thread.java +++ b/sgx-jvm/avian/classpath/java/lang/Thread.java @@ -25,7 +25,6 @@ public class Thread implements Runnable { private byte priority; private final Runnable task; private Map locals; - private Object sleepLock; private ClassLoader classLoader; private UncaughtExceptionHandler exceptionHandler; private String name; @@ -158,30 +157,6 @@ public class Thread implements Runnable { return interrupted; } - public static void sleep(long milliseconds) throws InterruptedException { - if (milliseconds <= 0) { - milliseconds = 1; - } - - Thread t = currentThread(); - if (t.sleepLock == null) { - t.sleepLock = new Object(); - } - synchronized (t.sleepLock) { - t.sleepLock.wait(milliseconds); - } - } - - public static void sleep(long milliseconds, int nanoseconds) - throws InterruptedException - { - if (nanoseconds > 0) { - ++ milliseconds; - } - - sleep(milliseconds); - } - public StackTraceElement[] getStackTrace() { long p = peer; if (p == 0) { @@ -269,27 +244,6 @@ public class Thread implements Runnable { } } - public synchronized void join(long milliseconds) throws InterruptedException - { - long then = System.currentTimeMillis(); - long remaining = milliseconds; - while (remaining > 0 && getState() != State.TERMINATED) { - wait(remaining); - - remaining = milliseconds - (System.currentTimeMillis() - then); - } - } - - public void join(long milliseconds, int nanoseconds) - throws InterruptedException - { - if (nanoseconds > 0) { - ++ milliseconds; - } - - join(milliseconds); - } - public ThreadGroup getThreadGroup() { return group; } diff --git a/sgx-jvm/avian/classpath/java/net/BindException.java b/sgx-jvm/avian/classpath/java/net/BindException.java deleted file mode 100644 index 18c6e08473..0000000000 --- a/sgx-jvm/avian/classpath/java/net/BindException.java +++ /dev/null @@ -1,21 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.net; - -public class BindException extends SocketException { - public BindException(String message) { - super(message); - } - - public BindException() { - this(null); - } -} diff --git a/sgx-jvm/avian/classpath/java/net/DatagramSocket.java b/sgx-jvm/avian/classpath/java/net/DatagramSocket.java deleted file mode 100644 index 911550a8aa..0000000000 --- a/sgx-jvm/avian/classpath/java/net/DatagramSocket.java +++ /dev/null @@ -1,19 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.net; - -import java.io.IOException; - -public abstract class DatagramSocket { - public abstract SocketAddress getRemoteSocketAddress(); - - public abstract void bind(SocketAddress address) throws SocketException; -} diff --git a/sgx-jvm/avian/classpath/java/net/InetAddress.java b/sgx-jvm/avian/classpath/java/net/InetAddress.java index 8ddecac67c..9bb8031362 100644 --- a/sgx-jvm/avian/classpath/java/net/InetAddress.java +++ b/sgx-jvm/avian/classpath/java/net/InetAddress.java @@ -13,66 +13,20 @@ package java.net; import java.io.IOException; public class InetAddress { - private final String name; - private final int ip; - - private InetAddress(String name) throws UnknownHostException { - this.name = name; - this.ip = ipv4AddressForName(name); - } public String getHostName() { - return name; + return null; } public String getHostAddress() { - try { - return new InetAddress(name).toString(); - } catch (UnknownHostException e) { - return null; // Strange case - } - } - - public static InetAddress getByName(String name) throws UnknownHostException { - try { - Socket.init(); - return new InetAddress(name); - } catch (IOException e) { - UnknownHostException uhe = new UnknownHostException(name); - uhe.initCause(e); - throw uhe; - } + return null; } public byte[] getAddress() { - byte[] res = new byte[4]; - res[0] = (byte) ( ip >>> 24); - res[1] = (byte) ((ip >>> 16) & 0xFF); - res[2] = (byte) ((ip >>> 8 ) & 0xFF); - res[3] = (byte) ((ip ) & 0xFF); - return res; + return null; } - @Override - public String toString() { - byte[] addr = getAddress(); - return (int)((addr[0] + 256) % 256) + "." + - (int)((addr[1] + 256) % 256) + "." + - (int)((addr[2] + 256) % 256) + "." + - (int)((addr[3] + 256) % 256); - } - public int getRawAddress() { - return ip; - } - - static native int ipv4AddressForName(String name) throws UnknownHostException; - - public boolean equals(Object o) { - return o instanceof InetAddress && ((InetAddress) o).ip == ip; - } - - public int hashCode() { - return ip; + return -1; } } diff --git a/sgx-jvm/avian/classpath/java/net/InetSocketAddress.java b/sgx-jvm/avian/classpath/java/net/InetSocketAddress.java deleted file mode 100644 index 01d34a8734..0000000000 --- a/sgx-jvm/avian/classpath/java/net/InetSocketAddress.java +++ /dev/null @@ -1,65 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.net; - -public class InetSocketAddress extends SocketAddress { - private final String host; - private final InetAddress address; - private final int port; - - public InetSocketAddress(String host, int port) { - InetAddress address; - try { - address = InetAddress.getByName(host); - host = address.getHostName(); - } catch (UnknownHostException e) { - address = null; - } - this.host = host; - this.address = address; - this.port = port; - } - - public InetSocketAddress(InetAddress address, int port) { - this.host = address.getHostName(); - this.address = address; - this.port = port; - } - - public InetAddress getAddress() { - return address; - } - - public String getHostName() { - return host; - } - - public int getPort() { - return port; - } - - public boolean equals(Object o) { - if (o instanceof InetSocketAddress) { - InetSocketAddress a = (InetSocketAddress) o; - return a.address.equals(address) && a.port == port; - } else { - return false; - } - } - - public int hashCode() { - return port ^ address.hashCode(); - } - - public String toString() { - return getHostName() + ":" + port; - } -} diff --git a/sgx-jvm/avian/classpath/java/net/ServerSocket.java b/sgx-jvm/avian/classpath/java/net/ServerSocket.java deleted file mode 100644 index 21836741ae..0000000000 --- a/sgx-jvm/avian/classpath/java/net/ServerSocket.java +++ /dev/null @@ -1,17 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.net; - -import java.io.IOException; - -public abstract class ServerSocket { - public abstract void bind(SocketAddress address) throws IOException; -} diff --git a/sgx-jvm/avian/classpath/java/net/Socket.java b/sgx-jvm/avian/classpath/java/net/Socket.java deleted file mode 100644 index 9a32b88f7c..0000000000 --- a/sgx-jvm/avian/classpath/java/net/Socket.java +++ /dev/null @@ -1,201 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.net; - -import java.io.Closeable; -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; - -public class Socket implements Closeable, AutoCloseable { - - private static final int SD_RECEIVE = 0x00; - private static final int SD_SEND = 0x01; - private static final int SD_BOTH = 0x02; - - private static final int BUFFER_SIZE = 65535; - - /** - * This method is called from all routines that depend on winsock in windows, - * so it has public visibility - * @throws IOException - */ - public static native void init() throws IOException; - - /** - * Creates the native socket object - * @return Handle to the native object - * @throws IOException - */ - private static native /* SOCKET */long create() throws IOException; - - /** - * Connects the native socket object to an address:port - * @param sock Native socket handler - * @param addr Address to connect to - * @param port Port to connect to - * @throws IOException - */ - private static native void connect(/* SOCKET */long sock, long addr, short port) throws IOException; - private static native void bind(/* SOCKET */long sock, long addr, short port) throws IOException; - - private static native void send(/* SOCKET */long sock, byte[] buffer, int start_pos, int count) throws IOException; - private static native int recv(/* SOCKET */long sock, byte[] buffer, int start_pos, int count) throws IOException; - - private static native void abort(/* SOCKET */long sock); - private static native void close(/* SOCKET */long sock); - private static native void closeOutput(/* SOCKET */long sock); - private static native void closeInput(/* SOCKET */long sock); - - private class SocketInputStream extends InputStream { - - private boolean closed = false; - - @Override - public void close() throws IOException { - if (!closed) { - closeInput(sock); - closed = true; - } - super.close(); - } - - @Override - protected void finalize() throws Throwable { - close(); - super.finalize(); - } - - @Override - public int read() throws IOException { - byte[] buffer = new byte[1]; - int size = recv(sock, buffer, 0, 1); - if (size == 0) { - return -1; - } - return buffer[0]; - } - - @Override - public int read(byte[] buffer) throws IOException { - if(buffer.length == 0) return 0; //spec says return 0 if buffer length is zero. - int fullSize = buffer.length; - int size; - size = recv(sock, buffer, 0, Math.min(fullSize, Socket.BUFFER_SIZE)); - fullSize -= size; - //removed loop, because otherwise interactive protocols will not work. - if(size < 0) throw new IOException("Error while reading stream"); //as the manpage of recv says, a value below zero indicates an error. - if(size == 0) return -1; // if the stream is closed (size == 0), then return -1 to indicate end of stream. - return size; - } - } - - private class SocketOutputStream extends OutputStream { - - private boolean closed = false; - - @Override - public void close() throws IOException { - if (!closed) { - closeOutput(sock); - closed = true; - } - super.close(); - } - - @Override - protected void finalize() throws Throwable { - close(); - super.finalize(); - } - - @Override - public void write(int c) throws IOException { - byte[] res = new byte[1]; - res[0] = (byte)c; - send(sock, res, 0, 1); - } - - @Override - public void write(byte[] buffer) throws IOException { - int fullSize = buffer.length; - int index = 0; - int size; - do { - size = Math.min(fullSize, Socket.BUFFER_SIZE); - send(sock, buffer, index, size); - fullSize -= size; - index += size; - } while (fullSize != 0 && size != 0); - } - - } - - private long sock; - private SocketInputStream inputStream; - private SocketOutputStream outputStream; - - public Socket() throws IOException { - Socket.init(); - sock = create(); - inputStream = new SocketInputStream(); - outputStream = new SocketOutputStream(); - } - - public SocketInputStream getInputStream() { - return inputStream; - } - - public SocketOutputStream getOutputStream() { - return outputStream; - } - - public Socket(InetAddress address, int port) throws IOException { - this(); - connect(sock, address.getRawAddress(), (short)port); - } - - public Socket(String host, int port) throws UnknownHostException, IOException { - this(InetAddress.getByName(host), port); - } - - public void bind(SocketAddress bindpoint) throws IOException { - if (bindpoint instanceof InetSocketAddress) { - InetSocketAddress inetBindpoint = (InetSocketAddress)bindpoint; - bind(sock, inetBindpoint.getAddress().getRawAddress(), (short) inetBindpoint.getPort()); - } - } - - public void setTcpNoDelay(boolean on) throws SocketException {} - - @Override - public void close() throws IOException { - close(sock); - } - - public void shutdownInput() throws IOException { - inputStream.close(); - } - - public void shutdownOutput() throws IOException { - outputStream.close(); - } - - public SocketAddress getRemoteSocketAddress() { - throw new UnsupportedOperationException(); - } - - @Override - protected void finalize() throws Throwable { - close(); - super.finalize(); - } -} diff --git a/sgx-jvm/avian/classpath/java/net/SocketAddress.java b/sgx-jvm/avian/classpath/java/net/SocketAddress.java deleted file mode 100644 index c0d6cafe42..0000000000 --- a/sgx-jvm/avian/classpath/java/net/SocketAddress.java +++ /dev/null @@ -1,13 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.net; - -public abstract class SocketAddress { } diff --git a/sgx-jvm/avian/classpath/java/net/URL.java b/sgx-jvm/avian/classpath/java/net/URL.java index 86f244786f..87a4683444 100644 --- a/sgx-jvm/avian/classpath/java/net/URL.java +++ b/sgx-jvm/avian/classpath/java/net/URL.java @@ -81,9 +81,7 @@ public final class URL { private static URLStreamHandler findHandler(String protocol) throws MalformedURLException { - if ("http".equals(protocol) || "https".equals(protocol)) { - return new avian.http.Handler(); - } else if ("avianvmresource".equals(protocol)) { + if ("avianvmresource".equals(protocol)) { return new avian.avianvmresource.Handler(); } else if ("file".equals(protocol)) { return new avian.file.Handler(); diff --git a/sgx-jvm/avian/classpath/java/nio/channels/ClosedSelectorException.java b/sgx-jvm/avian/classpath/java/nio/channels/ClosedSelectorException.java deleted file mode 100644 index df85114f18..0000000000 --- a/sgx-jvm/avian/classpath/java/nio/channels/ClosedSelectorException.java +++ /dev/null @@ -1,13 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.nio.channels; - -public class ClosedSelectorException extends IllegalStateException { } diff --git a/sgx-jvm/avian/classpath/java/nio/channels/DatagramChannel.java b/sgx-jvm/avian/classpath/java/nio/channels/DatagramChannel.java deleted file mode 100644 index f0a2b39a66..0000000000 --- a/sgx-jvm/avian/classpath/java/nio/channels/DatagramChannel.java +++ /dev/null @@ -1,239 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.nio.channels; - -import java.io.IOException; -import java.nio.ByteBuffer; -import java.net.SocketAddress; -import java.net.InetSocketAddress; -import java.net.ProtocolFamily; -import java.net.Socket; -import java.net.SocketException; -import java.net.DatagramSocket; -import java.net.StandardProtocolFamily; - -// TODO: This class is both divergent from the Java standard and incomplete. -public class DatagramChannel extends SelectableChannel - implements ReadableByteChannel, WritableByteChannel -{ - public static final int InvalidSocket = -1; - - private int socket = makeSocket(); - private boolean blocking = true; - private boolean connected = false; - - public SelectableChannel configureBlocking(boolean v) throws IOException { - blocking = v; - configureBlocking(); - return this; - } - - private void configureBlocking() throws IOException { - if (socket != InvalidSocket) { - configureBlocking(socket, blocking); - } - } - - int socketFD() { - return socket; - } - - void handleReadyOps(int ops) { - // ignore - } - - public static DatagramChannel open(ProtocolFamily family) - throws IOException - { - if (family.equals(StandardProtocolFamily.INET)) { - Socket.init(); - - return new DatagramChannel(); - } else { - throw new UnsupportedOperationException(); - } - } - - public static DatagramChannel open() - throws IOException - { - return open(StandardProtocolFamily.INET); - } - - public DatagramSocket socket() { - return new Handle(); - } - - public DatagramChannel bind(SocketAddress address) throws IOException { - InetSocketAddress inetAddress; - try { - inetAddress = (InetSocketAddress) address; - } catch (ClassCastException e) { - throw new UnsupportedAddressTypeException(); - } - - if (inetAddress == null) { - bind(socket, 0, 0); - } else { - bind(socket, inetAddress.getAddress().getRawAddress(), - inetAddress.getPort()); - } - - return this; - } - - public DatagramChannel connect(SocketAddress address) throws IOException { - InetSocketAddress inetAddress; - try { - inetAddress = (InetSocketAddress) address; - } catch (ClassCastException e) { - throw new UnsupportedAddressTypeException(); - } - - connected = connect(socket, inetAddress.getAddress().getRawAddress(), - inetAddress.getPort()); - - return this; - } - - public int write(ByteBuffer b) throws IOException { - if (b.remaining() == 0) return 0; - - byte[] array = b.array(); - if (array == null) throw new NullPointerException(); - - int c = write - (socket, array, b.arrayOffset() + b.position(), b.remaining(), blocking); - - if (c > 0) { - b.position(b.position() + c); - } - - return c; - } - - public int read(ByteBuffer b) throws IOException { - int p = b.position(); - receive(b); - return b.position() - p; - } - - public SocketAddress receive(ByteBuffer b) throws IOException { - if (b.remaining() == 0) return null; - - byte[] array = b.array(); - if (array == null) throw new NullPointerException(); - - int[] address = new int[2]; - - int c = receive - (socket, array, b.arrayOffset() + b.position(), b.remaining(), blocking, - address); - - if (c > 0) { - b.position(b.position() + c); - - return new InetSocketAddress(ipv4ToString(address[0]), address[1]); - } else { - return null; - } - } - - public int send(ByteBuffer b, SocketAddress address) throws IOException { - if (b.remaining() == 0) return 0; - - InetSocketAddress inetAddress; - try { - inetAddress = (InetSocketAddress) address; - } catch (ClassCastException e) { - throw new UnsupportedAddressTypeException(); - } - - byte[] array = b.array(); - if (array == null) throw new NullPointerException(); - - int c = send - (socket, inetAddress.getAddress().getRawAddress(), - inetAddress.getPort(), array, b.arrayOffset() + b.position(), - b.remaining(), blocking); - - if (c > 0) { - b.position(b.position() + c); - } - - return c; - } - - private static String ipv4ToString(int address) { - StringBuilder sb = new StringBuilder(); - - sb.append( address >> 24 ).append('.') - .append((address >> 16) & 0xFF).append('.') - .append((address >> 8) & 0xFF).append('.') - .append( address & 0xFF); - - return sb.toString(); - } - - public class Handle extends DatagramSocket { - public SocketAddress getRemoteSocketAddress() { - throw new UnsupportedOperationException(); - } - - public void bind(SocketAddress address) throws SocketException { - try { - DatagramChannel.this.bind(address); - } catch (SocketException e) { - throw e; - } catch (IOException e) { - SocketException se = new SocketException(); - se.initCause(e); - throw se; - } - } - } - - public boolean isConnected() { return connected; } - - /** TODO: This is probably incomplete. */ - public DatagramChannel disconnect() throws IOException { - connect(socket, 0, 0); - connected = false; - return this; - } - - public void close() throws IOException { - if (isOpen()) { - super.close(); - close(socket); - } - } - - private static native int makeSocket(); - private static native void configureBlocking(int socket, boolean blocking) - throws IOException; - private static native void bind(int socket, int host, int port) - throws IOException; - private static native boolean connect(int socket, int host, int port) - throws IOException; - private static native int write(int socket, byte[] array, int offset, - int length, boolean blocking) - throws IOException; - private static native int send(int socket, int host, int port, - byte[] array, int offset, - int length, boolean blocking) - throws IOException; - private static native int receive(int socket, byte[] array, int offset, - int length, boolean blocking, - int[] address) - throws IOException; - private static native void close(int socket); -} diff --git a/sgx-jvm/avian/classpath/java/nio/channels/FileChannel.java b/sgx-jvm/avian/classpath/java/nio/channels/FileChannel.java deleted file mode 100644 index af8102317b..0000000000 --- a/sgx-jvm/avian/classpath/java/nio/channels/FileChannel.java +++ /dev/null @@ -1,35 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.nio.channels; - -import java.io.IOException; -import java.nio.ByteBuffer; - -public abstract class FileChannel implements Channel { - - public static enum MapMode { - PRIVATE, READ_ONLY, READ_WRITE - }; - - public abstract int read(ByteBuffer dst) throws IOException; - - public abstract int read(ByteBuffer dst, long position) throws IOException; - - public abstract int write(ByteBuffer dst) throws IOException; - - public abstract int write(ByteBuffer dst, long position) throws IOException; - - public abstract long position() throws IOException; - - public abstract FileChannel position(long position) throws IOException; - - public abstract long size() throws IOException; -} diff --git a/sgx-jvm/avian/classpath/java/nio/channels/SelectableChannel.java b/sgx-jvm/avian/classpath/java/nio/channels/SelectableChannel.java deleted file mode 100644 index 3e544f937e..0000000000 --- a/sgx-jvm/avian/classpath/java/nio/channels/SelectableChannel.java +++ /dev/null @@ -1,43 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.nio.channels; - -import java.io.IOException; -import java.nio.ByteBuffer; - -public abstract class SelectableChannel implements Channel { - private SelectionKey key; - private boolean open = true; - - abstract int socketFD(); - - abstract void handleReadyOps(int ops); - - public abstract SelectableChannel configureBlocking(boolean v) - throws IOException; - - public SelectionKey register(Selector selector, int interestOps, - Object attachment) - { - key = new SelectionKey(this, selector, interestOps, attachment); - selector.add(key); - return key; - } - - public boolean isOpen() { - return open; - } - - public void close() throws IOException { - open = false; - key = null; - } -} diff --git a/sgx-jvm/avian/classpath/java/nio/channels/SelectionKey.java b/sgx-jvm/avian/classpath/java/nio/channels/SelectionKey.java deleted file mode 100644 index ca41b74d3a..0000000000 --- a/sgx-jvm/avian/classpath/java/nio/channels/SelectionKey.java +++ /dev/null @@ -1,83 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.nio.channels; - -public class SelectionKey { - public static final int OP_READ = 1 << 0; - public static final int OP_WRITE = 1 << 2; - public static final int OP_CONNECT = 1 << 3; - public static final int OP_ACCEPT = 1 << 4; - - private final SelectableChannel channel; - private final Selector selector; - private int interestOps; - private int readyOps; - private final Object attachment; - - public SelectionKey(SelectableChannel channel, Selector selector, - int interestOps, Object attachment) - { - this.channel = channel; - this.selector = selector; - this.interestOps = interestOps; - this.attachment = attachment; - this.readyOps = 0; - } - - public int interestOps() { - return interestOps; - } - - public SelectionKey interestOps(int v) { - this.interestOps = v; - return this; - } - - public int readyOps() { - return readyOps; - } - - public void readyOps(int v) { - this.readyOps = v; - } - - public boolean isReadable() { - return (readyOps & OP_READ) != 0; - } - - public boolean isWritable() { - return (readyOps & OP_WRITE) != 0; - } - - public boolean isConnectable() { - return (readyOps & OP_CONNECT) != 0; - } - - public boolean isAcceptable() { - return (readyOps & OP_ACCEPT) != 0; - } - - public boolean isValid() { - return channel.isOpen() && selector.isOpen(); - } - - public SelectableChannel channel() { - return channel; - } - - public Selector selector() { - return selector; - } - - public Object attachment() { - return attachment; - } -} diff --git a/sgx-jvm/avian/classpath/java/nio/channels/Selector.java b/sgx-jvm/avian/classpath/java/nio/channels/Selector.java deleted file mode 100644 index ceb45031eb..0000000000 --- a/sgx-jvm/avian/classpath/java/nio/channels/Selector.java +++ /dev/null @@ -1,52 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.nio.channels; - -import java.io.IOException; -import java.util.Set; -import java.util.HashSet; - -public abstract class Selector { - protected final Set keys = new HashSet(); - protected final Set selectedKeys = new HashSet(); - - public static Selector open() throws IOException { - return new SocketSelector(); - } - - public void add(SelectionKey key) { - keys.add(key); - } - - public void remove(SelectionKey key) { - keys.remove(key); - } - - public Set keys() { - return keys; - } - - public Set selectedKeys() { - return selectedKeys; - } - - public abstract boolean isOpen(); - - public abstract Selector wakeup(); - - public abstract int selectNow() throws IOException; - - public abstract int select(long interval) throws IOException; - - public abstract int select() throws IOException; - - public abstract void close(); -} diff --git a/sgx-jvm/avian/classpath/java/nio/channels/ServerSocketChannel.java b/sgx-jvm/avian/classpath/java/nio/channels/ServerSocketChannel.java deleted file mode 100644 index 6f0d601a8b..0000000000 --- a/sgx-jvm/avian/classpath/java/nio/channels/ServerSocketChannel.java +++ /dev/null @@ -1,93 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.nio.channels; - -import java.io.IOException; - -import java.net.InetSocketAddress; -import java.net.SocketAddress; -import java.net.ServerSocket; -import java.net.Socket; - -public class ServerSocketChannel extends SelectableChannel { - private final SocketChannel channel; - - private ServerSocketChannel() throws IOException { - channel = new SocketChannel(); - } - - public static ServerSocketChannel open() throws IOException { - Socket.init(); - - return new ServerSocketChannel(); - } - - public int socketFD() { - return channel.socketFD(); - } - - public void handleReadyOps(int ops) { - channel.handleReadyOps(ops); - } - - public SelectableChannel configureBlocking(boolean v) throws IOException { - return channel.configureBlocking(v); - } - - public void close() throws IOException { - channel.close(); - } - - public SocketChannel accept() throws IOException { - SocketChannel c = new SocketChannel(); - c.socket = doAccept(); - c.connected = true; - return c; - } - - public ServerSocket socket() { - return new Handle(); - } - - private int doAccept() throws IOException { - while (true) { - int s = natDoAccept(channel.socket); - if (s != -1) { - return s; - } - // todo: throw ClosedByInterruptException if this thread was - // interrupted during the accept call - } - } - - private void doListen(int socket, int host, int port) throws IOException { - Socket.init(); - - natDoListen(socket, host, port); - } - - public class Handle extends ServerSocket { - public void bind(SocketAddress address) - throws IOException - { - InetSocketAddress a; - try { - a = (InetSocketAddress) address; - } catch (ClassCastException e) { - throw new IllegalArgumentException(); - } - doListen(channel.socket, a.getAddress().getRawAddress(), a.getPort()); - } - } - - private static native int natDoAccept(int socket) throws IOException; - private static native void natDoListen(int socket, int host, int port) throws IOException; -} diff --git a/sgx-jvm/avian/classpath/java/nio/channels/SocketChannel.java b/sgx-jvm/avian/classpath/java/nio/channels/SocketChannel.java deleted file mode 100644 index f551eb1dc3..0000000000 --- a/sgx-jvm/avian/classpath/java/nio/channels/SocketChannel.java +++ /dev/null @@ -1,214 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.nio.channels; - -import java.io.IOException; -import java.net.SocketException; -import java.net.SocketAddress; -import java.net.InetSocketAddress; -import java.net.Socket; -import java.nio.ByteBuffer; - -public class SocketChannel extends SelectableChannel - implements ReadableByteChannel, GatheringByteChannel -{ - public static final int InvalidSocket = -1; - - int socket = makeSocket(); - boolean connected = false; - boolean readyToConnect = false; - boolean blocking = true; - - public static SocketChannel open() throws IOException { - Socket.init(); - - return new SocketChannel(); - } - - public SelectableChannel configureBlocking(boolean v) throws IOException { - blocking = v; - if (socket != InvalidSocket) { - configureBlocking(socket, v); - } - return this; - } - - public boolean isBlocking() { - return blocking; - } - - public boolean isConnected() { - return connected; - } - - public Socket socket() { - try { - return new Handle(); - } catch (IOException e) { - return null; - } - } - - public boolean connect(SocketAddress address) throws IOException { - InetSocketAddress a; - try { - a = (InetSocketAddress) address; - } catch (ClassCastException e) { - throw new UnsupportedAddressTypeException(); - } - doConnect(socket, a.getAddress().getRawAddress(), a.getPort()); - configureBlocking(blocking); - return connected; - } - - public boolean finishConnect() throws IOException { - if (! connected) { - while (! readyToConnect) { - Selector selector = Selector.open(); - SelectionKey key = register(selector, SelectionKey.OP_CONNECT, null); - - if (blocking) { - selector.select(); - } else { - selector.selectNow(); - break; - } - } - - natFinishConnect(socket); - - connected = readyToConnect; - } - - return connected; - } - - public void close() throws IOException { - if (isOpen()) { - super.close(); - closeSocket(); - } - } - - private void doConnect(int socket, int host, int port) - throws IOException - { - connected = natDoConnect(socket, host, port); - } - - public int read(ByteBuffer b) throws IOException { - if (! isOpen()) return -1; - if (b.remaining() == 0) return 0; - - byte[] array = b.array(); - if (array == null) throw new NullPointerException(); - - int r = natRead(socket, array, b.arrayOffset() + b.position(), b.remaining(), blocking); - if (r > 0) { - b.position(b.position() + r); - } - return r; - } - - public int write(ByteBuffer b) throws IOException { - if (! connected) { - natThrowWriteError(socket); - } - if (b.remaining() == 0) return 0; - - byte[] array = b.array(); - if (array == null) throw new NullPointerException(); - - int w = natWrite(socket, array, b.arrayOffset() + b.position(), b.remaining(), blocking); - if (w > 0) { - b.position(b.position() + w); - } - return w; - } - - public long write(ByteBuffer[] srcs) throws IOException { - return write(srcs, 0, srcs.length); - } - - public long write(ByteBuffer[] srcs, int offset, int length) - throws IOException - { - long total = 0; - for (int i = offset; i < offset + length; ++i) { - total += write(srcs[i]); - if (srcs[i].hasRemaining()) { - return total; - } - } - return total; - } - - private void closeSocket() { - natCloseSocket(socket); - } - - int socketFD() { - return socket; - } - - void handleReadyOps(int ops) { - if ((ops & SelectionKey.OP_CONNECT) != 0) { - readyToConnect = true; - } - } - - public class Handle extends Socket { - public Handle() throws IOException { - super(); - } - - public void setTcpNoDelay(boolean on) throws SocketException { - natSetTcpNoDelay(socket, on); - } - - public void bind(SocketAddress address) - throws IOException - { - InetSocketAddress a; - try { - a = (InetSocketAddress) address; - } catch (ClassCastException e) { - throw new IllegalArgumentException(); - } - - if (a == null) { - SocketChannel.bind(socket, 0, 0); - } else { - SocketChannel.bind - (socket, a.getAddress().getRawAddress(), a.getPort()); - } - } - } - - private static native int makeSocket(); - private static native void configureBlocking(int socket, boolean blocking) - throws IOException; - - private static native void natSetTcpNoDelay(int socket, boolean on) - throws SocketException; - private static native void bind(int socket, int host, int port) - throws IOException; - private static native boolean natDoConnect(int socket, int host, int port) - throws IOException; - private static native void natFinishConnect(int socket) - throws IOException; - private static native int natRead(int socket, byte[] buffer, int offset, int length, boolean blocking) - throws IOException; - private static native int natWrite(int socket, byte[] buffer, int offset, int length, boolean blocking) - throws IOException; - private static native void natThrowWriteError(int socket) throws IOException; - private static native void natCloseSocket(int socket); -} diff --git a/sgx-jvm/avian/classpath/java/nio/channels/SocketSelector.java b/sgx-jvm/avian/classpath/java/nio/channels/SocketSelector.java deleted file mode 100644 index c17d2afbf2..0000000000 --- a/sgx-jvm/avian/classpath/java/nio/channels/SocketSelector.java +++ /dev/null @@ -1,133 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.nio.channels; - -import java.io.IOException; -import java.util.Iterator; -import java.net.Socket; - -class SocketSelector extends Selector { - protected volatile long state; - protected final Object lock = new Object(); - protected boolean woken = false; - - public SocketSelector() throws IOException { - Socket.init(); - - state = natInit(); - } - - public boolean isOpen() { - return state != 0; - } - - public Selector wakeup() { - synchronized (lock) { - if (isOpen() && (! woken)) { - woken = true; - - natWakeup(state); - } - } - return this; - } - - private boolean clearWoken() { - synchronized (lock) { - if (woken) { - woken = false; - return true; - } else { - return false; - } - } - } - - public synchronized int selectNow() throws IOException { - return doSelect(-1); - } - - public synchronized int select() throws IOException { - return doSelect(0); - } - - public synchronized int select(long interval) throws IOException { - if (interval < 0) throw new IllegalArgumentException(); - - return doSelect(interval); - } - - public int doSelect(long interval) throws IOException { - if (! isOpen()) { - throw new ClosedSelectorException(); - } - - selectedKeys.clear(); - - if (clearWoken()) interval = -1; - - int max=0; - for (Iterator it = keys.iterator(); - it.hasNext();) - { - SelectionKey key = it.next(); - SelectableChannel c = key.channel(); - int socket = c.socketFD(); - if (c.isOpen()) { - key.readyOps(0); - max = natSelectUpdateInterestSet - (socket, key.interestOps(), state, max); - } else { - natSelectClearAll(socket, state); - it.remove(); - } - } - - int r = natDoSocketSelect(state, max, interval); - - if (r > 0) { - for (SelectionKey key : keys) { - SelectableChannel c = key.channel(); - int socket = c.socketFD(); - int ready = natUpdateReadySet(socket, key.interestOps(), state); - key.readyOps(ready); - if (ready != 0) { - c.handleReadyOps(ready); - selectedKeys.add(key); - } - } - } - clearWoken(); - - return selectedKeys.size(); - } - - public synchronized void close() { - synchronized (lock) { - if (isOpen()) { - natClose(state); - state = 0; - } - } - } - - private static native long natInit(); - private static native void natWakeup(long state); - private static native void natClose(long state); - private static native void natSelectClearAll(int socket, long state); - private static native int natSelectUpdateInterestSet(int socket, - int interest, - long state, - int max); - private static native int natDoSocketSelect(long state, int max, long interval) - throws IOException; - private static native int natUpdateReadySet(int socket, int interest, long state); -} diff --git a/sgx-jvm/avian/classpath/java/util/ArrayList.java b/sgx-jvm/avian/classpath/java/util/ArrayList.java index 325fa1591f..205392a8e0 100644 --- a/sgx-jvm/avian/classpath/java/util/ArrayList.java +++ b/sgx-jvm/avian/classpath/java/util/ArrayList.java @@ -11,8 +11,6 @@ package java.util; import java.io.IOException; -import java.io.ObjectInputStream; -import java.io.ObjectOutputStream; public class ArrayList extends AbstractList implements java.io.Serializable, RandomAccess { private static final int MinimumCapacity = 16; @@ -187,23 +185,4 @@ public class ArrayList extends AbstractList implements java.io.Serializabl public String toString() { return avian.Data.toString(this); } - - private void writeObject(ObjectOutputStream out) throws IOException { - out.defaultWriteObject(); - out.writeInt(array.length); - for (T o : this) { - out.writeObject(o); - } - } - - private void readObject(ObjectInputStream in) - throws ClassNotFoundException, IOException - { - in.defaultReadObject(); - int capacity = in.readInt(); - grow(capacity); - for (int i = 0; i < size; i++) { - array[i] = in.readObject(); - } - } } diff --git a/sgx-jvm/avian/classpath/java/util/Calendar.java b/sgx-jvm/avian/classpath/java/util/Calendar.java index 448f0f1bef..964241c5f7 100644 --- a/sgx-jvm/avian/classpath/java/util/Calendar.java +++ b/sgx-jvm/avian/classpath/java/util/Calendar.java @@ -34,7 +34,7 @@ public abstract class Calendar { protected Calendar() { } public static Calendar getInstance() { - return new MyCalendar(System.currentTimeMillis()); + return new MyCalendar(0); } public int get(int field) { diff --git a/sgx-jvm/avian/classpath/java/util/Collections.java b/sgx-jvm/avian/classpath/java/util/Collections.java index 9a6f998503..5fdb68c038 100644 --- a/sgx-jvm/avian/classpath/java/util/Collections.java +++ b/sgx-jvm/avian/classpath/java/util/Collections.java @@ -31,10 +31,6 @@ public class Collections { } } - public static void shuffle(List list) { - shuffle(list, new Random()); - } - public static void sort(List list) { sort(list, new Comparator() { public int compare(Object a, Object b) { @@ -200,6 +196,14 @@ public class Collections { return new ReverseComparator(cmp); } + public static boolean addAll(Collection collection, T... items) { + boolean modified = false; + for (T item : items) { + modified |= collection.add(item); + } + return modified; + } + static class IteratorEnumeration implements Enumeration { private final Iterator it; diff --git a/sgx-jvm/avian/classpath/java/util/Date.java b/sgx-jvm/avian/classpath/java/util/Date.java index 2681c84bf5..7154cf26a5 100644 --- a/sgx-jvm/avian/classpath/java/util/Date.java +++ b/sgx-jvm/avian/classpath/java/util/Date.java @@ -13,10 +13,6 @@ package java.util; public class Date { public final long when; - public Date() { - when = System.currentTimeMillis(); - } - public Date(long when) { this.when = when; } diff --git a/sgx-jvm/avian/classpath/java/util/Random.java b/sgx-jvm/avian/classpath/java/util/Random.java index 9d244c5e0c..802dc87f7a 100644 --- a/sgx-jvm/avian/classpath/java/util/Random.java +++ b/sgx-jvm/avian/classpath/java/util/Random.java @@ -23,16 +23,6 @@ public class Random { setSeed(seed); } - public Random() { - synchronized (Random.class) { - setSeed(nextSeed ^ System.currentTimeMillis()); - nextSeed *= 123456789987654321L; - if (nextSeed == 0) { - nextSeed = InitialSeed; - } - } - } - public void setSeed(long seed) { this.seed = (seed ^ Mask) & ((1L << 48) - 1); } diff --git a/sgx-jvm/avian/classpath/java/util/TreeMap.java b/sgx-jvm/avian/classpath/java/util/TreeMap.java index 9b8792d9d6..53a717e813 100644 --- a/sgx-jvm/avian/classpath/java/util/TreeMap.java +++ b/sgx-jvm/avian/classpath/java/util/TreeMap.java @@ -11,8 +11,6 @@ package java.util; import java.io.IOException; -import java.io.ObjectInputStream; -import java.io.ObjectOutputStream; public class TreeMap implements NavigableMap { private final Comparator comparator; @@ -279,26 +277,4 @@ public class TreeMap implements NavigableMap { return new avian.Data.ValueIterator(set.iterator()); } } - - public final static long serialVersionUID = 0x0cc1f63e2d256ae6l; - - private void writeObject(ObjectOutputStream out) throws IOException { - out.defaultWriteObject(); - out.writeInt(size()); - for (Entry entry : entrySet()) { - out.writeObject(entry.getKey()); - out.writeObject(entry.getValue()); - } - } - - private void readObject(ObjectInputStream in) throws IOException { - in.defaultReadObject(); - initializeSet(); - int size = in.readInt(); - for (int i = 0; i < size; i++) try { - put((K) in.readObject(), (V) in.readObject()); - } catch (ClassNotFoundException e) { - throw new IOException(e); - } - } } diff --git a/sgx-jvm/avian/classpath/java/util/UUID.java b/sgx-jvm/avian/classpath/java/util/UUID.java index 4c5be5ccac..883b9708ff 100644 --- a/sgx-jvm/avian/classpath/java/util/UUID.java +++ b/sgx-jvm/avian/classpath/java/util/UUID.java @@ -17,19 +17,6 @@ public class UUID { this.data = data; } - public static UUID randomUUID() { - byte[] array = new byte[16]; - - new Random().nextBytes(array); - - array[6] &= 0x0f; - array[6] |= 0x40; - array[8] &= 0x3f; - array[8] |= 0x80; - - return new UUID(array); - } - public String toString() { StringBuilder sb = new StringBuilder(); toHex(sb, data, 0, 4); sb.append('-'); diff --git a/sgx-jvm/avian/classpath/java/util/concurrent/ExecutorCompletionService.java b/sgx-jvm/avian/classpath/java/util/concurrent/ExecutorCompletionService.java deleted file mode 100644 index f08ef9960d..0000000000 --- a/sgx-jvm/avian/classpath/java/util/concurrent/ExecutorCompletionService.java +++ /dev/null @@ -1,73 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.util.concurrent; - -public class ExecutorCompletionService implements CompletionService { - private final Executor executor; - private final BlockingQueue> completionQueue; - - public ExecutorCompletionService(Executor executor) { - this(executor, new LinkedBlockingQueue>()); - } - - public ExecutorCompletionService(Executor executor, BlockingQueue> completionQueue) { - this.executor = executor; - this.completionQueue = completionQueue; - } - - @Override - public Future submit(Callable task) { - ECSFuture f = new ECSFuture(task); - - executor.execute(f); - - return f; - } - - @Override - public Future submit(Runnable task, T result) { - ECSFuture f = new ECSFuture(task, result); - - executor.execute(f); - - return f; - } - - @Override - public Future take() throws InterruptedException { - return completionQueue.take(); - } - - @Override - public Future poll() { - return completionQueue.poll(); - } - - @Override - public Future poll(long timeout, TimeUnit unit) throws InterruptedException { - return completionQueue.poll(timeout, unit); - } - - private class ECSFuture extends FutureTask implements Future { - private ECSFuture(Runnable r, T result) { - super(r, result); - } - - private ECSFuture(Callable callable) { - super(callable); - } - - @Override - protected void done() { - completionQueue.add(this); - } - } -} diff --git a/sgx-jvm/avian/classpath/java/util/concurrent/FutureTask.java b/sgx-jvm/avian/classpath/java/util/concurrent/FutureTask.java index 967d2c8a1d..2677ee27ff 100644 --- a/sgx-jvm/avian/classpath/java/util/concurrent/FutureTask.java +++ b/sgx-jvm/avian/classpath/java/util/concurrent/FutureTask.java @@ -64,11 +64,7 @@ public class FutureTask implements RunnableFuture { * and thus thread is in interrupted status, the exception should * throw immediately on the sleep call. */ - try { - Thread.sleep(Long.MAX_VALUE); - } catch (InterruptedException e) { - // expected - } + throw new UnsupportedOperationException("Blocking not supported."); } Thread.interrupted(); // reset interrupted status if set @@ -127,43 +123,13 @@ public class FutureTask implements RunnableFuture { @Override public T get() throws InterruptedException, ExecutionException { - try { - return get(Long.MAX_VALUE, TimeUnit.MILLISECONDS); - } catch (TimeoutException e) { - // not possible - throw new RuntimeException(e); - } + throw new UnsupportedOperationException("System clock unavailable"); } @Override public T get(long timeout, TimeUnit unit) throws InterruptedException, ExecutionException, TimeoutException { - long timeoutInMillis = unit.toMillis(timeout); - long startTime = 0; - if (timeoutInMillis < Long.MAX_VALUE) { - startTime = System.currentTimeMillis(); - } - long remainingTime; - synchronized (notifyLock) { - remainingTime = timeoutInMillis; - while (! isDone() && remainingTime > 0) { - notifyLock.wait(remainingTime); - - if (timeoutInMillis < Long.MAX_VALUE) { - remainingTime = timeoutInMillis - (System.currentTimeMillis() - startTime); - } - } - } - - if (remainingTime <= 0) { - throw new TimeoutException(); - } else if (currentState.get() == State.Canceled) { - throw new CancellationException(); - } else if (failure != null) { - throw new ExecutionException(failure); - } else { - return result; - } + throw new UnsupportedOperationException("System clock unavailable"); } } diff --git a/sgx-jvm/avian/classpath/java/util/concurrent/LinkedBlockingQueue.java b/sgx-jvm/avian/classpath/java/util/concurrent/LinkedBlockingQueue.java deleted file mode 100644 index 49be16ccb6..0000000000 --- a/sgx-jvm/avian/classpath/java/util/concurrent/LinkedBlockingQueue.java +++ /dev/null @@ -1,302 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -package java.util.concurrent; - -import java.util.AbstractQueue; -import java.util.Collection; -import java.util.Iterator; -import java.util.LinkedList; - -public class LinkedBlockingQueue extends AbstractQueue - implements BlockingQueue { - private final Object collectionLock; - private final LinkedList storage; - private final int capacity; - - public LinkedBlockingQueue() { - this(Integer.MAX_VALUE); - } - - public LinkedBlockingQueue(int capacity) { - collectionLock = new Object(); - this.capacity = capacity; - storage = new LinkedList(); - } - - // should be synchronized on collectionLock before calling - private void handleRemove() { - collectionLock.notifyAll(); - } - - // should be synchronized on collectionLock before calling - private void handleAdd() { - collectionLock.notifyAll(); - } - - // should be synchronized on collectionLock before calling - private void blockTillNotFull() throws InterruptedException { - blockTillNotFull(Long.MAX_VALUE); - } - - // should be synchronized on collectionLock before calling - private void blockTillNotFull(long maxWaitInMillis) throws InterruptedException { - if (capacity > storage.size()) { - return; - } - - long startTime = 0; - if (maxWaitInMillis != Long.MAX_VALUE) { - startTime = System.currentTimeMillis(); - } - long remainingWait = maxWaitInMillis; - while (remainingWait > 0) { - collectionLock.wait(remainingWait); - - if (capacity > storage.size()) { - return; - } else if (maxWaitInMillis != Long.MAX_VALUE) { - remainingWait = maxWaitInMillis - (System.currentTimeMillis() - startTime); - } - } - } - - // should be synchronized on collectionLock before calling - private void blockTillNotEmpty() throws InterruptedException { - blockTillNotEmpty(Long.MAX_VALUE); - } - - // should be synchronized on collectionLock before calling - private void blockTillNotEmpty(long maxWaitInMillis) throws InterruptedException { - if (! storage.isEmpty()) { - return; - } - - long startTime = 0; - if (maxWaitInMillis != Long.MAX_VALUE) { - startTime = System.currentTimeMillis(); - } - long remainingWait = maxWaitInMillis; - while (remainingWait > 0) { - collectionLock.wait(remainingWait); - - if (! storage.isEmpty()) { - return; - } else if (maxWaitInMillis != Long.MAX_VALUE) { - remainingWait = maxWaitInMillis - (System.currentTimeMillis() - startTime); - } - } - } - - @Override - public boolean offer(T element) { - synchronized (collectionLock) { - if (capacity > storage.size()) { - storage.addLast(element); - - handleAdd(); - - return true; - } else { - return false; - } - } - } - - @Override - public boolean offer(T e, long timeout, TimeUnit unit) throws InterruptedException { - long timeoutInMillis = unit.toMillis(timeout); - synchronized (collectionLock) { - // block till we can add or have reached timeout - blockTillNotFull(timeoutInMillis); - - return offer(e); - } - } - - @Override - public void put(T e) throws InterruptedException { - synchronized (collectionLock) { - // block till we have space - blockTillNotFull(); - - storage.add(e); - handleAdd(); - } - } - - @Override - public boolean addAll(Collection c) { - synchronized (collectionLock) { - if (storage.size() + c.size() > capacity) { - throw new IllegalStateException("Not enough space"); - } - - if (c.isEmpty()) { - return false; - } else { - storage.addAll(c); - - return true; - } - } - } - - @Override - public T peek() { - synchronized (collectionLock) { - if (storage.isEmpty()) { - return null; - } else { - return storage.getFirst(); - } - } - } - - // should be synchronized on collectionLock before calling - private T removeFirst() { - T result = storage.removeFirst(); - handleRemove(); - - return result; - } - - @Override - public T poll() { - synchronized (collectionLock) { - if (storage.isEmpty()) { - return null; - } else { - return removeFirst(); - } - } - } - - @Override - public T poll(long timeout, TimeUnit unit) throws InterruptedException { - long timeoutInMillis = unit.toMillis(timeout); - synchronized (collectionLock) { - // block till we available or timeout - blockTillNotEmpty(timeoutInMillis); - - return poll(); - } - } - - @Override - public T take() throws InterruptedException { - synchronized (collectionLock) { - // block till we available - blockTillNotEmpty(); - - return removeFirst(); - } - } - - @Override - public int drainTo(Collection c) { - return drainTo(c, Integer.MAX_VALUE); - } - - @Override - public int drainTo(Collection c, int maxElements) { - int remainingElements = maxElements; - synchronized (collectionLock) { - while (remainingElements > 0 && ! storage.isEmpty()) { - c.add(storage.removeFirst()); - remainingElements--; - } - - if (remainingElements != maxElements) { - handleRemove(); - } - - return maxElements - remainingElements; - } - } - - @Override - public int remainingCapacity() { - synchronized (collectionLock) { - return capacity - storage.size(); - } - } - - @Override - public int size() { - synchronized (collectionLock) { - return storage.size(); - } - } - - @Override - public boolean contains(Object element) { - synchronized (collectionLock) { - return storage.contains(element); - } - } - - @Override - public boolean containsAll(Collection c) { - synchronized (collectionLock) { - return storage.containsAll(c); - } - } - - @Override - public boolean remove(Object element) { - synchronized (collectionLock) { - if (storage.remove(element)) { - handleRemove(); - return true; - } else { - return false; - } - } - } - - @Override - public boolean removeAll(Collection c) { - synchronized (collectionLock) { - if (storage.removeAll(c)) { - handleRemove(); - return true; - } else { - return false; - } - } - } - - @Override - public void clear() { - synchronized (collectionLock) { - storage.clear(); - } - } - - @Override - public Object[] toArray() { - synchronized (collectionLock) { - return storage.toArray(); - } - } - - @Override - public S[] toArray(S[] array) { - synchronized (collectionLock) { - return storage.toArray(array); - } - } - - @Override - public Iterator iterator() { - throw new UnsupportedOperationException("Not implemented yet"); - } -} diff --git a/sgx-jvm/avian/classpath/java/util/concurrent/TimeUnit.java b/sgx-jvm/avian/classpath/java/util/concurrent/TimeUnit.java index 3503d672b9..94b91826e0 100644 --- a/sgx-jvm/avian/classpath/java/util/concurrent/TimeUnit.java +++ b/sgx-jvm/avian/classpath/java/util/concurrent/TimeUnit.java @@ -397,20 +397,4 @@ public enum TimeUnit { obj.wait(ms, ns); } } - - public void timedJoin(Thread thread, long timeout) throws InterruptedException { - if (timeout > 0) { - long ms = toMillis(timeout); - int ns = excessNanos(timeout, ms); - thread.join(ms, ns); - } - } - - public void sleep(long timeout) throws InterruptedException { - if (timeout > 0) { - long ms = toMillis(timeout); - int ns = excessNanos(timeout, ms); - Thread.sleep(ms, ns); - } - } } diff --git a/sgx-jvm/avian/classpath/java/util/zip/ZipEntry.java b/sgx-jvm/avian/classpath/java/util/zip/ZipEntry.java index 482f9d0347..f2a3ba09f6 100644 --- a/sgx-jvm/avian/classpath/java/util/zip/ZipEntry.java +++ b/sgx-jvm/avian/classpath/java/util/zip/ZipEntry.java @@ -48,7 +48,6 @@ public class ZipEntry { public ZipEntry(String name) { this.name = name; - setTime(System.currentTimeMillis()); } //Method to return name of the file diff --git a/sgx-jvm/avian/classpath/sockets.cpp b/sgx-jvm/avian/classpath/sockets.cpp deleted file mode 100644 index ddffc18576..0000000000 --- a/sgx-jvm/avian/classpath/sockets.cpp +++ /dev/null @@ -1,205 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -/* - * This file implements a simple cross-platform JNI sockets API - * It is used from different classes of the default Avian classpath - */ - -#ifndef SGX - -#include "sockets.h" - -namespace avian { -namespace classpath { -namespace sockets { - -int last_socket_error() -{ -#ifdef PLATFORM_WINDOWS - int error = WSAGetLastError(); -#else - int error = errno; -#endif - return error; -} - -void init(JNIEnv* ONLY_ON_WINDOWS(e)) -{ -#ifdef PLATFORM_WINDOWS - static bool wsaInitialized = false; - if (not wsaInitialized) { - WSADATA data; - int r = WSAStartup(MAKEWORD(2, 2), &data); - if (r or LOBYTE(data.wVersion) != 2 or HIBYTE(data.wVersion) != 2) { - throwNew(e, "java/io/IOException", "WSAStartup failed"); - } else { - wsaInitialized = true; - } - } -#endif -} - -SOCKET create(JNIEnv* e) -{ - SOCKET sock; - if (INVALID_SOCKET == (sock = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP))) { - char buf[255]; - sprintf( - buf, "Can't create a socket. System error: %d", last_socket_error()); - throwNew(e, "java/io/IOException", buf); - return 0; // This doesn't matter cause we have risen an exception - } - return sock; -} - -void connect(JNIEnv* e, SOCKET sock, long addr, short port) -{ - sockaddr_in adr; - adr.sin_family = AF_INET; -#ifdef PLATFORM_WINDOWS - adr.sin_addr.S_un.S_addr = htonl(addr); -#else - adr.sin_addr.s_addr = htonl(addr); -#endif - adr.sin_port = htons(port); - - if (SOCKET_ERROR == ::connect(sock, (sockaddr*)&adr, sizeof(adr))) { - char buf[255]; - sprintf( - buf, "Can't connect a socket. System error: %d", last_socket_error()); - throwNew(e, "java/io/IOException", buf); - return; - } -} - -void bind(JNIEnv* e, SOCKET sock, long addr, short port) -{ - sockaddr_in adr; - adr.sin_family = AF_INET; -#ifdef PLATFORM_WINDOWS - adr.sin_addr.S_un.S_addr = htonl(addr); -#else - adr.sin_addr.s_addr = htonl(addr); -#endif - adr.sin_port = htons(port); - - if (SOCKET_ERROR == ::bind(sock, (sockaddr*)&adr, sizeof(adr))) { - char buf[255]; - sprintf(buf, "Can't bind a socket. System error: %d", last_socket_error()); - throwNew(e, "java/io/IOException", buf); - return; - } -} - -SOCKET accept(JNIEnv* e, SOCKET sock, long* client_addr, short* client_port) -{ - sockaddr_in adr; - SOCKET client_socket = ::accept(sock, (sockaddr*)&adr, NULL); - if (INVALID_SOCKET == client_socket) { - char buf[255]; - sprintf(buf, - "Can't accept the incoming connection. System error: %d", - last_socket_error()); - throwNew(e, "java/io/IOException", buf); - return INVALID_SOCKET; - } - - if (client_addr != NULL) { -#ifdef PLATFORM_WINDOWS - *client_addr = ntohl(adr.sin_addr.S_un.S_addr); -#else - *client_addr = ntohl(adr.sin_addr.s_addr); -#endif - } - - if (client_port != NULL) { - *client_port = ntohs(adr.sin_port); - } - - return client_socket; -} - -void send(JNIEnv* e, SOCKET sock, const char* buff_ptr, int buff_size) -{ - if (SOCKET_ERROR == ::send(sock, buff_ptr, buff_size, 0)) { - char buf[255]; - sprintf(buf, - "Can't send data through the socket. System error: %d", - last_socket_error()); - throwNew(e, "java/io/IOException", buf); - return; - } -} - -int recv(JNIEnv* e, SOCKET sock, char* buff_ptr, int buff_size) -{ - int length = ::recv(sock, buff_ptr, buff_size, 0); - if (SOCKET_ERROR == length) { - char buf[255]; - sprintf(buf, - "Can't receive data through the socket. System error: %d", - last_socket_error()); - throwNew(e, "java/io/IOException", buf); - return 0; // This doesn't matter cause we have risen an exception - } - return length; -} - -void abort(JNIEnv* e, SOCKET sock) -{ - if (SOCKET_ERROR == ::closesocket(sock)) { - char buf[255]; - sprintf( - buf, "Can't close the socket. System error: %d", last_socket_error()); - throwNew(e, "java/io/IOException", buf); - } -} - -void close(JNIEnv* e, SOCKET sock) -{ - if (SOCKET_ERROR == ::shutdown(sock, SD_BOTH)) { - int errcode = last_socket_error(); - if (errcode != ENOTCONN) { - char buf[255]; - sprintf(buf, "Can't shutdown the socket. System error: %d", errcode); - throwNew(e, "java/io/IOException", buf); - } - } -} - -void close_input(JNIEnv* e, SOCKET sock) -{ - if (SOCKET_ERROR == ::shutdown(sock, SD_RECEIVE)) { - int errcode = last_socket_error(); - if (errcode != ENOTCONN) { - char buf[255]; - sprintf(buf, "Can't shutdown the socket. System error: %d", errcode); - throwNew(e, "java/io/IOException", buf); - } - } -} - -void close_output(JNIEnv* e, SOCKET sock) -{ - if (SOCKET_ERROR == ::shutdown(sock, SD_SEND)) { - int errcode = last_socket_error(); - if (errcode != ENOTCONN) { - char buf[255]; - sprintf(buf, "Can't shutdown the socket. System error: %d", errcode); - throwNew(e, "java/io/IOException", buf); - } - } -} -} -} -} - -#endif \ No newline at end of file diff --git a/sgx-jvm/avian/classpath/sockets.h b/sgx-jvm/avian/classpath/sockets.h deleted file mode 100644 index 31a45f2ce5..0000000000 --- a/sgx-jvm/avian/classpath/sockets.h +++ /dev/null @@ -1,74 +0,0 @@ -/* Copyright (c) 2008-2015, Avian Contributors - - Permission to use, copy, modify, and/or distribute this software - for any purpose with or without fee is hereby granted, provided - that the above copyright notice and this permission notice appear - in all copies. - - There is NO WARRANTY for this software. See license.txt for - details. */ - -/* - * This file represents a simple cross-platform JNI sockets API - * It is used from different classes of the default Avian classpath - */ - -#ifndef SOCKETS_H_ -#define SOCKETS_H_ - -#include "jni.h" -#include "jni-util.h" -#include "avian/common.h" - -#ifdef PLATFORM_WINDOWS -#include - -#define ONLY_ON_WINDOWS(x) x - -#ifndef ENOTCONN -#define ENOTCONN WSAENOTCONN -#endif -#else -#include -#include -#include -#include - -#define ONLY_ON_WINDOWS(x) -#define SOCKET int -#define INVALID_SOCKET -1 -#define SOCKET_ERROR -1 -#define closesocket(x) close(x) - -#define SD_RECEIVE SHUT_RD -#define SD_SEND SHUT_WR -#define SD_BOTH SHUT_RDWR - -#endif - -namespace avian { -namespace classpath { -namespace sockets { - -// Library initialization -void init(JNIEnv* ONLY_ON_WINDOWS(e)); - -// Socket initialization -SOCKET create(JNIEnv* e); -void connect(JNIEnv* e, SOCKET sock, long addr, short port); -void bind(JNIEnv* e, SOCKET sock, long addr, short port); -SOCKET accept(JNIEnv* e, SOCKET sock, long* client_addr, short* client_port); - -// I/O -void send(JNIEnv* e, SOCKET sock, const char* buff_ptr, int buff_size); -int recv(JNIEnv* e, SOCKET sock, char* buff_ptr, int buff_size); - -// Socket closing -void abort(JNIEnv* e, SOCKET sock); -void close(JNIEnv* e, SOCKET sock); -void close_input(JNIEnv* e, SOCKET sock); -void close_output(JNIEnv* e, SOCKET sock); -} -} -} -#endif /* SOCKETS_H_ */ diff --git a/sgx-jvm/avian/corda.pro b/sgx-jvm/avian/corda.pro new file mode 100644 index 0000000000..f2bd8b9713 --- /dev/null +++ b/sgx-jvm/avian/corda.pro @@ -0,0 +1,14 @@ +# proguard include file (http://proguard.sourceforge.net) + +# We need these for Corda deserialisation: +-keep class sun.security.ec.ECPublicKeyImpl +-keep class sun.security.ec.ECPrivateKeyImpl +-keep class org.bouncycastle.jcajce.provider.asymmetric.rsa.BCRSAPublicKey +-keep class org.bouncycastle.jcajce.provider.asymmetric.rsa.BCRSAPrivateCrtKey + +-keep class java.lang.invoke.SerializedLambda { + private java.lang.Object readResolve(); +} + +-keep class com.sun.org.apache.xerces.internal.jaxp.datatype.DatatypeFactoryImpl + diff --git a/sgx-jvm/avian/makefile b/sgx-jvm/avian/makefile index 7cf60292a0..1c64e4dad3 100755 --- a/sgx-jvm/avian/makefile +++ b/sgx-jvm/avian/makefile @@ -184,6 +184,10 @@ ifneq ($(openjdk),) x := $(error "android and openjdk are incompatible") endif + ifeq ($(openjdk-image),) + openjdk-image = $(openjdk)/jre + endif + ifneq ($(openjdk-src),) include openjdk-src.mk options := $(options)-openjdk-src @@ -2382,8 +2386,6 @@ $(openjdk-jar-dep): @mkdir -p $(classpath-build) (cd $(classpath-build) && \ $(jar) xf "$$($(native-path) "$(openjdk-image)/lib/rt.jar")" && \ - $(jar) xf "$$($(native-path) "$(openjdk-image)/lib/jsse.jar")" && \ - $(jar) xf "$$($(native-path) "$(openjdk-image)/lib/jce.jar")" && \ $(jar) xf "$$($(native-path) "$(openjdk-image)/lib/charsets.jar")" && \ $(jar) xf "$$($(native-path) "$(openjdk-image)/lib/resources.jar")" && \ $(jar) xf "$$($(native-path) "$(openjdk-image)/lib/ext/sunec.jar")") diff --git a/sgx-jvm/avian/openjdk-src.mk b/sgx-jvm/avian/openjdk-src.mk index 6fca90126a..4bf2a6c678 100644 --- a/sgx-jvm/avian/openjdk-src.mk +++ b/sgx-jvm/avian/openjdk-src.mk @@ -94,7 +94,6 @@ openjdk-headers-classes = \ sun.misc.VMSupport \ sun.misc.Version \ sun.misc.URLClassPath \ - sun.net.spi.DefaultProxySelector \ sun.nio.ch.IOStatus \ sun.reflect.ConstantPool \ sun.reflect.NativeConstructorAccessorImpl \ @@ -214,7 +213,6 @@ else "-I$(openjdk-src)/solaris/native/java/lang" \ "-I$(openjdk-src)/solaris/native/java/net" \ "-I$(openjdk-src)/solaris/native/java/util" \ - "-I$(openjdk-src)/solaris/native/sun/management" \ "-I$(openjdk-src)/solaris/native/sun/nio/ch" \ "-I$(openjdk-src)/solaris/javavm/include" \ "-I$(openjdk-src)/solaris/hpi/include" \ diff --git a/sgx-jvm/avian/src/avian/machine.h b/sgx-jvm/avian/src/avian/machine.h index 7bb8f1f095..b2a56b80ad 100644 --- a/sgx-jvm/avian/src/avian/machine.h +++ b/sgx-jvm/avian/src/avian/machine.h @@ -1341,6 +1341,9 @@ class Thread { return flags; } + bool isBlacklisting(); + void startBlacklisting(); + JNIEnvVTable* vtable; Machine* m; Thread* parent; diff --git a/sgx-jvm/avian/src/builtin.cpp b/sgx-jvm/avian/src/builtin.cpp index 4369ec62d2..6e1a4f53a0 100644 --- a/sgx-jvm/avian/src/builtin.cpp +++ b/sgx-jvm/avian/src/builtin.cpp @@ -183,6 +183,12 @@ extern "C" AVIAN_EXPORT int64_t JNICALL t->m->classpath->makeString(t, array, offset, length)); } +extern "C" AVIAN_EXPORT void JNICALL + Avian_avian_SystemClassLoader_startBlacklisting0(Thread* t, object, uintptr_t*) +{ + t->startBlacklisting(); +} + extern "C" AVIAN_EXPORT int64_t JNICALL Avian_avian_SystemClassLoader_appLoader(Thread* t, object, uintptr_t*) { diff --git a/sgx-jvm/avian/src/classpath-avian.cpp b/sgx-jvm/avian/src/classpath-avian.cpp index 41ca4b1637..a89a143d5d 100644 --- a/sgx-jvm/avian/src/classpath-avian.cpp +++ b/sgx-jvm/avian/src/classpath-avian.cpp @@ -66,6 +66,7 @@ class MyClasspath : public Classpath { 0, 0, group, + 0, 0); } diff --git a/sgx-jvm/avian/src/classpath-openjdk.cpp b/sgx-jvm/avian/src/classpath-openjdk.cpp index 4cf8d62f3f..e66427835c 100644 --- a/sgx-jvm/avian/src/classpath-openjdk.cpp +++ b/sgx-jvm/avian/src/classpath-openjdk.cpp @@ -3355,7 +3355,7 @@ uint64_t jvmInitProperties(Thread* t, uintptr_t* arguments) local::setProperty( t, method, *properties, "java.vm.vendor", "Avian Contributors"); - local::setProperty(t, method, *properties, "java.vm.name", "Avian"); + local::setProperty(t, method, *properties, "java.vm.name", "Avian (Corda)"); #ifdef AVIAN_VERSION local::setProperty(t, method, *properties, "java.vm.version", AVIAN_VERSION); #endif diff --git a/sgx-jvm/avian/src/machine.cpp b/sgx-jvm/avian/src/machine.cpp index 90f807c36f..469eb1a803 100644 --- a/sgx-jvm/avian/src/machine.cpp +++ b/sgx-jvm/avian/src/machine.cpp @@ -3964,6 +3964,18 @@ void Thread::dispose() m->processor->dispose(this); } +bool Thread::isBlacklisting() +{ + return (javaThread != NULL) && javaThread->blacklisting(); +} + +void Thread::startBlacklisting() +{ + if (javaThread != NULL) { + javaThread->setBlacklisting(this, 1); + } +} + void shutDown(Thread* t) { ACQUIRE(t, t->m->shutdownLock); @@ -4884,6 +4896,40 @@ GcClass* resolveSystemClass(Thread* t, ACQUIRE(t, t->m->classLock); + /* + * We require that SystemClassLoader.isForbidden() has already + * been executed once before isBlacklisting is set to true. + * Otherwise this code-block recurses until the stack explodes. + */ + if (t->isBlacklisting() + && ::strcmp("avian/SystemClassLoader", reinterpret_cast(spec->body().begin()))) { + GcMethod* forbid = resolveMethod(t, + roots(t)->bootLoader(), + "avian/SystemClassLoader", + "isForbidden", + "(Ljava/lang/String;)Z"); + GcString *name = t->m->classpath->makeString(t, spec, 0, spec->length()); + GcInt *result = cast(t, t->m->processor->invoke(t, forbid, NULL, name)); + if (UNLIKELY(t->exception)) { + if (throw_) { + GcThrowable* e = t->exception; + t->exception = 0; + vm::throw_(t, e); + } else { + t->exception = 0; + return 0; + } + } + + if (result->value() == JNI_TRUE) { + if (throw_) { + throwNew(t, throwType, "%s", spec->body().begin()); + } else { + return 0; + } + } + } + GcClass* class_ = findLoadedClass(t, loader, spec); if (class_ == 0) { PROTECT(t, class_); diff --git a/sgx-jvm/avian/src/types.def b/sgx-jvm/avian/src/types.def index da247c9d26..bf26c3c659 100644 --- a/sgx-jvm/avian/src/types.def +++ b/sgx-jvm/avian/src/types.def @@ -188,6 +188,7 @@ (require object interruptLock) (require uint8_t interrupted) (require uint8_t unparked) + (require uint8_t blacklisting) (alias peer uint64_t eetop) (alias peer uint64_t nativePeer) (require uint64_t peer)) diff --git a/sgx-jvm/avian/test/BufferedInputStreamTest.java b/sgx-jvm/avian/test/BufferedInputStreamTest.java index ba978cd5ef..c5db546849 100644 --- a/sgx-jvm/avian/test/BufferedInputStreamTest.java +++ b/sgx-jvm/avian/test/BufferedInputStreamTest.java @@ -51,16 +51,6 @@ public class BufferedInputStreamTest } //on all following calls block. The spec says, that a least one byte is returned, if the //stream is not at EOF. - while(available() == 0) - { - try - { - Thread.sleep(100); - } - catch (InterruptedException e) - { - } - } return 0; } diff --git a/sgx-jvm/avian/test/Buffers.java b/sgx-jvm/avian/test/Buffers.java index 2a4411d528..4af5fddfbc 100644 --- a/sgx-jvm/avian/test/Buffers.java +++ b/sgx-jvm/avian/test/Buffers.java @@ -1,4 +1,4 @@ -import java.io.IOException; +import java.io.UnsupportedEncodingException; import java.nio.ByteBuffer; import java.nio.BufferUnderflowException; import java.nio.BufferOverflowException; @@ -9,7 +9,7 @@ public class Buffers { System.loadLibrary("test"); } - private static void testArrays(Factory factory1, Factory factory2) throws IOException { + private static void testArrays(Factory factory1, Factory factory2) throws UnsupportedEncodingException { final int size = 64; ByteBuffer b1 = factory1.allocate(size); ByteBuffer b2 = factory2.allocate(size); @@ -118,16 +118,6 @@ public class Buffers { } }; - Factory direct = new Factory() { - public ByteBuffer allocate(int capacity) { - return ByteBuffer.allocateDirect(capacity); - } - - public void dispose(ByteBuffer b) { - // ignore - } - }; - Factory native_ = new Factory() { public ByteBuffer allocate(int capacity) { return allocateNative(capacity); @@ -140,22 +130,11 @@ public class Buffers { testPrimativeGetAndSet(array, array); testArrays(array, array); - testPrimativeGetAndSet(array, direct); - testArrays(array, direct); testPrimativeGetAndSet(array, native_); testArrays(array, native_); - testPrimativeGetAndSet(direct, array); - testArrays(direct, array); - testPrimativeGetAndSet(direct, direct); - testArrays(direct, direct); - testPrimativeGetAndSet(direct, native_); - testArrays(direct, native_); - testPrimativeGetAndSet(native_, array); testArrays(native_, array); - testPrimativeGetAndSet(native_, direct); - testArrays(native_, direct); testPrimativeGetAndSet(native_, native_); testArrays(native_, native_); diff --git a/sgx-jvm/avian/test/CompletionServiceTest.java b/sgx-jvm/avian/test/CompletionServiceTest.java deleted file mode 100644 index 975f632855..0000000000 --- a/sgx-jvm/avian/test/CompletionServiceTest.java +++ /dev/null @@ -1,54 +0,0 @@ -import java.util.concurrent.Callable; -import java.util.concurrent.ExecutionException; -import java.util.concurrent.Executor; -import java.util.concurrent.ExecutorCompletionService; -import java.util.concurrent.TimeUnit; - -public class CompletionServiceTest { - public static void main(String args[]) throws InterruptedException, ExecutionException { - Executor dumbExecutor = new Executor() { - @Override - public void execute(Runnable task) { - new Thread(task).start(); - } - }; - - pollNoResultTest(dumbExecutor); - pollTimeoutNoResultTest(dumbExecutor); - takeTest(dumbExecutor); - } - - private static void verify(boolean val) { - if (! val) { - throw new RuntimeException(); - } - } - - private static void pollNoResultTest(Executor executor) { - ExecutorCompletionService ecs = new ExecutorCompletionService(executor); - - verify(ecs.poll() == null); - } - - private static void pollTimeoutNoResultTest(Executor executor) throws InterruptedException { - long delayTime = 0; - ExecutorCompletionService ecs = new ExecutorCompletionService(executor); - - long startTime = System.currentTimeMillis(); - verify(ecs.poll(delayTime, TimeUnit.MILLISECONDS) == null); - verify(System.currentTimeMillis() - startTime >= delayTime); - } - - private static void takeTest(Executor executor) throws InterruptedException, ExecutionException { - ExecutorCompletionService ecs = new ExecutorCompletionService(executor); - final Object result = new Object(); - ecs.submit(new Callable() { - @Override - public Object call() throws Exception { - return result; - } - }); - - verify(ecs.take().get() == result); - } -} diff --git a/sgx-jvm/avian/test/FutureTaskTest.java b/sgx-jvm/avian/test/FutureTaskTest.java index 7a8ea9d9a7..13159320b9 100644 --- a/sgx-jvm/avian/test/FutureTaskTest.java +++ b/sgx-jvm/avian/test/FutureTaskTest.java @@ -11,10 +11,6 @@ public class FutureTaskTest { public static void main(String[] args) throws InterruptedException, ExecutionException { isDoneTest(false); isDoneTest(true); - getCallableResultTest(); - getRunnableResultTest(); - getTimeoutFail(); - getExecutionExceptionTest(); } private static void isDoneTest(final boolean throwException) { @@ -34,72 +30,4 @@ public class FutureTaskTest { throw new RuntimeException("Future should be done"); } } - - private static void getCallableResultTest() throws InterruptedException, ExecutionException { - final Object result = new Object(); - FutureTask future = new FutureTask(new Callable() { - @Override - public Object call() throws Exception { - return result; - } - }); - - future.run(); - if (future.get() != result) { - throw new RuntimeException("Bad result returned: " + future.get()); - } - } - - private static void getRunnableResultTest() throws InterruptedException, ExecutionException { - final Object result = new Object(); - FutureTask future = new FutureTask(new Runnable() { - @Override - public void run() { - // nothing here - } - }, result); - - future.run(); - if (future.get() != result) { - throw new RuntimeException("Bad result returned: " + future.get()); - } - } - - private static void getTimeoutFail() throws InterruptedException, - ExecutionException { - RunnableFuture future = new FutureTask(new Runnable() { - @Override - public void run() { - // wont run - } - }, null); - - long startTime = System.currentTimeMillis(); - try { - future.get(DELAY_TIME, TimeUnit.MILLISECONDS); - throw new RuntimeException("Exception should have been thrown"); - } catch (TimeoutException e) { - long catchTime = System.currentTimeMillis(); - if (catchTime - startTime < DELAY_TIME) { - throw new RuntimeException("get with timeout did not block long enough"); - } - } - } - - private static void getExecutionExceptionTest() throws InterruptedException, ExecutionException { - FutureTask future = new FutureTask(new Runnable() { - @Override - public void run() { - throw new RuntimeException(); - } - }, null); - - future.run(); - try { - future.get(); - throw new RuntimeException("Exception should have thrown"); - } catch (ExecutionException e) { - // expected - } - } } diff --git a/sgx-jvm/avian/test/LinkedBlockingQueueTest.java b/sgx-jvm/avian/test/LinkedBlockingQueueTest.java deleted file mode 100644 index f0eed44994..0000000000 --- a/sgx-jvm/avian/test/LinkedBlockingQueueTest.java +++ /dev/null @@ -1,208 +0,0 @@ -import java.util.LinkedList; -import java.util.concurrent.LinkedBlockingQueue; -import java.util.concurrent.TimeUnit; - -public class LinkedBlockingQueueTest { - private static final int DELAY_TILL_ACTION = 10; - - public static void main(String[] args) throws InterruptedException { - remainingCapacityTest(); - QueueHelper.sizeTest(new LinkedBlockingQueue()); - QueueHelper.isEmptyTest(new LinkedBlockingQueue()); - QueueHelper.addTest(new LinkedBlockingQueue()); - addCapacityFail(); - offerTest(); - offerWithTimeoutTest(); - offerTimeoutTest(); - putTest(); - QueueHelper.addAllTest(new LinkedBlockingQueue()); - addAllFail(); - QueueHelper.elementTest(new LinkedBlockingQueue()); - QueueHelper.elementFail(new LinkedBlockingQueue()); - pollEmptyTest(); - pollTest(); - pollTimeoutTest(); - takeTest(); - QueueHelper.removeEmptyFail(new LinkedBlockingQueue()); - QueueHelper.removeTest(new LinkedBlockingQueue()); - drainToTest(); - drainToLimitTest(); - QueueHelper.containsTest(new LinkedBlockingQueue()); - QueueHelper.containsAllTest(new LinkedBlockingQueue()); - QueueHelper.removeObjectTest(new LinkedBlockingQueue()); - QueueHelper.removeAllTest(new LinkedBlockingQueue()); - QueueHelper.clearTest(new LinkedBlockingQueue()); - QueueHelper.toArrayTest(new LinkedBlockingQueue()); - } - - private static void verify(boolean val) { - if (! val) { - throw new RuntimeException(); - } - } - - private static void remainingCapacityTest() { - LinkedBlockingQueue lbq = new LinkedBlockingQueue(2); - verify(lbq.remainingCapacity() == 2); - - lbq.add(new Object()); - verify(lbq.remainingCapacity() == 1); - } - - private static void addCapacityFail() { - LinkedBlockingQueue lbq = new LinkedBlockingQueue(1); - Object testObject = new Object(); - lbq.add(testObject); - - try { - lbq.add(new Object()); - throw new RuntimeException("Exception should have thrown"); - } catch (IllegalStateException e) { - // expected - } - - verify(lbq.size() == 1); - verify(lbq.peek() == testObject); - } - - private static void offerTest() { - LinkedBlockingQueue lbq = new LinkedBlockingQueue(1); - Object testObject = new Object(); - verify(lbq.offer(testObject)); - verify(! lbq.offer(new Object())); - - verify(lbq.size() == 1); - verify(lbq.peek() == testObject); - } - - private static void offerWithTimeoutTest() throws InterruptedException { - final LinkedBlockingQueue lbq = new LinkedBlockingQueue(1); - lbq.add(new Object()); - - new Thread(new Runnable() { - @Override - public void run() { - try { - // sleep to make sure offer call starts first - Thread.sleep(DELAY_TILL_ACTION); - lbq.take(); - } catch (InterruptedException e) { - Thread.currentThread().interrupt(); - } - } - }).start(); - - // should accept once thread starts - verify(lbq.offer(new Object(), 10, TimeUnit.SECONDS)); - } - - private static void offerTimeoutTest() throws InterruptedException { - LinkedBlockingQueue lbq = new LinkedBlockingQueue(1); - lbq.add(new Object()); - - verify(! lbq.offer(new Object(), 10, TimeUnit.MILLISECONDS)); - } - - private static void putTest() throws InterruptedException { - LinkedBlockingQueue lbq = new LinkedBlockingQueue(); - Object testObject = new Object(); - lbq.put(testObject); - - verify(lbq.size() == 1); - verify(lbq.peek() == testObject); - } - - private static void addAllFail() { - LinkedBlockingQueue lbq = new LinkedBlockingQueue(1); - LinkedList toAdd = new LinkedList(); - toAdd.add(new Object()); - toAdd.add(new Object()); - - try { - lbq.addAll(toAdd); - throw new RuntimeException("Exception should have thrown"); - } catch (IllegalStateException e) { - // expected - } - } - - private static void pollEmptyTest() { - LinkedBlockingQueue lbq = new LinkedBlockingQueue(); - - verify(lbq.poll() == null); - } - - private static void pollTest() { - LinkedBlockingQueue lbq = new LinkedBlockingQueue(); - Object testObject = new Object(); - lbq.add(testObject); - - verify(lbq.poll() == testObject); - } - - private static void pollTimeoutTest() throws InterruptedException { - final LinkedBlockingQueue lbq = new LinkedBlockingQueue(); - final Object testObject = new Object(); - new Thread(new Runnable() { - @Override - public void run() { - try { - Thread.sleep(DELAY_TILL_ACTION); - } catch (InterruptedException e) { - Thread.currentThread().interrupt(); - } - - lbq.add(testObject); - } - }).start(); - - - verify(lbq.poll(DELAY_TILL_ACTION * 10, TimeUnit.MILLISECONDS) == testObject); - } - - private static void takeTest() throws InterruptedException { - final LinkedBlockingQueue lbq = new LinkedBlockingQueue(); - final Object testObject = new Object(); - new Thread(new Runnable() { - @Override - public void run() { - try { - Thread.sleep(DELAY_TILL_ACTION); - } catch (InterruptedException e) { - Thread.currentThread().interrupt(); - } - - lbq.add(testObject); - } - }).start(); - - - verify(lbq.take() == testObject); - } - - private static void drainToTest() { - int objQty = 2; - LinkedBlockingQueue lbq = new LinkedBlockingQueue(); - for (int i = 0; i < objQty; i++) { - lbq.add(new Object()); - } - - LinkedList drainToResult = new LinkedList(); - verify(lbq.drainTo(drainToResult) == objQty); - verify(drainToResult.size() == objQty); - } - - private static void drainToLimitTest() { - int objQty = 4; - int limit = 2; - LinkedBlockingQueue lbq = new LinkedBlockingQueue(); - for (int i = 0; i < objQty; i++) { - lbq.add(new Object()); - } - - LinkedList drainToResult = new LinkedList(); - verify(lbq.drainTo(drainToResult, limit) == limit); - verify(drainToResult.size() == limit); - verify(lbq.size() == objQty - limit); - } -} diff --git a/sgx-jvm/avian/test/MemoryRamp.java b/sgx-jvm/avian/test/MemoryRamp.java index 2023a5483b..cba83ebb13 100644 --- a/sgx-jvm/avian/test/MemoryRamp.java +++ b/sgx-jvm/avian/test/MemoryRamp.java @@ -29,7 +29,6 @@ public class MemoryRamp implements Runnable { * @return time to create and access array in milliseconds */ private static long mem() { - long start = System.currentTimeMillis(); final byte[] array = new byte[ARRAY_SIZE]; if (ACCESS_ARRAY) { for (int i = 0; i < array.length; i++) { @@ -37,7 +36,7 @@ public class MemoryRamp implements Runnable { byte x = array[i]; //read } } - return System.currentTimeMillis() - start; + return 0; } /** @@ -46,7 +45,6 @@ public class MemoryRamp implements Runnable { */ private static long memMulti(int numOfThreads) { Thread[] threads = new Thread[numOfThreads]; - long start = System.currentTimeMillis(); for (int i = 0; i < threads.length; i++) { threads[i] = new Thread(new MemoryRamp(), "mem-"); @@ -61,6 +59,6 @@ public class MemoryRamp implements Runnable { catch (InterruptedException iex) { throw new RuntimeException(iex); } - return System.currentTimeMillis() - start; + return 0; } } diff --git a/sgx-jvm/avian/test/Misc.java b/sgx-jvm/avian/test/Misc.java index 49a51262d2..21d7937d4f 100644 --- a/sgx-jvm/avian/test/Misc.java +++ b/sgx-jvm/avian/test/Misc.java @@ -254,8 +254,6 @@ public class Misc { } } - System.out.println(new java.util.Date().toString()); - System.out.println('x'); System.out.println(true); System.out.println(42); diff --git a/sgx-jvm/avian/test/extra/SendFile.java b/sgx-jvm/avian/test/extra/SendFile.java deleted file mode 100644 index da77a33a21..0000000000 --- a/sgx-jvm/avian/test/extra/SendFile.java +++ /dev/null @@ -1,73 +0,0 @@ -package extra; - -import java.net.InetSocketAddress; -import java.nio.ByteBuffer; -import java.io.IOException; -import java.nio.channels.Selector; -import java.nio.channels.SelectionKey; -import java.nio.channels.SocketChannel; -import java.io.OutputStream; -import java.io.FileInputStream; - -public class SendFile { - private static class SocketOutputStream extends OutputStream { - private final SocketChannel channel; - private final Selector selector; - public SocketOutputStream(String host, int port) throws Exception { - channel = SocketChannel.open(); - channel.connect(new InetSocketAddress(host, port)); - channel.configureBlocking(false); - selector = Selector.open(); - channel.register(selector, SelectionKey.OP_WRITE, null); - } - - public void close() throws IOException { - channel.close(); - } - - public void write(int c) { - throw new RuntimeException("Do not use!"); - } - public void write(byte[] buffer, int offset, int length) - throws IOException { - ByteBuffer buf = ByteBuffer.wrap(buffer); - buf.position(offset); - buf.limit(offset+length); - while (buf.hasRemaining()) { - selector.select(10000); - for (SelectionKey key : selector.selectedKeys()) { - if (key.isWritable() && (key.channel() == channel)) { - channel.write(buf); - } - } - } - } - } - - public static void sendFile(String file, String host, int port) - throws Exception { - System.out.println("Sending " + file); - OutputStream os = new SocketOutputStream(host, port); - FileInputStream is = new FileInputStream(file); - byte[] buf = new byte[16384]; - int count=-1; - while ((count = is.read(buf)) >= 0) { - os.write(buf, 0, count); - } - is.close(); - os.close(); - } - - public static void main(String args[]) { - if (args.length != 2) { - System.out.println("Usage: SendFile file host"); - } else { - try { - sendFile(args[0], args[1], 8988); - } catch (Exception ex) { - ex.printStackTrace(); - } - } - } -} - diff --git a/sgx-jvm/avian/test/extra/SendServer.java b/sgx-jvm/avian/test/extra/SendServer.java deleted file mode 100644 index 5f60c962c1..0000000000 --- a/sgx-jvm/avian/test/extra/SendServer.java +++ /dev/null @@ -1,92 +0,0 @@ -package extra; - -import java.net.InetSocketAddress; -import java.nio.ByteBuffer; -import java.nio.channels.SelectionKey; -import java.nio.channels.Selector; -import java.nio.channels.ServerSocketChannel; -import java.nio.channels.SocketChannel; - -public class SendServer { - private static char cIndex = 'A'; - private static ByteBuffer inBuf = ByteBuffer.allocate(8192); - - private static void dumpByteBuffer(char note, ByteBuffer buf) { - System.out.println(note + ": Buffer position: " + buf.position() + " limit: " + - buf.limit() + " capacity: " + buf.capacity() + " remaining: " + - buf.remaining()); - } - - private static class Connection { - private final char myIndex; - private final java.io.FileOutputStream fos; - - public Connection() throws Exception { - myIndex = cIndex++; - fos = new java.io.FileOutputStream("dump." + myIndex); - } - - public void handleRead(SocketChannel channel) throws Exception { - int count = -1; - while ((count = channel.read(inBuf)) > 0) { - System.out.println(myIndex + ": read " + count); - } - inBuf.flip(); - fos.write(inBuf.array(), inBuf.arrayOffset()+inBuf.position(), inBuf.remaining()); - inBuf.position(inBuf.limit()); - if (count < 0) { - System.out.println(myIndex + ": Closing channel"); - fos.close(); - channel.close(); - } -// dumpByteBuffer(myIndex, inBuf); - inBuf.compact(); - } - } - - public void runMainLoop() throws Exception { - boolean keepRunning = true; - int port = 8988; - ServerSocketChannel serverChannel = ServerSocketChannel.open(); - try { - serverChannel.configureBlocking(false); - serverChannel.socket().bind(new InetSocketAddress("0.0.0.0", port)); - Selector selector = Selector.open(); - serverChannel.register(selector, SelectionKey.OP_ACCEPT, null); - while (keepRunning) { - System.out.println("Running main loop"); - selector.select(10000); - for (SelectionKey key : selector.selectedKeys()) { - if (key.isAcceptable()) { - System.out.println("Accepting new connection"); - SocketChannel c = ((ServerSocketChannel) key.channel()).accept(); - if (c != null) { - c.configureBlocking(false); - c.register(selector, SelectionKey.OP_READ, new Connection()); - } - } else { - SocketChannel c = (SocketChannel) key.channel(); - if (c.isOpen() && key.isReadable()) { - Connection connection = (Connection)key.attachment(); - connection.handleRead(c); - } - } - } - selector.selectedKeys().clear(); - } - } finally { - serverChannel.close(); - } - } - - public static void main(String args[]) { - try { - System.out.println("Starting server"); - if (args.length > 0) { - new SendServer().runMainLoop(); - } - } catch (Exception ex) { - ex.printStackTrace(); - } - } -} diff --git a/sgx-jvm/avian/test/extra/Sockets.java b/sgx-jvm/avian/test/extra/Sockets.java deleted file mode 100644 index 75cd278982..0000000000 --- a/sgx-jvm/avian/test/extra/Sockets.java +++ /dev/null @@ -1,41 +0,0 @@ -package extra; - -import java.io.BufferedReader; -import java.io.BufferedWriter; -import java.io.IOException; -import java.io.InputStreamReader; -import java.io.OutputStreamWriter; -import java.net.Socket; -import java.net.UnknownHostException; - -public class Sockets { - - /** - * @param args - * @throws IOException - * @throws UnknownHostException - */ - public static void main(String[] args) throws UnknownHostException, - IOException { - System.out.print("Requesting... " + args[0] + "\n"); - Socket sock = new Socket(args[0], 80); - try { - BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(sock.getOutputStream())); - String request = "GET /?gws_rd=cr HTTP/1.1\r\n" - + "Host: " + args[0] + "\r\n" + "Accept: */*\r\n" - + "User-Agent: Java\r\n" + "Connection: close\r\n" + "\r\n"; - bw.write(request); - bw.flush(); - - BufferedReader br = new BufferedReader(new InputStreamReader(sock.getInputStream())); - String read = null; - while ((read = br.readLine()) != null) { - System.out.println(read); - } - bw.close(); - } finally { - sock.close(); - } - } - -} \ No newline at end of file diff --git a/sgx-jvm/jvm-enclave/enclave/CMakeLists.txt b/sgx-jvm/jvm-enclave/enclave/CMakeLists.txt index a5b506d1ed..854926a696 100644 --- a/sgx-jvm/jvm-enclave/enclave/CMakeLists.txt +++ b/sgx-jvm/jvm-enclave/enclave/CMakeLists.txt @@ -23,6 +23,7 @@ set(ENCLAVE_SIGNED_OUTPUT_LIB cordaenclave.signed.so) set(SGX_SIGN_TOOL ${SGX_SDK}/build/linux/sgx_sign) set(PROGUARD_JAR_PATH ${CMAKE_CURRENT_SOURCE_DIR}/../../dependencies/root/usr/share/java/proguard.jar) set(AVIAN_PATH ${PROJECT_SOURCE_DIR}/../../avian) +set(JDK_IMAGE ${PROJECT_SOURCE_DIR}/../../jdk8u/build/linux-x86_64-normal-server-release/images/j2re-image) set(ENCLAVE_JAR_PATH ${PROJECT_SOURCE_DIR}/../../../verify-enclave/build/libs/corda-enclavelet.jar) set(AVIAN_PROCESS "-debug-openjdk-src") @@ -55,8 +56,8 @@ set(PRIVATE_KEY_NAME ${CMAKE_CURRENT_SOURCE_DIR}/selfsigning.pem) # Now add the compiled class files to our copy of the boot jar (as we need a single uni-jar for everything). add_custom_command( - OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/encjars/classpath.jar ${CMAKE_CURRENT_BINARY_DIR}/encjars/app.jar ${CMAKE_CURRENT_BINARY_DIR}/encjars/corda-enclavelet.jar ${CMAKE_CURRENT_BINARY_DIR}/encjars/jce.jar ${CMAKE_CURRENT_BINARY_DIR}/encjars/jsse.jar ${CMAKE_CURRENT_BINARY_DIR}/encjars/sunjce_provider.jar - COMMAND ${CMAKE_CURRENT_SOURCE_DIR}/create-boot-jar.sh ${AVIAN_PATH}/build/linux-x86_64${AVIAN_PROCESS} ${ENCLAVE_JAR_PATH} ${CMAKE_CURRENT_BINARY_DIR}/encjars ${PROGUARD_JAR_PATH} ${CMAKE_CURRENT_SOURCE_DIR}/proguard.pro ${JAVA_HOME} + OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/encjars/classpath.jar ${CMAKE_CURRENT_BINARY_DIR}/encjars/app.jar ${CMAKE_CURRENT_BINARY_DIR}/encjars/corda-enclavelet.jar ${CMAKE_CURRENT_BINARY_DIR}/encjars/jce.jar ${CMAKE_CURRENT_BINARY_DIR}/encjars/jsse.jar + COMMAND ${CMAKE_CURRENT_SOURCE_DIR}/create-boot-jar.sh ${AVIAN_PATH}/build/linux-x86_64${AVIAN_PROCESS} ${ENCLAVE_JAR_PATH} ${CMAKE_CURRENT_BINARY_DIR}/encjars ${PROGUARD_JAR_PATH} ${CMAKE_CURRENT_SOURCE_DIR}/proguard.pro ${JDK_IMAGE} DEPENDS ${ENCLAVE_JAR_PATH} ) diff --git a/sgx-jvm/jvm-enclave/enclave/create-boot-jar.sh b/sgx-jvm/jvm-enclave/enclave/create-boot-jar.sh index 6fbf9536c7..b7542729d2 100755 --- a/sgx-jvm/jvm-enclave/enclave/create-boot-jar.sh +++ b/sgx-jvm/jvm-enclave/enclave/create-boot-jar.sh @@ -6,7 +6,7 @@ # 3) path to the output dir # 4) path to proguard jar # 5) path to proguard conf -# 6) path to openjdk install +# 6) path to openjdk image if [ ! -d "$1" ]; then echo "$1 is not a directory"; exit 1; fi if [ ! -e "$2" ]; then echo "$2 does not exist"; exit 1; fi @@ -21,7 +21,7 @@ appjar=$( readlink -f $2 ) outputjardir=$( readlink -f $3 ) proguard_jar=$( readlink -f $4 ) proguard_conf=$( readlink -f $5 ) -openjdk_libs=$6/jre/lib +openjdk_libs=$6/lib mkdir -p $outputjardir if [ ! -e $openjdk_libs/jsse.jar ]; then @@ -29,7 +29,7 @@ if [ ! -e $openjdk_libs/jsse.jar ]; then exit 1 fi -cmd="java -jar $proguard_jar @$avianpath/../../vm.pro @$avianpath/../../openjdk.pro @$proguard_conf -injars $bootjar -injars $appjar -injars $openjdk_libs/jsse.jar -injars $openjdk_libs/jce.jar -injars $openjdk_libs/ext/sunjce_provider.jar -outjars $outputjardir" +cmd="java -jar $proguard_jar @$avianpath/../../vm.pro @$avianpath/../../openjdk.pro @$avianpath/../../corda.pro @$proguard_conf -injars $bootjar -injars $appjar -injars $openjdk_libs/jsse.jar -injars $openjdk_libs/jce.jar -outjars $outputjardir" # echo $cmd $cmd @@ -37,9 +37,12 @@ mkdir -p $outputjardir/temp cd $outputjardir/temp jar xf ../jce.jar jar xf ../jsse.jar -jar xf ../sunjce_provider.jar jar xf $openjdk_libs/charsets.jar jar xf $2 +rm -f META-INF/*.DSA +rm -f META-INF/*.RSA +rm -f META-INF/*.SF +rm -f META-INF/*.MF jar cf ../app.jar * cd .. rm -r temp diff --git a/sgx-jvm/jvm-enclave/enclave/enclave.cpp b/sgx-jvm/jvm-enclave/enclave/enclave.cpp index 95511b1c43..2de59b2263 100644 --- a/sgx-jvm/jvm-enclave/enclave/enclave.cpp +++ b/sgx-jvm/jvm-enclave/enclave/enclave.cpp @@ -35,8 +35,8 @@ void check_transaction(void *reqbuf, size_t buflen, char *error) { vmArgs.version = JNI_VERSION_1_2; vmArgs.ignoreUnrecognized = JNI_TRUE; - char xmxOption[256]; - snprintf(xmxOption, 256, "-Xmx%d", g_global_data.heap_size); + char xmxOption[32]; + snprintf(xmxOption, sizeof(xmxOption), "-Xmx%d", g_global_data.heap_size); JavaVMOption options[] = { // Tell Avian to call the functions above to find the embedded jar data. // We separate the app into boot and app jars because some code does not @@ -49,9 +49,8 @@ void check_transaction(void *reqbuf, size_t buflen, char *error) { vmArgs.nOptions = sizeof(options) / sizeof(JavaVMOption); JavaVM* vm = NULL; - void* env_void = NULL; - JNI_CreateJavaVM(&vm, &env_void, &vmArgs); - JNIEnv* env = static_cast(env_void); + JNIEnv* env = NULL; + JNI_CreateJavaVM(&vm, reinterpret_cast(&env), &vmArgs); env->FindClass("com/r3/enclaves/txverify/EnclaveletSerializationScheme"); if (!env->ExceptionCheck()) { @@ -60,7 +59,7 @@ void check_transaction(void *reqbuf, size_t buflen, char *error) { jmethodID m = env->GetStaticMethodID(c, "verifyInEnclave", "([B)V"); if (!env->ExceptionCheck()) { jbyteArray reqbits = env->NewByteArray((jsize) buflen); - env->SetByteArrayRegion(reqbits, 0, buflen, (const jbyte *)reqbuf); + env->SetByteArrayRegion(reqbits, 0, buflen, static_cast(reqbuf)); jobject result = env->CallStaticObjectMethod(c, m, reqbits); } } diff --git a/sgx-jvm/jvm-enclave/enclave/enclave.xml b/sgx-jvm/jvm-enclave/enclave/enclave.xml index e5f0e0f1a2..31d71b3465 100644 --- a/sgx-jvm/jvm-enclave/enclave/enclave.xml +++ b/sgx-jvm/jvm-enclave/enclave/enclave.xml @@ -2,7 +2,7 @@ 0 0 0x280000 - 0x5500000 + 0x8000000 1 10 1 diff --git a/sgx-jvm/jvm-enclave/jni/jni_sgx_api.cpp b/sgx-jvm/jvm-enclave/jni/jni_sgx_api.cpp index 07134637c1..a89314f05d 100644 --- a/sgx-jvm/jvm-enclave/jni/jni_sgx_api.cpp +++ b/sgx-jvm/jvm-enclave/jni/jni_sgx_api.cpp @@ -6,7 +6,7 @@ extern "C" { -JNIEXPORT jstring JNICALL Java_com_r3_enclaves_txverify_NativeSgxApi_verify(JNIEnv *env, jobject, jstring enclave_path, jbyteArray transaction) { +JNIEXPORT jstring JNICALL Java_com_r3_enclaves_txverify_NativeSgxApi_verify(JNIEnv *env, jclass, jstring enclave_path, jbyteArray transaction) { sgx_launch_token_t token = {0}; sgx_enclave_id_t enclave_id = {0}; int updated = 0; @@ -26,4 +26,4 @@ JNIEXPORT jstring JNICALL Java_com_r3_enclaves_txverify_NativeSgxApi_verify(JNIE } } -} \ No newline at end of file +} diff --git a/sgx-jvm/linux-sgx/psw/urts/loader.cpp b/sgx-jvm/linux-sgx/psw/urts/loader.cpp index 515b70df8e..cb1e0346eb 100644 --- a/sgx-jvm/linux-sgx/psw/urts/loader.cpp +++ b/sgx-jvm/linux-sgx/psw/urts/loader.cpp @@ -365,7 +365,7 @@ int CLoader::build_secs(sgx_attributes_t * const secs_attr, sgx_misc_attribute_t int ret = enclave_creator->create_enclave(&m_secs, &m_enclave_id, &m_start_addr, is_ae(&m_metadata->enclave_css)); if(SGX_SUCCESS == ret) { - SE_TRACE(SE_TRACE_NOTICE, "enclave start address = %p, size = %x\n", m_start_addr, m_metadata->enclave_size); + SE_TRACE(SE_TRACE_NOTICE, "enclave start address = %p, size = 0x%x\n", m_start_addr, m_metadata->enclave_size); } return ret; } diff --git a/verify-enclave/build.gradle b/verify-enclave/build.gradle index 99eea3e645..6b7c173dfc 100644 --- a/verify-enclave/build.gradle +++ b/verify-enclave/build.gradle @@ -67,11 +67,16 @@ jar { task integrationTest(type: Test) { testClassesDirs = sourceSets.integrationTest.output.classesDirs classpath = sourceSets.integrationTest.runtimeClasspath - jvmArgs '-Djava.library.path=../sgx-jvm/jvm-enclave/jni/build' + systemProperties['java.library.path'] = '../sgx-jvm/jvm-enclave/jni/build' +} + +test { + // Pending Gradle bug: https://github.com/gradle/gradle/issues/2657 + //systemProperties['java.system.class.loader'] = 'com.r3.enclaves.DummySystemClassLoader' } task generateNativeSgxHeaders(type: Exec) { def classpath = sourceSets.main.output.classesDirs.asPath - commandLine "javah", "-o", "build/native/include/jni_sgx_api.h", "-cp", classpath, "com.r3.enclaves.txverify.NativeSgxApi" + commandLine "javah", "-o", "$buildDir/native/include/jni_sgx_api.h", "-cp", classpath, "com.r3.enclaves.txverify.NativeSgxApi" dependsOn classes } diff --git a/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/Enclavelet.kt b/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/Enclavelet.kt index aa7b785ca9..4167abd734 100644 --- a/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/Enclavelet.kt +++ b/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/Enclavelet.kt @@ -7,6 +7,7 @@ import net.corda.core.contracts.Attachment import net.corda.core.serialization.CordaSerializable import net.corda.core.serialization.SerializedBytes import net.corda.core.serialization.deserialize +import net.corda.core.transactions.LedgerTransaction import net.corda.core.transactions.WireTransaction import java.io.File @@ -14,9 +15,22 @@ import java.io.File /** This is just used to simplify marshalling across the enclave boundary (EDL is a bit awkward) */ @CordaSerializable -class TransactionVerificationRequest(val wtxToVerify: SerializedBytes, - val dependencies: Array>, - val attachments: Array) +class TransactionVerificationRequest(private val wtxToVerify: SerializedBytes, + private val dependencies: Array>, + val attachments: Array) { + fun toLedgerTransaction(): LedgerTransaction { + val deps = dependencies.map { it.deserialize() }.associateBy(WireTransaction::id) + val attachments = attachments.map { it.deserialize() } + val attachmentMap = attachments.associateBy(Attachment::id) + val contractAttachmentMap = attachments.mapNotNull { it as? MockContractAttachment }.associateBy(MockContractAttachment::contract) + return wtxToVerify.deserialize().toLedgerTransaction( + resolveIdentity = { null }, + resolveAttachment = { attachmentMap[it] }, + resolveStateRef = { deps[it.txhash]?.outputs?.get(it.index) }, + resolveContractAttachment = { contractAttachmentMap[it.contract]?.id } + ) + } +} /** * Returns either null to indicate success when the transactions are validated, or a string with the @@ -30,21 +44,26 @@ class TransactionVerificationRequest(val wtxToVerify: SerializedBytes() - val wtxToVerify = req.wtxToVerify.deserialize() - val dependencies = req.dependencies.map { it.deserialize() }.associateBy { it.id } - val attachments = req.attachments.map { it.deserialize() } - val attachmentMap = attachments.associateBy(Attachment::id) - val contractAttachmentMap = attachments.mapNotNull { it as? MockContractAttachment }.associateBy { it.contract } - val ltx = wtxToVerify.toLedgerTransaction( - resolveIdentity = { null }, - resolveAttachment = { attachmentMap[it] }, - resolveStateRef = { dependencies[it.txhash]?.outputs?.get(it.index) }, - resolveContractAttachment = { contractAttachmentMap[it.contract]?.id } - ) + val ltx = deserialise(reqBytes) + // Prevent this thread from linking new classes against any + // blacklisted classes, e.g. ones needed by Kryo or by the + // JVM itself. Note that java.lang.Thread is also blacklisted. + startClassBlacklisting() ltx.verify() } +private fun startClassBlacklisting() { + val systemClassLoader = ClassLoader.getSystemClassLoader() + systemClassLoader.javaClass.getMethod("startBlacklisting").apply { + invoke(systemClassLoader) + } +} + +private fun deserialise(reqBytes: ByteArray): LedgerTransaction { + return reqBytes.deserialize() + .toLedgerTransaction() +} + // Note: This is only here for debugging purposes fun main(args: Array) { Log.TRACE() diff --git a/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/EnclaveletSerializationScheme.kt b/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/EnclaveletSerializationScheme.kt index 82a375dec2..0a447393c9 100644 --- a/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/EnclaveletSerializationScheme.kt +++ b/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/EnclaveletSerializationScheme.kt @@ -5,6 +5,7 @@ import net.corda.core.serialization.SerializationContext import net.corda.core.serialization.internal.SerializationEnvironmentImpl import net.corda.core.serialization.internal.nodeSerializationEnv import net.corda.core.utilities.ByteSequence +import net.corda.core.utilities.toHexString import net.corda.nodeapi.internal.serialization.* import net.corda.nodeapi.internal.serialization.amqp.AbstractAMQPSerializationScheme import net.corda.nodeapi.internal.serialization.amqp.AmqpHeaderV1_0 @@ -29,6 +30,11 @@ private class EnclaveletSerializationScheme { * incoming request received. */ KRYO_P2P_CONTEXT) + + /* + * Ensure that we initialise JAXP before blacklisting is enabled. + */ + ByteArray(0).toHexString() } } } diff --git a/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/NativeSgxApi.kt b/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/NativeSgxApi.kt index c8e83f180d..a74515bb05 100644 --- a/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/NativeSgxApi.kt +++ b/verify-enclave/src/main/kotlin/com/r3/enclaves/txverify/NativeSgxApi.kt @@ -6,5 +6,6 @@ object NativeSgxApi { System.loadLibrary("untrusted_corda_sgx") } + @JvmStatic external fun verify(enclavePath: String, transactionBytes: ByteArray): String? -} \ No newline at end of file +} diff --git a/verify-enclave/src/test/kotlin/com/r3/enclaves/DummySystemClassLoader.kt b/verify-enclave/src/test/kotlin/com/r3/enclaves/DummySystemClassLoader.kt new file mode 100644 index 0000000000..bc3db8109e --- /dev/null +++ b/verify-enclave/src/test/kotlin/com/r3/enclaves/DummySystemClassLoader.kt @@ -0,0 +1,6 @@ +package com.r3.enclaves + +@Suppress("unused") +class DummySystemClassLoader(parent: ClassLoader) : ClassLoader(parent) { + fun startBlacklisting() {} +} diff --git a/verify-enclave/src/test/kotlin/com/r3/enclaves/txverify/EnclaveletTest.kt b/verify-enclave/src/test/kotlin/com/r3/enclaves/txverify/EnclaveletTest.kt index 8461465916..1bd4bfc011 100644 --- a/verify-enclave/src/test/kotlin/com/r3/enclaves/txverify/EnclaveletTest.kt +++ b/verify-enclave/src/test/kotlin/com/r3/enclaves/txverify/EnclaveletTest.kt @@ -7,6 +7,7 @@ import net.corda.finance.`issued by` import net.corda.finance.contracts.asset.Cash import net.corda.finance.contracts.asset.DUMMY_CASH_ISSUER import net.corda.testing.* +import org.junit.Ignore import org.junit.Rule import org.junit.Test import java.nio.file.Files @@ -18,6 +19,8 @@ class EnclaveletTest { @Rule @JvmField val testSerialization = SerializationEnvironmentRule() + + @Ignore("Pending Gradle bug: https://github.com/gradle/gradle/issues/2657") @Test fun success() { ledger { @@ -50,6 +53,7 @@ class EnclaveletTest { } } + @Ignore("Pending Gradle bug: https://github.com/gradle/gradle/issues/2657") @Test fun fail() { ledger {