mozilla

Revision 485573 of Using C++ in Mozilla code

  • Revision slug: Using_CXX_in_Mozilla_code
  • Revision title: Using C++ in Mozilla code
  • Revision id: 485573
  • Created:
  • Creator: Jcranmer
  • Is current revision? No
  • Comment

Revision Content

This page is a draft for expository and exploratory purposes. Do not trust the information listed here.

C++ language features

Mozilla code only uses a subset of C++. Runtime type information (RTTI) is disabled, as it tends to cause a very large increase in codesize. This means that dynamic_cast, typeid() and <typeinfo> cannot be used in Mozilla code. Also disabled are exceptions; do not use try/catch or throw any exceptions. Libraries that throw exceptions may be used if you are willing to have the throw instead be treated as an abort.

As of Mozilla 25, C++11 mode is required to build Mozilla. This means that C++11 can be used where supported on all platforms. The list of acceptable features is given below:

Feature MSVC GCC Clang Can be used in code
type_t && 2010 4.3 2.9 Yes (see notes)
ref qualifiers on methods 4.8.1 2.9 No
member initializers 2013 4.7 3.0 No
variadic templates 2013 4.3 2.9 No
Initializer lists 2013 4.4 3.1 No
static_assert 2010 4.3 2.9 Yes
auto 2010 4.4 2.9 Yes
lambdas 2010 4.5 3.1 No
decltype 2010 4.3 2.9 Include mozilla/Types.h
Foo<Bar>> 2010 4.3 2.9 Yes
auto func() -> int 2010 4.4 3.1 Only when needed to avoid global-scope typedefs
Templated aliasing 2013 4.7 3.0 No
nullptr 2010 4.6 3.0 Include mozilla/NullPtr.h
Use decltype(nullptr) instead of std::nullptr_t.
enum class foo : int16_t {}; 2012 4.4 2.9 Use macros from mozilla/TypedEnum.h
enum foo; 2012 4.6 3.1 No
[[attributes]] 4.8 3.3 No (see notes)
constexpr 4.6 3.1 Use MOZ_CONSTEXPR from mozilla/Attributes.h
alignof/alignas 4.8 3.3 No (see notes)
Delegated constructors 2013 4.7 3.0 No
Inherited constructors 4.8 3.3 No
explicit operator bool() 2013 4.5 3.0 No
char16_t/u"string" 4.4 3.0 Include mozilla/Char16.h to use.
Use MOZ_UTF16("string") instead of u"string".
r"string" 2013 4.5 3.0 No
operator""() 4.7 3.1 No
=delete 2013 4.4 2.9 Use MOZ_DELETE from mozilla/Attributes.h
=default 2013 4.4 3.0 No
unrestricted unions 4.6 3.1 No
for (auto x : vec) 2012 4.6 3.0 No
override/final 2012 4.7 3.0 Use MOZ_OVERRIDE and MOZ_FINAL from mozilla/Attributes.h
thread_local 4.8 3.3 No (see notes)
function template default arguments 2013 4.3 2.9 No
0b100 (C++1y) 4.9 2.9 No
Generic lambdas (C++1y) No
Variable templates (C++1y) No

Notes

rvalue references: Implicit move method generation cannot be used. Temporaries may bind to lvalues in some cases on MSVC.

Attributes: Several common attributes are defined in mozilla/Attributes.h or nscore.h.

Alignment: Some alignment utilities are defined in mozilla/Alignment.h.

Thread locals: There is a thread-local variable helper in mozilla/ThreadLocal.h.

C++ and Mozilla standard libraries

The Mozilla codebase contains within it several subprojects which follow different rules for which libraries can and can't be used it. The rules listed here apply to normal platform code, and assume unrestricted usability of MFBT or XPCOM APIs.

As a general rule of thumb, prefer the use of MFBT or XPCOM APIs to standard C++ APIs. Some of our APIs include extra methods not found in the standard API (such as those reporting the size of data structures). A complete listing of MFBT APIs can be found in mfbt/; the XPCOM APIs can be found in xpcom/base, xpcom/ds, and xpcom/glue. What follows is a list of permissible standard C++ and Mozilla library calls for various tasks, broken down by function.

Data structures and algorithms

Name Header MSVC libstdc++ libc++ STLport Purpose Notes
std::array <array>         Compile-time sized sequence  
std::forward_list <forward_list>         Singly-linked list  
std::unordered_map <unordered_map>         Map backed by a hashtable  
std::unordered_multimap <unordered_map>         Multimap backed by a hashtable  
std::unordered_set <unordered_set>         Set backed by a hashtable  
std::unordered_multiset <unordered_set>         Multiset backed by a hashtable  
std::next/std::prev <iterator>         Increment iterators a set distance  
std::begin/std::end <iterator>         Ranged iterator  
std::cbegin/std::cend (C++14) <iterator>         Const ranged iterator  
emplace* methods various            
std::all_of/std::any_of/std::none_of <algorithm>            
std::find_if_not <algorithm>            
std::is_* methods <algorithm>            
std::shuffle <algorithm>            
std::iota <algorithm>            
std::minmax <algorithm>            

Strings

Name Header MSVC libstdc++ libc++ STLport Purpose Notes
std::u16string, std::u32string <string>            
std::codecvt_utf8 <codecvt>            

I/O

Don't use C++'s I/O functionality, particularly std::cin and std::cout. The interface is necessarily synchronous, and it causes static constructors to be added. Instead, use the stream APIs developed in XPCOM for input and output.

Platform support (POSIX/WinAPI)

Name Header MSVC libstdc++ libc++ STLport Purpose Notes
std::chrono::duration <chrono>            
std::chrono::*_clock <chrono>            
std::chrono::time_point <chrono>            
std::atomic <atomic> 2012 4.4 3.0     Use mozilla::Atomic from mozilla/Atomics.h instead.
std::thread <thread>            
std::mutex <mutex>            
std::shared_mutex (C++14) <mutex>            
std::lock_guard <mutex>            
std::shared_lock (C++14) <mutex>            
std::call_once <mutex>            
std::condition_variable <condition_variable>            
std::promise <future>            
std::future <future>            
std::async <future>            

Miscellaneous

sec 18: <limits> <new> <typeinfo> <exception> <initializer_list>

sec 19: <stdexcept> <system_error>

sec 20: <utility> <tuple> <memory> <functional> <type_traits> <ratio> <scoped_allocator> <type_index>

sec 26: <complex> <random> <numeric>

sec 28: <regex>

Revision Source

<div class="warning">
 <p>This page is a draft for expository and exploratory purposes. Do not trust the information listed here.</p>
