Merge

Fri, 26 Mar 2010 11:10:26 -0400

author
acorn
date
Fri, 26 Mar 2010 11:10:26 -0400
changeset 1765
4a9cc99938e3
parent 1764
84043c7507b9
parent 1751
cc98cc548f51
child 1766
7c358fbb6a84
child 1788
a2ea687fdc7c

Merge

src/cpu/x86/vm/methodHandles_x86.cpp file | annotate | diff | comparison | revisions
src/share/vm/includeDB_core file | annotate | diff | comparison | revisions
src/share/vm/runtime/globals.hpp file | annotate | diff | comparison | revisions
     1.1 --- a/.hgtags	Thu Mar 25 16:54:59 2010 -0700
     1.2 +++ b/.hgtags	Fri Mar 26 11:10:26 2010 -0400
     1.3 @@ -81,3 +81,5 @@
     1.4  fafab5d5349c7c066d677538db67a1ee0fb33bd2 hs15-b05
     1.5  3f370a32906eb5ba993fabd7b4279be7f31052b9 jdk7-b83
     1.6  ffc8d176b84bcfb5ac21302b4feb3b0c0d69b97c jdk7-b84
     1.7 +6c9796468b91dcbb39e09dfa1baf9779ac45eb66 jdk7-b85
     1.8 +418bc80ce13995149eadc9eecbba21d7a9fa02ae hs17-b10
     2.1 --- a/agent/src/os/linux/libproc_impl.c	Thu Mar 25 16:54:59 2010 -0700
     2.2 +++ b/agent/src/os/linux/libproc_impl.c	Fri Mar 26 11:10:26 2010 -0400
     2.3 @@ -174,7 +174,7 @@
     2.4        return NULL;
     2.5     }
     2.6  
     2.7 -   newlib->symtab = build_symtab(newlib->fd);
     2.8 +   newlib->symtab = build_symtab(newlib->fd, libname);
     2.9     if (newlib->symtab == NULL) {
    2.10        print_debug("symbol table build failed for %s\n", newlib->name);
    2.11     }
     3.1 --- a/agent/src/os/linux/symtab.c	Thu Mar 25 16:54:59 2010 -0700
     3.2 +++ b/agent/src/os/linux/symtab.c	Fri Mar 26 11:10:26 2010 -0400
     3.3 @@ -53,8 +53,274 @@
     3.4    struct hsearch_data *hash_table;
     3.5  } symtab_t;
     3.6  
     3.7 -// read symbol table from given fd.
     3.8 -struct symtab* build_symtab(int fd) {
     3.9 +
    3.10 +// Directory that contains global debuginfo files.  In theory it
    3.11 +// should be possible to change this, but in a Java environment there
    3.12 +// is no obvious place to put a user interface to do it.  Maybe this
    3.13 +// could be set with an environment variable.
    3.14 +static const char debug_file_directory[] = "/usr/lib/debug";
    3.15 +
    3.16 +/* The CRC used in gnu_debuglink, retrieved from
    3.17 +   http://sourceware.org/gdb/current/onlinedocs/gdb/Separate-Debug-Files.html#Separate-Debug-Files. */
    3.18 +unsigned int gnu_debuglink_crc32 (unsigned int crc,
    3.19 +                                  unsigned char *buf, size_t len)
    3.20 +{
    3.21 +  static const unsigned int crc32_table[256] =
    3.22 +    {
    3.23 +      0x00000000, 0x77073096, 0xee0e612c, 0x990951ba, 0x076dc419,
    3.24 +      0x706af48f, 0xe963a535, 0x9e6495a3, 0x0edb8832, 0x79dcb8a4,
    3.25 +      0xe0d5e91e, 0x97d2d988, 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07,
    3.26 +      0x90bf1d91, 0x1db71064, 0x6ab020f2, 0xf3b97148, 0x84be41de,
    3.27 +      0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7, 0x136c9856,
    3.28 +      0x646ba8c0, 0xfd62f97a, 0x8a65c9ec, 0x14015c4f, 0x63066cd9,
    3.29 +      0xfa0f3d63, 0x8d080df5, 0x3b6e20c8, 0x4c69105e, 0xd56041e4,
    3.30 +      0xa2677172, 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b,
    3.31 +      0x35b5a8fa, 0x42b2986c, 0xdbbbc9d6, 0xacbcf940, 0x32d86ce3,
    3.32 +      0x45df5c75, 0xdcd60dcf, 0xabd13d59, 0x26d930ac, 0x51de003a,
    3.33 +      0xc8d75180, 0xbfd06116, 0x21b4f4b5, 0x56b3c423, 0xcfba9599,
    3.34 +      0xb8bda50f, 0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924,
    3.35 +      0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d, 0x76dc4190,
    3.36 +      0x01db7106, 0x98d220bc, 0xefd5102a, 0x71b18589, 0x06b6b51f,
    3.37 +      0x9fbfe4a5, 0xe8b8d433, 0x7807c9a2, 0x0f00f934, 0x9609a88e,
    3.38 +      0xe10e9818, 0x7f6a0dbb, 0x086d3d2d, 0x91646c97, 0xe6635c01,
    3.39 +      0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e, 0x6c0695ed,
    3.40 +      0x1b01a57b, 0x8208f4c1, 0xf50fc457, 0x65b0d9c6, 0x12b7e950,
    3.41 +      0x8bbeb8ea, 0xfcb9887c, 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3,
    3.42 +      0xfbd44c65, 0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2,
    3.43 +      0x4adfa541, 0x3dd895d7, 0xa4d1c46d, 0xd3d6f4fb, 0x4369e96a,
    3.44 +      0x346ed9fc, 0xad678846, 0xda60b8d0, 0x44042d73, 0x33031de5,
    3.45 +      0xaa0a4c5f, 0xdd0d7cc9, 0x5005713c, 0x270241aa, 0xbe0b1010,
    3.46 +      0xc90c2086, 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f,
    3.47 +      0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4, 0x59b33d17,
    3.48 +      0x2eb40d81, 0xb7bd5c3b, 0xc0ba6cad, 0xedb88320, 0x9abfb3b6,
    3.49 +      0x03b6e20c, 0x74b1d29a, 0xead54739, 0x9dd277af, 0x04db2615,
    3.50 +      0x73dc1683, 0xe3630b12, 0x94643b84, 0x0d6d6a3e, 0x7a6a5aa8,
    3.51 +      0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1, 0xf00f9344,
    3.52 +      0x8708a3d2, 0x1e01f268, 0x6906c2fe, 0xf762575d, 0x806567cb,
    3.53 +      0x196c3671, 0x6e6b06e7, 0xfed41b76, 0x89d32be0, 0x10da7a5a,
    3.54 +      0x67dd4acc, 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5,
    3.55 +      0xd6d6a3e8, 0xa1d1937e, 0x38d8c2c4, 0x4fdff252, 0xd1bb67f1,
    3.56 +      0xa6bc5767, 0x3fb506dd, 0x48b2364b, 0xd80d2bda, 0xaf0a1b4c,
    3.57 +      0x36034af6, 0x41047a60, 0xdf60efc3, 0xa867df55, 0x316e8eef,
    3.58 +      0x4669be79, 0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236,
    3.59 +      0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f, 0xc5ba3bbe,
    3.60 +      0xb2bd0b28, 0x2bb45a92, 0x5cb36a04, 0xc2d7ffa7, 0xb5d0cf31,
    3.61 +      0x2cd99e8b, 0x5bdeae1d, 0x9b64c2b0, 0xec63f226, 0x756aa39c,
    3.62 +      0x026d930a, 0x9c0906a9, 0xeb0e363f, 0x72076785, 0x05005713,
    3.63 +      0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38, 0x92d28e9b,
    3.64 +      0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21, 0x86d3d2d4, 0xf1d4e242,
    3.65 +      0x68ddb3f8, 0x1fda836e, 0x81be16cd, 0xf6b9265b, 0x6fb077e1,
    3.66 +      0x18b74777, 0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c,
    3.67 +      0x8f659eff, 0xf862ae69, 0x616bffd3, 0x166ccf45, 0xa00ae278,
    3.68 +      0xd70dd2ee, 0x4e048354, 0x3903b3c2, 0xa7672661, 0xd06016f7,
    3.69 +      0x4969474d, 0x3e6e77db, 0xaed16a4a, 0xd9d65adc, 0x40df0b66,
    3.70 +      0x37d83bf0, 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9,
    3.71 +      0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6, 0xbad03605,
    3.72 +      0xcdd70693, 0x54de5729, 0x23d967bf, 0xb3667a2e, 0xc4614ab8,
    3.73 +      0x5d681b02, 0x2a6f2b94, 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b,
    3.74 +      0x2d02ef8d
    3.75 +    };
    3.76 +  unsigned char *end;
    3.77 +
    3.78 +  crc = ~crc & 0xffffffff;
    3.79 +  for (end = buf + len; buf < end; ++buf)
    3.80 +    crc = crc32_table[(crc ^ *buf) & 0xff] ^ (crc >> 8);
    3.81 +  return ~crc & 0xffffffff;
    3.82 +}
    3.83 +
    3.84 +/* Open a debuginfo file and check its CRC.  If it exists and the CRC
    3.85 +   matches return its fd.  */
    3.86 +static int
    3.87 +open_debug_file (const char *pathname, unsigned int crc)
    3.88 +{
    3.89 +  unsigned int file_crc = 0;
    3.90 +  unsigned char buffer[8 * 1024];
    3.91 +
    3.92 +  int fd = pathmap_open(pathname);
    3.93 +
    3.94 +  if (fd < 0)
    3.95 +    return -1;
    3.96 +
    3.97 +  lseek(fd, 0, SEEK_SET);
    3.98 +
    3.99 +  for (;;) {
   3.100 +    int len = read(fd, buffer, sizeof buffer);
   3.101 +    if (len <= 0)
   3.102 +      break;
   3.103 +    file_crc = gnu_debuglink_crc32(file_crc, buffer, len);
   3.104 +  }
   3.105 +
   3.106 +  if (crc == file_crc)
   3.107 +    return fd;
   3.108 +  else {
   3.109 +    close(fd);
   3.110 +    return -1;
   3.111 +  }
   3.112 +}
   3.113 +
   3.114 +/* Find an ELF section.  */
   3.115 +static struct elf_section *find_section_by_name(char *name,
   3.116 +                                                int fd,
   3.117 +                                                ELF_EHDR *ehdr,
   3.118 +                                                ELF_SHDR *shbuf,
   3.119 +                                                struct elf_section *scn_cache)
   3.120 +{
   3.121 +  ELF_SHDR* cursct = NULL;
   3.122 +  char *strtab;
   3.123 +  int cnt;
   3.124 +
   3.125 +  if (scn_cache[ehdr->e_shstrndx].c_data == NULL) {
   3.126 +    if ((scn_cache[ehdr->e_shstrndx].c_data
   3.127 +         = read_section_data(fd, ehdr, cursct)) == NULL) {
   3.128 +      return NULL;
   3.129 +    }
   3.130 +  }
   3.131 +
   3.132 +  strtab = scn_cache[ehdr->e_shstrndx].c_data;
   3.133 +
   3.134 +  for (cursct = shbuf, cnt = 0;
   3.135 +       cnt < ehdr->e_shnum;
   3.136 +       cnt++, cursct++) {
   3.137 +    if (strcmp(cursct->sh_name + strtab, name) == 0) {
   3.138 +      scn_cache[cnt].c_data = read_section_data(fd, ehdr, cursct);
   3.139 +      return &scn_cache[cnt];
   3.140 +    }
   3.141 +  }
   3.142 +
   3.143 +  return NULL;
   3.144 +}
   3.145 +
   3.146 +/* Look for a ".gnu_debuglink" section.  If one exists, try to open a
   3.147 +   suitable debuginfo file.  */
   3.148 +static int open_file_from_debug_link(const char *name,
   3.149 +                                     int fd,
   3.150 +                                     ELF_EHDR *ehdr,
   3.151 +                                     ELF_SHDR *shbuf,
   3.152 +                                     struct elf_section *scn_cache)
   3.153 +{
   3.154 +  int debug_fd;
   3.155 +  struct elf_section *debug_link = find_section_by_name(".gnu_debuglink", fd, ehdr,
   3.156 +                                                        shbuf, scn_cache);
   3.157 +  if (debug_link == NULL)
   3.158 +    return -1;
   3.159 +  char *debug_filename = debug_link->c_data;
   3.160 +  int offset = (strlen(debug_filename) + 4) >> 2;
   3.161 +  static unsigned int crc;
   3.162 +  crc = ((unsigned int*)debug_link->c_data)[offset];
   3.163 +  char *debug_pathname = malloc(strlen(debug_filename)
   3.164 +                                + strlen(name)
   3.165 +                                + strlen(".debug/")
   3.166 +                                + strlen(debug_file_directory)
   3.167 +                                + 2);
   3.168 +  strcpy(debug_pathname, name);
   3.169 +  char *last_slash = strrchr(debug_pathname, '/');
   3.170 +  if (last_slash == NULL)
   3.171 +    return -1;
   3.172 +
   3.173 +  /* Look in the same directory as the object.  */
   3.174 +  strcpy(last_slash+1, debug_filename);
   3.175 +
   3.176 +  debug_fd = open_debug_file(debug_pathname, crc);
   3.177 +  if (debug_fd >= 0) {
   3.178 +    free(debug_pathname);
   3.179 +    return debug_fd;
   3.180 +  }
   3.181 +
   3.182 +  /* Look in a subdirectory named ".debug".  */
   3.183 +  strcpy(last_slash+1, ".debug/");
   3.184 +  strcat(last_slash, debug_filename);
   3.185 +
   3.186 +  debug_fd = open_debug_file(debug_pathname, crc);
   3.187 +  if (debug_fd >= 0) {
   3.188 +    free(debug_pathname);
   3.189 +    return debug_fd;
   3.190 +  }
   3.191 +
   3.192 +  /* Look in /usr/lib/debug + the full pathname.  */
   3.193 +  strcpy(debug_pathname, debug_file_directory);
   3.194 +  strcat(debug_pathname, name);
   3.195 +  last_slash = strrchr(debug_pathname, '/');
   3.196 +  strcpy(last_slash+1, debug_filename);
   3.197 +
   3.198 +  debug_fd = open_debug_file(debug_pathname, crc);
   3.199 +  if (debug_fd >= 0) {
   3.200 +    free(debug_pathname);
   3.201 +    return debug_fd;
   3.202 +  }
   3.203 +
   3.204 +  free(debug_pathname);
   3.205 +  return -1;
   3.206 +}
   3.207 +
   3.208 +static struct symtab* build_symtab_internal(int fd, const char *filename, bool try_debuginfo);
   3.209 +
   3.210 +/* Look for a ".gnu_debuglink" section.  If one exists, try to open a
   3.211 +   suitable debuginfo file and read a symbol table from it.  */
   3.212 +static struct symtab *build_symtab_from_debug_link(const char *name,
   3.213 +                                     int fd,
   3.214 +                                     ELF_EHDR *ehdr,
   3.215 +                                     ELF_SHDR *shbuf,
   3.216 +                                     struct elf_section *scn_cache)
   3.217 +{
   3.218 +  fd = open_file_from_debug_link(name, fd, ehdr, shbuf, scn_cache);
   3.219 +
   3.220 +  if (fd >= 0) {
   3.221 +    struct symtab *symtab = build_symtab_internal(fd, NULL, /* try_debuginfo */ false);
   3.222 +    close(fd);
   3.223 +    return symtab;
   3.224 +  }
   3.225 +
   3.226 +  return NULL;
   3.227 +}
   3.228 +
   3.229 +// Given a build_id, find the associated debuginfo file
   3.230 +static char *
   3.231 +build_id_to_debug_filename (size_t size, unsigned char *data)
   3.232 +{
   3.233 +  char *filename, *s;
   3.234 +
   3.235 +  filename = malloc(strlen (debug_file_directory) + (sizeof "/.build-id/" - 1) + 1
   3.236 +                    + 2 * size + (sizeof ".debug" - 1) + 1);
   3.237 +  s = filename + sprintf (filename, "%s/.build-id/", debug_file_directory);
   3.238 +  if (size > 0)
   3.239 +    {
   3.240 +      size--;
   3.241 +      s += sprintf (s, "%02x", *data++);
   3.242 +    }
   3.243 +  if (size > 0)
   3.244 +    *s++ = '/';
   3.245 +  while (size-- > 0)
   3.246 +    s += sprintf (s, "%02x", *data++);
   3.247 +  strcpy (s, ".debug");
   3.248 +
   3.249 +  return filename;
   3.250 +}
   3.251 +
   3.252 +// Read a build ID note.  Try to open any associated debuginfo file
   3.253 +// and return its symtab
   3.254 +static struct symtab* build_symtab_from_build_id(Elf64_Nhdr *note)
   3.255 +{
   3.256 +  int fd;
   3.257 +  struct symtab *symtab = NULL;
   3.258 +
   3.259 +  unsigned char *bytes
   3.260 +    = (unsigned char*)(note+1) + note->n_namesz;
   3.261 +  unsigned char *filename
   3.262 +    = (build_id_to_debug_filename (note->n_descsz, bytes));
   3.263 +
   3.264 +  fd = pathmap_open(filename);
   3.265 +  if (fd >= 0) {
   3.266 +    symtab = build_symtab_internal(fd, NULL, /* try_debuginfo */ false);
   3.267 +    close(fd);
   3.268 +  }
   3.269 +  free(filename);
   3.270 +
   3.271 +  return symtab;
   3.272 +}
   3.273 +
   3.274 +// read symbol table from given fd.  If try_debuginfo) is true, also
   3.275 +// try to open an associated debuginfo file
   3.276 +static struct symtab* build_symtab_internal(int fd, const char *filename, bool try_debuginfo) {
   3.277    ELF_EHDR ehdr;
   3.278    char *names = NULL;
   3.279    struct symtab* symtab = NULL;
   3.280 @@ -66,6 +332,7 @@
   3.281    ELF_SHDR* cursct = NULL;
   3.282    ELF_PHDR* phbuf = NULL;
   3.283    ELF_PHDR* phdr = NULL;
   3.284 +  int sym_section = SHT_DYNSYM;
   3.285  
   3.286    uintptr_t baseaddr = (uintptr_t)-1;
   3.287  
   3.288 @@ -90,18 +357,23 @@
   3.289  
   3.290    for (cursct = shbuf, cnt = 0; cnt < ehdr.e_shnum; cnt++) {
   3.291      scn_cache[cnt].c_shdr = cursct;
   3.292 -    if (cursct->sh_type == SHT_SYMTAB || cursct->sh_type == SHT_STRTAB) {
   3.293 +    if (cursct->sh_type == SHT_SYMTAB || cursct->sh_type == SHT_STRTAB
   3.294 +        || cursct->sh_type == SHT_NOTE || cursct->sh_type == SHT_DYNSYM) {
   3.295        if ( (scn_cache[cnt].c_data = read_section_data(fd, &ehdr, cursct)) == NULL) {
   3.296           goto quit;
   3.297        }
   3.298      }
   3.299 +    if (cursct->sh_type == SHT_SYMTAB) {
   3.300 +      // Full symbol table available so use that
   3.301 +      sym_section = cursct->sh_type;
   3.302 +    }
   3.303      cursct++;
   3.304    }
   3.305  
   3.306    for (cnt = 1; cnt < ehdr.e_shnum; cnt++) {
   3.307      ELF_SHDR *shdr = scn_cache[cnt].c_shdr;
   3.308  
   3.309 -    if (shdr->sh_type == SHT_SYMTAB) {
   3.310 +    if (shdr->sh_type == sym_section) {
   3.311        ELF_SYM  *syms;
   3.312        int j, n, rslt;
   3.313        size_t size;
   3.314 @@ -163,6 +435,45 @@
   3.315      }
   3.316    }
   3.317  
   3.318 +  // Look for a separate debuginfo file.
   3.319 +  if (try_debuginfo) {
   3.320 +
   3.321 +    // We prefer a debug symtab to an object's own symtab, so look in
   3.322 +    // the debuginfo file.  We stash a copy of the old symtab in case
   3.323 +    // there is no debuginfo.
   3.324 +    struct symtab* prev_symtab = symtab;
   3.325 +    symtab = NULL;
   3.326 +
   3.327 +#ifdef NT_GNU_BUILD_ID
   3.328 +    // First we look for a Build ID
   3.329 +    for (cursct = shbuf, cnt = 0;
   3.330 +         symtab == NULL && cnt < ehdr.e_shnum;
   3.331 +         cnt++) {
   3.332 +      if (cursct->sh_type == SHT_NOTE) {
   3.333 +        Elf64_Nhdr *note = (Elf64_Nhdr *)scn_cache[cnt].c_data;
   3.334 +        if (note->n_type == NT_GNU_BUILD_ID) {
   3.335 +          symtab = build_symtab_from_build_id(note);
   3.336 +        }
   3.337 +      }
   3.338 +      cursct++;
   3.339 +    }
   3.340 +#endif
   3.341 +
   3.342 +    // Then, if that doesn't work, the debug link
   3.343 +    if (symtab == NULL) {
   3.344 +      symtab = build_symtab_from_debug_link(filename, fd, &ehdr, shbuf,
   3.345 +                                            scn_cache);
   3.346 +    }
   3.347 +
   3.348 +    // If we still haven't found a symtab, use the object's own symtab.
   3.349 +    if (symtab != NULL) {
   3.350 +      if (prev_symtab != NULL)
   3.351 +        destroy_symtab(prev_symtab);
   3.352 +    } else {
   3.353 +      symtab = prev_symtab;
   3.354 +    }
   3.355 +  }
   3.356 +
   3.357  quit:
   3.358    if (shbuf) free(shbuf);
   3.359    if (phbuf) free(phbuf);
   3.360 @@ -177,6 +488,11 @@
   3.361    return symtab;
   3.362  }
   3.363  
   3.364 +struct symtab* build_symtab(int fd, const char *filename) {
   3.365 +  return build_symtab_internal(fd, filename, /* try_debuginfo */ true);
   3.366 +}
   3.367 +
   3.368 +
   3.369  void destroy_symtab(struct symtab* symtab) {
   3.370    if (!symtab) return;
   3.371    if (symtab->strs) free(symtab->strs);
     4.1 --- a/agent/src/os/linux/symtab.h	Thu Mar 25 16:54:59 2010 -0700
     4.2 +++ b/agent/src/os/linux/symtab.h	Fri Mar 26 11:10:26 2010 -0400
     4.3 @@ -32,7 +32,7 @@
     4.4  struct symtab;
     4.5  
     4.6  // build symbol table for a given ELF file descriptor
     4.7 -struct symtab* build_symtab(int fd);
     4.8 +struct symtab* build_symtab(int fd, const char *filename);
     4.9  
    4.10  // destroy the symbol table
    4.11  void destroy_symtab(struct symtab* symtab);
     5.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     5.2 +++ b/make/linux/makefiles/build_vm_def.sh	Fri Mar 26 11:10:26 2010 -0400
     5.3 @@ -0,0 +1,5 @@
     5.4 +#!/bin/sh
     5.5 +
     5.6 +nm --defined-only $* | awk '
     5.7 +   { if ($3 ~ /^_ZTV/ || $3 ~ /^gHotSpotVM/) print "\t" $3 ";" }
     5.8 +   '
     6.1 --- a/make/linux/makefiles/mapfile-vers-debug	Thu Mar 25 16:54:59 2010 -0700
     6.2 +++ b/make/linux/makefiles/mapfile-vers-debug	Fri Mar 26 11:10:26 2010 -0400
     6.3 @@ -290,6 +290,9 @@
     6.4  
     6.5                  # This is for Forte Analyzer profiling support.
     6.6                  AsyncGetCallTrace;
     6.7 +
     6.8 +		# INSERT VTABLE SYMBOLS HERE
     6.9 +
    6.10          local:
    6.11                  *;
    6.12  };
     7.1 --- a/make/linux/makefiles/mapfile-vers-product	Thu Mar 25 16:54:59 2010 -0700
     7.2 +++ b/make/linux/makefiles/mapfile-vers-product	Fri Mar 26 11:10:26 2010 -0400
     7.3 @@ -285,6 +285,9 @@
     7.4  
     7.5                  # This is for Forte Analyzer profiling support.
     7.6                  AsyncGetCallTrace;
     7.7 +
     7.8 +		# INSERT VTABLE SYMBOLS HERE
     7.9 +
    7.10          local:
    7.11                  *;
    7.12  };
     8.1 --- a/make/linux/makefiles/vm.make	Thu Mar 25 16:54:59 2010 -0700
     8.2 +++ b/make/linux/makefiles/vm.make	Fri Mar 26 11:10:26 2010 -0400
     8.3 @@ -121,14 +121,21 @@
     8.4  
     8.5  vm_version.o: $(filter-out vm_version.o,$(JVM_OBJ_FILES))
     8.6  
     8.7 -mapfile : $(MAPFILE)
     8.8 +mapfile : $(MAPFILE) vm.def
     8.9  	rm -f $@
    8.10 -	cat $^ > $@
    8.11 +	awk '{ if ($$0 ~ "INSERT VTABLE SYMBOLS HERE")	\
    8.12 +                 { system ("cat vm.def"); }		\
    8.13 +               else					\
    8.14 +                 { print $$0 }				\
    8.15 +             }' > $@ < $(MAPFILE)
    8.16  
    8.17  mapfile_reorder : mapfile $(REORDERFILE)
    8.18  	rm -f $@
    8.19  	cat $^ > $@
    8.20  
    8.21 +vm.def: $(Res_Files) $(Obj_Files)
    8.22 +	sh $(GAMMADIR)/make/linux/makefiles/build_vm_def.sh *.o > $@
    8.23 +
    8.24  ifeq ($(ZERO_LIBARCH), ppc64)
    8.25    STATIC_CXX = false
    8.26  else
     9.1 --- a/src/cpu/sparc/vm/c1_CodeStubs_sparc.cpp	Thu Mar 25 16:54:59 2010 -0700
     9.2 +++ b/src/cpu/sparc/vm/c1_CodeStubs_sparc.cpp	Fri Mar 26 11:10:26 2010 -0400
     9.3 @@ -1,5 +1,5 @@
     9.4  /*
     9.5 - * Copyright 1999-2009 Sun Microsystems, Inc.  All Rights Reserved.
     9.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
     9.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     9.8   *
     9.9   * This code is free software; you can redistribute it and/or modify it
    9.10 @@ -377,6 +377,16 @@
    9.11  
    9.12  }
    9.13  
    9.14 +
    9.15 +void DeoptimizeStub::emit_code(LIR_Assembler* ce) {
    9.16 +  __ bind(_entry);
    9.17 +  __ call(SharedRuntime::deopt_blob()->unpack_with_reexecution());
    9.18 +  __ delayed()->nop();
    9.19 +  ce->add_call_info_here(_info);
    9.20 +  debug_only(__ should_not_reach_here());
    9.21 +}
    9.22 +
    9.23 +
    9.24  void ArrayCopyStub::emit_code(LIR_Assembler* ce) {
    9.25    //---------------slow case: call to native-----------------
    9.26    __ bind(_entry);
    10.1 --- a/src/cpu/sparc/vm/c1_FrameMap_sparc.hpp	Thu Mar 25 16:54:59 2010 -0700
    10.2 +++ b/src/cpu/sparc/vm/c1_FrameMap_sparc.hpp	Fri Mar 26 11:10:26 2010 -0400
    10.3 @@ -1,5 +1,5 @@
    10.4  /*
    10.5 - * Copyright 1999-2006 Sun Microsystems, Inc.  All Rights Reserved.
    10.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    10.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    10.8   *
    10.9   * This code is free software; you can redistribute it and/or modify it
   10.10 @@ -143,3 +143,6 @@
   10.11  
   10.12    static bool is_caller_save_register (LIR_Opr  reg);
   10.13    static bool is_caller_save_register (Register r);
   10.14 +
   10.15 +  // JSR 292
   10.16 +  static LIR_Opr& method_handle_invoke_SP_save_opr() { return L7_opr; }
    11.1 --- a/src/cpu/sparc/vm/c1_LIRAssembler_sparc.cpp	Thu Mar 25 16:54:59 2010 -0700
    11.2 +++ b/src/cpu/sparc/vm/c1_LIRAssembler_sparc.cpp	Fri Mar 26 11:10:26 2010 -0400
    11.3 @@ -378,12 +378,7 @@
    11.4  
    11.5    int offset = code_offset();
    11.6  
    11.7 -  if (compilation()->has_exception_handlers() || compilation()->env()->jvmti_can_post_on_exceptions()) {
    11.8 -    __ call(Runtime1::entry_for(Runtime1::handle_exception_id), relocInfo::runtime_call_type);
    11.9 -    __ delayed()->nop();
   11.10 -  }
   11.11 -
   11.12 -  __ call(Runtime1::entry_for(Runtime1::unwind_exception_id), relocInfo::runtime_call_type);
   11.13 +  __ call(Runtime1::entry_for(Runtime1::handle_exception_id), relocInfo::runtime_call_type);
   11.14    __ delayed()->nop();
   11.15    debug_only(__ stop("should have gone to the caller");)
   11.16    assert(code_offset() - offset <= exception_handler_size, "overflow");
   11.17 @@ -685,29 +680,29 @@
   11.18  }
   11.19  
   11.20  
   11.21 -void LIR_Assembler::call(address entry, relocInfo::relocType rtype, CodeEmitInfo* info) {
   11.22 -  __ call(entry, rtype);
   11.23 +void LIR_Assembler::call(LIR_OpJavaCall* op, relocInfo::relocType rtype) {
   11.24 +  __ call(op->addr(), rtype);
   11.25    // the peephole pass fills the delay slot
   11.26  }
   11.27  
   11.28  
   11.29 -void LIR_Assembler::ic_call(address entry, CodeEmitInfo* info) {
   11.30 +void LIR_Assembler::ic_call(LIR_OpJavaCall* op) {
   11.31    RelocationHolder rspec = virtual_call_Relocation::spec(pc());
   11.32    __ set_oop((jobject)Universe::non_oop_word(), G5_inline_cache_reg);
   11.33    __ relocate(rspec);
   11.34 -  __ call(entry, relocInfo::none);
   11.35 +  __ call(op->addr(), relocInfo::none);
   11.36    // the peephole pass fills the delay slot
   11.37  }
   11.38  
   11.39  
   11.40 -void LIR_Assembler::vtable_call(int vtable_offset, CodeEmitInfo* info) {
   11.41 -  add_debug_info_for_null_check_here(info);
   11.42 +void LIR_Assembler::vtable_call(LIR_OpJavaCall* op) {
   11.43 +  add_debug_info_for_null_check_here(op->info());
   11.44    __ ld_ptr(O0, oopDesc::klass_offset_in_bytes(), G3_scratch);
   11.45 -  if (__ is_simm13(vtable_offset) ) {
   11.46 -    __ ld_ptr(G3_scratch, vtable_offset, G5_method);
   11.47 +  if (__ is_simm13(op->vtable_offset())) {
   11.48 +    __ ld_ptr(G3_scratch, op->vtable_offset(), G5_method);
   11.49    } else {
   11.50      // This will generate 2 instructions
   11.51 -    __ set(vtable_offset, G5_method);
   11.52 +    __ set(op->vtable_offset(), G5_method);
   11.53      // ld_ptr, set_hi, set
   11.54      __ ld_ptr(G3_scratch, G5_method, G5_method);
   11.55    }
   11.56 @@ -717,6 +712,16 @@
   11.57  }
   11.58  
   11.59  
   11.60 +void LIR_Assembler::preserve_SP(LIR_OpJavaCall* op) {
   11.61 +  Unimplemented();
   11.62 +}
   11.63 +
   11.64 +
   11.65 +void LIR_Assembler::restore_SP(LIR_OpJavaCall* op) {
   11.66 +  Unimplemented();
   11.67 +}
   11.68 +
   11.69 +
   11.70  // load with 32-bit displacement
   11.71  int LIR_Assembler::load(Register s, int disp, Register d, BasicType ld_type, CodeEmitInfo *info) {
   11.72    int load_offset = code_offset();
   11.73 @@ -1067,7 +1072,8 @@
   11.74    LIR_Const* c = src->as_constant_ptr();
   11.75    switch (c->type()) {
   11.76      case T_INT:
   11.77 -    case T_FLOAT: {
   11.78 +    case T_FLOAT:
   11.79 +    case T_ADDRESS: {
   11.80        Register src_reg = O7;
   11.81        int value = c->as_jint_bits();
   11.82        if (value == 0) {
   11.83 @@ -1123,7 +1129,8 @@
   11.84    }
   11.85    switch (c->type()) {
   11.86      case T_INT:
   11.87 -    case T_FLOAT: {
   11.88 +    case T_FLOAT:
   11.89 +    case T_ADDRESS: {
   11.90        LIR_Opr tmp = FrameMap::O7_opr;
   11.91        int value = c->as_jint_bits();
   11.92        if (value == 0) {
   11.93 @@ -1195,6 +1202,7 @@
   11.94  
   11.95    switch (c->type()) {
   11.96      case T_INT:
   11.97 +    case T_ADDRESS:
   11.98        {
   11.99          jint con = c->as_jint();
  11.100          if (to_reg->is_single_cpu()) {
    12.1 --- a/src/cpu/sparc/vm/c1_MacroAssembler_sparc.cpp	Thu Mar 25 16:54:59 2010 -0700
    12.2 +++ b/src/cpu/sparc/vm/c1_MacroAssembler_sparc.cpp	Fri Mar 26 11:10:26 2010 -0400
    12.3 @@ -1,5 +1,5 @@
    12.4  /*
    12.5 - * Copyright 1999-2009 Sun Microsystems, Inc.  All Rights Reserved.
    12.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    12.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    12.8   *
    12.9   * This code is free software; you can redistribute it and/or modify it
   12.10 @@ -42,17 +42,6 @@
   12.11  }
   12.12  
   12.13  
   12.14 -void C1_MacroAssembler::method_exit(bool restore_frame) {
   12.15 -  // this code must be structured this way so that the return
   12.16 -  // instruction can be a safepoint.
   12.17 -  if (restore_frame) {
   12.18 -    restore();
   12.19 -  }
   12.20 -  retl();
   12.21 -  delayed()->nop();
   12.22 -}
   12.23 -
   12.24 -
   12.25  void C1_MacroAssembler::explicit_null_check(Register base) {
   12.26    Unimplemented();
   12.27  }
    13.1 --- a/src/cpu/sparc/vm/c1_Runtime1_sparc.cpp	Thu Mar 25 16:54:59 2010 -0700
    13.2 +++ b/src/cpu/sparc/vm/c1_Runtime1_sparc.cpp	Fri Mar 26 11:10:26 2010 -0400
    13.3 @@ -1,5 +1,5 @@
    13.4  /*
    13.5 - * Copyright 1999-2009 Sun Microsystems, Inc.  All Rights Reserved.
    13.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    13.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    13.8   *
    13.9   * This code is free software; you can redistribute it and/or modify it
   13.10 @@ -677,7 +677,7 @@
   13.11          __ add(I7, frame::pc_return_offset, Oissuing_pc->after_save());
   13.12  
   13.13          __ call_VM_leaf(L7_thread_cache, CAST_FROM_FN_PTR(address, SharedRuntime::exception_handler_for_return_address),
   13.14 -                        Oissuing_pc->after_save());
   13.15 +                        G2_thread, Oissuing_pc->after_save());
   13.16          __ verify_not_null_oop(Oexception->after_save());
   13.17          __ jmp(O0, 0);
   13.18          __ delayed()->restore();
   13.19 @@ -985,7 +985,6 @@
   13.20  
   13.21  void Runtime1::generate_handle_exception(StubAssembler* sasm, OopMapSet* oop_maps, OopMap* oop_map, bool) {
   13.22    Label no_deopt;
   13.23 -  Label no_handler;
   13.24  
   13.25    __ verify_not_null_oop(Oexception);
   13.26  
   13.27 @@ -1003,9 +1002,14 @@
   13.28    // whether it had a handler or not we will deoptimize
   13.29    // by entering the deopt blob with a pending exception.
   13.30  
   13.31 +#ifdef ASSERT
   13.32 +  Label done;
   13.33    __ tst(O0);
   13.34 -  __ br(Assembler::zero, false, Assembler::pn, no_handler);
   13.35 +  __ br(Assembler::notZero, false, Assembler::pn, done);
   13.36    __ delayed()->nop();
   13.37 +  __ stop("should have found address");
   13.38 +  __ bind(done);
   13.39 +#endif
   13.40  
   13.41    // restore the registers that were saved at the beginning and jump to the exception handler.
   13.42    restore_live_registers(sasm);
   13.43 @@ -1013,20 +1017,6 @@
   13.44    __ jmp(O0, 0);
   13.45    __ delayed()->restore();
   13.46  
   13.47 -  __ bind(no_handler);
   13.48 -  __ mov(L0, I7); // restore return address
   13.49 -
   13.50 -  // restore exception oop
   13.51 -  __ ld_ptr(G2_thread, in_bytes(JavaThread::exception_oop_offset()), Oexception->after_save());
   13.52 -  __ st_ptr(G0, G2_thread, in_bytes(JavaThread::exception_oop_offset()));
   13.53 -
   13.54 -  __ restore();
   13.55 -
   13.56 -  AddressLiteral exc(Runtime1::entry_for(Runtime1::unwind_exception_id));
   13.57 -  __ jump_to(exc, G4);
   13.58 -  __ delayed()->nop();
   13.59 -
   13.60 -
   13.61    oop_maps->add_gc_map(call_offset, oop_map);
   13.62  }
   13.63  
    14.1 --- a/src/cpu/sparc/vm/interp_masm_sparc.cpp	Thu Mar 25 16:54:59 2010 -0700
    14.2 +++ b/src/cpu/sparc/vm/interp_masm_sparc.cpp	Fri Mar 26 11:10:26 2010 -0400
    14.3 @@ -244,9 +244,10 @@
    14.4  }
    14.5  
    14.6  
    14.7 -void InterpreterMacroAssembler::super_call_VM_leaf(Register thread_cache, address entry_point, Register arg_1) {
    14.8 +void InterpreterMacroAssembler::super_call_VM_leaf(Register thread_cache, address entry_point, Register arg_1, Register arg_2) {
    14.9    mov(arg_1, O0);
   14.10 -  MacroAssembler::call_VM_leaf_base(thread_cache, entry_point, 1);
   14.11 +  mov(arg_2, O1);
   14.12 +  MacroAssembler::call_VM_leaf_base(thread_cache, entry_point, 2);
   14.13  }
   14.14  #endif /* CC_INTERP */
   14.15  
    15.1 --- a/src/cpu/sparc/vm/interp_masm_sparc.hpp	Thu Mar 25 16:54:59 2010 -0700
    15.2 +++ b/src/cpu/sparc/vm/interp_masm_sparc.hpp	Fri Mar 26 11:10:26 2010 -0400
    15.3 @@ -1,5 +1,5 @@
    15.4  /*
    15.5 - * Copyright 1997-2007 Sun Microsystems, Inc.  All Rights Reserved.
    15.6 + * Copyright 1997-2010 Sun Microsystems, Inc.  All Rights Reserved.
    15.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    15.8   *
    15.9   * This code is free software; you can redistribute it and/or modify it
   15.10 @@ -121,7 +121,7 @@
   15.11                       bool check_exception = true);
   15.12  
   15.13  #ifndef CC_INTERP
   15.14 -  void super_call_VM_leaf(Register thread_cache, address entry_point, Register arg_1);
   15.15 +  void super_call_VM_leaf(Register thread_cache, address entry_point, Register arg_1, Register arg_2);
   15.16  
   15.17    // Generate a subtype check: branch to ok_is_subtype if sub_klass is
   15.18    // a subtype of super_klass.  Blows registers tmp1, tmp2 and tmp3.
    16.1 --- a/src/cpu/sparc/vm/stubGenerator_sparc.cpp	Thu Mar 25 16:54:59 2010 -0700
    16.2 +++ b/src/cpu/sparc/vm/stubGenerator_sparc.cpp	Fri Mar 26 11:10:26 2010 -0400
    16.3 @@ -379,7 +379,7 @@
    16.4      __ save_frame(0);             // compensates for compiler weakness
    16.5      __ add(O7->after_save(), frame::pc_return_offset, Lscratch); // save the issuing PC
    16.6      BLOCK_COMMENT("call exception_handler_for_return_address");
    16.7 -    __ call_VM_leaf(L7_thread_cache, CAST_FROM_FN_PTR(address, SharedRuntime::exception_handler_for_return_address), Lscratch);
    16.8 +    __ call_VM_leaf(L7_thread_cache, CAST_FROM_FN_PTR(address, SharedRuntime::exception_handler_for_return_address), G2_thread, Lscratch);
    16.9      __ mov(O0, handler_reg);
   16.10      __ restore();                 // compensates for compiler weakness
   16.11  
    17.1 --- a/src/cpu/sparc/vm/stubRoutines_sparc.hpp	Thu Mar 25 16:54:59 2010 -0700
    17.2 +++ b/src/cpu/sparc/vm/stubRoutines_sparc.hpp	Fri Mar 26 11:10:26 2010 -0400
    17.3 @@ -1,5 +1,5 @@
    17.4  /*
    17.5 - * Copyright 1997-2007 Sun Microsystems, Inc.  All Rights Reserved.
    17.6 + * Copyright 1997-2010 Sun Microsystems, Inc.  All Rights Reserved.
    17.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    17.8   *
    17.9   * This code is free software; you can redistribute it and/or modify it
   17.10 @@ -37,8 +37,13 @@
   17.11  
   17.12  enum /* platform_dependent_constants */ {
   17.13    // %%%%%%%% May be able to shrink this a lot
   17.14 -  code_size1 = 20000,                                        // simply increase if too small (assembler will crash if too small)
   17.15 -  code_size2 = 20000                                         // simply increase if too small (assembler will crash if too small)
   17.16 +  code_size1 = 20000,           // simply increase if too small (assembler will crash if too small)
   17.17 +  code_size2 = 20000            // simply increase if too small (assembler will crash if too small)
   17.18 +};
   17.19 +
   17.20 +// MethodHandles adapters
   17.21 +enum method_handles_platform_dependent_constants {
   17.22 +  method_handles_adapters_code_size = 5000
   17.23  };
   17.24  
   17.25  class Sparc {
    18.1 --- a/src/cpu/sparc/vm/templateInterpreter_sparc.cpp	Thu Mar 25 16:54:59 2010 -0700
    18.2 +++ b/src/cpu/sparc/vm/templateInterpreter_sparc.cpp	Fri Mar 26 11:10:26 2010 -0400
    18.3 @@ -1,5 +1,5 @@
    18.4  /*
    18.5 - * Copyright 1997-2009 Sun Microsystems, Inc.  All Rights Reserved.
    18.6 + * Copyright 1997-2010 Sun Microsystems, Inc.  All Rights Reserved.
    18.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    18.8   *
    18.9   * This code is free software; you can redistribute it and/or modify it
   18.10 @@ -1822,7 +1822,7 @@
   18.11    __ add(issuing_pc_addr, Oissuing_pc->after_save());  // likewise set I1 to a value local to the caller
   18.12    __ super_call_VM_leaf(L7_thread_cache,
   18.13                          CAST_FROM_FN_PTR(address, SharedRuntime::exception_handler_for_return_address),
   18.14 -                        Oissuing_pc->after_save());
   18.15 +                        G2_thread, Oissuing_pc->after_save());
   18.16  
   18.17    // The caller's SP was adjusted upon method entry to accomodate
   18.18    // the callee's non-argument locals. Undo that adjustment.
    19.1 --- a/src/cpu/x86/vm/assembler_x86.cpp	Thu Mar 25 16:54:59 2010 -0700
    19.2 +++ b/src/cpu/x86/vm/assembler_x86.cpp	Fri Mar 26 11:10:26 2010 -0400
    19.3 @@ -8460,6 +8460,7 @@
    19.4    subptr(str1, result); // Restore counter
    19.5    shrl(str1, 1);
    19.6    addl(cnt1, str1);
    19.7 +  decrementl(cnt1);
    19.8    lea(str1, Address(result, 2)); // Reload string
    19.9  
   19.10    // Load substr
    20.1 --- a/src/cpu/x86/vm/c1_CodeStubs_x86.cpp	Thu Mar 25 16:54:59 2010 -0700
    20.2 +++ b/src/cpu/x86/vm/c1_CodeStubs_x86.cpp	Fri Mar 26 11:10:26 2010 -0400
    20.3 @@ -1,5 +1,5 @@
    20.4  /*
    20.5 - * Copyright 1999-2008 Sun Microsystems, Inc.  All Rights Reserved.
    20.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    20.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    20.8   *
    20.9   * This code is free software; you can redistribute it and/or modify it
   20.10 @@ -373,6 +373,14 @@
   20.11  }
   20.12  
   20.13  
   20.14 +void DeoptimizeStub::emit_code(LIR_Assembler* ce) {
   20.15 +  __ bind(_entry);
   20.16 +  __ call(RuntimeAddress(SharedRuntime::deopt_blob()->unpack_with_reexecution()));
   20.17 +  ce->add_call_info_here(_info);
   20.18 +  debug_only(__ should_not_reach_here());
   20.19 +}
   20.20 +
   20.21 +
   20.22  void ImplicitNullCheckStub::emit_code(LIR_Assembler* ce) {
   20.23    ce->compilation()->implicit_exception_table()->append(_offset, __ offset());
   20.24    __ bind(_entry);
    21.1 --- a/src/cpu/x86/vm/c1_FrameMap_x86.hpp	Thu Mar 25 16:54:59 2010 -0700
    21.2 +++ b/src/cpu/x86/vm/c1_FrameMap_x86.hpp	Fri Mar 26 11:10:26 2010 -0400
    21.3 @@ -1,5 +1,5 @@
    21.4  /*
    21.5 - * Copyright 1999-2008 Sun Microsystems, Inc.  All Rights Reserved.
    21.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    21.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    21.8   *
    21.9   * This code is free software; you can redistribute it and/or modify it
   21.10 @@ -126,3 +126,6 @@
   21.11      assert(i >= 0 && i < nof_caller_save_xmm_regs, "out of bounds");
   21.12      return _caller_save_xmm_regs[i];
   21.13    }
   21.14 +
   21.15 +  // JSR 292
   21.16 +  static LIR_Opr& method_handle_invoke_SP_save_opr() { return rbp_opr; }
    22.1 --- a/src/cpu/x86/vm/c1_LIRAssembler_x86.cpp	Thu Mar 25 16:54:59 2010 -0700
    22.2 +++ b/src/cpu/x86/vm/c1_LIRAssembler_x86.cpp	Fri Mar 26 11:10:26 2010 -0400
    22.3 @@ -436,40 +436,18 @@
    22.4  
    22.5    int offset = code_offset();
    22.6  
    22.7 -  // if the method does not have an exception handler, then there is
    22.8 -  // no reason to search for one
    22.9 -  if (compilation()->has_exception_handlers() || compilation()->env()->jvmti_can_post_on_exceptions()) {
   22.10 -    // the exception oop and pc are in rax, and rdx
   22.11 -    // no other registers need to be preserved, so invalidate them
   22.12 -    __ invalidate_registers(false, true, true, false, true, true);
   22.13 -
   22.14 -    // check that there is really an exception
   22.15 -    __ verify_not_null_oop(rax);
   22.16 -
   22.17 -    // search an exception handler (rax: exception oop, rdx: throwing pc)
   22.18 -    __ call(RuntimeAddress(Runtime1::entry_for(Runtime1::handle_exception_nofpu_id)));
   22.19 -
   22.20 -    // if the call returns here, then the exception handler for particular
   22.21 -    // exception doesn't exist -> unwind activation and forward exception to caller
   22.22 -  }
   22.23 -
   22.24 -  // the exception oop is in rax,
   22.25 +  // the exception oop and pc are in rax, and rdx
   22.26    // no other registers need to be preserved, so invalidate them
   22.27 -  __ invalidate_registers(false, true, true, true, true, true);
   22.28 +  __ invalidate_registers(false, true, true, false, true, true);
   22.29  
   22.30    // check that there is really an exception
   22.31    __ verify_not_null_oop(rax);
   22.32  
   22.33 -  // unlock the receiver/klass if necessary
   22.34 -  // rax,: exception
   22.35 -  ciMethod* method = compilation()->method();
   22.36 -  if (method->is_synchronized() && GenerateSynchronizationCode) {
   22.37 -    monitorexit(FrameMap::rbx_oop_opr, FrameMap::rcx_opr, SYNC_header, 0, rax);
   22.38 -  }
   22.39 -
   22.40 -  // unwind activation and forward exception to caller
   22.41 -  // rax,: exception
   22.42 -  __ jump(RuntimeAddress(Runtime1::entry_for(Runtime1::unwind_exception_id)));
   22.43 +  // search an exception handler (rax: exception oop, rdx: throwing pc)
   22.44 +  __ call(RuntimeAddress(Runtime1::entry_for(Runtime1::handle_exception_nofpu_id)));
   22.45 +
   22.46 +  __ stop("should not reach here");
   22.47 +
   22.48    assert(code_offset() - offset <= exception_handler_size, "overflow");
   22.49    __ end_a_stub();
   22.50  
   22.51 @@ -495,8 +473,10 @@
   22.52  
   22.53    int offset = code_offset();
   22.54    InternalAddress here(__ pc());
   22.55 +
   22.56    __ pushptr(here.addr());
   22.57    __ jump(RuntimeAddress(SharedRuntime::deopt_blob()->unpack()));
   22.58 +
   22.59    assert(code_offset() - offset <= deopt_handler_size, "overflow");
   22.60    __ end_a_stub();
   22.61  
   22.62 @@ -593,7 +573,7 @@
   22.63    }
   22.64  
   22.65    // Pop the stack before the safepoint code
   22.66 -  __ leave();
   22.67 +  __ remove_frame(initial_frame_size_in_bytes());
   22.68  
   22.69    bool result_is_oop = result->is_valid() ? result->is_oop() : false;
   22.70  
   22.71 @@ -648,7 +628,8 @@
   22.72    LIR_Const* c = src->as_constant_ptr();
   22.73  
   22.74    switch (c->type()) {
   22.75 -    case T_INT: {
   22.76 +    case T_INT:
   22.77 +    case T_ADDRESS: {
   22.78        assert(patch_code == lir_patch_none, "no patching handled here");
   22.79        __ movl(dest->as_register(), c->as_jint());
   22.80        break;
   22.81 @@ -731,6 +712,7 @@
   22.82    switch (c->type()) {
   22.83      case T_INT:  // fall through
   22.84      case T_FLOAT:
   22.85 +    case T_ADDRESS:
   22.86        __ movl(frame_map()->address_for_slot(dest->single_stack_ix()), c->as_jint_bits());
   22.87        break;
   22.88  
   22.89 @@ -766,6 +748,7 @@
   22.90    switch (type) {
   22.91      case T_INT:    // fall through
   22.92      case T_FLOAT:
   22.93 +    case T_ADDRESS:
   22.94        __ movl(as_Address(addr), c->as_jint_bits());
   22.95        break;
   22.96  
   22.97 @@ -2738,6 +2721,7 @@
   22.98      switch (code) {
   22.99        case lir_static_call:
  22.100        case lir_optvirtual_call:
  22.101 +      case lir_dynamic_call:
  22.102          offset += NativeCall::displacement_offset;
  22.103          break;
  22.104        case lir_icvirtual_call:
  22.105 @@ -2753,30 +2737,41 @@
  22.106  }
  22.107  
  22.108  
  22.109 -void LIR_Assembler::call(address entry, relocInfo::relocType rtype, CodeEmitInfo* info) {
  22.110 +void LIR_Assembler::call(LIR_OpJavaCall* op, relocInfo::relocType rtype) {
  22.111    assert(!os::is_MP() || (__ offset() + NativeCall::displacement_offset) % BytesPerWord == 0,
  22.112           "must be aligned");
  22.113 -  __ call(AddressLiteral(entry, rtype));
  22.114 -  add_call_info(code_offset(), info);
  22.115 +  __ call(AddressLiteral(op->addr(), rtype));
  22.116 +  add_call_info(code_offset(), op->info(), op->is_method_handle_invoke());
  22.117  }
  22.118  
  22.119  
  22.120 -void LIR_Assembler::ic_call(address entry, CodeEmitInfo* info) {
  22.121 +void LIR_Assembler::ic_call(LIR_OpJavaCall* op) {
  22.122    RelocationHolder rh = virtual_call_Relocation::spec(pc());
  22.123    __ movoop(IC_Klass, (jobject)Universe::non_oop_word());
  22.124    assert(!os::is_MP() ||
  22.125           (__ offset() + NativeCall::displacement_offset) % BytesPerWord == 0,
  22.126           "must be aligned");
  22.127 -  __ call(AddressLiteral(entry, rh));
  22.128 -  add_call_info(code_offset(), info);
  22.129 +  __ call(AddressLiteral(op->addr(), rh));
  22.130 +  add_call_info(code_offset(), op->info(), op->is_method_handle_invoke());
  22.131  }
  22.132  
  22.133  
  22.134  /* Currently, vtable-dispatch is only enabled for sparc platforms */
  22.135 -void LIR_Assembler::vtable_call(int vtable_offset, CodeEmitInfo* info) {
  22.136 +void LIR_Assembler::vtable_call(LIR_OpJavaCall* op) {
  22.137    ShouldNotReachHere();
  22.138  }
  22.139  
  22.140 +
  22.141 +void LIR_Assembler::preserve_SP(LIR_OpJavaCall* op) {
  22.142 +  __ movptr(FrameMap::method_handle_invoke_SP_save_opr()->as_register(), rsp);
  22.143 +}
  22.144 +
  22.145 +
  22.146 +void LIR_Assembler::restore_SP(LIR_OpJavaCall* op) {
  22.147 +  __ movptr(rsp, FrameMap::method_handle_invoke_SP_save_opr()->as_register());
  22.148 +}
  22.149 +
  22.150 +
  22.151  void LIR_Assembler::emit_static_call_stub() {
  22.152    address call_pc = __ pc();
  22.153    address stub = __ start_a_stub(call_stub_size);
  22.154 @@ -2829,10 +2824,12 @@
  22.155      } else {
  22.156        unwind_id = Runtime1::handle_exception_nofpu_id;
  22.157      }
  22.158 +    __ call(RuntimeAddress(Runtime1::entry_for(unwind_id)));
  22.159    } else {
  22.160 -    unwind_id = Runtime1::unwind_exception_id;
  22.161 +    // remove the activation
  22.162 +    __ remove_frame(initial_frame_size_in_bytes());
  22.163 +    __ jump(RuntimeAddress(Runtime1::entry_for(Runtime1::unwind_exception_id)));
  22.164    }
  22.165 -  __ call(RuntimeAddress(Runtime1::entry_for(unwind_id)));
  22.166  
  22.167    // enough room for two byte trap
  22.168    __ nop();
    23.1 --- a/src/cpu/x86/vm/c1_MacroAssembler_x86.cpp	Thu Mar 25 16:54:59 2010 -0700
    23.2 +++ b/src/cpu/x86/vm/c1_MacroAssembler_x86.cpp	Fri Mar 26 11:10:26 2010 -0400
    23.3 @@ -1,5 +1,5 @@
    23.4  /*
    23.5 - * Copyright 1999-2009 Sun Microsystems, Inc.  All Rights Reserved.
    23.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    23.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    23.8   *
    23.9   * This code is free software; you can redistribute it and/or modify it
   23.10 @@ -317,14 +317,6 @@
   23.11  }
   23.12  
   23.13  
   23.14 -void C1_MacroAssembler::method_exit(bool restore_frame) {
   23.15 -  if (restore_frame) {
   23.16 -    leave();
   23.17 -  }
   23.18 -  ret(0);
   23.19 -}
   23.20 -
   23.21 -
   23.22  void C1_MacroAssembler::build_frame(int frame_size_in_bytes) {
   23.23    // Make sure there is enough stack space for this method's activation.
   23.24    // Note that we do this before doing an enter(). This matches the
   23.25 @@ -333,7 +325,7 @@
   23.26    // between the two compilers.
   23.27    generate_stack_overflow_check(frame_size_in_bytes);
   23.28  
   23.29 -  enter();
   23.30 +  push(rbp);
   23.31  #ifdef TIERED
   23.32    // c2 leaves fpu stack dirty. Clean it on entry
   23.33    if (UseSSE < 2 ) {
   23.34 @@ -344,6 +336,12 @@
   23.35  }
   23.36  
   23.37  
   23.38 +void C1_MacroAssembler::remove_frame(int frame_size_in_bytes) {
   23.39 +  increment(rsp, frame_size_in_bytes);  // Does not emit code for frame_size == 0
   23.40 +  pop(rbp);
   23.41 +}
   23.42 +
   23.43 +
   23.44  void C1_MacroAssembler::unverified_entry(Register receiver, Register ic_klass) {
   23.45    if (C1Breakpoint) int3();
   23.46    inline_cache_check(receiver, ic_klass);
    24.1 --- a/src/cpu/x86/vm/c1_Runtime1_x86.cpp	Thu Mar 25 16:54:59 2010 -0700
    24.2 +++ b/src/cpu/x86/vm/c1_Runtime1_x86.cpp	Fri Mar 26 11:10:26 2010 -0400
    24.3 @@ -1,5 +1,5 @@
    24.4  /*
    24.5 - * Copyright 1999-2009 Sun Microsystems, Inc.  All Rights Reserved.
    24.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    24.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    24.8   *
    24.9   * This code is free software; you can redistribute it and/or modify it
   24.10 @@ -688,18 +688,21 @@
   24.11    int call_offset = __ call_RT(noreg, noreg, CAST_FROM_FN_PTR(address, exception_handler_for_pc));
   24.12    oop_maps->add_gc_map(call_offset, oop_map);
   24.13  
   24.14 -  // rax,: handler address or NULL if no handler exists
   24.15 +  // rax,: handler address
   24.16    //      will be the deopt blob if nmethod was deoptimized while we looked up
   24.17    //      handler regardless of whether handler existed in the nmethod.
   24.18  
   24.19    // only rax, is valid at this time, all other registers have been destroyed by the runtime call
   24.20    __ invalidate_registers(false, true, true, true, true, true);
   24.21  
   24.22 +#ifdef ASSERT
   24.23    // Do we have an exception handler in the nmethod?
   24.24 -  Label no_handler;
   24.25    Label done;
   24.26    __ testptr(rax, rax);
   24.27 -  __ jcc(Assembler::zero, no_handler);
   24.28 +  __ jcc(Assembler::notZero, done);
   24.29 +  __ stop("no handler found");
   24.30 +  __ bind(done);
   24.31 +#endif
   24.32  
   24.33    // exception handler found
   24.34    // patch the return address -> the stub will directly return to the exception handler
   24.35 @@ -712,36 +715,14 @@
   24.36    __ leave();
   24.37    __ ret(0);
   24.38  
   24.39 -  __ bind(no_handler);
   24.40 -  // no exception handler found in this method, so the exception is
   24.41 -  // forwarded to the caller (using the unwind code of the nmethod)
   24.42 -  // there is no need to restore the registers
   24.43 -
   24.44 -  // restore the real return address that was saved before the RT-call
   24.45 -  __ movptr(real_return_addr, Address(rsp, temp_1_off * VMRegImpl::stack_slot_size));
   24.46 -  __ movptr(Address(rbp, 1*BytesPerWord), real_return_addr);
   24.47 -
   24.48 -  // load address of JavaThread object for thread-local data
   24.49 -  NOT_LP64(__ get_thread(thread);)
   24.50 -  // restore exception oop into rax, (convention for unwind code)
   24.51 -  __ movptr(exception_oop, Address(thread, JavaThread::exception_oop_offset()));
   24.52 -
   24.53 -  // clear exception fields in JavaThread because they are no longer needed
   24.54 -  // (fields must be cleared because they are processed by GC otherwise)
   24.55 -  __ movptr(Address(thread, JavaThread::exception_oop_offset()), NULL_WORD);
   24.56 -  __ movptr(Address(thread, JavaThread::exception_pc_offset()), NULL_WORD);
   24.57 -
   24.58 -  // pop the stub frame off
   24.59 -  __ leave();
   24.60 -
   24.61 -  generate_unwind_exception(sasm);
   24.62 -  __ stop("should not reach here");
   24.63  }
   24.64  
   24.65  
   24.66  void Runtime1::generate_unwind_exception(StubAssembler *sasm) {
   24.67    // incoming parameters
   24.68    const Register exception_oop = rax;
   24.69 +  // callee-saved copy of exception_oop during runtime call
   24.70 +  const Register exception_oop_callee_saved = NOT_LP64(rsi) LP64_ONLY(r14);
   24.71    // other registers used in this stub
   24.72    const Register exception_pc = rdx;
   24.73    const Register handler_addr = rbx;
   24.74 @@ -769,38 +750,39 @@
   24.75    // clear the FPU stack in case any FPU results are left behind
   24.76    __ empty_FPU_stack();
   24.77  
   24.78 -  // leave activation of nmethod
   24.79 -  __ leave();
   24.80 -  // store return address (is on top of stack after leave)
   24.81 +  // save exception_oop in callee-saved register to preserve it during runtime calls
   24.82 +  __ verify_not_null_oop(exception_oop);
   24.83 +  __ movptr(exception_oop_callee_saved, exception_oop);
   24.84 +
   24.85 +  NOT_LP64(__ get_thread(thread);)
   24.86 +  // Get return address (is on top of stack after leave).
   24.87    __ movptr(exception_pc, Address(rsp, 0));
   24.88  
   24.89 -  __ verify_oop(exception_oop);
   24.90 +  // search the exception handler address of the caller (using the return address)
   24.91 +  __ call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::exception_handler_for_return_address), thread, exception_pc);
   24.92 +  // rax: exception handler address of the caller
   24.93  
   24.94 -  // save exception oop from rax, to stack before call
   24.95 -  __ push(exception_oop);
   24.96 -
   24.97 -  // search the exception handler address of the caller (using the return address)
   24.98 -  __ call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::exception_handler_for_return_address), exception_pc);
   24.99 -  // rax,: exception handler address of the caller
  24.100 -
  24.101 -  // only rax, is valid at this time, all other registers have been destroyed by the call
  24.102 -  __ invalidate_registers(false, true, true, true, true, true);
  24.103 +  // Only RAX and RSI are valid at this time, all other registers have been destroyed by the call.
  24.104 +  __ invalidate_registers(false, true, true, true, false, true);
  24.105  
  24.106    // move result of call into correct register
  24.107    __ movptr(handler_addr, rax);
  24.108  
  24.109 -  // restore exception oop in rax, (required convention of exception handler)
  24.110 -  __ pop(exception_oop);
  24.111 +  // Restore exception oop to RAX (required convention of exception handler).
  24.112 +  __ movptr(exception_oop, exception_oop_callee_saved);
  24.113  
  24.114 -  __ verify_oop(exception_oop);
  24.115 +  // verify that there is really a valid exception in rax
  24.116 +  __ verify_not_null_oop(exception_oop);
  24.117  
  24.118    // get throwing pc (= return address).
  24.119    // rdx has been destroyed by the call, so it must be set again
  24.120    // the pop is also necessary to simulate the effect of a ret(0)
  24.121    __ pop(exception_pc);
  24.122  
  24.123 -  // verify that that there is really a valid exception in rax,
  24.124 -  __ verify_not_null_oop(exception_oop);
  24.125 +  // Restore SP from BP if the exception PC is a MethodHandle call site.
  24.126 +  NOT_LP64(__ get_thread(thread);)
  24.127 +  __ cmpl(Address(thread, JavaThread::is_method_handle_exception_offset()), 0);
  24.128 +  __ cmovptr(Assembler::notEqual, rsp, rbp);
  24.129  
  24.130    // continue at exception handler (return address removed)
  24.131    // note: do *not* remove arguments when unwinding the
  24.132 @@ -808,9 +790,9 @@
  24.133    //       all arguments on the stack when entering the
  24.134    //       runtime to determine the exception handler
  24.135    //       (GC happens at call site with arguments!)
  24.136 -  // rax,: exception oop
  24.137 +  // rax: exception oop
  24.138    // rdx: throwing pc
  24.139 -  // rbx,: exception handler
  24.140 +  // rbx: exception handler
  24.141    __ jmp(handler_addr);
  24.142  }
  24.143  
    25.1 --- a/src/cpu/x86/vm/methodHandles_x86.cpp	Thu Mar 25 16:54:59 2010 -0700
    25.2 +++ b/src/cpu/x86/vm/methodHandles_x86.cpp	Fri Mar 26 11:10:26 2010 -0400
    25.3 @@ -1,5 +1,5 @@
    25.4  /*
    25.5 - * Copyright 1997-2009 Sun Microsystems, Inc.  All Rights Reserved.
    25.6 + * Copyright 1997-2010 Sun Microsystems, Inc.  All Rights Reserved.
    25.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    25.8   *
    25.9   * This code is free software; you can redistribute it and/or modify it
   25.10 @@ -60,13 +60,13 @@
   25.11  }
   25.12  
   25.13  #ifdef ASSERT
   25.14 -static void verify_argslot(MacroAssembler* _masm, Register rax_argslot,
   25.15 +static void verify_argslot(MacroAssembler* _masm, Register argslot_reg,
   25.16                             const char* error_message) {
   25.17    // Verify that argslot lies within (rsp, rbp].
   25.18    Label L_ok, L_bad;
   25.19 -  __ cmpptr(rax_argslot, rbp);
   25.20 +  __ cmpptr(argslot_reg, rbp);
   25.21    __ jccb(Assembler::above, L_bad);
   25.22 -  __ cmpptr(rsp, rax_argslot);
   25.23 +  __ cmpptr(rsp, argslot_reg);
   25.24    __ jccb(Assembler::below, L_ok);
   25.25    __ bind(L_bad);
   25.26    __ stop(error_message);
   25.27 @@ -178,22 +178,6 @@
   25.28  
   25.29    // Now move the argslot down, to point to the opened-up space.
   25.30    __ lea(rax_argslot, Address(rax_argslot, arg_slots, Address::times_ptr));
   25.31 -
   25.32 -  if (TaggedStackInterpreter && arg_mask != _INSERT_NO_MASK) {
   25.33 -    // The caller has specified a bitmask of tags to put into the opened space.
   25.34 -    // This only works when the arg_slots value is an assembly-time constant.
   25.35 -    int constant_arg_slots = arg_slots.as_constant() / stack_move_unit();
   25.36 -    int tag_offset = Interpreter::tag_offset_in_bytes() - Interpreter::value_offset_in_bytes();
   25.37 -    for (int slot = 0; slot < constant_arg_slots; slot++) {
   25.38 -      BasicType slot_type   = ((arg_mask & (1 << slot)) == 0 ? T_OBJECT : T_INT);
   25.39 -      int       slot_offset = Interpreter::stackElementSize() * slot;
   25.40 -      Address   tag_addr(rax_argslot, slot_offset + tag_offset);
   25.41 -      __ movptr(tag_addr, frame::tag_for_basic_type(slot_type));
   25.42 -    }
   25.43 -    // Note that the new argument slots are tagged properly but contain
   25.44 -    // garbage at this point.  The value portions must be initialized
   25.45 -    // by the caller.  (Especially references!)
   25.46 -  }
   25.47  }
   25.48  
   25.49  // Helper to remove argument slots from the stack.
   25.50 @@ -206,18 +190,9 @@
   25.51                               (!arg_slots.is_register() ? rsp : arg_slots.as_register()));
   25.52  
   25.53  #ifdef ASSERT
   25.54 -  {
   25.55 -    // Verify that [argslot..argslot+size) lies within (rsp, rbp).
   25.56 -    Label L_ok, L_bad;
   25.57 -    __ lea(rbx_temp, Address(rax_argslot, arg_slots, Address::times_ptr));
   25.58 -    __ cmpptr(rbx_temp, rbp);
   25.59 -    __ jccb(Assembler::above, L_bad);
   25.60 -    __ cmpptr(rsp, rax_argslot);
   25.61 -    __ jccb(Assembler::below, L_ok);
   25.62 -    __ bind(L_bad);
   25.63 -    __ stop("deleted argument(s) must fall within current frame");
   25.64 -    __ bind(L_ok);
   25.65 -  }
   25.66 +  // Verify that [argslot..argslot+size) lies within (rsp, rbp).
   25.67 +  __ lea(rbx_temp, Address(rax_argslot, arg_slots, Address::times_ptr));
   25.68 +  verify_argslot(_masm, rbx_temp, "deleted argument(s) must fall within current frame");
   25.69    if (arg_slots.is_register()) {
   25.70      Label L_ok, L_bad;
   25.71      __ cmpptr(arg_slots.as_register(), (int32_t) NULL_WORD);
   25.72 @@ -321,12 +296,6 @@
   25.73    Address rcx_amh_conversion( rcx_recv, sun_dyn_AdapterMethodHandle::conversion_offset_in_bytes() );
   25.74    Address vmarg;                // __ argument_address(vmargslot)
   25.75  
   25.76 -  int tag_offset = -1;
   25.77 -  if (TaggedStackInterpreter) {
   25.78 -    tag_offset = Interpreter::tag_offset_in_bytes() - Interpreter::value_offset_in_bytes();
   25.79 -    assert(tag_offset = wordSize, "stack grows as expected");
   25.80 -  }
   25.81 -
   25.82    const int java_mirror_offset = klassOopDesc::klass_part_offset_in_bytes() + Klass::java_mirror_offset_in_bytes();
   25.83  
   25.84    if (have_entry(ek)) {
   25.85 @@ -372,11 +341,8 @@
   25.86        __ mov(rsp, rsi);   // cut the stack back to where the caller started
   25.87  
   25.88        // Repush the arguments as if coming from the interpreter.
   25.89 -      if (TaggedStackInterpreter)  __ push(frame::tag_for_basic_type(T_INT));
   25.90        __ push(rdx_code);
   25.91 -      if (TaggedStackInterpreter)  __ push(frame::tag_for_basic_type(T_OBJECT));
   25.92        __ push(rcx_fail);
   25.93 -      if (TaggedStackInterpreter)  __ push(frame::tag_for_basic_type(T_OBJECT));
   25.94        __ push(rax_want);
   25.95  
   25.96        Register rbx_method = rbx_temp;
   25.97 @@ -397,7 +363,6 @@
   25.98        // Do something that is at least causes a valid throw from the interpreter.
   25.99        __ bind(no_method);
  25.100        __ pop(rax_want);
  25.101 -      if (TaggedStackInterpreter)  __ pop(rcx_fail);
  25.102        __ pop(rcx_fail);
  25.103        __ push(rax_want);
  25.104        __ push(rcx_fail);
  25.105 @@ -510,18 +475,10 @@
  25.106    case _bound_long_direct_mh:
  25.107      {
  25.108        bool direct_to_method = (ek >= _bound_ref_direct_mh);
  25.109 -      BasicType arg_type = T_ILLEGAL;
  25.110 -      if (ek == _bound_long_mh || ek == _bound_long_direct_mh) {
  25.111 -        arg_type = T_LONG;
  25.112 -      } else if (ek == _bound_int_mh || ek == _bound_int_direct_mh) {
  25.113 -        arg_type = T_INT;
  25.114 -      } else {
  25.115 -        assert(ek == _bound_ref_mh || ek == _bound_ref_direct_mh, "must be ref");
  25.116 -        arg_type = T_OBJECT;
  25.117 -      }
  25.118 -      int arg_slots = type2size[arg_type];
  25.119 -      int arg_mask  = (arg_type == T_OBJECT ? _INSERT_REF_MASK :
  25.120 -                       arg_slots == 1       ? _INSERT_INT_MASK :  _INSERT_LONG_MASK);
  25.121 +      BasicType arg_type  = T_ILLEGAL;
  25.122 +      int       arg_mask  = _INSERT_NO_MASK;
  25.123 +      int       arg_slots = -1;
  25.124 +      get_ek_bound_mh_info(ek, arg_type, arg_mask, arg_slots);
  25.125  
  25.126        // make room for the new argument:
  25.127        __ movl(rax_argslot, rcx_bmh_vmargslot);
  25.128 @@ -660,13 +617,10 @@
  25.129          }
  25.130          break;
  25.131        default:
  25.132 -        assert(false, "");
  25.133 +        ShouldNotReachHere();
  25.134        }
  25.135 -      goto finish_int_conversion;
  25.136 -    }
  25.137  
  25.138 -  finish_int_conversion:
  25.139 -    {
  25.140 +      // Do the requested conversion and store the value.
  25.141        Register rbx_vminfo = rbx_temp;
  25.142        __ movl(rbx_vminfo, rcx_amh_conversion);
  25.143        assert(CONV_VMINFO_SHIFT == 0, "preshifted");
  25.144 @@ -692,7 +646,7 @@
  25.145        __ shrl(rdx_temp /*, rcx*/);
  25.146  
  25.147        __ bind(done);
  25.148 -      __ movl(vmarg, rdx_temp);
  25.149 +      __ movl(vmarg, rdx_temp);  // Store the value.
  25.150        __ xchgptr(rcx, rbx_vminfo);                // restore rcx_recv
  25.151  
  25.152        __ jump_to_method_handle_entry(rcx_recv, rdx_temp);
  25.153 @@ -715,9 +669,14 @@
  25.154        switch (ek) {
  25.155        case _adapter_opt_i2l:
  25.156          {
  25.157 +#ifdef _LP64
  25.158 +          __ movslq(rdx_temp, vmarg1);  // Load sign-extended
  25.159 +          __ movq(vmarg1, rdx_temp);    // Store into first slot
  25.160 +#else
  25.161            __ movl(rdx_temp, vmarg1);
  25.162 -          __ sarl(rdx_temp, 31);  // __ extend_sign()
  25.163 +          __ sarl(rdx_temp, BitsPerInt - 1);  // __ extend_sign()
  25.164            __ movl(vmarg2, rdx_temp); // store second word
  25.165 +#endif
  25.166          }
  25.167          break;
  25.168        case _adapter_opt_unboxl:
  25.169 @@ -727,14 +686,19 @@
  25.170            int value_offset = java_lang_boxing_object::value_offset_in_bytes(T_LONG);
  25.171            assert(value_offset == java_lang_boxing_object::value_offset_in_bytes(T_DOUBLE), "");
  25.172            __ null_check(rdx_temp, value_offset);
  25.173 +#ifdef _LP64
  25.174 +          __ movq(rbx_temp, Address(rdx_temp, value_offset));
  25.175 +          __ movq(vmarg1, rbx_temp);
  25.176 +#else
  25.177            __ movl(rbx_temp, Address(rdx_temp, value_offset + 0*BytesPerInt));
  25.178            __ movl(rdx_temp, Address(rdx_temp, value_offset + 1*BytesPerInt));
  25.179            __ movl(vmarg1, rbx_temp);
  25.180            __ movl(vmarg2, rdx_temp);
  25.181 +#endif
  25.182          }
  25.183          break;
  25.184        default:
  25.185 -        assert(false, "");
  25.186 +        ShouldNotReachHere();
  25.187        }
  25.188  
  25.189        __ movptr(rcx_recv, rcx_mh_vmtarget);
  25.190 @@ -768,20 +732,9 @@
  25.191        if (ek == _adapter_opt_f2d) {
  25.192          __ fld_s(vmarg);        // load float to ST0
  25.193          __ fstp_s(vmarg);       // store single
  25.194 -      } else if (!TaggedStackInterpreter) {
  25.195 +      } else {
  25.196          __ fld_d(vmarg);        // load double to ST0
  25.197          __ fstp_s(vmarg);       // store single
  25.198 -      } else {
  25.199 -        Address vmarg_tag = vmarg.plus_disp(tag_offset);
  25.200 -        Address vmarg2    = vmarg.plus_disp(Interpreter::stackElementSize());
  25.201 -        // vmarg2_tag does not participate in this code
  25.202 -        Register rbx_tag = rbx_temp;
  25.203 -        __ movl(rbx_tag, vmarg_tag); // preserve tag
  25.204 -        __ movl(rdx_temp, vmarg2); // get second word of double
  25.205 -        __ movl(vmarg_tag, rdx_temp); // align with first word
  25.206 -        __ fld_d(vmarg);        // load double to ST0
  25.207 -        __ movl(vmarg_tag, rbx_tag); // restore tag
  25.208 -        __ fstp_s(vmarg);       // store single
  25.209        }
  25.210  #endif //_LP64
  25.211  
  25.212 @@ -812,19 +765,8 @@
  25.213    case _adapter_opt_rot_2_up:
  25.214    case _adapter_opt_rot_2_down:
  25.215      {
  25.216 -      int rotate = 0, swap_slots = 0;
  25.217 -      switch ((int)ek) {
  25.218 -      case _adapter_opt_swap_1:     swap_slots = 1; break;
  25.219 -      case _adapter_opt_swap_2:     swap_slots = 2; break;
  25.220 -      case _adapter_opt_rot_1_up:   swap_slots = 1; rotate++; break;
  25.221 -      case _adapter_opt_rot_1_down: swap_slots = 1; rotate--; break;
  25.222 -      case _adapter_opt_rot_2_up:   swap_slots = 2; rotate++; break;
  25.223 -      case _adapter_opt_rot_2_down: swap_slots = 2; rotate--; break;
  25.224 -      default: assert(false, "");
  25.225 -      }
  25.226 -
  25.227 -      // the real size of the move must be doubled if TaggedStackInterpreter:
  25.228 -      int swap_bytes = (int)( swap_slots * Interpreter::stackElementWords() * wordSize );
  25.229 +      int swap_bytes = 0, rotate = 0;
  25.230 +      get_ek_adapter_opt_swap_rot_info(ek, swap_bytes, rotate);
  25.231  
  25.232        // 'argslot' is the position of the first argument to swap
  25.233        __ movl(rax_argslot, rcx_amh_vmargslot);
  25.234 @@ -925,8 +867,8 @@
  25.235  
  25.236        // 'stack_move' is negative number of words to duplicate
  25.237        Register rdx_stack_move = rdx_temp;
  25.238 -      __ movl(rdx_stack_move, rcx_amh_conversion);
  25.239 -      __ sarl(rdx_stack_move, CONV_STACK_MOVE_SHIFT);
  25.240 +      __ movl2ptr(rdx_stack_move, rcx_amh_conversion);
  25.241 +      __ sarptr(rdx_stack_move, CONV_STACK_MOVE_SHIFT);
  25.242  
  25.243        int argslot0_num = 0;
  25.244        Address argslot0 = __ argument_address(RegisterOrConstant(argslot0_num));
  25.245 @@ -988,8 +930,8 @@
  25.246  
  25.247        // 'stack_move' is number of words to drop
  25.248        Register rdi_stack_move = rdi;
  25.249 -      __ movl(rdi_stack_move, rcx_amh_conversion);
  25.250 -      __ sarl(rdi_stack_move, CONV_STACK_MOVE_SHIFT);
  25.251 +      __ movl2ptr(rdi_stack_move, rcx_amh_conversion);
  25.252 +      __ sarptr(rdi_stack_move, CONV_STACK_MOVE_SHIFT);
  25.253        remove_arg_slots(_masm, rdi_stack_move,
  25.254                         rax_argslot, rbx_temp, rdx_temp);
  25.255  
  25.256 @@ -1014,11 +956,7 @@
  25.257    case _adapter_opt_spread_more:
  25.258      {
  25.259        // spread an array out into a group of arguments
  25.260 -      int length_constant = -1;
  25.261 -      switch (ek) {
  25.262 -      case _adapter_opt_spread_0: length_constant = 0; break;
  25.263 -      case _adapter_opt_spread_1: length_constant = 1; break;
  25.264 -      }
  25.265 +      int length_constant = get_ek_adapter_opt_spread_info(ek);
  25.266  
  25.267        // find the address of the array argument
  25.268        __ movl(rax_argslot, rcx_amh_vmargslot);
  25.269 @@ -1079,8 +1017,8 @@
  25.270          __ lea(rdx_argslot_limit, Address(rax_argslot, Interpreter::stackElementSize()));
  25.271          // 'stack_move' is negative number of words to insert
  25.272          Register rdi_stack_move = rdi;
  25.273 -        __ movl(rdi_stack_move, rcx_amh_conversion);
  25.274 -        __ sarl(rdi_stack_move, CONV_STACK_MOVE_SHIFT);
  25.275 +        __ movl2ptr(rdi_stack_move, rcx_amh_conversion);
  25.276 +        __ sarptr(rdi_stack_move, CONV_STACK_MOVE_SHIFT);
  25.277          Register rsi_temp = rsi_array;  // spill this
  25.278          insert_arg_slots(_masm, rdi_stack_move, -1,
  25.279                           rax_argslot, rbx_temp, rsi_temp);
  25.280 @@ -1114,10 +1052,6 @@
  25.281          __ movptr(rbx_temp, Address(rsi_source, 0));
  25.282          __ movptr(Address(rax_argslot, 0), rbx_temp);
  25.283          __ addptr(rsi_source, type2aelembytes(elem_type));
  25.284 -        if (TaggedStackInterpreter) {
  25.285 -          __ movptr(Address(rax_argslot, tag_offset),
  25.286 -                    frame::tag_for_basic_type(elem_type));
  25.287 -        }
  25.288          __ addptr(rax_argslot, Interpreter::stackElementSize());
  25.289          __ cmpptr(rax_argslot, rdx_argslot_limit);
  25.290          __ jccb(Assembler::less, loop);
  25.291 @@ -1131,11 +1065,7 @@
  25.292            __ movptr(rbx_temp, Address(rsi_array, elem_offset));
  25.293            __ movptr(Address(rax_argslot, slot_offset), rbx_temp);
  25.294            elem_offset += type2aelembytes(elem_type);
  25.295 -          if (TaggedStackInterpreter) {
  25.296 -            __ movptr(Address(rax_argslot, slot_offset + tag_offset),
  25.297 -                      frame::tag_for_basic_type(elem_type));
  25.298 -          }
  25.299 -          slot_offset += Interpreter::stackElementSize();
  25.300 +           slot_offset += Interpreter::stackElementSize();
  25.301          }
  25.302        }
  25.303  
    26.1 --- a/src/cpu/x86/vm/stubGenerator_x86_32.cpp	Thu Mar 25 16:54:59 2010 -0700
    26.2 +++ b/src/cpu/x86/vm/stubGenerator_x86_32.cpp	Fri Mar 26 11:10:26 2010 -0400
    26.3 @@ -369,7 +369,7 @@
    26.4    // The pending exception in Thread is converted into a Java-level exception.
    26.5    //
    26.6    // Contract with Java-level exception handlers:
    26.7 -  // rax,: exception
    26.8 +  // rax: exception
    26.9    // rdx: throwing pc
   26.10    //
   26.11    // NOTE: At entry of this stub, exception-pc must be on stack !!
   26.12 @@ -377,6 +377,12 @@
   26.13    address generate_forward_exception() {
   26.14      StubCodeMark mark(this, "StubRoutines", "forward exception");
   26.15      address start = __ pc();
   26.16 +    const Register thread = rcx;
   26.17 +
   26.18 +    // other registers used in this stub
   26.19 +    const Register exception_oop = rax;
   26.20 +    const Register handler_addr  = rbx;
   26.21 +    const Register exception_pc  = rdx;
   26.22  
   26.23      // Upon entry, the sp points to the return address returning into Java
   26.24      // (interpreted or compiled) code; i.e., the return address becomes the
   26.25 @@ -389,8 +395,8 @@
   26.26  #ifdef ASSERT
   26.27      // make sure this code is only executed if there is a pending exception
   26.28      { Label L;
   26.29 -      __ get_thread(rcx);
   26.30 -      __ cmpptr(Address(rcx, Thread::pending_exception_offset()), (int32_t)NULL_WORD);
   26.31 +      __ get_thread(thread);
   26.32 +      __ cmpptr(Address(thread, Thread::pending_exception_offset()), (int32_t)NULL_WORD);
   26.33        __ jcc(Assembler::notEqual, L);
   26.34        __ stop("StubRoutines::forward exception: no pending exception (1)");
   26.35        __ bind(L);
   26.36 @@ -398,33 +404,40 @@
   26.37  #endif
   26.38  
   26.39      // compute exception handler into rbx,
   26.40 -    __ movptr(rax, Address(rsp, 0));
   26.41 +    __ get_thread(thread);
   26.42 +    __ movptr(exception_pc, Address(rsp, 0));
   26.43      BLOCK_COMMENT("call exception_handler_for_return_address");
   26.44 -    __ call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::exception_handler_for_return_address), rax);
   26.45 -    __ mov(rbx, rax);
   26.46 +    __ call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::exception_handler_for_return_address), thread, exception_pc);
   26.47 +    __ mov(handler_addr, rax);
   26.48  
   26.49 -    // setup rax, & rdx, remove return address & clear pending exception
   26.50 -    __ get_thread(rcx);
   26.51 -    __ pop(rdx);
   26.52 -    __ movptr(rax, Address(rcx, Thread::pending_exception_offset()));
   26.53 -    __ movptr(Address(rcx, Thread::pending_exception_offset()), NULL_WORD);
   26.54 +    // setup rax & rdx, remove return address & clear pending exception
   26.55 +    __ get_thread(thread);
   26.56 +    __ pop(exception_pc);
   26.57 +    __ movptr(exception_oop, Address(thread, Thread::pending_exception_offset()));
   26.58 +    __ movptr(Address(thread, Thread::pending_exception_offset()), NULL_WORD);
   26.59  
   26.60  #ifdef ASSERT
   26.61      // make sure exception is set
   26.62      { Label L;
   26.63 -      __ testptr(rax, rax);
   26.64 +      __ testptr(exception_oop, exception_oop);
   26.65        __ jcc(Assembler::notEqual, L);
   26.66        __ stop("StubRoutines::forward exception: no pending exception (2)");
   26.67        __ bind(L);
   26.68      }
   26.69  #endif
   26.70  
   26.71 +    // Verify that there is really a valid exception in RAX.
   26.72 +    __ verify_oop(exception_oop);
   26.73 +
   26.74 +    // Restore SP from BP if the exception PC is a MethodHandle call site.
   26.75 +    __ cmpl(Address(thread, JavaThread::is_method_handle_exception_offset()), 0);
   26.76 +    __ cmovptr(Assembler::notEqual, rsp, rbp);
   26.77 +
   26.78      // continue at exception handler (return address removed)
   26.79 -    // rax,: exception
   26.80 -    // rbx,: exception handler
   26.81 +    // rax: exception
   26.82 +    // rbx: exception handler
   26.83      // rdx: throwing pc
   26.84 -    __ verify_oop(rax);
   26.85 -    __ jmp(rbx);
   26.86 +    __ jmp(handler_addr);
   26.87  
   26.88      return start;
   26.89    }
   26.90 @@ -2263,16 +2276,6 @@
   26.91      // arraycopy stubs used by compilers
   26.92      generate_arraycopy_stubs();
   26.93  
   26.94 -    // generic method handle stubs
   26.95 -    if (EnableMethodHandles && SystemDictionary::MethodHandle_klass() != NULL) {
   26.96 -      for (MethodHandles::EntryKind ek = MethodHandles::_EK_FIRST;
   26.97 -           ek < MethodHandles::_EK_LIMIT;
   26.98 -           ek = MethodHandles::EntryKind(1 + (int)ek)) {
   26.99 -        StubCodeMark mark(this, "MethodHandle", MethodHandles::entry_name(ek));
  26.100 -        MethodHandles::generate_method_handle_stub(_masm, ek);
  26.101 -      }
  26.102 -    }
  26.103 -
  26.104      generate_math_stubs();
  26.105    }
  26.106  
    27.1 --- a/src/cpu/x86/vm/stubGenerator_x86_64.cpp	Thu Mar 25 16:54:59 2010 -0700
    27.2 +++ b/src/cpu/x86/vm/stubGenerator_x86_64.cpp	Fri Mar 26 11:10:26 2010 -0400
    27.3 @@ -466,7 +466,7 @@
    27.4      BLOCK_COMMENT("call exception_handler_for_return_address");
    27.5      __ call_VM_leaf(CAST_FROM_FN_PTR(address,
    27.6                           SharedRuntime::exception_handler_for_return_address),
    27.7 -                    c_rarg0);
    27.8 +                    r15_thread, c_rarg0);
    27.9      __ mov(rbx, rax);
   27.10  
   27.11      // setup rax & rdx, remove return address & clear pending exception
   27.12 @@ -3009,16 +3009,6 @@
   27.13      // arraycopy stubs used by compilers
   27.14      generate_arraycopy_stubs();
   27.15  
   27.16 -    // generic method handle stubs
   27.17 -    if (EnableMethodHandles && SystemDictionary::MethodHandle_klass() != NULL) {
   27.18 -      for (MethodHandles::EntryKind ek = MethodHandles::_EK_FIRST;
   27.19 -           ek < MethodHandles::_EK_LIMIT;
   27.20 -           ek = MethodHandles::EntryKind(1 + (int)ek)) {
   27.21 -        StubCodeMark mark(this, "MethodHandle", MethodHandles::entry_name(ek));
   27.22 -        MethodHandles::generate_method_handle_stub(_masm, ek);
   27.23 -      }
   27.24 -    }
   27.25 -
   27.26      generate_math_stubs();
   27.27    }
   27.28  
    28.1 --- a/src/cpu/x86/vm/stubRoutines_x86_32.hpp	Thu Mar 25 16:54:59 2010 -0700
    28.2 +++ b/src/cpu/x86/vm/stubRoutines_x86_32.hpp	Fri Mar 26 11:10:26 2010 -0400
    28.3 @@ -1,5 +1,5 @@
    28.4  /*
    28.5 - * Copyright 1997-2008 Sun Microsystems, Inc.  All Rights Reserved.
    28.6 + * Copyright 1997-2010 Sun Microsystems, Inc.  All Rights Reserved.
    28.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    28.8   *
    28.9   * This code is free software; you can redistribute it and/or modify it
   28.10 @@ -31,6 +31,11 @@
   28.11    code_size2 = 22000            // simply increase if too small (assembler will crash if too small)
   28.12  };
   28.13  
   28.14 +// MethodHandles adapters
   28.15 +enum method_handles_platform_dependent_constants {
   28.16 +  method_handles_adapters_code_size = 5000
   28.17 +};
   28.18 +
   28.19  class x86 {
   28.20   friend class StubGenerator;
   28.21   friend class VMStructs;
    29.1 --- a/src/cpu/x86/vm/stubRoutines_x86_64.hpp	Thu Mar 25 16:54:59 2010 -0700
    29.2 +++ b/src/cpu/x86/vm/stubRoutines_x86_64.hpp	Fri Mar 26 11:10:26 2010 -0400
    29.3 @@ -1,5 +1,5 @@
    29.4  /*
    29.5 - * Copyright 2003-2008 Sun Microsystems, Inc.  All Rights Reserved.
    29.6 + * Copyright 2003-2010 Sun Microsystems, Inc.  All Rights Reserved.
    29.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    29.8   *
    29.9   * This code is free software; you can redistribute it and/or modify it
   29.10 @@ -28,12 +28,14 @@
   29.11  
   29.12  static bool    returns_to_call_stub(address return_pc)   { return return_pc == _call_stub_return_address; }
   29.13  
   29.14 -enum platform_dependent_constants
   29.15 -{
   29.16 -  code_size1 =  19000, // simply increase if too small (assembler will
   29.17 -                      // crash if too small)
   29.18 -  code_size2 = 22000  // simply increase if too small (assembler will
   29.19 -                      // crash if too small)
   29.20 +enum platform_dependent_constants {
   29.21 +  code_size1 = 19000,          // simply increase if too small (assembler will crash if too small)
   29.22 +  code_size2 = 22000           // simply increase if too small (assembler will crash if too small)
   29.23 +};
   29.24 +
   29.25 +// MethodHandles adapters
   29.26 +enum method_handles_platform_dependent_constants {
   29.27 +  method_handles_adapters_code_size = 13000
   29.28  };
   29.29  
   29.30  class x86 {
    30.1 --- a/src/cpu/x86/vm/templateInterpreter_x86_32.cpp	Thu Mar 25 16:54:59 2010 -0700
    30.2 +++ b/src/cpu/x86/vm/templateInterpreter_x86_32.cpp	Fri Mar 26 11:10:26 2010 -0400
    30.3 @@ -1550,6 +1550,7 @@
    30.4  void TemplateInterpreterGenerator::generate_throw_exception() {
    30.5    // Entry point in previous activation (i.e., if the caller was interpreted)
    30.6    Interpreter::_rethrow_exception_entry = __ pc();
    30.7 +  const Register thread = rcx;
    30.8  
    30.9    // Restore sp to interpreter_frame_last_sp even though we are going
   30.10    // to empty the expression stack for the exception processing.
   30.11 @@ -1598,10 +1599,10 @@
   30.12    // Set the popframe_processing bit in pending_popframe_condition indicating that we are
   30.13    // currently handling popframe, so that call_VMs that may happen later do not trigger new
   30.14    // popframe handling cycles.
   30.15 -  __ get_thread(rcx);
   30.16 -  __ movl(rdx, Address(rcx, JavaThread::popframe_condition_offset()));
   30.17 +  __ get_thread(thread);
   30.18 +  __ movl(rdx, Address(thread, JavaThread::popframe_condition_offset()));
   30.19    __ orl(rdx, JavaThread::popframe_processing_bit);
   30.20 -  __ movl(Address(rcx, JavaThread::popframe_condition_offset()), rdx);
   30.21 +  __ movl(Address(thread, JavaThread::popframe_condition_offset()), rdx);
   30.22  
   30.23    {
   30.24      // Check to see whether we are returning to a deoptimized frame.
   30.25 @@ -1629,8 +1630,8 @@
   30.26      __ subptr(rdi, rax);
   30.27      __ addptr(rdi, wordSize);
   30.28      // Save these arguments
   30.29 -    __ get_thread(rcx);
   30.30 -    __ super_call_VM_leaf(CAST_FROM_FN_PTR(address, Deoptimization::popframe_preserve_args), rcx, rax, rdi);
   30.31 +    __ get_thread(thread);
   30.32 +    __ super_call_VM_leaf(CAST_FROM_FN_PTR(address, Deoptimization::popframe_preserve_args), thread, rax, rdi);
   30.33  
   30.34      __ remove_activation(vtos, rdx,
   30.35                           /* throw_monitor_exception */ false,
   30.36 @@ -1638,8 +1639,8 @@
   30.37                           /* notify_jvmdi */ false);
   30.38  
   30.39      // Inform deoptimization that it is responsible for restoring these arguments
   30.40 -    __ get_thread(rcx);
   30.41 -    __ movl(Address(rcx, JavaThread::popframe_condition_offset()), JavaThread::popframe_force_deopt_reexecution_bit);
   30.42 +    __ get_thread(thread);
   30.43 +    __ movl(Address(thread, JavaThread::popframe_condition_offset()), JavaThread::popframe_force_deopt_reexecution_bit);
   30.44  
   30.45      // Continue in deoptimization handler
   30.46      __ jmp(rdx);
   30.47 @@ -1665,12 +1666,12 @@
   30.48    // expression stack if necessary.
   30.49    __ mov(rax, rsp);
   30.50    __ movptr(rbx, Address(rbp, frame::interpreter_frame_last_sp_offset * wordSize));
   30.51 -  __ get_thread(rcx);
   30.52 +  __ get_thread(thread);
   30.53    // PC must point into interpreter here
   30.54 -  __ set_last_Java_frame(rcx, noreg, rbp, __ pc());
   30.55 -  __ super_call_VM_leaf(CAST_FROM_FN_PTR(address, InterpreterRuntime::popframe_move_outgoing_args), rcx, rax, rbx);
   30.56 -  __ get_thread(rcx);
   30.57 -  __ reset_last_Java_frame(rcx, true, true);
   30.58 +  __ set_last_Java_frame(thread, noreg, rbp, __ pc());
   30.59 +  __ super_call_VM_leaf(CAST_FROM_FN_PTR(address, InterpreterRuntime::popframe_move_outgoing_args), thread, rax, rbx);
   30.60 +  __ get_thread(thread);
   30.61 +  __ reset_last_Java_frame(thread, true, true);
   30.62    // Restore the last_sp and null it out
   30.63    __ movptr(rsp, Address(rbp, frame::interpreter_frame_last_sp_offset * wordSize));
   30.64    __ movptr(Address(rbp, frame::interpreter_frame_last_sp_offset * wordSize), NULL_WORD);
   30.65 @@ -1684,8 +1685,8 @@
   30.66    }
   30.67  
   30.68    // Clear the popframe condition flag
   30.69 -  __ get_thread(rcx);
   30.70 -  __ movl(Address(rcx, JavaThread::popframe_condition_offset()), JavaThread::popframe_inactive);
   30.71 +  __ get_thread(thread);
   30.72 +  __ movl(Address(thread, JavaThread::popframe_condition_offset()), JavaThread::popframe_inactive);
   30.73  
   30.74    __ dispatch_next(vtos);
   30.75    // end of PopFrame support
   30.76 @@ -1694,27 +1695,27 @@
   30.77  
   30.78    // preserve exception over this code sequence
   30.79    __ pop_ptr(rax);
   30.80 -  __ get_thread(rcx);
   30.81 -  __ movptr(Address(rcx, JavaThread::vm_result_offset()), rax);
   30.82 +  __ get_thread(thread);
   30.83 +  __ movptr(Address(thread, JavaThread::vm_result_offset()), rax);
   30.84    // remove the activation (without doing throws on illegalMonitorExceptions)
   30.85    __ remove_activation(vtos, rdx, false, true, false);
   30.86    // restore exception
   30.87 -  __ get_thread(rcx);
   30.88 -  __ movptr(rax, Address(rcx, JavaThread::vm_result_offset()));
   30.89 -  __ movptr(Address(rcx, JavaThread::vm_result_offset()), NULL_WORD);
   30.90 +  __ get_thread(thread);
   30.91 +  __ movptr(rax, Address(thread, JavaThread::vm_result_offset()));
   30.92 +  __ movptr(Address(thread, JavaThread::vm_result_offset()), NULL_WORD);
   30.93    __ verify_oop(rax);
   30.94  
   30.95    // Inbetween activations - previous activation type unknown yet
   30.96    // compute continuation point - the continuation point expects
   30.97    // the following registers set up:
   30.98    //
   30.99 -  // rax,: exception
  30.100 +  // rax: exception
  30.101    // rdx: return address/pc that threw exception
  30.102    // rsp: expression stack of caller
  30.103 -  // rbp,: rbp, of caller
  30.104 +  // rbp: rbp, of caller
  30.105    __ push(rax);                                  // save exception
  30.106    __ push(rdx);                                  // save return address
  30.107 -  __ super_call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::exception_handler_for_return_address), rdx);
  30.108 +  __ super_call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::exception_handler_for_return_address), thread, rdx);
  30.109    __ mov(rbx, rax);                              // save exception handler
  30.110    __ pop(rdx);                                   // restore return address
  30.111    __ pop(rax);                                   // restore exception
  30.112 @@ -1728,6 +1729,7 @@
  30.113  //
  30.114  address TemplateInterpreterGenerator::generate_earlyret_entry_for(TosState state) {
  30.115    address entry = __ pc();
  30.116 +  const Register thread = rcx;
  30.117  
  30.118    __ restore_bcp();
  30.119    __ restore_locals();
  30.120 @@ -1735,8 +1737,8 @@
  30.121    __ empty_FPU_stack();
  30.122    __ load_earlyret_value(state);
  30.123  
  30.124 -  __ get_thread(rcx);
  30.125 -  __ movptr(rcx, Address(rcx, JavaThread::jvmti_thread_state_offset()));
  30.126 +  __ get_thread(thread);
  30.127 +  __ movptr(rcx, Address(thread, JavaThread::jvmti_thread_state_offset()));
  30.128    const Address cond_addr(rcx, JvmtiThreadState::earlyret_state_offset());
  30.129  
  30.130    // Clear the earlyret state
    31.1 --- a/src/cpu/x86/vm/templateInterpreter_x86_64.cpp	Thu Mar 25 16:54:59 2010 -0700
    31.2 +++ b/src/cpu/x86/vm/templateInterpreter_x86_64.cpp	Fri Mar 26 11:10:26 2010 -0400
    31.3 @@ -1741,7 +1741,7 @@
    31.4    __ push(rdx);                                  // save return address
    31.5    __ super_call_VM_leaf(CAST_FROM_FN_PTR(address,
    31.6                            SharedRuntime::exception_handler_for_return_address),
    31.7 -                        rdx);
    31.8 +                        r15_thread, rdx);
    31.9    __ mov(rbx, rax);                              // save exception handler
   31.10    __ pop(rdx);                                   // restore return address
   31.11    __ pop(rax);                                   // restore exception
    32.1 --- a/src/cpu/x86/vm/templateTable_x86_32.cpp	Thu Mar 25 16:54:59 2010 -0700
    32.2 +++ b/src/cpu/x86/vm/templateTable_x86_32.cpp	Fri Mar 26 11:10:26 2010 -0400
    32.3 @@ -1,5 +1,5 @@
    32.4  /*
    32.5 - * Copyright 1997-2009 Sun Microsystems, Inc.  All Rights Reserved.
    32.6 + * Copyright 1997-2010 Sun Microsystems, Inc.  All Rights Reserved.
    32.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    32.8   *
    32.9   * This code is free software; you can redistribute it and/or modify it
   32.10 @@ -2915,12 +2915,8 @@
   32.11      __ andl(recv, 0xFF);
   32.12      // recv count is 0 based?
   32.13      Address recv_addr(rsp, recv, Interpreter::stackElementScale(), -Interpreter::expr_offset_in_bytes(1));
   32.14 -    if (is_invokedynamic) {
   32.15 -      __ lea(recv, recv_addr);
   32.16 -    } else {
   32.17 -      __ movptr(recv, recv_addr);
   32.18 -      __ verify_oop(recv);
   32.19 -    }
   32.20 +    __ movptr(recv, recv_addr);
   32.21 +    __ verify_oop(recv);
   32.22    }
   32.23  
   32.24    // do null check if needed
    33.1 --- a/src/cpu/x86/vm/templateTable_x86_64.cpp	Thu Mar 25 16:54:59 2010 -0700
    33.2 +++ b/src/cpu/x86/vm/templateTable_x86_64.cpp	Fri Mar 26 11:10:26 2010 -0400
    33.3 @@ -1,5 +1,5 @@
    33.4  /*
    33.5 - * Copyright 2003-2009 Sun Microsystems, Inc.  All Rights Reserved.
    33.6 + * Copyright 2003-2010 Sun Microsystems, Inc.  All Rights Reserved.
    33.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    33.8   *
    33.9   * This code is free software; you can redistribute it and/or modify it
   33.10 @@ -2860,12 +2860,8 @@
   33.11      __ andl(recv, 0xFF);
   33.12      if (TaggedStackInterpreter) __ shll(recv, 1);  // index*2
   33.13      Address recv_addr(rsp, recv, Address::times_8, -Interpreter::expr_offset_in_bytes(1));
   33.14 -    if (is_invokedynamic) {
   33.15 -      __ lea(recv, recv_addr);
   33.16 -    } else {
   33.17 -      __ movptr(recv, recv_addr);
   33.18 -      __ verify_oop(recv);
   33.19 -    }
   33.20 +    __ movptr(recv, recv_addr);
   33.21 +    __ verify_oop(recv);
   33.22    }
   33.23  
   33.24    // do null check if needed
    34.1 --- a/src/os_cpu/linux_zero/vm/globals_linux_zero.hpp	Thu Mar 25 16:54:59 2010 -0700
    34.2 +++ b/src/os_cpu/linux_zero/vm/globals_linux_zero.hpp	Fri Mar 26 11:10:26 2010 -0400
    34.3 @@ -1,6 +1,6 @@
    34.4  /*
    34.5   * Copyright 2000-2005 Sun Microsystems, Inc.  All Rights Reserved.
    34.6 - * Copyright 2007, 2008 Red Hat, Inc.
    34.7 + * Copyright 2007, 2008, 2010 Red Hat, Inc.
    34.8   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    34.9   *
   34.10   * This code is free software; you can redistribute it and/or modify it
   34.11 @@ -29,11 +29,10 @@
   34.12  //
   34.13  
   34.14  define_pd_global(bool,  DontYieldALot,           false);
   34.15 +define_pd_global(intx,  ThreadStackSize,         1536);
   34.16  #ifdef _LP64
   34.17 -define_pd_global(intx,  ThreadStackSize,         1536);
   34.18  define_pd_global(intx,  VMThreadStackSize,       1024);
   34.19  #else
   34.20 -define_pd_global(intx,  ThreadStackSize,         1024);
   34.21  define_pd_global(intx,  VMThreadStackSize,       512);
   34.22  #endif // _LP64
   34.23  define_pd_global(intx,  SurvivorRatio,           8);
    35.1 --- a/src/share/vm/c1/c1_Canonicalizer.cpp	Thu Mar 25 16:54:59 2010 -0700
    35.2 +++ b/src/share/vm/c1/c1_Canonicalizer.cpp	Fri Mar 26 11:10:26 2010 -0400
    35.3 @@ -1,5 +1,5 @@
    35.4  /*
    35.5 - * Copyright 1999-2006 Sun Microsystems, Inc.  All Rights Reserved.
    35.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    35.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    35.8   *
    35.9   * This code is free software; you can redistribute it and/or modify it
   35.10 @@ -222,11 +222,15 @@
   35.11      }
   35.12    } else {
   35.13      LoadField* lf = x->array()->as_LoadField();
   35.14 -    if (lf != NULL && lf->field()->is_constant()) {
   35.15 -      ciObject* c = lf->field()->constant_value().as_object();
   35.16 -      if (c->is_array()) {
   35.17 -        ciArray* array = (ciArray*) c;
   35.18 -        set_constant(array->length());
   35.19 +    if (lf != NULL) {
   35.20 +      ciField* field = lf->field();
   35.21 +      if (field->is_constant() && field->is_static()) {
   35.22 +        // final static field
   35.23 +        ciObject* c = field->constant_value().as_object();
   35.24 +        if (c->is_array()) {
   35.25 +          ciArray* array = (ciArray*) c;
   35.26 +          set_constant(array->length());
   35.27 +        }
   35.28        }
   35.29      }
   35.30    }
    36.1 --- a/src/share/vm/c1/c1_CodeStubs.hpp	Thu Mar 25 16:54:59 2010 -0700
    36.2 +++ b/src/share/vm/c1/c1_CodeStubs.hpp	Fri Mar 26 11:10:26 2010 -0400
    36.3 @@ -1,5 +1,5 @@
    36.4  /*
    36.5 - * Copyright 1999-2006 Sun Microsystems, Inc.  All Rights Reserved.
    36.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    36.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    36.8   *
    36.9   * This code is free software; you can redistribute it and/or modify it
   36.10 @@ -415,6 +415,28 @@
   36.11  };
   36.12  
   36.13  
   36.14 +//------------------------------------------------------------------------------
   36.15 +// DeoptimizeStub
   36.16 +//
   36.17 +class DeoptimizeStub : public CodeStub {
   36.18 +private:
   36.19 +  CodeEmitInfo* _info;
   36.20 +
   36.21 +public:
   36.22 +  DeoptimizeStub(CodeEmitInfo* info) : _info(new CodeEmitInfo(info)) {}
   36.23 +
   36.24 +  virtual void emit_code(LIR_Assembler* e);
   36.25 +  virtual CodeEmitInfo* info() const           { return _info; }
   36.26 +  virtual bool is_exception_throw_stub() const { return true; }
   36.27 +  virtual void visit(LIR_OpVisitState* visitor) {
   36.28 +    visitor->do_slow_case(_info);
   36.29 +  }
   36.30 +#ifndef PRODUCT
   36.31 +  virtual void print_name(outputStream* out) const { out->print("DeoptimizeStub"); }
   36.32 +#endif // PRODUCT
   36.33 +};
   36.34 +
   36.35 +
   36.36  class SimpleExceptionStub: public CodeStub {
   36.37   private:
   36.38    LIR_Opr          _obj;
    37.1 --- a/src/share/vm/c1/c1_GraphBuilder.cpp	Thu Mar 25 16:54:59 2010 -0700
    37.2 +++ b/src/share/vm/c1/c1_GraphBuilder.cpp	Fri Mar 26 11:10:26 2010 -0400
    37.3 @@ -1,5 +1,5 @@
    37.4  /*
    37.5 - * Copyright 1999-2009 Sun Microsystems, Inc.  All Rights Reserved.
    37.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    37.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    37.8   *
    37.9   * This code is free software; you can redistribute it and/or modify it
   37.10 @@ -1524,18 +1524,14 @@
   37.11      code = Bytecodes::_invokespecial;
   37.12    }
   37.13  
   37.14 -  if (code == Bytecodes::_invokedynamic) {
   37.15 -    BAILOUT("invokedynamic NYI"); // FIXME
   37.16 -    return;
   37.17 -  }
   37.18 -
   37.19    // NEEDS_CLEANUP
   37.20    // I've added the target-is_loaded() test below but I don't really understand
   37.21    // how klass->is_loaded() can be true and yet target->is_loaded() is false.
   37.22    // this happened while running the JCK invokevirtual tests under doit.  TKR
   37.23    ciMethod* cha_monomorphic_target = NULL;
   37.24    ciMethod* exact_target = NULL;
   37.25 -  if (UseCHA && DeoptC1 && klass->is_loaded() && target->is_loaded()) {
   37.26 +  if (UseCHA && DeoptC1 && klass->is_loaded() && target->is_loaded() &&
   37.27 +      !target->is_method_handle_invoke()) {
   37.28      Value receiver = NULL;
   37.29      ciInstanceKlass* receiver_klass = NULL;
   37.30      bool type_is_exact = false;
   37.31 @@ -1681,11 +1677,20 @@
   37.32    CHECK_BAILOUT();
   37.33  
   37.34    // inlining not successful => standard invoke
   37.35 -  bool is_static = code == Bytecodes::_invokestatic;
   37.36 +  bool is_loaded = target->is_loaded();
   37.37 +  bool has_receiver =
   37.38 +    code == Bytecodes::_invokespecial   ||
   37.39 +    code == Bytecodes::_invokevirtual   ||
   37.40 +    code == Bytecodes::_invokeinterface;
   37.41 +  bool is_invokedynamic = code == Bytecodes::_invokedynamic;
   37.42    ValueType* result_type = as_ValueType(target->return_type());
   37.43 +
   37.44 +  // We require the debug info to be the "state before" because
   37.45 +  // invokedynamics may deoptimize.
   37.46 +  ValueStack* state_before = is_invokedynamic ? state()->copy() : NULL;
   37.47 +
   37.48    Values* args = state()->pop_arguments(target->arg_size_no_receiver());
   37.49 -  Value recv = is_static ? NULL : apop();
   37.50 -  bool is_loaded = target->is_loaded();
   37.51 +  Value recv = has_receiver ? apop() : NULL;
   37.52    int vtable_index = methodOopDesc::invalid_vtable_index;
   37.53  
   37.54  #ifdef SPARC
   37.55 @@ -1723,7 +1728,7 @@
   37.56      profile_call(recv, target_klass);
   37.57    }
   37.58  
   37.59 -  Invoke* result = new Invoke(code, result_type, recv, args, vtable_index, target);
   37.60 +  Invoke* result = new Invoke(code, result_type, recv, args, vtable_index, target, state_before);
   37.61    // push result
   37.62    append_split(result);
   37.63  
   37.64 @@ -2862,20 +2867,18 @@
   37.65    _initial_state = state_at_entry();
   37.66    start_block->merge(_initial_state);
   37.67  
   37.68 -  BlockBegin* sync_handler = NULL;
   37.69 -  if (method()->is_synchronized() || _compilation->env()->dtrace_method_probes()) {
   37.70 -    // setup an exception handler to do the unlocking and/or notification
   37.71 -    sync_handler = new BlockBegin(-1);
   37.72 -    sync_handler->set(BlockBegin::exception_entry_flag);
   37.73 -    sync_handler->set(BlockBegin::is_on_work_list_flag);
   37.74 -    sync_handler->set(BlockBegin::default_exception_handler_flag);
   37.75 -
   37.76 -    ciExceptionHandler* desc = new ciExceptionHandler(method()->holder(), 0, method()->code_size(), -1, 0);
   37.77 -    XHandler* h = new XHandler(desc);
   37.78 -    h->set_entry_block(sync_handler);
   37.79 -    scope_data()->xhandlers()->append(h);
   37.80 -    scope_data()->set_has_handler();
   37.81 -  }
   37.82 +  // setup an exception handler to do the unlocking and/or
   37.83 +  // notification and unwind the frame.
   37.84 +  BlockBegin* sync_handler = new BlockBegin(-1);
   37.85 +  sync_handler->set(BlockBegin::exception_entry_flag);
   37.86 +  sync_handler->set(BlockBegin::is_on_work_list_flag);
   37.87 +  sync_handler->set(BlockBegin::default_exception_handler_flag);
   37.88 +
   37.89 +  ciExceptionHandler* desc = new ciExceptionHandler(method()->holder(), 0, method()->code_size(), -1, 0);
   37.90 +  XHandler* h = new XHandler(desc);
   37.91 +  h->set_entry_block(sync_handler);
   37.92 +  scope_data()->xhandlers()->append(h);
   37.93 +  scope_data()->set_has_handler();
   37.94  
   37.95    // complete graph
   37.96    _vmap        = new ValueMap();
    38.1 --- a/src/share/vm/c1/c1_IR.cpp	Thu Mar 25 16:54:59 2010 -0700
    38.2 +++ b/src/share/vm/c1/c1_IR.cpp	Fri Mar 26 11:10:26 2010 -0400
    38.3 @@ -1,5 +1,5 @@
    38.4  /*
    38.5 - * Copyright 1999-2009 Sun Microsystems, Inc.  All Rights Reserved.
    38.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    38.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    38.8   *
    38.9   * This code is free software; you can redistribute it and/or modify it
   38.10 @@ -259,10 +259,10 @@
   38.11  }
   38.12  
   38.13  
   38.14 -void CodeEmitInfo::record_debug_info(DebugInformationRecorder* recorder, int pc_offset) {
   38.15 +void CodeEmitInfo::record_debug_info(DebugInformationRecorder* recorder, int pc_offset, bool is_method_handle_invoke) {
   38.16    // record the safepoint before recording the debug info for enclosing scopes
   38.17    recorder->add_safepoint(pc_offset, _oop_map->deep_copy());
   38.18 -  _scope_debug_info->record_debug_info(recorder, pc_offset, true/*topmost*/);
   38.19 +  _scope_debug_info->record_debug_info(recorder, pc_offset, true/*topmost*/, is_method_handle_invoke);
   38.20    recorder->end_safepoint(pc_offset);
   38.21  }
   38.22  
    39.1 --- a/src/share/vm/c1/c1_IR.hpp	Thu Mar 25 16:54:59 2010 -0700
    39.2 +++ b/src/share/vm/c1/c1_IR.hpp	Fri Mar 26 11:10:26 2010 -0400
    39.3 @@ -1,5 +1,5 @@
    39.4  /*
    39.5 - * Copyright 1999-2009 Sun Microsystems, Inc.  All Rights Reserved.
    39.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    39.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    39.8   *
    39.9   * This code is free software; you can redistribute it and/or modify it
   39.10 @@ -242,7 +242,7 @@
   39.11    //Whether we should reexecute this bytecode for deopt
   39.12    bool should_reexecute();
   39.13  
   39.14 -  void record_debug_info(DebugInformationRecorder* recorder, int pc_offset, bool topmost) {
   39.15 +  void record_debug_info(DebugInformationRecorder* recorder, int pc_offset, bool topmost, bool is_method_handle_invoke = false) {
   39.16      if (caller() != NULL) {
   39.17        // Order is significant:  Must record caller first.
   39.18        caller()->record_debug_info(recorder, pc_offset, false/*topmost*/);
   39.19 @@ -252,7 +252,6 @@
   39.20      DebugToken* monvals = recorder->create_monitor_values(monitors());
   39.21      // reexecute allowed only for the topmost frame
   39.22      bool reexecute = topmost ? should_reexecute() : false;
   39.23 -    bool is_method_handle_invoke = false;
   39.24      bool return_oop = false; // This flag will be ignored since it used only for C2 with escape analysis.
   39.25      recorder->describe_scope(pc_offset, scope()->method(), bci(), reexecute, is_method_handle_invoke, return_oop, locvals, expvals, monvals);
   39.26    }
   39.27 @@ -303,7 +302,7 @@
   39.28    int bci() const                                { return _bci; }
   39.29  
   39.30    void add_register_oop(LIR_Opr opr);
   39.31 -  void record_debug_info(DebugInformationRecorder* recorder, int pc_offset);
   39.32 +  void record_debug_info(DebugInformationRecorder* recorder, int pc_offset, bool is_method_handle_invoke = false);
   39.33  
   39.34    CodeEmitInfo* next() const        { return _next; }
   39.35    void set_next(CodeEmitInfo* next) { _next = next; }
    40.1 --- a/src/share/vm/c1/c1_Instruction.cpp	Thu Mar 25 16:54:59 2010 -0700
    40.2 +++ b/src/share/vm/c1/c1_Instruction.cpp	Fri Mar 26 11:10:26 2010 -0400
    40.3 @@ -1,5 +1,5 @@
    40.4  /*
    40.5 - * Copyright 1999-2006 Sun Microsystems, Inc.  All Rights Reserved.
    40.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    40.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    40.8   *
    40.9   * This code is free software; you can redistribute it and/or modify it
   40.10 @@ -334,13 +334,14 @@
   40.11  
   40.12  
   40.13  Invoke::Invoke(Bytecodes::Code code, ValueType* result_type, Value recv, Values* args,
   40.14 -               int vtable_index, ciMethod* target)
   40.15 +               int vtable_index, ciMethod* target, ValueStack* state_before)
   40.16    : StateSplit(result_type)
   40.17    , _code(code)
   40.18    , _recv(recv)
   40.19    , _args(args)
   40.20    , _vtable_index(vtable_index)
   40.21    , _target(target)
   40.22 +  , _state_before(state_before)
   40.23  {
   40.24    set_flag(TargetIsLoadedFlag,   target->is_loaded());
   40.25    set_flag(TargetIsFinalFlag,    target_is_loaded() && target->is_final_method());
   40.26 @@ -355,6 +356,9 @@
   40.27    _signature = new BasicTypeList(number_of_arguments() + (has_receiver() ? 1 : 0));
   40.28    if (has_receiver()) {
   40.29      _signature->append(as_BasicType(receiver()->type()));
   40.30 +  } else if (is_invokedynamic()) {
   40.31 +    // Add the synthetic MethodHandle argument to the signature.
   40.32 +    _signature->append(T_OBJECT);
   40.33    }
   40.34    for (int i = 0; i < number_of_arguments(); i++) {
   40.35      ValueType* t = argument_at(i)->type();
   40.36 @@ -364,6 +368,13 @@
   40.37  }
   40.38  
   40.39  
   40.40 +void Invoke::state_values_do(void f(Value*)) {
   40.41 +  StateSplit::state_values_do(f);
   40.42 +  if (state_before() != NULL) state_before()->values_do(f);
   40.43 +  if (state()        != NULL) state()->values_do(f);
   40.44 +}
   40.45 +
   40.46 +
   40.47  // Implementation of Contant
   40.48  intx Constant::hash() const {
   40.49    if (_state == NULL) {
    41.1 --- a/src/share/vm/c1/c1_Instruction.hpp	Thu Mar 25 16:54:59 2010 -0700
    41.2 +++ b/src/share/vm/c1/c1_Instruction.hpp	Fri Mar 26 11:10:26 2010 -0400
    41.3 @@ -1,5 +1,5 @@
    41.4  /*
    41.5 - * Copyright 1999-2006 Sun Microsystems, Inc.  All Rights Reserved.
    41.6 + * Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    41.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    41.8   *
    41.9   * This code is free software; you can redistribute it and/or modify it
   41.10 @@ -1134,17 +1134,18 @@
   41.11  
   41.12  LEAF(Invoke, StateSplit)
   41.13   private:
   41.14 -  Bytecodes::Code           _code;
   41.15 -  Value                     _recv;
   41.16 -  Values*                   _args;
   41.17 -  BasicTypeList*            _signature;
   41.18 -  int                       _vtable_index;
   41.19 -  ciMethod*                 _target;
   41.20 +  Bytecodes::Code _code;
   41.21 +  Value           _recv;
   41.22 +  Values*         _args;
   41.23 +  BasicTypeList*  _signature;
   41.24 +  int             _vtable_index;
   41.25 +  ciMethod*       _target;
   41.26 +  ValueStack*     _state_before;  // Required for deoptimization.
   41.27  
   41.28   public:
   41.29    // creation
   41.30    Invoke(Bytecodes::Code code, ValueType* result_type, Value recv, Values* args,
   41.31 -         int vtable_index, ciMethod* target);
   41.32 +         int vtable_index, ciMethod* target, ValueStack* state_before);
   41.33  
   41.34    // accessors
   41.35    Bytecodes::Code code() const                   { return _code; }
   41.36 @@ -1155,6 +1156,7 @@
   41.37    int vtable_index() const                       { return _vtable_index; }
   41.38    BasicTypeList* signature() const               { return _signature; }
   41.39    ciMethod* target() const                       { return _target; }
   41.40 +  ValueStack* state_before() const               { return _state_before; }
   41.41  
   41.42    // Returns false if target is not loaded
   41.43    bool target_is_final() const                   { return check_flag(TargetIsFinalFlag); }
   41.44 @@ -1162,6 +1164,9 @@
   41.45    // Returns false if target is not loaded
   41.46    bool target_is_strictfp() const                { return check_flag(TargetIsStrictfpFlag); }
   41.47  
   41.48 +  // JSR 292 support
   41.49 +  bool is_invokedynamic() const                  { return code() == Bytecodes::_invokedynamic; }
   41.50 +
   41.51    // generic
   41.52    virtual bool can_trap() const                  { return true; }
   41.53    virtual void input_values_do(void f(Value*)) {
   41.54 @@ -1169,6 +1174,7 @@
   41.55      if (has_receiver()) f(&_recv);
   41.56      for (int i = 0; i < _args->length(); i++) f(_args->adr_at(i));
   41.57    }
   41.58 +  virtual void state_values_do(void f(Value*));
   41.59  };
   41.60  
   41.61  
    42.1 --- a/src/share/vm/c1/c1_LIR.cpp	Thu Mar 25 16:54:59 2010 -0700
    42.2 +++ b/src/share/vm/c1/c1_LIR.cpp	Fri Mar 26 11:10:26 2010 -0400
    42.3 @@ -1,5 +1,5 @@
    42.4  /*
    42.5 - * Copyright 2000-2008 Sun Microsystems, Inc.  All Rights Reserved.
    42.6 + * Copyright 2000-2010 Sun Microsystems, Inc.  All Rights Reserved.
    42.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    42.8   *
    42.9   * This code is free software; you can redistribute it and/or modify it
   42.10 @@ -76,7 +76,7 @@
   42.11        return LIR_OprFact::oopConst(type->as_ObjectType()->encoding());
   42.12      }
   42.13    }
   42.14 -  case addressTag: return LIR_OprFact::intConst(type->as_AddressConstant()->value());
   42.15 +  case addressTag: return LIR_OprFact::addressConst(type->as_AddressConstant()->value());
   42.16    case intTag    : return LIR_OprFact::intConst(type->as_IntConstant()->value());
   42.17    case floatTag  : return LIR_OprFact::floatConst(type->as_FloatConstant()->value());
   42.18    case longTag   : return LIR_OprFact::longConst(type->as_LongConstant()->value());
   42.19 @@ -89,7 +89,7 @@
   42.20  LIR_Opr LIR_OprFact::dummy_value_type(ValueType* type) {
   42.21    switch (type->tag()) {
   42.22      case objectTag: return LIR_OprFact::oopConst(NULL);
   42.23 -    case addressTag:
   42.24 +    case addressTag:return LIR_OprFact::addressConst(0);
   42.25      case intTag:    return LIR_OprFact::intConst(0);
   42.26      case floatTag:  return LIR_OprFact::floatConst(0.0);
   42.27      case longTag:   return LIR_OprFact::longConst(0);
   42.28 @@ -689,9 +689,10 @@
   42.29      case lir_static_call:
   42.30      case lir_optvirtual_call:
   42.31      case lir_icvirtual_call:
   42.32 -    case lir_virtual_call: {
   42.33 -      assert(op->as_OpJavaCall() != NULL, "must be");
   42.34 -      LIR_OpJavaCall* opJavaCall = (LIR_OpJavaCall*)op;
   42.35 +    case lir_virtual_call:
   42.36 +    case lir_dynamic_call: {
   42.37 +      LIR_OpJavaCall* opJavaCall = op->as_OpJavaCall();
   42.38 +      assert(opJavaCall != NULL, "must be");
   42.39  
   42.40        if (opJavaCall->_receiver->is_valid())     do_input(opJavaCall->_receiver);
   42.41  
   42.42 @@ -704,6 +705,7 @@
   42.43        }
   42.44  
   42.45        if (opJavaCall->_info)                     do_info(opJavaCall->_info);
   42.46 +      if (opJavaCall->is_method_handle_invoke()) do_temp(FrameMap::method_handle_invoke_SP_save_opr());
   42.47        do_call();
   42.48        if (opJavaCall->_result->is_valid())       do_output(opJavaCall->_result);
   42.49  
   42.50 @@ -1410,6 +1412,7 @@
   42.51  // LIR_Address
   42.52  void LIR_Const::print_value_on(outputStream* out) const {
   42.53    switch (type()) {
   42.54 +    case T_ADDRESS:out->print("address:%d",as_jint());          break;
   42.55      case T_INT:    out->print("int:%d",   as_jint());           break;
   42.56      case T_LONG:   out->print("lng:%lld", as_jlong());          break;
   42.57      case T_FLOAT:  out->print("flt:%f",   as_jfloat());         break;
   42.58 @@ -1590,6 +1593,7 @@
   42.59       case lir_optvirtual_call:       s = "optvirtual";    break;
   42.60       case lir_icvirtual_call:        s = "icvirtual";     break;
   42.61       case lir_virtual_call:          s = "virtual";       break;
   42.62 +     case lir_dynamic_call:          s = "dynamic";       break;
   42.63       // LIR_OpArrayCopy
   42.64       case lir_arraycopy:             s = "arraycopy";     break;
   42.65       // LIR_OpLock
    43.1 --- a/src/share/vm/c1/c1_LIR.hpp	Thu Mar 25 16:54:59 2010 -0700
    43.2 +++ b/src/share/vm/c1/c1_LIR.hpp	Fri Mar 26 11:10:26 2010 -0400
    43.3 @@ -85,9 +85,10 @@
    43.4  
    43.5    void type_check(BasicType t) const   { assert(type() == t, "type check"); }
    43.6    void type_check(BasicType t1, BasicType t2) const   { assert(type() == t1 || type() == t2, "type check"); }
    43.7 +  void type_check(BasicType t1, BasicType t2, BasicType t3) const   { assert(type() == t1 || type() == t2 || type() == t3, "type check"); }
    43.8  
    43.9   public:
   43.10 -  LIR_Const(jint i)                              { _value.set_type(T_INT);     _value.set_jint(i); }
   43.11 +  LIR_Const(jint i, bool is_address=false)       { _value.set_type(is_address?T_ADDRESS:T_INT); _value.set_jint(i); }
   43.12    LIR_Const(jlong l)                             { _value.set_type(T_LONG);    _value.set_jlong(l); }
   43.13    LIR_Const(jfloat f)                            { _value.set_type(T_FLOAT);   _value.set_jfloat(f); }
   43.14    LIR_Const(jdouble d)                           { _value.set_type(T_DOUBLE);  _value.set_jdouble(d); }
   43.15 @@ -105,7 +106,7 @@
   43.16    virtual BasicType type()       const { return _value.get_type(); }
   43.17    virtual LIR_Const* as_constant()     { return this; }
   43.18  
   43.19 -  jint      as_jint()    const         { type_check(T_INT   ); return _value.get_jint(); }
   43.20 +  jint      as_jint()    const         { type_check(T_INT, T_ADDRESS); return _value.get_jint(); }
   43.21    jlong     as_jlong()   const         { type_check(T_LONG  ); return _value.get_jlong(); }
   43.22    jfloat    as_jfloat()  const         { type_check(T_FLOAT ); return _value.get_jfloat(); }
   43.23    jdouble   as_jdouble() const         { type_check(T_DOUBLE); return _value.get_jdouble(); }
   43.24 @@ -120,7 +121,7 @@
   43.25  #endif
   43.26  
   43.27  
   43.28 -  jint      as_jint_bits() const       { type_check(T_FLOAT, T_INT); return _value.get_jint(); }
   43.29 +  jint      as_jint_bits() const       { type_check(T_FLOAT, T_INT, T_ADDRESS); return _value.get_jint(); }
   43.30    jint      as_jint_lo_bits() const    {
   43.31      if (type() == T_DOUBLE) {
   43.32        return low(jlong_cast(_value.get_jdouble()));
   43.33 @@ -718,6 +719,7 @@
   43.34    static LIR_Opr intptrConst(void* p)            { return (LIR_Opr)(new LIR_Const(p)); }
   43.35    static LIR_Opr intptrConst(intptr_t v)         { return (LIR_Opr)(new LIR_Const((void*)v)); }
   43.36    static LIR_Opr illegal()                       { return (LIR_Opr)-1; }
   43.37 +  static LIR_Opr addressConst(jint i)            { return (LIR_Opr)(new LIR_Const(i, true)); }
   43.38  
   43.39    static LIR_Opr value_type(ValueType* type);
   43.40    static LIR_Opr dummy_value_type(ValueType* type);
   43.41 @@ -840,6 +842,7 @@
   43.42        , lir_optvirtual_call
   43.43        , lir_icvirtual_call
   43.44        , lir_virtual_call
   43.45 +      , lir_dynamic_call
   43.46    , end_opJavaCall
   43.47    , begin_opArrayCopy
   43.48        , lir_arraycopy
   43.49 @@ -1052,6 +1055,16 @@
   43.50    LIR_Opr receiver() const                       { return _receiver; }
   43.51    ciMethod* method() const                       { return _method;   }
   43.52  
   43.53 +  // JSR 292 support.
   43.54 +  bool is_invokedynamic() const                  { return code() == lir_dynamic_call; }
   43.55 +  bool is_method_handle_invoke() const {
   43.56 +    return
   43.57 +      is_invokedynamic()  // An invokedynamic is always a MethodHandle call site.
   43.58 +      ||
   43.59 +      (method()->holder()->name() == ciSymbol::java_dyn_MethodHandle() &&
   43.60 +       method()->name()           == ciSymbol::invoke_name());
   43.61 +  }
   43.62 +
   43.63    intptr_t vtable_offset() const {
   43.64      assert(_code == lir_virtual_call, "only have vtable for real vcall");
   43.65      return (intptr_t) addr();
   43.66 @@ -1766,6 +1779,10 @@
   43.67                      intptr_t vtable_offset, LIR_OprList* arguments, CodeEmitInfo* info) {
   43.68      append(new LIR_OpJavaCall(lir_virtual_call, method, receiver, result, vtable_offset, arguments, info));
   43.69    }
   43.70 +  void call_dynamic(ciMethod* method, LIR_Opr receiver, LIR_Opr result,
   43.71 +                    address dest, LIR_OprList* arguments, CodeEmitInfo* info) {
   43.72 +    append(new LIR_OpJavaCall(lir_dynamic_call, method, receiver, result, dest, arguments, info));
   43.73 +  }
   43.74  
   43.75    void get_thread(LIR_Opr result)                { append(new LIR_Op0(lir_get_thread, result)); }
   43.76    void word_align()                              { append(new LIR_Op0(lir_word_align)); }
    44.1 --- a/src/share/vm/c1/c1_LIRAssembler.cpp	Thu Mar 25 16:54:59 2010 -0700
    44.2 +++ b/src/share/vm/c1/c1_LIRAssembler.cpp	Fri Mar 26 11:10:26 2010 -0400
    44.3 @@ -1,5 +1,5 @@
    44.4  /*
    44.5 - * Copyright 2000-2009 Sun Microsystems, Inc.  All Rights Reserved.
    44.6 + * Copyright 2000-2010 Sun Microsystems, Inc.  All Rights Reserved.
    44.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    44.8   *
    44.9   * This code is free software; you can redistribute it and/or modify it
   44.10 @@ -301,9 +301,9 @@
   44.11  }
   44.12  
   44.13  
   44.14 -void LIR_Assembler::add_call_info(int pc_offset, CodeEmitInfo* cinfo) {
   44.15 +void LIR_Assembler::add_call_info(int pc_offset, CodeEmitInfo* cinfo, bool is_method_handle_invoke) {
   44.16    flush_debug_info(pc_offset);
   44.17 -  cinfo->record_debug_info(compilation()->debug_info_recorder(), pc_offset);
   44.18 +  cinfo->record_debug_info(compilation()->debug_info_recorder(), pc_offset, is_method_handle_invoke);
   44.19    if (cinfo->exception_handlers() != NULL) {
   44.20      compilation()->add_exception_handlers_for_pco(pc_offset, cinfo->exception_handlers());
   44.21    }
   44.22 @@ -413,6 +413,12 @@
   44.23  void LIR_Assembler::emit_call(LIR_OpJavaCall* op) {
   44.24    verify_oop_map(op->info());
   44.25  
   44.26 +  // JSR 292
   44.27 +  // Preserve the SP over MethodHandle call sites.
   44.28 +  if (op->is_method_handle_invoke()) {
   44.29 +    preserve_SP(op);
   44.30 +  }
   44.31 +
   44.32    if (os::is_MP()) {
   44.33      // must align calls sites, otherwise they can't be updated atomically on MP hardware
   44.34      align_call(op->code());
   44.35 @@ -423,19 +429,25 @@
   44.36  
   44.37    switch (op->code()) {
   44.38    case lir_static_call:
   44.39 -    call(op->addr(), relocInfo::static_call_type, op->info());
   44.40 +    call(op, relocInfo::static_call_type);
   44.41      break;
   44.42    case lir_optvirtual_call:
   44.43 -    call(op->addr(), relocInfo::opt_virtual_call_type, op->info());
   44.44 +  case lir_dynamic_call:
   44.45 +    call(op, relocInfo::opt_virtual_call_type);
   44.46      break;
   44.47    case lir_icvirtual_call:
   44.48 -    ic_call(op->addr(), op->info());
   44.49 +    ic_call(op);
   44.50      break;
   44.51    case lir_virtual_call:
   44.52 -    vtable_call(op->vtable_offset(), op->info());
   44.53 +    vtable_call(op);
   44.54      break;
   44.55    default: ShouldNotReachHere();
   44.56    }
   44.57 +
   44.58 +  if (op->is_method_handle_invoke()) {
   44.59 +    restore_SP(op);
   44.60 +  }
   44.61 +
   44.62  #if defined(X86) && defined(TIERED)
   44.63    // C2 leave fpu stack dirty clean it
   44.64    if (UseSSE < 2) {
    45.1 --- a/src/share/vm/c1/c1_LIRAssembler.hpp	Thu Mar 25 16:54:59 2010 -0700
    45.2 +++ b/src/share/vm/c1/c1_LIRAssembler.hpp	Fri Mar 26 11:10:26 2010 -0400
    45.3 @@ -82,7 +82,7 @@
    45.4    Address as_Address_hi(LIR_Address* addr);
    45.5  
    45.6    // debug information
    45.7 -  void add_call_info(int pc_offset, CodeEmitInfo* cinfo);
    45.8 +  void add_call_info(int pc_offset, CodeEmitInfo* cinfo, bool is_method_handle_invoke = false);
    45.9    void add_debug_info_for_branch(CodeEmitInfo* info);
   45.10    void add_debug_info_for_div0(int pc_offset, CodeEmitInfo* cinfo);
   45.11    void add_debug_info_for_div0_here(CodeEmitInfo* info);
   45.12 @@ -205,9 +205,13 @@
   45.13    void comp_fl2i(LIR_Code code, LIR_Opr left, LIR_Opr right, LIR_Opr result, LIR_Op2* op);
   45.14    void cmove(LIR_Condition code, LIR_Opr left, LIR_Opr right, LIR_Opr result);
   45.15  
   45.16 -  void ic_call(address destination, CodeEmitInfo* info);
   45.17 -  void vtable_call(int vtable_offset, CodeEmitInfo* info);
   45.18 -  void call(address entry, relocInfo::relocType rtype, CodeEmitInfo* info);
   45.19 +  void call(        LIR_OpJavaCall* op, relocInfo::relocType rtype);
   45.20 +  void ic_call(     LIR_OpJavaCall* op);
   45.21 +  void vtable_call( LIR_OpJavaCall* op);
   45.22 +
   45.23 +  // JSR 292
   45.24 +  void preserve_SP(LIR_OpJavaCall* op);
   45.25 +  void restore_SP( LIR_OpJavaCall* op);
   45.26  
   45.27    void osr_entry();
   45.28  
    46.1 --- a/src/share/vm/c1/c1_LIRGenerator.cpp	Thu Mar 25 16:54:59 2010 -0700
    46.2 +++ b/src/share/vm/c1/c1_LIRGenerator.cpp	Fri Mar 26 11:10:26 2010 -0400
    46.3 @@ -2284,7 +2284,7 @@
    46.4  
    46.5  
    46.6  void LIRGenerator::invoke_load_arguments(Invoke* x, LIRItemList* args, const LIR_OprList* arg_list) {
    46.7 -  int i = x->has_receiver() ? 1 : 0;
    46.8 +  int i = (x->has_receiver() || x->is_invokedynamic()) ? 1 : 0;
    46.9    for (; i < args->length(); i++) {
   46.10      LIRItem* param = args->at(i);
   46.11      LIR_Opr loc = arg_list->at(i);
   46.12 @@ -2322,6 +2322,10 @@
   46.13      LIRItem* receiver = new LIRItem(x->receiver(), this);
   46.14      argument_items->append(receiver);
   46.15    }
   46.16 +  if (x->is_invokedynamic()) {
   46.17 +    // Insert a dummy for the synthetic MethodHandle argument.
   46.18 +    argument_items->append(NULL);
   46.19 +  }
   46.20    int idx = x->has_receiver() ? 1 : 0;
   46.21    for (int i = 0; i < x->number_of_arguments(); i++) {
   46.22      LIRItem* param = new LIRItem(x->argument_at(i), this);
   46.23 @@ -2371,6 +2375,9 @@
   46.24  
   46.25    CodeEmitInfo* info = state_for(x, x->state());
   46.26  
   46.27 +  // invokedynamics can deoptimize.
   46.28 +  CodeEmitInfo* deopt_info = x->is_invokedynamic() ? state_for(x, x->state_before()) : NULL;
   46.29 +
   46.30    invoke_load_arguments(x, args, arg_list);
   46.31  
   46.32    if (x->has_receiver()) {
   46.33 @@ -2407,6 +2414,47 @@
   46.34          __ call_virtual(x->target(), receiver, result_register, vtable_offset, arg_list, info);
   46.35        }
   46.36        break;
   46.37 +    case Bytecodes::_invokedynamic: {
   46.38 +      ciBytecodeStream bcs(x->scope()->method());
   46.39 +      bcs.force_bci(x->bci());
   46.40 +      assert(bcs.cur_bc() == Bytecodes::_invokedynamic, "wrong stream");
   46.41 +      ciCPCache* cpcache = bcs.get_cpcache();
   46.42 +
   46.43 +      // Get CallSite offset from constant pool cache pointer.
   46.44 +      int index = bcs.get_method_index();
   46.45 +      size_t call_site_offset = cpcache->get_f1_offset(index);
   46.46 +
   46.47 +      // If this invokedynamic call site hasn't been executed yet in
   46.48 +      // the interpreter, the CallSite object in the constant pool
   46.49 +      // cache is still null and we need to deoptimize.
   46.50 +      if (cpcache->is_f1_null_at(index)) {
   46.51 +        // Cannot re-use same xhandlers for multiple CodeEmitInfos, so
   46.52 +        // clone all handlers.  This is handled transparently in other
   46.53 +        // places by the CodeEmitInfo cloning logic but is handled
   46.54 +        // specially here because a stub isn't being used.
   46.55 +        x->set_exception_handlers(new XHandlers(x->exception_handlers()));
   46.56 +
   46.57 +        DeoptimizeStub* deopt_stub = new DeoptimizeStub(deopt_info);
   46.58 +        __ jump(deopt_stub);
   46.59 +      }
   46.60 +
   46.61 +      // Use the receiver register for the synthetic MethodHandle
   46.62 +      // argument.
   46.63 +      receiver = LIR_Assembler::receiverOpr();
   46.64 +      LIR_Opr tmp = new_register(objectType);
   46.65 +
   46.66 +      // Load CallSite object from constant pool cache.
   46.67 +      __ oop2reg(cpcache->constant_encoding(), tmp);
   46.68 +      __ load(new LIR_Address(tmp, call_site_offset, T_OBJECT), tmp);
   46.69 +
   46.70 +      // Load target MethodHandle from CallSite object.
   46.71 +      __ load(new LIR_Address(tmp, java_dyn_CallSite::target_offset_in_bytes(), T_OBJECT), receiver);
   46.72 +
   46.73 +      __ call_dynamic(x->target(), receiver, result_register,
   46.74 +                      SharedRuntime::get_resolve_opt_virtual_call_stub(),
   46.75 +                      arg_list, info);
   46.76 +      break;
   46.77 +    }
   46.78      default:
   46.79        ShouldNotReachHere();
   46.80        break;
    47.1 --- a/src/share/vm/c1/c1_LinearScan.cpp	Thu Mar 25 16:54:59 2010 -0700
    47.2 +++ b/src/share/vm/c1/c1_LinearScan.cpp	Fri Mar 26 11:10:26 2010 -0400
    47.3 @@ -2479,6 +2479,15 @@
    47.4        return 2;
    47.5      }
    47.6  
    47.7 +    case T_ADDRESS: {
    47.8 +#ifdef _LP64
    47.9 +      scope_values->append(new ConstantLongValue(c->as_jint()));
   47.10 +#else
   47.11 +      scope_values->append(new ConstantIntValue(c->as_jint()));
   47.12 +#endif
   47.13 +      return 1;
   47.14 +    }
   47.15 +
   47.16      default:
   47.17        ShouldNotReachHere();
   47.18        return -1;
    48.1 --- a/src/share/vm/c1/c1_MacroAssembler.hpp	Thu Mar 25 16:54:59 2010 -0700
    48.2 +++ b/src/share/vm/c1/c1_MacroAssembler.hpp	Fri Mar 26 11:10:26 2010 -0400
    48.3 @@ -1,5 +1,5 @@
    48.4  /*
    48.5 - * Copyright 2000-2005 Sun Microsystems, Inc.  All Rights Reserved.
    48.6 + * Copyright 2000-2010 Sun Microsystems, Inc.  All Rights Reserved.
    48.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    48.8   *
    48.9   * This code is free software; you can redistribute it and/or modify it
   48.10 @@ -34,7 +34,7 @@
   48.11  
   48.12    void inline_cache_check(Register receiver, Register iCache);
   48.13    void build_frame(int frame_size_in_bytes);
   48.14 -  void method_exit(bool restore_frame);
   48.15 +  void remove_frame(int frame_size_in_bytes);
   48.16  
   48.17    void unverified_entry(Register receiver, Register ic_klass);
   48.18    void verified_entry();
    49.1 --- a/src/share/vm/ci/ciCPCache.cpp	Thu Mar 25 16:54:59 2010 -0700
    49.2 +++ b/src/share/vm/ci/ciCPCache.cpp	Fri Mar 26 11:10:26 2010 -0400
    49.3 @@ -1,5 +1,5 @@
    49.4  /*
    49.5 - * Copyright 2009 Sun Microsystems, Inc.  All Rights Reserved.
    49.6 + * Copyright 2009-2010 Sun Microsystems, Inc.  All Rights Reserved.
    49.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    49.8   *
    49.9   * This code is free software; you can redistribute it and/or modify it
   49.10 @@ -41,6 +41,16 @@
   49.11  
   49.12  
   49.13  // ------------------------------------------------------------------
   49.14 +// ciCPCache::is_f1_null_at
   49.15 +bool ciCPCache::is_f1_null_at(int index) {
   49.16 +  VM_ENTRY_MARK;
   49.17 +  constantPoolCacheOop cpcache = (constantPoolCacheOop) get_oop();
   49.18 +  oop f1 = cpcache->secondary_entry_at(index)->f1();
   49.19 +  return (f1 == NULL);
   49.20 +}
   49.21 +
   49.22 +
   49.23 +// ------------------------------------------------------------------
   49.24  // ciCPCache::print
   49.25  //
   49.26  // Print debugging information about the cache.
    50.1 --- a/src/share/vm/ci/ciCPCache.hpp	Thu Mar 25 16:54:59 2010 -0700
    50.2 +++ b/src/share/vm/ci/ciCPCache.hpp	Fri Mar 26 11:10:26 2010 -0400
    50.3 @@ -1,5 +1,5 @@
    50.4  /*
    50.5 - * Copyright 2009 Sun Microsystems, Inc.  All Rights Reserved.
    50.6 + * Copyright 2009-2010 Sun Microsystems, Inc.  All Rights Reserved.
    50.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    50.8   *
    50.9   * This code is free software; you can redistribute it and/or modify it
   50.10 @@ -39,5 +39,7 @@
   50.11    // requested entry.
   50.12    size_t get_f1_offset(int index);
   50.13  
   50.14 +  bool is_f1_null_at(int index);
   50.15 +
   50.16    void print();
   50.17  };
    51.1 --- a/src/share/vm/code/codeBlob.cpp	Thu Mar 25 16:54:59 2010 -0700
    51.2 +++ b/src/share/vm/code/codeBlob.cpp	Fri Mar 26 11:10:26 2010 -0400
    51.3 @@ -1,5 +1,5 @@
    51.4  /*
    51.5 - * Copyright 1998-2007 Sun Microsystems, Inc.  All Rights Reserved.
    51.6 + * Copyright 1998-2010 Sun Microsystems, Inc.  All Rights Reserved.
    51.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    51.8   *
    51.9   * This code is free software; you can redistribute it and/or modify it
   51.10 @@ -249,7 +249,6 @@
   51.11    size += round_to(buffer_size, oopSize);
   51.12    assert(name != NULL, "must provide a name");
   51.13    {
   51.14 -
   51.15      MutexLockerEx mu(CodeCache_lock, Mutex::_no_safepoint_check_flag);
   51.16      blob = new (size) BufferBlob(name, size);
   51.17    }
   51.18 @@ -271,7 +270,6 @@
   51.19    unsigned int size = allocation_size(cb, sizeof(BufferBlob));
   51.20    assert(name != NULL, "must provide a name");
   51.21    {
   51.22 -
   51.23      MutexLockerEx mu(CodeCache_lock, Mutex::_no_safepoint_check_flag);
   51.24      blob = new (size) BufferBlob(name, size, cb);
   51.25    }
   51.26 @@ -298,10 +296,48 @@
   51.27    MemoryService::track_code_cache_memory_usage();
   51.28  }
   51.29  
   51.30 -bool BufferBlob::is_adapter_blob() const {
   51.31 -  return (strcmp(AdapterHandlerEntry::name, name()) == 0);
   51.32 +
   51.33 +//----------------------------------------------------------------------------------------------------
   51.34 +// Implementation of AdapterBlob
   51.35 +
   51.36 +AdapterBlob* AdapterBlob::create(CodeBuffer* cb) {
   51.37 +  ThreadInVMfromUnknown __tiv;  // get to VM state in case we block on CodeCache_lock
   51.38 +
   51.39 +  AdapterBlob* blob = NULL;
   51.40 +  unsigned int size = allocation_size(cb, sizeof(AdapterBlob));
   51.41 +  {
   51.42 +    MutexLockerEx mu(CodeCache_lock, Mutex::_no_safepoint_check_flag);
   51.43 +    blob = new (size) AdapterBlob(size, cb);
   51.44 +  }
   51.45 +  // Track memory usage statistic after releasing CodeCache_lock
   51.46 +  MemoryService::track_code_cache_memory_usage();
   51.47 +
   51.48 +  return blob;
   51.49  }
   51.50  
   51.51 +
   51.52 +//----------------------------------------------------------------------------------------------------
   51.53 +// Implementation of MethodHandlesAdapterBlob
   51.54 +
   51.55 +MethodHandlesAdapterBlob* MethodHandlesAdapterBlob::create(int buffer_size) {
   51.56 +  ThreadInVMfromUnknown __tiv;  // get to VM state in case we block on CodeCache_lock
   51.57 +
   51.58 +  MethodHandlesAdapterBlob* blob = NULL;
   51.59 +  unsigned int size = sizeof(MethodHandlesAdapterBlob);
   51.60 +  // align the size to CodeEntryAlignment
   51.61 +  size = align_code_offset(size);
   51.62 +  size += round_to(buffer_size, oopSize);
   51.63 +  {
   51.64 +    MutexLockerEx mu(CodeCache_lock, Mutex::_no_safepoint_check_flag);
   51.65 +    blob = new (size) MethodHandlesAdapterBlob(size);
   51.66 +  }
   51.67 +  // Track memory usage statistic after releasing CodeCache_lock
   51.68 +  MemoryService::track_code_cache_memory_usage();
   51.69 +
   51.70 +  return blob;
   51.71 +}
   51.72 +
   51.73 +
   51.74  //----------------------------------------------------------------------------------------------------
   51.75  // Implementation of RuntimeStub
   51.76  
    52.1 --- a/src/share/vm/code/codeBlob.hpp	Thu Mar 25 16:54:59 2010 -0700
    52.2 +++ b/src/share/vm/code/codeBlob.hpp	Fri Mar 26 11:10:26 2010 -0400
    52.3 @@ -1,5 +1,5 @@
    52.4  /*
    52.5 - * Copyright 1998-2009 Sun Microsystems, Inc.  All Rights Reserved.
    52.6 + * Copyright 1998-2010 Sun Microsystems, Inc.  All Rights Reserved.
    52.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    52.8   *
    52.9   * This code is free software; you can redistribute it and/or modify it
   52.10 @@ -90,14 +90,15 @@
   52.11    void flush();
   52.12  
   52.13    // Typing
   52.14 -  virtual bool is_buffer_blob() const            { return false; }
   52.15 -  virtual bool is_nmethod() const                { return false; }
   52.16 -  virtual bool is_runtime_stub() const           { return false; }
   52.17 -  virtual bool is_deoptimization_stub() const    { return false; }
   52.18 -  virtual bool is_uncommon_trap_stub() const     { return false; }
   52.19 -  virtual bool is_exception_stub() const         { return false; }
   52.20 -  virtual bool is_safepoint_stub() const         { return false; }
   52.21 -  virtual bool is_adapter_blob() const           { return false; }
   52.22 +  virtual bool is_buffer_blob() const                 { return false; }
   52.23 +  virtual bool is_nmethod() const                     { return false; }
   52.24 +  virtual bool is_runtime_stub() const                { return false; }
   52.25 +  virtual bool is_deoptimization_stub() const         { return false; }
   52.26 +  virtual bool is_uncommon_trap_stub() const          { return false; }
   52.27 +  virtual bool is_exception_stub() const              { return false; }
   52.28 +  virtual bool is_safepoint_stub() const              { return false; }
   52.29 +  virtual bool is_adapter_blob() const                { return false; }
   52.30 +  virtual bool is_method_handles_adapter_blob() const { return false; }
   52.31  
   52.32    virtual bool is_compiled_by_c2() const         { return false; }
   52.33    virtual bool is_compiled_by_c1() const         { return false; }
   52.34 @@ -221,6 +222,9 @@
   52.35  
   52.36  class BufferBlob: public CodeBlob {
   52.37    friend class VMStructs;
   52.38 +  friend class AdapterBlob;
   52.39 +  friend class MethodHandlesAdapterBlob;
   52.40 +
   52.41   private:
   52.42    // Creation support
   52.43    BufferBlob(const char* name, int size);
   52.44 @@ -236,8 +240,7 @@
   52.45    static void free(BufferBlob* buf);
   52.46  
   52.47    // Typing
   52.48 -  bool is_buffer_blob() const                    { return true; }
   52.49 -  bool is_adapter_blob() const;
   52.50 +  virtual bool is_buffer_blob() const            { return true; }
   52.51  
   52.52    // GC/Verification support
   52.53    void preserve_callee_argument_oops(frame fr, const RegisterMap* reg_map, OopClosure* f)  { /* nothing to do */ }
   52.54 @@ -255,6 +258,40 @@
   52.55  
   52.56  
   52.57  //----------------------------------------------------------------------------------------------------
   52.58 +// AdapterBlob: used to hold C2I/I2C adapters
   52.59 +
   52.60 +class AdapterBlob: public BufferBlob {
   52.61 +private:
   52.62 +  AdapterBlob(int size)                 : BufferBlob("I2C/C2I adapters", size) {}
   52.63 +  AdapterBlob(int size, CodeBuffer* cb) : BufferBlob("I2C/C2I adapters", size, cb) {}
   52.64 +
   52.65 +public:
   52.66 +  // Creation
   52.67 +  static AdapterBlob* create(CodeBuffer* cb);
   52.68 +
   52.69 +  // Typing
   52.70 +  virtual bool is_adapter_blob() const { return true; }
   52.71 +};
   52.72 +
   52.73 +
   52.74 +//----------------------------------------------------------------------------------------------------
   52.75 +// MethodHandlesAdapterBlob: used to hold MethodHandles adapters
   52.76 +
   52.77 +class MethodHandlesAdapterBlob: public BufferBlob {
   52.78 +private:
   52.79 +  MethodHandlesAdapterBlob(int size)                 : BufferBlob("MethodHandles adapters", size) {}
   52.80 +  MethodHandlesAdapterBlob(int size, CodeBuffer* cb) : BufferBlob("MethodHandles adapters", size, cb) {}
   52.81 +
   52.82 +public:
   52.83 +  // Creation
   52.84 +  static MethodHandlesAdapterBlob* create(int buffer_size);
   52.85 +
   52.86 +  // Typing
   52.87 +  virtual bool is_method_handles_adapter_blob() const { return true; }
   52.88 +};
   52.89 +
   52.90 +
   52.91 +//----------------------------------------------------------------------------------------------------
   52.92  // RuntimeStub: describes stubs used by compiled code to call a (static) C++ runtime routine
   52.93  
   52.94  class RuntimeStub: public CodeBlob {
    53.1 --- a/src/share/vm/compiler/compileBroker.cpp	Thu Mar 25 16:54:59 2010 -0700
    53.2 +++ b/src/share/vm/compiler/compileBroker.cpp	Fri Mar 26 11:10:26 2010 -0400
    53.3 @@ -988,10 +988,12 @@
    53.4      }
    53.5      if (method->is_not_compilable(comp_level)) return NULL;
    53.6  
    53.7 -    nmethod* saved = CodeCache::find_and_remove_saved_code(method());
    53.8 -    if (saved != NULL) {
    53.9 -      method->set_code(method, saved);
   53.10 -      return saved;
   53.11 +    if (UseCodeCacheFlushing) {
   53.12 +      nmethod* saved = CodeCache::find_and_remove_saved_code(method());
   53.13 +      if (saved != NULL) {
   53.14 +        method->set_code(method, saved);
   53.15 +        return saved;
   53.16 +      }
   53.17      }
   53.18  
   53.19    } else {
    54.1 --- a/src/share/vm/gc_implementation/g1/concurrentMark.cpp	Thu Mar 25 16:54:59 2010 -0700
    54.2 +++ b/src/share/vm/gc_implementation/g1/concurrentMark.cpp	Fri Mar 26 11:10:26 2010 -0400
    54.3 @@ -3704,7 +3704,14 @@
    54.4          // enough to point to the next possible object header (the
    54.5          // bitmap knows by how much we need to move it as it knows its
    54.6          // granularity).
    54.7 -        move_finger_to(_nextMarkBitMap->nextWord(_finger));
    54.8 +        assert(_finger < _region_limit, "invariant");
    54.9 +        HeapWord* new_finger = _nextMarkBitMap->nextWord(_finger);
   54.10 +        // Check if bitmap iteration was aborted while scanning the last object
   54.11 +        if (new_finger >= _region_limit) {
   54.12 +            giveup_current_region();
   54.13 +        } else {
   54.14 +            move_finger_to(new_finger);
   54.15 +        }
   54.16        }
   54.17      }
   54.18      // At this point we have either completed iterating over the
    55.1 --- a/src/share/vm/gc_implementation/g1/concurrentMark.hpp	Thu Mar 25 16:54:59 2010 -0700
    55.2 +++ b/src/share/vm/gc_implementation/g1/concurrentMark.hpp	Fri Mar 26 11:10:26 2010 -0400
    55.3 @@ -24,8 +24,8 @@
    55.4  
    55.5  class G1CollectedHeap;
    55.6  class CMTask;
    55.7 -typedef GenericTaskQueue<oop> CMTaskQueue;
    55.8 -typedef GenericTaskQueueSet<oop> CMTaskQueueSet;
    55.9 +typedef GenericTaskQueue<oop>            CMTaskQueue;
   55.10 +typedef GenericTaskQueueSet<CMTaskQueue> CMTaskQueueSet;
   55.11  
   55.12  // A generic CM bit map.  This is essentially a wrapper around the BitMap
   55.13  // class, with one bit per (1<<_shifter) HeapWords.
    56.1 --- a/src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp	Thu Mar 25 16:54:59 2010 -0700
    56.2 +++ b/src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp	Fri Mar 26 11:10:26 2010 -0400
    56.3 @@ -2102,18 +2102,21 @@
    56.4  size_t G1CollectedHeap::unsafe_max_tlab_alloc(Thread* ignored) const {
    56.5    // Return the remaining space in the cur alloc region, but not less than
    56.6    // the min TLAB size.
    56.7 -  // Also, no more than half the region size, since we can't allow tlabs to
    56.8 -  // grow big enough to accomodate humongous objects.
    56.9 -
   56.10 -  // We need to story it locally, since it might change between when we
   56.11 -  // test for NULL and when we use it later.
   56.12 +
   56.13 +  // Also, this value can be at most the humongous object threshold,
   56.14 +  // since we can't allow tlabs to grow big enough to accomodate
   56.15 +  // humongous objects.
   56.16 +
   56.17 +  // We need to store the cur alloc region locally, since it might change
   56.18 +  // between when we test for NULL and when we use it later.
   56.19    ContiguousSpace* cur_alloc_space = _cur_alloc_region;
   56.20 +  size_t max_tlab_size = _humongous_object_threshold_in_words * wordSize;
   56.21 +
   56.22    if (cur_alloc_space == NULL) {
   56.23 -    return HeapRegion::GrainBytes/2;
   56.24 +    return max_tlab_size;
   56.25    } else {
   56.26 -    return MAX2(MIN2(cur_alloc_space->free(),
   56.27 -                     (size_t)(HeapRegion::GrainBytes/2)),
   56.28 -                (size_t)MinTLABSize);
   56.29 +    return MIN2(MAX2(cur_alloc_space->free(), (size_t)MinTLABSize),
   56.30 +                max_tlab_size);
   56.31    }
   56.32  }
   56.33  
    57.1 --- a/src/share/vm/gc_implementation/g1/g1CollectedHeap.hpp	Thu Mar 25 16:54:59 2010 -0700
    57.2 +++ b/src/share/vm/gc_implementation/g1/g1CollectedHeap.hpp	Fri Mar 26 11:10:26 2010 -0400
    57.3 @@ -56,8 +56,8 @@
    57.4  #  define IF_G1_DETAILED_STATS(code)
    57.5  #endif
    57.6  
    57.7 -typedef GenericTaskQueue<StarTask>    RefToScanQueue;
    57.8 -typedef GenericTaskQueueSet<StarTask> RefToScanQueueSet;
    57.9 +typedef GenericTaskQueue<StarTask>          RefToScanQueue;
   57.10 +typedef GenericTaskQueueSet<RefToScanQueue> RefToScanQueueSet;
   57.11  
   57.12  typedef int RegionIdx_t;   // needs to hold [ 0..max_regions() )
   57.13  typedef int CardIdx_t;     // needs to hold [ 0..CardsPerRegion )
   57.14 @@ -1055,7 +1055,12 @@
   57.15  
   57.16    // Returns "true" iff the given word_size is "very large".
   57.17    static bool isHumongous(size_t word_size) {
   57.18 -    return word_size >= _humongous_object_threshold_in_words;
   57.19 +    // Note this has to be strictly greater-than as the TLABs
   57.20 +    // are capped at the humongous thresold and we want to
   57.21 +    // ensure that we don't try to allocate a TLAB as
   57.22 +    // humongous and that we don't allocate a humongous
   57.23 +    // object in a TLAB.
   57.24 +    return word_size > _humongous_object_threshold_in_words;
   57.25    }
   57.26  
   57.27    // Update mod union table with the set of dirty cards.
    58.1 --- a/src/share/vm/gc_implementation/g1/g1MarkSweep.cpp	Thu Mar 25 16:54:59 2010 -0700
    58.2 +++ b/src/share/vm/gc_implementation/g1/g1MarkSweep.cpp	Fri Mar 26 11:10:26 2010 -0400
    58.3 @@ -101,6 +101,8 @@
    58.4  
    58.5    GenMarkSweep::_marking_stack =
    58.6      new (ResourceObj::C_HEAP) GrowableArray<oop>(4000, true);
    58.7 +  GenMarkSweep::_objarray_stack =
    58.8 +    new (ResourceObj::C_HEAP) GrowableArray<ObjArrayTask>(50, true);
    58.9  
   58.10    int size = SystemDictionary::number_of_classes() * 2;
   58.11    GenMarkSweep::_revisit_klass_stack =
    59.1 --- a/src/share/vm/gc_implementation/includeDB_gc_parallelScavenge	Thu Mar 25 16:54:59 2010 -0700
    59.2 +++ b/src/share/vm/gc_implementation/includeDB_gc_parallelScavenge	Fri Mar 26 11:10:26 2010 -0400
    59.3 @@ -175,6 +175,7 @@
    59.4  psAdaptiveSizePolicy.hpp		adaptiveSizePolicy.hpp
    59.5  
    59.6  psCompactionManager.cpp                 gcTaskManager.hpp
    59.7 +psCompactionManager.cpp                 objArrayKlass.inline.hpp
    59.8  psCompactionManager.cpp                 objectStartArray.hpp
    59.9  psCompactionManager.cpp                 oop.hpp
   59.10  psCompactionManager.cpp                 oop.inline.hpp
   59.11 @@ -189,6 +190,9 @@
   59.12  psCompactionManager.hpp                 allocation.hpp
   59.13  psCompactionManager.hpp                 taskqueue.hpp
   59.14  
   59.15 +psCompactionManager.inline.hpp		psCompactionManager.hpp
   59.16 +psCompactionManager.inline.hpp		psParallelCompact.hpp
   59.17 +
   59.18  psGCAdaptivePolicyCounters.hpp		gcAdaptivePolicyCounters.hpp
   59.19  psGCAdaptivePolicyCounters.hpp          gcPolicyCounters.hpp
   59.20  psGCAdaptivePolicyCounters.hpp          psAdaptiveSizePolicy.hpp
   59.21 @@ -379,12 +383,12 @@
   59.22  pcTasks.cpp                             jniHandles.hpp
   59.23  pcTasks.cpp                             jvmtiExport.hpp
   59.24  pcTasks.cpp                             management.hpp
   59.25 +pcTasks.cpp                             objArrayKlass.inline.hpp
   59.26  pcTasks.cpp                             psParallelCompact.hpp
   59.27  pcTasks.cpp                             pcTasks.hpp
   59.28  pcTasks.cpp                             oop.inline.hpp
   59.29  pcTasks.cpp                             oop.pcgc.inline.hpp
   59.30  pcTasks.cpp                             systemDictionary.hpp
   59.31 -pcTasks.cpp                             taskqueue.hpp
   59.32  pcTasks.cpp                             thread.hpp
   59.33  pcTasks.cpp                             universe.hpp
   59.34  pcTasks.cpp                             vmThread.hpp
    60.1 --- a/src/share/vm/gc_implementation/parallelScavenge/pcTasks.cpp	Thu Mar 25 16:54:59 2010 -0700
    60.2 +++ b/src/share/vm/gc_implementation/parallelScavenge/pcTasks.cpp	Fri Mar 26 11:10:26 2010 -0400
    60.3 @@ -48,7 +48,7 @@
    60.4      _vm_thread->oops_do(&mark_and_push_closure, &mark_and_push_in_blobs);
    60.5  
    60.6    // Do the real work
    60.7 -  cm->drain_marking_stacks(&mark_and_push_closure);
    60.8 +  cm->follow_marking_stacks();
    60.9  }
   60.10  
   60.11  
   60.12 @@ -118,7 +118,7 @@
   60.13    }
   60.14  
   60.15    // Do the real work
   60.16 -  cm->drain_marking_stacks(&mark_and_push_closure);
   60.17 +  cm->follow_marking_stacks();
   60.18    // cm->deallocate_stacks();
   60.19  }
   60.20  
   60.21 @@ -196,17 +196,19 @@
   60.22    PSParallelCompact::MarkAndPushClosure mark_and_push_closure(cm);
   60.23  
   60.24    oop obj = NULL;
   60.25 +  ObjArrayTask task;
   60.26    int random_seed = 17;
   60.27 -  while(true) {
   60.28 -    if (ParCompactionManager::steal(which, &random_seed, obj)) {
   60.29 +  do {
   60.30 +    while (ParCompactionManager::steal_objarray(which, &random_seed, task)) {
   60.31 +      objArrayKlass* const k = (objArrayKlass*)task.obj()->blueprint();
   60.32 +      k->oop_follow_contents(cm, task.obj(), task.index());
   60.33 +      cm->follow_marking_stacks();
   60.34 +    }
   60.35 +    while (ParCompactionManager::steal(which, &random_seed, obj)) {
   60.36        obj->follow_contents(cm);
   60.37 -      cm->drain_marking_stacks(&mark_and_push_closure);
   60.38 -    } else {
   60.39 -      if (terminator()->offer_termination()) {
   60.40 -        break;
   60.41 -      }
   60.42 +      cm->follow_marking_stacks();
   60.43      }
   60.44 -  }
   60.45 +  } while (!terminator()->offer_termination());
   60.46  }
   60.47  
   60.48  //
    61.1 --- a/src/share/vm/gc_implementation/parallelScavenge/psCompactionManager.cpp	Thu Mar 25 16:54:59 2010 -0700
    61.2 +++ b/src/share/vm/gc_implementation/parallelScavenge/psCompactionManager.cpp	Fri Mar 26 11:10:26 2010 -0400
    61.3 @@ -28,6 +28,8 @@
    61.4  PSOldGen*            ParCompactionManager::_old_gen = NULL;
    61.5  ParCompactionManager**  ParCompactionManager::_manager_array = NULL;
    61.6  OopTaskQueueSet*     ParCompactionManager::_stack_array = NULL;
    61.7 +ParCompactionManager::ObjArrayTaskQueueSet*
    61.8 +  ParCompactionManager::_objarray_queues = NULL;
    61.9  ObjectStartArray*    ParCompactionManager::_start_array = NULL;
   61.10  ParMarkBitMap*       ParCompactionManager::_mark_bitmap = NULL;
   61.11  RegionTaskQueueSet*   ParCompactionManager::_region_array = NULL;
   61.12 @@ -46,6 +48,11 @@
   61.13  
   61.14    // We want the overflow stack to be permanent
   61.15    _overflow_stack = new (ResourceObj::C_HEAP) GrowableArray<oop>(10, true);
   61.16 +
   61.17 +  _objarray_queue.initialize();
   61.18 +  _objarray_overflow_stack =
   61.19 +    new (ResourceObj::C_HEAP) ObjArrayOverflowStack(10, true);
   61.20 +
   61.21  #ifdef USE_RegionTaskQueueWithOverflow
   61.22    region_stack()->initialize();
   61.23  #else
   61.24 @@ -69,6 +76,7 @@
   61.25  
   61.26  ParCompactionManager::~ParCompactionManager() {
   61.27    delete _overflow_stack;
   61.28 +  delete _objarray_overflow_stack;
   61.29    delete _revisit_klass_stack;
   61.30    delete _revisit_mdo_stack;
   61.31    // _manager_array and _stack_array are statics
   61.32 @@ -86,18 +94,21 @@
   61.33  
   61.34    assert(_manager_array == NULL, "Attempt to initialize twice");
   61.35    _manager_array = NEW_C_HEAP_ARRAY(ParCompactionManager*, parallel_gc_threads+1 );
   61.36 -  guarantee(_manager_array != NULL, "Could not initialize promotion manager");
   61.37 +  guarantee(_manager_array != NULL, "Could not allocate manager_array");
   61.38  
   61.39    _stack_array = new OopTaskQueueSet(parallel_gc_threads);
   61.40 -  guarantee(_stack_array != NULL, "Count not initialize promotion manager");
   61.41 +  guarantee(_stack_array != NULL, "Could not allocate stack_array");
   61.42 +  _objarray_queues = new ObjArrayTaskQueueSet(parallel_gc_threads);
   61.43 +  guarantee(_objarray_queues != NULL, "Could not allocate objarray_queues");
   61.44    _region_array = new RegionTaskQueueSet(parallel_gc_threads);
   61.45 -  guarantee(_region_array != NULL, "Count not initialize promotion manager");
   61.46 +  guarantee(_region_array != NULL, "Could not allocate region_array");
   61.47  
   61.48    // Create and register the ParCompactionManager(s) for the worker threads.
   61.49    for(uint i=0; i<parallel_gc_threads; i++) {
   61.50      _manager_array[i] = new ParCompactionManager();
   61.51      guarantee(_manager_array[i] != NULL, "Could not create ParCompactionManager");
   61.52      stack_array()->register_queue(i, _manager_array[i]->marking_stack());
   61.53 +    _objarray_queues->register_queue(i, &_manager_array[i]->_objarray_queue);
   61.54  #ifdef USE_RegionTaskQueueWithOverflow
   61.55      region_array()->register_queue(i, _manager_array[i]->region_stack()->task_queue());
   61.56  #else
   61.57 @@ -203,36 +214,30 @@
   61.58    }
   61.59  }
   61.60  
   61.61 -void ParCompactionManager::drain_marking_stacks(OopClosure* blk) {
   61.62 -#ifdef ASSERT
   61.63 -  ParallelScavengeHeap* heap = (ParallelScavengeHeap*)Universe::heap();
   61.64 -  assert(heap->kind() == CollectedHeap::ParallelScavengeHeap, "Sanity");
   61.65 -  MutableSpace* to_space = heap->young_gen()->to_space();
   61.66 -  MutableSpace* old_space = heap->old_gen()->object_space();
   61.67 -  MutableSpace* perm_space = heap->perm_gen()->object_space();
   61.68 -#endif /* ASSERT */
   61.69 -
   61.70 -
   61.71 +void ParCompactionManager::follow_marking_stacks() {
   61.72    do {
   61.73 -
   61.74 -    // Drain overflow stack first, so other threads can steal from
   61.75 -    // claimed stack while we work.
   61.76 -    while(!overflow_stack()->is_empty()) {
   61.77 -      oop obj = overflow_stack()->pop();
   61.78 +    // Drain the overflow stack first, to allow stealing from the marking stack.
   61.79 +    oop obj;
   61.80 +    while (!overflow_stack()->is_empty()) {
   61.81 +      overflow_stack()->pop()->follow_contents(this);
   61.82 +    }
   61.83 +    while (marking_stack()->pop_local(obj)) {
   61.84        obj->follow_contents(this);
   61.85      }
   61.86  
   61.87 -    oop obj;
   61.88 -    // obj is a reference!!!
   61.89 -    while (marking_stack()->pop_local(obj)) {
   61.90 -      // It would be nice to assert about the type of objects we might
   61.91 -      // pop, but they can come from anywhere, unfortunately.
   61.92 -      obj->follow_contents(this);
   61.93 +    // Process ObjArrays one at a time to avoid marking stack bloat.
   61.94 +    ObjArrayTask task;
   61.95 +    if (!_objarray_overflow_stack->is_empty()) {
   61.96 +      task = _objarray_overflow_stack->pop();
   61.97 +      objArrayKlass* const k = (objArrayKlass*)task.obj()->blueprint();
   61.98 +      k->oop_follow_contents(this, task.obj(), task.index());
   61.99 +    } else if (_objarray_queue.pop_local(task)) {
  61.100 +      objArrayKlass* const k = (objArrayKlass*)task.obj()->blueprint();
  61.101 +      k->oop_follow_contents(this, task.obj(), task.index());
  61.102      }
  61.103 -  } while((marking_stack()->size() != 0) || (overflow_stack()->length() != 0));
  61.104 +  } while (!marking_stacks_empty());
  61.105  
  61.106 -  assert(marking_stack()->size() == 0, "Sanity");
  61.107 -  assert(overflow_stack()->length() == 0, "Sanity");
  61.108 +  assert(marking_stacks_empty(), "Sanity");
  61.109  }
  61.110  
  61.111  void ParCompactionManager::drain_region_overflow_stack() {
    62.1 --- a/src/share/vm/gc_implementation/parallelScavenge/psCompactionManager.hpp	Thu Mar 25 16:54:59 2010 -0700
    62.2 +++ b/src/share/vm/gc_implementation/parallelScavenge/psCompactionManager.hpp	Fri Mar 26 11:10:26 2010 -0400
    62.3 @@ -22,18 +22,6 @@
    62.4   *
    62.5   */
    62.6  
    62.7 -//
    62.8 -// psPromotionManager is used by a single thread to manage object survival
    62.9 -// during a scavenge. The promotion manager contains thread local data only.
   62.10 -//
   62.11 -// NOTE! Be carefull when allocating the stacks on cheap. If you are going
   62.12 -// to use a promotion manager in more than one thread, the stacks MUST be
   62.13 -// on cheap. This can lead to memory leaks, though, as they are not auto
   62.14 -// deallocated.
   62.15 -//
   62.16 -// FIX ME FIX ME Add a destructor, and don't rely on the user to drain/flush/deallocate!
   62.17 -//
   62.18 -
   62.19  // Move to some global location
   62.20  #define HAS_BEEN_MOVED 0x1501d01d
   62.21  // End move to some global location
   62.22 @@ -46,8 +34,6 @@
   62.23  class ParallelCompactData;
   62.24  class ParMarkBitMap;
   62.25  
   62.26 -// Move to it's own file if this works out.
   62.27 -
   62.28  class ParCompactionManager : public CHeapObj {
   62.29    friend class ParallelTaskTerminator;
   62.30    friend class ParMarkBitMap;
   62.31 @@ -72,14 +58,27 @@
   62.32  // ------------------------  End don't putback if not needed
   62.33  
   62.34   private:
   62.35 +  // 32-bit:  4K * 8 = 32KiB; 64-bit:  8K * 16 = 128KiB
   62.36 +  #define OBJARRAY_QUEUE_SIZE (1 << NOT_LP64(12) LP64_ONLY(13))
   62.37 +  typedef GenericTaskQueue<ObjArrayTask, OBJARRAY_QUEUE_SIZE> ObjArrayTaskQueue;
   62.38 +  typedef GenericTaskQueueSet<ObjArrayTaskQueue> ObjArrayTaskQueueSet;
   62.39 +  #undef OBJARRAY_QUEUE_SIZE
   62.40 +
   62.41    static ParCompactionManager** _manager_array;
   62.42    static OopTaskQueueSet*       _stack_array;
   62.43 +  static ObjArrayTaskQueueSet*  _objarray_queues;
   62.44    static ObjectStartArray*      _start_array;
   62.45    static RegionTaskQueueSet*    _region_array;
   62.46    static PSOldGen*              _old_gen;
   62.47  
   62.48 +private:
   62.49    OopTaskQueue                  _marking_stack;
   62.50    GrowableArray<oop>*           _overflow_stack;
   62.51 +
   62.52 +  typedef GrowableArray<ObjArrayTask> ObjArrayOverflowStack;
   62.53 +  ObjArrayTaskQueue             _objarray_queue;
   62.54 +  ObjArrayOverflowStack*        _objarray_overflow_stack;
   62.55 +
   62.56    // Is there a way to reuse the _marking_stack for the
   62.57    // saving empty regions?  For now just create a different
   62.58    // type of TaskQueue.
   62.59 @@ -128,8 +127,8 @@
   62.60    // Pushes onto the region stack.  If the region stack is full,
   62.61    // pushes onto the region overflow stack.
   62.62    void region_stack_push(size_t region_index);
   62.63 - public:
   62.64  
   62.65 +public:
   62.66    Action action() { return _action; }
   62.67    void set_action(Action v) { _action = v; }
   62.68  
   62.69 @@ -163,6 +162,8 @@
   62.70    // Get a oop for scanning.  If returns null, no oop were found.
   62.71    oop retrieve_for_scanning();
   62.72  
   62.73 +  inline void push_objarray(oop obj, size_t index);
   62.74 +
   62.75    // Save region for later processing.  Must not fail.
   62.76    void save_for_processing(size_t region_index);
   62.77    // Get a region for processing.  If returns null, no region were found.
   62.78 @@ -175,12 +176,17 @@
   62.79      return stack_array()->steal(queue_num, seed, t);
   62.80    }
   62.81  
   62.82 +  static bool steal_objarray(int queue_num, int* seed, ObjArrayTask& t) {
   62.83 +    return _objarray_queues->steal(queue_num, seed, t);
   62.84 +  }
   62.85 +
   62.86    static bool steal(int queue_num, int* seed, RegionTask& t) {
   62.87      return region_array()->steal(queue_num, seed, t);
   62.88    }
   62.89  
   62.90 -  // Process tasks remaining on any stack
   62.91 -  void drain_marking_stacks(OopClosure *blk);
   62.92 +  // Process tasks remaining on any marking stack
   62.93 +  void follow_marking_stacks();
   62.94 +  inline bool marking_stacks_empty() const;
   62.95  
   62.96    // Process tasks remaining on any stack
   62.97    void drain_region_stacks();
   62.98 @@ -200,3 +206,8 @@
   62.99      "out of range manager_array access");
  62.100    return _manager_array[index];
  62.101  }
  62.102 +
  62.103 +bool ParCompactionManager::marking_stacks_empty() const {
  62.104 +  return _marking_stack.size() == 0 && _overflow_stack->is_empty() &&
  62.105 +    _objarray_queue.size() == 0 && _objarray_overflow_stack->is_empty();
  62.106 +}
    63.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    63.2 +++ b/src/share/vm/gc_implementation/parallelScavenge/psCompactionManager.inline.hpp	Fri Mar 26 11:10:26 2010 -0400
    63.3 @@ -0,0 +1,32 @@
    63.4 +/*
    63.5 + * Copyright 2010 Sun Microsystems, Inc.  All Rights Reserved.
    63.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    63.7 + *
    63.8 + * This code is free software; you can redistribute it and/or modify it
    63.9 + * under the terms of the GNU General Public License version 2 only, as
   63.10 + * published by the Free Software Foundation.
   63.11 + *
   63.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   63.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   63.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   63.15 + * version 2 for more details (a copy is included in the LICENSE file that
   63.16 + * accompanied this code).
   63.17 + *
   63.18 + * You should have received a copy of the GNU General Public License version
   63.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   63.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   63.21 + *
   63.22 + * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
   63.23 + * CA 95054 USA or visit www.sun.com if you need additional information or
   63.24 + * have any questions.
   63.25 + *
   63.26 + */
   63.27 +
   63.28 +void ParCompactionManager::push_objarray(oop obj, size_t index)
   63.29 +{
   63.30 +  ObjArrayTask task(obj, index);
   63.31 +  assert(task.is_valid(), "bad ObjArrayTask");
   63.32 +  if (!_objarray_queue.push(task)) {
   63.33 +    _objarray_overflow_stack->push(task);
   63.34 +  }
   63.35 +}
    64.1 --- a/src/share/vm/gc_implementation/parallelScavenge/psMarkSweep.cpp	Thu Mar 25 16:54:59 2010 -0700
    64.2 +++ b/src/share/vm/gc_implementation/parallelScavenge/psMarkSweep.cpp	Fri Mar 26 11:10:26 2010 -0400
    64.3 @@ -479,6 +479,7 @@
    64.4    _preserved_oop_stack = NULL;
    64.5  
    64.6    _marking_stack = new (ResourceObj::C_HEAP) GrowableArray<oop>(4000, true);
    64.7 +  _objarray_stack = new (ResourceObj::C_HEAP) GrowableArray<ObjArrayTask>(50, true);
    64.8  
    64.9    int size = SystemDictionary::number_of_classes() * 2;
   64.10    _revisit_klass_stack = new (ResourceObj::C_HEAP) GrowableArray<Klass*>(size, true);
   64.11 @@ -497,6 +498,7 @@
   64.12    }
   64.13  
   64.14    delete _marking_stack;
   64.15 +  delete _objarray_stack;
   64.16    delete _revisit_klass_stack;
   64.17    delete _revisit_mdo_stack;
   64.18  }
    65.1 --- a/src/share/vm/gc_implementation/parallelScavenge/psParallelCompact.cpp	Thu Mar 25 16:54:59 2010 -0700
    65.2 +++ b/src/share/vm/gc_implementation/parallelScavenge/psParallelCompact.cpp	Fri Mar 26 11:10:26 2010 -0400
    65.3 @@ -785,7 +785,7 @@
    65.4  void PSParallelCompact::AdjustPointerClosure::do_oop(oop* p)       { adjust_pointer(p, _is_root); }
    65.5  void PSParallelCompact::AdjustPointerClosure::do_oop(narrowOop* p) { adjust_pointer(p, _is_root); }
    65.6  
    65.7 -void PSParallelCompact::FollowStackClosure::do_void() { follow_stack(_compaction_manager); }
    65.8 +void PSParallelCompact::FollowStackClosure::do_void() { _compaction_manager->follow_marking_stacks(); }
    65.9  
   65.10  void PSParallelCompact::MarkAndPushClosure::do_oop(oop* p)       { mark_and_push(_compaction_manager, p); }
   65.11  void PSParallelCompact::MarkAndPushClosure::do_oop(narrowOop* p) { mark_and_push(_compaction_manager, p); }
   65.12 @@ -2376,7 +2376,7 @@
   65.13    // Follow code cache roots.
   65.14    CodeCache::do_unloading(is_alive_closure(), &mark_and_push_closure,
   65.15                            purged_class);
   65.16 -  follow_stack(cm); // Flush marking stack.
   65.17 +  cm->follow_marking_stacks(); // Flush marking stack.
   65.18  
   65.19    // Update subklass/sibling/implementor links of live klasses
   65.20    // revisit_klass_stack is used in follow_weak_klass_links().
   65.21 @@ -2389,8 +2389,7 @@
   65.22    SymbolTable::unlink(is_alive_closure());
   65.23    StringTable::unlink(is_alive_closure());
   65.24  
   65.25 -  assert(cm->marking_stack()->size() == 0, "stack should be empty by now");
   65.26 -  assert(cm->overflow_stack()->is_empty(), "stack should be empty by now");
   65.27 +  assert(cm->marking_stacks_empty(), "marking stacks should be empty");
   65.28  }
   65.29  
   65.30  // This should be moved to the shared markSweep code!
   65.31 @@ -2709,22 +2708,6 @@
   65.32    young_gen->move_and_update(cm);
   65.33  }
   65.34  
   65.35 -
   65.36 -void PSParallelCompact::follow_stack(ParCompactionManager* cm) {
   65.37 -  while(!cm->overflow_stack()->is_empty()) {
   65.38 -    oop obj = cm->overflow_stack()->pop();
   65.39 -    obj->follow_contents(cm);
   65.40 -  }
   65.41 -
   65.42 -  oop obj;
   65.43 -  // obj is a reference!!!
   65.44 -  while (cm->marking_stack()->pop_local(obj)) {
   65.45 -    // It would be nice to assert about the type of objects we might
   65.46 -    // pop, but they can come from anywhere, unfortunately.
   65.47 -    obj->follow_contents(cm);
   65.48 -  }
   65.49 -}
   65.50 -
   65.51  void
   65.52  PSParallelCompact::follow_weak_klass_links() {
   65.53    // All klasses on the revisit stack are marked at this point.
   65.54 @@ -2745,7 +2728,7 @@
   65.55          &keep_alive_closure);
   65.56      }
   65.57      // revisit_klass_stack is cleared in reset()
   65.58 -    follow_stack(cm);
   65.59 +    cm->follow_marking_stacks();
   65.60    }
   65.61  }
   65.62  
   65.63 @@ -2776,7 +2759,7 @@
   65.64        rms->at(j)->follow_weak_refs(is_alive_closure());
   65.65      }
   65.66      // revisit_mdo_stack is cleared in reset()
   65.67 -    follow_stack(cm);
   65.68 +    cm->follow_marking_stacks();
   65.69    }
   65.70  }
   65.71  
    66.1 --- a/src/share/vm/gc_implementation/parallelScavenge/psParallelCompact.hpp	Thu Mar 25 16:54:59 2010 -0700
    66.2 +++ b/src/share/vm/gc_implementation/parallelScavenge/psParallelCompact.hpp	Fri Mar 26 11:10:26 2010 -0400
    66.3 @@ -901,7 +901,6 @@
    66.4    // Mark live objects
    66.5    static void marking_phase(ParCompactionManager* cm,
    66.6                              bool maximum_heap_compaction);
    66.7 -  static void follow_stack(ParCompactionManager* cm);
    66.8    static void follow_weak_klass_links();
    66.9    static void follow_mdo_weak_refs();
   66.10  
   66.11 @@ -1276,7 +1275,7 @@
   66.12        }
   66.13      }
   66.14    }
   66.15 -  follow_stack(cm);
   66.16 +  cm->follow_marking_stacks();
   66.17  }
   66.18  
   66.19  template <class T>
    67.1 --- a/src/share/vm/gc_implementation/shared/markSweep.cpp	Thu Mar 25 16:54:59 2010 -0700
    67.2 +++ b/src/share/vm/gc_implementation/shared/markSweep.cpp	Fri Mar 26 11:10:26 2010 -0400
    67.3 @@ -25,8 +25,9 @@
    67.4  #include "incls/_precompiled.incl"
    67.5  #include "incls/_markSweep.cpp.incl"
    67.6  
    67.7 -GrowableArray<oop>*     MarkSweep::_marking_stack       = NULL;
    67.8 -GrowableArray<Klass*>*  MarkSweep::_revisit_klass_stack = NULL;
    67.9 +GrowableArray<oop>*          MarkSweep::_marking_stack = NULL;
   67.10 +GrowableArray<ObjArrayTask>* MarkSweep::_objarray_stack = NULL;
   67.11 +GrowableArray<Klass*>*       MarkSweep::_revisit_klass_stack = NULL;
   67.12  GrowableArray<DataLayout*>*  MarkSweep::_revisit_mdo_stack = NULL;
   67.13  
   67.14  GrowableArray<oop>*     MarkSweep::_preserved_oop_stack = NULL;
   67.15 @@ -104,11 +105,19 @@
   67.16  void MarkSweep::MarkAndPushClosure::do_oop(narrowOop* p) { mark_and_push(p); }
   67.17  
   67.18  void MarkSweep::follow_stack() {
   67.19 -  while (!_marking_stack->is_empty()) {
   67.20 -    oop obj = _marking_stack->pop();
   67.21 -    assert (obj->is_gc_marked(), "p must be marked");
   67.22 -    obj->follow_contents();
   67.23 -  }
   67.24 +  do {
   67.25 +    while (!_marking_stack->is_empty()) {
   67.26 +      oop obj = _marking_stack->pop();
   67.27 +      assert (obj->is_gc_marked(), "p must be marked");
   67.28 +      obj->follow_contents();
   67.29 +    }
   67.30 +    // Process ObjArrays one at a time to avoid marking stack bloat.
   67.31 +    if (!_objarray_stack->is_empty()) {
   67.32 +      ObjArrayTask task = _objarray_stack->pop();
   67.33 +      objArrayKlass* const k = (objArrayKlass*)task.obj()->blueprint();
   67.34 +      k->oop_follow_contents(task.obj(), task.index());
   67.35 +    }
   67.36 +  } while (!_marking_stack->is_empty() || !_objarray_stack->is_empty());
   67.37  }
   67.38  
   67.39  MarkSweep::FollowStackClosure MarkSweep::follow_stack_closure;
    68.1 --- a/src/share/vm/gc_implementation/shared/markSweep.hpp	Thu Mar 25 16:54:59 2010 -0700
    68.2 +++ b/src/share/vm/gc_implementation/shared/markSweep.hpp	Fri Mar 26 11:10:26 2010 -0400
    68.3 @@ -110,8 +110,9 @@
    68.4    // Vars
    68.5    //
    68.6   protected:
    68.7 -  // Traversal stack used during phase1
    68.8 +  // Traversal stacks used during phase1
    68.9    static GrowableArray<oop>*             _marking_stack;
   68.10 +  static GrowableArray<ObjArrayTask>*    _objarray_stack;
   68.11    // Stack for live klasses to revisit at end of marking phase
   68.12    static GrowableArray<Klass*>*          _revisit_klass_stack;
   68.13    // Set (stack) of MDO's to revisit at end of marking phase
   68.14 @@ -188,6 +189,7 @@
   68.15    template <class T> static inline void mark_and_follow(T* p);
   68.16    // Check mark and maybe push on marking stack
   68.17    template <class T> static inline void mark_and_push(T* p);
   68.18 +  static inline void push_objarray(oop obj, size_t index);
   68.19  
   68.20    static void follow_stack();   // Empty marking stack.
   68.21  
    69.1 --- a/src/share/vm/gc_implementation/shared/markSweep.inline.hpp	Thu Mar 25 16:54:59 2010 -0700
    69.2 +++ b/src/share/vm/gc_implementation/shared/markSweep.inline.hpp	Fri Mar 26 11:10:26 2010 -0400
    69.3 @@ -77,6 +77,12 @@
    69.4    }
    69.5  }
    69.6  
    69.7 +void MarkSweep::push_objarray(oop obj, size_t index) {
    69.8 +  ObjArrayTask task(obj, index);
    69.9 +  assert(task.is_valid(), "bad ObjArrayTask");
   69.10 +  _objarray_stack->push(task);
   69.11 +}
   69.12 +
   69.13  template <class T> inline void MarkSweep::adjust_pointer(T* p, bool isroot) {
   69.14    T heap_oop = oopDesc::load_heap_oop(p);
   69.15    if (!oopDesc::is_null(heap_oop)) {
    70.1 --- a/src/share/vm/includeDB_compiler1	Thu Mar 25 16:54:59 2010 -0700
    70.2 +++ b/src/share/vm/includeDB_compiler1	Fri Mar 26 11:10:26 2010 -0400
    70.3 @@ -1,5 +1,5 @@
    70.4  //
    70.5 -// Copyright 1999-2009 Sun Microsystems, Inc.  All Rights Reserved.
    70.6 +// Copyright 1999-2010 Sun Microsystems, Inc.  All Rights Reserved.
    70.7  // DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    70.8  //
    70.9  // This code is free software; you can redistribute it and/or modify it
   70.10 @@ -246,6 +246,7 @@
   70.11  c1_LIRGenerator.cpp                     c1_LIRGenerator.hpp
   70.12  c1_LIRGenerator.cpp                     c1_ValueStack.hpp
   70.13  c1_LIRGenerator.cpp                     ciArrayKlass.hpp
   70.14 +c1_LIRGenerator.cpp                     ciCPCache.hpp
   70.15  c1_LIRGenerator.cpp                     ciInstance.hpp
   70.16  c1_LIRGenerator.cpp                     heapRegion.hpp
   70.17  c1_LIRGenerator.cpp                     sharedRuntime.hpp
    71.1 --- a/src/share/vm/includeDB_core	Thu Mar 25 16:54:59 2010 -0700
    71.2 +++ b/src/share/vm/includeDB_core	Fri Mar 26 11:10:26 2010 -0400
    71.3 @@ -541,6 +541,7 @@
    71.4  
    71.5  ciCPCache.cpp                           cpCacheOop.hpp
    71.6  ciCPCache.cpp                           ciCPCache.hpp
    71.7 +ciCPCache.cpp                           ciUtilities.hpp
    71.8  
    71.9  ciCPCache.hpp                           ciClassList.hpp
   71.10  ciCPCache.hpp                           ciObject.hpp
   71.11 @@ -2016,6 +2017,7 @@
   71.12  init.cpp                                icBuffer.hpp
   71.13  init.cpp                                icache.hpp
   71.14  init.cpp                                init.hpp
   71.15 +init.cpp                                methodHandles.hpp
   71.16  init.cpp                                safepoint.hpp
   71.17  init.cpp                                sharedRuntime.hpp
   71.18  init.cpp                                universe.hpp
   71.19 @@ -2726,8 +2728,10 @@
   71.20  
   71.21  markSweep.cpp                           compileBroker.hpp
   71.22  markSweep.cpp                           methodDataOop.hpp
   71.23 +markSweep.cpp				objArrayKlass.inline.hpp
   71.24  
   71.25  markSweep.hpp                           collectedHeap.hpp
   71.26 +markSweep.hpp				taskqueue.hpp
   71.27  
   71.28  memRegion.cpp                           globals.hpp
   71.29  memRegion.cpp                           memRegion.hpp
   71.30 @@ -2872,6 +2876,7 @@
   71.31  methodHandles.cpp                       oopFactory.hpp
   71.32  methodHandles.cpp                       reflection.hpp
   71.33  methodHandles.cpp                       signature.hpp
   71.34 +methodHandles.cpp                       stubRoutines.hpp
   71.35  methodHandles.cpp                       symbolTable.hpp
   71.36  
   71.37  methodHandles_<arch>.cpp                allocation.inline.hpp
   71.38 @@ -3056,8 +3061,10 @@
   71.39  objArrayKlass.cpp                       genOopClosures.inline.hpp
   71.40  objArrayKlass.cpp                       handles.inline.hpp
   71.41  objArrayKlass.cpp                       instanceKlass.hpp
   71.42 +objArrayKlass.cpp                       markSweep.inline.hpp
   71.43  objArrayKlass.cpp                       mutexLocker.hpp
   71.44  objArrayKlass.cpp                       objArrayKlass.hpp
   71.45 +objArrayKlass.cpp                       objArrayKlass.inline.hpp
   71.46  objArrayKlass.cpp                       objArrayKlassKlass.hpp
   71.47  objArrayKlass.cpp                       objArrayOop.hpp
   71.48  objArrayKlass.cpp                       oop.inline.hpp
   71.49 @@ -3068,11 +3075,12 @@
   71.50  objArrayKlass.cpp                       universe.inline.hpp
   71.51  objArrayKlass.cpp                       vmSymbols.hpp
   71.52  
   71.53 -
   71.54  objArrayKlass.hpp                       arrayKlass.hpp
   71.55  objArrayKlass.hpp                       instanceKlass.hpp
   71.56  objArrayKlass.hpp                       specialized_oop_closures.hpp
   71.57  
   71.58 +objArrayKlass.inline.hpp		objArrayKlass.hpp
   71.59 +
   71.60  objArrayKlassKlass.cpp                  collectedHeap.inline.hpp
   71.61  objArrayKlassKlass.cpp                  instanceKlass.hpp
   71.62  objArrayKlassKlass.cpp                  javaClasses.hpp
   71.63 @@ -4098,6 +4106,7 @@
   71.64  task.hpp                                top.hpp
   71.65  
   71.66  taskqueue.cpp                           debug.hpp
   71.67 +taskqueue.cpp				oop.inline.hpp
   71.68  taskqueue.cpp                           os.hpp
   71.69  taskqueue.cpp                           taskqueue.hpp
   71.70  taskqueue.cpp                           thread_<os_family>.inline.hpp
    72.1 --- a/src/share/vm/includeDB_gc_parallel	Thu Mar 25 16:54:59 2010 -0700
    72.2 +++ b/src/share/vm/includeDB_gc_parallel	Fri Mar 26 11:10:26 2010 -0400
    72.3 @@ -115,10 +115,14 @@
    72.4  objArrayKlass.cpp                       g1CollectedHeap.inline.hpp
    72.5  objArrayKlass.cpp                       g1OopClosures.inline.hpp
    72.6  objArrayKlass.cpp                       oop.pcgc.inline.hpp
    72.7 +objArrayKlass.cpp                       psCompactionManager.hpp
    72.8  objArrayKlass.cpp                       psPromotionManager.inline.hpp
    72.9  objArrayKlass.cpp                       psScavenge.inline.hpp
   72.10  objArrayKlass.cpp                       parOopClosures.inline.hpp
   72.11  
   72.12 +objArrayKlass.inline.hpp		psCompactionManager.inline.hpp
   72.13 +objArrayKlass.inline.hpp		psParallelCompact.hpp
   72.14 +
   72.15  oop.pcgc.inline.hpp                     parNewGeneration.hpp
   72.16  oop.pcgc.inline.hpp                     parallelScavengeHeap.hpp
   72.17  oop.pcgc.inline.hpp                     psCompactionManager.hpp
    73.1 --- a/src/share/vm/memory/genMarkSweep.cpp	Thu Mar 25 16:54:59 2010 -0700
    73.2 +++ b/src/share/vm/memory/genMarkSweep.cpp	Fri Mar 26 11:10:26 2010 -0400
    73.3 @@ -159,6 +159,7 @@
    73.4    _preserved_oop_stack = NULL;
    73.5  
    73.6    _marking_stack       = new (ResourceObj::C_HEAP) GrowableArray<oop>(4000, true);
    73.7 +  _objarray_stack      = new (ResourceObj::C_HEAP) GrowableArray<ObjArrayTask>(50, true);
    73.8  
    73.9    int size = SystemDictionary::number_of_classes() * 2;
   73.10    _revisit_klass_stack = new (ResourceObj::C_HEAP) GrowableArray<Klass*>(size, true);
   73.11 @@ -194,7 +195,6 @@
   73.12  
   73.13  
   73.14  void GenMarkSweep::deallocate_stacks() {
   73.15 -
   73.16    if (!UseG1GC) {
   73.17      GenCollectedHeap* gch = GenCollectedHeap::heap();
   73.18      gch->release_scratch();
   73.19 @@ -208,6 +208,7 @@
   73.20    }
   73.21  
   73.22    delete _marking_stack;
   73.23 +  delete _objarray_stack;
   73.24    delete _revisit_klass_stack;
   73.25    delete _revisit_mdo_stack;
   73.26  
    74.1 --- a/src/share/vm/memory/genOopClosures.hpp	Thu Mar 25 16:54:59 2010 -0700
    74.2 +++ b/src/share/vm/memory/genOopClosures.hpp	Fri Mar 26 11:10:26 2010 -0400
    74.3 @@ -28,10 +28,10 @@
    74.4  class CardTableModRefBS;
    74.5  class DefNewGeneration;
    74.6  
    74.7 -template<class E> class GenericTaskQueue;
    74.8 -typedef GenericTaskQueue<oop> OopTaskQueue;
    74.9 -template<class E> class GenericTaskQueueSet;
   74.10 -typedef GenericTaskQueueSet<oop> OopTaskQueueSet;
   74.11 +template<class E, unsigned int N> class GenericTaskQueue;
   74.12 +typedef GenericTaskQueue<oop, TASKQUEUE_SIZE> OopTaskQueue;
   74.13 +template<class T> class GenericTaskQueueSet;
   74.14 +typedef GenericTaskQueueSet<OopTaskQueue> OopTaskQueueSet;
   74.15  
   74.16  // Closure for iterating roots from a particular generation
   74.17  // Note: all classes deriving from this MUST call this do_barrier
    75.1 --- a/src/share/vm/oops/objArrayKlass.cpp	Thu Mar 25 16:54:59 2010 -0700
    75.2 +++ b/src/share/vm/oops/objArrayKlass.cpp	Fri Mar 26 11:10:26 2010 -0400
    75.3 @@ -314,24 +314,24 @@
    75.4  
    75.5  void objArrayKlass::oop_follow_contents(oop obj) {
    75.6    assert (obj->is_array(), "obj must be array");
    75.7 -  objArrayOop a = objArrayOop(obj);
    75.8 -  a->follow_header();
    75.9 -  ObjArrayKlass_OOP_ITERATE( \
   75.10 -    a, p, \
   75.11 -    /* we call mark_and_follow here to avoid excessive marking stack usage */ \
   75.12 -    MarkSweep::mark_and_follow(p))
   75.13 +  objArrayOop(obj)->follow_header();
   75.14 +  if (UseCompressedOops) {
   75.15 +    objarray_follow_contents<narrowOop>(obj, 0);
   75.16 +  } else {
   75.17 +    objarray_follow_contents<oop>(obj, 0);
   75.18 +  }
   75.19  }
   75.20  
   75.21  #ifndef SERIALGC
   75.22  void objArrayKlass::oop_follow_contents(ParCompactionManager* cm,
   75.23                                          oop obj) {
   75.24 -  assert (obj->is_array(), "obj must be array");
   75.25 -  objArrayOop a = objArrayOop(obj);
   75.26 -  a->follow_header(cm);
   75.27 -  ObjArrayKlass_OOP_ITERATE( \
   75.28 -    a, p, \
   75.29 -    /* we call mark_and_follow here to avoid excessive marking stack usage */ \
   75.30 -    PSParallelCompact::mark_and_follow(cm, p))
   75.31 +  assert(obj->is_array(), "obj must be array");
   75.32 +  objArrayOop(obj)->follow_header(cm);
   75.33 +  if (UseCompressedOops) {
   75.34 +    objarray_follow_contents<narrowOop>(cm, obj, 0);
   75.35 +  } else {
   75.36 +    objarray_follow_contents<oop>(cm, obj, 0);
   75.37 +  }
   75.38  }
   75.39  #endif // SERIALGC
   75.40  
    76.1 --- a/src/share/vm/oops/objArrayKlass.hpp	Thu Mar 25 16:54:59 2010 -0700
    76.2 +++ b/src/share/vm/oops/objArrayKlass.hpp	Fri Mar 26 11:10:26 2010 -0400
    76.3 @@ -91,10 +91,18 @@
    76.4  
    76.5    // Garbage collection
    76.6    void oop_follow_contents(oop obj);
    76.7 +  inline void oop_follow_contents(oop obj, int index);
    76.8 +  template <class T> inline void objarray_follow_contents(oop obj, int index);
    76.9 +
   76.10    int  oop_adjust_pointers(oop obj);
   76.11  
   76.12    // Parallel Scavenge and Parallel Old
   76.13    PARALLEL_GC_DECLS
   76.14 +#ifndef SERIALGC
   76.15 +  inline void oop_follow_contents(ParCompactionManager* cm, oop obj, int index);
   76.16 +  template <class T> inline void
   76.17 +    objarray_follow_contents(ParCompactionManager* cm, oop obj, int index);
   76.18 +#endif // !SERIALGC
   76.19  
   76.20    // Iterators
   76.21    int oop_oop_iterate(oop obj, OopClosure* blk) {
   76.22 @@ -131,5 +139,4 @@
   76.23    void oop_verify_on(oop obj, outputStream* st);
   76.24    void oop_verify_old_oop(oop obj, oop* p, bool allow_dirty);
   76.25    void oop_verify_old_oop(oop obj, narrowOop* p, bool allow_dirty);
   76.26 -
   76.27  };
    77.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    77.2 +++ b/src/share/vm/oops/objArrayKlass.inline.hpp	Fri Mar 26 11:10:26 2010 -0400
    77.3 @@ -0,0 +1,89 @@
    77.4 +/*
    77.5 + * Copyright 2010 Sun Microsystems, Inc.  All Rights Reserved.
    77.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    77.7 + *
    77.8 + * This code is free software; you can redistribute it and/or modify it
    77.9 + * under the terms of the GNU General Public License version 2 only, as
   77.10 + * published by the Free Software Foundation.
   77.11 + *
   77.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   77.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   77.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   77.15 + * version 2 for more details (a copy is included in the LICENSE file that
   77.16 + * accompanied this code).
   77.17 + *
   77.18 + * You should have received a copy of the GNU General Public License version
   77.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   77.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   77.21 + *
   77.22 + * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
   77.23 + * CA 95054 USA or visit www.sun.com if you need additional information or
   77.24 + * have any questions.
   77.25 + *
   77.26 + */
   77.27 +
   77.28 +void objArrayKlass::oop_follow_contents(oop obj, int index) {
   77.29 +  if (UseCompressedOops) {
   77.30 +    objarray_follow_contents<narrowOop>(obj, index);
   77.31 +  } else {
   77.32 +    objarray_follow_contents<oop>(obj, index);
   77.33 +  }
   77.34 +}
   77.35 +
   77.36 +template <class T>
   77.37 +void objArrayKlass::objarray_follow_contents(oop obj, int index) {
   77.38 +  objArrayOop a = objArrayOop(obj);
   77.39 +  const size_t len = size_t(a->length());
   77.40 +  const size_t beg_index = size_t(index);
   77.41 +  assert(beg_index < len || len == 0, "index too large");
   77.42 +
   77.43 +  const size_t stride = MIN2(len - beg_index, ObjArrayMarkingStride);
   77.44 +  const size_t end_index = beg_index + stride;
   77.45 +  T* const base = (T*)a->base();
   77.46 +  T* const beg = base + beg_index;
   77.47 +  T* const end = base + end_index;
   77.48 +
   77.49 +  // Push the non-NULL elements of the next stride on the marking stack.
   77.50 +  for (T* e = beg; e < end; e++) {
   77.51 +    MarkSweep::mark_and_push<T>(e);
   77.52 +  }
   77.53 +
   77.54 +  if (end_index < len) {
   77.55 +    MarkSweep::push_objarray(a, end_index); // Push the continuation.
   77.56 +  }
   77.57 +}
   77.58 +
   77.59 +#ifndef SERIALGC
   77.60 +void objArrayKlass::oop_follow_contents(ParCompactionManager* cm, oop obj,
   77.61 +                                        int index) {
   77.62 +  if (UseCompressedOops) {
   77.63 +    objarray_follow_contents<narrowOop>(cm, obj, index);
   77.64 +  } else {
   77.65 +    objarray_follow_contents<oop>(cm, obj, index);
   77.66 +  }
   77.67 +}
   77.68 +
   77.69 +template <class T>
   77.70 +void objArrayKlass::objarray_follow_contents(ParCompactionManager* cm, oop obj,
   77.71 +                                             int index) {
   77.72 +  objArrayOop a = objArrayOop(obj);
   77.73 +  const size_t len = size_t(a->length());
   77.74 +  const size_t beg_index = size_t(index);
   77.75 +  assert(beg_index < len || len == 0, "index too large");
   77.76 +
   77.77 +  const size_t stride = MIN2(len - beg_index, ObjArrayMarkingStride);
   77.78 +  const size_t end_index = beg_index + stride;
   77.79 +  T* const base = (T*)a->base();
   77.80 +  T* const beg = base + beg_index;
   77.81 +  T* const end = base + end_index;
   77.82 +
   77.83 +  // Push the non-NULL elements of the next stride on the marking stack.
   77.84 +  for (T* e = beg; e < end; e++) {
   77.85 +    PSParallelCompact::mark_and_push<T>(cm, e);
   77.86 +  }
   77.87 +
   77.88 +  if (end_index < len) {
   77.89 +    cm->push_objarray(a, end_index); // Push the continuation.
   77.90 +  }
   77.91 +}
   77.92 +#endif // #ifndef SERIALGC
    78.1 --- a/src/share/vm/opto/loopTransform.cpp	Thu Mar 25 16:54:59 2010 -0700
    78.2 +++ b/src/share/vm/opto/loopTransform.cpp	Fri Mar 26 11:10:26 2010 -0400
    78.3 @@ -1,5 +1,5 @@
    78.4  /*
    78.5 - * Copyright 2000-2009 Sun Microsystems, Inc.  All Rights Reserved.
    78.6 + * Copyright 2000-2010 Sun Microsystems, Inc.  All Rights Reserved.
    78.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    78.8   *
    78.9   * This code is free software; you can redistribute it and/or modify it
   78.10 @@ -2088,29 +2088,41 @@
   78.11  BoolNode* PhaseIdealLoop::rc_predicate(Node* ctrl,
   78.12                                         int scale, Node* offset,
   78.13                                         Node* init, Node* limit, Node* stride,
   78.14 -                                       Node* range) {
   78.15 +                                       Node* range, bool upper) {
   78.16 +  DEBUG_ONLY(ttyLocker ttyl);
   78.17 +  if (TraceLoopPredicate) tty->print("rc_predicate ");
   78.18 +
   78.19    Node* max_idx_expr  = init;
   78.20    int stride_con = stride->get_int();
   78.21 -  if ((stride_con > 0) == (scale > 0)) {
   78.22 +  if ((stride_con > 0) == (scale > 0) == upper) {
   78.23      max_idx_expr = new (C, 3) SubINode(limit, stride);
   78.24      register_new_node(max_idx_expr, ctrl);
   78.25 +    if (TraceLoopPredicate) tty->print("(limit - stride) ");
   78.26 +  } else {
   78.27 +    if (TraceLoopPredicate) tty->print("init ");
   78.28    }
   78.29  
   78.30    if (scale != 1) {
   78.31      ConNode* con_scale = _igvn.intcon(scale);
   78.32      max_idx_expr = new (C, 3) MulINode(max_idx_expr, con_scale);
   78.33      register_new_node(max_idx_expr, ctrl);
   78.34 +    if (TraceLoopPredicate) tty->print("* %d ", scale);
   78.35    }
   78.36  
   78.37    if (offset && (!offset->is_Con() || offset->get_int() != 0)){
   78.38      max_idx_expr = new (C, 3) AddINode(max_idx_expr, offset);
   78.39      register_new_node(max_idx_expr, ctrl);
   78.40 +    if (TraceLoopPredicate)
   78.41 +      if (offset->is_Con()) tty->print("+ %d ", offset->get_int());
   78.42 +      else tty->print("+ offset ");
   78.43    }
   78.44  
   78.45    CmpUNode* cmp = new (C, 3) CmpUNode(max_idx_expr, range);
   78.46    register_new_node(cmp, ctrl);
   78.47    BoolNode* bol = new (C, 2) BoolNode(cmp, BoolTest::lt);
   78.48    register_new_node(bol, ctrl);
   78.49 +
   78.50 +  if (TraceLoopPredicate) tty->print_cr("<u range");
   78.51    return bol;
   78.52  }
   78.53  
   78.54 @@ -2187,7 +2199,6 @@
   78.55    while (if_proj_list.size() > 0) {
   78.56      // Following are changed to nonnull when a predicate can be hoisted
   78.57      ProjNode* new_predicate_proj = NULL;
   78.58 -    BoolNode* new_predicate_bol   = NULL;
   78.59  
   78.60      ProjNode* proj = if_proj_list.pop()->as_Proj();
   78.61      IfNode*   iff  = proj->in(0)->as_If();
   78.62 @@ -2218,93 +2229,120 @@
   78.63        // Invariant test
   78.64        new_predicate_proj = create_new_if_for_predicate(predicate_proj);
   78.65        Node* ctrl = new_predicate_proj->in(0)->as_If()->in(0);
   78.66 -      new_predicate_bol  = invar.clone(bol, ctrl)->as_Bool();
   78.67 -      if (TraceLoopPredicate) tty->print("invariant");
   78.68 +      BoolNode* new_predicate_bol = invar.clone(bol, ctrl)->as_Bool();
   78.69 +
   78.70 +      // Negate test if necessary
   78.71 +      bool negated = false;
   78.72 +      if (proj->_con != predicate_proj->_con) {
   78.73 +        new_predicate_bol = new (C, 2) BoolNode(new_predicate_bol->in(1), new_predicate_bol->_test.negate());
   78.74 +        register_new_node(new_predicate_bol, ctrl);
   78.75 +        negated = true;
   78.76 +      }
   78.77 +      IfNode* new_predicate_iff = new_predicate_proj->in(0)->as_If();
   78.78 +      _igvn.hash_delete(new_predicate_iff);
   78.79 +      new_predicate_iff->set_req(1, new_predicate_bol);
   78.80 +      if (TraceLoopPredicate) tty->print_cr("invariant if%s: %d", negated ? " negated" : "", new_predicate_iff->_idx);
   78.81 +
   78.82      } else if (cl != NULL && loop->is_range_check_if(iff, this, invar)) {
   78.83 -      // Range check (only for counted loops)
   78.84 -      new_predicate_proj = create_new_if_for_predicate(predicate_proj);
   78.85 -      Node *ctrl = new_predicate_proj->in(0)->as_If()->in(0);
   78.86 +      assert(proj->_con == predicate_proj->_con, "must match");
   78.87 +
   78.88 +      // Range check for counted loops
   78.89        const Node*    cmp    = bol->in(1)->as_Cmp();
   78.90        Node*          idx    = cmp->in(1);
   78.91        assert(!invar.is_invariant(idx), "index is variant");
   78.92        assert(cmp->in(2)->Opcode() == Op_LoadRange, "must be");
   78.93 -      LoadRangeNode* ld_rng = (LoadRangeNode*)cmp->in(2); // LoadRangeNode
   78.94 +      Node* ld_rng = cmp->in(2); // LoadRangeNode
   78.95        assert(invar.is_invariant(ld_rng), "load range must be invariant");
   78.96 -      ld_rng = (LoadRangeNode*)invar.clone(ld_rng, ctrl);
   78.97        int scale    = 1;
   78.98        Node* offset = zero;
   78.99        bool ok = is_scaled_iv_plus_offset(idx, cl->phi(), &scale, &offset);
  78.100        assert(ok, "must be index expression");
  78.101 +
  78.102 +      Node* init    = cl->init_trip();
  78.103 +      Node* limit   = cl->limit();
  78.104 +      Node* stride  = cl->stride();
  78.105 +
  78.106 +      // Build if's for the upper and lower bound tests.  The
  78.107 +      // lower_bound test will dominate the upper bound test and all
  78.108 +      // cloned or created nodes will use the lower bound test as
  78.109 +      // their declared control.
  78.110 +      ProjNode* lower_bound_proj = create_new_if_for_predicate(predicate_proj);
  78.111 +      ProjNode* upper_bound_proj = create_new_if_for_predicate(predicate_proj);
  78.112 +      assert(upper_bound_proj->in(0)->as_If()->in(0) == lower_bound_proj, "should dominate");
  78.113 +      Node *ctrl = lower_bound_proj->in(0)->as_If()->in(0);
  78.114 +
  78.115 +      // Perform cloning to keep Invariance state correct since the
  78.116 +      // late schedule will place invariant things in the loop.
  78.117 +      ld_rng = invar.clone(ld_rng, ctrl);
  78.118        if (offset && offset != zero) {
  78.119          assert(invar.is_invariant(offset), "offset must be loop invariant");
  78.120          offset = invar.clone(offset, ctrl);
  78.121        }
  78.122 -      Node* init    = cl->init_trip();
  78.123 -      Node* limit   = cl->limit();
  78.124 -      Node* stride  = cl->stride();
  78.125 -      new_predicate_bol = rc_predicate(ctrl, scale, offset, init, limit, stride, ld_rng);
  78.126 -      if (TraceLoopPredicate) tty->print("range check");
  78.127 -    }
  78.128  
  78.129 -    if (new_predicate_proj == NULL) {
  78.130 +      // Test the lower bound
  78.131 +      Node*  lower_bound_bol = rc_predicate(ctrl, scale, offset, init, limit, stride, ld_rng, false);
  78.132 +      IfNode* lower_bound_iff = lower_bound_proj->in(0)->as_If();
  78.133 +      _igvn.hash_delete(lower_bound_iff);
  78.134 +      lower_bound_iff->set_req(1, lower_bound_bol);
  78.135 +      if (TraceLoopPredicate) tty->print_cr("lower bound check if: %d", lower_bound_iff->_idx);
  78.136 +
  78.137 +      // Test the upper bound
  78.138 +      Node* upper_bound_bol = rc_predicate(ctrl, scale, offset, init, limit, stride, ld_rng, true);
  78.139 +      IfNode* upper_bound_iff = upper_bound_proj->in(0)->as_If();
  78.140 +      _igvn.hash_delete(upper_bound_iff);
  78.141 +      upper_bound_iff->set_req(1, upper_bound_bol);
  78.142 +      if (TraceLoopPredicate) tty->print_cr("upper bound check if: %d", lower_bound_iff->_idx);
  78.143 +
  78.144 +      // Fall through into rest of the clean up code which will move
  78.145 +      // any dependent nodes onto the upper bound test.
  78.146 +      new_predicate_proj = upper_bound_proj;
  78.147 +    } else {
  78.148        // The other proj of the "iff" is a uncommon trap projection, and we can assume
  78.149        // the other proj will not be executed ("executed" means uct raised).
  78.150        continue;
  78.151 -    } else {
  78.152 -      // Success - attach condition (new_predicate_bol) to predicate if
  78.153 -      invar.map_ctrl(proj, new_predicate_proj); // so that invariance test can be appropriate
  78.154 -      IfNode* new_iff = new_predicate_proj->in(0)->as_If();
  78.155 +    }
  78.156  
  78.157 -      // Negate test if necessary
  78.158 -      if (proj->_con != predicate_proj->_con) {
  78.159 -        new_predicate_bol = new (C, 2) BoolNode(new_predicate_bol->in(1), new_predicate_bol->_test.negate());
  78.160 -        register_new_node(new_predicate_bol, new_iff->in(0));
  78.161 -        if (TraceLoopPredicate) tty->print_cr(" if negated: %d", iff->_idx);
  78.162 -      } else {
  78.163 -        if (TraceLoopPredicate) tty->print_cr(" if: %d", iff->_idx);
  78.164 +    // Success - attach condition (new_predicate_bol) to predicate if
  78.165 +    invar.map_ctrl(proj, new_predicate_proj); // so that invariance test can be appropriate
  78.166 +
  78.167 +    // Eliminate the old if in the loop body
  78.168 +    _igvn.hash_delete(iff);
  78.169 +    iff->set_req(1, proj->is_IfFalse() ? cond_false : cond_true);
  78.170 +
  78.171 +    Node* ctrl = new_predicate_proj; // new control
  78.172 +    ProjNode* dp = proj;     // old control
  78.173 +    assert(get_loop(dp) == loop, "guaranteed at the time of collecting proj");
  78.174 +    // Find nodes (depends only on the test) off the surviving projection;
  78.175 +    // move them outside the loop with the control of proj_clone
  78.176 +    for (DUIterator_Fast imax, i = dp->fast_outs(imax); i < imax; i++) {
  78.177 +      Node* cd = dp->fast_out(i); // Control-dependent node
  78.178 +      if (cd->depends_only_on_test()) {
  78.179 +        assert(cd->in(0) == dp, "");
  78.180 +        _igvn.hash_delete(cd);
  78.181 +        cd->set_req(0, ctrl); // ctrl, not NULL
  78.182 +        set_early_ctrl(cd);
  78.183 +        _igvn._worklist.push(cd);
  78.184 +        IdealLoopTree *new_loop = get_loop(get_ctrl(cd));
  78.185 +        if (new_loop != loop) {
  78.186 +          if (!loop->_child) loop->_body.yank(cd);
  78.187 +          if (!new_loop->_child ) new_loop->_body.push(cd);
  78.188 +        }
  78.189 +        --i;
  78.190 +        --imax;
  78.191        }
  78.192 +    }
  78.193  
  78.194 -      _igvn.hash_delete(new_iff);
  78.195 -      new_iff->set_req(1, new_predicate_bol);
  78.196 -
  78.197 -      _igvn.hash_delete(iff);
  78.198 -      iff->set_req(1, proj->is_IfFalse() ? cond_false : cond_true);
  78.199 -
  78.200 -      Node* ctrl = new_predicate_proj; // new control
  78.201 -      ProjNode* dp = proj;     // old control
  78.202 -      assert(get_loop(dp) == loop, "guarenteed at the time of collecting proj");
  78.203 -      // Find nodes (depends only on the test) off the surviving projection;
  78.204 -      // move them outside the loop with the control of proj_clone
  78.205 -      for (DUIterator_Fast imax, i = dp->fast_outs(imax); i < imax; i++) {
  78.206 -        Node* cd = dp->fast_out(i); // Control-dependent node
  78.207 -        if (cd->depends_only_on_test()) {
  78.208 -          assert(cd->in(0) == dp, "");
  78.209 -          _igvn.hash_delete(cd);
  78.210 -          cd->set_req(0, ctrl); // ctrl, not NULL
  78.211 -          set_early_ctrl(cd);
  78.212 -          _igvn._worklist.push(cd);
  78.213 -          IdealLoopTree *new_loop = get_loop(get_ctrl(cd));
  78.214 -          if (new_loop != loop) {
  78.215 -            if (!loop->_child) loop->_body.yank(cd);
  78.216 -            if (!new_loop->_child ) new_loop->_body.push(cd);
  78.217 -          }
  78.218 -          --i;
  78.219 -          --imax;
  78.220 -        }
  78.221 -      }
  78.222 -
  78.223 -      hoisted = true;
  78.224 -      C->set_major_progress();
  78.225 -    }
  78.226 +    hoisted = true;
  78.227 +    C->set_major_progress();
  78.228    } // end while
  78.229  
  78.230  #ifndef PRODUCT
  78.231 -    // report that the loop predication has been actually performed
  78.232 -    // for this loop
  78.233 -    if (TraceLoopPredicate && hoisted) {
  78.234 -      tty->print("Loop Predication Performed:");
  78.235 -      loop->dump_head();
  78.236 -    }
  78.237 +  // report that the loop predication has been actually performed
  78.238 +  // for this loop
  78.239 +  if (TraceLoopPredicate && hoisted) {
  78.240 +    tty->print("Loop Predication Performed:");
  78.241 +    loop->dump_head();
  78.242 +  }
  78.243  #endif
  78.244  
  78.245    return hoisted;
    79.1 --- a/src/share/vm/opto/loopnode.hpp	Thu Mar 25 16:54:59 2010 -0700
    79.2 +++ b/src/share/vm/opto/loopnode.hpp	Fri Mar 26 11:10:26 2010 -0400
    79.3 @@ -821,7 +821,7 @@
    79.4    BoolNode* rc_predicate(Node* ctrl,
    79.5                           int scale, Node* offset,
    79.6                           Node* init, Node* limit, Node* stride,
    79.7 -                         Node* range);
    79.8 +                         Node* range, bool upper);
    79.9  
   79.10    // Implementation of the loop predication to promote checks outside the loop
   79.11    bool loop_predication_impl(IdealLoopTree *loop);
    80.1 --- a/src/share/vm/opto/runtime.cpp	Thu Mar 25 16:54:59 2010 -0700
    80.2 +++ b/src/share/vm/opto/runtime.cpp	Fri Mar 26 11:10:26 2010 -0400
    80.3 @@ -864,7 +864,7 @@
    80.4      thread->set_exception_handler_pc(handler_address);
    80.5      thread->set_exception_stack_size(0);
    80.6  
    80.7 -    // Check if the exception PC is a MethodHandle call.
    80.8 +    // Check if the exception PC is a MethodHandle call site.
    80.9      thread->set_is_method_handle_exception(nm->is_method_handle_return(pc));
   80.10    }
   80.11  
   80.12 @@ -952,7 +952,7 @@
   80.13  
   80.14    thread->set_vm_result(exception);
   80.15    // Frame not compiled (handles deoptimization blob)
   80.16 -  return SharedRuntime::raw_exception_handler_for_return_address(ret_pc);
   80.17 +  return SharedRuntime::raw_exception_handler_for_return_address(thread, ret_pc);
   80.18  }
   80.19  
   80.20  
    81.1 --- a/src/share/vm/prims/methodHandles.cpp	Thu Mar 25 16:54:59 2010 -0700
    81.2 +++ b/src/share/vm/prims/methodHandles.cpp	Fri Mar 26 11:10:26 2010 -0400
    81.3 @@ -1,5 +1,5 @@
    81.4  /*
    81.5 - * Copyright 2008-2009 Sun Microsystems, Inc.  All Rights Reserved.
    81.6 + * Copyright 2008-2010 Sun Microsystems, Inc.  All Rights Reserved.
    81.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    81.8   *
    81.9   * This code is free software; you can redistribute it and/or modify it
   81.10 @@ -82,6 +82,10 @@
   81.11    NULL
   81.12  };
   81.13  
   81.14 +// Adapters.
   81.15 +MethodHandlesAdapterBlob* MethodHandles::_adapter_code      = NULL;
   81.16 +int                       MethodHandles::_adapter_code_size = StubRoutines::method_handles_adapters_code_size;
   81.17 +
   81.18  jobject MethodHandles::_raise_exception_method;
   81.19  
   81.20  #ifdef ASSERT
   81.21 @@ -95,6 +99,41 @@
   81.22  }
   81.23  #endif
   81.24  
   81.25 +
   81.26 +//------------------------------------------------------------------------------
   81.27 +// MethodHandles::generate_adapters
   81.28 +//
   81.29 +void MethodHandles::generate_adapters() {
   81.30 +  if (!EnableMethodHandles || SystemDictionary::MethodHandle_klass() == NULL)  return;
   81.31 +
   81.32 +  assert(_adapter_code == NULL, "generate only once");
   81.33 +
   81.34 +  ResourceMark rm;
   81.35 +  TraceTime timer("MethodHandles adapters generation", TraceStartupTime);
   81.36 +  _adapter_code = MethodHandlesAdapterBlob::create(_adapter_code_size);
   81.37 +  if (_adapter_code == NULL)
   81.38 +    vm_exit_out_of_memory(_adapter_code_size, "CodeCache: no room for MethodHandles adapters");
   81.39 +  CodeBuffer code(_adapter_code->instructions_begin(), _adapter_code->instructions_size());
   81.40 +
   81.41 +  MethodHandlesAdapterGenerator g(&code);
   81.42 +  g.generate();
   81.43 +}
   81.44 +
   81.45 +
   81.46 +//------------------------------------------------------------------------------
   81.47 +// MethodHandlesAdapterGenerator::generate
   81.48 +//
   81.49 +void MethodHandlesAdapterGenerator::generate() {
   81.50 +  // Generate generic method handle adapters.
   81.51 +  for (MethodHandles::EntryKind ek = MethodHandles::_EK_FIRST;
   81.52 +       ek < MethodHandles::_EK_LIMIT;
   81.53 +       ek = MethodHandles::EntryKind(1 + (int)ek)) {
   81.54 +    StubCodeMark mark(this, "MethodHandle", MethodHandles::entry_name(ek));
   81.55 +    MethodHandles::generate_method_handle_stub(_masm, ek);
   81.56 +  }
   81.57 +}
   81.58 +
   81.59 +
   81.60  void MethodHandles::set_enabled(bool z) {
   81.61    if (_enabled != z) {
   81.62      guarantee(z && EnableMethodHandles, "can only enable once, and only if -XX:+EnableMethodHandles");
    82.1 --- a/src/share/vm/prims/methodHandles.hpp	Thu Mar 25 16:54:59 2010 -0700
    82.2 +++ b/src/share/vm/prims/methodHandles.hpp	Fri Mar 26 11:10:26 2010 -0400
    82.3 @@ -1,5 +1,5 @@
    82.4  /*
    82.5 - * Copyright 2008-2009 Sun Microsystems, Inc.  All Rights Reserved.
    82.6 + * Copyright 2008-2010 Sun Microsystems, Inc.  All Rights Reserved.
    82.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    82.8   *
    82.9   * This code is free software; you can redistribute it and/or modify it
   82.10 @@ -115,6 +115,10 @@
   82.11    static const char*        _entry_names[_EK_LIMIT+1];
   82.12    static jobject            _raise_exception_method;
   82.13  
   82.14 +  // Adapters.
   82.15 +  static MethodHandlesAdapterBlob* _adapter_code;
   82.16 +  static int                       _adapter_code_size;
   82.17 +
   82.18    static bool ek_valid(EntryKind ek)            { return (uint)ek < (uint)_EK_LIMIT; }
   82.19    static bool conv_op_valid(int op)             { return (uint)op < (uint)CONV_OP_LIMIT; }
   82.20  
   82.21 @@ -133,6 +137,43 @@
   82.22      _entries[ek] = me;
   82.23    }
   82.24  
   82.25 +  // Some adapter helper functions.
   82.26 +  static void get_ek_bound_mh_info(EntryKind ek, BasicType& arg_type, int& arg_mask, int& arg_slots) {
   82.27 +    switch (ek) {
   82.28 +    case _bound_int_mh        : // fall-thru
   82.29 +    case _bound_int_direct_mh : arg_type = T_INT;    arg_mask = _INSERT_INT_MASK;  break;
   82.30 +    case _bound_long_mh       : // fall-thru
   82.31 +    case _bound_long_direct_mh: arg_type = T_LONG;   arg_mask = _INSERT_LONG_MASK; break;
   82.32 +    case _bound_ref_mh        : // fall-thru
   82.33 +    case _bound_ref_direct_mh : arg_type = T_OBJECT; arg_mask = _INSERT_REF_MASK;  break;
   82.34 +    default: ShouldNotReachHere();
   82.35 +    }
   82.36 +    arg_slots = type2size[arg_type];
   82.37 +  }
   82.38 +
   82.39 +  static void get_ek_adapter_opt_swap_rot_info(EntryKind ek, int& swap_bytes, int& rotate) {
   82.40 +    int swap_slots = 0;
   82.41 +    switch (ek) {
   82.42 +    case _adapter_opt_swap_1:     swap_slots = 1; rotate =  0; break;
   82.43 +    case _adapter_opt_swap_2:     swap_slots = 2; rotate =  0; break;
   82.44 +    case _adapter_opt_rot_1_up:   swap_slots = 1; rotate =  1; break;
   82.45 +    case _adapter_opt_rot_1_down: swap_slots = 1; rotate = -1; break;
   82.46 +    case _adapter_opt_rot_2_up:   swap_slots = 2; rotate =  1; break;
   82.47 +    case _adapter_opt_rot_2_down: swap_slots = 2; rotate = -1; break;
   82.48 +    default: ShouldNotReachHere();
   82.49 +    }
   82.50 +    // Return the size of the stack slots to move in bytes.
   82.51 +    swap_bytes = swap_slots * Interpreter::stackElementSize();
   82.52 +  }
   82.53 +
   82.54 +  static int get_ek_adapter_opt_spread_info(EntryKind ek) {
   82.55 +    switch (ek) {
   82.56 +    case _adapter_opt_spread_0: return  0;
   82.57 +    case _adapter_opt_spread_1: return  1;
   82.58 +    default                   : return -1;
   82.59 +    }
   82.60 +  }
   82.61 +
   82.62    static methodOop raise_exception_method() {
   82.63      oop rem = JNIHandles::resolve(_raise_exception_method);
   82.64      assert(rem == NULL || rem->is_method(), "");
   82.65 @@ -230,7 +271,10 @@
   82.66    // bit values for suppress argument to expand_MemberName:
   82.67    enum { _suppress_defc = 1, _suppress_name = 2, _suppress_type = 4 };
   82.68  
   82.69 -  // called from InterpreterGenerator and StubGenerator
   82.70 +  // Generate MethodHandles adapters.
   82.71 +  static void generate_adapters();
   82.72 +
   82.73 +  // Called from InterpreterGenerator and MethodHandlesAdapterGenerator.
   82.74    static address generate_method_handle_interpreter_entry(MacroAssembler* _masm);
   82.75    static void generate_method_handle_stub(MacroAssembler* _masm, EntryKind ek);
   82.76  
   82.77 @@ -385,13 +429,13 @@
   82.78    static void insert_arg_slots(MacroAssembler* _masm,
   82.79                                 RegisterOrConstant arg_slots,
   82.80                                 int arg_mask,
   82.81 -                               Register rax_argslot,
   82.82 -                               Register rbx_temp, Register rdx_temp);
   82.83 +                               Register argslot_reg,
   82.84 +                               Register temp_reg, Register temp2_reg);
   82.85  
   82.86    static void remove_arg_slots(MacroAssembler* _masm,
   82.87                                 RegisterOrConstant arg_slots,
   82.88 -                               Register rax_argslot,
   82.89 -                               Register rbx_temp, Register rdx_temp);
   82.90 +                               Register argslot_reg,
   82.91 +                               Register temp_reg, Register temp2_reg);
   82.92  };
   82.93  
   82.94  
   82.95 @@ -447,3 +491,14 @@
   82.96  
   82.97  address MethodHandles::from_compiled_entry(EntryKind ek) { return entry(ek)->from_compiled_entry(); }
   82.98  address MethodHandles::from_interpreted_entry(EntryKind ek) { return entry(ek)->from_interpreted_entry(); }
   82.99 +
  82.100 +
  82.101 +//------------------------------------------------------------------------------
  82.102 +// MethodHandlesAdapterGenerator
  82.103 +//
  82.104 +class MethodHandlesAdapterGenerator : public StubCodeGenerator {
  82.105 +public:
  82.106 +  MethodHandlesAdapterGenerator(CodeBuffer* code) : StubCodeGenerator(code) {}
  82.107 +
  82.108 +  void generate();
  82.109 +};
    83.1 --- a/src/share/vm/runtime/arguments.cpp	Thu Mar 25 16:54:59 2010 -0700
    83.2 +++ b/src/share/vm/runtime/arguments.cpp	Fri Mar 26 11:10:26 2010 -0400
    83.3 @@ -1346,9 +1346,7 @@
    83.4    }
    83.5  
    83.6    if (FLAG_IS_DEFAULT(MarkStackSize)) {
    83.7 -    // Size as a multiple of TaskQueueSuper::N which is larger
    83.8 -    // for 64-bit.
    83.9 -    FLAG_SET_DEFAULT(MarkStackSize, 128 * TaskQueueSuper::total_size());
   83.10 +    FLAG_SET_DEFAULT(MarkStackSize, 128 * TASKQUEUE_SIZE);
   83.11    }
   83.12    if (PrintGCDetails && Verbose) {
   83.13      tty->print_cr("MarkStackSize: %uk  MarkStackSizeMax: %uk",
   83.14 @@ -2859,6 +2857,12 @@
   83.15    }
   83.16  #endif // _LP64
   83.17  
   83.18 +  // MethodHandles code does not support TaggedStackInterpreter.
   83.19 +  if (EnableMethodHandles && TaggedStackInterpreter) {
   83.20 +    warning("TaggedStackInterpreter is not supported by MethodHandles code.  Disabling TaggedStackInterpreter.");
   83.21 +    TaggedStackInterpreter = false;
   83.22 +  }
   83.23 +
   83.24    // Check the GC selections again.
   83.25    if (!check_gc_consistency()) {
   83.26      return JNI_EINVAL;
    84.1 --- a/src/share/vm/runtime/globals.hpp	Thu Mar 25 16:54:59 2010 -0700
    84.2 +++ b/src/share/vm/runtime/globals.hpp	Fri Mar 26 11:10:26 2010 -0400
    84.3 @@ -1795,6 +1795,10 @@
    84.4    product(uintx, PreserveMarkStackSize, 1024,                               \
    84.5            "Size for stack used in promotion failure handling")              \
    84.6                                                                              \
    84.7 +  develop(uintx, ObjArrayMarkingStride, 512,                                \
    84.8 +          "Number of ObjArray elements to push onto the marking stack"      \
    84.9 +          "before pushing a continuation entry")                            \
   84.10 +                                                                            \
   84.11    product_pd(bool, UseTLAB, "Use thread-local object allocation")           \
   84.12                                                                              \
   84.13    product_pd(bool, ResizeTLAB,                                              \
    85.1 --- a/src/share/vm/runtime/init.cpp	Thu Mar 25 16:54:59 2010 -0700
    85.2 +++ b/src/share/vm/runtime/init.cpp	Fri Mar 26 11:10:26 2010 -0400
    85.3 @@ -1,5 +1,5 @@
    85.4  /*
    85.5 - * Copyright 1997-2008 Sun Microsystems, Inc.  All Rights Reserved.
    85.6 + * Copyright 1997-2010 Sun Microsystems, Inc.  All Rights Reserved.
    85.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    85.8   *
    85.9   * This code is free software; you can redistribute it and/or modify it
   85.10 @@ -118,6 +118,9 @@
   85.11    javaClasses_init();  // must happen after vtable initialization
   85.12    stubRoutines_init2(); // note: StubRoutines need 2-phase init
   85.13  
   85.14 +  // Generate MethodHandles adapters.
   85.15 +  MethodHandles::generate_adapters();
   85.16 +
   85.17    // Although we'd like to, we can't easily do a heap verify
   85.18    // here because the main thread isn't yet a JavaThread, so
   85.19    // its TLAB may not be made parseable from the usual interfaces.
    86.1 --- a/src/share/vm/runtime/sharedRuntime.cpp	Thu Mar 25 16:54:59 2010 -0700
    86.2 +++ b/src/share/vm/runtime/sharedRuntime.cpp	Fri Mar 26 11:10:26 2010 -0400
    86.3 @@ -256,7 +256,7 @@
    86.4  // The continuation address is the entry point of the exception handler of the
    86.5  // previous frame depending on the return address.
    86.6  
    86.7 -address SharedRuntime::raw_exception_handler_for_return_address(address return_address) {
    86.8 +address SharedRuntime::raw_exception_handler_for_return_address(JavaThread* thread, address return_address) {
    86.9    assert(frame::verify_return_pc(return_address), "must be a return pc");
   86.10  
   86.11    // the fastest case first
   86.12 @@ -264,6 +264,8 @@
   86.13    if (blob != NULL && blob->is_nmethod()) {
   86.14      nmethod* code = (nmethod*)blob;
   86.15      assert(code != NULL, "nmethod must be present");
   86.16 +    // Check if the return address is a MethodHandle call site.
   86.17 +    thread->set_is_method_handle_exception(code->is_method_handle_return(return_address));
   86.18      // native nmethods don't have exception handlers
   86.19      assert(!code->is_native_method(), "no exception handler");
   86.20      assert(code->header_begin() != code->exception_begin(), "no exception handler");
   86.21 @@ -289,6 +291,8 @@
   86.22      if (blob->is_nmethod()) {
   86.23        nmethod* code = (nmethod*)blob;
   86.24        assert(code != NULL, "nmethod must be present");
   86.25 +      // Check if the return address is a MethodHandle call site.
   86.26 +      thread->set_is_method_handle_exception(code->is_method_handle_return(return_address));
   86.27        assert(code->header_begin() != code->exception_begin(), "no exception handler");
   86.28        return code->exception_begin();
   86.29      }
   86.30 @@ -309,10 +313,11 @@
   86.31  }
   86.32  
   86.33  
   86.34 -JRT_LEAF(address, SharedRuntime::exception_handler_for_return_address(address return_address))
   86.35 -  return raw_exception_handler_for_return_address(return_address);
   86.36 +JRT_LEAF(address, SharedRuntime::exception_handler_for_return_address(JavaThread* thread, address return_address))
   86.37 +  return raw_exception_handler_for_return_address(thread, return_address);
   86.38  JRT_END
   86.39  
   86.40 +
   86.41  address SharedRuntime::get_poll_stub(address pc) {
   86.42    address stub;
   86.43    // Look up the code blob
   86.44 @@ -465,16 +470,6 @@
   86.45      t = table.entry_for(catch_pco, -1, 0);
   86.46    }
   86.47  
   86.48 -#ifdef COMPILER1
   86.49 -  if (nm->is_compiled_by_c1() && t == NULL && handler_bci == -1) {
   86.50 -    // Exception is not handled by this frame so unwind.  Note that
   86.51 -    // this is not the same as how C2 does this.  C2 emits a table
   86.52 -    // entry that dispatches to the unwind code in the nmethod.
   86.53 -    return NULL;
   86.54 -  }
   86.55 -#endif /* COMPILER1 */
   86.56 -
   86.57 -
   86.58    if (t == NULL) {
   86.59      tty->print_cr("MISSING EXCEPTION HANDLER for pc " INTPTR_FORMAT " and handler bci %d", ret_pc, handler_bci);
   86.60      tty->print_cr("   Exception:");
   86.61 @@ -587,7 +582,7 @@
   86.62            // 3. Implict null exception in nmethod
   86.63  
   86.64            if (!cb->is_nmethod()) {
   86.65 -            guarantee(cb->is_adapter_blob(),
   86.66 +            guarantee(cb->is_adapter_blob() || cb->is_method_handles_adapter_blob(),
   86.67                        "exception happened outside interpreter, nmethods and vtable stubs (1)");
   86.68              // There is no handler here, so we will simply unwind.
   86.69              return StubRoutines::throw_NullPointerException_at_call_entry();
   86.70 @@ -892,12 +887,13 @@
   86.71    RegisterMap cbl_map(thread, false);
   86.72    frame caller_frame = thread->last_frame().sender(&cbl_map);
   86.73  
   86.74 -  CodeBlob* cb = caller_frame.cb();
   86.75 -  guarantee(cb != NULL && cb->is_nmethod(), "must be called from nmethod");
   86.76 +  CodeBlob* caller_cb = caller_frame.cb();
   86.77 +  guarantee(caller_cb != NULL && caller_cb->is_nmethod(), "must be called from nmethod");
   86.78 +  nmethod* caller_nm = caller_cb->as_nmethod_or_null();
   86.79    // make sure caller is not getting deoptimized
   86.80    // and removed before we are done with it.
   86.81    // CLEANUP - with lazy deopt shouldn't need this lock
   86.82 -  nmethodLocker caller_lock((nmethod*)cb);
   86.83 +  nmethodLocker caller_lock(caller_nm);
   86.84  
   86.85  
   86.86    // determine call info & receiver
   86.87 @@ -929,6 +925,13 @@
   86.88    }
   86.89  #endif
   86.90  
   86.91 +  // JSR 292
   86.92 +  // If the resolved method is a MethodHandle invoke target the call
   86.93 +  // site must be a MethodHandle call site.
   86.94 +  if (callee_method->is_method_handle_invoke()) {
   86.95 +    assert(caller_nm->is_method_handle_return(caller_frame.pc()), "must be MH call site");
   86.96 +  }
   86.97 +
   86.98    // Compute entry points. This might require generation of C2I converter
   86.99    // frames, so we cannot be holding any locks here. Furthermore, the
  86.100    // computation of the entry points is independent of patching the call.  We
  86.101 @@ -940,13 +943,12 @@
  86.102    StaticCallInfo static_call_info;
  86.103    CompiledICInfo virtual_call_info;
  86.104  
  86.105 -
  86.106    // Make sure the callee nmethod does not get deoptimized and removed before
  86.107    // we are done patching the code.
  86.108 -  nmethod* nm = callee_method->code();
  86.109 -  nmethodLocker nl_callee(nm);
  86.110 +  nmethod* callee_nm = callee_method->code();
  86.111 +  nmethodLocker nl_callee(callee_nm);
  86.112  #ifdef ASSERT
  86.113 -  address dest_entry_point = nm == NULL ? 0 : nm->entry_point(); // used below
  86.114 +  address dest_entry_point = callee_nm == NULL ? 0 : callee_nm->entry_point(); // used below
  86.115  #endif
  86.116  
  86.117    if (is_virtual) {
  86.118 @@ -2077,7 +2079,6 @@
  86.119  
  86.120  // ---------------------------------------------------------------------------
  86.121  // Implementation of AdapterHandlerLibrary
  86.122 -const char* AdapterHandlerEntry::name = "I2C/C2I adapters";
  86.123  AdapterHandlerTable* AdapterHandlerLibrary::_adapters = NULL;
  86.124  AdapterHandlerEntry* AdapterHandlerLibrary::_abstract_method_handler = NULL;
  86.125  const int AdapterHandlerLibrary_size = 16*K;
  86.126 @@ -2129,7 +2130,7 @@
  86.127    ResourceMark rm;
  86.128  
  86.129    NOT_PRODUCT(int code_size);
  86.130 -  BufferBlob *B = NULL;
  86.131 +  AdapterBlob* B = NULL;
  86.132    AdapterHandlerEntry* entry = NULL;
  86.133    AdapterFingerPrint* fingerprint = NULL;
  86.134    {
  86.135 @@ -2179,7 +2180,7 @@
  86.136  
  86.137      // Create I2C & C2I handlers
  86.138  
  86.139 -    BufferBlob*  buf = buffer_blob(); // the temporary code buffer in CodeCache
  86.140 +    BufferBlob* buf = buffer_blob(); // the temporary code buffer in CodeCache
  86.141      if (buf != NULL) {
  86.142        CodeBuffer buffer(buf->instructions_begin(), buf->instructions_size());
  86.143        short buffer_locs[20];
  86.144 @@ -2208,7 +2209,7 @@
  86.145        }
  86.146  #endif
  86.147  
  86.148 -      B = BufferBlob::create(AdapterHandlerEntry::name, &buffer);
  86.149 +      B = AdapterBlob::create(&buffer);
  86.150        NOT_PRODUCT(code_size = buffer.code_size());
  86.151      }
  86.152      if (B == NULL) {
  86.153 @@ -2240,7 +2241,7 @@
  86.154      jio_snprintf(blob_id,
  86.155                   sizeof(blob_id),
  86.156                   "%s(%s)@" PTR_FORMAT,
  86.157 -                 AdapterHandlerEntry::name,
  86.158 +                 B->name(),
  86.159                   fingerprint->as_string(),
  86.160                   B->instructions_begin());
  86.161      VTune::register_stub(blob_id, B->instructions_begin(), B->instructions_end());
    87.1 --- a/src/share/vm/runtime/sharedRuntime.hpp	Thu Mar 25 16:54:59 2010 -0700
    87.2 +++ b/src/share/vm/runtime/sharedRuntime.hpp	Fri Mar 26 11:10:26 2010 -0400
    87.3 @@ -96,10 +96,9 @@
    87.4    static jdouble dexp(jdouble x);
    87.5    static jdouble dpow(jdouble x, jdouble y);
    87.6  
    87.7 -
    87.8    // exception handling across interpreter/compiler boundaries
    87.9 -  static address raw_exception_handler_for_return_address(address return_address);
   87.10 -  static address exception_handler_for_return_address(address return_address);
   87.11 +  static address raw_exception_handler_for_return_address(JavaThread* thread, address return_address);
   87.12 +  static address exception_handler_for_return_address(JavaThread* thread, address return_address);
   87.13  
   87.14  #ifndef SERIALGC
   87.15    // G1 write barriers
   87.16 @@ -568,9 +567,6 @@
   87.17    AdapterHandlerEntry();
   87.18  
   87.19   public:
   87.20 -  // The name we give all buffer blobs
   87.21 -  static const char* name;
   87.22 -
   87.23    address get_i2c_entry()            { return _i2c_entry; }
   87.24    address get_c2i_entry()            { return _c2i_entry; }
   87.25    address get_c2i_unverified_entry() { return _c2i_unverified_entry; }
    88.1 --- a/src/share/vm/runtime/vframeArray.cpp	Thu Mar 25 16:54:59 2010 -0700
    88.2 +++ b/src/share/vm/runtime/vframeArray.cpp	Fri Mar 26 11:10:26 2010 -0400
    88.3 @@ -223,7 +223,7 @@
    88.4          break;
    88.5        case Deoptimization::Unpack_exception:
    88.6          // exception is pending
    88.7 -        pc = SharedRuntime::raw_exception_handler_for_return_address(pc);
    88.8 +        pc = SharedRuntime::raw_exception_handler_for_return_address(thread, pc);
    88.9          // [phh] We're going to end up in some handler or other, so it doesn't
   88.10          // matter what mdp we point to.  See exception_handler_for_exception()
   88.11          // in interpreterRuntime.cpp.
    89.1 --- a/src/share/vm/utilities/globalDefinitions.hpp	Thu Mar 25 16:54:59 2010 -0700
    89.2 +++ b/src/share/vm/utilities/globalDefinitions.hpp	Fri Mar 26 11:10:26 2010 -0400
    89.3 @@ -827,6 +827,8 @@
    89.4  #define       badHeapWord       (::badHeapWordVal)
    89.5  #define       badJNIHandle      ((oop)::badJNIHandleVal)
    89.6  
    89.7 +// Default TaskQueue size is 16K (32-bit) or 128K (64-bit)
    89.8 +#define TASKQUEUE_SIZE (NOT_LP64(1<<14) LP64_ONLY(1<<17))
    89.9  
   89.10  //----------------------------------------------------------------------------------------------------
   89.11  // Utility functions for bitfield manipulations
    90.1 --- a/src/share/vm/utilities/taskqueue.cpp	Thu Mar 25 16:54:59 2010 -0700
    90.2 +++ b/src/share/vm/utilities/taskqueue.cpp	Fri Mar 26 11:10:26 2010 -0400
    90.3 @@ -31,10 +31,6 @@
    90.4  uint ParallelTaskTerminator::_total_peeks = 0;
    90.5  #endif
    90.6  
    90.7 -bool TaskQueueSuper::peek() {
    90.8 -  return _bottom != _age.top();
    90.9 -}
   90.10 -
   90.11  int TaskQueueSetSuper::randomParkAndMiller(int *seed0) {
   90.12    const int a =      16807;
   90.13    const int m = 2147483647;
   90.14 @@ -180,6 +176,13 @@
   90.15    }
   90.16  }
   90.17  
   90.18 +#ifdef ASSERT
   90.19 +bool ObjArrayTask::is_valid() const {
   90.20 +  return _obj != NULL && _obj->is_objArray() && _index > 0 &&
   90.21 +    _index < objArrayOop(_obj)->length();
   90.22 +}
   90.23 +#endif // ASSERT
   90.24 +
   90.25  bool RegionTaskQueueWithOverflow::is_empty() {
   90.26    return (_region_queue.size() == 0) &&
   90.27           (_overflow_stack->length() == 0);
    91.1 --- a/src/share/vm/utilities/taskqueue.hpp	Thu Mar 25 16:54:59 2010 -0700
    91.2 +++ b/src/share/vm/utilities/taskqueue.hpp	Fri Mar 26 11:10:26 2010 -0400
    91.3 @@ -22,6 +22,7 @@
    91.4   *
    91.5   */
    91.6  
    91.7 +template <unsigned int N>
    91.8  class TaskQueueSuper: public CHeapObj {
    91.9  protected:
   91.10    // Internal type for indexing the queue; also used for the tag.
   91.11 @@ -30,10 +31,7 @@
   91.12    // The first free element after the last one pushed (mod N).
   91.13    volatile uint _bottom;
   91.14  
   91.15 -  enum {
   91.16 -    N = 1 << NOT_LP64(14) LP64_ONLY(17), // Queue size: 16K or 128K
   91.17 -    MOD_N_MASK = N - 1                   // To compute x mod N efficiently.
   91.18 -  };
   91.19 +  enum { MOD_N_MASK = N - 1 };
   91.20  
   91.21    class Age {
   91.22    public:
   91.23 @@ -84,12 +82,12 @@
   91.24  
   91.25    // Returns a number in the range [0..N).  If the result is "N-1", it should be
   91.26    // interpreted as 0.
   91.27 -  uint dirty_size(uint bot, uint top) {
   91.28 +  uint dirty_size(uint bot, uint top) const {
   91.29      return (bot - top) & MOD_N_MASK;
   91.30    }
   91.31  
   91.32    // Returns the size corresponding to the given "bot" and "top".
   91.33 -  uint size(uint bot, uint top) {
   91.34 +  uint size(uint bot, uint top) const {
   91.35      uint sz = dirty_size(bot, top);
   91.36      // Has the queue "wrapped", so that bottom is less than top?  There's a
   91.37      // complicated special case here.  A pair of threads could perform pop_local
   91.38 @@ -111,17 +109,17 @@
   91.39  public:
   91.40    TaskQueueSuper() : _bottom(0), _age() {}
   91.41  
   91.42 -  // Return "true" if the TaskQueue contains any tasks.
   91.43 -  bool peek();
   91.44 +  // Return true if the TaskQueue contains any tasks.
   91.45 +  bool peek() { return _bottom != _age.top(); }
   91.46  
   91.47    // Return an estimate of the number of elements in the queue.
   91.48    // The "careful" version admits the possibility of pop_local/pop_global
   91.49    // races.
   91.50 -  uint size() {
   91.51 +  uint size() const {
   91.52      return size(_bottom, _age.top());
   91.53    }
   91.54  
   91.55 -  uint dirty_size() {
   91.56 +  uint dirty_size() const {
   91.57      return dirty_size(_bottom, _age.top());
   91.58    }
   91.59  
   91.60 @@ -132,19 +130,36 @@
   91.61  
   91.62    // Maximum number of elements allowed in the queue.  This is two less
   91.63    // than the actual queue size, for somewhat complicated reasons.
   91.64 -  uint max_elems() { return N - 2; }
   91.65 +  uint max_elems() const { return N - 2; }
   91.66  
   91.67    // Total size of queue.
   91.68    static const uint total_size() { return N; }
   91.69  };
   91.70  
   91.71 -template<class E> class GenericTaskQueue: public TaskQueueSuper {
   91.72 +template<class E, unsigned int N = TASKQUEUE_SIZE>
   91.73 +class GenericTaskQueue: public TaskQueueSuper<N> {
   91.74 +protected:
   91.75 +  typedef typename TaskQueueSuper<N>::Age Age;
   91.76 +  typedef typename TaskQueueSuper<N>::idx_t idx_t;
   91.77 +
   91.78 +  using TaskQueueSuper<N>::_bottom;
   91.79 +  using TaskQueueSuper<N>::_age;
   91.80 +  using TaskQueueSuper<N>::increment_index;
   91.81 +  using TaskQueueSuper<N>::decrement_index;
   91.82 +  using TaskQueueSuper<N>::dirty_size;
   91.83 +
   91.84 +public:
   91.85 +  using TaskQueueSuper<N>::max_elems;
   91.86 +  using TaskQueueSuper<N>::size;
   91.87 +
   91.88  private:
   91.89    // Slow paths for push, pop_local.  (pop_global has no fast path.)
   91.90    bool push_slow(E t, uint dirty_n_elems);
   91.91    bool pop_local_slow(uint localBot, Age oldAge);
   91.92  
   91.93  public:
   91.94 +  typedef E element_type;
   91.95 +
   91.96    // Initializes the queue to empty.
   91.97    GenericTaskQueue();
   91.98  
   91.99 @@ -175,19 +190,19 @@
  91.100    volatile E* _elems;
  91.101  };
  91.102  
  91.103 -template<class E>
  91.104 -GenericTaskQueue<E>::GenericTaskQueue():TaskQueueSuper() {
  91.105 +template<class E, unsigned int N>
  91.106 +GenericTaskQueue<E, N>::GenericTaskQueue() {
  91.107    assert(sizeof(Age) == sizeof(size_t), "Depends on this.");
  91.108  }
  91.109  
  91.110 -template<class E>
  91.111 -void GenericTaskQueue<E>::initialize() {
  91.112 +template<class E, unsigned int N>
  91.113 +void GenericTaskQueue<E, N>::initialize() {
  91.114    _elems = NEW_C_HEAP_ARRAY(E, N);
  91.115    guarantee(_elems != NULL, "Allocation failed.");
  91.116  }
  91.117  
  91.118 -template<class E>
  91.119 -void GenericTaskQueue<E>::oops_do(OopClosure* f) {
  91.120 +template<class E, unsigned int N>
  91.121 +void GenericTaskQueue<E, N>::oops_do(OopClosure* f) {
  91.122    // tty->print_cr("START OopTaskQueue::oops_do");
  91.123    uint iters = size();
  91.124    uint index = _bottom;
  91.125 @@ -203,21 +218,21 @@
  91.126    // tty->print_cr("END OopTaskQueue::oops_do");
  91.127  }
  91.128  
  91.129 -
  91.130 -template<class E>
  91.131 -bool GenericTaskQueue<E>::push_slow(E t, uint dirty_n_elems) {
  91.132 +template<class E, unsigned int N>
  91.133 +bool GenericTaskQueue<E, N>::push_slow(E t, uint dirty_n_elems) {
  91.134    if (dirty_n_elems == N - 1) {
  91.135      // Actually means 0, so do the push.
  91.136      uint localBot = _bottom;
  91.137 -    _elems[localBot] = t;
  91.138 +    // g++ complains if the volatile result of the assignment is unused.
  91.139 +    const_cast<E&>(_elems[localBot] = t);
  91.140      OrderAccess::release_store(&_bottom, increment_index(localBot));
  91.141      return true;
  91.142    }
  91.143    return false;
  91.144  }
  91.145  
  91.146 -template<class E>
  91.147 -bool GenericTaskQueue<E>::
  91.148 +template<class E, unsigned int N>
  91.149 +bool GenericTaskQueue<E, N>::
  91.150  pop_local_slow(uint localBot, Age oldAge) {
  91.151    // This queue was observed to contain exactly one element; either this
  91.152    // thread will claim it, or a competing "pop_global".  In either case,
  91.153 @@ -249,8 +264,8 @@
  91.154    return false;
  91.155  }
  91.156  
  91.157 -template<class E>
  91.158 -bool GenericTaskQueue<E>::pop_global(E& t) {
  91.159 +template<class E, unsigned int N>
  91.160 +bool GenericTaskQueue<E, N>::pop_global(E& t) {
  91.161    Age oldAge = _age.get();
  91.162    uint localBot = _bottom;
  91.163    uint n_elems = size(localBot, oldAge.top());
  91.164 @@ -258,7 +273,7 @@
  91.165      return false;
  91.166    }
  91.167  
  91.168 -  t = _elems[oldAge.top()];
  91.169 +  const_cast<E&>(t = _elems[oldAge.top()]);
  91.170    Age newAge(oldAge);
  91.171    newAge.increment();
  91.172    Age resAge = _age.cmpxchg(newAge, oldAge);
  91.173 @@ -269,8 +284,8 @@
  91.174    return resAge == oldAge;
  91.175  }
  91.176  
  91.177 -template<class E>
  91.178 -GenericTaskQueue<E>::~GenericTaskQueue() {
  91.179 +template<class E, unsigned int N>
  91.180 +GenericTaskQueue<E, N>::~GenericTaskQueue() {
  91.181    FREE_C_HEAP_ARRAY(E, _elems);
  91.182  }
  91.183  
  91.184 @@ -283,16 +298,18 @@
  91.185    virtual bool peek() = 0;
  91.186  };
  91.187  
  91.188 -template<class E> class GenericTaskQueueSet: public TaskQueueSetSuper {
  91.189 +template<class T>
  91.190 +class GenericTaskQueueSet: public TaskQueueSetSuper {
  91.191  private:
  91.192    uint _n;
  91.193 -  GenericTaskQueue<E>** _queues;
  91.194 +  T** _queues;
  91.195  
  91.196  public:
  91.197 +  typedef typename T::element_type E;
  91.198 +
  91.199    GenericTaskQueueSet(int n) : _n(n) {
  91.200 -    typedef GenericTaskQueue<E>* GenericTaskQueuePtr;
  91.201 +    typedef T* GenericTaskQueuePtr;
  91.202      _queues = NEW_C_HEAP_ARRAY(GenericTaskQueuePtr, n);
  91.203 -    guarantee(_queues != NULL, "Allocation failure.");
  91.204      for (int i = 0; i < n; i++) {
  91.205        _queues[i] = NULL;
  91.206      }
  91.207 @@ -302,9 +319,9 @@
  91.208    bool steal_best_of_2(uint queue_num, int* seed, E& t);
  91.209    bool steal_best_of_all(uint queue_num, int* seed, E& t);
  91.210  
  91.211 -  void register_queue(uint i, GenericTaskQueue<E>* q);
  91.212 +  void register_queue(uint i, T* q);
  91.213  
  91.214 -  GenericTaskQueue<E>* queue(uint n);
  91.215 +  T* queue(uint n);
  91.216  
  91.217    // The thread with queue number "queue_num" (and whose random number seed
  91.218    // is at "seed") is trying to steal a task from some other queue.  (It
  91.219 @@ -316,27 +333,27 @@
  91.220    bool peek();
  91.221  };
  91.222  
  91.223 -template<class E>
  91.224 -void GenericTaskQueueSet<E>::register_queue(uint i, GenericTaskQueue<E>* q) {
  91.225 +template<class T> void
  91.226 +GenericTaskQueueSet<T>::register_queue(uint i, T* q) {
  91.227    assert(i < _n, "index out of range.");
  91.228    _queues[i] = q;
  91.229  }
  91.230  
  91.231 -template<class E>
  91.232 -GenericTaskQueue<E>* GenericTaskQueueSet<E>::queue(uint i) {
  91.233 +template<class T> T*
  91.234 +GenericTaskQueueSet<T>::queue(uint i) {
  91.235    return _queues[i];
  91.236  }
  91.237  
  91.238 -template<class E>
  91.239 -bool GenericTaskQueueSet<E>::steal(uint queue_num, int* seed, E& t) {
  91.240 +template<class T> bool
  91.241 +GenericTaskQueueSet<T>::steal(uint queue_num, int* seed, E& t) {
  91.242    for (uint i = 0; i < 2 * _n; i++)
  91.243      if (steal_best_of_2(queue_num, seed, t))
  91.244        return true;
  91.245    return false;
  91.246  }
  91.247  
  91.248 -template<class E>
  91.249 -bool GenericTaskQueueSet<E>::steal_best_of_all(uint queue_num, int* seed, E& t) {
  91.250 +template<class T> bool
  91.251 +GenericTaskQueueSet<T>::steal_best_of_all(uint queue_num, int* seed, E& t) {
  91.252    if (_n > 2) {
  91.253      int best_k;
  91.254      uint best_sz = 0;
  91.255 @@ -359,8 +376,8 @@
  91.256    }
  91.257  }
  91.258  
  91.259 -template<class E>
  91.260 -bool GenericTaskQueueSet<E>::steal_1_random(uint queue_num, int* seed, E& t) {
  91.261 +template<class T> bool
  91.262 +GenericTaskQueueSet<T>::steal_1_random(uint queue_num, int* seed, E& t) {
  91.263    if (_n > 2) {
  91.264      uint k = queue_num;
  91.265      while (k == queue_num) k = randomParkAndMiller(seed) % _n;
  91.266 @@ -375,8 +392,8 @@
  91.267    }
  91.268  }
  91.269  
  91.270 -template<class E>
  91.271 -bool GenericTaskQueueSet<E>::steal_best_of_2(uint queue_num, int* seed, E& t) {
  91.272 +template<class T> bool
  91.273 +GenericTaskQueueSet<T>::steal_best_of_2(uint queue_num, int* seed, E& t) {
  91.274    if (_n > 2) {
  91.275      uint k1 = queue_num;
  91.276      while (k1 == queue_num) k1 = randomParkAndMiller(seed) % _n;
  91.277 @@ -397,8 +414,8 @@
  91.278    }
  91.279  }
  91.280  
  91.281 -template<class E>
  91.282 -bool GenericTaskQueueSet<E>::peek() {
  91.283 +template<class T>
  91.284 +bool GenericTaskQueueSet<T>::peek() {
  91.285    // Try all the queues.
  91.286    for (uint j = 0; j < _n; j++) {
  91.287      if (_queues[j]->peek())
  91.288 @@ -468,14 +485,16 @@
  91.289  #endif
  91.290  };
  91.291  
  91.292 -template<class E> inline bool GenericTaskQueue<E>::push(E t) {
  91.293 +template<class E, unsigned int N> inline bool
  91.294 +GenericTaskQueue<E, N>::push(E t) {
  91.295    uint localBot = _bottom;
  91.296    assert((localBot >= 0) && (localBot < N), "_bottom out of range.");
  91.297    idx_t top = _age.top();
  91.298    uint dirty_n_elems = dirty_size(localBot, top);
  91.299 -  assert((dirty_n_elems >= 0) && (dirty_n_elems < N), "n_elems out of range.");
  91.300 +  assert(dirty_n_elems < N, "n_elems out of range.");
  91.301    if (dirty_n_elems < max_elems()) {
  91.302 -    _elems[localBot] = t;
  91.303 +    // g++ complains if the volatile result of the assignment is unused.
  91.304 +    const_cast<E&>(_elems[localBot] = t);
  91.305      OrderAccess::release_store(&_bottom, increment_index(localBot));
  91.306      return true;
  91.307    } else {
  91.308 @@ -483,7 +502,8 @@
  91.309    }
  91.310  }
  91.311  
  91.312 -template<class E> inline bool GenericTaskQueue<E>::pop_local(E& t) {
  91.313 +template<class E, unsigned int N> inline bool
  91.314 +GenericTaskQueue<E, N>::pop_local(E& t) {
  91.315    uint localBot = _bottom;
  91.316    // This value cannot be N-1.  That can only occur as a result of
  91.317    // the assignment to bottom in this method.  If it does, this method
  91.318 @@ -497,7 +517,7 @@
  91.319    // This is necessary to prevent any read below from being reordered
  91.320    // before the store just above.
  91.321    OrderAccess::fence();
  91.322 -  t = _elems[localBot];
  91.323 +  const_cast<E&>(t = _elems[localBot]);
  91.324    // This is a second read of "age"; the "size()" above is the first.
  91.325    // If there's still at least one element in the queue, based on the
  91.326    // "_bottom" and "age" we've read, then there can be no interference with
  91.327 @@ -514,17 +534,23 @@
  91.328  }
  91.329  
  91.330  typedef oop Task;
  91.331 -typedef GenericTaskQueue<Task>         OopTaskQueue;
  91.332 -typedef GenericTaskQueueSet<Task>      OopTaskQueueSet;
  91.333 +typedef GenericTaskQueue<Task>            OopTaskQueue;
  91.334 +typedef GenericTaskQueueSet<OopTaskQueue> OopTaskQueueSet;
  91.335  
  91.336 -
  91.337 -#define COMPRESSED_OOP_MASK  1
  91.338 +#ifdef _MSC_VER
  91.339 +#pragma warning(push)
  91.340 +// warning C4522: multiple assignment operators specified
  91.341 +#pragma warning(disable:4522)
  91.342 +#endif
  91.343  
  91.344  // This is a container class for either an oop* or a narrowOop*.
  91.345  // Both are pushed onto a task queue and the consumer will test is_narrow()
  91.346  // to determine which should be processed.
  91.347  class StarTask {
  91.348    void*  _holder;        // either union oop* or narrowOop*
  91.349 +
  91.350 +  enum { COMPRESSED_OOP_MASK = 1 };
  91.351 +
  91.352   public:
  91.353    StarTask(narrowOop* p) {
  91.354      assert(((uintptr_t)p & COMPRESSED_OOP_MASK) == 0, "Information loss!");
  91.355 @@ -540,20 +566,61 @@
  91.356      return (narrowOop*)((uintptr_t)_holder & ~COMPRESSED_OOP_MASK);
  91.357    }
  91.358  
  91.359 -  // Operators to preserve const/volatile in assignments required by gcc
  91.360 -  void operator=(const volatile StarTask& t) volatile { _holder = t._holder; }
  91.361 +  StarTask& operator=(const StarTask& t) {
  91.362 +    _holder = t._holder;
  91.363 +    return *this;
  91.364 +  }
  91.365 +  volatile StarTask& operator=(const volatile StarTask& t) volatile {
  91.366 +    _holder = t._holder;
  91.367 +    return *this;
  91.368 +  }
  91.369  
  91.370    bool is_narrow() const {
  91.371      return (((uintptr_t)_holder & COMPRESSED_OOP_MASK) != 0);
  91.372    }
  91.373  };
  91.374  
  91.375 -typedef GenericTaskQueue<StarTask>     OopStarTaskQueue;
  91.376 -typedef GenericTaskQueueSet<StarTask>  OopStarTaskQueueSet;
  91.377 +class ObjArrayTask
  91.378 +{
  91.379 +public:
  91.380 +  ObjArrayTask(oop o = NULL, int idx = 0): _obj(o), _index(idx) { }
  91.381 +  ObjArrayTask(oop o, size_t idx): _obj(o), _index(int(idx)) {
  91.382 +    assert(idx <= size_t(max_jint), "too big");
  91.383 +  }
  91.384 +  ObjArrayTask(const ObjArrayTask& t): _obj(t._obj), _index(t._index) { }
  91.385 +
  91.386 +  ObjArrayTask& operator =(const ObjArrayTask& t) {
  91.387 +    _obj = t._obj;
  91.388 +    _index = t._index;
  91.389 +    return *this;
  91.390 +  }
  91.391 +  volatile ObjArrayTask&
  91.392 +  operator =(const volatile ObjArrayTask& t) volatile {
  91.393 +    _obj = t._obj;
  91.394 +    _index = t._index;
  91.395 +    return *this;
  91.396 +  }
  91.397 +
  91.398 +  inline oop obj()   const { return _obj; }
  91.399 +  inline int index() const { return _index; }
  91.400 +
  91.401 +  DEBUG_ONLY(bool is_valid() const); // Tasks to be pushed/popped must be valid.
  91.402 +
  91.403 +private:
  91.404 +  oop _obj;
  91.405 +  int _index;
  91.406 +};
  91.407 +
  91.408 +#ifdef _MSC_VER
  91.409 +#pragma warning(pop)
  91.410 +#endif
  91.411 +
  91.412 +typedef GenericTaskQueue<StarTask>            OopStarTaskQueue;
  91.413 +typedef GenericTaskQueueSet<OopStarTaskQueue> OopStarTaskQueueSet;
  91.414  
  91.415  typedef size_t RegionTask;  // index for region
  91.416 -typedef GenericTaskQueue<RegionTask>    RegionTaskQueue;
  91.417 -typedef GenericTaskQueueSet<RegionTask> RegionTaskQueueSet;
  91.418 +typedef GenericTaskQueue<RegionTask>         RegionTaskQueue;
  91.419 +typedef GenericTaskQueueSet<RegionTaskQueue> RegionTaskQueueSet;
  91.420  
  91.421  class RegionTaskQueueWithOverflow: public CHeapObj {
  91.422   protected:
    92.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    92.2 +++ b/test/compiler/6930043/Test6930043.java	Fri Mar 26 11:10:26 2010 -0400
    92.3 @@ -0,0 +1,76 @@
    92.4 +/*
    92.5 + * Copyright 2010 Sun Microsystems, Inc.  All Rights Reserved.
    92.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    92.7 + *
    92.8 + * This code is free software; you can redistribute it and/or modify it
    92.9 + * under the terms of the GNU General Public License version 2 only, as
   92.10 + * published by the Free Software Foundation.
   92.11 + *
   92.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   92.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   92.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   92.15 + * version 2 for more details (a copy is included in the LICENSE file that
   92.16 + * accompanied this code).
   92.17 + *
   92.18 + * You should have received a copy of the GNU General Public License version
   92.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   92.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   92.21 + *
   92.22 + * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
   92.23 + * CA 95054 USA or visit www.sun.com if you need additional information or
   92.24 + * have any questions.
   92.25 + *
   92.26 + */
   92.27 +
   92.28 +/**
   92.29 + * @test
   92.30 + * @bug 6930043
   92.31 + * @summary C2: SIGSEGV in javasoft.sqe.tests.lang.arr017.arr01702.arr01702.loop_forw(II)I
   92.32 + *
   92.33 + * @run main Test6930043
   92.34 + */
   92.35 +
   92.36 +import java.io.PrintStream;
   92.37 +
   92.38 +public class Test6930043 {
   92.39 +    int[] a;
   92.40 +    int idx;
   92.41 +
   92.42 +    public int loop_back(int i, int i_0_) {
   92.43 +        int i_1_ = 0;
   92.44 +        int[] is = a;
   92.45 +        if (is == null) return 0;
   92.46 +        for (int i_2_ = i; i_2_ >= i_0_; i_2_--)
   92.47 +            i_1_ += is[idx = i_2_];
   92.48 +        return i_1_;
   92.49 +    }
   92.50 +
   92.51 +    public int loop_forw(int start, int end) {
   92.52 +        int result = 0;
   92.53 +        int[] is = a;
   92.54 +        if (is == null) return 0;
   92.55 +        for (int index = start; index < end; index++)
   92.56 +            result += is[index];
   92.57 +            // result += is[idx = index];
   92.58 +        return result;
   92.59 +    }
   92.60 +
   92.61 +    public static void main(String[] strings) {
   92.62 +        Test6930043 var_Test6930043 = new Test6930043();
   92.63 +        var_Test6930043.a = new int[1000000];
   92.64 +        var_Test6930043.loop_forw(10, 999990);
   92.65 +        var_Test6930043.loop_forw(10, 999990);
   92.66 +        for (int i = 0; i < 3; i++) {
   92.67 +            try {
   92.68 +                if (var_Test6930043.loop_forw(-1, 999990) != 0) throw new InternalError();
   92.69 +            } catch (ArrayIndexOutOfBoundsException e) { }
   92.70 +        }
   92.71 +        var_Test6930043.loop_back(999990, 10);
   92.72 +        var_Test6930043.loop_back(999990, 10);
   92.73 +        for (int i = 0; i < 3; i++) {
   92.74 +            try {
   92.75 +                if (var_Test6930043.loop_back(999990, -1) != 0) throw new InternalError();
   92.76 +            } catch (ArrayIndexOutOfBoundsException e) { }
   92.77 +        }
   92.78 +    }
   92.79 +}
    93.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    93.2 +++ b/test/compiler/6932496/Test6932496.java	Fri Mar 26 11:10:26 2010 -0400
    93.3 @@ -0,0 +1,51 @@
    93.4 +/*
    93.5 + * Copyright 2010 Sun Microsystems, Inc.  All Rights Reserved.
    93.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    93.7 + *
    93.8 + * This code is free software; you can redistribute it and/or modify it
    93.9 + * under the terms of the GNU General Public License version 2 only, as
   93.10 + * published by the Free Software Foundation.
   93.11 + *
   93.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   93.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   93.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   93.15 + * version 2 for more details (a copy is included in the LICENSE file that
   93.16 + * accompanied this code).
   93.17 + *
   93.18 + * You should have received a copy of the GNU General Public License version
   93.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   93.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   93.21 + *
   93.22 + * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
   93.23 + * CA 95054 USA or visit www.sun.com if you need additional information or
   93.24 + * have any questions.
   93.25 + *
   93.26 + */
   93.27 +
   93.28 +/**
   93.29 + * @test
   93.30 + * @bug 6932496
   93.31 + * @summary incorrect deopt of jsr subroutine on 64 bit c1
   93.32 + *
   93.33 + * @compile -source 1.5 -target 1.5 -XDjsrlimit=0 Test6932496.java
   93.34 + * @run main/othervm -Xcomp -XX:CompileOnly=Test6932496.m Test6932496
   93.35 + */
   93.36 +
   93.37 +public class Test6932496 {
   93.38 +    static class A {
   93.39 +        volatile boolean flag = false;
   93.40 +    }
   93.41 +
   93.42 +    static void m() {
   93.43 +        try {
   93.44 +        } finally {
   93.45 +            A a = new A();
   93.46 +            a.flag = true;
   93.47 +        }
   93.48 +    }
   93.49 +
   93.50 +
   93.51 +    static public void main(String[] args) {
   93.52 +        m();
   93.53 +    }
   93.54 +}
    94.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    94.2 +++ b/test/compiler/6935535/Test.java	Fri Mar 26 11:10:26 2010 -0400
    94.3 @@ -0,0 +1,48 @@
    94.4 +/*
    94.5 + * Copyright 2010 Sun Microsystems, Inc.  All Rights Reserved.
    94.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    94.7 + *
    94.8 + * This code is free software; you can redistribute it and/or modify it
    94.9 + * under the terms of the GNU General Public License version 2 only, as
   94.10 + * published by the Free Software Foundation.
   94.11 + *
   94.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   94.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   94.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   94.15 + * version 2 for more details (a copy is included in the LICENSE file that
   94.16 + * accompanied this code).
   94.17 + *
   94.18 + * You should have received a copy of the GNU General Public License version
   94.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   94.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   94.21 + *
   94.22 + * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
   94.23 + * CA 95054 USA or visit www.sun.com if you need additional information or
   94.24 + * have any questions.
   94.25 + */
   94.26 +
   94.27 +/**
   94.28 + * @test
   94.29 + * @bug 6935535
   94.30 + * @summary String.indexOf() returns incorrect result on x86 with SSE4.2
   94.31 + *
   94.32 + * @run main/othervm -Xcomp Test
   94.33 + */
   94.34 +
   94.35 +public class Test {
   94.36 +
   94.37 +  static int IndexOfTest(String str) {
   94.38 +    return str.indexOf("1111111111111xx1x");
   94.39 +  }
   94.40 +
   94.41 +  public static void main(String args[]) {
   94.42 +    String str = "1111111111111xx1111111111111xx1x";
   94.43 +    str = str.substring(0, 31);
   94.44 +    int idx = IndexOfTest(str);
   94.45 +    System.out.println("IndexOf(" + "1111111111111xx1x" + ") = " + idx + " in " + str);
   94.46 +    if (idx != -1) {
   94.47 +      System.exit(97);
   94.48 +    }
   94.49 +  }
   94.50 +}
   94.51 +

mercurial