View | Details | Raw Unified | Return to bug 125 | Differences between
and this patch

Collapse All | Expand All

(-)LICENCE (+1 lines)
Lines 203-208 OpenSSH contains no GPL code. Link Here
203
	Wayne Schroeder
203
	Wayne Schroeder
204
	William Jones
204
	William Jones
205
	Darren Tucker
205
	Darren Tucker
206
	Sun Microsystems
206
207
207
     * Redistribution and use in source and binary forms, with or without
208
     * Redistribution and use in source and binary forms, with or without
208
     * modification, are permitted provided that the following conditions
209
     * modification, are permitted provided that the following conditions
(-)Makefile.in (-1 / +2 lines)
Lines 85-91 SSHDOBJS=sshd.o auth-rhosts.o auth-passw Link Here
85
	monitor_mm.o monitor.o monitor_wrap.o kexdhs.o kexgexs.o \
85
	monitor_mm.o monitor.o monitor_wrap.o kexdhs.o kexgexs.o \
86
	auth-krb5.o \
86
	auth-krb5.o \
87
	auth2-gss.o gss-serv.o gss-serv-krb5.o \
87
	auth2-gss.o gss-serv.o gss-serv-krb5.o \
88
	loginrec.o auth-pam.o auth-shadow.o auth-sia.o md5crypt.o audit.o
88
	loginrec.o auth-pam.o auth-shadow.o auth-sia.o md5crypt.o \
89
	audit.o audit-bsm.o
89
90
90
MANPAGES	= 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 sshd_config.5.out ssh_config.5.out
91
MANPAGES	= 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 sshd_config.5.out ssh_config.5.out
91
MANPAGES_IN	= scp.1 ssh-add.1 ssh-agent.1 ssh-keygen.1 ssh-keyscan.1 ssh.1 sshd.8 sftp-server.8 sftp.1 ssh-rand-helper.8 ssh-keysign.8 sshd_config.5 ssh_config.5
92
MANPAGES_IN	= scp.1 ssh-add.1 ssh-agent.1 ssh-keygen.1 ssh-keyscan.1 ssh.1 sshd.8 sftp-server.8 sftp.1 ssh-rand-helper.8 ssh-keysign.8 sshd_config.5 ssh_config.5
(-)README.platform (-3 / +15 lines)
Lines 23-30 openssl-devel, zlib, minres, minires-dev Link Here
23
23
24
Solaris
24
Solaris
25
-------
25
-------
26
Currently, sshd does not support BSM auditting.  This can show up as errors
26
If you enable BSM auditing on Solaris, you need to update audit_event(4)
27
when editting cron entries via crontab.  See.
27
for praudit(1m) to give sensible output.  The following line needs to be
28
http://bugzilla.mindrot.org/show_bug.cgi?id=125
28
added to /etc/security/audit_event:
29
30
	32800:AUE_openssh:OpenSSH login:lo
31
32
If the contrib/buildpkg.sh script is used, the included postinstall
33
script will add the line for you.
34
35
The BSM audit event range available for third party TCB applications is
36
32768 - 65535.  Event number 32800 has been choosen for AUE_openssh.
37
There is no official registry of 3rd party event numbers, so if this
38
number is already in use on your system, you may change it at build time
39
by configure'ing --with-cflags=-DAUE_openssh=32801 then rebuilding.
40
29
41
30
$Id: README.platform,v 1.2 2004/04/23 08:57:13 dtucker Exp $
42
$Id: README.platform,v 1.2 2004/04/23 08:57:13 dtucker Exp $
(-)audit-bsm.c (+329 lines)
Added Link Here
1
/* $Id$ */
2
3
/*
4
 * TODO
5
 *
6
 * - deal with overlap between this and sys_auth_allowed_user
7
 *   sys_auth_record_login and record_failed_login.
8
 */
