diff --git a/Sources/_StringProcessing/ByteCodeGen.swift b/Sources/_StringProcessing/ByteCodeGen.swift index e8c92f2b5..29739f25c 100644 --- a/Sources/_StringProcessing/ByteCodeGen.swift +++ b/Sources/_StringProcessing/ByteCodeGen.swift @@ -109,7 +109,7 @@ fileprivate extension Compiler.ByteCodeGen { } // Fast path for eliding boundary checks for an all ascii quoted literal - if optimizationsEnabled && s.allSatisfy(\.isASCII) { + if optimizationsEnabled && s.allSatisfy(\.isASCII) && !s.isEmpty { let lastIdx = s.unicodeScalars.indices.last! for idx in s.unicodeScalars.indices { let boundaryCheck = idx == lastIdx diff --git a/Tests/RegexTests/MatchTests.swift b/Tests/RegexTests/MatchTests.swift index 8e01582a9..287b3b7c9 100644 --- a/Tests/RegexTests/MatchTests.swift +++ b/Tests/RegexTests/MatchTests.swift @@ -2465,6 +2465,9 @@ extension RegexTests { // case insensitive tests firstMatchTest(#"(?i)abc\u{301}d"#, input: "AbC\u{301}d", match: "AbC\u{301}d", semanticLevel: .unicodeScalar) + + // check that we don't crash on empty strings + firstMatchTest(#"\Q\E"#, input: "", match: "") } func testCase() {