summaryrefslogtreecommitdiff
path: root/llvm/lib/Transforms/IPO/ArgumentPromotion.cpp
AgeCommit message (Collapse)Author
2025-06-12[DebugInfo][RemoveDIs] Delete debug-info-format flag (#143746)Jeremy Morse
This flag was used to let us incrementally introduce debug records into LLVM, however everything is now using records. It serves no purpose now, so delete it.
2025-04-16[llvm] Construct SmallVector with iterator ranges (NFC) (#136064)Kazu Hirata
2025-03-18[IPO] Avoid repeated hash lookups (NFC) (#131720)Kazu Hirata
2025-03-06[IPO] Avoid repeated hash lookups (NFC) (#129987)Kazu Hirata
2025-01-16[IR] Provide array with poison-generating metadata IDs. (#123188)Florian Hahn
Add Metadata::PoisonGeneratingIDs containing IDs of poison-generating metadata to allow easier re-use. PR: https://github.com/llvm/llvm-project/pull/123188
2024-11-05[ArgPromotion] Use poison instead of undef as placeholder in deleted ↵Nuno Lopes
metadata [NFC]
2024-10-17[APInt] Fix APInt constructions where value does not fit bitwidth (NFCI) ↵Nikita Popov
(#80309) This fixes all the places that hit the new assertion added in https://github.com/llvm/llvm-project/pull/106524 in tests. That is, cases where the value passed to the APInt constructor is not an N-bit signed/unsigned integer, where N is the bit width and signedness is determined by the isSigned flag. The fixes either set the correct value for isSigned, set the implicitTrunc flag, or perform more calculations inside APInt. Note that the assertion is currently still disabled by default, so this patch is mostly NFC.
2024-10-04[ArgPromotion] Consider InvokeInst in Caller alias analysis (#110335)Hari Limaye
Check that all users of a Function are CallBase rather than CallInst when performing alias analysis using actual arguments in the calling function, as this check is also valid for Invoke instructions. This allows replacing the existing check with an assert, as the Function only being used by CallBase derived instructions is a precondition of the transform. This addresses post-commit review on #106216.
2024-09-27[ArgPromotion] Perform alias analysis on actual arguments of Calls (#106216)Hari Limaye
Teach Argument Promotion to perform alias analysis on actual arguments of Calls to a Function, to try to prove that all Calls to the Function do not modify the memory pointed to by an argument. This surfaces more opportunities to perform Argument Promotion in cases where simply looking at a Function's instructions is insufficient to prove that the pointer argument is not invalidated before all loads from it.
2024-09-19Revert "[Transforms][IPO] Add func suffix in ArgumentPromotion and ↵Yonghong Song
DeadArgume… (#105742)" This reverts commit 959448fbd6bc6f74fb3f9655b1387d0e8a272ab8. Reverting because multiple test failures e.g. https://lab.llvm.org/buildbot/#/builders/187/builds/1290 https://lab.llvm.org/buildbot/#/builders/153/builds/9389 and maybe a few others.
2024-09-19[Transforms][IPO] Add func suffix in ArgumentPromotion and DeadArgume… ↵yonghong-song
(#105742) …ntElimination ArgumentPromotion and DeadArgumentElimination passes could change function signatures but the function name remains the same as before the transformation. This makes it hard for tracing with bpf programs where user tends to use function signature in the source. See discussion [1] for details. This patch added suffix to functions whose signatures are changed. The suffix lets users know that function signature has changed and they need to impact the IR or binary to find modified signature before tracing those functions. The suffix for ArgumentPromotion is ".argprom" and the suffixes for DeadArgumentElimination are ".argelim" and ".retelim". The suffix also gives user hints about what kind of transformation has been done. With this patch, I built a recent linux kernel with full LTO enabled. I got 4 functions with only argpromotion like ``` set_track_update.argelim.argprom pmd_trans_huge_lock.argprom ... ``` I got 1058 functions with only deadargelim like ``` process_bit0.argelim pci_io_ecs_init.argelim ... ``` I got 3 functions with both argpromotion and deadargelim ``` set_track_update.argelim.argprom zero_pud_populate.argelim.argprom zero_pmd_populate.argelim.argprom ``` [1] https://github.com/llvm/llvm-project/issues/104678
2024-08-31[Transforms][IPO] Add remarks for ArgumentPromotion and DeadArgumentE… ↵yonghong-song
(#105740) …limination ArgumentPromotion and DeadArgumentElimination passes may change function signature. This makes bpf tracing difficult since users either not aware of signature change or need to poke into IR or assembly to understand the function signature change. This patch enabled to emit some remarks so if recompiling with -foptimization-record-file=<file>, users can check remarks to see what kind of signature changes for a particular function. The following are some examples for implemented remarks: ``` Pass: deadargelim Name: ReturnValueRemoved DebugLoc: { File: 'bpf-next/net/mptcp/protocol.c', Line: 572, Column: 0 } Function: mptcp_check_data_fin Args: - String: 'removing return value ' - String: '0' Pass: deadargelim Name: ArgumentRemoved DebugLoc: { File: 'bpf-next/kernel/bpf/syscall.c', Line: 1670, Column: 0 } Function: map_delete_elem Args: - String: 'eliminating argument ' - ArgName: uattr.coerce0 - String: '(' - ArgIndex: '1' - String: ')' Pass: argpromotion Name: ArgumentPromoted DebugLoc: { File: 'bpf-next/net/mptcp/protocol.h', Line: 570, Column: 0 } Function: mptcp_subflow_ctx Args: - String: 'promoting argument ' - ArgName: sk - String: '(' - ArgIndex: '0' - String: ')' - String: ' to pass by value' ``` [1] https://github.com/llvm/llvm-project/issues/104678
2024-08-13[LLVM] Don't peek through bitcast on pointers and gep with zero indices. ↵Yingwei Zheng
NFC. (#102889) Since we are using opaque pointers now, we don't need to peek through bitcast on pointers and gep with zero indices.
2024-07-14[ArgPromotion] Remove redundant logic from recursive argpromotion code (#98657)Vedant Paranjape
This patch further cleans up the implementation by removing some redundant checks and replacing cast<> with get() calls. This contribution is based on the discussion in #78735
2024-07-11[ArgumentPromotion] Fix -Wunused-but-set-variable after #78735Fangrui Song
2024-07-12[ArgPromotion] Handle pointer arguments of recursive calls (#78735)Vedant Paranjape
Argument promotion doesn't handle recursive function calls to promote arguments. This patch adds functionality to handle self recursive function calls, i.e. whose SCC size is 1. Due to complexity of ValueTracking in recursive calls with SCC size greater than 1, we bail out in such cases.
2024-06-29[IRBuilder] Don't include Module.h (NFC) (#97159)Nikita Popov
This used to be necessary to fetch the DataLayout, but isn't anymore.
2024-06-28[IR] Add getDataLayout() helpers to Function and GlobalValue (#96919)Nikita Popov
Similar to https://github.com/llvm/llvm-project/pull/96902, this adds `getDataLayout()` helpers to Function and GlobalValue, replacing the current `getParent()->getDataLayout()` pattern.
2024-03-12[ArgPromotion] Remove incorrect TranspBlocks set for loads. (#84835)Florian Hahn
The TranspBlocks set was used to cache aliasing decision for all processed loads in the parent loop. This is incorrect, because each load can access a different location, which means one load not being modified in a block doesn't translate to another load not being modified in the same block. All loads access the same underlying object, so we could perhaps use a location without size for all loads and retain the cache, but that would mean we loose precision. For now, just drop the cache. Fixes https://github.com/llvm/llvm-project/issues/84807 PR: https://github.com/llvm/llvm-project/pull/84835
2024-03-05[NFC][RemoveDIs] Insert instruction using iterators in Transforms/Jeremy Morse
As part of the RemoveDIs project we need LLVM to insert instructions using iterators wherever possible, so that the iterators can carry a bit of debug-info. This commit implements some of that by updating the contents of llvm/lib/Transforms/Utils to always use iterator-versions of instruction constructors. There are two general flavours of update: * Almost all call-sites just call getIterator on an instruction * Several make use of an existing iterator (scenarios where the code is actually significant for debug-info) The underlying logic is that any call to getFirstInsertionPt or similar APIs that identify the start of a block need to have that iterator passed directly to the insertion function, without being converted to a bare Instruction pointer along the way. Noteworthy changes: * FindInsertedValue now takes an optional iterator rather than an instruction pointer, as we need to always insert with iterators, * I've added a few iterator-taking versions of some value-tracking and DomTree methods -- they just unwrap the iterator. These are purely convenience methods to avoid extra syntax in some passes. * A few calls to getNextNode become std::next instead (to keep in the theme of using iterators for positions), * SeparateConstOffsetFromGEP has it's insertion-position field changed. Noteworthy because it's not a purely localised spelling change. All this should be NFC.
2024-01-12[IRBuilder] Add CreatePtrAdd() method (NFC) (#77582)Nikita Popov
This abstracts over the common pattern of creating a gep with i8 element type.
2023-11-08Reapply 7d77bbef4ad92, adding new debug-info classesJeremy Morse
This reverts commit 957efa4ce4f0391147cec62746e997226ee2b836. Original commit message below -- in this follow up, I've shifted un-necessary inclusions of DebugProgramInstruction.h into being forward declarations (fixes clang-compile time I hope), and a memory leak in the DebugInfoTest.cpp IR unittests. I also tracked a compile-time regression in D154080, more explanation there, but the result of which is hiding some of the changes behind the EXPERIMENTAL_DEBUGINFO_ITERATORS compile-time flag. This is tested by the "new-debug-iterators" buildbot. [DebugInfo][RemoveDIs] Add prototype storage classes for "new" debug-info This patch adds a variety of classes needed to record variable location debug-info without using the existing intrinsic approach, see the rationale at [0]. The two added files and corresponding unit tests are the majority of the plumbing required for this, but at this point isn't accessible from the rest of LLVM as we need to stage it into the repo gently. An overview is that classes are added for recording variable information attached to Real (TM) instructions, in the form of DPValues and DPMarker objects. The metadata-uses of DPValues is plumbed into the metadata hierachy, and a field added to class Instruction, which are all stimulated in the unit tests. The next few patches in this series add utilities to convert to/from this new debug-info format and add instruction/block utilities to have debug-info automatically updated in the background when various operations occur. This patch was reviewed in Phab in D153990 and D154080, I've squashed them together into this commit as there are dependencies between the two patches, and there's little profit in landing them separately. [0] https://discourse.llvm.org/t/rfc-instruction-api-changes-needed-to-eliminate-debug-intrinsics-from-ir/68939
2023-11-02Revert "[DebugInfo][RemoveDIs] Add prototype storage classes for "new" ↵Jeremy Morse
debug-info" And some intervening fixups. There are two remaining problems: * A memory leak via https://lab.llvm.org/buildbot/#/builders/236/builds/7120/steps/10/logs/stdio * A performance slowdown with -g where I'm not completely sure what the cause it These might be fairly straightforwards to fix, but it's the end of the day hear, so I figure I'll clear the buildbots til tomorrow. This reverts commit 7d77bbef4ad9230f6f427649373fe46a668aa909. This reverts commit 9026f35afe6ffdc5e55b6615efcbd36f25b11558. This reverts commit d97b2b389a0e511c65af6845119eb08b8a2cb473.
2023-11-02[DebugInfo][RemoveDIs] Add prototype storage classes for "new" debug-infoJeremy Morse
This patch adds a variety of classes needed to record variable location debug-info without using the existing intrinsic approach, see the rationale at [0]. The two added files and corresponding unit tests are the majority of the plumbing required for this, but at this point isn't accessible from the rest of LLVM as we need to stage it into the repo gently. An overview is that classes are added for recording variable information attached to Real (TM) instructions, in the form of DPValues and DPMarker objects. The metadata-uses of DPValues is plumbed into the metadata hierachy, and a field added to class Instruction, which are all stimulated in the unit tests. The next few patches in this series add utilities to convert to/from this new debug-info format and add instruction/block utilities to have debug-info automatically updated in the background when various operations occur. This patch was reviewed in Phab in D153990 and D154080, I've squashed them together into this commit as there are dependencies between the two patches, and there's little profit in landing them separately. [0] https://discourse.llvm.org/t/rfc-instruction-api-changes-needed-to-eliminate-debug-intrinsics-from-ir/68939
2023-09-18[ArgPromotion] Update allocsize indices after promotionNikita Popov
Promotion can add/remove arguments. We need to update the indices in the allocsize attribute accordingly. Fixes https://github.com/llvm/llvm-project/issues/66103.
2023-06-23[ArgPromotion] Remove code for handling typed pointers (NFC)Nikita Popov
2023-05-05Revert "[ArgumentPromotion] Bail if any callers are minsize"Shoaib Meenai
This reverts commit 8b8466fd31e5a194fd8ba7a73a0f23d32f164318. This is causing size regressions with -Oz and FullLTO. Revert while I come up with a repro.
2023-05-03[ArgumentPromotion] Bail if any callers are minsizeArthur Eubanks
Argument promotion mostly works on functions with more than one caller (otherwise the function would be inlined or is dead), so there's a good chance that performing this increases code size since we introduce loads at every call site. If any caller is marked minsize, bail. We could compare the number of loads/stores removed from the function with the number of loads introduced in callers, but that's TODO. Reviewed By: nikic Differential Revision: https://reviews.llvm.org/D149768
2023-04-19[TTI][BPF] Ensure ArgumentPromotion Not Exceeding Target MaxArgsYonghong Song
With LLVM patch https://reviews.llvm.org/D148269, we hit a linux kernel bpf selftest compilation failure like below: ... progs/test_xdp_noinline.c:739:8: error: too many args to t8: i64 = GlobalAddress<ptr @encap_v4> 0, progs/test_xdp_noinline.c:739:8 if (!encap_v4(xdp, cval, &pckt, dst, pkt_bytes)) ^ ... progs/test_xdp_noinline.c:321:6: error: defined with too many args bool encap_v4(struct xdp_md *xdp, struct ctl_value *cval, ^ ... Note that bpf selftests are compiled with -O2 which is the recommended flag for bpf community. The bpf backend calling convention is only allowing 5 parameters in registers and does not allow pass arguments through stacks. In the above case, ArgumentPromotionPass replaced parameter '&pckt' as two parameters, so the total number of arguments after ArgumentPromotion pass becomes 6 and this caused later compilation failure during instruction selection phase. This patch added a TargetTransformInfo hook getMaxNumArgs() which returns 5 for BPF and UINT_MAX for other targets. Differential Revision: https://reviews.llvm.org/D148551
2023-04-05[ArgPromotion] Require noundef to copy poison-generating metadataNikita Popov
For poison-generating (rather than IUB) metadata, only copy it from the dominating must-exec load if it is combined with !noundef. This could be further extended by additionall intersecting the metadata from all loads, which does not require !noundef.
2023-03-23[ArgPromotion] Remove dead code produced by removing dead argumentsJeff Byrnes
ArgPromotion currently produces phantom / dead loads. A good example of this is store-into-inself.ll. First, ArgPromo finds the promotable argument %p in @l. Then it inserts a load of %p in the caller, and passes instead the loaded value / transforms the function body. PromoteMem2Reg is able to optimize out the entire function body, resulting in an unused argument. In a subsequent ArgPromotion pass, it removes the dead argument, resulting in a dead load in the caller. These dead loads may reduce effectiveness of other transformations (e.g. SimplifyCFG, MergedLoadStoreMotion). This patch removes loads and geps that are made dead in the caller after removal of dead args. Differential Revision: https://reviews.llvm.org/D146327
2023-01-11[NFC] Use TypeSize::getKnownMinValue() instead of TypeSize::getKnownMinSize()Guillaume Chatelet
This change is one of a series to implement the discussion from https://reviews.llvm.org/D141134.
2023-01-06Revert D141134 "[NFC] Only expose getXXXSize functions in TypeSize"Guillaume Chatelet
The patch should be discussed further. This reverts commit dd56e1c92b0e6e6be249f2d2dd40894e0417223f.
2023-01-06[NFC] Only expose getXXXSize functions in TypeSizeGuillaume Chatelet
Currently 'TypeSize' exposes two functions that serve the same purpose: - getFixedSize / getFixedValue - getKnownMinSize / getKnownMinValue source : https://github.com/llvm/llvm-project/blob/bf82070ea465969e9ae86a31dfcbf94c2a7b4c4c/llvm/include/llvm/Support/TypeSize.h#L337-L338 This patch offers to remove one of the two and stick to a single function in the code base. Differential Revision: https://reviews.llvm.org/D141134
2022-12-14[NFC] Cleanup: Replace Function::getBasicBlockList().splice() with ↵Vasileios Porpodas
Function::splice() This is part of a series of patches that aim at making Function::getBasicBlockList() private. Differential Revision: https://reviews.llvm.org/D139984
2022-12-05Transforms/IPO: llvm::Optional => std::optionalFangrui Song
2022-12-04[llvm] Use std::nullopt instead of None in comments (NFC)Kazu Hirata
This is part of an effort to migrate from llvm::Optional to std::optional: https://discourse.llvm.org/t/deprecating-llvm-optional-x-hasvalue-getvalue-getvalueor/63716
2022-12-02[Transforms] Use std::nullopt instead of None (NFC)Kazu Hirata
This patch mechanically replaces None with std::nullopt where the compiler would warn if None were deprecated. The intent is to reduce the amount of manual work required in migrating from Optional to std::optional. This is part of an effort to migrate from llvm::Optional to std::optional: https://discourse.llvm.org/t/deprecating-llvm-optional-x-hasvalue-getvalue-getvalueor/63716
2022-07-26[ArgPromotion] Transfer metadata nontemporal to promoted loadsPhoebe Wang
Fixes #56703 Reviewed By: nikic Differential Revision: https://reviews.llvm.org/D130536
2022-07-24Use llvm::less_first and llvm::less_second (NFC)Kazu Hirata
2022-06-29[ArgPromotion] Remove all the getters and ReplaceCallSite (NFC)Pavel Samolysov
AARGetter is an abstraction over a source of the `AAResults` introduced to support the legacy pass manager as well as the modern one. Since the Argument Promotion pass doesn't support the legacy pass manager anymore, the abstraction is not required and `AAResults` may be used directly. The instance of the `FunctionAnalysisManager` is passed through the functions to get all the required analyses just wherever they are required and do not use the awkward getter callbacks. The `ReplaceCallSite` parameter was required for the legacy pass manager only and isn't used anymore, so the parameter has been eliminated. Differential Revision: https://reviews.llvm.org/D128727
2022-06-29[ArgPromotion] Move isDenselyPacked static member (NFC)Pavel Samolysov
The `isDenselyPacked` static member of the `ArgumentPromotionPass` class is not used in the class itself anymore. The single known user of the function is in the `AttributorAttributes.cpp` file, so the function has been moved into the file. Differential Revision: https://reviews.llvm.org/D128725
2022-06-28[ArgPromotion] Unify byval promotion with non-byvalPavel Samolysov
It makes sense to handle byval promotion in the same way as non-byval but also allowing `store` instructions. However, these should use the same checks as the `load` instructions do, i.e. be part of the `ArgsToPromote` collection. For these instructions, the check for interfering modifications can be disabled, though. The promotion algorithm itself has been modified a lot: all the accesses (i.e. loads and stores) are rewritten to the emitted `alloca` instructions. To optimize these new `alloca`s out, the `PromoteMemToReg` function from `Transforms/Utils/PromoteMemoryToRegister.cpp` file is invoked after promotion. In order to let the `PromoteMemToReg` promote as many `alloca`s as it is possible, there should be no `GEP`s from the `alloca`s. To eliminate the `GEP`s, its own `alloca` is generated for every argument part because a single `alloca` for the whole argument (that significantly simplifies the code of the pass though) unfortunately cannot be used. The idea comes from the following discussion: https://reviews.llvm.org/D124514#3479676 Differential Revision: https://reviews.llvm.org/D125485
2022-06-27[ArgPromotion] Remove legacy PM supportNikita Popov
Support for the legacy pass manager in ArgPromotion causes complications in D125485. As the legacy pass manager for middle-end optimizations is unsupported, drop ArgPromotion from the legacy pipeline, rather than introducing additional complexity to deal with it. Differential Revision: https://reviews.llvm.org/D128536
2022-06-26[ArgumentPromotion] use poison when replacing dead instructions instead of ↵Nuno Lopes
undef [NFC]
2022-05-12[ArgPromotion] Make a non-byval promotion attempt firstPavel Samolysov
It makes sense to make a non-byval promotion attempt first and then fall back to the byval one. The non-byval ('usual') promotion is generally better, for example it does promotion even when a structure has more elements than 'MaxElements' but not all of them are actually used in the function. Differential Revision: https://reviews.llvm.org/D124514
2022-05-02[ArgPromotion][Attributor] Update min-legal-vector-width when do promotionPhoebe Wang
X86 codegen uses function attribute `min-legal-vector-width` to select the proper ABI. The intention of the attribute is to reflect user's requirement when they passing or returning vector arguments. So Clang front-end will iterate the vector arguments and set `min-legal-vector-width` to the width of the maximum for both caller and callee. It is assumed any middle end optimizations won't care of the attribute expect inlining and argument promotion. - For inlining, we will propagate the attribute of inlined functions because the inlining functions become the newer caller. - For argument promotion, we check the `min-legal-vector-width` of the caller and callee and refuse to promote when they don't match. The problem comes from the optimizations' combination, as shown by https://godbolt.org/z/zo3hba8xW. The caller `foo` has two callees `bar` and `baz`. When doing argument promotion, both `foo` and `bar` has the same `min-legal-vector-width`. So the argument was promoted to vector. Then the inlining inlines `baz` to `foo` and updates `min-legal-vector-width`, which results in ABI mismatch between `foo` and `bar`. This patch fixes the problem by expanding the concept of `min-legal-vector-width` to indicator of functions arguments. That says, any passes touch functions arguments have to set `min-legal-vector-width` to the value reflects the width of vector arguments. It makes sense to me because any arguments modifications are ABI related and should response for the ABI compatibility. Differential Revision: https://reviews.llvm.org/D123284
2022-04-28[ArgPromotion] Move ArgPart and OffsetAndArgPart to anonymous namespacePavel Samolysov
The structure ArgPart and alias OffsetAndArgPart have been moved into the anonymous namespace. NFC. Reviewed By: aeubanks Differential Revision: https://reviews.llvm.org/D124617
2022-04-28[ArgPromotion] Change the condition to check the promotion limitPavel Samolysov
The condition should be 'ArgParts.size() > MaxElements', so that if we have exactly 3 elements in the 'ArgParts' vector, the promotion should be allowed because the 'MaxElement' threshold is not exceeded yet. The default value for 'MaxElement' has been decreased to 2 in order to avoid an actual change in argument promoting behavior. However, this changes byval argument transformation behavior by allowing adding not more than 2 arguments to the function instead of 3 allowed before. Reviewed By: aeubanks Differential Revision: https://reviews.llvm.org/D124178
2022-04-28[ArgPromotion] Rename variables according to the code style. NFCPavel Samolysov
Some loop counters ('i', 'e') and variables ('type') were named not in accordance with the code style and clang-tidy issues warnings about the using of such variables. This patch renames the variables and fixes some typos in the comments within the source file. Differential Revision: https://reviews.llvm.org/D123662