Mercurial > hg > truffle
annotate src/share/vm/c1/c1_CodeStubs.hpp @ 1721:413ad0331a0c
6977924: Changes for 6975078 produce build error with certain gcc versions
Summary: The changes introduced for 6975078 assign badHeapOopVal to the _allocation field in the ResourceObj class. In 32 bit linux builds with certain versions of gcc this assignment will be flagged as an error while compiling allocation.cpp. In 32 bit builds the constant value badHeapOopVal (which is cast to an intptr_t) is negative. The _allocation field is typed as an unsigned intptr_t and gcc catches this as an error.
Reviewed-by: jcoomes, ysr, phh
author | johnc |
---|---|
date | Wed, 18 Aug 2010 10:59:06 -0700 |
parents | 126ea7725993 |
children | d5d065957597 |
rev | line source |
---|---|
0 | 1 /* |
1552
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1295
diff
changeset
|
2 * Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved. |
0 | 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
4 * | |
5 * This code is free software; you can redistribute it and/or modify it | |
6 * under the terms of the GNU General Public License version 2 only, as | |
7 * published by the Free Software Foundation. | |
8 * | |
9 * This code is distributed in the hope that it will be useful, but WITHOUT | |
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
12 * version 2 for more details (a copy is included in the LICENSE file that | |
13 * accompanied this code). | |
14 * | |
15 * You should have received a copy of the GNU General Public License version | |
16 * 2 along with this work; if not, write to the Free Software Foundation, | |
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. | |
18 * | |
1552
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1295
diff
changeset
|
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA |
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1295
diff
changeset
|
20 * or visit www.oracle.com if you need additional information or have any |
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1295
diff
changeset
|
21 * questions. |
0 | 22 * |
23 */ | |
24 | |
25 class CodeEmitInfo; | |
26 class LIR_Assembler; | |
27 class LIR_OpVisitState; | |
28 | |
29 // CodeStubs are little 'out-of-line' pieces of code that | |
30 // usually handle slow cases of operations. All code stubs | |
31 // are collected and code is emitted at the end of the | |
32 // nmethod. | |
33 | |
34 class CodeStub: public CompilationResourceObj { | |
35 protected: | |
36 Label _entry; // label at the stub entry point | |
37 Label _continuation; // label where stub continues, if any | |
38 | |
39 public: | |
40 CodeStub() {} | |
41 | |
42 // code generation | |
43 void assert_no_unbound_labels() { assert(!_entry.is_unbound() && !_continuation.is_unbound(), "unbound label"); } | |
44 virtual void emit_code(LIR_Assembler* e) = 0; | |
45 virtual CodeEmitInfo* info() const { return NULL; } | |
46 virtual bool is_exception_throw_stub() const { return false; } | |
47 virtual bool is_range_check_stub() const { return false; } | |
48 virtual bool is_divbyzero_stub() const { return false; } | |
49 #ifndef PRODUCT | |
50 virtual void print_name(outputStream* out) const = 0; | |
51 #endif | |
52 | |
53 // label access | |
54 Label* entry() { return &_entry; } | |
55 Label* continuation() { return &_continuation; } | |
56 // for LIR | |
57 virtual void visit(LIR_OpVisitState* visit) { | |
58 #ifndef PRODUCT | |
59 if (LIRTracePeephole && Verbose) { | |
60 tty->print("no visitor for "); | |
61 print_name(tty); | |
62 tty->cr(); | |
63 } | |
64 #endif | |
65 } | |
66 }; | |
67 | |
68 | |
69 define_array(CodeStubArray, CodeStub*) | |
70 define_stack(_CodeStubList, CodeStubArray) | |
71 | |
72 class CodeStubList: public _CodeStubList { | |
73 public: | |
74 CodeStubList(): _CodeStubList() {} | |
75 | |
76 void append(CodeStub* stub) { | |
77 if (!contains(stub)) { | |
78 _CodeStubList::append(stub); | |
79 } | |
80 } | |
81 }; | |
82 | |
83 #ifdef TIERED | |
84 class CounterOverflowStub: public CodeStub { | |
85 private: | |
86 CodeEmitInfo* _info; | |
87 int _bci; | |
88 | |
89 public: | |
90 CounterOverflowStub(CodeEmitInfo* info, int bci) : _info(info), _bci(bci) { | |
91 } | |
92 | |
93 virtual void emit_code(LIR_Assembler* e); | |
94 | |
95 virtual void visit(LIR_OpVisitState* visitor) { | |
96 visitor->do_slow_case(_info); | |
97 } | |
98 | |
99 #ifndef PRODUCT | |
100 virtual void print_name(outputStream* out) const { out->print("CounterOverflowStub"); } | |
101 #endif // PRODUCT | |
102 | |
103 }; | |
104 #endif // TIERED | |
105 | |
106 class ConversionStub: public CodeStub { | |
107 private: | |
108 Bytecodes::Code _bytecode; | |
109 LIR_Opr _input; | |
110 LIR_Opr _result; | |
111 | |
112 static float float_zero; | |
113 static double double_zero; | |
114 public: | |
115 ConversionStub(Bytecodes::Code bytecode, LIR_Opr input, LIR_Opr result) | |
116 : _bytecode(bytecode), _input(input), _result(result) { | |
117 } | |
118 | |
119 Bytecodes::Code bytecode() { return _bytecode; } | |
120 LIR_Opr input() { return _input; } | |
121 LIR_Opr result() { return _result; } | |
122 | |
123 virtual void emit_code(LIR_Assembler* e); | |
124 virtual void visit(LIR_OpVisitState* visitor) { | |
125 visitor->do_slow_case(); | |
126 visitor->do_input(_input); | |
127 visitor->do_output(_result); | |
128 } | |
129 #ifndef PRODUCT | |
130 virtual void print_name(outputStream* out) const { out->print("ConversionStub"); } | |
131 #endif // PRODUCT | |
132 }; | |
133 | |
134 | |
135 // Throws ArrayIndexOutOfBoundsException by default but can be | |
136 // configured to throw IndexOutOfBoundsException in constructor | |
137 class RangeCheckStub: public CodeStub { | |
138 private: | |
139 CodeEmitInfo* _info; | |
140 LIR_Opr _index; | |
141 bool _throw_index_out_of_bounds_exception; | |
142 | |
143 public: | |
144 RangeCheckStub(CodeEmitInfo* info, LIR_Opr index, bool throw_index_out_of_bounds_exception = false); | |
145 virtual void emit_code(LIR_Assembler* e); | |
146 virtual CodeEmitInfo* info() const { return _info; } | |
147 virtual bool is_exception_throw_stub() const { return true; } | |
148 virtual bool is_range_check_stub() const { return true; } | |
149 virtual void visit(LIR_OpVisitState* visitor) { | |
150 visitor->do_slow_case(_info); | |
151 visitor->do_input(_index); | |
152 } | |
153 #ifndef PRODUCT | |
154 virtual void print_name(outputStream* out) const { out->print("RangeCheckStub"); } | |
155 #endif // PRODUCT | |
156 }; | |
157 | |
158 | |
159 class DivByZeroStub: public CodeStub { | |
160 private: | |
161 CodeEmitInfo* _info; | |
162 int _offset; | |
163 | |
164 public: | |
165 DivByZeroStub(CodeEmitInfo* info) | |
166 : _info(info), _offset(-1) { | |
167 } | |
168 DivByZeroStub(int offset, CodeEmitInfo* info) | |
169 : _info(info), _offset(offset) { | |
170 } | |
171 virtual void emit_code(LIR_Assembler* e); | |
172 virtual CodeEmitInfo* info() const { return _info; } | |
173 virtual bool is_exception_throw_stub() const { return true; } | |
174 virtual bool is_divbyzero_stub() const { return true; } | |
175 virtual void visit(LIR_OpVisitState* visitor) { | |
176 visitor->do_slow_case(_info); | |
177 } | |
178 #ifndef PRODUCT | |
179 virtual void print_name(outputStream* out) const { out->print("DivByZeroStub"); } | |
180 #endif // PRODUCT | |
181 }; | |
182 | |
183 | |
184 class ImplicitNullCheckStub: public CodeStub { | |
185 private: | |
186 CodeEmitInfo* _info; | |
187 int _offset; | |
188 | |
189 public: | |
190 ImplicitNullCheckStub(int offset, CodeEmitInfo* info) | |
191 : _offset(offset), _info(info) { | |
192 } | |
193 virtual void emit_code(LIR_Assembler* e); | |
194 virtual CodeEmitInfo* info() const { return _info; } | |
195 virtual bool is_exception_throw_stub() const { return true; } | |
196 virtual void visit(LIR_OpVisitState* visitor) { | |
197 visitor->do_slow_case(_info); | |
198 } | |
199 #ifndef PRODUCT | |
200 virtual void print_name(outputStream* out) const { out->print("ImplicitNullCheckStub"); } | |
201 #endif // PRODUCT | |
202 }; | |
203 | |
204 | |
205 class NewInstanceStub: public CodeStub { | |
206 private: | |
207 ciInstanceKlass* _klass; | |
208 LIR_Opr _klass_reg; | |
209 LIR_Opr _result; | |
210 CodeEmitInfo* _info; | |
211 Runtime1::StubID _stub_id; | |
212 | |
213 public: | |
214 NewInstanceStub(LIR_Opr klass_reg, LIR_Opr result, ciInstanceKlass* klass, CodeEmitInfo* info, Runtime1::StubID stub_id); | |
215 virtual void emit_code(LIR_Assembler* e); | |
216 virtual CodeEmitInfo* info() const { return _info; } | |
217 virtual void visit(LIR_OpVisitState* visitor) { | |
218 visitor->do_slow_case(_info); | |
219 visitor->do_input(_klass_reg); | |
220 visitor->do_output(_result); | |
221 } | |
222 #ifndef PRODUCT | |
223 virtual void print_name(outputStream* out) const { out->print("NewInstanceStub"); } | |
224 #endif // PRODUCT | |
225 }; | |
226 | |
227 | |
228 class NewTypeArrayStub: public CodeStub { | |
229 private: | |
230 LIR_Opr _klass_reg; | |
231 LIR_Opr _length; | |
232 LIR_Opr _result; | |
233 CodeEmitInfo* _info; | |
234 | |
235 public: | |
236 NewTypeArrayStub(LIR_Opr klass_reg, LIR_Opr length, LIR_Opr result, CodeEmitInfo* info); | |
237 virtual void emit_code(LIR_Assembler* e); | |
238 virtual CodeEmitInfo* info() const { return _info; } | |
239 virtual void visit(LIR_OpVisitState* visitor) { | |
240 visitor->do_slow_case(_info); | |
241 visitor->do_input(_klass_reg); | |
242 visitor->do_input(_length); | |
243 assert(_result->is_valid(), "must be valid"); visitor->do_output(_result); | |
244 } | |
245 #ifndef PRODUCT | |
246 virtual void print_name(outputStream* out) const { out->print("NewTypeArrayStub"); } | |
247 #endif // PRODUCT | |
248 }; | |
249 | |
250 | |
251 class NewObjectArrayStub: public CodeStub { | |
252 private: | |
253 LIR_Opr _klass_reg; | |
254 LIR_Opr _length; | |
255 LIR_Opr _result; | |
256 CodeEmitInfo* _info; | |
257 | |
258 public: | |
259 NewObjectArrayStub(LIR_Opr klass_reg, LIR_Opr length, LIR_Opr result, CodeEmitInfo* info); | |
260 virtual void emit_code(LIR_Assembler* e); | |
261 virtual CodeEmitInfo* info() const { return _info; } | |
262 virtual void visit(LIR_OpVisitState* visitor) { | |
263 visitor->do_slow_case(_info); | |
264 visitor->do_input(_klass_reg); | |
265 visitor->do_input(_length); | |
266 assert(_result->is_valid(), "must be valid"); visitor->do_output(_result); | |
267 } | |
268 #ifndef PRODUCT | |
269 virtual void print_name(outputStream* out) const { out->print("NewObjectArrayStub"); } | |
270 #endif // PRODUCT | |
271 }; | |
272 | |
273 | |
274 class MonitorAccessStub: public CodeStub { | |
275 protected: | |
276 LIR_Opr _obj_reg; | |
277 LIR_Opr _lock_reg; | |
278 | |
279 public: | |
280 MonitorAccessStub(LIR_Opr obj_reg, LIR_Opr lock_reg) { | |
281 _obj_reg = obj_reg; | |
282 _lock_reg = lock_reg; | |
283 } | |
284 | |
285 #ifndef PRODUCT | |
286 virtual void print_name(outputStream* out) const { out->print("MonitorAccessStub"); } | |
287 #endif // PRODUCT | |
288 }; | |
289 | |
290 | |
291 class MonitorEnterStub: public MonitorAccessStub { | |
292 private: | |
293 CodeEmitInfo* _info; | |
294 | |
295 public: | |
296 MonitorEnterStub(LIR_Opr obj_reg, LIR_Opr lock_reg, CodeEmitInfo* info); | |
297 | |
298 virtual void emit_code(LIR_Assembler* e); | |
299 virtual CodeEmitInfo* info() const { return _info; } | |
300 virtual void visit(LIR_OpVisitState* visitor) { | |
301 visitor->do_input(_obj_reg); | |
302 visitor->do_input(_lock_reg); | |
303 visitor->do_slow_case(_info); | |
304 } | |
305 #ifndef PRODUCT | |
306 virtual void print_name(outputStream* out) const { out->print("MonitorEnterStub"); } | |
307 #endif // PRODUCT | |
308 }; | |
309 | |
310 | |
311 class MonitorExitStub: public MonitorAccessStub { | |
312 private: | |
313 bool _compute_lock; | |
314 int _monitor_ix; | |
315 | |
316 public: | |
317 MonitorExitStub(LIR_Opr lock_reg, bool compute_lock, int monitor_ix) | |
318 : MonitorAccessStub(LIR_OprFact::illegalOpr, lock_reg), | |
319 _compute_lock(compute_lock), _monitor_ix(monitor_ix) { } | |
320 virtual void emit_code(LIR_Assembler* e); | |
321 virtual void visit(LIR_OpVisitState* visitor) { | |
322 assert(_obj_reg->is_illegal(), "unused"); | |
323 if (_compute_lock) { | |
324 visitor->do_temp(_lock_reg); | |
325 } else { | |
326 visitor->do_input(_lock_reg); | |
327 } | |
328 } | |
329 #ifndef PRODUCT | |
330 virtual void print_name(outputStream* out) const { out->print("MonitorExitStub"); } | |
331 #endif // PRODUCT | |
332 }; | |
333 | |
334 | |
335 class PatchingStub: public CodeStub { | |
336 public: | |
337 enum PatchID { | |
338 access_field_id, | |
339 load_klass_id | |
340 }; | |
341 enum constants { | |
342 patch_info_size = 3 | |
343 }; | |
344 private: | |
345 PatchID _id; | |
346 address _pc_start; | |
347 int _bytes_to_copy; | |
348 Label _patched_code_entry; | |
349 Label _patch_site_entry; | |
350 Label _patch_site_continuation; | |
351 Register _obj; | |
352 CodeEmitInfo* _info; | |
353 int _oop_index; // index of the patchable oop in nmethod oop table if needed | |
354 static int _patch_info_offset; | |
355 | |
356 void align_patch_site(MacroAssembler* masm); | |
357 | |
358 public: | |
359 static int patch_info_offset() { return _patch_info_offset; } | |
360 | |
361 PatchingStub(MacroAssembler* masm, PatchID id, int oop_index = -1): | |
362 _id(id) | |
363 , _info(NULL) | |
364 , _oop_index(oop_index) { | |
365 if (os::is_MP()) { | |
366 // force alignment of patch sites on MP hardware so we | |
367 // can guarantee atomic writes to the patch site. | |
368 align_patch_site(masm); | |
369 } | |
370 _pc_start = masm->pc(); | |
371 masm->bind(_patch_site_entry); | |
372 } | |
373 | |
374 void install(MacroAssembler* masm, LIR_PatchCode patch_code, Register obj, CodeEmitInfo* info) { | |
375 _info = info; | |
376 _obj = obj; | |
377 masm->bind(_patch_site_continuation); | |
378 _bytes_to_copy = masm->pc() - pc_start(); | |
379 if (_id == PatchingStub::access_field_id) { | |
380 // embed a fixed offset to handle long patches which need to be offset by a word. | |
381 // the patching code will just add the field offset field to this offset so | |
382 // that we can refernce either the high or low word of a double word field. | |
383 int field_offset = 0; | |
384 switch (patch_code) { | |
385 case lir_patch_low: field_offset = lo_word_offset_in_bytes; break; | |
386 case lir_patch_high: field_offset = hi_word_offset_in_bytes; break; | |
387 case lir_patch_normal: field_offset = 0; break; | |
388 default: ShouldNotReachHere(); | |
389 } | |
390 NativeMovRegMem* n_move = nativeMovRegMem_at(pc_start()); | |
391 n_move->set_offset(field_offset); | |
392 } else if (_id == load_klass_id) { | |
393 assert(_obj != noreg, "must have register object for load_klass"); | |
394 #ifdef ASSERT | |
395 // verify that we're pointing at a NativeMovConstReg | |
396 nativeMovConstReg_at(pc_start()); | |
397 #endif | |
398 } else { | |
399 ShouldNotReachHere(); | |
400 } | |
401 assert(_bytes_to_copy <= (masm->pc() - pc_start()), "not enough bytes"); | |
402 } | |
403 | |
404 address pc_start() const { return _pc_start; } | |
405 PatchID id() const { return _id; } | |
406 | |
407 virtual void emit_code(LIR_Assembler* e); | |
408 virtual CodeEmitInfo* info() const { return _info; } | |
409 virtual void visit(LIR_OpVisitState* visitor) { | |
410 visitor->do_slow_case(_info); | |
411 } | |
412 #ifndef PRODUCT | |
413 virtual void print_name(outputStream* out) const { out->print("PatchingStub"); } | |
414 #endif // PRODUCT | |
415 }; | |
416 | |
417 | |
1295 | 418 //------------------------------------------------------------------------------ |
419 // DeoptimizeStub | |
420 // | |
421 class DeoptimizeStub : public CodeStub { | |
422 private: | |
423 CodeEmitInfo* _info; | |
424 | |
425 public: | |
426 DeoptimizeStub(CodeEmitInfo* info) : _info(new CodeEmitInfo(info)) {} | |
427 | |
428 virtual void emit_code(LIR_Assembler* e); | |
429 virtual CodeEmitInfo* info() const { return _info; } | |
430 virtual bool is_exception_throw_stub() const { return true; } | |
431 virtual void visit(LIR_OpVisitState* visitor) { | |
432 visitor->do_slow_case(_info); | |
433 } | |
434 #ifndef PRODUCT | |
435 virtual void print_name(outputStream* out) const { out->print("DeoptimizeStub"); } | |
436 #endif // PRODUCT | |
437 }; | |
438 | |
439 | |
0 | 440 class SimpleExceptionStub: public CodeStub { |
441 private: | |
442 LIR_Opr _obj; | |
443 Runtime1::StubID _stub; | |
444 CodeEmitInfo* _info; | |
445 | |
446 public: | |
447 SimpleExceptionStub(Runtime1::StubID stub, LIR_Opr obj, CodeEmitInfo* info): | |
448 _obj(obj), _info(info), _stub(stub) { | |
449 } | |
450 | |
1681
126ea7725993
6953477: Increase portability and flexibility of building Hotspot
bobv
parents:
1552
diff
changeset
|
451 void set_obj(LIR_Opr obj) { |
126ea7725993
6953477: Increase portability and flexibility of building Hotspot
bobv
parents:
1552
diff
changeset
|
452 _obj = obj; |
126ea7725993
6953477: Increase portability and flexibility of building Hotspot
bobv
parents:
1552
diff
changeset
|
453 } |
126ea7725993
6953477: Increase portability and flexibility of building Hotspot
bobv
parents:
1552
diff
changeset
|
454 |
0 | 455 virtual void emit_code(LIR_Assembler* e); |
456 virtual CodeEmitInfo* info() const { return _info; } | |
457 virtual bool is_exception_throw_stub() const { return true; } | |
458 virtual void visit(LIR_OpVisitState* visitor) { | |
459 if (_obj->is_valid()) visitor->do_input(_obj); | |
460 visitor->do_slow_case(_info); | |
461 } | |
462 #ifndef PRODUCT | |
463 virtual void print_name(outputStream* out) const { out->print("SimpleExceptionStub"); } | |
464 #endif // PRODUCT | |
465 }; | |
466 | |
467 | |
468 | |
469 class ArrayStoreExceptionStub: public CodeStub { | |
470 private: | |
471 CodeEmitInfo* _info; | |
472 | |
473 public: | |
474 ArrayStoreExceptionStub(CodeEmitInfo* info); | |
475 virtual void emit_code(LIR_Assembler* emit); | |
476 virtual CodeEmitInfo* info() const { return _info; } | |
477 virtual bool is_exception_throw_stub() const { return true; } | |
478 virtual void visit(LIR_OpVisitState* visitor) { | |
479 visitor->do_slow_case(_info); | |
480 } | |
481 #ifndef PRODUCT | |
482 virtual void print_name(outputStream* out) const { out->print("ArrayStoreExceptionStub"); } | |
483 #endif // PRODUCT | |
484 }; | |
485 | |
486 | |
487 class ArrayCopyStub: public CodeStub { | |
488 private: | |
489 LIR_OpArrayCopy* _op; | |
490 | |
491 public: | |
492 ArrayCopyStub(LIR_OpArrayCopy* op): _op(op) { } | |
493 | |
494 LIR_Opr src() const { return _op->src(); } | |
495 LIR_Opr src_pos() const { return _op->src_pos(); } | |
496 LIR_Opr dst() const { return _op->dst(); } | |
497 LIR_Opr dst_pos() const { return _op->dst_pos(); } | |
498 LIR_Opr length() const { return _op->length(); } | |
499 LIR_Opr tmp() const { return _op->tmp(); } | |
500 | |
501 virtual void emit_code(LIR_Assembler* e); | |
502 virtual CodeEmitInfo* info() const { return _op->info(); } | |
503 virtual void visit(LIR_OpVisitState* visitor) { | |
504 // don't pass in the code emit info since it's processed in the fast path | |
505 visitor->do_slow_case(); | |
506 } | |
507 #ifndef PRODUCT | |
508 virtual void print_name(outputStream* out) const { out->print("ArrayCopyStub"); } | |
509 #endif // PRODUCT | |
510 }; | |
342 | 511 |
512 ////////////////////////////////////////////////////////////////////////////////////////// | |
513 #ifndef SERIALGC | |
514 | |
515 // Code stubs for Garbage-First barriers. | |
516 class G1PreBarrierStub: public CodeStub { | |
517 private: | |
518 LIR_Opr _addr; | |
519 LIR_Opr _pre_val; | |
520 LIR_PatchCode _patch_code; | |
521 CodeEmitInfo* _info; | |
522 | |
523 public: | |
524 // pre_val (a temporary register) must be a register; | |
525 // addr (the address of the field to be read) must be a LIR_Address | |
526 G1PreBarrierStub(LIR_Opr addr, LIR_Opr pre_val, LIR_PatchCode patch_code, CodeEmitInfo* info) : | |
527 _addr(addr), _pre_val(pre_val), _patch_code(patch_code), _info(info) | |
528 { | |
529 assert(_pre_val->is_register(), "should be temporary register"); | |
530 assert(_addr->is_address(), "should be the address of the field"); | |
531 } | |
532 | |
533 LIR_Opr addr() const { return _addr; } | |
534 LIR_Opr pre_val() const { return _pre_val; } | |
535 LIR_PatchCode patch_code() const { return _patch_code; } | |
536 CodeEmitInfo* info() const { return _info; } | |
537 | |
538 virtual void emit_code(LIR_Assembler* e); | |
539 virtual void visit(LIR_OpVisitState* visitor) { | |
540 // don't pass in the code emit info since it's processed in the fast | |
541 // path | |
542 if (_info != NULL) | |
543 visitor->do_slow_case(_info); | |
544 else | |
545 visitor->do_slow_case(); | |
546 visitor->do_input(_addr); | |
547 visitor->do_temp(_pre_val); | |
548 } | |
549 #ifndef PRODUCT | |
550 virtual void print_name(outputStream* out) const { out->print("G1PreBarrierStub"); } | |
551 #endif // PRODUCT | |
552 }; | |
553 | |
554 class G1PostBarrierStub: public CodeStub { | |
555 private: | |
556 LIR_Opr _addr; | |
557 LIR_Opr _new_val; | |
558 | |
559 static jbyte* _byte_map_base; | |
560 static jbyte* byte_map_base_slow(); | |
561 static jbyte* byte_map_base() { | |
562 if (_byte_map_base == NULL) { | |
563 _byte_map_base = byte_map_base_slow(); | |
564 } | |
565 return _byte_map_base; | |
566 } | |
567 | |
568 public: | |
569 // addr (the address of the object head) and new_val must be registers. | |
570 G1PostBarrierStub(LIR_Opr addr, LIR_Opr new_val): _addr(addr), _new_val(new_val) { } | |
571 | |
572 LIR_Opr addr() const { return _addr; } | |
573 LIR_Opr new_val() const { return _new_val; } | |
574 | |
575 virtual void emit_code(LIR_Assembler* e); | |
576 virtual void visit(LIR_OpVisitState* visitor) { | |
577 // don't pass in the code emit info since it's processed in the fast path | |
578 visitor->do_slow_case(); | |
579 visitor->do_input(_addr); | |
580 visitor->do_input(_new_val); | |
581 } | |
582 #ifndef PRODUCT | |
583 virtual void print_name(outputStream* out) const { out->print("G1PostBarrierStub"); } | |
584 #endif // PRODUCT | |
585 }; | |
586 | |
587 #endif // SERIALGC | |
588 ////////////////////////////////////////////////////////////////////////////////////////// |