예제 #1
0
파일: slotsMap.cpp 프로젝트: AdamSpitz/self
oop slotsMap::copy_add_argument_slot(slotsOop obj,
                                     stringOop name, 
                                     slotType type,
                                     oop contents,
                                     oop anno,
                                     bool mustAllocate) {
  assert_smi(contents, "arg data must be position");

  if (!name->is_unary())
    return ErrorCodes::vmString_prim_error(ARGUMENTCOUNTERROR);

  slotDesc* old = find_slot(name);
  slotsOop result;
  if (old == NULL)
    result= obj;
  else if (old->is_arg_slot()) {
    // No need to remove and reinsert because order is the same.
    // Only the annotation might be really different.
    // The index will be off by one (assumes that added slot is new)
    assert(smiOop(contents)->value() == smiOop(old->data)->value() + 1,
           "arg index wrong");
    return change_slot(obj, old, type, old->data, anno, mustAllocate);
  } else {
    result= (slotsOop)copy_remove_slot(obj, name, mustAllocate);
    if (oop(result) == failedAllocationOop || result->is_mark()) return result;
    assert(result->is_slots(), "just checking");
  }
  assert(smiOop(contents)->value() == arg_count(), "arg index wrong");
  return ((slotsMap*)result->map())->copy_add_new_slot(result, 
                                                       name, 
                                                       type, 
                                                       contents,
                                                       anno,
                                                       mustAllocate);
}
예제 #2
0
PRIM_DECL_3(doubleByteArrayPrimitives::atPut, oop receiver, oop index, oop value) {
  PROLOGUE_3("atPut", receiver, index, value);
  ASSERT_RECEIVER;

  // check index type
  if (!index->is_smi())
    return markSymbol(vmSymbols::first_argument_has_wrong_type());

  // check value type
  if (!value->is_smi())
    return markSymbol(vmSymbols::second_argument_has_wrong_type());

  // check index value
  if (!doubleByteArrayOop(receiver)->is_within_bounds(smiOop(index)->value()))
     return markSymbol(vmSymbols::out_of_bounds());

  // check value as double byte
  unsigned int v = (unsigned int) smiOop(value)->value();
  if (v  >= (1<<16))
      return markSymbol(vmSymbols::value_out_of_range());

  // do the operation
  doubleByteArrayOop(receiver)->doubleByte_at_put(smiOop(index)->value(), v);
  return receiver;
}
예제 #3
0
PRIM_DECL_2(doubleByteArrayPrimitives::allocateSize, oop receiver, oop argument) {
  PROLOGUE_2("allocateSize", receiver, argument)
  assert(receiver->is_klass() && klassOop(receiver)->klass_part()->oop_is_doubleByteArray(),
         "receiver must double byte array class");
  if (!argument->is_smi())
    markSymbol(vmSymbols::first_argument_has_wrong_type());

  if (smiOop(argument)->value() < 0)
    return markSymbol(vmSymbols::negative_size());

  klassOop k        = klassOop(receiver);
  int      ni_size  = k->klass_part()->non_indexable_size();
  int      obj_size = ni_size + 1 + roundTo(smiOop(argument)->value() * 2, oopSize) / oopSize;
  // allocate
  doubleByteArrayOop obj = as_doubleByteArrayOop(Universe::allocate(obj_size, (memOop*)&k));
  // header
  memOop(obj)->initialize_header(true, k);
  // instance variables
  memOop(obj)->initialize_body(memOopDesc::header_size(), ni_size);
  // indexables
  oop* base = (oop*) obj->addr();
  oop* end  = base + obj_size;
  // %optimized 'obj->set_length(size)'
  base[ni_size] = argument;
  // %optimized 'for (int index = 1; index <= size; index++)
  //               obj->doubleByte_at_put(index, 0)'
  base = &base[ni_size+1];
  while (base < end) *base++ = (oop) 0;
  return obj;
}
예제 #4
0
PRIM_DECL_2(doubleValueArrayPrimitives::allocateSize, oop receiver, oop argument) {
  PROLOGUE_2("allocateSize", receiver, argument)
  assert(receiver->is_klass() && klassOop(receiver)->klass_part()->oop_is_doubleValueArray(),
         "receiver must double byte array class");
  if (!argument->is_smi())
    markSymbol(vmSymbols::first_argument_has_wrong_type());

  if (smiOop(argument)->value() < 0)
    return markSymbol(vmSymbols::negative_size());

  int length = smiOop(argument)->value();

  klassOop k        = klassOop(receiver);
  int      ni_size  = k->klass_part()->non_indexable_size();
  int      obj_size = ni_size + 1 + roundTo(length * sizeof(double), oopSize) / oopSize;
  // allocate
  doubleValueArrayOop obj = as_doubleValueArrayOop(Universe::allocate(obj_size, (memOop*)&k));
  // header
  memOop(obj)->initialize_header(true, k);
  // instance variables
  memOop(obj)->initialize_body(memOopDesc::header_size(), ni_size);
  obj->set_length(length);
  for (int index = 1; index <= length; index++) {
    obj->double_at_put(index, 0.0);
  }
  return obj;
}
예제 #5
0
파일: sic.cpp 프로젝트: AdamSpitz/self
 oop set_sic_params_prim(oop r, char* which, objVectorOop params, void* FH) {
   ResourceMark rm;
   IntBList* l = stringToList(which);
   if (!l) {
     failure(FH, SIC_PARAMS_ERROR_MSG);
     return 0;
   }
   fint len = params->length();
   fint *n= NEW_RESOURCE_ARRAY(fint, len);
   fint i;
   for (i = 0; i < len; i++) {
     oop param = params->obj_at(i);
     if (!param->is_smi() || smiOop(param)->value() < 1) {
       char msg[BUFSIZ];
       sprintf(msg, "arg2[%ld]: invalid parameter (not a positive integer)",
               long(i));
       failure(FH, msg);
       return 0;
     }
     n[i] = smiOop(param)->value();
   }
   oop res = get_sic_params_prim(r, which, NULL);
   l->clear();
   for (i = 0; i < len; i++) l->push(n[i]);
   return res;
 }
