将程序执行从编译代码变换到解释代码的制作方法

文档序号:6533008阅读:208来源:国知局
将程序执行从编译代码变换到解释代码的制作方法
【专利摘要】可以从源自以动态语言(例如JavaScript)编写的程序的字节代码来生成经优化的编译的代码。优化可以基于一种或多种假设。在经优化的编译的代码的执行期间,所述优化所基于的所述一种或多种假设可以被检查有效性。响应于确定所述优化是基于无效的一种或多种假设,经优化的代码的执行可以停止,解释器所使用的变量的状态可以被还原并且程序的执行可以在解释器中使用源自程序的未经优化的字节代码来恢复。程序的继续可以在字节代码中的一个点处恢复,所述点类似于在经优化的编译的代码中的所述一种或多种假设被确定为假的那点。
【专利说明】将程序执行从编译代码变换到解释代码
[0001] 背景
[0002] 动态编程语言是一种在运行时执行静态语言通常在编译期间执行或根本不执行 的行为的语言。在运行时由动态语言执行的行为可以包括通过添加新代码、通过扩展对象 和定义或通过修改类型系统对程序的扩展。在动态编程语言中,在编译时不可用的信息可 以显著地改变程序如何执行。例如,在静态程序中,当在源代码中声明变量时,该声明指定 了所述变量的类型。变量X是整数或变量X是字符串等。如果变量X是整数,则将X加到 整数常量将执行算术加法。如果变量X是字符串,则将X加到是字符串的常量将执行常量 和X的串联。在动态编程语言中,变量的类型直到该程序执行时才知道,因此,需要额外的 代码路径来处理不同类型的操作,这会出现为程序执行增加开销。
[0003] 通常被认为是动态语言的语言示例包括但不局限于:ActionScript、BASIC、 BeanShell、ColdFusion、Common Lisp 和一些其它 Lisp 语言、Groovy、E 编程语言; JavaScript、VBScript、MATLAB、Lua、Objective-C、Perl、PHP、Powershell、Python、Ruby、 Smalltalk、Tel 以及 Dolphin Smalltalk。
[0004] 概述
[0005] 通过动态语言,可以做出关于不太可能静态确定的类型信息的假设。随后可以使 用这种不精确的信息来应用优化。可以提供通过优化假设的无效所触发的后退或跳出机 制。可以从源自以动态语言(例如但不局限于JavaScript)编写的程序的字节代码来生成 经优化的编译代码。优化可以基于关于数据的特性的一种或多种假设。在经优化的编译的 代码的执行期间,所述优化所基于的所述一种或多种假设可以被检查有效性。响应于确定 所述优化是基于无效的一种或多种假设,经优化的代码的执行可以停止,解释器所使用的 对应的变量的状态可以被还原并且程序的执行可以在解释器中使用源自程序的未经优化 的字节代码来恢复。程序的继续可以在字节代码中的一个点处恢复,所述点类似于在经优 化的编译的代码中的所述一种或多种假设被确定为假的那点。
[0006] 在经优化的编译的代码中的优化可以包括对变量类型操作的优化。可以将传递给 解释器的跳出信息量最小化。非活动的编译的代码不需要被复活用于解释器。
[0007] 可以在经优化的编译的代码中预先确定的点处设定一个或多个跳出点。在每个跳 出点处,可以捕捉未经优化的字节代码中的变量位置和对应的位置。当在执行期间到达跳 出点时,可以检查与该跳出点相关联的一种或多种假设的有效性,并且变量状态可以被还 原用于对应的解释器的变量。可以将变量的状态和在未经优化的字节代码中的对应位置发 送给解释器。解释器可以在未经优化的字节代码中的所接收的对应位置处恢复未经优化的 字节代码的执行。
[0008] 提供本概述是为了以简化的形式介绍将在以下【具体实施方式】中进一步描述的概 念选择。本概述并不旨在标识所要求保护主题的关键特征或必要特征,也不旨在用于限制 所要求保护主题的范围。

【专利附图】

