Clang Global Constructors

Last update: December 7, 2024 pm

Global Constructors Generated by Clang

Background

In ReportFunctionExecutedPass, we are trying to build a customized C/C++ compiler for our research project to gather IO pairs of functions when fuzzing. We achieve this goal by building an LLVM Function Pass and using it as a plugin when compiling with clang. Recently, we discovered that if the target program includes <iostream>, the compiled executable will always result in a floating point exception.

Reproduction

1
2
#include <iostream>
int main() { return 0; }

Debugging

After diagnosing the issue, I found that the problem is caused by inserting into a hash table. Since the key of the table is a std::string, I suspected that the problem arises from hashing a string. To verify this, I attempted to avoid using a hash by changing the unordered_map to a map. However, the problem still persisted. Now, table.find() works fine, but table.insert() still triggers the exception.

Next, I used a debugger to step into the insert() function and discovered that the exception is caused by reporting __cxx_global_var_init and _GLOBAL__sub_I_example.cpp. These two functions are only reported when #include <iostream> is used.

Upon further investigation, I found that these two functions are global constructors generated by the clang frontend. However, these functions do not meet our requirements for the functions to be reported, so I ignore them in the pass to ensure the compiled executable functions properly.