SlideShare a Scribd company logo
1 of 79
Download to read offline
The C++ Rvalue Lifetime Disaster
by Arno Schoedl
aschoedl@think-cell.com
1 / 79
Rvalue References
STL advocates value semantics
lead to frequent copying in C++03
rvalue references invented to avoid copying
replaced by more efficent moving
2 / 79
Rvalue References
STL advocates value semantics
lead to frequent copying in C++03
rvalue references invented to avoid copying
replaced by more efficent moving
std::vector< std::vector<int> > vecvec;
std::vector<int> vec={1,2,3};
vecvec.emplace_back( std::move(vec) ); // rvalue reference avoids copy
3 / 79
Rvalue References
STL advocates value semantics
lead to frequent copying in C++03
rvalue references invented to avoid copying
replaced by more efficent moving
std::vector< std::vector<int> > vecvec;
std::vector<int> vec={1,2,3};
vecvec.emplace_back( std::move(vec) ); // rvalue reference avoids copy
Increasingly used to manage lifetime
C++11 std::cref
C++20 Ranges
4 / 79
Rvalue References
STL advocates value semantics
lead to frequent copying in C++03
rvalue references invented to avoid copying
replaced by more efficent moving
std::vector< std::vector<int> > vecvec;
std::vector<int> vec={1,2,3};
vecvec.emplace_back( std::move(vec) ); // rvalue reference avoids copy
Increasingly used to manage lifetime
C++11 std::cref
C++20 Ranges
auto rng=std::vector<int>{1,2,3} | std::views::filter([](int i){ return 0==i%2
; });
// DOES NOT COMPILE
rng would contain dangling reference to std::vector<int>
So std::views::filter does not compile for rvalues 5 / 79
Rvalue References for Moving - Pitfalls
A foo() {
A const a=...;
...
return std::move(a);
};
What happens?
6 / 79
Rvalue References for Moving - Pitfalls
A foo() {
A const a=...;
...
return std::move(a);
};
What happens?
Copy - cannot move out of const
7 / 79
Rvalue References for Moving - Pitfalls
A foo() {
A const a=...;
...
return std::move(a);
};
What happens?
Copy - cannot move out of const
A foo() {
A a=...;
...
return std::move(a);
};
What happens?
8 / 79
Rvalue References for Moving - Pitfalls
A foo() {
A const a=...;
...
return std::move(a);
};
What happens?
Copy - cannot move out of const
A foo() {
A a=...;
...
return std::move(a);
};
What happens?
Move
Best we can do?
9 / 79
Rvalue References for Moving - Pitfalls
A foo() {
A a=...;
...
return a;
};
What happens?
10 / 79
Rvalue References for Moving - Pitfalls
A foo() {
A a=...;
...
return a;
};
What happens?
NRVO (Named Return Value Optimization) - copy/move elided
std::move can make things worse
11 / 79
Rvalue References for Moving - Pitfalls
A foo() {
A a=...;
...
return a;
};
What happens?
NRVO (Named Return Value Optimization) - copy/move elided
std::move can make things worse
A foo() {
A const a=...;
...
return a;
};
What happens?
12 / 79
Rvalue References for Moving - Pitfalls
A foo() {
A a=...;
...
return a;
};
What happens?
NRVO (Named Return Value Optimization) - copy/move elided
std::move can make things worse
A foo() {
A const a=...;
...
return a;
};
What happens?
Still NRVO (Named Return Value Optimization) - copy/move elided
13 / 79
Rvalue References for Moving - Pitfalls
A foo() {
if(... condition ...) {
A const a=...;
...
return a;
} else {
A const a=...;
...
return a;
}
};
What happens?
14 / 79
Rvalue References for Moving - Pitfalls
A foo() {
if(... condition ...) {
A const a=...;
...
return a;
} else {
A const a=...;
...
return a;
}
};
What happens?
No NRVO, returned object is not always same one
Copy because of const :-(
15 / 79
Rvalue References for Moving - Pitfalls
A foo() {
if(... condition ...) {
A a =...;
...
return a;
} else {
A a=...;
...
return a;
}
};
What happens?
Move
16 / 79
Rvalue References for Moving - Pitfalls
struct B {
A m_a;
};
A foo() {
B b=...;
...
return b.m_a;
};
What happens?
17 / 79
Rvalue References for Moving - Pitfalls
struct B {
A m_a;
};
A foo() {
B b=...;
...
return b.m_a;
};
What happens?
Copy
Members do not automatically become rvalues
18 / 79
Rvalue References for Moving - Pitfalls
struct B {
A m_a;
};
A foo() {
B b=...;
...
return std::move(b).m_a;
};
What happens?
19 / 79
Rvalue References for Moving - Pitfalls
struct B {
A m_a;
};
A foo() {
B b=...;
...
return std::move(b).m_a;
};
What happens?
Move
Member access of rvalue is rvalue
20 / 79
Rvalue References for Moving - Pitfalls
struct B {
A m_a;
};
A foo() {
B b=...;
...
return std::move(b).m_a;
};
What happens?
Move
Member access of rvalue is rvalue
Recommendations
Make return variables non- const
Use Clang's -Wmove
21 / 79
Temporary Lifetime Extension
struct A;
struct B {
private:
A m_a;
public:
A const& getA() const& { return m_a; }
};
B b;
auto const& a=b.getA();
22 / 79
Temporary Lifetime Extension
struct A;
struct B {
private:
A m_a;
public:
A const& getA() const& { return m_a; }
};
struct C {
A getA() const&;
};
B b;
C c;
auto const& a=< b or c >.getA();
23 / 79
Temporary Lifetime Extension
struct A;
struct B {
private:
A m_a;
public:
A const& getA() const& { return m_a; }
};
struct C {
A getA() const&;
};
B b;
C c;
auto const& a=< b or c >.getA();
auto const& a=c.getA(); works thanks to temporary lifetime extension
Idea: always write auto const& , the right thing happens
24 / 79
Temporary Lifetime Extension vs.
Rvalues
bool operator<(A const&, A const&);
struct C {
A getA() const&;
} c1, c2;
auto const& a=std::min( c1.getA(), c2.getA() );
25 / 79
Temporary Lifetime Extension vs.
Rvalues
bool operator<(A const&, A const&);
struct C {
A getA() const&;
} c1, c2;
auto const& a=std::min( c1.getA(), c2.getA() );
namespace std {
template<typename T>
T const& min( T const& lhs, T const& rhs ) {
return rhs<lhs ? rhs : lhs;
}
}
std::min forgets about rvalue-ness
a dangles
26 / 79
Temporary Lifetime Extension vs.
Rvalues
bool operator<(A const&, A const&);
struct C {
A getA() const&;
} c1, c2;
auto const& a=our::min( c1.getA(), c2.getA() );
namespace our {
template<typename Lhs, typename Rhs>
decltype(auto) min( Lhs&& lhs, Rhs&& rhs ) {
return rhs<lhs ? std::forward<Rhs>(rhs) : std::forward<Lhs>(lhs);
}
}
our::min correctly returns A&&
27 / 79
Temporary Lifetime Extension vs.
Rvalues
bool operator<(A const&, A const&);
struct C {
A getA() const&;
} c1, c2;
auto const& a=our::min( c1.getA(), c2.getA() );
namespace our {
template<typename Lhs, typename Rhs>
decltype(auto) min( Lhs&& lhs, Rhs&& rhs ) {
return rhs<lhs ? std::forward<Rhs>(rhs) : std::forward<Lhs>(lhs);
}
}
our::min correctly returns A&&
a still dangles
temporary lifetime extension does not keep rvalue references alive!
would only be possible by creating a copy
28 / 79
Temporary Lifetime Extension vs.
decltype(auto)
A some_A();
- or -
A const& some_A();
forwarding return:
decltype(auto) foo() {
return some_A();
}
29 / 79
Temporary Lifetime Extension vs.
decltype(auto)
A some_A();
- or -
A const& some_A();
forwarding return:
decltype(auto) foo() {
return some_A();
}
forwarding return with code in between:
??? foo() {
??? a = some_A();
... do something ...
return a;
}
30 / 79
Temporary Lifetime Extension vs.
decltype(auto)
decltype(auto) foo() {
auto const& a = some_A();
... do something ...
return a;
}
31 / 79
Temporary Lifetime Extension vs.
decltype(auto)
decltype(auto) foo() {
auto const& a = some_A();
... do something ...
return a;
}
creates dangling reference if some_A() returns value
32 / 79
Temporary Lifetime Extension vs.
decltype(auto)
decltype(auto) foo() {
auto const& a = some_A();
... do something ...
return a;
}
creates dangling reference if some_A() returns value
auto foo() {
auto const& a = some_A();
... do something ...
return a;
}
33 / 79
Temporary Lifetime Extension vs.
decltype(auto)
decltype(auto) foo() {
auto const& a = some_A();
... do something ...
return a;
}
creates dangling reference if some_A() returns value
auto foo() {
auto const& a = some_A();
... do something ...
return a;
}
always copies
34 / 79
Temporary Lifetime Extension vs.
decltype(auto)
decltype(auto) foo() {
auto const& a = some_A();
... do something ...
return a;
}
creates dangling reference if some_A() returns value
auto foo() {
auto const& a = some_A();
... do something ...
return a;
}
always copies
Problem: temporary lifetime extension lies about its type
if some_A() returns value, a is really value, not reference
35 / 79
auto_cref
Deprecate temporary lifetime extension
Automatically declare variable
auto if constructed from value or rvalue reference, and
auto const& if constructed from lvalue reference
36 / 79
auto_cref
Deprecate temporary lifetime extension
Automatically declare variable
auto if constructed from value or rvalue reference, and
auto const& if constructed from lvalue reference
template<typename T>
struct decay_rvalues;
template<typename T>
struct decay_rvalues<T&> {
using type=T&;
};
template<typename T>
struct decay_rvalues<T&&> {
using type=std::decay_t<T>;
};
#define auto_cref( var, ... ) 
typename decay_rvalues<decltype((__VA_ARGS__))&&>::type var = ( __VA_ARGS__
);
37 / 79
auto_cref
decltype(auto) foo() {
auto_cref( a, some_A() );
... do something with a ...
return a;
}
38 / 79
auto_cref
decltype(auto) foo() {
auto_cref( a, some_A() );
... do something with a ...
return a; // no parentheses here!
}
39 / 79
auto_cref
decltype(auto) foo() {
auto_cref( a, some_A() );
... do something with a ...
return a; // no parentheses here!
}
Make it your default auto !
does not work yet if expression contains lambda, fixed in C++20
40 / 79
auto_cref
decltype(auto) foo() {
auto_cref( a, some_A() );
... do something with a ...
return a; // no parentheses here!
}
Make it your default auto !
does not work yet if expression contains lambda, fixed in C++20
Choice: auto_cref value const ?
template<typename T>
struct decay_rvalues<T&&> {
using type=std::decay_t<T> const;
};
Then auto_cref_return for NRVO/move optimization
41 / 79
auto_cref
bool operator<(A const&, A const&);
struct C {
A getA() const&;
} c1, c2;
auto_cref( a, our::min( c1.getA(), c2.getA() ) );
namespace our {
template<typename Lhs, typename Rhs>
decltype(auto) min( Lhs&& lhs, Rhs&& rhs ) {
return rhs<lhs ? std::forward<Rhs>(rhs) : std::forward<Lhs>(lhs);
}
}
our::min correctly returns rvalue reference
auto_cref correctly turns it into value
42 / 79
C++ Rvalue Amnesia
struct A;
struct B {
A m_a;
};
auto_cref( a, B().m_a );
43 / 79
C++ Rvalue Amnesia
struct A;
struct B {
A m_a;
};
auto_cref( a, B().m_a );
Works
decltype((B().m_a)) is A&&
a is value
44 / 79
C++ Rvalue Amnesia
struct A;
struct B {
private:
A m_a;
public:
A const& getA() const {
return m_a;
}
};
auto_cref( a, B().getA() );
45 / 79
C++ Rvalue Amnesia
struct A;
struct B {
private:
A m_a;
public:
A const& getA() const {
return m_a;
}
};
auto_cref( a, B().getA() );
Does not work
decltype(B().getA()) is A const&
a is const& , dangles
46 / 79
C++ Rvalue Amnesia
struct A;
struct B {
private:
A m_a;
public:
A const& getA() const& {
return m_a;
}
};
auto_cref( a, B().getA() );
Does not work
decltype(B().getA()) is A const&
a is const& , dangles
47 / 79
C++ Rvalue Amnesia
struct A;
struct B {
private:
A m_a;
public:
A const& getA() const& {
return m_a;
}
};
auto_cref( a, B().getA() );
Does not work
decltype(B().getA()) is A const&
a is const& , dangles
Fundamental problem: const& binds anything, including rvalues
Affects any const& accessor
48 / 79
Conditional Operator Afraid Of Rvalue
Amnesia
struct A;
A const& L();
A const&& R();
What is decltype( false ? L() : L() ) ?
A const&
What is decltype( false ? R() : R() ) ?
A const&&
49 / 79
Conditional Operator Afraid Of Rvalue
Amnesia
struct A;
A const& L();
A const&& R();
What is decltype( false ? L() : L() ) ?
A const&
What is decltype( false ? R() : R() ) ?
A const&&
What is decltype( false ? R() : L() ) ?
50 / 79
Conditional Operator Afraid Of Rvalue
Amnesia
struct A;
A const& L();
A const&& R();
What is decltype( false ? L() : L() ) ?
A const&
What is decltype( false ? R() : R() ) ?
A const&&
What is decltype( false ? R() : L() ) ?
A const
C++ forces a copy
51 / 79
C++20 common_reference Not Afraid
C++20 has new trait common_reference_t
invented for C++20 Ranges
52 / 79
C++20 common_reference Not Afraid
C++20 has new trait common_reference_t
invented for C++20 Ranges
std::common_reference_t< A const&, A const& > is
A const&
std::common_reference_t< A const&&, A const&& > is
A const&&
53 / 79
C++20 common_reference Not Afraid
C++20 has new trait common_reference_t
invented for C++20 Ranges
std::common_reference_t< A const&, A const& > is
A const&
std::common_reference_t< A const&&, A const&& > is
A const&&
std::common_reference_t< A const&&, A const& > is
54 / 79
C++20 common_reference Not Afraid
C++20 has new trait common_reference_t
invented for C++20 Ranges
std::common_reference_t< A const&, A const& > is
A const&
std::common_reference_t< A const&&, A const&& > is
A const&&
std::common_reference_t< A const&&, A const& > is
A const& !
55 / 79
C++20 common_reference Not Afraid
C++20 has new trait common_reference_t
invented for C++20 Ranges
std::common_reference_t< A const&, A const& > is
A const&
std::common_reference_t< A const&&, A const&& > is
A const&&
std::common_reference_t< A const&&, A const& > is
A const& !
std::common_reference_t< A const, A const& > is
56 / 79
C++20 common_reference Not Afraid
C++20 has new trait common_reference_t
invented for C++20 Ranges
std::common_reference_t< A const&, A const& > is
A const&
std::common_reference_t< A const&&, A const&& > is
A const&&
std::common_reference_t< A const&&, A const& > is
A const& !
std::common_reference_t< A const, A const& > is
A !
57 / 79
C++20 common_reference Not Afraid
C++20 has new trait common_reference_t
invented for C++20 Ranges
std::common_reference_t< A const&, A const& > is
A const&
std::common_reference_t< A const&&, A const&& > is
A const&&
std::common_reference_t< A const&&, A const& > is
A const& !
std::common_reference_t< A const, A const& > is
A !
std::common_reference embraces rvalue amnesia
58 / 79
C++20 common_reference Not Afraid
C++20 has new trait common_reference_t
invented for C++20 Ranges
std::common_reference_t< A const&, A const& > is
A const&
std::common_reference_t< A const&&, A const&& > is
A const&&
std::common_reference_t< A const&&, A const& > is
A const& !
std::common_reference_t< A const, A const& > is
A !
std::common_reference embraces rvalue amnesia
WHAT IS CORRECT?
59 / 79
Promises of References
Lifetime short long
Mutablity
immutable const&& const&
mutable && &
60 / 79
Promises of References
Lifetime short long
Mutablity
immutable const&& const&
mutable && &
[can scavenge]
61 / 79
Promises of References
Lifetime short long
Mutablity
immutable const&& -----> const&
->
^ / ^
| -- |
/
mutable && &
[can scavenge]
Current C++ reference binding strengthens lifetime promise
62 / 79
Promises of References
Lifetime short long
Mutablity
immutable const&& <----- const&
<-
^  ^
| -- |

mutable && &
[can scavenge]
Better: Allow binding only if promises get weaker
less lifetime
less mutability
less "scavenge-ability"
only lvalues should bind to const&
anything may bind to const&&
63 / 79
UUuuuuuuuh
This is so sad.
It is very sad.
We dug ourselves a hole.
And fell into it.
UUuuuuh.
64 / 79
Any Chance to Fix C++?
Warning: These are Ideas! Has not been Implemented!
65 / 79
Any Chance to Fix C++?
Warning: These are Ideas! Has not been Implemented!
Existing code must continue to work
Existing libraries must work with new code
gradual introduction of new binding rules within one codebase
66 / 79
Any Chance to Fix C++?
Warning: These are Ideas! Has not been Implemented!
Existing code must continue to work
Existing libraries must work with new code
gradual introduction of new binding rules within one codebase
Any reference uses either new or old rules
Reference binding only at beginning of reference lifetime
Type of resulting reference unchanged
67 / 79
Any Chance to Fix C++?
Warning: These are Ideas! Has not been Implemented!
Existing code must continue to work
Existing libraries must work with new code
gradual introduction of new binding rules within one codebase
Any reference uses either new or old rules
Reference binding only at beginning of reference lifetime
Type of resulting reference unchanged
All declarations inside #new-reference-binding on/off bind along new rules
auto const& a = ... // old rules apply
#new-reference-binding on
auto const& a = ... // new rules apply
#new-reference-binding off
auto const& a = ... // old rules apply
68 / 79
Reference Declarations (1)
local/global variable initialization
auto const& a = ...
structured binding
auto const& [a,b] = ...
function/lambda parameter lists
void foo(A const& a);
69 / 79
Reference Declarations (2)
members (initialized in PODs)
struct B {
A const& m_a;
} b = { a };
members (initialized in constructors)
struct B {
A const& m_a;
B(A const& a) : m_a(a) {}
};
lambda captures
[&a = b]() { .... };
70 / 79
How to opt in to new behavior?
All declarations inside #new-reference-binding on/off bind along new rules
void A(int const& a);
#new-reference-binding on
void B(int const& a);
void C(int const&& a);
#new-reference-binding off
void B(int const& a) { // error: declared with different binding behavior
...
}
A(5); // compiles
B(5); // error: cannot bind rvalue to lvalue
C(5); // compiles
int a=1;
C(a); // compiles
71 / 79
Impact on Standard Library
Feature-test macro if #new-reference-binding is enabled
Functions can be implemented equivalently
typically replace const& parameters with const&&
<type_traits>
std::common_reference
others not affected
72 / 79
Until then... Mitigations (1)
temporary lifetime extension
replace by auto_cref
73 / 79
Until then... Mitigations (1)
temporary lifetime extension
replace by auto_cref
member accessors
delete rvalue accessors
macro?
struct B {
private:
A m_a;
public:
A const& getA() const& {
return m_a;
}
A const& getA() const&& = delete;
};
74 / 79
Until then... Mitigations (2)
common_reference
namespace our {
template<typename... Ts>
struct common_reference {
using oldtype=std::common_reference_t<Ts...>;
using type=std::conditional_t<
std::is_lvalue_reference<oldtype>::value &&
std::disjunction<std::is_rvalue_reference<Ts> ...>::value,
std::remove_reference_t<oldtype>&&,
oldtype
>;
};
}
75 / 79
Until then... Mitigations (3)
decltype( false ? R() : L() ) ?
A const
C++ forces a copy
76 / 79
Until then... Mitigations (3)
decltype( false ? R() : L() ) ?
A const
C++ forces a copy
our::common_reference allows fearless conditional (ternary) operator
#define CONDITIONAL(b, l, r) ( 
b 
? static_cast< typename our::common_reference<decltype((l)),decltype((r))
>::type >(l) 
: static_cast< typename our::common_reference<decltype((l)),decltype((r))
>::type >(r) 
)
77 / 79
Until then... Mitigations (3)
decltype( false ? R() : L() ) ?
A const
C++ forces a copy
our::common_reference allows fearless conditional (ternary) operator
#define CONDITIONAL(b, l, r) ( 
b 
? static_cast< typename our::common_reference<decltype((l)),decltype((r))
>::type >(l) 
: static_cast< typename our::common_reference<decltype((l)),decltype((r))
>::type >(r) 
)
decltype( CONDITIONAL( false, R(), L() ) ) ?
A const&&
no immediate copy
78 / 79
Summary
const& should never have bound to rvalues
Fixing C++ may be possible, but must demonstrate it
Clang implementation
large code base to try it on
Until then, consider mitigations
THANK YOU!
Arno Schoedl aschoedl@think-cell.com
79 / 79

