Main Page   Reference Manual   Namespace List   Compound List   Namespace Members   Compound Members   File Members  

class_debug.h
Go to the documentation of this file.
1 // $Header$
2 //
3 // Copyright (C) 2000 - 2004, by
4 //
5 // Carlo Wood, Run on IRC <carlo@alinoe.com>
6 // RSA-1024 0x624ACAD5 1997-01-26 Sign & Encrypt
7 // Fingerprint16 = 32 EC A7 B6 AC DB 65 A6 F6 F6 55 DD 1C DC FF 61
8 //
9 // This file may be distributed under the terms of the Q Public License
10 // version 1.0 as appearing in the file LICENSE.QPL included in the
11 // packaging of this file.
12 //
13 
18 #ifndef LIBCWD_CLASS_DEBUG_H
19 #define LIBCWD_CLASS_DEBUG_H
20 
21 #ifndef LIBCWD_CONFIG_H
22 #include "config.h"
23 #endif
24 #ifndef LIBCWD_CLASS_CHANNEL_SET_H
25 #include "class_channel_set.h"
26 #endif
27 #ifndef LIBCWD_PRIVATE_STRUCT_TSD_H
28 #include "private_struct_TSD.h"
29 #endif
30 #ifndef LIBCWD_STRUCT_DEBUG_TSD_H
31 #include "struct_debug_tsd.h"
32 #endif
33 #ifndef LIBCWD_PRIVATE_LOCK_INTERFACE_H
34 #include "private_lock_interface.h"
35 #endif
36 #ifndef LIBCW_IOSFWD
37 #define LIBCW_IOSFWD
38 #include <iosfwd>
39 #endif
40 
41 namespace libcwd {
42 
43 class buffer_ct;
44 
45 #if CWDEBUG_ALLOC
46 namespace _private_ {
47 
48 struct debug_message_st {
49  struct debug_message_st* next;
50  struct debug_message_st* prev;
51  int curlen;
52  char buf[sizeof(int)];
53 };
54 
55 } // namespace _private_
56 #endif
57 
58 //===================================================================================================
59 // class debug_ct
60 //
61 // Note: Debug output is printed already *before* this object is constructed,
62 // and is still printed when this object is already destructed.
63 // This is why initialization is done with method init() *before* construction
64 // and debug is turned off when this object is destructed.
65 // I hope that this is no problem because libcwd::libcw_do is a global object.
66 // It means however that this object can not contain any attributes that have
67 // a constructor of their own!
68 
77 class debug_ct {
78  friend void debug_tsd_st::start(debug_ct&, channel_set_data_st& LIBCWD_COMMA_TSD_PARAM);
79  friend void debug_tsd_st::finish(debug_ct &, channel_set_data_st& LIBCWD_COMMA_TSD_PARAM);
80 #ifdef LIBCWD_DOXYGEN
81 protected:
82 #else
83 public: // Only public because macro LibcwDout needs acces, don't access this directly.
84 #endif
85 #if LIBCWD_THREAD_SAFE
86  int WNS_index;
87  static int S_index_count;
88 #else
89  //-------------------------------------------------------------------------------------------------
90  // Put the otherwise Thread Specific Data of this debug object
91  // directly into the object when we don't use threads.
92  //
93 
94  debug_tsd_st tsd;
95 #endif
96 
97 protected:
98  //-------------------------------------------------------------------------------------------------
99  // Protected attributes.
100  //
101 
102  std::ostream* real_os;
103  // The original output ostream (as set with set_ostream()).
104  //
105 #if LIBCWD_THREAD_SAFE
106  friend class libcwd::buffer_ct; // buffer_ct::writeto() needs access.
107  _private_::lock_interface_base_ct* M_mutex;
108  // Pointer to the mutex that should be used for `real_os' or NULL when no lock is used.
109  // A value of NULL is only allowed prior to creating a second thread.
110 
111  buffer_ct* unfinished_oss;
112  void const* newlineless_tsd;
113 #endif
114 
115 private:
116  //-------------------------------------------------------------------------------------------------
117  // Private attributes:
118  //
119 
120  bool WNS_initialized;
121  // Set to true when this object is initialized (by a call to NS_init()).
122 
123  bool NS_being_initialized;
124  // Set to true when this object is being initialized (by a call to NS_init()).
125 
126 #if CWDEBUG_DEBUG
127  long init_magic;
128  // Used to check if the trick with `WNS_initialized' really works.
129 #endif
130 
131  bool interactive;
132  // Set true if the last or current debug output is to cerr
133 
134 #if CWDEBUG_ALLOC
135 public:
136  _private_::debug_message_st* queue;
137  _private_::debug_message_st* queue_top;
138  // Queue of messages written inside malloc/realloc/calloc/free/new/delete.
139  // Locked by mutex provided through set_ostream.
140 #endif
141 
142 public:
156  debug_string_ct const& margin() const;
157 
168  debug_string_ct const& marker() const;
169 
172 public:
173  //-------------------------------------------------------------------------------------------------
174  // Manipulators and accessors for the "format" attributes:
175  //
176 
177  void set_indent(unsigned short indentation);
178  void inc_indent(unsigned short indentation);
179  void dec_indent(unsigned short indentation);
180  unsigned short get_indent() const;
181 
182  void push_margin();
183  void pop_margin();
184  void push_marker();
185  void pop_marker();
186 
187  //-------------------------------------------------------------------------------------------------
188  // Other accessors
189  //
190 
191  std::ostream* get_ostream() const; // The original ostream set with set_ostream.
192 
193 private:
194  //-------------------------------------------------------------------------------------------------
195  // Initialization function.
196  //
197 
198  friend class channel_ct;
199  friend class fatal_channel_ct;
200  friend void ST_initialize_globals(LIBCWD_TSD_PARAM);
201 #if CWDEBUG_LOCATION
202  friend bool cwbfd::ST_init(LIBCWD_TSD_PARAM);
203 #endif
204  bool NS_init(LIBCWD_TSD_PARAM);
205  // Initialize this object, needed because debug output can be written
206  // from the constructors of (other) global objects, and from the malloc()
207  // family when CWDEBUG_ALLOC is set to 1.
208  // This will return false when it is called recursively which can happen
209  // as part of initialization of libcwd via a call to malloc while creating
210  // laf_ct -> buffer_ct --> basic_stringbuf. In that case the initialization
211  // failed thus. On success, it returns true.
212 
213 public:
214  //-------------------------------------------------------------------------------------------------
215  // Constructors and destructors.
216  //
217 
218  debug_ct();
219 
220 private:
221  void private_set_ostream(std::ostream* os);
222 
223 public:
224  //-------------------------------------------------------------------------------------------------
225  // Manipulators:
226  //
227 
228  void set_ostream(std::ostream* os);
229 #if LIBCWD_THREAD_SAFE || defined(LIBCWD_DOXYGEN)
230  template<class T>
231  void set_ostream(std::ostream* os, T* mutex);
232 #ifdef LIBCWD_DOXYGEN
233  // Specialization.
234  template<>
235  void set_ostream(std::ostream* os, pthread_mutex_t* mutex);
236 #endif
237 #endif
238  void off();
239  void on();
240 
241  struct OnOffState {
242  int _off;
243 #if CWDEBUG_DEBUGOUTPUT
244  bool first_time;
245 #endif
246  };
247 
248  void force_on(OnOffState& state);
249  void restore(OnOffState const& state);
250  bool is_on(LIBCWD_TSD_PARAM) const;
251 };
252 
253 #if LIBCWD_THREAD_SAFE && !defined(LIBCWD_DOXYGEN)
254 // Specialization.
255 template<>
256  void debug_ct::set_ostream(std::ostream* os, pthread_mutex_t* mutex);
257 #endif
258 
259 } // namespace libcwd
260 
261 #ifndef LIBCWD_SET_OSTREAM_INL
262 #include "set_ostream.inl"
263 #endif
264 
265 #endif // LIBCWD_CLASS_DEBUG_H
266 
This object represents a debug channel, it has a fixed label. A debug channel can be viewed upon as a...
Definition: class_channel.h:82
The Debug Object class, this object represents one output device (ostream).
Definition: class_debug.h:77
debug_ct()
Constructor.
Definition: class_debug.inl:155
void on()
Cancel last call to off().
Definition: class_debug.inl:202
void off()
Turn this debug object off.
Definition: class_debug.inl:171
A string class used for the debug output margin and marker.
Definition: class_debug_string.h:48
continued_channel_ct finish
Definition: debug.cc:517
std::ostream * get_ostream() const
Get the ostream device as set with set_ostream().
Definition: class_debug.inl:128
void set_ostream(std::ostream *os)
Set output device (single threaded applications).
Definition: debug.cc:2041
void pop_margin()
Pop margin from the stack.
Definition: debug.cc:946
void push_marker()
Push the current marker on a stack.
Definition: debug.cc:962
void pop_marker()
Pop marker from the stack.
Definition: debug.cc:976
unsigned short get_indent() const
Get the current indentation.
Definition: class_debug.inl:112
void push_margin()
Push the current margin on a stack.
Definition: debug.cc:932
void set_indent(unsigned short indentation)
Set number of spaces to indent.
Definition: class_debug.inl:78
void dec_indent(unsigned short indentation)
Decrement number of spaces to indent.
Definition: class_debug.inl:100
void inc_indent(unsigned short indentation)
Increment number of spaces to indent.
Definition: class_debug.inl:89
debug_string_ct & margin()
The margin.
Definition: class_debug.inl:43
debug_string_ct & marker()
The marker.
Definition: class_debug.inl:59
namespace for libcwd.
Definition: debug.cc:87
Copyright © 2001 - 2004 Carlo Wood.  All rights reserved.