summaryrefslogtreecommitdiff
path: root/sshd.c
diff options
context:
space:
mode:
authorColin Watson <cjwatson@debian.org>2003-09-01 02:05:26 +0000
committerColin Watson <cjwatson@debian.org>2003-09-01 02:05:26 +0000
commit6d5a72bc1d98a42ba42f082e50a22e911c1d82d3 (patch)
tree1bf23174bdb6fc71e2846dda0eca195a418484e7 /sshd.c
parent2ee26b431f98cf1dc0e4fb9809ad1e0c879b8c08 (diff)
parent58657d96514cd6f16d82add8d6f4adbb36765758 (diff)
Debian release 3.5p1-1.
Diffstat (limited to 'sshd.c')
-rw-r--r--sshd.c93
1 files changed, 50 insertions, 43 deletions
diff --git a/sshd.c b/sshd.c
index 904629e95..35685643f 100644
--- a/sshd.c
+++ b/sshd.c
@@ -42,7 +42,7 @@
42 */ 42 */
43 43
44#include "includes.h" 44#include "includes.h"
45RCSID("$OpenBSD: sshd.c,v 1.251 2002/06/25 18:51:04 markus Exp $"); 45RCSID("$OpenBSD: sshd.c,v 1.260 2002/09/27 10:42:09 mickey Exp $");
46 46
47#include <openssl/dh.h> 47#include <openssl/dh.h>
48#include <openssl/bn.h> 48#include <openssl/bn.h>
@@ -303,11 +303,8 @@ grace_alarm_handler(int sig)
303{ 303{
304 /* XXX no idea how fix this signal handler */ 304 /* XXX no idea how fix this signal handler */
305 305
306 /* Close the connection. */
307 packet_close();
308
309 /* Log error and exit. */ 306 /* Log error and exit. */
310 fatal("Timeout before authentication for %s.", get_remote_ipaddr()); 307 fatal("Timeout before authentication for %s", get_remote_ipaddr());
311} 308}
312 309
313/* 310/*
@@ -320,7 +317,7 @@ grace_alarm_handler(int sig)
320static void 317static void
321generate_ephemeral_server_key(void) 318generate_ephemeral_server_key(void)
322{ 319{
323 u_int32_t rand = 0; 320 u_int32_t rnd = 0;
324 int i; 321 int i;
325 322
326 verbose("Generating %s%d bit RSA key.", 323 verbose("Generating %s%d bit RSA key.",
@@ -333,9 +330,9 @@ generate_ephemeral_server_key(void)
333 330
334 for (i = 0; i < SSH_SESSION_KEY_LENGTH; i++) { 331 for (i = 0; i < SSH_SESSION_KEY_LENGTH; i++) {
335 if (i % 4 == 0) 332 if (i % 4 == 0)
336 rand = arc4random(); 333 rnd = arc4random();
337 sensitive_data.ssh1_cookie[i] = rand & 0xff; 334 sensitive_data.ssh1_cookie[i] = rnd & 0xff;
338 rand >>= 8; 335 rnd >>= 8;
339 } 336 }
340 arc4random_stir(); 337 arc4random_stir();
341} 338}
@@ -427,6 +424,12 @@ sshd_exchange_identification(int sock_in, int sock_out)
427 424
428 compat_datafellows(remote_version); 425 compat_datafellows(remote_version);
429 426
427 if (datafellows & SSH_BUG_PROBE) {
428 log("probed from %s with %s. Don't panic.",
429 get_remote_ipaddr(), client_version_string);
430 fatal_cleanup();
431 }
432
430 if (datafellows & SSH_BUG_SCANNER) { 433 if (datafellows & SSH_BUG_SCANNER) {
431 log("scanned from %s with %s. Don't panic.", 434 log("scanned from %s with %s. Don't panic.",
432 get_remote_ipaddr(), client_version_string); 435 get_remote_ipaddr(), client_version_string);
@@ -529,8 +532,8 @@ demote_sensitive_data(void)
529static void 532static void
530privsep_preauth_child(void) 533privsep_preauth_child(void)
531{ 534{
532 u_int32_t rand[256]; 535 u_int32_t rnd[256];
533 gid_t gidset[2]; 536 gid_t gidset[1];
534 struct passwd *pw; 537 struct passwd *pw;
535 int i; 538 int i;
536 539
@@ -538,8 +541,8 @@ privsep_preauth_child(void)
538 privsep_challenge_enable(); 541 privsep_challenge_enable();
539 542
540 for (i = 0; i < 256; i++) 543 for (i = 0; i < 256; i++)
541 rand[i] = arc4random(); 544 rnd[i] = arc4random();
542 RAND_seed(rand, sizeof(rand)); 545 RAND_seed(rnd, sizeof(rnd));
543 546
544 /* Demote the private keys to public keys. */ 547 /* Demote the private keys to public keys. */
545 demote_sensitive_data(); 548 demote_sensitive_data();
@@ -550,7 +553,7 @@ privsep_preauth_child(void)
550 memset(pw->pw_passwd, 0, strlen(pw->pw_passwd)); 553 memset(pw->pw_passwd, 0, strlen(pw->pw_passwd));
551 endpwent(); 554 endpwent();
552 555
553 /* Change our root directory*/ 556 /* Change our root directory */
554 if (chroot(_PATH_PRIVSEP_CHROOT_DIR) == -1) 557 if (chroot(_PATH_PRIVSEP_CHROOT_DIR) == -1)
555 fatal("chroot(\"%s\"): %s", _PATH_PRIVSEP_CHROOT_DIR, 558 fatal("chroot(\"%s\"): %s", _PATH_PRIVSEP_CHROOT_DIR,
556 strerror(errno)); 559 strerror(errno));
@@ -573,7 +576,7 @@ privsep_preauth_child(void)
573#endif 576#endif
574} 577}
575 578
576static Authctxt* 579static Authctxt *
577privsep_preauth(void) 580privsep_preauth(void)
578{ 581{
579 Authctxt *authctxt = NULL; 582 Authctxt *authctxt = NULL;
@@ -589,6 +592,8 @@ privsep_preauth(void)
589 if (pid == -1) { 592 if (pid == -1) {
590 fatal("fork of unprivileged child failed"); 593 fatal("fork of unprivileged child failed");
591 } else if (pid != 0) { 594 } else if (pid != 0) {
595 fatal_remove_cleanup((void (*) (void *)) packet_close, NULL);
596
592 debug2("Network child is on pid %ld", (long)pid); 597 debug2("Network child is on pid %ld", (long)pid);
593 598
594 close(pmonitor->m_recvfd); 599 close(pmonitor->m_recvfd);
@@ -602,6 +607,10 @@ privsep_preauth(void)
602 while (waitpid(pid, &status, 0) < 0) 607 while (waitpid(pid, &status, 0) < 0)
603 if (errno != EINTR) 608 if (errno != EINTR)
604 break; 609 break;
610
611 /* Reinstall, since the child has finished */
612 fatal_add_cleanup((void (*) (void *)) packet_close, NULL);
613
605 return (authctxt); 614 return (authctxt);
606 } else { 615 } else {
607 /* child */ 616 /* child */
@@ -624,7 +633,7 @@ privsep_postauth(Authctxt *authctxt)
624 /* XXX - Remote port forwarding */ 633 /* XXX - Remote port forwarding */
625 x_authctxt = authctxt; 634 x_authctxt = authctxt;
626 635
627#ifdef BROKEN_FD_PASSING 636#ifdef DISABLE_FD_PASSING
628 if (1) { 637 if (1) {
629#else 638#else
630 if (authctxt->pw->pw_uid == 0 || options.use_login) { 639 if (authctxt->pw->pw_uid == 0 || options.use_login) {
@@ -649,6 +658,8 @@ privsep_postauth(Authctxt *authctxt)
649 if (pmonitor->m_pid == -1) 658 if (pmonitor->m_pid == -1)
650 fatal("fork of unprivileged child failed"); 659 fatal("fork of unprivileged child failed");
651 else if (pmonitor->m_pid != 0) { 660 else if (pmonitor->m_pid != 0) {
661 fatal_remove_cleanup((void (*) (void *)) packet_close, NULL);
662
652 debug2("User child is on pid %ld", (long)pmonitor->m_pid); 663 debug2("User child is on pid %ld", (long)pmonitor->m_pid);
653 close(pmonitor->m_recvfd); 664 close(pmonitor->m_recvfd);
654 monitor_child_postauth(pmonitor); 665 monitor_child_postauth(pmonitor);
@@ -801,7 +812,6 @@ main(int ac, char **av)
801 const char *remote_ip; 812 const char *remote_ip;
802 int remote_port; 813 int remote_port;
803 FILE *f; 814 FILE *f;
804 struct linger linger;
805 struct addrinfo *ai; 815 struct addrinfo *ai;
806 char ntop[NI_MAXHOST], strport[NI_MAXSERV]; 816 char ntop[NI_MAXHOST], strport[NI_MAXSERV];
807 int listen_sock, maxfd; 817 int listen_sock, maxfd;
@@ -911,6 +921,10 @@ main(int ac, char **av)
911 break; 921 break;
912 case 'u': 922 case 'u':
913 utmp_len = atoi(optarg); 923 utmp_len = atoi(optarg);
924 if (utmp_len > MAXHOSTNAMELEN) {
925 fprintf(stderr, "Invalid utmp length.\n");
926 exit(1);
927 }
914 break; 928 break;
915 case 'o': 929 case 'o':
916 if (process_server_config_line(&options, optarg, 930 if (process_server_config_line(&options, optarg,
@@ -937,7 +951,7 @@ main(int ac, char **av)
937 SYSLOG_FACILITY_AUTH : options.log_facility, 951 SYSLOG_FACILITY_AUTH : options.log_facility,
938 !inetd_flag); 952 !inetd_flag);
939 953
940#ifdef _CRAY 954#ifdef _UNICOS
941 /* Cray can define user privs drop all prives now! 955 /* Cray can define user privs drop all prives now!
942 * Not needed on PRIV_SU systems! 956 * Not needed on PRIV_SU systems!
943 */ 957 */
@@ -961,7 +975,8 @@ main(int ac, char **av)
961 debug("sshd version %.100s", SSH_VERSION); 975 debug("sshd version %.100s", SSH_VERSION);
962 976
963 /* load private host keys */ 977 /* load private host keys */
964 sensitive_data.host_keys = xmalloc(options.num_host_key_files*sizeof(Key*)); 978 sensitive_data.host_keys = xmalloc(options.num_host_key_files *
979 sizeof(Key *));
965 for (i = 0; i < options.num_host_key_files; i++) 980 for (i = 0; i < options.num_host_key_files; i++)
966 sensitive_data.host_keys[i] = NULL; 981 sensitive_data.host_keys[i] = NULL;
967 sensitive_data.server_key = NULL; 982 sensitive_data.server_key = NULL;
@@ -1040,7 +1055,14 @@ main(int ac, char **av)
1040 (S_ISDIR(st.st_mode) == 0)) 1055 (S_ISDIR(st.st_mode) == 0))
1041 fatal("Missing privilege separation directory: %s", 1056 fatal("Missing privilege separation directory: %s",
1042 _PATH_PRIVSEP_CHROOT_DIR); 1057 _PATH_PRIVSEP_CHROOT_DIR);
1058
1059#ifdef HAVE_CYGWIN
1060 if (check_ntsec(_PATH_PRIVSEP_CHROOT_DIR) &&
1061 (st.st_uid != getuid () ||
1062 (st.st_mode & (S_IWGRP|S_IWOTH)) != 0))
1063#else
1043 if (st.st_uid != 0 || (st.st_mode & (S_IWGRP|S_IWOTH)) != 0) 1064 if (st.st_uid != 0 || (st.st_mode & (S_IWGRP|S_IWOTH)) != 0)
1065#endif
1044 fatal("Bad owner or mode for %s", 1066 fatal("Bad owner or mode for %s",
1045 _PATH_PRIVSEP_CHROOT_DIR); 1067 _PATH_PRIVSEP_CHROOT_DIR);
1046 } 1068 }
@@ -1140,17 +1162,12 @@ main(int ac, char **av)
1140 continue; 1162 continue;
1141 } 1163 }
1142 /* 1164 /*
1143 * Set socket options. We try to make the port 1165 * Set socket options.
1144 * reusable and have it close as fast as possible 1166 * Allow local port reuse in TIME_WAIT.
1145 * without waiting in unnecessary wait states on
1146 * close.
1147 */ 1167 */
1148 setsockopt(listen_sock, SOL_SOCKET, SO_REUSEADDR, 1168 if (setsockopt(listen_sock, SOL_SOCKET, SO_REUSEADDR,
1149 &on, sizeof(on)); 1169 &on, sizeof(on)) == -1)
1150 linger.l_onoff = 1; 1170 error("setsockopt SO_REUSEADDR: %s", strerror(errno));
1151 linger.l_linger = 5;
1152 setsockopt(listen_sock, SOL_SOCKET, SO_LINGER,
1153 &linger, sizeof(linger));
1154 1171
1155 debug("Bind to port %s on %s.", strport, ntop); 1172 debug("Bind to port %s on %s.", strport, ntop);
1156 1173
@@ -1399,16 +1416,6 @@ main(int ac, char **av)
1399 signal(SIGCHLD, SIG_DFL); 1416 signal(SIGCHLD, SIG_DFL);
1400 signal(SIGINT, SIG_DFL); 1417 signal(SIGINT, SIG_DFL);
1401 1418
1402 /*
1403 * Set socket options for the connection. We want the socket to
1404 * close as fast as possible without waiting for anything. If the
1405 * connection is not a socket, these will do nothing.
1406 */
1407 /* setsockopt(sock_in, SOL_SOCKET, SO_REUSEADDR, (void *)&on, sizeof(on)); */
1408 linger.l_onoff = 1;
1409 linger.l_linger = 5;
1410 setsockopt(sock_in, SOL_SOCKET, SO_LINGER, &linger, sizeof(linger));
1411
1412 /* Set keepalives if requested. */ 1419 /* Set keepalives if requested. */
1413 if (options.keepalives && 1420 if (options.keepalives &&
1414 setsockopt(sock_in, SOL_SOCKET, SO_KEEPALIVE, &on, 1421 setsockopt(sock_in, SOL_SOCKET, SO_KEEPALIVE, &on,
@@ -1596,7 +1603,7 @@ do_ssh1_kex(void)
1596 u_char session_key[SSH_SESSION_KEY_LENGTH]; 1603 u_char session_key[SSH_SESSION_KEY_LENGTH];
1597 u_char cookie[8]; 1604 u_char cookie[8];
1598 u_int cipher_type, auth_mask, protocol_flags; 1605 u_int cipher_type, auth_mask, protocol_flags;
1599 u_int32_t rand = 0; 1606 u_int32_t rnd = 0;
1600 1607
1601 /* 1608 /*
1602 * Generate check bytes that the client must send back in the user 1609 * Generate check bytes that the client must send back in the user
@@ -1609,9 +1616,9 @@ do_ssh1_kex(void)
1609 */ 1616 */
1610 for (i = 0; i < 8; i++) { 1617 for (i = 0; i < 8; i++) {
1611 if (i % 4 == 0) 1618 if (i % 4 == 0)
1612 rand = arc4random(); 1619 rnd = arc4random();
1613 cookie[i] = rand & 0xff; 1620 cookie[i] = rnd & 0xff;
1614 rand >>= 8; 1621 rnd >>= 8;
1615 } 1622 }
1616 1623
1617 /* 1624 /*