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 requied 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 18 #ifndef DNS_TLS_FRONTEND_H 19 #define DNS_TLS_FRONTEND_H 20 21 #include <arpa/nameser.h> 22 23 #include <atomic> 24 #include <mutex> 25 #include <string> 26 #include <thread> 27 #include <unordered_map> 28 #include <vector> 29 30 #include <android-base/thread_annotations.h> 31 #include <android-base/unique_fd.h> 32 #include <openssl/ssl.h> 33 34 namespace test { 35 36 /* 37 * Simple DNS over TLS reverse proxy that forwards to a UDP backend. 38 * Only handles a single request at a time. 39 */ 40 class DnsTlsFrontend { 41 public: DnsTlsFrontend(const std::string & listen_address,const std::string & listen_service,const std::string & backend_address,const std::string & backend_service)42 DnsTlsFrontend(const std::string& listen_address, const std::string& listen_service, 43 const std::string& backend_address, const std::string& backend_service) 44 : listen_address_(listen_address), 45 listen_service_(listen_service), 46 backend_address_(backend_address), 47 backend_service_(backend_service) {} ~DnsTlsFrontend()48 ~DnsTlsFrontend() { 49 stopServer(); 50 } listen_address()51 const std::string& listen_address() const { 52 return listen_address_; 53 } listen_service()54 const std::string& listen_service() const { 55 return listen_service_; 56 } running()57 bool running() const { 58 return socket_ != -1; 59 } 60 bool startServer(); 61 bool stopServer(); queries()62 int queries() const { return queries_; } clearQueries()63 void clearQueries() { queries_ = 0; } 64 bool waitForQueries(int number, int timeoutMs) const; set_chain_length(int length)65 void set_chain_length(int length) { chain_length_ = length; } 66 // Represents a fingerprint from the middle of the certificate chain. fingerprint()67 const std::vector<uint8_t>& fingerprint() const { return fingerprint_; } 68 69 private: 70 void requestHandler(); 71 bool handleOneRequest(SSL* ssl); 72 73 // Trigger the handler thread to terminate. 74 bool sendToEventFd(); 75 76 // Used in the handler thread for the termination signal. 77 void handleEventFd(); 78 79 std::string listen_address_; 80 std::string listen_service_; 81 std::string backend_address_; 82 std::string backend_service_; 83 bssl::UniquePtr<SSL_CTX> ctx_; 84 // Socket on which the server is listening for a TCP connection with a client. 85 android::base::unique_fd socket_; 86 // Socket used to communicate with the backend DNS server. 87 android::base::unique_fd backend_socket_; 88 // Eventfd used to signal for the handler thread termination. 89 android::base::unique_fd event_fd_; 90 std::atomic<int> queries_ = 0; 91 std::thread handler_thread_ GUARDED_BY(update_mutex_); 92 std::mutex update_mutex_; 93 int chain_length_ = 1; 94 std::vector<uint8_t> fingerprint_; 95 }; 96 97 } // namespace test 98 99 #endif // DNS_TLS_FRONTEND_H 100