| View previous topic :: View next topic |
| Author |
Message |
Rex_VF5

Joined: 26 Dec 2007 Posts: 44
|
Posted: Sun Nov 02, 2008 5:56 am Post subject: C++ compilation problem |
|
|
First of all I swear I have gone through searching for solution and I have tried reordering libs and also adding extern "C" on every possible place. Nothing helped (maybe because I am pretty lame with C/C++ and much more skilled with Java). I am running SDK built out of SVN. I have narrowed the problem to be in static method of a class. Please help. Here's the scenario:
make output
| Code: | psp-gcc -I. -I/opt/toolchains/psp//psp/sdk/include -O2 -G0 -Wall -D_PSP_FW_VERSION=150 -L. -L/opt/toolchains/psp//psp/sdk/lib test.o -lstdc++ -lpspdebug -lpspdisplay -lpspge -lpspctrl -lpspsdk -lc -lpspnet -lpspnet_inet -lpspnet_apctl -lpspnet_resolver -lpsputility -lpspuser -lpspkernel -o test.elf
test.o: In function `main':
test.cpp:(.text+0x30): undefined reference to `XXX::Instance()'
collect2: ld returned 1 exit status
make: *** [test.elf] Error 1 |
Makefile
| Code: | PSPSDK = $(shell psp-config --pspsdk-path)
PSPLIBSDIR = $(PSPSDK)/..
TARGET = test
OBJS = test.o
LIBS = -lstdc++
CFLAGS = -O2 -G0 -Wall
ASFLAGS = $(CFLAGS)
include $(PSPSDK)/lib/build.mak |
test.h
| Code: | #ifndef TEST_H
#define TEST_H
#include "XXX.h"
class Test {
public:
Test();
~Test();
};
#endif // TEST_H
|
test.cpp
| Code: | #include "test.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <pspmoduleinfo.h>
/* Define the module info section */
PSP_MODULE_INFO("test", 0, 1, 0);
int main(int argc, char* argv[]){
Test* test = new Test();
XXX* xxx = XXX::Instance();
return 0;
}
Test::Test(){
}
Test::~Test(){
}
|
XXX.h
| Code: | #ifndef xxx_
#define xxx_
/* Export these Classes */
#pragma GCC visibility push(default)
#include <stdio.h>
using namespace std;
class XXX{
public:
/**
* Get an instance of the XXX class (Singleton Implementation)
*/
static XXX* Instance();
};
#pragma GCC visibility pop
#endif //xxx_ |
XXX.cpp
| Code: | #include <iostream>
#include "XXX.h"
//#include "XXXImpl.h"
XXX* instance = NULL;
XXX* XXX::Instance(){
if (instance == NULL) instance = new XXX();
return instance;
}
|
|
|
| Back to top |
|
 |
hlide
Joined: 10 Sep 2006 Posts: 750
|
Posted: Sun Nov 02, 2008 6:30 am Post subject: Re: C++ compilation problem |
|
|
| Rex_VF5 wrote: |
make output
| Code: | psp-gcc -I. -I/opt/toolchains/psp//psp/sdk/include -O2 -G0 -Wall -D_PSP_FW_VERSION=150 -L. -L/opt/toolchains/psp//psp/sdk/lib test.o -lstdc++ -lpspdebug -lpspdisplay -lpspge -lpspctrl -lpspsdk -lc -lpspnet -lpspnet_inet -lpspnet_apctl -lpspnet_resolver -lpsputility -lpspuser -lpspkernel -o test.elf
test.o: In function `main':
test.cpp:(.text+0x30): undefined reference to `XXX::Instance()'
collect2: ld returned 1 exit status
make: *** [test.elf] Error 1 |
|
no wonder, i cannot see xxx.o :
psp-gcc -I. -I/opt/toolchains/psp//psp/sdk/include -O2 -G0 -Wall -D_PSP_FW_VERSION=150 -L. -L/opt/toolchains/psp//psp/sdk/lib test.o
xxx.o -lstdc++ -lpspdebug -lpspdisplay -lpspge -lpspctrl -lpspsdk -lc -lpspnet -lpspnet_inet -lpspnet_apctl -lpspnet_resolver -lpsputility -lpspuser -lpspkernel -o test.elf
if you have N .o files so you should have them all as input files in linking stage of psp-gcc. Unless they are linked to a static library (say, xxx.a) you should add xxx.a |
|
| Back to top |
|
 |
Rex_VF5

