[or-cvs] clean up socks reply stuff more.

Roger Dingledine arma at seul.org
Sun Mar 27 06:37:59 UTC 2005


Update of /home2/or/cvsroot/tor/src/or
In directory moria.mit.edu:/home2/arma/work/onion/cvs/tor/src/or

Modified Files:
	connection_edge.c control.c main.c or.h relay.c rendclient.c 
Log Message:
clean up socks reply stuff more.
add a few more reasons so we can be more informative.


Index: connection_edge.c
===================================================================
RCS file: /home2/or/cvsroot/tor/src/or/connection_edge.c,v
retrieving revision 1.309
retrieving revision 1.310
diff -u -d -r1.309 -r1.310
--- connection_edge.c	27 Mar 2005 06:25:33 -0000	1.309
+++ connection_edge.c	27 Mar 2005 06:37:56 -0000	1.310
@@ -26,16 +26,24 @@
  */
 void
 connection_close_unattached_ap(connection_t *conn, int endreason) {
+
   tor_assert(conn->type == CONN_TYPE_AP);
   conn->has_sent_end = 1; /* no circ yet */
+
   if (!conn->socks_request->has_finished) {
     socks5_reply_status_t socksreason =
       connection_edge_end_reason_socks5_response(endreason);
+
+    if (endreason == END_STREAM_REASON_ALREADY_SOCKS_REPLIED)
+      log_fn(LOG_WARN,"Bug: stream (marked at %s:%d) sending two socks replies?",
+             conn->marked_for_close_file, conn->marked_for_close);
+
     if (conn->socks_request->command == SOCKS_COMMAND_CONNECT)
       connection_ap_handshake_socks_reply(conn, NULL, 0, socksreason);
     else
       connection_ap_handshake_socks_resolved(conn,RESOLVED_TYPE_ERROR,0,NULL);
   }
+
   connection_mark_for_close(conn);
   conn->hold_open_until_flushed = 1;
 }
@@ -90,7 +98,7 @@
   switch (conn->state) {
     case AP_CONN_STATE_SOCKS_WAIT:
       if (connection_ap_handshake_process_socks(conn) < 0) {
-        connection_close_unattached_ap(conn, END_STREAM_REASON_TIMEOUT);
+        /* already marked */
         return -1;
       }
       return 0;
@@ -345,7 +353,7 @@
     conn->timestamp_lastread += 15;
     /* move it back into 'pending' state, and try to attach. */
     if (connection_ap_detach_retriable(conn, circ)<0) {
-      connection_close_unattached_ap(conn, END_STREAM_REASON_MISC);
+      connection_close_unattached_ap(conn, END_STREAM_REASON_CANT_ATTACH);
     }
   } /* end for */
 }
@@ -368,7 +376,7 @@
         conn->state != AP_CONN_STATE_CIRCUIT_WAIT)
       continue;
     if (connection_ap_handshake_attach_circuit(conn) < 0) {
-      connection_close_unattached_ap(conn, END_STREAM_REASON_MISC);
+      connection_close_unattached_ap(conn, END_STREAM_REASON_CANT_ATTACH);
     }
   }
 }
@@ -865,12 +873,12 @@
       log_fn(LOG_DEBUG,"reply is already set for us. Using it.");
       connection_ap_handshake_socks_reply(conn, socks->reply, socks->replylen,
                                           SOCKS5_GENERAL_ERROR);
-      socks->replylen = 0; /* zero it out so we can do another round of negotiation */
     } else {
       log_fn(LOG_WARN,"Fetching socks handshake failed. Closing.");
       connection_ap_handshake_socks_reply(conn, NULL, 0, SOCKS5_GENERAL_ERROR);
     }
-    return sockshere;
+    connection_close_unattached_ap(conn, END_STREAM_REASON_ALREADY_SOCKS_REPLIED);
+    return -1;
   } /* else socks handshake is done, continue processing */
 
   tor_strlower(socks->address); /* normalize it */
