So here's the thing, and it's really just conceptual so don't let it bug you:I've got reasons for not wanting to rely on a specific build system. I don't mean to dis anybody's favorite, but I really just want to stick to what comes with the compiler. In this case, GCC. Automake has certain compatibility issues, especially with Windows. <3 GNU make is so limited that it often needs to be supplemented with shell scripts. Shell scripts can take many forms, and to make a long story short and probably piss a lot of people off, here is what I want to do --The main entry point is God. Be it a C or C++ source file, it is the center of the application. Not only do I want the main entry point to be the first thing that is executed, I also want it to be the first thing that is compiled. Let me explain --There was a time when proprietary and closed-source libraries were common. Thanks to Apple switching to Unix and Microsoft shooting themselves in the foot, that time is over. Any library that needs to be dynamically linked can be included as a supporting file of the application. For that reason, separate build instructions for .SOs (and maybe .DLLs ;]) is all fine and dandy, because they are separate executable files. Any other library should be statically linked. Now, let's talk about static linking --Static linking is a real bitch. That's what makefiles are for. If the whole project was written in one language (for instance C OR C++), you can #include the libraries as headers. That's just fine. But now, let's consider another scenario --Let's say you're like me and can't be arsed to figure out C's difficult excuse for strings, so you decide to use C++. But you want to use a C library, like for instance MiniBasic. God help us. If the C library wasn't designed to conform to C++'s syntax, you're screwed. That's when makefiles come in, since you need to compile the C source file with a C compiler and the C++ source file with a C++ compiler. I don't want to use makefiles. Bear with me --I would hope that there is a way to exploit GCC's preprocessor macros to tell it something like this:Hi, GCC. How are you doing? In case you forgot, this source file you're looking at right now is written in C++. You should of course compile it with G++. There's another file that this file needs, but it's written in C. It's called lolcats.c. I want you to compile that one with GCC into an object file and I want you to compile this one with G++ into the main object file, then I want you to link them together into an executable file.How might I write such a thing in preprocessor lingo? Does GCC even do that?
Compiling C/C++ code by way of including preprocessor build instructions in an actual C/C++ source file
gcc;c++;programming;linker;static linking
The main entry point is God. Be it a C or C++ source file, it is the center of the application.Only in the same way that nitrogen is the center of a pine tree. It is where everything starts, but there's nothing about C or C++ that makes you put the center of your application in main().A great many C and C++ programs are built on an event loop or an I/O pump. These are the centers of such programs. You don't even have to put these loops in the same module as main().Not only do I want the main entry point to be the first thing that is executed, I also want it to be the first thing that is compiled.It is actually easiest to put main() last in a C or C++ source file.C and C++ are not like some languages, where symbols can be used before they are declared. Putting main() first means you have to forward-declare everything else.There was a time when proprietary and closed-source libraries were common. Thanks to Apple switching to Unix and Microsoft shooting themselves in the foot, that time is over. Tell 'im 'e's dreamin'!OS X and iOS are full of proprietary code, and Microsoft isn't going away any time soon.What do Microsoft's current difficulties have to do with your question, anyway? You say you might want to make DLLs, and you mention Automake's inability to cope effectively with Windows. That tells me Microsoft remains relevant in your world, too.Static linking is a real bitch.Really? I've always found it easier than linking to dynamic libraries. It's an older, simpler technology, with fewer things to go wrong.Static linking incorporates the external dependencies into the executable, so that the executable stands alone, self-contained. From the rest of your question, that should appeal to you.you can #include the libraries as headersNo... You #include library headers, not libraries.This isn't just pedantry. The terminology matters. It has meaning.If you could #include libraries, #include </usr/lib/libfoo.a> would work. In many programming languages, that is the way external module/library references work. That is, you reference the external code directly.C and C++ are not among the languages that work that way.If the C library wasn't designed to conform to C++'s syntax, you're screwed.No, you just have to learn to use C++. Specifically here, extern C.How might I write such a thing in preprocessor lingo? It is perfectly legal to #include another C or C++ file:#include <some/library/main.cpp>#include <some/other/library/main.c>#include <some/other/library/secondary_module.c>#include <iostream>int main(){   call_the_library();   do_other_stuff();   return 0;}We don't use extern C here because this pulls the C and C++ code from those other libraries directly into our C++ file, so the C modules need to be legal C++ as well. There are a number of annoying little differences between C and C++, but if you're going to intermix the two languages, you're going to have to know how to cope with them regardless.Another tricky part of doing this is that the order of the #includes is more sensitive than the order of library references if a linker command. When you bypass the linker in this way, you end up having to do some things manually that the linker would otherwise do for you automatically.To prove the point, I took MiniBasic (your own example) and converted its script.c driver program to a standalone C++ program that says #include <basic.c> instead of #include <basic.h>. (patch) Just to prove that it's really a C++ program now, I changed all the printf() calls to cout stream insertions.I had to make a few other changes, all of them well within a normal day's work for someone who's going to intermix C and C++:The MiniBasic code makes use of C's willingness to tolerate automatic conversions from void* to any other pointer type. C++ makes you be explicit.Newer compilers are no longer tolerating use of C string constants (e.g. Hello, world!\n) in char* contexts. The standard says the compiler is allowed to place them into read-only memory, so you need to use const char*.That's it. Just a few minutes work, patching GCC complaints.I had to make some similar changes in basic.c to those in the linked script.c patch file. I haven't bothered posting the diffs, since they're just more of the same.For another way to go about this, study the SQLite Amalgamation, as compared to the SQLite source tree. SQLite doesn't use #include all the other files into a single master file; they're actually concatenated together, but that is also all #include does in C or C++.