<table border="1" cellspacing="0" cellpadding="8">
<tr>
<th>Issue</th>
<td>
<a href=https://github.com/llvm/llvm-project/issues/141559>141559</a>
</td>
</tr>
<tr>
<th>Summary</th>
<td>
Call-related operations cause stack variable dbg_values to be killed too eagerly in calculateDbgEntityHistory
</td>
</tr>
<tr>
<th>Labels</th>
<td>
new issue
</td>
</tr>
<tr>
<th>Assignees</th>
<td>
</td>
</tr>
<tr>
<th>Reporter</th>
<td>
khuey
</td>
</tr>
</table>
<pre>
It's a common pattern in Rust iterator code to create a closure that is passed to a function that does something on the iterator (e.g. `map`). When optimization is turned on, LLVM can generally chew through the iterator boilerplate and reduce the code to the imperative form.
When Rust closures have upvars, those are handled as you might expect: an anonymous type is created to hold the upvars, an instance of that anonymous type is created when the closure is created, and it is passed as a hidden first argument to the closure function when it is executed. The closures that are used in iterator code generally don't last beyond the function that created them, so once LLVM's optimizer chews through the iterator code and gets to inlining the closure function itself, SROA will generally recognize that the anonymous type is no longer necessary and it will rip it apart into its constituents.
Debug info generally seems to be propagated correctly up to this point. We end up with a dbg_value for the upvar *as seen inside the closure* at the point where the stack slot the upvar resides *in the outer function*. e.g.
```
DBG_VALUE_LIST !"foo", !DIExpression(DW_OP_LLVM_arg, 0, DW_OP_plus_uconst, 64, DW_OP_deref), $rsp, debug-location !1336; src/main.rs:0 @[ src/main.rs:18:12 ] line no:6
```
However, when we go to run `llvm::calculateDbgEntityHistory`, this value gets dropped because its out of range. The value gets killed well before we ever get to the code that's in the scope of the closure by a
```
ADJCALLSTACKDOWN64 0, 0, 0, implicit-def dead $rsp, ...
```
That precedes an unrelated function call.
It's more than a little surprising that this kills the debug value since
1. Guessing from the operands the ADJCALLSTACKDOWN64 doesn't actually change $rsp
2. There are a variety of ways in DWARF to cope with $rsp changing (using the CFA, DW_OP_entry_value, etc)
There's also code in `llvm::calculateDbgEntityHistory` that terminates values at the end of the basic block which seems likely to pose an obstacle here too.
It seems like what we want conceptually is for LLVM to recognize that this stack slot is valid from when it is first stored to until the function epilogue, to extend the dbg_value across the function accordingly, and then rely on trim-var-locs to cut the ranges down to where they're actually in scope in the program.
I have to believe I'm not the first person to run into this :) I haven't looked at how clang handles equivalent C++ lambda code yet but it either has the same problem or gets around this issue somehow. Maybe @jmorse and his people have some thoughts?
</pre>
<img width="1" height="1" alt="" src="http://email.email.llvm.org/o/eJyUVk1z4zgO_TX0BRWXLNuJffBBiTsz2c1sb3X3To4pioIlTihCyw-7Nb9-C6Qcu78OW9XlTkkiCLz38ADpvW4t4k6s78V6P5MxdOR2b13EcVZTM-6egijvPEhQ1PdkYZAhoLOgLXyKPoAO6GQgB4oahECgHMqAfMCQjw4hdDKA9jBI77HhTyQcolVBk80vG0IPnnoMnbYtpMd4iSzKDc7bOYjbopeDuC1EuZ3DS4cWaAi613_LFEt7CNFZbICsKB_g-fnPP0BJCy1adNKYEVSHJwido9h2315SkzboBpNytw04bKLC9M25svR9P_ABfUQ4kOvnoqhEUaVcEhxT0R46eUSIw1E6z7mEjjyCdAidtI3BBqSHkSL0uu0C4NcBVRDLCqQFacmOPUUPYRyQy8qYJuw6Mk3K5BJbMhs-SKsQ6JAh_XWME-eaypr4ubzLwRrQ13xJJr_TTYMWDtr5ANK1sUcbzpicA72Tmq7IQfArqhiwmcOXy5d-ytEhRL5C2-9kdCGsYSrvAhjpA9Q4ks3Vfyugd3w67LkIT0CMBisgyXfSCbqkAP9zCaSruf4Wg-fitDXasiJ_WqUOHs2Br_v86WMFJ23MVeIOFbVW_z3pnyP8yIklMGRbdGBRoffSjWcCUjinB_5bDtIF0JZTCh4UWR90iGiDnwS4xzq2oO2BrlLwiH2qo0YYHA2yTSApcg5VMCPEIVPIZJO2YQ4vCGgbfnHSoQMJTd2-HqWJSe4X3YEoK-n5hqQ93eA1RqKsYKo5xWVBuPyFD1K9gTcUroI55Aieg-qsTYoB3TvUoqzmAOwBuVq2gPyvqPb3v73-WT3_58Pr89PnLyDKhSjLA5EoS6ZGlIv904evg0PvU6TN_uX1479fWRmv0rX8TcE_-fFgon-NCWB-eLu6vGrQ4UGU2xx15fzAfzUM_I0hlS1IlIvFcnkrlvfgnRLlYy-1nTsvllUBYlWI9Y8vFhv-KUGs92C0RbAkltXtd3WKovqdTnhEx9emDjshtMQMumjZHI059mJZiWWlpFGRrWxftx9s0GH8XftAbkzm-ZApz7QmrTeOhgEbqFHJ6DGpjGJgN3HStpi79-rAmzbsYSc0Bmo8kEPOhrPj9-_GkIyzk3mETNR6RcPkU5emqkeQ8CO51f4fD9Xz8-cv1cM_9x9f_nW7ymRdfnQ_GK10uGnwAA3K5oqb-Xz-I4hfuBsHhwpZcdJCtA5Naoz3zlbSmElq0_jrKQ8yCxKMDsEg-OgGp322h6R2nXHxqbIkjAkyr61CUVSLOfwWWYi2hYOjPkudB4pt8qmfFMzDMXugVCFOU4xJOVdaVGXix-X5IuEoncYwMsYnOSbg9y_Vp8c0nRn81Nv5dI7FCYlyE_3Z7B4eq4vy0QY3ZhfghxgUt8GEJnK784JgPGXC9f8hxgk6dL22MuAkSn92D_aiSSm19FpBbUi9wanTqpvszeg3NCOXNqQJa4FqNhmDkE2H6J3KqyNw4otPCCdpAzuqwmFCV_vkdWl74Ob63si1v3ax3Ei6yYReTb48K7nQPLijDdp8O7tw0IbajGogwK8Bp_F2sV2pHHn_7TmpFLlG29aM55Ed-GLHSPBMdLq_OUrHvpQGgIoZz9TMHho6WX78bsujKO9YOmeBaTu16dSzg6PWyfO285SXmzRYjMYjwpMo73qwk6nnygd0nuzZntLwStixKMot5CDTcCd6400jQEcnUEbadlqTPOB_oz5Kw-vGgyjvRXkPRvZ1I7PYRgxQR15DAXXo0EEnM1pe9inx2mAP5LJvSUcxoaU9aO-5N6nHjk5z-EOONbJH_9WT83kRSJMRaWAxccn8Ma9yse2CF8vHWbNbNtvlVs5wt7hbbZbLZbG9nXW7VYGLxWq72eJqq3BzuGuau6bYLJvNarUtsZnpXVmU62Jd3hWbYrW-nRdKLZfNqri9K9eNWh7EqsBeajPnRpqTa2cp391itVivtzMjazQ-re1lafGUq-Ght97P3I4P3dSx9WJVGO2Dv4QJOhjcPUhjbs7GR3mnJesh-3_WN_uIrM2VGs_bxGT_gQhQtuiyZH7Z6LPozK4LYfCJ_EdRPrY6dLGeK-pF-Zi8Iv93Mzj6i1fh8jFV5EX5OJV83JX_CwAA___yNV5D">