[心缘地方]同学录
首页 | 功能说明 | 站长通知 | 最近更新 | 编码查看转换 | 代码下载 | 常见问题及讨论 | 《深入解析ASP核心技术》 | 王小鸭自动发工资条VBA版
登录系统:用户名: 密码: 如果要讨论问题,请先注册。

[转帖]JNI调用VISA的创建过程

上一篇:[备忘]Java中,使用JNA调用Visa32.dll,控制频谱仪~~
下一篇:[备忘]注意,URLEncode值作为post内容提交时,需要过滤4个字母~~

添加日期:2012/8/21 17:14:59 快速返回   返回列表 阅读5003次
http://www.csdnjava.com/forum.php?mod=viewthread&tid=18746
---------------------------------------------
安装VC++ 6.0
安装VISA。该软件主页为www.ni.com
具体下载地址应为:URL ftp://ftp.ni.com/support/visa/drivers/win32/3.2/visa320full.exe,下载前可能要免费注册。
其缺省安装目录是C:\Program Files\VISA。
建立c:\gpib目录,创建JNI本地接口类:JGpib.java
##c:\gpib\JGpib.java


package org.eleaf.jni.gpib;
public class JGpib
{
public native int open(String gpibAddr);

public native int close();

public native String read();

public native int write(String cmdStr);

}



使用javac命令编译JGpib.java.
c:\gpib>javac -d . .\JGpib.java

使用javah命令生成C++头文件:
c:\gpib>javah -classpath . -d . org.eleaf.jni.gpib.JGpib

这是生成的头文件:org_eleaf_jni_gpib_JGpib.h
##c:\gpib\org_eleaf_jni_gpib_JGpib.h


/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class org_eleaf_jni_gpib_JGpib */
#ifndef _Included_org_eleaf_jni_gpib_JGpib
#define _Included_org_eleaf_jni_gpib_JGpib
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: org_eleaf_jni_gpib_JGpib
* Method: open
* Signature: (Ljava/lang/String;)I
*/
JNIEXPORT jint JNICALL Java_org_eleaf_jni_gpib_JGpib_open
(JNIEnv *, jobject, jstring);
/*
* Class: org_eleaf_jni_gpib_JGpib
* Method: close
* Signature: ()I
*/
JNIEXPORT jint JNICALL Java_org_eleaf_jni_gpib_JGpib_close
(JNIEnv *, jobject);
/*
* Class: org_eleaf_jni_gpib_JGpib
* Method: read
* Signature: ()Ljava/lang/String;
*/
JNIEXPORT jstring JNICALL Java_org_eleaf_jni_gpib_JGpib_read
(JNIEnv *, jobject);
/*
* Class: org_eleaf_jni_gpib_JGpib
* Method: write
* Signature: (Ljava/lang/String;)I
*/
JNIEXPORT jint JNICALL Java_org_eleaf_jni_gpib_JGpib_write
(JNIEnv *, jobject, jstring);
#ifdef __cplusplus
}
#endif
#endif
/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class org_eleaf_jni_gpib_JGpib */
#ifndef _Included_org_eleaf_jni_gpib_JGpib
#define _Included_org_eleaf_jni_gpib_JGpib
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: org_eleaf_jni_gpib_JGpib
* Method: open
* Signature: (Ljava/lang/String;)I
*/
JNIEXPORT jint JNICALL Java_org_eleaf_jni_gpib_JGpib_open
(JNIEnv *, jobject, jstring);
/*
* Class: org_eleaf_jni_gpib_JGpib
* Method: close
* Signature: ()I
*/
JNIEXPORT jint JNICALL Java_org_eleaf_jni_gpib_JGpib_close
(JNIEnv *, jobject);
/*
* Class: org_eleaf_jni_gpib_JGpib
* Method: read
* Signature: ()Ljava/lang/String;
*/
JNIEXPORT jstring JNICALL Java_org_eleaf_jni_gpib_JGpib_read
(JNIEnv *, jobject);
/*
* Class: org_eleaf_jni_gpib_JGpib
* Method: write
* Signature: (Ljava/lang/String;)I
*/
JNIEXPORT jint JNICALL Java_org_eleaf_jni_gpib_JGpib_write
(JNIEnv *, jobject, jstring);
#ifdef __cplusplus
}
#endif
#endif



启动VC++ 6.0:
1) 选择[new]->[projects](选择[Win32 Dynamic-Link Library],以测试程序中System.loadLibrary()方法中指定的dll库名gpib作为工程名)->[OK]->[An ampty DLL project]->[Finish]。 

2) 选择[Tools]->[Options]->[Directories](添加目录%JAVA_HOME%\INCLUDE和%JAVA_HOME%\INCLUDE\WIN32)。在这些目录中包含JNI所需的头文件。 

3) 将上面天生的org_eleaf_jni_gpib_JGpib.h拷贝到gpib工程文件夹中。
该工程文件夹的缺省位置为:
C:\Program Files\Microsoft Visual Studio\MyProjects\gpib
然后把它添加到VC++中工程目录窗口中的[Head Files]条下。
然后是VC++中 VISA环境的设置,这在VISA的user guide文档visa.pdf中有具体说明。下面这段话是从该文档摘录过来的:


Microsoft Visual C++ Version 6.0 Compilers
1 Select Project > Settings from the menu and click the C/C++ tab.

2 Select Code Generation from the Category list box and select Multi-Threaded using DLL from the Use Run-Time Libraries list box. (VISA requires these definitions for Win32.) Click OK to close the dialog box.

3 Select Project > Settings from the menu. Click the Link tab and add visa32.lib to the Object/Library Modules list box. Optionally, you may add the library directly to your project file. Click OK to close the dialog box.
4 You may want to add the include files and library files search paths. They are set as follows:
?Select Tools > Options from the menu.
?Click the Directories tab to set the include file path.
?Select Include Files from the Show Directories For list box.
?Click at the bottom of the list box and type one of the following: C:\Program Files\VISA\win95\include or C:\Program Files\VISA\winnt\include.

5 Select Library Files from the Show Directories For list box.

6 Click at the bottom of the list box and type one of the following: C:\Program Files\VISA\win95\lib\msc or C:\Program Files\VISA\winnt\lib\msc


所有的环境设置都完成以后,就可以在VC++里编写cpp文件进行编译连接了:
点击工程目录窗口中的[Source Files]创建一个新的cpp文件,命名为org_eleaf_jni_gpib_JGpib.cpp:
##C:\Program Files\Microsoft Visual Studio\MyProjects\gpib\org_eleaf_jni_gpib_JGpib.cpp


#include <visa.h>
#include <stdio.h>
#include <string.h>
#include "org_eleaf_jni_gpib_JGpib.h"
//定义三个全局变量,供下面四个独立函数调用。
static ViSession defaultRM;
static ViSession vi;
static char buf[256] = {0};
//以下四个独立函数是按照上面的头文件里的函数定义创建的。
JNIEXPORT jint JNICALL Java_org_eleaf_jni_gpib_JGpib_open
(JNIEnv *env, jobject obj, jstring jstr)
{
//将从java程序中传进来的字符串转化为C++中的字符串格式。
const char *str = env->GetStringUTFChars(jstr, 0);
char cap[256];
strcpy(cap, str);
/*
在VISA中,viOpen()、viClose()、viScanf()、viPrintf()等方法都会返回一个ViStatus类型的值,这个值对应C++中的int型,代表方法执行的结果。假如是正确,ViStatus返回为VI_SUCCESS,值为0。假如出错,则返回各种负值,如:
-1073807299
VI_ERROR_INV_MASK
-1073807298
VI_ERROR_IO
-1073807297
VI_ERROR_INV_FMT
我们可以在C++程序中直接把这些ViStatus对象作为int型的值进行调用,如:
printf("result=%d\n", VI_SUCCESS);将打印出:
result=0
printf("result=%d\n", VI_ERROR_IO);将打印出:
result=-1073807298
关于这部分,在VISA的API文档里面有具体先容,对于windows 2000,该文档的地址为:
C:\Program Files\VISA\winnt\agvisa\visa.chm
ViStatus的说明在该文档[目录]下的[VISA Library Information]下的[VISA Error Codes]条里。
*/
ViStatus viss = viOpenDefaultRM (&defaultRM);
ViStatus vis = viOpen(defaultRM, cap, VI_NULL, VI_NULL, &vi);
return vis;
}

JNIEXPORT jint JNICALL Java_org_eleaf_jni_gpib_JGpib_close
(JNIEnv *env, jobject obj)
{
ViStatus viss = viClose(vi);
ViStatus vis = viClose(defaultRM);
return vis;
}
JNIEXPORT jstring JNICALL Java_org_eleaf_jni_gpib_JGpib_read
(JNIEnv *env, jobject obj)
{
viScanf(vi, "%t", &buf);
//将C++的字符串转换为java的字符串格式并返回。
return env->NewStringUTF(buf);
}

JNIEXPORT jint JNICALL Java_org_eleaf_jni_gpib_JGpib_write
(JNIEnv *env, jobject obj, jstring jstr)
{
const char *str = env->GetStringUTFChars(jstr, 0);
char cap[256];
strcpy(cap, str);
ViStatus vis = viPrintf(vi, cap);
return vis;
}


点击[Build]>[Compile org_eleaf_jni_gpib_JGpib.cpp]或按Ctrl + F7,编译该cpp文件。
检查一下下边的[Build]窗口,看是否有错误出现,假如没有错误,应该会出现如下的信息:


--------------------Configuration: gpib - Win32 Debug--------------------
Compiling...
Skipping... (no relevant changes detected)
org_eleaf_jni_gpib_JGpib.cpp
org_eleaf_jni_gpib_JGpib.obj - 0 error(s), 0 warning(s)


假如有错误,一般可能是语法题目或环境设置不正确,请仔细更正,然后重新编译。
然后点击[Build]>[Build gpib.dll],天生动态链接库文件。
编译连接完成后,请将天生的gpib.dll文件拷贝到系统环境变量PATH中可以找到的任意位置,比如%JAVA_HOME%\bin;%TOMCAT_HOME%\bin等。
编写测试程序:Test.java
##c:\gpib\Test.java


package org.eleaf.jni.gpib;
public class Test
{
//装载动态链接库gpib.dll.
static 
{
System.loadLibrary("gpib"); 
}
public static void main(String[] args)
{
JGpib jg = new JGpib();
/*
VISA可以连接电脑的GPIB/USB/Serial/COM/等端口。这里的ASRL1::INSTR字串表
示连接的是COM1端口,关于该字串的格式,在VISA的API文档里面有具体先容,对
于windows 2000,该文档的地址为:
C:\Program Files\VISA\winnt\agvisa\visa.chm
字串格式的说明在该文档[目录]下的[VISA Functions]下的[viOpen]条里。
*/
int i = jg.open("ASRL1::INSTR");
int j = jg.write("*RST\n");
int a = jg.write("*IDN?\n");
String s = jg.read();
System.out.println("s=" + s);
int b = jg.close();
//封闭会话以后,尝试调用write()方法发送指令,预计返回错误信息,即变量c、d的值将为负数:
int c = jg.write("*RST\n");
int d = jg.write("*IDN?\n");
System.out.println(i + ";" + j + ";" + a + ";" + b + ";" + c + ";" + d);

}



编译执行Test.java
c:\gpib>javac -classpath . -d . Test.java
c:\gpib>java -classpath . org.eleaf.jni.gpib.Test
0;0;0;0;-1073807346;-1073807346

前面四个值为0,代表ViStatus中的VI_SUCCESS,表示执行成功;
最后两个负数值-1073807346,对应ViStatus中的VI_ERROR_INV_OBJECT(The object reference is invalid. ),表明在viClose()方法执行以后,会话已被封闭,继续通过viPrintf()发送指令会发生错误。
 

评论 COMMENTS
没有评论 No Comments.

添加评论 Add new comment.
昵称 Name:
评论内容 Comment:
验证码(不区分大小写)
Validation Code:
(not case sensitive)
看不清?点这里换一张!(Change it here!)
 
评论由管理员查看后才能显示。the comment will be showed after it is checked by admin.
CopyRight © 心缘地方 2005-2999. All Rights Reserved