--- old/make/mapfiles/libjava/mapfile-vers 2018-02-15 14:56:19.000000000 -0800 +++ new/make/mapfiles/libjava/mapfile-vers 2018-02-15 14:56:19.000000000 -0800 @@ -142,7 +142,6 @@ Java_java_lang_StackStreamFactory_checkStackWalkModes; Java_java_lang_StackStreamFactory_00024AbstractStackWalker_callStackWalk; Java_java_lang_StackStreamFactory_00024AbstractStackWalker_fetchStackFrames; - Java_java_lang_Shutdown_runAllFinalizers; Java_java_lang_StrictMath_IEEEremainder; Java_java_lang_StrictMath_acos; Java_java_lang_StrictMath_asin; @@ -203,7 +202,6 @@ Java_java_lang_Runtime_freeMemory; Java_java_lang_Runtime_maxMemory; Java_java_lang_Runtime_gc; - Java_java_lang_Runtime_runFinalization0; Java_java_lang_Runtime_totalMemory; Java_java_lang_Runtime_availableProcessors; Java_java_lang_SecurityManager_getClassContext; --- old/src/hotspot/share/classfile/vmSymbols.hpp 2018-02-15 14:56:20.000000000 -0800 +++ new/src/hotspot/share/classfile/vmSymbols.hpp 2018-02-15 14:56:20.000000000 -0800 @@ -358,7 +358,6 @@ template(reference_lock_name, "lock") \ template(reference_discovered_name, "discovered") \ template(run_finalization_name, "runFinalization") \ - template(run_finalizers_on_exit_name, "runFinalizersOnExit") \ template(dispatchUncaughtException_name, "dispatchUncaughtException") \ template(loadClass_name, "loadClass") \ template(loadClassInternal_name, "loadClassInternal") \ --- old/src/hotspot/share/memory/universe.cpp 2018-02-15 14:56:21.000000000 -0800 +++ new/src/hotspot/share/memory/universe.cpp 2018-02-15 14:56:21.000000000 -0800 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1997, 2018, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -542,32 +542,6 @@ #undef assert_pll_locked #undef assert_pll_ownership - -static bool has_run_finalizers_on_exit = false; - -void Universe::run_finalizers_on_exit() { - if (has_run_finalizers_on_exit) return; - has_run_finalizers_on_exit = true; - - // Called on VM exit. This ought to be run in a separate thread. - log_trace(ref)("Callback to run finalizers on exit"); - { - PRESERVE_EXCEPTION_MARK; - Klass* finalizer_klass = SystemDictionary::Finalizer_klass(); - JavaValue result(T_VOID); - JavaCalls::call_static( - &result, - finalizer_klass, - vmSymbols::run_finalizers_on_exit_name(), - vmSymbols::void_method_signature(), - THREAD - ); - // Ignore any pending exceptions - CLEAR_PENDING_EXCEPTION; - } -} - - // initialize_vtable could cause gc if // 1) we specified true to initialize_vtable and // 2) this ran after gc was enabled --- old/src/hotspot/share/memory/universe.hpp 2018-02-15 14:56:22.000000000 -0800 +++ new/src/hotspot/share/memory/universe.hpp 2018-02-15 14:56:22.000000000 -0800 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1997, 2018, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -464,9 +464,6 @@ static bool should_fill_in_stack_trace(Handle throwable); static void check_alignment(uintx size, uintx alignment, const char* name); - // Finalizer support. - static void run_finalizers_on_exit(); - // Iteration // Apply "f" to the addresses of all the direct heap pointers maintained --- old/src/hotspot/share/runtime/thread.cpp 2018-02-15 14:56:24.000000000 -0800 +++ new/src/hotspot/share/runtime/thread.cpp 2018-02-15 14:56:23.000000000 -0800 @@ -4202,10 +4202,9 @@ // SystemDictionary::resolve_or_null will return null if there was // an exception. If we cannot load the Shutdown class, just don't // call Shutdown.shutdown() at all. This will mean the shutdown hooks - // and finalizers (if runFinalizersOnExit is set) won't be run. - // Note that if a shutdown hook was registered or runFinalizersOnExit + // won't be run. Note that if a shutdown hook was registered // was called, the Shutdown class would have already been loaded - // (Runtime.addShutdownHook and runFinalizersOnExit will load it). + // (Runtime.addShutdownHook will load it). JavaValue result(T_VOID); JavaCalls::call_static(&result, shutdown_klass, --- old/src/java.base/share/classes/java/lang/Runtime.java 2018-02-15 14:56:25.000000000 -0800 +++ new/src/java.base/share/classes/java/lang/Runtime.java 2018-02-15 14:56:25.000000000 -0800 @@ -35,6 +35,8 @@ import java.util.List; import java.util.Optional; import java.util.StringTokenizer; + +import jdk.internal.misc.SharedSecrets; import jdk.internal.reflect.CallerSensitive; import jdk.internal.reflect.Reflection; @@ -77,19 +79,16 @@ * serves as a status code; by convention, a nonzero status code indicates * abnormal termination. * - *

