fuzz coverage

Coverage Report

Created: 2026-04-24 13:48

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/root/bitcoin/src/torcontrol.h
Line
Count
Source
1
// Copyright (c) 2015-present The Bitcoin Core developers
2
// Distributed under the MIT software license, see the accompanying
3
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
4
5
/**
6
 * Functionality for communicating with Tor.
7
 */
8
#ifndef BITCOIN_TORCONTROL_H
9
#define BITCOIN_TORCONTROL_H
10
11
#include <netaddress.h>
12
#include <util/fs.h>
13
14
#include <event2/util.h>
15
16
#include <cstdint>
17
#include <deque>
18
#include <functional>
19
#include <string>
20
#include <vector>
21
22
constexpr uint16_t DEFAULT_TOR_SOCKS_PORT{9050};
23
constexpr int DEFAULT_TOR_CONTROL_PORT = 9051;
24
extern const std::string DEFAULT_TOR_CONTROL;
25
static const bool DEFAULT_LISTEN_ONION = true;
26
27
/** Tor control reply code. Ref: https://spec.torproject.org/control-spec/replies.html */
28
constexpr int TOR_REPLY_OK{250};
29
constexpr int TOR_REPLY_UNRECOGNIZED{510};
30
constexpr int TOR_REPLY_SYNTAX_ERROR{512}; //!< Syntax error in command argument
31
32
void StartTorControl(CService onion_service_target);
33
void InterruptTorControl();
34
void StopTorControl();
35
36
CService DefaultOnionServiceTarget(uint16_t port);
37
38
/** Reply from Tor, can be single or multi-line */
39
class TorControlReply
40
{
41
public:
42
0
    TorControlReply() { Clear(); }
43
44
    int code;
45
    std::vector<std::string> lines;
46
47
    void Clear()
48
0
    {
49
0
        code = 0;
50
0
        lines.clear();
51
0
    }
52
};
53
54
/** Low-level handling for Tor control connection.
55
 * Speaks the SMTP-like protocol as defined in torspec/control-spec.txt
56
 */
57
class TorControlConnection
58
{
59
public:
60
    typedef std::function<void(TorControlConnection&)> ConnectionCB;
61
    typedef std::function<void(TorControlConnection &,const TorControlReply &)> ReplyHandlerCB;
62
63
    /** Create a new TorControlConnection.
64
     */
65
    explicit TorControlConnection(struct event_base *base);
66
    ~TorControlConnection();
67
68
    /**
69
     * Connect to a Tor control port.
70
     * tor_control_center is address of the form host:port.
71
     * connected is the handler that is called when connection is successfully established.
72
     * disconnected is a handler that is called when the connection is broken.
73
     * Return true on success.
74
     */
75
    bool Connect(const std::string& tor_control_center, const ConnectionCB& connected, const ConnectionCB& disconnected);
76
77
    /**
78
     * Disconnect from Tor control port.
79
     */
80
    void Disconnect();
81
82
    /** Send a command, register a handler for the reply.
83
     * A trailing CRLF is automatically added.
84
     * Return true on success.
85
     */
86
    bool Command(const std::string &cmd, const ReplyHandlerCB& reply_handler);
87
88
private:
89
    /** Callback when ready for use */
90
    std::function<void(TorControlConnection&)> connected;
91
    /** Callback when connection lost */
92
    std::function<void(TorControlConnection&)> disconnected;
93
    /** Libevent event base */
94
    struct event_base *base;
95
    /** Connection to control socket */
96
    struct bufferevent* b_conn{nullptr};
97
    /** Message being received */
98
    TorControlReply message;
99
    /** Response handlers */
100
    std::deque<ReplyHandlerCB> reply_handlers;
101
102
    /** Libevent handlers: internal */
103
    static void readcb(struct bufferevent *bev, void *ctx);
104
    static void eventcb(struct bufferevent *bev, short what, void *ctx);
105
};
106
107
/****** Bitcoin specific TorController implementation ********/
108
109
/** Controller that connects to Tor control socket, authenticate, then create
110
 * and maintain an ephemeral onion service.
111
 */
112
class TorController
113
{
114
public:
115
    TorController(struct event_base* base, const std::string& tor_control_center, const CService& target);
116
0
    TorController() : conn{nullptr} {
117
        // Used for testing only.
118
0
    }
119
    ~TorController();
120
121
    /** Get name of file to store private key in */
122
    fs::path GetPrivateKeyFile();
123
124
    /** Reconnect, after getting disconnected */
125
    void Reconnect();
126
private:
127
    struct event_base* base;
128
    const std::string m_tor_control_center;
129
    TorControlConnection conn;
130
    std::string private_key;
131
    std::string service_id;
132
    bool reconnect;
133
    struct event *reconnect_ev = nullptr;
134
    float reconnect_timeout;
135
    CService service;
136
    const CService m_target;
137
    /** Cookie for SAFECOOKIE auth */
138
    std::vector<uint8_t> cookie;
139
    /** ClientNonce for SAFECOOKIE auth */
140
    std::vector<uint8_t> clientNonce;
141
142
public:
143
    /** Callback for GETINFO net/listeners/socks result */
144
    void get_socks_cb(TorControlConnection& conn, const TorControlReply& reply);
145
    /** Callback for ADD_ONION result */
146
    void add_onion_cb(TorControlConnection& conn, const TorControlReply& reply, bool pow_was_enabled);
147
    /** Callback for AUTHENTICATE result */
148
    void auth_cb(TorControlConnection& conn, const TorControlReply& reply);
149
    /** Callback for AUTHCHALLENGE result */
150
    void authchallenge_cb(TorControlConnection& conn, const TorControlReply& reply);
151
    /** Callback for PROTOCOLINFO result */
152
    void protocolinfo_cb(TorControlConnection& conn, const TorControlReply& reply);
153
    /** Callback after successful connection */
154
    void connected_cb(TorControlConnection& conn);
155
    /** Callback after connection lost or failed connection attempt */
156
    void disconnected_cb(TorControlConnection& conn);
157
158
    /** Callback for reconnect timer */
159
    static void reconnect_cb(evutil_socket_t fd, short what, void *arg);
160
};
161
162
#endif // BITCOIN_TORCONTROL_H