[obj.lifetime] # 20 Memory management library [[mem]](./#mem) ## 20.2 Memory [[memory]](memory#obj.lifetime) ### 20.2.6 Explicit lifetime management [obj.lifetime] [🔗](#lib:start_lifetime_as) `template T* start_lifetime_as(void* p) noexcept; template const T* start_lifetime_as(const void* p) noexcept; template volatile T* start_lifetime_as(volatile void* p) noexcept; template const volatile T* start_lifetime_as(const volatile void* p) noexcept; ` [1](#1) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1056) *Mandates*: T is an implicit-lifetime type ([[basic.types.general]](basic.types.general#term.implicit.lifetime.type "6.9.1 General")) and not an incomplete type ([[basic.types.general]](basic.types.general#term.incomplete.type "6.9.1 General"))[.](#1.sentence-1) [2](#2) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1061) *Preconditions*: [p, (char*)p + sizeof(T)) denotes a region of allocated storage that is a subset of the region of storage reachable through ([[basic.compound]](basic.compound "6.9.4 Compound types")) p and suitably aligned for the type T[.](#2.sentence-1) [3](#3) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1069) *Effects*: Implicitly creates objects ([[intro.object]](intro.object "6.8.2 Object model")) within the denoted region consisting of an object *a* of type T whose address is p, and objects nested within *a*, as follows: The object representation of *a* is the contents of the storage prior to the call to start_lifetime_as[.](#3.sentence-1) The value of each created object *o* of trivially copyable type ([[basic.types.general]](basic.types.general#term.trivially.copyable.type "6.9.1 General")) U is determined in the same manner as for a call to bit_cast(E) ([[bit.cast]](bit.cast "22.11.3 Function template bit_­cast")), where E is an lvalue of type U denoting *o*, except that the storage is not accessed[.](#3.sentence-2) The value of any other created object is unspecified[.](#3.sentence-3) [*Note [1](#note-1)*: The unspecified value can be indeterminate[.](#3.sentence-4) — *end note*] [4](#4) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1089) *Returns*: A pointer to the *a* defined in the *Effects* paragraph[.](#4.sentence-1) [🔗](#lib:start_lifetime_as_array) `template T* start_lifetime_as_array(void* p, size_t n) noexcept; template const T* start_lifetime_as_array(const void* p, size_t n) noexcept; template volatile T* start_lifetime_as_array(volatile void* p, size_t n) noexcept; template const volatile T* start_lifetime_as_array(const volatile void* p, size_t n) noexcept; ` [5](#5) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1108) *Mandates*: T is a complete type[.](#5.sentence-1) [6](#6) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1112) *Preconditions*: p is suitably aligned for an array of T or is null[.](#6.sentence-1) n <= size_t(-1) / sizeof(T) is true[.](#6.sentence-2) If n > 0 is true, [(char*)p, (char*)p + (n * sizeof(T))) denotes a region of allocated storage that is a subset of the region of storage reachable through ([[basic.compound]](basic.compound "6.9.4 Compound types")) p[.](#6.sentence-3) [7](#7) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1122) *Effects*: If n > 0 is true, equivalent tostart_lifetime_as(p) where U is the type “array of n T”[.](#7.sentence-1) Otherwise, there are no effects[.](#7.sentence-2) [8](#8) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1130) *Returns*: A pointer to the first element of the created array, if any; otherwise, a pointer that compares equal to p ([[expr.eq]](expr.eq "7.6.10 Equality operators"))[.](#8.sentence-1) [🔗](#lib:trivially_relocate) `template T* trivially_relocate(T* first, T* last, T* result); ` [9](#9) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1145) *Mandates*: is_trivially_relocatable_v && !is_const_v is true[.](#9.sentence-1) T is not an array of unknown bound[.](#9.sentence-2) [10](#10) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1150) *Preconditions*: - [(10.1)](#10.1) [first, last) is a valid range[.](#10.1.sentence-1) - [(10.2)](#10.2) [result, result + (last - first)) denotes a region of storage that is a subset of the region reachable through result ([[basic.compound]](basic.compound "6.9.4 Compound types")) and suitably aligned for the type T[.](#10.2.sentence-1) - [(10.3)](#10.3) No element in the range [first, last) is a potentially-overlapping subobject[.](#10.3.sentence-1) [11](#11) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1163) *Postconditions*: No effect if result == first is true[.](#11.sentence-1) Otherwise, the range denoted by [result, result + (last - first)) contains objects (including subobjects) whose lifetime has begun and whose object representations are the original object representations of the corresponding objects in the source range [first, last) except for any parts of the object representations used by the implementation to represent type information ([[intro.object]](intro.object "6.8.2 Object model"))[.](#11.sentence-2) If any of the objects has union type, its active member is the same as that of the corresponding object in the source range[.](#11.sentence-3) If any of the aforementioned objects has a non-static data member of reference type, that reference refers to the same entity as does the corresponding reference in the source range[.](#11.sentence-4) The lifetimes of the original objects in the source range have ended[.](#11.sentence-5) [12](#12) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1178) *Returns*: result + (last - first)[.](#12.sentence-1) [13](#13) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1182) *Throws*: Nothing[.](#13.sentence-1) [14](#14) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1186) *Complexity*: Linear in the length of the source range[.](#14.sentence-1) [15](#15) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1190) *Remarks*: The destination region of storage is considered reused ([[basic.life]](basic.life "6.8.4 Lifetime"))[.](#15.sentence-1) No constructors or destructors are invoked[.](#15.sentence-2) [*Note [2](#note-2)*: Overlapping ranges are supported[.](#15.sentence-3) — *end note*] [🔗](#lib:relocate) `template constexpr T* relocate(T* first, T* last, T* result); ` [16](#16) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1207) *Mandates*: is_nothrow_relocatable_v && !is_const_v is true[.](#16.sentence-1) T is not an array of unknown bound[.](#16.sentence-2) [17](#17) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1212) *Preconditions*: - [(17.1)](#17.1) [first, last) is a valid range[.](#17.1.sentence-1) - [(17.2)](#17.2) [result, result + (last - first)) denotes a region of storage that is a subset of the region reachable through result ([[basic.compound]](basic.compound "6.9.4 Compound types")) and suitably aligned for the type T[.](#17.2.sentence-1) - [(17.3)](#17.3) No element in the range [first, last) is a potentially-overlapping subobject[.](#17.3.sentence-1) [18](#18) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1226) *Effects*: - [(18.1)](#18.1) If result == first is true, no effect; - [(18.2)](#18.2) otherwise, if not called during constant evaluation and is_trivially_relocatable_v is true, then has effects equivalent to: trivially_relocate(first, last, result); - [(18.3)](#18.3) otherwise, for each integer i in [0, last - first), * [(18.3.1)](#18.3.1) if T is an array type, equivalent to: relocate(begin(first[i]), end(first[i]), *start_lifetime_as(result + i)); * [(18.3.2)](#18.3.2) otherwise, equivalent to: construct_at(result + i, std​::​move(first[i])); destroy_at(first + i); [19](#19) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1247) *Returns*: result + (last - first)[.](#19.sentence-1) [20](#20) [#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/memory.tex#L1251) *Throws*: Nothing[.](#20.sentence-1) [*Note [3](#note-3)*: Overlapping ranges are supported[.](#20.sentence-2) — *end note*]