使用JavaCard RMI接口

王朝厨房·作者佚名  2007-01-04
窄屏简体版  字體:   |    |    |  超大  

Java Card小应用程序编程的第二个模型是JavaCard RMI ( JCRMI),严格的说它是J2SE RMI分布对象模型的缩小版。

这是一个以对象为中心的模型,根据这个模型你在上一节看到的APDU通信和句柄将被抽象化;取而代之的是你处理对象。这简化了编程和集成基于Java Card技术的设备。

在RMI模型中,一个服务器应用程序创建并生成可访问的远程对象,并且一个客户应用程序获得到服务器的远程对象的远程引用,然后调用它们的远程方法。在JCRMI中,Java Card小应用程序是服务器,而主应用程序是客户端。

JavaCard RMI简介

两个程序包提供了JavaCard RMI支持:

1、java.rmi定义了Java 2标准版java.rmi程序包的一个子集。它定义了Remote接口和RemoteException类。除此之外,没有包含其他传统的java.rmi类。

2、Javacard.framework.service定义了Java Card小应用程序服务类,包括RMI服务类CardRemoteObject和RMIService。

3、Class CardRemoteObject定义了两个方法启动和禁止卡片外的对象的远程访问。类RMIService处理RMI请求(转化输入的命令APDU为远程方法调用)。

编写一个JCRMI应用程序类似于编写一个典型的基于RMI的应用程序:

1.定义远程类的行为为一个接口。

2.编写远程类的服务器实现,和支持类。

3.编写一个使用远程服务的客户机程序和支持类。

注意JCRMI没有改变小应用程序的基本结构或者生命周期,你不久就会看到。

远程接口

创建一个远程服务中的第一步是定义它的可见行为。远程接口定义你的小应用程序提供的服务。和在标准的J2SE RMI中一样,所有的Java Card RMI远程接口必须扩展java.rmi.Remote接口。为了说明,这里有一个远程接口,揭示一个取得保存在卡片里的余额的方法:

import java.rmi.*;

import javacard.framework.*;

public interface MyRemoteInterface extends Remote {

...

public short getBalance() throws RemoteException;

...

// A complete credit card application would also define other

// methods such as credit() and debit() methods.

...

}

列表1、远程接口

MyRemoteInterface定义这个远程方法,在我们的示例中一个getBalance ()方法,来取得保存在智能卡中的余额。注意,除了Java Card特定的导入之外,这个远程接口看起来完全象一个标准的RMI远程接口。

服务器实现

下一步是实现服务器的行为。服务器实现包含Java Card小应用程序,在所有的你已经定义的远程接口当中的实现,和任何与你的应用程序相关的特定类。

Java Card小应用程序

Java Card小应用程序是JCRMI服务器,并且是主机(客户端)应用程序可用的远程对象的所有者。一个典型的Java Card RMI小应用程序的结构在下面的图表中说明:

Figure 4. 典型的JavaCard RMI应用程序结构

当和明确地处理APDU消息的小应用程序相比,基于JCRMI的小应用程序更像一个对象容器。如图4所示,基于JCRMI的小应用程序有一个或多个远程对象,一个APDU Dispatcher和一个接收APDU并且把它们转化为远程方法调用的RMIService。Java Card远程类可以扩展CardRemoteObject类,自动导出对象,使之可用于远程使用。

JCRMI小应用程序必须扩展javacard.framework.Applet,遵循标准的小应用程序结构,并且定义适当的生命周期方法。它必须安装并且登记本身,并且分配APDU。下面这一代码片断说明一个基于JCRMI的小应用程序的典型结构:

