blob: ddf3a62c1688faeaf8b7971a14d2fef707874c1d [file] [log] [blame]
J. Duke319a3b92007-12-01 00:00:00 +00001/*
2 * Copyright 2001 Sun Microsystems, Inc. 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 Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
20 * CA 95054 USA or visit www.sun.com if you need additional information or
21 * have any questions.
22 */
23
24/* @test
25 * @bug 4487532
26 * @summary When the system property "sun.rmi.server.suppressStackTraces" is
27 * set to boolean true, then the RMI runtime should take positive action to
28 * counteract the new feature in 1.4 of an exception's stack trace being part
29 * of its serialized form so that the server-side stack trace of an exception
30 * that occurs during the execution of a remote method invocation gets
31 * marshalled to the client. In most cases, this feature-- along with the
32 * final fix to 4010355 to make the server-side stack trace data available
33 * at the RMI client application level-- is highly desirable, but this system
34 * property provides an opportunity to suppress the server-side stack trace
35 * data of exceptions thrown by remote methods from being marshalled, perhaps
36 * for reasons of performance or confidentiality requirements.
37 * @author Peter Jones
38 *
39 * @build SuppressStackTraces
40 * @build Impl2_Stub
41 * @build Impl1_Stub
42 * @build Impl1_Skel
43 * @run main/othervm SuppressStackTraces
44 */
45
46import java.io.IOException;
47import java.io.ObjectInputStream;
48import java.rmi.Remote;
49import java.rmi.RemoteException;
50import java.rmi.server.UnicastRemoteObject;
51import java.util.Arrays;
52
53interface Pong extends Remote {
54 void pong() throws PongException, RemoteException;
55}
56
57class PongException extends Exception {
58 private void readObject(ObjectInputStream in)
59 throws IOException, ClassNotFoundException
60 {
61 in.defaultReadObject();
62
63 /*
64 * Verify right at unmarshalling time that this exception instance
65 * contains no stack trace data from the server (regardless of whether
66 * or not it would be apparent at the RMI client application level).
67 */
68 StackTraceElement[] trace = getStackTrace();
69 if (trace.length > 0) {
70 throw new RuntimeException(
71 "TEST FAILED: exception contained non-empty stack trace: " +
72 Arrays.asList(trace));
73 }
74 }
75}
76
77 // stub class generated with "rmic -v1.2 ..."
78class Impl2 implements Pong {
79 public void pong() throws PongException { __BAR__(); }
80 public void __BAR__() throws PongException { throw new PongException(); }
81}
82
83 // stub and skeleton classes generated with "rmic -v1.1 ..."
84class Impl1 implements Pong {
85 public void pong() throws PongException { __BAR__(); }
86 public void __BAR__() throws PongException { throw new PongException(); }
87}
88
89public class SuppressStackTraces {
90
91 private static void __FOO__(Pong stub)
92 throws PongException, RemoteException
93 {
94 stub.pong();
95 }
96
97 public static void main(String[] args) throws Exception {
98
99 System.err.println("\nRegression test for RFE 4487532\n");
100
101 System.setProperty("sun.rmi.server.suppressStackTraces", "true");
102
103 Remote impl2 = new Impl2();
104 Remote impl1 = new Impl1();
105
106 try {
107 /*
108 * Verify behavior for both -v1.1 and -v1.2 stub protocols.
109 */
110 verifySuppression((Pong) UnicastRemoteObject.exportObject(impl2));
111 verifySuppression((Pong) UnicastRemoteObject.exportObject(impl1));
112
113 System.err.println(
114 "TEST PASSED (server-side stack trace data suppressed)");
115 } finally {
116 try {
117 UnicastRemoteObject.unexportObject(impl1, true);
118 } catch (Exception e) {
119 }
120 try {
121 UnicastRemoteObject.unexportObject(impl2, true);
122 } catch (Exception e) {
123 }
124 }
125 }
126
127 private static void verifySuppression(Pong stub) throws Exception {
128 System.err.println("testing stub for exported object: " + stub);
129
130 StackTraceElement[] remoteTrace;
131 try {
132 __FOO__(stub);
133 throw new RuntimeException("TEST FAILED: no exception caught");
134 } catch (PongException e) {
135 System.err.println(
136 "trace of exception thrown by remote call:");
137 e.printStackTrace();
138 System.err.println();
139 remoteTrace = e.getStackTrace();
140 }
141
142 int fooIndex = -1;
143 for (int i = 0; i < remoteTrace.length; i++) {
144 StackTraceElement e = remoteTrace[i];
145 if (e.getMethodName().equals("__FOO__")) {
146 if (fooIndex != -1) {
147 throw new RuntimeException(
148 "TEST FAILED: trace contains more than one __FOO__");
149 }
150 fooIndex = i;
151 } else if (e.getMethodName().equals("__BAR__")) {
152 throw new RuntimeException(
153 "TEST FAILED: trace contains __BAR__");
154 }
155 }
156 if (fooIndex == -1) {
157 throw new RuntimeException(
158 "TEST FAILED: trace lacks client-side method __FOO__");
159 }
160 }
161}