Opened 5 weeks ago

Last modified 8 days ago

#32036 new enhancement

output debug logs to logcat as early as possible on Android

Reported by: eighthave Owned by:
Priority: Medium Milestone: Tor: 0.4.3.x-final
Component: Core Tor/Tor Version:
Severity: Normal Keywords: tbb-mobile, Android, 043-should, BugSmashFund
Cc: Actual Points:
Parent ID: Points: 1
Reviewer: Sponsor:

Description

Now that I have a native TorService working on Android, I'm working on creating an Android-native test suite for it. For some reason, it fails to start there, but it fails quite early, so there is no way to get logs out. --Log debug android is enabled after this issue.

I've gotten earlier log output to logcat by executing add_android_log() at the beginning of options_act_reversible(). Ideally, there would be a way to have this built in. On Android, there is no way to see stderr or stdout from C code executed via JNI. Only from Java code. Yes, this is terrible design, but that's how it seems to be.

Here's one potential solution for redirecting stdout/stderr:
https://codelab.wordpress.com/2014/11/03/how-to-use-standard-output-streams-for-logging-in-android-apps/ Just ignore the part about Android being "basically a UNIX system" because Android is really not UNIX, its a lot more different from UNIX than Windows. Like Windows, it has some familiar UNIXish things.

Child Tickets

Attachments (1)

0001-Override-log_err-log_warn-in-connection-since-stdout.patch (1.2 KB) - added by eighthave 2 weeks ago.

Download all attachments as: .zip

Change History (10)

comment:1 Changed 5 weeks ago by eighthave

For a concrete example, my specific case was failing on "Could not bind to 127.0.0.1:9050: Address already in use. Is Tor already running?". Tor was outputting no messages because add_android_log() is executed after Tor binds to the ports. So even moving it a little earlier would be helpful.

comment:2 Changed 5 weeks ago by eighthave

Here's another example, if the app that includes TorService forgets to set the INTERNET permission, tor will silently fail to start. Here's the error:

              Tor-EARLY  I  Opening Socks listener on 127.0.0.1:0
                         W  Socket creation failed: Permission denied
                         I  Opening HTTP tunnel listener on 127.0.0.1:0
                         W  Socket creation failed: Permission denied
                         I  Opening Control listener on 127.0.0.1:0
                         W  Socket creation failed: Permission denied

comment:3 Changed 3 weeks ago by eighthave

I dug into syslog on Android. Though syslog works well as a logging mechanism for Android, it suffers from the same issue here, where output to syslog starts after some critical error points.

comment:4 Changed 2 weeks ago by eighthave

Here's a nice diagram and description of the Android logging system which could be helpful:
https://elinux.org/Android_Logging_System

comment:5 Changed 2 weeks ago by eighthave

The attached patch is the workaround we're using to provide error messages to logcat for this early startup stuff.

comment:6 Changed 2 weeks ago by nickm

Milestone: Tor: 0.4.3.x-final

comment:7 Changed 8 days ago by teor

Keywords: 043-should added

I wonder if we should have a separate layer for control logs (which require the network) and other function-based logs, like syslog, which do not.

But that's a big refactor, so maybe we should provide a way to change the default err log. At the moment, the default err log is a write() to stderr. When the err module is initialised, it can be replaced with stdout. When the log module is initialised, it can be replaced with a file or function.

Is syslog() interrupt-safe on Android?

comment:8 Changed 8 days ago by eighthave

The workings of both logcat and syslog are not really officially documented anywhere, or at least I've never found it. So it seems source code is the way. Android's libc is called Bionic, so that's where the syslog calls come from: https://android.googlesource.com/platform/bionic

And typical Android, liblog and lgocat source code is somewhere else entirely:
https://android.googlesource.com/platform/system/core

As far as I know, there is never a syslogd running on Android, so I don't understand out the strings get from syslog() to logcat. I imagine it is via /dev/log/* device or something similar.

comment:9 Changed 8 days ago by teor

Keywords: BugSmashFund added
Points: 1
Note: See TracTickets for help on using tickets.