Linked Questions

Popular Questions

Here's a little experiment:

@interface Model : NSObject

@property (copy) NSString *value;

-(instancetype)initWith:(NSString *)value;

@end

@implementation Model

-(instancetype)initWith:(NSString *)value {
    self = [super init];
    self.value = value;
    return self;
}

@end

#import <Foundation/Foundation.h>
#import "Model.h"

void experiment(Model *m);

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        // insert code here...
        NSLog(@"Hello, World!");

        Model *ma = [[Model alloc] initWith:[[NSUUID UUID] UUIDString]];

        experiment(ma);
        NSLog(@"yyy %@", [ma value]);
    }
    return 0;
}

void experiment(ModelA *m) {
    NSString *testValue = nil;
    testValue = [m value];
    NSLog(@"xxx %@", testValue);
}

When run, this produces the following:

Hello, World!
xxx 6005A7B0-F71C-4755-B1BF-792D6296B716
yyy 6005A7B0-F71C-4755-B1BF-792D6296B716
Program ended with exit code: 0

But suppose I make this line:

testValue = [m value];

part of a breakpoint:

enter image description here

And this changes everything:

Hello, World!
(__NSCFString *) $0 = 0x000000010071e220 @"1C0DCB39-BFBB-4E67-A041-E6B58615BDFD"
xxx 1C0DCB39-BFBB-4E67-A041-E6B58615BDFD
yyy 1C0DCB39-BFBB-4E67-A041-E6B58615BDFD
*** -[CFString release]: message sent to deallocated instance 0x10071e220

And a crash. I see what's happening--the string is released once we exit the function scope, and the second time when the Model object is destroyed, which is an overrelease. But why doesn't the breakpoint (or more precisely, the lldb expression inside the breakpoint) handle the reference count correctly?

Related Questions