* rcp (client mode) now uses rsh -x but still supports the old encryption in
authorSam Hartman <hartmans@mit.edu>
Thu, 1 Feb 1996 05:56:27 +0000 (05:56 +0000)
committerSam Hartman <hartmans@mit.edu>
Thu, 1 Feb 1996 05:56:27 +0000 (05:56 +0000)
     server mode.
* krshd will work in encrypting mode even when the port for stderr is null.
* rcp will work if stdin isn't not a socket, but is a pipe  in remote mode
* krshd destroys forwarded credentials properly
* For rsh, the secure_message got moved to the client; if you use a new client
     with an old server, you get secure_message twice, but it should be a
     useful change long-term.
* Fixed typo in rcp man page.

git-svn-id: svn://anonsvn.mit.edu/krb5/trunk@7423 dc483132-0cff-0310-8789-dd5450dbe970

src/appl/bsd/ChangeLog
src/appl/bsd/configure.in
src/appl/bsd/krcp.c
src/appl/bsd/krsh.c
src/appl/bsd/krshd.c
src/appl/bsd/rcp.M

index 02696fed1fb44ff2b8e40bc3d74adff4924357e9..289ce69ceedc7d75c1c58d789a594882c8787b77 100644 (file)
@@ -1,6 +1,29 @@
+Thu Feb  1 00:09:13 1996  Sam Hartman  <hartmans@tertius.mit.edu>
+
+       * rcp.M: Fix typo.
+
+       * krcp.c (des_write): If rcp tries to write to stdin, redirect it
+        to stdout.  That way it works with pipes; the right thing is for
+        rcp to not try and do this, but introducing remread and remwrite
+        as variables is significantly more work for only slightly better
+        code.
+       (main):  Use rsh encryption; not user-to-user. Note that we still
+       support the answer_auth mechanism for incoming connections
+       so older clients work, but this is depricated.
+       (send_auth): expunged with pleasure; answer_auth should go in a
+       a version or two.
+
 Wed Jan 31 16:24:50 1996  Sam Hartman  <hartmans@tertius.mit.edu>
 
-       * krlogind.c (recvauth): Psas ccache to rd_and_store_for_creds
+       * krsh.c (main): Print SECURE_MESSAGE when appropriate.
+
+       * krshd.c (doit): Fork and handle pipes either if stderr signal
+        processing is enabled *or* encryption is enabled.  Rsh always
+        enables stderr, but rcp won't.
+       (SECURE_MESSAGE): Moving to client where it belongs, so the stderr
+       lchannel doesn't get corrupted for rcp.  Besides, the client can determine if it is talking to a tty and only print this message to a tty.
+
+       * krlogind.c (recvauth): Pas ccache to rd_and_store_for_creds
 
        * krshd.c (recvauth): Pass address of ccache to rd_and_store_for_creds
        (ccache): new global variable.
@@ -19,16 +42,6 @@ Tue Jan 30 17:56:49 1996  Sam Hartman  <hartmans@tertius.mit.edu>
        beset, so our position cannot be fixed.
 
 
-
-
-
-             done
-
-
-
-
-             Auto-saving...Use execle because AIX doesn't use envron for the initial environment.
-
 Sat Jan 27 18:40:31 1996  Sam Hartman  <hartmans@tertius.mit.edu>
 
        * kcmd.c (kcmd): We no longer need F_SETOWN as nothing in appl/bsd
index 56df16ac0d9381f93f91864cd9864e83d74d77f0..de267b7b2e6d84a00eb170a432c2424cef494001 100644 (file)
@@ -35,6 +35,7 @@ AC_VFORK
 AC_TYPE_MODE_T
 AC_FUNC_CHECK(strsave,AC_DEFINE(HAS_STRSAVE))
 AC_FUNC_CHECK(utimes,AC_DEFINE(HAS_UTIMES))
+AC_CHECK_FUNCS(isatty) 
 AC_FUNC_CHECK(getutent,AC_DEFINE(HAVE_GETUTENT))
 AC_FUNC_CHECK(gettosbyname,AC_DEFINE(HAVE_GETTOSBYNAME))
 AC_FUNC_CHECK(killpg,AC_DEFINE(HAVE_KILLPG))
index c97897d58898c76d4fa94911a5bd62c9d823b8cf..f46e16352b5c6a851e81f2fdc2636e78be7c1252 100644 (file)
@@ -97,7 +97,7 @@ char  **save_argv();
 char   *strsave();
 #endif
 int    des_write(), des_read();
-void   send_auth(), answer_auth();
+void answer_auth();
 int    encryptflag = 0;
 
 #ifndef UCB_RCP
@@ -161,7 +161,7 @@ main(argc, argv)
     krb5_error_code status;    
     int euid;
     char **orig_argv = save_argv(argc, argv);
-    
+
     krb5_init_context(&bsd_context);
     krb5_init_ets(bsd_context);
     desinbuf.data = des_inbuf;
@@ -243,16 +243,18 @@ main(argc, argv)
            if (encryptflag)
              answer_auth(krb_config, krb_cache);
 #endif /* KERBEROS */
+
            (void) response();
            source(--argc, ++argv);
            exit(errs);
            
          case 't':             /* "to" */
            iamremote = 1;
-#if defined(KERBEROS) 
+#if defined(KERBEROS)
            if (encryptflag)
              answer_auth(krb_config, krb_cache);
 #endif /* KERBEROS */
+
            sink(--argc, ++argv);
            exit(errs);
            
@@ -300,9 +302,10 @@ main(argc, argv)
        fprintf(stderr, "rcp: Cannot malloc.\n");
        exit(1);
     }
-    (void) sprintf(cmd, "rcp%s%s%s%s%s%s%s%s%s%s",
+    (void) sprintf(cmd, "%srcp %s%s%s%s%s%s%s%s%s",
+                  encryptflag ? "-x " : "",
+
                   iamrecursive ? " -r" : "", pflag ? " -p" : "", 
-                  encryptflag ? " -x" : "",
                   targetshouldbedirectory ? " -d" : "",
                   krb_realm != NULL ? " -k " : "",
                   krb_realm != NULL ? krb_realm : "",
@@ -399,6 +402,7 @@ main(argc, argv)
                                   thost, targ);
                (void) susystem(buf);
            } else {            /* local to remote */
+krb5_creds *cred;
                if (rem == -1) {
                    (void) sprintf(buf, "%s -t %s",
                                   cmd, targ);
@@ -414,7 +418,7 @@ main(argc, argv)
                                  0,
                                  "host",
                                  krb_realm,
-                                 0,  /* No return cred */
+                                 &cred,  
                                  0,  /* No seq # */
                                  0,  /* No server seq # */
                                  (struct sockaddr_in *) 0,
@@ -430,8 +434,15 @@ main(argc, argv)
                    }
                    else {
                        rem = sock; 
-                       if (encryptflag)
-                         send_auth();
+                       session_key = &cred->keyblock;
+                                  
+    krb5_use_enctype(bsd_context, &eblock, session_key->enctype);
+    if ( status = krb5_process_key(bsd_context, &eblock, 
+                                  session_key)){
+       fprintf(stderr, "rcp: send_auth failed krb5_process_key: %s\n",
+               error_message(status));
+       exit(1);
+    }
                    }
 #else
                    rem = rcmd(&host, port, pwd->pw_name,
@@ -478,6 +489,7 @@ main(argc, argv)
                               argv[i], argv[argc - 1]);
                (void) susystem(buf);
            } else {            /* remote to local */
+               krb5_creds *cred;
                *src++ = 0;
                if (*src == 0)
                  src = ".";
@@ -503,7 +515,7 @@ main(argc, argv)
                              0,
                              "host",
                              krb_realm,
-                             0,  /* No return cred */
+                             &cred,  
                              0,  /* No seq # */
                              0,  /* No server seq # */
                              (struct sockaddr_in *) 0,
@@ -519,8 +531,16 @@ main(argc, argv)
                    
                } else {
                    rem = sock; 
-                   if (encryptflag)
-                     send_auth();
+                       session_key = &cred->keyblock;
+                                  
+    krb5_use_enctype(bsd_context, &eblock, session_key->enctype);
+    if ( status = krb5_process_key(bsd_context, &eblock, 
+                                  session_key)){
+       fprintf(stderr, "rcp: send_auth failed krb5_process_key: %s\n",
+               error_message(status));
+       exit(1);
+    }
+
                }
                euid = geteuid();
 #ifdef HAVE_SETREUID
