hotspot/src/share/vm/runtime/virtualspace.cpp
changeset 10237 df347ffafa0d
parent 7397 5b173b4ca846
child 10565 dc90c239f4ec
equal deleted inserted replaced
10236:c4256e927bed 10237:df347ffafa0d
     1 /*
     1 /*
     2  * Copyright (c) 1997, 2010, Oracle and/or its affiliates. All rights reserved.
     2  * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     4  *
     4  *
     5  * This code is free software; you can redistribute it and/or modify it
     5  * This code is free software; you can redistribute it and/or modify it
     6  * under the terms of the GNU General Public License version 2 only, as
     6  * under the terms of the GNU General Public License version 2 only, as
     7  * published by the Free Software Foundation.
     7  * published by the Free Software Foundation.
    66   assert(addr != NULL, "sanity");
    66   assert(addr != NULL, "sanity");
    67   const size_t required_size = prefix_size + suffix_size;
    67   const size_t required_size = prefix_size + suffix_size;
    68   assert(len >= required_size, "len too small");
    68   assert(len >= required_size, "len too small");
    69 
    69 
    70   const size_t s = size_t(addr);
    70   const size_t s = size_t(addr);
    71   const size_t beg_ofs = s + prefix_size & suffix_align - 1;
    71   const size_t beg_ofs = (s + prefix_size) & (suffix_align - 1);
    72   const size_t beg_delta = beg_ofs == 0 ? 0 : suffix_align - beg_ofs;
    72   const size_t beg_delta = beg_ofs == 0 ? 0 : suffix_align - beg_ofs;
    73 
    73 
    74   if (len < beg_delta + required_size) {
    74   if (len < beg_delta + required_size) {
    75      return NULL; // Cannot do proper alignment.
    75      return NULL; // Cannot do proper alignment.
    76   }
    76   }
   111     const size_t raw = size_t(raw_addr);
   111     const size_t raw = size_t(raw_addr);
   112     const size_t res = size_t(result);
   112     const size_t res = size_t(result);
   113     assert(res >= raw, "alignment decreased start addr");
   113     assert(res >= raw, "alignment decreased start addr");
   114     assert(res + prefix_size + suffix_size <= raw + reserve_size,
   114     assert(res + prefix_size + suffix_size <= raw + reserve_size,
   115            "alignment increased end addr");
   115            "alignment increased end addr");
   116     assert((res & prefix_align - 1) == 0, "bad alignment of prefix");
   116     assert((res & (prefix_align - 1)) == 0, "bad alignment of prefix");
   117     assert((res + prefix_size & suffix_align - 1) == 0,
   117     assert(((res + prefix_size) & (suffix_align - 1)) == 0,
   118            "bad alignment of suffix");
   118            "bad alignment of suffix");
   119   }
   119   }
   120 #endif
   120 #endif
   121 
   121 
   122   return result;
   122   return result;
   133     // Different reserve address may be acceptable in other cases
   133     // Different reserve address may be acceptable in other cases
   134     // but for compressed oops heap should be at requested address.
   134     // but for compressed oops heap should be at requested address.
   135     assert(UseCompressedOops, "currently requested address used only for compressed oops");
   135     assert(UseCompressedOops, "currently requested address used only for compressed oops");
   136     if (PrintCompressedOopsMode) {
   136     if (PrintCompressedOopsMode) {
   137       tty->cr();
   137       tty->cr();
   138       tty->print_cr("Reserved memory at not requested address: " PTR_FORMAT " vs " PTR_FORMAT, base, requested_address);
   138       tty->print_cr("Reserved memory not at requested address: " PTR_FORMAT " vs " PTR_FORMAT, base, requested_address);
   139     }
   139     }
   140     // OS ignored requested address. Try different address.
   140     // OS ignored requested address. Try different address.
   141     if (special) {
   141     if (special) {
   142       if (!os::release_memory_special(base, size)) {
   142       if (!os::release_memory_special(base, size)) {
   143         fatal("os::release_memory_special failed");
   143         fatal("os::release_memory_special failed");
   160 {
   160 {
   161   assert(prefix_size != 0, "sanity");
   161   assert(prefix_size != 0, "sanity");
   162   assert(prefix_align != 0, "sanity");
   162   assert(prefix_align != 0, "sanity");
   163   assert(suffix_size != 0, "sanity");
   163   assert(suffix_size != 0, "sanity");
   164   assert(suffix_align != 0, "sanity");
   164   assert(suffix_align != 0, "sanity");
   165   assert((prefix_size & prefix_align - 1) == 0,
   165   assert((prefix_size & (prefix_align - 1)) == 0,
   166     "prefix_size not divisible by prefix_align");
   166     "prefix_size not divisible by prefix_align");
   167   assert((suffix_size & suffix_align - 1) == 0,
   167   assert((suffix_size & (suffix_align - 1)) == 0,
   168     "suffix_size not divisible by suffix_align");
   168     "suffix_size not divisible by suffix_align");
   169   assert((suffix_align & prefix_align - 1) == 0,
   169   assert((suffix_align & (prefix_align - 1)) == 0,
   170     "suffix_align not divisible by prefix_align");
   170     "suffix_align not divisible by prefix_align");
   171 
   171 
   172   // Assert that if noaccess_prefix is used, it is the same as prefix_align.
   172   // Assert that if noaccess_prefix is used, it is the same as prefix_align.
   173   assert(noaccess_prefix == 0 ||
   173   assert(noaccess_prefix == 0 ||
   174          noaccess_prefix == prefix_align, "noaccess prefix wrong");
   174          noaccess_prefix == prefix_align, "noaccess prefix wrong");
   208     addr = os::reserve_memory(size, NULL, prefix_align);
   208     addr = os::reserve_memory(size, NULL, prefix_align);
   209   }
   209   }
   210   if (addr == NULL) return;
   210   if (addr == NULL) return;
   211 
   211 
   212   // Check whether the result has the needed alignment (unlikely unless
   212   // Check whether the result has the needed alignment (unlikely unless
   213   // prefix_align == suffix_align).
   213   // prefix_align < suffix_align).
   214   const size_t ofs = size_t(addr) + adjusted_prefix_size & suffix_align - 1;
   214   const size_t ofs = (size_t(addr) + adjusted_prefix_size) & (suffix_align - 1);
   215   if (ofs != 0) {
   215   if (ofs != 0) {
   216     // Wrong alignment.  Release, allocate more space and do manual alignment.
   216     // Wrong alignment.  Release, allocate more space and do manual alignment.
   217     //
   217     //
   218     // On most operating systems, another allocation with a somewhat larger size
   218     // On most operating systems, another allocation with a somewhat larger size
   219     // will return an address "close to" that of the previous allocation.  The
   219     // will return an address "close to" that of the previous allocation.  The
   230     if (addr == NULL) {
   230     if (addr == NULL) {
   231       // Try an even larger region.  If this fails, address space is exhausted.
   231       // Try an even larger region.  If this fails, address space is exhausted.
   232       addr = reserve_and_align(size + suffix_align, adjusted_prefix_size,
   232       addr = reserve_and_align(size + suffix_align, adjusted_prefix_size,
   233                                prefix_align, suffix_size, suffix_align);
   233                                prefix_align, suffix_size, suffix_align);
   234     }
   234     }
       
   235 
       
   236     if (requested_address != 0 &&
       
   237         failed_to_reserve_as_requested(addr, requested_address, size, false)) {
       
   238       // As a result of the alignment constraints, the allocated addr differs
       
   239       // from the requested address. Return back to the caller who can
       
   240       // take remedial action (like try again without a requested address).
       
   241       assert(_base == NULL, "should be");
       
   242       return;
       
   243     }
   235   }
   244   }
   236 
   245 
   237   _base = addr;
   246   _base = addr;
   238   _size = size;
   247   _size = size;
   239   _alignment = prefix_align;
   248   _alignment = prefix_align;
   243 void ReservedSpace::initialize(size_t size, size_t alignment, bool large,
   252 void ReservedSpace::initialize(size_t size, size_t alignment, bool large,
   244                                char* requested_address,
   253                                char* requested_address,
   245                                const size_t noaccess_prefix,
   254                                const size_t noaccess_prefix,
   246                                bool executable) {
   255                                bool executable) {
   247   const size_t granularity = os::vm_allocation_granularity();
   256   const size_t granularity = os::vm_allocation_granularity();
   248   assert((size & granularity - 1) == 0,
   257   assert((size & (granularity - 1)) == 0,
   249          "size not aligned to os::vm_allocation_granularity()");
   258          "size not aligned to os::vm_allocation_granularity()");
   250   assert((alignment & granularity - 1) == 0,
   259   assert((alignment & (granularity - 1)) == 0,
   251          "alignment not aligned to os::vm_allocation_granularity()");
   260          "alignment not aligned to os::vm_allocation_granularity()");
   252   assert(alignment == 0 || is_power_of_2((intptr_t)alignment),
   261   assert(alignment == 0 || is_power_of_2((intptr_t)alignment),
   253          "not a power of 2");
   262          "not a power of 2");
       
   263 
       
   264   alignment = MAX2(alignment, (size_t)os::vm_page_size());
       
   265 
       
   266   // Assert that if noaccess_prefix is used, it is the same as alignment.
       
   267   assert(noaccess_prefix == 0 ||
       
   268          noaccess_prefix == alignment, "noaccess prefix wrong");
   254 
   269 
   255   _base = NULL;
   270   _base = NULL;
   256   _size = 0;
   271   _size = 0;
   257   _special = false;
   272   _special = false;
   258   _executable = executable;
   273   _executable = executable;
   280       if (failed_to_reserve_as_requested(base, requested_address, size, true)) {
   295       if (failed_to_reserve_as_requested(base, requested_address, size, true)) {
   281         // OS ignored requested address. Try different address.
   296         // OS ignored requested address. Try different address.
   282         return;
   297         return;
   283       }
   298       }
   284       // Check alignment constraints
   299       // Check alignment constraints
   285       if (alignment > 0) {
   300       assert((uintptr_t) base % alignment == 0,
   286         assert((uintptr_t) base % alignment == 0,
   301              "Large pages returned a non-aligned address");
   287                "Large pages returned a non-aligned address");
       
   288       }
       
   289       _special = true;
   302       _special = true;
   290     } else {
   303     } else {
   291       // failed; try to reserve regular memory below
   304       // failed; try to reserve regular memory below
   292       if (UseLargePages && (!FLAG_IS_DEFAULT(UseLargePages) ||
   305       if (UseLargePages && (!FLAG_IS_DEFAULT(UseLargePages) ||
   293                             !FLAG_IS_DEFAULT(LargePageSizeInBytes))) {
   306                             !FLAG_IS_DEFAULT(LargePageSizeInBytes))) {
   319     }
   332     }
   320 
   333 
   321     if (base == NULL) return;
   334     if (base == NULL) return;
   322 
   335 
   323     // Check alignment constraints
   336     // Check alignment constraints
   324     if (alignment > 0 && ((size_t)base & alignment - 1) != 0) {
   337     if ((((size_t)base + noaccess_prefix) & (alignment - 1)) != 0) {
   325       // Base not aligned, retry
   338       // Base not aligned, retry
   326       if (!os::release_memory(base, size)) fatal("os::release_memory failed");
   339       if (!os::release_memory(base, size)) fatal("os::release_memory failed");
   327       // Reserve size large enough to do manual alignment and
   340       // Reserve size large enough to do manual alignment and
   328       // increase size to a multiple of the desired alignment
   341       // increase size to a multiple of the desired alignment
   329       size = align_size_up(size, alignment);
   342       size = align_size_up(size, alignment);
   336         assert(base >= extra_base, "just checking");
   349         assert(base >= extra_base, "just checking");
   337         // Re-reserve the region at the aligned base address.
   350         // Re-reserve the region at the aligned base address.
   338         os::release_memory(extra_base, extra_size);
   351         os::release_memory(extra_base, extra_size);
   339         base = os::reserve_memory(size, base);
   352         base = os::reserve_memory(size, base);
   340       } while (base == NULL);
   353       } while (base == NULL);
       
   354 
       
   355       if (requested_address != 0 &&
       
   356           failed_to_reserve_as_requested(base, requested_address, size, false)) {
       
   357         // As a result of the alignment constraints, the allocated base differs
       
   358         // from the requested address. Return back to the caller who can
       
   359         // take remedial action (like try again without a requested address).
       
   360         assert(_base == NULL, "should be");
       
   361         return;
       
   362       }
   341     }
   363     }
   342   }
   364   }
   343   // Done
   365   // Done
   344   _base = base;
   366   _base = base;
   345   _size = size;
   367   _size = size;
   346   _alignment = MAX2(alignment, (size_t) os::vm_page_size());
   368   _alignment = alignment;
   347   _noaccess_prefix = noaccess_prefix;
   369   _noaccess_prefix = noaccess_prefix;
   348 
   370 
   349   // Assert that if noaccess_prefix is used, it is the same as alignment.
   371   // Assert that if noaccess_prefix is used, it is the same as alignment.
   350   assert(noaccess_prefix == 0 ||
   372   assert(noaccess_prefix == 0 ||
   351          noaccess_prefix == _alignment, "noaccess prefix wrong");
   373          noaccess_prefix == _alignment, "noaccess prefix wrong");