[990] in Kerberos-V5-bugs

home help back first fref pref prev next nref lref last post

Encrypted rsh

daemon@ATHENA.MIT.EDU (Andrew Gross)
Sat Dec 17 04:02:56 1994

Date: Sat, 17 Dec 94 01:02:25 -0800
From: Andrew Gross <drew@drew.sdsc.edu>
To: krb5-bugs@MIT.EDU


Hello,

   Attached are patches that I made to appl/bsd/krsh.c and
appl/bsd/krshd.c to add encrypted rshs.  I just grabbed port
2106 for ekshell in /etc/services.

Andrew Gross
=========================================================================
*** xrsh.c	Fri Nov 11 02:49:43 1994
--- krsh.c	Thu Aug 18 14:05:09 1994
***************
*** 74,96 ****
  char	*krb_realm = (char *)0;
  void	try_normal();
  #define UCB_RSH "/usr/ucb/rsh"
- 
- #ifdef BUFSIZ
- #undef BUFSIZ
  #endif
- #define BUFSIZ 4096
  
- char des_inbuf[2*BUFSIZ];       /* needs to be > largest read size */
- char des_outbuf[2*BUFSIZ];      /* needs to be > largest write size */
- krb5_data desinbuf,desoutbuf;
- krb5_encrypt_block eblock;      /* eblock for encrypt/decrypt */
- krb5_creds *cred;
- int encrypt_flag=0;
- #else
- #define des_read read
- #define des_write write
- #endif
- 
  #ifndef RLOGIN_PROGRAM
  #ifdef KERBEROS
  #define RLOGIN_PROGRAM KRB5_PATH_RLOGIN
--- 74,81 ----
***************
*** 123,128 ****
--- 108,114 ----
      krb5_flags authopts;
      krb5_error_code status;
      int fflag = 0, Fflag = 0;
+     int xflag = 0;
      int debug_port = 0;
  #endif  /* KERBEROS */
     
***************
*** 183,189 ****
       */
      if (argc > 0 && !strncmp(*argv, "-x", 2)) {
  	argv++, argc--;
! 	encrypt_flag++;
  	goto another;
      }
      if (argc > 0 && !strncmp(*argv, "-f", 2)) {
--- 169,175 ----
       */
      if (argc > 0 && !strncmp(*argv, "-x", 2)) {
  	argv++, argc--;
! 	xflag++;
  	goto another;
      }
      if (argc > 0 && !strncmp(*argv, "-f", 2)) {
***************
*** 269,282 ****
         given and rlogin is not run, because the user could be
         dangerously confused otherwise.  He might think he's got a
         secure rsh channel, and there's no such thing yet.  */
! /*
!     if (encrypt_flag)
        {
  	fprintf (stderr, "%s: Encrypted rsh is not yet available.\n",
  		 argv0[0]);
  	return 1;
        }
- */
  
      pwd = getpwuid(getuid());
      if (pwd == 0) {
--- 255,266 ----
         given and rlogin is not run, because the user could be
         dangerously confused otherwise.  He might think he's got a
         secure rsh channel, and there's no such thing yet.  */
!     if (xflag)
        {
  	fprintf (stderr, "%s: Encrypted rsh is not yet available.\n",
  		 argv0[0]);
  	return 1;
        }
  
      pwd = getpwuid(getuid());
      if (pwd == 0) {
***************
*** 295,303 ****
  	  *cp++ = ' ';
      }
  #ifdef KERBEROS
-     if (encrypt_flag)
-       sp = getservbyname("ekshell","tcp");
-     else
        sp = getservbyname("kshell", "tcp");
  #else 
      sp = getservbyname("shell", "tcp");
--- 279,284 ----
***************
*** 304,311 ****
  #endif  /* KERBEROS */
      if (sp == 0) {
  #ifdef KERBEROS
! 	fprintf(stderr, "rsh: %s/tcp: unknown service\n",
! 		encrypt_flag ? "ekshell" : "kshell");
  	try_normal(argv0);
  #else 
  	fprintf(stderr, "rsh: shell/tcp: unknown service\n");
--- 285,291 ----
  #endif  /* KERBEROS */
      if (sp == 0) {
  #ifdef KERBEROS
! 	fprintf(stderr, "rsh: kshell/tcp: unknown service\n");
  	try_normal(argv0);
  #else 
  	fprintf(stderr, "rsh: shell/tcp: unknown service\n");
***************
*** 318,325 ****
      
  #ifdef KERBEROS
      krb5_init_ets();
-     desinbuf.data = des_inbuf;
-     desoutbuf.data = des_outbuf;        /* Set up des buffers */
      authopts = AP_OPTS_MUTUAL_REQUIRED;
  
      /* Piggy-back forwarding flags on top of authopts; */
--- 298,303 ----
***************
*** 333,339 ****
  		  pwd->pw_name,
  		  user ? user : pwd->pw_name,
  		  args, &rfd2, "host", krb_realm,
! 		  &cred,
  		  0,           /* No need for sequence number */
  		  0,           /* No need for server seq # */
  		  (struct sockaddr_in *) 0,
--- 311,317 ----
  		  pwd->pw_name,
  		  user ? user : pwd->pw_name,
  		  args, &rfd2, "host", krb_realm,
! 		  0,		/* No need for returned credentials */
  		  0,           /* No need for sequence number */
  		  0,           /* No need for server seq # */
  		  (struct sockaddr_in *) 0,
***************
*** 346,359 ****
  		error_message(status));
  	try_normal(argv0);
      }
-     /* setup eblock for des_read and write */
-     krb5_use_keytype(&eblock,cred->keyblock.keytype);
-     if ( status = krb5_process_key(&eblock,&cred->keyblock)) {
-         fprintf(stderr,
-                 "%s: Cannot process session key : %s.\n",
-                 argv0, error_message(status));
-         exit(1);
-     }
  #else /* !KERBEROS */
      rem = rcmd(&host, sp->s_port, pwd->pw_name,
  	       user ? user : pwd->pw_name, args, &rfd2);
--- 324,329 ----
***************
*** 397,407 ****
  	    exit(1);
  	}
      }
-     /* as per rlogind, crypto will fail on NB sockets... */
-     if (!encrypt_flag) {
          ioctl(rfd2, FIONBIO, &one);
          ioctl(rem, FIONBIO, &one);
-     }
      if (nflag == 0 && pid == 0) {
  	char *bp; int rembits, wc;
  	(void) close(rfd2);
--- 367,374 ----
***************
*** 422,428 ****
  	}
  	if ((rembits & (1<<rem)) == 0)
  	  goto rewrite;
! 	wc = des_write(rem, bp, cc);
  	if (wc < 0) {
  	    if (errno == EWOULDBLOCK)
  	      goto rewrite;
--- 389,395 ----
  	}
  	if ((rembits & (1<<rem)) == 0)
  	  goto rewrite;
! 	wc = write(rem, bp, cc);
  	if (wc < 0) {
  	    if (errno == EWOULDBLOCK)
  	      goto rewrite;
***************
*** 455,461 ****
  	}
  	if (ready & (1<<rfd2)) {
  	    errno = 0;
! 	    cc = des_read(rfd2, buf, sizeof buf);
  	    if (cc <= 0) {
  		if (errno != EWOULDBLOCK)
  		  readfrom &= ~(1<<rfd2);
--- 422,428 ----
  	}
  	if (ready & (1<<rfd2)) {
  	    errno = 0;
! 	    cc = read(rfd2, buf, sizeof buf);
  	    if (cc <= 0) {
  		if (errno != EWOULDBLOCK)
  		  readfrom &= ~(1<<rfd2);
***************
*** 464,470 ****
  	}
  	if (ready & (1<<rem)) {
  	    errno = 0;
! 	    cc = des_read(rem, buf, sizeof buf);
  	    if (cc <= 0) {
  		if (errno != EWOULDBLOCK)
  		  readfrom &= ~(1<<rem);
--- 431,437 ----
  	}
  	if (ready & (1<<rem)) {
  	    errno = 0;
! 	    cc = read(rem, buf, sizeof buf);
  	    if (cc <= 0) {
  		if (errno != EWOULDBLOCK)
  		  readfrom &= ~(1<<rem);
***************
*** 477,485 ****
      exit(0);
    usage:
      fprintf(stderr,
! 	   "usage: \trsh host [ -l login ] [ -x ] [ -n ] [ -f / -F] command\n");
      fprintf(stderr,
! 	   "OR \trsh [ -l login ] [-n ] [ -x ] [ -f / -F ] host command\n");
      exit(1);
  }
  
--- 444,452 ----
      exit(0);
    usage:
      fprintf(stderr,
! 	    "usage: \trsh host [ -l login ] [ -n ] [ -f / -F] command\n");
      fprintf(stderr,
! 	    "OR \trsh [ -l login ] [-n ] [ -f / -F ] host command\n");
      exit(1);
  }
  
***************
*** 489,495 ****
       char signo;
  {
      
!     (void) des_write(rfd2, &signo, 1);
  }
  
  
--- 456,462 ----
       char signo;
  {
      
!     (void) write(rfd2, &signo, 1);
  }
  
  
***************
*** 507,515 ****
       * We always want to call the Berkeley rsh as 'host mumble'
       */
  
-     if (encrypt_flag)
-       exit(1);
-     
      host = strrchr(argv[0], '/');
      if (host)
        host++;
--- 474,479 ----
***************
*** 525,651 ****
      execv(UCB_RSH, argv);
      perror("exec");
      exit(1);
- }
- 
- char storage[2*BUFSIZ];			/* storage for the decryption */
- int nstored = 0;
- char *store_ptr = storage;
- 
- int des_read(fd, buf, len)
-      int fd;
-      register char *buf;
-      int len;
- {
-     int nreturned = 0;
-     long net_len,rd_len;
-     int cc;
-     
-     if (!encrypt_flag)
-       return(read(fd, buf, len));
-     
-     if (nstored >= len) {
- 	memcpy(buf, store_ptr, len);
- 	store_ptr += len;
- 	nstored -= len;
- 	return(len);
-     } else if (nstored) {
- 	memcpy(buf, store_ptr, nstored);
- 	nreturned += nstored;
- 	buf += nstored;
- 	len -= nstored;
- 	nstored = 0;
-     }
-     
- #ifdef BITS64
-     /*
-      * XXX Ick.  This assumes big endian byte order.
-      */
-     rd_len = 0;
-     if ((cc = krb5_net_read(fd, (char *)&rd_len + 4, 4)) != 4) {
- #else
-     if ((cc = krb5_net_read(fd, (char *)&rd_len, sizeof(rd_len))) !=
- 	    sizeof(rd_len)) {
- #endif
- 		/* XXX can't read enough, pipe
- 		   must have closed */
- 	return(0);
-     }
-     rd_len = ntohl(rd_len);
-     net_len = krb5_encrypt_size(rd_len,eblock.crypto_entry);
-     if (net_len <= 0 || net_len > sizeof(des_inbuf)) {
- 	/* preposterous length; assume out-of-sync; only
- 	   recourse is to close connection, so return 0 */
- 	fprintf(stderr,"Read size problem.\n");
- 	return(0);
-     }
-     if ((cc = krb5_net_read(fd, desinbuf.data, net_len)) != net_len) {
- 	/* pipe must have closed, return 0 */
- 	fprintf(stderr,
- 		"Read error: length received %d != expected %d.\n",
- 		cc,net_len);
- 	return(0);
-     }
-     /* decrypt info */
-     if ((krb5_decrypt(desinbuf.data,
- 		      (krb5_pointer) storage,
- 		      net_len,
- 		      &eblock, 0))) {
- 	fprintf(stderr,"Cannot decrypt data from network.\n");
- 	return(0);
-     }
-     store_ptr = storage;
-     nstored = rd_len;
-     if (nstored > len) {
- 	memcpy(buf, store_ptr, len);
- 	nreturned += len;
- 	store_ptr += len;
- 	nstored -= len;
-     } else {
- 	memcpy(buf, store_ptr, nstored);
- 	nreturned += nstored;
- 	nstored = 0;
-     }
-     
-     return(nreturned);
- }
- 
- 
- 
- int des_write(fd, buf, len)
-      int fd;
-      char *buf;
-      int len;
- {
-     long net_len;
-     
-     if (!encrypt_flag)
-       return(write(fd, buf, len));
-     
-     desoutbuf.length = krb5_encrypt_size(len,eblock.crypto_entry);
-     if (desoutbuf.length > sizeof(des_outbuf)){
- 	fprintf(stderr,"Write size problem.\n");
- 	return(-1);
-     }
-     if (( krb5_encrypt((krb5_pointer)buf,
- 		       desoutbuf.data,
- 		       len,
- 		       &eblock,
- 		       0))){
- 	fprintf(stderr,"Write encrypt problem.\n");
- 	return(-1);
-     }
- 
-     
-     net_len = htonl(len);
- #ifdef BITS64
-     (void) write(fd,(char *)&net_len + 4, 4);
- #else
-     (void) write(fd, &net_len, sizeof(net_len));
- #endif
-     if (write(fd, desoutbuf.data,desoutbuf.length) != desoutbuf.length){
- 	fprintf(stderr,"Could not write out all data.\n");
- 	return(-1);
-     }
-     else return(len);
  }
  #endif /* KERBEROS */
--- 489,493 ----
========================================================================
*** xrshd.c	Fri Nov 11 02:51:02 1994
--- krshd.c	Tue Nov  8 23:24:57 1994
***************
*** 64,71 ****
       
  /* DEFINES:
   *   KERBEROS - Define this if application is to be kerberised.
!  *   KRB5_KRB4_COMPAT - Define this if v4 rlogin clients are also to be served.
!  *   CRYPT    - Define this if encryption is to be an option.
   *   ALWAYS_V5_KUSEROK - Define this if you want .k5login to be
   *              checked even for v4 clients (instead of .klogin).
   *   LOG_ALL_LOGINS - Define this if you want to log all logins.
--- 64,70 ----
       
  /* DEFINES:
   *   KERBEROS - Define this if application is to be kerberised.
!  *   SERVE_V4 - Define this if v4 rlogin clients are also to be served.
   *   ALWAYS_V5_KUSEROK - Define this if you want .k5login to be
   *              checked even for v4 clients (instead of .klogin).
   *   LOG_ALL_LOGINS - Define this if you want to log all logins.
***************
*** 80,87 ****
   *       Note:  Root account access is always logged.
   */
       
! #define CRYPT
! /*#define SERVE_NON_KRB     */
  #define LOG_REMOTE_REALM
  #define LOG_ALL_LOGINS
  #define LOG_CMD
--- 79,86 ----
   *       Note:  Root account access is always logged.
   */
       
! #define SERVE_V4
! #define SERVE_NON_KRB     
  #define LOG_REMOTE_REALM
  #define LOG_ALL_LOGINS
  #define LOG_CMD
***************
*** 170,209 ****
  #include <krb5/crc-32.h>
  #include <krb5/mit-des.h>
  #include <krb5/ext-proto.h>
- #include <kerberosIV/krb.h>
  
  #include <com_err.h>
  
  #include "loginpaths.h"
  
- #ifdef BUFSIZ
- #undef BUFSIZ
- #endif
- 
- int auth_sys = 0;       /* Which version of Kerberos used to
- authenticate */
- 
- #define KRB5_RECVAUTH_V4        4
- #define KRB5_RECVAUTH_V5        5
- 
- AUTH_DAT        *v4_kdata;
- Key_schedule v4_schedule;
- int v4_des_read(), v4_des_write();
- 
- #define BUFSIZ 5120
- 
- int v5_des_read(), v5_des_write();
- 
- #define SECURE_MESSAGE  "This rsh session is using DES encryption for all data transmissions.\r\n"
- 
- int (*des_read)(), (*des_write)();
- char des_inbuf[2*BUFSIZ];         /* needs to be > largest read size */
- krb5_encrypt_block eblock;        /* eblock for encrypt/decrypt */
- char des_outbuf[2*BUFSIZ];        /* needs to be > largest write size */
- krb5_data desinbuf,desoutbuf;
- #define MAXRETRIES 4
- 
- 
  #ifndef SETPGRP_TWOARG
  #define setpgrp(a,b) setpgrp()
  #endif
--- 169,179 ----
***************
*** 225,241 ****
  #endif
  /** XXX **/
  
! void fatal();
! #define ARGSTR	"rRxXeEkKD:?"
  #else /* !KERBEROS */
  #define ARGSTR	"rRD:?"
- #define (*des_read)  read
- #define (*des_write) write
  
  #endif /* KERBEROS */
       
  int must_pass_rhosts = 0, must_pass_k5 = 0, must_pass_one = 0;
! int failed_k5 = 0, do_encrypt = 0, netf = -1;
  char *progname;
  
  #define MAX_PROG_NAME 10
--- 195,208 ----
  #endif
  /** XXX **/
  
! #define ARGSTR	"rRkKD:?"
  #else /* !KERBEROS */
  #define ARGSTR	"rRD:?"
       
  #endif /* KERBEROS */
       
  int must_pass_rhosts = 0, must_pass_k5 = 0, must_pass_one = 0;
! int failed_k5 = 0;
  char *progname;
  
  #define MAX_PROG_NAME 10
***************
*** 279,286 ****
  #ifndef LOG_DAEMON
  #define LOG_DAEMON 0
  #endif
! /*    openlog(progname, LOG_PID | LOG_ODELAY, LOG_DAEMON);	*/
!     openlog(progname, LOG_PID | LOG_ODELAY, LOG_LOCAL6);	
  #endif /* 4.2 syslog */
      
      if (argc == 1) { /* Get parameters from program name. */
--- 246,252 ----
  #ifndef LOG_DAEMON
  #define LOG_DAEMON 0
  #endif
!     openlog(progname, LOG_PID | LOG_ODELAY, LOG_DAEMON);	
  #endif /* 4.2 syslog */
      
      if (argc == 1) { /* Get parameters from program name. */
***************
*** 326,340 ****
  	  if (must_pass_one)
  	    must_pass_one = 0;
  	  break;
- #ifdef CRYPT
-         case 'x':         /* Use encryption. */
-         case 'X':
-         case 'e':
-         case 'E':
-           do_encrypt = 1;
-           break;
  #endif
- #endif
  	case 'D':
  	  debug_port = atoi(optarg);
  	  break;
--- 292,298 ----
***************
*** 466,477 ****
  krb5_principal client;
  krb5_authenticator *kdata;
  
! #ifdef KRB5_KRB4_COMPAT
  #include <kerberosIV/krb.h>
  AUTH_DAT	*v4_kdata;
  KTEXT		v4_ticket;
  #endif
  
  
  #define KRB5_RECVAUTH_V4	4
  #define KRB5_RECVAUTH_V5	5
--- 424,436 ----
  krb5_principal client;
  krb5_authenticator *kdata;
  
! #ifdef SERVE_V4
  #include <kerberosIV/krb.h>
  AUTH_DAT	*v4_kdata;
  KTEXT		v4_ticket;
  #endif
  
+ int auth_sys = 0;	/* Which version of Kerberos used to authenticate */
  
  #define KRB5_RECVAUTH_V4	4
  #define KRB5_RECVAUTH_V5	5
***************
*** 485,491 ****
  #ifdef KERBEROS
      krb5_address peeraddr;
      krb5_error_code status;
-     char buferror[255];
  #endif
  
      int tmpint;
--- 444,449 ----
***************
*** 521,527 ****
      struct hostent *hp;
      char *hostname;
      short port;
!     int pv[2], pw[2], cc;
      long ready, readfrom;
      char buf[BUFSIZ], sig;
      int one = 1;
--- 479,485 ----
      struct hostent *hp;
      char *hostname;
      short port;
!     int pv[2], cc;
      long ready, readfrom;
      char buf[BUFSIZ], sig;
      int one = 1;
***************
*** 564,573 ****
  	exit(1);
      }
  #ifdef KERBEROS
-     netf = f;
      krb5_init_ets();
-     desinbuf.data = des_inbuf;
-     desoutbuf.data = des_outbuf;    /* Set up des buffers */
      if ((must_pass_rhosts || must_pass_one)
  	&& (fromp->sin_port >= IPPORT_RESERVED ||
  	    fromp->sin_port < IPPORT_RESERVED/2))
--- 522,528 ----
***************
*** 677,687 ****
  	error("Authentication failed: %s\n", error_message(status));
  	exit(1);
      }
- #ifndef KRB5_KRB4_COMPAT
-     if (auth_sys == KRB5_RECVAUTH_V4) {
-           fatal(f, "This server does not support Kerberos V4");
-   }
- #endif
  #else
      getstr(f, remuser, sizeof(remuser), "remuser");
      getstr(f, locuser, sizeof(locuser), "locuser");
--- 632,637 ----
***************
*** 704,710 ****
      }
  #endif /* CRAY */
      
!     pwd = (struct passwd *)getpwnam(locuser);
      if (pwd == (struct passwd *) 0 ) {
  	syslog(LOG_ERR ,
  	       "Principal %s (%s@%s) for local user %s has no account.\n",
--- 654,660 ----
      }
  #endif /* CRAY */
      
!     pwd = getpwnam(locuser);
      if (pwd == (struct passwd *) 0 ) {
  	syslog(LOG_ERR ,
  	       "Principal %s (%s@%s) for local user %s has no account.\n",
***************
*** 1071,1077 ****
        }
  #endif
      
!     (void) write(2, "", 1);
      
      if (port) {
  	if (pipe(pv) < 0) {
--- 1021,1027 ----
        }
  #endif
      
!     (void) write(2, "\0", 1);
      
      if (port) {
  	if (pipe(pv) < 0) {
***************
*** 1078,1087 ****
  	    error("Can't make pipe.\n");
  	    goto signout_please;
  	}
- 	if (pipe(pw) < 0) {
- 	    error("Can't make pipe 2.\n");
- 	    goto signout_please;
- 	}
  	pid = fork();
  	if (pid == -1)  {
  	    error("Fork failed.\n");
--- 1028,1033 ----
***************
*** 1096,1113 ****
  	    signal(SIGCHLD,SIG_IGN);
  	    
  	    (void) close(0); (void) close(1); (void) close(2);
! 	    /*(void) close(f);*/ (void) close(pv[1]); (void) close(pw[1]);
! 	    readfrom = (1L<<s) | (1L<<pv[0]) | (1L<<pw[0]);
! #ifdef KERBEROS
!             if (do_encrypt) {
!                 if (((*des_write)(s, SECURE_MESSAGE, sizeof(SECURE_MESSAGE))) < 0){
!                     sprintf(buferror, "Cannot encrypt-write network.");
!                     fatal(pw[0],buferror);
!                 }
!             }
! #endif
  	    ioctl(pv[0], FIONBIO, (char *)&one);
- 	    ioctl(pw[0], FIONBIO, (char *)&one);
  	    /* should set s nbio! */
  	    do {
  		ready = readfrom;
--- 1042,1050 ----
  	    signal(SIGCHLD,SIG_IGN);
  	    
  	    (void) close(0); (void) close(1); (void) close(2);
! 	    (void) close(f); (void) close(pv[1]);
! 	    readfrom = (1L<<s) | (1L<<pv[0]);
  	    ioctl(pv[0], FIONBIO, (char *)&one);
  	    /* should set s nbio! */
  	    do {
  		ready = readfrom;
***************
*** 1115,1121 ****
  			   (fd_set *)0, (struct timeval *)0) < 0)
  		  break;
  		if (ready & (1L<<s)) {
! 		    if ((*des_read)(s, &sig, 1) <= 0)
  		      readfrom &= ~(1L<<s);
  		    else {
  			signal(sig, cleanup);
--- 1052,1058 ----
  			   (fd_set *)0, (struct timeval *)0) < 0)
  		  break;
  		if (ready & (1L<<s)) {
! 		    if (read(s, &sig, 1) <= 0)
  		      readfrom &= ~(1L<<s);
  		    else {
  			signal(sig, cleanup);
***************
*** 1129,1145 ****
  			shutdown(s, 1+1);
  			readfrom &= ~(1L<<pv[0]);
  		    } else
! 		      (void) (*des_write)(s, buf, cc);
  		}
- 		if (ready & (1L<<pw[0])) {
- 		    errno = 0;
- 		    cc = read(pw[0], buf, sizeof (buf));
- 		    if (cc <= 0) {
- 			shutdown(f, 1+1);
- 			readfrom &= ~(1L<<pw[0]);
- 		    } else
- 		      (void) (*des_write)(f, buf, cc);
- 		}
  	    } while (readfrom);
  #ifdef KERBEROS
  	    syslog(LOG_INFO ,
--- 1066,1073 ----
  			shutdown(s, 1+1);
  			readfrom &= ~(1L<<pv[0]);
  		    } else
! 		      (void) write(s, buf, cc);
  		}
  	    } while (readfrom);
  #ifdef KERBEROS
  	    syslog(LOG_INFO ,
***************
*** 1154,1162 ****
  	    exit(0);
  	}
  	setpgrp(0, getpid());
! 	(void) close(s); (void) close(pv[0]); (void) close(pw[0]);
! 	dup2(pw[1], 1); dup2(pv[1], 2);
! 	(void) close(pv[1]); (void) close(pw[1]);
      }
      
      /*      We are simply execing a program over rshd : log entry into wtmp, 
--- 1082,1090 ----
  	    exit(0);
  	}
  	setpgrp(0, getpid());
! 	(void) close(s); (void) close(pv[0]);
! 	dup2(pv[1], 2);
! 	(void) close(pv[1]);
      }
      
      /*      We are simply execing a program over rshd : log entry into wtmp, 
***************
*** 1480,1513 ****
  
  #ifdef KERBEROS
  
- void fatal(f, msg)
-      int f;
-      char *msg;
- {
-     char buf[512];
-     int out = 1 ;          /* Output queue of f */
- 
-     buf[0] = '\01';             /* error indicator */
-     (void) sprintf(buf + 1, "%s: %s.\r\n",progname, msg);
-     if ((f == netf) && (pid > 0))
-       (void) (*des_write)(f, buf, strlen(buf));
-     else
-       (void) write(f, buf, strlen(buf));
-     syslog(LOG_ERR,"%s\n",msg);
-     if (pid > 0) {
-         signal(SIGCHLD,SIG_IGN);
-         kill(pid,SIGKILL);
- #ifdef  TIOCFLUSH
-         (void) ioctl(f, TIOCFLUSH, (char *)&out);
- #else
-         (void) ioctl(f, TCFLSH, out);
- #endif
-         cleanup();
-     }
-     exit(1);
- }
- 
- 
  #ifndef KRB_SENDAUTH_VLEN
  #define	KRB_SENDAUTH_VLEN 8	    /* length for version strings */
  #endif
--- 1408,1413 ----
***************
*** 1586,1592 ****
  				  0, /* default rc_type */
  				  0, /* no flags */
  
! 				  do_encrypt ? KOPT_DO_MUTUAL : 0, /*v4_opts*/
  				  "rcmd", /* v4_service */
  				  v4_instance, /* v4_instance */
  				  &peersin, /* foriegn address */
--- 1486,1492 ----
  				  0, /* default rc_type */
  				  0, /* no flags */
  
! 				  0, /*v4_opts*/
  				  "rcmd", /* v4_service */
  				  v4_instance, /* v4_instance */
  				  &peersin, /* foriegn address */
***************
*** 1599,1605 ****
  				  &ticket, /* return ticket */
  				  &kdata, /* return authenticator */
  				  
! 				  &v4_kdata, v4_schedule, v4_version);
  
      if (status) {
  	if (auth_sys == KRB5_RECVAUTH_V5) {
--- 1499,1505 ----
  				  &ticket, /* return ticket */
  				  &kdata, /* return authenticator */
  				  
! 				  &v4_kdata, 0, v4_version);
  
      if (status) {
  	if (auth_sys == KRB5_RECVAUTH_V5) {
***************
*** 1616,1627 ****
      getstr(netf, locuser, sizeof(locuser), "locuser");
      getstr(netf, cmdbuf, sizeof(cmdbuf), "command");
  
- #ifdef KRB5_KRB4_COMPAT
      if (auth_sys == KRB5_RECVAUTH_V4) {
- 
-         des_read  = v4_des_read;
-         des_write = v4_des_write;
- 
  	/* We do not really know the remote user's login name.
           * Assume it to be the same as the first component of the
  	 * principal's name. 
--- 1516,1522 ----
***************
*** 1637,1666 ****
  	  return(status);
  	return 0;
      }
- #endif
  
      /* Must be V5  */
  
-     des_read  = v5_des_read;
-     des_write = v5_des_write;
- 	
      getstr(netf, remuser, sizeof(locuser), "remuser");
  
      if (status = krb5_unparse_name(client, &kremuser))
  	return status;
  
-     /* Setup up eblock if encrypted login session */
-     /* otherwise zero out session key */
-     if (do_encrypt) {
-         krb5_use_keytype(&eblock,
-                          ticket->enc_part2->session->keytype);
-         if (status = krb5_process_key(&eblock,
-                                       ticket->enc_part2->session))
-             fatal(netf, "Permission denied");
- 	ticket->enc_part2->session=0;
-     }
- 
-     
      if (status = krb5_read_message((krb5_pointer)&netf, &inbuf)) {
  	error("Error reading message: %s\n",
  	      error_message(status));
--- 1532,1545 ----
***************
*** 1678,1951 ****
      return 0;
  }
  
- 
- char storage[2*BUFSIZ];                    /* storage for the decryption */
- int nstored = 0;
- char *store_ptr = storage;
- 
- int
- v5_des_read(fd, buf, len)
-      int fd;
-      register char *buf;
-      int len;
- {
-     int nreturned = 0;
-     long net_len,rd_len;
-     int cc,retry;
-     
-     if (!do_encrypt)
-       return(read(fd, buf, len));
-     
-     if (nstored >= len) {
- 	memcpy(buf, store_ptr, len);
- 	store_ptr += len;
- 	nstored -= len;
- 	return(len);
-     } else if (nstored) {
- 	memcpy(buf, store_ptr, nstored);
- 	nreturned += nstored;
- 	buf += nstored;
- 	len -= nstored;
- 	nstored = 0;
-     }
-     
- #ifdef BITS64
-     rd_len = 0;
-     if ((cc = krb5_net_read(fd, (char *)&rd_len + 4, 4)) != 4) {
- #else	
-     if ((cc = krb5_net_read(fd, (char *)&rd_len, sizeof(rd_len))) !=
- 	sizeof(rd_len)) {
- #endif
- 	if ((cc < 0)  && (errno == EWOULDBLOCK)) return(cc);
- 	/* XXX can't read enough, pipe
- 	   must have closed */
- 	return(0);
-     }
-     rd_len = ntohl(rd_len);
-     net_len = krb5_encrypt_size(rd_len,eblock.crypto_entry);
-     if (net_len < 0 || net_len > sizeof(des_inbuf)) {
- 	/* XXX preposterous length, probably out of sync.
- 	   act as if pipe closed */
- 	syslog(LOG_ERR,"Read size problem.");
- 	return(0);
-     }
-     retry = 0;
-   datard:
-     if ((cc = krb5_net_read(fd, desinbuf.data, net_len)) != net_len) {
- 	/* XXX can't read enough, pipe
- 	   must have closed */
- 	if ((cc < 0)  && (errno == EWOULDBLOCK)) {
- 	    retry++;
- 	    sleep(1);
- 	    if (retry > MAXRETRIES){
- 		syslog(LOG_ERR,
- 		       "des_read retry count exceeded %d\n",
- 		       retry);
- 		return(0);
- 	    }
- 	    goto datard;
- 	}
- 	syslog(LOG_ERR,
- 	       "Read data received %d != expected %d.",
- 	       cc, net_len);
- 	return(0);
-     }
-     /* decrypt info */
-     if ((krb5_decrypt(desinbuf.data,
- 		      (krb5_pointer) storage,
- 		      net_len,
- 		      &eblock, 0))) {
- 	syslog(LOG_ERR,"Read decrypt problem.");
- 	return(0);
-     }
-     store_ptr = storage;
-     nstored = rd_len;
-     if (nstored > len) {
- 	memcpy(buf, store_ptr, len);
- 	nreturned += len;
- 	store_ptr += len;
- 	nstored -= len;
-     } else {
- 	memcpy(buf, store_ptr, nstored);
- 	nreturned += nstored;
- 	nstored = 0;
-     }
-     return(nreturned);
- }
-     
- 
- int
- v5_des_write(fd, buf, len)
-      int fd;
-      char *buf;
-      int len;
- {
-     long net_len;
-     
-     if (!do_encrypt)
-       return(write(fd, buf, len));
-     
-     
-     desoutbuf.length = krb5_encrypt_size(len,eblock.crypto_entry);
-     if (desoutbuf.length > sizeof(des_outbuf)){
- 	syslog(LOG_ERR,"Write size problem.");
- 	return(-1);
-     }
-     if ((krb5_encrypt((krb5_pointer)buf,
- 		      desoutbuf.data,
- 		      len,
- 		      &eblock,
- 		      0))){
- 	syslog(LOG_ERR,"Write encrypt problem.");
- 	return(-1);
-     }
-     
-     net_len = htonl(len);	
- #ifdef BITS64
-     (void) write(fd,(char *)&net_len + 4, 4);
- #else
-     (void) write(fd, &net_len, sizeof(net_len));
- #endif
-     if (write(fd, desoutbuf.data,desoutbuf.length) != desoutbuf.length){
- 	syslog(LOG_ERR,"Could not write out all data.");
- 	return(-1);
-     }
-     else return(len);
- }
- 
- #ifdef KRB5_KRB4_COMPAT
- 
- int
- v4_des_read(fd, buf, len)
- int fd;
- register char *buf;
- int len;
- {
- 	int nreturned = 0;
- 	long net_len, rd_len;
- 	int cc;
- 
- 	if (!do_encrypt)
- 		return(read(fd, buf, len));
- 
- 	if (nstored >= len) {
- 		memcpy(buf, store_ptr, len);
- 		store_ptr += len;
- 		nstored -= len;
- 		return(len);
- 	} else if (nstored) {
- 		memcpy(buf, store_ptr, nstored);
- 		nreturned += nstored;
- 		buf += nstored;
- 		len -= nstored;
- 		nstored = 0;
- 	}
- 	
- 	if ((cc = krb_net_read(fd, &net_len, sizeof(net_len))) != sizeof(net_len)) {
- 		/* XXX can't read enough, pipe
- 		   must have closed */
- 		return(0);
- 	}
- 	net_len = ntohl(net_len);
- 	if (net_len < 0 || net_len > sizeof(des_inbuf)) {
- 		/* XXX preposterous length, probably out of sync.
- 		   act as if pipe closed */
- 		return(0);
- 	}
- 	/* the writer tells us how much real data we are getting, but
- 	   we need to read the pad bytes (8-byte boundary) */
- 	rd_len = roundup(net_len, 8);
- 	if ((cc = krb_net_read(fd, des_inbuf, rd_len)) != rd_len) {
- 		/* XXX can't read enough, pipe
- 		   must have closed */
- 		return(0);
- 	}
- 	(void) pcbc_encrypt(des_inbuf,
- 			    storage,
- 			    (net_len < 8) ? 8 : net_len,
- 			    v4_schedule,
- 			    v4_kdata->session,
- 			    DECRYPT);
- 	/* 
- 	 * when the cleartext block is < 8 bytes, it is "right-justified"
- 	 * in the block, so we need to adjust the pointer to the data
- 	 */
- 	if (net_len < 8)
- 		store_ptr = storage + 8 - net_len;
- 	else
- 		store_ptr = storage;
- 	nstored = net_len;
- 	if (nstored > len) {
- 		memcpy(buf, store_ptr, len);
- 		nreturned += len;
- 		store_ptr += len;
- 		nstored -= len;
- 	} else {
- 		memcpy(buf, store_ptr, nstored);
- 		nreturned += nstored;
- 		nstored = 0;
- 	}
- 	
- 	return(nreturned);
- }
- 
- int
- v4_des_write(fd, buf, len)
- int fd;
- char *buf;
- int len;
- {
- 	long net_len;
- 	static int seeded = 0;
- 	static char garbage_buf[8];
- 	long garbage;
- 
- 	if (!do_encrypt)
- 		return(write(fd, buf, len));
- 
- 	/* 
- 	 * pcbc_encrypt outputs in 8-byte (64 bit) increments
- 	 *
- 	 * it zero-fills the cleartext to 8-byte padding,
- 	 * so if we have cleartext of < 8 bytes, we want
- 	 * to insert random garbage before it so that the ciphertext
- 	 * differs for each transmission of the same cleartext.
- 	 * if len < 8 - sizeof(long), sizeof(long) bytes of random
- 	 * garbage should be sufficient; leave the rest as-is in the buffer.
- 	 * if len > 8 - sizeof(long), just garbage fill the rest.
- 	 */
- 
- #ifdef min
- #undef min
- #endif
- #define min(a,b) ((a < b) ? a : b)
- 
- 	if (len < 8) {
- 		if (!seeded) {
- 			seeded = 1;
- 			srandom((int) time((long *)0));
- 		}
- 		garbage = random();
- 		/* insert random garbage */
- 		(void) memcpy(garbage_buf, &garbage, min(sizeof(long),8));
- 
- 		/* this "right-justifies" the data in the buffer */
- 		(void) memcpy(garbage_buf + 8 - len, buf, len);
- 	}
- 	(void) pcbc_encrypt((len < 8) ? garbage_buf : buf,
- 			    des_outbuf,
- 			    (len < 8) ? 8 : len,
- 			    v4_schedule,
- 			    v4_kdata->session,
- 			    ENCRYPT);
- 
- 	/* tell the other end the real amount, but send an 8-byte padded
- 	   packet */
- 	net_len = htonl(len);
- 	(void) write(fd, &net_len, sizeof(net_len));
- 	(void) write(fd, des_outbuf, roundup(len,8));
- 	return(len);
- }
- 
- #endif /* KRB5_KRB4_COMPAT */
  #endif /* KERBEROS */
--- 1557,1560 ----

home help back first fref pref prev next nref lref last post