<html>

<head>
<meta http-equiv="Content-Language" content="en-us">
<meta name="GENERATOR" content="Microsoft FrontPage 5.0">
<meta name="ProgId" content="FrontPage.Editor.Document">
<meta http-equiv="Content-Type" content="text/html; charset=windows-1252">
<title>Diagnostics Issues</title>
</head>

<body>

<p>Doc. no.&nbsp;&nbsp; N2415=07-0275<br>
Date:&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 
<!--webbot bot="Timestamp" s-type="EDITED" s-format="%Y-%m-%d" startspan -->2007-09-09<!--webbot bot="Timestamp" endspan i-checksum="12604" --><br>
Project:&nbsp;&nbsp;&nbsp;&nbsp; Programming Language C++<br>
Reply to:&nbsp;&nbsp; Beman Dawes &lt;<a href="mailto:bdawes@acm.org">bdawes@acm.org</a>&gt;<br>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
<span id="_user_chris@kohlhoff.com">Christopher Kohlhoff</span><span style="font-weight: normal;" class="lg">&nbsp;&lt;chris@kohlhoff.com&gt;</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </p>
<h1>Diagnostics  Issues (Rev. 1)</h1>
<p><a href="#Issue1">Issue 1</a>: Missing error_code::clear() specification<br>
<a href="#Issue2">Issue 2</a>: &lt;system_error&gt; should not force an implementation 
to expose &lt;cerrno&gt; macros<br>
<a href="#Issue3">Issue 3</a>: &lt;functional&gt; hash specialization for error_code<br>
<a href="#Issue4">Issue 4</a>: Class error_code constructor should be explicit<br>
<a href="#Issue5">Issue 5</a>: Class error_code constructors should be constexpr<br>
<a href="#Issue6">Issue 6</a>: Class error_category should be non-copyable<br>
<a href="#Issue7">Issue 7</a>: Problems with posix_errno overloads<br>
<a href="#Issue8">Issue 8</a>: [Withdrawn]<br>
<a href="#Issue9">Issue 9</a>: EOTHER hijacks POSIX macro space, constant name 
too general<br>
<a href="#Issue10">Issue 10</a>: Header dependencies are non-trivial<br>
<a href="#Issue11">Issue 11</a>: Overly complex <code>error_code::value_type</code> 
with circular dependencies<br>
<a href="#Issue12">Issue 12</a>: Missing throw specifications<br>
<a href="#Issue13">Issue 13</a>: Missing <code>system_error</code> constructor<br>
<a href="#Issue14">Issue 14</a>: <code>error_category</code> equality via 
address comparison<br>
<a href="#Issue15">Issue 15</a>: Extending <code>error_code::value_types</code> constants and 
user-defined <code>error_category</code> objects<br>
<a href="#Issue16">Issue 16</a>: POSIX versus native <code>error_category<br>
</code><a href="#Issue17">Issue 17</a>: Broken <code>error_category::message</code> 
member functions<br>
<a href="#Issue18">Issue 18:</a> <code>system_error::what</code> and constructors<br>
<a href="#Issue19">Issue 19</a>: Should classes <code>error_code</code> and 
<code>error_category</code> be less-than 
comparable?<br>
<a href="#Issue20">Issue 20</a>: Which 
<code>error_category</code> applies to POSIX-like 
operating system errors unclear<br>
<a href="#Issue21">Issue 21</a>: Error enums add lots of names to namespace std<br>
<a href="#Issue22">Issue 22</a>: Out of memory should throw <code>bad_alloc</code>, 
not <code>system_error</code><span style="background-color: #FFFF00"><br>
</span><a href="#Issue23">Issue 23</a>: <code>error_category::name()</code> 
should return <code>const char *</code><span style="background-color: #FFFF00"><br>
</span><a href="#Issue24">Issue 24</a>: <code>system_error</code> 
what-less constructors needed<span style="background-color: #FFFF00"><br>
</span><a href="#Acknowledgements">Acknowledgements</a></p>
<p>This paper is a major revision of
<a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2007/n2296.html">
N2296</a>, Diagnostics Enhancements; Resolution of Small Issues. The name has 
been changed to reflect the wider scope of several proposals.</p>
<p>The resolution of many of the issues are interrelated or modify overlapping 
sections of text in the standard. The proposed resolutions of these issues are 
combined in the proposed resolution wording for <a href="#Issue7">issue 7</a>.</p>
<p>The proposed resolutions for many of these issues were 
drafted by Beman Dawes. The issue submitters do not necessarily agree with these 
PR's.</p>
<h3><a name="Issue1">Issue 1</a>: Missing error_code::clear() specification</h3>
<p>The <code>clear()</code> function is shown in the synopsis but is otherwise unspecified.</p>
<p>Reported separately by Pete Becker, PJ Plauger, and Benjamin Kosnik.</p>
<h4>Proposed resolution</h4>
<p><i>Specify the semantics. See proposed wording for <a href="#Issue7">issue 7</a>.</i></p>
<h3><a name="Issue2">Issue 2</a>: &lt;system_error&gt; should not force an implementation to expose &lt;cerrno&gt; 
macros</h3>
<p>In N2241, <code>enum posix_errno</code> did not specify values for each 
enumeration constant. Instead, a table of equivalence was provided showing the
<code>&lt;cerrno&gt;</code> E* macro the constant was to be equivalent to. During 
editing, that table was folded into the enum for brevity. That was a useful 
change, but had the unintended side effect of making it look like <code>&lt;system_error&gt;</code> 
was required to expose the <code>&lt;cerrno&gt; macros</code>, which was not the intent.</p>
<p>Submitted by PJ Plaguer</p>
<h4>Proposed resolution</h4>
<p><i>Change the form of <code>enum posix_errno</code> in 19.4 System error 
support [syserr] as indicated:</i></p>
<blockquote>
  <p><code>enum posix_errno {<br>
&nbsp; address_family_not_supported<strike><font color="#FF0000"> = EAFNOSUPPORT</font></strike>, <font color="#008080"><u>
  // EAFNOSUPPORT</u></font><br>
&nbsp; address_in_use<strike><font color="#FF0000"> = EADDRINUSE</font></strike>, <font color="#008080"><u>
  // EADDRINUSE<br>
  </u></font><br>
&nbsp; </code><i>... Apply same pattern of changes to all remaining constants 
  for the enum.</i></p>
</blockquote>
<p><i>At the end of 19.4 System error support [syserr] add:</i></p>
<blockquote>
  <p><u><font color="#009A9A">The value of each <code>enum posix_errno</code> constant shall be the same 
  as the value of the <code>&lt;cerrno&gt;</code> macro shown in the above 
  synopsis.</font></u></p>
</blockquote>
  <p><i>Whether or not the &lt;system_error&gt; implementation actually exposes the &lt;cerrno&gt; 
  macros is unspecified.</i></p>
<h3><a name="Issue3">Issue 3</a>: &lt;functional&gt; hash specialization for error_code</h3>
<p>The member function <code>hash_value</code> should be replaced or supplemented by an 
explicit specialization of template class hash (in &lt;functional&gt;) so people can 
easily make an unordered container keyed on errors.</p>
<p>Submitted by PJ Plauger.</p>
<h4>Proposed resolution</h4>
<p>In 19.4.2.1 Class error_code overview [syserr.errcode.overview], removed:</p>
<blockquote>
<p><font color="#FF0000"><strike><code>size_t hash_value(const error_code&amp; ec);</code></strike></font></p>
</blockquote>
<p>In 19.4.2.6 Class error_code non-member functions [syserr.errcode.nonmembers], 
remove:</p>
<blockquote>
<p><font color="#FF0000"><strike><code>size_t hash_value(const error_code&amp; ec);</code></strike></font></p>
  <blockquote>
<p><font color="#FF0000"><strike><i>Returns: </i>A hash value representing ec.</strike></font></p>
  </blockquote>
</blockquote>
<p><i>In 20.5 Function objects [function.objects], paragraph 2, Header 
&lt;functional&gt; synopsis, add:</i></p>
<blockquote>
<p><u><font color="#009A9A"><code>template &lt;&gt; struct hash&lt;std::error_code&gt;;</code></font></u></p>
</blockquote>
<p><i>Change 20.5.15 Class template hash [unord.hash] as indicated:</i></p>
<blockquote>
  <p>The unordered associative containers defined in clause 23.4 use 
  specializations of hash as the default hash function. This class template is 
  only required to be instantiable for integer types (3.9.1), floating point 
  types (3.9.1), pointer types (8.3.1), and <code>std::string</code>, <code>
  std::u16string</code>, <code>std::u32string</code>, <strike>
  <font color="#FF0000">and</font> </strike> <code>std::wstring</code><font color="#009a9a">,</font><font color="#008080"><i> 
  </i><u>and <code>std::error_code</code></u></font>.</p>
</blockquote>

  <h3><a name="Issue4">Issue 4</a>: Class error_code constructor should be explicit</h3>
  <p>Submitted by Alisdair Meredith.</p>
  <h4>Proposed resolution</h4>
  <p><i>No action necessary.</i></p>
  <h4>Rationale</h4>
  <p><i>The conversion constructor is important design element; without it error 
  enum ease-of-use suffers badly. </i></p>
  <h3><a name="Issue5">Issue 5</a>: Class error_code constructors should be constexpr</h3>
  <p>Objects of class <code>error_code</code> will commonly be constructed in 
  very low-level systems code where efficiency is a critical consideration. Thus 
  static initialization is quite desirable, and would remove the runtime and 
  code size cost implicit in the change to enumeration 
  style error values.</p>
  <p>A possible fix is to apply <code>constexpr</code>.</p>
  <p>Submitted by Chris Kohlhoff and Beman Dawes.</p>
  <h4>Proposed resolution</h4>
  <p><i>Take no action at this time.</i></p>
  <h4>Rationale</h4>
  <p><i>It doesn't appear at this time that constexpr works for the error_code 
  constructors, because error_category isn't a literal type. Once an 
  implementation of constexpr become available, it may be possible to develop a 
  workaround, but until then no action should be taken.</i></p>
  <h3><a name="Issue6">Issue 6</a>: Class error_category should be non-copyable</h3>
  <p>Class <code>error_category</code> equality is stated in terms of address 
  comparison, taking advantage of the C++ language rule that no two objects can 
  have the same address, and thus avoiding the possibility that independently 
  created user-defined error categories could inadvertently compare equal.</p>
  <p>Thus it makes no sense to allow <code>error_category</code> objects to be 
  copyable.</p>
  <p>Submitted by Pete Becker.</p>
  <h4>Proposed resolution</h4>
  <p><i>Make error_category non-copyable. See proposed wording for <a href="#Issue7">issue 7</a>.</i></p>
<h3><a name="Issue7">Issue 7</a>: Problems with posix_errno overloads</h3>
<p>The original Diagnostics proposal,
<a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2007/n2174.html">
N2174</a>, provided <code>error_code</code> constants for POSIX errors. The LWG 
requested that these be changed to an enum, and <code>enum posix_errno</code> 
was accordingly provided&nbsp; in the final proposal voted into the working paper. 
Since the enums are replacing objects of type <code>error_code</code>, rather 
than replacing simple integer constants, such a change has turned out to have 
considerable fallout.</p>
<p>The wording in the WP included several overloads on <code>posix_errno</code> 
introduced to make the enums workable. However, the introduced overloads have 
several problems:</p>
  <ul>
    <li><a href="#Unintended-consequences">Unintended consequences</a>.</li>
    <li>Do not support error categories other than POSIX.</li>
    <li>Obscure the distinction between system-specific errors and the general 
    and portable notion of an error condition.</li>
</ul>
<p>A solution to these problems must ensure:</p>
  <ul>
    <li>Users can continue write code using error enums as if they were error 
    codes. For example, <code>ec == windows::access_denied</code>.</li>
    <li>It is no more difficult to write portable code that system specific 
    code. If users can write <code>ec == windows::access_denied</code> to test 
    for a system-specific error, but have to write <code>ec.posix() == 
    posix::permission_denied</code> to get the portable equivalent, it is both 
    error prone and discourages portable code. </li>
</ul>
<h4>Proposed resolution</h4>
  <p><i>Change 19.4 System error support [syserr] as indicated. Note that <code>is_error_code_enum</code> 
  and <code>is_error_condition_enum</code> will be eliminated when the 
  library is conceptized.</i></p>
<blockquote>
  <blockquote>
  <pre>namespace std {

class system_error;
class error_code;
<font color="#009A9A"><u>class error_condition;</u></font>
class error_category;

<font color="#009A9A"><u>template&lt; class T &gt;
struct is_error_code_enum {
</u>  <u>static const bool value = false;
};

template&lt; class T &gt;
struct is_error_condition_enum {
</u>  <u>static const bool value = false;
};

namespace posix {</u></font>
  enum posix_errno {
    address_family_not_supported = EAFNOSUPPORT,
    address_in_use = EADDRINUSE,
    ...
    value_too_large = EOVERFLOW,
    wrong_protocol_type = EPROTOTYPE
    };
<font color="#009A9A"><u>}</u></font></pre>
  <pre><font color="#009A9A"><u>template&lt;&gt; struct is_error_condition_enum&lt;posix::posix_errno&gt; {
</u>  <u>static const bool value = true;
};
</u></font><strike><font color="#FF0000">
</font></strike><font color="#009A9A"><u>bool operator==(const error_code&amp; lhs, const error_code&amp; rhs);</u></font>
bool operator==(const error_code&amp; <strike><font color="#FF0000">ec</font></strike> <u><font color="#009A9A">code</font></u>, posix_errno <strike><font color="#FF0000">en</font></strike> <font color="#009A9A"><u>const error_condition&amp; </u></font><u><font color="#009A9A">condition</font></u>);
bool operator==(<strike><font color="#FF0000">posix_errno en</font></strike> <font color="#009A9A"><u>const error_condition&amp; </u></font><u><font color="#009A9A">condition</font></u>, const error_code&amp; <strike><font color="#FF0000">ec</font></strike> <u><font color="#009A9A">code</font></u>);
<font color="#009A9A"><u>bool operator==(const error_condition&amp; lhs, const error_condition&amp; rhs);</u></font>
<font color="#009A9A"><u>bool operator!=(const error_code&amp; lhs, const error_code&amp; rhs);</u></font>
bool operator!=(const error_code&amp; <strike><font color="#FF0000">ec</font></strike> <u><font color="#009A9A">code</font></u>, posix_errno <strike><font color="#FF0000">en</font></strike> <font color="#009A9A"><u>const error_condition&amp; </u></font><u><font color="#009A9A">condition</font></u>);
bool operator!=(<strike><font color="#FF0000">posix_errno en</font></strike> <font color="#009A9A"><u>const error_condition&amp; </u></font><u><font color="#009A9A">condition</font></u>, const error_code&amp; <strike><font color="#FF0000">ec</font></strike> <u><font color="#009A9A">code</font></u>);
<font color="#009A9A"><u>bool operator!=(const error_condition&amp; lhs, const error_condition&amp; rhs);</u></font>
<font color="#009A9A"><u>bool operator&lt;(const error_code&amp; lhs, const error_code&amp; rhs);</u></font>
<font color="#009A9A"><u>bool operator&lt;(const error_condition&amp; lhs, const error_condition&amp; rhs);

error_code make_error_code(posix::posix_errno e);
error_condition make_error_condition(posix::posix_errno e);

</u></font>} // <i>namespace std</i></pre>
  </blockquote>
  <p><font color="#009A9A"><u>Users may specialize <code>is_error_code_enum</code> 
  and <code>is_error_condition_enum</code> templates to indicate that a type is 
  eligible for <code>class error_code</code> and <code>error_condition</code> 
  automatic conversions respectively.</u></font></p>
</blockquote>
  <p><i>Change 19.4.1.1 Class error_category overview [syserr.errcat.overview] 
  as indicated:</i></p>
<blockquote>
  <pre>namespace std {

  class error_category {
  public:
    <font color="#009A9A"><u>virtual ~error_category();</u></font>
<font color="#009A9A"><code>  </code></font>  <font color="#009A9A"><code><u>error_category(const error_category&amp;) = delete;
</u>  </code></font>  <font color="#009A9A"><code><u>error_category&amp; operator=(const error_category&amp;) = delete;
</u></code></font>    virtual const string&amp; name() const = 0;
    <strike><font color="#FF0000">virtual posix_errno posix(error_code::value_type ev) const = 0;</font></strike>
<font color="#009A9A">  </font>  <font color="#009A9A"><u>virtual error_condition default_error_condition(int ev) const;
</u>  </font>  <font color="#009A9A"><u>virtual bool equivalent(int code, const error_condition &amp; condition) const;
</u>  </font>  <font color="#009A9A"><u>virtual bool equivalent(const error_code &amp; code, int condition) const;
</u></font>    virtual string message(error_code::value_type ev) const = 0;
    virtual wstring wmessage(error_code::value_type ev) const = 0;

    bool operator==(const error_category&amp; rhs) const;
    bool operator!=(const error_category&amp; rhs) const;
    <font color="#009A9A"><u>bool operator&lt;( const error_category &amp; rhs ) const;</u></font>
  };

  extern const error_category&amp; posix_category;
  extern const error_category&amp; <strike><font color="#FF0000">native_category</font></strike> <font color="#009A9A"><u>system_category</u></font>;

} // <i>namespace std</i></pre>
</blockquote>
<p><i>Change 19.4.1.2 Class error_category virtual members [<a name="syserr-errcat-virtuals">syserr.errcat.virtuals</a>] 
as indicated:</i></p>
<blockquote>
  <p><strike><font color="#FF0000"><code>virtual posix_errno 
  posix(error_code::value_type ev) const = 0;</code></font></strike><code><br>
  </code><font color="#009A9A"><u><code>virtual error_condition 
  default_error_condition(int ev) const;</code></u></font></p>
  <blockquote>
    <p><i>Returns:</i> <strike><font color="#FF0000">A value of type <code>
    posix_errno</code></font></strike><font color="#FF0000"><strike> that corresponds to <code>ev</code> if 
    such a corresponding POSIX error number exists, otherwise </strike></font> <strike>
    <font color="#FF0000">other</font></strike> <font color="#009A9A"><u><code>
    error_condition(ev, *this)</code></u></font>.&nbsp; <strike>
    <font color="#FF0000">[ <i>Note:</i> Since the possible 
    values of <code>ev</code> are not bounded, the intent is that implementations translate 
    commonly encountered values to the equivalent POSIX error number and 
    translate the rest to other. 
    <i>--end note</i> ]</font></strike></p>
    <p><i>Throws:</i> Nothing.</p>
  </blockquote>
  <p><font color="#009A9A"><u><code>virtual bool equivalent(int code, const 
  error_condition &amp; condition) const;</code></u></font></p>
  <blockquote>
    <p><u><font color="#009A9A"><i>Returns:</i> <code>default_error_condition( 
    code ) == condition</code>.</font></u></p>
    <p><font color="#009A9A"><u><i>Throws:</i> Nothing.</u></font></p>
  </blockquote>
  <p><u><font color="#009A9A"><code>virtual bool equivalent(const error_code &amp; 
  code, int condition) const;</code></font></u></p>
  <blockquote>
    <p><u><font color="#009A9A"><i>Returns:</i> <code>*this == code.category() 
    &amp;&amp; code.value() == condition</code>.</font></u></p>
    <p><font color="#009A9A"><u><i>Throws:</i> Nothing.</u></font></p>
  </blockquote>
</blockquote>
<p><i>Add to 19.4.1.3 Class error_category non-virtual members [syserr.errcat.nonvirtuals]:</i></p>
<blockquote>
  <pre><font color="#009A9A"><u>bool operator&lt;(const error_category &amp; rhs) const;</u></font></pre>
  <blockquote>
    <p><font color="#009A9A"><u><i>Returns:</i> <code>less&lt;const 
    error_category*&gt;()( this, &amp;rhs )</code>.</u></font></p>
    <blockquote>
    <p><u><font color="#009A9A">[<i>Note:</i> less([comparisons]) provides a 
    total ordering for pointers. <i>--end note</i>]</font></u></p>
    </blockquote>
    <p><font color="#009A9A"><u><i>Throws:</i> Nothing.</u></font></p>
  </blockquote>
</blockquote>
<p><i>Add a new section before 19.4.1.4 [syserr.errcat.objects], titled &quot;Program 
defined classes derived from error_category&quot;:</i></p>
<blockquote>
<p><span style="background-color: #FFFF00"><i>To be supplied: Requirements for 
classes derived from error_category.</i></span></p>
</blockquote>
<p><i>Add to 19.4.1.4 Error category objects [syserr.errcat.objects]:</i></p>
<blockquote>
<p><span style="font-style: italic; background-color: #FFFF00">To be supplied: 
Description of posix_category and system_category derived classes.</span></p>
</blockquote>
<p><i>Change 19.4.2.1 Class error_code overview [syserr.errcode.overview] as 
indicated:</i></p>
<blockquote>
  <pre>namespace std {

  class error_code {
  public:
    <strike><font color="#FF0000">typedef int_least32_t value_type;</font></strike>

    // constructors:
    error_code();
    error_code(<strike><font color="#FF0000">value_type</font></strike> <font color="#009A9A"><u>int</u></font> val, const error_category&amp; cat);
    <strike><font color="#ff0000">error_code(posix_errno val);</font></strike>
<font color="#009a9a">    <u>template &lt;class <code>ErrorCodeEnum</code>&gt;
</u>      <u>error_code(<code>ErrorCodeEnum</code> e,
</u>        <u>typename enable_if&lt;is_error_code_enum&lt;<code>ErrorCodeEnum</code>&gt; &gt;::type* = 0);</u></font>

    // modifiers:
    void assign(<strike><font color="#FF0000">value_type</font></strike> <font color="#009A9A"><u>int</u></font> val, const error_category&amp; cat);
    <strike><font color="#ff0000">error_code&amp; operator=(posix_errno val);
</font></strike><font color="#009a9a">    <u>template&lt;typename <code>ErrorCodeEnum</code>&gt;
</u>      <u>typename enable_if&lt;is_error_code_enum&lt;<code>ErrorCodeEnum</code>&gt;, error_code&gt;::type &amp;
</u>        <u>operator=( <code>ErrorCodeEnum</code> val );</u></font>;
    void clear();

    // observers:
    <strike><font color="#FF0000">value_type</font></strike> <font color="#009A9A"><u>int</u></font> value() const;
    cont error_category&amp; category() const;
    <strike><font color="#FF0000">posix_errno posix() const;</font></strike>
    <u><font color="#009A9A">error_condition default_error_condition() const;</font></u>
    string message() const;
    wstring wmessage() const;
    operator unspecified-bool-type const;

    <font color="#FF0000"><strike>// relational operators:
</strike></font>    <strike><font color="#FF0000">bool operator==(const error_code&amp; rhs) const;
</font></strike>    <strike><font color="#FF0000">bool operator!=(const error_code&amp; rhs) const;</font></strike>

    private:
    <strike><font color="#FF0000">value_type</font></strike> <font color="#009A9A"><u>int</u></font> val_; // exposition only
    const error_category&amp; cat_; // exposition only
  };

  template &lt;class charT, class traits&gt;
    basic_ostream&lt;charT,traits&gt;&amp;
      operator&lt;&lt;(basic_ostream&lt;charT,traits&gt;&amp; os, const error_code&amp; ec);

  size_t hash_value(const error_code&amp; ec);

} // <i>namespace std</i></pre>
</blockquote>
<p><i>Change 19.4.2.2 Class error_code constructors [syserr.errcode.constructors] 
as indicated:</i></p>
<blockquote>
  <pre>error_code();</pre>
  <blockquote>
    <p><i>Effects:</i> Constructs an object of type <code>error_code</code>.</p>
    <p><i>Postconditions: </i>&nbsp;<code>val_ == 0</code> and <code>cat_ ==
  <font color="#FF0000"><strike>posix_category</strike></font> <u>
  <font color="#009A9A">&amp;system_category</font></u></code>.</p>
    <p><i>Throws:</i> Nothing.</p>
  </blockquote>
  <pre><code>error_code(<strike><font color="#ff0000">value_type</font></strike> <font color="#009a9a"><u>int</u></font> val, const error_category&amp; cat);</code></pre>
  <blockquote>
    <p><i>Effects</i>: Constructs an object of type <code>error_code</code>.</p>
    <p><i>Postconditions: </i>&nbsp;<code>val_ == 0</code> and <code>cat_ == cat</code>.</p>
    <p><i>Throws:</i> Nothing.</p>
  </blockquote>
  <pre><strike><font color="#FF0000"><code>error_code(posix_errno val);
</code></font></strike><u><font color="#009A9A">template &lt;class </font></u><font color="#009A9A"><u><code>ErrorCodeEnum</code>&gt;
</u>  <u>error_code(<code>ErrorCodeEnum</code> e,
</u>    <u>typename enable_if&lt;is_error_code_enum&lt;<code>ErrorCodeEnum</code>&gt; &gt;::type* = 0);</u></font></pre>
  <blockquote>
    <p><i>Effects:</i> Constructs an object of 
    type <code>error_code</code>.</p>
    <p><i>Postconditions:</i> <code><strike><font color="#FF0000">val_ == static_cast&lt;value_type&gt;(val) and cat_ == posix_category</font></strike></code>
    <font color="#009A9A"><u><code>*this == make_error_code(val)</code></u></font>.</p>
    <p><i>Throws:</i> Nothing.</p>
  </blockquote>
</blockquote>
<p><i>Change 19.4.2.3 Class error_code modifiers [syserr.errcode.modifiers] as 
indicated:</i></p>
<blockquote>
  <pre><code>error_code(<strike><font color="#ff0000">value_type</font></strike> <font color="#009a9a"><u>int</u></font> val, const error_category&amp; cat);</code></pre>
  <blockquote>
    <p><i>Postconditions: </i>&nbsp;<code>val_ == val</code> and <code>cat_ == 
    cat</code>.</p>
    <p><i>Throws:</i> Nothing.</p>
  </blockquote>
  <pre><strike><font color="#FF0000"><code>error_code&amp; operator=(posix_errno val);
</code></font></strike><font color="#009A9A"><u>template&lt;typename <code>ErrorCodeEnum</code>&gt;
</u>  <u>typename enable_if&lt;is_error_code_enum&lt;<code>ErrorCodeEnum</code>&gt;, error_code&gt;::type &amp;
</u>    <u>operator=( <code>ErrorCodeEnum</code> val );</u></font></pre>
  <blockquote>
    <p><i>Postconditions:</i> <font color="#FF0000"><code><strike>val_ == static_cast&lt;value_type&gt;(val) and cat_ == posix_category</strike></code></font>
    <font color="#009A9A"><u><code>*this == make_error_code(val)</code></u></font>.</p>
    <p><font color="#009A9A"><u><i>Returns:</i> <code>*this</code>.</u></font></p>
    <p><i>Throws:</i> Nothing.</p>
  </blockquote>
</blockquote>
<p><i>Change 19.4.2.4 Class error_code observers [syserr.errcode.observers] as 
indicated:</i></p>
<blockquote>
  <p><strike><font color="#ff0000"><code>value_type</code></font></strike><code>
  <font color="#009a9a"><u>int</u></font> value() const;</code></p>
  <blockquote>
    <p><i>Returns:</i> <code>val_</code>.</p>
    <p><i>Throws:</i> Nothing.<br>
    <br>
    ...</p>
  </blockquote>
  <pre><strike><font color="#FF0000">posix_errno posix() const;</font></strike>
<u><font color="#009A9A">error_condition default_error_condition() const;</font></u></pre>
  <blockquote>
    <p><i>Returns:</i> <strike><font color="#FF0000"><code>
    category().posix(value)</code></font></strike><code> </code><u>
    <font color="#009A9A"><code>category().default_error_condition(value())</code></font></u>.</p>
    <p><i>Throws:</i> Nothing.</p>
  </blockquote>
</blockquote>
<p><i>Change 19.4.2.5 Class error_code relational operators [syserr.errcode.relational] 
as indicated:</i></p>
<blockquote>
  <pre><font color="#009A9A"><u>bool operator==(const error_code&amp; lhs, const error_code&amp; rhs);</u></font></pre>
  <blockquote>
    <p><font color="#009A9A"><u><i>Returns:</i> <code>lhs.category() == 
    rhs.category() &amp;&amp; lhs.value() == rhs.value()</code>.</u></font></p>
    <p><u><font color="#009A9A"><i>Throws: </i>Nothing.</font></u></p>
  </blockquote>
  <p>bool operator==(const error_code&amp; <strike><font color="#FF0000">ec</font></strike> <u><font color="#009A9A">code</font></u>,
  <strike><font color="#FF0000">posix_errno en</font></strike> <font color="#009A9A"><u>const error_condition&amp; </u></font><u><font color="#009A9A">condition</font></u>);<br>
  bool operator==(<strike><font color="#FF0000">posix_errno en</font></strike> <font color="#009A9A"><u>const error_condition&amp; </u></font><u><font color="#009A9A">condition</font></u>, const error_code&amp; <strike><font color="#FF0000">ec</font></strike> <u><font color="#009A9A">code</font></u>);</p>
  <blockquote>
    <p><i>Returns:</i> <strike><font color="#FF0000"><code>ec.value() == 
    static_cast&lt;error_code::value_type&gt;(en) &amp;&amp; ec.category() == posix_-<br>
    category</code></font></strike><code> </code><font color="#009A9A"><u><code>
    code.category().equivalent(code.value(), condition)<br>
    || condition.category().equivalent(code, condition.value())</code></u></font><code>.</code></p>
    <p><i>Throws: </i>Nothing.</p>
  </blockquote>
  <pre><font color="#009A9A"><u>bool operator==(const error_condition&amp; lhs, const error_condition&amp; rhs);</u></font></pre>
  <blockquote>
    <p><font color="#009A9A"><u><i>Returns:</i> <code>lhs.category() == 
    rhs.category() &amp;&amp; lhs.value() == rhs.value()</code>.</u></font></p>
    <p><u><font color="#009A9A"><i>Throws: </i>Nothing.</font></u></p>
  </blockquote>
  <pre><font color="#009A9A"><u>bool operator!=(const error_code&amp; lhs, const error_code&amp; rhs);</u></font></pre>
  <blockquote>
    <p><font color="#009A9A"><u><i>Returns:</i> <code>!(lhs == rhs)</code>.</u></font></p>
    <p><u><font color="#009A9A"><i>Throws: </i>Nothing.</font></u></p>
  </blockquote>
  <pre>bool operator!=(const error_code&amp; <strike><font color="#FF0000">ec</font></strike> <u><font color="#009A9A">code</font></u>, <strike><font color="#FF0000">posix_errno en</font></strike> <font color="#009A9A"><u>const error_condition&amp; </u></font><u><font color="#009A9A">condition</font></u>);
bool operator!=(<strike><font color="#FF0000">posix_errno en</font></strike> <font color="#009A9A"><u>const error_condition&amp; </u></font><u><font color="#009A9A">condition</font></u>, const error_code&amp; <strike><font color="#FF0000">ec</font></strike> <u><font color="#009A9A">code</font></u>);</pre>
  <blockquote>
    <pre><i>Returns:</i><code> !(</code><strike><font color="#FF0000">ec</font></strike><code> </code><font color="#009A9A"><u>code</u></font><code> == </code><strike><font color="#FF0000">en</font></strike><code> </code><font color="#009A9A"><u>condition</u></font><code>).</code></pre>
    <p><i>Throws: </i>Nothing.</p>
  </blockquote>
  <pre><font color="#009A9A"><u>bool operator!=(const error_condition&amp; lhs, const error_condition&amp; rhs);</u></font></pre>
  <blockquote>
    <p><font color="#009A9A"><u><i>Returns:</i> <code>!(lhs == rhs)</code>.</u></font></p>
    <p><u><font color="#009A9A"><i>Throws: </i>Nothing.</font></u></p>
  </blockquote>
  <pre><font color="#009A9A"><u>bool operator&lt;(const error_code&amp; lhs, const error_code&amp; rhs);</u></font></pre>
  <blockquote>
    <p><font color="#009A9A"><u><i>Returns:</i> <code>lhs.category() &lt; 
    rhs.category()<br>
    </code></u><code>&nbsp; <u>|| (lhs.category() == rhs.category() &amp;&amp; lhs.value() 
    &lt; rhs.value())</u></code><u>.</u></font></p>
    <p><u><font color="#009A9A"><i>Throws: </i>Nothing.</font></u></p>
  </blockquote>
  <pre><font color="#009A9A"><u>bool operator&lt;(const error_condition&amp; lhs, const error_condition&amp; rhs);</u></font></pre>
  <blockquote>
    <p><font color="#009A9A"><u><i>Returns:</i> <code>lhs.category() &lt; 
    rhs.category()<br>
    </code></u><code>&nbsp; <u>|| (lhs.category() == rhs.category() &amp;&amp; lhs.value() 
    &lt; rhs.value())</u></code><u>.</u></font></p>
    <p><u><font color="#009A9A"><i>Throws: </i>Nothing.</font></u></p>
  </blockquote>
  <pre><font color="#009A9A"><u>error_code make_error_code(posix::posix_errno e);</u></font></pre>
  <blockquote>
    <p><font color="#009A9A"><u><i>Returns:</i> <code>error_code(e, 
    posix_category)</code>.</u></font></p>
  </blockquote>
  <pre><font color="#009A9A"><u>error_condition make_error_condition(posix::posix_errno e);</u></font></pre>
  <blockquote>
    <p><font color="#009A9A"><u><i>Returns:</i> <code>error_condition(e, 
    posix_category)</code>.</u></font></p>
  </blockquote>
</blockquote>
    <p><i>Insert before 19.4.3 Class system_error [syserr.syserr], a new 
    section:</i></p>
  <blockquote>
    <p>19.4.n Class <code>error_condition</code> [syserr.errcondition]</p>
    <p>19.4.n.1 Class <code>error_condition</code> overview [syserr.errcondition.overview]</p>
    <p>The class <code>error_condition</code> describes an object used to hold 
    values identifying error conditions. [ Note: <code>
    error_condition</code> values are portable abstractions, while <code>error_code</code> 
    values ([syserr.errcode]) are implementation specific. —end note ]</p>
    
<pre>namespace std {

  class error_condition {
  public:

    // constructors:
    error_condition();
    error_condition(int val, const error_category& cat);
    template &lt;class ErrorConditionEnum&gt;
      error_condition(ErrorConditionEnum e,
        typename enable_if&lt;is_error_condition_enum&lt;ErrorConditionEnum&gt; &gt;::type* = 0);

    // modifiers:
    void assign(int val, const error_category& cat);
    template&lt;typename ErrorConditionEnum&gt;
      typename enable_if&lt;is_error_condition_enum&lt;ErrorConditionEnum&gt;, error_code&gt;::type &amp;
        operator=( ErrorConditionEnum val );
    void clear();

    // observers:
    int value() const;
    const error_category& category() const;
    string message() const;
    operator unspecified-bool-type () const;

  private:
    int val_; // exposition only
    const error_category& cat_; // exposition only
  };

} // namespace std</pre>

<p>19.4.n.2 Class <code>error_condition</code> constructors [syserr.errcondition.constructors]</p>

    <pre>error_condition(); </pre>
    <blockquote>
    
<p><i>Effects:</i> Constructs an object of type <code>error_condition</code>.</p>

<p><i>Postconditions:</i> <code>val_ == 0 and cat_ == posix_category</code>.</p>

<p><i>Throws:</i> Nothing.</p>

    </blockquote>
    <pre>error_condition(value_type val, const error_category&amp; cat);</pre>
    <blockquote>
    
<p><i>Effects: </i>Constructs an object of type error_condition.</p>

<p><i>Postconditions:</i> <code>val_ == val and cat_ == cat</code>.</p>

<p><i>Throws:</i> Nothing.</p>

    </blockquote>
    <pre>template &lt;class ErrorConditionEnum&gt;
  error_condition(ErrorConditionEnum e,
    typename enable_if&lt;is_error_condition_enum&lt;ErrorConditionEnum&gt; &gt;::type* = 0);<code>;</code></pre>
    <blockquote>
    <p><i>Effects:</i> Constructs an object of 
    type <code>error_condition</code>.</p>
    <p><i>Postconditions:</i> <code>*this == make_error_condition(val)</code>.</p>
    <p><i>Throws:</i> Nothing.</p>
    </blockquote>
    <p>19.4.n.3 Class <code>error_condition</code> modifiers [syserr.errcondition.modifiers]</p>
    <pre>void assign(value_type val, const error_category&amp; cat); </pre>
    <blockquote>
      <p><i>Postconditions:</i> <code>val_ == val and cat_ == cat</code>. </p>
      <p><i>Throws:</i> Nothing.</p>
    </blockquote>
    <pre>template&lt;typename ErrorConditionEnum&gt;
  typename enable_if&lt;is_error_condition_enum&lt;ErrorConditionEnum&gt;, error_code&gt;::type &amp;
    operator=( ErrorConditionEnum val );;</pre>
    <blockquote>
      <p><i>Postconditions:</i> <code>*this == make_error_condition(val)</code>.</p>
      <p><i>Throws:</i> Nothing.</p>
    </blockquote>
  <p><code>void clear();</code></p>
  <blockquote>
    <p><i>postcondition:</i> <code>value() == 0 &amp;&amp; category() == 
    posix_category</code></p>
  </blockquote>
    <p>19.4.n.4 Class <code>error_condition</code> observers [syserr.errcondition.observers]</p>
    <pre>value_type value() const;</pre>
    <blockquote>
      <p><i>Returns:</i> <code>val_</code>.</p>
      <p><i>Throws:</i> Nothing</p>
    </blockquote>
    <pre>const error_category&amp; category() const;</pre>
    <blockquote>
      <p><i>Returns:</i> <code>cat_</code>.</p>
      <p>Throws: Nothing.</p>
    </blockquote>
    <pre>string message() const;</pre>
    <blockquote>
      <p><i>Returns:</i> <code>category().message(value())</code>.</p>
      <p><i>Throws:</i> Nothing.</p>
    </blockquote>
    <pre>operator unspecified-bool-type () const;</pre>
    <blockquote>
      <p><i>Returns: </i>If <code>value() != 0</code>, returns a value that will 
      evaluate <code>true</code> in a boolean context; otherwise, returns a 
      value that will evaluate <code>false</code>. The return type shall not be 
      convertible to <code>int</code>. </p>
      <p><i>Throws:</i> Nothing.</p>
      <p>&nbsp;[ <i>Note:</i> This conversion can be used in contexts where a
      <code>bool</code> is expected (e.g., an if condition); however, implicit 
      conversions (e.g., to <code>int</code>) that can occur with <code>bool</code> 
      are not allowed, eliminating some sources of user error. One possible 
      implementation choice for this type is pointer to member. <i>—end note</i> 
      ]</p>
    </blockquote>

</blockquote>
<h4>Rationale</h4>
<h5><a name="Unintended-consequences">Unintended consequences </a></h5>
  <p>For example, say the user writes:</p>
  <blockquote>
  <p><code>error_code ec;<br>
  some_operation(ec);<br>
  if (ec == boo_boo)<br>
&nbsp; { ... }</code></p>
  </blockquote>
  <p><code>operator ==</code> is currently overload on <code>enum posix_errno</code> 
  , so if <code>boo_boo</code> is a <code>posix_errno</code> constant, the 
  result will be as if the code read:</p>
  <blockquote>
  <p><code>if (ec.posix() == boo_boo)</code></p>
  </blockquote>
  <p>But this is assuming the users is trying to write portable code. If the 
  user instead is writing system specific code, what is really wanted is the 
  equivalent of:</p>
  <blockquote>
  <p><code>if (ec == error_code(boo_boo, <i>boo_boo's category</i>))</code></p>
  </blockquote>
  <p>With the interface as currently specified, the user would have to write 
  that out in full. Unfortunately, the user might well opt for this instead:</p>
  <blockquote>
  <p><code>if (ec.value() == boo_boo)</code></p>
  </blockquote>
  <p>Unfortunately, that is really error prone. If the implementation happens to 
  return an <code>error_code</code> with the same value as <code>boo_boo</code>, 
  but in a different category, so the result will be true when it should be 
  false.</p>
  <h3><a name="Issue8">Issue 8</a>: [Withdrawn]</h3>
  <h3><a name="Issue9">Issue 9</a>: EOTHER hijacks POSIX macro space, constant 
  name too general. </h3>
<p>The working draft specifies <code>other = EOTHER</code> in the specification 
of posix_errno in 19.4 System error support, with the specification that <code>
EOTHER</code> is not a POSIX-defined macro in 19.3 Error numbers. Earlier papers 
stated that this new macro will be added to the include file <code>cerrno</code>.
</p>
<p>The problem with this is that C++ is hijacking the POSIX macro space, which 
should be avoided as future versions of the POSIX standard may add more error 
macros, including <code>EOTHER</code>, but may have it mean something else.</p>
<p>Submitted by Benjamin Kosnik.</p>
<h4>Proposed resolution</h4>
<p><i>Change 19.3 Error numbers [errno], paragraph one, as indicated:</i></p>
<blockquote>
  <p>The header <code>&lt;cerrno</code>&gt; is described in (Table 29). Its contents 
  are the same as the POSIX header <code>&lt;errno.h&gt;</code>, except that <code>
  errno</code> shall be defined as a macro<font color="#FF0000"><strike>, and an 
  additional macro EOTHER shall be defined to represent errors not specified by 
  the POSIX standard</strike></font>. [ <i>Note:</i> The intent is to remain in close 
  alignment with the POSIX standard. <i>--end note</i> ]</p>
</blockquote>
<p><i>From 19.3 Error numbers [errno], Header &lt;cerrno&gt; synopsis, strike </i>
<font color="#FF0000"><strike>EOTHER</strike></font><i>.</i></p>
<p><i>Change 19.4 System error support [syserr], Header &lt;system_error&gt; synopsis 
as indicated:</i></p>
<blockquote>
  <p><code><strike><font color="#FF0000">other = EOTHER,</font></strike></code></p>
</blockquote>
<p><i>For 19.4.1.2 Class error_category virtual members [syserr.errcat.virtuals] 
paragraph 3, see <a href="#syserr-errcat-virtuals">issue 7 proposed wording</a>.</i></p>
<h3><a name="Issue10">Issue 10</a>: Header dependencies are non-trivial</h3>
<p>In section <a href="http://19.4.2.6" target="_blank">19.4.2.6</a> Class 
error_code non-member functions, an ostream inserter for <code>error_code</code> 
is defined for the primary ostream template. This will necessitate the inclusion 
of the <code>ostream</code> include file, which has large dependencies on other 
standard library features. The practical result is that the <code>system_error</code> 
include, far from being a lightweight, stand-alone error-reporting facility, 
will instead come with significant compile time cost.</p>
  <p><i>Fix:</i> Move the <code>error_code</code> inserter to the <code>ostream</code> 
  include file, or relax the requirements such that only <code>char</code> and
  <code>wchar_t</code> specializations are required. </p>
<p>Submitted by Benjamin Kosnik.</p>
  <h4>Proposed resolution</h4>
  <p><i>Move the following text from 19.4.2.1 Class error_code overview [syserr.errcode.overview] 
  to the non-member section of the synopsis in 27.6.2.1 Class template 
  basic_ostream [ostream], making the indicated changes:</i></p>
<blockquote>
  <pre>template &lt;class charT, class traits&gt;
  basic_ostream&lt;charT,traits&gt;&amp; operator&lt;&lt;(basic_ostream&lt;charT,traits&gt;&amp;<font color="#FF0000"><strike> os</strike></font>, const error_code&amp;<font color="#FF0000"><strike> ec</strike></font>);

<u><font color="#009A9A">template &lt;class charT, class traits&gt;
  basic_ostream&lt;charT,traits&gt;&amp; operator&lt;&lt;(basic_ostream&lt;charT,traits&gt;&amp;&amp;, const error_code&amp;);</font></u></pre>
</blockquote>
<p><i>Move the following text from 9.4.2.6 Class error_code non-member functions 
[syserr.errcode.nonmembers] to a new sub-section following 27.6.2.6.4 Character 
inserter function templates [ostream.inserters.character], making the indicated 
changes:</i></p>
<blockquote>
  <pre>template &lt;class charT, class traits&gt;
  basic_ostream&lt;charT,traits&gt;&amp; operator&lt;&lt;(basic_ostream&lt;charT,traits&gt;&amp;<strike><font color="#FF0000"> os</font></strike> <u><font color="#009A9A">out</font></u>, const error_code&amp; ec);

<u><font color="#009A9A">template &lt;class charT, class traits&gt;
  basic_ostream&lt;charT,traits&gt;&amp; operator&lt;&lt;(basic_ostream&lt;charT,traits&gt;&amp;&amp; out, const error_code&amp; ec);</font></u></pre>
  <blockquote>
  <p><i>Effects:</i> <code><font color="#FF0000"><strike>os</strike></font>
  <font color="#009A9A"><u>out</u></font> &lt;&lt; ec.category().name() &lt;&lt; ’:’ &lt;&lt; 
  ec.value()</code>.</p>
  <p><font color="#009A9A"><u><i>Returns:</i> <code>out</code></u></font></p>
  </blockquote>
</blockquote>
<h3><a name="Issue11">Issue 11</a>: Overly complex <code>error_code::value_type</code> 
with circular dependencies</h3>
<p>Section <a href="http://19.4.2.1" target="_blank">19.4.2.1</a> specifies
<code>error_code::value_type</code> as <code>typedef int_least32_t value_type;</code>. 
However, this type is used in <code>error_category</code>, which has to be 
defined before any of the trivial members in <code>error_code</code> can be made 
inline. </p>
<p>In addition, this complexity results in unsightly casting in the <code>
error_code</code> relational operators and constructor specifications.</p>
<p><i>Possible Fix: </i>Assume <code>error_code::value_type</code> is of type
<code>int</code>, as specified by both C and POSIX.</p>
<p>Submitted by Benjamin Kosnik.</p>
<h4>Proposed resolution</h4>
<p><i>Change the type to int. See proposed wording for <a href="#Issue7">issue 7</a>.</i></p>
<h4>Rationale</h4>
<p><i>The typedef is a historical artifact left over from early development of 
the class. An int is sufficient for all operating systems we are aware of. </i></p>
<h3><a name="Issue12">Issue 12</a>: Missing throw specifications</h3>
<p>In <a href="http://19.4.1.2" target="_blank">19.4.1.2</a> Class 
error_category virtual members, all member functions are defined to not throw, 
but do not have <code>throw()</code> specifications. </p>
<p>The same hold for <code>error_code</code> member functions that are modifiers 
and observers. i.e, sections <a href="http://19.4.2.3" target="_blank">19.4.2.3</a> 
and <a href="http://19.4.2.4" target="_blank">19.4.2.4</a>.</p>
  <p><i>Proposed Fix:</i> Add in missing <code>throw()</code> specifications.</p>
<p>Submitted by Benjamin Kosnik.</p>
<h4>Proposed resolution</h4>
<p><i>No action necessary.</i></p>
<h4>Rationale</h4>
<p><i>The Working Paper is inconsistent in its use of&nbsp; <code>throw()</code> 
specifications. Many LWG members prefer the &quot;Throws: Nothing&quot; specification as 
used in the current working paper wording for diagnostics.</i></p>
<h3><a name="Issue13">Issue 13</a>: Missing <code>system_error</code> 
constructor</h3>
<p>All existing classes derived from <code>std::exception</code> provide either 
a default constructor or a constructor taking a single <code>const std::string&amp;</code> 
parameter. The current specification for <code>system_error</code> breaks with 
this.</p>
<p>Submitted by Benjamin Kosnik.</p>
<blockquote>
  <p><i>Proposed Fix:</i> Add a constructor to <code>system_error</code> that takes a<code> const 
  std::string&amp;</code> argument.</p>
</blockquote>
<h4>Proposed resolution</h4>
<p><i>No action necessary.</i></p>
<h4>Rationale</h4>
  <p><i>The design of the constructors, including order of 
  arguments, was a considered 
  decision after much discussion with Peter Dimov and others on the Boost list. A 
  primary objective of <code>system_error</code> is to report an <code>
  error_code</code>. We don't want to encourage construction of <code>
  system_error</code> objects that don't have one. Thus the constructors all 
  take <code>error_code</code> or equivalent arguments first in addition to the 
  what string argument. Not supplying a default constructor avoids the 
  nonsensical construction of system_error representing &quot;no error&quot;.</i></p>
<h3><a name="Issue14">Issue 14</a>: <code>error_category</code> equality via 
address comparison</h3>
<p>Section <a href="http://19.4.1.3" target="_blank">19.4.1.3</a> Class 
error_category non-virtual members specifies address comparisons between <code>
error_category</code> base objects to determine equality and inequality. This 
can be fragile or difficult in shared memory or distributed systems, and may 
lead to incorrect results for equivalent <code>error_category</code> objects.</p>
<p>Submitted by Benjamin Kosnik.</p>
<blockquote>
  <p><i>Fix: </i>Equality compare on internal details of the message catalog 
  characteristics.</p>
</blockquote>
  <h4>Proposed resolution</h4>
<p><i>No action necessary.</i></p>
<h4>Rationale</h4>
  <p><i>Resolved by <a href="#Issue6">Issue 6</a>: Class error_category should 
  be non-copyable. No further action needed.</i></p>
<h3><a name="Issue15">Issue 15</a>: Extending <code>error_code::value_types</code> constants and 
user-defined <code>error_category</code> objects</h3>
<p>Section 19.4 specifies <code>posix_errno</code> as an enum. As such, there is 
no way to extend it for native error values, which will presumably be in the 
form of another enum, in some user-defined space. </p>
<p>Section 19.4.1.4 Error category 
objects vaguely specifies <code>posix_category</code> and <code>native_category</code> 
as external objects. As such, the implementation details are likely to remain 
private, making simple derivation and extension tricky or difficult.</p>
<p>Submitted by Benjamin Kosnik.</p>
<h4>Proposed resolution</h4>
<p><i>To 19.4.1.1 Class error_category overview [syserr.errcat.overview], at the 
end, add:</i></p>
<blockquote>
<p>[<i>Example:</i> A user or third-party library can provide an additional
<code>error_category</code>:</p>
  <blockquote>
    <pre>extern const error_category&amp; my_error_category;

enum my_error { boo_boo_1=1, boo_boo_2 };

namespace std {
  inline error_code make_error_code(my_error e)
    { return error_code( e, my_error_category ); }
}</pre>
  </blockquote>
<p><i>-- end example</i>]</p>
</blockquote>
<p><i>After 17.4.4.8 Restrictions on exception handling [res.on.exception.handling], 
add a new sub-section (presumably 17.4.4.9):</i></p>
<blockquote>
<p>17.4.4.9 Value of error codes</p>
<p>Certain functions in the C++ Standard Library report errors via 
a <code>
std::error_code</code>([syserr.errcode.overview]) object. That object's <code>category()</code> 
member shall return a reference to <code>std::system_category</code> for errors 
originating from the operating system, or a reference to an implementation-defined
<code>error_category </code>object for errors originating elsewhere. The implementation shall define 
the possible 
values of <code>value()</code> 
for each of these error categories. [<i>Example:</i> For a POSIX-based operating 
system, an implementation is encouraged to define the <code>std::system_category</code> 
values as identical to the POSIX <code>errno</code> values, plus additional values 
as defined by the operating system's documentation. An 
implementation on a non-POSIX operating system is encouraged to define values 
identical to the operating system's error values. For errors that don't 
originate from the operating system, the implementation may provide enums for the associated values.
<i>-- end example</i>]</p>
</blockquote>
<h4><a name="Issue15-Rationale">Rationale</a></h4>
<p><i>posix_errno should not be extended by users or implementers. Only the 
POSIX committee can extend the set of POSIX errnos. Thus the concern about 19.4 
is not a defect.</i></p>
<p><i>Regarding 19.4.1.4; yes, the implementation details of error_categories 
are private, and that is deliberate encapsulation.</i></p>
<p><i>The concern over derivation and extension can be addressed in several 
ways. The proposed resolution's example should clarify what users need to do. For 
implementers, the proposed addition to clause 17 provides general guidance. An example 
of actual implementation could be outside the scope of the standard. For 
illustration, extracts from the current Boost implementation for several platforms 
are given 
below:</i></p>
<blockquote>
<pre>    //  Operating system specific interfaces  --------------------------------//

    //  The interface is divided into general and system-specific portions to
    //  meet these requirements:
    //
    //  * Code calling an operating system API can create an error_code with
    //    a single category (system_category), even for POSIX-like operating
    //    systems that return some POSIX errno values and some native errno
    //    values. This code should not have to pay the cost of distinguishing
    //    between categories, since it is not yet known if that is needed.
    //
    //  * Users wishing to write system-specific code should be given enums for
    //    at least the common error cases.
    //
    //  * System specific code should fail at compile time if moved to another
    //    operating system.

#ifdef BOOST_POSIX_API

    //  POSIX-based systems  -------------------------------------------------//

    //  To construct an error_code after a API error:
    //
    //      error_code( errno, system_category )

    //  User code should use the portable "posix" enums for POSIX errors; this
    //  allows such code to be portable to non-POSIX systems. For the non-POSIX
    //  errno values that POSIX-based systems typically provide in addition to 
    //  POSIX values, use the system specific enums below.

# ifdef __CYGWIN__

    namespace cygwin
    {
      enum cygwin_errno
      {
        no_net = ENONET,
        no_package = ENOPKG,
        no_share = ENOSHARE,
      };
    }  // namespace cygwin

    template<> struct is_error_code_enum<cygwin::cygwin_errno>
      { static const bool value = true; };

    inline error_code make_error_code(cygwin::cygwin_errno e)
      { return error_code( e, system_category ); }

# elif defined(linux) || defined(__linux) || defined(__linux__)

    namespace Linux  // linux lowercase name preempted by use as predefined macro
    {
      enum linux_error
      {
        advertise_error = EADV,
        bad_exchange = EBADE,
        bad_file_number = EBADFD,
        bad_font_format = EBFONT,
        bad_request_code = EBADRQC,
        ...
        unclean = EUCLEAN,
      };
    }  // namespace Linux

    template<> struct is_error_code_enum<Linux::linux_errno>
      { static const bool value = true; };

    inline error_code make_error_code(Linux::linux_error e)
      { return error_code( e, system_category ); }

# endif


#elif defined(BOOST_WINDOWS_API)

    //  Microsoft Windows  ---------------------------------------------------//

    //  To construct an error_code after a API error:
    //
    //      error_code( ::GetLastError(), system_category )

    namespace windows
    {
      enum windows_error
      {
        success = 0,
        // These names and values are based on Windows winerror.h
        invalid_function = ERROR_INVALID_FUNCTION,
        file_not_found = ERROR_FILE_NOT_FOUND,
        path_not_found = ERROR_PATH_NOT_FOUND,
        too_many_open_files = ERROR_TOO_MANY_OPEN_FILES,
        access_denied = ERROR_ACCESS_DENIED,
        invalid_handle = ERROR_INVALID_HANDLE,
        arena_trashed = ERROR_ARENA_TRASHED,
        not_enough_memory = ERROR_NOT_ENOUGH_MEMORY,
        ...
        already_exists = ERROR_ALREADY_EXISTS,
      };
    }  // namespace windows

    template<> struct is_error_code_enum<windows::windows_error>
      { static const bool value = true; };

    inline error_code make_error_code(windows::windows_error e)
      { return error_code( e, system_category ); }

#else
#  error BOOST_POSIX_API or BOOST_WINDOWS_API must be defined
#endif
</pre>
</blockquote>
<h3><a name="Issue16">Issue 16</a>: POSIX versus native <code>error_category</code></h3>
<p>Should <code>posix_category</code> and <code>native_category</code> be able 
to have the same address?</p>
<blockquote>
<p><i>In theory, yes. In practice, real POSIX-based operating systems such as 
Linux add additional error codes, so the error categories have to be different. 
That allows an implementation to use <code>error_code(errno, native_category)</code> 
to construct an error_code. If the POSIX values of errno were a different 
category from the non-POSIX values, an expensive lookup would have to be done to 
assign the category. </i></p>
</blockquote>
<p>Should the member function <code>error_category::posix</code> exist for the 
predefined object <code>posix_category</code>? Isn't this a no-op, and best 
added to the class implementing <code>native_category</code>?</p>
<blockquote>
<p><i>The <code>
error_category</code> virtuals exist to support the equivalent <code>error_code</code> 
and <code>error_condition</code> 
member functions, allowing user-defined error categories. This mechanism unravels if <code>error_category::posix</code> 
(or its <a href="#Issue7">issue 7</a> replacements) 
isn't present for all error categories.</i></p>
</blockquote>
<p>Should the division be between underlying system errors needed by the C++0x 
standard library and user-defined error messages, instead of between POSIX and 
native?</p>
<blockquote>
<p><i>Early versions of the current design did divide the world along 
standard library / native lines. The design evolved into a POSIX / 
operating-system / 
user-defined breakdown because it met specific needs of users and third-party 
library suppliers, who must deal with a variety of real-world use cases, and 
implementers who sometimes must rely on API's other than those of the operating 
system.. That 
isn't to say another design wouldn't work, but this design is known to work and 
represents successful existing practice. Note that the dichotomy between POSIX 
and native is clarified greatly by the introduction of <code>class 
error_condition</code> in <a href="#Issue7">
issue 7</a>.</i></p>
</blockquote>
<p>Submitted by Benjamin Kosnik.</p>
<h4>Proposed resolution</h4>
<p><i>Change the name <code>native_category</code> to <code>system_category</code>. 
See proposed wording for <a href="#Issue7">issue 7</a>.</i></p>
<h4>Rationale</h4>
<p><i>The name <code>native_category</code> seems to be causing some confusion. 
It is changed to <code>system_category</code> to more clearly indicate this 
category represents errors from the operating system itself rather than some 
other library used by the implementation.</i></p>
<p><i>The answers to the questions are given in italics above.</i></p>
<h3><a name="Issue17">Issue 17</a>: Broken <code>error_category::message</code> 
member functions</h3>
<p>Section <a href="http://19.4.1.2" target="_blank">19.4.1.2</a> Class 
error_category virtual members defines members <code>message</code> and <code>
wmessage</code>, and notes an intention to provide a locale-specific string. 
However, there is no indication that this is integrated into the existing 
standard library infrastructure for locale, ie <code>std::locale</code>.</p>
<p>There are two distinct issues: one, construction of <code>error_category</code> 
would have to take some kind of <code>std::locale</code> parameter, some kind of 
getter/setter would have to exist to provide locale data, or <code>message</code> 
would have to take a <code>std::locale</code> argument. This last option would 
require serious re-work of the <code>system_error::what</code> member function.</p>
<p>The second issue is code conversion so that <code>wmessage</code> could 
return a wide string from a message catalog. The use case for this is 
theoretical at the moment, as wide-character message catalogs are not known. For 
this, <code>std::codecvt</code> would be the preferred mechanism, and that 
depends on three template parameters. If this route is followed, it may make 
sense to templatize the entire class, and separate out <code>message</code> for
<code>char</code> instantiations and <code>wmessage</code> for <code>wchar_t</code> 
instantiations. </p>
<p>Note that <code>error_code</code> has these same member functions, which 
forward to the <code>error_category</code> member functions, so this could be 
considered a defect in both class specifications.</p>
<p>Submitted by Benjamin Kosnik.</p>
  <h4>Proposed resolution</h4>
  <p><i>Change 19.4.1.1 Class error_category overview [syserr.errcat.overview] 
  paragraph 1 as indicated:</i></p>
  <blockquote>
    <pre><font color="#FF0000"><strike>virtual string message(error_code::value_type ev) const = 0;
virtual wstring wmessage(error_code::value_type ev) const = 0;</strike></font></pre>
</blockquote>
  <p><i>Change 19.4.1.2 Class error_category virtual members [syserr.errcat.virtuals] 
  paragraph 4 and 5 as indicated:</i></p>
  <blockquote>
    <pre><font color="#FF0000"><strike>virtual string message(error_code::value_type ev) const = 0;
virtual wstring wmessage(error_code::value_type ev) const = 0;</strike></font></pre>
    <p><font color="#FF0000"><strike><i>Returns:</i> A string that describes the error condition denoted by ev.
    </strike></font><strike><font color="#FF0000">[ Note: The intent is to return a locale-specific string that describes the 
    error corresponding to ev. --end note ]</font></strike></p>
    <p><strike><font color="#FF0000"><i>Throws: </i>Nothing.</font></strike></p>
</blockquote>
  <p><i>Change 19.4.2.1 Class error_code overview [syserr.errcode.overview] 
  paragraph 1 as indicated:</i></p>
  <blockquote>
    <pre><font color="#FF0000"><strike>string message() const;
wstring wmessage() const;</strike></font></pre>
</blockquote>
  <p><i>Change 19.4.2.4 Class error_code observers [syserr.errcode.observers] 
  beginning at paragraph 6 as indicated:</i></p>
  <blockquote>
    <pre><font color="#FF0000"><strike>string message() const;</strike></font></pre>
    <blockquote>
  <p><font color="#FF0000"><strike><i>Returns</i>: <code>
  category().message(value())</code>.</strike></font></p>
  <p><font color="#FF0000"><strike><i>Throws:</i> Nothing.</strike></font></p>
    </blockquote>
    <pre><font color="#FF0000"><strike>wstring wmessage() const;</strike></font></pre>
    <blockquote>
  <p><font color="#FF0000"><strike><i>Returns</i>: <code>
  category().wmessage(value())</code>.</strike></font></p>
  <p><font color="#FF0000"><strike><i>Throws:</i> Nothing.</strike></font></p>
    </blockquote>
</blockquote>
  <p><i>Change 19.4.3.2 Class system_error members [syserr.syserr.members] as 
  indicated:</i></p>
  <blockquote>
    <pre><font color="#FF0000"><strike>const char *what() const;</strike></font></pre>
    <blockquote>
  <p><font color="#FF0000"><strike><i>Returns:</i> An NTBS incorporating 
  runtime_error::what() and code().message().</strike></font></p>
  <p><font color="#FF0000"><strike>[ <i>Note:</i> One possible implementation 
  would be:</strike></font></p>
      <blockquote>
        <pre><font color="#FF0000"><strike>if (msg.empty())
{
</strike>  <strike>try
</strike>  <strike>{
</strike>    <strike>std::string tmp = runtime_error::what();
</strike>    <strike>if (code())
</strike>    <strike>{
</strike>    <strike>if (!tmp.empty())
</strike>      <strike>tmp += &quot;: &quot;;
</strike>    <strike>tmp += code().message();
</strike>    <strike>}
</strike>  <strike>swap(msg, tmp);
</strike>  <strike>}
catch(...)
{
</strike>  <strike>return runtime_error::what();
}
return msg.c_str();</strike></font></pre>
      </blockquote>
      <p><font color="#FF0000"><strike><i>end note </i>]</strike></font></p>
    </blockquote>
</blockquote>
<h4>Rationale</h4>
  <p><i>Discussed by the LWG in Toronto. None of the current standard exception 
  classes worry about wide messages or locales, so a fix for one particular 
  exception probably isn't the right approach. Better to remove the functions 
  until the problem and solution can be more fully explored.</i></p>
  <p><i>After the Toronto meeting, an email discussion between Beman Dawes, 
  Peter Dimov, Christopher Kohlhoff, and Benjamin Kosnik discussed possible 
  solutions without reaching consensus. The most likely solution was something 
  along the lines of:</i></p>
<blockquote>
  <pre><span class="q">string error_message(error_code ec, const locale&amp; loc )
{
 &nbsp;messages&lt;char&gt;&amp; f = use_facet&lt; messages&lt;char&gt; &gt;( loc );
 &nbsp;int cat = f.open( ec.category().name(), loc );
 &nbsp;string r = f.get( cat, 0, ec.value(), &quot;&quot; );
 &nbsp;f.close( cat );
 &nbsp;return r;
}</span></pre>
</blockquote>
<p><i><span class="q">While this approach looked promising, it wasn't clear how 
it would work with user-defined error categories, and whether or not it was 
actually practical for the full range of operating systems.</span></i></p>
<h3><a name="Issue18">Issue 18</a>: <code>system_error::what</code> and constructors</h3>
<p>In <a href="http://19.4.3.2" target="_blank">19.4.3.2</a> Class system_error 
members, the constructor definitions and <code>what</code> specification collude 
to force exception-unsafe behavior, and multiple <code>std::string</code> data 
members.</p>
<p>This in effect mandates elaborate string modification as part of <code>
system_error::what</code>, which may cause unanticipated exceptions to occur, in 
addition to being inefficient.</p>
<p>These specifications are a break with the existing <code>stdexcept</code> 
requirements and the exception hierarchy design philosophy: by making <code>what</code> 
virtual, users can reasonably expect to have derived classes with different 
return strings from <code>what</code>. Indeed, that's the point.</p>
<p>In addition, with all these additional requirements, there still exists no 
way to pass in locale-specific strings.</p>
  <blockquote>
<p><i>See issue 17.</i></p>
  </blockquote>
<p>Submitted by Benjamin Kosnik.</p>
<h4>Proposed resolution</h4>
<p><i>Change 19.4.3.2 Class system_error members [syserr.syserr.members], 
paragraph 4, as indicated:</i></p>
<blockquote>
<p><code>const error_code&amp; code() const <u><font color="#009A9A">throw()</font></u>;</code></p>
</blockquote>
<p><i>Change 19.4.3.2 Class system_error members [syserr.syserr.members], 
paragraph 5, as indicated:</i></p>
<blockquote>
<p><code>const char *what() const <u><font color="#009A9A">throw()</font></u>;</code></p>
</blockquote>
<p><i>No additional action necessary.</i></p>
<h4>Rationale</h4>
<p><i>Exception safety is dealt with by the proposed resolution. The data 
members are not specified; implementations are free to use a std::string or some 
completely different mechanism. Implementations will presumably use lazy 
evaluation, so much of the cost will only occur if what() is actually called.</i> <i>No action necessary.</i></p>
<p><code>system_error::what</code><i>&nbsp; and </i><code>code</code><i> do 
specify throw() in the synopsis to deal with the exception issue, but not in the 
member descriptions. See proposed resolution.</i></p>
<p><i>The semantics of what() are 
extremely valuable to users, and any inefficiency is minor compared to the 
general overhead of an exception being thrown. Existing code, such as main() 
exception monitors that catch std::exception and report the results of 
exception::what(), works without modification for std::system_error. and that's 
very desirable. </i>&nbsp;<i>No additional action necessary. </i></p>
<p><i>what() is virtual in the base class, so is virtual in class </i><code>
system_error</code><i> too.</i> <i>And</i> <code>system_error::what</code><i> 
does normally return a different string than </i><code>runtime_error::what</code>. <i>No action necessary.</i></p>
<h3><a name="Issue19">Issue 19</a>: Should classes error_code and error_category be less-than 
comparable?</h3>
<p>The Boost version provides <code>operator&lt;</code>&nbsp; for both, allowing objects of class
<code>error_code</code> to be easily used as keys for associative containers. I 
can't remember any rationale for removing them from the proposal; it looks like 
a simple oversight.</p>
<p>Submitted by Beman Dawes.</p>
  <h4>Proposed resolution</h4>
  <p><i>See proposed wording for <a href="#Issue7">issue 7</a>.</i></p>
  <h3><a name="Issue20">Issue 20</a>: Which error_category applies to POSIX-like 
  operating system errors unclear</h3>
  <p>For POSIX based operating systems (Unix, Linux, Mac OS, etc.) it isn't 
  clear to either implementors or users whether operating system errors will be 
  classified as <code>native_category</code> or <code>posix_category</code>.</p>
  <p>Submitted by Beman Dawes.</p>
  <h4>Proposed resolution </h4>
  <p><i>No action necessary. This is essentially a FAQ (see below) that has to 
  be dealt with by education. The <a href="#Issue15-Rationale">issue 15 
  rationale</a> may also be helpful.</i></p>
  <h4>FAQ</h4>
  <p><i><b>What error_category are the errors arising from POSIX-based operating 
  systems such as Unix, Linux, Mac OS?</b></i> They are <code>system_category</code> 
  errors.</p>
  <h3><a name="Issue21">Issue 21</a>: Error enums add lots of names to namespace 
  std</h3>
  <p>Would it be better to move them into sub-namespaces?</p>
  <p>Submitted by Chris Kohlhoff</p>
  <h4>Proposed resolution</h4>
  <p><i>Resolved by moving POSIX enums into a sub-namespace. See proposed wording for <a href="#Issue7">issue 7</a>.</i></p>
  <h4>Rationale</h4>
  <p><i>These names should reflect the names assigned by the originating 
  organization, such as the POSIX committee, so are somewhat beyond the control 
  of the C++ committee. Also, name clashes with platform specific error enums 
  occur in the absence of sub-namespaces. Experiments with real code show 
  introduction of a posix sub-namespace improves readability</i>.</p>
  <h3><a name="Issue22">Issue 22</a>: Out of memory should throw <code>bad_alloc</code>, 
  not <code>system_error</code></h3>
  <p>If an out of memory condition occurs in a call to an operating system API 
  from a standard library implementation, should the resulting exception be
  <code>bad_alloc</code> or <code>system_error</code>?</p>
  <h4>Proposed resolution</h4>
  <p><i>To 19.4.3.1 Class system_error overview [syserr.syserr.overview] add:</i></p>
  <blockquote>
  <p>[<i>Note:</i> if an error represents an out-of-memory condition, 
  implementations are encouraged to throw an exception of type <code>bad_alloc</code> 
  ([bad.alloc]) rather than <code>system_error</code>. <i>--end note</i>]</p>
  </blockquote>
  <h4>Rationale</h4>
  <p><i>The LWG discussed this in Toronto, and wishes bad_alloc be thrown.</i></p>
  <p><i>The proposed wording is in the form of a non-normative note because the 
  type of exception throw on out of memory is implementation defined. See 
  17.4.4.8 Restrictions on exception handling [res.on.exception.handling]</i></p>
  <h3><a name="Issue23">Issue 23</a>: <code>error_category::name()</code> should 
  return <code>const char *</code></h3>
  <p>The specification of <code>error_category::name()</code> as returning a 
  constant string reference makes it too easy to implement in a non-thread-safe 
  way such as a static function-scope variable. To be safe I think the function 
  should return either a <code>std::string</code> by value or <code>const char*</code>. 
  My preference would be for the latter, since it better reflects that what you 
  are defining is a string constant that corresponds to the category.</p>
  <p>Submitted by Chris Kohlhoff.</p>
  <h4>Proposed resolution</h4>
  <p><i>Change 19.4.1.1 Class error_category overview [syserr.errcat.overview] as 
  indicated:</i></p>
  <blockquote>
    <pre>virtual const <font color="#FF0000"><strike>string&amp;</strike></font> <u><font color="#009A9A">char*</font></u> name() const = 0;</pre>
</blockquote>
  <h3><a name="Issue24">Issue 24</a>: <code>system_error</code> what-less 
  constructors needed</h3>
  <p>The problem of the what arg becomes more significant once you start
  composing operations. Since we're providing both throwing and
  non-throwing overloads, to reduce code duplication I like to implement
  the operation once in non-throwing form and then wrap it with the
  throwing version. For example:
  
  <blockquote>
  
  <pre>  error_code download_to_directory(
   &nbsp; &nbsp;std::string dirname, std::string url, error_code&amp; ec)
  {
   &nbsp;if (mkdir(dirname, ec))
   &nbsp; &nbsp;return ec;
  
   &nbsp;std::string host = url2host(url);
   &nbsp;tcp::endpoint ep = resolve(host, ec);
   &nbsp;if (ec) return ec;
  
   &nbsp;return download(dirname, ep, url2path(url), ec);
  }
  
  void download_to_directory(
   &nbsp; &nbsp;std::string dirname, std::string url)
  {
   &nbsp;error_code ec;
   &nbsp;download_to_directory(dirname, url, ec);
   &nbsp;if (ec) throw system_error(ec, ?);
  }  </pre>
  
  </blockquote>
  
  The functions resolve() and download() are themselves composed
  operations, which may in turn use other composed operations. The
  original &quot;what&quot; of any error code is well and truly lost by the time you
  reach the throw.</p>

  <p>Submitted by Chris Kohlhoff.</p>

  <p><i>Beman Dawes comments: It is often very useful to users to know the name 
  of the function where a system_error originates. Thus I would write the line 
  in question like this:</i></p>
  <blockquote>
    <pre>if (ec) throw system_error(ec, &quot;download_to_directory&quot;);</pre>
</blockquote>
<p><i>But that is a QOI issue, so I support adding constructors that do not 
require a what string.</i></p>
  <h4>Proposed resolution</h4>
  <p><i>Change 19.4.3.1 Class system_error overview [syserr.syserr.overview] as 
  indicated:</i></p>
  <blockquote>
    <pre>class system_error : public runtime_error {
public:
  system_error(error_code ec, const string&amp; what_arg);
  <font color="#009A9A"><u>system_error(error_code ec);</u></font>
  system_error(error_code::value_type ev, const error_category&amp; ecat,
      const string&amp; what_arg);
  <u><font color="#009A9A">system_error(error_code::value_type ev, const error_category&amp; ecat);</font></u>
  const error_code&amp; code() const throw();
  const char* what() const throw();
};</pre>
</blockquote>
  <p><i>To 19.4.3.2 Class system_error members [syserr.syserr.members] add:</i></p>
  <blockquote>
    <pre>system_error(error_code ec);</pre>
    <blockquote>
  <p><i>Effects:</i> Constructs an object of class <code>system_error</code>.</p>
  <p><i>Postconditions:</i> <code>code() == ec</code> and <code>
  strcmp(runtime_error::what(), &quot;&quot;) == 0</code>.</p>
    </blockquote>
    <pre>system_error(int ev, const error_category&amp; ecat);</pre>
    <blockquote>
  <p><i>Effects:</i> Constructs an object of class <code>system_error</code>.</p>
  <p><i>Postconditions:</i> <code>code() == error_code(ev, ecat)</code> and
  <code>strcmp(runtime_error::what(), &quot;&quot;) == 0</code>.</p>
    </blockquote>
</blockquote>
  <h3><a name="Acknowledgements">Acknowledgements</a></h3>
  <p>Chris Kohlhoff, Benjamin Kosnik, and Peter Dimov provided much assistance in identifying and resolving 
  issues.</p>
<hr>

</body>

</html>