destroy singleton?

R

Ron Eggler

Hi,

I created a singleton class and can't get rid of it anymore ;)
Uhm, the important things in the definition look like that:
[header]
class GPIOcontrol: public TSPThread
{
public:
static GPIOcontrol* instance(GPSData*); //Method returns pointer of
singleton instance of this class
~GPIOcontrol();
static GPIOcontrol* pinstance; //The instance pointer that is returned
by the method instance() - this is a singleton class

protected:
GPIOcontrol(GPSData *gpsDataObj);

private:
};

void PrepareToDie(void); //This method unsets the singleton pointer
[/header]
I call the PrepareToDie() function from the destructor and get a
segmentation fault, the implementation of this function looks like:
[implementation]
void PrepareToDie(void) //This method unsets the singleton pointer
{
delete GPIOcontrol::pinstance;
}
[/implementation]
I first had thsi delete PrepareToDie function as a public method in the
class what returned me a seg. fault so i thought i could resolve it by
moving it out of the class but it apparently wouldn't work.
Does anyone know how i can get rid of it and free its memory?

Thank you for hints & suggestions!
Ron
 
C

Christopher

Hi,

I created a singleton class and can't get rid of it anymore ;)
Uhm, the important things in the definition look like that:
[header]
class GPIOcontrol: public TSPThread
{
public:
static GPIOcontrol* instance(GPSData*); //Method returns pointer of
singleton instance of this class
~GPIOcontrol();
static GPIOcontrol* pinstance; //The instance pointer that is returned
by the method instance() - this is a singleton class

protected:
GPIOcontrol(GPSData *gpsDataObj);

private:

};

void PrepareToDie(void); //This method unsets the singleton pointer
[/header]
I call the PrepareToDie() function from the destructor and get a
segmentation fault, the implementation of this function looks like:
[implementation]
void PrepareToDie(void) //This method unsets the singleton pointer
{
delete GPIOcontrol::pinstance;
}
[/implementation]
I first had thsi delete PrepareToDie function as a public method in the
class what returned me a seg. fault so i thought i could resolve it by
moving it out of the class but it apparently wouldn't work.
Does anyone know how i can get rid of it and free its memory?

Thank you for hints & suggestions!
Ron


If its a singleton, then it should not be deleted until program exit.
There are many singleton patterns, one of which uses a reference
instead of a pointer, in order to rely on the program exit to release
it. I'd look over some of those. Also keep in mind the problems with
singletons and be sure you are handling them or IMO avoiding using
singletons to avoid the problems!

Google "static initialization fiasco"
Read up on global and static deallocation at program exit time, and
note the order is undefined! This caused a slew of bugs in the code
I've seen in the past.

IMHO it is better to avoid them altogether and create an instance of
the class at program start-up and then pass references to it around
instead. that way you can control init and release order. Especially
when it is obvious that one global,static (singleton) depends on
another.

Anyway, the obvious ism, your pointer is probably null by the time the
destructor gets called.
 
R

Ron Eggler

Andy said:
In the code you've supplied, you haven't initialised pinstance. Either
we're missing something - or you are... Also, you haven't shown what
else you do after the delete, nor what steps you take to make sure it
doesn't get deleted more than once.

i do initialize pinstance like this:
Code:
GPIOcontrol * GPIOcontrol::instance(GPSData *gpsDataObj)
{
        if (pinstance==NULL){//if this singleton hasn't been created yet...
                pinstance=new GPIOcontrol(gpsDataObj);          
        }       
        return pinstance;       
}

and before the delete command i check if it's "!=NULL" so that should be
fine.
What's a TSPThread?

That's a class handling threads, it just initializes and destoys the thread.
it also offers flags to check if the thread is running already.
The header looks like:
[tshpthread.h]
class TSPThread
{
public:
////////////////////////////////////////////////////////////////////////////////////
/// This method check to see the thread is still active or not
///@return bool true thread is still running
/// false thraed end already
////////////////////////////////////////////////////////////////////////////////////
bool IsActive(){return (m_pThread == 0?false:true);};

///The entry point of the thread, after TSPThread class was create, call
this method to start the real thread
///This method also make sure for every TSPThread instance, there's only
one thread runs
void start();

///Constructor
TSPThread();

///Destructor
virtual ~TSPThread();

// a global flag that can be set to true by a class above to end the
thread(s)
bool EndFlag;

protected:

////////////////////////////////////////////////////////////////////////////////////
///This method suppose to tell upper module the thread is terminated
already or not.
///@return true The thread is stopped already, it's safe to remove it from
memroy.
/// false The thread is still active, please wait
////////////////////////////////////////////////////////////////////////////////////
bool GetStopFlag(){return m_bStopThread;};

private:

////////////////////////////////////////////////////////////////////////////////////
///This is the pure virutal function, all subclass should implement this
fucntion. All stuff
///You wanna do in the thread whould go here.
////////////////////////////////////////////////////////////////////////////////////
virtual void run()=0;

////////////////////////////////////////////////////////////////////////////////////
///This is a helper function for TSPThread, it makes class TSPThread know
nothing about
///subclass, but subclass keeps all features as a normal class.
///@param void *i_ptr The pointer of current subclass object
///@return static void * Dummy type for pthread_create
////////////////////////////////////////////////////////////////////////////////////
static void *StartThread(void *i_ptr);

///The flag for thread is created already or not
bool m_bThreadAlready;

///Flag forcurrent thread is stopped or not
bool m_bStopThread;

///The handler for current thread
pthread_t m_pThread;

///Mutex for thread creation critical section
pthread_mutex_t mutex_single;


};
[/tshpthread.h]
 
