Thursday, November 27, 2014

Linking C and C++ functions using extern specifier

The way C and C++ compilers generate the assembly code is a little different, this could give lots of linker errors while trying to link a function written in a C file in a C++ code or vice-versa when using the extern specifier.

Always remember that C/C++ codes are directly converted to object and assembly codes that are just linear in nature like:

_printf_:
;Actual code to print
 _main_:
call _printf_    ;now the actual code under label _printf_ is called

Something like goto style code. Thus, printf() function might be atlast converted to _printf_ label in the object/assembly code. This label is used for linking stage.

Lets take a project which contains one C file and one CPP file.

test1.c
void function_c()
{
printf("From C");
}

test2.cpp
extern function_c();
void function_cpp()
{
function_c();
}

This will not work because C compiler generates function name for function_c something like "_function_c_". But the C++ compiler (as it supports function overloading concepts) looks for the label "?function_c@@YAXXZ", hence it wont compile. To resolve this use the extern "C" option:

test2.cpp
extern "C" function_c();
void function_cpp()
{
function_c();
}

For more insights, read about Name mangling in C++: http://en.wikipedia.org/wiki/Name_mangling#Name_mangling_in_C.2B.2B