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 jdk.internal.misc;
27
28 import jdk.internal.ref.Cleaner;
29 import jdk.internal.vm.annotation.ForceInline;
30 import jdk.internal.vm.annotation.IntrinsicCandidate;
31 import sun.nio.ch.DirectBuffer;
32
33 import java.lang.reflect.Field;
34 import java.security.ProtectionDomain;
35
36 import static jdk.internal.misc.UnsafeConstants.*;
37
38 /**
39 * A collection of methods for performing low-level, unsafe operations.
40 * Although the class and all methods are public, use of this class is
41 * limited because only trusted code can obtain instances of it.
42 *
43 * <em>Note:</em> It is the responsibility of the caller to make sure
44 * arguments are checked before methods of this class are
45 * called. While some rudimentary checks are performed on the input,
46 * the checks are best effort and when performance is an overriding
47 * priority, as when methods of this class are optimized by the
48 * runtime compiler, some or all checks (if any) may be elided. Hence,
165 * The first two parameters are interpreted exactly as with
166 * {@link #getInt(Object, long)} to refer to a specific
167 * Java variable (field or array element). The given value
168 * is stored into that variable.
169 * <p>
170 * The variable must be of the same type as the method
171 * parameter {@code x}.
172 *
173 * @param o Java heap object in which the variable resides, if any, else
174 * null
175 * @param offset indication of where the variable resides in a Java heap
176 * object, if any, else a memory address locating the variable
177 * statically
178 * @param x the value to store into the indicated Java variable
179 * @throws RuntimeException No defined exceptions are thrown, not even
180 * {@link NullPointerException}
181 */
182 @IntrinsicCandidate
183 public native void putInt(Object o, long offset, int x);
184
185 /**
186 * Fetches a reference value from a given Java variable.
187 * @see #getInt(Object, long)
188 */
189 @IntrinsicCandidate
190 public native Object getReference(Object o, long offset);
191
192 /**
193 * Stores a reference value into a given Java variable.
194 * <p>
195 * Unless the reference {@code x} being stored is either null
196 * or matches the field type, the results are undefined.
197 * If the reference {@code o} is non-null, card marks or
198 * other store barriers for that object (if the VM requires them)
199 * are updated.
200 * @see #putInt(Object, long, int)
201 */
202 @IntrinsicCandidate
203 public native void putReference(Object o, long offset, Object x);
204
205 /** @see #getInt(Object, long) */
206 @IntrinsicCandidate
207 public native boolean getBoolean(Object o, long offset);
208
209 /** @see #putInt(Object, long, int) */
210 @IntrinsicCandidate
211 public native void putBoolean(Object o, long offset, boolean x);
212
213 /** @see #getInt(Object, long) */
214 @IntrinsicCandidate
215 public native byte getByte(Object o, long offset);
216
217 /** @see #putInt(Object, long, int) */
218 @IntrinsicCandidate
219 public native void putByte(Object o, long offset, byte x);
220
221 /** @see #getInt(Object, long) */
222 @IntrinsicCandidate
223 public native short getShort(Object o, long offset);
224
1152 }
1153
1154 /**
1155 * Ensures the given class has been initialized (see JVMS-5.5 for details).
1156 * This is often needed in conjunction with obtaining the static field base
1157 * of a class.
1158 *
1159 * The call returns when either class {@code c} is fully initialized or
1160 * class {@code c} is being initialized and the call is performed from
1161 * the initializing thread. In the latter case a subsequent call to
1162 * {@link #shouldBeInitialized} will return {@code true}.
1163 */
1164 public void ensureClassInitialized(Class<?> c) {
1165 if (c == null) {
1166 throw new NullPointerException();
1167 }
1168
1169 ensureClassInitialized0(c);
1170 }
1171
1172 /**
1173 * Reports the offset of the first element in the storage allocation of a
1174 * given array class. If {@link #arrayIndexScale} returns a non-zero value
1175 * for the same class, you may use that scale factor, together with this
1176 * base offset, to form new offsets to access elements of arrays of the
1177 * given class.
1178 * <p>
1179 * The return value is in the range of a {@code int}. The return type is
1180 * {@code long} to emphasize that long arithmetic should always be used
1181 * for offset calculations to avoid overflows.
1182 *
1183 * @see #getInt(Object, long)
1184 * @see #putInt(Object, long, int)
1185 */
1186 public long arrayBaseOffset(Class<?> arrayClass) {
1187 if (arrayClass == null) {
1188 throw new NullPointerException();
1189 }
1190
1191 return arrayBaseOffset0(arrayClass);
1233 * allocation of a given array class. However, arrays of "narrow" types
1234 * will generally not work properly with accessors like {@link
1235 * #getByte(Object, long)}, so the scale factor for such classes is reported
1236 * as zero.
1237 * <p>
1238 * The computation of the actual memory offset should always use {@code
1239 * long} arithmetic to avoid overflows.
1240 *
1241 * @see #arrayBaseOffset
1242 * @see #getInt(Object, long)
1243 * @see #putInt(Object, long, int)
1244 */
1245 public int arrayIndexScale(Class<?> arrayClass) {
1246 if (arrayClass == null) {
1247 throw new NullPointerException();
1248 }
1249
1250 return arrayIndexScale0(arrayClass);
1251 }
1252
1253
1254 /** The value of {@code arrayIndexScale(boolean[].class)} */
1255 public static final int ARRAY_BOOLEAN_INDEX_SCALE
1256 = theUnsafe.arrayIndexScale(boolean[].class);
1257
1258 /** The value of {@code arrayIndexScale(byte[].class)} */
1259 public static final int ARRAY_BYTE_INDEX_SCALE
1260 = theUnsafe.arrayIndexScale(byte[].class);
1261
1262 /** The value of {@code arrayIndexScale(short[].class)} */
1263 public static final int ARRAY_SHORT_INDEX_SCALE
1264 = theUnsafe.arrayIndexScale(short[].class);
1265
1266 /** The value of {@code arrayIndexScale(char[].class)} */
1267 public static final int ARRAY_CHAR_INDEX_SCALE
1268 = theUnsafe.arrayIndexScale(char[].class);
1269
1270 /** The value of {@code arrayIndexScale(int[].class)} */
1271 public static final int ARRAY_INT_INDEX_SCALE
1272 = theUnsafe.arrayIndexScale(int[].class);
1411 return null;
1412 }
1413
1414 /** Throws the exception without telling the verifier. */
1415 public native void throwException(Throwable ee);
1416
1417 /**
1418 * Atomically updates Java variable to {@code x} if it is currently
1419 * holding {@code expected}.
1420 *
1421 * <p>This operation has memory semantics of a {@code volatile} read
1422 * and write. Corresponds to C11 atomic_compare_exchange_strong.
1423 *
1424 * @return {@code true} if successful
1425 */
1426 @IntrinsicCandidate
1427 public final native boolean compareAndSetReference(Object o, long offset,
1428 Object expected,
1429 Object x);
1430
1431 @IntrinsicCandidate
1432 public final native Object compareAndExchangeReference(Object o, long offset,
1433 Object expected,
1434 Object x);
1435
1436 @IntrinsicCandidate
1437 public final Object compareAndExchangeReferenceAcquire(Object o, long offset,
1438 Object expected,
1439 Object x) {
1440 return compareAndExchangeReference(o, offset, expected, x);
1441 }
1442
1443 @IntrinsicCandidate
1444 public final Object compareAndExchangeReferenceRelease(Object o, long offset,
1445 Object expected,
1446 Object x) {
1447 return compareAndExchangeReference(o, offset, expected, x);
1448 }
1449
1450 @IntrinsicCandidate
1451 public final boolean weakCompareAndSetReferencePlain(Object o, long offset,
1452 Object expected,
1453 Object x) {
1454 return compareAndSetReference(o, offset, expected, x);
1455 }
1456
1457 @IntrinsicCandidate
1458 public final boolean weakCompareAndSetReferenceAcquire(Object o, long offset,
1459 Object expected,
1460 Object x) {
1461 return compareAndSetReference(o, offset, expected, x);
1462 }
1463
1464 @IntrinsicCandidate
1465 public final boolean weakCompareAndSetReferenceRelease(Object o, long offset,
1466 Object expected,
1467 Object x) {
1468 return compareAndSetReference(o, offset, expected, x);
1469 }
1470
1471 @IntrinsicCandidate
1472 public final boolean weakCompareAndSetReference(Object o, long offset,
1473 Object expected,
1474 Object x) {
1475 return compareAndSetReference(o, offset, expected, x);
1476 }
1477
1478 /**
1479 * Atomically updates Java variable to {@code x} if it is currently
1480 * holding {@code expected}.
1481 *
1482 * <p>This operation has memory semantics of a {@code volatile} read
1483 * and write. Corresponds to C11 atomic_compare_exchange_strong.
1484 *
1485 * @return {@code true} if successful
1486 */
1487 @IntrinsicCandidate
1488 public final native boolean compareAndSetInt(Object o, long offset,
1489 int expected,
1490 int x);
1491
1492 @IntrinsicCandidate
1493 public final native int compareAndExchangeInt(Object o, long offset,
1494 int expected,
1495 int x);
1496
1497 @IntrinsicCandidate
2073 public final boolean weakCompareAndSetLongRelease(Object o, long offset,
2074 long expected,
2075 long x) {
2076 return compareAndSetLong(o, offset, expected, x);
2077 }
2078
2079 @IntrinsicCandidate
2080 public final boolean weakCompareAndSetLong(Object o, long offset,
2081 long expected,
2082 long x) {
2083 return compareAndSetLong(o, offset, expected, x);
2084 }
2085
2086 /**
2087 * Fetches a reference value from a given Java variable, with volatile
2088 * load semantics. Otherwise identical to {@link #getReference(Object, long)}
2089 */
2090 @IntrinsicCandidate
2091 public native Object getReferenceVolatile(Object o, long offset);
2092
2093 /**
2094 * Stores a reference value into a given Java variable, with
2095 * volatile store semantics. Otherwise identical to {@link #putReference(Object, long, Object)}
2096 */
2097 @IntrinsicCandidate
2098 public native void putReferenceVolatile(Object o, long offset, Object x);
2099
2100 /** Volatile version of {@link #getInt(Object, long)} */
2101 @IntrinsicCandidate
2102 public native int getIntVolatile(Object o, long offset);
2103
2104 /** Volatile version of {@link #putInt(Object, long, int)} */
2105 @IntrinsicCandidate
2106 public native void putIntVolatile(Object o, long offset, int x);
2107
2108 /** Volatile version of {@link #getBoolean(Object, long)} */
2109 @IntrinsicCandidate
2110 public native boolean getBooleanVolatile(Object o, long offset);
2111
2112 /** Volatile version of {@link #putBoolean(Object, long, boolean)} */
2113 @IntrinsicCandidate
2114 public native void putBooleanVolatile(Object o, long offset, boolean x);
2115
2116 /** Volatile version of {@link #getByte(Object, long)} */
2117 @IntrinsicCandidate
2118 public native byte getByteVolatile(Object o, long offset);
2119
2152 /** Volatile version of {@link #putFloat(Object, long, float)} */
2153 @IntrinsicCandidate
2154 public native void putFloatVolatile(Object o, long offset, float x);
2155
2156 /** Volatile version of {@link #getDouble(Object, long)} */
2157 @IntrinsicCandidate
2158 public native double getDoubleVolatile(Object o, long offset);
2159
2160 /** Volatile version of {@link #putDouble(Object, long, double)} */
2161 @IntrinsicCandidate
2162 public native void putDoubleVolatile(Object o, long offset, double x);
2163
2164
2165
2166 /** Acquire version of {@link #getReferenceVolatile(Object, long)} */
2167 @IntrinsicCandidate
2168 public final Object getReferenceAcquire(Object o, long offset) {
2169 return getReferenceVolatile(o, offset);
2170 }
2171
2172 /** Acquire version of {@link #getBooleanVolatile(Object, long)} */
2173 @IntrinsicCandidate
2174 public final boolean getBooleanAcquire(Object o, long offset) {
2175 return getBooleanVolatile(o, offset);
2176 }
2177
2178 /** Acquire version of {@link #getByteVolatile(Object, long)} */
2179 @IntrinsicCandidate
2180 public final byte getByteAcquire(Object o, long offset) {
2181 return getByteVolatile(o, offset);
2182 }
2183
2184 /** Acquire version of {@link #getShortVolatile(Object, long)} */
2185 @IntrinsicCandidate
2186 public final short getShortAcquire(Object o, long offset) {
2187 return getShortVolatile(o, offset);
2188 }
2189
2190 /** Acquire version of {@link #getCharVolatile(Object, long)} */
2191 @IntrinsicCandidate
2216 public final double getDoubleAcquire(Object o, long offset) {
2217 return getDoubleVolatile(o, offset);
2218 }
2219
2220 /*
2221 * Versions of {@link #putReferenceVolatile(Object, long, Object)}
2222 * that do not guarantee immediate visibility of the store to
2223 * other threads. This method is generally only useful if the
2224 * underlying field is a Java volatile (or if an array cell, one
2225 * that is otherwise only accessed using volatile accesses).
2226 *
2227 * Corresponds to C11 atomic_store_explicit(..., memory_order_release).
2228 */
2229
2230 /** Release version of {@link #putReferenceVolatile(Object, long, Object)} */
2231 @IntrinsicCandidate
2232 public final void putReferenceRelease(Object o, long offset, Object x) {
2233 putReferenceVolatile(o, offset, x);
2234 }
2235
2236 /** Release version of {@link #putBooleanVolatile(Object, long, boolean)} */
2237 @IntrinsicCandidate
2238 public final void putBooleanRelease(Object o, long offset, boolean x) {
2239 putBooleanVolatile(o, offset, x);
2240 }
2241
2242 /** Release version of {@link #putByteVolatile(Object, long, byte)} */
2243 @IntrinsicCandidate
2244 public final void putByteRelease(Object o, long offset, byte x) {
2245 putByteVolatile(o, offset, x);
2246 }
2247
2248 /** Release version of {@link #putShortVolatile(Object, long, short)} */
2249 @IntrinsicCandidate
2250 public final void putShortRelease(Object o, long offset, short x) {
2251 putShortVolatile(o, offset, x);
2252 }
2253
2254 /** Release version of {@link #putCharVolatile(Object, long, char)} */
2255 @IntrinsicCandidate
2272 /** Release version of {@link #putLongVolatile(Object, long, long)} */
2273 @IntrinsicCandidate
2274 public final void putLongRelease(Object o, long offset, long x) {
2275 putLongVolatile(o, offset, x);
2276 }
2277
2278 /** Release version of {@link #putDoubleVolatile(Object, long, double)} */
2279 @IntrinsicCandidate
2280 public final void putDoubleRelease(Object o, long offset, double x) {
2281 putDoubleVolatile(o, offset, x);
2282 }
2283
2284 // ------------------------------ Opaque --------------------------------------
2285
2286 /** Opaque version of {@link #getReferenceVolatile(Object, long)} */
2287 @IntrinsicCandidate
2288 public final Object getReferenceOpaque(Object o, long offset) {
2289 return getReferenceVolatile(o, offset);
2290 }
2291
2292 /** Opaque version of {@link #getBooleanVolatile(Object, long)} */
2293 @IntrinsicCandidate
2294 public final boolean getBooleanOpaque(Object o, long offset) {
2295 return getBooleanVolatile(o, offset);
2296 }
2297
2298 /** Opaque version of {@link #getByteVolatile(Object, long)} */
2299 @IntrinsicCandidate
2300 public final byte getByteOpaque(Object o, long offset) {
2301 return getByteVolatile(o, offset);
2302 }
2303
2304 /** Opaque version of {@link #getShortVolatile(Object, long)} */
2305 @IntrinsicCandidate
2306 public final short getShortOpaque(Object o, long offset) {
2307 return getShortVolatile(o, offset);
2308 }
2309
2310 /** Opaque version of {@link #getCharVolatile(Object, long)} */
2311 @IntrinsicCandidate
2326 }
2327
2328 /** Opaque version of {@link #getLongVolatile(Object, long)} */
2329 @IntrinsicCandidate
2330 public final long getLongOpaque(Object o, long offset) {
2331 return getLongVolatile(o, offset);
2332 }
2333
2334 /** Opaque version of {@link #getDoubleVolatile(Object, long)} */
2335 @IntrinsicCandidate
2336 public final double getDoubleOpaque(Object o, long offset) {
2337 return getDoubleVolatile(o, offset);
2338 }
2339
2340 /** Opaque version of {@link #putReferenceVolatile(Object, long, Object)} */
2341 @IntrinsicCandidate
2342 public final void putReferenceOpaque(Object o, long offset, Object x) {
2343 putReferenceVolatile(o, offset, x);
2344 }
2345
2346 /** Opaque version of {@link #putBooleanVolatile(Object, long, boolean)} */
2347 @IntrinsicCandidate
2348 public final void putBooleanOpaque(Object o, long offset, boolean x) {
2349 putBooleanVolatile(o, offset, x);
2350 }
2351
2352 /** Opaque version of {@link #putByteVolatile(Object, long, byte)} */
2353 @IntrinsicCandidate
2354 public final void putByteOpaque(Object o, long offset, byte x) {
2355 putByteVolatile(o, offset, x);
2356 }
2357
2358 /** Opaque version of {@link #putShortVolatile(Object, long, short)} */
2359 @IntrinsicCandidate
2360 public final void putShortOpaque(Object o, long offset, short x) {
2361 putShortVolatile(o, offset, x);
2362 }
2363
2364 /** Opaque version of {@link #putCharVolatile(Object, long, char)} */
2365 @IntrinsicCandidate
2374 }
2375
2376 /** Opaque version of {@link #putFloatVolatile(Object, long, float)} */
2377 @IntrinsicCandidate
2378 public final void putFloatOpaque(Object o, long offset, float x) {
2379 putFloatVolatile(o, offset, x);
2380 }
2381
2382 /** Opaque version of {@link #putLongVolatile(Object, long, long)} */
2383 @IntrinsicCandidate
2384 public final void putLongOpaque(Object o, long offset, long x) {
2385 putLongVolatile(o, offset, x);
2386 }
2387
2388 /** Opaque version of {@link #putDoubleVolatile(Object, long, double)} */
2389 @IntrinsicCandidate
2390 public final void putDoubleOpaque(Object o, long offset, double x) {
2391 putDoubleVolatile(o, offset, x);
2392 }
2393
2394 /**
2395 * Unblocks the given thread blocked on {@code park}, or, if it is
2396 * not blocked, causes the subsequent call to {@code park} not to
2397 * block. Note: this operation is "unsafe" solely because the
2398 * caller must somehow ensure that the thread has not been
2399 * destroyed. Nothing special is usually required to ensure this
2400 * when called from Java (in which there will ordinarily be a live
2401 * reference to the thread) but this is not nearly-automatically
2402 * so when calling from native code.
2403 *
2404 * @param thread the thread to unpark.
2405 */
2406 @IntrinsicCandidate
2407 public native void unpark(Object thread);
2408
2409 /**
2410 * Blocks current thread, returning when a balancing
2411 * {@code unpark} occurs, or a balancing {@code unpark} has
2412 * already occurred, or the thread is interrupted, or, if not
2413 * absolute and time is not zero, the given time nanoseconds have
2760 /**
2761 * Atomically exchanges the given reference value with the current
2762 * reference value of a field or array element within the given
2763 * object {@code o} at the given {@code offset}.
2764 *
2765 * @param o object/array to update the field/element in
2766 * @param offset field/element offset
2767 * @param newValue new value
2768 * @return the previous value
2769 * @since 1.8
2770 */
2771 @IntrinsicCandidate
2772 public final Object getAndSetReference(Object o, long offset, Object newValue) {
2773 Object v;
2774 do {
2775 v = getReferenceVolatile(o, offset);
2776 } while (!weakCompareAndSetReference(o, offset, v, newValue));
2777 return v;
2778 }
2779
2780 @ForceInline
2781 public final Object getAndSetReferenceRelease(Object o, long offset, Object newValue) {
2782 Object v;
2783 do {
2784 v = getReference(o, offset);
2785 } while (!weakCompareAndSetReferenceRelease(o, offset, v, newValue));
2786 return v;
2787 }
2788
2789 @ForceInline
2790 public final Object getAndSetReferenceAcquire(Object o, long offset, Object newValue) {
2791 Object v;
2792 do {
2793 v = getReferenceAcquire(o, offset);
2794 } while (!weakCompareAndSetReferenceAcquire(o, offset, v, newValue));
2795 return v;
2796 }
2797
2798 @IntrinsicCandidate
2799 public final byte getAndSetByte(Object o, long offset, byte newValue) {
2800 byte v;
2801 do {
2802 v = getByteVolatile(o, offset);
2803 } while (!weakCompareAndSetByte(o, offset, v, newValue));
2804 return v;
2805 }
2806
2807 @ForceInline
2808 public final byte getAndSetByteRelease(Object o, long offset, byte newValue) {
2809 byte v;
2810 do {
2811 v = getByte(o, offset);
2812 } while (!weakCompareAndSetByteRelease(o, offset, v, newValue));
2813 return v;
2814 }
2815
2816 @ForceInline
2817 public final byte getAndSetByteAcquire(Object o, long offset, byte newValue) {
3833 private static short convEndian(boolean big, short n) { return big == BIG_ENDIAN ? n : Short.reverseBytes(n) ; }
3834 private static int convEndian(boolean big, int n) { return big == BIG_ENDIAN ? n : Integer.reverseBytes(n) ; }
3835 private static long convEndian(boolean big, long n) { return big == BIG_ENDIAN ? n : Long.reverseBytes(n) ; }
3836
3837
3838
3839 private native long allocateMemory0(long bytes);
3840 private native long reallocateMemory0(long address, long bytes);
3841 private native void freeMemory0(long address);
3842 @IntrinsicCandidate
3843 private native void setMemory0(Object o, long offset, long bytes, byte value);
3844 @IntrinsicCandidate
3845 private native void copyMemory0(Object srcBase, long srcOffset, Object destBase, long destOffset, long bytes);
3846 private native void copySwapMemory0(Object srcBase, long srcOffset, Object destBase, long destOffset, long bytes, long elemSize);
3847 private native long objectFieldOffset0(Field f);
3848 private native long objectFieldOffset1(Class<?> c, String name);
3849 private native long staticFieldOffset0(Field f);
3850 private native Object staticFieldBase0(Field f);
3851 private native boolean shouldBeInitialized0(Class<?> c);
3852 private native void ensureClassInitialized0(Class<?> c);
3853 private native int arrayBaseOffset0(Class<?> arrayClass); // public version returns long to promote correct arithmetic
3854 private native int arrayIndexScale0(Class<?> arrayClass);
3855 private native int getLoadAverage0(double[] loadavg, int nelems);
3856
3857
3858 /**
3859 * Invokes the given direct byte buffer's cleaner, if any.
3860 *
3861 * @param directBuffer a direct byte buffer
3862 * @throws NullPointerException if {@code directBuffer} is null
3863 * @throws IllegalArgumentException if {@code directBuffer} is non-direct,
3864 * or is a {@link java.nio.Buffer#slice slice}, or is a
3865 * {@link java.nio.Buffer#duplicate duplicate}
3866 */
3867 public void invokeCleaner(java.nio.ByteBuffer directBuffer) {
3868 if (!directBuffer.isDirect())
3869 throw new IllegalArgumentException("buffer is non-direct");
3870
3871 DirectBuffer db = (DirectBuffer) directBuffer;
3872 if (db.attachment() != null)
3873 throw new IllegalArgumentException("duplicate or slice");
3874
|
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 jdk.internal.misc;
27
28 import jdk.internal.ref.Cleaner;
29 import jdk.internal.value.ValueClass;
30 import jdk.internal.vm.annotation.ForceInline;
31 import jdk.internal.vm.annotation.IntrinsicCandidate;
32 import sun.nio.ch.DirectBuffer;
33
34 import java.lang.reflect.Field;
35 import java.security.ProtectionDomain;
36
37 import static jdk.internal.misc.UnsafeConstants.*;
38
39 /**
40 * A collection of methods for performing low-level, unsafe operations.
41 * Although the class and all methods are public, use of this class is
42 * limited because only trusted code can obtain instances of it.
43 *
44 * <em>Note:</em> It is the responsibility of the caller to make sure
45 * arguments are checked before methods of this class are
46 * called. While some rudimentary checks are performed on the input,
47 * the checks are best effort and when performance is an overriding
48 * priority, as when methods of this class are optimized by the
49 * runtime compiler, some or all checks (if any) may be elided. Hence,
166 * The first two parameters are interpreted exactly as with
167 * {@link #getInt(Object, long)} to refer to a specific
168 * Java variable (field or array element). The given value
169 * is stored into that variable.
170 * <p>
171 * The variable must be of the same type as the method
172 * parameter {@code x}.
173 *
174 * @param o Java heap object in which the variable resides, if any, else
175 * null
176 * @param offset indication of where the variable resides in a Java heap
177 * object, if any, else a memory address locating the variable
178 * statically
179 * @param x the value to store into the indicated Java variable
180 * @throws RuntimeException No defined exceptions are thrown, not even
181 * {@link NullPointerException}
182 */
183 @IntrinsicCandidate
184 public native void putInt(Object o, long offset, int x);
185
186
187 /**
188 * Returns true if the given field is flattened.
189 */
190 public boolean isFlatField(Field f) {
191 if (f == null) {
192 throw new NullPointerException();
193 }
194 return isFlatField0(f);
195 }
196
197 private native boolean isFlatField0(Object o);
198
199 /* Returns true if the given field has a null marker
200 * <p>
201 * Nullable flat fields are stored in a flattened representation
202 * and have an associated null marker to indicate if the the field value is
203 * null or the one stored with the flat representation
204 */
205
206 public boolean hasNullMarker(Field f) {
207 if (f == null) {
208 throw new NullPointerException();
209 }
210 return hasNullMarker0(f);
211 }
212
213 private native boolean hasNullMarker0(Object o);
214
215 /* Returns the offset of the null marker of the field,
216 * or -1 if the field doesn't have a null marker
217 */
218
219 public int nullMarkerOffset(Field f) {
220 if (f == null) {
221 throw new NullPointerException();
222 }
223 return nullMarkerOffset0(f);
224 }
225
226 private native int nullMarkerOffset0(Object o);
227
228 public static final int NON_FLAT_LAYOUT = 0;
229
230 /* Reports the kind of layout used for an element in the storage
231 * allocation of the given array. Do not expect to perform any logic
232 * or layout control with this value, it is just an opaque token
233 * used for performance reasons.
234 *
235 * A layout of 0 indicates this array is not flat.
236 */
237 public int arrayLayout(Class<?> arrayClass) {
238 if (arrayClass == null) {
239 throw new NullPointerException();
240 }
241 return arrayLayout0(arrayClass);
242 }
243
244 private native int arrayLayout0(Object o);
245
246
247 /* Reports the kind of layout used for a given field in the storage
248 * allocation of its class. Do not expect to perform any logic
249 * or layout control with this value, it is just an opaque token
250 * used for performance reasons.
251 *
252 * A layout of 0 indicates this field is not flat.
253 */
254 public int fieldLayout(Field f) {
255 if (f == null) {
256 throw new NullPointerException();
257 }
258 return fieldLayout0(f);
259 }
260
261 private native int fieldLayout0(Object o);
262
263 public native Object[] newSpecialArray(Class<?> componentType,
264 int length, int layoutKind);
265
266 /**
267 * Returns true if the given class is a flattened array.
268 */
269 @IntrinsicCandidate
270 public native boolean isFlatArray(Class<?> arrayClass);
271
272 /**
273 * Fetches a reference value from a given Java variable.
274 * This method can return a reference to either an object or value
275 * or a null reference.
276 *
277 * @see #getInt(Object, long)
278 */
279 @IntrinsicCandidate
280 public native Object getReference(Object o, long offset);
281
282 /**
283 * Stores a reference value into a given Java variable.
284 * This method can store a reference to either an object or value
285 * or a null reference.
286 * <p>
287 * Unless the reference {@code x} being stored is either null
288 * or matches the field type, the results are undefined.
289 * If the reference {@code o} is non-null, card marks or
290 * other store barriers for that object (if the VM requires them)
291 * are updated.
292 * @see #putInt(Object, long, int)
293 */
294 @IntrinsicCandidate
295 public native void putReference(Object o, long offset, Object x);
296
297 /**
298 * Fetches a value of type {@code <V>} from a given Java variable.
299 * More specifically, fetches a field or array element within the given
300 * {@code o} object at the given offset, or (if {@code o} is null)
301 * from the memory address whose numerical value is the given offset.
302 *
303 * @param o Java heap object in which the variable resides, if any, else
304 * null
305 * @param offset indication of where the variable resides in a Java heap
306 * object, if any, else a memory address locating the variable
307 * statically
308 * @param valueType value type
309 * @param <V> the type of a value
310 * @return the value fetched from the indicated Java variable
311 * @throws RuntimeException No defined exceptions are thrown, not even
312 * {@link NullPointerException}
313 */
314 @IntrinsicCandidate
315 public native <V> V getValue(Object o, long offset, Class<?> valueType);
316
317 /**
318 * Fetches a value of type {@code <V>} from a given Java variable.
319 * More specifically, fetches a field or array element within the given
320 * {@code o} object at the given offset, or (if {@code o} is null)
321 * from the memory address whose numerical value is the given offset.
322 *
323 * @param o Java heap object in which the variable resides, if any, else
324 * null
325 * @param offset indication of where the variable resides in a Java heap
326 * object, if any, else a memory address locating the variable
327 * statically
328 * @param layoutKind opaque value used by the VM to know the layout
329 * the field or array element. This value must be retrieved with
330 * {@link #fieldLayout} or {@link #arrayLayout}.
331 * @param valueType value type
332 * @param <V> the type of a value
333 * @return the value fetched from the indicated Java variable
334 * @throws RuntimeException No defined exceptions are thrown, not even
335 * {@link NullPointerException}
336 */
337 @IntrinsicCandidate
338 public native <V> V getFlatValue(Object o, long offset, int layoutKind, Class<?> valueType);
339
340
341 /**
342 * Stores the given value into a given Java variable.
343 *
344 * Unless the reference {@code o} being stored is either null
345 * or matches the field type, the results are undefined.
346 *
347 * @param o Java heap object in which the variable resides, if any, else
348 * null
349 * @param offset indication of where the variable resides in a Java heap
350 * object, if any, else a memory address locating the variable
351 * statically
352 * @param valueType value type
353 * @param v the value to store into the indicated Java variable
354 * @param <V> the type of a value
355 * @throws RuntimeException No defined exceptions are thrown, not even
356 * {@link NullPointerException}
357 */
358 @IntrinsicCandidate
359 public native <V> void putValue(Object o, long offset, Class<?> valueType, V v);
360
361 /**
362 * Stores the given value into a given Java variable.
363 *
364 * Unless the reference {@code o} being stored is either null
365 * or matches the field type, the results are undefined.
366 *
367 * @param o Java heap object in which the variable resides, if any, else
368 * null
369 * @param offset indication of where the variable resides in a Java heap
370 * object, if any, else a memory address locating the variable
371 * statically
372 * @param layoutKind opaque value used by the VM to know the layout
373 * the field or array element. This value must be retrieved with
374 * {@link #fieldLayout} or {@link #arrayLayout}.
375 * @param valueType value type
376 * @param v the value to store into the indicated Java variable
377 * @param <V> the type of a value
378 * @throws RuntimeException No defined exceptions are thrown, not even
379 * {@link NullPointerException}
380 */
381 @IntrinsicCandidate
382 public native <V> void putFlatValue(Object o, long offset, int layoutKind, Class<?> valueType, V v);
383
384 /**
385 * Returns an object instance with a private buffered value whose layout
386 * and contents is exactly the given value instance. The return object
387 * is in the larval state that can be updated using the unsafe put operation.
388 *
389 * @param value a value instance
390 * @param <V> the type of the given value instance
391 */
392 @IntrinsicCandidate
393 public native <V> V makePrivateBuffer(V value);
394
395 /**
396 * Exits the larval state and returns a value instance.
397 *
398 * @param value a value instance
399 * @param <V> the type of the given value instance
400 */
401 @IntrinsicCandidate
402 public native <V> V finishPrivateBuffer(V value);
403
404 /**
405 * Returns the header size of the given value type.
406 *
407 * @param valueType value type
408 * @return the header size of the value type
409 */
410 public native <V> long valueHeaderSize(Class<V> valueType);
411
412 /** @see #getInt(Object, long) */
413 @IntrinsicCandidate
414 public native boolean getBoolean(Object o, long offset);
415
416 /** @see #putInt(Object, long, int) */
417 @IntrinsicCandidate
418 public native void putBoolean(Object o, long offset, boolean x);
419
420 /** @see #getInt(Object, long) */
421 @IntrinsicCandidate
422 public native byte getByte(Object o, long offset);
423
424 /** @see #putInt(Object, long, int) */
425 @IntrinsicCandidate
426 public native void putByte(Object o, long offset, byte x);
427
428 /** @see #getInt(Object, long) */
429 @IntrinsicCandidate
430 public native short getShort(Object o, long offset);
431
1359 }
1360
1361 /**
1362 * Ensures the given class has been initialized (see JVMS-5.5 for details).
1363 * This is often needed in conjunction with obtaining the static field base
1364 * of a class.
1365 *
1366 * The call returns when either class {@code c} is fully initialized or
1367 * class {@code c} is being initialized and the call is performed from
1368 * the initializing thread. In the latter case a subsequent call to
1369 * {@link #shouldBeInitialized} will return {@code true}.
1370 */
1371 public void ensureClassInitialized(Class<?> c) {
1372 if (c == null) {
1373 throw new NullPointerException();
1374 }
1375
1376 ensureClassInitialized0(c);
1377 }
1378
1379 /**
1380 * The reading or writing of strict static fields may require
1381 * special processing. Notify the VM that such an event is about
1382 * to happen. The VM may respond by throwing an exception, in the
1383 * case of a read of an uninitialized field. If the VM allows the
1384 * method to return normally, no further calls are needed, with
1385 * the same arguments.
1386 */
1387 public void notifyStrictStaticAccess(Class<?> c, long staticFieldOffset, boolean writing) {
1388 if (c == null) {
1389 throw new NullPointerException();
1390 }
1391 notifyStrictStaticAccess0(c, staticFieldOffset, writing);
1392 }
1393
1394 /**
1395 * Reports the offset of the first element in the storage allocation of a
1396 * given array class. If {@link #arrayIndexScale} returns a non-zero value
1397 * for the same class, you may use that scale factor, together with this
1398 * base offset, to form new offsets to access elements of arrays of the
1399 * given class.
1400 * <p>
1401 * The return value is in the range of a {@code int}. The return type is
1402 * {@code long} to emphasize that long arithmetic should always be used
1403 * for offset calculations to avoid overflows.
1404 *
1405 * @see #getInt(Object, long)
1406 * @see #putInt(Object, long, int)
1407 */
1408 public long arrayBaseOffset(Class<?> arrayClass) {
1409 if (arrayClass == null) {
1410 throw new NullPointerException();
1411 }
1412
1413 return arrayBaseOffset0(arrayClass);
1455 * allocation of a given array class. However, arrays of "narrow" types
1456 * will generally not work properly with accessors like {@link
1457 * #getByte(Object, long)}, so the scale factor for such classes is reported
1458 * as zero.
1459 * <p>
1460 * The computation of the actual memory offset should always use {@code
1461 * long} arithmetic to avoid overflows.
1462 *
1463 * @see #arrayBaseOffset
1464 * @see #getInt(Object, long)
1465 * @see #putInt(Object, long, int)
1466 */
1467 public int arrayIndexScale(Class<?> arrayClass) {
1468 if (arrayClass == null) {
1469 throw new NullPointerException();
1470 }
1471
1472 return arrayIndexScale0(arrayClass);
1473 }
1474
1475 /**
1476 * Return the size of the object in the heap.
1477 * @param o an object
1478 * @return the objects's size
1479 * @since Valhalla
1480 */
1481 public long getObjectSize(Object o) {
1482 if (o == null)
1483 throw new NullPointerException();
1484 return getObjectSize0(o);
1485 }
1486
1487 /** The value of {@code arrayIndexScale(boolean[].class)} */
1488 public static final int ARRAY_BOOLEAN_INDEX_SCALE
1489 = theUnsafe.arrayIndexScale(boolean[].class);
1490
1491 /** The value of {@code arrayIndexScale(byte[].class)} */
1492 public static final int ARRAY_BYTE_INDEX_SCALE
1493 = theUnsafe.arrayIndexScale(byte[].class);
1494
1495 /** The value of {@code arrayIndexScale(short[].class)} */
1496 public static final int ARRAY_SHORT_INDEX_SCALE
1497 = theUnsafe.arrayIndexScale(short[].class);
1498
1499 /** The value of {@code arrayIndexScale(char[].class)} */
1500 public static final int ARRAY_CHAR_INDEX_SCALE
1501 = theUnsafe.arrayIndexScale(char[].class);
1502
1503 /** The value of {@code arrayIndexScale(int[].class)} */
1504 public static final int ARRAY_INT_INDEX_SCALE
1505 = theUnsafe.arrayIndexScale(int[].class);
1644 return null;
1645 }
1646
1647 /** Throws the exception without telling the verifier. */
1648 public native void throwException(Throwable ee);
1649
1650 /**
1651 * Atomically updates Java variable to {@code x} if it is currently
1652 * holding {@code expected}.
1653 *
1654 * <p>This operation has memory semantics of a {@code volatile} read
1655 * and write. Corresponds to C11 atomic_compare_exchange_strong.
1656 *
1657 * @return {@code true} if successful
1658 */
1659 @IntrinsicCandidate
1660 public final native boolean compareAndSetReference(Object o, long offset,
1661 Object expected,
1662 Object x);
1663
1664 private final boolean isValueObject(Object o) {
1665 return o != null && o.getClass().isValue();
1666 }
1667
1668 /*
1669 * For value type, CAS should do substitutability test as opposed
1670 * to two pointers comparison.
1671 */
1672 @ForceInline
1673 public final <V> boolean compareAndSetReference(Object o, long offset,
1674 Class<?> type,
1675 V expected,
1676 V x) {
1677 if (type.isValue() || isValueObject(expected)) {
1678 while (true) {
1679 Object witness = getReferenceVolatile(o, offset);
1680 if (witness != expected) {
1681 return false;
1682 }
1683 if (compareAndSetReference(o, offset, witness, x)) {
1684 return true;
1685 }
1686 }
1687 } else {
1688 return compareAndSetReference(o, offset, expected, x);
1689 }
1690 }
1691
1692 @ForceInline
1693 public final <V> boolean compareAndSetFlatValue(Object o, long offset,
1694 int layout,
1695 Class<?> valueType,
1696 V expected,
1697 V x) {
1698 while (true) {
1699 Object witness = getFlatValueVolatile(o, offset, layout, valueType);
1700 if (witness != expected) {
1701 return false;
1702 }
1703 if (compareAndSetFlatValueAsBytes(o, offset, layout, valueType, witness, x)) {
1704 return true;
1705 }
1706 }
1707 }
1708
1709 @IntrinsicCandidate
1710 public final native Object compareAndExchangeReference(Object o, long offset,
1711 Object expected,
1712 Object x);
1713
1714 @ForceInline
1715 public final <V> Object compareAndExchangeReference(Object o, long offset,
1716 Class<?> valueType,
1717 V expected,
1718 V x) {
1719 if (valueType.isValue() || isValueObject(expected)) {
1720 while (true) {
1721 Object witness = getReferenceVolatile(o, offset);
1722 if (witness != expected) {
1723 return witness;
1724 }
1725 if (compareAndSetReference(o, offset, witness, x)) {
1726 return witness;
1727 }
1728 }
1729 } else {
1730 return compareAndExchangeReference(o, offset, expected, x);
1731 }
1732 }
1733
1734 @ForceInline
1735 public final <V> Object compareAndExchangeFlatValue(Object o, long offset,
1736 int layout,
1737 Class<?> valueType,
1738 V expected,
1739 V x) {
1740 while (true) {
1741 Object witness = getFlatValueVolatile(o, offset, layout, valueType);
1742 if (witness != expected) {
1743 return witness;
1744 }
1745 if (compareAndSetFlatValueAsBytes(o, offset, layout, valueType, witness, x)) {
1746 return witness;
1747 }
1748 }
1749 }
1750
1751 @IntrinsicCandidate
1752 public final Object compareAndExchangeReferenceAcquire(Object o, long offset,
1753 Object expected,
1754 Object x) {
1755 return compareAndExchangeReference(o, offset, expected, x);
1756 }
1757
1758 public final <V> Object compareAndExchangeReferenceAcquire(Object o, long offset,
1759 Class<?> valueType,
1760 V expected,
1761 V x) {
1762 return compareAndExchangeReference(o, offset, valueType, expected, x);
1763 }
1764
1765 @ForceInline
1766 public final <V> Object compareAndExchangeFlatValueAcquire(Object o, long offset,
1767 int layout,
1768 Class<?> valueType,
1769 V expected,
1770 V x) {
1771 return compareAndExchangeFlatValue(o, offset, layout, valueType, expected, x);
1772 }
1773
1774 @IntrinsicCandidate
1775 public final Object compareAndExchangeReferenceRelease(Object o, long offset,
1776 Object expected,
1777 Object x) {
1778 return compareAndExchangeReference(o, offset, expected, x);
1779 }
1780
1781 public final <V> Object compareAndExchangeReferenceRelease(Object o, long offset,
1782 Class<?> valueType,
1783 V expected,
1784 V x) {
1785 return compareAndExchangeReference(o, offset, valueType, expected, x);
1786 }
1787
1788 @ForceInline
1789 public final <V> Object compareAndExchangeFlatValueRelease(Object o, long offset,
1790 int layout,
1791 Class<?> valueType,
1792 V expected,
1793 V x) {
1794 return compareAndExchangeFlatValue(o, offset, layout, valueType, expected, x);
1795 }
1796
1797 @IntrinsicCandidate
1798 public final boolean weakCompareAndSetReferencePlain(Object o, long offset,
1799 Object expected,
1800 Object x) {
1801 return compareAndSetReference(o, offset, expected, x);
1802 }
1803
1804 public final <V> boolean weakCompareAndSetReferencePlain(Object o, long offset,
1805 Class<?> valueType,
1806 V expected,
1807 V x) {
1808 if (valueType.isValue() || isValueObject(expected)) {
1809 return compareAndSetReference(o, offset, valueType, expected, x);
1810 } else {
1811 return weakCompareAndSetReferencePlain(o, offset, expected, x);
1812 }
1813 }
1814
1815 @ForceInline
1816 public final <V> boolean weakCompareAndSetFlatValuePlain(Object o, long offset,
1817 int layout,
1818 Class<?> valueType,
1819 V expected,
1820 V x) {
1821 return compareAndSetFlatValue(o, offset, layout, valueType, expected, x);
1822 }
1823
1824 @IntrinsicCandidate
1825 public final boolean weakCompareAndSetReferenceAcquire(Object o, long offset,
1826 Object expected,
1827 Object x) {
1828 return compareAndSetReference(o, offset, expected, x);
1829 }
1830
1831 public final <V> boolean weakCompareAndSetReferenceAcquire(Object o, long offset,
1832 Class<?> valueType,
1833 V expected,
1834 V x) {
1835 if (valueType.isValue() || isValueObject(expected)) {
1836 return compareAndSetReference(o, offset, valueType, expected, x);
1837 } else {
1838 return weakCompareAndSetReferencePlain(o, offset, expected, x);
1839 }
1840 }
1841
1842 @ForceInline
1843 public final <V> boolean weakCompareAndSetFlatValueAcquire(Object o, long offset,
1844 int layout,
1845 Class<?> valueType,
1846 V expected,
1847 V x) {
1848 return compareAndSetFlatValue(o, offset, layout, valueType, expected, x);
1849 }
1850
1851 @IntrinsicCandidate
1852 public final boolean weakCompareAndSetReferenceRelease(Object o, long offset,
1853 Object expected,
1854 Object x) {
1855 return compareAndSetReference(o, offset, expected, x);
1856 }
1857
1858 public final <V> boolean weakCompareAndSetReferenceRelease(Object o, long offset,
1859 Class<?> valueType,
1860 V expected,
1861 V x) {
1862 if (valueType.isValue() || isValueObject(expected)) {
1863 return compareAndSetReference(o, offset, valueType, expected, x);
1864 } else {
1865 return weakCompareAndSetReferencePlain(o, offset, expected, x);
1866 }
1867 }
1868
1869 @ForceInline
1870 public final <V> boolean weakCompareAndSetFlatValueRelease(Object o, long offset,
1871 int layout,
1872 Class<?> valueType,
1873 V expected,
1874 V x) {
1875 return compareAndSetFlatValue(o, offset, layout, valueType, expected, x);
1876 }
1877
1878 @IntrinsicCandidate
1879 public final boolean weakCompareAndSetReference(Object o, long offset,
1880 Object expected,
1881 Object x) {
1882 return compareAndSetReference(o, offset, expected, x);
1883 }
1884
1885 public final <V> boolean weakCompareAndSetReference(Object o, long offset,
1886 Class<?> valueType,
1887 V expected,
1888 V x) {
1889 if (valueType.isValue() || isValueObject(expected)) {
1890 return compareAndSetReference(o, offset, valueType, expected, x);
1891 } else {
1892 return weakCompareAndSetReferencePlain(o, offset, expected, x);
1893 }
1894 }
1895
1896 @ForceInline
1897 public final <V> boolean weakCompareAndSetFlatValue(Object o, long offset,
1898 int layout,
1899 Class<?> valueType,
1900 V expected,
1901 V x) {
1902 return compareAndSetFlatValue(o, offset, layout, valueType, expected, x);
1903 }
1904
1905 /**
1906 * Atomically updates Java variable to {@code x} if it is currently
1907 * holding {@code expected}.
1908 *
1909 * <p>This operation has memory semantics of a {@code volatile} read
1910 * and write. Corresponds to C11 atomic_compare_exchange_strong.
1911 *
1912 * @return {@code true} if successful
1913 */
1914 @IntrinsicCandidate
1915 public final native boolean compareAndSetInt(Object o, long offset,
1916 int expected,
1917 int x);
1918
1919 @IntrinsicCandidate
1920 public final native int compareAndExchangeInt(Object o, long offset,
1921 int expected,
1922 int x);
1923
1924 @IntrinsicCandidate
2500 public final boolean weakCompareAndSetLongRelease(Object o, long offset,
2501 long expected,
2502 long x) {
2503 return compareAndSetLong(o, offset, expected, x);
2504 }
2505
2506 @IntrinsicCandidate
2507 public final boolean weakCompareAndSetLong(Object o, long offset,
2508 long expected,
2509 long x) {
2510 return compareAndSetLong(o, offset, expected, x);
2511 }
2512
2513 /**
2514 * Fetches a reference value from a given Java variable, with volatile
2515 * load semantics. Otherwise identical to {@link #getReference(Object, long)}
2516 */
2517 @IntrinsicCandidate
2518 public native Object getReferenceVolatile(Object o, long offset);
2519
2520 @ForceInline
2521 public final <V> Object getFlatValueVolatile(Object o, long offset, int layout, Class<?> valueType) {
2522 // we translate using fences (see: https://gee.cs.oswego.edu/dl/html/j9mm.html)
2523 Object res = getFlatValue(o, offset, layout, valueType);
2524 fullFence();
2525 return res;
2526 }
2527
2528 /**
2529 * Stores a reference value into a given Java variable, with
2530 * volatile store semantics. Otherwise identical to {@link #putReference(Object, long, Object)}
2531 */
2532 @IntrinsicCandidate
2533 public native void putReferenceVolatile(Object o, long offset, Object x);
2534
2535 @ForceInline
2536 public final <V> void putFlatValueVolatile(Object o, long offset, int layout, Class<?> valueType, V x) {
2537 // we translate using fences (see: https://gee.cs.oswego.edu/dl/html/j9mm.html)
2538 putFlatValueRelease(o, offset, layout, valueType, x);
2539 fullFence();
2540 }
2541
2542 /** Volatile version of {@link #getInt(Object, long)} */
2543 @IntrinsicCandidate
2544 public native int getIntVolatile(Object o, long offset);
2545
2546 /** Volatile version of {@link #putInt(Object, long, int)} */
2547 @IntrinsicCandidate
2548 public native void putIntVolatile(Object o, long offset, int x);
2549
2550 /** Volatile version of {@link #getBoolean(Object, long)} */
2551 @IntrinsicCandidate
2552 public native boolean getBooleanVolatile(Object o, long offset);
2553
2554 /** Volatile version of {@link #putBoolean(Object, long, boolean)} */
2555 @IntrinsicCandidate
2556 public native void putBooleanVolatile(Object o, long offset, boolean x);
2557
2558 /** Volatile version of {@link #getByte(Object, long)} */
2559 @IntrinsicCandidate
2560 public native byte getByteVolatile(Object o, long offset);
2561
2594 /** Volatile version of {@link #putFloat(Object, long, float)} */
2595 @IntrinsicCandidate
2596 public native void putFloatVolatile(Object o, long offset, float x);
2597
2598 /** Volatile version of {@link #getDouble(Object, long)} */
2599 @IntrinsicCandidate
2600 public native double getDoubleVolatile(Object o, long offset);
2601
2602 /** Volatile version of {@link #putDouble(Object, long, double)} */
2603 @IntrinsicCandidate
2604 public native void putDoubleVolatile(Object o, long offset, double x);
2605
2606
2607
2608 /** Acquire version of {@link #getReferenceVolatile(Object, long)} */
2609 @IntrinsicCandidate
2610 public final Object getReferenceAcquire(Object o, long offset) {
2611 return getReferenceVolatile(o, offset);
2612 }
2613
2614 @ForceInline
2615 public final <V> Object getFlatValueAcquire(Object o, long offset, int layout, Class<?> valueType) {
2616 // we translate using fences (see: https://gee.cs.oswego.edu/dl/html/j9mm.html)
2617 Object res = getFlatValue(o, offset, layout, valueType);
2618 loadFence();
2619 return res;
2620 }
2621
2622 /** Acquire version of {@link #getBooleanVolatile(Object, long)} */
2623 @IntrinsicCandidate
2624 public final boolean getBooleanAcquire(Object o, long offset) {
2625 return getBooleanVolatile(o, offset);
2626 }
2627
2628 /** Acquire version of {@link #getByteVolatile(Object, long)} */
2629 @IntrinsicCandidate
2630 public final byte getByteAcquire(Object o, long offset) {
2631 return getByteVolatile(o, offset);
2632 }
2633
2634 /** Acquire version of {@link #getShortVolatile(Object, long)} */
2635 @IntrinsicCandidate
2636 public final short getShortAcquire(Object o, long offset) {
2637 return getShortVolatile(o, offset);
2638 }
2639
2640 /** Acquire version of {@link #getCharVolatile(Object, long)} */
2641 @IntrinsicCandidate
2666 public final double getDoubleAcquire(Object o, long offset) {
2667 return getDoubleVolatile(o, offset);
2668 }
2669
2670 /*
2671 * Versions of {@link #putReferenceVolatile(Object, long, Object)}
2672 * that do not guarantee immediate visibility of the store to
2673 * other threads. This method is generally only useful if the
2674 * underlying field is a Java volatile (or if an array cell, one
2675 * that is otherwise only accessed using volatile accesses).
2676 *
2677 * Corresponds to C11 atomic_store_explicit(..., memory_order_release).
2678 */
2679
2680 /** Release version of {@link #putReferenceVolatile(Object, long, Object)} */
2681 @IntrinsicCandidate
2682 public final void putReferenceRelease(Object o, long offset, Object x) {
2683 putReferenceVolatile(o, offset, x);
2684 }
2685
2686 @ForceInline
2687 public final <V> void putFlatValueRelease(Object o, long offset, int layout, Class<?> valueType, V x) {
2688 // we translate using fences (see: https://gee.cs.oswego.edu/dl/html/j9mm.html)
2689 storeFence();
2690 putFlatValue(o, offset, layout, valueType, x);
2691 }
2692
2693 /** Release version of {@link #putBooleanVolatile(Object, long, boolean)} */
2694 @IntrinsicCandidate
2695 public final void putBooleanRelease(Object o, long offset, boolean x) {
2696 putBooleanVolatile(o, offset, x);
2697 }
2698
2699 /** Release version of {@link #putByteVolatile(Object, long, byte)} */
2700 @IntrinsicCandidate
2701 public final void putByteRelease(Object o, long offset, byte x) {
2702 putByteVolatile(o, offset, x);
2703 }
2704
2705 /** Release version of {@link #putShortVolatile(Object, long, short)} */
2706 @IntrinsicCandidate
2707 public final void putShortRelease(Object o, long offset, short x) {
2708 putShortVolatile(o, offset, x);
2709 }
2710
2711 /** Release version of {@link #putCharVolatile(Object, long, char)} */
2712 @IntrinsicCandidate
2729 /** Release version of {@link #putLongVolatile(Object, long, long)} */
2730 @IntrinsicCandidate
2731 public final void putLongRelease(Object o, long offset, long x) {
2732 putLongVolatile(o, offset, x);
2733 }
2734
2735 /** Release version of {@link #putDoubleVolatile(Object, long, double)} */
2736 @IntrinsicCandidate
2737 public final void putDoubleRelease(Object o, long offset, double x) {
2738 putDoubleVolatile(o, offset, x);
2739 }
2740
2741 // ------------------------------ Opaque --------------------------------------
2742
2743 /** Opaque version of {@link #getReferenceVolatile(Object, long)} */
2744 @IntrinsicCandidate
2745 public final Object getReferenceOpaque(Object o, long offset) {
2746 return getReferenceVolatile(o, offset);
2747 }
2748
2749 @ForceInline
2750 public final <V> Object getFlatValueOpaque(Object o, long offset, int layout, Class<?> valueType) {
2751 // this is stronger than opaque semantics
2752 return getFlatValueAcquire(o, offset, layout, valueType);
2753 }
2754
2755 /** Opaque version of {@link #getBooleanVolatile(Object, long)} */
2756 @IntrinsicCandidate
2757 public final boolean getBooleanOpaque(Object o, long offset) {
2758 return getBooleanVolatile(o, offset);
2759 }
2760
2761 /** Opaque version of {@link #getByteVolatile(Object, long)} */
2762 @IntrinsicCandidate
2763 public final byte getByteOpaque(Object o, long offset) {
2764 return getByteVolatile(o, offset);
2765 }
2766
2767 /** Opaque version of {@link #getShortVolatile(Object, long)} */
2768 @IntrinsicCandidate
2769 public final short getShortOpaque(Object o, long offset) {
2770 return getShortVolatile(o, offset);
2771 }
2772
2773 /** Opaque version of {@link #getCharVolatile(Object, long)} */
2774 @IntrinsicCandidate
2789 }
2790
2791 /** Opaque version of {@link #getLongVolatile(Object, long)} */
2792 @IntrinsicCandidate
2793 public final long getLongOpaque(Object o, long offset) {
2794 return getLongVolatile(o, offset);
2795 }
2796
2797 /** Opaque version of {@link #getDoubleVolatile(Object, long)} */
2798 @IntrinsicCandidate
2799 public final double getDoubleOpaque(Object o, long offset) {
2800 return getDoubleVolatile(o, offset);
2801 }
2802
2803 /** Opaque version of {@link #putReferenceVolatile(Object, long, Object)} */
2804 @IntrinsicCandidate
2805 public final void putReferenceOpaque(Object o, long offset, Object x) {
2806 putReferenceVolatile(o, offset, x);
2807 }
2808
2809 @ForceInline
2810 public final <V> void putFlatValueOpaque(Object o, long offset, int layout, Class<?> valueType, V x) {
2811 // this is stronger than opaque semantics
2812 putFlatValueRelease(o, offset, layout, valueType, x);
2813 }
2814
2815 /** Opaque version of {@link #putBooleanVolatile(Object, long, boolean)} */
2816 @IntrinsicCandidate
2817 public final void putBooleanOpaque(Object o, long offset, boolean x) {
2818 putBooleanVolatile(o, offset, x);
2819 }
2820
2821 /** Opaque version of {@link #putByteVolatile(Object, long, byte)} */
2822 @IntrinsicCandidate
2823 public final void putByteOpaque(Object o, long offset, byte x) {
2824 putByteVolatile(o, offset, x);
2825 }
2826
2827 /** Opaque version of {@link #putShortVolatile(Object, long, short)} */
2828 @IntrinsicCandidate
2829 public final void putShortOpaque(Object o, long offset, short x) {
2830 putShortVolatile(o, offset, x);
2831 }
2832
2833 /** Opaque version of {@link #putCharVolatile(Object, long, char)} */
2834 @IntrinsicCandidate
2843 }
2844
2845 /** Opaque version of {@link #putFloatVolatile(Object, long, float)} */
2846 @IntrinsicCandidate
2847 public final void putFloatOpaque(Object o, long offset, float x) {
2848 putFloatVolatile(o, offset, x);
2849 }
2850
2851 /** Opaque version of {@link #putLongVolatile(Object, long, long)} */
2852 @IntrinsicCandidate
2853 public final void putLongOpaque(Object o, long offset, long x) {
2854 putLongVolatile(o, offset, x);
2855 }
2856
2857 /** Opaque version of {@link #putDoubleVolatile(Object, long, double)} */
2858 @IntrinsicCandidate
2859 public final void putDoubleOpaque(Object o, long offset, double x) {
2860 putDoubleVolatile(o, offset, x);
2861 }
2862
2863 @ForceInline
2864 private boolean compareAndSetFlatValueAsBytes(Object o, long offset, int layout, Class<?> valueType, Object expected, Object x) {
2865 // We turn the payload of an atomic value into a numeric value (of suitable type)
2866 // by storing the value into an array element (of matching layout) and by reading
2867 // back the array element as an integral value. After which we can implement the CAS
2868 // as a plain numeric CAS. Note: this only works if the payload contains no oops
2869 // (see VarHandles::isAtomicFlat).
2870 Object expectedArray = newSpecialArray(valueType, 1, layout);
2871 Object xArray = newSpecialArray(valueType, 1, layout);
2872 long base = arrayBaseOffset(expectedArray.getClass());
2873 int scale = arrayIndexScale(expectedArray.getClass());
2874 putFlatValue(expectedArray, base, layout, valueType, expected);
2875 putFlatValue(xArray, base, layout, valueType, x);
2876 switch (scale) {
2877 case 1: {
2878 byte expectedByte = getByte(expectedArray, base);
2879 byte xByte = getByte(xArray, base);
2880 return compareAndSetByte(o, offset, expectedByte, xByte);
2881 }
2882 case 2: {
2883 short expectedShort = getShort(expectedArray, base);
2884 short xShort = getShort(xArray, base);
2885 return compareAndSetShort(o, offset, expectedShort, xShort);
2886 }
2887 case 4: {
2888 int expectedInt = getInt(expectedArray, base);
2889 int xInt = getInt(xArray, base);
2890 return compareAndSetInt(o, offset, expectedInt, xInt);
2891 }
2892 case 8: {
2893 long expectedLong = getLong(expectedArray, base);
2894 long xLong = getLong(xArray, base);
2895 return compareAndSetLong(o, offset, expectedLong, xLong);
2896 }
2897 default: {
2898 throw new UnsupportedOperationException();
2899 }
2900 }
2901 }
2902
2903 /**
2904 * Unblocks the given thread blocked on {@code park}, or, if it is
2905 * not blocked, causes the subsequent call to {@code park} not to
2906 * block. Note: this operation is "unsafe" solely because the
2907 * caller must somehow ensure that the thread has not been
2908 * destroyed. Nothing special is usually required to ensure this
2909 * when called from Java (in which there will ordinarily be a live
2910 * reference to the thread) but this is not nearly-automatically
2911 * so when calling from native code.
2912 *
2913 * @param thread the thread to unpark.
2914 */
2915 @IntrinsicCandidate
2916 public native void unpark(Object thread);
2917
2918 /**
2919 * Blocks current thread, returning when a balancing
2920 * {@code unpark} occurs, or a balancing {@code unpark} has
2921 * already occurred, or the thread is interrupted, or, if not
2922 * absolute and time is not zero, the given time nanoseconds have
3269 /**
3270 * Atomically exchanges the given reference value with the current
3271 * reference value of a field or array element within the given
3272 * object {@code o} at the given {@code offset}.
3273 *
3274 * @param o object/array to update the field/element in
3275 * @param offset field/element offset
3276 * @param newValue new value
3277 * @return the previous value
3278 * @since 1.8
3279 */
3280 @IntrinsicCandidate
3281 public final Object getAndSetReference(Object o, long offset, Object newValue) {
3282 Object v;
3283 do {
3284 v = getReferenceVolatile(o, offset);
3285 } while (!weakCompareAndSetReference(o, offset, v, newValue));
3286 return v;
3287 }
3288
3289 @ForceInline
3290 public final Object getAndSetReference(Object o, long offset, Class<?> valueType, Object newValue) {
3291 Object v;
3292 do {
3293 v = getReferenceVolatile(o, offset);
3294 } while (!compareAndSetReference(o, offset, valueType, v, newValue));
3295 return v;
3296 }
3297
3298 @ForceInline
3299 public Object getAndSetFlatValue(Object o, long offset, int layoutKind, Class<?> valueType, Object newValue) {
3300 Object v;
3301 do {
3302 v = getFlatValueVolatile(o, offset, layoutKind, valueType);
3303 } while (!compareAndSetFlatValue(o, offset, layoutKind, valueType, v, newValue));
3304 return v;
3305 }
3306
3307 @ForceInline
3308 public final Object getAndSetReferenceRelease(Object o, long offset, Object newValue) {
3309 Object v;
3310 do {
3311 v = getReference(o, offset);
3312 } while (!weakCompareAndSetReferenceRelease(o, offset, v, newValue));
3313 return v;
3314 }
3315
3316 @ForceInline
3317 public final Object getAndSetReferenceRelease(Object o, long offset, Class<?> valueType, Object newValue) {
3318 return getAndSetReference(o, offset, valueType, newValue);
3319 }
3320
3321 @ForceInline
3322 public Object getAndSetFlatValueRelease(Object o, long offset, int layoutKind, Class<?> valueType, Object x) {
3323 return getAndSetFlatValue(o, offset, layoutKind, valueType, x);
3324 }
3325
3326 @ForceInline
3327 public final Object getAndSetReferenceAcquire(Object o, long offset, Object newValue) {
3328 Object v;
3329 do {
3330 v = getReferenceAcquire(o, offset);
3331 } while (!weakCompareAndSetReferenceAcquire(o, offset, v, newValue));
3332 return v;
3333 }
3334
3335 @ForceInline
3336 public final Object getAndSetReferenceAcquire(Object o, long offset, Class<?> valueType, Object newValue) {
3337 return getAndSetReference(o, offset, valueType, newValue);
3338 }
3339
3340 @ForceInline
3341 public Object getAndSetFlatValueAcquire(Object o, long offset, int layoutKind, Class<?> valueType, Object x) {
3342 return getAndSetFlatValue(o, offset, layoutKind, valueType, x);
3343 }
3344
3345 @IntrinsicCandidate
3346 public final byte getAndSetByte(Object o, long offset, byte newValue) {
3347 byte v;
3348 do {
3349 v = getByteVolatile(o, offset);
3350 } while (!weakCompareAndSetByte(o, offset, v, newValue));
3351 return v;
3352 }
3353
3354 @ForceInline
3355 public final byte getAndSetByteRelease(Object o, long offset, byte newValue) {
3356 byte v;
3357 do {
3358 v = getByte(o, offset);
3359 } while (!weakCompareAndSetByteRelease(o, offset, v, newValue));
3360 return v;
3361 }
3362
3363 @ForceInline
3364 public final byte getAndSetByteAcquire(Object o, long offset, byte newValue) {
4380 private static short convEndian(boolean big, short n) { return big == BIG_ENDIAN ? n : Short.reverseBytes(n) ; }
4381 private static int convEndian(boolean big, int n) { return big == BIG_ENDIAN ? n : Integer.reverseBytes(n) ; }
4382 private static long convEndian(boolean big, long n) { return big == BIG_ENDIAN ? n : Long.reverseBytes(n) ; }
4383
4384
4385
4386 private native long allocateMemory0(long bytes);
4387 private native long reallocateMemory0(long address, long bytes);
4388 private native void freeMemory0(long address);
4389 @IntrinsicCandidate
4390 private native void setMemory0(Object o, long offset, long bytes, byte value);
4391 @IntrinsicCandidate
4392 private native void copyMemory0(Object srcBase, long srcOffset, Object destBase, long destOffset, long bytes);
4393 private native void copySwapMemory0(Object srcBase, long srcOffset, Object destBase, long destOffset, long bytes, long elemSize);
4394 private native long objectFieldOffset0(Field f);
4395 private native long objectFieldOffset1(Class<?> c, String name);
4396 private native long staticFieldOffset0(Field f);
4397 private native Object staticFieldBase0(Field f);
4398 private native boolean shouldBeInitialized0(Class<?> c);
4399 private native void ensureClassInitialized0(Class<?> c);
4400 private native void notifyStrictStaticAccess0(Class<?> c, long staticFieldOffset, boolean writing);
4401 private native int arrayBaseOffset0(Class<?> arrayClass); // public version returns long to promote correct arithmetic
4402 private native int arrayIndexScale0(Class<?> arrayClass);
4403 private native long getObjectSize0(Object o);
4404 private native int getLoadAverage0(double[] loadavg, int nelems);
4405
4406
4407 /**
4408 * Invokes the given direct byte buffer's cleaner, if any.
4409 *
4410 * @param directBuffer a direct byte buffer
4411 * @throws NullPointerException if {@code directBuffer} is null
4412 * @throws IllegalArgumentException if {@code directBuffer} is non-direct,
4413 * or is a {@link java.nio.Buffer#slice slice}, or is a
4414 * {@link java.nio.Buffer#duplicate duplicate}
4415 */
4416 public void invokeCleaner(java.nio.ByteBuffer directBuffer) {
4417 if (!directBuffer.isDirect())
4418 throw new IllegalArgumentException("buffer is non-direct");
4419
4420 DirectBuffer db = (DirectBuffer) directBuffer;
4421 if (db.attachment() != null)
4422 throw new IllegalArgumentException("duplicate or slice");
4423
|