一种基于标准工具生成Java Card程序库目标代码的方法和设备 【技术领域】
本发明涉及Java Card开发领域,更具体地,涉及基于Sun标准工具生成Java Card程序库目标代码的方法和设备。
背景技术
Java Card技术是用于智能卡的Java技术,是用途广泛的智能卡通用编程平台。Java作为一种基于虚拟机的编程平台,Java源代码首先编译成字节代码,然后运行在解释字节代码的虚拟机上。由于不产生本地代码,所以Java程序如果想调用本地函数的话,需要通过专门的Java本地接口(JNI,Java Native Interface)来实现。对于Java Card来讲,出于安全性的考虑,不允许Java Card的小应用程序(Applet)来访问本地接口,但是烧制在ROM或flash中的运行库可以访问本地代码,例如通过Sun公司的工具来访问本地代码。实际上,Java Card程序库通常都包含对本地函数的调用。
图1示出了利用Sun公司的标准工具包将Java Card程序库源代码(.java)编译成Java Card程序库目标代码的过程。如图所示,该标准工具包将Java Card程序库源代码(.java)转换成Java Card程序库字节代码(.class),再编译成汇编语言源代码(.jca),再通过汇编器转换成C语言程序源代码(.c),最后将该C语言源代码与卡操作系统(COS)、虚拟机等代码一起编译链接成目标代码写到智能卡的ROM或flash中。
上述利用Sun公司的标准工具生成Java Card程序库目标代码的过程具有缺点。首先,Java Card汇编语言是Sun公司私有的没有规范的语言,Sun公司不提供公开的规范来规定该语言的具体语法,只提供公开的工具开发包来将字节代码转换成Java Card汇编代码。这就导致了如果这种语言有缺陷或错误,没有有效的办法来修正它,而且这种修正也没有办法被业界所接受。其次,Java Card汇编语言源代码(.jca)与对应的Java Card字节代码(.class)相比,可能会丢失信息。例如,在异常处理者信息表(exceptionhandler info)中有一位用于优化的停止位(stop bit),当虚拟机发现停止位后,它会中止异常处理表的查找,这样就可以不用遍历所有的异常处理表,而达到优化的效果。停止位在异常处理者信息表中占用一个比特,与异常处理表中的异常长度信息共享两个字节。但是在Java Card汇编语言中,是不存储这个长度信息的,这是因为在Java Card汇编语言中记录的是起始地址和结束地址,就没有必要存储这个长度。所以这个优化位就丢失掉了,在汇编器汇编代码时,也就没有办法将其复原。这个停止位是在Java语言字节代码规范和Java Card虚拟机规范中明确定义的,对于智能卡这样的资源受限系统也确实会起到较好的优化效果。
【发明内容】
考虑到现有技术的上述缺陷,本发明提供了一种通用且符合规范的方法来实现本地函数的调用。
根据本发明的一个方面,提供了一种生成含有本地函数调用的JavaCard程序目标字节代码的方法,包括:将含有本地函数调用的Java Card程序源代码转换成Java Card程序字节代码;保存所述Java Card程序字节代码中的本地函数调用信息,并将所有本地函数替换成空函数,以得到无本地函数调用的Java Card程序字节代码;将所述无本地函数调用的Java Card程序字节代码转换成无本地函数调用的Java Card程序目标字节代码;以及根据所保存的本地函数调用信息,建立对所述空函数的调用与对相应本地函数的调用之间的映射,以得到含有本地函数调用的Java Card程序目标字节代码。
根据本发明的一个方面,提供了一种生成含有本地函数调用的JavaCard程序目标代码的方法,包括:
将含有本地函数调用的Java Card程序源代码转换成Java Card程序字节代码;保存所述Java Card程序字节代码中的本地函数调用信息,并将所有本地函数替换成空函数,以得到无本地函数调用的Java Card程序字节代码;将所述无本地函数调用的Java Card程序字节代码转换成无本地函数调用的Java Card程序目标字节代码;根据所保存的本地函数调用信息,建立对所述空函数的调用与对相应本地函数的调用之间的映射,以得到含有本地函数调用的Java Card程序目标字节代码;以及将所述含有本地函数调用的Java Card程序目标字节代码转换成含有本地函数调用地Java Card程序目标代码。
根据本发明的一个方面,所述含有本地函数调用的Java Card程序源代码包括Java Card程序库源代码。
根据本发明的一个方面,将含有本地函数调用的Java Card程序源代码转换成Java Card程序字节代码的步骤以及将所述无本地函数调用的JavaCard程序字节代码转换成无本地函数调用的Java Card程序目标字节代码的步骤是通过Sun标准工具来执行的。
本发明提供的生成Java Card程序库目标代码的技术方案完全兼容于现有的工具,而且完全符合标准,并且可以预期兼容将来的标准。
【附图说明】
在下文中结合附图对本发明具体实施例进行详细的说明,其中:
图1示出了现有技术中利用Sun标准工具将Java Card程序库源代码编译成Java Card程序库目标代码的过程;
图2示出了现有技术中利用Sun标准工具将Java Card小应用程序源代码编译成Java Card小应用程序目标字节代码的过程;以及
图3示出了按照本发明一个实施例、利用Sun标准工具将Java Card程序库源代码编译成Java Card程序库目标代码的过程。
【具体实施方式】
在下文中,将参考附图通过具体实施例对本发明进行描述,应该注意,本发明并不限于以下描述的实施例。本领域技术人员应该理解,为了说明的方便,在利用Sun标准工具开发Java Card程序库目标代码的实现方式下描述了本发明的具体实施例,但是本发明也可以应用于其它类似的开发工具,以及应用于Java Card程序库之外的Java Card程序,只要该Java Card程序需要调用本地函数,就适合于应用本发明进行处理。
图2示出了现有技术中利用Sun标准工具将Java Card小应用程序源代码编译成Java Card小应用程序目标字节代码的过程,该标准工具例如是Sun公司提供的标准工具Converter。
如背景技术中所提到的,不允许Java Card的小应用程序访问本地接口,因此小应用程序源代码不包含对本地函数的调用。如图2所示,Sun标准工具将Java Card小应用程序源代码(.java)转换成Java Card小应用程序字节代码(.class),然后将该字节代码编译成Java Card小应用程序目标字节代码(.cap)。该目标字节代码(.cap)是标准的二进制字节代码,与图1所示的生成汇编语言代码(.jca)的过程相比,该目标字节代码(.cap)不会丢失信息,也不存在未规范语言(例如Sun公司私有的汇编语言)的转化问题。该目标字节代码(.cap)可以直接装入到Java Card中运行。
上述Sun标准工具出于安全性的考虑,不把含有本地函数调用的JavaCard程序字节代码(.class)直接转换成目标字节代码(.cap)。例如,如果小应用程序中包含对本地函数的调用,那么Sun标准工具将无法把该小应用程序直接转换成目标字节代码(.cap)。
图3示出了按照本发明一个实施例、利用Sun标准工具将Java Card程序库源代码编译成Java Card程序库目标代码的过程。由于该Java Card程序库源代码包含对本地函数的调用,因此Sun标准工具无法把它编译成目标字节代码(.cap),而只能将它编译成Sun公司私有的汇编语言源代码(.jca)。
在图3所示的方法中,首先,利用Sun标准工具将Java Card程序库源代码(.java)转换成Java Card程序库字节代码(.class)。然后,根据本发明的一个实施例,提供一个本地调用预处理程序,用于保存Java Card程序库字节代码(.class)中的本地函数调用信息,并将所有本地函数替换成空函数,以得到无本地函数调用的Java Card程序库字节代码(.class)。经过上述预处理,所得到的无本地函数调用的Java Card程序库字节代码(.class)与图2中所示的小应用程序字节代码(.class)相似,不包含对本地函数的调用,因此可以利用Sun标准工具将其转换为目标字节代码(.cap)。
接下来,利用Sun标准工具将上述无本地函数调用的Java Card程序库字节代码(.class)转换成无本地函数调用的Java Card程序库目标字节代码(.cap)。该目标字节代码(.cap)可以直接装入Java Card中运行,只是所有对于原本地函数的调用均为空。
接下来,根据本发明的一个实施例,提供一个本地调用处理程序,用于根据所保存的本地函数调用信息,建立对空函数的调用与对相应本地函数的调用之间的映射,以得到含有本地函数调用的Java Card程序库目标字节代码(.cap)。具体而言,将本应该调用本地函数但是调用了空函数的JavaCard函数与相应的本地函数之间建立映射。可以将该Java Card程序库目标字节代码(.cap)作为运行库烧制到ROM或flash中,从而在运行时可以访问本地函数。可以通过以下方式在目标字节代码(.cap)中实现Java Card函数与本地函数之间的映射。例如,可以定义符合Java Card虚拟机规范的用户自定义组件,例如Java Card虚拟机规范6.1.2节提供的自定义组件Custom Component,在该自定义组件Custom Component中设置Java Card函数与本地函数的映射关系。举例来说,当执行一个需要本地函数支持的Java Card函数时,就会从这个自定义组件Custom Component中查找相应的映射信息,并执行对应的本地函数。例如,还可以使用自定义的指令来实现对本地函数的调用,该指令的参数用来标识要调用的本地函数。举例来说,假设使用自定义的指令0xFD来代表调用本地函数,如果一个Java Card函数对应于第0001号本地函数,则本地函数处理程序将该Java Card函数与代码0xFD,0x00,0x01相关联,当执行该Java Card函数时,通过执行代码0xFD,0x00,0x01来调用本地函数。
至此,已经生成含有本地函数调用的Java Card程序库目标字节代码(.cap),可以将该目标字节代码(.cap)编译、链接到虚拟机中,得到JavaCard程序库目标代码。
接下来,可以将Java Card程序库目标字节代码(.cap)转化成C语言源代码(.c)。对于从cap到c的转化,只是将二进制格式转化成一种方便于编译、链接进操作系统或虚拟机代码的一个过程,这个步骤没有统一的标准来定义,取决于具体的实现。这是本领域技术人员熟知的技术,各厂商均有自己的工具来实现此功能。
接下来,与图1中所示的步骤类似,将该C语言源代码与卡操作系统和/或虚拟机等代码一起编译、链接成目标代码,写到智能卡的ROM或flash中。
本领域技术人员应当理解,虽然上述实施例描述了利用Sun标准工具开发Java Card程序库目标代码的具体实施例,但是当使用其它类似的开发工具时也可以类似的使用本发明,并且本发明适用于编译任何需要调用本地函数的Java Card程序,而不限于Java Card程序库。
本领域技术人员应当理解,为了说明清楚的目的,详细描述了上述实施理的各个步骤,但不是每个步骤都是实现本发明所必需的。
上面各个实施例中所公开的方法,可以使用软件的方式来实现。
本领域技术人员应当理解,在本发明上述实施例的启示下,可以得到本发明实施例的各种变形,并且在不偏离本发明的精神或范围的情况下,本文中所定义的一般原理也可以应用到其他实施例中。因此本发明并不局限于本文中所示的实施例,而且要求与本文中所公开的原理和新颖特征相一致的最广的范围。