1diff --git a/src/lib/ares_init.c b/src/lib/ares_init.c 2index e8902c6..3a5a5f5 100644 3--- a/src/lib/ares_init.c 4+++ b/src/lib/ares_init.c 5@@ -58,6 +58,65 @@ 6 #undef WIN32 /* Redefined in MingW/MSVC headers */ 7 #endif 8 9+ 10+#if OHOS_DNS_PROXY_BY_NETSYS 11+#include <dlfcn.h> 12+#include <stdio.h> 13+ 14+#if DNS_CONFIG_DEBUG 15+#ifndef DNS_CONFIG_PRINT 16+#define DNS_CONFIG_PRINT(fmt, ...) printf("DNS " fmt "\n", ##__VA_ARGS__) 17+#endif 18+#else 19+#define DNS_CONFIG_PRINT(fmt, ...) 20+#endif 21+ 22+#define DNS_SO_PATH "libnetsys_client.z.so" 23+#define OHOS_GET_CONFIG_FUNC_NAME "NetSysGetResolvConf" 24+#define MAX_SERVER_NUM 5 25+#define MAX_SERVER_LENGTH 50 26+ 27+struct resolv_config { 28+ int32_t error; 29+ int32_t timeout_ms; 30+ uint32_t retry_count; 31+ uint32_t non_public; 32+ char nameservers[MAX_SERVER_NUM][MAX_SERVER_LENGTH + 1]; 33+}; 34+ 35+typedef int32_t (*GetConfig)(uint16_t netId, struct resolv_config *config); 36+ 37+static void *open_dns_lib(void) 38+{ 39+ static void *lib = NULL; 40+ if (lib != NULL) { 41+ return lib; 42+ } 43+ lib = dlopen(DNS_SO_PATH, RTLD_LAZY); 44+ if (lib == NULL) { 45+ DNS_CONFIG_PRINT("%s: dlopen %s failed: %s", 46+ __func__, DNS_SO_PATH, dlerror()); 47+ return NULL; 48+ } 49+ return lib; 50+} 51+ 52+static void *load_from_dns_lib(const char *symbol) 53+{ 54+ void *lib_handle = open_dns_lib(); 55+ if (lib_handle == NULL) { 56+ return NULL; 57+ } 58+ 59+ void *sym_addr = dlsym(lib_handle, symbol); 60+ if (sym_addr == NULL) { 61+ DNS_CONFIG_PRINT("%s: loading symbol %s with dlsym failed: %s", 62+ __func__, symbol, dlerror()); 63+ } 64+ return sym_addr; 65+} 66+#endif 67+ 68 static int init_by_options(ares_channel channel, 69 const struct ares_options *options, 70 int optmask); 71@@ -1705,6 +1764,12 @@ static int init_by_resolv_conf(ares_channel channel) 72 int error; 73 int update_domains; 74 const char *resolvconf_path; 75+#if OHOS_DNS_PROXY_BY_NETSYS 76+ int netid = 0; 77+ int ret = 0; 78+ int status_each = -1; 79+ GetConfig func = NULL; 80+#endif 81 82 /* Don't read resolv.conf and friends if we don't have to */ 83 if (ARES_CONFIG_CHECK(channel)) 84@@ -1720,6 +1785,36 @@ static int init_by_resolv_conf(ares_channel channel) 85 resolvconf_path = PATH_RESOLV_CONF; 86 } 87 88+#if OHOS_DNS_PROXY_BY_NETSYS 89+ *(void **) &func = load_from_dns_lib(OHOS_GET_CONFIG_FUNC_NAME); 90+ if (!func) { 91+ DNS_CONFIG_PRINT("%s: loading %s failed, use %s as a fallback", 92+ __func__, OHOS_GET_CONFIG_FUNC_NAME, DNS_RESOLV_CONF_PATH); 93+ goto etc_resolv_conf; 94+ } 95+ struct resolv_config config = {0}; 96+ ret = func(netid, &config); 97+ if (ret < 0) { 98+ DNS_CONFIG_PRINT("__get_resolv_conf OHOS_GET_CONFIG_FUNC_NAME err %d\n", ret); 99+ return ARES_ENONAME; 100+ } 101+ 102+ for (int i = 0; i < MAX_SERVER_NUM; ++i) { 103+ if (config.nameservers[i] == NULL || config.nameservers[i][0] == 0) { 104+ continue; 105+ } 106+ status_each = config_nameserver(&servers, &nservers, config.nameservers[i]); 107+ if (status_each == ARES_SUCCESS) { 108+ status = ARES_SUCCESS; 109+ } 110+ } 111+ 112+ if (status == ARES_SUCCESS && nservers > 0) { 113+ goto get_conf_ok; 114+ } 115+ 116+etc_resolv_conf: 117+#endif 118 fp = fopen(resolvconf_path, "r"); 119 if (fp) { 120 while ((status = ares__read_line(fp, &line, &linesize)) == ARES_SUCCESS) 121@@ -1866,7 +1961,9 @@ static int init_by_resolv_conf(ares_channel channel) 122 ares_free(sortlist); 123 return status; 124 } 125- 126+#if OHOS_DNS_PROXY_BY_NETSYS 127+get_conf_ok: 128+#endif 129 /* If we got any name server entries, fill them in. */ 130 if (servers) 131 { 132