<table border="1" cellspacing="0" cellpadding="8">
<tr>
<th>Issue</th>
<td>
<a href=https://github.com/llvm/llvm-project/issues/68605>68605</a>
</td>
</tr>
<tr>
<th>Summary</th>
<td>
False positive warning with `-Wshadow` when using structured binding and lambda capture
</td>
</tr>
<tr>
<th>Labels</th>
<td>
new issue
</td>
</tr>
<tr>
<th>Assignees</th>
<td>
</td>
</tr>
<tr>
<th>Reporter</th>
<td>
JIghtuse
</td>
</tr>
</table>
<pre>
Clang 17.0.1 started to emit shadowing warning in the following case. There is lambda capture of an entity[^1] made with structured binding, and entity has the same name as the capture name. See [example](https://godbolt.org/z/MbeEYM8Yj) on godbolt or below. The warning looks like false positive, because:
* It is not possible to use name from outer scope (from `get_descriptors` in the example) in lambda without capturing, so no shadowing possible.
* Note that there is no warning in the [similar case](https://godbolt.org/z/eqYPsWfvM) without structured binding.
This behavior is annoying, because it forces to come up with new names where old ones should work.
Affected versions:
* Clang 17.0.1
* Clang trunk (on godbolt)
Not affected versions:
* 16.0.0 and older.
Repeating problematic example with warning as a comment for completeness here:
```cpp
#include <algorithm>
#include <map>
#include <vector>
struct Descriptor
{
// some fields needed for descriptor
};
struct Metadata
{
};
using DescriptorMap = std::map<int, Descriptor>;
std::pair<DescriptorMap, Metadata> get_descriptor_map_with_metadata()
{
return std::pair(DescriptorMap
{
{ 1, Descriptor{} },
{ 42, Descriptor{} },
},
Metadata{});
}
std::vector<Descriptor> get_descriptors(const std::vector<int> & ids)
{
auto [id_to_descriptor, metadata] = get_descriptor_map_with_metadata();
std::vector<Descriptor> descriptors;
const auto fill_descriptors =
// warning: declaration shadows a structured binding [-Wshadow]
[id_to_descriptor = std::move(id_to_descriptor), &metadata, &descriptors]
(const int id)
{
descriptors.push_back(id_to_descriptor.at(id));
};
std::for_each(begin(ids), end(ids), fill_descriptors);
return descriptors;
}
```
[^1]: I know that structured binding creates not exactly a variable, hence I call it "entity".
</pre>
<img width="1px" height="1px" alt="" src="http://email.email.llvm.org/o/eJyMVt-P2jgQ_mvMy6hRcCCEBx52YZH2pK1Od5WqPqFJMhB3HTtnO9C9v_5kJ4Two9dKKIA945nv-ybjQWvFQRGt2PyZzTcTbF2lzeqP10PlWkuTXJcfq7VEdYDpIoqjKViHxlEJTgPVwoGtsNQnoQ5wQqP8t1DgKoK9lrLbKNBSBF8qMgTCgsQ6LxEKbFxrCPQeUAEpJ9xHyOJlyuYbqLEkOAlXgXWmLbxpCblQpVAHxteAquydoEIbIlqsCZR_9AvnEH4tgr-JgM2f6QfWjSQ23zCeVc41liVPjG8Z3x50mWvpIm0OjG__ZXz7ltPLt7fs23fGl6AV9BagDeQk9SnAGpBLrd8tSPFOsEdpCRpthRNH8gnnVGBryQeLNyx-YvwJXp0nRGnnLa3IJXleW9vD2Btdg24dGbCFbggYz8IaS-MDuV1JtjCicdpYlsZn4s8A-dKv9Gx7JnXrekp6Dq0GpUcKnpOILhl-1o7AVej80Z1-St9KzebPVtRCogla_x619M-3P-3X_fHNJ3pO717rcy7h-aUSFnKq8Ci08bmgUvqjR9MTDMLBXpuCrOey0DVB23SVpOgUiLVwCmC0LEErsmAr3coSTtq8X8V72u-p8NV-JGOFVvZKvfF7cbvqTKvevV6XomF8OT77s3aA_3v-NI3iKA6VrmVJ5iq1v6ghdEE1o3NJNTpRnLXv4J5VQgvoiahJBWr870aSI0XWgmfiEjaNu0_RNOdEEqEK2ZYELFmjPGgjXFWz5OXRfo3NT3aOVDhtLpvh2ckNm6GO-83Fc_cDAKCrH7BeyL0gWVpQRCWVAUp557phyfODGG_ksESHNxF-5tVaz9wlsTdsgCUbsK70ZCVPAelaKOdLbwQgebmL33s0KAxL1ldneuchs-QFrt_qXY3Nzku5q882PLuU0ZglQ641Cq6D8ew62GAdeB27jxZheoNo8cwWG_AU8XXv4c1m_Nd2w6mjtQFusPdoBr4Wm4fEnUtnfUUz3HZAnhVaWQf3fl6l5AUYT0GU9jGB2DrtG5kod06PzvUgB_bnm1AEv6nSdR34IL-CNIZz793BC4nuhZRj8D6tG86716bvASx5gpIKiQad0Krv-b4v3Hdcz8Knr52Fb-W95PfU3LwQ2t9z2T1_S08h4-mFnfB3jPUS5SyiUA5EOUh1X7Qj96hpbbXLsXh_ED9CF1ZDHhdNxqV5w_SAaK_NjrCoGM9yOggVzrE9IFLl1f9bRR4XQP-aPtR5qP5zD77qUMNk5KV8hXelT929_EDAwhA66gYL-oGFkx-AcEQjMJdhGKlIFQSvUKCU_sJknPcTGOfRpFwl5TJZ4oRW03SZZmnG0-mkWhVZMieaLbM4XuKMqECczmZpjMV8TmkRT8SKxzyZxvFymk4XSRblSZxjtiRaTOeL-Sxhs5hqFDKS8lj7YWAirG1plWZpPJ9IzEnaMIty7i_rsMk496OpWXmfT3l7sGwWS2GdvZzihJO02l4NXcP9Fy5DlsZDUaexHwAUdE3-AYH-yr0eUyetkaubkUa4qs2jQteMb30m_denxujvVDjGtyF_y_g24PsvAAD__32Wk8s">