error propagation

This commit is contained in:
Vitor Santos Costa 2018-05-14 16:03:02 +01:00
parent 3369e0085c
commit 65fa980773
15 changed files with 79 additions and 40 deletions

View File

@ -2334,7 +2334,7 @@ X_API void *YAP_RepStreamFromId(int sno) { return GLOBAL_Stream + sno; }
X_API void YAP_CloseAllOpenStreams(void) {
BACKUP_H();
Yap_CloseStreams(FALSE);
Yap_CloseStreams();
RECOVER_H();
}

View File

@ -1427,15 +1427,18 @@ static Int execute_depth_limit(USES_REGS1) {
static bool exec_absmi(bool top, yap_reset_t reset_mode USES_REGS) {
int lval = 0, out;
Int OldBorder = LOCAL_CBorder;
// yap_error_descriptor_t *err_info= LOCAL_ActiveError;
LOCAL_CBorder = LCL0 - ENV;
sigjmp_buf signew, *sighold = LOCAL_RestartEnv;
LOCAL_RestartEnv = &signew;
int i = AllocLevel();
if /* top &&*/( (lval = sigsetjmp(signew, 1)) != 0) {
switch (lval) {
case 1: { /* restart */
/* otherwise, SetDBForThrow will fail entering critical mode */
// LOCAL_ActiveError = err_info;
pop_text_stack(0);
LOCAL_PrologMode = UserMode;
/* find out where to cut to */
/* siglongjmp resets the TR hardware register */
@ -1454,12 +1457,14 @@ static bool exec_absmi(bool top, yap_reset_t reset_mode USES_REGS) {
}
break;
case 2: {
// LOCAL_ActiveError = err_info;
/* arithmetic exception */
/* must be done here, otherwise siglongjmp will clobber all the
* registers
*/
/* reset the registers so that we don't have trash in abstract
* machine */
pop_text_stack(i);
Yap_set_fpu_exceptions(
getAtomicGlobalPrologFlag(ARITHMETIC_EXCEPTIONS_FLAG));
P = (yamop *) FAILCODE;
@ -1467,6 +1472,8 @@ static bool exec_absmi(bool top, yap_reset_t reset_mode USES_REGS) {
}
break;
case 3: { /* saved state */
// LOCAL_ActiveError = err_info;
pop_text_stack(i);
LOCAL_CBorder = OldBorder;
LOCAL_RestartEnv = sighold;
LOCAL_PrologMode = UserMode;
@ -1476,6 +1483,7 @@ static bool exec_absmi(bool top, yap_reset_t reset_mode USES_REGS) {
/* abort */
/* can be called from anywhere, must reset registers,
*/
// LOCAL_ActiveError = err_info;
while (B) {
LOCAL_ActiveError->errorNo = ABORT_EVENT;
Yap_JumpToEnv();
@ -1483,6 +1491,7 @@ static bool exec_absmi(bool top, yap_reset_t reset_mode USES_REGS) {
LOCAL_PrologMode = UserMode;
P = (yamop *) FAILCODE;
LOCAL_RestartEnv = sighold;
pop_text_stack(i);
return false;
break;
case 5:
@ -1490,12 +1499,15 @@ static bool exec_absmi(bool top, yap_reset_t reset_mode USES_REGS) {
// but we should inform the caller on what happened.
// Yap_regp = old_rs;
// LOCAL_ActiveError = err_info;
restore_TR();
restore_B();
/* H is not so important, because we're gonna backtrack */
restore_H();
/* set stack */
Yap_JumpToEnv();
Yap_CloseTemporaryStreams();
pop_text_stack(i);
ASP = (CELL *) PROTECT_FROZEN_B(B);
if (B == NULL || B->cp_b == NULL || (CELL*)(B->cp_b) > LCL0 - LOCAL_CBorder) {

View File

@ -1478,7 +1478,7 @@ void Yap_exit(int value) {
run_halt_hooks(value);
Yap_ShutdownLoadForeign();
}
Yap_CloseStreams(false);
Yap_CloseStreams();
Yap_CloseReadline();
#if USE_SYSTEM_MALLOC
#endif

View File

@ -559,7 +559,7 @@ static Int do_save(int mode USES_REGS) {
Yap_Error(TYPE_ERROR_LIST, t1, "save/1");
return FALSE;
}
Yap_CloseStreams(TRUE);
Yap_CloseStreams();
if ((splfild = open_file(LOCAL_FileNameBuf, O_WRONLY | O_CREAT)) < 0) {
Yap_Error(SYSTEM_ERROR_INTERNAL,
MkAtomTerm(Yap_LookupAtom(LOCAL_FileNameBuf)),
@ -1322,7 +1322,7 @@ static int commit_to_saved_state(const char *s, CELL *Astate, CELL *ATrail,
strcpy(tmp, Yap_AbsoluteFile(s, true));
fprintf(stderr, "%% Restoring file %s\n", tmp);
}
Yap_CloseStreams(TRUE);
Yap_CloseStreams();
}
#ifdef DEBUG_RESTORE4
/*

View File

@ -667,7 +667,7 @@ static Term float_send(char *s, int sign) {
#endif
{
CACHE_REGS
return (MkEvalFl(f));
return MkFloatTerm(f);
}
}
@ -969,7 +969,8 @@ static Term get_num(int *chp, int *chbuffp, StreamDesc *st, int sign) {
*sp++ = ch;
ch = getchr(st);
if (!my_isxdigit(ch, 'F', 'f')) {
Yap_InitError(SYNTAX_ERROR, TermNil, "empty hexadecimal number 0x%C",ch) ;
Yap_syntax_error(NULL, st-GLOBAL_Stream);
Yap_ThrowError(SYNTAX_ERROR, TermNil, "empty hexadecimal number 0x%C",ch) ;
return 0;
}
while (my_isxdigit(ch, 'F', 'f')) {
@ -992,17 +993,19 @@ static Term get_num(int *chp, int *chbuffp, StreamDesc *st, int sign) {
base = 8;
ch = getchr(st);
if (ch < '0' || ch > '7') {
Yap_InitError(SYNTAX_ERROR, TermNil, "empty octal number 0b%C", ch) ;
Yap_syntax_error(NULL, st-GLOBAL_Stream);
Yap_ThrowError(SYNTAX_ERROR, TermNil, "empty octal number 0b%C", ch) ;
return 0;
}
} else if (ch == 'b' && base == 0) {
might_be_float = false;
base = 2;
ch = getchr(st);
if (ch < '0' || ch > '1') {
Yap_InitError(SYNTAX_ERROR, TermNil, "empty binary 0b%C", ch) ;
return 0;
}
if (ch < '0' || ch > '1') {
Yap_syntax_error(NULL, st-GLOBAL_Stream);
Yap_ThrowError(SYNTAX_ERROR, TermNil, "empty binary 0b%C", ch) ;
return 0;
}
} else {
@ -1032,7 +1035,6 @@ static Term get_num(int *chp, int *chbuffp, StreamDesc *st, int sign) {
if (has_dot) {
unsigned char *dp;
int dc;
if (chtype(ch = getchr(st)) != NU) {
if (ch == 'e' || ch == 'E') {
if (trueGlobalPrologFlag(ISO_FLAG))
@ -1173,11 +1175,6 @@ Term Yap_scan_num(StreamDesc *inp, bool error_on) {
while (isspace(ch = getchr(inp)))
;
#endif
if (LOCAL_ErrorMessage != NULL || ch != -1 || cherr) {
Yap_clean_tokenizer(old_tr, NULL, NULL);
Yap_InitError(SYNTAX_ERROR, ARG2, "while converting stream %d to number", inp-GLOBAL_Stream );
return 0;
}
return out;
}

View File

@ -757,16 +757,22 @@ static Term write_number(unsigned char *s, seq_tv_t *out,
Term t;
yap_error_descriptor_t new_error;
bool mdnew = true;
Yap_pushErrorContext(error_on, &new_error);
t = Yap_StringToNumberTerm((char *)s, &out->enc,error_on);
Yap_popErrorContext(mdnew, true);
if (error_on) {
if (t == 0 && LOCAL_ActiveError->errorNo != YAP_NO_ERROR) {
P = FAILCODE;
Yap_HandleError("scanningx");
}
if (!error_on) {
sigjmp_buf signew, *sighold = LOCAL_RestartEnv;
LOCAL_RestartEnv = &signew;
Yap_pushErrorContext(error_on, &new_error);
if /* top &&*/( sigsetjmp(signew, 1) == 0) {
t = Yap_StringToNumberTerm((char *)s, &out->enc,error_on);
} else {
Yap_ResetException(LOCAL_ActiveError);
t = 0;
}
Yap_popErrorContext(mdnew, true);
LOCAL_RestartEnv = sighold;
} else {
t = Yap_StringToNumberTerm((char *)s, &out->enc,error_on);
}
Yap_ResetException(LOCAL_ActiveError);
return t;
}

View File

@ -349,7 +349,7 @@ static void wrputf(Float f, struct write_globs *wglb) /* writes a float */
found_dot = TRUE;
wrputs(".0", stream);
}
found_dot = TRUE;
found_dot = true;
}
wrputc(ch, stream);
pt++;
@ -1264,6 +1264,7 @@ char *Yap_TermToBuffer(Term t, encoding_t enc, int flags) {
GLOBAL_Stream[sno].encoding = enc;
else
GLOBAL_Stream[sno].encoding = LOCAL_encoding;
GLOBAL_Stream[sno].status |= CloseOnException_Stream_f;
Yap_plwrite(t, GLOBAL_Stream + sno, 0, flags, GLOBAL_MaxPriority);
sf = Yap_MemExportStreamPtr(sno);

View File

@ -357,11 +357,11 @@ Functor EvalArg(Term);
#define FlIsInt(X) (FALSE)
#endif
#ifdef M_WILLIAMS
//#if defined(M_WILLIAMS)
#define MkEvalFl(X) MkFloatTerm(X)
#else
#define MkEvalFl(X) (FlIsInt(X) ? MkIntTerm((Int)(X)) : MkFloatTerm(X))
#endif
//#else
//#define MkEvalFl(X) (FlIsInt(X) ? MkIntTerm((Int)(X)) : MkFloatTerm(X))
//#endif
/* Macros used by some of the eval functions */
#define REvalInt(I) \

View File

@ -216,7 +216,7 @@
printed, `%g` will print all floats using 6 digits instead of the
default 15.
*/
YAP_FLAG(FLOAT_FORMAT_FLAG, "float_format", true, isatom, "%.16g",
YAP_FLAG(FLOAT_FORMAT_FLAG, "float_format", true, isatom, "%.16f",
NULL),
/**< `gc`

View File

@ -1958,7 +1958,7 @@ MAN_LINKS = NO
# captures the structure of the code including all documentation.
# The default value is: NO.
GENERATE_XML = NO
GENERATE_XML = YES
# The XML_OUTPUT tag is used to specify where the XML pages will be put. If a
# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of
@ -1966,7 +1966,7 @@ GENERATE_XML = NO
# The default directory is: xml.
# This tag requires that the tag GENERATE_XML is set to YES.
XML_OUTPUT = YES
XML_OUTPUT = xml
# If the XML_PROGRAMLISTING tag is set to YES, doxygen will dump the program
# listings (including syntax highlighting and cross-referencing information) to

View File

@ -391,7 +391,9 @@ typedef enum stream_f {
0x1000000, /**< do not close the stream after an abort event */
Readline_Stream_f = 0x2000000, /**< the stream is a readline stream */
FreeOnClose_Stream_f =
0x4000000 /**< the stream buffer should be releaed on close */
0x4000000, /**< the stream buffer should be releaed on close */
CloseOnException_Stream_f =
0x8000000 /**< the stream closed by Yap_Error and friends */
} estream_f;
typedef uint64_t stream_flags_t;

View File

@ -95,6 +95,7 @@ Term Yap_StringToNumberTerm(const char *s, encoding_t *encp, bool error_on) {
while (*s && isblank(*s) && Yap_wide_chtype(*s) == BS)
s++;
#endif
GLOBAL_Stream[sno].status |= CloseOnException_Stream_f;
t = Yap_scan_num(GLOBAL_Stream + sno, error_on);
Yap_CloseStream(sno);
UNLOCK(GLOBAL_Stream[sno].streamlock);

View File

@ -1384,6 +1384,7 @@ Term Yap_BufferToTerm(const char *s, Term opts) {
sno = Yap_open_buf_read_stream((char *)s, strlen((const char *)s), &l,
MEM_BUF_USER);
GLOBAL_Stream[sno].status |= CloseOnException_Stream_f;
rval = Yap_read_term(sno, opts, false);
Yap_CloseStream(sno);
return rval;
@ -1395,7 +1396,7 @@ Term Yap_UBufferToTerm(const unsigned char *s, Term opts) {
encoding_t l = ENC_ISO_UTF8;
sno = Yap_open_buf_read_stream((char *)s, strlen((const char *)s), &l,
MEM_BUF_USER);
GLOBAL_Stream[sno].status |= CloseOnException_Stream_f;
rval = Yap_read_term(sno, opts, false);
Yap_CloseStream(sno);
return rval;
@ -1515,6 +1516,7 @@ static Int read_term_from_string(USES_REGS1) {
char *ss = (char *)s;
encoding_t enc = ENC_ISO_UTF8;
int sno = Yap_open_buf_read_stream(ss, len, &enc, MEM_BUF_USER);
GLOBAL_Stream[sno].status |= CloseOnException_Stream_f;
rc = Yap_read_term(sno, Deref(ARG3), 3);
Yap_CloseStream(sno);
if (!rc)

View File

@ -964,11 +964,11 @@ static Int set_stream(USES_REGS1) { /* Init current_stream */
return do_set_stream(sno, Deref(ARG2) PASS_REGS);
}
/*
/**
* Called when you want to close all open streams, except for stdin, stdout
* and stderr
*/
void Yap_CloseStreams(int loud) {
void Yap_CloseStreams(void) {
CACHE_REGS
int sno;
fflush(NULL);
@ -979,6 +979,23 @@ void Yap_CloseStreams(int loud) {
}
}
/**
* Called when you want to close all temporary streams,
* except for stdin, stdout
* and stderr
*/
void Yap_CloseTemporaryStreams(void) {
CACHE_REGS
int sno;
fflush(NULL);
for (sno = 3; sno < MaxStreams; ++sno) {
if (GLOBAL_Stream[sno].status & Free_Stream_f)
continue;
if (GLOBAL_Stream[sno].status & CloseOnException_Stream_f)
CloseStream(sno);
}
}
static void CloseStream(int sno) {
CACHE_REGS

View File

@ -78,7 +78,8 @@ extern void Yap_UnLockStream(void *);
#define Yap_UnLockStream(X)
#endif
extern Int Yap_GetStreamFd(int);
extern void Yap_CloseStreams(int);
extern void Yap_CloseStreams(void);
extern void Yap_CloseTemporaryStreams(void);
extern void Yap_FlushStreams(void);
extern void Yap_ReleaseStream(int);
extern int Yap_PlGetchar(void);