RunToExit.java revision 11884:b45c81ca8671
1/*
2 * Copyright (c) 2004, 2015, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 */
23
24/* @test
25 * @bug 4997445
26 * @summary Test that with server=y, when VM runs to System.exit() no error happens
27 * @library /lib/testlibrary
28 * @modules java.management
29 *          jdk.jdi
30 * @build jdk.testlibrary.* VMConnection RunToExit Exit0
31 * @run driver RunToExit
32 */
33import java.net.ServerSocket;
34import com.sun.jdi.Bootstrap;
35import com.sun.jdi.VirtualMachine;
36import com.sun.jdi.event.*;
37import com.sun.jdi.connect.Connector;
38import com.sun.jdi.connect.AttachingConnector;
39import java.net.ConnectException;
40import java.util.Map;
41import java.util.List;
42import java.util.Iterator;
43import java.util.concurrent.TimeUnit;
44import java.util.stream.Collectors;
45import jdk.testlibrary.ProcessTools;
46
47public class RunToExit {
48
49    /* Increment this when ERROR: seen */
50    static volatile int error_seen = 0;
51    static volatile boolean ready = false;
52
53    /*
54     * Find a connector by name
55     */
56    private static Connector findConnector(String name) {
57        List connectors = Bootstrap.virtualMachineManager().allConnectors();
58        Iterator iter = connectors.iterator();
59        while (iter.hasNext()) {
60            Connector connector = (Connector)iter.next();
61            if (connector.name().equals(name)) {
62                return connector;
63            }
64        }
65        return null;
66    }
67
68    /*
69     * Launch a server debuggee with the given address
70     */
71    private static Process launch(String address, String class_name) throws Exception {
72        String args[] = new String[]{
73            "-agentlib:jdwp=transport=dt_socket,server=y,suspend=y,address="
74                + address,
75            class_name
76        };
77        args = VMConnection.insertDebuggeeVMOptions(args);
78
79        ProcessBuilder launcher = ProcessTools.createJavaProcessBuilder(args);
80
81        System.out.println(launcher.command().stream().collect(Collectors.joining(" ", "Starting: ", "")));
82
83        Process p = ProcessTools.startProcess(
84            class_name,
85            launcher,
86            RunToExit::checkForError,
87            RunToExit::isTransportListening,
88            0,
89            TimeUnit.NANOSECONDS
90        );
91
92        return p;
93    }
94
95    private static boolean isTransportListening(String line) {
96        return line.startsWith("Listening for transport dt_socket");
97    }
98
99    private static void checkForError(String line) {
100        if (line.contains("ERROR:")) {
101            error_seen++;
102        }
103    }
104
105    /*
106     * - pick a TCP port
107     * - Launch a server debuggee: server=y,suspend=y,address=${port}
108     * - run it to VM death
109     * - verify we saw no error
110     */
111    public static void main(String args[]) throws Exception {
112        // find a free port
113        ServerSocket ss = new ServerSocket(0);
114        int port = ss.getLocalPort();
115        ss.close();
116
117        String address = String.valueOf(port);
118
119        // launch the server debuggee
120        Process process = launch(address, "Exit0");
121
122        // attach to server debuggee and resume it so it can exit
123        AttachingConnector conn = (AttachingConnector)findConnector("com.sun.jdi.SocketAttach");
124        Map conn_args = conn.defaultArguments();
125        Connector.IntegerArgument port_arg =
126            (Connector.IntegerArgument)conn_args.get("port");
127        port_arg.setValue(port);
128
129        System.out.println("Connection arguments: " + conn_args);
130
131        VirtualMachine vm = null;
132        while (vm == null) {
133            try {
134                vm = conn.attach(conn_args);
135            } catch (ConnectException e) {
136                e.printStackTrace(System.out);
137                System.out.println("--- Debugee not ready. Retrying in 500ms. ---");
138                Thread.sleep(500);
139            }
140        }
141
142        // The first event is always a VMStartEvent, and it is always in
143        // an EventSet by itself.  Wait for it.
144        EventSet evtSet = vm.eventQueue().remove();
145        for (Event event: evtSet) {
146            if (event instanceof VMStartEvent) {
147                break;
148            }
149            throw new RuntimeException("Test failed - debuggee did not start properly");
150        }
151        vm.eventRequestManager().deleteAllBreakpoints();
152        vm.resume();
153
154        int exitCode = process.waitFor();
155
156        // if the server debuggee ran cleanly, we assume we were clean
157        if (exitCode == 0 && error_seen == 0) {
158            System.out.println("Test passed - server debuggee cleanly terminated");
159        } else {
160            throw new RuntimeException("Test failed - server debuggee generated an error when it terminated, " +
161                "exit code was " + exitCode + ", " + error_seen + " error(s) seen in debugee output.");
162        }
163    }
164}
165