9
10
/*
11
 * Copyright 1988-2002 Sun Microsystems, Inc.  All rights reserved.
12
 * Use is subject to license terms.
13
 *
14
 * Redistribution and use in source and binary forms, with or without
15
 * modification, are permitted provided that the following conditions
16
 * are met:
17
 * 1. Redistributions of source code must retain the above copyright
18
 *    notice, this list of conditions and the following disclaimer.
19
 * 2. Redistributions in binary form must reproduce the above copyright
20
 *    notice, this list of conditions and the following disclaimer in the
21
 *    documentation and/or other materials provided with the distribution.
22
 *
23
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
24
 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
25
 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
26
 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
27
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
28
 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
29
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
30
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
31
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
32
 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33
 *
34
 */
35
/* #pragma ident	"@(#)bsmaudit.c	1.1	01/09/17 SMI" */
36
37
#include "includes.h"
38
#if defined(USE_BSM_AUDIT)
39
40
#include "ssh.h"
41
#include "log.h"
42
#include "auth.h"
43
#include "xmalloc.h"
44
45
#ifndef AUE_openssh
46
# define AUE_openssh     32800
47
#endif
48
#include <bsm/audit.h>
49
#include <bsm/libbsm.h>
50
#include <bsm/audit_uevents.h>
51
#include <bsm/audit_record.h>
52
#include <locale.h>
53
54
#if defined(HAVE_GETAUDIT_ADDR)
55
#define	AuditInfoStruct		auditinfo_addr
56
#define AuditInfoTermID		au_tid_addr_t
57
#define GetAuditFunc(a,b)	getaudit_addr((a),(b))
58
#define GetAuditFuncText	"getaudit_addr"
59
#define SetAuditFunc(a,b)	setaudit_addr((a),(b))
60
#define SetAuditFuncText	"setaudit_addr"
61
#define AUToSubjectFunc		au_to_subject_ex
62
#define AUToReturnFunc(a,b)	au_to_return32((a), (int32_t)(b))
63
#else
64
#define	AuditInfoStruct		auditinfo
65
#define AuditInfoTermID		au_tid_t
66
#define GetAuditFunc(a,b)	getaudit(a)
67
#define GetAuditFuncText	"getaudit"
68
#define SetAuditFunc(a,b)	setaudit(a)
69
#define SetAuditFuncText	"setaudit"
70
#define AUToSubjectFunc		au_to_subject
71
#define AUToReturnFunc(a,b)	au_to_return((a), (u_int)(b))
72
#endif
73
74
extern int	cannot_audit(int);
75
extern void	aug_init(void);
76
extern dev_t	aug_get_port(void);
77
extern int 	aug_get_machine(char *, u_int32_t *, u_int32_t *);
78
extern void	aug_save_auid(au_id_t);
79
extern void	aug_save_uid(uid_t);
80
extern void	aug_save_euid(uid_t);
81
extern void	aug_save_gid(gid_t);
82
extern void	aug_save_egid(gid_t);
83
extern void	aug_save_pid(pid_t);
84
extern void	aug_save_asid(au_asid_t);
85
extern void	aug_save_tid(dev_t, unsigned int);
86
extern void	aug_save_tid_ex(dev_t, u_int32_t *, u_int32_t);
87
extern int	aug_save_me(void);
88
extern int	aug_save_namask(void);
89
extern void	aug_save_event(au_event_t);
90
extern void	aug_save_sorf(int);
91
extern void	aug_save_text(char *);
92
extern void	aug_save_text1(char *);
93
extern void	aug_save_text2(char *);
94
extern void	aug_save_na(int);
95
extern void	aug_save_user(char *);
96
extern void	aug_save_path(char *);
97
extern int	aug_save_policy(void);
98
extern void	aug_save_afunc(int (*)(int));
99
extern int	aug_audit(void);
100
extern int	aug_na_selected(void);
101
extern int	aug_selected(void);
102
extern int	aug_daemon_session(void);
103
104
#ifndef HAVE_GETTEXT
105
# define gettext(a)	(a)
106
#endif
107
108
extern Authctxt *the_authctxt;
109
static AuditInfoTermID ssh_bsm_tid;
110
111
/* Below is the low-level BSM interface code */
112
113
/*
114
 * Check if the specified event is selected (enabled) for auditting.
115
 * Returns 1 if the event is selected, 0 if not and -1 on failure.
116
 */
