Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 97ecbda9 authored by Hawkwood Glazier's avatar Hawkwood Glazier Committed by Automerger Merge Worker
Browse files

Merge "Skip dynamic load of known clock plugins" into udc-dev am: 9387c640 am: 6ee95746

parents 72c1eb87 6ee95746
Loading
Loading
Loading
Loading
+67 −2
Original line number Diff line number Diff line
@@ -48,6 +48,18 @@ import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext

private val KEY_TIMESTAMP = "appliedTimestamp"
private val KNOWN_PLUGINS =
    mapOf<String, List<ClockMetadata>>(
        "com.android.systemui.falcon.one" to listOf(ClockMetadata("ANALOG_CLOCK_BIGNUM")),
        "com.android.systemui.falcon.two" to listOf(ClockMetadata("DIGITAL_CLOCK_CALLIGRAPHY")),
        "com.android.systemui.falcon.three" to listOf(ClockMetadata("DIGITAL_CLOCK_FLEX")),
        "com.android.systemui.falcon.four" to listOf(ClockMetadata("DIGITAL_CLOCK_GROWTH")),
        "com.android.systemui.falcon.five" to listOf(ClockMetadata("DIGITAL_CLOCK_HANDWRITTEN")),
        "com.android.systemui.falcon.six" to listOf(ClockMetadata("DIGITAL_CLOCK_INFLATE")),
        "com.android.systemui.falcon.seven" to listOf(ClockMetadata("DIGITAL_CLOCK_METRO")),
        "com.android.systemui.falcon.eight" to listOf(ClockMetadata("DIGITAL_CLOCK_NUMBEROVERLAP")),
        "com.android.systemui.falcon.nine" to listOf(ClockMetadata("DIGITAL_CLOCK_WEATHER")),
    )

