2 * Copyright (c) 1996 by
3 * David Nugent <davidn@blaze.net.au>
6 * Redistribution and use in source and binary forms, with or without
7 * modification, is permitted provided that the following conditions
9 * 1. Redistributions of source code must retain the above copyright
10 * notice immediately at the beginning of the file, without modification,
11 * this list of conditions, and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * 3. This work was done expressly for inclusion into FreeBSD. Other use
16 * is permitted provided this notation is included.
17 * 4. Absolutely no warranty of function or purpose is made by the authors.
18 * 5. Modifications may be freely made to this file providing the above
21 * Support allow/deny lists in login class capabilities
24 #include <sys/cdefs.h>
25 #include <sys/types.h>
27 #include <sys/resource.h>
28 #include <sys/param.h>
31 #include <login_cap.h>
38 /* -- support functions -- */
42 * This function is intentionally public - reused by TAS.
43 * Returns TRUE (non-zero) if a string matches a pattern
44 * in a given array of patterns. 'flags' is passed directly
49 login_strinlist(const char **list, char const *str, int flags)
53 if (str != NULL && *str != '\0') {
56 while (rc == 0 && list[i] != NULL)
57 rc = fnmatch(list[i++], str, flags) == 0;
65 * Locate either or two strings in a given list
69 login_str2inlist(const char **ttlst, const char *str1, const char *str2, int flags)
73 if (login_strinlist(ttlst, str1, flags))
75 else if (login_strinlist(ttlst, str2, flags))
83 * This function is intentionally public - reused by TAS.
84 * Returns an allocated list of time periods given an array
85 * of time periods in ascii form.
89 login_timelist(login_cap_t *lc, char const *cap, int *ltno,
93 struct login_time *lt = NULL;
96 if ((tl = login_getcaplist(lc, cap, NULL)) != NULL) {
98 while (tl[j++] != NULL)
102 else if ((lt = realloc(*ltptr, j * sizeof(struct login_time))) != NULL) {
109 for (--j; i < j; i++)
110 lt[i] = parse_lt(tl[i]);
111 lt[i].lt_dow = LTM_NONE;
120 * This function is a variation of auth_ttyok(), but it checks two
121 * arbitrary capability lists not necessarily related to access.
122 * This hook is provided for the accounted/exclude accounting lists.
126 login_ttyok(login_cap_t *lc, const char *tty, const char *allowcap,
131 if (lc != NULL && tty != NULL && *tty != '\0') {
136 te = getttynam(tty); /* Need group name */
137 grp = te ? te->ty_group : NULL;
138 ttl = login_getcaplist(lc, allowcap, NULL);
140 if (ttl != NULL && !login_str2inlist(ttl, tty, grp, 0))
141 rc = 0; /* tty or ttygroup not in allow list */
144 ttl = login_getcaplist(lc, denycap, NULL);
145 if (ttl != NULL && login_str2inlist(ttl, tty, grp, 0))
146 rc = 0; /* tty or ttygroup in deny list */
156 * Determine whether or not login on a tty is accessible for
161 auth_ttyok(login_cap_t *lc, const char * tty)
163 return login_ttyok(lc, tty, "ttys.allow", "ttys.deny");
169 * This function is a variation of auth_hostok(), but it checks two
170 * arbitrary capability lists not necessarily related to access.
171 * This hook is provided for the accounted/exclude accounting lists.
175 login_hostok(login_cap_t *lc, const char *host, const char *ip,
176 const char *allowcap, const char *denycap)
178 int rc = 1; /* Default is ok */
181 ((host != NULL && *host != '\0') || (ip != NULL && *ip != '\0'))) {
184 hl = login_getcaplist(lc, allowcap, NULL);
185 if (hl != NULL && !login_str2inlist(hl, host, ip, FNM_CASEFOLD))
186 rc = 0; /* host or IP not in allow list */
189 hl = login_getcaplist(lc, denycap, NULL);
190 if (hl != NULL && login_str2inlist(hl, host, ip, FNM_CASEFOLD))
191 rc = 0; /* host or IP in deny list */
201 * Determine whether or not login from a host is ok
205 auth_hostok(login_cap_t *lc, const char *host, const char *ip)
207 return login_hostok(lc, host, ip, "host.allow", "host.deny");
213 * Determine whether or not login is ok at a given time
217 auth_timeok(login_cap_t *lc, time_t t)
219 int rc = 1; /* Default is ok */
221 if (lc != NULL && t != (time_t)0 && t != (time_t)-1) {
224 static int ltimesno = 0;
225 static struct login_time *ltimes = NULL;
227 if ((tptr = localtime(&t)) != NULL) {
228 struct login_time *lt;
230 lt = login_timelist(lc, "times.allow", <imesno, <imes);
231 if (lt != NULL && in_ltms(lt, tptr, NULL) == -1)
232 rc = 0; /* not in allowed times list */
235 lt = login_timelist(lc, "times.deny", <imesno, <imes);
236 if (lt != NULL && in_ltms(lt, tptr, NULL) != -1)
237 rc = 0; /* in deny times list */