diff options
author | Alexander Færøy <ahf@torproject.org> | 2022-03-24 19:13:41 +0000 |
---|---|---|
committer | David Goulet <dgoulet@torproject.org> | 2024-06-18 15:15:20 -0400 |
commit | b6e260e69946dc6ce9c7de64438d5af29959d037 (patch) | |
tree | 70279845441ad1ef505a5c62e28272f84c390897 | |
parent | 0c1a39a955b91062ab2f012b2a9ea9675babec08 (diff) | |
download | tor-b6e260e69946dc6ce9c7de64438d5af29959d037.tar.gz tor-b6e260e69946dc6ce9c7de64438d5af29959d037.zip |
Add support for PT STATUS TYPE=version messages.
This patch adds support for handling the version status message. Once we
receive such message, we add the given version string to the
managed_proxy_t instance. Note this value can be NULL and the value can
change throughout the lifetime of the PT as multiple status version
messages are handled.
See: tpo/core/tor#11101
-rw-r--r-- | src/feature/client/transports.c | 36 | ||||
-rw-r--r-- | src/feature/client/transports.h | 7 | ||||
-rw-r--r-- | src/test/test_pt.c | 35 |
3 files changed, 78 insertions, 0 deletions
diff --git a/src/feature/client/transports.c b/src/feature/client/transports.c index 4d92a2a67a..7c5132695a 100644 --- a/src/feature/client/transports.c +++ b/src/feature/client/transports.c @@ -741,6 +741,9 @@ managed_proxy_destroy(managed_proxy_t *mp, /* free the outgoing proxy URI */ tor_free(mp->proxy_uri); + /* free our version, if any is set. */ + tor_free(mp->version); + /* do we want to terminate our process if it's still running? */ if (also_terminate_process && mp->process) { /* Note that we do not call process_free(mp->process) here because we let @@ -1293,6 +1296,9 @@ parse_status_line(const char *line, managed_proxy_t *mp) goto done; } + /* Handle the different messages. */ + handle_status_message(values, mp); + /* Prepend the PT name. */ config_line_prepend(&values, "PT", mp->argv[0]); status_message = kvline_encode(values, KV_QUOTED); @@ -1306,6 +1312,36 @@ parse_status_line(const char *line, managed_proxy_t *mp) tor_free(status_message); } +STATIC void +handle_status_message(const config_line_t *values, + managed_proxy_t *mp) +{ + const config_line_t *message_type = config_line_find(values, "TYPE"); + + /* Check if we have a TYPE field? */ + if (message_type == NULL) { + log_debug(LD_PT, "Managed proxy \"%s\" wrote a STATUS line without " + "a defined message TYPE", mp->argv[0]); + return; + } + + /* Handle VERSION messages. */ + if (! strcasecmp(message_type->value, "version")) { + const config_line_t *version = config_line_find(values, "VERSION"); + + if (version == NULL) { + log_warn(LD_PT, "Managed proxy \"%s\" wrote a STATUS TYPE=version line " + "with a missing VERSION field", mp->argv[0]); + return; + } + + tor_free(mp->version); + mp->version = tor_strdup(version->value); + + return; + } +} + /** Return a newly allocated string that tor should place in * TOR_PT_SERVER_TRANSPORT_OPTIONS while configuring the server * manged proxy in <b>mp</b>. Return NULL if no such options are found. */ diff --git a/src/feature/client/transports.h b/src/feature/client/transports.h index 535689537c..1f6c10961d 100644 --- a/src/feature/client/transports.h +++ b/src/feature/client/transports.h @@ -114,11 +114,16 @@ typedef struct { /* transports to-be-launched by this proxy */ smartlist_t *transports_to_launch; + /** Version as set by STATUS TYPE=version messages. */ + char *version; + /* The 'transports' list contains all the transports this proxy has launched. */ smartlist_t *transports; } managed_proxy_t; +struct config_line_t; + STATIC transport_t *transport_new(const tor_addr_t *addr, uint16_t port, const char *name, int socks_ver, const char *extra_info_args); @@ -131,6 +136,8 @@ STATIC void parse_proxy_error(const char *line); STATIC void handle_proxy_line(const char *line, managed_proxy_t *mp); STATIC void parse_log_line(const char *line, managed_proxy_t *mp); STATIC void parse_status_line(const char *line, managed_proxy_t *mp); +STATIC void handle_status_message(const struct config_line_t *values, + managed_proxy_t *mp); STATIC char *get_transport_options_for_server_proxy(const managed_proxy_t *mp); STATIC void managed_proxy_destroy(managed_proxy_t *mp, diff --git a/src/test/test_pt.c b/src/test/test_pt.c index 07c5032933..e97b0b2087 100644 --- a/src/test/test_pt.c +++ b/src/test/test_pt.c @@ -143,6 +143,40 @@ test_pt_parsing(void *arg) } static void +test_pt_status_parsing(void *arg) +{ + char line[200]; + char *test_binary = tor_strdup("test-pt"); + char *argv[] = { + test_binary, + NULL, + }; + + managed_proxy_t *mp = tor_malloc_zero(sizeof(managed_proxy_t)); + (void)arg; + mp->conf_state = PT_PROTO_INFANT; + mp->transports = smartlist_new(); + mp->argv = argv; + + /* STATUS TYPE=version messages. */ + tt_ptr_op(mp->version, OP_EQ, NULL); + strlcpy(line, "STATUS TRANSPORT=x " + "TYPE=version " + "VERSION=\"1.33.7-hax beta\"", + sizeof(line)); + handle_proxy_line(line, mp); + tt_str_op(mp->version, OP_EQ, "1.33.7-hax beta"); + + reset_mp(mp); + + done: + reset_mp(mp); + smartlist_free(mp->transports); + tor_free(mp); + tor_free(test_binary); +} + +static void test_pt_get_transport_options(void *arg) { char **execve_args; @@ -590,6 +624,7 @@ test_get_pt_proxy_uri(void *arg) struct testcase_t pt_tests[] = { PT_LEGACY(parsing), + PT_LEGACY(status_parsing), PT_LEGACY(protocol), { "get_transport_options", test_pt_get_transport_options, TT_FORK, NULL, NULL }, |