mirror of
https://github.com/gbdev/rgbds.git
synced 2025-11-21 18:52:07 +00:00
Remove now-unnecessary struct keyword (#1320)
C++ acts like structs are `typedef`ed by default We do have to keep `struct stat`, since there's ambiguity with the function also called `stat`.
This commit is contained in:
@@ -30,17 +30,17 @@ struct CharmapNode {
|
||||
|
||||
struct Charmap {
|
||||
std::string name;
|
||||
std::vector<struct CharmapNode> nodes; // first node is reserved for the root node
|
||||
std::vector<CharmapNode> nodes; // first node is reserved for the root node
|
||||
};
|
||||
|
||||
static std::map<std::string, struct Charmap> charmaps;
|
||||
static std::map<std::string, Charmap> charmaps;
|
||||
|
||||
static struct Charmap *currentCharmap;
|
||||
std::stack<struct Charmap *> charmapStack;
|
||||
static Charmap *currentCharmap;
|
||||
std::stack<Charmap *> charmapStack;
|
||||
|
||||
void charmap_New(char const *name, char const *baseName)
|
||||
{
|
||||
struct Charmap *base = NULL;
|
||||
Charmap *base = NULL;
|
||||
|
||||
if (baseName != NULL) {
|
||||
auto search = charmaps.find(baseName);
|
||||
@@ -57,7 +57,7 @@ void charmap_New(char const *name, char const *baseName)
|
||||
}
|
||||
|
||||
// Init the new charmap's fields
|
||||
struct Charmap &charmap = charmaps[name];
|
||||
Charmap &charmap = charmaps[name];
|
||||
|
||||
if (base)
|
||||
charmap.nodes = base->nodes; // Copies `base->nodes`
|
||||
@@ -96,7 +96,7 @@ void charmap_Pop(void)
|
||||
|
||||
void charmap_Add(char *mapping, uint8_t value)
|
||||
{
|
||||
struct Charmap &charmap = *currentCharmap;
|
||||
Charmap &charmap = *currentCharmap;
|
||||
size_t nodeIdx = 0;
|
||||
|
||||
for (; *mapping; mapping++) {
|
||||
@@ -115,7 +115,7 @@ void charmap_Add(char *mapping, uint8_t value)
|
||||
nodeIdx = nextIdx;
|
||||
}
|
||||
|
||||
struct CharmapNode &node = charmap.nodes[nodeIdx];
|
||||
CharmapNode &node = charmap.nodes[nodeIdx];
|
||||
|
||||
if (node.isTerminal)
|
||||
warning(WARNING_CHARMAP_REDEF, "Overriding charmap mapping\n");
|
||||
@@ -126,7 +126,7 @@ void charmap_Add(char *mapping, uint8_t value)
|
||||
|
||||
bool charmap_HasChar(char const *input)
|
||||
{
|
||||
struct Charmap const &charmap = *currentCharmap;
|
||||
Charmap const &charmap = *currentCharmap;
|
||||
size_t nodeIdx = 0;
|
||||
|
||||
for (; *input; input++) {
|
||||
@@ -151,7 +151,7 @@ size_t charmap_ConvertNext(char const **input, std::vector<uint8_t> *output)
|
||||
// For that, advance through the trie with each character read.
|
||||
// If that would lead to a dead end, rewind characters until the last match, and output.
|
||||
// If no match, read a UTF-8 codepoint and output that.
|
||||
struct Charmap const &charmap = *currentCharmap;
|
||||
Charmap const &charmap = *currentCharmap;
|
||||
size_t matchIdx = 0;
|
||||
size_t rewindDistance = 0;
|
||||
|
||||
|
||||
@@ -12,29 +12,29 @@
|
||||
#include "asm/format.hpp"
|
||||
#include "asm/warning.hpp"
|
||||
|
||||
struct FormatSpec fmt_NewSpec(void)
|
||||
FormatSpec fmt_NewSpec(void)
|
||||
{
|
||||
struct FormatSpec fmt = {};
|
||||
FormatSpec fmt = {};
|
||||
|
||||
return fmt;
|
||||
}
|
||||
|
||||
bool fmt_IsEmpty(struct FormatSpec const *fmt)
|
||||
bool fmt_IsEmpty(FormatSpec const *fmt)
|
||||
{
|
||||
return !fmt->state;
|
||||
}
|
||||
|
||||
bool fmt_IsValid(struct FormatSpec const *fmt)
|
||||
bool fmt_IsValid(FormatSpec const *fmt)
|
||||
{
|
||||
return fmt->valid || fmt->state == FORMAT_DONE;
|
||||
}
|
||||
|
||||
bool fmt_IsFinished(struct FormatSpec const *fmt)
|
||||
bool fmt_IsFinished(FormatSpec const *fmt)
|
||||
{
|
||||
return fmt->state >= FORMAT_DONE;
|
||||
}
|
||||
|
||||
void fmt_UseCharacter(struct FormatSpec *fmt, int c)
|
||||
void fmt_UseCharacter(FormatSpec *fmt, int c)
|
||||
{
|
||||
if (fmt->state == FORMAT_INVALID)
|
||||
return;
|
||||
@@ -121,13 +121,13 @@ invalid:
|
||||
}
|
||||
}
|
||||
|
||||
void fmt_FinishCharacters(struct FormatSpec *fmt)
|
||||
void fmt_FinishCharacters(FormatSpec *fmt)
|
||||
{
|
||||
if (!fmt_IsValid(fmt))
|
||||
fmt->state = FORMAT_INVALID;
|
||||
}
|
||||
|
||||
void fmt_PrintString(char *buf, size_t bufLen, struct FormatSpec const *fmt, char const *value)
|
||||
void fmt_PrintString(char *buf, size_t bufLen, FormatSpec const *fmt, char const *value)
|
||||
{
|
||||
if (fmt->sign)
|
||||
error("Formatting string with sign flag '%c'\n", fmt->sign);
|
||||
@@ -166,7 +166,7 @@ void fmt_PrintString(char *buf, size_t bufLen, struct FormatSpec const *fmt, cha
|
||||
buf[totalLen] = '\0';
|
||||
}
|
||||
|
||||
void fmt_PrintNumber(char *buf, size_t bufLen, struct FormatSpec const *fmt, uint32_t value)
|
||||
void fmt_PrintNumber(char *buf, size_t bufLen, FormatSpec const *fmt, uint32_t value)
|
||||
{
|
||||
if (fmt->type != 'X' && fmt->type != 'x' && fmt->type != 'b' && fmt->type != 'o'
|
||||
&& fmt->prefix)
|
||||
|
||||
@@ -23,10 +23,10 @@
|
||||
#include "platform.hpp" // S_ISDIR (stat macro)
|
||||
|
||||
struct Context {
|
||||
struct FileStackNode *fileInfo;
|
||||
struct LexerState lexerState;
|
||||
FileStackNode *fileInfo;
|
||||
LexerState lexerState;
|
||||
uint32_t uniqueID;
|
||||
struct MacroArgs *macroArgs; // Macro args are *saved* here
|
||||
MacroArgs *macroArgs; // Macro args are *saved* here
|
||||
uint32_t nbReptIters;
|
||||
bool isForLoop;
|
||||
int32_t forValue;
|
||||
@@ -34,7 +34,7 @@ struct Context {
|
||||
std::string forName;
|
||||
};
|
||||
|
||||
static std::stack<struct Context> contextStack;
|
||||
static std::stack<Context> contextStack;
|
||||
size_t maxRecursionDepth;
|
||||
|
||||
// The first include path for `fstk_FindFile` to try is none at all
|
||||
@@ -42,7 +42,7 @@ static std::vector<std::string> includePaths = { "" };
|
||||
|
||||
static const char *preIncludeName;
|
||||
|
||||
static const char *dumpNodeAndParents(struct FileStackNode const *node)
|
||||
static const char *dumpNodeAndParents(FileStackNode const *node)
|
||||
{
|
||||
char const *name;
|
||||
|
||||
@@ -86,7 +86,7 @@ std::string const &FileStackNode::name() const {
|
||||
return std::get<std::string>(data);
|
||||
}
|
||||
|
||||
void fstk_Dump(struct FileStackNode const *node, uint32_t lineNo)
|
||||
void fstk_Dump(FileStackNode const *node, uint32_t lineNo)
|
||||
{
|
||||
dumpNodeAndParents(node);
|
||||
fprintf(stderr, "(%" PRIu32 ")", lineNo);
|
||||
@@ -101,15 +101,15 @@ void fstk_DumpCurrent(void)
|
||||
fstk_Dump(contextStack.top().fileInfo, lexer_GetLineNo());
|
||||
}
|
||||
|
||||
struct FileStackNode *fstk_GetFileStack(void)
|
||||
FileStackNode *fstk_GetFileStack(void)
|
||||
{
|
||||
if (contextStack.empty())
|
||||
return NULL;
|
||||
|
||||
struct FileStackNode *topNode = contextStack.top().fileInfo;
|
||||
FileStackNode *topNode = contextStack.top().fileInfo;
|
||||
|
||||
// Mark node and all of its parents as referenced if not already so they don't get freed
|
||||
for (struct FileStackNode *node = topNode; node && !node->referenced; node = node->parent) {
|
||||
for (FileStackNode *node = topNode; node && !node->referenced; node = node->parent) {
|
||||
node->ID = -1;
|
||||
node->referenced = true;
|
||||
}
|
||||
@@ -119,7 +119,7 @@ struct FileStackNode *fstk_GetFileStack(void)
|
||||
char const *fstk_GetFileName(void)
|
||||
{
|
||||
// Iterating via the nodes themselves skips nested REPTs
|
||||
struct FileStackNode const *node = contextStack.top().fileInfo;
|
||||
FileStackNode const *node = contextStack.top().fileInfo;
|
||||
|
||||
while (node->type != NODE_FILE)
|
||||
node = node->parent;
|
||||
@@ -196,12 +196,12 @@ bool yywrap(void)
|
||||
fatalerror("Ended block with %" PRIu32 " unterminated IF construct%s\n",
|
||||
ifDepth, ifDepth == 1 ? "" : "s");
|
||||
|
||||
if (struct Context &context = contextStack.top(); context.fileInfo->type == NODE_REPT) {
|
||||
if (Context &context = contextStack.top(); context.fileInfo->type == NODE_REPT) {
|
||||
// The context is a REPT or FOR block, which may loop
|
||||
|
||||
// If the node is referenced, we can't edit it; duplicate it
|
||||
if (context.fileInfo->referenced) {
|
||||
context.fileInfo = new(std::nothrow) struct FileStackNode(*context.fileInfo);
|
||||
context.fileInfo = new(std::nothrow) FileStackNode(*context.fileInfo);
|
||||
if (!context.fileInfo)
|
||||
fatalerror("Failed to duplicate REPT file node: %s\n", strerror(errno));
|
||||
// Copy all info but the referencing
|
||||
@@ -215,7 +215,7 @@ bool yywrap(void)
|
||||
// Avoid arithmetic overflow runtime error
|
||||
uint32_t forValue = (uint32_t)context.forValue + (uint32_t)context.forStep;
|
||||
context.forValue = forValue <= INT32_MAX ? forValue : -(int32_t)~forValue - 1;
|
||||
struct Symbol *sym = sym_AddVar(context.forName.c_str(), context.forValue);
|
||||
Symbol *sym = sym_AddVar(context.forName.c_str(), context.forValue);
|
||||
|
||||
// This error message will refer to the current iteration
|
||||
if (sym->type != SYM_VAR)
|
||||
@@ -233,7 +233,7 @@ bool yywrap(void)
|
||||
return true;
|
||||
}
|
||||
|
||||
struct Context oldContext = contextStack.top();
|
||||
Context oldContext = contextStack.top();
|
||||
|
||||
contextStack.pop();
|
||||
|
||||
@@ -256,7 +256,7 @@ bool yywrap(void)
|
||||
// Make sure not to switch the lexer state before calling this, so the saved line no is correct.
|
||||
// BE CAREFUL! This modifies the file stack directly, you should have set up the file info first.
|
||||
// Callers should set `contextStack.top().lexerState` after this so it is not NULL.
|
||||
static struct Context &newContext(struct FileStackNode *fileInfo)
|
||||
static Context &newContext(FileStackNode *fileInfo)
|
||||
{
|
||||
if (contextStack.size() > maxRecursionDepth)
|
||||
fatalerror("Recursion limit (%zu) exceeded\n", maxRecursionDepth);
|
||||
@@ -264,13 +264,13 @@ static struct Context &newContext(struct FileStackNode *fileInfo)
|
||||
// Save the current `\@` value, to be restored when this context ends
|
||||
contextStack.top().uniqueID = macro_GetUniqueID();
|
||||
|
||||
struct FileStackNode *parent = contextStack.top().fileInfo;
|
||||
FileStackNode *parent = contextStack.top().fileInfo;
|
||||
|
||||
fileInfo->parent = parent;
|
||||
fileInfo->lineNo = lexer_GetLineNo();
|
||||
fileInfo->referenced = false;
|
||||
|
||||
struct Context &context = contextStack.emplace();
|
||||
Context &context = contextStack.emplace();
|
||||
|
||||
context.fileInfo = fileInfo;
|
||||
context.isForLoop = false;
|
||||
@@ -294,7 +294,7 @@ void fstk_RunInclude(char const *path)
|
||||
return;
|
||||
}
|
||||
|
||||
struct FileStackNode *fileInfo = new(std::nothrow) struct FileStackNode();
|
||||
FileStackNode *fileInfo = new(std::nothrow) FileStackNode();
|
||||
|
||||
if (!fileInfo) {
|
||||
error("Failed to alloc file info for INCLUDE: %s\n", strerror(errno));
|
||||
@@ -305,7 +305,7 @@ void fstk_RunInclude(char const *path)
|
||||
delete fullPath;
|
||||
|
||||
uint32_t uniqueID = contextStack.top().uniqueID;
|
||||
struct Context &context = newContext(fileInfo);
|
||||
Context &context = newContext(fileInfo);
|
||||
|
||||
if (!lexer_OpenFile(context.lexerState, fileInfo->name().c_str()))
|
||||
fatalerror("Failed to set up lexer for file include\n");
|
||||
@@ -330,7 +330,7 @@ static void runPreIncludeFile(void)
|
||||
return;
|
||||
}
|
||||
|
||||
struct FileStackNode *fileInfo = new(std::nothrow) struct FileStackNode();
|
||||
FileStackNode *fileInfo = new(std::nothrow) FileStackNode();
|
||||
|
||||
if (!fileInfo) {
|
||||
error("Failed to alloc file info for pre-include: %s\n", strerror(errno));
|
||||
@@ -340,7 +340,7 @@ static void runPreIncludeFile(void)
|
||||
fileInfo->data = *fullPath;
|
||||
delete fullPath;
|
||||
|
||||
struct Context &context = newContext(fileInfo);
|
||||
Context &context = newContext(fileInfo);
|
||||
|
||||
if (!lexer_OpenFile(context.lexerState, fileInfo->name().c_str()))
|
||||
fatalerror("Failed to set up lexer for file include\n");
|
||||
@@ -349,9 +349,9 @@ static void runPreIncludeFile(void)
|
||||
context.uniqueID = macro_UndefUniqueID();
|
||||
}
|
||||
|
||||
void fstk_RunMacro(char const *macroName, struct MacroArgs *args)
|
||||
void fstk_RunMacro(char const *macroName, MacroArgs *args)
|
||||
{
|
||||
struct Symbol *macro = sym_FindExactSymbol(macroName);
|
||||
Symbol *macro = sym_FindExactSymbol(macroName);
|
||||
|
||||
if (!macro) {
|
||||
error("Macro \"%s\" not defined\n", macroName);
|
||||
@@ -363,7 +363,7 @@ void fstk_RunMacro(char const *macroName, struct MacroArgs *args)
|
||||
}
|
||||
contextStack.top().macroArgs = macro_GetCurrentArgs();
|
||||
|
||||
struct FileStackNode *fileInfo = new(std::nothrow) struct FileStackNode();
|
||||
FileStackNode *fileInfo = new(std::nothrow) FileStackNode();
|
||||
|
||||
if (!fileInfo) {
|
||||
error("Failed to alloc file info for \"%s\": %s\n", macro->name, strerror(errno));
|
||||
@@ -375,7 +375,7 @@ void fstk_RunMacro(char const *macroName, struct MacroArgs *args)
|
||||
// Print the name...
|
||||
std::string &fileInfoName = fileInfo->name();
|
||||
|
||||
for (struct FileStackNode const *node = macro->src; node; node = node->parent) {
|
||||
for (FileStackNode const *node = macro->src; node; node = node->parent) {
|
||||
if (node->type != NODE_REPT) {
|
||||
fileInfoName.append(node->name());
|
||||
break;
|
||||
@@ -396,7 +396,7 @@ void fstk_RunMacro(char const *macroName, struct MacroArgs *args)
|
||||
fileInfoName.append("::");
|
||||
fileInfoName.append(macro->name);
|
||||
|
||||
struct Context &context = newContext(fileInfo);
|
||||
Context &context = newContext(fileInfo);
|
||||
|
||||
lexer_OpenFileView(context.lexerState, "MACRO", macro->macro.value, macro->macro.size,
|
||||
macro->fileLine);
|
||||
@@ -410,7 +410,7 @@ static bool newReptContext(int32_t reptLineNo, char *body, size_t size)
|
||||
uint32_t reptDepth = contextStack.top().fileInfo->type == NODE_REPT
|
||||
? contextStack.top().fileInfo->iters().size()
|
||||
: 0;
|
||||
struct FileStackNode *fileInfo = new(std::nothrow) struct FileStackNode();
|
||||
FileStackNode *fileInfo = new(std::nothrow) FileStackNode();
|
||||
|
||||
if (!fileInfo) {
|
||||
error("Failed to alloc file info for REPT: %s\n", strerror(errno));
|
||||
@@ -423,7 +423,7 @@ static bool newReptContext(int32_t reptLineNo, char *body, size_t size)
|
||||
fileInfo->iters().insert(fileInfo->iters().end(), RANGE(contextStack.top().fileInfo->iters()));
|
||||
}
|
||||
|
||||
struct Context &context = newContext(fileInfo);
|
||||
Context &context = newContext(fileInfo);
|
||||
|
||||
// Correct our line number, which currently points to the `ENDR` line
|
||||
context.fileInfo->lineNo = reptLineNo;
|
||||
@@ -447,7 +447,7 @@ void fstk_RunRept(uint32_t count, int32_t reptLineNo, char *body, size_t size)
|
||||
void fstk_RunFor(char const *symName, int32_t start, int32_t stop, int32_t step,
|
||||
int32_t reptLineNo, char *body, size_t size)
|
||||
{
|
||||
struct Symbol *sym = sym_AddVar(symName, start);
|
||||
Symbol *sym = sym_AddVar(symName, start);
|
||||
|
||||
if (sym->type != SYM_VAR)
|
||||
return;
|
||||
@@ -470,7 +470,7 @@ void fstk_RunFor(char const *symName, int32_t start, int32_t stop, int32_t step,
|
||||
if (!newReptContext(reptLineNo, body, size))
|
||||
return;
|
||||
|
||||
struct Context &context = contextStack.top();
|
||||
Context &context = contextStack.top();
|
||||
|
||||
context.nbReptIters = count;
|
||||
context.isForLoop = true;
|
||||
@@ -505,13 +505,13 @@ void fstk_NewRecursionDepth(size_t newDepth)
|
||||
|
||||
void fstk_Init(char const *mainPath, size_t maxDepth)
|
||||
{
|
||||
struct Context &context = contextStack.emplace();
|
||||
Context &context = contextStack.emplace();
|
||||
|
||||
if (!lexer_OpenFile(context.lexerState, mainPath))
|
||||
fatalerror("Failed to open main file\n");
|
||||
lexer_SetState(&context.lexerState);
|
||||
|
||||
struct FileStackNode *fileInfo = new(std::nothrow) struct FileStackNode();
|
||||
FileStackNode *fileInfo = new(std::nothrow) FileStackNode();
|
||||
|
||||
if (!fileInfo)
|
||||
fatalerror("Failed to allocate memory for main file info: %s\n", strerror(errno));
|
||||
|
||||
@@ -298,10 +298,10 @@ static bool isWhitespace(int c)
|
||||
return c == ' ' || c == '\t';
|
||||
}
|
||||
|
||||
struct LexerState *lexerState = NULL;
|
||||
struct LexerState *lexerStateEOL = NULL;
|
||||
LexerState *lexerState = NULL;
|
||||
LexerState *lexerStateEOL = NULL;
|
||||
|
||||
static void initState(struct LexerState &state)
|
||||
static void initState(LexerState &state)
|
||||
{
|
||||
state.mode = LEXER_NORMAL;
|
||||
state.atLineStart = true; // yylex() will init colNo due to this
|
||||
@@ -364,7 +364,7 @@ void lexer_ReachELSEBlock(void)
|
||||
lexerState->ifStack.front().reachedElseBlock = true;
|
||||
}
|
||||
|
||||
bool lexer_OpenFile(struct LexerState &state, char const *path)
|
||||
bool lexer_OpenFile(LexerState &state, char const *path)
|
||||
{
|
||||
bool isStdin = !strcmp(path, "-");
|
||||
struct stat fileInfo;
|
||||
@@ -431,7 +431,7 @@ bool lexer_OpenFile(struct LexerState &state, char const *path)
|
||||
return true;
|
||||
}
|
||||
|
||||
void lexer_OpenFileView(struct LexerState &state, char const *path, char *buf, size_t size, uint32_t lineNo)
|
||||
void lexer_OpenFileView(LexerState &state, char const *path, char *buf, size_t size, uint32_t lineNo)
|
||||
{
|
||||
state.path = path; // Used to report read errors in `peekInternal`
|
||||
state.isFile = false;
|
||||
@@ -451,7 +451,7 @@ void lexer_RestartRept(uint32_t lineNo)
|
||||
lexerState->lineNo = lineNo;
|
||||
}
|
||||
|
||||
void lexer_CleanupState(struct LexerState &state)
|
||||
void lexer_CleanupState(LexerState &state)
|
||||
{
|
||||
// A big chunk of the lexer state soundness is the file stack ("fstack").
|
||||
// Each context in the fstack has its own *unique* lexer state; thus, we always guarantee
|
||||
@@ -523,7 +523,7 @@ void lexer_CheckRecursionDepth(void)
|
||||
fatalerror("Recursion limit (%zu) exceeded\n", maxRecursionDepth);
|
||||
}
|
||||
|
||||
static void freeExpansion(struct Expansion &expansion)
|
||||
static void freeExpansion(Expansion &expansion)
|
||||
{
|
||||
free(expansion.name);
|
||||
if (expansion.owned)
|
||||
@@ -573,7 +573,7 @@ static uint32_t readBracketedMacroArgNum(void)
|
||||
}
|
||||
symName[i] = '\0';
|
||||
|
||||
struct Symbol const *sym = sym_FindScopedValidSymbol(symName);
|
||||
Symbol const *sym = sym_FindScopedValidSymbol(symName);
|
||||
|
||||
if (!sym) {
|
||||
error("Bracketed symbol \"%s\" does not exist\n", symName);
|
||||
@@ -654,7 +654,7 @@ static size_t readInternal(size_t bufIndex, size_t nbChars)
|
||||
// We only need one character of lookahead, for macro arguments
|
||||
static int peekInternal(uint8_t distance)
|
||||
{
|
||||
for (struct Expansion &exp : lexerState->expansions) {
|
||||
for (Expansion &exp : lexerState->expansions) {
|
||||
// An expansion that has reached its end will have `exp->offset` == `exp->size`,
|
||||
// and `peekInternal` will continue with its parent
|
||||
assert(exp.offset <= exp.size);
|
||||
@@ -775,7 +775,7 @@ static void shiftChar(void)
|
||||
restart:
|
||||
if (!lexerState->expansions.empty()) {
|
||||
// Advance within the current expansion
|
||||
struct Expansion &expansion = lexerState->expansions.front();
|
||||
Expansion &expansion = lexerState->expansions.front();
|
||||
|
||||
assert(expansion.offset <= expansion.size);
|
||||
expansion.offset++;
|
||||
@@ -840,7 +840,7 @@ void lexer_DumpStringExpansions(void)
|
||||
if (!lexerState)
|
||||
return;
|
||||
|
||||
for (struct Expansion &exp : lexerState->expansions) {
|
||||
for (Expansion &exp : lexerState->expansions) {
|
||||
// Only register EQUS expansions, not string args
|
||||
if (exp.name)
|
||||
fprintf(stderr, "while expanding symbol \"%s\"\n", exp.name);
|
||||
@@ -1184,7 +1184,7 @@ static char const *readInterpolation(size_t depth)
|
||||
|
||||
char symName[MAXSYMLEN + 1];
|
||||
size_t i = 0;
|
||||
struct FormatSpec fmt = fmt_NewSpec();
|
||||
FormatSpec fmt = fmt_NewSpec();
|
||||
bool disableInterpolation = lexerState->disableInterpolation;
|
||||
|
||||
// In a context where `lexerState->disableInterpolation` is true, `peek` will expand
|
||||
@@ -1239,7 +1239,7 @@ static char const *readInterpolation(size_t depth)
|
||||
|
||||
static char buf[MAXSTRLEN + 1];
|
||||
|
||||
struct Symbol const *sym = sym_FindScopedValidSymbol(symName);
|
||||
Symbol const *sym = sym_FindScopedValidSymbol(symName);
|
||||
|
||||
if (!sym) {
|
||||
error("Interpolated symbol \"%s\" does not exist\n", symName);
|
||||
@@ -1881,7 +1881,7 @@ static int yylex_NORMAL(void)
|
||||
// Local symbols cannot be string expansions
|
||||
if (tokenType == T_ID && lexerState->expandStrings) {
|
||||
// Attempt string expansion
|
||||
struct Symbol const *sym = sym_FindExactSymbol(yylval.symName);
|
||||
Symbol const *sym = sym_FindExactSymbol(yylval.symName);
|
||||
|
||||
if (sym && sym->type == SYM_EQUS) {
|
||||
char const *s = sym_GetStringValue(sym);
|
||||
@@ -2286,7 +2286,7 @@ int yylex(void)
|
||||
return token;
|
||||
}
|
||||
|
||||
static void startCapture(struct CaptureBody *capture)
|
||||
static void startCapture(CaptureBody *capture)
|
||||
{
|
||||
assert(!lexerState->capturing);
|
||||
lexerState->capturing = true;
|
||||
@@ -2306,7 +2306,7 @@ static void startCapture(struct CaptureBody *capture)
|
||||
}
|
||||
}
|
||||
|
||||
static void endCapture(struct CaptureBody *capture)
|
||||
static void endCapture(CaptureBody *capture)
|
||||
{
|
||||
// This being NULL means we're capturing from the capture buf, which is `realloc`'d during
|
||||
// the whole capture process, and so MUST be retrieved at the end
|
||||
@@ -2320,7 +2320,7 @@ static void endCapture(struct CaptureBody *capture)
|
||||
lexerState->disableInterpolation = false;
|
||||
}
|
||||
|
||||
bool lexer_CaptureRept(struct CaptureBody *capture)
|
||||
bool lexer_CaptureRept(CaptureBody *capture)
|
||||
{
|
||||
startCapture(capture);
|
||||
|
||||
@@ -2378,7 +2378,7 @@ finish:
|
||||
return c != EOF;
|
||||
}
|
||||
|
||||
bool lexer_CaptureMacroBody(struct CaptureBody *capture)
|
||||
bool lexer_CaptureMacroBody(CaptureBody *capture)
|
||||
{
|
||||
startCapture(capture);
|
||||
|
||||
|
||||
@@ -18,7 +18,7 @@ struct MacroArgs {
|
||||
std::vector<char *> args;
|
||||
};
|
||||
|
||||
static struct MacroArgs *macroArgs = NULL;
|
||||
static MacroArgs *macroArgs = NULL;
|
||||
static uint32_t uniqueID = 0;
|
||||
static uint32_t maxUniqueID = 0;
|
||||
// The initialization is somewhat harmful, since it is never used, but it
|
||||
@@ -27,14 +27,14 @@ static uint32_t maxUniqueID = 0;
|
||||
static char uniqueIDBuf[] = "_u4294967295"; // UINT32_MAX
|
||||
static char *uniqueIDPtr = NULL;
|
||||
|
||||
struct MacroArgs *macro_GetCurrentArgs(void)
|
||||
MacroArgs *macro_GetCurrentArgs(void)
|
||||
{
|
||||
return macroArgs;
|
||||
}
|
||||
|
||||
struct MacroArgs *macro_NewArgs(void)
|
||||
MacroArgs *macro_NewArgs(void)
|
||||
{
|
||||
struct MacroArgs *args = new(std::nothrow) struct MacroArgs();
|
||||
MacroArgs *args = new(std::nothrow) MacroArgs();
|
||||
|
||||
if (!args)
|
||||
fatalerror("Unable to register macro arguments: %s\n", strerror(errno));
|
||||
@@ -43,7 +43,7 @@ struct MacroArgs *macro_NewArgs(void)
|
||||
return args;
|
||||
}
|
||||
|
||||
void macro_AppendArg(struct MacroArgs *args, char *s)
|
||||
void macro_AppendArg(MacroArgs *args, char *s)
|
||||
{
|
||||
if (s[0] == '\0')
|
||||
warning(WARNING_EMPTY_MACRO_ARG, "Empty macro argument\n");
|
||||
@@ -52,12 +52,12 @@ void macro_AppendArg(struct MacroArgs *args, char *s)
|
||||
args->args.push_back(s);
|
||||
}
|
||||
|
||||
void macro_UseNewArgs(struct MacroArgs *args)
|
||||
void macro_UseNewArgs(MacroArgs *args)
|
||||
{
|
||||
macroArgs = args;
|
||||
}
|
||||
|
||||
void macro_FreeArgs(struct MacroArgs *args)
|
||||
void macro_FreeArgs(MacroArgs *args)
|
||||
{
|
||||
for (char *arg : args->args)
|
||||
free(arg);
|
||||
|
||||
@@ -97,7 +97,7 @@ static int depType; // Variants of `-M`
|
||||
// except if it doesn't create any ambiguity (`verbose` versus `version`).
|
||||
// This is because long opt matching, even to a single char, is prioritized
|
||||
// over short opt matching
|
||||
static struct option const longopts[] = {
|
||||
static option const longopts[] = {
|
||||
{ "binary-digits", required_argument, NULL, 'b' },
|
||||
{ "define", required_argument, NULL, 'D' },
|
||||
{ "export-all", no_argument, NULL, 'E' },
|
||||
|
||||
@@ -31,7 +31,7 @@ struct OptStackEntry {
|
||||
enum WarningState warningStates[numWarningStates];
|
||||
};
|
||||
|
||||
static std::stack<struct OptStackEntry> stack;
|
||||
static std::stack<OptStackEntry> stack;
|
||||
|
||||
void opt_B(char const chars[2])
|
||||
{
|
||||
@@ -241,7 +241,7 @@ void opt_Parse(char *s)
|
||||
|
||||
void opt_Push(void)
|
||||
{
|
||||
struct OptStackEntry entry;
|
||||
OptStackEntry entry;
|
||||
|
||||
// Both of these are pulled from lexer.hpp
|
||||
entry.binary[0] = binDigits[0];
|
||||
@@ -280,7 +280,7 @@ void opt_Pop(void)
|
||||
return;
|
||||
}
|
||||
|
||||
struct OptStackEntry entry = stack.top();
|
||||
OptStackEntry entry = stack.top();
|
||||
stack.pop();
|
||||
|
||||
opt_B(entry.binary);
|
||||
|
||||
@@ -28,19 +28,19 @@
|
||||
#include "platform.hpp" // strdup
|
||||
|
||||
struct Assertion {
|
||||
struct Patch patch;
|
||||
struct Section *section;
|
||||
Patch patch;
|
||||
Section *section;
|
||||
std::string message;
|
||||
};
|
||||
|
||||
const char *objectName;
|
||||
|
||||
// List of symbols to put in the object file
|
||||
static std::vector<struct Symbol *> objectSymbols;
|
||||
static std::vector<Symbol *> objectSymbols;
|
||||
|
||||
static std::deque<struct Assertion> assertions;
|
||||
static std::deque<Assertion> assertions;
|
||||
|
||||
static std::deque<struct FileStackNode *> fileStackNodes;
|
||||
static std::deque<FileStackNode *> fileStackNodes;
|
||||
|
||||
// Write a long to a file (little-endian)
|
||||
static void putlong(uint32_t i, FILE *f)
|
||||
@@ -59,7 +59,7 @@ static void putstring(char const *s, FILE *f)
|
||||
putc(0, f);
|
||||
}
|
||||
|
||||
void out_RegisterNode(struct FileStackNode *node)
|
||||
void out_RegisterNode(FileStackNode *node)
|
||||
{
|
||||
// If node is not already registered, register it (and parents), and give it a unique ID
|
||||
for (; node && node->ID == (uint32_t)-1; node = node->parent) {
|
||||
@@ -68,7 +68,7 @@ void out_RegisterNode(struct FileStackNode *node)
|
||||
}
|
||||
}
|
||||
|
||||
void out_ReplaceNode(struct FileStackNode * /* node */)
|
||||
void out_ReplaceNode(FileStackNode * /* node */)
|
||||
{
|
||||
#if 0
|
||||
This is code intended to replace a node, which is pretty useless until ref counting is added...
|
||||
@@ -85,7 +85,7 @@ This is code intended to replace a node, which is pretty useless until ref count
|
||||
}
|
||||
|
||||
// Return a section's ID, or -1 if the section is not in the list
|
||||
static uint32_t getSectIDIfAny(struct Section *sect)
|
||||
static uint32_t getSectIDIfAny(Section *sect)
|
||||
{
|
||||
if (!sect)
|
||||
return (uint32_t)-1;
|
||||
@@ -99,7 +99,7 @@ static uint32_t getSectIDIfAny(struct Section *sect)
|
||||
}
|
||||
|
||||
// Write a patch to a file
|
||||
static void writepatch(struct Patch const &patch, FILE *f)
|
||||
static void writepatch(Patch const &patch, FILE *f)
|
||||
{
|
||||
assert(patch.src->ID != (uint32_t)-1);
|
||||
putlong(patch.src->ID, f);
|
||||
@@ -113,7 +113,7 @@ static void writepatch(struct Patch const &patch, FILE *f)
|
||||
}
|
||||
|
||||
// Write a section to a file
|
||||
static void writesection(struct Section const §, FILE *f)
|
||||
static void writesection(Section const §, FILE *f)
|
||||
{
|
||||
putstring(sect.name, f);
|
||||
|
||||
@@ -133,13 +133,13 @@ static void writesection(struct Section const §, FILE *f)
|
||||
fwrite(sect.data.data(), 1, sect.size, f);
|
||||
putlong(sect.patches.size(), f);
|
||||
|
||||
for (struct Patch const &patch : sect.patches)
|
||||
for (Patch const &patch : sect.patches)
|
||||
writepatch(patch, f);
|
||||
}
|
||||
}
|
||||
|
||||
// Write a symbol to a file
|
||||
static void writesymbol(struct Symbol const *sym, FILE *f)
|
||||
static void writesymbol(Symbol const *sym, FILE *f)
|
||||
{
|
||||
putstring(sym->name, f);
|
||||
if (!sym_IsDefined(sym)) {
|
||||
@@ -155,7 +155,7 @@ static void writesymbol(struct Symbol const *sym, FILE *f)
|
||||
}
|
||||
}
|
||||
|
||||
static void registerSymbol(struct Symbol *sym)
|
||||
static void registerSymbol(Symbol *sym)
|
||||
{
|
||||
sym->ID = objectSymbols.size();
|
||||
objectSymbols.push_back(sym);
|
||||
@@ -164,7 +164,7 @@ static void registerSymbol(struct Symbol *sym)
|
||||
|
||||
// Returns a symbol's ID within the object file
|
||||
// If the symbol does not have one, one is assigned by registering the symbol
|
||||
static uint32_t getSymbolID(struct Symbol *sym)
|
||||
static uint32_t getSymbolID(Symbol *sym)
|
||||
{
|
||||
if (sym->ID == (uint32_t)-1 && !sym_IsPC(sym))
|
||||
registerSymbol(sym);
|
||||
@@ -182,7 +182,7 @@ static void writerpn(std::vector<uint8_t> &rpnexpr, const std::vector<uint8_t> &
|
||||
uint8_t rpndata = popbyte();
|
||||
|
||||
switch (rpndata) {
|
||||
struct Symbol *sym;
|
||||
Symbol *sym;
|
||||
uint32_t value;
|
||||
uint8_t b;
|
||||
size_t i;
|
||||
@@ -267,9 +267,9 @@ static void writerpn(std::vector<uint8_t> &rpnexpr, const std::vector<uint8_t> &
|
||||
}
|
||||
}
|
||||
|
||||
static void initpatch(struct Patch &patch, uint32_t type, struct Expression const *expr, uint32_t ofs)
|
||||
static void initpatch(Patch &patch, uint32_t type, Expression const *expr, uint32_t ofs)
|
||||
{
|
||||
struct FileStackNode *node = fstk_GetFileStack();
|
||||
FileStackNode *node = fstk_GetFileStack();
|
||||
|
||||
patch.type = type;
|
||||
patch.src = node;
|
||||
@@ -295,10 +295,10 @@ static void initpatch(struct Patch &patch, uint32_t type, struct Expression cons
|
||||
}
|
||||
|
||||
// Create a new patch (includes the rpn expr)
|
||||
void out_CreatePatch(uint32_t type, struct Expression const *expr, uint32_t ofs, uint32_t pcShift)
|
||||
void out_CreatePatch(uint32_t type, Expression const *expr, uint32_t ofs, uint32_t pcShift)
|
||||
{
|
||||
// Add the patch to the list
|
||||
struct Patch &patch = currentSection->patches.emplace_front();
|
||||
Patch &patch = currentSection->patches.emplace_front();
|
||||
|
||||
initpatch(patch, type, expr, ofs);
|
||||
|
||||
@@ -309,22 +309,21 @@ void out_CreatePatch(uint32_t type, struct Expression const *expr, uint32_t ofs,
|
||||
}
|
||||
|
||||
// Creates an assert that will be written to the object file
|
||||
void out_CreateAssert(enum AssertionType type, struct Expression const *expr,
|
||||
char const *message, uint32_t ofs)
|
||||
void out_CreateAssert(enum AssertionType type, Expression const *expr, char const *message, uint32_t ofs)
|
||||
{
|
||||
struct Assertion &assertion = assertions.emplace_front();
|
||||
Assertion &assertion = assertions.emplace_front();
|
||||
|
||||
initpatch(assertion.patch, type, expr, ofs);
|
||||
assertion.message = message;
|
||||
}
|
||||
|
||||
static void writeassert(struct Assertion &assert, FILE *f)
|
||||
static void writeassert(Assertion &assert, FILE *f)
|
||||
{
|
||||
writepatch(assert.patch, f);
|
||||
putstring(assert.message.c_str(), f);
|
||||
}
|
||||
|
||||
static void writeFileStackNode(struct FileStackNode const *node, FILE *f)
|
||||
static void writeFileStackNode(FileStackNode const *node, FILE *f)
|
||||
{
|
||||
putlong(node->parent ? node->parent->ID : (uint32_t)-1, f);
|
||||
putlong(node->lineNo, f);
|
||||
@@ -341,7 +340,7 @@ static void writeFileStackNode(struct FileStackNode const *node, FILE *f)
|
||||
}
|
||||
}
|
||||
|
||||
static void registerUnregisteredSymbol(struct Symbol *symbol)
|
||||
static void registerUnregisteredSymbol(Symbol *symbol)
|
||||
{
|
||||
// Check for symbol->src, to skip any built-in symbol from rgbasm
|
||||
if (symbol->src && symbol->ID == (uint32_t)-1) {
|
||||
@@ -374,7 +373,7 @@ void out_WriteObject(void)
|
||||
|
||||
putlong(fileStackNodes.size(), f);
|
||||
for (auto it = fileStackNodes.begin(); it != fileStackNodes.end(); it++) {
|
||||
struct FileStackNode const *node = *it;
|
||||
FileStackNode const *node = *it;
|
||||
|
||||
writeFileStackNode(node, f);
|
||||
|
||||
@@ -385,15 +384,15 @@ void out_WriteObject(void)
|
||||
it[1]->ID, node->ID);
|
||||
}
|
||||
|
||||
for (struct Symbol const *sym : objectSymbols)
|
||||
for (Symbol const *sym : objectSymbols)
|
||||
writesymbol(sym, f);
|
||||
|
||||
for (struct Section § : sectionList)
|
||||
for (Section § : sectionList)
|
||||
writesection(sect, f);
|
||||
|
||||
putlong(assertions.size(), f);
|
||||
|
||||
for (struct Assertion &assert : assertions)
|
||||
for (Assertion &assert : assertions)
|
||||
writeassert(assert, f);
|
||||
|
||||
fclose(f);
|
||||
|
||||
@@ -31,7 +31,7 @@
|
||||
#include "linkdefs.hpp"
|
||||
#include "platform.hpp" // strncasecmp, strdup
|
||||
|
||||
static struct CaptureBody captureBody; // Captures a REPT/FOR or MACRO
|
||||
static CaptureBody captureBody; // Captures a REPT/FOR or MACRO
|
||||
|
||||
static void upperstring(char *dest, char const *src)
|
||||
{
|
||||
@@ -256,7 +256,7 @@ static void strrpl(char *dest, size_t destLen, char const *src, char const *old,
|
||||
dest[i] = '\0';
|
||||
}
|
||||
|
||||
static void initStrFmtArgList(struct StrFmtArgList *args)
|
||||
static void initStrFmtArgList(StrFmtArgList *args)
|
||||
{
|
||||
args->args = new(std::nothrow) std::vector<std::variant<uint32_t, char *>>();
|
||||
if (!args->args)
|
||||
@@ -264,7 +264,7 @@ static void initStrFmtArgList(struct StrFmtArgList *args)
|
||||
strerror(errno));
|
||||
}
|
||||
|
||||
static void freeStrFmtArgList(struct StrFmtArgList *args)
|
||||
static void freeStrFmtArgList(StrFmtArgList *args)
|
||||
{
|
||||
free(args->format);
|
||||
for (std::variant<uint32_t, char *> &arg : *args->args) {
|
||||
@@ -297,7 +297,7 @@ static void strfmt(char *dest, size_t destLen, char const *fmt,
|
||||
continue;
|
||||
}
|
||||
|
||||
struct FormatSpec spec = fmt_NewSpec();
|
||||
FormatSpec spec = fmt_NewSpec();
|
||||
|
||||
while (c != '\0') {
|
||||
fmt_UseCharacter(&spec, c);
|
||||
@@ -347,7 +347,7 @@ static void strfmt(char *dest, size_t destLen, char const *fmt,
|
||||
}
|
||||
|
||||
static void compoundAssignment(const char *symName, enum RPNCommand op, int32_t constValue) {
|
||||
struct Expression oldExpr, constExpr, newExpr;
|
||||
Expression oldExpr, constExpr, newExpr;
|
||||
int32_t newValue;
|
||||
|
||||
rpn_Symbol(&oldExpr, symName);
|
||||
@@ -357,9 +357,9 @@ static void compoundAssignment(const char *symName, enum RPNCommand op, int32_t
|
||||
sym_AddVar(symName, newValue);
|
||||
}
|
||||
|
||||
static void initDsArgList(std::vector<struct Expression> *&args)
|
||||
static void initDsArgList(std::vector<Expression> *&args)
|
||||
{
|
||||
args = new(std::nothrow) std::vector<struct Expression>();
|
||||
args = new(std::nothrow) std::vector<Expression>();
|
||||
if (!args)
|
||||
fatalerror("Failed to allocate memory for ds arg list: %s\n", strerror(errno));
|
||||
}
|
||||
@@ -455,18 +455,18 @@ enum {
|
||||
{
|
||||
char symName[MAXSYMLEN + 1];
|
||||
char string[MAXSTRLEN + 1];
|
||||
struct Expression expr;
|
||||
Expression expr;
|
||||
int32_t constValue;
|
||||
enum RPNCommand compoundEqual;
|
||||
enum SectionModifier sectMod;
|
||||
struct SectionSpec sectSpec;
|
||||
struct MacroArgs *macroArg;
|
||||
SectionSpec sectSpec;
|
||||
MacroArgs *macroArg;
|
||||
enum AssertionType assertType;
|
||||
struct AlignmentSpec alignSpec;
|
||||
std::vector<struct Expression> *dsArgs;
|
||||
AlignmentSpec alignSpec;
|
||||
std::vector<Expression> *dsArgs;
|
||||
std::vector<std::string> *purgeArgs;
|
||||
struct ForArgs forArgs;
|
||||
struct StrFmtArgList strfmtArgs;
|
||||
ForArgs forArgs;
|
||||
StrFmtArgList strfmtArgs;
|
||||
bool captureTerminated;
|
||||
}
|
||||
|
||||
@@ -704,7 +704,7 @@ line : plain_directive endofline
|
||||
lexer_SetMode(LEXER_NORMAL);
|
||||
lexer_ToggleStringExpansion(true);
|
||||
} endofline {
|
||||
struct Symbol *macro = sym_FindExactSymbol($1);
|
||||
Symbol *macro = sym_FindExactSymbol($1);
|
||||
|
||||
if (macro && macro->type == SYM_MACRO)
|
||||
fprintf(stderr,
|
||||
@@ -1649,11 +1649,11 @@ string : T_STRING
|
||||
freeStrFmtArgList(&$3);
|
||||
}
|
||||
| T_POP_SECTION T_LPAREN scoped_anon_id T_RPAREN {
|
||||
struct Symbol *sym = sym_FindScopedValidSymbol($3);
|
||||
Symbol *sym = sym_FindScopedValidSymbol($3);
|
||||
|
||||
if (!sym)
|
||||
fatalerror("Unknown symbol \"%s\"\n", $3);
|
||||
struct Section const *section = sym_GetSection(sym);
|
||||
Section const *section = sym_GetSection(sym);
|
||||
|
||||
if (!section)
|
||||
fatalerror("\"%s\" does not belong to any section\n", sym->name);
|
||||
|
||||
@@ -23,7 +23,7 @@
|
||||
|
||||
// Makes an expression "not known", also setting its error message
|
||||
template<typename... Ts>
|
||||
static void makeUnknown(struct Expression *expr, Ts ...parts)
|
||||
static void makeUnknown(Expression *expr, Ts ...parts)
|
||||
{
|
||||
expr->isKnown = false;
|
||||
expr->reason = new std::string();
|
||||
@@ -32,7 +32,7 @@ static void makeUnknown(struct Expression *expr, Ts ...parts)
|
||||
(expr->reason->append(parts), ...);
|
||||
}
|
||||
|
||||
static uint8_t *reserveSpace(struct Expression *expr, uint32_t size)
|
||||
static uint8_t *reserveSpace(Expression *expr, uint32_t size)
|
||||
{
|
||||
if (!expr->rpn) {
|
||||
expr->rpn = new(std::nothrow) std::vector<uint8_t>();
|
||||
@@ -47,7 +47,7 @@ static uint8_t *reserveSpace(struct Expression *expr, uint32_t size)
|
||||
}
|
||||
|
||||
// Init a RPN expression
|
||||
static void rpn_Init(struct Expression *expr)
|
||||
static void rpn_Init(Expression *expr)
|
||||
{
|
||||
expr->reason = NULL;
|
||||
expr->isKnown = true;
|
||||
@@ -57,7 +57,7 @@ static void rpn_Init(struct Expression *expr)
|
||||
}
|
||||
|
||||
// Free the RPN expression
|
||||
void rpn_Free(struct Expression *expr)
|
||||
void rpn_Free(Expression *expr)
|
||||
{
|
||||
delete expr->rpn;
|
||||
delete expr->reason;
|
||||
@@ -65,15 +65,15 @@ void rpn_Free(struct Expression *expr)
|
||||
}
|
||||
|
||||
// Add symbols, constants and operators to expression
|
||||
void rpn_Number(struct Expression *expr, uint32_t i)
|
||||
void rpn_Number(Expression *expr, uint32_t i)
|
||||
{
|
||||
rpn_Init(expr);
|
||||
expr->val = i;
|
||||
}
|
||||
|
||||
void rpn_Symbol(struct Expression *expr, char const *symName)
|
||||
void rpn_Symbol(Expression *expr, char const *symName)
|
||||
{
|
||||
struct Symbol *sym = sym_FindScopedSymbol(symName);
|
||||
Symbol *sym = sym_FindScopedSymbol(symName);
|
||||
|
||||
if (sym_IsPC(sym) && !sect_GetSymbolSection()) {
|
||||
error("PC has no value outside a section\n");
|
||||
@@ -98,7 +98,7 @@ void rpn_Symbol(struct Expression *expr, char const *symName)
|
||||
}
|
||||
}
|
||||
|
||||
void rpn_BankSelf(struct Expression *expr)
|
||||
void rpn_BankSelf(Expression *expr)
|
||||
{
|
||||
rpn_Init(expr);
|
||||
|
||||
@@ -114,9 +114,9 @@ void rpn_BankSelf(struct Expression *expr)
|
||||
}
|
||||
}
|
||||
|
||||
void rpn_BankSymbol(struct Expression *expr, char const *symName)
|
||||
void rpn_BankSymbol(Expression *expr, char const *symName)
|
||||
{
|
||||
struct Symbol const *sym = sym_FindScopedSymbol(symName);
|
||||
Symbol const *sym = sym_FindScopedSymbol(symName);
|
||||
|
||||
// The @ symbol is treated differently.
|
||||
if (sym_IsPC(sym)) {
|
||||
@@ -146,11 +146,11 @@ void rpn_BankSymbol(struct Expression *expr, char const *symName)
|
||||
}
|
||||
}
|
||||
|
||||
void rpn_BankSection(struct Expression *expr, char const *sectionName)
|
||||
void rpn_BankSection(Expression *expr, char const *sectionName)
|
||||
{
|
||||
rpn_Init(expr);
|
||||
|
||||
struct Section *section = sect_FindSectionByName(sectionName);
|
||||
Section *section = sect_FindSectionByName(sectionName);
|
||||
|
||||
if (section && section->bank != (uint32_t)-1) {
|
||||
expr->val = section->bank;
|
||||
@@ -166,11 +166,11 @@ void rpn_BankSection(struct Expression *expr, char const *sectionName)
|
||||
}
|
||||
}
|
||||
|
||||
void rpn_SizeOfSection(struct Expression *expr, char const *sectionName)
|
||||
void rpn_SizeOfSection(Expression *expr, char const *sectionName)
|
||||
{
|
||||
rpn_Init(expr);
|
||||
|
||||
struct Section *section = sect_FindSectionByName(sectionName);
|
||||
Section *section = sect_FindSectionByName(sectionName);
|
||||
|
||||
if (section && sect_IsSizeKnown(section)) {
|
||||
expr->val = section->size;
|
||||
@@ -186,11 +186,11 @@ void rpn_SizeOfSection(struct Expression *expr, char const *sectionName)
|
||||
}
|
||||
}
|
||||
|
||||
void rpn_StartOfSection(struct Expression *expr, char const *sectionName)
|
||||
void rpn_StartOfSection(Expression *expr, char const *sectionName)
|
||||
{
|
||||
rpn_Init(expr);
|
||||
|
||||
struct Section *section = sect_FindSectionByName(sectionName);
|
||||
Section *section = sect_FindSectionByName(sectionName);
|
||||
|
||||
if (section && section->org != (uint32_t)-1) {
|
||||
expr->val = section->org;
|
||||
@@ -206,7 +206,7 @@ void rpn_StartOfSection(struct Expression *expr, char const *sectionName)
|
||||
}
|
||||
}
|
||||
|
||||
void rpn_SizeOfSectionType(struct Expression *expr, enum SectionType type)
|
||||
void rpn_SizeOfSectionType(Expression *expr, enum SectionType type)
|
||||
{
|
||||
rpn_Init(expr);
|
||||
makeUnknown(expr, "Section type's size is not known");
|
||||
@@ -218,7 +218,7 @@ void rpn_SizeOfSectionType(struct Expression *expr, enum SectionType type)
|
||||
*ptr++ = type;
|
||||
}
|
||||
|
||||
void rpn_StartOfSectionType(struct Expression *expr, enum SectionType type)
|
||||
void rpn_StartOfSectionType(Expression *expr, enum SectionType type)
|
||||
{
|
||||
rpn_Init(expr);
|
||||
makeUnknown(expr, "Section type's start is not known");
|
||||
@@ -230,7 +230,7 @@ void rpn_StartOfSectionType(struct Expression *expr, enum SectionType type)
|
||||
*ptr++ = type;
|
||||
}
|
||||
|
||||
void rpn_CheckHRAM(struct Expression *expr, const struct Expression *src)
|
||||
void rpn_CheckHRAM(Expression *expr, const Expression *src)
|
||||
{
|
||||
*expr = *src;
|
||||
expr->isSymbol = false;
|
||||
@@ -246,7 +246,7 @@ void rpn_CheckHRAM(struct Expression *expr, const struct Expression *src)
|
||||
}
|
||||
}
|
||||
|
||||
void rpn_CheckRST(struct Expression *expr, const struct Expression *src)
|
||||
void rpn_CheckRST(Expression *expr, const Expression *src)
|
||||
{
|
||||
*expr = *src;
|
||||
|
||||
@@ -263,7 +263,7 @@ void rpn_CheckRST(struct Expression *expr, const struct Expression *src)
|
||||
}
|
||||
|
||||
// Checks that an RPN expression's value fits within N bits (signed or unsigned)
|
||||
void rpn_CheckNBit(struct Expression const *expr, uint8_t n)
|
||||
void rpn_CheckNBit(Expression const *expr, uint8_t n)
|
||||
{
|
||||
assert(n != 0); // That doesn't make sense
|
||||
assert(n < CHAR_BIT * sizeof(int)); // Otherwise `1 << n` is UB
|
||||
@@ -278,7 +278,7 @@ void rpn_CheckNBit(struct Expression const *expr, uint8_t n)
|
||||
}
|
||||
}
|
||||
|
||||
int32_t rpn_GetConstVal(struct Expression const *expr)
|
||||
int32_t rpn_GetConstVal(Expression const *expr)
|
||||
{
|
||||
if (!rpn_isKnown(expr)) {
|
||||
error("Expected constant expression: %s\n", expr->reason->c_str());
|
||||
@@ -287,7 +287,7 @@ int32_t rpn_GetConstVal(struct Expression const *expr)
|
||||
return expr->val;
|
||||
}
|
||||
|
||||
void rpn_LOGNOT(struct Expression *expr, const struct Expression *src)
|
||||
void rpn_LOGNOT(Expression *expr, const Expression *src)
|
||||
{
|
||||
*expr = *src;
|
||||
expr->isSymbol = false;
|
||||
@@ -300,28 +300,27 @@ void rpn_LOGNOT(struct Expression *expr, const struct Expression *src)
|
||||
}
|
||||
}
|
||||
|
||||
struct Symbol const *rpn_SymbolOf(struct Expression const *expr)
|
||||
Symbol const *rpn_SymbolOf(Expression const *expr)
|
||||
{
|
||||
if (!rpn_isSymbol(expr))
|
||||
return NULL;
|
||||
return sym_FindScopedSymbol((char const *)&(*expr->rpn)[1]);
|
||||
}
|
||||
|
||||
bool rpn_IsDiffConstant(struct Expression const *src, struct Symbol const *sym)
|
||||
bool rpn_IsDiffConstant(Expression const *src, Symbol const *sym)
|
||||
{
|
||||
// Check if both expressions only refer to a single symbol
|
||||
struct Symbol const *sym1 = rpn_SymbolOf(src);
|
||||
Symbol const *sym1 = rpn_SymbolOf(src);
|
||||
|
||||
if (!sym1 || !sym || sym1->type != SYM_LABEL || sym->type != SYM_LABEL)
|
||||
return false;
|
||||
|
||||
struct Section const *section1 = sym_GetSection(sym1);
|
||||
struct Section const *section2 = sym_GetSection(sym);
|
||||
Section const *section1 = sym_GetSection(sym1);
|
||||
Section const *section2 = sym_GetSection(sym);
|
||||
return section1 && (section1 == section2);
|
||||
}
|
||||
|
||||
static bool isDiffConstant(struct Expression const *src1,
|
||||
struct Expression const *src2)
|
||||
static bool isDiffConstant(Expression const *src1, Expression const *src2)
|
||||
{
|
||||
return rpn_IsDiffConstant(src1, rpn_SymbolOf(src2));
|
||||
}
|
||||
@@ -333,10 +332,10 @@ static bool isDiffConstant(struct Expression const *src1,
|
||||
*
|
||||
* @return The constant result if it can be computed, or -1 otherwise.
|
||||
*/
|
||||
static int32_t tryConstMask(struct Expression const *lhs, struct Expression const *rhs)
|
||||
static int32_t tryConstMask(Expression const *lhs, Expression const *rhs)
|
||||
{
|
||||
struct Symbol const *sym = rpn_SymbolOf(lhs);
|
||||
struct Expression const *expr = rhs;
|
||||
Symbol const *sym = rpn_SymbolOf(lhs);
|
||||
Expression const *expr = rhs;
|
||||
|
||||
if (!sym || !sym_GetSection(sym)) {
|
||||
// If the lhs isn't a symbol, try again the other way around
|
||||
@@ -351,7 +350,7 @@ static int32_t tryConstMask(struct Expression const *lhs, struct Expression cons
|
||||
if (!rpn_isKnown(expr))
|
||||
return -1;
|
||||
// We can now safely use `expr->val`
|
||||
struct Section const *sect = sym_GetSection(sym);
|
||||
Section const *sect = sym_GetSection(sym);
|
||||
int32_t unknownBits = (1 << 16) - (1 << sect->align); // The max alignment is 16
|
||||
|
||||
// The mask must ignore all unknown bits
|
||||
@@ -366,8 +365,7 @@ static int32_t tryConstMask(struct Expression const *lhs, struct Expression cons
|
||||
return (symbolOfs + sect->alignOfs) & ~unknownBits;
|
||||
}
|
||||
|
||||
void rpn_BinaryOp(enum RPNCommand op, struct Expression *expr,
|
||||
const struct Expression *src1, const struct Expression *src2)
|
||||
void rpn_BinaryOp(enum RPNCommand op, Expression *expr, const Expression *src1, const Expression *src2)
|
||||
{
|
||||
expr->isSymbol = false;
|
||||
int32_t constMaskVal;
|
||||
@@ -512,8 +510,8 @@ void rpn_BinaryOp(enum RPNCommand op, struct Expression *expr,
|
||||
}
|
||||
|
||||
} else if (op == RPN_SUB && isDiffConstant(src1, src2)) {
|
||||
struct Symbol const *symbol1 = rpn_SymbolOf(src1);
|
||||
struct Symbol const *symbol2 = rpn_SymbolOf(src2);
|
||||
Symbol const *symbol1 = rpn_SymbolOf(src1);
|
||||
Symbol const *symbol2 = rpn_SymbolOf(src2);
|
||||
|
||||
expr->val = sym_GetValue(symbol1) - sym_GetValue(symbol2);
|
||||
expr->isKnown = true;
|
||||
@@ -574,7 +572,7 @@ void rpn_BinaryOp(enum RPNCommand op, struct Expression *expr,
|
||||
}
|
||||
}
|
||||
|
||||
void rpn_HIGH(struct Expression *expr, const struct Expression *src)
|
||||
void rpn_HIGH(Expression *expr, const Expression *src)
|
||||
{
|
||||
*expr = *src;
|
||||
expr->isSymbol = false;
|
||||
@@ -589,7 +587,7 @@ void rpn_HIGH(struct Expression *expr, const struct Expression *src)
|
||||
}
|
||||
}
|
||||
|
||||
void rpn_LOW(struct Expression *expr, const struct Expression *src)
|
||||
void rpn_LOW(Expression *expr, const Expression *src)
|
||||
{
|
||||
*expr = *src;
|
||||
expr->isSymbol = false;
|
||||
@@ -604,7 +602,7 @@ void rpn_LOW(struct Expression *expr, const struct Expression *src)
|
||||
}
|
||||
}
|
||||
|
||||
void rpn_ISCONST(struct Expression *expr, const struct Expression *src)
|
||||
void rpn_ISCONST(Expression *expr, const Expression *src)
|
||||
{
|
||||
rpn_Init(expr);
|
||||
expr->val = rpn_isKnown(src);
|
||||
@@ -612,7 +610,7 @@ void rpn_ISCONST(struct Expression *expr, const struct Expression *src)
|
||||
expr->isSymbol = false;
|
||||
}
|
||||
|
||||
void rpn_NEG(struct Expression *expr, const struct Expression *src)
|
||||
void rpn_NEG(Expression *expr, const Expression *src)
|
||||
{
|
||||
*expr = *src;
|
||||
expr->isSymbol = false;
|
||||
@@ -625,7 +623,7 @@ void rpn_NEG(struct Expression *expr, const struct Expression *src)
|
||||
}
|
||||
}
|
||||
|
||||
void rpn_NOT(struct Expression *expr, const struct Expression *src)
|
||||
void rpn_NOT(Expression *expr, const Expression *src)
|
||||
{
|
||||
*expr = *src;
|
||||
expr->isSymbol = false;
|
||||
|
||||
@@ -33,20 +33,20 @@ struct UnionStackEntry {
|
||||
};
|
||||
|
||||
struct SectionStackEntry {
|
||||
struct Section *section;
|
||||
struct Section *loadSection;
|
||||
Section *section;
|
||||
Section *loadSection;
|
||||
char const *scope; // Section's symbol scope
|
||||
uint32_t offset;
|
||||
int32_t loadOffset;
|
||||
std::stack<struct UnionStackEntry> unionStack;
|
||||
std::stack<UnionStackEntry> unionStack;
|
||||
};
|
||||
|
||||
std::stack<struct UnionStackEntry> currentUnionStack;
|
||||
std::deque<struct SectionStackEntry> sectionStack;
|
||||
std::deque<struct Section> sectionList;
|
||||
std::stack<UnionStackEntry> currentUnionStack;
|
||||
std::deque<SectionStackEntry> sectionStack;
|
||||
std::deque<Section> sectionList;
|
||||
uint32_t curOffset; // Offset into the current section (see sect_GetSymbolOffset)
|
||||
struct Section *currentSection = NULL;
|
||||
static struct Section *currentLoadSection = NULL;
|
||||
Section *currentSection = NULL;
|
||||
static Section *currentLoadSection = NULL;
|
||||
char const *currentLoadScope = NULL;
|
||||
int32_t loadOffset; // Offset into the LOAD section's parent (see sect_GetOutputOffset)
|
||||
|
||||
@@ -75,7 +75,7 @@ attr_(warn_unused_result) static bool checkcodesection(void)
|
||||
return false;
|
||||
}
|
||||
|
||||
attr_(warn_unused_result) static bool checkSectionSize(struct Section const *sect, uint32_t size)
|
||||
attr_(warn_unused_result) static bool checkSectionSize(Section const *sect, uint32_t size)
|
||||
{
|
||||
uint32_t maxSize = sectionTypeInfo[sect->type].size;
|
||||
|
||||
@@ -110,9 +110,9 @@ attr_(warn_unused_result) static bool reserveSpace(uint32_t delta_size)
|
||||
&& (!currentLoadSection || currentLoadSection->size != UINT32_MAX);
|
||||
}
|
||||
|
||||
struct Section *sect_FindSectionByName(char const *name)
|
||||
Section *sect_FindSectionByName(char const *name)
|
||||
{
|
||||
for (struct Section § : sectionList) {
|
||||
for (Section § : sectionList) {
|
||||
if (strcmp(name, sect.name) == 0)
|
||||
return §
|
||||
}
|
||||
@@ -126,7 +126,7 @@ do { \
|
||||
nbSectErrors++; \
|
||||
} while (0)
|
||||
|
||||
static unsigned int mergeSectUnion(struct Section *sect, enum SectionType type, uint32_t org,
|
||||
static unsigned int mergeSectUnion(Section *sect, enum SectionType type, uint32_t org,
|
||||
uint8_t alignment, uint16_t alignOffset)
|
||||
{
|
||||
assert(alignment < 16); // Should be ensured by the caller
|
||||
@@ -171,8 +171,7 @@ static unsigned int mergeSectUnion(struct Section *sect, enum SectionType type,
|
||||
return nbSectErrors;
|
||||
}
|
||||
|
||||
static unsigned int mergeFragments(struct Section *sect, uint32_t org, uint8_t alignment,
|
||||
uint16_t alignOffset)
|
||||
static unsigned int mergeFragments(Section *sect, uint32_t org, uint8_t alignment, uint16_t alignOffset)
|
||||
{
|
||||
assert(alignment < 16); // Should be ensured by the caller
|
||||
unsigned int nbSectErrors = 0;
|
||||
@@ -220,7 +219,7 @@ static unsigned int mergeFragments(struct Section *sect, uint32_t org, uint8_t a
|
||||
return nbSectErrors;
|
||||
}
|
||||
|
||||
static void mergeSections(struct Section *sect, enum SectionType type, uint32_t org, uint32_t bank,
|
||||
static void mergeSections(Section *sect, enum SectionType type, uint32_t org, uint32_t bank,
|
||||
uint8_t alignment, uint16_t alignOffset, enum SectionModifier mod)
|
||||
{
|
||||
unsigned int nbSectErrors = 0;
|
||||
@@ -265,12 +264,11 @@ static void mergeSections(struct Section *sect, enum SectionType type, uint32_t
|
||||
#undef fail
|
||||
|
||||
// Create a new section, not yet in the list.
|
||||
static struct Section *createSection(char const *name, enum SectionType type,
|
||||
uint32_t org, uint32_t bank, uint8_t alignment,
|
||||
uint16_t alignOffset, enum SectionModifier mod)
|
||||
static Section *createSection(char const *name, enum SectionType type, uint32_t org, uint32_t bank,
|
||||
uint8_t alignment, uint16_t alignOffset, enum SectionModifier mod)
|
||||
{
|
||||
// Add the new section to the list (order doesn't matter)
|
||||
struct Section § = sectionList.emplace_front();
|
||||
Section § = sectionList.emplace_front();
|
||||
|
||||
sect.name = strdup(name);
|
||||
if (sect.name == NULL)
|
||||
@@ -294,8 +292,8 @@ static struct Section *createSection(char const *name, enum SectionType type,
|
||||
}
|
||||
|
||||
// Find a section by name and type. If it doesn't exist, create it.
|
||||
static struct Section *getSection(char const *name, enum SectionType type, uint32_t org,
|
||||
struct SectionSpec const *attrs, enum SectionModifier mod)
|
||||
static Section *getSection(char const *name, enum SectionType type, uint32_t org,
|
||||
SectionSpec const *attrs, enum SectionModifier mod)
|
||||
{
|
||||
uint32_t bank = attrs->bank;
|
||||
uint8_t alignment = attrs->alignment;
|
||||
@@ -357,7 +355,7 @@ static struct Section *getSection(char const *name, enum SectionType type, uint3
|
||||
|
||||
// Check if another section exists with the same name; merge if yes, otherwise create one
|
||||
|
||||
struct Section *sect = sect_FindSectionByName(name);
|
||||
Section *sect = sect_FindSectionByName(name);
|
||||
|
||||
if (sect) {
|
||||
mergeSections(sect, type, org, bank, alignment, alignOffset, mod);
|
||||
@@ -379,17 +377,17 @@ static void changeSection(void)
|
||||
|
||||
// Set the current section by name and type
|
||||
void sect_NewSection(char const *name, enum SectionType type, uint32_t org,
|
||||
struct SectionSpec const *attribs, enum SectionModifier mod)
|
||||
SectionSpec const *attribs, enum SectionModifier mod)
|
||||
{
|
||||
if (currentLoadSection)
|
||||
fatalerror("Cannot change the section within a `LOAD` block\n");
|
||||
|
||||
for (struct SectionStackEntry &entry : sectionStack) {
|
||||
for (SectionStackEntry &entry : sectionStack) {
|
||||
if (entry.section && !strcmp(name, entry.section->name))
|
||||
fatalerror("Section '%s' is already on the stack\n", name);
|
||||
}
|
||||
|
||||
struct Section *sect = getSection(name, type, org, attribs, mod);
|
||||
Section *sect = getSection(name, type, org, attribs, mod);
|
||||
|
||||
changeSection();
|
||||
curOffset = mod == SECTION_UNION ? 0 : sect->size;
|
||||
@@ -399,7 +397,7 @@ void sect_NewSection(char const *name, enum SectionType type, uint32_t org,
|
||||
|
||||
// Set the current section by name and type
|
||||
void sect_SetLoadSection(char const *name, enum SectionType type, uint32_t org,
|
||||
struct SectionSpec const *attribs, enum SectionModifier mod)
|
||||
SectionSpec const *attribs, enum SectionModifier mod)
|
||||
{
|
||||
// Important info: currently, UNION and LOAD cannot interact, since UNION is prohibited in
|
||||
// "code" sections, whereas LOAD is restricted to them.
|
||||
@@ -424,7 +422,7 @@ void sect_SetLoadSection(char const *name, enum SectionType type, uint32_t org,
|
||||
return;
|
||||
}
|
||||
|
||||
struct Section *sect = getSection(name, type, org, attribs, mod);
|
||||
Section *sect = getSection(name, type, org, attribs, mod);
|
||||
|
||||
currentLoadScope = sym_GetCurrentSymbolScope();
|
||||
changeSection();
|
||||
@@ -447,7 +445,7 @@ void sect_EndLoadSection(void)
|
||||
sym_SetCurrentSymbolScope(currentLoadScope);
|
||||
}
|
||||
|
||||
struct Section *sect_GetSymbolSection(void)
|
||||
Section *sect_GetSymbolSection(void)
|
||||
{
|
||||
return currentLoadSection ? currentLoadSection : currentSection;
|
||||
}
|
||||
@@ -466,7 +464,7 @@ uint32_t sect_GetOutputOffset(void)
|
||||
// Returns how many bytes need outputting for the specified alignment and offset to succeed
|
||||
uint32_t sect_GetAlignBytes(uint8_t alignment, uint16_t offset)
|
||||
{
|
||||
struct Section *sect = sect_GetSymbolSection();
|
||||
Section *sect = sect_GetSymbolSection();
|
||||
if (!sect)
|
||||
return 0;
|
||||
|
||||
@@ -489,7 +487,7 @@ void sect_AlignPC(uint8_t alignment, uint16_t offset)
|
||||
if (!checksection())
|
||||
return;
|
||||
|
||||
struct Section *sect = sect_GetSymbolSection();
|
||||
Section *sect = sect_GetSymbolSection();
|
||||
uint32_t alignSize = 1 << alignment; // Size of an aligned "block"
|
||||
|
||||
if (sect->org != (uint32_t)-1) {
|
||||
@@ -544,7 +542,7 @@ static void writelong(uint32_t b)
|
||||
writebyte(b >> 24);
|
||||
}
|
||||
|
||||
static void createPatch(enum PatchType type, struct Expression const *expr, uint32_t pcShift)
|
||||
static void createPatch(enum PatchType type, Expression const *expr, uint32_t pcShift)
|
||||
{
|
||||
out_CreatePatch(type, expr, sect_GetOutputOffset(), pcShift);
|
||||
}
|
||||
@@ -570,7 +568,7 @@ void sect_StartUnion(void)
|
||||
|
||||
static void endUnionMember(void)
|
||||
{
|
||||
struct UnionStackEntry &member = currentUnionStack.top();
|
||||
UnionStackEntry &member = currentUnionStack.top();
|
||||
uint32_t memberSize = curOffset - member.start;
|
||||
|
||||
if (memberSize > member.size)
|
||||
@@ -670,7 +668,7 @@ void sect_Skip(uint32_t skip, bool ds)
|
||||
|
||||
// Output a relocatable byte. Checking will be done to see if it
|
||||
// is an absolute value in disguise.
|
||||
void sect_RelByte(struct Expression *expr, uint32_t pcShift)
|
||||
void sect_RelByte(Expression *expr, uint32_t pcShift)
|
||||
{
|
||||
if (!checkcodesection())
|
||||
return;
|
||||
@@ -688,7 +686,7 @@ void sect_RelByte(struct Expression *expr, uint32_t pcShift)
|
||||
|
||||
// Output several copies of a relocatable byte. Checking will be done to see if
|
||||
// it is an absolute value in disguise.
|
||||
void sect_RelBytes(uint32_t n, std::vector<struct Expression> &exprs)
|
||||
void sect_RelBytes(uint32_t n, std::vector<Expression> &exprs)
|
||||
{
|
||||
if (!checkcodesection())
|
||||
return;
|
||||
@@ -696,7 +694,7 @@ void sect_RelBytes(uint32_t n, std::vector<struct Expression> &exprs)
|
||||
return;
|
||||
|
||||
for (uint32_t i = 0; i < n; i++) {
|
||||
struct Expression &expr = exprs[i % exprs.size()];
|
||||
Expression &expr = exprs[i % exprs.size()];
|
||||
|
||||
if (!rpn_isKnown(&expr)) {
|
||||
createPatch(PATCHTYPE_BYTE, &expr, i);
|
||||
@@ -706,13 +704,13 @@ void sect_RelBytes(uint32_t n, std::vector<struct Expression> &exprs)
|
||||
}
|
||||
}
|
||||
|
||||
for (struct Expression &expr : exprs)
|
||||
for (Expression &expr : exprs)
|
||||
rpn_Free(&expr);
|
||||
}
|
||||
|
||||
// Output a relocatable word. Checking will be done to see if
|
||||
// it's an absolute value in disguise.
|
||||
void sect_RelWord(struct Expression *expr, uint32_t pcShift)
|
||||
void sect_RelWord(Expression *expr, uint32_t pcShift)
|
||||
{
|
||||
if (!checkcodesection())
|
||||
return;
|
||||
@@ -730,7 +728,7 @@ void sect_RelWord(struct Expression *expr, uint32_t pcShift)
|
||||
|
||||
// Output a relocatable longword. Checking will be done to see if
|
||||
// is an absolute value in disguise.
|
||||
void sect_RelLong(struct Expression *expr, uint32_t pcShift)
|
||||
void sect_RelLong(Expression *expr, uint32_t pcShift)
|
||||
{
|
||||
if (!checkcodesection())
|
||||
return;
|
||||
@@ -748,19 +746,19 @@ void sect_RelLong(struct Expression *expr, uint32_t pcShift)
|
||||
|
||||
// Output a PC-relative relocatable byte. Checking will be done to see if it
|
||||
// is an absolute value in disguise.
|
||||
void sect_PCRelByte(struct Expression *expr, uint32_t pcShift)
|
||||
void sect_PCRelByte(Expression *expr, uint32_t pcShift)
|
||||
{
|
||||
if (!checkcodesection())
|
||||
return;
|
||||
if (!reserveSpace(1))
|
||||
return;
|
||||
struct Symbol const *pc = sym_GetPC();
|
||||
Symbol const *pc = sym_GetPC();
|
||||
|
||||
if (!rpn_IsDiffConstant(expr, pc)) {
|
||||
createPatch(PATCHTYPE_JR, expr, pcShift);
|
||||
writebyte(0);
|
||||
} else {
|
||||
struct Symbol const *sym = rpn_SymbolOf(expr);
|
||||
Symbol const *sym = rpn_SymbolOf(expr);
|
||||
// The offset wraps (jump from ROM to HRAM, for example)
|
||||
int16_t offset;
|
||||
|
||||
@@ -948,7 +946,7 @@ void sect_PopSection(void)
|
||||
if (currentLoadSection)
|
||||
fatalerror("Cannot change the section within a `LOAD` block\n");
|
||||
|
||||
struct SectionStackEntry entry = sectionStack.front();
|
||||
SectionStackEntry entry = sectionStack.front();
|
||||
sectionStack.pop_front();
|
||||
|
||||
changeSection();
|
||||
@@ -976,7 +974,7 @@ void sect_EndSection(void)
|
||||
sym_SetCurrentSymbolScope(NULL);
|
||||
}
|
||||
|
||||
bool sect_IsSizeKnown(struct Section const NONNULL(sect))
|
||||
bool sect_IsSizeKnown(Section const NONNULL(sect))
|
||||
{
|
||||
// SECTION UNION and SECTION FRAGMENT can still grow
|
||||
if (sect->modifier != SECTION_NORMAL)
|
||||
@@ -987,7 +985,7 @@ bool sect_IsSizeKnown(struct Section const NONNULL(sect))
|
||||
return false;
|
||||
|
||||
// Any section on the stack is still growing
|
||||
for (struct SectionStackEntry &entry : sectionStack) {
|
||||
for (SectionStackEntry &entry : sectionStack) {
|
||||
if (entry.section && !strcmp(sect->name, entry.section->name))
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -27,23 +27,23 @@
|
||||
#include "helpers.hpp"
|
||||
#include "version.hpp"
|
||||
|
||||
std::map<std::string, struct Symbol> symbols;
|
||||
std::map<std::string, Symbol> symbols;
|
||||
|
||||
static const char *labelScope; // Current section's label scope
|
||||
static struct Symbol *PCSymbol;
|
||||
static struct Symbol *_NARGSymbol;
|
||||
static Symbol *PCSymbol;
|
||||
static Symbol *_NARGSymbol;
|
||||
static char savedTIME[256];
|
||||
static char savedDATE[256];
|
||||
static char savedTIMESTAMP_ISO8601_LOCAL[256];
|
||||
static char savedTIMESTAMP_ISO8601_UTC[256];
|
||||
static bool exportAll;
|
||||
|
||||
bool sym_IsPC(struct Symbol const *sym)
|
||||
bool sym_IsPC(Symbol const *sym)
|
||||
{
|
||||
return sym == PCSymbol;
|
||||
}
|
||||
|
||||
void sym_ForEach(void (*callback)(struct Symbol *))
|
||||
void sym_ForEach(void (*callback)(Symbol *))
|
||||
{
|
||||
for (auto &it : symbols)
|
||||
callback(&it.second);
|
||||
@@ -60,13 +60,13 @@ static int32_t Callback_NARG(void)
|
||||
|
||||
static int32_t CallbackPC(void)
|
||||
{
|
||||
struct Section const *section = sect_GetSymbolSection();
|
||||
Section const *section = sect_GetSymbolSection();
|
||||
|
||||
return section ? section->org + sect_GetSymbolOffset() : 0;
|
||||
}
|
||||
|
||||
// Get the value field of a symbol
|
||||
int32_t sym_GetValue(struct Symbol const *sym)
|
||||
int32_t sym_GetValue(Symbol const *sym)
|
||||
{
|
||||
if (sym_IsNumeric(sym) && sym->hasCallback)
|
||||
return sym->numCallback();
|
||||
@@ -78,7 +78,7 @@ int32_t sym_GetValue(struct Symbol const *sym)
|
||||
return sym->value;
|
||||
}
|
||||
|
||||
static void dumpFilename(struct Symbol const *sym)
|
||||
static void dumpFilename(Symbol const *sym)
|
||||
{
|
||||
if (sym->src)
|
||||
fstk_Dump(sym->src, sym->fileLine);
|
||||
@@ -89,16 +89,16 @@ static void dumpFilename(struct Symbol const *sym)
|
||||
}
|
||||
|
||||
// Set a symbol's definition filename and line
|
||||
static void setSymbolFilename(struct Symbol *sym)
|
||||
static void setSymbolFilename(Symbol *sym)
|
||||
{
|
||||
sym->src = fstk_GetFileStack();
|
||||
sym->fileLine = sym->src ? lexer_GetLineNo() : 0; // This is (NULL, 1) for built-ins
|
||||
}
|
||||
|
||||
// Update a symbol's definition filename and line
|
||||
static void updateSymbolFilename(struct Symbol *sym)
|
||||
static void updateSymbolFilename(Symbol *sym)
|
||||
{
|
||||
struct FileStackNode *oldSrc = sym->src;
|
||||
FileStackNode *oldSrc = sym->src;
|
||||
|
||||
setSymbolFilename(sym);
|
||||
// If the old node was referenced, ensure the new one is
|
||||
@@ -108,9 +108,9 @@ static void updateSymbolFilename(struct Symbol *sym)
|
||||
}
|
||||
|
||||
// Create a new symbol by name
|
||||
static struct Symbol *createsymbol(char const *symName)
|
||||
static Symbol *createsymbol(char const *symName)
|
||||
{
|
||||
struct Symbol &sym = symbols[symName];
|
||||
Symbol &sym = symbols[symName];
|
||||
|
||||
if (snprintf(sym.name, MAXSYMLEN + 1, "%s", symName) > MAXSYMLEN)
|
||||
warning(WARNING_LONG_STR, "Symbol name is too long: '%s'\n", symName);
|
||||
@@ -138,7 +138,7 @@ static void fullSymbolName(char *output, size_t outputSize,
|
||||
fatalerror("Symbol name is too long: '%s%s'\n", scopeName, localName);
|
||||
}
|
||||
|
||||
static void assignStringSymbol(struct Symbol *sym, char const *value)
|
||||
static void assignStringSymbol(Symbol *sym, char const *value)
|
||||
{
|
||||
char *string = strdup(value);
|
||||
|
||||
@@ -150,13 +150,13 @@ static void assignStringSymbol(struct Symbol *sym, char const *value)
|
||||
sym->equs.size = strlen(string);
|
||||
}
|
||||
|
||||
struct Symbol *sym_FindExactSymbol(char const *symName)
|
||||
Symbol *sym_FindExactSymbol(char const *symName)
|
||||
{
|
||||
auto search = symbols.find(symName);
|
||||
return search != symbols.end() ? &search->second : NULL;
|
||||
}
|
||||
|
||||
struct Symbol *sym_FindScopedSymbol(char const *symName)
|
||||
Symbol *sym_FindScopedSymbol(char const *symName)
|
||||
{
|
||||
if (char const *localName = strchr(symName, '.'); localName) {
|
||||
if (strchr(localName + 1, '.'))
|
||||
@@ -173,9 +173,9 @@ struct Symbol *sym_FindScopedSymbol(char const *symName)
|
||||
return sym_FindExactSymbol(symName);
|
||||
}
|
||||
|
||||
struct Symbol *sym_FindScopedValidSymbol(char const *symName)
|
||||
Symbol *sym_FindScopedValidSymbol(char const *symName)
|
||||
{
|
||||
struct Symbol *sym = sym_FindScopedSymbol(symName);
|
||||
Symbol *sym = sym_FindScopedSymbol(symName);
|
||||
|
||||
// `@` has no value outside a section
|
||||
if (sym == PCSymbol && !sect_GetSymbolSection()) {
|
||||
@@ -188,12 +188,12 @@ struct Symbol *sym_FindScopedValidSymbol(char const *symName)
|
||||
return sym;
|
||||
}
|
||||
|
||||
struct Symbol const *sym_GetPC(void)
|
||||
Symbol const *sym_GetPC(void)
|
||||
{
|
||||
return PCSymbol;
|
||||
}
|
||||
|
||||
static bool isReferenced(struct Symbol const *sym)
|
||||
static bool isReferenced(Symbol const *sym)
|
||||
{
|
||||
return sym->ID != (uint32_t)-1;
|
||||
}
|
||||
@@ -201,7 +201,7 @@ static bool isReferenced(struct Symbol const *sym)
|
||||
// Purge a symbol
|
||||
void sym_Purge(std::string const &symName)
|
||||
{
|
||||
struct Symbol *sym = sym_FindScopedValidSymbol(symName.c_str());
|
||||
Symbol *sym = sym_FindScopedValidSymbol(symName.c_str());
|
||||
|
||||
if (!sym) {
|
||||
error("'%s' not defined\n", symName.c_str());
|
||||
@@ -223,7 +223,7 @@ void sym_Purge(std::string const &symName)
|
||||
|
||||
uint32_t sym_GetPCValue(void)
|
||||
{
|
||||
struct Section const *sect = sect_GetSymbolSection();
|
||||
Section const *sect = sect_GetSymbolSection();
|
||||
|
||||
if (!sect)
|
||||
error("PC has no value outside a section\n");
|
||||
@@ -235,7 +235,7 @@ uint32_t sym_GetPCValue(void)
|
||||
}
|
||||
|
||||
// Return a constant symbol's value, assuming it's defined
|
||||
uint32_t sym_GetConstantSymValue(struct Symbol const *sym)
|
||||
uint32_t sym_GetConstantSymValue(Symbol const *sym)
|
||||
{
|
||||
if (sym == PCSymbol)
|
||||
return sym_GetPCValue();
|
||||
@@ -250,7 +250,7 @@ uint32_t sym_GetConstantSymValue(struct Symbol const *sym)
|
||||
// Return a constant symbol's value
|
||||
uint32_t sym_GetConstantValue(char const *symName)
|
||||
{
|
||||
struct Symbol const *sym = sym_FindScopedSymbol(symName);
|
||||
Symbol const *sym = sym_FindScopedSymbol(symName);
|
||||
|
||||
if (!sym)
|
||||
error("'%s' not defined\n", symName);
|
||||
@@ -277,9 +277,9 @@ void sym_SetCurrentSymbolScope(char const *newScope)
|
||||
* @param symName The name of the symbol to create
|
||||
* @param numeric If false, the symbol may not have been referenced earlier
|
||||
*/
|
||||
static struct Symbol *createNonrelocSymbol(char const *symName, bool numeric)
|
||||
static Symbol *createNonrelocSymbol(char const *symName, bool numeric)
|
||||
{
|
||||
struct Symbol *sym = sym_FindExactSymbol(symName);
|
||||
Symbol *sym = sym_FindExactSymbol(symName);
|
||||
|
||||
if (!sym) {
|
||||
sym = createsymbol(symName);
|
||||
@@ -300,9 +300,9 @@ static struct Symbol *createNonrelocSymbol(char const *symName, bool numeric)
|
||||
}
|
||||
|
||||
// Add an equated symbol
|
||||
struct Symbol *sym_AddEqu(char const *symName, int32_t value)
|
||||
Symbol *sym_AddEqu(char const *symName, int32_t value)
|
||||
{
|
||||
struct Symbol *sym = createNonrelocSymbol(symName, true);
|
||||
Symbol *sym = createNonrelocSymbol(symName, true);
|
||||
|
||||
if (!sym)
|
||||
return NULL;
|
||||
@@ -313,9 +313,9 @@ struct Symbol *sym_AddEqu(char const *symName, int32_t value)
|
||||
return sym;
|
||||
}
|
||||
|
||||
struct Symbol *sym_RedefEqu(char const *symName, int32_t value)
|
||||
Symbol *sym_RedefEqu(char const *symName, int32_t value)
|
||||
{
|
||||
struct Symbol *sym = sym_FindExactSymbol(symName);
|
||||
Symbol *sym = sym_FindExactSymbol(symName);
|
||||
|
||||
if (!sym)
|
||||
return sym_AddEqu(symName, value);
|
||||
@@ -349,9 +349,9 @@ struct Symbol *sym_RedefEqu(char const *symName, int32_t value)
|
||||
* of the string are enough: sym_AddString("M_PI", "3.1415"). This is the same
|
||||
* as ``` M_PI EQUS "3.1415" ```
|
||||
*/
|
||||
struct Symbol *sym_AddString(char const *symName, char const *value)
|
||||
Symbol *sym_AddString(char const *symName, char const *value)
|
||||
{
|
||||
struct Symbol *sym = createNonrelocSymbol(symName, false);
|
||||
Symbol *sym = createNonrelocSymbol(symName, false);
|
||||
|
||||
if (!sym)
|
||||
return NULL;
|
||||
@@ -360,9 +360,9 @@ struct Symbol *sym_AddString(char const *symName, char const *value)
|
||||
return sym;
|
||||
}
|
||||
|
||||
struct Symbol *sym_RedefString(char const *symName, char const *value)
|
||||
Symbol *sym_RedefString(char const *symName, char const *value)
|
||||
{
|
||||
struct Symbol *sym = sym_FindExactSymbol(symName);
|
||||
Symbol *sym = sym_FindExactSymbol(symName);
|
||||
|
||||
if (!sym)
|
||||
return sym_AddString(symName, value);
|
||||
@@ -389,9 +389,9 @@ struct Symbol *sym_RedefString(char const *symName, char const *value)
|
||||
}
|
||||
|
||||
// Alter a mutable symbol's value
|
||||
struct Symbol *sym_AddVar(char const *symName, int32_t value)
|
||||
Symbol *sym_AddVar(char const *symName, int32_t value)
|
||||
{
|
||||
struct Symbol *sym = sym_FindExactSymbol(symName);
|
||||
Symbol *sym = sym_FindExactSymbol(symName);
|
||||
|
||||
if (!sym) {
|
||||
sym = createsymbol(symName);
|
||||
@@ -416,10 +416,10 @@ struct Symbol *sym_AddVar(char const *symName, int32_t value)
|
||||
* @param symName The label's full name (so `.name` is invalid)
|
||||
* @return The created symbol
|
||||
*/
|
||||
static struct Symbol *addLabel(char const *symName)
|
||||
static Symbol *addLabel(char const *symName)
|
||||
{
|
||||
assert(symName[0] != '.'); // The symbol name must have been expanded prior
|
||||
struct Symbol *sym = sym_FindExactSymbol(symName);
|
||||
Symbol *sym = sym_FindExactSymbol(symName);
|
||||
|
||||
if (!sym) {
|
||||
sym = createsymbol(symName);
|
||||
@@ -445,7 +445,7 @@ static struct Symbol *addLabel(char const *symName)
|
||||
}
|
||||
|
||||
// Add a local (`.name` or `Parent.name`) relocatable symbol
|
||||
struct Symbol *sym_AddLocalLabel(char const *symName)
|
||||
Symbol *sym_AddLocalLabel(char const *symName)
|
||||
{
|
||||
// Assuming no dots in `labelScope` if defined
|
||||
assert(!labelScope || !strchr(labelScope, '.'));
|
||||
@@ -479,9 +479,9 @@ struct Symbol *sym_AddLocalLabel(char const *symName)
|
||||
}
|
||||
|
||||
// Add a relocatable symbol
|
||||
struct Symbol *sym_AddLabel(char const *symName)
|
||||
Symbol *sym_AddLabel(char const *symName)
|
||||
{
|
||||
struct Symbol *sym = addLabel(symName);
|
||||
Symbol *sym = addLabel(symName);
|
||||
|
||||
// Set the symbol as the new scope
|
||||
if (sym)
|
||||
@@ -492,7 +492,7 @@ struct Symbol *sym_AddLabel(char const *symName)
|
||||
static uint32_t anonLabelID;
|
||||
|
||||
// Add an anonymous label
|
||||
struct Symbol *sym_AddAnonLabel(void)
|
||||
Symbol *sym_AddAnonLabel(void)
|
||||
{
|
||||
if (anonLabelID == UINT32_MAX) {
|
||||
error("Only %" PRIu32 " anonymous labels can be created!", anonLabelID);
|
||||
@@ -537,7 +537,7 @@ void sym_Export(char const *symName)
|
||||
return;
|
||||
}
|
||||
|
||||
struct Symbol *sym = sym_FindScopedSymbol(symName);
|
||||
Symbol *sym = sym_FindScopedSymbol(symName);
|
||||
|
||||
// If the symbol doesn't exist, create a ref that can be purged
|
||||
if (!sym)
|
||||
@@ -546,9 +546,9 @@ void sym_Export(char const *symName)
|
||||
}
|
||||
|
||||
// Add a macro definition
|
||||
struct Symbol *sym_AddMacro(char const *symName, int32_t defLineNo, char *body, size_t size)
|
||||
Symbol *sym_AddMacro(char const *symName, int32_t defLineNo, char *body, size_t size)
|
||||
{
|
||||
struct Symbol *sym = createNonrelocSymbol(symName, false);
|
||||
Symbol *sym = createNonrelocSymbol(symName, false);
|
||||
|
||||
if (!sym)
|
||||
return NULL;
|
||||
@@ -566,9 +566,9 @@ struct Symbol *sym_AddMacro(char const *symName, int32_t defLineNo, char *body,
|
||||
|
||||
// Flag that a symbol is referenced in an RPN expression
|
||||
// and create it if it doesn't exist yet
|
||||
struct Symbol *sym_Ref(char const *symName)
|
||||
Symbol *sym_Ref(char const *symName)
|
||||
{
|
||||
struct Symbol *sym = sym_FindScopedSymbol(symName);
|
||||
Symbol *sym = sym_FindScopedSymbol(symName);
|
||||
|
||||
if (!sym) {
|
||||
char fullname[MAXSYMLEN + 1];
|
||||
@@ -593,9 +593,9 @@ void sym_SetExportAll(bool set)
|
||||
exportAll = set;
|
||||
}
|
||||
|
||||
static struct Symbol *createBuiltinSymbol(char const *symName)
|
||||
static Symbol *createBuiltinSymbol(char const *symName)
|
||||
{
|
||||
struct Symbol *sym = createsymbol(symName);
|
||||
Symbol *sym = createsymbol(symName);
|
||||
|
||||
sym->isBuiltin = true;
|
||||
sym->hasCallback = true;
|
||||
@@ -620,7 +620,7 @@ void sym_Init(time_t now)
|
||||
sym_AddVar("_RS", 0)->isBuiltin = true;
|
||||
|
||||
#define addSym(fn, name, val) do { \
|
||||
struct Symbol *sym = fn(name, val); \
|
||||
Symbol *sym = fn(name, val); \
|
||||
assert(sym); \
|
||||
sym->isBuiltin = true; \
|
||||
} while (0)
|
||||
@@ -641,7 +641,7 @@ void sym_Init(time_t now)
|
||||
now = 0;
|
||||
}
|
||||
|
||||
const struct tm *time_local = localtime(&now);
|
||||
const tm *time_local = localtime(&now);
|
||||
|
||||
strftime(savedTIME, sizeof(savedTIME), "\"%H:%M:%S\"", time_local);
|
||||
strftime(savedDATE, sizeof(savedDATE), "\"%d %B %Y\"", time_local);
|
||||
@@ -649,7 +649,7 @@ void sym_Init(time_t now)
|
||||
sizeof(savedTIMESTAMP_ISO8601_LOCAL), "\"%Y-%m-%dT%H:%M:%S%z\"",
|
||||
time_local);
|
||||
|
||||
const struct tm *time_utc = gmtime(&now);
|
||||
const tm *time_utc = gmtime(&now);
|
||||
|
||||
strftime(savedTIMESTAMP_ISO8601_UTC,
|
||||
sizeof(savedTIMESTAMP_ISO8601_UTC), "\"%Y-%m-%dT%H:%M:%SZ\"",
|
||||
|
||||
Reference in New Issue
Block a user