【附图说明】
[0009] 在附图中:
[0010] 图la示出根据在此所述的主题的各方面的包括被配置为呈现来自所接收的文档 中的页的浏览器应用的系统100的示例;
[0011] 图lb示出根据在此所述的主题的各方面的包括被配置为从编译的代码变换到字 节代码的执行的运行时引擎的系统200的示例;
[0012] 图lc示出根据在此所述的主题的各方面的包括被配置为从编译的代码变换到字 节代码的执行的运行时引擎的系统300的示例;
[0013] 图Id示出根据在此所述的主题的各方面的程序源代码、对应的字节代码、编译的 代码和跳出表格的示例150 ;
[0014] 图le示出根据在此所述的主题的各方面的具有跳出信息的编译的代码的示例 170 ;
[0015] 图If示出根据在此所述的主题的各方面的程序源代码、以及具有跳出信息的编 译的代码的示例171 ;
[0016] 图lg示出根据在此所述的主题的各方面的程序源代码、对应的字节代码、以及具 有跳出信息的编译的代码的示例180 ;
[0017] 图2示出根据在此所述的主题的各方面的将程序执行从经优化的编译的代码变 换到解释的代码的方法250的示例;
[0018] 图3是根据本文公开的主题的各方面的计算环境的示例的框图。
[0019] 详细描述
[0020] 概览
[0021] 一些基于静态分析的传统的编译器优化对于动态语言是不可用的,因为进行优化 所需的信息在编译时不可用。然而,通过使用试探法或通过收集简档数据和/或使用所收 集的简档数据或通过以其他方式做出一种或多种假设来推导丢失的信息就可以执行某种 程度的优化。例如,假设脚本可由运行时引擎接收以作为网页或其它文档的一部分来执行。 运行时引擎可使用解释器来执行脚本。在一次或多次脚本的执行期间可由解释器来收集关 于该脚本的简档信息。简档信息可被用于确定脚本的哪些部分可通过使用编译器编译这些 部分并执行得到的机器代码,而非解释脚本的这些部分,来被更高效地执行。这样,使用解 释器可以执行脚本的一些部分,而使用编译器可以编译该脚本的其它部分,并且可以执行 所生成的编译的代码。脚本的经编译的部分(例如本机机器代码)可以被存储以供以后在 再次执行脚本的这些部分时使用。
[0022] 类似地,可以确定脚本的启动部分。可以对脚本的启动部分加标志,这样,在随后 的脚本运行中,在处理非启动部分之前可以由运行时引擎处理该启动部分。
[0023] 根据在此所述的主题的各方面,可以执行包括诸如方法或函数或者方法或函数的 任意部分之类的任意代码块的经编译的字节代码。可以基于关于在运行时对程序可用的信 息的特性的一种或多种假设来优化编译的字节代码。所述假设可以基于简档信息、试探法 或任意其它适合的信息。经优化的编译的字节代码可以包括基于在所述经编译的字节代码 中所做的特定优化来预先确定的一个或多个跳出点。对于每个跳出点,可以捕捉一组变量, 该组变量保持有解释器在跳出点处恢复执行所需的值。在寄存器分配之后可以创建每个跳 出点的跳出表格。每个跳出点的跳出表格可以包括跳出点的每个变量的位置(例如堆栈位 置、寄存器等)。跳出表格还可以包括每个变量的状态(例如在所述变量已经通过类型专用 化或其它优化被优化为int32、双精度等的情况)。
[0024] 在后续经优化的编译的字节代码的执行期间,可以对关于在其上生成所述字节代 码的程序将要操作的数据的假设进行测试。响应于确定在其中做出所述优化的一种或多 种假设是不正确的,执行可以"跳出"到解释器。就是说,可以停止经编译的代码的执行,并 且解释器可以执行与在跳出点处开始的经优化的编译的字节代码所对应的未经优化的字 节代码,所述跳出点对应于在经优化的编译的代码中的在其处确定所述一种或多种假设为 假的点。当跳出发生时,解释器所需的变量的状态可以通过检查跳出点的跳出表格来被重 新物化(rematerialized)。跳出点的跳出表格可以为变量提供一个值(对于常量)或位 置。跳出表格可以提供解释器在该跳出点恢复执行所需的每个变量的状态(对于类型专用 化)。在重新物化了解释器继续执行所需的变量的状态之后,解释器可以在跳出位置处恢复 控制以承载当前正在执行的函数的执行。
[0025] 根据在此所述的主题的一些方面,可以接收以动态语言编码的源代码以供执行。 源代码可以是任意代码块,例如方法或函数或者方法或函数的任意部分。源代码可被解析 以生成经解析的源代码。经解析的源代码被转换成字节代码。可以使用解释器来一次或多 次解释所述字节代码。可以生成关于字节代码的使用模式的简档信息。可以存储所述简档 信息。简档信息可被分析以确定与字节代码接收到的部分相关联的情况。该字节代码部分 可被即时(JIT)编译成经编译的字节代码部分,作为所确定的情况的结果。可存储经编译 的字节代码部分。字节代码部分可稍后在解释器处所接收的字节代码中再次被接收。与所 接收到的字节代码部分相对应的经编译的字节代码部分可被定位在存储中。可对位于存储 中的经编译的字节代码部分执行至少一个情况检查。如果所述至少一个情况检查通过,则 执行经编译的字节代码部分而非解释所接收到的字节代码部分。经编译的字节代码部分可 以包括基于假设的优化。所述假设可以基于简档数据、试探法或所提供的其它信息。当执 行经优化的代码时,可以执行情况检查。响应于确定所述优化所基于的假设是不正确的,经 编译的代码的执行可以结束。代码的执行可以在字节代码中的一个位置处恢复,所述位置 类似于在所述假设被确定为假的那点。
[0026] 在系统实现的一个示例中,可以提供运行时引擎。运行时引擎可以包括下述项的 全部或一些:解析器、字节代码生成器、执行控制器、解释器、JIT编译器、简档生成器以及 跳出引擎。解析器可以接收用动态语言编码的源代码并可以解析该源代码来生成经解析的 源代码。字节码生成器可以将经解析的源代码转换成字节代码。解释器可以被配置为当由 执行控制器启用时解释所述字节代码一次或多次。JIT编译器可被配置成当由执行控制器 启用时,编译字节代码。简档生成器可以从字节代码或从源代码中生成简档信息并可以存 储所述简档信息。执行控制器可以启用解释器或JIT编译器来基于简档信息执行它们各自 的功能。
[0027] 随后可以在经编译的代码中做出优化。可以将跳出点插入在经编译的代码中预先 确定的点处。可以基于特定优化的特性来预先确定跳出点。对于每个跳出点,可以捕捉一 组变量,该组变量保持有使得解释器在程序中的该点处恢复执行的值。可以存储对应于预 先确定的跳出点的变量的位置。在后续程序执行中,如果优化所基于的推断证明是不正确 的,可以提供后退或跳出机制。可以通过检查与假设相关联的情况来确定推断是不正确的。 根据在此所述的主题的各方面,机器代码执行器可以检查相关联的情况。响应于确定所述 推断是不正确的(例如通过机器代码执行器检查情况),根据在此所述的主题的各方面,经 编译的代码的执行可以停止,解释器所需的变量可以被重置为在预先确定的跳出点处所保 存的值并且可以在解释器处恢复执行。解释器可以在与不正确的假设相关联的跳出点处恢 复执行。
[0028] 根据在此所述的主题的各方面,跳出引擎可以通过将与机器代码相关联的变量的 状态转换成解释器所需的状态来还原相关联的活动的变量的状态。可以在编译时间(例如 由JIT编译器)来确定跳出点。在存在依赖于做出的假设的路径的任何地方出现跳出点。 每个跳出点可以具有与其相关联的表格,该表格包括关于为了解释器正确执行必须被复活 的该组解释器变量的信息,如何执行转换以将变量值从与机器代码相关联的值转换成与解 释器相关联的值的描述以及在字节代码中在其处恢复解释的位置。
[0029] 经编译的代码执行中的不再被需要因而非活动的变量可能需要为了解释器而被 复活。就是说,一个或多个变量的活跃度可能需要被延长至跳出点以使得该变量所持有的 信息对于解释器可用。可以执行优化以最小化对所需的寄存器的数目的影响。例如,如果 已知变量值在特定跳出点处为常量值,该常量可以被重新排序以便所述变量在该跳出点处 不再需要是可用的。类似地,如果已知变量在特定跳出点处具有与另一变量相同的值,则仅 使得一个包含该值的变量在该跳出点处对于解释器可用。
[0030] 将程序执行从经编译的代码变换为经解释的代码
[0031] 图1示出根据在此所述的主题的一些方面的web浏览器环境100。如在图la中所 示,环境100可以包括下述一个或多个:计算设备102、服务器104、网络106以及浏览器应 用108。Web浏览环境100可以包括本领域中已知的其它组件。
[0032] 计算设备102可以是任何类型的固定或移动计算设备,包括桌面计算机(例如,个 人计算机等)、移动计算机或计算设备(例如,Palm?设备、RM Blackberry?设备、个人 数字助理(PDA)、膝上型计算机、笔记本计算机、平板计算机(例如,Apple iPad?)、上网本 等等)、移动电话(例如,蜂窝电话、智能电话,诸如Apple iPhone、G〇〇gle Android?手机、 Microsoft Windows?手机等)或其它类型的移动设备。服务器104可在包括一个或多个 服务器的一个或多个计算机系统中实现,其可以是在此描述的任何类型的计算设备或能够 实现在此描述的相应功能的以其它方式知晓的计算设备。
[0033] 计算设备102和服务器104可通过网络106来通信地耦合。网络106可包括一 个或多个通信链路和/或通信网络,诸如PAN(个域网)、LAN(局域网)、WAN(广域网)、或 网络的组合,诸如因特网。可使用各种链路来将计算设备102和服务器通信地耦合到网络 106,该各种链路包括有线和/或无线链路,如IEEE 802. 11无线局域网(WLAN)无线链路、 全球微波互联接入(Wi-MAX)链路、蜂窝网络链路、无线个人区域网络(PAN)链路(例如, Bluetooth?链路)、以太网链路、USB链路等等。
[0034] 浏览器应用108可以是可在计算设备102上执行的程序。浏览器应用108可 使得网络信息资源能被检索、呈现和遍历。可使用网络地址(诸如统一资源标识符 (URI))来通过浏览器应用108检索信息资源或对象。信息资源的示例包括网页、图像、 视频,以及其它形式的内容。出现在信息资源中的超链接使得用户能够容易地将他们 的浏览器导航到相关的资源。浏览器应用108的示例包括由华盛顿州雷蒙德市的微软 公司开发的Internet Explorer?、由加利福尼亚州芒廷维市的Mozilia公司开发的 MozillaFirefox?、由加利福尼亚州库珀蒂诺市的Apple公司开发的Safari?,以及由加利 福尼亚州芒廷维尤市的Chrome公司开发的Google?。
[0035] 浏览器应用108可以通过网络106从服务器104检索文档112。文档112可以是包 括标记语言的代码的web文档,标记语言诸如超文本标记语言(HTML)、动态HTML (DHTML)、 可扩展HTML (XHTML)、可扩展标记语言(XML)等。文档112可以包括D0M (文档对象模型) 对象114和一个或多个脚本116。D0M对象114可以包括根据D0M规范在文档112中所表 示的一个或多个对象,该D0M规范是用于表示对象并与对象进行交互的跨平台且独立于语 言的规范。D0M对象114可包括被直接包括在文档112中的对象、和/或由文档112引用 的并分开地从服务器104或其它服务器检索的对象。脚本116包括根据动态语言(例如, JavaScript、VBScript、AJAX、Python、Perl等)来格式化的代码,该格式化的代码使得能够 对D0M对象114做出改变,包括基于诸如用户输入、环境情况(例如,一天中的时间或其它 变量)等因素的改变。脚本116的代码可在进行中访问和修改D0M对象114的对象,而无 需返回到服务器104。
[0036] 浏览器应用108可以接收(例如加载)文档112。浏览器应用108可包括浏览器 引擎(例如,布局引擎或呈现引擎),该浏览器引擎格式化文档112的信息并显示经格式化 的信息。例如,如图la显示的,浏览器应用108可基于由计算设备102的显示器110显示 的文档112来生成页面118。浏览器应用108可被配置成执行一个或多个脚本116,该一个 或多个脚本116被嵌入在文档112中或与文档112分开但与文档112相关联。
[0037] 图lb示出根据在此所述的主题的一些方面的系统200的框图。系统200可包括 一个或多个计算机或计算设备,例如包括诸如处理器143等之类的一个或多个处理器、存 储器145、执行控制器309、解释器311、诸如JIT(即时)编译器313、存储315、机器代码执 行器317和跳出引擎337之类的编译器的计算设备102。执行控制器309、解释器311、诸如 JIT(即时)编译器313的编译器、存储315、机器代码执行器317和跳出引擎337可被实现 为一个或多个程序模块,当所述程序模块被加载到存储器145中时使得所述一个或多个处 理器143等分别执行归因于执行控制器309、解释器311、诸如JIT (即时)编译器313、存储 315、机器代码执行器317和跳出引擎337的动作。
[0038] 执行控制器309、解释器311和/或JIT编译器313可以接收从源代码生成的字 节代码。源代码可以是任意以动态语言编写的源代码,例如但不局限于动态脚本语言(诸 如但不限于JavaScript、VBScript、Python等等。可以解析源代码并从经解析的源代码中 生成字节代码。基于字节码325和简档、试探法或其它信息,执行控制器309可启用解释器 311和JIT编译器313之一来对字节代码325进行操作。解释器311可被配置成,当由从执 行控制器309接收到的解释器控制信号启用时解释字节代码325。JIT编译器313可被配 置成,当由从执行控制器309接收到的编译器控制信号启用时编译字节代码325。
[0039] 当由解释器控制信号启用解释器311时,解释器311可以解释并执行未经优化的 字节代码325。解释器311可以被实现为JavaScript解释器、VBScript解释器、Python解 释器或用于在此其它地方提到的或以其它方式所知的另一动态语言或动态脚本语言的解 释器。通过该方式,源代码可至少部分地由解释器311的操作来执行。类似地,响应于接收 到启用编译器控制信号,JIT编译器313可以编译字节代码325。JIT编译器313可被实现 为JavaScript编译器、VBScript编译器、Python编译器或用于在此其它地方提到的或以其 它方式所知的另一动态语言或动态脚本语言的编译器。JIT编译器313被称为"即时"编译 器,这是因为由于需要经编译的字节代码(即,要被紧急执行的),特定的字节代码部分可 由JIT编译器313编译,而非在执行之前预先编译完整的字节代码325。JIT编译器313可 以生成具有机器可执行代码或指令形式的经编译的字节代码333。
[0040] JIT编译器313可以基于如上所述的假设执行代码优化。JIT编译器313可以在它 生成的经编译的字节代码中插入一个或多个预先确定的跳出点。对于每个跳出点,诸如跳 出表格303等之类的跳出表格可以被创建,在其中,可以记录变量的位置、在字节代码325 中与跳出点的位置相对应的位置以及其它信息。跳出表格303等可以描述在堆栈上或寄存 器中哪里可以找到变量。JIT编译器313可以生成一个或多个跳出表格并可以将它们与经 优化的编译的字节代码(例如作为机器代码)一起保存。可以通过编码跳出表格中的信息 来避免对变量的生存期的非必要的延长来优化跳出表格。例如,如果已知变量X的值在跳 出时间是常量10, X = 10可以被编码在跳出表格中,这样,值10就不需要在存储器或寄存 器中被复活。类似地,当超过一个变量在跳出点处具有相同的值(例如X = y),如果该信息 被编码在跳出表格中(例如跳出表格中的相同位置可以被用于X和y),则对于具有相同值 的所有变量来说,该相同的位置可被用在跳出表格中。
[0041] 这些技术可以使得寄存器分配更加有效。经优化的编译的字节代码可以被作为用 于在由系统200后续执行程序期间访问的经编译的字节代码333来存储在存储315中。
[0042] 当执行经优化的编译的字节代码时,可由机器代码执行器317(它可以是诸如处 理器143等的一个或多个处理器)接收经优化的编译的字节代码333。执行经编译的字节 代码可以与堆栈335上的编译器框架341相关联。在每个跳出点处可以确定所述优化所基 于的底层的一种或多种假设是有效还是无效的。响应于确定所述假设是有效的,经优化的 编译的代码可以继续执行。响应于确定所述假设是无效的,经优化的编译的代码的执行可 以被停止。可以将该跳出点的跳出表格传递给跳出引擎337。跳出引擎337可以还原解释 器所需的变量的状态(例如值)。跳出引擎可以为堆栈335创建新的框架(例如解释器框 架339)。如果解释器所需的变量已变成非活动的,则跳出引擎337可以通过将变量的状态 从非活动改变到活动来复活该变量。跳出引擎337可以实例化解释器311的一个实例,向 解释器传递在未经优化的字节代码中与在经优化的编译的代码中的跳出点相对应的位置 以及包括所有被还原的活动变量的值的新创建的解释器框架。因此这样,从其生成字节代 码325的源代码可以由JIT编译器313和机器代码执行器317的操作来部分执行并由解释 器311来部分执行。
[0043] 图lc示出根据在此所述的主题的各方面的系统300的另一示例。系统300可以 包括诸如处理器142等的一个或多个处理器、存储器144以及包括下述一个或多个项的运 行时引擎:引擎接口 302、解析器304、字节代码生成器306、执行控制器308、解释器310、诸 如但不限于JIT(即时)编译器312之类的编译器、存储314、机器代码执行器316、跳出引 擎336以及脚本库318。
[0044] 如在图lc中所示的,引擎接口 302可接收脚本源代码208。引擎接口 302可以是 在场的或不在场的。解析器304可以被配置作为到运行时引擎的接口,而不是使得引擎接 口 302在场。当在场时,引擎接口 302是提供用于将主机与图lc的运行时引擎对接的一个 或多个方法的通信接口。根据在此所述的主题的一些方面,可以根据由华盛顿州雷蒙德市 的微软公司所开发的IActiveScript来实现引擎接口 302。引擎接口 302可以为解析器304 提供源代码208。
[0045] 解析器304可以接收并解析源代码208。解析器304可对源代码208执行令牌生 成或词法分析,使得源代码208被格式化成符号或令牌。解析器304可对令牌执行差错校 验以确定是否形成可允许的表达式、句法差错不存在等。解析器304可以将经解析的源代 码作为经解析的源代码(未示出)输出。经解析的源代码可具有任何合适的形式,包括由 解析器304生成为AST (抽象句法树)代码,如本领域的技术人员知晓的,该AST代码包括 源代码208的抽象句法结构的树表示。
[0046] 字节代码生成器306可以接收经解析的源代码。字节代码生成器306可被配置成 将经解析的源代码转换成字节代码,其包括被配置成用于解释器的高效执行以及用于进一 步编译成机器代码的指令集。所生成的字节代码可以将经解析的源代码表示为数字代码 和相应的可选参数。字节代码生成器306可以输出经生成的字节代码(未示出)。字节代 码可具有任何合适的形式,包括由字节代码生成器306生成的如本领域的技术人员知晓的 P-代码(便携式代码)形式。
[0047] 执行控制器308、解释器310和JIT编译器312每个都可以接收所生成的字节代 码。解释器310可以包括简档生成器204。简档生成器204可被配置成分析所生成的字节 代码来收集有关源代码208的统计数据以及进一步的信息。简档生成器204可生成简档信 息320,其可包括所收集的信息并可被存储在存储314中。
[0048] 执行控制器308可以访问简档信息320,并且可以被通信地耦合到解释器310和 JIT编译器312。基于所生成的字节代码和简档信息320,执行控制器308可启用解释器310 和JIT编译器312之一来对所生成的字节代码进行操作。解释器310可被配置成,当由从 执行控制器308接收到的解释器控制信号启用时解释所生成的字节代码。JIT编译器312 可被配置成,当由从执行控制器308接收到的编译器控制信号启用时编译所生成的字节代 码。例如,在源代码208的第一次执行期间,简档信息320可能还不存在。在这种情况下, 执行控制器308可启用解释器310来解释所生成的字节代码并生成简档信息320。在源代 码208随后的执行期间(例如,在源代码208的相同的第一次执行期间的稍后,和/或在源 代码208的接下来的执行期间),根据简档信息320,执行控制器308可启用解释器310来 解释源代码208的各部分,并可启用JIT编译器312来编译源代码208的其它各部分。
[0049] 当由解释器控制信号启用解释器310时,解释器310可以解释并执行所生成的字 节代码。解释器310可被实现为JavaScript解释器、VBScript解释器、Python解释器或用 于在此其它地方提到的或以其它方式所知的另一动态语言的解释器。通过该方式,源代码 208可至少部分地由解释器310的操作来执行。
[0050] 当JIT编译器312由编译器控制信号启用时,JIT编译器312可编译所生成的字 节代码。JIT编译器312可被实现为JavaScript编译器、VBScript编译器、Python编译器 或用于在此其它地方提到的或以其它方式所知的另一动态语言的编译器。JIT编译器312 被称为"即时"编译器,这是因为由于需要经编译的字节代码(即,要被紧急执行的),特定 的字节代码部分可由JIT编译器312编译,而非在执行之前预先编译完整的字节代码。JIT 编译器312可以生成具有机器可执行代码或指令形式的经编译的字节代码332。
[0051] JIT编译器312可以基于如上所述的假设执行代码优化。JIT编译器312可以在 它生成的经编译的字节代码中插入一个或多个预先确定的跳出点。对于每个跳出点,诸如 跳出表格303等之类的跳出表格可以被创建,在其中,可以记录变量的状态、在所生成的字 节代码中与跳出点的位置相对应的位置。跳出表格可以描述在堆栈上或机器代码的寄存器 中哪里可以找到变量。JIT编译器312可以生成表格并将它们与经优化的编译的字节代码 332(例如机器代码)一起保存。经优化的编译的字节代码332可以被作为用于在由系统 300后续执行程序期间访问的经编译的字节代码332来存储在存储314中。
[0052] 当执行经优化的编译的字节代码时,可由机器代码执行器316(它可以是诸如处 理器142等的一个或多个处理器)接收经优化的编译的字节代码332。在每个跳出点处可 以检查所述优化所基于的底层的一种或多种假设是有效还是无效的。响应于确定所述假设 是有效的,经优化的编译的字节代码332可以继续执行。响应于确定所述假设是无效的,经 优化的编译的代码的执行可以被停止。可以将该跳出点的跳出表格传递给跳出引擎336。 跳出引擎336可以还原解释器所需的变量的状态(例如值)。如果解释器所需的变量已变 成非活动的,跳出引擎336可以通过将变量的状态从非活动改变到活动来复活该变量。跳 出引擎336可以实例化解释器310的实例,向解释器传递在未经优化的字节代码中与在经 优化的编译的代码中的跳出点相对应的位置、变量和它们的位置。因此这样,从其生成字节 代码的源代码可以由JIT编译器312和机器代码执行器316的操作来部分执行并由解释器 310来部分执行。
[0053] 跳出的使用可以允许多次优化。在许多动态编程语言中的变量可以是日期、字符 串、数组、整数等等。在一些动态语言中,为变量创建对象,并且存储在寄存器中并随后存 储在表格中的位置包括指向该对象的指针。对象自身可以存储对象的描述和对象的数据。 这样,如果变量a是字符串,可以为该字符串创建对象,指向该对象的指针可以被存储,且 对象自身可以标识变量a为字符串并可以指定该字符串自身(例如"你好世界"("Hello World"))。一种用于在当基于简档数据假设变量为整数的情况下的方案的优化是将整数自 身存储在变量中以取代指向为该整数创建的对象的指针或表示并描述该整数对象的经编 码的值。一种直接对整数对象进行编码的方案是使用单词的位之一来存储标记该值为整数 的指示符。这样,在32位处理器的情况下,32位的一个位可以指示其它31位的内容表示整 数值或可指示其它31位的内容不表示整数值。
[0054] 图Id示出以JavaScript编写的源代码152的示例150,在其中,函数foo执行两 个变量a和b的加法并返回加法操作的结果。在示例150中显示的字节代码154是从该示 例的源代码152中生成的字节代码。在行#1,将第一自变量(a)加载到解释器临时变量tl。 在行#2,将第二自变量(b)加载到解释器临时变量t2。在行#3,临时变量tl的内容和临时 变量t2的内容被相加并放置到解释器临时变量t0中。在行#4,返回临时变量t0的内容。 临时变量tl、临时变量t2和临时变量t0的内容在JavaScript中可以无论怎样都是合法 的,包括浮点数、整数、字符串等等。
[0055] 在图Id中,所生成的代码156示出表示编译字节代码154并基于简档数据对其进 行整数加法优化的结果的伪代码。当字节代码154被编译时,并不知道变量a和b的类型 是什么。变量a和/或变量b可以是字符串、日期、整数等等。如果变量a和b是日期,将 执行一种加法操作,如果变量a和变量b是字符串,串联操作将准备就绪,并且如果变量a 和变量b是浮点数,则将调用浮点加法操作。如果期望变量a和变量b很可能是整数(例 如通过运行解释器多次并发现变量a和变量b总是整数)是合理的,那么编译的代码的乐 观优化可以执行整数加法,如由所生成的代码156所示,该乐观优化针对整数加法进行了 优化。由于在当变量a和变量b是日期、字符串或非整数数字的情况下通过不提供代码路 径减少了执行的代码量,所述代码被优化了。
[0056] 在所生成的代码156的行#1,将第一自变量(a)加载到寄存器regl。在这点(跳 出点#1)处,检查regl的内容以查看regl的内容是否真的是整数。响应于regl的内容不 是整数,(行#2),所生成的代码的执行被停止,并且调用跳出引擎(在所生成的代码156的 行#3处执行跳出指令)。在解释器中在字节代码154的行#2处继续程序执行,因为字节代 码154的行#1已经被执行。tl的内容已经被放置在regl中。t2和t0还不是活动的,并 且不必被复活。发送给跳出引擎的表格的内容被示出在图Id的表格1的内容158中。表 格1的内容158描述了跳出点1的执行在字节代码154的行#2处恢复,变量tl的值被存 储在:regl中,而变量t2和t0当前并不是活的。这意味着变量t2和t0是不活动的且不需 要被复活。
[0057] 如果相反,regl的内容是整数,则所生成的代码156在所生成的代码156的行#4 处继续执行。在行#4处,自变量b被加载到寄存器reg2中。在所生成的代码156的行#5 处,检查reg2的内容以确定它是整数还是非整数。如果reg2的内容是非整数,在行#6执 行跳出指令。所生成的代码156的执行停止,且在解释器中在字节代码154的行#3处执行 恢复。变量a和b是活动的。存储在tl中的变量a的值驻留在regl,而存储在t2中的变 量b的值驻留在reg2。t0不是活的。该信息被放置在表格2(表格2160的内容)中。
[0058] 如果相反,reg2的内容是整数,则所生成的代码156在所生成的代码156的行#7 处继续执行。将1^81和^82的内容相加并放置在寄存器^83中。在行#7,^81和^82 相加的结果被放置在寄存器reg3中。在行#8,如果reg3溢出,则到达第三跳出点。在第 三跳出点,在行#9,跳出被定向到字节代码154的行#3以通过不丢失信息的方式来重做操 作。相关联的表格Table3162的内容与表格2是相同的。为了避免丢失信息,整数值可以 被转换成浮点数,并且在解释器中可以执行浮点加法。如果相反,reg3不溢出,所生成的代 码156在所生成的代码156的行#10处继续执行并返回reg3中的值。
[0059] 在上述示例中,JavaScript指针的一个位可以被设定为指示符值,该指示符值指 示了剩余的31位表示整数值。为了在整数上执行数学运算,可以从存储了指针的32位寄存 器中提取表示整数的31位并可以执行所述运算。随后可以在经解码的整数值上执行进一 步的数学运算。一旦数学运算的值或结果需要被存储或传递到当前编译范围之外的进程, 可以将其重新编码成JavaScript对象指针,将所述指示符位设定回指示符值。例如,根据 在此所述的主题的一些实施例,在所生成的代码156的行#10处返回reg3之前,可以撤消 整数类型的专用化并重新编码该值。(为了清楚起见,编码/解码步骤并没有包括在伪代码 示例中。)表格还可以捕捉tl是在regl中的信息。因为该信息是被解码的,它可以被重新 编码成JavaScript值,将指示符位重置为指示其它31位不是整数值。类似地,64位浮点值 可以被表示为对象,这样,对于在regl中的浮点数来说,可以做出regl的内容是浮点数的 检查。如果是,来自JavaScript数字的浮点数据被加载到浮点寄存器中并且最后可以创建 新的JavaScript数字,在该新的JavaScript数字中,在要返回给调用者的寄存器中放置结 果数字、放置指向JavaScript数字的指针。
[0060] 图le示出为图Id的相同的JavaScript源代码(源代码152)的浮点数的加法优 化的经编译的代码的示例170。源代码和字节代码154两者是相同的,例如170与例如150 相同,然而,仅仅为了示例170,假设期望变量是浮点数而不是整数是合理的。将理解的是, 第一跳出点和第一跳出点的对应的表格信息与针对整数加法优化的所生成代码156相同。
[0061] 在示例170的行#1处,变量可以被加载到寄存器regl中。在行#2处检查regl 的内容以确定regl的内容是否指向JavaScript数字。响应于确定regl的内容不是指向 JavaScript数字,可在行#3调用跳出引擎。存储在该跳出点(跳出点#1)的表格中的跳出 信息与先前示例150中的相同。如果regl的内容指向JavaScript数字,在行#4处,可以通 过使用regl访问来自JavaScript数字的浮点数据来从JavaScript数字中查明浮点值,并 将浮点数据加载到浮点寄存器floatRegl中。因为不再需要regl,编译器可以在行#5处重 用regl来加载变量b。在行#6处,可以检查regl以确定其内容是否指向JavaScript数字。 如果它没有,在行#7处可以调用跳出引擎。在跳出点#2,为了复活tl,可以从floatRegl 中查明变量a的值。
[0062] 跳出引擎可以确定变量a是浮点数字,并可创建JavaScript数字对象,并可放置 tl中的JavaScript数字的位置以允许解释器开始从字节代码154的行#3处执行,因为解 释器处理不是浮点值的JavaScript对象。在该点处,t2驻留在regl中,而t0不是活的。 如果相反,在行#6处,regl的内容确实指向JavaScript数字,可以通过使用regl访问来自 JavaScript数字的浮点数据来从JavaScript数字中查明浮点值,并在行#8将浮点数据加 载到浮点寄存器floatReg2中。在行#9,可以执行两个浮点数字的加法并可将结果存储在 fl〇atReg3中。在此不需要跳出,因为JavaScript将数字运算定义为正被双精度浮点运算 执行,因此,任何浮点溢出都将表现出按每JavaScript惯例的行为。因为不再需要regl,在 行#10处编译器可以重用regl以保持指向所构造的JavaScript数字对象的位置的指针, 所述JavaScript数字对象持有将两个浮点值相加的结果。在行#11,可将regl返回给调用 者。
[0063] 当第一函数(例如函数foo)调用第二函数(例如函数bar)时,可以应用另一种 被称为内联(in-lining)的优化。在这种情况下,函数bar的代码可以以顺序次序在函数 foo的代码内部被写出。如果在内联的函数内部出现跳出,则调用函数和被调用函数两者的 状态可都被还原,并且这两个函数可以运行。可以创建被调用函数的表格以及调用函数的 表格。
[0064] 当以诸如JavaScript之类的动态语言做出函数调用时,编译器不能确定在编译 时哪个函数正被调用。虽然脚本可以指示函数foo正被调用,在运行时,被称为foo的函数 可以改变。这样,就不能做出关于在编译时哪个函数正被调用的假设。内联在调用函数的 内部直接生成被调用函数的代码。当该代码被执行时,可以动态地做出经内联的函数是应 该实际被调用的函数的检查。根据在此所述的主题的各方面,如果正被调用的函数不是经 内联的函数,则可做出对跳出引擎的调用。在图If中,示例m,JavaScript函数barl72 以及JavaScript函数fool73被定义。经编译的代码在经编译的代码174中示出。
[0065] 编译器可以做出下述优化。如果bar被调用,贝U声明var c = a+b ;在函数fool73 中是非必要的,因为bar总是返回10。函数foo返回0,因为bar返回值10。但由于bar 可以改变,可做出一个检查来查看bar是否已经改变。如果bar已经改变,可以做出对跳出 引擎的调用。如果做出对跳出引擎的调用,解释器将需要变量c。为了使得c可用,将需要 a+b。a+b被存储在reg3中,因此,不能释放reg3以供重用直到跳出发生之后。这样,以其 它方式将变得非活动的变量可以被维持在活动状态。
[0066] 在图 lg 中的不例 180 中,JavaScript 函数 barl82 以及 JavaScript 函数 fool83 被定义。函数barl82具有两个自变量:变量a和函数func。脚本184调用具有a = 2和 func = foo的函数barl82。从脚本184生成的字节代码在字节代码185中被示出。
[0067] 在行#1处,函数barl85的字节代码将变量a的值(2)放置在tl中。在行#2处, 常量100被放置在t2中,在行#3处,函数foo被放置在t3中,而在行#4处,用自变量2 和100来调用函数foo。在行#5处,将用自变量2和100调用foo的结果与2相加并将结 果放置在被返回的t0中。函数foo的经编译的字节代码在图Id中被示为所生成的代码 156。将函数fool83内联到函数barl82的经编译的代码在图lg中被示为所生成的代码 186。在第一跳出点前,BarNativeCode(Bar本机代码)是堆栈的顶层框架。当在第一跳 出点处调用跳出引擎时,调用跳出引擎的新框架将被放置在堆栈的顶部。当跳出引擎创建 foo的存储的经解释的框架并开始在解释器上运行它时,顶部的4个框架将是foo经还原的 被解释的框架,下一个将是跳出引擎的框架,下一个是具有内联的foo和调用者框架的Bar NativeCode(本机代码)的框架。在经还原的foo完成正被解释之后,跳出引擎可以创建 bar的经还原的被解释的框架并可以开始在解释器上运行它。从上至下堆栈将出现:Bar经 还原的被解释的框架、跳出引擎的框架、具有内联的f〇〇和调用者框架的Bar NativeCode 的框架。最后,在经还原的bar完成解释之后,跳出引擎可以返回到bar本机代码,并且bar 本机代码可以返回到调用者。在这个点,堆栈的顶层框架将是调用者框架。
[0068] 内联代码188和经内联的代码189表示在所生成的代码186中来自已经被内联到 函数bar中的函数foo的代码。在函数foo已经被内联到函数bar中之后,函数foo可以 改变。到bar函数字节代码185的第一跳出检查foo是正确的函数。该函数被加载到reg3 中并检查reg3以查看函数是否是foo。如果是,经编译的代码的执行继续。如果不是,执 行在解释器中恢复。在第一跳出点处调用跳出引擎,并且执行在函数barl85的行#4处恢 复。这是一个简单的跳出,因为执行是在内联外部发生的,这样在还原tl、t2和t3之后,执 行可以在解释器中继续。如果该函数是f 〇〇,执行继续并且执行经内联的代码188。在经内 联的代码188中,如果regl的内容不是整数,则在第二跳出点处调用跳出引擎,并且执行在 foo (字节代码154)中的行#2处恢复。由于bar实际上正在被执行,到函数bar的行#5的 跳出可以被很好完成。在foo完成执行之后,foo的结果可以被放置在t4中。可以做出到 bar的行#5的跳出,tl在regl中,并且t4将包含从跳出到foo的解释器返回值。该信息 可以被编码到2个链接在一起的表格中,以便这两个跳出将一个接一个发生。在加法溢出 时,可以在内联代码189中执行类似的处理。将可以理解,如上所述,跳出在一行中出现一 次,而框架被每次复活一个框架。当返回给调用者时,调用者的框架被复活。
[0069] 在第一跳出点前,BarNativeCode是堆栈的顶层框架。当在第一跳出点处调用跳 出引擎时,调用跳出引擎的新框架将被放置在堆栈的顶部。当跳出引擎创建foo的存储的 经解释的框架并开始在解释器上运行它时,顶部的4个框架将是foo经还原的被解释的框 架,下一个将是跳出引擎的框架,下一个是具有内联的foo的Bar NativeCode的框架。在 经还原的f〇〇完成正被解释之后,跳出引擎可以创建bar的经还原的被解释的框架并可以 开始在解释器上运行它。从上至下堆栈将出现:Bar经还原的被解释的框架、跳出引擎的框 架、具有内联的foo和调用者框架的Bar NativeCode的框架。最后,在经还原bar完成解 释之后,跳出引擎可以返回到bar本机代码,并且bar本机代码可以返回到调用者。在这个 点,堆栈的顶层框架将是调用者框架。
[0070] 图2示出了可以将以动态语言编写的程序的执行从经编译的代码变换成经解释 的代码的方法250。方法250可以由诸如如上所述的系统100、系统200和/或系统300之 类的系统来实现。所描述的顺序是可选的。并不是所有的动作都要被采用。在252,可以由 计算设备的处理器接收字节代码。在254,可以做出关于程序可以在其上操作的数据的一种 或多种假设。在256,基于所述假设,可以基于所述一种或多种假设为所接收的字节代码的 一部分生成经优化的编译的代码。在预置的跳出点处可以捕捉变量值位置。还可以捕捉在 字节代码中的对应位置。在260,可以执行经优化的编译的代码。变量值可以被保存在变量 值位置中。在262,可以检查经编译的代码中的优化所基于的假设的有效性。在264,响应 于确定所述假设还是有效的,经编译的代码的执行可以继续。在266,响应于确定所述假设 是无效的,经编译的代码的执行可以在跳出点处停止。在268,来自所捕捉位置的变量值可 以被用于还原解释器变量值。在270,对在字节代码中的所指示的模拟位置处的字节代码的 解释可以开始。
[0071] 合适的计算环境的示例
[0072] 为了提供有关本文所公开主题的各方面的上下文,图3以及以下讨论旨在提供其 中可以实现本文所公开主题的各实施例的合适计算环境510的简要概括描述。尽管本文所 公开的主题是在诸如程序模块等由一个或多个计算机或其他计算设备执行的计算机可执 行指令的通用上下文中描述的,但本领域技术人员将认识到,本文所公开的主题的各部分 还能够结合其他程序模块和/或硬件和软件的组合来实现。通常,程序模块包括执行特定 任务或实现特定数据类型的例程、程序、对象、物理人为产物、数据结构等。通常,程序模块 的功能可在各个实施例中按需进行组合或分布。计算环境510只是合适的操作环境的一个 示例,并且不旨在对此处所公开的主题的使用范围或功能提出任何限制。
[0073] 参考图3,描述了计算机512形式的计算设备。计算机512可包括至少一个处理单 元514、系统存储器516和系统总线518。至少一个处理单元514可执行被存储在诸如但不 限于系统存储器516之类的存储器中的指令。处理单元514可以是各种可用处理器中的任 何一种。例如,处理单元514可以是GPU。这些指令可以是用于实现被描述为由上述一个 或多个组件或模块所执行的功能的指令或用于实现上述方法中的一个或多个的指令。也可 以使用双微处理器及其他多处理器体系结构作为处理单元514。计算机512可被用于支持 在显示屏上呈现图形的系统中。在另一示例中,计算设备的至少一部分可以用在包括图形 处理单元的系统中。系统存储器516可包括易失性存储器520和非易失性存储器522。非 易失性存储器522可包括只读存储器(ROM)、可编程ROM (PR0M)、电可编程ROM (EPR0M)或闪 存。易失性存储器520可包括可充当外高速缓冲存储器的随机存取存储器(RAM)。系统总 线518将包括系统存储器516的系统物理人为产物耦合到处理单元514。系统总线518可 以是几种类型的总线结构中的任何一种,包括存储器总线、存储控制器、外围总线、外总线 或局部总线,并且可以使用各种可用总线体系结构中的任一种。计算机512可包括处理单 元514可通过系统总线518访问的数据存储。数据存储可包括用于图形呈现的可执行指令、 3D模型、素材、材质等。
[0074] 计算机512通常包括各种计算机可读介质,诸如易失性和非易失性介质、可移动 和不可移动介质。计算机存储介质可以通过用于存储诸如计算机可读指令、数据结构、程 序模块或其它数据等信息的任何方法或技术来实现。计算机存储介质包括但不限于,RAM、 ROM、EEPR0M、闪存或其它存储器技术、CDR0M、数字多功能盘(DVD)或其它光盘存储、磁盒、 磁带、磁盘存储或其它磁存储设备、或可以用来储存所期望的信息并可由计算机512访问 的任何其他瞬态或非瞬态介质。
[0075] 将理解,图3描述了可充当用户与计算机资源之间的媒介的软件。该软件可以包 括可存储在盘存储524上的操作系统528,该操作系统可分配计算机512的资源。盘存储 524可以是通过诸如接口 526等不可移动存储器接口连接到系统总线518的硬盘驱动器。 系统应用程序530利用由操作系统528通过存储在系统存储器516或者存储在盘存储524 上的程序模块532和程序数据534对资源的管理。可以理解,计算机可用各种操作系统或 操作系统的组合来实现。
[0076] 用户可通过输入设备536向计算机512输入命令或信息。输入设备536包括但不 限于定点设备,诸如鼠标、跟踪球、指示笔、触摸垫、键盘、话筒等。这些及其他输入设备通过 系统总线518经由接口端口 538连接到处理单元514。接口端口 538可表示串行端口、并行 端口、通用串行总线(USB)等。输出设备540可与输入设备使用相同类型的端口。提供输 出适配器542以举例说明存在像监视器、扬声器、以及打印机的需要特定适配器的一些输 出设备540。输出适配器542包括但不限于,在输出设备540和系统总线518之间提供连接 的视频卡和声卡。其他设备和/或系统和/或设备,诸如远程计算机544,可提供输入和输 出两种能力。
[0077] 计算机512可以使用到诸如远程计算机544之类的一个或多个远程计算机的逻辑 连接来在联网环境中操作。远程计算机544可以是个人计算机、服务器、路由器、网络PC、对 等设备或其他常见的网络节点,并且通常包括许多或所有以上相对于计算机512所描述的 元件,但在图3中仅示出了存储器存储设备546。远程计算机544可经由通信连接550逻辑 地连接。网络接口 548涵盖诸如局域网(LAN)和广域网(WAN)这样的通信网络,但也可包 括其他网络。通信连接550是指用来将网络接口 548连接到总线518的硬件/软件。通信 连接550可以在计算机512内或外并且包括诸如调制解调器(电话、电缆、DSL和无线)和 ISDN适配器、以太网卡等内和外技术。
[0078] 可以理解,所示网络连接仅是示例,并且可以使用在计算机之间建立通信链路的 其他手段。本领域的普通技术人员可以理解,计算机512或其他客户机设备可作为计算机 网络的一部分来部署。在这一点上,本文所公开的主题涉及具有任意数量的存储器或存储 单元以及在任意数量的存储单元或卷上发生的任意数量的应用和进程的任何计算机系统。 本文所公开的主题的各方面可应用于具有部署在网络环境中的具有远程或本地存储的服 务器计算机和客户计算机的环境。本文所公开的主题的各方面也可应用于具有编程语言功 能、解释和执行能力的独立计算设备。
[0079] 本文所述的各种技术可结合硬件或软件,或在适当时以其组合来实现。由此,本文 所公开的方法和装置或其特定方面或部分可采取包含在诸如软盘、CD-ROM、硬盘驱动器或 任何其他机器可读存储介质等有形介质中的程序代码(即,指令)的形式,其中当程序代码 被加载到诸如计算机等机器内并由其执行时,该机器成为用于实现本文所公开的主题的各 方面的装置。如此出所用的,术语"机器可读介质"应被用来排除提供(即存储和/或传输) 任何形式的传播信号的任何机制。在程序代码在可编程计算机上执行的情况下,计算设备 通常将包括处理器、该处理器可读的存储介质(包括易失性和非易失性的存储器和/或存 储元件)、至少一个输入设备、以及至少一个输出设备。可例如通过使用数据处理API等来 利用域专用编程模型各方面的创建和/或实现的一个或多个程序可用高级过程语言或面 向对象的编程语言来实现以与计算机系统通信。然而,如果需要,该程序可以用汇编语言或 机器语言来实现。在任何情形中,语言可以是编译语言或解释语言,且与硬件实现相结合。
[0080] 尽管用结构特征和/或方法动作专用的语言描述了本主题,但可以理解,所附权 利要求书中定义的主题不必限于上述具体特征或动作。更确切而言,上述具体特征和动作 是作为实现权利要求的示例形式公开的。
【权利要求】
1. 一种系统,包括: 计算设备的至少一个处理器; 所述计算设备的存储器;以及 包括加载到所述存储器中的至少一个模块的跳出引擎,所述至少一个模块使所述至少 一个处理器: 响应于检测到关于程序在其上操作的数据的特性的至少一种假设的无效性,将以动态 语言编写的程序的执行从机器代码执行器执行的经编译的代码变换到由解释器解释的经 解释的字节代码,所述经编译的代码基于所述至少一种假设被优化,所述经解释的字节代 码没有基于所述至少一种假设被优化; 在所述经解释的字节代码中的一个点处恢复在解释器中的所述程序的执行,所述点对 应于在经优化的编译的代码中检测到无效性处的点。
2. 如权利要求1所述的系统,其特征在于,还包括: 加载到所述存储器中的至少一个模块,所述至少一个模块使所述至少一个处理器: 从由所述机器代码执行器所使用的对应变量中重新物化由所述解释器所使用的变量。
3. 如权利要求1所述的系统,其特征在于,还包括: 加载到所述存储器中的至少一个模块,所述至少一个模块使所述至少一个处理器: 在所述经优化的编译的字节代码中插入至少一个跳出点,所述至少一个跳出点与持有 所述解释器恢复所述程序的执行所需要的值的一组变量相关联。
4. 如权利要求1所述的系统,其特征在于,其中执行是在经优化的编译的代码中预先 确定的跳出点处被从经优化的编译的代码变换到未经优化的字节代码。
5. -种方法,包括: 在计算设备的处理器处接收字节代码,所接收的字节代码包括源自以动态语言编写的 程序的未经优化的字节代码; 接收关于由所述程序操作的数据的至少一种假设; 基于所述至少一种假设生成经优化的编译的代码; 执行所述经优化的编译的代码; 响应于确定所述至少一种假设的无效性,停止所述经优化的编译的代码的执行; 还原与所述经优化的编译的代码相关联的变量相对应的解释器变量; 在所述未经优化的字节代码中的一个点处恢复在解释器中的所述程序的执行,所述点 对应于在经优化的编译的代码中确定所述无效性处的点。
6. 如权利要求5所述的方法,其特征在于,还包括: 捕捉在所述未经优化的字节代码中与在所述经优化的编译的代码中的至少一个预先 确定的跳出点相对应的位置。
7. 如权利要求6所述的方法,其特征在于,还包括: 捕捉与在所述经优化的编译的代码中的至少一个预先确定的跳出点相关联的变量的 位置。
8. 如权利要求7所述的方法,其特征在于,还包括: 执行所述经优化的编译的代码;以及 在所述至少一个预先确定的跳出点处重新物化与所述经优化的编译的代码变量相关 联的对应的解释器变量。
9. 如权利要求5所述的方法,其特征在于,还包括: 复活由所述解释器所使用的变量。
10. -种包括当执行时使计算设备的至少一个处理器执行下列操作的计算机可执行指 令的计算机可读存储介质: 响应于在跳出点处检测到至少一个无效情况,从执行源自以动态语言编写的程序的经 优化的编译的代码中跳出,所述经优化的编译的代码基于至少一种无效假设被优化; 基于所述经优化的编译的代码变量的状态来还原解释器变量的状态; 在未经优化的字节代码中与在所述经优化的编译的代码中的所述跳出点相对应的点 处,在所述解释器中恢复所述程序的执行; 执行源自所述程序的经优化的编译的代码,所述程序以JavaScript编写;以及 保存包括在所述经优化的编译的程序执行期间在其处存储了变量的位置的跳出信息。
【文档编号】G06F9/30GK104115120SQ201380008460
【公开日】2014年10月22日 申请日期:2013年1月31日 优先权日:2012年2月7日
【发明者】L·拉弗里尼尔, C·曼 申请人:微软公司
网友询问留言 已有0条留言
  • 还没有人留言评论。精彩留言会获得点赞!
1