#import <Foundation/Foundation.h>
@interface TestInvocationRecorder: NSObject
{
	NSInvocation *invocationOne;
	NSInvocation *invocationTwo;
}
@end

@implementation TestInvocationRecorder
- (id) init
{
	if (nil == (self = [super init]))
	{
		return nil;
	}
	invocationOne = nil;
	invocationTwo = nil;
	return self;
}

- (void) dealloc
{
	[invocationOne release];
	[invocationTwo release];
	[super dealloc];
}

- (void)_playback
{
	NSString *stringOne = @"foo";
	NSString *stringTwo = @"bar";
	[invocationOne invokeWithTarget: stringOne];
	[invocationTwo invokeWithTarget: stringTwo];
	//BOOM:
	[invocationOne invokeWithTarget: stringOne];
}

- (NSMethodSignature *) methodSignatureForSelector: (SEL) aSelector
{
	NSString *aString = [[[NSString alloc] init] autorelease];
	if ([aString respondsToSelector: aSelector])
	{
		return [aString methodSignatureForSelector: aSelector];
	}
	else if ([NSStringFromSelector(aSelector) isEqual: @"playback"])
	{
		//dealloc has the same type signature.
		return [super methodSignatureForSelector: @selector(dealloc)];
	}
	return [super methodSignatureForSelector: aSelector];
}

- (void) forwardInvocation: (NSInvocation *)anInvocation
{
	[anInvocation retainArguments];
	NSString *selector = NSStringFromSelector([anInvocation selector]);
	if ((nil == invocationOne)
	   && [selector isEqual: @"uppercaseString"])
	{
		invocationOne = [anInvocation retain];
	}
	else if ((nil == invocationTwo)
	        && [selector isEqual: @"isEqualToString:"])
	{
		invocationTwo = [anInvocation retain];
	}
	else if ([selector isEqual: @"playback"])
	{
		[self _playback];
	}
	[anInvocation setReturnValue: &self];
}
@end
int main (void)
{
	NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
	TestInvocationRecorder *rec = [[TestInvocationRecorder alloc] init];
	NSString *testString = [NSString stringWithString: @"bar"];
	[[rec uppercaseString] isEqualToString: testString];
	//Goes to -forwardInvocation: and crashes:
	[rec playback];
	//[rec _playback] would work.
	[rec release];
	[pool release];
	return 0;
}
