Path: blob/master/test/jdk/java/net/ServerSocket/AcceptCauseFileDescriptorLeak.java
41152 views
/*1* Copyright (c) 2006, 2019, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation.7*8* This code is distributed in the hope that it will be useful, but WITHOUT9* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or10* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License11* version 2 for more details (a copy is included in the LICENSE file that12* accompanied this code).13*14* You should have received a copy of the GNU General Public License version15* 2 along with this work; if not, write to the Free Software Foundation,16* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.17*18* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA19* or visit www.oracle.com if you need additional information or have any20* questions.21*/2223/*24* author Edward Wang25*26* @test27* @bug 636898428* @key intermittent29* @summary Configuring unconnected Socket before passing to implAccept30* can cause fd leak.31* This test may fail intermittently if foreign processes will32* try to establish connection to the test server socket.33* @requires (os.family != "windows")34* @library /test/lib35* @build jdk.test.lib.Utils36* jdk.test.lib.Asserts37* jdk.test.lib.JDKToolFinder38* jdk.test.lib.JDKToolLauncher39* jdk.test.lib.Platform40* jdk.test.lib.process.*41* AcceptCauseFileDescriptorLeak42* @run main/othervm AcceptCauseFileDescriptorLeak root43* @run main/othervm -Djdk.net.usePlainSocketImpl AcceptCauseFileDescriptorLeak root44*/4546import java.io.IOException;47import java.net.InetAddress;48import java.net.InetSocketAddress;49import java.net.ServerSocket;50import java.net.Socket;51import java.util.List;5253import jdk.test.lib.JDKToolFinder;54import jdk.test.lib.process.OutputAnalyzer;5556public class AcceptCauseFileDescriptorLeak {57private static final int REPS = 2048;58private static final int THRESHOLD = 1024;5960public static void main(String[] args) throws Exception {61if (args.length != 0) {62OutputAnalyzer analyzer = execCmd("ulimit -n -H");63String output = analyzer.getOutput();64if (output == null || output.length() == 0) {65throw new RuntimeException("\"ulimit -n -H\" output nothing"66+ " and its exit code is " + analyzer.getExitValue());67} else {68output = output.trim();69// Set max open file descriptors to 102470// if it is unlimited or greater than 1024,71// otherwise just do test directly72if ("unlimited".equals(output)73|| Integer.valueOf(output) > THRESHOLD) {74analyzer = execCmd("ulimit -n " + THRESHOLD + "; "75+ composeJavaTestStr());76System.out.println("Output: ["77+ analyzer.getOutput() + "]");78int rc = analyzer.getExitValue();79if (rc != 0) {80throw new RuntimeException(81"Unexpected exit code: " + rc);82}83return;84}85}86}8788final ServerSocket ss = new ServerSocket() {89public Socket accept() throws IOException {90Socket s = new Socket() {91};92s.setSoTimeout(10000);93implAccept(s);94return s;95}96};97ss.bind(new InetSocketAddress(InetAddress.getLoopbackAddress(), 0));98Thread t = new Thread(new Runnable() {99public void run() {100int repsCompleted = 0;101try {102for (; repsCompleted < REPS; repsCompleted++) {103(new Socket(InetAddress.getLoopbackAddress(), ss.getLocalPort())).close();104}105} catch (IOException e) {106e.printStackTrace();107} finally {108System.out.println("Client iterations completed:" + repsCompleted);109}110}111});112t.start();113int repsCompleted = 0;114try {115for (; repsCompleted < REPS; repsCompleted++) {116ss.accept().close();117}118} finally {119System.out.println("Server iterations completed:" + repsCompleted);120ss.close();121}122t.join();123}124125/**126* Execute command with shell127*128* @param command129* @return OutputAnalyzer130* @throws IOException131*/132static OutputAnalyzer execCmd(String command) throws IOException {133List<String> cmd = List.of("sh", "-c", command);134System.out.println("Executing: " + cmd);135ProcessBuilder pb = new ProcessBuilder(cmd);136return new OutputAnalyzer(pb.start());137}138139static String composeJavaTestStr() {140return JDKToolFinder.getTestJDKTool("java") + " "141+ AcceptCauseFileDescriptorLeak.class.getName();142}143}144145146147