私は最終日を動的ストレージの問題の追跡に費やしましたが、トレイルの終わりには、NSString のサブクラス化について誤解/見逃したに違いないこと以外に何が起こっているのかわかりません。これは、問題のある大幅に削減され、多くのインストルメント化されたサンプルです。
IDStringBug.h には以下が含まれます。
#import <Foundation/NSArray.h>
#import <Foundation/NSString.h>
/*==================================*/
@interface IDStringBug:NSString {
NSString *_backingStore;
NSArray *path;
}
- (NSArray*) path;
- (void) dealloc;
- (NSUInteger) length;
-(id) initWithString: (NSString*) string;
-(unichar) characterAtIndex:(NSUInteger) index;
@end
IDStringBug.m には以下が含まれます。
#include <stdio.h>
#import "IDStringBug.h"
@implementation IDStringBug
- (NSArray*) path {
printf ("Return ptr to IDString: %s\n", [_backingStore cString]);
return path;}
- (void) dealloc {
printf ("Release IDString: %s\n", [_backingStore cString]);
printf ("Path count is %d\n", (int) [path retainCount]);
[_backingStore release];
printf ("Apres _backinstore\n");
printf ("Path count is %d\n", (int) [path retainCount]);
[path release];
printf ("After path release, done but for super\n");
[super dealloc];
}
-(id)initWithString:(NSString*)string {
if ((self = [self init])) {
_backingStore = [[NSString stringWithString:string] copy];
}
path = [_backingStore componentsSeparatedByString: @"."];
printf ("Path count is %d\n", (int) [path retainCount]);
return self;
}
-(NSUInteger) length {
return [_backingStore length];
}
-(unichar)characterAtIndex:(NSUInteger)index {
return [_backingStore characterAtIndex:index];
}
@end
bug.m には以下が含まれます。
#include <stdio.h>
#include <Foundation/NSAutoreleasePool.h>
#import "IDStringBug.h"
int main(int argc, char* argv[]) {
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
IDStringBug *myids = [IDStringBug stringWithString: @"a.b.c"];
printf ("Path count is %d\n", (int) [[myids path] retainCount]);
printf ("pool=%d\n", (int) [pool autoreleaseCount]);
[pool release];
}
出力は次のとおりです。
$ ./bug
Path count is 1
Return ptr to IDString: a.b.c
Path count is 1
pool=7
Release IDString: a.b.c
Segmentation fault (core dumped)