changeset 468:a3fedaf25c6d

annot, meth: prepare for review
author jrose
date Tue, 10 Jul 2012 23:31:05 -0700
parents 747688368d8f
children 2ebbc5f13bb6
files annot-6711908.patch annot-inline.patch annot.patch series
diffstat 4 files changed, 658 insertions(+), 687 deletions(-) [+]
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/annot-6711908.patch	Tue Jul 10 23:31:05 2012 -0700
@@ -0,0 +1,657 @@
+6711908: JVM needs direct access to some annotations
+Summary: Add annotation extraction code to class file parser.
+Contributed-by: jrose, michael.haupt@oracle.com
+Reviewed-by: twisti, jrose
+
+diff --git a/src/share/vm/c1/c1_GraphBuilder.cpp b/src/share/vm/c1/c1_GraphBuilder.cpp
+--- a/src/share/vm/c1/c1_GraphBuilder.cpp
++++ b/src/share/vm/c1/c1_GraphBuilder.cpp
+@@ -3505,8 +3505,9 @@
+   }
+ 
+   // now perform tests that are based on flag settings
+-  if (callee->should_inline()) {
++  if (callee->force_inline() || callee->should_inline()) {
+     // ignore heuristic controls on inlining
++    _inline_bailout_msg = "forced inlining";
+   } else {
+     if (inline_level() > MaxInlineLevel                         ) INLINE_BAILOUT("too-deep inlining");
+     if (recursive_inline_level(callee) > MaxRecursiveInlineLevel) INLINE_BAILOUT("too-deep recursive inlining");
+@@ -3531,7 +3532,7 @@
+   }
+ 
+ #ifndef PRODUCT
+-      // printing
++  // printing
+   if (PrintInlining) {
+     print_inline_result(callee, true);
+   }
+diff --git a/src/share/vm/ci/ciMethod.hpp b/src/share/vm/ci/ciMethod.hpp
+--- a/src/share/vm/ci/ciMethod.hpp
++++ b/src/share/vm/ci/ciMethod.hpp
+@@ -160,6 +160,8 @@
+   // Code size for inlining decisions.
+   int code_size_for_inlining();
+ 
++  bool force_inline() { return get_methodOop()->force_inline(); }
++
+   int comp_level();
+   int highest_osr_comp_level();
+ 
+diff --git a/src/share/vm/classfile/classFileParser.cpp b/src/share/vm/classfile/classFileParser.cpp
+--- a/src/share/vm/classfile/classFileParser.cpp
++++ b/src/share/vm/classfile/classFileParser.cpp
+@@ -318,6 +318,13 @@
+ 
+ bool inline valid_cp_range(int index, int length) { return (index > 0 && index < length); }
+ 
++inline Symbol* check_symbol_at(constantPoolHandle cp, int index) {
++  if (valid_cp_range(index, cp->length()) && cp->tag_at(index).is_utf8())
++    return cp->symbol_at(index);
++  else
++    return NULL;
++}
++
+ constantPoolHandle ClassFileParser::parse_constant_pool(Handle class_loader, TRAPS) {
+   ClassFileStream* cfs = stream();
+   constantPoolHandle nullHandle;
+@@ -902,6 +909,7 @@
+                                              bool* is_synthetic_addr,
+                                              u2* generic_signature_index_addr,
+                                              typeArrayHandle* field_annotations,
++                                             ClassFileParser::FieldAnnotationCollector* parsed_annotations,
+                                              TRAPS) {
+   ClassFileStream* cfs = stream();
+   assert(attributes_count > 0, "length should be greater than 0");
+@@ -1142,12 +1150,14 @@
+     bool is_synthetic = false;
+     u2 generic_signature_index = 0;
+     bool is_static = access_flags.is_static();
++    FieldAnnotationCollector parsed_annotations;
+ 
+     u2 attributes_count = cfs->get_u2_fast();
+     if (attributes_count > 0) {
+       parse_field_attributes(cp, attributes_count, is_static, signature_index,
+                              &constantvalue_index, &is_synthetic,
+                              &generic_signature_index, &field_annotations,
++                             &parsed_annotations,
+                              CHECK_(nullHandle));
+       if (field_annotations.not_null()) {
+         if (fields_annotations->is_null()) {
+@@ -1173,6 +1183,8 @@
+                       signature_index,
+                       constantvalue_index,
+                       0);
++    if (parsed_annotations.has_any_annotations())
++      parsed_annotations.apply_to(field);
+ 
+     BasicType type = cp->basic_type_for_signature_at(signature_index);
+ 
+@@ -1638,12 +1650,159 @@
+       name->as_C_string(), _class_name->as_C_string(), sig->as_C_string());
+ }
+ 
++// Skip an annotation.  Return >=limit if there is any problem.
++int ClassFileParser::skip_annotation(u1* buffer, int limit, int index) {
++  // annotation := atype:u2 do(nmem:u2) {member:u2 value}
++  // value := switch (tag:u1) { ... } 
++  index += 2;  // skip atype
++  if ((index += 2) >= limit)  return limit;  // read nmem
++  int nmem = Bytes::get_Java_u2(buffer+index-2);
++  while (--nmem >= 0 && index < limit) {
++    index += 2; // skip member
++    index = skip_annotation_value(buffer, limit, index);
++  }
++  return index;
++}
++
++// Skip an annotation value.  Return >=limit if there is any problem.
++int ClassFileParser::skip_annotation_value(u1* buffer, int limit, int index) {
++  // value := switch (tag:u1) {
++  //   case B, C, I, S, Z, D, F, J, c: con:u2;
++  //   case e: e_class:u2 e_name:u2;
++  //   case s: s_con:u2;
++  //   case [: do(nval:u2) {value};
++  //   case @: annotation;
++  //   case s: s_con:u2;
++  // }
++  if ((index += 1) >= limit)  return limit;  // read tag
++  u1 tag = buffer[index-1];
++  switch (tag) {
++  case 'B': case 'C': case 'I': case 'S': case 'Z':
++  case 'D': case 'F': case 'J': case 'c': case 's':
++    index += 2;  // skip con or s_con
++    break;
++  case 'e':
++    index += 4;  // skip e_class, e_name
++    break;
++  case '[':
++    {
++      if ((index += 2) >= limit)  return limit;  // read nval
++      int nval = Bytes::get_Java_u2(buffer+index-2);
++      while (--nval >= 0 && index < limit) {
++        index = skip_annotation_value(buffer, limit, index);
++      }
++    }
++    break;
++  case '@':
++    index = skip_annotation(buffer, limit, index);
++    break;
++  default:
++    assert(false, "annotation tag");
++    return limit;  //  bad tag byte
++  }
++  return index;
++}
++
++// Sift through annotations, looking for those significant to the VM:
++void ClassFileParser::parse_annotations(u1* buffer, int limit,
++                                        constantPoolHandle cp,
++                                        ClassFileParser::AnnotationCollector* coll,
++                                        TRAPS) {
++  // annotations := do(nann:u2) {annotation}
++  int index = 0;
++  if ((index += 2) >= limit)  return;  // read nann
++  int nann = Bytes::get_Java_u2(buffer+index-2);
++  enum {  // initial annotation layout
++    atype_off = 0,      // utf8 such as 'Ljava/lang/annotation/Retention;'
++    count_off = 2,      // u2   such as 1 (one value)
++    member_off = 4,     // utf8 such as 'value'
++    tag_off = 6,        // u1   such as 'c' (type) or 'e' (enum)
++    e_tag_val = 'e',
++      e_type_off = 7,   // utf8 such as 'Ljava/lang/annotation/RetentionPolicy;'
++      e_con_off = 9,    // utf8 payload, such as 'SOURCE', 'CLASS', 'RUNTIME'
++      e_size = 11,     // end of 'e' annotation
++    c_tag_val = 'c',
++      c_con_off = 7,    // utf8 payload, such as 'I' or 'Ljava/lang/String;'
++      c_size = 9,       // end of 'c' annotation
++    min_size = 6        // smallest possible size (zero members)
++  };
++  while (--nann >= 0 && index-2 + min_size <= limit) {
++    int index0 = index;
++    index = skip_annotation(buffer, limit, index);
++    u1* abase = buffer + index0;
++    int atype = Bytes::get_Java_u2(abase + atype_off);
++    int count = Bytes::get_Java_u2(abase + count_off);
++    Symbol* aname = check_symbol_at(cp, atype);
++    if (aname == NULL)  break;  // invalid annotation name
++    Symbol* member = NULL;
++    if (count >= 1) {
++      int member_index = Bytes::get_Java_u2(abase + member_off);
++      member = check_symbol_at(cp, member_index);
++      if (member == NULL)  break;  // invalid member name
++    }
++
++    // Here is where parsing particular annotations will take place.
++    AnnotationCollector::ID id = coll->annotation_index(aname);
++    if (id == AnnotationCollector::_unknown)  continue;
++    coll->set_annotation(id);
++    // If there are no values, just set the bit and move on:
++    if (count == 0)   continue;
++
++#if 0
++    // The parsing of @Retention is for example only.
++    if (id == AnnotationCollector::_class_Retention) {
++      Symbol* payload = NULL;
++      if (count == 1
++          && e_size == (index0 - index)  // match size
++          && e_tag_val == *(abase + tag_off)
++          && (check_symbol_at(cp, Bytes::get_Java_u2(abase + e_type_off))
++              == vmSymbols::RetentionPolicy_signature())
++          && member == vmSymbols::value_name()) {
++        payload = check_symbol_at(cp, Bytes::get_Java_u2(abase + e_con_off));
++      }
++      check_property(payload != NULL,
++                     "Invalid @Retention annotation at offset %u in class file %s",
++                     index0, CHECK);
++      if (payload != NULL) {
++          payload->increment_refcount();
++          coll->_class_RetentionPolicy = payload;
++      }
++    }
++#endif //0
++  }
++}
++
++ClassFileParser::AnnotationCollector::ID ClassFileParser::AnnotationCollector::annotation_index(Symbol* name) {
++  vmSymbols::SID sid = vmSymbols::find_sid(name);
++  switch (sid) {
++  case vmSymbols::VM_SYMBOL_ENUM_NAME(java_lang_invoke_ForceInline_signature):
++    if (_location != _in_class)  break;
++    return _method_ForceInline;
++  default: break;
++  }
++  return AnnotationCollector::_unknown;
++}
++
++void ClassFileParser::FieldAnnotationCollector::apply_to(FieldInfo* f) {
++  assert(false, "");
++}
++
++void ClassFileParser::MethodAnnotationCollector::apply_to(methodHandle m) {
++  if (has_annotation(_method_ForceInline))
++    m->set_force_inline(true);
++}
++
++void ClassFileParser::ClassAnnotationCollector::apply_to(instanceKlassHandle k) {
++  assert(false, "");
++}
++
++
+ #define MAX_ARGS_SIZE 255
+ #define MAX_CODE_SIZE 65535
+ #define INITIAL_MAX_LVT_NUMBER 256
+ 
+ // Note: the parse_method below is big and clunky because all parsing of the code and exceptions
+-// attribute is inlined. This is curbersome to avoid since we inline most of the parts in the
++// attribute is inlined. This is cumbersome to avoid since we inline most of the parts in the
+ // methodOop to save footprint, so we only know the size of the resulting methodOop when the
+ // entire method attribute is parsed.
+ //
+@@ -1733,6 +1892,7 @@
+   // stackmap attribute - JDK1.5
+   typeArrayHandle stackmap_data;
+   u2 generic_signature_index = 0;
++  MethodAnnotationCollector parsed_annotations;
+   u1* runtime_visible_annotations = NULL;
+   int runtime_visible_annotations_length = 0;
+   u1* runtime_invisible_annotations = NULL;
+@@ -1959,6 +2119,7 @@
+         runtime_visible_annotations_length = method_attribute_length;
+         runtime_visible_annotations = cfs->get_u1_buffer();
+         assert(runtime_visible_annotations != NULL, "null visible annotations");
++        parse_annotations(runtime_visible_annotations, runtime_visible_annotations_length, cp, &parsed_annotations, CHECK_(nullHandle));
+         cfs->skip_u1(runtime_visible_annotations_length, CHECK_(nullHandle));
+       } else if (PreserveAllAnnotations && method_attribute_name == vmSymbols::tag_runtime_invisible_annotations()) {
+         runtime_invisible_annotations_length = method_attribute_length;
+@@ -2136,6 +2297,8 @@
+     clear_hashtable(lvt_Hash);
+   }
+ 
++  if (parsed_annotations.has_any_annotations())
++    parsed_annotations.apply_to(m);
+   *method_annotations = assemble_annotations(runtime_visible_annotations,
+                                              runtime_visible_annotations_length,
+                                              runtime_invisible_annotations,
+@@ -2314,7 +2477,7 @@
+ }
+ 
+ 
+-void ClassFileParser::parse_classfile_sourcefile_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS) {
++void ClassFileParser::parse_classfile_sourcefile_attribute(constantPoolHandle cp, Symbol** sourcefile_ret, TRAPS) {
+   ClassFileStream* cfs = stream();
+   cfs->guarantee_more(2, CHECK);  // sourcefile_index
+   u2 sourcefile_index = cfs->get_u2_fast();
+@@ -2323,14 +2486,16 @@
+       cp->tag_at(sourcefile_index).is_utf8(),
+     "Invalid SourceFile attribute at constant pool index %u in class file %s",
+     sourcefile_index, CHECK);
+-  k->set_source_file_name(cp->symbol_at(sourcefile_index));
++  (*sourcefile_ret) = cp->symbol_at(sourcefile_index);
++  (*sourcefile_ret)->increment_refcount();
+ }
+ 
+ 
+ 
+ void ClassFileParser::parse_classfile_source_debug_extension_attribute(constantPoolHandle cp,
+-                                                                       instanceKlassHandle k,
+-                                                                       int length, TRAPS) {
++                                                                       int length,
++                                                                       TempNewSymbol* sde_symbol_ret,
++                                                                       TRAPS) {
+   ClassFileStream* cfs = stream();
+   u1* sde_buffer = cfs->get_u1_buffer();
+   assert(sde_buffer != NULL, "null sde buffer");
+@@ -2339,8 +2504,7 @@
+   if (JvmtiExport::can_get_source_debug_extension()) {
+     // Optimistically assume that only 1 byte UTF format is used
+     // (common case)
+-    TempNewSymbol sde_symbol = SymbolTable::new_symbol((const char*)sde_buffer, length, CHECK);
+-    k->set_source_debug_extension(sde_symbol);
++    (*sde_symbol_ret) = SymbolTable::new_symbol((const char*)sde_buffer, length, CHECK);
+     // Note that set_source_debug_extension() increments the reference count
+     // for its copy of the Symbol*, so use a TempNewSymbol here.
+   }
+@@ -2358,7 +2522,7 @@
+                                                             u2 enclosing_method_class_index,
+                                                             u2 enclosing_method_method_index,
+                                                             constantPoolHandle cp,
+-                                                            instanceKlassHandle k, TRAPS) {
++                                                            typeArrayHandle* inner_classes_ret, TRAPS) {
+   ClassFileStream* cfs = stream();
+   u1* current_mark = cfs->current();
+   u2 length = 0;
+@@ -2449,7 +2613,7 @@
+   assert(index == size, "wrong size");
+ 
+   // Update instanceKlass with inner class info.
+-  k->set_inner_classes(inner_classes());
++  (*inner_classes_ret) = inner_classes;
+ 
+   // Restore buffer's current position.
+   cfs->set_current(current_mark);
+@@ -2457,11 +2621,11 @@
+   return length;
+ }
+ 
+-void ClassFileParser::parse_classfile_synthetic_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS) {
+-  k->set_is_synthetic();
++void ClassFileParser::parse_classfile_synthetic_attribute(constantPoolHandle cp, bool* synthetic_flag_ret, TRAPS) {
++  (*synthetic_flag_ret) = true;
+ }
+ 
+-void ClassFileParser::parse_classfile_signature_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS) {
++void ClassFileParser::parse_classfile_signature_attribute(constantPoolHandle cp, Symbol** signature_ret, TRAPS) {
+   ClassFileStream* cfs = stream();
+   u2 signature_index = cfs->get_u2(CHECK);
+   check_property(
+@@ -2469,10 +2633,11 @@
+       cp->tag_at(signature_index).is_utf8(),
+     "Invalid constant pool index %u in Signature attribute in class file %s",
+     signature_index, CHECK);
+-  k->set_generic_signature(cp->symbol_at(signature_index));
++  (*signature_ret) = cp->symbol_at(signature_index);
++  (*signature_ret)->increment_refcount();
+ }
+ 
+-void ClassFileParser::parse_classfile_bootstrap_methods_attribute(constantPoolHandle cp, instanceKlassHandle k,
++void ClassFileParser::parse_classfile_bootstrap_methods_attribute(constantPoolHandle cp,
+                                                                   u4 attribute_byte_length, TRAPS) {
+   ClassFileStream* cfs = stream();
+   u1* current_start = cfs->current();
+@@ -2544,10 +2709,12 @@
+ }
+ 
+ 
+-void ClassFileParser::parse_classfile_attributes(constantPoolHandle cp, instanceKlassHandle k, TRAPS) {
++void ClassFileParser::parse_classfile_attributes(constantPoolHandle cp,
++                                                 ClassFileParser::ClassAnnotationCollector* parsed_annotations,
++                                                 TRAPS) {
+   ClassFileStream* cfs = stream();
+   // Set inner classes attribute to default sentinel
+-  k->set_inner_classes(Universe::the_empty_short_array());
++  _inner_classes = typeArrayHandle(THREAD, Universe::the_empty_short_array());
+   cfs->guarantee_more(2, CHECK);  // attributes_count
+   u2 attributes_count = cfs->get_u2_fast();
+   bool parsed_sourcefile_attribute = false;
+@@ -2562,6 +2729,7 @@
+   u4  inner_classes_attribute_length = 0;
+   u2  enclosing_method_class_index = 0;
+   u2  enclosing_method_method_index = 0;
++  TempNewSymbol sde_symbol = NULL;
+   // Iterate over attributes
+   while (attributes_count--) {
+     cfs->guarantee_more(6, CHECK);  // attribute_name_index, attribute_length
+@@ -2583,10 +2751,10 @@
+       } else {
+         parsed_sourcefile_attribute = true;
+       }
+-      parse_classfile_sourcefile_attribute(cp, k, CHECK);
++      parse_classfile_sourcefile_attribute(cp, &_sourcefile, CHECK);
+     } else if (tag == vmSymbols::tag_source_debug_extension()) {
+       // Check for SourceDebugExtension tag
+-      parse_classfile_source_debug_extension_attribute(cp, k, (int)attribute_length, CHECK);
++      parse_classfile_source_debug_extension_attribute(cp, (int)attribute_length, &_sde_symbol, CHECK);
+     } else if (tag == vmSymbols::tag_inner_classes()) {
+       // Check for InnerClasses tag
+       if (parsed_innerclasses_attribute) {
+@@ -2605,7 +2773,7 @@
+           "Invalid Synthetic classfile attribute length %u in class file %s",
+           attribute_length, CHECK);
+       }
+-      parse_classfile_synthetic_attribute(cp, k, CHECK);
++      parse_classfile_synthetic_attribute(cp, &_synthetic_flag, CHECK);
+     } else if (tag == vmSymbols::tag_deprecated()) {
+       // Check for Deprecatd tag - 4276120
+       if (attribute_length != 0) {
+@@ -2620,11 +2788,16 @@
+             "Wrong Signature attribute length %u in class file %s",
+             attribute_length, CHECK);
+         }
+-        parse_classfile_signature_attribute(cp, k, CHECK);
++        parse_classfile_signature_attribute(cp, &_generic_signature, CHECK);
+       } else if (tag == vmSymbols::tag_runtime_visible_annotations()) {
+         runtime_visible_annotations_length = attribute_length;
+         runtime_visible_annotations = cfs->get_u1_buffer();
+         assert(runtime_visible_annotations != NULL, "null visible annotations");
++        parse_annotations(runtime_visible_annotations,
++                          runtime_visible_annotations_length,
++                          cp,
++                          parsed_annotations,
++                          CHECK);
+         cfs->skip_u1(runtime_visible_annotations_length, CHECK);
+       } else if (PreserveAllAnnotations && tag == vmSymbols::tag_runtime_invisible_annotations()) {
+         runtime_invisible_annotations_length = attribute_length;
+@@ -2658,7 +2831,7 @@
+         if (parsed_bootstrap_methods_attribute)
+           classfile_parse_error("Multiple BootstrapMethods attributes in class file %s", CHECK);
+         parsed_bootstrap_methods_attribute = true;
+-        parse_classfile_bootstrap_methods_attribute(cp, k, attribute_length, CHECK);
++        parse_classfile_bootstrap_methods_attribute(cp, attribute_length, CHECK);
+       } else {
+         // Unknown attribute
+         cfs->skip_u1(attribute_length, CHECK);
+@@ -2673,7 +2846,7 @@
+                                                      runtime_invisible_annotations,
+                                                      runtime_invisible_annotations_length,
+                                                      CHECK);
+-  k->set_class_annotations(annotations());
++  _annotations = annotations;
+ 
+   if (parsed_innerclasses_attribute || parsed_enclosingmethod_attribute) {
+     u2 num_of_classes = parse_classfile_inner_classes_attribute(
+@@ -2681,7 +2854,7 @@
+                             parsed_innerclasses_attribute,
+                             enclosing_method_class_index,
+                             enclosing_method_method_index,
+-                            cp, k, CHECK);
++                            cp, &_inner_classes, CHECK);
+     if (parsed_innerclasses_attribute &&_need_verify && _major_version >= JAVA_1_5_VERSION) {
+       guarantee_property(
+         inner_classes_attribute_length == sizeof(num_of_classes) + 4 * sizeof(u2) * num_of_classes,
+@@ -2748,6 +2921,12 @@
+   _has_finalizer = _has_empty_finalizer = _has_vanilla_constructor = false;
+   _max_bootstrap_specifier_index = -1;
+ 
++  _synthetic_flag = false;
++
++  _sourcefile = NULL;
++  _generic_signature = NULL;
++  _sde_symbol = NULL;
++
+   if (JvmtiExport::should_post_class_file_load_hook()) {
+     // Get the cached class file bytes (if any) from the class that
+     // is being redefined or retransformed. We use jvmti_thread_state()
+@@ -2979,6 +3158,13 @@
+     objArrayHandle methods_parameter_annotations(THREAD, methods_parameter_annotations_oop);
+     objArrayHandle methods_default_annotations(THREAD, methods_default_annotations_oop);
+ 
++    // Additional attributes
++    ClassAnnotationCollector parsed_annotations;
++    parse_classfile_attributes(cp, &parsed_annotations, CHECK_(nullHandle));
++
++    // Make sure this is the end of class file stream
++    guarantee_property(cfs->at_eos(), "Extra bytes at the end of class file %s", CHECK_(nullHandle));
++
+     // We check super class after class file is parsed and format is checked
+     if (super_class_index > 0 && super_klass.is_null()) {
+       Symbol*  sk  = cp->klass_name_at(super_class_index);
+@@ -3467,11 +3653,15 @@
+       this_klass->set_has_miranda_methods(); // then set a flag
+     }
+ 
+-    // Additional attributes
+-    parse_classfile_attributes(cp, this_klass, CHECK_(nullHandle));
+-
+-    // Make sure this is the end of class file stream
+-    guarantee_property(cfs->at_eos(), "Extra bytes at the end of class file %s", CHECK_(nullHandle));
++    // Fill in field values from parse_classfile_attributes:
++    this_klass->set_inner_classes(_inner_classes());
++    this_klass->set_source_file_name(_sourcefile);
++    this_klass->set_source_debug_extension(_sde_symbol);
++    this_klass->set_generic_signature(_generic_signature);
++    if (_synthetic_flag)  this_klass->set_is_synthetic();
++    if (parsed_annotations.has_any_annotations())
++      parsed_annotations.apply_to(this_klass);
++    this_klass->set_class_annotations(_annotations());
+ 
+     // VerifyOops believes that once this has been set, the object is completely loaded.
+     // Compute transitive closure of interfaces this class implements
+diff --git a/src/share/vm/classfile/classFileParser.hpp b/src/share/vm/classfile/classFileParser.hpp
+--- a/src/share/vm/classfile/classFileParser.hpp
++++ b/src/share/vm/classfile/classFileParser.hpp
+@@ -31,8 +31,8 @@
+ #include "oops/typeArrayOop.hpp"
+ #include "runtime/handles.inline.hpp"
+ #include "utilities/accessFlags.hpp"
++#include "classfile/symbolTable.hpp"
+ 
+-class TempNewSymbol;
+ class FieldAllocationCount;
+ 
+ 
+@@ -54,6 +54,54 @@
+   bool _has_empty_finalizer;
+   bool _has_vanilla_constructor;
+ 
++  // class attributes parsed before the instance klass is created:
++  bool       _synthetic_flag;
++  Symbol*    _sourcefile;
++  Symbol*    _generic_signature;
++  TempNewSymbol   _sde_symbol;
++  typeArrayHandle _inner_classes;
++  typeArrayHandle _annotations;
++
++  class AnnotationCollector {
++  public:
++    enum Location { _in_field, _in_method, _in_class };
++    enum ID {
++      _unknown = 0,
++      _method_ForceInline,
++      _annotation_LIMIT
++    };
++    const Location _location;
++    int _annotations_present;
++    AnnotationCollector(Location location)
++    : _location(location), _annotations_present(0)
++    { }
++    // If this annotation name has an ID, report it (or _none).
++    ID annotation_index(Symbol* name);
++    // Set the annotation name:
++    void set_annotation(ID id) {
++      assert((int)id >= 0 && (int)id < BitsPerInt, "oob");
++      _annotations_present |= nth_bit((int)id);
++    }
++    // Report if the annotation is present.
++    bool has_any_annotations() { return _annotations_present != 0; }
++    bool has_annotation(ID id) { return (nth_bit((int)id) & _annotations_present) != 0; }
++  };
++  class FieldAnnotationCollector: public AnnotationCollector {
++  public:
++    FieldAnnotationCollector() : AnnotationCollector(_in_field) { }
++    void apply_to(FieldInfo* f);
++  };
++  class MethodAnnotationCollector: public AnnotationCollector {
++  public:
++    MethodAnnotationCollector() : AnnotationCollector(_in_method) { }
++    void apply_to(methodHandle m);
++  };
++  class ClassAnnotationCollector: public AnnotationCollector {
++  public:
++    ClassAnnotationCollector() : AnnotationCollector(_in_class) { }
++    void apply_to(instanceKlassHandle k);
++  };
++
+   int _max_bootstrap_specifier_index;
+ 
+   enum { fixed_buffer_size = 128 };
+@@ -87,7 +135,9 @@
+                               u2* constantvalue_index_addr,
+                               bool* is_synthetic_addr,
+                               u2* generic_signature_index_addr,
+-                              typeArrayHandle* field_annotations, TRAPS);
++                              typeArrayHandle* field_annotations,
++                              FieldAnnotationCollector* parsed_annotations,
++                              TRAPS);
+   typeArrayHandle parse_fields(Symbol* class_name,
+                                constantPoolHandle cp, bool is_interface,
+                                FieldAllocationCount *fac,
+@@ -128,25 +178,34 @@
+   typeArrayOop parse_stackmap_table(u4 code_attribute_length, TRAPS);
+ 
+   // Classfile attribute parsing
+-  void parse_classfile_sourcefile_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS);
+-  void parse_classfile_source_debug_extension_attribute(constantPoolHandle cp,
+-                                                instanceKlassHandle k, int length, TRAPS);
++  void parse_classfile_sourcefile_attribute(constantPoolHandle cp, Symbol** sourcefile, TRAPS);
++  void parse_classfile_source_debug_extension_attribute(constantPoolHandle cp, int length,
++                                                        TempNewSymbol* sde_symbol_ret,
++                                                        TRAPS);
+   u2   parse_classfile_inner_classes_attribute(u1* inner_classes_attribute_start,
+                                                bool parsed_enclosingmethod_attribute,
+                                                u2 enclosing_method_class_index,
+                                                u2 enclosing_method_method_index,
+                                                constantPoolHandle cp,
+-                                               instanceKlassHandle k, TRAPS);
+-  void parse_classfile_attributes(constantPoolHandle cp, instanceKlassHandle k, TRAPS);
+-  void parse_classfile_synthetic_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS);
+-  void parse_classfile_signature_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS);
+-  void parse_classfile_bootstrap_methods_attribute(constantPoolHandle cp, instanceKlassHandle k, u4 attribute_length, TRAPS);
++                                               typeArrayHandle* inner_classes, TRAPS);
++  void parse_classfile_attributes(constantPoolHandle cp,
++                                  ClassFileParser::ClassAnnotationCollector* parsed_annotations,
++                                  TRAPS);
++  void parse_classfile_synthetic_attribute(constantPoolHandle cp, bool* synthetic_flag, TRAPS);
++  void parse_classfile_signature_attribute(constantPoolHandle cp, Symbol** signature, TRAPS);
++  void parse_classfile_bootstrap_methods_attribute(constantPoolHandle cp, u4 attribute_length, TRAPS);
+ 
+   // Annotations handling
+   typeArrayHandle assemble_annotations(u1* runtime_visible_annotations,
+                                        int runtime_visible_annotations_length,
+                                        u1* runtime_invisible_annotations,
+                                        int runtime_invisible_annotations_length, TRAPS);
++  int skip_annotation(u1* buffer, int limit, int index);
++  int skip_annotation_value(u1* buffer, int limit, int index);
++  void parse_annotations(u1* buffer, int limit, constantPoolHandle cp,
++                         /* Results (currently, only one result is supported): */
++                         AnnotationCollector* result,
++                         TRAPS);
+ 
+   // Final setup
+   unsigned int compute_oop_map_count(instanceKlassHandle super,
+diff --git a/src/share/vm/classfile/vmSymbols.hpp b/src/share/vm/classfile/vmSymbols.hpp
+--- a/src/share/vm/classfile/vmSymbols.hpp
++++ b/src/share/vm/classfile/vmSymbols.hpp
+@@ -257,6 +257,7 @@
+   template(java_lang_invoke_BoundMethodHandle,        "java/lang/invoke/BoundMethodHandle")       \
+   template(java_lang_invoke_DirectMethodHandle,       "java/lang/invoke/DirectMethodHandle")      \
+   template(java_lang_invoke_CountingMethodHandle,     "java/lang/invoke/CountingMethodHandle")    \
++  template(java_lang_invoke_ForceInline_signature,    "Ljava/lang/invoke/ForceInline;")           \
+   /* internal up-calls made only by the JVM, via class sun.invoke.MethodHandleNatives: */         \
+   template(findMethodHandleType_name,                 "findMethodHandleType")                     \
+   template(findMethodHandleType_signature,       "(Ljava/lang/Class;[Ljava/lang/Class;)Ljava/lang/invoke/MethodType;") \
+diff --git a/src/share/vm/oops/methodOop.hpp b/src/share/vm/oops/methodOop.hpp
+--- a/src/share/vm/oops/methodOop.hpp
++++ b/src/share/vm/oops/methodOop.hpp
+@@ -122,8 +122,9 @@
+   u2                _max_locals;                 // Number of local variables used by this method
+   u2                _size_of_parameters;         // size of the parameter block (receiver + arguments) in words
+   u1                _intrinsic_id;               // vmSymbols::intrinsic_id (0 == _none)
+-  u1                _jfr_towrite : 1,            // Flags
+-                                 : 7;
++  u1                _jfr_towrite  : 1,           // Flags
++                    _force_inline : 1,
++                                  : 6;
+   u2                _interpreter_throwout_count; // Count of times method was exited via exception while interpreting
+   u2                _number_of_breakpoints;      // fullspeed debugging support
+   InvocationCounter _invocation_counter;         // Incremented before each activation of the method - used to trigger frequency-based optimizations
+@@ -655,6 +656,9 @@
+   bool jfr_towrite()                 { return _jfr_towrite; }
+   void set_jfr_towrite(bool towrite) { _jfr_towrite = towrite; }
+ 
++  bool force_inline()            { return _force_inline; }
++  void set_force_inline(bool fi) { _force_inline = fi; }
++
+   // On-stack replacement support
+   bool has_osr_nmethod(int level, bool match_level) {
+    return instanceKlass::cast(method_holder())->lookup_osr_nmethod(this, InvocationEntryBci, level, match_level) != NULL;
--- a/annot-inline.patch	Tue Jul 10 22:42:01 2012 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,105 +0,0 @@
-diff --git a/src/share/vm/c1/c1_GraphBuilder.cpp b/src/share/vm/c1/c1_GraphBuilder.cpp
---- a/src/share/vm/c1/c1_GraphBuilder.cpp
-+++ b/src/share/vm/c1/c1_GraphBuilder.cpp
-@@ -3489,8 +3489,9 @@
-   }
- 
-   // now perform tests that are based on flag settings
--  if (callee->should_inline()) {
-+  if (callee->force_inline() || callee->should_inline()) {
-     // ignore heuristic controls on inlining
-+    _inline_bailout_msg = "forced inlining";
-   } else {
-     if (inline_level() > MaxInlineLevel                         ) INLINE_BAILOUT("too-deep inlining");
-     if (recursive_inline_level(callee) > MaxRecursiveInlineLevel) INLINE_BAILOUT("too-deep recursive inlining");
-@@ -3515,7 +3516,7 @@
-   }
- 
- #ifndef PRODUCT
--      // printing
-+  // printing
-   if (PrintInlining) {
-     print_inline_result(callee, true);
-   }
-diff --git a/src/share/vm/ci/ciMethod.hpp b/src/share/vm/ci/ciMethod.hpp
---- a/src/share/vm/ci/ciMethod.hpp
-+++ b/src/share/vm/ci/ciMethod.hpp
-@@ -160,6 +160,8 @@
-   // Code size for inlining decisions.
-   int code_size_for_inlining();
- 
-+  bool force_inline() { return get_methodOop()->force_inline(); }
-+
-   int comp_level();
-   int highest_osr_comp_level();
- 
-diff --git a/src/share/vm/classfile/classFileParser.cpp b/src/share/vm/classfile/classFileParser.cpp
---- a/src/share/vm/classfile/classFileParser.cpp
-+++ b/src/share/vm/classfile/classFileParser.cpp
-@@ -1737,6 +1737,9 @@
- ClassFileParser::AnnotationCollector::ID ClassFileParser::AnnotationCollector::annotation_index(Symbol* name) {
-   vmSymbols::SID sid = vmSymbols::find_sid(name);
-   switch (sid) {
-+  case vmSymbols::VM_SYMBOL_ENUM_NAME(java_lang_invoke_ForceInline_signature):
-+    if (_location != _in_class)  break;
-+    return _method_ForceInline;
-   default: break;
-   }
-   return AnnotationCollector::_unknown;
-@@ -1747,7 +1750,8 @@
- }
- 
- void ClassFileParser::MethodAnnotationCollector::apply_to(methodHandle m) {
--  assert(false, "");
-+  if (has_annotation(_method_ForceInline))
-+    m->set_force_inline(true);
- }
- 
- void ClassFileParser::ClassAnnotationCollector::apply_to(instanceKlassHandle k) {
-diff --git a/src/share/vm/classfile/classFileParser.hpp b/src/share/vm/classfile/classFileParser.hpp
---- a/src/share/vm/classfile/classFileParser.hpp
-+++ b/src/share/vm/classfile/classFileParser.hpp
-@@ -67,6 +67,7 @@
-     enum Location { _in_field, _in_method, _in_class };
-     enum ID {
-       _unknown = 0,
-+      _method_ForceInline,
-       _annotation_LIMIT
-     };
-     const Location _location;
-diff --git a/src/share/vm/classfile/vmSymbols.hpp b/src/share/vm/classfile/vmSymbols.hpp
---- a/src/share/vm/classfile/vmSymbols.hpp
-+++ b/src/share/vm/classfile/vmSymbols.hpp
-@@ -252,6 +252,7 @@
-   template(java_lang_invoke_BoundMethodHandle,        "java/lang/invoke/BoundMethodHandle")       \
-   template(java_lang_invoke_DirectMethodHandle,       "java/lang/invoke/DirectMethodHandle")      \
-   template(java_lang_invoke_CountingMethodHandle,     "java/lang/invoke/CountingMethodHandle")    \
-+  template(java_lang_invoke_ForceInline_signature,    "Ljava/lang/invoke/ForceInline;")           \
-   /* internal up-calls made only by the JVM, via class sun.invoke.MethodHandleNatives: */         \
-   template(findMethodHandleType_name,                 "findMethodHandleType")                     \
-   template(findMethodHandleType_signature,       "(Ljava/lang/Class;[Ljava/lang/Class;)Ljava/lang/invoke/MethodType;") \
-diff --git a/src/share/vm/oops/methodOop.hpp b/src/share/vm/oops/methodOop.hpp
---- a/src/share/vm/oops/methodOop.hpp
-+++ b/src/share/vm/oops/methodOop.hpp
-@@ -124,8 +124,9 @@
-   u2                _max_locals;                 // Number of local variables used by this method
-   u2                _size_of_parameters;         // size of the parameter block (receiver + arguments) in words
-   u1                _intrinsic_id;               // vmSymbols::intrinsic_id (0 == _none)
--  u1                _jfr_towrite : 1,            // Flags
--                                 : 7;
-+  u1                _jfr_towrite  : 1,           // Flags
-+                    _force_inline : 1,
-+                                  : 6;
-   u2                _interpreter_throwout_count; // Count of times method was exited via exception while interpreting
-   u2                _number_of_breakpoints;      // fullspeed debugging support
-   InvocationCounter _invocation_counter;         // Incremented before each activation of the method - used to trigger frequency-based optimizations
-@@ -658,6 +659,9 @@
-   bool jfr_towrite()                 { return _jfr_towrite; }
-   void set_jfr_towrite(bool towrite) { _jfr_towrite = towrite; }
- 
-+  bool force_inline()            { return _force_inline; }
-+  void set_force_inline(bool fi) { _force_inline = fi; }
-+
-   // On-stack replacement support
-   bool has_osr_nmethod(int level, bool match_level) {
-    return instanceKlass::cast(method_holder())->lookup_osr_nmethod(this, InvocationEntryBci, level, match_level) != NULL;
--- a/annot.patch	Tue Jul 10 22:42:01 2012 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,580 +0,0 @@
-6711908: JVM needs direct access to some annotations
-Summary: Add annotation extraction code to class file parser.
-Contributed-by: jrose, michael.haupt@oracle.com
-
-diff --git a/src/share/vm/classfile/classFileParser.cpp b/src/share/vm/classfile/classFileParser.cpp
---- a/src/share/vm/classfile/classFileParser.cpp
-+++ b/src/share/vm/classfile/classFileParser.cpp
-@@ -318,6 +318,13 @@
- 
- bool inline valid_cp_range(int index, int length) { return (index > 0 && index < length); }
- 
-+inline Symbol* check_symbol_at(constantPoolHandle cp, int index) {
-+  if (valid_cp_range(index, cp->length()) && cp->tag_at(index).is_utf8())
-+    return cp->symbol_at(index);
-+  else
-+    return NULL;
-+}
-+
- constantPoolHandle ClassFileParser::parse_constant_pool(Handle class_loader, TRAPS) {
-   ClassFileStream* cfs = stream();
-   constantPoolHandle nullHandle;
-@@ -902,6 +909,7 @@
-                                              bool* is_synthetic_addr,
-                                              u2* generic_signature_index_addr,
-                                              typeArrayHandle* field_annotations,
-+                                             ClassFileParser::FieldAnnotationCollector* parsed_annotations,
-                                              TRAPS) {
-   ClassFileStream* cfs = stream();
-   assert(attributes_count > 0, "length should be greater than 0");
-@@ -1118,12 +1126,14 @@
-     bool is_synthetic = false;
-     u2 generic_signature_index = 0;
-     bool is_static = access_flags.is_static();
-+    FieldAnnotationCollector parsed_annotations;
- 
-     u2 attributes_count = cfs->get_u2_fast();
-     if (attributes_count > 0) {
-       parse_field_attributes(cp, attributes_count, is_static, signature_index,
-                              &constantvalue_index, &is_synthetic,
-                              &generic_signature_index, &field_annotations,
-+                             &parsed_annotations,
-                              CHECK_(nullHandle));
-       if (field_annotations.not_null()) {
-         if (fields_annotations->is_null()) {
-@@ -1144,6 +1154,8 @@
-                       signature_index,
-                       constantvalue_index,
-                       0);
-+    if (parsed_annotations.has_any_annotations())
-+      parsed_annotations.apply_to(field);
- 
-     BasicType type = cp->basic_type_for_signature_at(signature_index);
- 
-@@ -1600,12 +1612,155 @@
-       name->as_C_string(), _class_name->as_C_string(), sig->as_C_string());
- }
- 
-+// Skip an annotation.  Return >=limit if there is any problem.
-+int ClassFileParser::skip_annotation(u1* buffer, int limit, int index) {
-+  // annotation := atype:u2 do(nmem:u2) {member:u2 value}
-+  // value := switch (tag:u1) { ... } 
-+  index += 2;  // skip atype
-+  if ((index += 2) >= limit)  return limit;  // read nmem
-+  int nmem = Bytes::get_Java_u2(buffer+index-2);
-+  while (--nmem >= 0 && index < limit) {
-+    index += 2; // skip member
-+    index = skip_annotation_value(buffer, limit, index);
-+  }
-+  return index;
-+}
-+
-+// Skip an annotation value.  Return >=limit if there is any problem.
-+int ClassFileParser::skip_annotation_value(u1* buffer, int limit, int index) {
-+  // value := switch (tag:u1) {
-+  //   case B, C, I, S, Z, D, F, J, c: con:u2;
-+  //   case e: e_class:u2 e_name:u2;
-+  //   case s: s_con:u2;
-+  //   case [: do(nval:u2) {value};
-+  //   case @: annotation;
-+  //   case s: s_con:u2;
-+  // }
-+  if ((index += 1) >= limit)  return limit;  // read tag
-+  u1 tag = buffer[index-1];
-+  switch (tag) {
-+  case 'B': case 'C': case 'I': case 'S': case 'Z':
-+  case 'D': case 'F': case 'J': case 'c': case 's':
-+    index += 2;  // skip con or s_con
-+    break;
-+  case 'e':
-+    index += 4;  // skip e_class, e_name
-+    break;
-+  case '[':
-+    {
-+      if ((index += 2) >= limit)  return limit;  // read nval
-+      int nval = Bytes::get_Java_u2(buffer+index-2);
-+      while (--nval >= 0 && index < limit) {
-+        index = skip_annotation_value(buffer, limit, index);
-+      }
-+    }
-+    break;
-+  case '@':
-+    index = skip_annotation(buffer, limit, index);
-+    break;
-+  default:
-+    assert(false, "annotation tag");
-+    return limit;  //  bad tag byte
-+  }
-+  return index;
-+}
-+
-+// Sift through annotations, looking for those significant to the VM:
-+void ClassFileParser::parse_annotations(u1* buffer, int limit,
-+                                        constantPoolHandle cp,
-+                                        ClassFileParser::AnnotationCollector* coll,
-+                                        TRAPS) {
-+  // annotations := do(nann:u2) {annotation}
-+  int index = 0;
-+  if ((index += 2) >= limit)  return;  // read nann
-+  int nann = Bytes::get_Java_u2(buffer+index-2);
-+  enum {  // initial annotation layout
-+    atype_off = 0,      // utf8 such as 'Ljava/lang/annotation/Retention;'
-+    count_off = 2,      // u2   such as 1 (one value)
-+    member_off = 4,     // utf8 such as 'value'
-+    tag_off = 6,        // u1   such as 'c' (type) or 'e' (enum)
-+    e_tag_val = 'e',
-+      e_type_off = 7,   // utf8 such as 'Ljava/lang/annotation/RetentionPolicy;'
-+      e_con_off = 9,    // utf8 payload, such as 'SOURCE', 'CLASS', 'RUNTIME'
-+      e_size = 11,     // end of 'e' annotation
-+    c_tag_val = 'c',
-+      c_con_off = 7,    // utf8 payload, such as 'I' or 'Ljava/lang/String;'
-+      c_size = 9,       // end of 'c' annotation
-+    min_size = 6        // smallest possible size (zero members)
-+  };
-+  while (--nann >= 0 && index-2 + min_size <= limit) {
-+    int index0 = index;
-+    index = skip_annotation(buffer, limit, index);
-+    u1* abase = buffer + index0;
-+    int atype = Bytes::get_Java_u2(abase + atype_off);
-+    int count = Bytes::get_Java_u2(abase + count_off);
-+    Symbol* aname = check_symbol_at(cp, atype);
-+    if (aname == NULL)  break;  // invalid annotation name
-+    Symbol* member = NULL;
-+    if (count >= 1) {
-+      int member_index = Bytes::get_Java_u2(abase + member_off);
-+      member = check_symbol_at(cp, member_index);
-+      if (member == NULL)  break;  // invalid member name
-+    }
-+
-+    // Here is where parsing particular annotations will take place.
-+    AnnotationCollector::ID id = coll->annotation_index(aname);
-+    if (id == AnnotationCollector::_unknown)  continue;
-+    coll->set_annotation(id);
-+    // If there are no values, just set the bit and move on:
-+    if (count == 0)   continue;
-+
-+#if 0
-+    // The parsing of @Retention is for example only.
-+    if (id == AnnotationCollector::_class_Retention) {
-+      Symbol* payload = NULL;
-+      if (count == 1
-+          && e_size == (index0 - index)  // match size
-+          && e_tag_val == *(abase + tag_off)
-+          && (check_symbol_at(cp, Bytes::get_Java_u2(abase + e_type_off))
-+              == vmSymbols::RetentionPolicy_signature())
-+          && member == vmSymbols::value_name()) {
-+        payload = check_symbol_at(cp, Bytes::get_Java_u2(abase + e_con_off));
-+      }
-+      check_property(payload != NULL,
-+                     "Invalid @Retention annotation at offset %u in class file %s",
-+                     index0, CHECK);
-+      if (payload != NULL) {
-+          payload->increment_refcount();
-+          coll->_class_RetentionPolicy = payload;
-+      }
-+    }
-+#endif //0
-+  }
-+}
-+
-+ClassFileParser::AnnotationCollector::ID ClassFileParser::AnnotationCollector::annotation_index(Symbol* name) {
-+  vmSymbols::SID sid = vmSymbols::find_sid(name);
-+  switch (sid) {
-+  default: break;
-+  }
-+  return AnnotationCollector::_unknown;
-+}
-+
-+void ClassFileParser::FieldAnnotationCollector::apply_to(FieldInfo* f) {
-+  assert(false, "");
-+}
-+
-+void ClassFileParser::MethodAnnotationCollector::apply_to(methodHandle m) {
-+  assert(false, "");
-+}
-+
-+void ClassFileParser::ClassAnnotationCollector::apply_to(instanceKlassHandle k) {
-+  assert(false, "");
-+}
-+
-+
- #define MAX_ARGS_SIZE 255
- #define MAX_CODE_SIZE 65535
- #define INITIAL_MAX_LVT_NUMBER 256
- 
- // Note: the parse_method below is big and clunky because all parsing of the code and exceptions
--// attribute is inlined. This is curbersome to avoid since we inline most of the parts in the
-+// attribute is inlined. This is cumbersome to avoid since we inline most of the parts in the
- // methodOop to save footprint, so we only know the size of the resulting methodOop when the
- // entire method attribute is parsed.
- //
-@@ -1695,6 +1850,7 @@
-   // stackmap attribute - JDK1.5
-   typeArrayHandle stackmap_data;
-   u2 generic_signature_index = 0;
-+  MethodAnnotationCollector parsed_annotations;
-   u1* runtime_visible_annotations = NULL;
-   int runtime_visible_annotations_length = 0;
-   u1* runtime_invisible_annotations = NULL;
-@@ -1921,6 +2077,7 @@
-         runtime_visible_annotations_length = method_attribute_length;
-         runtime_visible_annotations = cfs->get_u1_buffer();
-         assert(runtime_visible_annotations != NULL, "null visible annotations");
-+        parse_annotations(runtime_visible_annotations, runtime_visible_annotations_length, cp, &parsed_annotations, CHECK_(nullHandle));
-         cfs->skip_u1(runtime_visible_annotations_length, CHECK_(nullHandle));
-       } else if (PreserveAllAnnotations && method_attribute_name == vmSymbols::tag_runtime_invisible_annotations()) {
-         runtime_invisible_annotations_length = method_attribute_length;
-@@ -2098,6 +2255,8 @@
-     clear_hashtable(lvt_Hash);
-   }
- 
-+  if (parsed_annotations.has_any_annotations())
-+    parsed_annotations.apply_to(m);
-   *method_annotations = assemble_annotations(runtime_visible_annotations,
-                                              runtime_visible_annotations_length,
-                                              runtime_invisible_annotations,
-@@ -2276,7 +2435,7 @@
- }
- 
- 
--void ClassFileParser::parse_classfile_sourcefile_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS) {
-+void ClassFileParser::parse_classfile_sourcefile_attribute(constantPoolHandle cp, Symbol** sourcefile_ret, TRAPS) {
-   ClassFileStream* cfs = stream();
-   cfs->guarantee_more(2, CHECK);  // sourcefile_index
-   u2 sourcefile_index = cfs->get_u2_fast();
-@@ -2285,14 +2444,16 @@
-       cp->tag_at(sourcefile_index).is_utf8(),
-     "Invalid SourceFile attribute at constant pool index %u in class file %s",
-     sourcefile_index, CHECK);
--  k->set_source_file_name(cp->symbol_at(sourcefile_index));
-+  (*sourcefile_ret) = cp->symbol_at(sourcefile_index);
-+  (*sourcefile_ret)->increment_refcount();
- }
- 
- 
- 
- void ClassFileParser::parse_classfile_source_debug_extension_attribute(constantPoolHandle cp,
--                                                                       instanceKlassHandle k,
--                                                                       int length, TRAPS) {
-+                                                                       int length,
-+                                                                       TempNewSymbol* sde_symbol_ret,
-+                                                                       TRAPS) {
-   ClassFileStream* cfs = stream();
-   u1* sde_buffer = cfs->get_u1_buffer();
-   assert(sde_buffer != NULL, "null sde buffer");
-@@ -2301,8 +2462,7 @@
-   if (JvmtiExport::can_get_source_debug_extension()) {
-     // Optimistically assume that only 1 byte UTF format is used
-     // (common case)
--    TempNewSymbol sde_symbol = SymbolTable::new_symbol((const char*)sde_buffer, length, CHECK);
--    k->set_source_debug_extension(sde_symbol);
-+    (*sde_symbol_ret) = SymbolTable::new_symbol((const char*)sde_buffer, length, CHECK);
-     // Note that set_source_debug_extension() increments the reference count
-     // for its copy of the Symbol*, so use a TempNewSymbol here.
-   }
-@@ -2320,7 +2480,7 @@
-                                                             u2 enclosing_method_class_index,
-                                                             u2 enclosing_method_method_index,
-                                                             constantPoolHandle cp,
--                                                            instanceKlassHandle k, TRAPS) {
-+                                                            typeArrayHandle* inner_classes_ret, TRAPS) {
-   ClassFileStream* cfs = stream();
-   u1* current_mark = cfs->current();
-   u2 length = 0;
-@@ -2411,7 +2571,7 @@
-   assert(index == size, "wrong size");
- 
-   // Update instanceKlass with inner class info.
--  k->set_inner_classes(inner_classes());
-+  (*inner_classes_ret) = inner_classes;
- 
-   // Restore buffer's current position.
-   cfs->set_current(current_mark);
-@@ -2419,11 +2579,11 @@
-   return length;
- }
- 
--void ClassFileParser::parse_classfile_synthetic_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS) {
--  k->set_is_synthetic();
-+void ClassFileParser::parse_classfile_synthetic_attribute(constantPoolHandle cp, bool* synthetic_flag_ret, TRAPS) {
-+  (*synthetic_flag_ret) = true;
- }
- 
--void ClassFileParser::parse_classfile_signature_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS) {
-+void ClassFileParser::parse_classfile_signature_attribute(constantPoolHandle cp, Symbol** signature_ret, TRAPS) {
-   ClassFileStream* cfs = stream();
-   u2 signature_index = cfs->get_u2(CHECK);
-   check_property(
-@@ -2431,10 +2591,11 @@
-       cp->tag_at(signature_index).is_utf8(),
-     "Invalid constant pool index %u in Signature attribute in class file %s",
-     signature_index, CHECK);
--  k->set_generic_signature(cp->symbol_at(signature_index));
-+  (*signature_ret) = cp->symbol_at(signature_index);
-+  (*signature_ret)->increment_refcount();
- }
- 
--void ClassFileParser::parse_classfile_bootstrap_methods_attribute(constantPoolHandle cp, instanceKlassHandle k,
-+void ClassFileParser::parse_classfile_bootstrap_methods_attribute(constantPoolHandle cp,
-                                                                   u4 attribute_byte_length, TRAPS) {
-   ClassFileStream* cfs = stream();
-   u1* current_start = cfs->current();
-@@ -2506,10 +2667,12 @@
- }
- 
- 
--void ClassFileParser::parse_classfile_attributes(constantPoolHandle cp, instanceKlassHandle k, TRAPS) {
-+void ClassFileParser::parse_classfile_attributes(constantPoolHandle cp,
-+                                                 ClassFileParser::ClassAnnotationCollector* parsed_annotations,
-+                                                 TRAPS) {
-   ClassFileStream* cfs = stream();
-   // Set inner classes attribute to default sentinel
--  k->set_inner_classes(Universe::the_empty_short_array());
-+  _inner_classes = typeArrayHandle(THREAD, Universe::the_empty_short_array());
-   cfs->guarantee_more(2, CHECK);  // attributes_count
-   u2 attributes_count = cfs->get_u2_fast();
-   bool parsed_sourcefile_attribute = false;
-@@ -2524,6 +2687,7 @@
-   u4  inner_classes_attribute_length = 0;
-   u2  enclosing_method_class_index = 0;
-   u2  enclosing_method_method_index = 0;
-+  TempNewSymbol sde_symbol = NULL;
-   // Iterate over attributes
-   while (attributes_count--) {
-     cfs->guarantee_more(6, CHECK);  // attribute_name_index, attribute_length
-@@ -2545,10 +2709,10 @@
-       } else {
-         parsed_sourcefile_attribute = true;
-       }
--      parse_classfile_sourcefile_attribute(cp, k, CHECK);
-+      parse_classfile_sourcefile_attribute(cp, &_sourcefile, CHECK);
-     } else if (tag == vmSymbols::tag_source_debug_extension()) {
-       // Check for SourceDebugExtension tag
--      parse_classfile_source_debug_extension_attribute(cp, k, (int)attribute_length, CHECK);
-+      parse_classfile_source_debug_extension_attribute(cp, (int)attribute_length, &_sde_symbol, CHECK);
-     } else if (tag == vmSymbols::tag_inner_classes()) {
-       // Check for InnerClasses tag
-       if (parsed_innerclasses_attribute) {
-@@ -2567,7 +2731,7 @@
-           "Invalid Synthetic classfile attribute length %u in class file %s",
-           attribute_length, CHECK);
-       }
--      parse_classfile_synthetic_attribute(cp, k, CHECK);
-+      parse_classfile_synthetic_attribute(cp, &_synthetic_flag, CHECK);
-     } else if (tag == vmSymbols::tag_deprecated()) {
-       // Check for Deprecatd tag - 4276120
-       if (attribute_length != 0) {
-@@ -2582,11 +2746,16 @@
-             "Wrong Signature attribute length %u in class file %s",
-             attribute_length, CHECK);
-         }
--        parse_classfile_signature_attribute(cp, k, CHECK);
-+        parse_classfile_signature_attribute(cp, &_generic_signature, CHECK);
-       } else if (tag == vmSymbols::tag_runtime_visible_annotations()) {
-         runtime_visible_annotations_length = attribute_length;
-         runtime_visible_annotations = cfs->get_u1_buffer();
-         assert(runtime_visible_annotations != NULL, "null visible annotations");
-+        parse_annotations(runtime_visible_annotations,
-+                          runtime_visible_annotations_length,
-+                          cp,
-+                          parsed_annotations,
-+                          CHECK);
-         cfs->skip_u1(runtime_visible_annotations_length, CHECK);
-       } else if (PreserveAllAnnotations && tag == vmSymbols::tag_runtime_invisible_annotations()) {
-         runtime_invisible_annotations_length = attribute_length;
-@@ -2620,7 +2789,7 @@
-         if (parsed_bootstrap_methods_attribute)
-           classfile_parse_error("Multiple BootstrapMethods attributes in class file %s", CHECK);
-         parsed_bootstrap_methods_attribute = true;
--        parse_classfile_bootstrap_methods_attribute(cp, k, attribute_length, CHECK);
-+        parse_classfile_bootstrap_methods_attribute(cp, attribute_length, CHECK);
-       } else {
-         // Unknown attribute
-         cfs->skip_u1(attribute_length, CHECK);
-@@ -2635,7 +2804,7 @@
-                                                      runtime_invisible_annotations,
-                                                      runtime_invisible_annotations_length,
-                                                      CHECK);
--  k->set_class_annotations(annotations());
-+  _annotations = annotations;
- 
-   if (parsed_innerclasses_attribute || parsed_enclosingmethod_attribute) {
-     u2 num_of_classes = parse_classfile_inner_classes_attribute(
-@@ -2643,7 +2812,7 @@
-                             parsed_innerclasses_attribute,
-                             enclosing_method_class_index,
-                             enclosing_method_method_index,
--                            cp, k, CHECK);
-+                            cp, &_inner_classes, CHECK);
-     if (parsed_innerclasses_attribute &&_need_verify && _major_version >= JAVA_1_5_VERSION) {
-       guarantee_property(
-         inner_classes_attribute_length == sizeof(num_of_classes) + 4 * sizeof(u2) * num_of_classes,
-@@ -2710,6 +2879,12 @@
-   _has_finalizer = _has_empty_finalizer = _has_vanilla_constructor = false;
-   _max_bootstrap_specifier_index = -1;
- 
-+  _synthetic_flag = false;
-+
-+  _sourcefile = NULL;
-+  _generic_signature = NULL;
-+  _sde_symbol = NULL;
-+
-   if (JvmtiExport::should_post_class_file_load_hook()) {
-     // Get the cached class file bytes (if any) from the class that
-     // is being redefined or retransformed. We use jvmti_thread_state()
-@@ -2941,6 +3116,13 @@
-     objArrayHandle methods_parameter_annotations(THREAD, methods_parameter_annotations_oop);
-     objArrayHandle methods_default_annotations(THREAD, methods_default_annotations_oop);
- 
-+    // Additional attributes
-+    ClassAnnotationCollector parsed_annotations;
-+    parse_classfile_attributes(cp, &parsed_annotations, CHECK_(nullHandle));
-+
-+    // Make sure this is the end of class file stream
-+    guarantee_property(cfs->at_eos(), "Extra bytes at the end of class file %s", CHECK_(nullHandle));
-+
-     // We check super class after class file is parsed and format is checked
-     if (super_class_index > 0 && super_klass.is_null()) {
-       Symbol*  sk  = cp->klass_name_at(super_class_index);
-@@ -3428,11 +3610,15 @@
-       this_klass->set_has_miranda_methods(); // then set a flag
-     }
- 
--    // Additional attributes
--    parse_classfile_attributes(cp, this_klass, CHECK_(nullHandle));
--
--    // Make sure this is the end of class file stream
--    guarantee_property(cfs->at_eos(), "Extra bytes at the end of class file %s", CHECK_(nullHandle));
-+    // Fill in field values from parse_classfile_attributes:
-+    this_klass->set_inner_classes(_inner_classes());
-+    this_klass->set_source_file_name(_sourcefile);
-+    this_klass->set_source_debug_extension(_sde_symbol);
-+    this_klass->set_generic_signature(_generic_signature);
-+    if (_synthetic_flag)  this_klass->set_is_synthetic();
-+    if (parsed_annotations.has_any_annotations())
-+      parsed_annotations.apply_to(this_klass);
-+    this_klass->set_class_annotations(_annotations());
- 
-     // VerifyOops believes that once this has been set, the object is completely loaded.
-     // Compute transitive closure of interfaces this class implements
-diff --git a/src/share/vm/classfile/classFileParser.hpp b/src/share/vm/classfile/classFileParser.hpp
---- a/src/share/vm/classfile/classFileParser.hpp
-+++ b/src/share/vm/classfile/classFileParser.hpp
-@@ -31,8 +31,8 @@
- #include "oops/typeArrayOop.hpp"
- #include "runtime/handles.inline.hpp"
- #include "utilities/accessFlags.hpp"
-+#include "classfile/symbolTable.hpp"
- 
--class TempNewSymbol;
- class FieldAllocationCount;
- 
- 
-@@ -54,6 +54,53 @@
-   bool _has_empty_finalizer;
-   bool _has_vanilla_constructor;
- 
-+  // class attributes parsed before the instance klass is created:
-+  bool       _synthetic_flag;
-+  Symbol*    _sourcefile;
-+  Symbol*    _generic_signature;
-+  TempNewSymbol   _sde_symbol;
-+  typeArrayHandle _inner_classes;
-+  typeArrayHandle _annotations;
-+
-+  class AnnotationCollector {
-+  public:
-+    enum Location { _in_field, _in_method, _in_class };
-+    enum ID {
-+      _unknown = 0,
-+      _annotation_LIMIT
-+    };
-+    const Location _location;
-+    int _annotations_present;
-+    AnnotationCollector(Location location)
-+    : _location(location), _annotations_present(0)
-+    { }
-+    // If this annotation name has an ID, report it (or _none).
-+    ID annotation_index(Symbol* name);
-+    // Set the annotation name:
-+    void set_annotation(ID id) {
-+      assert((int)id >= 0 && (int)id < BitsPerInt, "oob");
-+      _annotations_present |= nth_bit((int)id);
-+    }
-+    // Report if the annotation is present.
-+    bool has_any_annotations() { return _annotations_present != 0; }
-+    bool has_annotation(ID id) { return (nth_bit((int)id) & _annotations_present) != 0; }
-+  };
-+  class FieldAnnotationCollector: public AnnotationCollector {
-+  public:
-+    FieldAnnotationCollector() : AnnotationCollector(_in_field) { }
-+    void apply_to(FieldInfo* f);
-+  };
-+  class MethodAnnotationCollector: public AnnotationCollector {
-+  public:
-+    MethodAnnotationCollector() : AnnotationCollector(_in_method) { }
-+    void apply_to(methodHandle m);
-+  };
-+  class ClassAnnotationCollector: public AnnotationCollector {
-+  public:
-+    ClassAnnotationCollector() : AnnotationCollector(_in_class) { }
-+    void apply_to(instanceKlassHandle k);
-+  };
-+
-   int _max_bootstrap_specifier_index;
- 
-   enum { fixed_buffer_size = 128 };
-@@ -87,7 +134,9 @@
-                               u2* constantvalue_index_addr,
-                               bool* is_synthetic_addr,
-                               u2* generic_signature_index_addr,
--                              typeArrayHandle* field_annotations, TRAPS);
-+                              typeArrayHandle* field_annotations,
-+                              FieldAnnotationCollector* parsed_annotations,
-+                              TRAPS);
-   typeArrayHandle parse_fields(Symbol* class_name,
-                                constantPoolHandle cp, bool is_interface,
-                                FieldAllocationCount *fac,
-@@ -128,25 +177,34 @@
-   typeArrayOop parse_stackmap_table(u4 code_attribute_length, TRAPS);
- 
-   // Classfile attribute parsing
--  void parse_classfile_sourcefile_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS);
--  void parse_classfile_source_debug_extension_attribute(constantPoolHandle cp,
--                                                instanceKlassHandle k, int length, TRAPS);
-+  void parse_classfile_sourcefile_attribute(constantPoolHandle cp, Symbol** sourcefile, TRAPS);
-+  void parse_classfile_source_debug_extension_attribute(constantPoolHandle cp, int length,
-+                                                        TempNewSymbol* sde_symbol_ret,
-+                                                        TRAPS);
-   u2   parse_classfile_inner_classes_attribute(u1* inner_classes_attribute_start,
-                                                bool parsed_enclosingmethod_attribute,
-                                                u2 enclosing_method_class_index,
-                                                u2 enclosing_method_method_index,
-                                                constantPoolHandle cp,
--                                               instanceKlassHandle k, TRAPS);
--  void parse_classfile_attributes(constantPoolHandle cp, instanceKlassHandle k, TRAPS);
--  void parse_classfile_synthetic_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS);
--  void parse_classfile_signature_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS);
--  void parse_classfile_bootstrap_methods_attribute(constantPoolHandle cp, instanceKlassHandle k, u4 attribute_length, TRAPS);
-+                                               typeArrayHandle* inner_classes, TRAPS);
-+  void parse_classfile_attributes(constantPoolHandle cp,
-+                                  ClassFileParser::ClassAnnotationCollector* parsed_annotations,
-+                                  TRAPS);
-+  void parse_classfile_synthetic_attribute(constantPoolHandle cp, bool* synthetic_flag, TRAPS);
-+  void parse_classfile_signature_attribute(constantPoolHandle cp, Symbol** signature, TRAPS);
-+  void parse_classfile_bootstrap_methods_attribute(constantPoolHandle cp, u4 attribute_length, TRAPS);
- 
-   // Annotations handling
-   typeArrayHandle assemble_annotations(u1* runtime_visible_annotations,
-                                        int runtime_visible_annotations_length,
-                                        u1* runtime_invisible_annotations,
-                                        int runtime_invisible_annotations_length, TRAPS);
-+  int skip_annotation(u1* buffer, int limit, int index);
-+  int skip_annotation_value(u1* buffer, int limit, int index);
-+  void parse_annotations(u1* buffer, int limit, constantPoolHandle cp,
-+                         /* Results (currently, only one result is supported): */
-+                         AnnotationCollector* result,
-+                         TRAPS);
- 
-   // Final setup
-   unsigned int compute_oop_map_count(instanceKlassHandle super,
--- a/series	Tue Jul 10 22:42:01 2012 -0700
+++ b/series	Tue Jul 10 23:31:05 2012 -0700
@@ -3,8 +3,7 @@
 # review pending before push to hotspot-comp:
 
 # non-pushed files are under review or development, or merely experimental:
-annot.patch                     #-/annot #+70862d781d01
-annot-inline.patch              #-/annot #+70862d781d01
+annot-6711908.patch             #-/annot #+70862d781d01
 meth.patch                      #-/meth #+70862d781d01
 meth-lazy-7023639.patch         #-/meth #+70862d781d01 #-testable