Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[SR-11605] NSRangeException when obtaining substring from NSPathStore2/NSBigMutableString under macOS 10.14 #3384

Open
swift-ci opened this issue Oct 13, 2019 · 6 comments
Assignees

Comments

@swift-ci
Copy link
Contributor

Previous ID SR-11605
Radar rdar://problem/56226571
Original Reporter 1024jp (JIRA User)
Type Bug
Environment

Apple Swift version 5.1 (swiftlang-1100.0.270.13 clang-1100.0.33.7)

Target: x86_64-apple-darwin18.7.0

macOS: 10.14.6 (18G95)

Xcode: 11.1 (11A1027)

Additional Detail from JIRA
Votes 1
Component/s Foundation
Labels Bug
Assignee @Catfish-Man
Priority Medium

md5: aa68f9cc8ccaab9b757ab0270295576d

Issue Description:

Description

An NSRangeException arises and the application crashes when getting substring with a Swift range via subscript brackets from a specific Foundation's inner string class instance.

This issue occurs only when a compile optimization is enabled and under macOS 10.14. When runs the code without optimization or under macOS 10.15, it works correctly (I haven't tried macOS 10.13 or other environments yet).

Furthermore, if the same code is written in Objective-C it works even under the same conditions. So, something would go wrong with the range translation between Swift <-> ObjC.

Conditions

The conditions I found so far to reproduce this phenomenon are:

  • The execution environment is macOS 10.14 (not macOS 10.15).

  • Optimization -O is enabled.

  • The actual string instance class is not a pure Swift.String or __NSCFString but NSPathStore2 or NSBigMutableString at least.

  • The range to obtain substring contains the last index.

  • The range to obtain substring was made from a Foundation method (not like string.startIndex..<string.endIndex).

  • Obtaining substring with Range<String.Index> via subscript (not PartialRangeFrom<String.Index>).

In addition, the same code works when I used Xcode 10.3 with Swift 5. But I'm not sure from when (from Xcode 11, 11.1, or from Swift 5.1?) it has been broken.

If not satisfy one of those conditions, the code works as excepted without throwing any exception.

Expected Result

Succeed in obtaining substring without any exception.

Steps to Reproduce the Issue

The followings are sample codes to reproduce those issues.

Run it with -O option under macOS 10.14.x.

$swift -O foo.swift

It will crash due to an NSRangeException.

Sample code for NSPathStore2

import Foundation

// create NSPathStore2 instance
let string = NSString(string: "foo").appendingPathComponent("bar")
print((string as NSString).className)  // -> NSPathStore2

let range = string.range(of: "foo/bar")!
let substring = string[range]  // -[NSPathStore2 characterAtIndex:]: index (7) beyond bounds (7)
print(substring)

Sample code for NSBigMutableString

import Foundation
import AppKit.NSTextStorage

// create NSBigMutableString instance via NSTextStorage
let bigString = String(repeating: "a", count: 513)  // 512+1 for NSBigMutableString
let string = NSTextStorage(string: bigString).string
print((string as NSString).className)  // -> NSBigMutableString

let range = string.range(of: "a", options: .backwards)!
let substring = string[range]  // -[NSBigMutableString characterAtIndex:]: Index 513 out of bounds; string length 513'
print(substring)
@milseman
Copy link
Mannequin

milseman mannequin commented Oct 13, 2019

@Catfish-Man , any ideas here?

@belkadan
Copy link

Guessing that was meant for (a different) @Catfish-Man?

@Catfish-Man
Copy link
Member

Yeah. I'm going to look into this today most likely.

@Catfish-Man
Copy link
Member

The primary change in NSPathStore2 between those releases was to support CFStringGetCharactersPtr, so presumably this is something that occurs on the non-contiguous path. I'll see if I can force that to happen on a newer system with a different string subclass.

@Catfish-Man
Copy link
Member

Hmm. That hypothesis doesn't hold for NSBigMutableString though.

@Catfish-Man
Copy link
Member

I believe this is fixed in apple/swift#27779

Will attempt to confirm soon

@swift-ci swift-ci transferred this issue from apple/swift-issues Apr 25, 2022
@shahmishal shahmishal transferred this issue from apple/swift May 5, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants