Topic: Dnnnn - <scope_exit> RAII classes...


Author: Andrew Sandoval <sandoval@netwaysglobal.com>
Date: Fri, 12 Apr 2013 14:54:07 -0700 (PDT)
Raw View
------=_Part_2878_7147491.1365803647849
Content-Type: multipart/alternative;
 boundary="----=_Part_2879_3025499.1365803647849"

------=_Part_2879_3025499.1365803647849
Content-Type: text/plain; charset=ISO-8859-1

I've requested a document number on this but haven't received it yet.  In
the meantime I wanted to make sure that the latest version of the document
was available for review. It is here:
http://www.andrewlsandoval.com/scope_exit/scope_exit.h

Please be kind.  I'm not sure I am even in the ballpark on the
"standardese" section, but it was very painful and time consuming
(something I never have enough of to start with) to put together.

Thank you, and thanks to everyone that has contributed feedback thus far on
this proposal.

-Andrew Sandoval

--

---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/?hl=en.



------=_Part_2879_3025499.1365803647849
Content-Type: text/html; charset=ISO-8859-1
Content-Transfer-Encoding: quoted-printable

I've requested a document number on this but haven't received it yet.&nbsp;=
 In the meantime I wanted to make sure that the latest version of the docum=
ent was available for review. It is here: http://www.andrewlsandoval.com/sc=
ope_exit/scope_exit.h<br><br>Please be kind.&nbsp; I'm not sure I am even i=
n the ballpark on the "standardese" section, but it was very painful and ti=
me consuming (something I never have enough of to start with) to put togeth=
er.<br><br>Thank you, and thanks to everyone that has contributed feedback =
thus far on this proposal.<br><br>-Andrew Sandoval<br>

<p></p>

-- <br />
&nbsp;<br />
--- <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 std-proposals+unsubscribe@isocpp.org.<br />
To post to this group, send email to std-proposals@isocpp.org.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/?hl=3Den">http://groups.google.com/a/isocpp.org/group/std-pro=
posals/?hl=3Den</a>.<br />
&nbsp;<br />
&nbsp;<br />

------=_Part_2879_3025499.1365803647849--
------=_Part_2878_7147491.1365803647849
Content-Type: text/html; charset=windows-1252; name=proposal.html
Content-Transfer-Encoding: quoted-printable
Content-Disposition: attachment; filename=proposal.html
X-Attachment-Id: 24990523-e68c-4f75-b6fd-73fc4d06c466
Content-ID: <24990523-e68c-4f75-b6fd-73fc4d06c466>

<HTML>
<HEAD>
<META NAME=3D"GENERATOR" Content=3D"Microsoft Visual Studio 8.0">
<TITLE>A Proposal to Add additional RAII Wrappers to the Standard Library</=
TITLE>
    <style type=3D"text/css">
        .style1
        {
            color: #000099;
        }
        .style2
        {
            color: #800000;
        }
        .style4
        {
            color: #0000A0;
        }
        .style5
        {
            color: #400080;
        }
        .style6
        {
            color: #004000;
        }
        .style7
        {
            color: #004000;
            font-style: italic;
        }
        .style8
        {
            color: #FF0000;
        }
        .style9
        {
            color: #004000;
            font-weight: bold;
        }
        .style10
        {
            color: #000000;
        }
    </style>
</HEAD>
<BODY>



    <p><code>
        Document Number:&nbsp; Dnnnn=3D12-nnnn<br />
        Date:&nbsp; 2012-11-10<br />
        Project:&nbsp; Programming Language C++, Library Working Group<br /=
>
        Reply-to: Andrew L. Sandoval &lt;sandoval at netwaysglobal dot com&=
gt;<br />
    </code>
    </p>

<center> <h1>A Proposal to Add additional RAII Wrappers to the Standard Lib=
rary</h1> </center>
<h2>I.  Table of Contents</h2>
<ul>
<li>Introduction</li>
<li>Motivation and Scope</li>
<li>Impact on Standard</li>
<li>Design Decisions</li>
<li>Technical Specifications</li>
<li>Acknowledgments</li>
<li>References</li>
</ul>
<h2>II.  Introduction</h2>
This proposal seeks to add generic RAII wrappers to the standard library.  =
These wrappers will be used to manage the lifetime of various types of reso=
urces and to guarantee the execution of code blocks on scope exit.  It buil=
ds on the concept of smart pointers like <code>unique_ptr</code>, but is de=
signed for use with any type of resource=20
    that requires clean-up prior to scope exit, as well as any block of cod=
e (via=20
    lambda or function invocation) that needs to executed prior to scope ex=
it.
<h2>III.  Motivation and Scope</h2>
<p>Quality C++ code requires the use of RAII to manage all types of resourc=
es in=20
    order to prevent leakage as well as to limit resource lifetime.&nbsp; R=
esource leakage can occur from the obvious, though often overlooked, failur=
e to clean-up a resource at its intended end-of-life, as well as the less o=
bvious=20
    and arguably more common failure to ensure proper handling of resources=
 during exception unwinding.</p>
<p>Smart pointers such as <code>unique_ptr</code> and <code>shared_ptr</cod=
e> provide an excellent means of managing the lifetime of pointer types.  M=
any other RAII classes have been written to manage the lifetime and limit t=
he scope of locks, such as Boost's <code>boost::lock_guard</code>.  All of =
these and the many other types of RAII objects help to=20
    substantially improve C++ code quality.
  This proposal seeks to add a set of <i>generic</i>, light-weight RAII wra=
ppers intended to manage the scope and lifetime of any other type of resour=
ce.&nbsp;=20
    It also proposes an RAII wrapper intended to wrap a function, lambda, o=
r functor=20
    which needs to execute prior to scope exit.</p>
<p>There are many types of resources that <i>may</i> not justify encapsulat=
ion in a broader object -- when a simple RAII wrapper around the resource w=
ill suffice or will provide a more obvious implementation.=20
    This is especially true when object re-use is not expected. In addition=
, RAII=20
    wrappers will simplify the design of objects that <em>do</em> encapsula=
te resources,=20
    allowing the generation of, or the declaration of the resource, to also=
 declare its method of clean-up.&nbsp;=20
    This results in moving resource clean-up outside of an explicit destruc=
tor,=20
    which also assures proper order of destruction when initialization orde=
r is=20
    correct.&nbsp; This is common practice with pointers managed by <code>u=
nique_ptr</code> and <code>shared_ptr</code>, and even with buffers allocat=
ed and managed by <code>vector</code>.</p>
<p>This proposal requests the addition of the following RAII wrapper types:
<ul>
    <li><code><b>scoped_function</b></code></li>
    <ul>
        <li>Executes a function, functor, or lambda on scope exit.</li>
        <li>Is generated with <code><b>make_scoped_function</b>(<i>func</i>=
);</code></li>
        <li><code><b>func</b></code> is a function, functor, or lambda that=
 takes no parameters.  A lambda however may capture=20
        and use any scope variables.</li>
    </ul>
    <li><code><b>scoped_resource_unchecked</b></code></li>
    <ul>
        <li>Manages a resource's lifetime by executing a deleter function, =
functor, or lambda on scope exit.</li>
        <li>Is generated with <code><b>make_scoped_resource_unchecked</b>(<=
i>resource</i>, <i>deleter-func</i>);</code>, or with the=20
        more generic <code><b>make_scoped_resource(<i>resource</i>, <i>dele=
ter-func</i>);</b></code></li>
        <li><code><b>deleter-func</b></code> is a function, functor, or lam=
bda that takes a single parameter of the same type as <i>resource</i>.</li>
        <li>Is suitable for no-fail resources, or other resources in which =
a validity check by comparison to a no-delete value is not possible.</li>
    </ul>
    <li><code><b>scoped_resource</b></code></li>
    <ul>
        <li>Manages a resource's lifetime by executing a deleter function, =
functor, or lambda on scope exit, when the resource value can be validated =
by comparison to a no-delete value.</li>
        <li>Is generated with <code><b>make_scoped_resource</b>(<i>resource=
</i>, <i>deleter-func</i>, <i>no-delete-value</i>);</code></li>
        <li>When generated with <code><b>make_scoped_resource&lt;true&gt;</=
b>(<i>resource</i>, <i>deleter-func</i>, <i>no-delete-value</i>);</code> th=
e <code>scoped_resource</code> constructor will throw <code>failed_resource=
_initialization</code> if the resource is equal to the no-delete value.</li=
>
        <li><code><b>deleter-func</b></code> is a function, functor, or lam=
bda that takes a single parameter of the same type as <i>resource</i>.</li>
        <li><code><b>no-delete-value</b></code> is a value of type <i>resou=
rce</i> that is used to prevent calling <i>deleter-func</i> when the resour=
ce is not valid, as well as to check if the resource is <code>bool <b>valid=
</b>() const;</code></li>
    </ul>
    <li><code><b>unique_resource</b></code></li>=20
    <ul>
        <li>Manages a resource's lifetime by executing a <i>constexpr</i> d=
eleter function on scope exit, when the resource value can be validated by =
comparison to a=20
            <em>constexpr</em> no-delete value.</li>
        <li>It requires template arguments for:</li>
            <ol>
            <li>The type of a constexpr deleter function, which function ta=
kes a single parameter of the type of the resource, <i>and from which the r=
esource type is deduced</i></li>
            <li>The constexpr deleter function itself</li>
            <li>A bool value, which when set to true will cause the constru=
ctor to throw <code>failed_resource_initialization</code> if the value pass=
ed to the constructor matches the no-delete value.&nbsp;=20
                When false, a validity check is not performed on object con=
struction, but the=20
                deleter function will not be executed in the destructor if =
the validity check=20
                fails.</li>
            <li>A no-delete value of the deduced type of the resource.&nbsp=
; The types is<i> deduced from the sole parameter to the deleter-func type.=
</i>  The default no-delete value is <code>
                <span class=3D"style4">static_cast</span>&lt;T&gt;(<span cl=
ass=3D"style4">nullptr</span>)</code>.</li>
            </ol>
        <li>Because of the static or constexpr non-type template arguments =
for the deleter function and the no-delete value:</li>
        <ul>
            <li>The generated code is very tight and should be roughly the =
equivalent of adding:<br /> <code>if(resource !=3D nodelete) { deleter-func=
(resource); } </code> at a common exit point for the=20
                scope.</li>
            <li>There is no generator function template.</li>
            <li>The no-delete value of the same type as the resource.  It i=
s used to prevent calling the deleter function if the resource is not valid=
, as well as to check if the resource is <code>bool valid() const;</code></=
li>
        </ul>
        <li>Can be constructed without a resource value by using the defaul=
t constructor.&nbsp;=20
            This allows the resource value to be set using <code>operator=
=3D</code> at a later time.</li>
</ul>
<h3>A. Motivation for <code>scoped_function</code></h3>
<code>scoped_function</code> is ideal for tying a block of code -- such as =
a lambda to a particular scope, ensuring that the block is invoked prior to=
 scope exit.
Two examples should suffice:
<h4>Example <code>scoped_function</code> for mandatory logging on function =
exit:</h4>
<code><pre>
<span class=3D"style4">bool</span> <span class=3D"style2">SomeFunction</spa=
n>(<span=20
            class=3D"style4">const</span> input_t &input, modifier_t &modif=
ier, status_t &status)
{
    <span class=3D"style6">// Always log the status on scope-exit whether i=
t changes or not...</span>
    <span class=3D"style4">auto</span> &&log_status_on_exit =3D <span class=
=3D"style4">std</span>::<span=20
            class=3D"style2">make_scoped_function</span>([&status, &modifie=
r]() -&gt;<span=20
            class=3D"style4">void</span>
    {
        LogStatus(status, "SomeFunction", modifier);
    });

    <span class=3D"style4">if</span>(!<span class=3D"style2">AlterationOne<=
/span>(input, modifier, status))
    {
        <span class=3D"style4">return false</span>;
    }
    .
    .
    .
    <span class=3D"style4">return</span> <span class=3D"style2">AlterationF=
our</span>(modifier, status);
}
</pre></code>
<h4>Example <code>scoped_function</code> for loop advancement:</h4>
<code><pre>
LegacyDisassembler dis(pInstructionPointer, length);
<span class=3D"style4">while</span>(dis.<span class=3D"style2">RemainingByt=
es</span>())
{
    <span class=3D"style6">// Ensure that no matter where else the loop con=
tinues, dis gets advanced...</span>
    <span class=3D"style4">auto</span> &&advance =3D <span class=3D"style4"=
>std</span>::<span=20
            class=3D"style2">make_scoped_function</span>([&dis]() -&gt;<spa=
n=20
            class=3D"style4">void</span>
    {
        dis.<span class=3D"style2">Advance</span>(dis.<span class=3D"style2=
">InstructionLength</span>());
    });

    <span class=3D"style4">if</span>(dis.<span class=3D"style2">BadInstruct=
ion</span>())
    {
        std::cerr << "<span class=3D"style8">Error on </span>" << dis << st=
d::endl;
        <span class=3D"style4">continue</span>;   <span class=3D"style6">//=
 Skip the bad byte(s)</span>
    }

    <span class=3D"style6">// Handle special cases</span>
    .
    .
    .

    <span class=3D"style6">// Print the Instruction...</span>
    std::cerr &lt;&lt; dis.Address &lt;&lt; "<span class=3D"style8">: </spa=
n>" &lt;&lt; dis &lt;&lt; std::endl;
}
</pre></code>
<h3>B. Motivation for <code>scoped_resource_unchecked</code></h3>
<code>scoped_resource_unchecked</code> is ideal for managing a resource tha=
t either can't fail to be initialized, or whose deleter function <i>handles=
</i> exceptional cases (such as an invalid, uninitialized or previously del=
eted resource).&nbsp;=20
        It provides no validity checking, and unless <code>release()</code>=
&#39;d the deleter-function=20
        will be invoked with the resource on scope exit.
<h4><code>scoped_resource_unchecked</code> example:</h4>
<code>
<pre>
CRITICAL_SECTION cs;
<span class=3D"style2">InitializeCriticalSection</span>(&cs);
<span class=3D"style6">// InitializeCriticalSection() can't fail and return=
s void, but we need the delete to occur prior to scope exit...
// Otherwise it remains on the process&#39;s linked-list of active CRITICAL=
_SECTION's.</span>
<span class=3D"style4">auto</span> &&pCS =3D <span class=3D"style4">std</sp=
an>::<span=20
            class=3D"style2">make_scoped_resource_unchecked</span>(&cs, <sp=
an=20
            class=3D"style2">DeleteCriticalSection</span>);   <span class=
=3D"style6">// DeleteCriticalSection can't fail and return void</span>
</pre>
</code>
<h3>C. Motivation for <code>scoped_resource</code></h3>
<code>scoped_resource</code> is designed to handle most resources.  It keep=
s the user congnizant of how the resource will be destroyed when it exits s=
cope, and of the condition that must be met.
  Though it produces larger object code than <code>unique_resource</code>, =
it benefits from having a generator function template that deduces the temp=
late arguments.

<h4>Example using <code>scoped_resource</code> for with a C API:</h4>
<code>
<pre>
<span class=3D"style6">// Open a file, ensure it is closed when we leave sc=
ope, if the file descriptor is valid...</span>
<span class=3D"style4">auto</span>&& iFileDesc =3D <span class=3D"style4">s=
td</span>::<span=20
            class=3D"style2">make_scoped_resource</span>(<span class=3D"sty=
le2">_open</span>(pszPath, <span=20
            class=3D"style5">O_WRONLY</span>), <span class=3D"style2">_clos=
e</span>, -1);<span=20
            class=3D"style6">=09// if _open returns -1, don't call _close..=