@@ -1238,132 +1258,8 @@ char **save_argv(argc, argv)
 #define SIZEOF_INADDR sizeof(struct in_addr)
 #endif
 
-void send_auth()
-{
-    int sin_len;
-    char *princ;          /* principal in credentials cache */
-    krb5_ccache cc;
-    krb5_creds in_creds, *out_creds;
-    krb5_data reply, princ_data;
-    krb5_error_code status;
-    krb5_address faddr;
-    krb5_ticket * ticket = NULL;
-    krb5_auth_context auth_context = NULL;
-    
-    
-    if (status = krb5_cc_default(bsd_context, &cc)){
-       fprintf(stderr,"rcp: send_auth failed krb5_cc_default : %s\n",
-               error_message(status));
-       exit(1);
-    }
-    
-    memset ((char*)&in_creds, 0, sizeof(krb5_creds));
-    
-    if (status = krb5_cc_get_principal(bsd_context, cc, &in_creds.client)){
-       fprintf(stderr,
-               "rcp: send_auth failed krb5_cc_get_principal : %s\n",
-               error_message(status));
-       krb5_cc_close(bsd_context, cc);
-       exit(1);
-    }
-    
-    if (status = krb5_unparse_name(bsd_context, in_creds.client, &princ)){
-       fprintf(stderr,"rcp: send_auth failed krb5_parse_name : %s\n",
-               error_message(status));
-       krb5_cc_close(bsd_context, cc);
-       exit(1);
-    }
-    if (status = krb5_build_principal_ext(bsd_context, &in_creds.server,
-                         krb5_princ_realm(bsd_context,in_creds.client)->length,
-                         krb5_princ_realm(bsd_context,in_creds.client)->data,
-                                         6, "krbtgt",
-                         krb5_princ_realm(bsd_context,in_creds.client)->length,
-                         krb5_princ_realm(bsd_context,in_creds.client)->data,
-                                         0)){
-       fprintf(stderr,
-               "rcp: send_auth failed krb5_build_principal_ext : %s\n",
-               error_message(status));
-       krb5_cc_close(bsd_context, cc);
-       exit(1);
-    }
-    
-    /* Get TGT from credentials cache */
-    if (status = krb5_get_credentials(bsd_context, KRB5_GC_CACHED, cc, 
-                                     &in_creds, &out_creds)){
-       fprintf(stderr,
-                "rcp: send_auth failed krb5_get_credentials: %s\n",
-               error_message(status));
-       krb5_cc_close(bsd_context, cc);
-       exit(1);
-    }
-    krb5_cc_close(bsd_context, cc);
-    
-    princ_data.data = princ;
-    princ_data.length = strlen(princ_data.data) + 1; /* include null 
-                                                       terminator for
-                                                       server's convenience */
-    status = krb5_write_message(bsd_context, (krb5_pointer) &rem, &princ_data);
-    if (status){
-       fprintf(stderr,
-                "rcp: send_auth failed krb5_write_message: %s\n",
-               error_message(status));
-       exit(1);
-    }
-    krb5_xfree(princ);
-    status = krb5_write_message(bsd_context, (krb5_pointer)&rem, 
-                               &out_creds->ticket);
-    if (status){
-       fprintf(stderr,
-                "rcp: send_auth failed krb5_write_message: %s\n",
-               error_message(status));
-       exit(1);
-    }
-    
-    if (status = krb5_read_message(bsd_context, (krb5_pointer) &rem, &reply)) {
-       fprintf(stderr, "rcp: send_auth failed krb5_read_message: %s\n",
-               error_message(status));
-       exit(1);
-    }
-    
-    sin_len = SIZEOF_INADDR;
-    faddr.addrtype = foreign.sin_family;
-    faddr.length = SIZEOF_INADDR;
-    faddr.contents = (krb5_octet *) &foreign.sin_addr;
 
-    if (krb5_auth_con_init(bsd_context, &auth_context))
-       exit(1);
 
-    krb5_auth_con_setaddrs(bsd_context, auth_context, NULL, &faddr);
-    
-    if (krb5_auth_con_setuseruserkey(bsd_context, auth_context,
-                                    &out_creds->keyblock))
-       exit(1);
-    
-    /* read the ap_req to get the session key */
-    status = krb5_rd_req(bsd_context, &auth_context, &reply,
-                        0,               /* don't know server's name... */
-                        NULL,            /* default keytab */
-                        NULL, & ticket);
-    krb5_xfree(reply.data);
-    if (status) {
-       fprintf(stderr, "rcp: send_auth failed krb5_rd_req: %s\n",
-               error_message(status));
-       exit(1);
-    }
-    
-    krb5_copy_keyblock(bsd_context, ticket->enc_part2->session,
-                      &session_key);
-    krb5_free_creds(bsd_context, out_creds);
-    
-    krb5_use_enctype(bsd_context, &eblock, session_key->enctype);
-    if ( status = krb5_process_key(bsd_context, &eblock, 
-                                  session_key)){
-       fprintf(stderr, "rcp: send_auth failed krb5_process_key: %s\n",
-               error_message(status));
-       exit(1);
-    }
-    
-}
 
 void
   answer_auth(config_file, ccache_file)
