raw_logging.cc
Go to the documentation of this file.
1 // Copyright (c) 2006, Google Inc.
2 // All rights reserved.
3 //
4 // Redistribution and use in source and binary forms, with or without
5 // modification, are permitted provided that the following conditions are
6 // met:
7 //
8 // * Redistributions of source code must retain the above copyright
9 // notice, this list of conditions and the following disclaimer.
10 // * Redistributions in binary form must reproduce the above
11 // copyright notice, this list of conditions and the following disclaimer
12 // in the documentation and/or other materials provided with the
13 // distribution.
14 // * Neither the name of Google Inc. nor the names of its
15 // contributors may be used to endorse or promote products derived from
16 // this software without specific prior written permission.
17 //
18 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
21 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 //
30 // Author: Maxim Lifantsev
31 //
32 // logging_unittest.cc covers the functionality herein
33 
34 #include "utilities.h"
35 
36 #include <stdarg.h>
37 #include <cstdio>
38 #include <cerrno>
39 #ifdef HAVE_UNISTD_H
40 # include <unistd.h> // for close() and write()
41 #endif
42 #include <fcntl.h> // for open()
43 #include <ctime>
44 #include "config.h"
45 #include <glog/logging.h> // To pick up flag settings etc.
46 #include <glog/raw_logging.h>
47 #include "base/commandlineflags.h"
48 
49 #ifdef HAVE_STACKTRACE
50 # include "stacktrace.h"
51 #endif
52 
53 #if defined(HAVE_SYSCALL_H)
54 #include <syscall.h> // for syscall()
55 #elif defined(HAVE_SYS_SYSCALL_H)
56 #include <sys/syscall.h> // for syscall()
57 #endif
58 #ifdef HAVE_UNISTD_H
59 # include <unistd.h>
60 #endif
61 
62 #if (defined(HAVE_SYSCALL_H) || defined(HAVE_SYS_SYSCALL_H)) && (!(defined(GLOG_OS_MACOSX)))
63 # define safe_write(fd, s, len) syscall(SYS_write, fd, s, len)
64 #else
65  // Not so safe, but what can you do?
66 # define safe_write(fd, s, len) write(fd, s, len)
67 #endif
68 
70 
71 #if defined(__GNUC__)
72 #define GLOG_ATTRIBUTE_FORMAT(archetype, stringIndex, firstToCheck) \
73  __attribute__((format(archetype, stringIndex, firstToCheck)))
74 #define GLOG_ATTRIBUTE_FORMAT_ARG(stringIndex) \
75  __attribute__((format_arg(stringIndex)))
76 #else
77 #define GLOG_ATTRIBUTE_FORMAT(archetype, stringIndex, firstToCheck)
78 #define GLOG_ATTRIBUTE_FORMAT_ARG(stringIndex)
79 #endif
80 
81 // CAVEAT: vsnprintf called from *DoRawLog below has some (exotic) code paths
82 // that invoke malloc() and getenv() that might acquire some locks.
83 // If this becomes a problem we should reimplement a subset of vsnprintf
84 // that does not need locks and malloc.
85 
86 // Helper for RawLog__ below.
87 // *DoRawLog writes to *buf of *size and move them past the written portion.
88 // It returns true iff there was no overflow or error.
89 GLOG_ATTRIBUTE_FORMAT(printf, 3, 4)
90 static bool DoRawLog(char** buf, size_t* size, const char* format, ...) {
91  va_list ap;
92  va_start(ap, format);
93  int n = vsnprintf(*buf, *size, format, ap);
94  va_end(ap);
95  if (n < 0 || static_cast<size_t>(n) > *size) return false;
96  *size -= static_cast<size_t>(n);
97  *buf += n;
98  return true;
99 }
100 
101 // Helper for RawLog__ below.
102 inline static bool VADoRawLog(char** buf, size_t* size,
103  const char* format, va_list ap) {
104 #if defined(__GNUC__)
105 #pragma GCC diagnostic push
106 #pragma GCC diagnostic ignored "-Wformat-nonliteral"
107 #endif
108  int n = vsnprintf(*buf, *size, format, ap);
109 #if defined(__GNUC__)
110 #pragma GCC diagnostic pop
111 #endif
112  if (n < 0 || static_cast<size_t>(n) > *size) return false;
113  *size -= static_cast<size_t>(n);
114  *buf += n;
115  return true;
116 }
117 
118 static const int kLogBufSize = 3000;
119 static bool crashed = false;
120 static CrashReason crash_reason;
121 static char crash_buf[kLogBufSize + 1] = { 0 }; // Will end in '\0'
122 
123 GLOG_ATTRIBUTE_FORMAT(printf, 4, 5)
124 void RawLog__(LogSeverity severity, const char* file, int line,
125  const char* format, ...) {
126  if (!(FLAGS_logtostdout || FLAGS_logtostderr ||
127  severity >= FLAGS_stderrthreshold || FLAGS_alsologtostderr ||
129  return; // this stderr log message is suppressed
130  }
131  // can't call localtime_r here: it can allocate
132  char buffer[kLogBufSize];
133  char* buf = buffer;
134  size_t size = sizeof(buffer);
135 
136  // NOTE: this format should match the specification in base/logging.h
137  DoRawLog(&buf, &size, "%c00000000 00:00:00.000000 %5u %s:%d] RAW: ",
139  static_cast<unsigned int>(GetTID()),
140  const_basename(const_cast<char *>(file)), line);
141 
142  // Record the position and size of the buffer after the prefix
143  const char* msg_start = buf;
144  const size_t msg_size = size;
145 
146  va_list ap;
147  va_start(ap, format);
148  bool no_chop = VADoRawLog(&buf, &size, format, ap);
149  va_end(ap);
150  if (no_chop) {
151  DoRawLog(&buf, &size, "\n");
152  } else {
153  DoRawLog(&buf, &size, "RAW_LOG ERROR: The Message was too long!\n");
154  }
155  // We make a raw syscall to write directly to the stderr file descriptor,
156  // avoiding FILE buffering (to avoid invoking malloc()), and bypassing
157  // libc (to side-step any libc interception).
158  // We write just once to avoid races with other invocations of RawLog__.
159  safe_write(STDERR_FILENO, buffer, strlen(buffer));
160  if (severity == GLOG_FATAL) {
161  if (!sync_val_compare_and_swap(&crashed, false, true)) {
162  crash_reason.filename = file;
163  crash_reason.line_number = line;
164  memcpy(crash_buf, msg_start, msg_size); // Don't include prefix
165  crash_reason.message = crash_buf;
166 #ifdef HAVE_STACKTRACE
167  crash_reason.depth =
169 #else
170  crash_reason.depth = 0;
171 #endif
173  }
174  LogMessage::Fail(); // abort()
175  }
176 }
177 
178 _END_GOOGLE_NAMESPACE_
benchmarks.python.py_benchmark.const
const
Definition: py_benchmark.py:14
Fail
void Fail(const char *msg)
Definition: gtest_assert_by_exception_test.cc:52
VADoRawLog
static bool VADoRawLog(char **buf, size_t *size, const char *format, va_list ap)
Definition: raw_logging.cc:102
kLogBufSize
static const int kLogBufSize
Definition: raw_logging.cc:118
ARRAYSIZE
#define ARRAYSIZE(a)
Definition: utilities.h:128
msg_start
static bool msg_start(void *closure, const void *hd)
Definition: ruby/ext/google/protobuf_c/upb.c:9247
RawLog__
void RawLog__(LogSeverity severity, const char *file, int line, const char *format,...)
Definition: raw_logging.cc:124
LogSeverity
int LogSeverity
Definition: log_severity.h:51
GetStackTrace
_START_GOOGLE_NAMESPACE_ GLOG_EXPORT int GetStackTrace(void **result, int max_depth, int skip_count)
Definition: stacktrace_generic-inl.h:41
severity
GLenum GLuint GLenum severity
Definition: glcorearb.h:2695
glog_internal_namespace_::GetTID
pid_t GetTID()
Definition: utilities.cc:259
glog_internal_namespace_::SetCrashReason
void SetCrashReason(const CrashReason *r)
Definition: utilities.cc:358
buffer
GLuint buffer
Definition: glcorearb.h:2939
format
GLint GLint GLsizei GLint GLenum format
Definition: glcorearb.h:2773
GLOG_ATTRIBUTE_FORMAT
#define GLOG_ATTRIBUTE_FORMAT(archetype, stringIndex, firstToCheck)
Definition: raw_logging.cc:77
size
#define size
Definition: glcorearb.h:2944
FLAGS_logtostderr
static int FLAGS_logtostderr
Definition: sdk/include/aditof/log.h:67
buffer
Definition: buffer_processor.h:43
buf
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: glcorearb.h:4175
LogSeverityNames
const GLOG_EXPORT char *const LogSeverityNames[NUM_SEVERITIES]
Definition: logging.cc:404
crash_buf
static char crash_buf[kLogBufSize+1]
Definition: raw_logging.cc:121
commandlineflags.h
utilities.h
void
typedef void(APIENTRY *GLDEBUGPROCARB)(GLenum source
n
GLdouble n
Definition: glcorearb.h:4153
_START_GOOGLE_NAMESPACE_
Definition: signalhandler.cc:51
DoRawLog
static bool DoRawLog(char **buf, size_t *size, const char *format,...)
Definition: raw_logging.cc:90
IsGoogleLoggingInitialized
bool IsGoogleLoggingInitialized()
Definition: utilities.cc:69
size
GLsizeiptr size
Definition: glcorearb.h:2943
FLAGS_alsologtostderr
static int FLAGS_alsologtostderr
Definition: sdk/include/aditof/log.h:66
stacktrace.h
GLOG_FATAL
const int GLOG_FATAL
Definition: log_severity.h:53
crashed
static bool crashed
Definition: raw_logging.cc:119
glog_internal_namespace_::const_basename
const char * const_basename(const char *filepath)
Definition: utilities.cc:304
crash_reason
static CrashReason crash_reason
Definition: raw_logging.cc:120
glog_internal_namespace_::sync_val_compare_and_swap
T sync_val_compare_and_swap(T *ptr, T oldval, T newval)
Definition: utilities.h:168
safe_write
#define safe_write(fd, s, len)
Definition: raw_logging.cc:66


libaditof
Author(s):
autogenerated on Wed May 21 2025 02:06:58