220 36695 <6e78f3c4-267d-40c4-bcde-a026e90c3838@isocpp.org> article
Path: news.gmane.org!.POSTED!not-for-mail
From: mihailnajdenov@gmail.com
Newsgroups: gmane.comp.lang.c++.isocpp.proposals
Subject: Re: Static analysis and the future of C++
Date: Thu, 18 Jan 2018 04:35:12 -0800 (PST)
Lines: 246
Approved: news@gmane.org
Message-ID: <6e78f3c4-267d-40c4-bcde-a026e90c3838@isocpp.org>
References: <0087c1a4-0b36-40ca-8d43-5bfaf0af62ca@isocpp.org>
Reply-To: std-proposals@isocpp.org
NNTP-Posting-Host: blaine.gmane.org
Mime-Version: 1.0
Content-Type: multipart/mixed; 
	boundary="----=_Part_2436_2018171762.1516278912639"
X-Trace: blaine.gmane.org 1516278805 4649 195.159.176.226 (18 Jan 2018 12:33:25 GMT)
X-Complaints-To: usenet@blaine.gmane.org
NNTP-Posting-Date: Thu, 18 Jan 2018 12:33:25 +0000 (UTC)
Cc: mihailnajdenov@gmail.com
To: ISO C++ Standard - Future Proposals <std-proposals@isocpp.org>
Original-X-From: std-proposals+bncBCUJ3A7GRAPRBANJQLJQKGQE6YLORPI@isocpp.org Thu Jan 18 13:33:21 2018
Return-path: <std-proposals+bncBCUJ3A7GRAPRBANJQLJQKGQE6YLORPI@isocpp.org>
Envelope-to: gclcip-std-proposals@m.gmane.org
Original-Received: from mail-vk0-f70.google.com ([209.85.213.70])
	by blaine.gmane.org with esmtp (Exim 4.84_2)
	(envelope-from <std-proposals+bncBCUJ3A7GRAPRBANJQLJQKGQE6YLORPI@isocpp.org>)
	id 1ec9NW-0000Lo-Im
	for gclcip-std-proposals@m.gmane.org; Thu, 18 Jan 2018 13:33:10 +0100
Original-Received: by mail-vk0-f70.google.com with SMTP id a2sf13297850vkh.13
        for <gclcip-std-proposals@m.gmane.org>; Thu, 18 Jan 2018 04:35:15 -0800 (PST)
DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
        d=isocpp-org.20150623.gappssmtp.com; s=20150623;
        h=date:from:to:cc:message-id:in-reply-to:references:subject
         :mime-version:x-original-sender:reply-to:precedence:mailing-list
         :list-id:list-post:list-help:list-archive:list-subscribe
         :list-unsubscribe;
        bh=nacMTmDb4APU6qgICr7T/G2jPWCNE36xH6SJAPD1czo=;
        b=oP+SCQIJ3awswv5BmjTU/ccjAF5w8nPLrwI1twi31SnrWcS/nlW2nymXTiiXe/POmS
         IuyoPL+Cp08xFy+yhmY8pk5juzXKlMow3tx1znCB1Ocitw3SjrbLHj0oeOVZ6hup50f7
         mGrBNNBztixSfw6N1FzQfbp7YGgr2Z1vLkj0VcCgSh8i9A7fzS+lXEFq1kiGofBtG3X5
         CSPeg7uxlChCQRiVMbd+oTmYhiDRK8e9qdKC8LOmFKK5z/CcMLpiooujlbp7VrodspvL
         x/+0n3J6SUrbx3985Yq4mGS6vO4QYXyJY/WGZ/nqivnaGK8TaP+kU4evvOZ/Zwi0Ku6r
         /npA==
DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
        d=gmail.com; s=20161025;
        h=date:from:to:cc:message-id:in-reply-to:references:subject
         :mime-version:x-original-sender:reply-to:precedence:mailing-list
         :list-id:list-post:list-help:list-archive:list-subscribe
         :list-unsubscribe;
        bh=nacMTmDb4APU6qgICr7T/G2jPWCNE36xH6SJAPD1czo=;
        b=JKPxxzsAZN2zrk9tcP00vSsjXqHOi6bXmbivHqMokOZXc9f5Wv2YLy4iVDEmqi+ire
         KGj1NXCko8MFMU22cMpUaKgFtq/Rrrg6P8UR627z4GNkEDagVPJCl7MC2W3tdLYfTkeT
         pfqPCfA0gg7OYxrgN3c6Dpjv5Ozk3WwPe0IJcJ3hDqf0cUbq5Q5NWuc+7/UTGDR5XEyh
         mc+4R21sCYkwpIeq+3u9pgnof2OkL0yUyJcYtPI0IdWVHlO3hhXGiedGj50St/SnZMlA
         /VsdyG5ij01pRvrfFtF9OpWPO0dvMOTL7vnB0hc1qKlBFF0GieSd0Nux6a+xsAI8dhTS
         FApQ==
X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
        d=1e100.net; s=20161025;
        h=x-gm-message-state:date:from:to:cc:message-id:in-reply-to
         :references:subject:mime-version:x-original-sender:reply-to
         :precedence:mailing-list:list-id:x-spam-checked-in-group:list-post
         :list-help:list-archive:list-subscribe:list-unsubscribe;
        bh=nacMTmDb4APU6qgICr7T/G2jPWCNE36xH6SJAPD1czo=;
        b=RuPm8M6g0m+mOZtaP4gS27vEIweR6KJe5O4k1QNJ/L8EmKbaAuF+Trtx72KPN13Bo6
         Byjhtc1kHfbb4H3i+vaPrI4hpkaKbWw+5QcG9NoEaRFE0bL4fNkpYFUN9RL0FJG9qWJY
         YATK7uNUP/VjS/28Cnx9dCK4IEB29L3wgYz63Sm1DBzNi5tV5KSj356nip7/bmibPNZ0
         5TQbpljWC0NwneJfJh+ZPCEU2d/kVsGJtMk03/3oxoReKwf0A25W2PjP3WTxnTcRiUpF
         JzDTWNgkCWqkVlTePKUG6GdO4+mwPu21kcfDlGPHOqbMB/uPbFbZP2iV7zu6zqjURIMF
         +laA==
X-Gm-Message-State: AKwxytcgO0a2Qo95SjEV+ws4P4vOQIt8Nd/HrFYAW0exoXYo0RZyb81M
	USu+PcpEfYavUgeC/eCm4qNxVg==
X-Google-Smtp-Source: ACJfBov8mLXF8+I+7xQND3hT3OmHW0PVAB0ZZKW92c2HQMPWW1WduTHGGPGvS+DgNRSPh1WGcXHL+w==
X-Received: by 10.176.112.173 with SMTP id q13mr3074431ual.51.1516278914631;
        Thu, 18 Jan 2018 04:35:14 -0800 (PST)
X-BeenThere: std-proposals@isocpp.org
Original-Received: by 10.31.174.150 with SMTP id x144ls2615145vke.2.gmail; Thu, 18 Jan
 2018 04:35:13 -0800 (PST)
X-Received: by 10.31.169.23 with SMTP id s23mr500958vke.1.1516278912997;
        Thu, 18 Jan 2018 04:35:12 -0800 (PST)
