=================================================================== RCS file: /home/cvs/OpenXM/src/kan96xx/Kan/stackmachine.c,v retrieving revision 1.25 retrieving revision 1.41 diff -u -p -r1.25 -r1.41 --- OpenXM/src/kan96xx/Kan/stackmachine.c 2004/09/12 10:22:50 1.25 +++ OpenXM/src/kan96xx/Kan/stackmachine.c 2016/03/31 05:27:34 1.41 @@ -1,7 +1,9 @@ -/* $OpenXM: OpenXM/src/kan96xx/Kan/stackmachine.c,v 1.24 2004/09/12 08:55:36 takayama Exp $ */ +/* $OpenXM: OpenXM/src/kan96xx/Kan/stackmachine.c,v 1.40 2016/03/31 03:22:54 takayama Exp $ */ /* stackmachin.c */ #include +#include +#include #include "datatype.h" #include "stackm.h" #include "extern.h" @@ -9,7 +11,17 @@ #include "kclass.h" #include #include +#include "mysig.h" +/* The msys2 seems to make a buffer overflow of EnvOfStackmachine[]. +The code +[(x) ring_of_differential_operators 11] define_ring +( Dx*(x+Dx) ) /ff set +causes the segfault because Mp_zero is borken. Is it a bug of msys2? +Anyway, the following definition seems to be a workaround. 2015.09 +Singnals do not work properly on msys2. (gcc -dM -E ... to see macros defs) +See stackm.h +*/ /* #define OPERAND_STACK_SIZE 2000 */ #define OPERAND_STACK_SIZE 30000 @@ -52,7 +64,7 @@ struct context *CurrentContextp = &StandardContext; struct context *PrimitiveContextp = &StandardContext; -static struct object ObjTmp; /* for poor compiler */ +static struct object ObjTmp = OINIT; /* for poor compiler */ int Calling_ctrlC_hook = 0; @@ -74,6 +86,7 @@ static strToInteger(char *); static power(int s,int i); static void pstack(void); static struct object executableStringToExecutableArray(char *str); +static int isThereExecutableArrayOnStack(int n); extern int SerialCurrent; extern int QuoteMode; @@ -86,6 +99,10 @@ int OXlockSaved = 0; char *UD_str; int UD_attr; +struct object *MsgStackTraceInArrayp = NULL; +char *MsgStackTrace = NULL; +char *MsgSourceTrace = NULL; + struct object * newObject() { struct object *r; @@ -94,13 +111,14 @@ struct object * newObject() r->tag = 0; (r->lc).ival = 0; (r->rc).ival = 0; + r->attr = NULL; return(r); } struct object newObjectArray(size) int size; { - struct object rob; + struct object rob = OINIT; struct object *op; if (size < 0) return(NullObject); if (size > 0) { @@ -295,6 +313,12 @@ int putUserDictionary2(str,h0,h1,attr,dic) } return(0); } + if (OR_ATTR_FOR_ALL_WORDS & attr) { + for (i=0; i=0; i--) { @@ -645,7 +695,7 @@ struct object showSystemDictionary(int f) { int maxl; char format[1000]; int nl; - struct object rob; + struct object rob = OINIT; rob = NullObject; if (f != 0) { rob = newObjectArray(Sdp); @@ -718,7 +768,7 @@ static struct object executableStringToExecutableArray char *s; { struct tokens *tokenArray; - struct object ob; + struct object ob = OINIT; int i; int size; tokenArray = decomposeToTokens(s,&size); @@ -737,7 +787,7 @@ static struct object executableStringToExecutableArray /**************** stack machine **************************/ void scanner() { struct tokens token; - struct object ob; + struct object ob = OINIT; extern int Quiet; extern void ctrlC(); int tmp, status; @@ -747,20 +797,21 @@ void scanner() { extern int InSendmsg2; int infixOn = 0; struct tokens infixToken; + extern int RestrictedMode, RestrictedMode_saved; getokenSM(INIT); initSystemDictionary(); #if defined(__CYGWIN__) - if (sigsetjmp(EnvOfStackMachine,1)) { + if (MYSIGSETJMP(EnvOfStackMachine,1)) { #else - if (setjmp(EnvOfStackMachine)) { + if (MYSETJMP(EnvOfStackMachine)) { #endif /* do nothing in the case of error */ fprintf(stderr,"An error or interrupt in reading macros, files and command strings.\n"); exit(10); } else { } - if (signal(SIGINT,SIG_IGN) != SIG_IGN) { - signal(SIGINT,ctrlC); + if (mysignal(SIGINT,SIG_IGN) != SIG_IGN) { + mysignal(SIGINT,ctrlC); } /* setup quiet mode or not */ @@ -815,9 +866,9 @@ void scanner() { for (;;) { #if defined(__CYGWIN__) - if (jval=sigsetjmp(EnvOfStackMachine,1)) { + if (jval=MYSIGSETJMP(EnvOfStackMachine,1)) { #else - if (jval=setjmp(EnvOfStackMachine)) { + if (jval=MYSETJMP(EnvOfStackMachine)) { #endif /* *** The following does not work properly. **** if (jval == 2) { @@ -830,8 +881,9 @@ void scanner() { fprintf(Fstack,"\nscanner> "); } if (!Calling_ctrlC_hook) { /* to avoid recursive call of ctrlC-hook. */ - Calling_ctrlC_hook = 1; + Calling_ctrlC_hook = 1; RestrictedMode = 0; KSexecuteString(" ctrlC-hook "); /* Execute User Defined functions. */ + RestrictedMode = RestrictedMode_saved; } Calling_ctrlC_hook = 0; KSexecuteString(" (Computation is interrupted.) "); /* move to ctrlC-hook? */ @@ -862,9 +914,11 @@ void ctrlC(sig) extern int SGClock; extern int UserCtrlC; extern int OXlock; + extern int RestrictedMode, RestrictedMode_saved; - signal(sig,SIG_IGN); + mysignal(sig,SIG_IGN); /* see 133p */ + RestrictedMode = RestrictedMode_saved; cancelAlarm(); if (sig == SIGALRM) { fprintf(stderr,"ctrlC by SIGALRM\n"); @@ -873,7 +927,7 @@ void ctrlC(sig) if (SGClock) { UserCtrlC = 1; fprintf(stderr,"ctrl-c is locked because of gc.\n"); - signal(sig,ctrlC); if (sig == SIGALRM) alarm((unsigned int)10); + mysignal(sig,ctrlC); if (sig == SIGALRM) alarm((unsigned int)10); return; } if (OXlock) { @@ -882,11 +936,11 @@ void ctrlC(sig) if (UserCtrlC > 3) { fprintf(stderr,"OK. You are eager to cancel the computation.\n"); fprintf(stderr,"You should close the ox communication cannel.\n"); - signal(SIGINT,ctrlC); + mysignal(SIGINT,ctrlC); unlockCtrlCForOx(); } fprintf(stderr,"ctrl-c is locked because of ox lock %d.\n",UserCtrlC); - signal(sig,ctrlC); if (sig == SIGALRM) alarm((unsigned int)10); + mysignal(sig,ctrlC); if (sig == SIGALRM) alarm((unsigned int)10); return; } if (ErrorMessageMode != 1) { @@ -908,18 +962,18 @@ void ctrlC(sig) It SOMETIMES makes core dump. */ getokenSM(INIT); /* It might fix the bug above. 1992/11/14 */ - signal(SIGINT,ctrlC); + mysignal(SIGINT,ctrlC); #if defined(__CYGWIN__) - siglongjmp(EnvOfStackMachine,2); + MYSIGLONGJMP(EnvOfStackMachine,2); #else - longjmp(EnvOfStackMachine,2); /* returns 2 for ctrl-C */ + MYLONGJMP(EnvOfStackMachine,2); /* returns 2 for ctrl-C */ #endif } int executeToken(token) struct tokens token; { - struct object ob; + struct object ob = OINIT; int primitive; int size; int status; @@ -927,7 +981,10 @@ int executeToken(token) extern int WarningMessageMode; extern int Strict; extern int InSendmsg2; + extern int RestrictedMode, RestrictedMode_saved; + int localRestrictedMode_saved; + localRestrictedMode_saved = 0; if (GotoP) { /* for goto */ if (token.kind == ID && isLiteral(token.token)) { if (strcmp(&((token.token)[1]),GotoLabel) == 0) { @@ -981,7 +1038,23 @@ int executeToken(token) if (ob.tag >= 0) { /* there is a definition in the user dictionary */ if (ob.tag == SexecutableArray) { + if (RestrictedMode) { + if (UD_attr & ATTR_EXPORT) { + localRestrictedMode_saved = RestrictedMode; RestrictedMode = 0; + if (isThereExecutableArrayOnStack(5)) { + int i; + for (i=0; i<5; i++) { (void) Kpop(); } + errorStackmachine("Executable array is on the argument stack (restricted mode). They are automatically removed.\n"); + } + }else{ + tracePushName(token.token); + errorStackmachine("You cannot execute this function in restricted mode.\n"); + } + } + status = executeExecutableArray(ob,token.token,0); + + if (localRestrictedMode_saved) RestrictedMode = localRestrictedMode_saved; if ((status & STATUS_BREAK) || (status < 0)) return status; }else { Kpush(ob); @@ -1002,21 +1075,24 @@ int executeToken(token) return(0); /* normal exit.*/ } } - if (WarningMessageMode == 1 || WarningMessageMode == 2) { + { char tmpc[1024]; if (strlen(token.token) < 900) { - sprintf(tmpc,"\n%%Warning: The identifier <<%s>> is not in the system dictionary\n%% nor in the user dictionaries. Push NullObject.\n",token.token); - }else {strcpy(tmpc,"Warning: identifier is not in the dictionaries.");} - pushErrorStack(KnewErrorPacket(SerialCurrent,-1,tmpc)); + sprintf(tmpc,"\n>>Warning: The identifier <<%s>> is not in the system dictionary\n>> nor in the user dictionaries. Push NullObject.\n",token.token); + }else {strcpy(tmpc,"\n>>Warning: identifier is not in the dictionaries.\n");} + /* do not use %% in a string. tmpc will be used as fprintf(stderr,tmpc); */ + if (WarningMessageMode == 1 || WarningMessageMode == 2) { + pushErrorStack(KnewErrorPacket(SerialCurrent,-1,tmpc)); + } + if (WarningMessageMode != 1) { + fprintf(Fstack,"%s",tmpc); + /*fprintf(Fstack,"(%d,%d)\n",h0,h1);*/ + } + if (Strict) { + errorStackmachine(tmpc); + } + Kpush(NullObject); } - if (WarningMessageMode != 1) { - fprintf(Fstack,"\n%%Warning: The identifier <<%s>> is not in the system dictionary\n%% nor in the user dictionaries. Push NullObject.\n",token.token); - /*fprintf(Fstack,"(%d,%d)\n",h0,h1);*/ - } - if (Strict) { - errorStackmachine("Warning: identifier is not in the dictionaries"); - } - Kpush(NullObject); } } } else if (token.kind == EXECUTABLE_STRING) { @@ -1049,7 +1125,11 @@ errorStackmachine(str) char message0[1024]; char *message; extern int ErrorMessageMode; + extern int RestrictedMode, RestrictedMode_saved; + RestrictedMode = RestrictedMode_saved; cancelAlarm(); + MsgStackTrace = NULL; + MsgSourceTrace = NULL; if (ErrorMessageMode == 1 || ErrorMessageMode == 2) { pushErrorStack(KnewErrorPacket(SerialCurrent,-1,str)); } @@ -1083,7 +1163,9 @@ errorStackmachine(str) fprintf(stderr,str); } fprintf(stderr,"\n"); - (void) traceShowStack(); + MsgStackTraceInArrayp = traceNameStackToArrayp(); + MsgStackTrace = traceShowStack(); + MsgSourceTrace = traceShowScannerBuf(); } traceClearStack(); if (GotoP) { @@ -1093,7 +1175,7 @@ errorStackmachine(str) stdOperandStack(); contextControl(CCRESTORE); getokenSM(INIT); /* It might fix the bug. 1996/3/10 */ /* fprintf(stderr,"Now, Long jump!\n"); */ - longjmp(EnvOfStackMachine,1); + MYLONGJMP(EnvOfStackMachine,1); } warningStackmachine(str) @@ -1121,7 +1203,7 @@ KSexecuteString(s) char *s; { struct tokens token; - struct object ob; + struct object ob = OINIT; int tmp; extern int CatchCtrlC; int jval; @@ -1131,22 +1213,23 @@ KSexecuteString(s) jmp_buf saved_EnvOfStackMachine; void (*sigfunc)(); int localCatchCtrlC ; + extern int RestrictedMode, RestrictedMode_saved; localCatchCtrlC = CatchCtrlC; /* If CatchCtrlC is rewrited in this program, we crash. So, we use localCatchCtrlC. */ if (localCatchCtrlC) { - sigfunc = signal(SIGINT,SIG_IGN); - signal(SIGINT,ctrlC); + sigfunc = mysignal(SIGINT,SIG_IGN); + mysignal(SIGINT,ctrlC); } if (KSPushEnvMode) { *saved_EnvOfStackMachine = *EnvOfStackMachine; #if defined(__CYGWIN__) - if (jval = sigsetjmp(EnvOfStackMachine,1)) { + if (jval = MYSIGSETJMP(EnvOfStackMachine,1)) { #else - if (jval = setjmp(EnvOfStackMachine)) { + if (jval = MYSETJMP(EnvOfStackMachine)) { #endif *EnvOfStackMachine = *saved_EnvOfStackMachine; if (jval == 2) { @@ -1155,10 +1238,11 @@ KSexecuteString(s) } } recursive--; - if (localCatchCtrlC) { signal(SIGINT, sigfunc); } + if (localCatchCtrlC) { mysignal(SIGINT, sigfunc); } if (!Calling_ctrlC_hook) { - Calling_ctrlC_hook = 1; + Calling_ctrlC_hook = 1; RestrictedMode = 0; KSexecuteString(" ctrlC-hook "); /* Execute User Defined functions. */ + RestrictedMode_saved; } Calling_ctrlC_hook = 0; KSexecuteString(" (Computation is interrupted.) "); /* move to ctrlC-hook?*/ @@ -1167,9 +1251,9 @@ KSexecuteString(s) }else{ if (recursive == 0) { #if defined(__CYGWIN__) - if (jval=sigsetjmp(EnvOfStackMachine,1)) { + if (jval=MYSIGSETJMP(EnvOfStackMachine,1)) { #else - if (jval=setjmp(EnvOfStackMachine)) { + if (jval=MYSETJMP(EnvOfStackMachine)) { #endif if (jval == 2) { if (ErrorMessageMode == 1 || ErrorMessageMode == 2) { @@ -1177,10 +1261,11 @@ KSexecuteString(s) } } recursive = 0; - if (localCatchCtrlC) { signal(SIGINT, sigfunc); } + if (localCatchCtrlC) { mysignal(SIGINT, sigfunc); } if (!Calling_ctrlC_hook) { - Calling_ctrlC_hook = 1; + Calling_ctrlC_hook = 1; RestrictedMode = 0; KSexecuteString(" ctrlC-hook "); /* Execute User Defined functions. */ + RestrictedMode = RestrictedMode_saved; } Calling_ctrlC_hook = 0; Calling_ctrlC_hook = 0; @@ -1203,14 +1288,14 @@ KSexecuteString(s) executePrimitive(ob); recursive--; if (KSPushEnvMode) *EnvOfStackMachine = *saved_EnvOfStackMachine; - if (localCatchCtrlC) { signal(SIGINT, sigfunc); } + if (localCatchCtrlC) { mysignal(SIGINT, sigfunc); } return(0); } KSdefineMacros() { struct tokens token; int tmp; - struct object ob; + struct object ob = OINIT; if (StandardMacros && (strlen(SMacros))) { token.kind = EXECUTABLE_STRING; token.tflag = 0; @@ -1231,7 +1316,7 @@ KSdefineMacros() { void KSstart() { struct tokens token; int tmp; - struct object ob; + struct object ob = OINIT; extern int Quiet; stackmachine_init(); KinitKan(); @@ -1240,7 +1325,7 @@ void KSstart() { /* The following line may cause a core dump, if you do not setjmp properly after calling KSstart().*/ /* - if (setjmp(EnvOfStackMachine)) { + if (MYSETJMP(EnvOfStackMachine)) { fprintf(stderr,"KSstart(): An error or interrupt in reading macros, files and command strings.\n"); exit(10); } else { } */ @@ -1285,7 +1370,7 @@ struct object KSpeek(k) { char *KSstringPop() { /* pop a string */ - struct object rob; + struct object rob = OINIT; rob = Kpop(); if (rob.tag == Sdollar) { return(rob.lc.str); @@ -1325,6 +1410,10 @@ char *KSpopBinary(int *size) { return((char *)NULL); } +struct object KSnewObjectArray(int k) { + return newObjectArray(k); +} + int pushErrorStack(struct object obj) { if (CurrentOperandStack == &ErrorStack) { @@ -1355,8 +1444,8 @@ struct object popErrorStack(void) { } char *popErrorStackByString(void) { - struct object obj; - struct object eobj; + struct object obj = OINIT; + struct object eobj = OINIT; eobj = popErrorStack(); if (ectag(eobj) != CLASSNAME_ERROR_PACKET) { return(NULL); @@ -1385,7 +1474,7 @@ int KScheckErrorStack(void) struct object KnewErrorPacket(int serial,int no,char *message) { - struct object obj; + struct object obj = OINIT; struct object *myop; char *s; /* Set extended tag. */ @@ -1407,7 +1496,7 @@ struct object KnewErrorPacket(int serial,int no,char * struct object KnewErrorPacketObj(struct object ob1) { - struct object obj; + struct object obj = OINIT; struct object *myop; char *s; /* Set extended tag. */ @@ -1506,8 +1595,8 @@ int KSstackPointer() { } struct object KSdupErrors() { - struct object rob; - struct object ob; + struct object rob = OINIT; + struct object ob = OINIT; int i; int n; int m; @@ -1534,7 +1623,7 @@ struct object KSdupErrors() { void cancelAlarm() { alarm((unsigned int) 0); - signal(SIGALRM,SIG_DFL); + mysignal(SIGALRM,SIG_DFL); } /* back-trace */ @@ -1564,6 +1653,17 @@ char *tracePopName(void) { if (TraceNameStackp <= 0) return (char *) NULL; return TraceNameStack[--TraceNameStackp]; } +struct object *traceNameStackToArrayp(void) { + int n,i; + struct object *op; + op = sGC_malloc(sizeof(struct object)); + n = TraceNameStackp; if (n < 0) n = 0; + *op = newObjectArray(n); + for (i=0; i TRACE_MSG_SIZE) { - /* fprintf(stderr,"p=%d, TraceNameStackp=%d, strlen(t)=%d, t=%s\n",p,TraceNameStackp,strlen(t),t); */ + }else if ((strlen(t) + p) > (TRACE_MSG_SIZE-10)) { + /* fprintf(stderr,"p=%d, TraceNameStackp=%d, strlen(t)=%d, t=%s\n",p,TraceNameStackp,strlen(t),t); */ strcpy(&(s[p])," ..."); break; }