Because return of certain expressions, such as local automatic variables, are explicitly defined to return a moved object, if the moving operator is available.
So:
return p;
is more or less similar to:
return std::move(p);
But note that this will not work for example with a global variable.
std::unique_ptr g(new int(3));
std::unique_ptr ptr() {
return g; // error!!!
}