I have created an NSObject, for the sole purpose of locking. My question is, in my dealloc, how do I release(from memory) the lock. I have read that you should not modify the lock-object within synchronized. But In my scenario, I think that between the time since the @synchronized in dealloc completes, and the time that [_lockObject release] is called, another method in a different thread may acquire _lockObject. And hence if [_lockObject release] is called while _lockObject is held, bad things may happen.
What is the correct way to dispose of the lock in my dealloc method?
-(id)initWithImageFileName:(NSString*)imageFileName
{
if (self = [super init])
{
_imageFileName = [imageFileName retain];
_loadBackgroundCalled = NO;
_deallocing = NO;
_lockObject = [[NSObject alloc]init];
}
return self;
}
-(void)dealloc
{
_deallocing = YES;
@synchronized(_lockObject)
{
..... <releases some stuff>
}
[_lockObject release];
_lockObject = nil;
[_imageFileName release];
_imageFileName = nil;
[super dealloc];
}
-(void)loadBackground
{
@synchronized(_lockObject)
{
if (!_deallocing)
{
if (!_loadBackgroundCalled)
{
_loadBackgroundCalled = YES;
....
}
}
}
}
-(void)loadSprite:(XYTexture*)texture
{
@synchronized(_lockObject)
{
....
}
}
-(void)unloadBackground
{
@synchronized(_lockObject)
{
if (!_deallocing)
{
.....
_loadBackgroundCalled = NO;
}
}
}
Your object cannot be deallocated while it's being used by another object or thread. In other words, any thread that calls your object will already hold a reference to said object, and that reference will prevent the object from deallocating.
When your -dealloc
method is executed you can (and must) assume that no other objects or threads hold a reference to your object, and you therefore do not have to worry about concurrency.
If -dealloc
is called while your object is executing on a separate thread then that would indicate a bug in your application unrelated to this specific object. You do not solve the problem by setting flags like _deallocing
, as in your example code.