예제 #6
0
파일: slotsMap.cpp 프로젝트: AdamSpitz/self
slotsOop slotsMap::copy_remove_one_slot(slotsOop obj, slotDesc *slot,
                                        bool mustAllocate) {
  assert_slots(obj, "object isn't a slotsOop");
  assert(!obj->is_string(), "cannot clone strings!");
  assert(slot >= slots() && slot < slotsMap::slot(length_slots()),
         "slotDesc not part of map");

  slotsMap* new_map= (slotsMap*) remove(slot, 1, mustAllocate);
  if (new_map == NULL) return slotsOop(failedAllocationOop);
  new_map->slots_length = new_map->slots_length->decrement();
  new_map->init_dependents();
  mapOop new_moop = new_map->enclosing_mapOop();
  new_moop->init_mark();

  slotsOop new_obj;
  switch (slot->type->slot_type()) {
   case obj_slot_type:
    assert_smi(slot->data, "data slot contents isn't an offset");
    new_obj= obj->is_byteVector()
      ? (slotsOop) byteVectorOop(obj)->remove(object_size(obj),
                                              smiOop(slot->data)->value(), 
                                              1, mustAllocate, true)
      : (slotsOop) slotsOop(obj)->remove(object_size(obj),
                                         smiOop(slot->data)->value(), 
                                         1, mustAllocate, true);
    if (oop(new_obj) == failedAllocationOop)
      return slotsOop(failedAllocationOop);
    // check-stores done by remove already
    new_map->shift_obj_slots(smiOop(slot->data), -1);
    new_map->object_length = new_map->object_length->decrement();
    break;
   case arg_slot_type: {
    // fix up any arg slots after this one
    assert_smi(slot->data, "bad arg index");
    fint argIndex= smiOop(slot->data)->value();
    FOR_EACH_SLOTDESC(new_map, s) {
      if (s->is_arg_slot()) {
        assert_smi(s->data, "bad arg index");
        fint a= smiOop(s->data)->value();
        if (a > argIndex)
          s->data= as_smiOop(a - 1);
      }
    }
   }
   // fall through     
   case map_slot_type:
    new_obj= slotsOop(obj->clone(mustAllocate));
    if (oop(new_obj) == failedAllocationOop)
      return slotsOop(failedAllocationOop);
    break;
   default:
    ShouldNotReachHere(); // unexpected slot type;
  }

  new_obj->set_canonical_map(new_map);
  
  return new_obj;
}
예제 #7
0
PRIM_DECL_2(doubleByteArrayPrimitives::at, oop receiver, oop index) {
  PROLOGUE_2("at", receiver, index);
  ASSERT_RECEIVER;

  // check index type
  if (!index->is_smi())
    return markSymbol(vmSymbols::first_argument_has_wrong_type());

  // check index value
  if (!doubleByteArrayOop(receiver)->is_within_bounds(smiOop(index)->value()))
     return markSymbol(vmSymbols::out_of_bounds());

  return as_smiOop(doubleByteArrayOop(receiver)->doubleByte_at(smiOop(index)->value()));
}
예제 #8
0
 void CodeGen::assignment(Location receiver,
                          realSlotRef* path, Location val,
                          bool isMem) {
   // <move arg, t>
   // <loadPath rr, path, receiver>
   // store receiver/rr, offset - Mem_Tag, arg/t
   // <check_store>
     
   a.Comment("Begin Assignment");
   Location t;
   if (isRegister(val) && val != CReceiverReg) {
     t = val;
   } else {
     t = Temp1;
     move(t, val);    // load argument
   }
   assert(t != Temp2, "register conflict");
   int32 offset = smiOop(path->desc->data)->byte_count() - Mem_Tag;
   if (path->holder->is_object_or_map()) {
     Location t1 = loadPath(CReceiverReg, path->holder, receiver, Temp1);
     a.StoreI(t1, offset, t);    // store object data slot contents
     if (isMem) {
       a.AddI(t1, offset, Temp1);    // compute store address
       recordStore(Temp1);
     }
   } else {
     fatal("don't support vframe lookups yet");
   }
   a.Comment("End Assignment");
 }
