1 #ifndef _SECURITY_UTIL_H
2 #define _SECURITY_UTIL_H
3 
4 /*
5  * Amanda, The Advanced Maryland Automatic Network Disk Archiver
6  * Copyright (c) 1999 University of Maryland
7  * All Rights Reserved.
8  *
9  * Permission to use, copy, modify, distribute, and sell this software and its
10  * documentation for any purpose is hereby granted without fee, provided that
11  * the above copyright notice appear in all copies and that both that
12  * copyright notice and this permission notice appear in supporting
13  * documentation, and that the name of U.M. not be used in advertising or
14  * publicity pertaining to distribution of the software without specific,
15  * written prior permission.  U.M. makes no representations about the
16  * suitability of this software for any purpose.  It is provided "as is"
17  * without express or implied warranty.
18  *
19  * U.M. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
20  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL U.M.
21  * BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
22  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
23  * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
24  * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
25  *
26  * Authors: the Amanda Development Team.  Its members are listed in a
27  * file named AUTHORS, in the root directory of this distribution.
28  */
29 
30 /*
31  * $Id: security-util.h,v 1.5 2006/07/01 00:10:38 paddy_s Exp $
32  *
33  */
34 
35 #include "stream.h"
36 #include "dgram.h"
37 #include "conffile.h"
38 #include "security.h"
39 #include "event.h"
40 
41 #define auth_debug(i, ...) do {		\
42 	if ((i) <= debug_auth) {	\
43 	    dbprintf(__VA_ARGS__);	\
44 	}				\
45 } while (0)
46 
47 
48 /*
49  * Magic values for sec_conn->handle
50  */
51 #define H_TAKEN -1		/* sec_conn->tok was already read */
52 #define H_EOF   -2		/* this connection has been shut down */
53 
54 #ifdef KRB5_SECURITY
55 #  define KRB5_DEPRECATED 1
56 #  ifndef KRB5_HEIMDAL_INCLUDES
57 #    include <gssapi/gssapi_generic.h>
58 #  else
59 #    include <gssapi/gssapi.h>
60 #  endif
61 #  include <krb5.h>
62 #endif
63 
64 struct sec_handle;
65 
66 /*
67  * This is a sec connection to a host.  We should only have
68  * one connection per host.
69  */
70 struct tcp_conn {
71     const struct security_driver *driver;	/* MUST be first */
72     int			read, write;		/* pipes to sec */
73     pid_t		pid;			/* pid of sec process */
74     char *		pkt;			/* last pkt read */
75     ssize_t		pktlen;			/* len of above */
76     event_handle_t *	ev_read;		/* read (EV_READFD) handle */
77     int			ev_read_refcnt;		/* number of readers */
78     char		hostname[MAX_HOSTNAME_LENGTH+1];
79 						/* host we're talking to */
80     char *		errmsg;			/* error passed up */
81     int			refcnt;			/* number of handles using */
82     int			handle;			/* last proto handle read */
83     int			event_id;		/* event ID fired when token read */
84     void		(*accept_fn)(security_handle_t *, pkt_t *);
85     sockaddr_union	peer;
86     int			(*recv_security_ok)(struct sec_handle *, pkt_t *);
87     char *		(*prefix_packet)(void *, pkt_t *);
88     int			toclose;
89     int			donotclose;
90     int			auth;
91     char *              (*conf_fn)(char *, void *);
92     void *              datap;
93     time_t              logstamp;
94 #ifdef KRB5_SECURITY
95     gss_ctx_id_t	gss_context;
96 #endif
97     unsigned int	netint[2];
98     char *              buffer;
99     ssize_t             size_header_read;
100     ssize_t             size_buffer_read;
101 };
102 
103 
104 struct sec_stream;
105 
106 /*
107  * This is the private handle data.
108  */
109 struct sec_handle {
110     security_handle_t	sech;		/* MUST be first */
111     char *		hostname;	/* ptr to rc->hostname */
112     struct sec_stream *	rs;		/* virtual stream we xmit over */
113     struct tcp_conn *	rc;		/* */
114     union {
115 	void (*recvpkt)(void *, pkt_t *, security_status_t);
116 					/* func to call when packet recvd */
117 	void (*connect)(void *, security_handle_t *, security_status_t);
118 					/* func to call when connected */
119     } fn;
120     void *		arg;		/* argument to pass function */
121     event_handle_t *	ev_timeout;	/* timeout handle for recv */
122     sockaddr_union	peer;
123     int			sequence;
124     event_id_t		event_id;
125     char *		proto_handle;
126     event_handle_t *	ev_read;
127     struct sec_handle *	prev;
128     struct sec_handle *	next;
129     struct udp_handle *	udp;
130     void		(*accept_fn)(security_handle_t *, pkt_t *);
131     int			(*recv_security_ok)(struct sec_handle *, pkt_t *);
132     struct addrinfo    *res;
133     struct addrinfo    *next_res;
134     void                (*connect_callback)(void *, security_handle_t *, security_status_t);
135     void               *connect_arg;
136     char               *src_ip;
137     int                 port;
138 };
139 
140 /*
141  * This is the internal security_stream data for sec.
142  */
143 struct sec_stream {
144     security_stream_t	secstr;		/* MUST be first */
145     struct tcp_conn *	rc;		/* physical connection */
146     int			handle;		/* protocol handle */
147     event_handle_t *	ev_read;	/* read (EV_WAIT) event handle */
148     void		(*fn)(void *, void *, ssize_t);	/* read event fn */
149     void *		arg;		/* arg for previous */
150     int			fd;
151     char		databuf[NETWORK_BLOCK_BYTES];
152     ssize_t		len;
153     int			socket;
154     in_port_t		port;
155     int			closed_by_me;
156     int			closed_by_network;
157 };
158 
159 /*
160  * This is data local to the datagram socket.  We have one datagram
161  * per process per auth.
162  */
163 typedef struct udp_handle {
164     const struct security_driver *driver;	/* MUST be first */
165     dgram_t dgram;		/* datagram to read/write from */
166     sockaddr_union peer;	/* who sent it to us */
167     pkt_t pkt;			/* parsed form of dgram */
168     char *handle;		/* handle from recvd packet */
169     int sequence;		/* seq no of packet */
170     event_handle_t *ev_read;	/* read event handle from dgram */
171     int refcnt;			/* number of handles blocked for reading */
172     struct sec_handle *bh_first, *bh_last;
173     void (*accept_fn)(security_handle_t *, pkt_t *);
174     int (*recv_security_ok)(struct sec_handle *, pkt_t *);
175     char *(*prefix_packet)(void *, pkt_t *);
176 } udp_handle_t;
177 
178 /*
179  * We register one event handler for our network fd which takes
180  * care of all of our async requests.  When all async requests
181  * have either been satisfied or cancelled, we unregister our
182  * network event handler.
183  */
184 #define	udp_addref(udp, netfd_read_callback) do {			\
185     if ((udp)->refcnt++ == 0) {						\
186 	assert((udp)->ev_read == NULL);					\
187 	(udp)->ev_read = event_register((event_id_t)(udp)->dgram.socket,\
188 	    EV_READFD, netfd_read_callback, (udp));			\
189     }									\
190     assert((udp)->refcnt > 0);						\
191 } while (0)
192 
193 /*
194  * If this is the last request to be removed, then remove the
195  * reader event from the netfd.
196  */
197 #define	udp_delref(udp) do {						\
198     assert((udp)->refcnt > 0);						\
199     if (--(udp)->refcnt == 0) {						\
200 	assert((udp)->ev_read != NULL);					\
201 	event_release((udp)->ev_read);					\
202 	(udp)->ev_read = NULL;						\
203     }									\
204 } while (0)
205 
206 
207 int	sec_stream_auth(void *);
208 int	sec_stream_id(void *);
209 void	sec_accept(const security_driver_t *,
210 		   char *(*)(char *, void *),
211 		   int, int,
212 		   void (*)(security_handle_t *, pkt_t *),
213 		   void *);
214 void	sec_close(void *);
215 void	sec_connect_callback(void *);
216 void	sec_connect_timeout(void *);
217 void	sec_close_connection_none(void *, char *);
218 
219 ssize_t	stream_sendpkt(void *, pkt_t *);
220 void	stream_recvpkt(void *,
221 		        void (*)(void *, pkt_t *, security_status_t),
222 		        void *, int);
223 void	stream_recvpkt_timeout(void *);
224 void	stream_recvpkt_cancel(void *);
225 
226 int	tcpm_stream_write(void *, const void *, size_t);
227 void	tcpm_stream_read(void *, void (*)(void *, void *, ssize_t), void *);
228 ssize_t	tcpm_stream_read_sync(void *, void **);
229 void	tcpm_stream_read_cancel(void *);
230 ssize_t	tcpm_send_token(struct tcp_conn *, int, int, char **, const void *, size_t);
231 ssize_t	tcpm_recv_token_timeout(struct tcp_conn *, int, int *, char **, char **, ssize_t *, int);
232 ssize_t	tcpm_recv_token(struct tcp_conn *, int, int *, char **, char **, ssize_t *);
233 void	tcpm_close_connection(void *, char *);
234 
235 int	tcpma_stream_accept(void *);
236 void *	tcpma_stream_client(void *, int);
237 void *	tcpma_stream_server(void *);
238 void	tcpma_stream_close(void *);
239 
240 void *	tcp1_stream_server(void *);
241 int	tcp1_stream_accept(void *);
242 void *	tcp1_stream_client(void *, int);
243 
244 int	tcp_stream_write(void *, const void *, size_t);
245 
246 char *	bsd_prefix_packet(void *, pkt_t *);
247 int	bsd_recv_security_ok(struct sec_handle *, pkt_t *);
248 
249 ssize_t	udpbsd_sendpkt(void *, pkt_t *);
250 void	udp_close(void *);
251 void	udp_recvpkt(void *, void (*)(void *, pkt_t *, security_status_t),
252 		     void *, int);
253 void	udp_recvpkt_cancel(void *);
254 void	udp_recvpkt_callback(void *);
255 void	udp_recvpkt_timeout(void *);
256 int	udp_inithandle(udp_handle_t *, struct sec_handle *, char *hostname,
257 		       sockaddr_union *, in_port_t, char *, int);
258 void	udp_netfd_read_callback(void *);
259 
260 struct tcp_conn *sec_tcp_conn_get(const char *, int);
261 void	sec_tcp_conn_put(struct tcp_conn *);
262 void	sec_tcp_conn_read(struct tcp_conn *);
263 void	parse_pkt(pkt_t *, const void *, size_t);
264 const char *pkthdr2str(const struct sec_handle *, const pkt_t *);
265 int	str2pkthdr(udp_handle_t *);
266 char *	check_user(struct sec_handle *, const char *, const char *);
267 
268 char *	check_user_ruserok    (const char *host,
269 				struct passwd *pwd,
270 				const char *user);
271 char *	check_user_amandahosts(const char *host,
272 			        sockaddr_union *addr,
273 				struct passwd *pwd,
274 				const char *user,
275 				const char *service);
276 
277 ssize_t	net_read(int, void *, size_t, int);
278 ssize_t net_read_fillbuf(int, int, void *, size_t);
279 void	show_stat_info(char *a, char *b);
280 int     check_name_give_sockaddr(const char *hostname, struct sockaddr *addr,
281 				 char **errstr);
282 in_port_t find_port_for_service(char *service, char *proto);
283 char	*sec_get_authenticated_peer_name_gethostname(security_handle_t *);
284 char	*sec_get_authenticated_peer_name_hostname(security_handle_t *);
285 
286 #endif /* _SECURITY_INFO_H */
287