mirror of
https://github.com/gbdev/rgbds.git
synced 2025-11-23 03:22:08 +00:00
Replace assert with assume for release build optimization (#1390)
This commit is contained in:
@@ -3,7 +3,6 @@
|
||||
#include <sys/stat.h>
|
||||
#include <sys/types.h>
|
||||
|
||||
#include <assert.h>
|
||||
#include <inttypes.h>
|
||||
#include <limits.h>
|
||||
#include <stdarg.h>
|
||||
@@ -12,6 +11,7 @@
|
||||
|
||||
#include "error.hpp"
|
||||
#include "extern/getopt.hpp"
|
||||
#include "helpers.hpp" // assume
|
||||
#include "itertools.hpp"
|
||||
#include "platform.hpp"
|
||||
#include "script.hpp"
|
||||
@@ -46,28 +46,28 @@ FILE *linkerScript;
|
||||
static uint32_t nbErrors = 0;
|
||||
|
||||
std::vector<uint32_t> &FileStackNode::iters() {
|
||||
assert(std::holds_alternative<std::vector<uint32_t>>(data));
|
||||
assume(std::holds_alternative<std::vector<uint32_t>>(data));
|
||||
return std::get<std::vector<uint32_t>>(data);
|
||||
}
|
||||
|
||||
std::vector<uint32_t> const &FileStackNode::iters() const {
|
||||
assert(std::holds_alternative<std::vector<uint32_t>>(data));
|
||||
assume(std::holds_alternative<std::vector<uint32_t>>(data));
|
||||
return std::get<std::vector<uint32_t>>(data);
|
||||
}
|
||||
|
||||
std::string &FileStackNode::name() {
|
||||
assert(std::holds_alternative<std::string>(data));
|
||||
assume(std::holds_alternative<std::string>(data));
|
||||
return std::get<std::string>(data);
|
||||
}
|
||||
|
||||
std::string const &FileStackNode::name() const {
|
||||
assert(std::holds_alternative<std::string>(data));
|
||||
assume(std::holds_alternative<std::string>(data));
|
||||
return std::get<std::string>(data);
|
||||
}
|
||||
|
||||
std::string const &FileStackNode::dump(uint32_t curLineNo) const {
|
||||
if (std::holds_alternative<std::vector<uint32_t>>(data)) {
|
||||
assert(parent); // REPT nodes use their parent's name
|
||||
assume(parent); // REPT nodes use their parent's name
|
||||
std::string const &lastName = parent->dump(lineNo);
|
||||
fputs(" -> ", stderr);
|
||||
fputs(lastName.c_str(), stderr);
|
||||
@@ -223,7 +223,7 @@ static void parseScrambleSpec(char const *spec) {
|
||||
// indicating their scramble limit.
|
||||
while (spec) {
|
||||
// Invariant: we should not be pointing at whitespace at this point
|
||||
assert(*spec != ' ' && *spec != '\t');
|
||||
assume(*spec != ' ' && *spec != '\t');
|
||||
|
||||
// Remember where the region's name begins and ends
|
||||
char const *regionName = spec;
|
||||
@@ -232,7 +232,7 @@ static void parseScrambleSpec(char const *spec) {
|
||||
int regionNamePrintLen = regionNameLen > INT_MAX ? INT_MAX : (int)regionNameLen;
|
||||
ScrambledRegion region = SCRAMBLE_UNK;
|
||||
|
||||
// If this trips, `spec` must be pointing at a ',' or '=' (or NUL) due to the assert
|
||||
// If this trips, `spec` must be pointing at a ',' or '=' (or NUL) due to the assumption
|
||||
if (regionNameLen == 0) {
|
||||
argErr('S', "Missing region name");
|
||||
|
||||
@@ -322,7 +322,7 @@ static void parseScrambleSpec(char const *spec) {
|
||||
|
||||
next: // Can't `continue` a `for` loop with this nontrivial iteration logic
|
||||
if (spec) {
|
||||
assert(*spec == ',' || *spec == '\0');
|
||||
assume(*spec == ',' || *spec == '\0');
|
||||
if (*spec == ',')
|
||||
spec += 1 + strspn(&spec[1], " \t");
|
||||
if (*spec == '\0')
|
||||
|
||||
@@ -3,7 +3,6 @@
|
||||
#include "link/output.hpp"
|
||||
|
||||
#include <algorithm>
|
||||
#include <assert.h>
|
||||
#include <deque>
|
||||
#include <inttypes.h>
|
||||
#include <stdio.h>
|
||||
@@ -162,7 +161,7 @@ static void
|
||||
|
||||
if (bankSections) {
|
||||
for (Section const *section : *bankSections) {
|
||||
assert(section->offset == 0);
|
||||
assume(section->offset == 0);
|
||||
// Output padding up to the next SECTION
|
||||
while (offset + baseOffset < section->org) {
|
||||
putc(overlayFile ? getc(overlayFile) : padValue, outputFile);
|
||||
@@ -407,7 +406,7 @@ static void writeMapBank(SortedSections const §List, SectionType type, uint3
|
||||
Section const *sect = *pickedSection;
|
||||
|
||||
used += sect->size;
|
||||
assert(sect->offset == 0);
|
||||
assume(sect->offset == 0);
|
||||
|
||||
writeEmptySpace(prevEndAddr, sect->org);
|
||||
|
||||
|
||||
@@ -2,13 +2,13 @@
|
||||
|
||||
#include "link/patch.hpp"
|
||||
|
||||
#include <assert.h>
|
||||
#include <deque>
|
||||
#include <inttypes.h>
|
||||
#include <stdint.h>
|
||||
#include <variant>
|
||||
#include <vector>
|
||||
|
||||
#include "helpers.hpp" // assume
|
||||
#include "linkdefs.hpp"
|
||||
#include "opmath.hpp"
|
||||
|
||||
@@ -54,7 +54,7 @@ static uint32_t getRPNByte(uint8_t const *&expression, int32_t &size, Patch cons
|
||||
}
|
||||
|
||||
static Symbol const *getSymbol(std::vector<Symbol> const &symbolList, uint32_t index) {
|
||||
assert(index != (uint32_t)-1); // PC needs to be handled specially, not here
|
||||
assume(index != (uint32_t)-1); // PC needs to be handled specially, not here
|
||||
Symbol const &symbol = symbolList[index];
|
||||
|
||||
// If the symbol is defined elsewhere...
|
||||
@@ -297,7 +297,7 @@ static int32_t computeRPNExpr(Patch const &patch, std::vector<Symbol> const &fil
|
||||
isError = true;
|
||||
value = 1;
|
||||
} else {
|
||||
assert(sect->offset == 0);
|
||||
assume(sect->offset == 0);
|
||||
value = sect->org;
|
||||
}
|
||||
break;
|
||||
@@ -377,7 +377,7 @@ static int32_t computeRPNExpr(Patch const &patch, std::vector<Symbol> const &fil
|
||||
} else if (auto *label = std::get_if<Label>(&symbol->data); label) {
|
||||
value = label->section->org + label->offset;
|
||||
} else {
|
||||
assert(std::holds_alternative<int32_t>(symbol->data));
|
||||
assume(std::holds_alternative<int32_t>(symbol->data));
|
||||
value = std::get<int32_t>(symbol->data);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -15,7 +15,6 @@
|
||||
%code {
|
||||
#include <algorithm>
|
||||
#include <array>
|
||||
#include <assert.h>
|
||||
#include <bit>
|
||||
#include <fstream>
|
||||
#include <inttypes.h>
|
||||
@@ -329,7 +328,7 @@ yy::parser::symbol_type yylex() {
|
||||
std::string ident;
|
||||
auto strUpperCmp = [](char cmp, char ref) {
|
||||
// `locale::classic()` yields the "C" locale.
|
||||
assert(!std::use_facet<std::ctype<char>>(std::locale::classic())
|
||||
assume(!std::use_facet<std::ctype<char>>(std::locale::classic())
|
||||
.is(std::ctype_base::lower, ref));
|
||||
return std::use_facet<std::ctype<char>>(std::locale::classic()).toupper(cmp) == ref;
|
||||
};
|
||||
@@ -522,7 +521,7 @@ static void alignTo(uint32_t alignment, uint32_t alignOfs) {
|
||||
return;
|
||||
}
|
||||
|
||||
assert(pc >= typeInfo.startAddr);
|
||||
assume(pc >= typeInfo.startAddr);
|
||||
length %= alignSize;
|
||||
}
|
||||
|
||||
@@ -556,7 +555,7 @@ static void pad(uint32_t length) {
|
||||
auto const &typeInfo = sectionTypeInfo[activeType];
|
||||
auto &pc = curAddr[activeType][activeBankIdx];
|
||||
|
||||
assert(pc >= typeInfo.startAddr);
|
||||
assume(pc >= typeInfo.startAddr);
|
||||
if (uint16_t offset = pc - typeInfo.startAddr; length + offset > typeInfo.size) {
|
||||
scriptError(
|
||||
context,
|
||||
@@ -588,7 +587,7 @@ static void placeSection(std::string const &name, bool isOptional) {
|
||||
}
|
||||
|
||||
auto const &typeInfo = sectionTypeInfo[activeType];
|
||||
assert(section->offset == 0);
|
||||
assume(section->offset == 0);
|
||||
// Check that the linker script doesn't contradict what the code says.
|
||||
if (section->type == SECTTYPE_INVALID) {
|
||||
// SDCC areas don't have a type assigned yet, so the linker script is used to give them one.
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
|
||||
#include "link/sdas_obj.hpp"
|
||||
|
||||
#include <assert.h>
|
||||
#include <ctype.h>
|
||||
#include <inttypes.h>
|
||||
#include <memory>
|
||||
@@ -11,6 +10,7 @@
|
||||
#include <tuple>
|
||||
#include <variant>
|
||||
|
||||
#include "helpers.hpp" // assume
|
||||
#include "linkdefs.hpp"
|
||||
#include "platform.hpp"
|
||||
|
||||
@@ -255,7 +255,7 @@ void sdobj_ReadFile(FileStackNode const &where, FILE *file, std::vector<Symbol>
|
||||
std::unique_ptr<Section> curSection = std::make_unique<Section>();
|
||||
|
||||
getToken(line.data(), "'A' line is too short");
|
||||
assert(strlen(token) != 0); // This should be impossible, tokens are non-empty
|
||||
assume(strlen(token) != 0); // This should be impossible, tokens are non-empty
|
||||
// The following is required for fragment offsets to be reliably predicted
|
||||
for (FileSection &entry : fileSections) {
|
||||
if (!strcmp(token, entry.section->name.c_str()))
|
||||
@@ -365,7 +365,7 @@ void sdobj_ReadFile(FileStackNode const &where, FILE *file, std::vector<Symbol>
|
||||
// Symbols in sections are labels; their value is an offset
|
||||
Section *section = fileSections.back().section.get();
|
||||
if (section->isAddressFixed) {
|
||||
assert(value >= section->org && value <= section->org + section->size);
|
||||
assume(value >= section->org && value <= section->org + section->size);
|
||||
value -= section->org;
|
||||
}
|
||||
// No need to set the `sectionID`, since we set the pointer
|
||||
@@ -392,7 +392,7 @@ void sdobj_ReadFile(FileStackNode const &where, FILE *file, std::vector<Symbol>
|
||||
auto checkSymbol = [](Symbol const &sym) -> std::tuple<Section *, int32_t> {
|
||||
if (auto *label = std::get_if<Label>(&sym.data); label)
|
||||
return {label->section, label->offset};
|
||||
assert(std::holds_alternative<int32_t>(sym.data));
|
||||
assume(std::holds_alternative<int32_t>(sym.data));
|
||||
return {nullptr, std::get<int32_t>(sym.data)};
|
||||
};
|
||||
auto [symbolSection, symbolValue] = checkSymbol(symbol);
|
||||
@@ -468,7 +468,7 @@ void sdobj_ReadFile(FileStackNode const &where, FILE *file, std::vector<Symbol>
|
||||
areaIdx,
|
||||
fileSections.size()
|
||||
);
|
||||
assert(!fileSections.empty()); // There should be at least one, from the above check
|
||||
assume(!fileSections.empty()); // There should be at least one, from the above check
|
||||
Section *section = fileSections[areaIdx].section.get();
|
||||
uint16_t *writeIndex = &fileSections[areaIdx].writeIndex;
|
||||
uint8_t writtenOfs = ADDR_SIZE; // Bytes before this have been written to `->data`
|
||||
@@ -500,7 +500,7 @@ void sdobj_ReadFile(FileStackNode const &where, FILE *file, std::vector<Symbol>
|
||||
*writeIndex
|
||||
);
|
||||
if (section->data.empty()) {
|
||||
assert(section->size != 0);
|
||||
assume(section->size != 0);
|
||||
section->data.resize(section->size);
|
||||
}
|
||||
}
|
||||
@@ -584,7 +584,7 @@ void sdobj_ReadFile(FileStackNode const &where, FILE *file, std::vector<Symbol>
|
||||
uint8_t nbBaseBytes = patch.type == PATCHTYPE_BYTE ? ADDR_SIZE : 2;
|
||||
uint32_t baseValue = 0;
|
||||
|
||||
assert(offset < data.size());
|
||||
assume(offset < data.size());
|
||||
if (data.size() - offset < nbBaseBytes)
|
||||
fatal(
|
||||
&where,
|
||||
@@ -755,7 +755,7 @@ void sdobj_ReadFile(FileStackNode const &where, FILE *file, std::vector<Symbol>
|
||||
patch.rpnExpression.push_back(RPN_AND);
|
||||
}
|
||||
} else if (flags & 1 << RELOC_ISPCREL) {
|
||||
assert(patch.type == PATCHTYPE_WORD);
|
||||
assume(patch.type == PATCHTYPE_WORD);
|
||||
fatal(&where, lineNo, "16-bit PC-relative relocations are not supported");
|
||||
} else if (flags & (1 << RELOC_EXPR16 | 1 << RELOC_EXPR24)) {
|
||||
fatal(
|
||||
@@ -769,7 +769,7 @@ void sdobj_ReadFile(FileStackNode const &where, FILE *file, std::vector<Symbol>
|
||||
|
||||
// If there is some data left to append, do so
|
||||
if (writtenOfs != data.size()) {
|
||||
assert(data.size() > writtenOfs);
|
||||
assume(data.size() > writtenOfs);
|
||||
if (*writeIndex + (data.size() - writtenOfs) > section->size)
|
||||
fatal(
|
||||
&where,
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
|
||||
#include "link/section.hpp"
|
||||
|
||||
#include <assert.h>
|
||||
#include <inttypes.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
@@ -183,7 +182,7 @@ static void mergeSections(Section &target, std::unique_ptr<Section> &&other, Sec
|
||||
for (Patch &patch : other->patches)
|
||||
patch.pcOffset += other->offset;
|
||||
} else if (!target.data.empty()) {
|
||||
assert(other->size == 0);
|
||||
assume(other->size == 0);
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
@@ -5,18 +5,20 @@
|
||||
#include <stdlib.h>
|
||||
#include <unordered_map>
|
||||
|
||||
#include "helpers.hpp" // assume
|
||||
|
||||
#include "link/main.hpp"
|
||||
#include "link/section.hpp"
|
||||
|
||||
std::unordered_map<std::string, Symbol *> symbols;
|
||||
|
||||
Label &Symbol::label() {
|
||||
assert(std::holds_alternative<Label>(data));
|
||||
assume(std::holds_alternative<Label>(data));
|
||||
return std::get<Label>(data);
|
||||
}
|
||||
|
||||
Label const &Symbol::label() const {
|
||||
assert(std::holds_alternative<Label>(data));
|
||||
assume(std::holds_alternative<Label>(data));
|
||||
return std::get<Label>(data);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user