动态输入法 TSF 启动过程分析

为了解决 SampleIME + jvm 任务多开及 word 闪退的问题,对 动态输入法 TSF 的启动过程进行了分析。

顶层是 CSampleIME,在其构造函数中,startJVM() 启动 jvm(创建的 jvm 似乎只为了得到 penv0) 。这个过程中,对 penv0(jvm 环境), mainclass0(jar文件中的主类), dTyper0(主类的实例)进行初始化。

然后,在 CSampleIME::_AddTextProcessorEngine() 中:

	// Create composition processor engine
	if (_pCompositionProcessorEngine == nullptr)
	{
		_pCompositionProcessorEngine = new (std::nothrow) CCompositionProcessorEngine();
		
		// set JVM
		_pCompositionProcessorEngine->setJvm(penv0,&mainclass0,VER,&dTyper0,startinfo);
	}

_pCompositionProcessorEngine 是 CSmapleIME 的一个成员指针,它又包含了 ->dTyperJar,后者是 jar 文件的调用管理接口。它还包含  ->setJvm 方法。在 ->setJvm()中,做两件事:->dTyperJar.setJvm(), ->dTyperJar.startup(). 

在 CSmapleIME 中启动的 jvm,其环境指针 penv0,主类 mainclass0,主类实例 dTyper0,通过  _pCompositionProcessorEngine->setJvm()传递给其成员 ->dTyperJar。

dTyperJar 是一个接口,它有 3 个重要成员:penv, mainclass, dTyper。penv 可理解为连接到宿主线程的 jvm 环境,mainclass 是 mainclass0 的本地副本,dTyper = penv->NewGlobalRef(*_dTyper0); 可理解为宿主线程上挂接的 dTyper0。

dTyperJar 还有两个重要的成员函数:setJvm() 和 startup(). 在 setJvm()中,把 penv0, mainclass0 进行本地存储,penv0->GetJavaVM(&jvm); jvm->AttachCurrentThread((void **)&penv, &args);

至此,dTyper 完成了初始化,可以执行打字功能。当需要调用 dTyper 中的函数 func_xxx() 时,

jmethodID mid1 = penv->GetMethodID(mainclass, "func_xxx", "()Ljava/lang/String;");
jstring msg1 = (jstring)penv->CallObjectMethod(dTyper, mid1);

目前看起来,penv0->GetJavaVM(&jvm); jvm->AttachCurrentThread((void **)&penv, &args); 都有可能造成 word 闪退。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值