More Related Content

What's hot

[C++] The Curiously Recurring Template Pattern: Static Polymorphsim and Expre...
[C++] The Curiously Recurring Template Pattern: Static Polymorphsim and Expre...[C++] The Curiously Recurring Template Pattern: Static Polymorphsim and Expre...
[C++] The Curiously Recurring Template Pattern: Static Polymorphsim and Expre...Francesco Casalegno
 
C++11: Feel the New Language
C++11: Feel the New LanguageC++11: Feel the New Language
C++11: Feel the New Languagemspline
 
Gentle introduction to modern C++
Gentle introduction to modern C++Gentle introduction to modern C++
Gentle introduction to modern C++Mihai Todor
 
RailswayCon 2010 - Dynamic Language VMs
RailswayCon 2010 - Dynamic Language VMsRailswayCon 2010 - Dynamic Language VMs
RailswayCon 2010 - Dynamic Language VMsLourens Naudé
 
Regular types in C++
Regular types in C++Regular types in C++
Regular types in C++Ilio Catallo
 
Understand more about C
Understand more about CUnderstand more about C
Understand more about CYi-Hsiu Hsu
 
Lego: A brick system build by scala
Lego: A brick system build by scalaLego: A brick system build by scala
Lego: A brick system build by scalalunfu zhong
 
