Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit fc73d4d9 authored by Bruce Chen's avatar Bruce Chen Committed by android-build-merger
Browse files

Merge "Add resolv_callback_unit_test" am: cbc280ac

am: fe3afd63

Change-Id: If0371c155bdf355c59d5942994b5fe87c07227c4
parents f858d732 fe3afd63
Loading
Loading
Loading
Loading
+5 −0
Original line number Diff line number Diff line
@@ -166,6 +166,7 @@ cc_test {
    defaults: ["netd_defaults"],
    srcs: [
        "resolv_cache_unit_test.cpp",
        "resolv_callback_unit_test.cpp",
        "resolv_tls_unit_test.cpp",
        "resolv_unit_test.cpp",
        "DnsStatsTest.cpp",
@@ -188,6 +189,10 @@ cc_test {
        "libnetd_test_resolv_utils",
        "libnetdutils",
        "libprotobuf-cpp-lite",
        "libstatslog_resolv",
        "libstatssocket",
        "libsysutils",
        "libutils",
        "server_configurable_flags",
        "stats_proto",
    ],
+161 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2019 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#define LOG_TAG "resolv_callback_unit_test"

#include <android-base/properties.h>
#include <gtest/gtest.h>

#include "DnsResolver.h"
#include "getaddrinfo.h"
#include "resolv_cache.h"
#include "tests/resolv_test_utils.h"

namespace android::net {

using android::net::NetworkDnsEventReported;
using android::netdutils::ScopedAddrinfo;

// Use maximum reserved appId for applications to avoid conflict with existing uids.
const int TEST_UID = 99999;
// Use testUid to make sure TagSocketCallback is called.
static int testUid = 0;

bool isApiLevelSupported(size_t requiredVersion) {
    if (android::base::GetUintProperty<uint64_t>("ro.build.version.sdk", 0) >= requiredVersion)
        return true;
    else
        return false;
}

#define SKIP_IF_APILEVEL_LESS_THAN(version)                                        \
    do {                                                                           \
        if (!isApiLevelSupported(version)) {                                       \
            GTEST_LOG_(INFO) << "Skip. Required API version: " << version << "\n"; \
            return;                                                                \
        }                                                                          \
    } while (0)

void getNetworkContextCallback(uint32_t, uint32_t, android_net_context*) {
    // No-op
}

bool checkCallingPermissionCallback(const char*) {
    // No-op
    return true;
}

void logCallback(const char*) {
    // No-op
}

int tagSocketCallback(int, uint32_t, uid_t uid, pid_t) {
    testUid = uid;
    return true;
}

bool evaluateDomainNameCallback(const android_net_context&, const char*) {
    // No-op
    return true;
}

void initDnsResolverCallbacks() {
    ResolverNetdCallbacks callbacks = {
            .check_calling_permission = &checkCallingPermissionCallback,
            .get_network_context = &getNetworkContextCallback,
            .log = &logCallback,
            .tagSocket = &tagSocketCallback,
            .evaluate_domain_name = &evaluateDomainNameCallback,
    };
    // It returns fail since socket 'dnsproxyd' has been occupied.
    // But the callback funtions is configured successfully and can
    // be tested when running unit test cases.
    resolv_init(&callbacks);
}

void resetDnsResolverCallbacks() {
    ResolverNetdCallbacks callbacks = {
            .check_calling_permission = nullptr,
            .get_network_context = nullptr,
            .log = nullptr,
            .tagSocket = nullptr,
            .evaluate_domain_name = nullptr,
    };
    resolv_init(&callbacks);
}

void resetCallbackParams() {
    testUid = 0;
}

class CallbackTest : public ::testing::Test {
  protected:
    void SetUp() override {
        initDnsResolverCallbacks();
        // Create cache for test
        android::net::gDnsResolv->resolverCtrl.createNetworkCache(TEST_NETID);
    }

    void TearDown() override {
        // Reset related parameters and callback functions.
        resetCallbackParams();
        resetDnsResolverCallbacks();
        // Delete cache for test
        android::net::gDnsResolv->resolverCtrl.destroyNetworkCache(TEST_NETID);
    }

    int SetResolvers() {
        const std::vector<std::string> servers = {test::kDefaultListenAddr};
        const std::vector<std::string> domains = {"example.com"};
        const res_params params = {
                .sample_validity = 300,
                .success_threshold = 25,
                .min_samples = 8,
                .max_samples = 8,
                .base_timeout_msec = 1000,
                .retry_count = 2,
        };
        return resolv_set_nameservers(TEST_NETID, servers, domains, params);
    }

    const android_net_context mNetcontext = {
            .app_netid = TEST_NETID,
            .app_mark = MARK_UNSET,
            .dns_netid = TEST_NETID,
            .dns_mark = MARK_UNSET,
            .uid = TEST_UID,
    };
};

TEST_F(CallbackTest, tagSocketCallback) {
    // tagSocketCallback is used when ro.build.version.sdk >=30.
    // If ro.build.version.sdk < 30, don't run this test case.
    SKIP_IF_APILEVEL_LESS_THAN(30);
    test::DNSResponder dns;
    dns.addMapping(kHelloExampleCom, ns_type::ns_t_a, kHelloExampleComAddrV4);
    ASSERT_TRUE(dns.startServer());
    EXPECT_EQ(SetResolvers(), 0);

    addrinfo* result = nullptr;
    const addrinfo hints = {.ai_family = AF_INET};
    NetworkDnsEventReported event;
    // tagSocketCallback will be called.
    const int rv = resolv_getaddrinfo("hello", nullptr, &hints, &mNetcontext, &result, &event);
    ScopedAddrinfo result_cleanup(result);
    EXPECT_EQ(testUid, TEST_UID);
    EXPECT_EQ(rv, 0);
}
}  // end of namespace android::net