From 984073016903c7b8c84528579a89aeed4ecd084f Mon Sep 17 00:00:00 2001 From: Ryan Pavlik Date: Mon, 17 Apr 2023 10:56:16 -0500 Subject: [PATCH] ipc/android: Run spotlessApply to format Java and Kotlin code --- .../org/freedesktop/monado/ipc/Client.java | 194 +++++++++--------- .../freedesktop/monado/ipc/MonadoImpl.java | 59 +++--- .../freedesktop/monado/ipc/MonadoService.kt | 47 +++-- .../freedesktop/monado/ipc/SurfaceManager.kt | 25 +-- .../org/freedesktop/monado/ipc/Watchdog.kt | 26 +-- 5 files changed, 163 insertions(+), 188 deletions(-) diff --git a/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/Client.java b/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/Client.java index d604e16a8..aee97dcb3 100644 --- a/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/Client.java +++ b/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/Client.java @@ -7,7 +7,6 @@ * @ingroup ipc_android */ - package org.freedesktop.monado.ipc; import android.app.Activity; @@ -37,50 +36,40 @@ import java.util.concurrent.Executors; /** * Provides the client-side code to initiate connection to Monado IPC service. - *

- * This class will get loaded into the OpenXR client application by our native code. + * + *

This class will get loaded into the OpenXR client application by our native code. */ @Keep public class Client implements ServiceConnection { private static final String TAG = "monado-ipc-client"; - /** - * Used to block until binder is ready. - */ + /** Used to block until binder is ready. */ private final Object binderSync = new Object(); - /** - * Keep track of the ipc_client_android instance over on the native side. - */ + /** Keep track of the ipc_client_android instance over on the native side. */ private final NativeCounterpart nativeCounterpart; /** - * Pointer to local IPC proxy: calling methods on it automatically transports arguments across binder IPC. - *

- * May be null! + * Pointer to local IPC proxy: calling methods on it automatically transports arguments across + * binder IPC. + * + *

May be null! */ - @Keep - public IMonado monado = null; + @Keep public IMonado monado = null; /** * Indicates that we tried to connect but failed. - *

- * Used to distinguish a "not yet fully connected" null monado member from a "tried and failed" - * null monado member. + * + *

Used to distinguish a "not yet fully connected" null monado member from a "tried and + * failed" null monado member. */ - @Keep - public boolean failed = false; + @Keep public boolean failed = false; /** - * "Our" side of the socket pair - the other side is sent to the server automatically on connection. + * "Our" side of the socket pair - the other side is sent to the server automatically on + * connection. */ private ParcelFileDescriptor fd = null; - /** - * Context provided by app. - */ + /** Context provided by app. */ private Context context = null; - /** - * Context of the runtime package - */ + /** Context of the runtime package */ private Context runtimePackageContext = null; - /** - * Control system ui visibility - */ + /** Control system ui visibility */ private SystemUiController systemUiController = null; /** @@ -110,9 +99,7 @@ public class Client implements ServiceConnection { } } - /** - * Let the native code notify us that it is no longer using this class. - */ + /** Let the native code notify us that it is no longer using this class. */ @Keep public void markAsDiscardedByNative() { nativeCounterpart.markAsDiscardedByNative(TAG); @@ -121,22 +108,21 @@ public class Client implements ServiceConnection { /** * Bind to the Monado IPC service, and block until it is fully connected. - *

- * The IPC client code on Android should load this class (from the right package), instantiate - * this class (retaining a reference to it!), and call this method. - *

- * This method must not be called from the main (UI) thread. * - * @param context_ Context to use to make the connection. (We get the application context - * from it.) + *

The IPC client code on Android should load this class (from the right package), + * instantiate this class (retaining a reference to it!), and call this method. + * + *

This method must not be called from the main (UI) thread. + * + * @param context_ Context to use to make the connection. (We get the application context from + * it.) * @param packageName The package name containing the Monado runtime. The caller is guaranteed - * to know this because it had to load this class from that package. - * There's a define in xrt_config_android.h to use for this. + * to know this because it had to load this class from that package. There's a define in + * xrt_config_android.h to use for this. * @return the fd number - do not close! (dup if you want to be able to close it) Returns -1 if - * something went wrong. - *

- * Various builds, variants, etc. will have different package names, but we must specify the - * package name explicitly to avoid violating security restrictions. + * something went wrong. + *

Various builds, variants, etc. will have different package names, but we must specify + * the package name explicitly to avoid violating security restrictions. */ @Keep public int blockingConnect(Context context_, String packageName) { @@ -167,42 +153,49 @@ public class Client implements ServiceConnection { // TODO: just initiate MonadoView attachment and add callback to native code to // notify about Surface status and pass it to OpenXR application as a Session lifecycle // (ready ... synchronized ... visible ... focused) - new Thread(()-> { - boolean surfaceCreated = false; - Activity activity = null; - if (context_ instanceof Activity) { - activity = (Activity) context_; - } + new Thread( + () -> { + boolean surfaceCreated = false; + Activity activity = null; + if (context_ instanceof Activity) { + activity = (Activity) context_; + } - try { - // Determine whether runtime or client should create surface - if (monado.canDrawOverOtherApps()) { - WindowManager wm = (WindowManager) context_.getSystemService(Context.WINDOW_SERVICE); - surfaceCreated = monado.createSurface(wm.getDefaultDisplay().getDisplayId(), false); - } else { - if (activity != null) { - Surface surface = attachViewAndGetSurface(activity); - surfaceCreated = (surface != null); - if (surfaceCreated) { - monado.passAppSurface(surface); - } - } - } - } catch (RemoteException e) { - e.printStackTrace(); - } + try { + // Determine whether runtime or client should create surface + if (monado.canDrawOverOtherApps()) { + WindowManager wm = + (WindowManager) + context_.getSystemService( + Context.WINDOW_SERVICE); + surfaceCreated = + monado.createSurface( + wm.getDefaultDisplay().getDisplayId(), false); + } else { + if (activity != null) { + Surface surface = attachViewAndGetSurface(activity); + surfaceCreated = (surface != null); + if (surfaceCreated) { + monado.passAppSurface(surface); + } + } + } + } catch (RemoteException e) { + e.printStackTrace(); + } - if (!surfaceCreated) { - Log.e(TAG, "Failed to create surface"); - handleFailure(); - return; - } + if (!surfaceCreated) { + Log.e(TAG, "Failed to create surface"); + handleFailure(); + return; + } - if (activity != null) { - systemUiController = new SystemUiController(activity); - systemUiController.hide(); - } - }).start(); + if (activity != null) { + systemUiController = new SystemUiController(activity); + systemUiController.hide(); + } + }) + .start(); // Create socket pair ParcelFileDescriptor theirs; @@ -233,15 +226,13 @@ public class Client implements ServiceConnection { * Bind to the Monado IPC service - this asynchronously starts connecting (and launching the * service if it's not already running) * - * @param context_ Context to use to make the connection. (We get the application context - * from it.) + * @param context_ Context to use to make the connection. (We get the application context from + * it.) * @param packageName The package name containing the Monado runtime. The caller is guaranteed - * to know this because it had to load this class from that package. - * There's a define in xrt_config_android.h to use for this. - *

- * Various builds, variants, etc. will have different package names, but we - * must specify the package name explicitly to avoid violating security - * restrictions. + * to know this because it had to load this class from that package. There's a define in + * xrt_config_android.h to use for this. + *

Various builds, variants, etc. will have different package names, but we must specify + * the package name explicitly to avoid violating security restrictions. */ public boolean bind(Context context_, String packageName) { Log.i(TAG, "bind"); @@ -251,20 +242,20 @@ public class Client implements ServiceConnection { context = context_; } try { - runtimePackageContext = context.createPackageContext(packageName, - Context.CONTEXT_IGNORE_SECURITY | Context.CONTEXT_INCLUDE_CODE); + runtimePackageContext = + context.createPackageContext( + packageName, + Context.CONTEXT_IGNORE_SECURITY | Context.CONTEXT_INCLUDE_CODE); } catch (PackageManager.NameNotFoundException e) { e.printStackTrace(); Log.e(TAG, "bind: Could not find package " + packageName); return false; } - Intent intent = new Intent(BuildConfig.SERVICE_ACTION) - .setPackage(packageName); + Intent intent = new Intent(BuildConfig.SERVICE_ACTION).setPackage(packageName); if (!bindService(context, intent)) { - Log.e(TAG, - "bindService: Service " + intent + " could not be found to bind!"); + Log.e(TAG, "bindService: Service " + intent + " could not be found to bind!"); return false; } @@ -276,8 +267,12 @@ public class Client implements ServiceConnection { boolean result; int flags = Context.BIND_AUTO_CREATE | Context.BIND_IMPORTANT | Context.BIND_ABOVE_CLIENT; if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) { - result = context.bindService(intent, flags | Context.BIND_INCLUDE_CAPABILITIES, - Executors.newSingleThreadExecutor(), this); + result = + context.bindService( + intent, + flags | Context.BIND_INCLUDE_CAPABILITIES, + Executors.newSingleThreadExecutor(), + this); } else { result = context.bindService(intent, this, flags); } @@ -285,16 +280,13 @@ public class Client implements ServiceConnection { return result; } - /** - * Some on-failure cleanup. - */ + /** Some on-failure cleanup. */ private void handleFailure() { failed = true; shutdown(); } - @Nullable - private Surface attachViewAndGetSurface(Activity activity) { + @Nullable private Surface attachViewAndGetSurface(Activity activity) { MonadoView monadoView = MonadoView.attachToActivity(activity); SurfaceHolder holder = monadoView.waitGetSurfaceHolder(2000); Surface surface = null; @@ -308,7 +300,7 @@ public class Client implements ServiceConnection { /** * Handle the asynchronous connection of the binder IPC. * - * @param name should match the preceding intent, but not used. + * @param name should match the preceding intent, but not used. * @param service the associated service, which we cast in this function. */ @Override @@ -330,7 +322,7 @@ public class Client implements ServiceConnection { public void onServiceDisconnected(ComponentName name) { Log.i(TAG, "onServiceDisconnected"); shutdown(); - //! @todo tell C/C++ that the world is crumbling, then close the fd here. + // ! @todo tell C/C++ that the world is crumbling, then close the fd here. } /* diff --git a/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/MonadoImpl.java b/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/MonadoImpl.java index cbb855ec9..1803f0c80 100644 --- a/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/MonadoImpl.java +++ b/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/MonadoImpl.java @@ -7,7 +7,6 @@ * @ingroup ipc_android */ - package org.freedesktop.monado.ipc; import android.os.ParcelFileDescriptor; @@ -23,12 +22,12 @@ import java.io.IOException; /** * Java implementation of the IMonado IPC interface. - *

- * (This is the server-side code.) - *

- * All this does is delegate calls to native JNI implementations. - * The warning suppression is because Android Studio tends to have a hard time finding - * the (very real) implementations of these in service-lib. + * + *

(This is the server-side code.) + * + *

All this does is delegate calls to native JNI implementations. The warning suppression is + * because Android Studio tends to have a hard time finding the (very real) implementations of these + * in service-lib. */ @Keep public class MonadoImpl extends IMonado.Stub { @@ -45,21 +44,21 @@ public class MonadoImpl extends IMonado.Stub { public MonadoImpl(@NonNull SurfaceManager surfaceManager) { this.surfaceManager = surfaceManager; - this.surfaceManager.setCallback(new SurfaceHolder.Callback() { - @Override - public void surfaceCreated(@NonNull SurfaceHolder holder) { - Log.i(TAG, "surfaceCreated"); - passAppSurface(holder.getSurface()); - } + this.surfaceManager.setCallback( + new SurfaceHolder.Callback() { + @Override + public void surfaceCreated(@NonNull SurfaceHolder holder) { + Log.i(TAG, "surfaceCreated"); + passAppSurface(holder.getSurface()); + } - @Override - public void surfaceChanged(@NonNull SurfaceHolder holder, int format, int width, int height) { - } + @Override + public void surfaceChanged( + @NonNull SurfaceHolder holder, int format, int width, int height) {} - @Override - public void surfaceDestroyed(@NonNull SurfaceHolder holder) { - } - }); + @Override + public void surfaceDestroyed(@NonNull SurfaceHolder holder) {} + }); } @Override @@ -111,18 +110,16 @@ public class MonadoImpl extends IMonado.Stub { nativeShutdownServer(); } - /** - * Native method that starts server. - */ + /** Native method that starts server. */ @SuppressWarnings("JavaJniMissingFunction") private native void nativeStartServer(); /** * Native handling of receiving a surface: should convert it to an ANativeWindow then do stuff * with it. - *

- * Ignore warnings that this function is missing: it is not, it is just in a different module. - * See `src/xrt/targets/service-lib/service_target.cpp` for the implementation. + * + *

Ignore warnings that this function is missing: it is not, it is just in a different + * module. See `src/xrt/targets/service-lib/service_target.cpp` for the implementation. * * @param surface The surface to pass to native code * @todo figure out a good way to have a client ID @@ -133,13 +130,13 @@ public class MonadoImpl extends IMonado.Stub { /** * Native handling of receiving an FD for a new client: the FD should be used to start up the * rest of the native IPC code on that socket. - *

- * This is essentially the entry point for the monado service on Android: if it's already + * + *

This is essentially the entry point for the monado service on Android: if it's already * running, this will be called in it. If it's not already running, a process will be created, * and this will be the first native code executed in that process. - *

- * Ignore warnings that this function is missing: it is not, it is just in a different module. - * See `src/xrt/targets/service-lib/service_target.cpp` for the implementation. + * + *

Ignore warnings that this function is missing: it is not, it is just in a different + * module. See `src/xrt/targets/service-lib/service_target.cpp` for the implementation. * * @param fd The incoming file descriptor: ownership is transferred to native code here. * @return 0 on success, anything else means the fd wasn't sent and ownership not transferred. diff --git a/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/MonadoService.kt b/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/MonadoService.kt index 9613e3868..68e3c6a53 100644 --- a/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/MonadoService.kt +++ b/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/MonadoService.kt @@ -16,8 +16,8 @@ import android.os.Build import android.os.IBinder import android.util.Log import dagger.hilt.android.AndroidEntryPoint -import org.freedesktop.monado.auxiliary.IServiceNotification import javax.inject.Inject +import org.freedesktop.monado.auxiliary.IServiceNotification /** * Implementation of a Service that provides the Monado AIDL interface. @@ -30,8 +30,7 @@ class MonadoService : Service(), Watchdog.ShutdownListener { private lateinit var watchdog: Watchdog - @Inject - lateinit var serviceNotification: IServiceNotification + @Inject lateinit var serviceNotification: IServiceNotification private lateinit var surfaceManager: SurfaceManager @@ -40,12 +39,14 @@ class MonadoService : Service(), Watchdog.ShutdownListener { surfaceManager = SurfaceManager(this) binder = MonadoImpl(surfaceManager) - watchdog = Watchdog( - // If the surface comes from client, just stop the service when client disconnected - // because the surface belongs to the client. - if (surfaceManager.canDrawOverlays()) BuildConfig.WATCHDOG_TIMEOUT_MILLISECONDS else 0, - this - ) + watchdog = + Watchdog( + // If the surface comes from client, just stop the service when client disconnected + // because the surface belongs to the client. + if (surfaceManager.canDrawOverlays()) BuildConfig.WATCHDOG_TIMEOUT_MILLISECONDS + else 0, + this + ) watchdog.startMonitor() // start the service so it could be foregrounded @@ -58,7 +59,7 @@ class MonadoService : Service(), Watchdog.ShutdownListener { super.onDestroy() Log.d(TAG, "onDestroy") - binder.shutdown(); + binder.shutdown() watchdog.stopMonitor() surfaceManager.destroySurface() } @@ -76,7 +77,7 @@ class MonadoService : Service(), Watchdog.ShutdownListener { } override fun onBind(intent: Intent): IBinder? { - Log.d(TAG, "onBind"); + Log.d(TAG, "onBind") watchdog.onClientConnected() return binder } @@ -87,12 +88,13 @@ class MonadoService : Service(), Watchdog.ShutdownListener { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) { flags = PendingIntent.FLAG_IMMUTABLE } - val pendingShutdownIntent = PendingIntent.getForegroundService( - this, - 0, - Intent(BuildConfig.SHUTDOWN_ACTION).setPackage(packageName), - flags - ) + val pendingShutdownIntent = + PendingIntent.getForegroundService( + this, + 0, + Intent(BuildConfig.SHUTDOWN_ACTION).setPackage(packageName), + flags + ) val notification = serviceNotification.buildNotification(this, pendingShutdownIntent) @@ -103,21 +105,18 @@ class MonadoService : Service(), Watchdog.ShutdownListener { ServiceInfo.FOREGROUND_SERVICE_TYPE_MANIFEST ) } else { - startForeground( - serviceNotification.getNotificationId(), - notification - ) + startForeground(serviceNotification.getNotificationId(), notification) } } override fun onUnbind(intent: Intent?): Boolean { - Log.d(TAG, "onUnbind"); + Log.d(TAG, "onUnbind") watchdog.onClientDisconnected() - return true; + return true } override fun onRebind(intent: Intent?) { - Log.d(TAG, "onRebind"); + Log.d(TAG, "onRebind") watchdog.onClientConnected() } diff --git a/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/SurfaceManager.kt b/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/SurfaceManager.kt index dc6453d99..01fae2b31 100644 --- a/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/SurfaceManager.kt +++ b/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/SurfaceManager.kt @@ -24,9 +24,7 @@ import java.util.concurrent.TimeUnit import java.util.concurrent.locks.Condition import java.util.concurrent.locks.ReentrantLock -/** - * Class that creates/manages surface on display. - */ +/** Class that creates/manages surface on display. */ class SurfaceManager(context: Context) : SurfaceHolder.Callback { private val appContext: Context = context.applicationContext private val surfaceLock: ReentrantLock = ReentrantLock() @@ -109,8 +107,8 @@ class SurfaceManager(context: Context) : SurfaceHolder.Callback { /** * Check if current process has the capability to draw over other applications. * - * Implementation of [Settings.canDrawOverlays] checks both context and UID, - * therefore this cannot be done in client side. + * Implementation of [Settings.canDrawOverlays] checks both context and UID, therefore this + * cannot be done in client side. * * @return True if current process can draw over other applications; otherwise false. */ @@ -118,16 +116,12 @@ class SurfaceManager(context: Context) : SurfaceHolder.Callback { return Settings.canDrawOverlays(appContext) } - /** - * Destroy created surface. - */ + /** Destroy created surface. */ fun destroySurface() { viewHelper.removeView() } - /** - * Helper class that manages surface view. - */ + /** Helper class that manages surface view. */ private class ViewHelper(private val callback: SurfaceHolder.Callback) { private var view: SurfaceView? = null private var displayContext: Context? = null @@ -162,9 +156,7 @@ class SurfaceManager(context: Context) : SurfaceHolder.Callback { } } - /** - * Check whether given display is the one being used right now. - */ + /** Check whether given display is the one being used right now. */ @Suppress("DEPRECATION") private fun isSameDisplay(context: Context, display: Display): Boolean { val wm = context.getSystemService(Context.WINDOW_SERVICE) as WindowManager @@ -186,7 +178,7 @@ class SurfaceManager(context: Context) : SurfaceHolder.Callback { lp.flags = if (focusable) VIEW_FLAG_FOCUSABLE else VIEW_FLAG_NOT_FOCUSABLE if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) { lp.layoutInDisplayCutoutMode = - WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES; + WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES } val wm = context.getSystemService(Context.WINDOW_SERVICE) as WindowManager @@ -212,12 +204,11 @@ class SurfaceManager(context: Context) : SurfaceHolder.Callback { @Suppress("DEPRECATION") private const val VIEW_FLAG_NOT_FOCUSABLE = WindowManager.LayoutParams.FLAG_FULLSCREEN or - WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE + WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE } } companion object { private const val TAG = "SurfaceManager" } - } diff --git a/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/Watchdog.kt b/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/Watchdog.kt index 6397a7927..c42729844 100644 --- a/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/Watchdog.kt +++ b/src/xrt/ipc/android/src/main/java/org/freedesktop/monado/ipc/Watchdog.kt @@ -13,9 +13,7 @@ import android.os.HandlerThread import android.os.Message import java.util.concurrent.atomic.AtomicInteger -/** - * Client watchdog, to determine whether runtime service should be stopped. - */ +/** Client watchdog, to determine whether runtime service should be stopped. */ class Watchdog( private val shutdownDelayMilliseconds: Long, private val shutdownListener: ShutdownListener @@ -25,14 +23,10 @@ class Watchdog( * all the callbacks run on background thread. */ interface ShutdownListener { - /** - * Callback to be invoked when last client disconnected. - */ + /** Callback to be invoked when last client disconnected. */ fun onPrepareShutdown() - /** - * Callback to be invoked when shutdown delay ended and there's no new client connected. - */ + /** Callback to be invoked when shutdown delay ended and there's no new client connected. */ fun onShutdown() } @@ -45,15 +39,17 @@ class Watchdog( fun startMonitor() { shutdownThread = HandlerThread("monado-client-watchdog") shutdownThread.start() - shutdownHandler = object : Handler(shutdownThread.looper) { - override fun handleMessage(msg: Message) { - when (msg.what) { - MSG_SHUTDOWN -> if (clientCount.get() == 0) { - shutdownListener.onShutdown() + shutdownHandler = + object : Handler(shutdownThread.looper) { + override fun handleMessage(msg: Message) { + when (msg.what) { + MSG_SHUTDOWN -> + if (clientCount.get() == 0) { + shutdownListener.onShutdown() + } } } } - } } fun stopMonitor() {