(5) cpp dynamic memory_arrays_and_c-strings
(5) cpp dynamic memory_arrays_and_c-strings(5) cpp dynamic memory_arrays_and_c-strings
(5) cpp dynamic memory_arrays_and_c-stringsNico Ludwig
 
How to add an optimization for C# to RyuJIT
How to add an optimization for C# to RyuJITHow to add an optimization for C# to RyuJIT
How to add an optimization for C# to RyuJITEgor Bogatov
 
APassengerKnockOnDelayModelForTimetableOptimisation_beamer
APassengerKnockOnDelayModelForTimetableOptimisation_beamerAPassengerKnockOnDelayModelForTimetableOptimisation_beamer
APassengerKnockOnDelayModelForTimetableOptimisation_beamerPeter Sels
 
Функции обратного вызова в C++. Виталий Ткаченко. CoreHard Spring 2019
Функции обратного вызова в C++. Виталий Ткаченко. CoreHard Spring 2019Функции обратного вызова в C++. Виталий Ткаченко. CoreHard Spring 2019
Функции обратного вызова в C++. Виталий Ткаченко. CoreHard Spring 2019corehard_by
 
Working with Bytecode
Working with BytecodeWorking with Bytecode
Working with BytecodeMarcus Denker
 
(chapter 5) A Concise and Practical Introduction to Programming Algorithms in...
(chapter 5) A Concise and Practical Introduction to Programming Algorithms in...(chapter 5) A Concise and Practical Introduction to Programming Algorithms in...
(chapter 5) A Concise and Practical Introduction to Programming Algorithms in...Frank Nielsen
 

What's hot (20)

[C++] The Curiously Recurring Template Pattern: Static Polymorphsim and Expre...
[C++] The Curiously Recurring Template Pattern: Static Polymorphsim and Expre...[C++] The Curiously Recurring Template Pattern: Static Polymorphsim and Expre...
[C++] The Curiously Recurring Template Pattern: Static Polymorphsim and Expre...
 
Modern C++
Modern C++Modern C++
Modern C++
 
What's New in C++ 11?
What's New in C++ 11?What's New in C++ 11?
What's New in C++ 11?
 
C++11: Feel the New Language
C++11: Feel the New LanguageC++11: Feel the New Language
C++11: Feel the New Language
 
Gentle introduction to modern C++
Gentle introduction to modern C++Gentle introduction to modern C++
Gentle introduction to modern C++
 
Lambda
LambdaLambda
Lambda
 
The Style of C++ 11
The Style of C++ 11The Style of C++ 11
The Style of C++ 11
 
RailswayCon 2010 - Dynamic Language VMs
RailswayCon 2010 - Dynamic Language VMsRailswayCon 2010 - Dynamic Language VMs
RailswayCon 2010 - Dynamic Language VMs
 
Summary of C++17 features
Summary of C++17 featuresSummary of C++17 features
Summary of C++17 features
 
Regular types in C++
Regular types in C++Regular types in C++
Regular types in C++
 
Smart Pointers in C++
Smart Pointers in C++Smart Pointers in C++
Smart Pointers in C++
 
Understand more about C
Understand more about CUnderstand more about C
Understand more about C
 
Lego: A brick system build by scala
Lego: A brick system build by scalaLego: A brick system build by scala
Lego: A brick system build by scala
 
(5) cpp dynamic memory_arrays_and_c-strings
(5) cpp dynamic memory_arrays_and_c-strings(5) cpp dynamic memory_arrays_and_c-strings
(5) cpp dynamic memory_arrays_and_c-strings
 
How to add an optimization for C# to RyuJIT
How to add an optimization for C# to RyuJITHow to add an optimization for C# to RyuJIT
How to add an optimization for C# to RyuJIT
 
APassengerKnockOnDelayModelForTimetableOptimisation_beamer
APassengerKnockOnDelayModelForTimetableOptimisation_beamerAPassengerKnockOnDelayModelForTimetableOptimisation_beamer
APassengerKnockOnDelayModelForTimetableOptimisation_beamer
 
Функции обратного вызова в C++. Виталий Ткаченко. CoreHard Spring 2019
Функции обратного вызова в C++. Виталий Ткаченко. CoreHard Spring 2019Функции обратного вызова в C++. Виталий Ткаченко. CoreHard Spring 2019
Функции обратного вызова в C++. Виталий Ткаченко. CoreHard Spring 2019
 
C Programming lab
C Programming labC Programming lab
C Programming lab
 
Working with Bytecode
Working with BytecodeWorking with Bytecode
Working with Bytecode
 
(chapter 5) A Concise and Practical Introduction to Programming Algorithms in...
(chapter 5) A Concise and Practical Introduction to Programming Algorithms in...(chapter 5) A Concise and Practical Introduction to Programming Algorithms in...
(chapter 5) A Concise and Practical Introduction to Programming Algorithms in...
 

Similar to The C++ rvalue lifetime disaster. Arno Schödl ➠ CoreHard Autumn 2019

Swift 성능 이해하기
Swift 성능 이해하기Swift 성능 이해하기
Swift 성능 이해하기Hangyeol Lee
 
Whats New In C# 4 0 - NetPonto
Whats New In C# 4 0 - NetPontoWhats New In C# 4 0 - NetPonto
Whats New In C# 4 0 - NetPontoPaulo Morgado
 
07 140430-ipp-languages used in llvm during compilation
07 140430-ipp-languages used in llvm during compilation07 140430-ipp-languages used in llvm during compilation
07 140430-ipp-languages used in llvm during compilationAdam Husár
 
Unit 5 Foc
Unit 5 FocUnit 5 Foc
Unit 5 FocJAYA
 
Ti1220 Lecture 2: Names, Bindings, and Scopes
Ti1220 Lecture 2: Names, Bindings, and ScopesTi1220 Lecture 2: Names, Bindings, and Scopes
Ti1220 Lecture 2: Names, Bindings, and ScopesEelco Visser
 
Código Saudável => Programador Feliz - Rs on Rails 2010
Código Saudável => Programador Feliz - Rs on Rails 2010Código Saudável => Programador Feliz - Rs on Rails 2010
Código Saudável => Programador Feliz - Rs on Rails 2010Plataformatec
 
cppt-170218053903 (1).pptx
cppt-170218053903 (1).pptxcppt-170218053903 (1).pptx
cppt-170218053903 (1).pptxWatchDog13
 
Beginning direct3d gameprogrammingcpp02_20160324_jintaeks
Beginning direct3d gameprogrammingcpp02_20160324_jintaeksBeginning direct3d gameprogrammingcpp02_20160324_jintaeks
Beginning direct3d gameprogrammingcpp02_20160324_jintaeksJinTaek Seo
 
C Operators and Control Structures.pdf
C Operators and Control Structures.pdfC Operators and Control Structures.pdf
C Operators and Control Structures.pdfMaryJacob24
 
