From 21b59c46519eb80ea48211cae6ab055d487cea57 Mon Sep 17 00:00:00 2001 From: Eldred Habert Date: Sat, 1 May 2021 23:30:09 +0200 Subject: [PATCH] Reinstate PUSHS clearing the SECTION scope (#870) * Reinstate PUSHS clearing the SECTION scope Otherwise you can use `PUSHS` to simulate the old `ds -21`, and possibly cause bugs * Have PUSHS push LOAD block state as well It does not make sense not to, and coud cause bugs. --- include/asm/output.h | 2 +- include/asm/section.h | 2 ++ src/asm/output.c | 3 +-- src/asm/section.c | 14 +++++++++++++- test/asm/align-pc-outside-section.err | 2 +- test/asm/pops-restore-no-section.err | 2 +- test/asm/pushs.asm | 5 +++++ test/asm/pushs.err | 2 ++ test/asm/pushs.out | 0 9 files changed, 26 insertions(+), 6 deletions(-) create mode 100644 test/asm/pushs.asm create mode 100644 test/asm/pushs.err create mode 100644 test/asm/pushs.out diff --git a/include/asm/output.h b/include/asm/output.h index 7f5a5914..007e7ab0 100644 --- a/include/asm/output.h +++ b/include/asm/output.h @@ -17,7 +17,7 @@ struct Expression; struct FileStackNode; extern char *objectName; -extern struct Section *sectionList, *currentSection; +extern struct Section *sectionList; void out_RegisterNode(struct FileStackNode *node); void out_ReplaceNode(struct FileStackNode *node); diff --git a/include/asm/section.h b/include/asm/section.h index 5b2672d2..c8814911 100644 --- a/include/asm/section.h +++ b/include/asm/section.h @@ -40,6 +40,8 @@ struct SectionSpec { uint16_t alignOfs; }; +extern struct Section *currentSection; + struct Section *out_FindSectionByName(const char *name); void out_NewSection(char const *name, uint32_t secttype, uint32_t org, struct SectionSpec const *attributes, diff --git a/src/asm/output.c b/src/asm/output.c index 5c9e1f17..5b7aeba3 100644 --- a/src/asm/output.c +++ b/src/asm/output.c @@ -53,8 +53,7 @@ struct Assertion { char *objectName; -/* TODO: shouldn't `currentSection` be somewhere else? */ -struct Section *sectionList, *currentSection; +struct Section *sectionList; /* Linked list of symbols to put in the object file */ static struct Symbol *objectSymbols = NULL; diff --git a/src/asm/section.c b/src/asm/section.c index b9fc281c..0ed3fc46 100644 --- a/src/asm/section.c +++ b/src/asm/section.c @@ -22,13 +22,16 @@ uint8_t fillByte; struct SectionStackEntry { struct Section *section; + struct Section *loadSection; char const *scope; /* Section's symbol scope */ uint32_t offset; + int32_t loadOffset; struct SectionStackEntry *next; }; struct SectionStackEntry *sectionStack; uint32_t curOffset; /* Offset into the current section (see sect_GetSymbolOffset) */ +struct Section *currentSection = NULL; static struct Section *currentLoadSection = NULL; int32_t loadOffset; /* Offset into the LOAD section's parent (see sect_GetOutputOffset) */ @@ -44,7 +47,7 @@ struct UnionStackEntry { static void checksection(void) { if (currentSection == NULL) - fatalerror("Code generation before SECTION directive\n"); + fatalerror("Cannot output data outside of a SECTION\n"); } /* @@ -898,10 +901,17 @@ void out_PushSection(void) if (sect == NULL) fatalerror("No memory for section stack: %s\n", strerror(errno)); sect->section = currentSection; + sect->loadSection = currentLoadSection; sect->scope = sym_GetCurrentSymbolScope(); sect->offset = curOffset; + sect->loadOffset = loadOffset; sect->next = sectionStack; sectionStack = sect; + + // Reset the section scope + currentSection = NULL; + currentLoadSection = NULL; + sym_SetCurrentSymbolScope(NULL); } void out_PopSection(void) @@ -917,8 +927,10 @@ void out_PopSection(void) sect = sectionStack; changeSection(); currentSection = sect->section; + currentLoadSection = sect->loadSection; sym_SetCurrentSymbolScope(sect->scope); curOffset = sect->offset; + loadOffset = sect->loadOffset; sectionStack = sect->next; free(sect); diff --git a/test/asm/align-pc-outside-section.err b/test/asm/align-pc-outside-section.err index 4640ff9f..624648b3 100644 --- a/test/asm/align-pc-outside-section.err +++ b/test/asm/align-pc-outside-section.err @@ -1,2 +1,2 @@ FATAL: align-pc-outside-section.asm(1): - Code generation before SECTION directive + Cannot output data outside of a SECTION diff --git a/test/asm/pops-restore-no-section.err b/test/asm/pops-restore-no-section.err index c00efd30..30a5953b 100644 --- a/test/asm/pops-restore-no-section.err +++ b/test/asm/pops-restore-no-section.err @@ -1,4 +1,4 @@ ERROR: pops-restore-no-section.asm(9): Label "DisallowedContent" created outside of a SECTION FATAL: pops-restore-no-section.asm(10): - Code generation before SECTION directive + Cannot output data outside of a SECTION diff --git a/test/asm/pushs.asm b/test/asm/pushs.asm new file mode 100644 index 00000000..7ac2237c --- /dev/null +++ b/test/asm/pushs.asm @@ -0,0 +1,5 @@ +SECTION "This is invalid", ROM0 + ds 10, 42 + PUSHS + ; We should be outside of section scope now + db 69 diff --git a/test/asm/pushs.err b/test/asm/pushs.err new file mode 100644 index 00000000..7d14e163 --- /dev/null +++ b/test/asm/pushs.err @@ -0,0 +1,2 @@ +FATAL: pushs.asm(5): + Cannot output data outside of a SECTION diff --git a/test/asm/pushs.out b/test/asm/pushs.out new file mode 100644 index 00000000..e69de29b