@@ -61,8 +61,10 @@ namespace llvm {
6161 for (bool _c = \
6262 (::llvm::DebugFlag && ::llvm::isCurrentDebugType(TYPE, LEVEL)); \
6363 _c; _c = false ) \
64+ for (::llvm::impl::RAIINewLineStream NewLineStream{(STREAM)}; _c; \
65+ _c = false ) \
6466 ::llvm::impl::raw_ldbg_ostream{ \
65- ::llvm::impl::computePrefix (TYPE, FILE, LINE, LEVEL), (STREAM)} \
67+ ::llvm::impl::computePrefix (TYPE, FILE, LINE, LEVEL), NewLineStream} \
6668 .asLvalue ()
6769
6870#define DEBUGLOG_WITH_STREAM_TYPE_AND_FILE (STREAM, LEVEL, TYPE, FILE ) \
@@ -81,14 +83,15 @@ namespace llvm {
8183
8284namespace impl {
8385
84- // / A raw_ostream that tracks `\n` and print the prefix.
86+ // / A raw_ostream that tracks `\n` and print the prefix after each
87+ // / newline.
8588class LLVM_ABI raw_ldbg_ostream final : public raw_ostream {
8689 std::string Prefix;
8790 raw_ostream &Os;
88- bool HasPendingNewline = true ;
91+ bool HasPendingNewline;
8992
90- // / Split the line on newlines and insert the prefix before each newline.
91- // / Forward everything to the underlying stream.
93+ // / Split the line on newlines and insert the prefix before each
94+ // / newline. Forward everything to the underlying stream.
9295 void write_impl (const char *Ptr, size_t Size) final {
9396 auto Str = StringRef (Ptr, Size);
9497 // Handle the initial prefix.
@@ -109,22 +112,18 @@ class LLVM_ABI raw_ldbg_ostream final : public raw_ostream {
109112 }
110113 void emitPrefix () { Os.write (Prefix.c_str (), Prefix.size ()); }
111114 void writeWithPrefix (StringRef Str) {
112- if (HasPendingNewline) {
113- emitPrefix ();
114- HasPendingNewline = false ;
115- }
115+ flushEol ();
116116 Os.write (Str.data (), Str.size ());
117117 }
118118
119119public:
120- explicit raw_ldbg_ostream (std::string Prefix, raw_ostream &Os)
121- : Prefix(std::move(Prefix)), Os(Os) {
120+ explicit raw_ldbg_ostream (std::string Prefix, raw_ostream &Os,
121+ bool HasPendingNewline = true )
122+ : Prefix(std::move(Prefix)), Os(Os),
123+ HasPendingNewline(HasPendingNewline) {
122124 SetUnbuffered ();
123125 }
124- ~raw_ldbg_ostream () final {
125- flushEol ();
126- Os << ' \n ' ;
127- }
126+ ~raw_ldbg_ostream () final { flushEol (); }
128127 void flushEol () {
129128 if (HasPendingNewline) {
130129 emitPrefix ();
@@ -135,10 +134,22 @@ class LLVM_ABI raw_ldbg_ostream final : public raw_ostream {
135134 // / Forward the current_pos method to the underlying stream.
136135 uint64_t current_pos () const final { return Os.tell (); }
137136
138- // / Some of the `<<` operators expect an lvalue, so we trick the type system.
137+ // / Some of the `<<` operators expect an lvalue, so we trick the type
138+ // / system.
139139 raw_ldbg_ostream &asLvalue () { return *this ; }
140140};
141141
142+ // / A raw_ostream that prints a newline on destruction, useful for LDBG()
143+ class RAIINewLineStream final : public raw_ostream {
144+ raw_ostream &Os;
145+
146+ public:
147+ RAIINewLineStream (raw_ostream &Os) : Os(Os) { SetUnbuffered (); }
148+ ~RAIINewLineStream () { Os << ' \n ' ; }
149+ void write_impl (const char *Ptr, size_t Size) final { Os.write (Ptr, Size); }
150+ uint64_t current_pos () const final { return Os.tell (); }
151+ };
152+
142153// / Remove the path prefix from the file name.
143154static LLVM_ATTRIBUTE_UNUSED constexpr const char *
144155getShortFileName (const char *path) {
0 commit comments