[Libreoffice-commits] .: 3 commits - android/Bootstrap android/experimental sal/android
Tor Lillqvist
tml at kemper.freedesktop.org
Wed May 16 00:18:42 PDT 2012
android/Bootstrap/src/org/libreoffice/android/Bootstrap.java | 6
android/experimental/DocumentLoader/Makefile | 7
sal/android/lo-bootstrap.c | 208 +++++++++++
3 files changed, 216 insertions(+), 5 deletions(-)
New commits:
commit d31e409ec1eb3e5ea81ec2a2288a046cf1e395a1
Author: Tor Lillqvist <tlillqvist at suse.com>
Date: Wed May 16 09:56:29 2012 +0300
Update library list
Change-Id: I9c652fc6940bd856aa8ba5f7e2daaae6a5502b3d
diff --git a/android/experimental/DocumentLoader/Makefile b/android/experimental/DocumentLoader/Makefile
index b81c0b5..3c513ec 100644
--- a/android/experimental/DocumentLoader/Makefile
+++ b/android/experimental/DocumentLoader/Makefile
@@ -48,7 +48,6 @@ copy-stuff:
basebmplo \
basegfxlo \
bootstrap.uno \
- cdrimportlo \
comphelpgcc3 \
datelo \
dbaxmllo \
@@ -84,7 +83,6 @@ copy-stuff:
mergedlo \
msfilterlo \
mswordlo \
- msworkslo \
ooxlo \
reflection.uno \
reg \
@@ -116,10 +114,9 @@ copy-stuff:
utllo \
vbahelperlo \
vbaswobj.uno \
+ wpftdrawlo \
+ wpftwriterlo \
vcllo \
- visioimportlo \
- wpftlo \
- wpgimportlo \
xml2 \
xmlfdlo \
xmlreader \
commit 182c1e4f99d7d3ae73cafdae02573ca29b6639cc
Author: Tor Lillqvist <tlillqvist at suse.com>
Date: Wed May 16 09:55:48 2012 +0300
Call lo-bootstrap's redirect_stdio
Change-Id: I45732ac81d00837ce517ed5c527c8c767e690abf
diff --git a/android/Bootstrap/src/org/libreoffice/android/Bootstrap.java b/android/Bootstrap/src/org/libreoffice/android/Bootstrap.java
index b562da8..82a40b7 100644
--- a/android/Bootstrap/src/org/libreoffice/android/Bootstrap.java
+++ b/android/Bootstrap/src/org/libreoffice/android/Bootstrap.java
@@ -101,6 +101,10 @@ public class Bootstrap extends NativeActivity
// (contentbroker.cxx), also this called indirectly through the lo-bootstrap library
public static native void initUCBHelper();
+ // A method that starts a thread to redirect stdout and stderr writes to
+ // the Android logging mechanism, or stops the redirection.
+ public static native boolean redirect_stdio(boolean state);
+
// This setup() method is called 1) in apps that use *this* class as their activity from onCreate(),
// and 2) should be called from other kinds of LO code using apps.
public static void setup(Activity activity)
@@ -111,6 +115,8 @@ public class Bootstrap extends NativeActivity
dataDir = ai.dataDir;
Log.i(TAG, String.format("dataDir=%s\n", dataDir));
+ redirect_stdio(true);
+
String llp = System.getenv("LD_LIBRARY_PATH");
if (llp == null)
llp = "/vendor/lib:/system/lib";
commit c53c665de33d931e5d3a6ad767240fc83ac8bd69
Author: Tor Lillqvist <tlillqvist at suse.com>
Date: Wed May 16 09:50:52 2012 +0300
Add stdout and stderr redirection to the Android log
On a (non-rooted) device it is not possible to set the
log.redirect-stdio property so that it would be effective (i.e. read
by the Zygote process when it starts). Such redirection has to be done
in-process.
Add a (JNI-callable) method to set it up: Point file descriptors 1 and
2 at pipes that are read by a thread that logs each line through the
Android logging API. Code based on Android's own logwrapper.c.
Change-Id: Id5308293595096a44a2ffed2dbc0c252be109de7
diff --git a/sal/android/lo-bootstrap.c b/sal/android/lo-bootstrap.c
index 75a3898..f3ba3bb 100644
--- a/sal/android/lo-bootstrap.c
+++ b/sal/android/lo-bootstrap.c
@@ -67,6 +67,8 @@
#define ROUND_DOWN(ptr,multiple) (void *)(((unsigned) (ptr)) & ~((multiple)-1))
+#define MAX(a,b) ((a) > (b) ? (a) : (b))
+
struct engine {
int dummy;
};
@@ -1631,6 +1633,212 @@ Java_org_libreoffice_android_Bootstrap_initUCBHelper(JNIEnv* env,
(*InitUCBHelper)();
}
+/* Code for reading lines from the pipe based on the (Apache-licensed) Android
+ * logwrapper.c
+ */
+
+static int
+read_from(int fd, const char *tag, char *buffer, int *sz, int *a, int *b, size_t sizeof_buffer)
+{
+ int nread;
+
+ nread = read(fd, buffer+*b, sizeof_buffer - 1 - *b);
+ *sz = nread;
+
+ if (nread == -1) {
+ LOGE("redirect_thread: Reading from %d failed: %s", fd, strerror(errno));
+ close(fd);
+ return -1;
+ }
+
+ if (nread == 0) {
+ LOGI("redirect_thread: EOF from fd %d", fd);
+ close(fd);
+ return 0;
+ }
+
+ *sz += *b;
+
+ for (*b = 0; *b < *sz; (*b)++) {
+ if (buffer[*b] == '\n') {
+ buffer[*b] = '\0';
+ __android_log_print(ANDROID_LOG_INFO, tag, "%s", &buffer[*a]);
+ *a = *b + 1;
+ }
+ }
+
+ if (*a == 0 && *b == (int) sizeof_buffer - 1) {
+ // buffer is full, flush
+ buffer[*b] = '\0';
+ __android_log_print(ANDROID_LOG_INFO, tag, "%s", &buffer[*a]);
+ *b = 0;
+ } else if (*a != *b) {
+ // Keep left-overs
+ *b -= *a;
+ memmove(buffer, &buffer[*a], *b);
+ *a = 0;
+ } else {
+ *a = 0;
+ *b = 0;
+ }
+
+ return nread;
+}
+
+static int stdout_pipe[2], stderr_pipe[2];
+
+static void *
+redirect_thread(void *arg)
+{
+ char buffer[2][4096];
+ int a[2] = { 0, 0 };
+ int b[2] = { 0, 0 };
+ int sz[2];
+
+ (void) arg;
+
+ while (1) {
+ fd_set readfds;
+ int nfds = 0;
+
+ FD_ZERO(&readfds);
+ if (stdout_pipe[0] != -1) {
+ FD_SET(stdout_pipe[0], &readfds);
+ nfds = MAX(nfds, stdout_pipe[0] + 1);
+ }
+ if (stderr_pipe[0] != -1) {
+ FD_SET(stderr_pipe[0], &readfds);
+ nfds = MAX(nfds, stderr_pipe[0] + 1);
+ }
+ if (nfds == 0) {
+ LOGI("redirect_thread: Nothing to read any more, thread exiting");
+ return NULL;
+ }
+
+ if (select(nfds, &readfds, NULL, NULL, NULL) == -1) {
+ LOGE("redirect_thread: select failed: %s, thread exiting", strerror(errno));
+ close(stdout_pipe[0]);
+ stdout_pipe[0] = -1;
+ close(stderr_pipe[0]);
+ stderr_pipe[0] = -1;
+ return NULL;
+ }
+
+ if (stdout_pipe[0] != -1 &&
+ FD_ISSET(stdout_pipe[0], &readfds)) {
+ if (read_from(stdout_pipe[0], "stdout", buffer[0], &sz[0], &a[0], &b[0], sizeof(buffer[0])) <= 0) {
+ stdout_pipe[0] = -1;
+ }
+ }
+
+ if (stderr_pipe[0] != -1 &&
+ FD_ISSET(stderr_pipe[0], &readfds)) {
+ if (read_from(stderr_pipe[0], "stderr", buffer[1], &sz[1], &a[1], &b[1], sizeof(buffer[1])) <= 0) {
+ stderr_pipe[0] = -1;
+ }
+ }
+ }
+}
+
+static int
+redirect_to_null(void)
+{
+ int null = open("/dev/null", O_WRONLY);
+ if (null == -1) {
+ LOGE("redirect_stdio: Could not open /dev/null: %s", strerror(errno));
+ /* If we can't redirect stdout or stderr to /dev/null, just close them
+ * then instead. Huh?
+ */
+ close(1);
+ close(2);
+ return 0;
+ }
+ if (dup2(null, 1) == -1) {
+ LOGE("redirect_stdio: Could not dup2 %d to 1: %s", null, strerror(errno));
+ close(null);
+ close(1);
+ close(2);
+ return 0;
+ }
+ if (dup2(null, 2) == -1) {
+ LOGE("redirect_stdio: Could not dup2 %d to 2: %s", null, strerror(errno));
+ close(null);
+ close(1);
+ close(2);
+ return 0;
+ }
+ close(null);
+ return 1;
+}
+
+__attribute__ ((visibility("default")))
+jboolean
+Java_org_libreoffice_android_Bootstrap_redirect_1stdio(JNIEnv* env,
+ jobject clazz,
+ jboolean state)
+{
+ static jboolean current = JNI_FALSE;
+ pthread_t thread;
+
+ (void) env;
+ (void) clazz;
+
+ if (state == current)
+ return current;
+
+ if (state == JNI_FALSE) {
+ if (!redirect_to_null())
+ return current;
+ } else {
+ if (pipe(stdout_pipe) == -1) {
+ LOGE("redirect_stdio: Could not create pipes: %s", strerror(errno));
+ return current;
+ }
+ if (pipe(stderr_pipe) == -1) {
+ LOGE("redirect_stdio: Could not create pipes: %s", strerror(errno));
+ close(stdout_pipe[0]);
+ close(stdout_pipe[1]);
+ return current;
+ }
+ LOGI("redirect_stdio: stdout pipe: [%d,%d], stderr pipe: [%d,%d]",
+ stdout_pipe[0], stdout_pipe[1], stderr_pipe[0], stderr_pipe[1]);
+
+ if (dup2(stdout_pipe[1], 1) == -1) {
+ LOGE("redirect_stdio: Could not dup2 %d to 1: %s", stdout_pipe[1], strerror(errno));
+ close(stdout_pipe[0]);
+ close(stdout_pipe[1]);
+ close(stderr_pipe[0]);
+ close(stderr_pipe[1]);
+ return current;
+ }
+
+ if (dup2(stderr_pipe[1], 2) == -1) {
+ LOGE("redirect_stdio: Could not dup2 %d to 2: %s", stdout_pipe[1], strerror(errno));
+ /* stdout has already been redirected to its pipe, so redirect
+ * it back to /dev/null
+ */
+ redirect_to_null();
+ close(stdout_pipe[0]);
+ close(stdout_pipe[1]);
+ close(stderr_pipe[0]);
+ close(stderr_pipe[1]);
+ return current;
+ }
+ close(stdout_pipe[1]);
+ close(stderr_pipe[1]);
+
+ if (pthread_create(&thread, NULL, redirect_thread, NULL) != 0) {
+ LOGE("redirect_stdio: Could not create thread: %s", strerror(errno));
+ redirect_to_null();
+ close(stdout_pipe[0]);
+ close(stderr_pipe[0]);
+ return current;
+ }
+ }
+ current = state;
+ return current;
+}
+
__attribute__ ((visibility("default")))
JavaVM *
lo_get_javavm(void)
More information about the Libreoffice-commits
mailing list