</div>
<h2 id="C.2B.2B_language_features">C++ language features</h2>
<p>Mozilla code only uses a subset of C++. Runtime type information (RTTI) is disabled, as it tends to cause a very large increase in codesize. This means that <code>dynamic_cast</code>, <code>typeid()</code> and <code>&lt;typeinfo&gt;</code> cannot be used in Mozilla code. Also disabled are exceptions; do not use <code>try</code>/<code>catch</code> or throw any exceptions. Libraries that throw exceptions may be used if you are willing to have the throw instead be treated as an abort.</p>
<p>As of Mozilla 25, C++11 mode is required to build Mozilla. This means that C++11 can be used where supported on all platforms. The list of acceptable features is given below:</p>
<table class="standard-table">
 <thead>
  <tr>
   <th scope="col">Feature</th>
   <th scope="col">MSVC</th>
   <th scope="col">GCC</th>
   <th scope="col">Clang</th>
   <th scope="col">Can be used in code</th>
  </tr>
 </thead>
 <tbody>
  <tr>
   <td><code>type_t &amp;&amp;</code></td>
   <td style="background-color: rgb(204, 255, 153);">2010</td>
   <td style="background-color: rgb(204, 255, 153);">4.3</td>
   <td style="background-color: rgb(204, 255, 153);">2.9</td>
   <td style="background-color: rgb(204, 255, 153);">Yes (see notes)</td>
  </tr>
  <tr>
   <td>ref qualifiers on methods</td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">4.8.1</td>
   <td style="background-color: rgb(204, 255, 153);">2.9</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td>member initializers</td>
   <td style="background-color: rgb(255, 204, 204);">2013</td>
   <td style="background-color: rgb(255, 204, 204);">4.7</td>
   <td style="background-color: rgb(204, 255, 153);">3.0</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td>variadic templates</td>
   <td style="background-color: rgb(255, 204, 204);">2013</td>
   <td style="background-color: rgb(204, 255, 153);">4.3</td>
   <td style="background-color: rgb(204, 255, 153);">2.9</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td>Initializer lists</td>
   <td style="background-color: rgb(255, 204, 204);">2013</td>
   <td style="background-color: rgb(204, 255, 153);">4.4</td>
   <td style="background-color: rgb(204, 255, 153);">3.1</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td><code>static_assert</code></td>
   <td style="background-color: rgb(204, 255, 153);">2010</td>
   <td style="background-color: rgb(204, 255, 153);">4.3</td>
   <td style="background-color: rgb(204, 255, 153);">2.9</td>
   <td style="background-color: rgb(204, 255, 153);">Yes</td>
  </tr>
  <tr>
   <td><code>auto</code></td>
   <td style="background-color: rgb(204, 255, 153);">2010</td>
   <td style="background-color: rgb(204, 255, 153);">4.4</td>
   <td style="background-color: rgb(204, 255, 153);">2.9</td>
   <td style="background-color: rgb(204, 255, 153);">Yes</td>
  </tr>
  <tr>
   <td>lambdas</td>
   <td style="background-color: rgb(204, 255, 153);">2010</td>
   <td style="background-color: rgb(255, 204, 204);">4.5</td>
   <td style="background-color: rgb(204, 255, 153);">3.1</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td><code>decltype</code></td>
   <td style="background-color: rgb(204, 255, 153);">2010</td>
   <td style="background-color: rgb(204, 255, 153);">4.3</td>
   <td style="background-color: rgb(204, 255, 153);">2.9</td>
   <td style="background-color: rgb(255, 255, 153);">Include <a href="http://dxr.mozilla.org/mozilla-central/source/mfbt/Types.h" title="http://dxr.mozilla.org/mozilla-central/source/mfbt/Types.h">mozilla/Types.h</a></td>
  </tr>
  <tr>
   <td><code>Foo&lt;Bar&gt;&gt;</code></td>
   <td style="background-color: rgb(204, 255, 153);">2010</td>
   <td style="background-color: rgb(204, 255, 153);">4.3</td>
   <td style="background-color: rgb(204, 255, 153);">2.9</td>
   <td style="background-color: rgb(204, 255, 153);">Yes</td>
  </tr>
  <tr>
   <td><code>auto func() -&gt; int</code></td>
   <td style="background-color: rgb(204, 255, 153);">2010</td>
   <td style="background-color: rgb(204, 255, 153);">4.4</td>
   <td style="background-color: rgb(204, 255, 153);">3.1</td>
   <td style="background-color: rgb(255, 255, 153);">Only when needed to avoid global-scope typedefs</td>
  </tr>
  <tr>
   <td>Templated aliasing</td>
   <td style="background-color: rgb(255, 204, 204);">2013</td>
   <td style="background-color: rgb(255, 204, 204);">4.7</td>
   <td style="background-color: rgb(204, 255, 153);">3.0</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td style="vertical-align: middle;"><code>nullptr</code></td>
   <td style="vertical-align: middle; background-color: rgb(204, 255, 153);">2010</td>
   <td style="vertical-align: middle; background-color: rgb(255, 204, 204);">4.6</td>
   <td style="vertical-align: middle; background-color: rgb(204, 255, 153);">3.0</td>
   <td style="background-color: rgb(255, 255, 153);">Include <a href="http://dxr.mozilla.org/mozilla-central/source/mfbt/NullPtr.h" title="http://dxr.mozilla.org/mozilla-central/source/mfbt/NullPtr.h">mozilla/NullPtr.h</a><br />
    Use <code>decltype(nullptr)</code> instead of <code>std::nullptr_t</code>.</td>
  </tr>
  <tr>
   <td><code>enum class foo : int16_t</code> {};</td>
   <td style="background-color: rgb(255, 204, 204);">2012</td>
   <td style="background-color: rgb(204, 255, 153);">4.4</td>
   <td style="background-color: rgb(204, 255, 153);">2.9</td>
   <td style="background-color: rgb(255, 255, 153);">Use macros from <a href="http://dxr.mozilla.org/mozilla-central/source/mfbt/TypedEnum.h" title="http://dxr.mozilla.org/mozilla-central/source/mfbt/TypedEnum.h">mozilla/TypedEnum.h</a></td>
  </tr>
  <tr>
   <td><code>enum foo;</code></td>
   <td style="background-color: rgb(255, 204, 204);">2012</td>
   <td style="background-color: rgb(255, 204, 204);">4.6</td>
   <td style="background-color: rgb(204, 255, 153);">3.1</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td><code>[[attributes]]</code></td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">4.8</td>
   <td style="background-color: rgb(255, 204, 204);">3.3</td>
   <td style="background-color: rgb(255, 204, 204);">No (see notes)</td>
  </tr>
  <tr>
   <td><code>constexpr</code></td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">4.6</td>
   <td style="background-color: rgb(204, 255, 153);">3.1</td>
   <td style="background-color: rgb(255, 255, 153);">Use <code>MOZ_CONSTEXPR </code>from <a href="http://dxr.mozilla.org/mozilla-central/source/mfbt/Attributes.h" title="http://dxr.mozilla.org/mozilla-central/source/mfbt/Attributes.h">mozilla/Attributes.h</a></td>
  </tr>
  <tr>
   <td><code>alignof</code>/<code>alignas</code></td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">4.8</td>
   <td style="background-color: rgb(255, 204, 204);">3.3</td>
   <td style="background-color: rgb(255, 204, 204);">No (see notes)</td>
  </tr>
  <tr>
   <td>Delegated constructors</td>
   <td style="background-color: rgb(255, 204, 204);">2013</td>
   <td style="background-color: rgb(255, 204, 204);">4.7</td>
   <td style="background-color: rgb(204, 255, 153);">3.0</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td>Inherited constructors</td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">4.8</td>
   <td style="background-color: rgb(255, 204, 204);">3.3</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td><code>explicit operator bool()</code></td>
   <td style="background-color: rgb(255, 204, 204);">2013</td>
   <td style="background-color: rgb(255, 204, 204);">4.5</td>
   <td style="background-color: rgb(204, 255, 153);">3.0</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td style="vertical-align: middle;"><code>char16_t/u"string"</code></td>
   <td style="background-color: rgb(255, 204, 204); vertical-align: middle;">—</td>
   <td style="background-color: rgb(204, 255, 153); vertical-align: middle;">4.4</td>
   <td style="background-color: rgb(204, 255, 153); vertical-align: middle;">3.0</td>
   <td style="background-color: rgb(255, 255, 153);">Include <a href="http://dxr.mozilla.org/mozilla-central/source/mfbt/Char16.h" title="http://dxr.mozilla.org/mozilla-central/source/mfbt/Char16.h">mozilla/Char16.h</a> to use.<br />
    Use <code>MOZ_UTF16("string")</code> instead of u"string".</td>
  </tr>
  <tr>
   <td><code>r"string"</code></td>
   <td style="background-color: rgb(255, 204, 204);">2013</td>
   <td style="background-color: rgb(255, 204, 204);">4.5</td>
   <td style="background-color: rgb(204, 255, 153);">3.0</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td><code>operator""()</code></td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">4.7</td>
   <td style="background-color: rgb(204, 255, 153);">3.1</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td><code>=delete</code></td>
   <td style="background-color: rgb(255, 204, 204);">2013</td>
   <td style="background-color: rgb(204, 255, 153);">4.4</td>
   <td style="background-color: rgb(204, 255, 153);">2.9</td>
   <td style="background-color: rgb(255, 255, 153);">Use <code>MOZ_DELETE</code> from <a href="http://dxr.mozilla.org/mozilla-central/source/mfbt/Attributes.h" title="http://dxr.mozilla.org/mozilla-central/source/mfbt/Attributes.h">mozilla/Attributes.h</a></td>
  </tr>
  <tr>
   <td><code>=default</code></td>
   <td style="background-color: rgb(255, 204, 204);">2013</td>
   <td style="background-color: rgb(204, 255, 153);">4.4</td>
   <td style="background-color: rgb(204, 255, 153);">3.0</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td>unrestricted unions</td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">4.6</td>
   <td style="background-color: rgb(204, 255, 153);">3.1</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td><code>for (auto x : vec)</code></td>
   <td style="background-color: rgb(255, 204, 204);">2012</td>
   <td style="background-color: rgb(255, 204, 204);">4.6</td>
   <td style="background-color: rgb(204, 255, 153);">3.0</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td><code>override</code>/<code>final</code></td>
   <td style="background-color: rgb(255, 204, 204);">2012</td>
   <td style="background-color: rgb(255, 204, 204);">4.7</td>
   <td style="background-color: rgb(204, 255, 153);">3.0</td>
   <td style="background-color: rgb(255, 255, 153);">Use <code>MOZ_OVERRIDE</code> and <code>MOZ_FINAL</code> from <a href="http://dxr.mozilla.org/mozilla-central/source/mfbt/Attributes.h" title="http://dxr.mozilla.org/mozilla-central/source/mfbt/Attributes.h">mozilla/Attributes.h</a></td>
  </tr>
  <tr>
   <td><code>thread_local</code></td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">4.8</td>
   <td style="background-color: rgb(255, 204, 204);">3.3</td>
   <td style="background-color: rgb(255, 204, 204);">No (see notes)</td>
  </tr>
  <tr>
   <td>function template default arguments</td>
   <td style="background-color: rgb(255, 204, 204);">2013</td>
   <td style="background-color: rgb(204, 255, 153);">4.3</td>
   <td style="background-color: rgb(204, 255, 153);">2.9</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td><code>0b100</code> (C++1y)</td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">4.9</td>
   <td style="background-color: rgb(204, 255, 153);">2.9</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td>Generic lambdas (C++1y)</td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
  <tr>
   <td>Variable templates (C++1y)</td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">—</td>
   <td style="background-color: rgb(255, 204, 204);">No</td>
  </tr>
 </tbody>
