<table border="1" cellspacing="0" cellpadding="8">
<tr>
<th>Issue</th>
<td>
<a href=https://github.com/llvm/llvm-project/issues/64458>64458</a>
</td>
</tr>
<tr>
<th>Summary</th>
<td>
Suboptimal codegen in vector copy assignment
</td>
</tr>
<tr>
<th>Labels</th>
<td>
new issue
</td>
</tr>
<tr>
<th>Assignees</th>
<td>
</td>
</tr>
<tr>
<th>Reporter</th>
<td>
hiraditya
</td>
</tr>
</table>
<pre>
```cpp
// clang++ -std=c++17 -O3 -fno-exceptions -stdlib=libc++
#include<vector>
using Container = std::vector<int>;
int copy_assignment(const Container &v1, Container &v2) {
v2 = v1;
return 0;
}
```
I'd expect this to generate a `memcpy` but it generates a ton of seemingly unnecessary code
```asm
copy_assignment(std::__1::vector<int, std::__1::allocator<int> > const&, std::__1::vector<int, std::__1::allocator<int> >&): # @copy_assignment(std::__1::vector<int, std::__1::allocator<int> > const&, std::__1::vector<int, std::__1::allocator<int> >&)
cmp rsi, rdi
je .LBB0_2
push rax
mov rax, qword ptr [rdi]
mov rdx, qword ptr [rdi + 8]
mov rcx, rdx
sub rcx, rax
sar rcx, 2
mov rdi, rsi
mov rsi, rax
call void std::__1::vector<int, std::__1::allocator<int> >::__assign_with_size[abi:v180000]<int*, int*>(int*, int*, long)
add rsp, 8
.LBB0_2:
xor eax, eax
ret
void std::__1::vector<int, std::__1::allocator<int> >::__assign_with_size[abi:v180000]<int*, int*>(int*, int*, long): # @void std::__1::vector<int, std::__1::allocator<int> >::__assign_with_size[abi:v180000]<int*, int*>(int*, int*, long)
push rbp
push r15
push r14
push r13
push r12
push rbx
push rax
mov r13, rcx
mov rbx, rdx
mov r12, rsi
mov r14, rdi
mov r15, qword ptr [rdi]
mov rax, qword ptr [rdi + 16]
mov rcx, rax
sub rcx, r15
sar rcx, 2
cmp rcx, r13
jae .LBB1_1
test r15, r15
je .LBB1_11
mov qword ptr [r14 + 8], r15
mov rdi, r15
call operator delete(void*)@PLT
xorps xmm0, xmm0
movups xmmword ptr [r14], xmm0
mov qword ptr [r14 + 16], 0
xor eax, eax
.LBB1_11:
mov rcx, r13
shr rcx, 62
jne .LBB1_17
movabs rcx, 4611686018427387903
mov rbp, rax
sar rbp
cmp rbp, r13
cmovbe rbp, r13
movabs rdx, 9223372036854775804
cmp rax, rdx
cmovae rbp, rcx
cmp rbp, rcx
ja .LBB1_17
lea rdi, [4*rbp]
call operator new(unsigned long)@PLT
mov r15, rax
mov qword ptr [r14], rax
lea r13, [r14 + 8]
mov qword ptr [r14 + 8], rax
lea rax, [rax + 4*rbp]
mov qword ptr [r14 + 16], rax
sub rbx, r12
je .LBB1_15
mov rdi, r15
mov rsi, r12
mov rdx, rbx
call memcpy@PLT
.LBB1_15:
mov r14, r13
jmp .LBB1_16
.LBB1_1:
mov rax, qword ptr [r14 + 8]
add r14, 8
mov rdx, rax
sub rdx, r15
mov rcx, rdx
sar rcx, 2
cmp rcx, r13
jae .LBB1_7
lea r13, [r12 + 4*rcx]
cmp rax, r15
je .LBB1_4
mov rdi, r15
mov rsi, r12
call memmove@PLT
mov r15, qword ptr [r14]
.LBB1_4:
sub rbx, r13
je .LBB1_16
mov rdi, r15
mov rsi, r13
jmp .LBB1_6
.LBB1_7:
sub rbx, r12
je .LBB1_16
mov rdi, r15
mov rsi, r12
.LBB1_6:
mov rdx, rbx
call memmove@PLT
.LBB1_16:
add rbx, r15
mov qword ptr [r14], rbx
add rsp, 8
pop rbx
pop r12
pop r13
pop r14
pop r15
pop rbp
ret
.LBB1_17:
mov rdi, r14
call std::__1::vector<int, std::__1::allocator<int> >::__throw_length_error[abi:v180000]() const
std::__1::vector<int, std::__1::allocator<int> >::__throw_length_error[abi:v180000]() const: # @std::__1::vector<int, std::__1::allocator<int> >::__throw_length_error[abi:v180000]() const
push rax
lea rdi, [rip + .L.str]
call std::__1::__throw_length_error[abi:v180000](char const*)
std::__1::__throw_length_error[abi:v180000](char const*): # @std::__1::__throw_length_error[abi:v180000](char const*)
push rax
mov rsi, rdi
lea rdi, [rip + .L.str.1]
xor eax, eax
call std::__1::__libcpp_verbose_abort(char const*, ...)@PLT
.L.str:
.asciz "vector"
.L.str.1:
.asciz "length_error was thrown in -fno-exceptions mode with message \"%s\""
```
Ideally, the above C++ code should translate to the following C++ code:
```cpp
#include<vector>
using Container = std::vector<int>;
int copy_assignment(const Container &v1, Container &v2) {
if (v1.begin() != v2.begin())
std::memcpy(&v2[0], &v1[0], v1.size()*sizeof(int));
return 0;
}
```
</pre>
<img width="1px" height="1px" alt="" src="http://email.email.llvm.org/o/eJzUWVtv66gT_zTkBTUy-JqHPCTpv9JfOtKutPseYZvGVLbxGpyk59OvwPiG7aZ7Th_Oqdo68cDMMJffDECEYJeS0j3wj8B_3pBGZrzeZ6wmKZPvZBPz9H0PAqf9TaoKOM_AOQD8AvALTHJSXgA-AnyET0KmwH1O2q8ohE9_uPDpteRP9J7QSjJeCj0oZzFwn3MWm6EdR5eVSd6kFLinK00kr4H7P0PT_xvBygs88VISVtIaAvcZapkH4B66GSdWSjXPNWxZKWHCq_dzu9KClhLgKOGlkGNWOLgigE_WKwzwDoLQsILwirXQK-rZQ1hT2dQldPpXIHw2HzqrjRfxf4DDFNJ7RRMJZcYElBxeaElrIikkEAROQYukegeBA-NGQiZ7soAESl5C_goFpQUrL_k7bMqSJlQIUr_DhKd0LKzXgIiifTM3RW_B8xktmBKf4HwEyXOekLG9ofrTVgU4WJ70o2w1wx1wDxBgFwLP-X3XYEKm_UmKSj9rwRSrOmVT-huF22_Ho3PG0_dVIzI9j9ynhIJfYUfAJ_jPjdcprGQNgX9U3H0Tl8PAdHEgVNkcDcNt9sm91bcTL5p4QrD1EqQe0_EK27Q1g2C2lsY-NtuE5Ll6XjlLv9JVZlAbYOcbk9lZsO8U-EcSM8UYRY7jOMo-hvlB8TeflK-j2Vt8gjlXSGnFAElTs8ZKjYlaaud29zAdfeetIWnrYGpbpKayffGbmWRI7d9M8db6fULG1UqmIn-N4C0QauSuDV-Dgvj-CCP6bEKuzqZkDTxiK7ttOsLTNJ3RvUU0G-j-J8FpGcU0OKHgITqRNXSyffExOvUg3c3uXPNGqCaoXEVnNJ0lqZCjxc5kGmhHZ4SWVzFdNfIGSF5iZ0OoTe-QkleqjeA1TGlOJQU4UvmmY3oHPOfPb3_P8KYS6lkUjmKsn7bkRg25F4WlsdF1ccr6ElvH4hN0Pod8vRVtqFRSZj7rPJ5NPB5YLn8rJ54Nh7gksehneQFCQRQ4KPJw6EbhznHXEqparYozxOjDzUyyVU8Kfo3pAr3Xri3pO4xdN8SOG0S-F4Z-5HgrgoiV7koCGUmwccLW0Ka_EbhkvZyScYgC_-gBfFBM7ESeBWtJbwBHTak3KmmPvQvxamHMaoNkh16XV_b4XukWM-1U_IHMXZXQukFNIXc9Zc08n0ufebR1KGjg3a4kb3TiNn_WKS4ji92j2WytTnOoU52XzV5n5Mxeg6WUhqMKM0CxCUkzM5jwWWezVF_m7u07tFZq9PH6Vs2eLhef1Z66m_-wOK2B3LQ-hY8DGw9hl9yH9dtAsVDKRnK8_1aYHoXPKEoKfqVrOb_YU7RpPQoFbxYKs6ToI2qaDcFPrmo5UCdxGj5Wbp6xX6QeHisSrCeMncNjJy14qNfOZtinVPxxUqzBtK3A8iaqo1a86qWZfr17M2une4LdgPcEu1_n1UJ3z4cSubw_64vjYtvS-c0u2SYZvn57JLOa3845LS8yO9O65vXSBglHAO_M-YhW7FdQZNg6_graPNiDzZugmlUadrfftkLWy73QXO3Pq5ZkpO6OtA79jvVLOX7kgZ9VdGLK9fOulQO0R-beosHgj45WVj2RszipqvOV1jEX9ExiXsv5ek5wu91aXavxeQ8BWyIS9h1CgLGJXGzwaTx-O-9oRhPHhoY3IqC2fwlZOTuJL3hK4Y3JDBZUCHKhEPgnJRL7ovvUyV88yE4pyfN3tTaZUUhifqXwZO4CEsVcZLzJUyhrUoqcSAol10NfeZ7zmz7LHw3vl2XJHF05_PoXBOwVql012sb0wkqDDQAjfWuAx2-HGO81NL2wIivO_tExFa8VPny_oq0-xTKMDuoLf-3OqjTr_jLCKPaJW4pNunfTnbsjG7pHwQ5hhByMNtne9X3kugFCYRimNPCw5wVuSpPdLvbIaxRt2B472HUix3c838Foi1Do7PzXnRenHk53LvAcWhCWb_P8Wmx5fdkwIRq6DzzPjzY5iWku9A0UxiW9QU1U0ec_b-q9mvMUNxcBPCdnQoqBi2Qyp_u_mphXkhUk14F0oTreW39r18LBtZumzveZlJVQNteXWBcmsybeJrwA-EWxNo-nquZvNJEAv2iFBMAvWuF_AwAA__-F4D6K">