R

Ron Eggler

Christopher said:
Hi,

I created a singleton class and can't get rid of it anymore ;)
Uhm, the important things in the definition look like that:
[header]
class GPIOcontrol: public TSPThread
{
public:
static GPIOcontrol* instance(GPSData*); //Method returns pointer
of
singleton instance of this class
~GPIOcontrol();
static GPIOcontrol* pinstance; //The
instance pointer that is returned
by the method instance() - this is a singleton class

protected:
GPIOcontrol(GPSData *gpsDataObj);

private:

};

void PrepareToDie(void); //This
method unsets the singleton pointer
[/header]
I call the PrepareToDie() function from the destructor and get a
segmentation fault, the implementation of this function looks like:
[implementation]
void PrepareToDie(void) //This
method unsets the singleton pointer
{
delete GPIOcontrol::pinstance;
}
[/implementation]
I first had thsi delete PrepareToDie function as a public method in the
class what returned me a seg. fault so i thought i could resolve it by
moving it out of the class but it apparently wouldn't work.
Does anyone know how i can get rid of it and free its memory?

Thank you for hints & suggestions!
Ron


If its a singleton, then it should not be deleted until program exit.

It is at the program exit where i want to delete it.
There are many singleton patterns, one of which uses a reference
instead of a pointer, in order to rely on the program exit to release
it. I'd look over some of those. Also keep in mind the problems with
singletons and be sure you are handling them or IMO avoiding using
singletons to avoid the problems!

Will keep in mind for future designs....
Google "static initialization fiasco"
Read up on global and static deallocation at program exit time, and
note the order is undefined! This caused a slew of bugs in the code
I've seen in the past.

Oh wow, haven't heard of that but shouldn't be applicable in my application
IMHO it is better to avoid them altogether and create an instance of
the class at program start-up and then pass references to it around
instead. that way you can control init and release order. Especially
when it is obvious that one global,static (singleton) depends on
another.

Anyway, the obvious ism, your pointer is probably null by the time the
destructor gets called.

negative, it isn't. :(
 
C

Christopher

Andy said:
Ron Eggler wrote:
[snip]

i do initialize pinstance like this:
GPIOcontrol * GPIOcontrol::instance(GPSData *gpsDataObj)
{
if (pinstance==NULL){//if this singleton hasn't been created yet...
pinstance=new GPIOcontrol(gpsDataObj);
}
return pinstance; }

[snip]


1) The singleton was initialized with a GPDData object A, but what if
you call GPIOcontrol::instance() with GPSData object B, in which case
it gives you back the singleton initialized with A???
1a) If you take a parameter during initialization, your object might
not be a candidate for a singleton
1a1) After all, if it is to always exist and there can be only one, it
can only be initialized one way... at least for the life of the
process.
2) Do you not care if an invalid or NULL GPSData object was passed as
a parameter?
3) Since GPSData is being passed in as a pointer, who allocated it?
who is going to destroy it? Is your singleton attempting to destroy it
when someone else already did? Or perhaps it is another global object
whom was destroyed during program exit before the singleton?
 
J

James Kanze

I created a singleton class and can't get rid of it anymore ;)

That's usually a feature, not a bug, where singletons are
concerned. In general, I avoid ever deleting a singleton.
Uhm, the important things in the definition look like that:
[header]
class GPIOcontrol: public TSPThread
{
public:
static GPIOcontrol* instance(GPSData*);
// Method returns pointer of singleton
// instance of this class
~GPIOcontrol();
static GPIOcontrol* pinstance;
// The instance pointer that is returned
by the method instance() - this is a singleton class

protected:
GPIOcontrol(GPSData *gpsDataObj);

private:
};
void PrepareToDie(void);
// This method unsets the singleton pointer
[/header]
I call the PrepareToDie() function from the destructor and get
a segmentation fault, the implementation of this function
looks like:

From the destructor of what?
[implementation]
void PrepareToDie(void)
//This method unsets the singleton pointer
{
delete GPIOcontrol::pinstance;
}
[/implementation]
I first had thsi delete PrepareToDie function as a public
method in the class what returned me a seg. fault so i thought
i could resolve it by moving it out of the class but it
apparently wouldn't work. Does anyone know how i can get rid
of it and free its memory?

Most of the time, it is preferable not to delete the singleton,
ever. That way, it remains accessible even in destructors of
static objects. In the rare cases where deletion is necessary,
the usual solution I've seen is to use a local static:

GPIOcontrol*
GPIOcontrol::instance()
{
static GPIOcontrol theOneAndOnly ;
return theOneAndOnly ;
}

In this case, the compiler takes care of ensuring that the
object is only created once, and that the destructor is called
once during program shutdown.

(Note that this will only work in a multithreaded environment if
you can ensure that instance is called at least once before
threads are started, or that it is only called from a single
thread. Otherwise, you need a scoped lock before the static.)
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Similar Threads


Members online

No members online now.

Forum statistics

Threads
473,995
Messages
2,570,236
Members
46,822
Latest member
israfaceZa

Latest Threads

Top