@@ -886,6 +894,7 @@
      */
     log_fn(LOG_WARN,"Missing mapping for virtual address '%s'. Refusing.",
            socks->address);
+    connection_close_unattached_ap(conn, END_STREAM_REASON_INTERNAL);
     return -1;
   }
 
@@ -899,6 +908,7 @@
     char *s = strrchr(socks->address,'.');
     if (!s || s[1] == '\0') {
       log_fn(LOG_WARN,"Malformed exit address '%s'. Refusing.", socks->address);
+      connection_close_unattached_ap(conn, END_STREAM_REASON_TORPROTOCOL);
       return -1;
     }
     conn->chosen_exit_name = tor_strdup(s+1);
@@ -910,6 +920,7 @@
 
     if (address_is_invalid_destination(socks->address)) {
       log_fn(LOG_WARN,"Destination '%s' seems to be an invalid hostname. Failing.", socks->address);
+      connection_close_unattached_ap(conn, END_STREAM_REASON_TORPROTOCOL);
       return -1;
     }
 
@@ -920,13 +931,14 @@
       if (strlen(socks->address) > RELAY_PAYLOAD_SIZE) {
         log_fn(LOG_WARN,"Address to be resolved is too large. Failing.");
         connection_ap_handshake_socks_resolved(conn,RESOLVED_TYPE_ERROR,0,NULL);
+        connection_close_unattached_ap(conn, END_STREAM_REASON_ALREADY_SOCKS_REPLIED);
         return -1;
       }
       if (tor_inet_aton(socks->address, &in)) { /* see if it's an IP already */
         answer = in.s_addr;
         connection_ap_handshake_socks_resolved(conn,RESOLVED_TYPE_IPV4,4,
                                                (char*)&answer);
-        connection_close_unattached_ap(conn, END_STREAM_REASON_DONE);
+        connection_close_unattached_ap(conn, END_STREAM_REASON_ALREADY_SOCKS_REPLIED);
         return 0;
       }
       rep_hist_note_used_resolve(time(NULL)); /* help predict this next time */
@@ -934,6 +946,7 @@
     } else { /* socks->command == SOCKS_COMMAND_CONNECT */
       if (socks->port == 0) {
         log_fn(LOG_NOTICE,"Application asked to connect to port 0. Refusing.");
+        connection_close_unattached_ap(conn, END_STREAM_REASON_TORPROTOCOL);
         return -1;
       }
       rep_hist_note_used_port(socks->port, time(NULL)); /* help predict this next time */
@@ -941,7 +954,11 @@
     }
     if (! get_options()->LeaveStreamsUnattached) {
       conn->state = AP_CONN_STATE_CIRCUIT_WAIT;
-      return connection_ap_handshake_attach_circuit(conn);
+      if (connection_ap_handshake_attach_circuit(conn) < 0) {
+        connection_close_unattached_ap(conn, END_STREAM_REASON_CANT_ATTACH);
+        return -1;
+      }
+      return 0;
     } else {
       conn->state = AP_CONN_STATE_CONTROLLER_WAIT;
       return 0;
@@ -956,6 +973,7 @@
        * building all the circuits and then realizing it won't work. */
       log_fn(LOG_WARN,"Resolve requests to hidden services not allowed. Failing.");
       connection_ap_handshake_socks_resolved(conn,RESOLVED_TYPE_ERROR,0,NULL);
+      connection_close_unattached_ap(conn, END_STREAM_REASON_ALREADY_SOCKS_REPLIED);
       return -1;
     }
 
