more exception handling.

This commit is contained in:
Vitor Santos Costa 2018-04-16 14:54:53 +01:00
parent df961cbd62
commit abb328abf0
15 changed files with 262 additions and 283 deletions

View File

@ -284,6 +284,7 @@ Yap_InitConstExps(void)
} }
} }
/* This routine is called from Restore to make sure we have the same arithmetic operators */ /* This routine is called from Restore to make sure we have the same arithmetic operators */
int int
Yap_ReInitConstExps(void) Yap_ReInitConstExps(void)

View File

@ -972,7 +972,7 @@ p_unary_is( USES_REGS1 )
{ /* X is Y */ { /* X is Y */
Term t = Deref(ARG2); Term t = Deref(ARG2);
Term top; Term top;
yap_error_number err; bool go;
if (IsVarTerm(t)) { if (IsVarTerm(t)) {
Yap_EvalError(INSTANTIATION_ERROR, t, "unbound unary operator"); Yap_EvalError(INSTANTIATION_ERROR, t, "unbound unary operator");
@ -980,22 +980,12 @@ p_unary_is( USES_REGS1 )
} }
Yap_ClearExs(); Yap_ClearExs();
top = Yap_Eval(Deref(ARG3)); top = Yap_Eval(Deref(ARG3));
if ((err=Yap_FoundArithError())) {
Yap_EvalError(err,ARG3,"X is op(Y): error in Y ");
return FALSE;
}
if (IsIntTerm(t)) { if (IsIntTerm(t)) {
Term tout; Term tout;
Int i; Int i;
i = IntegerOfTerm(t); i = IntegerOfTerm(t);
tout = eval1(i, top PASS_REGS); tout = eval1(i, top PASS_REGS);
if ((err=Yap_FoundArithError())) {
Functor f = Yap_MkFunctor( Yap_NameOfUnaryOp(i), 1 );
Term t = Yap_MkApplTerm( f, 1, &top );
Yap_EvalError(err, t ,"error in %s/1 ", RepAtom(NameOfFunctor(f))->StrOfAE);
return FALSE;
}
return Yap_unify_constant(ARG1,tout); return Yap_unify_constant(ARG1,tout);
} else if (IsAtomTerm(t)) { } else if (IsAtomTerm(t)) {
Atom name = AtomOfTerm(t); Atom name = AtomOfTerm(t);
@ -1008,13 +998,13 @@ p_unary_is( USES_REGS1 )
RepAtom(name)->StrOfAE); RepAtom(name)->StrOfAE);
return FALSE; return FALSE;
} }
do {
out= eval1(p->FOfEE, top PASS_REGS); out= eval1(p->FOfEE, top PASS_REGS);
if ((err=Yap_FoundArithError())) { go = Yap_CheckArithError();
return FALSE; } while(go);
}
return Yap_unify_constant(ARG1,out); return Yap_unify_constant(ARG1,out);
} }
return(FALSE); return false;
} }
static Int static Int

View File

