From d93ff0b82f9c4a983677cddf02d43b40f801d1a0 Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Sat, 3 Apr 2004 03:37:11 +0000 Subject: [PATCH] Handle rendezvous relay cells svn:r1464 --- src/common/util.h | 21 +++++++++++++++------ src/or/connection_edge.c | 11 ++++++++++- src/or/or.h | 13 +++++++++++-- src/or/rendcommon.c | 36 +++++++++++++++++++++++++++++++++++- src/or/rendmid.c | 8 ++++---- src/or/rendservice.c | 2 +- 6 files changed, 76 insertions(+), 15 deletions(-) diff --git a/src/common/util.h b/src/common/util.h index 60c5a5d75d..ceed257928 100644 --- a/src/common/util.h +++ b/src/common/util.h @@ -68,15 +68,17 @@ void set_uint32(char *cp, uint32_t v); ((*(((uint8_t*)(cp))+3)) ) ) #define set_uint16(cp,v) \ do { \ + uint16_t u16v = (v); \ *(((uint8_t*)(cp))+0) = (v >> 8)&0xff; \ *(((uint8_t*)(cp))+1) = (v >> 0)&0xff; \ } while (0) -#define set_uint32(cp,v) \ +#define set_uint32(cp,val) \ do { \ - *(((uint8_t*)(cp))+0) = (v >> 24)&0xff; \ - *(((uint8_t*)(cp))+1) = (v >> 16)&0xff; \ - *(((uint8_t*)(cp))+2) = (v >> 8)&0xff; \ - *(((uint8_t*)(cp))+3) = (v >> 0)&0xff; \ + uint32_t u32v = (v); \ + *(((uint8_t*)(cp))+0) = s32 >> 24)&0xff; \ + *(((uint8_t*)(cp))+1) = s32 >> 16)&0xff; \ + *(((uint8_t*)(cp))+2) = s32 >> 8)&0xff; \ + *(((uint8_t*)(cp))+3) = s32 >> 0)&0xff; \ } while (0) #endif #endif @@ -197,5 +199,12 @@ int correct_socket_errno(int s); #define correct_socket_errno(s) (errno) #endif - #endif + +/* + Local Variables: + mode:c + indent-tabs-mode:nil + c-basic-offset:2 + End: +*/ diff --git a/src/or/connection_edge.c b/src/or/connection_edge.c index 77da7b211c..206f5dae7d 100644 --- a/src/or/connection_edge.c +++ b/src/or/connection_edge.c @@ -171,7 +171,7 @@ int connection_edge_end(connection_t *conn, char reason, crypt_path_t *cpath_lay * return -1. Else return 0. */ int connection_edge_send_command(connection_t *fromconn, circuit_t *circ, - int relay_command, void *payload, + int relay_command, const char *payload, int payload_len, crypt_path_t *cpath_layer) { cell_t cell; relay_header_t rh; @@ -433,6 +433,15 @@ int connection_edge_process_relay_cell(cell_t *cell, circuit_t *circ, connection_start_reading(conn); connection_edge_package_raw_inbuf(conn); /* handle whatever might still be on the inbuf */ return 0; + case RELAY_COMMAND_ESTABLISH_INTRO: + case RELAY_COMMAND_ESTABLISH_RENDEZVOUS: + case RELAY_COMMAND_INTRODUCE1: + case RELAY_COMMAND_INTRODUCE2: + case RELAY_COMMAND_RENDEZVOUS1: + case RELAY_COMMAND_RENDEZVOUS2: + rend_process_relay_cell(circ, rh.command, rh.length, + cell->payload+RELAY_HEADER_SIZE); + return 0; } log_fn(LOG_WARN,"unknown relay command %d.",rh.command); return -1; diff --git a/src/or/or.h b/src/or/or.h index d551b21630..0a8ecd46cc 100644 --- a/src/or/or.h +++ b/src/or/or.h @@ -829,7 +829,7 @@ int connection_edge_process_inbuf(connection_t *conn); int connection_edge_destroy(uint16_t circ_id, connection_t *conn); int connection_edge_end(connection_t *conn, char reason, crypt_path_t *cpath_layer); int connection_edge_send_command(connection_t *fromconn, circuit_t *circ, - int relay_command, void *payload, + int relay_command, const char *payload, int payload_len, crypt_path_t *cpath_layer); int connection_edge_process_relay_cell(cell_t *cell, circuit_t *circ, connection_t *conn, int edge_type, @@ -1044,6 +1044,9 @@ typedef struct rend_service_descriptor_t { char **intro_points; } rend_service_descriptor_t; +void rend_process_relay_cell(circuit_t *circ, int command, int length, + const char *payload); + void rend_service_descriptor_free(rend_service_descriptor_t *desc); int rend_encode_service_descriptor(rend_service_descriptor_t *desc, crypto_pk_env_t *key, @@ -1058,7 +1061,6 @@ int rend_valid_service_id(char *query); int rend_cache_lookup(char *query, const char **desc, int *desc_len); int rend_cache_store(char *desc, int desc_len); - /********************************* rendservice.c ***************************/ int rend_config_services(or_options_t *options); @@ -1067,6 +1069,13 @@ int rend_services_init(void); void rend_service_intro_is_ready(circuit_t *circuit); void rend_service_rendezvous_is_ready(circuit_t *circuit); +int rend_service_introduce(circuit_t *circuit, const char *request, int request_len); + +/********************************* rendmid.c *******************************/ +int rend_mid_establish_intro(circuit_t *circ, const char *request, int request_len); +int rend_mid_introduce(circuit_t *circ, const char *request, int request_len); +int rend_mid_establish_rendezvous(circuit_t *circ, const char *request, int request_len); +int rend_mid_rendezvous(circuit_t *circ, const char *request, int request_len); #endif diff --git a/src/or/rendcommon.c b/src/or/rendcommon.c index b318a212ad..83b19672f9 100644 --- a/src/or/rendcommon.c +++ b/src/or/rendcommon.c @@ -93,7 +93,11 @@ rend_service_descriptor_t *rend_parse_service_descriptor( cp = eos+1; } keylen = crypto_pk_keysize(result->pk); - if (end-cp != keylen) goto truncated; + if (end-cp < keylen) goto truncated; + if (end-cp > keylen) { + log_fn(LOG_WARN, "Signature too long on service descriptor"); + goto error; + } if (crypto_pk_public_checksig_digest(result->pk, (char*)str,cp-str, /* data */ (char*)cp,end-cp /* signature*/ @@ -248,6 +252,36 @@ int rend_cache_store(char *desc, int desc_len) return 0; } +/* Dispatch on rendezvous relay command. */ +void rend_process_relay_cell(circuit_t *circ, int command, int length, + const char *payload) +{ + int r; + switch(command) { + case RELAY_COMMAND_ESTABLISH_INTRO: + r = rend_mid_establish_intro(circ,payload,length); + break; + case RELAY_COMMAND_ESTABLISH_RENDEZVOUS: + r = rend_mid_establish_rendezvous(circ,payload,length); + break; + case RELAY_COMMAND_INTRODUCE1: + r = rend_mid_introduce(circ,payload,length); + break; + case RELAY_COMMAND_INTRODUCE2: + r = rend_service_introduce(circ,payload,length); + break; + case RELAY_COMMAND_RENDEZVOUS1: + r = rend_mid_rendezvous(circ,payload,length); + break; + case RELAY_COMMAND_RENDEZVOUS2: + /* r = rend_client_rendezvous(circ,payload,length); */ + log_fn(LOG_NOTICE, "Ignoring a rendezvous2 cell"); + break; + default: + assert(0); + } +} + /* Local Variables: mode:c diff --git a/src/or/rendmid.c b/src/or/rendmid.c index 0fd6c75902..691af35878 100644 --- a/src/or/rendmid.c +++ b/src/or/rendmid.c @@ -8,7 +8,7 @@ * rendevous service. */ int -rend_mid_establish_intro(circuit_t *circ, char *request, int request_len) +rend_mid_establish_intro(circuit_t *circ, const char *request, int request_len) { crypto_pk_env_t *pk = NULL; char buf[20+9]; @@ -97,7 +97,7 @@ rend_mid_establish_intro(circuit_t *circ, char *request, int request_len) * INTRODUCE2 cell. */ int -rend_mid_introduce(circuit_t *circ, char *request, int request_len) +rend_mid_introduce(circuit_t *circ, const char *request, int request_len) { circuit_t *intro_circ; char hexid[9]; @@ -149,7 +149,7 @@ rend_mid_introduce(circuit_t *circ, char *request, int request_len) * rendezvous cookie. */ int -rend_mid_establish_rendezvous(circuit_t *circ, char *request, int request_len) +rend_mid_establish_rendezvous(circuit_t *circ, const char *request, int request_len) { char hexid[9]; @@ -185,7 +185,7 @@ rend_mid_establish_rendezvous(circuit_t *circ, char *request, int request_len) * relaying the cell's body in a RENDEZVOUS2 cell, and connecting the two circuits. */ int -rend_mid_rendezvous(circuit_t *circ, char *request, int request_len) +rend_mid_rendezvous(circuit_t *circ, const char *request, int request_len) { circuit_t *rend_circ; char hexid[9]; diff --git a/src/or/rendservice.c b/src/or/rendservice.c index bbe7a69ab5..e05998c71b 100644 --- a/src/or/rendservice.c +++ b/src/or/rendservice.c @@ -302,7 +302,7 @@ rend_service_get_by_pk_digest(const char* digest) * rendezvous points. */ int -rend_service_introduce(circuit_t *circuit, char *request, int request_len) +rend_service_introduce(circuit_t *circuit, const char *request, int request_len) { char *ptr, *rp_nickname, *r_cookie; char buf[RELAY_PAYLOAD_SIZE];