Summary:
In non-PIC binaries compiler could save absolute addresses in constant
isalnd which we should handle properly. This patch adds relocations
handling in constant islands.
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD31416848)
Summary:
Change sed separator to allow replacing symbols with slash in the name.
This is required for symbol names produced by BOLT which include
"/1" suffix.
(cherry picked from FBD31324540)
Summary:
This patch adds R_AARCH64_TSTBR14 and R_AARCH64_CONDBR19 relocations
support in order to handle condition branches, cbz/cnbz and tbz/tbnz
instructions correctly
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD31416734)
Summary:
The ELF::R_AARCH64_TLSDESC_LD64_LO12 and
ELF::R_AARCH64_TLSDESC_ADR_PAGE21 relocations might also be relaxed to
mov instructions, handle these cases
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD31353063)
Summary:
Use the new API introduced in https://reviews.llvm.org/D106624
to request LLVM do not process relocations for debug sections, since
BOLT processes final binaries that are already relocated.
(cherry picked from FBD31449206)
Summary:
When the compiler emits line table program, it emits EOS using the label
at the end of the containing code section. Since each compilation unit
has its own set of code sections it works as expected (* see the excerpt
from the standard below). However, in BOLT the code from many CUs is
combined into a common section, such as hot text or cold text.
As a result, the symbol at the end of the section may point way past the
code sequence for a given unit.
Since we can emit functions in any order, we conservatively emit
end-of-sequence at the end of every emitted function.
Fixes a problem while intermixing source code with disassembly in
binutils' objdump.
(*) DWARF v4 6.2.5.3:
"Every line number program sequence must end with a DW_LNE_end_sequence
instruction which creates a row whose address is that of the byte after
the last target machine instruction of the sequence."
(cherry picked from FBD31347870)
Summary:
Generate line tables for original/unmodified functions directly from
input line tables, bypassing conversion into intermediate structures,
such as BinaryLineDivisions.
Emit end-of-sequence markers only when necessary, i.e. when the line
sequence is not adjacent to the next one, or at the end of the line
sequence for the compilation unit.
If the sequence starts with ambiguous line info (multiple lines per
address), make sure we emit all such lines.
Reduce memory consumption when updating debug info by eliminating
intermediate data structures allocation.
(cherry picked from FBD30829448)
Summary:
BOLT needs to generate line info tables using absolute addresses as well
as using the standard MC way of labels attached to instructions. Move
line table generation code under BOLT.
Ideally, we should be able to extend existing interfaces in LLVM, but
without other users of the interface it will be hard to justify the
change.
(cherry picked from FBD30723466)
Summary:
For historical reasons, we are populating FailedAddresses twice in
RewriteInstance. Remove the second (happening later) call to avoid the
confusion.
(cherry picked from FBD31278956)
Summary:
When rewriting .debug_abbrev section, update abbrev offsets for type
units in addition to compile units.
Reuse abbreviation entries if they were shared by multiple compile/type
units.
(cherry picked from FBD31262326)
Summary:
Create bolt/test/runtime folder and move tests that execute the binary.
Move lit.local.cfg with host_arch check to the corresponding folder.
Addresses issue facebookincubator/BOLT#132.
AArch64/tls.c shows a different behavior with clang hence marked as XFAIL
TODO: add a check for non-exec tests for a corresponding LLVM_TARGETS_TO_BUILD.
(cherry picked from FBD31132234)
Summary:
Previously, we were registering all CUs with aranges writer. Since DWO
CUs have offsets set to 0, and we were registering them after the
skeleton unit at offset 0 was already registered, it was mostly
harmless as DWO CUs were effectively ignored.
(cherry picked from FBD31162621)
Summary:
Instead of patching the original .debug_abbrev section contents,
generate new section data based on parsed compilation unit
abbreviations.
This eliminates the dependency on the LLVM extension that records
abbreviation attribute offsets while parsing .debug_abbrev contents.
The output with this patch should stay the same (NFC).
(cherry picked from FBD31133611)
Summary:
There are some cases, when relocations must not be processed by bolt.
This patch handles three of such cases:
* The linker might eliminate the instruction and replace it with NOP
* The linker might perform TLS relocations relaxations, replacing the
got to direct TP + offset access.
* Due to errata 843419 the linker might create a veneer, replacing the
load/store instruction with branching.
In both cases linker leaves old relocations, that are no longer matches
the instruction emmited to binary, so we must avoid processing of these
relocations.
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD31002384)
Summary:
There are few problems found when dealing with TLS relocations for
aarch64.
* RewriteInstance.cpp
** While analyzing TLS relocation we don't have to modify
SymbolAddress (which is the offset from the TLS section), so we need to
just skip verifiction
** The non-got related TLS relocations on aarch64 might be skipped too
** The forse relocation must be applied for GOT relocations on
Aarch64. The symbol adress for GOT relocation might no be pointing
on GOT section (for example ADRP GOT may point to the wrong section,
since GOT table is not page-aligned), so we won't try to get section by
the symbol address.
* Relocation.cpp - Remove R_AARCH64_TLSLE_ADD_TPREL_HI12 and
R_AARCH64_TLSLE_ADD_TPREL_LO12_NC from isGOT check, since they are not
got-related relocations
* BinaryFunction.h
** Remove R_AARCH64_TLSLE_ADD_TPREL_HI12 and
R_AARCH64_TLSLE_ADD_TPREL_LO12_NC from adding to relocation list, since
this is actually an offset in TLS section and BOLT does not change it we
don't need to do something with this relocations, the value won't change
in new binary files
** Refactor the code, separating aarch64 and x86 relocations
* AArch64MCPlusBuilder.cpp
** Add forgotten LO12 relocations to switch case to getTargetExprFor
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD31003349)
Summary:
LLVM started printing warnings when DWARFDebugInfoEntry::extractFast()
is invoked trying to read a DIE past the current unit limits. This
results in verbose warnings from BOLT which are harmless but confusing
to the user. Check the boundaries before calling the API above.
(cherry picked from FBD31097271)
Summary:
In "Add initial function injection support", Laith added this
code because injected functions would use the original text section as
the section to emit their code to. Now, what happens is that functions
are mapped to either their own section in non-reloc mode, or mapped to
a particular section in the pass reassign sections. So this section does
not need to have an output address anymore and this code is obsolete.
(cherry picked from FBD30980450)
Summary:
We have a problem where we will emit sections that we are not supposed
to emit (with no output offset assigned). This will make us write at
file offset 0 and corrupt the first sections in the binary (usually
.interp section will be corrupted and bash will refuse to run the
binary).
This only happens in non-reloc mode when using JTS_BASIC and when we
do not emit a function that has a jump table (if it gets too large).
Using -update-debug-sections will trigger the pass
check-large-functions, which will mark large funcs as non-simple
and will hide this bug.
(cherry picked from FBD30882012)
Summary:
This commit introduces TryLock usage for SimpleHashTable getter to
avoid deadlock and relax syscalls usage which causes significant
overhead in runtime.
The old behavior left under -conservative-instrumentation option passed
to instrumentation library.
Also, this commit includes a corresponding test case: instrumentation of
executable which performs indirect calls from common code and signal
handler.
Note: in case if TryLock was failed to acquire the lock - this indirect
call will not be accounted in the resulting profile.
Vasily Leonenko,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30821949)
Summary:
This commit adds checking if maxIndividualTestTime is availabe on
the platform. If available - it sets per test timeout to 60sec and
declares lit-max-individual-test-time feature for further checking
by particular test cases.
Based on https://reviews.llvm.org/D64251 implementation.
Vasily Leonenko,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30821986)
Summary:
The clang 12 doesn't want to build this place due to unrelated
types of iterator element and std vector.
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30821177)
Summary: Changing to use the new APIs for getting offset of attribute from .debug_info. They were split in to multiple ones so that Offset can be gotten seperatly.
(cherry picked from FBD30616705)
Summary:
Three way branches commonly appear
in HHVM. They have one test and then two jumps. The
jump's destinations are not currently optimized.
This pass attempts to optimize which is the first branch.
(cherry picked from FBD30460441)
Summary:
There are 2 problems found when handling ADR instruction:
1. When extracting value from the ADR instruction we need to do
it another way, then we do it for ADRP instruction.
2. When creating target expression the VariantKind should be other for
ADR instruction.
And we introduces R_AARCH64_ADR_PREL_LO21,
R_AARCH64_TLSDESC_ADR_PREL21 and R_AARCH64_ADR_PREL_PG_HI21_NC
relocations support.
Also this patch introduces AdrPass, which will replace non-local
pointing ADR instructions with ADRP + ADD instructions sequence due to
small offset range of ADR instruction, so after BOLT magic there are no
guarantees that ADR instruction will still be in the range of
just +- 1MB from its target. The instruction replacement needs
relocations to be avalailable, so we won't remove "IsFromCode"
relocations after disassembly from BF anymore. Also we need original
offset of ADR instruction to be available so we add offset annotation
for these instructions.
The last thing this patch adds is ARM testing directory, which will be
used only on ARM testing servers. The common tests (non-assembler tests
which are platform-independent) might be moved from the X86 directory to
the parent one in the future, so such tests could be tested on both X86
and ARM machines.
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30497379)
Summary:
Currently most of the warnings are printed only in debug mode. Since
relocations are very important for binary correct work I suggest to
print number of failed to process relocations to pay extra attention in
case some problems with them were met
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30500629)
Summary:
Added a function in TailDuplication
that will do Constant and Copy Propagation for blocks that
we duplicated as a part of tail duplication. Added supporting
functions to MCPlusBuilder to find src registers and replace
registers
(cherry picked from FBD30231907)
Summary:
This patch is part of preparation for golang support. The golang symbols
might have spaces in the name (for example "type..eq.[10]interface {}").
Since fdata uses spaces as a field separator such names brakes the fdata
format, so we need to escape whitespaces and backslashes in symbol names
using the backslash character.
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD29999491)
Summary:
Remove unused code introduced a while ago (2016), with its use removed
since then.
PR facebookincubator/BOLT#198
Author: Amir Aupov <aaupov@fb.com>
(cherry picked from FBD30376537)
Summary:
The ADRP instructions has 21 bits to store page offsets + 12 lowest bits
are zero, that give us a total of 33 bits (32 bits for address + 1 sign
bit, to address +- 4GB).
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30283044)
Summary:
This commit adds dummy tests for checking instrumentation
support for PIE executables and shared libraries.
Vasily Leonenko,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30092729)
Summary:
To avoid RELATIVE relocations avoid using of GOT table
by using hidden visibility for all symbols in library.
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30092712)
Summary:
The trampolines are no loger pointers to the functions. For
propper name resolving by bolt use extern "C" for all external symbols
in instr.cpp
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30092698)
Summary:
This commit introduces -instrumentation-binpath argument used
to point instuqmented binary in runtime in case if /proc/self/map_files
path is not accessible due to access restriction issues.
Vasily Leonenko
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30092681)
Summary:
This commit introduces static binaries instrumentation
support. Note that current implementation does not support profile
output on the instrumented binary finalization. So it requires to use
-instrumentation-sleep-time=N (N>0) option usage. Note: There is
unhandled case with static PIE executable which might have dynamic
header.
Vasily Leonenko,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30092471)
Summary:
This commit adds support for opening libs based on links
/proc/self/map_files. For this we're getting current virtual address
and searching the lib in the directory with such address range. After
that, we're getting full path to the binary by using readlink
function. Direct read from link in /proc/self/map_files entries is not
possible because of lack of permissions.
Elvina Yakubova,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30092422)
Summary:
This commit adds support for getting directory entries and
reading value of a symbolic link in instrumentation runtime library
Elvina Yakubova,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30092362)
Summary:
This commit implements new method for _start & _fini functions hooking
which allows to use relative jumps for future PIE & .so library support.
Instead of using absolute address of _start & _fini functions known on
linking stage - we'll use dynamically created trampoline functions and
use corresponding symbols in instrumentation runtime library.
As we would like to use instrumentation for dynamically loaded binaries
(with PIE & .so), thus we need to compile instrumentation library with
"-fPIC" flag to support relative address resolution for functions and
data.
For shared libraries we need to handle initialization of instrumentation
library case by using DT_INIT section entry point.
Also this commit adds detection if the binary is executable or shared
library based on existence of PT_INTERP header. In case of shared
library we save information about real library init function address
for further usage for instrumentation library init trampoline function
creation and also update DT_INIT to point instrumentation library init
function.
Functions called from init/fini functions should be called with forced
stack alignment to avoid issues with instructions which relies on it.
E.g. optimized string operations.
Vasily Leonenko,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD30092316)
Summary:
Move the common code into MCPlusBuilder.h.
Use group 1 `kTailCall` MCAnnotation instead of dynamically allocated
annotation.
This diff reduces the processing time overhead to 1.5% vs using
TAILJMP opcode.
(cherry picked from FBD30055585)
Summary:
The linker can generate 8- or 16-byte entries in .plt.got and .plt.sec
sections. On X86, the main differentiator is the presence of endbr64
instruction at the beginning of the entry. Detect the instruction and
adjust the size accordingly.
(cherry picked from FBD29847639)
Summary:
.stab and .stabstr are special sections containing debugging
information and strings associated with the debugging information.
This commit adds them to the list of debugging sections, so
these sections can be removed for output binary.
Vasily Leonenko,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD29746153)
Summary:
Match new direct call generated during ICP to correct pseudo probe
New call is matched to the probes of original call instruction.
(cherry picked from FBD29591662)
Summary:
Created a binary pass that records how many
times tail duplication would be used and how many cache
misses it would theoretically stop
(cherry picked from FBD29619858)
Summary:
We extended DynoStats to dump the histogram per instruction opcode. By
default the dump is turned off. Use '-print-dyno-opcode-stats' to enable
the dump.
BOLT also dumps for each instruction opcode the maximum execution count and
corresponding function name and basic block offsets where the instruction
occurs. Below is a sample of the dump:
Opcode, Execution Count, Max Exec Count, Function Name:Offset
SHR8rCL, 232, 232, _ZNK5folly14AsyncSSLSocket4goodEv:53
VPADDDYrr, 13956, 388, chacha20_encrypt_bytes.part.0/3:736
PMOVSXBWrr, 4, 2, ares_expand_name/1:264
VMOVAPSmr, 1082, 43, chacha20_encrypt_bytes.part.0/3:2864
VPSHUFBrr, 9540, 1667, chacha20_encrypt_bytes.part.0/3:4416
VPUNPCKLDQYrr, 1102, 188, jsimd_ycc_rgb_convert_avx2/1:125
VPBROADCASTQYrm, 39, 39, chacha20_encrypt_bytes.part.0/3:400
PMOVSXWDrr, 8, 2, ares_expand_name/1:264
VPORrr, 817, 129, jsimd_idct_islow_avx2/1:41
PSLLDri, 8690752, 65644, blockmix_salsa8_xor/1:1424
(cherry picked from FBD28859624)
Summary:
A binary can contain multiple PLT sections with different name and
attributes (such as an entry size). Extend the support to .plt.sec and
refactor the code to make future extensions simpler.
(cherry picked from FBD29502107)
Summary:
clang-12 now compiles bolt without warnings.
Some warnings were fixed if possible while others were suppressed by
doing (void)variable for unused variable warnings or moving code inside
assert statements of LLVM_DEBUG blocks.
(cherry picked from FBD29469054)
Summary:
Add code to read more dynamic relocations (DT_JMPREL) and enforce strict
checks that corresponding sections sizes match .dynamic entry
description.
(cherry picked from FBD29502109)
Summary:
The code for writing out dwo files wasn't handling case where DWP is an input.
Because all the sections are part of the same binary.
One note with current implementation. .debug-str.dwo will have strings for all the dwo objects.
This is because llvm-dwp de-duplicates strings and combines them in to one section. It then re-writes .debug-str-offsets.dwo to point to new .debug-str.dwo section.
(cherry picked from FBD29244835)
Summary:
Our YAML objects contain references to dynamic relocations via .dynamic,
but there are no corresponding relocation sections. Change .dynamic
contents to specify no dynamic relocations.
(cherry picked from FBD29502108)
Summary:
Move the code that handles true external references (non-unreachable)
out of a for-loop in `BinaryFunction::disassemble`.
(cherry picked from FBD29411345)
Summary:
Handle R_X86_64_64 the same way as R_X86_64_32;
`getSizeForType` takes care of the size:
```x86_64 ABI relocation types
Name Value Field Calculation
R_X86_64_64 1 word64 S + A
R_X86_64_32 10 word32 S + A
```
(cherry picked from FBD29370417)
Summary:
When we fold a function in relocation mode, make sure to clear its state
to avoid emitting relocations against undefined symbols.
(cherry picked from FBD29245320)
Summary:
Dived more in to DWARF APIs and llvm-symbolizer this is a more streamline way of doing it, and address base gets set properly.
Writing out dwo files with dwp input will be separate patch.
(cherry picked from FBD31361529)
Summary:
When indirect call is instrmented it locks SimpleHashTable's mutex on get() call.
If while locked we we receive a signal and signal handler also will call
indirect function we will end up with deadlock.
PR facebookincubator/BOLT#167
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD28909921)
Summary:
Suppresses the warning
```
src/DebugData.h:338:20: warning: 'addList' overrides a member function but is not marked 'override' [-Wsuggest-override]
```
(cherry picked from FBD28858201)
Summary:
Make bolt decode pseudo probe section in binary
For more detail of pseudo probe, check https://reviews.llvm.org/D86490.
(cherry picked from FBD28856316)
Summary:
While printing debug info for instructions, we should use line tables
from the corresponding DWARF CU which could be different from the
containing function CU in case of inlined instructions.
(cherry picked from FBD28908324)
Summary:
FBD55943 changed the way ProcessAllSections works in RuntimeDyld. After
the change, all sections, including symbol table, section table, etc.
are loaded into memory whenever ProcessAllSections is enabled.
In BOLT we rely on RuntimeDyld for processing sections with relocations.
These include most allocatable sections and additionally .debug_line.
The latter is skipped by RuntimeDyld without ProcessAllSections flag.
If we enable ProcessAllSections, we will have to deal with allocating
memory for more sections than we need (see above) and later to filter
them out.
The alternative is to mark all sections that we actually plan to use as
"required for execution" (using RuntimeDyld terminology). For
.debug_line section on ELF it means adding SHF_ALLOC flag. On MachO,
RuntimeDyld currently treats all sections as required.
(cherry picked from FBD28729398)
Summary:
This patch introduces LoopInversionPass. Its main purpose is to ensure
that the loop layout is optimal depending on the profile information. So
if profile information shows that the loop is used, the unconditional
jump instruction must be executed only once and vice-versa. Please take
a look to the pass header file and test for more details.
Also change link_fdata script a bit, to be able to change FDATA prefix,
like FileCheck does.
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
PR facebookincubator/BOLT#153
(cherry picked from FBD28391811)
Summary:
Implemented support for Debug Fission.
For the most part it doesn't impact Monolithic execution path.
One area that was changed is the DW_AT_low_pc/DW_AT_high_pc conversion. Before it was to DW_AT_ranges/DW_AT_low_pc, now DW_AT_low_pc is kept in same place.
Another more visible impact is in Skeleton CU the DW_AT_low_pc is replaced with DW_AT_ranges_base if it's not originally present and bolt converted ranges conversion inside the dwo units.
Output of this are multiple .dwo files with updated debug information.
(cherry picked from FBD29569788)
Summary:
Remove relocations against internal function labels, e.g. jump table
relocations, only when overwriting them.
While reading an input file with relocations, we create internal
relocations against code references (we skip PIC relocations).
Later, when we discover jump tables, we remove corresponding relocations
with the assumption that original relocations will either be ignored or
replaced by new relocations. However, it is possible to miss some
references to the jump table, in which case the original entries will
not be ignored. While such situation is abnormal, it is still a
better/safer approach to preserve relocations if we are not replacing
them with new ones.
(cherry picked from FBD28406628)
Summary:
Explicit assignment operator can be replaced with an implicit one.
Remove it to allow an implicit copy constructor:
```
bolt/src/Passes/DataflowAnalysis.h:74:8: warning: definition of
implicit copy constructor for 'ProgramPoint' is deprecated because it
has a user-declared copy assignment operator [-Wdeprecated-copy]
void operator=(const ProgramPoint &PP) {
^
bolt/src/Passes/DataflowAnalysis.h:62:14: note: in implicit copy
constructor for 'llvm::bolt::ProgramPoint' first required here
return ProgramPoint(&*Last);
```
(cherry picked from FBD28335138)
Summary:
Since gcc/ld could produce and expect PIE files we need to pass -no-pie option to avoid linking errors for tests.
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
(cherry picked from FBD28360045)
Summary:
Reorder-blocks optimization pass doesn't take into account that
available offset for legacy Jcc instructions (for example,
JRCXZ - operand 8 bits) has to be less than 255 bytes.
It's rare case and to exclude such functions with unsupported
instructions from optimization passes added extra checking
Alexey Moksyakov
Advanced Software Technology Lab, Huawei
(cherry picked from FBD28264117)
Summary:
Ran iwyu multiple times, manually picked header remove lines.
Reached fixed point wrt removal: iwyu doesn't automatically remove
any more headers or forward declarations.
(cherry picked from FBD29569221)
Summary:
Previously, we used p_align value of the code segment to predict the
mapping of the segment at runtime. However, at times the reported
value is not aligned and at other times the actual aligned value will
be different because of the different page size used.
All we know is that the page size used at runtime should not exceed
p_align value. Adjust our segment address matching accordingly.
(cherry picked from FBD28133066)
Summary:
Addressing comments from the review for "Expand auto types".
Use const reference in MCPlusBuilder for MCInstrDesc where the copy
is not necessary.
(cherry picked from FBD27844344)
Summary:
We may have a CU with empty ranges, so accept errors coming
from DWARFDie::getAddressRanges(). This happens when using tools that
selectively strip debuginfo from the binary.
(cherry picked from FBD27602731)
Summary:
Refactor SectionPatches to avoid the use of extra map and a cast
from StringRef to std::string.
cherry-picked from FBD26756560
(cherry picked from FBD27490641)
Summary:
The user may wish to run BOLT for printing statistics only
(i.e. to check that the profile is valid). Add an option to run BOLT
without writing any output file, similar to a dry run. This option
is triggered by supplying -o with "/dev/null".
(cherry picked from FBD29568632)
Summary:
During the initial indirect jump analysis, we used to assert that the
discovered jump table type matched the pattern of the corresponding
instruction sequence. E.g., for PIC jump table memory we expected the
PIC jump table instruction sequence. The assertions were too
conservative, as in the case of a mismatch we can mark the indirect jump
as having an unknown control flow. That should be sufficient to either
skip the function processing or rely on relocation information for
possible recovery of the control flow.
(cherry picked from FBD27255816)
Summary:
Fix a bug with instrumentation when trying to instrument
functions that share a jump table with multiple indirect
jumps. Usually, each indirect jump that uses a JT will have its own
copy of it. When this does not happen, we need to duplicate the jump
table safely, so we can split the edges correctly (each copy of the
jump table may have different split edges). For this to happen, we
need to correctly match the sequence of instructions that perform the
indirect jump to identify the base address of the jump table and patch
it to point to the new cloned JT. It was reported to us a case in
which the compiler generated suboptimal code to do an indirect jump
which our matcher failed to identify.
Fixesfacebookincubator/BOLT#126
(cherry picked from FBD27065579)
Summary:
Whenever BOLT encounters a data reference in code, it tries to convert
it into <Object+Offset> form. The primary reason behind this approach is
to support read-only data-reordering optimization. However, with the
current level of the linker and compiler support we don't have enough
information to always correctly restore the original <Object+Offset>.
E.g. with zero-sized symbols we have to speculate that the actual size
of the underlying object extends to the next symbol. Most of the time,
there will be an object pointed by a zero-sized symbol and even
if we are guessing incorrectly, there will be no harm in creating
references of such form.
The problem happens when there's no object corresponding to the original
symbol and the next object is an (unmarked) jump table:
A: # <- zero-sized object
.LJUMP_TABLE:
.long <entry1>
.long <entry2>
....
.LB:
.long 21
.LC:
.long 42
The jump table will be moved and all references past it (up to the next
named object) will be incorrectly updated.
We should not speculate about the size of A in a case like that and
treat all discovered data objects (and thus references) independently.
(cherry picked from FBD27005660)
Summary:
This PR introduces 2 new instrumentation options:
1. instrumentation-no-counters-clear: Discussed at https://github.com/facebookincubator/BOLT/issues/121
2. instrumentation-wait-forks: Since the instrumentation counters are mapped as MAP_SHARED it will be nice to add ability to wait until all forks of the parent process will die using tracking of process group.
The last patch is just emitBinary code refactor.
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
Pull Request resolved: https://github.com/facebookincubator/BOLT/pull/125
GitHub Author: Vladislav Khmelevskyi <Vladislav.Khmelevskyi@huawei.com>
(cherry picked from FBD26919011)
Summary:
TBSS section is a "virtual" section that does not take memory or file
space. Ignore it completely while adjusting section sizes.
(cherry picked from FBD26824484)
Summary:
There is no real link between CU and TU, so relying on fact
that address are the same, and we are updating all of them.
(cherry picked from FBD28112114)
Summary:
This commit is the first step in rebasing all of BOLT
history in the LLVM monorepo. It also solves trivial build issues
by updating BOLT codebase to use current LLVM. There is still work
left in rebasing some BOLT features and in making sure everything
is working as intended.
History has been rewritten to put BOLT in the /bolt folder, as
opposed to /tools/llvm-bolt.
(cherry picked from FBD33289252)
Summary:
1. Add support for __literal16 section in the instrumentation runtime library for MacOS.
2. Fix emitting __counters section.
(cherry picked from FBD25746342)
Summary:
a few minor updates in block reordering:
- some refactoring to improve readability;
- optimized chain splitting strategy to improve quality of layout and performance of the algorithm.
(cherry picked from FBD25126220)
Summary:
When looking at perf.data's available binaries and their
respective mmap'ed segments, match them with the input binary by
looking at both aligned and non-aligned addresses. If we suppose
the alignment is the mmap'ed page size, we may miss some cases and
perf2bolt will refuse to proceed because it failed to match the
input binary with a process recorded in perf.data.
(cherry picked from FBD25732673)
Summary:
Add options for trading processing speed for binary performance.
-lite-threshold-pct=<uint>
Threshold (in percent) for selecting functions to process in lite
mode. Higher threshold means fewer functions to process.
E.g threshold of 90 means only top 10 percent of functions with
profile will be processed.
-lite-threshold-count=<uint>
Similar to '-lite-threshold-pct' but specify threshold using
absolute function call count. I.e. limit processing to functions
executed at least the specified number of times.
-no-scan
Do not scan cold functions for external references (may result in
slower binary).
(cherry picked from FBD24739092)
Summary:
This fixes a bug with shrink wrapping when trying to move
push-pops in a function where we are not allowed to modify the
stack layout for alignment reasons. In this bug, we failed to
propagate alignment requirement upwards in the call graph from
function A to B when: (1) there is a cycle in the call graph and
(2) the distance from A to B is greater than 1 in the call graph
and (3) there is a node in the path from A to B, not including
A or B, that does not access parameters in the stack.
(cherry picked from FBD25315977)
Summary:
This diff is a preparation for dumping the profile generated by BOLT's instrumenation on MachO.
1/ Function "bolt_instr_fini" is placed into the predefined section "__fini"
2/ In the instrumentation pass we create a symbol "bolt_instr_fini" and
replace the last global destructor with it.
This is a temporary solution, in the future we need to register bolt_instr_fini in addition to the existing destructors without dropping the last one.
(cherry picked from FBD25071864)
Summary:
Fix corner case of insertion of updated CFI with unset `PrevBB`.
Handle it in the same way as inserting past hot-cold split point.
(cherry picked from FBD24943911)
Summary:
In BinaryContext::calculateEmittedSize(), after the temporary code
emission, we have to perform a cleanup and mark all symbols used
during the emission as undefined and unregistered (so that we can emit
them again later). The cleanup is happening even for symbols that were
referenced and not defined by emitted code.
If all emitted symbols are local, there is no risk that one thread will
define a symbol while some other thread will undefine it in its cleanup
code. Such behavior is expected as local symbols can only be referenced
within the containing function and each function is processed in one
thread. However, secondary entry points have associated global symbols
and if we emit them, then it is possible for a thread to undefine
a symbol while the other thread had defined it and was in the process of
emitting the fragment with it. In such case, a data race may happen and
the thread that contains the definition of the symbol may define it
twice causing a redefinition error.
To avoid the data race, we skip the emission of secondary entry global
symbols when emitting code used only for the size estimation.
(cherry picked from FBD24986007)
Summary:
A faster and better version of function reordering:
- fixed a bug when some computed probabilities were negative;
- changed an O(n^2) loop to a priority queue to find a candidate of chains to merge
(cherry picked from FBD24571208)
Summary:
Support jump tables belonging to split fragments with entries
pointing back to parent functions.
While skipping such families of functions, make sure to use the
topmost fragment to ignore its fragments.
(cherry picked from FBD24907438)
Summary:
In a jump table identification, register an invalid offset for jump table
entries pointing to function fragments.
These invalid offsets have no effect other than padding the jump
table size, calculated as `max(OffsetEntries, Entries)`.
Correct jump table size is required in strict mode (enabled by default
in aggregation mode by `perf2bolt`) in accounting of all PC-relative
relocations in data.
Functions containing these jump tables with invalid offsets are
marked to be ignored immediately afterwards in
`populateJumpTables`.
(cherry picked from FBD24897464)
Summary:
Introduce new BinaryFunction flag `IsCanonicalCFG`, which gets
unset by SCTC pass. Make DynoStats collection conditional on this
new flag.
SCTC leaves CFG in a state where branch counters of BBs with tail
calls/conditional tail calls are not available (except via annotations,
which get stripped by `lower-annotations`). Without branch
counters, DynoStats are invalid.
(cherry picked from FBD24558050)
Summary:
Fix cold fragment name matching regex by replacing existing
regexes `.*\.cold\..*` and `.*\.cold`
and combining them into `.*\.cold(\.\d)?`,
applied to restored name (with BOLT-added suffixes stripped)
This allows matching names like "execute_stack_op.cold/1", which
previously weren't recognized.
(cherry picked from FBD24804880)
Summary:
- Allow jump table entries to point to locations inside the function and its fragments.
Reasoning behind this is that jump table identification has the logic of stopping at entry which belongs to a function different from the one originally referencing jump table. This assumption is invalid for jump tables with entries pointing to both parent function and cold fragments, leading to "unclaimed PC-relative relocations" assertion.
- Add fragment identification heuristic based on function name regex and contiguous jump table entries.
Currently, parent-to-fragment relationship is set up based on interprocedural references – direct references from the parent function. These references don't include references through jump table.
Additionally, some fragments are only reachable through jump table. In that case, in order to fully consume jump table, add parent-to-fragment relationship during `analyzeJumpTable` using the following heuristics:
1. Fragment is identified as such based on name (contains `.cold.` part), but
2. Parent function is not set – no direct interprocedural references to that fragment, and
3. Fragment has the name of the form <parent>.cold(.\d+)
* For split functions with jump table entries spanning parent and fragments, mark parent and all fragments as ignored.
(cherry picked from FBD24456904)
Summary:
For interprocedural references to fragments, record them as
fragment entry points. Not registering these entry points leads to
UCE removing the blocks and "Undefined temporary symbol"
assertion.
(cherry picked from FBD24511281)
Summary:
Some of the TLS relocatios like R_AARCH64_TLSDESC_ADR_PAGE21 must be
handled by bolt and should not be skipped by the removed condition. Some
of the TLS relocations like R_AARCH64_TLS_TPREL64 could really be skipped
here, but AFAIU this condition was added as part of BOLT its self optimization, so
to prevent future problems here my suggestion is not to add another condition
like "isTLS(RType) && isTLSRelocatable(RType)", but just remove it since
absense of this condition should not broke any other TLS relocation.
Vladislav Khmelevsky,
Advanced Software Technology Lab, Huawei
Pull Request resolved: https://github.com/facebookincubator/BOLT/pull/103
GitHub Author: Vladislav Khmelevsky <Vladislav.Khmelevskyi@huawei.com>
(cherry picked from FBD24745928)
Summary:
Fix several issues to make C++ exceptions work in shared objects:
* Set MCObjectFileInfo PIC type based on the input binary type.
* Support indirect (DW_EH_PE_indirect) encoding while writing
exception Type Table.
* Use different LPStart value and landing pad encoding for .so's.
* Disable splitting of exception-handling code for .so's because of
the new encoding.
(cherry picked from FBD24698765)
Summary:
EliminateUnreachableBlocks has a data race because it depends
on BinaryContext::computeCodeSize. computeCodeSize supports independent
Emitters, enabling a lock-free execution. Unfortunately, that is almost
as expensive as the lock. Removing the boilerplate code for
parallellization of this pass turned out to be the best alternative: no
races and slightly better execution time for HHVM.
(cherry picked from FBD24716250)
Summary:
In BinaryContext, we had StringRef holding a reference to
an r-value std::string. This triggers clang's address sanitizer
warnings. In MCPlusBuilder we had a left shift overflowing a type,
which is undefined behavior. Similarly, in CallGraph, we had a hash
function shifting a negative value, which is also UB. The last two
triggers the UB sanitizer.
(cherry picked from FBD24661045)
Summary:
Some symbols in .dynsym will be erroneously marked as belonging to a
non-allocatable section that BOLT can remove. In that case, keep the
original invalid index for such symbols instead of setting the UNDEF
index.
(cherry picked from FBD24488677)
Summary:
Change .dot dumps filename format from
<function>-<passname>.dot
to
<function>-<passidx>_<passname>.dot
This change helps navigate dumps by making the pass order explicit.
Example:
execute_stack_op.cold.6-1(*2)-00_build-cfg.dot
execute_stack_op.cold.6-1(*2)-01_validate-internal-calls.dot
execute_stack_op.cold.6-1(*2)-02_strip-rep-ret.dot
...
(cherry picked from FBD24452903)
Summary:
While refactoring the pass, I removed the important transactional
property of the patching process. Restore it.
(cherry picked from FBD24440214)
Summary:
When -hot-text is on, do not read __hot_start and __hot_end
from input (inserted by a linker script with the intent of ordering
functions). This can confuse BOLT into creating a function with this
name depending on which address the symbol lands and we will assert
when trying to emit our own __hot_start/__hot_end with symbol
redefinition.
(cherry picked from FBD24366636)
Summary:
This diff is a preparation for loading the runtime on MachO.
The proposed schema is the following:
1/ Function "bolt_instr_setup" is placed into the predefined section "setup" (in the final setting this function will be coming from the instrumentation runtime but we still will be placing it into this section).
2/ In the instrumentation pass we create a symbol "bolt_instr_setup" and inject the corresponding call into the beginning of the function representing the entry point of the binary.
(cherry picked from FBD24329530)
Summary:
Do not store processed DWARF DIEs, but instead process them while
reading one at a time.
Reduces memory consumption when updating debug info by 10%-25%.
(cherry picked from FBD24327029)
Summary:
When placing restore instructions in the shrink wrapping pass,
we typically put them right before the last instruction of a block at
the dominance frontier. If this instruction happened to have a prefix,
because the MC lib separates prefix into separate MCInsts, we would
accidentally put a load between a prefix and another instruction. Fix
this.
(cherry picked from FBD24295324)
Summary:
Add first bits to support emitting instrumented code on MachO.
This diff enables us to instrument branches / emit counters.
(cherry picked from FBD24255164)
Summary:
On targets that support it, emit size of the emitted function symbol.
At the moment there's no use for the size except that it is visible in a
temporary .o file symbol table.
(cherry picked from FBD24246177)
Summary: _end is "defined" but its address doesn't belong to any section. This diff adds special handling for this symbol.
(cherry picked from FBD24249120)
Summary:
Append ".cold.0" suffix to the original part of the name, such that
"foo/1" becomes "foo.cold.0/1" instead of "foo/1.cold.0".
(cherry picked from FBD24246112)
Summary:
At the moment we are not using PatchEntries pass in non-relocation mode
on ELF. However, we will use it on MachO.
(cherry picked from FBD24235271)
Summary: Add ToolPath field to MachORewriteInstance. This will enable us to locate the runtime library relative to the tool's location.
(cherry picked from FBD24183448)
Summary:
Do not mix relocation codes from different archs. Even though
they do not intersect at the moment, this could easily introduce bugs
once new relocations are supported (for example, ILP32 for AArch64).
(cherry picked from FBD24169425)
Summary:
This diff adds a command line option to disable the check of overlapping elements in Mach-O parsing. This check in its current form is prohibitively expensive for large binaries.
A long-term fix would be to reimplement the check in a more efficient manner (and contribute it to the upstream).
(cherry picked from FBD24109468)
Summary:
In analyzeRelocations, we extract the result of the relocation
from binary code to recreate the target of it in a few special cases.
For R_X86_64_32S relocations, however, we were neglecting the
possibility of the encoded value in the instruction to be negative.
(cherry picked from FBD24096347)
Summary:
This patch fixes the assertion failure during instrumentation.
The assertion is raised by `getInstructionAtOffset` , which expects `CurrentState` to be either `Disassembled` or `CFG`.
The function is called from `postProcessEntryPoints`, which goes over Labels and performs a series of checks. The checks call BinaryFunction methods `setSimple(false)` or `setIgnored()`.
However, if `setIgnored` is invoked, it resets the state to `Empty`. Thus subsequent call to `getInstructionAtOffset` will fail.
(cherry picked from FBD24005197)
Summary:
Enable initial support for reading and patching special Linux kernel sections.
Author: Tanvir Ahmed Khan <takh@fb.com>
GitHub Author: takhandipu
(cherry picked from FBD22998869)
Summary:
Whenever we search for a function based on its address in the input
binary, we now always return a corresponding fragment for split
functions. If the user needs an access to the main fragment, they can
call getTopmostFragment().
(cherry picked from FBD23670311)
Summary:
Sections that do not originate from the input binary will have an
input address set to zero and thus do not have to be mapped.
Mapping such sections caused a build time regression in non-relocation
mode.
(cherry picked from FBD23670334)
Summary:
Fix issue with splitting critical edges originating at
the same BB in ShrinkWrapping::splitFrontierCritEdges.
Splitting of critical edges originating at the same FromBB
wasn't handled correctly as the Frontier at index corresponding
to FromBB was overwritten with basic blocks created for
multiple DestinationBBs.
(cherry picked from FBD23232398)
Summary:
Right now, if activity is recorded in cold parts, we write to
the .fdata file the ".cold" name instead of the correct name of the
function. Fix this.
(cherry picked from FBD23148705)
Summary:
When the input file is processed by BOLT, we cannot save profile in YAML
format as it requires CFG representation of functions.
(cherry picked from FBD22941794)