The virtual machine's shutdown sequence consists of two phases. In - * the first phase all registered {@link #addShutdownHook shutdown hooks}, - * if any, are started in some unspecified order and allowed to run - * concurrently until they finish. In the second phase all uninvoked - * finalizers are run if {@link #runFinalizersOnExit finalization-on-exit} - * has been enabled. Once this is done the virtual machine {@link #halt halts}. + *

The virtual machine first invokes all registered + * {@link #addShutdownHook shutdown hooks}, if any, are started in + * some unspecified order and allowed to run concurrently until they finish. + * Once this is done the virtual machine {@link #halt halts}. * *

If this method is invoked after the virtual machine has begun its * shutdown sequence then if shutdown hooks are being run this method will - * block indefinitely. If shutdown hooks have already been run and on-exit - * finalization has been enabled then this method halts the virtual machine - * with the given status code if the status is nonzero; otherwise, it - * blocks indefinitely. + * block indefinitely. If shutdown hooks have already been run + * then this method halts the virtual machine with the given status code + * if the status is nonzero; otherwise, it blocks indefinitely. * *

The {@link System#exit(int) System.exit} method is the * conventional and convenient means of invoking this method. @@ -107,7 +106,6 @@ * @see java.lang.SecurityManager#checkExit(int) * @see #addShutdownHook * @see #removeShutdownHook - * @see #runFinalizersOnExit * @see #halt(int) */ public void exit(int status) { @@ -140,10 +138,9 @@ * thread. When the virtual machine begins its shutdown sequence it will * start all registered shutdown hooks in some unspecified order and let * them run concurrently. When all the hooks have finished it will then - * run all uninvoked finalizers if finalization-on-exit has been enabled. - * Finally, the virtual machine will halt. Note that daemon threads will - * continue to run during the shutdown sequence, as will non-daemon threads - * if shutdown was initiated by invoking the {@link #exit exit} method. + * halt. Note that daemon threads will continue to run during the shutdown + * sequence, as will non-daemon threads if shutdown was initiated by + * invoking the {@link #exit exit} method. * *

Once the shutdown sequence has begun it can be stopped only by * invoking the {@link #halt halt} method, which forcibly @@ -253,10 +250,9 @@ * *

This method should be used with extreme caution. Unlike the * {@link #exit exit} method, this method does not cause shutdown - * hooks to be started and does not run uninvoked finalizers if - * finalization-on-exit has been enabled. If the shutdown sequence has - * already been initiated then this method does not wait for any running - * shutdown hooks or finalizers to finish their work. + * hooks to be started. If the shutdown sequence has already been + * initiated then this method does not wait for any running + * shutdown hooks to finish their work. * * @param status * Termination status. By convention, a nonzero status code @@ -284,46 +280,6 @@ } /** - * Enable or disable finalization on exit; doing so specifies that the - * finalizers of all objects that have finalizers that have not yet been - * automatically invoked are to be run before the Java runtime exits. - * By default, finalization on exit is disabled. - * - *

If there is a security manager, - * its {@code checkExit} method is first called - * with 0 as its argument to ensure the exit is allowed. - * This could result in a SecurityException. - * - * @param value true to enable finalization on exit, false to disable - * @deprecated This method is inherently unsafe. It may result in - * finalizers being called on live objects while other threads are - * concurrently manipulating those objects, resulting in erratic - * behavior or deadlock. - * This method is subject to removal in a future version of Java SE. - * - * @throws SecurityException - * if a security manager exists and its {@code checkExit} - * method doesn't allow the exit. - * - * @see java.lang.Runtime#exit(int) - * @see java.lang.Runtime#gc() - * @see java.lang.SecurityManager#checkExit(int) - * @since 1.1 - */ - @Deprecated(since="1.2", forRemoval=true) - public static void runFinalizersOnExit(boolean value) { - SecurityManager security = System.getSecurityManager(); - if (security != null) { - try { - security.checkExit(0); - } catch (SecurityException e) { - throw new SecurityException("runFinalizersOnExit"); - } - } - Shutdown.setRunFinalizersOnExit(value); - } - - /** * Executes the specified string command in a separate process. * *

This is a convenience method. An invocation of the form @@ -702,9 +658,6 @@ */ public native void gc(); - /* Wormhole for calling java.lang.ref.Finalizer.runFinalization */ - private static native void runFinalization0(); - /** * Runs the finalization methods of any objects pending finalization. * Calling this method suggests that the Java virtual machine expend @@ -724,7 +677,7 @@ * @see java.lang.Object#finalize() */ public void runFinalization() { - runFinalization0(); + SharedSecrets.getJavaLangRefAccess().runFinalization(); } /** --- old/src/java.base/share/classes/java/lang/Shutdown.java 2018-02-15 14:56:26.000000000 -0800 +++ new/src/java.base/share/classes/java/lang/Shutdown.java 2018-02-15 14:56:26.000000000 -0800 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1999, 2005, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1999, 2018, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -39,12 +39,9 @@ /* Shutdown state */ private static final int RUNNING = 0; private static final int HOOKS = 1; - private static final int FINALIZERS = 2; + private static final int COMPLETED = 2; private static int state = RUNNING; - /* Should we run all finalizers upon exit? */ - private static boolean runFinalizersOnExit = false; - // The system shutdown hooks are registered with a predefined slot. // The list of shutdown hooks is as follows: // (0) Console restore hook @@ -63,14 +60,6 @@ /* Lock object for the native halt method */ private static Object haltLock = new Lock(); - /* Invoked by Runtime.runFinalizersOnExit */ - static void setRunFinalizersOnExit(boolean run) { - synchronized (lock) { - runFinalizersOnExit = run; - } - } - - /** * Add a new shutdown hook. Checks the shutdown state and the hook itself, * but does not do any security checks. @@ -111,6 +100,13 @@ /* Run all registered shutdown hooks */ private static void runHooks() { + synchronized (lock) { + /* Guard against the possibility of a daemon thread invoking exit + * after DestroyJavaVM initiates the shutdown sequence + */ + if (state != HOOKS) return; + } + for (int i=0; i < MAX_SYSTEM_HOOKS; i++) { try { Runnable hook; @@ -128,6 +124,10 @@ } } } + + synchronized (lock) { + state = COMPLETED; + } } /* The halt method is synchronized on the halt lock @@ -142,74 +142,31 @@ static native void halt0(int status); - /* Wormhole for invoking java.lang.ref.Finalizer.runAllFinalizers */ - private static native void runAllFinalizers(); - - - /* The actual shutdown sequence is defined here. - * - * If it weren't for runFinalizersOnExit, this would be simple -- we'd just - * run the hooks and then halt. Instead we need to keep track of whether - * we're running hooks or finalizers. In the latter case a finalizer could - * invoke exit(1) to cause immediate termination, while in the former case - * any further invocations of exit(n), for any n, simply stall. Note that - * if on-exit finalizers are enabled they're run iff the shutdown is - * initiated by an exit(0); they're never run on exit(n) for n != 0 or in - * response to SIGINT, SIGTERM, etc. - */ - private static void sequence() { - synchronized (lock) { - /* Guard against the possibility of a daemon thread invoking exit - * after DestroyJavaVM initiates the shutdown sequence - */ - if (state != HOOKS) return; - } - runHooks(); - boolean rfoe; - synchronized (lock) { - state = FINALIZERS; - rfoe = runFinalizersOnExit; - } - if (rfoe) runAllFinalizers(); - } - - /* Invoked by Runtime.exit, which does all the security checks. * Also invoked by handlers for system-provided termination events, * which should pass a nonzero status code. */ static void exit(int status) { - boolean runMoreFinalizers = false; synchronized (lock) { - if (status != 0) runFinalizersOnExit = false; switch (state) { case RUNNING: /* Initiate shutdown */ state = HOOKS; break; case HOOKS: /* Stall and halt */ break; - case FINALIZERS: + case COMPLETED: if (status != 0) { /* Halt immediately on nonzero status */ halt(status); - } else { - /* Compatibility with old behavior: - * Run more finalizers and then halt - */ - runMoreFinalizers = runFinalizersOnExit; } break; } } - if (runMoreFinalizers) { - runAllFinalizers(); - halt(status); - } synchronized (Shutdown.class) { /* Synchronize on the class object, causing any other thread * that attempts to initiate shutdown to stall indefinitely */ - sequence(); + runHooks(); halt(status); } } @@ -226,12 +183,13 @@ state = HOOKS; break; case HOOKS: /* Stall and then return */ - case FINALIZERS: break; + case COMPLETED: + return; } } synchronized (Shutdown.class) { - sequence(); + runHooks(); } } --- old/src/java.base/share/classes/java/lang/System.java 2018-02-15 14:56:28.000000000 -0800 +++ new/src/java.base/share/classes/java/lang/System.java 2018-02-15 14:56:27.000000000 -0800 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1994, 2017, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1994, 2018, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -1766,38 +1766,6 @@ } /** - * Enable or disable finalization on exit; doing so specifies that the - * finalizers of all objects that have finalizers that have not yet been - * automatically invoked are to be run before the Java runtime exits. - * By default, finalization on exit is disabled. - * - *

If there is a security manager, - * its checkExit method is first called - * with 0 as its argument to ensure the exit is allowed. - * This could result in a SecurityException. - * - * @deprecated This method is inherently unsafe. It may result in - * finalizers being called on live objects while other threads are - * concurrently manipulating those objects, resulting in erratic - * behavior or deadlock. - * This method is subject to removal in a future version of Java SE. - * @param value indicating enabling or disabling of finalization - * @throws SecurityException - * if a security manager exists and its checkExit - * method doesn't allow the exit. - * - * @see java.lang.Runtime#exit(int) - * @see java.lang.Runtime#gc() - * @see java.lang.SecurityManager#checkExit(int) - * @since 1.1 - */ - @Deprecated(since="1.2", forRemoval=true) - @SuppressWarnings("removal") - public static void runFinalizersOnExit(boolean value) { - Runtime.runFinalizersOnExit(value); - } - - /** * Loads the native library specified by the filename argument. The filename * argument must be an absolute path name. * --- old/src/java.base/share/classes/java/lang/doc-files/threadPrimitiveDeprecation.html 2018-02-15 14:56:29.000000000 -0800 +++ new/src/java.base/share/classes/java/lang/doc-files/threadPrimitiveDeprecation.html 2018-02-15 14:56:29.000000000 -0800 @@ -1,6 +1,6 @@

--- old/src/java.base/share/classes/java/lang/ref/Finalizer.java 2018-02-15 14:56:30.000000000 -0800 +++ new/src/java.base/share/classes/java/lang/ref/Finalizer.java 2018-02-15 14:56:30.000000000 -0800 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1997, 2018, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -60,11 +60,7 @@ private void remove() { synchronized (lock) { if (unfinalized == this) { - if (this.next != null) { - unfinalized = this.next; - } else { - unfinalized = this.prev; - } + unfinalized = this.next; } if (this.next != null) { this.next.prev = this.prev; @@ -112,7 +108,7 @@ /* Create a privileged secondary finalizer thread in the system thread group for the given Runnable, and wait for it to complete. - This method is used by both runFinalization and runFinalizersOnExit. + This method is used by both runFinalization. The former method invokes all pending finalizers, while the latter invokes all uninvoked finalizers if on-exit finalization has been enabled. @@ -164,31 +160,6 @@ }); } - /* Invoked by java.lang.Shutdown */ - static void runAllFinalizers() { - if (VM.initLevel() == 0) { - return; - } - - forkSecondaryFinalizer(new Runnable() { - private volatile boolean running; - public void run() { - // in case of recursive call to run() - if (running) - return; - final JavaLangAccess jla = SharedSecrets.getJavaLangAccess(); - running = true; - for (;;) { - Finalizer f; - synchronized (lock) { - f = unfinalized; - if (f == null) break; - unfinalized = f.next; - } - f.runFinalizer(jla); - }}}); - } - private static class FinalizerThread extends Thread { private volatile boolean running; FinalizerThread(ThreadGroup g) { --- old/src/java.base/share/classes/java/lang/ref/Reference.java 2018-02-15 14:56:32.000000000 -0800 +++ new/src/java.base/share/classes/java/lang/ref/Reference.java 2018-02-15 14:56:32.000000000 -0800 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1997, 2018, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -235,6 +235,11 @@ { return Reference.waitForReferenceProcessing(); } + + @Override + public void runFinalization() { + Finalizer.runFinalization(); + } }); } --- old/src/java.base/share/classes/jdk/internal/misc/JavaLangRefAccess.java 2018-02-15 14:56:33.000000000 -0800 +++ new/src/java.base/share/classes/jdk/internal/misc/JavaLangRefAccess.java 2018-02-15 14:56:33.000000000 -0800 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2014, 2018, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -36,4 +36,11 @@ * {@link java.lang.ref.Reference}s, {@code false} otherwise. */ boolean waitForReferenceProcessing() throws InterruptedException; + + /** + * Runs the finalization methods of any objects pending finalization. + * + * Invoked by Runtime.runFinalization() + */ + void runFinalization(); } --- old/src/java.base/share/native/libjava/Runtime.c 2018-02-15 14:56:34.000000000 -0800 +++ new/src/java.base/share/native/libjava/Runtime.c 2018-02-15 14:56:34.000000000 -0800 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1994, 2014, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1994, 2018, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -65,19 +65,6 @@ JVM_GC(); } -JNIEXPORT void JNICALL -Java_java_lang_Runtime_runFinalization0(JNIEnv *env, jobject this) -{ - jclass cl; - jmethodID mid; - - if ((cl = (*env)->FindClass(env, "java/lang/ref/Finalizer")) - && (mid = (*env)->GetStaticMethodID(env, cl, - "runFinalization", "()V"))) { - (*env)->CallStaticVoidMethod(env, cl, mid); - } -} - JNIEXPORT jint JNICALL Java_java_lang_Runtime_availableProcessors(JNIEnv *env, jobject this) { --- old/src/java.base/share/native/libjava/Shutdown.c 2018-02-15 14:56:35.000000000 -0800 +++ new/src/java.base/share/native/libjava/Shutdown.c 2018-02-15 14:56:35.000000000 -0800 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1999, 2003, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1999, 2018, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -35,17 +35,3 @@ { JVM_Halt(code); } - - -JNIEXPORT void JNICALL -Java_java_lang_Shutdown_runAllFinalizers(JNIEnv *env, jclass ignored) -{ - jclass cl; - jmethodID mid; - - if ((cl = (*env)->FindClass(env, "java/lang/ref/Finalizer")) - && (mid = (*env)->GetStaticMethodID(env, cl, - "runAllFinalizers", "()V"))) { - (*env)->CallStaticVoidMethod(env, cl, mid); - } -} --- old/src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/Main.java 2018-02-15 14:56:37.000000000 -0800 +++ new/src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/Main.java 2018-02-15 14:56:36.000000000 -0800 @@ -80,8 +80,8 @@ * - handling of covariant overrides * - handling of override of method found in multiple superinterfaces * - convert type/method/field output to Java source like syntax, e.g. - * instead of java/lang/Runtime.runFinalizersOnExit(Z)V - * print void java.lang.Runtime.runFinalizersOnExit(boolean) + * instead of java/lang/Character.isJavaLetter(C)Z + * print void java.lang.Character.isJavaLetter(char)boolean * - more example output in man page * - more rigorous GNU style option parsing; use joptsimple? * --- old/src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/internals.md 2018-02-15 14:56:38.000000000 -0800 +++ new/src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/internals.md 2018-02-15 14:56:38.000000000 -0800 @@ -195,15 +195,14 @@ **EXAMPLE OUTPUT** Given the following method declaration and annotation from the -`java.lang.Runtime` class, +`java.lang.Character` class, - @Deprecated(since="1.2", - forRemoval=true) - public static void runFinalizersOnExit(boolean value) + @Deprecated(since="1.1") + public static boolean isJavaLetter(char ch) the following line will be emitted from **jdeprscan -Xprint-csv**: - METHOD,java/lang/Runtime,runFinalizersOnExit(Z)V,1.2,true + METHOD,java/lang/Character,isJavaLetter(C)Z,1.1,false [RFC]: https://www.ietf.org/rfc/rfc4180.txt --- old/src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/readme.md 2018-02-15 14:56:39.000000000 -0800 +++ new/src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/readme.md 2018-02-15 14:56:39.000000000 -0800 @@ -1,6 +1,6 @@