○ JNI ( Java Nayive Interface) 기술
JNI는 자바 언어로 작성된 프로그램에서 C/C++ 언어로 작성된 함수를 호출할 수 있도록 해준다.
JNI는 주로 하드웨어를 제어하기 위해서, 혹은 기존 C/C++ 라이브러리를 이용하기 위해서
사용될 수 있다. 그러나, JNI를 사용하면 플랫폼간에 호환성이 떨어지고, Applet에서 사용할 수 없다는
단점이 있다. 이러한 단점에도 불구하고 자바언어의 장점을 가지고 하드웨어에 접근하기 위한 방법으로
JNI는 매우 중요한 위치를 차지한다.
○ JNI의 기능
- creat, inspect,update java object
- java method 호출
- catch & throw exception
○ native method interface
- jdk 1.2.2
- Netscape's java runtime interface
- MS's Raw Native Interface
- Java/Com Interface
○ JNI Program의 작성 단계
① JAVA 클래스를 작성한다.
② JAVA 클래스를 컴파일 한다. ( Javac를 이용 )
③ C언어의 헤더 파일을 생성한다.
Javah를 이용해서 Native Method를 위한 C언어 헤더 파일을 생성한다.
Javah를 사용할때는 -jni옵션을 이용하고, Argument로 Native Method를 갖는
JAVA 클래스 이름을 기술한다.
④ Native Method를 작성한다.
실제적인 작업을 수행할 Native Method를 C 언어로 구현하는 것이다.
Native Method를 구현하기 위해서는 jni.h 헤더 파일과 Javah로 생성된 헤더 파일을
Include해야 한다.
⑤ 라이브러리를 만든다.
Visual C++같은 Tool을 이용해 동적 라이브러리(*.dll) 파일을 만든다.
⑥ 프로그램을 실행시킨다.
라이브러리를 작성하면 JAVA CLASS를 실행시킬 수 있다. 라이브러리 Path가 설정되지
않은 경우에 에러가 발생할 수 있다. Path가 설정되어 있지 않았다면 UNIX의 C-Shell에서
는 setenv 명령어를 이용해서 Path를 설정한다. Window 에서는 Autoexec.bat파일에
설정하거나, DOS창에서 환경변수를 맞추어줄 수 있다.
자바에서 JNI 를 쓰면 C 코드로 작성된 라이브러리를 불러 쓸 수 있다.
아래 테스트 환경은 vc++ 6.0 에서 했습니다.
JNI 형식에만 맞는다면 dll 을 로드 할수 있습니다.
[예는 두수를 곱하는것과 메세지를 출력하는 부분은 C 로 작성된 dll 라이브러리를 사용하는 예제]
jni 가 사용된 메소드는 native 한정자를 적음으로써 가능합니다.
--------------------------------NativeTest2.java-----------------------------------
public class NativeTest2
{
static
{
System.loadLibrary("DisplayMessage2");
}
public static void main(String []args)
{
System.out.println(calcul(3,4,true));
}
public static native void printMessage(String str);
public static native int calcul ( int a, int b, boolean bool );
}
printMessage 와 calcul 메소드는 다른 언어로 쓰여질 것이므로 native 라고 붙입니다.
그러므로 정의만 하고 내용은 없다.
이 파일을 우선 자바로 컴파일 한 후..
java -h NativeTest2 를 수행 시키면 C 에서 사용되는 헤더파일( NativeTest2.h ) 가 생깁니다.
헤더 파일의 내용은 다음과 같게 됩니다.
-----------------------NativeTest2.h(자동으로 생성되는 파일임)----------------------
/* DO NOT EDIT THIS FILE - it is machine generated */
#include
/* Header for class NativeTest2 */
#ifndef _Included_NativeTest2
#define _Included_NativeTest2
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: NativeTest2
* Method: printMessage
* Signature: (Ljava/lang/String;)V
*/
JNIEXPORT void JNICALL Java_NativeTest2_printMessage
(JNIEnv *, jclass, jstring);
/*
* Class: NativeTest2
* Method: calcul
* Signature: (IIZ)I
*/
JNIEXPORT jint JNICALL Java_NativeTest2_calcul__IIZ
(JNIEnv *, jclass, jint, jint, jboolean);
/*
* Class: NativeTest2
* Method: calcul
* Signature: ([I)I
*/
#ifdef __cplusplus
}
#endif
#endif
위와 같은 C 헤더 파일이 생깁니다.
여기서 주의 사항을 보자면 C 에서 include 하는것을 보면 jni.h 를 합니다.
그러나 vc++ 6.0 에는 해당 라이브 러리가 없는데, 이것은 자바에서 포함합니다.
Option → Directory 가셔서, 자바홈의 include\win32 디렉토리를 포함시켜야 합니다
예를 들면 c:\jdk1.4\include\win32 를 추가 시킵니다.
그리고 아래와 같이 C 코드를 아래와 같이 작성하는 됩니다.
위에서 라이브 러리는 DisplayMessage2 를 호출하는것으로 되어 있기 때문에,
DisplayMessage2.c 로 만들어야 합니다. 생성 결과는 dll 이어야 하므로 Project 는 dll 을 선택해야 합니다.
------------------------------Displaymessage2.c---------------------------------
#include
#include "NativeTest2.h"
JNIEXPORT void JNICALL Java_NativeTest2_printMessage
(JNIEnv *env, jclass cl , jstring text)
{
const char *asciiString = (*env)->GetStringUTFChars(env,text, 0);
printf("Hello. %s",asciiString);
(*env)->ReleaseStringUTFChars(env,text,asciiString);
}
JNIEXPORT jint JNICALL Java_NativeTest2_calcul
(JNIEnv *env, jclass cl, jint a, jint b, jboolean c)
{
jint d;
if ( c == JNI_TRUE )
{
d = a * b;
}
else
{
d = a / b;
}
return d;
}
jni 를 사용하므로 자체 자료형을 사용한다. jint 는 물론 일반 C 에서 int 와 같다.
int d 라고 선언했는데 jint d 라고 선언하더라도 관계 없다.
const char *asciiString = (*env)->GetStringUTFChars(env,text, 0); 부분은 UTF-8 형으로 변환시키는 작업
해당 파일을 빌드 시키면 dll 파일이 생성되게 된다.
이 dll 을 사용하려면 해당 파일을 windows\system32 폴더에 넣은 후, java NativeTest2 하면 수행이 된다.
public class NativeTest2
{
static
{
System.loadLibrary("DisplayMessage2");
}
public static void main(String []args)
{
System.out.println(calcul(3,4,true));
}
public static native void printMessage(String str);
public static native int calcul ( int a, int b, boolean bool );
}
이걸 다시 보자면 loadLibrary 에서 해당 dll 을 로드 하게 됩니다.
자바가 시스템 쪽에 컨트롤이 안되는데 jni 를 사용하면 이것이 가능하게 된다...
자바의 특성인 포터빌러티가 사라지게 되지만 괜찮다고 봅니다.
많이 응용이 되겠죠... 자바를 이용한 윈도우 서비스 제어도 되겠고....
파일의 속성을 변경한다던지 같은 기능이 되겠죠...
'IT_Programming > Java' 카테고리의 다른 글
[펌] Apache Commons Lang에 관한 내용2 (0) | 2009.01.02 |
---|---|
[펌] Apache Commons Lang에 관한 내용1 (0) | 2009.01.02 |
JInternalFrame 예제 .. MDI 만들기.. (0) | 2008.11.09 |
SWING 주요 컴포넌트 클래스 (0) | 2008.11.09 |
[AWT_CheckBox] 동적으로 객체를 생성하고 제거하기 (0) | 2008.10.16 |