| --- /dev/null Thu Jan 01 00:00:00 1970 +0000 |
| +++ b/cgen/templates/FastPyFunctionDerivative Thu Apr 26 11:08:47 2012 -0700 |
| @@ -0,0 +1,66 @@ |
| +<%namespace file="base.impl" import="*"/>\ |
| + |
| + TARGET(FAST_PYFUN_${ arity_str(instr) }) |
| + { |
| + if (oparg != ${ instr.arity() }) goto TARGET_CALL_FUNCTION_SKIP_DISPATCH; |
| + |
| + % for operand,accessor in get_enumerated_args(instr.arity()): |
| + ${operand}= ${accessor}(); |
| + % endfor |
| + |
| + ## deal with ic misses... |
| + % if config.create_inca_guards: |
| + /* guard against inline cache misses */ |
| + if (! (!(PyMethod_Check(v) && PyMethod_GET_SELF(v) != NULL) && PyFunction_Check(v))) { |
| + ${ dbg_inf_ic_miss(instr) } |
| + goto TARGET_CALL_FUNCTION_SKIP_DISPATCH; |
| + } // if |
| + PyCodeObject *code= (PyCodeObject*)PyFunction_GET_CODE(v); |
| + if (code->co_argcount != ${ instr.arity() }) { |
| + ${ dbg_inf_ic_miss(instr) } |
| + goto TARGET_CALL_FUNCTION_SKIP_DISPATCH; |
| + } // if |
| + if (! (code->co_flags == (CO_OPTIMIZED | CO_NEWLOCALS | CO_NOFREE))) { |
| + ${ dbg_inf_ic_miss(instr) } |
| + goto TARGET_CALL_FUNCTION_SKIP_DISPATCH; |
| + } // if |
| + % else: |
| + /* guard against inline cache misses OMITTED */ |
| + % endif |
| + ${ dbg_inf_ic_hit(instr) } |
| + |
| + % if instr.arity() > 0: |
| + STACKADJ(-${ instr.arity() }); |
| + % endif |
| + PyObject *globals= PyFunction_GET_GLOBALS(v); |
| + PyThreadState *tstate= PyThreadState_GET(); |
| + PyFrameObject *callee_frame= PyFrame_New( tstate, code, globals, NULL ); |
| + if (callee_frame == NULL) { |
| + SET_TOP((PyObject*)NULL); |
| + break; |
| + } // if |
| + |
| + ## pass arguments... |
| + <% |
| + i= 0 |
| + revargs= get_enumerated_args(instr.arity()) |
| + revargs.reverse() |
| + %>\ |
| + % for operand, accessor in revargs: |
| + % if operand != 'v': |
| + callee_frame->f_localsplus[${i}]= ${ operand }; |
| + <% i+= 1 %>\ |
| + % endif |
| + % endfor |
| + |
| + x= PyEval_EvalFrameEx(callee_frame, 0); |
| + |
| + ++tstate->recursion_depth; |
| + Py_DECREF(callee_frame); |
| + --tstate->recursion_depth; |
| + |
| + ${ push_result() } |
| + ${ dispatch() } |
| + } |
| + |
| + |