您的位置:首页 > 运维架构 > Linux

linux系统java通过jni方式获取硬盘序列号

2012-11-15 15:22 676 查看
最近项目需要从linux系统获取硬盘序列号,特把成果分享一下。至于什么是jni这里就不介绍了需要的童鞋可以google百度一把。这里包括两部分代码,一部分是java的代码供上层调用,一部分是c代码编译成so动态链接库供java代码,下面从c代码开始。

一 代码

c代码

getLocalSysInfo.cpp

#include "getLocalSysInfo.h"
#include <stdio.h>
#include <sys/ioctl.h>
#include <linux/hdreg.h>
#include <sys/fcntl.h>

JNIEXPORT void JNICALL Java_getSysInfo_getLocalHdSn(JNIEnv * env, jobject arg)
{
struct hd_driveid id;

/*打开设备文件*/
int fd = open("/dev/sda", O_RDONLY);
if (fd < 0)
{
printf("oh can not open sda/n");
return ;
}

/*读取设备信息*/
if(!ioctl(fd, HDIO_GET_IDENTITY, &id))
{
/*打印磁盘序列号信息*/
printf("Serial Number=%s\n",id.serial_no);
}

return;
}


头文件

getLocalSysInfo.h

这个头文件是在执行

javac getSysInfo.java

后生成getSysInfo.class文件后再执行

javah -classpath . -jni getSysInfo

后生成getSysInfo.h头文件,我手痒生成后把它改为getLocalSysInfo.h的(^0^)。

/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class HelloWorld */

#ifndef _Included_HelloWorld
#define _Included_HelloWorld
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class:     getSysInfo
* Method:    getLocalHdSn
* Signature: ()V
*/
JNIEXPORT void JNICALL Java_getSysInfo_getLocalHdSn
(JNIEnv *, jobject);

#ifdef __cplusplus
}
#endif
#endif


在c代码中打开硬盘设备文件/dev/sda(注意每个系统可能不一样请根据自己的系统修改路径),然后调用ioctrl读取设备信息获取硬盘序列号并打印出来。接下来就是编译了我写了个小小的makefile文件:

CC=g++
JDK_INCLUDE=/usr/lib/jvm/jdk1.7.0/include
INCLUDE=-I $(JDK_INCLUDE) -I $(JDK_INCLUDE)/linux
FLAG=-fPIC -shared
OBJ=libgetLocalSysInfo.so
all:getLocalSysInfo.cpp getLocalSysInfo.h
$(CC) $(FLAG) -cpp getLocalSysInfo.cpp -o $(OBJ)  $(INCLUDE)
clean:
rm -rf *.o *.so getLocalSysInfo


编译器我用的是g++,我jdk的路径是/usr/lib/jvm/jdk1.7.0/include,这个必须包含否则会提示找不到jni.h这个文件。编译标致选择-fPIC和-shared这两个的含义如下:

-fPIC

生成的目标文件可在不固定内存位置执行,就是可动态链接的意思了。

-shared

生成的目标文件可以被共享即可以多进程调用,如不加该选项会提示要你添加main函数(呵呵你懂的)。

java代码

getSysInfo.java

public class getSysInfo {
/*java本地方法申明*/
public native void getLocalHdSn( );

public getSysInfo() {
}
/*装入动态链接库getHdSn.so*/
static {
System.loadLibrary("getLocalSysInfo");
}
}


System.loadLibrary("getLocalSysInfo");

加载动态链接库libgetLocalSysInfo.so。编译java命令:

getHdSn.java

public class getHdSn{
/**
* @param args
*/
public static void main(String[] args) {
getSysInfo sysInfo = new getSysInfo();
sysInfo.getLocalHdSn( );
}
}


调用或者硬盘序列号方法。

编译和运行

编译和运行命令如下:



代码下载

我把完整代码上传到博客资源可直接下载

点击这里下载代码
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: