Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(345)

Side by Side Diff: third_party/protobuf/java/core/src/main/java/com/google/protobuf/UnsafeUtil.java

Issue 2495533002: third_party/protobuf: Update to HEAD (83d681ee2c) (Closed)
Patch Set: Make chrome settings proto generated file a component Created 4 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Protocol Buffers - Google's data interchange format
2 // Copyright 2008 Google Inc. All rights reserved.
3 // https://developers.google.com/protocol-buffers/
4 //
5 // Redistribution and use in source and binary forms, with or without
6 // modification, are permitted provided that the following conditions are
7 // met:
8 //
9 // * Redistributions of source code must retain the above copyright
10 // notice, this list of conditions and the following disclaimer.
11 // * Redistributions in binary form must reproduce the above
12 // copyright notice, this list of conditions and the following disclaimer
13 // in the documentation and/or other materials provided with the
14 // distribution.
15 // * Neither the name of Google Inc. nor the names of its
16 // contributors may be used to endorse or promote products derived from
17 // this software without specific prior written permission.
18 //
19 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
21 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
22 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
23 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
25 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30
31 package com.google.protobuf;
32
33 import java.lang.reflect.Field;
34 import java.nio.Buffer;
35 import java.nio.ByteBuffer;
36 import java.security.AccessController;
37 import java.security.PrivilegedExceptionAction;
38 import sun.misc.Unsafe;
39
40 /** Utility class for working with unsafe operations. */
41 // TODO(nathanmittler): Add support for Android Memory/MemoryBlock
42 final class UnsafeUtil {
43 private static final sun.misc.Unsafe UNSAFE = getUnsafe();
44 private static final boolean HAS_UNSAFE_BYTEBUFFER_OPERATIONS =
45 supportsUnsafeByteBufferOperations();
46 private static final boolean HAS_UNSAFE_ARRAY_OPERATIONS = supportsUnsafeArray Operations();
47 private static final long ARRAY_BASE_OFFSET = byteArrayBaseOffset();
48 private static final long BUFFER_ADDRESS_OFFSET = fieldOffset(field(Buffer.cla ss, "address"));
49
50 private UnsafeUtil() {}
51
52 static boolean hasUnsafeArrayOperations() {
53 return HAS_UNSAFE_ARRAY_OPERATIONS;
54 }
55
56 static boolean hasUnsafeByteBufferOperations() {
57 return HAS_UNSAFE_BYTEBUFFER_OPERATIONS;
58 }
59
60 static Object allocateInstance(Class<?> clazz) {
61 try {
62 return UNSAFE.allocateInstance(clazz);
63 } catch (InstantiationException e) {
64 throw new RuntimeException(e);
65 }
66 }
67
68 static long objectFieldOffset(Field field) {
69 return UNSAFE.objectFieldOffset(field);
70 }
71
72 static long getArrayBaseOffset() {
73 return ARRAY_BASE_OFFSET;
74 }
75
76 static byte getByte(Object target, long offset) {
77 return UNSAFE.getByte(target, offset);
78 }
79
80 static void putByte(Object target, long offset, byte value) {
81 UNSAFE.putByte(target, offset, value);
82 }
83
84 static int getInt(Object target, long offset) {
85 return UNSAFE.getInt(target, offset);
86 }
87
88 static void putInt(Object target, long offset, int value) {
89 UNSAFE.putInt(target, offset, value);
90 }
91
92 static long getLong(Object target, long offset) {
93 return UNSAFE.getLong(target, offset);
94 }
95
96 static void putLong(Object target, long offset, long value) {
97 UNSAFE.putLong(target, offset, value);
98 }
99
100 static boolean getBoolean(Object target, long offset) {
101 return UNSAFE.getBoolean(target, offset);
102 }
103
104 static void putBoolean(Object target, long offset, boolean value) {
105 UNSAFE.putBoolean(target, offset, value);
106 }
107
108 static float getFloat(Object target, long offset) {
109 return UNSAFE.getFloat(target, offset);
110 }
111
112 static void putFloat(Object target, long offset, float value) {
113 UNSAFE.putFloat(target, offset, value);
114 }
115
116 static double getDouble(Object target, long offset) {
117 return UNSAFE.getDouble(target, offset);
118 }
119
120 static void putDouble(Object target, long offset, double value) {
121 UNSAFE.putDouble(target, offset, value);
122 }
123
124 static Object getObject(Object target, long offset) {
125 return UNSAFE.getObject(target, offset);
126 }
127
128 static void putObject(Object target, long offset, Object value) {
129 UNSAFE.putObject(target, offset, value);
130 }
131
132 static void copyMemory(
133 Object src, long srcOffset, Object target, long targetOffset, long length) {
134 UNSAFE.copyMemory(src, srcOffset, target, targetOffset, length);
135 }
136
137 static byte getByte(long address) {
138 return UNSAFE.getByte(address);
139 }
140
141 static void putByte(long address, byte value) {
142 UNSAFE.putByte(address, value);
143 }
144
145 static int getInt(long address) {
146 return UNSAFE.getInt(address);
147 }
148
149 static void putInt(long address, int value) {
150 UNSAFE.putInt(address, value);
151 }
152
153 static long getLong(long address) {
154 return UNSAFE.getLong(address);
155 }
156
157 static void putLong(long address, long value) {
158 UNSAFE.putLong(address, value);
159 }
160
161 static void copyMemory(long srcAddress, long targetAddress, long length) {
162 UNSAFE.copyMemory(srcAddress, targetAddress, length);
163 }
164
165 static void setMemory(long address, long numBytes, byte value) {
166 UNSAFE.setMemory(address, numBytes, value);
167 }
168
169 /**
170 * Gets the offset of the {@code address} field of the given direct {@link Byt eBuffer}.
171 */
172 static long addressOffset(ByteBuffer buffer) {
173 return UNSAFE.getLong(buffer, BUFFER_ADDRESS_OFFSET);
174 }
175
176 /**
177 * Gets the {@code sun.misc.Unsafe} instance, or {@code null} if not available on this platform.
178 */
179 private static sun.misc.Unsafe getUnsafe() {
180 sun.misc.Unsafe unsafe = null;
181 try {
182 unsafe =
183 AccessController.doPrivileged(
184 new PrivilegedExceptionAction<Unsafe>() {
185 @Override
186 public sun.misc.Unsafe run() throws Exception {
187 Class<sun.misc.Unsafe> k = sun.misc.Unsafe.class;
188
189 for (Field f : k.getDeclaredFields()) {
190 f.setAccessible(true);
191 Object x = f.get(null);
192 if (k.isInstance(x)) {
193 return k.cast(x);
194 }
195 }
196 // The sun.misc.Unsafe field does not exist.
197 return null;
198 }
199 });
200 } catch (Throwable e) {
201 // Catching Throwable here due to the fact that Google AppEngine raises No ClassDefFoundError
202 // for Unsafe.
203 }
204 return unsafe;
205 }
206
207 /** Indicates whether or not unsafe array operations are supported on this pla tform. */
208 private static boolean supportsUnsafeArrayOperations() {
209 boolean supported = false;
210 if (UNSAFE != null) {
211 try {
212 Class<?> clazz = UNSAFE.getClass();
213 clazz.getMethod("objectFieldOffset", Field.class);
214 clazz.getMethod("allocateInstance", Class.class);
215 clazz.getMethod("arrayBaseOffset", Class.class);
216 clazz.getMethod("getByte", Object.class, long.class);
217 clazz.getMethod("putByte", Object.class, long.class, byte.class);
218 clazz.getMethod("getBoolean", Object.class, long.class);
219 clazz.getMethod("putBoolean", Object.class, long.class, boolean.class);
220 clazz.getMethod("getInt", Object.class, long.class);
221 clazz.getMethod("putInt", Object.class, long.class, int.class);
222 clazz.getMethod("getLong", Object.class, long.class);
223 clazz.getMethod("putLong", Object.class, long.class, long.class);
224 clazz.getMethod("getFloat", Object.class, long.class);
225 clazz.getMethod("putFloat", Object.class, long.class, float.class);
226 clazz.getMethod("getDouble", Object.class, long.class);
227 clazz.getMethod("putDouble", Object.class, long.class, double.class);
228 clazz.getMethod("getObject", Object.class, long.class);
229 clazz.getMethod("putObject", Object.class, long.class, Object.class);
230 clazz.getMethod(
231 "copyMemory", Object.class, long.class, Object.class, long.class, lo ng.class);
232 supported = true;
233 } catch (Throwable e) {
234 // Do nothing.
235 }
236 }
237 return supported;
238 }
239
240 private static boolean supportsUnsafeByteBufferOperations() {
241 boolean supported = false;
242 if (UNSAFE != null) {
243 try {
244 Class<?> clazz = UNSAFE.getClass();
245 // Methods for getting direct buffer address.
246 clazz.getMethod("objectFieldOffset", Field.class);
247 clazz.getMethod("getLong", Object.class, long.class);
248
249 clazz.getMethod("getByte", long.class);
250 clazz.getMethod("putByte", long.class, byte.class);
251 clazz.getMethod("getInt", long.class);
252 clazz.getMethod("putInt", long.class, int.class);
253 clazz.getMethod("getLong", long.class);
254 clazz.getMethod("putLong", long.class, long.class);
255 clazz.getMethod("setMemory", long.class, long.class, byte.class);
256 clazz.getMethod("copyMemory", long.class, long.class, long.class);
257 supported = true;
258 } catch (Throwable e) {
259 // Do nothing.
260 }
261 }
262 return supported;
263 }
264
265 /**
266 * Get the base offset for byte arrays, or {@code -1} if {@code sun.misc.Unsaf e} is not available.
267 */
268 private static int byteArrayBaseOffset() {
269 return HAS_UNSAFE_ARRAY_OPERATIONS ? UNSAFE.arrayBaseOffset(byte[].class) : -1;
270 }
271
272 /**
273 * Returns the offset of the provided field, or {@code -1} if {@code sun.misc. Unsafe} is not
274 * available.
275 */
276 private static long fieldOffset(Field field) {
277 return field == null || UNSAFE == null ? -1 : UNSAFE.objectFieldOffset(field );
278 }
279
280 /**
281 * Gets the field with the given name within the class, or {@code null} if not found. If found,
282 * the field is made accessible.
283 */
284 private static Field field(Class<?> clazz, String fieldName) {
285 Field field;
286 try {
287 field = clazz.getDeclaredField(fieldName);
288 field.setAccessible(true);
289 } catch (Throwable t) {
290 // Failed to access the fields.
291 field = null;
292 }
293 return field;
294 }
295 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698