From 867d7a5690ee7217f217731cf2f63215c18fa68a Mon Sep 17 00:00:00 2001 From: Ian Anderson Date: Tue, 19 Jan 2016 15:06:23 -0800 Subject: [PATCH] +[OCMArg setTo:] crashes if invoked with NULL OCMock 3.2.1 introduced a bug where something like this crashes. OCMStub([mockFileManager createSymbolicLinkAtURL:OCMOCK_ANY withDestinationURL:OCMOCK_ANY error:[OCMArg setTo:nil]]).andReturn(YES); [mockFileManager createSymbolicLinkAtURL:symlinkFile withDestinationURL:symlinkDestination error:NULL]; Fix it by checking for NULL in OCMPassByRefSetter. --- Source/OCMock/OCMPassByRefSetter.m | 12 +++++++---- Source/OCMockTests/OCMockObjectTests.m | 28 ++++++++++++++++++++++++++ 2 files changed, 36 insertions(+), 4 deletions(-) diff --git a/Source/OCMock/OCMPassByRefSetter.m b/Source/OCMock/OCMPassByRefSetter.m index 4bd6f95d..27141416 100644 --- a/Source/OCMock/OCMPassByRefSetter.m +++ b/Source/OCMock/OCMPassByRefSetter.m @@ -37,10 +37,14 @@ - (void)dealloc - (void)handleArgument:(id)arg { - if([value isKindOfClass:[NSValue class]]) - [(NSValue *)value getValue:[arg pointerValue]]; - else - *(id *)[arg pointerValue] = value; + void *pointerValue = [arg pointerValue]; + if(pointerValue != NULL) + { + if([value isKindOfClass:[NSValue class]]) + [(NSValue *)value getValue:pointerValue]; + else + *(id *)pointerValue = value; + } } @end diff --git a/Source/OCMockTests/OCMockObjectTests.m b/Source/OCMockTests/OCMockObjectTests.m index 1383f5d9..070b3e77 100644 --- a/Source/OCMockTests/OCMockObjectTests.m +++ b/Source/OCMockTests/OCMockObjectTests.m @@ -106,6 +106,25 @@ - (void)doStuffWithBlock:(void (^)())block andString:(id)aString; @end +@interface TestClassWithByReferenceMethod : NSObject + +- (void)returnValuesInObjectPointer:(id *)objectPointer booleanPointer:(BOOL *)booleanPointer; + +@end + +@implementation TestClassWithByReferenceMethod + +- (void)returnValuesInObjectPointer:(id *)objectPointer booleanPointer:(BOOL *)booleanPointer +{ + if(objectPointer != NULL) + *objectPointer = [[NSObject alloc] init]; + if(booleanPointer != NULL) + *booleanPointer = NO; +} + +@end + + @interface NotificationRecorderForTesting : NSObject { @public @@ -637,6 +656,15 @@ - (void)testReturnsValuesInNonObjectPassByReferenceArguments } +- (void)testReturnsValuesInNullPassByReferenceArguments +{ + mock = OCMClassMock([TestClassWithByReferenceMethod class]); + OCMStub([mock returnValuesInObjectPointer:[OCMArg setTo:nil] booleanPointer:[OCMArg setToValue:@NO]]); + [mock returnValuesInObjectPointer:NULL booleanPointer:NULL]; + OCMVerify([mock returnValuesInObjectPointer:NULL booleanPointer:NULL]); +} + + // -------------------------------------------------------------------------------------- // invoking block arguments // --------------------------------------------------------------------------------------