This commit is contained in:
Phil Race 2017-09-28 09:13:27 -07:00
commit 1c89e3aa56
390 changed files with 7435 additions and 10519 deletions

View file

@ -273,7 +273,7 @@ BUNDLE_UP_AND_EXIT = \
prep:
@$(MKDIR) -p $(ABS_TEST_OUTPUT_DIR)
@$(MKDIR) -p `$(DIRNAME) $(ARCHIVE_BUNDLE)`
@if [ ! -d $(TEST_ROOT)/../.hg ] ; then \
@if [ ! -d $(TEST_ROOT)/../../.hg ] && [ ! -d $(TEST_ROOT)/../../../.hg ]; then \
$(FIND) $(TEST_ROOT) \( -name \*.dll -o -name \*.DLL -o -name \*.so \) \
-exec $(CHMOD) a+rx {} \; ; \
fi

View file

@ -0,0 +1,68 @@
/*
* Copyright (c) 2017, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* 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).
*
* 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.
*
* 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.
*/
/**
* @test Testexecstack.java
* @summary Searches for all libraries in test VM and checks that they
* have the noexecstack bit set.
* @requires (os.family == "linux")
* @library /test/lib
* @modules java.base/jdk.internal.misc
* @build sun.hotspot.WhiteBox
* @run driver ClassFileInstaller sun.hotspot.WhiteBox
* sun.hotspot.WhiteBox$WhiteBoxPermission
* @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI
* TestCheckJDK
*/
import jdk.test.lib.Asserts;
import sun.hotspot.WhiteBox;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
public class TestCheckJDK {
static boolean testPassed = true;
private static final WhiteBox WB = WhiteBox.getWhiteBox();
static void checkExecStack(Path file) {
String filename = file.toString();
if (filename.endsWith(".so")) {
if (!WB.checkLibSpecifiesNoexecstack(filename)) {
System.out.println("Library does not have the noexecstack bit set: " + filename);
testPassed = false;
}
}
}
public static void main(String[] args) throws Throwable {
String vmInstallDir = System.getProperty("java.home");
Files.walk(Paths.get(vmInstallDir)).filter(Files::isRegularFile).forEach(TestCheckJDK::checkExecStack);
Asserts.assertTrue(testPassed,
"The tested VM contains libs that don't have the noexecstack " +
"bit set. They must be linked with -z,noexecstack.");
}
}

View file

@ -468,7 +468,6 @@ needs_jdk = \
com/sun/tools \
jdk/security/jarsigner \
sun/security/tools/jarsigner \
sun/security/tools/policytool \
sun/rmi/rmic \
sun/tools \
sun/jvmstat \
@ -785,8 +784,7 @@ compact1_minimal = \
-:needs_jdk
needs_headful = \
java/util/TimeZone/DefaultTimeZoneTest.java \
sun/security/tools/policytool
java/util/TimeZone/DefaultTimeZoneTest.java
needs_locales = \
-:needs_locales_and_charsets \

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 1999, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 2017, 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
@ -26,19 +26,56 @@
* @bug 4273031
* @summary ClassLoader.getResouce() should be able to
* find resources with leading "." in their names
* @build GetDotResource
* @run shell getdotresource.sh
* @library /lib/testlibrary
* @build jdk.testlibrary.*
* @run main GetDotResource
*/
import java.net.URL;
import java.net.URLClassLoader;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.jar.JarEntry;
import java.util.jar.JarOutputStream;
import jdk.testlibrary.ProcessTools;
public class GetDotResource {
public static void main(String[] args) throws Exception {
private static final String JAR_FILENAME = "resource.jar";
private static final String DOT_FILENAME = ".resource";
private static final String CP = JAR_FILENAME + File.pathSeparator
+ System.getProperty("test.class.path");
public static void main(String[] args) throws Throwable {
if (args.length == 0) {
createJar(JAR_FILENAME, DOT_FILENAME);
ProcessTools.executeTestJava("-cp", CP,
GetDotResource.class.getName(),
DOT_FILENAME)
.outputTo(System.out)
.errorTo(System.out)
.shouldHaveExitValue(0);
} else {
runTest(args[0]);
}
}
public static void runTest(String dotFileName) throws Exception {
if (GetDotResource.class.getClassLoader().
getResourceAsStream(".resource") == null)
throw new Exception("Could not find resource with " +
"leading . in their names");
getResourceAsStream(dotFileName) == null) {
throw new Exception("Could not find resource with "
+ "leading . in their names");
}
}
public static void createJar(String jarFileName, String dotFileName)
throws IOException {
try (FileOutputStream fos = new FileOutputStream(jarFileName);
JarOutputStream out = new JarOutputStream(fos))
{
out.putNextEntry(new JarEntry(dotFileName));
out.closeEntry();
}
}
}

View file

