1 /*
2  * Copyright (c) 2001, 2018, 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 package nsk.jdi.ThreadStartRequest.addThreadFilter;
25 
26 import nsk.share.*;
27 import nsk.share.jpda.*;
28 import nsk.share.jdi.*;
29 
30 import com.sun.jdi.*;
31 import com.sun.jdi.event.*;
32 import com.sun.jdi.request.*;
33 
34 import java.util.*;
35 import java.io.*;
36 
37 /**
38  * The test for the implementation of an object of the type
39  * ThreadStartRequest.
40  *
41  * The test checks that results of the method
42  * <code>com.sun.jdi.ThreadStartRequest.addThreadFilter()</code>
43  * complies with its spec.
44  *
45  * The test checks up on the following assertion:
46  *     Restricts the events generated by this request
47  *     to those in the given thread.
48  * The cases to test include re-invocations of the method
49  * addThreadFilter() on the same ThreadStartRequest object.
50  * There are two ThreadStartRequests to check as follows:
51  * (1) For ThreadStartRequest2, both invocations are with different
52  * ThreadReferences restricting one ThreadStart event to two threads.
53  * The test expects no ThreadStart event will be received.
54  * (2) For ThreadStartRequest1, both invocations are with the same
55  * ThreadReference restricting one ThreadStart event to one thread.
56  * The test expects this ThreadStart event will be received.
57  *
58  * The test works as follows.
59  * - The debugger resumes the debuggee and waits for the BreakpointEvent.
60  * - The debuggee creates two threads, thread1 and thread2, and invokes
61  *   the methodForCommunication to be suspended and
62  *   to inform the debugger with the event.
63  * - Upon getting the BreakpointEvent, the debugger
64  *   - sets up ThreadStartRequests 1&2 within the method
65  *     in the class addthreadfilter004aTestClass which will be calling by both threads,
66  *   - restricts the ThreadStartRequest1 only to thread1,
67  *   - restricts the ThreadStartRequest2 only to thread2,
68  *   - resumes debuggee's main thread, and
69  *   - waits for the requested events for both threads.
70  * - Debuggee's main thread starts both threads.
71  * - Upon getting the event, the debugger performs the checks required.
72  */
73 
74 public class addthreadfilter004 extends TestDebuggerType1 {
75 
main(String argv[])76     public static void main (String argv[]) {
77         System.exit(run(argv, System.out) + Consts.JCK_STATUS_BASE);
78     }
79 
run(String argv[], PrintStream out)80     public static int run (String argv[], PrintStream out) {
81         debuggeeName = "nsk.jdi.ThreadStartRequest.addThreadFilter.addthreadfilter004a";
82         return new addthreadfilter004().runThis(argv, out);
83     }
84 
85     private String testedClassName =
86       "nsk.jdi.ThreadStartRequest.addThreadFilter.addthreadfilter004aTestClass";
87 
testRun()88     protected void testRun() {
89 
90         EventRequest eventRequest1 = null;
91         EventRequest eventRequest2 = null;
92 
93         ThreadReference thread1 = null;
94         ThreadReference thread2 = null;
95 
96         String thread1Name = "thread1";
97         String thread2Name = "thread2";
98 
99         String property1 = "ThreadStartRequest1";
100         String property2 = "ThreadStartRequest2";
101 
102         ReferenceType testClassReference = null;
103 
104         boolean thread1EventReceived = false;
105         boolean thread2EventReceived = false;
106         boolean bpEventReceived = false;
107 
108         for (int i = 0; ; i++) {
109 
110             if (!shouldRunAfterBreakpoint()) {
111                 vm.resume();
112                 break;
113             }
114 
115             display(":::::: case: # " + i);
116 
117             switch (i) {
118 
119                 case 0:
120                 testClassReference =
121                      (ReferenceType) vm.classesByName(testedClassName).get(0);
122 
123                 thread1 = (ThreadReference) debuggeeClass.getValue(
124                                             debuggeeClass.fieldByName(thread1Name));
125                 thread2 = (ThreadReference) debuggeeClass.getValue(
126                                             debuggeeClass.fieldByName(thread2Name));
127 
128                 eventRequest1 = setting2ThreadStartRequest (thread1,
129                                        EventRequest.SUSPEND_ALL, property1);
130                 eventRequest2 = setting2ThreadStartRequest (thread1,
131                                        EventRequest.SUSPEND_ALL, property2);
132 
133                 ((ThreadStartRequest) eventRequest1).addThreadFilter(thread1);
134                 ((ThreadStartRequest) eventRequest2).addThreadFilter(thread2);
135 
136                 display("......waiting for ThreadStartEvent in tested thread");
137                 Event newEvent = eventHandler.waitForRequestedEvent(new EventRequest[]{eventRequest1, eventRequest2}, waitTime, true);
138 
139                 if ( !(newEvent instanceof ThreadStartEvent)) {
140                     setFailedStatus("ERROR: new event is not ThreadStartEvent");
141                 } else {
142                     String property = (String) newEvent.request().getProperty("number");
143                     display("       got new ThreadStartEvent with property 'number' == " + property);
144 
145                     if ( !property.equals(property1) ) {
146                         setFailedStatus("ERROR: property is not : " + property1);
147                     }
148 
149                     EventRequest newEventRequest = newEvent.request();
150                     if (!newEventRequest.equals(eventRequest1) ) {
151                         setFailedStatus("The ThreadStartEvent occured not for eventRequest1");
152                     }
153 
154                     ThreadReference thr = ((ThreadStartEvent)newEvent).thread();
155                     if (!thr.equals(thread1)) {
156                         setFailedStatus("The ThreadStartEvent occured in unexpected thread: " + thr);
157                     }
158                 }
159                 vm.resume();
160                 break;
161 
162                 default:
163                 throw new Failure("** default case 2 **");
164             }
165         }
166         return;
167     }
168 
setting2ThreadStartRequest( ThreadReference thread, int suspendPolicy, String property)169     private ThreadStartRequest setting2ThreadStartRequest( ThreadReference thread,
170                                                            int             suspendPolicy,
171                                                            String          property) {
172         try {
173             ThreadStartRequest tsr = eventRManager.createThreadStartRequest();
174             if (thread != null)
175                 tsr.addThreadFilter(thread);
176             tsr.setSuspendPolicy(suspendPolicy);
177             tsr.putProperty("number", property);
178             return tsr;
179         } catch ( Exception e ) {
180             throw new Failure("** FAILURE to set up ThreadStartRequest **");
181         }
182     }
183 }
184