policy.c: Check that the input file is a proper file.
[yaid] / yaid.h
CommitLineData
9da480be
MW
1/* -*-c-*-
2 *
3 * Common definitions for YAID
4 *
5 * (c) 2012 Straylight/Edgeware
6 */
7
8/*----- Licensing notice --------------------------------------------------*
9 *
10 * This file is part of Yet Another Ident Daemon (YAID).
11 *
12 * YAID is free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License as published by
14 * the Free Software Foundation; either version 2 of the License, or
15 * (at your option) any later version.
16 *
17 * YAID is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 * GNU General Public License for more details.
21 *
22 * You should have received a copy of the GNU General Public License
23 * along with YAID; if not, write to the Free Software Foundation,
24 * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
25 */
26
27#ifndef YAID_H
28#define YAID_H
29
30#ifdef __cplusplus
31 extern "C" {
32#endif
33
34/*----- Header files ------------------------------------------------------*/
35
bf4d9761
MW
36#include "config.h"
37
9da480be
MW
38#include <assert.h>
39#include <ctype.h>
40#include <errno.h>
41#include <limits.h>
42#include <stdarg.h>
43#include <stdio.h>
44#include <string.h>
45#include <string.h>
46
47#include <sys/types.h>
48#include <unistd.h>
49#include <fcntl.h>
50
51#include <pwd.h>
52
53#include <sys/socket.h>
54#include <netinet/in.h>
55#include <arpa/inet.h>
56
9da480be
MW
57#include <syslog.h>
58
59#include <mLib/bits.h>
60#include <mLib/conn.h>
61#include <mLib/darray.h>
62#include <mLib/dstr.h>
bf4d9761 63#include <mLib/fdflags.h>
9da480be
MW
64#include <mLib/fwatch.h>
65#include <mLib/quis.h>
66#include <mLib/report.h>
67#include <mLib/sel.h>
68#include <mLib/selbuf.h>
69
c3794524 70/*----- Address family handling -------------------------------------------*/
bf4d9761 71
c3794524
MW
72/* The maximum length of an address formatted as a text string, including the
73 * terminating null byte.
74 */
75#define ADDRLEN 64
bf4d9761 76
c3794524
MW
77/* A list of address types. */
78#define ADDRTYPES(_) \
79 _(ipv4, IPV4) \
80 _(ipv6, IPV6)
9da480be 81
c3794524
MW
82/* Address types for the various families, in the form acceptable to
83 * inet_ntop(3) and inet_pton(3). */
84#define TYPE_IPV4 struct in_addr
85#define TYPE_IPV6 struct in6_addr
9da480be 86
c3794524 87/* A union of address types. */
9da480be 88union addr {
c3794524
MW
89#define UMEMB(ty, TY) TYPE_##TY ty;
90 ADDRTYPES(UMEMB)
91#undef UMEMB
9da480be
MW
92};
93
c3794524 94/* A socket holds an address and a port number. */
9da480be 95struct socket {
c3794524
MW
96 union addr addr; /* The address */
97 unsigned port; /* The port, in /host/ byte order */
9da480be
MW
98};
99
c3794524
MW
100/* An address pattern consists of an address and a prefix length: the
101 * pattern matches an address if they agree in the first LEN bits.
102 */
bf4d9761 103struct addrpat {
c3794524
MW
104 union addr addr; /* The base address */
105 unsigned len; /* The prefix length */
bf4d9761
MW
106};
107
c3794524
MW
108/* A port pattern matches a port if the port is within the stated (inclusive)
109 * bounds.
110 */
bf4d9761
MW
111struct portpat {
112 unsigned lo, hi;
113};
114
c3794524
MW
115/* A socket pattern consists simply of an address pattern and a port pattern:
116 * it matches a socket componentwise.
117 */
bf4d9761
MW
118struct sockpat {
119 struct addrpat addr;
120 struct portpat port;
121};
122
c3794524
MW
123/* The table of address-type operations. Each address family has one of
124 * these, so that most of the program doesn't need to worry about these
125 * details.
126 */
bf4d9761 127struct addrops {
c3794524
MW
128 int af; /* The AF_* constant */
129 const char *name; /* Name of the protocol, for logs */
130 unsigned len; /* Length of an address, in bits */
131 const union addr *any; /* A wildcard address */
132 const struct addrops_sys *sys; /* Pointer to system-specific ops */
133
bf4d9761 134 int (*addreq)(const union addr *, const union addr *);
c3794524
MW
135 /* Return nonzero if the two addresses are equal. */
136
bf4d9761 137 int (*match_addrpat)(const struct addrpat *, const union addr *);
c3794524
MW
138 /* Return nonzero if the pattern matches the address. */
139
bf4d9761 140 void (*socket_to_sockaddr)(const struct socket *s, void *, size_t *);
c3794524
MW
141 /* Convert a socket structure to a `struct sockaddr', and return the
142 * size of the latter.
143 */
144
bf4d9761 145 void (*sockaddr_to_addr)(const void *, union addr *);
c3794524
MW
146 /* Extract the address from a `struct sockaddr'. */
147
bf4d9761 148 int (*init_listen_socket)(int);
c3794524
MW
149 /* Perform any necessary extra operations on a socket which is going
150 * to be used to listen for incoming connections.
151 */
bf4d9761
MW
152};
153
c3794524
MW
154/* A handy constant for each address family. These are more useful than the
155 * AF_* constants in that they form a dense sequence.
156 */
bf4d9761 157enum {
3b1bed1d 158#define DEFADDR(ty, TY) ADDR_##TY,
bf4d9761
MW
159 ADDRTYPES(DEFADDR)
160#undef DEFADDR
161 ADDR_LIMIT
162};
163
c3794524
MW
164/* The table of address operations, indexed by the ADDR_* constants defined
165 * just above.
166 */
bf4d9761 167extern const struct addrops addroptab[];
c3794524
MW
168
169/* System-specific operations, provided by the system-specific code for its
170 * own purposes.
171 */
172#define OPS_SYS(ty, TY) \
bf4d9761
MW
173 extern const struct addrops_sys addrops_sys_##ty;
174ADDRTYPES(OPS_SYS)
175#undef OPS_SYS
176
c3794524
MW
177/* Answer whether the sockets SA and SB are equal. */
178extern int sockeq(const struct addrops */*ao*/,
179 const struct socket */*sa*/, const struct socket */*sb*/);
180
181/* Write a textual description of S to the string D. */
182extern void dputsock(dstr */*d*/, const struct addrops */*ao*/,
183 const struct socket */*s*/);
184
185/*----- Queries and responses ---------------------------------------------*/
186
187/* Constants for describing the `L'ocal and `R'emote ends of a connection. */
9da480be
MW
188enum { L, R, NDIR };
189
c3794524
MW
190/* Response types, and the data needed to represent any associated data. A
191 * U(MEMB, TYPE) constructs a union member; an N means no associated data.
192 */
9da480be
MW
193#define RESPONSE(_) \
194 _(ERROR, U(error, unsigned)) \
195 _(UID, U(uid, uid_t)) \
196 _(NAT, U(nat, struct socket))
197
c3794524
MW
198enum {
199#define DEFENUM(what, branch) R_##what,
200 RESPONSE(DEFENUM)
201#undef DEFENUM
202 R_LIMIT
203};
204
205/* Protocol error tokens. */
9da480be
MW
206#define ERROR(_) \
207 _(INVPORT, "INVALID-PORT") \
208 _(NOUSER, "NO-USER") \
209 _(HIDDEN, "HIDDEN-USER") \
210 _(UNKNOWN, "UNKNOWN-ERROR")
9da480be
MW
211
212enum {
213#define DEFENUM(err, tok) E_##err,
214 ERROR(DEFENUM)
215#undef DEFENUM
216 E_LIMIT
217};
218
c3794524 219extern const char *const errtok[];
9da480be 220
c3794524
MW
221/* The query structure keeps together the parameters to the client's query
222 * and our response to it.
223 */
9da480be 224struct query {
c3794524
MW
225 const struct addrops *ao; /* Address family operations */
226 struct socket s[NDIR]; /* The local and remote ends */
227 unsigned resp; /* Our response type */
228 union { /* A union of response data */
9da480be
MW
229#define DEFBRANCH(WHAT, branch) branch
230#define U(memb, ty) ty memb;
231#define N
232 RESPONSE(DEFBRANCH)
233#undef U
234#undef N
235#undef DEFBRANCH
236 } u;
237} query;
238
c3794524
MW
239/*----- Common utility functions ------------------------------------------*/
240
241/* Format and log MSG somewhere sensible, at the syslog(3) priority PRIO.
242 * Prefix it with a description of the query Q, if non-null.
243 */
244extern void logmsg(const struct query */*q*/,
245 int /*prio*/, const char */*msg*/, ...);
9da480be 246
c3794524
MW
247/*----- System-specific connection identification code --------------------*/
248
249/* Find out who is responsible for the connection described in the query Q.
250 * Write the answer to Q. Errors are logged and reported via the query
251 * structure.
252 */
253extern void identify(struct query */*q*/);
254
255/* Initialize the system-specific code. */
256extern void init_sys(void);
257
258/*----- Policy management -------------------------------------------------*/
259
260/* The possible policy actions and their names. */
9da480be
MW
261#define ACTIONS(_) \
262 _(USER, "user") \
263 _(TOKEN, "token") \
264 _(NAME, "name") \
265 _(DENY, "deny") \
266 _(HIDE, "hide") \
267 _(LIE, "lie")
268
269enum {
270#define DEFENUM(tag, word) A_##tag,
271 ACTIONS(DEFENUM)
272#undef DEFENUM
273 A_LIMIT
274};
275
c3794524 276/* A policy action. */
9da480be
MW
277struct action {
278 unsigned act;
279 union {
c3794524
MW
280 unsigned user; /* Bitmask of permitted actions */
281 char *lie; /* The user name to impersonate */
9da480be
MW
282 } u;
283};
284
c3794524
MW
285/* A policy rule: if the query matches the pattern, then perform the
286 * action.
287 */
9da480be 288struct policy {
bf4d9761 289 const struct addrops *ao;
9da480be
MW
290 struct sockpat sp[NDIR];
291 struct action act;
292};
c3794524
MW
293#define POLICY_INIT(a) { .act.act = a }
294DA_DECL(policy_v, struct policy);
9da480be 295
c3794524
MW
296/* Initialize a policy structure. In this state, it doesn't actually have
297 * any resources allocated (so can be simply discarded) but it's safe to free
298 * (using `free_policy').
299 */
300extern void init_policy(struct policy */*p*/);
9da480be 301
c3794524
MW
302/* Free a policy structure, resetting it to its freshly-initialized state.
303 * This function is idempotent.
304 */
305extern void free_policy(struct policy */*p*/);
306
307/* Print a policy rule to standard output. */
308extern void print_policy(const struct policy */*p*/);
309
310/* Return true if the query matches the patterns in the policy rule. */
311extern int match_policy(const struct policy */*p*/,
312 const struct query */*q*/);
313
314/*----- Parsing policy files ----------------------------------------------*/
9da480be 315
c3794524
MW
316/* Possible results from a parse. */
317enum {
318 T_OK, /* Successful: results returned */
319 T_EOL, /* End-of-line found immediately */
320 T_EOF, /* End-of-file found immediately */
321 T_ERROR /* Some kind of error occurred */
322};
9da480be 323
c3794524
MW
324/* A context for parsing a policy file. */
325struct policy_file {
326 FILE *fp; /* The file to read from */
327 const struct query *q; /* A query to use for logging */
328 const char *name; /* The name of the file */
329 const char *what; /* A description of the file */
330 int err; /* Have there been any errors? */
331 int lno; /* The current line number */
332 struct policy p; /* Parsed policy rule goes here */
333};
bf4d9761 334
c3794524
MW
335/* Open a policy file by NAME. The description WHAT and query Q are used for
336 * formatting error messages for the log.
337 */
338extern int open_policy_file(struct policy_file */*pf*/, const char */*name*/,
339 const char */*what*/, const struct query */*q*/);
9da480be 340
c3794524
MW
341/* Read a policy rule from the file, storing it in PF->p. Return one of the
342 * T_* codes.
343 */
344extern int read_policy_file(struct policy_file */*pf*/);
345
346/* Close a policy file. It doesn't matter whether the file was completely
347 * read.
348 */
349extern void close_policy_file(struct policy_file */*pf*/);
9da480be 350
c3794524
MW
351/* Load a policy file, writing a vector of records into PV. If the policy
352 * file has errors, then leave PV unchanged and return nonzero.
353 */
354extern int load_policy_file(const char */*file*/, policy_v */*pv*/);
9da480be
MW
355
356/*----- That's all, folks -------------------------------------------------*/
357
358#ifdef __cplusplus
359 }
360#endif
361
362#endif