예제 #9
0
 void CodeGen::loadOop(Location dest, Location src_register, slotDesc* s) {
   Location t = isRegister(dest) ? dest : Temp1;
   int32 offset = smiOop(s->data)->byte_count() - Mem_Tag;
   a.LoadI(src_register, offset, t);
   if (dest != t)
     move(dest, t);
 }
예제 #10
0
void CodeGen::assignment(Location receiver,
                         realSlotRef* path, Location val,
                         bool isMem) {
  a.Comment("Begin Assignment");
  // called from assignmentCode; real assignment method
  int32 offset = smiOop(path->desc->data)->byte_count() - Mem_Tag;
  if (path->holder->is_object_or_map()) {
    Location tmp = val == Temp1 ? Temp2 : Temp1;
    bool yipes = tmp == receiver;
    if (yipes) a.pushl(val);
    
    Location tr = loadPath(tmp, path->holder, receiver, tmp);
    a.leal(tr, offset, NumberOperand, tr);

    Location r; int32 d; OperandType t;
    Location other_temp = tr == Temp1 ? Temp2 : Temp1;
    if (yipes) a.popl(other_temp);
    else if (val != other_temp) {
      reg_disp_type_of_loc(&r, &d, &t, val);
      a.movl(r, d, t, other_temp);
    }
    a.movl(other_temp, tr, 0, NumberOperand);

    if (isMem) {
      recordStore(tr);
    }
  } else {
    fatal("don't support vframe lookups yet");
  }
  a.Comment("End Assignment");
}
예제 #11
0
 void SendNode::gen() {
   BasicNode::gen();
   offset = theAssembler->offset();
   assert(bci() != IllegalBCI, "should have legal bci");
   genPcDesc();
   genBreakpointBeforeCall();
   theAssembler->CallB(Memory->code->trapdoors->SendMessage_stub_td());
   theAssembler->Nop();
   theAssembler->Data(mask());
   nlrCode();
   theAssembler->Zero();       // nmlns
   theAssembler->Zero();
   if (sel != badOop) {
     if (isPerformLookupType(l)) {
       assert_smi(sel, "should be an integer argcount");
       theAssembler->Data(smiOop(sel)->value());       // really arg count
     } else {
       assert_string(sel, "should be a string constant");
       theAssembler->Data(sel);                        // constant selector
     }
   }
   if ((l & UninlinableSendMask) == 0) theSIC->noInlinableSends = false;
   theAssembler->Data(l);
   verifySendInfo();
   if (del) {
     assert(needsDelegatee(l), "shouldn't have a delegatee");
     theAssembler->Data(del);
   }
 }
