MRPT  1.9.9
CConsoleRedirector.h
Go to the documentation of this file.
1 /* +------------------------------------------------------------------------+
2  | Mobile Robot Programming Toolkit (MRPT) |
3  | http://www.mrpt.org/ |
4  | |
5  | Copyright (c) 2005-2018, Individual contributors, see AUTHORS file |
6  | See: http://www.mrpt.org/Authors - All rights reserved. |
7  | Released under BSD License. See details in http://www.mrpt.org/License |
8  +------------------------------------------------------------------------+ */
9 #pragma once
10 
11 #include <streambuf>
12 #include <iostream>
13 #include <fstream>
14 #include <cstdio> // EOF
15 
16 namespace mrpt::system
17 {
18 /** By creating an object of this class, all the output to std::cout (and
19  * std::cerr) will be redirected to a text file, and optionally also shown on
20  * the console.
21  * Based on code from http://www.devmaster.net/forums/showthread.php?t=7037
22  * \ingroup mrpt_base_grp
23  */
24 class CConsoleRedirector : public std::streambuf
25 {
26  protected:
27  /** The text output file stream. */
28  std::ofstream m_of;
29  /** The "old" std::cout */
30  std::streambuf* sbOld;
31  /** The "old" std::cout */
32  std::streambuf* sbOld_cerr;
34  std::mutex m_cs;
35 
36  public:
37  /** Constructor
38  * \param out_file The file to create / append
39  * \param also_to_console Whether to redirect data to file *and* also dump
40  * data to the console as usual.
41  * \param append_file If set to false the file will be truncated on open
42  * \param bufferSize It's recommended to buffer the data instead of writing
43  * characters one by one.
44  * \param also_cerr Whether to redirect the output to std::cerr in addition
45  * to std::cout.
46  * \exception std::exception If the file cannot be opened.
47  */
49  const std::string& out_file, bool also_to_console = true,
50  bool also_cerr = true, bool append_file = false, int bufferSize = 1000)
51  : m_of(),
52  sbOld(nullptr),
53  sbOld_cerr(nullptr),
54  m_also_to_console(also_to_console),
55  m_cs()
56  {
57  // Open the file:
58  std::ios_base::openmode openMode =
59  std::ios_base::binary | std::ios_base::out;
60  if (append_file) openMode |= std::ios_base::app;
61  m_of.open(out_file.c_str(), openMode);
62  if (!m_of.is_open())
63  THROW_EXCEPTION_FMT("Error opening file: %s", out_file.c_str())
64 
65  if (bufferSize)
66  {
67  char* ptr = new char[bufferSize];
68  setp(ptr, ptr + bufferSize);
69  }
70  else
71  setp(0, 0);
72 
73  // Redirect:
74  sbOld = std::cout.rdbuf();
75  std::cout.rdbuf(this);
76 
77  if (also_cerr)
78  {
79  sbOld_cerr = std::cerr.rdbuf();
80  std::cerr.rdbuf(this);
81  }
82  }
83 
85  {
86  sync();
87  // Restore normal output:
88  std::cout.rdbuf(sbOld);
89  if (sbOld_cerr != nullptr) std::cerr.rdbuf(sbOld_cerr);
90  if (pbase()) delete[] pbase();
91  }
92 
93  void flush() { sync(); }
94  virtual void writeString(const std::string& str)
95  {
96  if (m_also_to_console) sbOld->sputn(str.c_str(), str.size());
97  m_of << str;
98  }
99 
100  private:
101  int overflow(int c) override
102  {
103  sync();
104 
105  m_cs.lock();
106  if (c != EOF)
107  {
108  if (pbase() == epptr())
109  {
110  std::string temp;
111  temp += char(c);
112  writeString(temp);
113  }
114  else
115  sputc(c);
116  }
117 
118  m_cs.unlock();
119  return 0;
120  }
121 
122  int sync() override
123  {
124  m_cs.lock();
125  if (pbase() != pptr())
126  {
127  int len = int(pptr() - pbase());
128  std::string temp(pbase(), len);
129  writeString(temp);
130  setp(pbase(), epptr());
131  }
132  m_cs.unlock();
133  return 0;
134  }
135 };
136 }
137 
GLenum GLsizei len
Definition: glext.h:4712
std::streambuf * sbOld
The "old" std::cout.
const GLubyte * c
Definition: glext.h:6313
GLsizei const GLchar ** string
Definition: glext.h:4101
CConsoleRedirector(const std::string &out_file, bool also_to_console=true, bool also_cerr=true, bool append_file=false, int bufferSize=1000)
Constructor.
std::ofstream m_of
The text output file stream.
virtual void writeString(const std::string &str)
By creating an object of this class, all the output to std::cout (and std::cerr) will be redirected t...
std::streambuf * sbOld_cerr
The "old" std::cout.
#define THROW_EXCEPTION_FMT(_FORMAT_STRING,...)
Definition: exceptions.h:43



Page generated by Doxygen 1.8.14 for MRPT 1.9.9 Git: 7d5e6d718 Fri Aug 24 01:51:28 2018 +0200 at lun nov 2 08:35:50 CET 2020