..</span>
<span class=3D"style4">if</span>(iFileDesc.<span class=3D"style2">valid</sp=
an>())
{
    <span class=3D"style2">_write</span>(iFileDesc, &data, <span class=3D"s=
tyle4">sizeof</span>(data));
}
</pre>
</code>

This could also be done using exception handling=20
        (where exception handling is allowed and expected)...
<code>
<pre>
<span class=3D"style4">try</span>
{
<span class=3D"style6">    // Open a file, ensure it is closed when we leav=
e scope, if the file descriptor is valid...</span>
<span class=3D"style4">    auto</span>&& iFileDesc =3D <span class=3D"style=
4">std</span>::<span=20
            class=3D"style2">make_scoped_resource</span>(<span class=3D"sty=
le2">_open</span>(pszPath, <span=20
            class=3D"style5">O_WRONLY</span>), <span class=3D"style2">_clos=
e</span>, -1);<span=20
            class=3D"style6">=09// if _open returns -1, throw...</span>

    <span class=3D"style2">_write</span>(iFileDesc, &data, <span class=3D"s=
tyle4">sizeof</span>(data));
}
<span class=3D"style4">catch</span> (<span class=3D"style4">const std::fail=
ed_resource_initialization</span> &e)
{
    std::cout &lt;&lt; "<span class=3D"style8">Exception: </span>" &lt;&lt;=
 e.<span=20
            class=3D"style2">what</span>() &lt;&lt; std::endl;
    <span class=3D"style4">return false</span>;
}
<span class=3D"style4">return true</span>;
</pre>
</code>
<h4>Example using <code>scoped_resource</code> for with a Windows API:</h4>
<pre>
<code>
<span class=3D"style6">// Create or open an event handle, wait on it, but a=
fter being signalled close the handle...</span>
<span class=3D"style6">// Don't CloseHandle() if we don't have permissions =
to open it, etc.</span>
<span class=3D"style6">// Another exception-free example, that with differe=
nt calls could be used in kernel-mode</span>
<span class=3D"style4">const HANDLE</span> INVALID_EVENT_HANDLE =3D <span c=
lass=3D"style4">static_cast</span>&lt;<span=20
            class=3D"style4">HANDLE</span>&gt;(<span class=3D"style4">nullp=
tr</span>);

<span class=3D"style4">auto</span> hEvent =3D <span class=3D"style4">std</s=
pan>::<span=20
            class=3D"style2">make_scoped_resource</span>(<span class=3D"sty=
le2">CreateEvent</span>(<span=20
            class=3D"style4">nullptr</span>, TRUE, FALSE, <span class=3D"st=
yle4">nullptr</span>), <span=20
            class=3D"style2">CloseHandle</span>, INVALID_EVENT_HANDLE);
<span class=3D"style4">if</span>(!hEvent.<span class=3D"style4">valid</span=
>())
{
    <span class=3D"style4">return false</span>;   <span class=3D"style6">//=
 CloseHandle will not be called</span>
}
DWORD dwWait =3D <span class=3D"style2">WaitForSingleObject</span>(hEvent, =
1000);
..
..
..
<span class=3D"style6">// CloseHandle() will be called as soon as hEvent le=
aves scope</span>
</pre>
</code>
NOTE: Microsoft defines <code>INVALID_HANDLE_VALUE</code> as <code>-1</code=
> for the <code>CreateFile</code> API, but returns <code>NULL</code> for mo=
st other APIs.  Compliant compilers can handle the case where <code>INVALID=
_HANDLE_VALUE</code> is passed to <code>scoped_ptr</code> as a no-delete va=
lue.&nbsp;=20
        Unfortunately this is not true of some c++11 compliant compilers (s=
uch as g++) when <code>INVALID_HANDLE_VALUE</code> is passed as a non-type =
template parameter:
<code><pre>
<span class=3D"style4">auto</span>&& hFile =3D <span class=3D"style4">std</=
span>::<span=20
            class=3D"style2">make_scoped_resource</span>(<span class=3D"sty=
le2">CreateFileW</span>(pwzPath, FILE_GENERIC_WRITE, FILE_SHARE_WRITE, <spa=
n=20
            class=3D"style4">nullptr</span>, CREATE_ALWAYS, FILE_ATTRIBUTE_=
NORMAL, <span=20
            class=3D"style4">nullptr</span>),
    <span class=3D"style2">CloseHandle</span>, <span class=3D"style5">INVAL=
ID_HANDLE_VALUE</span>);<span=20
            class=3D"style6">     // Compiles fine</span>
</pre>
<pre>
<span class=3D"style4">std</span>::<span class=3D"style4">unique_resource</=
span>&lt;<span=20
            class=3D"style5">UNIQUE_DELETER</span>(<span class=3D"style2">C=
loseHandle</span>),<span=20
            class=3D"style5"> INVALID_HANDLE_VALUE</span>&gt; <span class=
=3D"style6">// Compiler error on gcc-4.7, compiles on Visual Studio 2010</s=
pan>
    hFile(<span class=3D"style2">CreateFileW</span>(pwzPath, FILE_GENERIC_W=
RITE, FILE_SHARE_WRITE, <span=20
            class=3D"style4">nullptr</span>, CREATE_ALWAYS, FILE_ATTRIBUTE_=
NORMAL, <span=20
            class=3D"style4">nullptr</span>));
</pre>
</pre></code>


<h3>D. Motivation for <code>unique_resource</code></h3>
<p>The primary motivation for using <code>unique_resource</code> over <code=
>scoped_resource</code>=20
    is the size of the generated object code.&nbsp; It's use is restricted =
to resources that have a constexpr deleter function which takes a single ar=
gument of the same type as the resource.&nbsp;
Also, the deleter function and the no-delete value must be constant express=
ions.<br /></p>
<p>There is no generator like <code><nobr>make_scoped_resource()</nobr></co=
de> for <code>unique_resource</code>. It's construction requires=20
    4 template parameters, but unlike <code><nobr>make_scoped_resource()</n=
obr></code>, the static=20
    (constexpr) no-delete value has a default value of <code><span class=3D=
"style4">static_cast</span>&lt;T&gt;(<span=20
        class=3D"style4">nullptr</span>)</code>, where <code>T</code> is th=
e type of the first argument passed to the deleter function.<br /></p>

<p>In the reference implementation <code>unique_resource</code> uses a pare=
nt implementation class called <code>unique_resource_impl</code>.  This all=
ows the type of the resource to be deduced using template metaprogramming. =
 <code>unique_resource_impl</code> requires=20
    5 template parameters.  The <code>TFuncInfo1</code> template resolves t=
he parameter type of the deleter function for <code>unique_resource</code> =
which inherits from <code>unique_resource_impl</code>.<br /></p>

<p>To simplify use of <code>unique_resource</code>, a convenience macro is =
used in the examples below, and in the reference implementation.  It is def=
ined as:</p>
<code><pre>#<span class=3D"style4">define</span> <span class=3D"style5">UNI=
QUE_DELETER</span>(deleter_fn) decltype(&deleter_fn), deleter_fn, <span=20
            class=3D"style4">false</span>
#<span class=3D"style4">define</span> <span class=3D"style5">UNIQUE_DELETER=
_THROW</span>(deleter_fn) decltype(&deleter_fn), deleter_fn, <span=20
            class=3D"style4">true</span></pre></code>

<p>Another consideration when using <code>unique_resource</code> over <code=
>make_scoped_resource()</code> is the benefit it provides for member variab=
le resources.  For example, both of the following classes will accomplish t=
he same end-goal, of calling <code>CloseHandle</code>
 on <code>m_hEvent</code> when an instance of the class is destroyed, but t=
he <code>unique_resource</code> example is slightly easier to read, especia=
lly with the help of <code>UNIQUE_DELETER</code>.

<code>
<pre>
<span class=3D"style4">class</span> TestClassMember
{
<span class=3D"style4">private</span>:
    <span class=3D"style6">// auto &&m_hEvent; // error C3531: 'm_hEvent': =
a symbol whose type contains 'auto' must have an initializer</span>
    <span class=3D"style4">std</span>::<span class=3D"style2">scoped_resour=
ce</span>&lt;<span=20
            class=3D"style4">decltype</span>(&<span class=3D"style2">CloseH=
andle</span>), HANDLE&gt; m_hEvent;=09<span=20
            class=3D"style6">// </span><span class=3D"style9">ok, but a bit=
 bulky...  And a macro can't deduce the resource type...</span>

<span class=3D"style4">public</span>:
    <span class=3D"style6">// TestClassMember() : m_hEvent(std::make_scoped=
_resource(CreateEvent(nullptr, TRUE, FALSE, nullptr), [](HANDLE hEvent) { i=
f(hEvent) CloseHandle(hEvent); }))</span>
<span class=3D"style6">    // {  // ^^: error C2440: 'initializing' : canno=
t convert from 'std::scoped_resource_unchecked&lt;T,R&gt;' to 'int'</span>
<span class=3D"style6">    // }</span>

    TestClassMember() : m_hEvent(<span class=3D"style4">std</span>::<span c=
lass=3D"style2">make_scoped_resource</span>(<span=20
            class=3D"style2">CreateEvent</span>(<span class=3D"style4">null=
ptr</span>, TRUE, FALSE, <span=20
            class=3D"style4">nullptr</span>), <span class=3D"style2">CloseH=
andle</span>, <span=20
            class=3D"style4">static_cast</span><HANDLE>(<span class=3D"styl=
e4">nullptr</span>)))
    {
        <span class=3D"style6">// ^^ </span><span class=3D"style9">This how=
ever works, but it isn't quite as easy to follow as the example in TestClas=
sMember2</span>
    }

    <span class=3D"style4">void</span> Wait()
    {
        DWORD dwX =3D <span class=3D"style2">WaitForSingleObject</span>(m_h=
Event, <span=20
            class=3D"style5">INFINITE</span>);
        <span class=3D"style6">// Other stuff here...</span>
    }

    <span class=3D"style4">void</span> Set()
    {
        <span class=3D"style2">SetEvent</span>(m_hEvent);
    }

    <span class=3D"style6">// Other stuff here...</span>
};

<span class=3D"style4">class</span> TestClassMember2
{
<span class=3D"style4">private</span>:
    <span class=3D"style4">std</span>::<span class=3D"style4">unique_resour=
ce</span>&lt;<span=20
            class=3D"style5">UNIQUE_DELETER</span>(<span class=3D"style2">C=
loseHandle</span>)&gt; m_hEvent;
   <span class=3D"style6"> // </span><span class=3D"style9">^^ This is easy=
 to understand, ^^ draws attention to the deleter function</span>

<span class=3D"style4">public</span>:
    TestClassMember2() : m_hEvent(<span class=3D"style2">CreateEvent</span>=
(<span=20
            class=3D"style4">nullptr</span>, TRUE, FALSE, <span class=3D"st=
yle4">nullptr</span>))   <span=20
            class=3D"style6">// </span><span class=3D"style9">Initializatio=
n is natural, similar to the raw resource type</span>
    {
    }

    <span class=3D"style4">void</span> Wait()
    {
        DWORD dwX =3D <span class=3D"style2">WaitForSingleObject</span>(m_h=
Event, <span=20
            class=3D"style5">INFINITE</span>);
        <span class=3D"style6">// Other stuff here...</span>
    }

    <span class=3D"style4">void</span> Set()
    {
        <span class=3D"style2">SetEvent</span>(m_hEvent);
    }
    <span class=3D"style6">// Other stuff here...</span>
};
</code>
</pre>

</p>

<h4>Example of <code>unique_resource</code> compared to a <code>scoped_reso=
urce</code> generated with <code><nobr>make_scoped_resource()</nobr></code>=
</h4>
The following two (obviously useless) functions were compiled with Visual S=
tudio 2010 for 32-bit Windows.  Notice that the code generated by <code><no=
br>test_unique_resource()</nobr></code> is only 32 bytes, compared to the 5=
7 byte <code><nobr>test_scoped_resource()</nobr></code>, which does the sam=
e thing.

<code>
<pre>
<span class=3D"style1">void</span> <span class=3D"style2">test_unique_resou=
rce</span>(...)    <span=20
            class=3D"style6">//... added to prevent inlining</span>
{
    <span class=3D"style6">// Create an event which will be closed on scope=
-exit, if NOT NULL.  It can be passed to SetEvent/WFSO as hEvent</span>
   <span class=3D"style4"> std</span><span class=3D"style10">::</span><span=
 class=3D"style4">unique_resource</span>&lt;<span class=3D"style5">UNIQUE_D=
ELETER</span>(<span=20
            class=3D"style2">CloseHandle</span>)&gt; hEvent(<span=20
            class=3D"style2">CreateEvent</span>(<span class=3D"style4">null=
ptr</span>, TRUE, FALSE, <span=20
            class=3D"style4">nullptr</span>));
}

<span class=3D"style6">// Object Code: (32 bytes, no prologue, no epilogue,=
 1 byte for ret)</span>
<span class=3D"style6">// scope_exit!test_unique_resource [scope_exit\scope=
_exit.cpp @ 243]:</span>
<span class=3D"style6">//   243 003d1310 6a00            push    0</span>
<span class=3D"style6">//   245 003d1312 6a00            push    0</span>
<span class=3D"style6">//   245 003d1314 6a01            push    1</span>
<span class=3D"style6">//   245 003d1316 6a00            push    0</span>
<span class=3D"style6">//   245 003d1318 ff1510303d00    call    dword ptr =
[scope_exit!_imp__CreateEventW (003d3010)]</span>
<span class=3D"style6">//   246 003d131e 85c0            test    eax,eax</s=
pan>
<span class=3D"style6">//   246 003d1320 7407            je      scope_exit=
!test_unique_resource+0x19 (003d1329)</span>
<span class=3D"style6">//   246 003d1322 50              push    eax</span>
<span class=3D"style6">//   246 003d1323 ff1514303d00    call    dword ptr =
[scope_exit!_imp__CloseHandle (003d3014)]</span>
<span class=3D"style6">//   246 003d1329 c3              ret</span>

<span class=3D"style6">////////////////////////////////////////////////////=
///////////////////////////</span>
<span class=3D"style6">////////////////////////////////////////////////////=
///////////////////////////</span>

<span class=3D"style4">const HANDLE</span> INVALID_EVENT_HANDLE =3D <span c=
lass=3D"style4">static_cast</span>&lt;<span=20
            class=3D"style4">HANDLE</span>&gt;(<span class=3D"style4">nullp=
tr</span>);
<span class=3D"style4">void</span> <span class=3D"style2">test_scoped_resou=
rce</span>(...)   <span=20
            class=3D"style6"> //... added to prevent inlining</span>
{
    <span class=3D"style6">// Create an event which will be closed on scope=
-exit, if NOT NULL.  It can be passed to SetEvent/WFSO as hEvent</span>
    <span class=3D"style4">auto</span> hEvent =3D <span class=3D"style4">st=
d</span>::<span=20
            class=3D"style2">make_scoped_resource</span>(<span class=3D"sty=
le2">CreateEvent</span>(<span=20
            class=3D"style4">nullptr</span>, TRUE, FALSE, <span class=3D"st=
yle4">nullptr</span>), <span=20
            class=3D"style2">CloseHandle</span>, INVALID_EVENT_HANDLE);
}

<span class=3D"style6">// Object Code: (57 bytes, 3 prologue bytes and 3 ep=
ilogue bytes, </span><span=20
            class=3D"style7">to allow for scoped_resource (12 bytes, aligne=
d) on the stack</span><span=20
            class=3D"style6">, + 1 for ret)</span>
<span class=3D"style6">// scope_exit!test_scoped_resource [scope_exit.cpp @=
 250]:</span>
<span class=3D"style6">//   250 003d1330 55              push    ebp</span>
<span class=3D"style6">//   250 003d1331 8bec            mov     ebp,esp</s=
pan>
<span class=3D"style6">//   250 003d1333 83ec0c          sub     esp,0Ch</s=
pan>
<span class=3D"style6">//   252 003d1336 6a00            push    0</span>
<span class=3D"style6">//   252 003d1338 6a00            push    0</span>
<span class=3D"style6">//   252 003d133a 6a00            push    0</span>
<span class=3D"style6">//   252 003d133c 6a01            push    1</span>
<span class=3D"style6">//   252 003d133e 6a00            push    0</span>
<span class=3D"style6">//   252 003d1340 ff1510303d00    call    dword ptr =
[scope_exit!_imp__CreateEventW (003d3010)]</span>
<span class=3D"style6">//   252 003d1346 8b0d14303d00    mov     ecx,dword =
ptr [scope_exit!_imp__CloseHandle (003d3014)]</span>
<span class=3D"style6">//   252 003d134c 8bd0            mov     edx,eax</s=
pan>
<span class=3D"style6">//   252 003d134e 8d45f4          lea     eax,[ebp-0=
Ch]</span>
<span class=3D"style6">//   252 003d1351 e83a060000      call    scope_exit=
!std::make_scoped_resource&lt;int (__stdcall*)(void *),void *&gt; (003d1990=
)</span>
<span class=3D"style6">//   253 003d1356 8b45f8          mov     eax,dword =
ptr [ebp-8]</span>
<span class=3D"style6">//   253 003d1359 83c404          add     esp,4</spa=
n>
<span class=3D"style6">//   253 003d135c 3b45fc          cmp     eax,dword =
ptr [ebp-4]</span>
<span class=3D"style6">//   253 003d135f 7404            je      scope_exit=
!test_scoped_resource+0x35 (003d1365)</span>
<span class=3D"style6">//   253 003d1361 50              push    eax</span>
<span class=3D"style6">//   253 003d1362 ff55f4          call    dword ptr =
[ebp-0Ch]</span>
<span class=3D"style6">//   253 003d1365 8be5            mov     esp,ebp</s=
pan>
<span class=3D"style6">//   253 003d1367 5d              pop     ebp</span>
<span class=3D"style6">//   253 003d1368 c3              ret</span>
</pre></code>