117
static int
118
selected(char *username, uid_t uid, au_event_t event, int sf)
119
{
120
	int rc, sorf;
121
	char naflags[512];
122
	struct au_mask mask;
123
124
	mask.am_success = mask.am_failure = 0;
125
	if (uid < 0) {
126
		/* get flags for non-attributable (to a real user) events */
127
		rc = getacna(naflags, sizeof(naflags));
128
		if (rc == 0)
129
			(void) getauditflagsbin(naflags, &mask);
130
	} else
131
		rc = au_user_mask(username, &mask);
132
133
	sorf = (sf == 0) ? AU_PRS_SUCCESS : AU_PRS_FAILURE;
134
	return(au_preselect(event, &mask, sorf, AU_PRS_REREAD));
135
}
136
137
static void
138
bsm_audit_record(int typ, char *string, au_event_t event_no)
139
{
140
	int		ad, rc, sel;
141
	uid_t		uid = -1;
142
	gid_t		gid = -1;
143
	pid_t		pid = getpid();
144
	AuditInfoTermID	tid = ssh_bsm_tid;
145
146
	if (the_authctxt != NULL && the_authctxt->valid) {
147
		uid = the_authctxt->pw->pw_uid;
148
		gid = the_authctxt->pw->pw_gid;
149
	}
150
151
	rc = (typ == 0) ? 0 : -1;
152
	sel = selected(the_authctxt->user, uid, event_no, rc);
153
	debug3("BSM audit: typ %d rc %d \"%s\"", typ, rc, string);
154
	if (!sel)
155
		return;	/* audit event does not match mask, do not write */
156
157
	debug3("BSM audit: writing audit new record");
158
	ad = au_open();
159
160
	(void) au_write(ad, AUToSubjectFunc(uid, uid, gid, uid, gid,
161
	    pid, pid, &tid));
162
	(void) au_write(ad, au_to_text(string));
163
	(void) au_write(ad, AUToReturnFunc(typ, rc));
164
165
	rc = au_close(ad, AU_TO_WRITE, event_no);
166
	if (rc < 0)
167
		error("BSM audit: %s failed to write \"%s\" record: %s",
168
		    __func__, string, strerror(errno));
169
}
170
171
static void
172
bsm_audit_session_setup(void)
173
{
174
	int rc;
175
	struct AuditInfoStruct info;
176
	au_mask_t mask;
177
178
	if (the_authctxt == NULL) {
179
		error("BSM audit: session setup internal error (NULL ctxt)");
180
		return;
181
	}
182
183
	if (the_authctxt->valid)
184
		info.ai_auid = the_authctxt->pw->pw_uid;
185
	else
186
		info.ai_auid = -1;
187
	info.ai_asid = getpid();
188
	mask.am_success = 0;
189
	mask.am_failure = 0;
190
191
	(void) au_user_mask(the_authctxt->user, &mask);
192
193
	info.ai_mask.am_success  = mask.am_success;
194
	info.ai_mask.am_failure  = mask.am_failure;
195
196
	info.ai_termid = ssh_bsm_tid;
197
198
	rc = SetAuditFunc(&info, sizeof(info));
199
	if (rc < 0)
200
		error("BSM audit: %s: %s failed: %s", __func__,
201
		    SetAuditFuncText, strerror(errno));
202
}
203
204
static void
205
bsm_audit_bad_login(const char *what)
206
{
207
	char textbuf[BSM_TEXTBUFSZ];
208
209
	if (the_authctxt->valid) {
210
		(void) snprintf(textbuf, sizeof (textbuf),
211
			gettext("invalid %s for user %s"),
212
			    what, the_authctxt->user);
213
		bsm_audit_record(4, textbuf, AUE_openssh);
214
	} else {
215
		(void) snprintf(textbuf, sizeof (textbuf),
216
			gettext("invalid user name \"%s\""),
217
			    the_authctxt->user);
218
		bsm_audit_record(3, textbuf, AUE_openssh);
219
	}
220
}
221
222
/* Below is the sshd audit API code */
223
224
void
225
audit_connection_from(const char *host, int port)
226
{
227
	AuditInfoTermID *tid = &ssh_bsm_tid;
228
	char buf[1024];
229
230
	if (cannot_audit(0))
231
		return;
232
	debug3("BSM audit: connection from %.100s port %d", host, port);
233
234
	/* populate our terminal id structure */
235
#if defined(HAVE_GETAUDIT_ADDR)
236
	tid->at_port = (dev_t)port;
237
	aug_get_machine((char *)host, &(tid->at_addr[0]), &(tid->at_type));
238
	snprintf(buf, sizeof(buf), "%08x %08x %08x %08x", tid->at_addr[0],
239
	    tid->at_addr[1], tid->at_addr[2], tid->at_addr[3]);
240
	debug3("BSM audit: iptype %d machine ID %s", (int)tid->at_type, buf);
241
#else
242
	/* this is used on IPv4-only machines */
243
	tid->port = (dev_t)port;
244
	tid->machine = inet_addr(host);
245
	snprintf(buf, sizeof(buf), "%08x", tid->machine);
246
	debug3("BSM audit: machine ID %s", buf);
247
#endif
248
}
249
250
void
251
audit_run_command(const char *command)
252
{
253
	/* not implemented */
254
}
255
256
void
257
audit_session_open(const char *ttyn)
258
{
259
	/* not implemented */
260
}
261
262
void
263
audit_session_close(const char *ttyn)
264
{
265
	/* not implemented */
266
}
267
268
void
269
audit_event(ssh_audit_event_t event)
270
{
271
	char    textbuf[BSM_TEXTBUFSZ];
272
	static int logged_in = 0;
273
	const char *user = the_authctxt ? the_authctxt->user : "(unknown user)";
274
275
	if (cannot_audit(0))
276
		return;
277
278
	switch(event) {
279
	case SSH_AUTH_SUCCESS:
280
		logged_in = 1;
281
		bsm_audit_session_setup();
282
		snprintf(textbuf, sizeof(textbuf),
283
		    gettext("successful login %s"), user);
284
		bsm_audit_record(0, textbuf, AUE_openssh);
285
		break;
286
287
	case SSH_CONNECTION_CLOSE:
288
		/*
289
		 * We can also get a close event if the user attempted auth
290
		 * but never succeeded.
291
		 */
292
		if (logged_in) {
293
			snprintf(textbuf, sizeof(textbuf),
294
			    gettext("sshd logout %s"), the_authctxt->user);
295
			bsm_audit_record(0, textbuf, AUE_logout);
296
		} else {
297
			debug("%s: connection closed without authentication",
298
			    __func__);
299
		}
300
		break;
301
302
	case SSH_NOLOGIN:
303
		bsm_audit_record(1,
304
		    gettext("logins disabled by /etc/nologin"), AUE_openssh);
305
		break;
306
307
	case SSH_LOGIN_EXCEED_MAXTRIES:
308
		snprintf(textbuf, sizeof(textbuf),
309
		    gettext("too many tries for user %s"), the_authctxt->user);
310
		bsm_audit_record(1, textbuf, AUE_openssh);
311
		break;
312
313
	case SSH_LOGIN_ROOT_DENIED:
314
		bsm_audit_record(2, gettext("not_console"), AUE_openssh);
315
		break;
316
317
	case SSH_AUTH_FAIL_PASSWD:
318
		bsm_audit_bad_login("password");
319
		break;
320
321
	case SSH_AUTH_FAIL_KBDINT:
322
		bsm_audit_bad_login("interactive password entry");
323
		break;
324
325
	default:
326
		debug("%s: unhandled event %d", __func__, event);
327
	}
328
}
329
#endif /* BSM */
(-)configure.ac (+33 lines)
Lines 876-881 AC_ARG_WITH(libedit, Link Here
876
	fi ]