In-Reply-To: <0087c1a4-0b36-40ca-8d43-5bfaf0af62ca@isocpp.org>
X-Original-Sender: MihailNajdenov@gmail.com
Precedence: list
Mailing-list: list std-proposals@isocpp.org; contact std-proposals+owners@isocpp.org
List-ID: <std-proposals.isocpp.org>
X-Spam-Checked-In-Group: std-proposals@isocpp.org
X-Google-Group-Id: 399137483710
List-Post: <https://groups.google.com/a/isocpp.org/group/std-proposals/post>, <mailto:std-proposals@isocpp.org>
List-Help: <https://support.google.com/a/isocpp.org/bin/topic.py?topic=25838>, <mailto:std-proposals+help@isocpp.org>
List-Archive: <https://groups.google.com/a/isocpp.org/group/std-proposals/>
List-Subscribe: <https://groups.google.com/a/isocpp.org/group/std-proposals/subscribe>,
 <mailto:std-proposals+subscribe@isocpp.org>
List-Unsubscribe: <mailto:googlegroups-manage+399137483710+unsubscribe@googlegroups.com>,
 <https://groups.google.com/a/isocpp.org/group/std-proposals/subscribe>
Xref: news.gmane.org gmane.comp.lang.c++.isocpp.proposals:36695
Archived-At: <http://permalink.gmane.org/gmane.comp.lang.c++.isocpp.proposals/36695>

------=_Part_2436_2018171762.1516278912639
Content-Type: multipart/alternative; 
	boundary="----=_Part_2437_461684969.1516278912640"

------=_Part_2437_461684969.1516278912640
Content-Type: text/plain; charset="UTF-8"

For the sake of completeness, in cases when the viewed class creates the 
view, then the && overload should be marked as [[dependent_lifetime]] 

class string
{
  ...
  [[dependent_lifetime]] operator string_view() && { return {c_str(), 
size()}; } //< (probably not the correct place to set the attribute, but 
you get the idea)
};

Now the returned value (the variable created from it) depends on the 
lifetime of *this and should not be used after *this is dtor is called. 

*Further investigation *

Consider that case:

void f()
{
  string_view v;
 
 if(const auto str = getString(); str == "something")
 {
    v = str;
 }
  
 // 'v' is either empty or dangles!
}

The above mistake can happen even to an experienced programmer (if he is 
used to ref-counted strings for instance). People learning C++ and junior 
developers are basically guaranteed to fall in there at some point.

Here it is *painfully* obvious the compiler knows the right usage - he just 
keeps it shut! We *should* be able to make him speak.

BTW, that is an interesting case, as it is not about initialization, but 
assignment. However, does it matter? It is still clear the scope of 
tracking - from assignment tor dtor.

Even if we have a more involved case

void f( string_view& v)
{
 if(const auto str = getString(); str == "something")
 {
    v = str;
 }
}
int main()
{
 string_view& v;
 f(v);
 return 0;
}

The compiler still knows all that is needed, doesn't it? As long as the 
view is an automatic variable the compiler can always detected if, during 
its lifetime, it is used after the pointed-to dtor is called.
Isn't that always the case? Isn't that that case even if the pointed-to is 
heap allocated? 

o_view v = o_p->getView();

The compiler can still tell if *o_p is destroyed before v is destroyed. Am 
I mistaken here? 

Considering view classes are 99.9% of the time used as automatic variables, 
there is no good reason for them to be unsafe. 

(Or maybe there is, I might be missing something)


*And lets talk copies.*

Nothing is actually preventing this tracking to work for copies of the view 
as well - the rules are exactly the same - if before view.~view() there is 
a call to object.~object() there should be no view,access(). 
How many views are, it does not matter at all as long as they are 
automatic. 
It also does not matter if ~object() was called by the compiler 
(automatic), the user (delete p_object;) or by a ref counted shared_ptr!

With that in mind.

void f(view<B> vb) //< by copy
{
   destroy_b_unknowingly();
  vb.use(); //< warning, dtor of b was called already
}

*Even further investigation*

template<class T>
class unique_ptr
{
  ...
  [[dependent_lifetime]] T* get() { return _p; }
  ...
  T* _p;
};

Now the variable of type T* is a view to the unique_ptr. If ~unique_ptr() 
is called before the (automatic) T* variable, created/assigned by get, goes 
out of scope, it will be an error to use that variable. 

