Skip to content

Commit a34dfc8

Browse files
committed
Fix withCString in the presence of old binaries, and optimize it for ASCII
1 parent 093135c commit a34dfc8

File tree

2 files changed

+8
-1
lines changed

2 files changed

+8
-1
lines changed

stdlib/public/core/String.swift

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -723,7 +723,8 @@ extension String {
723723
encodedAs targetEncoding: TargetEncoding.Type,
724724
_ body: (UnsafePointer<TargetEncoding.CodeUnit>) throws -> Result
725725
) rethrows -> Result {
726-
if targetEncoding == UTF8.self {
726+
if targetEncoding == UTF8.self ||
727+
(targetEncoding == Unicode.ASCII.self && _guts.isASCII) {
727728
return try unsafe self.withCString {
728729
(cPtr: UnsafePointer<CChar>) -> Result in
729730
_internalInvariant(UInt8.self == TargetEncoding.CodeUnit.self)

stdlib/public/core/StringGuts.swift

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -245,6 +245,12 @@ extension _StringGuts {
245245
internal func _slowWithCString<Result>(
246246
_ body: (UnsafePointer<Int8>) throws -> Result
247247
) rethrows -> Result {
248+
if _object.isFastZeroTerminated {
249+
// This branch looks unreachable, but can be reached via `withCString`
250+
// in binaries that haven't been recompiled since the termination flag
251+
// was added to _StringObject. Retry the fast path if so.
252+
return try withCString(body)
253+
}
248254
_internalInvariant(!_object.isFastZeroTerminated)
249255
return try String(self).utf8CString.withUnsafeBufferPointer {
250256
let ptr = unsafe $0.baseAddress._unsafelyUnwrappedUnchecked

0 commit comments

Comments
 (0)