Merge "Query log size properties only within logd"

This commit is contained in:
Tom Cherry 2020-08-06 22:00:29 +00:00 committed by Gerrit Code Review
commit ca0a46aefa
14 changed files with 140 additions and 125 deletions

View File

@ -17,7 +17,6 @@
liblog_sources = [
"log_event_list.cpp",
"log_event_write.cpp",
"log_size.cpp",
"logger_name.cpp",
"logger_read.cpp",
"logger_write.cpp",

View File

@ -144,13 +144,6 @@ int __android_log_security_bwrite(int32_t tag, const void* payload, size_t len);
int __android_log_security_bswrite(int32_t tag, const char* payload);
int __android_log_security(); /* Device Owner is present */
#define LOG_BUFFER_SIZE (256 * 1024) /* Tuned with ro.logd.size per-platform \
*/
#define LOG_BUFFER_MIN_SIZE (64 * 1024UL)
#define LOG_BUFFER_MAX_SIZE (256 * 1024 * 1024UL)
unsigned long __android_logger_get_buffer_size(log_id_t logId);
bool __android_logger_valid_buffer_size(unsigned long value);
/* Retrieve the composed event buffer */
int android_log_write_list_buffer(android_log_context ctx, const char** msg);

View File

@ -84,7 +84,6 @@ LIBLOG_PRIVATE {
global:
__android_log_pmsg_file_read;
__android_log_pmsg_file_write;
__android_logger_get_buffer_size;
android_openEventTagMap;
android_log_processBinaryLogBuffer;
android_log_processLogBuffer;

View File

@ -1,83 +0,0 @@
/*
* Copyright 2020 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include <private/android_logger.h>
#include <array>
#include <optional>
#include <string>
#include <android-base/parseint.h>
#ifdef __ANDROID__
#include <sys/system_properties.h>
#endif
bool __android_logger_valid_buffer_size(unsigned long value) {
return LOG_BUFFER_MIN_SIZE <= value && value <= LOG_BUFFER_MAX_SIZE;
}
#ifdef __ANDROID__
static std::optional<unsigned long> GetBufferSizeProperty(const std::string& key) {
char value[PROP_VALUE_MAX] = {};
if (__system_property_get(key.c_str(), value) <= 0) {
return {};
}
uint32_t size;
if (!android::base::ParseByteCount(value, &size)) {
return {};
}
if (!__android_logger_valid_buffer_size(size)) {
return {};
}
return size;
}
unsigned long __android_logger_get_buffer_size(log_id_t log_id) {
std::string buffer_name = android_log_id_to_name(log_id);
std::array<std::string, 4> properties = {
"persist.logd.size." + buffer_name,
"ro.logd.size." + buffer_name,
"persist.logd.size",
"ro.logd.size",
};
for (const auto& property : properties) {
if (auto size = GetBufferSizeProperty(property)) {
return *size;
}
}
char value[PROP_VALUE_MAX] = {};
if (__system_property_get("ro.config.low_ram", value) > 0 && !strcmp(value, "true")) {
return LOG_BUFFER_MIN_SIZE;
}
return LOG_BUFFER_SIZE;
}
#else
// Default to 1MB for host.
unsigned long __android_logger_get_buffer_size(log_id_t) {
return 1024 * 1024;
}
#endif

View File

@ -57,6 +57,7 @@ cc_library_static {
"LogReaderList.cpp",
"LogReaderThread.cpp",
"LogBufferElement.cpp",
"LogSize.cpp",
"LogStatistics.cpp",
"LogTags.cpp",
"PruneList.cpp",

View File

@ -101,9 +101,9 @@ int CommandListener::GetBufSizeCmd::runCommand(SocketClient* cli, int argc,
return 0;
}
unsigned long size = buf()->GetSize((log_id_t)id);
size_t size = buf()->GetSize(static_cast<log_id_t>(id));
char buf[512];
snprintf(buf, sizeof(buf), "%lu", size);
snprintf(buf, sizeof(buf), "%zu", size);
cli->sendMsg(buf);
return 0;
}
@ -127,8 +127,8 @@ int CommandListener::SetBufSizeCmd::runCommand(SocketClient* cli, int argc,
return 0;
}
unsigned long size = atol(argv[2]);
if (buf()->SetSize((log_id_t)id, size)) {
size_t size = atol(argv[2]);
if (!buf()->SetSize(static_cast<log_id_t>(id), size)) {
cli->sendMsg("Range Error");
return 0;
}
@ -150,9 +150,9 @@ int CommandListener::GetBufSizeReadableCmd::runCommand(SocketClient* cli, int ar
return 0;
}
unsigned long size = stats()->SizeReadable((log_id_t)id);
size_t size = stats()->SizeReadable(static_cast<log_id_t>(id));
char buf[512];
snprintf(buf, sizeof(buf), "%lu", size);
snprintf(buf, sizeof(buf), "%zu", size);
cli->sendMsg(buf);
return 0;
}
@ -171,9 +171,9 @@ int CommandListener::GetBufSizeUsedCmd::runCommand(SocketClient* cli, int argc,
return 0;
}
unsigned long size = stats()->Sizes((log_id_t)id);
size_t size = stats()->Sizes(static_cast<log_id_t>(id));
char buf[512];
snprintf(buf, sizeof(buf), "%lu", size);
snprintf(buf, sizeof(buf), "%zu", size);
cli->sendMsg(buf);
return 0;
}

View File

@ -68,8 +68,8 @@ class LogBuffer {
log_time realtime)>& filter) = 0;
virtual bool Clear(log_id_t id, uid_t uid) = 0;
virtual unsigned long GetSize(log_id_t id) = 0;
virtual int SetSize(log_id_t id, unsigned long size) = 0;
virtual size_t GetSize(log_id_t id) = 0;
virtual bool SetSize(log_id_t id, size_t size) = 0;
virtual uint64_t sequence() const = 0;
};

View File

@ -75,6 +75,8 @@ class LogBufferTest : public testing::TestWithParam<std::string> {
} else {
FAIL() << "Unknown buffer type selected for test";
}
log_id_for_each(i) { log_buffer_->SetSize(i, 1024 * 1024); }
}
void LogMessages(const std::vector<LogMessage>& messages) {

68
logd/LogSize.cpp Normal file
View File

@ -0,0 +1,68 @@
/*
* Copyright 2020 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include <LogSize.h>
#include <array>
#include <optional>
#include <string>
#include <android-base/parseint.h>
#include <android-base/properties.h>
bool IsValidBufferSize(size_t value) {
return kLogBufferMinSize <= value && value <= kLogBufferMaxSize;
}
static std::optional<size_t> GetBufferSizeProperty(const std::string& key) {
std::string value = android::base::GetProperty(key, "");
if (value.empty()) {
return {};
}
uint32_t size;
if (!android::base::ParseByteCount(value, &size)) {
return {};
}
if (!IsValidBufferSize(size)) {
return {};
}
return size;
}
size_t GetBufferSizeFromProperties(log_id_t log_id) {
std::string buffer_name = android_log_id_to_name(log_id);
std::array<std::string, 4> properties = {
"persist.logd.size." + buffer_name,
"ro.logd.size." + buffer_name,
"persist.logd.size",
"ro.logd.size",
};
for (const auto& property : properties) {
if (auto size = GetBufferSizeProperty(property)) {
return *size;
}
}
if (android::base::GetBoolProperty("ro.config.low_ram", false)) {
return kLogBufferMinSize;
}
return kDefaultLogBufferSize;
}

34
logd/LogSize.h Normal file
View File

@ -0,0 +1,34 @@
/*
* Copyright 2020 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#pragma once
#include <stddef.h>
#include <log/log.h>
static constexpr size_t kDefaultLogBufferSize = 256 * 1024;
static constexpr size_t kLogBufferMinSize = 64 * 1024;
static constexpr size_t kLogBufferMaxSize = 256 * 1024 * 1024;
bool IsValidBufferSize(size_t value);
// This returns the buffer size as set in system properties for use in LogBuffer::Init().
// Note that `logcat -G` calls LogBuffer::SetSize(), which configures log buffer sizes without
// setting these properties, so this function should never be used except for LogBuffer::Init().
// LogBuffer::GetSize() should be used instead within logd. Other processes can use
// android_logger_get_log_size() or `logcat -g` to query the actual allotted buffer size.
size_t GetBufferSizeFromProperties(log_id_t log_id);

View File

@ -23,6 +23,7 @@
#include <android-base/logging.h>
#include <android-base/scopeguard.h>
#include "LogSize.h"
#include "LogStatistics.h"
#include "SerializedFlushToState.h"
@ -34,8 +35,8 @@ SerializedLogBuffer::SerializedLogBuffer(LogReaderList* reader_list, LogTags* ta
void SerializedLogBuffer::Init() {
log_id_for_each(i) {
if (SetSize(i, __android_logger_get_buffer_size(i))) {
SetSize(i, LOG_BUFFER_MIN_SIZE);
if (!SetSize(i, GetBufferSizeFromProperties(i))) {
SetSize(i, kLogBufferMinSize);
}
}
@ -299,7 +300,7 @@ bool SerializedLogBuffer::Clear(log_id_t id, uid_t uid) {
return Prune(id, ULONG_MAX, uid);
}
unsigned long SerializedLogBuffer::GetSizeUsed(log_id_t id) {
size_t SerializedLogBuffer::GetSizeUsed(log_id_t id) {
size_t total_size = 0;
for (const auto& chunk : logs_[id]) {
total_size += chunk.PruneSize();
@ -307,7 +308,7 @@ unsigned long SerializedLogBuffer::GetSizeUsed(log_id_t id) {
return total_size;
}
unsigned long SerializedLogBuffer::GetSize(log_id_t id) {
size_t SerializedLogBuffer::GetSize(log_id_t id) {
auto lock = std::lock_guard{lock_};
return max_size_[id];
}
@ -315,10 +316,10 @@ unsigned long SerializedLogBuffer::GetSize(log_id_t id) {
// New SerializedLogChunk objects will be allocated according to the new size, but older one are
// unchanged. MaybePrune() is called on the log buffer to reduce it to an appropriate size if the
// new size is lower.
int SerializedLogBuffer::SetSize(log_id_t id, unsigned long size) {
bool SerializedLogBuffer::SetSize(log_id_t id, size_t size) {
// Reasonable limits ...
if (!__android_logger_valid_buffer_size(size)) {
return -1;
if (!IsValidBufferSize(size)) {
return false;
}
auto lock = std::lock_guard{lock_};
@ -326,5 +327,5 @@ int SerializedLogBuffer::SetSize(log_id_t id, unsigned long size) {
MaybePrune(id);
return 0;
return true;
}

View File

@ -47,8 +47,8 @@ class SerializedLogBuffer final : public LogBuffer {
log_time realtime)>& filter) override;
bool Clear(log_id_t id, uid_t uid) override;
unsigned long GetSize(log_id_t id) override;
int SetSize(log_id_t id, unsigned long size) override;
size_t GetSize(log_id_t id) override;
bool SetSize(log_id_t id, size_t size) override;
uint64_t sequence() const override { return sequence_.load(std::memory_order_relaxed); }
@ -61,13 +61,13 @@ class SerializedLogBuffer final : public LogBuffer {
void NotifyReadersOfPrune(log_id_t log_id, const std::list<SerializedLogChunk>::iterator& chunk)
REQUIRES(reader_list_->reader_threads_lock());
void RemoveChunkFromStats(log_id_t log_id, SerializedLogChunk& chunk);
unsigned long GetSizeUsed(log_id_t id) REQUIRES(lock_);
size_t GetSizeUsed(log_id_t id) REQUIRES(lock_);
LogReaderList* reader_list_;
LogTags* tags_;
LogStatistics* stats_;
unsigned long max_size_[LOG_ID_MAX] GUARDED_BY(lock_) = {};
size_t max_size_[LOG_ID_MAX] GUARDED_BY(lock_) = {};
std::list<SerializedLogChunk> logs_[LOG_ID_MAX] GUARDED_BY(lock_);
RwLock lock_;

View File

@ -19,6 +19,7 @@
#include <android-base/logging.h>
#include "LogBufferElement.h"
#include "LogSize.h"
SimpleLogBuffer::SimpleLogBuffer(LogReaderList* reader_list, LogTags* tags, LogStatistics* stats)
: reader_list_(reader_list), tags_(tags), stats_(stats) {
@ -29,8 +30,8 @@ SimpleLogBuffer::~SimpleLogBuffer() {}
void SimpleLogBuffer::Init() {
log_id_for_each(i) {
if (SetSize(i, __android_logger_get_buffer_size(i))) {
SetSize(i, LOG_BUFFER_MIN_SIZE);
if (!SetSize(i, GetBufferSizeFromProperties(i))) {
SetSize(i, kLogBufferMinSize);
}
}
@ -247,22 +248,22 @@ bool SimpleLogBuffer::Clear(log_id_t id, uid_t uid) {
}
// get the total space allocated to "id"
unsigned long SimpleLogBuffer::GetSize(log_id_t id) {
size_t SimpleLogBuffer::GetSize(log_id_t id) {
auto lock = SharedLock{lock_};
size_t retval = max_size_[id];
return retval;
}
// set the total space allocated to "id"
int SimpleLogBuffer::SetSize(log_id_t id, unsigned long size) {
bool SimpleLogBuffer::SetSize(log_id_t id, size_t size) {
// Reasonable limits ...
if (!__android_logger_valid_buffer_size(size)) {
return -1;
if (!IsValidBufferSize(size)) {
return false;
}
auto lock = std::lock_guard{lock_};
max_size_[id] = size;
return 0;
return true;
}
void SimpleLogBuffer::MaybePrune(log_id_t id) {

View File

@ -41,8 +41,8 @@ class SimpleLogBuffer : public LogBuffer {
log_time realtime)>& filter) override;
bool Clear(log_id_t id, uid_t uid) override;
unsigned long GetSize(log_id_t id) override;
int SetSize(log_id_t id, unsigned long size) override final;
size_t GetSize(log_id_t id) override;
bool SetSize(log_id_t id, size_t size) override final;
uint64_t sequence() const override { return sequence_.load(std::memory_order_relaxed); }
@ -60,7 +60,7 @@ class SimpleLogBuffer : public LogBuffer {
LogStatistics* stats() { return stats_; }
LogReaderList* reader_list() { return reader_list_; }
unsigned long max_size(log_id_t id) REQUIRES_SHARED(lock_) { return max_size_[id]; }
size_t max_size(log_id_t id) REQUIRES_SHARED(lock_) { return max_size_[id]; }
std::list<LogBufferElement>& logs() { return logs_; }
RwLock lock_;
@ -75,7 +75,7 @@ class SimpleLogBuffer : public LogBuffer {
std::atomic<uint64_t> sequence_ = 1;
unsigned long max_size_[LOG_ID_MAX] GUARDED_BY(lock_);
size_t max_size_[LOG_ID_MAX] GUARDED_BY(lock_);
std::list<LogBufferElement> logs_ GUARDED_BY(lock_);
// Keeps track of the iterator to the oldest log message of a given log type, as an
// optimization when pruning logs. Use GetOldest() to retrieve.