Flutter Engine
The Flutter Engine
Loading...
Searching...
No Matches
logging.cc
Go to the documentation of this file.
1// Copyright 2013 The Flutter Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include <algorithm>
6#include <cstring>
7#include <iostream>
8
9#include "flutter/fml/build_config.h"
10#include "flutter/fml/log_level.h"
11#include "flutter/fml/log_settings.h"
12#include "flutter/fml/logging.h"
13
14#if defined(FML_OS_ANDROID)
15#include <android/log.h>
16#elif defined(FML_OS_IOS)
17#include <syslog.h>
18#elif defined(OS_FUCHSIA)
19#include <lib/syslog/structured_backend/cpp/fuchsia_syslog.h>
20#include <lib/syslog/structured_backend/fuchsia_syslog.h>
21#include <zircon/process.h>
22#include "flutter/fml/platform/fuchsia/log_state.h"
23#endif
24
25namespace fml {
26
27namespace {
28
29#if !defined(OS_FUCHSIA)
30const char* const kLogSeverityNames[kLogNumSeverities] = {
31 "INFO", "WARNING", "ERROR", "IMPORTANT", "FATAL"};
32
33const char* GetNameForLogSeverity(LogSeverity severity) {
34 if (severity >= kLogInfo && severity < kLogNumSeverities) {
35 return kLogSeverityNames[severity];
36 }
37 return "UNKNOWN";
38}
39#endif
40
41const char* StripDots(const char* path) {
42 while (strncmp(path, "../", 3) == 0) {
43 path += 3;
44 }
45 return path;
46}
47
48#if defined(OS_FUCHSIA)
49
50zx_koid_t GetKoid(zx_handle_t handle) {
51 zx_info_handle_basic_t info;
52 zx_status_t status = zx_object_get_info(handle, ZX_INFO_HANDLE_BASIC, &info,
53 sizeof(info), nullptr, nullptr);
54 return status == ZX_OK ? info.koid : ZX_KOID_INVALID;
55}
56
57thread_local zx_koid_t tls_thread_koid{ZX_KOID_INVALID};
58
59zx_koid_t GetCurrentThreadKoid() {
60 if (unlikely(tls_thread_koid == ZX_KOID_INVALID)) {
61 tls_thread_koid = GetKoid(zx_thread_self());
62 }
63 ZX_DEBUG_ASSERT(tls_thread_koid != ZX_KOID_INVALID);
64 return tls_thread_koid;
65}
66
67static zx_koid_t pid = GetKoid(zx_process_self());
68
69static thread_local zx_koid_t tid = GetCurrentThreadKoid();
70
71std::string GetProcessName(zx_handle_t handle) {
72 char process_name[ZX_MAX_NAME_LEN];
73 zx_status_t status = zx_object_get_property(
74 handle, ZX_PROP_NAME, &process_name, sizeof(process_name));
75 if (status != ZX_OK) {
76 process_name[0] = '\0';
77 }
78 return process_name;
79}
80
81static std::string process_name = GetProcessName(zx_process_self());
82
83static const zx::socket& socket = LogState::Default().socket();
84
85#endif
86
87} // namespace
88
90 const char* file,
91 int line,
92 const char* condition)
93 : severity_(severity), file_(StripDots(file)), line_(line) {
94#if !defined(OS_FUCHSIA)
95 stream_ << "[";
96 if (severity >= kLogInfo) {
97 stream_ << GetNameForLogSeverity(severity);
98 } else {
99 stream_ << "VERBOSE" << -severity;
100 }
101 stream_ << ":" << file_ << "(" << line_ << ")] ";
102#endif
103
104 if (condition) {
105 stream_ << "Check failed: " << condition << ". ";
106 }
107}
108
109// static
110thread_local std::ostringstream* LogMessage::capture_next_log_stream_ = nullptr;
111
112namespace testing {
113
117
121
122std::string LogCapture::str() const {
123 return stream_.str();
124}
125
126} // namespace testing
127
128// static
129void LogMessage::CaptureNextLog(std::ostringstream* stream) {
130 LogMessage::capture_next_log_stream_ = stream;
131}
132
134#if !defined(OS_FUCHSIA)
135 stream_ << std::endl;
136#endif
137 if (capture_next_log_stream_) {
138 *capture_next_log_stream_ << stream_.str();
139 capture_next_log_stream_ = nullptr;
140 } else {
141#if defined(FML_OS_ANDROID)
142 android_LogPriority priority =
143 (severity_ < 0) ? ANDROID_LOG_VERBOSE : ANDROID_LOG_UNKNOWN;
144 switch (severity_) {
145 case kLogImportant:
146 case kLogInfo:
147 priority = ANDROID_LOG_INFO;
148 break;
149 case kLogWarning:
150 priority = ANDROID_LOG_WARN;
151 break;
152 case kLogError:
153 priority = ANDROID_LOG_ERROR;
154 break;
155 case kLogFatal:
156 priority = ANDROID_LOG_FATAL;
157 break;
158 }
159 __android_log_write(priority, "flutter", stream_.str().c_str());
160#elif defined(FML_OS_IOS)
161 syslog(LOG_ALERT, "%s", stream_.str().c_str());
162#elif defined(OS_FUCHSIA)
163 FuchsiaLogSeverity severity;
164 switch (severity_) {
165 case kLogImportant:
166 case kLogInfo:
167 severity = FUCHSIA_LOG_INFO;
168 break;
169 case kLogWarning:
170 severity = FUCHSIA_LOG_WARNING;
171 break;
172 case kLogError:
173 severity = FUCHSIA_LOG_ERROR;
174 break;
175 case kLogFatal:
176 severity = FUCHSIA_LOG_FATAL;
177 break;
178 default:
179 if (severity_ < 0) {
180 severity = FUCHSIA_LOG_DEBUG;
181 } else {
182 // Unknown severity. Use INFO.
183 severity = FUCHSIA_LOG_INFO;
184 }
185 break;
186 }
187 fuchsia_syslog::LogBuffer buffer;
188 buffer.BeginRecord(severity, std::string_view(file_), line_,
189 std::string_view(stream_.str()), socket.borrow(), 0, pid,
190 tid);
191 if (!process_name.empty()) {
192 buffer.WriteKeyValue("tag", process_name);
193 }
194 if (auto tags_ptr = LogState::Default().tags()) {
195 for (auto& tag : *tags_ptr) {
196 buffer.WriteKeyValue("tag", tag);
197 }
198 }
199 buffer.FlushRecord();
200#else
201 // Don't use std::cerr here, because it may not be initialized properly yet.
202 fprintf(stderr, "%s", stream_.str().c_str());
203 fflush(stderr);
204#endif
205 }
206
207 if (severity_ >= kLogFatal) {
208 KillProcess();
209 }
210}
211
213 return std::max(-1, kLogInfo - GetMinLogLevel());
214}
215
217 return severity >= GetMinLogLevel();
218}
219
221 abort();
222}
223
224} // namespace fml
static void info(const char *fmt,...) SK_PRINTF_LIKE(1
Definition DM.cpp:213
LogMessage(LogSeverity severity, const char *file, int line, const char *condition)
Definition logging.cc:89
std::ostream & stream()
Definition logging.h:40
static void CaptureNextLog(std::ostringstream *stream)
Definition logging.cc:129
static LogState & Default()
Definition log_state.cc:61
const zx::socket & socket() const
Definition log_state.h:28
static const uint8_t buffer[]
DEF_SWITCHES_START aot vmservice shared library Name of the *so containing AOT compiled Dart assets for launching the service isolate vm snapshot The VM snapshot data that will be memory mapped as read only SnapshotAssetPath must be present isolate snapshot The isolate snapshot data that will be memory mapped as read only SnapshotAssetPath must be present cache dir path
Definition switches.h:57
void KillProcess()
Definition logging.cc:220
constexpr LogSeverity kLogFatal
Definition log_level.h:19
int LogSeverity
Definition log_level.h:11
constexpr LogSeverity kLogNumSeverities
Definition log_level.h:20
constexpr LogSeverity kLogImportant
Definition log_level.h:18
bool ShouldCreateLogMessage(LogSeverity severity)
Definition logging.cc:216
int GetMinLogLevel()
constexpr LogSeverity kLogError
Definition log_level.h:15
constexpr LogSeverity kLogInfo
Definition log_level.h:13
int GetVlogVerbosity()
Definition logging.cc:212
constexpr LogSeverity kLogWarning
Definition log_level.h:14
std::string str() const
Definition logging.cc:122