semantics.c (finish_decltype_type): Handle calls to function pointers and references to functions properly.
2008-08-07 Douglas Gregor <doug.gregor@gmail.com> * semantics.c (finish_decltype_type): Handle calls to function pointers and references to functions properly. 2008-08-07 Douglas Gregor <doug.gregor@gmail.com> * g++.dg/cpp0x/decltype12.C: New. From-SVN: r138843
This commit is contained in:
parent
e297d9fe0d
commit
ed85a1f60b
4 changed files with 66 additions and 7 deletions
|
@ -1,3 +1,8 @@
|
|||
2008-08-07 Douglas Gregor <doug.gregor@gmail.com>
|
||||
|
||||
* semantics.c (finish_decltype_type): Handle calls to function
|
||||
pointers and references to functions properly.
|
||||
|
||||
2008-08-06 Douglas Gregor <doug.gregor@gmail.com>
|
||||
|
||||
PR c++/36460
|
||||
|
|
|
@ -4586,8 +4586,6 @@ finish_decltype_type (tree expr, bool id_expression_or_member_access_p)
|
|||
}
|
||||
else
|
||||
{
|
||||
tree fndecl;
|
||||
|
||||
/* Expressions of reference type are sometimes wrapped in
|
||||
INDIRECT_REFs. INDIRECT_REFs are just internal compiler
|
||||
representation, not part of the language, so we have to look
|
||||
|
@ -4597,14 +4595,28 @@ finish_decltype_type (tree expr, bool id_expression_or_member_access_p)
|
|||
== REFERENCE_TYPE)
|
||||
expr = TREE_OPERAND (expr, 0);
|
||||
|
||||
if (TREE_CODE (expr) == CALL_EXPR
|
||||
&& (fndecl = get_callee_fndecl (expr))
|
||||
&& (fndecl != error_mark_node))
|
||||
/* If e is a function call (5.2.2 [expr.call]) or an
|
||||
if (TREE_CODE (expr) == CALL_EXPR)
|
||||
{
|
||||
/* If e is a function call (5.2.2 [expr.call]) or an
|
||||
invocation of an overloaded operator (parentheses around e
|
||||
are ignored), decltype(e) is defined as the return type of
|
||||
that function. */
|
||||
type = TREE_TYPE (TREE_TYPE (fndecl));
|
||||
tree fndecl = get_callee_fndecl (expr);
|
||||
if (fndecl && fndecl != error_mark_node)
|
||||
type = TREE_TYPE (TREE_TYPE (fndecl));
|
||||
else
|
||||
{
|
||||
tree target_type = TREE_TYPE (CALL_EXPR_FN (expr));
|
||||
if ((TREE_CODE (target_type) == REFERENCE_TYPE
|
||||
|| TREE_CODE (target_type) == POINTER_TYPE)
|
||||
&& (TREE_CODE (TREE_TYPE (target_type)) == FUNCTION_TYPE
|
||||
|| TREE_CODE (TREE_TYPE (target_type)) == METHOD_TYPE))
|
||||
type = TREE_TYPE (TREE_TYPE (target_type));
|
||||
else
|
||||
sorry ("unable to determine the declared type of expression %<%E%>",
|
||||
expr);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
type = is_bitfield_expr_with_lowered_type (expr);
|
||||
|
|
|
@ -1,3 +1,7 @@
|
|||
2008-08-07 Douglas Gregor <doug.gregor@gmail.com>
|
||||
|
||||
* g++.dg/cpp0x/decltype12.C: New.
|
||||
|
||||
2008-08-07 H.J. Lu <hongjiu.lu@intel.com>
|
||||
|
||||
PR target/36992
|
||||
|
|
38
gcc/testsuite/g++.dg/cpp0x/decltype12.C
Normal file
38
gcc/testsuite/g++.dg/cpp0x/decltype12.C
Normal file
|
@ -0,0 +1,38 @@
|
|||
// { dg-do compile }
|
||||
// { dg-options "-std=c++0x" }
|
||||
template<typename T, typename U>
|
||||
struct is_same
|
||||
{
|
||||
static const bool value = false;
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
struct is_same<T, T>
|
||||
{
|
||||
static const bool value = true;
|
||||
};
|
||||
|
||||
int&& f(const int&) {}
|
||||
int&& (*fp)(const int&) = f;
|
||||
int&& (&fr)(const int&) = f;
|
||||
|
||||
struct X { int&& f(const int&); };
|
||||
|
||||
int&& (X::*mfp)(const int&) = &X::f;
|
||||
|
||||
void g(X& xr, X* xp)
|
||||
{
|
||||
int i;
|
||||
static_assert(is_same<decltype(f(i)), int&&>::value, "direct call");
|
||||
static_assert(is_same<decltype(fp(i)), int&&>::value, "pointer");
|
||||
static_assert(is_same<decltype((*fp)(i)), int&&>::value,
|
||||
"dereferenced pointer");
|
||||
static_assert(is_same<decltype(fr(i)), int&&>::value,
|
||||
"reference");
|
||||
static_assert(is_same<decltype(xr.f(i)), int&&>::value,
|
||||
"member function call");
|
||||
static_assert(is_same<decltype((xr.*mfp)(i)), int&&>::value,
|
||||
"member function pointer with .*");
|
||||
static_assert(is_same<decltype((xp->*mfp)(i)), int&&>::value,
|
||||
"member function pointer with ->*");
|
||||
}
|
Loading…
Add table
Reference in a new issue