1 /* 2 * Copyright (c) 2014, 2024, 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 26 package java.lang.invoke; 27 28 import java.lang.constant.ClassDesc; 29 import java.lang.constant.Constable; 30 import java.lang.constant.ConstantDesc; 31 import java.lang.constant.ConstantDescs; 32 import java.lang.constant.DirectMethodHandleDesc; 33 import java.lang.constant.DynamicConstantDesc; 34 import java.util.List; 35 import java.util.Objects; 36 import java.util.Optional; 37 38 import jdk.internal.vm.annotation.DontInline; 39 import jdk.internal.vm.annotation.ForceInline; 40 import jdk.internal.vm.annotation.IntrinsicCandidate; 41 import jdk.internal.vm.annotation.Stable; 42 43 import static java.lang.invoke.MethodHandleStatics.UNSAFE; 44 45 /** 46 * A VarHandle is a dynamically strongly typed reference to a variable, or to a 47 * parametrically-defined family of variables, including static fields, 48 * non-static fields, array elements, or components of an off-heap data 49 * structure. Access to such variables is supported under various 50 * <em>access modes</em>, including plain read/write access, volatile 51 * read/write access, and compare-and-set. 52 * 53 * <p>VarHandles are immutable and have no visible state. VarHandles cannot be 54 * subclassed by the user. 55 * 56 * <p>A VarHandle has: 57 * <ul> 58 * <li>a {@link #varType variable type} T, the type of every variable referenced 59 * by this VarHandle; and 60 * <li>a list of {@link #coordinateTypes coordinate types} 61 * {@code CT1, CT2, ..., CTn}, the types of <em>coordinate expressions</em> that 62 * jointly locate a variable referenced by this VarHandle. 63 * </ul> 64 * Variable and coordinate types may be primitive or reference, and are 65 * represented by {@code Class} objects. The list of coordinate types may be 66 * empty. 67 * 68 * <p>Factory methods that produce or {@link java.lang.invoke.MethodHandles.Lookup 69 * lookup} VarHandle instances document the supported variable type and the list 70 * of coordinate types. 71 * 72 * <p>Each access mode is associated with one <em>access mode method</em>, a 73 * <a href="MethodHandle.html#sigpoly">signature polymorphic</a> method named 74 * for the access mode. When an access mode method is invoked on a VarHandle 75 * instance, the initial arguments to the invocation are coordinate expressions 76 * that indicate in precisely which object the variable is to be accessed. 77 * Trailing arguments to the invocation represent values of importance to the 78 * access mode. For example, the various compare-and-set or compare-and-exchange 79 * access modes require two trailing arguments for the variable's expected value 80 * and new value. 81 * 82 * <p>The arity and types of arguments to the invocation of an access mode 83 * method are not checked statically. Instead, each access mode method 84 * specifies an {@link #accessModeType(AccessMode) access mode type}, 85 * represented as an instance of {@link MethodType}, that serves as a kind of 86 * method signature against which the arguments are checked dynamically. An 87 * access mode type gives formal parameter types in terms of the coordinate 88 * types of a VarHandle instance and the types for values of importance to the 89 * access mode. An access mode type also gives a return type, often in terms of 90 * the variable type of a VarHandle instance. When an access mode method is 91 * invoked on a VarHandle instance, the symbolic type descriptor at the 92 * call site, the run time types of arguments to the invocation, and the run 93 * time type of the return value, must <a href="#invoke">match</a> the types 94 * given in the access mode type. A runtime exception will be thrown if the 95 * match fails. 96 * 97 * For example, the access mode method {@link #compareAndSet} specifies that if 98 * its receiver is a VarHandle instance with coordinate types 99 * {@code CT1, ..., CTn} and variable type {@code T}, then its access mode type 100 * is {@code (CT1 c1, ..., CTn cn, T expectedValue, T newValue)boolean}. 101 * Suppose that a VarHandle instance can access array elements, and that its 102 * coordinate types are {@code String[]} and {@code int} while its variable type 103 * is {@code String}. The access mode type for {@code compareAndSet} on this 104 * VarHandle instance would be 105 * {@code (String[] c1, int c2, String expectedValue, String newValue)boolean}. 106 * Such a VarHandle instance may be produced by the 107 * {@link MethodHandles#arrayElementVarHandle(Class) array factory method} and 108 * access array elements as follows: 109 * <pre> {@code 110 * String[] sa = ... 111 * VarHandle avh = MethodHandles.arrayElementVarHandle(String[].class); 112 * boolean r = avh.compareAndSet(sa, 10, "expected", "new"); 113 * }</pre> 114 * 115 * <p>Access modes control atomicity and consistency properties. 116 * <em>Plain</em> read ({@code get}) and write ({@code set}) 117 * accesses are guaranteed to be bitwise atomic only for references 118 * and for primitive values of at most 32 bits, and impose no observable 119 * ordering constraints with respect to threads other than the 120 * executing thread. <em>Opaque</em> operations are bitwise atomic and 121 * coherently ordered with respect to accesses to the same variable. 122 * In addition to obeying Opaque properties, <em>Acquire</em> mode 123 * reads and their subsequent accesses are ordered after matching 124 * <em>Release</em> mode writes and their previous accesses. In 125 * addition to obeying Acquire and Release properties, all 126 * <em>Volatile</em> operations are totally ordered with respect to 127 * each other. 128 * 129 * <p>Access modes are grouped into the following categories: 130 * <ul> 131 * <li>read access modes that get the value of a variable under specified 132 * memory ordering effects. 133 * The set of corresponding access mode methods belonging to this group 134 * consists of the methods 135 * {@link #get get}, 136 * {@link #getVolatile getVolatile}, 137 * {@link #getAcquire getAcquire}, 138 * {@link #getOpaque getOpaque}. 139 * <li>write access modes that set the value of a variable under specified 140 * memory ordering effects. 141 * The set of corresponding access mode methods belonging to this group 142 * consists of the methods 143 * {@link #set set}, 144 * {@link #setVolatile setVolatile}, 145 * {@link #setRelease setRelease}, 146 * {@link #setOpaque setOpaque}. 147 * <li>atomic update access modes that, for example, atomically compare and set 148 * the value of a variable under specified memory ordering effects. 149 * The set of corresponding access mode methods belonging to this group 150 * consists of the methods 151 * {@link #compareAndSet compareAndSet}, 152 * {@link #weakCompareAndSetPlain weakCompareAndSetPlain}, 153 * {@link #weakCompareAndSet weakCompareAndSet}, 154 * {@link #weakCompareAndSetAcquire weakCompareAndSetAcquire}, 155 * {@link #weakCompareAndSetRelease weakCompareAndSetRelease}, 156 * {@link #compareAndExchangeAcquire compareAndExchangeAcquire}, 157 * {@link #compareAndExchange compareAndExchange}, 158 * {@link #compareAndExchangeRelease compareAndExchangeRelease}, 159 * {@link #getAndSet getAndSet}, 160 * {@link #getAndSetAcquire getAndSetAcquire}, 161 * {@link #getAndSetRelease getAndSetRelease}. 162 * <li>numeric atomic update access modes that, for example, atomically get and 163 * set with addition the value of a variable under specified memory ordering 164 * effects. 165 * The set of corresponding access mode methods belonging to this group 166 * consists of the methods 167 * {@link #getAndAdd getAndAdd}, 168 * {@link #getAndAddAcquire getAndAddAcquire}, 169 * {@link #getAndAddRelease getAndAddRelease}, 170 * <li>bitwise atomic update access modes that, for example, atomically get and 171 * bitwise OR the value of a variable under specified memory ordering 172 * effects. 173 * The set of corresponding access mode methods belonging to this group 174 * consists of the methods 175 * {@link #getAndBitwiseOr getAndBitwiseOr}, 176 * {@link #getAndBitwiseOrAcquire getAndBitwiseOrAcquire}, 177 * {@link #getAndBitwiseOrRelease getAndBitwiseOrRelease}, 178 * {@link #getAndBitwiseAnd getAndBitwiseAnd}, 179 * {@link #getAndBitwiseAndAcquire getAndBitwiseAndAcquire}, 180 * {@link #getAndBitwiseAndRelease getAndBitwiseAndRelease}, 181 * {@link #getAndBitwiseXor getAndBitwiseXor}, 182 * {@link #getAndBitwiseXorAcquire getAndBitwiseXorAcquire}, 183 * {@link #getAndBitwiseXorRelease getAndBitwiseXorRelease}. 184 * </ul> 185 * 186 * <p>Factory methods that produce or {@link java.lang.invoke.MethodHandles.Lookup 187 * lookup} VarHandle instances document the set of access modes that are 188 * supported, which may also include documenting restrictions based on the 189 * variable type and whether a variable is read-only. If an access mode is not 190 * supported then the corresponding access mode method will on invocation throw 191 * an {@code UnsupportedOperationException}. Factory methods should document 192 * any additional undeclared exceptions that may be thrown by access mode 193 * methods. 194 * The {@link #get get} access mode is supported for all 195 * VarHandle instances and the corresponding method never throws 196 * {@code UnsupportedOperationException}. 197 * If a VarHandle references a read-only variable (for example a {@code final} 198 * field) then write, atomic update, numeric atomic update, and bitwise atomic 199 * update access modes are not supported and corresponding methods throw 200 * {@code UnsupportedOperationException}. 201 * Read/write access modes (if supported), with the exception of 202 * {@code get} and {@code set}, provide atomic access for 203 * reference types and all primitive types. 204 * Unless stated otherwise in the documentation of a factory method, the access 205 * modes {@code get} and {@code set} (if supported) provide atomic access for 206 * reference types and all primitives types, with the exception of {@code long} 207 * and {@code double} on 32-bit platforms. 208 * 209 * <p>Access modes will override any memory ordering effects specified at 210 * the declaration site of a variable. For example, a VarHandle accessing 211 * a field using the {@code get} access mode will access the field as 212 * specified <em>by its access mode</em> even if that field is declared 213 * {@code volatile}. When mixed access is performed extreme care should be 214 * taken since the Java Memory Model may permit surprising results. 215 * 216 * <p>In addition to supporting access to variables under various access modes, 217 * a set of static methods, referred to as memory fence methods, is also 218 * provided for fine-grained control of memory ordering. 219 * 220 * The Java Language Specification permits other threads to observe operations 221 * as if they were executed in orders different than are apparent in program 222 * source code, subject to constraints arising, for example, from the use of 223 * locks, {@code volatile} fields or VarHandles. The static methods, 224 * {@link #fullFence fullFence}, {@link #acquireFence acquireFence}, 225 * {@link #releaseFence releaseFence}, {@link #loadLoadFence loadLoadFence} and 226 * {@link #storeStoreFence storeStoreFence}, can also be used to impose 227 * constraints. Their specifications, as is the case for certain access modes, 228 * are phrased in terms of the lack of "reorderings" -- observable ordering 229 * effects that might otherwise occur if the fence was not present. More 230 * precise phrasing of the specification of access mode methods and memory fence 231 * methods may accompany future updates of the Java Language Specification. 232 * 233 * <h2>Compiling invocation of access mode methods</h2> 234 * A Java method call expression naming an access mode method can invoke a 235 * VarHandle from Java source code. From the viewpoint of source code, these 236 * methods can take any arguments and their polymorphic result (if expressed) 237 * can be cast to any return type. Formally this is accomplished by giving the 238 * access mode methods variable arity {@code Object} arguments and 239 * {@code Object} return types (if the return type is polymorphic), but they 240 * have an additional quality called <em>signature polymorphism</em> which 241 * connects this freedom of invocation directly to the JVM execution stack. 242 * <p> 243 * As is usual with virtual methods, source-level calls to access mode methods 244 * compile to an {@code invokevirtual} instruction. More unusually, the 245 * compiler must record the actual argument types, and may not perform method 246 * invocation conversions on the arguments. Instead, it must generate 247 * instructions to push them on the stack according to their own unconverted 248 * types. The VarHandle object itself will be pushed on the stack before the 249 * arguments. The compiler then generates an {@code invokevirtual} instruction 250 * that invokes the access mode method with a symbolic type descriptor which 251 * describes the argument and return types. 252 * <p> 253 * To issue a complete symbolic type descriptor, the compiler must also 254 * determine the return type (if polymorphic). This is based on a cast on the 255 * method invocation expression, if there is one, or else {@code Object} if the 256 * invocation is an expression, or else {@code void} if the invocation is a 257 * statement. The cast may be to a primitive type (but not {@code void}). 258 * <p> 259 * As a corner case, an uncasted {@code null} argument is given a symbolic type 260 * descriptor of {@code java.lang.Void}. The ambiguity with the type 261 * {@code Void} is harmless, since there are no references of type {@code Void} 262 * except the null reference. 263 * 264 * 265 * <h2><a id="invoke">Performing invocation of access mode methods</a></h2> 266 * The first time an {@code invokevirtual} instruction is executed it is linked 267 * by symbolically resolving the names in the instruction and verifying that 268 * the method call is statically legal. This also holds for calls to access mode 269 * methods. In this case, the symbolic type descriptor emitted by the compiler 270 * is checked for correct syntax, and names it contains are resolved. Thus, an 271 * {@code invokevirtual} instruction which invokes an access mode method will 272 * always link, as long as the symbolic type descriptor is syntactically 273 * well-formed and the types exist. 274 * <p> 275 * When the {@code invokevirtual} is executed after linking, the receiving 276 * VarHandle's access mode type is first checked by the JVM to ensure that it 277 * matches the symbolic type descriptor. If the type 278 * match fails, it means that the access mode method which the caller is 279 * invoking is not present on the individual VarHandle being invoked. 280 * 281 * <p id="invoke-behavior"> 282 * Invocation of an access mode method behaves, by default, as if an invocation of 283 * {@link MethodHandle#invoke}, where the receiving method handle accepts the 284 * VarHandle instance as the leading argument. More specifically, the 285 * following, where {@code {access-mode}} corresponds to the access mode method 286 * name: 287 * <pre> {@code 288 * VarHandle vh = .. 289 * R r = (R) vh.{access-mode}(p1, p2, ..., pN); 290 * }</pre> 291 * behaves as if: 292 * <pre> {@code 293 * VarHandle vh = .. 294 * VarHandle.AccessMode am = VarHandle.AccessMode.valueFromMethodName("{access-mode}"); 295 * MethodHandle mh = MethodHandles.varHandleExactInvoker( 296 * am, 297 * vh.accessModeType(am)); 298 * 299 * R r = (R) mh.invoke(vh, p1, p2, ..., pN) 300 * }</pre> 301 * (modulo access mode methods do not declare throwing of {@code Throwable}). 302 * This is equivalent to: 303 * <pre> {@code 304 * MethodHandle mh = MethodHandles.lookup().findVirtual( 305 * VarHandle.class, 306 * "{access-mode}", 307 * MethodType.methodType(R, p1, p2, ..., pN)); 308 * 309 * R r = (R) mh.invokeExact(vh, p1, p2, ..., pN) 310 * }</pre> 311 * where the desired method type is the symbolic type descriptor and a 312 * {@link MethodHandle#invokeExact} is performed, since before invocation of the 313 * target, the handle will apply reference casts as necessary and box, unbox, or 314 * widen primitive values, as if by {@link MethodHandle#asType asType} (see also 315 * {@link MethodHandles#varHandleInvoker}). 316 * 317 * More concisely, such behavior is equivalent to: 318 * <pre> {@code 319 * VarHandle vh = .. 320 * VarHandle.AccessMode am = VarHandle.AccessMode.valueFromMethodName("{access-mode}"); 321 * MethodHandle mh = vh.toMethodHandle(am); 322 * 323 * R r = (R) mh.invoke(p1, p2, ..., pN) 324 * }</pre> 325 * Where, in this case, the method handle is bound to the VarHandle instance. 326 * 327 * <p id="invoke-exact-behavior"> 328 * A VarHandle's invocation behavior can be adjusted (see {@link #withInvokeExactBehavior}) such that invocation of 329 * an access mode method behaves as if invocation of {@link MethodHandle#invokeExact}, 330 * where the receiving method handle accepts the VarHandle instance as the leading argument. 331 * More specifically, the following, where {@code {access-mode}} corresponds to the access mode method 332 * name: 333 * <pre> {@code 334 * VarHandle vh = .. 335 * R r = (R) vh.{access-mode}(p1, p2, ..., pN); 336 * }</pre> 337 * behaves as if: 338 * <pre> {@code 339 * VarHandle vh = .. 340 * VarHandle.AccessMode am = VarHandle.AccessMode.valueFromMethodName("{access-mode}"); 341 * MethodHandle mh = MethodHandles.varHandleExactInvoker( 342 * am, 343 * vh.accessModeType(am)); 344 * 345 * R r = (R) mh.invokeExact(vh, p1, p2, ..., pN) 346 * }</pre> 347 * (modulo access mode methods do not declare throwing of {@code Throwable}). 348 * 349 * More concisely, such behavior is equivalent to: 350 * <pre> {@code 351 * VarHandle vh = .. 352 * VarHandle.AccessMode am = VarHandle.AccessMode.valueFromMethodName("{access-mode}"); 353 * MethodHandle mh = vh.toMethodHandle(am); 354 * 355 * R r = (R) mh.invokeExact(p1, p2, ..., pN) 356 * }</pre> 357 * Where, in this case, the method handle is bound to the VarHandle instance. 358 * 359 * <h2>Invocation checking</h2> 360 * In typical programs, VarHandle access mode type matching will usually 361 * succeed. But if a match fails, the JVM will throw a 362 * {@link WrongMethodTypeException}. 363 * <p> 364 * Thus, an access mode type mismatch which might show up as a linkage error 365 * in a statically typed program can show up as a dynamic 366 * {@code WrongMethodTypeException} in a program which uses VarHandles. 367 * <p> 368 * Because access mode types contain "live" {@code Class} objects, method type 369 * matching takes into account both type names and class loaders. 370 * Thus, even if a VarHandle {@code VH} is created in one class loader 371 * {@code L1} and used in another {@code L2}, VarHandle access mode method 372 * calls are type-safe, because the caller's symbolic type descriptor, as 373 * resolved in {@code L2}, is matched against the original callee method's 374 * symbolic type descriptor, as resolved in {@code L1}. The resolution in 375 * {@code L1} happens when {@code VH} is created and its access mode types are 376 * assigned, while the resolution in {@code L2} happens when the 377 * {@code invokevirtual} instruction is linked. 378 * <p> 379 * Apart from type descriptor checks, a VarHandles's capability to 380 * access its variables is unrestricted. 381 * If a VarHandle is formed on a non-public variable by a class that has access 382 * to that variable, the resulting VarHandle can be used in any place by any 383 * caller who receives a reference to it. 384 * <p> 385 * Unlike with the Core Reflection API, where access is checked every time a 386 * reflective method is invoked, VarHandle access checking is performed 387 * <a href="MethodHandles.Lookup.html#access">when the VarHandle is 388 * created</a>. 389 * Thus, VarHandles to non-public variables, or to variables in non-public 390 * classes, should generally be kept secret. They should not be passed to 391 * untrusted code unless their use from the untrusted code would be harmless. 392 * 393 * 394 * <h2>VarHandle creation</h2> 395 * Java code can create a VarHandle that directly accesses any field that is 396 * accessible to that code. This is done via a reflective, capability-based 397 * API called {@link java.lang.invoke.MethodHandles.Lookup 398 * MethodHandles.Lookup}. 399 * For example, a VarHandle for a non-static field can be obtained 400 * from {@link java.lang.invoke.MethodHandles.Lookup#findVarHandle 401 * Lookup.findVarHandle}. 402 * There is also a conversion method from Core Reflection API objects, 403 * {@link java.lang.invoke.MethodHandles.Lookup#unreflectVarHandle 404 * Lookup.unreflectVarHandle}. 405 * <p> 406 * Access to protected field members is restricted to receivers only of the 407 * accessing class, or one of its subclasses, and the accessing class must in 408 * turn be a subclass (or package sibling) of the protected member's defining 409 * class. If a VarHandle refers to a protected non-static field of a declaring 410 * class outside the current package, the receiver argument will be narrowed to 411 * the type of the accessing class. 412 * 413 * <h2>Interoperation between VarHandles and the Core Reflection API</h2> 414 * Using factory methods in the {@link java.lang.invoke.MethodHandles.Lookup 415 * Lookup} API, any field represented by a Core Reflection API object 416 * can be converted to a behaviorally equivalent VarHandle. 417 * For example, a reflective {@link java.lang.reflect.Field Field} can 418 * be converted to a VarHandle using 419 * {@link java.lang.invoke.MethodHandles.Lookup#unreflectVarHandle 420 * Lookup.unreflectVarHandle}. 421 * The resulting VarHandles generally provide more direct and efficient 422 * access to the underlying fields. 423 * <p> 424 * As a special case, when the Core Reflection API is used to view the 425 * signature polymorphic access mode methods in this class, they appear as 426 * ordinary non-polymorphic methods. Their reflective appearance, as viewed by 427 * {@link java.lang.Class#getDeclaredMethod Class.getDeclaredMethod}, 428 * is unaffected by their special status in this API. 429 * For example, {@link java.lang.reflect.Method#getModifiers 430 * Method.getModifiers} 431 * will report exactly those modifier bits required for any similarly 432 * declared method, including in this case {@code native} and {@code varargs} 433 * bits. 434 * <p> 435 * As with any reflected method, these methods (when reflected) may be invoked 436 * directly via {@link java.lang.reflect.Method#invoke java.lang.reflect.Method.invoke}, 437 * via JNI, or indirectly via 438 * {@link java.lang.invoke.MethodHandles.Lookup#unreflect Lookup.unreflect}. 439 * However, such reflective calls do not result in access mode method 440 * invocations. Such a call, if passed the required argument (a single one, of 441 * type {@code Object[]}), will ignore the argument and will throw an 442 * {@code UnsupportedOperationException}. 443 * <p> 444 * Since {@code invokevirtual} instructions can natively invoke VarHandle 445 * access mode methods under any symbolic type descriptor, this reflective view 446 * conflicts with the normal presentation of these methods via bytecodes. 447 * Thus, these native methods, when reflectively viewed by 448 * {@code Class.getDeclaredMethod}, may be regarded as placeholders only. 449 * <p> 450 * In order to obtain an invoker method for a particular access mode type, 451 * use {@link java.lang.invoke.MethodHandles#varHandleExactInvoker} or 452 * {@link java.lang.invoke.MethodHandles#varHandleInvoker}. The 453 * {@link java.lang.invoke.MethodHandles.Lookup#findVirtual Lookup.findVirtual} 454 * API is also able to return a method handle to call an access mode method for 455 * any specified access mode type and is equivalent in behavior to 456 * {@link java.lang.invoke.MethodHandles#varHandleInvoker}. 457 * 458 * <h2>Interoperation between VarHandles and Java generics</h2> 459 * A VarHandle can be obtained for a variable, such as a field, which is 460 * declared with Java generic types. As with the Core Reflection API, the 461 * VarHandle's variable type will be constructed from the erasure of the 462 * source-level type. When a VarHandle access mode method is invoked, the 463 * types 464 * of its arguments or the return value cast type may be generic types or type 465 * instances. If this occurs, the compiler will replace those types by their 466 * erasures when it constructs the symbolic type descriptor for the 467 * {@code invokevirtual} instruction. 468 * 469 * @see MethodHandle 470 * @see MethodHandles 471 * @see MethodType 472 * @since 9 473 */ 474 public abstract sealed class VarHandle implements Constable 475 permits IndirectVarHandle, LazyInitializingVarHandle, SegmentVarHandle, 476 VarHandleByteArrayAsChars.ByteArrayViewVarHandle, 477 VarHandleByteArrayAsDoubles.ByteArrayViewVarHandle, 478 VarHandleByteArrayAsFloats.ByteArrayViewVarHandle, 479 VarHandleByteArrayAsInts.ByteArrayViewVarHandle, 480 VarHandleByteArrayAsLongs.ByteArrayViewVarHandle, 481 VarHandleByteArrayAsShorts.ByteArrayViewVarHandle, 482 VarHandleBooleans.Array, 483 VarHandleBooleans.FieldInstanceReadOnly, 484 VarHandleBooleans.FieldStaticReadOnly, 485 VarHandleBytes.Array, 486 VarHandleBytes.FieldInstanceReadOnly, 487 VarHandleBytes.FieldStaticReadOnly, 488 VarHandleChars.Array, 489 VarHandleChars.FieldInstanceReadOnly, 490 VarHandleChars.FieldStaticReadOnly, 491 VarHandleDoubles.Array, 492 VarHandleDoubles.FieldInstanceReadOnly, 493 VarHandleDoubles.FieldStaticReadOnly, 494 VarHandleFloats.Array, 495 VarHandleFloats.FieldInstanceReadOnly, 496 VarHandleFloats.FieldStaticReadOnly, 497 VarHandleInts.Array, 498 VarHandleInts.FieldInstanceReadOnly, 499 VarHandleInts.FieldStaticReadOnly, 500 VarHandleLongs.Array, 501 VarHandleLongs.FieldInstanceReadOnly, 502 VarHandleLongs.FieldStaticReadOnly, 503 VarHandleReferences.Array, 504 VarHandleReferences.FieldInstanceReadOnly, 505 VarHandleReferences.FieldStaticReadOnly, 506 VarHandleShorts.Array, 507 VarHandleShorts.FieldInstanceReadOnly, 508 VarHandleShorts.FieldStaticReadOnly, 509 VarHandleFlatValues.FieldInstanceReadOnly, 510 VarHandleNonAtomicReferences.Array, 511 VarHandleNonAtomicReferences.FieldInstanceReadOnly, 512 VarHandleNonAtomicReferences.FieldStaticReadOnly, 513 VarHandleNonAtomicFlatValues.FieldInstanceReadOnly { 514 final VarForm vform; 515 final boolean exact; 516 517 VarHandle(VarForm vform) { 518 this(vform, false); 519 } 520 521 VarHandle(VarForm vform, boolean exact) { 522 this.vform = vform; 523 this.exact = exact; 524 } 525 526 /** 527 * Returns the target VarHandle. Subclasses may override this method to implement 528 * additional logic for example lazily initializing the declaring class of a static field var handle. 529 */ 530 @ForceInline 531 VarHandle target() { 532 return asDirect(); 533 } 534 535 /** 536 * Returns the direct target VarHandle. Indirect VarHandle subclasses should implement 537 * this method. 538 * 539 * @see #getMethodHandle(int) 540 * @see #checkAccessModeThenIsDirect(AccessDescriptor) 541 */ 542 @ForceInline 543 VarHandle asDirect() { 544 return this; 545 } 546 547 /** 548 * Returns {@code true} if this VarHandle has <a href="#invoke-exact-behavior"><em>invoke-exact behavior</em></a>. 549 * 550 * @see #withInvokeExactBehavior() 551 * @see #withInvokeBehavior() 552 * @return {@code true} if this VarHandle has <a href="#invoke-exact-behavior"><em>invoke-exact behavior</em></a>. 553 * @since 16 554 */ 555 public boolean hasInvokeExactBehavior() { 556 return exact; 557 } 558 559 // Plain accessors 560 561 /** 562 * Returns the value of a variable, with memory semantics of reading as 563 * if the variable was declared non-{@code volatile}. Commonly referred to 564 * as plain read access. 565 * 566 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn)T}. 567 * 568 * <p>The symbolic type descriptor at the call site of {@code get} 569 * must match the access mode type that is the result of calling 570 * {@code accessModeType(VarHandle.AccessMode.GET)} on this VarHandle. 571 * 572 * <p>This access mode is supported by all VarHandle instances and never 573 * throws {@code UnsupportedOperationException}. 574 * 575 * @param args the signature-polymorphic parameter list of the form 576 * {@code (CT1 ct1, ..., CTn)} 577 * , statically represented using varargs. 578 * @return the signature-polymorphic result that is the value of the 579 * variable 580 * , statically represented using {@code Object}. 581 * @throws WrongMethodTypeException if the access mode type does not 582 * match the caller's symbolic type descriptor. 583 * @throws ClassCastException if the access mode type matches the caller's 584 * symbolic type descriptor, but a reference cast fails. 585 */ 586 public final native 587 @MethodHandle.PolymorphicSignature 588 @IntrinsicCandidate 589 Object get(Object... args); 590 591 /** 592 * Sets the value of a variable to the {@code newValue}, with memory 593 * semantics of setting as if the variable was declared non-{@code volatile} 594 * and non-{@code final}. Commonly referred to as plain write access. 595 * 596 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T newValue)void} 597 * 598 * <p>The symbolic type descriptor at the call site of {@code set} 599 * must match the access mode type that is the result of calling 600 * {@code accessModeType(VarHandle.AccessMode.SET)} on this VarHandle. 601 * 602 * @param args the signature-polymorphic parameter list of the form 603 * {@code (CT1 ct1, ..., CTn ctn, T newValue)} 604 * , statically represented using varargs. 605 * @throws UnsupportedOperationException if the access mode is unsupported 606 * for this VarHandle. 607 * @throws WrongMethodTypeException if the access mode type does not 608 * match the caller's symbolic type descriptor. 609 * @throws ClassCastException if the access mode type matches the caller's 610 * symbolic type descriptor, but a reference cast fails. 611 */ 612 public final native 613 @MethodHandle.PolymorphicSignature 614 @IntrinsicCandidate 615 void set(Object... args); 616 617 618 // Volatile accessors 619 620 /** 621 * Returns the value of a variable, with memory semantics of reading as if 622 * the variable was declared {@code volatile}. 623 * 624 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn)T}. 625 * 626 * <p>The symbolic type descriptor at the call site of {@code getVolatile} 627 * must match the access mode type that is the result of calling 628 * {@code accessModeType(VarHandle.AccessMode.GET_VOLATILE)} on this 629 * VarHandle. 630 * 631 * @param args the signature-polymorphic parameter list of the form 632 * {@code (CT1 ct1, ..., CTn ctn)} 633 * , statically represented using varargs. 634 * @return the signature-polymorphic result that is the value of the 635 * variable 636 * , statically represented using {@code Object}. 637 * @throws UnsupportedOperationException if the access mode is unsupported 638 * for this VarHandle. 639 * @throws WrongMethodTypeException if the access mode type does not 640 * match the caller's symbolic type descriptor. 641 * @throws ClassCastException if the access mode type matches the caller's 642 * symbolic type descriptor, but a reference cast fails. 643 */ 644 public final native 645 @MethodHandle.PolymorphicSignature 646 @IntrinsicCandidate 647 Object getVolatile(Object... args); 648 649 /** 650 * Sets the value of a variable to the {@code newValue}, with memory 651 * semantics of setting as if the variable was declared {@code volatile}. 652 * 653 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T newValue)void}. 654 * 655 * <p>The symbolic type descriptor at the call site of {@code setVolatile} 656 * must match the access mode type that is the result of calling 657 * {@code accessModeType(VarHandle.AccessMode.SET_VOLATILE)} on this 658 * VarHandle. 659 * 660 * @apiNote 661 * Ignoring the many semantic differences from C and C++, this method has 662 * memory ordering effects compatible with {@code memory_order_seq_cst}. 663 * 664 * @param args the signature-polymorphic parameter list of the form 665 * {@code (CT1 ct1, ..., CTn ctn, T newValue)} 666 * , statically represented using varargs. 667 * @throws UnsupportedOperationException if the access mode is unsupported 668 * for this VarHandle. 669 * @throws WrongMethodTypeException if the access mode type does not 670 * match the caller's symbolic type descriptor. 671 * @throws ClassCastException if the access mode type matches the caller's 672 * symbolic type descriptor, but a reference cast fails. 673 */ 674 public final native 675 @MethodHandle.PolymorphicSignature 676 @IntrinsicCandidate 677 void setVolatile(Object... args); 678 679 680 /** 681 * Returns the value of a variable, accessed in program order, but with no 682 * assurance of memory ordering effects with respect to other threads. 683 * 684 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn)T}. 685 * 686 * <p>The symbolic type descriptor at the call site of {@code getOpaque} 687 * must match the access mode type that is the result of calling 688 * {@code accessModeType(VarHandle.AccessMode.GET_OPAQUE)} on this 689 * VarHandle. 690 * 691 * @param args the signature-polymorphic parameter list of the form 692 * {@code (CT1 ct1, ..., CTn ctn)} 693 * , statically represented using varargs. 694 * @return the signature-polymorphic result that is the value of the 695 * variable 696 * , statically represented using {@code Object}. 697 * @throws UnsupportedOperationException if the access mode is unsupported 698 * for this VarHandle. 699 * @throws WrongMethodTypeException if the access mode type does not 700 * match the caller's symbolic type descriptor. 701 * @throws ClassCastException if the access mode type matches the caller's 702 * symbolic type descriptor, but a reference cast fails. 703 */ 704 public final native 705 @MethodHandle.PolymorphicSignature 706 @IntrinsicCandidate 707 Object getOpaque(Object... args); 708 709 /** 710 * Sets the value of a variable to the {@code newValue}, in program order, 711 * but with no assurance of memory ordering effects with respect to other 712 * threads. 713 * 714 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T newValue)void}. 715 * 716 * <p>The symbolic type descriptor at the call site of {@code setOpaque} 717 * must match the access mode type that is the result of calling 718 * {@code accessModeType(VarHandle.AccessMode.SET_OPAQUE)} on this 719 * VarHandle. 720 * 721 * @param args the signature-polymorphic parameter list of the form 722 * {@code (CT1 ct1, ..., CTn ctn, T newValue)} 723 * , statically represented using varargs. 724 * @throws UnsupportedOperationException if the access mode is unsupported 725 * for this VarHandle. 726 * @throws WrongMethodTypeException if the access mode type does not 727 * match the caller's symbolic type descriptor. 728 * @throws ClassCastException if the access mode type matches the caller's 729 * symbolic type descriptor, but a reference cast fails. 730 */ 731 public final native 732 @MethodHandle.PolymorphicSignature 733 @IntrinsicCandidate 734 void setOpaque(Object... args); 735 736 737 // Lazy accessors 738 739 /** 740 * Returns the value of a variable, and ensures that subsequent loads and 741 * stores are not reordered before this access. 742 * 743 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn)T}. 744 * 745 * <p>The symbolic type descriptor at the call site of {@code getAcquire} 746 * must match the access mode type that is the result of calling 747 * {@code accessModeType(VarHandle.AccessMode.GET_ACQUIRE)} on this 748 * VarHandle. 749 * 750 * @apiNote 751 * Ignoring the many semantic differences from C and C++, this method has 752 * memory ordering effects compatible with {@code memory_order_acquire} 753 * ordering. 754 * 755 * @param args the signature-polymorphic parameter list of the form 756 * {@code (CT1 ct1, ..., CTn ctn)} 757 * , statically represented using varargs. 758 * @return the signature-polymorphic result that is the value of the 759 * variable 760 * , statically represented using {@code Object}. 761 * @throws UnsupportedOperationException if the access mode is unsupported 762 * for this VarHandle. 763 * @throws WrongMethodTypeException if the access mode type does not 764 * match the caller's symbolic type descriptor. 765 * @throws ClassCastException if the access mode type matches the caller's 766 * symbolic type descriptor, but a reference cast fails. 767 */ 768 public final native 769 @MethodHandle.PolymorphicSignature 770 @IntrinsicCandidate 771 Object getAcquire(Object... args); 772 773 /** 774 * Sets the value of a variable to the {@code newValue}, and ensures that 775 * prior loads and stores are not reordered after this access. 776 * 777 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T newValue)void}. 778 * 779 * <p>The symbolic type descriptor at the call site of {@code setRelease} 780 * must match the access mode type that is the result of calling 781 * {@code accessModeType(VarHandle.AccessMode.SET_RELEASE)} on this 782 * VarHandle. 783 * 784 * @apiNote 785 * Ignoring the many semantic differences from C and C++, this method has 786 * memory ordering effects compatible with {@code memory_order_release} 787 * ordering. 788 * 789 * @param args the signature-polymorphic parameter list of the form 790 * {@code (CT1 ct1, ..., CTn ctn, T newValue)} 791 * , statically represented using varargs. 792 * @throws UnsupportedOperationException if the access mode is unsupported 793 * for this VarHandle. 794 * @throws WrongMethodTypeException if the access mode type does not 795 * match the caller's symbolic type descriptor. 796 * @throws ClassCastException if the access mode type matches the caller's 797 * symbolic type descriptor, but a reference cast fails. 798 */ 799 public final native 800 @MethodHandle.PolymorphicSignature 801 @IntrinsicCandidate 802 void setRelease(Object... args); 803 804 805 // Compare and set accessors 806 807 /** 808 * Atomically sets the value of a variable to the {@code newValue} with the 809 * memory semantics of {@link #setVolatile} if the variable's current value, 810 * referred to as the <em>witness value</em>, {@code ==} the 811 * {@code expectedValue}, as accessed with the memory semantics of 812 * {@link #getVolatile}. 813 * 814 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)boolean}. 815 * 816 * <p>The symbolic type descriptor at the call site of {@code 817 * compareAndSet} must match the access mode type that is the result of 818 * calling {@code accessModeType(VarHandle.AccessMode.COMPARE_AND_SET)} on 819 * this VarHandle. 820 * 821 * @param args the signature-polymorphic parameter list of the form 822 * {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)} 823 * , statically represented using varargs. 824 * @return {@code true} if successful, otherwise {@code false} if the 825 * <em>witness value</em> was not the same as the {@code expectedValue}. 826 * @throws UnsupportedOperationException if the access mode is unsupported 827 * for this VarHandle. 828 * @throws WrongMethodTypeException if the access mode type does not 829 * match the caller's symbolic type descriptor. 830 * @throws ClassCastException if the access mode type matches the caller's 831 * symbolic type descriptor, but a reference cast fails. 832 * @see #setVolatile(Object...) 833 * @see #getVolatile(Object...) 834 */ 835 public final native 836 @MethodHandle.PolymorphicSignature 837 @IntrinsicCandidate 838 boolean compareAndSet(Object... args); 839 840 /** 841 * Atomically sets the value of a variable to the {@code newValue} with the 842 * memory semantics of {@link #setVolatile} if the variable's current value, 843 * referred to as the <em>witness value</em>, {@code ==} the 844 * {@code expectedValue}, as accessed with the memory semantics of 845 * {@link #getVolatile}. 846 * 847 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)T}. 848 * 849 * <p>The symbolic type descriptor at the call site of {@code 850 * compareAndExchange} 851 * must match the access mode type that is the result of calling 852 * {@code accessModeType(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)} 853 * on this VarHandle. 854 * 855 * @param args the signature-polymorphic parameter list of the form 856 * {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)} 857 * , statically represented using varargs. 858 * @return the signature-polymorphic result that is the <em>witness value</em>, which 859 * will be the same as the {@code expectedValue} if successful 860 * , statically represented using {@code Object}. 861 * @throws UnsupportedOperationException if the access mode is unsupported 862 * for this VarHandle. 863 * @throws WrongMethodTypeException if the access mode type is not 864 * compatible with the caller's symbolic type descriptor. 865 * @throws ClassCastException if the access mode type is compatible with the 866 * caller's symbolic type descriptor, but a reference cast fails. 867 * @see #setVolatile(Object...) 868 * @see #getVolatile(Object...) 869 */ 870 public final native 871 @MethodHandle.PolymorphicSignature 872 @IntrinsicCandidate 873 Object compareAndExchange(Object... args); 874 875 /** 876 * Atomically sets the value of a variable to the {@code newValue} with the 877 * memory semantics of {@link #set} if the variable's current value, 878 * referred to as the <em>witness value</em>, {@code ==} the 879 * {@code expectedValue}, as accessed with the memory semantics of 880 * {@link #getAcquire}. 881 * 882 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)T}. 883 * 884 * <p>The symbolic type descriptor at the call site of {@code 885 * compareAndExchangeAcquire} 886 * must match the access mode type that is the result of calling 887 * {@code accessModeType(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)} on 888 * this VarHandle. 889 * 890 * @param args the signature-polymorphic parameter list of the form 891 * {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)} 892 * , statically represented using varargs. 893 * @return the signature-polymorphic result that is the <em>witness value</em>, which 894 * will be the same as the {@code expectedValue} if successful 895 * , statically represented using {@code Object}. 896 * @throws UnsupportedOperationException if the access mode is unsupported 897 * for this VarHandle. 898 * @throws WrongMethodTypeException if the access mode type does not 899 * match the caller's symbolic type descriptor. 900 * @throws ClassCastException if the access mode type matches the caller's 901 * symbolic type descriptor, but a reference cast fails. 902 * @see #set(Object...) 903 * @see #getAcquire(Object...) 904 */ 905 public final native 906 @MethodHandle.PolymorphicSignature 907 @IntrinsicCandidate 908 Object compareAndExchangeAcquire(Object... args); 909 910 /** 911 * Atomically sets the value of a variable to the {@code newValue} with the 912 * memory semantics of {@link #setRelease} if the variable's current value, 913 * referred to as the <em>witness value</em>, {@code ==} the 914 * {@code expectedValue}, as accessed with the memory semantics of 915 * {@link #get}. 916 * 917 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)T}. 918 * 919 * <p>The symbolic type descriptor at the call site of {@code 920 * compareAndExchangeRelease} 921 * must match the access mode type that is the result of calling 922 * {@code accessModeType(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)} 923 * on this VarHandle. 924 * 925 * @param args the signature-polymorphic parameter list of the form 926 * {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)} 927 * , statically represented using varargs. 928 * @return the signature-polymorphic result that is the <em>witness value</em>, which 929 * will be the same as the {@code expectedValue} if successful 930 * , statically represented using {@code Object}. 931 * @throws UnsupportedOperationException if the access mode is unsupported 932 * for this VarHandle. 933 * @throws WrongMethodTypeException if the access mode type does not 934 * match the caller's symbolic type descriptor. 935 * @throws ClassCastException if the access mode type matches the caller's 936 * symbolic type descriptor, but a reference cast fails. 937 * @see #setRelease(Object...) 938 * @see #get(Object...) 939 */ 940 public final native 941 @MethodHandle.PolymorphicSignature 942 @IntrinsicCandidate 943 Object compareAndExchangeRelease(Object... args); 944 945 // Weak (spurious failures allowed) 946 947 /** 948 * Possibly atomically sets the value of a variable to the {@code newValue} 949 * with the semantics of {@link #set} if the variable's current value, 950 * referred to as the <em>witness value</em>, {@code ==} the 951 * {@code expectedValue}, as accessed with the memory semantics of 952 * {@link #get}. 953 * 954 * <p>This operation may fail spuriously (typically, due to memory 955 * contention) even if the <em>witness value</em> does match the expected value. 956 * 957 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)boolean}. 958 * 959 * <p>The symbolic type descriptor at the call site of {@code 960 * weakCompareAndSetPlain} must match the access mode type that is the result of 961 * calling {@code accessModeType(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)} 962 * on this VarHandle. 963 * 964 * @param args the signature-polymorphic parameter list of the form 965 * {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)} 966 * , statically represented using varargs. 967 * @return {@code true} if successful, otherwise {@code false} if the 968 * <em>witness value</em> was not the same as the {@code expectedValue} or if this 969 * operation spuriously failed. 970 * @throws UnsupportedOperationException if the access mode is unsupported 971 * for this VarHandle. 972 * @throws WrongMethodTypeException if the access mode type does not 973 * match the caller's symbolic type descriptor. 974 * @throws ClassCastException if the access mode type matches the caller's 975 * symbolic type descriptor, but a reference cast fails. 976 * @see #set(Object...) 977 * @see #get(Object...) 978 */ 979 public final native 980 @MethodHandle.PolymorphicSignature 981 @IntrinsicCandidate 982 boolean weakCompareAndSetPlain(Object... args); 983 984 /** 985 * Possibly atomically sets the value of a variable to the {@code newValue} 986 * with the memory semantics of {@link #setVolatile} if the variable's 987 * current value, referred to as the <em>witness value</em>, {@code ==} the 988 * {@code expectedValue}, as accessed with the memory semantics of 989 * {@link #getVolatile}. 990 * 991 * <p>This operation may fail spuriously (typically, due to memory 992 * contention) even if the <em>witness value</em> does match the expected value. 993 * 994 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)boolean}. 995 * 996 * <p>The symbolic type descriptor at the call site of {@code 997 * weakCompareAndSet} must match the access mode type that is the 998 * result of calling {@code accessModeType(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)} 999 * on this VarHandle. 1000 * 1001 * @param args the signature-polymorphic parameter list of the form 1002 * {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)} 1003 * , statically represented using varargs. 1004 * @return {@code true} if successful, otherwise {@code false} if the 1005 * <em>witness value</em> was not the same as the {@code expectedValue} or if this 1006 * operation spuriously failed. 1007 * @throws UnsupportedOperationException if the access mode is unsupported 1008 * for this VarHandle. 1009 * @throws WrongMethodTypeException if the access mode type does not 1010 * match the caller's symbolic type descriptor. 1011 * @throws ClassCastException if the access mode type matches the caller's 1012 * symbolic type descriptor, but a reference cast fails. 1013 * @see #setVolatile(Object...) 1014 * @see #getVolatile(Object...) 1015 */ 1016 public final native 1017 @MethodHandle.PolymorphicSignature 1018 @IntrinsicCandidate 1019 boolean weakCompareAndSet(Object... args); 1020 1021 /** 1022 * Possibly atomically sets the value of a variable to the {@code newValue} 1023 * with the semantics of {@link #set} if the variable's current value, 1024 * referred to as the <em>witness value</em>, {@code ==} the 1025 * {@code expectedValue}, as accessed with the memory semantics of 1026 * {@link #getAcquire}. 1027 * 1028 * <p>This operation may fail spuriously (typically, due to memory 1029 * contention) even if the <em>witness value</em> does match the expected value. 1030 * 1031 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)boolean}. 1032 * 1033 * <p>The symbolic type descriptor at the call site of {@code 1034 * weakCompareAndSetAcquire} 1035 * must match the access mode type that is the result of calling 1036 * {@code accessModeType(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)} 1037 * on this VarHandle. 1038 * 1039 * @param args the signature-polymorphic parameter list of the form 1040 * {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)} 1041 * , statically represented using varargs. 1042 * @return {@code true} if successful, otherwise {@code false} if the 1043 * <em>witness value</em> was not the same as the {@code expectedValue} or if this 1044 * operation spuriously failed. 1045 * @throws UnsupportedOperationException if the access mode is unsupported 1046 * for this VarHandle. 1047 * @throws WrongMethodTypeException if the access mode type does not 1048 * match the caller's symbolic type descriptor. 1049 * @throws ClassCastException if the access mode type matches the caller's 1050 * symbolic type descriptor, but a reference cast fails. 1051 * @see #set(Object...) 1052 * @see #getAcquire(Object...) 1053 */ 1054 public final native 1055 @MethodHandle.PolymorphicSignature 1056 @IntrinsicCandidate 1057 boolean weakCompareAndSetAcquire(Object... args); 1058 1059 /** 1060 * Possibly atomically sets the value of a variable to the {@code newValue} 1061 * with the semantics of {@link #setRelease} if the variable's current 1062 * value, referred to as the <em>witness value</em>, {@code ==} the 1063 * {@code expectedValue}, as accessed with the memory semantics of 1064 * {@link #get}. 1065 * 1066 * <p>This operation may fail spuriously (typically, due to memory 1067 * contention) even if the <em>witness value</em> does match the expected value. 1068 * 1069 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)boolean}. 1070 * 1071 * <p>The symbolic type descriptor at the call site of {@code 1072 * weakCompareAndSetRelease} 1073 * must match the access mode type that is the result of calling 1074 * {@code accessModeType(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)} 1075 * on this VarHandle. 1076 * 1077 * @param args the signature-polymorphic parameter list of the form 1078 * {@code (CT1 ct1, ..., CTn ctn, T expectedValue, T newValue)} 1079 * , statically represented using varargs. 1080 * @return {@code true} if successful, otherwise {@code false} if the 1081 * <em>witness value</em> was not the same as the {@code expectedValue} or if this 1082 * operation spuriously failed. 1083 * @throws UnsupportedOperationException if the access mode is unsupported 1084 * for this VarHandle. 1085 * @throws WrongMethodTypeException if the access mode type does not 1086 * match the caller's symbolic type descriptor. 1087 * @throws ClassCastException if the access mode type matches the caller's 1088 * symbolic type descriptor, but a reference cast fails. 1089 * @see #setRelease(Object...) 1090 * @see #get(Object...) 1091 */ 1092 public final native 1093 @MethodHandle.PolymorphicSignature 1094 @IntrinsicCandidate 1095 boolean weakCompareAndSetRelease(Object... args); 1096 1097 /** 1098 * Atomically sets the value of a variable to the {@code newValue} with the 1099 * memory semantics of {@link #setVolatile} and returns the variable's 1100 * previous value, as accessed with the memory semantics of 1101 * {@link #getVolatile}. 1102 * 1103 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T newValue)T}. 1104 * 1105 * <p>The symbolic type descriptor at the call site of {@code getAndSet} 1106 * must match the access mode type that is the result of calling 1107 * {@code accessModeType(VarHandle.AccessMode.GET_AND_SET)} on this 1108 * VarHandle. 1109 * 1110 * @param args the signature-polymorphic parameter list of the form 1111 * {@code (CT1 ct1, ..., CTn ctn, T newValue)} 1112 * , statically represented using varargs. 1113 * @return the signature-polymorphic result that is the previous value of 1114 * the variable 1115 * , statically represented using {@code Object}. 1116 * @throws UnsupportedOperationException if the access mode is unsupported 1117 * for this VarHandle. 1118 * @throws WrongMethodTypeException if the access mode type does not 1119 * match the caller's symbolic type descriptor. 1120 * @throws ClassCastException if the access mode type matches the caller's 1121 * symbolic type descriptor, but a reference cast fails. 1122 * @see #setVolatile(Object...) 1123 * @see #getVolatile(Object...) 1124 */ 1125 public final native 1126 @MethodHandle.PolymorphicSignature 1127 @IntrinsicCandidate 1128 Object getAndSet(Object... args); 1129 1130 /** 1131 * Atomically sets the value of a variable to the {@code newValue} with the 1132 * memory semantics of {@link #set} and returns the variable's 1133 * previous value, as accessed with the memory semantics of 1134 * {@link #getAcquire}. 1135 * 1136 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T newValue)T}. 1137 * 1138 * <p>The symbolic type descriptor at the call site of {@code getAndSetAcquire} 1139 * must match the access mode type that is the result of calling 1140 * {@code accessModeType(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)} on this 1141 * VarHandle. 1142 * 1143 * @param args the signature-polymorphic parameter list of the form 1144 * {@code (CT1 ct1, ..., CTn ctn, T newValue)} 1145 * , statically represented using varargs. 1146 * @return the signature-polymorphic result that is the previous value of 1147 * the variable 1148 * , statically represented using {@code Object}. 1149 * @throws UnsupportedOperationException if the access mode is unsupported 1150 * for this VarHandle. 1151 * @throws WrongMethodTypeException if the access mode type does not 1152 * match the caller's symbolic type descriptor. 1153 * @throws ClassCastException if the access mode type matches the caller's 1154 * symbolic type descriptor, but a reference cast fails. 1155 * @see #setVolatile(Object...) 1156 * @see #getVolatile(Object...) 1157 */ 1158 public final native 1159 @MethodHandle.PolymorphicSignature 1160 @IntrinsicCandidate 1161 Object getAndSetAcquire(Object... args); 1162 1163 /** 1164 * Atomically sets the value of a variable to the {@code newValue} with the 1165 * memory semantics of {@link #setRelease} and returns the variable's 1166 * previous value, as accessed with the memory semantics of 1167 * {@link #get}. 1168 * 1169 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T newValue)T}. 1170 * 1171 * <p>The symbolic type descriptor at the call site of {@code getAndSetRelease} 1172 * must match the access mode type that is the result of calling 1173 * {@code accessModeType(VarHandle.AccessMode.GET_AND_SET_RELEASE)} on this 1174 * VarHandle. 1175 * 1176 * @param args the signature-polymorphic parameter list of the form 1177 * {@code (CT1 ct1, ..., CTn ctn, T newValue)} 1178 * , statically represented using varargs. 1179 * @return the signature-polymorphic result that is the previous value of 1180 * the variable 1181 * , statically represented using {@code Object}. 1182 * @throws UnsupportedOperationException if the access mode is unsupported 1183 * for this VarHandle. 1184 * @throws WrongMethodTypeException if the access mode type does not 1185 * match the caller's symbolic type descriptor. 1186 * @throws ClassCastException if the access mode type matches the caller's 1187 * symbolic type descriptor, but a reference cast fails. 1188 * @see #setVolatile(Object...) 1189 * @see #getVolatile(Object...) 1190 */ 1191 public final native 1192 @MethodHandle.PolymorphicSignature 1193 @IntrinsicCandidate 1194 Object getAndSetRelease(Object... args); 1195 1196 // Primitive adders 1197 // Throw UnsupportedOperationException for refs 1198 1199 /** 1200 * Atomically adds the {@code value} to the current value of a variable with 1201 * the memory semantics of {@link #setVolatile}, and returns the variable's 1202 * previous value, as accessed with the memory semantics of 1203 * {@link #getVolatile}. 1204 * 1205 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T value)T}. 1206 * 1207 * <p>The symbolic type descriptor at the call site of {@code getAndAdd} 1208 * must match the access mode type that is the result of calling 1209 * {@code accessModeType(VarHandle.AccessMode.GET_AND_ADD)} on this 1210 * VarHandle. 1211 * 1212 * @param args the signature-polymorphic parameter list of the form 1213 * {@code (CT1 ct1, ..., CTn ctn, T value)} 1214 * , statically represented using varargs. 1215 * @return the signature-polymorphic result that is the previous value of 1216 * the variable 1217 * , statically represented using {@code Object}. 1218 * @throws UnsupportedOperationException if the access mode is unsupported 1219 * for this VarHandle. 1220 * @throws WrongMethodTypeException if the access mode type does not 1221 * match the caller's symbolic type descriptor. 1222 * @throws ClassCastException if the access mode type matches the caller's 1223 * symbolic type descriptor, but a reference cast fails. 1224 * @see #setVolatile(Object...) 1225 * @see #getVolatile(Object...) 1226 */ 1227 public final native 1228 @MethodHandle.PolymorphicSignature 1229 @IntrinsicCandidate 1230 Object getAndAdd(Object... args); 1231 1232 /** 1233 * Atomically adds the {@code value} to the current value of a variable with 1234 * the memory semantics of {@link #set}, and returns the variable's 1235 * previous value, as accessed with the memory semantics of 1236 * {@link #getAcquire}. 1237 * 1238 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T value)T}. 1239 * 1240 * <p>The symbolic type descriptor at the call site of {@code getAndAddAcquire} 1241 * must match the access mode type that is the result of calling 1242 * {@code accessModeType(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)} on this 1243 * VarHandle. 1244 * 1245 * @param args the signature-polymorphic parameter list of the form 1246 * {@code (CT1 ct1, ..., CTn ctn, T value)} 1247 * , statically represented using varargs. 1248 * @return the signature-polymorphic result that is the previous value of 1249 * the variable 1250 * , statically represented using {@code Object}. 1251 * @throws UnsupportedOperationException if the access mode is unsupported 1252 * for this VarHandle. 1253 * @throws WrongMethodTypeException if the access mode type does not 1254 * match the caller's symbolic type descriptor. 1255 * @throws ClassCastException if the access mode type matches the caller's 1256 * symbolic type descriptor, but a reference cast fails. 1257 * @see #setVolatile(Object...) 1258 * @see #getVolatile(Object...) 1259 */ 1260 public final native 1261 @MethodHandle.PolymorphicSignature 1262 @IntrinsicCandidate 1263 Object getAndAddAcquire(Object... args); 1264 1265 /** 1266 * Atomically adds the {@code value} to the current value of a variable with 1267 * the memory semantics of {@link #setRelease}, and returns the variable's 1268 * previous value, as accessed with the memory semantics of 1269 * {@link #get}. 1270 * 1271 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T value)T}. 1272 * 1273 * <p>The symbolic type descriptor at the call site of {@code getAndAddRelease} 1274 * must match the access mode type that is the result of calling 1275 * {@code accessModeType(VarHandle.AccessMode.GET_AND_ADD_RELEASE)} on this 1276 * VarHandle. 1277 * 1278 * @param args the signature-polymorphic parameter list of the form 1279 * {@code (CT1 ct1, ..., CTn ctn, T value)} 1280 * , statically represented using varargs. 1281 * @return the signature-polymorphic result that is the previous value of 1282 * the variable 1283 * , statically represented using {@code Object}. 1284 * @throws UnsupportedOperationException if the access mode is unsupported 1285 * for this VarHandle. 1286 * @throws WrongMethodTypeException if the access mode type does not 1287 * match the caller's symbolic type descriptor. 1288 * @throws ClassCastException if the access mode type matches the caller's 1289 * symbolic type descriptor, but a reference cast fails. 1290 * @see #setVolatile(Object...) 1291 * @see #getVolatile(Object...) 1292 */ 1293 public final native 1294 @MethodHandle.PolymorphicSignature 1295 @IntrinsicCandidate 1296 Object getAndAddRelease(Object... args); 1297 1298 1299 // Bitwise operations 1300 // Throw UnsupportedOperationException for refs 1301 1302 /** 1303 * Atomically sets the value of a variable to the result of 1304 * bitwise OR between the variable's current value and the {@code mask} 1305 * with the memory semantics of {@link #setVolatile} and returns the 1306 * variable's previous value, as accessed with the memory semantics of 1307 * {@link #getVolatile}. 1308 * 1309 * <p>If the variable type is the non-integral {@code boolean} type then a 1310 * logical OR is performed instead of a bitwise OR. 1311 * 1312 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T mask)T}. 1313 * 1314 * <p>The symbolic type descriptor at the call site of {@code getAndBitwiseOr} 1315 * must match the access mode type that is the result of calling 1316 * {@code accessModeType(VarHandle.AccessMode.GET_AND_BITWISE_OR)} on this 1317 * VarHandle. 1318 * 1319 * @param args the signature-polymorphic parameter list of the form 1320 * {@code (CT1 ct1, ..., CTn ctn, T mask)} 1321 * , statically represented using varargs. 1322 * @return the signature-polymorphic result that is the previous value of 1323 * the variable 1324 * , statically represented using {@code Object}. 1325 * @throws UnsupportedOperationException if the access mode is unsupported 1326 * for this VarHandle. 1327 * @throws WrongMethodTypeException if the access mode type does not 1328 * match the caller's symbolic type descriptor. 1329 * @throws ClassCastException if the access mode type matches the caller's 1330 * symbolic type descriptor, but a reference cast fails. 1331 * @see #setVolatile(Object...) 1332 * @see #getVolatile(Object...) 1333 */ 1334 public final native 1335 @MethodHandle.PolymorphicSignature 1336 @IntrinsicCandidate 1337 Object getAndBitwiseOr(Object... args); 1338 1339 /** 1340 * Atomically sets the value of a variable to the result of 1341 * bitwise OR between the variable's current value and the {@code mask} 1342 * with the memory semantics of {@link #set} and returns the 1343 * variable's previous value, as accessed with the memory semantics of 1344 * {@link #getAcquire}. 1345 * 1346 * <p>If the variable type is the non-integral {@code boolean} type then a 1347 * logical OR is performed instead of a bitwise OR. 1348 * 1349 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T mask)T}. 1350 * 1351 * <p>The symbolic type descriptor at the call site of {@code getAndBitwiseOrAcquire} 1352 * must match the access mode type that is the result of calling 1353 * {@code accessModeType(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)} on this 1354 * VarHandle. 1355 * 1356 * @param args the signature-polymorphic parameter list of the form 1357 * {@code (CT1 ct1, ..., CTn ctn, T mask)} 1358 * , statically represented using varargs. 1359 * @return the signature-polymorphic result that is the previous value of 1360 * the variable 1361 * , statically represented using {@code Object}. 1362 * @throws UnsupportedOperationException if the access mode is unsupported 1363 * for this VarHandle. 1364 * @throws WrongMethodTypeException if the access mode type does not 1365 * match the caller's symbolic type descriptor. 1366 * @throws ClassCastException if the access mode type matches the caller's 1367 * symbolic type descriptor, but a reference cast fails. 1368 * @see #set(Object...) 1369 * @see #getAcquire(Object...) 1370 */ 1371 public final native 1372 @MethodHandle.PolymorphicSignature 1373 @IntrinsicCandidate 1374 Object getAndBitwiseOrAcquire(Object... args); 1375 1376 /** 1377 * Atomically sets the value of a variable to the result of 1378 * bitwise OR between the variable's current value and the {@code mask} 1379 * with the memory semantics of {@link #setRelease} and returns the 1380 * variable's previous value, as accessed with the memory semantics of 1381 * {@link #get}. 1382 * 1383 * <p>If the variable type is the non-integral {@code boolean} type then a 1384 * logical OR is performed instead of a bitwise OR. 1385 * 1386 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T mask)T}. 1387 * 1388 * <p>The symbolic type descriptor at the call site of {@code getAndBitwiseOrRelease} 1389 * must match the access mode type that is the result of calling 1390 * {@code accessModeType(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)} on this 1391 * VarHandle. 1392 * 1393 * @param args the signature-polymorphic parameter list of the form 1394 * {@code (CT1 ct1, ..., CTn ctn, T mask)} 1395 * , statically represented using varargs. 1396 * @return the signature-polymorphic result that is the previous value of 1397 * the variable 1398 * , statically represented using {@code Object}. 1399 * @throws UnsupportedOperationException if the access mode is unsupported 1400 * for this VarHandle. 1401 * @throws WrongMethodTypeException if the access mode type does not 1402 * match the caller's symbolic type descriptor. 1403 * @throws ClassCastException if the access mode type matches the caller's 1404 * symbolic type descriptor, but a reference cast fails. 1405 * @see #setRelease(Object...) 1406 * @see #get(Object...) 1407 */ 1408 public final native 1409 @MethodHandle.PolymorphicSignature 1410 @IntrinsicCandidate 1411 Object getAndBitwiseOrRelease(Object... args); 1412 1413 /** 1414 * Atomically sets the value of a variable to the result of 1415 * bitwise AND between the variable's current value and the {@code mask} 1416 * with the memory semantics of {@link #setVolatile} and returns the 1417 * variable's previous value, as accessed with the memory semantics of 1418 * {@link #getVolatile}. 1419 * 1420 * <p>If the variable type is the non-integral {@code boolean} type then a 1421 * logical AND is performed instead of a bitwise AND. 1422 * 1423 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T mask)T}. 1424 * 1425 * <p>The symbolic type descriptor at the call site of {@code getAndBitwiseAnd} 1426 * must match the access mode type that is the result of calling 1427 * {@code accessModeType(VarHandle.AccessMode.GET_AND_BITWISE_AND)} on this 1428 * VarHandle. 1429 * 1430 * @param args the signature-polymorphic parameter list of the form 1431 * {@code (CT1 ct1, ..., CTn ctn, T mask)} 1432 * , statically represented using varargs. 1433 * @return the signature-polymorphic result that is the previous value of 1434 * the variable 1435 * , statically represented using {@code Object}. 1436 * @throws UnsupportedOperationException if the access mode is unsupported 1437 * for this VarHandle. 1438 * @throws WrongMethodTypeException if the access mode type does not 1439 * match the caller's symbolic type descriptor. 1440 * @throws ClassCastException if the access mode type matches the caller's 1441 * symbolic type descriptor, but a reference cast fails. 1442 * @see #setVolatile(Object...) 1443 * @see #getVolatile(Object...) 1444 */ 1445 public final native 1446 @MethodHandle.PolymorphicSignature 1447 @IntrinsicCandidate 1448 Object getAndBitwiseAnd(Object... args); 1449 1450 /** 1451 * Atomically sets the value of a variable to the result of 1452 * bitwise AND between the variable's current value and the {@code mask} 1453 * with the memory semantics of {@link #set} and returns the 1454 * variable's previous value, as accessed with the memory semantics of 1455 * {@link #getAcquire}. 1456 * 1457 * <p>If the variable type is the non-integral {@code boolean} type then a 1458 * logical AND is performed instead of a bitwise AND. 1459 * 1460 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T mask)T}. 1461 * 1462 * <p>The symbolic type descriptor at the call site of {@code getAndBitwiseAndAcquire} 1463 * must match the access mode type that is the result of calling 1464 * {@code accessModeType(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)} on this 1465 * VarHandle. 1466 * 1467 * @param args the signature-polymorphic parameter list of the form 1468 * {@code (CT1 ct1, ..., CTn ctn, T mask)} 1469 * , statically represented using varargs. 1470 * @return the signature-polymorphic result that is the previous value of 1471 * the variable 1472 * , statically represented using {@code Object}. 1473 * @throws UnsupportedOperationException if the access mode is unsupported 1474 * for this VarHandle. 1475 * @throws WrongMethodTypeException if the access mode type does not 1476 * match the caller's symbolic type descriptor. 1477 * @throws ClassCastException if the access mode type matches the caller's 1478 * symbolic type descriptor, but a reference cast fails. 1479 * @see #set(Object...) 1480 * @see #getAcquire(Object...) 1481 */ 1482 public final native 1483 @MethodHandle.PolymorphicSignature 1484 @IntrinsicCandidate 1485 Object getAndBitwiseAndAcquire(Object... args); 1486 1487 /** 1488 * Atomically sets the value of a variable to the result of 1489 * bitwise AND between the variable's current value and the {@code mask} 1490 * with the memory semantics of {@link #setRelease} and returns the 1491 * variable's previous value, as accessed with the memory semantics of 1492 * {@link #get}. 1493 * 1494 * <p>If the variable type is the non-integral {@code boolean} type then a 1495 * logical AND is performed instead of a bitwise AND. 1496 * 1497 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T mask)T}. 1498 * 1499 * <p>The symbolic type descriptor at the call site of {@code getAndBitwiseAndRelease} 1500 * must match the access mode type that is the result of calling 1501 * {@code accessModeType(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)} on this 1502 * VarHandle. 1503 * 1504 * @param args the signature-polymorphic parameter list of the form 1505 * {@code (CT1 ct1, ..., CTn ctn, T mask)} 1506 * , statically represented using varargs. 1507 * @return the signature-polymorphic result that is the previous value of 1508 * the variable 1509 * , statically represented using {@code Object}. 1510 * @throws UnsupportedOperationException if the access mode is unsupported 1511 * for this VarHandle. 1512 * @throws WrongMethodTypeException if the access mode type does not 1513 * match the caller's symbolic type descriptor. 1514 * @throws ClassCastException if the access mode type matches the caller's 1515 * symbolic type descriptor, but a reference cast fails. 1516 * @see #setRelease(Object...) 1517 * @see #get(Object...) 1518 */ 1519 public final native 1520 @MethodHandle.PolymorphicSignature 1521 @IntrinsicCandidate 1522 Object getAndBitwiseAndRelease(Object... args); 1523 1524 /** 1525 * Atomically sets the value of a variable to the result of 1526 * bitwise XOR between the variable's current value and the {@code mask} 1527 * with the memory semantics of {@link #setVolatile} and returns the 1528 * variable's previous value, as accessed with the memory semantics of 1529 * {@link #getVolatile}. 1530 * 1531 * <p>If the variable type is the non-integral {@code boolean} type then a 1532 * logical XOR is performed instead of a bitwise XOR. 1533 * 1534 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T mask)T}. 1535 * 1536 * <p>The symbolic type descriptor at the call site of {@code getAndBitwiseXor} 1537 * must match the access mode type that is the result of calling 1538 * {@code accessModeType(VarHandle.AccessMode.GET_AND_BITWISE_XOR)} on this 1539 * VarHandle. 1540 * 1541 * @param args the signature-polymorphic parameter list of the form 1542 * {@code (CT1 ct1, ..., CTn ctn, T mask)} 1543 * , statically represented using varargs. 1544 * @return the signature-polymorphic result that is the previous value of 1545 * the variable 1546 * , statically represented using {@code Object}. 1547 * @throws UnsupportedOperationException if the access mode is unsupported 1548 * for this VarHandle. 1549 * @throws WrongMethodTypeException if the access mode type does not 1550 * match the caller's symbolic type descriptor. 1551 * @throws ClassCastException if the access mode type matches the caller's 1552 * symbolic type descriptor, but a reference cast fails. 1553 * @see #setVolatile(Object...) 1554 * @see #getVolatile(Object...) 1555 */ 1556 public final native 1557 @MethodHandle.PolymorphicSignature 1558 @IntrinsicCandidate 1559 Object getAndBitwiseXor(Object... args); 1560 1561 /** 1562 * Atomically sets the value of a variable to the result of 1563 * bitwise XOR between the variable's current value and the {@code mask} 1564 * with the memory semantics of {@link #set} and returns the 1565 * variable's previous value, as accessed with the memory semantics of 1566 * {@link #getAcquire}. 1567 * 1568 * <p>If the variable type is the non-integral {@code boolean} type then a 1569 * logical XOR is performed instead of a bitwise XOR. 1570 * 1571 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T mask)T}. 1572 * 1573 * <p>The symbolic type descriptor at the call site of {@code getAndBitwiseXorAcquire} 1574 * must match the access mode type that is the result of calling 1575 * {@code accessModeType(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)} on this 1576 * VarHandle. 1577 * 1578 * @param args the signature-polymorphic parameter list of the form 1579 * {@code (CT1 ct1, ..., CTn ctn, T mask)} 1580 * , statically represented using varargs. 1581 * @return the signature-polymorphic result that is the previous value of 1582 * the variable 1583 * , statically represented using {@code Object}. 1584 * @throws UnsupportedOperationException if the access mode is unsupported 1585 * for this VarHandle. 1586 * @throws WrongMethodTypeException if the access mode type does not 1587 * match the caller's symbolic type descriptor. 1588 * @throws ClassCastException if the access mode type matches the caller's 1589 * symbolic type descriptor, but a reference cast fails. 1590 * @see #set(Object...) 1591 * @see #getAcquire(Object...) 1592 */ 1593 public final native 1594 @MethodHandle.PolymorphicSignature 1595 @IntrinsicCandidate 1596 Object getAndBitwiseXorAcquire(Object... args); 1597 1598 /** 1599 * Atomically sets the value of a variable to the result of 1600 * bitwise XOR between the variable's current value and the {@code mask} 1601 * with the memory semantics of {@link #setRelease} and returns the 1602 * variable's previous value, as accessed with the memory semantics of 1603 * {@link #get}. 1604 * 1605 * <p>If the variable type is the non-integral {@code boolean} type then a 1606 * logical XOR is performed instead of a bitwise XOR. 1607 * 1608 * <p>The method signature is of the form {@code (CT1 ct1, ..., CTn ctn, T mask)T}. 1609 * 1610 * <p>The symbolic type descriptor at the call site of {@code getAndBitwiseXorRelease} 1611 * must match the access mode type that is the result of calling 1612 * {@code accessModeType(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)} on this 1613 * VarHandle. 1614 * 1615 * @param args the signature-polymorphic parameter list of the form 1616 * {@code (CT1 ct1, ..., CTn ctn, T mask)} 1617 * , statically represented using varargs. 1618 * @return the signature-polymorphic result that is the previous value of 1619 * the variable 1620 * , statically represented using {@code Object}. 1621 * @throws UnsupportedOperationException if the access mode is unsupported 1622 * for this VarHandle. 1623 * @throws WrongMethodTypeException if the access mode type does not 1624 * match the caller's symbolic type descriptor. 1625 * @throws ClassCastException if the access mode type matches the caller's 1626 * symbolic type descriptor, but a reference cast fails. 1627 * @see #setRelease(Object...) 1628 * @see #get(Object...) 1629 */ 1630 public final native 1631 @MethodHandle.PolymorphicSignature 1632 @IntrinsicCandidate 1633 Object getAndBitwiseXorRelease(Object... args); 1634 1635 /** 1636 * Returns a VarHandle, with access to the same variable(s) as this VarHandle, but whose 1637 * invocation behavior of access mode methods is adjusted to 1638 * <a href="#invoke-exact-behavior"><em>invoke-exact behavior</em></a>. 1639 * <p> 1640 * If this VarHandle already has invoke-exact behavior this VarHandle is returned. 1641 * <p> 1642 * Invoking {@link #hasInvokeExactBehavior()} on the returned var handle 1643 * is guaranteed to return {@code true}. 1644 * 1645 * @apiNote 1646 * Invoke-exact behavior guarantees that upon invocation of an access mode method 1647 * the types and arity of the arguments must match the {@link #accessModeType(AccessMode) access mode type}, 1648 * otherwise a {@link WrongMethodTypeException} is thrown. 1649 * 1650 * @see #withInvokeBehavior() 1651 * @see #hasInvokeExactBehavior() 1652 * @return a VarHandle with invoke-exact behavior 1653 * @since 16 1654 */ 1655 public abstract VarHandle withInvokeExactBehavior(); 1656 1657 /** 1658 * Returns a VarHandle, with access to the same variable(s) as this VarHandle, but whose 1659 * invocation behavior of access mode methods is adjusted to 1660 * <a href="#invoke-behavior"><em>invoke behavior</em></a>. 1661 * <p> 1662 * If this VarHandle already has invoke behavior this VarHandle is returned. 1663 * <p> 1664 * Invoking {@link #hasInvokeExactBehavior()} on the returned var handle 1665 * is guaranteed to return {@code false}. 1666 * 1667 * @see #withInvokeExactBehavior() 1668 * @see #hasInvokeExactBehavior() 1669 * @return a VarHandle with invoke behavior 1670 * @since 16 1671 */ 1672 public abstract VarHandle withInvokeBehavior(); 1673 1674 enum AccessType { 1675 GET(Object.class), 1676 SET(void.class), 1677 COMPARE_AND_SET(boolean.class), 1678 COMPARE_AND_EXCHANGE(Object.class), 1679 GET_AND_UPDATE(Object.class); 1680 1681 static final int COUNT = GET_AND_UPDATE.ordinal() + 1; 1682 static { 1683 assert (COUNT == values().length); 1684 } 1685 final Class<?> returnType; 1686 final boolean isMonomorphicInReturnType; 1687 1688 AccessType(Class<?> returnType) { 1689 this.returnType = returnType; 1690 isMonomorphicInReturnType = returnType != Object.class; 1691 } 1692 1693 MethodType accessModeType(Class<?> receiver, Class<?> value, 1694 Class<?>... intermediate) { 1695 Class<?>[] ps; 1696 int i; 1697 switch (this) { 1698 case GET: 1699 ps = allocateParameters(0, receiver, intermediate); 1700 fillParameters(ps, receiver, intermediate); 1701 return MethodType.methodType(value, ps); 1702 case SET: 1703 ps = allocateParameters(1, receiver, intermediate); 1704 i = fillParameters(ps, receiver, intermediate); 1705 ps[i] = value; 1706 return MethodType.methodType(void.class, ps); 1707 case COMPARE_AND_SET: 1708 ps = allocateParameters(2, receiver, intermediate); 1709 i = fillParameters(ps, receiver, intermediate); 1710 ps[i++] = value; 1711 ps[i] = value; 1712 return MethodType.methodType(boolean.class, ps); 1713 case COMPARE_AND_EXCHANGE: 1714 ps = allocateParameters(2, receiver, intermediate); 1715 i = fillParameters(ps, receiver, intermediate); 1716 ps[i++] = value; 1717 ps[i] = value; 1718 return MethodType.methodType(value, ps); 1719 case GET_AND_UPDATE: 1720 ps = allocateParameters(1, receiver, intermediate); 1721 i = fillParameters(ps, receiver, intermediate); 1722 ps[i] = value; 1723 return MethodType.methodType(value, ps); 1724 default: 1725 throw new InternalError("Unknown AccessType"); 1726 } 1727 } 1728 1729 private static Class<?>[] allocateParameters(int values, 1730 Class<?> receiver, Class<?>... intermediate) { 1731 int size = ((receiver != null) ? 1 : 0) + intermediate.length + values; 1732 return new Class<?>[size]; 1733 } 1734 1735 private static int fillParameters(Class<?>[] ps, 1736 Class<?> receiver, Class<?>... intermediate) { 1737 int i = 0; 1738 if (receiver != null) 1739 ps[i++] = receiver; 1740 for (int j = 0; j < intermediate.length; j++) 1741 ps[i++] = intermediate[j]; 1742 return i; 1743 } 1744 } 1745 1746 /** 1747 * The set of access modes that specify how a variable, referenced by a 1748 * VarHandle, is accessed. 1749 */ 1750 public enum AccessMode { 1751 /** 1752 * The access mode whose access is specified by the corresponding 1753 * method 1754 * {@link VarHandle#get VarHandle.get} 1755 */ 1756 GET("get", AccessType.GET), 1757 /** 1758 * The access mode whose access is specified by the corresponding 1759 * method 1760 * {@link VarHandle#set VarHandle.set} 1761 */ 1762 SET("set", AccessType.SET), 1763 /** 1764 * The access mode whose access is specified by the corresponding 1765 * method 1766 * {@link VarHandle#getVolatile VarHandle.getVolatile} 1767 */ 1768 GET_VOLATILE("getVolatile", AccessType.GET), 1769 /** 1770 * The access mode whose access is specified by the corresponding 1771 * method 1772 * {@link VarHandle#setVolatile VarHandle.setVolatile} 1773 */ 1774 SET_VOLATILE("setVolatile", AccessType.SET), 1775 /** 1776 * The access mode whose access is specified by the corresponding 1777 * method 1778 * {@link VarHandle#getAcquire VarHandle.getAcquire} 1779 */ 1780 GET_ACQUIRE("getAcquire", AccessType.GET), 1781 /** 1782 * The access mode whose access is specified by the corresponding 1783 * method 1784 * {@link VarHandle#setRelease VarHandle.setRelease} 1785 */ 1786 SET_RELEASE("setRelease", AccessType.SET), 1787 /** 1788 * The access mode whose access is specified by the corresponding 1789 * method 1790 * {@link VarHandle#getOpaque VarHandle.getOpaque} 1791 */ 1792 GET_OPAQUE("getOpaque", AccessType.GET), 1793 /** 1794 * The access mode whose access is specified by the corresponding 1795 * method 1796 * {@link VarHandle#setOpaque VarHandle.setOpaque} 1797 */ 1798 SET_OPAQUE("setOpaque", AccessType.SET), 1799 /** 1800 * The access mode whose access is specified by the corresponding 1801 * method 1802 * {@link VarHandle#compareAndSet VarHandle.compareAndSet} 1803 */ 1804 COMPARE_AND_SET("compareAndSet", AccessType.COMPARE_AND_SET), 1805 /** 1806 * The access mode whose access is specified by the corresponding 1807 * method 1808 * {@link VarHandle#compareAndExchange VarHandle.compareAndExchange} 1809 */ 1810 COMPARE_AND_EXCHANGE("compareAndExchange", AccessType.COMPARE_AND_EXCHANGE), 1811 /** 1812 * The access mode whose access is specified by the corresponding 1813 * method 1814 * {@link VarHandle#compareAndExchangeAcquire VarHandle.compareAndExchangeAcquire} 1815 */ 1816 COMPARE_AND_EXCHANGE_ACQUIRE("compareAndExchangeAcquire", AccessType.COMPARE_AND_EXCHANGE), 1817 /** 1818 * The access mode whose access is specified by the corresponding 1819 * method 1820 * {@link VarHandle#compareAndExchangeRelease VarHandle.compareAndExchangeRelease} 1821 */ 1822 COMPARE_AND_EXCHANGE_RELEASE("compareAndExchangeRelease", AccessType.COMPARE_AND_EXCHANGE), 1823 /** 1824 * The access mode whose access is specified by the corresponding 1825 * method 1826 * {@link VarHandle#weakCompareAndSetPlain VarHandle.weakCompareAndSetPlain} 1827 */ 1828 WEAK_COMPARE_AND_SET_PLAIN("weakCompareAndSetPlain", AccessType.COMPARE_AND_SET), 1829 /** 1830 * The access mode whose access is specified by the corresponding 1831 * method 1832 * {@link VarHandle#weakCompareAndSet VarHandle.weakCompareAndSet} 1833 */ 1834 WEAK_COMPARE_AND_SET("weakCompareAndSet", AccessType.COMPARE_AND_SET), 1835 /** 1836 * The access mode whose access is specified by the corresponding 1837 * method 1838 * {@link VarHandle#weakCompareAndSetAcquire VarHandle.weakCompareAndSetAcquire} 1839 */ 1840 WEAK_COMPARE_AND_SET_ACQUIRE("weakCompareAndSetAcquire", AccessType.COMPARE_AND_SET), 1841 /** 1842 * The access mode whose access is specified by the corresponding 1843 * method 1844 * {@link VarHandle#weakCompareAndSetRelease VarHandle.weakCompareAndSetRelease} 1845 */ 1846 WEAK_COMPARE_AND_SET_RELEASE("weakCompareAndSetRelease", AccessType.COMPARE_AND_SET), 1847 /** 1848 * The access mode whose access is specified by the corresponding 1849 * method 1850 * {@link VarHandle#getAndSet VarHandle.getAndSet} 1851 */ 1852 GET_AND_SET("getAndSet", AccessType.GET_AND_UPDATE), 1853 /** 1854 * The access mode whose access is specified by the corresponding 1855 * method 1856 * {@link VarHandle#getAndSetAcquire VarHandle.getAndSetAcquire} 1857 */ 1858 GET_AND_SET_ACQUIRE("getAndSetAcquire", AccessType.GET_AND_UPDATE), 1859 /** 1860 * The access mode whose access is specified by the corresponding 1861 * method 1862 * {@link VarHandle#getAndSetRelease VarHandle.getAndSetRelease} 1863 */ 1864 GET_AND_SET_RELEASE("getAndSetRelease", AccessType.GET_AND_UPDATE), 1865 /** 1866 * The access mode whose access is specified by the corresponding 1867 * method 1868 * {@link VarHandle#getAndAdd VarHandle.getAndAdd} 1869 */ 1870 GET_AND_ADD("getAndAdd", AccessType.GET_AND_UPDATE), 1871 /** 1872 * The access mode whose access is specified by the corresponding 1873 * method 1874 * {@link VarHandle#getAndAddAcquire VarHandle.getAndAddAcquire} 1875 */ 1876 GET_AND_ADD_ACQUIRE("getAndAddAcquire", AccessType.GET_AND_UPDATE), 1877 /** 1878 * The access mode whose access is specified by the corresponding 1879 * method 1880 * {@link VarHandle#getAndAddRelease VarHandle.getAndAddRelease} 1881 */ 1882 GET_AND_ADD_RELEASE("getAndAddRelease", AccessType.GET_AND_UPDATE), 1883 /** 1884 * The access mode whose access is specified by the corresponding 1885 * method 1886 * {@link VarHandle#getAndBitwiseOr VarHandle.getAndBitwiseOr} 1887 */ 1888 GET_AND_BITWISE_OR("getAndBitwiseOr", AccessType.GET_AND_UPDATE), 1889 /** 1890 * The access mode whose access is specified by the corresponding 1891 * method 1892 * {@link VarHandle#getAndBitwiseOrRelease VarHandle.getAndBitwiseOrRelease} 1893 */ 1894 GET_AND_BITWISE_OR_RELEASE("getAndBitwiseOrRelease", AccessType.GET_AND_UPDATE), 1895 /** 1896 * The access mode whose access is specified by the corresponding 1897 * method 1898 * {@link VarHandle#getAndBitwiseOrAcquire VarHandle.getAndBitwiseOrAcquire} 1899 */ 1900 GET_AND_BITWISE_OR_ACQUIRE("getAndBitwiseOrAcquire", AccessType.GET_AND_UPDATE), 1901 /** 1902 * The access mode whose access is specified by the corresponding 1903 * method 1904 * {@link VarHandle#getAndBitwiseAnd VarHandle.getAndBitwiseAnd} 1905 */ 1906 GET_AND_BITWISE_AND("getAndBitwiseAnd", AccessType.GET_AND_UPDATE), 1907 /** 1908 * The access mode whose access is specified by the corresponding 1909 * method 1910 * {@link VarHandle#getAndBitwiseAndRelease VarHandle.getAndBitwiseAndRelease} 1911 */ 1912 GET_AND_BITWISE_AND_RELEASE("getAndBitwiseAndRelease", AccessType.GET_AND_UPDATE), 1913 /** 1914 * The access mode whose access is specified by the corresponding 1915 * method 1916 * {@link VarHandle#getAndBitwiseAndAcquire VarHandle.getAndBitwiseAndAcquire} 1917 */ 1918 GET_AND_BITWISE_AND_ACQUIRE("getAndBitwiseAndAcquire", AccessType.GET_AND_UPDATE), 1919 /** 1920 * The access mode whose access is specified by the corresponding 1921 * method 1922 * {@link VarHandle#getAndBitwiseXor VarHandle.getAndBitwiseXor} 1923 */ 1924 GET_AND_BITWISE_XOR("getAndBitwiseXor", AccessType.GET_AND_UPDATE), 1925 /** 1926 * The access mode whose access is specified by the corresponding 1927 * method 1928 * {@link VarHandle#getAndBitwiseXorRelease VarHandle.getAndBitwiseXorRelease} 1929 */ 1930 GET_AND_BITWISE_XOR_RELEASE("getAndBitwiseXorRelease", AccessType.GET_AND_UPDATE), 1931 /** 1932 * The access mode whose access is specified by the corresponding 1933 * method 1934 * {@link VarHandle#getAndBitwiseXorAcquire VarHandle.getAndBitwiseXorAcquire} 1935 */ 1936 GET_AND_BITWISE_XOR_ACQUIRE("getAndBitwiseXorAcquire", AccessType.GET_AND_UPDATE), 1937 ; 1938 1939 static final int COUNT = GET_AND_BITWISE_XOR_ACQUIRE.ordinal() + 1; 1940 static { 1941 assert (COUNT == values().length); 1942 } 1943 final String methodName; 1944 final AccessType at; 1945 1946 AccessMode(final String methodName, AccessType at) { 1947 this.methodName = methodName; 1948 this.at = at; 1949 } 1950 1951 /** 1952 * Returns the {@code VarHandle} signature-polymorphic method name 1953 * associated with this {@code AccessMode} value. 1954 * 1955 * @return the signature-polymorphic method name 1956 * @see #valueFromMethodName 1957 */ 1958 public String methodName() { 1959 return methodName; 1960 } 1961 1962 /** 1963 * Returns the {@code AccessMode} value associated with the specified 1964 * {@code VarHandle} signature-polymorphic method name. 1965 * 1966 * @param methodName the signature-polymorphic method name 1967 * @return the {@code AccessMode} value 1968 * @throws IllegalArgumentException if there is no {@code AccessMode} 1969 * value associated with method name (indicating the method 1970 * name does not correspond to a {@code VarHandle} 1971 * signature-polymorphic method name). 1972 * @see #methodName() 1973 */ 1974 public static AccessMode valueFromMethodName(String methodName) { 1975 return switch (methodName) { 1976 case "get" -> GET; 1977 case "set" -> SET; 1978 case "getVolatile" -> GET_VOLATILE; 1979 case "setVolatile" -> SET_VOLATILE; 1980 case "getAcquire" -> GET_ACQUIRE; 1981 case "setRelease" -> SET_RELEASE; 1982 case "getOpaque" -> GET_OPAQUE; 1983 case "setOpaque" -> SET_OPAQUE; 1984 case "compareAndSet" -> COMPARE_AND_SET; 1985 case "compareAndExchange" -> COMPARE_AND_EXCHANGE; 1986 case "compareAndExchangeAcquire" -> COMPARE_AND_EXCHANGE_ACQUIRE; 1987 case "compareAndExchangeRelease" -> COMPARE_AND_EXCHANGE_RELEASE; 1988 case "weakCompareAndSet" -> WEAK_COMPARE_AND_SET; 1989 case "weakCompareAndSetPlain" -> WEAK_COMPARE_AND_SET_PLAIN; 1990 case "weakCompareAndSetAcquire" -> WEAK_COMPARE_AND_SET_ACQUIRE; 1991 case "weakCompareAndSetRelease" -> WEAK_COMPARE_AND_SET_RELEASE; 1992 case "getAndSet" -> GET_AND_SET; 1993 case "getAndSetAcquire" -> GET_AND_SET_ACQUIRE; 1994 case "getAndSetRelease" -> GET_AND_SET_RELEASE; 1995 case "getAndAdd" -> GET_AND_ADD; 1996 case "getAndAddAcquire" -> GET_AND_ADD_ACQUIRE; 1997 case "getAndAddRelease" -> GET_AND_ADD_RELEASE; 1998 case "getAndBitwiseOr" -> GET_AND_BITWISE_OR; 1999 case "getAndBitwiseOrRelease" -> GET_AND_BITWISE_OR_RELEASE; 2000 case "getAndBitwiseOrAcquire" -> GET_AND_BITWISE_OR_ACQUIRE; 2001 case "getAndBitwiseAnd" -> GET_AND_BITWISE_AND; 2002 case "getAndBitwiseAndRelease" -> GET_AND_BITWISE_AND_RELEASE; 2003 case "getAndBitwiseAndAcquire" -> GET_AND_BITWISE_AND_ACQUIRE; 2004 case "getAndBitwiseXor" -> GET_AND_BITWISE_XOR; 2005 case "getAndBitwiseXorRelease" -> GET_AND_BITWISE_XOR_RELEASE; 2006 case "getAndBitwiseXorAcquire" -> GET_AND_BITWISE_XOR_ACQUIRE; 2007 default -> throw new IllegalArgumentException("No AccessMode value for method name " + methodName); 2008 }; 2009 } 2010 2011 private static final @Stable AccessMode[] VALUES = values(); 2012 static AccessMode valueFromOrdinal(int mode) { 2013 return VALUES[mode]; 2014 } 2015 } 2016 2017 static final class AccessDescriptor { 2018 final MethodType symbolicMethodTypeExact; 2019 final MethodType symbolicMethodTypeErased; 2020 final MethodType symbolicMethodTypeInvoker; 2021 final Class<?> returnType; 2022 final int type; 2023 final int mode; 2024 2025 public AccessDescriptor(MethodType symbolicMethodType, int type, int mode) { 2026 this.symbolicMethodTypeExact = symbolicMethodType; 2027 this.symbolicMethodTypeErased = symbolicMethodType.erase(); 2028 this.symbolicMethodTypeInvoker = symbolicMethodType.insertParameterTypes(0, VarHandle.class); 2029 this.returnType = symbolicMethodType.returnType(); 2030 this.type = type; 2031 this.mode = mode; 2032 } 2033 } 2034 2035 /** 2036 * Returns a compact textual description of this {@linkplain VarHandle}, 2037 * including the type of variable described, and a description of its coordinates. 2038 * 2039 * @return A compact textual description of this {@linkplain VarHandle} 2040 */ 2041 @Override 2042 public final String toString() { 2043 return String.format("VarHandle[varType=%s, coord=%s]", 2044 varType().getName(), 2045 coordinateTypes()); 2046 } 2047 2048 /** 2049 * Returns the variable type of variables referenced by this VarHandle. 2050 * 2051 * @return the variable type of variables referenced by this VarHandle 2052 */ 2053 public Class<?> varType() { 2054 MethodType typeSet = accessModeType(AccessMode.SET); 2055 return typeSet.parameterType(typeSet.parameterCount() - 1); 2056 } 2057 2058 /** 2059 * Returns the coordinate types for this VarHandle. 2060 * 2061 * @return the coordinate types for this VarHandle. The returned 2062 * list is unmodifiable 2063 */ 2064 public List<Class<?>> coordinateTypes() { 2065 MethodType typeGet = accessModeType(AccessMode.GET); 2066 return typeGet.parameterList(); 2067 } 2068 2069 /** 2070 * Obtains the access mode type for this VarHandle and a given access mode. 2071 * 2072 * <p>The access mode type's parameter types will consist of a prefix that 2073 * is the coordinate types of this VarHandle followed by further 2074 * types as defined by the access mode method. 2075 * The access mode type's return type is defined by the return type of the 2076 * access mode method. 2077 * 2078 * @param accessMode the access mode, corresponding to the 2079 * signature-polymorphic method of the same name 2080 * @return the access mode type for the given access mode 2081 */ 2082 public final MethodType accessModeType(AccessMode accessMode) { 2083 return accessModeType(accessMode.at.ordinal()); 2084 } 2085 2086 /** 2087 * Validates that the given access descriptors method type matches up with 2088 * the access mode of this VarHandle, then returns if this is direct. 2089 * These operations were grouped together to slightly 2090 * improve efficiency during startup/warmup. 2091 * 2092 * A direct VarHandle's VarForm has implementation MemberNames that can 2093 * be linked directly. If a VarHandle is indirect, it must override 2094 * {@link #isAccessModeSupported} and {@link #getMethodHandleUncached} 2095 * which access MemberNames. 2096 * 2097 * @return true if this is a direct VarHandle, false if it's an indirect 2098 * VarHandle. 2099 * @throws WrongMethodTypeException if there's an access type mismatch 2100 * @see #asDirect() 2101 */ 2102 @ForceInline 2103 boolean checkAccessModeThenIsDirect(VarHandle.AccessDescriptor ad) { 2104 if (exact && accessModeType(ad.type) != ad.symbolicMethodTypeExact) { 2105 throwWrongMethodTypeException(ad); 2106 } 2107 // return true unless overridden in an IndirectVarHandle 2108 return true; 2109 } 2110 2111 @DontInline 2112 private final void throwWrongMethodTypeException(VarHandle.AccessDescriptor ad) { 2113 throw new WrongMethodTypeException("handle's method type " + accessModeType(ad.type) 2114 + " but found " + ad.symbolicMethodTypeExact); 2115 } 2116 2117 @ForceInline 2118 final MethodType accessModeType(int accessTypeOrdinal) { 2119 MethodType[] mtTable = methodTypeTable; 2120 if (mtTable == null) { 2121 mtTable = methodTypeTable = new MethodType[VarHandle.AccessType.COUNT]; 2122 } 2123 MethodType mt = mtTable[accessTypeOrdinal]; 2124 if (mt == null) { 2125 mt = mtTable[accessTypeOrdinal] = 2126 accessModeTypeUncached(accessTypeOrdinal); 2127 } 2128 return mt; 2129 } 2130 2131 final MethodType accessModeTypeUncached(int accessTypeOrdinal) { 2132 return accessModeTypeUncached(AccessType.values()[accessTypeOrdinal]); 2133 } 2134 2135 abstract MethodType accessModeTypeUncached(AccessType accessMode); 2136 2137 /** 2138 * Returns {@code true} if the given access mode is supported, otherwise 2139 * {@code false}. 2140 * 2141 * <p>The return of a {@code false} value for a given access mode indicates 2142 * that an {@code UnsupportedOperationException} is thrown on invocation 2143 * of the corresponding access mode method. 2144 * 2145 * @param accessMode the access mode, corresponding to the 2146 * signature-polymorphic method of the same name 2147 * @return {@code true} if the given access mode is supported, otherwise 2148 * {@code false}. 2149 */ 2150 public boolean isAccessModeSupported(AccessMode accessMode) { 2151 return vform.getMemberNameOrNull(accessMode.ordinal()) != null; 2152 } 2153 2154 /** 2155 * Obtains a method handle bound to this VarHandle and the given access 2156 * mode. 2157 * 2158 * @apiNote This method, for a VarHandle {@code vh} and access mode 2159 * {@code {access-mode}}, returns a method handle that is equivalent to 2160 * method handle {@code bmh} in the following code (though it may be more 2161 * efficient): 2162 * <pre>{@code 2163 * MethodHandle mh = MethodHandles.varHandleExactInvoker( 2164 * vh.accessModeType(VarHandle.AccessMode.{access-mode})); 2165 * 2166 * MethodHandle bmh = mh.bindTo(vh); 2167 * }</pre> 2168 * 2169 * @param accessMode the access mode, corresponding to the 2170 * signature-polymorphic method of the same name 2171 * @return a method handle bound to this VarHandle and the given access mode 2172 */ 2173 public MethodHandle toMethodHandle(AccessMode accessMode) { 2174 if (isAccessModeSupported(accessMode)) { 2175 MethodHandle mh = getMethodHandle(accessMode.ordinal()); 2176 return mh.bindTo(asDirect()); 2177 } 2178 else { 2179 // Ensure an UnsupportedOperationException is thrown 2180 return MethodHandles.varHandleInvoker(accessMode, accessModeType(accessMode)). 2181 bindTo(this); 2182 } 2183 } 2184 2185 /** 2186 * Return a nominal descriptor for this instance, if one can be 2187 * constructed, or an empty {@link Optional} if one cannot be. 2188 * 2189 * @return An {@link Optional} containing the resulting nominal descriptor, 2190 * or an empty {@link Optional} if one cannot be constructed. 2191 * @since 12 2192 */ 2193 @Override 2194 public Optional<VarHandleDesc> describeConstable() { 2195 // partial function for field and array only 2196 return Optional.empty(); 2197 } 2198 2199 @Stable 2200 MethodType[] methodTypeTable; 2201 2202 @Stable 2203 MethodHandle[] methodHandleTable; 2204 2205 @ForceInline 2206 final MethodHandle getMethodHandle(int mode) { 2207 MethodHandle[] mhTable = methodHandleTable; 2208 if (mhTable == null) { 2209 mhTable = methodHandleTable = new MethodHandle[AccessMode.COUNT]; 2210 } 2211 MethodHandle mh = mhTable[mode]; 2212 if (mh == null) { 2213 mh = mhTable[mode] = getMethodHandleUncached(mode); 2214 } 2215 return mh; 2216 } 2217 2218 /** 2219 * Computes a method handle that can be passed the {@linkplain #asDirect() direct} 2220 * var handle of this var handle with the given access mode. Pre/postprocessing 2221 * such as argument or return value filtering should be done by the returned 2222 * method handle. 2223 * 2224 * @throws UnsupportedOperationException if the access mode is not supported 2225 */ 2226 MethodHandle getMethodHandleUncached(int mode) { 2227 MethodType mt = accessModeType(AccessMode.valueFromOrdinal(mode)). 2228 insertParameterTypes(0, VarHandle.class); 2229 MemberName mn = vform.getMemberName(mode); 2230 DirectMethodHandle dmh = DirectMethodHandle.make(mn); 2231 // Such a method handle must not be publicly exposed directly 2232 // otherwise it can be cracked, it must be transformed or rebound 2233 // before exposure 2234 MethodHandle mh = dmh.copyWith(mt, dmh.form); 2235 assert mh.type().erase() == mn.getMethodType().erase(); 2236 return mh; 2237 } 2238 2239 2240 /*non-public*/ 2241 final void updateVarForm(VarForm newVForm) { 2242 if (vform == newVForm) return; 2243 UNSAFE.putReference(this, VFORM_OFFSET, newVForm); 2244 UNSAFE.fullFence(); 2245 } 2246 2247 private static final long VFORM_OFFSET; 2248 2249 static { 2250 VFORM_OFFSET = UNSAFE.objectFieldOffset(VarHandle.class, "vform"); 2251 2252 // The VarHandleGuards must be initialized to ensure correct 2253 // compilation of the guard methods 2254 UNSAFE.ensureClassInitialized(VarHandleGuards.class); 2255 } 2256 2257 2258 // Fence methods 2259 2260 /** 2261 * Ensures that loads and stores before the fence will not be reordered 2262 * with 2263 * loads and stores after the fence. 2264 * 2265 * @apiNote Ignoring the many semantic differences from C and C++, this 2266 * method has memory ordering effects compatible with 2267 * {@code atomic_thread_fence(memory_order_seq_cst)} 2268 */ 2269 @ForceInline 2270 public static void fullFence() { 2271 UNSAFE.fullFence(); 2272 } 2273 2274 /** 2275 * Ensures that loads before the fence will not be reordered with loads and 2276 * stores after the fence. 2277 * 2278 * @apiNote Ignoring the many semantic differences from C and C++, this 2279 * method has memory ordering effects compatible with 2280 * {@code atomic_thread_fence(memory_order_acquire)} 2281 */ 2282 @ForceInline 2283 public static void acquireFence() { 2284 UNSAFE.loadFence(); 2285 } 2286 2287 /** 2288 * Ensures that loads and stores before the fence will not be 2289 * reordered with stores after the fence. 2290 * 2291 * @apiNote Ignoring the many semantic differences from C and C++, this 2292 * method has memory ordering effects compatible with 2293 * {@code atomic_thread_fence(memory_order_release)} 2294 */ 2295 @ForceInline 2296 public static void releaseFence() { 2297 UNSAFE.storeFence(); 2298 } 2299 2300 /** 2301 * Ensures that loads before the fence will not be reordered with 2302 * loads after the fence. 2303 */ 2304 @ForceInline 2305 public static void loadLoadFence() { 2306 UNSAFE.loadLoadFence(); 2307 } 2308 2309 /** 2310 * Ensures that stores before the fence will not be reordered with 2311 * stores after the fence. 2312 */ 2313 @ForceInline 2314 public static void storeStoreFence() { 2315 UNSAFE.storeStoreFence(); 2316 } 2317 2318 /** 2319 * A <a href="{@docRoot}/java.base/java/lang/constant/package-summary.html#nominal">nominal descriptor</a> for a 2320 * {@link VarHandle} constant. 2321 * 2322 * @since 12 2323 */ 2324 public static final class VarHandleDesc extends DynamicConstantDesc<VarHandle> { 2325 2326 /** 2327 * Kinds of variable handle descs 2328 */ 2329 private enum Kind { 2330 FIELD(ConstantDescs.BSM_VARHANDLE_FIELD), 2331 STATIC_FIELD(ConstantDescs.BSM_VARHANDLE_STATIC_FIELD), 2332 ARRAY(ConstantDescs.BSM_VARHANDLE_ARRAY); 2333 2334 final DirectMethodHandleDesc bootstrapMethod; 2335 2336 Kind(DirectMethodHandleDesc bootstrapMethod) { 2337 this.bootstrapMethod = bootstrapMethod; 2338 } 2339 2340 ConstantDesc[] toBSMArgs(ClassDesc declaringClass, ClassDesc varType) { 2341 return switch (this) { 2342 case FIELD, STATIC_FIELD -> new ConstantDesc[]{declaringClass, varType}; 2343 case ARRAY -> new ConstantDesc[]{declaringClass}; 2344 default -> throw new InternalError("Cannot reach here"); 2345 }; 2346 } 2347 } 2348 2349 private final Kind kind; 2350 private final ClassDesc declaringClass; 2351 private final ClassDesc varType; 2352 2353 /** 2354 * Construct a {@linkplain VarHandleDesc} given a kind, name, and declaring 2355 * class. 2356 * 2357 * @param kind the kind of the var handle 2358 * @param name the unqualified name of the field, for field var handles; otherwise ignored 2359 * @param declaringClass a {@link ClassDesc} describing the declaring class, 2360 * for field var handles 2361 * @param varType a {@link ClassDesc} describing the type of the variable 2362 * @throws NullPointerException if any required argument is null 2363 * @jvms 4.2.2 Unqualified Names 2364 */ 2365 private VarHandleDesc(Kind kind, String name, ClassDesc declaringClass, ClassDesc varType) { 2366 super(kind.bootstrapMethod, name, 2367 ConstantDescs.CD_VarHandle, 2368 kind.toBSMArgs(declaringClass, varType)); 2369 this.kind = kind; 2370 this.declaringClass = declaringClass; 2371 this.varType = varType; 2372 } 2373 2374 /** 2375 * Returns a {@linkplain VarHandleDesc} corresponding to a {@link VarHandle} 2376 * for an instance field. 2377 * 2378 * @param declaringClass a {@link ClassDesc} describing the declaring class, 2379 * for field var handles 2380 * @param name the unqualified name of the field 2381 * @param fieldType a {@link ClassDesc} describing the type of the field 2382 * @return the {@linkplain VarHandleDesc} 2383 * @throws NullPointerException if any of the arguments are null 2384 * @jvms 4.2.2 Unqualified Names 2385 */ 2386 public static VarHandleDesc ofField(ClassDesc declaringClass, String name, ClassDesc fieldType) { 2387 Objects.requireNonNull(declaringClass); 2388 Objects.requireNonNull(name); 2389 Objects.requireNonNull(fieldType); 2390 return new VarHandleDesc(Kind.FIELD, name, declaringClass, fieldType); 2391 } 2392 2393 /** 2394 * Returns a {@linkplain VarHandleDesc} corresponding to a {@link VarHandle} 2395 * for a static field. 2396 * 2397 * @param declaringClass a {@link ClassDesc} describing the declaring class, 2398 * for field var handles 2399 * @param name the unqualified name of the field 2400 * @param fieldType a {@link ClassDesc} describing the type of the field 2401 * @return the {@linkplain VarHandleDesc} 2402 * @throws NullPointerException if any of the arguments are null 2403 * @jvms 4.2.2 Unqualified Names 2404 */ 2405 public static VarHandleDesc ofStaticField(ClassDesc declaringClass, String name, ClassDesc fieldType) { 2406 Objects.requireNonNull(declaringClass); 2407 Objects.requireNonNull(name); 2408 Objects.requireNonNull(fieldType); 2409 return new VarHandleDesc(Kind.STATIC_FIELD, name, declaringClass, fieldType); 2410 } 2411 2412 /** 2413 * Returns a {@linkplain VarHandleDesc} corresponding to a {@link VarHandle} 2414 * for an array type. 2415 * 2416 * @param arrayClass a {@link ClassDesc} describing the type of the array 2417 * @return the {@linkplain VarHandleDesc} 2418 * @throws NullPointerException if any of the arguments are null 2419 */ 2420 public static VarHandleDesc ofArray(ClassDesc arrayClass) { 2421 Objects.requireNonNull(arrayClass); 2422 if (!arrayClass.isArray()) 2423 throw new IllegalArgumentException("Array class argument not an array: " + arrayClass); 2424 return new VarHandleDesc(Kind.ARRAY, ConstantDescs.DEFAULT_NAME, arrayClass, arrayClass.componentType()); 2425 } 2426 2427 /** 2428 * Returns a {@link ClassDesc} describing the type of the variable described 2429 * by this descriptor. 2430 * 2431 * @return the variable type 2432 */ 2433 public ClassDesc varType() { 2434 return varType; 2435 } 2436 2437 @Override 2438 public VarHandle resolveConstantDesc(MethodHandles.Lookup lookup) 2439 throws ReflectiveOperationException { 2440 return switch (kind) { 2441 case FIELD -> lookup.findVarHandle(declaringClass.resolveConstantDesc(lookup), 2442 constantName(), 2443 varType.resolveConstantDesc(lookup)); 2444 case STATIC_FIELD -> lookup.findStaticVarHandle(declaringClass.resolveConstantDesc(lookup), 2445 constantName(), 2446 varType.resolveConstantDesc(lookup)); 2447 case ARRAY -> MethodHandles.arrayElementVarHandle(declaringClass.resolveConstantDesc(lookup)); 2448 default -> throw new InternalError("Cannot reach here"); 2449 }; 2450 } 2451 2452 /** 2453 * Returns a compact textual description of this constant description. 2454 * For a field {@linkplain VarHandle}, includes the owner, name, and type 2455 * of the field, and whether it is static; for an array {@linkplain VarHandle}, 2456 * the name of the component type. 2457 * 2458 * @return A compact textual description of this descriptor 2459 */ 2460 @Override 2461 public String toString() { 2462 return switch (kind) { 2463 case FIELD, STATIC_FIELD -> String.format("VarHandleDesc[%s%s.%s:%s]", 2464 (kind == Kind.STATIC_FIELD) ? "static " : "", 2465 declaringClass.displayName(), constantName(), varType.displayName()); 2466 case ARRAY -> String.format("VarHandleDesc[%s[]]", declaringClass.displayName()); 2467 default -> throw new InternalError("Cannot reach here"); 2468 }; 2469 } 2470 } 2471 2472 }