diff --git a/changes/fix-connection_printf_to_buf b/changes/fix-connection_printf_to_buf new file mode 100644 index 0000000000..e191eac8a5 --- /dev/null +++ b/changes/fix-connection_printf_to_buf @@ -0,0 +1,15 @@ + * Code simplifications and refactoring: + + - Make connection_printf_to_buf's behaviour sane. Its callers + expect it to emit a CRLF iff the format string ends with CRLF; + it actually emits a CRLF iff (a) the format string ends with + CRLF or (b) the resulting string is over 1023 characters long or + (c) the format string does not end with CRLF ''and'' the + resulting string is 1021 characters long or longer. Bugfix on + 0.1.1.9-alpha; fixes part of bug 3407. + + - Make send_control_event_impl's behaviour sane. Its callers + expect it to always emit a CRLF at the end of the string; it + might emit extra control characters as well. Bugfix on + 0.1.1.9-alpha; fixes another part of bug 3407. + diff --git a/src/or/connection_or.c b/src/or/connection_or.c index 2140e00803..679500deef 100644 --- a/src/or/connection_or.c +++ b/src/or/connection_or.c @@ -997,13 +997,16 @@ connection_tls_continue_handshake(or_connection_t *conn) if (! tor_tls_used_v1_handshake(conn->tls)) { if (!tor_tls_is_server(conn->tls)) { if (conn->_base.state == OR_CONN_STATE_TLS_HANDSHAKING) { - // log_notice(LD_OR,"Done. state was TLS_HANDSHAKING."); + log_debug(LD_OR, "Done with initial SSL handshake (client-side). " + "Requesting renegotiation."); conn->_base.state = OR_CONN_STATE_TLS_CLIENT_RENEGOTIATING; goto again; } // log_notice(LD_OR,"Done. state was %d.", conn->_base.state); } else { /* improved handshake, but not a client. */ + log_debug(LD_OR, "Done with initial SSL handshake (server-side). " + "Expecting renegotiation."); tor_tls_set_renegotiate_callback(conn->tls, connection_or_tls_renegotiated_cb, conn); diff --git a/src/or/control.c b/src/or/control.c index 4fcc3ab953..5e71a2ef94 100644 --- a/src/or/control.c +++ b/src/or/control.c @@ -105,7 +105,7 @@ static int disable_log_messages = 0; static int authentication_cookie_is_set = 0; /** If authentication_cookie_is_set, a secret cookie that we've stored to disk * and which we're using to authenticate controllers. (If the controller can - * read it off disk, it has permission to connect. */ + * read it off disk, it has permission to connect.) */ static char authentication_cookie[AUTHENTICATION_COOKIE_LEN]; /** A sufficiently large size to record the last bootstrap phase string. */ @@ -488,33 +488,26 @@ decode_escaped_string(const char *start, size_t in_len_max, } /** Acts like sprintf, but writes its formatted string to the end of - * conn-\>outbuf. The message may be truncated if it is too long, - * but it will always end with a CRLF sequence. - * - * Currently the length of the message is limited to 1024 (including the - * ending CR LF NUL ("\\r\\n\\0"). */ + * conn-\>outbuf. */ static void connection_printf_to_buf(control_connection_t *conn, const char *format, ...) { -#define CONNECTION_PRINTF_TO_BUF_BUFFERSIZE 1024 va_list ap; - char buf[CONNECTION_PRINTF_TO_BUF_BUFFERSIZE]; - int r; - size_t len; + char *buf = NULL; + int len; + va_start(ap,format); - r = tor_vsnprintf(buf, sizeof(buf), format, ap); + len = tor_vasprintf(&buf, format, ap); va_end(ap); - if (r<0) { + + if (len < 0) { log_warn(LD_BUG, "Unable to format string for controller."); return; } - len = strlen(buf); - if (fast_memcmp("\r\n\0", buf+len-2, 3)) { - buf[CONNECTION_PRINTF_TO_BUF_BUFFERSIZE-1] = '\0'; - buf[CONNECTION_PRINTF_TO_BUF_BUFFERSIZE-2] = '\n'; - buf[CONNECTION_PRINTF_TO_BUF_BUFFERSIZE-3] = '\r'; - } - connection_write_to_buf(buf, len, TO_CONN(conn)); + + connection_write_to_buf(buf, (size_t)len, TO_CONN(conn)); + + tor_free(buf); } /** Write all of the open control ports to ControlPortWriteToFile */ @@ -613,46 +606,31 @@ send_control_event_string(uint16_t event, event_format_t which, } SMARTLIST_FOREACH_END(conn); } -/** Helper for send_control1_event and send_control1_event_extended: +/** Helper for send_control_event and control_event_status: * Send an event to all v1 controllers that are listening for code * event. The event's body is created by the printf-style format in - * format, and other arguments as provided. - * - * Currently the length of the message is limited to 1024 (including the - * ending \\r\\n\\0). */ + * format, and other arguments as provided. */ static void send_control_event_impl(uint16_t event, event_format_t which, const char *format, va_list ap) { - /* This is just a little longer than the longest allowed log message */ -#define SEND_CONTROL1_EVENT_BUFFERSIZE 10064 - int r; - char buf[SEND_CONTROL1_EVENT_BUFFERSIZE]; - size_t len; + char *buf = NULL; + int len; - r = tor_vsnprintf(buf, sizeof(buf), format, ap); - if (r<0) { + len = tor_vasprintf(&buf, format, ap); + if (len < 0) { log_warn(LD_BUG, "Unable to format event for controller."); return; } - len = strlen(buf); - if (fast_memcmp("\r\n\0", buf+len-2, 3)) { - /* if it is not properly terminated, do it now */ - buf[SEND_CONTROL1_EVENT_BUFFERSIZE-1] = '\0'; - buf[SEND_CONTROL1_EVENT_BUFFERSIZE-2] = '\n'; - buf[SEND_CONTROL1_EVENT_BUFFERSIZE-3] = '\r'; - } - send_control_event_string(event, which|ALL_FORMATS, buf); + + tor_free(buf); } /** Send an event to all v1 controllers that are listening for code * event. The event's body is created by the printf-style format in - * format, and other arguments as provided. - * - * Currently the length of the message is limited to 1024 (including the - * ending \\n\\r\\0. */ + * format, and other arguments as provided. */ static void send_control_event(uint16_t event, event_format_t which, const char *format, ...)