summaryrefslogtreecommitdiffstats
path: root/logcat
diff options
context:
space:
mode:
authorbohu <bohu@google.com>2017-02-21 14:31:19 -0800
committerMark Salyzyn <salyzyn@google.com>2017-03-17 16:19:05 +0000
commit94aab86d57ebd8ff6d9b542080538252e9581cf1 (patch)
tree99d9ff37adc8f5d1f18b491652d7be97e5d8fee7 /logcat
parent4278f7111894c0f80193aa4b4b7b88879071fade (diff)
downloadsystem_core-94aab86d57ebd8ff6d9b542080538252e9581cf1.tar.gz
system_core-94aab86d57ebd8ff6d9b542080538252e9581cf1.tar.bz2
system_core-94aab86d57ebd8ff6d9b542080538252e9581cf1.zip
Emulator: enhance logcat -Q to handle qemu pipe device
Upon opening, qemu pipe (a.k.a. goldfish pipe) requires a purpose string so that emulator can route the content to the right channel on the host. This CL will ask emulator to send the content to pipe based 'logcat' service on the host. Change-Id: Icc71f81d5b95b64ea315fe10da82ff704416e449
Diffstat (limited to 'logcat')
-rw-r--r--logcat/logcat.cpp65
1 files changed, 54 insertions, 11 deletions
diff --git a/logcat/logcat.cpp b/logcat/logcat.cpp
index 4da503038..813493699 100644
--- a/logcat/logcat.cpp
+++ b/logcat/logcat.cpp
@@ -41,6 +41,7 @@
#include <vector>
#include <android-base/file.h>
+#include <android-base/properties.h>
#include <android-base/stringprintf.h>
#include <android-base/strings.h>
#include <cutils/sched_policy.h>
@@ -1195,39 +1196,71 @@ static int __logcat(android_logcat_context_internal* context) {
} break;
case 'Q':
-#define KERNEL_OPTION "androidboot.logcat="
+#define LOGCAT_FILTER "androidboot.logcat="
+#define CONSOLE_PIPE_OPTION "androidboot.consolepipe="
#define CONSOLE_OPTION "androidboot.console="
+#define QEMU_PROPERTY "ro.kernel.qemu"
+#define QEMU_CMDLINE "qemu.cmdline"
// This is a *hidden* option used to start a version of logcat
// in an emulated device only. It basically looks for
// androidboot.logcat= on the kernel command line. If
// something is found, it extracts a log filter and uses it to
- // run the program. If nothing is found, the program should
- // quit immediately.
+ // run the program. The logcat output will go to consolepipe if
+ // androiboot.consolepipe (e.g. qemu_pipe) is given, otherwise,
+ // it goes to androidboot.console (e.g. tty)
{
- std::string cmdline;
- android::base::ReadFileToString("/proc/cmdline", &cmdline);
+ // if not in emulator, exit quietly
+ if (false == android::base::GetBoolProperty(QEMU_PROPERTY, false)) {
+ context->retval = EXIT_SUCCESS;
+ goto exit;
+ }
+
+ std::string cmdline = android::base::GetProperty(QEMU_CMDLINE, "");
+ if (cmdline.empty()) {
+ android::base::ReadFileToString("/proc/cmdline", &cmdline);
+ }
- const char* logcat = strstr(cmdline.c_str(), KERNEL_OPTION);
+ const char* logcatFilter = strstr(cmdline.c_str(), LOGCAT_FILTER);
// if nothing found or invalid filters, exit quietly
- if (!logcat) {
+ if (!logcatFilter) {
context->retval = EXIT_SUCCESS;
goto exit;
}
- const char* p = logcat + strlen(KERNEL_OPTION);
+ const char* p = logcatFilter + strlen(LOGCAT_FILTER);
const char* q = strpbrk(p, " \t\n\r");
if (!q) q = p + strlen(p);
forceFilters = std::string(p, q);
- // redirect our output to the emulator console
+ // redirect our output to the emulator console pipe or console
+ const char* consolePipe =
+ strstr(cmdline.c_str(), CONSOLE_PIPE_OPTION);
const char* console =
strstr(cmdline.c_str(), CONSOLE_OPTION);
- if (!console) break;
- p = console + strlen(CONSOLE_OPTION);
+ if (consolePipe) {
+ p = consolePipe + strlen(CONSOLE_PIPE_OPTION);
+ } else if (console) {
+ p = console + strlen(CONSOLE_OPTION);
+ } else {
+ context->retval = EXIT_FAILURE;
+ goto exit;
+ }
+
q = strpbrk(p, " \t\n\r");
int len = q ? q - p : strlen(p);
std::string devname = "/dev/" + std::string(p, len);
+ std::string pipePurpose("pipe:logcat");
+ if (consolePipe) {
+ // example: "qemu_pipe,pipe:logcat"
+ // upon opening of /dev/qemu_pipe, the "pipe:logcat"
+ // string with trailing '\0' should be written to the fd
+ size_t pos = devname.find(",");
+ if (pos != std::string::npos) {
+ pipePurpose = devname.substr(pos + 1);
+ devname = devname.substr(0, pos);
+ }
+ }
cmdline.erase();
if (context->error) {
@@ -1239,6 +1272,16 @@ static int __logcat(android_logcat_context_internal* context) {
devname.erase();
if (!fp) break;
+ if (consolePipe) {
+ // need the trailing '\0'
+ if(!android::base::WriteFully(fileno(fp), pipePurpose.c_str(),
+ pipePurpose.size() + 1)) {
+ fclose(fp);
+ context->retval = EXIT_FAILURE;
+ goto exit;
+ }
+ }
+
// close output and error channels, replace with console
android::close_output(context);
android::close_error(context);