876
	fi ]
877
)
877
)
878
878
879
AUDIT_MODULE=none
880
AC_ARG_WITH(audit,
881
	[  --with-audit=module     Enable EXPERIMENTAL audit support (modules=debug,bsm)],
882
	[
883
	  AC_MSG_CHECKING(for supported audit module)
884
	  case "$withval" in
885
	  bsm)
886
		AC_MSG_RESULT(bsm)
887
		AUDIT_MODULE=bsm
888
		dnl    Checks for headers, libs and functions
889
		AC_CHECK_HEADERS(bsm/audit.h, [],
890
		    [AC_MSG_ERROR(BSM enabled and bsm/audit.h not found)])
891
		AC_CHECK_LIB(bsm, getaudit, [],
892
		    [AC_MSG_ERROR(BSM enabled and required library not found)])
893
		AC_CHECK_FUNCS(getaudit, [],
894
		    [AC_MSG_ERROR(BSM enabled and required function not found)])
895
		# These are optional
896
		AC_CHECK_FUNCS(getaudit_addr gettext)
897
		AC_DEFINE(USE_BSM_AUDIT, [], [Use BSM audit module])
898
		;;
899
	  debug)
900
		AUDIT_MODULE=debug
901
		AC_MSG_RESULT(debug)
902
		AC_DEFINE(SSH_AUDIT_EVENTS, [], Use audit debugging module)
