NSLinguisticTagger crash on iOS or OS X
| Originator: | iamleeg | ||
| Number: | rdar://14817240 | Date Originated: | 2013-08-23 |
| Status: | Open | Resolved: | |
| Product: | OS X SDK | Product Version: | Multiple |
| Classification: | Crash/hang/data loss | Reproducible: | Always |
Summary: NSLinguisticTagger can cause a segmentation violation with certain, apparently valid input.
Steps to Reproduce:
Execute the attached code. This can be reproduced on either OS X or iOS.
Expected Results:
The code asks an NSLinguisticTagger for the tag at range {.location=13, .range=1} which is a newline character in the input string. The result should be that the function goes into the true case of the if at line 22, then the else clause at line 30.
Actual Results:
Crash.
Regression:
Unknown.
Notes:
The length of the string after the two newline characters at line 15 doesn't seem to change the behaviour, except that if it is zero-length then the function (deliberately) doesn't trigger the described behaviour. One or more characters in this position will trigger the crash.
I think this case is consistent with expected usage of NSLinguisticTagger, and therefore that the behaviour should be as described in "Expected Behaviour" above. While it's possible that I'm holding it wrong and that this is actually programmer error, I would expect that case to generate either an NSInvalidArgumentException or NSRangeException, instead of crashing in the way actually demonstrated.
[the attached source code contained this function:
//
// main.m
// LinguisticTagCheck
//
// Created by Graham Lee on 23/08/2013.
// Copyright (c) 2013 Graham Lee. All rights reserved.
//
#import <Foundation/Foundation.h>
int main(int argc, const char * argv[])
{
@autoreleasepool {
NSString *data = @"0123456789ab\n\nc";
NSRange newlineCharacter = NSMakeRange(13, 1);
NSLinguisticTagger *tagger = [[NSLinguisticTagger alloc] initWithTagSchemes: @[NSLinguisticTagSchemeTokenType] options: 0];
tagger.string = data;
NSRange rangeToExamine = newlineCharacter;
if (rangeToExamine.location != NSNotFound && rangeToExamine.location + rangeToExamine.length < [data length]) {
//assumption that the addition in the if statement didn't overflow is acceptable in this demo
NSRange rangeOfWord = {0};
NSString *tag = [tagger tagAtIndex: rangeToExamine.location scheme: NSLinguisticTagSchemeTokenType tokenRange: &rangeOfWord sentenceRange: NULL];
if ([tag isEqualToString: NSLinguisticTagWord]) {
NSString *editedWord = [data substringWithRange: rangeOfWord];
NSLog(@"word: %@", editedWord);
}
else {
NSLog(@"tag found: %@", tag);
}
}
else {
NSLog(@"Bad range");
}
}
return 0;
}
]
Comments
Please note: Reports posted here will not necessarily be seen by Apple. All problems should be submitted at bugreport.apple.com before they are posted here. Please only post information for Radars that you have filed yourself, and please do not include Apple confidential information in your posts. Thank you!