Continuation Passing Style and Macros in Clojure - Jan 2012
Continuation Passing Style and Macros in Clojure - Jan 2012Continuation Passing Style and Macros in Clojure - Jan 2012
Continuation Passing Style and Macros in Clojure - Jan 2012Leonardo Borges
 
C sharp part 001
C sharp part 001C sharp part 001
C sharp part 001Ralph Weber
 
C++11 - A Change in Style - v2.0
C++11 - A Change in Style - v2.0C++11 - A Change in Style - v2.0
C++11 - A Change in Style - v2.0Yaser Zhian
 
parameter passing in c#
parameter passing in c#parameter passing in c#
parameter passing in c#khush_boo31
 

Similar to The C++ rvalue lifetime disaster. Arno Schödl ➠ CoreHard Autumn 2019 (20)

C++ references
C++ referencesC++ references
C++ references
 
Swift 성능 이해하기
Swift 성능 이해하기Swift 성능 이해하기
Swift 성능 이해하기
 
Whats New In C# 4 0 - NetPonto
Whats New In C# 4 0 - NetPontoWhats New In C# 4 0 - NetPonto
Whats New In C# 4 0 - NetPonto
 
Class7
Class7Class7
Class7
 
Presentation 2
Presentation 2Presentation 2
Presentation 2
 
07 140430-ipp-languages used in llvm during compilation
07 140430-ipp-languages used in llvm during compilation07 140430-ipp-languages used in llvm during compilation
07 140430-ipp-languages used in llvm during compilation
 
Unit 5 Foc
Unit 5 FocUnit 5 Foc
Unit 5 Foc
 
Ti1220 Lecture 2: Names, Bindings, and Scopes
Ti1220 Lecture 2: Names, Bindings, and ScopesTi1220 Lecture 2: Names, Bindings, and Scopes
Ti1220 Lecture 2: Names, Bindings, and Scopes
 
Java gets a closure
Java gets a closureJava gets a closure
Java gets a closure
 
unit 1 (1).pptx
unit 1 (1).pptxunit 1 (1).pptx
unit 1 (1).pptx
 
Código Saudável => Programador Feliz - Rs on Rails 2010
Código Saudável => Programador Feliz - Rs on Rails 2010Código Saudável => Programador Feliz - Rs on Rails 2010
Código Saudável => Programador Feliz - Rs on Rails 2010
 
U4.ppt
U4.pptU4.ppt
U4.ppt
 
cppt-170218053903 (1).pptx
cppt-170218053903 (1).pptxcppt-170218053903 (1).pptx
cppt-170218053903 (1).pptx
 
Beginning direct3d gameprogrammingcpp02_20160324_jintaeks
Beginning direct3d gameprogrammingcpp02_20160324_jintaeksBeginning direct3d gameprogrammingcpp02_20160324_jintaeks
Beginning direct3d gameprogrammingcpp02_20160324_jintaeks
 
C Operators and Control Structures.pdf
C Operators and Control Structures.pdfC Operators and Control Structures.pdf
C Operators and Control Structures.pdf
 
Continuation Passing Style and Macros in Clojure - Jan 2012
Continuation Passing Style and Macros in Clojure - Jan 2012Continuation Passing Style and Macros in Clojure - Jan 2012
Continuation Passing Style and Macros in Clojure - Jan 2012
 
C sharp part 001
C sharp part 001C sharp part 001
C sharp part 001
 
C++11 move semantics
C++11 move semanticsC++11 move semantics
C++11 move semantics
 
C++11 - A Change in Style - v2.0
C++11 - A Change in Style - v2.0C++11 - A Change in Style - v2.0
C++11 - A Change in Style - v2.0
 
parameter passing in c#
parameter passing in c#parameter passing in c#
parameter passing in c#
 

More from corehard_by

C++ CoreHard Autumn 2018. Создание пакетов для открытых библиотек через conan...
C++ CoreHard Autumn 2018. Создание пакетов для открытых библиотек через conan...C++ CoreHard Autumn 2018. Создание пакетов для открытых библиотек через conan...
C++ CoreHard Autumn 2018. Создание пакетов для открытых библиотек через conan...corehard_by
 
C++ CoreHard Autumn 2018. Что должен знать каждый C++ программист или Как про...
C++ CoreHard Autumn 2018. Что должен знать каждый C++ программист или Как про...C++ CoreHard Autumn 2018. Что должен знать каждый C++ программист или Как про...
C++ CoreHard Autumn 2018. Что должен знать каждый C++ программист или Как про...corehard_by
 
C++ CoreHard Autumn 2018. Actors vs CSP vs Tasks vs ... - Евгений Охотников
C++ CoreHard Autumn 2018. Actors vs CSP vs Tasks vs ... - Евгений ОхотниковC++ CoreHard Autumn 2018. Actors vs CSP vs Tasks vs ... - Евгений Охотников
C++ CoreHard Autumn 2018. Actors vs CSP vs Tasks vs ... - Евгений Охотниковcorehard_by
 
C++ CoreHard Autumn 2018. Знай свое "железо": иерархия памяти - Александр Титов
C++ CoreHard Autumn 2018. Знай свое "железо": иерархия памяти - Александр ТитовC++ CoreHard Autumn 2018. Знай свое "железо": иерархия памяти - Александр Титов
C++ CoreHard Autumn 2018. Знай свое "железо": иерархия памяти - Александр Титовcorehard_by
 
C++ CoreHard Autumn 2018. Информационная безопасность и разработка ПО - Евген...
C++ CoreHard Autumn 2018. Информационная безопасность и разработка ПО - Евген...C++ CoreHard Autumn 2018. Информационная безопасность и разработка ПО - Евген...
C++ CoreHard Autumn 2018. Информационная безопасность и разработка ПО - Евген...corehard_by
 
C++ CoreHard Autumn 2018. Заглядываем под капот «Поясов по C++» - Илья Шишков
C++ CoreHard Autumn 2018. Заглядываем под капот «Поясов по C++» - Илья ШишковC++ CoreHard Autumn 2018. Заглядываем под капот «Поясов по C++» - Илья Шишков
C++ CoreHard Autumn 2018. Заглядываем под капот «Поясов по C++» - Илья Шишковcorehard_by
 
C++ CoreHard Autumn 2018. Ускорение сборки C++ проектов, способы и последстви...
C++ CoreHard Autumn 2018. Ускорение сборки C++ проектов, способы и последстви...C++ CoreHard Autumn 2018. Ускорение сборки C++ проектов, способы и последстви...
C++ CoreHard Autumn 2018. Ускорение сборки C++ проектов, способы и последстви...corehard_by
 
C++ CoreHard Autumn 2018. Метаклассы: воплощаем мечты в реальность - Сергей С...
C++ CoreHard Autumn 2018. Метаклассы: воплощаем мечты в реальность - Сергей С...C++ CoreHard Autumn 2018. Метаклассы: воплощаем мечты в реальность - Сергей С...
C++ CoreHard Autumn 2018. Метаклассы: воплощаем мечты в реальность - Сергей С...corehard_by
 
C++ CoreHard Autumn 2018. Что не умеет оптимизировать компилятор - Александр ...
C++ CoreHard Autumn 2018. Что не умеет оптимизировать компилятор - Александр ...C++ CoreHard Autumn 2018. Что не умеет оптимизировать компилятор - Александр ...
C++ CoreHard Autumn 2018. Что не умеет оптимизировать компилятор - Александр ...corehard_by
 
C++ CoreHard Autumn 2018. Кодогенерация C++ кроссплатформенно. Продолжение - ...
C++ CoreHard Autumn 2018. Кодогенерация C++ кроссплатформенно. Продолжение - ...C++ CoreHard Autumn 2018. Кодогенерация C++ кроссплатформенно. Продолжение - ...
C++ CoreHard Autumn 2018. Кодогенерация C++ кроссплатформенно. Продолжение - ...corehard_by
 
C++ CoreHard Autumn 2018. Concurrency and Parallelism in C++17 and C++20/23 -...
C++ CoreHard Autumn 2018. Concurrency and Parallelism in C++17 and C++20/23 -...C++ CoreHard Autumn 2018. Concurrency and Parallelism in C++17 and C++20/23 -...
C++ CoreHard Autumn 2018. Concurrency and Parallelism in C++17 and C++20/23 -...corehard_by
 
C++ CoreHard Autumn 2018. Обработка списков на C++ в функциональном стиле - В...
C++ CoreHard Autumn 2018. Обработка списков на C++ в функциональном стиле - В...C++ CoreHard Autumn 2018. Обработка списков на C++ в функциональном стиле - В...
C++ CoreHard Autumn 2018. Обработка списков на C++ в функциональном стиле - В...corehard_by
 
C++ Corehard Autumn 2018. Обучаем на Python, применяем на C++ - Павел Филонов
C++ Corehard Autumn 2018. Обучаем на Python, применяем на C++ - Павел ФилоновC++ Corehard Autumn 2018. Обучаем на Python, применяем на C++ - Павел Филонов
C++ Corehard Autumn 2018. Обучаем на Python, применяем на C++ - Павел Филоновcorehard_by
 
C++ CoreHard Autumn 2018. Asynchronous programming with ranges - Ivan Čukić
C++ CoreHard Autumn 2018. Asynchronous programming with ranges - Ivan ČukićC++ CoreHard Autumn 2018. Asynchronous programming with ranges - Ivan Čukić
C++ CoreHard Autumn 2018. Asynchronous programming with ranges - Ivan Čukićcorehard_by
 
C++ CoreHard Autumn 2018. Debug C++ Without Running - Anastasia Kazakova
C++ CoreHard Autumn 2018. Debug C++ Without Running - Anastasia KazakovaC++ CoreHard Autumn 2018. Debug C++ Without Running - Anastasia Kazakova
C++ CoreHard Autumn 2018. Debug C++ Without Running - Anastasia Kazakovacorehard_by
 