@@ -965,6 +983,7 @@
     r = rend_cache_lookup_entry(conn->rend_query, &entry);
     if (r<0) {
       log_fn(LOG_WARN,"Invalid service descriptor %s", conn->rend_query);
+      connection_close_unattached_ap(conn, END_STREAM_REASON_TORPROTOCOL);
       return -1;
     }
     if (r==0) {
@@ -978,7 +997,11 @@
       if (time(NULL) - entry->received < NUM_SECONDS_BEFORE_REFETCH) {
         conn->state = AP_CONN_STATE_CIRCUIT_WAIT;
         log_fn(LOG_INFO, "Descriptor is here and fresh enough. Great.");
-        return connection_ap_handshake_attach_circuit(conn);
+        if (connection_ap_handshake_attach_circuit(conn) < 0) {
+          connection_close_unattached_ap(conn, END_STREAM_REASON_CANT_ATTACH);
+          return -1;
+        }
+        return 0;
       } else {
         conn->state = AP_CONN_STATE_RENDDESC_WAIT;
         log_fn(LOG_INFO, "Stale descriptor %s. Refetching.", conn->rend_query);
@@ -1144,7 +1167,7 @@
 
   /* attaching to a dirty circuit is fine */
   if (connection_ap_handshake_attach_circuit(conn) < 0) {
-    connection_close_unattached_ap(conn, END_STREAM_REASON_MISC);
+    connection_close_unattached_ap(conn, END_STREAM_REASON_CANT_ATTACH);
     tor_close_socket(fd[1]);
     return -1;
   }

Index: control.c
===================================================================
RCS file: /home2/or/cvsroot/tor/src/or/control.c,v
retrieving revision 1.69
retrieving revision 1.70
diff -u -d -r1.69 -r1.70
--- control.c	27 Mar 2005 04:55:12 -0000	1.69
+++ control.c	27 Mar 2005 06:37:56 -0000	1.70
@@ -736,7 +736,7 @@
   if (!circ_id) {
     ap_conn->state = AP_CONN_STATE_CIRCUIT_WAIT;
     if (connection_ap_handshake_attach_circuit(ap_conn)<0)
-      connection_close_unattached_ap(ap_conn, END_STREAM_REASON_MISC);
+      connection_close_unattached_ap(ap_conn, END_STREAM_REASON_CANT_ATTACH);
     send_control_done(conn);
     return 0;
   }

Index: main.c
===================================================================
RCS file: /home2/or/cvsroot/tor/src/or/main.c,v
retrieving revision 1.474
retrieving revision 1.475
diff -u -d -r1.474 -r1.475
--- main.c	27 Mar 2005 04:55:12 -0000	1.474
+++ main.c	27 Mar 2005 06:37:56 -0000	1.475
@@ -478,8 +478,7 @@
                                               AP_CONN_STATE_CIRCUIT_WAIT))) {
     log_fn(LOG_NOTICE,"Network down? Failing connection to '%s:%d'.",
            conn->socks_request->address, conn->socks_request->port);
-    connection_close_unattached_ap(conn, END_STREAM_REASON_TIMEOUT);
-// XXX should maybe reflect SOCKS5_NET_UNREACHABLE here. what reason is that?
+    connection_close_unattached_ap(conn, END_STREAM_REASON_NET_UNREACHABLE);
   }
 }
 

Index: or.h
===================================================================
RCS file: /home2/or/cvsroot/tor/src/or/or.h,v
retrieving revision 1.575
retrieving revision 1.576
diff -u -d -r1.575 -r1.576
--- or.h	27 Mar 2005 06:25:33 -0000	1.575
+++ or.h	27 Mar 2005 06:37:56 -0000	1.576
@@ -430,6 +430,14 @@
 #define END_STREAM_REASON_CONNRESET 12
 #define END_STREAM_REASON_TORPROTOCOL 13
 
+/* These high-numbered end reasons are not part of the official spec,
+ * and are not intended to be put in relay end cells. They are here
+ * to be more informative when sending back socks replies to the
+ * application. */
+#define END_STREAM_REASON_ALREADY_SOCKS_REPLIED 256
+#define END_STREAM_REASON_CANT_ATTACH 257
+#define END_STREAM_REASON_NET_UNREACHABLE 258
+
 #define RESOLVED_TYPE_HOSTNAME 0
 #define RESOLVED_TYPE_IPV4 4
 #define RESOLVED_TYPE_IPV6 6

