I am having a problem linking C libraries in my Android project using Android NDK r8b. I built the cURL library (without SSL) using the toolchain for ARM, and he provided me with the file libcurl.a and libcurl.so.4.2.0. I also created a C file to provide functions for Java code and use the cURL library.
Android.mk
LOCAL_PATH:= $(call my-dir) include $(CLEAR_VARS) LOCAL_MODULE:= libcurl LOCAL_SRC_FILES := libcurl.a include $(PREBUILT_STATIC_LIBRARY) include $(CLEAR_VARS) LOCAL_MODULE := curljni LOCAL_SRC_FILES := curljni.c LOCAL_STATIC_LIBRARIES := libcurl include $(BUILD_SHARED_LIBRARY)
and now my C file
#include <string.h> #include <jni.h> #include <stdio.h> #include <stdlib.h> jstring Java_test_curljni_MainActivity_stringFromJNI(JNIEnv* env, jobject thiz) { CURL *curl; CURLcode ...... }
When I try to build using the ndk-build command from my project folder, an output error occurs here:
Compile thumb : curljni <= curljni.c jni/curljni.c: In function 'Java_test_curljni_MainActivity_stringFromJNI': jni/curljni.c:8:3: error: unknown type name 'CURL' jni/curljni.c:9:3: error: unknown type name 'CURLcode' jni/curljni.c:11:8: warning: assignment makes pointer from integer without a cast [enabled by default] jni/curljni.c:13:28: error: 'CURLOPT_URL' undeclared (first use in this function) jni/curljni.c:13:28: note: each undeclared identifier is reported only once for each function it appears in /cygdrive/c/android-ndk-r8b/build/core/build-binary.mk:252: recipe for target `obj/local/armeabi/objs/curljni/curljni.o' failed make: *** [obj/local/armeabi/objs/curljni/curljni.o] Error 1
I tried a lot of things in the Android.mk file, nothing successful. Using PREBUILT_SHARED_LIBRARY does not help, because it only requires a .so file and changing the extension from .so.4.2.0 to .so just tells me that the format is not supported when creating ...
One thing, I'm not sure if I should include headers in my C file, but when I do this, of course, it does not find them.
As a side note, when I create only the curl library declared in my Android.mk file (the shared library with the C file is excluded), nothing is created in the libs folder!
Thanks in advance for your help!
EDIT ::
Actually it worked mbrenon (I tried it millions of times and now it works, I donβt know what else), but now I have
c:/android-ndk-r8b/toolchains/arm-linux-androideabi-4.6/prebuilt/windows/bin/../lib/gcc/arm-linux-androideabi/4.6.x-google/../../../. ./arm-linux-androideabi/bin/ld.exe: cannot find ./obj/local/armeabi/libcurl.a: Permission denied
I am using Cygwin, maybe that's why I am facing permission problems? I manage to get around it when .so and .a are created, returning a permission error, chmod on it and running ndk-build again, but that seems a little rude! Plus now none of my waving functions can be achieved ("undefined reference to (function)").
$ ../../../ndk-build SharedLibrary : libcurljni.so ./obj/local/armeabi/objs/curljni/curljni.o: In function `Java_test_curljni_MainActivity_stringFromJNI': C:\android-ndk-r8b\apps\curljni\project/jni/curljni.c:12: undefined reference to `curl_easy_init' C:\android-ndk-r8b\apps\curljni\project/jni/curljni.c:14: undefined reference to `curl_easy_setopt' C:\android-ndk-r8b\apps\curljni\project/jni/curljni.c:15: undefined reference to `curl_easy_perform' C:\android-ndk-r8b\apps\curljni\project/jni/curljni.c:17: undefined reference to `curl_easy_cleanup' collect2: ld returned 1 exit status /cygdrive/c/android-ndk-r8b/build/core/build-binary.mk:378: recipe for target `obj/local/armeabi/libcurljni.so' failed make: *** [obj/local/armeabi/libcurljni.so] Error 1
and my curljni.c next
jstring Java_test_curljni_MainActivity_stringFromJNI(JNIEnv* env, jobject thiz) { CURL *curl; CURLcode res; char buffer[10]; curl = curl_easy_init(); if(curl) { curl_easy_setopt(curl, CURLOPT_URL, "yahoo.com"); res = curl_easy_perform(curl); curl_easy_cleanup(curl); if(res == 0) return (*env)->NewStringUTF(env, "0 response"); else sprintf(buffer,"code: %i",res); return (*env)->NewStringUTF(env, buffer); } else { return (*env)->NewStringUTF(env, "no curl"); } }
I made sure that every required function is declared in curl.h