@@ -87,6 +87,7 @@ static object *apply_subscript PROTO((object *, object *));
8787static object * loop_subscript PROTO ((object * , object * ) );
8888static int slice_index PROTO ((object * , int , int * ) );
8989static object * apply_slice PROTO ((object * , object * , object * ) );
90+ static object * build_slice PROTO ((object * , object * , object * ) );
9091static int assign_subscript PROTO ((object * , object * , object * ) );
9192static int assign_slice PROTO ((object * , object * , object * , object * ) );
9293static int cmp_exception PROTO ((object * , object * ) );
@@ -187,6 +188,8 @@ restore_thread(x)
187188 thread (the main thread) ever takes things out of the queue.
188189*/
189190
191+ static int ticker = 0 ; /* main loop counter to do periodic things */
192+
190193#define NPENDINGCALLS 32
191194static struct {
192195 int (* func ) PROTO ((ANY * ));
@@ -215,6 +218,7 @@ Py_AddPendingCall(func, arg)
215218 pendingcalls [i ].func = func ;
216219 pendingcalls [i ].arg = arg ;
217220 pendinglast = j ;
221+ ticker = 0 ; /* Signal main loop */
218222 busy = 0 ;
219223 /* XXX End critical section */
220224 return 0 ;
@@ -225,11 +229,15 @@ Py_MakePendingCalls()
225229{
226230 static int busy = 0 ;
227231#ifdef WITH_THREAD
228- if (get_thread_ident () != main_thread )
232+ if (get_thread_ident () != main_thread ) {
233+ ticker = 0 ; /* We're not done yet */
229234 return 0 ;
235+ }
230236#endif
231- if (busy )
237+ if (busy ) {
238+ ticker = 0 ; /* We're not done yet */
232239 return 0 ;
240+ }
233241 busy = 1 ;
234242 for (;;) {
235243 int i ;
@@ -243,6 +251,7 @@ Py_MakePendingCalls()
243251 pendingfirst = (i + 1 ) % NPENDINGCALLS ;
244252 if (func (arg ) < 0 ) {
245253 busy = 0 ;
254+ ticker = 0 ; /* We're not done yet */
246255 return -1 ;
247256 }
248257 }
@@ -281,6 +290,12 @@ eval_code(co, globals, locals)
281290
282291/* Interpreter main loop */
283292
293+ #ifndef MAX_RECURSION_DEPTH
294+ #define MAX_RECURSION_DEPTH 10000
295+ #endif
296+
297+ static int recursion_depth = 0 ;
298+
284299static object *
285300eval_code2 (co , globals , locals ,
286301 args , argcount , kws , kwcount , defs , defcount , owner )
@@ -355,6 +370,13 @@ eval_code2(co, globals, locals,
355370#define SETLOCAL (i , value ) do { XDECREF(GETLOCAL(i)); \
356371 GETLOCAL(i) = value; } while (0)
357372
373+ #ifdef USE_STACKCHECK
374+ if (recursion_depth %10 == 0 && PyOS_CheckStack ()) {
375+ err_setstr (MemoryError , "Stack overflow" );
376+ return NULL ;
377+ }
378+ #endif
379+
358380 if (globals == NULL ) {
359381 err_setstr (SystemError , "eval_code2: NULL globals" );
360382 return NULL ;
@@ -514,6 +536,14 @@ eval_code2(co, globals, locals,
514536 }
515537 }
516538
539+ if (++ recursion_depth > MAX_RECURSION_DEPTH ) {
540+ -- recursion_depth ;
541+ err_setstr (RuntimeError , "Maximum recursion depth exceeded" );
542+ current_frame = f -> f_back ;
543+ DECREF (f );
544+ return NULL ;
545+ }
546+
517547 next_instr = GETUSTRINGVALUE (f -> f_code -> co_code );
518548 stack_pointer = f -> f_valuestack ;
519549
@@ -522,22 +552,23 @@ eval_code2(co, globals, locals,
522552 x = None ; /* Not a reference, just anything non-NULL */
523553
524554 for (;;) {
525- static int ticker ;
526-
527555 /* Do periodic things.
528556 Doing this every time through the loop would add
529557 too much overhead (a function call per instruction).
530- So we do it only every Nth instruction. */
531-
532- if (pendingfirst != pendinglast ) {
533- if (Py_MakePendingCalls () < 0 ) {
534- why = WHY_EXCEPTION ;
535- goto on_error ;
536- }
537- }
558+ So we do it only every Nth instruction.
559+
560+ The ticker is reset to zero if there are pending
561+ calls (see Py_AddPendingCalls() and
562+ Py_MakePendingCalls() above). */
538563
539564 if (-- ticker < 0 ) {
540565 ticker = sys_checkinterval ;
566+ if (pendingfirst != pendinglast ) {
567+ if (Py_MakePendingCalls () < 0 ) {
568+ why = WHY_EXCEPTION ;
569+ goto on_error ;
570+ }
571+ }
541572 if (sigcheck ()) {
542573 why = WHY_EXCEPTION ;
543574 goto on_error ;
@@ -1630,7 +1661,22 @@ eval_code2(co, globals, locals,
16301661 }
16311662 PUSH (x );
16321663 break ;
1633-
1664+
1665+ case BUILD_SLICE :
1666+ if (oparg == 3 )
1667+ w = POP ();
1668+ else
1669+ w = NULL ;
1670+ v = POP ();
1671+ u = POP ();
1672+ x = build_slice (u ,v ,w );
1673+ DECREF (u );
1674+ DECREF (v );
1675+ XDECREF (w );
1676+ PUSH (x );
1677+ break ;
1678+
1679+
16341680 default :
16351681 fprintf (stderr ,
16361682 "XXX lineno: %d, opcode: %d\n" ,
@@ -1793,6 +1839,7 @@ eval_code2(co, globals, locals,
17931839
17941840 current_frame = f -> f_back ;
17951841 DECREF (f );
1842+ -- recursion_depth ;
17961843
17971844 return retval ;
17981845}
@@ -2548,6 +2595,13 @@ slice_index(v, isize, pi)
25482595 return 0 ;
25492596}
25502597
2598+ static object *
2599+ build_slice (u , v , w ) /* u:v:w */
2600+ object * u , * v , * w ;
2601+ {
2602+ return PySlice_New (u ,v ,w );
2603+ }
2604+
25512605static object *
25522606apply_slice (u , v , w ) /* return u[v:w] */
25532607 object * u , * v , * w ;
0 commit comments