Replace assert with assume for release build optimization (#1390)

This commit is contained in:
Sylvie
2024-04-02 11:09:31 -04:00
committed by GitHub
parent 1d39e5ed56
commit a234da42a6
26 changed files with 158 additions and 147 deletions

View File

@@ -3,7 +3,6 @@
#ifndef RGBDS_FILE_HPP
#define RGBDS_FILE_HPP
#include <assert.h>
#include <fcntl.h>
#include <fstream>
#include <ios>
@@ -13,6 +12,7 @@
#include <string>
#include <variant>
#include "helpers.hpp" // assume
#include "platform.hpp"
#include "gfx/main.hpp"
@@ -33,7 +33,7 @@ public:
if (path != "-") {
return _file.emplace<std::filebuf>().open(path, mode) ? this : nullptr;
} else if (mode & std::ios_base::in) {
assert(!(mode & std::ios_base::out));
assume(!(mode & std::ios_base::out));
_file.emplace<std::streambuf *>(std::cin.rdbuf());
if (setmode(STDIN_FILENO, (mode & std::ios_base::binary) ? O_BINARY : O_TEXT) == -1) {
fatal(
@@ -43,7 +43,7 @@ public:
);
}
} else {
assert(mode & std::ios_base::out);
assume(mode & std::ios_base::out);
_file.emplace<std::streambuf *>(std::cout.rdbuf());
}
return this;

View File

@@ -3,12 +3,12 @@
#ifndef HELPERS_H
#define HELPERS_H
// Ideally, we'd use `__has_attribute` and `__has_builtin`, but these were only introduced in GCC 9
// Ideally we'd use `std::unreachable`, but it has insufficient compiler support
#ifdef __GNUC__ // GCC or compatible
// In release builds, define "unreachable" as such, but trap in debug builds
#ifdef NDEBUG
#define unreachable_ __builtin_unreachable
#else
// In release builds, define "unreachable" as such, but trap in debug builds
#define unreachable_ __builtin_trap
#endif
#else
@@ -18,32 +18,52 @@
}
#endif
// Use builtins whenever possible, and shim them otherwise
// Ideally we'd use `[[assume()]]`, but it has insufficient compiler support
#ifdef NDEBUG
#ifdef _MSC_VER
#define assume(x) __assume(x)
#else
// `[[gnu::assume()]]` for GCC or compatible also has insufficient support (GCC 13+ only)
#define assume(x) \
do { \
if (!(x)) \
unreachable_(); \
} while (0)
#endif
#else
// In release builds, define "assume" as such, but `assert` in debug builds
#include <assert.h>
#define assume assert
#endif
// Ideally we'd use `std::bit_width`, but it has insufficient compiler support
#ifdef __GNUC__ // GCC or compatible
#define ctz __builtin_ctz
#define clz __builtin_clz
#elif defined(_MSC_VER)
#include <assert.h>
#include <intrin.h>
#pragma intrinsic(_BitScanReverse, _BitScanForward)
static inline int ctz(unsigned int x) {
unsigned long cnt;
assert(x != 0);
assume(x != 0);
_BitScanForward(&cnt, x);
return cnt;
}
static inline int clz(unsigned int x) {
unsigned long cnt;
assert(x != 0);
assume(x != 0);
_BitScanReverse(&cnt, x);
return 31 - cnt;
}
#else
#include <limits.h>
static inline int ctz(unsigned int x) {
int cnt = 0;

View File

@@ -3,10 +3,11 @@
#ifndef RGBDS_LINKDEFS_H
#define RGBDS_LINKDEFS_H
#include <assert.h>
#include <stdint.h>
#include <string>
#include "helpers.hpp" // assume
#define RGBDS_OBJECT_VERSION_STRING "RGBA"
#define RGBDS_OBJECT_REV 10U
@@ -93,7 +94,7 @@ extern struct SectionTypeInfo {
* @return `true` if the section's definition includes data
*/
static inline bool sect_HasData(SectionType type) {
assert(type != SECTTYPE_INVALID);
assume(type != SECTTYPE_INVALID);
return type == SECTTYPE_ROM0 || type == SECTTYPE_ROMX;
}