From 47b15177777170345188fa24cbd6a4e52b82815d Mon Sep 17 00:00:00 2001 From: marcobaye Date: Mon, 29 Jul 2024 11:55:56 +0000 Subject: [PATCH] started refactoring input git-svn-id: https://svn.code.sf.net/p/acme-crossass/code-0/trunk@378 4df02467-bbd4-4a76-a152-e7ce94205b78 --- src/acme.c | 2 +- src/global.c | 26 ++++++++++++++++++ src/global.h | 9 ++++++- src/input.c | 65 +++++++++++++++++++-------------------------- src/input.h | 25 +++++++++++------ src/pseudoopcodes.c | 5 +--- src/version.h | 2 +- 7 files changed, 82 insertions(+), 52 deletions(-) diff --git a/src/acme.c b/src/acme.c index 5e2190e..53510ad 100644 --- a/src/acme.c +++ b/src/acme.c @@ -349,7 +349,7 @@ static void perform_pass(void) // Process toplevel files for (ii = 0; ii < toplevel_src_count; ++ii) { if ((fd = fopen(toplevel_sources_plat[ii], FILE_READBINARY))) { - input_parse_and_close_platform_file(toplevel_sources_plat[ii], fd); + parse_and_close_platform_file(fd, toplevel_sources_plat[ii]); } else { fprintf(stderr, "Error: Cannot open toplevel file \"%s\".\n", toplevel_sources_plat[ii]); if (toplevel_sources_plat[ii][0] == '-') diff --git a/src/global.c b/src/global.c index 4f91dff..eb7be59 100644 --- a/src/global.c +++ b/src/global.c @@ -430,6 +430,32 @@ int parse_optional_block(void) return TRUE; } +// parse a whole source code file +// file name must be given in platform style, i.e. +// "directory/basename.extension" on linux, +// "directory.basename/extension" on RISC OS, etc. +// and the pointer must remain valid forever! +void parse_and_close_platform_file(FILE *fd, const char *eternal_plat_filename) +{ + struct inputchange_buf icb; + + // be verbose + if (config.process_verbosity >= 3) + printf("Parsing source file \"%s\".\n", eternal_plat_filename); + // set up new input + inputchange_new_file(&icb, fd, eternal_plat_filename); + // parse block and check end reason + parse_until_eob_or_eof(); + if (GotByte != CHAR_EOF) + Throw_error("Expected EOF, found '}' instead." ); + // close sublevel src + // (this looks like we could just use "fd" as arg, but maybe the file + // has been replaced with a different one in the meantime...) + fclose(input_now->src.fd); + // restore outer input + inputchange_back(&icb); +} + // Error handling diff --git a/src/global.h b/src/global.h index c483e92..d2fad49 100644 --- a/src/global.h +++ b/src/global.h @@ -190,8 +190,15 @@ extern void parse_until_eob_or_eof(void); // Don't forget to call EnsureEOL() afterwards. extern int parse_optional_block(void); +// parse a whole source code file +// file name must be given in platform style, i.e. +// "directory/basename.extension" on linux, +// "directory.basename/extension" on RISC OS, etc. +// and the pointer must remain valid forever! +extern void parse_and_close_platform_file(FILE *fd, const char *eternal_plat_filename); + // generate a debug/info/warning/error message -void throw_message(enum debuglevel level, const char msg[]); +extern void throw_message(enum debuglevel level, const char msg[]); // output a warning (something looks wrong, like "label name starts with shift-space character") #define Throw_warning(msg) throw_message(DEBUGLEVEL_WARNING, msg) diff --git a/src/input.c b/src/input.c index 008db22..d45b6f6 100644 --- a/src/input.c +++ b/src/input.c @@ -46,43 +46,6 @@ char GotByte; // last byte read (processed) // functions -// parse a whole source code file -// file name must be given in platform style, i.e. -// "directory/basename.extension" on linux, -// "directory.basename/extension" on RISC OS, etc. -// and the pointer must remain valid forever! -void input_parse_and_close_platform_file(const char *eternal_plat_filename, FILE *fd) -{ - struct input new_input, - *outer_input; - - // be verbose - if (config.process_verbosity >= 3) - printf("Parsing source file \"%s\".\n", eternal_plat_filename); - // set up new input - new_input.plat_pathref_filename = eternal_plat_filename; - new_input.location.plat_filename = eternal_plat_filename; - new_input.location.line_number = 1; - new_input.source = INPUTSRC_FILE; - new_input.state = INPUTSTATE_SOF; - new_input.src.fd = fd; - // remember where outer input struct is - outer_input = input_now; - // activate new input struct - input_now = &new_input; - // parse block and check end reason - parse_until_eob_or_eof(); - if (GotByte != CHAR_EOF) - Throw_error("Expected EOF, found '}' instead." ); - // close sublevel src - // (this looks like we could just use "fd" as arg, but maybe the file - // has been replaced with a different one in the meantime...) - fclose(input_now->src.fd); - // restore outer input struct - input_now = outer_input; -} - - // remember source code character for report generator #define HEXBUFSIZE 9 // actually, 4+1 is enough, but for systems without snprintf(), let's be extra-safe. #define IF_WANTED_REPORT_SRCCHAR(c) do { if (report->fd) report_srcchar(c); } while(0) @@ -874,6 +837,34 @@ int input_read_output_filename(void) } +// "input change" stuff: + +// save current input struct in buffer, then switch input to new source code file +void inputchange_new_file(struct inputchange_buf *icb, FILE *fd, const char *eternal_plat_filename) +{ + // TODO: in future, really buffer old data here! (instead of storing new data and changing pointer) + // setup new input + icb->new_input.plat_pathref_filename = eternal_plat_filename; + icb->new_input.location.plat_filename = eternal_plat_filename; + icb->new_input.location.line_number = 1; + icb->new_input.source = INPUTSRC_FILE; + icb->new_input.state = INPUTSTATE_SOF; + icb->new_input.src.fd = fd; + // remember where outer input struct is + icb->outer_input = input_now; + // activate new input + icb->gb = GotByte; + input_now = &icb->new_input; +} + +// restore input struct from buffer +void inputchange_back(struct inputchange_buf *icb) +{ + input_now = icb->outer_input; + GotByte = icb->gb; +} + + // "include path" stuff: // ring list struct for "include path items" diff --git a/src/input.h b/src/input.h index c5901e6..96a5367 100644 --- a/src/input.h +++ b/src/input.h @@ -13,7 +13,7 @@ // type definitions -// values for input component "src.state" +// values for input component "src.state" (FIXME - try to move this into .c file!) enum inputstate { INPUTSTATE_SOF, // start of file (check for hashbang) INPUTSTATE_NORMAL, // everything's fine @@ -71,13 +71,6 @@ extern char GotByte; // last byte read (processed) // Prototypes -// parse a whole source code file -// file name must be given in platform style, i.e. -// "directory/basename.extension" on linux, -// "directory.basename/extension" on RISC OS, etc. -// and the pointer must remain valid forever! -extern void input_parse_and_close_platform_file(const char *eternal_plat_filename, FILE *fd); - // get next byte from currently active byte source in shortened high-level // format. When inside quotes, use input_quoted_to_dynabuf() instead! extern char GetByte(void); @@ -167,6 +160,22 @@ extern int input_expect(int chr); extern bits input_get_force_bit(void); +// "input change" stuff: + +// treat this struct as opaque, its components should only be referenced by inputchange_* functions! +struct inputchange_buf { + struct input new_input, + *outer_input; + char gb; // buffer for GotByte +}; + +// save current input struct in buffer, then switch input to new source code file +extern void inputchange_new_file(struct inputchange_buf *icb, FILE *fd, const char *eternal_plat_filename); + +// restore input struct from buffer +extern void inputchange_back(struct inputchange_buf *icb); + + // "include path" stuff: // add entry diff --git a/src/pseudoopcodes.c b/src/pseudoopcodes.c index 8243f83..ccaa36c 100644 --- a/src/pseudoopcodes.c +++ b/src/pseudoopcodes.c @@ -897,7 +897,6 @@ static enum eos po_source(void) // now GotByte = illegal char struct filespecflags flags; FILE *stream; const char *eternal_plat_filename; - char local_gotbyte; // enter new nesting level // quit program if recursion too deep @@ -912,9 +911,7 @@ static enum eos po_source(void) // now GotByte = illegal char stream = includepaths_open_ro(&flags); if (stream) { eternal_plat_filename = dynabuf_get_copy(GlobalDynaBuf); - local_gotbyte = GotByte; // CAUTION - ugly kluge - input_parse_and_close_platform_file(eternal_plat_filename, stream); - GotByte = local_gotbyte; // CAUTION - ugly kluge + parse_and_close_platform_file(stream, eternal_plat_filename); } // leave nesting level ++sanity.source_recursions_left; diff --git a/src/version.h b/src/version.h index a96aff9..a3aa8c1 100644 --- a/src/version.h +++ b/src/version.h @@ -9,7 +9,7 @@ #define RELEASE "0.97" // update before release FIXME #define CODENAME "Zem" // update before release -#define CHANGE_DATE "15 Jul" // update before release FIXME +#define CHANGE_DATE "16 Jul" // update before release FIXME #define CHANGE_YEAR "2024" // update before release //#define HOME_PAGE "http://home.pages.de/~mac_bacon/smorbrod/acme/" #define HOME_PAGE "http://sourceforge.net/p/acme-crossass/" // FIXME