But, lets take this to the next level:

template<class T>
class unique_ptr
{
  ...
  [[dependent_lifetime(*_p)]] T* get() { return _p; }
  ...
  T* _p;
};

Now it is an error to use T* after ~T(), and ~T(),  can come from any place 
- shared_ptr, manual delete, another, moved into unique_ptr. Everywhere.
And the rules are still the same - no use of this T* variable, after a 
~T(), until this T* variable goes out of scope ("as if" it has a dtor 
called). 
The relationship is still b/w an automatic variable and a dtor call. 

Am I fooling myself here? Isn't that mighty useful? Isn't that all 
implementable today? What is the harm? It does not even writes off lifetime 
extension and what not - it just reinforces safe use of the language, the 
way this language is right now. 
No new semantics, no new rules! 


-- 
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/6e78f3c4-267d-40c4-bcde-a026e90c3838%40isocpp.org.

------=_Part_2437_461684969.1516278912640
Content-Type: text/html; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr"><div>For the sake of completeness, in cases when the viewe=
d class creates the view, then the &amp;&amp; overload should be marked as =
[[dependent_lifetime]] </div><div><br></div><div><font face=3D"courier new,=
monospace">class string<br>{<br>=C2=A0 ...<br>=C2=A0 [[dependent_lifetime]]=
 operator string_view() &amp;&amp; { return {c_str(), size()}; } //&lt; (pr=
obably not the correct place to set the attribute, but you get the idea)<br=
>};</font></div><div><font face=3D"courier new"><br></font></div><div>Now t=
he returned value (the variable created from it) depends on the lifetime of=
 *this and should not be used after *this is dtor is called. </div><div><br=
></div><div><b>Further investigation </b></div><div><b></b><br>Consider tha=
t case:</div><div><br></div><div><font face=3D"courier new,monospace">void =
f()<br>{<br>=C2=A0 string_view v;<br>=C2=A0<br>=C2=A0if(const auto str =3D =
getString(); str =3D=3D &quot;something&quot;)<br>=C2=A0{<br>=C2=A0=C2=A0=
=C2=A0 v =3D str;<br>=C2=A0}<br>=C2=A0 <br>=C2=A0// &#39;v&#39; is either e=
mpty or dangles!<br>}</font></div><div><font face=3D"courier new,monospace"=
><br></font></div><div>The above mistake can happen even to an experienced =
programmer (if he is used to ref-counted strings for instance). People lear=
ning C++ and junior developers are basically guaranteed to fall in there at=
 some point.</div><div><br></div><div>Here it is <i>painfully</i> obvious t=
he compiler knows the right usage - he just keeps it shut! We <i>should</i>=
 be able to make him speak.</div><div><br></div><div>BTW, that is an intere=