</table>
<h3 id="Notes">Notes</h3>
<p>rvalue references: Implicit move method generation cannot be used. Temporaries may bind to lvalues in some cases on MSVC.</p>
<p>Attributes: Several common attributes are defined in <a href="http://dxr.mozilla.org/mozilla-central/source/mfbt/Attributes.h">mozilla/Attributes.h</a> or nscore.h.</p>
<p>Alignment: Some alignment utilities are defined in <a href="http://dxr.mozilla.org/mozilla-central/source/mfbt/Alignment.h">mozilla/Alignment.h</a>.</p>
<p>Thread locals: There is a thread-local variable helper in <a href="http://dxr.mozilla.org/mozilla-central/source/mfbt/ThreadLocal.h">mozilla/ThreadLocal.h</a>.</p>
<h2 id="C.2B.2B_and_Mozilla_standard_libraries">C++ and Mozilla standard libraries</h2>
<p>The Mozilla codebase contains within it several subprojects which follow different rules for which libraries can and can't be used it. The rules listed here apply to normal platform code, and assume unrestricted usability of MFBT or XPCOM APIs.</p>
<p>As a general rule of thumb, prefer the use of MFBT or XPCOM APIs to standard C++ APIs. Some of our APIs include extra methods not found in the standard API (such as those reporting the size of data structures). A complete listing of MFBT APIs can be found in <a href="/en-US/docs/http://dxr.mozilla.org/mozilla-central/source/mfbt">mfbt/</a>; the XPCOM APIs can be found in <a href="http://dxr.mozilla.org/mozilla-central/source/xpcom/base">xpcom/base</a>, <a href="http://dxr.mozilla.org/mozilla-central/source/xpcom/ds">xpcom/ds</a>, and <a href="http://dxr.mozilla.org/mozilla-central/source/xpcom/glue">xpcom/glue</a>. What follows is a list of permissible standard C++ and Mozilla library calls for various tasks, broken down by function.</p>
<h3 id="Data_structures_and_algorithms">Data structures and algorithms</h3>
<table class="standard-table">
 <thead>
  <tr>
   <th scope="col">Name</th>
   <th scope="col">Header</th>
   <th scope="col">MSVC</th>
   <th scope="col">libstdc++</th>
   <th scope="col">libc++</th>
   <th scope="col">STLport</th>
   <th scope="col">Purpose</th>
   <th scope="col">Notes</th>
  </tr>
 </thead>
 <tbody>
  <tr>
   <td><code>std::array</code></td>
   <td><code>&lt;array&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>Compile-time sized sequence</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::forward_list</code></td>
   <td><code>&lt;forward_list&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>Singly-linked list</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::unordered_map</code></td>
   <td><code>&lt;unordered_map&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>Map backed by a hashtable</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::unordered_multimap</code></td>
   <td><code>&lt;unordered_map&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>Multimap backed by a hashtable</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::unordered_set</code></td>
   <td><code>&lt;unordered_set&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>Set backed by a hashtable</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::unordered_multiset</code></td>
   <td><code>&lt;unordered_set&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>Multiset backed by a hashtable</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::next</code>/<code>std::prev</code></td>
   <td><code>&lt;iterator&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>Increment iterators a set distance</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::begin</code>/<code>std::end</code></td>
   <td><code>&lt;iterator&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>Ranged iterator</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::cbegin</code>/<code>std::cend</code> (C++14)</td>
   <td><code>&lt;iterator&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>Const ranged iterator</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>emplace</code>* methods</td>
   <td><em>various</em></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::all_of</code>/<code>std::any_of</code>/<code>std::none_of</code></td>
   <td><code>&lt;algorithm&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::find_if_not</code></td>
   <td><code>&lt;algorithm&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::is_</code>* methods</td>
   <td><code>&lt;algorithm&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::shuffle</code></td>
   <td><code>&lt;algorithm&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::iota</code></td>
   <td><code>&lt;algorithm&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::minmax</code></td>
   <td><code>&lt;algorithm&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
 </tbody>
