1 /* 2 * Copyright (C) 2017 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef _DNS_DNSTLSTRANSPORT_H 18 #define _DNS_DNSTLSTRANSPORT_H 19 20 #include <future> 21 #include <map> 22 #include <mutex> 23 #include <vector> 24 25 #include <android-base/thread_annotations.h> 26 #include <android-base/unique_fd.h> 27 #include <netdutils/Slice.h> 28 29 #include "DnsTlsQueryMap.h" 30 #include "DnsTlsServer.h" 31 #include "DnsTlsSessionCache.h" 32 #include "IDnsTlsSocket.h" 33 #include "IDnsTlsSocketObserver.h" 34 35 namespace android { 36 namespace net { 37 38 class IDnsTlsSocketFactory; 39 40 // Manages at most one DnsTlsSocket at a time. This class handles socket lifetime issues, 41 // such as reopening the socket and reissuing pending queries. 42 class DnsTlsTransport : public IDnsTlsSocketObserver { 43 public: DnsTlsTransport(const DnsTlsServer & server,unsigned mark,IDnsTlsSocketFactory * _Nonnull factory)44 DnsTlsTransport(const DnsTlsServer& server, unsigned mark, 45 IDnsTlsSocketFactory* _Nonnull factory) 46 : mMark(mark), mServer(server), mFactory(factory) {} 47 ~DnsTlsTransport(); 48 49 using Response = DnsTlsQueryMap::Response; 50 using Result = DnsTlsQueryMap::Result; 51 52 // Given a |query|, this method sends it to the server and returns the result asynchronously. 53 std::future<Result> query(const netdutils::Slice query) EXCLUDES(mLock); 54 55 // Check that a given TLS server is fully working with a specified mark. 56 // This function is used in ResolverController to ensure that we don't enable DNS over TLS 57 // on networks where it doesn't actually work. 58 static bool validate(const DnsTlsServer& server, uint32_t mark); 59 60 int getConnectCounter() const EXCLUDES(mLock); 61 62 // Implement IDnsTlsSocketObserver 63 void onResponse(std::vector<uint8_t> response) override; 64 void onClosed() override EXCLUDES(mLock); 65 66 private: 67 mutable std::mutex mLock; 68 69 DnsTlsSessionCache mCache; 70 DnsTlsQueryMap mQueries; 71 72 const unsigned mMark; // Socket mark 73 const DnsTlsServer mServer; 74 IDnsTlsSocketFactory* _Nonnull const mFactory; 75 76 void doConnect() REQUIRES(mLock); 77 78 // doReconnect is used by onClosed. It runs on the reconnect thread. 79 void doReconnect() EXCLUDES(mLock); 80 std::unique_ptr<std::thread> mReconnectThread GUARDED_BY(mLock); 81 82 // Used to prevent onClosed from starting a reconnect during the destructor. 83 bool mClosing GUARDED_BY(mLock) = false; 84 85 // Sending queries on the socket is thread-safe, but construction/destruction is not. 86 std::unique_ptr<IDnsTlsSocket> mSocket GUARDED_BY(mLock); 87 88 // Send a query to the socket. 89 bool sendQuery(const DnsTlsQueryMap::Query& q) REQUIRES(mLock); 90 91 // The number of times an attempt to connect the nameserver. 92 int mConnectCounter GUARDED_BY(mLock) = 0; 93 }; 94 95 } // end of namespace net 96 } // end of namespace android 97 98 #endif // _DNS_DNSTLSTRANSPORT_H 99