Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>Problem discovered; outline fix created...</p> <p>Code received, unpacked, and compiled; the linker produces essentially the same error that you're seeing...</p> <pre><code>Osiris-8 JL: make bgmath.o building.o customio.o filedaemon.o log.o main.o ui.o vsystem.o g++ -c -o bgmath.o bgmath.cpp g++ -c -o building.o building.cpp g++ -c -o customio.o customio.cpp g++ -c -o filedaemon.o filedaemon.cpp g++ -c -o log.o log.cpp g++ -c -o main.o main.cpp g++ -c -o ui.o ui.cpp g++ -c -o vsystem.o vsystem.cpp Osiris-8 JL: g++ -o cmd *.o Undefined symbols for architecture x86_64: "Building::Building(std::basic_string&lt;char, std::char_traits&lt;char&gt;, std::allocator&lt;char&gt; &gt;)", referenced from: runUI() in ui.o "Log::operator+=(std::basic_string&lt;char, std::char_traits&lt;char&gt;, std::allocator&lt;char&gt; &gt;)", referenced from: runUI() in ui.o "Log::getLog(std::basic_string&lt;char, std::char_traits&lt;char&gt;, std::allocator&lt;char&gt; &gt;)", referenced from: runUI() in ui.o "Log::Log()", referenced from: __static_initialization_and_destruction_0(int, int) in ui.o ld: symbol(s) not found for architecture x86_64 collect2: ld returned 1 exit status Osiris-8 JL: </code></pre> <p>This is on MacOS X 10.6.7 with GCC 4.6.0 (which I compiled). Since it is substantially the same as what you got, the version of G++ is essentially irrelevant (but not wholly; the c++filt distributed along with GCC 4.2.1 by Apple does not recognize the 'nm' output you provided, even after cleaning the BOM out of the file).</p> <p>OK - several grey hairs later - I know roughly what is going on.</p> <p>When I run <code>nm log.o</code>, it said '<code>nm: no name list</code>'. That's because it is, in fact, an empty object file. And it is an empty object file because all the code is in a class declaration, but is never used so there is no object code in the file, and no functions.</p> <p>I had a suspicion that it was something to do with definitions - I had not guessed it was as completely 'no defined functions' as it is.</p> <p>So, how do we fix it?</p> <p>The first problem is that you have log.cpp but it does not include log.h. This is a strong indicator of problems. The header defines the public interface to the class(es) defined in the source, and the only (sane) way of ensuring they are in agreement is to include the header in the source file. In fact, it is best to include the header first so that you can be sure it is self-contained (can be used in any source module).</p> <p>When we do that, we find immediately that log.h is not self-contained -- it needs <code>#include &lt;vector&gt;</code> too. When that's fixed, we find that you cannot compile log.cpp successfully:</p> <pre><code>g++ -c -o log.o log.cpp log.cpp:12:8: error: redefinition of ‘struct logResult’ log.h:15:8: error: previous definition of ‘struct logResult’ log.cpp:17:8: error: redefinition of ‘struct parsedLog’ log.h:20:8: error: previous definition of ‘struct parsedLog’ log.cpp:22:7: error: redefinition of ‘class Log’ log.h:25:7: error: previous definition of ‘class Log’ make: *** [log.o] Error 1 </code></pre> <p>The two structures are declared in the header, so they should not be redeclared in the source. The function definitions must be prefixed with Log:: and removed from the 'class Log { ... }' braces. There is then routine clean up of the compilation errors, leading to:</p> <hr> <h3>log.h</h3> <pre><code>#ifndef LOG_H_ #define LOG_H_ #include &lt;vector&gt; #include &lt;string&gt; using namespace std; struct logResult { vector &lt;string&gt; result; int status; }; struct parsedLog { string result; int status; }; class Log { public: int initialize(); int initialize(string text); Log (); Log (string text); bool isInitialized(); int add(string text); int operator+= (string text); int clearLog (bool init = true); logResult getLog(); parsedLog getLog(string delim); private: bool initialized; vector &lt;string&gt; actionLog; }; #endif /* LOG_H_ */ </code></pre> <h3>log.cpp</h3> <pre><code>#include "log.h" #include "consts.h" using namespace std; int Log::initialize(){ if (initialized) return ALREADY_INIT; actionLog.push_back("*** Log initialized ***"); initialized = true; return SUCCESS; } int Log::initialize(string text){ if (initialized) return ALREADY_INIT; // otherwise... initialize(); actionLog.push_back("Initialization message: "+text); return SUCCESS; } Log::Log (){ initialize(); } Log::Log (string text){ initialize(text); } bool Log::isInitialized(){ return initialized; } int Log::add(string text){ if (!initialized) return NOT_INIT; actionLog.push_back(text); return SUCCESS; } int Log::operator+= (string text){ return add(text); } int Log::clearLog(bool init){ if (!initialized) return NOT_INIT; //delete actionLog; initialized = false; if (init) return initialize(); // Else return SUCCESS; } logResult Log::getLog(){ if (!initialized){ logResult final; final.status = NOT_INIT; return final; } else { logResult final; final.result = actionLog; final.status = SUCCESS; return final; } } parsedLog Log::getLog(string delim){ if (!initialized){ parsedLog final; final.status = NOT_INIT; return final; } else { parsedLog final; string logString; for (unsigned int i; i&lt;actionLog.size()-1; i++){ logString += actionLog[i]; logString += delim; } logString += actionLog.back(); final.result = logString; final.status = SUCCESS; return final; } } </code></pre> <hr> <p>These files compile cleanly to generate log.o containing some useful functions. The link failure after that is:</p> <pre><code>Undefined symbols for architecture x86_64: "Building::Building(std::basic_string&lt;char, std::char_traits&lt;char&gt;, std::allocator&lt;char&gt; &gt;)", referenced from: runUI() in ui.o ld: symbol(s) not found for architecture x86_64 collect2: ld returned 1 exit status </code></pre> <p>Fixing that is left as an exercise for you - but I believe analogous changes are needed in building.h and building.cpp.</p> <hr> <p>There are still some issues that should be resolved. In particular, headers should not usually do <code>using namespace std;</code> as that is an unwarranted intrusion into other programmer's control over the namespaces they use. See <a href="https://stackoverflow.com/questions/5849457/using-namespace-in-c-headers">Using namespace in C++ headers</a> for a recent discussion of this issue.</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. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
    3. VO
      singulars
      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