diff options
Diffstat (limited to 'interpret.h')
-rw-r--r-- | interpret.h | 27 |
1 files changed, 13 insertions, 14 deletions
diff --git a/interpret.h b/interpret.h index 3bb4532e..9d7b423e 100644 --- a/interpret.h +++ b/interpret.h @@ -23,13 +23,19 @@ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA */ +/* + * If "r" is a field, valref should normally be > 1, because the field is + * created initially with valref 1, and valref should be bumped when it is + * pushed onto the stack by Op_field_spec. On the other hand, if we are + * assigning to $n, then Op_store_field calls unref(*lhs) before assigning + * the new value, so that decrements valref. So if the RHS is a field with + * valref 1, that effectively means that this is an assignment like "$n = $n", + * so a no-op, other than triggering $0 reconstitution. + */ #define UNFIELD(l, r) \ { \ /* if was a field, turn it into a var */ \ - if ((r->flags & FIELD) == 0) { \ - l = r; \ - } else if (r->valref == 1) { \ - r->flags &= ~FIELD; \ + if ((r->flags & MALLOC) != 0 || r->valref == 1) { \ l = r; \ } else { \ l = dupnode(r); \ @@ -129,13 +135,10 @@ top: case Op_push_i: m = pc->memory; if (! do_traditional && (m->flags & INTLSTR) != 0) { - char *orig, *trans, save; + char *orig, *trans; - save = m->stptr[m->stlen]; - m->stptr[m->stlen] = '\0'; orig = m->stptr; trans = dgettext(TEXTDOMAIN, orig); - m->stptr[m->stlen] = save; m = make_string(trans, strlen(trans)); } else UPREF(m); @@ -357,12 +360,8 @@ uninitialized_scalar: lhs = r_get_field(t1, (Func_ptr *) 0, true); decr_sp(); DEREF(t1); - /* only for $0, up ref count */ - if (*lhs == fields_arr[0]) { - r = *lhs; - UPREF(r); - } else - r = dupnode(*lhs); + r = *lhs; + UPREF(r); PUSH(r); break; |