I don't know why I keep getting unresolved external symbols when I compile
this code


// File - prochead.cpp
#include <stdio.h>
#include <malloc.h>
#include <process.h>
#include <stdlib.h>
//#include "resource.h"
#include "newexe.h"

//extern FILE *in, *rc;
//extern BOOL bWindows3;
//extern BOOL bDumpHeader;
//extern struct ResourceTable *pResourceEntry;


extern FILE *inFile, *rcFile;
extern struct ResourceTable *pResourceEntry;

void process_header(void);


// file - ne.cpp
#include <windows.h>
#include <string>

#include <ida.hpp>
#include <idp.hpp>
#include <loader.hpp>

#include "newexe.h"

extern FILE *inFile = NULL;
extern FILE *rcFile = NULL;
extern struct ResourceTable *pResourceEntry = NULL;

//////////////////////////////////////////////////////
Error 1 error LNK2019: unresolved external symbol "struct ResourceTable *
pResourceEntry" (?pResourceEntry@@3PAUResourceTable@@A) referenced in
function "void __cdecl process_header(void)" (?process_header@@YAXXZ)
prochead.obj
Error 2 error LNK2019: unresolved external symbol "struct _iobuf * rcFile"
(?rcFile@@3PAU_iobuf@@A) referenced in function "void __cdecl
process_header(void)" (?process_header@@YAXXZ) prochead.obj
Error 3 error LNK2019: unresolved external symbol "struct _iobuf * inFile"
(?inFile@@3PAU_iobuf@@A) referenced in function "void __cdecl
process_header(void)" (?process_header@@YAXXZ) prochead.obj

The question is why.... can you show me how?
Thanks
Jack

Re: Back to some basic stuff by Alex

Alex
Sat Dec 08 02:54:36 PST 2007

"Jack" wrote:
> I don't know why I keep getting unresolved external
> symbols when I compile this code

You get this error when you link the program rather than
compiling it. Compilation passes without a problem, right?

> // File - prochead.cpp
> // ...
> extern FILE *inFile, *rcFile;
> extern struct ResourceTable *pResourceEntry;
>
> // file - ne.cpp
> // ...
> extern FILE *inFile = NULL;
> extern FILE *rcFile = NULL;
> extern struct ResourceTable *pResourceEntry = NULL;
>
> Error 1 error LNK2019: unresolved external symbol "struct
> ResourceTable * pResourceEntry" ...

The LNK2019 (unresolved external symbol) error means that
linker searched for definition of given symbol across all
modules, but failed to find it (to resolve it).

Given your code, this is no wonder since you don't define
the above variables anywhere. When you specify `extern'
modifier it tells to the compiler: don't search for
definition, it defined elsewhere, let the linker find it
later. That's why the initialization of extern declarations
in "ne.cpp" file dosen't have any effect.

In order to solve it, you need to select one of project
files, where actual definition will be placed. Compiler
independent way to do it is to define a macro:

#if defined(MAIN_UNIT)
# define EXTERN
#else
# define EXTERN extern
#endif // MAIN_UNIT

Then you use `EXTERN' definition everywhere:

// File - prochead.cpp
EXTERN FILE *inFile;
EXTERN FILE *rcFile;

In one (and only) .CPP files define `MAIN_UNIT', so
declarations will omit `extern' modifier:

// file - ne.cpp
#define MAIN_UNIT
EXTERN FILE *inFile;
EXTERN FILE *rcFile;
...

You can save the hustle with a macro by using Microsoft
specific `__declspec( selectany )' modifier everywhere:

__declspec( selectany ) FILE *inFile;
__declspec( selectany ) FILE *rcFile;

Then linker will pick up one of a project files
automatically and put declarations there. Read more info
about `__declspec( selectany )' in MSDN.

HTH
Alex


Re: Back to some basic stuff by Alex

Alex
Sat Dec 08 02:59:43 PST 2007

