mirror of
https://github.com/gbdev/rgbds.git
synced 2025-11-20 10:12:06 +00:00
Use LCOV_EXCL comments to exclude some lines from test coverage (#1662)
This commit is contained in:
1
.gitignore
vendored
1
.gitignore
vendored
@@ -14,4 +14,5 @@ CMakeCache.txt
|
|||||||
CMakeFiles/
|
CMakeFiles/
|
||||||
cmake_install.cmake
|
cmake_install.cmake
|
||||||
build/
|
build/
|
||||||
|
*.dSYM/
|
||||||
callgrind.out.*
|
callgrind.out.*
|
||||||
|
|||||||
@@ -82,7 +82,6 @@ Symbol *sym_RedefEqu(std::string const &symName, int32_t value);
|
|||||||
Symbol *sym_AddVar(std::string const &symName, int32_t value);
|
Symbol *sym_AddVar(std::string const &symName, int32_t value);
|
||||||
int32_t sym_GetRSValue();
|
int32_t sym_GetRSValue();
|
||||||
void sym_SetRSValue(int32_t value);
|
void sym_SetRSValue(int32_t value);
|
||||||
uint32_t sym_GetConstantValue(std::string const &symName);
|
|
||||||
// Find a symbol by exact name, bypassing expansion checks
|
// Find a symbol by exact name, bypassing expansion checks
|
||||||
Symbol *sym_FindExactSymbol(std::string const &symName);
|
Symbol *sym_FindExactSymbol(std::string const &symName);
|
||||||
// Find a symbol, possibly scoped, by name
|
// Find a symbol, possibly scoped, by name
|
||||||
|
|||||||
@@ -103,7 +103,7 @@ public:
|
|||||||
} else if (other._tag == other._t2.tag_value) {
|
} else if (other._tag == other._t2.tag_value) {
|
||||||
*this = other._t2.value;
|
*this = other._t2.value;
|
||||||
} else {
|
} else {
|
||||||
_tag = nulltag;
|
_tag = nulltag; // LCOV_EXCL_LINE
|
||||||
}
|
}
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -119,9 +119,11 @@ void fstk_SetPreIncludeFile(std::string const &path) {
|
|||||||
warnx("Overriding pre-included filename %s", preIncludeName.c_str());
|
warnx("Overriding pre-included filename %s", preIncludeName.c_str());
|
||||||
}
|
}
|
||||||
preIncludeName = path;
|
preIncludeName = path;
|
||||||
|
// LCOV_EXCL_START
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
printf("Pre-included filename %s\n", preIncludeName.c_str());
|
printf("Pre-included filename %s\n", preIncludeName.c_str());
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
}
|
}
|
||||||
|
|
||||||
static void printDep(std::string const &path) {
|
static void printDep(std::string const &path) {
|
||||||
@@ -308,9 +310,11 @@ void fstk_RunInclude(std::string const &path, bool preInclude) {
|
|||||||
|
|
||||||
if (!fullPath) {
|
if (!fullPath) {
|
||||||
if (generatedMissingIncludes && !preInclude) {
|
if (generatedMissingIncludes && !preInclude) {
|
||||||
|
// LCOV_EXCL_START
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
printf("Aborting (-MG) on INCLUDE file '%s' (%s)\n", path.c_str(), strerror(errno));
|
printf("Aborting (-MG) on INCLUDE file '%s' (%s)\n", path.c_str(), strerror(errno));
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
failedOnMissingInclude = true;
|
failedOnMissingInclude = true;
|
||||||
} else {
|
} else {
|
||||||
error("Unable to open included file '%s': %s\n", path.c_str(), strerror(errno));
|
error("Unable to open included file '%s': %s\n", path.c_str(), strerror(errno));
|
||||||
@@ -319,7 +323,7 @@ void fstk_RunInclude(std::string const &path, bool preInclude) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!newFileContext(*fullPath, false)) {
|
if (!newFileContext(*fullPath, false)) {
|
||||||
fatalerror("Failed to set up lexer for file include\n");
|
fatalerror("Failed to set up lexer for file include\n"); // LCOV_EXCL_LINE
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -77,6 +77,7 @@ struct FileUnmapDeleter {
|
|||||||
|
|
||||||
static char *mapFile(int fd, std::string const &path, size_t size) {
|
static char *mapFile(int fd, std::string const &path, size_t size) {
|
||||||
void *mappingAddr = mmap(nullptr, size, PROT_READ, MAP_PRIVATE, fd, 0);
|
void *mappingAddr = mmap(nullptr, size, PROT_READ, MAP_PRIVATE, fd, 0);
|
||||||
|
// LCOV_EXCL_START
|
||||||
if (mappingAddr == MAP_FAILED && errno == ENOTSUP) {
|
if (mappingAddr == MAP_FAILED && errno == ENOTSUP) {
|
||||||
// The implementation may not support MAP_PRIVATE; try again with MAP_SHARED
|
// The implementation may not support MAP_PRIVATE; try again with MAP_SHARED
|
||||||
// instead, offering, I believe, weaker guarantees about external modifications to
|
// instead, offering, I believe, weaker guarantees about external modifications to
|
||||||
@@ -86,6 +87,7 @@ static char *mapFile(int fd, std::string const &path, size_t size) {
|
|||||||
}
|
}
|
||||||
mappingAddr = mmap(nullptr, size, PROT_READ, MAP_SHARED, fd, 0);
|
mappingAddr = mmap(nullptr, size, PROT_READ, MAP_SHARED, fd, 0);
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
return mappingAddr != MAP_FAILED ? static_cast<char *>(mappingAddr) : nullptr;
|
return mappingAddr != MAP_FAILED ? static_cast<char *>(mappingAddr) : nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -412,21 +414,27 @@ bool LexerState::setFileAsNextState(std::string const &filePath, bool updateStat
|
|||||||
if (filePath == "-") {
|
if (filePath == "-") {
|
||||||
path = "<stdin>";
|
path = "<stdin>";
|
||||||
content.emplace<BufferedContent>(STDIN_FILENO);
|
content.emplace<BufferedContent>(STDIN_FILENO);
|
||||||
|
// LCOV_EXCL_START
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
printf("Opening stdin\n");
|
printf("Opening stdin\n");
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
} else {
|
} else {
|
||||||
struct stat statBuf;
|
struct stat statBuf;
|
||||||
if (stat(filePath.c_str(), &statBuf) != 0) {
|
if (stat(filePath.c_str(), &statBuf) != 0) {
|
||||||
|
// LCOV_EXCL_START
|
||||||
error("Failed to stat file \"%s\": %s\n", filePath.c_str(), strerror(errno));
|
error("Failed to stat file \"%s\": %s\n", filePath.c_str(), strerror(errno));
|
||||||
return false;
|
return false;
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
}
|
}
|
||||||
path = filePath;
|
path = filePath;
|
||||||
|
|
||||||
int fd = open(path.c_str(), O_RDONLY);
|
int fd = open(path.c_str(), O_RDONLY);
|
||||||
if (fd < 0) {
|
if (fd < 0) {
|
||||||
|
// LCOV_EXCL_START
|
||||||
error("Failed to open file \"%s\": %s\n", path.c_str(), strerror(errno));
|
error("Failed to open file \"%s\": %s\n", path.c_str(), strerror(errno));
|
||||||
return false;
|
return false;
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
}
|
}
|
||||||
|
|
||||||
bool isMmapped = false;
|
bool isMmapped = false;
|
||||||
@@ -438,9 +446,11 @@ bool LexerState::setFileAsNextState(std::string const &filePath, bool updateStat
|
|||||||
content.emplace<ViewedContent>(
|
content.emplace<ViewedContent>(
|
||||||
std::shared_ptr<char[]>(mappingAddr, FileUnmapDeleter(size)), size
|
std::shared_ptr<char[]>(mappingAddr, FileUnmapDeleter(size)), size
|
||||||
);
|
);
|
||||||
|
// LCOV_EXCL_START
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
printf("File \"%s\" is mmap()ped\n", path.c_str());
|
printf("File \"%s\" is mmap()ped\n", path.c_str());
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
isMmapped = true;
|
isMmapped = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -448,6 +458,7 @@ bool LexerState::setFileAsNextState(std::string const &filePath, bool updateStat
|
|||||||
if (!isMmapped) {
|
if (!isMmapped) {
|
||||||
// Sometimes mmap() fails or isn't available, so have a fallback
|
// Sometimes mmap() fails or isn't available, so have a fallback
|
||||||
content.emplace<BufferedContent>(fd);
|
content.emplace<BufferedContent>(fd);
|
||||||
|
// LCOV_EXCL_START
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
if (statBuf.st_size == 0) {
|
if (statBuf.st_size == 0) {
|
||||||
printf("File \"%s\" is empty\n", path.c_str());
|
printf("File \"%s\" is empty\n", path.c_str());
|
||||||
@@ -457,6 +468,7 @@ bool LexerState::setFileAsNextState(std::string const &filePath, bool updateStat
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -552,7 +564,9 @@ size_t BufferedContent::readMore(size_t startIndex, size_t nbChars) {
|
|||||||
ssize_t nbReadChars = read(fd, &buf[startIndex], nbChars);
|
ssize_t nbReadChars = read(fd, &buf[startIndex], nbChars);
|
||||||
|
|
||||||
if (nbReadChars == -1) {
|
if (nbReadChars == -1) {
|
||||||
|
// LCOV_EXCL_START
|
||||||
fatalerror("Error while reading \"%s\": %s\n", lexerState->path.c_str(), strerror(errno));
|
fatalerror("Error while reading \"%s\": %s\n", lexerState->path.c_str(), strerror(errno));
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
}
|
}
|
||||||
|
|
||||||
size += nbReadChars;
|
size += nbReadChars;
|
||||||
@@ -761,7 +775,9 @@ int LexerState::peekCharAhead() {
|
|||||||
// and `.peekCharAhead()` will continue with its parent
|
// and `.peekCharAhead()` will continue with its parent
|
||||||
assume(exp.offset <= exp.size());
|
assume(exp.offset <= exp.size());
|
||||||
if (exp.offset + distance < exp.size()) {
|
if (exp.offset + distance < exp.size()) {
|
||||||
return static_cast<uint8_t>((*exp.contents)[exp.offset + distance]);
|
// Macro args can't be recursive, since `peek()` marks them as scanned, so
|
||||||
|
// this is a failsafe that (as far as I can tell) won't ever actually run.
|
||||||
|
return static_cast<uint8_t>((*exp.contents)[exp.offset + distance]); // LCOV_EXCL_LINE
|
||||||
}
|
}
|
||||||
distance -= exp.size() - exp.offset;
|
distance -= exp.size() - exp.offset;
|
||||||
}
|
}
|
||||||
@@ -1323,8 +1339,11 @@ static void appendEscapedString(std::string &str, std::string const &escape) {
|
|||||||
str += "\\n";
|
str += "\\n";
|
||||||
break;
|
break;
|
||||||
case '\r':
|
case '\r':
|
||||||
|
// A literal CR in a string may get treated as a LF, so '\r' is not tested.
|
||||||
|
// LCOV_EXCL_START
|
||||||
str += "\\r";
|
str += "\\r";
|
||||||
break;
|
break;
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
case '\t':
|
case '\t':
|
||||||
str += "\\t";
|
str += "\\t";
|
||||||
break;
|
break;
|
||||||
@@ -2163,7 +2182,8 @@ static Token skipIfBlock(bool toEndc) {
|
|||||||
|
|
||||||
case T_(POP_ELIF):
|
case T_(POP_ELIF):
|
||||||
if (lexer_ReachedELSEBlock()) {
|
if (lexer_ReachedELSEBlock()) {
|
||||||
fatalerror("Found ELIF after an ELSE block\n");
|
// This should be redundant, as the parser handles this error first.
|
||||||
|
fatalerror("Found ELIF after an ELSE block\n"); // LCOV_EXCL_LINE
|
||||||
}
|
}
|
||||||
if (!toEndc && lexer_GetIFDepth() == startingDepth) {
|
if (!toEndc && lexer_GetIFDepth() == startingDepth) {
|
||||||
return token;
|
return token;
|
||||||
@@ -2255,9 +2275,8 @@ static Token yylex_SKIP_TO_ENDR() {
|
|||||||
|
|
||||||
case T_(POP_ENDR):
|
case T_(POP_ENDR):
|
||||||
depth--;
|
depth--;
|
||||||
if (!depth) {
|
// `lexer_CaptureRept` has already guaranteed that the `ENDR`s are balanced
|
||||||
return Token(T_(YYEOF)); // yywrap() will finish the REPT/FOR loop
|
assume(depth > 0);
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case T_(POP_IF):
|
case T_(POP_IF):
|
||||||
|
|||||||
@@ -87,6 +87,7 @@ static option const longopts[] = {
|
|||||||
{nullptr, no_argument, nullptr, 0 }
|
{nullptr, no_argument, nullptr, 0 }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// LCOV_EXCL_START
|
||||||
static void printUsage() {
|
static void printUsage() {
|
||||||
fputs(
|
fputs(
|
||||||
"Usage: rgbasm [-EhVvw] [-b chars] [-D name[=value]] [-g chars] [-I path]\n"
|
"Usage: rgbasm [-EhVvw] [-b chars] [-D name[=value]] [-g chars] [-I path]\n"
|
||||||
@@ -107,6 +108,7 @@ static void printUsage() {
|
|||||||
stderr
|
stderr
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
|
|
||||||
int main(int argc, char *argv[]) {
|
int main(int argc, char *argv[]) {
|
||||||
time_t now = time(nullptr);
|
time_t now = time(nullptr);
|
||||||
@@ -176,8 +178,10 @@ int main(int argc, char *argv[]) {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case 'h':
|
case 'h':
|
||||||
|
// LCOV_EXCL_START
|
||||||
printUsage();
|
printUsage();
|
||||||
exit(0);
|
exit(0);
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
|
|
||||||
case 'I':
|
case 'I':
|
||||||
fstk_AddIncludePath(musl_optarg);
|
fstk_AddIncludePath(musl_optarg);
|
||||||
@@ -195,7 +199,7 @@ int main(int argc, char *argv[]) {
|
|||||||
dependFileName = "<stdout>";
|
dependFileName = "<stdout>";
|
||||||
}
|
}
|
||||||
if (dependFile == nullptr) {
|
if (dependFile == nullptr) {
|
||||||
err("Failed to open dependfile \"%s\"", dependFileName);
|
err("Failed to open dependfile \"%s\"", dependFileName); // LCOV_EXCL_LINE
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@@ -302,9 +306,11 @@ int main(int argc, char *argv[]) {
|
|||||||
if (stateFileSpecs.find(name) != stateFileSpecs.end()) {
|
if (stateFileSpecs.find(name) != stateFileSpecs.end()) {
|
||||||
warnx("Overriding state filename %s", name);
|
warnx("Overriding state filename %s", name);
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_START
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
printf("State filename %s\n", name);
|
printf("State filename %s\n", name);
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
stateFileSpecs.emplace(name, std::move(features));
|
stateFileSpecs.emplace(name, std::move(features));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -314,8 +320,10 @@ int main(int argc, char *argv[]) {
|
|||||||
exit(0);
|
exit(0);
|
||||||
|
|
||||||
case 'v':
|
case 'v':
|
||||||
|
// LCOV_EXCL_START
|
||||||
verbose = true;
|
verbose = true;
|
||||||
break;
|
break;
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
|
|
||||||
case 'W':
|
case 'W':
|
||||||
opt_W(musl_optarg);
|
opt_W(musl_optarg);
|
||||||
@@ -367,8 +375,10 @@ int main(int argc, char *argv[]) {
|
|||||||
|
|
||||||
// Unrecognized options
|
// Unrecognized options
|
||||||
default:
|
default:
|
||||||
|
// LCOV_EXCL_START
|
||||||
printUsage();
|
printUsage();
|
||||||
exit(1);
|
exit(1);
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -391,7 +401,7 @@ int main(int argc, char *argv[]) {
|
|||||||
std::string mainFileName = argv[musl_optind];
|
std::string mainFileName = argv[musl_optind];
|
||||||
|
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
printf("Assembling %s\n", mainFileName.c_str());
|
printf("Assembling %s\n", mainFileName.c_str()); // LCOV_EXCL_LINE
|
||||||
}
|
}
|
||||||
|
|
||||||
if (dependFile) {
|
if (dependFile) {
|
||||||
|
|||||||
@@ -61,7 +61,7 @@ void out_RegisterNode(std::shared_ptr<FileStackNode> node) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Return a section's ID, or UINT32_MAX if the section is not in the list
|
// Return a section's ID, or UINT32_MAX if the section does not exist
|
||||||
static uint32_t getSectIDIfAny(Section *sect) {
|
static uint32_t getSectIDIfAny(Section *sect) {
|
||||||
if (!sect) {
|
if (!sect) {
|
||||||
return UINT32_MAX;
|
return UINT32_MAX;
|
||||||
@@ -71,7 +71,8 @@ static uint32_t getSectIDIfAny(Section *sect) {
|
|||||||
return static_cast<uint32_t>(search->second);
|
return static_cast<uint32_t>(search->second);
|
||||||
}
|
}
|
||||||
|
|
||||||
fatalerror("Unknown section '%s'\n", sect->name.c_str());
|
// Every section that exists should be in `sectionMap`
|
||||||
|
fatalerror("Unknown section '%s'\n", sect->name.c_str()); // LCOV_EXCL_LINE
|
||||||
}
|
}
|
||||||
|
|
||||||
static void writePatch(Patch const &patch, FILE *file) {
|
static void writePatch(Patch const &patch, FILE *file) {
|
||||||
@@ -175,7 +176,7 @@ static void writeRpn(std::vector<uint8_t> &rpnexpr, std::vector<uint8_t> const &
|
|||||||
sym = sym_FindExactSymbol(symName);
|
sym = sym_FindExactSymbol(symName);
|
||||||
if (sym->isConstant()) {
|
if (sym->isConstant()) {
|
||||||
rpnexpr[rpnptr++] = RPN_CONST;
|
rpnexpr[rpnptr++] = RPN_CONST;
|
||||||
value = sym_GetConstantValue(symName);
|
value = sym->getConstantValue();
|
||||||
} else {
|
} else {
|
||||||
rpnexpr[rpnptr++] = RPN_SYM;
|
rpnexpr[rpnptr++] = RPN_SYM;
|
||||||
registerUnregisteredSymbol(*sym); // Ensure that `sym->ID` is set
|
registerUnregisteredSymbol(*sym); // Ensure that `sym->ID` is set
|
||||||
@@ -323,7 +324,7 @@ void out_WriteObject() {
|
|||||||
file = stdout;
|
file = stdout;
|
||||||
}
|
}
|
||||||
if (!file) {
|
if (!file) {
|
||||||
err("Failed to open object file '%s'", objectFileName.c_str());
|
err("Failed to open object file '%s'", objectFileName.c_str()); // LCOV_EXCL_LINE
|
||||||
}
|
}
|
||||||
Defer closeFile{[&] { fclose(file); }};
|
Defer closeFile{[&] { fclose(file); }};
|
||||||
|
|
||||||
@@ -343,14 +344,7 @@ void out_WriteObject() {
|
|||||||
writeFileStackNode(node, file);
|
writeFileStackNode(node, file);
|
||||||
|
|
||||||
// The list is supposed to have decrementing IDs
|
// The list is supposed to have decrementing IDs
|
||||||
if (it + 1 != fileStackNodes.end() && it[1]->ID != node.ID - 1) {
|
assume(it + 1 == fileStackNodes.end() || it[1]->ID == node.ID - 1);
|
||||||
fatalerror(
|
|
||||||
"Internal error: fstack node #%" PRIu32 " follows #%" PRIu32
|
|
||||||
". Please report this to the developers!\n",
|
|
||||||
it[1]->ID,
|
|
||||||
node.ID
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
for (Symbol const *sym : objectSymbols) {
|
for (Symbol const *sym : objectSymbols) {
|
||||||
@@ -373,9 +367,11 @@ void out_SetFileName(std::string const &name) {
|
|||||||
warnx("Overriding output filename %s", objectFileName.c_str());
|
warnx("Overriding output filename %s", objectFileName.c_str());
|
||||||
}
|
}
|
||||||
objectFileName = name;
|
objectFileName = name;
|
||||||
|
// LCOV_EXCL_START
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
printf("Output filename %s\n", objectFileName.c_str());
|
printf("Output filename %s\n", objectFileName.c_str());
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
}
|
}
|
||||||
|
|
||||||
static void dumpString(std::string const &escape, FILE *file) {
|
static void dumpString(std::string const &escape, FILE *file) {
|
||||||
@@ -528,7 +524,7 @@ void out_WriteState(std::string name, std::vector<StateFeature> const &features)
|
|||||||
file = stdout;
|
file = stdout;
|
||||||
}
|
}
|
||||||
if (!file) {
|
if (!file) {
|
||||||
err("Failed to open state file '%s'", name.c_str());
|
err("Failed to open state file '%s'", name.c_str()); // LCOV_EXCL_LINE
|
||||||
}
|
}
|
||||||
Defer closeFile{[&] { fclose(file); }};
|
Defer closeFile{[&] { fclose(file); }};
|
||||||
|
|
||||||
|
|||||||
@@ -94,7 +94,7 @@ void Expression::makeSymbol(std::string const &symName) {
|
|||||||
*ptr++ = RPN_SYM;
|
*ptr++ = RPN_SYM;
|
||||||
memcpy(ptr, sym->name.c_str(), nameLen);
|
memcpy(ptr, sym->name.c_str(), nameLen);
|
||||||
} else {
|
} else {
|
||||||
data = static_cast<int32_t>(sym_GetConstantValue(symName));
|
data = static_cast<int32_t>(sym->getConstantValue());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -325,42 +325,12 @@ void Expression::makeUnaryOp(RPNCommand op, Expression &&src) {
|
|||||||
case RPN_TZCOUNT:
|
case RPN_TZCOUNT:
|
||||||
data = val != 0 ? ctz(uval) : 32;
|
data = val != 0 ? ctz(uval) : 32;
|
||||||
break;
|
break;
|
||||||
|
default:
|
||||||
case RPN_LOGOR:
|
|
||||||
case RPN_LOGAND:
|
|
||||||
case RPN_LOGEQ:
|
|
||||||
case RPN_LOGGT:
|
|
||||||
case RPN_LOGLT:
|
|
||||||
case RPN_LOGGE:
|
|
||||||
case RPN_LOGLE:
|
|
||||||
case RPN_LOGNE:
|
|
||||||
case RPN_ADD:
|
|
||||||
case RPN_SUB:
|
|
||||||
case RPN_XOR:
|
|
||||||
case RPN_OR:
|
|
||||||
case RPN_AND:
|
|
||||||
case RPN_SHL:
|
|
||||||
case RPN_SHR:
|
|
||||||
case RPN_USHR:
|
|
||||||
case RPN_MUL:
|
|
||||||
case RPN_DIV:
|
|
||||||
case RPN_MOD:
|
|
||||||
case RPN_EXP:
|
|
||||||
case RPN_BANK_SYM:
|
|
||||||
case RPN_BANK_SECT:
|
|
||||||
case RPN_BANK_SELF:
|
|
||||||
case RPN_SIZEOF_SECT:
|
|
||||||
case RPN_STARTOF_SECT:
|
|
||||||
case RPN_SIZEOF_SECTTYPE:
|
|
||||||
case RPN_STARTOF_SECTTYPE:
|
|
||||||
case RPN_HRAM:
|
|
||||||
case RPN_RST:
|
|
||||||
case RPN_BIT_INDEX:
|
|
||||||
case RPN_CONST:
|
|
||||||
case RPN_SYM:
|
|
||||||
// `makeUnaryOp` should never be called with a non-unary operator!
|
// `makeUnaryOp` should never be called with a non-unary operator!
|
||||||
|
// LCOV_EXCL_START
|
||||||
unreachable_();
|
unreachable_();
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
} else if (op == RPN_LOGNOT && tryConstLogNot(src)) {
|
} else if (op == RPN_LOGNOT && tryConstLogNot(src)) {
|
||||||
data = 0;
|
data = 0;
|
||||||
} else if (int32_t constVal; op == RPN_LOW && (constVal = tryConstLow(src)) != -1) {
|
} else if (int32_t constVal; op == RPN_LOW && (constVal = tryConstLow(src)) != -1) {
|
||||||
@@ -503,29 +473,12 @@ void Expression::makeBinaryOp(RPNCommand op, Expression &&src1, Expression const
|
|||||||
|
|
||||||
data = op_exponent(lval, rval);
|
data = op_exponent(lval, rval);
|
||||||
break;
|
break;
|
||||||
|
default:
|
||||||
case RPN_NEG:
|
|
||||||
case RPN_NOT:
|
|
||||||
case RPN_LOGNOT:
|
|
||||||
case RPN_BANK_SYM:
|
|
||||||
case RPN_BANK_SECT:
|
|
||||||
case RPN_BANK_SELF:
|
|
||||||
case RPN_SIZEOF_SECT:
|
|
||||||
case RPN_STARTOF_SECT:
|
|
||||||
case RPN_SIZEOF_SECTTYPE:
|
|
||||||
case RPN_STARTOF_SECTTYPE:
|
|
||||||
case RPN_HRAM:
|
|
||||||
case RPN_RST:
|
|
||||||
case RPN_BIT_INDEX:
|
|
||||||
case RPN_HIGH:
|
|
||||||
case RPN_LOW:
|
|
||||||
case RPN_BITWIDTH:
|
|
||||||
case RPN_TZCOUNT:
|
|
||||||
case RPN_CONST:
|
|
||||||
case RPN_SYM:
|
|
||||||
// `makeBinaryOp` should never be called with a non-binary operator!
|
// `makeBinaryOp` should never be called with a non-binary operator!
|
||||||
|
// LCOV_EXCL_START
|
||||||
unreachable_();
|
unreachable_();
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
} else if (op == RPN_SUB && src1.isDiffConstant(src2.symbolOf())) {
|
} else if (op == RPN_SUB && src1.isDiffConstant(src2.symbolOf())) {
|
||||||
data = src1.symbolOf()->getValue() - src2.symbolOf()->getValue();
|
data = src1.symbolOf()->getValue() - src2.symbolOf()->getValue();
|
||||||
} else if ((op == RPN_LOGAND || op == RPN_AND) && tryConstZero(src1, src2)) {
|
} else if ((op == RPN_LOGAND || op == RPN_AND) && tryConstZero(src1, src2)) {
|
||||||
|
|||||||
@@ -875,9 +875,11 @@ void sect_BinaryFile(std::string const &name, int32_t startPos) {
|
|||||||
}
|
}
|
||||||
if (!file) {
|
if (!file) {
|
||||||
if (generatedMissingIncludes) {
|
if (generatedMissingIncludes) {
|
||||||
|
// LCOV_EXCL_START
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
printf("Aborting (-MG) on INCBIN file '%s' (%s)\n", name.c_str(), strerror(errno));
|
printf("Aborting (-MG) on INCBIN file '%s' (%s)\n", name.c_str(), strerror(errno));
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
failedOnMissingInclude = true;
|
failedOnMissingInclude = true;
|
||||||
} else {
|
} else {
|
||||||
error("Error opening INCBIN file '%s': %s\n", name.c_str(), strerror(errno));
|
error("Error opening INCBIN file '%s': %s\n", name.c_str(), strerror(errno));
|
||||||
@@ -942,9 +944,11 @@ void sect_BinaryFileSlice(std::string const &name, int32_t startPos, int32_t len
|
|||||||
}
|
}
|
||||||
if (!file) {
|
if (!file) {
|
||||||
if (generatedMissingIncludes) {
|
if (generatedMissingIncludes) {
|
||||||
|
// LCOV_EXCL_START
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
printf("Aborting (-MG) on INCBIN file '%s' (%s)\n", name.c_str(), strerror(errno));
|
printf("Aborting (-MG) on INCBIN file '%s' (%s)\n", name.c_str(), strerror(errno));
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
failedOnMissingInclude = true;
|
failedOnMissingInclude = true;
|
||||||
} else {
|
} else {
|
||||||
error("Error opening INCBIN file '%s': %s\n", name.c_str(), strerror(errno));
|
error("Error opening INCBIN file '%s': %s\n", name.c_str(), strerror(errno));
|
||||||
|
|||||||
@@ -325,19 +325,6 @@ uint32_t Symbol::getConstantValue() const {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t sym_GetConstantValue(std::string const &symName) {
|
|
||||||
if (Symbol const *sym = sym_FindScopedSymbol(symName); sym) {
|
|
||||||
return sym->getConstantValue();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (sym_IsPurgedScoped(symName)) {
|
|
||||||
error("'%s' not defined; it was purged\n", symName.c_str());
|
|
||||||
} else {
|
|
||||||
error("'%s' not defined\n", symName.c_str());
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
std::pair<Symbol const *, Symbol const *> sym_GetCurrentLabelScopes() {
|
std::pair<Symbol const *, Symbol const *> sym_GetCurrentLabelScopes() {
|
||||||
return {globalScope, localScope};
|
return {globalScope, localScope};
|
||||||
}
|
}
|
||||||
@@ -528,8 +515,10 @@ static uint32_t anonLabelID = 0;
|
|||||||
|
|
||||||
Symbol *sym_AddAnonLabel() {
|
Symbol *sym_AddAnonLabel() {
|
||||||
if (anonLabelID == UINT32_MAX) {
|
if (anonLabelID == UINT32_MAX) {
|
||||||
|
// LCOV_EXCL_START
|
||||||
error("Only %" PRIu32 " anonymous labels can be created!", anonLabelID);
|
error("Only %" PRIu32 " anonymous labels can be created!", anonLabelID);
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string anon = sym_MakeAnonLabelName(0, true); // The direction is important!
|
std::string anon = sym_MakeAnonLabelName(0, true); // The direction is important!
|
||||||
@@ -555,6 +544,7 @@ std::string sym_MakeAnonLabelName(uint32_t ofs, bool neg) {
|
|||||||
} else {
|
} else {
|
||||||
ofs--; // We're referencing symbols that haven't been created yet...
|
ofs--; // We're referencing symbols that haven't been created yet...
|
||||||
if (ofs > UINT32_MAX - anonLabelID) {
|
if (ofs > UINT32_MAX - anonLabelID) {
|
||||||
|
// LCOV_EXCL_START
|
||||||
error(
|
error(
|
||||||
"Reference to anonymous label %" PRIu32 " after, when only %" PRIu32
|
"Reference to anonymous label %" PRIu32 " after, when only %" PRIu32
|
||||||
" may still be created\n",
|
" may still be created\n",
|
||||||
@@ -562,6 +552,7 @@ std::string sym_MakeAnonLabelName(uint32_t ofs, bool neg) {
|
|||||||
UINT32_MAX - anonLabelID
|
UINT32_MAX - anonLabelID
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
id = anonLabelID + ofs;
|
id = anonLabelID + ofs;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -571,8 +562,11 @@ std::string sym_MakeAnonLabelName(uint32_t ofs, bool neg) {
|
|||||||
|
|
||||||
void sym_Export(std::string const &symName) {
|
void sym_Export(std::string const &symName) {
|
||||||
if (symName.starts_with('!')) {
|
if (symName.starts_with('!')) {
|
||||||
|
// LCOV_EXCL_START
|
||||||
|
// The parser does not accept anonymous labels for an `EXPORT` directive
|
||||||
error("Anonymous labels cannot be exported\n");
|
error("Anonymous labels cannot be exported\n");
|
||||||
return;
|
return;
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
}
|
}
|
||||||
|
|
||||||
Symbol *sym = sym_FindScopedSymbol(symName);
|
Symbol *sym = sym_FindScopedSymbol(symName);
|
||||||
@@ -654,11 +648,13 @@ void sym_Init(time_t now) {
|
|||||||
sym_AddEqu("__RGBDS_RC__"s, PACKAGE_VERSION_RC)->isBuiltin = true;
|
sym_AddEqu("__RGBDS_RC__"s, PACKAGE_VERSION_RC)->isBuiltin = true;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
// LCOV_EXCL_START
|
||||||
if (now == static_cast<time_t>(-1)) {
|
if (now == static_cast<time_t>(-1)) {
|
||||||
warn("Failed to determine current time");
|
warn("Failed to determine current time");
|
||||||
// Fall back by pretending we are at the Epoch
|
// Fall back by pretending we are at the Epoch
|
||||||
now = 0;
|
now = 0;
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
|
|
||||||
tm const *time_local = localtime(&now);
|
tm const *time_local = localtime(&now);
|
||||||
|
|
||||||
|
|||||||
@@ -54,6 +54,7 @@ static option const longopts[] = {
|
|||||||
{nullptr, no_argument, nullptr, 0 }
|
{nullptr, no_argument, nullptr, 0 }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// LCOV_EXCL_START
|
||||||
static void printUsage() {
|
static void printUsage() {
|
||||||
fputs(
|
fputs(
|
||||||
"Usage: rgbfix [-hjOsVv] [-C | -c] [-f <fix_spec>] [-i <game_id>] [-k <licensee>]\n"
|
"Usage: rgbfix [-hjOsVv] [-C | -c] [-f <fix_spec>] [-i <game_id>] [-k <licensee>]\n"
|
||||||
@@ -72,6 +73,7 @@ static void printUsage() {
|
|||||||
stderr
|
stderr
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
|
|
||||||
static uint8_t nbErrors;
|
static uint8_t nbErrors;
|
||||||
|
|
||||||
@@ -1322,8 +1324,10 @@ int main(int argc, char *argv[]) {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case 'h':
|
case 'h':
|
||||||
|
// LCOV_EXCL_START
|
||||||
printUsage();
|
printUsage();
|
||||||
exit(0);
|
exit(0);
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
|
|
||||||
case 'i':
|
case 'i':
|
||||||
gameID = musl_optarg;
|
gameID = musl_optarg;
|
||||||
|
|||||||
@@ -156,6 +156,7 @@ static option const longopts[] = {
|
|||||||
{nullptr, no_argument, nullptr, 0 }
|
{nullptr, no_argument, nullptr, 0 }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// LCOV_EXCL_START
|
||||||
static void printUsage() {
|
static void printUsage() {
|
||||||
fputs(
|
fputs(
|
||||||
"Usage: rgbgfx [-r stride] [-ChmOuVXYZ] [-v [-v ...]] [-a <attr_map> | -A]\n"
|
"Usage: rgbgfx [-r stride] [-ChmOuVXYZ] [-v [-v ...]] [-a <attr_map> | -A]\n"
|
||||||
@@ -174,6 +175,7 @@ static void printUsage() {
|
|||||||
stderr
|
stderr
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
|
|
||||||
// Parses a number at the beginning of a string, moving the pointer to skip the parsed characters.
|
// Parses a number at the beginning of a string, moving the pointer to skip the parsed characters.
|
||||||
// Returns the provided errVal on error.
|
// Returns the provided errVal on error.
|
||||||
@@ -425,8 +427,10 @@ static char *parseArgv(int argc, char *argv[]) {
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 'h':
|
case 'h':
|
||||||
|
// LCOV_EXCL_START
|
||||||
printUsage();
|
printUsage();
|
||||||
exit(0);
|
exit(0);
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
case 'i':
|
case 'i':
|
||||||
if (!options.inputTileset.empty()) {
|
if (!options.inputTileset.empty()) {
|
||||||
warning("Overriding input tileset file %s", options.inputTileset.c_str());
|
warning("Overriding input tileset file %s", options.inputTileset.c_str());
|
||||||
@@ -615,8 +619,10 @@ static char *parseArgv(int argc, char *argv[]) {
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
// LCOV_EXCL_START
|
||||||
printUsage();
|
printUsage();
|
||||||
exit(1);
|
exit(1);
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -163,6 +163,7 @@ static option const longopts[] = {
|
|||||||
{nullptr, no_argument, nullptr, 0 }
|
{nullptr, no_argument, nullptr, 0 }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// LCOV_EXCL_START
|
||||||
static void printUsage() {
|
static void printUsage() {
|
||||||
fputs(
|
fputs(
|
||||||
"Usage: rgblink [-dhMtVvwx] [-l script] [-m map_file] [-n sym_file]\n"
|
"Usage: rgblink [-dhMtVvwx] [-l script] [-m map_file] [-n sym_file]\n"
|
||||||
@@ -181,6 +182,7 @@ static void printUsage() {
|
|||||||
stderr
|
stderr
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
|
|
||||||
enum ScrambledRegion {
|
enum ScrambledRegion {
|
||||||
SCRAMBLE_ROMX,
|
SCRAMBLE_ROMX,
|
||||||
@@ -335,8 +337,10 @@ int main(int argc, char *argv[]) {
|
|||||||
isWRAM0Mode = true;
|
isWRAM0Mode = true;
|
||||||
break;
|
break;
|
||||||
case 'h':
|
case 'h':
|
||||||
|
// LCOV_EXCL_START
|
||||||
printUsage();
|
printUsage();
|
||||||
exit(0);
|
exit(0);
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
case 'l':
|
case 'l':
|
||||||
if (linkerScriptName) {
|
if (linkerScriptName) {
|
||||||
warnx("Overriding linker script %s", linkerScriptName);
|
warnx("Overriding linker script %s", linkerScriptName);
|
||||||
@@ -407,8 +411,10 @@ int main(int argc, char *argv[]) {
|
|||||||
is32kMode = true;
|
is32kMode = true;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
// LCOV_EXCL_START
|
||||||
printUsage();
|
printUsage();
|
||||||
exit(1);
|
exit(1);
|
||||||
|
// LCOV_EXCL_STOP
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -7,6 +7,17 @@ FOR V, 1, 100
|
|||||||
PRINTLN "cont"
|
PRINTLN "cont"
|
||||||
ENDR
|
ENDR
|
||||||
WARN "done {d:V}"
|
WARN "done {d:V}"
|
||||||
|
rept 2
|
||||||
|
break
|
||||||
|
; skips nested code
|
||||||
|
rept 3
|
||||||
|
println "\tinner"
|
||||||
|
endr
|
||||||
|
if 1
|
||||||
|
println "\tconditional"
|
||||||
|
endc
|
||||||
|
println "outer"
|
||||||
|
endr
|
||||||
rept 1
|
rept 1
|
||||||
break
|
break
|
||||||
; skips invalid code
|
; skips invalid code
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
warning: break.asm(9): [-Wuser]
|
warning: break.asm(9): [-Wuser]
|
||||||
done 5
|
done 5
|
||||||
warning: break.asm(17): [-Wuser]
|
warning: break.asm(28): [-Wuser]
|
||||||
OK
|
OK
|
||||||
error: break.asm(18):
|
error: break.asm(29):
|
||||||
BREAK can only be used inside a REPT/FOR block
|
BREAK can only be used inside a REPT/FOR block
|
||||||
FATAL: break.asm(19) -> break.asm::REPT~1(23):
|
FATAL: break.asm(30) -> break.asm::REPT~1(34):
|
||||||
Ended block with 1 unterminated IF construct
|
Ended block with 1 unterminated IF construct
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ DEF copy EQUS STRSUB("{invalid}", 1)
|
|||||||
println "\"{#s:invalid}\" == \"{#s:copy}\" ({d:n})"
|
println "\"{#s:invalid}\" == \"{#s:copy}\" ({d:n})"
|
||||||
|
|
||||||
DEF mid1 EQUS STRSUB("{invalid}", 5, 2)
|
DEF mid1 EQUS STRSUB("{invalid}", 5, 2)
|
||||||
DEF mid2 EQUS STRSUB("{invalid}", 9, 1)
|
DEF mid2 EQUS STRSLICE("{invalid}", 8, 9)
|
||||||
println "\"{#s:mid2}{#s:mid1}\""
|
println "\"{#s:mid2}{#s:mid1}\""
|
||||||
|
|
||||||
; characters:
|
; characters:
|
||||||
@@ -53,3 +53,6 @@ println "\"{#s:invalid}\": {d:n} == {d:r}"
|
|||||||
|
|
||||||
DEF final EQUS STRSUB("{invalid}", 4, 1)
|
DEF final EQUS STRSUB("{invalid}", 4, 1)
|
||||||
println "\"{#s:invalid}\" ends \"{#s:final}\""
|
println "\"{#s:invalid}\" ends \"{#s:final}\""
|
||||||
|
|
||||||
|
REDEF final EQUS STRSLICE("{invalid}", 3, 4)
|
||||||
|
println "\"{#s:invalid}\" ends \"{#s:final}\""
|
||||||
|
|||||||
@@ -15,9 +15,9 @@ error: invalid-utf-8-strings.asm(17):
|
|||||||
error: invalid-utf-8-strings.asm(17):
|
error: invalid-utf-8-strings.asm(17):
|
||||||
STRSUB: Invalid UTF-8 byte 0xA2
|
STRSUB: Invalid UTF-8 byte 0xA2
|
||||||
error: invalid-utf-8-strings.asm(22):
|
error: invalid-utf-8-strings.asm(22):
|
||||||
STRSUB: Invalid UTF-8 byte 0xA3
|
STRSLICE: Invalid UTF-8 byte 0xA3
|
||||||
error: invalid-utf-8-strings.asm(22):
|
error: invalid-utf-8-strings.asm(22):
|
||||||
STRSUB: Invalid UTF-8 byte 0xA4
|
STRSLICE: Invalid UTF-8 byte 0xA4
|
||||||
error: invalid-utf-8-strings.asm(35):
|
error: invalid-utf-8-strings.asm(35):
|
||||||
STRLEN: Invalid UTF-8 byte 0xFE
|
STRLEN: Invalid UTF-8 byte 0xFE
|
||||||
error: invalid-utf-8-strings.asm(35):
|
error: invalid-utf-8-strings.asm(35):
|
||||||
@@ -56,4 +56,6 @@ error: invalid-utf-8-strings.asm(50):
|
|||||||
STRLEN: Incomplete UTF-8 character
|
STRLEN: Incomplete UTF-8 character
|
||||||
error: invalid-utf-8-strings.asm(54):
|
error: invalid-utf-8-strings.asm(54):
|
||||||
STRSUB: Incomplete UTF-8 character
|
STRSUB: Incomplete UTF-8 character
|
||||||
error: Assembly aborted (29 errors)!
|
error: invalid-utf-8-strings.asm(57):
|
||||||
|
STRSLICE: Incomplete UTF-8 character
|
||||||
|
error: Assembly aborted (30 errors)!
|
||||||
|
|||||||
@@ -4,3 +4,4 @@
|
|||||||
"漢<>"
|
"漢<>"
|
||||||
"abc<62><63>": 4 == 4
|
"abc<62><63>": 4 == 4
|
||||||
"abc<62><63>" ends "<22><>"
|
"abc<62><63>" ends "<22><>"
|
||||||
|
"abc<62><63>" ends "<22><>"
|
||||||
|
|||||||
Binary file not shown.
Binary file not shown.
5
test/asm/macro-arg-illegal-escape.asm
Normal file
5
test/asm/macro-arg-illegal-escape.asm
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
MACRO mac
|
||||||
|
DEF s EQUS "\#"
|
||||||
|
println "{#s:s}"
|
||||||
|
ENDM
|
||||||
|
mac \\\"\t\r\0\n\{\}\,\(\)\w\
|
||||||
@@ -1,5 +1,5 @@
|
|||||||
error: macro-arg-escape-chars.asm(5):
|
error: macro-arg-illegal-escape.asm(5):
|
||||||
Illegal character escape 'w'
|
Illegal character escape 'w'
|
||||||
error: macro-arg-escape-chars.asm(5):
|
error: macro-arg-illegal-escape.asm(5):
|
||||||
Illegal character escape at end of input
|
Illegal character escape at end of input
|
||||||
error: Assembly aborted (2 errors)!
|
error: Assembly aborted (2 errors)!
|
||||||
1
test/asm/macro-arg-illegal-escape.out
Normal file
1
test/asm/macro-arg-illegal-escape.out
Normal file
@@ -0,0 +1 @@
|
|||||||
|
\\\"\t\r\0\n\{},()w\\
|
||||||
@@ -28,7 +28,10 @@ purge #name
|
|||||||
assert !def(name) && !def(#name) && def(hello)
|
assert !def(name) && !def(#name) && def(hello)
|
||||||
|
|
||||||
section "test", rom0
|
section "test", rom0
|
||||||
#label:
|
|
||||||
db #hello
|
db #hello
|
||||||
dw #hello
|
dw #hello
|
||||||
|
dl #hello
|
||||||
|
|
||||||
|
#label:
|
||||||
dw BANK(#label), #label
|
dw BANK(#label), #label
|
||||||
|
|||||||
Binary file not shown.
2
test/asm/unterminated-if-eof.asm
Normal file
2
test/asm/unterminated-if-eof.asm
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
if 0
|
||||||
|
; no newline at end of file
|
||||||
2
test/asm/unterminated-if-eof.err
Normal file
2
test/asm/unterminated-if-eof.err
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
FATAL: unterminated-if-eof.asm(2):
|
||||||
|
Ended block with 1 unterminated IF construct
|
||||||
@@ -109,6 +109,10 @@ for f in *.[12]bpp; do
|
|||||||
runTest && tryCmp "$f" result.2bpp || failTest $?
|
runTest && tryCmp "$f" result.2bpp || failTest $?
|
||||||
done
|
done
|
||||||
|
|
||||||
|
# Test writing to stdout
|
||||||
|
newTest "$RGBGFX -m -o - write_stdout.bin > result.2bpp"
|
||||||
|
runTest && tryCmp write_stdout.out.2bpp result.2bpp || failTest $?
|
||||||
|
|
||||||
if [[ "$failed" -eq 0 ]]; then
|
if [[ "$failed" -eq 0 ]]; then
|
||||||
echo "${bold}${green}All ${tests} tests passed!${rescolors}${resbold}"
|
echo "${bold}${green}All ${tests} tests passed!${rescolors}${resbold}"
|
||||||
else
|
else
|
||||||
|
|||||||
BIN
test/gfx/write_stdout.bin
Normal file
BIN
test/gfx/write_stdout.bin
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 127 B |
1
test/gfx/write_stdout.out.2bpp
Normal file
1
test/gfx/write_stdout.out.2bpp
Normal file
@@ -0,0 +1 @@
|
|||||||
|
? @@˙Ś˙’˙€˙€đ‚đŹxG~A? ˙ńâ~‚üřŕŕ
|
||||||
Reference in New Issue
Block a user