Browse Source
2010-05-07 Sami Wagiaalla <swagiaal@redhat.com> PR C++/7943: * valops.c (find_overload_match): Handle fsym == NULL case. Add int no_adl argument. (find_oload_champ_namespace_loop): Call make_symbol_overload_list_adl when appropriate. Add int no_adl argument. (find_oload_champ_namespace): Add int no_adl argument. * parse.c (operator_length_standard): Return length for OP_ADL_FUNC expression. * expprint.c (op_name_standard): Added string for OP_ADL_FUNC case. * eval.c (evaluate_subexp_standard): Added OP_ADL_FUNC case. Evaluate arguments and use them to perform ADL lookup. Pass no_adl argument to find_overload_match. Disable adl lookup when evaluating a fully qualified OP_FUNCALL. * cp-support.h: Added prototype for make_symbol_overload_list_namespace. * cp-support.c (make_symbol_overload_list_namespace): New function. (make_symbol_overload_list_adl_namespace): New function. (make_symbol_overload_list_adl): New function. (make_symbol_overload_list_using): Moved code to add function to overload set to make_symbol_overload_list_namespace. * c-exp.y: create UNKNOWN_CPP_NAME token. Add parse rule for ADL functions. (classify_name): Recognize an UNKNOWN_CPP_NAME. 2010-05-07 Sami Wagiaalla <swagiaal@redhat.com> * gdb.cp/koenig.exp: New test. * gdb.cp/koenig.cc: New test program.gdb_7_2-branch
13 changed files with 632 additions and 51 deletions
@ -0,0 +1,245 @@ |
|||
namespace A |
|||
{ |
|||
class C |
|||
{ |
|||
public: |
|||
static const int x = 11; |
|||
}; |
|||
|
|||
int |
|||
first (C c) |
|||
{ |
|||
return 11; |
|||
} |
|||
|
|||
int |
|||
first (int a, C c) |
|||
{ |
|||
return 22; |
|||
} |
|||
|
|||
int |
|||
second (int a, int b, C cc, int c, int d) |
|||
{ |
|||
return 33; |
|||
} |
|||
|
|||
} |
|||
|
|||
struct B |
|||
{ |
|||
A::C c; |
|||
}; |
|||
|
|||
//------------
|
|||
|
|||
namespace E |
|||
{ |
|||
class O{}; |
|||
int foo (O o){return 1; } |
|||
int foo (O o, O o2){return 2; } |
|||
int foo (O o, O o2, int i){return 3; } |
|||
} |
|||
|
|||
namespace F |
|||
{ |
|||
class O{}; |
|||
int foo ( O fo, ::E::O eo){ return 4;} |
|||
int foo (int i, O fo, ::E::O eo){ return 5;} |
|||
} |
|||
|
|||
namespace G |
|||
{ |
|||
class O{}; |
|||
int foo (O go, ::F::O fo, ::E::O eo){ return 6; } |
|||
} |
|||
|
|||
//------------
|
|||
|
|||
namespace H |
|||
{ |
|||
class O{}; |
|||
int foo (O){ return 7;} |
|||
} |
|||
|
|||
namespace I |
|||
{ |
|||
class O: public H::O {}; |
|||
class X: H::O{}; |
|||
} |
|||
|
|||
//------------
|
|||
|
|||
namespace J |
|||
{ |
|||
union U{}; |
|||
struct S{}; |
|||
enum E{}; |
|||
|
|||
class A{ |
|||
public: |
|||
class B{}; |
|||
}; |
|||
|
|||
class C{}; |
|||
|
|||
int foo (U){ return 8;} |
|||
int foo (S){ return 9;} |
|||
int foo (E){ return 10;} |
|||
int foo (A::B){ return 11;} |
|||
int foo (A*){ return 12;} |
|||
int foo (A**){ return 13;} |
|||
int foo (C[]){ return 14;} |
|||
|
|||
} |
|||
//------------
|
|||
|
|||
namespace K{ |
|||
class O{}; |
|||
|
|||
int foo(O, int){ |
|||
return 15; |
|||
} |
|||
|
|||
int bar(O, int){ |
|||
return 15; |
|||
} |
|||
} |
|||
|
|||
int foo(K::O, float){ |
|||
return 16; |
|||
} |
|||
|
|||
int bar(K::O, int){ |
|||
return 16; |
|||
} |
|||
//------------
|
|||
|
|||
namespace L { |
|||
namespace A{ |
|||
namespace B{ |
|||
class O {}; |
|||
|
|||
int foo (O){ |
|||
return 17; |
|||
} |
|||
|
|||
} |
|||
} |
|||
} |
|||
|
|||
//------------
|
|||
|
|||
namespace M { |
|||
class A{ |
|||
public: |
|||
int foo(char) { |
|||
return 18; |
|||
} |
|||
}; |
|||
|
|||
int foo(A,char){ |
|||
return 19; |
|||
} |
|||
|
|||
int foo(A *,char){ |
|||
return 23; |
|||
} |
|||
|
|||
int bar(char){ |
|||
return 21; |
|||
} |
|||
|
|||
namespace N { |
|||
int foo(::M::A,int){ |
|||
return 20; |
|||
} |
|||
|
|||
int bar(int){ |
|||
return 22; |
|||
} |
|||
} |
|||
} |
|||
//------------
|
|||
|
|||
namespace O { |
|||
class A{}; |
|||
|
|||
int foo(A,int){ |
|||
return 23; |
|||
} |
|||
|
|||
} |
|||
|
|||
typedef O::A TOA; |
|||
typedef TOA TTOA; |
|||
|
|||
//------------
|
|||
int |
|||
main () |
|||
{ |
|||
A::C c; |
|||
B b; |
|||
|
|||
A::first (c); |
|||
first (0, c); |
|||
second (0, 0, c, 0, 0); |
|||
A::first (b.c); |
|||
|
|||
E::O eo; |
|||
F::O fo; |
|||
G::O go; |
|||
|
|||
foo (eo); |
|||
foo (eo, eo); |
|||
foo (eo, eo, 1); |
|||
foo (fo, eo); |
|||
foo (1 ,fo, eo); |
|||
foo (go, fo, eo); |
|||
|
|||
I::O io; |
|||
I::X ix; |
|||
|
|||
foo (io); |
|||
//foo (ix);
|
|||
|
|||
J::U ju; |
|||
J::S js; |
|||
J::E je; |
|||
J::A::B jab; |
|||
J::A *jap; |
|||
J::A **japp; |
|||
J::C jca[3]; |
|||
|
|||
foo (ju); |
|||
foo (js); |
|||
foo (je); |
|||
foo (jab); |
|||
foo (jap); |
|||
foo (japp); |
|||
foo (jca); |
|||
|
|||
K::O ko; |
|||
foo (ko, 1); |
|||
foo (ko, 1.0f); |
|||
//bar(ko,1);
|
|||
|
|||
L::A::B::O labo; |
|||
foo (labo); |
|||
|
|||
M::A ma; |
|||
foo(ma,'a'); |
|||
ma.foo('a'); |
|||
M::N::foo(ma,'a'); |
|||
|
|||
M::bar('a'); |
|||
M::N::bar('a'); |
|||
|
|||
TTOA ttoa; |
|||
foo (ttoa, 'a'); |
|||
|
|||
return first (0, c) + foo (eo) + |
|||
foo (eo, eo) + foo (eo, eo, 1) + |
|||
foo (fo, eo) + foo (1 ,fo, eo) + |
|||
foo (go, fo, eo); |
|||
} |
|||
@ -0,0 +1,109 @@ |
|||
# Copyright 2008 Free Software Foundation, Inc. |
|||
|
|||
# This program is free software; you can redistribute it and/or modify |
|||
# it under the terms of the GNU General Public License as published by |
|||
# the Free Software Foundation; either version 3 of the License, or |
|||
# (at your option) any later version. |
|||
# |
|||
# This program is distributed in the hope that it will be useful, |
|||
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
|||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
|||
# GNU General Public License for more details. |
|||
# |
|||
# You should have received a copy of the GNU General Public License |
|||
# along with this program. If not, see <http://www.gnu.org/licenses/>. |
|||
|
|||
if $tracelevel then { |
|||
strace $tracelevel |
|||
} |
|||
|
|||
set prms_id 0 |
|||
set bug_id 0 |
|||
|
|||
set testfile koenig |
|||
set srcfile ${testfile}.cc |
|||
set binfile ${objdir}/${subdir}/${testfile} |
|||
if { [gdb_compile "${srcdir}/${subdir}/${srcfile}" "${binfile}" executable {debug c++}] != "" } { |
|||
untested "Couldn't compile test program" |
|||
return -1 |
|||
} |
|||
|
|||
# Get things started. |
|||
|
|||
gdb_exit |
|||
gdb_start |
|||
gdb_reinitialize_dir $srcdir/$subdir |
|||
gdb_load ${binfile} |
|||
|
|||
############################################ |
|||
|
|||
if ![runto_main] then { |
|||
perror "couldn't run to breakpoint main" |
|||
continue |
|||
} |
|||
|
|||
# Test that koenig lookup finds correct function |
|||
gdb_test "p first(c)" "= 11" |
|||
|
|||
# Change the number of parameters and position of |
|||
# the qualifying parameter |
|||
gdb_test "p second(0,0,c,0,0)" "= 33" |
|||
|
|||
# Test that koenig lookup finds correct function |
|||
# even if it is overloaded |
|||
gdb_test "p first(0,c)" "= 22" |
|||
|
|||
# Test that koenig lookup finds correct function |
|||
# when the argument is an expression |
|||
gdb_test "p first(b.c)" "= 11" |
|||
|
|||
# test that resolutions can be made across namespaces |
|||
gdb_test "p foo(eo)" "= 1" |
|||
gdb_test "p foo(eo, eo)" "= 2" |
|||
gdb_test "p foo(eo, eo, 1)" "= 3" |
|||
gdb_test "p foo(fo, eo)" "= 4" |
|||
gdb_test "p foo(1 ,fo, eo)" "= 5" |
|||
gdb_test "p foo(go, fo, eo)" "= 6" |
|||
|
|||
#test that gdb fails gracefully |
|||
gdb_test "p fake(eo)" "No symbol \"fake\" in current context." |
|||
|
|||
#test that namespaces of base classes are searched |
|||
gdb_test "p foo(io)" "= 7" |
|||
gdb_test "p foo(ix)" "Cannot resolve function foo to any overloaded instance" |
|||
|
|||
#test for other types |
|||
gdb_test "p foo(ju)" "= 8" |
|||
gdb_test "p foo(js)" "= 9" |
|||
gdb_test "p foo(je)" "= 10" |
|||
|
|||
#test for class members |
|||
setup_xfail "*-*-*" |
|||
gdb_test "p foo(jab)" "= 11" |
|||
|
|||
gdb_test "p foo(jap)" "= 12" |
|||
gdb_test "p foo(japp)" "= 13" |
|||
gdb_test "p foo(jca)" "= 14" |
|||
|
|||
#test overload resolution |
|||
gdb_test "p foo(ko,1)" "= 15" |
|||
gdb_test "p foo(ko,1.0f)" "= 16" |
|||
setup_xfail "*-*-*" |
|||
gdb_test "p bar(ko,1)" "= -1" |
|||
|
|||
#test lookup of objects belonging to nested namespaces |
|||
gdb_test "p foo(labo)" "= 17" |
|||
|
|||
#test koenig found function do not compete with qualified |
|||
#names |
|||
gdb_test "p ma.foo('a')" "= 18" |
|||
gdb_test "p foo(ma,'a')" "= 19" |
|||
gdb_test "p M::N::foo(ma,'a')" "= 20" |
|||
gdb_test "p M::FAKE::foo(ma,'a')" "No type \"FAKE\" within class or namespace \"M\"." |
|||
gdb_test "p M::N::fake(ma,'a')" "No symbol \"fake\" in namespace \"M::N\"." |
|||
|
|||
gdb_test "p M::bar('a')" "= 21" |
|||
gdb_test "p M::N::bar('a')" "= 22" |
|||
|
|||
#test that lookup supports typedef |
|||
gdb_test "p foo(ttoa, 'a')" "= 23" |
|||
Loading…
Reference in new issue