Remember that ANY other file in the build process can include a header. With the typical include guard: #ifndef MYHEADER \n #include MYHEADER, the header code is only inserted on the first instance. After that, the compiler has eaten it and remembers and doesn't need to include it again. Think of compiling as putting ALL the source code into one file and turning that into a binary. (you know, "compiling" as in putting it all in a pile). So it's not "into the same file" it's "into the same build".
You want a header file to be mutually exclusive with another header file. (Like, say, if you've got code that targets specific hardware via includes, and you obviously can't build towards two chips at the same time.) First off, if that's an issue, you should really have a single place where such things are defined (like the build script) so that's not a problem. But if you want a simple safeguard:
#ifndef PPC_e6500
#define PPC_e6500
#ifdef LINUX
#error This processor ain't big enough for the both of us, Tux. This here's 8548 territory!
#endif
That will fail to build and you can figure out who did whatever horrible thing that tried to build towards two targets at once.
_2into the_1files, and vice versa.ab.h, that correctly includes the right pair of files, and only ever include that in your other source code. The separatea_1.h..b_2.hfiles are then used only by the one header. Further, this can be extended to handlea_3.handb_3.hif necessary(next year? this year?). If there are source files that only work witha_1.h(and not witha_2.hor any of theb_*.hfiles), so be it. You'll be doing conditional builds for those source files anyway (but consider whetherab.cthat conditionally includesa_1.candb_1.c(ora_2.candb_2.c) would work.