<h3>Reference Implementation</h3>
<ul>
<li><a href=3D"http://www.andrewlsandoval.com/scope_exit/scope_exit.h">http=
://www.andrewlsandoval.com/scope_exit/scope_exit.h</a> : <code><b>&lt;scope=
_exit&gt;</b></code> header file</li>
<li><a href=3D"http://www.andrewlsandoval.com/scope_exit/scope_exit.cpp">ht=
tp://www.andrewlsandoval.com/scope_exit/scope_exit.cpp</a> : <code><b>scope=
_exit.cpp</b></code> file with tests</li>
<ul><li>Compiles on Windows x86 and x64, using Visual Studio 2010+ and MinG=
W g++ 4.7</li>
<li>Should compile on other platforms if Windows specific APIs are not used=
</li></li></ul>=20
</ul>
<h3>Scope</h3>
As demonstrated above, the scope of this proposal is intended to provide th=
e 4 new classes and 3 new function templates (as a generator for those=20
        the first three classes), to allow wrapping any type of resource or=
 code block in an object that ensures execution or clean-up=20
        of a resource on scope exit.  There will be no impact on users that=
 opt not to use <code>scope_exit</code>.  Otherwise the impact and scope sh=
ould be much the same as the impact and scope of <code>unique_ptr</code>, o=
nly=20
        with the intended use focused on non-pointer resources, and pointer=
 based=20
        resources for which one of these wrappers may be a better fit than =
<code>unique_ptr</code>.

<h3>Final Notes on Motivations and Scope:</h3>
NOTE: Despite similarity in name, this proposal is not related to Boost's S=
cope.Exit.  Though the goals are similar Scope.Exit uses macros to achieve =
its goals.

<h2>IV.  Impact on Standard</h2>
This proposal is a pure library extension. It proposes adding a new header,=
 <code>&lt;scope_exit&gt;</code>, but it does not require changes to any st=
andard classes or functions. It does not require any changes in the core la=
nguage, and it has been implemented in standard C++ conforming to c++11. Th=
e proposal does not depend on any other library extensions.  The reference =
implementation utilizes the standard <code>&lt;utility&gt;</code>=20
    header, for <code>std::move</code>, as well as <code>&lt;type_traits&gt=
;</code> for <code>std::remove_pointer</code>, and <code>std::add_reference=
</code>.
<h2>V.  Design Decisions</h2>
<h3>A.  General Principles</h3>
<ol>
<li>Simplicity</li>
<blockquote>Using an RAII resource wrapper should be as easy as using a raw=
 data=20
    type. Generally the cast operator accomplishes this goal.&nbsp; The <co=
de>get()</code> method=20
    would be a reasonable alternative to the cast operator if it were to me=
et with insurmountable opposition.&nbsp;=20
    Other operators are also provided to simplify usage in a natural manner=
 for the wrapped resource.</blockquote>
<blockquote>Simple construction and generation should encourage use of the =
wrappers over raw resource types. This is as true when resources are used w=
ithin functions and methods as it is when the wrappers are used in objects =
designed to encapsulate and provided additional related functionality aroun=
d the resource in a class.</blockquote>
<blockquote>The "generator" function templates <code>make_scoped_function</=
code>, and <code>make_scoped_resource</code> help ensure simplicity.</block=
quote>
<blockquote>Though macros are generally frowned upon, the <code>UNIQUE_DELE=
TER</code> macro used to simplify the passing of template parameters to <co=
de>unique_resource</code>, can also claim to improve simplicity.
  Unlike other macros, it does not hide functionality -- instead it draws a=
ttention to the the template arguments that matter most.  The end result is=
 a very easy to use and understand <code>unique_resource</code>.</blockquot=
e>
<blockquote>Code written with these RAII wrappers becomes simple to maintai=
n.  Lifetime of resources and their method of clean-up is evident from the =
time of declaration or generation.  The order of operations in clean-up is =
expected and simple.  And object lifetime is managed by scope rather than t=
he hopefully correct ordering of clean-up at scope-exit or in traditional d=
estructors.</blockquote>
<li>Transparency</li>
<blockquote>It should be obvious from a glance what each RAII resource wrap=
per does.  Constructors and generator function templates should clearly sho=
w the binding of the resource's clean-up to the resource.&nbsp;=20
    Similarly a glance at a <code>scoped_function</code> should make it obv=
ious what will happen when the object reaches scope exit.</blockquote>
<li>Resource Conservation and Lifetime Management</li>
<blockquote>Each wrapper is designed to encourage consideration of a resour=
ce's lifetime when it is created.  The cost of using these wrappers should =
not out weigh the benefits.</blockquote>
<li>Generated Object Code Size</li>
<blockquote>Code bloat should be avoided, and options should exist to minim=
ize generated object code size.  These wrappers should be usable in resourc=
e constrained environments.</blockquote>
<li>Exception Safety</li>
<blockquote>These RAII resource wrappers should be able to be used without =
introducing any new risk of throwing exceptions due to allocation failures,=
 etc.  They should be usable for example in kernel code where C++ exception=
s often can't be handled.</blockquote>
<blockquote>Both types of RAII wrappers that allow for a vailidity check (<=
code>scoped_resource</code>, and <code>unique_resource</code>) default to a=
 <b>nothrow</b> implementation.  Each also offer a=20
    simple means by which <code>failed_resource_initialization</code> may b=
e thrown on construction when a validity check fails.&nbsp;=20
    This provides the broadest opportunity for use, and adaptation to the u=
sers=20
    needs.</blockquote>
<li>Use of Lambdas</li>
<blockquote>These RAII resource wrappers should allow for the use of lambda=
s with and without capturing.&nbsp;=20
    Because lambda&#39;s may be used to capture by reference, these RAII wr=
appers can utilize or update references just prior to scope-exit, etc.&nbsp=
; Lambda's also provide a means of adding logic to deleter "functions", and=
 of returning status from a deleter function.</blockquote>
</ol>
<p>B.&nbsp; Prior implementations</p>
<ol>
<li>RAIIFunction and RAIIWrapper</li>
<blockquote><code>RAIIFunction</code> and <code>RAIIWrapper</code> have bee=
n in shipping commercial products.  They were initially posted to std-propo=
sals to begin the discussion leading to this proposal.  <code>RAIIWrapper</=
code> is very similar to <code>unique_resource</code>.
  <code>RAIIFunction</code> was original designed to inherit from <code>std=
::function&lt;void ()&gt;</code>, and was later changed to use the same in =
composition.  This class was posted to the Boost Developer mailing list, wh=
ere encouragement and feedback where given on possible inclusion in Boost. =
 It was noted however that <code>std::function</code> can throw on an alloc=
ation failure.  This was mentioned when posting to the std-proposals list, =
and=20
  the current solution -- of using template types (and generator function t=
emplates) instead of <code>std::function&lt;void ()&gt;</code> was recommen=
ded by one of the list participants (DeadMG).  <code>scoped_function</code>=
, <code>scoped_resource_unchecked</code>, and <code>scoped_resource</code> =
along with their <code>make_scoped_function</code> and <code>make_scoped_re=
source()</code> generators are the result of reworking <code>RAIIFunction</=
code> based on feedback from the group in general.
  The result is a much more usable set of classes, where lambda's can be us=
ed to clean-up resources with or without capturing, etc.
</blockquote>
<li>Boost Scope.Exit</li>
<blockquote>
During discussion on the Boost Developer mail list, attention was drawn to =
the Boost Scope.Exit library.  This library uses macros to provide the abil=
ity to execute clean-up code on scope exit.  For the purposes of this propo=
sal, macros have been avoided, other than the very simple <code>UNIQUE_DELE=
TER</code> macro that is used only for template parameters.  Macros often h=
ide details, including from debuggers, that can be crucial to understand an=
d troubleshooting problems.  For that reason, and because of the general di=
staste for macros in C++, Boost Scope.Exit was not considered for this prop=
osal. =20
That should not be in anyway interpreted as disrespect to the author of Boo=
st Scope.Exit, as it was designed to work with earlier C++ compilers that l=
ack C++11 support.  It should also be noted that the Boost Scope.Exit docum=
entation also includes a suggested alternative for a class compositing <cod=
e>std::function&lt;void (void)&gt;</code><sub><b><a href=3D"#reference1">1<=
/a></b></sub>.
</blockquote>
<li>std::unique_ptr</li>
<blockquote>During discussions on the std-proposal list, many examples were=
 given, and some suggestions that <code>std::unique_ptr</code> is sufficien=
t and additional RAII classes are not needed.  This proposal rejects those =
suggestions. =20
Though <code>std::unique_ptr</code> is vital to the Standard Library it is =
designed to work with pointers, not resources of other types.
Converting resources, whether they are <code>int</code>'s of a file descrip=
tors, or other non-pointer types isn't straightforward -- and requires that=
 the deleter be able to dereference the pointer.  That would rule out use w=
ith many functions, unless the deleter function was first wrapped in a lamb=
da or another function or functor for that purpose.
  Additionally, <code>std::unique_ptr</code> does not provide a cast operat=
or to allow natural use of the wrapped resource in API calls, etc.
</blockquote>
<li>ScopeGuard</li>
<blockquote>
An article<sub><b><a href=3D"#reference2">2</a></b></sub> written by Andrei=
 Alexandrescu and Petru Marginean, published by Dr. Dobbs Magazine in Decem=
ber 2000 introduces a class called <code>ScopeGuard</code>, which is very s=
imilar to <code>scope_resource_uc</code> as presented in the reference impl=
ementation associated with this proposal.
</blockquote>

</ol>
<p>C.&nbsp; Risks</p>
<blockquote>
The cast operator provided by each of the classes does pose a minor risk.  =
For example, if a confused user where to try to to mix the <code>make_scope=
d_resource()</code> call with construction of a <code>unique_resource</code=
>, the cast operator will allow initialization of <code>unique_resource</co=
de>,=20
but the return of the <code>make_scoped_resource()</code> will result in a =
temporary object, which after transfering the wrapped resource to the <code=
>unique_resource</code> will then be "deleted" by the deleter function pass=
ed to <code>make_scoped_resource</code>.  This would lead to the deleter be=
ing invoked more than once, and the resource being used after deletion.
  This is a minor risk.  The template parameters to <code>unique_resource</=
code> should make it obvious that it does not match up to <code>make_scoped=
_resource()</code>.
</blockquote>

<h2>VI.  Technical Specifications</h2>
<h3>Header</h3>
Add an extra row to table 44
<center>
<table border>
<caption>Table 44 &mdash; General utilities library summary</caption>
<tr><td>Subclause</td><td>Header(s)</td>
<tr><td>20.14  Scoped resources</td><td><code>&lt;scoped_resource&gt;</code=
></td>
</tr>
</tr>
</table>
</center>
<h3>20.14  Scoped resources</h3>
<h3>20.14.1  Class template <code>scoped_function</code></h3>
<table>
<tr><td>1</td><td>A <i>scoped function</i> is an object <i>s</i> that manag=
es a function object <i>f</i> such that <i>f</i> will be invoked when <i>s<=
/i> is destroyed (e.g., when leaving block scope (6.7)).</td></tr>
<tr><td>2</td><td>The function object managed by <code>scoped_function&lt;T=
&gt;</code> takes no parameters, so that <i>s</i> may invoke <i>f</i> as <c=
ode>f();</code>.</td></tr>
<tr><td>3</td><td><i>f</i> may be a function pointer, functor, callable fun=
ction as returned from <code>std::bind</code>, or a lambda=20
    taking no parameters.</td></tr>
</table>
<code>
<pre>
namespace std
{
    template&lt;typename T&gt; class scoped_function
    {
    public:
        // 20.14.1.1 constructors
        explicit scoped_function(T&& f) noexcept;
        explicit scoped_function(const T& f) noexcept;

        // 20.14.1.2 destructor
        ~scoped_function();

        // 20.14.1.3 modifiers
        scoped_function& release() noexcept();
        scoped_function& reset(T&& f);
        scoped_function& reset(const T& f);
        scoped_function& invoke(bool bRelease =3D true);
        void operator()();

        // 20.14.1.4 assignment
        void operator=3D(T&& f) noexcept;
        void operator=3D(const T& f) noexcept;
    };

    // 20.14.1.5 generator
    // Make a scoped_function
    // Takes 1 parameter - the function to be run on scope exit...
    template&lt;typename T&gt; scoped_function&lt;T&gt; make_scoped_functio=
n(T f) noexcept;
    {
        return scoped_function&lt;T&gt;(std::move(f));
    }
}
</pre>
</code>
<p>
<h4>20.14.1.1 scoped_function constructors</h4>
The <code>scoped_function</code> constructors take one argument, the type o=
f which must be a callable function taking no parameters.  It is intended t=
hat <code>std::make_scoped_function( f )</code> be used to generate a <code=
>scoped_function</code>, as in the following examples:
<code><pre>
//
// Using a lambda:
auto logOnScopeExit =3D std::make_scoped_function([&syslog, &someStateVaria=
ble]() ->void
{
    syslog &lt;&lt; "Exiting with state: " &lt;&lt; someStateVariable;
});

//
// Using a function:
// e.g. void SetFinalStatus();
auto setFinalStatus =3D std::make_scoped_function(SetFinalStatus);

//
// Using bind
auto closeFile =3D std::make_scoped_function( std::bind(close, fd) );     /=
/ std::bind may throw
</pre></code>

</p>
<h4>20.14.1.2 scoped_function's destructor</h4>
The <code>scoped_function</code> destructor will invoke the function object=
 passed to the constructor, as long as the <code>scoped_function</code> has=
 not been "released" via a call to <code>release()</code>, or <code>invoke(=
true)</code>.

<h4>20.14.1.3 scoped_function's modifiers</h4>
<ul>
<li><code>release()</code> instructs <code>scoped_function</code> that the =
function passed to the constructor (or reset / assignment operators) is not=
 to be called when the destructor is invoked.</li>
<li><code>reset()</code> accepts a new function, function object, or lambda=
 to be called when the <code>scoped_function</code> destructor is invoked. =
 The argument is the same as what is accepted by the constructors.  Resetin=
g the function also resets the state of a previously "released" <code>scope=
d_function</code></li>
<li><code>invoke(true)</code> performs an early (pre-destructor) invocation=
 of the function passed to the constructor, reset method, or assignment ope=
rator.  The default true parameter sets the <code>scoped_function</code> to=
 the "released" state so that the function will not be invoked again when t=
he destructor is called.</li>
<li><code>invoke(false)</code> performs an early (pre-destructor) invocatio=
n of the function passed to the constructor, reset method, or assignment op=
erator.  The false parameter leaves the <code>scoped_function</code> in the=
 "unreleased" state so that the function <b>will</b> be invoked again when =
the destructor is called.</li>
<li><code>operator()()</code> performs an early (pre-destructor) invocation=
 of the function passed to the constructor, the same as if <code>invoke(tru=
e)</code> had been called.</li>
</ul>

<h4>20.14.1.4 scoped_function's assignment operators</h4>
The assignment operator invokes <code>reset()</code> to replace the functio=
n that will be invoked when the destructor is called.  The object is set to=
 the "unreleased" state so that even if <code>release()</code>, or <code>in=
voke(true)</code> had been previously called, the new function will be invo=
ked when the destructor is called.

<h4>20.14.1.5 <code>make_scoped_function</code></h4>
<code>make_scoped_function(func)</code> is used to generate a <code>scoped_=
function</code> object.

<h3>20.14.2  Class template <code>scoped_resource_unchecked</code></h3>
<table>
    <tr><td>1</td><td>A <i>scoped_resource_unchecked</i> is an object <i>s<=
/i> that manages a generic resource <i>r</i> such that a clean-up function,=
 function object, or lambda, <i>f(r)</i> will be invoked when <i>s</i> is d=
estroyed (e.g., when leaving block scope (6.7)).</td></tr>
    <tr><td>2</td><td>The function object <i>f</i> managed by <code>scoped_=
resource_unchecked&lt;TDel,=20
        TRes&gt;</code> takes a single parameter of the type of the resourc=
e <i>r</i> so that <i>s</i> may invoke <i>f(r)</i> as <code>f(r);</code>, w=
hen <i>s</i> leaves the current scope.</td></tr>
    <tr><td>3</td><td><i>f</i> may be a function pointer, functor, a callab=
le function as returned from <code>std::bind</code>, or a lambda, taking a =
single argument of the type of the resource.</td</tr>
    <tr><td>4</td><td><i>r</i> may be accessed through cast operators as if=
 it were of the type of the resource <i>r</i>.</td></tr>
    <tr><td>5</td><td>Unlike scoped_resource, <i>r</i> is not compared to a=
 "no-delete value" prior to the invocation of <code>f(r)</code>.</td></tr>
    <tr><td>6</td><td>A <code>scoped_resource_unchecked</code> may be gener=
