31 #include "opto/convertnode.hpp"
32 #include "opto/locknode.hpp"
33 #include "opto/memnode.hpp"
34 #include "opto/mulnode.hpp"
35 #include "opto/node.hpp"
36 #include "opto/parse.hpp"
37 #include "opto/phaseX.hpp"
38 #include "opto/rootnode.hpp"
39 #include "opto/runtime.hpp"
40 #include "opto/type.hpp"
41 #include "runtime/stubRoutines.hpp"
42
43 //--------------------gen_stub-------------------------------
44 void GraphKit::gen_stub(address C_function,
45 const char *name,
46 int is_fancy_jump,
47 bool pass_tls,
48 bool return_pc) {
49 ResourceMark rm;
50
51 const TypeTuple *jdomain = C->tf()->domain();
52 const TypeTuple *jrange = C->tf()->range();
53
54 // The procedure start
55 StartNode* start = new StartNode(root(), jdomain);
56 _gvn.set_type_bottom(start);
57
58 // Make a map, with JVM state
59 uint parm_cnt = jdomain->cnt();
60 uint max_map = MAX2(2*parm_cnt+1, jrange->cnt());
61 // %%% SynchronizationEntryBCI is redundant; use InvocationEntryBci in interfaces
62 assert(SynchronizationEntryBCI == InvocationEntryBci, "");
63 JVMState* jvms = new (C) JVMState(0);
64 jvms->set_bci(InvocationEntryBci);
65 jvms->set_monoff(max_map);
66 jvms->set_scloff(max_map);
67 jvms->set_endoff(max_map);
68 {
69 SafePointNode *map = new SafePointNode( max_map, jvms );
70 jvms->set_map(map);
71 set_jvms(jvms);
72 assert(map == this->map(), "kit.map is set");
257 assert (StubRoutines::forward_exception_entry() != nullptr, "must be generated before");
258 Node *to_exc = new ForwardExceptionNode(if_not_null,
259 i_o(),
260 exit_memory,
261 frameptr(),
262 returnadr());
263 root()->add_req(_gvn.transform(to_exc)); // bind to root to keep live
264 C->verify_start(start);
265
266 //-----------------------------
267 // If this is a normal subroutine return, issue the return and be done.
268 Node *ret = nullptr;
269 switch( is_fancy_jump ) {
270 case 0: // Make a return instruction
271 // Return to caller, free any space for return address
272 ret = new ReturnNode(TypeFunc::Parms, if_null,
273 i_o(),
274 exit_memory,
275 frameptr(),
276 returnadr());
277 if (C->tf()->range()->cnt() > TypeFunc::Parms)
278 ret->add_req( map()->in(TypeFunc::Parms) );
279 break;
280 case 1: // This is a fancy tail-call jump. Jump to computed address.
281 // Jump to new callee; leave old return address alone.
282 ret = new TailCallNode(if_null,
283 i_o(),
284 exit_memory,
285 frameptr(),
286 returnadr(),
287 target, map()->in(TypeFunc::Parms));
288 break;
289 case 2: // Pop return address & jump
290 // Throw away old return address; jump to new computed address
291 //assert(C_function == CAST_FROM_FN_PTR(address, OptoRuntime::rethrow_C), "fancy_jump==2 only for rethrow");
292 ret = new TailJumpNode(if_null,
293 i_o(),
294 exit_memory,
295 frameptr(),
296 target, map()->in(TypeFunc::Parms));
297 break;
|
31 #include "opto/convertnode.hpp"
32 #include "opto/locknode.hpp"
33 #include "opto/memnode.hpp"
34 #include "opto/mulnode.hpp"
35 #include "opto/node.hpp"
36 #include "opto/parse.hpp"
37 #include "opto/phaseX.hpp"
38 #include "opto/rootnode.hpp"
39 #include "opto/runtime.hpp"
40 #include "opto/type.hpp"
41 #include "runtime/stubRoutines.hpp"
42
43 //--------------------gen_stub-------------------------------
44 void GraphKit::gen_stub(address C_function,
45 const char *name,
46 int is_fancy_jump,
47 bool pass_tls,
48 bool return_pc) {
49 ResourceMark rm;
50
51 const TypeTuple *jdomain = C->tf()->domain_sig();
52 const TypeTuple *jrange = C->tf()->range_sig();
53
54 // The procedure start
55 StartNode* start = new StartNode(root(), jdomain);
56 _gvn.set_type_bottom(start);
57
58 // Make a map, with JVM state
59 uint parm_cnt = jdomain->cnt();
60 uint max_map = MAX2(2*parm_cnt+1, jrange->cnt());
61 // %%% SynchronizationEntryBCI is redundant; use InvocationEntryBci in interfaces
62 assert(SynchronizationEntryBCI == InvocationEntryBci, "");
63 JVMState* jvms = new (C) JVMState(0);
64 jvms->set_bci(InvocationEntryBci);
65 jvms->set_monoff(max_map);
66 jvms->set_scloff(max_map);
67 jvms->set_endoff(max_map);
68 {
69 SafePointNode *map = new SafePointNode( max_map, jvms );
70 jvms->set_map(map);
71 set_jvms(jvms);
72 assert(map == this->map(), "kit.map is set");
257 assert (StubRoutines::forward_exception_entry() != nullptr, "must be generated before");
258 Node *to_exc = new ForwardExceptionNode(if_not_null,
259 i_o(),
260 exit_memory,
261 frameptr(),
262 returnadr());
263 root()->add_req(_gvn.transform(to_exc)); // bind to root to keep live
264 C->verify_start(start);
265
266 //-----------------------------
267 // If this is a normal subroutine return, issue the return and be done.
268 Node *ret = nullptr;
269 switch( is_fancy_jump ) {
270 case 0: // Make a return instruction
271 // Return to caller, free any space for return address
272 ret = new ReturnNode(TypeFunc::Parms, if_null,
273 i_o(),
274 exit_memory,
275 frameptr(),
276 returnadr());
277 if (C->tf()->range_sig()->cnt() > TypeFunc::Parms)
278 ret->add_req( map()->in(TypeFunc::Parms) );
279 break;
280 case 1: // This is a fancy tail-call jump. Jump to computed address.
281 // Jump to new callee; leave old return address alone.
282 ret = new TailCallNode(if_null,
283 i_o(),
284 exit_memory,
285 frameptr(),
286 returnadr(),
287 target, map()->in(TypeFunc::Parms));
288 break;
289 case 2: // Pop return address & jump
290 // Throw away old return address; jump to new computed address
291 //assert(C_function == CAST_FROM_FN_PTR(address, OptoRuntime::rethrow_C), "fancy_jump==2 only for rethrow");
292 ret = new TailJumpNode(if_null,
293 i_o(),
294 exit_memory,
295 frameptr(),
296 target, map()->in(TypeFunc::Parms));
297 break;
|