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