1/* 2 * Licensed to the Apache Software Foundation (ASF) under one or more 3 * contributor license agreements. See the NOTICE file distributed with 4 * this work for additional information regarding copyright ownership. 5 * The ASF licenses this file to You under the Apache License, Version 2.0 6 * (the "License"); you may not use this file except in compliance with 7 * the License. You may obtain a copy of the License at 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * 15 * See the License for the specific language governing permissions and 16 * limitations under the License. 17 */ 18 19/** 20 * @author Pavel N. Vyssotski 21 */ 22 23// $Id: InvokeMethod002Test.java,v 1.4 2006/06/20 11:15:16 rscherba Exp $ 24 25package org.apache.harmony.jpda.tests.jdwp.ClassType; 26 27import org.apache.harmony.jpda.tests.framework.jdwp.CommandPacket; 28import org.apache.harmony.jpda.tests.framework.jdwp.JDWPCommands; 29import org.apache.harmony.jpda.tests.framework.jdwp.JDWPConstants; 30import org.apache.harmony.jpda.tests.framework.jdwp.ReplyPacket; 31import org.apache.harmony.jpda.tests.framework.jdwp.TaggedObject; 32import org.apache.harmony.jpda.tests.framework.jdwp.Value; 33import org.apache.harmony.jpda.tests.jdwp.share.JDWPSyncTestCase; 34import org.apache.harmony.jpda.tests.share.JPDADebuggeeSynchronizer; 35 36 37/** 38 * JDWP unit test for ClassType.InvokeMethod command. 39 */ 40public class InvokeMethod002Test extends JDWPSyncTestCase { 41 protected String getDebuggeeClassName() { 42 return "org.apache.harmony.jpda.tests.jdwp.share.debuggee.InvokeMethodDebuggee"; 43 } 44 45 /** 46 * This testcase checks ClassType.InvokeMethod command. 47 * <BR>Checked method is 48 * <BR>public static String testMethod3( 49 * int, int[], int[][], String, String[], String[][]) 50 * <BR>of org.apache.harmony.jpda.tests.jdwp.share.debuggee.InvokeMethodDebuggee class. 51 * <BR> The testcase expects that returned value is not null object and returned 52 * exception object is null; 53 */ 54 private void testInvokeMethod(boolean deliberately_screw_up_types) { 55 synchronizer.receiveMessage(JPDADebuggeeSynchronizer.SGNL_READY); 56 57 // Get referenceTypeID 58 CommandPacket packet = new CommandPacket( 59 JDWPCommands.VirtualMachineCommandSet.CommandSetID, 60 JDWPCommands.VirtualMachineCommandSet.ClassesBySignatureCommand); 61 String classSig = "Lorg/apache/harmony/jpda/tests/jdwp/share/debuggee/InvokeMethodDebuggee;"; 62 packet.setNextValueAsString(classSig); 63 64 ReplyPacket reply = debuggeeWrapper.vmMirror.performCommand(packet); 65 checkReplyPacket(reply, "VirtualMachine::ClassesBySignature command"); 66 67 int classes = reply.getNextValueAsInt(); 68 assertEquals("VirtualMachine::ClassesBySignature returned invalid number of classes,", 69 1, classes); //this class may be loaded only once 70 byte refTypeTag = reply.getNextValueAsByte(); 71 long classID = reply.getNextValueAsReferenceTypeID(); 72 int status = reply.getNextValueAsInt(); 73 assertAllDataRead(reply); 74 assertEquals("VirtualMachine::ClassesBySignature returned invalid TypeTag,", 75 JDWPConstants.TypeTag.CLASS, refTypeTag, 76 JDWPConstants.TypeTag.getName(JDWPConstants.TypeTag.CLASS), 77 JDWPConstants.TypeTag.getName(refTypeTag)); 78 79 logWriter.println(" VirtualMachine.ClassesBySignature: classes=" 80 + classes + " refTypeTag=" + refTypeTag + " classID= " + classID 81 + " status=" + status); 82 83 // Get methodID 84 packet = new CommandPacket( 85 JDWPCommands.ReferenceTypeCommandSet.CommandSetID, 86 JDWPCommands.ReferenceTypeCommandSet.MethodsCommand); 87 packet.setNextValueAsClassID(classID); 88 89 reply = debuggeeWrapper.vmMirror.performCommand(packet); 90 checkReplyPacket(reply, "ReferenceType::Methods command"); 91 92 int declared = reply.getNextValueAsInt(); 93 logWriter.println(" ReferenceType.Methods: declared=" + declared); 94 long targetMethodID = 0; 95 for (int i = 0; i < declared; i++) { 96 long methodID = reply.getNextValueAsMethodID(); 97 String name = reply.getNextValueAsString(); 98 String signature = reply.getNextValueAsString(); 99 int modBits = reply.getNextValueAsInt(); 100 logWriter.println(" methodID=" + methodID + " name=" + name 101 + " signature=" + signature + " modBits=" + modBits); 102 if (name.equals("testMethod3")) { 103 targetMethodID = methodID; 104 } 105 } 106 assertAllDataRead(reply); 107 108 // Set EventRequest 109 packet = new CommandPacket( 110 JDWPCommands.EventRequestCommandSet.CommandSetID, 111 JDWPCommands.EventRequestCommandSet.SetCommand); 112 packet.setNextValueAsByte(JDWPConstants.EventKind.METHOD_ENTRY); 113 packet.setNextValueAsByte(JDWPConstants.SuspendPolicy.ALL); 114 packet.setNextValueAsInt(1); 115 packet.setNextValueAsByte((byte) 5); 116 packet.setNextValueAsString("*.InvokeMethodDebuggee"); 117 118 reply = debuggeeWrapper.vmMirror.performCommand(packet); 119 checkReplyPacket(reply, "EventRequest::Set command"); 120 121 int requestID = reply.getNextValueAsInt(); 122 logWriter.println(" EventRequest.Set: requestID=" + requestID); 123 assertAllDataRead(reply); 124 synchronizer.sendMessage(JPDADebuggeeSynchronizer.SGNL_CONTINUE); 125 126 long targetThreadID = 0; 127 // Wait event 128 CommandPacket event = debuggeeWrapper.vmMirror.receiveEvent(); 129 byte suspendPolicy = event.getNextValueAsByte(); 130 int events = event.getNextValueAsInt(); 131 logWriter.println(" EVENT_THREAD event: suspendPolicy=" + suspendPolicy 132 + " events=" + events); 133 for (int i = 0; i < events; i++) { 134 byte eventKind = event.getNextValueAsByte(); 135 int newRequestID = event.getNextValueAsInt(); 136 long threadID = event.getNextValueAsThreadID(); 137 //Location location = 138 event.getNextValueAsLocation(); 139 logWriter.println(" EVENT_THREAD event " + i + ": eventKind=" 140 + eventKind + " requestID=" + newRequestID + " threadID=" 141 + threadID); 142 if (newRequestID == requestID) { 143 targetThreadID = threadID; 144 } 145 } 146 assertAllDataRead(event); 147 assertTrue("Invalid targetThreadID, must be != 0", targetThreadID != 0); 148 149 // Let's clear event request 150 packet = new CommandPacket( 151 JDWPCommands.EventRequestCommandSet.CommandSetID, 152 JDWPCommands.EventRequestCommandSet.ClearCommand); 153 packet.setNextValueAsByte(JDWPConstants.EventKind.METHOD_ENTRY); 154 packet.setNextValueAsInt(requestID); 155 156 reply = debuggeeWrapper.vmMirror.performCommand(packet); 157 checkReplyPacket(reply, "EventRequest::Clear command"); 158 assertAllDataRead(reply); 159 160 logWriter.println("Read values of fields to pass them as arguments:"); 161 String fieldNames[] = { 162 "checkInt", 163 "checkIntArray", 164 "checkIntArray2", 165 "checkString", 166 "checkStringArray", 167 "checkStringArray2", 168 "checkClass", 169 "checkClassArray", 170 "checkClassArray2" 171 }; 172 long[] fieldIDs = {0,0,0,0,0,0,0,0,0}; 173 Value[] fieldValues = {null,null,null,null,null,null,null,null,null}; 174 175 if (deliberately_screw_up_types) { 176 fieldNames[1] = "checkStringArray"; 177 fieldNames[4] = "checkIntArray"; 178 } 179 180 packet = new CommandPacket( 181 JDWPCommands.ReferenceTypeCommandSet.CommandSetID, 182 JDWPCommands.ReferenceTypeCommandSet.FieldsCommand); 183 packet.setNextValueAsReferenceTypeID(classID); 184 185 reply = debuggeeWrapper.vmMirror.performCommand(packet); 186 checkReplyPacket(reply, "ReferenceType::Fields command"); 187 188 int fieldsCount = reply.getNextValueAsInt(); 189 assertTrue("Invalid fieldsCount=" + fieldsCount + ", must be >= " + fieldValues.length 190 , fieldsCount >= fieldValues.length); 191 192 for (int i = 0; i < fieldsCount; i++) { 193 long id = reply.getNextValueAsFieldID(); 194 String name = reply.getNextValueAsString(); 195 //String signature = 196 reply.getNextValueAsString(); 197 //int modifiers = 198 reply.getNextValueAsInt(); 199 for (int k = 0; k < fieldNames.length; k++) { 200 if (fieldNames[k].equals(name)) { 201 fieldIDs[k] = id; 202 logWriter.println(" name=" + name + ", ID=" + id); 203 break; 204 } 205 } 206 } 207 assertAllDataRead(reply); 208 209 for (int i = 0; i < fieldIDs.length; i++) { 210 if (fieldIDs[i] == 0) { 211 logWriter.println( 212 "ERROR: \"" + fieldNames[i] + "\" field not found"); 213 fail("\"" + fieldNames[i] + "\" field not found"); 214 } 215 } 216 217 packet = new CommandPacket( 218 JDWPCommands.ReferenceTypeCommandSet.CommandSetID, 219 JDWPCommands.ReferenceTypeCommandSet.GetValuesCommand); 220 packet.setNextValueAsReferenceTypeID(classID); 221 packet.setNextValueAsInt(fieldIDs.length); 222 for (int i = 0; i < fieldIDs.length; i++) { 223 packet.setNextValueAsFieldID(fieldIDs[i]); 224 } 225 226 reply = debuggeeWrapper.vmMirror.performCommand(packet); 227 checkReplyPacket(reply, "ReferenceType::GetValues command"); 228 229 int valuesCount = reply.getNextValueAsInt(); 230 for (int i = 0; i < valuesCount; i++) { 231 fieldValues[i] = reply.getNextValueAsValue(); 232 } 233 assertAllDataRead(reply); 234 235 // Make InvokeMethod 236 packet = new CommandPacket( 237 JDWPCommands.ClassTypeCommandSet.CommandSetID, 238 JDWPCommands.ClassTypeCommandSet.InvokeMethodCommand); 239 packet.setNextValueAsClassID(classID); 240 packet.setNextValueAsThreadID(targetThreadID); 241 packet.setNextValueAsMethodID(targetMethodID); 242 packet.setNextValueAsInt(fieldValues.length); 243 for (int i = 0; i < fieldValues.length; i++) { 244 packet.setNextValueAsValue(fieldValues[i]); 245 } 246 packet.setNextValueAsInt(0); 247 logWriter.println(" Send ClassType.InvokeMethod"); 248 reply = debuggeeWrapper.vmMirror.performCommand(packet); 249 250 if (deliberately_screw_up_types) { 251 checkReplyPacket(reply, "ClassType::InvokeMethod command", 252 JDWPConstants.Error.ILLEGAL_ARGUMENT); 253 } else { 254 checkReplyPacket(reply, "ClassType::InvokeMethod command"); 255 256 Value returnValue = reply.getNextValueAsValue(); 257 logWriter.println(" ClassType.InvokeMethod: returnValue=" + returnValue); 258 259 String returnedString = getStringValue(returnValue.getLongValue()); 260 logWriter.println(" ClassType.InvokeMethod: returnedString=" + returnedString); 261 assertEquals("qwerty", returnedString); 262 263 TaggedObject exception = reply.getNextValueAsTaggedObject(); 264 assertNotNull("ClassType::InvokeMethod returned null exception", 265 exception); 266 assertEquals("ClassType::InvokeMethod returned invalid exception objectID,", 267 0, exception.objectID); 268 assertEquals("ClassType::InvokeMethod returned invalid exception.tag", 269 JDWPConstants.Tag.OBJECT_TAG, exception.tag, 270 JDWPConstants.Tag.getName(JDWPConstants.Tag.OBJECT_TAG), 271 JDWPConstants.Tag.getName(exception.tag)); 272 logWriter.println(" ClassType.InvokeMethod: exception.tag=" + exception.tag + 273 " exception.objectID=" + exception.objectID); 274 } 275 276 assertAllDataRead(reply); 277 278 // Let's resume application 279 packet = new CommandPacket( 280 JDWPCommands.VirtualMachineCommandSet.CommandSetID, 281 JDWPCommands.VirtualMachineCommandSet.ResumeCommand); 282 reply = debuggeeWrapper.vmMirror.performCommand(packet); 283 checkReplyPacket(reply, "VirtualMachine::Resume command"); 284 assertAllDataRead(reply); 285 286 synchronizer.sendMessage(JPDADebuggeeSynchronizer.SGNL_CONTINUE); 287 } 288 289 public void testInvokeMethod_right_argument_types() { 290 testInvokeMethod(false); 291 } 292 293 public void testInvokeMethod_wrong_argument_types() { 294 testInvokeMethod(true); 295 } 296} 297