From 76307d910b81acb709143b2fd82e1ca724feb24c Mon Sep 17 00:00:00 2001 From: Paul Mackerras Date: Sun, 15 Jun 2008 04:35:50 +0000 Subject: [PATCH] Add pppoe-mac option to rp-pppoe plugin This allows the user to specify the MAC address of the pppoe server that s/he wishes to use. With this option, pppd will ignore PADO packets from any other MAC address. --- pppd/plugins/rp-pppoe/discovery.c | 9 +++++++-- pppd/plugins/rp-pppoe/plugin.c | 21 ++++++++++++++++++++- pppd/plugins/rp-pppoe/pppoe.h | 4 +++- 3 files changed, 30 insertions(+), 4 deletions(-) diff --git a/pppd/plugins/rp-pppoe/discovery.c b/pppd/plugins/rp-pppoe/discovery.c index dc61489..6e25ae7 100644 --- a/pppd/plugins/rp-pppoe/discovery.c +++ b/pppd/plugins/rp-pppoe/discovery.c @@ -9,7 +9,7 @@ ***********************************************************************/ static char const RCSID[] = -"$Id: discovery.c,v 1.5 2008/06/09 08:34:23 paulus Exp $"; +"$Id: discovery.c,v 1.6 2008/06/15 04:35:50 paulus Exp $"; #define _GNU_SOURCE 1 #include "pppoe.h" @@ -274,7 +274,7 @@ sendPADI(PPPoEConnection *conn) *%DESCRIPTION: * Waits for a PADO packet and copies useful information ***********************************************************************/ -static void +void waitForPADO(PPPoEConnection *conn, int timeout) { fd_set readable; @@ -333,6 +333,11 @@ waitForPADO(PPPoEConnection *conn, int timeout) error("Ignoring PADO packet from non-unicast MAC address"); continue; } + if (conn->req_peer + && memcmp(packet.ethHdr.h_source, conn->req_peer_mac, ETH_ALEN) != 0) { + warn("Ignoring PADO packet from wrong MAC address"); + continue; + } if (parsePacket(&packet, parsePADOTags, &pc) < 0) return; if (conn->error) diff --git a/pppd/plugins/rp-pppoe/plugin.c b/pppd/plugins/rp-pppoe/plugin.c index 2968e72..e94494b 100644 --- a/pppd/plugins/rp-pppoe/plugin.c +++ b/pppd/plugins/rp-pppoe/plugin.c @@ -23,7 +23,7 @@ ***********************************************************************/ static char const RCSID[] = -"$Id: plugin.c,v 1.16 2008/06/09 08:34:23 paulus Exp $"; +"$Id: plugin.c,v 1.17 2008/06/15 04:35:50 paulus Exp $"; #define _GNU_SOURCE 1 #include "pppoe.h" @@ -67,6 +67,8 @@ char *pppd_pppoe_service = NULL; static char *acName = NULL; static char *existingSession = NULL; static int printACNames = 0; +static char *pppoe_reqd_mac = NULL; +unsigned char pppoe_reqd_mac_addr[6]; static int PPPoEDevnameHook(char *cmd, char **argv, int doit); static option_t Options[] = { @@ -82,6 +84,8 @@ static option_t Options[] = { "Attach to existing session (sessid:macaddr)" }, { "rp_pppoe_verbose", o_int, &printACNames, "Be verbose about discovered access concentrators"}, + { "pppoe-mac", o_string, &pppoe_reqd_mac, + "Only connect to specified MAC address" }, { NULL } }; int (*OldDevnameHook)(char *cmd, char **argv, int doit) = NULL; @@ -348,6 +352,21 @@ plugin_init(void) void pppoe_check_options(void) { + unsigned int mac[6]; + int i; + + if (pppoe_reqd_mac != NULL) { + if (sscanf(pppoe_reqd_mac, "%x:%x:%x:%x:%x:%x", + &mac[0], &mac[1], &mac[2], &mac[3], + &mac[4], &mac[5]) != 6) { + option_error("cannot parse pppoe-mac option value"); + exit(EXIT_OPTION_ERROR); + } + for (i = 0; i < 6; ++i) + conn->req_peer_mac[i] = mac[i]; + conn->req_peer = 1; + } + lcp_allowoptions[0].neg_accompression = 0; lcp_wantoptions[0].neg_accompression = 0; diff --git a/pppd/plugins/rp-pppoe/pppoe.h b/pppd/plugins/rp-pppoe/pppoe.h index a4cf28a..3dba439 100644 --- a/pppd/plugins/rp-pppoe/pppoe.h +++ b/pppd/plugins/rp-pppoe/pppoe.h @@ -9,7 +9,7 @@ * This program may be distributed according to the terms of the GNU * General Public License, version 2 or (at your option) any later version. * -* $Id: pppoe.h,v 1.3 2008/06/09 08:34:23 paulus Exp $ +* $Id: pppoe.h,v 1.4 2008/06/15 04:35:50 paulus Exp $ * ***********************************************************************/ @@ -217,6 +217,8 @@ typedef struct PPPoEConnectionStruct { int sessionSocket; /* Raw socket for session frames */ unsigned char myEth[ETH_ALEN]; /* My MAC address */ unsigned char peerEth[ETH_ALEN]; /* Peer's MAC address */ + unsigned char req_peer_mac[ETH_ALEN]; /* required peer MAC address */ + unsigned char req_peer; /* require mac addr to match req_peer_mac */ UINT16_t session; /* Session ID */ char *ifName; /* Interface name */ char *serviceName; /* Desired service name, if any */ -- 2.39.2