From 1252c0b3a33e4fa30051e6b92cf400724ef0a3ca Mon Sep 17 00:00:00 2001 From: Rosa Date: Wed, 1 Feb 2012 14:38:48 +0400 Subject: [PATCH] Automatic import for version 5.8p2 --- .abf.yml | 4 + README.3.8p1.upgrade.urpmi | 33 + README.3.9p1-3.upgrade.urpmi | 5 + README.hpn | 41 + README.sftpfilecontrol | 22 + openssh-3.1p1-check-only-ssl-version.patch | 11 + openssh-4.0p1-exit-deadlock.patch | 13 + openssh-4.3p2-askpass-grab-info.patch | 18 + openssh-4.3p2-gssapi-canohost.patch | 27 + openssh-4.4p1-watchdog.diff | 468 +++ openssh-4.7p1-audit.patch | 238 ++ openssh-4.9p1.sftplogging-v1.5.diff | 711 ++++ openssh-5.1p1-askpass-progress.patch | 79 + openssh-5.2p1-hpn13v6.diff | 3693 ++++++++++++++++++++ openssh-5.8p2.tar.gz.asc | 7 + openssh-lpk-5.4p1-0.3.10.diff | 1881 ++++++++++ openssh-mdv_conf.diff | 78 + openssh-xinetd | 16 + openssh.spec | 1236 +++++++ openssh5.1-peaktput.diff | 72 + openssh_tcp_wrappers.patch | 19 + ssh-avahi-integration | 40 + ssh-copy-id | 50 + ssh_ldap_key.pl | 29 + sshd.init | 182 + sshd.pam | 7 + sshd.pam-0.77 | 7 + 27 files changed, 8987 insertions(+) create mode 100644 .abf.yml create mode 100644 README.3.8p1.upgrade.urpmi create mode 100644 README.3.9p1-3.upgrade.urpmi create mode 100644 README.hpn create mode 100644 README.sftpfilecontrol create mode 100644 openssh-3.1p1-check-only-ssl-version.patch create mode 100644 openssh-4.0p1-exit-deadlock.patch create mode 100644 openssh-4.3p2-askpass-grab-info.patch create mode 100644 openssh-4.3p2-gssapi-canohost.patch create mode 100644 openssh-4.4p1-watchdog.diff create mode 100644 openssh-4.7p1-audit.patch create mode 100644 openssh-4.9p1.sftplogging-v1.5.diff create mode 100644 openssh-5.1p1-askpass-progress.patch create mode 100644 openssh-5.2p1-hpn13v6.diff create mode 100644 openssh-5.8p2.tar.gz.asc create mode 100644 openssh-lpk-5.4p1-0.3.10.diff create mode 100644 openssh-mdv_conf.diff create mode 100644 openssh-xinetd create mode 100644 openssh.spec create mode 100644 openssh5.1-peaktput.diff create mode 100644 openssh_tcp_wrappers.patch create mode 100644 ssh-avahi-integration create mode 100644 ssh-copy-id create mode 100644 ssh_ldap_key.pl create mode 100644 sshd.init create mode 100644 sshd.pam create mode 100644 sshd.pam-0.77 diff --git a/.abf.yml b/.abf.yml new file mode 100644 index 0000000..84425f1 --- /dev/null +++ b/.abf.yml @@ -0,0 +1,4 @@ +sources: + "openssh-4.4p1-watchdog.patch.tgz": e4a13018c494faf7ed06fd74dad720a8a8ac9089 + "openssh-5.8p2.tar.gz": 64798328d310e4f06c9f01228107520adbc8b3e5 + "x11-ssh-askpass-1.2.4.1.tar.bz2": 2943ce34a319beb5674b623b4557cc8a30e569d0 diff --git a/README.3.8p1.upgrade.urpmi b/README.3.8p1.upgrade.urpmi new file mode 100644 index 0000000..ca2c8d5 --- /dev/null +++ b/README.3.8p1.upgrade.urpmi @@ -0,0 +1,33 @@ +Openssh changes upgrading from <= 3.6p2 to 3.8p1 +Jun-9-2004 Stew Benedict + +Some changes in the behavior of the openssh-server have +taken place in the 3.8p1 upgrade. UsePAM is now "no" by +default, and recommendations are not to enable it lightly. + +That said, some changes have been made to /etc/pam.d/ssh to +preserve expected behavior if UsePAM is enabled: + +auth required pam_listfile.so item=user sense=deny file=/etc/ssh/denyusers + +This line and the entry "root" in the referenced /etc/ssh/denyusers +allows "PermitRootLogin without-password" to behave as expected, +using keys. Otherwise, it's possible to still get a password prompt +and login without keys. + +The package has a trigger to attempt to detect alternative auth methods +(ldap, mysql, winbind), and change UsePAM to yes if one of these are +detected. If you update and suddenly your users can't login via ssh +you may need to review and correct the configuration. Please consult +"man sshd_config" for details of the configuration choices. + +You may also find you need to set: + +ChallengeResponseAuthentication=no + +For things like pam_mkhomedir to work. + +In addition, for X11 forwarding to work in 3.8p1, the option +"ForwardX11Trusted yes" must be enabled in /etc/ssh/ssh_config. +This is enabled by default. + diff --git a/README.3.9p1-3.upgrade.urpmi b/README.3.9p1-3.upgrade.urpmi new file mode 100644 index 0000000..55826ff --- /dev/null +++ b/README.3.9p1-3.upgrade.urpmi @@ -0,0 +1,5 @@ +As of 3.9p1-3mdk, sshd by default only accepts protocol 2 connections. +To restore the old behavior change: + +'Protocol 2' to 'Protocol 2,1' in /etc/ssh/sshd_config + diff --git a/README.hpn b/README.hpn new file mode 100644 index 0000000..247886e --- /dev/null +++ b/README.hpn @@ -0,0 +1,41 @@ +Q: What is HPN-SSH? +A: HPN-SSH is a patch set designed to remove a networking bottleneck in the base OpenSSH code. Removing this bottleneck can improve performance drastically. + +Q: What is this bottleneck? +A: SSH implements a multiplexed connection protocol so a single TCP/IP connection can host multiple SSH sessions at the same time. This means that SSH also has to implement a flow control mechanism in order to make sure that the network connection isn't overwhelmed. Much like TCP/IP it uses a recieve buffer to indicate how much data the sender should be sending at any one point. The developers of OpenSSH have set this buffer size to 64KiloBytes. This is often too small for very high speed connections over long distances. HPN-SSH allows this buffer to grow well past 64KB allowing transfers at very high rates. + +Q: Will HPN-SSH help me? +A: Maybe, it depends on a number of variables but the most important one is the speed of your network connection to the Internet. It also depends on the distance to the destination you are trying to reach. As a general rule of thumb, the farther away the destination and the faster your connection the greater the improvement will be. You can determine how much HPN-SSH will help by multiplying the bandwidth to the destination by the RTT (Round Trip Time). This is called the BDP (Bandwidth Delay Product) and is expressed as BDP = BW(B/s) * RTT(s) and gives you the number of bytes that can be in transit between any two hosts at one time. If this value is less than the previous mention receive buffer on the receiving host then the potential throughput of the connection will be near line rates*. If the BDP is greater than the receive buffer the throughput will be limited in direct proprotion to the difference between the BDP and the receive buffer. As a rule of thumb you will generally need at least a 10Mb/s connection to the internet to see a benefit from HPN-SSH. + +Q: I installed HPN-SSH but there is no improvement. Why not? +A: There are many possible answers to this but its important to understand that HPN-SSH will not make every transfer faster. Transfers in a local area network will not be improved by HPN-SSH and in some case might even be slower (in these cases use the -o HPNDisabled=yes option). You also have to make sure that your computer's network stacks are properly tuned. This is especially critical on the reciever side of the connection. Please see PSC's TCP Tuning page for details on how to do this. You might also be limited by firewalls, packet loss, network errors, and other problems that can affect network performance. + +Q:How do I use HPN-SSH? +A: Generally its a direct replacement for SSH and can be used in the exact same way. However, depending on your operating system you may need to enable some options. For people using Linux kernels that support receive side autotuning (some 2.4 kernels and most 2.6 kernels) and Microsoft Windows Vista you want to use -o TCPRcvBufPoll=yes on the receiver side. This works for both the server and the client. If you do not enable TCPRcvBufPoll your SSH receive buffer will be limited to the initial receive buffer window size (64K for Vista and 85K for Linux). Please read either the HPN-README file distributed as part of the patch or the online version of the HPN-README file for more information on available options. + +Q: What is the NONE Cipher Switch? +A: The NONE cipher switch disables data encryption AFTER you have been authenticated or logged into the remote host. This can significantly reduce the load on the CPUs of both machines and may improve performance even more. Its important to remember that the initial authentication process is still fully encrypted. Additionally, while the data is no longer encrypted each packet is still digitially signed and protected against in transit manipulation of the information. Anytime the NONE cipher is used a warning will be printed to screen saying "WARNING: NONE CIPHER ENABLED". If you do not see that warning then the None cipher is not in use. + +Q: Is it dangerous to use the NONE Cipher Switch? +A: That depends entirelly on what you are trying to do. First off, you can't use the NONE Cipher Switch in an interactive session and is designed to be only used in the transfer of bulk data - like with scp. Second, you should be aware of what kind of data you are transfering. If you are copying financial or medical data then you would not want to use the NONE cipher. However, if you are copying non-sensitive data like MP3s, archives, images, and so forth it may make sense to use the NONE Cipher Switch. You will have to make that determination yourself. Lastly, since the authentication process is still encrypted hackers and eavesdroppers will not be able to steal your password. + +Q: I have '-oNoneSwitch=yes' on the command line. Why doesn't it work? +A: You must use both '-oNoneSwitch=yes' and '-oNoneEnabled=yes' on the client command line. Only using one or the other will not work. Additionally, the None cipher must be enabled on the server with NoneEnabled=yes in the sshd_config file or on the command line. Anytime the None cipher is used a warning will be printed to screen saying "WARNING: NONE CIPHER ENABLED". If you do not see that warning then the NONE cipher is not in use. + +Q: I'm having a lot of problems using HPN-SSH can you help me? +A: We will certainly do our best but please try see PSC's TCP Tuning page first. If you are still having problems then contact us at hpn-ssh@psc.edu and include the following information. + + * The version of the operating system on both sides of the connection. + * The version of HPN-SSH you are using. + * As much information as you can about the network path (bandwidth, RTT, loss, etc) + * The level of throughput performance you expect to see and what you are seeing. + * The receive buffer sizes of the hosts + * Any other information you feel is important + +We can't help everyone but we will do our best. + +Q:If this HPN-SSH is so great why isn't it in the OpenSSH code base? +A: The HPN-SSH patch has been made available to the OpenSSH development team and I hope it will be incorporated (in either its current or some other form) in the near future. However, the team has other priorities and I'm perfectly able to maintain this patch until they can free up some time. Quite a number of organization are using HPN-SSH though including NASA, Sun Microsystems, HP, financial companies, research organizations, supercomputing ceneters, security concerns, and software developers. + +Q:I have a suggestion for HPN-SSH or this FAQ, a comment, want to send thanks, or ask some other question. Who should I contact? +A: To contact us with any suggestions, questions, comments, or criticisms please contact us at hpn-ssh@psc.edu diff --git a/README.sftpfilecontrol b/README.sftpfilecontrol new file mode 100644 index 0000000..9b15736 --- /dev/null +++ b/README.sftpfilecontrol @@ -0,0 +1,22 @@ +Sftpfilecontrol Patch v1.2 +A patch to provide control over umask, chmod, chown, and chgrp in the sftp-server that comes with openssh. +This patch is derived from the sftplogging patch. + +Original patch by Michael Martinez +Copyright (c) 2002 - 2007, Michael Martinez +All rights reserved. + +Redistribution and use in source and binary forms, with or without modification, are permitted provided that the +following conditions are met: + +- Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. +- Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. +- Neither the name of Michael Martinez nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, +INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF +LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/openssh-3.1p1-check-only-ssl-version.patch b/openssh-3.1p1-check-only-ssl-version.patch new file mode 100644 index 0000000..4002540 --- /dev/null +++ b/openssh-3.1p1-check-only-ssl-version.patch @@ -0,0 +1,11 @@ +--- openssh-5.7p1/entropy.c.mdv 2011-01-13 08:05:29.000000000 -0200 ++++ openssh-5.7p1/entropy.c 2011-01-29 15:41:52.000000000 -0200 +@@ -155,7 +155,7 @@ init_rng(void) + * OpenSSL version numbers: MNNFFPPS: major minor fix patch status + * We match major, minor, fix and status (not patch) + */ +- if ((SSLeay() ^ OPENSSL_VERSION_NUMBER) & ~0xff0L) ++ if ((SSLeay() >> 12) != (OPENSSL_VERSION_NUMBER >> 12)) + fatal("OpenSSL version mismatch. Built against %lx, you " + "have %lx", (u_long)OPENSSL_VERSION_NUMBER, SSLeay()); + diff --git a/openssh-4.0p1-exit-deadlock.patch b/openssh-4.0p1-exit-deadlock.patch new file mode 100644 index 0000000..66246d3 --- /dev/null +++ b/openssh-4.0p1-exit-deadlock.patch @@ -0,0 +1,13 @@ +--- openssh-4.0p1/channels.c.exit-deadlock 2005-03-01 11:24:33.000000000 +0100 ++++ openssh-4.0p1/channels.c 2005-04-05 22:25:15.197226237 +0200 +@@ -1403,6 +1403,10 @@ + u_int dlen; + int len; + ++ if(c->wfd != -1 && buffer_len(&c->output) > 0 && c->ostate == CHAN_OUTPUT_WAIT_DRAIN) { ++ debug("channel %d: forcing write", c->self); ++ FD_SET(c->wfd, writeset); ++ } + /* Send buffered output data to the socket. */ + if (c->wfd != -1 && + FD_ISSET(c->wfd, writeset) && diff --git a/openssh-4.3p2-askpass-grab-info.patch b/openssh-4.3p2-askpass-grab-info.patch new file mode 100644 index 0000000..e9dc835 --- /dev/null +++ b/openssh-4.3p2-askpass-grab-info.patch @@ -0,0 +1,18 @@ +--- openssh-4.3p2/contrib/gnome-ssh-askpass2.c.grab-info 2006-07-17 15:10:11.000000000 +0200 ++++ openssh-4.3p2/contrib/gnome-ssh-askpass2.c 2006-07-17 15:25:04.000000000 +0200 +@@ -65,9 +65,12 @@ + err = gtk_message_dialog_new(NULL, 0, + GTK_MESSAGE_ERROR, + GTK_BUTTONS_CLOSE, +- "Could not grab %s. " +- "A malicious client may be eavesdropping " +- "on your session.", what); ++ "SSH password dialog could not grab the %s input.\n" ++ "This might be caused by application such as screensaver, " ++ "however it could also mean that someone may be eavesdropping " ++ "on your session.\n" ++ "Either close the application which grabs the %s or " ++ "log out and log in again to prevent this from happening.", what, what); + gtk_window_set_position(GTK_WINDOW(err), GTK_WIN_POS_CENTER); + gtk_label_set_line_wrap(GTK_LABEL((GTK_MESSAGE_DIALOG(err))->label), + TRUE); diff --git a/openssh-4.3p2-gssapi-canohost.patch b/openssh-4.3p2-gssapi-canohost.patch new file mode 100644 index 0000000..190c1dd --- /dev/null +++ b/openssh-4.3p2-gssapi-canohost.patch @@ -0,0 +1,27 @@ +Symptom: intermittent errors on GSSAPI authentication vs +machines on DNS loadbalancer, stupid client message "Generic Error", +server-side debug complains about unknown principal. + +Comes from the fact that we resolve the generic DNS name once for +the connection, then again for getting the GSSAPI/Kerberos service +ticket. So the service ticket may be for a different host, if +the DNS alias switches in between the two resolves. +--- openssh-4.3p2/sshconnect2.c.gss-canohost 2006-11-28 21:58:03.000000000 +0100 ++++ openssh-4.3p2/sshconnect2.c 2006-11-30 11:33:14.000000000 +0100 +@@ -485,6 +485,7 @@ + static u_int mech = 0; + OM_uint32 min; + int ok = 0; ++ const char* remotehost = get_canonical_hostname(1); + + /* Try one GSSAPI method at a time, rather than sending them all at + * once. */ +@@ -497,7 +498,7 @@ + /* My DER encoding requires length<128 */ + if (gss_supported->elements[mech].length < 128 && + ssh_gssapi_check_mechanism(&gssctxt, +- &gss_supported->elements[mech], authctxt->host)) { ++ &gss_supported->elements[mech], remotehost)) { + ok = 1; /* Mechanism works */ + } else { + mech++; diff --git a/openssh-4.4p1-watchdog.diff b/openssh-4.4p1-watchdog.diff new file mode 100644 index 0000000..a27fb45 --- /dev/null +++ b/openssh-4.4p1-watchdog.diff @@ -0,0 +1,468 @@ +diff -Naurp openssh-5.3p1/clientloop.c openssh-5.3p1.oden/clientloop.c +--- openssh-5.3p1/clientloop.c 2009-08-28 03:21:07.000000000 +0200 ++++ openssh-5.3p1.oden/clientloop.c 2009-10-07 17:39:17.000000000 +0200 +@@ -155,6 +155,7 @@ static Buffer stderr_buffer; /* Buffer f + static u_int buffer_high;/* Soft max buffer size. */ + static int connection_in; /* Connection to server (input). */ + static int connection_out; /* Connection to server (output). */ ++static time_t idle_time_last; /* Last time of packet transmission. */ + static int need_rekeying; /* Set to non-zero if rekeying is requested. */ + static int session_closed = 0; /* In SSH2: login session closed. */ + +@@ -568,16 +569,19 @@ client_wait_until_can_do_something(fd_se + * event pending. + */ + +- if (options.server_alive_interval == 0 || !compat20) +- tvp = NULL; +- else { ++ if (options.server_alive_interval != 0 && compat20){ + tv.tv_sec = options.server_alive_interval; +- tv.tv_usec = 0; ++ tv.tv_usec = 0; ++ tvp = &tv; ++ } ++ else{ ++ tv.tv_sec = 0; ++ tv.tv_usec = 500 * 1000; /* time slot is 0.5sec */ + tvp = &tv; + } +- ret = select((*maxfdp)+1, *readsetp, *writesetp, NULL, tvp); +- if (ret < 0) { +- char buf[100]; ++ ret = select((*maxfdp)+1, *readsetp, *writesetp, NULL, tvp); ++ if (ret < 0) { ++ char buf[100]; + + /* + * We have to clear the select masks, because we return. +@@ -593,8 +597,43 @@ client_wait_until_can_do_something(fd_se + snprintf(buf, sizeof buf, "select: %s\r\n", strerror(errno)); + buffer_append(&stderr_buffer, buf, strlen(buf)); + quit_pending = 1; +- } else if (ret == 0) +- server_alive_check(); ++ } else if (ret == 0){ ++ if (options.server_alive_interval != 0 && compat20){ ++ server_alive_check(); ++ } ++ } ++ ++ /* If the output channel has been silent for more than a specified ++ * time, send a keepalive packet (heartbeat) to the server. ++ * Keepalive packet is useful for keeping the connection over ++ * IP masquerade / NAT boxes, firewalls, etc. ++ * Some servers equipped with a watchdog timer require keepalive ++ * packets (heartbeats) to detect link down. ++ * ++ * Note: Although the interval between keepalive packets is not ++ * very precise, it's okay. ++ * ++ * Note: Some old servers may crash when they receive SSH_MSG_IGNORE. ++ * Those who want to connect to such a server should turn this ++ * function off by the option setting (e.g. Heartbeat 0). ++ */ ++ if (options.heartbeat_interval > 0) { ++ if (FD_ISSET(connection_out,*writesetp)) { ++ /* Update the time of last data transmission. */ ++ idle_time_last = time(NULL); ++ } ++ if (time(NULL) - idle_time_last >= (int)options.heartbeat_interval){ ++ if (compat20) { ++ packet_start(SSH2_MSG_IGNORE); ++ } ++ else { ++ packet_start(SSH_MSG_IGNORE); ++ } ++ packet_put_string("", 0); ++ packet_send(); ++ /* fputs("*",stderr); */ ++ } ++ } + } + + static void +@@ -1312,6 +1351,7 @@ client_loop(int have_pty, int escape_cha + debug("Entering interactive session."); + + start_time = get_current_time(); ++ idle_time_last = time(NULL); + + /* Initialize variables. */ + escape_pending1 = 0; +diff -Naurp openssh-5.3p1/readconf.c openssh-5.3p1.oden/readconf.c +--- openssh-5.3p1/readconf.c 2009-07-05 23:12:27.000000000 +0200 ++++ openssh-5.3p1.oden/readconf.c 2009-10-07 17:39:17.000000000 +0200 +@@ -118,7 +118,7 @@ typedef enum { + oUser, oHost, oEscapeChar, oRhostsRSAAuthentication, oProxyCommand, + oGlobalKnownHostsFile, oUserKnownHostsFile, oConnectionAttempts, + oBatchMode, oCheckHostIP, oStrictHostKeyChecking, oCompression, +- oCompressionLevel, oTCPKeepAlive, oNumberOfPasswordPrompts, ++ oCompressionLevel, oTCPKeepAlive, oHeartbeat, oNumberOfPasswordPrompts, + oUsePrivilegedPort, oLogLevel, oCiphers, oProtocol, oMacs, + oGlobalKnownHostsFile2, oUserKnownHostsFile2, oPubkeyAuthentication, + oKbdInteractiveAuthentication, oKbdInteractiveDevices, oHostKeyAlias, +@@ -199,6 +199,7 @@ static struct { + { "compressionlevel", oCompressionLevel }, + { "tcpkeepalive", oTCPKeepAlive }, + { "keepalive", oTCPKeepAlive }, /* obsolete */ ++ { "heartbeat", oHeartbeat }, + { "numberofpasswordprompts", oNumberOfPasswordPrompts }, + { "loglevel", oLogLevel }, + { "dynamicforward", oDynamicForward }, +@@ -502,6 +503,10 @@ parse_yesnoask: + intptr = &options->no_host_authentication_for_localhost; + goto parse_flag; + ++ case oHeartbeat: ++ intptr = &options->heartbeat_interval; ++ goto parse_int; ++ + case oNumberOfPasswordPrompts: + intptr = &options->number_of_password_prompts; + goto parse_int; +@@ -1024,6 +1029,7 @@ initialize_options(Options * options) + options->strict_host_key_checking = -1; + options->compression = -1; + options->tcp_keep_alive = -1; ++ options->heartbeat_interval = -1; + options->compression_level = -1; + options->port = -1; + options->address_family = -1; +@@ -1125,6 +1131,8 @@ fill_default_options(Options * options) + options->compression = 0; + if (options->tcp_keep_alive == -1) + options->tcp_keep_alive = 1; ++ if (options->heartbeat_interval == -1) ++ options->heartbeat_interval = 0; /* 0 means "no heartbeat" */ + if (options->compression_level == -1) + options->compression_level = 6; + if (options->port == -1) +diff -Naurp openssh-5.3p1/readconf.h openssh-5.3p1.oden/readconf.h +--- openssh-5.3p1/readconf.h 2009-07-05 23:12:27.000000000 +0200 ++++ openssh-5.3p1.oden/readconf.h 2009-10-07 17:39:17.000000000 +0200 +@@ -57,6 +57,9 @@ typedef struct { + int compression_level; /* Compression level 1 (fast) to 9 + * (best). */ + int tcp_keep_alive; /* Set SO_KEEPALIVE. */ ++ int heartbeat_interval; /* Number of seconds between keepalive ++ * packets (heartbeats) over encrypted ++ * channel. (in secs.) */ + LogLevel log_level; /* Level for logging. */ + + int port; /* Port to connect. */ +diff -Naurp openssh-5.3p1/servconf.c openssh-5.3p1.oden/servconf.c +--- openssh-5.3p1/servconf.c 2009-06-21 12:26:17.000000000 +0200 ++++ openssh-5.3p1.oden/servconf.c 2009-10-07 17:39:17.000000000 +0200 +@@ -80,6 +80,8 @@ initialize_server_options(ServerOptions + options->xauth_location = NULL; + options->strict_modes = -1; + options->tcp_keep_alive = -1; ++ options->watchdog_timeout = -1; ++ options->watchdog_timeout1 = -1; + options->log_facility = SYSLOG_FACILITY_NOT_SET; + options->log_level = SYSLOG_LEVEL_NOT_SET; + options->rhosts_rsa_authentication = -1; +@@ -186,6 +188,10 @@ fill_default_server_options(ServerOption + options->strict_modes = 1; + if (options->tcp_keep_alive == -1) + options->tcp_keep_alive = 1; ++ if (options->watchdog_timeout == -1) ++ options->watchdog_timeout = 0; /* 0 means "no timeout" */ ++ if (options->watchdog_timeout1 == -1) ++ options->watchdog_timeout1 = 0; /* 0 means "no timeout" */ + if (options->log_facility == SYSLOG_FACILITY_NOT_SET) + options->log_facility = SYSLOG_FACILITY_AUTH; + if (options->log_level == SYSLOG_LEVEL_NOT_SET) +@@ -293,7 +299,7 @@ typedef enum { + sListenAddress, sAddressFamily, + sPrintMotd, sPrintLastLog, sIgnoreRhosts, + sX11Forwarding, sX11DisplayOffset, sX11UseLocalhost, +- sStrictModes, sEmptyPasswd, sTCPKeepAlive, ++ sStrictModes, sEmptyPasswd, sTCPKeepAlive, sWatchdogTimeout, sWatchdogTimeout1, + sPermitUserEnvironment, sUseLogin, sAllowTcpForwarding, sCompression, + sAllowUsers, sDenyUsers, sAllowGroups, sDenyGroups, + sIgnoreUserKnownHosts, sCiphers, sMacs, sProtocol, sPidFile, +@@ -395,6 +401,8 @@ static struct { + { "compression", sCompression, SSHCFG_GLOBAL }, + { "tcpkeepalive", sTCPKeepAlive, SSHCFG_GLOBAL }, + { "keepalive", sTCPKeepAlive, SSHCFG_GLOBAL }, /* obsolete alias */ ++ { "watchdogtimeout", sWatchdogTimeout, SSHCFG_GLOBAL }, ++ { "watchdogtimeout1", sWatchdogTimeout1, SSHCFG_GLOBAL }, + { "allowtcpforwarding", sAllowTcpForwarding, SSHCFG_ALL }, + { "allowagentforwarding", sAllowAgentForwarding, SSHCFG_ALL }, + { "allowusers", sAllowUsers, SSHCFG_GLOBAL }, +@@ -943,6 +951,14 @@ process_server_config_line(ServerOptions + intptr = &options->tcp_keep_alive; + goto parse_flag; + ++ case sWatchdogTimeout: ++ intptr = &options->watchdog_timeout; ++ goto parse_int; ++ ++ case sWatchdogTimeout1: ++ intptr = &options->watchdog_timeout1; ++ goto parse_int; ++ + case sEmptyPasswd: + intptr = &options->permit_empty_passwd; + goto parse_flag; +diff -Naurp openssh-5.3p1/servconf.h openssh-5.3p1.oden/servconf.h +--- openssh-5.3p1/servconf.h 2009-01-28 06:31:23.000000000 +0100 ++++ openssh-5.3p1.oden/servconf.h 2009-10-07 17:39:17.000000000 +0200 +@@ -67,6 +67,10 @@ typedef struct { + char *xauth_location; /* Location of xauth program */ + int strict_modes; /* If true, require string home dir modes. */ + int tcp_keep_alive; /* If true, set SO_KEEPALIVE. */ ++ int watchdog_timeout, watchdog_timeout1; ++ /* Timeout of the watchdog timer which ++ checks the input activities over ++ encrypted channel. (in secs.) */ + char *ciphers; /* Supported SSH2 ciphers. */ + char *macs; /* Supported SSH2 macs. */ + int protocol; /* Supported protocol versions. */ +diff -Naurp openssh-5.3p1/serverloop.c openssh-5.3p1.oden/serverloop.c +--- openssh-5.3p1/serverloop.c 2009-09-09 03:07:28.000000000 +0200 ++++ openssh-5.3p1.oden/serverloop.c 2009-10-07 17:40:09.000000000 +0200 +@@ -107,6 +107,8 @@ static int connection_out; /* Connection + static int connection_closed = 0; /* Connection to client closed. */ + static u_int buffer_high; /* "Soft" max buffer size. */ + static int no_more_sessions = 0; /* Disallow further sessions. */ ++static time_t idle_time_last; /* Last time of packet receipt. */ ++static int child_forced_to_terminate; /* The child will be killed by sshd. */ + + /* + * This SIGCHLD kludge is used to detect when the child exits. The server +@@ -281,6 +283,7 @@ wait_until_can_do_something(fd_set **rea + { + struct timeval tv, *tvp; + int ret; ++ int watchdog_timeout = 0; + int client_alive_scheduled = 0; + int program_alive_scheduled = 0; + +@@ -350,6 +353,19 @@ wait_until_can_do_something(fd_set **rea + if (max_time_milliseconds == 0 || client_alive_scheduled) + max_time_milliseconds = 100; + ++ /* When the watchdog is needed, set the maximum length ++ * of timeout to 0.25sec. ++ */ ++ watchdog_timeout = options.watchdog_timeout; ++ if (!compat20 && options.watchdog_timeout1 > 0){ ++ watchdog_timeout = options.watchdog_timeout1; ++ } ++ if (watchdog_timeout > 0) { ++ if (max_time_milliseconds == 0 || max_time_milliseconds > 250) { ++ max_time_milliseconds = 250; ++ } ++ } ++ + if (max_time_milliseconds == 0) + tvp = NULL; + else { +@@ -377,6 +393,23 @@ wait_until_can_do_something(fd_set **rea + } + } + ++ /* ++ * Watchdog timer: ++ * If the input channel has been silent for more than the specified ++ * time, try to kill the child process(es) to protect server resources. ++ */ ++ if (watchdog_timeout > 0) { ++ if (FD_ISSET(connection_in,*readsetp)) { ++ /* Update the time of last data receipt. */ ++ idle_time_last = time(NULL); ++ /* fputs("*",stderr); */ ++ } ++ if (!child_terminated && \ ++ (time(NULL) - idle_time_last) > watchdog_timeout) { ++ child_forced_to_terminate = 1; ++ } ++ } ++ + notify_done(*readsetp); + } + +@@ -560,7 +593,9 @@ server_loop(pid_t pid, int fdin_arg, int + u_int max_time_milliseconds; + u_int previous_stdout_buffer_bytes; + u_int stdout_buffer_bytes; +- int type; ++ int type, i; ++ ++ child_forced_to_terminate = 0; + + debug("Entering interactive session."); + +@@ -627,6 +662,8 @@ server_loop(pid_t pid, int fdin_arg, int + + server_init_dispatch(); + ++ idle_time_last = time(NULL); ++ + /* Main loop of the server for the interactive session mode. */ + for (;;) { + +@@ -707,6 +744,9 @@ server_loop(pid_t pid, int fdin_arg, int + cleanup_exit(255); + } + ++ /* Break, if watchdog timeout occured. */ ++ if (child_forced_to_terminate) break; ++ + /* Process any channel events. */ + channel_after_select(readset, writeset); + +@@ -716,6 +756,24 @@ server_loop(pid_t pid, int fdin_arg, int + /* Process output to the client and to program stdin. */ + process_output(writeset); + } ++ ++ /* ++ * If the child should be terminated due to ++ * watchdog timeout, send kill signal to the child. ++ */ ++ if (child_forced_to_terminate) { ++ /* We won't have pid=0. However, for safety... */ ++ if ( pid != 0 ){ ++ kill(pid, SIGHUP); ++ for (i=0 ; i<5 ; i++){ ++ sleep(1); ++ if (child_terminated) break; ++ } ++ if (i>=5) kill(pid, SIGKILL); ++ logit("Warning: Command has been killed due to watchdog timeout."); ++ } ++ } ++ + if (readset) + xfree(readset); + if (writeset) +@@ -724,7 +782,9 @@ server_loop(pid_t pid, int fdin_arg, int + /* Cleanup and termination code. */ + + /* Wait until all output has been sent to the client. */ +- drain_output(); ++ if (!child_forced_to_terminate) { ++ drain_output(); ++ } + + debug("End of interactive session; stdin %ld, stdout (read %ld, sent %ld), stderr %ld bytes.", + stdin_bytes, fdout_bytes, stdout_bytes, stderr_bytes); +@@ -752,6 +812,12 @@ server_loop(pid_t pid, int fdin_arg, int + /* We no longer want our SIGCHLD handler to be called. */ + mysignal(SIGCHLD, SIG_DFL); + ++ /* If the child has been terminated, free the session and exit here. */ ++ if (child_forced_to_terminate) { ++ session_destroy_all(NULL); ++ return; ++ } ++ + while ((wait_pid = waitpid(-1, &wait_status, 0)) < 0) + if (errno != EINTR) + packet_disconnect("wait: %.100s", strerror(errno)); +@@ -825,6 +891,7 @@ server_loop2(Authctxt *authctxt) + + mysignal(SIGCHLD, sigchld_handler); + child_terminated = 0; ++ child_forced_to_terminate = 0; + connection_in = packet_get_connection_in(); + connection_out = packet_get_connection_out(); + +@@ -841,6 +908,8 @@ server_loop2(Authctxt *authctxt) + + server_init_dispatch(); + ++ idle_time_last = time(NULL); ++ + for (;;) { + process_buffered_input_packets(); + +@@ -857,6 +926,12 @@ server_loop2(Authctxt *authctxt) + cleanup_exit(255); + } + ++ /* Terminate child processes, if watchdog timeout occured. */ ++ if (child_forced_to_terminate){ ++ packet_disconnect("Command has been killed due to watchdog timeout."); ++ logit("Warning: Command has been killed due to watchdog timeout."); ++ } ++ + collect_children(); + if (!rekeying) { + channel_after_select(readset, writeset); +diff -Naurp openssh-5.3p1/ssh.1 openssh-5.3p1.oden/ssh.1 +--- openssh-5.3p1/ssh.1 2009-06-21 09:48:52.000000000 +0200 ++++ openssh-5.3p1.oden/ssh.1 2009-10-07 17:39:17.000000000 +0200 +@@ -453,6 +453,7 @@ For full details of the options listed b + .It GSSAPIAuthentication + .It GSSAPIDelegateCredentials + .It HashKnownHosts ++.It Heartbeat + .It Host + .It HostbasedAuthentication + .It HostKeyAlgorithms +diff -Naurp openssh-5.3p1/ssh_config.5 openssh-5.3p1.oden/ssh_config.5 +--- openssh-5.3p1/ssh_config.5 2009-02-23 00:53:58.000000000 +0100 ++++ openssh-5.3p1.oden/ssh_config.5 2009-10-07 17:39:17.000000000 +0200 +@@ -500,6 +500,23 @@ Note that existing names and addresses i + will not be converted automatically, + but may be manually hashed using + .Xr ssh-keygen 1 . ++.It Cm Heartbeat ++Specifies the interval between heartbeats, in seconds. If the output ++channel has been silent for more than the specified time, a null message ++(SSH_MSG_IGNORE) is sent to the server. ++.Cm Heartbeat ++is useful for keeping alive connections over IP masquerade / NAT boxes, ++firewalls, etc., that implement connection timeouts, and in combination ++with the ++.Cm WatchdogTimeout ++option to ++.Xr sshd 8 . ++Heartbeat does not work if ++.Cm ServerAliveInterval ++is enabled at the same time. ++The default is ++.Dq 0 , ++which disables the hearbeat. + .It Cm HostbasedAuthentication + Specifies whether to try rhosts based authentication with public key + authentication. +diff -Naurp openssh-5.3p1/sshd_config.5 openssh-5.3p1.oden/sshd_config.5 +--- openssh-5.3p1/sshd_config.5 2009-08-28 02:27:08.000000000 +0200 ++++ openssh-5.3p1.oden/sshd_config.5 2009-10-07 17:39:17.000000000 +0200 +@@ -939,6 +939,30 @@ The goal of privilege separation is to p + escalation by containing any corruption within the unprivileged processes. + The default is + .Dq yes . ++.It Cm WatchdogTimeout ++Specifies the watchdog timeout interval, in seconds. ++If a session input channel has been silent for more than the specified interval, ++.Cm sshd ++terminates the session by killing the child process(es). Only input ++packets from the client reset the watchdog timer; this makes it possible ++to terminate a session even if the serever continues sending some data ++to the client. ++When used in combination with ++.Cm ClientAliveInterval ++and/or the ++.Cm Heartbeat ++option of ++.Xr ssh 1 ++this feature will detect and terminate hung sessions over unreliable ++networks, without interfering with normal usage. ++The default is ++.Dq 0 , ++which disables the watchdog. ++.It Cm WatchdogTimeout1 ++Specifies the watchdog timeout interval, in seconds, for SSH1 protocol ++only. See the ++.Cm WatchdogTimeout ++option. + .It Cm X11DisplayOffset + Specifies the first display number available for + .Xr sshd 8 Ns 's diff --git a/openssh-4.7p1-audit.patch b/openssh-4.7p1-audit.patch new file mode 100644 index 0000000..faf66bb --- /dev/null +++ b/openssh-4.7p1-audit.patch @@ -0,0 +1,238 @@ +diff -Naurp openssh-5.3p1/auth.c openssh-5.3p1.oden/auth.c +--- openssh-5.3p1/auth.c 2008-11-05 06:12:54.000000000 +0100 ++++ openssh-5.3p1.oden/auth.c 2009-10-07 18:46:05.000000000 +0200 +@@ -287,6 +287,12 @@ auth_log(Authctxt *authctxt, int authent + get_canonical_hostname(options.use_dns), "ssh", &loginmsg); + # endif + #endif ++#if HAVE_LINUX_AUDIT ++ if (authenticated == 0 && !authctxt->postponed) { ++ linux_audit_record_event(-1, authctxt->user, NULL, ++ get_remote_ipaddr(), "sshd", 0); ++ } ++#endif + #ifdef SSH_AUDIT_EVENTS + if (authenticated == 0 && !authctxt->postponed) + audit_event(audit_classify_auth(method)); +@@ -533,6 +539,10 @@ getpwnamallow(const char *user) + record_failed_login(user, + get_canonical_hostname(options.use_dns), "ssh"); + #endif ++#ifdef HAVE_LINUX_AUDIT ++ linux_audit_record_event(-1, user, NULL, get_remote_ipaddr(), ++ "sshd", 0); ++#endif + #ifdef SSH_AUDIT_EVENTS + audit_event(SSH_INVALID_USER); + #endif /* SSH_AUDIT_EVENTS */ +diff -Naurp openssh-5.3p1/config.h.in openssh-5.3p1.oden/config.h.in +--- openssh-5.3p1/config.h.in 2009-09-26 08:31:14.000000000 +0200 ++++ openssh-5.3p1.oden/config.h.in 2009-10-07 18:46:05.000000000 +0200 +@@ -533,6 +533,9 @@ + /* Define to 1 if you have the header file. */ + #undef HAVE_LASTLOG_H + ++/* Define to 1 if you have the header file. */ ++#undef HAVE_LIBAUDIT_H ++ + /* Define to 1 if you have the `bsm' library (-lbsm). */ + #undef HAVE_LIBBSM + +@@ -572,6 +575,9 @@ + /* Define to 1 if you have the header file. */ + #undef HAVE_LIMITS_H + ++/* Define if you want Linux audit support. */ ++#undef HAVE_LINUX_AUDIT ++ + /* Define to 1 if you have the header file. */ + #undef HAVE_LINUX_IF_TUN_H + +@@ -768,6 +774,9 @@ + /* Define to 1 if you have the `setgroups' function. */ + #undef HAVE_SETGROUPS + ++/* Define to 1 if you have the `setkeycreatecon' function. */ ++#undef HAVE_SETKEYCREATECON ++ + /* Define to 1 if you have the `setlogin' function. */ + #undef HAVE_SETLOGIN + +@@ -1348,6 +1357,11 @@ + /* Prepend the address family to IP tunnel traffic */ + #undef SSH_TUN_PREPEND_AF + ++/* Define to your vendor patch level, if it has been modified from the ++ upstream source release. */ ++#undef SSH_VENDOR_PATCHLEVEL ++ ++ + /* Define to 1 if you have the ANSI C header files. */ + #undef STDC_HEADERS + +diff -Naurp openssh-5.3p1/configure.ac openssh-5.3p1.oden/configure.ac +--- openssh-5.3p1/configure.ac 2009-09-11 06:56:08.000000000 +0200 ++++ openssh-5.3p1.oden/configure.ac 2009-10-07 18:46:05.000000000 +0200 +@@ -3407,6 +3407,18 @@ AC_ARG_WITH(selinux, + fi ] + ) + ++# Check whether user wants Linux audit support ++LINUX_AUDIT_MSG="no" ++AC_ARG_WITH(linux-audit, ++ [ --with-linux-audit Enable Linux audit support], ++ [ if test "x$withval" != "xno" ; then ++ AC_DEFINE(HAVE_LINUX_AUDIT,1,[Define if you want Linux audit support.]) ++ LINUX_AUDIT_MSG="yes" ++ AC_CHECK_HEADERS(libaudit.h) ++ SSHDLIBS="$SSHDLIBS -laudit" ++ fi ] ++) ++ + # Check whether user wants Kerberos 5 support + KRB5_MSG="no" + AC_ARG_WITH(kerberos5, +@@ -4226,6 +4238,7 @@ echo " PAM support + echo " OSF SIA support: $SIA_MSG" + echo " KerberosV support: $KRB5_MSG" + echo " SELinux support: $SELINUX_MSG" ++echo " Linux audit support: $LINUX_AUDIT_MSG" + echo " Smartcard support: $SCARD_MSG" + echo " S/KEY support: $SKEY_MSG" + echo " TCP Wrappers support: $TCPW_MSG" +diff -Naurp openssh-5.3p1/loginrec.c openssh-5.3p1.oden/loginrec.c +--- openssh-5.3p1/loginrec.c 2009-02-12 03:12:22.000000000 +0100 ++++ openssh-5.3p1.oden/loginrec.c 2009-10-07 18:46:05.000000000 +0200 +@@ -176,6 +176,10 @@ + #include "auth.h" + #include "buffer.h" + ++#ifdef HAVE_LINUX_AUDIT ++# include ++#endif ++ + #ifdef HAVE_UTIL_H + # include + #endif +@@ -202,6 +206,9 @@ int utmp_write_entry(struct logininfo *l + int utmpx_write_entry(struct logininfo *li); + int wtmp_write_entry(struct logininfo *li); + int wtmpx_write_entry(struct logininfo *li); ++#ifdef HAVE_LINUX_AUDIT ++int linux_audit_write_entry(struct logininfo *li); ++#endif + int lastlog_write_entry(struct logininfo *li); + int syslogin_write_entry(struct logininfo *li); + +@@ -440,6 +447,10 @@ login_write(struct logininfo *li) + + /* set the timestamp */ + login_set_current_time(li); ++#ifdef HAVE_LINUX_AUDIT ++ if (linux_audit_write_entry(li) == 0) ++ fatal("linux_audit_write_entry failed: %s", strerror(errno)); ++#endif + #ifdef USE_LOGIN + syslogin_write_entry(li); + #endif +@@ -1394,6 +1405,87 @@ wtmpx_get_entry(struct logininfo *li) + } + #endif /* USE_WTMPX */ + ++#ifdef HAVE_LINUX_AUDIT ++static void ++_audit_hexscape(const char *what, char *where, unsigned int size) ++{ ++ const char *ptr = what; ++ const char *hex = "0123456789ABCDEF"; ++ ++ while (*ptr) { ++ if (*ptr == '"' || *ptr < 0x21 || *ptr > 0x7E) { ++ unsigned int i; ++ ptr = what; ++ for (i = 0; *ptr && i+2 < size; i += 2) { ++ where[i] = hex[((unsigned)*ptr & 0xF0)>>4]; /* Upper nibble */ ++ where[i+1] = hex[(unsigned)*ptr & 0x0F]; /* Lower nibble */ ++ ptr++; ++ } ++ where[i] = '\0'; ++ return; ++ } ++ ptr++; ++ } ++ where[0] = '"'; ++ if ((unsigned)(ptr - what) < size - 3) ++ { ++ size = ptr - what + 3; ++ } ++ strncpy(where + 1, what, size - 3); ++ where[size-2] = '"'; ++ where[size-1] = '\0'; ++} ++ ++#define AUDIT_LOG_SIZE 128 ++#define AUDIT_ACCT_SIZE (AUDIT_LOG_SIZE - 8) ++ ++int ++linux_audit_record_event(int uid, const char *username, ++ const char *hostname, const char *ip, const char *ttyn, int success) ++{ ++ char buf[AUDIT_LOG_SIZE]; ++ int audit_fd, rc; ++ ++ audit_fd = audit_open(); ++ if (audit_fd < 0) { ++ if (errno == EINVAL || errno == EPROTONOSUPPORT || ++ errno == EAFNOSUPPORT) ++ return 1; /* No audit support in kernel */ ++ else ++ return 0; /* Must prevent login */ ++ } ++ if (username == NULL) ++ snprintf(buf, sizeof(buf), "uid=%d", uid); ++ else { ++ char encoded[AUDIT_ACCT_SIZE]; ++ _audit_hexscape(username, encoded, sizeof(encoded)); ++ snprintf(buf, sizeof(buf), "acct=%s", encoded); ++ } ++ rc = audit_log_user_message(audit_fd, AUDIT_USER_LOGIN, ++ buf, hostname, ip, ttyn, success); ++ close(audit_fd); ++ if (rc >= 0) ++ return 1; ++ else ++ return 0; ++} ++ ++int ++linux_audit_write_entry(struct logininfo *li) ++{ ++ switch(li->type) { ++ case LTYPE_LOGIN: ++ return (linux_audit_record_event(li->uid, NULL, li->hostname, ++ NULL, li->line, 1)); ++ case LTYPE_LOGOUT: ++ return (1); /* We only care about logins */ ++ default: ++ logit("%s: invalid type field", __func__); ++ return (0); ++ } ++} ++#endif /* HAVE_LINUX_AUDIT */ ++ + /** + ** Low-level libutil login() functions + **/ +diff -Naurp openssh-5.3p1/loginrec.h openssh-5.3p1.oden/loginrec.h +--- openssh-5.3p1/loginrec.h 2006-08-05 04:39:40.000000000 +0200 ++++ openssh-5.3p1.oden/loginrec.h 2009-10-07 18:46:05.000000000 +0200 +@@ -127,5 +127,9 @@ char *line_stripname(char *dst, const ch + char *line_abbrevname(char *dst, const char *src, int dstsize); + + void record_failed_login(const char *, const char *, const char *); ++#ifdef HAVE_LINUX_AUDIT ++int linux_audit_record_event(int uid, const char *username, ++ const char *hostname, const char *ip, const char *ttyn, int success); ++#endif /* HAVE_LINUX_AUDIT */ + + #endif /* _HAVE_LOGINREC_H_ */ diff --git a/openssh-4.9p1.sftplogging-v1.5.diff b/openssh-4.9p1.sftplogging-v1.5.diff new file mode 100644 index 0000000..1085d65 --- /dev/null +++ b/openssh-4.9p1.sftplogging-v1.5.diff @@ -0,0 +1,711 @@ +diff -Naurp openssh-4.9p1/servconf.c openssh-4.9p1.oden/servconf.c +--- openssh-4.9p1/servconf.c 2008-02-10 12:48:55.000000000 +0100 ++++ openssh-4.9p1.oden/servconf.c 2008-04-01 13:21:17.000000000 +0200 +@@ -118,6 +118,15 @@ initialize_server_options(ServerOptions + options->client_alive_count_max = -1; + options->authorized_keys_file = NULL; + options->authorized_keys_file2 = NULL; ++ options->log_sftp = LOG_SFTP_NOT_SET; ++ options->sftp_log_facility = SYSLOG_FACILITY_NOT_SET; ++ options->sftp_log_level = SYSLOG_LEVEL_NOT_SET; ++ ++ memset(options->sftp_umask, 0, SFTP_UMASK_LENGTH); ++ ++ options->sftp_permit_chmod = SFTP_PERMIT_NOT_SET; ++ options->sftp_permit_chown = SFTP_PERMIT_NOT_SET; ++ + options->num_accept_env = 0; + options->permit_tun = -1; + options->num_permitted_opens = -1; +@@ -251,6 +260,24 @@ fill_default_server_options(ServerOption + if (options->permit_tun == -1) + options->permit_tun = SSH_TUNMODE_NO; + ++ /* Turn sftp-server logging off by default */ ++ if (options->log_sftp == LOG_SFTP_NOT_SET) ++ options->log_sftp = LOG_SFTP_NO; ++ if (options->sftp_log_facility == SYSLOG_FACILITY_NOT_SET) ++ options->sftp_log_facility = SYSLOG_FACILITY_AUTH; ++ if (options->sftp_log_level == SYSLOG_LEVEL_NOT_SET) ++ options->sftp_log_level = SYSLOG_LEVEL_INFO; ++ ++ /* Don't set sftp-server umask */ ++ if (!options->sftp_umask) ++ memset(options->sftp_umask, 0, SFTP_UMASK_LENGTH); ++ ++ /* allow sftp client to issue chmod, chown / chgrp commands */ ++ if (options->sftp_permit_chmod == SFTP_PERMIT_NOT_SET) ++ options->sftp_permit_chmod = SFTP_PERMIT_YES; ++ if (options->sftp_permit_chown == SFTP_PERMIT_NOT_SET) ++ options->sftp_permit_chown = SFTP_PERMIT_YES; ++ + /* Turn privilege separation on by default */ + if (use_privsep == -1) + use_privsep = 1; +@@ -294,6 +321,9 @@ typedef enum { + sGssAuthentication, sGssCleanupCreds, sAcceptEnv, sPermitTunnel, + sMatch, sPermitOpen, sForceCommand, sChrootDirectory, + sUsePrivilegeSeparation, ++ sLogSftp, sSftpLogFacility, sSftpLogLevel, ++ sSftpUmask, ++ sSftpPermitChown, sSftpPermitChmod, + sDeprecated, sUnsupported + } ServerOpCodes; + +@@ -400,6 +430,12 @@ static struct { + { "authorizedkeysfile2", sAuthorizedKeysFile2, SSHCFG_GLOBAL }, + { "useprivilegeseparation", sUsePrivilegeSeparation, SSHCFG_GLOBAL }, + { "acceptenv", sAcceptEnv, SSHCFG_GLOBAL }, ++ { "logsftp", sLogSftp}, ++ { "sftplogfacility", sSftpLogFacility}, ++ { "sftploglevel", sSftpLogLevel}, ++ { "sftpumask", sSftpUmask}, ++ { "sftppermitchmod", sSftpPermitChmod}, ++ { "sftppermitchown", sSftpPermitChown}, + { "permittunnel", sPermitTunnel, SSHCFG_GLOBAL }, + { "match", sMatch, SSHCFG_ALL }, + { "permitopen", sPermitOpen, SSHCFG_ALL }, +@@ -626,6 +662,8 @@ process_server_config_line(ServerOptions + SyslogFacility *log_facility_ptr; + LogLevel *log_level_ptr; + ServerOpCodes opcode; ++ unsigned int umaskvalue = 0; ++ char *umaskptr; + u_short port; + u_int i, flags = 0; + size_t len; +@@ -1150,6 +1188,57 @@ parse_flag: + charptr = &options->banner; + goto parse_filename; + ++ case sLogSftp: ++ intptr = &options->log_sftp; ++ goto parse_flag; ++ ++ case sSftpLogFacility: ++ intptr = (int *) &options->sftp_log_facility; ++ arg = strdelim(&cp); ++ value = log_facility_number(arg); ++ if (value == SYSLOG_FACILITY_NOT_SET) ++ fatal("%.200s line %d: unsupported log facility '%s'", ++ filename, linenum, arg ? arg : ""); ++ if (*intptr == -1) ++ *intptr = (SyslogFacility) value; ++ break; ++ ++ case sSftpLogLevel: ++ intptr = (int *) &options->sftp_log_level; ++ arg = strdelim(&cp); ++ value = log_level_number(arg); ++ if (value == SYSLOG_LEVEL_NOT_SET) ++ fatal("%.200s line %d: unsupported log level '%s'", ++ filename, linenum, arg ? arg : ""); ++ if (*intptr == -1) ++ *intptr = (LogLevel) value; ++ break; ++ ++ case sSftpUmask: ++ arg = strdelim(&cp); ++ umaskptr = arg; ++ while (*arg && *arg >= '0' && *arg <= '9') ++ umaskvalue = umaskvalue * 8 + *arg++ - '0'; ++ if (*arg || umaskvalue > 0777) ++ fatal("%s line %d: bad value for umask", ++ filename, linenum); ++ else { ++ while (*umaskptr && *umaskptr == '0') ++ *umaskptr++; ++ strncpy(options->sftp_umask, umaskptr, ++ SFTP_UMASK_LENGTH); ++ } ++ ++ break; ++ ++ case sSftpPermitChmod: ++ intptr = &options->sftp_permit_chmod; ++ goto parse_flag; ++ ++ case sSftpPermitChown: ++ intptr = &options->sftp_permit_chown; ++ goto parse_flag; ++ + /* + * These options can contain %X options expanded at + * connect time, so that you can specify paths like: +diff -Naurp openssh-4.9p1/servconf.h openssh-4.9p1.oden/servconf.h +--- openssh-4.9p1/servconf.h 2008-03-07 08:31:24.000000000 +0100 ++++ openssh-4.9p1.oden/servconf.h 2008-04-01 13:18:51.000000000 +0200 +@@ -34,6 +34,18 @@ + #define PERMIT_NO_PASSWD 2 + #define PERMIT_YES 3 + ++/* sftp-server logging */ ++#define LOG_SFTP_NOT_SET -1 ++#define LOG_SFTP_NO 0 ++#define LOG_SFTP_YES 1 ++ ++/* sftp-server umask control */ ++#define SFTP_UMASK_LENGTH 5 ++ ++/* sftp-server client priviledge */ ++#define SFTP_PERMIT_NOT_SET -1 ++#define SFTP_PERMIT_NO 0 ++#define SFTP_PERMIT_YES 1 + #define DEFAULT_AUTH_FAIL_MAX 6 /* Default for MaxAuthTries */ + + /* Magic name for internal sftp-server */ +@@ -137,6 +149,12 @@ typedef struct { + char *authorized_keys_file; /* File containing public keys */ + char *authorized_keys_file2; + ++ int log_sftp; /* perform sftp-server logging */ ++ SyslogFacility sftp_log_facility; /* Facility for sftp subsystem logging. */ ++ LogLevel sftp_log_level; /* Level for sftp subsystem logging. */ ++ char sftp_umask[SFTP_UMASK_LENGTH]; /* Sftp Umask */ ++ int sftp_permit_chmod; ++ int sftp_permit_chown; + char *adm_forced_command; + + int use_pam; /* Enable auth via PAM */ +diff -Naurp openssh-4.9p1/session.c openssh-4.9p1.oden/session.c +--- openssh-4.9p1/session.c 2008-03-27 01:03:05.000000000 +0100 ++++ openssh-4.9p1.oden/session.c 2008-04-01 13:18:51.000000000 +0200 +@@ -144,6 +144,15 @@ login_cap_t *lc; + + static int is_child = 0; + ++/* so SFTP_LOG_FACILITY and SFTP_LOG_LEVEL can be passed through the ++ environment to the sftp-server subsystem. */ ++static const char *sysfac_to_int[] = { "0", "1", "2", "3", "4", "5", "6", ++ "7", "8", "9", "10", "11", "-1" }; ++static const char *syslevel_to_int[] = { "0", "1", "2", "3", "4", "5", "6", ++ "7", "-1" }; ++ ++static char *sftpumask; ++ + /* Name and directory of socket for authentication agent forwarding. */ + static char *auth_sock_name = NULL; + static char *auth_sock_dir = NULL; +@@ -1172,6 +1181,67 @@ do_setup_env(Session *s, const char *she + child_set_env(&env, &envsize, SSH_AUTHSOCKET_ENV_NAME, + auth_sock_name); + ++ /* LOG_SFTP */ ++ if (options.log_sftp == -1 ) ++ child_set_env(&env, &envsize, "LOG_SFTP", "-1"); ++ else if (options.log_sftp == 0) ++ child_set_env(&env, &envsize, "LOG_SFTP", "0"); ++ else ++ child_set_env(&env, &envsize, "LOG_SFTP", "1"); ++ ++ /* SFTP_LOG_FACILITY */ ++ if (options.sftp_log_facility < 0) ++ child_set_env(&env, &envsize, "SFTP_LOG_FACILITY", ++ "-1"); ++ else ++ child_set_env(&env, &envsize, "SFTP_LOG_FACILITY", ++ sysfac_to_int[options.sftp_log_facility]); ++ ++ /* SFTP_LOG_LEVEL */ ++ if (options.sftp_log_level < 0) ++ child_set_env(&env, &envsize, "SFTP_LOG_LEVEL", ++ "-1"); ++ else ++ child_set_env(&env, &envsize, "SFTP_LOG_LEVEL", ++ syslevel_to_int[options.sftp_log_level]); ++ ++ /* SFTP_UMASK */ ++ ++ if (options.sftp_umask[0] == '\0') ++ child_set_env(&env, &envsize, "SFTP_UMASK", ++ "" ); ++ else { ++ if (!(sftpumask = calloc(SFTP_UMASK_LENGTH,1))) { ++ ++logit("session.c: unabled to allocate memory for SftpUmask. SftpUmask control \ ++will be turned off."); ++ ++ child_set_env(&env, &envsize, "SFTP_UMASK", ++ "" ); ++ } else { ++ strncpy(sftpumask, options.sftp_umask, ++ SFTP_UMASK_LENGTH); ++ child_set_env(&env, &envsize, "SFTP_UMASK", ++ sftpumask ); ++ } ++ } ++ ++ /* SFTP_PERMIT_CHMOD */ ++ if (options.sftp_permit_chmod == -1 ) ++ child_set_env(&env, &envsize, "SFTP_PERMIT_CHMOD", "-1"); ++ else if (options.sftp_permit_chmod == 0) ++ child_set_env(&env, &envsize, "SFTP_PERMIT_CHMOD", "0"); ++ else ++ child_set_env(&env, &envsize, "SFTP_PERMIT_CHMOD", "1"); ++ ++ /* SFTP_PERMIT_CHOWN */ ++ if (options.sftp_permit_chown == -1 ) ++ child_set_env(&env, &envsize, "SFTP_PERMIT_CHOWN", "-1"); ++ else if (options.sftp_permit_chown == 0) ++ child_set_env(&env, &envsize, "SFTP_PERMIT_CHOWN", "0"); ++ else ++ child_set_env(&env, &envsize, "SFTP_PERMIT_CHOWN", "1"); ++ + /* read $HOME/.ssh/environment. */ + if (options.permit_user_env && !options.use_login) { + snprintf(buf, sizeof buf, "%.200s/.ssh/environment", +diff -Naurp openssh-4.9p1/sftp-server.8 openssh-4.9p1.oden/sftp-server.8 +--- openssh-4.9p1/sftp-server.8 2007-06-05 10:27:13.000000000 +0200 ++++ openssh-4.9p1.oden/sftp-server.8 2008-04-01 13:18:51.000000000 +0200 +@@ -50,6 +50,20 @@ should be specified in the + declaration. + See + .Xr sshd_config 5 ++for more information. Sftp-server transactions may be logged ++using the ++.Cm LogSftp , ++.Cm SftpLogFacility , ++and ++.Cm SftpLogLevel ++options. The administrator may exert control over the file and directory ++permission and ownership, with ++.Cm SftpUmask , ++.Cm SftpPermitChmod , ++and ++.Cm SftpPermitChown ++. See ++.Xr sshd_config 5 + for more information. + .Pp + Valid options are: +@@ -76,7 +90,8 @@ The default is ERROR. + .Xr sftp 1 , + .Xr ssh 1 , + .Xr sshd_config 5 , +-.Xr sshd 8 ++.Xr sshd 8, ++.Xr sshd_config 5 + .Rs + .%A T. Ylonen + .%A S. Lehtinen +diff -Naurp openssh-4.9p1/sftp-server.c openssh-4.9p1.oden/sftp-server.c +--- openssh-4.9p1/sftp-server.c 2008-03-07 08:33:53.000000000 +0100 ++++ openssh-4.9p1.oden/sftp-server.c 2008-04-01 13:27:43.000000000 +0200 +@@ -50,6 +50,13 @@ + #define get_int() buffer_get_int(&iqueue); + #define get_string(lenp) buffer_get_string(&iqueue, lenp); + ++/* SFTP_UMASK */ ++static mode_t setumask = 0; ++ ++static int permit_chmod = 1; ++static int permit_chown = 1; ++static int permit_logging = 0; ++ + /* Our verbosity */ + LogLevel log_level = SYSLOG_LEVEL_ERROR; + +@@ -509,6 +516,14 @@ process_open(void) + a = get_attrib(); + flags = flags_from_portable(pflags); + mode = (a->flags & SSH2_FILEXFER_ATTR_PERMISSIONS) ? a->perm : 0666; ++ ++ if (setumask != 0) { ++ if ( permit_logging == 1 ) ++ logit("setting file creation mode to 0666 and umask to %o", setumask); ++ mode = 0666; ++ umask(setumask); ++ } ++ + logit("open \"%s\" flags %s mode 0%o", + name, string_from_portable(pflags), mode); + fd = open(name, flags, mode); +@@ -523,6 +538,8 @@ process_open(void) + status = SSH2_FX_OK; + } + } ++ if ( permit_logging == 1 ) ++ logit("open %s", name); + if (status != SSH2_FX_OK) + send_status(id, status); + xfree(name); +@@ -560,7 +577,8 @@ process_read(void) + id, handle_to_name(handle), handle, (unsigned long long)off, len); + if (len > sizeof buf) { + len = sizeof buf; +- debug2("read change len %d", len); ++ if (permit_logging == 1) ++ logit("read change len %d", len); + } + fd = handle_to_fd(handle); + if (fd >= 0) { +@@ -580,6 +598,8 @@ process_read(void) + } + } + } ++ if ( permit_logging == 1 ) ++ logit("reading %d bytes from file", ret); + if (status != SSH2_FX_OK) + send_status(id, status); + } +@@ -615,10 +635,13 @@ process_write(void) + status = SSH2_FX_OK; + handle_update_write(handle, ret); + } else { +- debug2("nothing at all written"); ++ if ( permit_logging == 1 ) ++ logit("nothing at all written"); + } + } + } ++ if ( permit_logging == 1 ) ++ logit("writing %d bytes to file", ret); + send_status(id, status); + xfree(data); + } +@@ -720,15 +743,25 @@ process_setstat(void) + status = errno_to_portable(errno); + } + if (a->flags & SSH2_FILEXFER_ATTR_PERMISSIONS) { +- logit("set \"%s\" mode %04o", name, a->perm); +- ret = chmod(name, a->perm & 0777); +- if (ret == -1) +- status = errno_to_portable(errno); ++ if (permit_chmod == 1) { ++ ret = chmod(name, a->perm & 0777); ++ if (ret == -1) ++ status = errno_to_portable(errno); ++ else ++ if ( permit_logging == 1 ) ++ logit("chmod'ed %s", name); ++ } else { ++ status = SSH2_FX_PERMISSION_DENIED; ++ if ( permit_logging == 1 ) ++ logit("chmod %s: operation prohibited by sftp-server configuration.", name); ++ } + } + if (a->flags & SSH2_FILEXFER_ATTR_ACMODTIME) { + char buf[64]; + time_t t = a->mtime; + ++if ( permit_logging == 1 ) ++logit("process_setstat: utimes"); + strftime(buf, sizeof(buf), "%Y%m%d-%H:%M:%S", + localtime(&t)); + logit("set \"%s\" modtime %s", name, buf); +@@ -737,11 +770,18 @@ process_setstat(void) + status = errno_to_portable(errno); + } + if (a->flags & SSH2_FILEXFER_ATTR_UIDGID) { +- logit("set \"%s\" owner %lu group %lu", name, +- (u_long)a->uid, (u_long)a->gid); +- ret = chown(name, a->uid, a->gid); +- if (ret == -1) +- status = errno_to_portable(errno); ++ if (permit_chown == 1) { ++ ret = chown(name, a->uid, a->gid); ++ if (ret == -1) ++ status = errno_to_portable(errno); ++ else ++ if ( permit_logging == 1 ) ++ logit("chown'ed %s.", name); ++ } else { ++ status = SSH2_FX_PERMISSION_DENIED; ++ if ( permit_logging == 1 ) ++ logit("chown %s: operation prohibited by sftp-server configuration.", name); ++ } + } + send_status(id, status); + xfree(name); +@@ -755,8 +795,13 @@ process_fsetstat(void) + int handle, fd, ret; + int status = SSH2_FX_OK; + ++if ( permit_logging == 1 ) ++logit("process_fsetstat"); ++ + id = get_int(); + handle = get_handle(); ++if ( permit_logging == 1 ) ++logit("process_fsetstat: ftruncate"); + a = get_attrib(); + debug("request %u: fsetstat handle %d", id, handle); + fd = handle_to_fd(handle); +@@ -766,6 +811,8 @@ process_fsetstat(void) + char *name = handle_to_name(handle); + + if (a->flags & SSH2_FILEXFER_ATTR_SIZE) { ++ if ( permit_logging == 1 ) ++ logit("process_setstat: truncate"); + logit("set \"%s\" size %llu", + name, (unsigned long long)a->size); + ret = ftruncate(fd, a->size); +@@ -773,7 +820,9 @@ process_fsetstat(void) + status = errno_to_portable(errno); + } + if (a->flags & SSH2_FILEXFER_ATTR_PERMISSIONS) { ++if ( permit_logging == 1 ) + logit("set \"%s\" mode %04o", name, a->perm); ++ if (permit_chmod == 1) { + #ifdef HAVE_FCHMOD + ret = fchmod(fd, a->perm & 0777); + #else +@@ -781,11 +830,21 @@ process_fsetstat(void) + #endif + if (ret == -1) + status = errno_to_portable(errno); ++ else ++ if ( permit_logging == 1 ) ++ logit("chmod: succeeded."); ++ } else { // permit_chmod ++ status = SSH2_FX_PERMISSION_DENIED; ++ if ( permit_logging == 1 ) ++ logit("chmod: operation prohibited by sftp-server configuration."); ++ } // permit_chmod + } + if (a->flags & SSH2_FILEXFER_ATTR_ACMODTIME) { + char buf[64]; + time_t t = a->mtime; + ++if ( permit_logging == 1 ) ++logit("process_fsetstat: utimes"); + strftime(buf, sizeof(buf), "%Y%m%d-%H:%M:%S", + localtime(&t)); + logit("set \"%s\" modtime %s", name, buf); +@@ -800,6 +859,7 @@ process_fsetstat(void) + if (a->flags & SSH2_FILEXFER_ATTR_UIDGID) { + logit("set \"%s\" owner %lu group %lu", name, + (u_long)a->uid, (u_long)a->gid); ++ if (permit_chown == 1) { + #ifdef HAVE_FCHOWN + ret = fchown(fd, a->uid, a->gid); + #else +@@ -807,6 +867,14 @@ process_fsetstat(void) + #endif + if (ret == -1) + status = errno_to_portable(errno); ++ else ++ if ( permit_logging == 1 ) ++ logit("chown: succeeded"); ++ } else { // permit_chown ++ status = SSH2_FX_PERMISSION_DENIED; ++ if ( permit_logging == 1 ) ++ logit("chown: operation prohibited by sftp-server configuration."); ++ } // permit_chown + } + } + send_status(id, status); +@@ -929,6 +997,14 @@ process_mkdir(void) + a = get_attrib(); + mode = (a->flags & SSH2_FILEXFER_ATTR_PERMISSIONS) ? + a->perm & 0777 : 0777; ++ ++ if (setumask != 0) { ++ if ( permit_logging == 1 ) ++ logit("setting directory creation mode to 0777 and umask to %o.", setumask); ++ mode = 0777; ++ umask(setumask); ++ } ++ + debug3("request %u: mkdir", id); + logit("mkdir name \"%s\" mode 0%o", name, mode); + ret = mkdir(name, mode); +@@ -977,6 +1053,8 @@ process_realpath(void) + s.name = s.long_name = resolvedname; + send_names(id, 1, &s); + } ++ if ( permit_logging == 1 ) ++ logit("realpath %s", path); + xfree(path); + } + +@@ -1059,6 +1137,8 @@ process_readlink(void) + s.name = s.long_name = buf; + send_names(id, 1, &s); + } ++ if ( permit_logging == 1 ) ++ logit("readlink %s", path); + xfree(path); + } + +@@ -1246,6 +1326,8 @@ sftp_server_main(int argc, char **argv, + { + fd_set *rset, *wset; + int in, out, max, ch, skipargs = 0, log_stderr = 0; ++ unsigned int val = 0; ++ char *umask_env; + ssize_t len, olen, set_size; + SyslogFacility log_facility = SYSLOG_FACILITY_AUTH; + char *cp, buf[4*4096]; +@@ -1254,7 +1336,16 @@ sftp_server_main(int argc, char **argv, + extern char *__progname; + + __progname = ssh_get_progname(argv[0]); +- log_init(__progname, log_level, log_facility, log_stderr); ++ /* sftplogging */ ++ ++ if ( (getenv("LOG_SFTP") != NULL) && (atoi(getenv("LOG_SFTP")) == 1) ) ++ { ++ permit_logging = 1; ++ log_init("sftp-server", (getenv("SFTP_LOG_LEVEL") != NULL) ? atoi(getenv("SFTP_LOG_LEVEL")) : SYSLOG_LEVEL_DEBUG1, ++ (getenv("SFTP_LOG_FACILITY") != NULL) ? atoi(getenv("SFTP_LOG_FACILITY")) : SYSLOG_FACILITY_AUTH, 0); ++ }; ++ ++ + + while (!skipargs && (ch = getopt(argc, argv, "C:f:l:che")) != -1) { + switch (ch) { +@@ -1284,7 +1375,6 @@ sftp_server_main(int argc, char **argv, + } + } + +- log_init(__progname, log_level, log_facility, log_stderr); + + if ((cp = getenv("SSH_CONNECTION")) != NULL) { + client_addr = xstrdup(cp); +@@ -1302,6 +1392,41 @@ sftp_server_main(int argc, char **argv, + logit("session opened for local user %s from [%s]", + pw->pw_name, client_addr); + ++ if ( permit_logging == 1 ) ++ logit("Starting sftp-server logging for user %s.", getenv("USER")); ++ ++ /* Umask control */ ++ ++ if ( (umask_env = getenv("SFTP_UMASK")) != NULL ) ++ { ++ while (*umask_env && *umask_env >= '0' && *umask_env <= '9') ++ val = val * 8 + *umask_env++ - '0'; ++ ++ if (*umask_env || val > 0777 || val == 0) { ++ if ( permit_logging == 1 ) ++ logit("bad value %o for SFTP_UMASK, turning umask control off.", val); ++ setumask = 0; ++ } else { ++ if ( permit_logging == 1 ) ++ logit("umask control is on."); ++ setumask = val; ++ }; ++ } else setumask = 0; ++ ++ ++ /* Sensitive client commands */ ++ ++ if ( (getenv("SFTP_PERMIT_CHMOD") != NULL) && (atoi(getenv("SFTP_PERMIT_CHMOD")) != 1) ) { ++ permit_chmod = 0; ++ if ( permit_logging == 1 ) ++ logit("client is not permitted to chmod."); ++ }; ++ if ( (getenv("SFTP_PERMIT_CHOWN") != NULL) && (atoi(getenv("SFTP_PERMIT_CHOWN")) != 1) ) { ++ permit_chown = 0; ++ if ( permit_logging == 1 ) ++ logit("client is not permitted to chown."); ++ }; ++ + in = dup(STDIN_FILENO); + out = dup(STDOUT_FILENO); + +@@ -1352,6 +1477,8 @@ sftp_server_main(int argc, char **argv, + len = read(in, buf, sizeof buf); + if (len == 0) { + debug("read eof"); ++ if ( permit_logging == 1 ) ++ logit("sftp-server finished."); + sftp_server_cleanup_exit(0); + } else if (len < 0) { + error("read: %s", strerror(errno)); +diff -Naurp openssh-4.9p1/sshd.c openssh-4.9p1.oden/sshd.c +--- openssh-4.9p1/sshd.c 2008-03-11 12:58:25.000000000 +0100 ++++ openssh-4.9p1.oden/sshd.c 2008-04-01 13:18:51.000000000 +0200 +@@ -421,7 +421,7 @@ sshd_exchange_identification(int sock_in + major = PROTOCOL_MAJOR_1; + minor = PROTOCOL_MINOR_1; + } +- snprintf(buf, sizeof buf, "SSH-%d.%d-%.100s\n", major, minor, SSH_VERSION); ++ snprintf(buf, sizeof buf, "SSH-%d.%d-%.100s\n", major, minor, SSH_RELEASE); + server_version_string = xstrdup(buf); + + /* Send our protocol version identification. */ +diff -Naurp openssh-4.9p1/sshd_config openssh-4.9p1.oden/sshd_config +--- openssh-4.9p1/sshd_config 2008-02-10 12:40:12.000000000 +0100 ++++ openssh-4.9p1.oden/sshd_config 2008-04-01 13:18:51.000000000 +0200 +@@ -110,6 +110,17 @@ Protocol 2 + # override default of no subsystems + Subsystem sftp /usr/libexec/sftp-server + ++# sftp-server logging ++#LogSftp no ++#SftpLogFacility AUTH ++#SftpLogLevel INFO ++ ++# sftp-server umask control ++#SftpUmask ++ ++#SftpPermitChmod yes ++#SftpPermitChown yes ++ + # Example of overriding settings on a per-user basis + #Match User anoncvs + # X11Forwarding no +diff -Naurp openssh-4.9p1/sshd_config.5 openssh-4.9p1.oden/sshd_config.5 +--- openssh-4.9p1/sshd_config.5 2008-03-27 01:02:02.000000000 +0100 ++++ openssh-4.9p1.oden/sshd_config.5 2008-04-01 13:18:51.000000000 +0200 +@@ -530,6 +530,10 @@ The default is INFO. + DEBUG and DEBUG1 are equivalent. + DEBUG2 and DEBUG3 each specify higher levels of debugging output. + Logging with a DEBUG level violates the privacy of users and is not recommended. ++.It Cm LogSftp ++Specifies whether to perform logging of ++.Nm sftp-server ++subsystem transactions. Must be "yes" or "no." The default value is "no." + .It Cm MACs + Specifies the available MAC (message authentication code) algorithms. + The MAC algorithm is used in protocol version 2 +@@ -773,6 +777,37 @@ This option applies to protocol version + .It Cm ServerKeyBits + Defines the number of bits in the ephemeral protocol version 1 server key. + The minimum value is 512, and the default is 768. ++.It Cm SftpLogFacility ++Gives the facility code that is used when logging ++.Nm sftp-server . ++transactions. The possible values are: DAEMON, USER, AUTH, LOCAL0, ++LOCAL1, LOCAL2, LOCAL3, LOCAL4, LOCAL5, LOCAL6, LOCAL7. ++The default is AUTH. ++.It Cm SftpLogLevel ++Gives the verbosity level that is used when logging messages from ++.Nm sftp-server . ++The possible values are: ++QUIET, FATAL, ERROR, INFO, VERBOSE, DEBUG, DEBUG1, DEBUG2 and DEBUG3. ++The default is INFO. DEBUG and DEBUG1 are equivalent. DEBUG2 ++and DEBUG3 each specify higher levels of debugging output. ++Logging with a DEBUG level violates the privacy of users ++and is not recommended. ++.It Cm SftpPermitChmod ++Specifies whether the sftp-server allows the sftp client to execute chmod ++commands on the server. The default is yes. ++.It Cm SftpPermitChown ++Specifies whether the sftp-server allows the sftp client to execute chown ++or chgrp commands on the server. Turning this value on means that the client ++is allowed to execute both chown and chgrp commands. Turning it off means that ++the client is prohibited from executing either chown or chgrp. ++ The default is yes. ++.It Cm SftpUmask ++Specifies an optional umask for ++.Nm sftp-server ++subsystem transactions. If a umask is given, this umask will override all system, ++environment or sftp client permission modes. If ++no umask or an invalid umask is given, file creation mode defaults to the permission ++mode specified by the sftp client. The default is for no umask. + .It Cm StrictModes + Specifies whether + .Xr sshd 8 +diff -Naurp openssh-4.9p1/version.h openssh-4.9p1.oden/version.h +--- openssh-4.9p1/version.h 2008-03-27 01:18:13.000000000 +0100 ++++ openssh-4.9p1.oden/version.h 2008-04-01 13:18:51.000000000 +0200 +@@ -2,5 +2,5 @@ + + #define SSH_VERSION "OpenSSH_4.9" + +-#define SSH_PORTABLE "p1" ++#define SSH_PORTABLE "p1+sftplogging-v1.5" + #define SSH_RELEASE SSH_VERSION SSH_PORTABLE diff --git a/openssh-5.1p1-askpass-progress.patch b/openssh-5.1p1-askpass-progress.patch new file mode 100644 index 0000000..ec93b87 --- /dev/null +++ b/openssh-5.1p1-askpass-progress.patch @@ -0,0 +1,79 @@ +diff -up openssh-5.1p1/contrib/gnome-ssh-askpass2.c.progress openssh-5.1p1/contrib/gnome-ssh-askpass2.c +--- openssh-5.1p1/contrib/gnome-ssh-askpass2.c.progress 2008-07-23 19:05:26.000000000 +0200 ++++ openssh-5.1p1/contrib/gnome-ssh-askpass2.c 2008-07-23 19:05:26.000000000 +0200 +@@ -53,6 +53,7 @@ + #include + #include + #include ++#include + #include + #include + +@@ -83,13 +84,24 @@ ok_dialog(GtkWidget *entry, gpointer dia + gtk_dialog_response(GTK_DIALOG(dialog), GTK_RESPONSE_OK); + } + ++static void ++move_progress(GtkWidget *entry, gpointer progress) ++{ ++ gdouble step; ++ g_return_if_fail(GTK_IS_PROGRESS_BAR(progress)); ++ ++ step = g_random_double_range(0.03, 0.1); ++ gtk_progress_bar_set_pulse_step(GTK_PROGRESS_BAR(progress), step); ++ gtk_progress_bar_pulse(GTK_PROGRESS_BAR(progress)); ++} ++ + static int + passphrase_dialog(char *message) + { + const char *failed; + char *passphrase, *local; + int result, grab_tries, grab_server, grab_pointer; +- GtkWidget *dialog, *entry; ++ GtkWidget *dialog, *entry, *progress, *hbox; + GdkGrabStatus status; + + grab_server = (getenv("GNOME_SSH_ASKPASS_GRAB_SERVER") != NULL); +@@ -102,13 +114,31 @@ passphrase_dialog(char *message) + "%s", + message); + ++ hbox = gtk_hbox_new(FALSE, 0); ++ gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialog)->vbox), hbox, FALSE, ++ FALSE, 0); ++ gtk_widget_show(hbox); ++ + entry = gtk_entry_new(); +- gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialog)->vbox), entry, FALSE, ++ gtk_box_pack_start(GTK_BOX(hbox), entry, TRUE, + FALSE, 0); ++ gtk_entry_set_width_chars(GTK_ENTRY(entry), 2); + gtk_entry_set_visibility(GTK_ENTRY(entry), FALSE); + gtk_widget_grab_focus(entry); + gtk_widget_show(entry); + ++ hbox = gtk_hbox_new(FALSE, 0); ++ gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialog)->vbox), hbox, FALSE, ++ FALSE, 8); ++ gtk_widget_show(hbox); ++ ++ progress = gtk_progress_bar_new(); ++ ++ gtk_progress_bar_set_text(GTK_PROGRESS_BAR(progress), "Passphrase length hidden intentionally"); ++ gtk_box_pack_start(GTK_BOX(hbox), progress, TRUE, ++ TRUE, 5); ++ gtk_widget_show(progress); ++ + gtk_window_set_title(GTK_WINDOW(dialog), "OpenSSH"); + gtk_window_set_position (GTK_WINDOW(dialog), GTK_WIN_POS_CENTER); + gtk_window_set_keep_above(GTK_WINDOW(dialog), TRUE); +@@ -119,6 +149,8 @@ passphrase_dialog(char *message) + gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_OK); + g_signal_connect(G_OBJECT(entry), "activate", + G_CALLBACK(ok_dialog), dialog); ++ g_signal_connect(G_OBJECT(entry), "changed", ++ G_CALLBACK(move_progress), progress); + + gtk_window_set_keep_above(GTK_WINDOW(dialog), TRUE); + diff --git a/openssh-5.2p1-hpn13v6.diff b/openssh-5.2p1-hpn13v6.diff new file mode 100644 index 0000000..a8f179e --- /dev/null +++ b/openssh-5.2p1-hpn13v6.diff @@ -0,0 +1,3693 @@ +diff -NupwB openssh-5.2p1-canonical/auth2.c openssh-5.2p1-hpn13v6/auth2.c +--- openssh-5.2p1-canonical/auth2.c 2008-11-05 00:20:46.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/auth2.c 2009-05-14 12:36:10.000000000 -0400 +@@ -49,6 +49,7 @@ + #include "dispatch.h" + #include "pathnames.h" + #include "buffer.h" ++#include "canohost.h" + + #ifdef GSSAPI + #include "ssh-gss.h" +@@ -75,6 +76,9 @@ extern Authmethod method_gssapi; + extern Authmethod method_jpake; + #endif + ++static int log_flag = 0; ++ ++ + Authmethod *authmethods[] = { + &method_none, + &method_pubkey, +@@ -225,6 +229,11 @@ input_userauth_request(int type, u_int32 + service = packet_get_string(NULL); + method = packet_get_string(NULL); + debug("userauth-request for user %s service %s method %s", user, service, method); ++ if (!log_flag) { ++ logit("SSH: Server;Ltype: Authname;Remote: %s-%d;Name: %s", ++ get_remote_ipaddr(), get_remote_port(), user); ++ log_flag = 1; ++ } + debug("attempt %d failures %d", authctxt->attempt, authctxt->failures); + + if ((style = strchr(user, ':')) != NULL) +diff -NupwB openssh-5.2p1-canonical/buffer.c openssh-5.2p1-hpn13v6/buffer.c +--- openssh-5.2p1-canonical/buffer.c 2006-08-04 22:39:39.000000000 -0400 ++++ openssh-5.2p1-hpn13v6/buffer.c 2009-05-14 12:36:10.000000000 -0400 +@@ -127,7 +127,7 @@ restart: + + /* Increase the size of the buffer and retry. */ + newlen = roundup(buffer->alloc + len, BUFFER_ALLOCSZ); +- if (newlen > BUFFER_MAX_LEN) ++ if (newlen > BUFFER_MAX_LEN_HPN) + fatal("buffer_append_space: alloc %u not supported", + newlen); + buffer->buf = xrealloc(buffer->buf, 1, newlen); +diff -NupwB openssh-5.2p1-canonical/buffer.h openssh-5.2p1-hpn13v6/buffer.h +--- openssh-5.2p1-canonical/buffer.h 2008-05-19 00:59:37.000000000 -0400 ++++ openssh-5.2p1-hpn13v6/buffer.h 2009-05-14 12:36:10.000000000 -0400 +@@ -16,6 +16,9 @@ + #ifndef BUFFER_H + #define BUFFER_H + ++/* move the following to a more appropriate place and name */ ++#define BUFFER_MAX_LEN_HPN 0x4000000 /* 64MB */ ++ + typedef struct { + u_char *buf; /* Buffer for data. */ + u_int alloc; /* Number of bytes allocated for data. */ +diff -NupwB openssh-5.2p1-canonical/channels.c openssh-5.2p1-hpn13v6/channels.c +--- openssh-5.2p1-canonical/channels.c 2009-02-14 00:28:21.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/channels.c 2009-05-14 12:36:10.000000000 -0400 +@@ -169,8 +169,14 @@ static void port_open_helper(Channel *c, + static int connect_next(struct channel_connect *); + static void channel_connect_ctx_free(struct channel_connect *); + ++ ++static int hpn_disabled = 0; ++static int hpn_buffer_size = 2 * 1024 * 1024; ++ + /* -- channel core */ + ++ ++ + Channel * + channel_by_id(int id) + { +@@ -308,6 +314,7 @@ channel_new(char *ctype, int type, int r + c->local_window_max = window; + c->local_consumed = 0; + c->local_maxpacket = maxpack; ++ c->dynamic_window = 0; + c->remote_id = -1; + c->remote_name = xstrdup(remote_name); + c->remote_window = 0; +@@ -798,11 +805,35 @@ channel_pre_open_13(Channel *c, fd_set * + FD_SET(c->sock, writeset); + } + ++int channel_tcpwinsz () { ++ u_int32_t tcpwinsz = 0; ++ socklen_t optsz = sizeof(tcpwinsz); ++ int ret = -1; ++ ++ /* if we aren't on a socket return 128KB*/ ++ if(!packet_connection_is_on_socket()) ++ return(128*1024); ++ ret = getsockopt(packet_get_connection_in(), ++ SOL_SOCKET, SO_RCVBUF, &tcpwinsz, &optsz); ++ /* return no more than 64MB */ ++ if ((ret == 0) && tcpwinsz > BUFFER_MAX_LEN_HPN) ++ tcpwinsz = BUFFER_MAX_LEN_HPN; ++ debug2("tcpwinsz: %d for connection: %d", tcpwinsz, ++ packet_get_connection_in()); ++ return(tcpwinsz); ++} ++ + static void + channel_pre_open(Channel *c, fd_set *readset, fd_set *writeset) + { + u_int limit = compat20 ? c->remote_window : packet_get_maxsize(); + ++ /* check buffer limits */ ++ if ((!c->tcpwinsz) || (c->dynamic_window > 0)) ++ c->tcpwinsz = channel_tcpwinsz(); ++ ++ limit = MIN(limit, 2 * c->tcpwinsz); ++ + if (c->istate == CHAN_INPUT_OPEN && + limit > 0 && + buffer_len(&c->input) < limit && +@@ -1759,14 +1790,21 @@ channel_check_window(Channel *c) + c->local_maxpacket*3) || + c->local_window < c->local_window_max/2) && + c->local_consumed > 0) { ++ u_int addition = 0; ++ /* adjust max window size if we are in a dynamic environment */ ++ if (c->dynamic_window && (c->tcpwinsz > c->local_window_max)) { ++ /* grow the window somewhat aggressively to maintain pressure */ ++ addition = 1.5*(c->tcpwinsz - c->local_window_max); ++ c->local_window_max += addition; ++ } + packet_start(SSH2_MSG_CHANNEL_WINDOW_ADJUST); + packet_put_int(c->remote_id); +- packet_put_int(c->local_consumed); ++ packet_put_int(c->local_consumed + addition); + packet_send(); + debug2("channel %d: window %d sent adjust %d", + c->self, c->local_window, + c->local_consumed); +- c->local_window += c->local_consumed; ++ c->local_window += c->local_consumed + addition; + c->local_consumed = 0; + } + return 1; +@@ -1969,11 +2007,12 @@ channel_after_select(fd_set *readset, fd + + + /* If there is data to send to the connection, enqueue some of it now. */ +-void ++int + channel_output_poll(void) + { + Channel *c; + u_int i, len; ++ int packet_length = 0; + + for (i = 0; i < channels_alloc; i++) { + c = channels[i]; +@@ -2013,7 +2052,7 @@ channel_output_poll(void) + packet_start(SSH2_MSG_CHANNEL_DATA); + packet_put_int(c->remote_id); + packet_put_string(data, dlen); +- packet_send(); ++ packet_length = packet_send(); + c->remote_window -= dlen + 4; + xfree(data); + } +@@ -2043,7 +2082,7 @@ channel_output_poll(void) + SSH2_MSG_CHANNEL_DATA : SSH_MSG_CHANNEL_DATA); + packet_put_int(c->remote_id); + packet_put_string(buffer_ptr(&c->input), len); +- packet_send(); ++ packet_length = packet_send(); + buffer_consume(&c->input, len); + c->remote_window -= len; + } +@@ -2078,12 +2117,13 @@ channel_output_poll(void) + packet_put_int(c->remote_id); + packet_put_int(SSH2_EXTENDED_DATA_STDERR); + packet_put_string(buffer_ptr(&c->extended), len); +- packet_send(); ++ packet_length = packet_send(); + buffer_consume(&c->extended, len); + c->remote_window -= len; + debug2("channel %d: sent ext data %d", c->self, len); + } + } ++ return (packet_length); + } + + +@@ -2459,6 +2499,15 @@ channel_set_af(int af) + IPv4or6 = af; + } + ++ ++void ++channel_set_hpn(int external_hpn_disabled, int external_hpn_buffer_size) ++{ ++ hpn_disabled = external_hpn_disabled; ++ hpn_buffer_size = external_hpn_buffer_size; ++ debug("HPN Disabled: %d, HPN Buffer Size: %d", hpn_disabled, hpn_buffer_size); ++} ++ + static int + channel_setup_fwd_listener(int type, const char *listen_addr, + u_short listen_port, int *allocated_listen_port, +@@ -2610,9 +2659,15 @@ channel_setup_fwd_listener(int type, con + } + + /* Allocate a channel number for the socket. */ ++ /* explicitly test for hpn disabled option. if true use smaller window size */ ++ if (hpn_disabled) + c = channel_new("port listener", type, sock, sock, -1, + CHAN_TCP_WINDOW_DEFAULT, CHAN_TCP_PACKET_DEFAULT, + 0, "port listener", 1); ++ else ++ c = channel_new("port listener", type, sock, sock, -1, ++ hpn_buffer_size, CHAN_TCP_PACKET_DEFAULT, ++ 0, "port listener", 1); + c->path = xstrdup(host); + c->host_port = port_to_connect; + c->listening_port = listen_port; +@@ -3151,10 +3206,17 @@ x11_create_display_inet(int x11_display_ + *chanids = xcalloc(num_socks + 1, sizeof(**chanids)); + for (n = 0; n < num_socks; n++) { + sock = socks[n]; ++ /* Is this really necassary? */ ++ if (hpn_disabled) + nc = channel_new("x11 listener", + SSH_CHANNEL_X11_LISTENER, sock, sock, -1, + CHAN_X11_WINDOW_DEFAULT, CHAN_X11_PACKET_DEFAULT, + 0, "X11 inet listener", 1); ++ else ++ nc = channel_new("x11 listener", ++ SSH_CHANNEL_X11_LISTENER, sock, sock, -1, ++ hpn_buffer_size, CHAN_X11_PACKET_DEFAULT, ++ 0, "X11 inet listener", 1); + nc->single_connection = single_connection; + (*chanids)[n] = nc->self; + } +diff -NupwB openssh-5.2p1-canonical/channels.h openssh-5.2p1-hpn13v6/channels.h +--- openssh-5.2p1-canonical/channels.h 2009-02-14 00:28:21.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/channels.h 2009-05-14 12:36:10.000000000 -0400 +@@ -115,8 +115,10 @@ struct Channel { + u_int local_window_max; + u_int local_consumed; + u_int local_maxpacket; ++ int dynamic_window; + int extended_usage; + int single_connection; ++ u_int tcpwinsz; + + char *ctype; /* type */ + +@@ -146,9 +148,11 @@ struct Channel { + + /* default window/packet sizes for tcp/x11-fwd-channel */ + #define CHAN_SES_PACKET_DEFAULT (32*1024) +-#define CHAN_SES_WINDOW_DEFAULT (64*CHAN_SES_PACKET_DEFAULT) ++#define CHAN_SES_WINDOW_DEFAULT (4*CHAN_SES_PACKET_DEFAULT) ++ + #define CHAN_TCP_PACKET_DEFAULT (32*1024) +-#define CHAN_TCP_WINDOW_DEFAULT (64*CHAN_TCP_PACKET_DEFAULT) ++#define CHAN_TCP_WINDOW_DEFAULT (4*CHAN_TCP_PACKET_DEFAULT) ++ + #define CHAN_X11_PACKET_DEFAULT (16*1024) + #define CHAN_X11_WINDOW_DEFAULT (4*CHAN_X11_PACKET_DEFAULT) + +@@ -221,7 +225,7 @@ void channel_input_status_confirm(int, + + void channel_prepare_select(fd_set **, fd_set **, int *, u_int*, int); + void channel_after_select(fd_set *, fd_set *); +-void channel_output_poll(void); ++int channel_output_poll(void); + + int channel_not_very_much_buffered_data(void); + void channel_close_all(void); +@@ -277,4 +281,7 @@ void chan_rcvd_ieof(Channel *); + void chan_write_failed(Channel *); + void chan_obuf_empty(Channel *); + ++/* hpn handler */ ++void channel_set_hpn(int, int); ++ + #endif +diff -NupwB openssh-5.2p1-canonical/cipher.c openssh-5.2p1-hpn13v6/cipher.c +--- openssh-5.2p1-canonical/cipher.c 2009-01-28 00:38:41.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/cipher.c 2009-05-14 12:36:10.000000000 -0400 +@@ -55,6 +55,7 @@ extern const EVP_CIPHER *evp_ssh1_bf(voi + extern const EVP_CIPHER *evp_ssh1_3des(void); + extern void ssh1_3des_iv(EVP_CIPHER_CTX *, int, u_char *, int); + extern const EVP_CIPHER *evp_aes_128_ctr(void); ++extern const EVP_CIPHER *evp_aes_ctr_mt(void); + extern void ssh_aes_ctr_iv(EVP_CIPHER_CTX *, int, u_char *, u_int); + + struct Cipher { +@@ -82,9 +83,9 @@ struct Cipher { + { "aes256-cbc", SSH_CIPHER_SSH2, 16, 32, 0, 1, EVP_aes_256_cbc }, + { "rijndael-cbc@lysator.liu.se", + SSH_CIPHER_SSH2, 16, 32, 0, 1, EVP_aes_256_cbc }, +- { "aes128-ctr", SSH_CIPHER_SSH2, 16, 16, 0, 0, evp_aes_128_ctr }, +- { "aes192-ctr", SSH_CIPHER_SSH2, 16, 24, 0, 0, evp_aes_128_ctr }, +- { "aes256-ctr", SSH_CIPHER_SSH2, 16, 32, 0, 0, evp_aes_128_ctr }, ++ { "aes128-ctr", SSH_CIPHER_SSH2, 16, 16, 0, 0, evp_aes_ctr_mt }, ++ { "aes192-ctr", SSH_CIPHER_SSH2, 16, 24, 0, 0, evp_aes_ctr_mt }, ++ { "aes256-ctr", SSH_CIPHER_SSH2, 16, 32, 0, 0, evp_aes_ctr_mt }, + #ifdef USE_CIPHER_ACSS + { "acss@openssh.org", SSH_CIPHER_SSH2, 16, 5, 0, 0, EVP_acss }, + #endif +@@ -163,7 +164,8 @@ ciphers_valid(const char *names) + for ((p = strsep(&cp, CIPHER_SEP)); p && *p != '\0'; + (p = strsep(&cp, CIPHER_SEP))) { + c = cipher_by_name(p); +- if (c == NULL || c->number != SSH_CIPHER_SSH2) { ++ if (c == NULL || (c->number != SSH_CIPHER_SSH2 && ++c->number != SSH_CIPHER_NONE)) { + debug("bad cipher %s [%s]", p, names); + xfree(cipher_list); + return 0; +@@ -337,6 +339,7 @@ cipher_get_keyiv(CipherContext *cc, u_ch + int evplen; + + switch (c->number) { ++ case SSH_CIPHER_NONE: + case SSH_CIPHER_SSH2: + case SSH_CIPHER_DES: + case SSH_CIPHER_BLOWFISH: +@@ -371,6 +374,7 @@ cipher_set_keyiv(CipherContext *cc, u_ch + int evplen = 0; + + switch (c->number) { ++ case SSH_CIPHER_NONE: + case SSH_CIPHER_SSH2: + case SSH_CIPHER_DES: + case SSH_CIPHER_BLOWFISH: +diff -NupwB openssh-5.2p1-canonical/cipher-ctr-mt.c openssh-5.2p1-hpn13v6/cipher-ctr-mt.c +--- openssh-5.2p1-canonical/cipher-ctr-mt.c 1969-12-31 19:00:00.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/cipher-ctr-mt.c 2009-05-14 12:36:10.000000000 -0400 +@@ -0,0 +1,473 @@ ++/* ++ * OpenSSH Multi-threaded AES-CTR Cipher ++ * ++ * Author: Benjamin Bennett ++ * Copyright (c) 2008 Pittsburgh Supercomputing Center. All rights reserved. ++ * ++ * Based on original OpenSSH AES-CTR cipher. Small portions remain unchanged, ++ * Copyright (c) 2003 Markus Friedl ++ * ++ * Permission to use, copy, modify, and distribute this software for any ++ * purpose with or without fee is hereby granted, provided that the above ++ * copyright notice and this permission notice appear in all copies. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES ++ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF ++ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ++ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES ++ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ++ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF ++ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. ++ */ ++#include "includes.h" ++ ++#include ++ ++#include ++#include ++ ++#include ++ ++#include "xmalloc.h" ++#include "log.h" ++ ++/* compatibility with old or broken OpenSSL versions */ ++#include "openbsd-compat/openssl-compat.h" ++ ++#ifndef USE_BUILTIN_RIJNDAEL ++#include ++#endif ++ ++#include ++ ++/*-------------------- TUNABLES --------------------*/ ++/* Number of pregen threads to use */ ++#define CIPHER_THREADS 2 ++ ++/* Number of keystream queues */ ++#define NUMKQ (CIPHER_THREADS + 2) ++ ++/* Length of a keystream queue */ ++#define KQLEN 4096 ++ ++/* Processor cacheline length */ ++#define CACHELINE_LEN 64 ++ ++/* Collect thread stats and print at cancellation when in debug mode */ ++/* #define CIPHER_THREAD_STATS */ ++ ++/* Use single-byte XOR instead of 8-byte XOR */ ++/* #define CIPHER_BYTE_XOR */ ++/*-------------------- END TUNABLES --------------------*/ ++ ++ ++const EVP_CIPHER *evp_aes_ctr_mt(void); ++ ++#ifdef CIPHER_THREAD_STATS ++/* ++ * Struct to collect thread stats ++ */ ++struct thread_stats { ++ u_int fills; ++ u_int skips; ++ u_int waits; ++ u_int drains; ++}; ++ ++/* ++ * Debug print the thread stats ++ * Use with pthread_cleanup_push for displaying at thread cancellation ++ */ ++static void ++thread_loop_stats(void *x) ++{ ++ struct thread_stats *s = x; ++ ++ debug("tid %lu - %u fills, %u skips, %u waits", pthread_self(), ++ s->fills, s->skips, s->waits); ++} ++ ++ #define STATS_STRUCT(s) struct thread_stats s ++ #define STATS_INIT(s) { memset(&s, 0, sizeof(s)); } ++ #define STATS_FILL(s) { s.fills++; } ++ #define STATS_SKIP(s) { s.skips++; } ++ #define STATS_WAIT(s) { s.waits++; } ++ #define STATS_DRAIN(s) { s.drains++; } ++#else ++ #define STATS_STRUCT(s) ++ #define STATS_INIT(s) ++ #define STATS_FILL(s) ++ #define STATS_SKIP(s) ++ #define STATS_WAIT(s) ++ #define STATS_DRAIN(s) ++#endif ++ ++/* Keystream Queue state */ ++enum { ++ KQINIT, ++ KQEMPTY, ++ KQFILLING, ++ KQFULL, ++ KQDRAINING ++}; ++ ++/* Keystream Queue struct */ ++struct kq { ++ u_char keys[KQLEN][AES_BLOCK_SIZE]; ++ u_char ctr[AES_BLOCK_SIZE]; ++ u_char pad0[CACHELINE_LEN]; ++ volatile int qstate; ++ pthread_mutex_t lock; ++ pthread_cond_t cond; ++ u_char pad1[CACHELINE_LEN]; ++}; ++ ++/* Context struct */ ++struct ssh_aes_ctr_ctx ++{ ++ struct kq q[NUMKQ]; ++ AES_KEY aes_ctx; ++ STATS_STRUCT(stats); ++ u_char aes_counter[AES_BLOCK_SIZE]; ++ pthread_t tid[CIPHER_THREADS]; ++ int state; ++ int qidx; ++ int ridx; ++}; ++ ++/* ++ * increment counter 'ctr', ++ * the counter is of size 'len' bytes and stored in network-byte-order. ++ * (LSB at ctr[len-1], MSB at ctr[0]) ++ */ ++static void ++ssh_ctr_inc(u_char *ctr, u_int len) ++{ ++ int i; ++ ++ for (i = len - 1; i >= 0; i--) ++ if (++ctr[i]) /* continue on overflow */ ++ return; ++} ++ ++/* ++ * Add num to counter 'ctr' ++ */ ++static void ++ssh_ctr_add(u_char *ctr, uint32_t num, u_int len) ++{ ++ int i; ++ uint16_t n; ++ ++ for (n = 0, i = len - 1; i >= 0 && (num || n); i--) { ++ n = ctr[i] + (num & 0xff) + n; ++ num >>= 8; ++ ctr[i] = n & 0xff; ++ n >>= 8; ++ } ++} ++ ++/* ++ * Threads may be cancelled in a pthread_cond_wait, we must free the mutex ++ */ ++static void ++thread_loop_cleanup(void *x) ++{ ++ pthread_mutex_unlock((pthread_mutex_t *)x); ++} ++ ++/* ++ * The life of a pregen thread: ++ * Find empty keystream queues and fill them using their counter. ++ * When done, update counter for the next fill. ++ */ ++static void * ++thread_loop(void *x) ++{ ++ AES_KEY key; ++ STATS_STRUCT(stats); ++ struct ssh_aes_ctr_ctx *c = x; ++ struct kq *q; ++ int i; ++ int qidx; ++ ++ /* Threads stats on cancellation */ ++ STATS_INIT(stats); ++#ifdef CIPHER_THREAD_STATS ++ pthread_cleanup_push(thread_loop_stats, &stats); ++#endif ++ ++ /* Thread local copy of AES key */ ++ memcpy(&key, &c->aes_ctx, sizeof(key)); ++ ++ /* ++ * Handle the special case of startup, one thread must fill ++ * the first KQ then mark it as draining. Lock held throughout. ++ */ ++ if (pthread_equal(pthread_self(), c->tid[0])) { ++ q = &c->q[0]; ++ pthread_mutex_lock(&q->lock); ++ if (q->qstate == KQINIT) { ++ for (i = 0; i < KQLEN; i++) { ++ AES_encrypt(q->ctr, q->keys[i], &key); ++ ssh_ctr_inc(q->ctr, AES_BLOCK_SIZE); ++ } ++ ssh_ctr_add(q->ctr, KQLEN * (NUMKQ - 1), AES_BLOCK_SIZE); ++ q->qstate = KQDRAINING; ++ STATS_FILL(stats); ++ pthread_cond_broadcast(&q->cond); ++ } ++ pthread_mutex_unlock(&q->lock); ++ } ++ else ++ STATS_SKIP(stats); ++ ++ /* ++ * Normal case is to find empty queues and fill them, skipping over ++ * queues already filled by other threads and stopping to wait for ++ * a draining queue to become empty. ++ * ++ * Multiple threads may be waiting on a draining queue and awoken ++ * when empty. The first thread to wake will mark it as filling, ++ * others will move on to fill, skip, or wait on the next queue. ++ */ ++ for (qidx = 1;; qidx = (qidx + 1) % NUMKQ) { ++ /* Check if I was cancelled, also checked in cond_wait */ ++ pthread_testcancel(); ++ ++ /* Lock queue and block if its draining */ ++ q = &c->q[qidx]; ++ pthread_mutex_lock(&q->lock); ++ pthread_cleanup_push(thread_loop_cleanup, &q->lock); ++ while (q->qstate == KQDRAINING || q->qstate == KQINIT) { ++ STATS_WAIT(stats); ++ pthread_cond_wait(&q->cond, &q->lock); ++ } ++ pthread_cleanup_pop(0); ++ ++ /* If filling or full, somebody else got it, skip */ ++ if (q->qstate != KQEMPTY) { ++ pthread_mutex_unlock(&q->lock); ++ STATS_SKIP(stats); ++ continue; ++ } ++ ++ /* ++ * Empty, let's fill it. ++ * Queue lock is relinquished while we do this so others ++ * can see that it's being filled. ++ */ ++ q->qstate = KQFILLING; ++ pthread_mutex_unlock(&q->lock); ++ for (i = 0; i < KQLEN; i++) { ++ AES_encrypt(q->ctr, q->keys[i], &key); ++ ssh_ctr_inc(q->ctr, AES_BLOCK_SIZE); ++ } ++ ++ /* Re-lock, mark full and signal consumer */ ++ pthread_mutex_lock(&q->lock); ++ ssh_ctr_add(q->ctr, KQLEN * (NUMKQ - 1), AES_BLOCK_SIZE); ++ q->qstate = KQFULL; ++ STATS_FILL(stats); ++ pthread_cond_signal(&q->cond); ++ pthread_mutex_unlock(&q->lock); ++ } ++ ++#ifdef CIPHER_THREAD_STATS ++ /* Stats */ ++ pthread_cleanup_pop(1); ++#endif ++ ++ return NULL; ++} ++ ++static int ++ssh_aes_ctr(EVP_CIPHER_CTX *ctx, u_char *dest, const u_char *src, ++ u_int len) ++{ ++ struct ssh_aes_ctr_ctx *c; ++ struct kq *q, *oldq; ++ int ridx; ++ u_char *buf; ++ ++ if (len == 0) ++ return (1); ++ if ((c = EVP_CIPHER_CTX_get_app_data(ctx)) == NULL) ++ return (0); ++ ++ q = &c->q[c->qidx]; ++ ridx = c->ridx; ++ ++ /* src already padded to block multiple */ ++ while (len > 0) { ++ buf = q->keys[ridx]; ++ ++#ifdef CIPHER_BYTE_XOR ++ dest[0] = src[0] ^ buf[0]; ++ dest[1] = src[1] ^ buf[1]; ++ dest[2] = src[2] ^ buf[2]; ++ dest[3] = src[3] ^ buf[3]; ++ dest[4] = src[4] ^ buf[4]; ++ dest[5] = src[5] ^ buf[5]; ++ dest[6] = src[6] ^ buf[6]; ++ dest[7] = src[7] ^ buf[7]; ++ dest[8] = src[8] ^ buf[8]; ++ dest[9] = src[9] ^ buf[9]; ++ dest[10] = src[10] ^ buf[10]; ++ dest[11] = src[11] ^ buf[11]; ++ dest[12] = src[12] ^ buf[12]; ++ dest[13] = src[13] ^ buf[13]; ++ dest[14] = src[14] ^ buf[14]; ++ dest[15] = src[15] ^ buf[15]; ++#else ++ *(uint64_t *)dest = *(uint64_t *)src ^ *(uint64_t *)buf; ++ *(uint64_t *)(dest + 8) = *(uint64_t *)(src + 8) ^ ++ *(uint64_t *)(buf + 8); ++#endif ++ ++ dest += 16; ++ src += 16; ++ len -= 16; ++ ssh_ctr_inc(ctx->iv, AES_BLOCK_SIZE); ++ ++ /* Increment read index, switch queues on rollover */ ++ if ((ridx = (ridx + 1) % KQLEN) == 0) { ++ oldq = q; ++ ++ /* Mark next queue draining, may need to wait */ ++ c->qidx = (c->qidx + 1) % NUMKQ; ++ q = &c->q[c->qidx]; ++ pthread_mutex_lock(&q->lock); ++ while (q->qstate != KQFULL) { ++ STATS_WAIT(c->stats); ++ pthread_cond_wait(&q->cond, &q->lock); ++ } ++ q->qstate = KQDRAINING; ++ pthread_mutex_unlock(&q->lock); ++ ++ /* Mark consumed queue empty and signal producers */ ++ pthread_mutex_lock(&oldq->lock); ++ oldq->qstate = KQEMPTY; ++ STATS_DRAIN(c->stats); ++ pthread_cond_broadcast(&oldq->cond); ++ pthread_mutex_unlock(&oldq->lock); ++ } ++ } ++ c->ridx = ridx; ++ return (1); ++} ++ ++#define HAVE_NONE 0 ++#define HAVE_KEY 1 ++#define HAVE_IV 2 ++static int ++ssh_aes_ctr_init(EVP_CIPHER_CTX *ctx, const u_char *key, const u_char *iv, ++ int enc) ++{ ++ struct ssh_aes_ctr_ctx *c; ++ int i; ++ ++ if ((c = EVP_CIPHER_CTX_get_app_data(ctx)) == NULL) { ++ c = xmalloc(sizeof(*c)); ++ ++ c->state = HAVE_NONE; ++ for (i = 0; i < NUMKQ; i++) { ++ pthread_mutex_init(&c->q[i].lock, NULL); ++ pthread_cond_init(&c->q[i].cond, NULL); ++ } ++ ++ STATS_INIT(c->stats); ++ ++ EVP_CIPHER_CTX_set_app_data(ctx, c); ++ } ++ ++ if (c->state == (HAVE_KEY | HAVE_IV)) { ++ /* Cancel pregen threads */ ++ for (i = 0; i < CIPHER_THREADS; i++) ++ pthread_cancel(c->tid[i]); ++ for (i = 0; i < CIPHER_THREADS; i++) ++ pthread_join(c->tid[i], NULL); ++ /* Start over getting key & iv */ ++ c->state = HAVE_NONE; ++ } ++ ++ if (key != NULL) { ++ AES_set_encrypt_key(key, EVP_CIPHER_CTX_key_length(ctx) * 8, ++ &c->aes_ctx); ++ c->state |= HAVE_KEY; ++ } ++ ++ if (iv != NULL) { ++ memcpy(ctx->iv, iv, AES_BLOCK_SIZE); ++ c->state |= HAVE_IV; ++ } ++ ++ if (c->state == (HAVE_KEY | HAVE_IV)) { ++ /* Clear queues */ ++ memcpy(c->q[0].ctr, ctx->iv, AES_BLOCK_SIZE); ++ c->q[0].qstate = KQINIT; ++ for (i = 1; i < NUMKQ; i++) { ++ memcpy(c->q[i].ctr, ctx->iv, AES_BLOCK_SIZE); ++ ssh_ctr_add(c->q[i].ctr, i * KQLEN, AES_BLOCK_SIZE); ++ c->q[i].qstate = KQEMPTY; ++ } ++ c->qidx = 0; ++ c->ridx = 0; ++ ++ /* Start threads */ ++ for (i = 0; i < CIPHER_THREADS; i++) { ++ pthread_create(&c->tid[i], NULL, thread_loop, c); ++ } ++ pthread_mutex_lock(&c->q[0].lock); ++ while (c->q[0].qstate != KQDRAINING) ++ pthread_cond_wait(&c->q[0].cond, &c->q[0].lock); ++ pthread_mutex_unlock(&c->q[0].lock); ++ ++ } ++ return (1); ++} ++ ++static int ++ssh_aes_ctr_cleanup(EVP_CIPHER_CTX *ctx) ++{ ++ struct ssh_aes_ctr_ctx *c; ++ int i; ++ ++ if ((c = EVP_CIPHER_CTX_get_app_data(ctx)) != NULL) { ++#ifdef CIPHER_THREAD_STATS ++ debug("main thread: %u drains, %u waits", c->stats.drains, ++ c->stats.waits); ++#endif ++ /* Cancel pregen threads */ ++ for (i = 0; i < CIPHER_THREADS; i++) ++ pthread_cancel(c->tid[i]); ++ for (i = 0; i < CIPHER_THREADS; i++) ++ pthread_join(c->tid[i], NULL); ++ ++ memset(c, 0, sizeof(*c)); ++ xfree(c); ++ EVP_CIPHER_CTX_set_app_data(ctx, NULL); ++ } ++ return (1); ++} ++ ++/* */ ++const EVP_CIPHER * ++evp_aes_ctr_mt(void) ++{ ++ static EVP_CIPHER aes_ctr; ++ ++ memset(&aes_ctr, 0, sizeof(EVP_CIPHER)); ++ aes_ctr.nid = NID_undef; ++ aes_ctr.block_size = AES_BLOCK_SIZE; ++ aes_ctr.iv_len = AES_BLOCK_SIZE; ++ aes_ctr.key_len = 16; ++ aes_ctr.init = ssh_aes_ctr_init; ++ aes_ctr.cleanup = ssh_aes_ctr_cleanup; ++ aes_ctr.do_cipher = ssh_aes_ctr; ++#ifndef SSH_OLD_EVP ++ aes_ctr.flags = EVP_CIPH_CBC_MODE | EVP_CIPH_VARIABLE_LENGTH | ++ EVP_CIPH_ALWAYS_CALL_INIT | EVP_CIPH_CUSTOM_IV; ++#endif ++ return (&aes_ctr); ++} +diff -NupwB openssh-5.2p1-canonical/clientloop.c openssh-5.2p1-hpn13v6/clientloop.c +--- openssh-5.2p1-canonical/clientloop.c 2009-02-14 00:28:21.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/clientloop.c 2009-05-14 12:36:10.000000000 -0400 +@@ -1688,9 +1688,15 @@ client_request_x11(const char *request_t + sock = x11_connect_display(); + if (sock < 0) + return NULL; ++ /* again is this really necessary for X11? */ ++ if (options.hpn_disabled) + c = channel_new("x11", + SSH_CHANNEL_X11_OPEN, sock, sock, -1, + CHAN_TCP_WINDOW_DEFAULT, CHAN_X11_PACKET_DEFAULT, 0, "x11", 1); ++ else ++ c = channel_new("x11", ++ SSH_CHANNEL_X11_OPEN, sock, sock, -1, ++ options.hpn_buffer_size, CHAN_X11_PACKET_DEFAULT, 0, "x11", 1); + c->force_drain = 1; + return c; + } +@@ -1710,9 +1716,15 @@ client_request_agent(const char *request + sock = ssh_get_authentication_socket(); + if (sock < 0) + return NULL; ++ if (options.hpn_disabled) + c = channel_new("authentication agent connection", + SSH_CHANNEL_OPEN, sock, sock, -1, +- CHAN_X11_WINDOW_DEFAULT, CHAN_TCP_PACKET_DEFAULT, 0, ++ CHAN_X11_WINDOW_DEFAULT, CHAN_TCP_WINDOW_DEFAULT, 0, ++ "authentication agent connection", 1); ++ else ++ c = channel_new("authentication agent connection", ++ SSH_CHANNEL_OPEN, sock, sock, -1, ++ options.hpn_buffer_size, options.hpn_buffer_size, 0, + "authentication agent connection", 1); + c->force_drain = 1; + return c; +@@ -1740,10 +1752,18 @@ client_request_tun_fwd(int tun_mode, int + return -1; + } + ++ if(options.hpn_disabled) ++ c = channel_new("tun", SSH_CHANNEL_OPENING, fd, fd, -1, ++ CHAN_TCP_WINDOW_DEFAULT, CHAN_TCP_PACKET_DEFAULT, ++ 0, "tun", 1); ++ else + c = channel_new("tun", SSH_CHANNEL_OPENING, fd, fd, -1, +- CHAN_TCP_WINDOW_DEFAULT, CHAN_TCP_PACKET_DEFAULT, 0, "tun", 1); ++ options.hpn_buffer_size, CHAN_TCP_PACKET_DEFAULT, ++ 0, "tun", 1); + c->datagram = 1; + ++ ++ + #if defined(SSH_TUN_FILTER) + if (options.tun_open == SSH_TUNMODE_POINTOPOINT) + channel_register_filter(c->self, sys_tun_infilter, +diff -NupwB openssh-5.2p1-canonical/compat.c openssh-5.2p1-hpn13v6/compat.c +--- openssh-5.2p1-canonical/compat.c 2008-11-03 03:20:14.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/compat.c 2009-05-14 12:36:10.000000000 -0400 +@@ -170,6 +170,15 @@ compat_datafellows(const char *version) + strlen(check[i].pat), 0) == 1) { + debug("match: %s pat %s", version, check[i].pat); + datafellows = check[i].bugs; ++ /* Check to see if the remote side is OpenSSH and not HPN */ ++ if(strstr(version,"OpenSSH") != NULL) ++ { ++ if (strstr(version,"hpn") == NULL) ++ { ++ datafellows |= SSH_BUG_LARGEWINDOW; ++ debug("Remote is NON-HPN aware"); ++ } ++ } + return; + } + } +diff -NupwB openssh-5.2p1-canonical/compat.h openssh-5.2p1-hpn13v6/compat.h +--- openssh-5.2p1-canonical/compat.h 2008-11-03 03:20:14.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/compat.h 2009-05-14 12:36:10.000000000 -0400 +@@ -58,6 +58,7 @@ + #define SSH_OLD_FORWARD_ADDR 0x01000000 + #define SSH_BUG_RFWD_ADDR 0x02000000 + #define SSH_NEW_OPENSSH 0x04000000 ++#define SSH_BUG_LARGEWINDOW 0x08000000 + + void enable_compat13(void); + void enable_compat20(void); +Common subdirectories: openssh-5.2p1-canonical/contrib and openssh-5.2p1-hpn13v6/contrib +diff -NupwB openssh-5.2p1-canonical/HPN-README openssh-5.2p1-hpn13v6/HPN-README +--- openssh-5.2p1-canonical/HPN-README 1969-12-31 19:00:00.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/HPN-README 2009-05-14 12:36:10.000000000 -0400 +@@ -0,0 +1,128 @@ ++Notes: ++ ++MULTI-THREADED CIPHER: ++The AES cipher in CTR mode has been multithreaded (MTR-AES-CTR). This will allow ssh installations ++on hosts with multiple cores to use more than one processing core during encryption. ++Tests have show significant throughput performance increases when using MTR-AES-CTR up ++to and including a full gigabit per second on quad core systems. It should be possible to ++achieve full line rate on dual core systems but OS and data management overhead makes this ++more difficult to achieve. The cipher stream from MTR-AES-CTR is entirely compatible with single ++thread AES-CTR (ST-AES-CTR) implementations and should be 100% backward compatible. Optimal ++performance requires the MTR-AES-CTR mode be enabled on both ends of the connection. ++The MTR-AES-CTR replaces ST-AES-CTR and is used in exactly the same way with the same ++nomenclature. ++Use examples: ssh -caes128-ctr you@host.com ++ scp -oCipher=aes256-ctr file you@host.com:~/file ++ ++NONE CIPHER: ++To use the NONE option you must have the NoneEnabled switch set on the server and ++you *must* have *both* NoneEnabled and NoneSwitch set to yes on the client. The NONE ++feature works with ALL ssh subsystems (as far as we can tell) *AS LONG AS* a tty is not ++spawned. If a user uses the -T switch to prevent a tty being created the NONE cipher will ++be disabled. ++ ++The performance increase will only be as good as the network and TCP stack tuning ++on the reciever side of the connection allows. As a rule of thumb a user will need ++at least 10Mb/s connection with a 100ms RTT to see a doubling of performance. The ++HPN-SSH home page describes this in greater detail. ++ ++http://www.psc.edu/networking/projects/hpn-ssh ++ ++BUFFER SIZES: ++ ++If HPN is disabled the receive buffer size will be set to the ++OpenSSH default of 64K. ++ ++If an HPN system connects to a nonHPN system the receive buffer will ++be set to the HPNBufferSize value. The default is 2MB but user adjustable. ++ ++If an HPN to HPN connection is established a number of different things might ++happen based on the user options and conditions. ++ ++Conditions: HPNBufferSize NOT Set, TCPRcvBufPoll enabled, TCPRcvBuf NOT Set ++HPN Buffer Size = up to 64MB ++This is the default state. The HPN buffer size will grow to a maximum of 64MB ++as the TCP receive buffer grows. The maximum HPN Buffer size of 64MB is ++geared towards 10GigE transcontinental connections. ++ ++Conditions: HPNBufferSize NOT Set, TCPRcvBufPoll disabled, TCPRcvBuf NOT Set ++HPN Buffer Size = TCP receive buffer value. ++Users on non-autotuning systesm should disable TCPRcvBufPoll in the ++ssh_cofig and sshd_config ++ ++Conditions: HPNBufferSize SET, TCPRcvBufPoll disabled, TCPRcvBuf NOT Set ++HPN Buffer Size = minmum of TCP receive buffer and HPNBufferSize. ++This would be the system defined TCP receive buffer (RWIN). ++ ++Conditions: HPNBufferSize SET, TCPRcvBufPoll disabled, TCPRcvBuf SET ++HPN Buffer Size = minmum of TCPRcvBuf and HPNBufferSize. ++Generally there is no need to set both. ++ ++Conditions: HPNBufferSize SET, TCPRcvBufPoll enabled, TCPRcvBuf NOT Set ++HPN Buffer Size = grows to HPNBufferSize ++The buffer will grow up to the maximum size specified here. ++ ++Conditions: HPNBufferSize SET, TCPRcvBufPoll enabled, TCPRcvBuf SET ++HPN Buffer Size = minmum of TCPRcvBuf and HPNBufferSize. ++Generally there is no need to set both of these, especially on autotuning ++systems. However, if the users wishes to override the autotuning this would be ++one way to do it. ++ ++Conditions: HPNBufferSize NOT Set, TCPRcvBufPoll enabled, TCPRcvBuf SET ++HPN Buffer Size = TCPRcvBuf. ++This will override autotuning and set the TCP recieve buffer to the user defined ++value. ++ ++ ++HPN Specific Configuration options ++ ++TcpRcvBuf=[int]KB client ++ set the TCP socket receive buffer to n Kilobytes. It can be set up to the ++maximum socket size allowed by the system. This is useful in situations where ++the tcp receive window is set low but the maximum buffer size is set ++higher (as is typical). This works on a per TCP connection basis. You can also ++use this to artifically limit the transfer rate of the connection. In these ++cases the throughput will be no more than n/RTT. The minimum buffer size is 1KB. ++Default is the current system wide tcp receive buffer size. ++ ++TcpRcvBufPoll=[yes/no] client/server ++ enable of disable the polling of the tcp receive buffer through the life ++of the connection. You would want to make sure that this option is enabled ++for systems making use of autotuning kernels (linux 2.4.24+, 2.6, MS Vista) ++default is yes. ++ ++NoneEnabled=[yes/no] client/server ++ enable or disable the use of the None cipher. Care must always be used ++when enabling this as it will allow users to send data in the clear. However, ++it is important to note that authentication information remains encrypted ++even if this option is enabled. Set to no by default. ++ ++NoneSwitch=[yes/no] client ++ Switch the encryption cipher being used to the None cipher after ++authentication takes place. NoneEnabled must be enabled on both the client ++and server side of the connection. When the connection switches to the NONE ++cipher a warning is sent to STDERR. The connection attempt will fail with an ++error if a client requests a NoneSwitch from the server that does not explicitly ++have NoneEnabled set to yes. Note: The NONE cipher cannot be used in ++interactive (shell) sessions and it will fail silently. Set to no by default. ++ ++HPNDisabled=[yes/no] client/server ++ In some situations, such as transfers on a local area network, the impact ++of the HPN code produces a net decrease in performance. In these cases it is ++helpful to disable the HPN functionality. By default HPNDisabled is set to no. ++ ++HPNBufferSize=[int]KB client/server ++ This is the default buffer size the HPN functionality uses when interacting ++with nonHPN SSH installations. Conceptually this is similar to the TcpRcvBuf ++option as applied to the internal SSH flow control. This value can range from ++1KB to 64MB (1-65536). Use of oversized or undersized buffers can cause performance ++problems depending on the length of the network path. The default size of this buffer ++is 2MB. ++ ++ ++Credits: This patch was conceived, designed, and led by Chris Rapier (rapier@psc.edu) ++ The majority of the actual coding for versions up to HPN12v1 was performed ++ by Michael Stevens (mstevens@andrew.cmu.edu). The MT-AES-CTR cipher was ++ implemented by Ben Bennet (ben@psc.edu). This work was financed, in part, ++ by Cisco System, Inc., the National Library of Medicine, ++ and the National Science Foundation. +diff -NupwB openssh-5.2p1-canonical/kex.c openssh-5.2p1-hpn13v6/kex.c +--- openssh-5.2p1-canonical/kex.c 2008-11-03 03:19:12.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/kex.c 2009-05-14 12:36:10.000000000 -0400 +@@ -48,6 +48,7 @@ + #include "match.h" + #include "dispatch.h" + #include "monitor.h" ++#include "canohost.h" + + #define KEX_COOKIE_LEN 16 + +@@ -64,7 +65,8 @@ static void kex_kexinit_finish(Kex *); + static void kex_choose_conf(Kex *); + + /* put algorithm proposal into buffer */ +-static void ++/* used in sshconnect.c as well as kex.c */ ++void + kex_prop2buf(Buffer *b, char *proposal[PROPOSAL_MAX]) + { + u_int i; +@@ -376,6 +378,13 @@ kex_choose_conf(Kex *kex) + int nenc, nmac, ncomp; + u_int mode, ctos, need; + int first_kex_follows, type; ++ int log_flag = 0; ++ ++ int auth_flag; ++ ++ auth_flag = packet_authentication_state(); ++ ++ debug ("AUTH STATE IS %d", auth_flag); + + my = kex_buf2prop(&kex->my, NULL); + peer = kex_buf2prop(&kex->peer, &first_kex_follows); +@@ -400,11 +409,34 @@ kex_choose_conf(Kex *kex) + choose_enc (&newkeys->enc, cprop[nenc], sprop[nenc]); + choose_mac (&newkeys->mac, cprop[nmac], sprop[nmac]); + choose_comp(&newkeys->comp, cprop[ncomp], sprop[ncomp]); ++ debug("REQUESTED ENC.NAME is '%s'", newkeys->enc.name); ++ if (strcmp(newkeys->enc.name, "none") == 0) { ++ debug("Requesting NONE. Authflag is %d", auth_flag); ++ if (auth_flag == 1) { ++ debug("None requested post authentication."); ++ } else { ++ fatal("Pre-authentication none cipher requests are not allowed."); ++ } ++ } + debug("kex: %s %s %s %s", + ctos ? "client->server" : "server->client", + newkeys->enc.name, + newkeys->mac.name, + newkeys->comp.name); ++ /* client starts withctos = 0 && log flag = 0 and no log*/ ++ /* 2nd client pass ctos=1 and flag = 1 so no log*/ ++ /* server starts with ctos =1 && log_flag = 0 so log */ ++ /* 2nd sever pass ctos = 1 && log flag = 1 so no log*/ ++ /* -cjr*/ ++ if (ctos && !log_flag) { ++ logit("SSH: Server;Ltype: Kex;Remote: %s-%d;Enc: %s;MAC: %s;Comp: %s", ++ get_remote_ipaddr(), ++ get_remote_port(), ++ newkeys->enc.name, ++ newkeys->mac.name, ++ newkeys->comp.name); ++ } ++ log_flag = 1; + } + choose_kex(kex, cprop[PROPOSAL_KEX_ALGS], sprop[PROPOSAL_KEX_ALGS]); + choose_hostkeyalg(kex, cprop[PROPOSAL_SERVER_HOST_KEY_ALGS], +diff -NupwB openssh-5.2p1-canonical/kex.h openssh-5.2p1-hpn13v6/kex.h +--- openssh-5.2p1-canonical/kex.h 2007-06-11 00:01:42.000000000 -0400 ++++ openssh-5.2p1-hpn13v6/kex.h 2009-05-14 12:36:10.000000000 -0400 +@@ -127,6 +127,8 @@ struct Kex { + void (*kex[KEX_MAX])(Kex *); + }; + ++void kex_prop2buf(Buffer *, char *proposal[PROPOSAL_MAX]); ++ + Kex *kex_setup(char *[PROPOSAL_MAX]); + void kex_finish(Kex *); + +diff -NupwB openssh-5.2p1-canonical/Makefile.in openssh-5.2p1-hpn13v6/Makefile.in +--- openssh-5.2p1-canonical/Makefile.in 2008-11-05 00:20:46.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/Makefile.in 2009-05-14 12:36:10.000000000 -0400 +@@ -43,7 +43,7 @@ CC=@CC@ + LD=@LD@ + CFLAGS=@CFLAGS@ + CPPFLAGS=-I. -I$(srcdir) @CPPFLAGS@ $(PATHS) @DEFS@ +-LIBS=@LIBS@ ++LIBS=@LIBS@ -lpthread + SSHDLIBS=@SSHDLIBS@ + LIBEDIT=@LIBEDIT@ + AR=@AR@ +@@ -64,7 +64,7 @@ TARGETS=ssh$(EXEEXT) sshd$(EXEEXT) ssh-a + + LIBSSH_OBJS=acss.o authfd.o authfile.o bufaux.o bufbn.o buffer.o \ + canohost.o channels.o cipher.o cipher-acss.o cipher-aes.o \ +- cipher-bf1.o cipher-ctr.o cipher-3des1.o cleanup.o \ ++ cipher-bf1.o cipher-ctr.o cipher-ctr-mt.o cipher-3des1.o cleanup.o \ + compat.o compress.o crc32.o deattack.o fatal.o hostfile.o \ + log.o match.o md-sha256.o moduli.o nchan.o packet.o \ + readpass.o rsa.o ttymodes.o xmalloc.o addrmatch.o \ +diff -NupwB openssh-5.2p1-canonical/myproposal.h openssh-5.2p1-hpn13v6/myproposal.h +--- openssh-5.2p1-canonical/myproposal.h 2009-01-28 00:33:31.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/myproposal.h 2009-05-14 12:36:10.000000000 -0400 +@@ -47,6 +47,8 @@ + "arcfour256,arcfour128," \ + "aes128-cbc,3des-cbc,blowfish-cbc,cast128-cbc," \ + "aes192-cbc,aes256-cbc,arcfour,rijndael-cbc@lysator.liu.se" ++#define KEX_ENCRYPT_INCLUDE_NONE KEX_DEFAULT_ENCRYPT \ ++ ",none" + #define KEX_DEFAULT_MAC \ + "hmac-md5,hmac-sha1,umac-64@openssh.com,hmac-ripemd160," \ + "hmac-ripemd160@openssh.com," \ +Common subdirectories: openssh-5.2p1-canonical/openbsd-compat and openssh-5.2p1-hpn13v6/openbsd-compat +diff -NupwB openssh-5.2p1-canonical/packet.c openssh-5.2p1-hpn13v6/packet.c +--- openssh-5.2p1-canonical/packet.c 2009-02-14 00:35:01.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/packet.c 2009-05-14 12:36:10.000000000 -0400 +@@ -775,7 +775,7 @@ packet_enable_delayed_compress(void) + /* + * Finalize packet in SSH2 format (compress, mac, encrypt, enqueue) + */ +-static void ++static int + packet_send2_wrapped(void) + { + u_char type, *cp, *macbuf = NULL; +@@ -888,11 +888,13 @@ packet_send2_wrapped(void) + set_newkeys(MODE_OUT); + else if (type == SSH2_MSG_USERAUTH_SUCCESS && server_side) + packet_enable_delayed_compress(); ++ return(packet_length); + } + +-static void ++static int + packet_send2(void) + { ++ static int packet_length = 0; + static int rekeying = 0; + struct packet *p; + u_char type, *cp; +@@ -910,7 +912,7 @@ packet_send2(void) + memcpy(&p->payload, &outgoing_packet, sizeof(Buffer)); + buffer_init(&outgoing_packet); + TAILQ_INSERT_TAIL(&outgoing, p, next); +- return; ++ return(sizeof(Buffer)); + } + } + +@@ -918,7 +920,7 @@ packet_send2(void) + if (type == SSH2_MSG_KEXINIT) + rekeying = 1; + +- packet_send2_wrapped(); ++ packet_length = packet_send2_wrapped(); + + /* after a NEWKEYS message we can send the complete queue */ + if (type == SSH2_MSG_NEWKEYS) { +@@ -931,19 +933,22 @@ packet_send2(void) + sizeof(Buffer)); + TAILQ_REMOVE(&outgoing, p, next); + xfree(p); +- packet_send2_wrapped(); ++ packet_length += packet_send2_wrapped(); + } + } ++ return(packet_length); + } + +-void ++int + packet_send(void) + { ++ int packet_len = 0; + if (compat20) +- packet_send2(); ++ packet_len = packet_send2(); + else + packet_send1(); + DBG(debug("packet_send done")); ++ return(packet_len); + } + + /* +@@ -1544,23 +1549,25 @@ packet_disconnect(const char *fmt,...) + + /* Checks if there is any buffered output, and tries to write some of the output. */ + +-void ++int + packet_write_poll(void) + { +- int len = buffer_len(&output); ++ int len = 0; ++ len = buffer_len(&output); + + if (len > 0) { + len = write(connection_out, buffer_ptr(&output), len); + if (len == -1) { + if (errno == EINTR || errno == EAGAIN || + errno == EWOULDBLOCK) +- return; ++ return (0); + fatal("Write failed: %.100s", strerror(errno)); + } + if (len == 0) + fatal("Write connection closed"); + buffer_consume(&output, len); + } ++ return(len); + } + + +@@ -1569,16 +1576,17 @@ packet_write_poll(void) + * written. + */ + +-void ++int + packet_write_wait(void) + { + fd_set *setp; + int ret, ms_remain; + struct timeval start, timeout, *timeoutp = NULL; ++ u_int bytes_sent = 0; + + setp = (fd_set *)xcalloc(howmany(connection_out + 1, NFDBITS), + sizeof(fd_mask)); +- packet_write_poll(); ++ bytes_sent += packet_write_poll(); + while (packet_have_data_to_write()) { + memset(setp, 0, howmany(connection_out + 1, NFDBITS) * + sizeof(fd_mask)); +@@ -1612,7 +1620,7 @@ packet_write_wait(void) + "waiting to write", get_remote_ipaddr()); + cleanup_exit(255); + } +- packet_write_poll(); ++ bytes_sent += packet_write_poll(); + } + xfree(setp); + } +@@ -1736,12 +1744,24 @@ packet_send_ignore(int nbytes) + } + } + ++int rekey_requested = 0; ++void ++packet_request_rekeying(void) ++{ ++ rekey_requested = 1; ++} ++ + #define MAX_PACKETS (1U<<31) + int + packet_need_rekeying(void) + { + if (datafellows & SSH_BUG_NOREKEY) + return 0; ++ if (rekey_requested == 1) ++ { ++ rekey_requested = 0; ++ return 1; ++ } + return + (p_send.packets > MAX_PACKETS) || + (p_read.packets > MAX_PACKETS) || +@@ -1766,3 +1786,9 @@ packet_set_authenticated(void) + { + after_authentication = 1; + } ++ ++int ++packet_authentication_state(void) ++{ ++ return(after_authentication); ++} +diff -NupwB openssh-5.2p1-canonical/packet.h openssh-5.2p1-hpn13v6/packet.h +--- openssh-5.2p1-canonical/packet.h 2008-07-11 03:36:48.000000000 -0400 ++++ openssh-5.2p1-hpn13v6/packet.h 2009-05-14 12:36:10.000000000 -0400 +@@ -20,6 +20,9 @@ + + #include + ++void ++packet_request_rekeying(void); ++ + void packet_set_connection(int, int); + void packet_set_timeout(int, int); + void packet_set_nonblocking(void); +@@ -35,6 +38,7 @@ void packet_set_interactive(int); + int packet_is_interactive(void); + void packet_set_server(void); + void packet_set_authenticated(void); ++int packet_authentication_state(void); + + void packet_start(u_char); + void packet_put_char(int ch); +@@ -44,7 +48,7 @@ void packet_put_bignum2(BIGNUM * val + void packet_put_string(const void *buf, u_int len); + void packet_put_cstring(const char *str); + void packet_put_raw(const void *buf, u_int len); +-void packet_send(void); ++int packet_send(void); + + int packet_read(void); + void packet_read_expect(int type); +@@ -73,8 +77,8 @@ void packet_set_state(int, u_int32_t, u + int packet_get_ssh1_cipher(void); + void packet_set_iv(int, u_char *); + +-void packet_write_poll(void); +-void packet_write_wait(void); ++int packet_write_poll(void); ++int packet_write_wait(void); + int packet_have_data_to_write(void); + int packet_not_very_much_data_to_write(void); + +diff -NupwB openssh-5.2p1-canonical/progressmeter.c openssh-5.2p1-hpn13v6/progressmeter.c +--- openssh-5.2p1-canonical/progressmeter.c 2006-08-04 22:39:40.000000000 -0400 ++++ openssh-5.2p1-hpn13v6/progressmeter.c 2009-05-14 12:36:10.000000000 -0400 +@@ -68,6 +68,8 @@ static time_t last_update; /* last progr + static char *file; /* name of the file being transferred */ + static off_t end_pos; /* ending position of transfer */ + static off_t cur_pos; /* transfer position as of last refresh */ ++static off_t last_pos; ++static off_t max_delta_pos = 0; + static volatile off_t *counter; /* progress counter */ + static long stalled; /* how long we have been stalled */ + static int bytes_per_second; /* current speed in bytes per second */ +@@ -128,12 +130,17 @@ refresh_progress_meter(void) + int hours, minutes, seconds; + int i, len; + int file_len; ++ off_t delta_pos; + + transferred = *counter - cur_pos; + cur_pos = *counter; + now = time(NULL); + bytes_left = end_pos - cur_pos; + ++ delta_pos = cur_pos - last_pos; ++ if (delta_pos > max_delta_pos) ++ max_delta_pos = delta_pos; ++ + if (bytes_left > 0) + elapsed = now - last_update; + else { +@@ -158,7 +165,7 @@ refresh_progress_meter(void) + + /* filename */ + buf[0] = '\0'; +- file_len = win_size - 35; ++ file_len = win_size - 45; + if (file_len > 0) { + len = snprintf(buf, file_len + 1, "\r%s", file); + if (len < 0) +@@ -175,7 +182,8 @@ refresh_progress_meter(void) + percent = ((float)cur_pos / end_pos) * 100; + else + percent = 100; +- snprintf(buf + strlen(buf), win_size - strlen(buf), ++ ++ snprintf(buf + strlen(buf), win_size - strlen(buf-8), + " %3d%% ", percent); + + /* amount transferred */ +@@ -188,6 +196,15 @@ refresh_progress_meter(void) + (off_t)bytes_per_second); + strlcat(buf, "/s ", win_size); + ++ /* instantaneous rate */ ++ if (bytes_left > 0) ++ format_rate(buf + strlen(buf), win_size - strlen(buf), ++ delta_pos); ++ else ++ format_rate(buf + strlen(buf), win_size - strlen(buf), ++ max_delta_pos); ++ strlcat(buf, "/s ", win_size); ++ + /* ETA */ + if (!transferred) + stalled += elapsed; +@@ -224,6 +241,7 @@ refresh_progress_meter(void) + + atomicio(vwrite, STDOUT_FILENO, buf, win_size - 1); + last_update = now; ++ last_pos = cur_pos; + } + + /*ARGSUSED*/ +diff -NupwB openssh-5.2p1-canonical/readconf.c openssh-5.2p1-hpn13v6/readconf.c +--- openssh-5.2p1-canonical/readconf.c 2009-02-14 00:28:21.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/readconf.c 2009-05-14 12:36:10.000000000 -0400 +@@ -131,6 +131,8 @@ typedef enum { + oSendEnv, oControlPath, oControlMaster, oHashKnownHosts, + oTunnel, oTunnelDevice, oLocalCommand, oPermitLocalCommand, + oVisualHostKey, oZeroKnowledgePasswordAuthentication, ++ oNoneEnabled, oTcpRcvBufPoll, oTcpRcvBuf, oNoneSwitch, oHPNDisabled, ++ oHPNBufferSize, + oDeprecated, oUnsupported + } OpCodes; + +@@ -234,6 +236,12 @@ static struct { + #else + { "zeroknowledgepasswordauthentication", oUnsupported }, + #endif ++ { "noneenabled", oNoneEnabled }, ++ { "tcprcvbufpoll", oTcpRcvBufPoll }, ++ { "tcprcvbuf", oTcpRcvBuf }, ++ { "noneswitch", oNoneSwitch }, ++ { "hpndisabled", oHPNDisabled }, ++ { "hpnbuffersize", oHPNBufferSize }, + + { NULL, oBadOption } + }; +@@ -465,6 +473,37 @@ parse_flag: + intptr = &options->check_host_ip; + goto parse_flag; + ++ case oNoneEnabled: ++ intptr = &options->none_enabled; ++ goto parse_flag; ++ ++ /* we check to see if the command comes from the */ ++ /* command line or not. If it does then enable it */ ++ /* otherwise fail. NONE should never be a default configuration */ ++ case oNoneSwitch: ++ if(strcmp(filename,"command-line")==0) ++ { ++ intptr = &options->none_switch; ++ goto parse_flag; ++ } else { ++ error("NoneSwitch is found in %.200s.\nYou may only use this configuration option from the command line", filename); ++ error("Continuing..."); ++ debug("NoneSwitch directive found in %.200s.", filename); ++ return 0; ++ } ++ ++ case oHPNDisabled: ++ intptr = &options->hpn_disabled; ++ goto parse_flag; ++ ++ case oHPNBufferSize: ++ intptr = &options->hpn_buffer_size; ++ goto parse_int; ++ ++ case oTcpRcvBufPoll: ++ intptr = &options->tcp_rcv_buf_poll; ++ goto parse_flag; ++ + case oVerifyHostKeyDNS: + intptr = &options->verify_host_key_dns; + goto parse_yesnoask; +@@ -643,6 +682,10 @@ parse_int: + intptr = &options->connection_attempts; + goto parse_int; + ++ case oTcpRcvBuf: ++ intptr = &options->tcp_rcv_buf; ++ goto parse_int; ++ + case oCipher: + intptr = &options->cipher; + arg = strdelim(&s); +@@ -1065,6 +1108,12 @@ initialize_options(Options * options) + options->permit_local_command = -1; + options->visual_host_key = -1; + options->zero_knowledge_password_authentication = -1; ++ options->none_switch = -1; ++ options->none_enabled = -1; ++ options->hpn_disabled = -1; ++ options->hpn_buffer_size = -1; ++ options->tcp_rcv_buf_poll = -1; ++ options->tcp_rcv_buf = -1; + } + + /* +@@ -1187,6 +1236,29 @@ fill_default_options(Options * options) + options->server_alive_interval = 0; + if (options->server_alive_count_max == -1) + options->server_alive_count_max = 3; ++ if (options->none_switch == -1) ++ options->none_switch = 0; ++ if (options->hpn_disabled == -1) ++ options->hpn_disabled = 0; ++ if (options->hpn_buffer_size > -1) ++ { ++ /* if a user tries to set the size to 0 set it to 1KB */ ++ if (options->hpn_buffer_size == 0) ++ options->hpn_buffer_size = 1024; ++ /*limit the buffer to 64MB*/ ++ if (options->hpn_buffer_size > 65536) ++ { ++ options->hpn_buffer_size = 65536*1024; ++ debug("User requested buffer larger than 64MB. Request reverted to 64MB"); ++ } ++ debug("hpn_buffer_size set to %d", options->hpn_buffer_size); ++ } ++ if (options->tcp_rcv_buf == 0) ++ options->tcp_rcv_buf = 1; ++ if (options->tcp_rcv_buf > -1) ++ options->tcp_rcv_buf *=1024; ++ if (options->tcp_rcv_buf_poll == -1) ++ options->tcp_rcv_buf_poll = 1; + if (options->control_master == -1) + options->control_master = 0; + if (options->hash_known_hosts == -1) +diff -NupwB openssh-5.2p1-canonical/readconf.c.orig openssh-5.2p1-hpn13v6/readconf.c.orig +--- openssh-5.2p1-canonical/readconf.c.orig 1969-12-31 19:00:00.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/readconf.c.orig 2009-02-14 00:28:21.000000000 -0500 +@@ -0,0 +1,1310 @@ ++/* $OpenBSD: readconf.c,v 1.176 2009/02/12 03:00:56 djm Exp $ */ ++/* ++ * Author: Tatu Ylonen ++ * Copyright (c) 1995 Tatu Ylonen , Espoo, Finland ++ * All rights reserved ++ * Functions for reading the configuration files. ++ * ++ * As far as I am concerned, the code I have written for this software ++ * can be used freely for any purpose. Any derived versions of this ++ * software must be clearly marked as such, and if the derived work is ++ * incompatible with the protocol description in the RFC file, it must be ++ * called by a name other than "ssh" or "Secure Shell". ++ */ ++ ++#include "includes.h" ++ ++#include ++#include ++#include ++ ++#include ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include "xmalloc.h" ++#include "ssh.h" ++#include "compat.h" ++#include "cipher.h" ++#include "pathnames.h" ++#include "log.h" ++#include "key.h" ++#include "readconf.h" ++#include "match.h" ++#include "misc.h" ++#include "buffer.h" ++#include "kex.h" ++#include "mac.h" ++ ++/* Format of the configuration file: ++ ++ # Configuration data is parsed as follows: ++ # 1. command line options ++ # 2. user-specific file ++ # 3. system-wide file ++ # Any configuration value is only changed the first time it is set. ++ # Thus, host-specific definitions should be at the beginning of the ++ # configuration file, and defaults at the end. ++ ++ # Host-specific declarations. These may override anything above. A single ++ # host may match multiple declarations; these are processed in the order ++ # that they are given in. ++ ++ Host *.ngs.fi ngs.fi ++ User foo ++ ++ Host fake.com ++ HostName another.host.name.real.org ++ User blaah ++ Port 34289 ++ ForwardX11 no ++ ForwardAgent no ++ ++ Host books.com ++ RemoteForward 9999 shadows.cs.hut.fi:9999 ++ Cipher 3des ++ ++ Host fascist.blob.com ++ Port 23123 ++ User tylonen ++ PasswordAuthentication no ++ ++ Host puukko.hut.fi ++ User t35124p ++ ProxyCommand ssh-proxy %h %p ++ ++ Host *.fr ++ PublicKeyAuthentication no ++ ++ Host *.su ++ Cipher none ++ PasswordAuthentication no ++ ++ Host vpn.fake.com ++ Tunnel yes ++ TunnelDevice 3 ++ ++ # Defaults for various options ++ Host * ++ ForwardAgent no ++ ForwardX11 no ++ PasswordAuthentication yes ++ RSAAuthentication yes ++ RhostsRSAAuthentication yes ++ StrictHostKeyChecking yes ++ TcpKeepAlive no ++ IdentityFile ~/.ssh/identity ++ Port 22 ++ EscapeChar ~ ++ ++*/ ++ ++/* Keyword tokens. */ ++ ++typedef enum { ++ oBadOption, ++ oForwardAgent, oForwardX11, oForwardX11Trusted, oGatewayPorts, ++ oExitOnForwardFailure, ++ oPasswordAuthentication, oRSAAuthentication, ++ oChallengeResponseAuthentication, oXAuthLocation, ++ oIdentityFile, oHostName, oPort, oCipher, oRemoteForward, oLocalForward, ++ oUser, oHost, oEscapeChar, oRhostsRSAAuthentication, oProxyCommand, ++ oGlobalKnownHostsFile, oUserKnownHostsFile, oConnectionAttempts, ++ oBatchMode, oCheckHostIP, oStrictHostKeyChecking, oCompression, ++ oCompressionLevel, oTCPKeepAlive, oNumberOfPasswordPrompts, ++ oUsePrivilegedPort, oLogLevel, oCiphers, oProtocol, oMacs, ++ oGlobalKnownHostsFile2, oUserKnownHostsFile2, oPubkeyAuthentication, ++ oKbdInteractiveAuthentication, oKbdInteractiveDevices, oHostKeyAlias, ++ oDynamicForward, oPreferredAuthentications, oHostbasedAuthentication, ++ oHostKeyAlgorithms, oBindAddress, oSmartcardDevice, ++ oClearAllForwardings, oNoHostAuthenticationForLocalhost, ++ oEnableSSHKeysign, oRekeyLimit, oVerifyHostKeyDNS, oConnectTimeout, ++ oAddressFamily, oGssAuthentication, oGssDelegateCreds, ++ oServerAliveInterval, oServerAliveCountMax, oIdentitiesOnly, ++ oSendEnv, oControlPath, oControlMaster, oHashKnownHosts, ++ oTunnel, oTunnelDevice, oLocalCommand, oPermitLocalCommand, ++ oVisualHostKey, oZeroKnowledgePasswordAuthentication, ++ oDeprecated, oUnsupported ++} OpCodes; ++ ++/* Textual representations of the tokens. */ ++ ++static struct { ++ const char *name; ++ OpCodes opcode; ++} keywords[] = { ++ { "forwardagent", oForwardAgent }, ++ { "forwardx11", oForwardX11 }, ++ { "forwardx11trusted", oForwardX11Trusted }, ++ { "exitonforwardfailure", oExitOnForwardFailure }, ++ { "xauthlocation", oXAuthLocation }, ++ { "gatewayports", oGatewayPorts }, ++ { "useprivilegedport", oUsePrivilegedPort }, ++ { "rhostsauthentication", oDeprecated }, ++ { "passwordauthentication", oPasswordAuthentication }, ++ { "kbdinteractiveauthentication", oKbdInteractiveAuthentication }, ++ { "kbdinteractivedevices", oKbdInteractiveDevices }, ++ { "rsaauthentication", oRSAAuthentication }, ++ { "pubkeyauthentication", oPubkeyAuthentication }, ++ { "dsaauthentication", oPubkeyAuthentication }, /* alias */ ++ { "rhostsrsaauthentication", oRhostsRSAAuthentication }, ++ { "hostbasedauthentication", oHostbasedAuthentication }, ++ { "challengeresponseauthentication", oChallengeResponseAuthentication }, ++ { "skeyauthentication", oChallengeResponseAuthentication }, /* alias */ ++ { "tisauthentication", oChallengeResponseAuthentication }, /* alias */ ++ { "kerberosauthentication", oUnsupported }, ++ { "kerberostgtpassing", oUnsupported }, ++ { "afstokenpassing", oUnsupported }, ++#if defined(GSSAPI) ++ { "gssapiauthentication", oGssAuthentication }, ++ { "gssapidelegatecredentials", oGssDelegateCreds }, ++#else ++ { "gssapiauthentication", oUnsupported }, ++ { "gssapidelegatecredentials", oUnsupported }, ++#endif ++ { "fallbacktorsh", oDeprecated }, ++ { "usersh", oDeprecated }, ++ { "identityfile", oIdentityFile }, ++ { "identityfile2", oIdentityFile }, /* obsolete */ ++ { "identitiesonly", oIdentitiesOnly }, ++ { "hostname", oHostName }, ++ { "hostkeyalias", oHostKeyAlias }, ++ { "proxycommand", oProxyCommand }, ++ { "port", oPort }, ++ { "cipher", oCipher }, ++ { "ciphers", oCiphers }, ++ { "macs", oMacs }, ++ { "protocol", oProtocol }, ++ { "remoteforward", oRemoteForward }, ++ { "localforward", oLocalForward }, ++ { "user", oUser }, ++ { "host", oHost }, ++ { "escapechar", oEscapeChar }, ++ { "globalknownhostsfile", oGlobalKnownHostsFile }, ++ { "globalknownhostsfile2", oGlobalKnownHostsFile2 }, /* obsolete */ ++ { "userknownhostsfile", oUserKnownHostsFile }, ++ { "userknownhostsfile2", oUserKnownHostsFile2 }, /* obsolete */ ++ { "connectionattempts", oConnectionAttempts }, ++ { "batchmode", oBatchMode }, ++ { "checkhostip", oCheckHostIP }, ++ { "stricthostkeychecking", oStrictHostKeyChecking }, ++ { "compression", oCompression }, ++ { "compressionlevel", oCompressionLevel }, ++ { "tcpkeepalive", oTCPKeepAlive }, ++ { "keepalive", oTCPKeepAlive }, /* obsolete */ ++ { "numberofpasswordprompts", oNumberOfPasswordPrompts }, ++ { "loglevel", oLogLevel }, ++ { "dynamicforward", oDynamicForward }, ++ { "preferredauthentications", oPreferredAuthentications }, ++ { "hostkeyalgorithms", oHostKeyAlgorithms }, ++ { "bindaddress", oBindAddress }, ++#ifdef SMARTCARD ++ { "smartcarddevice", oSmartcardDevice }, ++#else ++ { "smartcarddevice", oUnsupported }, ++#endif ++ { "clearallforwardings", oClearAllForwardings }, ++ { "enablesshkeysign", oEnableSSHKeysign }, ++ { "verifyhostkeydns", oVerifyHostKeyDNS }, ++ { "nohostauthenticationforlocalhost", oNoHostAuthenticationForLocalhost }, ++ { "rekeylimit", oRekeyLimit }, ++ { "connecttimeout", oConnectTimeout }, ++ { "addressfamily", oAddressFamily }, ++ { "serveraliveinterval", oServerAliveInterval }, ++ { "serveralivecountmax", oServerAliveCountMax }, ++ { "sendenv", oSendEnv }, ++ { "controlpath", oControlPath }, ++ { "controlmaster", oControlMaster }, ++ { "hashknownhosts", oHashKnownHosts }, ++ { "tunnel", oTunnel }, ++ { "tunneldevice", oTunnelDevice }, ++ { "localcommand", oLocalCommand }, ++ { "permitlocalcommand", oPermitLocalCommand }, ++ { "visualhostkey", oVisualHostKey }, ++#ifdef JPAKE ++ { "zeroknowledgepasswordauthentication", ++ oZeroKnowledgePasswordAuthentication }, ++#else ++ { "zeroknowledgepasswordauthentication", oUnsupported }, ++#endif ++ ++ { NULL, oBadOption } ++}; ++ ++/* ++ * Adds a local TCP/IP port forward to options. Never returns if there is an ++ * error. ++ */ ++ ++void ++add_local_forward(Options *options, const Forward *newfwd) ++{ ++ Forward *fwd; ++#ifndef NO_IPPORT_RESERVED_CONCEPT ++ extern uid_t original_real_uid; ++ if (newfwd->listen_port < IPPORT_RESERVED && original_real_uid != 0) ++ fatal("Privileged ports can only be forwarded by root."); ++#endif ++ if (options->num_local_forwards >= SSH_MAX_FORWARDS_PER_DIRECTION) ++ fatal("Too many local forwards (max %d).", SSH_MAX_FORWARDS_PER_DIRECTION); ++ fwd = &options->local_forwards[options->num_local_forwards++]; ++ ++ fwd->listen_host = newfwd->listen_host; ++ fwd->listen_port = newfwd->listen_port; ++ fwd->connect_host = newfwd->connect_host; ++ fwd->connect_port = newfwd->connect_port; ++} ++ ++/* ++ * Adds a remote TCP/IP port forward to options. Never returns if there is ++ * an error. ++ */ ++ ++void ++add_remote_forward(Options *options, const Forward *newfwd) ++{ ++ Forward *fwd; ++ if (options->num_remote_forwards >= SSH_MAX_FORWARDS_PER_DIRECTION) ++ fatal("Too many remote forwards (max %d).", ++ SSH_MAX_FORWARDS_PER_DIRECTION); ++ fwd = &options->remote_forwards[options->num_remote_forwards++]; ++ ++ fwd->listen_host = newfwd->listen_host; ++ fwd->listen_port = newfwd->listen_port; ++ fwd->connect_host = newfwd->connect_host; ++ fwd->connect_port = newfwd->connect_port; ++} ++ ++static void ++clear_forwardings(Options *options) ++{ ++ int i; ++ ++ for (i = 0; i < options->num_local_forwards; i++) { ++ if (options->local_forwards[i].listen_host != NULL) ++ xfree(options->local_forwards[i].listen_host); ++ xfree(options->local_forwards[i].connect_host); ++ } ++ options->num_local_forwards = 0; ++ for (i = 0; i < options->num_remote_forwards; i++) { ++ if (options->remote_forwards[i].listen_host != NULL) ++ xfree(options->remote_forwards[i].listen_host); ++ xfree(options->remote_forwards[i].connect_host); ++ } ++ options->num_remote_forwards = 0; ++ options->tun_open = SSH_TUNMODE_NO; ++} ++ ++/* ++ * Returns the number of the token pointed to by cp or oBadOption. ++ */ ++ ++static OpCodes ++parse_token(const char *cp, const char *filename, int linenum) ++{ ++ u_int i; ++ ++ for (i = 0; keywords[i].name; i++) ++ if (strcasecmp(cp, keywords[i].name) == 0) ++ return keywords[i].opcode; ++ ++ error("%s: line %d: Bad configuration option: %s", ++ filename, linenum, cp); ++ return oBadOption; ++} ++ ++/* ++ * Processes a single option line as used in the configuration files. This ++ * only sets those values that have not already been set. ++ */ ++#define WHITESPACE " \t\r\n" ++ ++int ++process_config_line(Options *options, const char *host, ++ char *line, const char *filename, int linenum, ++ int *activep) ++{ ++ char *s, **charptr, *endofnumber, *keyword, *arg, *arg2, fwdarg[256]; ++ int opcode, *intptr, value, value2, scale; ++ LogLevel *log_level_ptr; ++ long long orig, val64; ++ size_t len; ++ Forward fwd; ++ ++ /* Strip trailing whitespace */ ++ for (len = strlen(line) - 1; len > 0; len--) { ++ if (strchr(WHITESPACE, line[len]) == NULL) ++ break; ++ line[len] = '\0'; ++ } ++ ++ s = line; ++ /* Get the keyword. (Each line is supposed to begin with a keyword). */ ++ if ((keyword = strdelim(&s)) == NULL) ++ return 0; ++ /* Ignore leading whitespace. */ ++ if (*keyword == '\0') ++ keyword = strdelim(&s); ++ if (keyword == NULL || !*keyword || *keyword == '\n' || *keyword == '#') ++ return 0; ++ ++ opcode = parse_token(keyword, filename, linenum); ++ ++ switch (opcode) { ++ case oBadOption: ++ /* don't panic, but count bad options */ ++ return -1; ++ /* NOTREACHED */ ++ case oConnectTimeout: ++ intptr = &options->connection_timeout; ++parse_time: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: missing time value.", ++ filename, linenum); ++ if ((value = convtime(arg)) == -1) ++ fatal("%s line %d: invalid time value.", ++ filename, linenum); ++ if (*activep && *intptr == -1) ++ *intptr = value; ++ break; ++ ++ case oForwardAgent: ++ intptr = &options->forward_agent; ++parse_flag: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing yes/no argument.", filename, linenum); ++ value = 0; /* To avoid compiler warning... */ ++ if (strcmp(arg, "yes") == 0 || strcmp(arg, "true") == 0) ++ value = 1; ++ else if (strcmp(arg, "no") == 0 || strcmp(arg, "false") == 0) ++ value = 0; ++ else ++ fatal("%.200s line %d: Bad yes/no argument.", filename, linenum); ++ if (*activep && *intptr == -1) ++ *intptr = value; ++ break; ++ ++ case oForwardX11: ++ intptr = &options->forward_x11; ++ goto parse_flag; ++ ++ case oForwardX11Trusted: ++ intptr = &options->forward_x11_trusted; ++ goto parse_flag; ++ ++ case oGatewayPorts: ++ intptr = &options->gateway_ports; ++ goto parse_flag; ++ ++ case oExitOnForwardFailure: ++ intptr = &options->exit_on_forward_failure; ++ goto parse_flag; ++ ++ case oUsePrivilegedPort: ++ intptr = &options->use_privileged_port; ++ goto parse_flag; ++ ++ case oPasswordAuthentication: ++ intptr = &options->password_authentication; ++ goto parse_flag; ++ ++ case oZeroKnowledgePasswordAuthentication: ++ intptr = &options->zero_knowledge_password_authentication; ++ goto parse_flag; ++ ++ case oKbdInteractiveAuthentication: ++ intptr = &options->kbd_interactive_authentication; ++ goto parse_flag; ++ ++ case oKbdInteractiveDevices: ++ charptr = &options->kbd_interactive_devices; ++ goto parse_string; ++ ++ case oPubkeyAuthentication: ++ intptr = &options->pubkey_authentication; ++ goto parse_flag; ++ ++ case oRSAAuthentication: ++ intptr = &options->rsa_authentication; ++ goto parse_flag; ++ ++ case oRhostsRSAAuthentication: ++ intptr = &options->rhosts_rsa_authentication; ++ goto parse_flag; ++ ++ case oHostbasedAuthentication: ++ intptr = &options->hostbased_authentication; ++ goto parse_flag; ++ ++ case oChallengeResponseAuthentication: ++ intptr = &options->challenge_response_authentication; ++ goto parse_flag; ++ ++ case oGssAuthentication: ++ intptr = &options->gss_authentication; ++ goto parse_flag; ++ ++ case oGssDelegateCreds: ++ intptr = &options->gss_deleg_creds; ++ goto parse_flag; ++ ++ case oBatchMode: ++ intptr = &options->batch_mode; ++ goto parse_flag; ++ ++ case oCheckHostIP: ++ intptr = &options->check_host_ip; ++ goto parse_flag; ++ ++ case oVerifyHostKeyDNS: ++ intptr = &options->verify_host_key_dns; ++ goto parse_yesnoask; ++ ++ case oStrictHostKeyChecking: ++ intptr = &options->strict_host_key_checking; ++parse_yesnoask: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing yes/no/ask argument.", ++ filename, linenum); ++ value = 0; /* To avoid compiler warning... */ ++ if (strcmp(arg, "yes") == 0 || strcmp(arg, "true") == 0) ++ value = 1; ++ else if (strcmp(arg, "no") == 0 || strcmp(arg, "false") == 0) ++ value = 0; ++ else if (strcmp(arg, "ask") == 0) ++ value = 2; ++ else ++ fatal("%.200s line %d: Bad yes/no/ask argument.", filename, linenum); ++ if (*activep && *intptr == -1) ++ *intptr = value; ++ break; ++ ++ case oCompression: ++ intptr = &options->compression; ++ goto parse_flag; ++ ++ case oTCPKeepAlive: ++ intptr = &options->tcp_keep_alive; ++ goto parse_flag; ++ ++ case oNoHostAuthenticationForLocalhost: ++ intptr = &options->no_host_authentication_for_localhost; ++ goto parse_flag; ++ ++ case oNumberOfPasswordPrompts: ++ intptr = &options->number_of_password_prompts; ++ goto parse_int; ++ ++ case oCompressionLevel: ++ intptr = &options->compression_level; ++ goto parse_int; ++ ++ case oRekeyLimit: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ if (arg[0] < '0' || arg[0] > '9') ++ fatal("%.200s line %d: Bad number.", filename, linenum); ++ orig = val64 = strtoll(arg, &endofnumber, 10); ++ if (arg == endofnumber) ++ fatal("%.200s line %d: Bad number.", filename, linenum); ++ switch (toupper(*endofnumber)) { ++ case '\0': ++ scale = 1; ++ break; ++ case 'K': ++ scale = 1<<10; ++ break; ++ case 'M': ++ scale = 1<<20; ++ break; ++ case 'G': ++ scale = 1<<30; ++ break; ++ default: ++ fatal("%.200s line %d: Invalid RekeyLimit suffix", ++ filename, linenum); ++ } ++ val64 *= scale; ++ /* detect integer wrap and too-large limits */ ++ if ((val64 / scale) != orig || val64 > UINT_MAX) ++ fatal("%.200s line %d: RekeyLimit too large", ++ filename, linenum); ++ if (val64 < 16) ++ fatal("%.200s line %d: RekeyLimit too small", ++ filename, linenum); ++ if (*activep && options->rekey_limit == -1) ++ options->rekey_limit = (u_int32_t)val64; ++ break; ++ ++ case oIdentityFile: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ if (*activep) { ++ intptr = &options->num_identity_files; ++ if (*intptr >= SSH_MAX_IDENTITY_FILES) ++ fatal("%.200s line %d: Too many identity files specified (max %d).", ++ filename, linenum, SSH_MAX_IDENTITY_FILES); ++ charptr = &options->identity_files[*intptr]; ++ *charptr = xstrdup(arg); ++ *intptr = *intptr + 1; ++ } ++ break; ++ ++ case oXAuthLocation: ++ charptr=&options->xauth_location; ++ goto parse_string; ++ ++ case oUser: ++ charptr = &options->user; ++parse_string: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ if (*activep && *charptr == NULL) ++ *charptr = xstrdup(arg); ++ break; ++ ++ case oGlobalKnownHostsFile: ++ charptr = &options->system_hostfile; ++ goto parse_string; ++ ++ case oUserKnownHostsFile: ++ charptr = &options->user_hostfile; ++ goto parse_string; ++ ++ case oGlobalKnownHostsFile2: ++ charptr = &options->system_hostfile2; ++ goto parse_string; ++ ++ case oUserKnownHostsFile2: ++ charptr = &options->user_hostfile2; ++ goto parse_string; ++ ++ case oHostName: ++ charptr = &options->hostname; ++ goto parse_string; ++ ++ case oHostKeyAlias: ++ charptr = &options->host_key_alias; ++ goto parse_string; ++ ++ case oPreferredAuthentications: ++ charptr = &options->preferred_authentications; ++ goto parse_string; ++ ++ case oBindAddress: ++ charptr = &options->bind_address; ++ goto parse_string; ++ ++ case oSmartcardDevice: ++ charptr = &options->smartcard_device; ++ goto parse_string; ++ ++ case oProxyCommand: ++ charptr = &options->proxy_command; ++parse_command: ++ if (s == NULL) ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ len = strspn(s, WHITESPACE "="); ++ if (*activep && *charptr == NULL) ++ *charptr = xstrdup(s + len); ++ return 0; ++ ++ case oPort: ++ intptr = &options->port; ++parse_int: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ if (arg[0] < '0' || arg[0] > '9') ++ fatal("%.200s line %d: Bad number.", filename, linenum); ++ ++ /* Octal, decimal, or hex format? */ ++ value = strtol(arg, &endofnumber, 0); ++ if (arg == endofnumber) ++ fatal("%.200s line %d: Bad number.", filename, linenum); ++ if (*activep && *intptr == -1) ++ *intptr = value; ++ break; ++ ++ case oConnectionAttempts: ++ intptr = &options->connection_attempts; ++ goto parse_int; ++ ++ case oCipher: ++ intptr = &options->cipher; ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ value = cipher_number(arg); ++ if (value == -1) ++ fatal("%.200s line %d: Bad cipher '%s'.", ++ filename, linenum, arg ? arg : ""); ++ if (*activep && *intptr == -1) ++ *intptr = value; ++ break; ++ ++ case oCiphers: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ if (!ciphers_valid(arg)) ++ fatal("%.200s line %d: Bad SSH2 cipher spec '%s'.", ++ filename, linenum, arg ? arg : ""); ++ if (*activep && options->ciphers == NULL) ++ options->ciphers = xstrdup(arg); ++ break; ++ ++ case oMacs: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ if (!mac_valid(arg)) ++ fatal("%.200s line %d: Bad SSH2 Mac spec '%s'.", ++ filename, linenum, arg ? arg : ""); ++ if (*activep && options->macs == NULL) ++ options->macs = xstrdup(arg); ++ break; ++ ++ case oHostKeyAlgorithms: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ if (!key_names_valid2(arg)) ++ fatal("%.200s line %d: Bad protocol 2 host key algorithms '%s'.", ++ filename, linenum, arg ? arg : ""); ++ if (*activep && options->hostkeyalgorithms == NULL) ++ options->hostkeyalgorithms = xstrdup(arg); ++ break; ++ ++ case oProtocol: ++ intptr = &options->protocol; ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ value = proto_spec(arg); ++ if (value == SSH_PROTO_UNKNOWN) ++ fatal("%.200s line %d: Bad protocol spec '%s'.", ++ filename, linenum, arg ? arg : ""); ++ if (*activep && *intptr == SSH_PROTO_UNKNOWN) ++ *intptr = value; ++ break; ++ ++ case oLogLevel: ++ log_level_ptr = &options->log_level; ++ arg = strdelim(&s); ++ value = log_level_number(arg); ++ if (value == SYSLOG_LEVEL_NOT_SET) ++ fatal("%.200s line %d: unsupported log level '%s'", ++ filename, linenum, arg ? arg : ""); ++ if (*activep && *log_level_ptr == SYSLOG_LEVEL_NOT_SET) ++ *log_level_ptr = (LogLevel) value; ++ break; ++ ++ case oLocalForward: ++ case oRemoteForward: ++ case oDynamicForward: ++ arg = strdelim(&s); ++ if (arg == NULL || *arg == '\0') ++ fatal("%.200s line %d: Missing port argument.", ++ filename, linenum); ++ ++ if (opcode == oLocalForward || ++ opcode == oRemoteForward) { ++ arg2 = strdelim(&s); ++ if (arg2 == NULL || *arg2 == '\0') ++ fatal("%.200s line %d: Missing target argument.", ++ filename, linenum); ++ ++ /* construct a string for parse_forward */ ++ snprintf(fwdarg, sizeof(fwdarg), "%s:%s", arg, arg2); ++ } else if (opcode == oDynamicForward) { ++ strlcpy(fwdarg, arg, sizeof(fwdarg)); ++ } ++ ++ if (parse_forward(&fwd, fwdarg, ++ opcode == oDynamicForward ? 1 : 0, ++ opcode == oRemoteForward ? 1 : 0) == 0) ++ fatal("%.200s line %d: Bad forwarding specification.", ++ filename, linenum); ++ ++ if (*activep) { ++ if (opcode == oLocalForward || ++ opcode == oDynamicForward) ++ add_local_forward(options, &fwd); ++ else if (opcode == oRemoteForward) ++ add_remote_forward(options, &fwd); ++ } ++ break; ++ ++ case oClearAllForwardings: ++ intptr = &options->clear_forwardings; ++ goto parse_flag; ++ ++ case oHost: ++ *activep = 0; ++ while ((arg = strdelim(&s)) != NULL && *arg != '\0') ++ if (match_pattern(host, arg)) { ++ debug("Applying options for %.100s", arg); ++ *activep = 1; ++ break; ++ } ++ /* Avoid garbage check below, as strdelim is done. */ ++ return 0; ++ ++ case oEscapeChar: ++ intptr = &options->escape_char; ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ if (arg[0] == '^' && arg[2] == 0 && ++ (u_char) arg[1] >= 64 && (u_char) arg[1] < 128) ++ value = (u_char) arg[1] & 31; ++ else if (strlen(arg) == 1) ++ value = (u_char) arg[0]; ++ else if (strcmp(arg, "none") == 0) ++ value = SSH_ESCAPECHAR_NONE; ++ else { ++ fatal("%.200s line %d: Bad escape character.", ++ filename, linenum); ++ /* NOTREACHED */ ++ value = 0; /* Avoid compiler warning. */ ++ } ++ if (*activep && *intptr == -1) ++ *intptr = value; ++ break; ++ ++ case oAddressFamily: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: missing address family.", ++ filename, linenum); ++ intptr = &options->address_family; ++ if (strcasecmp(arg, "inet") == 0) ++ value = AF_INET; ++ else if (strcasecmp(arg, "inet6") == 0) ++ value = AF_INET6; ++ else if (strcasecmp(arg, "any") == 0) ++ value = AF_UNSPEC; ++ else ++ fatal("Unsupported AddressFamily \"%s\"", arg); ++ if (*activep && *intptr == -1) ++ *intptr = value; ++ break; ++ ++ case oEnableSSHKeysign: ++ intptr = &options->enable_ssh_keysign; ++ goto parse_flag; ++ ++ case oIdentitiesOnly: ++ intptr = &options->identities_only; ++ goto parse_flag; ++ ++ case oServerAliveInterval: ++ intptr = &options->server_alive_interval; ++ goto parse_time; ++ ++ case oServerAliveCountMax: ++ intptr = &options->server_alive_count_max; ++ goto parse_int; ++ ++ case oSendEnv: ++ while ((arg = strdelim(&s)) != NULL && *arg != '\0') { ++ if (strchr(arg, '=') != NULL) ++ fatal("%s line %d: Invalid environment name.", ++ filename, linenum); ++ if (!*activep) ++ continue; ++ if (options->num_send_env >= MAX_SEND_ENV) ++ fatal("%s line %d: too many send env.", ++ filename, linenum); ++ options->send_env[options->num_send_env++] = ++ xstrdup(arg); ++ } ++ break; ++ ++ case oControlPath: ++ charptr = &options->control_path; ++ goto parse_string; ++ ++ case oControlMaster: ++ intptr = &options->control_master; ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing ControlMaster argument.", ++ filename, linenum); ++ value = 0; /* To avoid compiler warning... */ ++ if (strcmp(arg, "yes") == 0 || strcmp(arg, "true") == 0) ++ value = SSHCTL_MASTER_YES; ++ else if (strcmp(arg, "no") == 0 || strcmp(arg, "false") == 0) ++ value = SSHCTL_MASTER_NO; ++ else if (strcmp(arg, "auto") == 0) ++ value = SSHCTL_MASTER_AUTO; ++ else if (strcmp(arg, "ask") == 0) ++ value = SSHCTL_MASTER_ASK; ++ else if (strcmp(arg, "autoask") == 0) ++ value = SSHCTL_MASTER_AUTO_ASK; ++ else ++ fatal("%.200s line %d: Bad ControlMaster argument.", ++ filename, linenum); ++ if (*activep && *intptr == -1) ++ *intptr = value; ++ break; ++ ++ case oHashKnownHosts: ++ intptr = &options->hash_known_hosts; ++ goto parse_flag; ++ ++ case oTunnel: ++ intptr = &options->tun_open; ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: Missing yes/point-to-point/" ++ "ethernet/no argument.", filename, linenum); ++ value = 0; /* silence compiler */ ++ if (strcasecmp(arg, "ethernet") == 0) ++ value = SSH_TUNMODE_ETHERNET; ++ else if (strcasecmp(arg, "point-to-point") == 0) ++ value = SSH_TUNMODE_POINTOPOINT; ++ else if (strcasecmp(arg, "yes") == 0) ++ value = SSH_TUNMODE_DEFAULT; ++ else if (strcasecmp(arg, "no") == 0) ++ value = SSH_TUNMODE_NO; ++ else ++ fatal("%s line %d: Bad yes/point-to-point/ethernet/" ++ "no argument: %s", filename, linenum, arg); ++ if (*activep) ++ *intptr = value; ++ break; ++ ++ case oTunnelDevice: ++ arg = strdelim(&s); ++ if (!arg || *arg == '\0') ++ fatal("%.200s line %d: Missing argument.", filename, linenum); ++ value = a2tun(arg, &value2); ++ if (value == SSH_TUNID_ERR) ++ fatal("%.200s line %d: Bad tun device.", filename, linenum); ++ if (*activep) { ++ options->tun_local = value; ++ options->tun_remote = value2; ++ } ++ break; ++ ++ case oLocalCommand: ++ charptr = &options->local_command; ++ goto parse_command; ++ ++ case oPermitLocalCommand: ++ intptr = &options->permit_local_command; ++ goto parse_flag; ++ ++ case oVisualHostKey: ++ intptr = &options->visual_host_key; ++ goto parse_flag; ++ ++ case oDeprecated: ++ debug("%s line %d: Deprecated option \"%s\"", ++ filename, linenum, keyword); ++ return 0; ++ ++ case oUnsupported: ++ error("%s line %d: Unsupported option \"%s\"", ++ filename, linenum, keyword); ++ return 0; ++ ++ default: ++ fatal("process_config_line: Unimplemented opcode %d", opcode); ++ } ++ ++ /* Check that there is no garbage at end of line. */ ++ if ((arg = strdelim(&s)) != NULL && *arg != '\0') { ++ fatal("%.200s line %d: garbage at end of line; \"%.200s\".", ++ filename, linenum, arg); ++ } ++ return 0; ++} ++ ++ ++/* ++ * Reads the config file and modifies the options accordingly. Options ++ * should already be initialized before this call. This never returns if ++ * there is an error. If the file does not exist, this returns 0. ++ */ ++ ++int ++read_config_file(const char *filename, const char *host, Options *options, ++ int checkperm) ++{ ++ FILE *f; ++ char line[1024]; ++ int active, linenum; ++ int bad_options = 0; ++ ++ if ((f = fopen(filename, "r")) == NULL) ++ return 0; ++ ++ if (checkperm) { ++ struct stat sb; ++ ++ if (fstat(fileno(f), &sb) == -1) ++ fatal("fstat %s: %s", filename, strerror(errno)); ++ if (((sb.st_uid != 0 && sb.st_uid != getuid()) || ++ (sb.st_mode & 022) != 0)) ++ fatal("Bad owner or permissions on %s", filename); ++ } ++ ++ debug("Reading configuration data %.200s", filename); ++ ++ /* ++ * Mark that we are now processing the options. This flag is turned ++ * on/off by Host specifications. ++ */ ++ active = 1; ++ linenum = 0; ++ while (fgets(line, sizeof(line), f)) { ++ /* Update line number counter. */ ++ linenum++; ++ if (process_config_line(options, host, line, filename, linenum, &active) != 0) ++ bad_options++; ++ } ++ fclose(f); ++ if (bad_options > 0) ++ fatal("%s: terminating, %d bad configuration options", ++ filename, bad_options); ++ return 1; ++} ++ ++/* ++ * Initializes options to special values that indicate that they have not yet ++ * been set. Read_config_file will only set options with this value. Options ++ * are processed in the following order: command line, user config file, ++ * system config file. Last, fill_default_options is called. ++ */ ++ ++void ++initialize_options(Options * options) ++{ ++ memset(options, 'X', sizeof(*options)); ++ options->forward_agent = -1; ++ options->forward_x11 = -1; ++ options->forward_x11_trusted = -1; ++ options->exit_on_forward_failure = -1; ++ options->xauth_location = NULL; ++ options->gateway_ports = -1; ++ options->use_privileged_port = -1; ++ options->rsa_authentication = -1; ++ options->pubkey_authentication = -1; ++ options->challenge_response_authentication = -1; ++ options->gss_authentication = -1; ++ options->gss_deleg_creds = -1; ++ options->password_authentication = -1; ++ options->kbd_interactive_authentication = -1; ++ options->kbd_interactive_devices = NULL; ++ options->rhosts_rsa_authentication = -1; ++ options->hostbased_authentication = -1; ++ options->batch_mode = -1; ++ options->check_host_ip = -1; ++ options->strict_host_key_checking = -1; ++ options->compression = -1; ++ options->tcp_keep_alive = -1; ++ options->compression_level = -1; ++ options->port = -1; ++ options->address_family = -1; ++ options->connection_attempts = -1; ++ options->connection_timeout = -1; ++ options->number_of_password_prompts = -1; ++ options->cipher = -1; ++ options->ciphers = NULL; ++ options->macs = NULL; ++ options->hostkeyalgorithms = NULL; ++ options->protocol = SSH_PROTO_UNKNOWN; ++ options->num_identity_files = 0; ++ options->hostname = NULL; ++ options->host_key_alias = NULL; ++ options->proxy_command = NULL; ++ options->user = NULL; ++ options->escape_char = -1; ++ options->system_hostfile = NULL; ++ options->user_hostfile = NULL; ++ options->system_hostfile2 = NULL; ++ options->user_hostfile2 = NULL; ++ options->num_local_forwards = 0; ++ options->num_remote_forwards = 0; ++ options->clear_forwardings = -1; ++ options->log_level = SYSLOG_LEVEL_NOT_SET; ++ options->preferred_authentications = NULL; ++ options->bind_address = NULL; ++ options->smartcard_device = NULL; ++ options->enable_ssh_keysign = - 1; ++ options->no_host_authentication_for_localhost = - 1; ++ options->identities_only = - 1; ++ options->rekey_limit = - 1; ++ options->verify_host_key_dns = -1; ++ options->server_alive_interval = -1; ++ options->server_alive_count_max = -1; ++ options->num_send_env = 0; ++ options->control_path = NULL; ++ options->control_master = -1; ++ options->hash_known_hosts = -1; ++ options->tun_open = -1; ++ options->tun_local = -1; ++ options->tun_remote = -1; ++ options->local_command = NULL; ++ options->permit_local_command = -1; ++ options->visual_host_key = -1; ++ options->zero_knowledge_password_authentication = -1; ++} ++ ++/* ++ * Called after processing other sources of option data, this fills those ++ * options for which no value has been specified with their default values. ++ */ ++ ++void ++fill_default_options(Options * options) ++{ ++ int len; ++ ++ if (options->forward_agent == -1) ++ options->forward_agent = 0; ++ if (options->forward_x11 == -1) ++ options->forward_x11 = 0; ++ if (options->forward_x11_trusted == -1) ++ options->forward_x11_trusted = 0; ++ if (options->exit_on_forward_failure == -1) ++ options->exit_on_forward_failure = 0; ++ if (options->xauth_location == NULL) ++ options->xauth_location = _PATH_XAUTH; ++ if (options->gateway_ports == -1) ++ options->gateway_ports = 0; ++ if (options->use_privileged_port == -1) ++ options->use_privileged_port = 0; ++ if (options->rsa_authentication == -1) ++ options->rsa_authentication = 1; ++ if (options->pubkey_authentication == -1) ++ options->pubkey_authentication = 1; ++ if (options->challenge_response_authentication == -1) ++ options->challenge_response_authentication = 1; ++ if (options->gss_authentication == -1) ++ options->gss_authentication = 0; ++ if (options->gss_deleg_creds == -1) ++ options->gss_deleg_creds = 0; ++ if (options->password_authentication == -1) ++ options->password_authentication = 1; ++ if (options->kbd_interactive_authentication == -1) ++ options->kbd_interactive_authentication = 1; ++ if (options->rhosts_rsa_authentication == -1) ++ options->rhosts_rsa_authentication = 0; ++ if (options->hostbased_authentication == -1) ++ options->hostbased_authentication = 0; ++ if (options->batch_mode == -1) ++ options->batch_mode = 0; ++ if (options->check_host_ip == -1) ++ options->check_host_ip = 1; ++ if (options->strict_host_key_checking == -1) ++ options->strict_host_key_checking = 2; /* 2 is default */ ++ if (options->compression == -1) ++ options->compression = 0; ++ if (options->tcp_keep_alive == -1) ++ options->tcp_keep_alive = 1; ++ if (options->compression_level == -1) ++ options->compression_level = 6; ++ if (options->port == -1) ++ options->port = 0; /* Filled in ssh_connect. */ ++ if (options->address_family == -1) ++ options->address_family = AF_UNSPEC; ++ if (options->connection_attempts == -1) ++ options->connection_attempts = 1; ++ if (options->number_of_password_prompts == -1) ++ options->number_of_password_prompts = 3; ++ /* Selected in ssh_login(). */ ++ if (options->cipher == -1) ++ options->cipher = SSH_CIPHER_NOT_SET; ++ /* options->ciphers, default set in myproposals.h */ ++ /* options->macs, default set in myproposals.h */ ++ /* options->hostkeyalgorithms, default set in myproposals.h */ ++ if (options->protocol == SSH_PROTO_UNKNOWN) ++ options->protocol = SSH_PROTO_1|SSH_PROTO_2; ++ if (options->num_identity_files == 0) { ++ if (options->protocol & SSH_PROTO_1) { ++ len = 2 + strlen(_PATH_SSH_CLIENT_IDENTITY) + 1; ++ options->identity_files[options->num_identity_files] = ++ xmalloc(len); ++ snprintf(options->identity_files[options->num_identity_files++], ++ len, "~/%.100s", _PATH_SSH_CLIENT_IDENTITY); ++ } ++ if (options->protocol & SSH_PROTO_2) { ++ len = 2 + strlen(_PATH_SSH_CLIENT_ID_RSA) + 1; ++ options->identity_files[options->num_identity_files] = ++ xmalloc(len); ++ snprintf(options->identity_files[options->num_identity_files++], ++ len, "~/%.100s", _PATH_SSH_CLIENT_ID_RSA); ++ ++ len = 2 + strlen(_PATH_SSH_CLIENT_ID_DSA) + 1; ++ options->identity_files[options->num_identity_files] = ++ xmalloc(len); ++ snprintf(options->identity_files[options->num_identity_files++], ++ len, "~/%.100s", _PATH_SSH_CLIENT_ID_DSA); ++ } ++ } ++ if (options->escape_char == -1) ++ options->escape_char = '~'; ++ if (options->system_hostfile == NULL) ++ options->system_hostfile = _PATH_SSH_SYSTEM_HOSTFILE; ++ if (options->user_hostfile == NULL) ++ options->user_hostfile = _PATH_SSH_USER_HOSTFILE; ++ if (options->system_hostfile2 == NULL) ++ options->system_hostfile2 = _PATH_SSH_SYSTEM_HOSTFILE2; ++ if (options->user_hostfile2 == NULL) ++ options->user_hostfile2 = _PATH_SSH_USER_HOSTFILE2; ++ if (options->log_level == SYSLOG_LEVEL_NOT_SET) ++ options->log_level = SYSLOG_LEVEL_INFO; ++ if (options->clear_forwardings == 1) ++ clear_forwardings(options); ++ if (options->no_host_authentication_for_localhost == - 1) ++ options->no_host_authentication_for_localhost = 0; ++ if (options->identities_only == -1) ++ options->identities_only = 0; ++ if (options->enable_ssh_keysign == -1) ++ options->enable_ssh_keysign = 0; ++ if (options->rekey_limit == -1) ++ options->rekey_limit = 0; ++ if (options->verify_host_key_dns == -1) ++ options->verify_host_key_dns = 0; ++ if (options->server_alive_interval == -1) ++ options->server_alive_interval = 0; ++ if (options->server_alive_count_max == -1) ++ options->server_alive_count_max = 3; ++ if (options->control_master == -1) ++ options->control_master = 0; ++ if (options->hash_known_hosts == -1) ++ options->hash_known_hosts = 0; ++ if (options->tun_open == -1) ++ options->tun_open = SSH_TUNMODE_NO; ++ if (options->tun_local == -1) ++ options->tun_local = SSH_TUNID_ANY; ++ if (options->tun_remote == -1) ++ options->tun_remote = SSH_TUNID_ANY; ++ if (options->permit_local_command == -1) ++ options->permit_local_command = 0; ++ if (options->visual_host_key == -1) ++ options->visual_host_key = 0; ++ if (options->zero_knowledge_password_authentication == -1) ++ options->zero_knowledge_password_authentication = 0; ++ /* options->local_command should not be set by default */ ++ /* options->proxy_command should not be set by default */ ++ /* options->user will be set in the main program if appropriate */ ++ /* options->hostname will be set in the main program if appropriate */ ++ /* options->host_key_alias should not be set by default */ ++ /* options->preferred_authentications will be set in ssh */ ++} ++ ++/* ++ * parse_forward ++ * parses a string containing a port forwarding specification of the form: ++ * dynamicfwd == 0 ++ * [listenhost:]listenport:connecthost:connectport ++ * dynamicfwd == 1 ++ * [listenhost:]listenport ++ * returns number of arguments parsed or zero on error ++ */ ++int ++parse_forward(Forward *fwd, const char *fwdspec, int dynamicfwd, int remotefwd) ++{ ++ int i; ++ char *p, *cp, *fwdarg[4]; ++ ++ memset(fwd, '\0', sizeof(*fwd)); ++ ++ cp = p = xstrdup(fwdspec); ++ ++ /* skip leading spaces */ ++ while (isspace(*cp)) ++ cp++; ++ ++ for (i = 0; i < 4; ++i) ++ if ((fwdarg[i] = hpdelim(&cp)) == NULL) ++ break; ++ ++ /* Check for trailing garbage */ ++ if (cp != NULL) ++ i = 0; /* failure */ ++ ++ switch (i) { ++ case 1: ++ fwd->listen_host = NULL; ++ fwd->listen_port = a2port(fwdarg[0]); ++ fwd->connect_host = xstrdup("socks"); ++ break; ++ ++ case 2: ++ fwd->listen_host = xstrdup(cleanhostname(fwdarg[0])); ++ fwd->listen_port = a2port(fwdarg[1]); ++ fwd->connect_host = xstrdup("socks"); ++ break; ++ ++ case 3: ++ fwd->listen_host = NULL; ++ fwd->listen_port = a2port(fwdarg[0]); ++ fwd->connect_host = xstrdup(cleanhostname(fwdarg[1])); ++ fwd->connect_port = a2port(fwdarg[2]); ++ break; ++ ++ case 4: ++ fwd->listen_host = xstrdup(cleanhostname(fwdarg[0])); ++ fwd->listen_port = a2port(fwdarg[1]); ++ fwd->connect_host = xstrdup(cleanhostname(fwdarg[2])); ++ fwd->connect_port = a2port(fwdarg[3]); ++ break; ++ default: ++ i = 0; /* failure */ ++ } ++ ++ xfree(p); ++ ++ if (dynamicfwd) { ++ if (!(i == 1 || i == 2)) ++ goto fail_free; ++ } else { ++ if (!(i == 3 || i == 4)) ++ goto fail_free; ++ if (fwd->connect_port <= 0) ++ goto fail_free; ++ } ++ ++ if (fwd->listen_port < 0 || (!remotefwd && fwd->listen_port == 0)) ++ goto fail_free; ++ ++ if (fwd->connect_host != NULL && ++ strlen(fwd->connect_host) >= NI_MAXHOST) ++ goto fail_free; ++ if (fwd->listen_host != NULL && ++ strlen(fwd->listen_host) >= NI_MAXHOST) ++ goto fail_free; ++ ++ ++ return (i); ++ ++ fail_free: ++ if (fwd->connect_host != NULL) { ++ xfree(fwd->connect_host); ++ fwd->connect_host = NULL; ++ } ++ if (fwd->listen_host != NULL) { ++ xfree(fwd->listen_host); ++ fwd->listen_host = NULL; ++ } ++ return (0); ++} +diff -NupwB openssh-5.2p1-canonical/readconf.h openssh-5.2p1-hpn13v6/readconf.h +--- openssh-5.2p1-canonical/readconf.h 2009-02-14 00:28:21.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/readconf.h 2009-05-14 12:36:10.000000000 -0400 +@@ -57,6 +57,11 @@ typedef struct { + int compression_level; /* Compression level 1 (fast) to 9 + * (best). */ + int tcp_keep_alive; /* Set SO_KEEPALIVE. */ ++ int tcp_rcv_buf; /* user switch to set tcp recv buffer */ ++ int tcp_rcv_buf_poll; /* Option to poll recv buf every window transfer */ ++ int hpn_disabled; /* Switch to disable HPN buffer management */ ++ int hpn_buffer_size; /* User definable size for HPN buffer window */ ++ + LogLevel log_level; /* Level for logging. */ + + int port; /* Port to connect. */ +@@ -102,6 +107,8 @@ typedef struct { + + int enable_ssh_keysign; + int64_t rekey_limit; ++ int none_switch; /* Use none cipher */ ++ int none_enabled; /* Allow none to be used */ + int no_host_authentication_for_localhost; + int identities_only; + int server_alive_interval; +diff -NupwB openssh-5.2p1-canonical/readconf.h.orig openssh-5.2p1-hpn13v6/readconf.h.orig +--- openssh-5.2p1-canonical/readconf.h.orig 1969-12-31 19:00:00.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/readconf.h.orig 2009-02-14 00:28:21.000000000 -0500 +@@ -0,0 +1,145 @@ ++/* $OpenBSD: readconf.h,v 1.78 2009/02/12 03:00:56 djm Exp $ */ ++ ++/* ++ * Author: Tatu Ylonen ++ * Copyright (c) 1995 Tatu Ylonen , Espoo, Finland ++ * All rights reserved ++ * Functions for reading the configuration file. ++ * ++ * As far as I am concerned, the code I have written for this software ++ * can be used freely for any purpose. Any derived versions of this ++ * software must be clearly marked as such, and if the derived work is ++ * incompatible with the protocol description in the RFC file, it must be ++ * called by a name other than "ssh" or "Secure Shell". ++ */ ++ ++#ifndef READCONF_H ++#define READCONF_H ++ ++/* Data structure for representing a forwarding request. */ ++ ++typedef struct { ++ char *listen_host; /* Host (address) to listen on. */ ++ int listen_port; /* Port to forward. */ ++ char *connect_host; /* Host to connect. */ ++ int connect_port; /* Port to connect on connect_host. */ ++} Forward; ++/* Data structure for representing option data. */ ++ ++#define MAX_SEND_ENV 256 ++ ++typedef struct { ++ int forward_agent; /* Forward authentication agent. */ ++ int forward_x11; /* Forward X11 display. */ ++ int forward_x11_trusted; /* Trust Forward X11 display. */ ++ int exit_on_forward_failure; /* Exit if bind(2) fails for -L/-R */ ++ char *xauth_location; /* Location for xauth program */ ++ int gateway_ports; /* Allow remote connects to forwarded ports. */ ++ int use_privileged_port; /* Don't use privileged port if false. */ ++ int rhosts_rsa_authentication; /* Try rhosts with RSA ++ * authentication. */ ++ int rsa_authentication; /* Try RSA authentication. */ ++ int pubkey_authentication; /* Try ssh2 pubkey authentication. */ ++ int hostbased_authentication; /* ssh2's rhosts_rsa */ ++ int challenge_response_authentication; ++ /* Try S/Key or TIS, authentication. */ ++ int gss_authentication; /* Try GSS authentication */ ++ int gss_deleg_creds; /* Delegate GSS credentials */ ++ int password_authentication; /* Try password ++ * authentication. */ ++ int kbd_interactive_authentication; /* Try keyboard-interactive auth. */ ++ char *kbd_interactive_devices; /* Keyboard-interactive auth devices. */ ++ int zero_knowledge_password_authentication; /* Try jpake */ ++ int batch_mode; /* Batch mode: do not ask for passwords. */ ++ int check_host_ip; /* Also keep track of keys for IP address */ ++ int strict_host_key_checking; /* Strict host key checking. */ ++ int compression; /* Compress packets in both directions. */ ++ int compression_level; /* Compression level 1 (fast) to 9 ++ * (best). */ ++ int tcp_keep_alive; /* Set SO_KEEPALIVE. */ ++ LogLevel log_level; /* Level for logging. */ ++ ++ int port; /* Port to connect. */ ++ int address_family; ++ int connection_attempts; /* Max attempts (seconds) before ++ * giving up */ ++ int connection_timeout; /* Max time (seconds) before ++ * aborting connection attempt */ ++ int number_of_password_prompts; /* Max number of password ++ * prompts. */ ++ int cipher; /* Cipher to use. */ ++ char *ciphers; /* SSH2 ciphers in order of preference. */ ++ char *macs; /* SSH2 macs in order of preference. */ ++ char *hostkeyalgorithms; /* SSH2 server key types in order of preference. */ ++ int protocol; /* Protocol in order of preference. */ ++ char *hostname; /* Real host to connect. */ ++ char *host_key_alias; /* hostname alias for .ssh/known_hosts */ ++ char *proxy_command; /* Proxy command for connecting the host. */ ++ char *user; /* User to log in as. */ ++ int escape_char; /* Escape character; -2 = none */ ++ ++ char *system_hostfile;/* Path for /etc/ssh/ssh_known_hosts. */ ++ char *user_hostfile; /* Path for $HOME/.ssh/known_hosts. */ ++ char *system_hostfile2; ++ char *user_hostfile2; ++ char *preferred_authentications; ++ char *bind_address; /* local socket address for connection to sshd */ ++ char *smartcard_device; /* Smartcard reader device */ ++ int verify_host_key_dns; /* Verify host key using DNS */ ++ ++ int num_identity_files; /* Number of files for RSA/DSA identities. */ ++ char *identity_files[SSH_MAX_IDENTITY_FILES]; ++ Key *identity_keys[SSH_MAX_IDENTITY_FILES]; ++ ++ /* Local TCP/IP forward requests. */ ++ int num_local_forwards; ++ Forward local_forwards[SSH_MAX_FORWARDS_PER_DIRECTION]; ++ ++ /* Remote TCP/IP forward requests. */ ++ int num_remote_forwards; ++ Forward remote_forwards[SSH_MAX_FORWARDS_PER_DIRECTION]; ++ int clear_forwardings; ++ ++ int enable_ssh_keysign; ++ int64_t rekey_limit; ++ int no_host_authentication_for_localhost; ++ int identities_only; ++ int server_alive_interval; ++ int server_alive_count_max; ++ ++ int num_send_env; ++ char *send_env[MAX_SEND_ENV]; ++ ++ char *control_path; ++ int control_master; ++ ++ int hash_known_hosts; ++ ++ int tun_open; /* tun(4) */ ++ int tun_local; /* force tun device (optional) */ ++ int tun_remote; /* force tun device (optional) */ ++ ++ char *local_command; ++ int permit_local_command; ++ int visual_host_key; ++ ++} Options; ++ ++#define SSHCTL_MASTER_NO 0 ++#define SSHCTL_MASTER_YES 1 ++#define SSHCTL_MASTER_AUTO 2 ++#define SSHCTL_MASTER_ASK 3 ++#define SSHCTL_MASTER_AUTO_ASK 4 ++ ++void initialize_options(Options *); ++void fill_default_options(Options *); ++int read_config_file(const char *, const char *, Options *, int); ++int parse_forward(Forward *, const char *, int, int); ++ ++int ++process_config_line(Options *, const char *, char *, const char *, int, int *); ++ ++void add_local_forward(Options *, const Forward *); ++void add_remote_forward(Options *, const Forward *); ++ ++#endif /* READCONF_H */ +Common subdirectories: openssh-5.2p1-canonical/regress and openssh-5.2p1-hpn13v6/regress +Common subdirectories: openssh-5.2p1-canonical/scard and openssh-5.2p1-hpn13v6/scard +diff -NupwB openssh-5.2p1-canonical/scp.c openssh-5.2p1-hpn13v6/scp.c +--- openssh-5.2p1-canonical/scp.c 2008-11-03 03:23:45.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/scp.c 2009-05-14 12:36:10.000000000 -0400 +@@ -632,7 +632,7 @@ source(int argc, char **argv) + off_t i, statbytes; + size_t amt; + int fd = -1, haderr, indx; +- char *last, *name, buf[2048], encname[MAXPATHLEN]; ++ char *last, *name, buf[16384], encname[MAXPATHLEN]; + int len; + + for (indx = 0; indx < argc; ++indx) { +@@ -868,7 +868,7 @@ sink(int argc, char **argv) + mode_t mode, omode, mask; + off_t size, statbytes; + int setimes, targisdir, wrerrno = 0; +- char ch, *cp, *np, *targ, *why, *vect[1], buf[2048]; ++ char ch, *cp, *np, *targ, *why, *vect[1], buf[16384]; + struct timeval tv[2]; + + #define atime tv[0] +diff -NupwB openssh-5.2p1-canonical/servconf.c openssh-5.2p1-hpn13v6/servconf.c +--- openssh-5.2p1-canonical/servconf.c 2009-01-28 00:31:23.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/servconf.c 2009-05-14 12:36:10.000000000 -0400 +@@ -128,11 +128,20 @@ initialize_server_options(ServerOptions + options->adm_forced_command = NULL; + options->chroot_directory = NULL; + options->zero_knowledge_password_authentication = -1; ++ options->none_enabled = -1; ++ options->tcp_rcv_buf_poll = -1; ++ options->hpn_disabled = -1; ++ options->hpn_buffer_size = -1; + } + + void + fill_default_server_options(ServerOptions *options) + { ++ /* needed for hpn socket tests */ ++ int sock; ++ int socksize; ++ int socksizelen = sizeof(int); ++ + /* Portable-specific options */ + if (options->use_pam == -1) + options->use_pam = 0; +@@ -262,6 +271,42 @@ fill_default_server_options(ServerOption + if (options->zero_knowledge_password_authentication == -1) + options->zero_knowledge_password_authentication = 0; + ++ if (options->hpn_disabled == -1) ++ options->hpn_disabled = 0; ++ ++ if (options->hpn_buffer_size == -1) { ++ /* option not explicitly set. Now we have to figure out */ ++ /* what value to use */ ++ if (options->hpn_disabled == 1) { ++ options->hpn_buffer_size = CHAN_SES_WINDOW_DEFAULT; ++ } else { ++ /* get the current RCV size and set it to that */ ++ /*create a socket but don't connect it */ ++ /* we use that the get the rcv socket size */ ++ sock = socket(AF_INET, SOCK_STREAM, 0); ++ getsockopt(sock, SOL_SOCKET, SO_RCVBUF, ++ &socksize, &socksizelen); ++ close(sock); ++ options->hpn_buffer_size = socksize; ++ debug ("HPN Buffer Size: %d", options->hpn_buffer_size); ++ ++ } ++ } else { ++ /* we have to do this incase the user sets both values in a contradictory */ ++ /* manner. hpn_disabled overrrides hpn_buffer_size*/ ++ if (options->hpn_disabled <= 0) { ++ if (options->hpn_buffer_size == 0) ++ options->hpn_buffer_size = 1; ++ /* limit the maximum buffer to 64MB */ ++ if (options->hpn_buffer_size > 64*1024) { ++ options->hpn_buffer_size = 64*1024*1024; ++ } else { ++ options->hpn_buffer_size *= 1024; ++ } ++ } else ++ options->hpn_buffer_size = CHAN_TCP_WINDOW_DEFAULT; ++ } ++ + /* Turn privilege separation on by default */ + if (use_privsep == -1) + use_privsep = 1; +@@ -306,6 +351,7 @@ typedef enum { + sMatch, sPermitOpen, sForceCommand, sChrootDirectory, + sUsePrivilegeSeparation, sAllowAgentForwarding, + sZeroKnowledgePasswordAuthentication, ++ sNoneEnabled, sTcpRcvBufPoll, sHPNDisabled, sHPNBufferSize, + sDeprecated, sUnsupported + } ServerOpCodes; + +@@ -424,6 +470,10 @@ static struct { + { "permitopen", sPermitOpen, SSHCFG_ALL }, + { "forcecommand", sForceCommand, SSHCFG_ALL }, + { "chrootdirectory", sChrootDirectory, SSHCFG_ALL }, ++ { "noneenabled", sNoneEnabled }, ++ { "hpndisabled", sHPNDisabled }, ++ { "hpnbuffersize", sHPNBufferSize }, ++ { "tcprcvbufpoll", sTcpRcvBufPoll }, + { NULL, sBadOption, 0 } + }; + +@@ -450,6 +500,7 @@ parse_token(const char *cp, const char * + + for (i = 0; keywords[i].name; i++) + if (strcasecmp(cp, keywords[i].name) == 0) { ++ debug ("Config token is %s", keywords[i].name); + *flags = keywords[i].flags; + return keywords[i].opcode; + } +@@ -847,6 +898,22 @@ process_server_config_line(ServerOptions + *intptr = value; + break; + ++ case sNoneEnabled: ++ intptr = &options->none_enabled; ++ goto parse_flag; ++ ++ case sTcpRcvBufPoll: ++ intptr = &options->tcp_rcv_buf_poll; ++ goto parse_flag; ++ ++ case sHPNDisabled: ++ intptr = &options->hpn_disabled; ++ goto parse_flag; ++ ++ case sHPNBufferSize: ++ intptr = &options->hpn_buffer_size; ++ goto parse_int; ++ + case sIgnoreUserKnownHosts: + intptr = &options->ignore_user_known_hosts; + goto parse_flag; +diff -NupwB openssh-5.2p1-canonical/servconf.h openssh-5.2p1-hpn13v6/servconf.h +--- openssh-5.2p1-canonical/servconf.h 2009-01-28 00:31:23.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/servconf.h 2009-05-14 12:36:10.000000000 -0400 +@@ -145,6 +145,10 @@ typedef struct { + char *adm_forced_command; + + int use_pam; /* Enable auth via PAM */ ++ int none_enabled; /* enable NONE cipher switch */ ++ int tcp_rcv_buf_poll; /* poll tcp rcv window in autotuning kernels*/ ++ int hpn_disabled; /* disable hpn functionality. false by default */ ++ int hpn_buffer_size; /* set the hpn buffer size - default 3MB */ + + int permit_tun; + +diff -NupwB openssh-5.2p1-canonical/serverloop.c openssh-5.2p1-hpn13v6/serverloop.c +--- openssh-5.2p1-canonical/serverloop.c 2009-02-14 00:33:09.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/serverloop.c 2009-05-14 12:36:10.000000000 -0400 +@@ -93,10 +93,10 @@ static int fdin; /* Descriptor for stdi + static int fdout; /* Descriptor for stdout (for reading); + May be same number as fdin. */ + static int fderr; /* Descriptor for stderr. May be -1. */ +-static long stdin_bytes = 0; /* Number of bytes written to stdin. */ +-static long stdout_bytes = 0; /* Number of stdout bytes sent to client. */ +-static long stderr_bytes = 0; /* Number of stderr bytes sent to client. */ +-static long fdout_bytes = 0; /* Number of stdout bytes read from program. */ ++static u_long stdin_bytes = 0; /* Number of bytes written to stdin. */ ++static u_long stdout_bytes = 0; /* Number of stdout bytes sent to client. */ ++static u_long stderr_bytes = 0; /* Number of stderr bytes sent to client. */ ++static u_long fdout_bytes = 0; /* Number of stdout bytes read from program. */ + static int stdin_eof = 0; /* EOF message received from client. */ + static int fdout_eof = 0; /* EOF encountered reading from fdout. */ + static int fderr_eof = 0; /* EOF encountered readung from fderr. */ +@@ -121,6 +121,20 @@ static volatile sig_atomic_t received_si + static void server_init_dispatch(void); + + /* ++ * Returns current time in seconds from Jan 1, 1970 with the maximum ++ * available resolution. ++ */ ++ ++static double ++get_current_time(void) ++{ ++ struct timeval tv; ++ gettimeofday(&tv, NULL); ++ return (double) tv.tv_sec + (double) tv.tv_usec / 1000000.0; ++} ++ ++ ++/* + * we write to this pipe if a SIGCHLD is caught in order to avoid + * the race between select() and child_terminated + */ +@@ -410,6 +424,7 @@ process_input(fd_set *readset) + } else { + /* Buffer any received data. */ + packet_process_incoming(buf, len); ++ fdout_bytes += len; + } + } + if (compat20) +@@ -432,6 +447,7 @@ process_input(fd_set *readset) + } else { + buffer_append(&stdout_buffer, buf, len); + fdout_bytes += len; ++ debug ("FD out now: %ld", fdout_bytes); + } + } + /* Read and buffer any available stderr data from the program. */ +@@ -499,7 +515,7 @@ process_output(fd_set *writeset) + } + /* Send any buffered packet data to the client. */ + if (FD_ISSET(connection_out, writeset)) +- packet_write_poll(); ++ stdin_bytes += packet_write_poll(); + } + + /* +@@ -816,8 +832,10 @@ server_loop2(Authctxt *authctxt) + { + fd_set *readset = NULL, *writeset = NULL; + int rekeying = 0, max_fd, nalloc = 0; ++ double start_time, total_time; + + debug("Entering interactive session for SSH2."); ++ start_time = get_current_time(); + + mysignal(SIGCHLD, sigchld_handler); + child_terminated = 0; +@@ -879,6 +897,11 @@ server_loop2(Authctxt *authctxt) + + /* free remaining sessions, e.g. remove wtmp entries */ + session_destroy_all(NULL); ++ total_time = get_current_time() - start_time; ++ logit("SSH: Server;LType: Throughput;Remote: %s-%d;IN: %lu;OUT: %lu;Duration: %.1f;tPut_in: %.1f;tPut_out: %.1f", ++ get_remote_ipaddr(), get_remote_port(), ++ stdin_bytes, fdout_bytes, total_time, stdin_bytes / total_time, ++ fdout_bytes / total_time); + } + + static void +@@ -994,8 +1017,12 @@ server_request_tun(void) + sock = tun_open(tun, mode); + if (sock < 0) + goto done; ++ if (options.hpn_disabled) + c = channel_new("tun", SSH_CHANNEL_OPEN, sock, sock, -1, + CHAN_TCP_WINDOW_DEFAULT, CHAN_TCP_PACKET_DEFAULT, 0, "tun", 1); ++ else ++ c = channel_new("tun", SSH_CHANNEL_OPEN, sock, sock, -1, ++ options.hpn_buffer_size, CHAN_TCP_PACKET_DEFAULT, 0, "tun", 1); + c->datagram = 1; + #if defined(SSH_TUN_FILTER) + if (mode == SSH_TUNMODE_POINTOPOINT) +@@ -1031,6 +1058,8 @@ server_request_session(void) + c = channel_new("session", SSH_CHANNEL_LARVAL, + -1, -1, -1, /*window size*/0, CHAN_SES_PACKET_DEFAULT, + 0, "server-session", 1); ++ if ((options.tcp_rcv_buf_poll) && (!options.hpn_disabled)) ++ c->dynamic_window = 1; + if (session_open(the_authctxt, c->self) != 1) { + debug("session open failed, free channel %d", c->self); + channel_free(c); +diff -NupwB openssh-5.2p1-canonical/session.c openssh-5.2p1-hpn13v6/session.c +--- openssh-5.2p1-canonical/session.c 2009-01-28 00:29:49.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/session.c 2009-05-14 12:36:10.000000000 -0400 +@@ -230,6 +230,7 @@ auth_input_request_forwarding(struct pas + } + + /* Allocate a channel for the authentication agent socket. */ ++ /* this shouldn't matter if its hpn or not - cjr */ + nc = channel_new("auth socket", + SSH_CHANNEL_AUTH_SOCKET, sock, sock, -1, + CHAN_X11_WINDOW_DEFAULT, CHAN_X11_PACKET_DEFAULT, +@@ -2301,10 +2302,16 @@ session_set_fds(Session *s, int fdin, in + */ + if (s->chanid == -1) + fatal("no channel for session %d", s->self); ++ if (options.hpn_disabled) + channel_set_fds(s->chanid, + fdout, fdin, fderr, + fderr == -1 ? CHAN_EXTENDED_IGNORE : CHAN_EXTENDED_READ, + 1, is_tty, CHAN_SES_WINDOW_DEFAULT); ++ else ++ channel_set_fds(s->chanid, ++ fdout, fdin, fderr, ++ fderr == -1 ? CHAN_EXTENDED_IGNORE : CHAN_EXTENDED_READ, ++ 1, is_tty, options.hpn_buffer_size); + } + + /* +diff -NupwB openssh-5.2p1-canonical/sftp.1 openssh-5.2p1-hpn13v6/sftp.1 +--- openssh-5.2p1-canonical/sftp.1 2009-01-28 00:14:09.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/sftp.1 2009-05-14 12:36:10.000000000 -0400 +@@ -203,7 +203,8 @@ This option may be useful in debugging t + Specify how many requests may be outstanding at any one time. + Increasing this may slightly improve file transfer speed + but will increase memory usage. +-The default is 64 outstanding requests. ++The default is 256 outstanding requests providing for 8MB ++of outstanding data with a 32KB buffer. + .It Fl S Ar program + Name of the + .Ar program +diff -NupwB openssh-5.2p1-canonical/sftp.c openssh-5.2p1-hpn13v6/sftp.c +--- openssh-5.2p1-canonical/sftp.c 2009-02-14 00:26:19.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/sftp.c 2009-05-14 12:36:10.000000000 -0400 +@@ -75,7 +75,7 @@ int batchmode = 0; + size_t copy_buffer_len = 32768; + + /* Number of concurrent outstanding requests */ +-size_t num_requests = 64; ++size_t num_requests = 256; + + /* PID of ssh transport process */ + static pid_t sshpid = -1; +diff -NupwB openssh-5.2p1-canonical/ssh.c openssh-5.2p1-hpn13v6/ssh.c +--- openssh-5.2p1-canonical/ssh.c 2009-02-14 00:28:21.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/ssh.c 2009-05-14 12:36:10.000000000 -0400 +@@ -492,9 +492,6 @@ main(int ac, char **av) + no_shell_flag = 1; + no_tty_flag = 1; + break; +- case 'T': +- no_tty_flag = 1; +- break; + case 'o': + dummy = 1; + line = xstrdup(optarg); +@@ -503,6 +500,13 @@ main(int ac, char **av) + exit(255); + xfree(line); + break; ++ case 'T': ++ no_tty_flag = 1; ++ /* ensure that the user doesn't try to backdoor a */ ++ /* null cipher switch on an interactive session */ ++ /* so explicitly disable it no matter what */ ++ options.none_switch=0; ++ break; + case 's': + subsystem_flag = 1; + break; +@@ -1142,6 +1146,9 @@ ssh_session2_open(void) + { + Channel *c; + int window, packetmax, in, out, err; ++ int sock; ++ int socksize; ++ int socksizelen = sizeof(int); + + if (stdin_null_flag) { + in = open(_PATH_DEVNULL, O_RDONLY); +@@ -1162,9 +1169,75 @@ ssh_session2_open(void) + if (!isatty(err)) + set_nonblock(err); + +- window = CHAN_SES_WINDOW_DEFAULT; ++ /* we need to check to see if what they want to do about buffer */ ++ /* sizes here. In a hpn to nonhpn connection we want to limit */ ++ /* the window size to something reasonable in case the far side */ ++ /* has the large window bug. In hpn to hpn connection we want to */ ++ /* use the max window size but allow the user to override it */ ++ /* lastly if they disabled hpn then use the ssh std window size */ ++ ++ /* so why don't we just do a getsockopt() here and set the */ ++ /* ssh window to that? In the case of a autotuning receive */ ++ /* window the window would get stuck at the initial buffer */ ++ /* size generally less than 96k. Therefore we need to set the */ ++ /* maximum ssh window size to the maximum hpn buffer size */ ++ /* unless the user has specifically set the tcprcvbufpoll */ ++ /* to no. In which case we *can* just set the window to the */ ++ /* minimum of the hpn buffer size and tcp receive buffer size */ ++ ++ if (tty_flag) ++ options.hpn_buffer_size = CHAN_SES_WINDOW_DEFAULT; ++ else ++ options.hpn_buffer_size = 2*1024*1024; ++ ++ if (datafellows & SSH_BUG_LARGEWINDOW) ++ { ++ debug("HPN to Non-HPN Connection"); ++ } ++ else ++ { ++ if (options.tcp_rcv_buf_poll <= 0) ++ { ++ sock = socket(AF_INET, SOCK_STREAM, 0); ++ getsockopt(sock, SOL_SOCKET, SO_RCVBUF, ++ &socksize, &socksizelen); ++ close(sock); ++ debug("socksize %d", socksize); ++ options.hpn_buffer_size = socksize; ++ debug ("HPNBufferSize set to TCP RWIN: %d", options.hpn_buffer_size); ++ } ++ else ++ { ++ if (options.tcp_rcv_buf > 0) ++ { ++ /*create a socket but don't connect it */ ++ /* we use that the get the rcv socket size */ ++ sock = socket(AF_INET, SOCK_STREAM, 0); ++ /* if they are using the tcp_rcv_buf option */ ++ /* attempt to set the buffer size to that */ ++ if (options.tcp_rcv_buf) ++ setsockopt(sock, SOL_SOCKET, SO_RCVBUF, (void *)&options.tcp_rcv_buf, ++ sizeof(options.tcp_rcv_buf)); ++ getsockopt(sock, SOL_SOCKET, SO_RCVBUF, ++ &socksize, &socksizelen); ++ close(sock); ++ debug("socksize %d", socksize); ++ options.hpn_buffer_size = socksize; ++ debug ("HPNBufferSize set to user TCPRcvBuf: %d", options.hpn_buffer_size); ++ } ++ } ++ ++ } ++ ++ debug("Final hpn_buffer_size = %d", options.hpn_buffer_size); ++ ++ window = options.hpn_buffer_size; ++ ++ channel_set_hpn(options.hpn_disabled, options.hpn_buffer_size); ++ + packetmax = CHAN_SES_PACKET_DEFAULT; + if (tty_flag) { ++ window = 4*CHAN_SES_PACKET_DEFAULT; + window >>= 1; + packetmax >>= 1; + } +@@ -1172,7 +1245,10 @@ ssh_session2_open(void) + "session", SSH_CHANNEL_OPENING, in, out, err, + window, packetmax, CHAN_EXTENDED_WRITE, + "client-session", /*nonblock*/0); +- ++ if ((options.tcp_rcv_buf_poll > 0) && (!options.hpn_disabled)) { ++ c->dynamic_window = 1; ++ debug ("Enabled Dynamic Window Scaling\n"); ++ } + debug3("ssh_session2_open: channel_new: %d", c->self); + + channel_send_open(c->self); +diff -NupwB openssh-5.2p1-canonical/sshconnect2.c openssh-5.2p1-hpn13v6/sshconnect2.c +--- openssh-5.2p1-canonical/sshconnect2.c 2008-11-05 00:20:47.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/sshconnect2.c 2009-05-14 12:36:10.000000000 -0400 +@@ -78,6 +78,12 @@ + extern char *client_version_string; + extern char *server_version_string; + extern Options options; ++extern Kex *xxx_kex; ++ ++/* tty_flag is set in ssh.c. use this in ssh_userauth2 */ ++/* if it is set then prevent the switch to the null cipher */ ++ ++extern int tty_flag; + + /* + * SSH2 key exchange +@@ -350,6 +356,28 @@ ssh_userauth2(const char *local_user, co + pubkey_cleanup(&authctxt); + dispatch_range(SSH2_MSG_USERAUTH_MIN, SSH2_MSG_USERAUTH_MAX, NULL); + ++ /* if the user wants to use the none cipher do it */ ++ /* post authentication and only if the right conditions are met */ ++ /* both of the NONE commands must be true and there must be no */ ++ /* tty allocated */ ++ if ((options.none_switch == 1) && (options.none_enabled == 1)) ++ { ++ if (!tty_flag) /* no null on tty sessions */ ++ { ++ debug("Requesting none rekeying..."); ++ myproposal[PROPOSAL_ENC_ALGS_STOC] = "none"; ++ myproposal[PROPOSAL_ENC_ALGS_CTOS] = "none"; ++ kex_prop2buf(&xxx_kex->my,myproposal); ++ packet_request_rekeying(); ++ fprintf(stderr, "WARNING: ENABLED NONE CIPHER\n"); ++ } ++ else ++ { ++ /* requested NONE cipher when in a tty */ ++ debug("Cannot switch to NONE cipher with tty allocated"); ++ fprintf(stderr, "NONE cipher switch disabled when a TTY is allocated\n"); ++ } ++ } + debug("Authentication succeeded (%s).", authctxt.method->name); + } + +diff -NupwB openssh-5.2p1-canonical/sshconnect.c openssh-5.2p1-hpn13v6/sshconnect.c +--- openssh-5.2p1-canonical/sshconnect.c 2009-02-01 06:19:54.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/sshconnect.c 2009-05-14 12:36:10.000000000 -0400 +@@ -165,6 +165,31 @@ ssh_proxy_connect(const char *host, u_sh + } + + /* ++ * Set TCP receive buffer if requested. ++ * Note: tuning needs to happen after the socket is ++ * created but before the connection happens ++ * so winscale is negotiated properly -cjr ++ */ ++static void ++ssh_set_socket_recvbuf(int sock) ++{ ++ void *buf = (void *)&options.tcp_rcv_buf; ++ int sz = sizeof(options.tcp_rcv_buf); ++ int socksize; ++ int socksizelen = sizeof(int); ++ ++ debug("setsockopt Attempting to set SO_RCVBUF to %d", options.tcp_rcv_buf); ++ if (setsockopt(sock, SOL_SOCKET, SO_RCVBUF, buf, sz) >= 0) { ++ getsockopt(sock, SOL_SOCKET, SO_RCVBUF, &socksize, &socksizelen); ++ debug("setsockopt SO_RCVBUF: %.100s %d", strerror(errno), socksize); ++ } ++ else ++ error("Couldn't set socket receive buffer to %d: %.100s", ++ options.tcp_rcv_buf, strerror(errno)); ++} ++ ++ ++/* + * Creates a (possibly privileged) socket for use as the ssh connection. + */ + static int +@@ -187,12 +212,18 @@ ssh_create_socket(int privileged, struct + strerror(errno)); + else + debug("Allocated local port %d.", p); ++ ++ if (options.tcp_rcv_buf > 0) ++ ssh_set_socket_recvbuf(sock); + return sock; + } + sock = socket(ai->ai_family, ai->ai_socktype, ai->ai_protocol); + if (sock < 0) + error("socket: %.100s", strerror(errno)); + ++ if (options.tcp_rcv_buf > 0) ++ ssh_set_socket_recvbuf(sock); ++ + /* Bind the socket to an alternative local IP address */ + if (options.bind_address == NULL) + return sock; +@@ -536,7 +567,7 @@ ssh_exchange_identification(int timeout_ + snprintf(buf, sizeof buf, "SSH-%d.%d-%.100s%s", + compat20 ? PROTOCOL_MAJOR_2 : PROTOCOL_MAJOR_1, + compat20 ? PROTOCOL_MINOR_2 : minor1, +- SSH_VERSION, compat20 ? "\r\n" : "\n"); ++ SSH_RELEASE, compat20 ? "\r\n" : "\n"); + if (atomicio(vwrite, connection_out, buf, strlen(buf)) != strlen(buf)) + fatal("write: %.100s", strerror(errno)); + client_version_string = xstrdup(buf); +diff -NupwB openssh-5.2p1-canonical/sshd.c openssh-5.2p1-hpn13v6/sshd.c +--- openssh-5.2p1-canonical/sshd.c 2009-01-28 00:31:23.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/sshd.c 2009-05-14 12:36:10.000000000 -0400 +@@ -136,6 +136,9 @@ int deny_severity; + #define REEXEC_CONFIG_PASS_FD (STDERR_FILENO + 3) + #define REEXEC_MIN_FREE_FD (STDERR_FILENO + 4) + ++int myflag = 0; ++ ++ + extern char *__progname; + + /* Server configuration options. */ +@@ -415,7 +418,7 @@ sshd_exchange_identification(int sock_in + minor = PROTOCOL_MINOR_1; + } + snprintf(buf, sizeof buf, "SSH-%d.%d-%.100s%s", major, minor, +- SSH_VERSION, newline); ++ SSH_RELEASE, newline); + server_version_string = xstrdup(buf); + + /* Send our protocol version identification. */ +@@ -466,6 +469,9 @@ sshd_exchange_identification(int sock_in + } + debug("Client protocol version %d.%d; client software version %.100s", + remote_major, remote_minor, remote_version); ++ logit("SSH: Server;Ltype: Version;Remote: %s-%d;Protocol: %d.%d;Client: %.100s", ++ get_remote_ipaddr(), get_remote_port(), ++ remote_major, remote_minor, remote_version); + + compat_datafellows(remote_version); + +@@ -944,6 +950,8 @@ server_listen(void) + int ret, listen_sock, on = 1; + struct addrinfo *ai; + char ntop[NI_MAXHOST], strport[NI_MAXSERV]; ++ int socksize; ++ int socksizelen = sizeof(int); + + for (ai = options.listen_addrs; ai; ai = ai->ai_next) { + if (ai->ai_family != AF_INET && ai->ai_family != AF_INET6) +@@ -990,6 +998,11 @@ server_listen(void) + + debug("Bind to port %s on %s.", strport, ntop); + ++ getsockopt(listen_sock, SOL_SOCKET, SO_RCVBUF, ++ &socksize, &socksizelen); ++ debug("Server TCP RWIN socket size: %d", socksize); ++ debug("HPN Buffer Size: %d", options.hpn_buffer_size); ++ + /* Bind the socket to the desired port. */ + if (bind(listen_sock, ai->ai_addr, ai->ai_addrlen) < 0) { + error("Bind to port %s on %s failed: %.200s.", +@@ -1817,6 +1830,9 @@ main(int ac, char **av) + /* Log the connection. */ + verbose("Connection from %.500s port %d", remote_ip, remote_port); + ++ /* set the HPN options for the child */ ++ channel_set_hpn(options.hpn_disabled, options.hpn_buffer_size); ++ + /* + * We don't want to listen forever unless the other side + * successfully authenticates itself. So we set up an alarm which is +@@ -2171,9 +2187,15 @@ do_ssh2_kex(void) + { + Kex *kex; + ++ myflag++; ++ debug ("MYFLAG IS %d", myflag); + if (options.ciphers != NULL) { + myproposal[PROPOSAL_ENC_ALGS_CTOS] = + myproposal[PROPOSAL_ENC_ALGS_STOC] = options.ciphers; ++ } else if (options.none_enabled == 1) { ++ debug ("WARNING: None cipher enabled"); ++ myproposal[PROPOSAL_ENC_ALGS_CTOS] = ++ myproposal[PROPOSAL_ENC_ALGS_STOC] = KEX_ENCRYPT_INCLUDE_NONE; + } + myproposal[PROPOSAL_ENC_ALGS_CTOS] = + compat_cipher_proposal(myproposal[PROPOSAL_ENC_ALGS_CTOS]); +diff -NupwB openssh-5.2p1-canonical/sshd_config openssh-5.2p1-hpn13v6/sshd_config +--- openssh-5.2p1-canonical/sshd_config 2008-07-02 08:35:43.000000000 -0400 ++++ openssh-5.2p1-hpn13v6/sshd_config 2009-05-14 12:36:10.000000000 -0400 +@@ -112,6 +112,20 @@ Protocol 2 + # override default of no subsystems + Subsystem sftp /usr/libexec/sftp-server + ++# the following are HPN related configuration options ++# tcp receive buffer polling. disable in non autotuning kernels ++#TcpRcvBufPoll yes ++ ++# allow the use of the none cipher ++#NoneEnabled no ++ ++# disable hpn performance boosts. ++#HPNDisabled no ++ ++# buffer size for hpn to non-hpn connections ++#HPNBufferSize 2048 ++ ++ + # Example of overriding settings on a per-user basis + #Match User anoncvs + # X11Forwarding no +diff -NupwB openssh-5.2p1-canonical/version.h openssh-5.2p1-hpn13v6/version.h +--- openssh-5.2p1-canonical/version.h 2009-02-22 19:09:26.000000000 -0500 ++++ openssh-5.2p1-hpn13v6/version.h 2009-05-14 12:42:05.000000000 -0400 +@@ -3,4 +3,5 @@ + #define SSH_VERSION "OpenSSH_5.2" + + #define SSH_PORTABLE "p1" +-#define SSH_RELEASE SSH_VERSION SSH_PORTABLE ++#define SSH_HPN "-hpn13v6" ++#define SSH_RELEASE SSH_VERSION SSH_PORTABLE SSH_HPN diff --git a/openssh-5.8p2.tar.gz.asc b/openssh-5.8p2.tar.gz.asc new file mode 100644 index 0000000..a669a35 --- /dev/null +++ b/openssh-5.8p2.tar.gz.asc @@ -0,0 +1,7 @@ +-----BEGIN PGP SIGNATURE----- +Version: GnuPG v1.4.11 (OpenBSD) + +iD8DBQBNwgQ7zo7LA4b/nEgRAoSQAJ4o4iy2x9GRjjz0ffeAHswyhIRhugCgtYDe +drVlYJmSot+PGjSRblBDdx0= +=MfCT +-----END PGP SIGNATURE----- diff --git a/openssh-lpk-5.4p1-0.3.10.diff b/openssh-lpk-5.4p1-0.3.10.diff new file mode 100644 index 0000000..dc2fcc3 --- /dev/null +++ b/openssh-lpk-5.4p1-0.3.10.diff @@ -0,0 +1,1881 @@ +diff -Naurp openssh-5.4p1/auth2-pubkey.c openssh-5.4p1.oden/auth2-pubkey.c +--- openssh-5.4p1/auth2-pubkey.c 2010-03-04 11:53:35.000000000 +0100 ++++ openssh-5.4p1.oden/auth2-pubkey.c 2010-03-08 12:17:30.957380964 +0100 +@@ -58,6 +58,10 @@ + #include "misc.h" + #include "authfile.h" + ++#ifdef WITH_LDAP_PUBKEY ++#include "ldapauth.h" ++#endif ++ + /* import */ + extern ServerOptions options; + extern u_char *session_id2; +@@ -187,10 +191,79 @@ user_key_allowed2(struct passwd *pw, Key + u_long linenum = 0; + Key *found; + char *fp; ++#ifdef WITH_LDAP_PUBKEY ++ ldap_key_t * k; ++ unsigned int i = 0; ++#endif + + /* Temporarily use the user's uid. */ + temporarily_use_uid(pw); + ++#ifdef WITH_LDAP_PUBKEY ++ found_key = 0; ++ /* allocate a new key type */ ++ found = key_new(key->type); ++ ++ /* first check if the options is enabled, then try.. */ ++ if (options.lpk.on) { ++ debug("[LDAP] trying LDAP first uid=%s",pw->pw_name); ++ if (ldap_ismember(&options.lpk, pw->pw_name) > 0) { ++ if ((k = ldap_getuserkey(&options.lpk, pw->pw_name)) != NULL) { ++ /* Skip leading whitespace, empty and comment lines. */ ++ for (i = 0 ; i < k->num ; i++) { ++ /* dont forget if multiple keys to reset options */ ++ char *cp, *options = NULL; ++ ++ for (cp = (char *)k->keys[i]->bv_val; *cp == ' ' || *cp == '\t'; cp++) ++ ; ++ if (!*cp || *cp == '\n' || *cp == '#') ++ continue; ++ ++ if (key_read(found, &cp) != 1) { ++ /* no key? check if there are options for this key */ ++ int quoted = 0; ++ debug2("[LDAP] user_key_allowed: check options: '%s'", cp); ++ options = cp; ++ for (; *cp && (quoted || (*cp != ' ' && *cp != '\t')); cp++) { ++ if (*cp == '\\' && cp[1] == '"') ++ cp++; /* Skip both */ ++ else if (*cp == '"') ++ quoted = !quoted; ++ } ++ /* Skip remaining whitespace. */ ++ for (; *cp == ' ' || *cp == '\t'; cp++) ++ ; ++ if (key_read(found, &cp) != 1) { ++ debug2("[LDAP] user_key_allowed: advance: '%s'", cp); ++ /* still no key? advance to next line*/ ++ continue; ++ } ++ } ++ ++ if (key_equal(found, key) && ++ auth_parse_options(pw, options, file, linenum) == 1) { ++ found_key = 1; ++ debug("[LDAP] matching key found"); ++ fp = key_fingerprint(found, SSH_FP_MD5, SSH_FP_HEX); ++ verbose("[LDAP] Found matching %s key: %s", key_type(found), fp); ++ ++ /* restoring memory */ ++ ldap_keys_free(k); ++ xfree(fp); ++ restore_uid(); ++ key_free(found); ++ return found_key; ++ break; ++ } ++ }/* end of LDAP for() */ ++ } else { ++ logit("[LDAP] no keys found for '%s'!", pw->pw_name); ++ } ++ } else { ++ logit("[LDAP] '%s' is not in '%s'", pw->pw_name, options.lpk.sgroup); ++ } ++ } ++#endif + debug("trying public key file %s", file); + f = auth_openkeyfile(file, pw, options.strict_modes); + +diff -Naurp openssh-5.4p1/auth-rsa.c openssh-5.4p1.oden/auth-rsa.c +--- openssh-5.4p1/auth-rsa.c 2010-03-04 11:53:35.000000000 +0100 ++++ openssh-5.4p1.oden/auth-rsa.c 2010-03-08 12:17:30.958380880 +0100 +@@ -177,10 +177,96 @@ auth_rsa_key_allowed(struct passwd *pw, + FILE *f; + u_long linenum = 0; + Key *key; ++#ifdef WITH_LDAP_PUBKEY ++ ldap_key_t * k; ++ unsigned int i = 0; ++#endif + + /* Temporarily use the user's uid. */ + temporarily_use_uid(pw); + ++#ifdef WITH_LDAP_PUBKEY ++ /* here is the job */ ++ key = key_new(KEY_RSA1); ++ ++ if (options.lpk.on) { ++ debug("[LDAP] trying LDAP first uid=%s", pw->pw_name); ++ if ( ldap_ismember(&options.lpk, pw->pw_name) > 0) { ++ if ( (k = ldap_getuserkey(&options.lpk, pw->pw_name)) != NULL) { ++ for (i = 0 ; i < k->num ; i++) { ++ char *cp, *options = NULL; ++ ++ for (cp = k->keys[i]->bv_val; *cp == ' ' || *cp == '\t'; cp++) ++ ; ++ if (!*cp || *cp == '\n' || *cp == '#') ++ continue; ++ ++ /* ++ * Check if there are options for this key, and if so, ++ * save their starting address and skip the option part ++ * for now. If there are no options, set the starting ++ * address to NULL. ++ */ ++ if (*cp < '0' || *cp > '9') { ++ int quoted = 0; ++ options = cp; ++ for (; *cp && (quoted || (*cp != ' ' && *cp != '\t')); cp++) { ++ if (*cp == '\\' && cp[1] == '"') ++ cp++; /* Skip both */ ++ else if (*cp == '"') ++ quoted = !quoted; ++ } ++ } else ++ options = NULL; ++ ++ /* Parse the key from the line. */ ++ if (hostfile_read_key(&cp, &bits, key) == 0) { ++ debug("[LDAP] line %d: non ssh1 key syntax", i); ++ continue; ++ } ++ /* cp now points to the comment part. */ ++ ++ /* Check if the we have found the desired key (identified by its modulus). */ ++ if (BN_cmp(key->rsa->n, client_n) != 0) ++ continue; ++ ++ /* check the real bits */ ++ if (bits != (unsigned int)BN_num_bits(key->rsa->n)) ++ logit("[LDAP] Warning: ldap, line %lu: keysize mismatch: " ++ "actual %d vs. announced %d.", (unsigned long)i, BN_num_bits(key->rsa->n), bits); ++ ++ /* We have found the desired key. */ ++ /* ++ * If our options do not allow this key to be used, ++ * do not send challenge. ++ */ ++ if (!auth_parse_options(pw, options, "[LDAP]", (unsigned long) i)) ++ continue; ++ ++ /* break out, this key is allowed */ ++ allowed = 1; ++ ++ /* add the return stuff etc... */ ++ /* Restore the privileged uid. */ ++ restore_uid(); ++ ++ /* return key if allowed */ ++ if (allowed && rkey != NULL) ++ *rkey = key; ++ else ++ key_free(key); ++ ++ ldap_keys_free(k); ++ return (allowed); ++ } ++ } else { ++ logit("[LDAP] no keys found for '%s'!", pw->pw_name); ++ } ++ } else { ++ logit("[LDAP] '%s' is not in '%s'", pw->pw_name, options.lpk.sgroup); ++ } ++ } ++#endif + /* The authorized keys. */ + file = authorized_keys_file(pw); + debug("trying public RSA key file %s", file); +diff -Naurp openssh-5.4p1/config.h.in openssh-5.4p1.oden/config.h.in +--- openssh-5.4p1/config.h.in 2010-03-08 01:30:57.000000000 +0100 ++++ openssh-5.4p1.oden/config.h.in 2010-03-08 12:17:30.959380993 +0100 +@@ -575,6 +575,9 @@ + /* Define to 1 if you have the header file. */ + #undef HAVE_LINUX_IF_TUN_H + ++/* Define if you want LDAP support */ ++#undef WITH_LDAP_PUBKEY ++ + /* Define if your libraries define login() */ + #undef HAVE_LOGIN + +diff -Naurp openssh-5.4p1/configure openssh-5.4p1.oden/configure +--- openssh-5.4p1/configure 2010-03-08 01:30:59.000000000 +0100 ++++ openssh-5.4p1.oden/configure 2010-03-08 12:17:30.967381745 +0100 +@@ -1340,6 +1340,7 @@ Optional Packages: + --with-tcp-wrappers[=PATH] Enable tcpwrappers support (optionally in PATH) + --with-libedit[=PATH] Enable libedit support for sftp + --with-audit=module Enable EXPERIMENTAL audit support (modules=debug,bsm) ++ --with-ldap[=PATH] Enable LDAP pubkey support (optionally in PATH) + --with-ssl-dir=PATH Specify path to OpenSSL installation + --without-openssl-header-check Disable OpenSSL version consistency check + --with-ssl-engine Enable OpenSSL (hardware) ENGINE support +@@ -12845,6 +12846,85 @@ echo "$as_me: error: Unknown audit modul + fi + + ++# Check whether user wants LDAP support ++LDAP_MSG="no" ++ ++# Check whether --with-ldap was given. ++if test "${with_ldap+set}" = set; then ++ withval=$with_ldap; ++ if test "x$withval" != "xno" ; then ++ ++ if test "x$withval" != "xyes" ; then ++ CPPFLAGS="$CPPFLAGS -I${withval}/include" ++ LDFLAGS="$LDFLAGS -L${withval}/lib" ++ fi ++ ++ ++cat >>confdefs.h <<\_ACEOF ++#define WITH_LDAP_PUBKEY 1 ++_ACEOF ++ ++ LIBS="-lldap $LIBS" ++ LDAP_MSG="yes" ++ ++ { echo "$as_me:$LINENO: checking for LDAP support" >&5 ++echo $ECHO_N "checking for LDAP support... $ECHO_C" >&6; } ++ cat >conftest.$ac_ext <<_ACEOF ++/* confdefs.h. */ ++_ACEOF ++cat confdefs.h >>conftest.$ac_ext ++cat >>conftest.$ac_ext <<_ACEOF ++/* end confdefs.h. */ ++#include ++ #include ++int ++main () ++{ ++(void)ldap_init(0, 0); ++ ; ++ return 0; ++} ++_ACEOF ++rm -f conftest.$ac_objext ++if { (ac_try="$ac_compile" ++case "(($ac_try" in ++ *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; ++ *) ac_try_echo=$ac_try;; ++esac ++eval "echo \"\$as_me:$LINENO: $ac_try_echo\"") >&5 ++ (eval "$ac_compile") 2>conftest.er1 ++ ac_status=$? ++ grep -v '^ *+' conftest.er1 >conftest.err ++ rm -f conftest.er1 ++ cat conftest.err >&5 ++ echo "$as_me:$LINENO: \$? = $ac_status" >&5 ++ (exit $ac_status); } && { ++ test -z "$ac_c_werror_flag" || ++ test ! -s conftest.err ++ } && test -s conftest.$ac_objext; then ++ { echo "$as_me:$LINENO: result: yes" >&5 ++echo "${ECHO_T}yes" >&6; } ++else ++ echo "$as_me: failed program was:" >&5 ++sed 's/^/| /' conftest.$ac_ext >&5 ++ ++ ++ { echo "$as_me:$LINENO: result: no" >&5 ++echo "${ECHO_T}no" >&6; } ++ { { echo "$as_me:$LINENO: error: ** Incomplete or missing ldap libraries **" >&5 ++echo "$as_me: error: ** Incomplete or missing ldap libraries **" >&2;} ++ { (exit 1); exit 1; }; } ++ ++ ++fi ++ ++rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext ++ fi ++ ++ ++fi ++ ++ + + + +@@ -30786,6 +30866,7 @@ echo " SELinux support + echo " Smartcard support: $SCARD_MSG" + echo " S/KEY support: $SKEY_MSG" + echo " TCP Wrappers support: $TCPW_MSG" ++echo " LDAP support: $LDAP_MSG" + echo " MD5 password support: $MD5_MSG" + echo " libedit support: $LIBEDIT_MSG" + echo " Solaris process contract support: $SPC_MSG" +diff -Naurp openssh-5.4p1/configure.ac openssh-5.4p1.oden/configure.ac +--- openssh-5.4p1/configure.ac 2010-03-05 05:04:35.000000000 +0100 ++++ openssh-5.4p1.oden/configure.ac 2010-03-08 12:17:30.972381498 +0100 +@@ -1323,6 +1323,37 @@ AC_ARG_WITH(audit, + esac ] + ) + ++# Check whether user wants LDAP support ++LDAP_MSG="no" ++AC_ARG_WITH(ldap, ++ [ --with-ldap[[=PATH]] Enable LDAP pubkey support (optionally in PATH)], ++ [ ++ if test "x$withval" != "xno" ; then ++ ++ if test "x$withval" != "xyes" ; then ++ CPPFLAGS="$CPPFLAGS -I${withval}/include" ++ LDFLAGS="$LDFLAGS -L${withval}/lib" ++ fi ++ ++ AC_DEFINE([WITH_LDAP_PUBKEY], 1, [Enable LDAP pubkey support]) ++ LIBS="-lldap $LIBS" ++ LDAP_MSG="yes" ++ ++ AC_MSG_CHECKING([for LDAP support]) ++ AC_TRY_COMPILE( ++ [#include ++ #include ], ++ [(void)ldap_init(0, 0);], ++ [AC_MSG_RESULT(yes)], ++ [ ++ AC_MSG_RESULT(no) ++ AC_MSG_ERROR([** Incomplete or missing ldap libraries **]) ++ ] ++ ) ++ fi ++ ] ++) ++ + dnl Checks for library functions. Please keep in alphabetical order + AC_CHECK_FUNCS( \ + arc4random \ +@@ -4185,6 +4216,7 @@ echo " SELinux support + echo " Smartcard support: $SCARD_MSG" + echo " S/KEY support: $SKEY_MSG" + echo " TCP Wrappers support: $TCPW_MSG" ++echo " LDAP support: $LDAP_MSG" + echo " MD5 password support: $MD5_MSG" + echo " libedit support: $LIBEDIT_MSG" + echo " Solaris process contract support: $SPC_MSG" +diff -Naurp openssh-5.4p1/ldapauth.c openssh-5.4p1.oden/ldapauth.c +--- openssh-5.4p1/ldapauth.c 1970-01-01 01:00:00.000000000 +0100 ++++ openssh-5.4p1.oden/ldapauth.c 2010-03-08 12:17:30.974381643 +0100 +@@ -0,0 +1,575 @@ ++/* ++ * $Id: openssh-lpk-4.3p1-0.3.7.patch,v 1.3 2006/04/18 15:29:09 eau Exp $ ++ */ ++ ++/* ++ * ++ * Copyright (c) 2005, Eric AUGE ++ * All rights reserved. ++ * ++ * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: ++ * ++ * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. ++ * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. ++ * Neither the name of the phear.org nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. ++ * ++ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, ++ * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. ++ * IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, ++ * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; ++ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, ++ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ++ * ++ * ++ */ ++ ++#include "includes.h" ++ ++#ifdef WITH_LDAP_PUBKEY ++ ++#include ++#include ++#include ++#include ++ ++#include "ldapauth.h" ++#include "log.h" ++ ++static char *attrs[] = { ++ PUBKEYATTR, ++ NULL ++}; ++ ++/* filter building infos */ ++#define FILTER_GROUP_PREFIX "(&(objectclass=posixGroup)" ++#define FILTER_OR_PREFIX "(|" ++#define FILTER_OR_SUFFIX ")" ++#define FILTER_CN_PREFIX "(cn=" ++#define FILTER_CN_SUFFIX ")" ++#define FILTER_UID_FORMAT "(memberUid=%s)" ++#define FILTER_GROUP_SUFFIX ")" ++#define FILTER_GROUP_SIZE(group) (size_t) (strlen(group)+(ldap_count_group(group)*5)+52) ++ ++/* just filter building stuff */ ++#define REQUEST_GROUP_SIZE(filter, uid) (size_t) (strlen(filter)+strlen(uid)+1) ++#define REQUEST_GROUP(buffer, prefilter, pwname) \ ++ buffer = (char *) calloc(REQUEST_GROUP_SIZE(prefilter, pwname), sizeof(char)); \ ++ if (!buffer) { \ ++ perror("calloc()"); \ ++ return FAILURE; \ ++ } \ ++ snprintf(buffer, REQUEST_GROUP_SIZE(prefilter,pwname), prefilter, pwname) ++/* ++XXX OLD group building macros ++#define REQUEST_GROUP_SIZE(grp, uid) (size_t) (strlen(grp)+strlen(uid)+46) ++#define REQUEST_GROUP(buffer,pwname,grp) \ ++ buffer = (char *) calloc(REQUEST_GROUP_SIZE(grp, pwname), sizeof(char)); \ ++ if (!buffer) { \ ++ perror("calloc()"); \ ++ return FAILURE; \ ++ } \ ++ snprintf(buffer,REQUEST_GROUP_SIZE(grp,pwname),"(&(objectclass=posixGroup)(cn=%s)(memberUid=%s))",grp,pwname) ++ */ ++ ++/* ++XXX stock upstream version without extra filter support ++#define REQUEST_USER_SIZE(uid) (size_t) (strlen(uid)+64) ++#define REQUEST_USER(buffer, pwname) \ ++ buffer = (char *) calloc(REQUEST_USER_SIZE(pwname), sizeof(char)); \ ++ if (!buffer) { \ ++ perror("calloc()"); \ ++ return NULL; \ ++ } \ ++ snprintf(buffer,REQUEST_USER_SIZE(pwname),"(&(objectclass=posixAccount)(objectclass=ldapPublicKey)(uid=%s))",pwname) ++ */ ++ ++#define REQUEST_USER_SIZE(uid, filter) (size_t) (strlen(uid)+64+(filter != NULL ? strlen(filter) : 0)) ++#define REQUEST_USER(buffer, pwname, customfilter) \ ++ buffer = (char *) calloc(REQUEST_USER_SIZE(pwname, customfilter), sizeof(char)); \ ++ if (!buffer) { \ ++ perror("calloc()"); \ ++ return NULL; \ ++ } \ ++ snprintf(buffer, REQUEST_USER_SIZE(pwname, customfilter), \ ++ "(&(objectclass=posixAccount)(objectclass=ldapPublicKey)(uid=%s)%s)", \ ++ pwname, (customfilter != NULL ? customfilter : "")) ++ ++/* some portable and working tokenizer, lame though */ ++static int tokenize(char ** o, size_t size, char * input) { ++ unsigned int i = 0, num; ++ const char * charset = " \t"; ++ char * ptr = input; ++ ++ /* leading white spaces are ignored */ ++ num = strspn(ptr, charset); ++ ptr += num; ++ ++ while ((num = strcspn(ptr, charset))) { ++ if (i < size-1) { ++ o[i++] = ptr; ++ ptr += num; ++ if (*ptr) ++ *ptr++ = '\0'; ++ } ++ } ++ o[i] = NULL; ++ return SUCCESS; ++} ++ ++void ldap_close(ldap_opt_t * ldap) { ++ ++ if (!ldap) ++ return; ++ ++ if ( ldap_unbind_ext(ldap->ld, NULL, NULL) < 0) ++ ldap_perror(ldap->ld, "ldap_unbind()"); ++ ++ ldap->ld = NULL; ++ FLAG_SET_DISCONNECTED(ldap->flags); ++ ++ return; ++} ++ ++/* init && bind */ ++int ldap_connect(ldap_opt_t * ldap) { ++ int version = LDAP_VERSION3; ++ ++ if (!ldap->servers) ++ return FAILURE; ++ ++ /* Connection Init and setup */ ++ ldap->ld = ldap_init(ldap->servers, LDAP_PORT); ++ if (!ldap->ld) { ++ ldap_perror(ldap->ld, "ldap_init()"); ++ return FAILURE; ++ } ++ ++ if ( ldap_set_option(ldap->ld, LDAP_OPT_PROTOCOL_VERSION, &version) != LDAP_OPT_SUCCESS) { ++ ldap_perror(ldap->ld, "ldap_set_option(LDAP_OPT_PROTOCOL_VERSION)"); ++ return FAILURE; ++ } ++ ++ /* Timeouts setup */ ++ if (ldap_set_option(ldap->ld, LDAP_OPT_NETWORK_TIMEOUT, &ldap->b_timeout) != LDAP_SUCCESS) { ++ ldap_perror(ldap->ld, "ldap_set_option(LDAP_OPT_NETWORK_TIMEOUT)"); ++ } ++ if (ldap_set_option(ldap->ld, LDAP_OPT_TIMEOUT, &ldap->s_timeout) != LDAP_SUCCESS) { ++ ldap_perror(ldap->ld, "ldap_set_option(LDAP_OPT_TIMEOUT)"); ++ } ++ ++ /* TLS support */ ++ if ( (ldap->tls == -1) || (ldap->tls == 1) ) { ++ if (ldap_start_tls_s(ldap->ld, NULL, NULL ) != LDAP_SUCCESS) { ++ /* failed then reinit the initial connect */ ++ ldap_perror(ldap->ld, "ldap_connect: (TLS) ldap_start_tls()"); ++ if (ldap->tls == 1) ++ return FAILURE; ++ ++ ldap->ld = ldap_init(ldap->servers, LDAP_PORT); ++ if (!ldap->ld) { ++ ldap_perror(ldap->ld, "ldap_init()"); ++ return FAILURE; ++ } ++ ++ if ( ldap_set_option(ldap->ld, LDAP_OPT_PROTOCOL_VERSION, &version) != LDAP_OPT_SUCCESS) { ++ ldap_perror(ldap->ld, "ldap_set_option()"); ++ return FAILURE; ++ } ++ } ++ } ++ ++ ++ if ( ldap_simple_bind_s(ldap->ld, ldap->binddn, ldap->bindpw) != LDAP_SUCCESS) { ++ ldap_perror(ldap->ld, "ldap_simple_bind_s()"); ++ return FAILURE; ++ } ++ ++ /* says it is connected */ ++ FLAG_SET_CONNECTED(ldap->flags); ++ ++ return SUCCESS; ++} ++ ++/* must free allocated ressource */ ++static char * ldap_build_host(char *host, int port) { ++ unsigned int size = strlen(host)+11; ++ char * h = (char *) calloc (size, sizeof(char)); ++ int rc; ++ if (!h) ++ return NULL; ++ ++ rc = snprintf(h, size, "%s:%d ", host, port); ++ if (rc == -1) ++ return NULL; ++ return h; ++} ++ ++static int ldap_count_group(const char * input) { ++ const char * charset = " \t"; ++ const char * ptr = input; ++ unsigned int count = 0; ++ unsigned int num; ++ ++ num = strspn(ptr, charset); ++ ptr += num; ++ ++ while ((num = strcspn(ptr, charset))) { ++ count++; ++ ptr += num; ++ ptr++; ++ } ++ ++ return count; ++} ++ ++/* format filter */ ++char * ldap_parse_groups(const char * groups) { ++ unsigned int buffer_size = FILTER_GROUP_SIZE(groups); ++ char * buffer = (char *) calloc(buffer_size, sizeof(char)); ++ char * g = NULL; ++ char * garray[32]; ++ unsigned int i = 0; ++ ++ if ((!groups)||(!buffer)) ++ return NULL; ++ ++ g = strdup(groups); ++ if (!g) { ++ free(buffer); ++ return NULL; ++ } ++ ++ /* first separate into n tokens */ ++ if ( tokenize(garray, sizeof(garray)/sizeof(*garray), g) < 0) { ++ free(g); ++ free(buffer); ++ return NULL; ++ } ++ ++ /* build the final filter format */ ++ strlcat(buffer, FILTER_GROUP_PREFIX, buffer_size); ++ strlcat(buffer, FILTER_OR_PREFIX, buffer_size); ++ i = 0; ++ while (garray[i]) { ++ strlcat(buffer, FILTER_CN_PREFIX, buffer_size); ++ strlcat(buffer, garray[i], buffer_size); ++ strlcat(buffer, FILTER_CN_SUFFIX, buffer_size); ++ i++; ++ } ++ strlcat(buffer, FILTER_OR_SUFFIX, buffer_size); ++ strlcat(buffer, FILTER_UID_FORMAT, buffer_size); ++ strlcat(buffer, FILTER_GROUP_SUFFIX, buffer_size); ++ ++ free(g); ++ return buffer; ++} ++ ++/* a bit dirty but leak free */ ++char * ldap_parse_servers(const char * servers) { ++ char * s = NULL; ++ char * tmp = NULL, *urls[32]; ++ unsigned int num = 0 , i = 0 , asize = 0; ++ LDAPURLDesc *urld[32]; ++ ++ if (!servers) ++ return NULL; ++ ++ /* local copy of the arg */ ++ s = strdup(servers); ++ if (!s) ++ return NULL; ++ ++ /* first separate into URL tokens */ ++ if ( tokenize(urls, sizeof(urls)/sizeof(*urls), s) < 0) ++ return NULL; ++ ++ i = 0; ++ while (urls[i]) { ++ if (! ldap_is_ldap_url(urls[i]) || ++ (ldap_url_parse(urls[i], &urld[i]) != 0)) { ++ return NULL; ++ } ++ i++; ++ } ++ ++ /* now free(s) */ ++ free (s); ++ ++ /* how much memory do we need */ ++ num = i; ++ for (i = 0 ; i < num ; i++) ++ asize += strlen(urld[i]->lud_host)+11; ++ ++ /* alloc */ ++ s = (char *) calloc( asize+1 , sizeof(char)); ++ if (!s) { ++ for (i = 0 ; i < num ; i++) ++ ldap_free_urldesc(urld[i]); ++ return NULL; ++ } ++ ++ /* then build the final host string */ ++ for (i = 0 ; i < num ; i++) { ++ /* built host part */ ++ tmp = ldap_build_host(urld[i]->lud_host, urld[i]->lud_port); ++ strncat(s, tmp, strlen(tmp)); ++ ldap_free_urldesc(urld[i]); ++ free(tmp); ++ } ++ ++ return s; ++} ++ ++void ldap_options_print(ldap_opt_t * ldap) { ++ debug("ldap options:"); ++ debug("servers: %s", ldap->servers); ++ if (ldap->u_basedn) ++ debug("user basedn: %s", ldap->u_basedn); ++ if (ldap->g_basedn) ++ debug("group basedn: %s", ldap->g_basedn); ++ if (ldap->binddn) ++ debug("binddn: %s", ldap->binddn); ++ if (ldap->bindpw) ++ debug("bindpw: %s", ldap->bindpw); ++ if (ldap->sgroup) ++ debug("group: %s", ldap->sgroup); ++ if (ldap->filter) ++ debug("filter: %s", ldap->filter); ++} ++ ++void ldap_options_free(ldap_opt_t * l) { ++ if (!l) ++ return; ++ if (l->servers) ++ free(l->servers); ++ if (l->u_basedn) ++ free(l->u_basedn); ++ if (l->g_basedn) ++ free(l->g_basedn); ++ if (l->binddn) ++ free(l->binddn); ++ if (l->bindpw) ++ free(l->bindpw); ++ if (l->sgroup) ++ free(l->sgroup); ++ if (l->fgroup) ++ free(l->fgroup); ++ if (l->filter) ++ free(l->filter); ++ if (l->l_conf) ++ free(l->l_conf); ++ free(l); ++} ++ ++/* free keys */ ++void ldap_keys_free(ldap_key_t * k) { ++ ldap_value_free_len(k->keys); ++ free(k); ++ return; ++} ++ ++ldap_key_t * ldap_getuserkey(ldap_opt_t *l, const char * user) { ++ ldap_key_t * k = (ldap_key_t *) calloc (1, sizeof(ldap_key_t)); ++ LDAPMessage *res, *e; ++ char * filter; ++ int i; ++ ++ if ((!k) || (!l)) ++ return NULL; ++ ++ /* Am i still connected ? RETRY n times */ ++ /* XXX TODO: setup some conf value for retrying */ ++ if (!(l->flags & FLAG_CONNECTED)) ++ for (i = 0 ; i < 2 ; i++) ++ if (ldap_connect(l) == 0) ++ break; ++ ++ /* quick check for attempts to be evil */ ++ if ((strchr(user, '(') != NULL) || (strchr(user, ')') != NULL) || ++ (strchr(user, '*') != NULL) || (strchr(user, '\\') != NULL)) ++ return NULL; ++ ++ /* build filter for LDAP request */ ++ REQUEST_USER(filter, user, l->filter); ++ ++ if ( ldap_search_st( l->ld, ++ l->u_basedn, ++ LDAP_SCOPE_SUBTREE, ++ filter, ++ attrs, 0, &l->s_timeout, &res ) != LDAP_SUCCESS) { ++ ++ ldap_perror(l->ld, "ldap_search_st()"); ++ ++ free(filter); ++ free(k); ++ ++ /* XXX error on search, timeout etc.. close ask for reconnect */ ++ ldap_close(l); ++ ++ return NULL; ++ } ++ ++ /* free */ ++ free(filter); ++ ++ /* check if any results */ ++ i = ldap_count_entries(l->ld,res); ++ if (i <= 0) { ++ ldap_msgfree(res); ++ free(k); ++ return NULL; ++ } ++ ++ if (i > 1) ++ debug("[LDAP] duplicate entries, using the FIRST entry returned"); ++ ++ e = ldap_first_entry(l->ld, res); ++ k->keys = ldap_get_values_len(l->ld, e, PUBKEYATTR); ++ k->num = ldap_count_values_len(k->keys); ++ ++ ldap_msgfree(res); ++ return k; ++} ++ ++ ++/* -1 if trouble ++ 0 if user is NOT member of current server group ++ 1 if user IS MEMBER of current server group ++ */ ++int ldap_ismember(ldap_opt_t * l, const char * user) { ++ LDAPMessage *res; ++ char * filter; ++ int i; ++ ++ if ((!l->sgroup) || !(l->g_basedn)) ++ return 1; ++ ++ /* Am i still connected ? RETRY n times */ ++ /* XXX TODO: setup some conf value for retrying */ ++ if (!(l->flags & FLAG_CONNECTED)) ++ for (i = 0 ; i < 2 ; i++) ++ if (ldap_connect(l) == 0) ++ break; ++ ++ /* quick check for attempts to be evil */ ++ if ((strchr(user, '(') != NULL) || (strchr(user, ')') != NULL) || ++ (strchr(user, '*') != NULL) || (strchr(user, '\\') != NULL)) ++ return FAILURE; ++ ++ /* build filter for LDAP request */ ++ REQUEST_GROUP(filter, l->fgroup, user); ++ ++ if (ldap_search_st( l->ld, ++ l->g_basedn, ++ LDAP_SCOPE_SUBTREE, ++ filter, ++ NULL, 0, &l->s_timeout, &res) != LDAP_SUCCESS) { ++ ++ ldap_perror(l->ld, "ldap_search_st()"); ++ ++ free(filter); ++ ++ /* XXX error on search, timeout etc.. close ask for reconnect */ ++ ldap_close(l); ++ ++ return FAILURE; ++ } ++ ++ free(filter); ++ ++ /* check if any results */ ++ if (ldap_count_entries(l->ld, res) > 0) { ++ ldap_msgfree(res); ++ return 1; ++ } ++ ++ ldap_msgfree(res); ++ return 0; ++} ++ ++/* ++ * ldap.conf simple parser ++ * XXX TODO: sanity checks ++ * must either ++ * - free the previous ldap_opt_before replacing entries ++ * - free each necessary previously parsed elements ++ * ret: ++ * -1 on FAILURE, 0 on SUCCESS ++ */ ++int ldap_parse_lconf(ldap_opt_t * l) { ++ FILE * lcd; /* ldap.conf descriptor */ ++ char buf[BUFSIZ]; ++ char * s = NULL, * k = NULL, * v = NULL; ++ int li, len; ++ ++ lcd = fopen (l->l_conf, "r"); ++ if (lcd == NULL) { ++ /* debug("Cannot open %s", l->l_conf); */ ++ perror("ldap_parse_lconf()"); ++ return FAILURE; ++ } ++ ++ while (fgets (buf, sizeof (buf), lcd) != NULL) { ++ ++ if (*buf == '\n' || *buf == '#') ++ continue; ++ ++ k = buf; ++ v = k; ++ while (*v != '\0' && *v != ' ' && *v != '\t') ++ v++; ++ ++ if (*v == '\0') ++ continue; ++ ++ *(v++) = '\0'; ++ ++ while (*v == ' ' || *v == '\t') ++ v++; ++ ++ li = strlen (v) - 1; ++ while (v[li] == ' ' || v[li] == '\t' || v[li] == '\n') ++ --li; ++ v[li + 1] = '\0'; ++ ++ if (!strcasecmp (k, "uri")) { ++ if ((l->servers = ldap_parse_servers(v)) == NULL) { ++ fatal("error in ldap servers"); ++ return FAILURE; ++ } ++ ++ } ++ else if (!strcasecmp (k, "base")) { ++ s = strchr (v, '?'); ++ if (s != NULL) { ++ len = s - v; ++ l->u_basedn = malloc (len + 1); ++ strncpy (l->u_basedn, v, len); ++ l->u_basedn[len] = '\0'; ++ } else { ++ l->u_basedn = strdup (v); ++ } ++ } ++ else if (!strcasecmp (k, "binddn")) { ++ l->binddn = strdup (v); ++ } ++ else if (!strcasecmp (k, "bindpw")) { ++ l->bindpw = strdup (v); ++ } ++ else if (!strcasecmp (k, "timelimit")) { ++ l->s_timeout.tv_sec = atoi (v); ++ } ++ else if (!strcasecmp (k, "bind_timelimit")) { ++ l->b_timeout.tv_sec = atoi (v); ++ } ++ else if (!strcasecmp (k, "ssl")) { ++ if (!strcasecmp (v, "start_tls")) ++ l->tls = 1; ++ } ++ } ++ ++ fclose (lcd); ++ return SUCCESS; ++} ++ ++#endif /* WITH_LDAP_PUBKEY */ +diff -Naurp openssh-5.4p1/ldapauth.h openssh-5.4p1.oden/ldapauth.h +--- openssh-5.4p1/ldapauth.h 1970-01-01 01:00:00.000000000 +0100 ++++ openssh-5.4p1.oden/ldapauth.h 2010-03-08 12:17:30.974381643 +0100 +@@ -0,0 +1,124 @@ ++/* ++ * $Id: openssh-lpk-4.3p1-0.3.7.patch,v 1.3 2006/04/18 15:29:09 eau Exp $ ++ */ ++ ++/* ++ * ++ * Copyright (c) 2005, Eric AUGE ++ * All rights reserved. ++ * ++ * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: ++ * ++ * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. ++ * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. ++ * Neither the name of the phear.org nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. ++ * ++ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, ++ * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. ++ * IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, ++ * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; ++ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, ++ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ++ * ++ * ++ */ ++ ++#ifndef LDAPAUTH_H ++#define LDAPAUTH_H ++ ++#define LDAP_DEPRECATED 1 ++ ++#include ++#include ++#include ++#include ++ ++/* tokens in use for config */ ++#define _DEFAULT_LPK_TOKEN "UseLPK" ++#define _DEFAULT_SRV_TOKEN "LpkServers" ++#define _DEFAULT_USR_TOKEN "LpkUserDN" ++#define _DEFAULT_GRP_TOKEN "LpkGroupDN" ++#define _DEFAULT_BDN_TOKEN "LpkBindDN" ++#define _DEFAULT_BPW_TOKEN "LpkBindPw" ++#define _DEFAULT_MYG_TOKEN "LpkServerGroup" ++#define _DEFAULT_FIL_TOKEN "LpkFilter" ++#define _DEFAULT_TLS_TOKEN "LpkForceTLS" ++#define _DEFAULT_BTI_TOKEN "LpkBindTimelimit" ++#define _DEFAULT_STI_TOKEN "LpkSearchTimelimit" ++#define _DEFAULT_LDP_TOKEN "LpkLdapConf" ++ ++/* default options */ ++#define _DEFAULT_LPK_ON 0 ++#define _DEFAULT_LPK_SERVERS NULL ++#define _DEFAULT_LPK_UDN NULL ++#define _DEFAULT_LPK_GDN NULL ++#define _DEFAULT_LPK_BINDDN NULL ++#define _DEFAULT_LPK_BINDPW NULL ++#define _DEFAULT_LPK_SGROUP NULL ++#define _DEFAULT_LPK_FILTER NULL ++#define _DEFAULT_LPK_TLS -1 ++#define _DEFAULT_LPK_BTIMEOUT 10 ++#define _DEFAULT_LPK_STIMEOUT 10 ++#define _DEFAULT_LPK_LDP NULL ++ ++/* flags */ ++#define FLAG_EMPTY 0x00000000 ++#define FLAG_CONNECTED 0x00000001 ++ ++/* flag macros */ ++#define FLAG_SET_EMPTY(x) x&=(FLAG_EMPTY) ++#define FLAG_SET_CONNECTED(x) x|=(FLAG_CONNECTED) ++#define FLAG_SET_DISCONNECTED(x) x&=~(FLAG_CONNECTED) ++ ++/* defines */ ++#define FAILURE -1 ++#define SUCCESS 0 ++#define PUBKEYATTR "sshPublicKey" ++ ++/* ++ * ++ * defined files path ++ * (should be relocated to pathnames.h, ++ * if one day it's included within the tree) ++ * ++ */ ++#define _PATH_LDAP_CONFIG_FILE "/etc/ldap.conf" ++ ++/* structures */ ++typedef struct ldap_options { ++ int on; /* Use it or NOT */ ++ LDAP * ld; /* LDAP file desc */ ++ char * servers; /* parsed servers for ldaplib failover handling */ ++ char * u_basedn; /* user basedn */ ++ char * g_basedn; /* group basedn */ ++ char * binddn; /* binddn */ ++ char * bindpw; /* bind password */ ++ char * sgroup; /* server group */ ++ char * fgroup; /* group filter */ ++ char * filter; /* additional filter */ ++ char * l_conf; /* use ldap.conf */ ++ int tls; /* TLS only */ ++ struct timeval b_timeout; /* bind timeout */ ++ struct timeval s_timeout; /* search timeout */ ++ unsigned int flags; /* misc flags (reconnection, future use?) */ ++} ldap_opt_t; ++ ++typedef struct ldap_keys { ++ struct berval ** keys; /* the public keys retrieved */ ++ unsigned int num; /* number of keys */ ++} ldap_key_t; ++ ++ ++/* function headers */ ++void ldap_close(ldap_opt_t *); ++int ldap_connect(ldap_opt_t *); ++char * ldap_parse_groups(const char *); ++char * ldap_parse_servers(const char *); ++void ldap_options_print(ldap_opt_t *); ++void ldap_options_free(ldap_opt_t *); ++void ldap_keys_free(ldap_key_t *); ++int ldap_parse_lconf(ldap_opt_t *); ++ldap_key_t * ldap_getuserkey(ldap_opt_t *, const char *); ++int ldap_ismember(ldap_opt_t *, const char *); ++ ++#endif +diff -Naurp openssh-5.4p1/lpk-user-example.txt openssh-5.4p1.oden/lpk-user-example.txt +--- openssh-5.4p1/lpk-user-example.txt 1970-01-01 01:00:00.000000000 +0100 ++++ openssh-5.4p1.oden/lpk-user-example.txt 2010-03-08 12:17:30.975381130 +0100 +@@ -0,0 +1,117 @@ ++ ++Post to ML -> User Made Quick Install Doc. ++Contribution from John Lane ++ ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ++ ++OpenSSH LDAP keystore Patch ++=========================== ++ ++NOTE: these notes are a transcript of a specific installation ++ they work for me, your specifics may be different! ++ from John Lane March 17th 2005 john@lane.uk.net ++ ++This is a patch to OpenSSH 4.0p1 to allow it to obtain users' public keys ++from their LDAP record as an alternative to ~/.ssh/authorized_keys. ++ ++(Assuming here that necessary build stuff is in $BUILD) ++ ++cd $BUILD/openssh-4.0p1 ++patch -Np1 -i $BUILD/openssh-lpk-4.0p1-0.3.patch ++mkdir -p /var/empty && ++./configure --prefix=/usr --sysconfdir=/etc/ssh \ ++ --libexecdir=/usr/sbin --with-md5-passwords --with-pam \ ++ --with-libs="-lldap" --with-cppflags="-DWITH_LDAP_PUBKEY" ++Now do. ++make && ++make install ++ ++Add the following config to /etc/ssh/ssh_config ++UseLPK yes ++LpkServers ldap://myhost.mydomain.com ++LpkUserDN ou=People,dc=mydomain,dc=com ++ ++We need to tell sshd about the SSL keys during boot, as root's ++environment does not exist at that time. Edit /etc/rc.d/init.d/sshd. ++Change the startup code from this: ++ echo "Starting SSH Server..." ++ loadproc /usr/sbin/sshd ++ ;; ++to this: ++ echo "Starting SSH Server..." ++ LDAPRC="/root/.ldaprc" loadproc /usr/sbin/sshd ++ ;; ++ ++Re-start the sshd daemon: ++/etc/rc.d/init.d/sshd restart ++ ++Install the additional LDAP schema ++cp $BUILD/openssh-lpk-0.2.schema /etc/openldap/schema/openssh.schema ++ ++Now add the openSSH LDAP schema to /etc/openldap/slapd.conf: ++Add the following to the end of the existing block of schema includes ++include /etc/openldap/schema/openssh.schema ++ ++Re-start the LDAP server: ++/etc/rc.d/init.d/slapd restart ++ ++To add one or more public keys to a user, eg "testuser" : ++ldapsearch -x -W -Z -LLL -b "uid=testuser,ou=People,dc=mydomain,dc=com" -D ++"uid=testuser,ou=People,dc=mydomain,dc=com" > /tmp/testuser ++ ++append the following to this /tmp/testuser file ++objectclass: ldapPublicKey ++sshPublicKey: ssh-rsa ++AAAAB3NzaC1yc2EAAAABJQAAAIB3dsrwqXqD7E4zYYrxwdDKBUQxKMioXy9pxFVai64kAPxjU9KS ++qIo7QfkjslfsjflksjfldfkjsldfjLX/5zkzRmT28I5piGzunPv17S89z8XwSsuAoR1t86t+5dlI ++7eZE/gVbn2UQkQq7+kdDTS2yXV6VnC52N/kKLG3ciBkBAw== General Purpose RSA Key ++ ++Then do a modify: ++ldapmodify -x -D "uid=testuser,ou=People,dc=mydomain,dc=com" -W -f ++/tmp/testuser -Z ++Enter LDAP Password: ++modifying entry "uid=testuser,ou=People,dc=mydomain,dc=com" ++And check the modify is ok: ++ldapsearch -x -W -Z -b "uid=testuser,ou=People,dc=mydomain,dc=com" -D ++"uid=testuser,ou=People,dc=mydomain,dc=com" ++Enter LDAP Password: ++# extended LDIF ++# ++# LDAPv3 ++# base with scope sub ++# filter: (objectclass=*) ++# requesting: ALL ++# ++ ++# testuser, People, mydomain.com ++dn: uid=testuser,ou=People,dc=mydomain,dc=com ++uid: testuser ++cn: testuser ++objectClass: account ++objectClass: posixAccount ++objectClass: top ++objectClass: shadowAccount ++objectClass: ldapPublicKey ++shadowLastChange: 12757 ++shadowMax: 99999 ++shadowWarning: 7 ++loginShell: /bin/bash ++uidNumber: 9999 ++gidNumber: 501 ++homeDirectory: /home/testuser ++userPassword:: e1NTSEF9UDgwV1hnM1VjUDRJK0k1YnFiL1d4ZUJObXlZZ3Z3UTU= ++sshPublicKey: ssh-rsa ++AAAAB3NzaC1yc2EAAAABJQAAAIB3dsrwqXqD7E4zYYrxwdDKBUQxKMioXy9pxFVai64kAPxjU9KSqIo7QfkjslfsjflksjfldfkjsldfjLX/5zkzRmT28I5piGzunPv17S89z ++8XwSsuAoR1t86t+5dlI7eZE/gVbn2UQkQq7+kdDTS2yXV6VnC52N/kKLG3ciBkBAw== General Purpose RSA Key ++ ++# search result ++search: 3 ++result: 0 Success ++ ++# numResponses: 2 ++# numEntries: 1 ++ ++Now start a ssh session to user "testuser" from usual ssh client (e.g. ++puTTY). Login should succeed. ++ ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +diff -Naurp openssh-5.4p1/Makefile.in openssh-5.4p1.oden/Makefile.in +--- openssh-5.4p1/Makefile.in 2010-02-24 08:18:51.000000000 +0100 ++++ openssh-5.4p1.oden/Makefile.in 2010-03-08 12:18:42.727318804 +0100 +@@ -90,7 +90,7 @@ SSHDOBJS=sshd.o auth-rhosts.o auth-passw + auth-krb5.o \ + auth2-gss.o gss-serv.o gss-serv-krb5.o \ + loginrec.o auth-pam.o auth-shadow.o auth-sia.o md5crypt.o \ +- audit.o audit-bsm.o platform.o sftp-server.o sftp-common.o \ ++ audit.o audit-bsm.o platform.o ldapauth.o sftp-server.o sftp-common.o \ + roaming_common.o roaming_serv.o + + MANPAGES = moduli.5.out scp.1.out ssh-add.1.out ssh-agent.1.out ssh-keygen.1.out ssh-keyscan.1.out ssh.1.out sshd.8.out sftp-server.8.out sftp.1.out ssh-rand-helper.8.out ssh-keysign.8.out ssh-pkcs11-helper.8.out sshd_config.5.out ssh_config.5.out +diff -Naurp openssh-5.4p1/openssh-lpk_openldap.schema openssh-5.4p1.oden/openssh-lpk_openldap.schema +--- openssh-5.4p1/openssh-lpk_openldap.schema 1970-01-01 01:00:00.000000000 +0100 ++++ openssh-5.4p1.oden/openssh-lpk_openldap.schema 2010-03-08 12:17:30.976381509 +0100 +@@ -0,0 +1,19 @@ ++# ++# LDAP Public Key Patch schema for use with openssh-ldappubkey ++# Author: Eric AUGE ++# ++# Based on the proposal of : Mark Ruijter ++# ++ ++ ++# octetString SYNTAX ++attributetype ( 1.3.6.1.4.1.24552.500.1.1.1.13 NAME 'sshPublicKey' ++ DESC 'MANDATORY: OpenSSH Public key' ++ EQUALITY octetStringMatch ++ SYNTAX 1.3.6.1.4.1.1466.115.121.1.40 ) ++ ++# printableString SYNTAX yes|no ++objectclass ( 1.3.6.1.4.1.24552.500.1.1.2.0 NAME 'ldapPublicKey' SUP top AUXILIARY ++ DESC 'MANDATORY: OpenSSH LPK objectclass' ++ MUST ( sshPublicKey $ uid ) ++ ) +diff -Naurp openssh-5.4p1/openssh-lpk_sun.schema openssh-5.4p1.oden/openssh-lpk_sun.schema +--- openssh-5.4p1/openssh-lpk_sun.schema 1970-01-01 01:00:00.000000000 +0100 ++++ openssh-5.4p1.oden/openssh-lpk_sun.schema 2010-03-08 12:17:30.976381509 +0100 +@@ -0,0 +1,21 @@ ++# ++# LDAP Public Key Patch schema for use with openssh-ldappubkey ++# Author: Eric AUGE ++# ++# Schema for Sun Directory Server. ++# Based on the original schema, modified by Stefan Fischer. ++# ++ ++dn: cn=schema ++ ++# octetString SYNTAX ++attributeTypes: ( 1.3.6.1.4.1.24552.500.1.1.1.13 NAME 'sshPublicKey' ++ DESC 'MANDATORY: OpenSSH Public key' ++ EQUALITY octetStringMatch ++ SYNTAX 1.3.6.1.4.1.1466.115.121.1.40 ) ++ ++# printableString SYNTAX yes|no ++objectClasses: ( 1.3.6.1.4.1.24552.500.1.1.2.0 NAME 'ldapPublicKey' SUP top AUXILIARY ++ DESC 'MANDATORY: OpenSSH LPK objectclass' ++ MUST ( sshPublicKey $ uid ) ++ ) +diff -Naurp openssh-5.4p1/README.lpk openssh-5.4p1.oden/README.lpk +--- openssh-5.4p1/README.lpk 1970-01-01 01:00:00.000000000 +0100 ++++ openssh-5.4p1.oden/README.lpk 2010-03-08 12:17:30.977381495 +0100 +@@ -0,0 +1,267 @@ ++OpenSSH LDAP PUBLIC KEY PATCH ++Copyright (c) 2003 Eric AUGE (eau@phear.org) ++All rights reserved. ++ ++Redistribution and use in source and binary forms, with or without ++modification, are permitted provided that the following conditions ++are met: ++1. Redistributions of source code must retain the above copyright ++ notice, this list of conditions and the following disclaimer. ++2. Redistributions in binary form must reproduce the above copyright ++ notice, this list of conditions and the following disclaimer in the ++ documentation and/or other materials provided with the distribution. ++3. The name of the author may not be used to endorse or promote products ++ derived from this software without specific prior written permission. ++ ++THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR ++IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES ++OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. ++IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, ++INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT ++NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, ++DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY ++THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT ++(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF ++THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ++ ++purposes of this patch: ++ ++This patch would help to have authentication centralization policy ++using ssh public key authentication. ++This patch could be an alternative to other "secure" authentication system ++working in a similar way (Kerberos, SecurID, etc...), except the fact ++that it's based on OpenSSH and its public key abilities. ++ ++>> FYI: << ++'uid': means unix accounts existing on the current server ++'lpkServerGroup:' mean server group configured on the current server ('lpkServerGroup' in sshd_config) ++ ++example schema: ++ ++ ++ server1 (uid: eau,rival,toto) (lpkServerGroup: unix) ++ ___________ / ++ / \ --- - server3 (uid: eau, titi) (lpkServerGroup: unix) ++ | LDAP Server | \ ++ | eau ,rival | server2 (uid: rival, eau) (lpkServerGroup: unix) ++ | titi ,toto | ++ | userx,.... | server5 (uid: eau) (lpkServerGroup: mail) ++ \___________/ \ / ++ ----- - server4 (uid: eau, rival) (no group configured) ++ \ ++ etc... ++ ++- WHAT WE NEED : ++ ++ * configured LDAP server somewhere on the network (i.e. OpenLDAP) ++ * patched sshd (with this patch ;) ++ * LDAP user(/group) entry (look at users.ldif (& groups.ldif)): ++ User entry: ++ - attached to the 'ldapPublicKey' objectclass ++ - attached to the 'posixAccount' objectclass ++ - with a filled 'sshPublicKey' attribute ++ Example: ++ dn: uid=eau,ou=users,dc=cuckoos,dc=net ++ objectclass: top ++ objectclass: person ++ objectclass: organizationalPerson ++ objectclass: posixAccount ++ objectclass: ldapPublicKey ++ description: Eric AUGE Account ++ userPassword: blah ++ cn: Eric AUGE ++ sn: Eric AUGE ++ uid: eau ++ uidNumber: 1034 ++ gidNumber: 1 ++ homeDirectory: /export/home/eau ++ sshPublicKey: ssh-dss AAAAB3... ++ sshPublicKey: ssh-dss AAAAM5... ++ ++ Group entry: ++ - attached to the 'posixGroup' objectclass ++ - with a 'cn' groupname attribute ++ - with multiple 'memberUid' attributes filled with usernames allowed in this group ++ Example: ++ # few members ++ dn: cn=unix,ou=groups,dc=cuckoos,dc=net ++ objectclass: top ++ objectclass: posixGroup ++ description: Unix based servers group ++ cn: unix ++ gidNumber: 1002 ++ memberUid: eau ++ memberUid: user1 ++ memberUid: user2 ++ ++ ++- HOW IT WORKS : ++ ++ * without patch ++ If a user wants to authenticate to log in a server the sshd, will first look for authentication method allowed (RSAauth,kerberos,etc..) ++ and if RSAauth and tickets based auth fails, it will fallback to standard password authentication (if enabled). ++ ++ * with the patch ++ If a user want to authenticate to log in a server, the sshd will first look for auth method including LDAP pubkey, if the ldappubkey options is enabled. ++ It will do an ldapsearch to get the public key directly from the LDAP instead of reading it from the server filesystem. ++ (usually in $HOME/.ssh/authorized_keys) ++ ++ If groups are enabled, it will also check if the user that wants to login is in the group of the server he is trying to log into. ++ If it fails, it falls back on RSA auth files ($HOME/.ssh/authorized_keys), etc.. and finally to standard password authentication (if enabled). ++ ++ 7 tokens are added to sshd_config : ++ # here is the new patched ldap related tokens ++ # entries in your LDAP must be posixAccount & strongAuthenticationUser & posixGroup ++ UseLPK yes # look the pub key into LDAP ++ LpkServers ldap://10.31.32.5/ ldap://10.31.32.4 ldap://10.31.32.3 # which LDAP server for users ? (URL format) ++ LpkUserDN ou=users,dc=foobar,dc=net # which base DN for users ? ++ LpkGroupDN ou=groups,dc=foobar,dc=net # which base DN for groups ? ++ LpkBindDN cn=manager,dc=foobar,dc=net # which bind DN ? ++ LpkBindPw asecret # bind DN credidentials ++ LpkServerGroup agroupname # the group the server is part of ++ ++ Right now i'm using anonymous binding to get public keys, because getting public keys of someone doesn't impersonate him¸ but there is some ++ flaws you have to take care of. ++ ++- HOW TO INSERT A USER/KEY INTO AN LDAP ENTRY ++ ++ * my way (there is plenty :) ++ - create ldif file (i.e. users.ldif) ++ - cat ~/.ssh/id_dsa.pub OR cat ~/.ssh/id_rsa.pub OR cat ~/.ssh/identity.pub ++ - my way in 4 steps : ++ Example: ++ ++ # you add this to the user entry in the LDIF file : ++ [...] ++ objectclass: posixAccount ++ objectclass: ldapPublicKey ++ [...] ++ sshPubliKey: ssh-dss AAAABDh12DDUR2... ++ [...] ++ ++ # insert your entry and you're done :) ++ ldapadd -D balblabla -w bleh < file.ldif ++ ++ all standard options can be present in the 'sshPublicKey' attribute. ++ ++- WHY : ++ ++ Simply because, i was looking for a way to centralize all sysadmins authentication, easily, without completely using LDAP ++ as authentication method (like pam_ldap etc..). ++ ++ After looking into Kerberos, SecurID, and other centralized secure authentications systems, the use of RSA and LDAP to get ++ public key for authentication allows us to control who has access to which server (the user needs an account and to be in 'strongAuthenticationUser' ++ objectclass within LDAP and part of the group the SSH server is in). ++ ++ Passwords update are no longer a nightmare for a server farm (key pair passphrase is stored on each user's box and private key is locally encrypted using his passphrase ++ so each user can change it as much as he wants). ++ ++ Blocking a user account can be done directly from the LDAP (if sshd is using RSAAuth + ldap only). ++ ++- RULES : ++ Entry in the LDAP server must respect 'posixAccount' and 'ldapPublicKey' which are defined in core.schema. ++ and the additionnal lpk.schema. ++ ++ This patch could allow a smooth transition between standard auth (/etc/passwd) and complete LDAP based authentication ++ (pamldap, nss_ldap, etc..). ++ ++ This can be an alternative to other (old?/expensive?) authentication methods (Kerberos/SecurID/..). ++ ++ Referring to schema at the beginning of this file if user 'eau' is only in group 'unix' ++ 'eau' would ONLY access 'server1', 'server2', 'server3' AND 'server4' BUT NOT 'server5'. ++ If you then modify the LDAP 'mail' group entry to add 'memberUid: eau' THEN user 'eau' would be able ++ to log in 'server5' (i hope you got the idea, my english is bad :). ++ ++ Each server's sshd is patched and configured to ask the public key and the group infos in the LDAP ++ server. ++ When you want to allow a new user to have access to the server parc, you just add him an account on ++ your servers, you add his public key into his entry on the LDAP server, it's done. ++ ++ Because sshds are looking public keys into the LDAP directly instead of a file ($HOME/.ssh/authorized_keys). ++ ++ When the user needs to change his passphrase he can do it directly from his workstation by changing ++ his own key set lock passphrase, and all servers are automatically aware. ++ ++ With a CAREFUL LDAP server configuration you could allow a user to add/delete/modify his own entry himself ++ so he can add/modify/delete himself his public key when needed. ++ ++­ FLAWS : ++ LDAP must be well configured, getting the public key of some user is not a problem, but if anonymous LDAP ++ allow write to users dn, somebody could replace someuser's public key by its own and impersonate some ++ of your users in all your server farm be VERY CAREFUL. ++ ++ MITM attack when sshd is requesting the public key, could lead to a compromise of your servers allowing login ++ as the impersonnated user. ++ ++ If LDAP server is down then, fallback on passwd auth. ++ ++ the ldap code part has not been well audited yet. ++ ++- LDAP USER ENTRY EXAMPLES (LDIF Format, look in users.ldif) ++ --- CUT HERE --- ++ dn: uid=jdoe,ou=users,dc=foobar,dc=net ++ objectclass: top ++ objectclass: person ++ objectclass: organizationalPerson ++ objectclass: posixAccount ++ objectclass: ldapPublicKey ++ description: My account ++ cn: John Doe ++ sn: John Doe ++ uid: jdoe ++ uidNumber: 100 ++ gidNumber: 100 ++ homeDirectory: /home/jdoe ++ sshPublicKey: ssh-dss AAAAB3NzaC1kc3MAAAEBAOvL8pREUg9wSy/8+hQJ54YF3AXkB0OZrXB.... ++ [...] ++ --- CUT HERE --- ++ ++- LDAP GROUP ENTRY EXAMPLES (LDIF Format, look in groups.ldif) ++ --- CUT HERE --- ++ dn: cn=unix,ou=groups,dc=cuckoos,dc=net ++ objectclass: top ++ objectclass: posixGroup ++ description: Unix based servers group ++ cn: unix ++ gidNumber: 1002 ++ memberUid: jdoe ++ memberUid: user1 ++ memberUid: user2 ++ [...] ++ --- CUT HERE --- ++ ++>> FYI: << ++Multiple 'sshPublicKey' in a user entry are allowed, as well as multiple 'memberUid' attributes in a group entry ++ ++- COMPILING: ++ 1. Apply the patch ++ 2. ./configure --with-your-options --with-ldap=/prefix/to/ldap_libs_and_includes ++ 3. make ++ 4. it's done. ++ ++- BLA : ++ I hope this could help, and i hope to be clear enough,, or give ideas. questions/comments/improvements are welcome. ++ ++- TODO : ++ Redesign differently. ++ ++- DOCS/LINK : ++ http://pacsec.jp/core05/psj05-barisani-en.pdf ++ http://fritz.potsdam.edu/projects/openssh-lpk/ ++ http://fritz.potsdam.edu/projects/sshgate/ ++ http://dev.inversepath.com/trac/openssh-lpk ++ http://lam.sf.net/ ( http://lam.sourceforge.net/documentation/supportedSchemas.htm ) ++ ++- CONTRIBUTORS/IDEAS/GREETS : ++ - Falk Siemonsmeier. ++ - Jacob Rief. ++ - Michael Durchgraf. ++ - frederic peters. ++ - Finlay dobbie. ++ - Stefan Fisher. ++ - Robin H. Johnson. ++ - Adrian Bridgett. ++ ++- CONTACT : ++ - Eric AUGE ++ - Andrea Barisani +diff -Naurp openssh-5.4p1/servconf.c openssh-5.4p1.oden/servconf.c +--- openssh-5.4p1/servconf.c 2010-03-04 11:53:35.000000000 +0100 ++++ openssh-5.4p1.oden/servconf.c 2010-03-08 12:21:00.400414534 +0100 +@@ -42,6 +42,10 @@ + #include "channels.h" + #include "groupaccess.h" + ++#ifdef WITH_LDAP_PUBKEY ++#include "ldapauth.h" ++#endif ++ + static void add_listen_addr(ServerOptions *, char *, int); + static void add_one_listen_addr(ServerOptions *, char *, int); + +@@ -131,6 +135,25 @@ initialize_server_options(ServerOptions + options->zero_knowledge_password_authentication = -1; + options->revoked_keys_file = NULL; + options->trusted_user_ca_keys = NULL; ++#ifdef WITH_LDAP_PUBKEY ++ /* XXX dirty */ ++ options->lpk.ld = NULL; ++ options->lpk.on = -1; ++ options->lpk.servers = NULL; ++ options->lpk.u_basedn = NULL; ++ options->lpk.g_basedn = NULL; ++ options->lpk.binddn = NULL; ++ options->lpk.bindpw = NULL; ++ options->lpk.sgroup = NULL; ++ options->lpk.filter = NULL; ++ options->lpk.fgroup = NULL; ++ options->lpk.l_conf = NULL; ++ options->lpk.tls = -1; ++ options->lpk.b_timeout.tv_sec = -1; ++ options->lpk.s_timeout.tv_sec = -1; ++ options->lpk.flags = FLAG_EMPTY; ++#endif ++ + } + + void +@@ -265,6 +288,32 @@ fill_default_server_options(ServerOption + options->permit_tun = SSH_TUNMODE_NO; + if (options->zero_knowledge_password_authentication == -1) + options->zero_knowledge_password_authentication = 0; ++#ifdef WITH_LDAP_PUBKEY ++ if (options->lpk.on == -1) ++ options->lpk.on = _DEFAULT_LPK_ON; ++ if (options->lpk.servers == NULL) ++ options->lpk.servers = _DEFAULT_LPK_SERVERS; ++ if (options->lpk.u_basedn == NULL) ++ options->lpk.u_basedn = _DEFAULT_LPK_UDN; ++ if (options->lpk.g_basedn == NULL) ++ options->lpk.g_basedn = _DEFAULT_LPK_GDN; ++ if (options->lpk.binddn == NULL) ++ options->lpk.binddn = _DEFAULT_LPK_BINDDN; ++ if (options->lpk.bindpw == NULL) ++ options->lpk.bindpw = _DEFAULT_LPK_BINDPW; ++ if (options->lpk.sgroup == NULL) ++ options->lpk.sgroup = _DEFAULT_LPK_SGROUP; ++ if (options->lpk.filter == NULL) ++ options->lpk.filter = _DEFAULT_LPK_FILTER; ++ if (options->lpk.tls == -1) ++ options->lpk.tls = _DEFAULT_LPK_TLS; ++ if (options->lpk.b_timeout.tv_sec == -1) ++ options->lpk.b_timeout.tv_sec = _DEFAULT_LPK_BTIMEOUT; ++ if (options->lpk.s_timeout.tv_sec == -1) ++ options->lpk.s_timeout.tv_sec = _DEFAULT_LPK_STIMEOUT; ++ if (options->lpk.l_conf == NULL) ++ options->lpk.l_conf = _DEFAULT_LPK_LDP; ++#endif + + /* Turn privilege separation on by default */ + if (use_privsep == -1) +@@ -312,6 +361,12 @@ typedef enum { + sZeroKnowledgePasswordAuthentication, sHostCertificate, + sRevokedKeys, sTrustedUserCAKeys, + sDeprecated, sUnsupported ++#ifdef WITH_LDAP_PUBKEY ++ ,sLdapPublickey, sLdapServers, sLdapUserDN ++ ,sLdapGroupDN, sBindDN, sBindPw, sMyGroup ++ ,sLdapFilter, sForceTLS, sBindTimeout ++ ,sSearchTimeout, sLdapConf ++#endif + } ServerOpCodes; + + #define SSHCFG_GLOBAL 0x01 /* allowed in main section of sshd_config */ +@@ -422,6 +477,20 @@ static struct { + { "clientalivecountmax", sClientAliveCountMax, SSHCFG_GLOBAL }, + { "authorizedkeysfile", sAuthorizedKeysFile, SSHCFG_GLOBAL }, + { "authorizedkeysfile2", sAuthorizedKeysFile2, SSHCFG_GLOBAL }, ++#ifdef WITH_LDAP_PUBKEY ++ { _DEFAULT_LPK_TOKEN, sLdapPublickey, SSHCFG_GLOBAL }, ++ { _DEFAULT_SRV_TOKEN, sLdapServers, SSHCFG_GLOBAL }, ++ { _DEFAULT_USR_TOKEN, sLdapUserDN, SSHCFG_GLOBAL }, ++ { _DEFAULT_GRP_TOKEN, sLdapGroupDN, SSHCFG_GLOBAL }, ++ { _DEFAULT_BDN_TOKEN, sBindDN, SSHCFG_GLOBAL }, ++ { _DEFAULT_BPW_TOKEN, sBindPw, SSHCFG_GLOBAL }, ++ { _DEFAULT_MYG_TOKEN, sMyGroup, SSHCFG_GLOBAL }, ++ { _DEFAULT_FIL_TOKEN, sLdapFilter, SSHCFG_GLOBAL }, ++ { _DEFAULT_TLS_TOKEN, sForceTLS, SSHCFG_GLOBAL }, ++ { _DEFAULT_BTI_TOKEN, sBindTimeout, SSHCFG_GLOBAL }, ++ { _DEFAULT_STI_TOKEN, sSearchTimeout, SSHCFG_GLOBAL }, ++ { _DEFAULT_LDP_TOKEN, sLdapConf, SSHCFG_GLOBAL }, ++#endif + { "useprivilegeseparation", sUsePrivilegeSeparation, SSHCFG_GLOBAL}, + { "acceptenv", sAcceptEnv, SSHCFG_GLOBAL }, + { "permittunnel", sPermitTunnel, SSHCFG_GLOBAL }, +@@ -1349,6 +1418,107 @@ process_server_config_line(ServerOptions + while (arg) + arg = strdelim(&cp); + break; ++#ifdef WITH_LDAP_PUBKEY ++ case sLdapPublickey: ++ intptr = &options->lpk.on; ++ goto parse_flag; ++ case sLdapServers: ++ /* arg = strdelim(&cp); */ ++ p = line; ++ while(*p++); ++ arg = p; ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: missing ldap server",filename,linenum); ++ arg[strlen(arg)] = '\0'; ++ if ((options->lpk.servers = ldap_parse_servers(arg)) == NULL) ++ fatal("%s line %d: error in ldap servers", filename, linenum); ++ memset(arg,0,strlen(arg)); ++ break; ++ case sLdapUserDN: ++ arg = cp; ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: missing ldap server",filename,linenum); ++ arg[strlen(arg)] = '\0'; ++ options->lpk.u_basedn = xstrdup(arg); ++ memset(arg,0,strlen(arg)); ++ break; ++ case sLdapGroupDN: ++ arg = cp; ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: missing ldap server",filename,linenum); ++ arg[strlen(arg)] = '\0'; ++ options->lpk.g_basedn = xstrdup(arg); ++ memset(arg,0,strlen(arg)); ++ break; ++ case sBindDN: ++ arg = cp; ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: missing binddn",filename,linenum); ++ arg[strlen(arg)] = '\0'; ++ options->lpk.binddn = xstrdup(arg); ++ memset(arg,0,strlen(arg)); ++ break; ++ case sBindPw: ++ arg = cp; ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: missing bindpw",filename,linenum); ++ arg[strlen(arg)] = '\0'; ++ options->lpk.bindpw = xstrdup(arg); ++ memset(arg,0,strlen(arg)); ++ break; ++ case sMyGroup: ++ arg = cp; ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: missing groupname",filename, linenum); ++ arg[strlen(arg)] = '\0'; ++ options->lpk.sgroup = xstrdup(arg); ++ if (options->lpk.sgroup) ++ options->lpk.fgroup = ldap_parse_groups(options->lpk.sgroup); ++ memset(arg,0,strlen(arg)); ++ break; ++ case sLdapFilter: ++ arg = cp; ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: missing filter",filename, linenum); ++ arg[strlen(arg)] = '\0'; ++ options->lpk.filter = xstrdup(arg); ++ memset(arg,0,strlen(arg)); ++ break; ++ case sForceTLS: ++ intptr = &options->lpk.tls; ++ arg = strdelim(&cp); ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: missing yes/no argument.", ++ filename, linenum); ++ value = 0; /* silence compiler */ ++ if (strcmp(arg, "yes") == 0) ++ value = 1; ++ else if (strcmp(arg, "no") == 0) ++ value = 0; ++ else if (strcmp(arg, "try") == 0) ++ value = -1; ++ else ++ fatal("%s line %d: Bad yes/no argument: %s", ++ filename, linenum, arg); ++ if (*intptr == -1) ++ *intptr = value; ++ break; ++ case sBindTimeout: ++ intptr = (int *) &options->lpk.b_timeout.tv_sec; ++ goto parse_int; ++ case sSearchTimeout: ++ intptr = (int *) &options->lpk.s_timeout.tv_sec; ++ goto parse_int; ++ break; ++ case sLdapConf: ++ arg = cp; ++ if (!arg || *arg == '\0') ++ fatal("%s line %d: missing LpkLdapConf", filename, linenum); ++ arg[strlen(arg)] = '\0'; ++ options->lpk.l_conf = xstrdup(arg); ++ memset(arg, 0, strlen(arg)); ++ break; ++#endif + + default: + fatal("%s line %d: Missing handler for opcode %s (%d)", +diff -Naurp openssh-5.4p1/servconf.h openssh-5.4p1.oden/servconf.h +--- openssh-5.4p1/servconf.h 2010-03-04 11:53:35.000000000 +0100 ++++ openssh-5.4p1.oden/servconf.h 2010-03-08 12:17:30.980381555 +0100 +@@ -16,6 +16,10 @@ + #ifndef SERVCONF_H + #define SERVCONF_H + ++#ifdef WITH_LDAP_PUBKEY ++#include "ldapauth.h" ++#endif ++ + #define MAX_PORTS 256 /* Max # ports. */ + + #define MAX_ALLOW_USERS 256 /* Max # users on allow list. */ +@@ -150,6 +154,9 @@ typedef struct { + int use_pam; /* Enable auth via PAM */ + + int permit_tun; ++#ifdef WITH_LDAP_PUBKEY ++ ldap_opt_t lpk; ++#endif + + int num_permitted_opens; + +diff -Naurp openssh-5.4p1/sshd.c openssh-5.4p1.oden/sshd.c +--- openssh-5.4p1/sshd.c 2010-03-07 13:05:17.000000000 +0100 ++++ openssh-5.4p1.oden/sshd.c 2010-03-08 12:17:30.981381500 +0100 +@@ -127,6 +127,10 @@ int allow_severity; + int deny_severity; + #endif /* LIBWRAP */ + ++#ifdef WITH_LDAP_PUBKEY ++#include "ldapauth.h" ++#endif ++ + #ifndef O_NOCTTY + #define O_NOCTTY 0 + #endif +@@ -1530,6 +1534,16 @@ main(int ac, char **av) + exit(1); + } + ++#ifdef WITH_LDAP_PUBKEY ++ /* ldap_options_print(&options.lpk); */ ++ /* XXX initialize/check ldap connection and set *LD */ ++ if (options.lpk.on) { ++ if (options.lpk.l_conf && (ldap_parse_lconf(&options.lpk) < 0) ) ++ error("[LDAP] could not parse %s", options.lpk.l_conf); ++ if (ldap_connect(&options.lpk) < 0) ++ error("[LDAP] could not initialize ldap connection"); ++ } ++#endif + debug("sshd version %.100s", SSH_RELEASE); + + /* Store privilege separation user for later use if required. */ +diff -Naurp openssh-5.4p1/sshd_config openssh-5.4p1.oden/sshd_config +--- openssh-5.4p1/sshd_config 2009-10-11 12:51:09.000000000 +0200 ++++ openssh-5.4p1.oden/sshd_config 2010-03-08 12:17:30.982381546 +0100 +@@ -107,6 +107,21 @@ + # no default banner path + #Banner none + ++# here are the new patched ldap related tokens ++# entries in your LDAP must have posixAccount & ldapPublicKey objectclass ++#UseLPK yes ++#LpkLdapConf /etc/ldap.conf ++#LpkServers ldap://10.1.7.1/ ldap://10.1.7.2/ ++#LpkUserDN ou=users,dc=phear,dc=org ++#LpkGroupDN ou=groups,dc=phear,dc=org ++#LpkBindDN cn=Manager,dc=phear,dc=org ++#LpkBindPw secret ++#LpkServerGroup mail ++#LpkFilter (hostAccess=master.phear.org) ++#LpkForceTLS no ++#LpkSearchTimelimit 3 ++#LpkBindTimelimit 3 ++ + # override default of no subsystems + Subsystem sftp /usr/libexec/sftp-server + +diff -Naurp openssh-5.4p1/sshd_config.5 openssh-5.4p1.oden/sshd_config.5 +--- openssh-5.4p1/sshd_config.5 2010-03-05 00:41:45.000000000 +0100 ++++ openssh-5.4p1.oden/sshd_config.5 2010-03-08 12:17:30.983381553 +0100 +@@ -1043,6 +1043,62 @@ Specifies the full pathname of the + program. + The default is + .Pa /usr/X11R6/bin/xauth . ++.It Cm UseLPK ++Specifies whether LDAP public key retrieval must be used or not. It allow ++an easy centralisation of public keys within an LDAP directory. The argument must be ++.Dq yes ++or ++.Dq no . ++.It Cm LpkLdapConf ++Specifies whether LDAP Public keys should parse the specified ldap.conf file ++instead of sshd_config Tokens. The argument must be a valid path to an ldap.conf ++file like ++.Pa /etc/ldap.conf ++.It Cm LpkServers ++Specifies LDAP one or more [:space:] separated server's url the following form may be used: ++.Pp ++LpkServers ldaps://127.0.0.1 ldap://127.0.0.2 ldap://127.0.0.3 ++.It Cm LpkUserDN ++Specifies the LDAP user DN. ++.Pp ++LpkUserDN ou=users,dc=phear,dc=org ++.It Cm LpkGroupDN ++Specifies the LDAP groups DN. ++.Pp ++LpkGroupDN ou=groups,dc=phear,dc=org ++.It Cm LpkBindDN ++Specifies the LDAP bind DN to use if necessary. ++.Pp ++LpkBindDN cn=Manager,dc=phear,dc=org ++.It Cm LpkBindPw ++Specifies the LDAP bind credential. ++.Pp ++LpkBindPw secret ++.It Cm LpkServerGroup ++Specifies one or more [:space:] separated group the server is part of. ++.Pp ++LpkServerGroup unix mail prod ++.It Cm LpkFilter ++Specifies an additional LDAP filter to use for finding SSH keys ++.Pp ++LpkFilter (hostAccess=master.phear.org) ++.It Cm LpkForceTLS ++Specifies if the LDAP server connection must be tried, forced or not used. The argument must be ++.Dq yes ++or ++.Dq no ++or ++.Dq try . ++.It Cm LpkSearchTimelimit ++Sepcifies the search time limit before the search is considered over. value is ++in seconds. ++.Pp ++LpkSearchTimelimit 3 ++.It Cm LpkBindTimelimit ++Sepcifies the bind time limit before the connection is considered dead. value is ++in seconds. ++.Pp ++LpkBindTimelimit 3 + .El + .Sh TIME FORMATS + .Xr sshd 8 diff --git a/openssh-mdv_conf.diff b/openssh-mdv_conf.diff new file mode 100644 index 0000000..5f82cd6 --- /dev/null +++ b/openssh-mdv_conf.diff @@ -0,0 +1,78 @@ +--- openssh-5.7p1/ssh_config.mdv 2010-01-12 06:40:27.000000000 -0200 ++++ openssh-5.7p1/ssh_config 2011-01-29 15:40:38.000000000 -0200 +@@ -45,3 +45,17 @@ + # PermitLocalCommand no + # VisualHostKey no + # ProxyCommand ssh -q -W %h:%p gateway.example.com ++ ++Host * ++ ForwardX11 yes ++ Protocol 2,1 ++ ++ # If this option is set to yes then remote X11 clients will have full access ++ # to the original X11 display. As virtually no X11 client supports the untrusted ++ # mode correctly we set this to yes. ++ ForwardX11Trusted yes ++ ++ # Send locale-related environment variables ++ #SendEnv LANG LC_CTYPE LC_NUMERIC LC_TIME LC_COLLATE LC_MONETARY LC_MESSAGES ++ #SendEnv LC_PAPER LC_NAME LC_ADDRESS LC_TELEPHONE LC_MEASUREMENT ++ #SendEnv LC_IDENTIFICATION LC_ALL +--- openssh-5.7p1/sshd_config.mdv 2010-09-09 22:20:12.000000000 -0300 ++++ openssh-5.7p1/sshd_config 2011-01-29 15:41:11.000000000 -0200 +@@ -3,7 +3,7 @@ + # This is the sshd server system-wide configuration file. See + # sshd_config(5) for more information. + +-# This sshd was compiled with PATH=/usr/bin:/bin:/usr/sbin:/sbin ++# This sshd was compiled with PATH=_OPENSSH_PATH_ + + # The strategy used for options in the default sshd_config shipped with + # OpenSSH is to specify options with their default value where +@@ -20,9 +20,10 @@ + + # HostKey for protocol version 1 + #HostKey /etc/ssh/ssh_host_key ++HostKey /etc/ssh/ssh_host_key + # HostKeys for protocol version 2 +-#HostKey /etc/ssh/ssh_host_rsa_key +-#HostKey /etc/ssh/ssh_host_dsa_key ++HostKey /etc/ssh/ssh_host_rsa_key ++HostKey /etc/ssh/ssh_host_dsa_key + #HostKey /etc/ssh/ssh_host_ecdsa_key + + # Lifetime and size of ephemeral version 1 server key +@@ -37,7 +38,7 @@ + # Authentication: + + #LoginGraceTime 2m +-#PermitRootLogin yes ++PermitRootLogin no + #StrictModes yes + #MaxAuthTries 6 + #MaxSessions 10 +@@ -84,17 +85,22 @@ + # and ChallengeResponseAuthentication to 'no'. + #UsePAM no + ++# Accept locale-related environment variables ++AcceptEnv LANG LC_CTYPE LC_NUMERIC LC_TIME LC_COLLATE LC_MONETARY LC_MESSAGES ++AcceptEnv LC_PAPER LC_NAME LC_ADDRESS LC_TELEPHONE LC_MEASUREMENT ++AcceptEnv LC_IDENTIFICATION LC_ALL ++ + #AllowAgentForwarding yes + #AllowTcpForwarding yes + #GatewayPorts no +-#X11Forwarding no ++X11Forwarding yes + #X11DisplayOffset 10 + #X11UseLocalhost yes + #PrintMotd yes + #PrintLastLog yes + #TCPKeepAlive yes + #UseLogin no +-#UsePrivilegeSeparation yes ++UsePrivilegeSeparation yes + #PermitUserEnvironment no + #Compression delayed + #ClientAliveInterval 0 diff --git a/openssh-xinetd b/openssh-xinetd new file mode 100644 index 0000000..b7cd017 --- /dev/null +++ b/openssh-xinetd @@ -0,0 +1,16 @@ +# default: off +# description: sshd server, xinetd version. \ +# Don't run the standalone version if you run \ +# this. +service ssh +{ + disable = yes + socket_type = stream + wait = no + user = root + server = /usr/sbin/sshd + server_args = -i + log_on_success += DURATION USERID + log_on_failure += USERID + nice = 10 +} diff --git a/openssh.spec b/openssh.spec new file mode 100644 index 0000000..a19d84a --- /dev/null +++ b/openssh.spec @@ -0,0 +1,1236 @@ +## Do not apply any unauthorized patches to this package! +## - vdanen 05/18/01 +## + +# Version of ssh-askpass +%define aversion 1.2.4.1 +# Version of watchdog patch +%define wversion 4.4p1 + +# Version of the hpn patch +%define hpnver 13v6 + +# overrides +%define build_skey 0 +%define build_krb5 1 +%define build_watchdog 0 +%define build_x11askpass 1 +%define build_gnomeaskpass 1 +%define build_ldap 0 +%define build_sftpcontrol 0 +%define build_hpn 0 +%define build_audit 0 +%define build_libedit 1 + +%{?_with_skey: %{expand: %%global build_skey 1}} +%{?_without_skey: %{expand: %%global build_skey 0}} +%{?_with_krb5: %{expand: %%global build_krb5 1}} +%{?_without_krb5: %{expand: %%global build_krb5 0}} +%{?_with_watchdog: %{expand: %%global build_watchdog 1}} +%{?_without_watchdog: %{expand: %%global build_watchdog 0}} +%{?_with_x11askpass: %{expand: %%global build_x11askpass 1}} +%{?_without_x11askpass: %{expand: %%global build_x11askpass 0}} +%{?_with_gnomeaskpass: %{expand: %%global build_gnomeaskpass 1}} +%{?_without_gnomeaskpass: %{expand: %%global build_gnomeaskpass 0}} +%{?_with_ldap: %{expand: %%global build_ldap 1}} +%{?_without_ldap: %{expand: %%global build_ldap 0}} +%{?_with_sftpcontrol: %{expand: %%global build_sftpcontrol 1}} +%{?_without_sftpcontrol: %{expand: %%global build_sftpcontrol 0}} +%{?_with_hpn: %{expand: %%global build_hpn 1}} +%{?_without_hpn: %{expand: %%global build_hpn 0}} +%{?_with_audit: %{expand: %%global build_audit 1}} +%{?_without_audit: %{expand: %%global build_audit 0}} +%{?_with_libedit: %{expand: %%global build_libedit 1}} +%{?_without_libedit: %{expand: %%global build_libedit 0}} + +%if %{mdkversion} < 200700 +%define OPENSSH_PATH "/usr/local/bin:/bin:%{_bindir}:/usr/X11R6/bin" +%define XAUTH /usr/X11R6/bin/xauth +%else +%define OPENSSH_PATH "/usr/local/bin:/bin:%{_bindir}" +%define XAUTH %{_bindir}/xauth +%endif + +Summary: OpenSSH free Secure Shell (SSH) implementation +Name: openssh +Version: 5.8p2 +Release: %mkrel 1 +License: BSD +Group: Networking/Remote access +URL: http://www.openssh.com/ +Source0: ftp://ftp.openbsd.org/pub/OpenBSD/OpenSSH/portable/openssh-%{version}.tar.gz +Source1: ftp://ftp.openbsd.org/pub/OpenBSD/OpenSSH/portable/openssh-%{version}.tar.gz.asc +Source2: http://www.ntrnet.net/~jmknoble/software/x11-ssh-askpass/x11-ssh-askpass-%{aversion}.tar.bz2 +# ssh-copy-id taken from debian, with "usage" added +Source3: ssh-copy-id +Source7: openssh-xinetd +Source9: README.sftpfilecontrol +# this is never to be applied by default +# http://www.sc.isc.tohoku.ac.jp/~hgot/sources/openssh-watchdog.html +Source10: openssh-%{wversion}-watchdog.patch.tgz +Source12: ssh_ldap_key.pl +Source15: ssh-avahi-integration +Source16: sshd.pam-0.77 +Source17: sshd.pam +Source18: sshd.init +Source19: README.3.8p1.upgrade.urpmi +Source20: README.3.9p1-3.upgrade.urpmi +Source21: README.hpn +Patch1: openssh-mdv_conf.diff +# authorized by Damien Miller +Patch3: openssh-3.1p1-check-only-ssl-version.patch +# rediffed from openssh-4.4p1-watchdog.patch.tgz +Patch4: openssh-4.4p1-watchdog.diff +# optional ldap support +# http://dev.inversepath.com/trac/openssh-lpk +#Patch6: http://dev.inversepath.com/openssh-lpk/openssh-lpk-4.6p1-0.3.9.patch +# new location for the lpk patch. +# rediffed from "svn checkout http://openssh-lpk.googlecode.com/svn/trunk/ openssh-lpk-read-only" +Patch6: openssh-lpk-5.4p1-0.3.10.diff +# http://sftpfilecontrol.sourceforge.net +# Not applied by default +# P7 is rediffed and slightly adjusted from http://sftplogging.sourceforge.net/download/v1.5/openssh-4.4p1.sftplogging-v1.5.patch +Patch7: openssh-4.9p1.sftplogging-v1.5.diff +# (tpg) http://www.psc.edu/networking/projects/hpn-ssh/ +Patch11: http://www.psc.edu/networking/projects/hpn-ssh/openssh-5.2p1-hpn%{hpnver}.diff +Patch12: http://www.psc.edu/networking/projects/hpn-ssh/openssh5.1-peaktput.diff +#gw: from Fedora: +#fix round-robin DNS with GSSAPI authentification +Patch13: openssh-4.3p2-gssapi-canohost.patch +Patch14: openssh-4.7p1-audit.patch +Patch17: openssh-5.1p1-askpass-progress.patch +Patch18: openssh-4.3p2-askpass-grab-info.patch +Patch19: openssh-4.0p1-exit-deadlock.patch +Patch21: openssh_tcp_wrappers.patch +Obsoletes: ssh +Provides: ssh +Requires(post): openssl >= 0.9.7 +Requires(post): makedev +Requires(preun): openssl >= 0.9.7 +Requires: tcp_wrappers +BuildRequires: groff-for-man +BuildRequires: openssl-devel >= 0.9.7 +BuildRequires: pam-devel +BuildRequires: tcp_wrappers-devel +BuildRequires: zlib-devel +%if %{build_skey} +BuildRequires: skey-devel +%endif +%if %{build_krb5} +BuildRequires: krb5-devel +%endif +%if %{build_x11askpass} +%if %{mdkversion} < 200700 +BuildRequires: X11-devel xorg-x11 +%else +BuildRequires: imake +BuildRequires: rman +# http://qa.mandriva.com/show_bug.cgi?id=22736 +BuildRequires: x11-util-cf-files >= 1.0.2 +BuildRequires: gccmakedep +BuildRequires: libx11-devel +BuildRequires: libxt-devel +%endif +%endif +%if %{build_gnomeaskpass} +BuildRequires: gtk+2-devel +%endif +%if %{build_ldap} +BuildRequires: openldap-devel >= 2.0 +%endif +%if %{build_audit} +BuildRequires: audit-devel +%endif +%if %{build_libedit} +BuildRequires: edit-devel ncurses-devel +%endif +BuildConflicts: libgssapi-devel +BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-buildroot + +%description +Ssh (Secure Shell) is a program for logging into a remote machine and for +executing commands in a remote machine. It is intended to replace +rlogin and rsh, and provide secure encrypted communications between +two untrusted hosts over an insecure network. X11 connections and +arbitrary TCP/IP ports can also be forwarded over the secure channel. + +OpenSSH is OpenBSD's rework of the last free version of SSH, bringing it +up to date in terms of security and features, as well as removing all +patented algorithms to separate libraries (OpenSSL). + +This package includes the core files necessary for both the OpenSSH +client and server. To make this package useful, you should also +install openssh-clients, openssh-server, or both. + +You can build %{name} with some conditional build swithes; + +(ie. use with rpm --rebuild): + +--with[out] skey smartcard support (disabled) +--with[out] krb5 kerberos support (enabled) +--with[out] watchdog watchdog support (disabled) +--with[out] x11askpass X11 ask pass support (enabled) +--with[out] gnomeaskpass Gnome ask pass support (enabled) +--with[out] ldap OpenLDAP support (disabled) +--with[out] sftpcontrol sftp file control support (disabled) +--with[out] hpn HPN ssh/scp support (disabled) +--with[out] audit audit support (disabled) +--with[out] libedit libedit support in sftp (enabled) + +%package clients +Summary: OpenSSH Secure Shell protocol clients +Group: Networking/Remote access +Requires: %{name} = %{version}-%{release} +Obsoletes: ssh-clients, sftp, ssh +Provides: ssh-clients, sftp, ssh +# scp was moved from openssh to openssh-clients +# http://qa.mandriva.com/show_bug.cgi?id=17491 +Conflicts: %{name} <= 4.1p1-6mdk + +%description clients +Ssh (Secure Shell) is a program for logging into a remote machine and for +executing commands in a remote machine. It is intended to replace +rlogin and rsh, and provide secure encrypted communications between +two untrusted hosts over an insecure network. X11 connections and +arbitrary TCP/IP ports can also be forwarded over the secure channel. + +OpenSSH is OpenBSD's rework of the last free version of SSH, bringing it +up to date in terms of security and features, as well as removing all +patented algorithms to separate libraries (OpenSSL). + +This package includes the clients necessary to make encrypted connections +to SSH servers. + +%package server +Summary: OpenSSH Secure Shell protocol server (sshd) +Group: System/Servers +Requires(pre): %{name} = %{version}-%{release} chkconfig >= 0.9 +Requires(pre): pam >= 0.74 +Requires(pre): rpm-helper +Requires(post): rpm-helper +Requires(preun): rpm-helper +Requires(postun): rpm-helper +Requires(post): openssl >= 0.9.7 +Requires(post): makedev +Requires: %{name}-clients = %{version}-%{release} +%if %{build_skey} +Requires: skey +%endif +%if %{build_audit} +BuildRequires: audit +%endif +Obsoletes: ssh-server, sshd +Provides: ssh-server, sshd + +%description server +Ssh (Secure Shell) is a program for logging into a remote machine and for +executing commands in a remote machine. It is intended to replace +rlogin and rsh, and provide secure encrypted communications between +two untrusted hosts over an insecure network. X11 connections and +arbitrary TCP/IP ports can also be forwarded over the secure channel. + +OpenSSH is OpenBSD's rework of the last free version of SSH, bringing it +up to date in terms of security and features, as well as removing all +patented algorithms to separate libraries (OpenSSL). + +This package contains the secure shell daemon. The sshd is the server +part of the secure shell protocol and allows ssh clients to connect to +your host. + +%package askpass-common +Summary: OpenSSH X11 passphrase common scripts +Group: Networking/Remote access + +%description askpass-common +OpenSSH X11 passphrase common scripts + +%if %{build_x11askpass} +%package askpass +Summary: OpenSSH X11 passphrase dialog +Group: Networking/Remote access +Requires: %{name} = %{version}-%{release} +Requires: %{name}-askpass-common +Obsoletes: ssh-extras, ssh-askpass +Provides: ssh-extras, ssh-askpass +Requires(pre): update-alternatives + +%description askpass +Ssh (Secure Shell) is a program for logging into a remote machine and for +executing commands in a remote machine. It is intended to replace +rlogin and rsh, and provide secure encrypted communications between +two untrusted hosts over an insecure network. X11 connections and +arbitrary TCP/IP ports can also be forwarded over the secure channel. + +OpenSSH is OpenBSD's rework of the last free version of SSH, bringing it +up to date in terms of security and features, as well as removing all +patented algorithms to separate libraries (OpenSSL). + +This package contains Jim Knoble's X11 passphrase +dialog. +%endif + +%if %{build_gnomeaskpass} +%package askpass-gnome +Summary: OpenSSH GNOME passphrase dialog +Group: Networking/Remote access +Requires: %{name} = %{version}-%{release} +Requires: %{name}-askpass-common +Obsoletes: ssh-extras +Requires(pre): update-alternatives +Provides: %{name}-askpass, ssh-askpass, ssh-extras + +%description askpass-gnome +Ssh (Secure Shell) is a program for logging into a remote machine and for +executing commands in a remote machine. It is intended to replace +rlogin and rsh, and provide secure encrypted communications between +two untrusted hosts over an insecure network. X11 connections and +arbitrary TCP/IP ports can also be forwarded over the secure channel. + +OpenSSH is OpenBSD's rework of the last free version of SSH, bringing it +up to date in terms of security and features, as well as removing all +patented algorithms to separate libraries (OpenSSL). + +This package contains the GNOME passphrase dialog. +%endif + +%prep +%if %{build_x11askpass} +echo "Building with x11 askpass..." +%endif +%if %{build_gnomeaskpass} +echo "Building with GNOME askpass..." +%endif +%if %{build_krb5} +echo "Building with Kerberos5 support..." +%endif +%if %{build_skey} +echo "Building with S/KEY support..." +%endif +%if %{build_watchdog} +echo "Building with watchdog support..." +%endif +%if %{build_ldap} +echo "Buiding with support for authenticating to public keys in ldap" +%endif +%if %{build_sftpcontrol} +echo "Buiding with support for sftp file control" +%endif +%if %{build_hpn} +echo "Buiding with support for High Performance Network SSH/SCP" +%endif +%if %{build_audit} +echo "Buiding with audit support" +%endif + +%setup -q -a2 -a10 + +%patch1 -p1 -b .mdkconf +%patch3 -p1 -b .ssl_ver +%if %{build_watchdog} +#patch -p0 -s -z .wdog < %{name}-%{wversion}-watchdog.patch +%patch4 -p1 -b .watchdog +%endif +%if %{build_ldap} +sed -i 's|UsePrivilegeSeparation yes|#UsePrivilegeSeparation yes|' sshd_config +%patch6 -p1 -b .lpk +rm -f README.lpk.lpk +%define _default_patch_fuzz 3 +%else +%define _default_patch_fuzz 2 +%endif +%if %{build_sftpcontrol} +#cat %{SOURCE8} | patch -p1 -s -z .sftpcontrol +echo "This patch is broken or needs to be updated/rediffed"; exit 1 +%patch7 -p1 -b .sftplogging-v1.5 +# README with license terms for this patch +install -m 0644 %{SOURCE9} . +%endif +%if %{build_hpn} +echo "This patch is broken or needs to be updated/rediffed"; exit 1 +%patch11 -p1 -b .hpn +%patch12 -p1 -b .peak +install %{SOURCE21} . +%endif +%patch13 -p1 -b .canohost +%if %{build_audit} +%patch14 -p1 -b .audit +%endif +%patch17 -p1 -b .progress +%patch18 -p1 -b .grab-info +%patch19 -p1 -b .exit-deadlock +%patch21 -p1 -b .tcp_wrappers_mips + +install %{SOURCE12} %{SOURCE19} %{SOURCE20} . + +# fix conditional pam config file +%if %{mdkversion} < 200610 +install -m 0644 %{SOURCE16} sshd.pam +%else +install -m 0644 %{SOURCE17} sshd.pam +%endif + +install -m 0755 %{SOURCE18} sshd.init + +# fix attribs +chmod 644 ChangeLog OVERVIEW README* INSTALL CREDITS LICENCE TODO ssh_ldap_key.pl + +# http://qa.mandriva.com/show_bug.cgi?id=22957 +perl -pi -e "s|_OPENSSH_PATH_|%{OPENSSH_PATH}|g" sshd_config + +%build +autoreconf -fi + +%serverbuild + +%if %{build_x11askpass} +pushd x11-ssh-askpass-%{aversion} +%configure2_5x \ + --prefix=%{_prefix} --libdir=%{_libdir} \ + --mandir=%{_mandir} --libexecdir=%{_libdir}/ssh \ + --with-app-defaults-dir=%{_sysconfdir}/X11/app-defaults \ +%if %{build_libedit} + --with-libedit \ +%else + --without-libedit \ +%endif + +xmkmf -a + +%ifarch x86_64 +perl -pi -e "s|/usr/lib\b|%{_libdir}|g" Makefile +perl -pi -e "s|i586-mandriva-linux-gnu|x86_64-mandriva-linux-gnu|g" Makefile +#perl -pi -e "s|%{_libdir}/gcc/|/usr/lib/gcc/|g" Makefile +perl -pi -e "s|-m32|-m64|g" Makefile +perl -pi -e "s|__i386__|__x86_64__|g" Makefile +%endif + +make \ + BINDIR=%{_libdir}/ssh \ + CDEBUGFLAGS="$RPM_OPT_FLAGS" \ + CXXDEBUGFLAGS="$RPM_OPT_FLAGS" + +# For some reason the x11-ssh-askpass.1.html file is not created on 10.0/10.1 +# x86_64, so we just do it manually here... (oden) +rm -f x11-ssh-askpass.1x.html x11-ssh-askpass.1x-html +rman -f HTML < x11-ssh-askpass._man > x11-ssh-askpass.1x-html && \ +mv -f x11-ssh-askpass.1x-html x11-ssh-askpass.1.html +popd +%endif + +%if %{build_gnomeaskpass} +pushd contrib +make gnome-ssh-askpass2 CC="%__cc %optflags %ldflags" +mv gnome-ssh-askpass2 gnome-ssh-askpass +popd +%endif + +%configure2_5x \ + --prefix=%{_prefix} \ + --sysconfdir=%{_sysconfdir}/ssh \ + --mandir=%{_mandir} \ + --libdir=%{_libdir} \ + --libexecdir=%{_libdir}/ssh \ + --datadir=%{_datadir}/ssh \ + --disable-strip \ + --with-tcp-wrappers \ + --with-pam \ + --with-default-path=%{OPENSSH_PATH} \ + --with-xauth=%{XAUTH} \ + --with-privsep-path=/var/empty \ + --without-zlib-version-check \ +%if %{build_krb5} + --with-kerberos5=%{_prefix} \ +%endif +%if %{build_skey} + --with-skey \ +%endif +%if %{build_ldap} + --with-libs="-lldap -llber" \ + --with-cppflags="-DWITH_LDAP_PUBKEY -DLDAP_DEPRECATED" \ +%endif + --with-superuser-path=/usr/local/sbin:/usr/local/bin:/sbin:/bin:%{_sbindir}:%{_bindir} \ +%if %{build_libedit} + --with-libedit \ +%else + --without-libedit \ +%endif +%if %{build_audit} + --with-linux-audit \ +%endif + +%make + +%install +rm -rf %{buildroot} + +%makeinstall_std + +install -d %{buildroot}%{_sysconfdir}/ssh +install -d %{buildroot}%{_sysconfdir}/pam.d/ +install -d %{buildroot}%{_sysconfdir}/sysconfig +install -d %{buildroot}%{_initrddir} +install -m644 sshd.pam %{buildroot}%{_sysconfdir}/pam.d/sshd +install -m755 sshd.init %{buildroot}%{_initrddir}/sshd + +if [[ -f sshd_config.out ]]; then + install -m600 sshd_config.out %{buildroot}%{_sysconfdir}/ssh/sshd_config +else + install -m600 sshd_config %{buildroot}%{_sysconfdir}/ssh/sshd_config +fi +echo "root" > %{buildroot}%{_sysconfdir}/ssh/denyusers + +if [[ -f ssh_config.out ]]; then + install -m644 ssh_config.out %{buildroot}%{_sysconfdir}/ssh/ssh_config +else + install -m644 ssh_config %{buildroot}%{_sysconfdir}/ssh/ssh_config +fi +echo " StrictHostKeyChecking no" >> %{buildroot}%{_sysconfdir}/ssh/ssh_config + +mkdir -p %{buildroot}%{_libdir}/ssh +%if %{build_x11askpass} +pushd x11-ssh-askpass-%{aversion} +#make DESTDIR=%{buildroot} install +#make DESTDIR=%{buildroot} install.man +#install -d %{buildroot}%{_prefix}/X11R6/lib/X11/doc/html +#install -m0644 x11-ssh-askpass.1.html %{buildroot}%{_prefix}/X11R6/lib/X11/doc/html/ +install -d %{buildroot}%{_libdir}/ssh +install -d %{buildroot}%{_sysconfdir}/X11/app-defaults +install -m0644 SshAskpass.ad %{buildroot}%{_sysconfdir}/X11/app-defaults/SshAskpass +install -m0755 x11-ssh-askpass %{buildroot}%{_libdir}/ssh/ +install -m0644 x11-ssh-askpass.man %{buildroot}%{_mandir}/man1/x11-ssh-askpass.1 +popd +%endif + +install -d %{buildroot}%{_sysconfdir}/profile.d/ +%if %{build_gnomeaskpass} +install -m 755 contrib/gnome-ssh-askpass %{buildroot}%{_libdir}/ssh/gnome-ssh-askpass +%endif + +cat > %{buildroot}%{_sysconfdir}/profile.d/90ssh-askpass.csh < %{buildroot}%{_sysconfdir}/profile.d/90ssh-askpass.sh < %{buildroot}%{_sysconfdir}/profile.d/90ssh-client.sh <<'EOF' +# fix hanging ssh clients on exit +if [ -n "$BASH_VERSION" ]; then + shopt -s huponexit +elif [ -n "$ZSH_VERSION" ]; then + setopt hup +fi +EOF + +install -m 0755 %{SOURCE3} %{buildroot}/%{_bindir}/ssh-copy-id +chmod a+x %{buildroot}/%{_bindir}/ssh-copy-id +install -m 644 contrib/ssh-copy-id.1 %{buildroot}/%{_mandir}/man1/ + +# create pre-authentication directory +mkdir -p %{buildroot}/var/empty + +# remove unwanted files +rm -f %{buildroot}%{_libdir}/ssh/ssh-askpass + +# xinetd support (tv) +mkdir -p %{buildroot}%{_sysconfdir}/xinetd.d/ +install -m 0644 %{SOURCE7} %{buildroot}%{_sysconfdir}/xinetd.d/sshd-xinetd + +cat > %{buildroot}%{_sysconfdir}/sysconfig/sshd << EOF +#SSHD="%{_sbindir}/sshd" +#PID_FILE="/var/run/sshd.pid" +#OPTIONS="" +EOF + +# avahi integration support (misc) +mkdir -p %{buildroot}%{_sysconfdir}/avahi/services/ +install -m 0644 %{SOURCE15} %{buildroot}%{_sysconfdir}/avahi/services/%{name}.service + +# make sure strip can touch it +chmod 755 %{buildroot}%{_libdir}/ssh/ssh-keysign + +%clean +rm -rf %{buildroot} + +%pre server +%_pre_useradd sshd /var/empty /bin/true + +%post server +# do some key management; taken from the initscript + +KEYGEN=/usr/bin/ssh-keygen +RSA1_KEY=/etc/ssh/ssh_host_key +RSA_KEY=/etc/ssh/ssh_host_rsa_key +DSA_KEY=/etc/ssh/ssh_host_dsa_key + +do_rsa1_keygen() { + if [ ! -s $RSA1_KEY ]; then + echo -n "Generating SSH1 RSA host key... " + if $KEYGEN -q -t rsa1 -f $RSA1_KEY -C '' -N '' >&/dev/null; then + chmod 600 $RSA1_KEY + chmod 644 $RSA1_KEY.pub + echo "done" + echo + else + echo "failed" + echo + exit 1 + fi + fi +} + +do_rsa_keygen() { + if [ ! -s $RSA_KEY ]; then + echo "Generating SSH2 RSA host key... " + if $KEYGEN -q -t rsa -f $RSA_KEY -C '' -N '' >&/dev/null; then + chmod 600 $RSA_KEY + chmod 644 $RSA_KEY.pub + echo "done" + echo + else + echo "failed" + echo + exit 1 + fi + fi +} + +do_dsa_keygen() { + if [ ! -s $DSA_KEY ]; then + echo "Generating SSH2 DSA host key... " + if $KEYGEN -q -t dsa -f $DSA_KEY -C '' -N '' >&/dev/null; then + chmod 600 $DSA_KEY + chmod 644 $DSA_KEY.pub + echo "done" + echo + else + echo "failed" + echo + exit 1 + fi + fi +} + +do_rsa1_keygen +do_rsa_keygen +do_dsa_keygen +%_post_service sshd + +%preun server +%_preun_service sshd + +%postun server +%_postun_userdel sshd + +%if %{build_x11askpass} +%post askpass +update-alternatives --install %{_libdir}/ssh/ssh-askpass ssh-askpass %{_libdir}/ssh/x11-ssh-askpass 10 +update-alternatives --install %{_bindir}/ssh-askpass bssh-askpass %{_libdir}/ssh/x11-ssh-askpass 10 + +%postun askpass +[ $1 = 0 ] || exit 0 +update-alternatives --remove ssh-askpass %{_libdir}/ssh/x11-ssh-askpass +update-alternatives --remove bssh-askpass %{_libdir}/ssh/x11-ssh-askpass +%endif + +%if %{build_gnomeaskpass} +%post askpass-gnome +update-alternatives --install %{_libdir}/ssh/ssh-askpass ssh-askpass %{_libdir}/ssh/gnome-ssh-askpass 20 +update-alternatives --install %{_bindir}/ssh-askpass bssh-askpass %{_libdir}/ssh/gnome-ssh-askpass 20 + +%postun askpass-gnome +[ $1 = 0 ] || exit 0 +update-alternatives --remove ssh-askpass %{_libdir}/ssh/gnome-ssh-askpass +update-alternatives --remove bssh-askpass %{_libdir}/ssh/gnome-ssh-askpass +%endif + +%triggerpostun server -- openssh-server < 3.8p1 +if grep -qE "^\W*auth\W+\w+\W+.*pam_(ldap|winbind|mysql)" /etc/pam.d/system-auth /etc/pam.d/sshd; then + perl -pi -e 's|^#UsePAM no|UsePAM yes|' /etc/ssh/sshd_config +fi + +%files +%defattr(-,root,root) +%doc ChangeLog OVERVIEW README* INSTALL CREDITS LICENCE TODO ssh_ldap_key.pl +%if %{build_ldap} +%doc *.schema +%endif +%if %{build_watchdog} +%doc CHANGES-openssh-watchdog openssh-watchdog.html +%endif +%if %{build_sftpcontrol} +%doc README.sftpfilecontrol +%endif +%{_bindir}/ssh-keygen +%dir %{_sysconfdir}/ssh +%{_bindir}/ssh-keyscan +%attr(4711,root,root) %{_libdir}/ssh/ssh-keysign +%{_libdir}/ssh/ssh-pkcs11-helper +%{_mandir}/man1/ssh-keygen.1* +%{_mandir}/man1/ssh-keyscan.1* +%{_mandir}/man8/ssh-keysign.8* +%{_mandir}/man8/ssh-pkcs11-helper.8* + +%files clients +%defattr(-,root,root) +%{_bindir}/scp +%{_bindir}/ssh +%{_bindir}/ssh-agent +%{_bindir}/ssh-add +%{_bindir}/ssh-copy-id +%{_bindir}/slogin +%{_bindir}/sftp +%{_mandir}/man1/scp.1* +%{_mandir}/man1/ssh-copy-id.1* +%{_mandir}/man1/slogin.1* +%{_mandir}/man1/ssh.1* +%{_mandir}/man1/ssh-agent.1* +%{_mandir}/man1/ssh-add.1* +%{_mandir}/man1/sftp.1* +%{_mandir}/man5/ssh_config.5* +%config(noreplace) %{_sysconfdir}/ssh/ssh_config +%{_sysconfdir}/profile.d/90ssh-client.sh + +%files server +%defattr(-,root,root) +%attr(0644,root,root) %config(noreplace) %{_sysconfdir}/sysconfig/sshd +%{_sbindir}/sshd +%dir %{_libdir}/ssh +%{_libdir}/ssh/sftp-server +%{_mandir}/man5/sshd_config.5* +%{_mandir}/man5/moduli.5* +%{_mandir}/man8/sshd.8* +%{_mandir}/man8/sftp-server.8* +%attr(0600,root,root) %config(noreplace) %{_sysconfdir}/ssh/sshd_config +%attr(0600,root,root) %config(noreplace) %{_sysconfdir}/ssh/denyusers +%attr(0600,root,root) %config(noreplace) %{_sysconfdir}/pam.d/sshd +%config(noreplace) %_sysconfdir/xinetd.d/sshd-xinetd +%config(noreplace) %{_sysconfdir}/avahi/services/%{name}.service +%config(noreplace) %{_sysconfdir}/ssh/moduli +%attr(0755,root,root) %{_initrddir}/sshd +%dir %attr(0755,root,root) /var/empty + +%files askpass-common +%defattr(-,root,root) +%{_sysconfdir}/profile.d/90ssh-askpass.* + +%if %{build_x11askpass} +%files askpass +%defattr(-,root,root) +%doc x11-ssh-askpass-%{aversion}/README +%doc x11-ssh-askpass-%{aversion}/ChangeLog +%doc x11-ssh-askpass-%{aversion}/SshAskpass*.ad +%doc x11-ssh-askpass-%{aversion}/x11-ssh-askpass.1.html +%{_libdir}/ssh/x11-ssh-askpass +%{_sysconfdir}/X11/app-defaults/SshAskpass +#%{_prefix}/X11R6/lib/X11/doc/html/x11-ssh-askpass.1.html +%{_mandir}/man1/x11-ssh-askpass.1* +%endif + +%if %{build_gnomeaskpass} +%files askpass-gnome +%defattr(-,root,root) +%{_libdir}/ssh/gnome-ssh-askpass +%endif + + +%changelog +* Sun May 15 2011 Oden Eriksson 5.8p2-1mdv2011.0 ++ Revision: 674747 +- 5.8p2 +- fix build +- mass rebuild + +* Sun Feb 27 2011 Funda Wang 5.8p1-2 ++ Revision: 640301 +- rebuild to obsolete old packages + +* Fri Feb 04 2011 Oden Eriksson 5.8p1-1 ++ Revision: 635967 +- 5.8p1 (fixes CVE-2011-0539) + +* Sat Jan 29 2011 Eugeni Dodonov 5.7p1-1 ++ Revision: 633939 +- Updated to 5.7p1. + Rediff P1 and P3. + +* Tue Dec 07 2010 Oden Eriksson 5.6p1-2mdv2011.0 ++ Revision: 613606 +- provide a useful debug package + +* Tue Aug 24 2010 Funda Wang 5.6p1-1mdv2011.0 ++ Revision: 572678 +- New version 5.6p1 +- use our own build flags + +* Mon Jun 07 2010 Eugeni Dodonov 5.5p1-2mdv2010.1 ++ Revision: 547228 +- Do not display bogus FAILED messages when stopping service (#58283). + +* Fri Apr 16 2010 Eugeni Dodonov 5.5p1-1mdv2010.1 ++ Revision: 535499 +- Updated to 5.5p1. + +* Mon Apr 05 2010 Funda Wang 5.4p1-3mdv2010.1 ++ Revision: 531711 +- rebuild for new openssl + +* Mon Mar 08 2010 Oden Eriksson 5.4p1-2mdv2010.1 ++ Revision: 515815 +- whoops!, the ldap patch wasn't supposed to be applied per default +- 5.4p1 +- dropped upstream added patches +- rediffed two patches +- adjust the spec file for 5.4p1 + +* Tue Mar 02 2010 Olivier Blin 5.3p1-6mdv2010.1 ++ Revision: 513571 +- kill sshd clients at shutdown (#57782) + +* Fri Feb 26 2010 Oden Eriksson 5.3p1-5mdv2010.1 ++ Revision: 511605 +- rebuilt against openssl-0.9.8m + +* Fri Jan 15 2010 Oden Eriksson 5.3p1-4mdv2010.1 ++ Revision: 491719 +- fix #55951 (the openssh-server package needs openssl and makedev in Requires(post)) + + + Jérôme Quelin + - reverting to bash, till all functions get fixed + - remove bashisms, switch to dash + + + Olivier Blin + - require makedev in post (random/entropy devices are needed by openssl) + +* Wed Oct 07 2009 Oden Eriksson 5.3p1-2mdv2010.0 ++ Revision: 455652 +- rediffed most of the third party patches + +* Thu Oct 01 2009 Oden Eriksson 5.3p1-1mdv2010.0 ++ Revision: 452225 +- 5.3p1 + + + Olivier Blin + - fix build on mips (from Arnaud Patard) + +* Thu Sep 03 2009 Christophe Fergeau 5.2p1-2mdv2010.0 ++ Revision: 426348 +- rebuild + +* Mon Feb 23 2009 Oden Eriksson 5.2p1-1mdv2009.1 ++ Revision: 344077 +- 5.2p1 +- rediffed P1 +- dropped one upstream patch (P21) + +* Tue Feb 03 2009 Guillaume Rousse 5.1p1-6mdv2009.1 ++ Revision: 337115 +- keep bash completion in its own package + +* Fri Jan 09 2009 Guillaume Rousse 5.1p1-5mdv2009.1 ++ Revision: 327518 +- bash completion, splitted from main file in upstream project + +* Tue Dec 16 2008 Oden Eriksson 5.1p1-4mdv2009.1 ++ Revision: 314936 +- rebuild + +* Thu Oct 16 2008 Oden Eriksson 5.1p1-3mdv2009.1 ++ Revision: 294182 +- rebuild + +* Mon Sep 29 2008 Oden Eriksson 5.1p1-2mdv2009.0 ++ Revision: 289727 +- rebuild +- fix #43747 (transfering locales with ssh creates problems) + +* Tue Aug 05 2008 Oden Eriksson 5.1p1-1mdv2009.0 ++ Revision: 263950 +- hpn13v5 +- sync with openssh-5.1p1-2.fc10.src.rpm + +* Mon Jul 28 2008 Oden Eriksson 5.1p1-0.1mdv2009.0 ++ Revision: 251404 +- 5.1p1 +- rediffed P1,P21 +- disabled P22 for now +- 3rd party patches needs to be fixed + +* Thu Jul 17 2008 Oden Eriksson 5.0p1-5mdv2009.0 ++ Revision: 236780 +- rebuilt x11-ssh-askpass with LDFLAGS="-Wl,--as-needed" +- rebuild +- added P21, P22 from openssh-5.0p1-1.fc9 - fix race on control + master and cleanup stale control socket (#436311) patches by + David Woodhouse +- added P20 from openssh-5.0p1-1.fc9 - set FD_CLOEXEC on client socket +- added P19 from openssh-5.0p1-1.fc9 - don't deadlock on exit with + multiple X forwarded channels (rh #152432) +- added 3 patches for gnome-ssh-askpass from openssh-5.0p1-1.fc9 +- make it possible to build without libedit support (rpmbuild --rebuild --without libedit ...) +- added audit support from openssh-5.0p1-1.fc9 (disabled for now, though it works) +- sync with fc9 (SendEnv AcceptEnv) + +* Wed Apr 23 2008 Götz Waschk 5.0p1-3mdv2009.0 ++ Revision: 196921 +- fix gssapi with DNS loadbalanced clusters + +* Tue Apr 15 2008 Tomasz Pawel Gajc 5.0p1-2mdv2009.0 ++ Revision: 194354 +- update HPN SSH/SCP patches against latest openssh version + +* Wed Apr 09 2008 Oden Eriksson 5.0p1-1mdv2009.0 ++ Revision: 192500 +- 5.0p1 +- drop P2 (CVE-2008-1483 is fixed in 5.0p1) +- 4.9p1 +- dropped the chroot patch since another approach is in 4.9p1 +- dropped the ctimeout patch since it's in there +- rediffed all patches that are not applied per default, except for the HPN patches + +* Thu Mar 27 2008 Gustavo De Nardin 4.7p1-9mdv2008.1 ++ Revision: 190750 +- security fix for CVE-2008-1483 + + + Giuseppe Ghibò + - Move 2007.1 backports ssp flags to a more effective place in the building. + +* Mon Mar 17 2008 Tomasz Pawel Gajc 4.7p1-7mdv2008.1 ++ Revision: 188362 +- new version of HPN patch + +* Wed Jan 23 2008 Thierry Vignaud 4.7p1-6mdv2008.1 ++ Revision: 157259 +- rebuild with fixed %%serverbuild macro + +* Mon Jan 14 2008 Olivier Blin 4.7p1-5mdv2008.1 ++ Revision: 151175 +- use ConnectTimeout option for banner exchange, to timeout on stuck servers (rediffed from CVS) + +* Thu Jan 03 2008 Tomasz Pawel Gajc 4.7p1-4mdv2008.1 ++ Revision: 142673 +- disable hpn support by default + + + Olivier Blin + - restore BuildRoot + +* Tue Jan 01 2008 Tomasz Pawel Gajc 4.7p1-3mdv2008.1 ++ Revision: 140105 +- add support for High Performance SSH/SCP - HPN-SSH + o add patch 11, the hpn core + o add patch 12, which displays peak throughput through the life of the connection + o add README.hpn, all info about hpn idea + + + Guillaume Rousse + - no executable bit on profile scriptlets + order prefix on profile scriptlets + use herein-documents instead of additional source for profile scriptlets + + + Thierry Vignaud + - kill re-definition of %%buildroot on Pixel's request + +* Wed Sep 12 2007 Anssi Hannula 4.7p1-2mdv2008.0 ++ Revision: 84669 +- show upgrade notes only on relevant upgrades + +* Wed Sep 05 2007 Oden Eriksson 4.7p1-1mdv2008.0 ++ Revision: 80390 +- 4.7p1 +- rediffed P1,S8 +- dropped upstream chan_read_failed patch (P2) +- fixed build deps (edit-devel) + + + Giuseppe Ghibò + - Add conditional flags for 2007.1 and CD4. + + + Thierry Vignaud + - kill file require on update-alternatives + +* Fri Aug 03 2007 Andreas Hasenack 4.6p1-8mdv2008.0 ++ Revision: 58559 +- updated lpk patch (still not applied by default) + +* Mon Jul 02 2007 Andreas Hasenack 4.6p1-7mdv2008.0 ++ Revision: 47243 +- updated sftplogging patch, which is now called sftpfilecontrol +- added README file for it with the license + +* Wed Jun 27 2007 Andreas Hasenack 4.6p1-6mdv2008.0 ++ Revision: 45218 +- added patch from openssh's bugzilla to fix the chan_read_failed error + messages in logs (#31664) + +* Thu Jun 21 2007 Andreas Hasenack 4.6p1-5mdv2008.0 ++ Revision: 42382 +- rebuild + +* Wed Jun 20 2007 Andreas Hasenack 4.6p1-4mdv2008.0 ++ Revision: 41658 +- don't use %%{optflags} macro when using %%serverbuild +- don't use -fstack-protector explicitly, as it is now defined by + the %%serverbuild macro +- move lpk doc to main base package +- remove empty README.lpk.lpk file, caused by patch backup +- install lpk schema files as %%doc if using ldap patch +- updated lpk patch and its url + +* Wed Apr 18 2007 Oden Eriksson 4.6p1-3mdv2008.0 ++ Revision: 14713 +- use conditionals for the -fstack-protector gcc clags + + +* Sat Apr 07 2007 David Walluck 4.6p1-2mdv2007.1 ++ Revision: 151271 +- enable libedit support for sftp + +* Sun Mar 11 2007 Oden Eriksson 4.6p1-1mdv2007.1 ++ Revision: 141301 +- 4.6p1 +- new openssh-4.4p1.sftplogging-v1.5.patch (S8) +- rediffed the openssh-lpk-4.3p1-0.3.7.patch patch (P6) +- fixed deps + + + Andreas Hasenack + - enabled gcc's stack-protector, let's try it + +* Sat Jan 20 2007 Olivier Blin 4.5p1-3mdv2007.1 ++ Revision: 111120 +- use Should-Start/Should-Stop tags for remote_fs system facility in sshd service (#25757) + +* Fri Nov 10 2006 Andreas Hasenack 4.5p1-2mdv2007.1 ++ Revision: 80618 +- rebuild with new openssl +- get rid of svn comment, not needed anymore + +* Tue Nov 07 2006 Andreas Hasenack 4.5p1-1mdv2007.0 ++ Revision: 77765 +- updated to version 4.5p1 +- updated to version 4.4p1, fixing CVE-2006-4924, + CVE-2006-4925 and CVE-2006-5051 (#26249) + + + Oden Eriksson + - don't use bugus config in the lpk patch, it prevents the sshd server from starting... + - it really links against the shared skey libs, so nuke one build dep + - kerberos was not found on my cs4 box, using "--with-kerberos5=%%{_prefix}" fixed it (!?) + - pass "-DLDAP_DEPRECATED" to the CPPFLAGS if building with ldap support + +* Thu Aug 03 2006 Andreas Hasenack 4.3p2-12mdv2007.0 ++ Revision: 42979 +- bunzipped remaining source files +- updated sftploggin patch (still not applied by default) +- fixed pam configuration file for recent pam (#22008) +- removed requirement for xauth (#23086) +- removed workaround for #22736 +- added versioned buildrequires for x11-util-cf-files in order + to fix #22736. Rebuild. +- added other missing buildrequires due to xorg xplit +- re-generate ssh-askpass html doc page again during build + +* Mon Jul 31 2006 Helio Chissini de Castro 4.3p2-11mdv2007.0 ++ Revision: 42821 +- Fixed file list +- Wrong.. askpass env should come *before* keyring +- Fixed source list +- Added ordering for askpass script. Same change will be added on keychain + script + + + Andreas Hasenack + - add svn warning + - import openssh-4.3p2-10mdv2007.0 + +* Fri Jul 28 2006 Helio Chissini de Castro 4.3p2-10mdv2007.0 +- Created script package askpass-common to enable just one file on profile.d and rely on +correct alternatives, with recent introduction of qt version of ssh-askpass ( separated +package ). +- Nuke the old invalid buildrequires dependency for db1 + +* Tue Jul 04 2006 Per Øyvind Karlsen 4.3p2-9mdv2007.0 +- fix buildrequires +- fix macro-in-%%changelog + +* Thu Jun 08 2006 Oden Eriksson 4.3p2-8mdv2007.0 +- fix #22957 (P1 + spec file hack) +- make it backportable for older X +- fix deps + +* Mon May 29 2006 Oden Eriksson 4.3p2-7mdv2007.0 +- fix #22736 with a temporary hack + +* Mon Mar 06 2006 Buchan Milne 4.3p2-5mdk +- update lpk patch to 0.3.7 + +* Sun Feb 19 2006 Michael Scherer 4.3p2-4mdk +- fix avahi config file naming + +* Mon Feb 13 2006 Oden Eriksson 4.3p2-3mdk +- make it backportable for older pam (S16) + +* Sun Feb 12 2006 Oden Eriksson 4.3p2-2mdk +- use "include" directive instead of the deprecated pam_stack.so + module and provide our own pam configuration file (S16) +- removed patches that touches the initscript, provide our own + initscript and remove deprecated calls to "initlog" from there (S17) +- fix attribs on the doc files + +* Sun Feb 12 2006 Oden Eriksson 4.3p2-1mdk +- 4.3p2 (Minor bugfixes) + +* Fri Feb 10 2006 Michael Scherer 4.3p1-3mdk +- add a avahi service file for ssh and sftp + +* Fri Feb 10 2006 Oden Eriksson 4.3p1-2mdk +- fix deps +- added P12 to make it possible to use a different sshd binary by using + the /etc/sysconfig/sshd file. also add that file (David Walluck) + +* Wed Feb 01 2006 Oden Eriksson 4.3p1-1mdk +- 4.3p1 (fixes CVE-2006-0225) +- spec file "massage" +- rediff P1 + +* Mon Jan 09 2006 Olivier Blin 4.2p1-13mdk +- fix typo in initscript + +* Mon Jan 09 2006 Olivier Blin 4.2p1-12mdk +- convert parallel init to LSB + +* Mon Jan 02 2006 Oden Eriksson 4.2p1-11mdk +- rebuilt due a missing package + +* Sun Jan 01 2006 Couriousous 4.2p1-10mdk +- Add parallel init stuff + +* Wed Dec 28 2005 Christiaan Welvaart 4.2p1-9mdk +- re-add BuildRequires: xorg-x11 (was removed in previous update) + +* Mon Dec 05 2005 Andreas Hasenack 4.2p1-8mdk +- fixed X11 buildrequires (used the x11askpass is built) + +* Sun Dec 04 2005 Andreas Hasenack 4.2p1-7mdk +- fixed smart card build (but it's still disabled by default) + +* Sun Nov 13 2005 Oden Eriksson 4.2p1-6mdk +- rebuilt against openssl-0.9.8a + +* Thu Nov 10 2005 Olivier Blin 4.2p1-5mdk +- fix gnome-ssh-askpass.sh generation + +* Sun Nov 06 2005 Oden Eriksson 4.2p1-4mdk +- update S8 (openssh-4.2p1.sftplogging-v1.4.patch) +- update S10 (openssh-4.0p1-watchdog.patch) +- update P10 + +* Sun Nov 06 2005 Guillaume Rousse 4.2p1-3mdk +- use here-in document for generating profile scripts, so as to get correct installation location + +* Thu Oct 13 2005 Oden Eriksson 4.2p1-2mdk +- rebuilt against openssl-0.9.7h + +* Tue Sep 06 2005 Oden Eriksson 4.2p1-1mdk +- 4.2p1 (Minor security fixes) + +* Fri Aug 19 2005 Oden Eriksson 4.1p1-9mdk +- make the --with[out] stuff work (Andrzej Kukula) + +* Wed Aug 17 2005 Leonardo Chiquitto Filho 4.1p1-8mdk +- add a conflict on openssh-clients with versions prior to 6mdk because + of the scp change +- fix typo in description + +* Wed Aug 17 2005 Oden Eriksson 4.1p1-7mdk +- fix #17491 + +* Sun Jul 31 2005 Oden Eriksson 4.1p1-6mdk +- fix the "executable-marked-as-config-file" errors + +* Sun Jul 31 2005 Oden Eriksson 4.1p1-5mdk +- updated the ldap public key patch (P6) to v0.3.6 + +* Wed Jul 06 2005 Stew Benedict 4.1p1-4mdk +- openssh-server provides sshd (Zero_Dogg, cooker IRC) + openssh-client provides ssh + +* Wed Jun 15 2005 Stew Benedict 4.1p1-3mdk +- --without-zlib-version-check (Oden, for backports) + +* Sat Jun 11 2005 Buchan Milne 4.1p1-2mdk +- Rebuild + +* Wed Jun 01 2005 Stew Benedict 4.1p1-1mdk +- 4.1p1 +- fix ssh-client.sh (#16180, Claudio) +- construct the x11-ssh-askpass.1.html file manually as it + sometimes seems to fail (Oden) + +* Thu May 05 2005 Stew Benedict 4.0p1-2mdk +- rebuild, upload bot lost openssh-askpass somewhere + +* Tue May 03 2005 Stew Benedict 4.0p1-1mdk +- 4.0p1, redo P1, remove P9 (merged upstream) +- new S8 (sftplogging), new P10 (chroot, upstream patch malformed? - fix) +- new P6, drop P7, reverse a bit of P1 so P6 can apply unchanged (ldap) + +* Mon Apr 25 2005 Oden Eriksson 3.9p1-10mdk +- rebuilt against latests openssl + +* Tue Mar 22 2005 Stew Benedict 3.9p1-9mdk +- README.chroot (Bruno Cornec) + +* Mon Mar 21 2005 Stew Benedict 3.9p1-8mdk +- optional chroot build (http://chrootssh.sourceforge.net, Bruno Cornec) +- spec massages - Oden +- use fuzz 3 with sftplogging patch if ldap is used + +* Fri Mar 04 2005 Stew Benedict 3.9p1-7mdk +- enable krb5, GSSAPI - (Bugzilla 14222) +- fix "need to reset console after ctrl-c" (Bugzilla 14153, P9) +- script-without-shellbang (Source 4,5,6) + +* Mon Jan 03 2005 Stew Benedict 3.9p1-6mdk +- drop reference to renamed README.mdk in description (Dick Gevers) + +* Fri Dec 31 2004 Christiaan Welvaart 3.9p1-5mdk +- add BuildRequires: XFree86 (for rman) + +* Mon Dec 27 2004 Stew Benedict 3.9p1-4mdk +- optional sftplogging build (http://sftplogging.sourceforge.net, Josh Sehn) + +* Tue Sep 14 2004 Stew Benedict 3.9p1-3mdk +- accept only protocol 2 as default for sshd (redo patch1, #11413) +- rename Source11, add note about protocol change + +* Fri Sep 10 2004 Stew Benedict 3.9p1-2mdk +- rediff ldap patch (Buchan Milne) +- add sample ssh_ldap_key.pl (Buchan Milne) + +* Fri Aug 20 2004 Stew Benedict 3.9p1-1mdk +- 3.9p1, rework patch1 + +* Fri Jul 30 2004 Stew Benedict 3.8.1p1-3mdk +- move app-defaults file to correct dir (Peggy KUTYLA) + +* Thu Jun 17 2004 Stew Benedict 3.8.1p1-2mdk +- definitive fix for ldap support (patch7, Tibor Pittich) + +* Sat Jun 12 2004 Stew Benedict 3.8.1p1-1mdk +- 3.8.1p1, rework patch1 (config) +- mod to patch6 from Buchan (ldap) +- trigger doesn't need epoch now (was running on rpm -e) + +* Fri Jun 11 2004 Stew Benedict 3.8p1-4mdk +- add README.mdk to docs to explain differences from <= 3.6.1p2 +- add trigger to try and catch alternative auth methods on upgrade, + re-enabling PAM if in use (Bugzilla #9800, thx Buchan) +- add optional (--with ldap) support for authenticating to public keys + stored in ldap (Buchan Milne) + +* Tue Jun 08 2004 Stew Benedict 3.8p1-3mdk +- add "ForwardX11Trusted yes" to ssh_config so X11 forwarding works + (patch1, Bugzilla #9719) + +* Tue May 11 2004 Stew Benedict 3.8p1-2mdk +- modified pam stack so enabling UsePAM doesn't change +- "PermitRootLogin without-password" behavior (rework patch1) +- "root" in /etc/ssh/denyusers + diff --git a/openssh5.1-peaktput.diff b/openssh5.1-peaktput.diff new file mode 100644 index 0000000..47f7877 --- /dev/null +++ b/openssh5.1-peaktput.diff @@ -0,0 +1,72 @@ +--- ../openssh-5.1p1/progressmeter.c 2006-08-04 22:39:40.000000000 -0400 ++++ ./progressmeter.c 2008-07-29 14:33:13.000000000 -0400 +@@ -68,6 +68,8 @@ + static char *file; /* name of the file being transferred */ + static off_t end_pos; /* ending position of transfer */ + static off_t cur_pos; /* transfer position as of last refresh */ ++static off_t last_pos; ++static off_t max_delta_pos = 0; + static volatile off_t *counter; /* progress counter */ + static long stalled; /* how long we have been stalled */ + static int bytes_per_second; /* current speed in bytes per second */ +@@ -128,12 +130,17 @@ + int hours, minutes, seconds; + int i, len; + int file_len; ++ off_t delta_pos; + + transferred = *counter - cur_pos; + cur_pos = *counter; + now = time(NULL); + bytes_left = end_pos - cur_pos; + ++ delta_pos = cur_pos - last_pos; ++ if (delta_pos > max_delta_pos) ++ max_delta_pos = delta_pos; ++ + if (bytes_left > 0) + elapsed = now - last_update; + else { +@@ -158,7 +165,7 @@ + + /* filename */ + buf[0] = '\0'; +- file_len = win_size - 35; ++ file_len = win_size - 45; + if (file_len > 0) { + len = snprintf(buf, file_len + 1, "\r%s", file); + if (len < 0) +@@ -175,7 +182,8 @@ + percent = ((float)cur_pos / end_pos) * 100; + else + percent = 100; +- snprintf(buf + strlen(buf), win_size - strlen(buf), ++ ++ snprintf(buf + strlen(buf), win_size - strlen(buf-8), + " %3d%% ", percent); + + /* amount transferred */ +@@ -188,6 +196,15 @@ + (off_t)bytes_per_second); + strlcat(buf, "/s ", win_size); + ++ /* instantaneous rate */ ++ if (bytes_left > 0) ++ format_rate(buf + strlen(buf), win_size - strlen(buf), ++ delta_pos); ++ else ++ format_rate(buf + strlen(buf), win_size - strlen(buf), ++ max_delta_pos); ++ strlcat(buf, "/s ", win_size); ++ + /* ETA */ + if (!transferred) + stalled += elapsed; +@@ -224,6 +241,7 @@ + + atomicio(vwrite, STDOUT_FILENO, buf, win_size - 1); + last_update = now; ++ last_pos = cur_pos; + } + + /*ARGSUSED*/ diff --git a/openssh_tcp_wrappers.patch b/openssh_tcp_wrappers.patch new file mode 100644 index 0000000..5670053 --- /dev/null +++ b/openssh_tcp_wrappers.patch @@ -0,0 +1,19 @@ +--- + sshd.c | 4 2 + 2 - 0 ! + 1 file changed, 2 insertions(+), 2 deletions(-) + +Index: openssh-5.2p1/sshd.c +=================================================================== +--- openssh-5.2p1.orig/sshd.c 2009-01-28 00:31:23.000000000 -0500 ++++ openssh-5.2p1/sshd.c 2009-05-28 13:00:03.000000000 -0400 +@@ -122,8 +122,8 @@ + #ifdef LIBWRAP + #include + #include +-int allow_severity; +-int deny_severity; ++extern int allow_severity; ++extern int deny_severity; + #endif /* LIBWRAP */ + + #ifndef O_NOCTTY diff --git a/ssh-avahi-integration b/ssh-avahi-integration new file mode 100644 index 0000000..2357507 --- /dev/null +++ b/ssh-avahi-integration @@ -0,0 +1,40 @@ + + + + + + + + + + + + Remote Access on %h + + + _ssh._tcp + 22 + + + _sftp-ssh._tcp + 22 + + + diff --git a/ssh-copy-id b/ssh-copy-id new file mode 100644 index 0000000..dcc8a6d --- /dev/null +++ b/ssh-copy-id @@ -0,0 +1,50 @@ +#!/bin/sh + +# Shell script to install your identity.pub on a remote machine +# Takes the remote machine name as an argument. +# Obviously, the remote machine must accept password authentication, +# or one of the other keys in your ssh-agent, for this to work. + +ID_FILE="${HOME}/.ssh/identity.pub" + +if [ "-i" = "$1" ]; then + shift + # check if we have 2 parameters left, if so the first is the new ID file + if [ -n "$2" ]; then + if expr "$1" : ".*\.pub" ; then + ID_FILE="$1" + else + ID_FILE="$1.pub" + fi + shift # and this should leave $1 as the target name + fi +else + if [ x$SSH_AUTH_SOCK != x ] ; then + GET_ID="$GET_ID ssh-add -L" + fi +fi + +if [ $# != 1 ]; then + echo "usage: ssh-copy-id [-i identity_file] [user@]hostname" + exit 1 +fi + +if [ -z "`eval $GET_ID`" -a -r "${ID_FILE}" ] ; then + GET_ID="cat ${ID_FILE}" +fi + +if [ -z "`eval $GET_ID`" ]; then + echo "$0: ERROR: No identities found" + exit 1 +fi + +{ eval "$GET_ID" ; } | ssh $1 "test -d .ssh || mkdir .ssh ; cat >> .ssh/authorized_keys ; chmod g-w . .ssh .ssh/authorized_keys" + +cat <; +close FH; +chomp @list; +foreach (@list) { +~ /(.+)\s(\w+)\@(.+$)/; +$warez=$1; +$uid=$2; +$warez64 = encode_base64("$warez"); +$warez64 =~ s/\n//g; +print "dn: uid=$uid,ou=People,$DEFAULT_BASE\n"; +print "changetype: modify\n"; +print "add: objectClass\n"; +print "objectClass: strongAuthenticationUser\n"; +print "userCertificate;binary:: $warez64\n\n"; +} +exit; diff --git a/sshd.init b/sshd.init new file mode 100644 index 0000000..ec35a7b --- /dev/null +++ b/sshd.init @@ -0,0 +1,182 @@ +#!/bin/bash +# +# Init file for OpenSSH server daemon +# +# chkconfig: 2345 55 25 +# description: OpenSSH server daemon +# +# processname: sshd +# config: /etc/ssh/ssh_host_key +# config: /etc/ssh/ssh_host_key.pub +# config: /etc/ssh/ssh_random_seed +# config: /etc/ssh/sshd_config +# pidfile: /var/run/sshd.pid +# +### BEGIN INIT INFO +# Provides: sshd +# Required-Start: $network +# Should-Start: $remote_fs +# Required-Stop: $network +# Should-Stop: $remote_fs +# Default-Start: 2 3 4 5 +# Short-Description: OpenSSH server daemon +# Description: OpenSSH server daemon +### END INIT INFO + +# source function library +. /etc/rc.d/init.d/functions + +RETVAL=0 +prog="sshd" + +# Some functions to make the below more readable +KEYGEN=/usr/bin/ssh-keygen +SSHD=/usr/sbin/sshd +RSA1_KEY=/etc/ssh/ssh_host_key +RSA_KEY=/etc/ssh/ssh_host_rsa_key +DSA_KEY=/etc/ssh/ssh_host_dsa_key +PID_FILE=/var/run/sshd.pid + +# pull in sysconfig settings +[ -f /etc/sysconfig/sshd ] && . /etc/sysconfig/sshd + +do_rsa1_keygen() { + if [ ! -s $RSA1_KEY ]; then + echo -n $"Generating SSH1 RSA host key: " + if $KEYGEN -q -t rsa1 -f $RSA1_KEY -C '' -N '' >/dev/null 2>&1; then + chmod 600 $RSA1_KEY + chmod 644 $RSA1_KEY.pub + success $"RSA1 key generation" + echo + else + failure $"RSA1 key generation" + echo + exit 1 + fi + fi +} + +do_rsa_keygen() { + if [ ! -s $RSA_KEY ]; then + echo -n $"Generating SSH2 RSA host key: " + if $KEYGEN -q -t rsa -f $RSA_KEY -C '' -N '' >/dev/null 2>&1; then + chmod 600 $RSA_KEY + chmod 644 $RSA_KEY.pub + success $"RSA key generation" + echo + else + failure $"RSA key generation" + echo + exit 1 + fi + fi +} + +do_dsa_keygen() { + if [ ! -s $DSA_KEY ]; then + echo -n $"Generating SSH2 DSA host key: " + if $KEYGEN -q -t dsa -f $DSA_KEY -C '' -N '' >/dev/null 2>&1; then + chmod 600 $DSA_KEY + chmod 644 $DSA_KEY.pub + success $"DSA key generation" + echo + else + failure $"DSA key generation" + echo + exit 1 + fi + fi +} + +do_restart_sanity_check() +{ + $SSHD -t + RETVAL=$? + if [ ! "$RETVAL" = 0 ]; then + failure $"Configuration file or keys are invalid" + echo + fi +} + +start() +{ + # Create keys if necessary + do_rsa1_keygen + do_rsa_keygen + do_dsa_keygen + + echo -n $"Starting $prog:" + $SSHD $OPTIONS && success "startup" || failure "startup" + RETVAL=$? + [ "$RETVAL" = 0 ] && touch /var/lock/subsys/sshd + echo +} + +stop() +{ + echo -n $"Stopping $prog:" + if [ -r /var/run/sshd.pid ]; then + kill -s TERM `cat /var/run/sshd.pid` + RETVAL=$? + if [ "$runlevel" = 0 -o "$runlevel" = 6 ]; then + # stopping the system, kill active sshd clients + killproc -p "" sshd + fi + [ "$RETVAL" = 0 ] && success "stop" || failure "stop" + else + success "already stopped" + RETVAL=0 + fi + [ "$RETVAL" = 0 ] && rm -f /var/lock/subsys/sshd + echo +} + +reload() +{ + echo -n $"Reloading $prog:" + if [ -r /var/run/sshd.pid ]; then + kill -s HUP `cat /var/run/sshd.pid` + RETVAL=$? + [ "$RETVAL" = 0 ] && success "config reload" || failure "config reload" + else + failure "not running so config reload" + RETVAL=1 + fi + echo +} + +case "$1" in + start) + start + ;; + stop) + stop + ;; + restart) + stop + sleep 1 + start + ;; + reload) + reload + ;; + condrestart) + if [ -f /var/lock/subsys/sshd ] ; then + do_restart_sanity_check + if [ "$RETVAL" = 0 ] ; then + stop + # avoid race + sleep 3 + start + fi + fi + ;; + status) + status $SSHD + RETVAL=$? + ;; + *) + echo $"Usage: $0 {start|stop|restart|reload|condrestart|status}" + RETVAL=1 +esac +exit $RETVAL diff --git a/sshd.pam b/sshd.pam new file mode 100644 index 0000000..9921c6f --- /dev/null +++ b/sshd.pam @@ -0,0 +1,7 @@ +#%PAM-1.0 +auth required pam_listfile.so item=user sense=deny file=/etc/ssh/denyusers +auth include system-auth +account required pam_nologin.so +account include system-auth +password include system-auth +session include system-auth diff --git a/sshd.pam-0.77 b/sshd.pam-0.77 new file mode 100644 index 0000000..9352cf8 --- /dev/null +++ b/sshd.pam-0.77 @@ -0,0 +1,7 @@ +#%PAM-1.0 +auth required pam_listfile.so item=user sense=deny file=/etc/ssh/denyusers +auth required pam_stack.so service=system-auth +auth required pam_nologin.so +account required pam_stack.so service=system-auth +password required pam_stack.so service=system-auth +session required pam_stack.so service=system-auth