The short answer is: Because the standard says you won’t.
The C++ Standard 12.8/9 (Draft N3242) tells:
The implicitly-declared copy constructor for a class X will have the form
- X::X(const X&)
if
- each direct or virtual base class B of X has a copy constructor whose first parameter is of type const
B& or const volatile B&, and- for all the non-static data members of X that are of a class type M (or array thereof), each such class
type has a copy constructor whose first parameter is of type const M& or const volatile M&. [Note: 119]Otherwise, the implicitly-declared copy constructor will have the form
- X::X(X&)
Note 119 says:
This implies that the reference parameter of the implicitly-declared copy constructor cannot bind to a volatile lvalue;
see C.1.9.
In C.1.9 you’ll find:
The implicitly-declared copy constructor and implicitly-declared copy assignment operator cannot make a
copy of a volatile lvalue. For example, the following is valid in ISO C:
struct X { int i; };
volatile struct X x1 = {0};
struct X x2(x1); // invalid C++
struct X x3;
x3 = x1; // also invalid C++
Rationale: Several alternatives were debated at length. Changing the parameter to volatile const X& would greatly complicate the generation of efficient code for class objects. Discussion of providing two alternative signatures for these implicitly-defined operations raised unanswered concerns about creating ambiguities and complicating the rules that specify the formation of these operators according to the bases and members.