C++ CoreHard Autumn 2018. Полезный constexpr - Антон Полухин
C++ CoreHard Autumn 2018. Полезный constexpr - Антон ПолухинC++ CoreHard Autumn 2018. Полезный constexpr - Антон Полухин
C++ CoreHard Autumn 2018. Полезный constexpr - Антон Полухинcorehard_by
 
C++ CoreHard Autumn 2018. Text Formatting For a Future Range-Based Standard L...
C++ CoreHard Autumn 2018. Text Formatting For a Future Range-Based Standard L...C++ CoreHard Autumn 2018. Text Formatting For a Future Range-Based Standard L...
C++ CoreHard Autumn 2018. Text Formatting For a Future Range-Based Standard L...corehard_by
 
Исключительная модель памяти. Алексей Ткаченко ➠ CoreHard Autumn 2019
Исключительная модель памяти. Алексей Ткаченко ➠ CoreHard Autumn 2019Исключительная модель памяти. Алексей Ткаченко ➠ CoreHard Autumn 2019
Исключительная модель памяти. Алексей Ткаченко ➠ CoreHard Autumn 2019corehard_by
 
Как помочь и как помешать компилятору. Андрей Олейников ➠ CoreHard Autumn 2019
Как помочь и как помешать компилятору. Андрей Олейников ➠  CoreHard Autumn 2019Как помочь и как помешать компилятору. Андрей Олейников ➠  CoreHard Autumn 2019
Как помочь и как помешать компилятору. Андрей Олейников ➠ CoreHard Autumn 2019corehard_by
 
Автоматизируй это. Кирилл Тихонов ➠ CoreHard Autumn 2019
Автоматизируй это. Кирилл Тихонов ➠  CoreHard Autumn 2019Автоматизируй это. Кирилл Тихонов ➠  CoreHard Autumn 2019
Автоматизируй это. Кирилл Тихонов ➠ CoreHard Autumn 2019corehard_by
 

More from corehard_by (20)

C++ CoreHard Autumn 2018. Создание пакетов для открытых библиотек через conan...
C++ CoreHard Autumn 2018. Создание пакетов для открытых библиотек через conan...C++ CoreHard Autumn 2018. Создание пакетов для открытых библиотек через conan...
C++ CoreHard Autumn 2018. Создание пакетов для открытых библиотек через conan...
 
C++ CoreHard Autumn 2018. Что должен знать каждый C++ программист или Как про...
C++ CoreHard Autumn 2018. Что должен знать каждый C++ программист или Как про...C++ CoreHard Autumn 2018. Что должен знать каждый C++ программист или Как про...
C++ CoreHard Autumn 2018. Что должен знать каждый C++ программист или Как про...
 
C++ CoreHard Autumn 2018. Actors vs CSP vs Tasks vs ... - Евгений Охотников
C++ CoreHard Autumn 2018. Actors vs CSP vs Tasks vs ... - Евгений ОхотниковC++ CoreHard Autumn 2018. Actors vs CSP vs Tasks vs ... - Евгений Охотников
C++ CoreHard Autumn 2018. Actors vs CSP vs Tasks vs ... - Евгений Охотников
 
C++ CoreHard Autumn 2018. Знай свое "железо": иерархия памяти - Александр Титов
C++ CoreHard Autumn 2018. Знай свое "железо": иерархия памяти - Александр ТитовC++ CoreHard Autumn 2018. Знай свое "железо": иерархия памяти - Александр Титов
C++ CoreHard Autumn 2018. Знай свое "железо": иерархия памяти - Александр Титов
 
C++ CoreHard Autumn 2018. Информационная безопасность и разработка ПО - Евген...
C++ CoreHard Autumn 2018. Информационная безопасность и разработка ПО - Евген...C++ CoreHard Autumn 2018. Информационная безопасность и разработка ПО - Евген...
C++ CoreHard Autumn 2018. Информационная безопасность и разработка ПО - Евген...
 
C++ CoreHard Autumn 2018. Заглядываем под капот «Поясов по C++» - Илья Шишков
C++ CoreHard Autumn 2018. Заглядываем под капот «Поясов по C++» - Илья ШишковC++ CoreHard Autumn 2018. Заглядываем под капот «Поясов по C++» - Илья Шишков
C++ CoreHard Autumn 2018. Заглядываем под капот «Поясов по C++» - Илья Шишков
 
C++ CoreHard Autumn 2018. Ускорение сборки C++ проектов, способы и последстви...
C++ CoreHard Autumn 2018. Ускорение сборки C++ проектов, способы и последстви...C++ CoreHard Autumn 2018. Ускорение сборки C++ проектов, способы и последстви...
C++ CoreHard Autumn 2018. Ускорение сборки C++ проектов, способы и последстви...
 
C++ CoreHard Autumn 2018. Метаклассы: воплощаем мечты в реальность - Сергей С...
C++ CoreHard Autumn 2018. Метаклассы: воплощаем мечты в реальность - Сергей С...C++ CoreHard Autumn 2018. Метаклассы: воплощаем мечты в реальность - Сергей С...
C++ CoreHard Autumn 2018. Метаклассы: воплощаем мечты в реальность - Сергей С...
 
C++ CoreHard Autumn 2018. Что не умеет оптимизировать компилятор - Александр ...
C++ CoreHard Autumn 2018. Что не умеет оптимизировать компилятор - Александр ...C++ CoreHard Autumn 2018. Что не умеет оптимизировать компилятор - Александр ...
C++ CoreHard Autumn 2018. Что не умеет оптимизировать компилятор - Александр ...
 
C++ CoreHard Autumn 2018. Кодогенерация C++ кроссплатформенно. Продолжение - ...
C++ CoreHard Autumn 2018. Кодогенерация C++ кроссплатформенно. Продолжение - ...C++ CoreHard Autumn 2018. Кодогенерация C++ кроссплатформенно. Продолжение - ...
C++ CoreHard Autumn 2018. Кодогенерация C++ кроссплатформенно. Продолжение - ...
 
C++ CoreHard Autumn 2018. Concurrency and Parallelism in C++17 and C++20/23 -...
C++ CoreHard Autumn 2018. Concurrency and Parallelism in C++17 and C++20/23 -...C++ CoreHard Autumn 2018. Concurrency and Parallelism in C++17 and C++20/23 -...
C++ CoreHard Autumn 2018. Concurrency and Parallelism in C++17 and C++20/23 -...
 
C++ CoreHard Autumn 2018. Обработка списков на C++ в функциональном стиле - В...
C++ CoreHard Autumn 2018. Обработка списков на C++ в функциональном стиле - В...C++ CoreHard Autumn 2018. Обработка списков на C++ в функциональном стиле - В...
C++ CoreHard Autumn 2018. Обработка списков на C++ в функциональном стиле - В...
 
C++ Corehard Autumn 2018. Обучаем на Python, применяем на C++ - Павел Филонов
C++ Corehard Autumn 2018. Обучаем на Python, применяем на C++ - Павел ФилоновC++ Corehard Autumn 2018. Обучаем на Python, применяем на C++ - Павел Филонов
C++ Corehard Autumn 2018. Обучаем на Python, применяем на C++ - Павел Филонов
 
C++ CoreHard Autumn 2018. Asynchronous programming with ranges - Ivan Čukić
C++ CoreHard Autumn 2018. Asynchronous programming with ranges - Ivan ČukićC++ CoreHard Autumn 2018. Asynchronous programming with ranges - Ivan Čukić
C++ CoreHard Autumn 2018. Asynchronous programming with ranges - Ivan Čukić
 
C++ CoreHard Autumn 2018. Debug C++ Without Running - Anastasia Kazakova
C++ CoreHard Autumn 2018. Debug C++ Without Running - Anastasia KazakovaC++ CoreHard Autumn 2018. Debug C++ Without Running - Anastasia Kazakova
C++ CoreHard Autumn 2018. Debug C++ Without Running - Anastasia Kazakova
 
C++ CoreHard Autumn 2018. Полезный constexpr - Антон Полухин
C++ CoreHard Autumn 2018. Полезный constexpr - Антон ПолухинC++ CoreHard Autumn 2018. Полезный constexpr - Антон Полухин
C++ CoreHard Autumn 2018. Полезный constexpr - Антон Полухин
 
C++ CoreHard Autumn 2018. Text Formatting For a Future Range-Based Standard L...
C++ CoreHard Autumn 2018. Text Formatting For a Future Range-Based Standard L...C++ CoreHard Autumn 2018. Text Formatting For a Future Range-Based Standard L...
C++ CoreHard Autumn 2018. Text Formatting For a Future Range-Based Standard L...
 
Исключительная модель памяти. Алексей Ткаченко ➠ CoreHard Autumn 2019
Исключительная модель памяти. Алексей Ткаченко ➠ CoreHard Autumn 2019Исключительная модель памяти. Алексей Ткаченко ➠ CoreHard Autumn 2019
Исключительная модель памяти. Алексей Ткаченко ➠ CoreHard Autumn 2019
 
Как помочь и как помешать компилятору. Андрей Олейников ➠ CoreHard Autumn 2019
Как помочь и как помешать компилятору. Андрей Олейников ➠  CoreHard Autumn 2019Как помочь и как помешать компилятору. Андрей Олейников ➠  CoreHard Autumn 2019
Как помочь и как помешать компилятору. Андрей Олейников ➠ CoreHard Autumn 2019
 
Автоматизируй это. Кирилл Тихонов ➠ CoreHard Autumn 2019
Автоматизируй это. Кирилл Тихонов ➠  CoreHard Autumn 2019Автоматизируй это. Кирилл Тихонов ➠  CoreHard Autumn 2019
Автоматизируй это. Кирилл Тихонов ➠ CoreHard Autumn 2019
 

Recently uploaded

Potential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and InsightsPotential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and InsightsRavi Sanghani
 
