diff --git a/make/jprt.properties b/make/jprt.properties index 4c88ed02650ad2a0dda17e8ced329afb0365bd80..76944a03919825dffcad8c9214aa14f4584d44be 100644 --- a/make/jprt.properties +++ b/make/jprt.properties @@ -541,9 +541,20 @@ jprt.make.rule.test.targets.standard.server = \ ${jprt.my.windows.i586}-*-c2-servertest, \ ${jprt.my.windows.x64}-*-c2-servertest +jprt.make.rule.test.targets.standard.internalvmtests = \ + ${jprt.my.solaris.sparc}-fastdebug-c2-internalvmtests, \ + ${jprt.my.solaris.sparcv9}-fastdebug-c2-internalvmtests, \ + ${jprt.my.solaris.i586}-fastdebug-c2-internalvmtests, \ + ${jprt.my.solaris.x64}-fastdebug-c2-internalvmtests, \ + ${jprt.my.linux.i586}-fastdebug-c2-internalvmtests, \ + ${jprt.my.linux.x64}-fastdebug-c2-internalvmtests, \ + ${jprt.my.windows.i586}-fastdebug-c2-internalvmtests, \ + ${jprt.my.windows.x64}-fastdebug-c2-internalvmtests + jprt.make.rule.test.targets.standard = \ ${jprt.make.rule.test.targets.standard.client}, \ - ${jprt.make.rule.test.targets.standard.server} + ${jprt.make.rule.test.targets.standard.server}, \ + ${jprt.make.rule.test.targets.standard.internalvmtests} jprt.make.rule.test.targets.embedded = \ ${jprt.make.rule.test.targets.standard.client} diff --git a/src/share/vm/oops/arrayOop.cpp b/src/share/vm/oops/arrayOop.cpp index 62a971a618247a3ec2927ba7561c5b5ccdcc9938..c159438358fd996c8188a98e420ee21365a02b78 100644 --- a/src/share/vm/oops/arrayOop.cpp +++ b/src/share/vm/oops/arrayOop.cpp @@ -23,9 +23,40 @@ */ #include "precompiled.hpp" + +/////////////// Unit tests /////////////// + +#ifndef PRODUCT + #include "oops/arrayOop.hpp" -#include "oops/objArrayOop.hpp" -#include "oops/oop.inline.hpp" -#include "oops/symbol.hpp" +#include "utilities/globalDefinitions.hpp" + +bool arrayOopDesc::check_max_length_overflow(BasicType type) { + julong length = max_array_length(type); + julong bytes_per_element = type2aelembytes(type); + julong bytes = length * bytes_per_element + header_size_in_bytes(); + return (julong)(size_t)bytes == bytes; +} + +bool arrayOopDesc::test_max_array_length() { + tty->print_cr("test_max_array_length"); + + assert(check_max_length_overflow(T_BOOLEAN), "size_t overflow for boolean array"); + assert(check_max_length_overflow(T_CHAR), "size_t overflow for char array"); + assert(check_max_length_overflow(T_FLOAT), "size_t overflow for float array"); + assert(check_max_length_overflow(T_DOUBLE), "size_t overflow for double array"); + assert(check_max_length_overflow(T_BYTE), "size_t overflow for byte array"); + assert(check_max_length_overflow(T_SHORT), "size_t overflow for short array"); + assert(check_max_length_overflow(T_INT), "size_t overflow for int array"); + assert(check_max_length_overflow(T_LONG), "size_t overflow for long array"); + assert(check_max_length_overflow(T_OBJECT), "size_t overflow for object array"); + assert(check_max_length_overflow(T_ARRAY), "size_t overflow for array array"); + assert(check_max_length_overflow(T_NARROWOOP), "size_t overflow for narrowOop array"); + + // T_VOID and T_ADDRESS are not supported by max_array_length() + + return true; +} + -// <> +#endif //PRODUCT diff --git a/src/share/vm/oops/arrayOop.hpp b/src/share/vm/oops/arrayOop.hpp index 0e762397c0c74417e42d430a404c1450a5f6d42f..58377fe9c4af892f5be4582868b6bcbf91f09a15 100644 --- a/src/share/vm/oops/arrayOop.hpp +++ b/src/share/vm/oops/arrayOop.hpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997, 2010, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -104,20 +104,26 @@ class arrayOopDesc : public oopDesc { // Return the maximum length of an array of BasicType. The length can passed // to typeArrayOop::object_size(scale, length, header_size) without causing an - // overflow. + // overflow. We also need to make sure that this will not overflow a size_t on + // 32 bit platforms when we convert it to a byte size. static int32_t max_array_length(BasicType type) { assert(type >= 0 && type < T_CONFLICT, "wrong type"); assert(type2aelembytes(type) != 0, "wrong type"); - const int bytes_per_element = type2aelembytes(type); - if (bytes_per_element < HeapWordSize) { + + const size_t max_element_words_per_size_t = align_size_down((SIZE_MAX/HeapWordSize - header_size(type)), MinObjAlignment); + const size_t max_elements_per_size_t = HeapWordSize * max_element_words_per_size_t / type2aelembytes(type); + if ((size_t)max_jint < max_elements_per_size_t) { return max_jint; } - - const int32_t max_words = align_size_down(max_jint, MinObjAlignment); - const int32_t max_element_words = max_words - header_size(type); - const int32_t words_per_element = bytes_per_element >> LogHeapWordSize; - return max_element_words / words_per_element; + return (int32_t)max_elements_per_size_t; } + +// for unit testing +#ifndef PRODUCT + static bool check_max_length_overflow(BasicType type); + static int32_t old_max_array_length(BasicType type); + static bool test_max_array_length(); +#endif }; #endif // SHARE_VM_OOPS_ARRAYOOP_HPP diff --git a/src/share/vm/prims/jni.cpp b/src/share/vm/prims/jni.cpp index 300fe63a43d93b7d0fa1c6ba271ff9f5529f4636..aef42cb38219d80f4a53acf106d304b4d5d01bd3 100644 --- a/src/share/vm/prims/jni.cpp +++ b/src/share/vm/prims/jni.cpp @@ -5042,7 +5042,8 @@ _JNI_IMPORT_OR_EXPORT_ jint JNICALL JNI_GetDefaultJavaVMInitArgs(void *args_) { void execute_internal_vm_tests() { if (ExecuteInternalVMTests) { assert(QuickSort::test_quick_sort(), "test_quick_sort failed"); - tty->print_cr("All tests passed"); + assert(arrayOopDesc::test_max_array_length(), "test_max_array_length failed"); + tty->print_cr("All internal VM tests passed"); } } diff --git a/src/share/vm/utilities/quickSort.cpp b/src/share/vm/utilities/quickSort.cpp index 947b420e7a9e4dd23f857bba2954c790adf1bd22..bf68af1fc8d46f14f841ba25822f46791f0285e4 100644 --- a/src/share/vm/utilities/quickSort.cpp +++ b/src/share/vm/utilities/quickSort.cpp @@ -23,13 +23,13 @@ */ #include "precompiled.hpp" -#include "utilities/quickSort.hpp" -#ifndef PRODUCT +/////////////// Unit tests /////////////// -// Unit tests +#ifndef PRODUCT #include "runtime/os.hpp" +#include "utilities/quickSort.hpp" #include static int test_comparator(int a, int b) { @@ -94,7 +94,7 @@ bool QuickSort::sort_and_compare(int* arrayToSort, int* expectedResult, int leng } bool QuickSort::test_quick_sort() { - tty->print_cr("test_quick_sort\n"); + tty->print_cr("test_quick_sort"); { int* test_array = NULL; int* expected_array = NULL; diff --git a/test/Makefile b/test/Makefile index 50818dd01bebd7949dfa3d75bf035aa58e1fd28e..f5365929b9e49648503829a1b200ee8864e8f498 100644 --- a/test/Makefile +++ b/test/Makefile @@ -1,5 +1,5 @@ # -# Copyright (c) 1995, 2010, Oracle and/or its affiliates. All rights reserved. +# Copyright (c) 1995, 2011, Oracle and/or its affiliates. All rights reserved. # DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. # # This code is free software; you can redistribute it and/or modify it @@ -219,6 +219,15 @@ PHONY_LIST += servertest ################################################################ +# internalvmtests (run internal unit tests inside the VM) + +internalvmtests: prep $(PRODUCT_HOME) + $(PRODUCT_HOME)/bin/java $(JAVA_OPTIONS) -XX:+ExecuteInternalVMTests -version + +PHONY_LIST += internalvmtests + +################################################################ + # packtest # Expect JPRT to set JPRT_PACKTEST_HOME.