circuit.c 8.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319
  1. #include "or.h"
  2. /********* START VARIABLES **********/
  3. circuit_t *global_circuitlist=NULL;
  4. /********* END VARIABLES ************/
  5. void circuit_add(circuit_t *circ) {
  6. if(!global_circuitlist) { /* first one */
  7. global_circuitlist = circ;
  8. circ->next = NULL;
  9. } else {
  10. circ->next = global_circuitlist;
  11. global_circuitlist = circ;
  12. }
  13. }
  14. void circuit_remove(circuit_t *circ) {
  15. circuit_t *tmpcirc;
  16. if(!circ || !global_circuitlist)
  17. return;
  18. if(global_circuitlist == circ) {
  19. global_circuitlist = global_circuitlist->next;
  20. return;
  21. }
  22. for(tmpcirc = global_circuitlist;tmpcirc->next;tmpcirc = tmpcirc->next) {
  23. if(tmpcirc->next == circ) {
  24. tmpcirc->next = circ->next;
  25. return;
  26. }
  27. }
  28. }
  29. circuit_t *circuit_new(aci_t p_aci, connection_t *p_conn) {
  30. circuit_t *circ;
  31. circ = (circuit_t *)malloc(sizeof(circuit_t));
  32. if(!circ)
  33. return NULL;
  34. memset(circ,0,sizeof(circuit_t)); /* zero it out */
  35. circ->p_aci = p_aci;
  36. circ->p_conn = p_conn;
  37. circ->state = CIRCUIT_STATE_OPEN_WAIT;
  38. circ->onion = NULL;
  39. circ->onionlen=0;
  40. circ->recvlen=0;
  41. /* ACIs */
  42. circ->p_aci = p_aci;
  43. circ->n_aci = 0; /* we need to have identified the next hop to choose a correct ACI */
  44. circuit_add(circ);
  45. return circ;
  46. }
  47. void circuit_free(circuit_t *circ) {
  48. EVP_CIPHER_CTX_cleanup(&circ->n_ctx);
  49. EVP_CIPHER_CTX_cleanup(&circ->p_ctx);
  50. if(circ->onion)
  51. free(circ->onion);
  52. free(circ);
  53. }
  54. aci_t get_unique_aci_by_addr_port(uint32_t addr, uint16_t port, int aci_type) {
  55. aci_t test_aci;
  56. connection_t *conn;
  57. log(LOG_DEBUG,"get_unique_aci_by_addr_port() trying to get a unique aci");
  58. RAND_pseudo_bytes((unsigned char *)&test_aci, 2);
  59. if(aci_type == ACI_TYPE_LOWER)
  60. test_aci &= htons(0x00FF);
  61. if(aci_type == ACI_TYPE_HIGHER)
  62. test_aci &= htons(0xFF00);
  63. if(test_aci == 0)
  64. return get_unique_aci_by_addr_port(addr, port, aci_type); /* try again */
  65. conn = connection_get_by_addr_port(addr,port);
  66. if(!conn) /* there can't be a conflict -- no connection of that sort yet */
  67. return test_aci;
  68. if(circuit_get_by_aci_conn(test_aci, conn))
  69. return get_unique_aci_by_addr_port(addr, port, aci_type); /* try again */
  70. return test_aci;
  71. }
  72. int circuit_init(circuit_t *circ, int aci_type) {
  73. onion_layer_t *ol;
  74. int retval = 0;
  75. unsigned char digest1[20];
  76. unsigned char digest2[20];
  77. if (!circ)
  78. return -1;
  79. ol = (onion_layer_t *)circ->onion;
  80. if (!ol)
  81. return -1;
  82. log(LOG_DEBUG,"circuit_init(): starting");
  83. circ->n_addr = ol->addr;
  84. circ->n_port = ol->port;
  85. log(LOG_DEBUG,"circuit_init(): Set port to %u.",ntohs(ol->port));
  86. circ->p_f = ol->backf;
  87. log(LOG_DEBUG,"circuit_init(): Set BACKF to %u.",ol->backf);
  88. circ->n_f = ol->forwf;
  89. log(LOG_DEBUG,"circuit_init(): Set FORWF to %u.",ol->forwf);
  90. circ->state = CIRCUIT_STATE_OPEN;
  91. log(LOG_DEBUG,"circuit_init(): aci_type = %u.",aci_type);
  92. circ->n_aci = get_unique_aci_by_addr_port(circ->n_addr, circ->n_port, aci_type);
  93. log(LOG_DEBUG,"circuit_init(): Chosen ACI %u.",circ->n_aci);
  94. /* keys */
  95. SHA1(ol->keyseed,16,digest1);
  96. SHA1(digest1,20,digest2);
  97. SHA1(digest2,20,digest1);
  98. memcpy(circ->p_key,digest2,16);
  99. memcpy(circ->n_key,digest1,16);
  100. log(LOG_DEBUG,"circuit_init(): Computed keys.");
  101. /* set IVs to zero */
  102. memset(circ->n_iv,0,16);
  103. memset(circ->p_iv,0,16);
  104. /* initialize cipher context */
  105. EVP_CIPHER_CTX_init(&circ->n_ctx);
  106. EVP_CIPHER_CTX_init(&circ->p_ctx);
  107. /* initialize crypto engines */
  108. switch(circ->p_f)
  109. {
  110. case ONION_CIPHER_DES :
  111. retval = EVP_EncryptInit(&circ->p_ctx, EVP_des_ofb(), circ->p_key, circ->p_iv);
  112. break;
  113. case ONION_CIPHER_RC4 :
  114. retval = EVP_EncryptInit(&circ->p_ctx, EVP_rc4(), circ->p_key,circ->p_iv);
  115. break;
  116. case ONION_CIPHER_IDENTITY :
  117. retval = EVP_EncryptInit(&circ->p_ctx, EVP_enc_null(), circ->p_key, circ->p_iv);
  118. break;
  119. default :
  120. log(LOG_ERR,"Onion contains unrecognized cipher(%u) for ACI : %u.",circ->p_f,circ->n_aci);
  121. return -1;
  122. break;
  123. }
  124. if (!retval) /* EVP_EncryptInit() error */
  125. {
  126. log(LOG_ERR,"Cipher initialization failed (ACI %u).",circ->n_aci);
  127. EVP_CIPHER_CTX_cleanup(&circ->n_ctx);
  128. EVP_CIPHER_CTX_cleanup(&circ->p_ctx);
  129. return -1;
  130. }
  131. switch(circ->n_f)
  132. {
  133. case ONION_CIPHER_DES :
  134. retval = EVP_DecryptInit(&circ->n_ctx, EVP_des_ofb(), circ->n_key, circ->n_iv);
  135. break;
  136. case ONION_CIPHER_RC4 :
  137. retval = EVP_DecryptInit(&circ->n_ctx, EVP_rc4(), circ->n_key,circ->n_iv);
  138. break;
  139. case ONION_CIPHER_IDENTITY :
  140. retval = EVP_DecryptInit(&circ->n_ctx, EVP_enc_null(), circ->n_key, circ->n_iv);
  141. break;
  142. default :
  143. log(LOG_ERR,"Onion contains unrecognized cipher for ACI : %u.",circ->n_aci);
  144. return -1;
  145. break;
  146. }
  147. if (!retval) /* EVP_EncryptInit() error */
  148. {
  149. log(LOG_ERR,"Cipher initialization failed (ACI %u).",circ->n_aci);
  150. EVP_CIPHER_CTX_cleanup(&circ->n_ctx);
  151. EVP_CIPHER_CTX_cleanup(&circ->p_ctx);
  152. return -1;
  153. }
  154. log(LOG_DEBUG,"circuit_init(): Cipher initialization complete.");
  155. circ->expire = ol->expire;
  156. return 0;
  157. }
  158. circuit_t *circuit_get_by_aci_conn(aci_t aci, connection_t *conn) {
  159. circuit_t *circ;
  160. for(circ=global_circuitlist;circ;circ = circ->next) {
  161. if(circ->p_conn == conn && circ->p_aci == aci)
  162. return circ;
  163. if(circ->n_conn == conn && circ->n_aci == aci)
  164. return circ;
  165. }
  166. return NULL;
  167. }
  168. circuit_t *circuit_get_by_conn(connection_t *conn) {
  169. circuit_t *circ;
  170. for(circ=global_circuitlist;circ;circ = circ->next) {
  171. if(circ->p_conn == conn)
  172. return circ;
  173. if(circ->n_conn == conn)
  174. return circ;
  175. }
  176. return NULL;
  177. }
  178. int circuit_deliver_data_cell(cell_t *cell, circuit_t *circ, connection_t *conn, int crypt_type) {
  179. /* first decrypt cell->length */
  180. if(circuit_crypt(circ, &(cell->length), 1, crypt_type) < 0) {
  181. log(LOG_DEBUG,"circuit_deliver_data_cell(): length decryption failed. Dropping connection.");
  182. return -1;
  183. }
  184. /* then decrypt the payload */
  185. if(circuit_crypt(circ, (char *)&(cell->payload), CELL_PAYLOAD_SIZE, crypt_type) < 0) {
  186. log(LOG_DEBUG,"circuit_deliver_data_cell(): payload decryption failed. Dropping connection.");
  187. return -1;
  188. }
  189. if(conn->type == CONN_TYPE_APP) { /* send payload directly */
  190. log(LOG_DEBUG,"circuit_deliver_data_cell(): Sending to application.");
  191. if(connection_app_process_data_cell(cell, conn) < 0) {
  192. return -1;
  193. }
  194. } else { /* send it as a cell */
  195. log(LOG_DEBUG,"circuit_deliver_data_cell(): Sending to connection.");
  196. if(connection_write_cell_to_buf(cell, conn) < 0) {
  197. return -1;
  198. }
  199. }
  200. return 0; /* success */
  201. }
  202. int circuit_crypt(circuit_t *circ, char *in, size_t inlen, char crypt_type) {
  203. char *out;
  204. int outlen;
  205. if(!circ || !in)
  206. return -1;
  207. out = malloc(inlen);
  208. if(!out)
  209. return -1;
  210. if(crypt_type == 'e') {
  211. log(LOG_DEBUG,"circuit_crypt(): Encrypting %d bytes.",inlen);
  212. if(!EVP_EncryptUpdate(&circ->p_ctx,out,&outlen,in,inlen)) {
  213. log(LOG_ERR,"circuit_encrypt(): Encryption failed for ACI : %u (%s).",circ->p_aci, ERR_reason_error_string(ERR_get_error()));
  214. return -1;
  215. }
  216. } else if(crypt_type == 'd') {
  217. log(LOG_DEBUG,"circuit_crypt(): Decrypting %d bytes.",inlen);
  218. if(!EVP_DecryptUpdate(&circ->n_ctx,out,&outlen,in,inlen)) {
  219. log(LOG_ERR,"circuit_crypt(): Decryption failed for ACI : %u (%s).",circ->n_aci, ERR_reason_error_string(ERR_get_error()));
  220. return -1;
  221. }
  222. }
  223. if(outlen != inlen) {
  224. log(LOG_DEBUG,"circuit_crypt(): %d bytes crypted to %d bytes. Weird.",inlen,outlen);
  225. return -1;
  226. }
  227. memcpy(in,out,inlen);
  228. free(out);
  229. return 0;
  230. }
  231. void circuit_close(circuit_t *circ) {
  232. circuit_remove(circ);
  233. connection_send_destroy(circ->n_aci, circ->n_conn);
  234. connection_send_destroy(circ->p_aci, circ->p_conn);
  235. circuit_free(circ);
  236. }
  237. void circuit_about_to_close_connection(connection_t *conn) {
  238. /* send destroys for all circuits using conn */
  239. /* currently, we assume it's too late to flush conn's buf here.
  240. * down the road, maybe we'll consider that eof doesn't mean can't-write
  241. */
  242. circuit_t *circ;
  243. while((circ = circuit_get_by_conn(conn))) {
  244. circuit_remove(circ);
  245. if(circ->n_conn == conn) /* it's closing in front of us */
  246. connection_send_destroy(circ->p_aci, circ->p_conn);
  247. if(circ->p_conn == conn) /* it's closing behind us */
  248. connection_send_destroy(circ->n_aci, circ->n_conn);
  249. circuit_free(circ);
  250. }
  251. }