Branch: Tag:

2004-03-12

2004-03-12 21:58:28 by Martin Stjernholm <mast@lysator.liu.se>

Separated the return address from Pike_fp->pc. pc always points to the
current opcode now, which makes everything a lot simpler. This fixes
off-by-one bugs that could occur for the innermost line in backtraces when
machine code is used.

Rev: src/builtin.cmod:1.108
Rev: src/interpret.h:1.124
Rev: src/interpret_functions.h:1.127

2:   || This file is part of Pike. For copyright information see COPYRIGHT.   || Pike is distributed under GPL, LGPL and MPL. See the file COPYING   || for more information. - || $Id: interpret_functions.h,v 1.126 2003/09/11 19:23:54 mast Exp $ + || $Id: interpret_functions.h,v 1.127 2004/03/12 21:58:28 mast Exp $   */      /*
158:    \    DO_IF_DEBUG(if (t_flag > 5) \    fprintf(stderr, "Returning to 0x%p\n", \ -  Pike_fp->pc)); \ -  DO_JUMP_TO(Pike_fp->pc); \ +  Pike_fp->return_addr)); \ +  DO_JUMP_TO(Pike_fp->return_addr); \    } \    DO_IF_DEBUG(if (t_flag > 5) \    fprintf(stderr, "Inter return\n")); \
1194:    DO_DUMB_RETURN;    case 2:    /* Escape catch, continue after the escape instruction. */ -  DO_JUMP_TO(Pike_fp->pc); +  DO_JUMP_TO(Pike_fp->return_addr);    break;    default:    DOJUMP();
1203:   });      OPCODE0_RETURN(F_ESCAPE_CATCH, "escape catch", 0, { -  Pike_fp->pc = PROG_COUNTER; +  Pike_fp->return_addr = PROG_COUNTER;    INTER_ESCAPE_CATCH;   });      OPCODE0_RETURN(F_EXIT_CATCH, "exit catch", 0, {    push_undefined(); -  Pike_fp->pc = PROG_COUNTER; +  Pike_fp->return_addr = PROG_COUNTER;    INTER_ESCAPE_CATCH;   });   
1773:   OPCODE1_ALIAS(F_SSCANF, "sscanf", 0, o_sscanf);      #define MKAPPLY(OP,OPCODE,NAME,TYPE, ARG2, ARG3) \ - OP(PIKE_CONCAT(F_,OPCODE),NAME, I_PC_AT_NEXT, { \ - Pike_fp->pc=PROG_COUNTER; \ + OP(PIKE_CONCAT(F_,OPCODE),NAME, 0, { \ + Pike_fp->return_addr=PROG_COUNTER; \   if(low_mega_apply(TYPE,DO_NOT_WARN((INT32)(Pike_sp - *--Pike_mark_sp)), \    ARG2, ARG3)) \   { \
1783:   } \   }); \    \ - OP(PIKE_CONCAT3(F_,OPCODE,_AND_POP),NAME " & pop", I_PC_AT_NEXT, { \ -  Pike_fp->pc=PROG_COUNTER; \ + OP(PIKE_CONCAT3(F_,OPCODE,_AND_POP),NAME " & pop", 0, { \ +  Pike_fp->return_addr=PROG_COUNTER; \    if(low_mega_apply(TYPE, DO_NOT_WARN((INT32)(Pike_sp - *--Pike_mark_sp)), \    ARG2, ARG3)) \    { \
1814:    \   MKAPPLY(OP,OPCODE,NAME,TYPE, ARG2, ARG3) \    \ - OP(PIKE_CONCAT(F_MARK_,OPCODE),"mark, " NAME, I_PC_AT_NEXT, { \ -  Pike_fp->pc=PROG_COUNTER; \ + OP(PIKE_CONCAT(F_MARK_,OPCODE),"mark, " NAME, 0, { \ +  Pike_fp->return_addr=PROG_COUNTER; \    if(low_mega_apply(TYPE,0, \    ARG2, ARG3)) \    { \
1824:    } \   }); \    \ - OP(PIKE_CONCAT3(F_MARK_,OPCODE,_AND_POP),"mark, " NAME " & pop", I_PC_AT_NEXT, { \ -  Pike_fp->pc=PROG_COUNTER; \ + OP(PIKE_CONCAT3(F_MARK_,OPCODE,_AND_POP),"mark, " NAME " & pop", 0, { \ +  Pike_fp->return_addr=PROG_COUNTER; \    if(low_mega_apply(TYPE, 0, \    ARG2, ARG3)) \    { \
1860:      MKAPPLY(OPCODE0,CALL_FUNCTION,"call function",APPLY_STACK, 0,0);    - OPCODE1(F_CALL_OTHER,"call other", I_PC_AT_NEXT, { + OPCODE1(F_CALL_OTHER,"call other", 0, {    INT32 args=DO_NOT_WARN((INT32)(Pike_sp - *--Pike_mark_sp));    struct svalue *s=Pike_sp-args; -  Pike_fp->pc=PROG_COUNTER; +  Pike_fp->return_addr=PROG_COUNTER;    if(s->type == T_OBJECT)    {    struct object *o=s->u.object;
1912:    }   });    - OPCODE1(F_CALL_OTHER_AND_POP,"call other & pop", I_PC_AT_NEXT, { + OPCODE1(F_CALL_OTHER_AND_POP,"call other & pop", 0, {    INT32 args=DO_NOT_WARN((INT32)(Pike_sp - *--Pike_mark_sp));    struct svalue *s=Pike_sp-args; -  Pike_fp->pc=PROG_COUNTER; +  Pike_fp->return_addr=PROG_COUNTER;    if(s->type == T_OBJECT)    {    struct object *o=s->u.object;
2115:    new_frame->refs=1; \    new_frame->next=Pike_fp; \    \ -  Pike_fp->pc = (PIKE_OPCODE_T *)(((INT32 *)PROG_COUNTER) + 1); \ +  Pike_fp->return_addr = (PIKE_OPCODE_T *)(((INT32 *)PROG_COUNTER) + 1); \    addr = PROG_COUNTER+GET_JUMP(); \    \    new_frame->num_locals = READ_INCR_BYTE(addr); \
2153:   }while(0)      /* Assume that the number of arguments is correct */ - OPCODE1_JUMP(F_COND_RECUR, "recur if not overloaded", I_PC_AT_NEXT, { + OPCODE1_JUMP(F_COND_RECUR, "recur if not overloaded", 0, {    struct program *p = Pike_fp->current_object->prog;    PIKE_OPCODE_T *addr = (PIKE_OPCODE_T *)(((INT32 *)PROG_COUNTER) + 1); -  Pike_fp->pc=addr; +  Pike_fp->return_addr=addr;       /* Test if the function is overloaded.    *