ated (is intended to be generated) using <code>make_scoped_resource(r, f)</=
code></td></tr>
</table>
<code>
<pre>
namespace std
{
    template&lt;typename TDel, typename TRes&gt; class scoped_resource_unch=
ecked
    {
    public:
        // 20.14.2.1 constructors
        explicit scoped_resource_unchecked(TDel&& arg, TRes&& resource) noe=
xcept;
        explicit scoped_resource_unchecked(const TDel& arg, const TRes& res=
ource) noexcept;

        // 20.14.2.2 destructor
        ~scoped_resource_unchecked();

        // 20.14.2.3 modifiers
        scoped_resource_unchecked& release() throw();
        scoped_resource_unchecked& reset(TRes&& resource);
        scoped_resource_unchecked& reset(const TRes& resource);
        scoped_resource_unchecked& invoke(bool bRelease =3D true);
        void operator()();

        // 20.14.2.4 access
        TRes get() const throw();
        operator TRes() const throw();
        TRes operator-&gt;() const;
        TRes* operator&();
        TDel& get_deleter();
        const TDel& get_deleter() const;
    };

    // 20.14.2.5 Specific Generator
    // Make a scoped_resource_unchecked (unchecked)
    // Takes 2 arguments: The resource and the deleter
    template&lt;typename TDel, typename TRes&gt;
    scoped_resource_unchecked&lt;TDel, TRes&gt; make_scoped_resource_unchec=
ked(TRes r, TDel d) throw()    // Specific request
    {
        return scoped_resource_unchecked&lt;TDel, TRes&gt;(std::move(d), st=
d::move(r));
    }

    // 20.14.2.6 Generic Generator
    template&lt;typename TDel, typename TRes&gt;
    scoped_resource_unchecked&lt;TDel, TRes&gt; make_scoped_resource(TRes r=
, TDel d) throw()              // Generic request
    {
        return scoped_resource_unchecked&lt;TDel, TRes&gt;(std::move(d), st=
d::move(r));
    }
}
</pre>
</code>
<p>
<h4>20.14.2.1 scoped_resource_unchecked constructors</h4>
The <code>scoped_resource_unchecked</code> constructors take two arguments.=
 The type of the first must be a callable function taking a single paramete=
r of the type of the second template argument.  It is intended that <code>s=
td::make_scoped_resource(resource, deleter)</code> be used to generate a <c=
ode>scoped_resource_unchecked</code>, as in the following examples:
<code><pre>
//
// Most common usage - close "handle" types on scope-exit, using a function=
....
extern PACCESS_TOKEN PsReferencePrimaryToken(IN PEPROCESS pProcess);    // =
Assumption: Always returns a valid value that can be passed to ObDerference=
Token
extern void ObDereferenceToken(PACCESS_TOKEN pToken);                   // =
Deleter: Handles any value (including nullptr) from PsReferencePrimaryToken=
()

// Manual Construction (not intended):
std::scoped_resource_unchecked&lt;decltype(&ObDereferenceToken), PACCESS_TO=
KEN&gt; pToken(PsReferencePrimaryToken(PsGetCurrentProcess(), ObDereference=
Token));

// Construction via Generic Generator (preferred method) (see 20.14.2.6):
auto pToken =3D std::make_scoped_resource(PsReferencePrimaryToken(PsGetCurr=
entProcess(), ObDereferenceToken));

//
// Using a lambda:
extern PACCESS_TOKEN PsReferencePrimaryToken(IN PEPROCESS pProcess);    // =
Assumption: Always returns a valid value that can be passed to ObDerference=
Token
extern void ObDereferenceObject(PVOID pObject);                         // =
Generic deleter
auto pToken =3D std::make_scoped_resource(PsReferencePrimaryToken(PsGetCurr=
entProcess()), [](PACCESS_TOKEN pToken) ->void
{
    if(pToken =3D=3D nullptr)
    {
        syslog &lt;&lt; "Warning, closing nullptr primary token on scope-ex=
it!!!";
    }
    ObDereferenceObject(pToken);
});

//
// Using bind
extern void * VirtualAllocGuaranteed(PVOID pPreferredBaseAddr, size_t szSiz=
e, unsigned int flags, unsigned int pageProtection);  // System API that al=
ways returns usable pointer (even if nullptr / page zero)
extern void VirtualFree(void *pAddress, size_t size, unsigned int freeFlags=
);       // Generic System API for releasing, freeing, etc. virtual memory

auto pVirtMem =3D std::make_scoped_resource(VirtualAllocGuaranteed(nullptr,=
 4096, MEM_COMMIT|MEM_RESERVE, PAGE_READWRITE),
    std::bind(VirtualFree, _1, 0, MEM_RELEASE));
</pre></code>

</p>
<h4>20.14.2.2 scoped_resource_unchecked's destructor</h4>
The <code>scoped_resource_unchecked</code> destructor will invoke the "dele=
ter" function object passed to the constructor, passing it the=20
        tracked resource, as long as the <code>scoped_resource_unchecked</c=
ode> has not been "released" via a call to <code>release()</code>, or <code=
>invoke(true)</code>.  By this means the resource clean-up is carried out b=
y the "deleter" function on scope-exit or unwind.

<h4>20.14.2.3 scoped_resource_unchecked's modifiers</h4>
<ul>
<li><code>release()</code> prevents the <code>scoped_resource_unchecked</co=
de> from=20
    invoking the &quot;deleter&quot; function in the destructor.</li>
<li><code>reset(resource)</code> causes the <code>scoped_resource_unchecked=
</code> to invoke the "deleter" function for any currently tracked resource=
 that has not been "released", and assigns a new resource to the <code>scop=
ed_resource_unchecked</code> to be tracked.  The <code>scoped_resource_unch=
ecked</code> will be set to an "un-released" state when a new resource is a=
ssigned.</li>
<li><code>invoke(true)</code> performs an early (pre-destructor) invocation=
 of the "deleter" function.  The=20
    <em>default</em> true parameter sets the <code>scoped_resource_unchecke=
d</code> to the "released" state so that the deleter function will not be i=
nvoked again when the destructor is called, unless the object is subsequent=
ly "reset."</li>
<li><code>invoke(false)</code> performs an early (pre-destructor) invocatio=
n of the "deleter" function.  The false parameter leaves the <code>scoped_r=
esource_unchecked</code> in the "un-released" state so that the deleter fun=
ction <b>will</b> be invoked again when the destructor is called.</li>
<li><code>operator()()</code> performs an early (pre-destructor) invocation=
 of the deleter function, the same as if <code>invoke(true)</code> had been=
 called.</li>
</ul>

<h4>20.14.2.4 scoped_resource_unchecked's accessors</h4>
<ul>
<li><code>TRes get() const throw()</code> returns the resource being manage=
d by the <code>scoped_resource_unchecked</code> object.</li>=20
<li><code>operator TRes() const throw()</code> returns the resource being m=
anaged by the <code>scoped_resource_unchecked</code> object.</li>=20
<li><code>TRes operator-&gt;() const</code> returns the resource being mana=
ged by the <code>scoped_resource_unchecked</code> object.</li>
<li><code>TRes* operator&()</code> returns a pointer to the resource being =
managed by the <code>scoped_resource_unchecked</code> object, where the <co=
de>scoped_resouce_unchecked</code> has a private member of type <code>TRes<=
/code> such as <code>TRes m_resource;</code> which is returned from this ac=
cessor with <code>return &m_resource;</code></li>
<li><code>TDel& get_deleter()</code> returns a reference to the deleter fun=
ction.=20
    This allows the caller to modify the deleter function if needed on a no=
n-const=20
    object.</li>
<li><code>const TDel& get_deleter() const</code> returns a reference to the=
 deleter=20
    function.</li>
</ul>

<h4>20.14.2.5 <code>make_scoped_resource_unchecked</code></h4>
<code>make_scoped_resource_unchecked(resource, deleterfunc)</code> is used =
to generate a <code>scoped_resource_unchecked</code> object.&nbsp;=20
        See the examples above in 20.14.2.1.

<h4>20.14.2.6 <code>make_scoped_resource</code></h4>
<code>make_scoped_resource(resource, deleterfunc)</code> is used to generat=
e a <code>scoped_resource_unchecked</code> object in a manner that is compa=
tible with the generation of a <code>scoped_resource</code> object.  The di=
fference between the generator for a <code>scoped_resource_unchecked</code>=
 object and the generator for a <code>scoped_resource</code> is that the <c=
ode>scoped_resource</code> requires a 3rd parameter that is used for validi=
ty checking prior to invoking the deleter function.  Also, <code>scoped_res=
ource</code> can be controlled through template parameters to <code>throw f=
ailed_resource_initialization();</code> when it is constructed with a resou=
rce that matches the "no-delete" value.

<h3>20.14.3  Addition of <code>std::failed_resource_initialization exceptio=
n</code></h3>
It is necessary to add an exception to the standard library to be thrown wh=
en invalid resources are assigned (or passed to the constructor) of a <code=
>scoped_resource</code> or <code>unique_resource</code> object.  The follow=
ing is an example implementation.

<pre>
<code>
namespace std
{
    ///////////////////////////////////////////////////////////////////////=
/////
    // failed_resource_initialization
    // An exception thrown when a no-delete value is passed to a scoped_res=
ource
    // or unique_resource constructor, assignment, or reset IF the template
    // arguments allow for throwing.  Throwing is optional so that these cl=
asses
    // may be used in environment where exception can not be handled (e.g.
    // kernel drivers, etc.)  In those cases the resource should be validat=
ed
    // using .valid() prior to use.
    ///////////////////////////////////////////////////////////////////////=
/////
    class failed_resource_initialization : public exception
    {
    public:
        explicit failed_resource_initialization(const char * =3D nullptr) t=
hrow()
        {
        }

        virtual const char * what() const throw()
        {
            return "resource initialization failed";
        }
    };
}
</code>
</pre>

<h3>20.14.4  Class template <code>scoped_resource</code></h3>
<table>
    <tr><td>1</td><td>A <i>scoped_resource</i> is an object <i>s</i> that m=
anages a generic resource <i>r</i> such that a clean-up function, function =
object, or lambda, <i>f(r)</i> will be invoked when <i>s</i> is destroyed (=
e.g., when leaving block scope (6.7)), as long as the resource passes a val=
idity check.</td></tr>
    <tr><td>2</td><td>The function object <i>f</i> managed by <code>scoped_=
resource&lt;TDel,=20
        TRes, const bool throw_on_init_failure =3D false&gt;</code> takes a=
 single parameter of the type of the resource <i>r</i> so that <i>s</i> may=
 invoke <i>f(r)</i> as <code>f(r);</code>, when <i>s</i> leaves the current=
 scope=20
        or is otherwise destructed.</td></tr>
    <tr><td>3</td><td><i>f</i> may be a function pointer, functor, a callab=
le function as returned from <code>std::bind</code>, or a lambda, taking a =
single argument of the type of the resource.</td</tr>
    <tr><td>4</td><td><i>r</i> may be accessed through cast operators as if=
 it were of the type of the resource <i>r</i>.</td></tr>
    <tr><td>5</td><td>Unlike scoped_resource_unchecked, <i>r</i> <b>is</b> =
compared to a "no-delete value" prior to the invocation of <code>f(r)</code=
>.</td></tr>
    <tr><td>6</td><td>A <code>scoped_resource</code> may be generated (is i=
ntended to be generated) using <code>make_scoped_resource(r, f, nd)</code><=
/td></tr>
    <tr><td>7</td><td>The 3rd template parameter, when true, allows the con=
structors to throw if the resource matches the "invalid" or "no-delete" val=
ue.</code></td></tr>
</table>
<code>
<pre>
namespace std
{
    template&lt;typename TDel, typename TRes, const bool throw_on_init_fail=
ure&gt; class scoped_resource
    {
    public:
        // 20.14.4.1 constructors
        explicit scoped_resource(TDel&& arg, TRes&& resource, TRes no_delet=
e_value);
        explicit scoped_resource(const TDel& arg, const TRes& resource, TRe=
s no_delete_value);

        // 20.14.4.2 destructor
        ~scoped_resource();

        // 20.14.4.3 modifiers
        scoped_resource& release() throw();
        scoped_resource& reset(TRes&& resource);
        scoped_resource& reset(const TRes& resource);
        scoped_resource& invoke(bool bRelease =3D true);
        void operator()();

        // 20.14.4.4 access
        TRes get() const throw();
        operator TRes() const throw();
        TRes operator-&gt;() const;
        TRes* operator&();
        TDel& get_deleter();
        const TDel& get_deleter() const;

        // 20.14.4.5 validity checking
        bool valid() const throw();
    };

    // 20.14.4.6 Default Generator Function
    // Takes 3 parameters: The Resource, the Deleter, and a "invalid" or "n=
o-delete" value
    template&lt;typename TDel, typename TRes&gt;
    scoped_resource&lt;TDel, TRes, false&gt; make_scoped_resource(TRes reso=
urce, TDel deleter, TRes nodelete)
    {
       return scoped_resource&lt;TDel, TRes, false&gt;(std::move(deleter), =
std::move(resource), std::move(nodelete));
    }

    // 20.14.4.7 Generator Function for throw_on_init
    template&lt;bool t_throw_on_init_failure, typename T, typename R&gt;
    scoped_resource&lt;T, R, t_throw_on_init_failure&gt; make_scoped_resour=
ce(R r, T t, R nd)
    {
       return scoped_resource&lt;T, R, t_throw_on_init_failure&gt;(std::mov=
e(t), std::move(r), std::move(nd));
    }
}
</pre>
</code>
<p>
<h4>20.14.4.1 scoped_resource constructors</h4>
The <code>scoped_resource</code> constructors take three arguments:
<ol>
<li>The deleter function - a callable function (or lambda) taking a single =
parameter of the type of the second template argument.</li>
<li>The resource to be managed / tracked by the <code>scoped_resource.</cod=
e>
<li>A no-delete or "invalid" value of the type of the resource which may be=
 used for comparision to:
<ul>
<li>Prevent calling the deleter function in the destructor, when the resour=
ce has an invalid value (e.g. -1 for a file descriptor).</li>
<li>Allow a comparision for the valid() method.</li>
<li>Allow a comparision for when throwing an exception is enabled in the co=
nstructor when passed an invalid value.</li>
</ul>
</li>
</ol>It is intended that <code>std::make_scoped_resource(resource, deleter,=
 nodelete)</code> be used to generate a <code>scoped_resource</code>, as in=
 the following examples:
<code><pre>
//
// Most common usage - close "handle" types on scope-exit, using a function=
....
extern HANDLE CreateEventW(PSECURITY_ATTRIBUTES pEventAttributes, BOOL bMan=
ualReset, BOOL bInitialState, PCWSTR pName);
extern void CloseHandle(HANDLE h);
extern int open(const char *pszFilename, int oflags, ...);
extern void close(int iFileDesc);

// Construction via Generic Generator with nullptr check, no-throw option
auto hEvent =3D std::make_scoped_resource(CreateEvent(nullptr, FALSE, FALSE=
, nullptr), CloseHandle, nullptr);
if(hEvent.valid()) // After Initialization check if (hEvent =3D=3D nullptr)

//
// Construction via Generic Generator with nullptr check, throw on allocati=
on failure...
try
{
    auto hEvent =3D std::make_scoped_resource&lt;true&gt;(CreateEvent(nullp=
tr, FALSE, FALSE, nullptr), CloseHandle, nullptr);
}
catch (const std::failed_resource_initialization &e)
{
    // Deal with failure to CreateEvent, IOW hEvent =3D=3D nullptr
}

//
// Construction via Generic Generator with -1 check, no-throw option
auto iFileDesc =3D std::make_scoped_resource(open("/tmp/log.txt", O_WRONLY|=
O_APPEND), close, -1);
if(iFileDesc.valid()) // Check validity
{
    write(iFileDesc, ...);
}

