675 // ZeroBased - Use zero based compressed oops with encoding when |
675 // ZeroBased - Use zero based compressed oops with encoding when |
676 // NarrowOopHeapBaseMin + heap_size < 32Gb |
676 // NarrowOopHeapBaseMin + heap_size < 32Gb |
677 // HeapBased - Use compressed oops with heap base + encoding. |
677 // HeapBased - Use compressed oops with heap base + encoding. |
678 |
678 |
679 // 4Gb |
679 // 4Gb |
680 static const uint64_t NarrowOopHeapMax = (uint64_t(max_juint) + 1); |
680 static const uint64_t UnscaledOopHeapMax = (uint64_t(max_juint) + 1); |
681 // 32Gb |
681 // 32Gb |
682 // OopEncodingHeapMax == NarrowOopHeapMax << LogMinObjAlignmentInBytes; |
682 // OopEncodingHeapMax == UnscaledOopHeapMax << LogMinObjAlignmentInBytes; |
683 |
683 |
684 char* Universe::preferred_heap_base(size_t heap_size, size_t alignment, NARROW_OOP_MODE mode) { |
684 char* Universe::preferred_heap_base(size_t heap_size, size_t alignment, NARROW_OOP_MODE mode) { |
685 assert(is_size_aligned((size_t)OopEncodingHeapMax, alignment), "Must be"); |
685 assert(is_size_aligned((size_t)OopEncodingHeapMax, alignment), "Must be"); |
686 assert(is_size_aligned((size_t)NarrowOopHeapMax, alignment), "Must be"); |
686 assert(is_size_aligned((size_t)UnscaledOopHeapMax, alignment), "Must be"); |
687 assert(is_size_aligned(heap_size, alignment), "Must be"); |
687 assert(is_size_aligned(heap_size, alignment), "Must be"); |
688 |
688 |
689 uintx heap_base_min_address_aligned = align_size_up(HeapBaseMinAddress, alignment); |
689 uintx heap_base_min_address_aligned = align_size_up(HeapBaseMinAddress, alignment); |
690 |
690 |
691 size_t base = 0; |
691 size_t base = 0; |
700 base = heap_base_min_address_aligned; |
700 base = heap_base_min_address_aligned; |
701 |
701 |
702 // If the total size is small enough to allow UnscaledNarrowOop then |
702 // If the total size is small enough to allow UnscaledNarrowOop then |
703 // just use UnscaledNarrowOop. |
703 // just use UnscaledNarrowOop. |
704 } else if ((total_size <= OopEncodingHeapMax) && (mode != HeapBasedNarrowOop)) { |
704 } else if ((total_size <= OopEncodingHeapMax) && (mode != HeapBasedNarrowOop)) { |
705 if ((total_size <= NarrowOopHeapMax) && (mode == UnscaledNarrowOop) && |
705 if ((total_size <= UnscaledOopHeapMax) && (mode == UnscaledNarrowOop) && |
706 (Universe::narrow_oop_shift() == 0)) { |
706 (Universe::narrow_oop_shift() == 0)) { |
707 // Use 32-bits oops without encoding and |
707 // Use 32-bits oops without encoding and |
708 // place heap's top on the 4Gb boundary |
708 // place heap's top on the 4Gb boundary |
709 base = (NarrowOopHeapMax - heap_size); |
709 base = (UnscaledOopHeapMax - heap_size); |
710 } else { |
710 } else { |
711 // Can't reserve with NarrowOopShift == 0 |
711 // Can't reserve with NarrowOopShift == 0 |
712 Universe::set_narrow_oop_shift(LogMinObjAlignmentInBytes); |
712 Universe::set_narrow_oop_shift(LogMinObjAlignmentInBytes); |
|
713 |
713 if (mode == UnscaledNarrowOop || |
714 if (mode == UnscaledNarrowOop || |
714 mode == ZeroBasedNarrowOop && total_size <= NarrowOopHeapMax) { |
715 mode == ZeroBasedNarrowOop && total_size <= UnscaledOopHeapMax) { |
|
716 |
715 // Use zero based compressed oops with encoding and |
717 // Use zero based compressed oops with encoding and |
716 // place heap's top on the 32Gb boundary in case |
718 // place heap's top on the 32Gb boundary in case |
717 // total_size > 4Gb or failed to reserve below 4Gb. |
719 // total_size > 4Gb or failed to reserve below 4Gb. |
718 base = (OopEncodingHeapMax - heap_size); |
720 uint64_t heap_top = OopEncodingHeapMax; |
|
721 |
|
722 // For small heaps, save some space for compressed class pointer |
|
723 // space so it can be decoded with no base. |
|
724 if (UseCompressedClassPointers && !UseSharedSpaces && |
|
725 OopEncodingHeapMax <= 32*G) { |
|
726 |
|
727 uint64_t class_space = align_size_up(CompressedClassSpaceSize, alignment); |
|
728 assert(is_size_aligned((size_t)OopEncodingHeapMax-class_space, |
|
729 alignment), "difference must be aligned too"); |
|
730 uint64_t new_top = OopEncodingHeapMax-class_space; |
|
731 |
|
732 if (total_size <= new_top) { |
|
733 heap_top = new_top; |
|
734 } |
|
735 } |
|
736 |
|
737 // Align base to the adjusted top of the heap |
|
738 base = heap_top - heap_size; |
719 } |
739 } |
720 } |
740 } |
721 } else { |
741 } else { |
722 // UnscaledNarrowOop encoding didn't work, and no base was found for ZeroBasedOops or |
742 // UnscaledNarrowOop encoding didn't work, and no base was found for ZeroBasedOops or |
723 // HeapBasedNarrowOop encoding was requested. So, can't reserve below 32Gb. |
743 // HeapBasedNarrowOop encoding was requested. So, can't reserve below 32Gb. |
735 Universe::set_narrow_oop_use_implicit_null_checks(true); |
755 Universe::set_narrow_oop_use_implicit_null_checks(true); |
736 } else { |
756 } else { |
737 // Set to a non-NULL value so the ReservedSpace ctor computes |
757 // Set to a non-NULL value so the ReservedSpace ctor computes |
738 // the correct no-access prefix. |
758 // the correct no-access prefix. |
739 // The final value will be set in initialize_heap() below. |
759 // The final value will be set in initialize_heap() below. |
740 Universe::set_narrow_oop_base((address)NarrowOopHeapMax); |
760 Universe::set_narrow_oop_base((address)UnscaledOopHeapMax); |
741 #ifdef _WIN64 |
761 #ifdef _WIN64 |
742 if (UseLargePages) { |
762 if (UseLargePages) { |
743 // Cannot allocate guard pages for implicit checks in indexed |
763 // Cannot allocate guard pages for implicit checks in indexed |
744 // addressing mode when large pages are specified on windows. |
764 // addressing mode when large pages are specified on windows. |
745 Universe::set_narrow_oop_use_implicit_null_checks(false); |
765 Universe::set_narrow_oop_use_implicit_null_checks(false); |
833 // Don't need guard page for implicit checks in indexed addressing |
853 // Don't need guard page for implicit checks in indexed addressing |
834 // mode with zero based Compressed Oops. |
854 // mode with zero based Compressed Oops. |
835 Universe::set_narrow_oop_use_implicit_null_checks(true); |
855 Universe::set_narrow_oop_use_implicit_null_checks(true); |
836 } |
856 } |
837 #endif // _WIN64 |
857 #endif // _WIN64 |
838 if((uint64_t)Universe::heap()->reserved_region().end() > NarrowOopHeapMax) { |
858 if((uint64_t)Universe::heap()->reserved_region().end() > UnscaledOopHeapMax) { |
839 // Can't reserve heap below 4Gb. |
859 // Can't reserve heap below 4Gb. |
840 Universe::set_narrow_oop_shift(LogMinObjAlignmentInBytes); |
860 Universe::set_narrow_oop_shift(LogMinObjAlignmentInBytes); |
841 } else { |
861 } else { |
842 Universe::set_narrow_oop_shift(0); |
862 Universe::set_narrow_oop_shift(0); |
843 if (verbose) { |
863 if (verbose) { |
1029 // These are the only Java fields that are currently set during shared space dumping. |
1049 // These are the only Java fields that are currently set during shared space dumping. |
1030 // We prefer to not handle this generally, so we always reinitialize these detail messages. |
1050 // We prefer to not handle this generally, so we always reinitialize these detail messages. |
1031 Handle msg = java_lang_String::create_from_str("Java heap space", CHECK_false); |
1051 Handle msg = java_lang_String::create_from_str("Java heap space", CHECK_false); |
1032 java_lang_Throwable::set_message(Universe::_out_of_memory_error_java_heap, msg()); |
1052 java_lang_Throwable::set_message(Universe::_out_of_memory_error_java_heap, msg()); |
1033 |
1053 |
1034 msg = java_lang_String::create_from_str("Metadata space", CHECK_false); |
1054 msg = java_lang_String::create_from_str("Metaspace", CHECK_false); |
1035 java_lang_Throwable::set_message(Universe::_out_of_memory_error_metaspace, msg()); |
1055 java_lang_Throwable::set_message(Universe::_out_of_memory_error_metaspace, msg()); |
1036 msg = java_lang_String::create_from_str("Compressed class space", CHECK_false); |
1056 msg = java_lang_String::create_from_str("Compressed class space", CHECK_false); |
1037 java_lang_Throwable::set_message(Universe::_out_of_memory_error_class_metaspace, msg()); |
1057 java_lang_Throwable::set_message(Universe::_out_of_memory_error_class_metaspace, msg()); |
1038 |
1058 |
1039 msg = java_lang_String::create_from_str("Requested array size exceeds VM limit", CHECK_false); |
1059 msg = java_lang_String::create_from_str("Requested array size exceeds VM limit", CHECK_false); |