Merge branch 'master' into jgrpp

# Conflicts:
#	src/core/strong_typedef_type.hpp
#	src/gfx.cpp
#	src/group_cmd.cpp
#	src/industry_cmd.cpp
#	src/map_func.h
#	src/newgrf_debug_gui.cpp
#	src/order_cmd.cpp
#	src/pathfinder/follow_track.hpp
#	src/rail_cmd.cpp
#	src/road_cmd.cpp
#	src/road_gui.cpp
#	src/saveload/saveload.cpp
#	src/screenshot.cpp
#	src/smallmap_gui.cpp
#	src/station_cmd.cpp
#	src/strings.cpp
#	src/tile_type.h
#	src/timetable_gui.cpp
#	src/town_cmd.cpp
#	src/train_cmd.cpp
#	src/viewport.cpp
This commit is contained in:
Jonathan G Rennison
2023-02-10 17:18:39 +00:00
55 changed files with 345 additions and 294 deletions

View File

@@ -334,6 +334,51 @@
#define OTTD_PRINTFHEX64 "%" OTTD_PRINTFHEX64_SUFFIX
#define OTTD_PRINTFHEX64PAD "%016" OTTD_PRINTFHEX64_SUFFIX
/*
* When making a (pure) debug build, the compiler will by default disable
* inlining of functions. This has a detremental effect on the performance of
* debug builds, especially when more and more trivial (wrapper) functions get
* added to the code base.
* Take for example the savegame called "Wentbourne", when running this game
* for 100 ticks with the null video driver a number of fairly trivial
* functions show up on top. The most common one is the implicit conversion
* operator of TileIndex to unsigned int, which takes up over 5% of the total
* run time and functionally does absolutely nothing. The remaining functions
* for the top 5 are GB, GetTileType, Map::Size and IsTileType to a total of
* about 12.5% of the game's total run time.
* It is possible to still force inlining in the most commonly used compilers,
* but that is at the cost of some problems with debugging due to the forced
* inlining. However, the performance benefit can be enormous; when forcing
* inlining for the previously mentioned top 5, the debug build ran about 15%
* quicker.
* The following debug_inline annotation may be added to functions comply
* with the following preconditions:
* 1: the function takes more than 0.5% of a profiled debug runtime
* 2: the function does not modify the game state
* 3: the function does not contain selection or iteration statements,
* i.e. no if, switch, for, do, while, etcetera.
* 4: the function is one line of code, excluding assertions.
* 5: the function is defined in a header file.
* The debug_inline annotation must be placed in front of the function, i.e.
* before the optional static or constexpr modifier.
*/
#if !defined(_DEBUG) || defined(NO_DEBUG_INLINE)
/*
* Do not force inlining when not in debug. This way we do not work against
* any carefully designed compiler optimizations.
*/
#define debug_inline inline
#elif defined(__clang__) || defined(__GNUC__)
#define debug_inline [[gnu::always_inline]] inline
#else
/*
* MSVC explicitly disables inlining, even forced inlining, in debug builds
* so __forceinline makes no difference compared to inline. Other unknown
* compilers can also just fallback to a normal inline.
*/
#define debug_inline inline
#endif
typedef unsigned char byte;
/* This is already defined in unix, but not in QNX Neutrino (6.x) or Cygwin. */