// Copyright 2012 The Chromium Authors // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #ifndef NET_DNS_ADDRESS_SORTER_POSIX_H_ #define NET_DNS_ADDRESS_SORTER_POSIX_H_ #include #include #include "base/containers/unique_ptr_adapters.h" #include "base/memory/raw_ptr.h" #include "base/threading/thread_checker.h" #include "net/base/ip_address.h" #include "net/base/net_export.h" #include "net/base/network_change_notifier.h" #include "net/dns/address_sorter.h" #include "net/socket/datagram_client_socket.h" namespace net { class ClientSocketFactory; // This implementation uses explicit policy to perform the sorting. It is not // thread-safe and always completes synchronously. class NET_EXPORT_PRIVATE AddressSorterPosix : public AddressSorter, public NetworkChangeNotifier::IPAddressObserver { public: // Generic policy entry. struct PolicyEntry { // IPv4 addresses must be mapped to IPv6. unsigned char prefix[IPAddress::kIPv6AddressSize]; unsigned prefix_length; unsigned value; }; typedef std::vector PolicyTable; enum AddressScope { SCOPE_UNDEFINED = 0, SCOPE_NODELOCAL = 1, SCOPE_LINKLOCAL = 2, SCOPE_SITELOCAL = 5, SCOPE_ORGLOCAL = 8, SCOPE_GLOBAL = 14, }; struct SourceAddressInfo { // Values read from policy tables. AddressScope scope = SCOPE_UNDEFINED; unsigned label = 0; // Values from the OS, matter only if more than one source address is used. size_t prefix_length = 0; bool deprecated = false; // vs. preferred RFC4862 bool home = false; // vs. care-of RFC6275 bool native = false; }; typedef std::map SourceAddressMap; explicit AddressSorterPosix(ClientSocketFactory* socket_factory); AddressSorterPosix(const AddressSorterPosix&) = delete; AddressSorterPosix& operator=(const AddressSorterPosix&) = delete; ~AddressSorterPosix() override; // AddressSorter: void Sort(const std::vector& endpoints, CallbackType callback) const override; private: friend class AddressSorterPosixTest; class SortContext; // NetworkChangeNotifier::IPAddressObserver: void OnIPAddressChanged() override; // Fills |info| with values for |address| from policy tables. void FillPolicy(const IPAddress& address, SourceAddressInfo* info) const; void FinishedSort(SortContext* sort_context) const; // Mutable to allow using default values for source addresses which were not // found in most recent OnIPAddressChanged. mutable SourceAddressMap source_map_; raw_ptr socket_factory_; PolicyTable precedence_table_; PolicyTable label_table_; PolicyTable ipv4_scope_table_; // SortContext stores data for an outstanding Sort() that is completing // asynchronously. Mutable to allow pushing a new SortContext when Sort is // called. Since Sort can be called multiple times, a container is necessary // to track different SortContexts. mutable std::set, base::UniquePtrComparator> sort_contexts_; THREAD_CHECKER(thread_checker_); }; } // namespace net #endif // NET_DNS_ADDRESS_SORTER_POSIX_H_