void Parse::do_put_xxx(Node* obj, ciField* field, bool is_field) {
  bool is_vol = field->is_volatile();
  // If reference is volatile, prevent following memory ops from
  // floating down past the volatile write.  Also prevents commoning
  // another volatile read.
  if (is_vol)  insert_mem_bar(Op_MemBarRelease);

  // Compute address and memory type.
  int offset = field->offset_in_bytes();
  const TypePtr* adr_type = C->alias_type(field)->adr_type();
  Node* adr = basic_plus_adr(obj, obj, offset);
  BasicType bt = field->layout_type();
  // Value to be stored
  Node* val = type2size[bt] == 1 ? pop() : pop_pair();
  // Round doubles before storing
  if (bt == T_DOUBLE)  val = dstore_rounding(val);

  // Store the value.
  Node* store;
  if (bt == T_OBJECT) {
    const TypeOopPtr* field_type;
    if (!field->type()->is_loaded()) {
      field_type = TypeInstPtr::BOTTOM;
    } else {
      field_type = TypeOopPtr::make_from_klass(field->type()->as_klass());
    }
    store = store_oop_to_object( control(), obj, adr, adr_type, val, field_type, bt);
  } else {
    store = store_to_memory( control(), adr, val, bt, adr_type, is_vol );
  }

  // If reference is volatile, prevent following volatiles ops from
  // floating up before the volatile write.
  if (is_vol) {
    // First place the specific membar for THIS volatile index. This first
    // membar is dependent on the store, keeping any other membars generated
    // below from floating up past the store.
    int adr_idx = C->get_alias_index(adr_type);
    insert_mem_bar_volatile(Op_MemBarVolatile, adr_idx, store);

    // Now place a membar for AliasIdxBot for the unknown yet-to-be-parsed
    // volatile alias indices. Skip this if the membar is redundant.
    if (adr_idx != Compile::AliasIdxBot) {
      insert_mem_bar_volatile(Op_MemBarVolatile, Compile::AliasIdxBot, store);
    }

    // Finally, place alias-index-specific membars for each volatile index
    // that isn't the adr_idx membar. Typically there's only 1 or 2.
    for( int i = Compile::AliasIdxRaw; i < C->num_alias_types(); i++ ) {
      if (i != adr_idx && C->alias_type(i)->is_volatile()) {
        insert_mem_bar_volatile(Op_MemBarVolatile, i, store);
      }
    }
  }

  // If the field is final, the rules of Java say we are in <init> or <clinit>.
  // Note the presence of writes to final non-static fields, so that we
  // can insert a memory barrier later on to keep the writes from floating
  // out of the constructor.
  if (is_field && field->is_final()) {
    set_wrote_final(true);
  }
}
Example #2
0
 Node* pop_node(BasicType n_type) {
   int n_size = type2size[n_type];
   if      (n_size == 1)  return pop();
   else if (n_size == 2)  return pop_pair();
   else                   return NULL;
 }