Skip to content

Instantly share code, notes, and snippets.

@valenting
Last active January 31, 2025 10:38
Show Gist options
  • Select an option

  • Save valenting/1aee0a1209da05118a2a3fa24762f5e1 to your computer and use it in GitHub Desktop.

Select an option

Save valenting/1aee0a1209da05118a2a3fa24762f5e1 to your computer and use it in GitHub Desktop.
android_res_nquery
export NDK_HOME=$HOME/.mozbuild/android-ndk-r27c/
export TOOLCHAIN=$NDK_HOME/toolchains/llvm/prebuilt/linux-x86_64
export SYSROOT=$TOOLCHAIN/sysroot
export CC="$TOOLCHAIN/bin/aarch64-linux-android21-clang"
export CXX="$TOOLCHAIN/bin/aarch64-linux-android21-clang++"

$CXX -o dns_query android_res_nquery.cpp -DANDROID -I$SYSROOT/usr/include -L$SYSROOT/usr/lib -static-libstdc++ -ldl
adb push dns_query /data/local/tmp/
adb shell chmod +x /data/local/tmp/dns_query
adb shell /data/local/tmp/dns_query

The output will look something like this:

3
Data is available to read.
Received 61 bytes: 
00 00 00 00 00 00 00 35 86 b7 81 80 00 01 00 01 
00 00 00 00 06 67 6f 6f 67 6c 65 03 63 6f 6d 00 
00 41 00 01 c0 0c 00 41 00 01 00 00 50 5b 00 0d 
00 01 00 00 01 00 06 02 68 32 02 68 33
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <netinet/in.h>
#include <resolv.h>
#include <arpa/nameser.h>
#include <netdb.h> // Include for hstrerror
//#include <android/multinetwork.h>
#include <dlfcn.h>
// #include <jni.h>
#include <stdio.h>
#include <poll.h>
#include <errno.h>
#include <iostream>
#include <iostream>
#include <iomanip>
#include <cstring>
void printHexDump(const char* buffer, size_t length) {
for (size_t i = 0; i < length; ++i) {
if (i > 0 && i % 16 == 0) {
std::cout << std::endl;
}
std::cout << std::hex << std::setw(2) << std::setfill('0') << (static_cast<int>(buffer[i]) & 0xff) << " ";
}
std::cout << std::endl;
}
int main() {
void* handle = dlopen("libandroid_net.so", RTLD_LAZY);
if (!handle) {
fprintf(stderr, "Error: %s\n", dlerror());
return 1; // or handle the error as needed
}
auto android_res_nquery = (int (*)(...)) dlsym(handle, "android_res_nquery");
if (!android_res_nquery) {
fprintf(stderr, "Error: %s\n", dlerror());
dlclose(handle);
return 1; // or handle the error as needed
}
int resp_handle = android_res_nquery(0, "google.com", ns_c_in, 65, 0);
printf("%d\n", resp_handle);
struct pollfd fds;
fds.fd = resp_handle;
fds.events = POLLIN; // Wait for read events
// Wait for an event on the file descriptor
int ret = poll(&fds, 1, -1); // -1 means no timeout
if (ret == -1) {
std::cerr << "Poll error: " << strerror(errno) << '\n';
} else if (ret == 0) {
std::cout << "No data within the timeout period.\n";
} else {
if (fds.revents & POLLIN) {
std::cout << "Data is available to read.\n";
}
}
int rcode;
char answer[3200];
ssize_t bytes_received = recv(resp_handle, answer, 3200 - 1, 0);
if (bytes_received == -1) {
std::cerr << "recv failed: " << strerror(errno) << std::endl;
} else if (bytes_received == 0) {
std::cout << "Connection closed by peer" << std::endl;
} else {
std::cout << "Received " << bytes_received << " bytes: " << answer << std::endl;
}
printHexDump(answer, bytes_received);
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment