ibm 的java实现_使用IBM Java Toolbox实现Java/C混合编程

Body

某些项目的开发需要在Java中调用非Java代码(例如C/C++)编写的接口。例如我们需要使用一些系统级别的API来完成开发工作,但是这些API并不提供Java语言的接口。在这种情形下,我们通常会选择使用Java本地方法来实现Java对这类API的调用。

Java本地方法最普遍的一种实现方式是JNI(Java Native Interface)调用。通过JNI,Java可以与被调用的C/C++对象之间交换数据。虽然JNI的功能非常强大,但是使用JNI的本地方法必须遵循一系列的特殊规范,例如新的数据类型和使用javah -jni命令生成的头文件等等。一般而言,使用JNI方式的工程需要更多的开发和维护成本。

在一些简单的应用场景中,我们仅仅希望通过Java调用某些service program中的函数,获取相应的处理结果。此时,采用IBM Java Toolbox中提供的Service program call方法也许是一种更为快捷的实现方式。

本文将通过一个简单的范例介绍在IBM i上开发基于service program call模式的Java/C混合编程项目的思路。

1)创建一个简单的C程序。

这个C程序里定义了一个函数RelayCall,该函数接受一个输入参数input,一个输出参数output。函数将对输入参数input中的字符串进行一定处理后,将结果放回输出字符串中,并根据执行的成功与否给出相应的返回值。

#include

#include

#include

int RelayCall(char* input, char* output)

{

if(!input || !output)return -1;

if(strlen(input) == 0)return -2;

strcpy(output, "We are in C code. Input is ");

strcat(output, input);

return 0;

}

2)将这段C代码编译成一个service program.

假设第一步中的代码被保存在了IFS路径/samplelib/samplec.c下。而生成的service program将放置在MYLIB这个Library下。我们通过如下两条命令来编译这个service program:

CRTCMOD MODULE(MYLIB/SAMPLEC) SRCSTMF('/samplelib/samplec.c')

CRTSRVPGM SRVPGM(MYLIB/SAMPLEC) MODULE(MYLIB/SAMPLEC) EXPORT(*ALL) SRCFILE(MYLIB/SAMPLEC)

201210181.JPG

编译完成后,可以通过

WRKLIB MYLIB

检测该service program是否已经成功生成到该Library下面。

201210182.JPG

201210183.JPG

3)编写Java代码

首先请确保你的机器上安装了最新版本的IBM Java Toolbox产品。我们将下面的Java代码保存为SrvpgmCallSample.java文件,并同样放置在/samplelib目录下。

import com.ibm.as400.access.AS400;

import com.ibm.as400.access.AS400Bin4;

import com.ibm.as400.access.AS400Message;

import com.ibm.as400.access.AS400Text;

import com.ibm.as400.access.ProgramParameter;

import com.ibm.as400.access.ServiceProgramCall;

public class SrvpgmCallSample {

public static void main(String[] args) {

try {

//创建与本地方法相对应的参数列表。

ProgramParameter[] parameterList = new ProgramParameter[2];

//创建AS400对象,调用的service program必须存在于这台AS400机器上。

AS400 system = new AS400();

AS400Bin4 bin4 = new AS400Bin4();

String input = args[0];

//将输入字符串转换成Byte数组的格式,注意添加结束字符'\0'。

byte[] inputString = new AS400Text(input.length() + 1, system).toBytes(input+'\0');

parameterList[0] = new ProgramParameter(ProgramParameter.PASS_BY_REFERENCE, inputString);

parameterList[1] = new ProgramParameter(ProgramParameter.PASS_BY_REFERENCE, new byte[1024], 1024);

ServiceProgramCall sPGMCall = new ServiceProgramCall(system);

//设置要调用的service program的完整路径

sPGMCall.setProgram("/QSYS.LIB/MYLIB.LIB/SAMPLEC.SRVPGM", parameterList);

//设置需要调用的函数名.

sPGMCall.setProcedureName("RelayCall");

//设置函数返回值的类型,这里我们使用整型。

sPGMCall.setReturnValueFormat(ServiceProgramCall.RETURN_INTEGER);

System.out.println("(Java) Input field is '" + input + "'");

//调用service program中的方法。

if (sPGMCall.run() != true) {

//如果调用失败,输出错误信息

AS400Message[] messageList = sPGMCall.getMessageList();

for (int i = 0; i < messageList.length; ++i) {

System.out.println(messageList[i].getText());

}

} else {

//调用成功,获取并打印返回值

byte[] outbytes = parameterList[1].getOutputData();

String out = ((String) new AS400Text(1024, system).toObject(outbytes)).trim();

int i = bin4.toInt(sPGMCall.getReturnValue());

System.out.println("Returncode is " + i + "\r\nOutput is: " + out);

}

} catch (Exception e) {e.printStackTrace();}

System.out.println("(Java) Returned from the native method");

}

}

需要注意的是,IBM Java Toolbox中的ServiceProgramCall对象只能接受Byte数组形式的字符串参数,因而在将字符串转换为Byte数组的时候,需要手动添加结束字符'\0'。

4)编译并执行该Java代码

在IBM i上输入QSH进入QShell环境,通过cd /samplelib命令切换到/samplelib目录。通过javac命令编译该Java文件。编译过程需要添加jt400native.jar的classpath。

javac -classpath /QIBM/ProdData/OS/OSGi/shared/com.ibm.i5os.jt400native/jt400native.jar:. SrvpgmCallSample.java

201210184.JPG

如果编译成功的话,通过java命令执行该Java程序。同样需要添加jt400native.jar的classpath。

java -classpath /QIBM/ProdData/OS/OSGi/shared/com.ibm.i5os.jt400native/jt400native.jar:. SrvpgmCallSample 'Hello'

(Java) Input field is 'Hello'

Returncode is 0

Output is: We are in C code. Input is Hello

(Java) Returned from the native method

(Java) All done...

201210185.JPG

可以看到,程序成功执行完毕,打印出了C代码中的执行结果。

通过非常简单的几步,我们便实现了在Java对C编写的函数的调用以及两者间数据的传输。相比复杂的JNI调用,IBM Java Toolbox的service program call可以更快速的实现轻量级的Java/C混合编程开发。

作者: Xu Meng

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值