6c5c41f0e771f225871f09ab02712f71c46ee820
[debian/amanda] / common-src / security-util.h
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 #ifdef KRB5_SECURITY
49 #  define KRB5_DEPRECATED 1
50 #  ifndef KRB5_HEIMDAL_INCLUDES
51 #    include <gssapi/gssapi_generic.h>
52 #  else
53 #    include <gssapi/gssapi.h>
54 #  endif
55 #  include <krb5.h>
56 #endif
57
58 struct sec_handle;
59
60 /*
61  * This is a sec connection to a host.  We should only have
62  * one connection per host.
63  */
64 struct tcp_conn {
65     const struct security_driver *driver;       /* MUST be first */
66     int                 read, write;            /* pipes to sec */
67     pid_t               pid;                    /* pid of sec process */
68     char *              pkt;                    /* last pkt read */
69     ssize_t             pktlen;                 /* len of above */
70     event_handle_t *    ev_read;                /* read (EV_READFD) handle */
71     int                 ev_read_refcnt;         /* number of readers */
72     char                hostname[MAX_HOSTNAME_LENGTH+1];
73                                                 /* host we're talking to */
74     char *              errmsg;                 /* error passed up */
75     int                 refcnt;                 /* number of handles using */
76     int                 handle;                 /* last proto handle read */
77     int                 event_id;               /* event ID fired when token read */
78     void                (*accept_fn)(security_handle_t *, pkt_t *);
79     sockaddr_union      peer;
80     int                 (*recv_security_ok)(struct sec_handle *, pkt_t *);
81     char *              (*prefix_packet)(void *, pkt_t *);
82     int                 toclose;
83     int                 donotclose;
84     int                 auth;
85     char *              (*conf_fn)(char *, void *);
86     void *              datap;
87 #ifdef KRB5_SECURITY
88     gss_ctx_id_t        gss_context;
89 #endif
90 };
91
92
93 struct sec_stream;
94
95 /*
96  * This is the private handle data.
97  */
98 struct sec_handle {
99     security_handle_t   sech;           /* MUST be first */
100     char *              hostname;       /* ptr to rc->hostname */
101     struct sec_stream * rs;             /* virtual stream we xmit over */
102     struct tcp_conn *   rc;             /* */
103     union {
104         void (*recvpkt)(void *, pkt_t *, security_status_t);
105                                         /* func to call when packet recvd */
106         void (*connect)(void *, security_handle_t *, security_status_t);
107                                         /* func to call when connected */
108     } fn;
109     void *              arg;            /* argument to pass function */
110     event_handle_t *    ev_timeout;     /* timeout handle for recv */
111     sockaddr_union      peer;
112     int                 sequence;
113     event_id_t          event_id;
114     char *              proto_handle;
115     event_handle_t *    ev_read;
116     struct sec_handle * prev;
117     struct sec_handle * next;
118     struct udp_handle * udp;
119     void                (*accept_fn)(security_handle_t *, pkt_t *);
120     int                 (*recv_security_ok)(struct sec_handle *, pkt_t *);
121 };
122
123 /*
124  * This is the internal security_stream data for sec.
125  */
126 struct sec_stream {
127     security_stream_t   secstr;         /* MUST be first */
128     struct tcp_conn *   rc;             /* physical connection */
129     int                 handle;         /* protocol handle */
130     event_handle_t *    ev_read;        /* read (EV_WAIT) event handle */
131     void                (*fn)(void *, void *, ssize_t); /* read event fn */
132     void *              arg;            /* arg for previous */
133     int                 fd;
134     char                databuf[NETWORK_BLOCK_BYTES];
135     ssize_t             len;
136     int                 socket;
137     in_port_t           port;
138     int                 closed_by_me;
139     int                 closed_by_network;
140 };
141
142 /*
143  * This is data local to the datagram socket.  We have one datagram
144  * per process per auth.
145  */
146 typedef struct udp_handle {
147     const struct security_driver *driver;       /* MUST be first */
148     dgram_t dgram;              /* datagram to read/write from */
149     sockaddr_union peer;        /* who sent it to us */
150     pkt_t pkt;                  /* parsed form of dgram */
151     char *handle;               /* handle from recvd packet */
152     int sequence;               /* seq no of packet */
153     event_handle_t *ev_read;    /* read event handle from dgram */
154     int refcnt;                 /* number of handles blocked for reading */
155     struct sec_handle *bh_first, *bh_last;
156     void (*accept_fn)(security_handle_t *, pkt_t *);
157     int (*recv_security_ok)(struct sec_handle *, pkt_t *);
158     char *(*prefix_packet)(void *, pkt_t *);
159 } udp_handle_t;
160
161 /*
162  * We register one event handler for our network fd which takes
163  * care of all of our async requests.  When all async requests
164  * have either been satisfied or cancelled, we unregister our
165  * network event handler.
166  */
167 #define udp_addref(udp, netfd_read_callback) do {                       \
168     if ((udp)->refcnt++ == 0) {                                         \
169         assert((udp)->ev_read == NULL);                                 \
170         (udp)->ev_read = event_register((event_id_t)(udp)->dgram.socket,\
171             EV_READFD, netfd_read_callback, (udp));                     \
172     }                                                                   \
173     assert((udp)->refcnt > 0);                                          \
174 } while (0)
175
176 /*
177  * If this is the last request to be removed, then remove the
178  * reader event from the netfd.
179  */
180 #define udp_delref(udp) do {                                            \
181     assert((udp)->refcnt > 0);                                          \
182     if (--(udp)->refcnt == 0) {                                         \
183         assert((udp)->ev_read != NULL);                                 \
184         event_release((udp)->ev_read);                                  \
185         (udp)->ev_read = NULL;                                          \
186     }                                                                   \
187 } while (0)
188
189
190 int     sec_stream_auth(void *);
191 int     sec_stream_id(void *);
192 void    sec_accept(const security_driver_t *,
193                    char *(*)(char *, void *),
194                    int, int,
195                    void (*)(security_handle_t *, pkt_t *),
196                    void *);
197 void    sec_close(void *);
198 void    sec_connect_callback(void *);
199 void    sec_connect_timeout(void *);
200 void    sec_close_connection_none(void *, char *);
201
202 ssize_t stream_sendpkt(void *, pkt_t *);
203 void    stream_recvpkt(void *,
204                         void (*)(void *, pkt_t *, security_status_t),
205                         void *, int);
206 void    stream_recvpkt_timeout(void *);
207 void    stream_recvpkt_cancel(void *);
208
209 int     tcpm_stream_write(void *, const void *, size_t);
210 void    tcpm_stream_read(void *, void (*)(void *, void *, ssize_t), void *);
211 ssize_t tcpm_stream_read_sync(void *, void **);
212 void    tcpm_stream_read_cancel(void *);
213 ssize_t tcpm_send_token(struct tcp_conn *, int, int, char **, const void *, size_t);
214 ssize_t tcpm_recv_token(struct tcp_conn *, int, int *, char **, char **, ssize_t *, int);
215 void    tcpm_close_connection(void *, char *);
216
217 int     tcpma_stream_accept(void *);
218 void *  tcpma_stream_client(void *, int);
219 void *  tcpma_stream_server(void *);
220 void    tcpma_stream_close(void *);
221
222 void *  tcp1_stream_server(void *);
223 int     tcp1_stream_accept(void *);
224 void *  tcp1_stream_client(void *, int);
225
226 int     tcp_stream_write(void *, const void *, size_t);
227
228 char *  bsd_prefix_packet(void *, pkt_t *);
229 int     bsd_recv_security_ok(struct sec_handle *, pkt_t *);
230
231 ssize_t udpbsd_sendpkt(void *, pkt_t *);
232 void    udp_close(void *);
233 void    udp_recvpkt(void *, void (*)(void *, pkt_t *, security_status_t),
234                      void *, int);
235 void    udp_recvpkt_cancel(void *);
236 void    udp_recvpkt_callback(void *);
237 void    udp_recvpkt_timeout(void *);
238 int     udp_inithandle(udp_handle_t *, struct sec_handle *, char *hostname,
239                        sockaddr_union *, in_port_t, char *, int);
240 void    udp_netfd_read_callback(void *);
241
242 struct tcp_conn *sec_tcp_conn_get(const char *, int);
243 void    sec_tcp_conn_put(struct tcp_conn *);
244 void    sec_tcp_conn_read(struct tcp_conn *);
245 void    parse_pkt(pkt_t *, const void *, size_t);
246 const char *pkthdr2str(const struct sec_handle *, const pkt_t *);
247 int     str2pkthdr(udp_handle_t *);
248 char *  check_user(struct sec_handle *, const char *, const char *);
249
250 char *  check_user_ruserok    (const char *host,
251                                 struct passwd *pwd,
252                                 const char *user);
253 char *  check_user_amandahosts(const char *host,
254                                 sockaddr_union *addr,
255                                 struct passwd *pwd,
256                                 const char *user,
257                                 const char *service);
258
259 ssize_t net_read(int, void *, size_t, int);
260 ssize_t net_read_fillbuf(int, int, void *, size_t);
261 void    show_stat_info(char *a, char *b);
262 int     check_name_give_sockaddr(const char *hostname, struct sockaddr *addr,
263                                  char **errstr);
264 in_port_t find_port_for_service(char *service, char *proto);
265
266
267 #endif /* _SECURITY_INFO_H */