283
286
interpreter_lock = PyThread_allocate_lock();
284
287
PyThread_acquire_lock(interpreter_lock, 1);
285
288
main_thread = PyThread_get_thread_ident();
290
/* Update the threading module with the new state.
292
tstate = PyThreadState_GET();
293
threading = PyMapping_GetItemString(tstate->interp->modules,
295
if (threading == NULL) {
296
/* threading not imported */
300
result = PyObject_CallMethod(threading, "_after_fork", NULL);
302
PyErr_WriteUnraisable(threading);
305
Py_DECREF(threading);
615
635
COMPARE_OP is often followed by JUMP_IF_FALSE or JUMP_IF_TRUE. And,
616
636
those opcodes are often followed by a POP_TOP.
618
Verifying the prediction costs a single high-speed test of register
638
Verifying the prediction costs a single high-speed test of a register
619
639
variable against a constant. If the pairing was good, then the
620
processor has a high likelihood of making its own successful branch
621
prediction which results in a nearly zero overhead transition to the
624
A successful prediction saves a trip through the eval-loop including
625
its two unpredictable branches, the HAS_ARG test and the switch-case.
627
If collecting opcode statistics, turn off prediction so that
628
statistics are accurately maintained (the predictions bypass
629
the opcode frequency counter updates).
640
processor's own internal branch predication has a high likelihood of
641
success, resulting in a nearly zero-overhead transition to the
642
next opcode. A successful prediction saves a trip through the eval-loop
643
including its two unpredictable branches, the HAS_ARG test and the
644
switch-case. Combined with the processor's internal branch prediction,
645
a successful PREDICT has the effect of making the two opcodes run as if
646
they were a single new opcode with the bodies combined.
648
If collecting opcode statistics, your choices are to either keep the
649
predictions turned-on and interpret the results as if some opcodes
650
had been combined or turn-off predictions so that the opcode frequency
651
counter updates for both opcodes.
632
654
#ifdef DYNAMIC_EXECUTION_PROFILE
715
737
an argument which depends on the situation.
716
738
The global trace function is also called
717
739
whenever an exception is detected. */
718
if (call_trace_protected(tstate->c_tracefunc,
740
if (call_trace_protected(tstate->c_tracefunc,
719
741
tstate->c_traceobj,
720
742
f, PyTrace_CALL, Py_None)) {
721
743
/* Trace function raised an error */
747
769
this wasn't always true before 2.3! PyFrame_New now sets
748
770
f->f_lasti to -1 (i.e. the index *before* the first instruction)
749
771
and YIELD_VALUE doesn't fiddle with f_lasti any more. So this
752
774
When the PREDICT() macros are enabled, some opcode pairs follow in
753
direct succession without updating f->f_lasti. A successful
775
direct succession without updating f->f_lasti. A successful
754
776
prediction effectively links the two codes together as if they
755
777
were a single new opcode; accordingly,f->f_lasti will point to
756
778
the first code in the pair (for instance, GET_ITER followed by
2184
2210
because it prevents detection of a control-break in tight loops like
2185
2211
"while 1: pass". Compile with this option turned-on when you need
2186
2212
the speed-up and do not need break checking inside tight loops (ones
2187
that contain only instructions ending with goto fast_next_opcode).
2213
that contain only instructions ending with goto fast_next_opcode).
2189
2215
goto fast_next_opcode;
2762
2789
PyString_AsString(co->co_name));
2765
/* XXX slow -- speed up using dictionary? */
2766
for (j = 0; j < co->co_argcount; j++) {
2767
PyObject *nm = PyTuple_GET_ITEM(
2768
co->co_varnames, j);
2792
/* Speed hack: do raw pointer compares. As names are
2793
normally interned this should almost always hit. */
2794
co_varnames = PySequence_Fast_ITEMS(co->co_varnames);
2795
for (j = 0; j < co->co_argcount; j++) {
2796
PyObject *nm = co_varnames[j];
2800
/* Slow fallback, just in case */
2801
for (j = 0; j < co->co_argcount; j++) {
2802
PyObject *nm = co_varnames[j];
2769
2803
int cmp = PyObject_RichCompareBool(
2770
2804
keyword, nm, Py_EQ);
2773
2807
else if (cmp < 0)
2788
2822
PyDict_SetItem(kwdict, keyword, value);
2791
if (GETLOCAL(j) != NULL) {
2792
PyErr_Format(PyExc_TypeError,
2793
"%.200s() got multiple "
2794
"values for keyword "
2795
"argument '%.400s'",
2796
PyString_AsString(co->co_name),
2797
PyString_AsString(keyword));
2826
if (GETLOCAL(j) != NULL) {
2827
PyErr_Format(PyExc_TypeError,
2828
"%.200s() got multiple "
2829
"values for keyword "
2830
"argument '%.400s'",
2831
PyString_AsString(co->co_name),
2832
PyString_AsString(keyword));
2804
2838
if (argcount < co->co_argcount) {
2805
2839
int m = co->co_argcount - defcount;