@@ -1526,7 +1422,14 @@ int des_write(fd, buf, len)
      int len;
 {
     unsigned char len_buf[4];
+/* Note that rcp depends on the same
+ * file descriptor being both input and output to the remote
+ * side.  This is bogus, especially when rcp
+ * is being run by a rsh that pipes. Fix it here because
+ * it would require significantly more work in other places. --hartmans 1/96*/
     
+    if (fd == 0)
+       fd = 1;
     if (!encryptflag)
       return(write(fd, buf, len));
     
index 8aaa588ca056f6ed39bb5899eee77b023038072c..e9162e8d7152e6de4cf4ce1b75a07307c96f1d3e 100644 (file)
@@ -70,6 +70,7 @@ char copyright[] =
 /*
  * rsh - remote shell
  */
+#define SECURE_MESSAGE "This rsh session is using DES encryption for all data transmissions.\r\n"
 
 int    error();
      
@@ -372,6 +373,12 @@ main(argc, argv0)
                 argv0, error_message(status));
         exit(1);
     }
+#ifdef HAVE_ISATTY
+    if(isatty(2)) {
+       write(2,SECURE_MESSAGE, strlen(SECURE_MESSAGE));
+    }
+#endif
+    
 #else /* !KERBEROS */
     rem = rcmd(&host, debug_port, pwd->pw_name,
               user ? user : pwd->pw_name, args, &rfd2);
index 6e264bdde1e9a7befbab4e1438a1fd81bc41af5a..98d49744c9a53d2e7f99099920e5381c8de02547 100644 (file)
@@ -157,7 +157,6 @@ char copyright[] =
 
 #define ARGSTR "rek54cD:S:M:AP:?"
 
-#define SECURE_MESSAGE "This rsh session is using DES encryption for all data transmissions.\r\n"
 
 #define RSHD_BUFSIZ 5120
 
