Path: blob/master/test/hotspot/jtreg/vmTestbase/nsk/jdwp/ThreadReference/SuspendCount/suspendcnt001.java
41161 views
/*1* Copyright (c) 2001, 2018, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation.7*8* This code is distributed in the hope that it will be useful, but WITHOUT9* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or10* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License11* version 2 for more details (a copy is included in the LICENSE file that12* accompanied this code).13*14* You should have received a copy of the GNU General Public License version15* 2 along with this work; if not, write to the Free Software Foundation,16* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.17*18* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA19* or visit www.oracle.com if you need additional information or have any20* questions.21*/2223package nsk.jdwp.ThreadReference.SuspendCount;2425import java.io.*;2627import nsk.share.*;28import nsk.share.jpda.*;29import nsk.share.jdwp.*;3031/**32* Test for JDWP command: ThreadReference.SuspendCount.33*34* See suspendcnt001.README for description of test execution.35*36* This class represents debugger part of the test.37* Test is executed by invoking method runIt().38* JDWP command is tested in the method testCommand().39*40* @see #runIt()41* @see #testCommand()42*/43public class suspendcnt001 {4445// exit status constants46static final int JCK_STATUS_BASE = 95;47static final int PASSED = 0;48static final int FAILED = 2;4950// communication signals constants51static final String READY = "ready";52static final String ERROR = "error";53static final String QUIT = "quit";5455// package and classes names constants56static final String PACKAGE_NAME = "nsk.jdwp.ThreadReference.SuspendCount";57static final String TEST_CLASS_NAME = PACKAGE_NAME + "." + "suspendcnt001";58static final String DEBUGEE_CLASS_NAME = TEST_CLASS_NAME + "a";5960// tested JDWP command constants61static final String JDWP_COMMAND_NAME = "ThreadReference.SuspendCount";62static final int JDWP_COMMAND_ID = JDWP.Command.ThreadReference.SuspendCount;6364// tested class name and signature constants65static final String TESTED_CLASS_NAME = DEBUGEE_CLASS_NAME + "$" + "TestedClass";66static final String TESTED_CLASS_SIGNATURE = "L" + TESTED_CLASS_NAME.replace('.', '/') + ";";6768// name of the tested thread and statioc field with thread value69static final String TESTED_CLASS_FIELD_NAME = suspendcnt001a.FIELD_NAME;70static final String TESTED_THREAD_NAME = suspendcnt001a.THREAD_NAME;7172// expected number od suspend count73static final int SUSPEND_COUNT = 5;7475// usual scaffold objects76ArgumentHandler argumentHandler = null;77Log log = null;78Binder binder = null;79Debugee debugee = null;80Transport transport = null;81IOPipe pipe = null;8283// test passed or not84boolean success = true;8586// -------------------------------------------------------------------8788/**89* Start test from command line.90*/91public static void main (String argv[]) {92System.exit(run(argv,System.out) + JCK_STATUS_BASE);93}9495/**96* Start JCK-compilant test.97*/98public static int run(String argv[], PrintStream out) {99return new suspendcnt001().runIt(argv, out);100}101102// -------------------------------------------------------------------103104/**105* Perform test execution.106*/107public int runIt(String argv[], PrintStream out) {108109// make log for debugger messages110argumentHandler = new ArgumentHandler(argv);111log = new Log(out, argumentHandler);112113// execute test and display results114try {115log.display("\n>>> Preparing debugee for testing \n");116117// launch debuggee118binder = new Binder(argumentHandler, log);119log.display("Launching debugee");120debugee = binder.bindToDebugee(DEBUGEE_CLASS_NAME);121transport = debugee.getTransport();122pipe = debugee.createIOPipe();123124// make debuggee ready for testing125prepareDebugee();126127long threadID = 0;128129// work with prepared debuggee130try {131log.display("\n>>> Obtaining requred data from debugee \n");132133// query debuggee for classID of tested class134log.display("Getting classID by signature:\n"135+ " " + TESTED_CLASS_SIGNATURE);136long classID = debugee.getReferenceTypeID(TESTED_CLASS_SIGNATURE);137log.display(" got classID: " + classID);138139// query debuggee for threadID value from a static field140log.display("Getting threadID value from static field: "141+ TESTED_CLASS_FIELD_NAME);142threadID = queryThreadID(classID, TESTED_CLASS_FIELD_NAME);143log.display(" got threadID: " + threadID);144145// request debuggee to suspend tested thread146log.display("Suspendig thread " + SUSPEND_COUNT + " times for threadID: " + threadID);147for (int i = 0; i < SUSPEND_COUNT; i++) {148debugee.suspendThread(threadID);149}150151// perform testing JDWP command152log.display("\n>>> Testing JDWP command \n");153testCommand(threadID);154155} finally {156157log.display("\n>>> Finishing test \n");158159// resumme suspended thread160if (threadID != 0) {161log.display("Resuming " + SUSPEND_COUNT + " times suspended thread: " + threadID);162for (int i = 0; i < SUSPEND_COUNT; i++) {163debugee.resumeThread(threadID);164}165}166167// quit debugee168quitDebugee();169}170171} catch (Failure e) {172log.complain("TEST FAILED: " + e.getMessage());173success = false;174} catch (Exception e) {175e.printStackTrace(out);176log.complain("Caught unexpected exception while running the test:\n\t" + e);177success = false;178}179180if (!success) {181log.complain("TEST FAILED");182return FAILED;183}184185out.println("TEST PASSED");186return PASSED;187188}189190/**191* Prepare debugee for testing and waiting for ready signal.192*/193void prepareDebugee() {194// wait for VM_INIT event from debugee195log.display("Waiting for VM_INIT event");196debugee.waitForVMInit();197198// query debugee for VM-dependent ID sizes199log.display("Querying for IDSizes");200debugee.queryForIDSizes();201202// resume initially suspended debugee203log.display("Resuming debugee VM");204debugee.resume();205206// wait for READY signal from debugee207log.display("Waiting for signal from debugee: " + READY);208String signal = pipe.readln();209log.display("Received signal from debugee: " + signal);210if (signal == null) {211throw new TestBug("Null signal received from debugee: " + signal212+ " (expected: " + READY + ")");213} else if (signal.equals(ERROR)) {214throw new TestBug("Debugee was not able to start tested thread"215+ " (received signal: " + signal + ")");216} else if (!signal.equals(READY)) {217throw new TestBug("Unexpected signal received from debugee: " + signal218+ " (expected: " + READY + ")");219}220}221222/**223* Sending debugee signal to quit and waiting for it exits.224*/225void quitDebugee() {226// send debugee signal to quit227log.display("Sending signal to debugee: " + QUIT);228pipe.println(QUIT);229230// wait for debugee exits231log.display("Waiting for debugee exits");232int code = debugee.waitFor();233234// analize debugee exit status code235if (code == JCK_STATUS_BASE + PASSED) {236log.display("Debugee PASSED with exit code: " + code);237} else {238log.complain("Debugee FAILED with exit code: " + code);239success = false;240}241}242243/**244* Query debuggee for threadID value of statuic field of the class.245*/246long queryThreadID(long classID, String fieldName) {247// get fieledID for static field (declared in the class)248long fieldID = debugee.getClassFieldID(classID, fieldName, true);249// get value of the field250JDWP.Value value = debugee.getStaticFieldValue(classID, fieldID);251252// check that value has THREAD tag253if (value.getTag() != JDWP.Tag.THREAD) {254throw new Failure("Not threadID value returned from debuggee: " + value);255}256257// extract threadID from the value258long threadID = ((Long)value.getValue()).longValue();259return threadID;260}261262/**263* Query debuggee for suspend status of the thread.264*/265int querySuspendStatus(long threadID) {266log.display("Getting suspend status for threadID: " + threadID);267CommandPacket command = new CommandPacket(JDWP.Command.ThreadReference.Status);268command.addObjectID(threadID);269ReplyPacket reply = debugee.receiveReplyFor(command);270271try {272reply.resetPosition();273274int threadStatus = reply.getInt();275int suspendStatus = reply.getInt();276log.display(" got suspendStatus: " + suspendStatusString(suspendStatus));277return suspendStatus;278} catch (BoundException e) {279throw new Failure("Caught BoundException while parsing reply for ThreadReference.Status:\n\t"280+ e);281}282}283284/**285* Perform testing JDWP command for specified threadID.286*/287void testCommand(long threadID) {288// create command packet and fill requred out data289log.display("Create command packet:");290log.display("Command: " + JDWP_COMMAND_NAME);291CommandPacket command = new CommandPacket(JDWP_COMMAND_ID);292log.display(" threadID: " + threadID);293command.addObjectID(threadID);294command.setLength();295296// send command packet to debugee297try {298log.display("Sending command packet:\n" + command);299transport.write(command);300} catch (IOException e) {301log.complain("Unable to send command packet:\n\t" + e);302success = false;303return;304}305306ReplyPacket reply = new ReplyPacket();307308// receive reply packet from debugee309try {310log.display("Waiting for reply packet");311transport.read(reply);312log.display("Reply packet received:\n" + reply);313} catch (IOException e) {314log.complain("Unable to read reply packet:\n\t" + e);315success = false;316return;317}318319// check reply packet header320try{321log.display("Checking reply packet header");322reply.checkHeader(command.getPacketID());323} catch (BoundException e) {324log.complain("Bad header of reply packet:\n\t" + e.getMessage());325success = false;326return;327}328329// start parsing reply packet data330log.display("Parsing reply packet:");331reply.resetPosition();332333int suspendCount = 0;334try {335suspendCount = reply.getInt();336log.display(" suspendCount: " + suspendCount);337} catch (BoundException e) {338log.complain("Unable to extract suspend count number form the reply packet:\n\t"339+ e.getMessage());340success = false;341return;342}343344// check for extra data in reply packet345if (!reply.isParsed()) {346log.complain("Extra trailing bytes found in reply packet at: "347+ reply.offsetString());348success = false;349}350351if (suspendCount < 0) {352log.complain("Negative number of suspend count returned: " + suspendCount353+ "(expected: " + SUSPEND_COUNT + ")");354success = false;355}356357if (suspendCount != SUSPEND_COUNT) {358log.complain("Unexpected number of suspend count returned: " + suspendCount359+ "(expected: " + SUSPEND_COUNT + ")");360success = false;361}362363}364365/**366* Return string representation of thread suspend status.367*/368private static String suspendStatusString(int status) {369String s = null;370if ((status & JDWP.SuspendStatus.SUSPEND_STATUS_SUSPENDED) != 0) {371s = "SUSPEND_STATUS_SUSPENDED";372} else if (status == 0) {373s = "NONE";374} else {375s = "unknown";376}377return status + "=" + s;378}379}380381382