diff options
-rw-r--r-- | src/or/command.c | 22 | ||||
-rw-r--r-- | src/or/connection.c | 16 | ||||
-rw-r--r-- | src/or/connection_ap.c | 14 | ||||
-rw-r--r-- | src/or/connection_exit.c | 20 | ||||
-rw-r--r-- | src/or/or.h | 5 |
5 files changed, 70 insertions, 7 deletions
diff --git a/src/or/command.c b/src/or/command.c index 0e2d34c4b..bbcb6d23f 100644 --- a/src/or/command.c +++ b/src/or/command.c @@ -22,6 +22,9 @@ void command_process_cell(cell_t *cell, connection_t *conn) { case CELL_SENDME: command_process_sendme_cell(cell, conn); break; + case CELL_CONNECTED: + command_process_connected_cell(cell, conn); + break; default: log(LOG_DEBUG,"Cell of unknown type (%d) received. Dropping.", cell->command); break; @@ -297,3 +300,22 @@ void command_process_destroy_cell(cell_t *cell, connection_t *conn) { circuit_free(circ); } +void command_process_connected_cell(cell_t *cell, connection_t *conn) { + circuit_t *circ; + + circ = circuit_get_by_aci_conn(cell->aci, conn); + + if(!circ) { + log(LOG_DEBUG,"command_process_connected_cell(): unknown circuit %d. Dropping.", cell->aci); + return; + } + + if(circ->n_conn != conn) { + log(LOG_WARNING,"command_process_connected_cell(): cell didn't come from n_conn! (aci %d)",cell->aci); + return; + } + + log(LOG_DEBUG,"command_process_connected_cell(): Received for aci %d.",cell->aci); + connection_send_connected(circ->p_aci, circ->p_conn); +} + diff --git a/src/or/connection.c b/src/or/connection.c index 8b86d253b..39fa2965c 100644 --- a/src/or/connection.c +++ b/src/or/connection.c @@ -496,7 +496,23 @@ int connection_send_destroy(aci_t aci, connection_t *conn) { cell.command = CELL_DESTROY; log(LOG_INFO,"connection_send_destroy(): Sending destroy (aci %d).",aci); return connection_write_cell_to_buf(&cell, conn); +} + +int connection_send_connected(aci_t aci, connection_t *conn) { + cell_t cell; + assert(conn); + + if(!connection_speaks_cells(conn)) { + log(LOG_INFO,"connection_send_connected(): Aci %d: At entry point. Notifying proxy.", aci); + connection_ap_send_connected(conn); + return 0; + } + + cell.aci = aci; + cell.command = CELL_CONNECTED; + log(LOG_INFO,"connection_send_connected(): passing back cell (aci %d).",aci); + return connection_write_cell_to_buf(&cell, conn); } int connection_write_cell_to_buf(cell_t *cellp, connection_t *conn) { diff --git a/src/or/connection_ap.c b/src/or/connection_ap.c index 3080fe822..732af7b06 100644 --- a/src/or/connection_ap.c +++ b/src/or/connection_ap.c @@ -253,7 +253,6 @@ int ap_handshake_send_onion(connection_t *ap_conn, connection_t *n_conn, circuit cell_t cell; int tmpbuflen, dataleft; char *tmpbuf; - char zero=0; circ->n_aci = get_unique_aci_by_addr_port(circ->n_addr, circ->n_port, ACI_TYPE_BOTH); circ->n_conn = n_conn; @@ -331,13 +330,18 @@ int ap_handshake_send_onion(connection_t *ap_conn, connection_t *n_conn, circuit /* FIXME should set circ->expire to something here */ - /* now we want to give the AP a "0" byte, because it wants to hear - * back from us */ - connection_write_to_buf(&zero, 1, ap_conn); /* this does connection_start_writing() too */ - return 0; } +int connection_ap_send_connected(connection_t *conn) { + char zero=0; + + assert(conn); + + /* give the AP a "0" byte, because it wants to hear that we've connected */ + return connection_write_to_buf(&zero, 1, conn); +} + int connection_ap_process_data_cell(cell_t *cell, connection_t *conn) { /* an incoming data cell has arrived */ diff --git a/src/or/connection_exit.c b/src/or/connection_exit.c index cbae5512e..455e54462 100644 --- a/src/or/connection_exit.c +++ b/src/or/connection_exit.c @@ -53,7 +53,9 @@ int connection_exit_finished_flushing(connection_t *conn) { if(connection_wants_to_flush(conn)) /* in case there are any queued data cells */ connection_start_writing(conn); connection_start_reading(conn); - return 0; + + /* also, deliver a 'connected' cell back through the circuit. */ + return connection_exit_send_connected(conn); case EXIT_CONN_STATE_OPEN: /* FIXME down the road, we'll clear out circuits that are pending to close */ connection_stop_writing(conn); @@ -67,6 +69,18 @@ int connection_exit_finished_flushing(connection_t *conn) { return 0; } +int connection_exit_send_connected(connection_t *conn) { + circuit_t *circ; + + assert(conn); + + circ = circuit_get_by_conn(conn); + + assert(circ && circ->p_conn && circ->n_conn == conn); /* is this true? i guess i'll see if it breaks. */ + + return connection_send_connected(circ->p_aci, circ->p_conn); +} + int connection_exit_process_data_cell(cell_t *cell, connection_t *conn) { struct hostent *rent; struct sockaddr_in dest_addr; @@ -154,7 +168,9 @@ int connection_exit_process_data_cell(cell_t *cell, connection_t *conn) { connection_set_poll_socket(conn); conn->state = EXIT_CONN_STATE_OPEN; connection_watch_events(conn, POLLIN); - return 0; + + /* also, deliver a 'connected' cell back through the circuit. */ + return connection_exit_send_connected(conn); } else { log(LOG_DEBUG,"connection_exit_process_data_cell(): in connecting_wait, but I've already received everything. Closing."); return -1; diff --git a/src/or/or.h b/src/or/or.h index cdec91bb1..e1b7f8fd3 100644 --- a/src/or/or.h +++ b/src/or/or.h @@ -132,6 +132,7 @@ #define CELL_ACK 4 #define CELL_NACK 5 #define CELL_SENDME 6 +#define CELL_CONNECTED 7 #define CELL_PAYLOAD_SIZE 120 @@ -394,6 +395,7 @@ void command_process_create_cell(cell_t *cell, connection_t *conn); void command_process_sendme_cell(cell_t *cell, connection_t *conn); void command_process_data_cell(cell_t *cell, connection_t *conn); void command_process_destroy_cell(cell_t *cell, connection_t *conn); +void command_process_connected_cell(cell_t *cell, connection_t *conn); /********************************* config.c ***************************/ @@ -441,6 +443,7 @@ int connection_speaks_cells(connection_t *conn); int connection_state_is_open(connection_t *conn); int connection_send_destroy(aci_t aci, connection_t *conn); +int connection_send_connected(aci_t aci, connection_t *conn); int connection_encrypt_cell(cell_t *cellp, connection_t *conn); int connection_write_cell_to_buf(cell_t *cellp, connection_t *conn); @@ -467,6 +470,7 @@ int ap_handshake_n_conn_open(connection_t *or_conn); int ap_handshake_send_onion(connection_t *ap_conn, connection_t *or_conn, circuit_t *circ); +int connection_ap_send_connected(connection_t *conn); int connection_ap_process_data_cell(cell_t *cell, connection_t *conn); int connection_ap_finished_flushing(connection_t *conn); @@ -479,6 +483,7 @@ int connection_ap_handle_listener_read(connection_t *conn); int connection_exit_process_inbuf(connection_t *conn); int connection_exit_package_inbuf(connection_t *conn); +int connection_exit_send_connected(connection_t *conn); int connection_exit_process_data_cell(cell_t *cell, connection_t *conn); int connection_exit_finished_flushing(connection_t *conn); |