@@ -1091,8 +1090,8 @@ if (require_encrypt&&(!do_encrypt)) {
     
     (void) write(2, "", 1);
     
-    if (port) {
-       if (pipe(pv) < 0) {
+    if (port||do_encrypt) {
+       if (port&&(pipe(pv) < 0)) {
            error("Can't make pipe.\n");
            goto signout_please;
        }
@@ -1130,22 +1129,23 @@ if (require_encrypt&&(!do_encrypt)) {
 #endif
            
            (void) close(0); (void) close(1); (void) close(2);
-           (void) close(pv[1]);
+if(port)
+    (void) close(pv[1]);
            (void) close(pw[1]);
            (void) close(px[0]);
            
-           ioctl(pv[0], FIONBIO, (char *)&one);
+if(port)
+    ioctl(pv[0], FIONBIO, (char *)&one);
            ioctl(pw[0], FIONBIO, (char *)&one);
            /* should set s nbio! */
 
-           if (do_encrypt)
-               if (((*des_write)(s, SECURE_MESSAGE, sizeof(SECURE_MESSAGE))) < 0)
-                   fatal(pw[0], "Cannot encrypt-write network.");
            
            FD_ZERO(&readfrom);
            FD_SET(f, &readfrom);
-           FD_SET(s, &readfrom);
-           FD_SET(pv[0], &readfrom);
+if(port)
+    FD_SET(s, &readfrom);
+if(port)
+    FD_SET(pv[0], &readfrom);
            FD_SET(pw[0], &readfrom);
            
            do {
@@ -1157,7 +1157,7 @@ if (require_encrypt&&(!do_encrypt)) {
                    else
                        break;
                }
-               if (FD_ISSET(s, &ready)) {
+               if (port&&FD_ISSET(s, &ready)) {
                    if ((*des_read)(s, &sig, 1) <= 0)
                        FD_CLR(s, &readfrom);
                    else {
@@ -1180,7 +1180,7 @@ if (require_encrypt&&(!do_encrypt)) {
                    } else
                        (void) write(px[1], buf, cc);
                }
-               if (FD_ISSET(pv[0], &ready)) {
+               if (port&&FD_ISSET(pv[0], &ready)) {
                    errno = 0;
                    cc = read(pv[0], buf, sizeof (buf));
                    if (cc <= 0) {
@@ -1198,9 +1198,9 @@ if (require_encrypt&&(!do_encrypt)) {
                    } else
                        (void) (*des_write)(f, buf, cc);
                }
-           } while (FD_ISSET(s, &readfrom) ||
+           } while ((port&&FD_ISSET(s, &readfrom)) ||
                     FD_ISSET(f, &readfrom) ||
-                    FD_ISSET(pv[0], &readfrom) ||
+                    (port&&FD_ISSET(pv[0], &readfrom) )||
                     FD_ISSET(pw[0], &readfrom));
 #ifdef KERBEROS
            syslog(LOG_INFO ,
@@ -1222,16 +1222,20 @@ if (ccache)
        (void) close(s);
        (void) close(f);
        (void) close(pw[0]);
-       (void) close(pv[0]);
+       if (port)
+           (void) close(pv[0]);
        (void) close(px[1]);
 
        (void) dup2(px[0], 0);
        (void) dup2(pw[1], 1);
-       (void) dup2(pv[1], 2);
+       if(port)
+           (void) dup2(pv[1], 2);
+       else dup2(pw[1], 2);
 
        (void) close(px[0]);
        (void) close(pw[1]);
-       (void) close(pv[1]);
+       if(port)
+           (void) close(pv[1]);
     }
     
     /*      We are simply execing a program over rshd : log entry into wtmp, 
index b8b0a476a332b1702da0d16b5a4775d4a8934643..39b13c40ee5e7f8e0c2ea19b265fea707b15c8ef 100644 (file)
@@ -100,7 +100,7 @@ Kerberos principal name of the form
 .IR principal/instance@realm .
 If there is a ~/.k5login file, then access is granted to the account if
 and only if the originater user is authenticated to one of the
-princiapls named in the ~/.k5login file.  Otherwise, the originating
+principals named in the ~/.k5login file.  Otherwise, the originating
 user will be granted access to the account if and only if the
 authenticated principal name of the user can be mapped to the local
 account name using the aname -> lname mapping rules (see \fIkrb5_anadd(8)\fP