37 #include "code/pcDesc.hpp" |
37 #include "code/pcDesc.hpp" |
38 #include "code/scopeDesc.hpp" |
38 #include "code/scopeDesc.hpp" |
39 #include "code/vtableStubs.hpp" |
39 #include "code/vtableStubs.hpp" |
40 #include "compiler/disassembler.hpp" |
40 #include "compiler/disassembler.hpp" |
41 #include "gc/shared/barrierSet.hpp" |
41 #include "gc/shared/barrierSet.hpp" |
|
42 #include "gc/shared/c1/barrierSetC1.hpp" |
42 #include "gc/shared/collectedHeap.hpp" |
43 #include "gc/shared/collectedHeap.hpp" |
43 #include "interpreter/bytecode.hpp" |
44 #include "interpreter/bytecode.hpp" |
44 #include "interpreter/interpreter.hpp" |
45 #include "interpreter/interpreter.hpp" |
45 #include "logging/log.hpp" |
46 #include "logging/log.hpp" |
46 #include "memory/allocation.inline.hpp" |
47 #include "memory/allocation.inline.hpp" |
176 Deoptimization::deoptimize_frame(thread, caller_frame.id()); |
177 Deoptimization::deoptimize_frame(thread, caller_frame.id()); |
177 assert(caller_is_deopted(), "Must be deoptimized"); |
178 assert(caller_is_deopted(), "Must be deoptimized"); |
178 } |
179 } |
179 } |
180 } |
180 |
181 |
181 |
182 class StubIDStubAssemblerCodeGenClosure: public StubAssemblerCodeGenClosure { |
182 void Runtime1::generate_blob_for(BufferBlob* buffer_blob, StubID id) { |
183 private: |
183 assert(0 <= id && id < number_of_ids, "illegal stub id"); |
184 Runtime1::StubID _id; |
|
185 public: |
|
186 StubIDStubAssemblerCodeGenClosure(Runtime1::StubID id) : _id(id) {} |
|
187 virtual OopMapSet* generate_code(StubAssembler* sasm) { |
|
188 return Runtime1::generate_code_for(_id, sasm); |
|
189 } |
|
190 }; |
|
191 |
|
192 CodeBlob* Runtime1::generate_blob(BufferBlob* buffer_blob, int stub_id, const char* name, bool expect_oop_map, StubAssemblerCodeGenClosure* cl) { |
184 ResourceMark rm; |
193 ResourceMark rm; |
185 // create code buffer for code storage |
194 // create code buffer for code storage |
186 CodeBuffer code(buffer_blob); |
195 CodeBuffer code(buffer_blob); |
187 |
196 |
188 OopMapSet* oop_maps; |
197 OopMapSet* oop_maps; |
190 bool must_gc_arguments; |
199 bool must_gc_arguments; |
191 |
200 |
192 Compilation::setup_code_buffer(&code, 0); |
201 Compilation::setup_code_buffer(&code, 0); |
193 |
202 |
194 // create assembler for code generation |
203 // create assembler for code generation |
195 StubAssembler* sasm = new StubAssembler(&code, name_for(id), id); |
204 StubAssembler* sasm = new StubAssembler(&code, name, stub_id); |
196 // generate code for runtime stub |
205 // generate code for runtime stub |
197 oop_maps = generate_code_for(id, sasm); |
206 oop_maps = cl->generate_code(sasm); |
198 assert(oop_maps == NULL || sasm->frame_size() != no_frame_size, |
207 assert(oop_maps == NULL || sasm->frame_size() != no_frame_size, |
199 "if stub has an oop map it must have a valid frame size"); |
208 "if stub has an oop map it must have a valid frame size"); |
200 |
209 assert(!expect_oop_map || oop_maps != NULL, "must have an oopmap"); |
|
210 |
|
211 // align so printing shows nop's instead of random code at the end (SimpleStubs are aligned) |
|
212 sasm->align(BytesPerWord); |
|
213 // make sure all code is in code buffer |
|
214 sasm->flush(); |
|
215 |
|
216 frame_size = sasm->frame_size(); |
|
217 must_gc_arguments = sasm->must_gc_arguments(); |
|
218 // create blob - distinguish a few special cases |
|
219 CodeBlob* blob = RuntimeStub::new_runtime_stub(name, |
|
220 &code, |
|
221 CodeOffsets::frame_never_safe, |
|
222 frame_size, |
|
223 oop_maps, |
|
224 must_gc_arguments); |
|
225 assert(blob != NULL, "blob must exist"); |
|
226 return blob; |
|
227 } |
|
228 |
|
229 void Runtime1::generate_blob_for(BufferBlob* buffer_blob, StubID id) { |
|
230 assert(0 <= id && id < number_of_ids, "illegal stub id"); |
|
231 bool expect_oop_map = true; |
201 #ifdef ASSERT |
232 #ifdef ASSERT |
202 // Make sure that stubs that need oopmaps have them |
233 // Make sure that stubs that need oopmaps have them |
203 switch (id) { |
234 switch (id) { |
204 // These stubs don't need to have an oopmap |
235 // These stubs don't need to have an oopmap |
205 case dtrace_object_alloc_id: |
236 case dtrace_object_alloc_id: |
206 case g1_pre_barrier_slow_id: |
|
207 case g1_post_barrier_slow_id: |
|
208 case slow_subtype_check_id: |
237 case slow_subtype_check_id: |
209 case fpu2long_stub_id: |
238 case fpu2long_stub_id: |
210 case unwind_exception_id: |
239 case unwind_exception_id: |
211 case counter_overflow_id: |
240 case counter_overflow_id: |
212 #if defined(SPARC) || defined(PPC32) |
241 #if defined(SPARC) || defined(PPC32) |
213 case handle_exception_nofpu_id: // Unused on sparc |
242 case handle_exception_nofpu_id: // Unused on sparc |
214 #endif |
243 #endif |
|
244 expect_oop_map = false; |
215 break; |
245 break; |
216 |
|
217 // All other stubs should have oopmaps |
|
218 default: |
246 default: |
219 assert(oop_maps != NULL, "must have an oopmap"); |
247 break; |
220 } |
248 } |
221 #endif |
249 #endif |
222 |
250 StubIDStubAssemblerCodeGenClosure cl(id); |
223 // align so printing shows nop's instead of random code at the end (SimpleStubs are aligned) |
251 CodeBlob* blob = generate_blob(buffer_blob, id, name_for(id), expect_oop_map, &cl); |
224 sasm->align(BytesPerWord); |
|
225 // make sure all code is in code buffer |
|
226 sasm->flush(); |
|
227 |
|
228 frame_size = sasm->frame_size(); |
|
229 must_gc_arguments = sasm->must_gc_arguments(); |
|
230 // create blob - distinguish a few special cases |
|
231 CodeBlob* blob = RuntimeStub::new_runtime_stub(name_for(id), |
|
232 &code, |
|
233 CodeOffsets::frame_never_safe, |
|
234 frame_size, |
|
235 oop_maps, |
|
236 must_gc_arguments); |
|
237 // install blob |
252 // install blob |
238 assert(blob != NULL, "blob must exist"); |
|
239 _blobs[id] = blob; |
253 _blobs[id] = blob; |
240 } |
254 } |
241 |
|
242 |
255 |
243 void Runtime1::initialize(BufferBlob* blob) { |
256 void Runtime1::initialize(BufferBlob* blob) { |
244 // platform-dependent initialization |
257 // platform-dependent initialization |
245 initialize_pd(); |
258 initialize_pd(); |
246 // generate stubs |
259 // generate stubs |