mirror of
https://github.com/python/cpython.git
synced 2025-07-09 20:35:26 +00:00
Changes for slice and ellipses
This commit is contained in:
parent
3ecebf1732
commit
8861b74445
6 changed files with 389 additions and 215 deletions
|
@ -87,6 +87,7 @@ static object *apply_subscript PROTO((object *, object *));
|
|||
static object *loop_subscript PROTO((object *, object *));
|
||||
static int slice_index PROTO((object *, int, int *));
|
||||
static object *apply_slice PROTO((object *, object *, object *));
|
||||
static object *build_slice PROTO((object *, object *, object *));
|
||||
static int assign_subscript PROTO((object *, object *, object *));
|
||||
static int assign_slice PROTO((object *, object *, object *, object *));
|
||||
static int cmp_exception PROTO((object *, object *));
|
||||
|
@ -187,6 +188,8 @@ restore_thread(x)
|
|||
thread (the main thread) ever takes things out of the queue.
|
||||
*/
|
||||
|
||||
static int ticker = 0; /* main loop counter to do periodic things */
|
||||
|
||||
#define NPENDINGCALLS 32
|
||||
static struct {
|
||||
int (*func) PROTO((ANY *));
|
||||
|
@ -215,6 +218,7 @@ Py_AddPendingCall(func, arg)
|
|||
pendingcalls[i].func = func;
|
||||
pendingcalls[i].arg = arg;
|
||||
pendinglast = j;
|
||||
ticker = 0; /* Signal main loop */
|
||||
busy = 0;
|
||||
/* XXX End critical section */
|
||||
return 0;
|
||||
|
@ -225,11 +229,15 @@ Py_MakePendingCalls()
|
|||
{
|
||||
static int busy = 0;
|
||||
#ifdef WITH_THREAD
|
||||
if (get_thread_ident() != main_thread)
|
||||
if (get_thread_ident() != main_thread) {
|
||||
ticker = 0; /* We're not done yet */
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
if (busy)
|
||||
if (busy) {
|
||||
ticker = 0; /* We're not done yet */
|
||||
return 0;
|
||||
}
|
||||
busy = 1;
|
||||
for (;;) {
|
||||
int i;
|
||||
|
@ -243,6 +251,7 @@ Py_MakePendingCalls()
|
|||
pendingfirst = (i + 1) % NPENDINGCALLS;
|
||||
if (func(arg) < 0) {
|
||||
busy = 0;
|
||||
ticker = 0; /* We're not done yet */
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
@ -281,6 +290,12 @@ eval_code(co, globals, locals)
|
|||
|
||||
/* Interpreter main loop */
|
||||
|
||||
#ifndef MAX_RECURSION_DEPTH
|
||||
#define MAX_RECURSION_DEPTH 10000
|
||||
#endif
|
||||
|
||||
static int recursion_depth = 0;
|
||||
|
||||
static object *
|
||||
eval_code2(co, globals, locals,
|
||||
args, argcount, kws, kwcount, defs, defcount, owner)
|
||||
|
@ -355,6 +370,13 @@ eval_code2(co, globals, locals,
|
|||
#define SETLOCAL(i, value) do { XDECREF(GETLOCAL(i)); \
|
||||
GETLOCAL(i) = value; } while (0)
|
||||
|
||||
#ifdef USE_STACKCHECK
|
||||
if (recursion_depth%10 == 0 && PyOS_CheckStack()) {
|
||||
err_setstr(MemoryError, "Stack overflow");
|
||||
return NULL;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (globals == NULL) {
|
||||
err_setstr(SystemError, "eval_code2: NULL globals");
|
||||
return NULL;
|
||||
|
@ -514,6 +536,14 @@ eval_code2(co, globals, locals,
|
|||
}
|
||||
}
|
||||
|
||||
if (++recursion_depth > MAX_RECURSION_DEPTH) {
|
||||
--recursion_depth;
|
||||
err_setstr(RuntimeError, "Maximum recursion depth exceeded");
|
||||
current_frame = f->f_back;
|
||||
DECREF(f);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
next_instr = GETUSTRINGVALUE(f->f_code->co_code);
|
||||
stack_pointer = f->f_valuestack;
|
||||
|
||||
|
@ -522,22 +552,23 @@ eval_code2(co, globals, locals,
|
|||
x = None; /* Not a reference, just anything non-NULL */
|
||||
|
||||
for (;;) {
|
||||
static int ticker;
|
||||
|
||||
/* Do periodic things.
|
||||
Doing this every time through the loop would add
|
||||
too much overhead (a function call per instruction).
|
||||
So we do it only every Nth instruction. */
|
||||
|
||||
if (pendingfirst != pendinglast) {
|
||||
if (Py_MakePendingCalls() < 0) {
|
||||
why = WHY_EXCEPTION;
|
||||
goto on_error;
|
||||
}
|
||||
}
|
||||
So we do it only every Nth instruction.
|
||||
|
||||
The ticker is reset to zero if there are pending
|
||||
calls (see Py_AddPendingCalls() and
|
||||
Py_MakePendingCalls() above). */
|
||||
|
||||
if (--ticker < 0) {
|
||||
ticker = sys_checkinterval;
|
||||
if (pendingfirst != pendinglast) {
|
||||
if (Py_MakePendingCalls() < 0) {
|
||||
why = WHY_EXCEPTION;
|
||||
goto on_error;
|
||||
}
|
||||
}
|
||||
if (sigcheck()) {
|
||||
why = WHY_EXCEPTION;
|
||||
goto on_error;
|
||||
|
@ -1630,7 +1661,22 @@ eval_code2(co, globals, locals,
|
|||
}
|
||||
PUSH(x);
|
||||
break;
|
||||
|
||||
|
||||
case BUILD_SLICE:
|
||||
if (oparg == 3)
|
||||
w = POP();
|
||||
else
|
||||
w = NULL;
|
||||
v = POP();
|
||||
u = POP();
|
||||
x = build_slice(u,v,w);
|
||||
DECREF(u);
|
||||
DECREF(v);
|
||||
XDECREF(w);
|
||||
PUSH(x);
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
fprintf(stderr,
|
||||
"XXX lineno: %d, opcode: %d\n",
|
||||
|
@ -1793,6 +1839,7 @@ eval_code2(co, globals, locals,
|
|||
|
||||
current_frame = f->f_back;
|
||||
DECREF(f);
|
||||
--recursion_depth;
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
@ -2548,6 +2595,13 @@ slice_index(v, isize, pi)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static object *
|
||||
build_slice(u, v, w) /* u:v:w */
|
||||
object *u, *v, *w;
|
||||
{
|
||||
return PySlice_New(u,v,w);
|
||||
}
|
||||
|
||||
static object *
|
||||
apply_slice(u, v, w) /* return u[v:w] */
|
||||
object *u, *v, *w;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue