AIX 4.3.3 + sshd = bug

Sandor W. Sklar ssklar at stanford.edu
Tue Mar 6 05:32:24 EST 2001


Hello,

I believe that there is a bug in OpenSSH that affects its usage on 
AIX 4.3.3 - Maintenance Level 3 and higher.  This bug was introduced 
by a change by IBM in the "/usr/lib/drivers/ptydd" driver, and it 
affected IBM's own telnetd daemon (reference 
<http://techsupport.services.ibm.com/rs6000/aix.uhuic_getrec?args=DVhuron.boulder.ibm.com+DBAIX+DA69743+STIY09667+USbin>). 
However, IBM chose not to fix the cause of the problem, but to 
instead modify telnetd to deal with the issue.

The problem occurs in the sshd program; when a program on the server 
writes a zero-length string to the terminal, the sshd daemon abruptly 
closes the connection, logging no information.  The following code 
causes the problem to exhibit itself:

#include <stdio.h>
#include <fcntl.h>
main()
{
     int tty_fd;
     int old_tty_fd;
     int old_stdout_fd;
     char str[100];

     old_tty_fd = open("/dev/tty",O_RDWR);
     tty_fd = dup(old_tty_fd);    /* 1 will be /dev/tty */
     close(old_tty_fd);

     strcpy(str,"this is the last thing you will see if sshd is broken.\n");
         fprintf(stderr,"len = %d str = %s",strlen(str),str);
     write(tty_fd,str,strlen(str));
     strcpy(str,"");
         fprintf(stderr,"len = %d str = %s\n",strlen(str),str);
     write(tty_fd,str,strlen(str));    /* we die here on 433 */
         fprintf(stderr,"if you can read this then all is good.\n");
}


This bug pops up with both OpenSSH 2.3.0.p1 and 2.5.1p1 (and with the 
commercial ssh 1.2.26), but only when the daemon is running on 
4.3.3-ML3 or higher.  The same daemon works fine on AIX 4.3.2-ML2, 
and 4.3.3 with no ML applied.

With a lot of help, I figured that the cause of the disconnect is a 
comparison in the "serverloop.c" file.  Changing the comparison 
operator from a "<=" to just a "<" in the serverloop.c file fixes the 
issue.  Here is the code block (taken from the 2.3.0p1 source 
distribution:

   +304          /* Read and buffer any available stdout data from the 
program. */
   +305          if (!fdout_eof && FD_ISSET(fdout, readset)) {
   +306                  len = read(fdout, buf, sizeof(buf));
   +307                  if (len < 0 && (errno == EINTR || errno == EAGAIN)) {
   +308                          /* do nothing */
   +309                  } else if (len <= 0) {
   +310                          fdout_eof = 1;
   +311                  } else {
   +312                          buffer_append(&stdout_buffer, buf, len);
   +313                          fdout_bytes += len;
   +314                  }

Line # 309 needs to be changed to ...

   +309                  } else if (len < 0) {


Making the above change in the 2.3.0p1 and the 2.5.1p1 source 
distributions solves the problem, however, I don't know if there 
might be any other ill effect, or if the change will have an effect 
on other platforms.

Thanks,
--Sandy

-- 
sandor w. sklar                 http://lindy.stanford.edu/~ssklar/
unix systems administrator      polya hall, 255 panama -- mc: 4136
stanford university itss-css    mailto:ssklar at stanford.edu







More information about the openssh-unix-dev mailing list