> You can save the hustle with a macro by using Microsoft
> specific `__declspec( selectany )' modifier everywhere:
>
> __declspec( selectany ) FILE *inFile;
> __declspec( selectany ) FILE *rcFile;


Sory for the typo, it should be:

extern __declspec( selectany ) FILE *inFile;
extern __declspec( selectany ) FILE *rcFile;

Alex


Re: Back to some basic stuff by Alexander

Alexander
Sat Dec 08 07:22:51 PST 2007

If you declare an object 'extern' AND initialize it, it becomes defined. In
this case, 'extern' is usually redundant.

"Alex Blekhman" <tkfx.REMOVE@yahoo.com> wrote in message
news:%23puiJiYOIHA.5524@TK2MSFTNGP05.phx.gbl...
> "Jack" wrote:
>> I don't know why I keep getting unresolved external symbols when I
>> compile this code
>
> You get this error when you link the program rather than compiling it.
> Compilation passes without a problem, right?
>
>> // File - prochead.cpp
>> // ...
>> extern FILE *inFile, *rcFile;
>> extern struct ResourceTable *pResourceEntry;
>>
>> // file - ne.cpp
>> // ...
>> extern FILE *inFile = NULL;
>> extern FILE *rcFile = NULL;
>> extern struct ResourceTable *pResourceEntry = NULL;
>>
>> Error 1 error LNK2019: unresolved external symbol "struct ResourceTable *
>> pResourceEntry" ...
>
> The LNK2019 (unresolved external symbol) error means that linker searched
> for definition of given symbol across all modules, but failed to find it
> (to resolve it).
>
> Given your code, this is no wonder since you don't define the above
> variables anywhere. When you specify `extern' modifier it tells to the
> compiler: don't search for definition, it defined elsewhere, let the
> linker find it later. That's why the initialization of extern declarations
> in "ne.cpp" file dosen't have any effect.
>
> In order to solve it, you need to select one of project files, where
> actual definition will be placed. Compiler independent way to do it is to
> define a macro:
>
> #if defined(MAIN_UNIT)
> # define EXTERN
> #else
> # define EXTERN extern
> #endif // MAIN_UNIT
>
> Then you use `EXTERN' definition everywhere:
>
> // File - prochead.cpp
> EXTERN FILE *inFile;
> EXTERN FILE *rcFile;
>
> In one (and only) .CPP files define `MAIN_UNIT', so declarations will omit
> `extern' modifier:
>
> // file - ne.cpp
> #define MAIN_UNIT
> EXTERN FILE *inFile;
> EXTERN FILE *rcFile;
> ...
>
> You can save the hustle with a macro by using Microsoft specific
> `__declspec( selectany )' modifier everywhere:
>
> __declspec( selectany ) FILE *inFile;
> __declspec( selectany ) FILE *rcFile;
>
> Then linker will pick up one of a project files automatically and put
> declarations there. Read more info about `__declspec( selectany )' in
> MSDN.
>
> HTH
> Alex



Re: Back to some basic stuff by Alex

Alex
Sat Dec 08 08:20:54 PST 2007

"Alexander Grigoriev" wrote:
> If you declare an object 'extern' AND initialize it, it
> becomes defined. In this case, 'extern' is usually
> redundant.

An initialization of `extern' variable is allowed only if
it's also `const' variable. Otherwise, the result of such
initialization is undefined:

extern const int a = 42; // OK
extern int b = 0; // undefined

Alex


Re: Back to some basic stuff by Alexander

Alexander
Sat Dec 08 17:49:42 PST 2007

I don't see such wording in C++ standard.

C standard explicitly shows such as valid in 6.9.2/4:

extern int i3 = 3; // definition, external linkage

"Alex Blekhman" <tkfx.REMOVE@yahoo.com> wrote in message
news:edAgeYbOIHA.3556@TK2MSFTNGP03.phx.gbl...
> "Alexander Grigoriev" wrote:
>> If you declare an object 'extern' AND initialize it, it becomes defined.
>> In this case, 'extern' is usually redundant.
>
> An initialization of `extern' variable is allowed only if it's also
> `const' variable. Otherwise, the result of such initialization is
> undefined:
>
> extern const int a = 42; // OK
> extern int b = 0; // undefined
>
> Alex



Re: Back to some basic stuff by Alex

Alex
Sun Dec 09 01:40:33 PST 2007

"Alexander Grigoriev" wrote:
> I don't see such wording in C++ standard.
>
> C standard explicitly shows such as valid in 6.9.2/4:
>
> extern int i3 = 3; // definition, external linkage

I can't find explicit mentioning about it either. Moreover,
according to 3.1/2 ("Declarations and definitions") it seems
that you're right about initializing extern variables.

However, I remember that VC++ constantly made troubles for
me with externs unless I declare/define them with above
mentioned macro or "__declspec(selectany)". Apparently, the
OP has the same troubles.

Alex



Re: Back to some basic stuff by Alexander

Alexander
Sun Dec 09 12:28:38 PST 2007

Apparently "zero-initialized" objects were put into "default-initialized",
then fell into "implicitly initialized", then fell further to "not
initialized". So VC got confused.

"Alex Blekhman" <tkfx.REMOVE@yahoo.com> wrote in message
news:uKspMekOIHA.280@TK2MSFTNGP03.phx.gbl...
> "Alexander Grigoriev" wrote:
>> I don't see such wording in C++ standard.
>>
>> C standard explicitly shows such as valid in 6.9.2/4:
>>
>> extern int i3 = 3; // definition, external linkage
>
> I can't find explicit mentioning about it either. Moreover, according to
> 3.1/2 ("Declarations and definitions") it seems that you're right about
> initializing extern variables.
>
> However, I remember that VC++ constantly made troubles for me with externs
> unless I declare/define them with above mentioned macro or
> "__declspec(selectany)". Apparently, the OP has the same troubles.
>
> Alex
>