Pure functions in C++

The following assembly code shows two calls to the add function.The compiler could not optimize away the second call, as it cannot assume that the square function does not have side effects.main: push rbp mov ebp, edi push rbx sub rsp, 8 call square(int) mov edi, ebp mov ebx, eax call square(int) add rsp, 8 add eax, ebx pop rbx pop rbp retOptimization with the pure function attributeIf there was a way to tell the compiler that a function is pure, the compiler could use this information to optimize the code.If we just add the [[gnu::pure]] attribute to the square function, the compiler will assume that the function does not cause side effects.When a function is declared pure, the compiler will also ensure that:The function does not access or update any global variables.The return value of the function just depends upon the input parameters.[[gnu::pure]] int square(int x);int main(int argc, char *argv[]){ auto x = square(argc); auto y = square(argc); return x+y;}This results in a significant optimization and the compiler can just call the square function once and just double the result — add eax, eax..The pure declaration guarantees that multiple calls to the function with the same parameters will always result in the same return value.main: sub rsp, 8 call square(int) add rsp, 8 add eax, eax retAt the time of this writing, the [[gnu::pure]] attribute is supported by GCC and Clang compilers.Learn moreJason Turner’s C++ weekly video that forms the basis of this post.Compiler explorer links for the example presented above:Square function with no pure function attributeSquare function after applying the pure function attribute. More details

Leave a Reply