private fun <TKey, TVal> ConcurrentHashMap<TKey, TVal>.concurrentGetOrPut(
    key: TKey,
@@ -127,8 +139,61 @@ open class ClockRegistry(

    private val pluginListener =
        object : PluginListener<ClockProviderPlugin> {
            override fun onPluginAttached(manager: PluginLifecycleManager<ClockProviderPlugin>) {
                manager.loadPlugin()
            override fun onPluginAttached(
                manager: PluginLifecycleManager<ClockProviderPlugin>
            ): Boolean {
                if (keepAllLoaded) {
                    // Always load new plugins if requested
                    return true
                }

                val knownClocks = KNOWN_PLUGINS.get(manager.getPackage())
                if (knownClocks == null) {
                    logBuffer.tryLog(
                        TAG,
                        LogLevel.WARNING,
                        { str1 = manager.getPackage() },
                        { "Loading unrecognized clock package: $str1" }
                    )
                    return true
                }

                logBuffer.tryLog(
                    TAG,
                    LogLevel.INFO,
                    { str1 = manager.getPackage() },
                    { "Skipping initial load of known clock package package: $str1" }
                )

                var isClockListChanged = false
                for (metadata in knownClocks) {
                    val id = metadata.clockId
                    val info =
                        availableClocks.concurrentGetOrPut(id, ClockInfo(metadata, null, manager)) {
                            isClockListChanged = true
                            onConnected(id)
                        }

                    if (manager != info.manager) {
                        logBuffer.tryLog(
                            TAG,
                            LogLevel.ERROR,
                            { str1 = id },
                            { "Clock Id conflict on known attach: $str1 is double registered" }
                        )
                        continue
                    }

                    info.provider = null
                }

                if (isClockListChanged) {
                    triggerOnAvailableClocksChanged()
                }
                verifyLoadedProviders()

                // Load executed via verifyLoadedProviders
                return false
            }

            override fun onPluginLoaded(
+3 −1
Original line number Diff line number Diff line
@@ -190,7 +190,9 @@ enum class ClockTickRate(val value: Int) {
data class ClockMetadata(
    val clockId: ClockId,
    val name: String,
)
) {
    constructor(clockId: ClockId) : this(clockId, clockId) {}
}

/** Render configuration for the full clock. Modifies the way systemUI behaves with this clock. */
data class ClockConfig(
+8 −0
Original line number Diff line number Diff line
@@ -16,12 +16,20 @@

package com.android.systemui.plugins;

import android.content.ComponentName;

/**
 * Provides the ability for consumers to control plugin lifecycle.
 *
 * @param <T> is the target plugin type
 */
public interface PluginLifecycleManager<T extends Plugin> {
    /** Returns the ComponentName of the target plugin. Maybe be called when not loaded. */
    ComponentName getComponentName();

    /** Returns the package name of the target plugin. May be called when not loaded. */
    String getPackage();

    /** Returns the currently loaded plugin instance (if plugin is loaded) */
    T getPlugin();

+10 −5
Original line number Diff line number Diff line
@@ -60,13 +60,18 @@ public interface PluginListener<T extends Plugin> {

    /**
     * Called when the plugin is first attached to the host application. {@link #onPluginLoaded}
     * will be automatically called as well when first attached. This may be called multiple times
     * if multiple plugins are allowed. It may also be called in the future if the plugin package
     * changes and needs to be reloaded. Each call to {@link #onPluginAttached} will provide a new
     * or different {@link PluginLifecycleManager}.
     * will be automatically called as well when first attached if true is returned. This may be
     * called multiple times if multiple plugins are allowed. It may also be called in the future
     * if the plugin package changes and needs to be reloaded. Each call to
     * {@link #onPluginAttached} will provide a new or different {@link PluginLifecycleManager}.
     *
     * @return returning true will immediately load the plugin and call onPluginLoaded with the
     *   created object. false will skip loading, but the listener can load it at any time using the
     *   provided PluginLifecycleManager. Loading plugins immediately is the default behavior.
     */
    default void onPluginAttached(PluginLifecycleManager<T> manager) {
    default boolean onPluginAttached(PluginLifecycleManager<T> manager) {
        // Optional
        return true;
    }

    /**
+22 −14
Original line number Diff line number Diff line
@@ -79,10 +79,20 @@ public class PluginInstance<T extends Plugin> implements PluginLifecycleManager

    /** Alerts listener and plugin that the plugin has been created. */
    public void onCreate() {
        mListener.onPluginAttached(this);
        boolean loadPlugin = mListener.onPluginAttached(this);
        if (!loadPlugin) {
            if (mPlugin != null) {
                unloadPlugin();
            }
            return;
        }

        if (mPlugin == null) {
            loadPlugin();
        } else {
            return;
        }

        mPluginFactory.checkVersion(mPlugin);
        if (!(mPlugin instanceof PluginFragment)) {
            // Only call onCreate for plugins that aren't fragments, as fragments
            // will get the onCreate as part of the fragment lifecycle.
@@ -90,7 +100,6 @@ public class PluginInstance<T extends Plugin> implements PluginLifecycleManager
        }
        mListener.onPluginLoaded(mPlugin, mPluginContext, this);
    }
    }

    /** Alerts listener and plugin that the plugin is being shutdown. */
    public void onDestroy() {
@@ -118,6 +127,7 @@ public class PluginInstance<T extends Plugin> implements PluginLifecycleManager
            return;
        }

        mPluginFactory.checkVersion(mPlugin);
        if (!(mPlugin instanceof PluginFragment)) {
            // Only call onCreate for plugins that aren't fragments, as fragments
            // will get the onCreate as part of the fragment lifecycle.
@@ -205,12 +215,8 @@ public class PluginInstance<T extends Plugin> implements PluginLifecycleManager
            PluginFactory<T> pluginFactory = new PluginFactory<T>(
                    context, mInstanceFactory, appInfo, componentName, mVersionChecker, pluginClass,
                    () -> getClassLoader(appInfo, mBaseClassLoader));
            // TODO: Only create the plugin before version check if we need it for
            // legacy version check.
            T instance = pluginFactory.createPlugin();
            pluginFactory.checkVersion(instance);
            return new PluginInstance<T>(
                    context, listener, componentName, pluginFactory, instance);
                    context, listener, componentName, pluginFactory, null);
        }

        private boolean isPluginPackagePrivileged(String packageName) {
@@ -332,7 +338,9 @@ public class PluginInstance<T extends Plugin> implements PluginLifecycleManager
                ClassLoader loader = mClassLoaderFactory.get();
                Class<T> instanceClass = (Class<T>) Class.forName(
                        mComponentName.getClassName(), true, loader);
                return (T) mInstanceFactory.create(instanceClass);
                T result = (T) mInstanceFactory.create(instanceClass);
                Log.v(TAG, "Created plugin: " + result);
                return result;
            } catch (ClassNotFoundException ex) {
                Log.e(TAG, "Failed to load plugin", ex);
            } catch (IllegalAccessException ex) {
Loading