From 0cecb79ff97c73a24acacf8afdc3edba93507661 Mon Sep 17 00:00:00 2001 From: "Erik M. Bray" Date: Thu, 22 Nov 2018 10:53:31 +0100 Subject: [PATCH 2/3] kernel: add helper function for writing error messages to the file/stream referenced by the ERROR_OUTPUT global variable --- src/error.c | 42 ++++++++++++++++++++++++++++++++++++++++++ src/error.h | 8 ++++++++ src/scanner.c | 3 ++- 3 files changed, 52 insertions(+), 1 deletion(-) diff --git a/src/error.c b/src/error.c index 9bb3be8..d43347d 100644 --- a/src/error.c +++ b/src/error.c @@ -33,6 +33,8 @@ static Obj ErrorInner; +static Obj ERROR_OUTPUT = NULL; +static Obj IsOutputStream; /**************************************************************************** @@ -40,6 +42,44 @@ static Obj ErrorInner; *F * * * * * * * * * * * * * * error functions * * * * * * * * * * * * * * * */ +/**************************************************************************** +** +*F OpenErrorOutput() . . . . . . . open the file or stream assigned to the +** ERROR_OUTPUT global variable defined in +** error.g, or "*errout*" otherwise +*/ +UInt OpenErrorOutput( void ) +{ + /* Try to print the output to stream. Use *errout* as a fallback. */ + UInt ret = 0; + + if (ERROR_OUTPUT != NULL) { + if (IsStringConv(ERROR_OUTPUT)) { + ret = OpenOutput(CSTR_STRING(ERROR_OUTPUT)); + } + else { + if (CALL_1ARGS(IsOutputStream, ERROR_OUTPUT) == True) { + ret = OpenOutputStream(ERROR_OUTPUT); + } + } + } + + if (!ret) { + /* It may be we already tried and failed to open *errout* above but + * but this is an extreme case so it can't hurt to try again + * anyways */ + ret = OpenOutput("*errout*"); + if (ret) { + Pr("failed to open error stream\n", 0, 0); + } + else { + Panic("failed to open *errout*"); + } + } + + return ret; +} + /**************************************************************************** ** @@ -615,6 +655,8 @@ static Int InitKernel(StructInitInfo * module) InitHdlrFuncsFromTable(GVarFuncs); ImportFuncFromLibrary("ErrorInner", &ErrorInner); + ImportFuncFromLibrary("IsOutputStream", &IsOutputStream); + ImportGVarFromLibrary("ERROR_OUTPUT", &ERROR_OUTPUT); // return success return 0; diff --git a/src/error.h b/src/error.h index 31af256..1f5ee5d 100644 --- a/src/error.h +++ b/src/error.h @@ -32,6 +32,14 @@ Int RegisterBreakloopObserver(intfunc func); /**************************************************************************** ** +*F OpenErrorOutput() . . . . . . . open the file or stream assigned to the +** ERROR_OUTPUT global variable defined in +** error.g, or "*errout*" otherwise +*/ +extern UInt OpenErrorOutput(); + +/**************************************************************************** +** *F ErrorQuit( , , ) . . . . . . . . . . . print and quit */ extern void ErrorQuit(const Char * msg, Int arg1, Int arg2) NORETURN; diff --git a/src/scanner.c b/src/scanner.c index 4db17b3..071c0e3 100644 --- a/src/scanner.c +++ b/src/scanner.c @@ -16,6 +16,7 @@ #include "scanner.h" +#include "error.h" #include "gapstate.h" #include "gaputils.h" #include "io.h" @@ -42,7 +43,7 @@ static void SyntaxErrorOrWarning(const Char * msg, UInt error) if (STATE(NrErrLine) == 0) { // open error output - OpenOutput("*errout*"); + OpenErrorOutput(); // print the message ... if (error) -- 1.9.1