1*d9f75844SAndroid Build Coastguard Worker /* 2*d9f75844SAndroid Build Coastguard Worker * Copyright 2021 The WebRTC Project Authors. All rights reserved. 3*d9f75844SAndroid Build Coastguard Worker * 4*d9f75844SAndroid Build Coastguard Worker * Use of this source code is governed by a BSD-style license 5*d9f75844SAndroid Build Coastguard Worker * that can be found in the LICENSE file in the root of the source 6*d9f75844SAndroid Build Coastguard Worker * tree. An additional intellectual property rights grant can be found 7*d9f75844SAndroid Build Coastguard Worker * in the file PATENTS. All contributing project authors may 8*d9f75844SAndroid Build Coastguard Worker * be found in the AUTHORS file in the root of the source tree. 9*d9f75844SAndroid Build Coastguard Worker */ 10*d9f75844SAndroid Build Coastguard Worker 11*d9f75844SAndroid Build Coastguard Worker #ifndef API_WRAPPING_ASYNC_DNS_RESOLVER_H_ 12*d9f75844SAndroid Build Coastguard Worker #define API_WRAPPING_ASYNC_DNS_RESOLVER_H_ 13*d9f75844SAndroid Build Coastguard Worker 14*d9f75844SAndroid Build Coastguard Worker #include <functional> 15*d9f75844SAndroid Build Coastguard Worker #include <memory> 16*d9f75844SAndroid Build Coastguard Worker #include <utility> 17*d9f75844SAndroid Build Coastguard Worker 18*d9f75844SAndroid Build Coastguard Worker #include "absl/memory/memory.h" 19*d9f75844SAndroid Build Coastguard Worker #include "api/async_dns_resolver.h" 20*d9f75844SAndroid Build Coastguard Worker #include "api/sequence_checker.h" 21*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/async_resolver.h" 22*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/async_resolver_interface.h" 23*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/checks.h" 24*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/socket_address.h" 25*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/third_party/sigslot/sigslot.h" 26*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/thread_annotations.h" 27*d9f75844SAndroid Build Coastguard Worker 28*d9f75844SAndroid Build Coastguard Worker // This file defines a DNS resolver that wraps an old-style 29*d9f75844SAndroid Build Coastguard Worker // AsyncResolver. 30*d9f75844SAndroid Build Coastguard Worker // It is part of the conversion to the newer interface, and will go away 31*d9f75844SAndroid Build Coastguard Worker // once conversion is finished. 32*d9f75844SAndroid Build Coastguard Worker // TODO(bugs.webrtc.org/12598): Delete this API. 33*d9f75844SAndroid Build Coastguard Worker 34*d9f75844SAndroid Build Coastguard Worker namespace webrtc { 35*d9f75844SAndroid Build Coastguard Worker 36*d9f75844SAndroid Build Coastguard Worker class WrappingAsyncDnsResolver; 37*d9f75844SAndroid Build Coastguard Worker 38*d9f75844SAndroid Build Coastguard Worker class RTC_EXPORT WrappingAsyncDnsResolverResult 39*d9f75844SAndroid Build Coastguard Worker : public AsyncDnsResolverResult { 40*d9f75844SAndroid Build Coastguard Worker public: WrappingAsyncDnsResolverResult(WrappingAsyncDnsResolver * owner)41*d9f75844SAndroid Build Coastguard Worker explicit WrappingAsyncDnsResolverResult(WrappingAsyncDnsResolver* owner) 42*d9f75844SAndroid Build Coastguard Worker : owner_(owner) {} ~WrappingAsyncDnsResolverResult()43*d9f75844SAndroid Build Coastguard Worker ~WrappingAsyncDnsResolverResult() {} 44*d9f75844SAndroid Build Coastguard Worker 45*d9f75844SAndroid Build Coastguard Worker // Note: Inline declaration not possible, since it refers to 46*d9f75844SAndroid Build Coastguard Worker // WrappingAsyncDnsResolver. 47*d9f75844SAndroid Build Coastguard Worker bool GetResolvedAddress(int family, rtc::SocketAddress* addr) const override; 48*d9f75844SAndroid Build Coastguard Worker int GetError() const override; 49*d9f75844SAndroid Build Coastguard Worker 50*d9f75844SAndroid Build Coastguard Worker private: 51*d9f75844SAndroid Build Coastguard Worker WrappingAsyncDnsResolver* const owner_; 52*d9f75844SAndroid Build Coastguard Worker }; 53*d9f75844SAndroid Build Coastguard Worker 54*d9f75844SAndroid Build Coastguard Worker class RTC_EXPORT WrappingAsyncDnsResolver : public AsyncDnsResolverInterface, 55*d9f75844SAndroid Build Coastguard Worker public sigslot::has_slots<> { 56*d9f75844SAndroid Build Coastguard Worker public: WrappingAsyncDnsResolver(rtc::AsyncResolverInterface * wrapped)57*d9f75844SAndroid Build Coastguard Worker explicit WrappingAsyncDnsResolver(rtc::AsyncResolverInterface* wrapped) 58*d9f75844SAndroid Build Coastguard Worker : wrapped_(absl::WrapUnique(wrapped)), result_(this) {} 59*d9f75844SAndroid Build Coastguard Worker ~WrappingAsyncDnsResolver()60*d9f75844SAndroid Build Coastguard Worker ~WrappingAsyncDnsResolver() override { 61*d9f75844SAndroid Build Coastguard Worker // Workaround to get around the fact that sigslot-using objects can't be 62*d9f75844SAndroid Build Coastguard Worker // destroyed from within their callback: Alert class users early. 63*d9f75844SAndroid Build Coastguard Worker // TODO(bugs.webrtc.org/12651): Delete this class once the sigslot users are 64*d9f75844SAndroid Build Coastguard Worker // gone. 65*d9f75844SAndroid Build Coastguard Worker RTC_CHECK(!within_resolve_result_); 66*d9f75844SAndroid Build Coastguard Worker wrapped_.release()->Destroy(false); 67*d9f75844SAndroid Build Coastguard Worker } 68*d9f75844SAndroid Build Coastguard Worker Start(const rtc::SocketAddress & addr,std::function<void ()> callback)69*d9f75844SAndroid Build Coastguard Worker void Start(const rtc::SocketAddress& addr, 70*d9f75844SAndroid Build Coastguard Worker std::function<void()> callback) override { 71*d9f75844SAndroid Build Coastguard Worker RTC_DCHECK_RUN_ON(&sequence_checker_); 72*d9f75844SAndroid Build Coastguard Worker PrepareToResolve(std::move(callback)); 73*d9f75844SAndroid Build Coastguard Worker wrapped_->Start(addr); 74*d9f75844SAndroid Build Coastguard Worker } 75*d9f75844SAndroid Build Coastguard Worker Start(const rtc::SocketAddress & addr,int family,std::function<void ()> callback)76*d9f75844SAndroid Build Coastguard Worker void Start(const rtc::SocketAddress& addr, 77*d9f75844SAndroid Build Coastguard Worker int family, 78*d9f75844SAndroid Build Coastguard Worker std::function<void()> callback) override { 79*d9f75844SAndroid Build Coastguard Worker RTC_DCHECK_RUN_ON(&sequence_checker_); 80*d9f75844SAndroid Build Coastguard Worker PrepareToResolve(std::move(callback)); 81*d9f75844SAndroid Build Coastguard Worker wrapped_->Start(addr, family); 82*d9f75844SAndroid Build Coastguard Worker } 83*d9f75844SAndroid Build Coastguard Worker result()84*d9f75844SAndroid Build Coastguard Worker const AsyncDnsResolverResult& result() const override { 85*d9f75844SAndroid Build Coastguard Worker RTC_DCHECK_RUN_ON(&sequence_checker_); 86*d9f75844SAndroid Build Coastguard Worker RTC_DCHECK_EQ(State::kResolved, state_); 87*d9f75844SAndroid Build Coastguard Worker return result_; 88*d9f75844SAndroid Build Coastguard Worker } 89*d9f75844SAndroid Build Coastguard Worker 90*d9f75844SAndroid Build Coastguard Worker private: 91*d9f75844SAndroid Build Coastguard Worker enum class State { kNotStarted, kStarted, kResolved }; 92*d9f75844SAndroid Build Coastguard Worker 93*d9f75844SAndroid Build Coastguard Worker friend class WrappingAsyncDnsResolverResult; 94*d9f75844SAndroid Build Coastguard Worker // For use by WrappingAsyncDnsResolverResult wrapped()95*d9f75844SAndroid Build Coastguard Worker rtc::AsyncResolverInterface* wrapped() const { 96*d9f75844SAndroid Build Coastguard Worker RTC_DCHECK_RUN_ON(&sequence_checker_); 97*d9f75844SAndroid Build Coastguard Worker return wrapped_.get(); 98*d9f75844SAndroid Build Coastguard Worker } 99*d9f75844SAndroid Build Coastguard Worker PrepareToResolve(std::function<void ()> callback)100*d9f75844SAndroid Build Coastguard Worker void PrepareToResolve(std::function<void()> callback) { 101*d9f75844SAndroid Build Coastguard Worker RTC_DCHECK_RUN_ON(&sequence_checker_); 102*d9f75844SAndroid Build Coastguard Worker RTC_DCHECK_EQ(State::kNotStarted, state_); 103*d9f75844SAndroid Build Coastguard Worker state_ = State::kStarted; 104*d9f75844SAndroid Build Coastguard Worker callback_ = std::move(callback); 105*d9f75844SAndroid Build Coastguard Worker wrapped_->SignalDone.connect(this, 106*d9f75844SAndroid Build Coastguard Worker &WrappingAsyncDnsResolver::OnResolveResult); 107*d9f75844SAndroid Build Coastguard Worker } 108*d9f75844SAndroid Build Coastguard Worker OnResolveResult(rtc::AsyncResolverInterface * ref)109*d9f75844SAndroid Build Coastguard Worker void OnResolveResult(rtc::AsyncResolverInterface* ref) { 110*d9f75844SAndroid Build Coastguard Worker RTC_DCHECK_RUN_ON(&sequence_checker_); 111*d9f75844SAndroid Build Coastguard Worker RTC_DCHECK(state_ == State::kStarted); 112*d9f75844SAndroid Build Coastguard Worker RTC_DCHECK_EQ(ref, wrapped_.get()); 113*d9f75844SAndroid Build Coastguard Worker state_ = State::kResolved; 114*d9f75844SAndroid Build Coastguard Worker within_resolve_result_ = true; 115*d9f75844SAndroid Build Coastguard Worker callback_(); 116*d9f75844SAndroid Build Coastguard Worker within_resolve_result_ = false; 117*d9f75844SAndroid Build Coastguard Worker } 118*d9f75844SAndroid Build Coastguard Worker 119*d9f75844SAndroid Build Coastguard Worker // The class variables need to be accessed on a single thread. 120*d9f75844SAndroid Build Coastguard Worker SequenceChecker sequence_checker_; 121*d9f75844SAndroid Build Coastguard Worker std::function<void()> callback_ RTC_GUARDED_BY(sequence_checker_); 122*d9f75844SAndroid Build Coastguard Worker std::unique_ptr<rtc::AsyncResolverInterface> wrapped_ 123*d9f75844SAndroid Build Coastguard Worker RTC_GUARDED_BY(sequence_checker_); 124*d9f75844SAndroid Build Coastguard Worker State state_ RTC_GUARDED_BY(sequence_checker_) = State::kNotStarted; 125*d9f75844SAndroid Build Coastguard Worker WrappingAsyncDnsResolverResult result_ RTC_GUARDED_BY(sequence_checker_); 126*d9f75844SAndroid Build Coastguard Worker bool within_resolve_result_ RTC_GUARDED_BY(sequence_checker_) = false; 127*d9f75844SAndroid Build Coastguard Worker }; 128*d9f75844SAndroid Build Coastguard Worker 129*d9f75844SAndroid Build Coastguard Worker } // namespace webrtc 130*d9f75844SAndroid Build Coastguard Worker 131*d9f75844SAndroid Build Coastguard Worker #endif // API_WRAPPING_ASYNC_DNS_RESOLVER_H_ 132