Invoke nothrow callees only in try-blocks with at least 1 catch-block,
otherwise call them directly.
Errors thrown by nothrow callees can thus still be caught inside a
try-catch-statement (and this is apparently required for release builds
too).
Most calls will be direct calls though, and this small change will lead
to substantially less IR as we then skip the clean-ups after an Error.
Proper clean-up when unwinding after an Error seems not to be guaranteed
anyway. There are apparent RAII front-end optimizations for structs with
nothrow dtor - see PR #1656.
Previously, the transitory state only needed and valid during
generation of the LLVM IR for the function body was conflated
with the general codegen metadata for the function declaration
in IrFunction.
There is further potential for cleanup regarding the use of
gIR->func() and so on all over the code base, but this is out
of scope of this commit, which is only concerned with those
IrFunction members moved to FuncGenState.
GitHub: Fixes#1661.
Add the commandline options -fprofile-instr-generate[=filename] and -profile-instr-use=filename
-fprofile-instr-generate
-- Add instrumentation on branches, switches, and function entry; uses LLVM's InstrProf pass.
-- Link to profile runtime that writes instrumentation counters to a file.
-fprofile-instr-use
-- Read profile data from a file and apply branch weights to branches and switches, and annotate functions with entrycount in LLVM IR.
-- Functions with low or high entrycount are marked with 'cold' or 'inlinehint'.
The only statement type without PGO yet is "try-finally".
A new pragma, `pragma(LDC_profile_instr, [ true | false ])`, is added to selectively disable/enable instrumentation of functions (granularity = whole functions).
The runtime library ldc-profile-rt is a copy of LLVM compiler-rt lib/profile. It has to be exactly in-sync with the LLVM version, and thus we need a copy for each PGO-supported LLVM (>=3.7).
import ldc.profile for a D interface to ldc-profile-rt (for example to reset execution counts after a program startup phase).
The instrumentation data is mainly passed on to LLVM: function-entry counts and branch counts/probabilities. LDC marks functions as hot when "execution count is 30% of the maximum function execution count", and marks functions as cold if their count is 1% of maximum function execution count.
The source of LLVM's llvm-profdata tool is hereby included in LDCs repository (different source for each LLVM version), and the binary is included in the install bin folder.
The executable is named "ldc-profdata" to avoid clashing with llvm-profdata on the same machine. This is needed because profdata executable has to be in-sync with the LLVM version used to build LDC.
Maintenance burden: for trunk LLVM, we have to keep ldc-profile-rt and llvm-profdata in sync. There is no diff with upstream; but because of active development there are the occasional API changes.
- do not inline functions into the cleanup funclets, it can break exception handling
- even if no var given, retrieve the caught exception to pass it to _d_eh_enter_catch
Also adds the CMake infrastructure to compile and link the D source files.
The build is partially broken:
- A few files in Phobos and druntime do not build
- MSVC build is broken because of unresolved symbols involving reals
Now the resume unwind block isn't literally created in between
two other, unrelated lines – I must have made a mistake when
resolving a merge conflict or something like that before.
Now with *almost* working EH codegen. Does not compile Phobos yet
because we run into the "instruction does not dominate all uses"
issue when an r-value result of toElemDtor is used and we need to
run cleanups in between. Should easily be fixed by promoting those
values to allocas.
Most of the changes outside of ir/irfunction.{h, cpp} are just
because CreateCallOrInvoke moved locations. I took the
opportunity to also make use of the different arg count
overloads where possible.
Never generates any landing pads or invoke instructions right now
for simplicity. The code for emitting them will be added back in
the next step.
The "after..." blocks without any precedessors remain for now, as
we need a clean way to suppress any codegen for that block (but
not new blocks, which might resolve labels) before tackling that
one.
Builds druntime/Phobos on OS X x86_64 (albeit without EH, of course).
Specifying the basic block before which to insert the new one
is not mandatory when calling llvm::BasicBlock::Create. This
was the only use of the tracked "end" block. The concept was
phony anyway because there is no single "end" to a scope with
unwinding and so on.
For prettying up the IR, it is possible to change the order
of basic blocks using move{Before, After}().
1. Main include corresponding to .cpp file, if any.
2. DMD and LDC includes.
3. LLVM includes.
4. System includes.
Also updated a few include guards to match the default format.
This is based on Item 2 of "More Effective C++". In general, the C++ cast operators are more expressive and easy to find,
e.g. by grep. Using const_cast also shuts up some compiler warnings.