@ -1,46 +0,0 @@
#! /bin/sh
#
# Copyright (c) 1999, 2012, 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
# under the terms of the GNU General Public License version 2 only, as
# published by the Free Software Foundation.
#
# 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).
#
# 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.
#
# 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.
#
if [ x"$TESTJAVA" = x ]; then
TESTJAVA=$1
shift
fi
if [ x"$TESTCLASSES" = x ]; then TESTCLASSES=.; fi
if [ x"$TESTSRC" = x ]; then TESTSRC=.; fi
OS=`uname -s`
case "$OS" in
Windows* | CYGWIN* )
PS=";"
FS="\\"
;;
* )
PS=":"
FS="/"
;;
esac
# now start the test
${TESTJAVA}/bin/java ${TESTVMOPTS} -cp ${TESTSRC}${FS}resource.jar${PS}${TESTCLASSES} GetDotResource

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2012, 2017, 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
@ -22,13 +22,15 @@
*/
/* @test
* @summary High arity invocations, up to the maximum of 255 arguments
* @summary High arity invocations
* @compile BigArityTest.java
* @run junit/othervm/timeout=2500 -XX:+IgnoreUnrecognizedVMOptions -XX:-VerifyDependencies -esa -DBigArityTest.ITERATION_COUNT=1 test.java.lang.invoke.BigArityTest
*/
package test.java.lang.invoke;
import org.junit.Test;
import java.lang.invoke.MethodHandle;
import java.lang.invoke.MethodHandles;
import java.lang.invoke.MethodType;
@ -37,8 +39,8 @@ import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.Objects;
import static org.junit.Assert.assertEquals;
import org.junit.Test;
public class BigArityTest {
@ -63,12 +65,70 @@ public class BigArityTest {
static Object hashArguments(Object... args) {
return Objects.hash(args);
}
static Object hashArguments(int... args) {
Object[] wrappedArgs = new Object[args.length];
for (int i = 0; i < args.length; i++) {
wrappedArgs[i] = args[i];
}
return hashArguments(wrappedArgs);
}
static Object hashArguments(long... args) {
Object[] wrappedArgs = new Object[args.length];
for (int i = 0; i < args.length; i++) {
wrappedArgs[i] = (int) args[i];
}
return hashArguments(wrappedArgs);
}
static Object hashArguments1(Object o, Object... args) {
Object[] arr = new Object[args.length + 1];
arr[0] = 0;
System.arraycopy(args, 0, arr, 1, args.length);
return Objects.hash(arr);
}
static Object hashArguments1(int i0, int... args) {
Object[] wrappedArgs = new Object[args.length + 1];
wrappedArgs[0] = i0;
for (int i = 0; i < args.length; i++) {
wrappedArgs[i + 1] = args[i];
}
return hashArguments(wrappedArgs);
}
static Object hashArguments1(long l0, long... args) {
Object[] wrappedArgs = new Object[args.length + 1];
wrappedArgs[0] = l0;
for (int i = 0; i < args.length; i++) {
wrappedArgs[i + 1] = (int) args[i];
}
return hashArguments(wrappedArgs);
}
static final MethodHandle MH_hashArguments_VA;
static final MethodHandle MH_hashArguments_IVA;
static final MethodHandle MH_hashArguments_JVA;
static final MethodHandle MH_hashArguments1_VA;
static final MethodHandle MH_hashArguments1_IVA;
static final MethodHandle MH_hashArguments1_JVA;
static {
try {
MH_hashArguments_VA =
MethodHandles.lookup().unreflect(
BigArityTest.class.getDeclaredMethod("hashArguments", Object[].class));
MH_hashArguments_IVA =
MethodHandles.lookup().unreflect(
BigArityTest.class.getDeclaredMethod("hashArguments", int[].class));
MH_hashArguments_JVA =
MethodHandles.lookup().unreflect(
BigArityTest.class.getDeclaredMethod("hashArguments", long[].class));
MH_hashArguments1_VA =
MethodHandles.lookup().unreflect(
BigArityTest.class.getDeclaredMethod("hashArguments1", Object.class, Object[].class));
MH_hashArguments1_IVA =
MethodHandles.lookup().unreflect(
BigArityTest.class.getDeclaredMethod("hashArguments1", int.class, int[].class));
MH_hashArguments1_JVA =
MethodHandles.lookup().unreflect(
BigArityTest.class.getDeclaredMethod("hashArguments1", long.class, long[].class));
} catch (ReflectiveOperationException ex) {
throw new Error(ex);
}
@ -345,6 +405,28 @@ public class BigArityTest {
assertEquals("arity=MAX_ARITY", r0, r);
}
@Test
public void testInvokeWithArgumentsJumbo() throws Throwable {
System.out.println("testing invokeWithArguments on jumbo arities");
ArrayList<Integer> arities = new ArrayList<>();
for (int arity = 125; arity < 1000; arity += (arity < MAX_ARITY+10 ? 1 : arity/7)) {
arities.add(arity);
Object[] args = testArgs(arity);
Object r0 = Objects.hash(args);
assertEquals("jumbo arity="+arity, r0, MH_hashArguments_VA.invokeWithArguments(args));
assertEquals("jumbo arity="+arity, r0, MH_hashArguments1_VA.invokeWithArguments(args));
// use primitive typed argument lists also:
assertEquals("jumbo int arity="+arity, r0, MH_hashArguments_IVA.invokeWithArguments(args));
assertEquals("jumbo int arity="+arity, r0, MH_hashArguments1_IVA.invokeWithArguments(args));
assertEquals("jumbo long arity="+arity, r0, MH_hashArguments_JVA.invokeWithArguments(args));
assertEquals("jumbo long arity="+arity, r0, MH_hashArguments1_JVA.invokeWithArguments(args));
}
System.out.println(" jumbo arities = "+arities);
}
static Object[] cat(Object a, Object[] b) {
int alen = 1, blen = b.length;
Object[] c = new Object[alen + blen];

View file

@ -0,0 +1,135 @@
/*
* Copyright (c) 2017, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* 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).
*
* 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.
*
* 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.
*/
/* @test
* @summary basic tests for MethodHandle.invokeWithArguments
* @run testng test.java.lang.invoke.InvokeWithArgumentsTest
*/
package test.java.lang.invoke;
import org.testng.Assert;
import org.testng.annotations.Test;
import java.lang.invoke.MethodHandle;
import java.lang.invoke.MethodHandles;
import java.lang.invoke.WrongMethodTypeException;
import static java.lang.invoke.MethodType.methodType;
public class InvokeWithArgumentsTest {
static final MethodHandles.Lookup L = MethodHandles.lookup();
static Object[] arity(Object o1, Object o2, Object... a) {
return a;
}
@Test
public void testArity() throws Throwable {
MethodHandle mh = L.findStatic(L.lookupClass(), "arity",
methodType(Object[].class, Object.class, Object.class, Object[].class));
try {
mh.invokeWithArguments("");
Assert.fail("WrongMethodTypeException expected");
} catch (WrongMethodTypeException e) {}
}
static Object[] passThrough(String... a) {
return a;
}
static Object[] pack(Object o, Object... a) {
return a;
}
@Test
public void testArrayNoPassThrough() throws Throwable {
String[] actual = {"A", "B"};
MethodHandle mh = L.findStatic(L.lookupClass(), "passThrough",
methodType(Object[].class, String[].class));
// Note: the actual array is not preserved, the elements will be
// unpacked and then packed into a new array before invoking the method
String[] expected = (String[]) mh.invokeWithArguments(actual);
Assert.assertTrue(actual != expected, "Array should not pass through");
Assert.assertEquals(actual, expected, "Array contents should be equal");
}
@Test
public void testArrayPack() throws Throwable {
String[] actual = new String[]{"A", "B"};
MethodHandle mh = L.findStatic(L.lookupClass(), "pack",
methodType(Object[].class, Object.class, Object[].class));
// Note: since String[] can be cast to Object, the actual String[] array
// will cast to Object become the single element of a new Object[] array
Object[] expected = (Object[]) mh.invokeWithArguments("", actual);
Assert.assertEquals(1, expected.length, "Array should contain just one element");
Assert.assertTrue(actual == expected[0], "Array should pass through");
}
static void intArray(int... a) {
}
@Test
public void testPrimitiveArrayWithNull() throws Throwable {
MethodHandle mh = L.findStatic(L.lookupClass(), "intArray",
methodType(void.class, int[].class));
try {
mh.invokeWithArguments(null, null);
Assert.fail("NullPointerException expected");
} catch (NullPointerException e) {}
}
@Test
public void testPrimitiveArrayWithRef() throws Throwable {
MethodHandle mh = L.findStatic(L.lookupClass(), "intArray",
methodType(void.class, int[].class));
try {
mh.invokeWithArguments("A", "B");
Assert.fail("ClassCastException expected");
} catch (ClassCastException e) {}
}
static void numberArray(Number... a) {
}
@Test
public void testRefArrayWithCast() throws Throwable {
MethodHandle mh = L.findStatic(L.lookupClass(), "numberArray",
methodType(void.class, Number[].class));
// All numbers, should not throw
mh.invokeWithArguments(1, 1.0, 1.0F, 1L);
try {
mh.invokeWithArguments("A");
Assert.fail("ClassCastException expected");
} catch (ClassCastException e) {}
}
}

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2015, 2017, 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
@ -203,10 +203,8 @@ abstract class VarHandleBaseTest {
static List<TestAccessMode> testAccessModesOfType(TestAccessType... ats) {
Stream<TestAccessMode> s = Stream.of(TestAccessMode.values());
for (TestAccessType at : ats) {
s = s.filter(e -> e.isOfType(at));
}
return s.collect(toList());
return s.filter(e -> Stream.of(ats).anyMatch(e::isOfType))
.collect(toList());
}
static List<VarHandle.AccessMode> accessModes() {
@ -215,10 +213,9 @@ abstract class VarHandleBaseTest {
static List<VarHandle.AccessMode> accessModesOfType(TestAccessType... ats) {
Stream<TestAccessMode> s = Stream.of(TestAccessMode.values());
for (TestAccessType at : ats) {
s = s.filter(e -> e.isOfType(at));
}
return s.map(TestAccessMode::toAccessMode).collect(toList());
return s.filter(e -> Stream.of(ats).anyMatch(e::isOfType))
.map(TestAccessMode::toAccessMode)
.collect(toList());
}
static MethodHandle toMethodHandle(VarHandle vh, TestAccessMode tam, MethodType mt) {

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2000, 2017, 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
@ -24,11 +24,11 @@
/**
* @test
* @bug 4361783
* @key intermittent
* @summary Test to see if ICMP Port Unreachable on non-connected
* DatagramSocket causes a SocketException "socket closed"
* exception on Windows 2000.
*/
import java.net.BindException;
import java.net.InetAddress;
import java.net.DatagramSocket;
import java.net.DatagramPacket;
@ -50,7 +50,7 @@ public class PortUnreachable {
serverPort);
clientSock.send(packet);
DatagramSocket sock = new DatagramSocket(serverPort);
DatagramSocket sock = recreateServerSocket(serverPort);
b = "Greetings from the server".getBytes();
packet = new DatagramPacket(b, b.length, addr, clientPort);
sock.send(packet);
@ -60,6 +60,29 @@ public class PortUnreachable {
}
}
DatagramSocket recreateServerSocket (int serverPort) throws Exception {
DatagramSocket serverSocket = null;
int retryCount = 0;
System.out.println("Attempting to recreate server socket with port: " +
serverPort);
while (serverSocket == null) {
try {
serverSocket = new DatagramSocket(serverPort);
} catch (BindException bEx) {
if (retryCount++ < 5) {
Thread.sleep(500);
} else {
System.out.println("Give up after 5 retries");
throw bEx;
}
}
}
System.out.println("PortUnreachableTest.recreateServerSocket: returning socket == "
+ serverSocket.getLocalAddress() + ":" + serverSocket.getLocalPort());
return serverSocket;
}
PortUnreachable() throws Exception {
clientSock = new DatagramSocket();
@ -103,3 +126,4 @@ public class PortUnreachable {
}
}

View file

@ -0,0 +1,881 @@
/*
* Copyright (c) 2017, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* 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).
*
* 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.
*
* 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.
*/
/**
* @test
* @bug 8185072
* @summary network006 times out in many configs in JDK10-hs nightly
* @run main/othervm/manual HugeDataTransferTest 1
*/
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.PrintStream;
import java.net.InetAddress;
import java.net.ServerSocket;
import java.net.Socket;
import java.net.UnknownHostException;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.Random;
/**
* This test makes huge number of data transfers between 2 Java virtual machines
* using the TCP/IP protocol, and checks if those data are transfered correctly.
* Both client and server VMs run on the same local computer and attach TCP/IP
* sockets to the local host, or to the loopback domain
* ``<code>localhost</code>'' (having IP address <code>127.0.0.1</code>).
*
* <p>
* In this test, 128 client/server connections are established. Once a
* connection is established, client passes a data parcel to server, and server
* reads that parcel and checks if it is same as expected (byte-to-byte equality
* is desired). Then server passes (some other) parcel to the client, and client
* reads and verifies those bytes. This ping-pong game is repeated 128 times;
* and after that each pair of sockets checks if there are no extra bytes
* accedentally passed through their connection.
*
* <p>
* Parcels lengths and contents are chosen randomly, and average parcel length
* is 128 bytes. So totally, each pair of sockets passes ~16Kb of data to each
* other, and thus ~32Kb of data are transfered by each sockets pair. Totally,
* ~4Mb of data are transfered by all client/server pairs.
*
* @author vtewari
*/
public class HugeDataTransferTest {
/**
* Timeout for TCP/IP sockets (currently set to 1 min).
*/
private static int SO_TIMEOUT;// = 2*60*1000;
/**
* Maximal number of connections this test should open simultaneously.
*/
private final static int MAX_CONNECTIONS = 128;
/**
* Check few more connections to make sure that MAX_CONNECTIONS are safe.
*/
private final static int CONNECTIONS_RESERVE = 10;
/**
* The test used to fail with connection reset by peer set to 50. (and once
* in a three if it was set to 10). So now we set it to MAX_CONNECTIONS
* (128).
*/
private final static int BACKLOG_QUEUE_LENGTH = MAX_CONNECTIONS;
/**
* Number of parcels to be sent/recieved.
*/
private final static int DATA_PARCELS = 128;
/**
* Maximal length of data parcel to be sent/recieved (it equals to 256 bytes
* now).
*/
private final static int MAX_PARCEL = 1 << 8;
/**
* Either actually display optional reports or not.
*/
static private final boolean DEBUG_MODE = false;
/**
* How many IP sockets can we open simultaneously? Check if
* <code>MAX_CONNECTIONS</code> connections can be open simultaneously.
*/
private static int detectOSLimitation() {
final int CONNECTIONS_TO_TRY = MAX_CONNECTIONS + CONNECTIONS_RESERVE;
display("--- Trying to open " + CONNECTIONS_TO_TRY + " connections:");
InetAddress address;
ServerSocket serverSocket;
try {
address = InetAddress.getLocalHost();
int anyPort = 0;
int defaultBacklog = BACKLOG_QUEUE_LENGTH;
serverSocket = new ServerSocket(anyPort, defaultBacklog, address);
} catch (IOException ioe) {
throw new Error("FATAL error while loading the test: " + ioe);
}
display(serverSocket.toString());
Socket server[] = new Socket[CONNECTIONS_TO_TRY];
Socket client[] = new Socket[CONNECTIONS_TO_TRY];
int i, port = serverSocket.getLocalPort();
for (i = 0; i < CONNECTIONS_TO_TRY; i++) {
try {
client[i] = new Socket(address, port);
display(">Open: client[" + i + "] = " + client[i]);
server[i] = serverSocket.accept();
display(">Open: server[" + i + "] = " + server[i]);
} catch (IOException ioe) {
display(">OOPS! -- failed to open connection #" + i);
break;
}
}
display("> Could open "
+ (i < CONNECTIONS_TO_TRY ? "only " : "") + i + " connections.");
display(">Closing them:");
for (int j = 0; j < i; j++) {
try {
server[j].close();
client[j].close();
} catch (IOException ioe) {
throw new Error("FATAL error while loading the test: " + ioe);
}
}
display(">OK.");
int safeConnections = i - CONNECTIONS_RESERVE;
if (safeConnections < 1) {
safeConnections = 1;
}
if (safeConnections < MAX_CONNECTIONS) {
complain("------------------------- CAUTION: -------------------");
complain("While checking the OS limitations, the test found that");
complain("only " + i + " TCP/IP socket connections could be safely open");
complain("simultaneously. However, possibility to open at least");
complain("" + MAX_CONNECTIONS + "+" + CONNECTIONS_RESERVE
+ " connections were expected.");
complain("");
complain("So, the test will check only " + safeConnections + " connection"
+ (safeConnections == 1 ? "" : "s") + " which seem");
complain("safe to be open simultaneously.");
complain("------------------------------------------------------");
}
return safeConnections;
}
//----------------------------------------------------------------//
/**
* Re-calls to the method <code>run(args[],out)</code> actually performing
* the test. After <code>run(args[],out)</code> stops, follow JDK-like
* convention for exit codes. I.e.: stop with exit status 95 if the test has
* passed, or with status 97 if the test has failed.
*
* @see #run(String[],PrintStream)
*/
public static void main(String args[]) {
int exitCode = run(args, System.out);
System.exit(exitCode + 95);
// JCK-like exit status.
}
public static int run(String args[], PrintStream out) {
HugeDataTransferTest.out = out;
//
// Get the Internet address of the local machine.
//
InetAddress address = null;
try {
address = InetAddress.getLocalHost();
} catch (UnknownHostException exception) {
complain(exception.toString());
return 2; // FAILED
}
display("Host: " + address);
//
// Detect if it is safe to open MAX_CONNETIONS simultaneously:
//
final int CONNECTIONS = detectOSLimitation();
//
// Assign ServerSocket, and start client VM which should open
// the prescribed number of CONNECTIONS to that ServerSocket.
//
ServerSocket serverSocket;
try {
final int anyPort = 0;
final int defaultBacklog = BACKLOG_QUEUE_LENGTH;
serverSocket = new ServerSocket(anyPort, defaultBacklog, address);
} catch (IOException exception) {
complain("Cannot assign a ServerSocket on: " + address);
return 2;
}
//
// Start the client process on different VM.
//
String jdkPath = System.getProperty("test.jdk");
Path toolName = Paths.get("bin", "java" + (isWindows() ? ".exe" : ""));
Path jdkTool = Paths.get(jdkPath, toolName.toString());
String IPAddress = address.getHostAddress();
int localPort = serverSocket.getLocalPort();
String arguments = " " + CONNECTIONS + " " + IPAddress + " " + localPort;
//String command = args[0] + " " + network006.class.getName() + "$Client " + arguments;
String command = jdkTool.toAbsolutePath().toString() + " " + Client.class.getName() + " " + arguments;
try {
SO_TIMEOUT = Integer.parseInt(args[0]) * 60 * 1000;
} catch (NumberFormatException e) {
complain("Wrong timeout argument: " + e);
return 2;
}
Runtime runtime = Runtime.getRuntime();
Process client = null;
IORedirector redirectOut = null;
IORedirector redirectErr = null;
try {
// Start clients on different JVM:
client = runtime.exec(command);
// Provide clients with access to stderr and stdout:
InputStream clientOut = client.getInputStream();
InputStream clientErr = client.getErrorStream();
redirectOut = new IORedirector(clientOut, DEBUG_MODE ? out : null);
redirectErr = new IORedirector(clientErr, out);
redirectOut.start();
redirectErr.start();
} catch (IOException exception) {
complain("Failed to start client: " + exception);
return 2;
}
//
// Start the server threads (and let them establish connections):
//
Server server[] = new Server[CONNECTIONS];
for (int i = 0; i < CONNECTIONS; i++) {
server[i] = new Server(serverSocket);
display("Server #" + i + ": " + server[i]);
server[i].start();
}
//
// Wait for the servers and the clients:
//
boolean testFailed = false;
try {
client.waitFor();
int clientStatus = client.exitValue();
display("Client VM exitCode=" + clientStatus);
// Let I/O redirectors to flush:
if (redirectOut.isAlive()) {
redirectOut.join();
}
if (redirectErr.isAlive()) {
redirectErr.join();
}
// If client has crashed, also terminate the server (to avoid hangup).
if (clientStatus != 95) {
complain("Client VM has crashed: exit status=" + clientStatus);
testFailed = true;
}
// Client has finished OK; wait for the server.
for (int i = 0; i < CONNECTIONS; i++) {
display("Server: waiting for #" + i);
if (server[i].isAlive()) {
display("Server #" + i + ": (joining...)" + server[i]);
server[i].join();
}
if (server[i].exception != null) {
if (server[i].message != null) {
complain("Server #" + i + "(finished): with message:" + server[i].message);
}
complain("Server #" + i + "(finished): " + server[i].exception);
server[i].exception.printStackTrace(out);
out.flush();
// complain("Server #"+i+": "+server[i].exception.getStackTrace());
testFailed = true;
}
}
} catch (InterruptedException exception) {
complain("Test interrupted: " + exception);
testFailed = true;
}
if (testFailed) {
complain("Test failed.");
} else {
display("Test passed.");
}
return testFailed ? 2 : 0;
}
private static boolean isWindows() {
return System.getProperty("os.name").toLowerCase().startsWith("win");
}
//----------------------------------------------------------------//
/**
* Log stream for error messages and/or (optional) execution trace.
*/
private static PrintStream out;
/**
* Print error message.
*/
private static synchronized void complain(Object message) {
out.println("# " + message);
out.flush();
}
;
/**
* Display optional report: comment ca va?
*/
private static synchronized void display(Object report) {
if (DEBUG_MODE) {
out.println(report.toString());
}
out.flush(); //todo shouldn't this be inside if??
}
;
//----------------------------------------------------------------//
/**
* Server thread should reply to data parcels sent by Client VM.
*/
private static class Server extends Thread {
/**
* The socket is assigned at the Server instantiation.
*/
private ServerSocket serverSocket;
/**
* The socket is assigned at the Server runtime.
*/
private Socket socket;
/**
* Display the server socket.
*/
@Override
public String toString() {
return "ServerSocket: " + serverSocket.toString();
// + " socket: " + socket.toString();
}
/**
* Which port is this socket listening?
*/
int getPort() {
return serverSocket.getLocalPort();
}
/**
* Find some free port at the given <code>address</code> and attach new
* server to hear that port. // lidsten to??
*/
public Server(ServerSocket serverSocket) {
this.serverSocket = serverSocket;
}
/**
* Exception just arisen while the server was working, or
* <code>null</code> if it was OK with the server.
*/
Exception exception = null;
String message = null;
/**
* Accept connection, then reply to client's parcels.
*/
@Override
public void run() {
try {
socket = serverSocket.accept();
socket.setSoTimeout(SO_TIMEOUT);
InputStream istream = socket.getInputStream();
OutputStream ostream = socket.getOutputStream();
Random random = new Random(getPort());
for (int i = 0; i < DATA_PARCELS; i++) {
Parcel etalon = new Parcel(random);
message = "reading parcel number " + i;
Parcel sample = new Parcel(istream); // read
if (!sample.equals(etalon)) {
complain("Server thread for port #"
+ getPort() + " got unexpected parcel:\n"
+ "sample=" + sample + "\n"
+ "etalon=" + etalon);
throw new TestFailure( //received??
"server has read unexpected parcel");
}
message = "sending parcel number " + i;
etalon.send(ostream);
ostream.flush();
}
int datum = istream.read(); // wait for client close()
if (datum >= 0) {
throw new TestFailure(
"server has read ambigous byte: " + datum);
}
ostream.close(); // implies: socket.close();
} catch (Exception oops) {
exception = oops;
}
}
}
//----------------------------------------------------------------//
/**
* Client VM should send data parcels to Server VM and recieve and verify
* the server's replies.
*/
private static class Client extends Thread {
/**
* This thread uses the single client socket.
*/
private Socket socket;
/**
* Address and port of this socket.
*/
@Override
public String toString() {
return socket.toString();
}
/**
* Did the thread failed? If yes, what is the failure's reason.
*/
Exception exception = null;
String message = null;
public static java.io.PrintStream complainStream = System.out;
public static java.io.PrintStream displayStream = System.err;
/**
* Connect client socket on the given <code>address</code> and
* <code>port</code>.
*/
Client(InetAddress address, int port) throws IOException {
socket = new Socket(address, port);
socket.setSoTimeout(SO_TIMEOUT);
}
/**
* What is the port number this socket is listening for?
*/
int getPort() {
return socket.getPort();
}
/**
* Establish connection, then read/respond <code>DATA_PARCELS</code>
* parcels of random data. Set initial seed for pseudo-random numbers
* generator to the value of the local port number.
*
* @see #DATA_PARCELS
* @see #getPort()
*/
@Override
public void run() {
try {
InputStream istream = socket.getInputStream();
OutputStream ostream = socket.getOutputStream();
Random random = new Random(getPort());
// suggested by Oleg -- to avoid race conditions
/* try{
Thread.sleep(500);
}
catch (java.lang.InterruptedException e)
{
}*/
for (int i = 0; i < DATA_PARCELS; i++) {
Parcel etalon = new Parcel(random);
message = "sending parcel number: " + i;
etalon.send(ostream);
ostream.flush();
message = "reading parcel number: " + i;
Parcel sample = new Parcel(istream); // read
if (!sample.equals(etalon)) {
complain("Client thread for port #"
+ getPort() + " got unexpected parcel:\n"
+ "sample=" + sample + "\n"
+ "etalon=" + etalon);
throw new TestFailure(
"parcel context is unexpected to client");
}
}
if (istream.available() > 0) {
int datum = istream.read();
throw new TestFailure(
"client has read ambigous byte: " + datum);
}
ostream.close(); // implies: socket.close()
} catch (Exception oops) {
exception = oops;
}
}
/**
* Establish lots of connections to server socket, attack servers with
* huge data parcels, and check if they reply correctly. The number of
* connections to try, the address and port number for the server socket
* are passed through <code>args[]</code>, like:
* <pre>
* java network006$Client connections_to_try address port
* </pre>
*/
public static void main(String args[]) {
if (DEBUG_MODE) {
try {
String filename = "Client" + ((args.length == 3) ? args[2] : "new");
displayStream = new PrintStream(filename + ".out");
complainStream = new PrintStream(filename + ".err");
} catch (FileNotFoundException exception) {
complain(exception);
}
}
if (args.length != 3) {
complain("Client expects 3 paramenets:");
complain(" java " + Client.class.getName() + " connections_to_try address port");
exit(1); // FAILED
}
int CONNECTIONS = Integer.parseInt(args[0]);
display("Client VM: will try " + CONNECTIONS + " connections.");
InetAddress address;
try {
address = InetAddress.getByName(args[1]);
} catch (UnknownHostException exception) {
address = null;
complain("Client: cannot find host: \"" + args[1] + "\"");
exit(4);
}
display("Client: host to contact: " + address);
int port = Integer.parseInt(args[2]);
display("Client: port to contact: " + port);
//
// Establish connections, and start client processes:
//
Client client[] = new Client[CONNECTIONS];
for (int i = 0; i < CONNECTIONS; i++) {
try {
client[i] = new Client(address, port);
display("Client #" + i + ": " + client[i]);
} catch (IOException ioe) {
complain("Client #" + i + "(creation): " + ioe);
ioe.printStackTrace(complainStream);
complainStream.flush();
// complain("Client #" + i + "(creation): " + ioe.getStackTrace());
exit(3);
}
}
for (int i = 0; i < CONNECTIONS; i++) {
client[i].start();
}
//
// Wait until testing is not finished:
//
int status = 0;
for (int i = 0; i < CONNECTIONS; i++) {
display("Client: waiting for #" + i);
if (client[i].isAlive()) {
display("Client #" + i + ": (joining...)" + client[i]);
try {
client[i].join();
} catch (InterruptedException ie) {
complain("Client #" + i + ": " + ie);
status = 3;
}
}
if (client[i].exception != null) {
if (client[i].message != null) {
complain("Client #" + i + "(finished) with message: " + client[i].message);
}
complain("Client #" + i + "(finished): " + client[i].exception);
client[i].exception.printStackTrace(complainStream);
complainStream.flush();
if (status == 0) {
status = 2;
}
}
}
exit(status);
}
/**
* Print error message.
*/
private static synchronized void complain(Object message) {
complainStream.println("# " + message);
complainStream.flush();
}
/**
* Display execution trace.
*/
private static synchronized void display(Object message) {
if (!DEBUG_MODE) {
return;
}
displayStream.println(message.toString());
displayStream.flush();
}
/**
* Exit with JCK-like status.
*/
private static void exit(int exitCode) {
int status = exitCode + 95;
// display("Client: exiting with code=" + status);
System.exit(status);
}
}
/**
* Two of such threads should redirect <code>out</code> and <code>err</code>
* streams of client VM.
*/
private static class IORedirector extends Thread {
/**
* Source stream.
*/
InputStream in;
/**
* Destination stream.
*/
OutputStream out;
/**
* Redirect <code>in</code> to <code>out</code>.
*/
public IORedirector(InputStream in, OutputStream out) {
this.in = in;
this.out = out;
}
/**
* Read input stream until the EOF, and write everithing to output
* stream. If output stream is assigned to <code>null</code>, do not
* print anything, but read the input stream anywhere.
*/
@Override
public void run() {
try {
for (;;) {
int symbol = in.read();
if (symbol < 0) {
break; // EOF
}
if (out != null) {
out.write(symbol);
}
}
if (out != null) {
out.flush();
}
} catch (IOException exception) {
throw new TestFailure("IORedirector exception: " + exception);
}
}
}
//----------------------------------------------------------------//
/**
* A data parcel to be sent/recieved between Client VM and Server thread.
* When data parcel is sent, first 4 bytes are transfered which encode the
* <code>int</code> number equal to size of the parcel minus 1. I.e.: if
* number of data bytes in the parcel's contents is <code>N</code>, then the
* first 4 bytes encode the number <code>N-1</code>. After that, the
* parcel's contents bytes are transered.
*/
static class Parcel {
private final byte[] parcel;
/**
* Display all bytes as integer values from 0 to 255; or return
* ``<tt>null</tt>'' if this Parcel is not yet initialized.
*/
@Override
public String toString() {
if (parcel == null) {
return "null";
}
String s = "{";
for (int i = 0; i < parcel.length; i++) {
s += (i > 0 ? ", " : "") + ((int) parcel[i] & 0xFF);
}
return s + "}";
}
/**
* Generate new <code>parcel[]</code> array using the given
* <code>random</code> numbers generator. Client and Server threads
* should use identical <code>random</code> generators, so that those
* threads could generate equal data parcels and check the parcel just
* transfered.
*/
public Parcel(Random random) {
int size = random.nextInt(MAX_PARCEL) + 1;
parcel = new byte[size];
for (int i = 0; i < size; i++) {
parcel[i] = (byte) random.nextInt(256);
}
}
;
/**
* Read exactly <code>size</code> bytes from the <code>istream</code>
* if possible, or throw <code>TestFailure</code> if unexpected end of
* <code>istream</code> occurs.
*/
private static byte[] readBytes(int size, InputStream istream)
throws IOException {
byte data[] = new byte[size];
for (int i = 0; i < size; i++) {
int datum = istream.read();
if (datum < 0) {
throw new TestFailure(
"unexpected EOF: have read: " + i + " bytes of " + size);
}
data[i] = (byte) datum;
}
return data;
}
/**
* Read 4 bytes from <code>istream</code> and threat them to encode size
* of data parcel following these 4 bytes.
*/
private static int getSize(InputStream istream) throws IOException {
byte data[] = readBytes(4, istream);
int data0 = (int) data[0] & 0xFF;
int data1 = (int) data[1] & 0xFF;
int data2 = (int) data[2] & 0xFF;
int data3 = (int) data[3] & 0xFF;
int sizeWord = data0 + (data1 << 8) + (data2 << 16) + (data3 << 24);
int size = sizeWord + 1;
if (size <= 0) {
throw new TestFailure("illegal size: " + size);
}
return size;
}
/**
* Send 4 bytes encoding actual size of the parcel just to be
* transfered.
*/
private static void putSize(OutputStream ostream, int size)
throws IOException {
if (size <= 0) {
throw new TestFailure("illegal size: " + size);
}
int sizeWord = size - 1;
byte data[] = new byte[4];
data[0] = (byte) sizeWord;
data[1] = (byte) (sizeWord >> 8);
data[2] = (byte) (sizeWord >> 16);
data[3] = (byte) (sizeWord >> 24);
ostream.write(data);
}
/**
* Recieve data parcel.
*/
public Parcel(InputStream istream) throws IOException {
int size = getSize(istream);
parcel = readBytes(size, istream);
}
/**
* Send <code>this</code> data parcel.
*/
public void send(OutputStream ostream) throws IOException {
int size = parcel.length;
putSize(ostream, size);
ostream.write(parcel);
}
/**
* Check byte-to-byte equality between <code>this</code> and the
* <code>other</code> parcels.
*/
public boolean equals(Parcel other) {
if (this.parcel.length != other.parcel.length) {
return false;
}
int size = parcel.length;
for (int i = 0; i < size; i++) {
if (this.parcel[i] != other.parcel[i]) {
return false;
}
}
return true;
}
}
/**
* Server or Client may throw this exception to report the test failure.
*/
static class TestFailure extends RuntimeException {
/**
* Report particular <code>purpose</code> of the test failure.
*/
public TestFailure(String purpose) {
super(purpose);
}
}
}

View file

@ -24,7 +24,6 @@
/*
* @test
* @bug 8087112
* @key intermittent
* @library /lib/testlibrary server
* @build jdk.testlibrary.SimpleSSLContext
* @modules jdk.incubator.httpclient/jdk.incubator.http.internal.common

View file

@ -105,7 +105,7 @@ public final class DummyWebSocketServer implements Closeable {
channel.configureBlocking(true);
StringBuilder request = new StringBuilder();
if (!readRequest(channel, request)) {
throw new IOException("Bad request");
throw new IOException("Bad request:" + request);
}
List<String> strings = asList(request.toString().split("\r\n"));
List<String> response = mapping.apply(strings);
@ -156,6 +156,7 @@ public final class DummyWebSocketServer implements Closeable {
public void close() {
log.log(INFO, "Stopping: " + getURI());
thread.interrupt();
close(ssc);
}
URI getURI() {
@ -169,19 +170,21 @@ public final class DummyWebSocketServer implements Closeable {
throws IOException
{
ByteBuffer buffer = ByteBuffer.allocate(512);
int num = channel.read(buffer);
if (num == -1) {
return false;
while (channel.read(buffer) != -1) {
// read the complete HTTP request headers, there should be no body
CharBuffer decoded;
buffer.flip();
try {
decoded = ISO_8859_1.newDecoder().decode(buffer);
} catch (CharacterCodingException e) {
throw new UncheckedIOException(e);
}
request.append(decoded);
if (Pattern.compile("\r\n\r\n").matcher(request).find())
return true;
buffer.clear();
}
CharBuffer decoded;
buffer.flip();
try {
decoded = ISO_8859_1.newDecoder().decode(buffer);
} catch (CharacterCodingException e) {
throw new UncheckedIOException(e);
}
request.append(decoded);
return Pattern.compile("\r\n\r\n").matcher(request).find();
return false;
}
private void writeResponse(SocketChannel channel, List<String> response)

View file

@ -32,7 +32,7 @@ public final class LoggingHelper {
* @run main/othervm/jul=logging.properties ClassUnderTest
*/
public static void setupLogging() {
String path = System.getProperty("test.src") + File.separator + "logging.properties";
String path = System.getProperty("test.src", ".") + File.separator + "logging.properties";
System.setProperty("java.util.logging.config.file", path);
}
}

View file

@ -323,9 +323,12 @@ public class Proc {
br = new BufferedReader(new InputStreamReader(p.getInputStream()));
return this;
}
String getId(String prefix) {
if (debug != null) return prefix + "." + debug;
else return prefix + "." + System.identityHashCode(this);
String getId(String suffix) {
if (debug != null) {
return debug + "." + suffix;
} else {
return System.identityHashCode(this) + "." + suffix;
}
}
// Reads a line from stdout of proc
public String readLine() throws IOException {
@ -395,9 +398,13 @@ public class Proc {
boolean isEmpty = true;
while (true) {
int i = System.in.read();
if (i == -1) break;
if (i == -1) {
break;
}
isEmpty = false;
if (i == '\n') break;
if (i == '\n') {
break;
}
if (i != 13) {
// Force it to a char, so only simple ASCII works.
sb.append((char)i);

View file

@ -22,19 +22,27 @@
*/
/* @test
@bug 4241361 4842702 4985614 6646605 5032358 6923692 6233323 8144977
@bug 4241361 4842702 4985614 6646605 5032358 6923692 6233323 8144977 8186464
@summary Make sure we can read a zip file.
@key randomness
*/
import java.io.*;
import java.net.URI;
import java.nio.file.Files;
import java.nio.file.FileSystem;
import java.nio.file.FileSystems;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.nio.file.NoSuchFileException;
import java.nio.file.StandardCopyOption;
import java.nio.file.StandardOpenOption;
import java.util.List;
import java.util.Map;
import java.util.zip.*;
import static java.nio.charset.StandardCharsets.US_ASCII;
public class ReadZip {
private static void unreached (Object o)
throws Exception
@ -137,8 +145,6 @@ public class ReadZip {
newZip.delete();
}
// Throw a FNF exception when read a non-existing zip file
try { unreached (new ZipFile(
new File(System.getProperty("test.src", "."),
@ -146,5 +152,54 @@ public class ReadZip {
+ String.valueOf(new java.util.Random().nextInt())
+ ".zip")));
} catch (NoSuchFileException nsfe) {}
// read a zip file with ZIP64 end
Path path = Paths.get(System.getProperty("test.dir", ""), "end64.zip");
try {
URI uri = URI.create("jar:" + path.toUri());
Map<String, Object> env = Map.of("create", "true", "forceZIP64End", "true");
try (FileSystem fs = FileSystems.newFileSystem(uri, env)) {
Files.write(fs.getPath("hello"), "hello".getBytes());
}
try (ZipFile zf = new ZipFile(path.toFile())) {
if (!"hello".equals(new String(zf.getInputStream(new ZipEntry("hello"))
.readAllBytes(),
US_ASCII)))
throw new RuntimeException("zipfile: read entry failed");
} catch (IOException x) {
throw new RuntimeException("zipfile: zip64 end failed");
}
try (FileSystem fs = FileSystems.newFileSystem(uri, Map.of())) {
if (!"hello".equals(new String(Files.readAllBytes(fs.getPath("hello")))))
throw new RuntimeException("zipfs: read entry failed");
} catch (IOException x) {
throw new RuntimeException("zipfile: zip64 end failed");
}
} finally {
Files.deleteIfExists(path);
}
// read a zip file created via "echo hello | zip dst.zip -", which uses
// ZIP64 end record
if (Files.notExists(Paths.get("/usr/bin/zip")))
return;
try {
Process zip = new ProcessBuilder("zip", path.toString().toString(), "-").start();
OutputStream os = zip.getOutputStream();
os.write("hello".getBytes(US_ASCII));
os.close();
zip.waitFor();
if (zip.exitValue() == 0 && Files.exists(path)) {
try (ZipFile zf = new ZipFile(path.toFile())) {
if (!"hello".equals(new String(zf.getInputStream(new ZipEntry("-"))
.readAllBytes())))
throw new RuntimeException("zipfile: read entry failed");
} catch (IOException x) {
throw new RuntimeException("zipfile: zip64 end failed");
}
}
} finally {
Files.deleteIfExists(path);
}
}
}

View file

@ -30,6 +30,7 @@
* @modules java.security.jgss
* jdk.security.auth
* java.base/sun.security.util
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /test/lib /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -27,6 +27,7 @@
* @summary Testing DTLS engines do not enable RC4 ciphers by default.
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @key randomness
* @library /sun/security/krb5/auto /test/lib /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /test/lib /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -28,6 +28,7 @@
* causes IllegalArgumentException.
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -1,4 +1,5 @@
modules = \
java.security.jgss/sun.security.jgss.krb5 \
java.security.jgss/sun.security.krb5:+open \
java.security.jgss/sun.security.krb5.internal.crypto \
java.security.jgss/sun.security.krb5.internal.ccache \

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon /javax/net/ssl/DTLS
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /test/lib /javax/net/ssl/TLSCommon /javax/net/ssl/DTLS
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -27,6 +27,7 @@
* @summary Testing DTLS engines do not enable RC4 ciphers by default.
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @key randomness
* @library /sun/security/krb5/auto /test/lib /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /lib/testlibrary /javax/net/ssl/TLSCommon /javax/net/ssl/DTLS
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -28,6 +28,7 @@
* causes IllegalArgumentException.
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -1,4 +1,5 @@
modules = \
java.security.jgss/sun.security.jgss.krb5 \
java.security.jgss/sun.security.krb5:+open \
java.security.jgss/sun.security.krb5.internal.crypto \
java.security.jgss/sun.security.krb5.internal.ccache \

View file

@ -1,4 +1,5 @@
modules = \
java.security.jgss/sun.security.jgss.krb5 \
java.security.jgss/sun.security.krb5:+open \
java.security.jgss/sun.security.krb5.internal.crypto \
java.security.jgss/sun.security.krb5.internal.ktab \

View file

@ -28,6 +28,7 @@
* @summary javax/net/ssl/TLS/TLSClientPropertyTest.java needs to be
* updated for JDK-8061210
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -27,6 +27,7 @@
* @summary Testing TLS engines do not enable RC4 ciphers by default.
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @key randomness
* @library /sun/security/krb5/auto /test/lib /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -28,6 +28,7 @@
* causes IllegalArgumentException.
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -1,4 +1,5 @@
modules = \
java.security.jgss/sun.security.jgss.krb5 \
java.security.jgss/sun.security.krb5:+open \
java.security.jgss/sun.security.krb5.internal.crypto \
java.security.jgss/sun.security.krb5.internal.ccache \

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -27,6 +27,7 @@
* @summary Testing TLS engines do not enable RC4 ciphers by default.
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @key randomness
* @library /sun/security/krb5/auto /test/lib /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -28,6 +28,7 @@
* causes IllegalArgumentException.
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -34,6 +34,7 @@
* @summary Support TLS 1.1
* @run main/othervm EmptyCertificateAuthorities
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -34,6 +34,7 @@
* @summary Support TLS 1.1
* @run main/othervm ExportableBlockCipher
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -33,6 +33,7 @@
* @bug 4873188
* @summary Support TLS 1.1
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -28,6 +28,7 @@
* @bug 4873188
* @summary Support TLS 1.1
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -28,6 +28,7 @@
* @bug 4873188
* @summary Support TLS 1.1
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -1,4 +1,5 @@
modules = \
java.security.jgss/sun.security.jgss.krb5 \
java.security.jgss/sun.security.krb5:+open \
java.security.jgss/sun.security.krb5.internal.crypto \
java.security.jgss/sun.security.krb5.internal.ccache \

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -27,6 +27,7 @@
* @summary Testing TLS engines do not enable RC4 ciphers by default.
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -29,6 +29,7 @@
* @key randomness
* @library /sun/security/krb5/auto /test/lib /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -30,6 +30,7 @@
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* jdk.security.auth
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -28,6 +28,7 @@
* causes IllegalArgumentException.
* @library /sun/security/krb5/auto /javax/net/ssl/TLSCommon
* @modules java.security.jgss
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.krb5.internal.ccache

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2013, 2017, 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
@ -23,170 +23,312 @@
/*
* @test
* @bug 8009977
* @summary A test library to launch multiple Java processes
* @bug 8009977 8186884
* @summary A test to launch multiple Java processes using either Java GSS
* or native GSS
* @library ../../../../java/security/testlibrary/
* @compile -XDignore.symbol.file BasicProc.java
* @run main/othervm BasicProc
* @run main/othervm BasicProc launcher
*/
import java.io.File;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.nio.file.attribute.PosixFilePermission;
import java.util.Arrays;
import java.util.PropertyPermission;
import java.util.Random;
import java.util.Set;
import org.ietf.jgss.Oid;
import sun.security.krb5.Config;
import javax.security.auth.PrivateCredentialPermission;
/**
* Run this test automatically and test Java GSS with embedded KDC.
*
* Run with customized native.krb5.libs to test interop between Java GSS
* and native GSS, and native.kdc.path with a native KDC. For example,
* run the following command to test interop among Java, default native,
* MIT, and Heimdal krb5 libraries with the Heimdal KDC:
*
* jtreg -Dnative.krb5.libs=j=,
* n=,
* k=/usr/local/krb5/lib/libgssapi_krb5.so,
* h=/space/install/heimdal/lib/libgssapi.so \
* -Dnative.kdc.path=/usr/local/heimdal \
* BasicProc.java
*
* Note: The first 4 lines should be concatenated to make a long system
* property value with no blank around ",". This comma-separated value
* has each element being name=libpath. The special name "j" means the
* Java library and libpath is ignored. Otherwise it means a native library,
* and libpath (can be empty) will be the value for the sun.security.jgss.lib
* system property. If this system property is not set, only the Java
* library will be tested.
*/
public class BasicProc {
static String CONF = "krb5.conf";
static String KTAB = "ktab";
private static final String CONF = "krb5.conf";
private static final String KTAB_S = "server.ktab";
private static final String KTAB_B = "backend.ktab";
private static final String HOST = "localhost";
private static final String SERVER = "server/" + HOST;
private static final String BACKEND = "backend/" + HOST;
private static final String USER = "user";
private static final char[] PASS = "password".toCharArray();
private static final String REALM = "REALM";
private static final int MSGSIZE = 1024;
public static void main(String[] args) throws Exception {
String HOST = "localhost";
String SERVER = "server/" + HOST;
String BACKEND = "backend/" + HOST;
String USER = "user";
char[] PASS = "password".toCharArray();
String REALM = "REALM";
Oid oid = new Oid("1.2.840.113554.1.2.2");
byte[] token, msg;
if (args.length == 0) {
System.setProperty("java.security.krb5.conf", CONF);
KDC kdc = KDC.create(REALM, HOST, 0, true);
kdc.addPrincipal(USER, PASS);
kdc.addPrincipalRandKey("krbtgt/" + REALM);
kdc.addPrincipalRandKey(SERVER);
kdc.addPrincipalRandKey(BACKEND);
switch (args[0]) {
case "launcher":
KDC kdc = KDC.create(REALM, HOST, 0, true);
try {
kdc.addPrincipal(USER, PASS);
kdc.addPrincipalRandKey("krbtgt/" + REALM);
kdc.addPrincipalRandKey(SERVER);
kdc.addPrincipalRandKey(BACKEND);
String cwd = System.getProperty("user.dir");
kdc.writeKtab(KTAB);
KDC.saveConfig(CONF, kdc, "forwardable = true");
// Native lib might do some name lookup
KDC.saveConfig(CONF, kdc,
"dns_lookup_kdc = no",
"ticket_lifetime = 1h",
"dns_lookup_realm = no",
"dns_canonicalize_hostname = false",
"forwardable = true");
System.setProperty("java.security.krb5.conf", CONF);
Config.refresh();
kdc.writeKtab(KTAB_S, false, SERVER);
kdc.writeKtab(KTAB_B, false, BACKEND);
Proc pc = Proc.create("BasicProc")
.args("client")
.prop("java.security.krb5.conf", CONF)
.prop("java.security.manager", "")
.perm(new java.util.PropertyPermission(
"sun.security.krb5.principal", "read"))
.perm(new javax.security.auth.AuthPermission(
"modifyPrincipals"))
.perm(new javax.security.auth.AuthPermission(
"modifyPrivateCredentials"))
.perm(new javax.security.auth.AuthPermission("doAs"))
.perm(new javax.security.auth.kerberos.ServicePermission(
"krbtgt/" + REALM + "@" + REALM, "initiate"))
.perm(new javax.security.auth.kerberos.ServicePermission(
"server/localhost@" + REALM, "initiate"))
.perm(new javax.security.auth.kerberos.DelegationPermission(
"\"server/localhost@" + REALM + "\" " +
"\"krbtgt/" + REALM + "@" + REALM + "\""))
.debug("C")
.start();
Proc ps = Proc.create("BasicProc")
.args("server")
.prop("java.security.krb5.conf", CONF)
.prop("java.security.manager", "")
.perm(new java.util.PropertyPermission(
"sun.security.krb5.principal", "read"))
.perm(new javax.security.auth.AuthPermission(
"modifyPrincipals"))
.perm(new javax.security.auth.AuthPermission(
"modifyPrivateCredentials"))
.perm(new javax.security.auth.AuthPermission("doAs"))
.perm(new PrivateCredentialPermission(
"javax.security.auth.kerberos.KeyTab * \"*\"",
"read"))
.perm(new javax.security.auth.kerberos.ServicePermission(
"server/localhost@" + REALM, "accept"))
.perm(new java.io.FilePermission(
cwd + File.separator + KTAB, "read"))
.perm(new javax.security.auth.kerberos.ServicePermission(
"backend/localhost@" + REALM, "initiate"))
.debug("S")
.start();
Proc pb = Proc.create("BasicProc")
.args("backend")
.prop("java.security.krb5.conf", CONF)
.prop("java.security.manager", "")
.perm(new java.util.PropertyPermission(
"sun.security.krb5.principal", "read"))
.perm(new javax.security.auth.AuthPermission(
"modifyPrincipals"))
.perm(new javax.security.auth.AuthPermission(
"modifyPrivateCredentials"))
.perm(new javax.security.auth.AuthPermission("doAs"))
.perm(new PrivateCredentialPermission(
"javax.security.auth.kerberos.KeyTab * \"*\"",
"read"))
.perm(new javax.security.auth.kerberos.ServicePermission(
"backend/localhost@" + REALM, "accept"))
.perm(new java.io.FilePermission(
cwd + File.separator + KTAB, "read"))
.debug("B")
.start();
String[] tmp = System.getProperty("native.krb5.libs", "j=")
.split(",");
// Client and server handshake
String token = pc.readData();
ps.println(token);
token = ps.readData();
pc.println(token);
// Server and backend handshake
token = ps.readData();
pb.println(token);
token = pb.readData();
ps.println(token);
// wrap/unwrap/getMic/verifyMic and plain text
token = ps.readData();
pb.println(token);
token = pb.readData();
ps.println(token);
token = pb.readData();
ps.println(token);
// Library paths. The 1st one is always null which means
// Java, "" means the default native lib.
String[] libs = new String[tmp.length];
if ((pc.waitFor() | ps.waitFor() | pb.waitFor()) != 0) {
throw new Exception();
}
} else if (args[0].equals("client")) {
Context c = Context.fromUserPass(USER, PASS, false);
c.startAsClient(SERVER, oid);
c.x().requestCredDeleg(true);
Proc.binOut(c.take(new byte[0]));
byte[] token = Proc.binIn();
c.take(token);
} else if (args[0].equals("server")) {
Context s = Context.fromUserKtab(SERVER, KTAB, true);
s.startAsServer(oid);
byte[] token = Proc.binIn();
token = s.take(token);
Proc.binOut(token);
Context s2 = s.delegated();
s2.startAsClient(BACKEND, oid);
Proc.binOut(s2.take(new byte[0]));
token = Proc.binIn();
s2.take(token);
byte[] msg = "Hello".getBytes();
Proc.binOut(s2.wrap(msg, true));
s2.verifyMic(Proc.binIn(), msg);
String in = Proc.textIn();
if (!in.equals("Hello")) {
throw new Exception();
}
} else if (args[0].equals("backend")) {
Context b = Context.fromUserKtab(BACKEND, KTAB, true);
b.startAsServer(oid);
byte[] token = Proc.binIn();
Proc.binOut(b.take(token));
byte[] msg = b.unwrap(Proc.binIn(), true);
Proc.binOut(b.getMic(msg));
Proc.textOut(new String(msg));
// Names for each lib above. Use in file names.
String[] names = new String[tmp.length];
boolean hasNative = false;
for (int i = 0; i < tmp.length; i++) {
if (tmp[i].isEmpty()) {
throw new Exception("Invalid native.krb5.libs");
}
String[] pair = tmp[i].split("=", 2);
names[i] = pair[0];
if (!pair[0].equals("j")) {
libs[i] = pair.length > 1 ? pair[1] : "";
hasNative = true;
}
}
if (hasNative) {
kdc.kinit(USER, "base.ccache");
}
// Try the same lib first
for (int i = 0; i < libs.length; i++) {
once(names[i] + names[i] + names[i],
libs[i], libs[i], libs[i]);
}
for (int i = 0; i < libs.length; i++) {
for (int j = 0; j < libs.length; j++) {
for (int k = 0; k < libs.length; k++) {
if (i != j || i != k) {
once(names[i] + names[j] + names[k],
libs[i], libs[j], libs[k]);
}
}
}
}
} finally {
kdc.terminate();
}
break;
case "client":
Context c = args[1].equals("n") ?
Context.fromThinAir() :
Context.fromUserPass(USER, PASS, false);
c.startAsClient(SERVER, oid);
c.x().requestCredDeleg(true);
Proc.binOut(c.take(new byte[0])); // AP-REQ
token = Proc.binIn(); // AP-REP
c.take(token);
break;
case "server":
Context s = args[1].equals("n") ?
Context.fromThinAir() :
Context.fromUserKtab(SERVER, KTAB_S, true);
s.startAsServer(oid);
token = Proc.binIn(); // AP-REQ
token = s.take(token);
Proc.binOut(token); // AP-REP
Context s2 = s.delegated();
s2.startAsClient(BACKEND, oid);
Proc.binOut(s2.take(new byte[0])); // AP-REQ
token = Proc.binIn();
s2.take(token); // AP-REP
Random r = new Random();
msg = new byte[MSGSIZE];
r.nextBytes(msg);
Proc.binOut(s2.wrap(msg, true)); // enc1
Proc.binOut(s2.wrap(msg, true)); // enc2
Proc.binOut(s2.wrap(msg, true)); // enc3
s2.verifyMic(Proc.binIn(), msg); // mic
byte[] msg2 = Proc.binIn(); // msg
if (!Arrays.equals(msg, msg2)) {
throw new Exception("diff msg");
}
break;
case "backend":
Context b = args[1].equals("n") ?
Context.fromThinAir() :
Context.fromUserKtab(BACKEND, KTAB_B, true);
b.startAsServer(oid);
token = Proc.binIn(); // AP-REQ
Proc.binOut(b.take(token)); // AP-REP
msg = b.unwrap(Proc.binIn(), true); // enc1
if (!Arrays.equals(msg, b.unwrap(Proc.binIn(), true))) { // enc2
throw new Exception("diff msg");
}
if (!Arrays.equals(msg, b.unwrap(Proc.binIn(), true))) { // enc3
throw new Exception("diff msg");
}
Proc.binOut(b.getMic(msg)); // mic
Proc.binOut(msg); // msg
break;
}
}
// create a native server
private static Proc ns(Proc p) throws Exception {
return p
.env("KRB5_CONFIG", CONF)
.env("KRB5_KTNAME", KTAB)
.prop("sun.security.jgss.native", "true")
.prop("javax.security.auth.useSubjectCredsOnly", "false")
.prop("sun.security.nativegss.debug", "true");
/**
* One test run.
*
* @param label test label
* @param lc lib of client
* @param ls lib of server
* @param lb lib of backend
*/
private static void once(String label, String lc, String ls, String lb)
throws Exception {
Proc pc = proc(lc)
.args("client", lc == null ? "j" : "n")
.perm(new javax.security.auth.kerberos.ServicePermission(
"krbtgt/" + REALM + "@" + REALM, "initiate"))
.perm(new javax.security.auth.kerberos.ServicePermission(
SERVER + "@" + REALM, "initiate"))
.perm(new javax.security.auth.kerberos.DelegationPermission(
"\"" + SERVER + "@" + REALM + "\" " +
"\"krbtgt/" + REALM + "@" + REALM + "\""))
.debug(label + "-C");
if (lc == null) {
// for Krb5LoginModule::promptForName
pc.perm(new PropertyPermission("user.name", "read"));
} else {
Files.copy(Paths.get("base.ccache"), Paths.get(label + ".ccache"));
Files.setPosixFilePermissions(Paths.get(label + ".ccache"),
Set.of(PosixFilePermission.OWNER_READ,
PosixFilePermission.OWNER_WRITE));
pc.env("KRB5CCNAME", label + ".ccache");
// Do not try system ktab if ccache fails
pc.env("KRB5_KTNAME", "none");
}
pc.start();
Proc ps = proc(ls)
.args("server", ls == null ? "j" : "n")
.perm(new javax.security.auth.kerberos.ServicePermission(
SERVER + "@" + REALM, "accept"))
.perm(new javax.security.auth.kerberos.ServicePermission(
BACKEND + "@" + REALM, "initiate"))
.debug(label + "-S");
if (ls == null) {
ps.perm(new PrivateCredentialPermission(
"javax.security.auth.kerberos.KeyTab * \"*\"", "read"))
.perm(new java.io.FilePermission(KTAB_S, "read"));
} else {
ps.env("KRB5_KTNAME", KTAB_S);
}
ps.start();
Proc pb = proc(lb)
.args("backend", lb == null ? "j" : "n")
.perm(new javax.security.auth.kerberos.ServicePermission(
BACKEND + "@" + REALM, "accept"))
.debug(label + "-B");
if (lb == null) {
pb.perm(new PrivateCredentialPermission(
"javax.security.auth.kerberos.KeyTab * \"*\"", "read"))
.perm(new java.io.FilePermission(KTAB_B, "read"));
} else {
pb.env("KRB5_KTNAME", KTAB_B);
}
pb.start();
// Client and server handshake
ps.println(pc.readData());
pc.println(ps.readData());
// Server and backend handshake
pb.println(ps.readData());
ps.println(pb.readData());
// wrap/unwrap/getMic/verifyMic and plain text
pb.println(ps.readData());
pb.println(ps.readData());
pb.println(ps.readData());
ps.println(pb.readData());
ps.println(pb.readData());
if ((pc.waitFor() | ps.waitFor() | pb.waitFor()) != 0) {
throw new Exception("Process failed");
}
}
/**
* A Proc for a child process.
*
* @param lib the library. Null is Java. "" is default native lib.
*/
private static Proc proc(String lib) throws Exception {
Proc p = Proc.create("BasicProc")
.prop("java.security.manager", "")
.perm(new javax.security.auth.AuthPermission("doAs"));
if (lib != null) {
p.env("KRB5_CONFIG", CONF)
.env("KRB5_TRACE", "/dev/stderr")
.prop("sun.security.jgss.native", "true")
.prop("sun.security.jgss.lib", lib)
.prop("javax.security.auth.useSubjectCredsOnly", "false")
.prop("sun.security.nativegss.debug", "true");
int pos = lib.lastIndexOf('/');
if (pos > 0) {
p.env("LD_LIBRARY_PATH", lib.substring(0, pos));
p.env("DYLD_LIBRARY_PATH", lib.substring(0, pos));
}
} else {
p.perm(new java.util.PropertyPermission(
"sun.security.krb5.principal", "read"))
// For Krb5LoginModule::login.
.perm(new javax.security.auth.AuthPermission(
"modifyPrincipals"))
.perm(new javax.security.auth.AuthPermission(
"modifyPrivateCredentials"))
.prop("sun.security.krb5.debug", "true")
.prop("java.security.krb5.conf", CONF);
}
return p;
}
}

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2008, 2013, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2008, 2017, 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
@ -23,6 +23,7 @@
import com.sun.security.auth.module.Krb5LoginModule;
import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.security.PrivilegedActionException;
@ -31,6 +32,11 @@ import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;
import javax.security.auth.Subject;
import javax.security.auth.callback.Callback;
import javax.security.auth.callback.CallbackHandler;
import javax.security.auth.callback.NameCallback;
import javax.security.auth.callback.PasswordCallback;
import javax.security.auth.callback.UnsupportedCallbackException;
import javax.security.auth.kerberos.KerberosKey;
import javax.security.auth.kerberos.KerberosTicket;
import javax.security.auth.login.LoginContext;
@ -41,9 +47,14 @@ import org.ietf.jgss.GSSManager;
import org.ietf.jgss.GSSName;
import org.ietf.jgss.MessageProp;
import org.ietf.jgss.Oid;
import sun.security.jgss.krb5.Krb5Util;
import sun.security.krb5.Credentials;
import sun.security.krb5.internal.ccache.CredentialsCache;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.security.Principal;
import java.util.Set;
/**
* Context of a JGSS subject, encapsulating Subject and GSSContext.
@ -149,24 +160,36 @@ public class Context {
Map<String, String> map = new HashMap<>();
Map<String, Object> shared = new HashMap<>();
if (storeKey) {
map.put("storeKey", "true");
}
if (pass != null) {
map.put("useFirstPass", "true");
shared.put("javax.security.auth.login.name", user);
shared.put("javax.security.auth.login.password", pass);
krb5.initialize(out.s, new CallbackHandler() {
@Override
public void handle(Callback[] callbacks)
throws IOException, UnsupportedCallbackException {
for (Callback cb: callbacks) {
if (cb instanceof NameCallback) {
((NameCallback)cb).setName(user);
} else if (cb instanceof PasswordCallback) {
((PasswordCallback)cb).setPassword(pass);
}
}
}
}, shared, map);
} else {
map.put("doNotPrompt", "true");
map.put("useTicketCache", "true");
if (user != null) {
map.put("principal", user);
}
}
if (storeKey) {
map.put("storeKey", "true");
krb5.initialize(out.s, null, shared, map);
}
krb5.initialize(out.s, null, shared, map);
krb5.login();
krb5.commit();
return out;
}
@ -529,9 +552,23 @@ public class Context {
* @param s2 the receiver
* @throws java.lang.Exception If anything goes wrong
*/
static public void transmit(final String message, final Context s1,
static public void transmit(String message, final Context s1,
final Context s2) throws Exception {
transmit(message.getBytes(), s1, s2);
}
/**
* Transmits a message from one Context to another. The sender wraps the
* message and sends it to the receiver. The receiver unwraps it, creates
* a MIC of the clear text and sends it back to the sender. The sender
* verifies the MIC against the message sent earlier.
* @param messageBytes the message
* @param s1 the sender
* @param s2 the receiver
* @throws java.lang.Exception If anything goes wrong
*/
static public void transmit(byte[] messageBytes, final Context s1,
final Context s2) throws Exception {
final byte[] messageBytes = message.getBytes();
System.out.printf("-------------------- TRANSMIT from %s to %s------------------------\n",
s1.name, s2.name);
byte[] wrapped = s1.wrap(messageBytes, true);
@ -618,6 +655,32 @@ public class Context {
}, in);
}
/**
* Saves the tickets to a ccache file.
*
* @param file pathname of the ccache file
* @return true if created, false otherwise.
*/
public boolean ccache(String file) throws Exception {
Set<KerberosTicket> tickets
= s.getPrivateCredentials(KerberosTicket.class);
if (tickets != null && !tickets.isEmpty()) {
CredentialsCache cc = null;
for (KerberosTicket t : tickets) {
Credentials cred = Krb5Util.ticketToCreds(t);
if (cc == null) {
cc = CredentialsCache.create(cred.getClient(), file);
}
cc.update(cred.toCCacheCreds());
}
if (cc != null) {
cc.save();
return true;
}
}
return false;
}
/**
* Handshake (security context establishment process) between two Contexts
* @param c the initiator

View file

@ -0,0 +1,50 @@
/*
* Copyright (c) 2017, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* 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).
*
* 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.
*
* 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.
*/
/*
* @test
* @bug 8186831
* @summary Kerberos ignores PA-DATA with a non-null s2kparams
* @compile -XDignore.symbol.file DiffSaltParams.java
* @run main/othervm -Dsun.security.krb5.debug=true DiffSaltParams
*/
public class DiffSaltParams {
public static void main(String[] args) throws Exception {
OneKDC kdc = new OneKDC(null).writeJAASConf();
kdc.addPrincipal("user1", "user1pass".toCharArray(),
"hello", new byte[]{0, 0, 1, 0});
kdc.addPrincipal("user2", "user2pass".toCharArray(),
"hello", null);
kdc.addPrincipal("user3", "user3pass".toCharArray(),
null, new byte[]{0, 0, 1, 0});
kdc.addPrincipal("user4", "user4pass".toCharArray());
Context.fromUserPass("user1", "user1pass".toCharArray(), true);
Context.fromUserPass("user2", "user2pass".toCharArray(), true);
Context.fromUserPass("user3", "user3pass".toCharArray(), true);
Context.fromUserPass("user4", "user4pass".toCharArray(), true);
}
}

View file

@ -28,6 +28,7 @@
* java.security.jgss/sun.security.krb5.internal:+open
* java.security.jgss/sun.security.jgss
* java.security.jgss/sun.security.krb5:+open
* java.security.jgss/sun.security.jgss.krb5
* java.security.jgss/sun.security.krb5.internal.ccache
* java.security.jgss/sun.security.krb5.internal.crypto
* java.security.jgss/sun.security.krb5.internal.ktab

View file

@ -27,11 +27,12 @@ import java.lang.reflect.InvocationTargetException;
import java.net.*;
import java.io.*;
import java.lang.reflect.Method;
import java.security.SecureRandom;
import java.time.Instant;
import java.time.temporal.ChronoUnit;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.*;
import java.util.concurrent.*;
import java.util.stream.Collectors;
import java.util.stream.Stream;
import sun.security.krb5.*;
import sun.security.krb5.internal.*;
@ -45,6 +46,11 @@ import sun.security.util.DerValue;
/**
* A KDC server.
*
* Note: By setting the system property native.kdc.path to a native
* krb5 installation, this class starts a native KDC with the
* given realm and host. It can also add new principals and save keytabs.
* Other features might not be available.
* <p>
* Features:
* <ol>
@ -125,19 +131,38 @@ public class KDC {
public static final int DEFAULT_LIFETIME = 39600;
public static final int DEFAULT_RENEWTIME = 86400;
public static String NOT_EXISTING_HOST = "not.existing.host";
public static final String NOT_EXISTING_HOST = "not.existing.host";
// What etypes the KDC supports. Comma-separated strings. Null for all.
// Please note native KDCs might use different names.
private static final String SUPPORTED_ETYPES
= System.getProperty("kdc.supported.enctypes");
// The native KDC
private final NativeKdc nativeKdc;
// The native KDC process
private Process kdcProc = null;
// Under the hood.
// The random generator to generate random keys (including session keys)
private static SecureRandom secureRandom = new SecureRandom();
// Principal db. principal -> pass. A case-insensitive TreeMap is used
// so that even if the client provides a name with different case, the KDC
// can still locate the principal and give back correct salt.
private TreeMap<String,char[]> passwords = new TreeMap<>
(String.CASE_INSENSITIVE_ORDER);
// Non default salts. Precisely, there should be different salts for
// different etypes, pretend they are the same at the moment.
private TreeMap<String,String> salts = new TreeMap<>
(String.CASE_INSENSITIVE_ORDER);
// Non default s2kparams for newer etypes. Precisely, there should be
// different s2kparams for different etypes, pretend they are the same
// at the moment.
private TreeMap<String,byte[]> s2kparamses = new TreeMap<>
(String.CASE_INSENSITIVE_ORDER);
// Realm name
private String realm;
// KDC
@ -218,7 +243,8 @@ public class KDC {
static {
if (System.getProperty("jdk.net.hosts.file") == null) {
String hostsFileName = System.getProperty("test.src", ".") + "/TestHosts";
String hostsFileName
= System.getProperty("test.src", ".") + "/TestHosts";
System.setProperty("jdk.net.hosts.file", hostsFileName);
}
}
@ -262,7 +288,8 @@ public class KDC {
* @return the running KDC instance
* @throws java.io.IOException for any socket creation error
*/
public static KDC create(String realm, String kdc, int port, boolean asDaemon) throws IOException {
public static KDC create(String realm, String kdc, int port,
boolean asDaemon) throws IOException {
return new KDC(realm, kdc, port, asDaemon);
}
@ -302,26 +329,38 @@ public class KDC {
*/
public void writeKtab(String tab, boolean append, String... names)
throws IOException, KrbException {
KeyTab ktab = append ? KeyTab.getInstance(tab) : KeyTab.create(tab);
KeyTab ktab = null;
if (nativeKdc == null) {
ktab = append ? KeyTab.getInstance(tab) : KeyTab.create(tab);
}
Iterable<String> entries =
(names.length != 0) ? Arrays.asList(names): passwords.keySet();
for (String name : entries) {
char[] pass = passwords.get(name);
int kvno = 0;
if (Character.isDigit(pass[pass.length-1])) {
kvno = pass[pass.length-1] - '0';
if (name.indexOf('@') < 0) {
name = name + "@" + realm;
}
PrincipalName pn = new PrincipalName(name,
if (nativeKdc == null) {
char[] pass = passwords.get(name);
int kvno = 0;
if (Character.isDigit(pass[pass.length - 1])) {
kvno = pass[pass.length - 1] - '0';
}
PrincipalName pn = new PrincipalName(name,
name.indexOf('/') < 0 ?
PrincipalName.KRB_NT_UNKNOWN :
PrincipalName.KRB_NT_SRV_HST);
ktab.addEntry(pn,
PrincipalName.KRB_NT_UNKNOWN :
PrincipalName.KRB_NT_SRV_HST);
ktab.addEntry(pn,
getSalt(pn),
pass,
kvno,
true);
} else {
nativeKdc.ktadd(name, tab);
}
}
if (nativeKdc == null) {
ktab.save();
}
ktab.save();
}
/**
@ -367,10 +406,36 @@ public class KDC {
* @param pass the password for the principal
*/
public void addPrincipal(String user, char[] pass) {
addPrincipal(user, pass, null, null);
}
/**
* Adds a new principal to this realm with a given password.
* @param user the principal's name. For a service principal, use the
* form of host/f.q.d.n
* @param pass the password for the principal
* @param salt the salt, or null if a default value will be used
* @param s2kparams the s2kparams, or null if a default value will be used
*/
public void addPrincipal(
String user, char[] pass, String salt, byte[] s2kparams) {
if (user.indexOf('@') < 0) {
user = user + "@" + realm;
}
passwords.put(user, pass);
if (nativeKdc != null) {
if (!user.equals("krbtgt/" + realm)) {
nativeKdc.addPrincipal(user, new String(pass));
}
passwords.put(user, new char[0]);
} else {
passwords.put(user, pass);
if (salt != null) {
salts.put(user, salt);
}
if (s2kparams != null) {
s2kparamses.put(user, s2kparams);
}
}
}
/**
@ -466,12 +531,11 @@ public class KDC {
*/
public static void saveConfig(String file, KDC kdc, Object... more)
throws IOException {
File f = new File(file);
StringBuffer sb = new StringBuffer();
sb.append("[libdefaults]\ndefault_realm = ");
sb.append(kdc.realm);
sb.append("\n");
for (Object o: more) {
for (Object o : more) {
if (o instanceof String) {
sb.append(o);
sb.append("\n");
@ -479,14 +543,12 @@ public class KDC {
}
sb.append("\n[realms]\n");
sb.append(kdc.realmLine());
for (Object o: more) {
for (Object o : more) {
if (o instanceof KDC) {
sb.append(((KDC)o).realmLine());
sb.append(((KDC) o).realmLine());
}
}
FileOutputStream fos = new FileOutputStream(f);
fos.write(sb.toString().getBytes());
fos.close();
Files.write(Paths.get(file), sb.toString().getBytes());
}
/**
@ -506,6 +568,7 @@ public class KDC {
private KDC(String realm, String kdc) {
this.realm = realm;
this.kdc = kdc;
this.nativeKdc = null;
}
/**
@ -513,7 +576,9 @@ public class KDC {
*/
protected KDC(String realm, String kdc, int port, boolean asDaemon)
throws IOException {
this(realm, kdc);
this.realm = realm;
this.kdc = kdc;
this.nativeKdc = NativeKdc.get(this);
startServer(port, asDaemon);
}
/**
@ -522,8 +587,9 @@ public class KDC {
*/
private static char[] randomPassword() {
char[] pass = new char[32];
Random r = new Random();
for (int i=0; i<31; i++)
pass[i] = (char)secureRandom.nextInt();
pass[i] = (char)('a' + r.nextInt(26));
// The last char cannot be a number, otherwise, keyForUser()
// believes it's a sign of kvno
pass[31] = 'Z';
@ -585,6 +651,9 @@ public class KDC {
if (p.getRealmString() == null) {
pn = pn + "@" + getRealm();
}
if (salts.containsKey(pn)) {
return salts.get(pn);
}
if (passwords.containsKey(pn)) {
try {
// Find the principal name with correct case.
@ -601,6 +670,29 @@ public class KDC {
return s;
}
/**
* Returns the s2kparams for the principal given the etype.
* @param p principal
* @param etype encryption type
* @return the s2kparams, might be null
*/
protected byte[] getParams(PrincipalName p, int etype) {
switch (etype) {
case EncryptedData.ETYPE_AES128_CTS_HMAC_SHA1_96:
case EncryptedData.ETYPE_AES256_CTS_HMAC_SHA1_96:
String pn = p.toString();
if (p.getRealmString() == null) {
pn = pn + "@" + getRealm();
}
if (s2kparamses.containsKey(pn)) {
return s2kparamses.get(pn);
}
return new byte[] {0, 0, 0x10, 0};
default:
return null;
}
}
/**
* Returns the key for a given principal of the given encryption type
* @param p the principal
@ -624,7 +716,7 @@ public class KDC {
}
}
return new EncryptionKey(EncryptionKeyDotStringToKey(
getPassword(p, server), getSalt(p), null, etype),
getPassword(p, server), getSalt(p), getParams(p, etype), etype),
etype, kvno);
} catch (KrbException ke) {
throw ke;
@ -633,6 +725,15 @@ public class KDC {
}
}
/**
* Returns a KerberosTime.
*
* @param offset offset from NOW in milliseconds
*/
private static KerberosTime timeFor(long offset) {
return new KerberosTime(new Date().getTime() + offset);
}
/**
* Processes an incoming request and generates a response.
* @param in the request
@ -664,7 +765,10 @@ public class KDC {
" sends TGS-REQ for " +
service + ", " + tgsReq.reqBody.kdcOptions);
KDCReqBody body = tgsReq.reqBody;
int[] eTypes = KDCReqBodyDotEType(body);
int[] eTypes = filterSupported(KDCReqBodyDotEType(body));
if (eTypes.length == 0) {
throw new KrbException(Krb5.KDC_ERR_ETYPE_NOSUPP);
}
int e2 = eTypes[0]; // etype for outgoing session key
int e3 = eTypes[0]; // etype for outgoing ticket
@ -701,13 +805,14 @@ public class KDC {
PAForUserEnc p4u = new PAForUserEnc(
new DerValue(pa.getValue()), null);
forUserCName = p4u.name;
System.out.println(realm + "> presenting a PA_FOR_USER "
System.out.println(realm + "> See PA_FOR_USER "
+ " in the name of " + p4u.name);
}
}
}
if (forUserCName != null) {
List<String> names = (List<String>)options.get(Option.ALLOW_S4U2SELF);
List<String> names = (List<String>)
options.get(Option.ALLOW_S4U2SELF);
if (!names.contains(cname.toString())) {
// Mimic the normal KDC behavior. When a server is not
// allowed to send S4U2self, do not send an error.
@ -728,11 +833,15 @@ public class KDC {
EncryptionKey key = generateRandomKey(e2);
// Check time, TODO
KerberosTime from = body.from;
KerberosTime till = body.till;
if (from == null || from.isZero()) {
from = timeFor(0);
}
if (till == null) {
throw new KrbException(Krb5.KDC_ERR_NEVER_VALID); // TODO
} else if (till.isZero()) {
till = new KerberosTime(new Date().getTime() + 1000 * DEFAULT_LIFETIME);
till = timeFor(1000 * DEFAULT_LIFETIME);
}
boolean[] bFlags = new boolean[Krb5.TKT_OPTS_MAX+1];
@ -758,7 +867,7 @@ public class KDC {
}
if (body.kdcOptions.get(KDCOptions.RENEWABLE)) {
bFlags[Krb5.TKT_OPTS_RENEWABLE] = true;
//renew = new KerberosTime(new Date().getTime() + 1000 * 3600 * 24 * 7);
//renew = timeFor(1000 * 3600 * 24 * 7);
}
if (body.kdcOptions.get(KDCOptions.PROXIABLE)) {
bFlags[Krb5.TKT_OPTS_PROXIABLE] = true;
@ -777,7 +886,8 @@ public class KDC {
Map<String,List<String>> map = (Map<String,List<String>>)
options.get(Option.ALLOW_S4U2PROXY);
Ticket second = KDCReqBodyDotFirstAdditionalTicket(body);
EncryptionKey key2 = keyForUser(second.sname, second.encPart.getEType(), true);
EncryptionKey key2 = keyForUser(
second.sname, second.encPart.getEType(), true);
byte[] bb = second.encPart.decrypt(key2, KeyUsage.KU_TICKET);
DerInputStream derIn = new DerInputStream(bb);
DerValue der = derIn.getDerValue();
@ -827,8 +937,8 @@ public class KDC {
key,
cname,
new TransitedEncoding(1, new byte[0]), // TODO
new KerberosTime(new Date()),
body.from,
timeFor(0),
from,
till, renewTill,
body.addresses != null ? body.addresses
: etp.caddr,
@ -845,20 +955,21 @@ public class KDC {
);
EncTGSRepPart enc_part = new EncTGSRepPart(
key,
new LastReq(new LastReqEntry[]{
new LastReqEntry(0, new KerberosTime(new Date().getTime() - 10000))
new LastReq(new LastReqEntry[] {
new LastReqEntry(0, timeFor(-10000))
}),
body.getNonce(), // TODO: detect replay
new KerberosTime(new Date().getTime() + 1000 * 3600 * 24),
timeFor(1000 * 3600 * 24),
// Next 5 and last MUST be same with ticket
tFlags,
new KerberosTime(new Date()),
body.from,
timeFor(0),
from,
till, renewTill,
service,
body.addresses
);
EncryptedData edata = new EncryptedData(ckey, enc_part.asn1Encode(), KeyUsage.KU_ENC_TGS_REP_PART_SESSKEY);
EncryptedData edata = new EncryptedData(ckey, enc_part.asn1Encode(),
KeyUsage.KU_ENC_TGS_REP_PART_SESSKEY);
TGSRep tgsRep = new TGSRep(null,
cname,
t,
@ -879,7 +990,7 @@ public class KDC {
+ " " +ke.returnCodeMessage());
if (kerr == null) {
kerr = new KRBError(null, null, null,
new KerberosTime(new Date()),
timeFor(0),
0,
ke.returnCode(),
body.cname,
@ -915,16 +1026,11 @@ public class KDC {
KDCReqBody body = asReq.reqBody;
eTypes = KDCReqBodyDotEType(body);
int eType = eTypes[0];
// Maybe server does not support aes256, but a kinit does
if (!EType.isSupported(eType)) {
if (eTypes.length < 2) {
throw new KrbException(Krb5.KDC_ERR_ETYPE_NOSUPP);
}
eType = eTypes[1];
eTypes = filterSupported(KDCReqBodyDotEType(body));
if (eTypes.length == 0) {
throw new KrbException(Krb5.KDC_ERR_ETYPE_NOSUPP);
}
int eType = eTypes[0];
EncryptionKey ckey = keyForUser(body.cname, eType, false);
EncryptionKey skey = keyForUser(service, eType, true);
@ -953,31 +1059,32 @@ public class KDC {
// Session key
EncryptionKey key = generateRandomKey(eType);
// Check time, TODO
KerberosTime from = body.from;
KerberosTime till = body.till;
KerberosTime rtime = body.rtime;
if (from == null || from.isZero()) {
from = timeFor(0);
}
if (till == null) {
throw new KrbException(Krb5.KDC_ERR_NEVER_VALID); // TODO
} else if (till.isZero()) {
till = new KerberosTime(
new Date().getTime() + 1000 * DEFAULT_LIFETIME);
} else if (till.greaterThan(new KerberosTime(Instant.now()
.plus(1, ChronoUnit.DAYS)))) {
till = timeFor(1000 * DEFAULT_LIFETIME);
} else if (till.greaterThan(timeFor(24 * 3600 * 1000))) {
// If till is more than 1 day later, make it renewable
till = new KerberosTime(
new Date().getTime() + 1000 * DEFAULT_LIFETIME);
till = timeFor(1000 * DEFAULT_LIFETIME);
body.kdcOptions.set(KDCOptions.RENEWABLE, true);
if (rtime == null) rtime = till;
}
if (rtime == null && body.kdcOptions.get(KDCOptions.RENEWABLE)) {
rtime = new KerberosTime(
new Date().getTime() + 1000 * DEFAULT_RENEWTIME);
rtime = timeFor(1000 * DEFAULT_RENEWTIME);
}
//body.from
boolean[] bFlags = new boolean[Krb5.TKT_OPTS_MAX+1];
if (body.kdcOptions.get(KDCOptions.FORWARDABLE)) {
List<String> sensitives = (List<String>)
options.get(Option.SENSITIVE_ACCOUNTS);
if (sensitives != null && sensitives.contains(body.cname.toString())) {
if (sensitives != null
&& sensitives.contains(body.cname.toString())) {
// Cannot make FORWARDABLE
} else {
bFlags[Krb5.TKT_OPTS_FORWARDABLE] = true;
@ -985,7 +1092,7 @@ public class KDC {
}
if (body.kdcOptions.get(KDCOptions.RENEWABLE)) {
bFlags[Krb5.TKT_OPTS_RENEWABLE] = true;
//renew = new KerberosTime(new Date().getTime() + 1000 * 3600 * 24 * 7);
//renew = timeFor(1000 * 3600 * 24 * 7);
}
if (body.kdcOptions.get(KDCOptions.PROXIABLE)) {
bFlags[Krb5.TKT_OPTS_PROXIABLE] = true;
@ -1007,7 +1114,8 @@ public class KDC {
pas2 = new DerValue[] {
new DerValue(new ETypeInfo2(1, null, null).asn1Encode()),
new DerValue(new ETypeInfo2(1, "", null).asn1Encode()),
new DerValue(new ETypeInfo2(1, realm, new byte[]{1}).asn1Encode()),
new DerValue(new ETypeInfo2(
1, realm, new byte[]{1}).asn1Encode()),
};
pas = new DerValue[] {
new DerValue(new ETypeInfo(1, null).asn1Encode()),
@ -1017,7 +1125,8 @@ public class KDC {
break;
case 2: // we still reject non-null s2kparams and prefer E2 over E
pas2 = new DerValue[] {
new DerValue(new ETypeInfo2(1, realm, new byte[]{1}).asn1Encode()),
new DerValue(new ETypeInfo2(
1, realm, new byte[]{1}).asn1Encode()),
new DerValue(new ETypeInfo2(1, null, null).asn1Encode()),
new DerValue(new ETypeInfo2(1, "", null).asn1Encode()),
};
@ -1068,7 +1177,7 @@ public class KDC {
epas[i],
epas[i] == EncryptedData.ETYPE_ARCFOUR_HMAC ?
null : getSalt(body.cname),
null).asn1Encode());
getParams(body.cname, epas[i])).asn1Encode());
}
boolean allOld = true;
for (int i: eTypes) {
@ -1110,11 +1219,15 @@ public class KDC {
}
} else {
try {
EncryptedData data = newEncryptedData(new DerValue(inPAs[0].getValue()));
EncryptionKey pakey = keyForUser(body.cname, data.getEType(), false);
EncryptedData data = newEncryptedData(
new DerValue(inPAs[0].getValue()));
EncryptionKey pakey
= keyForUser(body.cname, data.getEType(), false);
data.decrypt(pakey, KeyUsage.KU_PA_ENC_TS);
} catch (Exception e) {
throw new KrbException(Krb5.KDC_ERR_PREAUTH_FAILED);
KrbException ke = new KrbException(Krb5.KDC_ERR_PREAUTH_FAILED);
ke.initCause(e);
throw ke;
}
bFlags[Krb5.TKT_OPTS_PRE_AUTHENT] = true;
}
@ -1125,8 +1238,8 @@ public class KDC {
key,
body.cname,
new TransitedEncoding(1, new byte[0]),
new KerberosTime(new Date()),
body.from,
timeFor(0),
from,
till, rtime,
body.addresses,
null);
@ -1137,19 +1250,20 @@ public class KDC {
EncASRepPart enc_part = new EncASRepPart(
key,
new LastReq(new LastReqEntry[]{
new LastReqEntry(0, new KerberosTime(new Date().getTime() - 10000))
new LastReqEntry(0, timeFor(-10000))
}),
body.getNonce(), // TODO: detect replay?
new KerberosTime(new Date().getTime() + 1000 * 3600 * 24),
timeFor(1000 * 3600 * 24),
// Next 5 and last MUST be same with ticket
tFlags,
new KerberosTime(new Date()),
body.from,
timeFor(0),
from,
till, rtime,
service,
body.addresses
);
EncryptedData edata = new EncryptedData(ckey, enc_part.asn1Encode(), KeyUsage.KU_ENC_AS_REP_PART);
EncryptedData edata = new EncryptedData(ckey, enc_part.asn1Encode(),
KeyUsage.KU_ENC_AS_REP_PART);
ASRep asRep = new ASRep(
outPAs.toArray(new PAData[outPAs.size()]),
body.cname,
@ -1204,7 +1318,7 @@ public class KDC {
eData = temp.toByteArray();
}
kerr = new KRBError(null, null, null,
new KerberosTime(new Date()),
timeFor(0),
0,
ke.returnCode(),
body.cname,
@ -1216,6 +1330,35 @@ public class KDC {
}
}
private int[] filterSupported(int[] input) {
int count = 0;
for (int i = 0; i < input.length; i++) {
if (!EType.isSupported(input[i])) {
continue;
}
if (SUPPORTED_ETYPES != null) {
boolean supported = false;
for (String se : SUPPORTED_ETYPES.split(",")) {
if (Config.getType(se) == input[i]) {
supported = true;
break;
}
}
if (!supported) {
continue;
}
}
if (count != i) {
input[count] = input[i];
}
count++;
}
if (count != input.length) {
input = Arrays.copyOf(input, count);
}
return input;
}
/**
* Generates a line for a KDC to put inside [realms] of krb5.conf
* @return REALM.NAME = { kdc = host:port etc }
@ -1240,6 +1383,20 @@ public class KDC {
* @throws java.io.IOException for any communication error
*/
protected void startServer(int port, boolean asDaemon) throws IOException {
if (nativeKdc != null) {
startNativeServer(port, asDaemon);
} else {
startJavaServer(port, asDaemon);
}
}
private void startNativeServer(int port, boolean asDaemon) throws IOException {
nativeKdc.prepare();
nativeKdc.init();
kdcProc = nativeKdc.kdc();
}
private void startJavaServer(int port, boolean asDaemon) throws IOException {
if (port > 0) {
u1 = new DatagramSocket(port, InetAddress.getByName("127.0.0.1"));
t1 = new ServerSocket(port);
@ -1336,19 +1493,37 @@ public class KDC {
}
}
public void kinit(String user, String ccache) throws Exception {
if (user.indexOf('@') < 0) {
user = user + "@" + realm;
}
if (nativeKdc != null) {
nativeKdc.kinit(user, ccache);
} else {
Context.fromUserPass(user, passwords.get(user), false)
.ccache(ccache);
}
}
boolean isReady() {
return udpConsumerReady && tcpConsumerReady && dispatcherReady;
}
public void terminate() {
try {
thread1.stop();
thread2.stop();
thread3.stop();
u1.close();
t1.close();
} catch (Exception e) {
// OK
if (nativeKdc != null) {
System.out.println("Killing kdc...");
kdcProc.destroyForcibly();
System.out.println("Done");
} else {
try {
thread1.stop();
thread2.stop();
thread3.stop();
u1.close();
t1.close();
} catch (Exception e) {
// OK
}
}
}
@ -1463,6 +1638,266 @@ public class KDC {
}
}
/**
* A native KDC using the binaries in nativePath. Attention:
* this is using binaries, not an existing KDC instance.
* An implementation of this takes care of configuration,
* principal db managing and KDC startup.
*/
static abstract class NativeKdc {
protected Map<String,String> env;
protected String nativePath;
protected String base;
protected String realm;
protected int port;
NativeKdc(String nativePath, KDC kdc) {
if (kdc.port == 0) {
kdc.port = 8000 + new java.util.Random().nextInt(10000);
}
this.nativePath = nativePath;
this.realm = kdc.realm;
this.port = kdc.port;
this.base = Paths.get("" + port).toAbsolutePath().toString();
}
// Add a new principal
abstract void addPrincipal(String user, String pass);
// Add a keytab entry
abstract void ktadd(String user, String ktab);
// Initialize KDC
abstract void init();
// Start kdc
abstract Process kdc();
// Configuration
abstract void prepare();
// Fill ccache
abstract void kinit(String user, String ccache);
static NativeKdc get(KDC kdc) {
String prop = System.getProperty("native.kdc.path");
if (prop == null) {
return null;
} else if (Files.exists(Paths.get(prop, "sbin/krb5kdc"))) {
return new MIT(true, prop, kdc);
} else if (Files.exists(Paths.get(prop, "kdc/krb5kdc"))) {
return new MIT(false, prop, kdc);
} else if (Files.exists(Paths.get(prop, "libexec/kdc"))) {
return new Heimdal(prop, kdc);
} else {
throw new IllegalArgumentException("Strange " + prop);
}
}
Process run(boolean wait, String... cmd) {
try {
System.out.println("Running " + cmd2str(env, cmd));
ProcessBuilder pb = new ProcessBuilder();
pb.inheritIO();
pb.environment().putAll(env);
Process p = pb.command(cmd).start();
if (wait) {
if (p.waitFor() < 0) {
throw new RuntimeException("exit code is not null");
}
return null;
} else {
return p;
}
} catch (Exception e) {
throw new RuntimeException(e);
}
}
private String cmd2str(Map<String,String> env, String... cmd) {
return env.entrySet().stream().map(e -> e.getKey()+"="+e.getValue())
.collect(Collectors.joining(" ")) + " " +
Stream.of(cmd).collect(Collectors.joining(" "));
}
}
// Heimdal KDC. Build your own and run "make install" to nativePath.
static class Heimdal extends NativeKdc {
Heimdal(String nativePath, KDC kdc) {
super(nativePath, kdc);
this.env = Map.of(
"KRB5_CONFIG", base + "/krb5.conf",
"KRB5_TRACE", "/dev/stderr",
"DYLD_LIBRARY_PATH", nativePath + "/lib",
"LD_LIBRARY_PATH", nativePath + "/lib");
}
@Override
public void addPrincipal(String user, String pass) {
run(true, nativePath + "/bin/kadmin", "-l", "-r", realm,
"add", "-p", pass, "--use-defaults", user);
}
@Override
public void ktadd(String user, String ktab) {
run(true, nativePath + "/bin/kadmin", "-l", "-r", realm,
"ext_keytab", "-k", ktab, user);
}
@Override
public void init() {
run(true, nativePath + "/bin/kadmin", "-l", "-r", realm,
"init", "--realm-max-ticket-life=1day",
"--realm-max-renewable-life=1month", realm);
}
@Override
public Process kdc() {
return run(false, nativePath + "/libexec/kdc",
"--addresses=127.0.0.1", "-P", "" + port);
}
@Override
public void prepare() {
try {
Files.createDirectory(Paths.get(base));
Files.write(Paths.get(base + "/krb5.conf"), Arrays.asList(
"[libdefaults]",
"default_realm = " + realm,
"default_keytab_name = FILE:" + base + "/krb5.keytab",
"forwardable = true",
"dns_lookup_kdc = no",
"dns_lookup_realm = no",
"dns_canonicalize_hostname = false",
"\n[realms]",
realm + " = {",
" kdc = localhost:" + port,
"}",
"\n[kdc]",
"db-dir = " + base,
"database = {",
" label = {",
" dbname = " + base + "/current-db",
" realm = " + realm,
" mkey_file = " + base + "/mkey.file",
" acl_file = " + base + "/heimdal.acl",
" log_file = " + base + "/current.log",
" }",
"}",
SUPPORTED_ETYPES == null ? ""
: ("\n[kadmin]\ndefault_keys = "
+ (SUPPORTED_ETYPES + ",")
.replaceAll(",", ":pw-salt ")),
"\n[logging]",
"kdc = 0-/FILE:" + base + "/messages.log",
"krb5 = 0-/FILE:" + base + "/messages.log",
"default = 0-/FILE:" + base + "/messages.log"
));
} catch (IOException e) {
throw new UncheckedIOException(e);
}
}
@Override
void kinit(String user, String ccache) {
String tmpName = base + "/" + user + "." +
System.identityHashCode(this) + ".keytab";
ktadd(user, tmpName);
run(true, nativePath + "/bin/kinit",
"-f", "-t", tmpName, "-c", ccache, user);
}
}
// MIT krb5 KDC. Make your own exploded (install == false), or
// "make install" into nativePath (install == true).
static class MIT extends NativeKdc {
private boolean install; // "make install" or "make"
MIT(boolean install, String nativePath, KDC kdc) {
super(nativePath, kdc);
this.install = install;
this.env = Map.of(
"KRB5_KDC_PROFILE", base + "/kdc.conf",
"KRB5_CONFIG", base + "/krb5.conf",
"KRB5_TRACE", "/dev/stderr",
"DYLD_LIBRARY_PATH", nativePath + "/lib",
"LD_LIBRARY_PATH", nativePath + "/lib");
}
@Override
public void addPrincipal(String user, String pass) {
run(true, nativePath +
(install ? "/sbin/" : "/kadmin/cli/") + "kadmin.local",
"-q", "addprinc -pw " + pass + " " + user);
}
@Override
public void ktadd(String user, String ktab) {
run(true, nativePath +
(install ? "/sbin/" : "/kadmin/cli/") + "kadmin.local",
"-q", "ktadd -k " + ktab + " -norandkey " + user);
}
@Override
public void init() {
run(true, nativePath +
(install ? "/sbin/" : "/kadmin/dbutil/") + "kdb5_util",
"create", "-s", "-W", "-P", "olala");
}
@Override
public Process kdc() {
return run(false, nativePath +
(install ? "/sbin/" : "/kdc/") + "krb5kdc",
"-n");
}
@Override
public void prepare() {
try {
Files.createDirectory(Paths.get(base));
Files.write(Paths.get(base + "/kdc.conf"), Arrays.asList(
"[kdcdefaults]",
"\n[realms]",
realm + "= {",
" kdc_listen = " + this.port,
" kdc_tcp_listen = " + this.port,
" database_name = " + base + "/principal",
" key_stash_file = " + base + "/.k5.ATHENA.MIT.EDU",
SUPPORTED_ETYPES == null ? ""
: (" supported_enctypes = "
+ (SUPPORTED_ETYPES + ",")
.replaceAll(",", ":normal ")),
"}"
));
Files.write(Paths.get(base + "/krb5.conf"), Arrays.asList(
"[libdefaults]",
"default_realm = " + realm,
"default_keytab_name = FILE:" + base + "/krb5.keytab",
"forwardable = true",
"dns_lookup_kdc = no",
"dns_lookup_realm = no",
"dns_canonicalize_hostname = false",
"\n[realms]",
realm + " = {",
" kdc = localhost:" + port,
"}",
"\n[logging]",
"kdc = FILE:" + base + "/krb5kdc.log"
));
} catch (IOException e) {
throw new UncheckedIOException(e);
}
}
@Override
void kinit(String user, String ccache) {
String tmpName = base + "/" + user + "." +
System.identityHashCode(this) + ".keytab";
ktadd(user, tmpName);
run(true, nativePath +
(install ? "/bin/" : "/clients/kinit/") + "kinit",
"-f", "-t", tmpName, "-c", ccache, user);
}
}
// Calling private methods thru reflections
private static final Field getPADataField;

View file

@ -95,6 +95,7 @@ public class SSLwithPerms {
.prop("javax.net.ssl", "handshake")
.prop("sun.security.krb5.debug", "true")
.perm(new SecurityPermission("setProperty.jdk.tls.disabledAlgorithms"))
.perm(new java.util.PropertyPermission("user.name", "read"))
.perm(new PropertyPermission("sun.security.krb5.principal", "read"))
.perm(new FilePermission("port", "read"))
.perm(new FilePermission(hostsFileName, "read"))

View file

@ -1,6 +1,7 @@
modules java.base/jdk.internal.misc \
java.base/sun.security.util \
java.security.jgss/sun.security.jgss \
java.security.jgss/sun.security.jgss.krb5 \
java.security.jgss/sun.security.krb5:+open \
java.security.jgss/sun.security.krb5.internal:+open \
java.security.jgss/sun.security.krb5.internal.ccache \

View file

@ -0,0 +1,271 @@
/*
* Copyright (c) 2017, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* 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).
*
* 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.
*
* 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.
*/
/*
* @test
* @bug 8184328
* @summary JDK8u131-b34-socketRead0 hang at SSL read
* @run main/othervm SSLSocketCloseHang
*/
import java.io.*;
import java.net.*;
import java.util.*;
import java.security.*;
import javax.net.ssl.*;
public class SSLSocketCloseHang {
/*
* =============================================================
* Set the various variables needed for the tests, then
* specify what tests to run on each side.
*/
/*
* Should we run the client or server in a separate thread?
* Both sides can throw exceptions, but do you have a preference
* as to which side should be the main thread.
*/
static boolean separateServerThread = true;
/*
* Where do we find the keystores?
*/
static String pathToStores = "../../../../javax/net/ssl/etc";
static String keyStoreFile = "keystore";
static String trustStoreFile = "truststore";
static String passwd = "passphrase";
/*
* Is the server ready to serve?
*/
volatile static boolean serverReady = false;
/*
* Was the client responsible for closing the socket
*/
volatile static boolean clientClosed = false;
/*
* Turn on SSL debugging?
*/
static boolean debug = false;
/*
* If the client or server is doing some kind of object creation
* that the other side depends on, and that thread prematurely
* exits, you may experience a hang. The test harness will
* terminate all hung threads after its timeout has expired,
* currently 3 minutes by default, but you might try to be
* smart about it....
*/
/*
* Define the server side of the test.
*
* If the server prematurely exits, serverReady will be set to true
* to avoid infinite hangs.
*/
void doServerSide() throws Exception {
SSLServerSocketFactory sslssf =
(SSLServerSocketFactory) SSLServerSocketFactory.getDefault();
SSLServerSocket sslServerSocket =
(SSLServerSocket) sslssf.createServerSocket(serverPort);
serverPort = sslServerSocket.getLocalPort();
/*
* Signal Client, we're ready for his connect.
*/
serverReady = true;
SSLSocket sslSocket = (SSLSocket) sslServerSocket.accept();
sslSocket.startHandshake();
while (!clientClosed) {
Thread.sleep(500);
}
}
/*
* Define the client side of the test.
*
* If the server prematurely exits, serverReady will be set to true
* to avoid infinite hangs.
*/
void doClientSide() throws Exception {
boolean caught = false;
/*
* Wait for server to get started.
*/
System.out.println("waiting on server");
while (!serverReady) {
Thread.sleep(50);
}
System.out.println("server ready");
Socket baseSocket = new Socket("localhost", serverPort);
baseSocket.setSoTimeout(100);
SSLSocketFactory sslsf =
(SSLSocketFactory) SSLSocketFactory.getDefault();
SSLSocket sslSocket = (SSLSocket)
sslsf.createSocket(baseSocket, "localhost", serverPort, false);
// handshaking
sslSocket.startHandshake();
System.out.println("handshake done");
Thread.sleep(500);
System.out.println("client closing");
sslSocket.close();
clientClosed = true;
System.out.println("client closed");
}
/*
* =============================================================
* The remainder is just support stuff
*/
// use any free port by default
volatile int serverPort = 0;
volatile Exception serverException = null;
volatile Exception clientException = null;
volatile byte[] serverDigest = null;
public static void main(String[] args) throws Exception {
String keyFilename =
System.getProperty("test.src", "./") + "/" + pathToStores +
"/" + keyStoreFile;
String trustFilename =
System.getProperty("test.src", "./") + "/" + pathToStores +
"/" + trustStoreFile;
System.setProperty("javax.net.ssl.keyStore", keyFilename);
System.setProperty("javax.net.ssl.keyStorePassword", passwd);
System.setProperty("javax.net.ssl.trustStore", trustFilename);
System.setProperty("javax.net.ssl.trustStorePassword", passwd);
if (debug)
System.setProperty("javax.net.debug", "all");
/*
* Start the tests.
*/
new SSLSocketCloseHang();
}
Thread clientThread = null;
Thread serverThread = null;
/*
* Primary constructor, used to drive remainder of the test.
*
* Fork off the other side, then do your work.
*/
SSLSocketCloseHang() throws Exception {
if (separateServerThread) {
startServer(true);
startClient(false);
} else {
startClient(true);
startServer(false);
}
/*
* Wait for other side to close down.
*/
if (separateServerThread) {
serverThread.join();
} else {
clientThread.join();
}
/*
* When we get here, the test is pretty much over.
*
* If the main thread excepted, that propagates back
* immediately. If the other thread threw an exception, we
* should report back.
*/
if (serverException != null) {
System.out.print("Server Exception:");
throw serverException;
}
if (clientException != null) {
System.out.print("Client Exception:");
throw clientException;
}
}
void startServer(boolean newThread) throws Exception {
if (newThread) {
serverThread = new Thread() {
public void run() {
try {
doServerSide();
} catch (Exception e) {
/*
* Our server thread just died.
*
* Release the client, if not active already...
*/
System.err.println("Server died...");
System.err.println(e);
serverReady = true;
serverException = e;
}
}
};
serverThread.start();
} else {
doServerSide();
}
}
void startClient(boolean newThread) throws Exception {
if (newThread) {
clientThread = new Thread() {
public void run() {
try {
doClientSide();
} catch (Exception e) {
/*
* Our client thread just died.
*/
System.err.println("Client died...");
clientException = e;
}
}
};
clientThread.start();
} else {
doClientSide();
}
}
}

View file

@ -0,0 +1,185 @@
/*
* Copyright (c) 2017, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* 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).
*
* 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.
*
* 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.
*/
/*
* @test
* @bug 6695402
* @summary verify signatures of jars containing classes with names
* with multi-byte unicode characters broken across lines
* @library /test/lib
*/
import java.io.IOException;
import java.io.InputStream;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.jar.JarFile;
import java.util.jar.Attributes.Name;
import java.util.jar.JarEntry;
import static java.nio.charset.StandardCharsets.UTF_8;
import jdk.test.lib.SecurityTools;
import jdk.test.lib.util.JarUtils;
public class LineBrokenMultiByteCharacter {
/**
* this name will break across lines in MANIFEST.MF at the
* middle of a two-byte utf-8 encoded character due to its e acute letter
* at its exact position.
*
* because no file with such a name exists {@link JarUtils} will add the
* name itself as contents to the jar entry which would have contained a
* compiled class in the original bug. For this test, the contents of the
* files contained in the jar file is not important as long as they get
* signed.
*
* @see #verifyClassNameLineBroken(JarFile, String)
*/
static final String testClassName =
"LineBrokenMultiByteCharacterA1234567890B1234567890C123456789D12\u00E9xyz.class";
static final String anotherName =
"LineBrokenMultiByteCharacterA1234567890B1234567890C123456789D1234567890.class";
static final String alias = "a";
static final String keystoreFileName = "test.jks";
static final String manifestFileName = "MANIFEST.MF";
public static void main(String[] args) throws Exception {
prepare();
testSignJar("test.jar");
testSignJarNoManifest("test-no-manifest.jar");
testSignJarUpdate("test-update.jar", "test-updated.jar");
}
static void prepare() throws Exception {
SecurityTools.keytool("-keystore", keystoreFileName, "-genkeypair",
"-storepass", "changeit", "-keypass", "changeit", "-storetype",
"JKS", "-alias", alias, "-dname", "CN=X", "-validity", "366")
.shouldHaveExitValue(0);
Files.write(Paths.get(manifestFileName), (Name.
MANIFEST_VERSION.toString() + ": 1.0\r\n").getBytes(UTF_8));
}
static void testSignJar(String jarFileName) throws Exception {
JarUtils.createJar(jarFileName, manifestFileName, testClassName);
verifyJarSignature(jarFileName);
}
static void testSignJarNoManifest(String jarFileName) throws Exception {
JarUtils.createJar(jarFileName, testClassName);
verifyJarSignature(jarFileName);
}
static void testSignJarUpdate(
String initialFileName, String updatedFileName) throws Exception {
JarUtils.createJar(initialFileName, manifestFileName, anotherName);
SecurityTools.jarsigner("-keystore", keystoreFileName, "-storetype",
"JKS", "-storepass", "changeit", "-debug", initialFileName,
alias).shouldHaveExitValue(0);
JarUtils.updateJar(initialFileName, updatedFileName, testClassName);
verifyJarSignature(updatedFileName);
}
static void verifyJarSignature(String jarFileName) throws Exception {
// actually sign the jar
SecurityTools.jarsigner("-keystore", keystoreFileName, "-storetype",
"JKS", "-storepass", "changeit", "-debug", jarFileName, alias)
.shouldHaveExitValue(0);
try (
JarFile jar = new JarFile(jarFileName);
) {
verifyClassNameLineBroken(jar, testClassName);
verifyCodeSigners(jar, jar.getJarEntry(testClassName));
}
}
/**
* it would be too easy to miss the actual test case by just renaming an
* identifier so that the multi-byte encoded character would not any longer
* be broken across a line break.
*
* this check here verifies that the actual test case is tested based on
* the manifest and not based on the signature file because at the moment,
* the signature file does not even contain the desired entry at all.
*
* this relies on {@link java.util.jar.Manifest} breaking lines unaware
* of bytes that belong to the same multi-byte utf characters.
*/
static void verifyClassNameLineBroken(JarFile jar, String className)
throws IOException {
byte[] eAcute = "\u00E9".getBytes(UTF_8);
byte[] eAcuteBroken =
new byte[] {eAcute[0], '\r', '\n', ' ', eAcute[1]};
if (jar.getManifest().getAttributes(className) == null) {
throw new AssertionError(className + " not found in manifest");
}
JarEntry manifestEntry = jar.getJarEntry(JarFile.MANIFEST_NAME);
try (
InputStream manifestIs = jar.getInputStream(manifestEntry);
) {
int bytesMatched = 0;
for (int b = manifestIs.read(); b > -1; b = manifestIs.read()) {
if ((byte) b == eAcuteBroken[bytesMatched]) {
bytesMatched++;
if (bytesMatched == eAcuteBroken.length) {
break;
}
} else {
bytesMatched = 0;
}
}
if (bytesMatched < eAcuteBroken.length) {
throw new AssertionError("self-test failed: multi-byte "
+ "utf-8 character not broken across lines");
}
}
}
static void verifyCodeSigners(JarFile jar, JarEntry jarEntry)
throws IOException {
// codeSigners is initialized only after the entry has been read
try (
InputStream inputStream = jar.getInputStream(jarEntry);
) {
inputStream.readAllBytes();
}
// a check for the presence of code signers is sufficient to check
// bug JDK-6695402. no need to also verify the actual code signers
// attributes here.
if (jarEntry.getCodeSigners() == null
|| jarEntry.getCodeSigners().length == 0) {
throw new AssertionError(
"no signing certificate found for " + jarEntry.getName());
}
}
}

View file

@ -1,34 +0,0 @@
<html>
<body>
<applet width=100 height=100 code=Alias.class>
</applet>
This is a multi-stage test. Click on "done" when you have completed
reading these instructions.<br><br>
<ol>
<li> PolicyTool will be invoked
<li> Click on "Add Policy Entry"
<li> Click on "Add Principal"
<li> Type "myalias" in the "Principal Name" field
(leave "Principal Type" empty)
<li> Click on "OK"
<li> Confirm there is a message:
'myalias' will be interpreted as a key store alias. ...
Click on "OK"
<li> Click on "Done"
<li> Open the "File" menu, and "View Warning Log"
<li> Confirm there is a warning:
Warning: Principal name 'myalias' specified without a Principal class.
<li> Click on "OK"
<li> Open the "File" menu, and "Save As"
<li> Save using the file name "p1"
<li> Click on "OK" in the status message window
<li> Open the "File" menu and "Open Policy"
<li> Open the file named "p1"
<li> If the file opens successfully, the test passed.
Otherwise, the test failed.
</ol>
</body>
</html>

View file

@ -1,78 +0,0 @@
#
# Copyright (c) 2001, 2013, 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
# under the terms of the GNU General Public License version 2 only, as
# published by the Free Software Foundation.
#
# 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).
#
# 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.
#
# 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.
#
# @test
# @bug 4449491
# @summary policytool should allow principal type to be empty
# (keystore alias substitution)
#
# @run applet/manual=done Alias.html
# @run shell Alias.sh
# @run applet/manual=yesno Alias.html
# set a few environment variables so that the shell-script can run stand-alone
# in the source directory
if [ "${TESTSRC}" = "" ] ; then
TESTSRC="."
fi
if [ "${TESTCLASSES}" = "" ] ; then
TESTCLASSES="."
fi
if [ "${TESTJAVA}" = "" ] ; then
echo "TESTJAVA not set. Test cannot execute."
echo "FAILED!!!"
exit 1
fi
# set platform-dependent variables
OS=`uname -s`
case "$OS" in
SunOS | Linux | Darwin | AIX )
NULL=/dev/null
PS=":"
FS="/"
;;
CYGWIN* )
NULL=/dev/null
PS=";"
FS="/"
;;
Windows* )
NULL=NUL
PS=";"
FS="\\"
;;
* )
echo "Unrecognized system!"
exit 1;
;;
esac
# the test code
echo "HELLO!"
${TESTJAVA}${FS}bin${FS}policytool
exit $?

View file

@ -1,85 +0,0 @@
<html>
<body>
<applet width=100 height=100 code=ChangeUI.class>
</applet>
<b>ATTENTION:</b> policytool now contains no platform-specific codes anymore and
should behaves exactly the same across all platforms. This also means:
<ol>
<li>You may only need to test it on one platform</li>
<li>You can create policy files for a platform which is different than
the platform you are running policytool on</li>
</ol>
This is a multi-stage test. Click on "done" when you have completed
reading these instructions.<br><br>
First, policytool will be invoked.<br><br>
<ol start="0">
<li>Find (or create) a temporary directory that you have write access to.
(Example: 'C:\foo\tmp' on Windows or '/tmp' on other systems)
<li>Add new policy entry
<li>Add permission:
<pre>
Type Target name Actions
FilePermission c:\\foo\\bar read
</pre>
<ol>
<li>Press OK</li>
<li>Confirm the file name warning dialog appears</li>
<li>Choose Retain, confirm the permission edit dialog is closed</li>
<li>Double click the newly created FilePermission entry to edit it</li>
<li>Press OK</li>
<li>Confirm the file name warning dialog appears</li>
<li>Choose Edit, confirm the permission edit dialog is still opened</li>
<li>change Target name to c:\foo\bar</li>
<li>Press OK, no warning dialog is shown</li>
</ol>
<li>Add permission:
<pre>
Type Target name
DelegationPermission "me@SOMEWHERE" "you@SOMEWHERE"
</pre>
<ol>
<li>Press OK</li>
<li>Double click the newly craeted DelegationPermission entry to edit it</li>
<li>Confirm the target name is still "me@SOMEWHERE" "you@SOMEWHERE"</li>
<li>Press OK</li>
</ol>
<li>Confirm there are 2 entries in the permission list
<li>Press Done
<li>Double click the new policy entry to edit it
<li>Add permission:
<pre>
Type
AllPermission
</pre>
<li>Add a new Principal, say, KerberosPrincipal with Principal Name as aaa
<li>Confirm there is 1 entry in the Principals list
<li>Confirm there are 3 entries in the permission list
<li>Press cancel
<li>Double click the policy entry to edit it
<li>Confirm there are ZERO entries in the Principals list
<li>Confirm there are 2 entries in the permission list
<li>Press cancel
<li>Save as "/tmp/p"<br>
(Or use the temporary directory mentioned in Step 0 if it's not '/tmp'.
For example, "C:\foo\tmp\p" on Windows)
<li>Confirm that the file created in the previous step looks like
<pre>
/* AUTOMATICALLY GENERATED ON Tue Jul 19 16:27:30 CST 2005*/
/* DO NOT EDIT */
grant {
permission java.io.FilePermission "c:\\foo\\bar", "read";
permission javax.security.auth.kerberos.DelegationPermission "\"me@SOMEWHERE\" \"you@SOMEWHERE\"";
};
</pre>
</ol>
<br><br>
Press "Pass" if ... press "Fail" otherwise.<br><br>
</body>
</html>

View file

@ -1,77 +0,0 @@
#
# Copyright (c) 2005, 2013, 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
# under the terms of the GNU General Public License version 2 only, as
# published by the Free Software Foundation.
#
# 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).
#
# 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.
#
# 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.
#
# @test
# @bug 6296772 6293981 6290216 8015276
# @summary FilePermission and DelegationPermission, and cancel button
#
# @run applet/manual=done ChangeUI.html
# @run shell ChangeUI.sh
# @run applet/manual=yesno ChangeUI.html
# set a few environment variables so that the shell-script can run stand-alone
# in the source directory
if [ "${TESTSRC}" = "" ] ; then
TESTSRC="."
fi
if [ "${TESTCLASSES}" = "" ] ; then
TESTCLASSES="."
fi
if [ "${TESTJAVA}" = "" ] ; then
echo "TESTJAVA not set. Test cannot execute."
echo "FAILED!!!"
exit 1
fi
# set platform-dependent variables
OS=`uname -s`
case "$OS" in
SunOS | Linux | Darwin | AIX )
NULL=/dev/null
PS=":"
FS="/"
;;
CYGWIN* )
NULL=/dev/null
PS=";"
FS="/"
;;
Windows* )
NULL=NUL
PS=";"
FS="\\"
;;
* )
echo "Unrecognized system!"
exit 1;
;;
esac
# the test code
echo "HELLO!"
${TESTJAVA}${FS}bin${FS}policytool
exit $?

View file

@ -1,26 +0,0 @@
<html>
<body>
<applet width=100 height=100 code=OpenPolicy.class>
</applet>
This is a multi-stage test. Click on "done" when you have completed
reading these instructions.<br><br>
First, policytool will be invoked.<br><br>
Pull down 'File' menu and select 'View Warning Log', which shows that
the default Policy File is not found. On Windows, if the file name
has the File separator character pointing the wrong way, like:<br><br>
C:\windows/java.policy<br><br>
Then the bug fix failed.
Otherwise, the bug fix succeeded.
Exit policytool.<br><br>
Press "Pass" if ... press "Fail" otherwise.<br><br>
</body>
</html>

View file

@ -1,77 +0,0 @@
#
# Copyright (c) 1999, 2013, 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
# under the terms of the GNU General Public License version 2 only, as
# published by the Free Software Foundation.
#
# 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).
#
# 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.
#
# 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.
#
# @test
# @bug 4224186
# @summary missing File.separatorChar when initially opening policy file
#
# @run applet/manual=done OpenPolicy.html
# @run shell OpenPolicy.sh
# @run applet/manual=yesno OpenPolicy.html
# set a few environment variables so that the shell-script can run stand-alone
# in the source directory
if [ "${TESTSRC}" = "" ] ; then
TESTSRC="."
fi
if [ "${TESTCLASSES}" = "" ] ; then
TESTCLASSES="."
fi
if [ "${TESTJAVA}" = "" ] ; then
echo "TESTJAVA not set. Test cannot execute."
echo "FAILED!!!"
exit 1
fi
# set platform-dependent variables
OS=`uname -s`
case "$OS" in
SunOS | Linux | Darwin | AIX )
NULL=/dev/null
PS=":"
FS="/"
;;
CYGWIN* )
NULL=/dev/null
PS=";"
FS="/"
;;
Windows* )
NULL=NUL
PS=";"
FS="\\"
;;
* )
echo "Unrecognized system!"
exit 1;
;;
esac
# the test code
echo "HELLO!"
${TESTJAVA}${FS}bin${FS}policytool
exit $?

View file

@ -1,26 +0,0 @@
<html>
<body>
<applet width=100 height=100 code=SaveAs.class>
</applet>
This is a multi-stage test. Click on "done" when you have completed
reading these instructions.<br><br>
First, policytool will be invoked.<br><br>
Then, go to the "File" menu, and select, "New".<br>
Next, go back to the "File" menu, and select, "Save".<br>
If you get the "Save As" File window, where you can enter<br>
a new filename, then the bug fix succeeded.<br>
If you get a FileNotFoundException, then the bug fix failed.<br><br>
If you are at the "Save As" File window, click on "Cancel"
and exit policytool.<br>
Otherwise, if you see an Exception window, click on "OK"
and exit policytool.<br><br>
Press "Pass" if ... press "Fail" otherwise.<br><br>
</body>
</html>

View file

@ -1,78 +0,0 @@
#
# Copyright (c) 1999, 2013, 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
# under the terms of the GNU General Public License version 2 only, as
# published by the Free Software Foundation.
#
# 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).
#
# 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.
#
# 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.
#
# @test
# @bug 4252583
# @summary policytool throws FileNotFoundException when user tries to
# save new policy file
#
# @run applet/manual=done SaveAs.html
# @run shell SaveAs.sh
# @run applet/manual=yesno SaveAs.html
# set a few environment variables so that the shell-script can run stand-alone
# in the source directory
if [ "${TESTSRC}" = "" ] ; then
TESTSRC="."
fi
if [ "${TESTCLASSES}" = "" ] ; then
TESTCLASSES="."
fi
if [ "${TESTJAVA}" = "" ] ; then
echo "TESTJAVA not set. Test cannot execute."
echo "FAILED!!!"
exit 1
fi
# set platform-dependent variables
OS=`uname -s`
case "$OS" in
SunOS | Linux | Darwin | AIX )
NULL=/dev/null
PS=":"
FS="/"
;;
CYGWIN* )
NULL=/dev/null
PS=";"
FS="/"
;;
Windows* )
NULL=NUL
PS=";"
FS="\\"
;;
* )
echo "Unrecognized system!"
exit 1;
;;
esac
# the test code
echo "HELLO!"
${TESTJAVA}${FS}bin${FS}policytool
exit $?

View file

@ -1,60 +0,0 @@
<html>
<body>
<applet width=100 height=100 code=UpdatePermissions.class>
</applet>
This is a multi-stage test. Click on "done" when you have completed
reading these instructions.<br><br>
First, policytool will be invoked.<br><br>
Then, follow these steps:<br>
0) Find (or create) a temporary directory that you have write access to.
(Example: 'C:\foo\tmp' on Windows or '/tmp' on other systems)<br><br>
1) Click on the "Add Policy Entry" button in the
main policytool window.<br><br>
2) Click on the "Add Permission" button in the Policy Entry window.<br><br>
3) In the Permission window, pull down the "Permission" menu and
select "AWTPermission".<br><br>
4) In the Permission window, pull down the "Target Name" menu and
select "listenToAllAWTEvents".<br><br>
5) Click on the "OK" button in the Permission window.<br><br>
6) Click on the "Done" button in the Policy Entry window.<br><br>
7) In the main policytool window, pull down the "File" menu and
select "Save As".<br><br>
8) In the SaveAs window, enter "/tmp/ptool.test" as the file name
and save it. If the file already exists, just replace it.<br>
(Or use the temporary directory mentioned in Step 0 if it's not '/tmp'.
For example, "C:\foo\tmp\ptool.test" on Windows)<br><br>
9) Check the content of the file created in the previous step<br><br>
10) check to make sure that the new entry is in the policy file.<br><br>
11) repeat steps 1-10 for:<br>
AWTPermission: readDisplayPixels<br>
NetPermission: specifyStreamHandler<br>
RuntimePermission: setContextClassLoader,
setSecurityManager,
shutdownHooks,
stopThread<br>
SecurityPermission: createAccessControlContext<br><br>
In the confirmation dialog pop-up, click "OK".<br><br>
Exit policytool. Delete the files created during this test. If the
temporary directory is also newly created, empty and delete it.<br><br>
Press "Pass" if ... press "Fail" otherwise.<br><br>
</body>
</html>

