KEYCODE_VOLUME_MUTE should be forwarded to Emacs. */
public static native boolean shouldForwardMultimediaButtons ();
+ /* Initialize the current thread, by blocking signals that do not
+ interest it. */
+ public static native void setupSystemThread ();
+
\f
/* Input connection functions. These mostly correspond to their
import java.util.List;
+import java.util.concurrent.Semaphore;
import java.util.concurrent.atomic.AtomicInteger;
import android.graphics.Matrix;
final String filesDir, libDir, cacheDir, classPath;
final double pixelDensityX;
final double pixelDensityY;
+ final Semaphore signalSemaphore;
SERVICE = this;
handler = new Handler (Looper.getMainLooper ());
pixelDensityX = metrics.xdpi;
pixelDensityY = metrics.ydpi;
resolver = getContentResolver ();
+ signalSemaphore = new Semaphore (0);
try
{
cacheDir, (float) pixelDensityX,
(float) pixelDensityY,
classPath, EmacsService.this);
+
+ /* Wait for the signal mask to be set up in the UI
+ thread. */
+
+ while (true)
+ {
+ try
+ {
+ signalSemaphore.acquire ();
+ break;
+ }
+ catch (InterruptedException e)
+ {
+ ;;
+ }
+ }
}
}, extraStartupArgument,
/* If any file needs to be opened, open it now. */
EmacsOpenActivity.fileToOpen);
thread.start ();
+
+ /* Now that the thread has been started, block signals which
+ don't interest the current thread. */
+
+ EmacsNative.setupSystemThread ();
+ signalSemaphore.release ();
}
catch (IOException exception)
{
android_answer_query_spin ();
}
+\f
+
+/* System thread setup. Android doesn't always block signals Emacs is
+ interested in from being received by the UI or render threads,
+ which can lead to problems when those signals then interrupt one of
+ those threads. */
+
+JNIEXPORT void JNICALL
+NATIVE_NAME (setupSystemThread) (void)
+{
+ sigset_t sigset;
+
+ /* Block everything except for SIGSEGV and SIGBUS; those two are
+ used by the runtime. */
+
+ sigfillset (&sigset);
+ sigaddset (&sigset, SIGSEGV);
+ sigaddset (&sigset, SIGBUS);
+
+ if (pthread_sigmask (SIG_BLOCK, &sigset, NULL))
+ __android_log_print (ANDROID_LOG_WARN, __func__,
+ "pthread_sigmask: %s", strerror (errno));
+}
+
#ifdef __clang__
#pragma clang diagnostic pop
#else