std::thread
's constructor needs to be able to report general memory allocation failuresSection: 32.4.3.3 [thread.thread.constr], 32.4.4.2 [thread.jthread.cons] Status: New Submitter: Billy O'Neal III Opened: 2020-08-14 Last modified: 2020-09-06
Priority: 3
View all other issues in [thread.thread.constr].
View all issues with New status.
Discussion:
(j)thread
's constructor needs to decay-copy
the supplied parameters and callable over to the started
thread through an operating system API that generally only accepts a single void*
. The MSVC++ and libc++
implementations do this by putting the parameters in a std::tuple
allocated from the heap, passing a
pointer to that tuple through the operating system API, and leaving ownership of the parameters to the other thread.
resource_unavailable_try_again
, but the description for this error in the standard is that some thread-based
limitation has been reached, not a general memory limit, so that doesn't seem to meet the spirit of the requirement.
[2020-08-21; Issue processing telecon: set priority to 3]
Jonathan: I prefer Option A, but I think we need something like:
"any exceptions thrown by the decay-copy
calls, or ...".
Proposed resolution:
This wording is relative to N4861.
[Drafting Note: Two mutually exclusive options are prepared, depicted below by Option A and Option B, respectively.]
Option A: The memory allocation failure results in bad_alloc
.
Modify 32.4.3.3 [thread.thread.constr] as indicated:
template<class F, class... Args> explicit thread(F&& f, Args&&... args);-3- Constraints: […]
[…] -8- Postconditions:get_id() != id()
.*this
represents the newly started thread. -9- Throws:bad_alloc
if memory to transfer parameters to the new thread cannot be obtained.system_error
if unable to start the new thread. -10- Error conditions:
(10.1) —
resource_unavailable_try_again
— the system lacked the necessary resources to create another thread, or the system-imposed limit on the number of threads in a process would be exceeded.
Modify 32.4.4.2 [thread.jthread.cons] as indicated:
template<class F, class... Args> explicit jthread(F&& f, Args&&... args);-3- Constraints: […]
[…] -8- Postconditions:get_id() != id()
istrue
andssource.stop_possible()
istrue
and*this
represents the newly started thread. [Note: The calling thread can make a stop request only once, because it cannot replace this stop token. — end note] -9- Throws:bad_alloc
if memory to transfer parameters to the new thread cannot be obtained.system_error
if unable to start the new thread. -10- Error conditions:
(10.1) —
resource_unavailable_try_again
— the system lacked the necessary resources to create another thread, or the system-imposed limit on the number of threads in a process would be exceeded.
Option B: The memory allocation failure results in a system_error
with the error condition
out_of_memory
.
Modify 32.4.3.3 [thread.thread.constr] as indicated:
template<class F, class... Args> explicit thread(F&& f, Args&&... args);-3- Constraints: […]
[…] -8- Postconditions:get_id() != id()
.*this
represents the newly started thread. -9- Throws:system_error
if unable to start the new thread. -10- Error conditions:
(10.?) —
not_enough_memory
— the system lacked memory resources to transfer parameters to the new thread.(10.1) —
resource_unavailable_try_again
— the system lacked the necessary resources to create another thread, or the system-imposed limit on the number of threads in a process would be exceeded.
Modify 32.4.4.2 [thread.jthread.cons] as indicated:
template<class F, class... Args> explicit jthread(F&& f, Args&&... args);-3- Constraints: […]
[…] -8- Postconditions:get_id() != id()
istrue
andssource.stop_possible()
istrue
and*this
represents the newly started thread. [Note: The calling thread can make a stop request only once, because it cannot replace this stop token. — end note] -9- Throws:system_error
if unable to start the new thread. -10- Error conditions:
(10.?) —
not_enough_memory
— the system lacked memory resources to transfer parameters to the new thread.(10.1) —
resource_unavailable_try_again
— the system lacked the necessary resources to create another thread, or the system-imposed limit on the number of threads in a process would be exceeded.