CN107992344B - 一种协程实现方法及装置 - Google Patents
一种协程实现方法及装置 Download PDFInfo
- Publication number
- CN107992344B CN107992344B CN201610938968.8A CN201610938968A CN107992344B CN 107992344 B CN107992344 B CN 107992344B CN 201610938968 A CN201610938968 A CN 201610938968A CN 107992344 B CN107992344 B CN 107992344B
- Authority
- CN
- China
- Prior art keywords
- coroutine
- function call
- function
- call stack
- execution
- Prior art date
- Legal status (The legal status is an assumption and is not a legal conclusion. Google has not performed a legal analysis and makes no representation as to the accuracy of the status listed.)
- Active
Links
Images
Landscapes
- Executing Machine-Instructions (AREA)
- Devices For Executing Special Programs (AREA)
Abstract
本发明实施例提供一种协程实现方法及装置,该方法包括:根据协程对应函数的脚本语言字节码,确定协程对应的函数调用栈所需的目标内存空间;其中,一个协程对应一个函数调用栈;为所述函数调用栈分配与所述目标内存空间相应的独立内存空间;其中,各协程对应的函数调用栈的内存空间互不干扰;在所述独立内存空间中,为所述函数调用栈的各结构体填充内容;对所述函数调用栈进行协程执行前的预处理;将虚拟机的执行状态指向所述函数调用栈,以执行所述协程。进一步,本发明实施例还可以实现协程的切换。本发明实施例可以提升协程实现的效率。
Description
技术领域
本发明涉及程序技术领域,具体涉及一种协程实现方法及装置。
背景技术
协程作为用户态的一种可重入的子程序在计算机程序、数据处理过程中应用广泛;目前集成协程能力的框架一般通过Generator(迭代器)提供的函数重入能力实现,即将一个Generator作为一个协程,并在应用层面实现协程的调度器。
然而,基于Generator实现协程,必须采用Generator的yield关键字(yield代表一种控制权的放弃、转移);一旦协程对应的函数采用了yield关键字,函数的上层调用都必须采用yield去调用子函数,且同时要定义yield关键字的函数调用和函数返回语义;可见,基于Generator,采用yield关键字实现协程,会带入yield关键字本身存在的实现较复杂的问题,导致协程的实现较为复杂、麻烦,降低了协程的实现效率。
发明内容
有鉴于此,本发明实施例提供一种协程实现方法及装置,以降低协程实现的复杂度,提升协程实现的效率。
为实现上述目的,本发明实施例提供如下技术方案:
一种协程实现方法,包括:
根据协程对应函数的脚本语言字节码,确定协程对应的函数调用栈所需的目标内存空间;其中,一个协程对应一个函数调用栈;
为所述函数调用栈分配与所述目标内存空间相应的独立内存空间;其中,各协程对应的函数调用栈的内存空间互不干扰;
在所述独立内存空间中,为所述函数调用栈的各结构体填充内容;
对所述函数调用栈进行协程执行前的预处理;
将虚拟机的执行状态指向所述函数调用栈,以执行所述协程。
本发明实施例还提供一种协程实现装置,包括:
目标内存空间确定模块,用于根据协程对应函数的脚本语言字节码,确定协程对应的函数调用栈所需的目标内存空间;其中,一个协程对应一个函数调用栈;
空间分配模块,用于为所述函数调用栈分配与所述目标内存空间相应的独立内存空间;其中,各协程对应的函数调用栈的内存空间互不干扰;
内容填充模块,用于在所述独立内存空间中,为所述函数调用栈的各结构体填充内容;
预处理模块,用于对所述函数调用栈进行协程执行前的预处理;
执行模块,用于将虚拟机的执行状态指向所述函数调用栈,以执行所述协程。
基于上述技术方案,本发明实施例提供的协程实现方法,可以为协程分配相应的函数调用栈,从而通过确定函数调用栈所需的内存空间,可为协程在内存中分配独立的函数调用栈所用空间,实现不同协程的函数调用栈执行互不干扰;然后在独立的内存空间中,将协程在函数调用栈的各结构体的内容进行填充,并进行协程执行前的处理,可为协程划分独立的可用的函数调用栈,使得协程对应的函数调用栈具有协程能力,进而将虚拟机的执行状态指向所述函数调用栈,可实现相应协程的执行。本发明实施例提供的协程实现方法,可直接基于脚本语言的开发环境底层的内存空间,为每个协程划分独立的函数调用栈,从而直接基于协程的函数调用栈的调用,来实现协程执行,降低了协程实现的复杂度,提升了协程实现的效率。
附图说明
为了更清楚地说明本发明实施例或现有技术中的技术方案,下面将对实施例或现有技术描述中所需要实现的附图作简单地介绍,显而易见地,下面描述中的附图仅仅是本发明的实施例,对于本领域普通技术人员来讲,在不付出创造性劳动的前提下,还可以根据提供的附图获得其他的附图。
图1为本发明实施例提供的函数调用栈的结构示意图;
图2为本发明实施例提供的协程实现方法的流程图;
图3为本发明实施例提供的函数调用栈相互独立的示意图;
图4为本发明实施例提供的协程切换的方法流程图;
图5为本发明实施例提供的协程切换示意图;
图6为本发明实施例提供的协程实现装置的结构框图;
图7为本发明实施例提供的协程实现装置的另一结构框图;
图8为本发明实施例提供的处理设备的硬件结构框图。
具体实施方式
下面将结合本发明实施例中的附图,对本发明实施例中的技术方案进行清楚、完整地描述,显然,所描述的实施例仅仅是本发明一部分实施例,而不是全部的实施例。基于本发明中的实施例,本领域普通技术人员在没有做出创造性劳动前提下所获得的所有其他实施例,都属于本发明保护的范围。
区别于现有基于Generator,采用yield关键字实现协程的方式,本发明实施例可在脚本语言(如PHP语言)的开发环境底层(如Zend底层),基于编程语言(如C语言),为应用层的脚本语言以及脚本语言的扩展开发提供协程能力;具体的,本发明实施例可直接基于脚本语言的开发环境底层的内存空间,为每个协程划分独立的函数调用栈,且各个协程的函数调用栈对应的内存空间相应独立、互不干扰;
从而在执行某一协程时,通过将虚拟机的执行状态指向对应的函数调用栈,则可实现协程的执行。虚拟机的执行状态可以由函数位置指针指示,函数位置指针可以在各个协程对应的函数调用栈中,全局维护当前所执行到的函数调用栈;由于在协程的实现过程中,避免了yield关键字的采用,而是直接通过创建和执行协程对应的函数调用栈,来实现协程的创建和执行,降低了协程实现的复杂度,提升了协程实现的效率。
协程的实现可以包括协程的创建和调用执行;进一步可以涉及协程间的切换。
下面以脚本语言为PHP语言(Hypertext Preprocessor,超文本预处理器,一种服务端脚本语言,常用语网络开发),脚本语言的开发环境底层为Zend(PHP语言的核心组件,提供了PHP的编译能力以及语言的执行器),编程语言为C语言(The C ProgrammingLanguage,一门通用计算机编程语言)为例,对本发明实施例提供的协程实现方法进行介绍;相应的,本发明实施例可在Zend底层基于C语言,为应用层PHP语言开发以及PHP的扩展开发提供协程能力,且可直接基于Zend的内存空间,为每个协程划分独立的函数调用栈;
显然,脚本语言、脚本语言的开发环境底层、编程语言并不限于上段描述的示例,本发明实施例还可采用其他形式的脚本语言、开发环境底层、编程语言,进行协程的实现。
在介绍具体的协程实现过程前,本发明实施例先为协程分配的函数调用栈的结构进行介绍;参照图1,图1所示的一组组合在一起的虚线框表示的结构为一个协程对应的函数调用栈的结构;一个函数调用栈具有,TMP_VAR、CV、CALL_SLOT、ARGUMENTS、zend_execute_data等结构体。
其中,TMP_VAR表示协程对应函数的临时变量;CV表示协程对应函数的局部变量;CALL_SLOT表示协程对应函数的嵌套调用信息;ARGUMENTS表示协程对应函数调用的参数;zend_execute_data(简称execute_data)表示协程对应函数的函数执行信息,函数执行信息包括:op_array地址(协程对应函数的PHP字节码的地址),名空间等基本信息。
图1所示函数调用栈的结构仅为可选的,需要说明的是,一个协程对应的函数调用栈可以包括:函数执行信息的结构体,函数变量信息的结构体,及函数调用信息的结构体等;
在一个函数调用栈中,函数执行信息的结构体可以是zend_execute_data结构体;在一个函数调用栈中,函数变量信息的结构体的数量可以是至少一个,TMP_VAR、CV等结构体,仅是函数变量信息的结构体的可选形式;在一个函数调用栈中,函数调用信息的结构体的数量可以是至少一个,CALL_SLOT、ARGUMENTS仅是函数调用信息的结构体的可选形式。
需要说明的是,executor_global(简称EG,函数位置指针的一种可选形式)这一结构体,可以在各个函数调用栈中,全局维护虚拟机当前执行的函数调用栈,并指向该函数调用栈;具体的,EG在指向虚拟机当前执行的函数调用栈时,可以指向该函数调用栈的execute_data的结构体;
进一步,zend_execute_data还可以保存协程对应函数所调用的函数信息,并通过关联指针(如prev指针)指向上一次调用的另一函数调用栈的函数执行信息,从而通过prev指针可以将依次执行的函数调用栈关联起来。
在定义了上述协程对应的函数调用栈的结构后,本发明实施例可以在发生一次协程调用的时候,计算并在内存中分配协程对应的函数调用栈,并执行函数调用栈来实现协程执行。
图2示出了本发明实施例提供的协程实现方法的流程图,参照图2,该方法可以包括:
步骤S10、根据协程对应函数的PHP字节码,计算所述协程对应的函数调用栈的函数变量信息的结构体,及函数调用信息的结构体所需的内存空间。
其中,一个协程对应一个函数调用栈。
op_array可以认为是协程对应函数的PHP字节码,PHP函数的op_array中通过last_var,T,used_stack等变量维护了PHP函数所需的内存空间;可选的,一个PHP函数本质上是由大量字节码组成的数据,因此根据协程对应函数的op_array表示的字节码,所用到的具体变量,调用信息等数据,本发明实施例可以计算出协程对应函数执行需要多大的内存空间去保存这些变量,和函数调用信息,从而相应的确定出协程对应的函数调用栈的函数变量信息的结构体,及函数调用信息的结构体所需的内存空间。
可选的,步骤S10可以计算协程对应的函数调用栈的TMP_VAR、CV、CALL_SLOT、ARGUMENTS等结构体所需的内存空间。
可选的,PHP仅是本发明实施例所采用的脚本语言的可选形式;步骤S10可以认为是,根据协程对应函数的脚本语言字节码,计算所述函数调用栈的函数变量信息的结构体,及函数调用信息的结构体所需的内存空间的可选方式;在选用其他形式的脚本语言的情况下,本发明实施例可相应的以其他形式脚本语言的字节码,进行函数变量信息的结构体,及函数调用信息的结构体所需的内存空间的计算。
步骤S11、根据所述函数调用栈的函数执行信息的结构体,预设定的所需内存空间,及所确定的函数变量信息的结构体,和函数调用信息的结构体所需的内存空间,确定所述函数调用栈所需的目标内存空间。
可选的,函数调用栈的函数执行信息的结构体的长度可以是预先设定的(如函数执行信息的结构体的长度,可以是预先固定的),相应的,其所需的内存空间可以通过预定设定来确定(如确定预先固定的函数执行信息的结构体的内存空间);在步骤S10计算出函数变量信息的结构体,及函数调用信息的结构体所需的内存空间后,本发明实施例可以结合函数执行信息的结构体预设定的所需内存空间,确定出协程对应的函数调用栈所需的目标内存空间。
可选的,函数执行信息的结构体所需的内存空间是固定的,仅是预设定函数执行信息的结构体所需内存空间的可选形式;本发明实施例还可以在每次实现协程时,进行函数执行信息的结构体所需的内存空间的指定设置。
进一步,协程对应的函数调用栈还可以维持有维护协程自身信息的结构体(如coro_task结构体),该结构体的长度可以是固定的,即该结构体所需的内存空间可以是固定的;从而本发明实施例可以根据函数执行信息的结构体,预设定的所需内存空间,维护协程自身信息的结构体所需的固定内存空间,及步骤S10所确定的函数变量信息的结构体,函数调用信息的结构体所需的内存空间,确定所述函数调用栈所需的目标内存空间;相应的,实现的伪代码可以如下:
size_texecute_data_size=sizeof(zend_execute_data);
size_tCVs_size=(sizeof(zval**)*op_array->last_var*2);
size_tTs_size=(sizeof(temp_variable))*op_array->T;
size_tcall_slots_size=(sizeof(call_slot))*op_array->nested_calls;
size_tstack_size=(sizeof(zval*))*op_array->used_stack;
size_ttask_size=sizeof(coro_task);
size_ttotal_size=execute_data_size+Ts_size+CVs_size+call_slots_size+stack_size。
可选的,步骤S10至步骤S11仅是根据协程对应函数的脚本语言字节码,确定协程对应的函数调用栈所需的目标内存空间的可选形式;除步骤S10至步骤S11的实现方式外,脚本语言字节码可能仅可对应确定出函数变量信息的结构体,或函数调用信息的结构体所需的内存空间,本发明实施例还可指定脚本语言字节码未对应的结构体所需的内存空间,从而根据脚本语言字节码,及脚本语言字节码未对应的结构体指定的所需内存空间,确定协程对应的函数调用栈的各结构体所需的目标内存空间。
步骤S12、在PHP的内存中为所述函数调用栈分配与所述目标内存空间相应的独立内存空间。
可选的,步骤S12仅是为协程对应的函数调用栈分配与所述目标内存空间相应的独立内存空间的可选方式。
本发明实施例定义了每个协程对应的函数调用栈的结构,在确定函数调用栈的目标内存空间后,可为每个协程对应的函数调用栈分配相应的独立内存空间,且不同的协程对应的函数调用栈的内存空间互不干扰。
步骤S13、将所述函数调用栈的各结构体的内容,拷贝到所述独立内存空间中的函数调用栈中。
在为协程对应的函数调用栈分配独立内存空间后,可将协程在该函数调用栈的各结构体中的内容,进行参数拷贝,从而将各结构体的内容填入到独立内存空间中的函数调用栈中。
拷贝的结构体内容可以包括:函数执行信息的结构体,函数变量信息的结构体,及函数调用信息的结构体的内容等;各结构体表示的内容含义可参照图1部分的介绍。
可选的,步骤S13可以是在所述独立内存空间中,为所述函数调用栈的各结构体填充内容的可选方式。
步骤S14、将所述函数调用栈的函数执行信息的结构体进行初始化。
可选的,本发明实施例可将execute_data初始化。
步骤S15、初始化PHP字节码缓存。
可选的,本发明实施例可初始化op_array缓存;可选的,每一个op_array需要缓存空间来缓存op_array在反复被执行过程中可被重用的信息,比如子调用的函数信息等,从而可以加速函数执行速度。
可选的,步骤S15可以是初始化脚本语言字节码缓存的可选方式。
步骤S16、初始化This指针。
可选的,This指针指向当前执行函数所属的类的实例,如果用一个实例的方法作为协程的入口,则必须实现这个实例初始化的This指针,才能保证协程的正常执行。
至此,本发明实施例基于入口函数的信息完成了对协程内存空间的初始化。
步骤S17、更新协程信息。
可选的,更新协程信息包括:更新已创建协程的总数等描述信息。
可选的,步骤S14至步骤S17可以认为是对所述函数调用栈进行协程执行前的预处理。
至此,协程创建完成,可进行调用执行。
步骤S18、将虚拟机的执行状态指向所述函数调用栈,以执行所述协程。
可选的,本发明实施例可以调取EG(executor_global,函数位置指针的一种可选形式),确定EG当前指向的函数调用栈,从而通过将Zend虚拟机的执行状态,指向EG所指向的函数调用栈,以将执行流程交给虚拟机,从而执行协程。
可选的,虚拟机可以是Zend虚拟机。
本发明实施例提供的协程实现方法,可以为协程分配相应的函数调用栈,从而通过确定函数调用栈所需的内存空间,可为协程在内存中分配独立的函数调用栈所用空间,实现不同协程的函数调用栈执行互不干扰;然后在独立的内存空间中,将协程在函数调用栈的各结构体的内容进行填充,并进行协程执行前的处理,可为协程划分独立的可用的函数调用栈,使得协程对应的函数调用栈具有协程能力,进而将虚拟机的执行状态指向所述函数调用栈,可实现相应协程的执行。本发明实施例提供的协程实现方法,可直接基于脚本语言的开发环境底层的内存空间,为每个协程划分独立的函数调用栈,从而直接基于协程的函数调用栈的调用,来实现协程执行,降低了协程实现的复杂度,提升了协程实现的效率。
如图3所示,本发明实施例可为协程划分独立的可用的函数调用栈,且各个协程的函数调用栈对应的内存空间相互独立、互不干扰;图3中一个虚线框代表一个协程的内存空间,不同协程之间是空间隔离的,在一个协程里每次有函数的嵌套调用时,这个协程自己的空间就会随着新的栈而增长,但是不会干扰其他协程。
可选的,在实现协程的执行后,本发明实施例可通过编程语言的非本地跳转能力控制脚本语言的逻辑执行语言,从而实现协程的切换;如通过C语言的非本地跳转能力控制PHP语言的逻辑执行流程,实现协程的切换。
现有技术中,Generator由编译阶段生成的opcode yield来实现当前执行流程的退出;虽然在扩展里,可以操作Zend来实现或者保存上下文,但是没有编译器的帮助,并没有办法实现Zend虚拟机本身的调用栈的退出;因此现有技术在扩展函数里只能重新返回到PHP空间去继续执行协程,实现协程的切换;
而本发明实施例可以通过non-local jump(非本地跳转,在C语言中用来实现跨多级函数的跳转)技术来实现协程切换;相应的,图4示出了协程切换的方法流程图,参照图4,该方法可以包括:
步骤S20、在执行协程时,创建当前执行状态的存档,所述存档记录有所述协程的执行入口。
可选的,non-local jump包括两个函数:setjmp和longjmp;setjmp作用是生成一个记录点,longjmp可以返回这个记录点,类似于游戏存档;本发明实施例可以采用setjmp创建当前执行状态的存档;
可选的,当前执行状态可以是当前PHP内核的执行状态,本质是这个时刻CPU所有寄存器的值。
步骤S21、在需切换协程时,根据历史记录的存档,确定需切换至的协程的执行入口,返回所确定的执行入口,以切换到需切换至的协程进行执行。
可选的,本发明实施例可为每个协程标记相应的标识,从而存档可以记录各执行过的协程的标识与执行入口的关系;进而在需切换协程时,本发明实施例可根据需切换至的协程标识,从存档中确定该标识相应的执行入口,实现需切换至的协程的执行入口的确定。
可选的,当需要进行协程的切换的时候,本发明实施例可以通过longjmp返回到需切换至的协程的入口处,从而执行需切换至的协程,完成协程的切换;具体的,本发明实施例可以将虚拟机的执行状态指向该执行入口的函数调用栈,从而执行需切换至的协程。
相应的,图5示出了相应的协程切换示意图;其中,实现协程的过程可以参照图2部分介绍;恢复上下文是协程切换的另一种描述。
可选的,本发明实施例提供的协程创建、调用、切换功能可以整合在协程组件中,协程组件可以认为是一个功能模块,该协程组件可以提供协程功能(包括协程的创建、调用、切换等);可选的,协程可以是原生协程,相应的,协程组件可以是原生协程组件。
可选的,在进行协程切换时,上层业务可以将协程组件和网络请求相整合;如在协程A执行过程中,如果需要调用网络请求接口,网络请求接口可以调用协程组件的协程切换接口,此时协程组件会将当前协程A的函数调用栈的信息保存成一个php_context结构(上下文结构的可选形式),并和网络请求映射起来;相应的,实现存档的方式可以是:在执行协程时,若需要调用网络请求接口,则可将协程的函数调用栈的信息保存成一个上下文结构,并将所述上下文结构和网络请求映射起来,以形成所述存档。
然后通过longjmp返回到setjmp在协程A执行前所保存存档,完成了协程A的保存和切出;php_context的主要结构如下。
structphp_context{
zend_execute_data*execute_data;//execute_data的地址
zend_op**opline_ptr;//协程切出前执行到的字节码
zend_op_array*active_op_array;//协程所执行的op_array
zval*this;//协程的This指针
zend_class_entry*scope;//协程的名空间
zend_vm_stackvm_stack;//协程的调用栈地址
php_context_state state;//协程的状态
};
等到协程A发出的网络请求返回时,协程组件会根据协程A所保存php_context重新设置executor_global从而恢复Zend虚拟机状态,通过setjmp生成新的存档点,然后调用虚拟机运行,恢复协程A的执行。这样协程组件就可以根据php_context在不同的协程之间切换并且整个切换的过程非常的快。
本发明实施例提供的协程实现方法,可以在底层直接实现协程对应的函数调用栈,实现协程的创建、执行,协程的实现效率得以提升;同时基于Zend等底层实现了协程调度能力,提高了协程切换的性能。进一步,本发明实施例可以在PHP等脚本语言扩展上,调用协程组件的能力,利用协程的能力。
下面对本发明实施例提供的协程实现装置进行介绍,下文描述的协程实现装置可以与上文描述的协程实现方法相互对应参照。
图6为本发明实施例提供的协程实现装置的结构框图,该装置可设置于具有协程创建、调度能力的处理设备中,该处理设备可以是用户侧的终端设备,也可以是网络侧的服务器;
参照图6,该装置可以包括:
目标内存空间确定模块100,用于根据协程对应函数的脚本语言字节码,确定协程对应的函数调用栈所需的目标内存空间;其中,一个协程对应一个函数调用栈;
空间分配模块200,用于为所述函数调用栈分配与所述目标内存空间相应的独立内存空间;其中,各协程对应的函数调用栈的内存空间互不干扰;
内容填充模块300,用于在所述独立内存空间中,为所述函数调用栈的各结构体填充内容;
预处理模块400,用于对所述函数调用栈进行协程执行前的预处理;
执行模块500,用于将虚拟机的执行状态指向所述函数调用栈,以执行所述协程。
可选的,所述函数调用栈包括:函数执行信息的结构体,函数变量信息的结构体,及函数调用信息的结构体;
相应的,目标内存空间确定模块100,用于根据协程对应函数的脚本语言字节码,确定协程对应的函数调用栈所需的目标内存空间,具体包括:
根据协程对应函数的脚本语言字节码,计算所述函数调用栈的函数变量信息的结构体,及函数调用信息的结构体所需的内存空间;
根据所述函数调用栈的函数执行信息的结构体,预设定的所需内存空间,及所确定的函数变量信息的结构体,和函数调用信息的结构体所需的内存空间,确定所述函数调用栈所需的目标内存空间。
可选的,所述函数执行信息的结构体包括:协程对应函数所调用的函数信息;所述函数调用栈通过关联指针指向上一次调用的函数调用栈的函数执行信息。
可选的,预处理模块400,用于对所述函数调用栈进行协程执行前的预处理,具体包括:
将所述函数调用栈的函数执行信息的结构体进行初始化;
初始化脚本语言字节码缓存;
初始化This指针;
更新协程信息。
可选的,执行模块500,用于虚拟机的执行状态指向所述函数调用栈,以执行所述协程,具体包括:
确定函数位置指针当前指向的函数调用栈;其中,所述函数位置指针在各个函数调用栈中,全局维护虚拟机当前执行的函数调用栈,并指向该函数调用栈;
将虚拟机的执行状态,指向所述函数位置指针所指向的函数调用栈,以执行所述协程。
可选的,如图7所示,本发明实施例提供的协程实现装置还可以包括:
存档创建模块600,用于在执行协程时,创建当前执行状态的存档,所述存档记录有所述协程的执行入口;
协程切换执行模块700,用于在需切换协程时,根据历史记录的存档,确定需切换至的协程的执行入口,返回所确定的执行入口,以切换到需切换至的协程进行执行。
可选的,存档创建模块600,用于创建当前执行状态的存档,具体包括:
在执行协程时,若需要调用网络请求接口,则调用协程切换接口,将协程的函数调用栈的信息保存成一个上下文结构,并将所述上下文结构和网络请求映射起来,以形成所述存档;
相应的,协程切换执行模块700,用于返回所确定的执行入口,以切换到需切换至的协程进行执行,具体包括:
返回到所述协程执行前所保存的存档对应的执行入口。
可选的,本发明实施例采用的脚本语言为PHP语言;脚本语言的开发环境底层为Zend底层;脚本语言采用的编程语言为C语言。相应的,本发明实施例可在Zend底层基于C语言,为应用层PHP语言开发以及PHP扩展开发提供协程能力,且可基于直接基于Zend的内存空间,为每个协程划分独立的函数调用栈。
本发明实施例还提供一种处理设备,该处理设备可以包括上述所述的协程实现装置。
图8示出了该处理设备的硬件结构框图,参照图8,该处理设备可以包括:处理器1,通信接口2,存储器3和通信总线4;
其中处理器1、通信接口2、存储器3通过通信总线4完成相互间的通信;
可选的,通信接口2可以为通信模块的接口,如GSM模块的接口;
处理器1可能是一个中央处理器CPU,或者是特定集成电路ASIC(ApplicationSpecific Integrated Circuit),或者是被配置成实施本发明实施例的一个或多个集成电路。
存储器3可能包含高速RAM存储器,也可能还包括非易失性存储器(non-volatilememory),例如至少一个磁盘存储器。
其中,处理器1具体用于:
根据协程对应函数的脚本语言字节码,确定协程对应的函数调用栈所需的目标内存空间;其中,一个协程对应一个函数调用栈;
为所述函数调用栈分配与所述目标内存空间相应的独立内存空间;其中,各协程对应的函数调用栈的内存空间互不干扰;
在所述独立内存空间中,为所述函数调用栈的各结构体填充内容;
对所述函数调用栈进行协程执行前的预处理;
将虚拟机的执行状态指向所述函数调用栈,以执行所述协程。
本说明书中各个实施例采用递进的方式描述,每个实施例重点说明的都是与其他实施例的不同之处,各个实施例之间相同相似部分互相参见即可。对于实施例公开的装置而言,由于其与实施例公开的方法相对应,所以描述的比较简单,相关之处参见方法部分说明即可。
专业人员还可以进一步意识到,结合本文中所公开的实施例描述的各示例的单元及算法步骤,能够以电子硬件、计算机软件或者二者的结合来实现,为了清楚地说明硬件和软件的可互换性,在上述说明中已经按照功能一般性地描述了各示例的组成及步骤。这些功能究竟以硬件还是软件方式来执行,取决于技术方案的特定应用和设计约束条件。专业技术人员可以对每个特定的应用来实现不同方法来实现所描述的功能,但是这种实现不应认为超出本发明的范围。
结合本文中所公开的实施例描述的方法或算法的步骤可以直接用硬件、处理器执行的软件模块,或者二者的结合来实施。软件模块可以置于随机存储器(RAM)、内存、只读存储器(ROM)、电可编程ROM、电可擦除可编程ROM、寄存器、硬盘、可移动磁盘、CD-ROM、或技术领域内所公知的任意其它形式的存储介质中。
对所公开的实施例的上述说明,使本领域专业技术人员能够实现或实现本发明。对这些实施例的多种修改对本领域的专业技术人员来说将是显而易见的,本文中所定义的一般原理可以在不脱离本发明的核心思想或范围的情况下,在其它实施例中实现。因此,本发明将不会被限制于本文所示的这些实施例,而是要符合与本文所公开的原理和新颖特点相一致的最宽的范围。
Claims (13)
1.一种协程实现方法,其特征在于,包括:
根据协程对应函数的脚本语言字节码,确定协程对应的函数调用栈所需的目标内存空间;其中,一个协程对应一个函数调用栈;
为所述函数调用栈分配与所述目标内存空间相应的独立内存空间;其中,各协程对应的函数调用栈的内存空间互不干扰;
将所述函数调用栈的各结构体的内容,拷贝到所述独立内存空间中的函数调用栈中,其中,拷贝的各结构体的内容包括:函数执行信息的结构体,函数变量信息的结构体,及函数调用信息的结构体的内容;
对所述函数调用栈进行协程执行前的预处理;
将虚拟机的执行状态指向所述函数调用栈,以执行所述协程。
2.根据权利要求1所述的协程实现方法,其特征在于,所述函数调用栈包括:函数执行信息的结构体,函数变量信息的结构体,及函数调用信息的结构体;
所述根据协程对应函数的脚本语言字节码,确定协程对应的函数调用栈所需的目标内存空间包括:
根据协程对应函数的脚本语言字节码,计算所述函数调用栈的函数变量信息的结构体,及函数调用信息的结构体所需的内存空间;
根据所述函数调用栈的函数执行信息的结构体,预设定的所需内存空间,及所确定的函数变量信息的结构体,和函数调用信息的结构体所需的内存空间,确定所述函数调用栈所需的目标内存空间。
3.根据权利要求2所述的协程实现方法,其特征在于,所述函数执行信息的结构体包括:协程对应函数所调用的函数信息;所述函数调用栈通过关联指针指向上一次调用的函数调用栈的函数执行信息。
4.根据权利要求2所述的协程实现方法,其特征在于,所述对所述函数调用栈进行协程执行前的预处理包括:
将所述函数调用栈的函数执行信息的结构体进行初始化;
初始化脚本语言字节码缓存;
初始化This指针;
更新协程信息。
5.根据权利要求1-4任一项所述的协程实现方法,其特征在于,所述将虚拟机的执行状态指向所述函数调用栈,以执行所述协程包括:
确定函数位置指针当前指向的函数调用栈;其中,所述函数位置指针在各个函数调用栈中,全局维护虚拟机当前执行的函数调用栈,并指向该函数调用栈;
将虚拟机的执行状态,指向所述函数位置指针所指向的函数调用栈,以执行所述协程。
6.根据权利要求1所述的协程实现方法,其特征在于,所述方法还包括:
在执行协程时,创建当前执行状态的存档,所述存档记录有所述协程的执行入口;
在需切换协程时,根据历史记录的存档,确定需切换至的协程的执行入口,返回所确定的执行入口,以切换到需切换至的协程进行执行。
7.根据权利要求6所述的协程实现方法,其特征在于,所述创建当前执行状态的存档包括:
在执行协程时,若需要调用网络请求接口,则调用协程切换接口,将协程的函数调用栈的信息保存成一个上下文结构,并将所述上下文结构和网络请求映射起来,以形成所述存档;
相应的,所述返回所确定的执行入口,以切换到需切换至的协程进行执行包括:
返回到所述协程执行前所保存的存档对应的执行入口。
8.根据权利要求1所述的协程实现方法,其特征在于,所述脚本语言为超文本预处理器PHP语言;所述脚本语言的开发环境底层为Zend底层;所述脚本语言采用的编程语言为C语言。
9.一种协程实现装置,其特征在于,包括:
目标内存空间确定模块,用于根据协程对应函数的脚本语言字节码,确定协程对应的函数调用栈所需的目标内存空间;其中,一个协程对应一个函数调用栈;
空间分配模块,用于为所述函数调用栈分配与所述目标内存空间相应的独立内存空间;其中,各协程对应的函数调用栈的内存空间互不干扰;
内容填充模块,用于将所述函数调用栈的各结构体的内容,拷贝到所述独立内存空间中的函数调用栈中,其中,拷贝的各结构体的内容包括:函数执行信息的结构体,函数变量信息的结构体,及函数调用信息的结构体的内容;
预处理模块,用于对所述函数调用栈进行协程执行前的预处理;
执行模块,用于将虚拟机的执行状态指向所述函数调用栈,以执行所述协程。
10.根据权利要求9所述的协程实现装置,其特征在于,所述函数调用栈包括:函数执行信息的结构体,函数变量信息的结构体,及函数调用信息的结构体;
所述函数执行信息的结构体包括:协程对应函数所调用的函数信息;所述函数调用栈通过关联指针指向上一次调用的函数调用栈的函数执行信息。
11.根据权利要求9所述的协程实现装置,其特征在于,还包括:
存档创建模块,用于在执行协程时,创建当前执行状态的存档,所述存档记录有所述协程的执行入口;
协程切换执行模块,用于在需切换协程时,根据历史记录的存档,确定需切换至的协程的执行入口,返回所确定的执行入口,以切换到需切换至的协程进行执行。
12.一种处理设备,其特征在于,包括处理器和存储器;
所述存储器用于存储软件模块;
所述处理器用于执行所述软件模块,以实现如权利要求1-8任一项所述的协程实现方法。
13.一种计算机可读存储介质,其特征在于,所述计算机可读存储介质中存储有软件模块,所述软件模块用于在被处理器执行时,实现如权利要求1-8任一项所述的协程实现方法。
Priority Applications (1)
Application Number | Priority Date | Filing Date | Title |
---|---|---|---|
CN201610938968.8A CN107992344B (zh) | 2016-10-25 | 2016-10-25 | 一种协程实现方法及装置 |
Applications Claiming Priority (1)
Application Number | Priority Date | Filing Date | Title |
---|---|---|---|
CN201610938968.8A CN107992344B (zh) | 2016-10-25 | 2016-10-25 | 一种协程实现方法及装置 |
Publications (2)
Publication Number | Publication Date |
---|---|
CN107992344A CN107992344A (zh) | 2018-05-04 |
CN107992344B true CN107992344B (zh) | 2021-03-02 |
Family
ID=62028528
Family Applications (1)
Application Number | Title | Priority Date | Filing Date |
---|---|---|---|
CN201610938968.8A Active CN107992344B (zh) | 2016-10-25 | 2016-10-25 | 一种协程实现方法及装置 |
Country Status (1)
Country | Link |
---|---|
CN (1) | CN107992344B (zh) |
Families Citing this family (12)
Publication number | Priority date | Publication date | Assignee | Title |
---|---|---|---|---|
CN108647087B (zh) * | 2018-05-17 | 2022-05-17 | 腾讯科技(深圳)有限公司 | 实现php内核可重入的方法、装置、服务器和存储介质 |
CN109460255B (zh) * | 2018-11-13 | 2022-12-02 | 北京奇虎科技有限公司 | 内存地址的查询方法及装置 |
CN110247984B (zh) * | 2019-06-27 | 2022-02-22 | 腾讯科技(深圳)有限公司 | 业务处理方法、装置及存储介质 |
CN110879742B (zh) * | 2019-10-15 | 2023-08-11 | 平安科技(深圳)有限公司 | 虚拟机异步创建内部快照方法、装置及存储介质 |
CN112905267B (zh) * | 2019-12-03 | 2024-05-10 | 阿里巴巴集团控股有限公司 | 虚拟机接入协程库的方法、装置及设备 |
CN112346835B (zh) * | 2020-10-22 | 2022-12-09 | 上海瀚之友信息技术服务有限公司 | 一种基于协程的调度处理方法及系统 |
CN112363779A (zh) * | 2020-11-25 | 2021-02-12 | 王志平 | 一种动态链接程序的安全控制方法 |
CN113608843B (zh) * | 2021-07-08 | 2023-08-25 | 广东开放大学(广东理工职业学院) | 协程实现方法和系统 |
CN114064011A (zh) * | 2021-11-25 | 2022-02-18 | 北京字跳网络技术有限公司 | 确定进程性能的方法、装置、存储介质及电子设备 |
CN115113922A (zh) * | 2022-05-31 | 2022-09-27 | 青岛海尔科技有限公司 | 无栈协程的实现方法、装置、设备及存储介质 |
CN117270831B (zh) * | 2023-11-17 | 2024-02-23 | 天津华来科技股份有限公司 | 一种协议类同步与协程调用兼容实现方法 |
CN117850994A (zh) * | 2023-12-11 | 2024-04-09 | 天翼云科技有限公司 | 一种基于异步事件回调的协程调度模型与方法 |
Citations (3)
Publication number | Priority date | Publication date | Assignee | Title |
---|---|---|---|---|
CN103136047A (zh) * | 2011-11-30 | 2013-06-05 | 大唐联诚信息系统技术有限公司 | 一种多线程管理方法及架构 |
CN103955362A (zh) * | 2014-04-03 | 2014-07-30 | 广东工业大学 | 一种基于Xen的操作系统内核监控方法 |
CN105760237A (zh) * | 2016-02-05 | 2016-07-13 | 南京贝伦思网络科技股份有限公司 | 一种基于协程机制的通讯方法 |
Family Cites Families (1)
Publication number | Priority date | Publication date | Assignee | Title |
---|---|---|---|---|
US20120047495A1 (en) * | 2010-08-18 | 2012-02-23 | Microsoft Corporation | Execution environment support for reactive programming |
-
2016
- 2016-10-25 CN CN201610938968.8A patent/CN107992344B/zh active Active
Patent Citations (3)
Publication number | Priority date | Publication date | Assignee | Title |
---|---|---|---|---|
CN103136047A (zh) * | 2011-11-30 | 2013-06-05 | 大唐联诚信息系统技术有限公司 | 一种多线程管理方法及架构 |
CN103955362A (zh) * | 2014-04-03 | 2014-07-30 | 广东工业大学 | 一种基于Xen的操作系统内核监控方法 |
CN105760237A (zh) * | 2016-02-05 | 2016-07-13 | 南京贝伦思网络科技股份有限公司 | 一种基于协程机制的通讯方法 |
Non-Patent Citations (1)
Title |
---|
一种低成本的C语言协程实现;李中跃;《辽宁省交通高等专科学校学报》;20120815;第14卷(第4期);第23-25页 * |
Also Published As
Publication number | Publication date |
---|---|
CN107992344A (zh) | 2018-05-04 |
Similar Documents
Publication | Publication Date | Title |
---|---|---|
CN107992344B (zh) | 一种协程实现方法及装置 | |
KR101366402B1 (ko) | 가상 실행 시스템 및 가상 실행 시스템의 성능 향상 방법 | |
US8756591B2 (en) | Generating compiled code that indicates register liveness | |
KR101963912B1 (ko) | 라이브러리 운영체제들과의 애플리케이션 호환성을 가능하게 하는 기법 | |
CN107943485B (zh) | 一种补丁编译平台及补丁编译方法 | |
US8214812B2 (en) | Method of interpreting method bytecode and system operated by the same | |
WO2013192104A2 (en) | Optimized execution of dynamic languages | |
JP4873423B2 (ja) | 仮想化プログラム、シミュレーション装置、仮想化方法 | |
CN112219196B (zh) | 表示用于无暂停垃圾收集的激活帧的方法和装置 | |
Stadler et al. | Efficient coroutines for the Java platform | |
JP2006323844A (ja) | ジャバ仮想マシンでバイトコードの実行時間を短縮するシステム及び方法 | |
EP3719645B1 (en) | Extension application mechanisms through intra-process operation systems | |
US8769498B2 (en) | Warning of register and storage area assignment errors | |
CN112130988B (zh) | 一种基于优先级分区的任务加速优化方法及装置 | |
CN116107728B (zh) | 一种任务执行方法、装置、存储介质及电子设备 | |
KR20040071831A (ko) | 자바 프로그램에서 클래스 로딩 과정을 단축시키는 시스템및 방법 | |
US20170262292A1 (en) | Method of operating embedded system and control chip thereof | |
US11573777B2 (en) | Method and apparatus for enabling autonomous acceleration of dataflow AI applications | |
US20130166887A1 (en) | Data processing apparatus and data processing method | |
JP2008250838A (ja) | ソフトウェア生成装置、方法、およびプログラム | |
RU2718235C1 (ru) | Архитектура операционной системы для обеспечения поддержки поколений микроядер | |
Kushsairy et al. | Embedded vision: Enhancing embedded platform for face detection system | |
JP6295914B2 (ja) | プログラマブルコントローラシステム、その支援装置、プログラマブルコントローラ | |
US9483303B2 (en) | Differential stack-based symmetric co-routines | |
Antoy et al. | A target implementation for high-performance functional programs |
Legal Events
Date | Code | Title | Description |
---|---|---|---|
PB01 | Publication | ||
PB01 | Publication | ||
SE01 | Entry into force of request for substantive examination | ||
SE01 | Entry into force of request for substantive examination | ||
GR01 | Patent grant | ||
GR01 | Patent grant |