I am developing a program in C and I need to have one .h file and two .c files that share the same name on the methods but have different implementations. So basically what I am trying to do is:
header.h --->
void f();
void d();
source1.c --->
#include "header.h"
void f(){
print("Hello");
}
void f(){
print("World");
}
source2.c --->
#include "header.h"
void f(){
print("My name");
}
void f(){
print("is Danni");
}
but I have an error of multiple declarations :(
So I was wondering if there is any kind of trick about how to do this, maybe using macros or somenthing like that.
Thanks...
Well, there are two solutions ..
The first solution (not recommended)
It is based entirely on the compilation process. You simply compile the source.c file with the main function with the source you want to use. This should work without errors simply because the compiler is not aware of the other file. This is not recommended because it provides the same functionality (at some extent), use the same header file but are seperated source files. You might risk losing one of them. Also, you have to be aware of that whenever you're compiling a program that uses that header.
The second solution (recommended)
It is based on the preprocessing step, which is much more safer than the compilation command because it works the same with any compiler options or commands.
You have to use Macro Conditionals because they're processed before compilation. The behaviour of macro conditionals is almost entirely based on variable existence or comparison.
You can use something like that:
#ifndef _HEADER_H
#define _HEADER_H
void f();
void d();
#ifndef _HEADER_H_2 /* Where this is the default behavior if nothing the macro wasn't defined */
# include "source1.c"
#else
# include "source2.c"
#endif
#endif /* _HEADER_H */
Related
I am in the process of exploring the C programming language and have started to learn about header files.
I am working with three different files in my program. One header file and two source files:
encrypt.h
void encrypt(char *message);
encrypt.c
#include "encrypt.h"
void encrypt(char *message)
{
while(*message)
{
*message = *message ^ 31;
message++;
}
}
main.c
#include <stdio.h>
#include "encrypt.h"
int main()
{
char myMessage[] = "Hello";
printf("Regular message: %s\n", myMessage);
encrypt(myMessage);
printf("Encrypted message: %s\n", myMessage);
return 0;
}
The first line in the encrypt.c file is the #include statement:
#include "encrypt.h"
My question is why is this line necessary inside of this file. I was reading how the #include directive has a copy/paste functionality and inside of the main.c file I can see how this approach would support forward declaration for the encrypt function; however, inside of the encrypt.c file, it would seem that forward declaration of the function is not necessary, and was wondering what was the purpose of using the include directive in this situation?
I apologize if this question has been asked elsewhere and will mark as duplicate as required. Thank you for the clarification.
In your particular case, it is not necessary for encrypt.c to include encrypt.h, but it is conventional for it to do so.
The normal purpose of header files is to provide a common location for declarations that can be shared among multiple source files. This avoids inconsistent declarations in different parts of the program, and when changes need to be made, it may reduce the number of files that need to be updated.
encrypt.c does not need to include encrypt.h because the latter contains only a declaration of function encrypt(), and encrypt.c already has one in the form of a definition of that function. It is nevertheless useful, because it allows the compiler to verify that the declaration in encrypt.h is consistent with the definition in encrypt.c.
If encrypt.c defined more functions, and encrypt.h provided declarations for all of them, then it could also serve in encrypt.c to ensure that declarations of all functions therein were visible to all functions therein, thus overcoming any dependency on the relative order of the actual definitions.
Side note:
The moment you add a new source file fancy_encrypt.c which calls the encrypt() function you must have a compile guard in the encrypt.hfile:
#ifndef ENCRYPT_H
#define ENCRYPT.H
void encrypt(char * message);
#endif
Otherwise you will get a compiler error due to multiple declarations of encrypt().
If I have a c project where my main program needs file1 and file2 but file2 also needs file1. Is there a way I can get around including file2 in both main and file1? If I have an include guard, will this prevent file1.c from being added twice?
//file1.h
#ifndef FILE1_H
#define FILE1_H
void func1(void);
#endif
--
//file1.c
#include "file1.h"
void func1(void) {
..do something
}
--
//file2.h
#ifndef FILE2_H
#define FILE2_H
void func2(void);
#endif
--
//file2.c
#include "file2.h"
#include "file1.h"
void func2(void) {
..do something
func1();
}
--
//main.c
#include "file1.h"
#include "file2.h"
int main(void) {
func1();
func2();
return 0;
}
-- Since file2 includes file1, can I do this? will it prevent repetition of file1 code?
//main.c (alternate)
#include "file2.h"
int main(void) {
func1();
func2();
return 0;
}
I'm not too concerned about problems arising if file2 decides to no longer include file1 in the future. I'm much more concerned with wasted space.
What I'd like to know is A: does the include guard prevent the code duplication and if so, there is no additional space used by including file1 in both main.c and file2.c. B: in the case that extra space is being used, will my alternate main.c work?
Quick explanation (with the note that all of this can be overwritten by people that know what they are doing):
First of all, two definitions: declaration is when you write down that something exists. For example, "int foo();" or "struct bar;". Note that we can't actually use this thing yet, we've just given it a name. As long as you declare them as the same thing, you can declare things as many times as you want! (variable declaration has its own rules).
Anything you want to use needs to be declared before you reference it.
definition is when you say what the declaration is. int foo() {asdfadf;} or struct bar{int x;}. Things can be (and often are) defined when they are declared, but not always.
In C, you must follow the One Definition Rule. Things can be declared as often as you like, but they can be only defined once per translation unit (defined in one sec). (in addition, function calls can only be declared once per entire executable).
There are very few things that need to be defined before you use them...other than variables, you only need to define a struct before you use it in a context where you need its size or access to its members.
What is a translation unit? It is all the files used to compile a single source file. Your header files aren't targeted for compilation. Only your .c files (called "source files") are. For each c file, we have the idea of a "translation unit", which is all the files that are used to compile that c file. The ultimate output of that code is a .o file. A .o files contains all the symbols required to run the code defined in that c++ file. So your c file and any files included are withing the header file. Note: not everything declared in the translation unit needs to be defined in it to get a valid .o file.
So what is in a header file? Well (in general) you have a few things:
function declarations
global definitions & declarations
struct definitions & declarations
Basically, you have the bare bones declarations and definitions that need to be shared between the translation units. #include allows you to keep this in one shared file, rather than copying and pasting this code all over.
Your definitions can only happen once, so a include guard prevents that from being a problem. But if you only have declarations, you don't technically need and include guard. (You should still use them anyway, they can limit the cross-includes you do, as well as work as a guarantee against infinitely recursive inclusion). However, you do need to include all declarations relative to each translation unit, so you will most likely include it multiple times. THIS IS OK. At-least the declaration is in one file.
When you compile a .o file, the compiler checks that you followed the one definition rule, as well as all your syntax is correct. This is why you'll get these types of errors in "creating .o" steps of compilation.
So in your example, after we compile, we get file1.o (containing the definition of func1), file2.o (containing the definition of func2), and main.o (containing the definition of main). The next step is to link all these files together, using the linker. When we do, the compiler takes all these .o files, and makes sure that there is only one definition for each function symbol in the file. This is where the magic of letting main.o know what is in file1.o and file2.o happens: it resolves the "unresolved symbols" and detects when there are conflicting symbols.
Final Thought:
Keeping code short is kindof a misguided task. You want your code to be maintainable and readable, and making the code as short as possible is about the opposite of that. I can write a whole program on one line with only single letter alpha-numberic variables names, but no one would ever know what it did...what you want to avoid is code duplication in things like declarations. Maintaining a long list of #includes can become tricky, so it is often good to group related functions together (A good rule of thumb is that if I almost always use A and B together) then they should probably be in the same header file.
Another thing I occasionally (occasionally because it has some serious drawbacks) is to use a convenience header file:
//convience.h
#ifndef CONVIENIENCE_H
#define CONVIENIENCE_H
#include "file1.h"
#include "file2.h"
#endif
The convenience header file only has other header files in it, which ensures that it NEVER contains code, which makes it a little easier to maintain, but still kindof a mess. Also note that if you do the include guards in file1 and file2, the convienience guard isn't nessisary, though it can (theoretically) speed up compilation.
Why can't you have a single header where you can put both your functions func1() and func2().
Just include the header in different files.
Didn't get what you mean by code duplication.
//file1.h
extern void func1();
extern void func2();
//file1.c
#include<file1.h>
void func1()
{`
enter code here`
}
//file2.c
#include<file1.h>
void func2()
{
}
//main.c
#include <file1.h>
main()
{
func1();
func2();
}
I have the following code layout
header.h
#ifndef _header_h
#define _header_h
void empty(float *array, int l)
{
int i;
for (i=1 ; i<=l ; i++)
{
array[i]=0;
}
}
#endif
and two files (lets call them file1.c and file2.c)
#include "header.h"
void function/*1 or 2*/(){
....
empty(a,b);
....
}
So compiling works fine but the linker command fails as the compiler says that there is a duplicate function definition. How can I avoid that with still using the header file? It is working fine when I only define the function in the header and create another .c file containing the full function. I always thought declaring it in the header is the way to go.
I always thought declaring it in the header is the way to go.
Yes, it is. Declaring it in the header is fine. It is not any good to define it in a header, though. (unless it's static inline, but you probably don't want to do that these days.)
You should never have things in a header that require memory in the running program. This is a rough way of specifying it, but it works pretty well in practice.
In other words, the header should only have the prototype for the function, which is a compile-time thing that doesn't "exist" in the running program (unlike the code of the function itself, which of course exists at runtime):
void empty(float *array, int l);
Then put the code in a separate C file, which you compile and link separately.
You have the function empty defined as a global symbol in the header. This means it will be a visible symbol in all compilation units that include it. There are three general workarounds:
make it a static function
static void empty(...) {...}
put the implementation into a separate compilation unit
in header.h:
void empty(float *array, int l);
in empty.c implement it
instruct your linker to ignore duplicate symbols. This differs from linker to linker, consult man ld.
On OS X: -m flag.
On Linux: -z muldefs
So I am doing some work in C where I have implementation of the same function in both assembly and C and I want to compare the performance of C vs assembly implementation. Now for that I would want to be able to compile and call the function conditionally i.e I would want to create a function which would act as an interface between the caller and the right function that I want to call. somehow I am not sure how to do that.
I was thinking somewhere along the line of following:
//header file containing the C definition and the assembly definition
void getstate(state* m, int* values);
extern void kalmanstate(state* m, int* values);
Then the caller can include the above header file and pass either &getstate or &kalmanstate.
void callTheRightFunction(state* m, int* values, void *fnptr(state*,int*))
{
*fnptr(m,values);
}
However the problem with this is that both getstate and kalmanstate will be compiled which kind of defeats the purpose of my simulation. It does not sound to me the best implementation of the wrapper I want to have. I know conditional execution exists in C but how would I use it to get the right function compile? I mean if I do something like this in the header file:
#ifdef __C__FUNC
void getstate(state* m, int *values);
#endif
#ifdef __kalman
void kalmanstate(state *m, int *values)
#endif
Then in the caller:
include "headerfile.h" //include the above header file
//caller defining _C_FUNC
define __C_FUNC
callTheRightFunction(m,p,&getstate);
But since I include the header file at the beginning when none of them are defined it would probably not include any of them at all and thus will generate runtime errro.
Any suggestions towards right direction would be appreciated. Thanks in advance guys!
Based on your addition to the original question, you were wondering if none of the functions would be compiled. Then you'll have to define __C__FUNC or __kalman before you include the header file:
#define __C__FUNC
#include "header.h"
But to avoid this problem when you don't define anything, an approach would be for you to use just one definition, like this, on the SOURCE file:
#ifdef __GSTATE_USE_C_FUNCTION
void getstate(state* m, int *values)
{
// C version
}
#else
void getstate(state *m, int *values)
{
// Assembly version
}
#endif
And on the header file:
void getstate(state *m, int *values);
(Note the same function name, so you don't need to modify the code when you're calling the function)
But this would only work if you're including the header on the source file where getstate is being implemented too. (*1)
Then if you forgot to define __GSTATE_USE_C_FUNCTION before your header inclusion, the second function would be used, because it triggered the #else.
Now, you'd use it like this on a header file that BOTH source files include (that is, the file that implements the function, and the file that uses it):
// Comment the line below if you want the other version
#define __GSTATE_USE_C_FUNCTION
Of course you'd have to include this header before including the header which contains the prototype declaration.
And on the source file:
// Somewhere else on the code where you use the function
getstate(m, values);
So you'd only have to change the #define line on the global header.
In addition, if your compiler has an option to do preprocessor defining in the command line for it, then you'd not even need to define __GSTATE_USE_C_FUNCTION before the #include, you'd just use as a command line option, something like this (for example in bcc32):
bcc32 /D"__GSTATE_USE_C_FUNCTION" hello.c
This would avoid the problem (*1), and you'd not have to make a global header file that both source files have to include.
I see no problem here.
Options:
name the ASM and C functions that do the same differently. Use if or switch or, god forbid, ?: to call the right one.
Same name setup as above. Use a function pointer. If you assign it the address of the ASM function, then function calls through this pointer will go there. If you assign it the address of the C function, the calls will similarly go to the C function.
Same name setup as above. Define a macro that would expand to either the ASM or the C function's name. You can define the macro at compile time using the compiler's options. Use that macro in the code that needs to call one of the two functions.
Place the ASM and C functions into separate .asm/.s and .c files. When compiling either include one file in the list of compiled files or include the other.
Should header files have #includes?
I'm generally of the opinion that this kind of hierarchical include is bad. Say you have this:
foo.h:
#include <stdio.h> // we use something from this library here
struct foo { ... } foo;
main.c
#include "foo.h"
/* use foo for something */
printf(...)
The day main.c's implementation changes, and you no longer use foo.h, the compilation will break and you must add <stdio.h> by hand.
Versus having this:
foo.h
// Warning! we depend on stdio.h
struct foo {...
main.c
#include <stdio.h> //required for foo.h, also for other stuff
#include "foo.h"
And when you stop using foo, removing it breaks nothing, but removing stdio.h will break foo.h.
Should #includes be banned from .h files?
You've outlined the two main philosophies on this subject.
My own opinion (and I think that's all that one can really have on this) is that headers should as self-contained as possible. I don't want to have to know all the dependencies of foo.h just to be able to use that header. I also despise having to include headers in a particular order.
However, the developer of foo.h should also take responsibility for making it as dependency-free as possible. For example, the foo.h header should be written to be free of a dependency on stdio.h if that's at all possible (using forward declarations can help with that).
Note that the C standard forbids a standard header from including another standard header, but the C++ standard doesn't. So you can see the problem you describe when moving from one C++ compiler version to another. For example, in MSVC, including <vector> used to bring in <iterator>, but that no longer occurs in MSVC 2010, so code that compiled before might not any more becuase you may need to specifically include <iterator>.
However, even though the C standard might seem to advocate the second philosophy, note that it also mandates that no header depend on another and that you can include headers in any order. So you get the best of both worlds, but at a cost of complexity to the implementers of the C library. They have to jump through some hoops to do this (particularly to support definitions that can be brought in through any of several headers, like NULL or size_t). I guess that the people who drafted the C++ standard decided adding that complexity to impersonators was no longer reasonable (I don't know to what degree C++ library implementors take advantage of the 'loophole' - it looks like MS might be tightening this up, even if it's not technically required).
My general recommendations are:
A file should #include what it needs.
It should not expect something else to #include something it needs.
It should not #include something it doesn't need because something else might want it.
The real test is this: you should be able to compile a source file consisting of any single #include and get no errors or warnings beyond "There is no main()". If you pass this test, then you can expect anything else to be able to #include your file with no problems. I've written a short script called "hcheck" which I use to test this:
#!/usr/bin/env bash
# hcheck: Check header file syntax (works on source files, too...)
if [ $# -eq 0 ]; then
echo "Usage: $0 <filename>"
exit 1
fi
for f in "$#" ; do
case $f in
*.c | *.cpp | *.cc | *.h | *.hh | *.hpp )
echo "#include \"$f\"" > hcheck.cc
printf "\n\033[4mChecking $f\033[0m\n"
make -s $hcheck.o
rm -f hcheck.o hcheck.cc
;;
esac
done
I'm sure there are several things that this script could do better, but it should be a good starting point.
If this is too much, and if your header files almost always have corresponding source files, then another technique is to require that the associated header be the first #include in the source file. For example:
Foo.h:
#ifndef Foo_h
#define Foo_h
/* #includes that Foo.h needs go here. */
/* Other header declarations here */
#endif
Foo.c:
#include "Foo.h"
/* other #includes that Foo.c needs go here. */
/* source code here */
This also shows the "include guards" in Foo.h that others mentioned.
By putting #include "Foo.h" first, Foo.h must #include its dependencies, otherwise you'll get a compile error.
Well, main shouldn't rely on "foo.h" in the first place for stdio. There's no harm in including something twice.
Also, perhaps foo.h doesn't really need stdio. What's more likely is that foo.c (the implementation) needs stdio.
Long story short, I think everyone should just include whatever they need and rely on include guards.
Once you get into projects with hundreds or thousands of header files, this gets untenable. Say I have a header file called "MyCoolFunction.h" that contains the prototype for MyCoolFunction(), and that function takes pointers to structs as parameters. I should be able to assume that including MyCoolFunction.h will include everything that's necessary and allow me to use that function without looking in the .h file to see what else I need to include.
If the header file needs a specific header, add it to the header file
#ifndef HEADER_GUARD_YOUR_STYLE
#define HEADER_GUARD_YOUR_STYLE
#include <stdio.h> /* FILE */
int foo(FILE *);
#endif /* HEADER GUARD */
if the code file doesn't need a header, don't add it
/* #include <stdio.h> */ /* removed because unneeded */
#include <stddef.h> /* NULL */
#include "header.h"
int main(void) {
foo(NULL);
return 0;
}
Why don't you #include stuff in the *.c file corresponding to the header?