aboutsummaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorChris Lattner <sabre@nondot.org>2008-08-23 19:23:10 +0000
committerChris Lattner <sabre@nondot.org>2008-08-23 19:23:10 +0000
commit097af7fc8f8688cc21453a5561347f14ca7c5771 (patch)
tree3278cf5420b9c3a9e07d8ccfd4afd8e7fb36a886 /lib
parent8ff7ce3dd2c0b57283372e9ed939ab07018fec2f (diff)
add a simple mechanism for formatted output. This gives raw_ostream's
all the power and risk of fprintf format strings. Use them like this: OS << format("%10.4f", 42.0) << "\n" << format("%x", 42) << '\n'; git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@55246 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib')
-rw-r--r--lib/Support/raw_ostream.cpp50
1 files changed, 50 insertions, 0 deletions
diff --git a/lib/Support/raw_ostream.cpp b/lib/Support/raw_ostream.cpp
index d776fa583f..104dc77149 100644
--- a/lib/Support/raw_ostream.cpp
+++ b/lib/Support/raw_ostream.cpp
@@ -12,6 +12,7 @@
//===----------------------------------------------------------------------===//
#include "llvm/Support/raw_ostream.h"
+#include "llvm/ADT/SmallVector.h"
#include "llvm/Config/config.h"
#include <ostream>
@@ -134,6 +135,55 @@ raw_ostream &raw_ostream::write(const char *Ptr, unsigned Size) {
return *this;
}
+// Formatted output.
+raw_ostream &raw_ostream::operator<<(const format_object_base &Fmt) {
+ // If we have more than a few bytes left in our output buffer, try formatting
+ // directly onto its end.
+ unsigned NextBufferSize = 127;
+ if (OutBufEnd-OutBufCur > 3) {
+ unsigned BufferBytesLeft = OutBufEnd-OutBufCur;
+ unsigned BytesUsed = Fmt.print(OutBufCur, BufferBytesLeft);
+
+ // Common case is that we have plenty of space.
+ if (BytesUsed < BufferBytesLeft) {
+ OutBufCur += BytesUsed;
+ return *this;
+ }
+
+ // Otherwise, we overflowed and the return value tells us the size to try
+ // again with.
+ NextBufferSize = BytesUsed;
+ }
+
+ // If we got here, we didn't have enough space in the output buffer for the
+ // string. Try printing into a SmallVector that is resized to have enough
+ // space. Iterate until we win.
+ SmallVector<char, 128> V;
+
+ while (1) {
+ V.resize(NextBufferSize);
+
+ // Try formatting into the SmallVector.
+ unsigned BytesUsed = Fmt.print(&V[0], NextBufferSize);
+
+ // If BytesUsed fit into the vector, we win.
+ if (BytesUsed < NextBufferSize)
+ return write(&V[0], BytesUsed);
+
+ // Otherwise, try again with a new size.
+ assert(BytesUsed > NextBufferSize && "Didn't grow buffer!?");
+ NextBufferSize = BytesUsed;
+ }
+}
+
+//===----------------------------------------------------------------------===//
+// Formatted Output
+//===----------------------------------------------------------------------===//
+
+// Out of line virtual method.
+void format_object_base::home() {
+}
+
//===----------------------------------------------------------------------===//
// raw_fd_ostream
//===----------------------------------------------------------------------===//