From 690cb7e85ff9dadbfca3e3bc91826161011712f1 Mon Sep 17 00:00:00 2001 From: Richard Maudsley <richard.maudsley@isode.com> Date: Wed, 9 Jul 2014 11:00:13 +0100 Subject: Fix DNS resolution on Android. Test-Information: Try accessing local hosts on a local network and make sure that the local DNS server is queried. Change-Id: Ie594b3eed5772c58d46ec1a4435b2df24d6d8212 diff --git a/3rdParty/Unbound/01_android_fixes.diff b/3rdParty/Unbound/01_android_fixes.diff index c8144ad..40b01e0 100644 --- a/3rdParty/Unbound/01_android_fixes.diff +++ b/3rdParty/Unbound/01_android_fixes.diff @@ -1,13 +1,30 @@ ---- a/3rdParty/Unbound/src/unbound/libunbound/libunbound.c -+++ b/3rdParty/Unbound/src/unbound/libunbound/libunbound.c -@@ -812,6 +812,10 @@ ub_ctx_resolvconf(struct ub_ctx* ctx, char* fname) +diff -rupN ./3rdParty/Unbound/src/unbound/libunbound/libunbound.c ./3rdParty/Unbound/src/unbound/libunbound/libunbound.c +--- ./3rdParty/Unbound/src/unbound/libunbound/libunbound.c 2012-01-12 13:52:38.000000000 +0000 ++++ ./3rdParty/Unbound/src/unbound/libunbound/libunbound.c 2014-07-10 09:21:22.999839053 +0100 +@@ -66,6 +66,10 @@ + #include <iphlpapi.h> + #endif /* UB_ON_WINDOWS */ + ++#ifdef __ANDROID__ ++#include "dns_android.h" ++#endif ++ + struct ub_ctx* + ub_ctx_create(void) + { +@@ -811,6 +815,15 @@ ub_ctx_resolvconf(struct ub_ctx* ctx, ch + char buf[1024]; char* parse, *addr; int r; - +#ifdef __ANDROID__ -+ ub_ctx_set_fwd(ctx, "8.8.8.8"); -+ ub_ctx_set_fwd(ctx, "8.8.4.4"); ++ int i; ++ r = dns_android_server_count(); ++ for (i = 0; i < r; ++i) { ++ if (dns_android_server_get(i, buf, sizeof(buf)) == DNS_ANDROID_SUCCESS) { ++ ub_ctx_set_fwd(ctx, buf); ++ } ++ } +#endif + if(fname == NULL) { #if !defined(UB_ON_WINDOWS) || !defined(HAVE_WINDOWS_H) - fname = "/etc/resolv.conf"; \ No newline at end of file diff --git a/3rdParty/Unbound/SConscript b/3rdParty/Unbound/SConscript index 99cd6a3..b0e6f42 100644 --- a/3rdParty/Unbound/SConscript +++ b/3rdParty/Unbound/SConscript @@ -32,6 +32,7 @@ if env.get("UNBOUND_BUNDLED", False) : myenv.Append(CPPPATH = ["../Ldns/src/ldns", "src/unbound", "."]) if env["target"] == "android" : myenv.Append(CPPPATH = ["src/android/compat", "src/android/config"]) + myenv.Append(CPPPATH = ["src/android/dns"]) myenv.Append(CPPPATH = ["../Ldns/src/android"]) myenv.UseFlags(env["OPENSSL_FLAGS"]) @@ -105,4 +106,5 @@ if env.get("UNBOUND_BUNDLED", False) : ] if env["target"] == "android" : unbound_objects.append("src/android/compat/glob.c") + unbound_objects.append("src/android/dns/dns_android.cpp") env["UNBOUND_OBJECTS"] = myenv.SwiftenObject(unbound_objects) diff --git a/3rdParty/Unbound/src/android/dns/dns_android.cpp b/3rdParty/Unbound/src/android/dns/dns_android.cpp new file mode 100644 index 0000000..4b1c368 --- /dev/null +++ b/3rdParty/Unbound/src/android/dns/dns_android.cpp @@ -0,0 +1,79 @@ +/* + * Copyright (c) 2014 Kevin Smith and Remko Tronçon + * Licensed under the GNU General Public License v3. + * See Documentation/Licenses/GPLv3.txt for more information. + */ + +#include "dns_android.h" +#include <vector> +#include <string> +#include <jni.h> + +JavaVM* javaVM = 0; + +JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM* vm, void* /*aReserved*/) { + javaVM = vm; + return JNI_VERSION_1_6; +} + +std::vector<std::string> get_servers() { + std::vector<std::string> servers; + + JNIEnv* env = 0; + int result = javaVM->GetEnv(reinterpret_cast<void**>(&env), JNI_VERSION_1_6); + if (result == JNI_EDETACHED) { + if (javaVM->AttachCurrentThread(&env, 0) != 0) { + return servers; + } + } else if (result != JNI_OK) { + return servers; + } + + jclass systemProperties = env->FindClass("android.os.SystemProperties"); + if (!systemProperties) { + return servers; + } + + jmethodID method = env->GetStaticMethodID(systemProperties, "get", "(Ljava/lang/String;)Ljava/lang/String;"); + if (!method) { + return servers; + } + + const char* parameters[] = { + "net.dns1", + "net.dns2", + "net.dns3", + "net.dns4" + }; + + for (size_t i = 0; i < sizeof(parameters)/sizeof(*parameters); ++i) { + jstring parameter = env->NewStringUTF(parameters[i]); + jstring value = jstring(env->CallStaticObjectMethod(systemProperties, method, parameter)); + const char* server = env->GetStringUTFChars(value, JNI_FALSE); + if (strcmp(server, "")) { + servers.push_back(server); + } + env->ReleaseStringUTFChars(value, server); + } + + return servers; +} + +size_t dns_android_server_count() { + std::vector<std::string> servers = get_servers(); + return servers.size(); +} + +dns_android_result dns_android_server_get(size_t index, char* buffer, size_t length) { + std::vector<std::string> servers = get_servers(); + if (index >= servers.size()) { + return DNS_ANDROID_FAILURE; /* invalid server index */ + } + + if (length < servers[index].length() + 1) { + return DNS_ANDROID_FAILURE; /* insufficient buffer space */ + } + + strncpy(buffer, servers[index].c_str(), length); + return DNS_ANDROID_SUCCESS; +} diff --git a/3rdParty/Unbound/src/android/dns/dns_android.h b/3rdParty/Unbound/src/android/dns/dns_android.h new file mode 100644 index 0000000..6d38a6f --- /dev/null +++ b/3rdParty/Unbound/src/android/dns/dns_android.h @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2014 Kevin Smith and Remko Tronçon + * Licensed under the GNU General Public License v3. + * See Documentation/Licenses/GPLv3.txt for more information. + */ + +#ifndef __DNS_ANDROID_H__ +#define __DNS_ANDROID_H__ + +#include <string.h> + +#ifdef __cplusplus +extern "C" { +#endif + +/*! Result codes for dns_android_server_get */ +typedef enum { + DNS_ANDROID_SUCCESS = 0, + DNS_ANDROID_FAILURE +} dns_android_result; + +/*! + \brief Retrieve the number of dns servers available. + \return Zero in case of error. +*/ +size_t dns_android_server_count(); + +/*! + \brief Retrieve the address of a dns server + \param index The server index between zero and the number returned by the count function + \param buffer Output buffer into which the null terminated dns server string is written + \param length Size in bytes available in the output buffer + \return Error code. The buffer contents are invalid if an error occurs. +*/ +dns_android_result dns_android_server_get(size_t index, char* buffer, size_t length); + +#ifdef __cplusplus +} +#endif + +#endif // __DNS_ANDROID_H__ -- cgit v0.10.2-6-g49f6