/* DO NOT EDIT THIS FILE - it is machine generated */
#include "JNIInclude/jni.h"
/* Header for class pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI */
#ifndef _Included_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
#define _Included_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: getLastError
* Signature: ()J
*/
JNIEXPORT jlong JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_getLastError
(JNIEnv *, jclass);
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: createFile
* Signature: ([BZ)J
*/
JNIEXPORT jlong JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_createFile
(JNIEnv *, jclass, jbyteArray, jboolean);
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: closeHandle
* Signature: (J)Z
*/
JNIEXPORT jboolean JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_closeHandle
(JNIEnv *, jclass, jlong);
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: setupComm
* Signature: (JJJ)Z
*/
JNIEXPORT jboolean JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_setupComm
(JNIEnv *, jclass, jlong, jlong, jlong);
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: setCommTimeouts
* Signature: (JJJJJJ)Z
*/
JNIEXPORT jboolean JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_setCommTimeouts
(JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jlong);
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: setCommState
* Signature: (JJJJJ)Z
*/
JNIEXPORT jboolean JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_setCommState
(JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong);
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: purgeComm
* Signature: (J)Z
*/
JNIEXPORT jboolean JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_purgeComm
(JNIEnv *, jclass, jlong);
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: readFile
* Signature: (J[B)I
*/
JNIEXPORT jint JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_readFile
(JNIEnv *, jclass, jlong, jbyteArray);
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: writeFile
* Signature: (J[BI)I
*/
JNIEXPORT jint JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_writeFile
(JNIEnv *, jclass, jlong, jbyteArray, jint);
#ifdef __cplusplus
}
#endif
#endif
#include <malloc.h>
#include <windows.h>
#include "pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI.h"
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: getLastError
* Signature: ()J
*/
JNIEXPORT jlong JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_getLastError
(JNIEnv*, jclass) {
return (unsigned long long) GetLastError();
}
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: createFile
* Signature: ([BZ)J
*/
JNIEXPORT jlong JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_createFile
(JNIEnv *jEnv, jclass jCls, jbyteArray jPortName, jboolean isOverlapped) {
int len = jEnv->GetArrayLength(jPortName);
char *buf = (char*) malloc(len);
jEnv->GetByteArrayRegion(jPortName, 0, len, (jbyte*) buf);
//异步通信不支持频繁开关操作,不能满足Java版LaserpenUtil的快速自动重启机制的要求,因此只能使用同步通信。
HANDLE handle = CreateFile(buf, GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING,
isOverlapped ? (FILE_ATTRIBUTE_NORMAL | FILE_FLAG_OVERLAPPED) : 0, NULL);
free(buf);
return (jlong) handle;
}
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: closeHandle
* Signature: (J)Z
*/
JNIEXPORT jboolean JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_closeHandle
(JNIEnv *jEnv, jclass jCls, jlong handle) {
return CloseHandle((HANDLE) handle);
}
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: setupComm
* Signature: (JJJ)Z
*/
JNIEXPORT jboolean JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_setupComm
(JNIEnv *jEnv, jclass jCls, jlong handle, jlong inBuffer, jlong outBuffer) {
return SetupComm((HANDLE) handle, inBuffer, outBuffer);
}
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: setCommTimeouts
* Signature: (JJJJJJ)Z
*/
JNIEXPORT jboolean JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_setCommTimeouts
(JNIEnv *jEnv, jclass jCls, jlong handle, jlong ReadIntervalTimeout, jlong ReadTotalTimeoutConstant,
jlong ReadTotalTimeoutMultiplier, jlong WriteTotalTimeoutConstant, jlong WriteTotalTimeoutMultiplier) {
COMMTIMEOUTS timeouts;
timeouts.ReadIntervalTimeout = ReadIntervalTimeout;
timeouts.ReadTotalTimeoutConstant = ReadTotalTimeoutConstant;
timeouts.ReadTotalTimeoutMultiplier = ReadTotalTimeoutMultiplier;
timeouts.WriteTotalTimeoutConstant = WriteTotalTimeoutConstant;
timeouts.WriteTotalTimeoutMultiplier = WriteTotalTimeoutMultiplier;
return SetCommTimeouts((HANDLE) handle, &timeouts);
}
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: setCommState
* Signature: (JJJJJ)Z
*/
JNIEXPORT jboolean JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_setCommState
(JNIEnv *jEnv, jclass jCls, jlong handle, jlong BaudRate, jlong ByteSize, jlong Parity, jlong StopBits) {
DCB dcb;
GetCommState((HANDLE) handle, &dcb);
dcb.BaudRate = BaudRate;
dcb.ByteSize = ByteSize;
dcb.Parity = Parity;
dcb.fBinary = TRUE;
dcb.fParity = TRUE;
dcb.StopBits = StopBits;
return SetCommState((HANDLE) handle, &dcb);
}
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: purgeComm
* Signature: (J)Z
*/
JNIEXPORT jboolean JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_purgeComm
(JNIEnv *jEnv, jclass jCls, jlong handle) {
return PurgeComm((HANDLE) handle, PURGE_TXABORT | PURGE_RXABORT | PURGE_TXCLEAR | PURGE_RXCLEAR);
}
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: readFile
* Signature: (J[B)I
*/
JNIEXPORT jint JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_readFile
(JNIEnv *jEnv, jclass jCls, jlong handle, jbyteArray jBuffer) {
int bufLen = jEnv->GetArrayLength(jBuffer);
char *buf = (char*) malloc(bufLen);
//jEnv->GetByteArrayRegion(jBuffer, 0, bufLen, (jbyte*)buf);
DWORD recvLen;
DWORD dwErrorFlags;
COMSTAT ComStat;
OVERLAPPED ov;
ClearCommError((HANDLE) handle, &dwErrorFlags, &ComStat);
memset(&ov, 0, sizeof(ov));
if (!ReadFile((HANDLE) handle, buf, bufLen, &recvLen, &ov)) {
if (GetLastError() == ERROR_IO_PENDING) {
GetOverlappedResult((HANDLE) handle, &ov, &recvLen, TRUE);
jEnv->SetByteArrayRegion(jBuffer, 0, recvLen, (jbyte*) buf);
} else {
recvLen = -1;
}
} else {
jEnv->SetByteArrayRegion(jBuffer, 0, recvLen, (jbyte*) buf);
}
free(buf);
return recvLen;
}
/*
* Class: pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_JNI
* Method: writeFile
* Signature: (J[BI)I
*/
JNIEXPORT jint JNICALL Java_pers_laserpen_util_communication_serialPort_NativeSerialPortUtils_1JNI_writeFile
(JNIEnv *jEnv, jclass jCls, jlong handle, jbyteArray jBuffer, jint length) {
int bufLen = jEnv->GetArrayLength(jBuffer);
char *buf = (char*) malloc(bufLen);
jEnv->GetByteArrayRegion(jBuffer, 0, bufLen, (jbyte*) buf);
DWORD sendLen;
DWORD dwErrorFlags;
COMSTAT ComStat;
OVERLAPPED ov;
ClearCommError((HANDLE) handle, &dwErrorFlags, &ComStat);
memset(&ov, 0, sizeof(ov));
if (!WriteFile((HANDLE) handle, buf, length, &sendLen, &ov)) {
if (GetLastError() == ERROR_IO_PENDING) {
GetOverlappedResult((HANDLE) handle, &ov, &sendLen, TRUE);
} else {
sendLen = -1;
}
}
//jEnv->SetByteArrayRegion(jBuffer, 0, recvLen, (jbyte*)buf);
free(buf);
return sendLen;
}
#ifdef __cplusplus
}
#endif
package pers.laserpen.util.communication.serialPort;
/**
* javac -h 需要像编译class一样把所有引用的java文件都编译,为了防止引用java文件,把jni部分单独放在一个类中。
*
* @author Laserpen
*/
class NativeSerialPortUtils_JNI {
native static long getLastError();
native static long createFile(byte[] portName, boolean isOverlapped);
native static boolean closeHandle(long handle);
native static boolean setupComm(long handle, long inBuffer, long outBuffer);
native static boolean setCommTimeouts(long handle, long readIntervalTimeout, long readTotalTimeoutConstant,
long readTotalTimeoutMultiplier, long writeTotalTimeoutConstant, long writeTotalTimeoutMultiplier);
native static boolean setCommState(long handle, long baudRate, long byteSize, long parity, long stopBits);
native static boolean purgeComm(long handle);
native static int readFile(long handle, byte[] buffer);
native static int writeFile(long handle, byte[] buffer, int length);
}
package pers.laserpen.util.communication.serialPort;
import pers.laserpen.util.string.ENCODING;
public abstract class NativeSerialPortUtils extends NativeSerialPortUtils_JNI {
public static final int NOPARITY = 0;
public static final int ODDPARITY = 1;
public static final int EVENPARITY = 2;
public static final int MARKPARITY = 3;
public static final int SPACEPARITY = 4;
public static final int ONESTOPBIT = 0;
public static final int ONE5STOPBITS = 1;
public static final int TWOSTOPBITS = 2;
public static final int CBR_110 = 110;
public static final int CBR_300 = 300;
public static final int CBR_600 = 600;
public static final int CBR_1200 = 1200;
public static final int CBR_2400 = 2400;
public static final int CBR_4800 = 4800;
public static final int CBR_9600 = 9600;
public static final int CBR_14400 = 14400;
public static final int CBR_19200 = 19200;
public static final int CBR_38400 = 38400;
public static final int CBR_56000 = 56000;
public static final int CBR_57600 = 57600;
public static final int CBR_115200 = 115200;
public static final int CBR_128000 = 128000;
public static final int CBR_256000 = 256000;
public static final long getLastErrorCode() {
return getLastError();
}
public static final long openCom(int com, boolean isOverlapped) {
String portStr = "\\\\.\\COM" + com + "\0";// C和C++无法识别byte[]的长度,需要添加一个0字符。
return createFile(portStr.getBytes(ENCODING.US_ASCII()), isOverlapped);
}
public static final boolean closeCom(long handle) {
return closeHandle(handle);
}
public static boolean setBuffer(long handle, int inBuffer, int outBuffer) {
return setupComm(handle, inBuffer, outBuffer);
}
public static boolean setSimpleTimeout(long handle) {
return setCommTimeouts(handle, -1, 0, 0, 0, 0);
}
public static boolean setTimeout(long handle, long readIntervalTimeout, long readTotalTimeoutConstant,
long readTotalTimeoutMultiplier, long writeTotalTimeoutConstant, long writeTotalTimeoutMultiplier) {
return setCommTimeouts(handle, readIntervalTimeout, readTotalTimeoutConstant, readTotalTimeoutMultiplier,
writeTotalTimeoutConstant, writeTotalTimeoutMultiplier);
}
public static final boolean setState(long handle, long baudRate, ByteSize byteSize, Parity parity,
StopBits stopBits) {
return setCommState(handle, baudRate, byteSize.getFlag(), parity.getFlag(), stopBits.getFlag());
}
public static final boolean ready(long handle) {
return purgeComm(handle);
}
public static final int read(long handle, byte[] buffer) {
return readFile(handle, buffer);
}
public static final int write(long handle, byte[] buffer, int length) {
return writeFile(handle, buffer, length);
}
}
重叠方式打开时,五个超时参数的设置都不能小于0,否则即使成功打开串口,也无法操作。推荐用1,0,0,0,0,然后在应用层处理数据拼接。
需要自己设计的原因是在Win10上已经没有可用的Java串口包了。