1 /*
2 * Copyright (c) 2000, 2025, 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
25
26 package jdk.internal.misc;
27
28 import jdk.internal.vm.annotation.AOTRuntimeSetup;
29 import jdk.internal.vm.annotation.AOTSafeClassInitializer;
30 import jdk.internal.vm.annotation.ForceInline;
31 import jdk.internal.vm.annotation.IntrinsicCandidate;
32 import sun.nio.Cleaner;
33 import sun.nio.ch.DirectBuffer;
34
35 import java.lang.reflect.Field;
36 import java.security.ProtectionDomain;
37
38 import static jdk.internal.misc.UnsafeConstants.*;
39
40 /**
41 * A collection of methods for performing low-level, unsafe operations.
42 * Although the class and all methods are public, use of this class is
43 * limited because only trusted code can obtain instances of it.
44 *
45 * <em>Note:</em> It is the responsibility of the caller to make sure
46 * arguments are checked before methods of this class are
47 * called. While some rudimentary checks are performed on the input,
48 * the checks are best effort and when performance is an overriding
49 * priority, as when methods of this class are optimized by the
50 * runtime compiler, some or all checks (if any) may be elided. Hence,
51 * the caller must not rely on the checks and corresponding
52 * exceptions!
53 *
54 * @author John R. Rose
55 * @see #getUnsafe
56 */
57 @AOTSafeClassInitializer
58 public final class Unsafe {
59
60 private static native void registerNatives();
61 static {
62 runtimeSetup();
63 }
64
65 /// BASE_OFFSET, INDEX_SCALE, and ADDRESS_SIZE fields are equivalent if the
66 /// AOT initialized heap is reused, so just register natives
67 @AOTRuntimeSetup
68 private static void runtimeSetup() {
69 registerNatives();
70 }
71
72 private Unsafe() {}
169 * The first two parameters are interpreted exactly as with
170 * {@link #getInt(Object, long)} to refer to a specific
171 * Java variable (field or array element). The given value
172 * is stored into that variable.
173 * <p>
174 * The variable must be of the same type as the method
175 * parameter {@code x}.
176 *
177 * @param o Java heap object in which the variable resides, if any, else
178 * null
179 * @param offset indication of where the variable resides in a Java heap
180 * object, if any, else a memory address locating the variable
181 * statically
182 * @param x the value to store into the indicated Java variable
183 * @throws RuntimeException No defined exceptions are thrown, not even
184 * {@link NullPointerException}
185 */
186 @IntrinsicCandidate
187 public native void putInt(Object o, long offset, int x);
188
189 /**
190 * Fetches a reference value from a given Java variable.
191 * @see #getInt(Object, long)
192 */
193 @IntrinsicCandidate
194 public native Object getReference(Object o, long offset);
195
196 /**
197 * Stores a reference value into a given Java variable.
198 * <p>
199 * Unless the reference {@code x} being stored is either null
200 * or matches the field type, the results are undefined.
201 * If the reference {@code o} is non-null, card marks or
202 * other store barriers for that object (if the VM requires them)
203 * are updated.
204 * @see #putInt(Object, long, int)
205 */
206 @IntrinsicCandidate
207 public native void putReference(Object o, long offset, Object x);
208
209 /** @see #getInt(Object, long) */
210 @IntrinsicCandidate
211 public native boolean getBoolean(Object o, long offset);
212
213 /** @see #putInt(Object, long, int) */
214 @IntrinsicCandidate
215 public native void putBoolean(Object o, long offset, boolean x);
216
217 /** @see #getInt(Object, long) */
218 @IntrinsicCandidate
219 public native byte getByte(Object o, long offset);
220
221 /** @see #putInt(Object, long, int) */
222 @IntrinsicCandidate
223 public native void putByte(Object o, long offset, byte x);
224
225 /** @see #getInt(Object, long) */
226 @IntrinsicCandidate
227 public native short getShort(Object o, long offset);
228
1178 }
1179
1180 /**
1181 * Ensures the given class has been initialized (see JVMS-5.5 for details).
1182 * This is often needed in conjunction with obtaining the static field base
1183 * of a class.
1184 *
1185 * The call returns when either class {@code c} is fully initialized or
1186 * class {@code c} is being initialized and the call is performed from
1187 * the initializing thread. In the latter case a subsequent call to
1188 * {@link #shouldBeInitialized} will return {@code true}.
1189 */
1190 public void ensureClassInitialized(Class<?> c) {
1191 if (c == null) {
1192 throw new NullPointerException();
1193 }
1194
1195 ensureClassInitialized0(c);
1196 }
1197
1198 /**
1199 * Reports the offset of the first element in the storage allocation of a
1200 * given array class. If {@link #arrayIndexScale} returns a non-zero value
1201 * for the same class, you may use that scale factor, together with this
1202 * base offset, to form new offsets to access elements of arrays of the
1203 * given class.
1204 * <p>
1205 * The return value is in the range of a {@code int}. The return type is
1206 * {@code long} to emphasize that long arithmetic should always be used
1207 * for offset calculations to avoid overflows.
1208 *
1209 * @see #getInt(Object, long)
1210 * @see #putInt(Object, long, int)
1211 */
1212 public long arrayBaseOffset(Class<?> arrayClass) {
1213 if (arrayClass == null) {
1214 throw new NullPointerException();
1215 }
1216
1217 return arrayBaseOffset0(arrayClass);
1218 }
1219
1220
1221 /** The value of {@code arrayBaseOffset(boolean[].class)} */
1222 public static final long ARRAY_BOOLEAN_BASE_OFFSET
1223 = theUnsafe.arrayBaseOffset(boolean[].class);
1224
1225 /** The value of {@code arrayBaseOffset(byte[].class)} */
1226 public static final long ARRAY_BYTE_BASE_OFFSET
1227 = theUnsafe.arrayBaseOffset(byte[].class);
1228
1229 /** The value of {@code arrayBaseOffset(short[].class)} */
1230 public static final long ARRAY_SHORT_BASE_OFFSET
1231 = theUnsafe.arrayBaseOffset(short[].class);
1232
1233 /** The value of {@code arrayBaseOffset(char[].class)} */
1234 public static final long ARRAY_CHAR_BASE_OFFSET
1235 = theUnsafe.arrayBaseOffset(char[].class);
1236
1237 /** The value of {@code arrayBaseOffset(int[].class)} */
1238 public static final long ARRAY_INT_BASE_OFFSET
1239 = theUnsafe.arrayBaseOffset(int[].class);
1246 public static final long ARRAY_FLOAT_BASE_OFFSET
1247 = theUnsafe.arrayBaseOffset(float[].class);
1248
1249 /** The value of {@code arrayBaseOffset(double[].class)} */
1250 public static final long ARRAY_DOUBLE_BASE_OFFSET
1251 = theUnsafe.arrayBaseOffset(double[].class);
1252
1253 /** The value of {@code arrayBaseOffset(Object[].class)} */
1254 public static final long ARRAY_OBJECT_BASE_OFFSET
1255 = theUnsafe.arrayBaseOffset(Object[].class);
1256
1257 /**
1258 * Reports the scale factor for addressing elements in the storage
1259 * allocation of a given array class. However, arrays of "narrow" types
1260 * will generally not work properly with accessors like {@link
1261 * #getByte(Object, long)}, so the scale factor for such classes is reported
1262 * as zero.
1263 * <p>
1264 * The computation of the actual memory offset should always use {@code
1265 * long} arithmetic to avoid overflows.
1266 *
1267 * @see #arrayBaseOffset
1268 * @see #getInt(Object, long)
1269 * @see #putInt(Object, long, int)
1270 */
1271 public int arrayIndexScale(Class<?> arrayClass) {
1272 if (arrayClass == null) {
1273 throw new NullPointerException();
1274 }
1275
1276 return arrayIndexScale0(arrayClass);
1277 }
1278
1279
1280 /** The value of {@code arrayIndexScale(boolean[].class)} */
1281 public static final int ARRAY_BOOLEAN_INDEX_SCALE
1282 = theUnsafe.arrayIndexScale(boolean[].class);
1283
1284 /** The value of {@code arrayIndexScale(byte[].class)} */
1285 public static final int ARRAY_BYTE_INDEX_SCALE
1286 = theUnsafe.arrayIndexScale(byte[].class);
1287
1288 /** The value of {@code arrayIndexScale(short[].class)} */
1289 public static final int ARRAY_SHORT_INDEX_SCALE
1290 = theUnsafe.arrayIndexScale(short[].class);
1291
1292 /** The value of {@code arrayIndexScale(char[].class)} */
1293 public static final int ARRAY_CHAR_INDEX_SCALE
1294 = theUnsafe.arrayIndexScale(char[].class);
1295
1296 /** The value of {@code arrayIndexScale(int[].class)} */
1297 public static final int ARRAY_INT_INDEX_SCALE
1298 = theUnsafe.arrayIndexScale(int[].class);
1362 public Class<?> defineClass(String name, byte[] b, int off, int len,
1363 ClassLoader loader,
1364 ProtectionDomain protectionDomain) {
1365 if (b == null) {
1366 throw new NullPointerException();
1367 }
1368 if (len < 0) {
1369 throw new ArrayIndexOutOfBoundsException();
1370 }
1371
1372 return defineClass0(name, b, off, len, loader, protectionDomain);
1373 }
1374
1375 public native Class<?> defineClass0(String name, byte[] b, int off, int len,
1376 ClassLoader loader,
1377 ProtectionDomain protectionDomain);
1378
1379 /**
1380 * Allocates an instance but does not run any constructor.
1381 * Initializes the class if it has not yet been.
1382 */
1383 @IntrinsicCandidate
1384 public native Object allocateInstance(Class<?> cls)
1385 throws InstantiationException;
1386
1387 /**
1388 * Allocates an array of a given type, but does not do zeroing.
1389 * <p>
1390 * This method should only be used in the very rare cases where a high-performance code
1391 * overwrites the destination array completely, and compilers cannot assist in zeroing elimination.
1392 * In an overwhelming majority of cases, a normal Java allocation should be used instead.
1393 * <p>
1394 * Users of this method are <b>required</b> to overwrite the initial (garbage) array contents
1395 * before allowing untrusted code, or code in other threads, to observe the reference
1396 * to the newly allocated array. In addition, the publication of the array reference must be
1397 * safe according to the Java Memory Model requirements.
1398 * <p>
1399 * The safest approach to deal with an uninitialized array is to keep the reference to it in local
1400 * variable at least until the initialization is complete, and then publish it <b>once</b>, either
1401 * by writing it to a <em>volatile</em> field, or storing it into a <em>final</em> field in constructor,
1437 return null;
1438 }
1439
1440 /** Throws the exception without telling the verifier. */
1441 public native void throwException(Throwable ee);
1442
1443 /**
1444 * Atomically updates Java variable to {@code x} if it is currently
1445 * holding {@code expected}.
1446 *
1447 * <p>This operation has memory semantics of a {@code volatile} read
1448 * and write. Corresponds to C11 atomic_compare_exchange_strong.
1449 *
1450 * @return {@code true} if successful
1451 */
1452 @IntrinsicCandidate
1453 public final native boolean compareAndSetReference(Object o, long offset,
1454 Object expected,
1455 Object x);
1456
1457 @IntrinsicCandidate
1458 public final native Object compareAndExchangeReference(Object o, long offset,
1459 Object expected,
1460 Object x);
1461
1462 @IntrinsicCandidate
1463 public final Object compareAndExchangeReferenceAcquire(Object o, long offset,
1464 Object expected,
1465 Object x) {
1466 return compareAndExchangeReference(o, offset, expected, x);
1467 }
1468
1469 @IntrinsicCandidate
1470 public final Object compareAndExchangeReferenceRelease(Object o, long offset,
1471 Object expected,
1472 Object x) {
1473 return compareAndExchangeReference(o, offset, expected, x);
1474 }
1475
1476 @IntrinsicCandidate
1477 public final boolean weakCompareAndSetReferencePlain(Object o, long offset,
1478 Object expected,
1479 Object x) {
1480 return compareAndSetReference(o, offset, expected, x);
1481 }
1482
1483 @IntrinsicCandidate
1484 public final boolean weakCompareAndSetReferenceAcquire(Object o, long offset,
1485 Object expected,
1486 Object x) {
1487 return compareAndSetReference(o, offset, expected, x);
1488 }
1489
1490 @IntrinsicCandidate
1491 public final boolean weakCompareAndSetReferenceRelease(Object o, long offset,
1492 Object expected,
1493 Object x) {
1494 return compareAndSetReference(o, offset, expected, x);
1495 }
1496
1497 @IntrinsicCandidate
1498 public final boolean weakCompareAndSetReference(Object o, long offset,
1499 Object expected,
1500 Object x) {
1501 return compareAndSetReference(o, offset, expected, x);
1502 }
1503
1504 /**
1505 * Atomically updates Java variable to {@code x} if it is currently
1506 * holding {@code expected}.
1507 *
1508 * <p>This operation has memory semantics of a {@code volatile} read
1509 * and write. Corresponds to C11 atomic_compare_exchange_strong.
1510 *
1511 * @return {@code true} if successful
1512 */
1513 @IntrinsicCandidate
1514 public final native boolean compareAndSetInt(Object o, long offset,
1515 int expected,
1516 int x);
1517
1518 @IntrinsicCandidate
1519 public final native int compareAndExchangeInt(Object o, long offset,
1520 int expected,
1521 int x);
1522
1523 @IntrinsicCandidate
2099 public final boolean weakCompareAndSetLongRelease(Object o, long offset,
2100 long expected,
2101 long x) {
2102 return compareAndSetLong(o, offset, expected, x);
2103 }
2104
2105 @IntrinsicCandidate
2106 public final boolean weakCompareAndSetLong(Object o, long offset,
2107 long expected,
2108 long x) {
2109 return compareAndSetLong(o, offset, expected, x);
2110 }
2111
2112 /**
2113 * Fetches a reference value from a given Java variable, with volatile
2114 * load semantics. Otherwise identical to {@link #getReference(Object, long)}
2115 */
2116 @IntrinsicCandidate
2117 public native Object getReferenceVolatile(Object o, long offset);
2118
2119 /**
2120 * Stores a reference value into a given Java variable, with
2121 * volatile store semantics. Otherwise identical to {@link #putReference(Object, long, Object)}
2122 */
2123 @IntrinsicCandidate
2124 public native void putReferenceVolatile(Object o, long offset, Object x);
2125
2126 /** Volatile version of {@link #getInt(Object, long)} */
2127 @IntrinsicCandidate
2128 public native int getIntVolatile(Object o, long offset);
2129
2130 /** Volatile version of {@link #putInt(Object, long, int)} */
2131 @IntrinsicCandidate
2132 public native void putIntVolatile(Object o, long offset, int x);
2133
2134 /** Volatile version of {@link #getBoolean(Object, long)} */
2135 @IntrinsicCandidate
2136 public native boolean getBooleanVolatile(Object o, long offset);
2137
2138 /** Volatile version of {@link #putBoolean(Object, long, boolean)} */
2139 @IntrinsicCandidate
2140 public native void putBooleanVolatile(Object o, long offset, boolean x);
2141
2142 /** Volatile version of {@link #getByte(Object, long)} */
2143 @IntrinsicCandidate
2144 public native byte getByteVolatile(Object o, long offset);
2145
2178 /** Volatile version of {@link #putFloat(Object, long, float)} */
2179 @IntrinsicCandidate
2180 public native void putFloatVolatile(Object o, long offset, float x);
2181
2182 /** Volatile version of {@link #getDouble(Object, long)} */
2183 @IntrinsicCandidate
2184 public native double getDoubleVolatile(Object o, long offset);
2185
2186 /** Volatile version of {@link #putDouble(Object, long, double)} */
2187 @IntrinsicCandidate
2188 public native void putDoubleVolatile(Object o, long offset, double x);
2189
2190
2191
2192 /** Acquire version of {@link #getReferenceVolatile(Object, long)} */
2193 @IntrinsicCandidate
2194 public final Object getReferenceAcquire(Object o, long offset) {
2195 return getReferenceVolatile(o, offset);
2196 }
2197
2198 /** Acquire version of {@link #getBooleanVolatile(Object, long)} */
2199 @IntrinsicCandidate
2200 public final boolean getBooleanAcquire(Object o, long offset) {
2201 return getBooleanVolatile(o, offset);
2202 }
2203
2204 /** Acquire version of {@link #getByteVolatile(Object, long)} */
2205 @IntrinsicCandidate
2206 public final byte getByteAcquire(Object o, long offset) {
2207 return getByteVolatile(o, offset);
2208 }
2209
2210 /** Acquire version of {@link #getShortVolatile(Object, long)} */
2211 @IntrinsicCandidate
2212 public final short getShortAcquire(Object o, long offset) {
2213 return getShortVolatile(o, offset);
2214 }
2215
2216 /** Acquire version of {@link #getCharVolatile(Object, long)} */
2217 @IntrinsicCandidate
2242 public final double getDoubleAcquire(Object o, long offset) {
2243 return getDoubleVolatile(o, offset);
2244 }
2245
2246 /*
2247 * Versions of {@link #putReferenceVolatile(Object, long, Object)}
2248 * that do not guarantee immediate visibility of the store to
2249 * other threads. This method is generally only useful if the
2250 * underlying field is a Java volatile (or if an array cell, one
2251 * that is otherwise only accessed using volatile accesses).
2252 *
2253 * Corresponds to C11 atomic_store_explicit(..., memory_order_release).
2254 */
2255
2256 /** Release version of {@link #putReferenceVolatile(Object, long, Object)} */
2257 @IntrinsicCandidate
2258 public final void putReferenceRelease(Object o, long offset, Object x) {
2259 putReferenceVolatile(o, offset, x);
2260 }
2261
2262 /** Release version of {@link #putBooleanVolatile(Object, long, boolean)} */
2263 @IntrinsicCandidate
2264 public final void putBooleanRelease(Object o, long offset, boolean x) {
2265 putBooleanVolatile(o, offset, x);
2266 }
2267
2268 /** Release version of {@link #putByteVolatile(Object, long, byte)} */
2269 @IntrinsicCandidate
2270 public final void putByteRelease(Object o, long offset, byte x) {
2271 putByteVolatile(o, offset, x);
2272 }
2273
2274 /** Release version of {@link #putShortVolatile(Object, long, short)} */
2275 @IntrinsicCandidate
2276 public final void putShortRelease(Object o, long offset, short x) {
2277 putShortVolatile(o, offset, x);
2278 }
2279
2280 /** Release version of {@link #putCharVolatile(Object, long, char)} */
2281 @IntrinsicCandidate
2298 /** Release version of {@link #putLongVolatile(Object, long, long)} */
2299 @IntrinsicCandidate
2300 public final void putLongRelease(Object o, long offset, long x) {
2301 putLongVolatile(o, offset, x);
2302 }
2303
2304 /** Release version of {@link #putDoubleVolatile(Object, long, double)} */
2305 @IntrinsicCandidate
2306 public final void putDoubleRelease(Object o, long offset, double x) {
2307 putDoubleVolatile(o, offset, x);
2308 }
2309
2310 // ------------------------------ Opaque --------------------------------------
2311
2312 /** Opaque version of {@link #getReferenceVolatile(Object, long)} */
2313 @IntrinsicCandidate
2314 public final Object getReferenceOpaque(Object o, long offset) {
2315 return getReferenceVolatile(o, offset);
2316 }
2317
2318 /** Opaque version of {@link #getBooleanVolatile(Object, long)} */
2319 @IntrinsicCandidate
2320 public final boolean getBooleanOpaque(Object o, long offset) {
2321 return getBooleanVolatile(o, offset);
2322 }
2323
2324 /** Opaque version of {@link #getByteVolatile(Object, long)} */
2325 @IntrinsicCandidate
2326 public final byte getByteOpaque(Object o, long offset) {
2327 return getByteVolatile(o, offset);
2328 }
2329
2330 /** Opaque version of {@link #getShortVolatile(Object, long)} */
2331 @IntrinsicCandidate
2332 public final short getShortOpaque(Object o, long offset) {
2333 return getShortVolatile(o, offset);
2334 }
2335
2336 /** Opaque version of {@link #getCharVolatile(Object, long)} */
2337 @IntrinsicCandidate
2352 }
2353
2354 /** Opaque version of {@link #getLongVolatile(Object, long)} */
2355 @IntrinsicCandidate
2356 public final long getLongOpaque(Object o, long offset) {
2357 return getLongVolatile(o, offset);
2358 }
2359
2360 /** Opaque version of {@link #getDoubleVolatile(Object, long)} */
2361 @IntrinsicCandidate
2362 public final double getDoubleOpaque(Object o, long offset) {
2363 return getDoubleVolatile(o, offset);
2364 }
2365
2366 /** Opaque version of {@link #putReferenceVolatile(Object, long, Object)} */
2367 @IntrinsicCandidate
2368 public final void putReferenceOpaque(Object o, long offset, Object x) {
2369 putReferenceVolatile(o, offset, x);
2370 }
2371
2372 /** Opaque version of {@link #putBooleanVolatile(Object, long, boolean)} */
2373 @IntrinsicCandidate
2374 public final void putBooleanOpaque(Object o, long offset, boolean x) {
2375 putBooleanVolatile(o, offset, x);
2376 }
2377
2378 /** Opaque version of {@link #putByteVolatile(Object, long, byte)} */
2379 @IntrinsicCandidate
2380 public final void putByteOpaque(Object o, long offset, byte x) {
2381 putByteVolatile(o, offset, x);
2382 }
2383
2384 /** Opaque version of {@link #putShortVolatile(Object, long, short)} */
2385 @IntrinsicCandidate
2386 public final void putShortOpaque(Object o, long offset, short x) {
2387 putShortVolatile(o, offset, x);
2388 }
2389
2390 /** Opaque version of {@link #putCharVolatile(Object, long, char)} */
2391 @IntrinsicCandidate
2400 }
2401
2402 /** Opaque version of {@link #putFloatVolatile(Object, long, float)} */
2403 @IntrinsicCandidate
2404 public final void putFloatOpaque(Object o, long offset, float x) {
2405 putFloatVolatile(o, offset, x);
2406 }
2407
2408 /** Opaque version of {@link #putLongVolatile(Object, long, long)} */
2409 @IntrinsicCandidate
2410 public final void putLongOpaque(Object o, long offset, long x) {
2411 putLongVolatile(o, offset, x);
2412 }
2413
2414 /** Opaque version of {@link #putDoubleVolatile(Object, long, double)} */
2415 @IntrinsicCandidate
2416 public final void putDoubleOpaque(Object o, long offset, double x) {
2417 putDoubleVolatile(o, offset, x);
2418 }
2419
2420 /**
2421 * Unblocks the given thread blocked on {@code park}, or, if it is
2422 * not blocked, causes the subsequent call to {@code park} not to
2423 * block. Note: this operation is "unsafe" solely because the
2424 * caller must somehow ensure that the thread has not been
2425 * destroyed. Nothing special is usually required to ensure this
2426 * when called from Java (in which there will ordinarily be a live
2427 * reference to the thread) but this is not nearly-automatically
2428 * so when calling from native code.
2429 *
2430 * @param thread the thread to unpark.
2431 */
2432 @IntrinsicCandidate
2433 public native void unpark(Object thread);
2434
2435 /**
2436 * Blocks current thread, returning when a balancing
2437 * {@code unpark} occurs, or a balancing {@code unpark} has
2438 * already occurred, or the thread is interrupted, or, if not
2439 * absolute and time is not zero, the given time nanoseconds have
2786 /**
2787 * Atomically exchanges the given reference value with the current
2788 * reference value of a field or array element within the given
2789 * object {@code o} at the given {@code offset}.
2790 *
2791 * @param o object/array to update the field/element in
2792 * @param offset field/element offset
2793 * @param newValue new value
2794 * @return the previous value
2795 * @since 1.8
2796 */
2797 @IntrinsicCandidate
2798 public final Object getAndSetReference(Object o, long offset, Object newValue) {
2799 Object v;
2800 do {
2801 v = getReferenceVolatile(o, offset);
2802 } while (!weakCompareAndSetReference(o, offset, v, newValue));
2803 return v;
2804 }
2805
2806 @ForceInline
2807 public final Object getAndSetReferenceRelease(Object o, long offset, Object newValue) {
2808 Object v;
2809 do {
2810 v = getReference(o, offset);
2811 } while (!weakCompareAndSetReferenceRelease(o, offset, v, newValue));
2812 return v;
2813 }
2814
2815 @ForceInline
2816 public final Object getAndSetReferenceAcquire(Object o, long offset, Object newValue) {
2817 Object v;
2818 do {
2819 v = getReferenceAcquire(o, offset);
2820 } while (!weakCompareAndSetReferenceAcquire(o, offset, v, newValue));
2821 return v;
2822 }
2823
2824 @IntrinsicCandidate
2825 public final byte getAndSetByte(Object o, long offset, byte newValue) {
2826 byte v;
2827 do {
2828 v = getByteVolatile(o, offset);
2829 } while (!weakCompareAndSetByte(o, offset, v, newValue));
2830 return v;
2831 }
2832
2833 @ForceInline
2834 public final byte getAndSetByteRelease(Object o, long offset, byte newValue) {
2835 byte v;
2836 do {
2837 v = getByte(o, offset);
2838 } while (!weakCompareAndSetByteRelease(o, offset, v, newValue));
2839 return v;
2840 }
2841
2842 @ForceInline
2843 public final byte getAndSetByteAcquire(Object o, long offset, byte newValue) {
3859 private static short convEndian(boolean big, short n) { return big == BIG_ENDIAN ? n : Short.reverseBytes(n) ; }
3860 private static int convEndian(boolean big, int n) { return big == BIG_ENDIAN ? n : Integer.reverseBytes(n) ; }
3861 private static long convEndian(boolean big, long n) { return big == BIG_ENDIAN ? n : Long.reverseBytes(n) ; }
3862
3863
3864
3865 private native long allocateMemory0(long bytes);
3866 private native long reallocateMemory0(long address, long bytes);
3867 private native void freeMemory0(long address);
3868 @IntrinsicCandidate
3869 private native void setMemory0(Object o, long offset, long bytes, byte value);
3870 @IntrinsicCandidate
3871 private native void copyMemory0(Object srcBase, long srcOffset, Object destBase, long destOffset, long bytes);
3872 private native void copySwapMemory0(Object srcBase, long srcOffset, Object destBase, long destOffset, long bytes, long elemSize);
3873 private native long objectFieldOffset0(Field f); // throws IAE
3874 private native long knownObjectFieldOffset0(Class<?> c, String name); // error code: -1 not found, -2 static
3875 private native long staticFieldOffset0(Field f); // throws IAE
3876 private native Object staticFieldBase0(Field f); // throws IAE
3877 private native boolean shouldBeInitialized0(Class<?> c);
3878 private native void ensureClassInitialized0(Class<?> c);
3879 private native int arrayBaseOffset0(Class<?> arrayClass); // public version returns long to promote correct arithmetic
3880 private native int arrayIndexScale0(Class<?> arrayClass);
3881 private native int getLoadAverage0(double[] loadavg, int nelems);
3882
3883
3884 /**
3885 * Invokes the given direct byte buffer's cleaner, if any.
3886 *
3887 * @param directBuffer a direct byte buffer
3888 * @throws NullPointerException if {@code directBuffer} is null
3889 * @throws IllegalArgumentException if {@code directBuffer} is non-direct,
3890 * or is a {@link java.nio.Buffer#slice slice}, or is a
3891 * {@link java.nio.Buffer#duplicate duplicate}
3892 */
3893 public void invokeCleaner(java.nio.ByteBuffer directBuffer) {
3894 if (!directBuffer.isDirect())
3895 throw new IllegalArgumentException("buffer is non-direct");
3896
3897 DirectBuffer db = (DirectBuffer) directBuffer;
3898 if (db.attachment() != null)
3899 throw new IllegalArgumentException("duplicate or slice");
3900
3901 Cleaner cleaner = db.cleaner();
|
1 /*
2 * Copyright (c) 2000, 2026, 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
25
26 package jdk.internal.misc;
27
28 import jdk.internal.vm.annotation.AOTRuntimeSetup;
29 import jdk.internal.vm.annotation.AOTSafeClassInitializer;
30 import jdk.internal.vm.annotation.ForceInline;
31 import jdk.internal.vm.annotation.IntrinsicCandidate;
32 import sun.nio.Cleaner;
33 import sun.nio.ch.DirectBuffer;
34
35 import java.lang.reflect.Field;
36 import java.security.ProtectionDomain;
37
38 import static jdk.internal.misc.UnsafeConstants.*;
39
40 /**
41 * A collection of methods for performing low-level, unsafe operations.
42 * Although the class and all methods are public, use of this class is
43 * limited because only trusted code can obtain instances of it.
44 *
45 * <h2><a id="undefined-behavior">Undefined Behavior</a></h2>
46 * For performance reasons, {@code Unsafe} is allowed to work outside the
47 * restrictions enforced by the JVM. As a result, it is the responsibility of
48 * the caller to ensure that an invocation of an {@code Unsafe} method is
49 * conformant, and failure to do so will result in undefined behavior. The
50 * runtime and the JIT compiler may assume that undefined behavior never
51 * happens, and operate accordingly. For example, the runtime assumes that each
52 * object has a header with a particular layout, and if the users use
53 * {@code Unsafe} to overwrite this header with invalid data, the behavior of
54 * the runtime becomes unpredictable. Another example is that the JIT compiler
55 * may assume that accesses on separate objects are unrelated, and schedule
56 * each of them without taking into consideration the others. If there is an
57 * {@code Unsafe} access that is out of bounds and points to object different
58 * from the declared base, the program may execute in a way that a variable
59 * seems to have multiple values at the same time. As a result, when a program
60 * exhibits undefined behavior, there is no restrictions on its behaviors. Such
61 * behaviors may include but not be limited to:
62 *
63 * <ul>
64 * <li>Working as expected.
65 * <li>Crashing the VM.
66 * <li>Corruption of the heap or JVM memory.
67 * <li>Nonsensical variable value. E.g. an {@code int} may appear to be
68 * simultaneously 0 and 1.
69 * <li>Impossible code execution. E.g. the branches of an {@code if} are
70 * both executed or both not executed.
71 * <li>Wiping out the hard drive.
72 * </ul>
73 *
74 * Undefined behavior, as described in this class, is analogous to the
75 * terminology with the same name in the C++ language.
76 * <p>
77 * Some methods (e.g. {@link #getInt}) exhibit undefined behavior if they
78 * are invoked at runtime with illegal arguments. This means that they will
79 * never exhibit undefined behavior if they are not actually reachable at
80 * runtime. On the other hands, other methods (e.g.
81 * {@link #allocateInstance(Class)}) exhibit undefined behavior if they are
82 * used incorrectly, even if the invocation may not be reachable at runtime.
83 * The analogous terminology in C++ is that such programs are ill-formed.
84 * <p>
85 * For methods exhibiting undefined behavior if they are invoked at runtime
86 * with illegal arguments, undefined behavior may time travel. That is, if a
87 * control path may eventually reach an invocation of an {@code Unsafe} method
88 * with illegal arguments, the symptoms of undefined behavior may be present
89 * even before the invocation of the {@code Unsafe} method. This is because the
90 * JIT compiler may have certain assumptions about the inputs of an
91 * {@code Unsafe} invocation, these assumptions may propagate backward to
92 * previous statements, leading to wrong executions if the assumptions are
93 * invalid.
94 *
95 * @author John R. Rose
96 * @see #getUnsafe
97 */
98 @AOTSafeClassInitializer
99 public final class Unsafe {
100
101 private static native void registerNatives();
102 static {
103 runtimeSetup();
104 }
105
106 /// BASE_OFFSET, INDEX_SCALE, and ADDRESS_SIZE fields are equivalent if the
107 /// AOT initialized heap is reused, so just register natives
108 @AOTRuntimeSetup
109 private static void runtimeSetup() {
110 registerNatives();
111 }
112
113 private Unsafe() {}
210 * The first two parameters are interpreted exactly as with
211 * {@link #getInt(Object, long)} to refer to a specific
212 * Java variable (field or array element). The given value
213 * is stored into that variable.
214 * <p>
215 * The variable must be of the same type as the method
216 * parameter {@code x}.
217 *
218 * @param o Java heap object in which the variable resides, if any, else
219 * null
220 * @param offset indication of where the variable resides in a Java heap
221 * object, if any, else a memory address locating the variable
222 * statically
223 * @param x the value to store into the indicated Java variable
224 * @throws RuntimeException No defined exceptions are thrown, not even
225 * {@link NullPointerException}
226 */
227 @IntrinsicCandidate
228 public native void putInt(Object o, long offset, int x);
229
230 /**
231 * Returns true if the given field is flattened.
232 */
233 public boolean isFlatField(Field f) {
234 if (f == null) {
235 throw new NullPointerException();
236 }
237 return isFlatField0(f);
238 }
239
240 private native boolean isFlatField0(Object o);
241
242 /* Returns true if the given field has a null marker
243 * <p>
244 * Nullable flat fields are stored in a flattened representation
245 * and have an associated null marker to indicate if the the field value is
246 * null or the one stored with the flat representation
247 */
248
249 public boolean hasNullMarker(Field f) {
250 if (f == null) {
251 throw new NullPointerException();
252 }
253 return hasNullMarker0(f);
254 }
255
256 private native boolean hasNullMarker0(Object o);
257
258 /* Returns the offset of the null marker of the field,
259 * or -1 if the field doesn't have a null marker
260 */
261
262 public int nullMarkerOffset(Field f) {
263 if (f == null) {
264 throw new NullPointerException();
265 }
266 return nullMarkerOffset0(f);
267 }
268
269 private native int nullMarkerOffset0(Object o);
270
271 public static final int NON_FLAT_LAYOUT = 0;
272
273 /* Reports the kind of layout used for an element in the storage
274 * allocation of the given array. Do not expect to perform any logic
275 * or layout control with this value, it is just an opaque token
276 * used for performance reasons.
277 *
278 * A layout of 0 indicates this array is not flat.
279 */
280 public int arrayLayout(Object[] array) {
281 if (array == null) {
282 throw new NullPointerException();
283 }
284 return arrayLayout0(array);
285 }
286
287 @IntrinsicCandidate
288 private native int arrayLayout0(Object[] array);
289
290
291 /* Reports the kind of layout used for a given field in the storage
292 * allocation of its class. Do not expect to perform any logic
293 * or layout control with this value, it is just an opaque token
294 * used for performance reasons.
295 *
296 * A layout of 0 indicates this field is not flat.
297 */
298 public int fieldLayout(Field f) {
299 if (f == null) {
300 throw new NullPointerException();
301 }
302 return fieldLayout0(f);
303 }
304
305 private native int fieldLayout0(Object o);
306
307 public native Object[] newSpecialArray(Class<?> componentType,
308 int length, int layoutKind);
309
310 /**
311 * Fetches a reference value from a given Java variable.
312 * This method can return a reference to either an object or value
313 * or a null reference.
314 *
315 * @see #getInt(Object, long)
316 */
317 @IntrinsicCandidate
318 public native Object getReference(Object o, long offset);
319
320 /**
321 * Stores a reference value into a given Java variable.
322 * This method can store a reference to either an object or value
323 * or a null reference.
324 * <p>
325 * Unless the reference {@code x} being stored is either null
326 * or matches the field type, the results are undefined.
327 * If the reference {@code o} is non-null, card marks or
328 * other store barriers for that object (if the VM requires them)
329 * are updated.
330 * @see #putInt(Object, long, int)
331 */
332 @IntrinsicCandidate
333 public native void putReference(Object o, long offset, Object x);
334
335 /**
336 * Fetches a value of type {@code <V>} from a given Java variable.
337 * More specifically, fetches a field or array element within the given
338 * {@code o} object at the given offset, or (if {@code o} is null)
339 * from the memory address whose numerical value is the given offset.
340 *
341 * @apiNote
342 * The returned object is newly allocated into the heap, because flat
343 * values lack object headers and thus can't be used as objects directly.
344 *
345 * @param o Java heap object in which the variable resides, if any, else
346 * null
347 * @param offset indication of where the variable resides in a Java heap
348 * object, if any, else a memory address locating the variable
349 * statically
350 * @param layoutKind opaque value used by the VM to know the layout
351 * the field or array element. This value must be retrieved with
352 * {@link #fieldLayout} or {@link #arrayLayout}.
353 * @param valueType value type
354 * @param <V> the type of a value
355 * @return the value fetched from the indicated Java variable
356 * @throws RuntimeException No defined exceptions are thrown, not even
357 * {@link NullPointerException}
358 */
359 @IntrinsicCandidate
360 public native <V> V getFlatValue(Object o, long offset, int layoutKind, Class<?> valueType);
361
362 /**
363 * Stores the given value into a given Java variable.
364 *
365 * Unless the reference {@code o} being stored is either null
366 * or matches the field type, the results are undefined.
367 *
368 * @param o Java heap object in which the variable resides, if any, else
369 * null
370 * @param offset indication of where the variable resides in a Java heap
371 * object, if any, else a memory address locating the variable
372 * statically
373 * @param layoutKind opaque value used by the VM to know the layout
374 * the field or array element. This value must be retrieved with
375 * {@link #fieldLayout} or {@link #arrayLayout}.
376 * @param valueType value type
377 * @param v the value to store into the indicated Java variable
378 * @param <V> the type of a value
379 * @throws RuntimeException No defined exceptions are thrown, not even
380 * {@link NullPointerException}
381 */
382 @IntrinsicCandidate
383 public native <V> void putFlatValue(Object o, long offset, int layoutKind, Class<?> valueType, V v);
384
385 /**
386 * Returns the header size of the given value type.
387 *
388 * @param valueType value type
389 * @return the header size of the value type
390 */
391 public native <V> long valueHeaderSize(Class<V> valueType);
392
393 /** @see #getInt(Object, long) */
394 @IntrinsicCandidate
395 public native boolean getBoolean(Object o, long offset);
396
397 /** @see #putInt(Object, long, int) */
398 @IntrinsicCandidate
399 public native void putBoolean(Object o, long offset, boolean x);
400
401 /** @see #getInt(Object, long) */
402 @IntrinsicCandidate
403 public native byte getByte(Object o, long offset);
404
405 /** @see #putInt(Object, long, int) */
406 @IntrinsicCandidate
407 public native void putByte(Object o, long offset, byte x);
408
409 /** @see #getInt(Object, long) */
410 @IntrinsicCandidate
411 public native short getShort(Object o, long offset);
412
1362 }
1363
1364 /**
1365 * Ensures the given class has been initialized (see JVMS-5.5 for details).
1366 * This is often needed in conjunction with obtaining the static field base
1367 * of a class.
1368 *
1369 * The call returns when either class {@code c} is fully initialized or
1370 * class {@code c} is being initialized and the call is performed from
1371 * the initializing thread. In the latter case a subsequent call to
1372 * {@link #shouldBeInitialized} will return {@code true}.
1373 */
1374 public void ensureClassInitialized(Class<?> c) {
1375 if (c == null) {
1376 throw new NullPointerException();
1377 }
1378
1379 ensureClassInitialized0(c);
1380 }
1381
1382 /**
1383 * The reading or writing of strict static fields may require
1384 * special processing. Notify the VM that such an event is about
1385 * to happen. The VM may respond by throwing an exception, in the
1386 * case of a read of an uninitialized field. If the VM allows the
1387 * method to return normally, no further calls are needed, with
1388 * the same arguments.
1389 */
1390 public void notifyStrictStaticAccess(Class<?> c, long staticFieldOffset, boolean writing) {
1391 if (c == null) {
1392 throw new NullPointerException();
1393 }
1394 notifyStrictStaticAccess0(c, staticFieldOffset, writing);
1395 }
1396
1397 /**
1398 * Reports the offset of the first element in the storage allocation of a
1399 * given array class. If {@link #arrayIndexScale} returns a non-zero value
1400 * for the same class, you may use that scale factor, together with this
1401 * base offset, to form new offsets to access elements of arrays of the
1402 * given class.
1403 * <p>
1404 * The return value is in the range of a {@code int}. The return type is
1405 * {@code long} to emphasize that long arithmetic should always be used
1406 * for offset calculations to avoid overflows.
1407 * <p>
1408 * This method doesn't support arrays with an element type that is
1409 * a value class, because this type of array can have multiple layouts.
1410 * For these arrays, {@code arrayInstanceBaseOffset(Object[] array)}
1411 * must be used instead.
1412 *
1413 * @see #getInt(Object, long)
1414 * @see #putInt(Object, long, int)
1415 */
1416 public long arrayBaseOffset(Class<?> arrayClass) {
1417 if (arrayClass == null) {
1418 throw new NullPointerException();
1419 }
1420
1421 return arrayBaseOffset0(arrayClass);
1422 }
1423
1424 public long arrayInstanceBaseOffset(Object[] array) {
1425 if (array == null) {
1426 throw new NullPointerException();
1427 }
1428
1429 return arrayInstanceBaseOffset0(array);
1430 }
1431
1432 /** The value of {@code arrayBaseOffset(boolean[].class)} */
1433 public static final long ARRAY_BOOLEAN_BASE_OFFSET
1434 = theUnsafe.arrayBaseOffset(boolean[].class);
1435
1436 /** The value of {@code arrayBaseOffset(byte[].class)} */
1437 public static final long ARRAY_BYTE_BASE_OFFSET
1438 = theUnsafe.arrayBaseOffset(byte[].class);
1439
1440 /** The value of {@code arrayBaseOffset(short[].class)} */
1441 public static final long ARRAY_SHORT_BASE_OFFSET
1442 = theUnsafe.arrayBaseOffset(short[].class);
1443
1444 /** The value of {@code arrayBaseOffset(char[].class)} */
1445 public static final long ARRAY_CHAR_BASE_OFFSET
1446 = theUnsafe.arrayBaseOffset(char[].class);
1447
1448 /** The value of {@code arrayBaseOffset(int[].class)} */
1449 public static final long ARRAY_INT_BASE_OFFSET
1450 = theUnsafe.arrayBaseOffset(int[].class);
1457 public static final long ARRAY_FLOAT_BASE_OFFSET
1458 = theUnsafe.arrayBaseOffset(float[].class);
1459
1460 /** The value of {@code arrayBaseOffset(double[].class)} */
1461 public static final long ARRAY_DOUBLE_BASE_OFFSET
1462 = theUnsafe.arrayBaseOffset(double[].class);
1463
1464 /** The value of {@code arrayBaseOffset(Object[].class)} */
1465 public static final long ARRAY_OBJECT_BASE_OFFSET
1466 = theUnsafe.arrayBaseOffset(Object[].class);
1467
1468 /**
1469 * Reports the scale factor for addressing elements in the storage
1470 * allocation of a given array class. However, arrays of "narrow" types
1471 * will generally not work properly with accessors like {@link
1472 * #getByte(Object, long)}, so the scale factor for such classes is reported
1473 * as zero.
1474 * <p>
1475 * The computation of the actual memory offset should always use {@code
1476 * long} arithmetic to avoid overflows.
1477 * <p>
1478 * This method doesn't support arrays with an element type that is
1479 * a value class, because this type of array can have multiple layouts.
1480 * For these arrays, {@code arrayInstanceIndexScale(Object[] array)}
1481 * must be used instead.
1482 *
1483 * @see #arrayBaseOffset
1484 * @see #getInt(Object, long)
1485 * @see #putInt(Object, long, int)
1486 */
1487 public int arrayIndexScale(Class<?> arrayClass) {
1488 if (arrayClass == null) {
1489 throw new NullPointerException();
1490 }
1491
1492 return arrayIndexScale0(arrayClass);
1493 }
1494
1495 public int arrayInstanceIndexScale(Object[] array) {
1496 if (array == null) {
1497 throw new NullPointerException();
1498 }
1499
1500 return arrayInstanceIndexScale0(array);
1501 }
1502
1503 /**
1504 * Returns the acmp map of this class, which must be a concrete value class.
1505 * Intended to be used by substitutability test in ValueObjectMethods only.
1506 * The format is subject to change.
1507 */
1508 public int[] getFieldMap(Class<?> c) {
1509 if (c == null) {
1510 throw new NullPointerException();
1511 }
1512 return getFieldMap0(c);
1513 }
1514
1515 /**
1516 * For a field of type {@code c}, returns true if and only if there is
1517 * a possible flat layout that contains no oop.
1518 * Required for numerical CAS safety.
1519 */
1520 public boolean isFlatPayloadBinary(Class<?> c) {
1521 int[] map = getFieldMap(c);
1522 int nbNonRef = map[0];
1523 return nbNonRef * 2 + 1 == map.length;
1524 }
1525
1526 /**
1527 * Return the size of the object in the heap.
1528 * @param o an object
1529 * @return the objects's size
1530 * @since Valhalla
1531 */
1532 public long getObjectSize(Object o) {
1533 if (o == null)
1534 throw new NullPointerException();
1535 return getObjectSize0(o);
1536 }
1537
1538 /** The value of {@code arrayIndexScale(boolean[].class)} */
1539 public static final int ARRAY_BOOLEAN_INDEX_SCALE
1540 = theUnsafe.arrayIndexScale(boolean[].class);
1541
1542 /** The value of {@code arrayIndexScale(byte[].class)} */
1543 public static final int ARRAY_BYTE_INDEX_SCALE
1544 = theUnsafe.arrayIndexScale(byte[].class);
1545
1546 /** The value of {@code arrayIndexScale(short[].class)} */
1547 public static final int ARRAY_SHORT_INDEX_SCALE
1548 = theUnsafe.arrayIndexScale(short[].class);
1549
1550 /** The value of {@code arrayIndexScale(char[].class)} */
1551 public static final int ARRAY_CHAR_INDEX_SCALE
1552 = theUnsafe.arrayIndexScale(char[].class);
1553
1554 /** The value of {@code arrayIndexScale(int[].class)} */
1555 public static final int ARRAY_INT_INDEX_SCALE
1556 = theUnsafe.arrayIndexScale(int[].class);
1620 public Class<?> defineClass(String name, byte[] b, int off, int len,
1621 ClassLoader loader,
1622 ProtectionDomain protectionDomain) {
1623 if (b == null) {
1624 throw new NullPointerException();
1625 }
1626 if (len < 0) {
1627 throw new ArrayIndexOutOfBoundsException();
1628 }
1629
1630 return defineClass0(name, b, off, len, loader, protectionDomain);
1631 }
1632
1633 public native Class<?> defineClass0(String name, byte[] b, int off, int len,
1634 ClassLoader loader,
1635 ProtectionDomain protectionDomain);
1636
1637 /**
1638 * Allocates an instance but does not run any constructor.
1639 * Initializes the class if it has not yet been.
1640 * <p>
1641 * This method returns an uninitialized instance. In general, this is undefined behavior, this
1642 * method is treated specially by the JVM to allow this behavior. The returned value must be
1643 * passed into a constructor using {@link MethodHandle#linkToSpecial} before any other
1644 * operation can be performed on it. Otherwise, the program is ill-formed.
1645 */
1646 @IntrinsicCandidate
1647 public native Object allocateInstance(Class<?> cls)
1648 throws InstantiationException;
1649
1650 /**
1651 * Allocates an array of a given type, but does not do zeroing.
1652 * <p>
1653 * This method should only be used in the very rare cases where a high-performance code
1654 * overwrites the destination array completely, and compilers cannot assist in zeroing elimination.
1655 * In an overwhelming majority of cases, a normal Java allocation should be used instead.
1656 * <p>
1657 * Users of this method are <b>required</b> to overwrite the initial (garbage) array contents
1658 * before allowing untrusted code, or code in other threads, to observe the reference
1659 * to the newly allocated array. In addition, the publication of the array reference must be
1660 * safe according to the Java Memory Model requirements.
1661 * <p>
1662 * The safest approach to deal with an uninitialized array is to keep the reference to it in local
1663 * variable at least until the initialization is complete, and then publish it <b>once</b>, either
1664 * by writing it to a <em>volatile</em> field, or storing it into a <em>final</em> field in constructor,
1700 return null;
1701 }
1702
1703 /** Throws the exception without telling the verifier. */
1704 public native void throwException(Throwable ee);
1705
1706 /**
1707 * Atomically updates Java variable to {@code x} if it is currently
1708 * holding {@code expected}.
1709 *
1710 * <p>This operation has memory semantics of a {@code volatile} read
1711 * and write. Corresponds to C11 atomic_compare_exchange_strong.
1712 *
1713 * @return {@code true} if successful
1714 */
1715 @IntrinsicCandidate
1716 public final native boolean compareAndSetReference(Object o, long offset,
1717 Object expected,
1718 Object x);
1719
1720 private final boolean isValueObject(Object o) {
1721 return o != null && o.getClass().isValue();
1722 }
1723
1724 /*
1725 * For value type, CAS should do substitutability test as opposed
1726 * to two pointers comparison.
1727 */
1728 @ForceInline
1729 public final <V> boolean compareAndSetReference(Object o, long offset,
1730 Class<?> type,
1731 V expected,
1732 V x) {
1733 if (type.isValue() || isValueObject(expected)) {
1734 while (true) {
1735 Object witness = getReferenceVolatile(o, offset);
1736 if (witness != expected) {
1737 return false;
1738 }
1739 if (compareAndSetReference(o, offset, witness, x)) {
1740 return true;
1741 }
1742 }
1743 } else {
1744 return compareAndSetReference(o, offset, expected, x);
1745 }
1746 }
1747
1748 @ForceInline
1749 public final <V> boolean compareAndSetFlatValue(Object o, long offset,
1750 int layout,
1751 Class<?> valueType,
1752 V expected,
1753 V x) {
1754 Object[] array = newSpecialArray(valueType, 2, layout);
1755 return compareAndSetFlatValueAsBytes(array, o, offset, layout, valueType, expected, x);
1756 }
1757
1758 @IntrinsicCandidate
1759 public final native Object compareAndExchangeReference(Object o, long offset,
1760 Object expected,
1761 Object x);
1762
1763 @ForceInline
1764 public final <V> Object compareAndExchangeReference(Object o, long offset,
1765 Class<?> valueType,
1766 V expected,
1767 V x) {
1768 if (valueType.isValue() || isValueObject(expected)) {
1769 while (true) {
1770 Object witness = getReferenceVolatile(o, offset);
1771 if (witness != expected) {
1772 return witness;
1773 }
1774 if (compareAndSetReference(o, offset, witness, x)) {
1775 return witness;
1776 }
1777 }
1778 } else {
1779 return compareAndExchangeReference(o, offset, expected, x);
1780 }
1781 }
1782
1783 @ForceInline
1784 public final <V> Object compareAndExchangeFlatValue(Object o, long offset,
1785 int layout,
1786 Class<?> valueType,
1787 V expected,
1788 V x) {
1789 Object[] array = newSpecialArray(valueType, 2, layout);
1790 compareAndSetFlatValueAsBytes(array, o, offset, layout, valueType, expected, x);
1791 return array[0];
1792 }
1793
1794 @IntrinsicCandidate
1795 public final Object compareAndExchangeReferenceAcquire(Object o, long offset,
1796 Object expected,
1797 Object x) {
1798 return compareAndExchangeReference(o, offset, expected, x);
1799 }
1800
1801 public final <V> Object compareAndExchangeReferenceAcquire(Object o, long offset,
1802 Class<?> valueType,
1803 V expected,
1804 V x) {
1805 return compareAndExchangeReference(o, offset, valueType, expected, x);
1806 }
1807
1808 @ForceInline
1809 public final <V> Object compareAndExchangeFlatValueAcquire(Object o, long offset,
1810 int layout,
1811 Class<?> valueType,
1812 V expected,
1813 V x) {
1814 return compareAndExchangeFlatValue(o, offset, layout, valueType, expected, x);
1815 }
1816
1817 @IntrinsicCandidate
1818 public final Object compareAndExchangeReferenceRelease(Object o, long offset,
1819 Object expected,
1820 Object x) {
1821 return compareAndExchangeReference(o, offset, expected, x);
1822 }
1823
1824 public final <V> Object compareAndExchangeReferenceRelease(Object o, long offset,
1825 Class<?> valueType,
1826 V expected,
1827 V x) {
1828 return compareAndExchangeReference(o, offset, valueType, expected, x);
1829 }
1830
1831 @ForceInline
1832 public final <V> Object compareAndExchangeFlatValueRelease(Object o, long offset,
1833 int layout,
1834 Class<?> valueType,
1835 V expected,
1836 V x) {
1837 return compareAndExchangeFlatValue(o, offset, layout, valueType, expected, x);
1838 }
1839
1840 @IntrinsicCandidate
1841 public final boolean weakCompareAndSetReferencePlain(Object o, long offset,
1842 Object expected,
1843 Object x) {
1844 return compareAndSetReference(o, offset, expected, x);
1845 }
1846
1847 public final <V> boolean weakCompareAndSetReferencePlain(Object o, long offset,
1848 Class<?> valueType,
1849 V expected,
1850 V x) {
1851 if (valueType.isValue() || isValueObject(expected)) {
1852 return compareAndSetReference(o, offset, valueType, expected, x);
1853 } else {
1854 return weakCompareAndSetReferencePlain(o, offset, expected, x);
1855 }
1856 }
1857
1858 @ForceInline
1859 public final <V> boolean weakCompareAndSetFlatValuePlain(Object o, long offset,
1860 int layout,
1861 Class<?> valueType,
1862 V expected,
1863 V x) {
1864 return compareAndSetFlatValue(o, offset, layout, valueType, expected, x);
1865 }
1866
1867 @IntrinsicCandidate
1868 public final boolean weakCompareAndSetReferenceAcquire(Object o, long offset,
1869 Object expected,
1870 Object x) {
1871 return compareAndSetReference(o, offset, expected, x);
1872 }
1873
1874 public final <V> boolean weakCompareAndSetReferenceAcquire(Object o, long offset,
1875 Class<?> valueType,
1876 V expected,
1877 V x) {
1878 if (valueType.isValue() || isValueObject(expected)) {
1879 return compareAndSetReference(o, offset, valueType, expected, x);
1880 } else {
1881 return weakCompareAndSetReferencePlain(o, offset, expected, x);
1882 }
1883 }
1884
1885 @ForceInline
1886 public final <V> boolean weakCompareAndSetFlatValueAcquire(Object o, long offset,
1887 int layout,
1888 Class<?> valueType,
1889 V expected,
1890 V x) {
1891 return compareAndSetFlatValue(o, offset, layout, valueType, expected, x);
1892 }
1893
1894 @IntrinsicCandidate
1895 public final boolean weakCompareAndSetReferenceRelease(Object o, long offset,
1896 Object expected,
1897 Object x) {
1898 return compareAndSetReference(o, offset, expected, x);
1899 }
1900
1901 public final <V> boolean weakCompareAndSetReferenceRelease(Object o, long offset,
1902 Class<?> valueType,
1903 V expected,
1904 V x) {
1905 if (valueType.isValue() || isValueObject(expected)) {
1906 return compareAndSetReference(o, offset, valueType, expected, x);
1907 } else {
1908 return weakCompareAndSetReferencePlain(o, offset, expected, x);
1909 }
1910 }
1911
1912 @ForceInline
1913 public final <V> boolean weakCompareAndSetFlatValueRelease(Object o, long offset,
1914 int layout,
1915 Class<?> valueType,
1916 V expected,
1917 V x) {
1918 return compareAndSetFlatValue(o, offset, layout, valueType, expected, x);
1919 }
1920
1921 @IntrinsicCandidate
1922 public final boolean weakCompareAndSetReference(Object o, long offset,
1923 Object expected,
1924 Object x) {
1925 return compareAndSetReference(o, offset, expected, x);
1926 }
1927
1928 public final <V> boolean weakCompareAndSetReference(Object o, long offset,
1929 Class<?> valueType,
1930 V expected,
1931 V x) {
1932 if (valueType.isValue() || isValueObject(expected)) {
1933 return compareAndSetReference(o, offset, valueType, expected, x);
1934 } else {
1935 return weakCompareAndSetReferencePlain(o, offset, expected, x);
1936 }
1937 }
1938
1939 @ForceInline
1940 public final <V> boolean weakCompareAndSetFlatValue(Object o, long offset,
1941 int layout,
1942 Class<?> valueType,
1943 V expected,
1944 V x) {
1945 return compareAndSetFlatValue(o, offset, layout, valueType, expected, x);
1946 }
1947
1948 /**
1949 * Atomically updates Java variable to {@code x} if it is currently
1950 * holding {@code expected}.
1951 *
1952 * <p>This operation has memory semantics of a {@code volatile} read
1953 * and write. Corresponds to C11 atomic_compare_exchange_strong.
1954 *
1955 * @return {@code true} if successful
1956 */
1957 @IntrinsicCandidate
1958 public final native boolean compareAndSetInt(Object o, long offset,
1959 int expected,
1960 int x);
1961
1962 @IntrinsicCandidate
1963 public final native int compareAndExchangeInt(Object o, long offset,
1964 int expected,
1965 int x);
1966
1967 @IntrinsicCandidate
2543 public final boolean weakCompareAndSetLongRelease(Object o, long offset,
2544 long expected,
2545 long x) {
2546 return compareAndSetLong(o, offset, expected, x);
2547 }
2548
2549 @IntrinsicCandidate
2550 public final boolean weakCompareAndSetLong(Object o, long offset,
2551 long expected,
2552 long x) {
2553 return compareAndSetLong(o, offset, expected, x);
2554 }
2555
2556 /**
2557 * Fetches a reference value from a given Java variable, with volatile
2558 * load semantics. Otherwise identical to {@link #getReference(Object, long)}
2559 */
2560 @IntrinsicCandidate
2561 public native Object getReferenceVolatile(Object o, long offset);
2562
2563 @ForceInline
2564 public final <V> Object getFlatValueVolatile(Object o, long offset, int layout, Class<?> valueType) {
2565 // we translate using fences (see: https://gee.cs.oswego.edu/dl/html/j9mm.html)
2566 Object res = getFlatValue(o, offset, layout, valueType);
2567 fullFence();
2568 return res;
2569 }
2570
2571 /**
2572 * Stores a reference value into a given Java variable, with
2573 * volatile store semantics. Otherwise identical to {@link #putReference(Object, long, Object)}
2574 */
2575 @IntrinsicCandidate
2576 public native void putReferenceVolatile(Object o, long offset, Object x);
2577
2578 @ForceInline
2579 public final <V> void putFlatValueVolatile(Object o, long offset, int layout, Class<?> valueType, V x) {
2580 // we translate using fences (see: https://gee.cs.oswego.edu/dl/html/j9mm.html)
2581 putFlatValueRelease(o, offset, layout, valueType, x);
2582 fullFence();
2583 }
2584
2585 /** Volatile version of {@link #getInt(Object, long)} */
2586 @IntrinsicCandidate
2587 public native int getIntVolatile(Object o, long offset);
2588
2589 /** Volatile version of {@link #putInt(Object, long, int)} */
2590 @IntrinsicCandidate
2591 public native void putIntVolatile(Object o, long offset, int x);
2592
2593 /** Volatile version of {@link #getBoolean(Object, long)} */
2594 @IntrinsicCandidate
2595 public native boolean getBooleanVolatile(Object o, long offset);
2596
2597 /** Volatile version of {@link #putBoolean(Object, long, boolean)} */
2598 @IntrinsicCandidate
2599 public native void putBooleanVolatile(Object o, long offset, boolean x);
2600
2601 /** Volatile version of {@link #getByte(Object, long)} */
2602 @IntrinsicCandidate
2603 public native byte getByteVolatile(Object o, long offset);
2604
2637 /** Volatile version of {@link #putFloat(Object, long, float)} */
2638 @IntrinsicCandidate
2639 public native void putFloatVolatile(Object o, long offset, float x);
2640
2641 /** Volatile version of {@link #getDouble(Object, long)} */
2642 @IntrinsicCandidate
2643 public native double getDoubleVolatile(Object o, long offset);
2644
2645 /** Volatile version of {@link #putDouble(Object, long, double)} */
2646 @IntrinsicCandidate
2647 public native void putDoubleVolatile(Object o, long offset, double x);
2648
2649
2650
2651 /** Acquire version of {@link #getReferenceVolatile(Object, long)} */
2652 @IntrinsicCandidate
2653 public final Object getReferenceAcquire(Object o, long offset) {
2654 return getReferenceVolatile(o, offset);
2655 }
2656
2657 @ForceInline
2658 public final <V> Object getFlatValueAcquire(Object o, long offset, int layout, Class<?> valueType) {
2659 // we translate using fences (see: https://gee.cs.oswego.edu/dl/html/j9mm.html)
2660 Object res = getFlatValue(o, offset, layout, valueType);
2661 loadFence();
2662 return res;
2663 }
2664
2665 /** Acquire version of {@link #getBooleanVolatile(Object, long)} */
2666 @IntrinsicCandidate
2667 public final boolean getBooleanAcquire(Object o, long offset) {
2668 return getBooleanVolatile(o, offset);
2669 }
2670
2671 /** Acquire version of {@link #getByteVolatile(Object, long)} */
2672 @IntrinsicCandidate
2673 public final byte getByteAcquire(Object o, long offset) {
2674 return getByteVolatile(o, offset);
2675 }
2676
2677 /** Acquire version of {@link #getShortVolatile(Object, long)} */
2678 @IntrinsicCandidate
2679 public final short getShortAcquire(Object o, long offset) {
2680 return getShortVolatile(o, offset);
2681 }
2682
2683 /** Acquire version of {@link #getCharVolatile(Object, long)} */
2684 @IntrinsicCandidate
2709 public final double getDoubleAcquire(Object o, long offset) {
2710 return getDoubleVolatile(o, offset);
2711 }
2712
2713 /*
2714 * Versions of {@link #putReferenceVolatile(Object, long, Object)}
2715 * that do not guarantee immediate visibility of the store to
2716 * other threads. This method is generally only useful if the
2717 * underlying field is a Java volatile (or if an array cell, one
2718 * that is otherwise only accessed using volatile accesses).
2719 *
2720 * Corresponds to C11 atomic_store_explicit(..., memory_order_release).
2721 */
2722
2723 /** Release version of {@link #putReferenceVolatile(Object, long, Object)} */
2724 @IntrinsicCandidate
2725 public final void putReferenceRelease(Object o, long offset, Object x) {
2726 putReferenceVolatile(o, offset, x);
2727 }
2728
2729 @ForceInline
2730 public final <V> void putFlatValueRelease(Object o, long offset, int layout, Class<?> valueType, V x) {
2731 // we translate using fences (see: https://gee.cs.oswego.edu/dl/html/j9mm.html)
2732 storeFence();
2733 putFlatValue(o, offset, layout, valueType, x);
2734 }
2735
2736 /** Release version of {@link #putBooleanVolatile(Object, long, boolean)} */
2737 @IntrinsicCandidate
2738 public final void putBooleanRelease(Object o, long offset, boolean x) {
2739 putBooleanVolatile(o, offset, x);
2740 }
2741
2742 /** Release version of {@link #putByteVolatile(Object, long, byte)} */
2743 @IntrinsicCandidate
2744 public final void putByteRelease(Object o, long offset, byte x) {
2745 putByteVolatile(o, offset, x);
2746 }
2747
2748 /** Release version of {@link #putShortVolatile(Object, long, short)} */
2749 @IntrinsicCandidate
2750 public final void putShortRelease(Object o, long offset, short x) {
2751 putShortVolatile(o, offset, x);
2752 }
2753
2754 /** Release version of {@link #putCharVolatile(Object, long, char)} */
2755 @IntrinsicCandidate
2772 /** Release version of {@link #putLongVolatile(Object, long, long)} */
2773 @IntrinsicCandidate
2774 public final void putLongRelease(Object o, long offset, long x) {
2775 putLongVolatile(o, offset, x);
2776 }
2777
2778 /** Release version of {@link #putDoubleVolatile(Object, long, double)} */
2779 @IntrinsicCandidate
2780 public final void putDoubleRelease(Object o, long offset, double x) {
2781 putDoubleVolatile(o, offset, x);
2782 }
2783
2784 // ------------------------------ Opaque --------------------------------------
2785
2786 /** Opaque version of {@link #getReferenceVolatile(Object, long)} */
2787 @IntrinsicCandidate
2788 public final Object getReferenceOpaque(Object o, long offset) {
2789 return getReferenceVolatile(o, offset);
2790 }
2791
2792 @ForceInline
2793 public final <V> Object getFlatValueOpaque(Object o, long offset, int layout, Class<?> valueType) {
2794 // this is stronger than opaque semantics
2795 return getFlatValueAcquire(o, offset, layout, valueType);
2796 }
2797
2798 /** Opaque version of {@link #getBooleanVolatile(Object, long)} */
2799 @IntrinsicCandidate
2800 public final boolean getBooleanOpaque(Object o, long offset) {
2801 return getBooleanVolatile(o, offset);
2802 }
2803
2804 /** Opaque version of {@link #getByteVolatile(Object, long)} */
2805 @IntrinsicCandidate
2806 public final byte getByteOpaque(Object o, long offset) {
2807 return getByteVolatile(o, offset);
2808 }
2809
2810 /** Opaque version of {@link #getShortVolatile(Object, long)} */
2811 @IntrinsicCandidate
2812 public final short getShortOpaque(Object o, long offset) {
2813 return getShortVolatile(o, offset);
2814 }
2815
2816 /** Opaque version of {@link #getCharVolatile(Object, long)} */
2817 @IntrinsicCandidate
2832 }
2833
2834 /** Opaque version of {@link #getLongVolatile(Object, long)} */
2835 @IntrinsicCandidate
2836 public final long getLongOpaque(Object o, long offset) {
2837 return getLongVolatile(o, offset);
2838 }
2839
2840 /** Opaque version of {@link #getDoubleVolatile(Object, long)} */
2841 @IntrinsicCandidate
2842 public final double getDoubleOpaque(Object o, long offset) {
2843 return getDoubleVolatile(o, offset);
2844 }
2845
2846 /** Opaque version of {@link #putReferenceVolatile(Object, long, Object)} */
2847 @IntrinsicCandidate
2848 public final void putReferenceOpaque(Object o, long offset, Object x) {
2849 putReferenceVolatile(o, offset, x);
2850 }
2851
2852 @ForceInline
2853 public final <V> void putFlatValueOpaque(Object o, long offset, int layout, Class<?> valueType, V x) {
2854 // this is stronger than opaque semantics
2855 putFlatValueRelease(o, offset, layout, valueType, x);
2856 }
2857
2858 /** Opaque version of {@link #putBooleanVolatile(Object, long, boolean)} */
2859 @IntrinsicCandidate
2860 public final void putBooleanOpaque(Object o, long offset, boolean x) {
2861 putBooleanVolatile(o, offset, x);
2862 }
2863
2864 /** Opaque version of {@link #putByteVolatile(Object, long, byte)} */
2865 @IntrinsicCandidate
2866 public final void putByteOpaque(Object o, long offset, byte x) {
2867 putByteVolatile(o, offset, x);
2868 }
2869
2870 /** Opaque version of {@link #putShortVolatile(Object, long, short)} */
2871 @IntrinsicCandidate
2872 public final void putShortOpaque(Object o, long offset, short x) {
2873 putShortVolatile(o, offset, x);
2874 }
2875
2876 /** Opaque version of {@link #putCharVolatile(Object, long, char)} */
2877 @IntrinsicCandidate
2886 }
2887
2888 /** Opaque version of {@link #putFloatVolatile(Object, long, float)} */
2889 @IntrinsicCandidate
2890 public final void putFloatOpaque(Object o, long offset, float x) {
2891 putFloatVolatile(o, offset, x);
2892 }
2893
2894 /** Opaque version of {@link #putLongVolatile(Object, long, long)} */
2895 @IntrinsicCandidate
2896 public final void putLongOpaque(Object o, long offset, long x) {
2897 putLongVolatile(o, offset, x);
2898 }
2899
2900 /** Opaque version of {@link #putDoubleVolatile(Object, long, double)} */
2901 @IntrinsicCandidate
2902 public final void putDoubleOpaque(Object o, long offset, double x) {
2903 putDoubleVolatile(o, offset, x);
2904 }
2905
2906 @ForceInline
2907 private boolean compareAndSetFlatValueAsBytes(Object[] array, Object o, long offset, int layout, Class<?> valueType, Object expected, Object x) {
2908 // We can convert between a value object and a binary value (of suitable size) using array elements.
2909 // This only works if the payload contains no oops (see VarHandles::isAtomicFlat).
2910 // Thus, we can implement the CAS with a plain numeric CAS.
2911
2912 // array[0]: witness (put as binary, get as object), at base
2913 // array[1]: x (put as object, get as binary), at base + scale
2914 // When witness == expected, the witness binary may be different from the expected binary.
2915 // This happens when compiler does not zero unused positions in the witness.
2916 // So we must obtain the witness binary and use it as expected binary for the numeric CAS.
2917 long base = arrayInstanceBaseOffset(array);
2918 int scale = arrayInstanceIndexScale(array);
2919 putFlatValue(array, base + scale, layout, valueType, x); // put x as object
2920 switch (scale) {
2921 case 1: {
2922 do {
2923 byte witnessByte = getByteVolatile(o, offset);
2924 putByte(array, base, witnessByte); // put witness as binary
2925 Object witness = getFlatValue(array, base, layout, valueType); // get witness as object
2926 if (witness != expected) {
2927 return false;
2928 }
2929 byte xByte = getByte(array, base + scale); // get x as binary
2930 if (compareAndSetByte(o, offset, witnessByte, xByte)) {
2931 return true;
2932 }
2933 } while (true);
2934 }
2935 case 2: {
2936 do {
2937 short witnessShort = getShortVolatile(o, offset);
2938 putShort(array, base, witnessShort); // put witness as binary
2939 Object witness = getFlatValue(array, base, layout, valueType); // get witness as object
2940 if (witness != expected) {
2941 return false;
2942 }
2943 short xShort = getShort(array, base + scale); // get x as binary
2944 if (compareAndSetShort(o, offset, witnessShort, xShort)) {
2945 return true;
2946 }
2947 } while (true);
2948 }
2949 case 4: {
2950 do {
2951 int witnessInt = getIntVolatile(o, offset);
2952 putInt(array, base, witnessInt); // put witness as binary
2953 Object witness = getFlatValue(array, base, layout, valueType); // get witness as object
2954 if (witness != expected) {
2955 return false;
2956 }
2957 int xInt = getInt(array, base + scale); // get x as binary
2958 if (compareAndSetInt(o, offset, witnessInt, xInt)) {
2959 return true;
2960 }
2961 } while (true);
2962 }
2963 case 8: {
2964 do {
2965 long witnessLong = getLongVolatile(o, offset);
2966 putLong(array, base, witnessLong); // put witness as binary
2967 Object witness = getFlatValue(array, base, layout, valueType);
2968 if (witness != expected) {
2969 return false;
2970 }
2971 long xLong = getLong(array, base + scale); // get x as binary
2972 if (compareAndSetLong(o, offset, witnessLong, xLong)) {
2973 return true;
2974 }
2975 } while (true);
2976 }
2977 default: {
2978 throw new UnsupportedOperationException();
2979 }
2980 }
2981 }
2982
2983 /**
2984 * Unblocks the given thread blocked on {@code park}, or, if it is
2985 * not blocked, causes the subsequent call to {@code park} not to
2986 * block. Note: this operation is "unsafe" solely because the
2987 * caller must somehow ensure that the thread has not been
2988 * destroyed. Nothing special is usually required to ensure this
2989 * when called from Java (in which there will ordinarily be a live
2990 * reference to the thread) but this is not nearly-automatically
2991 * so when calling from native code.
2992 *
2993 * @param thread the thread to unpark.
2994 */
2995 @IntrinsicCandidate
2996 public native void unpark(Object thread);
2997
2998 /**
2999 * Blocks current thread, returning when a balancing
3000 * {@code unpark} occurs, or a balancing {@code unpark} has
3001 * already occurred, or the thread is interrupted, or, if not
3002 * absolute and time is not zero, the given time nanoseconds have
3349 /**
3350 * Atomically exchanges the given reference value with the current
3351 * reference value of a field or array element within the given
3352 * object {@code o} at the given {@code offset}.
3353 *
3354 * @param o object/array to update the field/element in
3355 * @param offset field/element offset
3356 * @param newValue new value
3357 * @return the previous value
3358 * @since 1.8
3359 */
3360 @IntrinsicCandidate
3361 public final Object getAndSetReference(Object o, long offset, Object newValue) {
3362 Object v;
3363 do {
3364 v = getReferenceVolatile(o, offset);
3365 } while (!weakCompareAndSetReference(o, offset, v, newValue));
3366 return v;
3367 }
3368
3369 @ForceInline
3370 public final Object getAndSetReference(Object o, long offset, Class<?> valueType, Object newValue) {
3371 Object v;
3372 do {
3373 v = getReferenceVolatile(o, offset);
3374 } while (!compareAndSetReference(o, offset, valueType, v, newValue));
3375 return v;
3376 }
3377
3378 @ForceInline
3379 public Object getAndSetFlatValue(Object o, long offset, int layoutKind, Class<?> valueType, Object newValue) {
3380 Object v;
3381 do {
3382 v = getFlatValueVolatile(o, offset, layoutKind, valueType);
3383 } while (!compareAndSetFlatValue(o, offset, layoutKind, valueType, v, newValue));
3384 return v;
3385 }
3386
3387 @ForceInline
3388 public final Object getAndSetReferenceRelease(Object o, long offset, Object newValue) {
3389 Object v;
3390 do {
3391 v = getReference(o, offset);
3392 } while (!weakCompareAndSetReferenceRelease(o, offset, v, newValue));
3393 return v;
3394 }
3395
3396 @ForceInline
3397 public final Object getAndSetReferenceRelease(Object o, long offset, Class<?> valueType, Object newValue) {
3398 return getAndSetReference(o, offset, valueType, newValue);
3399 }
3400
3401 @ForceInline
3402 public Object getAndSetFlatValueRelease(Object o, long offset, int layoutKind, Class<?> valueType, Object x) {
3403 return getAndSetFlatValue(o, offset, layoutKind, valueType, x);
3404 }
3405
3406 @ForceInline
3407 public final Object getAndSetReferenceAcquire(Object o, long offset, Object newValue) {
3408 Object v;
3409 do {
3410 v = getReferenceAcquire(o, offset);
3411 } while (!weakCompareAndSetReferenceAcquire(o, offset, v, newValue));
3412 return v;
3413 }
3414
3415 @ForceInline
3416 public final Object getAndSetReferenceAcquire(Object o, long offset, Class<?> valueType, Object newValue) {
3417 return getAndSetReference(o, offset, valueType, newValue);
3418 }
3419
3420 @ForceInline
3421 public Object getAndSetFlatValueAcquire(Object o, long offset, int layoutKind, Class<?> valueType, Object x) {
3422 return getAndSetFlatValue(o, offset, layoutKind, valueType, x);
3423 }
3424
3425 @IntrinsicCandidate
3426 public final byte getAndSetByte(Object o, long offset, byte newValue) {
3427 byte v;
3428 do {
3429 v = getByteVolatile(o, offset);
3430 } while (!weakCompareAndSetByte(o, offset, v, newValue));
3431 return v;
3432 }
3433
3434 @ForceInline
3435 public final byte getAndSetByteRelease(Object o, long offset, byte newValue) {
3436 byte v;
3437 do {
3438 v = getByte(o, offset);
3439 } while (!weakCompareAndSetByteRelease(o, offset, v, newValue));
3440 return v;
3441 }
3442
3443 @ForceInline
3444 public final byte getAndSetByteAcquire(Object o, long offset, byte newValue) {
4460 private static short convEndian(boolean big, short n) { return big == BIG_ENDIAN ? n : Short.reverseBytes(n) ; }
4461 private static int convEndian(boolean big, int n) { return big == BIG_ENDIAN ? n : Integer.reverseBytes(n) ; }
4462 private static long convEndian(boolean big, long n) { return big == BIG_ENDIAN ? n : Long.reverseBytes(n) ; }
4463
4464
4465
4466 private native long allocateMemory0(long bytes);
4467 private native long reallocateMemory0(long address, long bytes);
4468 private native void freeMemory0(long address);
4469 @IntrinsicCandidate
4470 private native void setMemory0(Object o, long offset, long bytes, byte value);
4471 @IntrinsicCandidate
4472 private native void copyMemory0(Object srcBase, long srcOffset, Object destBase, long destOffset, long bytes);
4473 private native void copySwapMemory0(Object srcBase, long srcOffset, Object destBase, long destOffset, long bytes, long elemSize);
4474 private native long objectFieldOffset0(Field f); // throws IAE
4475 private native long knownObjectFieldOffset0(Class<?> c, String name); // error code: -1 not found, -2 static
4476 private native long staticFieldOffset0(Field f); // throws IAE
4477 private native Object staticFieldBase0(Field f); // throws IAE
4478 private native boolean shouldBeInitialized0(Class<?> c);
4479 private native void ensureClassInitialized0(Class<?> c);
4480 private native void notifyStrictStaticAccess0(Class<?> c, long staticFieldOffset, boolean writing);
4481 private native int arrayBaseOffset0(Class<?> arrayClass); // public version returns long to promote correct arithmetic
4482 @IntrinsicCandidate
4483 private native int arrayInstanceBaseOffset0(Object[] array);
4484 private native int arrayIndexScale0(Class<?> arrayClass);
4485 @IntrinsicCandidate
4486 private native int arrayInstanceIndexScale0(Object[] array);
4487 private native long getObjectSize0(Object o);
4488 private native int getLoadAverage0(double[] loadavg, int nelems);
4489 @IntrinsicCandidate
4490 private native int[] getFieldMap0(Class <?> c);
4491
4492
4493 /**
4494 * Invokes the given direct byte buffer's cleaner, if any.
4495 *
4496 * @param directBuffer a direct byte buffer
4497 * @throws NullPointerException if {@code directBuffer} is null
4498 * @throws IllegalArgumentException if {@code directBuffer} is non-direct,
4499 * or is a {@link java.nio.Buffer#slice slice}, or is a
4500 * {@link java.nio.Buffer#duplicate duplicate}
4501 */
4502 public void invokeCleaner(java.nio.ByteBuffer directBuffer) {
4503 if (!directBuffer.isDirect())
4504 throw new IllegalArgumentException("buffer is non-direct");
4505
4506 DirectBuffer db = (DirectBuffer) directBuffer;
4507 if (db.attachment() != null)
4508 throw new IllegalArgumentException("duplicate or slice");
4509
4510 Cleaner cleaner = db.cleaner();
|