903
		;;
904
	  *)
905
		AC_MSG_ERROR([Unknown audit module $withval])
906
		;;
907
	esac ]
908
)
909
879
dnl    Checks for library functions. Please keep in alphabetical order
910
dnl    Checks for library functions. Please keep in alphabetical order
880
AC_CHECK_FUNCS(\
911
AC_CHECK_FUNCS(\
881
	arc4random __b64_ntop b64_ntop __b64_pton b64_pton bcopy \
912
	arc4random __b64_ntop b64_ntop __b64_pton b64_pton bcopy \
Lines 1783-1788 TYPE_SOCKLEN_T Link Here
1783
1814
1784
AC_CHECK_TYPES(sig_atomic_t,,,[#include <signal.h>])
1815
AC_CHECK_TYPES(sig_atomic_t,,,[#include <signal.h>])
1785
1816
1817
AC_CHECK_TYPES(in_addr_t,,,[#include <netinet/in.h>])
1818
1786
AC_CACHE_CHECK([for size_t], ac_cv_have_size_t, [
1819
AC_CACHE_CHECK([for size_t], ac_cv_have_size_t, [
1787
	AC_TRY_COMPILE(
1820
	AC_TRY_COMPILE(
1788
		[
1821
		[
(-)defines.h (+9 lines)
Lines 288-293 struct sockaddr_un { Link Here
288
};
288
};
289
#endif /* HAVE_SYS_UN_H */
289
#endif /* HAVE_SYS_UN_H */
290
290
291
#ifndef HAVE_IN_ADDR_T
292
typedef u_int32_t	in_addr_t;
293
#endif
294
291
#if defined(BROKEN_SYS_TERMIO_H) && !defined(_STRUCT_WINSIZE)
295
#if defined(BROKEN_SYS_TERMIO_H) && !defined(_STRUCT_WINSIZE)
292
#define _STRUCT_WINSIZE
296
#define _STRUCT_WINSIZE
293
struct winsize {
297
struct winsize {
Lines 530-535 struct winsize { Link Here
530
# define getpgrp() getpgrp(0)
534
# define getpgrp() getpgrp(0)
531
#endif
535
#endif
532
536
537
#ifdef USE_BSM_AUDIT
538
# define SSH_AUDIT_EVENTS
539
# define CUSTOM_SSH_AUDIT_EVENTS
540
#endif
541
533
/* OPENSSL_free() is Free() in versions before OpenSSL 0.9.6 */
542
/* OPENSSL_free() is Free() in versions before OpenSSL 0.9.6 */
534
#if !defined(OPENSSL_VERSION_NUMBER) || (OPENSSL_VERSION_NUMBER < 0x0090600f)
543
#if !defined(OPENSSL_VERSION_NUMBER) || (OPENSSL_VERSION_NUMBER < 0x0090600f)
535
# define OPENSSL_free(x) Free(x)
544
# define OPENSSL_free(x) Free(x)

Return to bug 125