Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>Your makefile must have a list of objects to link together, like so:</p> <pre><code>OBJ_FILES = inner_definitions.o inner_class_1.o inner_class_2.o \ outer_class.o executable.o executable : $(OBJ_FILES) gcc $^ -o $@ </code></pre> <p>Someone must write this; gcc can't do it for you, Make can't do it for you. Not every developer on the project needs to know how to construct that list, only the one who writes that part of the makefile. All the others will use that makefile, and a developer who adds a new dependency (e.g. <code>inner_class_3</code>) can add it to the list.</p> <p>And if your makefile is lost in a fire and the only developer who knows all the dependencies is hit by a bus, it really isn't hard to reconstruct the list: when you try to make <code>executable</code>, the linker complains that <code>foo::bar()</code> is undefined, you grep around and discover that <code>foo::bar()</code> is defined in <code>inner_class_2.cpp</code>, you add <code>inner_class_2.o</code> to the list. Repeat until the linker stops complaining.</p> <p><b>P.S.</b> Once that's in order, you can simplify the rest of the makefile quite a lot:</p> <pre><code>%.o: %.cpp %.h gcc -c $&lt; -o $@ inner_class_1.o inner_class_2.o : inner_definitions.h outer_class.o : inner_class_1.h inner_class_2.h executable.o : outer_class.h </code></pre> <p><b>EDIT:</b><br></p> <ol> <li>The method I suggested does <em>not</em> require listing every object file that can be made, just the ones that are actually needed to build `executable`; I inferred the list from your question. <li> Passing extra object files to the linker makes no difference to the final executable, but it does lead to unnecessary rebuilding. For example, suppose you add `alien.o` to `OBJ_FILES`. Then if you modify `alien.cpp` and run `make executable`, it will rebuild `alien.o` and `executable` even though there's no real need to do so. <b>Correction (thanks to slowdog):</b> unnecessary object files go into the final executable as dead code-- but I'm still right about unnecessary rebuilding. <li> Organizing object files into archives and shared libraries is often convenient, but doesn't really change anything here. <li>I know of no robust way to automatically construct the object list -- that is, a way that could deal with problem cases such as when the same function is defined in two different source files. This could become a real problem if unit tests are involved. <b>But</b> you could do it within your makefile <b>if</b> you follow a simple naming convention. <li>The trick for doing it within your makefile is a pretty advanced one. I honestly think you'd be better off doing this the simple way until you're more comfortable with the tools. </ol> <p><b>EDIT:</b><br> All right, here's an outline of the advanced technique.</p> <p>First, consider all of the #included header files. It would be nice to have Make handle the dependencies instead of putting them in by hand, as in the makefile above. And this is a straightforward task: if X.cpp #includes Y.h (either directly or through some chain of #included header files), then X.o will depend on Y.h. This has already been worked out as <a href="http://mad-scientist.net/make/autodep.html" rel="nofollow">"Advanced Auto-Dependency Generation"</a>. But if you follow a strict naming convention, you can take it a step further: if everything declared but not defines in X.h is defined in X.cpp, then by following the same tree of #include statements we should be able to construct a list of the needed object files, which will then be the dependencies of <code>executable</code>.</p> <p>This really is a lot to absorb at once, so I won't try to work through an example. I suggest you look over the document and see how it can generate the Y.h dependencies, then try applying it to the example makefile, then think about what the "step further" should do.</p> <p>Later you can apply it to the test harness, where the object files are, e.g., <code>outer_class.o</code>, <code>stub_inner_class_1.o</code>, <code>stub_inner_class_2.o</code> and <code>test_outer_class.o</code>.</p>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload