constexpr macrosistream_viewuses_allocator_construction_argsBranching from P0829R4. This "omnibus" paper is still the direction I am aiming for. However, it is too difficult to review. It needs to change with almost every meeting. Therefore, it is getting split up into smaller, more manageable chunks.
Limiting paper to the [utilities], [ranges], and [iterators] clauses.
This paper proposes adding many of the facilities in the [utilities], [ranges], and [iterators] clause to the freestanding subset of C++. The paper will only be adding complete entities, and will not tackle partial classes. In other words, classes like pair and tuple are being added, but trickier classes like optional, variant, and bitset will come in another paper.
The <memory> header has a dependency on facilities in <ranges> and <iterator>, so those headers (and clauses) are addressed as well.
Many existing facilities in the C++ standard library could be used without trouble in freestanding environments. This series of papers will specify the maximal subset of the C++ standard library that does not require an OS or space overhead.
For a more in depth rationale, see P0829.
<optional>, <variant>, and <bitset> are not in this paper, as all have non-essential functions that can throw an exception. <charconv> is not in this paper as it will require us to deal with the thorny issue of overload sets involving floating point and non-floating point types. I plan on addressing all four of these headers in later papers, so that the topics in question can be debated in relative isolation.
Modifying an overload set needs to be treated with great care. Ideally, libraries built in freestanding environments will have the same semantics (including selected overloads) when built in a hosted environment. I don't think that goal is 100% achievable, as sufficiently clever programmers will be able to detect the difference and modify behavior accordingly.
My approach will be to avoid splitting overload sets that could cause accidental freestanding / hosted differences. In future papers, I may need to lean on = delete techniques to avoid silent behavior changes, but this paper hasn't needed that approach.
swap has shared_ptr, weak_ptr, and unique_ptr overloads, but this paper only marks the unique_ptr overload as freestanding. <memory> has many algorithms with ExecutionPolicy overloads. This paper does not mark the ExectuionPolicy overloads as freestanding. I was unable to come up with any compelling "accidental" way to select one swap or algorithm overload in freestanding, but a different one in hosted.
Also note that the swap overload set visible to a given translation unit is already indeterminate. A user may include <memory> which guarantees the smart pointer overloads, but an implementation could expose any (or none!) of the other swap overloads from other STL headers.
The following functions and classes rely on dynamic memory allocation and exceptions:
make_obj_using_allocatormake_uniquemake_unique_default_initshared_ptrweak_ptrfunctionboyer_moore_searcherboyer_moore_horspool_searcherThe following classes rely on iostreams facilities. iostreams facilities use dynamic memory allocations and rely on the operating system.
istream_iteratorostream_iteratoristreambuf_iteratorostreambuf_iteratorbasic_istream_viewistream_viewThe ExecutionPolicy overloads of algorithms are of minimal utility on systems that do not support C++ threads.
| Name | Header |
|---|---|
__cpp_lib_freestanding_utility |
<utility> |
__cpp_lib_freestanding_tuple |
<tuple> |
__cpp_lib_freestanding_ratio |
<ratio> |
__cpp_lib_freestanding_memory |
<memory> |
__cpp_lib_freestanding_functional |
<functional> |
__cpp_lib_freestanding_iterator |
<iterator> |
__cpp_lib_freestanding_ranges |
<ranges> |
The following, existing feature test macros cover some features that I am making freestanding, and some features that I am not requiring to be freestanding. These feature test macros won't be required in freestanding, as they could cause substantial confusion when the hosted parts of those features aren't available. The header-based __cpp_lib_freestanding_* macros should provide a suitable replacement in freestanding environments.
__cpp_lib_boyer_moore_searcher__cpp_lib_constexpr_dynamic_alloc__cpp_lib_ranges__cpp_lib_raw_memory_algorithmspointer_traitsto_addressalignassume_alignedallocator_arg_tallocator_arguses_allocatoruses_allocator_vuses_allocator_construction_argsallocator_traitsExecutionPolicy overloads. This includes the algorithms in the ranges namespacedefault_deleteunique_ptrunique_ptr overload of swapunique_ptrhashunique_ptr specialization of hashatomic<memory> are omitted. No change to the working draft should be made for these declarations:
make_obj_using_allocatoruninitialized_construct_using_allocatorallocator and associated comparisonsExecutionPolicy overloads in [specialized.algorithms]make_uniquemake_unique_default_initoperator<< overloadsbad_weak_ptrshared_ptrmake_sharedallocate_sharedmake_shared_default_initallocate_shared_default_initshared_ptrshared_ptr overload of swapstatic_pointer_castdynamic_pointer_castconst_pointer_castreinterpret_pointer_castget_deleterweak_ptrweak_ptr overload of swapowner_lessenable_shared_from_thisshared_ptr specialization of hashshared_ptr specialization of atomicweak_ptr specialization of atomic<functional> except for the following entities:
bad_function_callfunctionfunction overloads of swapfunction overloads of operator==boyer_moore_searcherboyer_moore_horspool_searcher<iterator> except for the following entities:
istream_iterator and associated comparison operatorsostream_iteratoristreambuf_iterator and associated comparison operatorsostreambuf_iterator<ranges> except for the following entities:
basic_istream_viewistream_view__cpp_lib_addressof_constexpr__cpp_lib_allocator_traits_is_always_equal__cpp_lib_apply__cpp_lib_as_const__cpp_lib_assume_aligned__cpp_lib_atomic_value_initialization__cpp_lib_bind_front__cpp_lib_constexpr_functional__cpp_lib_constexpr_iterator__cpp_lib_constexpr_memory__cpp_lib_constexpr_tuple__cpp_lib_constexpr_utility__cpp_lib_exchange_function__cpp_lib_integer_sequence__cpp_lib_invoke__cpp_lib_make_from_tuple__cpp_lib_make_reverse_iterator__cpp_lib_nonmember_container_access__cpp_lib_not_fn__cpp_lib_null_iterators__cpp_lib_ssize__cpp_lib_to_address__cpp_lib_transparent_operators__cpp_lib_tuple_element_t__cpp_lib_tuples_by_type__cpp_lib_unwrap_ref#define __cpp_lib_freestanding_functional 202005L // also in <functional>, freestanding only #define __cpp_lib_freestanding_iterator 202005L // also in <iterator>, freestanding only #define __cpp_lib_freestanding_memory 202005L // also in <memory>, freestanding only #define __cpp_lib_freestanding_ranges 202005L // also in <ranges>, freestanding only #define __cpp_lib_freestanding_ratio 202005L // also in <ratio>, freestanding only #define __cpp_lib_freestanding_tuple 202005L // also in <tuple>, freestanding only #define __cpp_lib_freestanding_utility 202005L // also in <utility>, freestanding only
Thanks to Brandon Streiff, Joshua Cannon, Phil Hindman, and Irwan Djajadi for reviewing P0829.
Thanks to Odin Holmes for providing feedback and helping publicize P0829.
Thanks to Paul Bendixen for providing feedback while prototyping P0829.
Similar work was done in the C++11 timeframe by Lawrence Crowl and Alberto Ganesh Barbati in N3256.