blob: 39eeb715a15be2d081b9d4e16e2e5bc508f91ad9 [file] [log] [blame]
lh9ed821d2023-04-07 01:36:19 -07001/*
2 * auth.c - PPP authentication and phase control.
3 *
4 * Copyright (c) 1993 The Australian National University.
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms are permitted
8 * provided that the above copyright notice and this paragraph are
9 * duplicated in all such forms and that any documentation,
10 * advertising materials, and other materials related to such
11 * distribution and use acknowledge that the software was developed
12 * by the Australian National University. The name of the University
13 * may not be used to endorse or promote products derived from this
14 * software without specific prior written permission.
15 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
16 * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
17 * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
18 *
19 * Copyright (c) 1989 Carnegie Mellon University.
20 * All rights reserved.
21 *
22 * Redistribution and use in source and binary forms are permitted
23 * provided that the above copyright notice and this paragraph are
24 * duplicated in all such forms and that any documentation,
25 * advertising materials, and other materials related to such
26 * distribution and use acknowledge that the software was developed
27 * by Carnegie Mellon University. The name of the
28 * University may not be used to endorse or promote products derived
29 * from this software without specific prior written permission.
30 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
31 * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
32 * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
33 */
34
35#define RCSID "$Id: auth.c,v 1.1 2008-08-04 06:11:52 winfred Exp $"
36
37#include <string.h>
38#include <netinet/in.h>
39
40#include "pppd.h"
41#include "fsm.h"
42#include "lcp.h"
43#include "ipcp.h"
44#include "upap.h"
45#include "chap.h"
46
47/* The name by which the peer authenticated itself to us. */
48char peer_authname[MAXNAMELEN];
49
50/* Records which authentication operations haven't completed yet. */
51static int auth_pending[NUM_PPP];
52
53/* Number of network protocols which we have opened. */
54static int num_np_open;
55
56/* Number of network protocols which have come up. */
57static int num_np_up;
58
59/*
60 * Option variables.
61 */
62bool uselogin = 0; /* Use /etc/passwd for checking PAP */
63bool cryptpap = 0; /* Passwords in pap-secrets are encrypted */
64bool refuse_pap = 0; /* Don't wanna auth. ourselves with PAP */
65bool refuse_chap = 0; /* Don't wanna auth. ourselves with CHAP */
66bool usehostname = 0; /* Use hostname for our_name */
67bool auth_required = 0; /* Always require authentication from peer */
68bool allow_any_ip = 0; /* Allow peer to use any IP address */
69bool explicit_remote = 0; /* User specified explicit remote name */
70char remote_name[MAXNAMELEN]; /* Peer's name for authentication */
71
72/* Bits in auth_pending[] */
73#define PAP_WITHPEER 1
74#define PAP_PEER 2
75#define CHAP_WITHPEER 4
76#define CHAP_PEER 8
77
78/* Prototypes for procedures local to this file. */
79
80static void network_phase __P((int));
81static void check_idle __P((void *));
82static void connect_time_expired __P((void *));
83
84/*
85 * LCP has terminated the link; go to the Dead phase and take the
86 * physical layer down.
87 */
88void
89link_terminated(unit)
90 int unit;
91{
92 if (phase == PHASE_DEAD)
93 return;
94 new_phase(PHASE_DEAD);
95 notice("Connection terminated.");
96}
97
98/*
99 * LCP has gone down; it will either die or try to re-establish.
100 */
101void
102link_down(unit)
103 int unit;
104{
105 int i;
106 struct protent *protp;
107
108 for (i = 0; (protp = protocols[i]) != NULL; ++i) {
109 if (!protp->enabled_flag)
110 continue;
111 if (protp->protocol != PPP_LCP && protp->lowerdown != NULL)
112 (*protp->lowerdown)(unit);
113 if (protp->protocol < 0xC000 && protp->close != NULL)
114 (*protp->close)(unit, "LCP down");
115 }
116 num_np_open = 0;
117 num_np_up = 0;
118 if (phase != PHASE_DEAD)
119 new_phase(PHASE_TERMINATE);
120}
121
122/*
123 * The link is established.
124 * Proceed to the Dead, Authenticate or Network phase as appropriate.
125 */
126void
127link_established(unit)
128 int unit;
129{
130 int auth;
131 lcp_options *ho = &lcp_hisoptions[unit];
132 int i;
133 struct protent *protp;
134
135 /*
136 * Tell higher-level protocols that LCP is up.
137 */
138 for (i = 0; (protp = protocols[i]) != NULL; ++i)
139 if (protp->protocol != PPP_LCP && protp->enabled_flag
140 && protp->lowerup != NULL)
141 (*protp->lowerup)(unit);
142
143 new_phase(PHASE_AUTHENTICATE);
144 auth = 0;
145 if (ho->neg_chap) {
146#ifdef CHAP_SUPPORT
147 ChapAuthWithPeer(unit, user, ho->chap_mdtype);
148 auth |= CHAP_WITHPEER;
149#else
150 error("CHAP unsupported");
151#endif
152 } else if (ho->neg_upap) {
153 if (passwd[0] == 0) {
154 error("No secret found for PAP login");
155 }
156 upap_authwithpeer(unit, user, passwd);
157 auth |= PAP_WITHPEER;
158 }
159 auth_pending[unit] = auth;
160
161 if (!auth)
162 network_phase(unit);
163}
164
165/*
166 * Proceed to the network phase.
167 */
168static void
169network_phase(unit)
170 int unit;
171{
172 start_networks();
173}
174
175void
176start_networks()
177{
178 int i;
179 struct protent *protp;
180
181 new_phase(PHASE_NETWORK);
182
183 for (i = 0; (protp = protocols[i]) != NULL; ++i)
184 if (protp->protocol < 0xC000 && protp->enabled_flag
185 && protp->open != NULL) {
186 (*protp->open)(0);
187 if (protp->protocol != PPP_CCP)
188 ++num_np_open;
189 }
190
191 if (num_np_open == 0)
192 /* nothing to do */
193 lcp_close(0, "No network protocols running");
194}
195
196/*
197 * The peer has failed to authenticate himself using `protocol'.
198 */
199void
200auth_peer_fail(unit, protocol)
201 int unit, protocol;
202{
203 /*
204 * Authentication failure: take the link down
205 */
206 lcp_close(unit, "Authentication failed");
207 status = EXIT_PEER_AUTH_FAILED;
208}
209
210/*
211 * The peer has been successfully authenticated using `protocol'.
212 */
213void
214auth_peer_success(unit, protocol, name, namelen)
215 int unit, protocol;
216 char *name;
217 int namelen;
218{
219 int bit;
220
221 switch (protocol) {
222 case PPP_CHAP:
223 bit = CHAP_PEER;
224 break;
225 case PPP_PAP:
226 bit = PAP_PEER;
227 break;
228 default:
229 warn("auth_peer_success: unknown protocol %x", protocol);
230 return;
231 }
232
233 /*
234 * Save the authenticated name of the peer for later.
235 */
236 if (namelen > sizeof(peer_authname) - 1)
237 namelen = sizeof(peer_authname) - 1;
238 BCOPY(name, peer_authname, namelen);
239 peer_authname[namelen] = 0;
240 script_setenv("PEERNAME", peer_authname, 0);
241
242 /*
243 * If there is no more authentication still to be done,
244 * proceed to the network (or callback) phase.
245 */
246 if ((auth_pending[unit] &= ~bit) == 0)
247 network_phase(unit);
248}
249
250/*
251 * We have failed to authenticate ourselves to the peer using `protocol'.
252 */
253void
254auth_withpeer_fail(unit, protocol)
255 int unit, protocol;
256{
257 /*
258 * We've failed to authenticate ourselves to our peer.
259 * Some servers keep sending CHAP challenges, but there
260 * is no point in persisting without any way to get updated
261 * authentication secrets.
262 */
263 lcp_close(unit, "Failed to authenticate ourselves to peer");
264 status = EXIT_AUTH_TOPEER_FAILED;
265}
266
267/*
268 * We have successfully authenticated ourselves with the peer using `protocol'.
269 */
270void
271auth_withpeer_success(unit, protocol)
272 int unit, protocol;
273{
274 int bit;
275
276 switch (protocol) {
277 case PPP_CHAP:
278 bit = CHAP_WITHPEER;
279 break;
280 case PPP_PAP:
281 bit = PAP_WITHPEER;
282 break;
283 default:
284 warn("auth_withpeer_success: unknown protocol %x", protocol);
285 bit = 0;
286 }
287
288 /*
289 * If there is no more authentication still being done,
290 * proceed to the network (or callback) phase.
291 */
292 if ((auth_pending[unit] &= ~bit) == 0)
293 network_phase(unit);
294}
295
296
297/*
298 * np_up - a network protocol has come up.
299 */
300void
301np_up(unit, proto)
302 int unit, proto;
303{
304 int tlim;
305
306 if (num_np_up == 0) {
307 /*
308 * At this point we consider that the link has come up successfully.
309 */
310 status = EXIT_OK;
311 unsuccess = 0;
312 new_phase(PHASE_RUNNING);
313
314 tlim = idle_time_limit;
315 if (tlim > 0)
316 TIMEOUT(check_idle, NULL, tlim);
317
318 /*
319 * Set a timeout to close the connection once the maximum
320 * connect time has expired.
321 */
322 if (maxconnect > 0)
323 TIMEOUT(connect_time_expired, 0, maxconnect);
324
325 /*
326 * Detach now, if the updetach option was given.
327 */
328 if (updetach && !nodetach)
329 detach();
330 }
331 ++num_np_up;
332}
333
334/*
335 * np_down - a network protocol has gone down.
336 */
337void
338np_down(unit, proto)
339 int unit, proto;
340{
341 if (--num_np_up == 0) {
342 UNTIMEOUT(check_idle, NULL);
343 new_phase(PHASE_NETWORK);
344 }
345}
346
347/*
348 * np_finished - a network protocol has finished using the link.
349 */
350void
351np_finished(unit, proto)
352 int unit, proto;
353{
354 if (--num_np_open <= 0) {
355 /* no further use for the link: shut up shop. */
356 lcp_close(0, "No network protocols running");
357 }
358}
359
360/*
361 * check_idle - check whether the link has been idle for long
362 * enough that we can shut it down.
363 */
364static void
365check_idle(arg)
366 void *arg;
367{
368 struct ppp_idle idle;
369 time_t itime;
370 int tlim;
371
372 if (!get_idle_time(0, &idle))
373 return;
374 itime = MIN(idle.xmit_idle, idle.recv_idle);
375 tlim = idle_time_limit - itime;
376 if (tlim <= 0) {
377 /* link is idle: shut it down. */
378 notice("Terminating connection due to lack of activity.");
379 lcp_close(0, "Link inactive");
380 need_holdoff = 0;
381 status = EXIT_IDLE_TIMEOUT;
382 } else {
383 TIMEOUT(check_idle, NULL, tlim);
384 }
385}
386
387/*
388 * connect_time_expired - log a message and close the connection.
389 */
390static void
391connect_time_expired(arg)
392 void *arg;
393{
394 info("Connect time expired");
395 lcp_close(0, "Connect time expired"); /* Close connection */
396 status = EXIT_CONNECT_TIME;
397}
398
399/*
400 * auth_reset - called when LCP is starting negotiations to recheck
401 * authentication options, i.e. whether we have appropriate secrets
402 * to use for authenticating ourselves and/or the peer.
403 */
404void
405auth_reset(unit)
406 int unit;
407{
408 lcp_options *ao = &lcp_allowoptions[0];
409
410 ao->neg_upap = !refuse_pap && (passwd[0] != 0);
411 ao->neg_chap = !refuse_chap && (passwd[0] != 0);
412}
413
414/*
415 * get_secret - open the CHAP secret file and return the secret
416 * for authenticating the given client on the given server.
417 * (We could be either client or server).
418 */
419int
420get_secret(unit, client, server, secret, secret_len, am_server)
421 int unit;
422 char *client;
423 char *server;
424 char *secret;
425 int *secret_len;
426 int am_server;
427{
428 *secret_len = strlen(passwd);
429 BCOPY(passwd, secret, *secret_len);
430 return 1;
431}
432
433/*
434 * bad_ip_adrs - return 1 if the IP address is one we don't want
435 * to use, such as an address in the loopback net or a multicast address.
436 * addr is in network byte order.
437 */
438int
439bad_ip_adrs(addr)
440 u_int32_t addr;
441{
442 addr = ntohl(addr);
443 return (addr >> IN_CLASSA_NSHIFT) == IN_LOOPBACKNET
444 || IN_MULTICAST(addr) || IN_BADCLASS(addr);
445}