summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog7
-rw-r--r--Makefile.in5
-rw-r--r--authfile.c4
-rw-r--r--authfile.h3
-rw-r--r--pathnames.h7
-rw-r--r--ssh-keysign.858
-rw-r--r--ssh-keysign.c204
-rw-r--r--ssh.c21
-rw-r--r--sshconnect.c8
-rw-r--r--sshconnect.h15
-rw-r--r--sshconnect1.c12
-rw-r--r--sshconnect2.c95
12 files changed, 403 insertions, 36 deletions
diff --git a/ChangeLog b/ChangeLog
index ff710913b..8ed0d7377 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -16,6 +16,11 @@
16 - deraadt@cvs.openbsd.org 2002/05/22 23:18:25 16 - deraadt@cvs.openbsd.org 2002/05/22 23:18:25
17 [ssh.c sshd.c] 17 [ssh.c sshd.c]
18 spelling; abishoff@arc.nasa.gov 18 spelling; abishoff@arc.nasa.gov
19 - markus@cvs.openbsd.org 2002/05/23 19:24:30
20 [authfile.c authfile.h pathnames.h ssh.c sshconnect.c sshconnect.h
21 sshconnect1.c sshconnect2.c ssh-keysign.8 ssh-keysign.c Makefile.in]
22 add /usr/libexec/ssh-keysign: a setuid helper program for hostbased
23 authentication in protocol v2 (needs to access the hostkeys).
19 24
2020020604 2520020604
21 - (stevesk) [channels.c] bug #164 patch from YOSHIFUJI Hideaki (changed 26 - (stevesk) [channels.c] bug #164 patch from YOSHIFUJI Hideaki (changed
@@ -700,4 +705,4 @@
700 - (stevesk) entropy.c: typo in debug message 705 - (stevesk) entropy.c: typo in debug message
701 - (djm) ssh-keygen -i needs seeded RNG; report from markus@ 706 - (djm) ssh-keygen -i needs seeded RNG; report from markus@
702 707
703$Id: ChangeLog,v 1.2148 2002/06/06 19:51:58 mouring Exp $ 708$Id: ChangeLog,v 1.2149 2002/06/06 19:57:33 mouring Exp $
diff --git a/Makefile.in b/Makefile.in
index e3b145150..ec235f827 100644
--- a/Makefile.in
+++ b/Makefile.in
@@ -1,4 +1,4 @@
1# $Id: Makefile.in,v 1.208 2002/05/13 04:12:05 djm Exp $ 1# $Id: Makefile.in,v 1.209 2002/06/06 19:57:33 mouring Exp $
2 2
3# uncomment if you run a non bourne compatable shell. Ie. csh 3# uncomment if you run a non bourne compatable shell. Ie. csh
4#SHELL = @SH@ 4#SHELL = @SH@
@@ -125,6 +125,9 @@ ssh-agent$(EXEEXT): $(LIBCOMPAT) libssh.a ssh-agent.o
125ssh-keygen$(EXEEXT): $(LIBCOMPAT) libssh.a ssh-keygen.o 125ssh-keygen$(EXEEXT): $(LIBCOMPAT) libssh.a ssh-keygen.o
126 $(LD) -o $@ ssh-keygen.o $(LDFLAGS) -lssh -lopenbsd-compat $(LIBS) 126 $(LD) -o $@ ssh-keygen.o $(LDFLAGS) -lssh -lopenbsd-compat $(LIBS)
127 127
128ssh-keysign$(EXEEXT): $(LIBCOMPAT) libssh.a ssh-keysign.o
129 $(LD) -o $@ ssh-keysign.o $(LDFLAGS) -lssh -lopenbsd-compat $(LIBS)
130
128ssh-keyscan$(EXEEXT): $(LIBCOMPAT) libssh.a ssh-keyscan.o 131ssh-keyscan$(EXEEXT): $(LIBCOMPAT) libssh.a ssh-keyscan.o
129 $(LD) -o $@ ssh-keyscan.o $(LDFLAGS) -lssh -lopenbsd-compat -lssh $(LIBS) 132 $(LD) -o $@ ssh-keyscan.o $(LDFLAGS) -lssh -lopenbsd-compat -lssh $(LIBS)
130 133
diff --git a/authfile.c b/authfile.c
index de8b1022e..6d936de56 100644
--- a/authfile.c
+++ b/authfile.c
@@ -36,7 +36,7 @@
36 */ 36 */
37 37
38#include "includes.h" 38#include "includes.h"
39RCSID("$OpenBSD: authfile.c,v 1.48 2002/02/28 15:46:33 markus Exp $"); 39RCSID("$OpenBSD: authfile.c,v 1.49 2002/05/23 19:24:30 markus Exp $");
40 40
41#include <openssl/err.h> 41#include <openssl/err.h>
42#include <openssl/evp.h> 42#include <openssl/evp.h>
@@ -421,7 +421,7 @@ fail:
421 return NULL; 421 return NULL;
422} 422}
423 423
424static Key * 424Key *
425key_load_private_pem(int fd, int type, const char *passphrase, 425key_load_private_pem(int fd, int type, const char *passphrase,
426 char **commentp) 426 char **commentp)
427{ 427{
diff --git a/authfile.h b/authfile.h
index c614ca12c..7f92701ec 100644
--- a/authfile.h
+++ b/authfile.h
@@ -1,4 +1,4 @@
1/* $OpenBSD: authfile.h,v 1.9 2002/03/04 17:27:39 stevesk Exp $ */ 1/* $OpenBSD: authfile.h,v 1.10 2002/05/23 19:24:30 markus Exp $ */
2 2
3/* 3/*
4 * Author: Tatu Ylonen <ylo@cs.hut.fi> 4 * Author: Tatu Ylonen <ylo@cs.hut.fi>
@@ -20,5 +20,6 @@ Key *key_load_public(const char *, char **);
20Key *key_load_public_type(int, const char *, char **); 20Key *key_load_public_type(int, const char *, char **);
21Key *key_load_private(const char *, const char *, char **); 21Key *key_load_private(const char *, const char *, char **);
22Key *key_load_private_type(int, const char *, const char *, char **); 22Key *key_load_private_type(int, const char *, const char *, char **);
23Key *key_load_private_pem(int, int, const char *, char **);
23 24
24#endif 25#endif
diff --git a/pathnames.h b/pathnames.h
index 691293c33..89e22c77a 100644
--- a/pathnames.h
+++ b/pathnames.h
@@ -1,4 +1,4 @@
1/* $OpenBSD: pathnames.h,v 1.12 2002/03/19 03:03:43 stevesk Exp $ */ 1/* $OpenBSD: pathnames.h,v 1.13 2002/05/23 19:24:30 markus Exp $ */
2 2
3/* 3/*
4 * Author: Tatu Ylonen <ylo@cs.hut.fi> 4 * Author: Tatu Ylonen <ylo@cs.hut.fi>
@@ -120,6 +120,11 @@
120#define _PATH_SSH_ASKPASS_DEFAULT "/usr/X11R6/bin/ssh-askpass" 120#define _PATH_SSH_ASKPASS_DEFAULT "/usr/X11R6/bin/ssh-askpass"
121#endif 121#endif
122 122
123/* Location of ssh-keysign for hostbased authentication */
124#ifndef _PATH_SSH_KEY_SIGN
125#define _PATH_SSH_KEY_SIGN "/usr/libexec/ssh-keysign"
126#endif
127
123/* xauth for X11 forwarding */ 128/* xauth for X11 forwarding */
124#ifndef _PATH_XAUTH 129#ifndef _PATH_XAUTH
125#define _PATH_XAUTH "/usr/X11R6/bin/xauth" 130#define _PATH_XAUTH "/usr/X11R6/bin/xauth"
diff --git a/ssh-keysign.8 b/ssh-keysign.8
new file mode 100644
index 000000000..fccbd7c27
--- /dev/null
+++ b/ssh-keysign.8
@@ -0,0 +1,58 @@
1.\" $OpenBSD: ssh-keysign.8,v 1.1 2002/05/25 08:16:59 markus Exp $
2.\"
3.\" Copyright (c) 2002 Markus Friedl. All rights reserved.
4.\"
5.\" Redistribution and use in source and binary forms, with or without
6.\" modification, are permitted provided that the following conditions
7.\" are met:
8.\" 1. Redistributions of source code must retain the above copyright
9.\" notice, this list of conditions and the following disclaimer.
10.\" 2. Redistributions in binary form must reproduce the above copyright
11.\" notice, this list of conditions and the following disclaimer in the
12.\" documentation and/or other materials provided with the distribution.
13.\"
14.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
15.\" IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
16.\" OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
17.\" IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
18.\" INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
19.\" NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
20.\" DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
21.\" THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22.\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
23.\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24.\"
25.Dd May 24, 2002
26.Dt SSH-KEYSIGN 8
27.Os
28.Sh NAME
29.Nm ssh-keysign
30.Nd ssh helper program for hostbased authentication
31.Sh SYNOPSIS
32.Nm ssh-keysign
33.Sh DESCRIPTION
34.Nm
35is used by
36.Xr ssh 1
37to access the local host keys during hostbased authentication with
38SSH protocol version 2.
39Since the host keys are readable only by root
40.Nm
41must be setuid root.
42.Nm
43is not intended to be invoked by the user, but from
44.Xr ssh 1 .
45See
46.Xr ssh 1
47and
48.Xr sshd 8
49for more information about hostbased authentication.
50.Sh SEE ALSO
51.Xr ssh 1 ,
52.Xr sshd 8
53.Sh AUTHORS
54Markus Friedl <markus@openbsd.org>
55.Sh HISTORY
56.Nm
57first appeared in
58.Ox 3.2 .
diff --git a/ssh-keysign.c b/ssh-keysign.c
new file mode 100644
index 000000000..da630708d
--- /dev/null
+++ b/ssh-keysign.c
@@ -0,0 +1,204 @@
1/*
2 * Copyright (c) 2002 Markus Friedl. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
6 * are met:
7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 *
13 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
14 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
15 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
16 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
17 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
18 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
19 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
20 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
21 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
22 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
23 */
24#include "includes.h"
25RCSID("$OpenBSD: ssh-keysign.c,v 1.2 2002/05/31 10:30:33 markus Exp $");
26
27#include <openssl/evp.h>
28
29#include "log.h"
30#include "key.h"
31#include "ssh2.h"
32#include "misc.h"
33#include "xmalloc.h"
34#include "buffer.h"
35#include "bufaux.h"
36#include "authfile.h"
37#include "msg.h"
38#include "canohost.h"
39#include "pathnames.h"
40
41static int
42valid_request(struct passwd *pw, char *host, Key **ret, u_char *data,
43 u_int datalen)
44{
45 Buffer b;
46 Key *key;
47 u_char *pkblob;
48 u_int blen, len;
49 char *pkalg, *p;
50 int pktype, fail;
51
52 fail = 0;
53
54 buffer_init(&b);
55 buffer_append(&b, data, datalen);
56
57 /* session id */
58 buffer_skip_string(&b);
59 if (buffer_get_char(&b) != SSH2_MSG_USERAUTH_REQUEST)
60 fail++;
61
62 /* server user */
63 buffer_skip_string(&b);
64
65 /* service */
66 p = buffer_get_string(&b, NULL);
67 if (strcmp("ssh-connection", p) != 0)
68 fail++;
69 xfree(p);
70
71 /* method */
72 p = buffer_get_string(&b, NULL);
73 if (strcmp("hostbased", p) != 0)
74 fail++;
75 xfree(p);
76
77 /* pubkey */
78 pkalg = buffer_get_string(&b, NULL);
79 pkblob = buffer_get_string(&b, &blen);
80
81 pktype = key_type_from_name(pkalg);
82 if (pktype == KEY_UNSPEC)
83 fail++;
84 else if ((key = key_from_blob(pkblob, blen)) == NULL)
85 fail++;
86 else if (key->type != pktype)
87 fail++;
88 xfree(pkalg);
89 xfree(pkblob);
90
91 /* client host name, handle trailing dot */
92 p = buffer_get_string(&b, &len);
93 debug2("valid_request: check expect chost %s got %s", host, p);
94 if (strlen(host) != len - 1)
95 fail++;
96 else if (p[len - 1] != '.')
97 fail++;
98 else if (strncasecmp(host, p, len - 1) != 0)
99 fail++;
100 xfree(p);
101
102 /* local user */
103 p = buffer_get_string(&b, NULL);
104
105 if (strcmp(pw->pw_name, p) != 0)
106 fail++;
107 xfree(p);
108
109 /* end of message */
110 if (buffer_len(&b) != 0)
111 fail++;
112
113 debug3("valid_request: fail %d", fail);
114
115 if (fail && key != NULL)
116 key_free(key);
117 else
118 *ret = key;
119
120 return (fail ? -1 : 0);
121}
122
123int
124main(int argc, char **argv)
125{
126 Buffer b;
127 Key *keys[2], *key;
128 struct passwd *pw;
129 int key_fd[2], i, found, version = 2, fd;
130 u_char *signature, *data;
131 char *host;
132 u_int slen, dlen;
133
134 key_fd[0] = open(_PATH_HOST_RSA_KEY_FILE, O_RDONLY);
135 key_fd[1] = open(_PATH_HOST_DSA_KEY_FILE, O_RDONLY);
136
137 seteuid(getuid());
138 setuid(getuid());
139
140#ifdef DEBUG_SSH_KEYSIGN
141 log_init("ssh-keysign", SYSLOG_LEVEL_DEBUG3, SYSLOG_FACILITY_AUTH, 0);
142#endif
143
144 if (key_fd[0] == -1 && key_fd[1] == -1)
145 fatal("could not open any host key");
146
147 if ((pw = getpwuid(getuid())) == NULL)
148 fatal("getpwuid failed");
149 pw = pwcopy(pw);
150
151 SSLeay_add_all_algorithms();
152
153 found = 0;
154 for (i = 0; i < 2; i++) {
155 keys[i] = NULL;
156 if (key_fd[i] == -1)
157 continue;
158 keys[i] = key_load_private_pem(key_fd[i], KEY_UNSPEC,
159 NULL, NULL);
160 close(key_fd[i]);
161 if (keys[i] != NULL)
162 found = 1;
163 }
164 if (!found)
165 fatal("no hostkey found");
166
167 buffer_init(&b);
168 if (msg_recv(STDIN_FILENO, &b) < 0)
169 fatal("msg_recv failed");
170 if (buffer_get_char(&b) != version)
171 fatal("bad version");
172 fd = buffer_get_int(&b);
173 if ((fd == STDIN_FILENO) || (fd == STDOUT_FILENO))
174 fatal("bad fd");
175 if ((host = get_local_name(fd)) == NULL)
176 fatal("cannot get sockname for fd");
177
178 data = buffer_get_string(&b, &dlen);
179 if (valid_request(pw, host, &key, data, dlen) < 0)
180 fatal("not a valid request");
181 xfree(data);
182 xfree(host);
183
184 found = 0;
185 for (i = 0; i < 2; i++) {
186 if (keys[i] != NULL &&
187 key_equal(key, keys[i])) {
188 found = 1;
189 break;
190 }
191 }
192 if (!found)
193 fatal("no matching hostkey found");
194
195 if (key_sign(keys[i], &signature, &slen, data, dlen) != 0)
196 fatal("key_sign failed");
197
198 /* send reply */
199 buffer_clear(&b);
200 buffer_put_string(&b, signature, slen);
201 msg_send(STDOUT_FILENO, version, &b);
202
203 return (0);
204}
diff --git a/ssh.c b/ssh.c
index 4b82d1e7e..2e479d521 100644
--- a/ssh.c
+++ b/ssh.c
@@ -40,7 +40,7 @@
40 */ 40 */
41 41
42#include "includes.h" 42#include "includes.h"
43RCSID("$OpenBSD: ssh.c,v 1.172 2002/05/22 23:18:25 deraadt Exp $"); 43RCSID("$OpenBSD: ssh.c,v 1.173 2002/05/23 19:24:30 markus Exp $");
44 44
45#include <openssl/evp.h> 45#include <openssl/evp.h>
46#include <openssl/err.h> 46#include <openssl/err.h>
@@ -132,10 +132,7 @@ char *host;
132struct sockaddr_storage hostaddr; 132struct sockaddr_storage hostaddr;
133 133
134/* Private host keys. */ 134/* Private host keys. */
135struct { 135Sensitive sensitive_data;
136 Key **keys;
137 int nkeys;
138} sensitive_data;
139 136
140/* Original real UID. */ 137/* Original real UID. */
141uid_t original_real_uid; 138uid_t original_real_uid;
@@ -689,6 +686,7 @@ again:
689 */ 686 */
690 sensitive_data.nkeys = 0; 687 sensitive_data.nkeys = 0;
691 sensitive_data.keys = NULL; 688 sensitive_data.keys = NULL;
689 sensitive_data.external_keysign = 0;
692 if (!cerr && (options.rhosts_rsa_authentication || 690 if (!cerr && (options.rhosts_rsa_authentication ||
693 options.hostbased_authentication)) { 691 options.hostbased_authentication)) {
694 sensitive_data.nkeys = 3; 692 sensitive_data.nkeys = 3;
@@ -699,6 +697,16 @@ again:
699 _PATH_HOST_DSA_KEY_FILE, "", NULL); 697 _PATH_HOST_DSA_KEY_FILE, "", NULL);
700 sensitive_data.keys[2] = key_load_private_type(KEY_RSA, 698 sensitive_data.keys[2] = key_load_private_type(KEY_RSA,
701 _PATH_HOST_RSA_KEY_FILE, "", NULL); 699 _PATH_HOST_RSA_KEY_FILE, "", NULL);
700
701 if (sensitive_data.keys[0] == NULL &&
702 sensitive_data.keys[1] == NULL &&
703 sensitive_data.keys[2] == NULL) {
704 sensitive_data.keys[1] = key_load_public(
705 _PATH_HOST_DSA_KEY_FILE, NULL);
706 sensitive_data.keys[2] = key_load_public(
707 _PATH_HOST_RSA_KEY_FILE, NULL);
708 sensitive_data.external_keysign = 1;
709 }
702 } 710 }
703 /* 711 /*
704 * Get rid of any extra privileges that we may have. We will no 712 * Get rid of any extra privileges that we may have. We will no
@@ -758,8 +766,7 @@ again:
758 signal(SIGPIPE, SIG_IGN); /* ignore SIGPIPE early */ 766 signal(SIGPIPE, SIG_IGN); /* ignore SIGPIPE early */
759 767
760 /* Log into the remote system. This never returns if the login fails. */ 768 /* Log into the remote system. This never returns if the login fails. */
761 ssh_login(sensitive_data.keys, sensitive_data.nkeys, 769 ssh_login(&sensitive_data, host, (struct sockaddr *)&hostaddr, pw);
762 host, (struct sockaddr *)&hostaddr, pw);
763 770
764 /* We no longer need the private host keys. Clear them now. */ 771 /* We no longer need the private host keys. Clear them now. */
765 if (sensitive_data.nkeys != 0) { 772 if (sensitive_data.nkeys != 0) {
diff --git a/sshconnect.c b/sshconnect.c
index 5bb50e0e9..7af0b9a80 100644
--- a/sshconnect.c
+++ b/sshconnect.c
@@ -13,7 +13,7 @@
13 */ 13 */
14 14
15#include "includes.h" 15#include "includes.h"
16RCSID("$OpenBSD: sshconnect.c,v 1.119 2002/01/21 15:13:51 markus Exp $"); 16RCSID("$OpenBSD: sshconnect.c,v 1.120 2002/05/23 19:24:30 markus Exp $");
17 17
18#include <openssl/bn.h> 18#include <openssl/bn.h>
19 19
@@ -844,7 +844,7 @@ verify_host_key(char *host, struct sockaddr *hostaddr, Key *host_key)
844 * This function does not require super-user privileges. 844 * This function does not require super-user privileges.
845 */ 845 */
846void 846void
847ssh_login(Key **keys, int nkeys, const char *orighost, 847ssh_login(Sensitive *sensitive, const char *orighost,
848 struct sockaddr *hostaddr, struct passwd *pw) 848 struct sockaddr *hostaddr, struct passwd *pw)
849{ 849{
850 char *host, *cp; 850 char *host, *cp;
@@ -869,10 +869,10 @@ ssh_login(Key **keys, int nkeys, const char *orighost,
869 /* authenticate user */ 869 /* authenticate user */
870 if (compat20) { 870 if (compat20) {
871 ssh_kex2(host, hostaddr); 871 ssh_kex2(host, hostaddr);
872 ssh_userauth2(local_user, server_user, host, keys, nkeys); 872 ssh_userauth2(local_user, server_user, host, sensitive);
873 } else { 873 } else {
874 ssh_kex(host, hostaddr); 874 ssh_kex(host, hostaddr);
875 ssh_userauth1(local_user, server_user, host, keys, nkeys); 875 ssh_userauth1(local_user, server_user, host, sensitive);
876 } 876 }
877} 877}
878 878
diff --git a/sshconnect.h b/sshconnect.h
index b475adde0..ad34ee64a 100644
--- a/sshconnect.h
+++ b/sshconnect.h
@@ -1,4 +1,4 @@
1/* $OpenBSD: sshconnect.h,v 1.13 2001/10/08 19:05:05 markus Exp $ */ 1/* $OpenBSD: sshconnect.h,v 1.14 2002/05/23 19:24:30 markus Exp $ */
2 2
3/* 3/*
4 * Copyright (c) 2000 Markus Friedl. All rights reserved. 4 * Copyright (c) 2000 Markus Friedl. All rights reserved.
@@ -26,20 +26,27 @@
26#ifndef SSHCONNECT_H 26#ifndef SSHCONNECT_H
27#define SSHCONNECT_H 27#define SSHCONNECT_H
28 28
29typedef struct Sensitive Sensitive;
30struct Sensitive {
31 Key **keys;
32 int nkeys;
33 int external_keysign;
34};
35
29int 36int
30ssh_connect(const char *, struct sockaddr_storage *, u_short, int, int, 37ssh_connect(const char *, struct sockaddr_storage *, u_short, int, int,
31 int, struct passwd *, const char *); 38 int, struct passwd *, const char *);
32 39
33void 40void
34ssh_login(Key **, int, const char *, struct sockaddr *, struct passwd *); 41ssh_login(Sensitive *, const char *, struct sockaddr *, struct passwd *);
35 42
36int verify_host_key(char *, struct sockaddr *, Key *); 43int verify_host_key(char *, struct sockaddr *, Key *);
37 44
38void ssh_kex(char *, struct sockaddr *); 45void ssh_kex(char *, struct sockaddr *);
39void ssh_kex2(char *, struct sockaddr *); 46void ssh_kex2(char *, struct sockaddr *);
40 47
41void ssh_userauth1(const char *, const char *, char *, Key **, int); 48void ssh_userauth1(const char *, const char *, char *, Sensitive *);
42void ssh_userauth2(const char *, const char *, char *, Key **, int); 49void ssh_userauth2(const char *, const char *, char *, Sensitive *);
43 50
44void ssh_put_password(char *); 51void ssh_put_password(char *);
45 52
diff --git a/sshconnect1.c b/sshconnect1.c
index d2024a2b7..e28b7fc72 100644
--- a/sshconnect1.c
+++ b/sshconnect1.c
@@ -13,7 +13,7 @@
13 */ 13 */
14 14
15#include "includes.h" 15#include "includes.h"
16RCSID("$OpenBSD: sshconnect1.c,v 1.50 2002/04/21 16:25:06 stevesk Exp $"); 16RCSID("$OpenBSD: sshconnect1.c,v 1.51 2002/05/23 19:24:30 markus Exp $");
17 17
18#include <openssl/bn.h> 18#include <openssl/bn.h>
19#include <openssl/md5.h> 19#include <openssl/md5.h>
@@ -1138,7 +1138,7 @@ ssh_kex(char *host, struct sockaddr *hostaddr)
1138 */ 1138 */
1139void 1139void
1140ssh_userauth1(const char *local_user, const char *server_user, char *host, 1140ssh_userauth1(const char *local_user, const char *server_user, char *host,
1141 Key **keys, int nkeys) 1141 Sensitive *sensitive)
1142{ 1142{
1143#ifdef KRB5 1143#ifdef KRB5
1144 krb5_context context = NULL; 1144 krb5_context context = NULL;
@@ -1224,9 +1224,11 @@ ssh_userauth1(const char *local_user, const char *server_user, char *host,
1224 */ 1224 */
1225 if ((supported_authentications & (1 << SSH_AUTH_RHOSTS_RSA)) && 1225 if ((supported_authentications & (1 << SSH_AUTH_RHOSTS_RSA)) &&
1226 options.rhosts_rsa_authentication) { 1226 options.rhosts_rsa_authentication) {
1227 for (i = 0; i < nkeys; i++) { 1227 for (i = 0; i < sensitive->nkeys; i++) {
1228 if (keys[i] != NULL && keys[i]->type == KEY_RSA1 && 1228 if (sensitive->keys[i] != NULL &&
1229 try_rhosts_rsa_authentication(local_user, keys[i])) 1229 sensitive->keys[i]->type == KEY_RSA1 &&
1230 try_rhosts_rsa_authentication(local_user,
1231 sensitive->keys[i]))
1230 goto success; 1232 goto success;
1231 } 1233 }
1232 } 1234 }
diff --git a/sshconnect2.c b/sshconnect2.c
index 1ee92ab0d..2736856fa 100644
--- a/sshconnect2.c
+++ b/sshconnect2.c
@@ -23,7 +23,7 @@
23 */ 23 */
24 24
25#include "includes.h" 25#include "includes.h"
26RCSID("$OpenBSD: sshconnect2.c,v 1.99 2002/03/26 15:58:46 markus Exp $"); 26RCSID("$OpenBSD: sshconnect2.c,v 1.100 2002/05/23 19:24:30 markus Exp $");
27 27
28#include "ssh.h" 28#include "ssh.h"
29#include "ssh2.h" 29#include "ssh2.h"
@@ -45,6 +45,8 @@ RCSID("$OpenBSD: sshconnect2.c,v 1.99 2002/03/26 15:58:46 markus Exp $");
45#include "match.h" 45#include "match.h"
46#include "dispatch.h" 46#include "dispatch.h"
47#include "canohost.h" 47#include "canohost.h"
48#include "msg.h"
49#include "pathnames.h"
48 50
49/* import */ 51/* import */
50extern char *client_version_string; 52extern char *client_version_string;
@@ -154,8 +156,7 @@ struct Authctxt {
154 int last_key_hint; 156 int last_key_hint;
155 AuthenticationConnection *agent; 157 AuthenticationConnection *agent;
156 /* hostbased */ 158 /* hostbased */
157 Key **keys; 159 Sensitive *sensitive;
158 int nkeys;
159 /* kbd-interactive */ 160 /* kbd-interactive */
160 int info_req_seen; 161 int info_req_seen;
161}; 162};
@@ -215,7 +216,7 @@ Authmethod authmethods[] = {
215 216
216void 217void
217ssh_userauth2(const char *local_user, const char *server_user, char *host, 218ssh_userauth2(const char *local_user, const char *server_user, char *host,
218 Key **keys, int nkeys) 219 Sensitive *sensitive)
219{ 220{
220 Authctxt authctxt; 221 Authctxt authctxt;
221 int type; 222 int type;
@@ -255,8 +256,7 @@ ssh_userauth2(const char *local_user, const char *server_user, char *host,
255 authctxt.success = 0; 256 authctxt.success = 0;
256 authctxt.method = authmethod_lookup("none"); 257 authctxt.method = authmethod_lookup("none");
257 authctxt.authlist = NULL; 258 authctxt.authlist = NULL;
258 authctxt.keys = keys; 259 authctxt.sensitive = sensitive;
259 authctxt.nkeys = nkeys;
260 authctxt.info_req_seen = 0; 260 authctxt.info_req_seen = 0;
261 if (authctxt.method == NULL) 261 if (authctxt.method == NULL)
262 fatal("ssh_userauth2: internal error: cannot send userauth none request"); 262 fatal("ssh_userauth2: internal error: cannot send userauth none request");
@@ -893,6 +893,75 @@ input_userauth_info_req(int type, u_int32_t seq, void *ctxt)
893 packet_send(); 893 packet_send();
894} 894}
895 895
896static int
897ssh_keysign(
898 Key *key,
899 u_char **sigp, u_int *lenp,
900 u_char *data, u_int datalen)
901{
902 Buffer b;
903 pid_t pid;
904 int to[2], from[2], status, version = 1;
905
906 debug("ssh_keysign called");
907
908 if (fflush(stdout) != 0)
909 error("ssh_keysign: fflush: %s", strerror(errno));
910 if (pipe(to) < 0) {
911 error("ssh_keysign: pipe: %s", strerror(errno));
912 return -1;
913 }
914 if (pipe(from) < 0) {
915 error("ssh_keysign: pipe: %s", strerror(errno));
916 return -1;
917 }
918 if ((pid = fork()) < 0) {
919 error("ssh_keysign: fork: %s", strerror(errno));
920 return -1;
921 }
922 if (pid == 0) {
923 seteuid(getuid());
924 setuid(getuid());
925 close(from[0]);
926 if (dup2(from[1], STDOUT_FILENO) < 0)
927 fatal("ssh_keysign: dup2: %s", strerror(errno));
928 close(to[1]);
929 if (dup2(to[0], STDIN_FILENO) < 0)
930 fatal("ssh_keysign: dup2: %s", strerror(errno));
931 execlp(_PATH_SSH_KEY_SIGN, _PATH_SSH_KEY_SIGN, (char *) 0);
932 fatal("ssh_keysign: exec(%s): %s", _PATH_SSH_KEY_SIGN,
933 strerror(errno));
934 }
935 close(from[1]);
936 close(to[0]);
937
938 buffer_init(&b);
939 buffer_put_string(&b, data, datalen);
940 msg_send(to[1], version, &b);
941
942 if (msg_recv(from[0], &b) < 0) {
943 debug("ssh_keysign: no reply");
944 buffer_clear(&b);
945 return -1;
946 }
947 if (buffer_get_char(&b) != version) {
948 debug("ssh_keysign: bad version");
949 buffer_clear(&b);
950 return -1;
951 }
952 *sigp = buffer_get_string(&b, lenp);
953 buffer_clear(&b);
954
955 close(from[0]);
956 close(to[1]);
957
958 while (waitpid(pid, &status, 0) < 0)
959 if (errno != EINTR)
960 break;
961
962 return 0;
963}
964
896/* 965/*
897 * this will be move to an external program (ssh-keysign) ASAP. ssh-keysign 966 * this will be move to an external program (ssh-keysign) ASAP. ssh-keysign
898 * will be setuid-root and the sbit can be removed from /usr/bin/ssh. 967 * will be setuid-root and the sbit can be removed from /usr/bin/ssh.
@@ -901,6 +970,7 @@ int
901userauth_hostbased(Authctxt *authctxt) 970userauth_hostbased(Authctxt *authctxt)
902{ 971{
903 Key *private = NULL; 972 Key *private = NULL;
973 Sensitive *sensitive = authctxt->sensitive;
904 Buffer b; 974 Buffer b;
905 u_char *signature, *blob; 975 u_char *signature, *blob;
906 char *chost, *pkalg, *p; 976 char *chost, *pkalg, *p;
@@ -909,12 +979,12 @@ userauth_hostbased(Authctxt *authctxt)
909 int ok, i, len, found = 0; 979 int ok, i, len, found = 0;
910 980
911 /* check for a useful key */ 981 /* check for a useful key */
912 for (i = 0; i < authctxt->nkeys; i++) { 982 for (i = 0; i < sensitive->nkeys; i++) {
913 private = authctxt->keys[i]; 983 private = sensitive->keys[i];
914 if (private && private->type != KEY_RSA1) { 984 if (private && private->type != KEY_RSA1) {
915 found = 1; 985 found = 1;
916 /* we take and free the key */ 986 /* we take and free the key */
917 authctxt->keys[i] = NULL; 987 sensitive->keys[i] = NULL;
918 break; 988 break;
919 } 989 }
920 } 990 }
@@ -956,7 +1026,12 @@ userauth_hostbased(Authctxt *authctxt)
956#ifdef DEBUG_PK 1026#ifdef DEBUG_PK
957 buffer_dump(&b); 1027 buffer_dump(&b);
958#endif 1028#endif
959 ok = key_sign(private, &signature, &slen, buffer_ptr(&b), buffer_len(&b)); 1029 if (sensitive->external_keysign)
1030 ok = ssh_keysign(private, &signature, &slen,
1031 buffer_ptr(&b), buffer_len(&b));
1032 else
1033 ok = key_sign(private, &signature, &slen,
1034 buffer_ptr(&b), buffer_len(&b));
960 key_free(private); 1035 key_free(private);
961 buffer_free(&b); 1036 buffer_free(&b);
962 if (ok != 0) { 1037 if (ok != 0) {