View file

@ -1,28 +0,0 @@
/*
* Copyright (c) 1999, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* 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).
*
* 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.
*
* 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.
*/
// This trivial file is only necessary to display instructions and "pass/fail"
// buttons for a manual test.
public class UpdatePermissions extends java.applet.Applet
{
}

View file

@ -1,78 +0,0 @@
#
# Copyright (c) 1999, 2013, 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
# under the terms of the GNU General Public License version 2 only, as
# published by the Free Software Foundation.
#
# 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).
#
# 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.
#
# 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.
#
# @test
# @bug 4218206
# @bug 8015276
# @summary missing or invalid permission target names in policy tool
#
# @run applet/manual=done UpdatePermissions.html
# @run shell UpdatePermissions.sh
# @run applet/manual=yesno UpdatePermissions.html
# set a few environment variables so that the shell-script can run stand-alone
# in the source directory
if [ "${TESTSRC}" = "" ] ; then
TESTSRC="."
fi
if [ "${TESTCLASSES}" = "" ] ; then
TESTCLASSES="."
fi
if [ "${TESTJAVA}" = "" ] ; then
echo "TESTJAVA not set. Test cannot execute."
echo "FAILED!!!"
exit 1
fi
# set platform-dependent variables
OS=`uname -s`
case "$OS" in
SunOS | Linux | Darwin | AIX )
NULL=/dev/null
PS=":"
FS="/"
;;
CYGWIN* )
NULL=/dev/null
PS=";"
FS="/"
;;
Windows* )
NULL=NUL
PS=";"
FS="\\"
;;
* )
echo "Unrecognized system!"
exit 1;
;;
esac
# the test code
echo "HELLO!"
${TESTJAVA}${FS}bin${FS}policytool
exit $?

Some files were not shown because too many files have changed in this diff Show more