LLVM  14.0.0git
FileCheck.cpp
Go to the documentation of this file.
1 //===- FileCheck.cpp - Check that File's Contents match what is expected --===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // FileCheck does a line-by line check of a file that validates whether it
10 // contains the expected content. This is useful for regression tests etc.
11 //
12 // This file implements most of the API that will be used by the FileCheck utility
13 // as well as various unittests.
14 //===----------------------------------------------------------------------===//
15 
17 #include "FileCheckImpl.h"
18 #include "llvm/ADT/STLExtras.h"
19 #include "llvm/ADT/StringSet.h"
20 #include "llvm/ADT/Twine.h"
23 #include <cstdint>
24 #include <list>
25 #include <set>
26 #include <tuple>
27 #include <utility>
28 
29 using namespace llvm;
30 
32  switch (Value) {
33  case Kind::NoFormat:
34  return StringRef("<none>");
35  case Kind::Unsigned:
36  return StringRef("%u");
37  case Kind::Signed:
38  return StringRef("%d");
39  case Kind::HexUpper:
40  return StringRef("%X");
41  case Kind::HexLower:
42  return StringRef("%x");
43  }
44  llvm_unreachable("unknown expression format");
45 }
46 
48  StringRef AlternateFormPrefix = AlternateForm ? StringRef("0x") : StringRef();
49 
50  auto CreatePrecisionRegex = [&](StringRef S) {
51  return (Twine(AlternateFormPrefix) + S + Twine('{') + Twine(Precision) +
52  "}")
53  .str();
54  };
55 
56  switch (Value) {
57  case Kind::Unsigned:
58  if (Precision)
59  return CreatePrecisionRegex("([1-9][0-9]*)?[0-9]");
60  return std::string("[0-9]+");
61  case Kind::Signed:
62  if (Precision)
63  return CreatePrecisionRegex("-?([1-9][0-9]*)?[0-9]");
64  return std::string("-?[0-9]+");
65  case Kind::HexUpper:
66  if (Precision)
67  return CreatePrecisionRegex("([1-9A-F][0-9A-F]*)?[0-9A-F]");
68  return (Twine(AlternateFormPrefix) + Twine("[0-9A-F]+")).str();
69  case Kind::HexLower:
70  if (Precision)
71  return CreatePrecisionRegex("([1-9a-f][0-9a-f]*)?[0-9a-f]");
72  return (Twine(AlternateFormPrefix) + Twine("[0-9a-f]+")).str();
73  default:
74  return createStringError(std::errc::invalid_argument,
75  "trying to match value with invalid format");
76  }
77 }
78 
81  uint64_t AbsoluteValue;
82  StringRef SignPrefix = IntegerValue.isNegative() ? "-" : "";
83 
84  if (Value == Kind::Signed) {
85  Expected<int64_t> SignedValue = IntegerValue.getSignedValue();
86  if (!SignedValue)
87  return SignedValue.takeError();
88  if (*SignedValue < 0)
89  AbsoluteValue = cantFail(IntegerValue.getAbsolute().getUnsignedValue());
90  else
91  AbsoluteValue = *SignedValue;
92  } else {
93  Expected<uint64_t> UnsignedValue = IntegerValue.getUnsignedValue();
94  if (!UnsignedValue)
95  return UnsignedValue.takeError();
96  AbsoluteValue = *UnsignedValue;
97  }
98 
99  std::string AbsoluteValueStr;
100  switch (Value) {
101  case Kind::Unsigned:
102  case Kind::Signed:
103  AbsoluteValueStr = utostr(AbsoluteValue);
104  break;
105  case Kind::HexUpper:
106  case Kind::HexLower:
107  AbsoluteValueStr = utohexstr(AbsoluteValue, Value == Kind::HexLower);
108  break;
109  default:
110  return createStringError(std::errc::invalid_argument,
111  "trying to match value with invalid format");
112  }
113 
114  StringRef AlternateFormPrefix = AlternateForm ? StringRef("0x") : StringRef();
115 
116  if (Precision > AbsoluteValueStr.size()) {
117  unsigned LeadingZeros = Precision - AbsoluteValueStr.size();
118  return (Twine(SignPrefix) + Twine(AlternateFormPrefix) +
119  std::string(LeadingZeros, '0') + AbsoluteValueStr)
120  .str();
121  }
122 
123  return (Twine(SignPrefix) + Twine(AlternateFormPrefix) + AbsoluteValueStr)
124  .str();
125 }
126 
129  const SourceMgr &SM) const {
130  bool ValueIsSigned = Value == Kind::Signed;
131  // Both the FileCheck utility and library only call this method with a valid
132  // value in StrVal. This is guaranteed by the regex returned by
133  // getWildcardRegex() above. Only underflow and overflow errors can thus
134  // occur. However new uses of this method could be added in the future so
135  // the error message does not make assumptions about StrVal.
136  StringRef IntegerParseErrorStr = "unable to represent numeric value";
137  if (ValueIsSigned) {
138  int64_t SignedValue;
139 
140  if (StrVal.getAsInteger(10, SignedValue))
141  return ErrorDiagnostic::get(SM, StrVal, IntegerParseErrorStr);
142 
143  return ExpressionValue(SignedValue);
144  }
145 
146  bool Hex = Value == Kind::HexUpper || Value == Kind::HexLower;
147  uint64_t UnsignedValue;
148  bool MissingFormPrefix = AlternateForm && !StrVal.consume_front("0x");
149  if (StrVal.getAsInteger(Hex ? 16 : 10, UnsignedValue))
150  return ErrorDiagnostic::get(SM, StrVal, IntegerParseErrorStr);
151 
152  // Error out for a missing prefix only now that we know we have an otherwise
153  // valid integer. For example, "-0x18" is reported above instead.
154  if (MissingFormPrefix)
155  return ErrorDiagnostic::get(SM, StrVal, "missing alternate form prefix");
156 
157  return ExpressionValue(UnsignedValue);
158 }
159 
160 static int64_t getAsSigned(uint64_t UnsignedValue) {
161  // Use memcpy to reinterpret the bitpattern in Value since casting to
162  // signed is implementation-defined if the unsigned value is too big to be
163  // represented in the signed type and using an union violates type aliasing
164  // rules.
165  int64_t SignedValue;
166  memcpy(&SignedValue, &UnsignedValue, sizeof(SignedValue));
167  return SignedValue;
168 }
169 
171  if (Negative)
172  return getAsSigned(Value);
173 
175  return make_error<OverflowError>();
176 
177  // Value is in the representable range of int64_t so we can use cast.
178  return static_cast<int64_t>(Value);
179 }
180 
182  if (Negative)
183  return make_error<OverflowError>();
184 
185  return Value;
186 }
187 
189  if (!Negative)
190  return *this;
191 
192  int64_t SignedValue = getAsSigned(Value);
193  int64_t MaxInt64 = std::numeric_limits<int64_t>::max();
194  // Absolute value can be represented as int64_t.
195  if (SignedValue >= -MaxInt64)
197 
198  // -X == -(max int64_t + Rem), negate each component independently.
199  SignedValue += MaxInt64;
200  uint64_t RemainingValueAbsolute = -SignedValue;
201  return ExpressionValue(MaxInt64 + RemainingValueAbsolute);
202 }
203 
205  const ExpressionValue &RightOperand) {
206  if (LeftOperand.isNegative() && RightOperand.isNegative()) {
207  int64_t LeftValue = cantFail(LeftOperand.getSignedValue());
208  int64_t RightValue = cantFail(RightOperand.getSignedValue());
209  Optional<int64_t> Result = checkedAdd<int64_t>(LeftValue, RightValue);
210  if (!Result)
211  return make_error<OverflowError>();
212 
213  return ExpressionValue(*Result);
214  }
215 
216  // (-A) + B == B - A.
217  if (LeftOperand.isNegative())
218  return RightOperand - LeftOperand.getAbsolute();
219 
220  // A + (-B) == A - B.
221  if (RightOperand.isNegative())
222  return LeftOperand - RightOperand.getAbsolute();
223 
224  // Both values are positive at this point.
225  uint64_t LeftValue = cantFail(LeftOperand.getUnsignedValue());
226  uint64_t RightValue = cantFail(RightOperand.getUnsignedValue());
227  Optional<uint64_t> Result =
228  checkedAddUnsigned<uint64_t>(LeftValue, RightValue);
229  if (!Result)
230  return make_error<OverflowError>();
231 
232  return ExpressionValue(*Result);
233 }
234 
236  const ExpressionValue &RightOperand) {
237  // Result will be negative and thus might underflow.
238  if (LeftOperand.isNegative() && !RightOperand.isNegative()) {
239  int64_t LeftValue = cantFail(LeftOperand.getSignedValue());
240  uint64_t RightValue = cantFail(RightOperand.getUnsignedValue());
241  // Result <= -1 - (max int64_t) which overflows on 1- and 2-complement.
242  if (RightValue > (uint64_t)std::numeric_limits<int64_t>::max())
243  return make_error<OverflowError>();
244  Optional<int64_t> Result =
245  checkedSub(LeftValue, static_cast<int64_t>(RightValue));
246  if (!Result)
247  return make_error<OverflowError>();
248 
249  return ExpressionValue(*Result);
250  }
251 
252  // (-A) - (-B) == B - A.
253  if (LeftOperand.isNegative())
254  return RightOperand.getAbsolute() - LeftOperand.getAbsolute();
255 
256  // A - (-B) == A + B.
257  if (RightOperand.isNegative())
258  return LeftOperand + RightOperand.getAbsolute();
259 
260  // Both values are positive at this point.
261  uint64_t LeftValue = cantFail(LeftOperand.getUnsignedValue());
262  uint64_t RightValue = cantFail(RightOperand.getUnsignedValue());
263  if (LeftValue >= RightValue)
264  return ExpressionValue(LeftValue - RightValue);
265  else {
266  uint64_t AbsoluteDifference = RightValue - LeftValue;
268  // Value might underflow.
269  if (AbsoluteDifference > MaxInt64) {
270  AbsoluteDifference -= MaxInt64;
271  int64_t Result = -MaxInt64;
272  int64_t MinInt64 = std::numeric_limits<int64_t>::min();
273  // Underflow, tested by:
274  // abs(Result + (max int64_t)) > abs((min int64_t) + (max int64_t))
275  if (AbsoluteDifference > static_cast<uint64_t>(-(MinInt64 - Result)))
276  return make_error<OverflowError>();
277  Result -= static_cast<int64_t>(AbsoluteDifference);
278  return ExpressionValue(Result);
279  }
280 
281  return ExpressionValue(-static_cast<int64_t>(AbsoluteDifference));
282  }
283 }
284 
286  const ExpressionValue &RightOperand) {
287  // -A * -B == A * B
288  if (LeftOperand.isNegative() && RightOperand.isNegative())
289  return LeftOperand.getAbsolute() * RightOperand.getAbsolute();
290 
291  // A * -B == -B * A
292  if (RightOperand.isNegative())
293  return RightOperand * LeftOperand;
294 
295  assert(!RightOperand.isNegative() && "Unexpected negative operand!");
296 
297  // Result will be negative and can underflow.
298  if (LeftOperand.isNegative()) {
299  auto Result = LeftOperand.getAbsolute() * RightOperand.getAbsolute();
300  if (!Result)
301  return Result;
302 
303  return ExpressionValue(0) - *Result;
304  }
305 
306  // Result will be positive and can overflow.
307  uint64_t LeftValue = cantFail(LeftOperand.getUnsignedValue());
308  uint64_t RightValue = cantFail(RightOperand.getUnsignedValue());
309  Optional<uint64_t> Result =
310  checkedMulUnsigned<uint64_t>(LeftValue, RightValue);
311  if (!Result)
312  return make_error<OverflowError>();
313 
314  return ExpressionValue(*Result);
315 }
316 
318  const ExpressionValue &RightOperand) {
319  // -A / -B == A / B
320  if (LeftOperand.isNegative() && RightOperand.isNegative())
321  return LeftOperand.getAbsolute() / RightOperand.getAbsolute();
322 
323  // Check for divide by zero.
324  if (RightOperand == ExpressionValue(0))
325  return make_error<OverflowError>();
326 
327  // Result will be negative and can underflow.
328  if (LeftOperand.isNegative() || RightOperand.isNegative())
329  return ExpressionValue(0) -
330  cantFail(LeftOperand.getAbsolute() / RightOperand.getAbsolute());
331 
332  uint64_t LeftValue = cantFail(LeftOperand.getUnsignedValue());
333  uint64_t RightValue = cantFail(RightOperand.getUnsignedValue());
334  return ExpressionValue(LeftValue / RightValue);
335 }
336 
338  const ExpressionValue &RightOperand) {
339  if (LeftOperand.isNegative() && RightOperand.isNegative()) {
340  int64_t LeftValue = cantFail(LeftOperand.getSignedValue());
341  int64_t RightValue = cantFail(RightOperand.getSignedValue());
342  return ExpressionValue(std::max(LeftValue, RightValue));
343  }
344 
345  if (!LeftOperand.isNegative() && !RightOperand.isNegative()) {
346  uint64_t LeftValue = cantFail(LeftOperand.getUnsignedValue());
347  uint64_t RightValue = cantFail(RightOperand.getUnsignedValue());
348  return ExpressionValue(std::max(LeftValue, RightValue));
349  }
350 
351  if (LeftOperand.isNegative())
352  return RightOperand;
353 
354  return LeftOperand;
355 }
356 
358  const ExpressionValue &RightOperand) {
359  if (cantFail(max(LeftOperand, RightOperand)) == LeftOperand)
360  return RightOperand;
361 
362  return LeftOperand;
363 }
364 
367  if (Value)
368  return *Value;
369 
370  return make_error<UndefVarError>(getExpressionStr());
371 }
372 
374  Expected<ExpressionValue> LeftOp = LeftOperand->eval();
375  Expected<ExpressionValue> RightOp = RightOperand->eval();
376 
377  // Bubble up any error (e.g. undefined variables) in the recursive
378  // evaluation.
379  if (!LeftOp || !RightOp) {
380  Error Err = Error::success();
381  if (!LeftOp)
382  Err = joinErrors(std::move(Err), LeftOp.takeError());
383  if (!RightOp)
384  Err = joinErrors(std::move(Err), RightOp.takeError());
385  return std::move(Err);
386  }
387 
388  return EvalBinop(*LeftOp, *RightOp);
389 }
390 
393  Expected<ExpressionFormat> LeftFormat = LeftOperand->getImplicitFormat(SM);
394  Expected<ExpressionFormat> RightFormat = RightOperand->getImplicitFormat(SM);
395  if (!LeftFormat || !RightFormat) {
396  Error Err = Error::success();
397  if (!LeftFormat)
398  Err = joinErrors(std::move(Err), LeftFormat.takeError());
399  if (!RightFormat)
400  Err = joinErrors(std::move(Err), RightFormat.takeError());
401  return std::move(Err);
402  }
403 
404  if (*LeftFormat != ExpressionFormat::Kind::NoFormat &&
405  *RightFormat != ExpressionFormat::Kind::NoFormat &&
406  *LeftFormat != *RightFormat)
407  return ErrorDiagnostic::get(
408  SM, getExpressionStr(),
409  "implicit format conflict between '" + LeftOperand->getExpressionStr() +
410  "' (" + LeftFormat->toString() + ") and '" +
411  RightOperand->getExpressionStr() + "' (" + RightFormat->toString() +
412  "), need an explicit format specifier");
413 
414  return *LeftFormat != ExpressionFormat::Kind::NoFormat ? *LeftFormat
415  : *RightFormat;
416 }
417 
419  assert(ExpressionPointer->getAST() != nullptr &&
420  "Substituting empty expression");
421  Expected<ExpressionValue> EvaluatedValue =
422  ExpressionPointer->getAST()->eval();
423  if (!EvaluatedValue)
424  return EvaluatedValue.takeError();
425  ExpressionFormat Format = ExpressionPointer->getFormat();
426  return Format.getMatchingString(*EvaluatedValue);
427 }
428 
430  // Look up the value and escape it so that we can put it into the regex.
432  if (!VarVal)
433  return VarVal.takeError();
434  return Regex::escape(*VarVal);
435 }
436 
437 bool Pattern::isValidVarNameStart(char C) { return C == '_' || isAlpha(C); }
438 
441  if (Str.empty())
442  return ErrorDiagnostic::get(SM, Str, "empty variable name");
443 
444  size_t I = 0;
445  bool IsPseudo = Str[0] == '@';
446 
447  // Global vars start with '$'.
448  if (Str[0] == '$' || IsPseudo)
449  ++I;
450 
451  if (!isValidVarNameStart(Str[I++]))
452  return ErrorDiagnostic::get(SM, Str, "invalid variable name");
453 
454  for (size_t E = Str.size(); I != E; ++I)
455  // Variable names are composed of alphanumeric characters and underscores.
456  if (Str[I] != '_' && !isAlnum(Str[I]))
457  break;
458 
459  StringRef Name = Str.take_front(I);
460  Str = Str.substr(I);
461  return VariableProperties {Name, IsPseudo};
462 }
463 
464 // StringRef holding all characters considered as horizontal whitespaces by
465 // FileCheck input canonicalization.
466 constexpr StringLiteral SpaceChars = " \t";
467 
468 // Parsing helper function that strips the first character in S and returns it.
469 static char popFront(StringRef &S) {
470  char C = S.front();
471  S = S.drop_front();
472  return C;
473 }
474 
475 char OverflowError::ID = 0;
476 char UndefVarError::ID = 0;
477 char ErrorDiagnostic::ID = 0;
478 char NotFoundError::ID = 0;
479 char ErrorReported::ID = 0;
480 
481 Expected<NumericVariable *> Pattern::parseNumericVariableDefinition(
483  Optional<size_t> LineNumber, ExpressionFormat ImplicitFormat,
484  const SourceMgr &SM) {
485  Expected<VariableProperties> ParseVarResult = parseVariable(Expr, SM);
486  if (!ParseVarResult)
487  return ParseVarResult.takeError();
488  StringRef Name = ParseVarResult->Name;
489 
490  if (ParseVarResult->IsPseudo)
491  return ErrorDiagnostic::get(
492  SM, Name, "definition of pseudo numeric variable unsupported");
493 
494  // Detect collisions between string and numeric variables when the latter
495  // is created later than the former.
496  if (Context->DefinedVariableTable.find(Name) !=
497  Context->DefinedVariableTable.end())
498  return ErrorDiagnostic::get(
499  SM, Name, "string variable with name '" + Name + "' already exists");
500 
501  Expr = Expr.ltrim(SpaceChars);
502  if (!Expr.empty())
503  return ErrorDiagnostic::get(
504  SM, Expr, "unexpected characters after numeric variable name");
505 
506  NumericVariable *DefinedNumericVariable;
507  auto VarTableIter = Context->GlobalNumericVariableTable.find(Name);
508  if (VarTableIter != Context->GlobalNumericVariableTable.end()) {
509  DefinedNumericVariable = VarTableIter->second;
510  if (DefinedNumericVariable->getImplicitFormat() != ImplicitFormat)
511  return ErrorDiagnostic::get(
512  SM, Expr, "format different from previous variable definition");
513  } else
514  DefinedNumericVariable =
515  Context->makeNumericVariable(Name, ImplicitFormat, LineNumber);
516 
517  return DefinedNumericVariable;
518 }
519 
520 Expected<std::unique_ptr<NumericVariableUse>> Pattern::parseNumericVariableUse(
521  StringRef Name, bool IsPseudo, Optional<size_t> LineNumber,
523  if (IsPseudo && !Name.equals("@LINE"))
524  return ErrorDiagnostic::get(
525  SM, Name, "invalid pseudo numeric variable '" + Name + "'");
526 
527  // Numeric variable definitions and uses are parsed in the order in which
528  // they appear in the CHECK patterns. For each definition, the pointer to the
529  // class instance of the corresponding numeric variable definition is stored
530  // in GlobalNumericVariableTable in parsePattern. Therefore, if the pointer
531  // we get below is null, it means no such variable was defined before. When
532  // that happens, we create a dummy variable so that parsing can continue. All
533  // uses of undefined variables, whether string or numeric, are then diagnosed
534  // in printNoMatch() after failing to match.
535  auto VarTableIter = Context->GlobalNumericVariableTable.find(Name);
537  if (VarTableIter != Context->GlobalNumericVariableTable.end())
538  NumericVariable = VarTableIter->second;
539  else {
540  NumericVariable = Context->makeNumericVariable(
542  Context->GlobalNumericVariableTable[Name] = NumericVariable;
543  }
544 
546  if (DefLineNumber && LineNumber && *DefLineNumber == *LineNumber)
547  return ErrorDiagnostic::get(
548  SM, Name,
549  "numeric variable '" + Name +
550  "' defined earlier in the same CHECK directive");
551 
552  return std::make_unique<NumericVariableUse>(Name, NumericVariable);
553 }
554 
555 Expected<std::unique_ptr<ExpressionAST>> Pattern::parseNumericOperand(
556  StringRef &Expr, AllowedOperand AO, bool MaybeInvalidConstraint,
558  const SourceMgr &SM) {
559  if (Expr.startswith("(")) {
560  if (AO != AllowedOperand::Any)
561  return ErrorDiagnostic::get(
562  SM, Expr, "parenthesized expression not permitted here");
563  return parseParenExpr(Expr, LineNumber, Context, SM);
564  }
565 
566  if (AO == AllowedOperand::LineVar || AO == AllowedOperand::Any) {
567  // Try to parse as a numeric variable use.
569  parseVariable(Expr, SM);
570  if (ParseVarResult) {
571  // Try to parse a function call.
572  if (Expr.ltrim(SpaceChars).startswith("(")) {
573  if (AO != AllowedOperand::Any)
574  return ErrorDiagnostic::get(SM, ParseVarResult->Name,
575  "unexpected function call");
576 
577  return parseCallExpr(Expr, ParseVarResult->Name, LineNumber, Context,
578  SM);
579  }
580 
581  return parseNumericVariableUse(ParseVarResult->Name,
582  ParseVarResult->IsPseudo, LineNumber,
583  Context, SM);
584  }
585 
586  if (AO == AllowedOperand::LineVar)
587  return ParseVarResult.takeError();
588  // Ignore the error and retry parsing as a literal.
589  consumeError(ParseVarResult.takeError());
590  }
591 
592  // Otherwise, parse it as a literal.
593  int64_t SignedLiteralValue;
594  uint64_t UnsignedLiteralValue;
595  StringRef SaveExpr = Expr;
596  // Accept both signed and unsigned literal, default to signed literal.
597  if (!Expr.consumeInteger((AO == AllowedOperand::LegacyLiteral) ? 10 : 0,
598  UnsignedLiteralValue))
599  return std::make_unique<ExpressionLiteral>(SaveExpr.drop_back(Expr.size()),
600  UnsignedLiteralValue);
601  Expr = SaveExpr;
602  if (AO == AllowedOperand::Any && !Expr.consumeInteger(0, SignedLiteralValue))
603  return std::make_unique<ExpressionLiteral>(SaveExpr.drop_back(Expr.size()),
604  SignedLiteralValue);
605 
606  return ErrorDiagnostic::get(
607  SM, Expr,
608  Twine("invalid ") +
609  (MaybeInvalidConstraint ? "matching constraint or " : "") +
610  "operand format");
611 }
612 
614 Pattern::parseParenExpr(StringRef &Expr, Optional<size_t> LineNumber,
616  Expr = Expr.ltrim(SpaceChars);
617  assert(Expr.startswith("("));
618 
619  // Parse right operand.
620  Expr.consume_front("(");
621  Expr = Expr.ltrim(SpaceChars);
622  if (Expr.empty())
623  return ErrorDiagnostic::get(SM, Expr, "missing operand in expression");
624 
625  // Note: parseNumericOperand handles nested opening parentheses.
626  Expected<std::unique_ptr<ExpressionAST>> SubExprResult = parseNumericOperand(
627  Expr, AllowedOperand::Any, /*MaybeInvalidConstraint=*/false, LineNumber,
628  Context, SM);
629  Expr = Expr.ltrim(SpaceChars);
630  while (SubExprResult && !Expr.empty() && !Expr.startswith(")")) {
631  StringRef OrigExpr = Expr;
632  SubExprResult = parseBinop(OrigExpr, Expr, std::move(*SubExprResult), false,
633  LineNumber, Context, SM);
634  Expr = Expr.ltrim(SpaceChars);
635  }
636  if (!SubExprResult)
637  return SubExprResult;
638 
639  if (!Expr.consume_front(")")) {
640  return ErrorDiagnostic::get(SM, Expr,
641  "missing ')' at end of nested expression");
642  }
643  return SubExprResult;
644 }
645 
647 Pattern::parseBinop(StringRef Expr, StringRef &RemainingExpr,
648  std::unique_ptr<ExpressionAST> LeftOp,
649  bool IsLegacyLineExpr, Optional<size_t> LineNumber,
651  RemainingExpr = RemainingExpr.ltrim(SpaceChars);
652  if (RemainingExpr.empty())
653  return std::move(LeftOp);
654 
655  // Check if this is a supported operation and select a function to perform
656  // it.
657  SMLoc OpLoc = SMLoc::getFromPointer(RemainingExpr.data());
658  char Operator = popFront(RemainingExpr);
659  binop_eval_t EvalBinop;
660  switch (Operator) {
661  case '+':
662  EvalBinop = operator+;
663  break;
664  case '-':
665  EvalBinop = operator-;
666  break;
667  default:
668  return ErrorDiagnostic::get(
669  SM, OpLoc, Twine("unsupported operation '") + Twine(Operator) + "'");
670  }
671 
672  // Parse right operand.
673  RemainingExpr = RemainingExpr.ltrim(SpaceChars);
674  if (RemainingExpr.empty())
675  return ErrorDiagnostic::get(SM, RemainingExpr,
676  "missing operand in expression");
677  // The second operand in a legacy @LINE expression is always a literal.
678  AllowedOperand AO =
679  IsLegacyLineExpr ? AllowedOperand::LegacyLiteral : AllowedOperand::Any;
681  parseNumericOperand(RemainingExpr, AO, /*MaybeInvalidConstraint=*/false,
682  LineNumber, Context, SM);
683  if (!RightOpResult)
684  return RightOpResult;
685 
686  Expr = Expr.drop_back(RemainingExpr.size());
687  return std::make_unique<BinaryOperation>(Expr, EvalBinop, std::move(LeftOp),
688  std::move(*RightOpResult));
689 }
690 
692 Pattern::parseCallExpr(StringRef &Expr, StringRef FuncName,
693  Optional<size_t> LineNumber,
695  Expr = Expr.ltrim(SpaceChars);
696  assert(Expr.startswith("("));
697 
698  auto OptFunc = StringSwitch<Optional<binop_eval_t>>(FuncName)
699  .Case("add", operator+)
700  .Case("div", operator/)
701  .Case("max", max)
702  .Case("min", min)
703  .Case("mul", operator*)
704  .Case("sub", operator-)
705  .Default(None);
706 
707  if (!OptFunc)
708  return ErrorDiagnostic::get(
709  SM, FuncName, Twine("call to undefined function '") + FuncName + "'");
710 
711  Expr.consume_front("(");
712  Expr = Expr.ltrim(SpaceChars);
713 
714  // Parse call arguments, which are comma separated.
716  while (!Expr.empty() && !Expr.startswith(")")) {
717  if (Expr.startswith(","))
718  return ErrorDiagnostic::get(SM, Expr, "missing argument");
719 
720  // Parse the argument, which is an arbitary expression.
721  StringRef OuterBinOpExpr = Expr;
722  Expected<std::unique_ptr<ExpressionAST>> Arg = parseNumericOperand(
723  Expr, AllowedOperand::Any, /*MaybeInvalidConstraint=*/false, LineNumber,
724  Context, SM);
725  while (Arg && !Expr.empty()) {
726  Expr = Expr.ltrim(SpaceChars);
727  // Have we reached an argument terminator?
728  if (Expr.startswith(",") || Expr.startswith(")"))
729  break;
730 
731  // Arg = Arg <op> <expr>
732  Arg = parseBinop(OuterBinOpExpr, Expr, std::move(*Arg), false, LineNumber,
733  Context, SM);
734  }
735 
736  // Prefer an expression error over a generic invalid argument message.
737  if (!Arg)
738  return Arg.takeError();
739  Args.push_back(std::move(*Arg));
740 
741  // Have we parsed all available arguments?
742  Expr = Expr.ltrim(SpaceChars);
743  if (!Expr.consume_front(","))
744  break;
745 
746  Expr = Expr.ltrim(SpaceChars);
747  if (Expr.startswith(")"))
748  return ErrorDiagnostic::get(SM, Expr, "missing argument");
749  }
750 
751  if (!Expr.consume_front(")"))
752  return ErrorDiagnostic::get(SM, Expr,
753  "missing ')' at end of call expression");
754 
755  const unsigned NumArgs = Args.size();
756  if (NumArgs == 2)
757  return std::make_unique<BinaryOperation>(Expr, *OptFunc, std::move(Args[0]),
758  std::move(Args[1]));
759 
760  // TODO: Support more than binop_eval_t.
761  return ErrorDiagnostic::get(SM, FuncName,
762  Twine("function '") + FuncName +
763  Twine("' takes 2 arguments but ") +
764  Twine(NumArgs) + " given");
765 }
766 
768  StringRef Expr, Optional<NumericVariable *> &DefinedNumericVariable,
769  bool IsLegacyLineExpr, Optional<size_t> LineNumber,
771  std::unique_ptr<ExpressionAST> ExpressionASTPointer = nullptr;
772  StringRef DefExpr = StringRef();
773  DefinedNumericVariable = None;
774  ExpressionFormat ExplicitFormat = ExpressionFormat();
775  unsigned Precision = 0;
776 
777  // Parse format specifier (NOTE: ',' is also an argument seperator).
778  size_t FormatSpecEnd = Expr.find(',');
779  size_t FunctionStart = Expr.find('(');
780  if (FormatSpecEnd != StringRef::npos && FormatSpecEnd < FunctionStart) {
781  StringRef FormatExpr = Expr.take_front(FormatSpecEnd);
782  Expr = Expr.drop_front(FormatSpecEnd + 1);
783  FormatExpr = FormatExpr.trim(SpaceChars);
784  if (!FormatExpr.consume_front("%"))
785  return ErrorDiagnostic::get(
786  SM, FormatExpr,
787  "invalid matching format specification in expression");
788 
789  // Parse alternate form flag.
790  SMLoc AlternateFormFlagLoc = SMLoc::getFromPointer(FormatExpr.data());
791  bool AlternateForm = FormatExpr.consume_front("#");
792 
793  // Parse precision.
794  if (FormatExpr.consume_front(".")) {
795  if (FormatExpr.consumeInteger(10, Precision))
796  return ErrorDiagnostic::get(SM, FormatExpr,
797  "invalid precision in format specifier");
798  }
799 
800  if (!FormatExpr.empty()) {
801  // Check for unknown matching format specifier and set matching format in
802  // class instance representing this expression.
803  SMLoc FmtLoc = SMLoc::getFromPointer(FormatExpr.data());
804  switch (popFront(FormatExpr)) {
805  case 'u':
806  ExplicitFormat =
808  break;
809  case 'd':
810  ExplicitFormat =
812  break;
813  case 'x':
815  Precision, AlternateForm);
816  break;
817  case 'X':
819  Precision, AlternateForm);
820  break;
821  default:
822  return ErrorDiagnostic::get(SM, FmtLoc,
823  "invalid format specifier in expression");
824  }
825  }
826 
827  if (AlternateForm && ExplicitFormat != ExpressionFormat::Kind::HexLower &&
828  ExplicitFormat != ExpressionFormat::Kind::HexUpper)
829  return ErrorDiagnostic::get(
830  SM, AlternateFormFlagLoc,
831  "alternate form only supported for hex values");
832 
833  FormatExpr = FormatExpr.ltrim(SpaceChars);
834  if (!FormatExpr.empty())
835  return ErrorDiagnostic::get(
836  SM, FormatExpr,
837  "invalid matching format specification in expression");
838  }
839 
840  // Save variable definition expression if any.
841  size_t DefEnd = Expr.find(':');
842  if (DefEnd != StringRef::npos) {
843  DefExpr = Expr.substr(0, DefEnd);
844  Expr = Expr.substr(DefEnd + 1);
845  }
846 
847  // Parse matching constraint.
848  Expr = Expr.ltrim(SpaceChars);
849  bool HasParsedValidConstraint = false;
850  if (Expr.consume_front("=="))
851  HasParsedValidConstraint = true;
852 
853  // Parse the expression itself.
854  Expr = Expr.ltrim(SpaceChars);
855  if (Expr.empty()) {
856  if (HasParsedValidConstraint)
857  return ErrorDiagnostic::get(
858  SM, Expr, "empty numeric expression should not have a constraint");
859  } else {
860  Expr = Expr.rtrim(SpaceChars);
861  StringRef OuterBinOpExpr = Expr;
862  // The first operand in a legacy @LINE expression is always the @LINE
863  // pseudo variable.
864  AllowedOperand AO =
865  IsLegacyLineExpr ? AllowedOperand::LineVar : AllowedOperand::Any;
866  Expected<std::unique_ptr<ExpressionAST>> ParseResult = parseNumericOperand(
867  Expr, AO, !HasParsedValidConstraint, LineNumber, Context, SM);
868  while (ParseResult && !Expr.empty()) {
869  ParseResult = parseBinop(OuterBinOpExpr, Expr, std::move(*ParseResult),
870  IsLegacyLineExpr, LineNumber, Context, SM);
871  // Legacy @LINE expressions only allow 2 operands.
872  if (ParseResult && IsLegacyLineExpr && !Expr.empty())
873  return ErrorDiagnostic::get(
874  SM, Expr,
875  "unexpected characters at end of expression '" + Expr + "'");
876  }
877  if (!ParseResult)
878  return ParseResult.takeError();
879  ExpressionASTPointer = std::move(*ParseResult);
880  }
881 
882  // Select format of the expression, i.e. (i) its explicit format, if any,
883  // otherwise (ii) its implicit format, if any, otherwise (iii) the default
884  // format (unsigned). Error out in case of conflicting implicit format
885  // without explicit format.
886  ExpressionFormat Format;
887  if (ExplicitFormat)
888  Format = ExplicitFormat;
889  else if (ExpressionASTPointer) {
890  Expected<ExpressionFormat> ImplicitFormat =
891  ExpressionASTPointer->getImplicitFormat(SM);
892  if (!ImplicitFormat)
893  return ImplicitFormat.takeError();
894  Format = *ImplicitFormat;
895  }
896  if (!Format)
898 
899  std::unique_ptr<Expression> ExpressionPointer =
900  std::make_unique<Expression>(std::move(ExpressionASTPointer), Format);
901 
902  // Parse the numeric variable definition.
903  if (DefEnd != StringRef::npos) {
904  DefExpr = DefExpr.ltrim(SpaceChars);
905  Expected<NumericVariable *> ParseResult = parseNumericVariableDefinition(
906  DefExpr, Context, LineNumber, ExpressionPointer->getFormat(), SM);
907 
908  if (!ParseResult)
909  return ParseResult.takeError();
910  DefinedNumericVariable = *ParseResult;
911  }
912 
913  return std::move(ExpressionPointer);
914 }
915 
917  SourceMgr &SM, const FileCheckRequest &Req) {
918  bool MatchFullLinesHere = Req.MatchFullLines && CheckTy != Check::CheckNot;
919  IgnoreCase = Req.IgnoreCase;
920 
921  PatternLoc = SMLoc::getFromPointer(PatternStr.data());
922 
923  if (!(Req.NoCanonicalizeWhiteSpace && Req.MatchFullLines))
924  // Ignore trailing whitespace.
925  while (!PatternStr.empty() &&
926  (PatternStr.back() == ' ' || PatternStr.back() == '\t'))
927  PatternStr = PatternStr.substr(0, PatternStr.size() - 1);
928 
929  // Check that there is something on the line.
930  if (PatternStr.empty() && CheckTy != Check::CheckEmpty) {
931  SM.PrintMessage(PatternLoc, SourceMgr::DK_Error,
932  "found empty check string with prefix '" + Prefix + ":'");
933  return true;
934  }
935 
936  if (!PatternStr.empty() && CheckTy == Check::CheckEmpty) {
937  SM.PrintMessage(
938  PatternLoc, SourceMgr::DK_Error,
939  "found non-empty check string for empty check with prefix '" + Prefix +
940  ":'");
941  return true;
942  }
943 
944  if (CheckTy == Check::CheckEmpty) {
945  RegExStr = "(\n$)";
946  return false;
947  }
948 
949  // If literal check, set fixed string.
950  if (CheckTy.isLiteralMatch()) {
951  FixedStr = PatternStr;
952  return false;
953  }
954 
955  // Check to see if this is a fixed string, or if it has regex pieces.
956  if (!MatchFullLinesHere &&
957  (PatternStr.size() < 2 ||
958  (!PatternStr.contains("{{") && !PatternStr.contains("[[")))) {
959  FixedStr = PatternStr;
960  return false;
961  }
962 
963  if (MatchFullLinesHere) {
964  RegExStr += '^';
965  if (!Req.NoCanonicalizeWhiteSpace)
966  RegExStr += " *";
967  }
968 
969  // Paren value #0 is for the fully matched string. Any new parenthesized
970  // values add from there.
971  unsigned CurParen = 1;
972 
973  // Otherwise, there is at least one regex piece. Build up the regex pattern
974  // by escaping scary characters in fixed strings, building up one big regex.
975  while (!PatternStr.empty()) {
976  // RegEx matches.
977  if (PatternStr.startswith("{{")) {
978  // This is the start of a regex match. Scan for the }}.
979  size_t End = PatternStr.find("}}");
980  if (End == StringRef::npos) {
981  SM.PrintMessage(SMLoc::getFromPointer(PatternStr.data()),
983  "found start of regex string with no end '}}'");
984  return true;
985  }
986 
987  // Enclose {{}} patterns in parens just like [[]] even though we're not
988  // capturing the result for any purpose. This is required in case the
989  // expression contains an alternation like: CHECK: abc{{x|z}}def. We
990  // want this to turn into: "abc(x|z)def" not "abcx|zdef".
991  RegExStr += '(';
992  ++CurParen;
993 
994  if (AddRegExToRegEx(PatternStr.substr(2, End - 2), CurParen, SM))
995  return true;
996  RegExStr += ')';
997 
998  PatternStr = PatternStr.substr(End + 2);
999  continue;
1000  }
1001 
1002  // String and numeric substitution blocks. Pattern substitution blocks come
1003  // in two forms: [[foo:.*]] and [[foo]]. The former matches .* (or some
1004  // other regex) and assigns it to the string variable 'foo'. The latter
1005  // substitutes foo's value. Numeric substitution blocks recognize the same
1006  // form as string ones, but start with a '#' sign after the double
1007  // brackets. They also accept a combined form which sets a numeric variable
1008  // to the evaluation of an expression. Both string and numeric variable
1009  // names must satisfy the regular expression "[a-zA-Z_][0-9a-zA-Z_]*" to be
1010  // valid, as this helps catch some common errors.
1011  if (PatternStr.startswith("[[")) {
1012  StringRef UnparsedPatternStr = PatternStr.substr(2);
1013  // Find the closing bracket pair ending the match. End is going to be an
1014  // offset relative to the beginning of the match string.
1015  size_t End = FindRegexVarEnd(UnparsedPatternStr, SM);
1016  StringRef MatchStr = UnparsedPatternStr.substr(0, End);
1017  bool IsNumBlock = MatchStr.consume_front("#");
1018 
1019  if (End == StringRef::npos) {
1020  SM.PrintMessage(SMLoc::getFromPointer(PatternStr.data()),
1022  "Invalid substitution block, no ]] found");
1023  return true;
1024  }
1025  // Strip the substitution block we are parsing. End points to the start
1026  // of the "]]" closing the expression so account for it in computing the
1027  // index of the first unparsed character.
1028  PatternStr = UnparsedPatternStr.substr(End + 2);
1029 
1030  bool IsDefinition = false;
1031  bool SubstNeeded = false;
1032  // Whether the substitution block is a legacy use of @LINE with string
1033  // substitution block syntax.
1034  bool IsLegacyLineExpr = false;
1035  StringRef DefName;
1036  StringRef SubstStr;
1037  StringRef MatchRegexp;
1038  std::string WildcardRegexp;
1039  size_t SubstInsertIdx = RegExStr.size();
1040 
1041  // Parse string variable or legacy @LINE expression.
1042  if (!IsNumBlock) {
1043  size_t VarEndIdx = MatchStr.find(':');
1044  size_t SpacePos = MatchStr.substr(0, VarEndIdx).find_first_of(" \t");
1045  if (SpacePos != StringRef::npos) {
1046  SM.PrintMessage(SMLoc::getFromPointer(MatchStr.data() + SpacePos),
1047  SourceMgr::DK_Error, "unexpected whitespace");
1048  return true;
1049  }
1050 
1051  // Get the name (e.g. "foo") and verify it is well formed.
1052  StringRef OrigMatchStr = MatchStr;
1053  Expected<Pattern::VariableProperties> ParseVarResult =
1054  parseVariable(MatchStr, SM);
1055  if (!ParseVarResult) {
1056  logAllUnhandledErrors(ParseVarResult.takeError(), errs());
1057  return true;
1058  }
1059  StringRef Name = ParseVarResult->Name;
1060  bool IsPseudo = ParseVarResult->IsPseudo;
1061 
1062  IsDefinition = (VarEndIdx != StringRef::npos);
1063  SubstNeeded = !IsDefinition;
1064  if (IsDefinition) {
1065  if ((IsPseudo || !MatchStr.consume_front(":"))) {
1068  "invalid name in string variable definition");
1069  return true;
1070  }
1071 
1072  // Detect collisions between string and numeric variables when the
1073  // former is created later than the latter.
1074  if (Context->GlobalNumericVariableTable.find(Name) !=
1075  Context->GlobalNumericVariableTable.end()) {
1076  SM.PrintMessage(
1078  "numeric variable with name '" + Name + "' already exists");
1079  return true;
1080  }
1081  DefName = Name;
1082  MatchRegexp = MatchStr;
1083  } else {
1084  if (IsPseudo) {
1085  MatchStr = OrigMatchStr;
1086  IsLegacyLineExpr = IsNumBlock = true;
1087  } else {
1088  if (!MatchStr.empty()) {
1091  "invalid name in string variable use");
1092  return true;
1093  }
1094  SubstStr = Name;
1095  }
1096  }
1097  }
1098 
1099  // Parse numeric substitution block.
1100  std::unique_ptr<Expression> ExpressionPointer;
1101  Optional<NumericVariable *> DefinedNumericVariable;
1102  if (IsNumBlock) {
1104  parseNumericSubstitutionBlock(MatchStr, DefinedNumericVariable,
1105  IsLegacyLineExpr, LineNumber, Context,
1106  SM);
1107  if (!ParseResult) {
1108  logAllUnhandledErrors(ParseResult.takeError(), errs());
1109  return true;
1110  }
1111  ExpressionPointer = std::move(*ParseResult);
1112  SubstNeeded = ExpressionPointer->getAST() != nullptr;
1113  if (DefinedNumericVariable) {
1114  IsDefinition = true;
1115  DefName = (*DefinedNumericVariable)->getName();
1116  }
1117  if (SubstNeeded)
1118  SubstStr = MatchStr;
1119  else {
1120  ExpressionFormat Format = ExpressionPointer->getFormat();
1121  WildcardRegexp = cantFail(Format.getWildcardRegex());
1122  MatchRegexp = WildcardRegexp;
1123  }
1124  }
1125 
1126  // Handle variable definition: [[<def>:(...)]] and [[#(...)<def>:(...)]].
1127  if (IsDefinition) {
1128  RegExStr += '(';
1129  ++SubstInsertIdx;
1130 
1131  if (IsNumBlock) {
1132  NumericVariableMatch NumericVariableDefinition = {
1133  *DefinedNumericVariable, CurParen};
1134  NumericVariableDefs[DefName] = NumericVariableDefinition;
1135  // This store is done here rather than in match() to allow
1136  // parseNumericVariableUse() to get the pointer to the class instance
1137  // of the right variable definition corresponding to a given numeric
1138  // variable use.
1139  Context->GlobalNumericVariableTable[DefName] =
1140  *DefinedNumericVariable;
1141  } else {
1142  VariableDefs[DefName] = CurParen;
1143  // Mark string variable as defined to detect collisions between
1144  // string and numeric variables in parseNumericVariableUse() and
1145  // defineCmdlineVariables() when the latter is created later than the
1146  // former. We cannot reuse GlobalVariableTable for this by populating
1147  // it with an empty string since we would then lose the ability to
1148  // detect the use of an undefined variable in match().
1149  Context->DefinedVariableTable[DefName] = true;
1150  }
1151 
1152  ++CurParen;
1153  }
1154 
1155  if (!MatchRegexp.empty() && AddRegExToRegEx(MatchRegexp, CurParen, SM))
1156  return true;
1157 
1158  if (IsDefinition)
1159  RegExStr += ')';
1160 
1161  // Handle substitutions: [[foo]] and [[#<foo expr>]].
1162  if (SubstNeeded) {
1163  // Handle substitution of string variables that were defined earlier on
1164  // the same line by emitting a backreference. Expressions do not
1165  // support substituting a numeric variable defined on the same line.
1166  if (!IsNumBlock && VariableDefs.find(SubstStr) != VariableDefs.end()) {
1167  unsigned CaptureParenGroup = VariableDefs[SubstStr];
1168  if (CaptureParenGroup < 1 || CaptureParenGroup > 9) {
1169  SM.PrintMessage(SMLoc::getFromPointer(SubstStr.data()),
1171  "Can't back-reference more than 9 variables");
1172  return true;
1173  }
1174  AddBackrefToRegEx(CaptureParenGroup);
1175  } else {
1176  // Handle substitution of string variables ([[<var>]]) defined in
1177  // previous CHECK patterns, and substitution of expressions.
1179  IsNumBlock
1180  ? Context->makeNumericSubstitution(
1181  SubstStr, std::move(ExpressionPointer), SubstInsertIdx)
1182  : Context->makeStringSubstitution(SubstStr, SubstInsertIdx);
1183  Substitutions.push_back(Substitution);
1184  }
1185  }
1186  }
1187 
1188  // Handle fixed string matches.
1189  // Find the end, which is the start of the next regex.
1190  size_t FixedMatchEnd = PatternStr.find("{{");
1191  FixedMatchEnd = std::min(FixedMatchEnd, PatternStr.find("[["));
1192  RegExStr += Regex::escape(PatternStr.substr(0, FixedMatchEnd));
1193  PatternStr = PatternStr.substr(FixedMatchEnd);
1194  }
1195 
1196  if (MatchFullLinesHere) {
1197  if (!Req.NoCanonicalizeWhiteSpace)
1198  RegExStr += " *";
1199  RegExStr += '$';
1200  }
1201 
1202  return false;
1203 }
1204 
1205 bool Pattern::AddRegExToRegEx(StringRef RS, unsigned &CurParen, SourceMgr &SM) {
1206  Regex R(RS);
1207  std::string Error;
1208  if (!R.isValid(Error)) {
1210  "invalid regex: " + Error);
1211  return true;
1212  }
1213 
1214  RegExStr += RS.str();
1215  CurParen += R.getNumMatches();
1216  return false;
1217 }
1218 
1219 void Pattern::AddBackrefToRegEx(unsigned BackrefNum) {
1220  assert(BackrefNum >= 1 && BackrefNum <= 9 && "Invalid backref number");
1221  std::string Backref = std::string("\\") + std::string(1, '0' + BackrefNum);
1222  RegExStr += Backref;
1223 }
1224 
1226  const SourceMgr &SM) const {
1227  // If this is the EOF pattern, match it immediately.
1228  if (CheckTy == Check::CheckEOF)
1229  return MatchResult(Buffer.size(), 0, Error::success());
1230 
1231  // If this is a fixed string pattern, just match it now.
1232  if (!FixedStr.empty()) {
1233  size_t Pos =
1234  IgnoreCase ? Buffer.find_insensitive(FixedStr) : Buffer.find(FixedStr);
1235  if (Pos == StringRef::npos)
1236  return make_error<NotFoundError>();
1237  return MatchResult(Pos, /*MatchLen=*/FixedStr.size(), Error::success());
1238  }
1239 
1240  // Regex match.
1241 
1242  // If there are substitutions, we need to create a temporary string with the
1243  // actual value.
1244  StringRef RegExToMatch = RegExStr;
1245  std::string TmpStr;
1246  if (!Substitutions.empty()) {
1247  TmpStr = RegExStr;
1248  if (LineNumber)
1249  Context->LineVariable->setValue(ExpressionValue(*LineNumber));
1250 
1251  size_t InsertOffset = 0;
1252  // Substitute all string variables and expressions whose values are only
1253  // now known. Use of string variables defined on the same line are handled
1254  // by back-references.
1255  Error Errs = Error::success();
1256  for (const auto &Substitution : Substitutions) {
1257  // Substitute and check for failure (e.g. use of undefined variable).
1259  if (!Value) {
1260  // Convert to an ErrorDiagnostic to get location information. This is
1261  // done here rather than printMatch/printNoMatch since now we know which
1262  // substitution block caused the overflow.
1263  Errs = joinErrors(std::move(Errs),
1264  handleErrors(
1265  Value.takeError(),
1266  [&](const OverflowError &E) {
1267  return ErrorDiagnostic::get(
1268  SM, Substitution->getFromString(),
1269  "unable to substitute variable or "
1270  "numeric expression: overflow error");
1271  },
1272  [&SM](const UndefVarError &E) {
1273  return ErrorDiagnostic::get(SM, E.getVarName(),
1274  E.message());
1275  }));
1276  continue;
1277  }
1278 
1279  // Plop it into the regex at the adjusted offset.
1280  TmpStr.insert(TmpStr.begin() + Substitution->getIndex() + InsertOffset,
1281  Value->begin(), Value->end());
1282  InsertOffset += Value->size();
1283  }
1284  if (Errs)
1285  return std::move(Errs);
1286 
1287  // Match the newly constructed regex.
1288  RegExToMatch = TmpStr;
1289  }
1290 
1291  SmallVector<StringRef, 4> MatchInfo;
1292  unsigned int Flags = Regex::Newline;
1293  if (IgnoreCase)
1294  Flags |= Regex::IgnoreCase;
1295  if (!Regex(RegExToMatch, Flags).match(Buffer, &MatchInfo))
1296  return make_error<NotFoundError>();
1297 
1298  // Successful regex match.
1299  assert(!MatchInfo.empty() && "Didn't get any match");
1300  StringRef FullMatch = MatchInfo[0];
1301 
1302  // If this defines any string variables, remember their values.
1303  for (const auto &VariableDef : VariableDefs) {
1304  assert(VariableDef.second < MatchInfo.size() && "Internal paren error");
1305  Context->GlobalVariableTable[VariableDef.first] =
1306  MatchInfo[VariableDef.second];
1307  }
1308 
1309  // Like CHECK-NEXT, CHECK-EMPTY's match range is considered to start after
1310  // the required preceding newline, which is consumed by the pattern in the
1311  // case of CHECK-EMPTY but not CHECK-NEXT.
1312  size_t MatchStartSkip = CheckTy == Check::CheckEmpty;
1313  Match TheMatch;
1314  TheMatch.Pos = FullMatch.data() - Buffer.data() + MatchStartSkip;
1315  TheMatch.Len = FullMatch.size() - MatchStartSkip;
1316 
1317  // If this defines any numeric variables, remember their values.
1318  for (const auto &NumericVariableDef : NumericVariableDefs) {
1319  const NumericVariableMatch &NumericVariableMatch =
1320  NumericVariableDef.getValue();
1321  unsigned CaptureParenGroup = NumericVariableMatch.CaptureParenGroup;
1322  assert(CaptureParenGroup < MatchInfo.size() && "Internal paren error");
1323  NumericVariable *DefinedNumericVariable =
1324  NumericVariableMatch.DefinedNumericVariable;
1325 
1326  StringRef MatchedValue = MatchInfo[CaptureParenGroup];
1327  ExpressionFormat Format = DefinedNumericVariable->getImplicitFormat();
1329  Format.valueFromStringRepr(MatchedValue, SM);
1330  if (!Value)
1331  return MatchResult(TheMatch, Value.takeError());
1332  DefinedNumericVariable->setValue(*Value, MatchedValue);
1333  }
1334 
1335  return MatchResult(TheMatch, Error::success());
1336 }
1337 
1338 unsigned Pattern::computeMatchDistance(StringRef Buffer) const {
1339  // Just compute the number of matching characters. For regular expressions, we
1340  // just compare against the regex itself and hope for the best.
1341  //
1342  // FIXME: One easy improvement here is have the regex lib generate a single
1343  // example regular expression which matches, and use that as the example
1344  // string.
1345  StringRef ExampleString(FixedStr);
1346  if (ExampleString.empty())
1347  ExampleString = RegExStr;
1348 
1349  // Only compare up to the first line in the buffer, or the string size.
1350  StringRef BufferPrefix = Buffer.substr(0, ExampleString.size());
1351  BufferPrefix = BufferPrefix.split('\n').first;
1352  return BufferPrefix.edit_distance(ExampleString);
1353 }
1354 
1355 void Pattern::printSubstitutions(const SourceMgr &SM, StringRef Buffer,
1356  SMRange Range,
1357  FileCheckDiag::MatchType MatchTy,
1358  std::vector<FileCheckDiag> *Diags) const {
1359  // Print what we know about substitutions.
1360  if (!Substitutions.empty()) {
1361  for (const auto &Substitution : Substitutions) {
1362  SmallString<256> Msg;
1363  raw_svector_ostream OS(Msg);
1364 
1365  Expected<std::string> MatchedValue = Substitution->getResult();
1366  // Substitution failures are handled in printNoMatch().
1367  if (!MatchedValue) {
1368  consumeError(MatchedValue.takeError());
1369  continue;
1370  }
1371 
1372  OS << "with \"";
1373  OS.write_escaped(Substitution->getFromString()) << "\" equal to \"";
1374  OS.write_escaped(*MatchedValue) << "\"";
1375 
1376  // We report only the start of the match/search range to suggest we are
1377  // reporting the substitutions as set at the start of the match/search.
1378  // Indicating a non-zero-length range might instead seem to imply that the
1379  // substitution matches or was captured from exactly that range.
1380  if (Diags)
1381  Diags->emplace_back(SM, CheckTy, getLoc(), MatchTy,
1382  SMRange(Range.Start, Range.Start), OS.str());
1383  else
1384  SM.PrintMessage(Range.Start, SourceMgr::DK_Note, OS.str());
1385  }
1386  }
1387 }
1388 
1389 void Pattern::printVariableDefs(const SourceMgr &SM,
1390  FileCheckDiag::MatchType MatchTy,
1391  std::vector<FileCheckDiag> *Diags) const {
1392  if (VariableDefs.empty() && NumericVariableDefs.empty())
1393  return;
1394  // Build list of variable captures.
1395  struct VarCapture {
1396  StringRef Name;
1397  SMRange Range;
1398  };
1399  SmallVector<VarCapture, 2> VarCaptures;
1400  for (const auto &VariableDef : VariableDefs) {
1401  VarCapture VC;
1402  VC.Name = VariableDef.first;
1403  StringRef Value = Context->GlobalVariableTable[VC.Name];
1404  SMLoc Start = SMLoc::getFromPointer(Value.data());
1405  SMLoc End = SMLoc::getFromPointer(Value.data() + Value.size());
1406  VC.Range = SMRange(Start, End);
1407  VarCaptures.push_back(VC);
1408  }
1409  for (const auto &VariableDef : NumericVariableDefs) {
1410  VarCapture VC;
1411  VC.Name = VariableDef.getKey();
1412  Optional<StringRef> StrValue =
1413  VariableDef.getValue().DefinedNumericVariable->getStringValue();
1414  if (!StrValue)
1415  continue;
1416  SMLoc Start = SMLoc::getFromPointer(StrValue->data());
1417  SMLoc End = SMLoc::getFromPointer(StrValue->data() + StrValue->size());
1418  VC.Range = SMRange(Start, End);
1419  VarCaptures.push_back(VC);
1420  }
1421  // Sort variable captures by the order in which they matched the input.
1422  // Ranges shouldn't be overlapping, so we can just compare the start.
1423  llvm::sort(VarCaptures, [](const VarCapture &A, const VarCapture &B) {
1424  assert(A.Range.Start != B.Range.Start &&
1425  "unexpected overlapping variable captures");
1426  return A.Range.Start.getPointer() < B.Range.Start.getPointer();
1427  });
1428  // Create notes for the sorted captures.
1429  for (const VarCapture &VC : VarCaptures) {
1430  SmallString<256> Msg;
1431  raw_svector_ostream OS(Msg);
1432  OS << "captured var \"" << VC.Name << "\"";
1433  if (Diags)
1434  Diags->emplace_back(SM, CheckTy, getLoc(), MatchTy, VC.Range, OS.str());
1435  else
1436  SM.PrintMessage(VC.Range.Start, SourceMgr::DK_Note, OS.str(), VC.Range);
1437  }
1438 }
1439 
1440 static SMRange ProcessMatchResult(FileCheckDiag::MatchType MatchTy,
1441  const SourceMgr &SM, SMLoc Loc,
1442  Check::FileCheckType CheckTy,
1443  StringRef Buffer, size_t Pos, size_t Len,
1444  std::vector<FileCheckDiag> *Diags,
1445  bool AdjustPrevDiags = false) {
1446  SMLoc Start = SMLoc::getFromPointer(Buffer.data() + Pos);
1447  SMLoc End = SMLoc::getFromPointer(Buffer.data() + Pos + Len);
1448  SMRange Range(Start, End);
1449  if (Diags) {
1450  if (AdjustPrevDiags) {
1451  SMLoc CheckLoc = Diags->rbegin()->CheckLoc;
1452  for (auto I = Diags->rbegin(), E = Diags->rend();
1453  I != E && I->CheckLoc == CheckLoc; ++I)
1454  I->MatchTy = MatchTy;
1455  } else
1456  Diags->emplace_back(SM, CheckTy, Loc, MatchTy, Range);
1457  }
1458  return Range;
1459 }
1460 
1461 void Pattern::printFuzzyMatch(const SourceMgr &SM, StringRef Buffer,
1462  std::vector<FileCheckDiag> *Diags) const {
1463  // Attempt to find the closest/best fuzzy match. Usually an error happens
1464  // because some string in the output didn't exactly match. In these cases, we
1465  // would like to show the user a best guess at what "should have" matched, to
1466  // save them having to actually check the input manually.
1467  size_t NumLinesForward = 0;
1468  size_t Best = StringRef::npos;
1469  double BestQuality = 0;
1470 
1471  // Use an arbitrary 4k limit on how far we will search.
1472  for (size_t i = 0, e = std::min(size_t(4096), Buffer.size()); i != e; ++i) {
1473  if (Buffer[i] == '\n')
1474  ++NumLinesForward;
1475 
1476  // Patterns have leading whitespace stripped, so skip whitespace when
1477  // looking for something which looks like a pattern.
1478  if (Buffer[i] == ' ' || Buffer[i] == '\t')
1479  continue;
1480 
1481  // Compute the "quality" of this match as an arbitrary combination of the
1482  // match distance and the number of lines skipped to get to this match.
1483  unsigned Distance = computeMatchDistance(Buffer.substr(i));
1484  double Quality = Distance + (NumLinesForward / 100.);
1485 
1486  if (Quality < BestQuality || Best == StringRef::npos) {
1487  Best = i;
1488  BestQuality = Quality;
1489  }
1490  }
1491 
1492  // Print the "possible intended match here" line if we found something
1493  // reasonable and not equal to what we showed in the "scanning from here"
1494  // line.
1495  if (Best && Best != StringRef::npos && BestQuality < 50) {
1496  SMRange MatchRange =
1497  ProcessMatchResult(FileCheckDiag::MatchFuzzy, SM, getLoc(),
1498  getCheckTy(), Buffer, Best, 0, Diags);
1499  SM.PrintMessage(MatchRange.Start, SourceMgr::DK_Note,
1500  "possible intended match here");
1501 
1502  // FIXME: If we wanted to be really friendly we would show why the match
1503  // failed, as it can be hard to spot simple one character differences.
1504  }
1505 }
1506 
1509  auto VarIter = GlobalVariableTable.find(VarName);
1510  if (VarIter == GlobalVariableTable.end())
1511  return make_error<UndefVarError>(VarName);
1512 
1513  return VarIter->second;
1514 }
1515 
1516 template <class... Types>
1517 NumericVariable *FileCheckPatternContext::makeNumericVariable(Types... args) {
1518  NumericVariables.push_back(std::make_unique<NumericVariable>(args...));
1519  return NumericVariables.back().get();
1520 }
1521 
1522 Substitution *
1523 FileCheckPatternContext::makeStringSubstitution(StringRef VarName,
1524  size_t InsertIdx) {
1525  Substitutions.push_back(
1526  std::make_unique<StringSubstitution>(this, VarName, InsertIdx));
1527  return Substitutions.back().get();
1528 }
1529 
1530 Substitution *FileCheckPatternContext::makeNumericSubstitution(
1531  StringRef ExpressionStr, std::unique_ptr<Expression> Expression,
1532  size_t InsertIdx) {
1533  Substitutions.push_back(std::make_unique<NumericSubstitution>(
1534  this, ExpressionStr, std::move(Expression), InsertIdx));
1535  return Substitutions.back().get();
1536 }
1537 
1538 size_t Pattern::FindRegexVarEnd(StringRef Str, SourceMgr &SM) {
1539  // Offset keeps track of the current offset within the input Str
1540  size_t Offset = 0;
1541  // [...] Nesting depth
1542  size_t BracketDepth = 0;
1543 
1544  while (!Str.empty()) {
1545  if (Str.startswith("]]") && BracketDepth == 0)
1546  return Offset;
1547  if (Str[0] == '\\') {
1548  // Backslash escapes the next char within regexes, so skip them both.
1549  Str = Str.substr(2);
1550  Offset += 2;
1551  } else {
1552  switch (Str[0]) {
1553  default:
1554  break;
1555  case '[':
1556  BracketDepth++;
1557  break;
1558  case ']':
1559  if (BracketDepth == 0) {
1560  SM.PrintMessage(SMLoc::getFromPointer(Str.data()),
1562  "missing closing \"]\" for regex variable");
1563  exit(1);
1564  }
1565  BracketDepth--;
1566  break;
1567  }
1568  Str = Str.substr(1);
1569  Offset++;
1570  }
1571  }
1572 
1573  return StringRef::npos;
1574 }
1575 
1577  SmallVectorImpl<char> &OutputBuffer) {
1578  OutputBuffer.reserve(MB.getBufferSize());
1579 
1580  for (const char *Ptr = MB.getBufferStart(), *End = MB.getBufferEnd();
1581  Ptr != End; ++Ptr) {
1582  // Eliminate trailing dosish \r.
1583  if (Ptr <= End - 2 && Ptr[0] == '\r' && Ptr[1] == '\n') {
1584  continue;
1585  }
1586 
1587  // If current char is not a horizontal whitespace or if horizontal
1588  // whitespace canonicalization is disabled, dump it to output as is.
1589  if (Req.NoCanonicalizeWhiteSpace || (*Ptr != ' ' && *Ptr != '\t')) {
1590  OutputBuffer.push_back(*Ptr);
1591  continue;
1592  }
1593 
1594  // Otherwise, add one space and advance over neighboring space.
1595  OutputBuffer.push_back(' ');
1596  while (Ptr + 1 != End && (Ptr[1] == ' ' || Ptr[1] == '\t'))
1597  ++Ptr;
1598  }
1599 
1600  // Add a null byte and then return all but that byte.
1601  OutputBuffer.push_back('\0');
1602  return StringRef(OutputBuffer.data(), OutputBuffer.size() - 1);
1603 }
1604 
1606  const Check::FileCheckType &CheckTy,
1607  SMLoc CheckLoc, MatchType MatchTy,
1608  SMRange InputRange, StringRef Note)
1609  : CheckTy(CheckTy), CheckLoc(CheckLoc), MatchTy(MatchTy), Note(Note) {
1610  auto Start = SM.getLineAndColumn(InputRange.Start);
1611  auto End = SM.getLineAndColumn(InputRange.End);
1612  InputStartLine = Start.first;
1613  InputStartCol = Start.second;
1614  InputEndLine = End.first;
1615  InputEndCol = End.second;
1616 }
1617 
1618 static bool IsPartOfWord(char c) {
1619  return (isAlnum(c) || c == '-' || c == '_');
1620 }
1621 
1623  assert(Count > 0 && "zero and negative counts are not supported");
1624  assert((C == 1 || Kind == CheckPlain) &&
1625  "count supported only for plain CHECK directives");
1626  Count = C;
1627  return *this;
1628 }
1629 
1631  if (Modifiers.none())
1632  return "";
1633  std::string Ret;
1634  raw_string_ostream OS(Ret);
1635  OS << '{';
1636  if (isLiteralMatch())
1637  OS << "LITERAL";
1638  OS << '}';
1639  return OS.str();
1640 }
1641 
1643  // Append directive modifiers.
1644  auto WithModifiers = [this, Prefix](StringRef Str) -> std::string {
1645  return (Prefix + Str + getModifiersDescription()).str();
1646  };
1647 
1648  switch (Kind) {
1649  case Check::CheckNone:
1650  return "invalid";
1651  case Check::CheckPlain:
1652  if (Count > 1)
1653  return WithModifiers("-COUNT");
1654  return WithModifiers("");
1655  case Check::CheckNext:
1656  return WithModifiers("-NEXT");
1657  case Check::CheckSame:
1658  return WithModifiers("-SAME");
1659  case Check::CheckNot:
1660  return WithModifiers("-NOT");
1661  case Check::CheckDAG:
1662  return WithModifiers("-DAG");
1663  case Check::CheckLabel:
1664  return WithModifiers("-LABEL");
1665  case Check::CheckEmpty:
1666  return WithModifiers("-EMPTY");
1667  case Check::CheckComment:
1668  return std::string(Prefix);
1669  case Check::CheckEOF:
1670  return "implicit EOF";
1671  case Check::CheckBadNot:
1672  return "bad NOT";
1673  case Check::CheckBadCount:
1674  return "bad COUNT";
1675  }
1676  llvm_unreachable("unknown FileCheckType");
1677 }
1678 
1679 static std::pair<Check::FileCheckType, StringRef>
1680 FindCheckType(const FileCheckRequest &Req, StringRef Buffer, StringRef Prefix) {
1681  if (Buffer.size() <= Prefix.size())
1682  return {Check::CheckNone, StringRef()};
1683 
1684  StringRef Rest = Buffer.drop_front(Prefix.size());
1685  // Check for comment.
1687  if (Rest.consume_front(":"))
1688  return {Check::CheckComment, Rest};
1689  // Ignore a comment prefix if it has a suffix like "-NOT".
1690  return {Check::CheckNone, StringRef()};
1691  }
1692 
1693  auto ConsumeModifiers = [&](Check::FileCheckType Ret)
1694  -> std::pair<Check::FileCheckType, StringRef> {
1695  if (Rest.consume_front(":"))
1696  return {Ret, Rest};
1697  if (!Rest.consume_front("{"))
1698  return {Check::CheckNone, StringRef()};
1699 
1700  // Parse the modifiers, speparated by commas.
1701  do {
1702  // Allow whitespace in modifiers list.
1703  Rest = Rest.ltrim();
1704  if (Rest.consume_front("LITERAL"))
1705  Ret.setLiteralMatch();
1706  else
1707  return {Check::CheckNone, Rest};
1708  // Allow whitespace in modifiers list.
1709  Rest = Rest.ltrim();
1710  } while (Rest.consume_front(","));
1711  if (!Rest.consume_front("}:"))
1712  return {Check::CheckNone, Rest};
1713  return {Ret, Rest};
1714  };
1715 
1716  // Verify that the prefix is followed by directive modifiers or a colon.
1717  if (Rest.consume_front(":"))
1718  return {Check::CheckPlain, Rest};
1719  if (Rest.front() == '{')
1720  return ConsumeModifiers(Check::CheckPlain);
1721 
1722  if (!Rest.consume_front("-"))
1723  return {Check::CheckNone, StringRef()};
1724 
1725  if (Rest.consume_front("COUNT-")) {
1726  int64_t Count;
1727  if (Rest.consumeInteger(10, Count))
1728  // Error happened in parsing integer.
1729  return {Check::CheckBadCount, Rest};
1730  if (Count <= 0 || Count > INT32_MAX)
1731  return {Check::CheckBadCount, Rest};
1732  if (Rest.front() != ':' && Rest.front() != '{')
1733  return {Check::CheckBadCount, Rest};
1734  return ConsumeModifiers(
1735  Check::FileCheckType(Check::CheckPlain).setCount(Count));
1736  }
1737 
1738  // You can't combine -NOT with another suffix.
1739  if (Rest.startswith("DAG-NOT:") || Rest.startswith("NOT-DAG:") ||
1740  Rest.startswith("NEXT-NOT:") || Rest.startswith("NOT-NEXT:") ||
1741  Rest.startswith("SAME-NOT:") || Rest.startswith("NOT-SAME:") ||
1742  Rest.startswith("EMPTY-NOT:") || Rest.startswith("NOT-EMPTY:"))
1743  return {Check::CheckBadNot, Rest};
1744 
1745  if (Rest.consume_front("NEXT"))
1746  return ConsumeModifiers(Check::CheckNext);
1747 
1748  if (Rest.consume_front("SAME"))
1749  return ConsumeModifiers(Check::CheckSame);
1750 
1751  if (Rest.consume_front("NOT"))
1752  return ConsumeModifiers(Check::CheckNot);
1753 
1754  if (Rest.consume_front("DAG"))
1755  return ConsumeModifiers(Check::CheckDAG);
1756 
1757  if (Rest.consume_front("LABEL"))
1758  return ConsumeModifiers(Check::CheckLabel);
1759 
1760  if (Rest.consume_front("EMPTY"))
1761  return ConsumeModifiers(Check::CheckEmpty);
1762 
1763  return {Check::CheckNone, Rest};
1764 }
1765 
1766 // From the given position, find the next character after the word.
1767 static size_t SkipWord(StringRef Str, size_t Loc) {
1768  while (Loc < Str.size() && IsPartOfWord(Str[Loc]))
1769  ++Loc;
1770  return Loc;
1771 }
1772 
1773 /// Searches the buffer for the first prefix in the prefix regular expression.
1774 ///
1775 /// This searches the buffer using the provided regular expression, however it
1776 /// enforces constraints beyond that:
1777 /// 1) The found prefix must not be a suffix of something that looks like
1778 /// a valid prefix.
1779 /// 2) The found prefix must be followed by a valid check type suffix using \c
1780 /// FindCheckType above.
1781 ///
1782 /// \returns a pair of StringRefs into the Buffer, which combines:
1783 /// - the first match of the regular expression to satisfy these two is
1784 /// returned,
1785 /// otherwise an empty StringRef is returned to indicate failure.
1786 /// - buffer rewound to the location right after parsed suffix, for parsing
1787 /// to continue from
1788 ///
1789 /// If this routine returns a valid prefix, it will also shrink \p Buffer to
1790 /// start at the beginning of the returned prefix, increment \p LineNumber for
1791 /// each new line consumed from \p Buffer, and set \p CheckTy to the type of
1792 /// check found by examining the suffix.
1793 ///
1794 /// If no valid prefix is found, the state of Buffer, LineNumber, and CheckTy
1795 /// is unspecified.
1796 static std::pair<StringRef, StringRef>
1797 FindFirstMatchingPrefix(const FileCheckRequest &Req, Regex &PrefixRE,
1798  StringRef &Buffer, unsigned &LineNumber,
1799  Check::FileCheckType &CheckTy) {
1800  SmallVector<StringRef, 2> Matches;
1801 
1802  while (!Buffer.empty()) {
1803  // Find the first (longest) match using the RE.
1804  if (!PrefixRE.match(Buffer, &Matches))
1805  // No match at all, bail.
1806  return {StringRef(), StringRef()};
1807 
1808  StringRef Prefix = Matches[0];
1809  Matches.clear();
1810 
1811  assert(Prefix.data() >= Buffer.data() &&
1812  Prefix.data() < Buffer.data() + Buffer.size() &&
1813  "Prefix doesn't start inside of buffer!");
1814  size_t Loc = Prefix.data() - Buffer.data();
1815  StringRef Skipped = Buffer.substr(0, Loc);
1816  Buffer = Buffer.drop_front(Loc);
1817  LineNumber += Skipped.count('\n');
1818 
1819  // Check that the matched prefix isn't a suffix of some other check-like
1820  // word.
1821  // FIXME: This is a very ad-hoc check. it would be better handled in some
1822  // other way. Among other things it seems hard to distinguish between
1823  // intentional and unintentional uses of this feature.
1824  if (Skipped.empty() || !IsPartOfWord(Skipped.back())) {
1825  // Now extract the type.
1826  StringRef AfterSuffix;
1827  std::tie(CheckTy, AfterSuffix) = FindCheckType(Req, Buffer, Prefix);
1828 
1829  // If we've found a valid check type for this prefix, we're done.
1830  if (CheckTy != Check::CheckNone)
1831  return {Prefix, AfterSuffix};
1832  }
1833 
1834  // If we didn't successfully find a prefix, we need to skip this invalid
1835  // prefix and continue scanning. We directly skip the prefix that was
1836  // matched and any additional parts of that check-like word.
1837  Buffer = Buffer.drop_front(SkipWord(Buffer, Prefix.size()));
1838  }
1839 
1840  // We ran out of buffer while skipping partial matches so give up.
1841  return {StringRef(), StringRef()};
1842 }
1843 
1845  assert(!LineVariable && "@LINE pseudo numeric variable already created");
1846  StringRef LineName = "@LINE";
1847  LineVariable = makeNumericVariable(
1849  GlobalNumericVariableTable[LineName] = LineVariable;
1850 }
1851 
1853  : Req(Req), PatternContext(std::make_unique<FileCheckPatternContext>()),
1854  CheckStrings(std::make_unique<std::vector<FileCheckString>>()) {}
1855 
1856 FileCheck::~FileCheck() = default;
1857 
1859  SourceMgr &SM, StringRef Buffer, Regex &PrefixRE,
1860  std::pair<unsigned, unsigned> *ImpPatBufferIDRange) {
1861  if (ImpPatBufferIDRange)
1862  ImpPatBufferIDRange->first = ImpPatBufferIDRange->second = 0;
1863 
1864  Error DefineError =
1865  PatternContext->defineCmdlineVariables(Req.GlobalDefines, SM);
1866  if (DefineError) {
1867  logAllUnhandledErrors(std::move(DefineError), errs());
1868  return true;
1869  }
1870 
1871  PatternContext->createLineVariable();
1872 
1873  std::vector<Pattern> ImplicitNegativeChecks;
1874  for (StringRef PatternString : Req.ImplicitCheckNot) {
1875  // Create a buffer with fake command line content in order to display the
1876  // command line option responsible for the specific implicit CHECK-NOT.
1877  std::string Prefix = "-implicit-check-not='";
1878  std::string Suffix = "'";
1879  std::unique_ptr<MemoryBuffer> CmdLine = MemoryBuffer::getMemBufferCopy(
1880  (Prefix + PatternString + Suffix).str(), "command line");
1881 
1882  StringRef PatternInBuffer =
1883  CmdLine->getBuffer().substr(Prefix.size(), PatternString.size());
1884  unsigned BufferID = SM.AddNewSourceBuffer(std::move(CmdLine), SMLoc());
1885  if (ImpPatBufferIDRange) {
1886  if (ImpPatBufferIDRange->first == ImpPatBufferIDRange->second) {
1887  ImpPatBufferIDRange->first = BufferID;
1888  ImpPatBufferIDRange->second = BufferID + 1;
1889  } else {
1890  assert(BufferID == ImpPatBufferIDRange->second &&
1891  "expected consecutive source buffer IDs");
1892  ++ImpPatBufferIDRange->second;
1893  }
1894  }
1895 
1896  ImplicitNegativeChecks.push_back(
1897  Pattern(Check::CheckNot, PatternContext.get()));
1898  ImplicitNegativeChecks.back().parsePattern(PatternInBuffer,
1899  "IMPLICIT-CHECK", SM, Req);
1900  }
1901 
1902  std::vector<Pattern> DagNotMatches = ImplicitNegativeChecks;
1903 
1904  // LineNumber keeps track of the line on which CheckPrefix instances are
1905  // found.
1906  unsigned LineNumber = 1;
1907 
1908  std::set<StringRef> PrefixesNotFound(Req.CheckPrefixes.begin(),
1909  Req.CheckPrefixes.end());
1910  const size_t DistinctPrefixes = PrefixesNotFound.size();
1911  while (true) {
1912  Check::FileCheckType CheckTy;
1913 
1914  // See if a prefix occurs in the memory buffer.
1915  StringRef UsedPrefix;
1916  StringRef AfterSuffix;
1917  std::tie(UsedPrefix, AfterSuffix) =
1918  FindFirstMatchingPrefix(Req, PrefixRE, Buffer, LineNumber, CheckTy);
1919  if (UsedPrefix.empty())
1920  break;
1921  if (CheckTy != Check::CheckComment)
1922  PrefixesNotFound.erase(UsedPrefix);
1923 
1924  assert(UsedPrefix.data() == Buffer.data() &&
1925  "Failed to move Buffer's start forward, or pointed prefix outside "
1926  "of the buffer!");
1927  assert(AfterSuffix.data() >= Buffer.data() &&
1928  AfterSuffix.data() < Buffer.data() + Buffer.size() &&
1929  "Parsing after suffix doesn't start inside of buffer!");
1930 
1931  // Location to use for error messages.
1932  const char *UsedPrefixStart = UsedPrefix.data();
1933 
1934  // Skip the buffer to the end of parsed suffix (or just prefix, if no good
1935  // suffix was processed).
1936  Buffer = AfterSuffix.empty() ? Buffer.drop_front(UsedPrefix.size())
1937  : AfterSuffix;
1938 
1939  // Complain about useful-looking but unsupported suffixes.
1940  if (CheckTy == Check::CheckBadNot) {
1942  "unsupported -NOT combo on prefix '" + UsedPrefix + "'");
1943  return true;
1944  }
1945 
1946  // Complain about invalid count specification.
1947  if (CheckTy == Check::CheckBadCount) {
1949  "invalid count in -COUNT specification on prefix '" +
1950  UsedPrefix + "'");
1951  return true;
1952  }
1953 
1954  // Okay, we found the prefix, yay. Remember the rest of the line, but ignore
1955  // leading whitespace.
1956  if (!(Req.NoCanonicalizeWhiteSpace && Req.MatchFullLines))
1957  Buffer = Buffer.substr(Buffer.find_first_not_of(" \t"));
1958 
1959  // Scan ahead to the end of line.
1960  size_t EOL = Buffer.find_first_of("\n\r");
1961 
1962  // Remember the location of the start of the pattern, for diagnostics.
1963  SMLoc PatternLoc = SMLoc::getFromPointer(Buffer.data());
1964 
1965  // Extract the pattern from the buffer.
1966  StringRef PatternBuffer = Buffer.substr(0, EOL);
1967  Buffer = Buffer.substr(EOL);
1968 
1969  // If this is a comment, we're done.
1970  if (CheckTy == Check::CheckComment)
1971  continue;
1972 
1973  // Parse the pattern.
1974  Pattern P(CheckTy, PatternContext.get(), LineNumber);
1975  if (P.parsePattern(PatternBuffer, UsedPrefix, SM, Req))
1976  return true;
1977 
1978  // Verify that CHECK-LABEL lines do not define or use variables
1979  if ((CheckTy == Check::CheckLabel) && P.hasVariable()) {
1980  SM.PrintMessage(
1981  SMLoc::getFromPointer(UsedPrefixStart), SourceMgr::DK_Error,
1982  "found '" + UsedPrefix + "-LABEL:'"
1983  " with variable definition or use");
1984  return true;
1985  }
1986 
1987  // Verify that CHECK-NEXT/SAME/EMPTY lines have at least one CHECK line before them.
1988  if ((CheckTy == Check::CheckNext || CheckTy == Check::CheckSame ||
1989  CheckTy == Check::CheckEmpty) &&
1990  CheckStrings->empty()) {
1991  StringRef Type = CheckTy == Check::CheckNext
1992  ? "NEXT"
1993  : CheckTy == Check::CheckEmpty ? "EMPTY" : "SAME";
1994  SM.PrintMessage(SMLoc::getFromPointer(UsedPrefixStart),
1996  "found '" + UsedPrefix + "-" + Type +
1997  "' without previous '" + UsedPrefix + ": line");
1998  return true;
1999  }
2000 
2001  // Handle CHECK-DAG/-NOT.
2002  if (CheckTy == Check::CheckDAG || CheckTy == Check::CheckNot) {
2003  DagNotMatches.push_back(P);
2004  continue;
2005  }
2006 
2007  // Okay, add the string we captured to the output vector and move on.
2008  CheckStrings->emplace_back(P, UsedPrefix, PatternLoc);
2009  std::swap(DagNotMatches, CheckStrings->back().DagNotStrings);
2010  DagNotMatches = ImplicitNegativeChecks;
2011  }
2012 
2013  // When there are no used prefixes we report an error except in the case that
2014  // no prefix is specified explicitly but -implicit-check-not is specified.
2015  const bool NoPrefixesFound = PrefixesNotFound.size() == DistinctPrefixes;
2016  const bool SomePrefixesUnexpectedlyNotUsed =
2017  !Req.AllowUnusedPrefixes && !PrefixesNotFound.empty();
2018  if ((NoPrefixesFound || SomePrefixesUnexpectedlyNotUsed) &&
2019  (ImplicitNegativeChecks.empty() || !Req.IsDefaultCheckPrefix)) {
2020  errs() << "error: no check strings found with prefix"
2021  << (PrefixesNotFound.size() > 1 ? "es " : " ");
2022  bool First = true;
2023  for (StringRef MissingPrefix : PrefixesNotFound) {
2024  if (!First)
2025  errs() << ", ";
2026  errs() << "\'" << MissingPrefix << ":'";
2027  First = false;
2028  }
2029  errs() << '\n';
2030  return true;
2031  }
2032 
2033  // Add an EOF pattern for any trailing --implicit-check-not/CHECK-DAG/-NOTs,
2034  // and use the first prefix as a filler for the error message.
2035  if (!DagNotMatches.empty()) {
2036  CheckStrings->emplace_back(
2037  Pattern(Check::CheckEOF, PatternContext.get(), LineNumber + 1),
2038  *Req.CheckPrefixes.begin(), SMLoc::getFromPointer(Buffer.data()));
2039  std::swap(DagNotMatches, CheckStrings->back().DagNotStrings);
2040  }
2041 
2042  return false;
2043 }
2044 
2045 /// Returns either (1) \c ErrorSuccess if there was no error or (2)
2046 /// \c ErrorReported if an error was reported, such as an unexpected match.
2047 static Error printMatch(bool ExpectedMatch, const SourceMgr &SM,
2048  StringRef Prefix, SMLoc Loc, const Pattern &Pat,
2049  int MatchedCount, StringRef Buffer,
2050  Pattern::MatchResult MatchResult,
2051  const FileCheckRequest &Req,
2052  std::vector<FileCheckDiag> *Diags) {
2053  // Suppress some verbosity if there's no error.
2054  bool HasError = !ExpectedMatch || MatchResult.TheError;
2055  bool PrintDiag = true;
2056  if (!HasError) {
2057  if (!Req.Verbose)
2058  return ErrorReported::reportedOrSuccess(HasError);
2059  if (!Req.VerboseVerbose && Pat.getCheckTy() == Check::CheckEOF)
2060  return ErrorReported::reportedOrSuccess(HasError);
2061  // Due to their verbosity, we don't print verbose diagnostics here if we're
2062  // gathering them for Diags to be rendered elsewhere, but we always print
2063  // other diagnostics.
2064  PrintDiag = !Diags;
2065  }
2066 
2067  // Add "found" diagnostic, substitutions, and variable definitions to Diags.
2068  FileCheckDiag::MatchType MatchTy = ExpectedMatch
2071  SMRange MatchRange = ProcessMatchResult(MatchTy, SM, Loc, Pat.getCheckTy(),
2072  Buffer, MatchResult.TheMatch->Pos,
2073  MatchResult.TheMatch->Len, Diags);
2074  if (Diags) {
2075  Pat.printSubstitutions(SM, Buffer, MatchRange, MatchTy, Diags);
2076  Pat.printVariableDefs(SM, MatchTy, Diags);
2077  }
2078  if (!PrintDiag) {
2079  assert(!HasError && "expected to report more diagnostics for error");
2080  return ErrorReported::reportedOrSuccess(HasError);
2081  }
2082 
2083  // Print the match.
2084  std::string Message = formatv("{0}: {1} string found in input",
2086  (ExpectedMatch ? "expected" : "excluded"))
2087  .str();
2088  if (Pat.getCount() > 1)
2089  Message += formatv(" ({0} out of {1})", MatchedCount, Pat.getCount()).str();
2090  SM.PrintMessage(
2091  Loc, ExpectedMatch ? SourceMgr::DK_Remark : SourceMgr::DK_Error, Message);
2092  SM.PrintMessage(MatchRange.Start, SourceMgr::DK_Note, "found here",
2093  {MatchRange});
2094 
2095  // Print additional information, which can be useful even if there are errors.
2096  Pat.printSubstitutions(SM, Buffer, MatchRange, MatchTy, nullptr);
2097  Pat.printVariableDefs(SM, MatchTy, nullptr);
2098 
2099  // Print errors and add them to Diags. We report these errors after the match
2100  // itself because we found them after the match. If we had found them before
2101  // the match, we'd be in printNoMatch.
2102  handleAllErrors(std::move(MatchResult.TheError),
2103  [&](const ErrorDiagnostic &E) {
2104  E.log(errs());
2105  if (Diags) {
2106  Diags->emplace_back(SM, Pat.getCheckTy(), Loc,
2107  FileCheckDiag::MatchFoundErrorNote,
2108  E.getRange(), E.getMessage().str());
2109  }
2110  });
2111  return ErrorReported::reportedOrSuccess(HasError);
2112 }
2113 
2114 /// Returns either (1) \c ErrorSuccess if there was no error, or (2)
2115 /// \c ErrorReported if an error was reported, such as an expected match not
2116 /// found.
2117 static Error printNoMatch(bool ExpectedMatch, const SourceMgr &SM,
2118  StringRef Prefix, SMLoc Loc, const Pattern &Pat,
2119  int MatchedCount, StringRef Buffer, Error MatchError,
2120  bool VerboseVerbose,
2121  std::vector<FileCheckDiag> *Diags) {
2122  // Print any pattern errors, and record them to be added to Diags later.
2123  bool HasError = ExpectedMatch;
2124  bool HasPatternError = false;
2125  FileCheckDiag::MatchType MatchTy = ExpectedMatch
2126  ? FileCheckDiag::MatchNoneButExpected
2127  : FileCheckDiag::MatchNoneAndExcluded;
2128  SmallVector<std::string, 4> ErrorMsgs;
2130  std::move(MatchError),
2131  [&](const ErrorDiagnostic &E) {
2132  HasError = HasPatternError = true;
2133  MatchTy = FileCheckDiag::MatchNoneForInvalidPattern;
2134  E.log(errs());
2135  if (Diags)
2136  ErrorMsgs.push_back(E.getMessage().str());
2137  },
2138  // NotFoundError is why printNoMatch was invoked.
2139  [](const NotFoundError &E) {});
2140 
2141  // Suppress some verbosity if there's no error.
2142  bool PrintDiag = true;
2143  if (!HasError) {
2144  if (!VerboseVerbose)
2145  return ErrorReported::reportedOrSuccess(HasError);
2146  // Due to their verbosity, we don't print verbose diagnostics here if we're
2147  // gathering them for Diags to be rendered elsewhere, but we always print
2148  // other diagnostics.
2149  PrintDiag = !Diags;
2150  }
2151 
2152  // Add "not found" diagnostic, substitutions, and pattern errors to Diags.
2153  //
2154  // We handle Diags a little differently than the errors we print directly:
2155  // we add the "not found" diagnostic to Diags even if there are pattern
2156  // errors. The reason is that we need to attach pattern errors as notes
2157  // somewhere in the input, and the input search range from the "not found"
2158  // diagnostic is all we have to anchor them.
2159  SMRange SearchRange = ProcessMatchResult(MatchTy, SM, Loc, Pat.getCheckTy(),
2160  Buffer, 0, Buffer.size(), Diags);
2161  if (Diags) {
2162  SMRange NoteRange = SMRange(SearchRange.Start, SearchRange.Start);
2163  for (StringRef ErrorMsg : ErrorMsgs)
2164  Diags->emplace_back(SM, Pat.getCheckTy(), Loc, MatchTy, NoteRange,
2165  ErrorMsg);
2166  Pat.printSubstitutions(SM, Buffer, SearchRange, MatchTy, Diags);
2167  }
2168  if (!PrintDiag) {
2169  assert(!HasError && "expected to report more diagnostics for error");
2170  return ErrorReported::reportedOrSuccess(HasError);
2171  }
2172 
2173  // Print "not found" diagnostic, except that's implied if we already printed a
2174  // pattern error.
2175  if (!HasPatternError) {
2176  std::string Message = formatv("{0}: {1} string not found in input",
2178  (ExpectedMatch ? "expected" : "excluded"))
2179  .str();
2180  if (Pat.getCount() > 1)
2181  Message +=
2182  formatv(" ({0} out of {1})", MatchedCount, Pat.getCount()).str();
2183  SM.PrintMessage(Loc,
2184  ExpectedMatch ? SourceMgr::DK_Error : SourceMgr::DK_Remark,
2185  Message);
2186  SM.PrintMessage(SearchRange.Start, SourceMgr::DK_Note,
2187  "scanning from here");
2188  }
2189 
2190  // Print additional information, which can be useful even after a pattern
2191  // error.
2192  Pat.printSubstitutions(SM, Buffer, SearchRange, MatchTy, nullptr);
2193  if (ExpectedMatch)
2194  Pat.printFuzzyMatch(SM, Buffer, Diags);
2195  return ErrorReported::reportedOrSuccess(HasError);
2196 }
2197 
2198 /// Returns either (1) \c ErrorSuccess if there was no error, or (2)
2199 /// \c ErrorReported if an error was reported.
2200 static Error reportMatchResult(bool ExpectedMatch, const SourceMgr &SM,
2201  StringRef Prefix, SMLoc Loc, const Pattern &Pat,
2202  int MatchedCount, StringRef Buffer,
2203  Pattern::MatchResult MatchResult,
2204  const FileCheckRequest &Req,
2205  std::vector<FileCheckDiag> *Diags) {
2206  if (MatchResult.TheMatch)
2207  return printMatch(ExpectedMatch, SM, Prefix, Loc, Pat, MatchedCount, Buffer,
2208  std::move(MatchResult), Req, Diags);
2209  return printNoMatch(ExpectedMatch, SM, Prefix, Loc, Pat, MatchedCount, Buffer,
2210  std::move(MatchResult.TheError), Req.VerboseVerbose,
2211  Diags);
2212 }
2213 
2214 /// Counts the number of newlines in the specified range.
2215 static unsigned CountNumNewlinesBetween(StringRef Range,
2216  const char *&FirstNewLine) {
2217  unsigned NumNewLines = 0;
2218  while (1) {
2219  // Scan for newline.
2220  Range = Range.substr(Range.find_first_of("\n\r"));
2221  if (Range.empty())
2222  return NumNewLines;
2223 
2224  ++NumNewLines;
2225 
2226  // Handle \n\r and \r\n as a single newline.
2227  if (Range.size() > 1 && (Range[1] == '\n' || Range[1] == '\r') &&
2228  (Range[0] != Range[1]))
2229  Range = Range.substr(1);
2230  Range = Range.substr(1);
2231 
2232  if (NumNewLines == 1)
2233  FirstNewLine = Range.begin();
2234  }
2235 }
2236 
2237 size_t FileCheckString::Check(const SourceMgr &SM, StringRef Buffer,
2238  bool IsLabelScanMode, size_t &MatchLen,
2239  FileCheckRequest &Req,
2240  std::vector<FileCheckDiag> *Diags) const {
2241  size_t LastPos = 0;
2242  std::vector<const Pattern *> NotStrings;
2243 
2244  // IsLabelScanMode is true when we are scanning forward to find CHECK-LABEL
2245  // bounds; we have not processed variable definitions within the bounded block
2246  // yet so cannot handle any final CHECK-DAG yet; this is handled when going
2247  // over the block again (including the last CHECK-LABEL) in normal mode.
2248  if (!IsLabelScanMode) {
2249  // Match "dag strings" (with mixed "not strings" if any).
2250  LastPos = CheckDag(SM, Buffer, NotStrings, Req, Diags);
2251  if (LastPos == StringRef::npos)
2252  return StringRef::npos;
2253  }
2254 
2255  // Match itself from the last position after matching CHECK-DAG.
2256  size_t LastMatchEnd = LastPos;
2257  size_t FirstMatchPos = 0;
2258  // Go match the pattern Count times. Majority of patterns only match with
2259  // count 1 though.
2260  assert(Pat.getCount() != 0 && "pattern count can not be zero");
2261  for (int i = 1; i <= Pat.getCount(); i++) {
2262  StringRef MatchBuffer = Buffer.substr(LastMatchEnd);
2263  // get a match at current start point
2264  Pattern::MatchResult MatchResult = Pat.match(MatchBuffer, SM);
2265 
2266  // report
2267  if (Error Err = reportMatchResult(/*ExpectedMatch=*/true, SM, Prefix, Loc,
2268  Pat, i, MatchBuffer,
2269  std::move(MatchResult), Req, Diags)) {
2270  cantFail(handleErrors(std::move(Err), [&](const ErrorReported &E) {}));
2271  return StringRef::npos;
2272  }
2273 
2274  size_t MatchPos = MatchResult.TheMatch->Pos;
2275  if (i == 1)
2276  FirstMatchPos = LastPos + MatchPos;
2277 
2278  // move start point after the match
2279  LastMatchEnd += MatchPos + MatchResult.TheMatch->Len;
2280  }
2281  // Full match len counts from first match pos.
2282  MatchLen = LastMatchEnd - FirstMatchPos;
2283 
2284  // Similar to the above, in "label-scan mode" we can't yet handle CHECK-NEXT
2285  // or CHECK-NOT
2286  if (!IsLabelScanMode) {
2287  size_t MatchPos = FirstMatchPos - LastPos;
2288  StringRef MatchBuffer = Buffer.substr(LastPos);
2289  StringRef SkippedRegion = Buffer.substr(LastPos, MatchPos);
2290 
2291  // If this check is a "CHECK-NEXT", verify that the previous match was on
2292  // the previous line (i.e. that there is one newline between them).
2293  if (CheckNext(SM, SkippedRegion)) {
2294  ProcessMatchResult(FileCheckDiag::MatchFoundButWrongLine, SM, Loc,
2295  Pat.getCheckTy(), MatchBuffer, MatchPos, MatchLen,
2296  Diags, Req.Verbose);
2297  return StringRef::npos;
2298  }
2299 
2300  // If this check is a "CHECK-SAME", verify that the previous match was on
2301  // the same line (i.e. that there is no newline between them).
2302  if (CheckSame(SM, SkippedRegion)) {
2303  ProcessMatchResult(FileCheckDiag::MatchFoundButWrongLine, SM, Loc,
2304  Pat.getCheckTy(), MatchBuffer, MatchPos, MatchLen,
2305  Diags, Req.Verbose);
2306  return StringRef::npos;
2307  }
2308 
2309  // If this match had "not strings", verify that they don't exist in the
2310  // skipped region.
2311  if (CheckNot(SM, SkippedRegion, NotStrings, Req, Diags))
2312  return StringRef::npos;
2313  }
2314 
2315  return FirstMatchPos;
2316 }
2317 
2318 bool FileCheckString::CheckNext(const SourceMgr &SM, StringRef Buffer) const {
2319  if (Pat.getCheckTy() != Check::CheckNext &&
2321  return false;
2322 
2323  Twine CheckName =
2324  Prefix +
2325  Twine(Pat.getCheckTy() == Check::CheckEmpty ? "-EMPTY" : "-NEXT");
2326 
2327  // Count the number of newlines between the previous match and this one.
2328  const char *FirstNewLine = nullptr;
2329  unsigned NumNewLines = CountNumNewlinesBetween(Buffer, FirstNewLine);
2330 
2331  if (NumNewLines == 0) {
2333  CheckName + ": is on the same line as previous match");
2335  "'next' match was here");
2337  "previous match ended here");
2338  return true;
2339  }
2340 
2341  if (NumNewLines != 1) {
2343  CheckName +
2344  ": is not on the line after the previous match");
2346  "'next' match was here");
2348  "previous match ended here");
2350  "non-matching line after previous match is here");
2351  return true;
2352  }
2353 
2354  return false;
2355 }
2356 
2357 bool FileCheckString::CheckSame(const SourceMgr &SM, StringRef Buffer) const {
2358  if (Pat.getCheckTy() != Check::CheckSame)
2359  return false;
2360 
2361  // Count the number of newlines between the previous match and this one.
2362  const char *FirstNewLine = nullptr;
2363  unsigned NumNewLines = CountNumNewlinesBetween(Buffer, FirstNewLine);
2364 
2365  if (NumNewLines != 0) {
2367  Prefix +
2368  "-SAME: is not on the same line as the previous match");
2370  "'next' match was here");
2372  "previous match ended here");
2373  return true;
2374  }
2375 
2376  return false;
2377 }
2378 
2379 bool FileCheckString::CheckNot(const SourceMgr &SM, StringRef Buffer,
2380  const std::vector<const Pattern *> &NotStrings,
2381  const FileCheckRequest &Req,
2382  std::vector<FileCheckDiag> *Diags) const {
2383  bool DirectiveFail = false;
2384  for (const Pattern *Pat : NotStrings) {
2385  assert((Pat->getCheckTy() == Check::CheckNot) && "Expect CHECK-NOT!");
2386  Pattern::MatchResult MatchResult = Pat->match(Buffer, SM);
2387  if (Error Err = reportMatchResult(/*ExpectedMatch=*/false, SM, Prefix,
2388  Pat->getLoc(), *Pat, 1, Buffer,
2389  std::move(MatchResult), Req, Diags)) {
2390  cantFail(handleErrors(std::move(Err), [&](const ErrorReported &E) {}));
2391  DirectiveFail = true;
2392  continue;
2393  }
2394  }
2395  return DirectiveFail;
2396 }
2397 
2398 size_t FileCheckString::CheckDag(const SourceMgr &SM, StringRef Buffer,
2399  std::vector<const Pattern *> &NotStrings,
2400  const FileCheckRequest &Req,
2401  std::vector<FileCheckDiag> *Diags) const {
2402  if (DagNotStrings.empty())
2403  return 0;
2404 
2405  // The start of the search range.
2406  size_t StartPos = 0;
2407 
2408  struct MatchRange {
2409  size_t Pos;
2410  size_t End;
2411  };
2412  // A sorted list of ranges for non-overlapping CHECK-DAG matches. Match
2413  // ranges are erased from this list once they are no longer in the search
2414  // range.
2415  std::list<MatchRange> MatchRanges;
2416 
2417  // We need PatItr and PatEnd later for detecting the end of a CHECK-DAG
2418  // group, so we don't use a range-based for loop here.
2419  for (auto PatItr = DagNotStrings.begin(), PatEnd = DagNotStrings.end();
2420  PatItr != PatEnd; ++PatItr) {
2421  const Pattern &Pat = *PatItr;
2423  Pat.getCheckTy() == Check::CheckNot) &&
2424  "Invalid CHECK-DAG or CHECK-NOT!");
2425 
2426  if (Pat.getCheckTy() == Check::CheckNot) {
2427  NotStrings.push_back(&Pat);
2428  continue;
2429  }
2430 
2431  assert((Pat.getCheckTy() == Check::CheckDAG) && "Expect CHECK-DAG!");
2432 
2433  // CHECK-DAG always matches from the start.
2434  size_t MatchLen = 0, MatchPos = StartPos;
2435 
2436  // Search for a match that doesn't overlap a previous match in this
2437  // CHECK-DAG group.
2438  for (auto MI = MatchRanges.begin(), ME = MatchRanges.end(); true; ++MI) {
2439  StringRef MatchBuffer = Buffer.substr(MatchPos);
2440  Pattern::MatchResult MatchResult = Pat.match(MatchBuffer, SM);
2441  // With a group of CHECK-DAGs, a single mismatching means the match on
2442  // that group of CHECK-DAGs fails immediately.
2443  if (MatchResult.TheError || Req.VerboseVerbose) {
2444  if (Error Err = reportMatchResult(/*ExpectedMatch=*/true, SM, Prefix,
2445  Pat.getLoc(), Pat, 1, MatchBuffer,
2446  std::move(MatchResult), Req, Diags)) {
2447  cantFail(
2448  handleErrors(std::move(Err), [&](const ErrorReported &E) {}));
2449  return StringRef::npos;
2450  }
2451  }
2452  MatchLen = MatchResult.TheMatch->Len;
2453  // Re-calc it as the offset relative to the start of the original
2454  // string.
2455  MatchPos += MatchResult.TheMatch->Pos;
2456  MatchRange M{MatchPos, MatchPos + MatchLen};
2457  if (Req.AllowDeprecatedDagOverlap) {
2458  // We don't need to track all matches in this mode, so we just maintain
2459  // one match range that encompasses the current CHECK-DAG group's
2460  // matches.
2461  if (MatchRanges.empty())
2462  MatchRanges.insert(MatchRanges.end(), M);
2463  else {
2464  auto Block = MatchRanges.begin();
2465  Block->Pos = std::min(Block->Pos, M.Pos);
2466  Block->End = std::max(Block->End, M.End);
2467  }
2468  break;
2469  }
2470  // Iterate previous matches until overlapping match or insertion point.
2471  bool Overlap = false;
2472  for (; MI != ME; ++MI) {
2473  if (M.Pos < MI->End) {
2474  // !Overlap => New match has no overlap and is before this old match.
2475  // Overlap => New match overlaps this old match.
2476  Overlap = MI->Pos < M.End;
2477  break;
2478  }
2479  }
2480  if (!Overlap) {
2481  // Insert non-overlapping match into list.
2482  MatchRanges.insert(MI, M);
2483  break;
2484  }
2485  if (Req.VerboseVerbose) {
2486  // Due to their verbosity, we don't print verbose diagnostics here if
2487  // we're gathering them for a different rendering, but we always print
2488  // other diagnostics.
2489  if (!Diags) {
2490  SMLoc OldStart = SMLoc::getFromPointer(Buffer.data() + MI->Pos);
2491  SMLoc OldEnd = SMLoc::getFromPointer(Buffer.data() + MI->End);
2492  SMRange OldRange(OldStart, OldEnd);
2493  SM.PrintMessage(OldStart, SourceMgr::DK_Note,
2494  "match discarded, overlaps earlier DAG match here",
2495  {OldRange});
2496  } else {
2497  SMLoc CheckLoc = Diags->rbegin()->CheckLoc;
2498  for (auto I = Diags->rbegin(), E = Diags->rend();
2499  I != E && I->CheckLoc == CheckLoc; ++I)
2501  }
2502  }
2503  MatchPos = MI->End;
2504  }
2505  if (!Req.VerboseVerbose)
2506  cantFail(printMatch(
2507  /*ExpectedMatch=*/true, SM, Prefix, Pat.getLoc(), Pat, 1, Buffer,
2508  Pattern::MatchResult(MatchPos, MatchLen, Error::success()), Req,
2509  Diags));
2510 
2511  // Handle the end of a CHECK-DAG group.
2512  if (std::next(PatItr) == PatEnd ||
2513  std::next(PatItr)->getCheckTy() == Check::CheckNot) {
2514  if (!NotStrings.empty()) {
2515  // If there are CHECK-NOTs between two CHECK-DAGs or from CHECK to
2516  // CHECK-DAG, verify that there are no 'not' strings occurred in that
2517  // region.
2518  StringRef SkippedRegion =
2519  Buffer.slice(StartPos, MatchRanges.begin()->Pos);
2520  if (CheckNot(SM, SkippedRegion, NotStrings, Req, Diags))
2521  return StringRef::npos;
2522  // Clear "not strings".
2523  NotStrings.clear();
2524  }
2525  // All subsequent CHECK-DAGs and CHECK-NOTs should be matched from the
2526  // end of this CHECK-DAG group's match range.
2527  StartPos = MatchRanges.rbegin()->End;
2528  // Don't waste time checking for (impossible) overlaps before that.
2529  MatchRanges.clear();
2530  }
2531  }
2532 
2533  return StartPos;
2534 }
2535 
2536 static bool ValidatePrefixes(StringRef Kind, StringSet<> &UniquePrefixes,
2537  ArrayRef<StringRef> SuppliedPrefixes) {
2538  for (StringRef Prefix : SuppliedPrefixes) {
2539  if (Prefix.empty()) {
2540  errs() << "error: supplied " << Kind << " prefix must not be the empty "
2541  << "string\n";
2542  return false;
2543  }
2544  static const Regex Validator("^[a-zA-Z0-9_-]*$");
2545  if (!Validator.match(Prefix)) {
2546  errs() << "error: supplied " << Kind << " prefix must start with a "
2547  << "letter and contain only alphanumeric characters, hyphens, and "
2548  << "underscores: '" << Prefix << "'\n";
2549  return false;
2550  }
2551  if (!UniquePrefixes.insert(Prefix).second) {
2552  errs() << "error: supplied " << Kind << " prefix must be unique among "
2553  << "check and comment prefixes: '" << Prefix << "'\n";
2554  return false;
2555  }
2556  }
2557  return true;
2558 }
2559 
2560 static const char *DefaultCheckPrefixes[] = {"CHECK"};
2561 static const char *DefaultCommentPrefixes[] = {"COM", "RUN"};
2562 
2564  StringSet<> UniquePrefixes;
2565  // Add default prefixes to catch user-supplied duplicates of them below.
2566  if (Req.CheckPrefixes.empty()) {
2567  for (const char *Prefix : DefaultCheckPrefixes)
2568  UniquePrefixes.insert(Prefix);
2569  }
2570  if (Req.CommentPrefixes.empty()) {
2571  for (const char *Prefix : DefaultCommentPrefixes)
2572  UniquePrefixes.insert(Prefix);
2573  }
2574  // Do not validate the default prefixes, or diagnostics about duplicates might
2575  // incorrectly indicate that they were supplied by the user.
2576  if (!ValidatePrefixes("check", UniquePrefixes, Req.CheckPrefixes))
2577  return false;
2578  if (!ValidatePrefixes("comment", UniquePrefixes, Req.CommentPrefixes))
2579  return false;
2580  return true;
2581 }
2582 
2584  if (Req.CheckPrefixes.empty()) {
2585  for (const char *Prefix : DefaultCheckPrefixes)
2586  Req.CheckPrefixes.push_back(Prefix);
2587  Req.IsDefaultCheckPrefix = true;
2588  }
2589  if (Req.CommentPrefixes.empty()) {
2590  for (const char *Prefix : DefaultCommentPrefixes)
2591  Req.CommentPrefixes.push_back(Prefix);
2592  }
2593 
2594  // We already validated the contents of CheckPrefixes and CommentPrefixes so
2595  // just concatenate them as alternatives.
2596  SmallString<32> PrefixRegexStr;
2597  for (size_t I = 0, E = Req.CheckPrefixes.size(); I != E; ++I) {
2598  if (I != 0)
2599  PrefixRegexStr.push_back('|');
2600  PrefixRegexStr.append(Req.CheckPrefixes[I]);
2601  }
2602  for (StringRef Prefix : Req.CommentPrefixes) {
2603  PrefixRegexStr.push_back('|');
2604  PrefixRegexStr.append(Prefix);
2605  }
2606 
2607  return Regex(PrefixRegexStr);
2608 }
2609 
2611  ArrayRef<StringRef> CmdlineDefines, SourceMgr &SM) {
2612  assert(GlobalVariableTable.empty() && GlobalNumericVariableTable.empty() &&
2613  "Overriding defined variable with command-line variable definitions");
2614 
2615  if (CmdlineDefines.empty())
2616  return Error::success();
2617 
2618  // Create a string representing the vector of command-line definitions. Each
2619  // definition is on its own line and prefixed with a definition number to
2620  // clarify which definition a given diagnostic corresponds to.
2621  unsigned I = 0;
2622  Error Errs = Error::success();
2623  std::string CmdlineDefsDiag;
2624  SmallVector<std::pair<size_t, size_t>, 4> CmdlineDefsIndices;
2625  for (StringRef CmdlineDef : CmdlineDefines) {
2626  std::string DefPrefix = ("Global define #" + Twine(++I) + ": ").str();
2627  size_t EqIdx = CmdlineDef.find('=');
2628  if (EqIdx == StringRef::npos) {
2629  CmdlineDefsIndices.push_back(std::make_pair(CmdlineDefsDiag.size(), 0));
2630  continue;
2631  }
2632  // Numeric variable definition.
2633  if (CmdlineDef[0] == '#') {
2634  // Append a copy of the command-line definition adapted to use the same
2635  // format as in the input file to be able to reuse
2636  // parseNumericSubstitutionBlock.
2637  CmdlineDefsDiag += (DefPrefix + CmdlineDef + " (parsed as: [[").str();
2638  std::string SubstitutionStr = std::string(CmdlineDef);
2639  SubstitutionStr[EqIdx] = ':';
2640  CmdlineDefsIndices.push_back(
2641  std::make_pair(CmdlineDefsDiag.size(), SubstitutionStr.size()));
2642  CmdlineDefsDiag += (SubstitutionStr + Twine("]])\n")).str();
2643  } else {
2644  CmdlineDefsDiag += DefPrefix;
2645  CmdlineDefsIndices.push_back(
2646  std::make_pair(CmdlineDefsDiag.size(), CmdlineDef.size()));
2647  CmdlineDefsDiag += (CmdlineDef + "\n").str();
2648  }
2649  }
2650 
2651  // Create a buffer with fake command line content in order to display
2652  // parsing diagnostic with location information and point to the
2653  // global definition with invalid syntax.
2654  std::unique_ptr<MemoryBuffer> CmdLineDefsDiagBuffer =
2655  MemoryBuffer::getMemBufferCopy(CmdlineDefsDiag, "Global defines");
2656  StringRef CmdlineDefsDiagRef = CmdLineDefsDiagBuffer->getBuffer();
2657  SM.AddNewSourceBuffer(std::move(CmdLineDefsDiagBuffer), SMLoc());
2658 
2659  for (std::pair<size_t, size_t> CmdlineDefIndices : CmdlineDefsIndices) {
2660  StringRef CmdlineDef = CmdlineDefsDiagRef.substr(CmdlineDefIndices.first,
2661  CmdlineDefIndices.second);
2662  if (CmdlineDef.empty()) {
2663  Errs = joinErrors(
2664  std::move(Errs),
2665  ErrorDiagnostic::get(SM, CmdlineDef,
2666  "missing equal sign in global definition"));
2667  continue;
2668  }
2669 
2670  // Numeric variable definition.
2671  if (CmdlineDef[0] == '#') {
2672  // Now parse the definition both to check that the syntax is correct and
2673  // to create the necessary class instance.
2674  StringRef CmdlineDefExpr = CmdlineDef.substr(1);
2675  Optional<NumericVariable *> DefinedNumericVariable;
2676  Expected<std::unique_ptr<Expression>> ExpressionResult =
2678  CmdlineDefExpr, DefinedNumericVariable, false, None, this, SM);
2679  if (!ExpressionResult) {
2680  Errs = joinErrors(std::move(Errs), ExpressionResult.takeError());
2681  continue;
2682  }
2683  std::unique_ptr<Expression> Expression = std::move(*ExpressionResult);
2684  // Now evaluate the expression whose value this variable should be set
2685  // to, since the expression of a command-line variable definition should
2686  // only use variables defined earlier on the command-line. If not, this
2687  // is an error and we report it.
2689  if (!Value) {
2690  Errs = joinErrors(std::move(Errs), Value.takeError());
2691  continue;
2692  }
2693 
2694  assert(DefinedNumericVariable && "No variable defined");
2695  (*DefinedNumericVariable)->setValue(*Value);
2696 
2697  // Record this variable definition.
2698  GlobalNumericVariableTable[(*DefinedNumericVariable)->getName()] =
2699  *DefinedNumericVariable;
2700  } else {
2701  // String variable definition.
2702  std::pair<StringRef, StringRef> CmdlineNameVal = CmdlineDef.split('=');
2703  StringRef CmdlineName = CmdlineNameVal.first;
2704  StringRef OrigCmdlineName = CmdlineName;
2705  Expected<Pattern::VariableProperties> ParseVarResult =
2706  Pattern::parseVariable(CmdlineName, SM);
2707  if (!ParseVarResult) {
2708  Errs = joinErrors(std::move(Errs), ParseVarResult.takeError());
2709  continue;
2710  }
2711  // Check that CmdlineName does not denote a pseudo variable is only
2712  // composed of the parsed numeric variable. This catches cases like
2713  // "FOO+2" in a "FOO+2=10" definition.
2714  if (ParseVarResult->IsPseudo || !CmdlineName.empty()) {
2715  Errs = joinErrors(std::move(Errs),
2717  SM, OrigCmdlineName,
2718  "invalid name in string variable definition '" +
2719  OrigCmdlineName + "'"));
2720  continue;
2721  }
2722  StringRef Name = ParseVarResult->Name;
2723 
2724  // Detect collisions between string and numeric variables when the former
2725  // is created later than the latter.
2726  if (GlobalNumericVariableTable.find(Name) !=
2727  GlobalNumericVariableTable.end()) {
2728  Errs = joinErrors(std::move(Errs),
2730  "numeric variable with name '" +
2731  Name + "' already exists"));
2732  continue;
2733  }
2734  GlobalVariableTable.insert(CmdlineNameVal);
2735  // Mark the string variable as defined to detect collisions between
2736  // string and numeric variables in defineCmdlineVariables when the latter
2737  // is created later than the former. We cannot reuse GlobalVariableTable
2738  // for this by populating it with an empty string since we would then
2739  // lose the ability to detect the use of an undefined variable in
2740  // match().
2741  DefinedVariableTable[Name] = true;
2742  }
2743  }
2744 
2745  return Errs;
2746 }
2747 
2749  SmallVector<StringRef, 16> LocalPatternVars, LocalNumericVars;
2750  for (const StringMapEntry<StringRef> &Var : GlobalVariableTable)
2751  if (Var.first()[0] != '$')
2752  LocalPatternVars.push_back(Var.first());
2753 
2754  // Numeric substitution reads the value of a variable directly, not via
2755  // GlobalNumericVariableTable. Therefore, we clear local variables by
2756  // clearing their value which will lead to a numeric substitution failure. We
2757  // also mark the variable for removal from GlobalNumericVariableTable since
2758  // this is what defineCmdlineVariables checks to decide that no global
2759  // variable has been defined.
2760  for (const auto &Var : GlobalNumericVariableTable)
2761  if (Var.first()[0] != '$') {
2762  Var.getValue()->clearValue();
2763  LocalNumericVars.push_back(Var.first());
2764  }
2765 
2766  for (const auto &Var : LocalPatternVars)
2767  GlobalVariableTable.erase(Var);
2768  for (const auto &Var : LocalNumericVars)
2769  GlobalNumericVariableTable.erase(Var);
2770 }
2771 
2772 bool FileCheck::checkInput(SourceMgr &SM, StringRef Buffer,
2773  std::vector<FileCheckDiag> *Diags) {
2774  bool ChecksFailed = false;
2775 
2776  unsigned i = 0, j = 0, e = CheckStrings->size();
2777  while (true) {
2778  StringRef CheckRegion;
2779  if (j == e) {
2780  CheckRegion = Buffer;
2781  } else {
2782  const FileCheckString &CheckLabelStr = (*CheckStrings)[j];
2783  if (CheckLabelStr.Pat.getCheckTy() != Check::CheckLabel) {
2784  ++j;
2785  continue;
2786  }
2787 
2788  // Scan to next CHECK-LABEL match, ignoring CHECK-NOT and CHECK-DAG
2789  size_t MatchLabelLen = 0;
2790  size_t MatchLabelPos =
2791  CheckLabelStr.Check(SM, Buffer, true, MatchLabelLen, Req, Diags);
2792  if (MatchLabelPos == StringRef::npos)
2793  // Immediately bail if CHECK-LABEL fails, nothing else we can do.
2794  return false;
2795 
2796  CheckRegion = Buffer.substr(0, MatchLabelPos + MatchLabelLen);
2797  Buffer = Buffer.substr(MatchLabelPos + MatchLabelLen);
2798  ++j;
2799  }
2800 
2801  // Do not clear the first region as it's the one before the first
2802  // CHECK-LABEL and it would clear variables defined on the command-line
2803  // before they get used.
2804  if (i != 0 && Req.EnableVarScope)
2805  PatternContext->clearLocalVars();
2806 
2807  for (; i != j; ++i) {
2808  const FileCheckString &CheckStr = (*CheckStrings)[i];
2809 
2810  // Check each string within the scanned region, including a second check
2811  // of any final CHECK-LABEL (to verify CHECK-NOT and CHECK-DAG)
2812  size_t MatchLen = 0;
2813  size_t MatchPos =
2814  CheckStr.Check(SM, CheckRegion, false, MatchLen, Req, Diags);
2815 
2816  if (MatchPos == StringRef::npos) {
2817  ChecksFailed = true;
2818  i = j;
2819  break;
2820  }
2821 
2822  CheckRegion = CheckRegion.substr(MatchPos + MatchLen);
2823  }
2824 
2825  if (j == e)
2826  break;
2827  }
2828 
2829  // Success if no checks failed.
2830  return !ChecksFailed;
2831 }
FileCheck.h
llvm::StringSwitch::Case
StringSwitch & Case(StringLiteral S, T Value)
Definition: StringSwitch.h:67
llvm::ExpressionValue::ExpressionValue
ExpressionValue(T Val)
Definition: FileCheckImpl.h:128
i
i
Definition: README.txt:29
llvm::StringRef::back
LLVM_NODISCARD char back() const
back - Get the last character in the string.
Definition: StringRef.h:168
llvm::ExpressionValue
Class representing a numeric value.
Definition: FileCheckImpl.h:121
llvm::SMRange::Start
SMLoc Start
Definition: SMLoc.h:50
llvm::StringRef::startswith
LLVM_NODISCARD bool startswith(StringRef Prefix) const
Check if this string starts with the given Prefix.
Definition: StringRef.h:286
llvm::ExpressionValue::isNegative
bool isNegative() const
Returns true if value is signed and negative, false otherwise.
Definition: FileCheckImpl.h:139
MI
IRTranslator LLVM IR MI
Definition: IRTranslator.cpp:105
llvm::ExpressionFormat::Kind::Unsigned
@ Unsigned
Value is an unsigned integer and should be printed as a decimal number.
llvm
This file implements support for optimizing divisions by a constant.
Definition: AllocatorList.h:23
llvm::StringSubstitution::getResult
Expected< std::string > getResult() const override
Definition: FileCheck.cpp:429
llvm::FileCheckRequest::AllowDeprecatedDagOverlap
bool AllowDeprecatedDagOverlap
Definition: FileCheck.h:39
llvm::FileCheckString::Pat
Pattern Pat
The pattern to match.
Definition: FileCheckImpl.h:867
llvm::handleErrors
Error handleErrors(Error E, HandlerTs &&... Hs)
Pass the ErrorInfo(s) contained in E to their respective handlers.
Definition: Error.h:945
llvm::Operator
This is a utility class that provides an abstraction for the common functionality between Instruction...
Definition: Operator.h:31
llvm::ExpressionFormat::Kind::Signed
@ Signed
Value is a signed integer and should be printed as a decimal number.
M
We currently emits eax Perhaps this is what we really should generate is Is imull three or four cycles eax eax The current instruction priority is based on pattern complexity The former is more complex because it folds a load so the latter will not be emitted Perhaps we should use AddedComplexity to give LEA32r a higher priority We should always try to match LEA first since the LEA matching code does some estimate to determine whether the match is profitable if we care more about code then imull is better It s two bytes shorter than movl leal On a Pentium M
Definition: README.txt:252
llvm::StringRef::empty
LLVM_NODISCARD bool empty() const
empty - Check if the string is empty.
Definition: StringRef.h:153
llvm::StringMapEntry
StringMapEntry - This is used to represent one value that is inserted into a StringMap.
Definition: StringMapEntry.h:98
llvm::StringRef::count
LLVM_NODISCARD size_t count(char C) const
Return the number of occurrences of C in the string.
Definition: StringRef.h:489
llvm::StringRef::rtrim
LLVM_NODISCARD StringRef rtrim(char Char) const
Return string with consecutive Char characters starting from the right removed.
Definition: StringRef.h:856
llvm::FileCheckRequest::GlobalDefines
std::vector< StringRef > GlobalDefines
Definition: FileCheck.h:32
llvm::OverflowError
Class to represent an overflow error that might result when manipulating a value.
Definition: FileCheckImpl.h:109
llvm::FileCheckRequest::NoCanonicalizeWhiteSpace
bool NoCanonicalizeWhiteSpace
Definition: FileCheck.h:30
llvm::cl::Prefix
@ Prefix
Definition: CommandLine.h:164
llvm::FileCheckRequest::IsDefaultCheckPrefix
bool IsDefaultCheckPrefix
Definition: FileCheck.h:37
llvm::FileCheckString::CheckNext
bool CheckNext(const SourceMgr &SM, StringRef Buffer) const
Verifies that there is a single line in the given Buffer.
Note
We currently emits eax Perhaps this is what we really should generate is Is imull three or four cycles Note
Definition: README.txt:239
P
This currently compiles esp xmm0 movsd esp eax eax esp ret We should use not the dag combiner This is because dagcombine2 needs to be able to see through the X86ISD::Wrapper which DAGCombine can t really do The code for turning x load into a single vector load is target independent and should be moved to the dag combiner The code for turning x load into a vector load can only handle a direct load from a global or a direct load from the stack It should be generalized to handle any load from P
Definition: README-SSE.txt:411
llvm::StringSwitch::Default
LLVM_NODISCARD R Default(T Value)
Definition: StringSwitch.h:181
llvm::SMRange::End
SMLoc End
Definition: SMLoc.h:50
llvm::raw_string_ostream
A raw_ostream that writes to an std::string.
Definition: raw_ostream.h:625
llvm::FileCheckRequest::Verbose
bool Verbose
Definition: FileCheck.h:40
llvm::Check::CheckSame
@ CheckSame
Definition: FileCheck.h:50
llvm::NumericVariable::setValue
void setValue(ExpressionValue NewValue, Optional< StringRef > NewStrValue=None)
Sets value of this numeric variable to NewValue, and sets the input buffer string from which it was p...
Definition: FileCheckImpl.h:308
llvm::Check::CheckLabel
@ CheckLabel
Definition: FileCheck.h:53
llvm::StringRef::npos
static constexpr size_t npos
Definition: StringRef.h:60
llvm::StringRef::find
LLVM_NODISCARD size_t find(char C, size_t From=0) const
Search for the first character C in the string.
Definition: StringRef.h:315
llvm::SmallVector
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Definition: SmallVector.h:1168
llvm::FileCheck::~FileCheck
~FileCheck()
llvm::Error::success
static ErrorSuccess success()
Create a success value.
Definition: Error.h:331
llvm::FileCheckString::Loc
SMLoc Loc
The location in the match file that the check string was specified.
Definition: FileCheckImpl.h:873
llvm::StringRef::ltrim
LLVM_NODISCARD StringRef ltrim(char Char) const
Return string with consecutive Char characters starting from the the left removed.
Definition: StringRef.h:842
popFront
static char popFront(StringRef &S)
Definition: FileCheck.cpp:469
llvm::StringRef::consume_front
bool consume_front(StringRef Prefix)
Returns true if this StringRef has the given prefix and removes that prefix.
Definition: StringRef.h:682
llvm::tgtok::VarName
@ VarName
Definition: TGLexer.h:71
getAsSigned
static int64_t getAsSigned(uint64_t UnsignedValue)
Definition: FileCheck.cpp:160
llvm::Check::FileCheckType::setCount
FileCheckType & setCount(int C)
llvm::UndefVarError::ID
static char ID
Definition: FileCheckImpl.h:220
llvm::Pattern::parsePattern
bool parsePattern(StringRef PatternStr, StringRef Prefix, SourceMgr &SM, const FileCheckRequest &Req)
Parses the pattern in PatternStr and initializes this Pattern instance accordingly.
Definition: FileCheck.cpp:916
llvm::Type
The instances of the Type class are immutable: once they are created, they are never changed.
Definition: Type.h:45
llvm::NumericVariableUse::eval
Expected< ExpressionValue > eval() const override
Definition: FileCheck.cpp:365
llvm::FileCheckDiag::FileCheckDiag
FileCheckDiag(const SourceMgr &SM, const Check::FileCheckType &CheckTy, SMLoc CheckLoc, MatchType MatchTy, SMRange InputRange, StringRef Note="")
llvm::Pattern::MatchResult
Definition: FileCheckImpl.h:738
llvm::Optional< int64_t >
llvm::FileCheck::checkInput
bool checkInput(SourceMgr &SM, StringRef Buffer, std::vector< FileCheckDiag > *Diags=nullptr)
Checks the input to FileCheck provided in the Buffer against the expected strings read from the check...
Offset
uint64_t Offset
Definition: ELFObjHandler.cpp:81
llvm::FileCheckPatternContext::clearLocalVars
void clearLocalVars()
Undefines local variables (variables whose name does not start with a '$' sign), i....
llvm::SourceMgr::DK_Note
@ DK_Note
Definition: SourceMgr.h:37
llvm::errs
raw_fd_ostream & errs()
This returns a reference to a raw_ostream for standard error.
Definition: raw_ostream.cpp:893
llvm::StringSet::insert
std::pair< typename Base::iterator, bool > insert(StringRef key)
Definition: StringSet.h:33
llvm::MipsISD::Ret
@ Ret
Definition: MipsISelLowering.h:116
llvm::Expected
Tagged union holding either a T or a Error.
Definition: APFloat.h:42
STLExtras.h
llvm::DiagnosticPredicateTy::Match
@ Match
llvm::StringRef::slice
LLVM_NODISCARD StringRef slice(size_t Start, size_t End) const
Return a reference to the substring from [Start, End).
Definition: StringRef.h:732
llvm::FileCheckPatternContext::getPatternVarValue
Expected< StringRef > getPatternVarValue(StringRef VarName)
llvm::Pattern::match
MatchResult match(StringRef Buffer, const SourceMgr &SM) const
Matches the pattern string against the input buffer Buffer.
llvm::Regex::match
bool match(StringRef String, SmallVectorImpl< StringRef > *Matches=nullptr, std::string *Error=nullptr) const
matches - Match the regex against a given String.
Definition: Regex.cpp:86
llvm::consumeError
void consumeError(Error Err)
Consume a Error without doing anything.
Definition: Error.h:1045
llvm::MemoryBuffer
This interface provides simple read-only access to a block of memory, and provides simple methods for...
Definition: MemoryBuffer.h:50
llvm::ArrayRef::empty
bool empty() const
empty - Check if the array is empty.
Definition: ArrayRef.h:160
llvm::operator/
Align operator/(Align Lhs, uint64_t Divisor)
Definition: Alignment.h:327
llvm::NumericVariable::getImplicitFormat
ExpressionFormat getImplicitFormat() const
Definition: FileCheckImpl.h:293
llvm::SourceMgr::DK_Remark
@ DK_Remark
Definition: SourceMgr.h:36
Context
LLVMContext & Context
Definition: NVVMIntrRange.cpp:66
llvm::ExpressionValue::getAbsolute
ExpressionValue getAbsolute() const
Definition: FileCheck.cpp:188
llvm::StringRef::substr
LLVM_NODISCARD StringRef substr(size_t Start, size_t N=npos) const
Return a reference to the substring from [Start, Start + N).
Definition: StringRef.h:611
Arg
amdgpu Simplify well known AMD library false FunctionCallee Value * Arg
Definition: AMDGPULibCalls.cpp:206
llvm::Pattern::printSubstitutions
void printSubstitutions(const SourceMgr &SM, StringRef Buffer, SMRange MatchRange, FileCheckDiag::MatchType MatchTy, std::vector< FileCheckDiag > *Diags) const
Prints the value of successful substitutions.
llvm::FileCheck::buildCheckPrefixRegex
Regex buildCheckPrefixRegex()
llvm::formatv
auto formatv(const char *Fmt, Ts &&... Vals) -> formatv_object< decltype(std::make_tuple(detail::build_format_adapter(std::forward< Ts >(Vals))...))>
Definition: FormatVariadic.h:250
llvm::StringLiteral
A wrapper around a string literal that serves as a proxy for constructing global tables of StringRefs...
Definition: StringRef.h:891
llvm::ErrorReported
An error that has already been reported.
Definition: FileCheckImpl.h:594
llvm::checkedSub
std::enable_if_t< std::is_signed< T >::value, llvm::Optional< T > > checkedSub(T LHS, T RHS)
Subtract two signed integers LHS and RHS.
Definition: CheckedArithmetic.h:57
llvm::AArch64CC::VC
@ VC
Definition: AArch64BaseInfo.h:262
llvm::BinaryOperation::eval
Expected< ExpressionValue > eval() const override
Evaluates the value of the binary operation represented by this AST, using EvalBinop on the result of...
Definition: FileCheck.cpp:373
llvm::SMLoc
Represents a location in source code.
Definition: SMLoc.h:23
llvm::ExpressionFormat
Type representing the format an expression value should be textualized into for matching.
Definition: FileCheckImpl.h:39
CheckedArithmetic.h
llvm::StringRef::take_front
LLVM_NODISCARD StringRef take_front(size_t N=1) const
Return a StringRef equal to 'this' but with only the first N elements remaining.
Definition: StringRef.h:620
llvm::MemoryBuffer::getBufferEnd
const char * getBufferEnd() const
Definition: MemoryBuffer.h:66
E
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
llvm::ErrorDiagnostic
Class to represent an error holding a diagnostic with location information used when printing it.
Definition: FileCheckImpl.h:536
llvm::StringRef::split
LLVM_NODISCARD std::pair< StringRef, StringRef > split(char Separator) const
Split into two substrings around the first occurrence of a separator character.
Definition: StringRef.h:749
llvm::FileCheck::ValidateCheckPrefixes
bool ValidateCheckPrefixes()
llvm::MemoryBuffer::getBufferSize
size_t getBufferSize() const
Definition: MemoryBuffer.h:67
SpaceChars
constexpr StringLiteral SpaceChars
Definition: FileCheck.cpp:466
llvm::FileCheckRequest::CheckPrefixes
std::vector< StringRef > CheckPrefixes
Definition: FileCheck.h:28
C
(vector float) vec_cmpeq(*A, *B) C
Definition: README_ALTIVEC.txt:86
llvm::Expression::getAST
ExpressionAST * getAST() const
Definition: FileCheckImpl.h:253
llvm::NotFoundError
Definition: FileCheckImpl.h:570
llvm::ARM_PROC::A
@ A
Definition: ARMBaseInfo.h:34
Twine.h
llvm::NumericSubstitution::getResult
Expected< std::string > getResult() const override
Definition: FileCheck.cpp:418
llvm::Substitution::FromStr
StringRef FromStr
The string that needs to be substituted for something else.
Definition: FileCheckImpl.h:400
llvm::FileCheckDiag::MatchFoundAndExpected
@ MatchFoundAndExpected
Indicates a good match for an expected pattern.
Definition: FileCheck.h:129
llvm::ExpressionFormat::getMatchingString
Expected< std::string > getMatchingString(ExpressionValue Value) const
Definition: FileCheck.cpp:80
B
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
First
into llvm powi allowing the code generator to produce balanced multiplication trees First
Definition: README.txt:54
llvm::Pattern::getCheckTy
Check::FileCheckType getCheckTy() const
Definition: FileCheckImpl.h:771
llvm::Check::CheckNot
@ CheckNot
Definition: FileCheck.h:51
llvm::UndefVarError
Class to represent an undefined variable error, which quotes that variable's name when printed.
Definition: FileCheckImpl.h:215
llvm::StringRef::contains
LLVM_NODISCARD bool contains(StringRef Other) const
Return true if the given string is a substring of *this, and false otherwise.
Definition: StringRef.h:462
llvm::ExpressionValue::getSignedValue
Expected< int64_t > getSignedValue() const
Definition: FileCheck.cpp:170
llvm::operator-
APInt operator-(APInt)
Definition: APInt.h:2058
llvm::FileCheckPatternContext
Class holding the Pattern global state, shared by all patterns: tables holding values of variables an...
Definition: FileCheckImpl.h:459
llvm::OverflowError::ID
static char ID
Definition: FileCheckImpl.h:111
llvm::Pattern::parseVariable
static Expected< VariableProperties > parseVariable(StringRef &Str, const SourceMgr &SM)
Parses the string at the start of Str for a variable name.
Definition: FileCheck.cpp:440
llvm::FileCheckString::Check
size_t Check(const SourceMgr &SM, StringRef Buffer, bool IsLabelScanMode, size_t &MatchLen, FileCheckRequest &Req, std::vector< FileCheckDiag > *Diags) const
Matches check string and its "not strings" and/or "dag strings".
llvm::ErrorReported::reportedOrSuccess
static Error reportedOrSuccess(bool HasErrorReported)
Definition: FileCheckImpl.h:607
llvm::FileCheckDiag::MatchFoundButWrongLine
@ MatchFoundButWrongLine
Indicates a match for an expected pattern, but the match is on the wrong line.
Definition: FileCheck.h:134
c
the resulting code requires compare and branches when and if the revised code is with conditional branches instead of More there is a byte word extend before each where there should be only and the condition codes are not remembered when the same two values are compared twice More LSR enhancements i8 and i32 load store addressing modes are identical int int c
Definition: README.txt:418
FormatVariadic.h
llvm::StringRef::str
LLVM_NODISCARD std::string str() const
str - Get the contents as an std::string.
Definition: StringRef.h:245
llvm::None
const NoneType None
Definition: None.h:23
llvm::Check::FileCheckType::getDescription
std::string getDescription(StringRef Prefix) const
llvm::lltok::Kind
Kind
Definition: LLToken.h:18
llvm::FileCheckString::CheckNot
bool CheckNot(const SourceMgr &SM, StringRef Buffer, const std::vector< const Pattern * > &NotStrings, const FileCheckRequest &Req, std::vector< FileCheckDiag > *Diags) const
Verifies that none of the strings in NotStrings are found in the given Buffer.
llvm::SmallString< 256 >
FileCheckImpl.h
llvm::FileCheckString::Prefix
StringRef Prefix
Which prefix name this check matched.
Definition: FileCheckImpl.h:870
llvm::NumericVariable::getValue
Optional< ExpressionValue > getValue() const
Definition: FileCheckImpl.h:296
llvm::SmallString::append
void append(StringRef RHS)
Append from a StringRef.
Definition: SmallString.h:67
llvm::StringRef::trim
LLVM_NODISCARD StringRef trim(char Char) const
Return string with consecutive Char characters starting from the left and right removed.
Definition: StringRef.h:870
Check
static bool Check(DecodeStatus &Out, DecodeStatus In)
Definition: AArch64Disassembler.cpp:242
llvm::FileCheckDiag::MatchType
MatchType
What type of match result does this diagnostic describe?
Definition: FileCheck.h:127
llvm::ExpressionAST::eval
virtual Expected< ExpressionValue > eval() const =0
Evaluates and.
llvm::Check::FileCheckType
Definition: FileCheck.h:76
llvm::FileCheck::readCheckFile
bool readCheckFile(SourceMgr &SM, StringRef Buffer, Regex &PrefixRE, std::pair< unsigned, unsigned > *ImpPatBufferIDRange=nullptr)
Reads the check file from Buffer and records the expected strings it contains.
llvm::FileCheckString
A check that we found in the input file.
Definition: FileCheckImpl.h:865
llvm::Check::CheckNext
@ CheckNext
Definition: FileCheck.h:49
uint64_t
llvm::FileCheckDiag::MatchFoundButExcluded
@ MatchFoundButExcluded
Indicates a match for an excluded pattern.
Definition: FileCheck.h:131
llvm::Substitution
Class representing a substitution to perform in the RegExStr string.
Definition: FileCheckImpl.h:388
llvm::StringRef::end
iterator end() const
Definition: StringRef.h:130
llvm::NotFoundError::ID
static char ID
Definition: FileCheckImpl.h:572
llvm::SourceMgr::PrintMessage
void PrintMessage(raw_ostream &OS, SMLoc Loc, DiagKind Kind, const Twine &Msg, ArrayRef< SMRange > Ranges={}, ArrayRef< SMFixIt > FixIts={}, bool ShowColors=true) const
Emit a message about the specified location with the specified string.
Definition: SourceMgr.cpp:341
move
compiles ldr LCPI1_0 ldr ldr mov lsr tst moveq r1 ldr LCPI1_1 and r0 bx lr It would be better to do something like to fold the shift into the conditional move
Definition: README.txt:546
llvm::numbers::e
constexpr double e
Definition: MathExtras.h:57
llvm::StringRef::front
LLVM_NODISCARD char front() const
front - Get the first character in the string.
Definition: StringRef.h:161
I
#define I(x, y, z)
Definition: MD5.cpp:59
llvm::joinErrors
Error joinErrors(Error E1, Error E2)
Concatenate errors.
Definition: Error.h:428
llvm::is_contained
bool is_contained(R &&Range, const E &Element)
Wrapper function around std::find to detect if an element exists in a container.
Definition: STLExtras.h:1616
assert
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
std::swap
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
Definition: BitVector.h:840
memcpy
<%struct.s * > cast struct s *S to sbyte *< sbyte * > sbyte uint cast struct s *agg result to sbyte *< sbyte * > sbyte uint cast struct s *memtmp to sbyte *< sbyte * > sbyte uint ret void llc ends up issuing two memcpy or custom lower memcpy(of small size) to be ldmia/stmia. I think option 2 is better but the current register allocator cannot allocate a chunk of registers at a time. A feasible temporary solution is to use specific physical registers at the lowering time for small(<
llvm::ExpressionFormat::Kind::NoFormat
@ NoFormat
Denote absence of format.
llvm::StringRef::find_first_not_of
LLVM_NODISCARD size_t find_first_not_of(char C, size_t From=0) const
Find the first character in the string that is not C or npos if not found.
Definition: StringRef.cpp:241
llvm::Check::CheckBadCount
@ CheckBadCount
Marks when parsing found a -COUNT directive with invalid count value.
Definition: FileCheck.h:65
llvm::operator+
APInt operator+(APInt a, const APInt &b)
Definition: APInt.h:2063
llvm::Pattern::MatchResult::TheError
Error TheError
Definition: FileCheckImpl.h:740
llvm::StringRef::drop_back
LLVM_NODISCARD StringRef drop_back(size_t N=1) const
Return a StringRef equal to 'this' but with the last N elements dropped.
Definition: StringRef.h:661
llvm::FileCheck::FileCheck
FileCheck(FileCheckRequest Req)
llvm::Check::CheckBadNot
@ CheckBadNot
Marks when parsing found a -NOT check combined with another CHECK suffix.
Definition: FileCheck.h:62
llvm::Expression
Class representing an expression and its matching format.
Definition: FileCheckImpl.h:237
llvm::StringSet
StringSet - A wrapper for StringMap that provides set-like functionality.
Definition: StringSet.h:22
llvm::FileCheckString::CheckSame
bool CheckSame(const SourceMgr &SM, StringRef Buffer) const
Verifies that there is no newline in the given Buffer.
llvm::operator*
APInt operator*(APInt a, uint64_t RHS)
Definition: APInt.h:2105
llvm::FileCheckRequest::MatchFullLines
bool MatchFullLines
Definition: FileCheck.h:35
llvm::ArrayRef
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition: APInt.h:32
llvm::FileCheck::CanonicalizeFile
StringRef CanonicalizeFile(MemoryBuffer &MB, SmallVectorImpl< char > &OutputBuffer)
Canonicalizes whitespaces in the file.
llvm::min
Expected< ExpressionValue > min(const ExpressionValue &Lhs, const ExpressionValue &Rhs)
Definition: FileCheck.cpp:357
llvm::Pattern::parseNumericSubstitutionBlock
static Expected< std::unique_ptr< Expression > > parseNumericSubstitutionBlock(StringRef Expr, Optional< NumericVariable * > &DefinedNumericVariable, bool IsLegacyLineExpr, Optional< size_t > LineNumber, FileCheckPatternContext *Context, const SourceMgr &SM)
Parses Expr for a numeric substitution block at line LineNumber, or before input is parsed if LineNum...
Definition: FileCheck.cpp:767
llvm::StringRef
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:58
llvm_unreachable
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
Definition: ErrorHandling.h:134
llvm::cantFail
void cantFail(Error Err, const char *Msg=nullptr)
Report a fatal error if Err is a failure value.
Definition: Error.h:747
llvm::ErrorReported::ID
static char ID
Definition: FileCheckImpl.h:596
llvm::SourceMgr
This owns the files read by a parser, handles include stacks, and handles diagnostic wrangling.
Definition: SourceMgr.h:31
S
add sub stmia L5 ldr r0 bl L_printf $stub Instead of a and a wouldn t it be better to do three moves *Return an aggregate type is even return S
Definition: README.txt:210
llvm::FileCheckDiag::MatchFuzzy
@ MatchFuzzy
Indicates a fuzzy match that serves as a suggestion for the next intended match for an expected patte...
Definition: FileCheck.h:156
llvm::Regex::IgnoreCase
@ IgnoreCase
Compile for matching that ignores upper/lower case distinctions.
Definition: Regex.h:33
llvm::StringRef::consumeInteger
std::enable_if_t< std::numeric_limits< T >::is_signed, bool > consumeInteger(unsigned Radix, T &Result)
Parse the current string as an integer of the specified radix.
Definition: StringRef.h:544
llvm::ExpressionValue::getUnsignedValue
Expected< uint64_t > getUnsignedValue() const
Definition: FileCheck.cpp:181
llvm::Regex::Newline
@ Newline
Compile for newline-sensitive matching.
Definition: Regex.h:39
llvm::logAllUnhandledErrors
void logAllUnhandledErrors(Error E, raw_ostream &OS, Twine ErrorBanner={})
Log all errors (if any) in E to OS.
Definition: Error.cpp:61
llvm::tgtok::StrVal
@ StrVal
Definition: TGLexer.h:71
StringSet.h
j
return j(j<< 16)
llvm::Pattern::printFuzzyMatch
void printFuzzyMatch(const SourceMgr &SM, StringRef Buffer, std::vector< FileCheckDiag > *Diags) const
llvm::FileCheckRequest::EnableVarScope
bool EnableVarScope
Definition: FileCheck.h:38
llvm::Twine
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
Definition: Twine.h:83
llvm::Check::CheckDAG
@ CheckDAG
Definition: FileCheck.h:52
llvm::Pattern::getCount
int getCount() const
Definition: FileCheckImpl.h:773
llvm::createStringError
Error createStringError(std::error_code EC, char const *Fmt, const Ts &... Vals)
Create formatted StringError object.
Definition: Error.h:1241
llvm::MemoryBuffer::getBufferStart
const char * getBufferStart() const
Definition: MemoryBuffer.h:65
llvm::GraphProgram::Name
Name
Definition: GraphWriter.h:52
std
Definition: BitVector.h:838
llvm::StringRef::drop_front
LLVM_NODISCARD StringRef drop_front(size_t N=1) const
Return a StringRef equal to 'this' but with the first N elements dropped.
Definition: StringRef.h:653
llvm::Check::CheckEmpty
@ CheckEmpty
Definition: FileCheck.h:54
llvm::ExpressionFormat::getWildcardRegex
Expected< std::string > getWildcardRegex() const
Definition: FileCheck.cpp:47
llvm::Error
Lightweight error class with error context and mandatory checking.
Definition: Error.h:157
llvm::ErrorDiagnostic::ID
static char ID
Definition: FileCheckImpl.h:542
llvm::sort
void sort(IteratorTy Start, IteratorTy End)
Definition: STLExtras.h:1492
llvm::TargetStackID::Value
Value
Definition: TargetFrameLowering.h:27
llvm::Substitution::getResult
virtual Expected< std::string > getResult() const =0
llvm::ExpressionFormat::valueFromStringRepr
Expected< ExpressionValue > valueFromStringRepr(StringRef StrVal, const SourceMgr &SM) const
Definition: FileCheck.cpp:128
llvm::SourceMgr::DK_Error
@ DK_Error
Definition: SourceMgr.h:34
llvm::Check::FileCheckType::getModifiersDescription
std::string getModifiersDescription() const
llvm::SourceMgr::AddNewSourceBuffer
unsigned AddNewSourceBuffer(std::unique_ptr< MemoryBuffer > F, SMLoc IncludeLoc)
Add a new source buffer to this source manager.
Definition: SourceMgr.h:141
llvm::SmallVectorImpl::clear
void clear()
Definition: SmallVector.h:585
llvm::ErrorDiagnostic::get
static Error get(const SourceMgr &SM, SMLoc Loc, const Twine &ErrMsg, SMRange Range=None)
Definition: FileCheckImpl.h:557
llvm::FileCheckDiag::MatchFoundButDiscarded
@ MatchFoundButDiscarded
Indicates a discarded match for an expected pattern.
Definition: FileCheck.h:136
llvm::FileCheckRequest::CommentPrefixes
std::vector< StringRef > CommentPrefixes
Definition: FileCheck.h:29
llvm::FileCheckRequest::IgnoreCase
bool IgnoreCase
Definition: FileCheck.h:36
llvm::Expected::takeError
Error takeError()
Take ownership of the stored error.
Definition: Error.h:599
llvm::Pattern
Definition: FileCheckImpl.h:614
llvm::Substitution::getIndex
size_t getIndex() const
Definition: FileCheckImpl.h:416
llvm::FileCheckRequest
Contains info about various FileCheck options.
Definition: FileCheck.h:27
llvm::FileCheckRequest::VerboseVerbose
bool VerboseVerbose
Definition: FileCheck.h:41
exit
declare void exit(i32) noreturn nounwind This compiles into
Definition: README.txt:1072
llvm::SMRange
Represents a range in source code.
Definition: SMLoc.h:48
llvm::Check::CheckPlain
@ CheckPlain
Definition: FileCheck.h:48
llvm::FileCheckPatternContext::defineCmdlineVariables
Error defineCmdlineVariables(ArrayRef< StringRef > CmdlineDefines, SourceMgr &SM)
Defines string and numeric variables from definitions given on the command line, passed as a vector o...
llvm::Pattern::isValidVarNameStart
static bool isValidVarNameStart(char C)
Definition: FileCheck.cpp:437
llvm::max
Align max(MaybeAlign Lhs, Align Rhs)
Definition: Alignment.h:340
llvm::Pattern::printVariableDefs
void printVariableDefs(const SourceMgr &SM, FileCheckDiag::MatchType MatchTy, std::vector< FileCheckDiag > *Diags) const
llvm::raw_svector_ostream
A raw_ostream that writes to an SmallVector or SmallString.
Definition: raw_ostream.h:658
llvm::StringRef::data
const LLVM_NODISCARD char * data() const
data - Get a pointer to the start of the string (which may not be null terminated).
Definition: StringRef.h:149
llvm::SmallVectorImpl< char >
llvm::SMLoc::getFromPointer
static SMLoc getFromPointer(const char *Ptr)
Definition: SMLoc.h:36
llvm::StringRef::find_insensitive
LLVM_NODISCARD size_t find_insensitive(char C, size_t From=0) const
Search for the first character C in the string, ignoring case.
Definition: StringRef.cpp:55
llvm::BinaryOperation::getImplicitFormat
Expected< ExpressionFormat > getImplicitFormat(const SourceMgr &SM) const override
Definition: FileCheck.cpp:392
llvm::StringSwitch
A switch()-like statement whose cases are string literals.
Definition: StringSwitch.h:42
llvm::Pattern::getLoc
SMLoc getLoc() const
Definition: FileCheckImpl.h:689
llvm::NumericVariable::getDefLineNumber
Optional< size_t > getDefLineNumber() const
Definition: FileCheckImpl.h:323
llvm::NumericVariable
Class representing a numeric variable and its associated current value.
Definition: FileCheckImpl.h:259
llvm::Check::CheckNone
@ CheckNone
Definition: FileCheck.h:47
llvm::ExpressionAST::getExpressionStr
StringRef getExpressionStr() const
Definition: FileCheckImpl.h:182
llvm::Substitution::Context
FileCheckPatternContext * Context
Pointer to a class instance holding, among other things, the table with the values of live string var...
Definition: FileCheckImpl.h:396
llvm::StringRef::edit_distance
LLVM_NODISCARD unsigned edit_distance(StringRef Other, bool AllowReplacements=true, unsigned MaxEditDistance=0) const
Determine the edit distance between this string and another string.
Definition: StringRef.cpp:92
llvm::StringRef::find_first_of
LLVM_NODISCARD size_t find_first_of(char C, size_t From=0) const
Find the first character in the string that is C, or npos if not found.
Definition: StringRef.h:410
llvm::SourceMgr::getLineAndColumn
std::pair< unsigned, unsigned > getLineAndColumn(SMLoc Loc, unsigned BufferID=0) const
Find the line and column number for the specified location in the specified file.
Definition: SourceMgr.cpp:180
llvm::ExpressionFormat::toString
StringRef toString() const
Definition: FileCheck.cpp:31
llvm::Check::FileCheckType::isLiteralMatch
bool isLiteralMatch() const
Definition: FileCheck.h:93
llvm::FileCheckString::CheckDag
size_t CheckDag(const SourceMgr &SM, StringRef Buffer, std::vector< const Pattern * > &NotStrings, const FileCheckRequest &Req, std::vector< FileCheckDiag > *Diags) const
Matches "dag strings" and their mixed "not strings".
llvm::AMDGPU::HSAMD::Kernel::Key::Args
constexpr char Args[]
Key for Kernel::Metadata::mArgs.
Definition: AMDGPUMetadata.h:389
llvm::Regex
Definition: Regex.h:28
llvm::FileCheckRequest::ImplicitCheckNot
std::vector< StringRef > ImplicitCheckNot
Definition: FileCheck.h:31
llvm::StringRef::size
LLVM_NODISCARD size_t size() const
size - Get the string size.
Definition: StringRef.h:157
llvm::MemoryBuffer::getMemBufferCopy
static std::unique_ptr< MemoryBuffer > getMemBufferCopy(StringRef InputData, const Twine &BufferName="")
Open the specified memory range as a MemoryBuffer, copying the contents and taking ownership of it.
Definition: MemoryBuffer.cpp:136
llvm::SmallVectorImpl::reserve
void reserve(size_type N)
Definition: SmallVector.h:624
llvm::Substitution::getFromString
StringRef getFromString() const
Definition: FileCheckImpl.h:413
llvm::StringRef::begin
iterator begin() const
Definition: StringRef.h:128
llvm::pdb::PDB_SymType::Block
@ Block
llvm::FileCheckPatternContext::createLineVariable
void createLineVariable()
Create @LINE pseudo variable.
llvm::FileCheckRequest::AllowUnusedPrefixes
bool AllowUnusedPrefixes
Definition: FileCheck.h:34
llvm::ExpressionFormat::Kind::HexLower
@ HexLower
Value should be printed as a lowercase hex number.
llvm::handleAllErrors
void handleAllErrors(Error E, HandlerTs &&... Handlers)
Behaves the same as handleErrors, except that by contract all errors must be handled by the given han...
Definition: Error.h:968
llvm::Value
LLVM Value Representation.
Definition: Value.h:74
llvm::Check::CheckEOF
@ CheckEOF
Indicates the pattern only matches the end of file.
Definition: FileCheck.h:59
llvm::Check::CheckComment
@ CheckComment
Definition: FileCheck.h:55
llvm::Optional::getValue
constexpr const T & getValue() const LLVM_LVALUE_FUNCTION
Definition: Optional.h:282
llvm::Pattern::MatchResult::TheMatch
Optional< Match > TheMatch
Definition: FileCheckImpl.h:739
llvm::Pattern::VariableProperties
Parsing information about a variable.
Definition: FileCheckImpl.h:699
llvm::ExpressionFormat::Kind::HexUpper
@ HexUpper
Value should be printed as an uppercase hex number.
llvm::AbsoluteDifference
std::enable_if_t< std::is_unsigned< T >::value, T > AbsoluteDifference(T X, T Y)
Subtract two unsigned integers, X and Y, of type T and return the absolute value of the result.
Definition: MathExtras.h:794
llvm::FileCheckString::DagNotStrings
std::vector< Pattern > DagNotStrings
All of the strings that are disallowed from occurring between this match string and the previous one ...
Definition: FileCheckImpl.h:877
llvm::remarks::Format
Format
The format used for serializing/deserializing remarks.
Definition: RemarkFormat.h:25
llvm::Regex::escape
static std::string escape(StringRef String)
Turn String into a regex by escaping its special characters.
Definition: Regex.cpp:219