Microsoft 365 Copilot: How to boost your productivity with AI – Part two: Dat...
Microsoft 365 Copilot: How to boost your productivity with AI – Part two: Dat...Microsoft 365 Copilot: How to boost your productivity with AI – Part two: Dat...
Microsoft 365 Copilot: How to boost your productivity with AI – Part two: Dat...Nikki Chapple
 
Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)Kaya Weers
 
JET Technology Labs White Paper for Virtualized Security and Encryption Techn...
JET Technology Labs White Paper for Virtualized Security and Encryption Techn...JET Technology Labs White Paper for Virtualized Security and Encryption Techn...
JET Technology Labs White Paper for Virtualized Security and Encryption Techn...amber724300
 
[Webinar] SpiraTest - Setting New Standards in Quality Assurance
[Webinar] SpiraTest - Setting New Standards in Quality Assurance[Webinar] SpiraTest - Setting New Standards in Quality Assurance
[Webinar] SpiraTest - Setting New Standards in Quality AssuranceInflectra
 
Abdul Kader Baba- Managing Cybersecurity Risks and Compliance Requirements i...
Abdul Kader Baba- Managing Cybersecurity Risks  and Compliance Requirements i...Abdul Kader Baba- Managing Cybersecurity Risks  and Compliance Requirements i...
Abdul Kader Baba- Managing Cybersecurity Risks and Compliance Requirements i...itnewsafrica
 
UiPath Community: Communication Mining from Zero to Hero
UiPath Community: Communication Mining from Zero to HeroUiPath Community: Communication Mining from Zero to Hero
UiPath Community: Communication Mining from Zero to HeroUiPathCommunity
 
Testing tools and AI - ideas what to try with some tool examples
Testing tools and AI - ideas what to try with some tool examplesTesting tools and AI - ideas what to try with some tool examples
Testing tools and AI - ideas what to try with some tool examplesKari Kakkonen
 
QMMS Lesson 2 - Using MS Excel Formula.pdf
QMMS Lesson 2 - Using MS Excel Formula.pdfQMMS Lesson 2 - Using MS Excel Formula.pdf
QMMS Lesson 2 - Using MS Excel Formula.pdfROWELL MARQUINA
 
Generative Artificial Intelligence: How generative AI works.pdf
Generative Artificial Intelligence: How generative AI works.pdfGenerative Artificial Intelligence: How generative AI works.pdf
Generative Artificial Intelligence: How generative AI works.pdfIngrid Airi González
 
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...Nikki Chapple
 
A Glance At The Java Performance Toolbox
A Glance At The Java Performance ToolboxA Glance At The Java Performance Toolbox
A Glance At The Java Performance ToolboxAna-Maria Mihalceanu
 
Generative AI - Gitex v1Generative AI - Gitex v1.pptx
Generative AI - Gitex v1Generative AI - Gitex v1.pptxGenerative AI - Gitex v1Generative AI - Gitex v1.pptx
Generative AI - Gitex v1Generative AI - Gitex v1.pptxfnnc6jmgwh
 
Digital Tools & AI in Career Development
Digital Tools & AI in Career DevelopmentDigital Tools & AI in Career Development
Digital Tools & AI in Career DevelopmentMahmoud Rabie
 
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...Alkin Tezuysal
 
Emixa Mendix Meetup 11 April 2024 about Mendix Native development
Emixa Mendix Meetup 11 April 2024 about Mendix Native developmentEmixa Mendix Meetup 11 April 2024 about Mendix Native development
Emixa Mendix Meetup 11 April 2024 about Mendix Native developmentPim van der Noll
 
Tampa BSides - The No BS SOC (slides from April 6, 2024 talk)
Tampa BSides - The No BS SOC (slides from April 6, 2024 talk)Tampa BSides - The No BS SOC (slides from April 6, 2024 talk)
Tampa BSides - The No BS SOC (slides from April 6, 2024 talk)Mark Simos
 
Which standard is best for your content?
Which standard is best for your content?Which standard is best for your content?
Which standard is best for your content?Rustici Software
 
QCon London: Mastering long-running processes in modern architectures
QCon London: Mastering long-running processes in modern architecturesQCon London: Mastering long-running processes in modern architectures
QCon London: Mastering long-running processes in modern architecturesBernd Ruecker
 
Kuma Meshes Part I - The basics - A tutorial
Kuma Meshes Part I - The basics - A tutorialKuma Meshes Part I - The basics - A tutorial
Kuma Meshes Part I - The basics - A tutorialJoão Esperancinha
 

Recently uploaded (20)

Potential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and InsightsPotential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and Insights
 
Microsoft 365 Copilot: How to boost your productivity with AI – Part two: Dat...
Microsoft 365 Copilot: How to boost your productivity with AI – Part two: Dat...Microsoft 365 Copilot: How to boost your productivity with AI – Part two: Dat...
Microsoft 365 Copilot: How to boost your productivity with AI – Part two: Dat...
 
Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)
 
JET Technology Labs White Paper for Virtualized Security and Encryption Techn...
JET Technology Labs White Paper for Virtualized Security and Encryption Techn...JET Technology Labs White Paper for Virtualized Security and Encryption Techn...
JET Technology Labs White Paper for Virtualized Security and Encryption Techn...
 
[Webinar] SpiraTest - Setting New Standards in Quality Assurance
[Webinar] SpiraTest - Setting New Standards in Quality Assurance[Webinar] SpiraTest - Setting New Standards in Quality Assurance
[Webinar] SpiraTest - Setting New Standards in Quality Assurance
 
Abdul Kader Baba- Managing Cybersecurity Risks and Compliance Requirements i...
Abdul Kader Baba- Managing Cybersecurity Risks  and Compliance Requirements i...Abdul Kader Baba- Managing Cybersecurity Risks  and Compliance Requirements i...
Abdul Kader Baba- Managing Cybersecurity Risks and Compliance Requirements i...
 
UiPath Community: Communication Mining from Zero to Hero
UiPath Community: Communication Mining from Zero to HeroUiPath Community: Communication Mining from Zero to Hero
UiPath Community: Communication Mining from Zero to Hero
 
Testing tools and AI - ideas what to try with some tool examples
Testing tools and AI - ideas what to try with some tool examplesTesting tools and AI - ideas what to try with some tool examples
Testing tools and AI - ideas what to try with some tool examples
 
QMMS Lesson 2 - Using MS Excel Formula.pdf
QMMS Lesson 2 - Using MS Excel Formula.pdfQMMS Lesson 2 - Using MS Excel Formula.pdf
QMMS Lesson 2 - Using MS Excel Formula.pdf
 
Generative Artificial Intelligence: How generative AI works.pdf
Generative Artificial Intelligence: How generative AI works.pdfGenerative Artificial Intelligence: How generative AI works.pdf
Generative Artificial Intelligence: How generative AI works.pdf
 
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...
 
A Glance At The Java Performance Toolbox
A Glance At The Java Performance ToolboxA Glance At The Java Performance Toolbox
A Glance At The Java Performance Toolbox
 
Generative AI - Gitex v1Generative AI - Gitex v1.pptx
Generative AI - Gitex v1Generative AI - Gitex v1.pptxGenerative AI - Gitex v1Generative AI - Gitex v1.pptx
Generative AI - Gitex v1Generative AI - Gitex v1.pptx
 
Digital Tools & AI in Career Development
Digital Tools & AI in Career DevelopmentDigital Tools & AI in Career Development
Digital Tools & AI in Career Development
 
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
 
Emixa Mendix Meetup 11 April 2024 about Mendix Native development
Emixa Mendix Meetup 11 April 2024 about Mendix Native developmentEmixa Mendix Meetup 11 April 2024 about Mendix Native development
Emixa Mendix Meetup 11 April 2024 about Mendix Native development
 
Tampa BSides - The No BS SOC (slides from April 6, 2024 talk)
Tampa BSides - The No BS SOC (slides from April 6, 2024 talk)Tampa BSides - The No BS SOC (slides from April 6, 2024 talk)
Tampa BSides - The No BS SOC (slides from April 6, 2024 talk)
 
Which standard is best for your content?
Which standard is best for your content?Which standard is best for your content?
Which standard is best for your content?
 
QCon London: Mastering long-running processes in modern architectures
QCon London: Mastering long-running processes in modern architecturesQCon London: Mastering long-running processes in modern architectures
QCon London: Mastering long-running processes in modern architectures
 
Kuma Meshes Part I - The basics - A tutorial
Kuma Meshes Part I - The basics - A tutorialKuma Meshes Part I - The basics - A tutorial
Kuma Meshes Part I - The basics - A tutorial
 