Index: relay.c
===================================================================
RCS file: /home2/or/cvsroot/tor/src/or/relay.c,v
retrieving revision 1.57
retrieving revision 1.58
diff -u -d -r1.57 -r1.58
--- relay.c	27 Mar 2005 04:55:13 -0000	1.57
+++ relay.c	27 Mar 2005 06:37:56 -0000	1.58
@@ -500,13 +500,13 @@
     case END_STREAM_REASON_CONNECTREFUSED:
       return SOCKS5_CONNECTION_REFUSED;
     case END_STREAM_REASON_EXITPOLICY:
-      return SOCKS5_CONNECTION_REFUSED; // XXX should be SOCKS5_NOT_ALLOWED ?
+      return SOCKS5_NOT_ALLOWED;
     case END_STREAM_REASON_DESTROY:
       return SOCKS5_GENERAL_ERROR;
     case END_STREAM_REASON_DONE:
       return SOCKS5_SUCCEEDED;
     case END_STREAM_REASON_TIMEOUT:
-      return SOCKS5_TTL_EXPIRED; // XXX is this correct?
+      return SOCKS5_TTL_EXPIRED;
     case END_STREAM_REASON_RESOURCELIMIT:
       return SOCKS5_GENERAL_ERROR;
     case END_STREAM_REASON_HIBERNATING:
@@ -517,6 +517,13 @@
       return SOCKS5_CONNECTION_REFUSED;
     case END_STREAM_REASON_TORPROTOCOL:
       return SOCKS5_GENERAL_ERROR;
+
+    case END_STREAM_REASON_ALREADY_SOCKS_REPLIED:
+      return SOCKS5_SUCCEEDED; /* never used */
+    case END_STREAM_REASON_CANT_ATTACH:
+      return SOCKS5_GENERAL_ERROR;
+    case END_STREAM_REASON_NET_UNREACHABLE:
+      return SOCKS5_NET_UNREACHABLE;
     default:
       log_fn(LOG_WARN,"Reason for ending (%d) not recognized.",reason);
       return SOCKS5_GENERAL_ERROR;
@@ -716,7 +723,7 @@
                    cell->payload[RELAY_HEADER_SIZE], /*answer_type*/
                    cell->payload[RELAY_HEADER_SIZE+1], /*answer_len*/
                    cell->payload+RELAY_HEADER_SIZE+2); /* answer */
-    connection_close_unattached_ap(conn, END_STREAM_REASON_DONE);
+    connection_close_unattached_ap(conn, END_STREAM_REASON_ALREADY_SOCKS_REPLIED);
     return 0;
   }
 

Index: rendclient.c
===================================================================
RCS file: /home2/or/cvsroot/tor/src/or/rendclient.c,v
retrieving revision 1.80
retrieving revision 1.81
diff -u -d -r1.80 -r1.81
--- rendclient.c	27 Mar 2005 04:55:13 -0000	1.80
+++ rendclient.c	27 Mar 2005 06:37:56 -0000	1.81
@@ -394,7 +394,7 @@
       if (connection_ap_handshake_attach_circuit(conn) < 0) {
         /* it will never work */
         log_fn(LOG_WARN,"attaching to a rend circ failed. Closing conn.");
-        connection_close_unattached_ap(conn, END_STREAM_REASON_MISC);
+        connection_close_unattached_ap(conn, END_STREAM_REASON_CANT_ATTACH);
       }
       tor_assert(conn->state != AP_CONN_STATE_RENDDESC_WAIT); /* avoid loop */
     } else { /* 404, or fetch didn't get that far */



More information about the tor-commits mailing list