mirror of
https://github.com/openwrt/openwrt.git
synced 2026-07-21 20:21:54 +04:00
ppp: update to 2.5.3
Update to 2.5.3 and use the official tarball. Changelog: https://github.com/ppp-project/ppp/releases/tag/v2.5.3 Removed upstreamed: - 000-pppd-session-fixed-building-with-gcc-15.patch - 001-pppdump-fixed-building-with-gcc-15.patch - 501-fix-memcpy-fortify.patch - 502-remove_mru.patch Manually rebased: - 500-add-pptp-plugin.patch Add a pending patch to relax the check to avoid breaking existing configurations. Signed-off-by: Qingfang Deng <dqfext@gmail.com> Link: https://github.com/openwrt/openwrt/pull/23540 Signed-off-by: Jonas Jelonek <jelonek.jonas@gmail.com>
This commit is contained in:
committed by
Jonas Jelonek
parent
db533a6235
commit
b25d90b7e4
@@ -9,14 +9,12 @@ include $(TOPDIR)/rules.mk
|
||||
include $(INCLUDE_DIR)/kernel.mk
|
||||
|
||||
PKG_NAME:=ppp
|
||||
PKG_VERSION:=2.5.2
|
||||
PKG_RELEASE:=3
|
||||
PKG_VERSION:=2.5.3
|
||||
PKG_RELEASE:=1
|
||||
|
||||
PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_URL:=https://github.com/ppp-project/ppp
|
||||
PKG_MIRROR_HASH:=381668ce1547afeaf599f08ae37935bfd3d5841747c62bca5a870c11e3e9bedb
|
||||
PKG_SOURCE_DATE:=2024-12-31
|
||||
PKG_SOURCE_VERSION:=9f612dc02c34509f062ed63b60bcc7e937e25178
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz
|
||||
PKG_SOURCE_URL:=https://download.samba.org/pub/ppp
|
||||
PKG_HASH:=ddda28dec8aca99a403ab6070d94ffd2b17d63e9a4c5509158e99e148f572d4f
|
||||
|
||||
PKG_MAINTAINER:=Felix Fietkau <nbd@nbd.name>
|
||||
PKG_LICENSE:=BSD-4-Clause
|
||||
|
||||
-30
@@ -1,30 +0,0 @@
|
||||
From 5edcb01f1d8d521c819d45df1f1bb87697252130 Mon Sep 17 00:00:00 2001
|
||||
From: Khem Raj <raj.khem@gmail.com>
|
||||
Date: Mon, 17 Mar 2025 14:38:26 -0700
|
||||
Subject: [PATCH] pppd/session: Fixed building with GCC 15
|
||||
|
||||
Fixed building with GCC 15 which defaults to C23
|
||||
and find conflicting declration of getspnam() here
|
||||
with the one provided by shadow.h (extern struct spwd *getspnam (const char *__name);)
|
||||
|
||||
Fixes
|
||||
../../ppp-2.5.2/pppd/session.c: In function 'session_start':
|
||||
../../ppp-2.5.2/pppd/session.c:185:18: error: conflicting types for 'getspnam'; have 'struct spwd *(void)'
|
||||
185 | struct spwd *getspnam();
|
||||
| ^~~~~~~~
|
||||
|
||||
Signed-off-by: Khem Raj <raj.khem@gmail.com>
|
||||
---
|
||||
pppd/session.c | 1 -
|
||||
1 file changed, 1 deletion(-)
|
||||
|
||||
--- a/pppd/session.c
|
||||
+++ b/pppd/session.c
|
||||
@@ -182,7 +182,6 @@ session_start(const int flags, const cha
|
||||
char *cbuf;
|
||||
#ifdef HAVE_SHADOW_H
|
||||
struct spwd *spwd;
|
||||
- struct spwd *getspnam();
|
||||
long now = 0;
|
||||
#endif /* #ifdef HAVE_SHADOW_H */
|
||||
#endif /* #ifdef PPP_WITH_PAM */
|
||||
@@ -1,70 +0,0 @@
|
||||
From c6c84c77c16878745be4955f2f5baac1f2280c96 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Jaroslav=20=C5=A0karvada?= <jskarvad@redhat.com>
|
||||
Date: Thu, 27 Feb 2025 11:44:08 +0100
|
||||
Subject: [PATCH] Fixed building with GCC 15
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
GCC 15 defaults to C23 which does not allow K&R declarations.
|
||||
|
||||
Credit Yaakov Selkowitz in:
|
||||
https://src.fedoraproject.org/rpms/ppp/pull-request/12
|
||||
|
||||
Signed-off-by: Jaroslav Škarvada <jskarvad@redhat.com>
|
||||
---
|
||||
pppdump/pppdump.c | 20 +++++++-------------
|
||||
1 file changed, 7 insertions(+), 13 deletions(-)
|
||||
|
||||
--- a/pppdump/pppdump.c
|
||||
+++ b/pppdump/pppdump.c
|
||||
@@ -42,14 +42,12 @@ int tot_sent, tot_rcvd;
|
||||
extern int optind;
|
||||
extern char *optarg;
|
||||
|
||||
-void dumplog();
|
||||
-void dumpppp();
|
||||
-void show_time();
|
||||
+void dumplog(FILE *);
|
||||
+void dumpppp(FILE *);
|
||||
+void show_time(FILE *, int);
|
||||
|
||||
int
|
||||
-main(ac, av)
|
||||
- int ac;
|
||||
- char **av;
|
||||
+main(int ac, char **av)
|
||||
{
|
||||
int i;
|
||||
char *p;
|
||||
@@ -97,8 +95,7 @@ main(ac, av)
|
||||
}
|
||||
|
||||
void
|
||||
-dumplog(f)
|
||||
- FILE *f;
|
||||
+dumplog(FILE *f)
|
||||
{
|
||||
int c, n, k, col;
|
||||
int nb, c2;
|
||||
@@ -241,8 +238,7 @@ struct pkt {
|
||||
unsigned char dbuf[8192];
|
||||
|
||||
void
|
||||
-dumpppp(f)
|
||||
- FILE *f;
|
||||
+dumpppp(FILE *f)
|
||||
{
|
||||
int c, n, k;
|
||||
int nb, nl, dn, proto, rv;
|
||||
@@ -375,9 +371,7 @@ dumpppp(f)
|
||||
}
|
||||
|
||||
void
|
||||
-show_time(f, c)
|
||||
- FILE *f;
|
||||
- int c;
|
||||
+show_time(FILE *f, int c)
|
||||
{
|
||||
time_t t;
|
||||
int n;
|
||||
@@ -137,7 +137,7 @@
|
||||
} else {
|
||||
--- a/pppd/ipcp.c
|
||||
+++ b/pppd/ipcp.c
|
||||
@@ -1915,7 +1915,7 @@ ipcp_up(fsm *f)
|
||||
@@ -1930,7 +1930,7 @@ ipcp_up(fsm *f)
|
||||
proxy_arp_set[f->unit] = 1;
|
||||
|
||||
}
|
||||
@@ -148,7 +148,7 @@
|
||||
} else {
|
||||
--- a/pppd/ipv6cp.c
|
||||
+++ b/pppd/ipv6cp.c
|
||||
@@ -1338,7 +1338,7 @@ ipv6cp_up(fsm *f)
|
||||
@@ -1344,7 +1344,7 @@ ipv6cp_up(fsm *f)
|
||||
if (sif6defaultroute(f->unit, go->ourid, ho->hisid))
|
||||
default_route_set[f->unit] = 1;
|
||||
}
|
||||
@@ -159,7 +159,7 @@
|
||||
} else {
|
||||
--- a/pppd/pppd-private.h
|
||||
+++ b/pppd/pppd-private.h
|
||||
@@ -370,7 +370,7 @@ void demand_conf(void); /* config interf
|
||||
@@ -375,7 +375,7 @@ void demand_conf(void); /* config interf
|
||||
void demand_block(void); /* set all NPs to queue up packets */
|
||||
void demand_unblock(void); /* set all NPs to pass packets */
|
||||
void demand_discard(void); /* set all NPs to discard packets */
|
||||
|
||||
@@ -12,7 +12,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
|
||||
--- a/pppd/main.c
|
||||
+++ b/pppd/main.c
|
||||
@@ -1150,7 +1150,8 @@ get_input(void)
|
||||
@@ -1159,7 +1159,8 @@ get_input(void)
|
||||
}
|
||||
notice("Modem hangup");
|
||||
hungup = 1;
|
||||
|
||||
@@ -23,7 +23,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
#
|
||||
# SunOS provides a version of libpcap that would work, but SunOS has no support for activity filter
|
||||
AM_CONDITIONAL([PPP_WITH_FILTER], [ test "x${with_pcap}" = "xyes" && test "x${build_sunos}" != "xyes" ])
|
||||
@@ -348,6 +351,7 @@ $PACKAGE_NAME version $PACKAGE_VERSION
|
||||
@@ -349,6 +352,7 @@ $PACKAGE_NAME version $PACKAGE_VERSION
|
||||
With libatm..........: ${with_atm:-no}
|
||||
With libpam..........: ${with_pam:-no}
|
||||
With libpcap.........: ${with_pcap:-no}
|
||||
@@ -56,7 +56,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
/*
|
||||
* There have been 3 or 4 different names for this in libpcap CVS, but
|
||||
* this seems to be what they have settled on...
|
||||
@@ -182,6 +183,13 @@ static int setlogfile(char **);
|
||||
@@ -186,6 +187,13 @@ static int setlogfile(char **);
|
||||
static int loadplugin(char **);
|
||||
#endif
|
||||
|
||||
@@ -70,7 +70,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
#ifdef PPP_WITH_FILTER
|
||||
static int setpassfilter(char **);
|
||||
static int setactivefilter(char **);
|
||||
@@ -391,6 +399,14 @@ struct option general_options[] = {
|
||||
@@ -404,6 +412,14 @@ struct option general_options[] = {
|
||||
"set filter for active pkts", OPT_PRIO },
|
||||
#endif
|
||||
|
||||
@@ -85,7 +85,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
{ "maxoctets", o_int, &maxoctets,
|
||||
"Set connection traffic limit",
|
||||
OPT_PRIO | OPT_LLIMIT | OPT_NOINCR | OPT_ZEROINF },
|
||||
@@ -1666,6 +1682,27 @@ callfile(char **argv)
|
||||
@@ -1690,6 +1706,27 @@ callfile(char **argv)
|
||||
return ok;
|
||||
}
|
||||
|
||||
|
||||
@@ -119,7 +119,7 @@ Signed-off-by: George Kashperko <george@znau.edu.ua>
|
||||
&& memcmp(vd.dptr, key.dptr, vd.dsize) == 0;
|
||||
--- a/pppd/sys-linux.c
|
||||
+++ b/pppd/sys-linux.c
|
||||
@@ -980,6 +980,16 @@ void cfg_bundle(int mrru, int mtru, int
|
||||
@@ -1111,6 +1111,16 @@ void cfg_bundle(int mrru, int mtru, int
|
||||
add_fd(ppp_dev_fd);
|
||||
}
|
||||
|
||||
@@ -136,7 +136,7 @@ Signed-off-by: George Kashperko <george@znau.edu.ua>
|
||||
/*
|
||||
* make_new_bundle - create a new PPP unit (i.e. a bundle)
|
||||
* and connect our channel to it. This should only get called
|
||||
@@ -998,6 +1008,8 @@ void make_new_bundle(int mrru, int mtru,
|
||||
@@ -1129,6 +1139,8 @@ void make_new_bundle(int mrru, int mtru,
|
||||
|
||||
/* set the mrru and flags */
|
||||
cfg_bundle(mrru, mtru, rssn, tssn);
|
||||
|
||||
@@ -13,7 +13,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
|
||||
--- a/pppd/sys-linux.c
|
||||
+++ b/pppd/sys-linux.c
|
||||
@@ -2247,6 +2247,9 @@ int sifdefaultroute (int unit, u_int32_t
|
||||
@@ -2374,6 +2374,9 @@ int sifdefaultroute (int unit, u_int32_t
|
||||
memset (&rt, 0, sizeof (rt));
|
||||
SET_SA_FAMILY (rt.rt_dst, AF_INET);
|
||||
|
||||
@@ -23,7 +23,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
rt.rt_dev = ifname;
|
||||
rt.rt_metric = dfl_route_metric + 1; /* +1 for binary compatibility */
|
||||
|
||||
@@ -2255,7 +2258,7 @@ int sifdefaultroute (int unit, u_int32_t
|
||||
@@ -2382,7 +2385,7 @@ int sifdefaultroute (int unit, u_int32_t
|
||||
SIN_ADDR(rt.rt_genmask) = 0L;
|
||||
}
|
||||
|
||||
|
||||
@@ -10,8 +10,8 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
|
||||
--- a/pppd/sys-linux.c
|
||||
+++ b/pppd/sys-linux.c
|
||||
@@ -220,14 +220,10 @@ static fd_set in_fds; /* set of fds tha
|
||||
static int max_in_fd; /* highest fd set in in_fds */
|
||||
@@ -218,14 +218,10 @@ static int chindex; /* channel index (n
|
||||
static unsigned routing_table_id = RT_TABLE_MAIN;
|
||||
|
||||
static int has_proxy_arp = 0;
|
||||
-static int driver_version = 0;
|
||||
@@ -26,7 +26,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
|
||||
static char loop_name[20];
|
||||
static unsigned char inbuf[512]; /* buffer for chars read from loopback */
|
||||
@@ -245,9 +241,8 @@ static int dynaddr_set; /* 1 if ip_dyna
|
||||
@@ -241,9 +237,8 @@ static int dynaddr_set; /* 1 if ip_dyna
|
||||
static int looped; /* 1 if using loop */
|
||||
static int link_mtu; /* mtu for the link (not bundle) */
|
||||
|
||||
@@ -37,7 +37,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
|
||||
#define MAX_IFS 100
|
||||
|
||||
@@ -1966,11 +1961,12 @@ int ccp_fatal_error (int unit)
|
||||
@@ -2067,11 +2062,12 @@ int ccp_fatal_error (int unit)
|
||||
*
|
||||
* path_to_procfs - find the path to the proc file system mount point
|
||||
*/
|
||||
@@ -52,7 +52,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
struct mntent *mntent;
|
||||
FILE *fp;
|
||||
|
||||
@@ -1992,6 +1988,7 @@ static char *path_to_procfs(const char *
|
||||
@@ -2093,6 +2089,7 @@ static char *path_to_procfs(const char *
|
||||
fclose (fp);
|
||||
}
|
||||
}
|
||||
@@ -60,7 +60,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
|
||||
strlcpy(proc_path + proc_path_len, tail,
|
||||
sizeof(proc_path) - proc_path_len);
|
||||
@@ -2883,6 +2880,8 @@ ppp_registered(void)
|
||||
@@ -2874,6 +2871,8 @@ ppp_registered(void)
|
||||
|
||||
int ppp_check_kernel_support(void)
|
||||
{
|
||||
@@ -69,7 +69,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
int s, ok, fd;
|
||||
struct ifreq ifr;
|
||||
int size;
|
||||
@@ -3010,6 +3009,7 @@ int ppp_check_kernel_support(void)
|
||||
@@ -3001,6 +3000,7 @@ int ppp_check_kernel_support(void)
|
||||
}
|
||||
close(s);
|
||||
return ok;
|
||||
@@ -77,7 +77,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
}
|
||||
|
||||
#ifndef HAVE_LOGWTMP
|
||||
@@ -3571,6 +3571,7 @@ get_pty(int *master_fdp, int *slave_fdp,
|
||||
@@ -3562,6 +3562,7 @@ get_pty(int *master_fdp, int *slave_fdp,
|
||||
}
|
||||
#endif /* TIOCGPTN */
|
||||
|
||||
@@ -85,7 +85,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
if (sfd < 0) {
|
||||
/* the old way - scan through the pty name space */
|
||||
for (i = 0; i < 64; ++i) {
|
||||
@@ -3595,6 +3596,7 @@ get_pty(int *master_fdp, int *slave_fdp,
|
||||
@@ -3586,6 +3587,7 @@ get_pty(int *master_fdp, int *slave_fdp,
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -93,7 +93,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
|
||||
if (sfd < 0)
|
||||
return 0;
|
||||
@@ -3710,6 +3712,7 @@ get_host_seed(void)
|
||||
@@ -3701,6 +3703,7 @@ get_host_seed(void)
|
||||
int
|
||||
sys_check_options(void)
|
||||
{
|
||||
@@ -101,7 +101,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
if (demand && driver_is_old) {
|
||||
ppp_option_error("demand dialling is not supported by kernel driver "
|
||||
"version %d.%d.%d", driver_version, driver_modification,
|
||||
@@ -3720,6 +3723,7 @@ sys_check_options(void)
|
||||
@@ -3711,6 +3714,7 @@ sys_check_options(void)
|
||||
warn("Warning: multilink is not supported by the kernel driver");
|
||||
multilink = 0;
|
||||
}
|
||||
@@ -147,7 +147,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
info("PPPoE plugin from pppd %s", PPPD_VERSION);
|
||||
--- a/pppd/plugins/pppol2tp/pppol2tp.c
|
||||
+++ b/pppd/plugins/pppol2tp/pppol2tp.c
|
||||
@@ -501,10 +501,6 @@ static void pppol2tp_cleanup(void)
|
||||
@@ -502,10 +502,6 @@ static void pppol2tp_cleanup(void)
|
||||
void plugin_init(void)
|
||||
{
|
||||
#if defined(__linux__)
|
||||
|
||||
@@ -7,7 +7,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
|
||||
--- a/pppd/main.c
|
||||
+++ b/pppd/main.c
|
||||
@@ -982,14 +982,17 @@ struct protocol_list {
|
||||
@@ -991,14 +991,17 @@ struct protocol_list {
|
||||
const char *name;
|
||||
} protocol_list[] = {
|
||||
{ 0x21, "IP" },
|
||||
@@ -25,7 +25,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
{ 0x33, "Stream Protocol ST-II" },
|
||||
{ 0x35, "Banyan Vines" },
|
||||
{ 0x39, "AppleTalk EDDP" },
|
||||
@@ -1003,8 +1006,11 @@ struct protocol_list {
|
||||
@@ -1012,8 +1015,11 @@ struct protocol_list {
|
||||
{ 0x49, "Serial Data Transport Protocol (PPP-SDTP)" },
|
||||
{ 0x4b, "SNA over 802.2" },
|
||||
{ 0x4d, "SNA" },
|
||||
@@ -37,7 +37,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
{ 0x53, "Encryption" },
|
||||
{ 0x55, "Individual Link Encryption" },
|
||||
{ 0x57, "IPv6" },
|
||||
@@ -1015,12 +1021,15 @@ struct protocol_list {
|
||||
@@ -1024,12 +1030,15 @@ struct protocol_list {
|
||||
{ 0x65, "RTP IPHC Compressed non-TCP" },
|
||||
{ 0x67, "RTP IPHC Compressed UDP 8" },
|
||||
{ 0x69, "RTP IPHC Compressed RTP 8" },
|
||||
@@ -53,7 +53,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
{ 0x0203, "IBM Source Routing BPDU" },
|
||||
{ 0x0205, "DEC LANBridge100 Spanning Tree" },
|
||||
{ 0x0207, "Cisco Discovery Protocol" },
|
||||
@@ -1032,15 +1041,19 @@ struct protocol_list {
|
||||
@@ -1041,15 +1050,19 @@ struct protocol_list {
|
||||
{ 0x0231, "Luxcom" },
|
||||
{ 0x0233, "Sigma Network Systems" },
|
||||
{ 0x0235, "Apple Client Server Protocol" },
|
||||
@@ -73,7 +73,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
{ 0x4001, "Cray Communications Control Protocol" },
|
||||
{ 0x4003, "CDPD Mobile Network Registration Protocol" },
|
||||
{ 0x4005, "Expand accelerator protocol" },
|
||||
@@ -1051,8 +1064,10 @@ struct protocol_list {
|
||||
@@ -1060,8 +1073,10 @@ struct protocol_list {
|
||||
{ 0x4023, "RefTek Protocol" },
|
||||
{ 0x4025, "Fibre Channel" },
|
||||
{ 0x4027, "EMIT Protocols" },
|
||||
@@ -84,7 +84,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
{ 0x8023, "OSI Network Layer Control Protocol" },
|
||||
{ 0x8025, "Xerox NS IDP Control Protocol" },
|
||||
{ 0x8027, "DECnet Phase IV Control Protocol" },
|
||||
@@ -1061,7 +1076,9 @@ struct protocol_list {
|
||||
@@ -1070,7 +1085,9 @@ struct protocol_list {
|
||||
{ 0x8031, "Bridging NCP" },
|
||||
{ 0x8033, "Stream Protocol Control Protocol" },
|
||||
{ 0x8035, "Banyan Vines Control Protocol" },
|
||||
@@ -94,7 +94,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
{ 0x803f, "NETBIOS Framing Control Protocol" },
|
||||
{ 0x8041, "Cisco Systems Control Protocol" },
|
||||
{ 0x8043, "Ascom Timeplex" },
|
||||
@@ -1070,18 +1087,24 @@ struct protocol_list {
|
||||
@@ -1079,18 +1096,24 @@ struct protocol_list {
|
||||
{ 0x8049, "Serial Data Control Protocol (PPP-SDCP)" },
|
||||
{ 0x804b, "SNA over 802.2 Control Protocol" },
|
||||
{ 0x804d, "SNA Control Protocol" },
|
||||
@@ -119,7 +119,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
{ 0x8207, "Cisco Discovery Protocol Control" },
|
||||
{ 0x8209, "Netcs Twin Routing" },
|
||||
{ 0x820b, "STP - Control Protocol" },
|
||||
@@ -1090,24 +1113,29 @@ struct protocol_list {
|
||||
@@ -1099,24 +1122,29 @@ struct protocol_list {
|
||||
{ 0x8281, "MPLSCP" },
|
||||
{ 0x8285, "IEEE p1284.4 standard - Protocol Control" },
|
||||
{ 0x8287, "ETSI TETRA TNP1 Control Protocol" },
|
||||
|
||||
@@ -9,7 +9,7 @@ Signed-off-by: Jo-Philipp Wich <jo@mein.io>
|
||||
|
||||
--- a/pppd/options.c
|
||||
+++ b/pppd/options.c
|
||||
@@ -379,13 +379,14 @@ struct option general_options[] = {
|
||||
@@ -392,13 +392,14 @@ struct option general_options[] = {
|
||||
"Enable multilink operation", OPT_PRIOSUB | OPT_ALIAS | 1 },
|
||||
{ "nomultilink", o_bool, &multilink,
|
||||
"Disable multilink operation", OPT_PRIOSUB | 0 },
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
--- a/configure.ac
|
||||
+++ b/configure.ac
|
||||
@@ -333,6 +333,7 @@ AC_CONFIG_FILES([
|
||||
pppd/plugins/pppoatm/Makefile
|
||||
@@ -334,6 +334,7 @@ AC_CONFIG_FILES([
|
||||
pppd/plugins/pppol2tp/Makefile
|
||||
pppd/plugins/radius/Makefile
|
||||
pppd/plugins/dhcpv6relay/Makefile
|
||||
+ pppd/plugins/pptp/Makefile
|
||||
pppdump/Makefile
|
||||
pppstats/Makefile
|
||||
@@ -14,8 +14,8 @@
|
||||
winbind_la_SOURCES = winbind.c
|
||||
|
||||
if !SUNOS
|
||||
-SUBDIRS = pppoe pppoatm pppol2tp radius
|
||||
+SUBDIRS = pppoe pppoatm pppol2tp radius pptp
|
||||
-SUBDIRS = pppoe pppoatm pppol2tp radius dhcpv6relay
|
||||
+SUBDIRS = pppoe pppoatm pppol2tp radius dhcpv6relay pptp
|
||||
endif
|
||||
--- /dev/null
|
||||
+++ b/pppd/plugins/pptp/Makefile.am
|
||||
|
||||
@@ -1,37 +0,0 @@
|
||||
From f8d994052e3858848ce11318085e04fe7a1cfb28 Mon Sep 17 00:00:00 2001
|
||||
From: LGA1150 <9155358+LGA1150@users.noreply.github.com>
|
||||
Date: Thu, 5 Mar 2026 05:41:30 +0800
|
||||
Subject: [PATCH] pppd: fix memcpy overlap (#579)
|
||||
|
||||
memcpy() with overlapping src and dest buffers is an undefined behavior
|
||||
in C. In the current code, a ConfRej response is generated by copying
|
||||
input data in-place, where the dest address is lower than the src.
|
||||
This happens to work in practice because memcpy() forward-copies data,
|
||||
matching the behavior of memmove() in this case.
|
||||
|
||||
However, if FORTIFY_SOURCE or Address Sanitizer is enabled, memcpy()
|
||||
will detect the overlap at run time and abort the program.
|
||||
|
||||
Replace the memcpy() with memmove() to ensure a well-defined behavior.
|
||||
|
||||
Reported-by: Filippo Carletti <filippo.carletti@gmail.com>
|
||||
Closes: #576
|
||||
|
||||
Signed-off-by: Qingfang Deng <dqfext@gmail.com>
|
||||
---
|
||||
pppd/pppd-private.h | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/pppd/pppd-private.h b/pppd/pppd-private.h
|
||||
index 5f841824..29ea940c 100644
|
||||
--- a/pppd/pppd-private.h
|
||||
+++ b/pppd/pppd-private.h
|
||||
@@ -525,7 +525,7 @@ int parse_dotted_ip(char *, u_int32_t *)
|
||||
#define TIMEOUT(r, f, t) ppp_timeout((r), (f), (t), 0)
|
||||
#define UNTIMEOUT(r, f) ppp_untimeout((r), (f))
|
||||
|
||||
-#define BCOPY(s, d, l) memcpy(d, s, l)
|
||||
+#define BCOPY(s, d, l) memmove(d, s, l)
|
||||
#define BZERO(s, n) memset(s, 0, n)
|
||||
#define BCMP(s1, s2, l) memcmp(s1, s2, l)
|
||||
|
||||
@@ -0,0 +1,749 @@
|
||||
From 71d3d3a6703fce993432151d363f405b51e7b75c Mon Sep 17 00:00:00 2001
|
||||
From: Qingfang Deng <dqfext@gmail.com>
|
||||
Date: Fri, 12 Jun 2026 10:52:39 +0800
|
||||
Subject: [PATCH] pppd: relax and simplify permission check
|
||||
|
||||
The additional check added in v2.5.3 is intended to mitigate symlink
|
||||
attacks, but it checks the permissions of every component of a path and
|
||||
is too strict, breaking existing configurations. Relax and simplify the
|
||||
check by only checking the opened file descriptor of a path, so the path
|
||||
is resolved only once.
|
||||
|
||||
Signed-off-by: Qingfang Deng <dqfext@gmail.com>
|
||||
---
|
||||
configure.ac | 2 +
|
||||
pppd/auth.c | 146 +++++++++++++++++++++++++-------------------
|
||||
pppd/main.c | 46 ++++++++++----
|
||||
pppd/options.c | 56 +++++++++++++----
|
||||
pppd/pppd-private.h | 2 +-
|
||||
pppd/pppd.8 | 10 ---
|
||||
pppd/pppd.h | 2 +-
|
||||
pppd/utils.c | 84 ++++++-------------------
|
||||
8 files changed, 184 insertions(+), 164 deletions(-)
|
||||
|
||||
--- a/configure.ac
|
||||
+++ b/configure.ac
|
||||
@@ -2,6 +2,7 @@ AC_PREREQ([2.69])
|
||||
AC_INIT([ppp],
|
||||
[2.5.3],
|
||||
[https://github.com/ppp-project/ppp])
|
||||
+AC_USE_SYSTEM_EXTENSIONS
|
||||
|
||||
m4_ifdef([AM_SILENT_RULES],[AM_SILENT_RULES([yes])])
|
||||
AC_CONFIG_MACRO_DIR([m4])
|
||||
@@ -93,6 +94,7 @@ AC_CHECK_SIZEOF(unsigned short)
|
||||
|
||||
# Checks for library functions.
|
||||
AC_CHECK_FUNCS([ \
|
||||
+ fexecve \
|
||||
mmap \
|
||||
logwtmp \
|
||||
strerror])
|
||||
--- a/pppd/auth.c
|
||||
+++ b/pppd/auth.c
|
||||
@@ -307,7 +307,7 @@ static int setupapfile (char **);
|
||||
static int privgroup (char **);
|
||||
static int set_noauth_addr (char **);
|
||||
static int set_permitted_number (char **);
|
||||
-static void check_access (FILE *, char *);
|
||||
+static void check_access (int, const char *);
|
||||
static int wordlist_count (struct wordlist *);
|
||||
static void check_maxoctets (void *);
|
||||
|
||||
@@ -532,7 +532,7 @@ setupapfile(char **argv)
|
||||
free(fname);
|
||||
return 0;
|
||||
}
|
||||
- check_access(ufile, fname);
|
||||
+ check_access(fileno(ufile), fname);
|
||||
uafname = fname;
|
||||
|
||||
/* get username */
|
||||
@@ -1543,8 +1543,7 @@ check_passwd(int unit,
|
||||
* Open the file of pap secrets and scan for a suitable secret
|
||||
* for authenticating this user.
|
||||
*/
|
||||
- if (!ppp_check_access(path_upapfile, &filename, 0, 0))
|
||||
- return UPAP_AUTHNAK;
|
||||
+ filename = path_upapfile;
|
||||
addrs = opts = NULL;
|
||||
ret = UPAP_AUTHNAK;
|
||||
f = fopen(filename, "r");
|
||||
@@ -1552,7 +1551,13 @@ check_passwd(int unit,
|
||||
error("Can't open PAP password file %s: %m", filename);
|
||||
|
||||
} else {
|
||||
- check_access(f, filename);
|
||||
+ int fd = fileno(f);
|
||||
+
|
||||
+ if (!ppp_check_access(fd, filename, 0)) {
|
||||
+ fclose(f);
|
||||
+ return UPAP_AUTHNAK;
|
||||
+ }
|
||||
+ check_access(fd, filename);
|
||||
if (scan_authfile(f, user, our_name, secret, &addrs, &opts, filename, 0) < 0) {
|
||||
warn("no PAP secret found for %s", user);
|
||||
} else {
|
||||
@@ -1586,7 +1591,6 @@ check_passwd(int unit,
|
||||
}
|
||||
fclose(f);
|
||||
}
|
||||
- free(filename);
|
||||
|
||||
if (ret == UPAP_AUTHNAK) {
|
||||
if (**msg == 0)
|
||||
@@ -1646,21 +1650,24 @@ null_login(int unit)
|
||||
* Open the file of pap secrets and scan for a suitable secret.
|
||||
*/
|
||||
if (ret <= 0) {
|
||||
- if (!ppp_check_access(path_upapfile, &filename, 0, 0))
|
||||
- return 0;
|
||||
+ int fd;
|
||||
+
|
||||
+ filename = path_upapfile;
|
||||
addrs = NULL;
|
||||
f = fopen(filename, "r");
|
||||
- if (f == NULL) {
|
||||
- free(filename);
|
||||
+ if (f == NULL)
|
||||
+ return 0;
|
||||
+ fd = fileno(f);
|
||||
+ if (!ppp_check_access(fd, filename, 0)) {
|
||||
+ fclose(f);
|
||||
return 0;
|
||||
}
|
||||
- check_access(f, filename);
|
||||
+ check_access(fd, filename);
|
||||
|
||||
i = scan_authfile(f, "", our_name, secret, &addrs, &opts, filename, 0);
|
||||
ret = i >= 0 && secret[0] == 0;
|
||||
BZERO(secret, sizeof(secret));
|
||||
fclose(f);
|
||||
- free(filename);
|
||||
}
|
||||
|
||||
if (ret)
|
||||
@@ -1701,7 +1708,7 @@ get_pap_passwd(char *passwd)
|
||||
f = fopen(filename, "r");
|
||||
if (f == NULL)
|
||||
return 0;
|
||||
- check_access(f, filename);
|
||||
+ check_access(fileno(f), filename);
|
||||
ret = scan_authfile(f, user,
|
||||
(remote_name[0]? remote_name: NULL),
|
||||
secret, NULL, NULL, filename, 0);
|
||||
@@ -1734,18 +1741,18 @@ have_pap_secret(int *lacks_ipp)
|
||||
return ret;
|
||||
}
|
||||
|
||||
- if (!ppp_check_access(path_upapfile, &filename, 0, 0))
|
||||
- return 0;
|
||||
+ filename = path_upapfile;
|
||||
f = fopen(filename, "r");
|
||||
- if (f == NULL) {
|
||||
- free(filename);
|
||||
+ if (f == NULL)
|
||||
return 0;
|
||||
- }
|
||||
|
||||
+ if (!ppp_check_access(fileno(f), filename, 0)) {
|
||||
+ fclose(f);
|
||||
+ return 0;
|
||||
+ }
|
||||
ret = scan_authfile(f, (explicit_remote? remote_name: NULL), our_name,
|
||||
NULL, &addrs, NULL, filename, 0);
|
||||
fclose(f);
|
||||
- free(filename);
|
||||
if (ret >= 0 && !some_ip_ok(addrs)) {
|
||||
if (lacks_ipp != 0)
|
||||
*lacks_ipp = 1;
|
||||
@@ -1780,11 +1787,13 @@ have_chap_secret(char *client, char *ser
|
||||
}
|
||||
}
|
||||
|
||||
- if (!ppp_check_access(path_chapfile, &filename, 0, 0))
|
||||
- return 0;
|
||||
+ filename = path_chapfile;
|
||||
f = fopen(filename, "r");
|
||||
- if (f == NULL) {
|
||||
- free(filename);
|
||||
+ if (f == NULL)
|
||||
+ return 0;
|
||||
+
|
||||
+ if (!ppp_check_access(fileno(f), filename, 0)) {
|
||||
+ fclose(f);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1795,7 +1804,6 @@ have_chap_secret(char *client, char *ser
|
||||
|
||||
ret = scan_authfile(f, client, server, NULL, &addrs, NULL, filename, 0);
|
||||
fclose(f);
|
||||
- free(filename);
|
||||
if (ret >= 0 && need_ip && !some_ip_ok(addrs)) {
|
||||
if (lacks_ipp != 0)
|
||||
*lacks_ipp = 1;
|
||||
@@ -1822,11 +1830,13 @@ have_srp_secret(char *client, char *serv
|
||||
char *filename;
|
||||
struct wordlist *addrs;
|
||||
|
||||
- if (!ppp_check_access(PPP_PATH_SRPFILE, &filename, 0, 0))
|
||||
- return 0;
|
||||
+ filename = PPP_PATH_SRPFILE;
|
||||
f = fopen(filename, "r");
|
||||
- if (f == NULL) {
|
||||
- free(filename);
|
||||
+ if (f == NULL)
|
||||
+ return 0;
|
||||
+
|
||||
+ if (!ppp_check_access(fileno(f), filename, 0)) {
|
||||
+ fclose(f);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1837,7 +1847,6 @@ have_srp_secret(char *client, char *serv
|
||||
|
||||
ret = scan_authfile(f, client, server, NULL, &addrs, NULL, filename, 0);
|
||||
fclose(f);
|
||||
- free(filename);
|
||||
if (ret >= 0 && need_ip && !some_ip_ok(addrs)) {
|
||||
if (lacks_ipp != 0)
|
||||
*lacks_ipp = 1;
|
||||
@@ -1874,22 +1883,27 @@ get_secret(int unit, char *client, char
|
||||
return 0;
|
||||
}
|
||||
} else {
|
||||
- if (!ppp_check_access(path_chapfile, &filename, 0, 0))
|
||||
- return 0;
|
||||
+ int fd;
|
||||
+
|
||||
+ filename = path_chapfile;
|
||||
addrs = NULL;
|
||||
secbuf[0] = 0;
|
||||
|
||||
f = fopen(filename, "r");
|
||||
if (f == NULL) {
|
||||
error("Can't open chap secret file %s: %m", filename);
|
||||
- free(filename);
|
||||
return 0;
|
||||
}
|
||||
- check_access(f, filename);
|
||||
+
|
||||
+ fd = fileno(f);
|
||||
+ if (!ppp_check_access(fd, filename, 0)) {
|
||||
+ fclose(f);
|
||||
+ return 0;
|
||||
+ }
|
||||
+ check_access(fd, filename);
|
||||
|
||||
ret = scan_authfile(f, client, server, secbuf, &addrs, &opts, filename, 0);
|
||||
fclose(f);
|
||||
- free(filename);
|
||||
if (ret < 0)
|
||||
return 0;
|
||||
|
||||
@@ -1931,23 +1945,27 @@ get_srp_secret(int unit, char *client, c
|
||||
if (!am_server && passwd[0] != '\0') {
|
||||
strlcpy(secret, passwd, MAXWORDLEN);
|
||||
} else {
|
||||
- if (!ppp_check_access(PPP_PATH_SRPFILE, &filename, 0, 0))
|
||||
- return 0;
|
||||
- addrs = NULL;
|
||||
+ int fd;
|
||||
|
||||
+ filename = PPP_PATH_SRPFILE;
|
||||
+ addrs = NULL;
|
||||
fp = fopen(filename, "r");
|
||||
if (fp == NULL) {
|
||||
error("Can't open srp secret file %s: %m", filename);
|
||||
- free(filename);
|
||||
return 0;
|
||||
}
|
||||
- check_access(fp, filename);
|
||||
+
|
||||
+ fd = fileno(fp);
|
||||
+ if (!ppp_check_access(fd, filename, 0)) {
|
||||
+ fclose(fp);
|
||||
+ return 0;
|
||||
+ }
|
||||
+ check_access(fd, filename);
|
||||
|
||||
secret[0] = '\0';
|
||||
ret = scan_authfile(fp, client, server, secret, &addrs, &opts,
|
||||
filename, am_server);
|
||||
fclose(fp);
|
||||
- free(filename);
|
||||
if (ret < 0)
|
||||
return 0;
|
||||
|
||||
@@ -2214,11 +2232,11 @@ auth_number(void)
|
||||
* check_access - complain if a secret file has too-liberal permissions.
|
||||
*/
|
||||
static void
|
||||
-check_access(FILE *f, char *filename)
|
||||
+check_access(int fd, const char *filename)
|
||||
{
|
||||
struct stat sbuf;
|
||||
|
||||
- if (fstat(fileno(f), &sbuf) < 0) {
|
||||
+ if (fstat(fd, &sbuf) < 0) {
|
||||
warn("cannot stat secret file %s: %m", filename);
|
||||
} else if ((sbuf.st_mode & (S_IRWXG | S_IRWXO)) != 0) {
|
||||
warn("Warning - secret file %s has world and/or group access",
|
||||
@@ -2326,25 +2344,25 @@ scan_authfile(FILE *f, char *client, cha
|
||||
* Special syntax: @/pathname means read secret from file.
|
||||
*/
|
||||
if (word[0] == '@' && word[1] == '/') {
|
||||
- char *realname;
|
||||
+ int fd;
|
||||
|
||||
strlcpy(atfile, word+1, sizeof(atfile));
|
||||
- if (!ppp_check_access(atfile, &realname, 0, 0))
|
||||
- continue;
|
||||
- if ((sf = fopen(realname, "r")) == NULL) {
|
||||
+ if ((sf = fopen(atfile, "r")) == NULL) {
|
||||
warn("can't open indirect secret file %s", atfile);
|
||||
- free(realname);
|
||||
continue;
|
||||
}
|
||||
- check_access(sf, atfile);
|
||||
+ fd = fileno(sf);
|
||||
+ if (!ppp_check_access(fd, atfile, 0)) {
|
||||
+ fclose(sf);
|
||||
+ continue;
|
||||
+ }
|
||||
+ check_access(fd, atfile);
|
||||
if (!getword(sf, word, &xxx, atfile)) {
|
||||
warn("no secret in indirect secret file %s", atfile);
|
||||
fclose(sf);
|
||||
- free(realname);
|
||||
continue;
|
||||
}
|
||||
fclose(sf);
|
||||
- free(realname);
|
||||
}
|
||||
strlcpy(lsecret, word, sizeof(lsecret));
|
||||
}
|
||||
@@ -2503,14 +2521,15 @@ have_eaptls_secret_server(char *client,
|
||||
char cacertfile[MAXWORDLEN];
|
||||
char pkfile[MAXWORDLEN];
|
||||
|
||||
- if (!ppp_check_access(PPP_PATH_EAPTLSSERVFILE, &filename, 0, 0))
|
||||
- return 0;
|
||||
+ filename = PPP_PATH_EAPTLSSERVFILE;
|
||||
f = fopen(filename, "r");
|
||||
- if (f == NULL) {
|
||||
- free(filename);
|
||||
+ if (f == NULL)
|
||||
return 0;
|
||||
- }
|
||||
|
||||
+ if (!ppp_check_access(fileno(f), filename, 0)) {
|
||||
+ fclose(f);
|
||||
+ return 0;
|
||||
+ }
|
||||
if (client != NULL && client[0] == 0)
|
||||
client = NULL;
|
||||
else if (server != NULL && server[0] == 0)
|
||||
@@ -2522,7 +2541,6 @@ have_eaptls_secret_server(char *client,
|
||||
0);
|
||||
|
||||
fclose(f);
|
||||
- free(filename);
|
||||
|
||||
/*
|
||||
if (ret >= 0 && !eaptls_init_ssl(1, cacertfile, servcertfile,
|
||||
@@ -2782,26 +2800,28 @@ get_eaptls_secret(int unit, char *client
|
||||
}
|
||||
else
|
||||
{
|
||||
+ int fd;
|
||||
+
|
||||
filename = (am_server ? PPP_PATH_EAPTLSSERVFILE : PPP_PATH_EAPTLSCLIFILE);
|
||||
addrs = NULL;
|
||||
|
||||
- if (!ppp_check_access(filename, &filename, 0, 0))
|
||||
- return 0;
|
||||
fp = fopen(filename, "r");
|
||||
- if (fp == NULL)
|
||||
- {
|
||||
+ if (fp == NULL) {
|
||||
error("Can't open eap-tls secret file %s: %m", filename);
|
||||
- free(filename);
|
||||
return 0;
|
||||
}
|
||||
|
||||
- check_access(fp, filename);
|
||||
+ fd = fileno(fp);
|
||||
+ if (!ppp_check_access(fd, filename, 0)) {
|
||||
+ fclose(fp);
|
||||
+ return 0;
|
||||
+ }
|
||||
+ check_access(fd, filename);
|
||||
|
||||
ret = scan_authfile_eaptls(fp, client, server, clicertfile, servcertfile,
|
||||
cacertfile, pkfile, &addrs, &opts, filename, 0);
|
||||
|
||||
fclose(fp);
|
||||
- free(filename);
|
||||
|
||||
if (ret < 0) return 0;
|
||||
}
|
||||
--- a/pppd/main.c
|
||||
+++ b/pppd/main.c
|
||||
@@ -1952,22 +1952,37 @@ update_script_environment(void)
|
||||
pid_t
|
||||
run_program(char *prog, char * const *args, int must_exist, void (*done)(void *), void *arg, int wait)
|
||||
{
|
||||
- int pid, status, ret;
|
||||
- char *rpath;
|
||||
+ int fd, pid, status, ret;
|
||||
|
||||
/*
|
||||
* First check if the file exists and is executable by root,
|
||||
* and couldn't have been modified by a non-root process.
|
||||
*/
|
||||
- if (!ppp_check_access(prog, &rpath, must_exist, 1))
|
||||
+#if defined(O_PATH)
|
||||
+ fd = open(prog, O_PATH);
|
||||
+#elif defined(O_EXEC)
|
||||
+ fd = open(prog, O_EXEC);
|
||||
+#else
|
||||
+ fd = open(prog, O_RDONLY);
|
||||
+#endif
|
||||
+ if (fd < 0) {
|
||||
+ if (errno != ENOENT || must_exist)
|
||||
+ error("Can't access %s: %m", prog);
|
||||
+ return 0;
|
||||
+ }
|
||||
+ if (!ppp_check_access(fd, prog, 1)) {
|
||||
+ close(fd);
|
||||
return 0;
|
||||
+ }
|
||||
|
||||
pid = ppp_safe_fork(fd_devnull, fd_devnull, fd_devnull);
|
||||
if (pid == -1) {
|
||||
error("Failed to create child process for %s: %m", prog);
|
||||
+ close(fd);
|
||||
return -1;
|
||||
}
|
||||
if (pid != 0) {
|
||||
+ close(fd);
|
||||
if (debug)
|
||||
dbglog("Script %s started (pid %d)", prog, pid);
|
||||
record_child(pid, prog, done, arg, 0);
|
||||
@@ -1979,7 +1994,6 @@ run_program(char *prog, char * const *ar
|
||||
}
|
||||
forget_child(pid, status);
|
||||
}
|
||||
- free(rpath);
|
||||
return pid;
|
||||
}
|
||||
|
||||
@@ -2007,14 +2021,24 @@ run_program(char *prog, char * const *ar
|
||||
|
||||
/* run the program */
|
||||
update_script_environment();
|
||||
- execve(rpath, args, script_env);
|
||||
- if (must_exist || errno != ENOENT) {
|
||||
- /* have to reopen the log, there's nowhere else
|
||||
- for the message to go. */
|
||||
- reopen_log();
|
||||
- syslog(LOG_ERR, "Can't execute %s: %m", rpath);
|
||||
- closelog();
|
||||
+#ifdef HAVE_FEXECVE
|
||||
+ fexecve(fd, args, script_env);
|
||||
+#else
|
||||
+ {
|
||||
+ char fdpath[32];
|
||||
+
|
||||
+ snprintf(fdpath, sizeof(fdpath), "/dev/fd/%d", fd);
|
||||
+ execve(fdpath, args, script_env);
|
||||
+ if (errno == ENOENT) {
|
||||
+ snprintf(fdpath, sizeof(fdpath), "/proc/self/fd/%d", fd);
|
||||
+ execve(fdpath, args, script_env);
|
||||
+ }
|
||||
}
|
||||
+#endif
|
||||
+ /* have to reopen the log, there's nowhere else for the message to go. */
|
||||
+ reopen_log();
|
||||
+ syslog(LOG_ERR, "Can't execute %s: %m", prog);
|
||||
+ closelog();
|
||||
_exit(99);
|
||||
}
|
||||
|
||||
--- a/pppd/options.c
|
||||
+++ b/pppd/options.c
|
||||
@@ -210,6 +210,8 @@ static struct option *find_option(char *
|
||||
static int process_option(struct option *, char *, char **);
|
||||
static int n_arguments(struct option *);
|
||||
static int number_option(char *, u_int32_t *, int);
|
||||
+static int ppp_options_open(const char *, int, int, FILE **);
|
||||
+static int ppp_options_from_fp(FILE *, const char *, int);
|
||||
|
||||
/*
|
||||
* Structure to store extra lists of options.
|
||||
@@ -588,14 +590,23 @@ int
|
||||
ppp_options_from_file(char *filename, int must_exist, int check_prot, int priv)
|
||||
{
|
||||
FILE *f;
|
||||
- int i, newline, ret, err;
|
||||
- struct option *opt;
|
||||
- int oldpriv, n;
|
||||
- char *oldsource;
|
||||
+
|
||||
+ if (!ppp_options_open(filename, must_exist, check_prot, &f))
|
||||
+ return 0;
|
||||
+ if (f == NULL)
|
||||
+ return 1;
|
||||
+ return ppp_options_from_fp(f, filename, priv);
|
||||
+}
|
||||
+
|
||||
+/*
|
||||
+ * ppp_options_open - Open a file for options
|
||||
+ */
|
||||
+static int
|
||||
+ppp_options_open(const char *filename, int must_exist, int check_prot, FILE **fp)
|
||||
+{
|
||||
uid_t euid;
|
||||
- char *argv[MAXARGS];
|
||||
- char args[MAXARGS][MAXWORDLEN];
|
||||
- char cmd[MAXWORDLEN];
|
||||
+ FILE *f;
|
||||
+ int err;
|
||||
|
||||
euid = geteuid();
|
||||
if (check_prot && seteuid(getuid()) == -1) {
|
||||
@@ -606,6 +617,7 @@ ppp_options_from_file(char *filename, in
|
||||
err = errno;
|
||||
if (check_prot && seteuid(euid) == -1)
|
||||
fatal("unable to regain privileges");
|
||||
+ *fp = f;
|
||||
if (f == NULL) {
|
||||
errno = err;
|
||||
if (!must_exist) {
|
||||
@@ -616,6 +628,22 @@ ppp_options_from_file(char *filename, in
|
||||
ppp_option_error("Can't open options file %s: %m", filename);
|
||||
return 0;
|
||||
}
|
||||
+ return 1;
|
||||
+}
|
||||
+
|
||||
+/*
|
||||
+ * Parse options from an open FILE pointer.
|
||||
+ */
|
||||
+static int
|
||||
+ppp_options_from_fp(FILE *f, const char *filename, int priv)
|
||||
+{
|
||||
+ int i, newline, ret;
|
||||
+ struct option *opt;
|
||||
+ int oldpriv, n;
|
||||
+ char *oldsource;
|
||||
+ char *argv[MAXARGS];
|
||||
+ char args[MAXARGS][MAXWORDLEN];
|
||||
+ char cmd[MAXWORDLEN];
|
||||
|
||||
oldpriv = privileged_option;
|
||||
privileged_option = priv;
|
||||
@@ -1371,7 +1399,7 @@ readable(int fd)
|
||||
* \<newline> is ignored.
|
||||
*/
|
||||
int
|
||||
-getword(FILE *f, char *word, int *newlinep, char *filename)
|
||||
+getword(FILE *f, char *word, int *newlinep, const char *filename)
|
||||
{
|
||||
int c, len, escape;
|
||||
int quoted, comment;
|
||||
@@ -1666,7 +1694,7 @@ callfile(char **argv)
|
||||
{
|
||||
char *fname, *arg, *p;
|
||||
int l, ok;
|
||||
- char *realname;
|
||||
+ FILE *f;
|
||||
|
||||
arg = *argv;
|
||||
ok = 1;
|
||||
@@ -1695,15 +1723,19 @@ callfile(char **argv)
|
||||
slprintf(fname, l, "%s%s", PPP_PATH_PEERFILES, arg);
|
||||
ppp_script_setenv("CALL_FILE", arg, 0);
|
||||
|
||||
- if (!ppp_check_access(fname, &realname, 1, 0)) {
|
||||
+ if (!ppp_options_open(fname, 1, 1, &f)) {
|
||||
+ free(fname);
|
||||
+ return 0;
|
||||
+ }
|
||||
+ if (!ppp_check_access(fileno(f), fname, 0)) {
|
||||
free(fname);
|
||||
+ fclose(f);
|
||||
return 0;
|
||||
}
|
||||
|
||||
- ok = ppp_options_from_file(realname, 1, 1, 1);
|
||||
+ ok = ppp_options_from_fp(f, fname, 1);
|
||||
|
||||
free(fname);
|
||||
- free(realname);
|
||||
return ok;
|
||||
}
|
||||
|
||||
--- a/pppd/pppd-private.h
|
||||
+++ b/pppd/pppd-private.h
|
||||
@@ -470,7 +470,7 @@ int get_first_ether_hwaddr(unsigned cha
|
||||
int setipaddr(char *, char **, int); /* Set local/remote ip addresses */
|
||||
int parse_args(int argc, char **argv);
|
||||
/* Parse options from arguments given */
|
||||
-int getword(FILE *f, char *word, int *newlinep, char *filename);
|
||||
+int getword(FILE *f, char *word, int *newlinep, const char *filename);
|
||||
/* Read a word from a file */
|
||||
int options_from_user(void); /* Parse options from user's .ppprc */
|
||||
int options_for_tty(void); /* Parse options from /etc/ppp/options.tty */
|
||||
--- a/pppd/pppd.8
|
||||
+++ b/pppd/pppd.8
|
||||
@@ -1334,16 +1334,6 @@ file under /etc/ppp/peers, the system ad
|
||||
establish a ppp connection via a device which they would not normally
|
||||
have permission to access. Otherwise pppd uses the invoking user's
|
||||
real UID when opening the device.
|
||||
-.PP
|
||||
-To avoid the possibility of privileged options files, secrets files,
|
||||
-and other files which contain sensitive information being compromised,
|
||||
-\fIpppd\fR performs a path check on these files before opening them.
|
||||
-This involves first translating the file path into a real absolute path
|
||||
-containing no symlinks or ".." components. Then each component from
|
||||
-the root down is checked to ensure that it is owned by root and that
|
||||
-its permissions do not permit writing by group or other. Failure to
|
||||
-conform to these requirements will cause \fIpppd\fR to exit with a
|
||||
-suitable error message.
|
||||
.SH AUTHENTICATION
|
||||
Authentication is the process whereby one peer convinces the other of
|
||||
its identity. This involves the first peer sending its name to the
|
||||
--- a/pppd/pppd.h
|
||||
+++ b/pppd/pppd.h
|
||||
@@ -300,7 +300,7 @@ void pr_log(void *, char *, ...);
|
||||
void end_pr_log(void);
|
||||
|
||||
/* Check that a file can safely be used */
|
||||
-int ppp_check_access(const char *path, char **path_to_use, int must_exist, int exec);
|
||||
+int ppp_check_access(int fd, const char *path, int exec);
|
||||
|
||||
/*
|
||||
* Get the current exist status of pppd
|
||||
--- a/pppd/utils.c
|
||||
+++ b/pppd/utils.c
|
||||
@@ -75,98 +75,50 @@ struct buffer_info {
|
||||
};
|
||||
|
||||
/*
|
||||
- * Check that a file is owned by root, not writable by group or other,
|
||||
- * and that all the directories in the path leading to it is likewise
|
||||
- * owned by root and not writable by group or other. The real path to
|
||||
- * the file is returned in *path_to_use, which should be freed after
|
||||
- * use (real meaning not containing any symlinks or ".." components).
|
||||
+ * Check that a file descriptor is owned by root, not writable by group or
|
||||
+ * other.
|
||||
* If exec is true, check for execute permission, otherwise for read
|
||||
* permission.
|
||||
+ * Note: the path argument is only used for log messages.
|
||||
* Returns 1 if OK; if not, prints an error message and returns 0.
|
||||
*/
|
||||
int
|
||||
-ppp_check_access(const char *path, char **path_to_use, int must_exist, int exec)
|
||||
+ppp_check_access(int fd, const char *path, int exec)
|
||||
{
|
||||
- char *rpath, *slash, *part;
|
||||
struct stat sbuf;
|
||||
int perm;
|
||||
|
||||
- /*
|
||||
- * Resolve symlinks such that we eliminate a few potential ToCToU
|
||||
- * attack avenues (eg, changing symlinks).
|
||||
- */
|
||||
- rpath = realpath(path, NULL);
|
||||
- if (!rpath) {
|
||||
- if (errno == ENOMEM)
|
||||
- fatal("Insufficient memory for real path");
|
||||
- if (must_exist || errno != ENOENT)
|
||||
- error("Can't access %s: %m", path);
|
||||
- return 0;
|
||||
+ if (fstat(fd, &sbuf) != 0) {
|
||||
+ error("Can't stat %v: %m", path);
|
||||
+ goto err;
|
||||
}
|
||||
|
||||
- /*
|
||||
- * full check the entire path, must be root: owned, and NOT be writable
|
||||
- * to group/other (which incorporates FACL bits somehow, so we can ignore
|
||||
- * explicit FACL checks).
|
||||
- */
|
||||
- part = "/";
|
||||
- slash = rpath;
|
||||
- for (;;) {
|
||||
- bool ok = false;
|
||||
- const char *pname = (slash? part: "it");
|
||||
-
|
||||
- if (lstat(part, &sbuf) != 0) {
|
||||
- if (must_exist || errno != ENOENT) {
|
||||
- if (!slash) {
|
||||
- error("Can't access %v: %m", rpath);
|
||||
- } else {
|
||||
- error("Can't use %v, because of error accessing", path);
|
||||
- error("path component %v: %m");
|
||||
- }
|
||||
- }
|
||||
- goto err;
|
||||
- }
|
||||
-
|
||||
- if (sbuf.st_uid != 0) {
|
||||
- error("Can't safely use %v because %v is not owned by root",
|
||||
- path, pname);
|
||||
- goto err;
|
||||
- }
|
||||
-
|
||||
- if (0 != (sbuf.st_mode & (S_IWGRP | S_IWOTH))) {
|
||||
- error("Can't safely use %v because %v is group or other writable",
|
||||
- path, pname);
|
||||
- goto err;
|
||||
- }
|
||||
-
|
||||
- if (!slash)
|
||||
- break;
|
||||
-
|
||||
- *slash = '/';
|
||||
- part = rpath;
|
||||
-
|
||||
- slash = strchr(slash + 1, '/');
|
||||
- if (slash)
|
||||
- *slash = 0;
|
||||
+ if (!S_ISREG(sbuf.st_mode)) {
|
||||
+ error("Can't use %v: not a regular file", path);
|
||||
+ goto err;
|
||||
}
|
||||
|
||||
- if (!S_ISREG(sbuf.st_mode)) {
|
||||
- error("Can't use %v: not a regular file", rpath);
|
||||
+ if (sbuf.st_uid != 0) {
|
||||
+ error("Can't safely use %v because it is not owned by root", path);
|
||||
+ goto err;
|
||||
+ }
|
||||
+
|
||||
+ if (0 != (sbuf.st_mode & (S_IWGRP | S_IWOTH))) {
|
||||
+ error("Can't safely use %v because it is group or other writable",
|
||||
+ path);
|
||||
goto err;
|
||||
}
|
||||
|
||||
perm = exec? S_IXUSR : S_IRUSR;
|
||||
if ((sbuf.st_mode & perm) == 0) {
|
||||
- error("Can't use %v: not %sable by root", rpath,
|
||||
+ error("Can't use %v: not %sable by root", path,
|
||||
exec? "execut": "read");
|
||||
goto err;
|
||||
}
|
||||
|
||||
- *path_to_use = rpath;
|
||||
return 1;
|
||||
|
||||
err:
|
||||
- free(rpath);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1,28 +0,0 @@
|
||||
From f691c224e12ee13a1b317a1838d150f1ffef14a1 Mon Sep 17 00:00:00 2001
|
||||
From: Mateusz Poliwczak <mpoliwczak34@gmail.com>
|
||||
Date: Wed, 11 Feb 2026 00:40:14 +0100
|
||||
Subject: [PATCH] Remove MRU limit on PPPoE (#573)
|
||||
|
||||
Fixes #331
|
||||
|
||||
Signed-off-by: Mateusz Poliwczak <mpoliwczak34@gmail.com>
|
||||
---
|
||||
pppd/plugins/pppoe/plugin.c | 5 -----
|
||||
1 file changed, 5 deletions(-)
|
||||
|
||||
diff --git a/pppd/plugins/pppoe/plugin.c b/pppd/plugins/pppoe/plugin.c
|
||||
index b429a2fd..0f672166 100644
|
||||
--- a/pppd/plugins/pppoe/plugin.c
|
||||
+++ b/pppd/plugins/pppoe/plugin.c
|
||||
@@ -446,11 +446,6 @@ void pppoe_check_options(void)
|
||||
lcp_allowoptions[0].neg_pcompression = 0;
|
||||
lcp_wantoptions[0].neg_pcompression = 0;
|
||||
|
||||
- if (lcp_allowoptions[0].mru > MAX_PPPOE_MTU)
|
||||
- lcp_allowoptions[0].mru = MAX_PPPOE_MTU;
|
||||
- if (lcp_wantoptions[0].mru > MAX_PPPOE_MTU)
|
||||
- lcp_wantoptions[0].mru = MAX_PPPOE_MTU;
|
||||
-
|
||||
/* Save configuration */
|
||||
conn->storedmtu = lcp_allowoptions[0].mru;
|
||||
conn->storedmru = lcp_wantoptions[0].mru;
|
||||
Reference in New Issue
Block a user