예제 #12
0
파일: nodeGen.cpp 프로젝트: ardeujho/self
  Node* NodeGen::testNLR(smi homeID) {
    // test if NLR has reached home; the node returned is the success
    // branch (i.e. the home has been reached), current is the other
    // branch
    Node* homeIDTest = NULL;
    if (homeID) {       // note: will be 0 if no inlining
      if (isImmediate(smiOop(homeID))) {
        APPEND(new ArithRCNode(SubCCArithOp, nlrHomeIDPR, homeID, noPR));
      } else {
        APPEND(new LoadIntNode(homeID, nlrTempPR));
        APPEND(new ArithRRNode(SubCCArithOp, nlrHomeIDPR, nlrTempPR, noPR));
      }
      homeIDTest = APPEND(new BranchNode(EQBranchOp));
      APPEND1(new ArithRRNode(SubCCArithOp, nlrHomePR, framePR, noPR));
    } else {
      APPEND (new ArithRRNode(SubCCArithOp, nlrHomePR, framePR, noPR));
    }
    Node* homeFrameTest = APPEND(new BranchNode(EQBranchOp));

    // home & homeID match
    Node* finalReturn = new NopNode;
    APPEND1(finalReturn);

    // no match, continue NLR
    Node* cont = new MergeNode("testNLR cont"); 
    if (homeIDTest) homeIDTest->append(cont);
    homeFrameTest->append(cont);
    current = cont;
    return finalReturn;
  }
예제 #13
0
Label* CodeGen::SendDesc(RegisterState* s, LookupType lookupType,
                         oop selector, oop delegatee) {
  a.Comment("begin SendDesc");
  Label past_send_desc(a.printing);
  a.jmp(&past_send_desc);
  s->genMask();                               // mask of used regs
  Label* l = new Label(a.printing);
  a.jmp(l);                      // non-local return code
  assert((a.offset() & Tag_Mask) == 0, "must be aligned");
  a.Zero();   // nmlns
  a.Zero();
  if (selector != badOop) {
    if (isPerformLookupType(lookupType)) {
      assert_smi(selector, "should be an integer argcount");
      a.Data(smiOop(selector)->value(), true);      // really arg count
    } else {
      assert_string(selector, "should be a string constant");
      a.Data(selector, true);                       // constant selector
    }
  }
  
#   ifdef SIC_COMPILER
  if (theCompiler->containsLoop) {
    // need counters for the sends to know how often the loop executes
    a.Data(withCountBits(lookupType, Counting), true);
  } 
  else {
    a.Data(lookupType, true);
  }
#   else
    a.Data(lookupType, true);
#   endif
  
#   if GENERATE_DEBUGGING_AIDS
  if (CheckAssertions)
    switch (lookupType) {
     case DirectedResendLookupType:
      assert(lookupType & DelegateeStaticBit, "should have static delegatee");
      assert_string(delegatee, "should be a string");
      // fall through
     case ImplicitSelfLookupType:
     case ResendLookupType:
     case StaticNormalLookupType:
     case NormalLookupType:
      assert(!isPerformLookupType(lookupType),
             "should have a static selector");
      assert_string(selector, "should be a string");
      break;
     default: break;
    }
#   endif
  if (delegatee != badOop) {
    assert(needsDelegatee(lookupType), "shouldn't have a delegatee");
    a.Data(delegatee, true);
  }
  past_send_desc.define();
  a.Comment("end SendDesc");
  return l;
}
예제 #14
0
파일: nodeGen.cpp 프로젝트: ardeujho/self
 void NodeGen::pathLookup(realSlotRef* path, PReg* receiver, PReg* dest) {
   if (path->holder->is_object_or_map()) {
     PReg* base = loadPath(path->holder, receiver, dest);
     fint offset = smiOop(path->desc->data)->byte_count() - Mem_Tag;
     APPEND(new LoadOffsetNode(base, offset, dest));
   } else {
     fatal("don't support vframe lookups");
   }
 }
