Closed kouberl closed 9 years ago
Highly interesting. I've modified your case to add prints to find where it fails, but the moment I do that it stops failing & just works as intended.
... Feels like a compiler issue, somehow. Perhaps it's rescheduling something it shouldn't?
It stops failing as soon as the call to the mocked function is not the last function. Looks like GCC is inlining this function in -O0 in case it's a tail-recurse, but not otherwise.
One of the limitations of static function mocking is that your compiler should NOT inline them. I cannot mock an inlined function.
More interesting though, it looks like it closes the try... catch block before actually tail-recursing, even if it is not actually inlining the block.
Modifying the original function to throw an exception fixes this behaviour. GCC uses its prior knowledge about the function to move it out of the try-catch block, which HippoMocks then modifies behind the scenes to throw an exception anyway, causing it to stop. Funny thing is that this also happens when you disable any and all inlining - literally attribute ((noinline)).
If you move the function external it will work. If your function is not deduced as "will not throw exception" otherwise, it's also fine.
I've seen similar behaviour from MSVC, where noreturn functions cause the calling function to not have any code generated after the call to it, so if you'd mock "exit" to return 1, your program would just crash as there's no code to return to.
Thank you for your efforts. That's interesting. Now I'm mocking extern functions, this works without complaining :-)
I cannot catch any exception when mocking static functions. (using a decent g++ compiler under linux)
A minimal example: http://coliru.stacked-crooked.com/a/1f5ea78f50a29b3d