1*6777b538SAndroid Build Coastguard Worker // Copyright 2016 The Chromium Authors 2*6777b538SAndroid Build Coastguard Worker // Use of this source code is governed by a BSD-style license that can be 3*6777b538SAndroid Build Coastguard Worker // found in the LICENSE file. 4*6777b538SAndroid Build Coastguard Worker 5*6777b538SAndroid Build Coastguard Worker #ifndef NET_SOCKET_FUZZED_SOCKET_H_ 6*6777b538SAndroid Build Coastguard Worker #define NET_SOCKET_FUZZED_SOCKET_H_ 7*6777b538SAndroid Build Coastguard Worker 8*6777b538SAndroid Build Coastguard Worker #include <stdint.h> 9*6777b538SAndroid Build Coastguard Worker 10*6777b538SAndroid Build Coastguard Worker #include "base/memory/raw_ptr.h" 11*6777b538SAndroid Build Coastguard Worker #include "base/memory/weak_ptr.h" 12*6777b538SAndroid Build Coastguard Worker #include "base/strings/string_piece.h" 13*6777b538SAndroid Build Coastguard Worker #include "net/base/completion_once_callback.h" 14*6777b538SAndroid Build Coastguard Worker #include "net/base/ip_endpoint.h" 15*6777b538SAndroid Build Coastguard Worker #include "net/base/net_errors.h" 16*6777b538SAndroid Build Coastguard Worker #include "net/log/net_log_with_source.h" 17*6777b538SAndroid Build Coastguard Worker #include "net/socket/transport_client_socket.h" 18*6777b538SAndroid Build Coastguard Worker #include "net/traffic_annotation/network_traffic_annotation.h" 19*6777b538SAndroid Build Coastguard Worker 20*6777b538SAndroid Build Coastguard Worker class FuzzedDataProvider; 21*6777b538SAndroid Build Coastguard Worker 22*6777b538SAndroid Build Coastguard Worker namespace net { 23*6777b538SAndroid Build Coastguard Worker 24*6777b538SAndroid Build Coastguard Worker class IPEndPoint; 25*6777b538SAndroid Build Coastguard Worker class IOBuffer; 26*6777b538SAndroid Build Coastguard Worker class NetLog; 27*6777b538SAndroid Build Coastguard Worker 28*6777b538SAndroid Build Coastguard Worker // A StreamSocket that uses a FuzzedDataProvider to generate responses. Writes 29*6777b538SAndroid Build Coastguard Worker // can succeed synchronously or asynchronously, can write some or all of the 30*6777b538SAndroid Build Coastguard Worker // provided data, and can fail with several different errors. Reads can do the 31*6777b538SAndroid Build Coastguard Worker // same, but the read data is also generated from the FuzzedDataProvider. The 32*6777b538SAndroid Build Coastguard Worker // number of bytes written/read from a single call is currently capped at 255 33*6777b538SAndroid Build Coastguard Worker // bytes. 34*6777b538SAndroid Build Coastguard Worker // 35*6777b538SAndroid Build Coastguard Worker // Reads and writes are executed independently of one another, so to guarantee 36*6777b538SAndroid Build Coastguard Worker // the fuzzer behaves the same across repeated runs with the same input, the 37*6777b538SAndroid Build Coastguard Worker // reads and writes must be done in a deterministic order and for a 38*6777b538SAndroid Build Coastguard Worker // deterministic number of bytes, every time the fuzzer is run with the same 39*6777b538SAndroid Build Coastguard Worker // data. 40*6777b538SAndroid Build Coastguard Worker class FuzzedSocket : public TransportClientSocket { 41*6777b538SAndroid Build Coastguard Worker public: 42*6777b538SAndroid Build Coastguard Worker // |data_provider| is used as to determine behavior of the FuzzedSocket. It 43*6777b538SAndroid Build Coastguard Worker // must remain valid until after the FuzzedSocket is destroyed. 44*6777b538SAndroid Build Coastguard Worker FuzzedSocket(FuzzedDataProvider* data_provider, net::NetLog* net_log); 45*6777b538SAndroid Build Coastguard Worker 46*6777b538SAndroid Build Coastguard Worker FuzzedSocket(const FuzzedSocket&) = delete; 47*6777b538SAndroid Build Coastguard Worker FuzzedSocket& operator=(const FuzzedSocket&) = delete; 48*6777b538SAndroid Build Coastguard Worker 49*6777b538SAndroid Build Coastguard Worker ~FuzzedSocket() override; 50*6777b538SAndroid Build Coastguard Worker 51*6777b538SAndroid Build Coastguard Worker // If set to true, the socket will fuzz the result of the Connect() call. 52*6777b538SAndroid Build Coastguard Worker // It can fail or succeed, and return synchronously or asynchronously. If 53*6777b538SAndroid Build Coastguard Worker // false, Connect() succeeds synchronously. Defaults to false. set_fuzz_connect_result(bool fuzz_connect_result)54*6777b538SAndroid Build Coastguard Worker void set_fuzz_connect_result(bool fuzz_connect_result) { 55*6777b538SAndroid Build Coastguard Worker fuzz_connect_result_ = fuzz_connect_result; 56*6777b538SAndroid Build Coastguard Worker } 57*6777b538SAndroid Build Coastguard Worker 58*6777b538SAndroid Build Coastguard Worker // Sets the remote address the socket claims to be using. set_remote_address(const IPEndPoint & remote_address)59*6777b538SAndroid Build Coastguard Worker void set_remote_address(const IPEndPoint& remote_address) { 60*6777b538SAndroid Build Coastguard Worker remote_address_ = remote_address; 61*6777b538SAndroid Build Coastguard Worker } 62*6777b538SAndroid Build Coastguard Worker 63*6777b538SAndroid Build Coastguard Worker // Socket implementation: 64*6777b538SAndroid Build Coastguard Worker int Read(IOBuffer* buf, 65*6777b538SAndroid Build Coastguard Worker int buf_len, 66*6777b538SAndroid Build Coastguard Worker CompletionOnceCallback callback) override; 67*6777b538SAndroid Build Coastguard Worker int Write(IOBuffer* buf, 68*6777b538SAndroid Build Coastguard Worker int buf_len, 69*6777b538SAndroid Build Coastguard Worker CompletionOnceCallback callback, 70*6777b538SAndroid Build Coastguard Worker const NetworkTrafficAnnotationTag& traffic_annotation) override; 71*6777b538SAndroid Build Coastguard Worker int SetReceiveBufferSize(int32_t size) override; 72*6777b538SAndroid Build Coastguard Worker int SetSendBufferSize(int32_t size) override; 73*6777b538SAndroid Build Coastguard Worker 74*6777b538SAndroid Build Coastguard Worker // TransportClientSocket implementation: 75*6777b538SAndroid Build Coastguard Worker int Bind(const net::IPEndPoint& local_addr) override; 76*6777b538SAndroid Build Coastguard Worker // StreamSocket implementation: 77*6777b538SAndroid Build Coastguard Worker int Connect(CompletionOnceCallback callback) override; 78*6777b538SAndroid Build Coastguard Worker void Disconnect() override; 79*6777b538SAndroid Build Coastguard Worker bool IsConnected() const override; 80*6777b538SAndroid Build Coastguard Worker bool IsConnectedAndIdle() const override; 81*6777b538SAndroid Build Coastguard Worker int GetPeerAddress(IPEndPoint* address) const override; 82*6777b538SAndroid Build Coastguard Worker int GetLocalAddress(IPEndPoint* address) const override; 83*6777b538SAndroid Build Coastguard Worker const NetLogWithSource& NetLog() const override; 84*6777b538SAndroid Build Coastguard Worker bool WasEverUsed() const override; 85*6777b538SAndroid Build Coastguard Worker NextProto GetNegotiatedProtocol() const override; 86*6777b538SAndroid Build Coastguard Worker bool GetSSLInfo(SSLInfo* ssl_info) override; 87*6777b538SAndroid Build Coastguard Worker int64_t GetTotalReceivedBytes() const override; 88*6777b538SAndroid Build Coastguard Worker void ApplySocketTag(const net::SocketTag& tag) override; 89*6777b538SAndroid Build Coastguard Worker 90*6777b538SAndroid Build Coastguard Worker private: 91*6777b538SAndroid Build Coastguard Worker // Returns a net::Error that can be returned by a read or a write. Reads and 92*6777b538SAndroid Build Coastguard Worker // writes return basically the same set of errors, at the TCP socket layer. 93*6777b538SAndroid Build Coastguard Worker Error ConsumeReadWriteErrorFromData(); 94*6777b538SAndroid Build Coastguard Worker 95*6777b538SAndroid Build Coastguard Worker void OnReadComplete(CompletionOnceCallback callback, int result); 96*6777b538SAndroid Build Coastguard Worker void OnWriteComplete(CompletionOnceCallback callback, int result); 97*6777b538SAndroid Build Coastguard Worker void OnConnectComplete(CompletionOnceCallback callback, int result); 98*6777b538SAndroid Build Coastguard Worker 99*6777b538SAndroid Build Coastguard Worker // Returns whether all operations should be synchronous. Starts returning 100*6777b538SAndroid Build Coastguard Worker // true once there have been too many async reads and writes, as spinning the 101*6777b538SAndroid Build Coastguard Worker // message loop too often tends to cause fuzzers to time out. 102*6777b538SAndroid Build Coastguard Worker // See https://crbug.com/823012 103*6777b538SAndroid Build Coastguard Worker bool ForceSync() const; 104*6777b538SAndroid Build Coastguard Worker 105*6777b538SAndroid Build Coastguard Worker raw_ptr<FuzzedDataProvider> data_provider_; 106*6777b538SAndroid Build Coastguard Worker 107*6777b538SAndroid Build Coastguard Worker // If true, the result of the Connect() call is fuzzed - it can succeed or 108*6777b538SAndroid Build Coastguard Worker // fail with a variety of connection errors, and it can complete synchronously 109*6777b538SAndroid Build Coastguard Worker // or asynchronously. 110*6777b538SAndroid Build Coastguard Worker bool fuzz_connect_result_ = false; 111*6777b538SAndroid Build Coastguard Worker 112*6777b538SAndroid Build Coastguard Worker bool connect_pending_ = false; 113*6777b538SAndroid Build Coastguard Worker bool read_pending_ = false; 114*6777b538SAndroid Build Coastguard Worker bool write_pending_ = false; 115*6777b538SAndroid Build Coastguard Worker 116*6777b538SAndroid Build Coastguard Worker // This is true when the first callback returning an error is pending in the 117*6777b538SAndroid Build Coastguard Worker // message queue. If true, the socket acts like it's connected until that task 118*6777b538SAndroid Build Coastguard Worker // is run (Or Disconnect() is called), and reads / writes will return the same 119*6777b538SAndroid Build Coastguard Worker // error asynchronously, until it becomes false, at which point they'll return 120*6777b538SAndroid Build Coastguard Worker // it synchronously. 121*6777b538SAndroid Build Coastguard Worker bool error_pending_ = false; 122*6777b538SAndroid Build Coastguard Worker // If this is not OK, all reads/writes will fail with this error. 123*6777b538SAndroid Build Coastguard Worker int net_error_ = ERR_CONNECTION_CLOSED; 124*6777b538SAndroid Build Coastguard Worker 125*6777b538SAndroid Build Coastguard Worker int64_t total_bytes_read_ = 0; 126*6777b538SAndroid Build Coastguard Worker int64_t total_bytes_written_ = 0; 127*6777b538SAndroid Build Coastguard Worker 128*6777b538SAndroid Build Coastguard Worker int num_async_reads_and_writes_ = 0; 129*6777b538SAndroid Build Coastguard Worker 130*6777b538SAndroid Build Coastguard Worker NetLogWithSource net_log_; 131*6777b538SAndroid Build Coastguard Worker 132*6777b538SAndroid Build Coastguard Worker IPEndPoint remote_address_; 133*6777b538SAndroid Build Coastguard Worker 134*6777b538SAndroid Build Coastguard Worker base::WeakPtrFactory<FuzzedSocket> weak_factory_{this}; 135*6777b538SAndroid Build Coastguard Worker }; 136*6777b538SAndroid Build Coastguard Worker 137*6777b538SAndroid Build Coastguard Worker } // namespace net 138*6777b538SAndroid Build Coastguard Worker 139*6777b538SAndroid Build Coastguard Worker #endif // NET_SOCKET_FUZZED_SOCKET_H_ 140