if_pppoe.c revision 1.95
1/* $NetBSD: if_pppoe.c,v 1.95 2010/01/19 22:08:01 pooka Exp $ */
2
3/*-
4 * Copyright (c) 2002, 2008 The NetBSD Foundation, Inc.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Martin Husemann <martin@NetBSD.org>.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 *    notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 *    notice, this list of conditions and the following disclaimer in the
17 *    documentation and/or other materials provided with the distribution.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
30 */
31
32#include <sys/cdefs.h>
33__KERNEL_RCSID(0, "$NetBSD: if_pppoe.c,v 1.95 2010/01/19 22:08:01 pooka Exp $");
34
35#include "pppoe.h"
36#include "opt_pfil_hooks.h"
37#include "opt_pppoe.h"
38
39#include <sys/param.h>
40#include <sys/systm.h>
41#include <sys/kernel.h>
42#include <sys/callout.h>
43#include <sys/malloc.h>
44#include <sys/mbuf.h>
45#include <sys/socket.h>
46#include <sys/proc.h>
47#include <sys/ioctl.h>
48#include <sys/kauth.h>
49#include <sys/intr.h>
50#include <sys/socketvar.h>
51
52#include <net/if.h>
53#include <net/if_types.h>
54#include <net/if_ether.h>
55#include <net/if_sppp.h>
56#include <net/if_spppvar.h>
57#include <net/if_pppoe.h>
58
59#include <net/bpf.h>
60
61
62#undef PPPOE_DEBUG		/* XXX - remove this or make it an option */
63/* #define PPPOE_DEBUG 1 */
64
65struct pppoehdr {
66	uint8_t vertype;
67	uint8_t code;
68	uint16_t session;
69	uint16_t plen;
70} __packed;
71
72struct pppoetag {
73	uint16_t tag;
74	uint16_t len;
75} __packed;
76
77#define	PPPOE_HEADERLEN	sizeof(struct pppoehdr)
78#define	PPPOE_OVERHEAD	(PPPOE_HEADERLEN + 2)
79#define	PPPOE_VERTYPE	0x11	/* VER=1, TYPE = 1 */
80
81#define	PPPOE_TAG_EOL		0x0000		/* end of list */
82#define	PPPOE_TAG_SNAME		0x0101		/* service name */
83#define	PPPOE_TAG_ACNAME	0x0102		/* access concentrator name */
84#define	PPPOE_TAG_HUNIQUE	0x0103		/* host unique */
85#define	PPPOE_TAG_ACCOOKIE	0x0104		/* AC cookie */
86#define	PPPOE_TAG_VENDOR	0x0105		/* vendor specific */
87#define	PPPOE_TAG_RELAYSID	0x0110		/* relay session id */
88#define	PPPOE_TAG_SNAME_ERR	0x0201		/* service name error */
89#define	PPPOE_TAG_ACSYS_ERR	0x0202		/* AC system error */
90#define	PPPOE_TAG_GENERIC_ERR	0x0203		/* gerneric error */
91
92#define	PPPOE_CODE_PADI		0x09		/* Active Discovery Initiation */
93#define	PPPOE_CODE_PADO		0x07		/* Active Discovery Offer */
94#define	PPPOE_CODE_PADR		0x19		/* Active Discovery Request */
95#define	PPPOE_CODE_PADS		0x65		/* Active Discovery Session confirmation */
96#define	PPPOE_CODE_PADT		0xA7		/* Active Discovery Terminate */
97
98/* two byte PPP protocol discriminator, then IP data */
99#define	PPPOE_MAXMTU	(ETHERMTU - PPPOE_OVERHEAD)
100
101/* Add a 16 bit unsigned value to a buffer pointed to by PTR */
102#define	PPPOE_ADD_16(PTR, VAL)			\
103		*(PTR)++ = (VAL) / 256;		\
104		*(PTR)++ = (VAL) % 256
105
106/* Add a complete PPPoE header to the buffer pointed to by PTR */
107#define	PPPOE_ADD_HEADER(PTR, CODE, SESS, LEN)	\
108		*(PTR)++ = PPPOE_VERTYPE;	\
109		*(PTR)++ = (CODE);		\
110		PPPOE_ADD_16(PTR, SESS);	\
111		PPPOE_ADD_16(PTR, LEN)
112
113#define	PPPOE_DISC_TIMEOUT	(hz*5)	/* base for quick timeout calculation */
114#define	PPPOE_SLOW_RETRY	(hz*60)	/* persistent retry interval */
115#define	PPPOE_RECON_FAST	(hz*15)	/* first retry after auth failure */
116#define	PPPOE_RECON_IMMEDIATE	(hz/10)	/* "no delay" reconnect */
117#define	PPPOE_DISC_MAXPADI	4	/* retry PADI four times (quickly) */
118#define	PPPOE_DISC_MAXPADR	2	/* retry PADR twice */
119
120#ifdef PPPOE_SERVER
121/* from if_spppsubr.c */
122#define	IFF_PASSIVE	IFF_LINK0	/* wait passively for connection */
123#endif
124
125struct pppoe_softc {
126	struct sppp sc_sppp;		/* contains a struct ifnet as first element */
127	LIST_ENTRY(pppoe_softc) sc_list;
128	struct ifnet *sc_eth_if;	/* ethernet interface we are using */
129
130	int sc_state;			/* discovery phase or session connected */
131	struct ether_addr sc_dest;	/* hardware address of concentrator */
132	uint16_t sc_session;		/* PPPoE session id */
133
134	char *sc_service_name;		/* if != NULL: requested name of service */
135	char *sc_concentrator_name;	/* if != NULL: requested concentrator id */
136	uint8_t *sc_ac_cookie;		/* content of AC cookie we must echo back */
137	size_t sc_ac_cookie_len;	/* length of cookie data */
138	uint8_t *sc_relay_sid;		/* content of relay SID we must echo back */
139	size_t sc_relay_sid_len;	/* length of relay SID data */
140#ifdef PPPOE_SERVER
141	uint8_t *sc_hunique;		/* content of host unique we must echo back */
142	size_t sc_hunique_len;		/* length of host unique */
143#endif
144	callout_t sc_timeout;	/* timeout while not in session state */
145	int sc_padi_retried;		/* number of PADI retries already done */
146	int sc_padr_retried;		/* number of PADR retries already done */
147};
148
149/* incoming traffic will be queued here */
150struct ifqueue ppoediscinq = { .ifq_maxlen = IFQ_MAXLEN };
151struct ifqueue ppoeinq = { .ifq_maxlen = IFQ_MAXLEN };
152
153void *pppoe_softintr = NULL;
154static void pppoe_softintr_handler(void *);
155
156extern int sppp_ioctl(struct ifnet *, unsigned long, void *);
157
158/* input routines */
159static void pppoe_input(void);
160static void pppoe_disc_input(struct mbuf *);
161static void pppoe_dispatch_disc_pkt(struct mbuf *, int);
162static void pppoe_data_input(struct mbuf *);
163
164/* management routines */
165void pppoeattach(int);
166static int pppoe_connect(struct pppoe_softc *);
167static int pppoe_disconnect(struct pppoe_softc *);
168static void pppoe_abort_connect(struct pppoe_softc *);
169static int pppoe_ioctl(struct ifnet *, unsigned long, void *);
170static void pppoe_tls(struct sppp *);
171static void pppoe_tlf(struct sppp *);
172static void pppoe_start(struct ifnet *);
173static void pppoe_clear_softc(struct pppoe_softc *, const char *);
174
175/* internal timeout handling */
176static void pppoe_timeout(void *);
177
178/* sending actual protocol controll packets */
179static int pppoe_send_padi(struct pppoe_softc *);
180static int pppoe_send_padr(struct pppoe_softc *);
181#ifdef PPPOE_SERVER
182static int pppoe_send_pado(struct pppoe_softc *);
183static int pppoe_send_pads(struct pppoe_softc *);
184#endif
185static int pppoe_send_padt(struct ifnet *, u_int, const uint8_t *);
186
187/* raw output */
188static int pppoe_output(struct pppoe_softc *, struct mbuf *);
189
190/* internal helper functions */
191static struct pppoe_softc * pppoe_find_softc_by_session(u_int, struct ifnet *);
192static struct pppoe_softc * pppoe_find_softc_by_hunique(uint8_t *, size_t, struct ifnet *);
193static struct mbuf *pppoe_get_mbuf(size_t len);
194
195#ifdef PFIL_HOOKS
196static int pppoe_ifattach_hook(void *, struct mbuf **, struct ifnet *, int);
197#endif
198
199static LIST_HEAD(pppoe_softc_head, pppoe_softc) pppoe_softc_list;
200
201static int	pppoe_clone_create(struct if_clone *, int);
202static int	pppoe_clone_destroy(struct ifnet *);
203
204static struct if_clone pppoe_cloner =
205    IF_CLONE_INITIALIZER("pppoe", pppoe_clone_create, pppoe_clone_destroy);
206
207/* ARGSUSED */
208void
209pppoeattach(int count)
210{
211	LIST_INIT(&pppoe_softc_list);
212	if_clone_attach(&pppoe_cloner);
213
214	pppoe_softintr = softint_establish(SOFTINT_NET, pppoe_softintr_handler, NULL);
215}
216
217static int
218pppoe_clone_create(struct if_clone *ifc, int unit)
219{
220	struct pppoe_softc *sc;
221
222	sc = malloc(sizeof(struct pppoe_softc), M_DEVBUF, M_WAITOK|M_ZERO);
223
224	if_initname(&sc->sc_sppp.pp_if, "pppoe", unit);
225	sc->sc_sppp.pp_if.if_softc = sc;
226	sc->sc_sppp.pp_if.if_mtu = PPPOE_MAXMTU;
227	sc->sc_sppp.pp_if.if_flags = IFF_SIMPLEX|IFF_POINTOPOINT|IFF_MULTICAST;
228	sc->sc_sppp.pp_if.if_type = IFT_PPP;
229	sc->sc_sppp.pp_if.if_hdrlen = sizeof(struct ether_header) + PPPOE_HEADERLEN;
230	sc->sc_sppp.pp_if.if_dlt = DLT_PPP_ETHER;
231	sc->sc_sppp.pp_flags |= PP_KEEPALIVE |	/* use LCP keepalive */
232				PP_NOFRAMING;	/* no serial encapsulation */
233	sc->sc_sppp.pp_if.if_ioctl = pppoe_ioctl;
234	IFQ_SET_MAXLEN(&sc->sc_sppp.pp_if.if_snd, IFQ_MAXLEN);
235	IFQ_SET_READY(&sc->sc_sppp.pp_if.if_snd);
236
237	/* changed to real address later */
238	memcpy(&sc->sc_dest, etherbroadcastaddr, sizeof(sc->sc_dest));
239
240	callout_init(&sc->sc_timeout, 0);
241
242	sc->sc_sppp.pp_if.if_start = pppoe_start;
243	sc->sc_sppp.pp_tls = pppoe_tls;
244	sc->sc_sppp.pp_tlf = pppoe_tlf;
245	sc->sc_sppp.pp_framebytes = PPPOE_HEADERLEN;	/* framing added to ppp packets */
246
247	if_attach(&sc->sc_sppp.pp_if);
248	sppp_attach(&sc->sc_sppp.pp_if);
249
250	bpf_ops->bpf_attach(&sc->sc_sppp.pp_if, DLT_PPP_ETHER,
251	    0, &sc->sc_sppp.pp_if.if_bpf);
252#ifdef PFIL_HOOKS
253	if (LIST_EMPTY(&pppoe_softc_list))
254		pfil_add_hook(pppoe_ifattach_hook, NULL,
255		    PFIL_IFNET|PFIL_WAITOK, &if_pfil);
256#endif
257	LIST_INSERT_HEAD(&pppoe_softc_list, sc, sc_list);
258	return 0;
259}
260
261static int
262pppoe_clone_destroy(struct ifnet *ifp)
263{
264	struct pppoe_softc * sc = ifp->if_softc;
265
266	callout_stop(&sc->sc_timeout);
267	LIST_REMOVE(sc, sc_list);
268#ifdef PFIL_HOOKS
269	if (LIST_EMPTY(&pppoe_softc_list))
270		pfil_remove_hook(pppoe_ifattach_hook, NULL,
271		    PFIL_IFNET|PFIL_WAITOK, &if_pfil);
272#endif
273	bpf_ops->bpf_detach(ifp);
274	sppp_detach(&sc->sc_sppp.pp_if);
275	if_detach(ifp);
276	if (sc->sc_concentrator_name)
277		free(sc->sc_concentrator_name, M_DEVBUF);
278	if (sc->sc_service_name)
279		free(sc->sc_service_name, M_DEVBUF);
280	if (sc->sc_ac_cookie)
281		free(sc->sc_ac_cookie, M_DEVBUF);
282	if (sc->sc_relay_sid)
283		free(sc->sc_relay_sid, M_DEVBUF);
284	callout_destroy(&sc->sc_timeout);
285	free(sc, M_DEVBUF);
286
287	return (0);
288}
289
290/*
291 * Find the interface handling the specified session.
292 * Note: O(number of sessions open), this is a client-side only, mean
293 * and lean implementation, so number of open sessions typically should
294 * be 1.
295 */
296static struct pppoe_softc *
297pppoe_find_softc_by_session(u_int session, struct ifnet *rcvif)
298{
299	struct pppoe_softc *sc;
300
301	if (session == 0)
302		return NULL;
303
304	LIST_FOREACH(sc, &pppoe_softc_list, sc_list) {
305		if (sc->sc_state == PPPOE_STATE_SESSION
306		    && sc->sc_session == session
307		    && sc->sc_eth_if == rcvif)
308			return sc;
309	}
310	return NULL;
311}
312
313/* Check host unique token passed and return appropriate softc pointer,
314 * or NULL if token is bogus. */
315static struct pppoe_softc *
316pppoe_find_softc_by_hunique(uint8_t *token, size_t len, struct ifnet *rcvif)
317{
318	struct pppoe_softc *sc, *t;
319
320	if (LIST_EMPTY(&pppoe_softc_list))
321		return NULL;
322
323	if (len != sizeof sc)
324		return NULL;
325	memcpy(&t, token, len);
326
327	LIST_FOREACH(sc, &pppoe_softc_list, sc_list)
328		if (sc == t) break;
329
330	if (sc == NULL) {
331#ifdef PPPOE_DEBUG
332		printf("pppoe: alien host unique tag, no session found\n");
333#endif
334		return NULL;
335	}
336
337	/* should be safe to access *sc now */
338	if (sc->sc_state < PPPOE_STATE_PADI_SENT || sc->sc_state >= PPPOE_STATE_SESSION) {
339		printf("%s: host unique tag found, but it belongs to a connection in state %d\n",
340			sc->sc_sppp.pp_if.if_xname, sc->sc_state);
341		return NULL;
342	}
343	if (sc->sc_eth_if != rcvif) {
344		printf("%s: wrong interface, not accepting host unique\n",
345			sc->sc_sppp.pp_if.if_xname);
346		return NULL;
347	}
348	return sc;
349}
350
351static void
352pppoe_softintr_handler(void *dummy)
353{
354	/* called at splsoftnet() */
355	mutex_enter(softnet_lock);
356	pppoe_input();
357	mutex_exit(softnet_lock);
358}
359
360/* called at appropriate protection level */
361static void
362pppoe_input(void)
363{
364	struct mbuf *m;
365	int s, disc_done, data_done;
366
367	do {
368		disc_done = 0;
369		data_done = 0;
370		for (;;) {
371			s = splnet();
372			IF_DEQUEUE(&ppoediscinq, m);
373			splx(s);
374			if (m == NULL) break;
375			disc_done = 1;
376			pppoe_disc_input(m);
377		}
378
379		for (;;) {
380			s = splnet();
381			IF_DEQUEUE(&ppoeinq, m);
382			splx(s);
383			if (m == NULL) break;
384			data_done = 1;
385			pppoe_data_input(m);
386		}
387	} while (disc_done || data_done);
388}
389
390/* analyze and handle a single received packet while not in session state */
391static void
392pppoe_dispatch_disc_pkt(struct mbuf *m, int off)
393{
394	uint16_t tag, len;
395	uint16_t session, plen;
396	struct pppoe_softc *sc;
397	const char *err_msg, *devname;
398	char *error;
399	uint8_t *ac_cookie;
400	size_t ac_cookie_len;
401	uint8_t *relay_sid;
402	size_t relay_sid_len;
403#ifdef PPPOE_SERVER
404	uint8_t *hunique;
405	size_t hunique_len;
406#endif
407	struct pppoehdr *ph;
408	struct pppoetag *pt;
409	struct mbuf *n;
410	int noff, err, errortag;
411	struct ether_header *eh;
412
413	devname = "pppoe";	/* as long as we don't know which instance */
414	err_msg = NULL;
415	errortag = 0;
416	if (m->m_len < sizeof(*eh)) {
417		m = m_pullup(m, sizeof(*eh));
418		if (!m)
419			goto done;
420	}
421	eh = mtod(m, struct ether_header *);
422	off += sizeof(*eh);
423
424	ac_cookie = NULL;
425	ac_cookie_len = 0;
426	relay_sid = NULL;
427	relay_sid_len = 0;
428#ifdef PPPOE_SERVER
429	hunique = NULL;
430	hunique_len = 0;
431#endif
432	session = 0;
433	if (m->m_pkthdr.len - off <= PPPOE_HEADERLEN) {
434		printf("pppoe: packet too short: %d\n", m->m_pkthdr.len);
435		goto done;
436	}
437
438	n = m_pulldown(m, off, sizeof(*ph), &noff);
439	if (!n) {
440		printf("pppoe: could not get PPPoE header\n");
441		m = NULL;
442		goto done;
443	}
444	ph = (struct pppoehdr *)(mtod(n, char *) + noff);
445	if (ph->vertype != PPPOE_VERTYPE) {
446		printf("pppoe: unknown version/type packet: 0x%x\n",
447		    ph->vertype);
448		goto done;
449	}
450	session = ntohs(ph->session);
451	plen = ntohs(ph->plen);
452	off += sizeof(*ph);
453
454	if (plen + off > m->m_pkthdr.len) {
455		printf("pppoe: packet content does not fit: data available = %d, packet size = %u\n",
456		    m->m_pkthdr.len - off, plen);
457		goto done;
458	}
459	m_adj(m, off + plen - m->m_pkthdr.len);	/* ignore trailing garbage */
460	tag = 0;
461	len = 0;
462	sc = NULL;
463	while (off + sizeof(*pt) <= m->m_pkthdr.len) {
464		n = m_pulldown(m, off, sizeof(*pt), &noff);
465		if (!n) {
466			printf("%s: parse error\n", devname);
467			m = NULL;
468			goto done;
469		}
470		pt = (struct pppoetag *)(mtod(n, char *) + noff);
471		tag = ntohs(pt->tag);
472		len = ntohs(pt->len);
473		if (off + len + sizeof(*pt) > m->m_pkthdr.len) {
474			printf("pppoe: tag 0x%x len 0x%x is too long\n",
475			    tag, len);
476			goto done;
477		}
478		switch (tag) {
479		case PPPOE_TAG_EOL:
480			goto breakbreak;
481		case PPPOE_TAG_SNAME:
482			break;	/* ignored */
483		case PPPOE_TAG_ACNAME:
484			error = NULL;
485			if (sc != NULL && len > 0) {
486				error = malloc(len+1, M_TEMP, M_NOWAIT);
487				if (error) {
488					n = m_pulldown(m, off + sizeof(*pt),
489					    len, &noff);
490					if (n) {
491						strncpy(error,
492						    mtod(n, char*) + noff,
493						    len);
494						error[len] = '\0';
495					}
496					printf("%s: connected to %s\n",
497					    devname, error);
498					free(error, M_TEMP);
499				}
500			}
501			break;	/* ignored */
502		case PPPOE_TAG_HUNIQUE:
503			if (sc != NULL)
504				break;
505			n = m_pulldown(m, off + sizeof(*pt), len, &noff);
506			if (!n) {
507				m = NULL;
508				err_msg = "TAG HUNIQUE ERROR";
509				break;
510			}
511#ifdef PPPOE_SERVER
512			hunique = mtod(n, uint8_t *) + noff;
513			hunique_len = len;
514#endif
515			sc = pppoe_find_softc_by_hunique(mtod(n, char *) + noff,
516			    len, m->m_pkthdr.rcvif);
517			if (sc != NULL)
518				devname = sc->sc_sppp.pp_if.if_xname;
519			break;
520		case PPPOE_TAG_ACCOOKIE:
521			if (ac_cookie == NULL) {
522				n = m_pulldown(m, off + sizeof(*pt), len,
523				    &noff);
524				if (!n) {
525					err_msg = "TAG ACCOOKIE ERROR";
526					m = NULL;
527					break;
528				}
529				ac_cookie = mtod(n, char *) + noff;
530				ac_cookie_len = len;
531			}
532			break;
533		case PPPOE_TAG_RELAYSID:
534			if (relay_sid == NULL) {
535				n = m_pulldown(m, off + sizeof(*pt), len,
536				    &noff);
537				if (!n) {
538					err_msg = "TAG RELAYSID ERROR";
539					m = NULL;
540					break;
541				}
542				relay_sid = mtod(n, char *) + noff;
543				relay_sid_len = len;
544			}
545			break;
546		case PPPOE_TAG_SNAME_ERR:
547			err_msg = "SERVICE NAME ERROR";
548			errortag = 1;
549			break;
550		case PPPOE_TAG_ACSYS_ERR:
551			err_msg = "AC SYSTEM ERROR";
552			errortag = 1;
553			break;
554		case PPPOE_TAG_GENERIC_ERR:
555			err_msg = "GENERIC ERROR";
556			errortag = 1;
557			break;
558		}
559		if (err_msg) {
560			error = NULL;
561			if (errortag && len) {
562				error = malloc(len+1, M_TEMP, M_NOWAIT);
563				n = m_pulldown(m, off + sizeof(*pt), len,
564				    &noff);
565				if (n && error) {
566					strncpy(error,
567					    mtod(n, char *) + noff, len);
568					error[len] = '\0';
569				}
570			}
571			if (error) {
572				printf("%s: %s: %s\n", devname,
573				    err_msg, error);
574				free(error, M_TEMP);
575			} else
576				printf("%s: %s\n", devname, err_msg);
577			if (errortag || m == NULL)
578				goto done;
579		}
580		off += sizeof(*pt) + len;
581	}
582breakbreak:;
583	switch (ph->code) {
584	case PPPOE_CODE_PADI:
585#ifdef PPPOE_SERVER
586		/*
587		 * got service name, concentrator name, and/or host unique.
588		 * ignore if we have no interfaces with IFF_PASSIVE|IFF_UP.
589		 */
590		if (LIST_EMPTY(&pppoe_softc_list))
591			goto done;
592		LIST_FOREACH(sc, &pppoe_softc_list, sc_list) {
593			if (!(sc->sc_sppp.pp_if.if_flags & IFF_UP))
594				continue;
595			if (!(sc->sc_sppp.pp_if.if_flags & IFF_PASSIVE))
596				continue;
597			if (sc->sc_state == PPPOE_STATE_INITIAL)
598				break;
599		}
600		if (sc == NULL) {
601/*			printf("pppoe: free passive interface is not found\n");*/
602			goto done;
603		}
604		if (hunique) {
605			if (sc->sc_hunique)
606				free(sc->sc_hunique, M_DEVBUF);
607			sc->sc_hunique = malloc(hunique_len, M_DEVBUF,
608			    M_DONTWAIT);
609			if (sc->sc_hunique == NULL)
610				goto done;
611			sc->sc_hunique_len = hunique_len;
612			memcpy(sc->sc_hunique, hunique, hunique_len);
613		}
614		memcpy(&sc->sc_dest, eh->ether_shost, sizeof sc->sc_dest);
615		sc->sc_state = PPPOE_STATE_PADO_SENT;
616		pppoe_send_pado(sc);
617		break;
618#endif /* PPPOE_SERVER */
619	case PPPOE_CODE_PADR:
620#ifdef PPPOE_SERVER
621		/*
622		 * get sc from ac_cookie if IFF_PASSIVE
623		 */
624		if (ac_cookie == NULL) {
625			/* be quiet if there is not a single pppoe instance */
626			printf("pppoe: received PADR but not includes ac_cookie\n");
627			goto done;
628		}
629		sc = pppoe_find_softc_by_hunique(ac_cookie,
630						 ac_cookie_len,
631						 m->m_pkthdr.rcvif);
632		if (sc == NULL) {
633			/* be quiet if there is not a single pppoe instance */
634			if (!LIST_EMPTY(&pppoe_softc_list))
635				printf("pppoe: received PADR but could not find request for it\n");
636			goto done;
637		}
638		if (sc->sc_state != PPPOE_STATE_PADO_SENT) {
639			printf("%s: received unexpected PADR\n",
640			    sc->sc_sppp.pp_if.if_xname);
641			goto done;
642		}
643		if (hunique) {
644			if (sc->sc_hunique)
645				free(sc->sc_hunique, M_DEVBUF);
646			sc->sc_hunique = malloc(hunique_len, M_DEVBUF,
647			    M_DONTWAIT);
648			if (sc->sc_hunique == NULL)
649				goto done;
650			sc->sc_hunique_len = hunique_len;
651			memcpy(sc->sc_hunique, hunique, hunique_len);
652		}
653		pppoe_send_pads(sc);
654		sc->sc_state = PPPOE_STATE_SESSION;
655		sc->sc_sppp.pp_up(&sc->sc_sppp);
656		break;
657#else
658		/* ignore, we are no access concentrator */
659		goto done;
660#endif /* PPPOE_SERVER */
661	case PPPOE_CODE_PADO:
662		if (sc == NULL) {
663			/* be quiet if there is not a single pppoe instance */
664			if (!LIST_EMPTY(&pppoe_softc_list))
665				printf("pppoe: received PADO but could not find request for it\n");
666			goto done;
667		}
668		if (sc->sc_state != PPPOE_STATE_PADI_SENT) {
669			printf("%s: received unexpected PADO\n",
670			    sc->sc_sppp.pp_if.if_xname);
671			goto done;
672		}
673		if (ac_cookie) {
674			if (sc->sc_ac_cookie)
675				free(sc->sc_ac_cookie, M_DEVBUF);
676			sc->sc_ac_cookie = malloc(ac_cookie_len, M_DEVBUF,
677			    M_DONTWAIT);
678			if (sc->sc_ac_cookie == NULL) {
679				printf("%s: FATAL: could not allocate memory "
680				    "for AC cookie\n",
681				    sc->sc_sppp.pp_if.if_xname);
682				goto done;
683			}
684			sc->sc_ac_cookie_len = ac_cookie_len;
685			memcpy(sc->sc_ac_cookie, ac_cookie, ac_cookie_len);
686		}
687		if (relay_sid) {
688			if (sc->sc_relay_sid)
689				free(sc->sc_relay_sid, M_DEVBUF);
690			sc->sc_relay_sid = malloc(relay_sid_len, M_DEVBUF,
691			    M_DONTWAIT);
692			if (sc->sc_relay_sid == NULL) {
693				printf("%s: FATAL: could not allocate memory "
694				    "for relay SID\n",
695				    sc->sc_sppp.pp_if.if_xname);
696				goto done;
697			}
698			sc->sc_relay_sid_len = relay_sid_len;
699			memcpy(sc->sc_relay_sid, relay_sid, relay_sid_len);
700		}
701		memcpy(&sc->sc_dest, eh->ether_shost, sizeof sc->sc_dest);
702		callout_stop(&sc->sc_timeout);
703		sc->sc_padr_retried = 0;
704		sc->sc_state = PPPOE_STATE_PADR_SENT;
705		if ((err = pppoe_send_padr(sc)) != 0) {
706			if (sc->sc_sppp.pp_if.if_flags & IFF_DEBUG)
707				printf("%s: failed to send PADR, "
708				    "error=%d\n", sc->sc_sppp.pp_if.if_xname,
709				    err);
710		}
711		callout_reset(&sc->sc_timeout,
712		    PPPOE_DISC_TIMEOUT * (1 + sc->sc_padr_retried),
713		    pppoe_timeout, sc);
714		break;
715	case PPPOE_CODE_PADS:
716		if (sc == NULL)
717			goto done;
718		sc->sc_session = session;
719		callout_stop(&sc->sc_timeout);
720		if (sc->sc_sppp.pp_if.if_flags & IFF_DEBUG)
721			printf("%s: session 0x%x connected\n",
722			    sc->sc_sppp.pp_if.if_xname, session);
723		sc->sc_state = PPPOE_STATE_SESSION;
724		sc->sc_sppp.pp_up(&sc->sc_sppp);	/* notify upper layers */
725		break;
726	case PPPOE_CODE_PADT:
727		if (sc == NULL)
728			goto done;
729		pppoe_clear_softc(sc, "received PADT");
730		break;
731	default:
732		printf("%s: unknown code (0x%04x) session = 0x%04x\n",
733		    sc? sc->sc_sppp.pp_if.if_xname : "pppoe",
734		    ph->code, session);
735		break;
736	}
737
738done:
739	if (m)
740		m_freem(m);
741	return;
742}
743
744static void
745pppoe_disc_input(struct mbuf *m)
746{
747
748	/* avoid error messages if there is not a single pppoe instance */
749	if (!LIST_EMPTY(&pppoe_softc_list)) {
750		KASSERT(m->m_flags & M_PKTHDR);
751		pppoe_dispatch_disc_pkt(m, 0);
752	} else
753		m_freem(m);
754}
755
756static void
757pppoe_data_input(struct mbuf *m)
758{
759	uint16_t session, plen;
760	struct pppoe_softc *sc;
761	struct pppoehdr *ph;
762#ifdef PPPOE_TERM_UNKNOWN_SESSIONS
763	uint8_t shost[ETHER_ADDR_LEN];
764#endif
765
766	KASSERT(m->m_flags & M_PKTHDR);
767
768#ifdef PPPOE_TERM_UNKNOWN_SESSIONS
769	memcpy(shost, mtod(m, struct ether_header*)->ether_shost, ETHER_ADDR_LEN);
770#endif
771	m_adj(m, sizeof(struct ether_header));
772	if (m->m_pkthdr.len <= PPPOE_HEADERLEN) {
773		printf("pppoe (data): dropping too short packet: %d bytes\n",
774		    m->m_pkthdr.len);
775		goto drop;
776	}
777
778	if (m->m_len < sizeof(*ph)) {
779		m = m_pullup(m, sizeof(*ph));
780		if (!m) {
781			printf("pppoe: could not get PPPoE header\n");
782			return;
783		}
784	}
785	ph = mtod(m, struct pppoehdr *);
786
787	if (ph->vertype != PPPOE_VERTYPE) {
788		printf("pppoe (data): unknown version/type packet: 0x%x\n",
789		    ph->vertype);
790		goto drop;
791	}
792	if (ph->code != 0)
793		goto drop;
794
795	session = ntohs(ph->session);
796	sc = pppoe_find_softc_by_session(session, m->m_pkthdr.rcvif);
797	if (sc == NULL) {
798#ifdef PPPOE_TERM_UNKNOWN_SESSIONS
799		printf("pppoe: input for unknown session 0x%x, sending PADT\n",
800		    session);
801		pppoe_send_padt(m->m_pkthdr.rcvif, session, shost);
802#endif
803		goto drop;
804	}
805
806	plen = ntohs(ph->plen);
807
808	if(sc->sc_sppp.pp_if.if_bpf)
809		bpf_ops->bpf_mtap(sc->sc_sppp.pp_if.if_bpf, m);
810
811	m_adj(m, PPPOE_HEADERLEN);
812
813#ifdef PPPOE_DEBUG
814	{
815		struct mbuf *p;
816
817		printf("%s: pkthdr.len=%d, pppoe.len=%d",
818			sc->sc_sppp.pp_if.if_xname,
819			m->m_pkthdr.len, plen);
820		p = m;
821		while (p) {
822			printf(" l=%d", p->m_len);
823			p = p->m_next;
824		}
825		printf("\n");
826	}
827#endif
828
829	if (m->m_pkthdr.len < plen)
830		goto drop;
831
832	/* fix incoming interface pointer (not the raw ethernet interface anymore) */
833	m->m_pkthdr.rcvif = &sc->sc_sppp.pp_if;
834
835	/* pass packet up and account for it */
836	sc->sc_sppp.pp_if.if_ipackets++;
837	sppp_input(&sc->sc_sppp.pp_if, m);
838	return;
839
840drop:
841	m_freem(m);
842}
843
844static int
845pppoe_output(struct pppoe_softc *sc, struct mbuf *m)
846{
847	struct sockaddr dst;
848	struct ether_header *eh;
849	uint16_t etype;
850
851	if (sc->sc_eth_if == NULL) {
852		m_freem(m);
853		return EIO;
854	}
855
856	memset(&dst, 0, sizeof dst);
857	dst.sa_family = AF_UNSPEC;
858	eh = (struct ether_header*)&dst.sa_data;
859	etype = sc->sc_state == PPPOE_STATE_SESSION ? ETHERTYPE_PPPOE : ETHERTYPE_PPPOEDISC;
860	eh->ether_type = htons(etype);
861	memcpy(&eh->ether_dhost, &sc->sc_dest, sizeof sc->sc_dest);
862
863#ifdef PPPOE_DEBUG
864	printf("%s (%x) state=%d, session=0x%x output -> %s, len=%d\n",
865	    sc->sc_sppp.pp_if.if_xname, etype,
866	    sc->sc_state, sc->sc_session,
867	    ether_sprintf((const unsigned char *)&sc->sc_dest), m->m_pkthdr.len);
868#endif
869
870	m->m_flags &= ~(M_BCAST|M_MCAST);
871	sc->sc_sppp.pp_if.if_opackets++;
872	return sc->sc_eth_if->if_output(sc->sc_eth_if, m, &dst, NULL);
873}
874
875static int
876pppoe_ioctl(struct ifnet *ifp, unsigned long cmd, void *data)
877{
878	struct lwp *l = curlwp;	/* XXX */
879	struct pppoe_softc *sc = (struct pppoe_softc*)ifp;
880	struct ifreq *ifr = data;
881	int error = 0;
882
883	switch (cmd) {
884	case PPPOESETPARMS:
885	{
886		struct pppoediscparms *parms = (struct pppoediscparms*)data;
887		if (kauth_authorize_network(l->l_cred, KAUTH_NETWORK_INTERFACE,
888		    KAUTH_REQ_NETWORK_INTERFACE_SETPRIV, ifp, (void *)cmd,
889		    NULL) != 0)
890			return (EPERM);
891		if (parms->eth_ifname[0] != 0) {
892			struct ifnet	*eth_if;
893
894			eth_if = ifunit(parms->eth_ifname);
895			if (eth_if == NULL || eth_if->if_dlt != DLT_EN10MB) {
896				sc->sc_eth_if = NULL;
897				return ENXIO;
898			}
899
900			if (sc->sc_sppp.pp_if.if_mtu >
901			    eth_if->if_mtu - PPPOE_OVERHEAD) {
902				sc->sc_sppp.pp_if.if_mtu = eth_if->if_mtu -
903				    PPPOE_OVERHEAD;
904			}
905			sc->sc_eth_if = eth_if;
906		}
907		if (parms->ac_name != NULL) {
908			size_t s;
909			char *b = malloc(parms->ac_name_len + 1, M_DEVBUF,
910			    M_WAITOK);
911			if (b == NULL)
912				return ENOMEM;
913			error = copyinstr(parms->ac_name, b,
914			    parms->ac_name_len+1, &s);
915			if (error != 0) {
916				free(b, M_DEVBUF);
917				return error;
918			}
919			if (s != parms->ac_name_len+1) {
920				free(b, M_DEVBUF);
921				return EINVAL;
922			}
923			if (sc->sc_concentrator_name)
924				free(sc->sc_concentrator_name, M_DEVBUF);
925			sc->sc_concentrator_name = b;
926		}
927		if (parms->service_name != NULL) {
928			size_t s;
929			char *b = malloc(parms->service_name_len + 1, M_DEVBUF,
930			    M_WAITOK);
931			if (b == NULL)
932				return ENOMEM;
933			error = copyinstr(parms->service_name, b,
934			    parms->service_name_len+1, &s);
935			if (error != 0) {
936				free(b, M_DEVBUF);
937				return error;
938			}
939			if (s != parms->service_name_len+1) {
940				free(b, M_DEVBUF);
941				return EINVAL;
942			}
943			if (sc->sc_service_name)
944				free(sc->sc_service_name, M_DEVBUF);
945			sc->sc_service_name = b;
946		}
947		return 0;
948	}
949	break;
950	case PPPOEGETPARMS:
951	{
952		struct pppoediscparms *parms = (struct pppoediscparms*)data;
953		memset(parms, 0, sizeof *parms);
954		if (sc->sc_eth_if)
955			strncpy(parms->ifname, sc->sc_eth_if->if_xname, IFNAMSIZ);
956		return 0;
957	}
958	break;
959	case PPPOEGETSESSION:
960	{
961		struct pppoeconnectionstate *state = (struct pppoeconnectionstate*)data;
962		state->state = sc->sc_state;
963		state->session_id = sc->sc_session;
964		state->padi_retry_no = sc->sc_padi_retried;
965		state->padr_retry_no = sc->sc_padr_retried;
966		return 0;
967	}
968	break;
969	case SIOCSIFFLAGS:
970		/*
971		 * Prevent running re-establishment timers overriding
972		 * administrators choice.
973		 */
974		if ((ifr->ifr_flags & IFF_UP) == 0
975		     && sc->sc_state >= PPPOE_STATE_PADI_SENT
976		     && sc->sc_state < PPPOE_STATE_SESSION) {
977			callout_stop(&sc->sc_timeout);
978			sc->sc_state = PPPOE_STATE_INITIAL;
979			sc->sc_padi_retried = 0;
980			sc->sc_padr_retried = 0;
981			memcpy(&sc->sc_dest, etherbroadcastaddr,
982			    sizeof(sc->sc_dest));
983		}
984		return sppp_ioctl(ifp, cmd, data);
985	case SIOCSIFMTU:
986		if (ifr->ifr_mtu > (sc->sc_eth_if == NULL ?
987		    PPPOE_MAXMTU : (sc->sc_eth_if->if_mtu - PPPOE_OVERHEAD))) {
988			return EINVAL;
989		}
990		/*FALLTHROUGH*/
991	default:
992		return sppp_ioctl(ifp, cmd, data);
993	}
994	return 0;
995}
996
997/*
998 * Allocate a mbuf/cluster with space to store the given data length
999 * of payload, leaving space for prepending an ethernet header
1000 * in front.
1001 */
1002static struct mbuf *
1003pppoe_get_mbuf(size_t len)
1004{
1005	struct mbuf *m;
1006
1007	MGETHDR(m, M_DONTWAIT, MT_DATA);
1008	if (m == NULL)
1009		return NULL;
1010	if (len + sizeof(struct ether_header) > MHLEN) {
1011		MCLGET(m, M_DONTWAIT);
1012		if ((m->m_flags & M_EXT) == 0) {
1013			struct mbuf *n;
1014			MFREE(m, n);
1015			return 0;
1016		}
1017	}
1018	m->m_data += sizeof(struct ether_header);
1019	m->m_len = len;
1020	m->m_pkthdr.len = len;
1021	m->m_pkthdr.rcvif = NULL;
1022
1023	return m;
1024}
1025
1026static int
1027pppoe_send_padi(struct pppoe_softc *sc)
1028{
1029	struct mbuf *m0;
1030	int len, l1 = 0, l2 = 0; /* XXX: gcc */
1031	uint8_t *p;
1032
1033	if (sc->sc_state >PPPOE_STATE_PADI_SENT)
1034		panic("pppoe_send_padi in state %d", sc->sc_state);
1035
1036	/* calculate length of frame (excluding ethernet header + pppoe header) */
1037	len = 2 + 2 + 2 + 2 + sizeof sc;	/* service name tag is required, host unique is send too */
1038	if (sc->sc_service_name != NULL) {
1039		l1 = strlen(sc->sc_service_name);
1040		len += l1;
1041	}
1042	if (sc->sc_concentrator_name != NULL) {
1043		l2 = strlen(sc->sc_concentrator_name);
1044		len += 2 + 2 + l2;
1045	}
1046
1047	/* allocate a buffer */
1048	m0 = pppoe_get_mbuf(len + PPPOE_HEADERLEN);	/* header len + payload len */
1049	if (!m0)
1050		return ENOBUFS;
1051
1052	/* fill in pkt */
1053	p = mtod(m0, uint8_t *);
1054	PPPOE_ADD_HEADER(p, PPPOE_CODE_PADI, 0, len);
1055	PPPOE_ADD_16(p, PPPOE_TAG_SNAME);
1056	if (sc->sc_service_name != NULL) {
1057		PPPOE_ADD_16(p, l1);
1058		memcpy(p, sc->sc_service_name, l1);
1059		p += l1;
1060	} else {
1061		PPPOE_ADD_16(p, 0);
1062	}
1063	if (sc->sc_concentrator_name != NULL) {
1064		PPPOE_ADD_16(p, PPPOE_TAG_ACNAME);
1065		PPPOE_ADD_16(p, l2);
1066		memcpy(p, sc->sc_concentrator_name, l2);
1067		p += l2;
1068	}
1069	PPPOE_ADD_16(p, PPPOE_TAG_HUNIQUE);
1070	PPPOE_ADD_16(p, sizeof(sc));
1071	memcpy(p, &sc, sizeof sc);
1072
1073#ifdef PPPOE_DEBUG
1074	p += sizeof sc;
1075	if (p - mtod(m0, uint8_t *) != len + PPPOE_HEADERLEN)
1076		panic("pppoe_send_padi: garbled output len, should be %ld, is %ld",
1077		    (long)(len + PPPOE_HEADERLEN), (long)(p - mtod(m0, uint8_t *)));
1078#endif
1079
1080	/* send pkt */
1081	return pppoe_output(sc, m0);
1082}
1083
1084static void
1085pppoe_timeout(void *arg)
1086{
1087	int x, retry_wait, err;
1088	struct pppoe_softc *sc = (struct pppoe_softc*)arg;
1089
1090#ifdef PPPOE_DEBUG
1091	printf("%s: timeout\n", sc->sc_sppp.pp_if.if_xname);
1092#endif
1093
1094	switch (sc->sc_state) {
1095	case PPPOE_STATE_INITIAL:
1096		/* delayed connect from pppoe_tls() */
1097		pppoe_connect(sc);
1098		break;
1099	case PPPOE_STATE_PADI_SENT:
1100		/*
1101		 * We have two basic ways of retrying:
1102		 *  - Quick retry mode: try a few times in short sequence
1103		 *  - Slow retry mode: we already had a connection successfully
1104		 *    established and will try infinitely (without user
1105		 *    intervention)
1106		 * We only enter slow retry mode if IFF_LINK1 (aka autodial)
1107		 * is not set.
1108		 */
1109
1110		/* initialize for quick retry mode */
1111		retry_wait = PPPOE_DISC_TIMEOUT * (1 + sc->sc_padi_retried);
1112
1113		x = splnet();
1114		sc->sc_padi_retried++;
1115		if (sc->sc_padi_retried >= PPPOE_DISC_MAXPADI) {
1116			if ((sc->sc_sppp.pp_if.if_flags & IFF_LINK1) == 0) {
1117				/* slow retry mode */
1118				retry_wait = PPPOE_SLOW_RETRY;
1119			} else {
1120				pppoe_abort_connect(sc);
1121				splx(x);
1122				return;
1123			}
1124		}
1125		if ((err = pppoe_send_padi(sc)) != 0) {
1126			sc->sc_padi_retried--;
1127			if (sc->sc_sppp.pp_if.if_flags & IFF_DEBUG)
1128				printf("%s: failed to transmit PADI, "
1129				    "error=%d\n",
1130				    sc->sc_sppp.pp_if.if_xname, err);
1131		}
1132		callout_reset(&sc->sc_timeout, retry_wait,
1133		    pppoe_timeout, sc);
1134		splx(x);
1135		break;
1136
1137	case PPPOE_STATE_PADR_SENT:
1138		x = splnet();
1139		sc->sc_padr_retried++;
1140		if (sc->sc_padr_retried >= PPPOE_DISC_MAXPADR) {
1141			memcpy(&sc->sc_dest, etherbroadcastaddr,
1142			    sizeof(sc->sc_dest));
1143			sc->sc_state = PPPOE_STATE_PADI_SENT;
1144			sc->sc_padr_retried = 0;
1145			if ((err = pppoe_send_padi(sc)) != 0) {
1146				if (sc->sc_sppp.pp_if.if_flags & IFF_DEBUG)
1147					printf("%s: failed to send PADI"
1148					    ", error=%d\n",
1149					    sc->sc_sppp.pp_if.if_xname,
1150					    err);
1151			}
1152			callout_reset(&sc->sc_timeout,
1153			    PPPOE_DISC_TIMEOUT * (1 + sc->sc_padi_retried),
1154			    pppoe_timeout, sc);
1155			splx(x);
1156			return;
1157		}
1158		if ((err = pppoe_send_padr(sc)) != 0) {
1159			sc->sc_padr_retried--;
1160			if (sc->sc_sppp.pp_if.if_flags & IFF_DEBUG)
1161				printf("%s: failed to send PADR, "
1162				    "error=%d\n", sc->sc_sppp.pp_if.if_xname,
1163				    err);
1164		}
1165		callout_reset(&sc->sc_timeout,
1166		    PPPOE_DISC_TIMEOUT * (1 + sc->sc_padr_retried),
1167		    pppoe_timeout, sc);
1168		splx(x);
1169		break;
1170	case PPPOE_STATE_CLOSING:
1171		pppoe_disconnect(sc);
1172		break;
1173	default:
1174		return;	/* all done, work in peace */
1175	}
1176}
1177
1178/* Start a connection (i.e. initiate discovery phase) */
1179static int
1180pppoe_connect(struct pppoe_softc *sc)
1181{
1182	int x, err;
1183
1184	if (sc->sc_state != PPPOE_STATE_INITIAL)
1185		return EBUSY;
1186
1187#ifdef PPPOE_SERVER
1188	/* wait PADI if IFF_PASSIVE */
1189	if ((sc->sc_sppp.pp_if.if_flags & IFF_PASSIVE))
1190		return 0;
1191#endif
1192	x = splnet();
1193	/* save state, in case we fail to send PADI */
1194	sc->sc_state = PPPOE_STATE_PADI_SENT;
1195	sc->sc_padr_retried = 0;
1196	err = pppoe_send_padi(sc);
1197	if (err != 0 && sc->sc_sppp.pp_if.if_flags & IFF_DEBUG)
1198		printf("%s: failed to send PADI, error=%d\n",
1199		    sc->sc_sppp.pp_if.if_xname, err);
1200	callout_reset(&sc->sc_timeout, PPPOE_DISC_TIMEOUT, pppoe_timeout, sc);
1201	splx(x);
1202	return err;
1203}
1204
1205/* disconnect */
1206static int
1207pppoe_disconnect(struct pppoe_softc *sc)
1208{
1209	int err, x;
1210
1211	x = splnet();
1212
1213	if (sc->sc_state < PPPOE_STATE_SESSION)
1214		err = EBUSY;
1215	else {
1216		if (sc->sc_sppp.pp_if.if_flags & IFF_DEBUG)
1217			printf("%s: disconnecting\n",
1218			    sc->sc_sppp.pp_if.if_xname);
1219		err = pppoe_send_padt(sc->sc_eth_if, sc->sc_session, (const uint8_t *)&sc->sc_dest);
1220	}
1221
1222	/* cleanup softc */
1223	sc->sc_state = PPPOE_STATE_INITIAL;
1224	memcpy(&sc->sc_dest, etherbroadcastaddr, sizeof(sc->sc_dest));
1225	if (sc->sc_ac_cookie) {
1226		free(sc->sc_ac_cookie, M_DEVBUF);
1227		sc->sc_ac_cookie = NULL;
1228	}
1229	sc->sc_ac_cookie_len = 0;
1230	if (sc->sc_relay_sid) {
1231		free(sc->sc_relay_sid, M_DEVBUF);
1232		sc->sc_relay_sid = NULL;
1233	}
1234	sc->sc_relay_sid_len = 0;
1235#ifdef PPPOE_SERVER
1236	if (sc->sc_hunique) {
1237		free(sc->sc_hunique, M_DEVBUF);
1238		sc->sc_hunique = NULL;
1239	}
1240	sc->sc_hunique_len = 0;
1241#endif
1242	sc->sc_session = 0;
1243
1244	/* notify upper layer */
1245	sc->sc_sppp.pp_down(&sc->sc_sppp);
1246
1247	splx(x);
1248
1249	return err;
1250}
1251
1252/* Connection attempt aborted */
1253static void
1254pppoe_abort_connect(struct pppoe_softc *sc)
1255{
1256	printf("%s: could not establish connection\n",
1257		sc->sc_sppp.pp_if.if_xname);
1258	sc->sc_state = PPPOE_STATE_CLOSING;
1259
1260	/* notify upper layer */
1261	sc->sc_sppp.pp_down(&sc->sc_sppp);
1262
1263	/* clear connection state */
1264	memcpy(&sc->sc_dest, etherbroadcastaddr, sizeof(sc->sc_dest));
1265	sc->sc_state = PPPOE_STATE_INITIAL;
1266}
1267
1268/* Send a PADR packet */
1269static int
1270pppoe_send_padr(struct pppoe_softc *sc)
1271{
1272	struct mbuf *m0;
1273	uint8_t *p;
1274	size_t len, l1 = 0; /* XXX: gcc */
1275
1276	if (sc->sc_state != PPPOE_STATE_PADR_SENT)
1277		return EIO;
1278
1279	len = 2 + 2 + 2 + 2 + sizeof(sc);		/* service name, host unique */
1280	if (sc->sc_service_name != NULL) {		/* service name tag maybe empty */
1281		l1 = strlen(sc->sc_service_name);
1282		len += l1;
1283	}
1284	if (sc->sc_ac_cookie_len > 0)
1285		len += 2 + 2 + sc->sc_ac_cookie_len;	/* AC cookie */
1286	if (sc->sc_relay_sid_len > 0)
1287		len += 2 + 2 + sc->sc_relay_sid_len;	/* Relay SID */
1288	m0 = pppoe_get_mbuf(len + PPPOE_HEADERLEN);
1289	if (!m0)
1290		return ENOBUFS;
1291	p = mtod(m0, uint8_t *);
1292	PPPOE_ADD_HEADER(p, PPPOE_CODE_PADR, 0, len);
1293	PPPOE_ADD_16(p, PPPOE_TAG_SNAME);
1294	if (sc->sc_service_name != NULL) {
1295		PPPOE_ADD_16(p, l1);
1296		memcpy(p, sc->sc_service_name, l1);
1297		p += l1;
1298	} else {
1299		PPPOE_ADD_16(p, 0);
1300	}
1301	if (sc->sc_ac_cookie_len > 0) {
1302		PPPOE_ADD_16(p, PPPOE_TAG_ACCOOKIE);
1303		PPPOE_ADD_16(p, sc->sc_ac_cookie_len);
1304		memcpy(p, sc->sc_ac_cookie, sc->sc_ac_cookie_len);
1305		p += sc->sc_ac_cookie_len;
1306	}
1307	if (sc->sc_relay_sid_len > 0) {
1308		PPPOE_ADD_16(p, PPPOE_TAG_RELAYSID);
1309		PPPOE_ADD_16(p, sc->sc_relay_sid_len);
1310		memcpy(p, sc->sc_relay_sid, sc->sc_relay_sid_len);
1311		p += sc->sc_relay_sid_len;
1312	}
1313	PPPOE_ADD_16(p, PPPOE_TAG_HUNIQUE);
1314	PPPOE_ADD_16(p, sizeof(sc));
1315	memcpy(p, &sc, sizeof sc);
1316
1317#ifdef PPPOE_DEBUG
1318	p += sizeof sc;
1319	if (p - mtod(m0, uint8_t *) != len + PPPOE_HEADERLEN)
1320		panic("pppoe_send_padr: garbled output len, should be %ld, is %ld",
1321			(long)(len + PPPOE_HEADERLEN), (long)(p - mtod(m0, uint8_t *)));
1322#endif
1323
1324	return pppoe_output(sc, m0);
1325}
1326
1327/* send a PADT packet */
1328static int
1329pppoe_send_padt(struct ifnet *outgoing_if, u_int session, const uint8_t *dest)
1330{
1331	struct ether_header *eh;
1332	struct sockaddr dst;
1333	struct mbuf *m0;
1334	uint8_t *p;
1335
1336	m0 = pppoe_get_mbuf(PPPOE_HEADERLEN);
1337	if (!m0)
1338		return EIO;
1339	p = mtod(m0, uint8_t *);
1340	PPPOE_ADD_HEADER(p, PPPOE_CODE_PADT, session, 0);
1341
1342	memset(&dst, 0, sizeof dst);
1343	dst.sa_family = AF_UNSPEC;
1344	eh = (struct ether_header*)&dst.sa_data;
1345	eh->ether_type = htons(ETHERTYPE_PPPOEDISC);
1346	memcpy(&eh->ether_dhost, dest, ETHER_ADDR_LEN);
1347
1348	m0->m_flags &= ~(M_BCAST|M_MCAST);
1349	return outgoing_if->if_output(outgoing_if, m0, &dst, NULL);
1350}
1351
1352#ifdef PPPOE_SERVER
1353static int
1354pppoe_send_pado(struct pppoe_softc *sc)
1355{
1356	struct mbuf *m0;
1357	uint8_t *p;
1358	size_t len;
1359
1360	if (sc->sc_state != PPPOE_STATE_PADO_SENT)
1361		return EIO;
1362
1363	/* calc length */
1364	len = 0;
1365	/* include ac_cookie */
1366	len += 2 + 2 + sizeof(sc);
1367	/* include hunique */
1368	len += 2 + 2 + sc->sc_hunique_len;
1369	m0 = pppoe_get_mbuf(len + PPPOE_HEADERLEN);
1370	if (!m0)
1371		return EIO;
1372	p = mtod(m0, uint8_t *);
1373	PPPOE_ADD_HEADER(p, PPPOE_CODE_PADO, 0, len);
1374	PPPOE_ADD_16(p, PPPOE_TAG_ACCOOKIE);
1375	PPPOE_ADD_16(p, sizeof(sc));
1376	memcpy(p, &sc, sizeof(sc));
1377	p += sizeof(sc);
1378	PPPOE_ADD_16(p, PPPOE_TAG_HUNIQUE);
1379	PPPOE_ADD_16(p, sc->sc_hunique_len);
1380	memcpy(p, sc->sc_hunique, sc->sc_hunique_len);
1381	return pppoe_output(sc, m0);
1382}
1383
1384static int
1385pppoe_send_pads(struct pppoe_softc *sc)
1386{
1387	struct bintime bt;
1388	struct mbuf *m0;
1389	uint8_t *p;
1390	size_t len, l1 = 0;	/* XXX: gcc */
1391
1392	if (sc->sc_state != PPPOE_STATE_PADO_SENT)
1393		return EIO;
1394
1395	getbinuptime(&bt);
1396	sc->sc_session = bt.sec % 0xff + 1;
1397	/* calc length */
1398	len = 0;
1399	/* include hunique */
1400	len += 2 + 2 + 2 + 2 + sc->sc_hunique_len;	/* service name, host unique*/
1401	if (sc->sc_service_name != NULL) {		/* service name tag maybe empty */
1402		l1 = strlen(sc->sc_service_name);
1403		len += l1;
1404	}
1405	m0 = pppoe_get_mbuf(len + PPPOE_HEADERLEN);
1406	if (!m0)
1407		return ENOBUFS;
1408	p = mtod(m0, uint8_t *);
1409	PPPOE_ADD_HEADER(p, PPPOE_CODE_PADS, sc->sc_session, len);
1410	PPPOE_ADD_16(p, PPPOE_TAG_SNAME);
1411	if (sc->sc_service_name != NULL) {
1412		PPPOE_ADD_16(p, l1);
1413		memcpy(p, sc->sc_service_name, l1);
1414		p += l1;
1415	} else {
1416		PPPOE_ADD_16(p, 0);
1417	}
1418	PPPOE_ADD_16(p, PPPOE_TAG_HUNIQUE);
1419	PPPOE_ADD_16(p, sc->sc_hunique_len);
1420	memcpy(p, sc->sc_hunique, sc->sc_hunique_len);
1421	return pppoe_output(sc, m0);
1422}
1423#endif
1424
1425static void
1426pppoe_tls(struct sppp *sp)
1427{
1428	struct pppoe_softc *sc = (void *)sp;
1429	int wtime;
1430
1431	if (sc->sc_state != PPPOE_STATE_INITIAL)
1432		return;
1433
1434	if (sc->sc_sppp.pp_phase == SPPP_PHASE_ESTABLISH &&
1435	    sc->sc_sppp.pp_auth_failures > 0) {
1436		/*
1437		 * Delay trying to reconnect a bit more - the peer
1438		 * might have failed to contact it's radius server.
1439		 */
1440		wtime = PPPOE_RECON_FAST * sc->sc_sppp.pp_auth_failures;
1441		if (wtime > PPPOE_SLOW_RETRY)
1442			wtime = PPPOE_SLOW_RETRY;
1443	} else {
1444		wtime = PPPOE_RECON_IMMEDIATE;
1445	}
1446	callout_reset(&sc->sc_timeout, wtime, pppoe_timeout, sc);
1447}
1448
1449static void
1450pppoe_tlf(struct sppp *sp)
1451{
1452	struct pppoe_softc *sc = (void *)sp;
1453	if (sc->sc_state < PPPOE_STATE_SESSION)
1454		return;
1455	/*
1456	 * Do not call pppoe_disconnect here, the upper layer state
1457	 * machine gets confused by this. We must return from this
1458	 * function and defer disconnecting to the timeout handler.
1459	 */
1460	sc->sc_state = PPPOE_STATE_CLOSING;
1461	callout_reset(&sc->sc_timeout, hz/50, pppoe_timeout, sc);
1462}
1463
1464static void
1465pppoe_start(struct ifnet *ifp)
1466{
1467	struct pppoe_softc *sc = (void *)ifp;
1468	struct mbuf *m;
1469	uint8_t *p;
1470	size_t len;
1471
1472	if (sppp_isempty(ifp))
1473		return;
1474
1475	/* are we ready to process data yet? */
1476	if (sc->sc_state < PPPOE_STATE_SESSION) {
1477		sppp_flush(&sc->sc_sppp.pp_if);
1478		return;
1479	}
1480
1481	while ((m = sppp_dequeue(ifp)) != NULL) {
1482		len = m->m_pkthdr.len;
1483		M_PREPEND(m, PPPOE_HEADERLEN, M_DONTWAIT);
1484		if (m == NULL) {
1485			ifp->if_oerrors++;
1486			continue;
1487		}
1488		p = mtod(m, uint8_t *);
1489		PPPOE_ADD_HEADER(p, 0, sc->sc_session, len);
1490
1491		if(sc->sc_sppp.pp_if.if_bpf)
1492			bpf_ops->bpf_mtap(sc->sc_sppp.pp_if.if_bpf, m);
1493
1494		pppoe_output(sc, m);
1495	}
1496}
1497
1498
1499#ifdef PFIL_HOOKS
1500static int
1501pppoe_ifattach_hook(void *arg, struct mbuf **mp, struct ifnet *ifp,
1502    int dir)
1503{
1504	struct pppoe_softc *sc;
1505	int s;
1506
1507	if (mp != (struct mbuf **)PFIL_IFNET_DETACH)
1508		return 0;
1509
1510	s = splnet();
1511	LIST_FOREACH(sc, &pppoe_softc_list, sc_list) {
1512		if (sc->sc_eth_if != ifp)
1513			continue;
1514		if (sc->sc_sppp.pp_if.if_flags & IFF_UP) {
1515			sc->sc_sppp.pp_if.if_flags &= ~(IFF_UP|IFF_RUNNING);
1516			printf("%s: ethernet interface detached, going down\n",
1517			    sc->sc_sppp.pp_if.if_xname);
1518		}
1519		sc->sc_eth_if = NULL;
1520		pppoe_clear_softc(sc, "ethernet interface detached");
1521	}
1522	splx(s);
1523
1524	return 0;
1525}
1526#endif
1527
1528static void
1529pppoe_clear_softc(struct pppoe_softc *sc, const char *message)
1530{
1531	/* stop timer */
1532	callout_stop(&sc->sc_timeout);
1533	if (sc->sc_sppp.pp_if.if_flags & IFF_DEBUG)
1534		printf("%s: session 0x%x terminated, %s\n",
1535		    sc->sc_sppp.pp_if.if_xname, sc->sc_session, message);
1536
1537	/* fix our state */
1538	sc->sc_state = PPPOE_STATE_INITIAL;
1539
1540	/* signal upper layer */
1541	sc->sc_sppp.pp_down(&sc->sc_sppp);
1542
1543	/* clean up softc */
1544	memcpy(&sc->sc_dest, etherbroadcastaddr, sizeof(sc->sc_dest));
1545	if (sc->sc_ac_cookie) {
1546		free(sc->sc_ac_cookie, M_DEVBUF);
1547		sc->sc_ac_cookie = NULL;
1548	}
1549	if (sc->sc_relay_sid) {
1550		free(sc->sc_relay_sid, M_DEVBUF);
1551		sc->sc_relay_sid = NULL;
1552	}
1553	sc->sc_ac_cookie_len = 0;
1554	sc->sc_session = 0;
1555}
1556