aboutsummaryrefslogtreecommitdiff
path: root/networking
diff options
context:
space:
mode:
authorRon Yorston <rmy@pobox.com>2020-02-15 13:25:04 +0000
committerRon Yorston <rmy@pobox.com>2020-02-15 13:25:04 +0000
commit0abe89bc214c9d1f16f32c4339792066b875b7c6 (patch)
tree3748f654565bd08513093ebfbb68487f612b5e3f /networking
parent6885083a7e4f94938ca0a98e2c6c69a84eb08a1f (diff)
parenta6e48dead331c3c19e070992d2d571e74a1d9a8d (diff)
downloadbusybox-w32-0abe89bc214c9d1f16f32c4339792066b875b7c6.tar.gz
busybox-w32-0abe89bc214c9d1f16f32c4339792066b875b7c6.tar.bz2
busybox-w32-0abe89bc214c9d1f16f32c4339792066b875b7c6.zip
Merge branch 'busybox' into merge
Diffstat (limited to 'networking')
-rw-r--r--networking/tftp.c87
-rw-r--r--networking/udhcp/dhcpd.c2
2 files changed, 50 insertions, 39 deletions
diff --git a/networking/tftp.c b/networking/tftp.c
index 04bfe844f..60fdff232 100644
--- a/networking/tftp.c
+++ b/networking/tftp.c
@@ -319,7 +319,7 @@ static int tftp_protocol(
319 uint16_t opcode; 319 uint16_t opcode;
320 uint16_t block_nr; 320 uint16_t block_nr;
321 uint16_t recv_blk; 321 uint16_t recv_blk;
322 int open_mode, local_fd; 322 int local_fd = -1;
323 int retries, waittime_ms; 323 int retries, waittime_ms;
324 int io_bufsize = blksize + 4; 324 int io_bufsize = blksize + 4;
325 char *cp; 325 char *cp;
@@ -354,19 +354,6 @@ static int tftp_protocol(
354 } 354 }
355 } 355 }
356 356
357 /* Prepare open mode */
358 if (CMD_PUT(option_mask32)) {
359 open_mode = O_RDONLY;
360 } else {
361 open_mode = O_WRONLY | O_TRUNC | O_CREAT;
362#if ENABLE_TFTPD
363 if ((option_mask32 & (TFTPD_OPT+TFTPD_OPT_c)) == TFTPD_OPT) {
364 /* tftpd without -c */
365 open_mode = O_WRONLY | O_TRUNC;
366 }
367#endif
368 }
369
370 /* Examples of network traffic. 357 /* Examples of network traffic.
371 * Note two cases when ACKs with block# of 0 are sent. 358 * Note two cases when ACKs with block# of 0 are sent.
372 * 359 *
@@ -400,12 +387,29 @@ static int tftp_protocol(
400 387
401 if (!ENABLE_TFTP || our_lsa) { /* tftpd */ 388 if (!ENABLE_TFTP || our_lsa) { /* tftpd */
402 /* Open file (must be after changing user) */ 389 /* Open file (must be after changing user) */
390 int open_mode = O_RDONLY;
391 if (CMD_GET(option_mask32)) {
392 open_mode = O_WRONLY | O_TRUNC | O_CREAT;
393 if ((option_mask32 & (TFTPD_OPT+TFTPD_OPT_c)) == TFTPD_OPT) {
394 /* tftpd without -c */
395 open_mode = O_WRONLY | O_TRUNC;
396 }
397 }
403 local_fd = open(local_file, open_mode, 0666); 398 local_fd = open(local_file, open_mode, 0666);
404 if (local_fd < 0) { 399 if (local_fd < 0) {
400 /* sanitize name, it came from untrusted remote side */
401 unsigned char *p = (void *) local_file;
402 while (*p) {
403 if (*p < ' ')
404 *p = '?';
405 p++;
406 }
407 bb_perror_msg("can't open '%s'", local_file);
405 G_error_pkt_reason = ERR_NOFILE; 408 G_error_pkt_reason = ERR_NOFILE;
406 strcpy(G_error_pkt_str, "can't open file"); 409 strcpy(G_error_pkt_str, "can't open file");
407 goto send_err_pkt; 410 goto send_err_pkt_nomsg;
408 } 411 }
412
409/* gcc 4.3.1 would NOT optimize it out as it should! */ 413/* gcc 4.3.1 would NOT optimize it out as it should! */
410#if ENABLE_FEATURE_TFTP_BLOCKSIZE 414#if ENABLE_FEATURE_TFTP_BLOCKSIZE
411 if (blksize != TFTP_BLKSIZE_DEFAULT || want_transfer_size) { 415 if (blksize != TFTP_BLKSIZE_DEFAULT || want_transfer_size) {
@@ -424,10 +428,11 @@ static int tftp_protocol(
424 block_nr = 0; 428 block_nr = 0;
425 } 429 }
426 } else { /* tftp */ 430 } else { /* tftp */
427 /* Open file (must be after changing user) */ 431 if (CMD_PUT(option_mask32)) {
428 local_fd = CMD_GET(option_mask32) ? STDOUT_FILENO : STDIN_FILENO; 432 local_fd = STDIN_FILENO;
429 if (NOT_LONE_DASH(local_file)) 433 if (local_file)
430 local_fd = xopen(local_file, open_mode); 434 local_fd = xopen(local_file, O_RDONLY);
435 }
431/* Removing #if, or using if() statement instead of #if may lead to 436/* Removing #if, or using if() statement instead of #if may lead to
432 * "warning: null argument where non-null required": */ 437 * "warning: null argument where non-null required": */
433#if ENABLE_TFTP 438#if ENABLE_TFTP
@@ -451,16 +456,14 @@ static int tftp_protocol(
451 } 456 }
452 /* add filename and mode */ 457 /* add filename and mode */
453 /* fill in packet if the filename fits into xbuf */ 458 /* fill in packet if the filename fits into xbuf */
454 len = strlen(remote_file) + 1; 459 len = strlen(remote_file);
455 if (2 + len + sizeof("octet") >= io_bufsize) { 460 if (len + 3 + sizeof("octet") >= io_bufsize) {
456 bb_simple_error_msg("remote filename is too long"); 461 bb_simple_error_msg("remote filename is too long");
457 goto ret; 462 goto ret;
458 } 463 }
459 strcpy(cp, remote_file); 464 cp = stpcpy(cp, remote_file) + 1;
460 cp += len;
461 /* add "mode" part of the packet */ 465 /* add "mode" part of the packet */
462 strcpy(cp, "octet"); 466 cp = stpcpy(cp, "octet") + 1;
463 cp += sizeof("octet");
464 467
465# if ENABLE_FEATURE_TFTP_BLOCKSIZE 468# if ENABLE_FEATURE_TFTP_BLOCKSIZE
466 if (blksize == TFTP_BLKSIZE_DEFAULT && !want_transfer_size) 469 if (blksize == TFTP_BLKSIZE_DEFAULT && !want_transfer_size)
@@ -485,7 +488,7 @@ static int tftp_protocol(
485 } 488 }
486 if (want_transfer_size) { 489 if (want_transfer_size) {
487 /* add "tsize", <nul>, size, <nul> (see RFC2349) */ 490 /* add "tsize", <nul>, size, <nul> (see RFC2349) */
488 /* if tftp and downloading, we send "0" (since we opened local_fd with O_TRUNC) 491 /* if tftp and downloading, we send "0" (local_fd is not open yet)
489 * and this makes server to send "tsize" option with the size */ 492 * and this makes server to send "tsize" option with the size */
490 /* if tftp and uploading, we send file size (maybe dont, to not confuse old servers???) */ 493 /* if tftp and uploading, we send file size (maybe dont, to not confuse old servers???) */
491 /* if tftpd and downloading, we are answering to client's request */ 494 /* if tftpd and downloading, we are answering to client's request */
@@ -494,7 +497,8 @@ static int tftp_protocol(
494 strcpy(cp, "tsize"); 497 strcpy(cp, "tsize");
495 cp += sizeof("tsize"); 498 cp += sizeof("tsize");
496 st.st_size = 0; 499 st.st_size = 0;
497 fstat(local_fd, &st); 500 if (local_fd >= 0)
501 fstat(local_fd, &st);
498 cp += sprintf(cp, "%"OFF_FMT"u", (off_t)st.st_size) + 1; 502 cp += sprintf(cp, "%"OFF_FMT"u", (off_t)st.st_size) + 1;
499# if ENABLE_FEATURE_TFTP_PROGRESS_BAR 503# if ENABLE_FEATURE_TFTP_PROGRESS_BAR
500 /* Save for progress bar. If 0 (tftp downloading), 504 /* Save for progress bar. If 0 (tftp downloading),
@@ -684,7 +688,13 @@ static int tftp_protocol(
684 688
685 if (CMD_GET(option_mask32) && (opcode == TFTP_DATA)) { 689 if (CMD_GET(option_mask32) && (opcode == TFTP_DATA)) {
686 if (recv_blk == block_nr) { 690 if (recv_blk == block_nr) {
687 int sz = full_write(local_fd, &rbuf[4], len - 4); 691 int sz;
692 if (local_fd == -1) {
693 local_fd = STDOUT_FILENO;
694 if (local_file)
695 local_fd = xopen(local_file, O_WRONLY | O_TRUNC | O_CREAT);
696 }
697 sz = full_write(local_fd, &rbuf[4], len - 4);
688 if (sz != len - 4) { 698 if (sz != len - 4) {
689 strcpy(G_error_pkt_str, bb_msg_write_error); 699 strcpy(G_error_pkt_str, bb_msg_write_error);
690 G_error_pkt_reason = ERR_WRITE; 700 G_error_pkt_reason = ERR_WRITE;
@@ -721,7 +731,7 @@ static int tftp_protocol(
721 * must never resend the current DATA packet on receipt 731 * must never resend the current DATA packet on receipt
722 * of a duplicate ACK". 732 * of a duplicate ACK".
723 * DATA pkts are resent ONLY on timeout. 733 * DATA pkts are resent ONLY on timeout.
724 * Thus "goto send_again" will ba a bad mistake above. 734 * Thus "goto send_again" will be a bad mistake above.
725 * See: 735 * See:
726 * http://en.wikipedia.org/wiki/Sorcerer's_Apprentice_Syndrome 736 * http://en.wikipedia.org/wiki/Sorcerer's_Apprentice_Syndrome
727 */ 737 */
@@ -733,22 +743,27 @@ static int tftp_protocol(
733 free(xbuf); 743 free(xbuf);
734 free(rbuf); 744 free(rbuf);
735 } 745 }
736 return finished == 0; /* returns 1 on failure */ 746 if (!finished)
747 goto err;
748 return EXIT_SUCCESS;
737 749
738 send_read_err_pkt: 750 send_read_err_pkt:
739 strcpy(G_error_pkt_str, bb_msg_read_error); 751 strcpy(G_error_pkt_str, bb_msg_read_error);
740 send_err_pkt: 752 send_err_pkt:
741 if (G_error_pkt_str[0]) 753 if (G_error_pkt_str[0])
742 bb_simple_error_msg(G_error_pkt_str); 754 bb_simple_error_msg(G_error_pkt_str);
755 send_err_pkt_nomsg:
743 G.error_pkt[1] = TFTP_ERROR; 756 G.error_pkt[1] = TFTP_ERROR;
744 xsendto(socket_fd, G.error_pkt, 4 + 1 + strlen(G_error_pkt_str), 757 xsendto(socket_fd, G.error_pkt, 4 + 1 + strlen(G_error_pkt_str),
745 &peer_lsa->u.sa, peer_lsa->len); 758 &peer_lsa->u.sa, peer_lsa->len);
759 err:
760 if (local_fd >= 0 && CMD_GET(option_mask32) && local_file)
761 unlink(local_file);
746 return EXIT_FAILURE; 762 return EXIT_FAILURE;
747#undef remote_file 763#undef remote_file
748} 764}
749 765
750#if ENABLE_TFTP 766#if ENABLE_TFTP
751
752int tftp_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; 767int tftp_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
753int tftp_main(int argc UNUSED_PARAM, char **argv) 768int tftp_main(int argc UNUSED_PARAM, char **argv)
754{ 769{
@@ -761,7 +776,6 @@ int tftp_main(int argc UNUSED_PARAM, char **argv)
761# endif 776# endif
762 int result; 777 int result;
763 int port; 778 int port;
764 IF_GETPUT(int opt;)
765 779
766 INIT_G(); 780 INIT_G();
767 781
@@ -802,7 +816,7 @@ int tftp_main(int argc UNUSED_PARAM, char **argv)
802 } 816 }
803 } 817 }
804 818
805 IF_GETPUT(opt =) getopt32(argv, "^" 819 getopt32(argv, "^"
806 IF_FEATURE_TFTP_GET("g") IF_FEATURE_TFTP_PUT("p") 820 IF_FEATURE_TFTP_GET("g") IF_FEATURE_TFTP_PUT("p")
807 "l:r:" IF_FEATURE_TFTP_BLOCKSIZE("b:") 821 "l:r:" IF_FEATURE_TFTP_BLOCKSIZE("b:")
808 IF_FEATURE_TFTP_HPA_COMPAT("m:") 822 IF_FEATURE_TFTP_HPA_COMPAT("m:")
@@ -853,18 +867,14 @@ int tftp_main(int argc UNUSED_PARAM, char **argv)
853# endif 867# endif
854 result = tftp_protocol( 868 result = tftp_protocol(
855 NULL /*our_lsa*/, peer_lsa, 869 NULL /*our_lsa*/, peer_lsa,
856 local_file, remote_file 870 (LONE_DASH(local_file) ? NULL : local_file), remote_file
857 IF_FEATURE_TFTP_BLOCKSIZE(, 1 /* want_transfer_size */) 871 IF_FEATURE_TFTP_BLOCKSIZE(, 1 /* want_transfer_size */)
858 IF_FEATURE_TFTP_BLOCKSIZE(, blksize) 872 IF_FEATURE_TFTP_BLOCKSIZE(, blksize)
859 ); 873 );
860 tftp_progress_done(); 874 tftp_progress_done();
861 875
862 if (result != EXIT_SUCCESS && NOT_LONE_DASH(local_file) && CMD_GET(opt)) {
863 unlink(local_file);
864 }
865 return result; 876 return result;
866} 877}
867
868#endif /* ENABLE_TFTP */ 878#endif /* ENABLE_TFTP */
869 879
870#if ENABLE_TFTPD 880#if ENABLE_TFTPD
@@ -1001,7 +1011,6 @@ int tftpd_main(int argc UNUSED_PARAM, char **argv)
1001 strcpy(G_error_pkt_str, error_msg); 1011 strcpy(G_error_pkt_str, error_msg);
1002 goto do_proto; 1012 goto do_proto;
1003} 1013}
1004
1005#endif /* ENABLE_TFTPD */ 1014#endif /* ENABLE_TFTPD */
1006 1015
1007#endif /* ENABLE_FEATURE_TFTP_GET || ENABLE_FEATURE_TFTP_PUT */ 1016#endif /* ENABLE_FEATURE_TFTP_GET || ENABLE_FEATURE_TFTP_PUT */
diff --git a/networking/udhcp/dhcpd.c b/networking/udhcp/dhcpd.c
index 3e08ec011..9d6604943 100644
--- a/networking/udhcp/dhcpd.c
+++ b/networking/udhcp/dhcpd.c
@@ -192,6 +192,8 @@ static struct dyn_lease *add_lease(
192 * but merely make dumpleases output safe for shells to use. 192 * but merely make dumpleases output safe for shells to use.
193 * We accept "0-9A-Za-z._-", all other chars turn to dots. 193 * We accept "0-9A-Za-z._-", all other chars turn to dots.
194 */ 194 */
195 if (*p == '-')
196 *p = '.'; /* defeat "-option" attacks too */
195 while (*p) { 197 while (*p) {
196 if (!isalnum(*p) && *p != '-' && *p != '_') 198 if (!isalnum(*p) && *p != '-' && *p != '_')
197 *p = '.'; 199 *p = '.';