Skip to content

Commit

Permalink
Fix native function setting
Browse files Browse the repository at this point in the history
  • Loading branch information
DonLakeFlyer committed Oct 18, 2015
1 parent 9fcdda7 commit 0c251d7
Show file tree
Hide file tree
Showing 6 changed files with 66 additions and 42 deletions.
1 change: 0 additions & 1 deletion android/src/org/qgroundcontrol/qgchelper/UsbDeviceJNI.java
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,6 @@ public void onNewData(final byte[] dataA, int userDataA)
}
};


// NATIVE C++ FUNCTION THAT WILL BE CALLED IF THE DEVICE IS UNPLUGGED
private static native void nativeDeviceHasDisconnected(int userDataA);
private static native void nativeDeviceException(int userDataA, String messageA);
Expand Down
6 changes: 6 additions & 0 deletions libs/qtandroidserialport/src/qserialport.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1370,6 +1370,12 @@ void QSerialPort::setError(QSerialPort::SerialPortError serialPortError, const Q
emit error(serialPortError);
}

void QSerialPort::setNativeMethods(void)
{
QSerialPortPrivate::setNativeMethods();
}


#include "moc_qserialport.cpp"

QT_END_NAMESPACE
2 changes: 2 additions & 0 deletions libs/qtandroidserialport/src/qserialport.h
Original file line number Diff line number Diff line change
Expand Up @@ -247,6 +247,8 @@ class QSerialPort : public QIODevice

Handle handle() const;

static void setNativeMethods(void);

Q_SIGNALS:
void baudRateChanged(qint32 baudRate, QSerialPort::Directions directions);
void dataBitsChanged(QSerialPort::DataBits dataBits);
Expand Down
77 changes: 37 additions & 40 deletions libs/qtandroidserialport/src/qserialport_android.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,6 @@ QSerialPortPrivate::QSerialPortPrivate(QSerialPort *q)
, isCustomBaudRateSupported(false)
, emittedBytesWritten(false)
, pendingBytesWritten(0)
, hasRegisteredFunctions(false)
, jniDataBits(8)
, jniStopBits(1)
, jniParity(0)
Expand All @@ -115,6 +114,43 @@ QSerialPortPrivate::QSerialPortPrivate(QSerialPort *q)
{
}

void QSerialPortPrivate::setNativeMethods(void)
{
__android_log_print(ANDROID_LOG_INFO, kJTag, "Registering Native Functions");

// REGISTER THE C++ FUNCTION WITH JNI
JNINativeMethod javaMethods[] {
{"nativeDeviceHasDisconnected", "(I)V", reinterpret_cast<void *>(jniDeviceHasDisconnected)},
{"nativeDeviceNewData", "(I[B)V", reinterpret_cast<void *>(jniDeviceNewData)},
{"nativeDeviceException", "(ILjava/lang/String;)V", reinterpret_cast<void *>(jniDeviceException)}
};

QAndroidJniEnvironment jniEnv;
if (jniEnv->ExceptionCheck()) {
jniEnv->ExceptionDescribe();
jniEnv->ExceptionClear();
}

jclass objectClass = jniEnv->FindClass(kJniClassName);
if(!objectClass) {
__android_log_print(ANDROID_LOG_ERROR, kJTag, "Couldn't find class: %s", kJniClassName);
return;
}

jint val = jniEnv->RegisterNatives(objectClass, javaMethods, sizeof(javaMethods) / sizeof(javaMethods[0]));

__android_log_print(ANDROID_LOG_INFO, kJTag, "Native Functions Registered");

if (jniEnv->ExceptionCheck()) {
jniEnv->ExceptionDescribe();
jniEnv->ExceptionClear();
}

if (val < 0) {
__android_log_print(ANDROID_LOG_ERROR, kJTag, "Error registering methods");
}
}

bool QSerialPortPrivate::open(QIODevice::OpenMode mode)
{
rwMode = mode;
Expand All @@ -140,45 +176,6 @@ bool QSerialPortPrivate::open(QIODevice::OpenMode mode)
return false;
}

if (!hasRegisteredFunctions)
{
__android_log_print(ANDROID_LOG_INFO, kJTag, "Registering Native Functions");
// REGISTER THE C++ FUNCTION WITH JNI
JNINativeMethod javaMethods[] {
{"nativeDeviceHasDisconnected", "(I)V", reinterpret_cast<void *>(jniDeviceHasDisconnected)},
{"nativeDeviceNewData", "(I[B)V", reinterpret_cast<void *>(jniDeviceNewData)},
{"nativeDeviceException", "(ILjava/lang/String;)V", reinterpret_cast<void *>(jniDeviceException)}
};

QAndroidJniEnvironment jniEnv;
if (jniEnv->ExceptionCheck()) {
jniEnv->ExceptionDescribe();
jniEnv->ExceptionClear();
}

QAndroidJniObject javaClass(kJniClassName);
if(!javaClass.isValid()) {
__android_log_print(ANDROID_LOG_ERROR, kJTag, "Java class %s not valid", kJniClassName);
return false;
}
jclass objectClass = jniEnv->GetObjectClass(javaClass.object<jobject>());
jint val = jniEnv->RegisterNatives(objectClass, javaMethods, sizeof(javaMethods) / sizeof(javaMethods[0]));
jniEnv->DeleteLocalRef(objectClass);
hasRegisteredFunctions = true;
__android_log_print(ANDROID_LOG_INFO, kJTag, "Native Functions Registered");

if (jniEnv->ExceptionCheck()) {
jniEnv->ExceptionDescribe();
jniEnv->ExceptionClear();
}

if(val < 0) {
__android_log_print(ANDROID_LOG_ERROR, kJTag, "Error registering methods");
q_ptr->setError(QSerialPort::OpenError);
return false;
}
}

__android_log_print(ANDROID_LOG_INFO, kJTag, "Calling Java getDeviceHandle");
cleanJavaException();
descriptor = QAndroidJniObject::callStaticMethod<jint>(
Expand Down
3 changes: 2 additions & 1 deletion libs/qtandroidserialport/src/qserialport_android_p.h
Original file line number Diff line number Diff line change
Expand Up @@ -108,10 +108,11 @@ class QSerialPortPrivate : public QSerialPortPrivateData

qint64 pendingBytesWritten;

static void setNativeMethods(void);

private:
QIODevice::OpenMode rwMode;
int deviceId;
bool hasRegisteredFunctions;
int jniDataBits;
int jniStopBits;
int jniParity;
Expand Down
19 changes: 19 additions & 0 deletions src/main.cc
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,25 @@ int WindowsCrtReportHook(int reportType, char* message, int* returnValue)

#endif

#ifdef __android__
#include <jni.h>
#include "qserialport.h"

jint JNI_OnLoad(JavaVM* vm, void* reserved)
{
Q_UNUSED(reserved);

JNIEnv* env;
if (vm->GetEnv(reinterpret_cast<void**>(&env), JNI_VERSION_1_6) != JNI_OK) {
return -1;
}

QSerialPort::setNativeMethods();

return JNI_VERSION_1_6;
}
#endif

/**
* @brief Starts the application
*
Expand Down

0 comments on commit 0c251d7

Please sign in to comment.