Joined: 26 Dec 2007 Posts: 44
|
Posted: Sun Nov 02, 2008 6:42 am Post subject: Re: C++ compilation problem |
|
|
| hlide wrote: |
no wonder, i cannot see xxx.o :
psp-gcc -I. -I/opt/toolchains/psp//psp/sdk/include -O2 -G0 -Wall -D_PSP_FW_VERSION=150 -L. -L/opt/toolchains/psp//psp/sdk/lib test.o
xxx.o -lstdc++ -lpspdebug -lpspdisplay -lpspge -lpspctrl -lpspsdk -lc -lpspnet -lpspnet_inet -lpspnet_apctl -lpspnet_resolver -lpsputility -lpspuser -lpspkernel -o test.elf
if you have N .o files so you should have them all as input files in linking stage of psp-gcc. Unless they are linked to a static library (say, xxx.a) you should add xxx.a |
Now I will sound stupid - but how do I do that? I tried adding xxx.o to OBJS in Makefile but that doesn't work. |
|
| Back to top |
|
 |
hlide
Joined: 10 Sep 2006 Posts: 750
|
Posted: Sun Nov 02, 2008 7:02 am Post subject: |
|
|
| Code: | PSPSDK = $(shell psp-config --pspsdk-path)
PSPLIBSDIR = $(PSPSDK)/..
TARGET = test
OBJS = test.o XXX.o
LIBS = -lstdc++
CFLAGS = -O2 -G0 -Wall
ASFLAGS = $(CFLAGS)
include $(PSPSDK)/lib/build.mak |
|
|
| Back to top |
|
 |
Rex_VF5

Joined: 26 Dec 2007 Posts: 44
|
Posted: Sun Nov 02, 2008 7:09 am Post subject: |
|
|
| Thank you very much. I know I deserve this post to be marked "lamer of the month" ;-) |
|
| Back to top |
|
 |
PosX100
Joined: 15 Aug 2007 Posts: 98
|
Posted: Mon Nov 03, 2008 1:47 am Post subject: |
|
|
| Rex_VF5 wrote: | | I know I deserve this post to be marked "lamer of the month" ;-) |
Yes , but for another reason ... For abusing C++.
Singletons & CPP = bad choise ... |
|
| Back to top |
|
 |
Rex_VF5

Joined: 26 Dec 2007 Posts: 44
|
Posted: Mon Nov 03, 2008 3:02 am Post subject: |
|
|
| PosX100 wrote: | | Rex_VF5 wrote: | | I know I deserve this post to be marked "lamer of the month" ;-) |
Yes , but for another reason ... For abusing C++.
Singletons & CPP = bad choise ... |
In Java this is one of the most used patterns. Also this is part of a library - not my code. Anyway - can you tell me what would "good" C++ equivalent to singleton be and how to implement it? |
|
| Back to top |
|
 |
Onii
Joined: 05 Oct 2008 Posts: 40
|
Posted: Mon Nov 03, 2008 3:41 am Post subject: |
|
|
| There's nothing wrong with using the singleton design pattern in c++. Design patterns are language agnostic anyway so I'm not exactly sure what PosX100 is talking about. |
|
| Back to top |
|
 |
hlide
Joined: 10 Sep 2006 Posts: 750
|
Posted: Mon Nov 03, 2008 3:44 am Post subject: |
|
|
don't worry
PosX100 is probably a C++ hater or likes to code piggy code :P.
I prefer this way :
| Code: |
Singleton.h:
class Singleton
{
public:
Singleton *instance()
{
static Singleton singleton;
return &singleton;
}
private:
Singleton() {}
};
|
if I'm not wrong, g++ should be able to issue just "return &singleton;" when calling Singleton::instance() because it should instantiate "singleton();" before executing main() so "singleton" is already instantiated at the first call of Singleton::instance(). To be tested.
or you can also use only static methods if you don't need members.
EDIT:
well, apparently g++ produces something like :
| Code: |
Singleton *instance()
{
static instanciated = false;
static char placeholder[sizeof(Singleton)];
if (!instanciated)
{
new(placeholder) singleton();
instanciated = true;
}
return (Singleton *)placeholder;
}
|
i'm kinda disappointed but at least, it doesn't produce any heap allocation.
Last edited by hlide on Mon Nov 03, 2008 4:27 am; edited 1 time in total |
|
| Back to top |
|
 |
PosX100
Joined: 15 Aug 2007 Posts: 98
|
Posted: Mon Nov 03, 2008 3:55 am Post subject: |
|
|
In java it makes sense , since the only available globally namespace
are classes , so this is actually a common thing to do.
(Unless you wanna build your own ref registry or use something similar with JNDI)
C++ program with singleton classes =
C program with namespace support + garbage collection.
Singleton is for lazy programmers , who are just too lazy to pass
parameters to class member function.
Now , tell me ,as far as usability goes , ... which is more usable , this:
.A.
| Code: |
{
const float& delta = Engine::GetInstance()->MotionController::GetInstance->getDelta();
Renderer::GetInstance()->SceneManager::GetInstance()->present(delta);
}
|
or THIS:
.B.
| Code: |
{
const float& delta = engine.motionController.getDelta();
renderer.scene.present(delta);
}
|
??
And the answer is b of course or maybe ... not? |
|
| Back to top |
|
 |
