ActivityThread源码解析之Application与Activity启动

  • 前言

在看ActivityThread源码的时候,看到有博客提到它承担着整个应用的运转以及生命周期。于是很好奇想一探究竟,跟着跟着大概就把应用启动过程过程了解了一下。这篇文章主要是介绍ActivityThread中有关于应用启动过程以及Activity启动部分。有关Binder的机制或者其他部分内容太多了,以后专门看看。

  • 源码分析

Activity有且只有一个ActivityThread对象,他是每一个应用程序所在进程的主线程,。先看看主入口方法main,整个应用的loop死循环是从这边启动的。贴上代码:

public static void main(String[] args) {
	...
    ActivityThread thread = new ActivityThread();
    thread.attach(false);
    ...
    Looper.loop();
    throw new RuntimeException("Main thread loop unexpectedly exited");
}

第一部分是ActivityThread对象执行attach方法。这个是本文要分析的部分,就是他来启动应用。

第二部分是启动Looper,这个是整个应用程序的心脏。下一篇文章将分析。

OK!先跟进attach方法看下。贴上代码:

private void attach(boolean system) {
   	if (!system) {
    	final IActivityManager mgr = ActivityManagerNative.getDefault();
     	try {
        	mgr.attachApplication(mAppThread);
     	} catch (RemoteException ex) {
          	throw ex.rethrowFromSystemServer();
     	}
 	} else {
      	...
 	}    
    ...
}

传入system值为false,那么这里会进入判断为true的代码块里面。其中attachApplication是启动Application的方法,也是作为本文分析流程的入口。

1、ActivityThreadmAppThread对象传给AMS

上面介绍到了attachApplication方法,那么接下来看下mAppThread怎么传给AMS的。贴上时序图:

在这里插入图片描述

可以看到Activity通过ActivityManagerProxy代理来和AMS通信的。

那么先看下ActivityManagerNative.getDefault()是怎么获取对象的。先进入ActivityManagerNativegetDefault方法,贴上代码:

	/**
     * Retrieve the system's default/global activity manager.
     */
    static public IActivityManager getDefault() {
   
        return gDefault.get();
    }

注意到是gDefault对象的方法,跟进去:

private static final Singleton<IActivityManager> gDefault = new Singleton<IActivityManager>() {
        protected IActivityManager create() {
            IBinder b = ServiceManager.getService("activity");
            if (false) {
                Log.v("ActivityManager", "default service binder = " + b);
            }
            IActivityManager am = asInterface(b);
            if (false) {
                Log.v("ActivityManager", "default service = " + am);
            }
            return am;
        }
    };

public abstract class Singleton<T> {
    private T mInstance;
    protected abstract T create();
    public final T get() {
        synchronized (this) {
            if (mInstance == null) {
                mInstance = create();
            }
            return mInstance;
        }
    }
}

首先Singleton是一个获取单例对象的方法。首次调用get()方法就会执行create(),那么回到gDefault对象的create()方法看看。

首先是ServiceManager.getService("activity")。跟进ServiceManager类源码看一下:

 private static IServiceManager getIServiceManager() {
        if (sServiceManager != null) {
            return sServiceManager;
        }   // Find the service manager
    sServiceManager = ServiceManagerNative.asInterface(BinderInternal.getContextObject());
    return sServiceManager;
}

/**
 * Returns a reference to a service with the given name.
 * 
 * @param name the name of the service to get
 * @return a reference to the service, or <code>null</code> if the service doesn't exist
 */
public static IBinder getService(String name) {
    try {
        IBinder service = sCache.get(name);
        if (service != null) {
            return service;
        } else {
            return getIServiceManager().getService(name);
        }
    } catch (RemoteException e) {
        Log.e(TAG, "error in getService", e);
    }
    return null;
}

先看下getIServiceManager()方法,他返回的sServiceManager对象(ServiceManagerService的代理)。ServiceManagerService不是真实存在的,而是存在于C++层的一个单独的进程。

那么getService就是通过代理获取String为activity的服务的IBinder对象,其实也就是AMS的IBinder对象。

现在回到gDefault方法中。看下asInterface(b)方法,其中b也就是上面从ServiceManagerService获取的IBinder对象。

现在看下asInterface方法,贴上代码:

static public IActivityManager asInterface(IBinder obj) {
        if (obj == null) {
            return null;
        }
        IActivityManager in =
            (IActivityManager)obj.queryLocalInterface(descriptor);
        if (in != null) {
            return in;
        }
   	return new ActivityManagerProxy(obj);
}

queryLocalInterface方法用于检查obj是否位于本地进程,很明显前面获取AMS的IBinder对象位于另一个进程。那么asInterface返回的就是new出来的ActivityManagerProxy对象了。

到这一步返回到上面的getDefault()方法,可以知道他实际上返回的是AMS的ActivityManagerProxy代理对象。也就是说attach方法中的mgr对象其实也就是AMS的代理了。

那么看下attach方法中的mgr.attachApplication(mAppThread),也就是通过代理把mAppThread参数传给了AMS。

那到底是传什么东西呢?

看看ActivityManagerProxy源码:

class ActivityManagerProxy implements IActivityManager
{
   
    ...
    public void attachApplication(IApplicationThread app) throws RemoteException
    {
   
        Parcel data = Parcel.obtain();
        Parcel reply = Parcel<
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值