r16b - Android NDK/JNI: referencia no definida a la función definida en el archivo de encabezado personalizado
ndk root (2)
Simplemente haciendo su C ++ nativo - código entre
extern "C" {
your code
}
Es algo que no siempre funcionará necesariamente, como puede comprobar here .
Intenta agregar al archivo Android.mk:
LOCAL_ALLOW_UNDEFINED_SYMBOLS := true
Aquí encontrarás más info respecto.
Utilizando JNI, estoy intentando escribir un método C ++ nativo para el NDK de Android que realiza una llamada a una función de C definida en un archivo de encabezado personalizado. Sin embargo, recibo un error de referencia no definido para mi llamada a la función C.
Aquí está mi código C ++ que realiza una llamada a la función C y devuelve su resultado a Java como un jstring:
#include <jni.h>
#include "gesture_detector.h"
JNIEXPORT jstring JNICALL Java_com_example_bmtitest_JavaAbstractionLayer_callGestureAnalysis(JNIEnv *env, jobject obj, jfloat previousX, jfloat previousY, jfloat currentX, jfloat currentY) {
return env->NewStringUTF(gestureAnalysis(previousX, previousY, currentX, currentY));
}
Aquí está mi función C:
#include <stdio.h>
#include "gesture_detector.h"
//implemented from gesture_detector.h
const char* gestureAnalysis(float previousX, float previousY, float currentX, float currentY)
{
float xOffset = currentX - previousX;
float yOffset = currentY - previousY;
if(xOffset == 0 && yOffset == 0)
{
return "TAP";
}
return "0";
}
Aquí está mi código de Android.mk:
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := gestureDetector
LOCAL_SRC_FILES := gestureDetector.c NativeAbstractionLayer.cpp
LOCAL_LDLIBS := -landroid
include $(BUILD_SHARED_LIBRARY)
Aparentemente, parece que la definición de la función definida en el archivo de encabezado personalizado ( gesture_detector.h
) no se encuentra. Creo que puede ser un problema en mi archivo Android.mk.
¿Alguien podría decirme qué estoy haciendo mal aquí?
Un error de "referencia no definida" proviene del vinculador . Su archivo de cabecera sólo satisfizo el compilador.
Sin embargo, ya que está mezclando C y C ++, su problema es probablemente la manipulación de nombres . Básicamente, debe decirle al compilador de C ++ que la función a la que está intentando llamar fue creada por un compilador de C en lugar de uno de C ++, por lo que no tiene códigos de tipo de argumento injertados en su nombre. En este momento no lo sabe, por lo que está tratando de llamar a la función con un nombre decorado de estilo C ++ que difiere del nombre en C simple de la función que el enlazador realmente tiene disponible.
Agregue esto al comienzo de su archivo gestor_detector.h:
#ifdef __cplusplus
extern "C" {
#endif
Y esto al final.
#ifdef __cplusplus
}
#endif
Y hacer una reconstrucción limpia.
Si su lógica jni encolada es tan trivial como la versión presentada aquí, cambiar a una versión C de eso también podría ser una opción, pero tenga en cuenta que la sintaxis jni es diferente en C y C ++, por lo que no puede simplemente cambiar la extensión del archivo. .