@@ -33,7 +33,7 @@ void forEachToken(const UnwrappedLine &Line, const T &Call,
3333 FormatToken *Parent = nullptr ) {
3434 bool First = true ;
3535 for (const auto &N : Line.Tokens ) {
36- Call (N.Tok , Parent, First);
36+ Call (N.Tok , Parent, First, Line. Level );
3737 First = false ;
3838 for (const auto &Child : N.Children )
3939 forEachToken (Child, Call, N.Tok );
@@ -44,26 +44,25 @@ MacroCallReconstructor::MacroCallReconstructor(
4444 unsigned Level,
4545 const llvm::DenseMap<FormatToken *, std::unique_ptr<UnwrappedLine>>
4646 &ActiveExpansions)
47- : Level (Level), IdToReconstructed(ActiveExpansions) {
47+ : Result (Level), IdToReconstructed(ActiveExpansions) {
4848 Result.Tokens .push_back (std::make_unique<LineNode>());
4949 ActiveReconstructedLines.push_back (&Result);
5050}
5151
5252void MacroCallReconstructor::addLine (const UnwrappedLine &Line) {
5353 assert (State != Finalized);
5454 LLVM_DEBUG (llvm::dbgs () << " MCR: new line...\n " );
55- forEachToken (Line, [&](FormatToken *Token, FormatToken *Parent, bool First) {
56- add (Token, Parent, First);
57- });
55+ forEachToken (Line, [&](FormatToken *Token, FormatToken *Parent, bool First,
56+ unsigned Level) { add (Token, Parent, First, Level); });
5857 assert (InProgress || finished ());
5958}
6059
6160UnwrappedLine MacroCallReconstructor::takeResult () && {
6261 finalize ();
6362 assert (Result.Tokens .size () == 1 &&
6463 Result.Tokens .front ()->Children .size () == 1 );
65- UnwrappedLine Final =
66- createUnwrappedLine ( *Result.Tokens .front ()->Children .front (), Level);
64+ UnwrappedLine Final = createUnwrappedLine (
65+ *Result.Tokens .front ()->Children .front (), Result. Level );
6766 assert (!Final.Tokens .empty ());
6867 return Final;
6968}
@@ -72,7 +71,8 @@ UnwrappedLine MacroCallReconstructor::takeResult() && {
7271// ExpandedParent in the incoming unwrapped line. \p First specifies whether it
7372// is the first token in a given unwrapped line.
7473void MacroCallReconstructor::add (FormatToken *Token,
75- FormatToken *ExpandedParent, bool First) {
74+ FormatToken *ExpandedParent, bool First,
75+ unsigned Level) {
7676 LLVM_DEBUG (
7777 llvm::dbgs () << " MCR: Token: " << Token->TokenText << " , Parent: "
7878 << (ExpandedParent ? ExpandedParent->TokenText : " <null>" )
@@ -102,7 +102,7 @@ void MacroCallReconstructor::add(FormatToken *Token,
102102 First = true ;
103103 }
104104
105- prepareParent (ExpandedParent, First);
105+ prepareParent (ExpandedParent, First, Level );
106106
107107 if (Token->MacroCtx ) {
108108 // If this token was generated by a macro call, add the reconstructed
@@ -129,7 +129,7 @@ void MacroCallReconstructor::add(FormatToken *Token,
129129// is the parent of ActiveReconstructedLines.back() in the reconstructed
130130// unwrapped line.
131131void MacroCallReconstructor::prepareParent (FormatToken *ExpandedParent,
132- bool NewLine) {
132+ bool NewLine, unsigned Level ) {
133133 LLVM_DEBUG ({
134134 llvm::dbgs () << " ParentMap:\n " ;
135135 debugParentMap ();
@@ -172,7 +172,7 @@ void MacroCallReconstructor::prepareParent(FormatToken *ExpandedParent,
172172 }
173173 assert (!ActiveReconstructedLines.empty ());
174174 ActiveReconstructedLines.back ()->Tokens .back ()->Children .push_back (
175- std::make_unique<ReconstructedLine>());
175+ std::make_unique<ReconstructedLine>(Level ));
176176 ActiveReconstructedLines.push_back (
177177 &*ActiveReconstructedLines.back ()->Tokens .back ()->Children .back ());
178178 } else if (parentLine ().Tokens .back ()->Tok != Parent) {
@@ -424,7 +424,8 @@ bool MacroCallReconstructor::processNextReconstructed() {
424424 SpelledParentToReconstructedParent[MacroCallStructure.back ()
425425 .ParentLastToken ] = Token;
426426 appendToken (Token);
427- prepareParent (Token, /* NewLine=*/ true );
427+ prepareParent (Token, /* NewLine=*/ true ,
428+ MacroCallStructure.back ().Line ->Level );
428429 Token->MacroParent = true ;
429430 return false ;
430431 }
@@ -435,7 +436,8 @@ bool MacroCallReconstructor::processNextReconstructed() {
435436 [MacroCallStructure.back ().Line ->Tokens .back ()->Tok ] = Token;
436437 Token->MacroParent = true ;
437438 appendToken (Token, MacroCallStructure.back ().Line );
438- prepareParent (Token, /* NewLine=*/ true );
439+ prepareParent (Token, /* NewLine=*/ true ,
440+ MacroCallStructure.back ().Line ->Level );
439441 return true ;
440442 }
441443 if (Token->is (tok::r_paren)) {
@@ -509,16 +511,36 @@ MacroCallReconstructor::createUnwrappedLine(const ReconstructedLine &Line,
509511 for (const auto &N : Line.Tokens ) {
510512 Result.Tokens .push_back (N->Tok );
511513 UnwrappedLineNode &Current = Result.Tokens .back ();
512- for (const auto &Child : N->Children ) {
513- if (Child->Tokens .empty ())
514- continue ;
515- Current.Children .push_back (createUnwrappedLine (*Child, Level + 1 ));
516- }
517- if (Current.Children .size () == 1 &&
518- Current.Tok ->isOneOf (tok::l_paren, tok::comma)) {
519- Result.Tokens .splice (Result.Tokens .end (),
520- Current.Children .front ().Tokens );
521- Current.Children .clear ();
514+ auto NumChildren =
515+ std::count_if (N->Children .begin (), N->Children .end (),
516+ [](const auto &Child) { return !Child->Tokens .empty (); });
517+ if (NumChildren == 1 && Current.Tok ->isOneOf (tok::l_paren, tok::comma)) {
518+ // If we only have one child, and the child is due to a macro expansion
519+ // (either attached to a left parenthesis or comma), merge the child into
520+ // the current line to prevent forced breaks for macro arguments.
521+ auto *Child = std::find_if (
522+ N->Children .begin (), N->Children .end (),
523+ [](const auto &Child) { return !Child->Tokens .empty (); });
524+ auto Line = createUnwrappedLine (**Child, Level);
525+ Result.Tokens .splice (Result.Tokens .end (), Line.Tokens );
526+ } else if (NumChildren > 0 ) {
527+ // When there are multiple children with different indent, make sure that
528+ // we indent them:
529+ // 1. One level below the current line's level.
530+ // 2. At the correct level relative to each other.
531+ unsigned MinChildLevel =
532+ std::min_element (N->Children .begin (), N->Children .end (),
533+ [](const auto &E1 , const auto &E2 ) {
534+ return E1 ->Level < E2 ->Level ;
535+ })
536+ ->get ()
537+ ->Level ;
538+ for (const auto &Child : N->Children ) {
539+ if (Child->Tokens .empty ())
540+ continue ;
541+ Current.Children .push_back (createUnwrappedLine (
542+ *Child, Level + 1 + (Child->Level - MinChildLevel)));
543+ }
522544 }
523545 }
524546 return Result;
0 commit comments