예제 #15
0
oop objVectorOopClass::ov_at_put_prim(oop rcvr, oop indexOop, oop contents) {
  if (!rcvr->is_objVector()) return ErrorCodes::vmString_prim_error(BADTYPEERROR);
  if (!indexOop->is_smi()) return ErrorCodes::vmString_prim_error(BADTYPEERROR);
  smi index = smiOop(indexOop)->value();
  if (unsigned(index) >= unsigned(objVectorOop(rcvr)->length()))
    return ErrorCodes::vmString_prim_error(BADINDEXERROR);
  objVectorOop(rcvr)->obj_at_put(index, contents);
  return rcvr;
}
예제 #16
0
파일: smiMap.cpp 프로젝트: AdamSpitz/self
void smiMap::print(oop obj) {
  if (obj->is_map()) {
    lprintf("smi ");
  } else {
    smiOop(obj)->print_oop();
    lprintf(": ");
  }
  immediateMap::print(obj);
}
예제 #17
0
void CodeGen::loadOop(Location dest, Location src, slotDesc* s) {
  a.Comment("loadOop1");
  int32 offset = smiOop(s->data)->byte_count() - Mem_Tag;
  Location t  = isRegister(src)  ? src  :  dest != Temp1 ? Temp1 : Temp2;
  Location tt = isRegister(dest) ? dest :  src  != Temp1 ? Temp1 : Temp2;
  move(t, src);
  a.movl(t, offset, NumberOperand, tt);
  move(dest, tt);
}
예제 #18
0
void slot_info::init(oop node_pt, char* selector) {
  // Check if node_pt has data_slot selector and save offset in _offset.
  stringOop sel = Memory->string_table->lookup(selector, strlen(selector));
  slotDesc* sd = node_pt->find_slot(sel);
  if (sd && sd->type->is_obj_slot()) {
    _offset = smiOop(sd->data)->value();
  } else {
    _offset = invalid_offset;
  }
}
예제 #19
0
extern "C" oop* setup_deoptimization_and_return_new_sp(oop* old_sp, int* old_fp, objArrayOop frame_array, int* current_frame) {
  ResourceMark rm;

  // Save all parameters for later use (check unpack_frame_array)
  ::old_sp      = old_sp;
  ::old_fp      = old_fp;
  ::frame_array = frame_array;
  ::cur_fp      = current_frame;

  smiOop number_of_vframes = smiOop(frame_array->obj_at(StackChunkBuilder::number_of_vframes_index));
  smiOop number_of_locals  = smiOop(frame_array->obj_at(StackChunkBuilder::number_of_locals_index));

  assert(number_of_vframes->is_smi(), "must be smi");
  assert(number_of_locals->is_smi(), "must be smi");

  new_sp = old_sp - frame::interpreter_stack_size(number_of_vframes->value(),
	                                          number_of_locals->value());
  return new_sp;
}
예제 #20
0
PRIM_DECL_3(doubleValueArrayPrimitives::atPut, oop receiver, oop index, oop value) {
  PROLOGUE_3("atPut", receiver, index, value);
  ASSERT_RECEIVER;

  // check index type
  if (!index->is_smi())
    return markSymbol(vmSymbols::first_argument_has_wrong_type());

  // check value type
  if (!value->is_double())
    return markSymbol(vmSymbols::second_argument_has_wrong_type());

  // check index value
  if (!doubleValueArrayOop(receiver)->is_within_bounds(smiOop(index)->value()))
     return markSymbol(vmSymbols::out_of_bounds());

  // do the operation
  doubleValueArrayOop(receiver)->double_at_put(smiOop(index)->value(), doubleOop(value)->value());
  return receiver;
}
예제 #21
0
 void SICGenHelper::loadImmediateOop(oop p, Location dest, bool isInt) {
   assert(isRegister(dest), "must be a register");
   if (p == 0) {
     a->OrR(G0, G0, dest);
   } else if ((isInt || !p->is_mem()) && isImmediate(smiOop(p))) {
     a->OrI(G0, (int)p, dest);
   } else {
     a->SetHiO(p, dest);                       // load high part of value
     a->AddO(dest, p, dest);                   // add low part 
   }
 }