Rex_VF5

Joined: 26 Dec 2007 Posts: 44
|
Posted: Mon Nov 03, 2008 4:09 am Post subject: |
|
|
PosX100,
while b) looks certainly nicer I wonder if it is equivalent. Main purpose of singleton pattern is to ensure only one instance of certain class exists. That is done by making constructor private and only used in singleton getter method. In your example I do not quite get how that is done but as I said earlier: I am C/C++ beginner and I already have another questions ready to be asked... |
|
| Back to top |
|
 |
hlide
Joined: 10 Sep 2006 Posts: 750
|
Posted: Mon Nov 03, 2008 4:47 am Post subject: |
|
|
| Code: |
Singleton.h:
class Singleton
{
friend void __unique_singleton() __attribute__((constructor))
{
extern Singleton *singleton;
static Singleton unique;
singleton = &unique;
}
public:
// your public methods
void doSomething() {}
private:
Singleton() {}
};
Singleton.cpp:
Singleton *singleton;
|
now "singleton" should be really instantiated before running main() so you can call "singleton->doSomething();" without fear. |
|
| Back to top |
|
 |
PosX100
Joined: 15 Aug 2007 Posts: 98
|
Posted: Mon Nov 03, 2008 4:57 am Post subject: |
|
|
| Rex_VF5 wrote: |
Main purpose of singleton pattern is to ensure only one instance of certain class exists. |
First of all , do you really need that(ask yourself :"Do i really need that")?
For example , if you were going to program a game , there are only
a few parts of the engine that will have to be initialized once(window/graphics/sound/input).
So , their types/classes can become member variables of the head application class object.
Now , if (for example) we plan to limit the maximum instances of object "X"
rendered on screen , we can simple create a factory system with a maximum available
objects to be respawned/rendered/etc.
There is really no reason to use singleton for such thing , actually ,
there are many ways to avoid singleton-itis for any case
(actually,even instance reference counter is much better). |
|
| Back to top |
|
 |
Rex_VF5

Joined: 26 Dec 2007 Posts: 44
|
Posted: Mon Nov 03, 2008 5:24 am Post subject: |
|
|
| PosX100 wrote: |
First of all , do you really need that(ask yourself :"Do i really need that")?
For example , if you were going to program a game , there are only
a few parts of the engine that will have to be initialized once(window/graphics/sound/input).
So , their types/classes can become member variables of the head application class object.
Now , if (for example) we plan to limit the maximum instances of object "X"
rendered on screen , we can simple create a factory system with a maximum available
objects to be respawned/rendered/etc.
There is really no reason to use singleton for such thing , actually ,
there are many ways to avoid singleton-itis for any case
(actually,even instance reference counter is much better). |
Now you're attacking the whole singleton pattern. I do not really feel myself to be that much of coding professional to argue with you. One example that comes to my mind is: you're creating a library people can use and extend. What you describe as an alternative would require people to behave properly (not calling constructor) while singleton pattern makes sure only one instance of class can be created. |
|
| Back to top |
|
 |
PosX100
Joined: 15 Aug 2007 Posts: 98
|
Posted: Mon Nov 03, 2008 6:30 pm Post subject: |
|
|
I'll give you a good example...
Lets take as example the above code:
| Code: |
Singleton.h:
class Singleton
{
friend void __unique_singleton() __attribute__((constructor))
{
extern Singleton *singleton;
static Singleton unique;
singleton = &unique;
}
public:
// your public methods
void doSomething() {}
private:
Singleton() {}
};
Singleton.cpp:
Singleton *singleton;
|
What does it do?(or,if you like , the advantages of the pattern)
It does 4 things :
1.It enforces "lazy" creation
2.It enforces "safe" destruction
3.Allows access globally
4.Enforces the existence of a single instance(at any point in time)
So , how about breaking the thingies into a single different thingy??
You get the point i bet...
| Quote: |
What you describe as an alternative would require people to behave properly (not calling constructor)
while singleton pattern makes sure only one instance of class can be created.
|
I'll ask you again , do you really need that? , answer is NO.
And why you shouldn't need such a thing? ,because you can always handle the
limit of an instance via many ways(private namespaces/private member classes in the head virtual application object/instance ref counter , ... OR , you can use patterns(such as mediator pattern for handling large projects)). |
|
| Back to top |
|
 |
leonliu
Joined: 15 Dec 2008 Posts: 5
|
Posted: Mon Dec 15, 2008 1:40 am Post subject: |
|
|
| Your file test must be test.c,so the sdk choose psp-gcc to complite.you`d better use test.cpp instead of test.c |
|
| Back to top |
|
 |
|