public class MyApplet extends javacard.framework.Applet {

private Dispatcher disp;

private RemoteService serv;

private Remote myRemoteInterface;

/**

* Construct the applet. Here instantiate the remote

* implementation(s), the APDU Dispatcher, and the

* RMIService. Before returning, register the applet.

*/

public MyApplet () {

// Create the implementation for my applet.

myRemoteInterface = new MyRemoteInterfaceImpl();

// Create a new Dispatcher that can hold a maximum of 1

// service, the RMIService.

disp = new Dispatcher((short)1);

// Create the RMIService

serv = new RMIService(myRemoteInterface);

disp.addService(serv, Dispatcher.PROCESS_COMMAND);

// Complete the registration process

register();

}

...

小应用程序创建一个Dispatcher和一个处理输入的JCRMI APDU的RMIService。

...

/**

* Installs the Applet. Creates an instance of MyApplet.

* The JCRE calls this static method during applet

* installation.

* @param bArray install parameter array.

* @param bOffset where install data begins.

* @param bLength install parameter data length.

*/

public static void install(byte[] aid, short s, byte b) {

new MyApplet();

}

在JavaCard环境中,JVM的生命周期是物理卡片的生命周期,而不是提供垃圾收集器的所有的Java Card实现的,所以你需要最小化内存分配。在安装时间创建对象,这样内存只被分配给它们一次。

/**

* Called by the JCRE to process an incoming APDU command. An

* applet is expected to perform the action requested and

* return response data, if any.

*

* This JCRMI version of the applet dispatches remote

* invocation APDUs by invoking the Dispatcher.

*

* Upon normal return from this method the JCRE sends the ISO-

* 7816-4-defined success status (90 00) in the APDU response.

* If this method throws an ISOException, the JCRE sends the

* associated reason code as the response status instead.

* @param apdu is the incoming APDU.

* @throw ISOException if the install method fails.

*/

public void process(APDU apdu) throws ISOException {

// Dispatch the incoming command APDU to the RMIService.

disp.process(apdu);

}

代码列表13.Java Card RMI小应用程序

小应用程序的process()方法接收一个APDU命令并且把它发送到RMIService,RMIService通过把它转化为一个RMI调用和后续响应处理这条命令。

实现远程对象

实现一个JCRMI远程对象类似于实现标准的J2SE RMI远程对象。主要区别是在JCRMI中你的远程对象有扩展CardRemoteObject的选择(除了实现你的远程接口之外)。

CardRemoteObject定义两个方法export()和unexport(),分别允许或者禁止从卡外到对象的访问。通过扩展CardRemoteObject,你自动地导出你的远程对象所有的方法。如果你决定不扩展CardRemoteObject,你将要负责通过调用CardRemoteObject.export()导出它们。

import java.rmi.RemoteException;

import javacard.framework.service.CardRemoteObject;

import javacard.framework.Util;

import javacard.framework.UserException;

/**

* Provides the implementation for MyRemoteInterface.

*/

public class MyRemoteImpl extends CardRemoteObject implements MyRemoteInterface {

/** The balance. */

private short balance = 0;

/**

* The Constructor invokes the superclass constructor,

* which exports this remote implementation.

*/

public MyRemoteImpl() {

super(); // make this remote object visible

}

/**

* This method returns the balance.

* @return the stored balance.

* @throws RemoteException if a JCRMI exception is

* encountered

*/

public short getBalance() throws RemoteException {

return balance;

}

// Other methods

...

}

列表⒕远程对象实现

一个完整的Java Card RMI应用程序的流程

让我们概述一个JCRMI应用程序的流程。客户端(主机)应用程序通过传递RMI APDU到卡上的JCRE来产生RMI调用,依次转送这些APDU到相应的JCRMI小应用程序。这个小应用程序分配接收的APDU到RMIService,依次处理APDU并且转化它为一个RMI调用。一个JCRMI小应用程序的典型流程在下面说明:

Figure 5. 基于JavaCard RMI模型的应用程序流程

简言之,JCRMI提供一个基于APDU的消息传递模型的分布式对象模型机制。JCRMI消息被封装到传送到RMIService的APDU消息中,负责解码APDU命令,并且转化这些命名到方法调用和响应。这允许服务器和客户端通信,来回传送方法信息、参数和返回值。

 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
 
© 2005- 王朝網路 版權所有 導航