Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is it required to add 'extern C' in source file also?

Tags:

c++

c

I found some code recently where extern "C" was added in source file also for functions. They were also added in the header files where they were declared.

I was under the assumption that adding 'extern "C" in header files was sufficient.

Where should extern "C" blocks be added?

UPDATE: Suppose I am compiling my C code using a CPP compiler and have added extern "C" guards for all the functions in header files (i.e. all my functions have their prototypes in headers), but in source files I have not added the same. Will this cause a problem?

like image 950
Jay Avatar asked Jan 30 '10 14:01

Jay


People also ask

Do you need to use the extern C?

You need to use extern "C" in C++ when declaring a function that was implemented/compiled in C. Using extern "C" lets the compiler know that we want to use C naming and calling conventions. This causes the compiler to sort of entering C mode inside our C++ code.

Should externs be in header files?

All variables and functions in header files should be extern. Separate header files should be used for variables and functions. Use a C code file to declare the variables and functions and use this in end user code. Extern must be used instead of using global variables.

How do I use extern to share variables between source files?

The clean, reliable way to declare and define global variables is to use a header file to contain an extern declaration of the variable. The header is included by the one source file that defines the variable and by all the source files that reference the variable.

Do I need to include header file in source file?

Generally, you only want to put the minimum necessary includes into a class header file, as anyone else who uses that header will be forced to #include all of them too. In larger projects, this leads towards slower builds, dependency issues, and all sorts of other nastiness.


Video Answer


2 Answers

Since you mean

extern "C" { ... } 

style guards, these declare some functions to be of "C" linkage, rather than "C++" linkage (which typically has a bunch of extra name decoration to support things like overloaded functions).

The purpose, of course, is to allow C++ code to interface with C code, which is usually in a library. If the library's headers weren't written with C++ in mind, then they won't include the extern "C" guards for C++.

A C header written with C++ in mind will include something along the lines of

#ifdef __cplusplus extern "C" { #endif  ...  #ifdef __cplusplus } #endif 

to make sure C++ programs see the correct linkage. However, not all libraries were written with C++ in mind, so sometimes you have to do

extern "C" { #include "myclibrary.h" } 

to get the linkage correct. If the header file is provided by someone else then it's not good practice to change it (because then you can't update it easily), so it's better to wrap the header file with your own guard (possibly in your own header file).

extern "C" isn't (AFAIK) ANSI C, so can't be included in normal C code without the preprocessor guards.

In response to your edit:

If you are using a C++ compiler, and you declare a function as extern "C" in the header file, you do not need to also declare that function as extern "C" in the implementation file. From section 7.5 of the C++ standard (emphasis mine):

If two declarations of the same function or object specify different linkage-specifications (that is, the linkage-specifications of these declarations specify different string-literals), the program is ill-formed if the declarations appear in the same translation unit, and the one definition rule applies if the declarations appear in different translation units. Except for functions with C++ linkage, a function declaration without a linkage specification shall not precede the first linkage specification for that function. A function can be declared without a linkage specification after an explicit linkage specification has been seen; the linkage explicitly specified in the earlier declaration is not affected by such a function declaration.

I'm not convinced it's good practice though, since there's the potential for the linkage specifications to diverge by accident (if, for example, the header file containing the linkage specification isn't included in the implementing file). I think it's better to be explicit in the implementation file.

like image 111
Adam Bowen Avatar answered Oct 16 '22 04:10

Adam Bowen


They only need to go in anything that is included by other source files.

With some idioms you'll find people including source files.

like image 27
Peter Alexander Avatar answered Oct 16 '22 03:10

Peter Alexander