diff options
author | Ian Rogers <irogers@google.com> | 2014-02-27 17:01:55 -0800 |
---|---|---|
committer | Ian Rogers <irogers@google.com> | 2014-02-28 17:39:53 -0800 |
commit | 10af76d5af1d87686ff9ab8d00f3dadc15a84fb7 (patch) | |
tree | 9379ee44171cd5bc848ea5d0854b3cda5e5787da /luni | |
parent | 25f9a3d57eeddd56d86f84c2bd27027b8e91d591 (diff) | |
download | libcore-10af76d5af1d87686ff9ab8d00f3dadc15a84fb7.zip libcore-10af76d5af1d87686ff9ab8d00f3dadc15a84fb7.tar.gz libcore-10af76d5af1d87686ff9ab8d00f3dadc15a84fb7.tar.bz2 |
Add unpadded array allocations.
Unpadded array allocations avoid unused bytes following arrays. API conventions
follow those of newNonMovableArray.
Dalvik implementation assume dlmalloc allocation properties, ART implementation
is handled by resizing the array post-allocation:
https://android-review.googlesource.com/83670
Add VMRuntimeTest to check the properties of the array allocation routines.
Change java.lang.reflect.Array.newInstance to compare more probable array types
before less probable ones.
Bug: 13028925.
Change-Id: Icf6bfb1aa5ad4faa062b393082c689b6118a84b5
Diffstat (limited to 'luni')
-rw-r--r-- | luni/src/main/java/java/lang/reflect/Array.java | 12 | ||||
-rw-r--r-- | luni/src/test/java/dalvik/system/VMRuntimeTest.java | 135 |
2 files changed, 141 insertions, 6 deletions
diff --git a/luni/src/main/java/java/lang/reflect/Array.java b/luni/src/main/java/java/lang/reflect/Array.java index 088a434..a7dacfe 100644 --- a/luni/src/main/java/java/lang/reflect/Array.java +++ b/luni/src/main/java/java/lang/reflect/Array.java @@ -352,16 +352,16 @@ public final class Array { public static Object newInstance(Class<?> componentType, int size) throws NegativeArraySizeException { if (!componentType.isPrimitive()) { return createObjectArray(componentType, size); - } else if (componentType == boolean.class) { - return new boolean[size]; - } else if (componentType == byte.class) { - return new byte[size]; } else if (componentType == char.class) { return new char[size]; - } else if (componentType == short.class) { - return new short[size]; } else if (componentType == int.class) { return new int[size]; + } else if (componentType == byte.class) { + return new byte[size]; + } else if (componentType == boolean.class) { + return new boolean[size]; + } else if (componentType == short.class) { + return new short[size]; } else if (componentType == long.class) { return new long[size]; } else if (componentType == float.class) { diff --git a/luni/src/test/java/dalvik/system/VMRuntimeTest.java b/luni/src/test/java/dalvik/system/VMRuntimeTest.java new file mode 100644 index 0000000..44af461 --- /dev/null +++ b/luni/src/test/java/dalvik/system/VMRuntimeTest.java @@ -0,0 +1,135 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package dalvik.system; + +import java.lang.reflect.Array; +import junit.framework.TestCase; + +/** + * Test VMRuntime behavior. + */ +public final class VMRuntimeTest extends TestCase { + + private void doTestNewNonMovableArray(Class<?> componentType, int step, int maxLength) { + // Can't create negative sized arrays. + try { + Object array = VMRuntime.getRuntime().newNonMovableArray(componentType, -1); + assertTrue(false); + } catch (NegativeArraySizeException expected) { + } + + try { + Object array = VMRuntime.getRuntime().newNonMovableArray(componentType, Integer.MIN_VALUE); + assertTrue(false); + } catch (NegativeArraySizeException expected) { + } + + // Allocate arrays in a loop and check their properties. + for (int i = 0; i <= maxLength; i += step) { + Object array = VMRuntime.getRuntime().newNonMovableArray(componentType, i); + assertTrue(array.getClass().isArray()); + assertEquals(array.getClass().getComponentType(), componentType); + assertEquals(Array.getLength(array), i); + } + } + + public void testNewNonMovableArray() { + // Can't create arrays with no component type. + try { + Object array = VMRuntime.getRuntime().newNonMovableArray(null, 0); + assertTrue(false); + } catch (NullPointerException expected) { + } + + // Can't create arrays of void. + try { + Object array = VMRuntime.getRuntime().newNonMovableArray(void.class, 0); + assertTrue(false); + } catch (IllegalArgumentException expected) { + } + + int maxLengthForLoop = 16 * 1024; + int step = 67; + doTestNewNonMovableArray(boolean.class, step, maxLengthForLoop); + doTestNewNonMovableArray(byte.class, step, maxLengthForLoop); + doTestNewNonMovableArray(char.class, step, maxLengthForLoop); + doTestNewNonMovableArray(short.class, step, maxLengthForLoop); + doTestNewNonMovableArray(int.class, step, maxLengthForLoop); + doTestNewNonMovableArray(long.class, step, maxLengthForLoop); + doTestNewNonMovableArray(float.class, step, maxLengthForLoop); + doTestNewNonMovableArray(double.class, step, maxLengthForLoop); + doTestNewNonMovableArray(Object.class, step, maxLengthForLoop); + doTestNewNonMovableArray(Number.class, step, maxLengthForLoop); + doTestNewNonMovableArray(String.class, step, maxLengthForLoop); + doTestNewNonMovableArray(Runnable.class, step, maxLengthForLoop); + } + + private void doTestNewUnpaddedArray(Class<?> componentType, int step, int maxLength) { + // Can't create negative sized arrays. + try { + Object array = VMRuntime.getRuntime().newUnpaddedArray(componentType, -1); + assertTrue(false); + } catch (NegativeArraySizeException expected) { + } + + try { + Object array = VMRuntime.getRuntime().newUnpaddedArray(componentType, Integer.MIN_VALUE); + assertTrue(false); + } catch (NegativeArraySizeException expected) { + } + + // Allocate arrays in a loop and check their properties. + for (int i = 0; i <= maxLength; i += step) { + Object array = VMRuntime.getRuntime().newUnpaddedArray(componentType, i); + assertTrue(array.getClass().isArray()); + assertEquals(array.getClass().getComponentType(), componentType); + assertTrue(Array.getLength(array) >= i); + } + } + + public void testNewUnpaddedArray() { + // Can't create arrays with no component type. + try { + Object array = VMRuntime.getRuntime().newUnpaddedArray(null, 0); + assertTrue(false); + } catch (NullPointerException expected) { + } + + // Can't create arrays of void. + try { + Object array = VMRuntime.getRuntime().newUnpaddedArray(void.class, 0); + assertTrue(false); + } catch (IllegalArgumentException expected) { + } + + int maxLengthForLoop = 16 * 1024; + int step = 67; + doTestNewUnpaddedArray(boolean.class, step, maxLengthForLoop); + doTestNewUnpaddedArray(byte.class, step, maxLengthForLoop); + doTestNewUnpaddedArray(char.class, step, maxLengthForLoop); + doTestNewUnpaddedArray(short.class, step, maxLengthForLoop); + doTestNewUnpaddedArray(int.class, step, maxLengthForLoop); + doTestNewUnpaddedArray(long.class, step, maxLengthForLoop); + doTestNewUnpaddedArray(float.class, step, maxLengthForLoop); + doTestNewUnpaddedArray(double.class, step, maxLengthForLoop); + doTestNewUnpaddedArray(Object.class, step, maxLengthForLoop); + doTestNewUnpaddedArray(Number.class, step, maxLengthForLoop); + doTestNewUnpaddedArray(String.class, step, maxLengthForLoop); + doTestNewUnpaddedArray(Runnable.class, step, maxLengthForLoop); + } +} + |