The C++ rvalue lifetime disaster. Arno Schödl ➠ CoreHard Autumn 2019

  • 1. The C++ Rvalue Lifetime Disaster by Arno Schoedl aschoedl@think-cell.com 1 / 79
  • 2. Rvalue References STL advocates value semantics lead to frequent copying in C++03 rvalue references invented to avoid copying replaced by more efficent moving 2 / 79
  • 3. Rvalue References STL advocates value semantics lead to frequent copying in C++03 rvalue references invented to avoid copying replaced by more efficent moving std::vector< std::vector<int> > vecvec; std::vector<int> vec={1,2,3}; vecvec.emplace_back( std::move(vec) ); // rvalue reference avoids copy 3 / 79
  • 4. Rvalue References STL advocates value semantics lead to frequent copying in C++03 rvalue references invented to avoid copying replaced by more efficent moving std::vector< std::vector<int> > vecvec; std::vector<int> vec={1,2,3}; vecvec.emplace_back( std::move(vec) ); // rvalue reference avoids copy Increasingly used to manage lifetime C++11 std::cref C++20 Ranges 4 / 79
  • 5. Rvalue References STL advocates value semantics lead to frequent copying in C++03 rvalue references invented to avoid copying replaced by more efficent moving std::vector< std::vector<int> > vecvec; std::vector<int> vec={1,2,3}; vecvec.emplace_back( std::move(vec) ); // rvalue reference avoids copy Increasingly used to manage lifetime C++11 std::cref C++20 Ranges auto rng=std::vector<int>{1,2,3} | std::views::filter([](int i){ return 0==i%2 ; }); // DOES NOT COMPILE rng would contain dangling reference to std::vector<int> So std::views::filter does not compile for rvalues 5 / 79
  • 6. Rvalue References for Moving - Pitfalls A foo() { A const a=...; ... return std::move(a); }; What happens? 6 / 79
  • 7. Rvalue References for Moving - Pitfalls A foo() { A const a=...; ... return std::move(a); }; What happens? Copy - cannot move out of const 7 / 79
  • 8. Rvalue References for Moving - Pitfalls A foo() { A const a=...; ... return std::move(a); }; What happens? Copy - cannot move out of const A foo() { A a=...; ... return std::move(a); }; What happens? 8 / 79
  • 9. Rvalue References for Moving - Pitfalls A foo() { A const a=...; ... return std::move(a); }; What happens? Copy - cannot move out of const A foo() { A a=...; ... return std::move(a); }; What happens? Move Best we can do? 9 / 79
  • 10. Rvalue References for Moving - Pitfalls A foo() { A a=...; ... return a; }; What happens? 10 / 79
  • 11. Rvalue References for Moving - Pitfalls A foo() { A a=...; ... return a; }; What happens? NRVO (Named Return Value Optimization) - copy/move elided std::move can make things worse 11 / 79
  • 12. Rvalue References for Moving - Pitfalls A foo() { A a=...; ... return a; }; What happens? NRVO (Named Return Value Optimization) - copy/move elided std::move can make things worse A foo() { A const a=...; ... return a; }; What happens? 12 / 79
  • 13. Rvalue References for Moving - Pitfalls A foo() { A a=...; ... return a; }; What happens? NRVO (Named Return Value Optimization) - copy/move elided std::move can make things worse A foo() { A const a=...; ... return a; }; What happens? Still NRVO (Named Return Value Optimization) - copy/move elided 13 / 79
  • 14. Rvalue References for Moving - Pitfalls A foo() { if(... condition ...) { A const a=...; ... return a; } else { A const a=...; ... return a; } }; What happens? 14 / 79
  • 15. Rvalue References for Moving - Pitfalls A foo() { if(... condition ...) { A const a=...; ... return a; } else { A const a=...; ... return a; } }; What happens? No NRVO, returned object is not always same one Copy because of const :-( 15 / 79
  • 16. Rvalue References for Moving - Pitfalls A foo() { if(... condition ...) { A a =...; ... return a; } else { A a=...; ... return a; } }; What happens? Move 16 / 79
  • 17. Rvalue References for Moving - Pitfalls struct B { A m_a; }; A foo() { B b=...; ... return b.m_a; }; What happens? 17 / 79
  • 18. Rvalue References for Moving - Pitfalls struct B { A m_a; }; A foo() { B b=...; ... return b.m_a; }; What happens? Copy Members do not automatically become rvalues 18 / 79
  • 19. Rvalue References for Moving - Pitfalls struct B { A m_a; }; A foo() { B b=...; ... return std::move(b).m_a; }; What happens? 19 / 79
  • 20. Rvalue References for Moving - Pitfalls struct B { A m_a; }; A foo() { B b=...; ... return std::move(b).m_a; }; What happens? Move Member access of rvalue is rvalue 20 / 79
  • 21. Rvalue References for Moving - Pitfalls struct B { A m_a; }; A foo() { B b=...; ... return std::move(b).m_a; }; What happens? Move Member access of rvalue is rvalue Recommendations Make return variables non- const Use Clang's -Wmove 21 / 79
  • 22. Temporary Lifetime Extension struct A; struct B { private: A m_a; public: A const& getA() const& { return m_a; } }; B b; auto const& a=b.getA(); 22 / 79
  • 23. Temporary Lifetime Extension struct A; struct B { private: A m_a; public: A const& getA() const& { return m_a; } }; struct C { A getA() const&; }; B b; C c; auto const& a=< b or c >.getA(); 23 / 79
  • 24. Temporary Lifetime Extension struct A; struct B { private: A m_a; public: A const& getA() const& { return m_a; } }; struct C { A getA() const&; }; B b; C c; auto const& a=< b or c >.getA(); auto const& a=c.getA(); works thanks to temporary lifetime extension Idea: always write auto const& , the right thing happens 24 / 79
  • 25. Temporary Lifetime Extension vs. Rvalues bool operator<(A const&, A const&); struct C { A getA() const&; } c1, c2; auto const& a=std::min( c1.getA(), c2.getA() ); 25 / 79
  • 26. Temporary Lifetime Extension vs. Rvalues bool operator<(A const&, A const&); struct C { A getA() const&; } c1, c2; auto const& a=std::min( c1.getA(), c2.getA() ); namespace std { template<typename T> T const& min( T const& lhs, T const& rhs ) { return rhs<lhs ? rhs : lhs; } } std::min forgets about rvalue-ness a dangles 26 / 79
  • 27. Temporary Lifetime Extension vs. Rvalues bool operator<(A const&, A const&); struct C { A getA() const&; } c1, c2; auto const& a=our::min( c1.getA(), c2.getA() ); namespace our { template<typename Lhs, typename Rhs> decltype(auto) min( Lhs&& lhs, Rhs&& rhs ) { return rhs<lhs ? std::forward<Rhs>(rhs) : std::forward<Lhs>(lhs); } } our::min correctly returns A&& 27 / 79
  • 28. Temporary Lifetime Extension vs. Rvalues bool operator<(A const&, A const&); struct C { A getA() const&; } c1, c2; auto const& a=our::min( c1.getA(), c2.getA() ); namespace our { template<typename Lhs, typename Rhs> decltype(auto) min( Lhs&& lhs, Rhs&& rhs ) { return rhs<lhs ? std::forward<Rhs>(rhs) : std::forward<Lhs>(lhs); } } our::min correctly returns A&& a still dangles temporary lifetime extension does not keep rvalue references alive! would only be possible by creating a copy 28 / 79
  • 29. Temporary Lifetime Extension vs. decltype(auto) A some_A(); - or - A const& some_A(); forwarding return: decltype(auto) foo() { return some_A(); } 29 / 79
  • 30. Temporary Lifetime Extension vs. decltype(auto) A some_A(); - or - A const& some_A(); forwarding return: decltype(auto) foo() { return some_A(); } forwarding return with code in between: ??? foo() { ??? a = some_A(); ... do something ... return a; } 30 / 79
  • 31. Temporary Lifetime Extension vs. decltype(auto) decltype(auto) foo() { auto const& a = some_A(); ... do something ... return a; } 31 / 79
  • 32. Temporary Lifetime Extension vs. decltype(auto) decltype(auto) foo() { auto const& a = some_A(); ... do something ... return a; } creates dangling reference if some_A() returns value 32 / 79
  • 33. Temporary Lifetime Extension vs. decltype(auto) decltype(auto) foo() { auto const& a = some_A(); ... do something ... return a; } creates dangling reference if some_A() returns value auto foo() { auto const& a = some_A(); ... do something ... return a; } 33 / 79
  • 34. Temporary Lifetime Extension vs. decltype(auto) decltype(auto) foo() { auto const& a = some_A(); ... do something ... return a; } creates dangling reference if some_A() returns value auto foo() { auto const& a = some_A(); ... do something ... return a; } always copies 34 / 79
  • 35. Temporary Lifetime Extension vs. decltype(auto) decltype(auto) foo() { auto const& a = some_A(); ... do something ... return a; } creates dangling reference if some_A() returns value auto foo() { auto const& a = some_A(); ... do something ... return a; } always copies Problem: temporary lifetime extension lies about its type if some_A() returns value, a is really value, not reference 35 / 79
  • 36. auto_cref Deprecate temporary lifetime extension Automatically declare variable auto if constructed from value or rvalue reference, and auto const& if constructed from lvalue reference 36 / 79
  • 37. auto_cref Deprecate temporary lifetime extension Automatically declare variable auto if constructed from value or rvalue reference, and auto const& if constructed from lvalue reference template<typename T> struct decay_rvalues; template<typename T> struct decay_rvalues<T&> { using type=T&; }; template<typename T> struct decay_rvalues<T&&> { using type=std::decay_t<T>; }; #define auto_cref( var, ... ) typename decay_rvalues<decltype((__VA_ARGS__))&&>::type var = ( __VA_ARGS__ ); 37 / 79
  • 38. auto_cref decltype(auto) foo() { auto_cref( a, some_A() ); ... do something with a ... return a; } 38 / 79
  • 39. auto_cref decltype(auto) foo() { auto_cref( a, some_A() ); ... do something with a ... return a; // no parentheses here! } 39 / 79
  • 40. auto_cref decltype(auto) foo() { auto_cref( a, some_A() ); ... do something with a ... return a; // no parentheses here! } Make it your default auto ! does not work yet if expression contains lambda, fixed in C++20 40 / 79
  • 41. auto_cref decltype(auto) foo() { auto_cref( a, some_A() ); ... do something with a ... return a; // no parentheses here! } Make it your default auto ! does not work yet if expression contains lambda, fixed in C++20 Choice: auto_cref value const ? template<typename T> struct decay_rvalues<T&&> { using type=std::decay_t<T> const; }; Then auto_cref_return for NRVO/move optimization 41 / 79
  • 42. auto_cref bool operator<(A const&, A const&); struct C { A getA() const&; } c1, c2; auto_cref( a, our::min( c1.getA(), c2.getA() ) ); namespace our { template<typename Lhs, typename Rhs> decltype(auto) min( Lhs&& lhs, Rhs&& rhs ) { return rhs<lhs ? std::forward<Rhs>(rhs) : std::forward<Lhs>(lhs); } } our::min correctly returns rvalue reference auto_cref correctly turns it into value 42 / 79
  • 43. C++ Rvalue Amnesia struct A; struct B { A m_a; }; auto_cref( a, B().m_a ); 43 / 79
  • 44. C++ Rvalue Amnesia struct A; struct B { A m_a; }; auto_cref( a, B().m_a ); Works decltype((B().m_a)) is A&& a is value 44 / 79
  • 45. C++ Rvalue Amnesia struct A; struct B { private: A m_a; public: A const& getA() const { return m_a; } }; auto_cref( a, B().getA() ); 45 / 79
  • 46. C++ Rvalue Amnesia struct A; struct B { private: A m_a; public: A const& getA() const { return m_a; } }; auto_cref( a, B().getA() ); Does not work decltype(B().getA()) is A const& a is const& , dangles 46 / 79
  • 47. C++ Rvalue Amnesia struct A; struct B { private: A m_a; public: A const& getA() const& { return m_a; } }; auto_cref( a, B().getA() ); Does not work decltype(B().getA()) is A const& a is const& , dangles 47 / 79
  • 48. C++ Rvalue Amnesia struct A; struct B { private: A m_a; public: A const& getA() const& { return m_a; } }; auto_cref( a, B().getA() ); Does not work decltype(B().getA()) is A const& a is const& , dangles Fundamental problem: const& binds anything, including rvalues Affects any const& accessor 48 / 79
  • 49. Conditional Operator Afraid Of Rvalue Amnesia struct A; A const& L(); A const&& R(); What is decltype( false ? L() : L() ) ? A const& What is decltype( false ? R() : R() ) ? A const&& 49 / 79
  • 50. Conditional Operator Afraid Of Rvalue Amnesia struct A; A const& L(); A const&& R(); What is decltype( false ? L() : L() ) ? A const& What is decltype( false ? R() : R() ) ? A const&& What is decltype( false ? R() : L() ) ? 50 / 79
  • 51. Conditional Operator Afraid Of Rvalue Amnesia struct A; A const& L(); A const&& R(); What is decltype( false ? L() : L() ) ? A const& What is decltype( false ? R() : R() ) ? A const&& What is decltype( false ? R() : L() ) ? A const C++ forces a copy 51 / 79
  • 52. C++20 common_reference Not Afraid C++20 has new trait common_reference_t invented for C++20 Ranges 52 / 79
  • 53. C++20 common_reference Not Afraid C++20 has new trait common_reference_t invented for C++20 Ranges std::common_reference_t< A const&, A const& > is A const& std::common_reference_t< A const&&, A const&& > is A const&& 53 / 79
  • 54. C++20 common_reference Not Afraid C++20 has new trait common_reference_t invented for C++20 Ranges std::common_reference_t< A const&, A const& > is A const& std::common_reference_t< A const&&, A const&& > is A const&& std::common_reference_t< A const&&, A const& > is 54 / 79
  • 55. C++20 common_reference Not Afraid C++20 has new trait common_reference_t invented for C++20 Ranges std::common_reference_t< A const&, A const& > is A const& std::common_reference_t< A const&&, A const&& > is A const&& std::common_reference_t< A const&&, A const& > is A const& ! 55 / 79
  • 56. C++20 common_reference Not Afraid C++20 has new trait common_reference_t invented for C++20 Ranges std::common_reference_t< A const&, A const& > is A const& std::common_reference_t< A const&&, A const&& > is A const&& std::common_reference_t< A const&&, A const& > is A const& ! std::common_reference_t< A const, A const& > is 56 / 79
  • 57. C++20 common_reference Not Afraid C++20 has new trait common_reference_t invented for C++20 Ranges std::common_reference_t< A const&, A const& > is A const& std::common_reference_t< A const&&, A const&& > is A const&& std::common_reference_t< A const&&, A const& > is A const& ! std::common_reference_t< A const, A const& > is A ! 57 / 79
  • 58. C++20 common_reference Not Afraid C++20 has new trait common_reference_t invented for C++20 Ranges std::common_reference_t< A const&, A const& > is A const& std::common_reference_t< A const&&, A const&& > is A const&& std::common_reference_t< A const&&, A const& > is A const& ! std::common_reference_t< A const, A const& > is A ! std::common_reference embraces rvalue amnesia 58 / 79
  • 59. C++20 common_reference Not Afraid C++20 has new trait common_reference_t invented for C++20 Ranges std::common_reference_t< A const&, A const& > is A const& std::common_reference_t< A const&&, A const&& > is A const&& std::common_reference_t< A const&&, A const& > is A const& ! std::common_reference_t< A const, A const& > is A ! std::common_reference embraces rvalue amnesia WHAT IS CORRECT? 59 / 79
  • 60. Promises of References Lifetime short long Mutablity immutable const&& const& mutable && & 60 / 79
  • 61. Promises of References Lifetime short long Mutablity immutable const&& const& mutable && & [can scavenge] 61 / 79
  • 62. Promises of References Lifetime short long Mutablity immutable const&& -----> const& -> ^ / ^ | -- | / mutable && & [can scavenge] Current C++ reference binding strengthens lifetime promise 62 / 79
  • 63. Promises of References Lifetime short long Mutablity immutable const&& <----- const& <- ^ ^ | -- | mutable && & [can scavenge] Better: Allow binding only if promises get weaker less lifetime less mutability less "scavenge-ability" only lvalues should bind to const& anything may bind to const&& 63 / 79
  • 64. UUuuuuuuuh This is so sad. It is very sad. We dug ourselves a hole. And fell into it. UUuuuuh. 64 / 79
  • 65. Any Chance to Fix C++? Warning: These are Ideas! Has not been Implemented! 65 / 79
  • 66. Any Chance to Fix C++? Warning: These are Ideas! Has not been Implemented! Existing code must continue to work Existing libraries must work with new code gradual introduction of new binding rules within one codebase 66 / 79
  • 67. Any Chance to Fix C++? Warning: These are Ideas! Has not been Implemented! Existing code must continue to work Existing libraries must work with new code gradual introduction of new binding rules within one codebase Any reference uses either new or old rules Reference binding only at beginning of reference lifetime Type of resulting reference unchanged 67 / 79
  • 68. Any Chance to Fix C++? Warning: These are Ideas! Has not been Implemented! Existing code must continue to work Existing libraries must work with new code gradual introduction of new binding rules within one codebase Any reference uses either new or old rules Reference binding only at beginning of reference lifetime Type of resulting reference unchanged All declarations inside #new-reference-binding on/off bind along new rules auto const& a = ... // old rules apply #new-reference-binding on auto const& a = ... // new rules apply #new-reference-binding off auto const& a = ... // old rules apply 68 / 79
  • 69. Reference Declarations (1) local/global variable initialization auto const& a = ... structured binding auto const& [a,b] = ... function/lambda parameter lists void foo(A const& a); 69 / 79
  • 70. Reference Declarations (2) members (initialized in PODs) struct B { A const& m_a; } b = { a }; members (initialized in constructors) struct B { A const& m_a; B(A const& a) : m_a(a) {} }; lambda captures [&a = b]() { .... }; 70 / 79
  • 71. How to opt in to new behavior? All declarations inside #new-reference-binding on/off bind along new rules void A(int const& a); #new-reference-binding on void B(int const& a); void C(int const&& a); #new-reference-binding off void B(int const& a) { // error: declared with different binding behavior ... } A(5); // compiles B(5); // error: cannot bind rvalue to lvalue C(5); // compiles int a=1; C(a); // compiles 71 / 79
  • 72. Impact on Standard Library Feature-test macro if #new-reference-binding is enabled Functions can be implemented equivalently typically replace const& parameters with const&& <type_traits> std::common_reference others not affected 72 / 79
  • 73. Until then... Mitigations (1) temporary lifetime extension replace by auto_cref 73 / 79
  • 74. Until then... Mitigations (1) temporary lifetime extension replace by auto_cref member accessors delete rvalue accessors macro? struct B { private: A m_a; public: A const& getA() const& { return m_a; } A const& getA() const&& = delete; }; 74 / 79
  • 75. Until then... Mitigations (2) common_reference namespace our { template<typename... Ts> struct common_reference { using oldtype=std::common_reference_t<Ts...>; using type=std::conditional_t< std::is_lvalue_reference<oldtype>::value && std::disjunction<std::is_rvalue_reference<Ts> ...>::value, std::remove_reference_t<oldtype>&&, oldtype >; }; } 75 / 79
  • 76. Until then... Mitigations (3) decltype( false ? R() : L() ) ? A const C++ forces a copy 76 / 79
  • 77. Until then... Mitigations (3) decltype( false ? R() : L() ) ? A const C++ forces a copy our::common_reference allows fearless conditional (ternary) operator #define CONDITIONAL(b, l, r) ( b ? static_cast< typename our::common_reference<decltype((l)),decltype((r)) >::type >(l) : static_cast< typename our::common_reference<decltype((l)),decltype((r)) >::type >(r) ) 77 / 79
  • 78. Until then... Mitigations (3) decltype( false ? R() : L() ) ? A const C++ forces a copy our::common_reference allows fearless conditional (ternary) operator #define CONDITIONAL(b, l, r) ( b ? static_cast< typename our::common_reference<decltype((l)),decltype((r)) >::type >(l) : static_cast< typename our::common_reference<decltype((l)),decltype((r)) >::type >(r) ) decltype( CONDITIONAL( false, R(), L() ) ) ? A const&& no immediate copy 78 / 79
  • 79. Summary const& should never have bound to rvalues Fixing C++ may be possible, but must demonstrate it Clang implementation large code base to try it on Until then, consider mitigations THANK YOU! Arno Schoedl aschoedl@think-cell.com 79 / 79