@@ -407,6 +407,21 @@ private func readCheckStrings(in buf : UnsafeBufferPointer<CChar>, withPrefixes
407
407
return contents
408
408
}
409
409
410
+ private final class BoxedTable {
411
+ var table : [ String : String ] = [ : ]
412
+
413
+ init ( ) { }
414
+
415
+ subscript( _ i : String ) -> String ? {
416
+ set {
417
+ self . table [ i] = newValue!
418
+ }
419
+ get {
420
+ return self . table [ i]
421
+ }
422
+ }
423
+ }
424
+
410
425
/// Check the input to FileCheck provided in the \p Buffer against the \p
411
426
/// CheckStrings read from the check file.
412
427
///
@@ -416,7 +431,7 @@ private func check(input b : String, against checkStrings : [CheckString]) -> Bo
416
431
var failedChecks = false
417
432
418
433
// This holds all the current filecheck variables.
419
- var variableTable = [ String : String ] ( )
434
+ var variableTable = BoxedTable ( )
420
435
421
436
var i = 0
422
437
var j = 0
@@ -604,7 +619,7 @@ private class Pattern {
604
619
///
605
620
/// The \p VariableTable StringMap provides the current values of filecheck
606
621
/// variables and is updated if this match defines new values.
607
- func match( _ buffer : String , _ variableTable : [ String : String ] ) -> ( Int , Int ) ? {
622
+ func match( _ buffer : String , _ variableTable : BoxedTable ) -> ( Int , Int ) ? {
608
623
var matchLen : Int = 0
609
624
// If this is the EOF pattern, match it immediately.
610
625
if self . type == . EOF {
@@ -626,9 +641,9 @@ private class Pattern {
626
641
// If there are variable uses, we need to create a temporary string with the
627
642
// actual value.
628
643
var regExToMatch = self . regExPattern
629
- if !variableUses. isEmpty {
644
+ if !self . variableUses. isEmpty {
630
645
var insertOffset = 0
631
- for (v, offset) in variableUses {
646
+ for (v, offset) in self . variableUses {
632
647
var value : String = " "
633
648
634
649
if let c = v. characters. first, c == " @ " {
@@ -663,9 +678,21 @@ private class Pattern {
663
678
}
664
679
665
680
// If this defines any variables, remember their values.
666
- for (_, index) in self . variableDefs {
667
- assert ( index < matchInfo. count, " Internal paren error " )
668
- // VariableTable[VariableDef.0] = MatchInfo[VariableDef.second]
681
+ for (v, index) in self . variableDefs {
682
+ assert ( index < fullMatch. numberOfRanges, " Internal paren error " )
683
+ #if os(macOS)
684
+ let r = fullMatch. rangeAt ( index)
685
+ #else
686
+ let r = fullMatch. range ( at: index)
687
+ #endif
688
+ variableTable [ v] = buffer. substring (
689
+ with: Range < String . Index > (
690
+ uncheckedBounds: (
691
+ buffer. index ( buffer. startIndex, offsetBy: r. location) ,
692
+ buffer. index ( buffer. startIndex, offsetBy: NSMaxRange ( r) )
693
+ )
694
+ )
695
+ )
669
696
}
670
697
671
698
matchLen = fullMatch. range. length
@@ -829,7 +856,7 @@ private class Pattern {
829
856
if let end = nameEnd? . lowerBound {
830
857
name = matchStr. substring ( to: end)
831
858
} else {
832
- name = " "
859
+ name = matchStr
833
860
}
834
861
835
862
if name. isEmpty {
@@ -868,14 +895,14 @@ private class Pattern {
868
895
guard let ne = nameEnd else {
869
896
// Handle variables that were defined earlier on the same line by
870
897
// emitting a backreference.
871
- if let VarParenNum = self . variableDefs [ name] {
872
- if VarParenNum < 1 || VarParenNum > 9 {
898
+ if let varParenNum = self . variableDefs [ name] {
899
+ if varParenNum < 1 || varParenNum > 9 {
873
900
diagnose ( . error, diagLoc, " Can't back-reference more than 9 variables " )
874
901
return true
875
902
}
876
- self . addBackrefToRegEx ( VarParenNum )
903
+ self . addBackrefToRegEx ( varParenNum )
877
904
} else {
878
- variableUses. append ( ( name, regExPattern. utf8 . count) )
905
+ variableUses. append ( ( name, regExPattern. characters . count) )
879
906
}
880
907
continue
881
908
}
@@ -899,6 +926,9 @@ private class Pattern {
899
926
if let fixedMatchEnd = mino ( patternStr. range ( of: " {{ " ) ? . lowerBound, patternStr. range ( of: " [[ " ) ? . lowerBound) {
900
927
self . regExPattern += NSRegularExpression . escapedPattern ( for: patternStr. substring ( to: fixedMatchEnd) )
901
928
patternStr = patternStr. substring ( from: fixedMatchEnd)
929
+ } else {
930
+ // No more matches, time to quit.
931
+ break
902
932
}
903
933
}
904
934
@@ -958,7 +988,7 @@ private struct CheckString {
958
988
let dagNotStrings : Array < Pattern > = [ ]
959
989
960
990
/// Match check string and its "not strings" and/or "dag strings".
961
- func check( _ buffer : String , _ isLabelScanMode : Bool , _ variableTable : [ String : String ] ) -> ( Int , Int ) ? {
991
+ func check( _ buffer : String , _ isLabelScanMode : Bool , _ variableTable : BoxedTable ) -> ( Int , Int ) ? {
962
992
var lastPos = 0
963
993
964
994
// IsLabelScanMode is true when we are scanning forward to find CHECK-LABEL
@@ -1092,11 +1122,11 @@ private struct CheckString {
1092
1122
}
1093
1123
1094
1124
/// Verify there's no "not strings" in the given buffer.
1095
- private func checkNot( _ buffer : String , _ notStrings : [ Pattern ] , _ VariableTable : [ String : String ] ) -> Bool {
1125
+ private func checkNot( _ buffer : String , _ notStrings : [ Pattern ] , _ variableTable : BoxedTable ) -> Bool {
1096
1126
for pat in notStrings {
1097
1127
assert ( pat. type == . not, " Expect CHECK-NOT! " )
1098
1128
1099
- guard let ( Pos, _) /*(Pos, MatchLen)*/ = pat. match ( buffer, VariableTable ) else {
1129
+ guard let ( Pos, _) /*(Pos, MatchLen)*/ = pat. match ( buffer, variableTable ) else {
1100
1130
continue
1101
1131
}
1102
1132
buffer. cString ( using: . utf8) ? . withUnsafeBufferPointer { buf in
@@ -1111,7 +1141,7 @@ private struct CheckString {
1111
1141
}
1112
1142
1113
1143
/// Match "dag strings" and their mixed "not strings".
1114
- func checkDAG( _ buffer : String , _ variableTable : [ String : String ] ) -> Int ? {
1144
+ func checkDAG( _ buffer : String , _ variableTable : BoxedTable ) -> Int ? {
1115
1145
var notStrings = [ Pattern] ( )
1116
1146
if dagNotStrings. isEmpty {
1117
1147
return 0
0 commit comments