@@ -1560,9 +1560,9 @@ static size_t commonPrefixLength(StringRef shorter, StringRef longer) {
1560
1560
1561
1561
// / getMultilineTrailingIndent:
1562
1562
// / Determine trailing indent to be used for multiline literal indent stripping.
1563
- static std::tuple< StringRef, SourceLoc>
1564
- getMultilineTrailingIndent (const Token &Str , DiagnosticEngine *Diags) {
1565
- StringRef Bytes = getStringLiteralContent (Str);
1563
+ StringRef
1564
+ getMultilineTrailingIndent (StringRef Bytes , DiagnosticEngine *Diags = nullptr ,
1565
+ unsigned CustomDelimiterLen = 0 ) {
1566
1566
const char *begin = Bytes.begin (), *end = Bytes.end (), *start = end;
1567
1567
bool sawNonWhitespace = false ;
1568
1568
@@ -1575,11 +1575,9 @@ getMultilineTrailingIndent(const Token &Str, DiagnosticEngine *Diags) {
1575
1575
case ' \n ' :
1576
1576
case ' \r ' : {
1577
1577
++start;
1578
- auto startLoc = Lexer::getSourceLoc (start);
1579
- auto string = StringRef (start, end - start);
1580
1578
1581
1579
// Disallow escaped newline in the last line.
1582
- if (Diags && Str. getCustomDelimiterLen () == 0 ) {
1580
+ if (Diags && !CustomDelimiterLen ) {
1583
1581
auto *Ptr = start - 1 ;
1584
1582
if (*Ptr == ' \n ' ) --Ptr;
1585
1583
if (*Ptr == ' \r ' ) --Ptr;
@@ -1595,7 +1593,7 @@ getMultilineTrailingIndent(const Token &Str, DiagnosticEngine *Diags) {
1595
1593
}
1596
1594
}
1597
1595
1598
- return std::make_tuple (string, startLoc );
1596
+ return StringRef (start, end - start );
1599
1597
}
1600
1598
default :
1601
1599
sawNonWhitespace = true ;
@@ -1609,7 +1607,7 @@ getMultilineTrailingIndent(const Token &Str, DiagnosticEngine *Diags) {
1609
1607
.fixItInsert (loc, " \n " );
1610
1608
}
1611
1609
1612
- return std::make_tuple ( " " , Lexer::getSourceLoc (end - 1 )) ;
1610
+ return " " ;
1613
1611
}
1614
1612
1615
1613
// / diagnoseInvalidMultilineIndents:
@@ -1673,12 +1671,13 @@ static void diagnoseInvalidMultilineIndents(
1673
1671
// / Diagnose contents of string literal that have inconsistent indentation.
1674
1672
static void validateMultilineIndents (const Token &Str,
1675
1673
DiagnosticEngine *Diags) {
1676
- StringRef Indent ;
1677
- SourceLoc IndentStartLoc;
1678
- std::tie (Indent, IndentStartLoc) = getMultilineTrailingIndent (Str , Diags);
1674
+ StringRef Bytes = getStringLiteralContent (Str) ;
1675
+ StringRef Indent =
1676
+ getMultilineTrailingIndent (Bytes , Diags, Str. getCustomDelimiterLen () );
1679
1677
if (Indent.empty ())
1680
1678
return ;
1681
-
1679
+ SourceLoc IndentStartLoc = Lexer::getSourceLoc (Indent.data ());
1680
+
1682
1681
// The offset into the previous line where it experienced its first indentation
1683
1682
// error, or Indent.size() if every character matched.
1684
1683
size_t lastMistakeOffset = std::numeric_limits<size_t >::max ();
@@ -1688,7 +1687,6 @@ static void validateMultilineIndents(const Token &Str,
1688
1687
// Prefix of indentation that's present on all lines in linesWithLastMatchLength.
1689
1688
StringRef commonIndentation = " " ;
1690
1689
1691
- StringRef Bytes = getStringLiteralContent (Str);
1692
1690
for (size_t pos = Bytes.find (' \n ' ); pos != StringRef::npos; pos = Bytes.find (' \n ' , pos + 1 )) {
1693
1691
size_t nextpos = pos + 1 ;
1694
1692
auto restOfBytes = Bytes.substr (nextpos);
@@ -2109,6 +2107,11 @@ StringRef Lexer::getEncodedStringSegmentImpl(StringRef Bytes,
2109
2107
// BytesPtr to avoid a range check subscripting on the StringRef.
2110
2108
const char *BytesPtr = Bytes.begin ();
2111
2109
2110
+ // Special case when being called from EncodedDiagnosticMessage(...)
2111
+ // This should allow multiline strings to work as attribute messages.
2112
+ if (IndentToStrip == ~0U )
2113
+ IndentToStrip = getMultilineTrailingIndent (Bytes).size ();
2114
+
2112
2115
bool IsEscapedNewline = false ;
2113
2116
while (BytesPtr < Bytes.end ()) {
2114
2117
char CurChar = *BytesPtr++;
@@ -2203,8 +2206,7 @@ void Lexer::getStringLiteralSegments(
2203
2206
bool MultilineString = Str.isMultilineString (), IsFirstSegment = true ;
2204
2207
unsigned IndentToStrip = 0 , CustomDelimiterLen = Str.getCustomDelimiterLen ();
2205
2208
if (MultilineString)
2206
- IndentToStrip =
2207
- std::get<0 >(getMultilineTrailingIndent (Str, /* Diags=*/ nullptr )).size ();
2209
+ IndentToStrip = getMultilineTrailingIndent (Bytes).size ();
2208
2210
2209
2211
// Note that it is always safe to read one over the end of "Bytes" because
2210
2212
// we know that there is a terminating " character. Use BytesPtr to avoid a
0 commit comments