</table>
<h3 id="Strings">Strings</h3>
<table class="standard-table">
 <thead>
  <tr>
   <th scope="col">Name</th>
   <th scope="col">Header</th>
   <th scope="col">MSVC</th>
   <th scope="col">libstdc++</th>
   <th scope="col">libc++</th>
   <th scope="col">STLport</th>
   <th scope="col">Purpose</th>
   <th scope="col">Notes</th>
  </tr>
 </thead>
 <tbody>
  <tr>
   <td><code>std::u16string</code>, <code>std::u32string</code></td>
   <td><code>&lt;string&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::codecvt_utf8</code></td>
   <td><code>&lt;codecvt&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
 </tbody>
</table>
<h3 id="I.2FO">I/O</h3>
<p>Don't use C++'s I/O functionality, particularly <code>std::cin</code> and <code>std::cout</code>. The interface is necessarily synchronous, and it causes static constructors to be added. Instead, use the stream APIs developed in XPCOM for input and output.</p>
<h3 id="Platform_support_(POSIX.2FWinAPI)">Platform support (POSIX/WinAPI)</h3>
<table class="standard-table">
 <thead>
  <tr>
   <th scope="col">Name</th>
   <th scope="col">Header</th>
   <th scope="col">MSVC</th>
   <th scope="col">libstdc++</th>
   <th scope="col">libc++</th>
   <th scope="col">STLport</th>
   <th scope="col">Purpose</th>
   <th scope="col">Notes</th>
  </tr>
 </thead>
 <tbody>
  <tr>
   <td><code>std::chrono::duration</code></td>
   <td><code>&lt;chrono&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::chrono::</code>*<code>_clock</code></td>
   <td><code>&lt;chrono&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::chrono::time_point</code></td>
   <td><code>&lt;chrono&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::atomic</code></td>
   <td><code>&lt;atomic&gt;</code></td>
   <td>2012</td>
   <td>4.4</td>
   <td>3.0</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>Use <code>mozilla::Atomic</code> from <code>mozilla/Atomics.h</code> instead.</td>
  </tr>
  <tr>
   <td><code>std::thread</code></td>
   <td>&lt;thread&gt;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::mutex</code></td>
   <td><code>&lt;mutex&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::shared_mutex</code> (C++14)</td>
   <td><code>&lt;mutex&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::lock_guard</code></td>
   <td><code>&lt;mutex&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::shared_lock</code> (C++14)</td>
   <td><code>&lt;mutex&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::call_once</code></td>
   <td><code>&lt;mutex&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::condition_variable</code></td>
   <td><code>&lt;condition_variable&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::promise</code></td>
   <td><code>&lt;future&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::future</code></td>
   <td><code>&lt;future&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
  <tr>
   <td><code>std::async</code></td>
   <td><code>&lt;future&gt;</code></td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
   <td>&nbsp;</td>
  </tr>
 </tbody>
</table>
<h3 id="Miscellaneous">Miscellaneous</h3>
<p>sec 18: &lt;limits&gt; &lt;new&gt; &lt;typeinfo&gt; &lt;exception&gt; &lt;initializer_list&gt;</p>
<p>sec 19: &lt;stdexcept&gt; &lt;system_error&gt;</p>
<p>sec 20: &lt;utility&gt; &lt;tuple&gt; &lt;memory&gt; &lt;functional&gt; &lt;type_traits&gt; &lt;ratio&gt; &lt;scoped_allocator&gt; &lt;type_index&gt;</p>
<p>sec 26: &lt;complex&gt; &lt;random&gt; &lt;numeric&gt;</p>
<p>sec 28: &lt;regex&gt;</p>
Revert to this revision