Enable uptake by Avatar.

This commit is contained in:
Bryan Atsatt 2014-01-31 10:28:49 -08:00
parent ff8e42b472
commit edf0d64020
4 changed files with 129 additions and 130 deletions

View File

@ -1,26 +1,27 @@
/*
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
* Copyright (c) 2013-2014 Oracle and/or its affiliates. All rights reserved.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
* The contents of this file are subject to the terms of the GNU General
* Public License Version 2 only ("GPL"). You may not use this file except
* in compliance with the License. You can obtain a copy of the License at
* https://avatar.java.net/license.html or legal/LICENSE.txt. See the
* License for the specific language governing permissions and limitations
* under the License.
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
* When distributing the software, include this License Header Notice in each
* file and include the License file at legal/LICENSE.txt.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
* GPL Classpath Exception:
* Oracle designates this particular file as subject to the "Classpath"
* exception as provided by Oracle in the GPL Version 2 section of the License
* file that accompanied this code.
*
* Modifications:
* If applicable, add the following below the License Header, with the fields
* enclosed by brackets [] replaced by your own identifying information:
* "Portions Copyright [year] [name of copyright owner]"
*/
package com.oracle.avatar.js;
@ -34,7 +35,6 @@ import java.security.AccessControlContext;
import java.security.AccessController;
import java.util.ArrayList;
import java.util.List;
import javax.script.Bindings;
import javax.script.Compilable;
import javax.script.CompiledScript;
@ -48,9 +48,7 @@ import com.oracle.avatar.js.eventloop.EventLoop;
import com.oracle.avatar.js.eventloop.ThreadPool;
import com.oracle.avatar.js.log.Logger;
import com.oracle.avatar.js.log.Logging;
import com.oracle.libuv.LibUV;
import jdk.nashorn.api.scripting.URLReader;
/**
@ -127,7 +125,7 @@ public final class Server {
final Loader loader,
final Logging logging,
final String workDir) throws Exception {
this(engine, loader, logging, workDir, engine.getContext(), 0, ThreadPool.getInstance());
this(engine, loader, logging, workDir, engine.getContext(), 0, ThreadPool.getInstance(), false);
}
public Server(final ScriptEngine engine,
@ -136,7 +134,8 @@ public final class Server {
final String workDir,
final ScriptContext context,
final int instanceNumber,
final ThreadPool threadPool) {
final ThreadPool executor,
final boolean sharedExecutor) throws Exception {
this.engine = engine;
this.context = context;
this.bindings = context.getBindings(ScriptContext.ENGINE_SCOPE);
@ -146,7 +145,7 @@ public final class Server {
assert version != null;
uvVersion = loader.getBuildProperty(LIBUV_VERSION_BUILD_PROPERTY);
assert uvVersion != null;
this.eventLoop = new EventLoop(version, uvVersion, logging, workDir, instanceNumber, threadPool);
this.eventLoop = new EventLoop(version, uvVersion, logging, workDir, instanceNumber, executor, sharedExecutor);
this.holder = new SecureHolder(eventLoop, loader, (Invocable) engine);
}
@ -183,11 +182,12 @@ public final class Server {
eventLoop.stop();
}
private void runSystemScript(final SystemScriptRunner... scripts)
throws FileNotFoundException, ScriptException {
for (final SystemScriptRunner scriptRunner : scripts) {
log.log("loading system script " + scriptRunner.script);
scriptRunner.run(context);
private void runSystemScript(final SystemScriptRunner... scripts) throws FileNotFoundException, ScriptException {
if (!eventLoop.stopped()) {
for (final SystemScriptRunner scriptRunner : scripts) {
log.log("loading system script " + scriptRunner.script);
scriptRunner.run(context);
}
}
}

View File

@ -1,26 +1,27 @@
/*
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
* Copyright (c) 2013-2014 Oracle and/or its affiliates. All rights reserved.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
* The contents of this file are subject to the terms of the GNU General
* Public License Version 2 only ("GPL"). You may not use this file except
* in compliance with the License. You can obtain a copy of the License at
* https://avatar.java.net/license.html or legal/LICENSE.txt. See the
* License for the specific language governing permissions and limitations
* under the License.
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
* When distributing the software, include this License Header Notice in each
* file and include the License file at legal/LICENSE.txt.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
* GPL Classpath Exception:
* Oracle designates this particular file as subject to the "Classpath"
* exception as provided by Oracle in the GPL Version 2 section of the License
* file that accompanied this code.
*
* Modifications:
* If applicable, add the following below the License Header, with the fields
* enclosed by brackets [] replaced by your own identifying information:
* "Portions Copyright [year] [name of copyright owner]"
*/
package com.oracle.avatar.js;
@ -41,7 +42,7 @@ import java.net.URLStreamHandler;
* <li>avatar:jar:file:{path to script file inside jar file}</li>
* </ul>
*/
final class WrappingStreamHandler extends URLStreamHandler {
public class WrappingStreamHandler extends URLStreamHandler {
private static final class ContentWrapper {

View File

@ -1,26 +1,27 @@
/*
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
* Copyright (c) 2013-2014 Oracle and/or its affiliates. All rights reserved.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
* The contents of this file are subject to the terms of the GNU General
* Public License Version 2 only ("GPL"). You may not use this file except
* in compliance with the License. You can obtain a copy of the License at
* https://avatar.java.net/license.html or legal/LICENSE.txt. See the
* License for the specific language governing permissions and limitations
* under the License.
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
* When distributing the software, include this License Header Notice in each
* file and include the License file at legal/LICENSE.txt.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
* GPL Classpath Exception:
* Oracle designates this particular file as subject to the "Classpath"
* exception as provided by Oracle in the GPL Version 2 section of the License
* file that accompanied this code.
*
* Modifications:
* If applicable, add the following below the License Header, with the fields
* enclosed by brackets [] replaced by your own identifying information:
* "Portions Copyright [year] [name of copyright owner]"
*/
package com.oracle.avatar.js.eventloop;
@ -35,24 +36,25 @@ import java.util.Map;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.Future;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.atomic.AtomicInteger;
import javax.script.ScriptException;
import jdk.nashorn.api.scripting.NashornException;
import jdk.nashorn.internal.runtime.ECMAException;
import jdk.nashorn.internal.runtime.ScriptObject;
import jdk.nashorn.api.scripting.ScriptObjectMirror;
import com.oracle.avatar.js.dns.DNS;
import com.oracle.avatar.js.log.Logger;
import com.oracle.avatar.js.log.Logging;
import com.oracle.libuv.LibUV;
import com.oracle.libuv.cb.AsyncCallback;
import com.oracle.libuv.cb.CallbackExceptionHandler;
import com.oracle.libuv.cb.ContextProvider;
import com.oracle.libuv.cb.CallbackHandler;
import com.oracle.libuv.cb.CallbackHandlerFactory;
import com.oracle.libuv.cb.ContextProvider;
import com.oracle.libuv.handles.AsyncHandle;
import com.oracle.libuv.handles.LoopHandle;
import jdk.nashorn.api.scripting.NashornException;
import jdk.nashorn.api.scripting.ScriptObjectMirror;
import jdk.nashorn.internal.runtime.ECMAException;
import jdk.nashorn.internal.runtime.ScriptObject;
public final class EventLoop {
@ -69,6 +71,8 @@ public final class EventLoop {
private final AsyncHandle asyncHandle;
private final AsyncHandle interruptMainLoopHandle;
private final Thread mainThread;
private final boolean sharedExecutor;
private final AtomicBoolean stopped = new AtomicBoolean(false);
private Callback isHandlerRegistered = null;
private Callback uncaughtExceptionHandler = null;
@ -115,7 +119,6 @@ public final class EventLoop {
}
public void nextTick(final Callback cb) {
assert Thread.currentThread() == mainThread : "called from non-event thread " + Thread.currentThread().getName();
eventQueue.add(new Event("nextTick", cb));
}
@ -209,14 +212,24 @@ public final class EventLoop {
}
public void stop() {
executor.shutdown();
asyncHandle.close();
uvLoop.stop();
if (stopped.compareAndSet(false, true)) {
if (!sharedExecutor) {
executor.shutdown();
}
asyncHandle.close();
uvLoop.stop();
}
}
public void release() {
hooks.set(0);
executor.clearQueuedTasks();
if (!sharedExecutor) {
executor.clearQueuedTasks();
}
}
public boolean stopped() {
return stopped.get();
}
// filename, line, column, name, message
@ -358,7 +371,8 @@ public final class EventLoop {
final Logging logging,
final String workDir,
final int instanceNumber,
final ThreadPool executor) {
final ThreadPool executor,
final boolean sharedExecutor) throws IOException {
mainThread = Thread.currentThread();
final String uv = LibUV.version();
if (!uvVersion.equals(uv)) {
@ -410,6 +424,7 @@ public final class EventLoop {
this.instanceNumber = instanceNumber;
this.executor = executor;
this.sharedExecutor = sharedExecutor;
LibUV.chdir(workDir);
LOG = logger("eventloop");

View File

@ -1,65 +1,45 @@
/*
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
* Copyright (c) 2013-2014 Oracle and/or its affiliates. All rights reserved.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
* The contents of this file are subject to the terms of the GNU General
* Public License Version 2 only ("GPL"). You may not use this file except
* in compliance with the License. You can obtain a copy of the License at
* https://avatar.java.net/license.html or legal/LICENSE.txt. See the
* License for the specific language governing permissions and limitations
* under the License.
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
* When distributing the software, include this License Header Notice in each
* file and include the License file at legal/LICENSE.txt.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
* GPL Classpath Exception:
* Oracle designates this particular file as subject to the "Classpath"
* exception as provided by Oracle in the GPL Version 2 section of the License
* file that accompanied this code.
*
* Modifications:
* If applicable, add the following below the License Header, with the fields
* enclosed by brackets [] replaced by your own identifying information:
* "Portions Copyright [year] [name of copyright owner]"
*/
package com.oracle.avatar.js.log;
import java.io.File;
import java.io.IOException;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.atomic.AtomicInteger;
import com.oracle.avatar.js.eventloop.DaemonThreadFactory;
public final class Logging {
private final BlockingQueue<LogEvent> logQueue = new LinkedBlockingQueue<>();
private final ThreadFactory logThreadFactory = new DaemonThreadFactory("avatar-js.log");
private final AtomicBoolean logThreadStarted = new AtomicBoolean(false);
private final Thread logThread = logThreadFactory.newThread(new Runnable() {
@Override
public void run() {
while (true) {
try {
logQueue.take().write();
} catch (final IOException | InterruptedException ignore) {
return;
}
}
}
});
// each logger instance within a category is given a unique id
private final ConcurrentHashMap<String, AtomicInteger> NEXT_ID = new ConcurrentHashMap<>();
private final LogQueue queue;
private final boolean sharedQueue;
private final File logDirectory;
private volatile boolean enabled;
@ -99,20 +79,17 @@ public final class Logging {
}
};
void log(final LogEvent event) {
logQueue.add(event);
// start log thread lazily on the very first log event
if (logThreadStarted.compareAndSet(false, true)) {
logThread.start();
}
}
public Logging(final boolean enabled) {
this(null, enabled);
}
public Logging(final File logDirectory, final boolean enabled) {
this(new LogQueue(), false, logDirectory, enabled);
}
public Logging(final LogQueue queue, final boolean sharedQueue, final File logDirectory, final boolean enabled) {
this.queue = queue;
this.sharedQueue = sharedQueue;
if (logDirectory != null && logDirectory.exists() && logDirectory.isDirectory()) {
this.logDirectory = logDirectory;
} else {
@ -147,8 +124,14 @@ public final class Logging {
return defaultLogger;
}
public void log(final LogEvent event) {
queue.log(event);
}
public void shutdown() {
logThread.interrupt();
if (!sharedQueue) {
queue.shutdown();
}
}
private Logger create(final String name) {