From c821ef451373849c403686042466d30a7bf8138a Mon Sep 17 00:00:00 2001 From: Juneyoung Lee Date: Thu, 4 Mar 2021 09:57:50 +0900 Subject: [PATCH] [LangRef] Make lifetime intrinsic's semantics consistent with StackColoring's comment This patch is an update to LangRef by describing lifetime intrinsics' behavior by following the description of MIR's LIFETIME_START/LIFETIME_END markers at StackColoring.cpp (https://github.com/llvm/llvm-project/blob/eb44682d671d66e422b02595a636050582a4d84a/llvm/lib/CodeGen/StackColoring.cpp#L163) and the discussion in llvm-dev. In order to explicitly define the meaning of an object lifetime, I added 'Object Lifetime' subsection. Reviewed By: nlopes Differential Revision: https://reviews.llvm.org/D94002 --- llvm/docs/LangRef.rst | 72 ++++++++++++++++++++++++++++++++++--------- 1 file changed, 58 insertions(+), 14 deletions(-) diff --git a/llvm/docs/LangRef.rst b/llvm/docs/LangRef.rst index cc2fcef30831..6866cc362f57 100644 --- a/llvm/docs/LangRef.rst +++ b/llvm/docs/LangRef.rst @@ -2544,6 +2544,33 @@ This information is passed along to the backend so that it generates code for the proper architecture. It's possible to override this on the command line with the ``-mtriple`` command line option. +.. _objectlifetime: + +Object Lifetime +---------------------- + +A memory object, or simply object, is a region of a memory space that is +reserved by a memory allocation such as :ref:`alloca `, heap +allocation calls, and global variable definitions. +Once it is allocated, the bytes stored in the region can only be read or written +through a pointer that is :ref:`based on <_pointeraliasing>` the allocation +value. +If a pointer that is not based on the object tries to read or write to the +object, it is undefined behavior. + +A lifetime of a memory object is a property that decides its accessibility. +Unless stated otherwise, a memory object is alive since its allocation, and +dead after its deallocation. +It is undefined behavior to access a memory object that isn't alive, but +operations that don't dereference it such as +:ref:`getelementptr `, :ref:`ptrtoint ` and +:ref:`icmp ` return a valid result. +This explains code motion of these instructions across operations that +impact the object's lifetime. +A stack object's lifetime can be explicitly specified using +:ref:`llvm.lifetime.start <_int_lifestart>` and +:ref:`llvm.lifetime.end <_int_lifeend>` intrinsic function calls. + .. _pointeraliasing: Pointer Aliasing Rules @@ -17808,8 +17835,9 @@ Other targets may support this intrinsic differently, for example, by lowering i Memory Use Markers ------------------ -This class of intrinsics provides information about the lifetime of -memory objects and ranges where variables are immutable. +This class of intrinsics provides information about the +:ref:`lifetime of memory objects <_objectlifetime>` and ranges where variables +are immutable. .. _int_lifestart: @@ -17826,8 +17854,8 @@ Syntax: Overview: """"""""" -The '``llvm.lifetime.start``' intrinsic specifies the start of a memory -object's lifetime. +The '``llvm.lifetime.start``' intrinsic specifies the start of +:ref:`a memory object's lifetime <_objectlifetime>`. Arguments: """""""""" @@ -17839,10 +17867,23 @@ to the object. Semantics: """""""""" -This intrinsic indicates that before this point in the code, the value -of the memory pointed to by ``ptr`` is dead. This means that it is known -to never be used and has an undefined value. A load from the pointer -that precedes this intrinsic can be replaced with ``'undef'``. +If ``ptr`` is a stack-allocated object and its offset is zero, the object is +initially marked as dead. +After '``llvm.lifetime.start``', the stack object that ``ptr`` points is marked +as alive and has an uninitialized value. +The stack object is marked as dead when either +:ref:`llvm.lifetime.end ` to the alloca is executed or the +function returns. + +After :ref:`llvm.lifetime.end ` is called, +'``llvm.lifetime.start``' on the stack object can be called again. +The second '``llvm.lifetime.start``' call marks the object as alive, but it +does not change the address of the object. + +If ``ptr`` is a non-stack-allocated object, its offset is non-zero or it is +a stack object that is already alive, it simply fills all bytes of the object +with ``poison``. + .. _int_lifeend: @@ -17859,8 +17900,8 @@ Syntax: Overview: """"""""" -The '``llvm.lifetime.end``' intrinsic specifies the end of a memory -object's lifetime. +The '``llvm.lifetime.end``' intrinsic specifies the end of +:ref:`a memory object's lifetime <_objectlifetime>`. Arguments: """""""""" @@ -17872,10 +17913,13 @@ to the object. Semantics: """""""""" -This intrinsic indicates that after this point in the code, the value of -the memory pointed to by ``ptr`` is dead. This means that it is known to -never be used and has an undefined value. Any stores into the memory -object following this intrinsic may be removed as dead. +If ``ptr`` is a stack-allocated object and its offset is zero, the object is +dead. +Calling ``llvm.lifetime.end`` on an already dead alloca is no-op. + +If ``ptr`` is a non-stack-allocated object or its offset is non-zero, +it is equivalent to simply filling all bytes of the object with ``poison``. + '``llvm.invariant.start``' Intrinsic ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^