Bridge.java revision 807:408c9c621938
1/* 2 * Copyright (c) 2004, 2016, 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. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26package sun.corba ; 27 28import java.io.OptionalDataException; 29import java.lang.invoke.MethodHandle; 30import java.lang.reflect.Field ; 31import java.lang.reflect.Constructor ; 32 33import java.security.AccessController; 34import java.security.Permission; 35import java.security.PrivilegedAction; 36 37import sun.misc.Unsafe; 38import sun.reflect.ReflectionFactory; 39 40/** This class provides the methods for fundamental JVM operations 41 * needed in the ORB that are not part of the public Java API. This includes: 42 * <ul> 43 * <li>throwException, which can throw undeclared checked exceptions. 44 * This is needed to handle throwing arbitrary exceptions across a standardized 45 * OMG interface that (incorrectly) does not specify appropriate exceptions.</li> 46 * <li>putXXX/getXXX methods that allow unchecked access to fields of objects. 47 * This is used for setting uninitialzed non-static final fields (which is 48 * impossible with reflection) and for speed.</li> 49 * <li>objectFieldOffset to obtain the field offsets for use in the putXXX/getXXX methods</li> 50 * <li>newConstructorForSerialization to get the special constructor required for a 51 * Serializable class</li> 52 * <li>latestUserDefinedLoader to get the latest user defined class loader from 53 * the call stack as required by the RMI-IIOP specification (really from the 54 * JDK 1.1 days)</li> 55 * </ul> 56 * The code that calls Bridge.get() must have the following Permissions: 57 * <ul> 58 * <li>RuntimePermission "reflectionFactoryAccess"</li> 59 * <li>BridgePermission "getBridge"</li> 60 * <li>ReflectPermission "suppressAccessChecks"</li> 61 * </ul> 62 * <p> 63 * All of these permissions are required to obtain and correctly initialize 64 * the instance of Bridge. No security checks are performed on calls 65 * made to Bridge instance methods, so access to the Bridge instance 66 * must be protected. 67 * <p> 68 * This class is a singleton (per ClassLoader of course). Access to the 69 * instance is obtained through the Bridge.get() method. 70 */ 71public final class Bridge 72{ 73 private static final Permission getBridgePermission = 74 new BridgePermission("getBridge"); 75 private static Bridge bridge = null ; 76 77 /** Access to Unsafe to read/write fields. */ 78 private static final Unsafe unsafe = AccessController.doPrivileged( 79 (PrivilegedAction<Unsafe>)() -> { 80 try { 81 Field field = Unsafe.class.getDeclaredField("theUnsafe"); 82 field.setAccessible(true); 83 return (Unsafe)field.get(null); 84 85 } catch (NoSuchFieldException |IllegalAccessException ex) { 86 throw new InternalError("Unsafe.theUnsafe field not available", ex); 87 } 88 } 89 ) ; 90 91 private final ReflectionFactory reflectionFactory ; 92 93 private Bridge() { 94 reflectionFactory = ReflectionFactory.getReflectionFactory(); 95 } 96 97 /** Fetch the Bridge singleton. This requires the following 98 * permissions: 99 * <ul> 100 * <li>RuntimePermission "reflectionFactoryAccess"</li> 101 * <li>BridgePermission "getBridge"</li> 102 * <li>ReflectPermission "suppressAccessChecks"</li> 103 * </ul> 104 * @return The singleton instance of the Bridge class 105 * @throws SecurityException if the caller does not have the 106 * required permissions and the caller has a non-null security manager. 107 */ 108 public static final synchronized Bridge get() 109 { 110 SecurityManager sman = System.getSecurityManager() ; 111 if (sman != null) 112 sman.checkPermission( getBridgePermission ) ; 113 114 if (bridge == null) { 115 bridge = new Bridge() ; 116 } 117 118 return bridge ; 119 } 120 121 /** Obtain the latest user defined ClassLoader from the call stack. 122 * This is required by the RMI-IIOP specification. 123 */ 124 public final ClassLoader getLatestUserDefinedLoader() { 125 return jdk.internal.misc.VM.latestUserDefinedLoader(); 126 } 127 128 /** 129 * Fetches a field element within the given 130 * object <code>o</code> at the given offset. 131 * The result is undefined unless the offset was obtained from 132 * {@link #objectFieldOffset} on the {@link java.lang.reflect.Field} 133 * of some Java field and the object referred to by <code>o</code> 134 * is of a class compatible with that field's class. 135 * @param o Java heap object in which the field from which the offset 136 * was obtained resides 137 * @param offset indication of where the field resides in a Java heap 138 * object 139 * @return the value fetched from the indicated Java field 140 * @throws RuntimeException No defined exceptions are thrown, not even 141 * {@link NullPointerException} 142 */ 143 public final int getInt(Object o, long offset) 144 { 145 return unsafe.getInt( o, offset ) ; 146 } 147 148 /** 149 * Stores a value into a given Java field. 150 * <p> 151 * The first two parameters are interpreted exactly as with 152 * {@link #getInt(Object, long)} to refer to a specific 153 * Java field. The given value is stored into that field. 154 * <p> 155 * The field must be of the same type as the method 156 * parameter <code>x</code>. 157 * 158 * @param o Java heap object in which the field resides, if any, else 159 * null 160 * @param offset indication of where the field resides in a Java heap 161 * object. 162 * @param x the value to store into the indicated Java field 163 * @throws RuntimeException No defined exceptions are thrown, not even 164 * {@link NullPointerException} 165 */ 166 public final void putInt(Object o, long offset, int x) 167 { 168 unsafe.putInt( o, offset, x ) ; 169 } 170 171 /** 172 * @see #getInt(Object, long) 173 */ 174 public final Object getObject(Object o, long offset) 175 { 176 return unsafe.getObject( o, offset ) ; 177 } 178 179 /** 180 * @see #putInt(Object, long, int) 181 */ 182 public final void putObject(Object o, long offset, Object x) 183 { 184 unsafe.putObject( o, offset, x ) ; 185 } 186 187 /** @see #getInt(Object, long) */ 188 public final boolean getBoolean(Object o, long offset) 189 { 190 return unsafe.getBoolean( o, offset ) ; 191 } 192 /** @see #putInt(Object, long, int) */ 193 public final void putBoolean(Object o, long offset, boolean x) 194 { 195 unsafe.putBoolean( o, offset, x ) ; 196 } 197 /** @see #getInt(Object, long) */ 198 public final byte getByte(Object o, long offset) 199 { 200 return unsafe.getByte( o, offset ) ; 201 } 202 /** @see #putInt(Object, long, int) */ 203 public final void putByte(Object o, long offset, byte x) 204 { 205 unsafe.putByte( o, offset, x ) ; 206 } 207 /** @see #getInt(Object, long) */ 208 public final short getShort(Object o, long offset) 209 { 210 return unsafe.getShort( o, offset ) ; 211 } 212 /** @see #putInt(Object, long, int) */ 213 public final void putShort(Object o, long offset, short x) 214 { 215 unsafe.putShort( o, offset, x ) ; 216 } 217 /** @see #getInt(Object, long) */ 218 public final char getChar(Object o, long offset) 219 { 220 return unsafe.getChar( o, offset ) ; 221 } 222 /** @see #putInt(Object, long, int) */ 223 public final void putChar(Object o, long offset, char x) 224 { 225 unsafe.putChar( o, offset, x ) ; 226 } 227 /** @see #getInt(Object, long) */ 228 public final long getLong(Object o, long offset) 229 { 230 return unsafe.getLong( o, offset ) ; 231 } 232 /** @see #putInt(Object, long, int) */ 233 public final void putLong(Object o, long offset, long x) 234 { 235 unsafe.putLong( o, offset, x ) ; 236 } 237 /** @see #getInt(Object, long) */ 238 public final float getFloat(Object o, long offset) 239 { 240 return unsafe.getFloat( o, offset ) ; 241 } 242 /** @see #putInt(Object, long, int) */ 243 public final void putFloat(Object o, long offset, float x) 244 { 245 unsafe.putFloat( o, offset, x ) ; 246 } 247 /** @see #getInt(Object, long) */ 248 public final double getDouble(Object o, long offset) 249 { 250 return unsafe.getDouble( o, offset ) ; 251 } 252 /** @see #putInt(Object, long, int) */ 253 public final void putDouble(Object o, long offset, double x) 254 { 255 unsafe.putDouble( o, offset, x ) ; 256 } 257 258 /** 259 * This constant differs from all results that will ever be returned from 260 * {@link #objectFieldOffset}. 261 */ 262 public static final long INVALID_FIELD_OFFSET = -1; 263 264 /** 265 * Returns the offset of a non-static field. 266 */ 267 public final long objectFieldOffset(Field f) 268 { 269 return unsafe.objectFieldOffset( f ) ; 270 } 271 272 /** 273 * Returns the offset of a static field. 274 */ 275 public final long staticFieldOffset(Field f) 276 { 277 return unsafe.staticFieldOffset( f ) ; 278 } 279 280 /** 281 * Ensure that the class has been initalized. 282 * @param cl the class to ensure is initialized 283 */ 284 public final void ensureClassInitialized(Class<?> cl) { 285 unsafe.ensureClassInitialized(cl); 286 } 287 288 289 /** Throw the exception. 290 * The exception may be an undeclared checked exception. 291 */ 292 public final void throwException(Throwable ee) 293 { 294 unsafe.throwException( ee ) ; 295 } 296 297 /** 298 * Obtain a constructor for Class cl. 299 * This is used to create a constructor for Serializable classes that 300 * construct an instance of the Serializable class using the 301 * no args constructor of the first non-Serializable superclass 302 * of the Serializable class. 303 */ 304 public final Constructor<?> newConstructorForSerialization( Class<?> cl ) { 305 return reflectionFactory.newConstructorForSerialization( cl ) ; 306 } 307 308 public final Constructor<?> newConstructorForExternalization(Class<?> cl) { 309 return reflectionFactory.newConstructorForExternalization( cl ) ; 310 } 311 312 /** 313 * Returns true if the given class defines a static initializer method, 314 * false otherwise. 315 */ 316 public final boolean hasStaticInitializerForSerialization(Class<?> cl) { 317 return reflectionFactory.hasStaticInitializerForSerialization(cl); 318 } 319 320 public final MethodHandle writeObjectForSerialization(Class<?> cl) { 321 return reflectionFactory.writeObjectForSerialization(cl); 322 } 323 324 public final MethodHandle readObjectForSerialization(Class<?> cl) { 325 return reflectionFactory.readObjectForSerialization(cl); 326 } 327 328 public final MethodHandle readObjectNoDataForSerialization(Class<?> cl) { 329 return reflectionFactory.readObjectNoDataForSerialization(cl); 330 } 331 332 public final MethodHandle readResolveForSerialization(Class<?> cl) { 333 return reflectionFactory.readResolveForSerialization(cl); 334 } 335 336 public final MethodHandle writeReplaceForSerialization(Class<?> cl) { 337 return reflectionFactory.writeReplaceForSerialization(cl); 338 } 339 340 /** 341 * Return a new OptionalDataException instance. 342 * @return a new OptionalDataException instance 343 */ 344 public final OptionalDataException newOptionalDataExceptionForSerialization(boolean bool) { 345 return reflectionFactory.newOptionalDataExceptionForSerialization(bool); 346 } 347 348} 349