@ -1146,28 +1146,16 @@ static Int
p_binary_is( USES_REGS1 ) p_binary_is( USES_REGS1 )
{ /* X is Y */ { /* X is Y */
Term t = Deref(ARG2); Term t = Deref(ARG2);
Term t1, t2; Term t1, t2, tout;
yap_error_number err;
if (IsVarTerm(t)) { if (IsVarTerm(t)) {
Yap_ArithError(INSTANTIATION_ERROR,t, "VAR(X , Y)"); Yap_ArithError(INSTANTIATION_ERROR,t, "VAR(X , Y)");
return(FALSE); return(FALSE);
} }
Yap_ClearExs(); Yap_ClearExs();
t1 = Yap_Eval(Deref(ARG3)); t1 = Yap_Eval(Deref(ARG3));
if ((err = Yap_FoundArithError())) {
Atom name;
if (IsIntTerm(t)) {
Int i = IntOfTerm(t);
name = Yap_NameOfBinaryOp(i);
} else {
name = AtomOfTerm(Deref(ARG2));
}
Yap_EvalError(err,ARG3,"X is ~s/2: error in first argument ", RepAtom(name)->StrOfAE);
return FALSE;
}
t2 = Yap_Eval(Deref(ARG4)); t2 = Yap_Eval(Deref(ARG4));
if ((err=Yap_FoundArithError())) { {
Atom name; Atom name;
if (IsIntTerm(t)) { if (IsIntTerm(t)) {
Int i = IntOfTerm(t); Int i = IntOfTerm(t);
@ -1175,47 +1163,35 @@ p_binary_is( USES_REGS1 )
} else { } else {
name = AtomOfTerm(Deref(ARG2)); name = AtomOfTerm(Deref(ARG2));
} }
Yap_EvalError(err,ARG3,"X is ~s/2: error in first argument ", RepAtom(name)->StrOfAE);
return FALSE;
} }
if (IsIntTerm(t)) { if (IsIntTerm(t)) {
Int i = IntOfTerm(t); Int i = IntOfTerm(t);
Term tout = eval2(i, t1, t2 PASS_REGS); bool go;
if ((err = Yap_FoundArithError()) != YAP_NO_ERROR) { do {
Term ts[2], terr; go = false;
Atom name = Yap_NameOfBinaryOp( i ); tout = eval2(i, t1, t2 PASS_REGS);
Functor f = Yap_MkFunctor( name, 2 ); go = Yap_CheckArithError();
ts[0] = t1; } while (go);
ts[1] = t2;
terr = Yap_MkApplTerm( f, 2, ts );
Yap_EvalError(err, terr ,"error in %s/2 ", RepAtom(name)->StrOfAE);
return FALSE;
}
return Yap_unify_constant(ARG1,tout); return Yap_unify_constant(ARG1,tout);
} }
if (IsAtomTerm(t)) { if (IsAtomTerm(t)) {
Atom name = AtomOfTerm(t); Atom name = AtomOfTerm(t);
ExpEntry *p; ExpEntry *p;
Term out; bool go;
int j;
if (EndOfPAEntr(p = RepExpProp(Yap_GetExpProp(name, 2)))) { if (EndOfPAEntr(p = RepExpProp(Yap_GetExpProp(name, 2)))) {
Yap_EvalError(TYPE_ERROR_EVALUABLE, takeIndicator(t), Yap_EvalError(TYPE_ERROR_EVALUABLE, t, "`%s ", name->StrOfAE
"functor %s/2 for arithmetic expression", );
RepAtom(name)->StrOfAE);
P = FAILCODE;
return(FALSE);
} }
out= eval2(p->FOfEE, t1, t2 PASS_REGS); j = p->FOfEE;
if ((err = Yap_FoundArithError()) != YAP_NO_ERROR) {
Term ts[2], terr; do {
Functor f = Yap_MkFunctor( name, 2 ); go = false;
ts[0] = t1; Yap_ClearExs();
ts[1] = t2; tout = eval2(j, t1, t2 PASS_REGS);
terr = Yap_MkApplTerm( f, 2, ts ); go = Yap_CheckArithError();
Yap_EvalError(err, terr ,"error in ~s/2 ", RepAtom(name)->StrOfAE); } while (go);
return FALSE; return Yap_unify_constant(ARG1,tout);
}
return Yap_unify_constant(ARG1,out);
} }
return FALSE; return FALSE;
} }
@ -1226,31 +1202,22 @@ static Int
do_arith23(arith2_op op USES_REGS) do_arith23(arith2_op op USES_REGS)
{ /* X is Y */ { /* X is Y */
Term t = Deref(ARG1); Term t = Deref(ARG1);
Int out; bool go;
Term t1, t2; Term t1, t2, out;
yap_error_number err;
Yap_ClearExs();
if (IsVarTerm(t)) { if (IsVarTerm(t)) {
Yap_EvalError(INSTANTIATION_ERROR,t, "X is Y"); Yap_EvalError(INSTANTIATION_ERROR,t, "X is Y");
return(FALSE); return(FALSE);
} }
t1 = Yap_Eval(t); do {
if (t1 == 0L) go = false;
return FALSE; Yap_ClearExs();
t1 = Yap_Eval(t);
t2 = Yap_Eval(Deref(ARG2)); t2 = Yap_Eval(Deref(ARG2));
if (t2 == 0L)
return FALSE;
out= eval2(op, t1, t2 PASS_REGS); out= eval2(op, t1, t2 PASS_REGS);
if ((err=Yap_FoundArithError())) {
Term ts[2], t; go = Yap_CheckArithError();
Functor f = Yap_MkFunctor( Yap_NameOfBinaryOp(op), 2 ); } while (go);
ts[0] = t1;
ts[1] = t2;
t = Yap_MkApplTerm( f, 2, ts );
Yap_EvalError(err, t ,"error in ~s(Y,Z) ",Yap_NameOfBinaryOp(op));
return FALSE;
}
return Yap_unify_constant(ARG3,out); return Yap_unify_constant(ARG3,out);
} }
@ -1317,7 +1284,6 @@ p_binary_op_as_integer( USES_REGS1 )
if (IsAtomTerm(t)) { if (IsAtomTerm(t)) {
Atom name = AtomOfTerm(t); Atom name = AtomOfTerm(t);
ExpEntry *p; ExpEntry *p;
if (EndOfPAEntr(p = RepExpProp(Yap_GetExpProp(name, 2)))) { if (EndOfPAEntr(p = RepExpProp(Yap_GetExpProp(name, 2)))) {
return Yap_unify(ARG1,ARG2); return Yap_unify(ARG1,ARG2);
} }

View File

@ -3940,11 +3940,11 @@ static void complete_lu_erase(LogUpdClause *clau) {
static void EraseLogUpdCl(LogUpdClause *clau) { static void EraseLogUpdCl(LogUpdClause *clau) {
PredEntry *ap; PredEntry *ap;
ap = clau->ClPred; ap = clau->ClPred;
/* no need to erase what has been erased */ /* no need to erase what has been erased */
if (!(clau->ClFlags & ErasedMask)) { if (!(clau->ClFlags & ErasedMask)) {
/* get ourselves out of the list */ clau->ClFlags |= ErasedMask;
/* get ourselves out of the list */
if (clau->ClNext != NULL) { if (clau->ClNext != NULL) {
clau->ClNext->ClPrev = clau->ClPrev; clau->ClNext->ClPrev = clau->ClPrev;
} }
@ -3968,7 +3968,6 @@ static void EraseLogUpdCl(LogUpdClause *clau) {
} }
ap->cs.p_code.NOfClauses--; ap->cs.p_code.NOfClauses--;
} }
clau->ClFlags |= ErasedMask;
#ifndef THREADS #ifndef THREADS
{ {
LogUpdClause *er_head = DBErasedList; LogUpdClause *er_head = DBErasedList;

View File

@ -264,7 +264,6 @@ bool Yap_Warning(const char *s, ...) {
(void)vsprintf(tmpbuf, fmt, ap); (void)vsprintf(tmpbuf, fmt, ap);
#endif #endif
} else { } else {
Yap_popErrorContext(false);
return false; return false;
} }
va_end(ap); va_end(ap);
@ -272,14 +271,12 @@ bool Yap_Warning(const char *s, ...) {
fprintf(stderr, "warning message: %s\n", tmpbuf); fprintf(stderr, "warning message: %s\n", tmpbuf);
LOCAL_DoingUndefp = false; LOCAL_DoingUndefp = false;
LOCAL_PrologMode &= ~InErrorMode; LOCAL_PrologMode &= ~InErrorMode;
Yap_popErrorContext(false);
return false; return false;
} }
ts[1] = MkAtomTerm(AtomWarning); ts[1] = MkAtomTerm(AtomWarning);
ts[0] = MkAtomTerm(Yap_LookupAtom(tmpbuf)); ts[0] = MkAtomTerm(Yap_LookupAtom(tmpbuf));
rc = Yap_execute_pred(pred, ts, true PASS_REGS); rc = Yap_execute_pred(pred, ts, true PASS_REGS);
Yap_popErrorContext(false);
LOCAL_PrologMode &= ~InErrorMode; LOCAL_PrologMode &= ~InErrorMode;
return rc; return rc;
} }
@ -553,11 +550,12 @@ static char tmpbuf[YAP_BUF_SIZE];
#include "YapErrors.h" #include "YapErrors.h"
void Yap_pushErrorContext(yap_error_descriptor_t *new_error) { bool Yap_pushErrorContext(bool pass, yap_error_descriptor_t *new_error) {
memset(new_error, 0, sizeof(yap_error_descriptor_t)); yap_error_number err = LOCAL_ActiveError->errorNo;
new_error->top_error = LOCAL_ActiveError; memset(new_error, 0, sizeof(yap_error_descriptor_t));
LOCAL_ActiveError = new_error; new_error->top_error = LOCAL_ActiveError;
LOCAL_PrologMode = UserMode; LOCAL_ActiveError = new_error;
return true;
} }
/* static void */ /* static void */
@ -568,17 +566,24 @@ void Yap_pushErrorContext(yap_error_descriptor_t *new_error) {
/* LOCAL_ActiveError->top_error = bf; */ /* LOCAL_ActiveError->top_error = bf; */
/* } */ /* } */
yap_error_descriptor_t *Yap_popErrorContext(bool mdnew, bool pass) {
yap_error_descriptor_t *Yap_popErrorContext(bool pass) { yap_error_descriptor_t *e =LOCAL_ActiveError;
if (pass && LOCAL_ActiveError->top_error->errorNo == YAP_NO_ERROR && // last block
LOCAL_ActiveError->errorNo != YAP_NO_ERROR) LOCAL_ActiveError = e->top_error;
memcpy(LOCAL_ActiveError->top_error, LOCAL_ActiveError, if (e->errorNo) {
sizeof(yap_error_descriptor_t)); if (!LOCAL_ActiveError->errorNo && pass) {
yap_error_descriptor_t *new_error = LOCAL_ActiveError; memcpy(LOCAL_ActiveError, e, sizeof(*LOCAL_ActiveError));
LOCAL_ActiveError = LOCAL_ActiveError->top_error; } else {
return new_error; return e;
}
} else {
if (e->errorNo)
return e;
}
return NULL;
} }
void Yap_ThrowError__(const char *file, const char *function, int lineno, void Yap_ThrowError__(const char *file, const char *function, int lineno,
yap_error_number type, Term where, ...) { yap_error_number type, Term where, ...) {
va_list ap; va_list ap;
@ -642,6 +647,82 @@ yamop *Yap_Error__(bool throw, const char *file, const char *function,
va_list ap; va_list ap;
char *fmt; char *fmt;
char s[MAXPATHLEN]; char s[MAXPATHLEN];
switch (type) {
case SYSTEM_ERROR_INTERNAL: {
fprintf(stderr, "%% Internal YAP Error: %s exiting....\n", tmpbuf);
// serious = true;
if (LOCAL_PrologMode & BootMode) {
fprintf(stderr, "%% YAP crashed while booting %s\n", tmpbuf);
} else {
Yap_detect_bug_location(P, FIND_PRED_FROM_ANYWHERE, YAP_BUF_SIZE);
if (tmpbuf[0]) {
fprintf(stderr, "%% Bug found while executing %s\n", tmpbuf);
}
#if HAVE_BACKTRACE
void *callstack[256];
int i;
int frames = backtrace(callstack, 256);
char **strs = backtrace_symbols(callstack, frames);
fprintf(stderr, "Execution stack:\n");
for (i = 0; i < frames; ++i) {
fprintf(stderr, " %s\n", strs[i]);
}
free(strs);
#endif
}
error_exit_yap(1);
}
case SYSTEM_ERROR_FATAL: {
fprintf(stderr, "%% Fatal YAP Error: %s exiting....\n", tmpbuf);
error_exit_yap(1);
}
case INTERRUPT_EVENT: {
error_exit_yap(1);
}
case ABORT_EVENT:
// fun = FunctorDollarVar;
// serious = true;
LOCAL_ActiveError->errorNo = ABORT_EVENT;
Yap_JumpToEnv();
P = FAILCODE;
LOCAL_PrologMode &= ~InErrorMode;
return P;
case CALL_COUNTER_UNDERFLOW_EVENT:
/* Do a long jump */
LOCAL_ReductionsCounterOn = FALSE;
LOCAL_PredEntriesCounterOn = FALSE;
LOCAL_RetriesCounterOn = FALSE;
LOCAL_ActiveError->errorNo = CALL_COUNTER_UNDERFLOW_EVENT;
Yap_JumpToEnv();
P = FAILCODE;
LOCAL_PrologMode &= ~InErrorMode;
return P;
case PRED_ENTRY_COUNTER_UNDERFLOW_EVENT:
/* Do a long jump */
LOCAL_ReductionsCounterOn = FALSE;
LOCAL_PredEntriesCounterOn = FALSE;
LOCAL_RetriesCounterOn = FALSE;
LOCAL_ActiveError->errorNo = PRED_ENTRY_COUNTER_UNDERFLOW_EVENT;
Yap_JumpToEnv();
P = FAILCODE;
LOCAL_PrologMode &= ~InErrorMode;
return P;
case RETRY_COUNTER_UNDERFLOW_EVENT:
/* Do a long jump */
LOCAL_ReductionsCounterOn = FALSE;
LOCAL_PredEntriesCounterOn = FALSE;
LOCAL_RetriesCounterOn = FALSE;
LOCAL_ActiveError->errorNo = RETRY_COUNTER_UNDERFLOW_EVENT;
Yap_JumpToEnv();
P = FAILCODE;
LOCAL_PrologMode &= ~InErrorMode;
return P;
default:
if (!Yap_pc_add_location(LOCAL_ActiveError, CP, B, ENV))
Yap_env_add_location(LOCAL_ActiveError, CP, B, ENV, 0);
break;
}
yap_error_number err = LOCAL_ActiveError->errorNo; yap_error_number err = LOCAL_ActiveError->errorNo;
/* disallow recursive error handling */ /* disallow recursive error handling */
if (LOCAL_PrologMode & InErrorMode && err) { if (LOCAL_PrologMode & InErrorMode && err) {
@ -751,81 +832,6 @@ if (type == INTERRUPT_EVENT) {
// DumpActiveGoals( USES_REGS1 ); // DumpActiveGoals( USES_REGS1 );
#endif /* DEBUG */ #endif /* DEBUG */
switch (type) {
case SYSTEM_ERROR_INTERNAL: {
fprintf(stderr, "%% Internal YAP Error: %s exiting....\n", tmpbuf);
// serious = true;
if (LOCAL_PrologMode & BootMode) {
fprintf(stderr, "%% YAP crashed while booting %s\n", tmpbuf);
} else {
Yap_detect_bug_location(P, FIND_PRED_FROM_ANYWHERE, YAP_BUF_SIZE);
if (tmpbuf[0]) {
fprintf(stderr, "%% Bug found while executing %s\n", tmpbuf);
}
#if HAVE_BACKTRACE
void *callstack[256];
int i;
int frames = backtrace(callstack, 256);
char **strs = backtrace_symbols(callstack, frames);
fprintf(stderr, "Execution stack:\n");
for (i = 0; i < frames; ++i) {
fprintf(stderr, " %s\n", strs[i]);
}
free(strs);
#endif
}
error_exit_yap(1);
}
case SYSTEM_ERROR_FATAL: {
fprintf(stderr, "%% Fatal YAP Error: %s exiting....\n", tmpbuf);
error_exit_yap(1);
}
case INTERRUPT_EVENT: {
error_exit_yap(1);
}
case ABORT_EVENT:
// fun = FunctorDollarVar;
// serious = true;
LOCAL_ActiveError->errorNo = ABORT_EVENT;
Yap_JumpToEnv();
P = FAILCODE;
LOCAL_PrologMode &= ~InErrorMode;
return P;
case CALL_COUNTER_UNDERFLOW_EVENT:
/* Do a long jump */
LOCAL_ReductionsCounterOn = FALSE;
LOCAL_PredEntriesCounterOn = FALSE;
LOCAL_RetriesCounterOn = FALSE;
LOCAL_ActiveError->errorNo = CALL_COUNTER_UNDERFLOW_EVENT;
Yap_JumpToEnv();
P = FAILCODE;
LOCAL_PrologMode &= ~InErrorMode;
return P;
case PRED_ENTRY_COUNTER_UNDERFLOW_EVENT:
/* Do a long jump */
LOCAL_ReductionsCounterOn = FALSE;
LOCAL_PredEntriesCounterOn = FALSE;
LOCAL_RetriesCounterOn = FALSE;
LOCAL_ActiveError->errorNo = PRED_ENTRY_COUNTER_UNDERFLOW_EVENT;
Yap_JumpToEnv();
P = FAILCODE;
LOCAL_PrologMode &= ~InErrorMode;
return P;
case RETRY_COUNTER_UNDERFLOW_EVENT:
/* Do a long jump */
LOCAL_ReductionsCounterOn = FALSE;
LOCAL_PredEntriesCounterOn = FALSE;
LOCAL_RetriesCounterOn = FALSE;
LOCAL_ActiveError->errorNo = RETRY_COUNTER_UNDERFLOW_EVENT;
Yap_JumpToEnv();
P = FAILCODE;
LOCAL_PrologMode &= ~InErrorMode;
return P;
default:
if (!Yap_pc_add_location(LOCAL_ActiveError, CP, B, ENV))
Yap_env_add_location(LOCAL_ActiveError, CP, B, ENV, 0);
break;
}
CalculateStackGap(PASS_REGS1); CalculateStackGap(PASS_REGS1);
#if DEBUG #if DEBUG
@ -1037,25 +1043,21 @@ yap_error_descriptor_t *event(Term t, yap_error_descriptor_t *i) {
yap_error_descriptor_t *Yap_UserError(Term t, yap_error_descriptor_t *i) { yap_error_descriptor_t *Yap_UserError(Term t, yap_error_descriptor_t *i) {
Term t1, t2;
t1 = ArgOfTerm(1, t);
t2 = ArgOfTerm(2, t);
char ename[65];
Term n = t; Term n = t;
bool found = false, wellformed = true; bool found = false, wellformed = true;
LOCAL_PrologMode = InErrorMode; if (!IsApplTerm(t) || FunctorOfTerm(t) != FunctorError) {
if (IsVarTerm(t)) { LOCAL_Error_TYPE = THROW_EVENT;
Yap_Error(INSTANTIATION_ERROR, t, "throw ball must be bound");
return false;
} else if (!IsApplTerm(t) || FunctorOfTerm(t) != FunctorError) {
LOCAL_Error_TYPE = THROW_EVENT;
LOCAL_ActiveError->errorClass = EVENT; LOCAL_ActiveError->errorClass = EVENT;
LOCAL_ActiveError->errorAsText = Yap_errorName(THROW_EVENT); LOCAL_ActiveError->errorAsText = Yap_errorName(THROW_EVENT);
LOCAL_ActiveError->classAsText = Yap_errorClassName(Yap_errorClass(THROW_EVENT)); LOCAL_ActiveError->classAsText = Yap_errorClassName(Yap_errorClass(THROW_EVENT));
LOCAL_ActiveError->errorRawTerm = Yap_SaveTerm(t); LOCAL_ActiveError->errorRawTerm = Yap_SaveTerm(t);
LOCAL_ActiveError->culprit = NULL; LOCAL_ActiveError->culprit = NULL;
} else { } else {
// LOCAL_Error_TYPE = ERROR_EVENT; char ename[65];
Term t1, t2;
t1 = ArgOfTerm(1, t);
t2 = ArgOfTerm(2, t);
// LOCAL_Error_TYPE = ERROR_EVENT;
i->errorNo = ERROR_EVENT; i->errorNo = ERROR_EVENT;
i->errorClass = EVENT; i->errorClass = EVENT;
if (IsApplTerm(t1)) { if (IsApplTerm(t1)) {

View File

@ -200,26 +200,17 @@ arithmetic_operators
/// @memberof is/2 /// @memberof is/2
static Int p_is(USES_REGS1) { /* X is Y */ static Int p_is(USES_REGS1) { /* X is Y */
Term out = TermNil; Term out = TermNil;
yap_error_number err; bool go;
Term t = Deref(ARG2); Term t = Deref(ARG2);
if (IsVarTerm(t)) { if (IsVarTerm(t)) {
Yap_ThrowError(INSTANTIATION_ERROR, t, "var(Y) in X is Y"); Yap_ThrowError(INSTANTIATION_ERROR, t, "var(Y) in X is Y");
return (FALSE); return (FALSE);
} }
Yap_ClearExs();
do { do {
go = false;
out = Yap_InnerEval(Deref(ARG2)); out = Yap_InnerEval(Deref(ARG2));
if ( (err = Yap_FoundArithError()) == YAP_NO_ERROR ) Yap_CheckArithError();
break; } while (go);
if (err == RESOURCE_ERROR_STACK) {
LOCAL_Error_TYPE = YAP_NO_ERROR;
if (!Yap_gcl(LOCAL_Error_Size, 2, ENV, CP)) {
Yap_EvalError(RESOURCE_ERROR_STACK, ARG2, LOCAL_ErrorMessage);
return FALSE;
}
}
} while (TRUE);
return Yap_unify_constant(ARG1, out); return Yap_unify_constant(ARG1, out);
} }

View File

@ -770,8 +770,10 @@ static Int Yap_ignore(Term t, bool fail USES_REGS) {
Int oENV = LCL0 - ENV; Int oENV = LCL0 - ENV;
Int oYENV = LCL0 - YENV; Int oYENV = LCL0 - YENV;
Int oB = LCL0 - (CELL *)B; Int oB = LCL0 - (CELL *)B;
yap_error_descriptor_t ctx;
bool newxp = Yap_pushErrorContext(true, &ctx);
bool rc = Yap_RunTopGoal(t, false); bool rc = Yap_RunTopGoal(t, false);
Yap_popErrorContext(newxp, true);
if (!rc) { if (!rc) {
complete_inner_computation((choiceptr)(LCL0 - oB)); complete_inner_computation((choiceptr)(LCL0 - oB));
// We'll pass it through // We'll pass it through
@ -948,7 +950,7 @@ static Int tag_cleanup(USES_REGS1) {
static Int cleanup_on_exit(USES_REGS1) { static Int cleanup_on_exit(USES_REGS1) {
choiceptr B0 = (choiceptr)(LCL0 - IntegerOfTerm(Deref(ARG1))), bp; choiceptr B0 = (choiceptr)(LCL0 - IntegerOfTerm(Deref(ARG1)));
Term task = Deref(ARG2); Term task = Deref(ARG2);
bool box = ArgOfTerm(1, task) == TermTrue; bool box = ArgOfTerm(1, task) == TermTrue;
Term cleanup = ArgOfTerm(3, task); Term cleanup = ArgOfTerm(3, task);
@ -2058,6 +2060,9 @@ bool Yap_JumpToEnv(void) {
/* This does very nasty stuff!!!!! */ /* This does very nasty stuff!!!!! */
static Int jump_env(USES_REGS1) { static Int jump_env(USES_REGS1) {
Term t = Deref(ARG1), t0 = t; Term t = Deref(ARG1), t0 = t;
if (IsVarTerm(t)) {
Yap_ThrowError(INSTANTIATION_ERROR, t, "throw/1 must be called instantiated");
}
// Yap_DebugPlWriteln(t); // Yap_DebugPlWriteln(t);
LOCAL_ActiveError = Yap_UserError(t0, LOCAL_ActiveError); LOCAL_ActiveError = Yap_UserError(t0, LOCAL_ActiveError);
bool out = JumpToEnv(PASS_REGS1); bool out = JumpToEnv(PASS_REGS1);

View File

@ -735,21 +735,21 @@ static size_t write_length(const unsigned char *s0, seq_tv_t *out USES_REGS) {
static Term write_number(unsigned char *s, seq_tv_t *out, static Term write_number(unsigned char *s, seq_tv_t *out,
bool error_on USES_REGS) { bool error_on USES_REGS) {
Term t; Term t;
yap_error_descriptor_t new_error; yap_error_descriptor_t new_error;
int i = push_text_stack(); int i = push_text_stack();
Yap_pushErrorContext(&new_error); bool new_rec = Yap_pushErrorContext(true,&new_error);
t = Yap_StringToNumberTerm((char *)s, &out->enc,true); t = Yap_StringToNumberTerm((char *)s, &out->enc,true);
pop_text_stack(i); pop_text_stack(i);
Yap_popErrorContext(error_on); Yap_popErrorContext(new_rec , true);
return t; return t;
} }
static Term string_to_term(void *s, seq_tv_t *out USES_REGS) { static Term string_to_term(void *s, seq_tv_t *out USES_REGS) {
Term o; Term o;
yap_error_descriptor_t new_error; yap_error_descriptor_t new_error;
Yap_pushErrorContext(&new_error); bool mdnew = Yap_pushErrorContext(true, &new_error);
o = out->val.t = Yap_BufferToTerm(s, TermNil); o = out->val.t = Yap_BufferToTerm(s, TermNil);
Yap_popErrorContext(true); Yap_popErrorContext(mdnew, true);
return o; return o;
} }

View File

@ -114,7 +114,7 @@ static char *send_tracer_message(char *start, char *name, arity_t arity,
return s; return s;
} }
#if defined(__GNUC__) #if defined(__GNUC__) || defined(__clang__)
unsigned long long vsc_count; unsigned long long vsc_count;
#else #else
unsigned long vsc_count; unsigned long vsc_count;
@ -202,6 +202,7 @@ bool low_level_trace__(yap_low_level_port port, PredEntry *pred, CELL *args) {
int l = push_text_stack(); int l = push_text_stack();
/* extern int gc_calls; */ /* extern int gc_calls; */
vsc_count++; vsc_count++;
//fprintf(stderr,"%p-%p\n",B->cp_tr,TR);
// if (HR < ASP ) return; // if (HR < ASP ) return;
// fif (vsc_count == 12534) jmp_deb( 2 ); // fif (vsc_count == 12534) jmp_deb( 2 );
char *buf = Malloc(512), *top = buf + 511, *b = buf; char *buf = Malloc(512), *top = buf + 511, *b = buf;

View File

@ -1231,9 +1231,9 @@ void Yap_plwrite(Term t, StreamDesc *mywrite, int max_depth, int flags,
wglb.Write_strings = flags & BackQuote_String_f; wglb.Write_strings = flags & BackQuote_String_f;
/* protect slots for portray */ /* protect slots for portray */
yap_error_descriptor_t ne; yap_error_descriptor_t ne;
Yap_pushErrorContext(&ne); bool err = Yap_pushErrorContext(true, &ne);
writeTerm(from_pointer(&t, &rwt, &wglb), priority, 1, FALSE, &wglb, &rwt); writeTerm(from_pointer(&t, &rwt, &wglb), priority, 1, FALSE, &wglb, &rwt);
Yap_popErrorContext(true); Yap_popErrorContext(err,true);
if (flags & New_Line_f) { if (flags & New_Line_f) {
if (flags & Fullstop_f) { if (flags & Fullstop_f) {
wrputc('.', wglb.stream); wrputc('.', wglb.stream);

View File

@ -1,19 +1,18 @@
/************************************************************************* /*************************************************************************
* * * *
* YAP Prolog @(#)YapEval.h 1.2 * YAP Prolog @(#)YapEval.h 1.2
* * * *
* Yap Prolog was developed at NCCUP - Universidade do Porto * * Yap Prolog was developed at NCCUP - Universidade do Porto *
* * * *
* Copyright L.Damas, V.S.Costa and Universidade do Porto 1985-1997 * * Copyright L.Damas, V.S.Costa and Universidade do Porto 1985-1997 *
* * * *
************************************************************************** **************************************************************************
* * * *
* File: YapEval.h * * File: YapEval.h
* Last rev: * ** Last rev: * mods:
* mods: * ** comments: arithmetical functions info *
* comments: arithmetical functions info * * *
* * *************************************************************************/
*************************************************************************/
/** /**
@ -165,7 +164,7 @@ overflow
* @addtogroup arithmetic_operators * @addtogroup arithmetic_operators
* @enum arith0_op constant operators * @enum arith0_op constant operators
* @brief specifies the available unary arithmetic operators * @brief specifies the available unary arithmetic operators
*/ */
typedef enum { typedef enum {
/** pi [ISO] /** pi [ISO]
@ -259,25 +258,25 @@ typedef enum {
*/ */
op_log, op_log,
/** log10( _X_ ) [ISO] /** log10( _X_ ) [ISO]
* *
* Decimal logarithm. * Decimal logarithm.
* *
* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~{.prolog} * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~{.prolog}
* ?- between(1, 10, I), Delta is log10(I*10) + log10(1/(I*10)), format('0 * ?- between(1, 10, I), Delta is log10(I*10) + log10(1/(I*10)), format('0
* == ~3g~n',[Delta]), fail. * == ~3g~n',[Delta]), fail.
* 0 == 0 * 0 == 0
* 0 == 0 * 0 == 0
* 0 == 0 * 0 == 0
* 0 == 0 * 0 == 0
* 0 == 0 * 0 == 0
* 0 == 0 * 0 == 0
* 0 == 0 * 0 == 0
* 0 == 0 * 0 == 0
* 0 == 2.22e-16 * 0 == 2.22e-16
* 0 == 0 * 0 == 0
* false. * false.
* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
*/ */
op_log10, op_log10,
op_sqrt, op_sqrt,
op_sin, op_sin,
@ -399,7 +398,6 @@ extern Term Yap_eval_atom(Int);
extern Term Yap_eval_unary(Int, Term); extern Term Yap_eval_unary(Int, Term);
extern Term Yap_eval_binary(Int, Term, Term); extern Term Yap_eval_binary(Int, Term, Term);
typedef struct eval_context { typedef struct eval_context {
Functor f; Functor f;
CELL *fp; CELL *fp;
@ -409,17 +407,31 @@ typedef struct eval_context {
extern Term Yap_InnerEval__(Term USES_REGS); extern Term Yap_InnerEval__(Term USES_REGS);
#define Yap_EvalError(id, t, ...) \ #define Yap_EvalError(id, t, ...) \
Yap_ThrowError__(__FILE__, __FUNCTION__, __LINE__, id, t, __VA_ARGS__) { \
eval_context_t *ctx = LOCAL_ctx; \
LOCAL_ctx = NULL; \
while (ctx) { \
*ctx->fp = (CELL)(ctx->f); \
ctx = ctx->p; \
} \
Yap_ThrowError__(__FILE__, __FUNCTION__, __LINE__, id, t, __VA_ARGS__); \
}
#define Yap_ArithError(id, t, ...) \ #define Yap_ArithError(id, t, ...) \
{ eval_context_t *ctx = LOCAL_ctx; LOCAL_ctx = NULL; while(ctx) {*ctx->fp = (CELL)(ctx->f); ctx = ctx->p; } \ { \
Yap_ThrowError__(__FILE__, __FUNCTION__, __LINE__, id, t, __VA_ARGS__);} eval_context_t *ctx = LOCAL_ctx; \
LOCAL_ctx = NULL; \
while (ctx) { \
*ctx->fp = (CELL)(ctx->f); \
ctx = ctx->p; \
} \
Yap_ThrowError__(__FILE__, __FUNCTION__, __LINE__, id, t, __VA_ARGS__); \
}
#define Yap_BinError(id) \ #define Yap_BinError(id) \
Yap_Error__(false, __FILE__, __FUNCTION__, __LINE__, id, 0L, "") Yap_Error__(false, __FILE__, __FUNCTION__, __LINE__, id, 0L, "")
#define Yap_AbsmiError(id) \ #define Yap_AbsmiError(id) \
Yap_ThrowError__( __FILE__, __FUNCTION__, __LINE__, id, 0L, "") Yap_ThrowError__(__FILE__, __FUNCTION__, __LINE__, id, 0L, "")
#include "inline-only.h" #include "inline-only.h"
@ -427,7 +439,28 @@ extern Term Yap_InnerEval__(Term USES_REGS);
#define Yap_InnerEval(x) Yap_InnerEval__(x PASS_REGS) #define Yap_InnerEval(x) Yap_InnerEval__(x PASS_REGS)
#define Yap_Eval(x) Yap_Eval__(x PASS_REGS) #define Yap_Eval(x) Yap_Eval__(x PASS_REGS)
#define Yap_FoundArithError() Yap_FoundArithError__(PASS_REGS1)
static inline bool Yap_CheckArithError(void)
{
bool on = false;
yap_error_number err;
if (LOCAL_Error_TYPE== RESOURCE_ERROR_STACK) {
LOCAL_Error_TYPE = YAP_NO_ERROR;
if (!Yap_gcl(LOCAL_Error_Size, 2, ENV, CP)) {
on = false;
Yap_ThrowError(RESOURCE_ERROR_STACK, ARG2, "while running arithmetic");
} else {
on = true;
}
};
if (trueGlobalPrologFlag(
ARITHMETIC_EXCEPTIONS_FLAG) &&
(err = Yap_MathException())) {
Yap_ThrowError(err,ARG2,"Math Error");
}
return on;
}
INLINE_ONLY inline EXTERN Term Yap_Eval__(Term t USES_REGS); INLINE_ONLY inline EXTERN Term Yap_Eval__(Term t USES_REGS);
@ -443,14 +476,6 @@ inline static void Yap_ClearExs(void) { feclearexcept(FE_ALL_EXCEPT); }
inline static void Yap_ClearExs(void) {} inline static void Yap_ClearExs(void) {}
#endif #endif
inline static yap_error_number Yap_FoundArithError__(USES_REGS1) {
if (LOCAL_Error_TYPE != YAP_NO_ERROR )
return LOCAL_Error_TYPE;
if (trueGlobalPrologFlag(
ARITHMETIC_EXCEPTIONS_FLAG)) // test support for exception
return Yap_MathException();
return YAP_NO_ERROR;
}
static inline Term takeIndicator(Term t) { static inline Term takeIndicator(Term t) {
Term ts[2]; Term ts[2];
@ -475,9 +500,7 @@ Atom Yap_NameOfBinaryOp(int i);
#define RFLOAT(v) return (MkFloatTerm(v)) #define RFLOAT(v) return (MkFloatTerm(v))
#define RBIG(v) return (Yap_MkBigIntTerm(v)) #define RBIG(v) return (Yap_MkBigIntTerm(v))
#define RERROR() \ #define RERROR() \
{ \ { return (0L); }
return (0L); \
}
static inline blob_type ETypeOfTerm(Term t) { static inline blob_type ETypeOfTerm(Term t) {
if (IsIntTerm(t)) if (IsIntTerm(t))
@ -608,18 +631,19 @@ __Yap_Mk64IntegerTerm(YAP_LONG_LONG i USES_REGS) {
} }
} }
inline static Term add_int(Int i, Int j USES_REGS) { inline static Term add_int(Int i, Int j USES_REGS) {
#if defined(__clang__) #if defined(__clang__)
Int w; Int w;
if (!__builtin_add_overflow(i,j,&w)) if (!__builtin_add_overflow(i, j, &w))
RINT(w); RINT(w);
return Yap_gmp_add_ints(i, j);; return Yap_gmp_add_ints(i, j);
;
#elif defined(__GNUC__) #elif defined(__GNUC__)
Int w; Int w;
if (!__builtin_add_overflow_p(i,j,w)) if (!__builtin_add_overflow_p(i, j, w))
RINT(w); RINT(w);
return Yap_gmp_add_ints(i, j);; return Yap_gmp_add_ints(i, j);
;
#elif USE_GMP #elif USE_GMP
UInt w = (UInt)i + (UInt)j; UInt w = (UInt)i + (UInt)j;
if (i > 0) { if (i > 0) {

View File

@ -247,7 +247,7 @@ extern yap_error_descriptor_t *Yap_env_add_location(yap_error_descriptor_t *t,vo
extern const char *Yap_errorName(yap_error_number e); extern const char *Yap_errorName(yap_error_number e);
extern const char *Yap_errorClassName(yap_error_class_number e); extern const char *Yap_errorClassName(yap_error_class_number e);
extern void Yap_pushErrorContext(yap_error_descriptor_t * new_error); extern bool Yap_pushErrorContext(bool pass, yap_error_descriptor_t *new_error);
extern yap_error_descriptor_t *Yap_popErrorContext(bool pass); extern yap_error_descriptor_t *Yap_popErrorContext(bool oerr, bool pass);
#endif #endif

View File

@ -991,7 +991,7 @@ Term Yap_read_term(int sno, Term opts, bool clause) {
yap_error_descriptor_t new; yap_error_descriptor_t new;
Yap_pushErrorContext(&new); bool err = Yap_pushErrorContext(true,&new);
int lvl = push_text_stack(); int lvl = push_text_stack();
parser_state_t state = YAP_START_PARSING; parser_state_t state = YAP_START_PARSING;
while (true) { while (true) {
@ -1000,7 +1000,7 @@ Term Yap_read_term(int sno, Term opts, bool clause) {
state = initParser(opts, &fe, &re, sno, clause); state = initParser(opts, &fe, &re, sno, clause);
if (state == YAP_PARSING_FINISHED) { if (state == YAP_PARSING_FINISHED) {
pop_text_stack(lvl); pop_text_stack(lvl);
Yap_popErrorContext(true); Yap_popErrorContext(err, true);
return 0; return 0;
} }
break; break;
@ -1031,8 +1031,8 @@ Term Yap_read_term(int sno, Term opts, bool clause) {
#if EMACS #if EMACS
first_char = tokstart->TokPos; first_char = tokstart->TokPos;
#endif /* EMACS */ #endif /* EMACS */
Yap_popErrorContext(true);
pop_text_stack(lvl); pop_text_stack(lvl);
Yap_popErrorContext(err, true);
if (LOCAL_Error_TYPE != YAP_NO_ERROR) { if (LOCAL_Error_TYPE != YAP_NO_ERROR) {
Yap_Error(LOCAL_Error_TYPE, ARG1, LOCAL_ErrorMessage); Yap_Error(LOCAL_Error_TYPE, ARG1, LOCAL_ErrorMessage);
} }
@ -1040,7 +1040,7 @@ Term Yap_read_term(int sno, Term opts, bool clause) {
} }
} }
} }
Yap_popErrorContext(true); Yap_popErrorContext(err,true);
pop_text_stack(lvl); pop_text_stack(lvl);
return 0; return 0;
} }

View File

@ -299,17 +299,14 @@ bool Yap_WriteTerm(int output_stream, Term t, Term opts USES_REGS) {
Yap_Error(LOCAL_Error_TYPE, opts, NULL); Yap_Error(LOCAL_Error_TYPE, opts, NULL);
return false; return false;
} }
yap_error_descriptor_t new;
Yap_pushErrorContext(&new);
yhandle_t mySlots = Yap_StartSlots(); yhandle_t mySlots = Yap_StartSlots();
LOCK(GLOBAL_Stream[output_stream].streamlock); LOCK(GLOBAL_Stream[output_stream].streamlock);
write_term(output_stream, t, args PASS_REGS); write_term(output_stream, t, args PASS_REGS);
UNLOCK(GLOBAL_Stream[output_stream].streamlock); UNLOCK(GLOBAL_Stream[output_stream].streamlock);
free(args); free(args);
Yap_CloseSlots(mySlots); Yap_CloseSlots(mySlots);
Yap_popErrorContext(true);
return (TRUE); return (TRUE);
} }

View File

@ -965,11 +965,14 @@ catch(G, C, A) :-
). ).
'$catch'(_,C,A) :- '$catch'(_,C,A) :-
'$get_exception'(C), '$get_exception'(C),
'$run_catch'(A, C). !,
'$run_catch'(A, C).
'$catch'(_,_C,A) :-
throw(A).
% variable throws are user-handled. % variable throws are user-handled.
'$run_catch'(G,E) :- '$run_catch'(G,E) :-
E = '$VAR'(_), var(E),
!, !,
call(G ). call(G ).
'$run_catch'(abort,_) :- '$run_catch'(abort,_) :-