//
// Construction via Generic Generator with -1 check, throw on allocation fa=
ilure
try
{
    auto iFileDesc =3D std::make_scoped_resource&lt;true&gt;(open("/tmp/log=
..txt", O_WRONLY|O_APPEND), close, -1);
    write(iFileDesc, ...);  // Can't get here if allocation failed
}
catch (const std::failed_resource_initialization &e)
{
    // Deal with failure to open file, IOW iFileDesc =3D=3D -1
}
</pre></code>
Note: Manual constuction is also possible with <code>scoped_resource</code>=
 in much the same way as with <code>scoped_resource_unchecked</code>.  Also=
, leaving the decision on whether to throw, or require testing for allocati=
on failures up to the user makes it possible to use <code>scoped_resource</=
code> in places, such as kernel-mode code, where exceptions can not be tole=
rated.

</p>
<h4>20.14.4.2 scoped_resource_unchecked's destructor</h4>
The <code>scoped_resource</code> destructor will invoke the "deleter" funct=
ion object passed to the constructor, passing it the tracked resource, as l=
ong as the <code>scoped_resource</code> has not been "released" via a call =
to <code>release()</code>, or <code>invoke(true)</code>, and if the resourc=
e does not match the no-delete value.  By this means the resource clean-up =
is carried out by the "deleter" function on scope-exit or unwind.

<h4>20.14.4.3 scoped_resource's modifiers</h4>
<ul>
<li><code>release()</code> prevents the <code>scoped_resource</code> from i=
nvoking the &quot;deleter&quot; function in the destructor.</li>
<li><code>reset(resource)</code> causes the <code>scoped_resource</code> to=
 invoke the "deleter" function for any currently tracked <i>and valid</i> r=
esource that has not been "released", and assigns a new resource to the <co=
de>scoped_resource</code> to be tracked.  The <code>scoped_resource</code> =
will be set to the "un-released" state when a new resource is assigned.  Th=
e deleter function does not change.  If the <code>scoped_resource</code> wa=
s constructed with the throw-option, the new resource will be compared to t=
he no-delete value passed to the constructor and <code>std::failed_resource=
_initialization</code> exception will be thrown if it matches.</li>
<li><code>invoke(true)</code> performs an early (pre-destructor) invocation=
 of the "deleter" function <i>for a valid resource</i>.  The <em>default</e=
m> true parameter sets the <code>scoped_resource</code> to the "released" s=
tate so that the deleter function will not be invoked again when the destru=
ctor is called, unless the object is subsequently "reset."</li>
<li><code>invoke(false)</code> performs an early (pre-destructor) invocatio=
n of the "deleter" function <i>for a valid resource</i>.  The false paramet=
er leaves the <code>scoped_resource</code> in the "un-released" state so th=
at the deleter function <b>will</b> be invoked again when the destructor is=
 called.</li>
<li><code>operator()()</code> performs an early (pre-destructor) invocation=
 of the deleter function, the same as if <code>invoke(true)</code> had been=
 called.</li>
</ul>

<h4>20.14.4.4 scoped_resource accessors</h4>
<ul>
<li><code>TRes get() const throw()</code> returns the resource being manage=
d by the <code>scoped_resource</code> object.</li>=20
<li><code>operator TRes() const throw()</code> returns the resource being m=
anaged by the <code>scoped_resource</code> object.</li>=20
<li><code>TRes operator-&gt;() const</code> returns the resource being mana=
ged by the <code>scoped_resource</code> object.</li>
<li><code>TRes* operator&()</code> returns a pointer to the resource being =
managed by the <code>scoped_resource</code> object, where the <code>scoped_=
resouce</code> has a private member of type <code>TRes</code> such as <code=
>TRes m_resource;</code> which is returned from this accessor with <code>re=
turn &m_resource;</code></li>
<li><code>TDel& get_deleter()</code> returns a reference to the deleter fun=
ction. This allows the caller to modify the deleter function if needed on a=
 non-const object.</li>
<li><code>const TDel& get_deleter() const</code> returns a reference to the=
 deleter function.</li>
</ul>

<h4>20.14.4.5 scoped_resource validity checking</h4>
The <code>valid()</code> member may be used to compare the tracked resource=
 to the no-delete value used when constructing the <code>scoped_resource</c=
ode> object.  It returns true if the resource is NOT equal to the no-delete=
 value.

<h4>20.14.4.6 <code>make_scoped_resource - Default Generator Function</code=
></h4>
<code>make_scoped_resource_unchecked(resource, deleterfunc, no_delete_value=
)</code> is used to generate a <code>scoped_resource</code> object.&nbsp;Se=
e the examples above in 20.14.3.1.
The absence of the true bool template parameter indicates that an exception=
 should NOT be thrown if the tracked resource is assigned a value equal to =
the no_delete_value, or in other words, <code>if(resource =3D=3D no_delete_=
value)</code>.  In this case the user is responsible for checking the valid=
ity of the resource via the <code>valid()</code> member function.  This all=
ows <code>scoped_resource</code> to be used in enviroments (such as kernel-=
mode code) where exceptions can not be tolerated.

<h4>20.14.4.7 <code>make_scoped_resource&lt;true&gt; - Generator Function w=
hich allows throws on allocation failure</code></h4>
<code>make_scoped_resource_unchecked&lt;bool&gt;(resource, deleterfunc, no_=
delete_value)</code> is used to generate a <code>scoped_resource</code> obj=
ect.&nbsp;See the examples above in 20.14.3.1.
The bool template parameter indicates whether or not a <code>std::failed_re=
source_initialization</code> exception should be thrown if the tracked reso=
urce is assigned a value equal to the no_delete_value, or in other words:<b=
r/>
<code>if(resource =3D=3D no_delete_value)</code>.

<h3>20.14.5  Class template <code>unique_resource</code></h3>
<table>
    <tr><td>1</td><td>A <i>unique_resource</i> is an object <i>s</i> that m=
anages a generic resource <i>r</i> such that a <i>static</i> clean-up funct=
ion, <i>f(r)</i> will be invoked when <i>s</i> is destroyed (e.g., when lea=
ving block scope (6.7)), as long as the resource passes a validity check.</=
td></tr>
    <tr><td>2</td><td>The clean-up function <i>f</i> managed by <code>uniqu=
e_resource</code> takes a single parameter of the type of the resource <i>r=
</i> so that <i>s</i> may invoke <i>f(r)</i> as <code>f(r);</code>, when <i=
>s</i> leaves the current scope=20
        or is otherwise destructed.</td></tr>
    <tr><td>3</td><td><i>f</i> must be a function that can be passed and in=
voked as a template argument, known at compile time.  The no-delete value m=
ust also be a static value that may be passed and evaluated as a template a=
rgument.  This allows the compiler to generate the least possible amount of=
 code for each <code>unique_resource</code>.</td</tr>
    <tr><td>4</td><td><i>r</i> may be accessed through cast operators as if=
 it were of the type of the resource <i>r</i>.</td></tr>
    <tr><td>5</td><td>Like scoped_resource, <i>r</i> <b>is</b> compared to =
a "no-delete value" prior to the invocation of <code>f(r)</code>.</td></tr>
    <tr><td>6</td><td>There is no generator for <code>unique_resource</code=
>.  It is designed for use in places where a generator is not convenient, a=
nd where the smallest generated code possible is needed.</td></tr>
    <tr><td>7</td><td>The 3rd template parameter, when true, allows the con=
structors to throw if the resource matches the "invalid" or "no-delete" val=
ue.</code></td></tr>
    <tr><td>8</td><td>Convenience macros are provided to simplify the decla=
ration of template parameters.</code></td></tr>
    <tr><td>9</td><td>As shown below, the reference implementation uses an =
implementation-defined class and a set of implementation defined helper cla=
sses to aid in deducing template parameters.  While these classes are not p=
art of the specification, the interfaces they expose must be carried forwar=
d to the actual <code>unique_resource</code> implementation which in this c=
ase inherits from the base class.</td></tr>
</table>
<code>
<pre>
namespace std
{
    // 20.14.5.1 unique_resource_impl
    template&lt;typename TResource, typename TDeleter, TDeleter t_deleter, =
bool throw_on_init_failure, TResource t_nodelete&gt;
    class unique_resource_impl
    {
    private:
        unique_resource_impl(const unique_resource_impl &);
        void operator=3D(const unique_resource_impl &);

    public:
        unique_resource_impl() : m_resource(t_nodelete)    // Allows for op=
erator=3D(TResource) later...
        {
        }

        explicit unique_resource_impl(TResource&& resource) : m_resource(st=
d::move(resource))
        {
            if(throw_on_init_failure && t_nodelete =3D=3D m_resource)
            {
                throw failed_resource_initialization();
            }
        }

        explicit unique_resource_impl(const TResource& resource) : m_resour=
ce(resource)
        {
            if(throw_on_init_failure && t_nodelete =3D=3D m_resource)
            {
                throw failed_resource_initialization();
            }
        }

        ~unique_resource_impl()
        {
            invoke(true);
        }

        unique_resource_impl& release() throw()
        {
            m_resource =3D t_nodelete;
            return *this;
        }

        unique_resource_impl& reset(TResource&& resource)
        {
            invoke(false);        // false because we are going to change i=
t manually here...
            m_resource =3D std::move(resource);
            if(throw_on_init_failure && t_nodelete =3D=3D m_resource)
            {
                throw failed_resource_initialization();
            }
            return *this;
        }

        unique_resource_impl& reset(TResource const& resource)
        {
            invoke(false);        // false because we are going to change i=
t manually here...
            m_resource =3D resource;
            if(throw_on_init_failure && t_nodelete =3D=3D m_resource)
            {
                throw failed_resource_initialization();
            }
            return *this;
        }

        void operator()()
        {
            invoke(true);
        }

        TResource get() const throw()
        {
            return m_resource;
        }

        void operator=3D(TResource &&res)
        {
            reset(res);
        }

        void operator=3D(TResource const &res)
        {
            reset(res);
        }

        //
        // Cast operator - for access to resource
        // WARNING: This can cause make_scoped_resource*(R, T) to return a =
temporary that initializes something else!  Be careful with scope_exit usag=
e!
        // Nevertheless, it provides transparency for API calls, etc.
        operator TResource() const throw()
        {
            return m_resource;
        }

        //
        // operator-&gt; for accessing members on pointer types
        TResource operator-&gt;() const
        {
            return m_resource;
        }

        //
        // operator& for getting the address of the resource - not const!
        TResource* operator&()
        {
            return &m_resource;
        }

        const TDeleter get_deleter() const
        {
            return t_deleter;
        }

        //
        // invoke...(e.g. early invocation), allows for repeated
        // invocation, if bRelease =3D false.  Use with caution!
        unique_resource_impl& invoke(bool bRelease =3D true)
        {
            if(valid())
            {
                t_deleter(m_resource);
                if(bRelease)
                {
                    m_resource =3D t_nodelete;
                }
            }
            return *this;
        }

        //
        // Check for a valid / usable resource
        bool __inline valid() const throw()
        {
            return m_resource !=3D t_nodelete;
        }
    };

    // 20.14.5.2 implementation specific helper classes used to deduce temp=
late parameters
    //
    // Extract First Parameter Type
    //
    template &lt;typename T&gt;
    struct TFuncInfo1;

    #if defined(_WIN32) && !defined(_WIN64)        // Support Microsoft cal=
ling conventions
    template &lt;typename TReturn, typename TParam&gt;
    struct TFuncInfo1&lt;TReturn (__stdcall *)(TParam)&gt;
    {
        typedef TReturn tReturnType;
        typedef TParam tParameter1;
    };

    template &lt;typename TReturn, typename TParam&gt;
    struct TFuncInfo1&lt;TReturn (__cdecl *)(TParam)&gt;
    {
        typedef TReturn tReturnType;
        typedef TParam tParameter1;
    };

    template &lt;typename TReturn, typename TParam&gt;
    struct TFuncInfo1&lt;TReturn (__fastcall *)(TParam)&gt;
    {
        typedef TReturn tReturnType;
        typedef TParam tParameter1;
    };
    #else    // All other compilers
    template &lt;typename TReturn, typename TParam&gt;
    struct TFuncInfo1&lt;TReturn (*)(TParam)&gt;
    {
        typedef TReturn tReturnType;
        typedef TParam tParameter1;
    };
    #endif    // _WIN32 && !_WIN64

    // 20.14.5.3 unique_resource (reference implementation)
    template&lt;typename TDeleter,
        TDeleter t_deleter,
        bool throw_on_init_failure =3D false,        // Set to true if you =
want throw(failed_resource_initialization) when m_resource =3D=3D t_nodelet=
e_value
        typename TFuncInfo1&lt;TDeleter&gt;::tParameter1 t_nodelete_value =
=3D static_cast&lt;typename TFuncInfo1&lt;TDeleter&gt;::tParameter1&gt;(nul=
lptr)&gt;
    struct unique_resource : public
        unique_resource_impl&lt;typename TFuncInfo1&lt;TDeleter&gt;::tParam=
eter1, TDeleter, t_deleter, throw_on_init_failure, t_nodelete_value&gt;=20
    {
        typedef typename TFuncInfo1&lt;TDeleter&gt;::tParameter1 TResource;

        unique_resource() :=20
            unique_resource_impl&lt;typename TFuncInfo1&lt;TDeleter&gt;::tP=
arameter1, TDeleter, t_deleter, throw_on_init_failure, t_nodelete_value&gt;=
()
        {
        }

        unique_resource(TResource &&resource) :=20
            unique_resource_impl&lt;typename TFuncInfo1&lt;TDeleter&gt;::tP=
arameter1, TDeleter, t_deleter, throw_on_init_failure, t_nodelete_value&gt;=
(std::move(resource))
        {
        }

        unique_resource(TResource const &resource) :=20
            unique_resource_impl&lt;typename TFuncInfo1&lt;TDeleter&gt;::tP=
arameter1, TDeleter, t_deleter, throw_on_init_failure, t_nodelete_value&gt;=
(resource)
        {
        }

        void operator=3D(TResource &&resource)
        {
            this-&gt;reset(resource);
        }

        void operator=3D(TResource const &resource)
        {
            this-&gt;reset(resource);
        }
    };

    //
    // 20.14.5.4 unique_resource (specification)
    template&lt;typename TDeleter,
        TDeleter t_deleter,
        bool throw_on_init_failure =3D false,        // Set to true if you =
want throw(failed_resource_initialization) when m_resource =3D=3D t_nodelet=
e_value
        typename TFuncInfo1&lt;TDeleter&gt;::tParameter1 t_nodelete_value =
=3D static_cast&lt;typename TFuncInfo1&lt;TDeleter&gt;::tParameter1&gt;(nul=
lptr)&gt;
    class unique_resource=20
    {
        typedef typename TFuncInfo1&lt;TDeleter&gt;::tParameter1 TResource;

        // 20.14.5.4.1 - unique_resource constructors
        unique_resource();
        unique_resource(TResource &&resource);
        unique_resource(TResource const &resource);

        // 20.14.5.4.2 - unique_resource destructor
        ~unique_resource();

        // 20.14.5.4.3 - unique_resource modifiers
        unique_resource& release() throw();
        unique_resource_impl& reset(TResource&& resource);
        unique_resource_impl& reset(TResource const& resource);
        unique_resource_impl& invoke(bool bRelease =3D true);
        void operator()();
        void operator=3D(TResource &&resource);
        void operator=3D(TResource const &resource);

        // 20.14.5.4.4 - unique_resource accessors
        TResource get() const throw();
        operator TResource() const throw();
        TResource operator-&gt;() const;
        TResource* operator&();
        const TDeleter get_deleter() const;

        // 20.14.5.4.5 - unique_resource validity checking
        bool __inline valid() const throw();
    };

    //
    // 20.14.5.5 Helper Macros
    // The following macros simplify template parameters for unique_resourc=
e
    #define UNIQUE_DELETER(deleter_fn) decltype(&deleter_fn), deleter_fn, f=
alse
    #define UNIQUE_DELETER_THROW(deleter_fn) decltype(&deleter_fn), deleter=
_fn, true
    #define UNIQUE_DELETER_NOTHROW(deleter_fn) decltype(&deleter_fn), delet=
er_fn, false
}
</pre>
</code>
<p>
<h4>20.14.5.1 The Reference Implementation - <code>unique_resource_impl</co=
de></h4>
The reference implementation is shown above to provide insight on the inten=
ded design of <code>unique_resource</code> with its implementation specific=
 classes the accomodate template deduction.  All code shown in the referenc=
e implementation is provided as an example only and not part of an official=
 specification.  Each actual implemenation will need to supply it's own met=
hods of providing adequate template deduction methods to support constructi=
on of a <code>unique_resource</code> as shown in section 20.14.5.4.1.

<h4>20.14.5.2 Helper Classes</h4>
The classes and template metaprogramming shown here is also provided only a=
s an example so that the definition provided in section 20.14.5.4 makes sen=
se.  These helper classes are implementation specific and are used to allow=
 automatic deducing of the type of the resource being tracked by <code>uniq=
ue_resource</code>.  An implementation that can satisify the construction s=
pecification shown in section 20.14.5.4.1 below may or may not need these h=
elper classes (specifically) <code>TFuncInfo</code>.

<h4>20.14.5.3 The Reference Implentation - <code>unique_resource</code></h4=
>
The reference implementation is shown above to provide insight on the inten=
ded design of <code>unique_resource</code> and how it utilizes template met=
aprogramming to deduce template arguments for the construction of <code>uni=
que_resource</code> and it's implementation specific base class <code>uniqu=
e_resource_impl</code> (20.14.5.1) to satisify the construction specificati=
ons laid out in section 20.14.5.4.1.

<h4>20.14.5.4 <code>unique_resource</code></h4>
<h5>20.14.5.4.1 <code>unique_resource</code> construction</h5>

<code>unique_resource</code> may be constructed using one (1) or zero (0) a=
rguments.  This is possible because the template parameters supplied provid=
e a deleter function used to clean-up the resource on <code>unique_resource=
</code> destruction.  A zero parameter constructor creates an object that h=
as no resource to track until a subsequent assignment or reset.

Template Parameters:
<ol>
<li>The <i>type</i> of the deleter function - a function taking a single pa=
rameter of the <i>type</i> of the resource being tracked.  The resource <i>=
type</i> is deduced from the argument to the deleter function.</li>
<li>The deleter function itself.  A static value that is known at compile t=
ime and can be expressed as a template parameter and invoked in the destruc=
tor by passing the tracked resource as the solitary parameter.</li>
<li>A bool value indicating whether or not the constructor or assignment op=
erator should throw <code>std::failed_resource_initialization</code> if the=
 resource is assigned (or constructed with) a value matching the no-delete =
or "invalid" value.  The no-delete value must be of the <i>type</i> of the =
resource which is deduced from the argument required by the deleter functio=
n.</li>
<li>A no-delete or "invalid" value of the <i>type</i> of the resource being=
 tracked.  This parameter defaults to <code>nullptr</code> after having bee=
n cast (<code>static_cast</code> to the <i>type</i> of the resource.)  The =
no-delete value must be a static value known at compile time that may be pa=
ssed as a template parameter and used in a comparison withing the invoke() =
method or the destructor.</li>
</ol>
</br>
<code>unique_resource</code> is meant to be used in places where:
<ul>
<li><code>make_scoped_resource()</code> is unsuitable or awkward, such as i=
s the case for class member variables that can not be declared as <code>aut=
o</code>.</li>
<li>Where very small (tight) code generation is desired, since the deleter =
function and no-delete value are static values that <i>should not</i> be st=
ored in member variables.</li>
</ul>
</br>
The following are examples of <code>unique_resource</code> objects being co=
nstructed:
<code><pre>
//
// Most common usage - close "handle" types on scope-exit or class destruct=
ion...
extern HANDLE OpenFileW(const wchar_t *pwzFilename);
extern HANDLE CreateEventW(PSECURITY_ATTRIBUTES pEventAttributes, BOOL bMan=
ualReset, BOOL bInitialState, PCWSTR pName);
extern void SetEvent(HANDLE hEvent);
extern void CloseHandle(HANDLE h);
extern int open(const char *pszFilename, int oflags, ...);
extern void close(int iFileDesc);
extern ssize_t pwrite(int iFileDes, const void *pBuf, size_t szBytes, off_t=
 offset);

class MyDataFile
{
private:
    const std::unique_resource&lt;UNIQUE_DELETER(CloseHandle)&gt; m_hWriteS=
ignaledEvent;            // NOTE: Using helper macro
    std::unique_resource&lt;decltype(&CloseHandle), CloseHandle, INVALID_HA=
NDLE_VALUE&gt; m_hFile;  // NOTE: Not using helper macro, also with non-def=
ault no-delete value
    std::unique_resource&lt;UNIQUE_DELETER_NOTHROW(SetEvent)&gt; hSignalThr=
ead;                     // NOTE: In this case we only want a .valid() even=
t handle if it is created/assigned later - using default constructor
    std::vector&lt;unsigned char&gt; m_vData;
public:

    MyDataFile(const wchar_t *pwzFileName) :
        m_hWriteSignaledEvent(CreateEvent(nullptr, FALSE, FALSE, nullptr)),=
     // Note, very simple construction
        m_hFile(OpenFileW(pwzFileName))                                    =
      // Notice that we let m_hSignalThread use the default constructor, it=
 starts with .valid() =3D=3D false
    {
    }
    .
    .
    .
    void SetEventToSignalOnClassDestruction(HANDLE hEvent)
    {
        m_hSignalThread =3D hEvent;           // Contrived example, but sho=
wing assignment operator after default construction...
        // When this class is destroyed, the event handle will be passed to=
 SetEvent.  Also happens to an existing event handle prior to assignment of=
 a new value.
    }

    DWORD WriteOnSignal()
    {
        DWORD dwWait =3D WaitForSingleObject(m_hWriteSignaledEvent, INFINIT=
E);
        if(false =3D=3D m_hFile.valid())        // Use validation method
        {
            return;
        }

        DWORD dwWritten =3D 0;
        if(WAIT_OBJECT_O =3D=3D dwWait)
        {
            WriteFile(m_hFile, &m_vData, m_vData.size(), &dwWritten, nullpt=
r);
        }
        return dwWritten;
    }
};

//
// Example using throw option...
void DumpVector(const char *pszFilename, std::vector&lt;unsigned char&gt; &=
vBuffer, off_t where)
{
    try
    {
        std::unique_resource&lt;UNIQUE_DELETER_THROW(close, -1)&gt; iFileDe=
sc(open(pszFilename, O_RDWR|O_APPEND));
        if(pwrite(iFileDesc, &vBuffer[0], vBuffer.size(), where) !=3D vBuff=
er.size())
        {
            throw write_failed;     // example, not defined here...
        }
    }
    catch (const std::failed_resource_initialization &e)
    {
        // Deal with error (file open failed) condition!
    }
}
</pre></code>

</p>
<h5>20.14.5.4.2 unique_resource's destructor</h5>
The <code>unique_resource</code> destructor will invoke the "deleter" funct=
ion object supplied as a template parameter, passing it the tracked resourc=
e, as long as the <code>unique_resource</code> has not been "released" via =
a call to <code>release()</code>, or <code>invoke(true)</code>, and does no=
t match the no-delete value.  By this means the resource clean-up is carrie=
d out by the "deleter" function on scope-exit or unwind.

<h5>20.14.5.4.3 unique_resource's modifiers</h5>
<ul>
<li><code>release()</code> prevents the <code>unique_resource</code> from i=
nvoking the &quot;deleter&quot; function in the destructor, by assigning th=
e no-delete value to the internally tracked resource.</li>
<li><code>reset(resource)</code> causes the <code>unique_resource</code> to=
 invoke the "deleter" function for any currently tracked <i>and valid</i> r=
esource that has not been "released", and assigns a new resource to the <co=
de>unique_resource</code> to be tracked.  The <code>unique_resource</code> =
will be set to the "un-released" state when a new resource is assigned.  Th=
e deleter function does not change.  If the <code>unique_resource</code> wa=
s constructed with the throw-option, the new resource will be compared to t=
he no-delete value passed to the constructor and <code>std::failed_resource=
_initialization</code> exception will be thrown if it matches.</li>
<li><code>invoke(true)</code> performs an early (pre-destructor) invocation=
 of the "deleter" function <i>for a valid resource</i>.  The <em>default</e=
m> true parameter sets the <code>unique_resource</code> to the "released" s=
tate so that the deleter function will not be invoked again when the destru=
ctor is called, unless the object is subsequently "reset."</li>
<li><code>invoke(false)</code> performs an early (pre-destructor) invocatio=
n of the "deleter" function <i>for a valid resource</i>.  The false paramet=
er leaves the <code>unique_resource</code> in the "un-released" state so th=
at the deleter function <b>will</b> be invoked again when the destructor is=
 called.</li>
<li><code>operator()()</code> performs an early (pre-destructor) invocation=
 of the deleter function <i>for a valid resource</i>, the same as if <code>=
invoke(true)</code> had been called.</li>
<li><code>operator=3D(TResource &&res)</code> performs an early (pre-destru=
ctor) invocation of the deleter function <i>for a valid, assigned resource<=
/i>, and assigns a tracks a new resource the same as if <code>reset(res)</c=
ode> had been called.</li>
<li><code>operator=3D(TResource const &res)</code> performs an early (pre-d=
estructor) invocation of the deleter function <i>for a valid, assigned reso=
urce</i>, and assigns a tracks a new resource the same as if <code>reset(re=
s)</code> had been called.</li>
</ul>

<h5>20.14.5.4.4 unique_resource accessors</h5>
<ul>
<li><code>TResource get() const throw()</code> returns the resource being m=
anaged by the <code>unique_resource</code> object.</li>=20
<li><code>operator TResource() const throw()</code> returns the resource be=
ing managed by the <code>unique_resource</code> object.</li>=20
<li><code>TResource operator-&gt;() const</code> returns the resource being=
 managed by the <code>unique_resource</code> object.</li>
<li><code>TResource* operator&()</code> returns a pointer to the resource b=
eing managed by the <code>unique_resource</code> object, where the <code>un=
ique_resource</code> has a private member of type <code>TResource</code> su=
ch as <code>TResource m_resource;</code> which is returned from this access=
or with <code>return &m_resource;</code></li>
<li><code>const TDeleter& get_deleter() const</code> returns a reference to=
 the deleter function.  The deleter function can not be modified.</li>
</ul>
        // 20.14.5.4.5 - unique_resource validity checking
        bool __inline valid() const throw();

<h5>20.14.5.4.5 unique_resource validity checking</h5>
The <code>valid()</code> member may be used to compare the tracked resource=
 to the no-delete value specified in the template parameters.  It returns t=
rue if the resource is NOT equal to the no-delete value.

<h4>20.14.5.5 Helper Macros</h4>
The following helper macros are defined to simplify the passing of template=
 parameters for <code>unique_resource</code>:
<ul>
<li><code>UNIQUE_DELETER(delter_fn)</code> - supplies the <i>type of</i> th=
e deleter function, and the deleter function parameters, supplying false fo=
r the throw option.</li>
<li><code>UNIQUE_DELETER_THROW(delter_fn)</code> - supplies the <i>type of<=
/i> the deleter function, and the deleter function parameters, supplying tr=
ue for the throw option.</li>
<li><code>UNIQUE_DELETER_NOTHROW(delter_fn)</code> - supplies the <i>type o=
f</i> the deleter function, and the deleter function parameters, supplying =
false for the throw option.</li>
</ul>
For usage examples please see section 20.14.5.4.1.  Use of the macros is no=
t a requirement.  They are provided only to simplify declaration of an othe=
rwise long list of parameters.


<h2>VII.  Acknowledgements</h2>
<ul>
<li>Special thanks and recognition to those on both the Boost Developer mai=
ling list and the ISO C++ std-proposal mailing list for advancing the desig=
n of the classes presented in this proposal and for general encouragement!&=
nbsp;=20
    Also, recognition is due to <a href=3D"http://www.openspan.com/">OpenSp=
an, Inc</a>.=20
    for supporting the production of this proposal and for early adoption a=
nd=20
    testing of the reference implementation and prior implementations of th=
e=20
    proposal in real world (and for that matter world class) products.</li>
</ul>=20
<h2>VIII.  Reference Implemenation</h2>
A <a href=3D"http://www.andrewlsandoval.com/scope_exit/scope_exit.h">refere=
nce implementation</a> may be viewed, downloaded, and used from <a href=3D"=
http://www.andrewlsandoval.com/scope_exit/scope_exit.h">http://www.andrewls=
andoval.com/scope_exit/scope_exit.h</a>.

<h2>IX.  References</h2>
<ol>
<a name=3D"reference1"><li><a href=3D"http://www.boost.org/doc/libs/1_52_0/=
libs/scope_exit/doc/html/scope_exit/alternatives.html">Boost.org, Boost Sco=
pe.Exit: Annex - Alternatives</a></li></a>
<a name=3D"reference2"><li><a href=3D"http://www.drdobbs.com/cpp/generic-ch=
ange-the-way-you-write-excepti/184403758">Dr. Dobbs Magazine, <u>Change the=
 Way You Write Exception-Safe Code =97 Forever</u>, Andrei Alexandrescu and=
 Petru Marginean, December 01, 2000</a></li>
</ol>

</BODY>
</HTML>

------=_Part_2878_7147491.1365803647849--

.


Author: Peter Sommerlad <peter.sommerlad@hsr.ch>
Date: Sat, 13 Apr 2013 13:18:48 +0200
Raw View
the loop advancement example is not very convincing because it can easily b=
e dealt with by using for() instead of while() which is much simpler than t=
he alternative you are proposing.

I also wonder if an local struct with a destructor and a corresponding vari=
able wouldn't be simpler than the scoped example or alternatives like uniqu=
e_ptr or shared_ptr or boost::scoped_ptr that already provide much of the f=
unctionality you are proposing.

The example given as Motivation B calls for a dedicated RAII class for Crit=
icalSection IMHO, so again not very convincing.

IMHO it would greatly improve your paper if you would provide additional ex=
amples showing the "uglyness" of using existing alternatives to your propos=
al, i.e., DIY local structs with destructors, or "misusing" unique_ptr/shar=
ed_ptr for that purpose, in contrast to scoped_function and scoped_resource=
..

Also providing the no-delete value is not very convincing. What if all valu=
es less than zero are "no-delete", or 7, 23 and 42? It complicates the clas=
s and API and doesn't serve a general purpose. Usually a predicate is used =
in other cases to provide a hook for bool checks.

Just my CHF0.02 from a quick scan.

Peter.

On 12.04.2013, at 23:54, Andrew Sandoval <sandoval@netwaysglobal.com> wrote=
:

> I've requested a document number on this but haven't received it yet.  In=
 the meantime I wanted to make sure that the latest version of the document=
 was available for review. It is here: http://www.andrewlsandoval.com/scope=
_exit/scope_exit.h
>=20
> Please be kind.  I'm not sure I am even in the ballpark on the "standarde=
se" section, but it was very painful and time consuming (something I never =
have enough of to start with) to put together.
>=20
> Thank you, and thanks to everyone that has contributed feedback thus far =
on this proposal.
>=20
> -Andrew Sandoval
>=20
> --=20
> =20
> ---=20
> 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.
> Visit this group at http://groups.google.com/a/isocpp.org/group/std-propo=
sals/?hl=3Den.
> =20
> =20
> <proposal.html>

--=20
Prof. Peter Sommerlad

Institut f=FCr Software: Bessere Software - Einfach, Schneller!
HSR Hochschule f=FCr Technik Rapperswil
Oberseestr 10, Postfach 1475, CH-8640 Rapperswil

http://ifs.hsr.ch http://cute-test.com http://linticator.com http://includa=
tor.com
tel:+41 55 222 49 84 =3D=3D mobile:+41 79 432 23 32
fax:+41 55 222 46 29 =3D=3D mailto:peter.sommerlad@hsr.ch





--=20

---=20
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 e=
mail to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposa=
ls/?hl=3Den.



.


Author: Andrew Sandoval <sandoval@netwaysglobal.com>
Date: Mon, 15 Apr 2013 12:38:55 -0700 (PDT)
Raw View
------=_Part_553_7913120.1366054735940
Content-Type: text/plain; charset=ISO-8859-1

On Saturday, April 13, 2013 6:18:48 AM UTC-5, PeterSommerlad wrote:
>
> the loop advancement example is not very convincing because it can easily
> be dealt with by using for() instead of while() which is much simpler than
> the alternative you are proposing.
>
> I can remove that example if there is consensus.  I find it a useful
method of preventing someone from producing a tight loop by accidentally
creating a path in the loop that skips the advancement.

I also wonder if an local struct with a destructor and a corresponding
> variable wouldn't be simpler than the scoped example or alternatives like
> unique_ptr or shared_ptr or boost::scoped_ptr that already provide much of
> the functionality you are proposing.
>
> That horse has been beat to death already in the original thread on this.
The consensus was that these class are useful and serve a different purpose
than unique_ptr.  You will find several that back your view point, but
there is no reason for us to revisit this point.  I didn't put hundreds of
hours into the document after we'd already had that discussion, just to
fight that fight again now.  Please feel free to look at the previous posts.


> The example given as Motivation B calls for a dedicated RAII class for
> CriticalSection IMHO, so again not very convincing.
>
> IMHO it would greatly improve your paper if you would provide additional
> examples showing the "uglyness" of using existing alternatives to your
> proposal, i.e., DIY local structs with destructors, or "misusing"
> unique_ptr/shared_ptr for that purpose, in contrast to scoped_function and
> scoped_resource.
>

Okay, I can definitely consider that.  Anyone concur?

>
> Also providing the no-delete value is not very convincing. What if all
> values less than zero are "no-delete", or 7, 23 and 42? It complicates the
> class and API and doesn't serve a general purpose. Usually a predicate is
> used in other cases to provide a hook for bool checks.
>
> I disagree with that 100%.  In most cases resources -- real resources like
file handles or descriptors, etc. are allocated and have either a 0 /
nullptr or a -1 value on failure  Making the no-delete value simple saves a
lot of duplicate code.


> Just my CHF0.02 from a quick scan.
>
> Peter.
>
> Thank you for your feedback.
Where is everyone else lately?  Is this the week that the committee is in
meetings in Bristol?
-Andrew Sandoval

--

---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/?hl=en.



------=_Part_553_7913120.1366054735940
Content-Type: text/html; charset=ISO-8859-1
Content-Transfer-Encoding: quoted-printable

On Saturday, April 13, 2013 6:18:48 AM UTC-5, PeterSommerlad wrote:<blockqu=
ote class=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;border-left=
: 1px #ccc solid;padding-left: 1ex;">the loop advancement example is not ve=
ry convincing because it can easily be dealt with by using for() instead of=
 while() which is much simpler than the alternative you are proposing.
<br>
<br></blockquote><div>I can remove that example if there is consensus.&nbsp=
; I find it a useful method of preventing someone from producing a tight lo=
op by accidentally creating a path in the loop that skips the advancement.<=
br><br></div><blockquote class=3D"gmail_quote" style=3D"margin: 0;margin-le=
ft: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;">I also wonder if =
an local struct with a destructor and a corresponding variable wouldn't be =
simpler than the scoped example or alternatives like unique_ptr or shared_p=
tr or boost::scoped_ptr that already provide much of the functionality you =
are proposing.
<br>
<br></blockquote><div>That horse has been beat to death already in the orig=
inal thread on this.&nbsp; The consensus was that these class are useful an=
d serve a different purpose than unique_ptr.&nbsp; You will find several th=
at back your view point, but there is no reason for us to revisit this poin=
t.&nbsp; I didn't put hundreds of hours into the document after we'd alread=
y had that discussion, just to fight that fight again now.&nbsp; Please fee=
l free to look at the previous posts.<br>&nbsp;<br></div><blockquote class=
=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;border-left: 1px #cc=
c solid;padding-left: 1ex;">The example given as Motivation B calls for a d=
edicated RAII class for CriticalSection IMHO, so again not very convincing.
<br>
<br>IMHO it would greatly improve your paper if you would provide additiona=
l examples showing the "uglyness" of using existing alternatives to your pr=
oposal, i.e., DIY local structs with destructors, or "misusing" unique_ptr/=
shared_ptr for that purpose, in contrast to scoped_function and scoped_reso=
urce.
<br></blockquote><div>&nbsp;</div><div>Okay, I can definitely consider that=
..&nbsp; Anyone concur? <br></div><blockquote class=3D"gmail_quote" style=3D=
"margin: 0;margin-left: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex=
;">
<br>Also providing the no-delete value is not very convincing. What if all =
values less than zero are "no-delete", or 7, 23 and 42? It complicates the =
class and API and doesn't serve a general purpose. Usually a predicate is u=
sed in other cases to provide a hook for bool checks.
<br>
<br></blockquote><div>I disagree with that 100%.&nbsp; In most cases resour=
ces -- real resources like file handles or descriptors, etc. are allocated =
and have either a 0 / nullptr or a -1 value on failure&nbsp; Making the no-=
delete value simple saves a lot of duplicate code.<br>&nbsp;<br></div><bloc=
kquote class=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;border-l=
eft: 1px #ccc solid;padding-left: 1ex;">Just my CHF0.02 from a quick scan.
<br>
<br>Peter.
<br>
<br></blockquote><div>Thank you for your feedback.<br>Where is everyone els=
e lately?&nbsp; Is this the week that the committee is in meetings in Brist=
ol?<br>-Andrew Sandoval<br></div>

<p></p>

-- <br />
&nbsp;<br />
--- <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 std-proposals+unsubscribe@isocpp.org.<br />
To post to this group, send email to std-proposals@isocpp.org.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/?hl=3Den">http://groups.google.com/a/isocpp.org/group/std-pro=
posals/?hl=3Den</a>.<br />
&nbsp;<br />
&nbsp;<br />

------=_Part_553_7913120.1366054735940--

.


Author: =?ISO-8859-1?Q?Mikael_Kilpel=E4inen?=
Date: Tue, 16 Apr 2013 00:54:39 +0200
Raw View
15.4.2013 21:38, Andrew Sandoval kirjoitti:
>
> Thank you for your feedback.
> Where is everyone else lately?  Is this the week that the committee is
> in meetings in Bristol?

Yes it is.


Mikael

--

---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/?hl=en.



.


Author: Francisco Lopes <francisco.mailing.lists@oblita.com>
Date: Wed, 29 Jan 2014 16:41:25 -0200
Raw View
--001a11c20364c9b7df04f1204922
Content-Type: text/plain; charset=ISO-8859-1

2013-04-15 Andrew Sandoval <sandoval@netwaysglobal.com>

> On Saturday, April 13, 2013 6:18:48 AM UTC-5, PeterSommerlad wrote:
>>
>> the loop advancement example is not very convincing because it can easily
>> be dealt with by using for() instead of while() which is much simpler than
>> the alternative you are proposing.
>>
>> I can remove that example if there is consensus.  I find it a useful
> method of preventing someone from producing a tight loop by accidentally
> creating a path in the loop that skips the advancement.
>
> I also wonder if an local struct with a destructor and a corresponding
>> variable wouldn't be simpler than the scoped example or alternatives like
>> unique_ptr or shared_ptr or boost::scoped_ptr that already provide much of
>> the functionality you are proposing.
>>
>> That horse has been beat to death already in the original thread on
> this.  The consensus was that these class are useful and serve a different
> purpose than unique_ptr.  You will find several that back your view point,
> but there is no reason for us to revisit this point.  I didn't put hundreds
> of hours into the document after we'd already had that discussion, just to
> fight that fight again now.  Please feel free to look at the previous posts.
>
>
>> The example given as Motivation B calls for a dedicated RAII class for
>> CriticalSection IMHO, so again not very convincing.
>>
>> IMHO it would greatly improve your paper if you would provide additional
>> examples showing the "uglyness" of using existing alternatives to your
>> proposal, i.e., DIY local structs with destructors, or "misusing"
>> unique_ptr/shared_ptr for that purpose, in contrast to scoped_function and
>> scoped_resource.
>>
>
> Okay, I can definitely consider that.  Anyone concur?
>

I do, and I feel Peter was not trying to bringing up the previous noise
again, but only, at the end,
to make a point on what should be the focus.


>
>> Also providing the no-delete value is not very convincing. What if all
>> values less than zero are "no-delete", or 7, 23 and 42? It complicates the
>> class and API and doesn't serve a general purpose. Usually a predicate is
>> used in other cases to provide a hook for bool checks.
>>
>> I disagree with that 100%.  In most cases resources -- real resources
> like file handles or descriptors, etc. are allocated and have either a 0 /
> nullptr or a -1 value on failure  Making the no-delete value simple saves a
> lot of duplicate code.
>

Windows WaitForMultipleObjects<http://msdn.microsoft.com/en-us/library/windows/desktop/ms687025%28v=vs.85%29.aspx>is
an example of API that, may not completely fit scoped_resource
scenery,
but may give an idea of the problem. I too, have found that the current
state fits a scenery that's not general
enough, but may cover most cases in the wild... maybe, I can't be sure
about that.


>
>
>> Just my CHF0.02 from a quick scan.
>>
>> Peter.
>>
>> Thank you for your feedback.
> Where is everyone else lately?  Is this the week that the committee is in
> meetings in Bristol?
> -Andrew Sandoval
>

By the way, I'd like to have the newer reference implementations available
in source code form (on github for example)...

Regards,
Francisco Lopes

--

---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

--001a11c20364c9b7df04f1204922
Content-Type: text/html; charset=ISO-8859-1
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr">2013-04-15 Andrew Sandoval <span dir=3D"ltr">&lt;<a href=
=3D"mailto:sandoval@netwaysglobal.com" target=3D"_blank">sandoval@netwaysgl=
obal.com</a>&gt;</span><br><div class=3D"gmail_extra"><div class=3D"gmail_q=
uote"><blockquote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;b=
order-left:1px solid rgb(204,204,204);padding-left:1ex">
<div class=3D"im">On Saturday, April 13, 2013 6:18:48 AM UTC-5, PeterSommer=
lad wrote:<blockquote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8=
ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">the loop advanc=
ement example is not very convincing because it can easily be dealt with by=
 using for() instead of while() which is much simpler than the alternative =
you are proposing.
<br>
<br></blockquote></div><div>I can remove that example if there is consensus=
..=A0 I find it a useful method of preventing someone from producing a tight=
 loop by accidentally creating a path in the loop that skips the advancemen=
t.<br>
<br></div><div class=3D"im"><blockquote class=3D"gmail_quote" style=3D"marg=
in:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1e=
x">I also wonder if an local struct with a destructor and a corresponding v=
ariable wouldn&#39;t be simpler than the scoped example or alternatives lik=
e unique_ptr or shared_ptr or boost::scoped_ptr that already provide much o=
f the functionality you are proposing.
<br>
<br></blockquote></div><div>That horse has been beat to death already in th=
e original thread on this.=A0 The consensus was that these class are useful=
 and serve a different purpose than unique_ptr.=A0 You will find several th=
at back your view point, but there is no reason for us to revisit this poin=
t.=A0 I didn&#39;t put hundreds of hours into the document after we&#39;d a=
lready had that discussion, just to fight that fight again now.=A0 Please f=
eel free to look at the previous posts.<br>
=A0<br></div><div class=3D"im"><blockquote class=3D"gmail_quote" style=3D"m=
argin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left=
:1ex">The example given as Motivation B calls for a dedicated RAII class fo=
r CriticalSection IMHO, so again not very convincing.
<br>
<br>IMHO it would greatly improve your paper if you would provide additiona=
l examples showing the &quot;uglyness&quot; of using existing alternatives =
to your proposal, i.e., DIY local structs with destructors, or &quot;misusi=
ng&quot; unique_ptr/shared_ptr for that purpose, in contrast to scoped_func=
tion and scoped_resource.
<br></blockquote><div>=A0</div></div><div>Okay, I can definitely consider t=
hat.=A0 Anyone concur? <br></div></blockquote><div><br></div><div>I do, and=
 I feel Peter was not trying to bringing up the previous noise again, but o=
nly, at the end,<br>
to make a point on what should be the focus. <br></div><div>=A0</div><block=
quote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-left:1=
px solid rgb(204,204,204);padding-left:1ex"><div></div><div class=3D"im"><b=
lockquote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-le=
ft:1px solid rgb(204,204,204);padding-left:1ex">

<br>Also providing the no-delete value is not very convincing. What if all =
values less than zero are &quot;no-delete&quot;, or 7, 23 and 42? It compli=
cates the class and API and doesn&#39;t serve a general purpose. Usually a =
predicate is used in other cases to provide a hook for bool checks.
<br>
<br></blockquote></div><div>I disagree with that 100%.=A0 In most cases res=
ources -- real resources like file handles or descriptors, etc. are allocat=
ed and have either a 0 / nullptr or a -1 value on failure=A0 Making the no-=
delete value simple saves a lot of duplicate code.<br>
</div></blockquote><div><br></div><div>Windows <a href=3D"http://msdn.micro=
soft.com/en-us/library/windows/desktop/ms687025%28v=3Dvs.85%29.aspx">WaitFo=
rMultipleObjects</a> is an example of API that, may not completely fit scop=
ed_resource scenery,<br>
but may give an idea of the problem. I too, have found that the current sta=
te fits a scenery that&#39;s not general<br>enough, but may cover most case=
s in the wild... maybe, I can&#39;t be sure about that.<br></div><div>=A0</=
div>
<blockquote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-=
left:1px solid rgb(204,204,204);padding-left:1ex"><div>=A0<br></div><div cl=
ass=3D"im"><blockquote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.=
8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">
Just my CHF0.02 from a quick scan.
<br>
<br>Peter.
<br>
<br></blockquote></div><div>Thank you for your feedback.<br>Where is everyo=
ne else lately?=A0 Is this the week that the committee is in meetings in Br=
istol?<span class=3D""><font color=3D"#888888"><br>-Andrew Sandoval<br></fo=
nt></span></div>
</blockquote><div><br></div><div>By the way, I&#39;d like to have the newer=
 reference implementations available in source code form (on github for exa=
mple)...<br><br></div><div>Regards,<br></div><div>Francisco Lopes<br></div>
</div></div></div>

<p></p>

-- <br />
&nbsp;<br />
--- <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 std-proposals+unsubscribe@isocpp.org.<br />
To post to this group, send email to std-proposals@isocpp.org.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

--001a11c20364c9b7df04f1204922--

.


Author: Andrew Sandoval <sandoval@netwaysglobal.com>
Date: Wed, 29 Jan 2014 14:24:32 -0800 (PST)
Raw View
------=_Part_114_5981518.1391034272750
Content-Type: text/plain; charset=UTF-8

On Wednesday, January 29, 2014 12:41:25 PM UTC-6, Francisco Lopes wrote:
>
> 2013-04-15 Andrew Sandoval <sand...@netwaysglobal.com <javascript:>>
>
>> On Saturday, April 13, 2013 6:18:48 AM UTC-5, PeterSommerlad wrote:
>>>
>>> the loop advancement example is not very convincing because it can
>>> easily be dealt with by using for() instead of while() which is much
>>> simpler than the alternative you are proposing.
>>>
>>> I can remove that example if there is consensus.  I find it a useful
>> method of preventing someone from producing a tight loop by accidentally
>> creating a path in the loop that skips the advancement.
>>
>> I also wonder if an local struct with a destructor and a corresponding
>>> variable wouldn't be simpler than the scoped example or alternatives like
>>> unique_ptr or shared_ptr or boost::scoped_ptr that already provide much of
>>> the functionality you are proposing.
>>>
>>> That horse has been beat to death already in the original thread on
>> this.  The consensus was that these class are useful and serve a different
>> purpose than unique_ptr.  You will find several that back your view point,
>> but there is no reason for us to revisit this point.  I didn't put hundreds
>> of hours into the document after we'd already had that discussion, just to
>> fight that fight again now.  Please feel free to look at the previous posts.
>>
>>
>>> The example given as Motivation B calls for a dedicated RAII class for
>>> CriticalSection IMHO, so again not very convincing.
>>>
>>> IMHO it would greatly improve your paper if you would provide additional
>>> examples showing the "uglyness" of using existing alternatives to your
>>> proposal, i.e., DIY local structs with destructors, or "misusing"
>>> unique_ptr/shared_ptr for that purpose, in contrast to scoped_function and
>>> scoped_resource.
>>>
>>
>> Okay, I can definitely consider that.  Anyone concur?
>>
>
> I do, and I feel Peter was not trying to bringing up the previous noise
> again, but only, at the end,
> to make a point on what should be the focus.
>
>
>>
>>> Also providing the no-delete value is not very convincing. What if all
>>> values less than zero are "no-delete", or 7, 23 and 42? It complicates the
>>> class and API and doesn't serve a general purpose. Usually a predicate is
>>> used in other cases to provide a hook for bool checks.
>>>
>>> I disagree with that 100%.  In most cases resources -- real resources
>> like file handles or descriptors, etc. are allocated and have either a 0 /
>> nullptr or a -1 value on failure  Making the no-delete value simple saves a
>> lot of duplicate code.
>>
>
> Windows WaitForMultipleObjects<http://msdn.microsoft.com/en-us/library/windows/desktop/ms687025%28v=vs.85%29.aspx>is an example of API that, may not completely fit scoped_resource scenery,
> but may give an idea of the problem. I too, have found that the current
> state fits a scenery that's not general
> enough, but may cover most cases in the wild... maybe, I can't be sure
> about that.
>
>
>>
>>
>>> Just my CHF0.02 from a quick scan.
>>>
>>> Peter.
>>>
>>> Thank you for your feedback.
>> Where is everyone else lately?  Is this the week that the committee is in
>> meetings in Bristol?
>> -Andrew Sandoval
>>
>
> By the way, I'd like to have the newer reference implementations available
> in source code form (on github for example)...
>
> Regards,
> Francisco Lopes
>

Francisco,

Were you aware that this has been replaced by N3830?  The entire reference
implementation is in the PDF document that Peter Sommerlad produced for the
mailing.  (He did amazing work on the reference implementation1)

-Andrew Sandoval

--

---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_114_5981518.1391034272750
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr">On Wednesday, January 29, 2014 12:41:25 PM UTC-6, Francisc=
o Lopes wrote:<blockquote class=3D"gmail_quote" style=3D"margin: 0px 0px 0p=
x 0.8ex; padding-left: 1ex; border-left-color: rgb(204, 204, 204); border-l=
eft-width: 1px; border-left-style: solid;"><div dir=3D"ltr">2013-04-15 Andr=
ew Sandoval <span dir=3D"ltr">&lt;<a onmousedown=3D"this.href=3D'javascript=
:';return true;" onclick=3D"this.href=3D'javascript:';return true;" href=3D=
"javascript:" target=3D"_blank" gdf-obfuscated-mailto=3D"A8URdUlVYZsJ">sand=
....@netwaysglobal.com</a>&gt;</span><br><div><div class=3D"gmail_quote"><bl=
ockquote class=3D"gmail_quote" style=3D"margin: 0px 0px 0px 0.8ex; padding-=
left: 1ex; border-left-color: rgb(204, 204, 204); border-left-width: 1px; b=
order-left-style: solid;">
<div>On Saturday, April 13, 2013 6:18:48 AM UTC-5, PeterSommerlad wrote:<bl=
ockquote class=3D"gmail_quote" style=3D"margin: 0px 0px 0px 0.8ex; padding-=
left: 1ex; border-left-color: rgb(204, 204, 204); border-left-width: 1px; b=
order-left-style: solid;">the loop advancement example is not very convinci=
ng because it can easily be dealt with by using for() instead of while() wh=
ich is much simpler than the alternative you are proposing.
<br>
<br></blockquote></div><div>I can remove that example if there is consensus=
..&nbsp; I find it a useful method of preventing someone from producing a ti=
ght loop by accidentally creating a path in the loop that skips the advance=
ment.<br>
<br></div><div><blockquote class=3D"gmail_quote" style=3D"margin: 0px 0px 0=
px 0.8ex; padding-left: 1ex; border-left-color: rgb(204, 204, 204); border-=
left-width: 1px; border-left-style: solid;">I also wonder if an local struc=
t with a destructor and a corresponding variable wouldn't be simpler than t=
he scoped example or alternatives like unique_ptr or shared_ptr or boost::s=
coped_ptr that already provide much of the functionality you are proposing.
<br>
<br></blockquote></div><div>That horse has been beat to death already in th=
e original thread on this.&nbsp; The consensus was that these class are use=
ful and serve a different purpose than unique_ptr.&nbsp; You will find seve=
ral that back your view point, but there is no reason for us to revisit thi=
s point.&nbsp; I didn't put hundreds of hours into the document after we'd =
already had that discussion, just to fight that fight again now.&nbsp; Plea=
se feel free to look at the previous posts.<br>
&nbsp;<br></div><div><blockquote class=3D"gmail_quote" style=3D"margin: 0px=
 0px 0px 0.8ex; padding-left: 1ex; border-left-color: rgb(204, 204, 204); b=
order-left-width: 1px; border-left-style: solid;">The example given as Moti=
vation B calls for a dedicated RAII class for CriticalSection IMHO, so agai=
n not very convincing.
<br>
<br>IMHO it would greatly improve your paper if you would provide additiona=
l examples showing the "uglyness" of using existing alternatives to your pr=
oposal, i.e., DIY local structs with destructors, or "misusing" unique_ptr/=
shared_ptr for that purpose, in contrast to scoped_function and scoped_reso=
urce.
<br></blockquote><div>&nbsp;</div></div><div>Okay, I can definitely conside=
r that.&nbsp; Anyone concur? <br></div></blockquote><div><br></div><div>I d=
o, and I feel Peter was not trying to bringing up the previous noise again,=
 but only, at the end,<br>
to make a point on what should be the focus. <br></div><div>&nbsp;</div><bl=
ockquote class=3D"gmail_quote" style=3D"margin: 0px 0px 0px 0.8ex; padding-=
left: 1ex; border-left-color: rgb(204, 204, 204); border-left-width: 1px; b=
order-left-style: solid;"><div></div><div><blockquote class=3D"gmail_quote"=
 style=3D"margin: 0px 0px 0px 0.8ex; padding-left: 1ex; border-left-color: =
rgb(204, 204, 204); border-left-width: 1px; border-left-style: solid;">

<br>Also providing the no-delete value is not very convincing. What if all =
values less than zero are "no-delete", or 7, 23 and 42? It complicates the =
class and API and doesn't serve a general purpose. Usually a predicate is u=
sed in other cases to provide a hook for bool checks.
<br>
<br></blockquote></div><div>I disagree with that 100%.&nbsp; In most cases =
resources -- real resources like file handles or descriptors, etc. are allo=
cated and have either a 0 / nullptr or a -1 value on failure&nbsp; Making t=
he no-delete value simple saves a lot of duplicate code.<br>
</div></blockquote><div><br></div><div>Windows <a onmousedown=3D"this.href=
=3D'http://www.google.com/url?q\75http%3A%2F%2Fmsdn.microsoft.com%2Fen-us%2=
Flibrary%2Fwindows%2Fdesktop%2Fms687025%2528v%3Dvs.85%2529.aspx\46sa\75D\46=
sntz\0751\46usg\75AFQjCNFncFqGhB5I1hCdXcerljOJTs_70A';return true;" onclick=
=3D"this.href=3D'http://www.google.com/url?q\75http%3A%2F%2Fmsdn.microsoft.=
com%2Fen-us%2Flibrary%2Fwindows%2Fdesktop%2Fms687025%2528v%3Dvs.85%2529.asp=
x\46sa\75D\46sntz\0751\46usg\75AFQjCNFncFqGhB5I1hCdXcerljOJTs_70A';return t=
rue;" href=3D"http://msdn.microsoft.com/en-us/library/windows/desktop/ms687=
025%28v=3Dvs.85%29.aspx" target=3D"_blank">WaitForMultipleObjects</a> is an=
 example of API that, may not completely fit scoped_resource scenery,<br>
but may give an idea of the problem. I too, have found that the current sta=
te fits a scenery that's not general<br>enough, but may cover most cases in=
 the wild... maybe, I can't be sure about that.<br></div><div>&nbsp;</div>
<blockquote class=3D"gmail_quote" style=3D"margin: 0px 0px 0px 0.8ex; paddi=
ng-left: 1ex; border-left-color: rgb(204, 204, 204); border-left-width: 1px=
; border-left-style: solid;"><div>&nbsp;<br></div><div><blockquote class=3D=
"gmail_quote" style=3D"margin: 0px 0px 0px 0.8ex; padding-left: 1ex; border=
-left-color: rgb(204, 204, 204); border-left-width: 1px; border-left-style:=
 solid;">
Just my CHF0.02 from a quick scan.
<br>
<br>Peter.
<br>
<br></blockquote></div><div>Thank you for your feedback.<br>Where is everyo=
ne else lately?&nbsp; Is this the week that the committee is in meetings in=
 Bristol?<span><font color=3D"#888888"><br>-Andrew Sandoval<br></font></spa=
n></div>
</blockquote><div><br></div><div>By the way, I'd like to have the newer ref=
erence implementations available in source code form (on github for example=
)...<br><br></div><div>Regards,<br></div><div>Francisco Lopes<br></div></di=
v></div></div></blockquote><div><br></div><div>Francisco,</div><div><br></d=
iv><div>Were you aware that this&nbsp;has been replaced by N3830?&nbsp; The=
 entire reference implementation is in the PDF document&nbsp;that Peter Som=
merlad produced for the mailing.&nbsp; (He did amazing work on&nbsp;the ref=
erence implementation1)</div><div><br></div><div>-Andrew Sandoval&nbsp;</di=
v></div>

<p></p>

-- <br />
&nbsp;<br />
--- <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 std-proposals+unsubscribe@isocpp.org.<br />
To post to this group, send email to std-proposals@isocpp.org.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_114_5981518.1391034272750--

.


Author: Francisco Lopes <francisco.mailing.lists@oblita.com>
Date: Wed, 29 Jan 2014 20:40:04 -0200
Raw View
--001a1134bb9a438cfe04f1239fea
Content-Type: text/plain; charset=ISO-8859-1

2014-01-29 Andrew Sandoval <sandoval@netwaysglobal.com>

> Francisco,
>
> Were you aware that this has been replaced by N3830?  The entire reference
> implementation is in the PDF document that Peter Sommerlad produced for the
> mailing.  (He did amazing work on the reference implementation1)
>
> -Andrew Sandoval
>

oh, indeed, I was aware, I did look at the paper, but I don't recall
whether the "no delete" was addressed, will check again, and  also, I just
missed a reference implementation that I could grab and use with latest
clang/g++ -std=c++1y.

--

---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

--001a1134bb9a438cfe04f1239fea
Content-Type: text/html; charset=ISO-8859-1
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr"><br><div class=3D"gmail_extra">2014-01-29 Andrew Sandoval =
<span dir=3D"ltr">&lt;<a href=3D"mailto:sandoval@netwaysglobal.com" target=
=3D"_blank">sandoval@netwaysglobal.com</a>&gt;</span><br><div class=3D"gmai=
l_quote"><blockquote class=3D"gmail_quote" style=3D"margin:0 0 0 .8ex;borde=
r-left:1px #ccc solid;padding-left:1ex">
<div dir=3D"ltr">Francisco,<div><br></div><div>Were you aware that this=A0h=
as been replaced by N3830?=A0 The entire reference implementation is in the=
 PDF document=A0that Peter Sommerlad produced for the mailing.=A0 (He did a=
mazing work on=A0the reference implementation1)</div>
<div><br></div><div>-Andrew Sandoval=A0</div></div></blockquote><div><br></=
div><div>oh, indeed, I was aware, I did look at the paper, but I don&#39;t =
recall whether the &quot;no delete&quot; was addressed, will check again, a=
nd=A0 also, I just missed a reference implementation that I could grab and =
use with latest clang/g++ -std=3Dc++1y.<br>
</div></div></div></div>

<p></p>

-- <br />
&nbsp;<br />
--- <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 std-proposals+unsubscribe@isocpp.org.<br />
To post to this group, send email to std-proposals@isocpp.org.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

--001a1134bb9a438cfe04f1239fea--

.


Author: Andrew Sandoval <sandoval@netwaysglobal.com>
Date: Wed, 29 Jan 2014 15:17:42 -0800 (PST)
Raw View
------=_Part_151_598622.1391037462497
Content-Type: text/plain; charset=UTF-8

On Wednesday, January 29, 2014 4:40:04 PM UTC-6, Francisco Lopes wrote:
>
>
> 2014-01-29 Andrew Sandoval <sand...@netwaysglobal.com <javascript:>>
>
>> Francisco,
>>
>> Were you aware that this has been replaced by N3830?  The entire
>> reference implementation is in the PDF document that Peter Sommerlad
>> produced for the mailing.  (He did amazing work on the reference
>> implementation1)
>>
>> -Andrew Sandoval
>>
>
> oh, indeed, I was aware, I did look at the paper, but I don't recall
> whether the "no delete" was addressed, will check again, and  also, I just
> missed a reference implementation that I could grab and use with latest
> clang/g++ -std=c++1y.
>

Understood.  I just created this and put the implementation that I use
there.  Please feel free to try it out.

https://github.com/alsliahona/N3830

-Andrew Sandoval

--

---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_151_598622.1391037462497
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr">On Wednesday, January 29, 2014 4:40:04 PM UTC-6, Francisco=
 Lopes wrote:<blockquote class=3D"gmail_quote" style=3D"margin: 0px 0px 0px=
 0.8ex; padding-left: 1ex; border-left-color: rgb(204, 204, 204); border-le=
ft-width: 1px; border-left-style: solid;"><div dir=3D"ltr"><br><div>2014-01=
-29 Andrew Sandoval <span dir=3D"ltr">&lt;<a onmousedown=3D"this.href=3D'ja=
vascript:';return true;" onclick=3D"this.href=3D'javascript:';return true;"=
 href=3D"javascript:" target=3D"_blank" gdf-obfuscated-mailto=3D"0V3oR3uT7K=
EJ">sand...@netwaysglobal.com</a>&gt;</span><br><div class=3D"gmail_quote">=
<blockquote class=3D"gmail_quote" style=3D"margin: 0px 0px 0px 0.8ex; paddi=
ng-left: 1ex; border-left-color: rgb(204, 204, 204); border-left-width: 1px=
; border-left-style: solid;">
<div dir=3D"ltr">Francisco,<div><br></div><div>Were you aware that this&nbs=
p;has been replaced by N3830?&nbsp; The entire reference implementation is =
in the PDF document&nbsp;that Peter Sommerlad produced for the mailing.&nbs=
p; (He did amazing work on&nbsp;the reference implementation1)</div>
<div><br></div><div>-Andrew Sandoval&nbsp;</div></div></blockquote><div><br=
></div><div>oh, indeed, I was aware, I did look at the paper, but I don't r=
ecall whether the "no delete" was addressed, will check again, and&nbsp; al=
so, I just missed a reference implementation that I could grab and use with=
 latest clang/g++ -std=3Dc++1y.<br></div></div></div></div></blockquote><di=
v><br></div><div>Understood.&nbsp; I just created this&nbsp;and put the imp=
lementation that I use there.&nbsp; Please feel free to try it out.</div><d=
iv><br></div><div><a href=3D"https://github.com/alsliahona/N3830">https://g=
ithub.com/alsliahona/N3830</a></div><div><br></div><div>-Andrew Sandoval&nb=
sp;</div></div>

<p></p>

-- <br />
&nbsp;<br />
--- <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 std-proposals+unsubscribe@isocpp.org.<br />
To post to this group, send email to std-proposals@isocpp.org.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_151_598622.1391037462497--

.


Author: Francisco Lopes <francisco.mailing.lists@oblita.com>
Date: Wed, 29 Jan 2014 23:54:26 -0200
Raw View
--089e011822645febbf04f126560e
Content-Type: text/plain; charset=ISO-8859-1

2014-01-29 Andrew Sandoval <sandoval@netwaysglobal.com>

> On Wednesday, January 29, 2014 4:40:04 PM UTC-6, Francisco Lopes wrote:
>>
>>
>> 2014-01-29 Andrew Sandoval <sand...@netwaysglobal.com>
>>
>> Francisco,
>>>
>>> Were you aware that this has been replaced by N3830?  The entire
>>> reference implementation is in the PDF document that Peter Sommerlad
>>> produced for the mailing.  (He did amazing work on the reference
>>> implementation1)
>>>
>>> -Andrew Sandoval
>>>
>>
>> oh, indeed, I was aware, I did look at the paper, but I don't recall
>> whether the "no delete" was addressed, will check again, and  also, I just
>> missed a reference implementation that I could grab and use with latest
>> clang/g++ -std=c++1y.
>>
>
> Understood.  I just created this and put the implementation that I use
> there.  Please feel free to try it out.
>
> https://github.com/alsliahona/N3830
>
> -Andrew Sandoval
>

Thanks Andrew

--

---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

--089e011822645febbf04f126560e
Content-Type: text/html; charset=ISO-8859-1
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr"><div class=3D"gmail_extra">2014-01-29 Andrew Sandoval <spa=
n dir=3D"ltr">&lt;<a href=3D"mailto:sandoval@netwaysglobal.com" target=3D"_=
blank">sandoval@netwaysglobal.com</a>&gt;</span><br><div class=3D"gmail_quo=
te"><blockquote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;bor=
der-left:1px solid rgb(204,204,204);padding-left:1ex">
<div dir=3D"ltr">On Wednesday, January 29, 2014 4:40:04 PM UTC-6, Francisco=
 Lopes wrote:<blockquote class=3D"gmail_quote" style=3D"margin:0px 0px 0px =
0.8ex;padding-left:1ex;border-left:1px solid rgb(204,204,204)"><div dir=3D"=
ltr">
<br><div>2014-01-29 Andrew Sandoval <span dir=3D"ltr">&lt;<a>sand...@netway=
sglobal.com</a>&gt;</span><div><div class=3D"h5"><br><div class=3D"gmail_qu=
ote"><blockquote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;pa=
dding-left:1ex;border-left:1px solid rgb(204,204,204)">

<div dir=3D"ltr">Francisco,<div><br></div><div>Were you aware that this=A0h=
as been replaced by N3830?=A0 The entire reference implementation is in the=
 PDF document=A0that Peter Sommerlad produced for the mailing.=A0 (He did a=
mazing work on=A0the reference implementation1)</div>

<div><br></div><div>-Andrew Sandoval=A0</div></div></blockquote><div><br></=
div><div>oh, indeed, I was aware, I did look at the paper, but I don&#39;t =
recall whether the &quot;no delete&quot; was addressed, will check again, a=
nd=A0 also, I just missed a reference implementation that I could grab and =
use with latest clang/g++ -std=3Dc++1y.<br>
</div></div></div></div></div></div></blockquote><div><br></div><div>Unders=
tood.=A0 I just created this=A0and put the implementation that I use there.=
=A0 Please feel free to try it out.</div><div><br></div><div><a href=3D"htt=
ps://github.com/alsliahona/N3830" target=3D"_blank">https://github.com/alsl=
iahona/N3830</a></div>
<span class=3D""><font color=3D"#888888"><div><br></div><div>-Andrew Sandov=
al=A0</div></font></span></div></blockquote><div><br>Thanks Andrew<br></div=
></div></div></div>

<p></p>

-- <br />
&nbsp;<br />
--- <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 std-proposals+unsubscribe@isocpp.org.<br />
To post to this group, send email to std-proposals@isocpp.org.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

--089e011822645febbf04f126560e--

.