Skip to content

Commit c84bf47

Browse files
committed
Improve deduction for dependent/pointer in parameters, see #369 comment thread
1. For a constructor parameter when `T` is a template parameter on the class, pass `T const&` for CTAD deduction. We do that already for all functions when `T` is a template parameter on the function, for general deduction. 2. For a parameter `* <anything>`, pass `<anything> *` by value (not `in<>`). We know it's a pointer, and should be passed by value.
1 parent e0125d7 commit c84bf47

File tree

8 files changed

+131
-99
lines changed

8 files changed

+131
-99
lines changed

regression-tests/test-results/mixed-lifetime-safety-and-null-contracts.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ auto try_pointer_stuff() -> void;
2626

2727

2828
#line 21 "mixed-lifetime-safety-and-null-contracts.cpp2"
29-
auto call_my_framework(cpp2::in<char const*> msg) -> void;
29+
auto call_my_framework(char const* msg) -> void;
3030

3131

3232
//=== Cpp2 function definitions =================================================
@@ -46,7 +46,7 @@ auto try_pointer_stuff() -> void{
4646
// to show -n
4747
}
4848

49-
auto call_my_framework(cpp2::in<char const*> msg) -> void{
49+
auto call_my_framework(char const* msg) -> void{
5050
std::cout
5151
<< "sending error to my framework... ["
5252
<< msg << "]\n";

regression-tests/test-results/pure2-types-order-independence-and-nesting.cpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -65,9 +65,9 @@ class X {
6565
class Y {
6666
private: X* px;
6767

68-
public: explicit Y(cpp2::in<X*> x);
68+
public: explicit Y(X* x);
6969
#line 49 "pure2-types-order-independence-and-nesting.cpp2"
70-
public: auto operator=(cpp2::in<X*> x) -> Y& ;
70+
public: auto operator=(X* x) -> Y& ;
7171

7272
public: auto why(cpp2::in<int> count) const -> void;
7373

@@ -160,12 +160,12 @@ namespace N {
160160
}
161161

162162
#line 49 "pure2-types-order-independence-and-nesting.cpp2"
163-
Y::Y(cpp2::in<X*> x)
163+
Y::Y(X* x)
164164
: px{ x }
165165
#line 49 "pure2-types-order-independence-and-nesting.cpp2"
166166
{ }
167167
#line 49 "pure2-types-order-independence-and-nesting.cpp2"
168-
auto Y::operator=(cpp2::in<X*> x) -> Y& {
168+
auto Y::operator=(X* x) -> Y& {
169169
px = x;
170170
return *this;
171171
#line 49 "pure2-types-order-independence-and-nesting.cpp2"

regression-tests/test-results/version

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11

2-
cppfront compiler v0.2.1 Build 8521:0840
2+
cppfront compiler v0.2.1 Build 8521:1217
33
Copyright(c) Herb Sutter All rights reserved
44

55
SPDX-License-Identifier: CC-BY-NC-ND-4.0

source/build.info

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
"8521:0840"
1+
"8521:1217"

source/cppfront.cpp

Lines changed: 48 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -3852,36 +3852,50 @@ class cppfront
38523852

38533853
auto param_type = print_to_string(type_id);
38543854

3855-
// If there are template parameters, see if this parameter's name is an
3856-
// unqualified-id with a template parameter name, or mentions a template
3857-
// parameter as a template argument
3858-
auto is_dependent_parameter_type = false;
3859-
if (
3860-
current_declarations.back()
3861-
&& current_declarations.back()->template_parameters
3855+
// If there are template parameters on this function or its enclosing
3856+
// type, see if this parameter's name is an unqualified-id with a
3857+
// template parameter name, or mentions a template parameter as a
3858+
// template argument
3859+
auto has_template_parameter_type_named = [](
3860+
declaration_node const& decl,
3861+
std::string_view name
38623862
)
3863+
-> bool
38633864
{
3864-
for (auto& tparam : current_declarations.back()->template_parameters->parameters)
3865-
{
3866-
assert(
3867-
tparam
3868-
&& tparam->name()
3869-
);
3870-
// For now just do a quick string match
3871-
auto tparam_name = tparam->name()->to_string(true);
3872-
if (
3873-
tparam->declaration->is_type()
3874-
&& (
3875-
param_type == tparam_name
3876-
|| std::string_view{param_type}.find("<"+tparam_name) != std::string_view::npos
3877-
|| std::string_view{param_type}.find(","+tparam_name) != std::string_view::npos
3878-
)
3879-
)
3865+
if (decl.template_parameters) {
3866+
for (auto& tparam : decl.template_parameters->parameters)
38803867
{
3881-
is_dependent_parameter_type = true;
3868+
assert(
3869+
tparam
3870+
&& tparam->name()
3871+
);
3872+
// For now just do a quick string match
3873+
auto tparam_name = tparam->name()->to_string(true);
3874+
if (
3875+
tparam->declaration->is_type()
3876+
&& (
3877+
name == tparam_name
3878+
|| name.find("<"+tparam_name) != std::string_view::npos
3879+
|| name.find(","+tparam_name) != std::string_view::npos
3880+
)
3881+
)
3882+
{
3883+
return true;
3884+
}
38823885
}
38833886
}
3884-
}
3887+
return false;
3888+
};
3889+
3890+
assert( current_declarations.back() );
3891+
auto is_dependent_parameter_type =
3892+
has_template_parameter_type_named( *current_declarations.back(), param_type )
3893+
|| (
3894+
current_declarations.back()->parent_is_type()
3895+
&& current_declarations.back()->has_name("operator=")
3896+
&& has_template_parameter_type_named( *current_declarations.back()->get_parent(), param_type)
3897+
)
3898+
;
38853899

38863900
assert( n.declaration->identifier );
38873901
auto identifier = print_to_string( *n.declaration->identifier );
@@ -3891,6 +3905,7 @@ class cppfront
38913905
!is_returns
38923906
&& !type_id.is_wildcard()
38933907
&& !is_dependent_parameter_type
3908+
&& !type_id.is_pointer_qualified()
38943909
)
38953910
{
38963911
switch (n.pass) {
@@ -3903,6 +3918,13 @@ class cppfront
39033918
printer.preempt_position_push( n.position() );
39043919

39053920
if (
3921+
type_id.is_pointer_qualified()
3922+
&& n.pass == passing_style::in
3923+
)
3924+
{
3925+
printer.print_cpp2( print_to_string(type_id), n.position() );
3926+
}
3927+
else if (
39063928
type_id.is_wildcard()
39073929
|| is_dependent_parameter_type
39083930
)
@@ -3960,6 +3982,7 @@ class cppfront
39603982
!is_returns
39613983
&& !type_id.is_wildcard()
39623984
&& !is_dependent_parameter_type
3985+
&& !type_id.is_pointer_qualified()
39633986
)
39643987
{
39653988
switch (n.pass) {

source/parse.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2001,6 +2001,12 @@ struct declaration_node
20012001

20022002
// API
20032003
//
2004+
auto get_parent() const
2005+
-> declaration_node*
2006+
{
2007+
return parent_declaration;
2008+
}
2009+
20042010
auto is_public() const
20052011
-> bool
20062012
{

0 commit comments

Comments
 (0)