예제 #22
0
PRIM_DECL_2(doubleByteArrayPrimitives::characterAt, oop receiver, oop index) {
  PROLOGUE_2("characterAt", receiver, index);
  ASSERT_RECEIVER;

  // check index type
  if (!index->is_smi()) 
    return markSymbol(vmSymbols::first_argument_has_wrong_type());

  // range check
  if (!doubleByteArrayOop(receiver)->is_within_bounds(smiOop(index)->value()))
    return markSymbol(vmSymbols::out_of_bounds());

  // fetch double byte
  doubleByte byte = doubleByteArrayOop(receiver)->doubleByte_at(smiOop(index)->value());
 
  if (byte < 256) {
    // return the byte+1'th element in asciiCharacter
    return Universe::asciiCharacters()->obj_at(byte+1);
  } else return markSymbol(vmSymbols::out_of_bounds());
}
예제 #23
0
void WeakArrayRegister::follow_contents() {
  for(int index = 0; index < weakArrays->length(); index++) {
    weakArrayOop w = weakArrays->at(index);
    int non_indexable_size = nis->at(index);
    bool encounted_near_death_objects = false;
    int length = smiOop(w->raw_at(non_indexable_size))->value();
    for(int i = 1; i <= length; i++) {
      MarkSweep::reverse_and_follow(w->oops(non_indexable_size+i));
    }
  }
}
예제 #24
0
파일: blockOop.cpp 프로젝트: ardeujho/self
void blockOopClass::setScope(frame* newScope) {
  blockOopClass *b= addr();
  frame* f= b->homeFr();
  if (NLRSupport::is_bad_home_reference((char*)f)) {
    // prototype block or non-LIFO block
    if (newScope != NULL)
      ShouldNotReachHere(); // shouldn't try to set scope pointer
  } else {
    assert_smi(newScope, "should be a word-aligned pointer");
    b->setHomeFr(smiOop(newScope));
  }
}
예제 #25
0
파일: smiOop.cpp 프로젝트: ardeujho/self
oop smi_mod_prim(smiOop rcvr,  smiOop arg) {
  if (!rcvr->is_smi())   return ErrorCodes::vmString_prim_error(BADTYPEERROR);
  if (! arg->is_smi())   return ErrorCodes::vmString_prim_error(BADTYPEERROR);
  smi r = rcvr->value();
  smi a = arg->value();
  smi aa = a >= 0  ?  a  :  -a;
  if (a == 0) return ErrorCodes::vmString_prim_error(DIVISIONBYZEROERROR);
  int32 res = r % a;
  assert( smiOop(smi_div_prim(rcvr, arg))->value() * a   +  res  ==  r,
          "smi_mod_prim incorrect on this platform");
  return as_smiOop(res);
}
예제 #26
0
PRIM_DECL_2(behaviorPrimitives::classVariableAt, oop behavior, oop index) {
  PROLOGUE_2("classVariableAt", behavior, index);
  if (!behavior->is_klass())
    return markSymbol(vmSymbols::first_argument_has_wrong_type());
  if (!index->is_smi())
    return markSymbol(vmSymbols::second_argument_has_wrong_type());

  int i = smiOop(index)->value();
  if (i > 0 && i <= klassOop(behavior)->klass_part()->number_of_classVars())
    return klassOop(behavior)->klass_part()->classVar_at(i);
  return markSymbol(vmSymbols::out_of_bounds());
}
예제 #27
0
bool CompiledLoop::isIncrement(PReg* p, ArithOpCode op) {
  // is p a suitable increment (i.e., a positive constant or loop-invariant variable)?
  _increment = p;
  if (p->isConstPReg()) {
    oop c = ((ConstPReg*)p)->constant;
    if (!c->is_smi()) return false;
    _isCountingUp = (smiOop(c)->value() > 0) ^ (op == tSubArithOp);
    return true;
  } else {
    // fix this: need to check sign in loop header
    return defsInLoop(p) == 0;
  }
}
예제 #28
0
int32* objVectorOopClass::convertIntArray() {
  oop*   src    = objs();
  oop*   end    = src + length();
  int32* result = NEW_RESOURCE_ARRAY( int32, length());
  int32* dst    = result;
  while (src < end) {
    oop s = *src++;
    if (!s->is_smi())
      return NULL;
    *dst++ = smiOop(s)->value();
  }
  return result;
}
예제 #29
0
Expr* PrimInliner::smi_Mod(Expr* x, Expr* y) {
  if (y->preg()->isConstPReg()) {
    assert(y->is_smi(), "type check should have failed");
    int d = smiOop(((ConstPReg*)y->preg())->constant)->value();
    if (is_power_of_2(d)) {
      // replace it with mask
      ConstPReg* preg = new_ConstPReg(_scope, as_smiOop(d-1));
      return smi_BitOp(tAndArithOp, x, new ConstantExpr(preg->constant, preg, _gen->_current));
    }
  }
  // otherwise leave it alone
  return NULL;
}
예제 #30
0
void CodeGen::assignment(Location receiver, slotDesc* s, Location val) {
  // this one called for impl self, arg on stack
  a.Comment("Begin Simple Assignment");
  assert(!isRegister(receiver) && !isRegister(val), 
    "called from genReceiverDataAccess, rcvr is self, val is arg or local, check this so I can use Temp[12]");
  move(Temp2, receiver);
  int32 offset = smiOop(s->data)->byte_count() - Mem_Tag;
  a.leal(Temp2, offset, NumberOperand, Temp2); // store object data slot contents
  move(Temp1, val);
  a.movl(Temp1, Temp2, 0, NumberOperand); // store object data slot contents
  recordStore(Temp2); // NB: recordStore will clobber Temp2 till I put in ByteMapBaseReg
  a.Comment("End Simple Assignment");
}