sting case, as it is not about initialization, but assignment. However, doe=
s it matter? It is still clear the scope of tracking - from assignment tor =
dtor.</div><div><br></div><div>Even if we have a more involved case</div><d=
iv><br></div><div><font face=3D"courier new,monospace">void f( string_view&=
amp; v)<br>{<br>=C2=A0if(const auto str =3D getString(); str =3D=3D &quot;s=
omething&quot;)<br>=C2=A0{<br>=C2=A0=C2=A0=C2=A0 v =3D str;<br>=C2=A0}<br>}=
</font></div><div><font face=3D"courier new,monospace">int main()<br>{<br>=
=C2=A0string_view&amp; v;<br>=C2=A0f(v);</font></div><div><font face=3D"cou=
rier new,monospace">=C2=A0return 0;<br>}</font></div><div><font face=3D"cou=
rier new,monospace"><br></font></div><div>The compiler still knows all that=
 is needed, doesn&#39;t it? As long as the view is an automatic variable th=
e compiler can always detected if, during its lifetime, it is used after th=
e pointed-to dtor is called.</div><div>Isn&#39;t that always the case? Isn&=
#39;t that that case even if the pointed-to is heap allocated? </div><div><=
br></div><div><font face=3D"courier new,monospace">o_view v =3D o_p-&gt;get=
View();</font></div><div><font face=3D"courier new,monospace"><br></font></=
div><div>The compiler can still tell if *o_p is destroyed before v is destr=
oyed. Am I mistaken here? </div><div><br></div><div>Considering view classe=
s are 99.9% of the time used as automatic variables, there is no good reaso=
n for them to be unsafe. </div><div><br></div><div>(Or maybe there is, I mi=
ght be missing something)</div><div><br></div><div><b><br>And lets talk cop=
ies.</b></div><div><b><br></b></div><div>Nothing is actually preventing thi=
s tracking to work for copies of the view as well - the rules are exactly t=
he same - if before view.~view() there is a call to object.~object() there =
should be no view,access(). </div><div>How many views are, it does not matt=
er at all as long as they are automatic. </div><div>It also does not matter=
 if ~object() was called by the compiler (automatic), the user (delete p_ob=
ject;) or by a ref counted shared_ptr!</div><div><br>With that in mind.</di=
v><div><br></div><div><font face=3D"courier new,monospace">void f(view&lt;B=
&gt; vb) //&lt; by copy<br>{<br>=C2=A0=C2=A0 destroy_b_unknowingly();</font=
></div><div><font face=3D"courier new,monospace">=C2=A0 vb.use(); //&lt; wa=
rning, dtor of b was called already<br>}</font></div><div><font face=3D"cou=
rier new,monospace"><br></font></div><div><b>Even further investigation</b>=
</div><div><b><br></b></div><div><font face=3D"courier new,monospace">templ=
ate&lt;class T&gt;<br>class unique_ptr<br>{<br>=C2=A0 ...<br>=C2=A0 [[depen=
dent_lifetime]] T* get() { return _p; }<br>=C2=A0 ...<br>=C2=A0 T* _p;<br>}=
;</font></div><div><font face=3D"courier new,monospace"></font><br>Now the =
variable of type T* is a view to the unique_ptr. If ~unique_ptr() is called=
 before the (automatic) T* variable, created/assigned by get, goes out of s=
cope, it will be an error to use that variable. </div><div><br>But, lets ta=
ke this to the next level:</div><div><br></div><div><font face=3D"courier n=
ew,monospace">template&lt;class T&gt;<br>class unique_ptr<br>{<br>=C2=A0 ..=
..<br>=C2=A0 [[dependent_lifetime(*_p)]] T* get() { return _p; }<br>=C2=A0 .=
...<br>=C2=A0 T* _p;<br>};</font></div><div><font face=3D"courier new,monosp=
ace"><br></font></div><div>Now it is an error to use T* after ~T(), and ~T(=
),=C2=A0 can come from any place - shared_ptr, manual delete, another, move=
d into unique_ptr. Everywhere.</div><div>And the rules are still the same -=
 no use of this T* variable, after a ~T(), until this T* variable goes out =
of scope (&quot;as if&quot; it has a dtor called). </div><div>The relations=
hip is still b/w an automatic variable and a dtor call. </div><div><br></di=
v><div>Am I fooling myself here? Isn&#39;t that mighty useful? Isn&#39;t th=
at all implementable today? What is the harm? It does not even writes off l=
ifetime extension and what not - it just reinforces safe use of the languag=
e, the way this language is right now. <br>No new semantics, no new rules! =
</div><div><br></div><div><br></div></div>

<p></p>

-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/6e78f3c4-267d-40c4-bcde-a026e90c3838%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/6e78f3c4-267d-40c4-bcde-a026e90c3838=
%40isocpp.org</a>.<br />

------=_Part_2437_461684969.1516278912640--

------=_Part_2436_2018171762.1516278912639--

.
