Merge "Remove liblog/uio.c and <log/uio.h>"
diff --git a/adb/client/adb_install.cpp b/adb/client/adb_install.cpp
index 0d0375d..21e0874 100644
--- a/adb/client/adb_install.cpp
+++ b/adb/client/adb_install.cpp
@@ -500,17 +500,22 @@
int install_multi_package(int argc, const char** argv) {
// Find all APK arguments starting at end.
// All other arguments passed through verbatim.
- int first_apk = -1;
+ bool apex_found = false;
+ int first_package = -1;
for (int i = argc - 1; i >= 0; i--) {
const char* file = argv[i];
- if (android::base::EndsWithIgnoreCase(file, ".apk")) {
- first_apk = i;
+ if (android::base::EndsWithIgnoreCase(file, ".apk") ||
+ android::base::EndsWithIgnoreCase(file, ".apex")) {
+ first_package = i;
+ if (android::base::EndsWithIgnoreCase(file, ".apex")) {
+ apex_found = true;
+ }
} else {
break;
}
}
- if (first_apk == -1) error_exit("need APK file on command line");
+ if (first_package == -1) error_exit("need APK or APEX files on command line");
if (use_legacy_install()) {
fprintf(stderr, "adb: multi-package install is not supported on this device\n");
@@ -520,6 +525,9 @@
std::string multi_package_cmd =
android::base::StringPrintf("%s install-create --multi-package", install_cmd.c_str());
+ if (apex_found) {
+ multi_package_cmd += " --staged";
+ }
// Create multi-package install session
std::string error;
@@ -557,15 +565,25 @@
std::string individual_cmd =
android::base::StringPrintf("%s install-create", install_cmd.c_str());
std::string all_session_ids = "";
- for (int i = 1; i < first_apk; i++) {
+ for (int i = 1; i < first_package; i++) {
individual_cmd += " " + escape_arg(argv[i]);
}
+ if (apex_found) {
+ individual_cmd += " --staged";
+ }
+ std::string individual_apex_cmd = individual_cmd + " --apex";
std::string cmd = "";
- for (int i = first_apk; i < argc; i++) {
- // Create individual install session
+ for (int i = first_package; i < argc; i++) {
+ const char* file = argv[i];
char buf[BUFSIZ];
{
- unique_fd fd(adb_connect(individual_cmd, &error));
+ unique_fd fd;
+ // Create individual install session
+ if (android::base::EndsWithIgnoreCase(file, ".apex")) {
+ fd.reset(adb_connect(individual_apex_cmd, &error));
+ } else {
+ fd.reset(adb_connect(individual_cmd, &error));
+ }
if (fd < 0) {
fprintf(stderr, "adb: connect error for create: %s\n", error.c_str());
goto finalize_multi_package_session;
@@ -591,7 +609,6 @@
fprintf(stdout, "Created child session ID %d.\n", session_id);
session_ids.push_back(session_id);
- const char* file = argv[i];
struct stat sb;
if (stat(file, &sb) == -1) {
fprintf(stderr, "adb: failed to stat %s: %s\n", file, strerror(errno));
@@ -633,7 +650,7 @@
{
unique_fd fd(adb_connect(cmd, &error));
if (fd < 0) {
- fprintf(stderr, "adb: connect error for create: %s\n", error.c_str());
+ fprintf(stderr, "adb: connect error for install-add-session: %s\n", error.c_str());
goto finalize_multi_package_session;
}
read_status_line(fd.get(), buf, sizeof(buf));
diff --git a/fs_mgr/fs_mgr.cpp b/fs_mgr/fs_mgr.cpp
index 785f9a2..19445c8 100644
--- a/fs_mgr/fs_mgr.cpp
+++ b/fs_mgr/fs_mgr.cpp
@@ -556,9 +556,17 @@
mkdir(target.c_str(), 0755);
errno = 0;
unsigned long mountflags = entry.flags;
- int ret = mount(source.c_str(), target.c_str(), entry.fs_type.c_str(), mountflags,
+ int ret = 0;
+ int save_errno = 0;
+ do {
+ if (save_errno == EAGAIN) {
+ PINFO << "Retrying mount (source=" << source << ",target=" << target
+ << ",type=" << entry.fs_type << ")=" << ret << "(" << save_errno << ")";
+ }
+ ret = mount(source.c_str(), target.c_str(), entry.fs_type.c_str(), mountflags,
entry.fs_options.c_str());
- int save_errno = errno;
+ save_errno = errno;
+ } while (ret && save_errno == EAGAIN);
const char* target_missing = "";
const char* source_missing = "";
if (save_errno == ENOENT) {
diff --git a/init/reboot.cpp b/init/reboot.cpp
index 45dc6d3..008a868 100644
--- a/init/reboot.cpp
+++ b/init/reboot.cpp
@@ -103,13 +103,17 @@
int st;
if (IsF2Fs()) {
const char* f2fs_argv[] = {
- "/system/bin/fsck.f2fs", "-f", mnt_fsname_.c_str(),
+ "/system/bin/fsck.f2fs",
+ "-a",
+ mnt_fsname_.c_str(),
};
android_fork_execvp_ext(arraysize(f2fs_argv), (char**)f2fs_argv, &st, true, LOG_KLOG,
true, nullptr, nullptr, 0);
} else if (IsExt4()) {
const char* ext4_argv[] = {
- "/system/bin/e2fsck", "-f", "-y", mnt_fsname_.c_str(),
+ "/system/bin/e2fsck",
+ "-y",
+ mnt_fsname_.c_str(),
};
android_fork_execvp_ext(arraysize(ext4_argv), (char**)ext4_argv, &st, true, LOG_KLOG,
true, nullptr, nullptr, 0);
diff --git a/liblog/Android.bp b/liblog/Android.bp
index 58d88df..4fd36f5 100644
--- a/liblog/Android.bp
+++ b/liblog/Android.bp
@@ -19,7 +19,6 @@
"config_write.cpp",
"log_event_list.cpp",
"log_event_write.cpp",
- "log_ratelimit.cpp",
"logger_lock.cpp",
"logger_name.cpp",
"logger_read.cpp",
diff --git a/liblog/include/log/log.h b/liblog/include/log/log.h
index 6f93396..5928649 100644
--- a/liblog/include/log/log.h
+++ b/liblog/include/log/log.h
@@ -164,33 +164,6 @@
*/
void __android_log_close(void);
-/*
- * if last is NULL, caller _must_ provide a consistent value for seconds.
- *
- * Return -1 if we can not acquire a lock, which below will permit the logging,
- * error on allowing a log message through.
- */
-int __android_log_ratelimit(time_t seconds, time_t* last);
-
-/*
- * Usage:
- *
- * // Global default and state
- * IF_ALOG_RATELIMIT() {
- * ALOG*(...);
- * }
- *
- * // local state, 10 seconds ratelimit
- * static time_t local_state;
- * IF_ALOG_RATELIMIT_LOCAL(10, &local_state) {
- * ALOG*(...);
- * }
- */
-
-#define IF_ALOG_RATELIMIT() if (__android_log_ratelimit(0, NULL) > 0)
-#define IF_ALOG_RATELIMIT_LOCAL(seconds, state) \
- if (__android_log_ratelimit(seconds, state) > 0)
-
#if defined(__clang__)
#pragma clang diagnostic pop
#endif
diff --git a/liblog/include/log/log_event_list.h b/liblog/include/log/log_event_list.h
index b376504..636d417 100644
--- a/liblog/include/log/log_event_list.h
+++ b/liblog/include/log/log_event_list.h
@@ -109,8 +109,6 @@
/* android_log_list C++ helpers */
extern "C++" {
class android_log_event_list {
- friend class __android_log_event_list;
-
private:
android_log_context ctx;
int ret;
@@ -122,10 +120,6 @@
explicit android_log_event_list(int tag) : ret(0) {
ctx = create_android_logger(static_cast<uint32_t>(tag));
}
- explicit android_log_event_list(log_msg& log_msg) : ret(0) {
- ctx = create_android_log_parser(log_msg.msg() + sizeof(uint32_t),
- log_msg.entry.len - sizeof(uint32_t));
- }
~android_log_event_list() {
android_log_destroy(&ctx);
}
@@ -283,13 +277,6 @@
if (retval < 0) ret = retval;
return ret >= 0;
}
-
- android_log_list_element read() {
- return android_log_read_next(ctx);
- }
- android_log_list_element peek() {
- return android_log_peek_next(ctx);
- }
};
}
#endif
diff --git a/liblog/include/log/log_time.h b/liblog/include/log/log_time.h
index be69255..09c9910 100644
--- a/liblog/include/log/log_time.h
+++ b/liblog/include/log/log_time.h
@@ -42,23 +42,19 @@
*/
struct log_time {
public:
- uint32_t tv_sec; /* good to Feb 5 2106 */
- uint32_t tv_nsec;
+ uint32_t tv_sec = 0; /* good to Feb 5 2106 */
+ uint32_t tv_nsec = 0;
static const uint32_t tv_sec_max = 0xFFFFFFFFUL;
static const uint32_t tv_nsec_max = 999999999UL;
+ static const timespec EPOCH;
- log_time(const timespec& T)
- : tv_sec(static_cast<uint32_t>(T.tv_sec)),
- tv_nsec(static_cast<uint32_t>(T.tv_nsec)) {
- }
+ log_time() {}
+ explicit log_time(const timespec& T)
+ : tv_sec(static_cast<uint32_t>(T.tv_sec)), tv_nsec(static_cast<uint32_t>(T.tv_nsec)) {}
explicit log_time(uint32_t sec, uint32_t nsec = 0)
: tv_sec(sec), tv_nsec(nsec) {
}
-#define __struct_log_time_private_defined
- static const timespec EPOCH;
- log_time() {
- }
#ifdef __linux__
explicit log_time(clockid_t id) {
timespec T;
diff --git a/liblog/include/private/android_logger.h b/liblog/include/private/android_logger.h
index 830f651..5e04148 100644
--- a/liblog/include/private/android_logger.h
+++ b/liblog/include/private/android_logger.h
@@ -150,37 +150,6 @@
/* Retrieve the composed event buffer */
int android_log_write_list_buffer(android_log_context ctx, const char** msg);
-#ifdef __cplusplus
-#ifdef __class_android_log_event_list_defined
-#ifndef __class_android_log_event_list_private_defined
-#define __class_android_log_event_list_private_defined
-/* android_log_context C++ helpers */
-extern "C++" {
-class __android_log_event_list : public android_log_event_list {
- __android_log_event_list(const android_log_event_list&) = delete;
- void operator=(const __android_log_event_list&) = delete;
-
- public:
- explicit __android_log_event_list(int tag) : android_log_event_list(tag) {
- }
- explicit __android_log_event_list(log_msg& log_msg)
- : android_log_event_list(log_msg) {
- }
-
- operator std::string() {
- if (ret) return std::string("");
- const char* cp = nullptr;
- ssize_t len = android_log_write_list_buffer(ctx, &cp);
- if (len < 0) ret = len;
- if (!cp || (len <= 0)) return std::string("");
- return std::string(cp, len);
- }
-};
-}
-#endif
-#endif
-#endif
-
#if defined(__cplusplus)
}
#endif
diff --git a/liblog/log_ratelimit.cpp b/liblog/log_ratelimit.cpp
deleted file mode 100644
index 33770dd..0000000
--- a/liblog/log_ratelimit.cpp
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
-** Copyright 2016, 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 <errno.h>
-#include <pthread.h>
-#include <time.h>
-
-#include <log/log.h>
-
-#include "log_portability.h"
-
-// Global default if 'last' argument in __android_log_ratelimit is NULL
-static time_t g_last_clock;
-// Global above can not deal well with callers playing games with the
-// seconds argument, so we will also hold on to the maximum value
-// ever provided and use that to gain consistency. If the caller
-// provides their own 'last' argument, then they can play such games
-// of varying the 'seconds' argument to their pleasure.
-static time_t g_last_seconds;
-static const time_t last_seconds_default = 10;
-static const time_t last_seconds_max = 24 * 60 * 60; // maximum of a day
-static const time_t last_seconds_min = 2; // granularity
-// Lock to protect last_clock and last_seconds, but also 'last'
-// argument (not NULL) as supplied to __android_log_ratelimit.
-static pthread_mutex_t lock_ratelimit = PTHREAD_MUTEX_INITIALIZER;
-
-// if last is NULL, caller _must_ provide a consistent value for
-// seconds, otherwise we will take the maximum ever issued and hold
-// on to that. Preserves value of non-zero errno. Return -1 if we
-// can not acquire a lock, 0 if we are not to log a message, and 1
-// if we are ok to log a message. Caller should check > 0 for true.
-LIBLOG_ABI_PUBLIC int __android_log_ratelimit(time_t seconds, time_t* last) {
- int save_errno = errno;
-
- // Two reasons for trylock failure:
- // 1. In a signal handler. Must prevent deadlock
- // 2. Too many threads calling __android_log_ratelimit.
- // Bonus to not print if they race here because that
- // dovetails the goal of ratelimiting. One may print
- // and the others will wait their turn ...
- if (pthread_mutex_trylock(&lock_ratelimit)) {
- if (save_errno) errno = save_errno;
- return -1;
- }
-
- if (seconds == 0) {
- seconds = last_seconds_default;
- } else if (seconds < last_seconds_min) {
- seconds = last_seconds_min;
- } else if (seconds > last_seconds_max) {
- seconds = last_seconds_max;
- }
-
- if (!last) {
- if (g_last_seconds > seconds) {
- seconds = g_last_seconds;
- } else if (g_last_seconds < seconds) {
- g_last_seconds = seconds;
- }
- last = &g_last_clock;
- }
-
- time_t now = time(NULL);
- if ((now == (time_t)-1) || ((*last + seconds) > now)) {
- pthread_mutex_unlock(&lock_ratelimit);
- if (save_errno) errno = save_errno;
- return 0;
- }
- *last = now;
- pthread_mutex_unlock(&lock_ratelimit);
- if (save_errno) errno = save_errno;
- return 1;
-}
diff --git a/liblog/log_time.cpp b/liblog/log_time.cpp
index ae376be..77bb94f 100644
--- a/liblog/log_time.cpp
+++ b/liblog/log_time.cpp
@@ -137,7 +137,7 @@
LIBLOG_ABI_PRIVATE log_time log_time::operator-=(const timespec& T) {
// No concept of negative time, clamp to EPOCH
if (*this <= T) {
- return *this = EPOCH;
+ return *this = log_time(EPOCH);
}
if (this->tv_nsec < (unsigned long int)T.tv_nsec) {
@@ -165,7 +165,7 @@
LIBLOG_ABI_PRIVATE log_time log_time::operator-=(const log_time& T) {
// No concept of negative time, clamp to EPOCH
if (*this <= T) {
- return *this = EPOCH;
+ return *this = log_time(EPOCH);
}
if (this->tv_nsec < T.tv_nsec) {
diff --git a/liblog/tests/Android.bp b/liblog/tests/Android.bp
index 2c47fd6..4ab2acb 100644
--- a/liblog/tests/Android.bp
+++ b/liblog/tests/Android.bp
@@ -29,10 +29,10 @@
"-fno-builtin",
],
shared_libs: [
- "liblog",
"libm",
"libbase",
],
+ static_libs: ["liblog"],
srcs: ["liblog_benchmark.cpp"],
}
@@ -63,10 +63,10 @@
"log_wrap_test.cpp",
],
shared_libs: [
- "liblog",
"libcutils",
"libbase",
],
+ static_libs: ["liblog"],
}
// Build tests for the device (with .so). Run with:
diff --git a/liblog/tests/liblog_test.cpp b/liblog/tests/liblog_test.cpp
index 2d0fc9b..83f0fa9 100644
--- a/liblog/tests/liblog_test.cpp
+++ b/liblog/tests/liblog_test.cpp
@@ -3160,41 +3160,6 @@
}
#endif // USING_LOGGER_DEFAULT
-#ifdef USING_LOGGER_DEFAULT // Do not retest ratelimit
-TEST(liblog, __android_log_ratelimit) {
- time_t state = 0;
-
- errno = 42;
- // Prime
- __android_log_ratelimit(3, &state);
- EXPECT_EQ(errno, 42);
- // Check
- EXPECT_FALSE(__android_log_ratelimit(3, &state));
- sleep(1);
- EXPECT_FALSE(__android_log_ratelimit(3, &state));
- sleep(4);
- EXPECT_TRUE(__android_log_ratelimit(3, &state));
- sleep(5);
- EXPECT_TRUE(__android_log_ratelimit(3, &state));
-
- // API checks
- IF_ALOG_RATELIMIT_LOCAL(3, &state) {
- EXPECT_FALSE(0 != "IF_ALOG_RATELIMIT_LOCAL(3, &state)");
- }
-
- IF_ALOG_RATELIMIT() {
- ;
- }
- else {
- EXPECT_TRUE(0 == "IF_ALOG_RATELIMIT()");
- }
- IF_ALOG_RATELIMIT() {
- EXPECT_FALSE(0 != "IF_ALOG_RATELIMIT()");
- }
- // Do not test default seconds, to allow liblog to tune freely
-}
-#endif // USING_LOGGER_DEFAULT
-
#ifdef USING_LOGGER_DEFAULT // Do not retest event mapping functionality
TEST(liblog, android_lookupEventTagNum) {
#ifdef __ANDROID__
diff --git a/libnativeloader/Android.bp b/libnativeloader/Android.bp
index 8903b72..2802d36 100644
--- a/libnativeloader/Android.bp
+++ b/libnativeloader/Android.bp
@@ -23,15 +23,6 @@
"llndk.libraries.txt",
"vndksp.libraries.txt",
],
- target: {
- android: {
- version_script: "libnativeloader.map.txt",
- },
- },
- stubs: {
- symbol_file: "libnativeloader.map.txt",
- versions: ["1"],
- },
}
cc_library_headers {
diff --git a/libnativeloader/OWNERS b/libnativeloader/OWNERS
index 5c28a9f..f735653 100644
--- a/libnativeloader/OWNERS
+++ b/libnativeloader/OWNERS
@@ -1,2 +1,6 @@
dimitry@google.com
jiyong@google.com
+ngeoffray@google.com
+oth@google.com
+mast@google.com
+rpl@google.com
diff --git a/libnativeloader/native_loader.cpp b/libnativeloader/native_loader.cpp
index f231afa..af7df72 100644
--- a/libnativeloader/native_loader.cpp
+++ b/libnativeloader/native_loader.cpp
@@ -632,7 +632,7 @@
*needs_native_bridge = false;
void* handle = dlopen(path, RTLD_NOW);
if (handle == nullptr) {
- *error_msg = dlerror();
+ *error_msg = strdup(dlerror());
}
return handle;
}
diff --git a/libstats/include/stats_event_list.h b/libstats/include/stats_event_list.h
index 162d1cf..b5bc5af 100644
--- a/libstats/include/stats_event_list.h
+++ b/libstats/include/stats_event_list.h
@@ -51,10 +51,6 @@
explicit stats_event_list(int tag) : ret(0) {
ctx = create_android_logger(static_cast<uint32_t>(tag));
}
- explicit stats_event_list(log_msg& log_msg) : ret(0) {
- ctx = create_android_log_parser(log_msg.msg() + sizeof(uint32_t),
- log_msg.entry.len - sizeof(uint32_t));
- }
~stats_event_list() { android_log_destroy(&ctx); }
int close() {
@@ -251,9 +247,6 @@
}
return ret >= 0;
}
-
- android_log_list_element read() { return android_log_read_next(ctx); }
- android_log_list_element peek() { return android_log_peek_next(ctx); }
};
#endif
diff --git a/libunwindstack/Android.bp b/libunwindstack/Android.bp
index e267f58..73dc921 100644
--- a/libunwindstack/Android.bp
+++ b/libunwindstack/Android.bp
@@ -127,6 +127,10 @@
},
},
+ whole_static_libs: [
+ "libdemangle"
+ ],
+
static_libs: [
"libprocinfo",
],
@@ -189,6 +193,7 @@
"tests/MapInfoCreateMemoryTest.cpp",
"tests/MapInfoGetElfTest.cpp",
"tests/MapInfoGetLoadBiasTest.cpp",
+ "tests/MapInfoTest.cpp",
"tests/MapsTest.cpp",
"tests/MemoryBufferTest.cpp",
"tests/MemoryCacheTest.cpp",
diff --git a/libunwindstack/MapInfo.cpp b/libunwindstack/MapInfo.cpp
index 39a09cf..b9d8b3d 100644
--- a/libunwindstack/MapInfo.cpp
+++ b/libunwindstack/MapInfo.cpp
@@ -221,6 +221,19 @@
return elf.get();
}
+bool MapInfo::GetFunctionName(uint64_t addr, std::string* name, uint64_t* func_offset) {
+ {
+ // Make sure no other thread is trying to update this elf object.
+ std::lock_guard<std::mutex> guard(mutex_);
+ if (elf == nullptr) {
+ return false;
+ }
+ }
+ // No longer need the lock, once the elf object is created, it is not deleted
+ // until this object is deleted.
+ return elf->GetFunctionName(addr, name, func_offset);
+}
+
uint64_t MapInfo::GetLoadBias(const std::shared_ptr<Memory>& process_memory) {
uint64_t cur_load_bias = load_bias.load();
if (cur_load_bias != static_cast<uint64_t>(-1)) {
diff --git a/libunwindstack/Unwinder.cpp b/libunwindstack/Unwinder.cpp
index 8133639..57207de 100644
--- a/libunwindstack/Unwinder.cpp
+++ b/libunwindstack/Unwinder.cpp
@@ -26,10 +26,13 @@
#include <android-base/stringprintf.h>
+#include <demangle.h>
+
#include <unwindstack/Elf.h>
#include <unwindstack/JitDebug.h>
#include <unwindstack/MapInfo.h>
#include <unwindstack/Maps.h>
+#include <unwindstack/Memory.h>
#include <unwindstack/Unwinder.h>
#if !defined(NO_LIBDEXFILE_SUPPORT)
@@ -306,7 +309,7 @@
}
if (!frame.function_name.empty()) {
- data += " (" + frame.function_name;
+ data += " (" + demangle(frame.function_name.c_str());
if (frame.function_offset != 0) {
data += android::base::StringPrintf("+%" PRId64, frame.function_offset);
}
@@ -327,4 +330,29 @@
}
#endif
+bool UnwinderFromPid::Init(ArchEnum arch) {
+ if (pid_ == getpid()) {
+ maps_ptr_.reset(new LocalMaps());
+ } else {
+ maps_ptr_.reset(new RemoteMaps(pid_));
+ }
+ if (!maps_ptr_->Parse()) {
+ return false;
+ }
+ maps_ = maps_ptr_.get();
+
+ process_memory_ = Memory::CreateProcessMemoryCached(pid_);
+
+ jit_debug_ptr_.reset(new JitDebug(process_memory_));
+ jit_debug_ = jit_debug_ptr_.get();
+ SetJitDebug(jit_debug_, arch);
+#if !defined(NO_LIBDEXFILE_SUPPORT)
+ dex_files_ptr_.reset(new DexFiles(process_memory_));
+ dex_files_ = dex_files_ptr_.get();
+ SetDexFiles(dex_files_, arch);
+#endif
+
+ return true;
+}
+
} // namespace unwindstack
diff --git a/libunwindstack/include/unwindstack/MapInfo.h b/libunwindstack/include/unwindstack/MapInfo.h
index 5e3d6f6..a9febd1 100644
--- a/libunwindstack/include/unwindstack/MapInfo.h
+++ b/libunwindstack/include/unwindstack/MapInfo.h
@@ -75,6 +75,8 @@
Memory* CreateMemory(const std::shared_ptr<Memory>& process_memory);
+ bool GetFunctionName(uint64_t addr, std::string* name, uint64_t* func_offset);
+
private:
MapInfo(const MapInfo&) = delete;
void operator=(const MapInfo&) = delete;
diff --git a/libunwindstack/include/unwindstack/Unwinder.h b/libunwindstack/include/unwindstack/Unwinder.h
index d7bbd9d..ab239c1 100644
--- a/libunwindstack/include/unwindstack/Unwinder.h
+++ b/libunwindstack/include/unwindstack/Unwinder.h
@@ -24,7 +24,9 @@
#include <string>
#include <vector>
+#include <unwindstack/DexFiles.h>
#include <unwindstack/Error.h>
+#include <unwindstack/JitDebug.h>
#include <unwindstack/Maps.h>
#include <unwindstack/Memory.h>
#include <unwindstack/Regs.h>
@@ -32,9 +34,7 @@
namespace unwindstack {
// Forward declarations.
-class DexFiles;
class Elf;
-class JitDebug;
enum ArchEnum : uint8_t;
struct FrameData {
@@ -67,6 +67,11 @@
: max_frames_(max_frames), maps_(maps), regs_(regs), process_memory_(process_memory) {
frames_.reserve(max_frames);
}
+ Unwinder(size_t max_frames, Maps* maps, std::shared_ptr<Memory> process_memory)
+ : max_frames_(max_frames), maps_(maps), process_memory_(process_memory) {
+ frames_.reserve(max_frames);
+ }
+
~Unwinder() = default;
void Unwind(const std::vector<std::string>* initial_map_names_to_skip = nullptr,
@@ -81,6 +86,10 @@
void SetJitDebug(JitDebug* jit_debug, ArchEnum arch);
+ void SetRegs(Regs* regs) { regs_ = regs; }
+ Maps* GetMaps() { return maps_; }
+ std::shared_ptr<Memory>& GetProcessMemory() { return process_memory_; }
+
// Disabling the resolving of names results in the function name being
// set to an empty string and the function offset being set to zero.
void SetResolveNames(bool resolve) { resolve_names_ = resolve; }
@@ -92,7 +101,9 @@
ErrorCode LastErrorCode() { return last_error_.code; }
uint64_t LastErrorAddress() { return last_error_.address; }
- private:
+ protected:
+ Unwinder(size_t max_frames) : max_frames_(max_frames) { frames_.reserve(max_frames); }
+
void FillInDexFrame();
void FillInFrame(MapInfo* map_info, Elf* elf, uint64_t rel_pc, uint64_t func_pc,
uint64_t pc_adjustment);
@@ -110,6 +121,22 @@
ErrorData last_error_;
};
+class UnwinderFromPid : public Unwinder {
+ public:
+ UnwinderFromPid(size_t max_frames, pid_t pid) : Unwinder(max_frames), pid_(pid) {}
+ ~UnwinderFromPid() = default;
+
+ bool Init(ArchEnum arch);
+
+ private:
+ pid_t pid_;
+ std::unique_ptr<Maps> maps_ptr_;
+ std::unique_ptr<JitDebug> jit_debug_ptr_;
+#if !defined(NO_LIBDEXFILE_SUPPORT)
+ std::unique_ptr<DexFiles> dex_files_ptr_;
+#endif
+};
+
} // namespace unwindstack
#endif // _LIBUNWINDSTACK_UNWINDER_H
diff --git a/libunwindstack/tests/MapInfoTest.cpp b/libunwindstack/tests/MapInfoTest.cpp
new file mode 100644
index 0000000..e2cbb98
--- /dev/null
+++ b/libunwindstack/tests/MapInfoTest.cpp
@@ -0,0 +1,75 @@
+/*
+ * Copyright (C) 2018 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 <stdint.h>
+
+#include <gtest/gtest.h>
+
+#include <unwindstack/MapInfo.h>
+#include <unwindstack/Maps.h>
+
+#include "ElfFake.h"
+
+namespace unwindstack {
+
+TEST(MapInfoTest, maps_constructor_const_char) {
+ MapInfo prev_map(nullptr, 0, 0, 0, 0, "");
+ MapInfo map_info(&prev_map, 1, 2, 3, 4, "map");
+
+ EXPECT_EQ(&prev_map, map_info.prev_map);
+ EXPECT_EQ(1UL, map_info.start);
+ EXPECT_EQ(2UL, map_info.end);
+ EXPECT_EQ(3UL, map_info.offset);
+ EXPECT_EQ(4UL, map_info.flags);
+ EXPECT_EQ("map", map_info.name);
+ EXPECT_EQ(static_cast<uint64_t>(-1), map_info.load_bias);
+ EXPECT_EQ(0UL, map_info.elf_offset);
+ EXPECT_TRUE(map_info.elf.get() == nullptr);
+}
+
+TEST(MapInfoTest, maps_constructor_string) {
+ std::string name("string_map");
+ MapInfo prev_map(nullptr, 0, 0, 0, 0, "");
+ MapInfo map_info(&prev_map, 1, 2, 3, 4, name);
+
+ EXPECT_EQ(&prev_map, map_info.prev_map);
+ EXPECT_EQ(1UL, map_info.start);
+ EXPECT_EQ(2UL, map_info.end);
+ EXPECT_EQ(3UL, map_info.offset);
+ EXPECT_EQ(4UL, map_info.flags);
+ EXPECT_EQ("string_map", map_info.name);
+ EXPECT_EQ(static_cast<uint64_t>(-1), map_info.load_bias);
+ EXPECT_EQ(0UL, map_info.elf_offset);
+ EXPECT_TRUE(map_info.elf.get() == nullptr);
+}
+
+TEST(MapInfoTest, get_function_name) {
+ ElfFake* elf = new ElfFake(nullptr);
+ ElfInterfaceFake* interface = new ElfInterfaceFake(nullptr);
+ elf->FakeSetInterface(interface);
+ interface->FakePushFunctionData(FunctionData("function", 1000));
+
+ MapInfo map_info(nullptr, 1, 2, 3, 4, "");
+ map_info.elf.reset(elf);
+
+ std::string name;
+ uint64_t offset;
+ ASSERT_TRUE(map_info.GetFunctionName(1000, &name, &offset));
+ EXPECT_EQ("function", name);
+ EXPECT_EQ(1000UL, offset);
+}
+
+} // namespace unwindstack
diff --git a/libunwindstack/tests/UnwindOfflineTest.cpp b/libunwindstack/tests/UnwindOfflineTest.cpp
index aab9ec2..0588a84 100644
--- a/libunwindstack/tests/UnwindOfflineTest.cpp
+++ b/libunwindstack/tests/UnwindOfflineTest.cpp
@@ -210,8 +210,8 @@
ASSERT_EQ(4U, unwinder.NumFrames()) << "Unwind:\n" << frame_info;
EXPECT_EQ(
" #00 pc 0001a9f8 libc.so (abort+64)\n"
- " #01 pc 00006a1b libbase.so (_ZN7android4base14DefaultAborterEPKc+6)\n"
- " #02 pc 00007441 libbase.so (_ZN7android4base10LogMessageD2Ev+748)\n"
+ " #01 pc 00006a1b libbase.so (android::base::DefaultAborter(char const*)+6)\n"
+ " #02 pc 00007441 libbase.so (android::base::LogMessage::~LogMessage()+748)\n"
" #03 pc 00015147 /does/not/exist/libhidlbase.so\n",
frame_info);
EXPECT_EQ(0xf31ea9f8U, unwinder.frames()[0].pc);
@@ -234,9 +234,10 @@
ASSERT_EQ(2U, unwinder.NumFrames()) << "Unwind:\n" << frame_info;
EXPECT_EQ(
" #00 pc 0006dc49 libandroid_runtime.so "
- "(_ZN7android14AndroidRuntime15javaThreadShellEPv+80)\n"
+ "(android::AndroidRuntime::javaThreadShell(void*)+80)\n"
" #01 pc 0006dce5 libandroid_runtime.so "
- "(_ZN7android14AndroidRuntime19javaCreateThreadEtcEPFiPvES1_PKcijPS1_)\n",
+ "(android::AndroidRuntime::javaCreateThreadEtc(int (*)(void*), void*, char const*, int, "
+ "unsigned int, void**))\n",
frame_info);
EXPECT_EQ(0xf1f6dc49U, unwinder.frames()[0].pc);
EXPECT_EQ(0xd8fe6930U, unwinder.frames()[0].sp);
@@ -257,10 +258,10 @@
" #01 pc 000000000042a078 libunwindstack_test (SignalMiddleFunction+8)\n"
" #02 pc 000000000042a08c libunwindstack_test (SignalOuterFunction+8)\n"
" #03 pc 000000000042d8fc libunwindstack_test "
- "(_ZN11unwindstackL19RemoteThroughSignalEij+20)\n"
+ "(unwindstack::RemoteThroughSignal(int, unsigned int)+20)\n"
" #04 pc 000000000042d8d8 libunwindstack_test "
- "(_ZN11unwindstack37UnwindTest_remote_through_signal_Test8TestBodyEv+32)\n"
- " #05 pc 0000000000455d70 libunwindstack_test (_ZN7testing4Test3RunEv+392)\n",
+ "(unwindstack::UnwindTest_remote_through_signal_Test::TestBody()+32)\n"
+ " #05 pc 0000000000455d70 libunwindstack_test (testing::Test::Run()+392)\n",
frame_info);
EXPECT_EQ(0x64d09d4fd8U, unwinder.frames()[0].pc);
EXPECT_EQ(0x7fe0d84040U, unwinder.frames()[0].sp);
@@ -296,54 +297,57 @@
std::string frame_info(DumpFrames(unwinder));
ASSERT_EQ(69U, unwinder.NumFrames()) << "Unwind:\n" << frame_info;
EXPECT_EQ(
- " #00 pc 00068fb8 libarttestd.so (_ZN3artL13CauseSegfaultEv+72)\n"
+ " #00 pc 00068fb8 libarttestd.so (art::CauseSegfault()+72)\n"
" #01 pc 00067f00 libarttestd.so (Java_Main_unwindInProcess+10032)\n"
" #02 pc 000021a8 137-cfi.odex (offset 0x2000) (boolean Main.unwindInProcess(boolean, int, "
"boolean)+136)\n"
" #03 pc 0000fe80 anonymous:ee74c000 (boolean Main.bar(boolean)+64)\n"
" #04 pc 006ad4d2 libartd.so (art_quick_invoke_stub+338)\n"
" #05 pc 00146ab5 libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+885)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+885)\n"
" #06 pc 0039cf0d libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+653)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+653)\n"
" #07 pc 00392552 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+354)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+354)\n"
" #08 pc 0039399a libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+234)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+234)\n"
" #09 pc 00684362 libartd.so (artQuickToInterpreterBridge+1058)\n"
" #10 pc 006b35bd libartd.so (art_quick_to_interpreter_bridge+77)\n"
" #11 pc 0000fe03 anonymous:ee74c000 (int Main.compare(Main, Main)+51)\n"
" #12 pc 006ad4d2 libartd.so (art_quick_invoke_stub+338)\n"
" #13 pc 00146ab5 libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+885)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+885)\n"
" #14 pc 0039cf0d libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+653)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+653)\n"
" #15 pc 00392552 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+354)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+354)\n"
" #16 pc 0039399a libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+234)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+234)\n"
" #17 pc 00684362 libartd.so (artQuickToInterpreterBridge+1058)\n"
" #18 pc 006b35bd libartd.so (art_quick_to_interpreter_bridge+77)\n"
" #19 pc 0000fd3b anonymous:ee74c000 (int Main.compare(java.lang.Object, "
"java.lang.Object)+107)\n"
" #20 pc 006ad4d2 libartd.so (art_quick_invoke_stub+338)\n"
" #21 pc 00146ab5 libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+885)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+885)\n"
" #22 pc 0039cf0d libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+653)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+653)\n"
" #23 pc 00392552 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+354)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+354)\n"
" #24 pc 0039399a libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+234)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+234)\n"
" #25 pc 00684362 libartd.so (artQuickToInterpreterBridge+1058)\n"
" #26 pc 006b35bd libartd.so (art_quick_to_interpreter_bridge+77)\n"
" #27 pc 0000fbdb anonymous:ee74c000 (int "
@@ -351,81 +355,86 @@
"java.util.Comparator)+331)\n"
" #28 pc 006ad6a2 libartd.so (art_quick_invoke_static_stub+418)\n"
" #29 pc 00146acb libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+907)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+907)\n"
" #30 pc 0039cf0d libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+653)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+653)\n"
" #31 pc 00392552 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+354)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+354)\n"
" #32 pc 0039399a libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+234)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+234)\n"
" #33 pc 00684362 libartd.so (artQuickToInterpreterBridge+1058)\n"
" #34 pc 006b35bd libartd.so (art_quick_to_interpreter_bridge+77)\n"
" #35 pc 0000f624 anonymous:ee74c000 (boolean Main.foo()+164)\n"
" #36 pc 006ad4d2 libartd.so (art_quick_invoke_stub+338)\n"
" #37 pc 00146ab5 libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+885)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+885)\n"
" #38 pc 0039cf0d libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+653)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+653)\n"
" #39 pc 00392552 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+354)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+354)\n"
" #40 pc 0039399a libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+234)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+234)\n"
" #41 pc 00684362 libartd.so (artQuickToInterpreterBridge+1058)\n"
" #42 pc 006b35bd libartd.so (art_quick_to_interpreter_bridge+77)\n"
" #43 pc 0000eedb anonymous:ee74c000 (void Main.runPrimary()+59)\n"
" #44 pc 006ad4d2 libartd.so (art_quick_invoke_stub+338)\n"
" #45 pc 00146ab5 libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+885)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+885)\n"
" #46 pc 0039cf0d libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+653)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+653)\n"
" #47 pc 00392552 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+354)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+354)\n"
" #48 pc 0039399a libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+234)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+234)\n"
" #49 pc 00684362 libartd.so (artQuickToInterpreterBridge+1058)\n"
" #50 pc 006b35bd libartd.so (art_quick_to_interpreter_bridge+77)\n"
" #51 pc 0000ac21 anonymous:ee74c000 (void Main.main(java.lang.String[])+97)\n"
" #52 pc 006ad6a2 libartd.so (art_quick_invoke_static_stub+418)\n"
" #53 pc 00146acb libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+907)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+907)\n"
" #54 pc 0039cf0d libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+653)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+653)\n"
" #55 pc 00392552 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+354)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+354)\n"
" #56 pc 0039399a libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+234)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+234)\n"
" #57 pc 00684362 libartd.so (artQuickToInterpreterBridge+1058)\n"
" #58 pc 006b35bd libartd.so (art_quick_to_interpreter_bridge+77)\n"
" #59 pc 006ad6a2 libartd.so (art_quick_invoke_static_stub+418)\n"
" #60 pc 00146acb libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+907)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+907)\n"
" #61 pc 005aac95 libartd.so "
- "(_ZN3artL18InvokeWithArgArrayERKNS_33ScopedObjectAccessAlreadyRunnableEPNS_9ArtMethodEPNS_"
- "8ArgArrayEPNS_6JValueEPKc+85)\n"
+ "(art::InvokeWithArgArray(art::ScopedObjectAccessAlreadyRunnable const&, art::ArtMethod*, "
+ "art::ArgArray*, art::JValue*, char const*)+85)\n"
" #62 pc 005aab5a libartd.so "
- "(_ZN3art17InvokeWithVarArgsERKNS_33ScopedObjectAccessAlreadyRunnableEP8_jobjectP10_"
- "jmethodIDPc+362)\n"
+ "(art::InvokeWithVarArgs(art::ScopedObjectAccessAlreadyRunnable const&, _jobject*, "
+ "_jmethodID*, char*)+362)\n"
" #63 pc 0048a3dd libartd.so "
- "(_ZN3art3JNI21CallStaticVoidMethodVEP7_JNIEnvP7_jclassP10_jmethodIDPc+125)\n"
+ "(art::JNI::CallStaticVoidMethodV(_JNIEnv*, _jclass*, _jmethodID*, char*)+125)\n"
" #64 pc 0018448c libartd.so "
- "(_ZN3art8CheckJNI11CallMethodVEPKcP7_JNIEnvP8_jobjectP7_jclassP10_jmethodIDPcNS_"
- "9Primitive4TypeENS_10InvokeTypeE+1964)\n"
+ "(art::CheckJNI::CallMethodV(char const*, _JNIEnv*, _jobject*, _jclass*, _jmethodID*, char*, "
+ "art::Primitive::Type, art::InvokeType)+1964)\n"
" #65 pc 0017cf06 libartd.so "
- "(_ZN3art8CheckJNI21CallStaticVoidMethodVEP7_JNIEnvP7_jclassP10_jmethodIDPc+70)\n"
+ "(art::CheckJNI::CallStaticVoidMethodV(_JNIEnv*, _jclass*, _jmethodID*, char*)+70)\n"
" #66 pc 00001d8c dalvikvm32 "
- "(_ZN7_JNIEnv20CallStaticVoidMethodEP7_jclassP10_jmethodIDz+60)\n"
+ "(_JNIEnv::CallStaticVoidMethod(_jclass*, _jmethodID*, ...)+60)\n"
" #67 pc 00001a80 dalvikvm32 (main+1312)\n"
" #68 pc 00018275 libc.so\n",
frame_info);
@@ -597,32 +606,34 @@
" #03 pc 00462175 libartd.so (art_quick_invoke_stub_internal+68)\n"
" #04 pc 00467129 libartd.so (art_quick_invoke_stub+228)\n"
" #05 pc 000bf7a9 libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+864)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+864)\n"
" #06 pc 00247833 libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+382)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+382)\n"
" #07 pc 0022e935 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+244)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+244)\n"
" #08 pc 0022f71d libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+128)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+128)\n"
" #09 pc 00442865 libartd.so (artQuickToInterpreterBridge+796)\n"
" #10 pc 004666ff libartd.so (art_quick_to_interpreter_bridge+30)\n"
" #11 pc 00011c31 anonymous:e2796000 (int Main.compare(Main, Main)+64)\n"
" #12 pc 00462175 libartd.so (art_quick_invoke_stub_internal+68)\n"
" #13 pc 00467129 libartd.so (art_quick_invoke_stub+228)\n"
" #14 pc 000bf7a9 libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+864)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+864)\n"
" #15 pc 00247833 libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+382)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+382)\n"
" #16 pc 0022e935 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+244)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+244)\n"
" #17 pc 0022f71d libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+128)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+128)\n"
" #18 pc 00442865 libartd.so (artQuickToInterpreterBridge+796)\n"
" #19 pc 004666ff libartd.so (art_quick_to_interpreter_bridge+30)\n"
" #20 pc 00011b77 anonymous:e2796000 (int Main.compare(java.lang.Object, "
@@ -630,16 +641,17 @@
" #21 pc 00462175 libartd.so (art_quick_invoke_stub_internal+68)\n"
" #22 pc 00467129 libartd.so (art_quick_invoke_stub+228)\n"
" #23 pc 000bf7a9 libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+864)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+864)\n"
" #24 pc 00247833 libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+382)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+382)\n"
" #25 pc 0022e935 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+244)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+244)\n"
" #26 pc 0022f71d libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+128)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+128)\n"
" #27 pc 00442865 libartd.so (artQuickToInterpreterBridge+796)\n"
" #28 pc 004666ff libartd.so (art_quick_to_interpreter_bridge+30)\n"
" #29 pc 00011a29 anonymous:e2796000 (int "
@@ -648,85 +660,90 @@
" #30 pc 00462175 libartd.so (art_quick_invoke_stub_internal+68)\n"
" #31 pc 0046722f libartd.so (art_quick_invoke_static_stub+226)\n"
" #32 pc 000bf7bb libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+882)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+882)\n"
" #33 pc 00247833 libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+382)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+382)\n"
" #34 pc 0022e935 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+244)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+244)\n"
" #35 pc 0022f71d libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+128)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+128)\n"
" #36 pc 00442865 libartd.so (artQuickToInterpreterBridge+796)\n"
" #37 pc 004666ff libartd.so (art_quick_to_interpreter_bridge+30)\n"
" #38 pc 0001139b anonymous:e2796000 (boolean Main.foo()+178)\n"
" #39 pc 00462175 libartd.so (art_quick_invoke_stub_internal+68)\n"
" #40 pc 00467129 libartd.so (art_quick_invoke_stub+228)\n"
" #41 pc 000bf7a9 libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+864)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+864)\n"
" #42 pc 00247833 libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+382)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+382)\n"
" #43 pc 0022e935 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+244)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+244)\n"
" #44 pc 0022f71d libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+128)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+128)\n"
" #45 pc 00442865 libartd.so (artQuickToInterpreterBridge+796)\n"
" #46 pc 004666ff libartd.so (art_quick_to_interpreter_bridge+30)\n"
" #47 pc 00010aa7 anonymous:e2796000 (void Main.runPrimary()+70)\n"
" #48 pc 00462175 libartd.so (art_quick_invoke_stub_internal+68)\n"
" #49 pc 00467129 libartd.so (art_quick_invoke_stub+228)\n"
" #50 pc 000bf7a9 libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+864)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+864)\n"
" #51 pc 00247833 libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+382)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+382)\n"
" #52 pc 0022e935 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+244)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+244)\n"
" #53 pc 0022f71d libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+128)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+128)\n"
" #54 pc 00442865 libartd.so (artQuickToInterpreterBridge+796)\n"
" #55 pc 004666ff libartd.so (art_quick_to_interpreter_bridge+30)\n"
" #56 pc 0000ba99 anonymous:e2796000 (void Main.main(java.lang.String[])+144)\n"
" #57 pc 00462175 libartd.so (art_quick_invoke_stub_internal+68)\n"
" #58 pc 0046722f libartd.so (art_quick_invoke_static_stub+226)\n"
" #59 pc 000bf7bb libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+882)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+882)\n"
" #60 pc 00247833 libartd.so "
- "(_ZN3art11interpreter34ArtInterpreterToCompiledCodeBridgeEPNS_6ThreadEPNS_9ArtMethodEPNS_"
- "11ShadowFrameEtPNS_6JValueE+382)\n"
+ "(art::interpreter::ArtInterpreterToCompiledCodeBridge(art::Thread*, art::ArtMethod*, "
+ "art::ShadowFrame*, unsigned short, art::JValue*)+382)\n"
" #61 pc 0022e935 libartd.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+244)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+244)\n"
" #62 pc 0022f71d libartd.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+128)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+128)\n"
" #63 pc 00442865 libartd.so (artQuickToInterpreterBridge+796)\n"
" #64 pc 004666ff libartd.so (art_quick_to_interpreter_bridge+30)\n"
" #65 pc 00462175 libartd.so (art_quick_invoke_stub_internal+68)\n"
" #66 pc 0046722f libartd.so (art_quick_invoke_static_stub+226)\n"
" #67 pc 000bf7bb libartd.so "
- "(_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+882)\n"
+ "(art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char "
+ "const*)+882)\n"
" #68 pc 003b292d libartd.so "
- "(_ZN3artL18InvokeWithArgArrayERKNS_33ScopedObjectAccessAlreadyRunnableEPNS_9ArtMethodEPNS_"
- "8ArgArrayEPNS_6JValueEPKc+52)\n"
+ "(art::InvokeWithArgArray(art::ScopedObjectAccessAlreadyRunnable const&, art::ArtMethod*, "
+ "art::ArgArray*, art::JValue*, char const*)+52)\n"
" #69 pc 003b26c3 libartd.so "
- "(_ZN3art17InvokeWithVarArgsERKNS_33ScopedObjectAccessAlreadyRunnableEP8_jobjectP10_"
- "jmethodIDSt9__va_list+210)\n"
+ "(art::InvokeWithVarArgs(art::ScopedObjectAccessAlreadyRunnable const&, _jobject*, "
+ "_jmethodID*, std::__va_list)+210)\n"
" #70 pc 00308411 libartd.so "
- "(_ZN3art3JNI21CallStaticVoidMethodVEP7_JNIEnvP7_jclassP10_jmethodIDSt9__va_list+76)\n"
+ "(art::JNI::CallStaticVoidMethodV(_JNIEnv*, _jclass*, _jmethodID*, std::__va_list)+76)\n"
" #71 pc 000e6a9f libartd.so "
- "(_ZN3art8CheckJNI11CallMethodVEPKcP7_JNIEnvP8_jobjectP7_jclassP10_jmethodIDSt9__va_listNS_"
- "9Primitive4TypeENS_10InvokeTypeE+1486)\n"
+ "(art::CheckJNI::CallMethodV(char const*, _JNIEnv*, _jobject*, _jclass*, _jmethodID*, "
+ "std::__va_list, art::Primitive::Type, art::InvokeType)+1486)\n"
" #72 pc 000e19b9 libartd.so "
- "(_ZN3art8CheckJNI21CallStaticVoidMethodVEP7_JNIEnvP7_jclassP10_jmethodIDSt9__va_list+40)\n"
+ "(art::CheckJNI::CallStaticVoidMethodV(_JNIEnv*, _jclass*, _jmethodID*, std::__va_list)+40)\n"
" #73 pc 0000159f dalvikvm32 "
- "(_ZN7_JNIEnv20CallStaticVoidMethodEP7_jclassP10_jmethodIDz+30)\n"
+ "(_JNIEnv::CallStaticVoidMethod(_jclass*, _jmethodID*, ...)+30)\n"
" #74 pc 00001349 dalvikvm32 (main+896)\n"
" #75 pc 000850c9 libc.so\n",
frame_info);
@@ -997,41 +1014,44 @@
"(com.example.simpleperf.simpleperfexamplewithnative.MixActivity$1.run+60)\n"
" #02 pc 004135bb libart.so (art_quick_osr_stub+42)\n"
" #03 pc 002657a5 libart.so "
- "(_ZN3art3jit3Jit25MaybeDoOnStackReplacementEPNS_6ThreadEPNS_9ArtMethodEjiPNS_6JValueE+876)\n"
+ "(art::jit::Jit::MaybeDoOnStackReplacement(art::Thread*, art::ArtMethod*, unsigned int, int, "
+ "art::JValue*)+876)\n"
" #04 pc 004021a7 libart.so (MterpMaybeDoOnStackReplacement+86)\n"
" #05 pc 00412474 libart.so (ExecuteMterpImpl+66164)\n"
" #06 pc cd8365b0 <unknown>\n" // symbol in dex file
" #07 pc 001d7f1b libart.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+374)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+374)\n"
" #08 pc 001dc593 libart.so "
- "(_ZN3art11interpreter33ArtInterpreterToInterpreterBridgeEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameEPNS_6JValueE+154)\n"
+ "(art::interpreter::ArtInterpreterToInterpreterBridge(art::Thread*, "
+ "art::CodeItemDataAccessor const&, art::ShadowFrame*, art::JValue*)+154)\n"
" #09 pc 001f4d01 libart.so "
- "(_ZN3art11interpreter6DoCallILb0ELb0EEEbPNS_9ArtMethodEPNS_6ThreadERNS_11ShadowFrameEPKNS_"
- "11InstructionEtPNS_6JValueE+732)\n"
+ "(bool art::interpreter::DoCall<false, false>(art::ArtMethod*, art::Thread*, "
+ "art::ShadowFrame&, art::Instruction const*, unsigned short, art::JValue*)+732)\n"
" #10 pc 003fe427 libart.so (MterpInvokeInterface+1354)\n"
" #11 pc 00405b94 libart.so (ExecuteMterpImpl+14740)\n"
" #12 pc 7004873e <unknown>\n" // symbol in dex file
" #13 pc 001d7f1b libart.so "
- "(_ZN3art11interpreterL7ExecuteEPNS_6ThreadERKNS_20CodeItemDataAccessorERNS_11ShadowFrameENS_"
- "6JValueEb+374)\n"
+ "(art::interpreter::Execute(art::Thread*, art::CodeItemDataAccessor const&, "
+ "art::ShadowFrame&, art::JValue, bool)+374)\n"
" #14 pc 001dc4d5 libart.so "
- "(_ZN3art11interpreter30EnterInterpreterFromEntryPointEPNS_6ThreadERKNS_"
- "20CodeItemDataAccessorEPNS_11ShadowFrameE+92)\n"
+ "(art::interpreter::EnterInterpreterFromEntryPoint(art::Thread*, art::CodeItemDataAccessor "
+ "const&, art::ShadowFrame*)+92)\n"
" #15 pc 003f25ab libart.so (artQuickToInterpreterBridge+970)\n"
" #16 pc 00417aff libart.so (art_quick_to_interpreter_bridge+30)\n"
" #17 pc 00413575 libart.so (art_quick_invoke_stub_internal+68)\n"
" #18 pc 00418531 libart.so (art_quick_invoke_stub+236)\n"
- " #19 pc 000b468d libart.so (_ZN3art9ArtMethod6InvokeEPNS_6ThreadEPjjPNS_6JValueEPKc+136)\n"
+ " #19 pc 000b468d libart.so (art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned "
+ "int, art::JValue*, char const*)+136)\n"
" #20 pc 00362f49 libart.so "
- "(_ZN3art12_GLOBAL__N_118InvokeWithArgArrayERKNS_33ScopedObjectAccessAlreadyRunnableEPNS_"
- "9ArtMethodEPNS0_8ArgArrayEPNS_6JValueEPKc+52)\n"
+ "(art::(anonymous namespace)::InvokeWithArgArray(art::ScopedObjectAccessAlreadyRunnable "
+ "const&, art::ArtMethod*, art::(anonymous namespace)::ArgArray*, art::JValue*, char "
+ "const*)+52)\n"
" #21 pc 00363cd9 libart.so "
- "(_ZN3art35InvokeVirtualOrInterfaceWithJValuesERKNS_33ScopedObjectAccessAlreadyRunnableEP8_"
- "jobjectP10_jmethodIDP6jvalue+332)\n"
- " #22 pc 003851dd libart.so (_ZN3art6Thread14CreateCallbackEPv+868)\n"
- " #23 pc 00062925 libc.so (_ZL15__pthread_startPv+22)\n"
+ "(art::InvokeVirtualOrInterfaceWithJValues(art::ScopedObjectAccessAlreadyRunnable const&, "
+ "_jobject*, _jmethodID*, jvalue*)+332)\n"
+ " #22 pc 003851dd libart.so (art::Thread::CreateCallback(void*)+868)\n"
+ " #23 pc 00062925 libc.so (__pthread_start(void*)+22)\n"
" #24 pc 0001de39 libc.so (__start_thread+24)\n",
frame_info);
EXPECT_EQ(0xd025c788U, unwinder.frames()[0].pc);
@@ -1107,8 +1127,8 @@
"(com.example.simpleperf.simpleperfexamplewithnative.MixActivity$1.run+60)\n"
" #02 pc 004135bb libart.so (art_quick_osr_stub+42)\n"
- " #03 pc 003851dd libart.so (_ZN3art6Thread14CreateCallbackEPv+868)\n"
- " #04 pc 00062925 libc.so (_ZL15__pthread_startPv+22)\n"
+ " #03 pc 003851dd libart.so (art::Thread::CreateCallback(void*)+868)\n"
+ " #04 pc 00062925 libc.so (__pthread_start(void*)+22)\n"
" #05 pc 0001de39 libc.so (__start_thread+24)\n",
frame_info);
@@ -1139,22 +1159,22 @@
" #01 pc 0032bfeb libunwindstack_test (SignalMiddleFunction+2)\n"
" #02 pc 0032bff3 libunwindstack_test (SignalOuterFunction+2)\n"
" #03 pc 0032fed3 libunwindstack_test "
- "(_ZN11unwindstackL19SignalCallerHandlerEiP7siginfoPv+26)\n"
+ "(unwindstack::SignalCallerHandler(int, siginfo*, void*)+26)\n"
" #04 pc 00026528 libc.so\n"
" #05 pc 00000000 <unknown>\n"
" #06 pc 0032c2d9 libunwindstack_test (InnerFunction+736)\n"
" #07 pc 0032cc4f libunwindstack_test (MiddleFunction+42)\n"
" #08 pc 0032cc81 libunwindstack_test (OuterFunction+42)\n"
" #09 pc 0032e547 libunwindstack_test "
- "(_ZN11unwindstackL19RemoteThroughSignalEij+270)\n"
+ "(unwindstack::RemoteThroughSignal(int, unsigned int)+270)\n"
" #10 pc 0032ed99 libunwindstack_test "
- "(_ZN11unwindstack55UnwindTest_remote_through_signal_with_invalid_func_Test8TestBodyEv+16)\n"
- " #11 pc 00354453 libunwindstack_test (_ZN7testing4Test3RunEv+154)\n"
- " #12 pc 00354de7 libunwindstack_test (_ZN7testing8TestInfo3RunEv+194)\n"
- " #13 pc 00355105 libunwindstack_test (_ZN7testing8TestCase3RunEv+180)\n"
+ "(unwindstack::UnwindTest_remote_through_signal_with_invalid_func_Test::TestBody()+16)\n"
+ " #11 pc 00354453 libunwindstack_test (testing::Test::Run()+154)\n"
+ " #12 pc 00354de7 libunwindstack_test (testing::TestInfo::Run()+194)\n"
+ " #13 pc 00355105 libunwindstack_test (testing::TestCase::Run()+180)\n"
" #14 pc 0035a215 libunwindstack_test "
- "(_ZN7testing8internal12UnitTestImpl11RunAllTestsEv+664)\n"
- " #15 pc 00359f4f libunwindstack_test (_ZN7testing8UnitTest3RunEv+110)\n"
+ "(testing::internal::UnitTestImpl::RunAllTests()+664)\n"
+ " #15 pc 00359f4f libunwindstack_test (testing::UnitTest::Run()+110)\n"
" #16 pc 0034d3db libunwindstack_test (main+38)\n"
" #17 pc 00092c0d libc.so (__libc_init+48)\n"
" #18 pc 0004202f libunwindstack_test (_start_main+38)\n",
@@ -1213,9 +1233,9 @@
EXPECT_EQ(
" #00 pc 0005138c libc.so (__ioctl+8)\n"
" #01 pc 0002140f libc.so (ioctl+30)\n"
- " #02 pc 00039535 libbinder.so (_ZN7android14IPCThreadState14talkWithDriverEb+204)\n"
- " #03 pc 00039633 libbinder.so (_ZN7android14IPCThreadState20getAndExecuteCommandEv+10)\n"
- " #04 pc 00039b57 libbinder.so (_ZN7android14IPCThreadState14joinThreadPoolEb+38)\n"
+ " #02 pc 00039535 libbinder.so (android::IPCThreadState::talkWithDriver(bool)+204)\n"
+ " #03 pc 00039633 libbinder.so (android::IPCThreadState::getAndExecuteCommand()+10)\n"
+ " #04 pc 00039b57 libbinder.so (android::IPCThreadState::joinThreadPool(bool)+38)\n"
" #05 pc 00000c21 mediaserver (main+104)\n"
" #06 pc 00084b89 libc.so (__libc_init+48)\n"
" #07 pc 00000b77 mediaserver (_start_main+38)\n",
diff --git a/libunwindstack/tests/UnwindTest.cpp b/libunwindstack/tests/UnwindTest.cpp
index ea992c7..a91bd95 100644
--- a/libunwindstack/tests/UnwindTest.cpp
+++ b/libunwindstack/tests/UnwindTest.cpp
@@ -44,6 +44,13 @@
namespace unwindstack {
+enum TestTypeEnum : uint8_t {
+ TEST_TYPE_LOCAL_UNWINDER = 0,
+ TEST_TYPE_LOCAL_UNWINDER_FROM_PID,
+ TEST_TYPE_REMOTE,
+ TEST_TYPE_REMOTE_WITH_INVALID_CALL,
+};
+
static std::atomic_bool g_ready;
static volatile bool g_ready_for_remote;
static volatile bool g_signal_ready_for_remote;
@@ -88,10 +95,10 @@
SignalOuterFunction();
}
-static std::string ErrorMsg(const std::vector<const char*>& function_names, Unwinder& unwinder) {
+static std::string ErrorMsg(const std::vector<const char*>& function_names, Unwinder* unwinder) {
std::string unwind;
- for (size_t i = 0; i < unwinder.NumFrames(); i++) {
- unwind += unwinder.FormatFrame(i) + '\n';
+ for (size_t i = 0; i < unwinder->NumFrames(); i++) {
+ unwind += unwinder->FormatFrame(i) + '\n';
}
return std::string(
@@ -100,14 +107,10 @@
function_names.front() + "\n" + "Unwind data:\n" + unwind;
}
-static void VerifyUnwind(pid_t pid, Maps* maps, Regs* regs,
- std::vector<const char*> expected_function_names) {
- auto process_memory(Memory::CreateProcessMemory(pid));
+static void VerifyUnwind(Unwinder* unwinder, std::vector<const char*> expected_function_names) {
+ unwinder->Unwind();
- Unwinder unwinder(512, maps, regs, process_memory);
- unwinder.Unwind();
-
- for (auto& frame : unwinder.frames()) {
+ for (auto& frame : unwinder->frames()) {
if (frame.function_name == expected_function_names.back()) {
expected_function_names.pop_back();
if (expected_function_names.empty()) {
@@ -119,35 +122,55 @@
ASSERT_TRUE(expected_function_names.empty()) << ErrorMsg(expected_function_names, unwinder);
}
+static void VerifyUnwind(pid_t pid, Maps* maps, Regs* regs,
+ std::vector<const char*> expected_function_names) {
+ auto process_memory(Memory::CreateProcessMemory(pid));
+
+ Unwinder unwinder(512, maps, regs, process_memory);
+ VerifyUnwind(&unwinder, expected_function_names);
+}
+
// This test assumes that this code is compiled with optimizations turned
// off. If this doesn't happen, then all of the calls will be optimized
// away.
-extern "C" void InnerFunction(bool local, bool trigger_invalid_call) {
- if (local) {
- LocalMaps maps;
- ASSERT_TRUE(maps.Parse());
- std::unique_ptr<Regs> regs(Regs::CreateFromLocal());
- RegsGetLocal(regs.get());
-
- VerifyUnwind(getpid(), &maps, regs.get(), kFunctionOrder);
- } else {
+extern "C" void InnerFunction(TestTypeEnum test_type) {
+ if (test_type == TEST_TYPE_REMOTE || test_type == TEST_TYPE_REMOTE_WITH_INVALID_CALL) {
g_ready_for_remote = true;
g_ready = true;
- if (trigger_invalid_call) {
+ if (test_type == TEST_TYPE_REMOTE_WITH_INVALID_CALL) {
void (*crash_func)() = nullptr;
crash_func();
}
while (!g_finish.load()) {
}
+ return;
}
+
+ std::unique_ptr<Unwinder> unwinder;
+ std::unique_ptr<Regs> regs(Regs::CreateFromLocal());
+ RegsGetLocal(regs.get());
+ std::unique_ptr<Maps> maps;
+
+ if (test_type == TEST_TYPE_LOCAL_UNWINDER) {
+ maps.reset(new LocalMaps());
+ ASSERT_TRUE(maps->Parse());
+ auto process_memory(Memory::CreateProcessMemory(getpid()));
+ unwinder.reset(new Unwinder(512, maps.get(), regs.get(), process_memory));
+ } else {
+ UnwinderFromPid* unwinder_from_pid = new UnwinderFromPid(512, getpid());
+ ASSERT_TRUE(unwinder_from_pid->Init(regs->Arch()));
+ unwinder_from_pid->SetRegs(regs.get());
+ unwinder.reset(unwinder_from_pid);
+ }
+ VerifyUnwind(unwinder.get(), kFunctionOrder);
}
-extern "C" void MiddleFunction(bool local, bool trigger_invalid_call) {
- InnerFunction(local, trigger_invalid_call);
+extern "C" void MiddleFunction(TestTypeEnum test_type) {
+ InnerFunction(test_type);
}
-extern "C" void OuterFunction(bool local, bool trigger_invalid_call) {
- MiddleFunction(local, trigger_invalid_call);
+extern "C" void OuterFunction(TestTypeEnum test_type) {
+ MiddleFunction(test_type);
}
class UnwindTest : public ::testing::Test {
@@ -156,7 +179,11 @@
};
TEST_F(UnwindTest, local) {
- OuterFunction(true, false);
+ OuterFunction(TEST_TYPE_LOCAL_UNWINDER);
+}
+
+TEST_F(UnwindTest, local_use_from_pid) {
+ OuterFunction(TEST_TYPE_LOCAL_UNWINDER_FROM_PID);
}
void WaitForRemote(pid_t pid, uint64_t addr, bool leave_attached, bool* completed) {
@@ -191,7 +218,7 @@
TEST_F(UnwindTest, remote) {
pid_t pid;
if ((pid = fork()) == 0) {
- OuterFunction(false, false);
+ OuterFunction(TEST_TYPE_REMOTE);
exit(0);
}
ASSERT_NE(-1, pid);
@@ -212,11 +239,39 @@
<< "ptrace detach failed with unexpected error: " << strerror(errno);
}
+TEST_F(UnwindTest, unwind_from_pid_remote) {
+ pid_t pid;
+ if ((pid = fork()) == 0) {
+ OuterFunction(TEST_TYPE_REMOTE);
+ exit(0);
+ }
+ ASSERT_NE(-1, pid);
+ TestScopedPidReaper reap(pid);
+
+ bool completed;
+ WaitForRemote(pid, reinterpret_cast<uint64_t>(&g_ready_for_remote), true, &completed);
+ ASSERT_TRUE(completed) << "Timed out waiting for remote process to be ready.";
+
+ std::unique_ptr<Regs> regs(Regs::RemoteGet(pid));
+ ASSERT_TRUE(regs.get() != nullptr);
+
+ UnwinderFromPid unwinder(512, pid);
+ ASSERT_TRUE(unwinder.Init(regs->Arch()));
+ unwinder.SetRegs(regs.get());
+
+ VerifyUnwind(&unwinder, kFunctionOrder);
+
+ // Verify that calling the same object works again.
+
+ ASSERT_EQ(0, ptrace(PTRACE_DETACH, pid, 0, 0))
+ << "ptrace detach failed with unexpected error: " << strerror(errno);
+}
+
TEST_F(UnwindTest, from_context) {
std::atomic_int tid(0);
std::thread thread([&]() {
tid = syscall(__NR_gettid);
- OuterFunction(false, false);
+ OuterFunction(TEST_TYPE_REMOTE);
});
struct sigaction act, oldact;
@@ -266,7 +321,7 @@
act.sa_flags = SA_RESTART | SA_ONSTACK | sa_flags;
ASSERT_EQ(0, sigaction(signal, &act, &oldact));
- OuterFunction(false, signal == SIGSEGV);
+ OuterFunction(signal != SIGSEGV ? TEST_TYPE_REMOTE : TEST_TYPE_REMOTE_WITH_INVALID_CALL);
exit(0);
}
ASSERT_NE(-1, pid);
diff --git a/libunwindstack/tests/UnwinderTest.cpp b/libunwindstack/tests/UnwinderTest.cpp
index 1fdeee5..49aeeb3 100644
--- a/libunwindstack/tests/UnwinderTest.cpp
+++ b/libunwindstack/tests/UnwinderTest.cpp
@@ -1080,6 +1080,12 @@
Unwinder::FormatFrame(frame, false));
EXPECT_EQ(" #01 pc 00001000 /fake/libfake.so (function)", Unwinder::FormatFrame(frame, true));
+ // Verify the function name is demangled.
+ frame.function_name = "_ZN4funcEv";
+ EXPECT_EQ(" #01 pc 0000000000001000 /fake/libfake.so (func())",
+ Unwinder::FormatFrame(frame, false));
+ EXPECT_EQ(" #01 pc 00001000 /fake/libfake.so (func())", Unwinder::FormatFrame(frame, true));
+
frame.function_name = "";
EXPECT_EQ(" #01 pc 0000000000001000 /fake/libfake.so", Unwinder::FormatFrame(frame, false));
EXPECT_EQ(" #01 pc 00001000 /fake/libfake.so", Unwinder::FormatFrame(frame, true));
diff --git a/libunwindstack/tools/unwind.cpp b/libunwindstack/tools/unwind.cpp
index e729453..1812e50 100644
--- a/libunwindstack/tools/unwind.cpp
+++ b/libunwindstack/tools/unwind.cpp
@@ -57,12 +57,6 @@
}
void DoUnwind(pid_t pid) {
- unwindstack::RemoteMaps remote_maps(pid);
- if (!remote_maps.Parse()) {
- printf("Failed to parse map data.\n");
- return;
- }
-
unwindstack::Regs* regs = unwindstack::Regs::RemoteGet(pid);
if (regs == nullptr) {
printf("Unable to get remote reg data\n");
@@ -95,15 +89,13 @@
}
printf("\n");
- auto process_memory = unwindstack::Memory::CreateProcessMemory(pid);
- unwindstack::Unwinder unwinder(128, &remote_maps, regs, process_memory);
+ unwindstack::UnwinderFromPid unwinder(1024, pid);
+ if (!unwinder.Init(regs->Arch())) {
+ printf("Failed to init unwinder object.\n");
+ return;
+ }
- unwindstack::JitDebug jit_debug(process_memory);
- unwinder.SetJitDebug(&jit_debug, regs->Arch());
-
- unwindstack::DexFiles dex_files(process_memory);
- unwinder.SetDexFiles(&dex_files, regs->Arch());
-
+ unwinder.SetRegs(regs);
unwinder.Unwind();
// Print the frames.
diff --git a/libunwindstack/tools/unwind_for_offline.cpp b/libunwindstack/tools/unwind_for_offline.cpp
index 5ae8874..4f67d67 100644
--- a/libunwindstack/tools/unwind_for_offline.cpp
+++ b/libunwindstack/tools/unwind_for_offline.cpp
@@ -240,12 +240,6 @@
return 1;
}
- unwindstack::RemoteMaps maps(pid);
- if (!maps.Parse()) {
- printf("Unable to parse maps.\n");
- return 1;
- }
-
// Save the current state of the registers.
if (!SaveRegs(regs)) {
return 1;
@@ -253,35 +247,38 @@
// Do an unwind so we know how much of the stack to save, and what
// elf files are involved.
+ unwindstack::UnwinderFromPid unwinder(1024, pid);
+ if (!unwinder.Init(regs->Arch())) {
+ printf("Unable to init unwinder object.\n");
+ return 1;
+ }
+ unwinder.SetRegs(regs);
uint64_t sp = regs->sp();
- auto process_memory = unwindstack::Memory::CreateProcessMemory(pid);
- unwindstack::JitDebug jit_debug(process_memory);
- unwindstack::Unwinder unwinder(1024, &maps, regs, process_memory);
- unwinder.SetJitDebug(&jit_debug, regs->Arch());
unwinder.Unwind();
std::unordered_map<uint64_t, map_info_t> maps_by_start;
std::vector<std::pair<uint64_t, uint64_t>> stacks;
+ unwindstack::Maps* maps = unwinder.GetMaps();
uint64_t sp_map_start = 0;
- unwindstack::MapInfo* map_info = maps.Find(sp);
+ unwindstack::MapInfo* map_info = maps->Find(sp);
if (map_info != nullptr) {
stacks.emplace_back(std::make_pair(sp, map_info->end));
sp_map_start = map_info->start;
}
for (const auto& frame : unwinder.frames()) {
- map_info = maps.Find(frame.sp);
+ map_info = maps->Find(frame.sp);
if (map_info != nullptr && sp_map_start != map_info->start) {
stacks.emplace_back(std::make_pair(frame.sp, map_info->end));
sp_map_start = map_info->start;
}
if (maps_by_start.count(frame.map_start) == 0) {
- map_info = maps.Find(frame.map_start);
+ map_info = maps->Find(frame.map_start);
auto info = FillInAndGetMapInfo(maps_by_start, map_info);
bool file_copied = false;
- SaveMapInformation(process_memory, info, &file_copied);
+ SaveMapInformation(unwinder.GetProcessMemory(), info, &file_copied);
// If you are using a a linker that creates two maps (one read-only, one
// read-executable), it's necessary to capture the previous map
@@ -291,7 +288,7 @@
prev_map->flags == PROT_READ && map_info->name == prev_map->name &&
maps_by_start.count(prev_map->start) == 0) {
info = FillInAndGetMapInfo(maps_by_start, prev_map);
- SaveMapInformation(process_memory, info, &file_copied);
+ SaveMapInformation(unwinder.GetProcessMemory(), info, &file_copied);
}
}
}
diff --git a/logd/.clang-format b/logd/.clang-format
deleted file mode 100644
index 393c309..0000000
--- a/logd/.clang-format
+++ /dev/null
@@ -1,11 +0,0 @@
-BasedOnStyle: Google
-AllowShortFunctionsOnASingleLine: false
-
-CommentPragmas: NOLINT:.*
-DerivePointerAlignment: false
-IndentWidth: 4
-PointerAlignment: Left
-TabWidth: 4
-PenaltyExcessCharacter: 32
-
-Cpp11BracedListStyle: false
diff --git a/logd/.clang-format b/logd/.clang-format
new file mode 120000
index 0000000..1af4f51
--- /dev/null
+++ b/logd/.clang-format
@@ -0,0 +1 @@
+../.clang-format-4
\ No newline at end of file
diff --git a/logd/LogAudit.cpp b/logd/LogAudit.cpp
index 18d5287..470ffed 100644
--- a/logd/LogAudit.cpp
+++ b/logd/LogAudit.cpp
@@ -300,7 +300,7 @@
return 0;
}
- log_time now;
+ log_time now(log_time::EPOCH);
static const char audit_str[] = " audit(";
char* timeptr = strstr(str, audit_str);
diff --git a/logd/LogBuffer.cpp b/logd/LogBuffer.cpp
index fbdbf79..9cbc7c4 100644
--- a/logd/LogBuffer.cpp
+++ b/logd/LogBuffer.cpp
@@ -399,7 +399,7 @@
((*it)->getLogId() != LOG_ID_KERNEL))) {
mLogElements.push_back(elem);
} else {
- log_time end = log_time::EPOCH;
+ log_time end(log_time::EPOCH);
bool end_set = false;
bool end_always = false;
diff --git a/logd/LogKlog.cpp b/logd/LogKlog.cpp
index 513c0c3..edd326a 100644
--- a/logd/LogKlog.cpp
+++ b/logd/LogKlog.cpp
@@ -197,10 +197,9 @@
// NOTREACHED
}
-log_time LogKlog::correction =
- (log_time(CLOCK_REALTIME) < log_time(CLOCK_MONOTONIC))
- ? log_time::EPOCH
- : (log_time(CLOCK_REALTIME) - log_time(CLOCK_MONOTONIC));
+log_time LogKlog::correction = (log_time(CLOCK_REALTIME) < log_time(CLOCK_MONOTONIC))
+ ? log_time(log_time::EPOCH)
+ : (log_time(CLOCK_REALTIME) - log_time(CLOCK_MONOTONIC));
LogKlog::LogKlog(LogBuffer* buf, LogReader* reader, int fdWrite, int fdRead,
bool auditd)
@@ -268,7 +267,7 @@
static const char real_format[] = "%Y-%m-%d %H:%M:%S.%09q UTC";
if (len < (ssize_t)(strlen(real_format) + 5)) return;
- log_time real;
+ log_time real(log_time::EPOCH);
const char* ep = real.strptime(real_string, real_format);
if (!ep || (ep > &real_string[len]) || (real > log_time(CLOCK_REALTIME))) {
return;
@@ -282,20 +281,20 @@
tm.tm_isdst = -1;
localtime_r(&now, &tm);
if ((tm.tm_gmtoff < 0) && ((-tm.tm_gmtoff) > (long)real.tv_sec)) {
- real = log_time::EPOCH;
+ real = log_time(log_time::EPOCH);
} else {
real.tv_sec += tm.tm_gmtoff;
}
if (monotonic > real) {
- correction = log_time::EPOCH;
+ correction = log_time(log_time::EPOCH);
} else {
correction = real - monotonic;
}
}
-void LogKlog::sniffTime(log_time& now, const char*& buf, ssize_t len,
- bool reverse) {
- if (len <= 0) return;
+log_time LogKlog::sniffTime(const char*& buf, ssize_t len, bool reverse) {
+ log_time now(log_time::EPOCH);
+ if (len <= 0) return now;
const char* cp = nullptr;
if ((len > 10) && (*buf == '[')) {
@@ -310,7 +309,7 @@
}
buf = cp;
- if (isMonotonic()) return;
+ if (isMonotonic()) return now;
const char* b;
if (((b = android::strnstr(cp, len, suspendStr))) &&
@@ -329,11 +328,11 @@
// trigger a check for ntp-induced or hardware clock drift.
log_time real(CLOCK_REALTIME);
log_time mono(CLOCK_MONOTONIC);
- correction = (real < mono) ? log_time::EPOCH : (real - mono);
+ correction = (real < mono) ? log_time(log_time::EPOCH) : (real - mono);
} else if (((b = android::strnstr(cp, len, suspendedStr))) &&
(((b += strlen(suspendStr)) - cp) < len)) {
len -= b - cp;
- log_time real;
+ log_time real(log_time::EPOCH);
char* endp;
real.tv_sec = strtol(b, &endp, 10);
if ((*endp == '.') && ((endp - b) < len)) {
@@ -345,7 +344,7 @@
}
if (reverse) {
if (real > correction) {
- correction = log_time::EPOCH;
+ correction = log_time(log_time::EPOCH);
} else {
correction -= real;
}
@@ -363,6 +362,7 @@
now = log_time(CLOCK_REALTIME);
}
}
+ return now;
}
pid_t LogKlog::sniffPid(const char*& buf, ssize_t len) {
@@ -451,8 +451,7 @@
}
parseKernelPrio(cp, len - (cp - buf));
- log_time now;
- sniffTime(now, cp, len - (cp - buf), true);
+ log_time now = sniffTime(cp, len - (cp - buf), true);
const char* suspended = android::strnstr(buf, len, suspendedStr);
if (!suspended || (suspended > cp)) {
@@ -468,7 +467,7 @@
}
parseKernelPrio(cp, len - (cp - buf));
- sniffTime(now, cp, len - (cp - buf), true);
+ sniffTime(cp, len - (cp - buf), true);
}
// Convert kernel log priority number into an Android Logger priority number
@@ -548,8 +547,7 @@
const char* p = buf;
int pri = parseKernelPrio(p, len);
- log_time now;
- sniffTime(now, p, len - (p - buf), false);
+ log_time now = sniffTime(p, len - (p - buf), false);
// sniff for start marker
const char* start = android::strnstr(p, len - (p - buf), klogdStr);
diff --git a/logd/LogKlog.h b/logd/LogKlog.h
index bb92dd2..6bfd6a8 100644
--- a/logd/LogKlog.h
+++ b/logd/LogKlog.h
@@ -55,11 +55,10 @@
}
protected:
- void sniffTime(log_time& now, const char*& buf, ssize_t len, bool reverse);
- pid_t sniffPid(const char*& buf, ssize_t len);
- void calculateCorrection(const log_time& monotonic, const char* real_string,
- ssize_t len);
- virtual bool onDataAvailable(SocketClient* cli);
+ log_time sniffTime(const char*& buf, ssize_t len, bool reverse);
+ pid_t sniffPid(const char*& buf, ssize_t len);
+ void calculateCorrection(const log_time& monotonic, const char* real_string, ssize_t len);
+ virtual bool onDataAvailable(SocketClient* cli);
};
#endif
diff --git a/logd/LogTags.cpp b/logd/LogTags.cpp
index 1ab9dd1..f19e7b0 100644
--- a/logd/LogTags.cpp
+++ b/logd/LogTags.cpp
@@ -30,6 +30,7 @@
#include <android-base/file.h>
#include <android-base/macros.h>
+#include <android-base/scopeguard.h>
#include <android-base/stringprintf.h>
#include <log/log_event_list.h>
#include <log/log_properties.h>
@@ -38,6 +39,8 @@
#include "LogTags.h"
#include "LogUtils.h"
+using android::base::make_scope_guard;
+
static LogTags* logtags;
const char LogTags::system_event_log_tags[] = "/system/etc/event-log-tags";
@@ -316,27 +319,29 @@
std::string Format;
android_log_list_element elem;
{
- android_log_event_list ctx(log_msg);
- elem = ctx.read();
+ auto ctx = create_android_log_parser(log_msg.msg() + sizeof(uint32_t),
+ log_msg.entry.len - sizeof(uint32_t));
+ auto guard = make_scope_guard([&ctx]() { android_log_destroy(&ctx); });
+ elem = android_log_read_next(ctx);
if (elem.type != EVENT_TYPE_LIST) {
continue;
}
- elem = ctx.read();
+ elem = android_log_read_next(ctx);
if (elem.type != EVENT_TYPE_INT) {
continue;
}
Tag = elem.data.int32;
- elem = ctx.read();
+ elem = android_log_read_next(ctx);
if (elem.type != EVENT_TYPE_STRING) {
continue;
}
Name = std::string(elem.data.string, elem.len);
- elem = ctx.read();
+ elem = android_log_read_next(ctx);
if (elem.type != EVENT_TYPE_STRING) {
continue;
}
Format = std::string(elem.data.string, elem.len);
- elem = ctx.read();
+ elem = android_log_read_next(ctx);
}
if ((elem.type != EVENT_TYPE_LIST_STOP) || !elem.complete) continue;
@@ -524,10 +529,22 @@
tag2format_const_iterator iform = tag2format.find(tag);
std::string Format = (iform != tag2format.end()) ? iform->second : "";
- __android_log_event_list ctx(TAG_DEF_LOG_TAG);
- ctx << tag << Name << Format;
- std::string buffer(ctx);
- if (buffer.length() <= 0) return; // unlikely
+ auto ctx = create_android_logger(TAG_DEF_LOG_TAG);
+ auto guard = make_scope_guard([&ctx]() { android_log_destroy(&ctx); });
+ if (android_log_write_int32(ctx, static_cast<int32_t>(tag) < 0) ||
+ android_log_write_string8_len(ctx, Name.c_str(), Name.size()) < 0 ||
+ android_log_write_string8_len(ctx, Format.c_str(), Format.size()) < 0) {
+ return;
+ }
+
+ const char* cp = nullptr;
+ ssize_t len = android_log_write_list_buffer(ctx, &cp);
+
+ if (len <= 0 || cp == nullptr) {
+ return;
+ }
+
+ std::string buffer(cp, len);
/*
* struct {
diff --git a/rootdir/init.rc b/rootdir/init.rc
index 372f481..9b20964 100644
--- a/rootdir/init.rc
+++ b/rootdir/init.rc
@@ -117,8 +117,6 @@
mkdir /mnt/runtime/read/self 0755 root root
mkdir /mnt/runtime/write 0755 root root
mkdir /mnt/runtime/write/self 0755 root root
- mkdir /mnt/runtime/full 0755 root root
- mkdir /mnt/runtime/full/self 0755 root root
# Symlink to keep legacy apps working in multi-user world
symlink /storage/self/primary /sdcard
diff --git a/sdcard/sdcard.cpp b/sdcard/sdcard.cpp
index e1de130..dc36596 100644
--- a/sdcard/sdcard.cpp
+++ b/sdcard/sdcard.cpp
@@ -160,7 +160,6 @@
std::string dest_path_default = "/mnt/runtime/default/" + label;
std::string dest_path_read = "/mnt/runtime/read/" + label;
std::string dest_path_write = "/mnt/runtime/write/" + label;
- std::string dest_path_full = "/mnt/runtime/full/" + label;
umask(0);
if (multi_user) {
@@ -173,10 +172,7 @@
default_normal, use_esdfs) ||
!sdcardfs_setup_secondary(dest_path_default, source_path, dest_path_write, uid, gid,
multi_user, userid, AID_EVERYBODY, full_write ? 0007 : 0027,
- derive_gid, default_normal, use_esdfs) ||
- !sdcardfs_setup_secondary(dest_path_default, source_path, dest_path_full, uid, gid,
- multi_user, userid, AID_EVERYBODY, 0007, derive_gid,
- default_normal, use_esdfs)) {
+ derive_gid, default_normal, use_esdfs)) {
LOG(FATAL) << "failed to sdcardfs_setup";
}
} else {
@@ -190,10 +186,7 @@
derive_gid, default_normal, use_esdfs) ||
!sdcardfs_setup_secondary(dest_path_default, source_path, dest_path_write, uid, gid,
multi_user, userid, AID_EVERYBODY, full_write ? 0007 : 0022,
- derive_gid, default_normal, use_esdfs) ||
- !sdcardfs_setup_secondary(dest_path_default, source_path, dest_path_full, uid, gid,
- multi_user, userid, AID_EVERYBODY, 0007, derive_gid,
- default_normal, use_esdfs)) {
+ derive_gid, default_normal, use_esdfs)) {
LOG(FATAL) << "failed to sdcardfs_setup";
}
}
diff --git a/storaged/storaged.cpp b/storaged/storaged.cpp
index 77c6167..6897663 100644
--- a/storaged/storaged.cpp
+++ b/storaged/storaged.cpp
@@ -341,20 +341,14 @@
if (mConfig.event_time_check_usec &&
clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &start_ts) < 0) {
check_time = false;
- static time_t state_a;
- IF_ALOG_RATELIMIT_LOCAL(300, &state_a) {
- PLOG_TO(SYSTEM, ERROR) << "clock_gettime() failed";
- }
+ PLOG_TO(SYSTEM, ERROR) << "clock_gettime() failed";
}
event();
if (mConfig.event_time_check_usec && check_time) {
if (clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &end_ts) < 0) {
- static time_t state_b;
- IF_ALOG_RATELIMIT_LOCAL(300, &state_b) {
- PLOG_TO(SYSTEM, ERROR) << "clock_gettime() failed";
- }
+ PLOG_TO(SYSTEM, ERROR) << "clock_gettime() failed";
return;
}
int64_t cost = (end_ts.tv_sec - start_ts.tv_sec) * SEC_TO_USEC +
diff --git a/toolbox/getevent.c b/toolbox/getevent.c
index 39033ad..e2c77c3 100644
--- a/toolbox/getevent.c
+++ b/toolbox/getevent.c
@@ -530,6 +530,9 @@
const char *device = NULL;
const char *device_path = "/dev/input";
+ /* disable buffering on stdout */
+ setbuf(stdout, NULL);
+
opterr = 0;
do {
c = getopt(argc, argv, "tns:Sv::dpilqc:rh");