4139
4140 int restore_offset;
4141 if (offset == -1) {
4142 restore_offset = restore_size - gp_reg_size;
4143 } else {
4144 restore_offset = offset + restore_size - gp_reg_size;
4145 }
4146 for (ReverseRegSetIterator<Register> it = set.rbegin(); *it != noreg; ++it) {
4147 movptr(*it, Address(rsp, restore_offset));
4148 restore_offset -= gp_reg_size;
4149 }
4150
4151 if (offset == -1) {
4152 addptr(rsp, aligned_size);
4153 }
4154 }
4155
4156 // Preserves the contents of address, destroys the contents length_in_bytes and temp.
4157 void MacroAssembler::zero_memory(Register address, Register length_in_bytes, int offset_in_bytes, Register temp) {
4158 assert(address != length_in_bytes && address != temp && temp != length_in_bytes, "registers must be different");
4159 assert((offset_in_bytes & (BytesPerWord - 1)) == 0, "offset must be a multiple of BytesPerWord");
4160 Label done;
4161
4162 testptr(length_in_bytes, length_in_bytes);
4163 jcc(Assembler::zero, done);
4164
4165 // initialize topmost word, divide index by 2, check if odd and test if zero
4166 // note: for the remaining code to work, index must be a multiple of BytesPerWord
4167 #ifdef ASSERT
4168 {
4169 Label L;
4170 testptr(length_in_bytes, BytesPerWord - 1);
4171 jcc(Assembler::zero, L);
4172 stop("length must be a multiple of BytesPerWord");
4173 bind(L);
4174 }
4175 #endif
4176 Register index = length_in_bytes;
4177 xorptr(temp, temp); // use _zero reg to clear memory (shorter code)
4178 if (UseIncDec) {
4179 shrptr(index, 3); // divide by 8/16 and set carry flag if bit 2 was set
4180 } else {
4181 shrptr(index, 2); // use 2 instructions to avoid partial flag stall
4182 shrptr(index, 1);
4183 }
4184 #ifndef _LP64
4185 // index could have not been a multiple of 8 (i.e., bit 2 was set)
4186 {
4187 Label even;
4188 // note: if index was a multiple of 8, then it cannot
4189 // be 0 now otherwise it must have been 0 before
4190 // => if it is even, we don't need to check for 0 again
4191 jcc(Assembler::carryClear, even);
4192 // clear topmost word (no jump would be needed if conditional assignment worked here)
4193 movptr(Address(address, index, Address::times_8, offset_in_bytes - 0*BytesPerWord), temp);
4194 // index could be 0 now, must check again
4195 jcc(Assembler::zero, done);
4196 bind(even);
4197 }
5208
5209 void MacroAssembler::load_mirror(Register mirror, Register method, Register tmp) {
5210 // get mirror
5211 const int mirror_offset = in_bytes(Klass::java_mirror_offset());
5212 load_method_holder(mirror, method);
5213 movptr(mirror, Address(mirror, mirror_offset));
5214 resolve_oop_handle(mirror, tmp);
5215 }
5216
5217 void MacroAssembler::load_method_holder_cld(Register rresult, Register rmethod) {
5218 load_method_holder(rresult, rmethod);
5219 movptr(rresult, Address(rresult, InstanceKlass::class_loader_data_offset()));
5220 }
5221
5222 void MacroAssembler::load_method_holder(Register holder, Register method) {
5223 movptr(holder, Address(method, Method::const_offset())); // ConstMethod*
5224 movptr(holder, Address(holder, ConstMethod::constants_offset())); // ConstantPool*
5225 movptr(holder, Address(holder, ConstantPool::pool_holder_offset())); // InstanceKlass*
5226 }
5227
5228 void MacroAssembler::load_klass(Register dst, Register src, Register tmp) {
5229 assert_different_registers(src, tmp);
5230 assert_different_registers(dst, tmp);
5231 #ifdef _LP64
5232 if (UseCompressedClassPointers) {
5233 movl(dst, Address(src, oopDesc::klass_offset_in_bytes()));
5234 decode_klass_not_null(dst, tmp);
5235 } else
5236 #endif
5237 movptr(dst, Address(src, oopDesc::klass_offset_in_bytes()));
5238 }
5239
5240 void MacroAssembler::store_klass(Register dst, Register src, Register tmp) {
5241 assert_different_registers(src, tmp);
5242 assert_different_registers(dst, tmp);
5243 #ifdef _LP64
5244 if (UseCompressedClassPointers) {
5245 encode_klass_not_null(src, tmp);
5246 movl(Address(dst, oopDesc::klass_offset_in_bytes()), src);
5247 } else
5248 #endif
5249 movptr(Address(dst, oopDesc::klass_offset_in_bytes()), src);
5250 }
5251
5252 void MacroAssembler::access_load_at(BasicType type, DecoratorSet decorators, Register dst, Address src,
5253 Register tmp1, Register thread_tmp) {
5254 BarrierSetAssembler* bs = BarrierSet::barrier_set()->barrier_set_assembler();
5255 decorators = AccessInternal::decorator_fixup(decorators, type);
5256 bool as_raw = (decorators & AS_RAW) != 0;
5257 if (as_raw) {
5258 bs->BarrierSetAssembler::load_at(this, decorators, type, dst, src, tmp1, thread_tmp);
5259 } else {
5260 bs->load_at(this, decorators, type, dst, src, tmp1, thread_tmp);
5261 }
5262 }
5263
5264 void MacroAssembler::access_store_at(BasicType type, DecoratorSet decorators, Address dst, Register val,
5265 Register tmp1, Register tmp2, Register tmp3) {
5266 BarrierSetAssembler* bs = BarrierSet::barrier_set()->barrier_set_assembler();
5267 decorators = AccessInternal::decorator_fixup(decorators, type);
5268 bool as_raw = (decorators & AS_RAW) != 0;
5269 if (as_raw) {
|
4139
4140 int restore_offset;
4141 if (offset == -1) {
4142 restore_offset = restore_size - gp_reg_size;
4143 } else {
4144 restore_offset = offset + restore_size - gp_reg_size;
4145 }
4146 for (ReverseRegSetIterator<Register> it = set.rbegin(); *it != noreg; ++it) {
4147 movptr(*it, Address(rsp, restore_offset));
4148 restore_offset -= gp_reg_size;
4149 }
4150
4151 if (offset == -1) {
4152 addptr(rsp, aligned_size);
4153 }
4154 }
4155
4156 // Preserves the contents of address, destroys the contents length_in_bytes and temp.
4157 void MacroAssembler::zero_memory(Register address, Register length_in_bytes, int offset_in_bytes, Register temp) {
4158 assert(address != length_in_bytes && address != temp && temp != length_in_bytes, "registers must be different");
4159 assert((offset_in_bytes & (BytesPerInt - 1)) == 0, "offset must be a multiple of BytesPerInt");
4160 Label done;
4161
4162 testptr(length_in_bytes, length_in_bytes);
4163 jcc(Assembler::zero, done);
4164
4165 // Emit single 32bit store to clear leading bytes, if necessary.
4166 xorptr(temp, temp); // use _zero reg to clear memory (shorter code)
4167 #ifdef _LP64
4168 if (!is_aligned(offset_in_bytes, BytesPerWord)) {
4169 movl(Address(address, offset_in_bytes), temp);
4170 offset_in_bytes += BytesPerInt;
4171 decrement(length_in_bytes, BytesPerInt);
4172 }
4173 assert((offset_in_bytes & (BytesPerWord - 1)) == 0, "offset must be a multiple of BytesPerWord");
4174 testptr(length_in_bytes, length_in_bytes);
4175 jcc(Assembler::zero, done);
4176 #endif
4177
4178 // initialize topmost word, divide index by 2, check if odd and test if zero
4179 // note: for the remaining code to work, index must be a multiple of BytesPerWord
4180 #ifdef ASSERT
4181 {
4182 Label L;
4183 testptr(length_in_bytes, BytesPerWord - 1);
4184 jcc(Assembler::zero, L);
4185 stop("length must be a multiple of BytesPerWord");
4186 bind(L);
4187 }
4188 #endif
4189 Register index = length_in_bytes;
4190 if (UseIncDec) {
4191 shrptr(index, 3); // divide by 8/16 and set carry flag if bit 2 was set
4192 } else {
4193 shrptr(index, 2); // use 2 instructions to avoid partial flag stall
4194 shrptr(index, 1);
4195 }
4196 #ifndef _LP64
4197 // index could have not been a multiple of 8 (i.e., bit 2 was set)
4198 {
4199 Label even;
4200 // note: if index was a multiple of 8, then it cannot
4201 // be 0 now otherwise it must have been 0 before
4202 // => if it is even, we don't need to check for 0 again
4203 jcc(Assembler::carryClear, even);
4204 // clear topmost word (no jump would be needed if conditional assignment worked here)
4205 movptr(Address(address, index, Address::times_8, offset_in_bytes - 0*BytesPerWord), temp);
4206 // index could be 0 now, must check again
4207 jcc(Assembler::zero, done);
4208 bind(even);
4209 }
5220
5221 void MacroAssembler::load_mirror(Register mirror, Register method, Register tmp) {
5222 // get mirror
5223 const int mirror_offset = in_bytes(Klass::java_mirror_offset());
5224 load_method_holder(mirror, method);
5225 movptr(mirror, Address(mirror, mirror_offset));
5226 resolve_oop_handle(mirror, tmp);
5227 }
5228
5229 void MacroAssembler::load_method_holder_cld(Register rresult, Register rmethod) {
5230 load_method_holder(rresult, rmethod);
5231 movptr(rresult, Address(rresult, InstanceKlass::class_loader_data_offset()));
5232 }
5233
5234 void MacroAssembler::load_method_holder(Register holder, Register method) {
5235 movptr(holder, Address(method, Method::const_offset())); // ConstMethod*
5236 movptr(holder, Address(holder, ConstMethod::constants_offset())); // ConstantPool*
5237 movptr(holder, Address(holder, ConstantPool::pool_holder_offset())); // InstanceKlass*
5238 }
5239
5240 #ifdef _LP64
5241 void MacroAssembler::load_nklass(Register dst, Register src) {
5242 assert(UseCompressedClassPointers, "expect compressed class pointers");
5243
5244 if (!UseCompactObjectHeaders) {
5245 movl(dst, Address(src, oopDesc::klass_offset_in_bytes()));
5246 return;
5247 }
5248
5249 Label fast;
5250 movq(dst, Address(src, oopDesc::mark_offset_in_bytes()));
5251 testb(dst, markWord::monitor_value);
5252 jccb(Assembler::zero, fast);
5253
5254 // Fetch displaced header
5255 movq(dst, Address(dst, OM_OFFSET_NO_MONITOR_VALUE_TAG(header)));
5256
5257 bind(fast);
5258 shrq(dst, markWord::klass_shift);
5259 }
5260 #endif
5261
5262 void MacroAssembler::load_klass(Register dst, Register src, Register tmp) {
5263 assert_different_registers(src, tmp);
5264 assert_different_registers(dst, tmp);
5265 #ifdef _LP64
5266 if (UseCompressedClassPointers) {
5267 load_nklass(dst, src);
5268 decode_klass_not_null(dst, tmp);
5269 } else
5270 #endif
5271 movptr(dst, Address(src, oopDesc::klass_offset_in_bytes()));
5272 }
5273
5274 void MacroAssembler::store_klass(Register dst, Register src, Register tmp) {
5275 assert(!UseCompactObjectHeaders, "not with compact headers");
5276 assert_different_registers(src, tmp);
5277 assert_different_registers(dst, tmp);
5278 #ifdef _LP64
5279 if (UseCompressedClassPointers) {
5280 encode_klass_not_null(src, tmp);
5281 movl(Address(dst, oopDesc::klass_offset_in_bytes()), src);
5282 } else
5283 #endif
5284 movptr(Address(dst, oopDesc::klass_offset_in_bytes()), src);
5285 }
5286
5287 void MacroAssembler::cmp_klass(Register klass, Register obj, Register tmp) {
5288 #ifdef _LP64
5289 if (UseCompactObjectHeaders) {
5290 // NOTE: We need to deal with possible ObjectMonitor in object header.
5291 // Eventually we might be able to do simple movl & cmpl like in
5292 // the CCP path below.
5293 load_nklass(tmp, obj);
5294 cmpl(klass, tmp);
5295 } else if (UseCompressedClassPointers) {
5296 cmpl(klass, Address(obj, oopDesc::klass_offset_in_bytes()));
5297 } else
5298 #endif
5299 {
5300 cmpptr(klass, Address(obj, oopDesc::klass_offset_in_bytes()));
5301 }
5302 }
5303
5304 void MacroAssembler::cmp_klass(Register src, Register dst, Register tmp1, Register tmp2) {
5305 #ifdef _LP64
5306 if (UseCompactObjectHeaders) {
5307 // NOTE: We need to deal with possible ObjectMonitor in object header.
5308 // Eventually we might be able to do simple movl & cmpl like in
5309 // the CCP path below.
5310 assert(tmp2 != noreg, "need tmp2");
5311 assert_different_registers(src, dst, tmp1, tmp2);
5312 load_nklass(tmp1, src);
5313 load_nklass(tmp2, dst);
5314 cmpl(tmp1, tmp2);
5315 } else if (UseCompressedClassPointers) {
5316 movl(tmp1, Address(src, oopDesc::klass_offset_in_bytes()));
5317 cmpl(tmp1, Address(dst, oopDesc::klass_offset_in_bytes()));
5318 } else
5319 #endif
5320 {
5321 movptr(tmp1, Address(src, oopDesc::klass_offset_in_bytes()));
5322 cmpptr(tmp1, Address(dst, oopDesc::klass_offset_in_bytes()));
5323 }
5324 }
5325
5326 void MacroAssembler::access_load_at(BasicType type, DecoratorSet decorators, Register dst, Address src,
5327 Register tmp1, Register thread_tmp) {
5328 BarrierSetAssembler* bs = BarrierSet::barrier_set()->barrier_set_assembler();
5329 decorators = AccessInternal::decorator_fixup(decorators, type);
5330 bool as_raw = (decorators & AS_RAW) != 0;
5331 if (as_raw) {
5332 bs->BarrierSetAssembler::load_at(this, decorators, type, dst, src, tmp1, thread_tmp);
5333 } else {
5334 bs->load_at(this, decorators, type, dst, src, tmp1, thread_tmp);
5335 }
5336 }
5337
5338 void MacroAssembler::access_store_at(BasicType type, DecoratorSet decorators, Address dst, Register val,
5339 Register tmp1, Register tmp2, Register tmp3) {
5340 BarrierSetAssembler* bs = BarrierSet::barrier_set()->barrier_set_assembler();
5341 decorators = AccessInternal::decorator_fixup(decorators, type);
5342 bool as_raw = (decorators & AS_RAW) != 0;
5343 if (as_raw) {
|