1 /* 2 * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 */ 23 24 /* 25 * @test 26 * @summary Verify correctnes of the random generator from Utility.java 27 * @library /testlibrary 28 * @modules java.base/sun.misc 29 * java.management 30 * @run driver RandomGeneratorTest SAME_SEED 31 * @run driver RandomGeneratorTest NO_SEED 32 * @run driver RandomGeneratorTest DIFFERENT_SEED 33 */ 34 35 import jdk.test.lib.ProcessTools; 36 import jdk.test.lib.Utils; 37 import java.util.ArrayList; 38 import java.util.List; 39 import java.util.Random; 40 41 /** 42 * The test verifies correctness of work {@link jdk.test.lib.Utils#getRandomInstance()}. 43 * Test works in three modes: same seed provided, no seed provided and 44 * different seed provided. In the first case the test expects that all random numbers 45 * will be repeated in all next iterations. For other two modes test expects that 46 * randomly generated numbers differ from original. 47 */ 48 public class RandomGeneratorTest { 49 private static final String SEED_VM_OPTION = "-D" + Utils.SEED_PROPERTY_NAME + "="; 50 51 public static void main( String[] args) throws Throwable { 52 if (args.length == 0) { 53 throw new Error("TESTBUG: No test mode provided."); 54 } 55 SeedOption seedOpt = SeedOption.valueOf(args[0]); 56 List<String> jvmArgs = new ArrayList<String>(); 57 String optStr = seedOpt.getSeedOption(); 58 if (optStr != null) { 59 jvmArgs.add(optStr); 60 } 61 jvmArgs.add(RandomRunner.class.getName()); 62 String[] cmdLineArgs = jvmArgs.toArray(new String[jvmArgs.size()]); 63 String etalon = ProcessTools.executeTestJvm(cmdLineArgs).getStdout().trim(); 64 seedOpt.verify(etalon, cmdLineArgs); 65 } 66 67 /** 68 * The utility enum helps to generate an appropriate string that should be passed 69 * to the command line depends on the testing mode. It is also responsible for the result 70 * validation. 71 */ 72 private enum SeedOption { 73 SAME_SEED { 74 @Override 75 public String getSeedOption() { 76 return SEED_VM_OPTION + Utils.SEED; 77 } 78 79 @Override 80 protected boolean isOutputExpected(String orig, String output) { 81 return output.equals(orig); 82 } 83 }, 84 DIFFERENT_SEED { 85 @Override 86 public String getSeedOption() { 87 return SEED_VM_OPTION + Utils.getRandomInstance().nextLong(); 88 } 89 90 @Override 91 public void verify(String orig, String[] cmdLine) { 92 cmdLine[0] = getSeedOption(); 93 super.verify(orig, cmdLine); 94 } 95 }, 96 NO_SEED { 97 @Override 98 public String getSeedOption() { 99 return null; 100 } 101 }; 102 103 /** 104 * Generates a string to be added as a command line argument. 105 * It contains "-D" prefix, system property name, '=' sign 106 * and seed value. 107 * @return command line argument 108 */ 109 public abstract String getSeedOption(); 110 111 protected boolean isOutputExpected(String orig, String output) { 112 return !output.equals(orig); 113 } 114 115 /** 116 * Verifies that the original output meets expectations 117 * depending on the test mode. It compares the output of second execution 118 * to original one. 119 * @param orig original output 120 * @param cmdLine command line arguments 121 * @throws Throwable - Throws an exception in case test failure. 122 */ 123 public void verify(String orig, String[] cmdLine) { 124 String lastLineOrig = getLastLine(orig); 125 String lastLine; 126 try { 127 lastLine = getLastLine(ProcessTools.executeTestJvm(cmdLine).getStdout().trim()); 128 } catch (Throwable t) { 129 throw new Error("TESTBUG: Unexpedted exception during jvm execution.", t); 130 } 131 if (!isOutputExpected(lastLineOrig, lastLine)) { 132 throw new AssertionError("Unexpected random number sequence for mode: " + this.name()); 133 } 134 } 135 136 private static String getLastLine(String output) { 137 return output.substring(output.lastIndexOf(Utils.NEW_LINE)).trim(); 138 } 139 } 140 141 /** 142 * The helper class generates several random numbers 143 * and prints them out. 144 */ 145 public static class RandomRunner { 146 private static final int COUNT = 10; 147 public static void main(String[] args) { 148 StringBuilder sb = new StringBuilder(); 149 Random rng = Utils.getRandomInstance(); 150 for (int i = 0; i < COUNT; i++) { 151 sb.append(rng.nextLong()).append(' '); 152 } 153 System.out.println(sb.toString()); 154 } 155 } 156 }