diff options
author | Chris Liddell <chris.liddell@artifex.com> | 2016-10-25 11:16:13 +0100 |
---|---|---|
committer | Chris Liddell <chris.liddell@artifex.com> | 2016-10-25 15:37:36 +0100 |
commit | 2f3679b53632c5b7b9e9a416311ae82f36645fc9 (patch) | |
tree | c8cc20dadef2631f3fba28053a243be42ce3f3d3 /psi/interp.c | |
parent | 3f09e7022e39412af98602cdfe22adfb34a7fa63 (diff) | |
download | ghostpdl-2f3679b53632c5b7b9e9a416311ae82f36645fc9.tar.gz |
Bug 697220(2): Fix returning execstackoverflow
In one case of returning execstackoverflow from the main interpreter loop,
we'd set the interpreter's private count value of objects to execute, *before*
we try to push the ref array onto the stack. As a consequence the object
count was for the new array, but the top of the exec stack was still the
previous array. This meant when we sync'ed the interpreter loop's internal
state with the state in the interpreter context, the size of the top object
on the exec stack could be wrong, causing problems in the garbager - especially
if the length was too long.
To resolve, move the exec stack bounds check before the count gets set.
Diffstat (limited to 'psi/interp.c')
-rw-r--r-- | psi/interp.c | 8 |
1 files changed, 6 insertions, 2 deletions
diff --git a/psi/interp.c b/psi/interp.c index 0ce633f03..654d9dba0 100644 --- a/psi/interp.c +++ b/psi/interp.c @@ -1156,6 +1156,12 @@ x_sub: INCR(x_sub); prst: /* Prepare to call the procedure (array) in *pvalue. */ store_state(iesp); pr: /* Call the array in *pvalue. State has been stored. */ + /* We want to do this check before assigning icount so icount is correct + * in the event of a gs_error_execstackoverflow + */ + if (iesp >= estop) { + return_with_error_iref(gs_error_execstackoverflow); + } if ((icount = r_size(pvalue) - 1) <= 0) { if (icount < 0) goto up; /* 0-element proc */ @@ -1163,8 +1169,6 @@ x_sub: INCR(x_sub); if (--(*ticks_left) > 0) goto top; } - if (iesp >= estop) - return_with_error_iref(gs_error_execstackoverflow); ++iesp; /* Do a ref_assign, but also set iref. */ iesp->tas = pvalue->tas; |