summaryrefslogtreecommitdiff
path: root/main.c
diff options
context:
space:
mode:
Diffstat (limited to 'main.c')
-rw-r--r--main.c107
1 files changed, 55 insertions, 52 deletions
diff --git a/main.c b/main.c
index 7c9df58..3c3a4fb 100644
--- a/main.c
+++ b/main.c
@@ -94,7 +94,7 @@ tunnel *tunnel_create(int sockfd, int connid, uint32_t friendnumber)
94 94
95void tunnel_delete(tunnel *t) 95void tunnel_delete(tunnel *t)
96{ 96{
97 printf("Deleting tunnel #%d\n", t->connid); 97 fprintf(stderr, "Deleting tunnel #%d\n", t->connid);
98 if(t->sockfd) 98 if(t->sockfd)
99 { 99 {
100 close(t->sockfd); 100 close(t->sockfd);
@@ -130,40 +130,21 @@ void set_tox_username(Tox *tox)
130 130
131 gethostname(hostname, 1024); 131 gethostname(hostname, 1024);
132 hostname[1023] = '\0'; 132 hostname[1023] = '\0';
133# if 0
134 memset(&hints, 0, sizeof hints);
135 hints.ai_family = AF_UNSPEC; /*either IPV4 or IPV6*/
136 hints.ai_socktype = SOCK_STREAM;
137 hints.ai_flags = AI_CANONNAME;
138
139 if ((gai_result = getaddrinfo(hostname, "ftp", &hints, &info)) != 0)
140 {
141 fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(gai_result));
142 exit(1);
143 }
144
145 for(p = info; p != NULL; p = p->ai_next)
146 {
147 printf("hostname: %s\n", p->ai_canonname);
148 }
149# endif
150 133
151 tox_set_name(tox, hostname, strlen(hostname)); 134 tox_set_name(tox, hostname, strlen(hostname));
152
153// freeaddrinfo(info);
154} 135}
155// get sockaddr, IPv4 or IPv6: 136
156/* From Beej */ 137/* Get sockaddr, IPv4 or IPv6 */
157void *get_in_addr(struct sockaddr *sa) 138void *get_in_addr(struct sockaddr *sa)
158{ 139{
159 if (sa->sa_family == AF_INET) { 140 if (sa->sa_family == AF_INET)
141 {
160 return &(((struct sockaddr_in*)sa)->sin_addr); 142 return &(((struct sockaddr_in*)sa)->sin_addr);
161 } 143 }
162 144
163 return &(((struct sockaddr_in6*)sa)->sin6_addr); 145 return &(((struct sockaddr_in6*)sa)->sin6_addr);
164} 146}
165 147
166/* From Beej */
167int get_client_socket(char *hostname, int port) 148int get_client_socket(char *hostname, int port)
168{ 149{
169 int sockfd, numbytes; 150 int sockfd, numbytes;
@@ -179,13 +160,27 @@ int get_client_socket(char *hostname, int port)
179 hints.ai_family = AF_INET; 160 hints.ai_family = AF_INET;
180 hints.ai_socktype = SOCK_STREAM; 161 hints.ai_socktype = SOCK_STREAM;
181 162
182 if ((rv = getaddrinfo(hostname, port_str, &hints, &servinfo)) != 0) { 163 if ((rv = getaddrinfo(hostname, port_str, &hints, &servinfo)) != 0)
183 fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(rv)); 164 {
184 return -1; 165 /* Add a special case for "localhost" when name resolution is broken */
166 if(!strncmp("localhost", hostname, 256))
167 {
168 const char localhostname[] = "127.0.0.1";
169 if ((rv = getaddrinfo(localhostname, port_str, &hints, &servinfo)) != 0) {
170 fprintf(stderr, "getaddrinfo failed for 127.0.0.1: %s\n", gai_strerror(rv));
171 return -1;
172 }
173 }
174 else
175 {
176 fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(rv));
177 return -1;
178 }
185 } 179 }
186 180
187 // loop through all the results and connect to the first we can 181 // loop through all the results and connect to the first we can
188 for(p = servinfo; p != NULL; p = p->ai_next) { 182 for(p = servinfo; p != NULL; p = p->ai_next)
183 {
189 if (p->ai_family != AF_INET && p->ai_family != AF_INET6) 184 if (p->ai_family != AF_INET && p->ai_family != AF_INET6)
190 continue; 185 continue;
191 186
@@ -209,8 +204,7 @@ int get_client_socket(char *hostname, int port)
209 return -1; 204 return -1;
210 } 205 }
211 206
212 inet_ntop(p->ai_family, get_in_addr((struct sockaddr *)p->ai_addr), 207 inet_ntop(p->ai_family, get_in_addr((struct sockaddr *)p->ai_addr), s, sizeof s);
213 s, sizeof s);
214 fprintf(stderr, "connecting to %s\n", s); 208 fprintf(stderr, "connecting to %s\n", s);
215 209
216 freeaddrinfo(servinfo); // all done with this structure 210 freeaddrinfo(servinfo); // all done with this structure
@@ -229,6 +223,7 @@ int get_client_socket(char *hostname, int port)
229int send_frame(protocol_frame *frame, uint8_t *data) 223int send_frame(protocol_frame *frame, uint8_t *data)
230{ 224{
231 int rv = -1; 225 int rv = -1;
226 int try = 0;
232 int i; 227 int i;
233 228
234 data[0] = PROTOCOL_MAGIC_HIGH; 229 data[0] = PROTOCOL_MAGIC_HIGH;
@@ -240,10 +235,12 @@ int send_frame(protocol_frame *frame, uint8_t *data)
240 data[6] = BYTE2(frame->data_length); 235 data[6] = BYTE2(frame->data_length);
241 data[7] = BYTE1(frame->data_length); 236 data[7] = BYTE1(frame->data_length);
242 237
243 for(i = 0; i < 17;) 238 for(i = 0; i < 65;) /* 1.27 seconds per packet max */
244 { 239 {
245 int j; 240 int j;
246 241
242 try++;
243
247 rv = tox_send_lossless_packet( 244 rv = tox_send_lossless_packet(
248 tox, 245 tox,
249 frame->friendnumber, 246 frame->friendnumber,
@@ -273,7 +270,7 @@ int send_frame(protocol_frame *frame, uint8_t *data)
273 270
274 if(i > 0 && rv >= 0) 271 if(i > 0 && rv >= 0)
275 { 272 {
276 fprintf(stderr, "Packet succeeded at try %d\n", i+1); 273 fprintf(stderr, "Packet succeeded at try %d\n", try);
277 } 274 }
278 275
279 return rv; 276 return rv;
@@ -337,10 +334,10 @@ int handle_request_tunnel_frame(protocol_frame *rcvd_frame)
337 strncpy(hostname, rcvd_frame->data, rcvd_frame->data_length); 334 strncpy(hostname, rcvd_frame->data, rcvd_frame->data_length);
338 hostname[rcvd_frame->data_length] = '\0'; 335 hostname[rcvd_frame->data_length] = '\0';
339 336
340 printf("Got a request to forward data from %s:%d\n", hostname, port); 337 fprintf(stderr, "Got a request to forward data from %s:%d\n", hostname, port);
341 338
342 tunnel_id = get_random_tunnel_id(); 339 tunnel_id = get_random_tunnel_id();
343 printf("Tunnel ID: %d\n", tunnel_id); 340 fprintf(stderr, "Tunnel ID: %d\n", tunnel_id);
344 /* TODO make connection */ 341 /* TODO make connection */
345 sockfd = get_client_socket(hostname, port); 342 sockfd = get_client_socket(hostname, port);
346 if(sockfd > 0) 343 if(sockfd > 0)
@@ -380,6 +377,12 @@ int handle_client_tcp_frame(protocol_frame *rcvd_frame)
380 return -1; 377 return -1;
381 } 378 }
382 379
380 if(tun->friendnumber != rcvd_frame->friendnumber)
381 {
382 fprintf(stderr, "Friend #%d tried to send packet to a tunnel which belongs to #%d\n", rcvd_frame->friendnumber, tun->friendnumber);
383 return -1;
384 }
385
383 while(offset < rcvd_frame->data_length) 386 while(offset < rcvd_frame->data_length)
384 { 387 {
385 int sent_bytes; 388 int sent_bytes;
@@ -388,7 +391,7 @@ int handle_client_tcp_frame(protocol_frame *rcvd_frame)
388 tun->sockfd, 391 tun->sockfd,
389 rcvd_frame->data + offset, 392 rcvd_frame->data + offset,
390 rcvd_frame->data_length - offset, 393 rcvd_frame->data_length - offset,
391 0 394 MSG_NOSIGNAL
392 ); 395 );
393 396
394 if(sent_bytes < 0) 397 if(sent_bytes < 0)
@@ -403,11 +406,6 @@ int handle_client_tcp_frame(protocol_frame *rcvd_frame)
403 return 0; 406 return 0;
404} 407}
405 408
406int handle_server_tcp_fin_frame(protocol_frame *rcvd_frame)
407{
408
409}
410
411/* Handle close-tunnel frame received from the client */ 409/* Handle close-tunnel frame received from the client */
412int handle_client_tcp_fin_frame(protocol_frame *rcvd_frame) 410int handle_client_tcp_fin_frame(protocol_frame *rcvd_frame)
413{ 411{
@@ -520,9 +518,9 @@ int parse_lossless_packet(void *sender_uc, const uint8_t *data, uint32_t len)
520 frame->packet_type = INT16_AT(data, 2); 518 frame->packet_type = INT16_AT(data, 2);
521 frame->connid = INT16_AT(data, 4); 519 frame->connid = INT16_AT(data, 4);
522 frame->data_length = INT16_AT(data, 6); 520 frame->data_length = INT16_AT(data, 6);
523 frame->data = data + PROTOCOL_BUFFER_OFFSET; 521 frame->data = (uint8_t *)(data + PROTOCOL_BUFFER_OFFSET);
524 frame->friendnumber = *((uint32_t*)sender_uc); 522 frame->friendnumber = *((uint32_t*)sender_uc);
525 printf("Got protocol frame magic 0x%x type 0x%x from friend %d\n", frame->magic, frame->packet_type, frame->friendnumber); 523 fprintf(stderr, "Got protocol frame magic 0x%x type 0x%x from friend %d\n", frame->magic, frame->packet_type, frame->friendnumber);
526 524
527 if(len < frame->data_length + PROTOCOL_BUFFER_OFFSET) 525 if(len < frame->data_length + PROTOCOL_BUFFER_OFFSET)
528 { 526 {
@@ -652,12 +650,13 @@ void accept_friend_request(Tox *tox, const uint8_t *public_key, const uint8_t *d
652 int32_t friendnumber; 650 int32_t friendnumber;
653 int32_t *friendnumber_ptr = NULL; 651 int32_t *friendnumber_ptr = NULL;
654 652
655 printf("Got friend request\n"); 653 fprintf(stderr, "Got friend request\n");
656 654
657 friendnumber = tox_add_friend_norequest(tox, public_key); 655 friendnumber = tox_add_friend_norequest(tox, public_key);
658 656
657 memset(tox_printable_id, '\0', sizeof(tox_printable_id));
659 id_to_string(tox_printable_id, public_key); 658 id_to_string(tox_printable_id, public_key);
660 printf("Accepted friend request from %s as %d\n", tox_printable_id, friendnumber); 659 fprintf(stderr, "Accepted friend request from %s as %d\n", tox_printable_id, friendnumber);
661 660
662 /* TODO: this is not freed right now, we're leaking 4 bytes per contact (OMG!) */ 661 /* TODO: this is not freed right now, we're leaking 4 bytes per contact (OMG!) */
663 friendnumber_ptr = malloc(sizeof(int32_t)); 662 friendnumber_ptr = malloc(sizeof(int32_t));
@@ -674,7 +673,7 @@ void accept_friend_request(Tox *tox, const uint8_t *public_key, const uint8_t *d
674 673
675void cleanup(int status, void *tmp) 674void cleanup(int status, void *tmp)
676{ 675{
677 printf("kthxbye\n"); 676 fprintf(stderr, "kthxbye\n");
678 fflush(stdout); 677 fflush(stdout);
679 tox_kill(tox); 678 tox_kill(tox);
680 if(client_socket) 679 if(client_socket)
@@ -738,7 +737,7 @@ int do_server_loop()
738 char data[PROTOCOL_BUFFER_OFFSET]; 737 char data[PROTOCOL_BUFFER_OFFSET];
739 protocol_frame frame_st, *frame; 738 protocol_frame frame_st, *frame;
740 739
741 printf("conn closed!\n"); 740 fprintf(stderr, "conn closed!\n");
742 741
743 frame = &frame_st; 742 frame = &frame_st;
744 memset(frame, 0, sizeof(protocol_frame)); 743 memset(frame, 0, sizeof(protocol_frame));
@@ -750,7 +749,6 @@ int do_server_loop()
750 749
751 tunnel_delete(tun); 750 tunnel_delete(tun);
752 751
753 /* TODO remove tunnel? resume connection? */
754 continue; 752 continue;
755 } 753 }
756 else 754 else
@@ -787,7 +785,7 @@ int main(int argc, char *argv[])
787 unsigned char tox_printable_id[TOX_FRIEND_ADDRESS_SIZE * 2 + 1]; 785 unsigned char tox_printable_id[TOX_FRIEND_ADDRESS_SIZE * 2 + 1];
788 int oc; 786 int oc;
789 787
790 while ((oc = getopt(argc, argv, "L:pi:C:")) != -1) 788 while ((oc = getopt(argc, argv, "L:pi:C:P:")) != -1)
791 { 789 {
792 switch(oc) 790 switch(oc)
793 { 791 {
@@ -806,8 +804,12 @@ int main(int argc, char *argv[])
806 /* Pipe forwarding */ 804 /* Pipe forwarding */
807 client_mode = 1; 805 client_mode = 1;
808 client_pipe_mode = 1; 806 client_pipe_mode = 1;
809 remote_port = atoi(optarg); 807 if(parse_pipe_port_forward(optarg, &remote_host, &remote_port) < 0)
810 fprintf(stderr, "Forwarding remote port %d\n", remote_port); 808 {
809 fprintf(stderr, "Invalid value for -P option - use something like -P 127.0.0.1:22\n");
810 exit(1);
811 }
812 fprintf(stderr, "Forwarding remote port %d to stdin/out\n", remote_port);
811 break; 813 break;
812 case 'p': 814 case 'p':
813 /* Ping */ 815 /* Ping */
@@ -868,7 +870,7 @@ int main(int argc, char *argv[])
868 tox_get_address(tox, tox_id); 870 tox_get_address(tox, tox_id);
869 id_to_string(tox_printable_id, tox_id); 871 id_to_string(tox_printable_id, tox_id);
870 tox_printable_id[TOX_FRIEND_ADDRESS_SIZE * 2] = '\0'; 872 tox_printable_id[TOX_FRIEND_ADDRESS_SIZE * 2] = '\0';
871 printf("Generated Tox ID: %s\n", tox_printable_id); 873 fprintf(stderr, "Generated Tox ID: %s\n", tox_printable_id);
872 874
873 if(!remote_tox_id) 875 if(!remote_tox_id)
874 { 876 {
@@ -888,9 +890,10 @@ int main(int argc, char *argv[])
888 } 890 }
889 891
890 tox_get_address(tox, tox_id); 892 tox_get_address(tox, tox_id);
893 memset(tox_printable_id, '\0', sizeof(tox_printable_id));
891 id_to_string(tox_printable_id, tox_id); 894 id_to_string(tox_printable_id, tox_id);
892 tox_printable_id[TOX_FRIEND_ADDRESS_SIZE * 2] = '\0'; 895 tox_printable_id[TOX_FRIEND_ADDRESS_SIZE * 2] = '\0';
893 printf("Using Tox ID: %s\n", tox_printable_id); 896 fprintf(stderr, "Using Tox ID: %s\n", tox_printable_id);
894 897
895 tox_callback_friend_request(tox, accept_friend_request, NULL); 898 tox_callback_friend_request(tox, accept_friend_request, NULL);
896 do_server_loop(); 899 do_server_loop();