From 551100331fc59409c6c0f7738ab22eb197b8df20 Mon Sep 17 00:00:00 2001 From: Max Laier Date: Wed, 10 Dec 2008 19:31:42 +0000 Subject: [PATCH 01/39] Flatten out the pf userland vendor area --- {contrib/pf/authpf => authpf}/authpf.8 | 0 {contrib/pf/authpf => authpf}/authpf.c | 0 {contrib/pf/authpf => authpf}/pathnames.h | 0 {contrib/pf/ftp-proxy => ftp-proxy}/filter.c | 0 {contrib/pf/ftp-proxy => ftp-proxy}/filter.h | 0 {contrib/pf/ftp-proxy => ftp-proxy}/ftp-proxy.8 | 0 {contrib/pf/ftp-proxy => ftp-proxy}/ftp-proxy.c | 0 {contrib/pf/ftp-proxy => ftp-proxy}/getline.c | 0 {contrib/pf/ftp-proxy => ftp-proxy}/util.c | 0 {contrib/pf/ftp-proxy => ftp-proxy}/util.h | 0 {contrib/pf/libevent => libevent}/buffer.c | 0 {contrib/pf/libevent => libevent}/evbuffer.c | 0 {contrib/pf/libevent => libevent}/event-internal.h | 0 {contrib/pf/libevent => libevent}/event.c | 0 {contrib/pf/libevent => libevent}/event.h | 0 {contrib/pf/libevent => libevent}/evsignal.h | 0 {contrib/pf/libevent => libevent}/kqueue.c | 0 {contrib/pf/libevent => libevent}/log.c | 0 {contrib/pf/libevent => libevent}/log.h | 0 {contrib/pf/libevent => libevent}/poll.c | 0 {contrib/pf/libevent => libevent}/select.c | 0 {contrib/pf/libevent => libevent}/signal.c | 0 {contrib/pf/man => man}/pf.4 | 0 {contrib/pf/man => man}/pf.conf.5 | 0 {contrib/pf/man => man}/pf.os.5 | 0 {contrib/pf/man => man}/pflog.4 | 0 {contrib/pf/man => man}/pfsync.4 | 0 {contrib/pf/pfctl => pfctl}/parse.y | 0 {contrib/pf/pfctl => pfctl}/pf_print_state.c | 0 {contrib/pf/pfctl => pfctl}/pfctl.8 | 0 {contrib/pf/pfctl => pfctl}/pfctl.c | 0 {contrib/pf/pfctl => pfctl}/pfctl.h | 0 {contrib/pf/pfctl => pfctl}/pfctl_altq.c | 0 {contrib/pf/pfctl => pfctl}/pfctl_optimize.c | 0 {contrib/pf/pfctl => pfctl}/pfctl_osfp.c | 0 {contrib/pf/pfctl => pfctl}/pfctl_parser.c | 0 {contrib/pf/pfctl => pfctl}/pfctl_parser.h | 0 {contrib/pf/pfctl => pfctl}/pfctl_qstats.c | 0 {contrib/pf/pfctl => pfctl}/pfctl_radix.c | 0 {contrib/pf/pfctl => pfctl}/pfctl_table.c | 0 {contrib/pf/pflogd => pflogd}/pflogd.8 | 0 {contrib/pf/pflogd => pflogd}/pflogd.c | 0 {contrib/pf/pflogd => pflogd}/pflogd.h | 0 {contrib/pf/pflogd => pflogd}/pidfile.c | 0 {contrib/pf/pflogd => pflogd}/pidfile.h | 0 {contrib/pf/pflogd => pflogd}/privsep.c | 0 {contrib/pf/pflogd => pflogd}/privsep_fdpass.c | 0 {contrib/pf/tftp-proxy => tftp-proxy}/filter.c | 0 {contrib/pf/tftp-proxy => tftp-proxy}/filter.h | 0 {contrib/pf/tftp-proxy => tftp-proxy}/tftp-proxy.8 | 0 {contrib/pf/tftp-proxy => tftp-proxy}/tftp-proxy.c | 0 51 files changed, 0 insertions(+), 0 deletions(-) rename {contrib/pf/authpf => authpf}/authpf.8 (100%) rename {contrib/pf/authpf => authpf}/authpf.c (100%) rename {contrib/pf/authpf => authpf}/pathnames.h (100%) rename {contrib/pf/ftp-proxy => ftp-proxy}/filter.c (100%) rename {contrib/pf/ftp-proxy => ftp-proxy}/filter.h (100%) rename {contrib/pf/ftp-proxy => ftp-proxy}/ftp-proxy.8 (100%) rename {contrib/pf/ftp-proxy => ftp-proxy}/ftp-proxy.c (100%) rename {contrib/pf/ftp-proxy => ftp-proxy}/getline.c (100%) rename {contrib/pf/ftp-proxy => ftp-proxy}/util.c (100%) rename {contrib/pf/ftp-proxy => ftp-proxy}/util.h (100%) rename {contrib/pf/libevent => libevent}/buffer.c (100%) rename {contrib/pf/libevent => libevent}/evbuffer.c (100%) rename {contrib/pf/libevent => libevent}/event-internal.h (100%) rename {contrib/pf/libevent => libevent}/event.c (100%) rename {contrib/pf/libevent => libevent}/event.h (100%) rename {contrib/pf/libevent => libevent}/evsignal.h (100%) rename {contrib/pf/libevent => libevent}/kqueue.c (100%) rename {contrib/pf/libevent => libevent}/log.c (100%) rename {contrib/pf/libevent => libevent}/log.h (100%) rename {contrib/pf/libevent => libevent}/poll.c (100%) rename {contrib/pf/libevent => libevent}/select.c (100%) rename {contrib/pf/libevent => libevent}/signal.c (100%) rename {contrib/pf/man => man}/pf.4 (100%) rename {contrib/pf/man => man}/pf.conf.5 (100%) rename {contrib/pf/man => man}/pf.os.5 (100%) rename {contrib/pf/man => man}/pflog.4 (100%) rename {contrib/pf/man => man}/pfsync.4 (100%) rename {contrib/pf/pfctl => pfctl}/parse.y (100%) rename {contrib/pf/pfctl => pfctl}/pf_print_state.c (100%) rename {contrib/pf/pfctl => pfctl}/pfctl.8 (100%) rename {contrib/pf/pfctl => pfctl}/pfctl.c (100%) rename {contrib/pf/pfctl => pfctl}/pfctl.h (100%) rename {contrib/pf/pfctl => pfctl}/pfctl_altq.c (100%) rename {contrib/pf/pfctl => pfctl}/pfctl_optimize.c (100%) rename {contrib/pf/pfctl => pfctl}/pfctl_osfp.c (100%) rename {contrib/pf/pfctl => pfctl}/pfctl_parser.c (100%) rename {contrib/pf/pfctl => pfctl}/pfctl_parser.h (100%) rename {contrib/pf/pfctl => pfctl}/pfctl_qstats.c (100%) rename {contrib/pf/pfctl => pfctl}/pfctl_radix.c (100%) rename {contrib/pf/pfctl => pfctl}/pfctl_table.c (100%) rename {contrib/pf/pflogd => pflogd}/pflogd.8 (100%) rename {contrib/pf/pflogd => pflogd}/pflogd.c (100%) rename {contrib/pf/pflogd => pflogd}/pflogd.h (100%) rename {contrib/pf/pflogd => pflogd}/pidfile.c (100%) rename {contrib/pf/pflogd => pflogd}/pidfile.h (100%) rename {contrib/pf/pflogd => pflogd}/privsep.c (100%) rename {contrib/pf/pflogd => pflogd}/privsep_fdpass.c (100%) rename {contrib/pf/tftp-proxy => tftp-proxy}/filter.c (100%) rename {contrib/pf/tftp-proxy => tftp-proxy}/filter.h (100%) rename {contrib/pf/tftp-proxy => tftp-proxy}/tftp-proxy.8 (100%) rename {contrib/pf/tftp-proxy => tftp-proxy}/tftp-proxy.c (100%) diff --git a/contrib/pf/authpf/authpf.8 b/authpf/authpf.8 similarity index 100% rename from contrib/pf/authpf/authpf.8 rename to authpf/authpf.8 diff --git a/contrib/pf/authpf/authpf.c b/authpf/authpf.c similarity index 100% rename from contrib/pf/authpf/authpf.c rename to authpf/authpf.c diff --git a/contrib/pf/authpf/pathnames.h b/authpf/pathnames.h similarity index 100% rename from contrib/pf/authpf/pathnames.h rename to authpf/pathnames.h diff --git a/contrib/pf/ftp-proxy/filter.c b/ftp-proxy/filter.c similarity index 100% rename from contrib/pf/ftp-proxy/filter.c rename to ftp-proxy/filter.c diff --git a/contrib/pf/ftp-proxy/filter.h b/ftp-proxy/filter.h similarity index 100% rename from contrib/pf/ftp-proxy/filter.h rename to ftp-proxy/filter.h diff --git a/contrib/pf/ftp-proxy/ftp-proxy.8 b/ftp-proxy/ftp-proxy.8 similarity index 100% rename from contrib/pf/ftp-proxy/ftp-proxy.8 rename to ftp-proxy/ftp-proxy.8 diff --git a/contrib/pf/ftp-proxy/ftp-proxy.c b/ftp-proxy/ftp-proxy.c similarity index 100% rename from contrib/pf/ftp-proxy/ftp-proxy.c rename to ftp-proxy/ftp-proxy.c diff --git a/contrib/pf/ftp-proxy/getline.c b/ftp-proxy/getline.c similarity index 100% rename from contrib/pf/ftp-proxy/getline.c rename to ftp-proxy/getline.c diff --git a/contrib/pf/ftp-proxy/util.c b/ftp-proxy/util.c similarity index 100% rename from contrib/pf/ftp-proxy/util.c rename to ftp-proxy/util.c diff --git a/contrib/pf/ftp-proxy/util.h b/ftp-proxy/util.h similarity index 100% rename from contrib/pf/ftp-proxy/util.h rename to ftp-proxy/util.h diff --git a/contrib/pf/libevent/buffer.c b/libevent/buffer.c similarity index 100% rename from contrib/pf/libevent/buffer.c rename to libevent/buffer.c diff --git a/contrib/pf/libevent/evbuffer.c b/libevent/evbuffer.c similarity index 100% rename from contrib/pf/libevent/evbuffer.c rename to libevent/evbuffer.c diff --git a/contrib/pf/libevent/event-internal.h b/libevent/event-internal.h similarity index 100% rename from contrib/pf/libevent/event-internal.h rename to libevent/event-internal.h diff --git a/contrib/pf/libevent/event.c b/libevent/event.c similarity index 100% rename from contrib/pf/libevent/event.c rename to libevent/event.c diff --git a/contrib/pf/libevent/event.h b/libevent/event.h similarity index 100% rename from contrib/pf/libevent/event.h rename to libevent/event.h diff --git a/contrib/pf/libevent/evsignal.h b/libevent/evsignal.h similarity index 100% rename from contrib/pf/libevent/evsignal.h rename to libevent/evsignal.h diff --git a/contrib/pf/libevent/kqueue.c b/libevent/kqueue.c similarity index 100% rename from contrib/pf/libevent/kqueue.c rename to libevent/kqueue.c diff --git a/contrib/pf/libevent/log.c b/libevent/log.c similarity index 100% rename from contrib/pf/libevent/log.c rename to libevent/log.c diff --git a/contrib/pf/libevent/log.h b/libevent/log.h similarity index 100% rename from contrib/pf/libevent/log.h rename to libevent/log.h diff --git a/contrib/pf/libevent/poll.c b/libevent/poll.c similarity index 100% rename from contrib/pf/libevent/poll.c rename to libevent/poll.c diff --git a/contrib/pf/libevent/select.c b/libevent/select.c similarity index 100% rename from contrib/pf/libevent/select.c rename to libevent/select.c diff --git a/contrib/pf/libevent/signal.c b/libevent/signal.c similarity index 100% rename from contrib/pf/libevent/signal.c rename to libevent/signal.c diff --git a/contrib/pf/man/pf.4 b/man/pf.4 similarity index 100% rename from contrib/pf/man/pf.4 rename to man/pf.4 diff --git a/contrib/pf/man/pf.conf.5 b/man/pf.conf.5 similarity index 100% rename from contrib/pf/man/pf.conf.5 rename to man/pf.conf.5 diff --git a/contrib/pf/man/pf.os.5 b/man/pf.os.5 similarity index 100% rename from contrib/pf/man/pf.os.5 rename to man/pf.os.5 diff --git a/contrib/pf/man/pflog.4 b/man/pflog.4 similarity index 100% rename from contrib/pf/man/pflog.4 rename to man/pflog.4 diff --git a/contrib/pf/man/pfsync.4 b/man/pfsync.4 similarity index 100% rename from contrib/pf/man/pfsync.4 rename to man/pfsync.4 diff --git a/contrib/pf/pfctl/parse.y b/pfctl/parse.y similarity index 100% rename from contrib/pf/pfctl/parse.y rename to pfctl/parse.y diff --git a/contrib/pf/pfctl/pf_print_state.c b/pfctl/pf_print_state.c similarity index 100% rename from contrib/pf/pfctl/pf_print_state.c rename to pfctl/pf_print_state.c diff --git a/contrib/pf/pfctl/pfctl.8 b/pfctl/pfctl.8 similarity index 100% rename from contrib/pf/pfctl/pfctl.8 rename to pfctl/pfctl.8 diff --git a/contrib/pf/pfctl/pfctl.c b/pfctl/pfctl.c similarity index 100% rename from contrib/pf/pfctl/pfctl.c rename to pfctl/pfctl.c diff --git a/contrib/pf/pfctl/pfctl.h b/pfctl/pfctl.h similarity index 100% rename from contrib/pf/pfctl/pfctl.h rename to pfctl/pfctl.h diff --git a/contrib/pf/pfctl/pfctl_altq.c b/pfctl/pfctl_altq.c similarity index 100% rename from contrib/pf/pfctl/pfctl_altq.c rename to pfctl/pfctl_altq.c diff --git a/contrib/pf/pfctl/pfctl_optimize.c b/pfctl/pfctl_optimize.c similarity index 100% rename from contrib/pf/pfctl/pfctl_optimize.c rename to pfctl/pfctl_optimize.c diff --git a/contrib/pf/pfctl/pfctl_osfp.c b/pfctl/pfctl_osfp.c similarity index 100% rename from contrib/pf/pfctl/pfctl_osfp.c rename to pfctl/pfctl_osfp.c diff --git a/contrib/pf/pfctl/pfctl_parser.c b/pfctl/pfctl_parser.c similarity index 100% rename from contrib/pf/pfctl/pfctl_parser.c rename to pfctl/pfctl_parser.c diff --git a/contrib/pf/pfctl/pfctl_parser.h b/pfctl/pfctl_parser.h similarity index 100% rename from contrib/pf/pfctl/pfctl_parser.h rename to pfctl/pfctl_parser.h diff --git a/contrib/pf/pfctl/pfctl_qstats.c b/pfctl/pfctl_qstats.c similarity index 100% rename from contrib/pf/pfctl/pfctl_qstats.c rename to pfctl/pfctl_qstats.c diff --git a/contrib/pf/pfctl/pfctl_radix.c b/pfctl/pfctl_radix.c similarity index 100% rename from contrib/pf/pfctl/pfctl_radix.c rename to pfctl/pfctl_radix.c diff --git a/contrib/pf/pfctl/pfctl_table.c b/pfctl/pfctl_table.c similarity index 100% rename from contrib/pf/pfctl/pfctl_table.c rename to pfctl/pfctl_table.c diff --git a/contrib/pf/pflogd/pflogd.8 b/pflogd/pflogd.8 similarity index 100% rename from contrib/pf/pflogd/pflogd.8 rename to pflogd/pflogd.8 diff --git a/contrib/pf/pflogd/pflogd.c b/pflogd/pflogd.c similarity index 100% rename from contrib/pf/pflogd/pflogd.c rename to pflogd/pflogd.c diff --git a/contrib/pf/pflogd/pflogd.h b/pflogd/pflogd.h similarity index 100% rename from contrib/pf/pflogd/pflogd.h rename to pflogd/pflogd.h diff --git a/contrib/pf/pflogd/pidfile.c b/pflogd/pidfile.c similarity index 100% rename from contrib/pf/pflogd/pidfile.c rename to pflogd/pidfile.c diff --git a/contrib/pf/pflogd/pidfile.h b/pflogd/pidfile.h similarity index 100% rename from contrib/pf/pflogd/pidfile.h rename to pflogd/pidfile.h diff --git a/contrib/pf/pflogd/privsep.c b/pflogd/privsep.c similarity index 100% rename from contrib/pf/pflogd/privsep.c rename to pflogd/privsep.c diff --git a/contrib/pf/pflogd/privsep_fdpass.c b/pflogd/privsep_fdpass.c similarity index 100% rename from contrib/pf/pflogd/privsep_fdpass.c rename to pflogd/privsep_fdpass.c diff --git a/contrib/pf/tftp-proxy/filter.c b/tftp-proxy/filter.c similarity index 100% rename from contrib/pf/tftp-proxy/filter.c rename to tftp-proxy/filter.c diff --git a/contrib/pf/tftp-proxy/filter.h b/tftp-proxy/filter.h similarity index 100% rename from contrib/pf/tftp-proxy/filter.h rename to tftp-proxy/filter.h diff --git a/contrib/pf/tftp-proxy/tftp-proxy.8 b/tftp-proxy/tftp-proxy.8 similarity index 100% rename from contrib/pf/tftp-proxy/tftp-proxy.8 rename to tftp-proxy/tftp-proxy.8 diff --git a/contrib/pf/tftp-proxy/tftp-proxy.c b/tftp-proxy/tftp-proxy.c similarity index 100% rename from contrib/pf/tftp-proxy/tftp-proxy.c rename to tftp-proxy/tftp-proxy.c From b39deb12b639171038aee6f8770d9bbd44c34fd1 Mon Sep 17 00:00:00 2001 From: Max Laier Date: Wed, 10 Dec 2008 20:54:37 +0000 Subject: [PATCH 03/39] Import OPENBSD_4_2_BASE --- authpf/Makefile | 11 ++ authpf/authpf.8 | 4 +- ftp-proxy/Makefile | 13 ++ ftp-proxy/filter.c | 9 +- ftp-proxy/filter.h | 4 +- ftp-proxy/ftp-proxy.8 | 11 +- ftp-proxy/ftp-proxy.c | 59 ++++++-- ftp-proxy/getline.c | 259 ---------------------------------- ftp-proxy/util.c | 306 ---------------------------------------- ftp-proxy/util.h | 68 --------- man/pf.4 | 4 +- man/pf.conf.5 | 45 +++--- man/pf.os.5 | 4 +- man/pflog.4 | 4 +- man/pfsync.4 | 4 +- pfctl/Makefile | 18 +++ pfctl/parse.y | 15 +- pfctl/pf_print_state.c | 31 ++-- pfctl/pfctl.8 | 66 ++------- pfctl/pfctl.c | 41 ++---- pfctl/pfctl.h | 8 +- pfctl/pfctl_altq.c | 6 +- pflogd/Makefile | 11 ++ pflogd/pflogd.8 | 15 +- pflogd/pflogd.c | 63 +++++++-- pflogd/pidfile.c | 121 ---------------- pflogd/pidfile.h | 1 - tftp-proxy/Makefile | 7 + tftp-proxy/filter.c | 6 +- tftp-proxy/tftp-proxy.8 | 4 +- 30 files changed, 287 insertions(+), 931 deletions(-) create mode 100644 authpf/Makefile create mode 100644 ftp-proxy/Makefile delete mode 100644 ftp-proxy/getline.c delete mode 100644 ftp-proxy/util.c delete mode 100644 ftp-proxy/util.h create mode 100644 pfctl/Makefile create mode 100644 pflogd/Makefile delete mode 100644 pflogd/pidfile.c delete mode 100644 pflogd/pidfile.h create mode 100644 tftp-proxy/Makefile diff --git a/authpf/Makefile b/authpf/Makefile new file mode 100644 index 00000000000..3e0538a8d23 --- /dev/null +++ b/authpf/Makefile @@ -0,0 +1,11 @@ +# $OpenBSD: Makefile,v 1.12 2004/04/25 19:24:52 deraadt Exp $ + +PROG= authpf +MAN= authpf.8 +BINOWN= root +BINGRP= authpf +BINMODE= 6555 +SRCS= authpf.c +CFLAGS+= -Wall + +.include diff --git a/authpf/authpf.8 b/authpf/authpf.8 index ee0dcaa423b..566d3a9627c 100644 --- a/authpf/authpf.8 +++ b/authpf/authpf.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: authpf.8,v 1.43 2007/02/24 17:21:04 beck Exp $ +.\" $OpenBSD: authpf.8,v 1.44 2007/05/31 19:20:22 jmc Exp $ .\" .\" Copyright (c) 1998-2007 Bob Beck (beck@openbsd.org>. All rights reserved. .\" @@ -14,7 +14,7 @@ .\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF .\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .\" -.Dd January 10, 2002 +.Dd $Mdocdate$ .Dt AUTHPF 8 .Os .Sh NAME diff --git a/ftp-proxy/Makefile b/ftp-proxy/Makefile new file mode 100644 index 00000000000..9541b955e7f --- /dev/null +++ b/ftp-proxy/Makefile @@ -0,0 +1,13 @@ +# $OpenBSD: Makefile,v 1.3 2006/11/26 11:31:13 deraadt Exp $ + +PROG= ftp-proxy +SRCS= ftp-proxy.c filter.c +MAN= ftp-proxy.8 + +CFLAGS+= -I${.CURDIR} +CFLAGS+= -Wall -Wstrict-prototypes -Wmissing-prototypes -Wpointer-arith \ + -Wno-uninitialized +LDADD+= -levent +DPADD+= ${LIBEVENT} + +.include diff --git a/ftp-proxy/filter.c b/ftp-proxy/filter.c index f86429db51d..b33c541457a 100644 --- a/ftp-proxy/filter.c +++ b/ftp-proxy/filter.c @@ -1,4 +1,4 @@ -/* $OpenBSD: filter.c,v 1.5 2006/12/01 07:31:21 camield Exp $ */ +/* $OpenBSD: filter.c,v 1.6 2007/08/01 09:31:41 henning Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, @@ -53,7 +53,7 @@ static struct pfioc_rule pfr; static struct pfioc_trans pft; static struct pfioc_trans_e pfte[TRANS_SIZE]; static int dev, rule_log; -static char *qname; +static char *qname, *tagname; int add_filter(u_int32_t id, u_int8_t dir, struct sockaddr *src, @@ -159,11 +159,12 @@ do_rollback(void) } void -init_filter(char *opt_qname, int opt_verbose) +init_filter(char *opt_qname, char *opt_tagname, int opt_verbose) { struct pf_status status; qname = opt_qname; + tagname = opt_tagname; if (opt_verbose == 1) rule_log = PF_LOG; @@ -276,6 +277,8 @@ prepare_rule(u_int32_t id, int rs_num, struct sockaddr *src, } pfr.rule.dst.port_op = PF_OP_EQ; pfr.rule.dst.port[0] = htons(d_port); + if (tagname != NULL) + strlcpy(pfr.rule.tagname, tagname, sizeof pfr.rule.tagname); switch (rs_num) { case PF_RULESET_FILTER: diff --git a/ftp-proxy/filter.h b/ftp-proxy/filter.h index 6779c597446..150bc49d3ce 100644 --- a/ftp-proxy/filter.h +++ b/ftp-proxy/filter.h @@ -1,4 +1,4 @@ -/* $OpenBSD: filter.h,v 1.3 2005/06/07 14:12:07 camield Exp $ */ +/* $OpenBSD: filter.h,v 1.4 2007/08/01 09:31:41 henning Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, @@ -26,6 +26,6 @@ int add_rdr(u_int32_t, struct sockaddr *, struct sockaddr *, u_int16_t, struct sockaddr *, u_int16_t); int do_commit(void); int do_rollback(void); -void init_filter(char *, int); +void init_filter(char *, char *, int); int prepare_commit(u_int32_t); int server_lookup(struct sockaddr *, struct sockaddr *, struct sockaddr *); diff --git a/ftp-proxy/ftp-proxy.8 b/ftp-proxy/ftp-proxy.8 index 44e6e59d22f..d48997b05a6 100644 --- a/ftp-proxy/ftp-proxy.8 +++ b/ftp-proxy/ftp-proxy.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: ftp-proxy.8,v 1.7 2006/12/30 13:01:54 camield Exp $ +.\" $OpenBSD: ftp-proxy.8,v 1.10 2007/08/01 15:45:41 jmc Exp $ .\" .\" Copyright (c) 2004, 2005 Camiel Dobbelaar, .\" @@ -14,7 +14,7 @@ .\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF .\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .\" -.Dd November 28, 2004 +.Dd $Mdocdate$ .Dt FTP-PROXY 8 .Os .Sh NAME @@ -22,6 +22,7 @@ .Nd Internet File Transfer Protocol proxy daemon .Sh SYNOPSIS .Nm ftp-proxy +.Bk -words .Op Fl 6Adrv .Op Fl a Ar address .Op Fl b Ar address @@ -31,7 +32,9 @@ .Op Fl p Ar port .Op Fl q Ar queue .Op Fl R Ar address +.Op Fl T Ar tag .Op Fl t Ar timeout +.Ek .Sh DESCRIPTION .Nm is a proxy for the Internet File Transfer Protocol. @@ -128,6 +131,10 @@ connections to another proxy. .It Fl r Rewrite sourceport to 20 in active mode to suit ancient clients that insist on this RFC property. +.It Fl T Ar tag +Automatically tag packets passing through the +.Xr pf 4 +rule with the name supplied. .It Fl t Ar timeout Number of seconds that the control connection can be idle, before the proxy will disconnect. diff --git a/ftp-proxy/ftp-proxy.c b/ftp-proxy/ftp-proxy.c index 99e417472fb..3a691859c32 100644 --- a/ftp-proxy/ftp-proxy.c +++ b/ftp-proxy/ftp-proxy.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ftp-proxy.c,v 1.13 2006/12/30 13:24:00 camield Exp $ */ +/* $OpenBSD: ftp-proxy.c,v 1.15 2007/08/15 15:18:02 camield Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, @@ -102,6 +102,7 @@ u_int16_t pick_proxy_port(void); void proxy_reply(int, struct sockaddr *, u_int16_t); void server_error(struct bufferevent *, short, void *); int server_parse(struct session *s); +int allow_data_connection(struct session *s); void server_read(struct bufferevent *, void *); const char *sock_ntop(struct sockaddr *); void usage(void); @@ -113,7 +114,7 @@ char ntop_buf[NTOP_BUFS][INET6_ADDRSTRLEN]; struct sockaddr_storage fixed_server_ss, fixed_proxy_ss; char *fixed_server, *fixed_server_port, *fixed_proxy, *listen_ip, *listen_port, - *qname; + *qname, *tagname; int anonymous_only, daemonize, id_count, ipv6_mode, loglevel, max_sessions, rfc_mode, session_count, timeout, verbose; extern char *__progname; @@ -149,8 +150,19 @@ client_parse(struct session *s) return (1); if (linebuf[0] == 'P' || linebuf[0] == 'p' || - linebuf[0] == 'E' || linebuf[0] == 'e') - return (client_parse_cmd(s)); + linebuf[0] == 'E' || linebuf[0] == 'e') { + if (!client_parse_cmd(s)) + return (0); + + /* + * Allow active mode connections immediately, instead of + * waiting for a positive reply from the server. Some + * rare servers/proxies try to probe or setup the data + * connection before an actual transfer request. + */ + if (s->cmd == CMD_PORT || s->cmd == CMD_EPRT) + return (allow_data_connection(s)); + } if (anonymous_only && (linebuf[0] == 'U' || linebuf[0] == 'u')) return (client_parse_anon(s)); @@ -588,6 +600,7 @@ main(int argc, char *argv[]) max_sessions = 100; qname = NULL; rfc_mode = 0; + tagname = NULL; timeout = 24 * 3600; verbose = 0; @@ -595,7 +608,7 @@ main(int argc, char *argv[]) id_count = 1; session_count = 0; - while ((ch = getopt(argc, argv, "6Aa:b:D:dm:P:p:q:R:rt:v")) != -1) { + while ((ch = getopt(argc, argv, "6Aa:b:D:dm:P:p:q:R:rT:t:v")) != -1) { switch (ch) { case '6': ipv6_mode = 1; @@ -640,6 +653,11 @@ main(int argc, char *argv[]) case 'r': rfc_mode = 1; break; + case 'T': + if (strlen(optarg) >= PF_TAG_NAME_SIZE) + errx(1, "tagname too long"); + tagname = optarg; + break; case 't': timeout = strtonum(optarg, 0, 86400, &errstr); if (errstr) @@ -720,7 +738,7 @@ main(int argc, char *argv[]) freeaddrinfo(res); /* Initialize pf. */ - init_filter(qname, verbose); + init_filter(qname, tagname, verbose); if (daemonize) { if (daemon(0, 0) == -1) @@ -888,12 +906,26 @@ server_error(struct bufferevent *bufev, short what, void *arg) int server_parse(struct session *s) { - struct sockaddr *client_sa, *orig_sa, *proxy_sa, *server_sa; - int prepared = 0; - if (s->cmd == CMD_NONE || linelen < 4 || linebuf[0] != '2') goto out; + if ((s->cmd == CMD_PASV && strncmp("227 ", linebuf, 4) == 0) || + (s->cmd == CMD_EPSV && strncmp("229 ", linebuf, 4) == 0)) + return (allow_data_connection(s)); + + out: + s->cmd = CMD_NONE; + s->port = 0; + + return (1); +} + +int +allow_data_connection(struct session *s) +{ + struct sockaddr *client_sa, *orig_sa, *proxy_sa, *server_sa; + int prepared = 0; + /* * The pf rules below do quite some NAT rewriting, to keep up * appearances. Points to keep in mind: @@ -918,8 +950,7 @@ server_parse(struct session *s) orig_sa = sstosa(&s->server_ss); /* Passive modes. */ - if ((s->cmd == CMD_PASV && strncmp("227 ", linebuf, 4) == 0) || - (s->cmd == CMD_EPSV && strncmp("229 ", linebuf, 4) == 0)) { + if (s->cmd == CMD_PASV || s->cmd == CMD_EPSV) { s->port = parse_port(s->cmd); if (s->port < MIN_PORT) { logmsg(LOG_CRIT, "#%d bad port in '%s'", s->id, @@ -960,8 +991,7 @@ server_parse(struct session *s) } /* Active modes. */ - if ((s->cmd == CMD_PORT || s->cmd == CMD_EPRT) && - strncmp("200 ", linebuf, 4) == 0) { + if (s->cmd == CMD_PORT || s->cmd == CMD_EPRT) { logmsg(LOG_INFO, "#%d active: server to client port %d" " via port %d", s->id, s->port, s->proxy_port); @@ -1011,7 +1041,6 @@ server_parse(struct session *s) goto fail; } - out: s->cmd = CMD_NONE; s->port = 0; @@ -1088,6 +1117,6 @@ usage(void) { fprintf(stderr, "usage: %s [-6Adrv] [-a address] [-b address]" " [-D level] [-m maxsessions]\n [-P port]" - " [-p port] [-q queue] [-R address] [-t timeout]\n", __progname); + " [-p port] [-q queue] [-R address] [-T tag] [-t timeout]\n", __progname); exit(1); } diff --git a/ftp-proxy/getline.c b/ftp-proxy/getline.c deleted file mode 100644 index 97ffd48c6e3..00000000000 --- a/ftp-proxy/getline.c +++ /dev/null @@ -1,259 +0,0 @@ -/* $OpenBSD: getline.c,v 1.16 2004/09/16 04:50:51 deraadt Exp $ */ - -/* - * Copyright (c) 1985, 1988 Regents of the University of California. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the University nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - * @(#)ftpcmd.y 5.24 (Berkeley) 2/25/91 - */ - -#include -#include - -#include -#include - -#include -#include -#include -#include -#include -#include -#include - -#include "util.h" - -int refill_buffer(struct csiob *iobp); - -/* - * Refill the io buffer if we KNOW that data is available - * - * Returns 1 if any new data was obtained, 0 otherwise. - */ - -int -refill_buffer(struct csiob *iobp) -{ - int rqlen, rlen; - - if (!(iobp->data_available)) - return(0); - - if (iobp->got_eof) - return(0); - - /* - * The buffer has been entirely consumed if next_byte == io_buffer_len. - * Otherwise, there is some still-to-be-used data in io_buffer. - * Shuffle it to the start of the buffer. - * Note that next_byte will never exceed io_buffer_len. - * Also, note that we MUST use bcopy because the two regions could - * overlap (memcpy isn't defined to work properly with overlapping - * regions). - */ - if (iobp->next_byte < iobp->io_buffer_len) { - int dst_ix = 0; - int src_ix = iobp->next_byte; - int amount = iobp->io_buffer_len - iobp->next_byte; - - bcopy(&iobp->io_buffer[src_ix], &iobp->io_buffer[dst_ix], - amount); - iobp->io_buffer_len = amount; - } else if (iobp->next_byte == iobp->io_buffer_len) - iobp->io_buffer_len = 0; - else { - syslog(LOG_ERR, "next_byte(%d) > io_buffer_len(%d)", - iobp->next_byte, iobp->io_buffer_len); - exit(EX_OSERR); - } - - iobp->next_byte = 0; - - /* don't do tiny reads, grow first if we need to */ - rqlen = iobp->io_buffer_size - iobp->io_buffer_len; - if (rqlen <= 128) { - unsigned char *tmp; - - iobp->io_buffer_size += 128; - tmp = realloc(iobp->io_buffer, iobp->io_buffer_size); - if (tmp == NULL) { - syslog(LOG_INFO, "Insufficient memory"); - exit(EX_UNAVAILABLE); - } - iobp->io_buffer = tmp; - rqlen = iobp->io_buffer_size - iobp->io_buffer_len; - } - - /* - * Always leave an unused byte at the end of the buffer - * because the debug output uses that byte from time to time - * to ensure that something that is being printed is \0 terminated. - */ - rqlen -= 1; - - doread: - rlen = read(iobp->fd, &iobp->io_buffer[iobp->io_buffer_len], rqlen); - iobp->data_available = 0; - switch (rlen) { - case -1: - if (errno == EAGAIN || errno == EINTR) - goto doread; - if (errno != ECONNRESET) { - syslog(LOG_INFO, "read() failed on socket from %s (%m)", - iobp->who); - exit(EX_DATAERR); - } - /* fall through to EOF case */ - case 0: - iobp->got_eof = 1; - return(0); - break; - default: - iobp->io_buffer_len += rlen; - break; - } - return(1); -} - -/* - * telnet_getline - a hacked up version of fgets to ignore TELNET escape codes. - * - * This code is derived from the getline routine found in the UC Berkeley - * ftpd code. - * - */ - -int -telnet_getline(struct csiob *iobp, struct csiob *telnet_passthrough) -{ - unsigned char ch; - int ix; - unsigned char tbuf[100]; - - iobp->line_buffer[0] = '\0'; - - /* - * If the buffer is empty then refill it right away. - */ - if (iobp->next_byte == iobp->io_buffer_len) - if (!refill_buffer(iobp)) - return(0); - - /* - * Is there a telnet command in the buffer? - */ - ch = iobp->io_buffer[iobp->next_byte]; - if (ch == IAC) { - /* - * Yes - buffer must have at least three bytes in it - */ - if (iobp->io_buffer_len - iobp->next_byte < 3) { - if (!refill_buffer(iobp)) - return(0); - if (iobp->io_buffer_len - iobp->next_byte < 3) - return(0); - } - - iobp->next_byte++; - ch = iobp->io_buffer[iobp->next_byte++]; - - switch (ch) { - case WILL: - case WONT: - case DO: - case DONT: - tbuf[0] = IAC; - tbuf[1] = ch; - tbuf[2] = iobp->io_buffer[iobp->next_byte++]; - (void)send(telnet_passthrough->fd, tbuf, 3, - telnet_passthrough->send_oob_flags); - break; - case IAC: - break; - default: - break; - } - return(1); - } else { - int clen; - - /* - * Is there a newline in the buffer? - */ - for (ix = iobp->next_byte; ix < iobp->io_buffer_len; - ix += 1) { - if (iobp->io_buffer[ix] == '\n') - break; - if (iobp->io_buffer[ix] == '\0') { - syslog(LOG_INFO, - "got NUL byte from %s - bye!", - iobp->who); - exit(EX_DATAERR); - } - } - - if (ix == iobp->io_buffer_len) { - if (!refill_buffer(iobp)) - return(0); - /* - * Empty line returned - * will try again soon! - */ - return(1); - } - - /* - * Expand the line buffer if it isn't big enough. We - * use a fudge factor of 5 rather than trying to - * figure out exactly how to account for the '\0 \r\n' and - * such. The correct fudge factor is 0, 1 or 2 but - * anything higher also works. We also grow it by a - * bunch to avoid having to do this often. Yes this is - * nasty. - */ - if (ix - iobp->next_byte > iobp->line_buffer_size - 5) { - unsigned char *tmp; - - iobp->line_buffer_size = 256 + ix - iobp->next_byte; - tmp = realloc(iobp->line_buffer, - iobp->line_buffer_size); - if (tmp == NULL) { - syslog(LOG_INFO, "Insufficient memory"); - exit(EX_UNAVAILABLE); - } - iobp->line_buffer = tmp; - } - - /* +1 is for the newline */ - clen = (ix+1) - iobp->next_byte; - memcpy(iobp->line_buffer, &iobp->io_buffer[iobp->next_byte], - clen); - iobp->next_byte += clen; - iobp->line_buffer[clen] = '\0'; - return(1); - } -} diff --git a/ftp-proxy/util.c b/ftp-proxy/util.c deleted file mode 100644 index 61c9f1f1bc8..00000000000 --- a/ftp-proxy/util.c +++ /dev/null @@ -1,306 +0,0 @@ -/* $OpenBSD: util.c,v 1.19 2004/07/06 19:49:11 dhartmei Exp $ */ - -/* - * Copyright (c) 1996-2001 - * Obtuse Systems Corporation. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the Obtuse Systems nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE OBTUSE SYSTEMS AND CONTRIBUTORS - * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS - * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL OBTUSE - * SYSTEMS CORPORATION OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, - * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES - * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR - * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, - * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED - * OF THE POSSIBILITY OF SUCH DAMAGE. - * - */ - -#include -#include -#include -#include -#include -#include -#include -#include - -#include - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "util.h" - -extern int ReverseMode; - -int Debug_Level; -int Use_Rdns; -in_addr_t Bind_Addr = INADDR_NONE; - -void debuglog(int debug_level, const char *fmt, ...); - -void -debuglog(int debug_level, const char *fmt, ...) -{ - va_list ap; - va_start(ap, fmt); - - if (Debug_Level >= debug_level) - vsyslog(LOG_DEBUG, fmt, ap); - va_end(ap); -} - -int -get_proxy_env(int connected_fd, struct sockaddr_in *real_server_sa_ptr, - struct sockaddr_in *client_sa_ptr, struct sockaddr_in *proxy_sa_ptr) -{ - struct pfioc_natlook natlook; - socklen_t slen; - int fd; - - slen = sizeof(*proxy_sa_ptr); - if (getsockname(connected_fd, (struct sockaddr *)proxy_sa_ptr, - &slen) != 0) { - syslog(LOG_ERR, "getsockname() failed (%m)"); - return(-1); - } - slen = sizeof(*client_sa_ptr); - if (getpeername(connected_fd, (struct sockaddr *)client_sa_ptr, - &slen) != 0) { - syslog(LOG_ERR, "getpeername() failed (%m)"); - return(-1); - } - - if (ReverseMode) - return(0); - - /* - * Build up the pf natlook structure. - * Just for IPv4 right now - */ - memset((void *)&natlook, 0, sizeof(natlook)); - natlook.af = AF_INET; - natlook.saddr.addr32[0] = client_sa_ptr->sin_addr.s_addr; - natlook.daddr.addr32[0] = proxy_sa_ptr->sin_addr.s_addr; - natlook.proto = IPPROTO_TCP; - natlook.sport = client_sa_ptr->sin_port; - natlook.dport = proxy_sa_ptr->sin_port; - natlook.direction = PF_OUT; - - /* - * Open the pf device and lookup the mapping pair to find - * the original address we were supposed to connect to. - */ - fd = open("/dev/pf", O_RDWR); - if (fd == -1) { - syslog(LOG_ERR, "cannot open /dev/pf (%m)"); - exit(EX_UNAVAILABLE); - } - - if (ioctl(fd, DIOCNATLOOK, &natlook) == -1) { - syslog(LOG_INFO, - "pf nat lookup failed %s:%hu (%m)", - inet_ntoa(client_sa_ptr->sin_addr), - ntohs(client_sa_ptr->sin_port)); - close(fd); - return(-1); - } - close(fd); - - /* - * Now jam the original address and port back into the into - * destination sockaddr_in for the proxy to deal with. - */ - memset((void *)real_server_sa_ptr, 0, sizeof(struct sockaddr_in)); - real_server_sa_ptr->sin_port = natlook.rdport; - real_server_sa_ptr->sin_addr.s_addr = natlook.rdaddr.addr32[0]; - real_server_sa_ptr->sin_len = sizeof(struct sockaddr_in); - real_server_sa_ptr->sin_family = AF_INET; - return(0); -} - - -/* - * Transfer one unit of data across a pair of sockets - * - * A unit of data is as much as we get with a single read(2) call. - */ -int -xfer_data(const char *what_read,int from_fd, int to_fd, struct in_addr from, - struct in_addr to) -{ - int rlen, offset, xerrno, mark, flags = 0; - char tbuf[4096]; - - /* - * Are we at the OOB mark? - */ - if (ioctl(from_fd, SIOCATMARK, &mark) < 0) { - xerrno = errno; - syslog(LOG_ERR, "cannot ioctl(SIOCATMARK) socket from %s (%m)", - what_read); - errno = xerrno; - return(-1); - } - if (mark) - flags = MSG_OOB; /* Yes - at the OOB mark */ - -snarf: - rlen = recv(from_fd, tbuf, sizeof(tbuf), flags); - if (rlen == -1 && flags == MSG_OOB && errno == EINVAL) { - /* OOB didn't work */ - flags = 0; - rlen = recv(from_fd, tbuf, sizeof(tbuf), flags); - } - if (rlen == 0) { - debuglog(3, "EOF on read socket"); - return(0); - } else if (rlen == -1) { - if (errno == EAGAIN || errno == EINTR) - goto snarf; - xerrno = errno; - syslog(LOG_ERR, "xfer_data (%s): failed (%m) with flags 0%o", - what_read, flags); - errno = xerrno; - return(-1); - } else { - offset = 0; - debuglog(3, "got %d bytes from socket", rlen); - - while (offset < rlen) { - int wlen; - fling: - wlen = send(to_fd, &tbuf[offset], rlen - offset, - flags); - if (wlen == 0) { - debuglog(3, "zero-length write"); - goto fling; - } else if (wlen == -1) { - if (errno == EAGAIN || errno == EINTR) - goto fling; - xerrno = errno; - syslog(LOG_INFO, "write failed (%m)"); - errno = xerrno; - return(-1); - } else { - debuglog(3, "wrote %d bytes to socket",wlen); - offset += wlen; - } - } - return(offset); - } -} - -/* - * get_backchannel_socket gets us a socket bound somewhere in a - * particular range of ports - */ -int -get_backchannel_socket(int type, int min_port, int max_port, int start_port, - int direction, struct sockaddr_in *sap) -{ - int count; - - /* - * Make sure that direction is 'defined' and that min_port is not - * greater than max_port. - */ - if (direction != -1) - direction = 1; - - /* by default we go up by one port until we find one */ - if (min_port > max_port) { - errno = EINVAL; - return(-1); - } - - count = 1 + max_port - min_port; - - /* - * Pick a port we can bind to from within the range we want. - * If the caller specifies -1 as the starting port number then - * we pick one somewhere in the range to try. - * This is an optimization intended to speedup port selection and - * has NOTHING to do with security. - */ - if (start_port == -1) - start_port = (arc4random() % count) + min_port; - - if (start_port < min_port || start_port > max_port) { - errno = EINVAL; - return(-1); - } - - while (count-- > 0) { - struct sockaddr_in sa; - int one, fd; - - fd = socket(AF_INET, type, 0); - - bzero(&sa, sizeof sa); - sa.sin_family = AF_INET; - if (Bind_Addr == INADDR_NONE) - if (sap == NULL) - sa.sin_addr.s_addr = INADDR_ANY; - else - sa.sin_addr.s_addr = sap->sin_addr.s_addr; - else - sa.sin_addr.s_addr = Bind_Addr; - - /* - * Indicate that we want to reuse a port if it happens that the - * port in question was a listen port recently. - */ - one = 1; - if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &one, - sizeof(one)) == -1) - return(-1); - - sa.sin_port = htons(start_port); - - if (bind(fd, (struct sockaddr *)&sa, sizeof(sa)) == 0) { - if (sap != NULL) - *sap = sa; - return(fd); - } - - if (errno != EADDRINUSE) - return(-1); - - /* if it's in use, try the next port */ - close(fd); - - start_port += direction; - if (start_port < min_port) - start_port = max_port; - else if (start_port > max_port) - start_port = min_port; - } - errno = EAGAIN; - return(-1); -} diff --git a/ftp-proxy/util.h b/ftp-proxy/util.h deleted file mode 100644 index ce1e9159393..00000000000 --- a/ftp-proxy/util.h +++ /dev/null @@ -1,68 +0,0 @@ -/* $OpenBSD: util.h,v 1.5 2005/02/24 15:49:08 dhartmei Exp $ */ - -/* - * Copyright (c) 1996-2001 - * Obtuse Systems Corporation. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 4. Neither the name of the Obtuse Systems nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL OBTUSE SYSTEMS CORPORATION OR - * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, - * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, - * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; - * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, - * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR - * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF - * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -struct proxy_channel { - int pc_to_fd, pc_from_fd; - int pc_alive; - int pc_nextbyte; - int pc_flags; - int pc_length; - int pc_size; - struct sockaddr_in pc_from_sa, pc_to_sa; - int (*pc_filter)( void ** databuf, int datalen); - char *pc_buffer; -}; - -struct csiob { - int fd; - int line_buffer_size, io_buffer_size, io_buffer_len, next_byte; - unsigned char *io_buffer, *line_buffer; - struct sockaddr_in sa, real_sa; - const char *who; - char alive, got_eof, data_available; - int send_oob_flags; -}; - -extern int telnet_getline(struct csiob *iobp, - struct csiob *telnet_passthrough); - -extern int get_proxy_env(int fd, struct sockaddr_in *server_sa_ptr, - struct sockaddr_in *client_sa_ptr, struct sockaddr_in *proxy_sa_ptr); - -extern int get_backchannel_socket(int type, int min_port, int max_port, - int start_port, int direction, struct sockaddr_in *sap); - -extern int xfer_data(const char *what_read, int from_fd, int to_fd, - struct in_addr from, struct in_addr to); - -extern char *ProgName; - - diff --git a/man/pf.4 b/man/pf.4 index 1164202d234..3b6cec93ad4 100644 --- a/man/pf.4 +++ b/man/pf.4 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pf.4,v 1.58 2007/02/09 11:39:06 henning Exp $ +.\" $OpenBSD: pf.4,v 1.59 2007/05/31 19:19:51 jmc Exp $ .\" .\" Copyright (C) 2001, Kjell Wooding. All rights reserved. .\" @@ -26,7 +26,7 @@ .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF .\" SUCH DAMAGE. .\" -.Dd June 24, 2001 +.Dd $Mdocdate$ .Dt PF 4 .Os .Sh NAME diff --git a/man/pf.conf.5 b/man/pf.conf.5 index bb210fc7fc0..b6b609e733c 100644 --- a/man/pf.conf.5 +++ b/man/pf.conf.5 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pf.conf.5,v 1.376 2006/12/01 07:23:26 camield Exp $ +.\" $OpenBSD: pf.conf.5,v 1.383 2007/07/17 16:27:38 jmc Exp $ .\" .\" Copyright (c) 2002, Daniel Hartmeier .\" All rights reserved. @@ -27,7 +27,7 @@ .\" ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE .\" POSSIBILITY OF SUCH DAMAGE. .\" -.Dd November 19, 2002 +.Dd $Mdocdate: June 26 2007 $ .Dt PF.CONF 5 .Os .Sh NAME @@ -402,9 +402,10 @@ set limit { states 20000, frags 20000, src-nodes 2000 } .Bl -tag -width xxxxxxxx -compact .It Ar none Disable the ruleset optimizer. -This is the default behaviour. .It Ar basic -Enable basic ruleset optimization, which does four things to improve the +Enable basic ruleset optimization. +This is the default behaviour. +Basic ruleset optimization does four things to improve the performance of ruleset evaluations: .Pp .Bl -enum -compact @@ -1247,7 +1248,7 @@ block all .Ed .It Ar pass The packet is passed; -state is created state unless the +state is created unless the .Ar no state option is specified. .El @@ -1418,7 +1419,8 @@ This rule applies only to packets with the specified source and destination addresses and ports. .Pp Addresses can be specified in CIDR notation (matching netblocks), as -symbolic host names or interface names, or as any of the following keywords: +symbolic host names, interface names or interface group names, or as any +of the following keywords: .Pp .Bl -tag -width xxxxxxxxxxxxxx -compact .It Ar any @@ -1440,7 +1442,7 @@ the route back to the packet's source address. Any address that matches the given table. .El .Pp -Interface names can have modifiers appended: +Interface names and interface group names can have modifiers appended: .Pp .Bl -tag -width xxxxxxxxxxxx -compact .It Ar :network @@ -1603,7 +1605,7 @@ Flags not specified in are ignored. For stateful connections, the default is .Ar flags S/SA . -To indicate that flags should not be checkd at all, specify +To indicate that flags should not be checked at all, specify .Ar flags any . The flags are: (F)IN, (S)YN, (R)ST, (P)USH, (A)CK, (U)RG, (E)CE, and C(W)R. .Bl -tag -width Fl @@ -1687,13 +1689,14 @@ pass all tos 0x10 pass all tos 16 .Ed .It Ar allow-opts -By default, packets which contain IP options are blocked. +By default, IPv4 packets with IP options or IPv6 packets with routing +extension headers are blocked. When .Ar allow-opts is specified for a .Ar pass rule, packets that pass the filter based on that rule (last matching) -do so even if they contain IP options. +do so even if they contain IP options or routing extension headers. For packets that match state, the rule that initially created the state is used. The implicit @@ -1914,7 +1917,7 @@ pool options. Note that by default these associations are destroyed as soon as there are no longer states which refer to them; in order to make the mappings last beyond the lifetime of the states, increase the global options with -.Ar set timeout source-track +.Ar set timeout src.track . See .Sx STATEFUL TRACKING OPTIONS for more ways to control the source tracking. @@ -2759,7 +2762,7 @@ option = "set" ( [ "timeout" ( timeout | "{" timeout-list "}" ) ] | [ "state-policy" ( "if-bound" | "floating" ) ] [ "require-order" ( "yes" | "no" ) ] [ "fingerprints" filename ] | - [ "skip on" ( interface-name | "{" interface-list "}" ) ] | + [ "skip on" ifspec ] | [ "debug" ( "none" | "urgent" | "misc" | "loud" ) ] ) pf-rule = action [ ( "in" | "out" ) ] @@ -2801,8 +2804,7 @@ rdr-rule = [ "no" ] "rdr" [ "pass" [ "log" [ "(" logopts ")" ] ] ] [ portspec ] [ pooltype ] ] antispoof-rule = "antispoof" [ "log" ] [ "quick" ] - "for" ( interface-name | "{" interface-list "}" ) - [ af ] [ "label" string ] + "for" ifspec [ af ] [ "label" string ] table-rule = "table" "\*(Lt" string "\*(Gt" [ tableopts-list ] tableopts-list = tableopts-list tableopts | tableopts @@ -2810,8 +2812,8 @@ tableopts = "persist" | "const" | "file" string | "{" [ tableaddr-list ] "}" tableaddr-list = tableaddr-list [ "," ] tableaddr-spec | tableaddr-spec tableaddr-spec = [ "!" ] tableaddr [ "/" mask-bits ] -tableaddr = hostname | ipv4-dotted-quad | ipv6-coloned-hex | - interface-name | "self" +tableaddr = hostname | ifspec | "self" | + ipv4-dotted-quad | ipv6-coloned-hex altq-rule = "altq on" interface-name queueopts-list "queue" subqueue @@ -2842,8 +2844,10 @@ return = "drop" | "return" | "return-rst" [ "( ttl" number ")" ] | icmpcode = ( icmp-code-name | icmp-code-number ) icmp6code = ( icmp6-code-name | icmp6-code-number ) -ifspec = ( [ "!" ] interface-name ) | "{" interface-list "}" -interface-list = [ "!" ] interface-name [ [ "," ] interface-list ] +ifspec = ( [ "!" ] ( interface-name | interface-group ) ) | + "{" interface-list "}" +interface-list = [ "!" ] ( interface-name | interface-group ) + [ [ "," ] interface-list ] route = ( "route-to" | "reply-to" | "dup-to" ) ( routehost | "{" routehost-list "}" ) [ pooltype ] @@ -2863,8 +2867,9 @@ ipspec = "any" | host | "{" host-list "}" host = [ "!" ] ( address [ "/" mask-bits ] | "\*(Lt" string "\*(Gt" ) redirhost = address [ "/" mask-bits ] routehost = "(" interface-name [ address [ "/" mask-bits ] ] ")" -address = ( interface-name | "(" interface-name ")" | hostname | - ipv4-dotted-quad | ipv6-coloned-hex ) +address = ( interface-name | interface-group | + "(" ( interface-name | interface-group ) ")" | + hostname | ipv4-dotted-quad | ipv6-coloned-hex ) host-list = host [ [ "," ] host-list ] redirhost-list = redirhost [ [ "," ] redirhost-list ] routehost-list = routehost [ [ "," ] routehost-list ] diff --git a/man/pf.os.5 b/man/pf.os.5 index 69e8344885e..7ee63ce52f4 100644 --- a/man/pf.os.5 +++ b/man/pf.os.5 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pf.os.5,v 1.7 2005/11/16 20:07:18 stevesk Exp $ +.\" $OpenBSD: pf.os.5,v 1.8 2007/05/31 19:19:58 jmc Exp $ .\" .\" Copyright (c) 2003 Mike Frantzen .\" @@ -13,7 +13,7 @@ .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN .\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF .\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. -.Dd August 18, 2003 +.Dd $Mdocdate$ .Dt PF.OS 5 .Os .Sh NAME diff --git a/man/pflog.4 b/man/pflog.4 index 2b2e22b8877..1b42a83f437 100644 --- a/man/pflog.4 +++ b/man/pflog.4 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pflog.4,v 1.9 2006/10/25 12:51:31 jmc Exp $ +.\" $OpenBSD: pflog.4,v 1.10 2007/05/31 19:19:51 jmc Exp $ .\" .\" Copyright (c) 2001 Tobias Weingartner .\" All rights reserved. @@ -23,7 +23,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.Dd December 10, 2001 +.Dd $Mdocdate$ .Dt PFLOG 4 .Os .Sh NAME diff --git a/man/pfsync.4 b/man/pfsync.4 index 43f13b2f30c..07f61874b6d 100644 --- a/man/pfsync.4 +++ b/man/pfsync.4 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pfsync.4,v 1.24 2006/10/23 07:05:49 jmc Exp $ +.\" $OpenBSD: pfsync.4,v 1.25 2007/05/31 19:19:51 jmc Exp $ .\" .\" Copyright (c) 2002 Michael Shalayeff .\" Copyright (c) 2003-2004 Ryan McBride @@ -24,7 +24,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.Dd November 29, 2002 +.Dd $Mdocdate$ .Dt PFSYNC 4 .Os .Sh NAME diff --git a/pfctl/Makefile b/pfctl/Makefile new file mode 100644 index 00000000000..df74f88c63f --- /dev/null +++ b/pfctl/Makefile @@ -0,0 +1,18 @@ +# $OpenBSD: Makefile,v 1.19 2006/12/24 18:52:43 miod Exp $ + +PROG= pfctl +SRCS= pfctl.c parse.y pfctl_parser.c pf_print_state.c pfctl_altq.c +SRCS+= pfctl_osfp.c pfctl_radix.c pfctl_table.c pfctl_qstats.c +SRCS+= pfctl_optimize.c pf_ruleset.c +CFLAGS+= -Wall -Wmissing-prototypes -Wno-uninitialized +CFLAGS+= -Wstrict-prototypes -I${.CURDIR} +YFLAGS= +MAN= pfctl.8 + +# Ruleset and Anchor handling +.PATH: ${.CURDIR}/../../sys/net + +LDADD+= -lm +DPADD+= ${LIBM} + +.include diff --git a/pfctl/parse.y b/pfctl/parse.y index ef5d77b6ec4..a491f3ead7d 100644 --- a/pfctl/parse.y +++ b/pfctl/parse.y @@ -1,4 +1,4 @@ -/* $OpenBSD: parse.y,v 1.517 2007/02/03 23:26:40 dhartmei Exp $ */ +/* $OpenBSD: parse.y,v 1.519 2007/06/21 19:30:03 henning Exp $ */ /* * Copyright (c) 2001 Markus Friedl. All rights reserved. @@ -425,7 +425,7 @@ typedef struct { %type tos not yesno %type no dir af fragcache optimizer %type sourcetrack flush unaryop statelock -%type action nataction natpass scrubaction +%type action nataction natpasslog scrubaction %type flags flag blockspec %type port rport %type hashkey @@ -3439,12 +3439,13 @@ redirection : /* empty */ { $$ = NULL; } } ; -natpass : /* empty */ { $$.b1 = $$.b2 = 0; } - | PASS { $$.b1 = 1; $$.b2 = 0; } +natpasslog : /* empty */ { $$.b1 = $$.b2 = 0; $$.w2 = 0; } + | PASS { $$.b1 = 1; $$.b2 = 0; $$.w2 = 0; } | PASS log { $$.b1 = 1; $$.b2 = $2.log; $$.w2 = $2.logif; } + | log { $$.b1 = 0; $$.b2 = $1.log; $$.w2 = $1.logif; } ; -nataction : no NAT natpass { +nataction : no NAT natpasslog { if ($1 && $3.b1) { yyerror("\"pass\" not valid with \"no\""); YYERROR; @@ -3457,7 +3458,7 @@ nataction : no NAT natpass { $$.w = $3.b2; $$.w2 = $3.w2; } - | no RDR natpass { + | no RDR natpasslog { if ($1 && $3.b1) { yyerror("\"pass\" not valid with \"no\""); YYERROR; @@ -3631,7 +3632,7 @@ natrule : nataction interface af proto fromto tag tagged rtable } ; -binatrule : no BINAT natpass interface af proto FROM host TO ipspec tag +binatrule : no BINAT natpasslog interface af proto FROM host TO ipspec tag tagged rtable redirection { struct pf_rule binat; diff --git a/pfctl/pf_print_state.c b/pfctl/pf_print_state.c index e36b1fd94bf..e4830a1268f 100644 --- a/pfctl/pf_print_state.c +++ b/pfctl/pf_print_state.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pf_print_state.c,v 1.44 2007/03/01 17:20:53 deraadt Exp $ */ +/* $OpenBSD: pf_print_state.c,v 1.45 2007/05/31 04:13:37 mcbride Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -151,7 +151,7 @@ print_name(struct pf_addr *addr, sa_family_t af) } void -print_host(struct pf_state_host *h, sa_family_t af, int opts) +print_host(struct pfsync_state_host *h, sa_family_t af, int opts) { u_int16_t p = ntohs(h->port); @@ -180,7 +180,7 @@ print_host(struct pf_state_host *h, sa_family_t af, int opts) } void -print_seq(struct pf_state_peer *p) +print_seq(struct pfsync_state_peer *p) { if (p->seqdiff) printf("[%u + %u](+%u)", p->seqlo, p->seqhi - p->seqlo, @@ -190,9 +190,9 @@ print_seq(struct pf_state_peer *p) } void -print_state(struct pf_state *s, int opts) +print_state(struct pfsync_state *s, int opts) { - struct pf_state_peer *src, *dst; + struct pfsync_state_peer *src, *dst; struct protoent *p; int min, sec; @@ -203,7 +203,7 @@ print_state(struct pf_state *s, int opts) src = &s->dst; dst = &s->src; } - printf("%s ", s->u.ifname); + printf("%s ", s->ifname); if ((p = getprotobynumber(s->proto)) != NULL) printf("%s ", p->p_name); else @@ -278,20 +278,23 @@ print_state(struct pf_state *s, int opts) s->expire /= 60; printf(", expires in %.2u:%.2u:%.2u", s->expire, min, sec); printf(", %llu:%llu pkts, %llu:%llu bytes", - s->packets[0], s->packets[1], s->bytes[0], s->bytes[1]); - if (s->anchor.nr != -1) - printf(", anchor %u", s->anchor.nr); - if (s->rule.nr != -1) - printf(", rule %u", s->rule.nr); - if (s->src_node != NULL) + pf_state_counter_from_pfsync(s->packets[0]), + pf_state_counter_from_pfsync(s->packets[1]), + pf_state_counter_from_pfsync(s->bytes[0]), + pf_state_counter_from_pfsync(s->bytes[1])); + if (s->anchor != -1) + printf(", anchor %u", s->anchor); + if (s->rule != -1) + printf(", rule %u", s->rule); + if (s->sync_flags & PFSYNC_FLAG_SRCNODE) printf(", source-track"); - if (s->nat_src_node != NULL) + if (s->sync_flags & PFSYNC_FLAG_NATSRCNODE) printf(", sticky-address"); printf("\n"); } if (opts & PF_OPT_VERBOSE2) { printf(" id: %016llx creatorid: %08x%s\n", - betoh64(s->id), ntohl(s->creatorid), + pf_state_counter_from_pfsync(s->id), ntohl(s->creatorid), ((s->sync_flags & PFSTATE_NOSYNC) ? " (no-sync)" : "")); } } diff --git a/pfctl/pfctl.8 b/pfctl/pfctl.8 index b5be8a1f624..4dfbc407aae 100644 --- a/pfctl/pfctl.8 +++ b/pfctl/pfctl.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pfctl.8,v 1.128 2007/01/30 21:01:56 jmc Exp $ +.\" $OpenBSD: pfctl.8,v 1.133 2007/07/01 11:38:51 henning Exp $ .\" .\" Copyright (c) 2001 Kjell Wooding. All rights reserved. .\" @@ -24,7 +24,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.Dd November 20, 2002 +.Dd $Mdocdate: May 31 2007 $ .Dt PFCTL 8 .Os .Sh NAME @@ -42,14 +42,14 @@ .Op Fl i Ar interface .Op Fl K Ar host | network .Op Fl k Ar host | network -.Op Fl o Op Ar level +.Op Fl o Ar level .Op Fl p Ar device .Op Fl s Ar modifier -.Oo -.Fl t Ar table +.Xo +.Oo Fl t Ar table .Fl T Ar command -.Op Ar address ... -.Oc +.Op Ar address ... Oc +.Xc .Op Fl x Ar level .Ek .Sh DESCRIPTION @@ -209,7 +209,7 @@ Flush the NAT rules. Flush the queue rules. .It Fl F Cm rules Flush the filter rules. -.It Fl F Cm state +.It Fl F Cm states Flush the state table (NAT and filter). .It Fl F Cm Sources Flush the source tracking table. @@ -296,58 +296,20 @@ Do not actually load rules, just parse them. .It Fl O Load only the options present in the rule file. Other rules and options are ignored. -.It Fl o Op Ar level -Control the ruleset optimizer. -The ruleset optimizer attempts to improve rulesets by removing rule -duplication and making better use of rule ordering. +.It Fl o Ar level +Control the ruleset optimizer, overriding any rule file settings. .Pp .Bl -tag -width xxxxxxxxxxxx -compact .It Fl o Cm none Disable the ruleset optimizer. .It Fl o Cm basic Enable basic ruleset optimizations. +This is the default behaviour. .It Fl o Cm profile Enable basic ruleset optimizations with profiling. .El -.Pp -.Cm basic -optimization does does four things: -.Pp -.Bl -enum -compact -.It -remove duplicate rules -.It -remove rules that are a subset of another rule -.It -combine multiple rules into a table when advantageous -.It -re-order the rules to improve evaluation performance -.El -.Pp -If -.Cm profile -is specified, the currently loaded ruleset will be examined as a feedback -profile to tailor the optimization of the -.Ar quick -rules to the actual network behavior. -.Pp -It is important to note that the ruleset optimizer will modify the ruleset -to improve performance. -A side effect of the ruleset modification is that per-rule accounting -statistics will have different meanings than before. -If per-rule accounting is important for billing purposes or whatnot, either -the ruleset optimizer should not be used or a -.Ar label -field should be added to all of the accounting rules to act as optimization -barriers. -.Pp -To retain compatibility with previous behaviour, a single -.Fl o -without any options will enable -.Cm basic -optimizations, and a second -.Fl o -will enable profiling. +For further information on the ruleset optimizer, see +.Xr pf.conf 5 . .It Fl p Ar device Use the device file .Ar device @@ -402,7 +364,7 @@ If .Fl v is specified, all anchors attached under the target anchor will be displayed recursively. -.It Fl s Cm state +.It Fl s Cm states Show the contents of the state table. .It Fl s Cm Sources Show the contents of the source tracking table. diff --git a/pfctl/pfctl.c b/pfctl/pfctl.c index cf338c7d40b..0aeb0fc7807 100644 --- a/pfctl/pfctl.c +++ b/pfctl/pfctl.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl.c,v 1.262 2007/03/01 17:20:53 deraadt Exp $ */ +/* $OpenBSD: pfctl.c,v 1.268 2007/06/30 18:25:08 henning Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -201,11 +201,11 @@ static const struct { static const char *clearopt_list[] = { "nat", "queue", "rules", "Sources", - "state", "info", "Tables", "osfp", "all", NULL + "states", "info", "Tables", "osfp", "all", NULL }; static const char *showopt_list[] = { - "nat", "queue", "rules", "Anchors", "Sources", "state", "info", + "nat", "queue", "rules", "Anchors", "Sources", "states", "info", "Interfaces", "labels", "timeouts", "memory", "Tables", "osfp", "all", NULL }; @@ -220,7 +220,7 @@ static const char *debugopt_list[] = { }; static const char *optiopt_list[] = { - "o", "none", "basic", "profile", NULL + "none", "basic", "profile", NULL }; void @@ -231,8 +231,8 @@ usage(void) fprintf(stderr, "usage: %s [-AdeghmNnOqRrvz] ", __progname); fprintf(stderr, "[-a anchor] [-D macro=value] [-F modifier]\n"); fprintf(stderr, "\t[-f file] [-i interface] [-K host | network] "); - fprintf(stderr, "[-k host | network ]\n"); - fprintf(stderr, "\t[-o [level]] [-p device] [-s modifier ]\n"); + fprintf(stderr, "[-k host | network]\n"); + fprintf(stderr, "\t[-o level] [-p device] [-s modifier]\n"); fprintf(stderr, "\t[-t table -T command [address ...]] [-x level]\n"); exit(1); } @@ -998,7 +998,7 @@ int pfctl_show_states(int dev, const char *iface, int opts) { struct pfioc_states ps; - struct pf_state *p; + struct pfsync_state *p; char *inbuf = NULL, *newinbuf = NULL; unsigned len = 0; int i, dotitle = (opts & PF_OPT_SHOWALL); @@ -1029,7 +1029,7 @@ pfctl_show_states(int dev, const char *iface, int opts) } p = ps.ps_states; for (i = 0; i < ps.ps_len; i += sizeof(*p), p++) { - if (iface != NULL && strcmp(p->u.ifname, iface)) + if (iface != NULL && strcmp(p->ifname, iface)) continue; if (dotitle) { pfctl_print_title("STATES:"); @@ -1954,7 +1954,7 @@ main(int argc, char *argv[]) int ch; int mode = O_RDONLY; int opts = 0; - int optimize = 0; + int optimize = PF_OPTIMIZE_BASIC; char anchorname[MAXPATHLEN]; char *path; FILE *fin = NULL; @@ -1963,7 +1963,7 @@ main(int argc, char *argv[]) usage(); while ((ch = getopt(argc, argv, - "a:AdD:eqf:F:ghi:k:K:mnNOo::p:rRs:t:T:vx:z")) != -1) { + "a:AdD:eqf:F:ghi:k:K:mnNOo:p:rRs:t:T:vx:z")) != -1) { switch (ch) { case 'a': anchoropt = optarg; @@ -2039,24 +2039,11 @@ main(int argc, char *argv[]) loadopt |= PFCTL_FLAG_FILTER; break; case 'o': - if (optarg) { - optiopt = pfctl_lookup_option(optarg, - optiopt_list); - if (optiopt == NULL) { - warnx("Unknown optimization '%s'", - optarg); - usage(); - } + optiopt = pfctl_lookup_option(optarg, optiopt_list); + if (optiopt == NULL) { + warnx("Unknown optimization '%s'", optarg); + usage(); } - if (opts & PF_OPT_OPTIMIZE) { - if (optiopt != NULL) { - warnx("Cannot specify -o multiple times" - "with optimizer level"); - usage(); - } - optimize |= PF_OPTIMIZE_PROFILE; - } - optimize |= PF_OPTIMIZE_BASIC; opts |= PF_OPT_OPTIMIZE; break; case 'O': diff --git a/pfctl/pfctl.h b/pfctl/pfctl.h index 9450a5586a0..49cf6e75ec7 100644 --- a/pfctl/pfctl.h +++ b/pfctl/pfctl.h @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl.h,v 1.40 2007/02/09 11:25:27 henning Exp $ */ +/* $OpenBSD: pfctl.h,v 1.41 2007/05/31 04:13:37 mcbride Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -112,9 +112,9 @@ struct pf_altq *pfaltq_lookup(const char *); char *rate2str(double); void print_addr(struct pf_addr_wrap *, sa_family_t, int); -void print_host(struct pf_state_host *, sa_family_t, int); -void print_seq(struct pf_state_peer *); -void print_state(struct pf_state *, int); +void print_host(struct pfsync_state_host *, sa_family_t, int); +void print_seq(struct pfsync_state_peer *); +void print_state(struct pfsync_state *, int); int unmask(struct pf_addr *, sa_family_t); int pfctl_cmdline_symset(char *); diff --git a/pfctl/pfctl_altq.c b/pfctl/pfctl_altq.c index b4faaa04464..b2397fcd078 100644 --- a/pfctl/pfctl_altq.c +++ b/pfctl/pfctl_altq.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_altq.c,v 1.91 2006/11/28 00:08:50 henning Exp $ */ +/* $OpenBSD: pfctl_altq.c,v 1.92 2007/05/27 05:15:17 claudio Exp $ */ /* * Copyright (c) 2002 @@ -1091,8 +1091,6 @@ getifspeed(char *ifname) ifr.ifr_data = (caddr_t)&ifrdat; if (ioctl(s, SIOCGIFDATA, (caddr_t)&ifr) == -1) err(1, "SIOCGIFDATA"); - if (shutdown(s, SHUT_RDWR) == -1) - err(1, "shutdown"); if (close(s)) err(1, "close"); return ((u_int32_t)ifrdat.ifi_baudrate); @@ -1112,8 +1110,6 @@ getifmtu(char *ifname) errx(1, "getifmtu: strlcpy"); if (ioctl(s, SIOCGIFMTU, (caddr_t)&ifr) == -1) err(1, "SIOCGIFMTU"); - if (shutdown(s, SHUT_RDWR) == -1) - err(1, "shutdown"); if (close(s)) err(1, "close"); if (ifr.ifr_mtu > 0) diff --git a/pflogd/Makefile b/pflogd/Makefile new file mode 100644 index 00000000000..377cad99635 --- /dev/null +++ b/pflogd/Makefile @@ -0,0 +1,11 @@ +# $OpenBSD: Makefile,v 1.7 2006/11/26 11:31:08 deraadt Exp $ + +CFLAGS+=-Wall -Wmissing-prototypes -Wshadow +LDADD+= -lpcap -lutil +DPADD+= ${LIBPCAP} ${LIBUTIL} + +PROG= pflogd +SRCS= pflogd.c privsep.c privsep_fdpass.c +MAN= pflogd.8 + +.include diff --git a/pflogd/pflogd.8 b/pflogd/pflogd.8 index cbb7802419e..4c5762b380b 100644 --- a/pflogd/pflogd.8 +++ b/pflogd/pflogd.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pflogd.8,v 1.32 2006/12/08 10:26:38 joel Exp $ +.\" $OpenBSD: pflogd.8,v 1.35 2007/05/31 19:19:47 jmc Exp $ .\" .\" Copyright (c) 2001 Can Erkin Acar. All rights reserved. .\" @@ -24,7 +24,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.Dd July 9, 2001 +.Dd $Mdocdate$ .Dt PFLOGD 8 .Os .Sh NAME @@ -32,12 +32,15 @@ .Nd packet filter logging daemon .Sh SYNOPSIS .Nm pflogd +.Bk -words .Op Fl Dx .Op Fl d Ar delay .Op Fl f Ar filename .Op Fl i Ar interface +.Op Fl p Ar pidfile .Op Fl s Ar snaplen .Op Ar expression +.Ek .Sh DESCRIPTION .Nm is a background daemon which reads packets logged by @@ -114,6 +117,14 @@ By default, .Nm will use .Ar pflog0 . +.It Fl p Ar pidfile +Writes a file containing the process ID of the program. +The file name has the form +.Pa /var/run/pidname.pid . +If the option is not given, +.Ar pidfile +defaults to +.Pa pflogd . .It Fl s Ar snaplen Analyze at most the first .Ar snaplen diff --git a/pflogd/pflogd.c b/pflogd/pflogd.c index 168deb12edd..cd7a273924a 100644 --- a/pflogd/pflogd.c +++ b/pflogd/pflogd.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pflogd.c,v 1.37 2006/10/26 13:34:47 jmc Exp $ */ +/* $OpenBSD: pflogd.c,v 1.45 2007/06/06 14:11:26 henning Exp $ */ /* * Copyright (c) 2001 Theo de Raadt @@ -34,6 +34,8 @@ #include #include #include +#include +#include #include #include #include @@ -42,6 +44,7 @@ #include #include #include +#include #include #include #include @@ -70,6 +73,7 @@ char *copy_argv(char * const *); void dump_packet(u_char *, const struct pcap_pkthdr *, const u_char *); void dump_packet_nobuf(u_char *, const struct pcap_pkthdr *, const u_char *); int flush_buffer(FILE *); +int if_exists(char *); int init_pcap(void); void logmsg(int, const char *, ...); void purge_buffer(void); @@ -151,8 +155,8 @@ __dead void usage(void) { fprintf(stderr, "usage: pflogd [-Dx] [-d delay] [-f filename]"); - fprintf(stderr, " [-i interface] [-s snaplen]\n"); - fprintf(stderr, " [expression]\n"); + fprintf(stderr, " [-i interface] [-p pidfile]\n"); + fprintf(stderr, " [-s snaplen] [expression]\n"); exit(1); } @@ -188,6 +192,28 @@ set_pcap_filter(void) } } +int +if_exists(char *ifname) +{ + int s; + struct ifreq ifr; + struct if_data ifrdat; + + if ((s = socket(AF_INET, SOCK_DGRAM, 0)) == -1) + err(1, "socket"); + bzero(&ifr, sizeof(ifr)); + if (strlcpy(ifr.ifr_name, ifname, sizeof(ifr.ifr_name)) >= + sizeof(ifr.ifr_name)) + errx(1, "main ifr_name: strlcpy"); + ifr.ifr_data = (caddr_t)&ifrdat; + if (ioctl(s, SIOCGIFDATA, (caddr_t)&ifr) == -1) + return (0); + if (close(s)) + err(1, "close"); + + return (1); +} + int init_pcap(void) { @@ -528,13 +554,16 @@ int main(int argc, char **argv) { struct pcap_stat pstat; - int ch, np, Xflag = 0; + int ch, np, ret, Xflag = 0; pcap_handler phandler = dump_packet; const char *errstr = NULL; + char *pidf = NULL; + + ret = 0; closefrom(STDERR_FILENO + 1); - while ((ch = getopt(argc, argv, "Dxd:f:i:s:")) != -1) { + while ((ch = getopt(argc, argv, "Dxd:f:i:p:s:")) != -1) { switch (ch) { case 'D': Debug = 1; @@ -550,6 +579,9 @@ main(int argc, char **argv) case 'i': interface = optarg; break; + case 'p': + pidf = optarg; + break; case 's': snaplen = strtonum(optarg, 0, PFLOGD_MAXSNAPLEN, &errstr); @@ -571,13 +603,21 @@ main(int argc, char **argv) argc -= optind; argv += optind; + /* does interface exist */ + if (!if_exists(interface)) { + warn("Failed to initialize: %s", interface); + logmsg(LOG_ERR, "Failed to initialize: %s", interface); + logmsg(LOG_ERR, "Exiting, init failure"); + exit(1); + } + if (!Debug) { openlog("pflogd", LOG_PID | LOG_CONS, LOG_DAEMON); if (daemon(0, 0)) { logmsg(LOG_WARNING, "Failed to become daemon: %s", strerror(errno)); } - pidfile(NULL); + pidfile(pidf); } tzset(); @@ -634,8 +674,15 @@ main(int argc, char **argv) while (1) { np = pcap_dispatch(hpcap, PCAP_NUM_PKTS, phandler, (u_char *)dpcap); - if (np < 0) + if (np < 0) { + if (!if_exists(interface) == -1) { + logmsg(LOG_NOTICE, "interface %s went away", + interface); + ret = -1; + break; + } logmsg(LOG_NOTICE, "%s", pcap_geterr(hpcap)); + } if (gotsig_close) break; @@ -675,5 +722,5 @@ main(int argc, char **argv) pcap_close(hpcap); if (!Debug) closelog(); - return (0); + return (ret); } diff --git a/pflogd/pidfile.c b/pflogd/pidfile.c deleted file mode 100644 index 61eca262efe..00000000000 --- a/pflogd/pidfile.c +++ /dev/null @@ -1,121 +0,0 @@ -/* $OpenBSD: pidfile.c,v 1.5 2002/05/26 09:29:02 deraadt Exp $ */ -/* $NetBSD: pidfile.c,v 1.4 2001/02/19 22:43:42 cgd Exp $ */ - -/*- - * Copyright (c) 1999 The NetBSD Foundation, Inc. - * All rights reserved. - * - * This code is derived from software contributed to The NetBSD Foundation - * by Jason R. Thorpe. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. All advertising materials mentioning features or use of this software - * must display the following acknowledgement: - * This product includes software developed by the NetBSD - * Foundation, Inc. and its contributors. - * 4. Neither the name of The NetBSD Foundation nor the names of its - * contributors may be used to endorse or promote products derived - * from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS - * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED - * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS - * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF - * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS - * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN - * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGE. - */ - -#if defined(LIBC_SCCS) && !defined(lint) -static const char rcsid[] = "$OpenBSD: pidfile.c,v 1.5 2002/05/26 09:29:02 deraadt Exp $"; -#endif /* LIBC_SCCS and not lint */ - -#include -#include -#include -#include -#include -#include -#if defined(__FreeBSD__) -#include "pidfile.h" -#else -#include -#endif - -static char *pidfile_path; -static pid_t pidfile_pid; - -static void pidfile_cleanup(void); - -extern char *__progname; - -int -pidfile(const char *basename) -{ - FILE *f; - int save_errno; - pid_t pid; - - if (basename == NULL) - basename = __progname; - - if (pidfile_path != NULL) { - free(pidfile_path); - pidfile_path = NULL; - } - - /* _PATH_VARRUN includes trailing / */ - (void) asprintf(&pidfile_path, "%s%s.pid", _PATH_VARRUN, basename); - if (pidfile_path == NULL) - return (-1); - - if ((f = fopen(pidfile_path, "w")) == NULL) { - save_errno = errno; - free(pidfile_path); - pidfile_path = NULL; - errno = save_errno; - return (-1); - } - - pid = getpid(); - if (fprintf(f, "%ld\n", (long)pid) <= 0 || fclose(f) != 0) { - save_errno = errno; - (void) unlink(pidfile_path); - free(pidfile_path); - pidfile_path = NULL; - errno = save_errno; - return (-1); - } - - pidfile_pid = pid; - if (atexit(pidfile_cleanup) < 0) { - save_errno = errno; - (void) unlink(pidfile_path); - free(pidfile_path); - pidfile_path = NULL; - pidfile_pid = 0; - errno = save_errno; - return (-1); - } - - return (0); -} - -static void -pidfile_cleanup(void) -{ - - if (pidfile_path != NULL && pidfile_pid == getpid()) - (void) unlink(pidfile_path); -} diff --git a/pflogd/pidfile.h b/pflogd/pidfile.h deleted file mode 100644 index 542325fdcda..00000000000 --- a/pflogd/pidfile.h +++ /dev/null @@ -1 +0,0 @@ -int pidfile(const char *); diff --git a/tftp-proxy/Makefile b/tftp-proxy/Makefile new file mode 100644 index 00000000000..b5f4eefc089 --- /dev/null +++ b/tftp-proxy/Makefile @@ -0,0 +1,7 @@ +# $OpenBSD: Makefile,v 1.1 2005/12/28 19:07:07 jcs Exp $ + +PROG= tftp-proxy +SRCS= tftp-proxy.c filter.c +MAN= tftp-proxy.8 + +.include diff --git a/tftp-proxy/filter.c b/tftp-proxy/filter.c index cd6ce3cd1e7..61b3a1756bb 100644 --- a/tftp-proxy/filter.c +++ b/tftp-proxy/filter.c @@ -1,4 +1,4 @@ -/* $OpenBSD: filter.c,v 1.1 2005/12/28 19:07:07 jcs Exp $ */ +/* $OpenBSD: filter.c,v 1.2 2007/06/23 15:51:21 jcs Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, @@ -297,9 +297,9 @@ prepare_rule(u_int32_t id, int rs_num, struct sockaddr *src, pfr.rule.quick = 1; pfr.rule.log = rule_log; pfr.rule.keep_state = 1; - pfr.rule.flags = (proto == IPPROTO_TCP ? TH_SYN : NULL); + pfr.rule.flags = (proto == IPPROTO_TCP ? TH_SYN : 0); pfr.rule.flagset = (proto == IPPROTO_TCP ? - (TH_SYN|TH_ACK|TH_FIN|TH_RST) : NULL); + (TH_SYN|TH_ACK|TH_FIN|TH_RST) : 0); pfr.rule.max_states = 1; if (qname != NULL) strlcpy(pfr.rule.qname, qname, sizeof pfr.rule.qname); diff --git a/tftp-proxy/tftp-proxy.8 b/tftp-proxy/tftp-proxy.8 index b9098ef4d17..511b641bce3 100644 --- a/tftp-proxy/tftp-proxy.8 +++ b/tftp-proxy/tftp-proxy.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: tftp-proxy.8,v 1.1 2005/12/28 19:07:07 jcs Exp $ +.\" $OpenBSD: tftp-proxy.8,v 1.2 2007/05/31 19:19:41 jmc Exp $ .\" .\" Copyright (c) 2005 joshua stein .\" @@ -25,7 +25,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.Dd November 28, 2005 +.Dd $Mdocdate$ .Dt TFTP-PROXY 8 .Os .Sh NAME From a13f3058fbd67e3bbda784171bacc8343faf6edf Mon Sep 17 00:00:00 2001 From: Max Laier Date: Wed, 10 Dec 2008 20:59:26 +0000 Subject: [PATCH 04/39] Import OPENBSD_4_3_BASE --- authpf/Makefile | 6 +- authpf/authpf.8 | 105 ++-- authpf/authpf.c | 227 +++++---- authpf/pathnames.h | 3 +- ftp-proxy/filter.c | 13 +- ftp-proxy/ftp-proxy.8 | 24 +- ftp-proxy/ftp-proxy.c | 5 +- man/pf.4 | 17 +- man/pf.conf.5 | 53 ++- man/pfsync.4 | 8 +- pfctl/parse.y | 1028 +++++++++++++++++++++++++++------------- pfctl/pf_print_state.c | 18 +- pfctl/pfctl.c | 39 +- pfctl/pfctl.h | 5 +- pfctl/pfctl_altq.c | 13 +- pfctl/pfctl_optimize.c | 13 +- pfctl/pfctl_parser.c | 4 +- pfctl/pfctl_parser.h | 6 +- pfctl/pfctl_qstats.c | 6 +- pfctl/pfctl_radix.c | 51 +- pflogd/pflogd.8 | 15 +- 21 files changed, 1064 insertions(+), 595 deletions(-) diff --git a/authpf/Makefile b/authpf/Makefile index 3e0538a8d23..100001a0a74 100644 --- a/authpf/Makefile +++ b/authpf/Makefile @@ -1,7 +1,11 @@ -# $OpenBSD: Makefile,v 1.12 2004/04/25 19:24:52 deraadt Exp $ +# $OpenBSD: Makefile,v 1.13 2008/02/14 01:49:17 mcbride Exp $ PROG= authpf MAN= authpf.8 + +LINKS= ${BINDIR}/authpf ${BINDIR}/authpf-noip +MLINKS+=authpf.8 authpf-noip.8 + BINOWN= root BINGRP= authpf BINMODE= 6555 diff --git a/authpf/authpf.8 b/authpf/authpf.8 index 566d3a9627c..be1f0c46fde 100644 --- a/authpf/authpf.8 +++ b/authpf/authpf.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: authpf.8,v 1.44 2007/05/31 19:20:22 jmc Exp $ +.\" $OpenBSD: authpf.8,v 1.45 2008/02/14 01:49:17 mcbride Exp $ .\" .\" Copyright (c) 1998-2007 Bob Beck (beck@openbsd.org>. All rights reserved. .\" @@ -14,14 +14,16 @@ .\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF .\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .\" -.Dd $Mdocdate$ +.Dd $Mdocdate: May 31 2007 $ .Dt AUTHPF 8 .Os .Sh NAME -.Nm authpf +.Nm authpf , +.Nm authpf-noip .Nd authenticating gateway user shell .Sh SYNOPSIS .Nm authpf +.Nm authpf-noip .Sh DESCRIPTION .Nm is a user shell for authenticating gateways. @@ -30,43 +32,63 @@ It is used to change rules when a user authenticates and starts a session with .Xr sshd 8 and to undo these changes when the user's session exits. -It is designed for changing filter and translation rules for an individual -source IP address as long as a user maintains an active -.Xr ssh 1 -session. Typical use would be for a gateway that authenticates users before allowing them Internet use, or a gateway that allows different users into different places. +Combined with properly set up filter rules and secure switches, .Nm -logs the successful start and end of a session to -.Xr syslogd 8 . -This, combined with properly set up filter rules and secure switches, can be used to ensure users are held accountable for their network traffic. -.Pp -.Nm -can add filter and translation rules using the syntax described in -.Xr pf.conf 5 . -.Nm -requires that the -.Xr pf 4 -system be enabled before use. -.Nm -can also maintain the list of IP address of connected users -in the "authpf_users" -.Pa table . -.Pp -.Nm -is meant to be used with users who can connect via +It is meant to be used with users who can connect via .Xr ssh 1 -only. -On startup, +only, and requires the +.Xr pf 4 +subsystem to be enabled. +.Pp +.Nm authpf-noip +is a user shell +which allows multiple connections to take +place from the same IP address. +It is useful primarily in cases where connections are tunneled via +the gateway system, and can be directly associated with the user name. +It cannot ensure accountability when +classifying connections by IP address; +in this case the client's IP address +is not provided to the packet filter via the +.Ar client_ip +macro or the +.Ar authpf users +table. +Additionally, states associated with the client IP address +are not purged when the session is ended. +.Pp +To use either +.Nm +or +.Nm authpf-noip , +the user's shell needs to be set to +.Pa /usr/sbin/authpf +or +.Pa /usr/sbin/authpf-noip . +.Pp +.Nm +uses the +.Xr pf.conf 5 +syntax to change filter and translation rules for an individual +user or client IP address as long as a user maintains an active +.Xr ssh 1 +session, and logs the successful start and end of a session to +.Xr syslogd 8 . .Nm retrieves the client's connecting IP address via the .Ev SSH_CLIENT environment variable and, after performing additional access checks, reads a template file to determine what filter and translation rules -(if any) to add. -On session exit the same rules that were added at startup are removed. +(if any) to add, and +maintains the list of IP addresses of connected users in the +.Ar authpf_users +table. +On session exit the same rules and table entries that were added at startup +are removed, and all states associated with the client's IP address are purged. .Pp Each .Nm @@ -496,6 +518,31 @@ table persist anchor "authpf/*" from rdr-anchor "authpf/*" from .Ed +.Pp +.Sy Tunneled users +\- normally +.Nm +allows only one session per client IP address. +However in some cases, such as when connections are tunneled via +.Xr ssh 1 +or +.Xr ipsec 4 , +the connections can be authorized based on the userid of the user instead of +the client IP address. +In this case it is appropriate to use +.Nm authpf-noip +to allow multiple users behind a NAT gateway to connect. +In the +.Pa /etc/authpf/authpf.rules +example below, the remote user could tunnel a remote desktop session to their +workstation: +.Bd -literal +internal_if="bge0" +workstation_ip="10.2.3.4" + +pass out on $internal_if from (self) to $workstation_ip port 3389 \e + user $user_id +.Ed .Sh FILES .Bl -tag -width "/etc/authpf/authpf.conf" -compact .It Pa /etc/authpf/authpf.conf diff --git a/authpf/authpf.c b/authpf/authpf.c index 68adcd258ee..1416b0db917 100644 --- a/authpf/authpf.c +++ b/authpf/authpf.c @@ -1,4 +1,4 @@ -/* $OpenBSD: authpf.c,v 1.104 2007/02/24 17:35:08 beck Exp $ */ +/* $OpenBSD: authpf.c,v 1.107 2008/02/14 01:49:17 mcbride Exp $ */ /* * Copyright (C) 1998 - 2007 Bob Beck (beck@openbsd.org). @@ -46,6 +46,7 @@ static void print_message(char *); static int allowed_luser(char *); static int check_luser(char *, char *); static int remove_stale_rulesets(void); +static int recursive_ruleset_purge(char *, char *); static int change_filter(int, const char *, const char *); static int change_table(int, const char *); static void authpf_kill_states(void); @@ -54,6 +55,7 @@ int dev; /* pf device */ char anchorname[PF_ANCHOR_NAME_SIZE] = "authpf"; char rulesetname[MAXPATHLEN - PF_ANCHOR_NAME_SIZE - 2]; char tablename[PF_TABLE_NAME_SIZE] = "authpf_users"; +int user_ip = 1; /* controls whether $user_ip is set */ FILE *pidfp; char luser[MAXLOGNAME]; /* username */ @@ -65,6 +67,7 @@ struct timeval Tstart, Tend; /* start and end times of session */ volatile sig_atomic_t want_death; static void need_death(int signo); static __dead void do_death(int); +extern char *__progname; /* program name */ /* * User shell for authenticating gateways. Sole purpose is to allow @@ -85,6 +88,9 @@ main(int argc, char *argv[]) char *shell; login_cap_t *lc; + if (strcmp(__progname, "-authpf-noip") == 0) + user_ip = 0; + config = fopen(PATH_CONFFILE, "r"); if (config == NULL) { syslog(LOG_ERR, "can not open %s (%m)", PATH_CONFFILE); @@ -139,7 +145,8 @@ main(int argc, char *argv[]) login_close(lc); - if (strcmp(shell, PATH_AUTHPF_SHELL)) { + if (strcmp(shell, PATH_AUTHPF_SHELL) && + strcmp(shell, PATH_AUTHPF_SHELL_NOIP)) { syslog(LOG_ERR, "wrong shell for user %s, uid %u", pw->pw_name, pw->pw_uid); if (shell != pw->pw_shell) @@ -171,8 +178,9 @@ main(int argc, char *argv[]) } - /* Make our entry in /var/authpf as /var/authpf/ipaddr */ - n = snprintf(pidfile, sizeof(pidfile), "%s/%s", PATH_PIDFILE, ipsrc); + /* Make our entry in /var/authpf as ipaddr or username */ + n = snprintf(pidfile, sizeof(pidfile), "%s/%s", + PATH_PIDFILE, user_ip ? ipsrc : luser); if (n < 0 || (u_int)n >= sizeof(pidfile)) { syslog(LOG_ERR, "path to pidfile too long"); goto die; @@ -292,7 +300,7 @@ main(int argc, char *argv[]) printf("Unable to modify filters\r\n"); do_death(0); } - if (change_table(1, ipsrc) == -1) { + if (user_ip && change_table(1, ipsrc) == -1) { printf("Unable to modify table\r\n"); change_filter(0, luser, ipsrc); do_death(0); @@ -349,6 +357,8 @@ read_config(FILE *f) } i++; len = strlen(buf); + if (len == 0) + continue; if (buf[len - 1] != '\n' && !feof(f)) { syslog(LOG_ERR, "line %d too long in %s", i, PATH_CONFFILE); @@ -569,7 +579,7 @@ static int remove_stale_rulesets(void) { struct pfioc_ruleset prs; - u_int32_t nr, mnr; + u_int32_t nr; memset(&prs, 0, sizeof(prs)); strlcpy(prs.path, anchorname, sizeof(prs.path)); @@ -580,13 +590,12 @@ remove_stale_rulesets(void) return (1); } - mnr = prs.nr; - nr = 0; - while (nr < mnr) { + nr = prs.nr; + while (nr) { char *s, *t; pid_t pid; - prs.nr = nr; + prs.nr = nr - 1; if (ioctl(dev, DIOCGETRULESET, &prs)) return (1); errno = 0; @@ -598,111 +607,156 @@ remove_stale_rulesets(void) if (!prs.name[0] || errno || (*s && (t == prs.name || *s != ')'))) return (1); - if (kill(pid, 0) && errno != EPERM) { - int i; - struct pfioc_trans_e t_e[PF_RULESET_MAX+1]; - struct pfioc_trans t; - - bzero(&t, sizeof(t)); - bzero(t_e, sizeof(t_e)); - t.size = PF_RULESET_MAX+1; - t.esize = sizeof(t_e[0]); - t.array = t_e; - for (i = 0; i < PF_RULESET_MAX+1; ++i) { - t_e[i].rs_num = i; - snprintf(t_e[i].anchor, sizeof(t_e[i].anchor), - "%s/%s", anchorname, prs.name); - } - t_e[PF_RULESET_MAX].rs_num = PF_RULESET_TABLE; - if ((ioctl(dev, DIOCXBEGIN, &t) || - ioctl(dev, DIOCXCOMMIT, &t)) && - errno != EINVAL) + if ((kill(pid, 0) && errno != EPERM) || pid == getpid()) { + if (recursive_ruleset_purge(anchorname, prs.name)) return (1); - mnr--; - } else - nr++; + } + nr--; } return (0); } +static int +recursive_ruleset_purge(char *an, char *rs) +{ + struct pfioc_trans_e *t_e = NULL; + struct pfioc_trans *t = NULL; + struct pfioc_ruleset *prs = NULL; + int i; + + + /* purge rules */ + errno = 0; + if ((t = calloc(1, sizeof(struct pfioc_trans))) == NULL) + goto no_mem; + if ((t_e = calloc(PF_RULESET_MAX+1, + sizeof(struct pfioc_trans_e))) == NULL) + goto no_mem; + t->size = PF_RULESET_MAX+1; + t->esize = sizeof(struct pfioc_trans_e); + t->array = t_e; + for (i = 0; i < PF_RULESET_MAX+1; ++i) { + t_e[i].rs_num = i; + snprintf(t_e[i].anchor, sizeof(t_e[i].anchor), "%s/%s", an, rs); + } + t_e[PF_RULESET_MAX].rs_num = PF_RULESET_TABLE; + if ((ioctl(dev, DIOCXBEGIN, t) || + ioctl(dev, DIOCXCOMMIT, t)) && + errno != EINVAL) + goto cleanup; + + /* purge any children */ + if ((prs = calloc(1, sizeof(struct pfioc_ruleset))) == NULL) + goto no_mem; + snprintf(prs->path, sizeof(prs->path), "%s/%s", an, rs); + if (ioctl(dev, DIOCGETRULESETS, prs)) { + if (errno != EINVAL) + goto cleanup; + errno = 0; + } else { + int nr = prs->nr; + + while (nr) { + prs->nr = 0; + if (ioctl(dev, DIOCGETRULESET, prs)) + goto cleanup; + + if (recursive_ruleset_purge(prs->path, prs->name)) + goto cleanup; + nr--; + } + } + +no_mem: + if (errno == ENOMEM) + syslog(LOG_ERR, "calloc failed"); + +cleanup: + free(t); + free(t_e); + free(prs); + return (errno); +} + /* * Add/remove filter entries for user "luser" from ip "ipsrc" */ static int change_filter(int add, const char *luser, const char *ipsrc) { - char *pargv[13] = { - "pfctl", "-p", "/dev/pf", "-q", "-a", "anchor/ruleset", - "-D", "user_ip=X", "-D", "user_id=X", "-f", - "file", NULL - }; char *fdpath = NULL, *userstr = NULL, *ipstr = NULL; char *rsn = NULL, *fn = NULL; pid_t pid; gid_t gid; int s; - if (luser == NULL || !luser[0] || ipsrc == NULL || !ipsrc[0]) { - syslog(LOG_ERR, "invalid luser/ipsrc"); - goto error; - } - - if (asprintf(&rsn, "%s/%s", anchorname, rulesetname) == -1) - goto no_mem; - if (asprintf(&fdpath, "/dev/fd/%d", dev) == -1) - goto no_mem; - if (asprintf(&ipstr, "user_ip=%s", ipsrc) == -1) - goto no_mem; - if (asprintf(&userstr, "user_id=%s", luser) == -1) - goto no_mem; - if (add) { struct stat sb; + char *pargv[13] = { + "pfctl", "-p", "/dev/pf", "-q", "-a", "anchor/ruleset", + "-D", "user_id=X", "-D", "user_ip=X", "-f", "file", NULL + }; - if (asprintf(&fn, "%s/%s/authpf.rules", PATH_USER_DIR, luser) - == -1) + if (luser == NULL || !luser[0] || ipsrc == NULL || !ipsrc[0]) { + syslog(LOG_ERR, "invalid luser/ipsrc"); + goto error; + } + + if (asprintf(&rsn, "%s/%s", anchorname, rulesetname) == -1) + goto no_mem; + if (asprintf(&fdpath, "/dev/fd/%d", dev) == -1) + goto no_mem; + if (asprintf(&ipstr, "user_ip=%s", ipsrc) == -1) + goto no_mem; + if (asprintf(&userstr, "user_id=%s", luser) == -1) + goto no_mem; + if (asprintf(&fn, "%s/%s/authpf.rules", + PATH_USER_DIR, luser) == -1) goto no_mem; if (stat(fn, &sb) == -1) { free(fn); if ((fn = strdup(PATH_PFRULES)) == NULL) goto no_mem; } - } - pargv[2] = fdpath; - pargv[5] = rsn; - pargv[7] = userstr; - pargv[9] = ipstr; - if (!add) - pargv[11] = "/dev/null"; - else - pargv[11] = fn; - - switch (pid = fork()) { - case -1: - syslog(LOG_ERR, "fork failed"); - goto error; - case 0: - /* revoke group privs before exec */ - gid = getgid(); - if (setregid(gid, gid) == -1) { - err(1, "setregid"); + pargv[2] = fdpath; + pargv[5] = rsn; + pargv[7] = userstr; + if (user_ip) { + pargv[9] = ipstr; + pargv[11] = fn; + } else { + pargv[8] = "-f"; + pargv[9] = fn; + pargv[10] = NULL; } - execvp(PATH_PFCTL, pargv); - warn("exec of %s failed", PATH_PFCTL); - _exit(1); - } - /* parent */ - waitpid(pid, &s, 0); - if (s != 0) { - syslog(LOG_ERR, "pfctl exited abnormally"); - goto error; - } + switch (pid = fork()) { + case -1: + syslog(LOG_ERR, "fork failed"); + goto error; + case 0: + /* revoke group privs before exec */ + gid = getgid(); + if (setregid(gid, gid) == -1) { + err(1, "setregid"); + } + execvp(PATH_PFCTL, pargv); + warn("exec of %s failed", PATH_PFCTL); + _exit(1); + } + + /* parent */ + waitpid(pid, &s, 0); + if (s != 0) { + syslog(LOG_ERR, "pfctl exited abnormally"); + goto error; + } - if (add) { gettimeofday(&Tstart, NULL); syslog(LOG_INFO, "allowing %s, user %s", ipsrc, luser); } else { + remove_stale_rulesets(); + gettimeofday(&Tend, NULL); syslog(LOG_INFO, "removed %s, user %s - duration %ld seconds", ipsrc, luser, Tend.tv_sec - Tstart.tv_sec); @@ -819,9 +873,10 @@ do_death(int active) if (active) { change_filter(0, luser, ipsrc); - change_table(0, ipsrc); - authpf_kill_states(); - remove_stale_rulesets(); + if (user_ip) { + change_table(0, ipsrc); + authpf_kill_states(); + } } if (pidfile[0] && (pidfp != NULL)) if (unlink(pidfile) == -1) diff --git a/authpf/pathnames.h b/authpf/pathnames.h index 358bfd0c106..e02cf77c9fe 100644 --- a/authpf/pathnames.h +++ b/authpf/pathnames.h @@ -1,4 +1,4 @@ -/* $OpenBSD: pathnames.h,v 1.7 2004/04/25 18:40:42 beck Exp $ */ +/* $OpenBSD: pathnames.h,v 1.8 2008/02/14 01:49:17 mcbride Exp $ */ /* * Copyright (C) 2002 Chris Kuethe (ckuethe@ualberta.ca) @@ -35,4 +35,5 @@ #define PATH_DEVFILE "/dev/pf" #define PATH_PIDFILE "/var/authpf" #define PATH_AUTHPF_SHELL "/usr/sbin/authpf" +#define PATH_AUTHPF_SHELL_NOIP "/usr/sbin/authpf-noip" #define PATH_PFCTL "/sbin/pfctl" diff --git a/ftp-proxy/filter.c b/ftp-proxy/filter.c index b33c541457a..d99dfcbd6b1 100644 --- a/ftp-proxy/filter.c +++ b/ftp-proxy/filter.c @@ -1,4 +1,4 @@ -/* $OpenBSD: filter.c,v 1.6 2007/08/01 09:31:41 henning Exp $ */ +/* $OpenBSD: filter.c,v 1.7 2008/02/26 18:52:53 henning Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, @@ -277,15 +277,13 @@ prepare_rule(u_int32_t id, int rs_num, struct sockaddr *src, } pfr.rule.dst.port_op = PF_OP_EQ; pfr.rule.dst.port[0] = htons(d_port); - if (tagname != NULL) - strlcpy(pfr.rule.tagname, tagname, sizeof pfr.rule.tagname); switch (rs_num) { case PF_RULESET_FILTER: /* - * pass quick [log] inet[6] proto tcp \ + * pass [quick] [log] inet[6] proto tcp \ * from $src to $dst port = $d_port flags S/SA keep state - * (max 1) [queue qname] + * (max 1) [queue qname] [tag tagname] */ pfr.rule.action = PF_PASS; pfr.rule.quick = 1; @@ -296,6 +294,11 @@ prepare_rule(u_int32_t id, int rs_num, struct sockaddr *src, pfr.rule.max_states = 1; if (qname != NULL) strlcpy(pfr.rule.qname, qname, sizeof pfr.rule.qname); + if (tagname != NULL) { + pfr.rule.quick = 0; + strlcpy(pfr.rule.tagname, tagname, + sizeof pfr.rule.tagname); + } break; case PF_RULESET_NAT: /* diff --git a/ftp-proxy/ftp-proxy.8 b/ftp-proxy/ftp-proxy.8 index d48997b05a6..30a75415c18 100644 --- a/ftp-proxy/ftp-proxy.8 +++ b/ftp-proxy/ftp-proxy.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: ftp-proxy.8,v 1.10 2007/08/01 15:45:41 jmc Exp $ +.\" $OpenBSD: ftp-proxy.8,v 1.11 2008/02/26 18:52:53 henning Exp $ .\" .\" Copyright (c) 2004, 2005 Camiel Dobbelaar, .\" @@ -21,7 +21,7 @@ .Nm ftp-proxy .Nd Internet File Transfer Protocol proxy daemon .Sh SYNOPSIS -.Nm ftp-proxy +.Nm .Bk -words .Op Fl 6Adrv .Op Fl a Ar address @@ -59,7 +59,7 @@ facility for this. Assuming the FTP control connection is from $client to $server, the proxy connected to the server using the $proxy source address, and $port is negotiated, then -.Nm ftp-proxy +.Nm adds the following rules to the various anchors. (These example rules use inet, but the proxy also supports inet6.) .Pp @@ -132,9 +132,19 @@ connections to another proxy. Rewrite sourceport to 20 in active mode to suit ancient clients that insist on this RFC property. .It Fl T Ar tag -Automatically tag packets passing through the +The filter rules will add tag +.Ar tag +to data connections, and not match quick. +This way alternative rules that use the +.Ar tagged +keyword can be implemented following the +.Nm +anchor. +These rules can use special .Xr pf 4 -rule with the name supplied. +features like route-to, reply-to, label, rtable, overload, etc. that +.Nm +does not implement itself. .It Fl t Ar timeout Number of seconds that the control connection can be idle, before the proxy will disconnect. @@ -177,7 +187,7 @@ does not allow the ruleset to be modified if the system is running at a .Xr securelevel 7 higher than 1. At that level -.Nm ftp-proxy +.Nm cannot add rules to the anchors and FTP data connections may get blocked. .Pp Negotiated data connection ports below 1024 are not allowed. @@ -186,5 +196,5 @@ The negotiated IP address for active modes is ignored for security reasons. This makes third party file transfers impossible. .Pp -.Nm ftp-proxy +.Nm chroots to "/var/empty" and changes to user "proxy" to drop privileges. diff --git a/ftp-proxy/ftp-proxy.c b/ftp-proxy/ftp-proxy.c index 3a691859c32..1a3bdf55fbd 100644 --- a/ftp-proxy/ftp-proxy.c +++ b/ftp-proxy/ftp-proxy.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ftp-proxy.c,v 1.15 2007/08/15 15:18:02 camield Exp $ */ +/* $OpenBSD: ftp-proxy.c,v 1.16 2008/02/26 18:52:53 henning Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, @@ -1117,6 +1117,7 @@ usage(void) { fprintf(stderr, "usage: %s [-6Adrv] [-a address] [-b address]" " [-D level] [-m maxsessions]\n [-P port]" - " [-p port] [-q queue] [-R address] [-T tag] [-t timeout]\n", __progname); + " [-p port] [-q queue] [-R address] [-T tag]\n" + " [-t timeout]\n", __progname); exit(1); } diff --git a/man/pf.4 b/man/pf.4 index 3b6cec93ad4..ab9ad88f82c 100644 --- a/man/pf.4 +++ b/man/pf.4 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pf.4,v 1.59 2007/05/31 19:19:51 jmc Exp $ +.\" $OpenBSD: pf.4,v 1.60 2007/12/02 12:08:04 pascoe Exp $ .\" .\" Copyright (C) 2001, Kjell Wooding. All rights reserved. .\" @@ -26,7 +26,7 @@ .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF .\" SUCH DAMAGE. .\" -.Dd $Mdocdate$ +.Dd $Mdocdate: May 31 2007 $ .Dt PF 4 .Os .Sh NAME @@ -292,14 +292,17 @@ if another process is concurrently updating a ruleset. Add a state entry. .Bd -literal struct pfioc_state { - u_int32_t nr; - struct pf_state state; + struct pfsync_state state; }; .Ed .It Dv DIOCGETSTATE Fa "struct pfioc_state *ps" -Extract the entry with the specified number -.Va nr -from the state table. +Extract the entry identified by the +.Va id +and +.Va creatorid +fields of the +.Va state +structure from the state table. .It Dv DIOCKILLSTATES Fa "struct pfioc_state_kill *psk" Remove matching entries from the state table. This ioctl returns the number of killed states in diff --git a/man/pf.conf.5 b/man/pf.conf.5 index b6b609e733c..7624dc07405 100644 --- a/man/pf.conf.5 +++ b/man/pf.conf.5 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pf.conf.5,v 1.383 2007/07/17 16:27:38 jmc Exp $ +.\" $OpenBSD: pf.conf.5,v 1.393 2008/02/11 07:46:32 jmc Exp $ .\" .\" Copyright (c) 2002, Daniel Hartmeier .\" All rights reserved. @@ -27,7 +27,7 @@ .\" ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE .\" POSSIBILITY OF SUCH DAMAGE. .\" -.Dd $Mdocdate: June 26 2007 $ +.Dd $Mdocdate: Febuary 1 2008 $ .Dt PF.CONF 5 .Os .Sh NAME @@ -78,6 +78,17 @@ By default enforces this order (see .Ar set require-order below). +.Pp +Comments can be put anywhere in the file using a hash mark +.Pq Sq # , +and extend to the end of the current line. +.Pp +Additional configuration files can be included with the +.Ic include +keyword, for example: +.Bd -literal -offset indent +include "/etc/pf/sub.filter.conf" +.Ed .Sh MACROS Macros can be defined that will later be expanded in context. Macro names must start with a letter, and may contain letters, digits @@ -327,7 +338,8 @@ With 9000 state table entries, the timeout values are scaled to 50% (tcp.first 60, tcp.established 43200). .Pp .It Ar set loginterface -Enable collection of packet and byte count statistics for the given interface. +Enable collection of packet and byte count statistics for the given +interface or interface group. These statistics can be viewed using .Bd -literal -offset indent # pfctl -s info @@ -808,7 +820,7 @@ assigned. .Ar Priority mainly controls the time packets take to get sent out, while .Ar bandwidth -has primarily effects on throughput. +primarily affects throughput. .Ar hfsc supports both link-sharing and guaranteed real-time services. It employs a service curve based QoS model, @@ -1163,7 +1175,7 @@ or to the firewall itself. Note that redirecting external incoming connections to the loopback address, as in .Bd -literal -offset indent -rdr on ne3 inet proto tcp to port spamd -\*(Gt 127.0.0.1 port smtp +rdr on ne3 inet proto tcp to port smtp -\*(Gt 127.0.0.1 port spamd .Ed .Pp will effectively allow an external host to connect to daemons @@ -1442,6 +1454,14 @@ the route back to the packet's source address. Any address that matches the given table. .El .Pp +Ranges of addresses are specified by using the +.Sq - +operator. +For instance: +.Dq 10.1.1.10 - 10.1.1.12 +means all addresses from 10.1.1.10 to 10.1.1.12, +hence addresses 10.1.1.10, 10.1.1.11, and 10.1.1.12. +.Pp Interface names and interface group names can have modifiers appended: .Pp .Bl -tag -width xxxxxxxxxxxx -compact @@ -2023,8 +2043,8 @@ must be specified explicitly to apply options to a rule. .Bl -tag -width xxxx -compact .It Ar max Aq Ar number Limits the number of concurrent states the rule may create. -When this limit is reached, further packets matching the rule that would -create state are dropped, until existing states time out. +When this limit is reached, further packets that would create +state will not match this rule until existing states time out. .It Ar no-sync Prevent state changes for states created by this rule from appearing on the .Xr pfsync 4 @@ -2442,10 +2462,8 @@ into the anchor. .Pp Optionally, .Ar anchor -rules can specify the parameter's -direction, interface, address family, protocol and source/destination -address/port -using the same syntax as filter rules. +rules can specify packet filtering parameters using the same syntax as +filter rules. When parameters are used, the .Ar anchor rule is only evaluated for matching packets. @@ -2526,8 +2544,8 @@ anchor "external" on egress { .Ed .Pp Since the parser specification for anchor names is a string, any -reference to an anchor name containing solidus -.Pq Sq / +reference to an anchor name containing +.Sq / characters will require double quote .Pq Sq \&" characters around the anchor name. @@ -2749,10 +2767,11 @@ in BNF: .Bd -literal line = ( option | pf-rule | nat-rule | binat-rule | rdr-rule | antispoof-rule | altq-rule | queue-rule | trans-anchors | - anchor-rule | anchor-close | load-anchor | table-rule | ) + anchor-rule | anchor-close | load-anchor | table-rule | + include ) option = "set" ( [ "timeout" ( timeout | "{" timeout-list "}" ) ] | - [ "ruleset-optimization" [ "none" | "basic" | "profile" ]] | + [ "ruleset-optimization" [ "none" | "basic" | "profile" ]] | [ "optimization" [ "default" | "normal" | "high-latency" | "satellite" | "aggressive" | "conservative" ] ] @@ -2821,7 +2840,7 @@ queue-rule = "queue" string [ "on" interface-name ] queueopts-list subqueue anchor-rule = "anchor" [ string ] [ ( "in" | "out" ) ] [ "on" ifspec ] - [ af ] [ protospec ] [ hosts ] [ "{" ] + [ af ] [ protospec ] [ hosts ] [ filteropt-list ] [ "{" ] anchor-close = "}" @@ -2956,8 +2975,6 @@ Default location of OS fingerprints. Protocol name database. .It Pa /etc/services Service name database. -.It Pa /usr/share/pf -Example rulesets. .El .Sh SEE ALSO .Xr carp 4 , diff --git a/man/pfsync.4 b/man/pfsync.4 index 07f61874b6d..027d46014d1 100644 --- a/man/pfsync.4 +++ b/man/pfsync.4 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pfsync.4,v 1.25 2007/05/31 19:19:51 jmc Exp $ +.\" $OpenBSD: pfsync.4,v 1.26 2007/09/20 20:50:07 mpf Exp $ .\" .\" Copyright (c) 2002 Michael Shalayeff .\" Copyright (c) 2003-2004 Ryan McBride @@ -24,7 +24,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.Dd $Mdocdate$ +.Dd $Mdocdate: May 31 2007 $ .Dt PFSYNC 4 .Os .Sh NAME @@ -199,8 +199,8 @@ traffic through. The following should be added to the top of .Pa /etc/pf.conf : .Bd -literal -offset indent -pass quick on { sis2 } proto pfsync -pass on { sis0 sis1 } proto carp +pass quick on { sis2 } proto pfsync keep state (no-sync) +pass on { sis0 sis1 } proto carp keep state (no-sync) .Ed .Pp If it is preferable that one firewall handle the traffic, diff --git a/pfctl/parse.y b/pfctl/parse.y index a491f3ead7d..c4189963198 100644 --- a/pfctl/parse.y +++ b/pfctl/parse.y @@ -1,4 +1,4 @@ -/* $OpenBSD: parse.y,v 1.519 2007/06/21 19:30:03 henning Exp $ */ +/* $OpenBSD: parse.y,v 1.536 2008/02/01 06:58:45 mcbride Exp $ */ /* * Copyright (c) 2001 Markus Friedl. All rights reserved. @@ -29,6 +29,7 @@ %{ #include #include +#include #include #include #include @@ -43,6 +44,7 @@ #include #include +#include #include #include #include @@ -60,10 +62,7 @@ #include "pfctl.h" static struct pfctl *pf = NULL; -static FILE *fin = NULL; static int debug = 0; -static int lineno = 1; -static int errors = 0; static int rulestate = 0; static u_int16_t returnicmpdefault = (ICMP_UNREACH << 8) | ICMP_UNREACH_PORT; @@ -73,6 +72,39 @@ static int blockpolicy = PFRULE_DROP; static int require_order = 1; static int default_statelock; +TAILQ_HEAD(files, file) files = TAILQ_HEAD_INITIALIZER(files); +static struct file { + TAILQ_ENTRY(file) entry; + FILE *stream; + char *name; + int lineno; + int errors; +} *file; +struct file *pushfile(const char *, int); +int popfile(void); +int check_file_secrecy(int, const char *); +int yyparse(void); +int yylex(void); +int yyerror(const char *, ...); +int kw_cmp(const void *, const void *); +int lookup(char *); +int lgetc(int); +int lungetc(int); +int findeol(void); + +TAILQ_HEAD(symhead, sym) symhead = TAILQ_HEAD_INITIALIZER(symhead); +struct sym { + TAILQ_ENTRY(sym) entry; + int used; + int persist; + char *nam; + char *val; +}; +int symset(const char *, const char *, int); +char *symget(const char *); + +int atoul(char *, u_long *); + enum { PFCTL_STATE_NONE, PFCTL_STATE_OPTION, @@ -199,12 +231,12 @@ struct filter_opts { char *tag; char *match_tag; u_int8_t match_tag_not; - int rtableid; + u_int rtableid; } filter_opts; struct antispoof_opts { char *label; - int rtableid; + u_int rtableid; } antispoof_opts; struct scrub_opts { @@ -218,7 +250,7 @@ struct scrub_opts { int fragcache; int randomid; int reassemble_tcp; - int rtableid; + u_int rtableid; } scrub_opts; struct queue_opts { @@ -255,61 +287,42 @@ struct pool_opts { struct node_hfsc_opts hfsc_opts; -int yyerror(const char *, ...); -int disallow_table(struct node_host *, const char *); -int disallow_urpf_failed(struct node_host *, const char *); -int disallow_alias(struct node_host *, const char *); -int rule_consistent(struct pf_rule *, int); -int filter_consistent(struct pf_rule *, int); -int nat_consistent(struct pf_rule *); -int rdr_consistent(struct pf_rule *); -int process_tabledef(char *, struct table_opts *); -int yyparse(void); -void expand_label_str(char *, size_t, const char *, const char *); -void expand_label_if(const char *, char *, size_t, const char *); -void expand_label_addr(const char *, char *, size_t, u_int8_t, - struct node_host *); -void expand_label_port(const char *, char *, size_t, struct node_port *); -void expand_label_proto(const char *, char *, size_t, u_int8_t); -void expand_label_nr(const char *, char *, size_t); -void expand_label(char *, size_t, const char *, u_int8_t, struct node_host *, - struct node_port *, struct node_host *, struct node_port *, - u_int8_t); -void expand_rule(struct pf_rule *, struct node_if *, struct node_host *, - struct node_proto *, struct node_os*, struct node_host *, - struct node_port *, struct node_host *, struct node_port *, - struct node_uid *, struct node_gid *, struct node_icmp *, - const char *); -int expand_altq(struct pf_altq *, struct node_if *, struct node_queue *, - struct node_queue_bw bwspec, struct node_queue_opt *); -int expand_queue(struct pf_altq *, struct node_if *, struct node_queue *, - struct node_queue_bw, struct node_queue_opt *); -int expand_skip_interface(struct node_if *); +int disallow_table(struct node_host *, const char *); +int disallow_urpf_failed(struct node_host *, const char *); +int disallow_alias(struct node_host *, const char *); +int rule_consistent(struct pf_rule *, int); +int filter_consistent(struct pf_rule *, int); +int nat_consistent(struct pf_rule *); +int rdr_consistent(struct pf_rule *); +int process_tabledef(char *, struct table_opts *); +void expand_label_str(char *, size_t, const char *, const char *); +void expand_label_if(const char *, char *, size_t, const char *); +void expand_label_addr(const char *, char *, size_t, u_int8_t, + struct node_host *); +void expand_label_port(const char *, char *, size_t, + struct node_port *); +void expand_label_proto(const char *, char *, size_t, u_int8_t); +void expand_label_nr(const char *, char *, size_t); +void expand_label(char *, size_t, const char *, u_int8_t, + struct node_host *, struct node_port *, struct node_host *, + struct node_port *, u_int8_t); +void expand_rule(struct pf_rule *, struct node_if *, + struct node_host *, struct node_proto *, struct node_os *, + struct node_host *, struct node_port *, struct node_host *, + struct node_port *, struct node_uid *, struct node_gid *, + struct node_icmp *, const char *); +int expand_altq(struct pf_altq *, struct node_if *, + struct node_queue *, struct node_queue_bw bwspec, + struct node_queue_opt *); +int expand_queue(struct pf_altq *, struct node_if *, + struct node_queue *, struct node_queue_bw, + struct node_queue_opt *); +int expand_skip_interface(struct node_if *); int check_rulestate(int); -int kw_cmp(const void *, const void *); -int lookup(char *); -int lgetc(FILE *); -int lungetc(int); -int findeol(void); -int yylex(void); -int atoul(char *, u_long *); int getservice(char *); int rule_label(struct pf_rule *, char *); -TAILQ_HEAD(symhead, sym) symhead = TAILQ_HEAD_INITIALIZER(symhead); -struct sym { - TAILQ_ENTRY(sym) entries; - int used; - int persist; - char *nam; - char *val; -}; - - -int symset(const char *, const char *, int); -char *symget(const char *); - void mv_rules(struct pf_ruleset *, struct pf_ruleset *); void decide_address_family(struct node_host *, sa_family_t *); void remove_invalid_hosts(struct node_host **, sa_family_t *); @@ -327,10 +340,11 @@ struct loadanchors { typedef struct { union { - u_int32_t number; + int64_t number; + double probability; int i; char *string; - int rtableid; + u_int rtableid; struct { u_int8_t b1; u_int8_t b2; @@ -410,7 +424,7 @@ typedef struct { %token REASSEMBLE FRAGDROP FRAGCROP ANCHOR NATANCHOR RDRANCHOR BINATANCHOR %token SET OPTIMIZATION TIMEOUT LIMIT LOGINTERFACE BLOCKPOLICY RANDOMID %token REQUIREORDER SYNPROXY FINGERPRINTS NOSYNC DEBUG SKIP HOSTID -%token ANTISPOOF FOR +%token ANTISPOOF FOR INCLUDE %token BITMASK RANDOM SOURCEHASH ROUNDROBIN STATICPORT PROBABILITY %token ALTQ CBQ PRIQ HFSC BANDWIDTH TBRSIZE LINKSHARE REALTIME UPPERLIMIT %token QUEUE PRIORITY QLIMIT RTABLE @@ -419,10 +433,12 @@ typedef struct { %token MAXSRCCONN MAXSRCCONNRATE OVERLOAD FLUSH %token TAGGED TAG IFBOUND FLOATING STATEPOLICY ROUTE %token STRING +%token NUMBER %token PORTBINARY %type interface if_list if_item_not if_item %type number icmptype icmp6type uid gid %type tos not yesno +%type probability %type no dir af fragcache optimizer %type sourcetrack flush unaryop statelock %type action nataction natpasslog scrubaction @@ -430,9 +446,11 @@ typedef struct { %type port rport %type hashkey %type proto proto_list proto_item +%type protoval %type icmpspec %type icmp_list icmp_item %type icmp6_list icmp6_item +%type reticmpspec reticmp6spec %type fromto %type ipportspec from to %type ipspec xhost host dynaddr host_list @@ -444,7 +462,7 @@ typedef struct { %type gids gid_list gid_item %type route %type redirection redirpool -%type label string tag anchorname +%type label string stringall tag anchorname %type keep %type state_opt_spec state_opt_list state_opt_item %type logquick quick log logopts logopt @@ -467,6 +485,7 @@ typedef struct { %% ruleset : /* empty */ + | ruleset include '\n' | ruleset '\n' | ruleset option '\n' | ruleset scrubrule '\n' @@ -481,7 +500,22 @@ ruleset : /* empty */ | ruleset antispoof '\n' | ruleset tabledef '\n' | '{' fakeanchor '}' '\n'; - | ruleset error '\n' { errors++; } + | ruleset error '\n' { file->errors++; } + ; + +include : INCLUDE STRING { + struct file *nfile; + + if ((nfile = pushfile($2, 0)) == NULL) { + yyerror("failed to include file %s", $2); + free($2); + YYERROR; + } + free($2); + + file = nfile; + lungetc('\n'); + } ; /* @@ -532,7 +566,7 @@ option : SET OPTIMIZATION STRING { | SET TIMEOUT '{' timeout_list '}' | SET LIMIT limit_spec | SET LIMIT '{' limit_list '}' - | SET LOGINTERFACE STRING { + | SET LOGINTERFACE stringall { if (check_rulestate(PFCTL_STATE_OPTION)) { free($3); YYERROR; @@ -545,7 +579,7 @@ option : SET OPTIMIZATION STRING { free($3); } | SET HOSTID number { - if ($3 == 0) { + if ($3 == 0 || $3 > UINT_MAX) { yyerror("hostid must be non-zero"); YYERROR; } @@ -624,6 +658,14 @@ option : SET OPTIMIZATION STRING { } ; +stringall : STRING { $$ = $1; } + | ALL { + if (($$ = strdup("all")) == NULL) { + err(1, "stringall: strdup"); + } + } + ; + string : string STRING { if (asprintf(&$$, "%s %s", $1, $2) == -1) err(1, "string: asprintf"); @@ -641,6 +683,19 @@ varset : STRING '=' string { free($1); free($3); } + | STRING '=' NUMBER { + char *s; + if (asprintf(&s, "%lld", $3) == -1) { + yyerror("string: asprintf"); + YYERROR; + } + if (pf->opts & PF_OPT_VERBOSE) + printf("%s = \"%s\"\n", $1, s); + if (symset($1, s, 0) == -1) + err(1, "cannot store variable %s", $1); + free($1); + free(s); + } ; anchorname : STRING { $$ = $1; } @@ -687,6 +742,7 @@ anchorrule : ANCHOR anchorname dir quick interface af proto fromto filter_opts pfa_anchor { struct pf_rule r; + struct node_proto *proto; if (check_rulestate(PFCTL_STATE_FILTER)) { if ($2) @@ -737,6 +793,55 @@ anchorrule : ANCHOR anchorname dir quick interface af proto fromto r.prob = $9.prob; r.rtableid = $9.rtableid; + if ($9.tag) + if (strlcpy(r.tagname, $9.tag, + PF_TAG_NAME_SIZE) >= PF_TAG_NAME_SIZE) { + yyerror("tag too long, max %u chars", + PF_TAG_NAME_SIZE - 1); + YYERROR; + } + if ($9.match_tag) + if (strlcpy(r.match_tagname, $9.match_tag, + PF_TAG_NAME_SIZE) >= PF_TAG_NAME_SIZE) { + yyerror("tag too long, max %u chars", + PF_TAG_NAME_SIZE - 1); + YYERROR; + } + r.match_tag_not = $9.match_tag_not; + if (rule_label(&r, $9.label)) + YYERROR; + free($9.label); + r.flags = $9.flags.b1; + r.flagset = $9.flags.b2; + if (($9.flags.b1 & $9.flags.b2) != $9.flags.b1) { + yyerror("flags always false"); + YYERROR; + } + if ($9.flags.b1 || $9.flags.b2 || $8.src_os) { + for (proto = $7; proto != NULL && + proto->proto != IPPROTO_TCP; + proto = proto->next) + ; /* nothing */ + if (proto == NULL && $7 != NULL) { + if ($9.flags.b1 || $9.flags.b2) + yyerror( + "flags only apply to tcp"); + if ($8.src_os) + yyerror( + "OS fingerprinting only " + "applies to tcp"); + YYERROR; + } + } + + r.tos = $9.tos; + + if ($9.keep.action) { + yyerror("cannot specify state handling " + "on anchors"); + YYERROR; + } + if ($9.match_tag) if (strlcpy(r.match_tagname, $9.match_tag, PF_TAG_NAME_SIZE) >= PF_TAG_NAME_SIZE) { @@ -751,8 +856,8 @@ anchorrule : ANCHOR anchorname dir quick interface af proto fromto expand_rule(&r, $5, NULL, $7, $8.src_os, $8.src.host, $8.src.port, $8.dst.host, $8.dst.port, - 0, 0, 0, pf->astack[pf->asd + 1] ? - pf->alast->name : $2); + $9.uid, $9.gid, $9.icmpspec, + pf->astack[pf->asd + 1] ? pf->alast->name : $2); free($2); pf->astack[pf->asd + 1] = NULL; } @@ -966,24 +1071,24 @@ scrub_opt : NODF { } scrub_opts.nodf = 1; } - | MINTTL number { + | MINTTL NUMBER { if (scrub_opts.marker & SOM_MINTTL) { yyerror("min-ttl cannot be respecified"); YYERROR; } - if ($2 > 255) { + if ($2 < 0 || $2 > 255) { yyerror("illegal min-ttl value %d", $2); YYERROR; } scrub_opts.marker |= SOM_MINTTL; scrub_opts.minttl = $2; } - | MAXMSS number { + | MAXMSS NUMBER { if (scrub_opts.marker & SOM_MAXMSS) { yyerror("max-mss cannot be respecified"); YYERROR; } - if ($2 > 65535) { + if ($2 < 0 || $2 > 65535) { yyerror("illegal max-mss value %d", $2); YYERROR; } @@ -1019,8 +1124,8 @@ scrub_opt : NODF { } scrub_opts.randomid = 1; } - | RTABLE number { - if ($2 > RT_TABLEID_MAX || $2 < 0) { + | RTABLE NUMBER { + if ($2 < 0 || $2 > RT_TABLEID_MAX) { yyerror("invalid rtable id"); YYERROR; } @@ -1162,8 +1267,8 @@ antispoof_opt : label { } antispoof_opts.label = $1; } - | RTABLE number { - if ($2 > RT_TABLEID_MAX || $2 < 0) { + | RTABLE NUMBER { + if ($2 < 0 || $2 > RT_TABLEID_MAX) { yyerror("invalid rtable id"); YYERROR; } @@ -1244,6 +1349,10 @@ table_opt : STRING { switch (n->addr.type) { case PF_ADDR_ADDRMASK: continue; /* ok */ + case PF_ADDR_RANGE: + yyerror("address ranges are not " + "permitted inside tables"); + break; case PF_ADDR_DYNIFTL: yyerror("dynamic addresses are not " "permitted inside tables"); @@ -1376,24 +1485,24 @@ queue_opt : BANDWIDTH bandwidth { queue_opts.marker |= QOM_BWSPEC; queue_opts.queue_bwspec = $2; } - | PRIORITY number { + | PRIORITY NUMBER { if (queue_opts.marker & QOM_PRIORITY) { yyerror("priority cannot be respecified"); YYERROR; } - if ($2 > 255) { + if ($2 < 0 || $2 > 255) { yyerror("priority out of range: max 255"); YYERROR; } queue_opts.marker |= QOM_PRIORITY; queue_opts.priority = $2; } - | QLIMIT number { + | QLIMIT NUMBER { if (queue_opts.marker & QOM_QLIMIT) { yyerror("qlimit cannot be respecified"); YYERROR; } - if ($2 > 65535) { + if ($2 < 0 || $2 > 65535) { yyerror("qlimit out of range: max 65535"); YYERROR; } @@ -1408,12 +1517,12 @@ queue_opt : BANDWIDTH bandwidth { queue_opts.marker |= QOM_SCHEDULER; queue_opts.scheduler = $1; } - | TBRSIZE number { + | TBRSIZE NUMBER { if (queue_opts.marker & QOM_TBRSIZE) { yyerror("tbrsize cannot be respecified"); YYERROR; } - if ($2 > 65535) { + if ($2 < 0 || $2 > 65535) { yyerror("tbrsize too big: max 65535"); YYERROR; } @@ -1456,6 +1565,14 @@ bandwidth : STRING { free($1); $$.bw_absolute = (u_int32_t)bps; } + | NUMBER { + if ($1 < 0 || $1 > UINT_MAX) { + yyerror("bandwidth number too big"); + YYERROR; + } + $$.bw_percent = 0; + $$.bw_absolute = $1; + } ; scheduler : CBQ { @@ -1552,8 +1669,12 @@ hfscopts_item : LINKSHARE bandwidth { hfsc_opts.linkshare.m2 = $2; hfsc_opts.linkshare.used = 1; } - | LINKSHARE '(' bandwidth comma number comma bandwidth ')' + | LINKSHARE '(' bandwidth comma NUMBER comma bandwidth ')' { + if ($5 < 0 || $5 > INT_MAX) { + yyerror("timing in curve out of range"); + YYERROR; + } if (hfsc_opts.linkshare.used) { yyerror("linkshare already specified"); YYERROR; @@ -1571,8 +1692,12 @@ hfscopts_item : LINKSHARE bandwidth { hfsc_opts.realtime.m2 = $2; hfsc_opts.realtime.used = 1; } - | REALTIME '(' bandwidth comma number comma bandwidth ')' + | REALTIME '(' bandwidth comma NUMBER comma bandwidth ')' { + if ($5 < 0 || $5 > INT_MAX) { + yyerror("timing in curve out of range"); + YYERROR; + } if (hfsc_opts.realtime.used) { yyerror("realtime already specified"); YYERROR; @@ -1590,8 +1715,12 @@ hfscopts_item : LINKSHARE bandwidth { hfsc_opts.upperlimit.m2 = $2; hfsc_opts.upperlimit.used = 1; } - | UPPERLIMIT '(' bandwidth comma number comma bandwidth ')' + | UPPERLIMIT '(' bandwidth comma NUMBER comma bandwidth ')' { + if ($5 < 0 || $5 > INT_MAX) { + yyerror("timing in curve out of range"); + YYERROR; + } if (hfsc_opts.upperlimit.used) { yyerror("upperlimit already specified"); YYERROR; @@ -2113,30 +2242,20 @@ filter_opt : USER uids { filter_opts.match_tag = $3; filter_opts.match_tag_not = $1; } - | PROBABILITY STRING { - char *e; - double p = strtod($2, &e); + | PROBABILITY probability { + double p; - if (*e == '%') { - p *= 0.01; - e++; - } - if (*e) { - yyerror("invalid probability: %s", $2); - free($2); - YYERROR; - } - p = floor(p * (UINT_MAX+1.0) + 0.5); - if (p < 1.0 || p >= (UINT_MAX+1.0)) { - yyerror("invalid probability: %s", $2); - free($2); + p = floor($2 * UINT_MAX + 0.5); + if (p < 0.0 || p > UINT_MAX) { + yyerror("invalid probability: %lf", p); YYERROR; } filter_opts.prob = (u_int32_t)p; - free($2); + if (filter_opts.prob == 0) + filter_opts.prob = 1; } - | RTABLE number { - if ($2 > RT_TABLEID_MAX || $2 < 0) { + | RTABLE NUMBER { + if ($2 < 0 || $2 > RT_TABLEID_MAX) { yyerror("invalid rtable id"); YYERROR; } @@ -2144,6 +2263,28 @@ filter_opt : USER uids { } ; +probability : STRING { + char *e; + double p = strtod($1, &e); + + if (*e == '%') { + p *= 0.01; + e++; + } + if (*e) { + yyerror("invalid probability: %s", $1); + free($1); + YYERROR; + } + free($1); + $$ = p; + } + | NUMBER { + $$ = (double)$1; + } + ; + + action : PASS { $$.b1 = PF_PASS; $$.b2 = $$.w = 0; } | BLOCK blockspec { $$ = $2; $$.b1 = PF_DROP; } ; @@ -2163,8 +2304,8 @@ blockspec : /* empty */ { $$.w = 0; $$.w2 = 0; } - | RETURNRST '(' TTL number ')' { - if ($4 > 255) { + | RETURNRST '(' TTL NUMBER ')' { + if ($4 < 0 || $4 > 255) { yyerror("illegal ttl value %d", $4); YYERROR; } @@ -2182,34 +2323,20 @@ blockspec : /* empty */ { $$.w = returnicmpdefault; $$.w2 = returnicmp6default; } - | RETURNICMP '(' STRING ')' { + | RETURNICMP '(' reticmpspec ')' { $$.b2 = PFRULE_RETURNICMP; - if (!($$.w = parseicmpspec($3, AF_INET))) { - free($3); - YYERROR; - } - free($3); - $$.w2 = returnicmp6default; + $$.w = $3; + $$.w2 = returnicmpdefault; } - | RETURNICMP6 '(' STRING ')' { + | RETURNICMP6 '(' reticmp6spec ')' { $$.b2 = PFRULE_RETURNICMP; $$.w = returnicmpdefault; - if (!($$.w2 = parseicmpspec($3, AF_INET6))) { - free($3); - YYERROR; - } - free($3); + $$.w2 = $3; } - | RETURNICMP '(' STRING comma STRING ')' { + | RETURNICMP '(' reticmpspec comma reticmp6spec ')' { $$.b2 = PFRULE_RETURNICMP; - if (!($$.w = parseicmpspec($3, AF_INET)) || - !($$.w2 = parseicmpspec($5, AF_INET6))) { - free($3); - free($5); - YYERROR; - } - free($3); - free($5); + $$.w = $3; + $$.w2 = $5; } | RETURN { $$.b2 = PFRULE_RETURN; @@ -2218,6 +2345,44 @@ blockspec : /* empty */ { } ; +reticmpspec : STRING { + if (!($$ = parseicmpspec($1, AF_INET))) { + free($1); + YYERROR; + } + free($1); + } + | NUMBER { + u_int8_t icmptype; + + if ($1 < 0 || $1 > 255) { + yyerror("invalid icmp code %lu", $1); + YYERROR; + } + icmptype = returnicmpdefault >> 8; + $$ = (icmptype << 8 | $1); + } + ; + +reticmp6spec : STRING { + if (!($$ = parseicmpspec($1, AF_INET6))) { + free($1); + YYERROR; + } + free($1); + } + | NUMBER { + u_int8_t icmptype; + + if ($1 < 0 || $1 > 255) { + yyerror("invalid icmp code %lu", $1); + YYERROR; + } + icmptype = returnicmp6default >> 8; + $$ = (icmptype << 8 | $1); + } + ; + dir : /* empty */ { $$ = 0; } | IN { $$ = PF_IN; } | OUT { $$ = PF_OUT; } @@ -2332,29 +2497,10 @@ proto_list : proto_item { $$ = $1; } } ; -proto_item : STRING { +proto_item : protoval { u_int8_t pr; - u_long ulval; - if (atoul($1, &ulval) == 0) { - if (ulval > 255) { - yyerror("protocol outside range"); - free($1); - YYERROR; - } - pr = (u_int8_t)ulval; - } else { - struct protoent *p; - - p = getprotobyname($1); - if (p == NULL) { - yyerror("unknown protocol %s", $1); - free($1); - YYERROR; - } - pr = p->p_proto; - } - free($1); + pr = (u_int8_t)$1; if (pr == 0) { yyerror("proto 0 cannot be used"); YYERROR; @@ -2368,6 +2514,26 @@ proto_item : STRING { } ; +protoval : STRING { + struct protoent *p; + + p = getprotobyname($1); + if (p == NULL) { + yyerror("unknown protocol %s", $1); + free($1); + YYERROR; + } + $$ = p->p_proto; + free($1); + } + | NUMBER { + if ($1 < 0 || $1 > 255) { + yyerror("protocol outside range"); + YYERROR; + } + } + ; + fromto : ALL { $$.src.host = NULL; $$.src.port = NULL; @@ -2495,10 +2661,43 @@ host : STRING { free($1); } - | STRING '/' number { + | STRING '-' STRING { + struct node_host *b, *e; + + if ((b = host($1)) == NULL || (e = host($3)) == NULL) { + free($1); + free($3); + yyerror("could not parse host specification"); + YYERROR; + } + if (b->af != e->af || + b->addr.type != PF_ADDR_ADDRMASK || + e->addr.type != PF_ADDR_ADDRMASK || + unmask(&b->addr.v.a.mask, b->af) != + (b->af == AF_INET ? 32 : 128) || + unmask(&e->addr.v.a.mask, e->af) != + (e->af == AF_INET ? 32 : 128) || + b->next != NULL || b->not || + e->next != NULL || e->not) { + free(b); + free(e); + free($1); + free($3); + yyerror("invalid address range"); + YYERROR; + } + memcpy(&b->addr.v.a.mask, &e->addr.v.a.addr, + sizeof(b->addr.v.a.mask)); + b->addr.type = PF_ADDR_RANGE; + $$ = b; + free(e); + free($1); + free($3); + } + | STRING '/' NUMBER { char *buf; - if (asprintf(&buf, "%s/%u", $1, $3) == -1) + if (asprintf(&buf, "%s/%lld", $1, $3) == -1) err(1, "host: asprintf"); free($1); if (($$ = host(buf)) == NULL) { @@ -2509,10 +2708,28 @@ host : STRING { } free(buf); } + | NUMBER '/' NUMBER { + char *buf; + + /* ie. for 10/8 parsing */ + if (asprintf(&buf, "%lld/%lld", $1, $3) == -1) + err(1, "host: asprintf"); + if (($$ = host(buf)) == NULL) { + /* error. "any" is handled elsewhere */ + free(buf); + yyerror("could not parse host specification"); + YYERROR; + } + free(buf); + } | dynaddr - | dynaddr '/' number { + | dynaddr '/' NUMBER { struct node_host *n; + if ($3 < 0 || $3 > 128) { + yyerror("bit number too big"); + YYERROR; + } $$ = $1; for (n = $1; n != NULL; n = n->next) set_ipmask(n, $3); @@ -2557,7 +2774,8 @@ host : STRING { } ; -number : STRING { +number : NUMBER + | STRING { u_long ulval; if (atoul($1, &ulval) == -1) { @@ -2705,6 +2923,14 @@ port : STRING { } free($1); } + | NUMBER { + if ($1 < 0 || $1 > 65535) { + yyerror("illegal port value %lu", $1); + YYERROR; + } + $$.a = ntohs($1); + $$.b = $$.t = 0; + } ; uids : uid_item { $$ = $1; } @@ -2762,31 +2988,27 @@ uid_item : uid { ; uid : STRING { - u_long ulval; + if (!strcmp($1, "unknown")) + $$ = UID_MAX; + else { + struct passwd *pw; - if (atoul($1, &ulval) == -1) { - if (!strcmp($1, "unknown")) - $$ = UID_MAX; - else { - struct passwd *pw; - - if ((pw = getpwnam($1)) == NULL) { - yyerror("unknown user %s", $1); - free($1); - YYERROR; - } - $$ = pw->pw_uid; - } - } else { - if (ulval >= UID_MAX) { + if ((pw = getpwnam($1)) == NULL) { + yyerror("unknown user %s", $1); free($1); - yyerror("illegal uid value %lu", ulval); YYERROR; } - $$ = ulval; + $$ = pw->pw_uid; } free($1); } + | NUMBER { + if ($1 < 0 || $1 >= UID_MAX) { + yyerror("illegal uid value %lu", $1); + YYERROR; + } + $$ = $1; + } ; gids : gid_item { $$ = $1; } @@ -2844,31 +3066,27 @@ gid_item : gid { ; gid : STRING { - u_long ulval; + if (!strcmp($1, "unknown")) + $$ = GID_MAX; + else { + struct group *grp; - if (atoul($1, &ulval) == -1) { - if (!strcmp($1, "unknown")) - $$ = GID_MAX; - else { - struct group *grp; - - if ((grp = getgrnam($1)) == NULL) { - yyerror("unknown group %s", $1); - free($1); - YYERROR; - } - $$ = grp->gr_gid; - } - } else { - if (ulval >= GID_MAX) { - yyerror("illegal gid value %lu", ulval); + if ((grp = getgrnam($1)) == NULL) { + yyerror("unknown group %s", $1); free($1); YYERROR; } - $$ = ulval; + $$ = grp->gr_gid; } free($1); } + | NUMBER { + if ($1 < 0 || $1 >= GID_MAX) { + yyerror("illegal gid value %lu", $1); + YYERROR; + } + $$ = $1; + } ; flag : STRING { @@ -2923,29 +3141,33 @@ icmp_item : icmptype { } | icmptype CODE STRING { const struct icmpcodeent *p; - u_long ulval; - if (atoul($3, &ulval) == 0) { - if (ulval > 255) { - free($3); - yyerror("illegal icmp-code %lu", ulval); - YYERROR; - } - } else { - if ((p = geticmpcodebyname($1-1, $3, - AF_INET)) == NULL) { - yyerror("unknown icmp-code %s", $3); - free($3); - YYERROR; - } - ulval = p->code; + if ((p = geticmpcodebyname($1-1, $3, AF_INET)) == NULL) { + yyerror("unknown icmp-code %s", $3); + free($3); + YYERROR; } + free($3); $$ = calloc(1, sizeof(struct node_icmp)); if ($$ == NULL) err(1, "icmp_item: calloc"); $$->type = $1; - $$->code = ulval + 1; + $$->code = p->code + 1; + $$->proto = IPPROTO_ICMP; + $$->next = NULL; + $$->tail = $$; + } + | icmptype CODE NUMBER { + if ($3 < 0 || $3 > 255) { + yyerror("illegal icmp-code %lu", $3); + YYERROR; + } + $$ = calloc(1, sizeof(struct node_icmp)); + if ($$ == NULL) + err(1, "icmp_item: calloc"); + $$->type = $1; + $$->code = $3 + 1; $$->proto = IPPROTO_ICMP; $$->next = NULL; $$->tail = $$; @@ -2964,30 +3186,33 @@ icmp6_item : icmp6type { } | icmp6type CODE STRING { const struct icmpcodeent *p; - u_long ulval; - if (atoul($3, &ulval) == 0) { - if (ulval > 255) { - yyerror("illegal icmp6-code %lu", - ulval); - free($3); - YYERROR; - } - } else { - if ((p = geticmpcodebyname($1-1, $3, - AF_INET6)) == NULL) { - yyerror("unknown icmp6-code %s", $3); - free($3); - YYERROR; - } - ulval = p->code; + if ((p = geticmpcodebyname($1-1, $3, AF_INET6)) == NULL) { + yyerror("unknown icmp6-code %s", $3); + free($3); + YYERROR; } free($3); + $$ = calloc(1, sizeof(struct node_icmp)); if ($$ == NULL) err(1, "icmp_item: calloc"); $$->type = $1; - $$->code = ulval + 1; + $$->code = p->code + 1; + $$->proto = IPPROTO_ICMPV6; + $$->next = NULL; + $$->tail = $$; + } + | icmp6type CODE NUMBER { + if ($3 < 0 || $3 > 255) { + yyerror("illegal icmp-code %lu", $3); + YYERROR; + } + $$ = calloc(1, sizeof(struct node_icmp)); + if ($$ == NULL) + err(1, "icmp_item: calloc"); + $$->type = $1; + $$->code = $3 + 1; $$->proto = IPPROTO_ICMPV6; $$->next = NULL; $$->tail = $$; @@ -2996,51 +3221,43 @@ icmp6_item : icmp6type { icmptype : STRING { const struct icmptypeent *p; - u_long ulval; - if (atoul($1, &ulval) == 0) { - if (ulval > 255) { - yyerror("illegal icmp-type %lu", ulval); - free($1); - YYERROR; - } - $$ = ulval + 1; - } else { - if ((p = geticmptypebyname($1, AF_INET)) == - NULL) { - yyerror("unknown icmp-type %s", $1); - free($1); - YYERROR; - } - $$ = p->type + 1; + if ((p = geticmptypebyname($1, AF_INET)) == NULL) { + yyerror("unknown icmp-type %s", $1); + free($1); + YYERROR; } + $$ = p->type + 1; free($1); } + | NUMBER { + if ($1 < 0 || $1 > 255) { + yyerror("illegal icmp-type %lu", $1); + YYERROR; + } + $$ = $1 + 1; + } ; icmp6type : STRING { const struct icmptypeent *p; - u_long ulval; - if (atoul($1, &ulval) == 0) { - if (ulval > 255) { - yyerror("illegal icmp6-type %lu", - ulval); - free($1); - YYERROR; - } - $$ = ulval + 1; - } else { - if ((p = geticmptypebyname($1, AF_INET6)) == - NULL) { - yyerror("unknown icmp6-type %s", $1); - free($1); - YYERROR; - } - $$ = p->type + 1; + if ((p = geticmptypebyname($1, AF_INET6)) == + NULL) { + yyerror("unknown icmp6-type %s", $1); + free($1); + YYERROR; } + $$ = p->type + 1; free($1); } + | NUMBER { + if ($1 < 0 || $1 > 255) { + yyerror("illegal icmp6-type %lu", $1); + YYERROR; + } + $$ = $1 + 1; + } ; tos : TOS STRING { @@ -3053,7 +3270,7 @@ tos : TOS STRING { else if ($2[0] == '0' && $2[1] == 'x') $$ = strtoul($2, NULL, 16); else - $$ = strtoul($2, NULL, 10); + $$ = 0; /* flag bad argument */ if (!$$ || $$ > 255) { yyerror("illegal tos value %s", $2); free($2); @@ -3061,6 +3278,13 @@ tos : TOS STRING { } free($2); } + | TOS NUMBER { + $$ = $2; + if (!$$ || $$ > 255) { + yyerror("illegal tos value %s", $2); + YYERROR; + } + } ; sourcetrack : SOURCETRACK { $$ = PF_SRCTRACK; } @@ -3113,7 +3337,11 @@ state_opt_list : state_opt_item { $$ = $1; } } ; -state_opt_item : MAXIMUM number { +state_opt_item : MAXIMUM NUMBER { + if ($2 < 0 || $2 > UINT_MAX) { + yyerror("only positive values permitted"); + YYERROR; + } $$ = calloc(1, sizeof(struct node_state_opt)); if ($$ == NULL) err(1, "state_opt_item: calloc"); @@ -3130,7 +3358,11 @@ state_opt_item : MAXIMUM number { $$->next = NULL; $$->tail = $$; } - | MAXSRCSTATES number { + | MAXSRCSTATES NUMBER { + if ($2 < 0 || $2 > UINT_MAX) { + yyerror("only positive values permitted"); + YYERROR; + } $$ = calloc(1, sizeof(struct node_state_opt)); if ($$ == NULL) err(1, "state_opt_item: calloc"); @@ -3139,7 +3371,11 @@ state_opt_item : MAXIMUM number { $$->next = NULL; $$->tail = $$; } - | MAXSRCCONN number { + | MAXSRCCONN NUMBER { + if ($2 < 0 || $2 > UINT_MAX) { + yyerror("only positive values permitted"); + YYERROR; + } $$ = calloc(1, sizeof(struct node_state_opt)); if ($$ == NULL) err(1, "state_opt_item: calloc"); @@ -3148,7 +3384,12 @@ state_opt_item : MAXIMUM number { $$->next = NULL; $$->tail = $$; } - | MAXSRCCONNRATE number '/' number { + | MAXSRCCONNRATE NUMBER '/' NUMBER { + if ($2 < 0 || $2 > UINT_MAX || + $4 < 0 || $4 > UINT_MAX) { + yyerror("only positive values permitted"); + YYERROR; + } $$ = calloc(1, sizeof(struct node_state_opt)); if ($$ == NULL) err(1, "state_opt_item: calloc"); @@ -3176,7 +3417,11 @@ state_opt_item : MAXIMUM number { $$->next = NULL; $$->tail = $$; } - | MAXSRCNODES number { + | MAXSRCNODES NUMBER { + if ($2 < 0 || $2 > UINT_MAX) { + yyerror("only positive values permitted"); + YYERROR; + } $$ = calloc(1, sizeof(struct node_state_opt)); if ($$ == NULL) err(1, "state_opt_item: calloc"); @@ -3203,9 +3448,13 @@ state_opt_item : MAXIMUM number { $$->next = NULL; $$->tail = $$; } - | STRING number { + | STRING NUMBER { int i; + if ($2 < 0 || $2 > UINT_MAX) { + yyerror("only positive values permitted"); + YYERROR; + } for (i = 0; pf_timeouts[i].name && strcmp(pf_timeouts[i].name, $1); ++i) ; /* nothing */ @@ -3282,6 +3531,14 @@ rport : STRING { } free($1); } + | NUMBER { + if ($1 < 0 || $1 > 65535) { + yyerror("illegal port value %ld", $1); + YYERROR; + } + $$.a = ntohs($1); + $$.b = $$.t = 0; + } ; redirspec : host { $$ = $1; } @@ -3808,8 +4065,8 @@ tagged : /* empty */ { $$.neg = 0; $$.name = NULL; } ; rtable : /* empty */ { $$ = -1; } - | RTABLE number { - if ($2 > RT_TABLEID_MAX || $2 < 0) { + | RTABLE NUMBER { + if ($2 < 0 || $2 > RT_TABLEID_MAX) { yyerror("invalid rtable id"); YYERROR; } @@ -3884,12 +4141,16 @@ route : /* empty */ { } ; -timeout_spec : STRING number +timeout_spec : STRING NUMBER { if (check_rulestate(PFCTL_STATE_OPTION)) { free($1); YYERROR; } + if ($2 < 0 || $2 > UINT_MAX) { + yyerror("only positive values permitted"); + YYERROR; + } if (pfctl_set_timeout(pf, $1, $2, 0) != 0) { yyerror("unknown timeout %s", $1); free($1); @@ -3903,12 +4164,16 @@ timeout_list : timeout_list comma timeout_spec | timeout_spec ; -limit_spec : STRING number +limit_spec : STRING NUMBER { if (check_rulestate(PFCTL_STATE_OPTION)) { free($1); YYERROR; } + if ($2 < 0 || $2 > UINT_MAX) { + yyerror("only positive values permitted"); + YYERROR; + } if (pfctl_set_limit(pf, $1, $2) != 0) { yyerror("unable to set limit %s %u", $1, $2); free($1); @@ -3954,11 +4219,10 @@ int yyerror(const char *fmt, ...) { va_list ap; - extern char *infile; - errors = 1; + file->errors++; va_start(ap, fmt); - fprintf(stderr, "%s:%d: ", infile, yylval.lineno); + fprintf(stderr, "%s:%d: ", file->name, yylval.lineno); vfprintf(stderr, fmt, ap); fprintf(stderr, "\n"); va_end(ap); @@ -4889,6 +5153,7 @@ lookup(char *s) { "icmp6-type", ICMP6TYPE}, { "if-bound", IFBOUND}, { "in", IN}, + { "include", INCLUDE}, { "inet", INET}, { "inet6", INET6}, { "keep", KEEP}, @@ -4990,9 +5255,9 @@ char pushback_buffer[MAXPUSHBACK]; int pushback_index = 0; int -lgetc(FILE *f) +lgetc(int quotec) { - int c, next; + int c, next; if (parsebuf) { /* Read character from the parsebuffer instead of input. */ @@ -5008,24 +5273,31 @@ lgetc(FILE *f) if (pushback_index) return (pushback_buffer[--pushback_index]); - while ((c = getc(f)) == '\\') { - next = getc(f); + if (quotec) { + if ((c = getc(file->stream)) == EOF) { + yyerror("reached end of file while parsing quoted string"); + if (popfile() == EOF) + return (EOF); + return (quotec); + } + return (c); + } + + while ((c = getc(file->stream)) == '\\') { + next = getc(file->stream); if (next != '\n') { c = next; break; } - yylval.lineno = lineno; - lineno++; - } - if (c == '\t' || c == ' ') { - /* Compress blanks to a single space. */ - do { - c = getc(f); - } while (c == '\t' || c == ' '); - ungetc(c, f); - c = ' '; + yylval.lineno = file->lineno; + file->lineno++; } + while (c == EOF) { + if (popfile() == EOF) + return (EOF); + c = getc(file->stream); + } return (c); } @@ -5055,9 +5327,9 @@ findeol(void) /* skip to either EOF or the first real EOL */ while (1) { - c = lgetc(fin); + c = lgetc(0); if (c == '\n') { - lineno++; + file->lineno++; break; } if (c == EOF) @@ -5071,21 +5343,21 @@ yylex(void) { char buf[8096]; char *p, *val; - int endc, c, next; + int quotec, next, c; int token; top: p = buf; - while ((c = lgetc(fin)) == ' ') + while ((c = lgetc(0)) == ' ' || c == '\t') ; /* nothing */ - yylval.lineno = lineno; + yylval.lineno = file->lineno; if (c == '#') - while ((c = lgetc(fin)) != '\n' && c != EOF) + while ((c = lgetc(0)) != '\n' && c != EOF) ; /* nothing */ if (c == '$' && parsebuf == NULL) { while (1) { - if ((c = lgetc(fin)) == EOF) + if ((c = lgetc(0)) == EOF) return (0); if (p + 1 >= buf + sizeof(buf) - 1) { @@ -5113,18 +5385,26 @@ top: switch (c) { case '\'': case '"': - endc = c; + quotec = c; while (1) { - if ((c = lgetc(fin)) == EOF) + if ((c = lgetc(quotec)) == EOF) return (0); - if (c == endc) { + if (c == '\n') { + file->lineno++; + continue; + } else if (c == '\\') { + if ((next = lgetc(quotec)) == EOF) + return (0); + if (next == quotec || c == ' ' || c == '\t') + c = next; + else if (next == '\n') + continue; + else + lungetc(next); + } else if (c == quotec) { *p = '\0'; break; } - if (c == '\n') { - lineno++; - continue; - } if (p + 1 >= buf + sizeof(buf) - 1) { yyerror("string too long"); return (findeol()); @@ -5136,7 +5416,7 @@ top: err(1, "yylex: strdup"); return (STRING); case '<': - next = lgetc(fin); + next = lgetc(0); if (next == '>') { yylval.v.i = PF_OP_XRG; return (PORTBINARY); @@ -5144,7 +5424,7 @@ top: lungetc(next); break; case '>': - next = lgetc(fin); + next = lgetc(0); if (next == '<') { yylval.v.i = PF_OP_IRG; return (PORTBINARY); @@ -5152,13 +5432,49 @@ top: lungetc(next); break; case '-': - next = lgetc(fin); + next = lgetc(0); if (next == '>') return (ARROW); lungetc(next); break; } +#define allowed_to_end_number(x) \ + (isspace(x) || x == ')' || x ==',' || x == '/' || x == '}' || x == '=') + + if (c == '-' || isdigit(c)) { + do { + *p++ = c; + if ((unsigned)(p-buf) >= sizeof(buf)) { + yyerror("string too long"); + return (findeol()); + } + } while ((c = lgetc(0)) != EOF && isdigit(c)); + lungetc(c); + if (p == buf + 1 && buf[0] == '-') + goto nodigits; + if (c == EOF || allowed_to_end_number(c)) { + const char *errstr = NULL; + + *p = '\0'; + yylval.v.number = strtonum(buf, LLONG_MIN, + LLONG_MAX, &errstr); + if (errstr) { + yyerror("\"%s\" invalid number: %s", + buf, errstr); + return (findeol()); + } + return (NUMBER); + } else { +nodigits: + while (p > buf + 1) + lungetc(*--p); + c = *--p; + if (c == '-') + return (c); + } + } + #define allowed_in_string(x) \ (isalnum(x) || (ispunct(x) && x != '(' && x != ')' && \ x != '{' && x != '}' && x != '<' && x != '>' && \ @@ -5172,7 +5488,7 @@ top: yyerror("string too long"); return (findeol()); } - } while ((c = lgetc(fin)) != EOF && (allowed_in_string(c))); + } while ((c = lgetc(0)) != EOF && (allowed_in_string(c))); lungetc(c); *p = '\0'; if ((token = lookup(buf)) == STRING) @@ -5181,8 +5497,8 @@ top: return (token); } if (c == '\n') { - yylval.lineno = lineno; - lineno++; + yylval.lineno = file->lineno; + file->lineno++; } if (c == EOF) return (0); @@ -5190,13 +5506,84 @@ top: } int -parse_rules(FILE *input, struct pfctl *xpf) +check_file_secrecy(int fd, const char *fname) { - struct sym *sym, *next; + struct stat st; + + if (fstat(fd, &st)) { + warn("cannot stat %s", fname); + return (-1); + } + if (st.st_uid != 0 && st.st_uid != getuid()) { + warnx("%s: owner not root or current user", fname); + return (-1); + } + if (st.st_mode & (S_IRWXG | S_IRWXO)) { + warnx("%s: group/world readable/writeable", fname); + return (-1); + } + return (0); +} + +struct file * +pushfile(const char *name, int secret) +{ + struct file *nfile; + + if ((nfile = calloc(1, sizeof(struct file))) == NULL || + (nfile->name = strdup(name)) == NULL) { + warn("malloc"); + return (NULL); + } + if (TAILQ_FIRST(&files) == NULL && strcmp(nfile->name, "-") == 0) { + nfile->stream = stdin; + free(nfile->name); + if ((nfile->name = strdup("stdin")) == NULL) { + warn("strdup"); + free(nfile); + return (NULL); + } + } else if ((nfile->stream = fopen(nfile->name, "r")) == NULL) { + warn("%s", nfile->name); + free(nfile->name); + free(nfile); + return (NULL); + } else if (secret && + check_file_secrecy(fileno(nfile->stream), nfile->name)) { + fclose(nfile->stream); + free(nfile->name); + free(nfile); + return (NULL); + } + nfile->lineno = 1; + TAILQ_INSERT_TAIL(&files, nfile, entry); + return (nfile); +} + +int +popfile(void) +{ + struct file *prev; + + if ((prev = TAILQ_PREV(file, files, entry)) != NULL) { + prev->errors += file->errors; + TAILQ_REMOVE(&files, file, entry); + fclose(file->stream); + free(file->name); + free(file); + file = prev; + return (0); + } + return (EOF); +} + +int +parse_config(char *filename, struct pfctl *xpf) +{ + int errors = 0; + struct sym *sym; - fin = input; pf = xpf; - lineno = 1; errors = 0; rulestate = PFCTL_STATE_NONE; returnicmpdefault = (ICMP_UNREACH << 8) | ICMP_UNREACH_PORT; @@ -5205,34 +5592,36 @@ parse_rules(FILE *input, struct pfctl *xpf) blockpolicy = PFRULE_DROP; require_order = 1; + if ((file = pushfile(filename, 0)) == NULL) { + warn("cannot open the main config file!"); + return (-1); + } + yyparse(); + errors = file->errors; + popfile(); /* Free macros and check which have not been used. */ - for (sym = TAILQ_FIRST(&symhead); sym != NULL; sym = next) { - next = TAILQ_NEXT(sym, entries); + while ((sym = TAILQ_FIRST(&symhead))) { if ((pf->opts & PF_OPT_VERBOSE2) && !sym->used) fprintf(stderr, "warning: macro '%s' not " "used\n", sym->nam); free(sym->nam); free(sym->val); - TAILQ_REMOVE(&symhead, sym, entries); + TAILQ_REMOVE(&symhead, sym, entry); free(sym); } return (errors ? -1 : 0); } -/* - * Over-designed efficiency is a French and German concept, so how about - * we wait until they discover this ugliness and make it all fancy. - */ int symset(const char *nam, const char *val, int persist) { struct sym *sym; for (sym = TAILQ_FIRST(&symhead); sym && strcmp(nam, sym->nam); - sym = TAILQ_NEXT(sym, entries)) + sym = TAILQ_NEXT(sym, entry)) ; /* nothing */ if (sym != NULL) { @@ -5241,7 +5630,7 @@ symset(const char *nam, const char *val, int persist) else { free(sym->nam); free(sym->val); - TAILQ_REMOVE(&symhead, sym, entries); + TAILQ_REMOVE(&symhead, sym, entry); free(sym); } } @@ -5261,7 +5650,7 @@ symset(const char *nam, const char *val, int persist) } sym->used = 0; sym->persist = persist; - TAILQ_INSERT_TAIL(&symhead, sym, entries); + TAILQ_INSERT_TAIL(&symhead, sym, entry); return (0); } @@ -5290,7 +5679,7 @@ symget(const char *nam) { struct sym *sym; - TAILQ_FOREACH(sym, &symhead, entries) + TAILQ_FOREACH(sym, &symhead, entry) if (strcmp(nam, sym->nam) == 0) { sym->used = 1; return (sym->val); @@ -5476,17 +5865,12 @@ int pfctl_load_anchors(int dev, struct pfctl *pf, struct pfr_buffer *trans) { struct loadanchors *la; - FILE *fin; TAILQ_FOREACH(la, &loadanchorshead, entries) { if (pf->opts & PF_OPT_VERBOSE) fprintf(stderr, "\nLoading anchor %s from %s\n", la->anchorname, la->filename); - if ((fin = pfctl_fopen(la->filename, "r")) == NULL) { - warn("%s", la->filename); - continue; - } - if (pfctl_rules(dev, la->filename, fin, pf->opts, pf->optimize, + if (pfctl_rules(dev, la->filename, pf->opts, pf->optimize, la->anchorname, trans) == -1) return (-1); } diff --git a/pfctl/pf_print_state.c b/pfctl/pf_print_state.c index e4830a1268f..8489c38c73a 100644 --- a/pfctl/pf_print_state.c +++ b/pfctl/pf_print_state.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pf_print_state.c,v 1.45 2007/05/31 04:13:37 mcbride Exp $ */ +/* $OpenBSD: pf_print_state.c,v 1.46 2007/08/30 09:28:49 dhartmei Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -79,6 +79,19 @@ print_addr(struct pf_addr_wrap *addr, sa_family_t af, int verbose) else printf("<%s>", addr->v.tblname); return; + case PF_ADDR_RANGE: { + char buf[48]; + + if (inet_ntop(af, &addr->v.a.addr, buf, sizeof(buf)) == NULL) + printf("?"); + else + printf("%s", buf); + if (inet_ntop(af, &addr->v.a.mask, buf, sizeof(buf)) == NULL) + printf(" - ?"); + else + printf(" - %s", buf); + break; + } case PF_ADDR_ADDRMASK: if (PF_AZERO(&addr->v.a.addr, AF_INET6) && PF_AZERO(&addr->v.a.mask, AF_INET6)) @@ -108,7 +121,8 @@ print_addr(struct pf_addr_wrap *addr, sa_family_t af, int verbose) } /* mask if not _both_ address and mask are zero */ - if (!(PF_AZERO(&addr->v.a.addr, AF_INET6) && + if (addr->type != PF_ADDR_RANGE && + !(PF_AZERO(&addr->v.a.addr, AF_INET6) && PF_AZERO(&addr->v.a.mask, AF_INET6))) { int bits = unmask(&addr->v.a.mask, af); diff --git a/pfctl/pfctl.c b/pfctl/pfctl.c index 0aeb0fc7807..3829f2cb413 100644 --- a/pfctl/pfctl.c +++ b/pfctl/pfctl.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl.c,v 1.268 2007/06/30 18:25:08 henning Exp $ */ +/* $OpenBSD: pfctl.c,v 1.273 2008/02/13 19:55:12 kettenis Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -119,8 +119,6 @@ int dev = -1; int first_title = 1; int labels = 0; -const char *infile; - #define INDENT(d, o) do { \ if (o) { \ int i; \ @@ -955,7 +953,7 @@ pfctl_show_src_nodes(int dev, int opts) struct pfioc_src_nodes psn; struct pf_src_node *p; char *inbuf = NULL, *newinbuf = NULL; - unsigned len = 0; + unsigned int len = 0; int i; memset(&psn, 0, sizeof(psn)); @@ -1000,7 +998,7 @@ pfctl_show_states(int dev, const char *iface, int opts) struct pfioc_states ps; struct pfsync_state *p; char *inbuf = NULL, *newinbuf = NULL; - unsigned len = 0; + unsigned int len = 0; int i, dotitle = (opts & PF_OPT_SHOWALL); memset(&ps, 0, sizeof(ps)); @@ -1337,7 +1335,7 @@ pfctl_add_altq(struct pfctl *pf, struct pf_altq *a) } int -pfctl_rules(int dev, char *filename, FILE *fin, int opts, int optimize, +pfctl_rules(int dev, char *filename, int opts, int optimize, char *anchorname, struct pfr_buffer *trans) { #define ERR(x) do { warn(x); goto _error; } while(0) @@ -1373,7 +1371,6 @@ pfctl_rules(int dev, char *filename, FILE *fin, int opts, int optimize, if (strlcpy(trs.pfrt_anchor, anchorname, sizeof(trs.pfrt_anchor)) >= sizeof(trs.pfrt_anchor)) ERRX("pfctl_rules: strlcpy"); - infile = filename; pf.dev = dev; pf.opts = opts; pf.optimize = optimize; @@ -1417,7 +1414,7 @@ pfctl_rules(int dev, char *filename, FILE *fin, int opts, int optimize, pfctl_get_ticket(t, PF_RULESET_TABLE, anchorname); } - if (parse_rules(fin, &pf) < 0) { + if (parse_config(filename, &pf) < 0) { if ((opts & PF_OPT_NOACTION) == 0) ERRX("Syntax error in config file: " "pf rules not loaded"); @@ -1443,11 +1440,6 @@ pfctl_rules(int dev, char *filename, FILE *fin, int opts, int optimize, if (check_commit_altq(dev, opts) != 0) ERRX("errors in altq config"); - if (fin != stdin) { - fclose(fin); - fin = NULL; - } - /* process "load anchor" directives */ if (!anchorname[0]) if (pfctl_load_anchors(dev, &pf, t) == -1) @@ -1469,8 +1461,6 @@ _error: err(1, "DIOCXROLLBACK"); exit(1); } else { /* sub ruleset */ - if (fin != NULL && fin != stdin) - fclose(fin); return (-1); } @@ -1502,7 +1492,8 @@ pfctl_fopen(const char *name, const char *mode) void pfctl_init_options(struct pfctl *pf) { - int mib[2], mem; + int64_t mem; + int mib[2]; size_t size; pf->timeout[PFTM_TCP_FIRST_PACKET] = PFTM_TCP_FIRST_PACKET_VAL; @@ -1533,7 +1524,7 @@ pfctl_init_options(struct pfctl *pf) pf->limit[PF_LIMIT_TABLE_ENTRIES] = PFR_KENTRY_HIWAT; mib[0] = CTL_HW; - mib[1] = HW_PHYSMEM; + mib[1] = HW_PHYSMEM64; size = sizeof(mem); (void) sysctl(mib, 2, &mem, &size, NULL, 0); if (mem <= 100*1024*1024) @@ -1559,7 +1550,7 @@ pfctl_load_options(struct pfctl *pf) } /* - * If we've set the limit, but havn't explicitly set adaptive + * If we've set the limit, but haven't explicitly set adaptive * timeouts, do it now with a start of 60% and end of 120%. */ if (pf->limit_set[PF_LIMIT_STATES] && @@ -1957,7 +1948,6 @@ main(int argc, char *argv[]) int optimize = PF_OPTIMIZE_BASIC; char anchorname[MAXPATHLEN]; char *path; - FILE *fin = NULL; if (argc < 2) usage(); @@ -2292,15 +2282,6 @@ main(int argc, char *argv[]) } } - if (rulesopt != NULL) { - if (strcmp(rulesopt, "-") == 0) { - fin = stdin; - rulesopt = "stdin"; - } else { - if ((fin = pfctl_fopen(rulesopt, "r")) == NULL) - err(1, "%s", rulesopt); - } - } if ((rulesopt != NULL) && (loadopt & PFCTL_FLAG_OPTION) && !anchorname[0]) if (pfctl_clear_interface_flags(dev, opts | PF_OPT_QUIET)) @@ -2315,7 +2296,7 @@ main(int argc, char *argv[]) if (anchorname[0] == '_' || strstr(anchorname, "/_") != NULL) errx(1, "anchor names beginning with '_' cannot " "be modified from the command line"); - if (pfctl_rules(dev, rulesopt, fin, opts, optimize, + if (pfctl_rules(dev, rulesopt, opts, optimize, anchorname, NULL)) error = 1; else if (!(opts & PF_OPT_NOACTION) && diff --git a/pfctl/pfctl.h b/pfctl/pfctl.h index 49cf6e75ec7..7b7156e735d 100644 --- a/pfctl/pfctl.h +++ b/pfctl/pfctl.h @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl.h,v 1.41 2007/05/31 04:13:37 mcbride Exp $ */ +/* $OpenBSD: pfctl.h,v 1.42 2007/12/05 12:01:47 chl Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -48,7 +48,6 @@ struct pfr_buffer { (var) != NULL; \ (var) = pfr_buf_next((buf), (var))) -void pfr_set_fd(int); int pfr_get_fd(void); int pfr_clr_tables(struct pfr_table *, int *, int); int pfr_add_tables(struct pfr_table *, int, int *, int); @@ -63,9 +62,7 @@ int pfr_set_addrs(struct pfr_table *, struct pfr_addr *, int, int *, int *, int *, int *, int); int pfr_get_addrs(struct pfr_table *, struct pfr_addr *, int *, int); int pfr_get_astats(struct pfr_table *, struct pfr_astats *, int *, int); -int pfr_clr_astats(struct pfr_table *, struct pfr_addr *, int, int *, int); int pfr_tst_addrs(struct pfr_table *, struct pfr_addr *, int, int *, int); -int pfr_set_tflags(struct pfr_table *, int, int, int, int *, int *, int); int pfr_ina_define(struct pfr_table *, struct pfr_addr *, int, int *, int *, int, int); void pfr_buf_clear(struct pfr_buffer *); diff --git a/pfctl/pfctl_altq.c b/pfctl/pfctl_altq.c index b2397fcd078..d1a46609ccb 100644 --- a/pfctl/pfctl_altq.c +++ b/pfctl/pfctl_altq.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_altq.c,v 1.92 2007/05/27 05:15:17 claudio Exp $ */ +/* $OpenBSD: pfctl_altq.c,v 1.93 2007/10/15 02:16:35 deraadt Exp $ */ /* * Copyright (c) 2002 @@ -138,8 +138,8 @@ qname_to_qid(const char *qname) } void -print_altq(const struct pf_altq *a, unsigned level, struct node_queue_bw *bw, - struct node_queue_opt *qopts) +print_altq(const struct pf_altq *a, unsigned int level, + struct node_queue_bw *bw, struct node_queue_opt *qopts) { if (a->qname[0] != 0) { print_queue(a, level, bw, 1, qopts); @@ -175,10 +175,11 @@ print_altq(const struct pf_altq *a, unsigned level, struct node_queue_bw *bw, } void -print_queue(const struct pf_altq *a, unsigned level, struct node_queue_bw *bw, - int print_interface, struct node_queue_opt *qopts) +print_queue(const struct pf_altq *a, unsigned int level, + struct node_queue_bw *bw, int print_interface, + struct node_queue_opt *qopts) { - unsigned i; + unsigned int i; printf("queue "); for (i = 0; i < level; ++i) diff --git a/pfctl/pfctl_optimize.c b/pfctl/pfctl_optimize.c index 37d9320ac22..8a80232cc5b 100644 --- a/pfctl/pfctl_optimize.c +++ b/pfctl/pfctl_optimize.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_optimize.c,v 1.13 2006/10/31 14:17:45 mcbride Exp $ */ +/* $OpenBSD: pfctl_optimize.c,v 1.16 2008/01/26 13:16:36 mcbride Exp $ */ /* * Copyright (c) 2004 Mike Frantzen @@ -395,7 +395,7 @@ optimize_superblock(struct pfctl *pf, struct superblock *block) * out rules. */ - /* shortcut. there will be alot of 1-rule superblocks */ + /* shortcut. there will be a lot of 1-rule superblocks */ if (!TAILQ_NEXT(TAILQ_FIRST(&block->sb_rules), por_entry)) return (0); @@ -1313,8 +1313,9 @@ again: if (pfctl_define_table(tbl->pt_name, PFR_TFLAG_CONST, 1, - pf->anchor->name, tbl->pt_buf, pf->anchor->ruleset.tticket)) { - warn("failed to create table %s", tbl->pt_name); + pf->astack[0]->name, tbl->pt_buf, pf->astack[0]->ruleset.tticket)) { + warn("failed to create table %s in %s", + tbl->pt_name, pf->astack[0]->name); return (1); } return (0); @@ -1417,7 +1418,7 @@ superblock_inclusive(struct superblock *block, struct pf_opt_rule *por) return (0); /* - * Have to handle interface groups seperately. Consider the following + * Have to handle interface groups separately. Consider the following * rules: * block on EXTIFS to any port 22 * pass on em0 to any port 22 @@ -1465,7 +1466,7 @@ superblock_inclusive(struct superblock *block, struct pf_opt_rule *por) } if (closest >= 0) - DEBUG("superblock break @ %d on %s+%xh", + DEBUG("superblock break @ %d on %s+%lxh", por->por_rule.nr, pf_rule_desc[closest].prf_name, i - pf_rule_desc[closest].prf_offset - diff --git a/pfctl/pfctl_parser.c b/pfctl/pfctl_parser.c index e7b3b852735..e88306b30f4 100644 --- a/pfctl/pfctl_parser.c +++ b/pfctl/pfctl_parser.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_parser.c,v 1.234 2006/10/31 23:46:24 mcbride Exp $ */ +/* $OpenBSD: pfctl_parser.c,v 1.235 2007/10/15 02:16:35 deraadt Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -491,7 +491,7 @@ print_status(struct pf_status *s, int opts) running = s->running ? "Enabled" : "Disabled"; if (s->since) { - unsigned sec, min, hrs, day = runtime; + unsigned int sec, min, hrs, day = runtime; sec = day % 60; day /= 60; diff --git a/pfctl/pfctl_parser.h b/pfctl/pfctl_parser.h index b901fb906ec..97b0325ddc7 100644 --- a/pfctl/pfctl_parser.h +++ b/pfctl/pfctl_parser.h @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_parser.h,v 1.86 2006/10/31 23:46:25 mcbride Exp $ */ +/* $OpenBSD: pfctl_parser.h,v 1.87 2007/10/13 16:35:18 deraadt Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -187,7 +187,7 @@ struct pf_opt_rule { TAILQ_HEAD(pf_opt_queue, pf_opt_rule); -int pfctl_rules(int, char *, FILE *, int, int, char *, struct pfr_buffer *); +int pfctl_rules(int, char *, int, int, char *, struct pfr_buffer *); int pfctl_optimize_ruleset(struct pfctl *, struct pf_ruleset *); int pfctl_add_rule(struct pfctl *, struct pf_rule *, const char *); @@ -204,7 +204,7 @@ int pfctl_set_hostid(struct pfctl *, u_int32_t); int pfctl_set_debug(struct pfctl *, char *); int pfctl_set_interface_flags(struct pfctl *, char *, int, int); -int parse_rules(FILE *, struct pfctl *); +int parse_config(char *, struct pfctl *); int parse_flags(char *); int pfctl_load_anchors(int, struct pfctl *, struct pfr_buffer *); diff --git a/pfctl/pfctl_qstats.c b/pfctl/pfctl_qstats.c index 1731ce9ba3b..ba0c18aef5b 100644 --- a/pfctl/pfctl_qstats.c +++ b/pfctl/pfctl_qstats.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_qstats.c,v 1.30 2004/04/27 21:47:32 kjc Exp $ */ +/* $OpenBSD: pfctl_qstats.c,v 1.31 2007/10/15 02:16:35 deraadt Exp $ */ /* * Copyright (c) Henning Brauer @@ -233,8 +233,8 @@ pfctl_find_altq_node(struct pf_altq_node *root, const char *qname, } void -pfctl_print_altq_node(int dev, const struct pf_altq_node *node, unsigned level, - int opts) +pfctl_print_altq_node(int dev, const struct pf_altq_node *node, + unsigned int level, int opts) { const struct pf_altq_node *child; diff --git a/pfctl/pfctl_radix.c b/pfctl/pfctl_radix.c index 01ad4758ff1..becd0305b83 100644 --- a/pfctl/pfctl_radix.c +++ b/pfctl/pfctl_radix.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_radix.c,v 1.27 2005/05/21 21:03:58 henning Exp $ */ +/* $OpenBSD: pfctl_radix.c,v 1.28 2007/12/05 12:01:47 chl Exp $ */ /* * Copyright (c) 2002 Cedric Berger @@ -299,29 +299,6 @@ pfr_get_astats(struct pfr_table *tbl, struct pfr_astats *addr, int *size, return (0); } -int -pfr_clr_astats(struct pfr_table *tbl, struct pfr_addr *addr, int size, - int *nzero, int flags) -{ - struct pfioc_table io; - - if (tbl == NULL || size < 0 || (size && addr == NULL)) { - errno = EINVAL; - return (-1); - } - bzero(&io, sizeof io); - io.pfrio_flags = flags; - io.pfrio_table = *tbl; - io.pfrio_buffer = addr; - io.pfrio_esize = sizeof(*addr); - io.pfrio_size = size; - if (ioctl(dev, DIOCRCLRASTATS, &io)) - return (-1); - if (nzero != NULL) - *nzero = io.pfrio_nzero; - return (0); -} - int pfr_clr_tstats(struct pfr_table *tbl, int size, int *nzero, int flags) { @@ -343,32 +320,6 @@ pfr_clr_tstats(struct pfr_table *tbl, int size, int *nzero, int flags) return (0); } -int -pfr_set_tflags(struct pfr_table *tbl, int size, int setflag, int clrflag, - int *nchange, int *ndel, int flags) -{ - struct pfioc_table io; - - if (size < 0 || (size && !tbl)) { - errno = EINVAL; - return (-1); - } - bzero(&io, sizeof io); - io.pfrio_flags = flags; - io.pfrio_buffer = tbl; - io.pfrio_esize = sizeof(*tbl); - io.pfrio_size = size; - io.pfrio_setflag = setflag; - io.pfrio_clrflag = clrflag; - if (ioctl(dev, DIOCRSETTFLAGS, &io)) - return (-1); - if (nchange) - *nchange = io.pfrio_nchange; - if (ndel) - *ndel = io.pfrio_ndel; - return (0); -} - int pfr_tst_addrs(struct pfr_table *tbl, struct pfr_addr *addr, int size, int *nmatch, int flags) diff --git a/pflogd/pflogd.8 b/pflogd/pflogd.8 index 4c5762b380b..e16f866ea85 100644 --- a/pflogd/pflogd.8 +++ b/pflogd/pflogd.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pflogd.8,v 1.35 2007/05/31 19:19:47 jmc Exp $ +.\" $OpenBSD: pflogd.8,v 1.36 2008/01/14 17:03:42 okan Exp $ .\" .\" Copyright (c) 2001 Can Erkin Acar. All rights reserved. .\" @@ -24,7 +24,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.Dd $Mdocdate$ +.Dd $Mdocdate: May 31 2007 $ .Dt PFLOGD 8 .Os .Sh NAME @@ -118,13 +118,12 @@ By default, will use .Ar pflog0 . .It Fl p Ar pidfile -Writes a file containing the process ID of the program. +Writes a file containing the process ID of the program to +.Pa /var/run . The file name has the form -.Pa /var/run/pidname.pid . -If the option is not given, -.Ar pidfile -defaults to -.Pa pflogd . +.Ao Ar pidfile Ac Ns .pid . +The default is +.Ar pflogd . .It Fl s Ar snaplen Analyze at most the first .Ar snaplen From 89a3159080a774bd9de50eaf1861a1f0c1657a9f Mon Sep 17 00:00:00 2001 From: Max Laier Date: Wed, 10 Dec 2008 21:08:42 +0000 Subject: [PATCH 05/39] Import OPENBSD_4_4_BASE and libevent 1.3e --- authpf/authpf.8 | 6 +- ftp-proxy/filter.c | 4 +- ftp-proxy/ftp-proxy.c | 21 +- libevent/buffer.c | 22 +- libevent/event-internal.h | 5 + libevent/event.c | 174 ++++++++----- libevent/event.h | 41 ++-- libevent/evsignal.h | 13 +- libevent/kqueue.c | 32 ++- libevent/poll.c | 29 ++- libevent/select.c | 25 +- libevent/signal.c | 85 ++++--- man/pf.conf.5 | 61 ++++- man/pfsync.4 | 6 +- pfctl/parse.y | 505 +++++++++++++++++++++++--------------- pfctl/pf_print_state.c | 110 +++++---- pfctl/pfctl.8 | 71 ++++-- pfctl/pfctl.c | 132 +++++++--- pfctl/pfctl.h | 4 +- pfctl/pfctl_altq.c | 3 +- pfctl/pfctl_optimize.c | 6 +- pfctl/pfctl_parser.c | 30 ++- pfctl/pfctl_table.c | 13 +- pflogd/privsep_fdpass.c | 20 +- tftp-proxy/tftp-proxy.c | 16 +- 25 files changed, 922 insertions(+), 512 deletions(-) diff --git a/authpf/authpf.8 b/authpf/authpf.8 index be1f0c46fde..6b6afa4616c 100644 --- a/authpf/authpf.8 +++ b/authpf/authpf.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: authpf.8,v 1.45 2008/02/14 01:49:17 mcbride Exp $ +.\" $OpenBSD: authpf.8,v 1.46 2008/03/18 23:03:14 merdely Exp $ .\" .\" Copyright (c) 1998-2007 Bob Beck (beck@openbsd.org>. All rights reserved. .\" @@ -14,7 +14,7 @@ .\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF .\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .\" -.Dd $Mdocdate: May 31 2007 $ +.Dd $Mdocdate: February 14 2008 $ .Dt AUTHPF 8 .Os .Sh NAME @@ -56,7 +56,7 @@ in this case the client's IP address is not provided to the packet filter via the .Ar client_ip macro or the -.Ar authpf users +.Ar authpf_users table. Additionally, states associated with the client IP address are not purged when the session is ended. diff --git a/ftp-proxy/filter.c b/ftp-proxy/filter.c index d99dfcbd6b1..80625a6fd9c 100644 --- a/ftp-proxy/filter.c +++ b/ftp-proxy/filter.c @@ -1,4 +1,4 @@ -/* $OpenBSD: filter.c,v 1.7 2008/02/26 18:52:53 henning Exp $ */ +/* $OpenBSD: filter.c,v 1.8 2008/06/13 07:25:26 claudio Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, @@ -173,7 +173,7 @@ init_filter(char *opt_qname, char *opt_tagname, int opt_verbose) dev = open("/dev/pf", O_RDWR); if (dev == -1) - err(1, "/dev/pf"); + err(1, "open /dev/pf"); if (ioctl(dev, DIOCGETSTATUS, &status) == -1) err(1, "DIOCGETSTATUS"); if (!status.running) diff --git a/ftp-proxy/ftp-proxy.c b/ftp-proxy/ftp-proxy.c index 1a3bdf55fbd..131991a4bb8 100644 --- a/ftp-proxy/ftp-proxy.c +++ b/ftp-proxy/ftp-proxy.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ftp-proxy.c,v 1.16 2008/02/26 18:52:53 henning Exp $ */ +/* $OpenBSD: ftp-proxy.c,v 1.19 2008/06/13 07:25:26 claudio Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, @@ -91,7 +91,7 @@ int client_parse_cmd(struct session *s); void client_read(struct bufferevent *, void *); int drop_privs(void); void end_session(struct session *); -int exit_daemon(void); +void exit_daemon(void); int getline(char *, size_t *); void handle_connection(const int, short, void *); void handle_signal(int, short, void *); @@ -282,6 +282,12 @@ end_session(struct session *s) logmsg(LOG_INFO, "#%d ending session", s->id); + /* Flush output buffers. */ + if (s->client_bufev && s->client_fd != -1) + evbuffer_write(s->client_bufev->output, s->client_fd); + if (s->server_bufev && s->server_fd != -1) + evbuffer_write(s->server_bufev->output, s->server_fd); + if (s->client_fd != -1) close(s->client_fd); if (s->server_fd != -1) @@ -309,7 +315,7 @@ end_session(struct session *s) session_count--; } -int +void exit_daemon(void) { struct session *s, *next; @@ -323,9 +329,6 @@ exit_daemon(void) closelog(); exit(0); - - /* NOTREACHED */ - return (-1); } int @@ -519,7 +522,7 @@ handle_signal(int sig, short event, void *arg) * Signal handler rules don't apply, libevent decouples for us. */ - logmsg(LOG_ERR, "%s exiting on signal %d", __progname, sig); + logmsg(LOG_ERR, "exiting on signal %d", sig); exit_daemon(); } @@ -834,8 +837,8 @@ u_int16_t pick_proxy_port(void) { /* Random should be good enough for avoiding port collisions. */ - return (IPPORT_HIFIRSTAUTO + (arc4random() % - (IPPORT_HILASTAUTO - IPPORT_HIFIRSTAUTO))); + return (IPPORT_HIFIRSTAUTO + + arc4random_uniform(IPPORT_HILASTAUTO - IPPORT_HIFIRSTAUTO)); } void diff --git a/libevent/buffer.c b/libevent/buffer.c index 77efd0cfa3e..0327eb54938 100644 --- a/libevent/buffer.c +++ b/libevent/buffer.c @@ -44,6 +44,7 @@ #include #endif +#include #include #include #include @@ -106,7 +107,7 @@ evbuffer_add_buffer(struct evbuffer *outbuf, struct evbuffer *inbuf) /* * Optimization comes with a price; we need to notify the * buffer if necessary of the changes. oldoff is the amount - * of data that we tranfered from inbuf to outbuf + * of data that we transfered from inbuf to outbuf */ if (inbuf->off != oldoff && inbuf->cb != NULL) (*inbuf->cb)(inbuf, oldoff, inbuf->off, inbuf->cbarg); @@ -134,9 +135,13 @@ evbuffer_add_vprintf(struct evbuffer *buf, const char *fmt, va_list ap) int sz; va_list aq; + /* make sure that at least some space is available */ + evbuffer_expand(buf, 64); for (;;) { + size_t used = buf->misalign + buf->off; buffer = (char *)buf->buffer + buf->off; - space = buf->totallen - buf->misalign - buf->off; + assert(buf->totallen >= used); + space = buf->totallen - used; #ifndef va_copy #define va_copy(dst, src) memcpy(&(dst), &(src), sizeof(va_list)) @@ -152,7 +157,7 @@ evbuffer_add_vprintf(struct evbuffer *buf, const char *fmt, va_list ap) va_end(aq); - if (sz == -1) + if (sz < 0) return (-1); if (sz < space) { buf->off += sz; @@ -244,7 +249,7 @@ evbuffer_readline(struct evbuffer *buffer) /* Adds data to an event buffer */ -static inline void +static void evbuffer_align(struct evbuffer *buf) { memmove(buf->orig_buffer, buf->buffer, buf->off); @@ -431,13 +436,12 @@ evbuffer_write(struct evbuffer *buffer, int fd) u_char * evbuffer_find(struct evbuffer *buffer, const u_char *what, size_t len) { - size_t remain = buffer->off; - u_char *search = buffer->buffer; + u_char *search = buffer->buffer, *end = search + buffer->off; u_char *p; - while ((p = memchr(search, *what, remain)) != NULL) { - remain = buffer->off - (size_t)(search - buffer->buffer); - if (remain < len) + while (search < end && + (p = memchr(search, *what, end - search)) != NULL) { + if (p + len > end) break; if (memcmp(p, what, len) == 0) return (p); diff --git a/libevent/event-internal.h b/libevent/event-internal.h index becb6691d52..7fd4b6c690f 100644 --- a/libevent/event-internal.h +++ b/libevent/event-internal.h @@ -31,6 +31,8 @@ extern "C" { #endif +#include "evsignal.h" + struct event_base { const struct eventop *evsel; void *evbase; @@ -43,6 +45,9 @@ struct event_base { struct event_list **activequeues; int nactivequeues; + /* signal handling info */ + struct evsignal_info sig; + struct event_list eventqueue; struct timeval event_tv; diff --git a/libevent/event.c b/libevent/event.c index f6d2b1cc42c..15bf14cf3b4 100644 --- a/libevent/event.c +++ b/libevent/event.c @@ -51,6 +51,7 @@ #include #include #include +#include #include "event.h" #include "event-internal.h" @@ -111,9 +112,9 @@ const struct eventop *eventops[] = { }; /* Global state */ -struct event_list signalqueue; - struct event_base *current_base = NULL; +extern struct event_base *evsignal_base; +static int use_monotonic; /* Handle signals - This is a deprecated interface */ int (*event_sigcb)(void); /* Signal callback when gotsig is set */ @@ -126,7 +127,7 @@ static int event_haveevents(struct event_base *); static void event_process_active(struct event_base *); -static int timeout_next(struct event_base *, struct timeval *); +static int timeout_next(struct event_base *, struct timeval **); static void timeout_process(struct event_base *); static void timeout_correct(struct event_base *, struct timeval *); @@ -144,25 +145,34 @@ compare(struct event *a, struct event *b) return (0); } +static void +detect_monotonic(void) +{ +#if defined(HAVE_CLOCK_GETTIME) && defined(CLOCK_MONOTONIC) + struct timespec ts; + + if (clock_gettime(CLOCK_MONOTONIC, &ts) == 0) + use_monotonic = 1; +#endif +} + static int gettime(struct timeval *tp) { -#ifdef HAVE_CLOCK_GETTIME +#if defined(HAVE_CLOCK_GETTIME) && defined(CLOCK_MONOTONIC) struct timespec ts; -#ifdef HAVE_CLOCK_MONOTONIC - if (clock_gettime(CLOCK_MONOTONIC, &ts) == -1) -#else - if (clock_gettime(CLOCK_REALTIME, &ts) == -1) -#endif - return (-1); - tp->tv_sec = ts.tv_sec; - tp->tv_usec = ts.tv_nsec / 1000; -#else - gettimeofday(tp, NULL); + if (use_monotonic) { + if (clock_gettime(CLOCK_MONOTONIC, &ts) == -1) + return (-1); + + tp->tv_sec = ts.tv_sec; + tp->tv_usec = ts.tv_nsec / 1000; + return (0); + } #endif - return (0); + return (gettimeofday(tp, NULL)); } RB_PROTOTYPE(event_tree, event, ev_timeout_node, compare); @@ -174,36 +184,42 @@ void * event_init(void) { int i; + struct event_base *base; - if ((current_base = calloc(1, sizeof(struct event_base))) == NULL) + if ((base = calloc(1, sizeof(struct event_base))) == NULL) event_err(1, "%s: calloc"); event_sigcb = NULL; event_gotsig = 0; - gettime(¤t_base->event_tv); - - RB_INIT(¤t_base->timetree); - TAILQ_INIT(¤t_base->eventqueue); - TAILQ_INIT(&signalqueue); - - current_base->evbase = NULL; - for (i = 0; eventops[i] && !current_base->evbase; i++) { - current_base->evsel = eventops[i]; - current_base->evbase = current_base->evsel->init(); + detect_monotonic(); + gettime(&base->event_tv); + + RB_INIT(&base->timetree); + TAILQ_INIT(&base->eventqueue); + TAILQ_INIT(&base->sig.signalqueue); + base->sig.ev_signal_pair[0] = -1; + base->sig.ev_signal_pair[1] = -1; + + base->evbase = NULL; + for (i = 0; eventops[i] && !base->evbase; i++) { + base->evsel = eventops[i]; + + base->evbase = base->evsel->init(base); } - if (current_base->evbase == NULL) + if (base->evbase == NULL) event_errx(1, "%s: no event mechanism available", __func__); if (getenv("EVENT_SHOW_METHOD")) event_msgx("libevent using: %s\n", - current_base->evsel->name); + base->evsel->name); /* allocate a single active event queue */ - event_base_priority_init(current_base, 1); + event_base_priority_init(base, 1); - return (current_base); + current_base = base; + return (base); } void @@ -217,7 +233,8 @@ event_base_free(struct event_base *base) current_base = NULL; assert(base); - assert(TAILQ_EMPTY(&base->eventqueue)); + if (base->evsel->dealloc != NULL) + base->evsel->dealloc(base, base->evbase); for (i=0; i < base->nactivequeues; ++i) assert(TAILQ_EMPTY(base->activequeues[i])); @@ -227,8 +244,7 @@ event_base_free(struct event_base *base) free(base->activequeues[i]); free(base->activequeues); - if (base->evsel->dealloc != NULL) - base->evsel->dealloc(base->evbase); + assert(TAILQ_EMPTY(&base->eventqueue)); free(base); } @@ -343,7 +359,6 @@ event_loopexit_cb(int fd, short what, void *arg) } /* not thread safe */ - int event_loopexit(struct timeval *tv) { @@ -354,7 +369,7 @@ event_loopexit(struct timeval *tv) int event_base_loopexit(struct event_base *event_base, struct timeval *tv) { - return (event_once(-1, EV_TIMEOUT, event_loopexit_cb, + return (event_base_once(event_base, -1, EV_TIMEOUT, event_loopexit_cb, event_base, tv)); } @@ -372,8 +387,13 @@ event_base_loop(struct event_base *base, int flags) const struct eventop *evsel = base->evsel; void *evbase = base->evbase; struct timeval tv; + struct timeval *tv_p; int res, done; +#ifndef WIN32 + if(!TAILQ_EMPTY(&base->sig.signalqueue)) + evsignal_base = base; +#endif done = 0; while (!done) { /* Calculate the initial events that we are waiting for */ @@ -398,21 +418,18 @@ event_base_loop(struct event_base *base, int flags) } } - /* Check if time is running backwards */ - gettime(&tv); - if (timercmp(&tv, &base->event_tv, <)) { - struct timeval off; - event_debug(("%s: time is running backwards, corrected", - __func__)); - timersub(&base->event_tv, &tv, &off); - timeout_correct(base, &off); - } - base->event_tv = tv; + timeout_correct(base, &tv); - if (!base->event_count_active && !(flags & EVLOOP_NONBLOCK)) - timeout_next(base, &tv); - else + tv_p = &tv; + if (!base->event_count_active && !(flags & EVLOOP_NONBLOCK)) { + timeout_next(base, &tv_p); + } else { + /* + * if we have active events, we just poll new events + * without waiting. + */ timerclear(&tv); + } /* If we have no events, we just exit */ if (!event_haveevents(base)) { @@ -420,7 +437,8 @@ event_base_loop(struct event_base *base, int flags) return (1); } - res = evsel->dispatch(base, evbase, &tv); + res = evsel->dispatch(base, evbase, tv_p); + if (res == -1) return (-1); @@ -459,11 +477,18 @@ event_once_cb(int fd, short events, void *arg) free(eonce); } -/* Schedules an event once */ - +/* not threadsafe, event scheduled once. */ int event_once(int fd, short events, void (*callback)(int, short, void *), void *arg, struct timeval *tv) +{ + return event_base_once(current_base, fd, events, callback, arg, tv); +} + +/* Schedules an event once */ +int +event_base_once(struct event_base *base, int fd, short events, + void (*callback)(int, short, void *), void *arg, struct timeval *tv) { struct event_once *eonce; struct timeval etv; @@ -496,7 +521,9 @@ event_once(int fd, short events, return (-1); } - res = event_add(&eonce->ev, tv); + res = event_base_set(base, &eonce->ev); + if (res == 0) + res = event_add(&eonce->ev, tv); if (res != 0) { free(eonce); return (res); @@ -516,12 +543,14 @@ event_set(struct event *ev, int fd, short events, ev->ev_arg = arg; ev->ev_fd = fd; ev->ev_events = events; + ev->ev_res = 0; ev->ev_flags = EVLIST_INIT; ev->ev_ncalls = 0; ev->ev_pncalls = NULL; /* by default, we put new events into the middle priority */ - ev->ev_pri = current_base->nactivequeues/2; + if(current_base) + ev->ev_pri = current_base->nactivequeues/2; } int @@ -710,16 +739,16 @@ event_active(struct event *ev, int res, short ncalls) event_queue_insert(ev->ev_base, ev, EVLIST_ACTIVE); } -int -timeout_next(struct event_base *base, struct timeval *tv) +static int +timeout_next(struct event_base *base, struct timeval **tv_p) { - struct timeval dflt = TIMEOUT_DEFAULT; - struct timeval now; struct event *ev; + struct timeval *tv = *tv_p; if ((ev = RB_MIN(event_tree, &base->timetree)) == NULL) { - *tv = dflt; + /* if no time-based events are active wait for I/O */ + *tv_p = NULL; return (0); } @@ -740,17 +769,38 @@ timeout_next(struct event_base *base, struct timeval *tv) return (0); } +/* + * Determines if the time is running backwards by comparing the current + * time against the last time we checked. Not needed when using clock + * monotonic. + */ + static void -timeout_correct(struct event_base *base, struct timeval *off) +timeout_correct(struct event_base *base, struct timeval *tv) { struct event *ev; + struct timeval off; + + if (use_monotonic) + return; + + /* Check if time is running backwards */ + gettime(tv); + if (timercmp(tv, &base->event_tv, >=)) { + base->event_tv = *tv; + return; + } + + event_debug(("%s: time is running backwards, corrected", + __func__)); + timersub(&base->event_tv, tv, &off); /* * We can modify the key element of the node without destroying * the key, beause we apply it to all in the right order. */ RB_FOREACH(ev, event_tree, &base->timetree) - timersub(&ev->ev_timeout, off, &ev->ev_timeout); + timersub(&ev->ev_timeout, &off, &ev->ev_timeout); } void @@ -801,7 +851,7 @@ event_queue_remove(struct event_base *base, struct event *ev, int queue) ev, ev_active_next); break; case EVLIST_SIGNAL: - TAILQ_REMOVE(&signalqueue, ev, ev_signal_next); + TAILQ_REMOVE(&base->sig.signalqueue, ev, ev_signal_next); break; case EVLIST_TIMEOUT: RB_REMOVE(event_tree, &base->timetree, ev); @@ -843,7 +893,7 @@ event_queue_insert(struct event_base *base, struct event *ev, int queue) ev,ev_active_next); break; case EVLIST_SIGNAL: - TAILQ_INSERT_TAIL(&signalqueue, ev, ev_signal_next); + TAILQ_INSERT_TAIL(&base->sig.signalqueue, ev, ev_signal_next); break; case EVLIST_TIMEOUT: { struct event *tmp = RB_INSERT(event_tree, &base->timetree, ev); diff --git a/libevent/event.h b/libevent/event.h index 3f2032dd068..4c39939cc50 100644 --- a/libevent/event.h +++ b/libevent/event.h @@ -31,6 +31,8 @@ extern "C" { #endif +#include +#include #include #ifdef WIN32 @@ -131,16 +133,14 @@ TAILQ_HEAD (evkeyvalq, evkeyval); struct eventop { char *name; - void *(*init)(void); + void *(*init)(struct event_base *); int (*add)(void *, struct event *); int (*del)(void *, struct event *); int (*recalc)(struct event_base *, void *, int); int (*dispatch)(struct event_base *, void *, struct timeval *); - void (*dealloc)(void *); + void (*dealloc)(struct event_base *, void *); }; -#define TIMEOUT_DEFAULT {5, 0} - void *event_init(void); int event_dispatch(void); int event_base_dispatch(struct event_base *); @@ -184,6 +184,7 @@ int event_base_loopexit(struct event_base *, struct timeval *); void event_set(struct event *, int, short, void (*)(int, short, void *), void *); int event_once(int, short, void (*)(int, short, void *), void *, struct timeval *); +int event_base_once(struct event_base *, int, short, void (*)(int, short, void *), void *, struct timeval *); int event_add(struct event *, struct timeval *); int event_del(struct event *); @@ -299,39 +300,37 @@ void evbuffer_setcb(struct evbuffer *, void (*)(struct evbuffer *, size_t, size_ void evtag_init(void); -void evtag_marshal(struct evbuffer *evbuf, u_int8_t tag, const void *data, - u_int32_t len); +void evtag_marshal(struct evbuffer *evbuf, uint8_t tag, const void *data, + uint32_t len); -void encode_int(struct evbuffer *evbuf, u_int32_t number); +void encode_int(struct evbuffer *evbuf, uint32_t number); -void evtag_marshal_int(struct evbuffer *evbuf, u_int8_t tag, - u_int32_t integer); +void evtag_marshal_int(struct evbuffer *evbuf, uint8_t tag, uint32_t integer); -void evtag_marshal_string(struct evbuffer *buf, u_int8_t tag, +void evtag_marshal_string(struct evbuffer *buf, uint8_t tag, const char *string); -void evtag_marshal_timeval(struct evbuffer *evbuf, u_int8_t tag, +void evtag_marshal_timeval(struct evbuffer *evbuf, uint8_t tag, struct timeval *tv); void evtag_test(void); -int evtag_unmarshal(struct evbuffer *src, u_int8_t *ptag, - struct evbuffer *dst); -int evtag_peek(struct evbuffer *evbuf, u_int8_t *ptag); -int evtag_peek_length(struct evbuffer *evbuf, u_int32_t *plength); -int evtag_payload_length(struct evbuffer *evbuf, u_int32_t *plength); +int evtag_unmarshal(struct evbuffer *src, uint8_t *ptag, struct evbuffer *dst); +int evtag_peek(struct evbuffer *evbuf, uint8_t *ptag); +int evtag_peek_length(struct evbuffer *evbuf, uint32_t *plength); +int evtag_payload_length(struct evbuffer *evbuf, uint32_t *plength); int evtag_consume(struct evbuffer *evbuf); -int evtag_unmarshal_int(struct evbuffer *evbuf, u_int8_t need_tag, - u_int32_t *pinteger); +int evtag_unmarshal_int(struct evbuffer *evbuf, uint8_t need_tag, + uint32_t *pinteger); -int evtag_unmarshal_fixed(struct evbuffer *src, u_int8_t need_tag, void *data, +int evtag_unmarshal_fixed(struct evbuffer *src, uint8_t need_tag, void *data, size_t len); -int evtag_unmarshal_string(struct evbuffer *evbuf, u_int8_t need_tag, +int evtag_unmarshal_string(struct evbuffer *evbuf, uint8_t need_tag, char **pstring); -int evtag_unmarshal_timeval(struct evbuffer *evbuf, u_int8_t need_tag, +int evtag_unmarshal_timeval(struct evbuffer *evbuf, uint8_t need_tag, struct timeval *ptv); #ifdef __cplusplus diff --git a/libevent/evsignal.h b/libevent/evsignal.h index 5b92bd6e55f..7efbcabec89 100644 --- a/libevent/evsignal.h +++ b/libevent/evsignal.h @@ -27,9 +27,18 @@ #ifndef _EVSIGNAL_H_ #define _EVSIGNAL_H_ -void evsignal_init(void); -void evsignal_process(void); +struct evsignal_info { + struct event_list signalqueue; + struct event ev_signal; + int ev_signal_pair[2]; + int ev_signal_added; + volatile sig_atomic_t evsignal_caught; + sig_atomic_t evsigcaught[NSIG]; +}; +void evsignal_init(struct event_base *); +void evsignal_process(struct event_base *); int evsignal_add(struct event *); int evsignal_del(struct event *); +void evsignal_dealloc(struct event_base *); #endif /* _EVSIGNAL_H_ */ diff --git a/libevent/kqueue.c b/libevent/kqueue.c index 08369c6dd51..059d94a0b4d 100644 --- a/libevent/kqueue.c +++ b/libevent/kqueue.c @@ -48,10 +48,13 @@ #include #endif -#if defined(HAVE_INTTYPES_H) && !defined(__OpenBSD__) && !defined(__FreeBSD__) -#define INTPTR(x) (intptr_t)x +/* Some platforms apparently define the udata field of struct kevent as + * ntptr_t, whereas others define it as void*. There doesn't seem to be an + * easy way to tell them apart via autoconf, so we need to use OS macros. */ +#if defined(HAVE_INTTYPES_H) && !defined(__OpenBSD__) && !defined(__FreeBSD__) && !defined(__darwin__) && !defined(__APPLE__) +#define PTR_TO_UDATA(x) ((intptr_t)(x)) #else -#define INTPTR(x) x +#define PTR_TO_UDATA(x) (x) #endif #include "event.h" @@ -69,13 +72,13 @@ struct kqop { int kq; }; -void *kq_init (void); +void *kq_init (struct event_base *); int kq_add (void *, struct event *); int kq_del (void *, struct event *); int kq_recalc (struct event_base *, void *, int); int kq_dispatch (struct event_base *, void *, struct timeval *); int kq_insert (struct kqop *, struct kevent *); -void kq_dealloc (void *); +void kq_dealloc (struct event_base *, void *); const struct eventop kqops = { "kqueue", @@ -88,7 +91,7 @@ const struct eventop kqops = { }; void * -kq_init(void) +kq_init(struct event_base *base) { int kq; struct kqop *kqueueop; @@ -212,13 +215,16 @@ kq_dispatch(struct event_base *base, void *arg, struct timeval *tv) struct kevent *changes = kqop->changes; struct kevent *events = kqop->events; struct event *ev; - struct timespec ts; + struct timespec ts, *ts_p = NULL; int i, res; - TIMEVAL_TO_TIMESPEC(tv, &ts); + if (tv != NULL) { + TIMEVAL_TO_TIMESPEC(tv, &ts); + ts_p = &ts; + } res = kevent(kqop->kq, changes, kqop->nchanges, - events, kqop->nevents, &ts); + events, kqop->nevents, ts_p); kqop->nchanges = 0; if (res == -1) { if (errno != EINTR) { @@ -294,7 +300,7 @@ kq_add(void *arg, struct event *ev) kev.flags = EV_ADD; if (!(ev->ev_events & EV_PERSIST)) kev.flags |= EV_ONESHOT; - kev.udata = INTPTR(ev); + kev.udata = PTR_TO_UDATA(ev); if (kq_insert(kqop, &kev) == -1) return (-1); @@ -317,7 +323,7 @@ kq_add(void *arg, struct event *ev) kev.flags = EV_ADD; if (!(ev->ev_events & EV_PERSIST)) kev.flags |= EV_ONESHOT; - kev.udata = INTPTR(ev); + kev.udata = PTR_TO_UDATA(ev); if (kq_insert(kqop, &kev) == -1) return (-1); @@ -332,7 +338,7 @@ kq_add(void *arg, struct event *ev) kev.flags = EV_ADD; if (!(ev->ev_events & EV_PERSIST)) kev.flags |= EV_ONESHOT; - kev.udata = INTPTR(ev); + kev.udata = PTR_TO_UDATA(ev); if (kq_insert(kqop, &kev) == -1) return (-1); @@ -398,7 +404,7 @@ kq_del(void *arg, struct event *ev) } void -kq_dealloc(void *arg) +kq_dealloc(struct event_base *base, void *arg) { struct kqop *kqop = arg; diff --git a/libevent/poll.c b/libevent/poll.c index 14ca8453739..123d36a5602 100644 --- a/libevent/poll.c +++ b/libevent/poll.c @@ -54,8 +54,6 @@ #include "evsignal.h" #include "log.h" -extern volatile sig_atomic_t evsignal_caught; - struct pollop { int event_count; /* Highest number alloc */ int nfds; /* Size of event_* */ @@ -68,12 +66,12 @@ struct pollop { * "no entry." */ }; -void *poll_init (void); +void *poll_init (struct event_base *); int poll_add (void *, struct event *); int poll_del (void *, struct event *); int poll_recalc (struct event_base *, void *, int); int poll_dispatch (struct event_base *, void *, struct timeval *); -void poll_dealloc (void *); +void poll_dealloc (struct event_base *, void *); const struct eventop pollops = { "poll", @@ -86,7 +84,7 @@ const struct eventop pollops = { }; void * -poll_init(void) +poll_init(struct event_base *base) { struct pollop *pollop; @@ -97,7 +95,7 @@ poll_init(void) if (!(pollop = calloc(1, sizeof(struct pollop)))) return (NULL); - evsignal_init(); + evsignal_init(base); return (pollop); } @@ -150,13 +148,16 @@ poll_check_ok(struct pollop *pop) int poll_dispatch(struct event_base *base, void *arg, struct timeval *tv) { - int res, i, sec, nfds; + int res, i, msec = -1, nfds; struct pollop *pop = arg; poll_check_ok(pop); - sec = tv->tv_sec * 1000 + (tv->tv_usec + 999) / 1000; + + if (tv != NULL) + msec = tv->tv_sec * 1000 + (tv->tv_usec + 999) / 1000; + nfds = pop->nfds; - res = poll(pop->event_set, nfds, sec); + res = poll(pop->event_set, nfds, msec); if (res == -1) { if (errno != EINTR) { @@ -164,10 +165,11 @@ poll_dispatch(struct event_base *base, void *arg, struct timeval *tv) return (-1); } - evsignal_process(); + evsignal_process(base); return (0); - } else if (evsignal_caught) - evsignal_process(); + } else if (base->sig.evsignal_caught) { + evsignal_process(base); + } event_debug(("%s: poll reports %d", __func__, res)); @@ -370,10 +372,11 @@ poll_del(void *arg, struct event *ev) } void -poll_dealloc(void *arg) +poll_dealloc(struct event_base *base, void *arg) { struct pollop *pop = arg; + evsignal_dealloc(base); if (pop->event_set) free(pop->event_set); if (pop->event_r_back) diff --git a/libevent/select.c b/libevent/select.c index 6ce81a232bb..d645f1a3703 100644 --- a/libevent/select.c +++ b/libevent/select.c @@ -36,6 +36,9 @@ #else #include #endif +#ifdef HAVE_SYS_SELECT_H +#include +#endif #include #include #include @@ -57,8 +60,6 @@ #define howmany(x, y) (((x)+((y)-1))/(y)) #endif -extern volatile sig_atomic_t evsignal_caught; - struct selectop { int event_fds; /* Highest fd in fd set */ int event_fdsz; @@ -70,12 +71,12 @@ struct selectop { struct event **event_w_by_fd; }; -void *select_init (void); +void *select_init (struct event_base *); int select_add (void *, struct event *); int select_del (void *, struct event *); int select_recalc (struct event_base *, void *, int); int select_dispatch (struct event_base *, void *, struct timeval *); -void select_dealloc (void *); +void select_dealloc (struct event_base *, void *); const struct eventop selectops = { "select", @@ -90,7 +91,7 @@ const struct eventop selectops = { static int select_resize(struct selectop *sop, int fdsz); void * -select_init(void) +select_init(struct event_base *base) { struct selectop *sop; @@ -103,7 +104,7 @@ select_init(void) select_resize(sop, howmany(32 + 1, NFDBITS)*sizeof(fd_mask)); - evsignal_init(); + evsignal_init(base); return (sop); } @@ -113,7 +114,7 @@ static void check_selectop(struct selectop *sop) { int i; - for (i=0;i<=sop->event_fds;++i) { + for (i = 0; i <= sop->event_fds; ++i) { if (FD_ISSET(i, sop->event_readset_in)) { assert(sop->event_r_by_fd[i]); assert(sop->event_r_by_fd[i]->ev_events & EV_READ); @@ -174,10 +175,11 @@ select_dispatch(struct event_base *base, void *arg, struct timeval *tv) return (-1); } - evsignal_process(); + evsignal_process(base); return (0); - } else if (evsignal_caught) - evsignal_process(); + } else if (base->sig.evsignal_caught) { + evsignal_process(base); + } event_debug(("%s: select reports %d", __func__, res)); @@ -348,10 +350,11 @@ select_del(void *arg, struct event *ev) } void -select_dealloc(void *arg) +select_dealloc(struct event_base *base, void *arg) { struct selectop *sop = arg; + evsignal_dealloc(base); if (sop->event_readset_in) free(sop->event_readset_in); if (sop->event_writeset_in) diff --git a/libevent/signal.c b/libevent/signal.c index 71bcffcba5b..6c0953d9e12 100644 --- a/libevent/signal.c +++ b/libevent/signal.c @@ -31,6 +31,7 @@ #endif #include +#include #ifdef HAVE_SYS_TIME_H #include #else @@ -47,19 +48,14 @@ #ifdef HAVE_FCNTL_H #include #endif +#include #include "event.h" +#include "event-internal.h" #include "evsignal.h" #include "log.h" -extern struct event_list signalqueue; - -static sig_atomic_t evsigcaught[NSIG]; -volatile sig_atomic_t evsignal_caught = 0; - -static struct event ev_signal; -static int ev_signal_pair[2]; -static int ev_signal_added; +struct event_base *evsignal_base = NULL; static void evsignal_handler(int sig); @@ -87,24 +83,27 @@ evsignal_cb(int fd, short what, void *arg) #endif void -evsignal_init(void) +evsignal_init(struct event_base *base) { /* * Our signal handler is going to write to one end of the socket * pair to wake up our event loop. The event loop then scans for * signals that got delivered. */ - if (socketpair(AF_UNIX, SOCK_STREAM, 0, ev_signal_pair) == -1) + if (socketpair(AF_UNIX, SOCK_STREAM, 0, base->sig.ev_signal_pair) == -1) event_err(1, "%s: socketpair", __func__); - FD_CLOSEONEXEC(ev_signal_pair[0]); - FD_CLOSEONEXEC(ev_signal_pair[1]); + FD_CLOSEONEXEC(base->sig.ev_signal_pair[0]); + FD_CLOSEONEXEC(base->sig.ev_signal_pair[1]); + base->sig.evsignal_caught = 0; + memset(&base->sig.evsigcaught, 0, sizeof(sig_atomic_t)*NSIG); - fcntl(ev_signal_pair[0], F_SETFL, O_NONBLOCK); + fcntl(base->sig.ev_signal_pair[0], F_SETFL, O_NONBLOCK); - event_set(&ev_signal, ev_signal_pair[1], EV_READ, - evsignal_cb, &ev_signal); - ev_signal.ev_flags |= EVLIST_INTERNAL; + event_set(&base->sig.ev_signal, base->sig.ev_signal_pair[1], EV_READ, + evsignal_cb, &base->sig.ev_signal); + base->sig.ev_signal.ev_base = base; + base->sig.ev_signal.ev_flags |= EVLIST_INTERNAL; } int @@ -112,6 +111,7 @@ evsignal_add(struct event *ev) { int evsignal; struct sigaction sa; + struct event_base *base = ev->ev_base; if (ev->ev_events & (EV_READ|EV_WRITE)) event_errx(1, "%s: EV_SIGNAL incompatible use", __func__); @@ -121,29 +121,23 @@ evsignal_add(struct event *ev) sa.sa_handler = evsignal_handler; sigfillset(&sa.sa_mask); sa.sa_flags |= SA_RESTART; + /* catch signals if they happen quickly */ + evsignal_base = base; if (sigaction(evsignal, &sa, NULL) == -1) return (-1); - if (!ev_signal_added) { - ev_signal_added = 1; - event_add(&ev_signal, NULL); + if (!base->sig.ev_signal_added) { + base->sig.ev_signal_added = 1; + event_add(&base->sig.ev_signal, NULL); } return (0); } -/* - * Nothing to be done here. - */ - int evsignal_del(struct event *ev) { - int evsignal; - - evsignal = EVENT_SIGNAL(ev); - return (sigaction(EVENT_SIGNAL(ev),(struct sigaction *)SIG_DFL, NULL)); } @@ -152,29 +146,50 @@ evsignal_handler(int sig) { int save_errno = errno; - evsigcaught[sig]++; - evsignal_caught = 1; + if(evsignal_base == NULL) { + event_warn( + "%s: received signal %s, but have no base configured", + __func__, sig); + return; + } + + evsignal_base->sig.evsigcaught[sig]++; + evsignal_base->sig.evsignal_caught = 1; /* Wake up our notification mechanism */ - write(ev_signal_pair[0], "a", 1); + write(evsignal_base->sig.ev_signal_pair[0], "a", 1); errno = save_errno; } void -evsignal_process(void) +evsignal_process(struct event_base *base) { struct event *ev; sig_atomic_t ncalls; - evsignal_caught = 0; - TAILQ_FOREACH(ev, &signalqueue, ev_signal_next) { - ncalls = evsigcaught[EVENT_SIGNAL(ev)]; + base->sig.evsignal_caught = 0; + TAILQ_FOREACH(ev, &base->sig.signalqueue, ev_signal_next) { + ncalls = base->sig.evsigcaught[EVENT_SIGNAL(ev)]; if (ncalls) { if (!(ev->ev_events & EV_PERSIST)) event_del(ev); event_active(ev, EV_SIGNAL, ncalls); - evsigcaught[EVENT_SIGNAL(ev)] = 0; + base->sig.evsigcaught[EVENT_SIGNAL(ev)] = 0; } } } +void +evsignal_dealloc(struct event_base *base) +{ + if(base->sig.ev_signal_added) { + event_del(&base->sig.ev_signal); + base->sig.ev_signal_added = 0; + } + assert(TAILQ_EMPTY(&base->sig.signalqueue)); + + close(base->sig.ev_signal_pair[0]); + base->sig.ev_signal_pair[0] = -1; + close(base->sig.ev_signal_pair[1]); + base->sig.ev_signal_pair[1] = -1; +} diff --git a/man/pf.conf.5 b/man/pf.conf.5 index 7624dc07405..5e49a3c2493 100644 --- a/man/pf.conf.5 +++ b/man/pf.conf.5 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pf.conf.5,v 1.393 2008/02/11 07:46:32 jmc Exp $ +.\" $OpenBSD: pf.conf.5,v 1.402 2008/06/11 07:21:00 jmc Exp $ .\" .\" Copyright (c) 2002, Daniel Hartmeier .\" All rights reserved. @@ -27,7 +27,7 @@ .\" ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE .\" POSSIBILITY OF SUCH DAMAGE. .\" -.Dd $Mdocdate: Febuary 1 2008 $ +.Dd $Mdocdate: June 10 2008 $ .Dt PF.CONF 5 .Os .Sh NAME @@ -164,7 +164,7 @@ A table initialized with the empty list, will be cleared on load. .El .Pp -Tables may be defined with the following two attributes: +Tables may be defined with the following attributes: .Bl -tag -width persist .It Ar persist The @@ -183,6 +183,11 @@ can be used to add or remove addresses from the table at any time, even when running with .Xr securelevel 7 = 2. +.It Ar counters +The +.Ar counters +flag enables per-address packet and byte counters which can be displayed with +.Xr pfctl 8 . .El .Pp For example, @@ -629,6 +634,19 @@ modifier to ensure unique IP identifiers. Enforces a minimum TTL for matching IP packets. .It Ar max-mss Aq Ar number Enforces a maximum MSS for matching TCP packets. +.It Xo Ar set-tos Aq Ar string +.No \*(Ba Aq Ar number +.Xc +Enforces a +.Em TOS +for matching IP packets. +.Em TOS +may be +given as one of +.Ar lowdelay , +.Ar throughput , +.Ar reliability , +or as either hex or decimal. .It Ar random-id Replaces the IP identification field with random values to compensate for predictable values generated by many hosts. @@ -1808,7 +1826,8 @@ or rules in addition to filter rules. Tags take the same macros as labels (see above). .It Ar tagged Aq Ar string -Used with filter or translation rules to specify that packets must already +Used with filter, translation or scrub rules +to specify that packets must already be tagged with the given tag in order to match the rule. Inverse tag matching can also be done by specifying the @@ -1819,6 +1838,22 @@ keyword. .It Ar rtable Aq Ar number Used to select an alternate routing table for the routing lookup. Only effective before the route lookup happened, i.e. when filtering inbound. +.It Xo Ar divert-to Aq Ar host +.Ar port Aq Ar port +.Xc +Used to redirect packets to a local socket bound to +.Ar host +and +.Ar port . +The packets will not be modified, so +.Xr getsockname 2 +on the socket will return the original destination address of the packet. +.It Ar divert-reply +Used to receive replies for sockets that are bound to addresses +which are not local to the machine. +See +.Xr setsockopt 2 +for information on how to bind these sockets. .It Ar probability Aq Ar number A probability attribute can be attached to a rule, with a value set between 0 and 1, bounds not included. @@ -2056,6 +2091,13 @@ Changes the timeout values used for states created by this rule. For a list of all valid timeout names, see .Sx OPTIONS above. +.It Ar sloppy +Uses a sloppy TCP connection tracker that does not check sequence +numbers at all, which makes insertion and ICMP teardown attacks way +easier. +This is intended to be used in situations where one does not see all +packets of a connection, e.g. in asymmetric routing situations. +Cannot be used with modulate or synproxy state. .El .Pp Multiple options can be specified, separated by commas: @@ -2793,10 +2835,10 @@ logopts = logopt [ "," logopts ] logopt = "all" | "user" | "to" interface-name filteropt-list = filteropt-list filteropt | filteropt -filteropt = user | group | flags | icmp-type | icmp6-type | tos | +filteropt = user | group | flags | icmp-type | icmp6-type | "tos" tos | ( "no" | "keep" | "modulate" | "synproxy" ) "state" [ "(" state-opts ")" ] | - "fragment" | "no-df" | "min-ttl" number | + "fragment" | "no-df" | "min-ttl" number | "set-tos" tos | "max-mss" number | "random-id" | "reassemble tcp" | fragmentation | "allow-opts" | "label" string | "tag" string | [ ! ] "tagged" string | @@ -2827,7 +2869,7 @@ antispoof-rule = "antispoof" [ "log" ] [ "quick" ] table-rule = "table" "\*(Lt" string "\*(Gt" [ tableopts-list ] tableopts-list = tableopts-list tableopts | tableopts -tableopts = "persist" | "const" | "file" string | +tableopts = "persist" | "const" | "counters" | "file" string | "{" [ tableaddr-list ] "}" tableaddr-list = tableaddr-list [ "," ] tableaddr-spec | tableaddr-spec tableaddr-spec = [ "!" ] tableaddr [ "/" mask-bits ] @@ -2917,11 +2959,11 @@ icmp-type-code = ( icmp-type-name | icmp-type-number ) [ "code" ( icmp-code-name | icmp-code-number ) ] icmp-list = icmp-type-code [ [ "," ] icmp-list ] -tos = "tos" ( "lowdelay" | "throughput" | "reliability" | +tos = ( "lowdelay" | "throughput" | "reliability" | [ "0x" ] number ) state-opts = state-opt [ [ "," ] state-opts ] -state-opt = ( "max" number | "no-sync" | timeout | +state-opt = ( "max" number | "no-sync" | timeout | sloppy | "source-track" [ ( "rule" | "global" ) ] | "max-src-nodes" number | "max-src-states" number | "max-src-conn" number | @@ -2962,6 +3004,7 @@ realtime-sc = "realtime" sc-spec upperlimit-sc = "upperlimit" sc-spec sc-spec = ( bandwidth-spec | "(" bandwidth-spec number bandwidth-spec ")" ) +include = "include" filename .Ed .Sh FILES .Bl -tag -width "/etc/protocols" -compact diff --git a/man/pfsync.4 b/man/pfsync.4 index 027d46014d1..d10131457ad 100644 --- a/man/pfsync.4 +++ b/man/pfsync.4 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pfsync.4,v 1.26 2007/09/20 20:50:07 mpf Exp $ +.\" $OpenBSD: pfsync.4,v 1.27 2008/06/03 19:51:02 jmc Exp $ .\" .\" Copyright (c) 2002 Michael Shalayeff .\" Copyright (c) 2003-2004 Ryan McBride @@ -24,7 +24,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.Dd $Mdocdate: May 31 2007 $ +.Dd $Mdocdate: September 20 2007 $ .Dt PFSYNC 4 .Os .Sh NAME @@ -121,7 +121,7 @@ e.g.: It is important that the pfsync traffic be well secured as there is no authentication on the protocol and it would be trivial to spoof packets which create states, bypassing the pf ruleset. -Either run the pfsync protocol on a trusted network \- ideally a network +Either run the pfsync protocol on a trusted network \- ideally a network dedicated to pfsync messages such as a crossover cable between two firewalls, or specify a peer address and protect the traffic with .Xr ipsec 4 . diff --git a/pfctl/parse.y b/pfctl/parse.y index c4189963198..55c3a755373 100644 --- a/pfctl/parse.y +++ b/pfctl/parse.y @@ -1,4 +1,4 @@ -/* $OpenBSD: parse.y,v 1.536 2008/02/01 06:58:45 mcbride Exp $ */ +/* $OpenBSD: parse.y,v 1.549 2008/07/03 16:09:34 deraadt Exp $ */ /* * Copyright (c) 2001 Markus Friedl. All rights reserved. @@ -153,7 +153,7 @@ enum { PF_STATE_OPT_MAX, PF_STATE_OPT_NOSYNC, PF_STATE_OPT_SRCTRACK, PF_STATE_OPT_MAX_SRC_STATES, PF_STATE_OPT_MAX_SRC_CONN, PF_STATE_OPT_MAX_SRC_CONN_RATE, PF_STATE_OPT_MAX_SRC_NODES, PF_STATE_OPT_OVERLOAD, PF_STATE_OPT_STATELOCK, - PF_STATE_OPT_TIMEOUT }; + PF_STATE_OPT_TIMEOUT, PF_STATE_OPT_SLOPPY }; enum { PF_SRCTRACK_NONE, PF_SRCTRACK, PF_SRCTRACK_GLOBAL, PF_SRCTRACK_RULE }; @@ -232,6 +232,10 @@ struct filter_opts { char *match_tag; u_int8_t match_tag_not; u_int rtableid; + struct { + struct node_host *addr; + u_int16_t port; + } divert; } filter_opts; struct antispoof_opts { @@ -244,12 +248,16 @@ struct scrub_opts { #define SOM_MINTTL 0x01 #define SOM_MAXMSS 0x02 #define SOM_FRAGCACHE 0x04 +#define SOM_SETTOS 0x08 int nodf; int minttl; int maxmss; + int settos; int fragcache; int randomid; int reassemble_tcp; + char *match_tag; + u_int8_t match_tag_not; u_int rtableid; } scrub_opts; @@ -410,6 +418,10 @@ typedef struct { int lineno; } YYSTYPE; +#define PPORT_RANGE 1 +#define PPORT_STAR 2 +int parseport(char *, struct range *r, int); + #define DYNIF_MULTIADDR(addr) ((addr).type == PF_ADDR_DYNIFTL && \ (!((addr).iflags & PFI_AFLAG_NOALIAS) || \ !isdigit((addr).v.ifname[strlen((addr).v.ifname)-1]))) @@ -430,8 +442,9 @@ typedef struct { %token QUEUE PRIORITY QLIMIT RTABLE %token LOAD RULESET_OPTIMIZATION %token STICKYADDRESS MAXSRCSTATES MAXSRCNODES SOURCETRACK GLOBAL RULE -%token MAXSRCCONN MAXSRCCONNRATE OVERLOAD FLUSH -%token TAGGED TAG IFBOUND FLOATING STATEPOLICY ROUTE +%token MAXSRCCONN MAXSRCCONNRATE OVERLOAD FLUSH SLOPPY +%token TAGGED TAG IFBOUND FLOATING STATEPOLICY ROUTE SETTOS +%token DIVERTTO DIVERTREPLY %token STRING %token NUMBER %token PORTBINARY @@ -443,7 +456,7 @@ typedef struct { %type sourcetrack flush unaryop statelock %type action nataction natpasslog scrubaction %type flags flag blockspec -%type port rport +%type portplain portstar portrange %type hashkey %type proto proto_list proto_item %type protoval @@ -453,7 +466,7 @@ typedef struct { %type reticmpspec reticmp6spec %type fromto %type ipportspec from to -%type ipspec xhost host dynaddr host_list +%type ipspec toipspec xhost host dynaddr host_list %type redir_host_list redirspec %type route_host route_host_list routespec %type os xos os_list @@ -462,7 +475,8 @@ typedef struct { %type gids gid_list gid_item %type route %type redirection redirpool -%type label string stringall tag anchorname +%type label stringall tag anchorname +%type string varstring numberstring %type keep %type state_opt_spec state_opt_list state_opt_item %type logquick quick log logopts logopt @@ -563,9 +577,9 @@ option : SET OPTIMIZATION STRING { } } | SET TIMEOUT timeout_spec - | SET TIMEOUT '{' timeout_list '}' + | SET TIMEOUT '{' optnl timeout_list '}' | SET LIMIT limit_spec - | SET LIMIT '{' limit_list '}' + | SET LIMIT '{' optnl limit_list '}' | SET LOGINTERFACE stringall { if (check_rulestate(PFCTL_STATE_OPTION)) { free($3); @@ -666,7 +680,7 @@ stringall : STRING { $$ = $1; } } ; -string : string STRING { +string : STRING string { if (asprintf(&$$, "%s %s", $1, $2) == -1) err(1, "string: asprintf"); free($1); @@ -675,7 +689,27 @@ string : string STRING { | STRING ; -varset : STRING '=' string { +varstring : numberstring varstring { + if (asprintf(&$$, "%s %s", $1, $2) == -1) + err(1, "string: asprintf"); + free($1); + free($2); + } + | numberstring + ; + +numberstring : NUMBER { + char *s; + if (asprintf(&s, "%lld", $1) == -1) { + yyerror("string: asprintf"); + YYERROR; + } + $$ = s; + } + | STRING + ; + +varset : STRING '=' varstring { if (pf->opts & PF_OPT_VERBOSE) printf("%s = \"%s\"\n", $1, $3); if (symset($1, $3, 0) == -1) @@ -683,33 +717,16 @@ varset : STRING '=' string { free($1); free($3); } - | STRING '=' NUMBER { - char *s; - if (asprintf(&s, "%lld", $3) == -1) { - yyerror("string: asprintf"); - YYERROR; - } - if (pf->opts & PF_OPT_VERBOSE) - printf("%s = \"%s\"\n", $1, s); - if (symset($1, s, 0) == -1) - err(1, "cannot store variable %s", $1); - free($1); - free(s); - } ; anchorname : STRING { $$ = $1; } | /* empty */ { $$ = NULL; } ; -optnl : optnl '\n' - | - ; - -pfa_anchorlist : pfrule optnl - | anchorrule optnl - | pfa_anchorlist pfrule optnl - | pfa_anchorlist anchorrule optnl +pfa_anchorlist : /* empty */ + | pfa_anchorlist '\n' + | pfa_anchorlist pfrule '\n' + | pfa_anchorlist anchorrule '\n' ; pfa_anchor : '{' @@ -1037,8 +1054,20 @@ scrubrule : scrubaction dir logquick interface af proto fromto scrub_opts r.min_ttl = $8.minttl; if ($8.maxmss) r.max_mss = $8.maxmss; + if ($8.marker & SOM_SETTOS) { + r.rule_flag |= PFRULE_SET_TOS; + r.set_tos = $8.settos; + } if ($8.fragcache) r.rule_flag |= $8.fragcache; + if ($8.match_tag) + if (strlcpy(r.match_tagname, $8.match_tag, + PF_TAG_NAME_SIZE) >= PF_TAG_NAME_SIZE) { + yyerror("tag too long, max %u chars", + PF_TAG_NAME_SIZE - 1); + YYERROR; + } + r.match_tag_not = $8.match_tag_not; r.rtableid = $8.rtableid; expand_rule(&r, $4, NULL, $6, $7.src_os, @@ -1095,6 +1124,14 @@ scrub_opt : NODF { scrub_opts.marker |= SOM_MAXMSS; scrub_opts.maxmss = $2; } + | SETTOS tos { + if (scrub_opts.marker & SOM_SETTOS) { + yyerror("set-tos cannot be respecified"); + YYERROR; + } + scrub_opts.marker |= SOM_SETTOS; + scrub_opts.settos = $2; + } | fragcache { if (scrub_opts.marker & SOM_FRAGCACHE) { yyerror("fragcache cannot be respecified"); @@ -1131,6 +1168,10 @@ scrub_opt : NODF { } scrub_opts.rtableid = $2; } + | not TAGGED string { + scrub_opts.match_tag = $3; + scrub_opts.match_tag_not = $1; + } ; fragcache : FRAGMENT REASSEMBLE { $$ = 0; /* default */ } @@ -1225,11 +1266,11 @@ antispoof : ANTISPOOF logquick antispoof_ifspc af antispoof_opts { ; antispoof_ifspc : FOR antispoof_if { $$ = $2; } - | FOR '{' antispoof_iflst '}' { $$ = $3; } + | FOR '{' optnl antispoof_iflst '}' { $$ = $4; } ; -antispoof_iflst : antispoof_if { $$ = $1; } - | antispoof_iflst comma antispoof_if { +antispoof_iflst : antispoof_if optnl { $$ = $1; } + | antispoof_iflst comma antispoof_if optnl { $1->tail->next = $3; $1->tail = $3; $$ = $1; @@ -1333,6 +1374,8 @@ table_opt : STRING { table_opts.flags |= PFR_TFLAG_CONST; else if (!strcmp($1, "persist")) table_opts.flags |= PFR_TFLAG_PERSIST; + else if (!strcmp($1, "counters")) + table_opts.flags |= PFR_TFLAG_COUNTERS; else { yyerror("invalid table option '%s'", $1); free($1); @@ -1340,12 +1383,12 @@ table_opt : STRING { } free($1); } - | '{' '}' { table_opts.init_addr = 1; } - | '{' host_list '}' { + | '{' optnl '}' { table_opts.init_addr = 1; } + | '{' optnl host_list '}' { struct node_host *n; struct node_tinit *ti; - for (n = $2; n != NULL; n = n->next) { + for (n = $3; n != NULL; n = n->next) { switch (n->addr.type) { case PF_ADDR_ADDRMASK: continue; /* ok */ @@ -1376,7 +1419,7 @@ table_opt : STRING { } if (!(ti = calloc(1, sizeof(*ti)))) err(1, "table_opt: calloc"); - ti->host = $2; + ti->host = $3; SIMPLEQ_INSERT_TAIL(&table_opts.init_nodes, ti, entries); table_opts.init_addr = 1; @@ -1750,11 +1793,11 @@ hfscopts_item : LINKSHARE bandwidth { qassign : /* empty */ { $$ = NULL; } | qassign_item { $$ = $1; } - | '{' qassign_list '}' { $$ = $2; } + | '{' optnl qassign_list '}' { $$ = $3; } ; -qassign_list : qassign_item { $$ = $1; } - | qassign_list comma qassign_item { +qassign_list : qassign_item optnl { $$ = $1; } + | qassign_list comma qassign_item optnl { $1->tail->next = $3; $1->tail = $3; $$ = $1; @@ -2009,6 +2052,14 @@ pfrule : action dir logquick interface route af proto fromto statelock = 1; r.rule_flag |= o->data.statelock; break; + case PF_STATE_OPT_SLOPPY: + if (r.rule_flag & PFRULE_STATESLOPPY) { + yyerror("state sloppy option: " + "multiple definitions"); + YYERROR; + } + r.rule_flag |= PFRULE_STATESLOPPY; + break; case PF_STATE_OPT_TIMEOUT: if (o->data.timeout.number == PFTM_ADAPTIVE_START || @@ -2145,6 +2196,30 @@ pfrule : action dir logquick interface route af proto fromto } free($9.queues.pqname); } + if ((r.divert.port = $9.divert.port)) { + if (r.direction == PF_OUT) { + if ($9.divert.addr) { + yyerror("address specified " + "for outgoing divert"); + YYERROR; + } + bzero(&r.divert.addr, + sizeof(r.divert.addr)); + } else { + if (!$9.divert.addr) { + yyerror("no address specified " + "for incoming divert"); + YYERROR; + } + if ($9.divert.addr->af != r.af) { + yyerror("address family " + "mismatch for divert"); + YYERROR; + } + r.divert.addr = + $9.divert.addr->addr.v.a.addr; + } + } expand_rule(&r, $4, $5.host, $7, $8.src_os, $8.src.host, $8.src.port, $8.dst.host, $8.dst.port, @@ -2198,13 +2273,13 @@ filter_opt : USER uids { filter_opts.marker |= FOM_ICMP; filter_opts.icmpspec = $1; } - | tos { + | TOS tos { if (filter_opts.marker & FOM_TOS) { yyerror("tos cannot be redefined"); YYERROR; } filter_opts.marker |= FOM_TOS; - filter_opts.tos = $1; + filter_opts.tos = $2; } | keep { if (filter_opts.marker & FOM_KEEP) { @@ -2261,6 +2336,23 @@ filter_opt : USER uids { } filter_opts.rtableid = $2; } + | DIVERTTO STRING PORT portplain { + if ((filter_opts.divert.addr = host($2)) == NULL) { + yyerror("could not parse divert address: %s", + $2); + free($2); + YYERROR; + } + free($2); + filter_opts.divert.port = $4.a; + if (!filter_opts.divert.port) { + yyerror("invalid divert port: %u", ntohs($4.a)); + YYERROR; + } + } + | DIVERTREPLY { + filter_opts.divert.port = 1; /* some random value */ + } ; probability : STRING { @@ -2383,7 +2475,7 @@ reticmp6spec : STRING { } ; -dir : /* empty */ { $$ = 0; } +dir : /* empty */ { $$ = PF_INOUT; } | IN { $$ = PF_IN; } | OUT { $$ = PF_OUT; } ; @@ -2441,11 +2533,11 @@ logopt : ALL { $$.log = PF_LOG_ALL; $$.logif = 0; } interface : /* empty */ { $$ = NULL; } | ON if_item_not { $$ = $2; } - | ON '{' if_list '}' { $$ = $3; } + | ON '{' optnl if_list '}' { $$ = $4; } ; -if_list : if_item_not { $$ = $1; } - | if_list comma if_item_not { +if_list : if_item_not optnl { $$ = $1; } + | if_list comma if_item_not optnl { $1->tail->next = $3; $1->tail = $3; $$ = $1; @@ -2484,13 +2576,13 @@ af : /* empty */ { $$ = 0; } | INET6 { $$ = AF_INET6; } ; -proto : /* empty */ { $$ = NULL; } - | PROTO proto_item { $$ = $2; } - | PROTO '{' proto_list '}' { $$ = $3; } +proto : /* empty */ { $$ = NULL; } + | PROTO proto_item { $$ = $2; } + | PROTO '{' optnl proto_list '}' { $$ = $4; } ; -proto_list : proto_item { $$ = $1; } - | proto_list comma proto_item { +proto_list : proto_item optnl { $$ = $1; } + | proto_list comma proto_item optnl { $1->tail->next = $3; $1->tail = $3; $$ = $1; @@ -2550,7 +2642,7 @@ fromto : ALL { os : /* empty */ { $$ = NULL; } | OS xos { $$ = $2; } - | OS '{' os_list '}' { $$ = $3; } + | OS '{' optnl os_list '}' { $$ = $4; } ; xos : STRING { @@ -2562,8 +2654,8 @@ xos : STRING { } ; -os_list : xos { $$ = $1; } - | os_list comma xos { +os_list : xos optnl { $$ = $1; } + | os_list comma xos optnl { $1->tail->next = $3; $1->tail = $3; $$ = $1; @@ -2605,13 +2697,21 @@ ipportspec : ipspec { } ; -ipspec : ANY { $$ = NULL; } - | xhost { $$ = $1; } - | '{' host_list '}' { $$ = $2; } +optnl : '\n' optnl + | ; -host_list : ipspec { $$ = $1; } - | host_list comma ipspec { +ipspec : ANY { $$ = NULL; } + | xhost { $$ = $1; } + | '{' optnl host_list '}' { $$ = $3; } + ; + +toipspec : TO ipspec { $$ = $2; } + | /* empty */ { $$ = NULL; } + ; + +host_list : ipspec optnl { $$ = $1; } + | host_list comma ipspec optnl { if ($3 == NULL) $$ = $1; else if ($1 == NULL) @@ -2843,18 +2943,18 @@ dynaddr : '(' STRING ')' { ; portspec : port_item { $$ = $1; } - | '{' port_list '}' { $$ = $2; } + | '{' optnl port_list '}' { $$ = $3; } ; -port_list : port_item { $$ = $1; } - | port_list comma port_item { +port_list : port_item optnl { $$ = $1; } + | port_list comma port_item optnl { $1->tail->next = $3; $1->tail = $3; $$ = $1; } ; -port_item : port { +port_item : portrange { $$ = calloc(1, sizeof(struct node_port)); if ($$ == NULL) err(1, "port_item: calloc"); @@ -2867,7 +2967,7 @@ port_item : port { $$->next = NULL; $$->tail = $$; } - | unaryop port { + | unaryop portrange { if ($2.t) { yyerror("':' cannot be used with an other " "port operator"); @@ -2882,7 +2982,7 @@ port_item : port { $$->next = NULL; $$->tail = $$; } - | port PORTBINARY port { + | portrange PORTBINARY portrange { if ($1.t || $3.t) { yyerror("':' cannot be used with an other " "port operator"); @@ -2899,46 +2999,30 @@ port_item : port { } ; -port : STRING { - char *p = strchr($1, ':'); - - if (p == NULL) { - if (($$.a = getservice($1)) == -1) { - free($1); - YYERROR; - } - $$.b = $$.t = 0; - } else { - int port[2]; - - *p++ = 0; - if ((port[0] = getservice($1)) == -1 || - (port[1] = getservice(p)) == -1) { - free($1); - YYERROR; - } - $$.a = port[0]; - $$.b = port[1]; - $$.t = PF_OP_RRG; +portplain : numberstring { + if (parseport($1, &$$, 0) == -1) { + free($1); + YYERROR; } free($1); } - | NUMBER { - if ($1 < 0 || $1 > 65535) { - yyerror("illegal port value %lu", $1); + ; + +portrange : numberstring { + if (parseport($1, &$$, PPORT_RANGE) == -1) { + free($1); YYERROR; } - $$.a = ntohs($1); - $$.b = $$.t = 0; + free($1); } ; uids : uid_item { $$ = $1; } - | '{' uid_list '}' { $$ = $2; } + | '{' optnl uid_list '}' { $$ = $3; } ; -uid_list : uid_item { $$ = $1; } - | uid_list comma uid_item { +uid_list : uid_item optnl { $$ = $1; } + | uid_list comma uid_item optnl { $1->tail->next = $3; $1->tail = $3; $$ = $1; @@ -3012,11 +3096,11 @@ uid : STRING { ; gids : gid_item { $$ = $1; } - | '{' gid_list '}' { $$ = $2; } + | '{' optnl gid_list '}' { $$ = $3; } ; -gid_list : gid_item { $$ = $1; } - | gid_list comma gid_item { +gid_list : gid_item optnl { $$ = $1; } + | gid_list comma gid_item optnl { $1->tail->next = $3; $1->tail = $3; $$ = $1; @@ -3107,22 +3191,22 @@ flags : FLAGS flag '/' flag { $$.b1 = $2.b1; $$.b2 = $4.b1; } | FLAGS ANY { $$.b1 = 0; $$.b2 = 0; } ; -icmpspec : ICMPTYPE icmp_item { $$ = $2; } - | ICMPTYPE '{' icmp_list '}' { $$ = $3; } - | ICMP6TYPE icmp6_item { $$ = $2; } - | ICMP6TYPE '{' icmp6_list '}' { $$ = $3; } +icmpspec : ICMPTYPE icmp_item { $$ = $2; } + | ICMPTYPE '{' optnl icmp_list '}' { $$ = $4; } + | ICMP6TYPE icmp6_item { $$ = $2; } + | ICMP6TYPE '{' optnl icmp6_list '}' { $$ = $4; } ; -icmp_list : icmp_item { $$ = $1; } - | icmp_list comma icmp_item { +icmp_list : icmp_item optnl { $$ = $1; } + | icmp_list comma icmp_item optnl { $1->tail->next = $3; $1->tail = $3; $$ = $1; } ; -icmp6_list : icmp6_item { $$ = $1; } - | icmp6_list comma icmp6_item { +icmp6_list : icmp6_item optnl { $$ = $1; } + | icmp6_list comma icmp6_item optnl { $1->tail->next = $3; $1->tail = $3; $$ = $1; @@ -3260,28 +3344,28 @@ icmp6type : STRING { } ; -tos : TOS STRING { - if (!strcmp($2, "lowdelay")) +tos : STRING { + if (!strcmp($1, "lowdelay")) $$ = IPTOS_LOWDELAY; - else if (!strcmp($2, "throughput")) + else if (!strcmp($1, "throughput")) $$ = IPTOS_THROUGHPUT; - else if (!strcmp($2, "reliability")) + else if (!strcmp($1, "reliability")) $$ = IPTOS_RELIABILITY; - else if ($2[0] == '0' && $2[1] == 'x') - $$ = strtoul($2, NULL, 16); + else if ($1[0] == '0' && $1[1] == 'x') + $$ = strtoul($1, NULL, 16); else $$ = 0; /* flag bad argument */ if (!$$ || $$ > 255) { - yyerror("illegal tos value %s", $2); - free($2); + yyerror("illegal tos value %s", $1); + free($1); YYERROR; } - free($2); + free($1); } - | TOS NUMBER { - $$ = $2; + | NUMBER { + $$ = $1; if (!$$ || $$ > 255) { - yyerror("illegal tos value %s", $2); + yyerror("illegal tos value %s", $1); YYERROR; } } @@ -3448,6 +3532,14 @@ state_opt_item : MAXIMUM NUMBER { $$->next = NULL; $$->tail = $$; } + | SLOPPY { + $$ = calloc(1, sizeof(struct node_state_opt)); + if ($$ == NULL) + err(1, "state_opt_item: calloc"); + $$->type = PF_STATE_OPT_SLOPPY; + $$->next = NULL; + $$->tail = $$; + } | STRING NUMBER { int i; @@ -3487,9 +3579,11 @@ label : LABEL STRING { qname : QUEUE STRING { $$.qname = $2; + $$.pqname = NULL; } | QUEUE '(' STRING ')' { $$.qname = $3; + $$.pqname = NULL; } | QUEUE '(' STRING comma STRING ')' { $$.qname = $3; @@ -3501,52 +3595,21 @@ no : /* empty */ { $$ = 0; } | NO { $$ = 1; } ; -rport : STRING { - char *p = strchr($1, ':'); - - if (p == NULL) { - if (($$.a = getservice($1)) == -1) { - free($1); - YYERROR; - } - $$.b = $$.t = 0; - } else if (!strcmp(p+1, "*")) { - *p = 0; - if (($$.a = getservice($1)) == -1) { - free($1); - YYERROR; - } - $$.b = 0; - $$.t = 1; - } else { - *p++ = 0; - if (($$.a = getservice($1)) == -1 || - ($$.b = getservice(p)) == -1) { - free($1); - YYERROR; - } - if ($$.a == $$.b) - $$.b = 0; - $$.t = 0; - } - free($1); - } - | NUMBER { - if ($1 < 0 || $1 > 65535) { - yyerror("illegal port value %ld", $1); +portstar : numberstring { + if (parseport($1, &$$, PPORT_RANGE|PPORT_STAR) == -1) { + free($1); YYERROR; } - $$.a = ntohs($1); - $$.b = $$.t = 0; + free($1); } ; redirspec : host { $$ = $1; } - | '{' redir_host_list '}' { $$ = $2; } + | '{' optnl redir_host_list '}' { $$ = $3; } ; -redir_host_list : host { $$ = $1; } - | redir_host_list comma host { +redir_host_list : host optnl { $$ = $1; } + | redir_host_list comma host optnl { $1->tail->next = $3; $1->tail = $3->tail; $$ = $1; @@ -3561,7 +3624,7 @@ redirpool : /* empty */ { $$ = NULL; } $$->host = $2; $$->rport.a = $$->rport.b = $$->rport.t = 0; } - | ARROW redirspec PORT rport { + | ARROW redirspec PORT portstar { $$ = calloc(1, sizeof(struct redirection)); if ($$ == NULL) err(1, "redirection: calloc"); @@ -3687,7 +3750,7 @@ redirection : /* empty */ { $$ = NULL; } $$->host = $2; $$->rport.a = $$->rport.b = $$->rport.t = 0; } - | ARROW host PORT rport { + | ARROW host PORT portstar { $$ = calloc(1, sizeof(struct redirection)); if ($$ == NULL) err(1, "redirection: calloc"); @@ -3889,7 +3952,7 @@ natrule : nataction interface af proto fromto tag tagged rtable } ; -binatrule : no BINAT natpasslog interface af proto FROM host TO ipspec tag +binatrule : no BINAT natpasslog interface af proto FROM host toipspec tag tagged rtable redirection { struct pf_rule binat; @@ -3897,7 +3960,7 @@ binatrule : no BINAT natpasslog interface af proto FROM host TO ipspec tag if (check_rulestate(PFCTL_STATE_NAT)) YYERROR; - if (disallow_urpf_failed($10, "\"urpf-failed\" is not " + if (disallow_urpf_failed($9, "\"urpf-failed\" is not " "permitted as a binat destination")) YYERROR; @@ -3917,11 +3980,11 @@ binatrule : no BINAT natpasslog interface af proto FROM host TO ipspec tag binat.af = $5; if (!binat.af && $8 != NULL && $8->af) binat.af = $8->af; - if (!binat.af && $10 != NULL && $10->af) - binat.af = $10->af; + if (!binat.af && $9 != NULL && $9->af) + binat.af = $9->af; - if (!binat.af && $14 != NULL && $14->host) - binat.af = $14->host->af; + if (!binat.af && $13 != NULL && $13->host) + binat.af = $13->host->af; if (!binat.af) { yyerror("address family (inet/inet6) " "undefined"); @@ -3935,22 +3998,22 @@ binatrule : no BINAT natpasslog interface af proto FROM host TO ipspec tag free($4); } - if ($11 != NULL) - if (strlcpy(binat.tagname, $11, + if ($10 != NULL) + if (strlcpy(binat.tagname, $10, PF_TAG_NAME_SIZE) >= PF_TAG_NAME_SIZE) { yyerror("tag too long, max %u chars", PF_TAG_NAME_SIZE - 1); YYERROR; } - if ($12.name) - if (strlcpy(binat.match_tagname, $12.name, + if ($11.name) + if (strlcpy(binat.match_tagname, $11.name, PF_TAG_NAME_SIZE) >= PF_TAG_NAME_SIZE) { yyerror("tag too long, max %u chars", PF_TAG_NAME_SIZE - 1); YYERROR; } - binat.match_tag_not = $12.neg; - binat.rtableid = $13; + binat.match_tag_not = $11.neg; + binat.rtableid = $12; if ($6 != NULL) { binat.proto = $6->proto; @@ -3964,12 +4027,12 @@ binatrule : no BINAT natpasslog interface af proto FROM host TO ipspec tag "interface (%s) as the source address of a binat " "rule")) YYERROR; - if ($14 != NULL && $14->host != NULL && disallow_table( - $14->host, "invalid use of table <%s> as the " + if ($13 != NULL && $13->host != NULL && disallow_table( + $13->host, "invalid use of table <%s> as the " "redirect address of a binat rule")) YYERROR; - if ($14 != NULL && $14->host != NULL && disallow_alias( - $14->host, "invalid use of interface (%s) as the " + if ($13 != NULL && $13->host != NULL && disallow_alias( + $13->host, "invalid use of interface (%s) as the " "redirect address of a binat rule")) YYERROR; @@ -3990,51 +4053,51 @@ binatrule : no BINAT natpasslog interface af proto FROM host TO ipspec tag sizeof(binat.src.addr)); free($8); } - if ($10 != NULL) { - if ($10->next) { + if ($9 != NULL) { + if ($9->next) { yyerror("multiple binat ip addresses"); YYERROR; } - if ($10->af != binat.af && $10->af) { + if ($9->af != binat.af && $9->af) { yyerror("binat ip versions must match"); YYERROR; } - if (check_netmask($10, binat.af)) + if (check_netmask($9, binat.af)) YYERROR; - memcpy(&binat.dst.addr, &$10->addr, + memcpy(&binat.dst.addr, &$9->addr, sizeof(binat.dst.addr)); - binat.dst.neg = $10->not; - free($10); + binat.dst.neg = $9->not; + free($9); } if (binat.action == PF_NOBINAT) { - if ($14 != NULL) { + if ($13 != NULL) { yyerror("'no binat' rule does not need" " '->'"); YYERROR; } } else { - if ($14 == NULL || $14->host == NULL) { + if ($13 == NULL || $13->host == NULL) { yyerror("'binat' rule requires" " '-> address'"); YYERROR; } - remove_invalid_hosts(&$14->host, &binat.af); - if (invalid_redirect($14->host, binat.af)) + remove_invalid_hosts(&$13->host, &binat.af); + if (invalid_redirect($13->host, binat.af)) YYERROR; - if ($14->host->next != NULL) { + if ($13->host->next != NULL) { yyerror("binat rule must redirect to " "a single address"); YYERROR; } - if (check_netmask($14->host, binat.af)) + if (check_netmask($13->host, binat.af)) YYERROR; if (!PF_AZERO(&binat.src.addr.v.a.mask, binat.af) && !PF_AEQ(&binat.src.addr.v.a.mask, - &$14->host->addr.v.a.mask, binat.af)) { + &$13->host->addr.v.a.mask, binat.af)) { yyerror("'binat' source mask and " "redirect mask must be the same"); YYERROR; @@ -4044,12 +4107,12 @@ binatrule : no BINAT natpasslog interface af proto FROM host TO ipspec tag pa = calloc(1, sizeof(struct pf_pooladdr)); if (pa == NULL) err(1, "binat: calloc"); - pa->addr = $14->host->addr; + pa->addr = $13->host->addr; pa->ifname[0] = 0; TAILQ_INSERT_TAIL(&binat.rpool.list, pa, entries); - free($14); + free($13); } pfctl_add_rule(pf, &binat, ""); @@ -4089,8 +4152,8 @@ route_host : STRING { } ; -route_host_list : route_host { $$ = $1; } - | route_host_list comma route_host { +route_host_list : route_host optnl { $$ = $1; } + | route_host_list comma route_host optnl { if ($1->af == 0) $1->af = $3->af; if ($1->af != $3->af) { @@ -4105,7 +4168,7 @@ route_host_list : route_host { $$ = $1; } ; routespec : route_host { $$ = $1; } - | '{' route_host_list '}' { $$ = $2; } + | '{' optnl route_host_list '}' { $$ = $3; } ; route : /* empty */ { @@ -4160,8 +4223,8 @@ timeout_spec : STRING NUMBER } ; -timeout_list : timeout_list comma timeout_spec - | timeout_spec +timeout_list : timeout_list comma timeout_spec optnl + | timeout_spec optnl ; limit_spec : STRING NUMBER @@ -4183,8 +4246,8 @@ limit_spec : STRING NUMBER } ; -limit_list : limit_list comma limit_spec - | limit_spec +limit_list : limit_list comma limit_spec optnl + | limit_spec optnl ; comma : ',' @@ -4343,6 +4406,13 @@ filter_consistent(struct pf_rule *r, int anchor_call) yyerror("keep state on block rules doesn't make sense"); problems++; } + if (r->rule_flag & PFRULE_STATESLOPPY && + (r->keep_state == PF_STATE_MODULATE || + r->keep_state == PF_STATE_SYNPROXY)) { + yyerror("sloppy state matching cannot be used with " + "synproxy state or modulate state"); + problems++; + } return (-problems); } @@ -5133,6 +5203,8 @@ lookup(char *s) { "code", CODE}, { "crop", FRAGCROP}, { "debug", DEBUG}, + { "divert-reply", DIVERTREPLY}, + { "divert-to", DIVERTTO}, { "drop", DROP}, { "drop-ovl", FRAGDROP}, { "dup-to", DUPTO}, @@ -5211,7 +5283,9 @@ lookup(char *s) { "ruleset-optimization", RULESET_OPTIMIZATION}, { "scrub", SCRUB}, { "set", SET}, + { "set-tos", SETTOS}, { "skip", SKIP}, + { "sloppy", SLOPPY}, { "source-hash", SOURCEHASH}, { "source-track", SOURCETRACK}, { "state", STATE}, @@ -5861,6 +5935,41 @@ parseicmpspec(char *w, sa_family_t af) return (icmptype << 8 | ulval); } +int +parseport(char *port, struct range *r, int extensions) +{ + char *p = strchr(port, ':'); + + if (p == NULL) { + if ((r->a = getservice(port)) == -1) + return (-1); + r->b = 0; + r->t = PF_OP_NONE; + return (0); + } + if ((extensions & PPORT_STAR) && !strcmp(p+1, "*")) { + *p = 0; + if ((r->a = getservice(port)) == -1) + return (-1); + r->b = 0; + r->t = PF_OP_IRG; + return (0); + } + if ((extensions & PPORT_RANGE)) { + *p++ = 0; + if ((r->a = getservice(port)) == -1 || + (r->b = getservice(p)) == -1) + return (-1); + if (r->a == r->b) { + r->b = 0; + r->t = PF_OP_NONE; + } else + r->t = PF_OP_RRG; + return (0); + } + return (-1); +} + int pfctl_load_anchors(int dev, struct pfctl *pf, struct pfr_buffer *trans) { diff --git a/pfctl/pf_print_state.c b/pfctl/pf_print_state.c index 8489c38c73a..e95f2b04a06 100644 --- a/pfctl/pf_print_state.c +++ b/pfctl/pf_print_state.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pf_print_state.c,v 1.46 2007/08/30 09:28:49 dhartmei Exp $ */ +/* $OpenBSD: pf_print_state.c,v 1.51 2008/06/29 08:42:15 mcbride Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -165,17 +165,15 @@ print_name(struct pf_addr *addr, sa_family_t af) } void -print_host(struct pfsync_state_host *h, sa_family_t af, int opts) +print_host(struct pf_addr *addr, u_int16_t port, sa_family_t af, int opts) { - u_int16_t p = ntohs(h->port); - if (opts & PF_OPT_USEDNS) - print_name(&h->addr, af); + print_name(addr, af); else { struct pf_addr_wrap aw; memset(&aw, 0, sizeof(aw)); - aw.v.a.addr = h->addr; + aw.v.a.addr = *addr; if (af == AF_INET) aw.v.a.mask.addr32[0] = 0xffffffff; else { @@ -185,11 +183,11 @@ print_host(struct pfsync_state_host *h, sa_family_t af, int opts) print_addr(&aw, af, opts & PF_OPT_VERBOSE2); } - if (p) { + if (port) { if (af == AF_INET) - printf(":%u", p); + printf(":%u", ntohs(port)); else - printf("[%u]", p); + printf("[%u]", ntohs(port)); } } @@ -197,45 +195,60 @@ void print_seq(struct pfsync_state_peer *p) { if (p->seqdiff) - printf("[%u + %u](+%u)", p->seqlo, p->seqhi - p->seqlo, - p->seqdiff); + printf("[%u + %u](+%u)", ntohl(p->seqlo), + ntohl(p->seqhi) - ntohl(p->seqlo), ntohl(p->seqdiff)); else - printf("[%u + %u]", p->seqlo, p->seqhi - p->seqlo); + printf("[%u + %u]", ntohl(p->seqlo), + ntohl(p->seqhi) - ntohl(p->seqlo)); } void print_state(struct pfsync_state *s, int opts) { struct pfsync_state_peer *src, *dst; + struct pfsync_state_key *sk, *nk; struct protoent *p; int min, sec; if (s->direction == PF_OUT) { src = &s->src; dst = &s->dst; + sk = &s->key[PF_SK_STACK]; + nk = &s->key[PF_SK_WIRE]; + if (s->proto == IPPROTO_ICMP || s->proto == IPPROTO_ICMPV6) + sk->port[0] = nk->port[0]; } else { src = &s->dst; dst = &s->src; + sk = &s->key[PF_SK_WIRE]; + nk = &s->key[PF_SK_STACK]; + if (s->proto == IPPROTO_ICMP || s->proto == IPPROTO_ICMPV6) + sk->port[1] = nk->port[1]; } printf("%s ", s->ifname); if ((p = getprotobynumber(s->proto)) != NULL) printf("%s ", p->p_name); else printf("%u ", s->proto); - if (PF_ANEQ(&s->lan.addr, &s->gwy.addr, s->af) || - (s->lan.port != s->gwy.port)) { - print_host(&s->lan, s->af, opts); - if (s->direction == PF_OUT) - printf(" -> "); - else - printf(" <- "); + + print_host(&nk->addr[1], nk->port[1], s->af, opts); + if (PF_ANEQ(&nk->addr[1], &sk->addr[1], s->af) || + nk->port[1] != sk->port[1]) { + printf(" ("); + print_host(&sk->addr[1], sk->port[1], s->af, opts); + printf(")"); } - print_host(&s->gwy, s->af, opts); if (s->direction == PF_OUT) printf(" -> "); else printf(" <- "); - print_host(&s->ext, s->af, opts); + print_host(&nk->addr[0], nk->port[0], s->af, opts); + if (PF_ANEQ(&nk->addr[0], &sk->addr[0], s->af) || + nk->port[0] != sk->port[0]) { + printf(" ("); + print_host(&sk->addr[0], sk->port[0], s->af, opts); + printf(")"); + } printf(" "); if (s->proto == IPPROTO_TCP) { @@ -281,25 +294,37 @@ print_state(struct pfsync_state *s, int opts) } if (opts & PF_OPT_VERBOSE) { - sec = s->creation % 60; - s->creation /= 60; - min = s->creation % 60; - s->creation /= 60; - printf(" age %.2u:%.2u:%.2u", s->creation, min, sec); - sec = s->expire % 60; - s->expire /= 60; + u_int64_t packets[2]; + u_int64_t bytes[2]; + u_int32_t creation = ntohl(s->creation); + u_int32_t expire = ntohl(s->expire); + + sec = creation % 60; + creation /= 60; + min = creation % 60; + creation /= 60; + printf(" age %.2u:%.2u:%.2u", creation, min, sec); + sec = expire % 60; + expire /= 60; min = s->expire % 60; - s->expire /= 60; - printf(", expires in %.2u:%.2u:%.2u", s->expire, min, sec); + expire /= 60; + printf(", expires in %.2u:%.2u:%.2u", expire, min, sec); + + bcopy(s->packets[0], &packets[0], sizeof(u_int64_t)); + bcopy(s->packets[1], &packets[1], sizeof(u_int64_t)); + bcopy(s->bytes[0], &bytes[0], sizeof(u_int64_t)); + bcopy(s->bytes[1], &bytes[1], sizeof(u_int64_t)); printf(", %llu:%llu pkts, %llu:%llu bytes", - pf_state_counter_from_pfsync(s->packets[0]), - pf_state_counter_from_pfsync(s->packets[1]), - pf_state_counter_from_pfsync(s->bytes[0]), - pf_state_counter_from_pfsync(s->bytes[1])); - if (s->anchor != -1) - printf(", anchor %u", s->anchor); - if (s->rule != -1) - printf(", rule %u", s->rule); + betoh64(packets[0]), + betoh64(packets[1]), + betoh64(bytes[0]), + betoh64(bytes[1])); + if (ntohl(s->anchor) != -1) + printf(", anchor %u", ntohl(s->anchor)); + if (ntohl(s->rule) != -1) + printf(", rule %u", ntohl(s->rule)); + if (s->state_flags & PFSTATE_SLOPPY) + printf(", sloppy"); if (s->sync_flags & PFSYNC_FLAG_SRCNODE) printf(", source-track"); if (s->sync_flags & PFSYNC_FLAG_NATSRCNODE) @@ -307,9 +332,12 @@ print_state(struct pfsync_state *s, int opts) printf("\n"); } if (opts & PF_OPT_VERBOSE2) { - printf(" id: %016llx creatorid: %08x%s\n", - pf_state_counter_from_pfsync(s->id), ntohl(s->creatorid), - ((s->sync_flags & PFSTATE_NOSYNC) ? " (no-sync)" : "")); + u_int64_t id; + + bcopy(&s->id, &id, sizeof(u_int64_t)); + printf(" id: %016llx creatorid: %08x", + betoh64(id), ntohl(s->creatorid)); + printf("\n"); } } diff --git a/pfctl/pfctl.8 b/pfctl/pfctl.8 index 4dfbc407aae..9ce34ce4112 100644 --- a/pfctl/pfctl.8 +++ b/pfctl/pfctl.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pfctl.8,v 1.133 2007/07/01 11:38:51 henning Exp $ +.\" $OpenBSD: pfctl.8,v 1.139 2008/06/11 07:23:36 jmc Exp $ .\" .\" Copyright (c) 2001 Kjell Wooding. All rights reserved. .\" @@ -24,12 +24,12 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.Dd $Mdocdate: May 31 2007 $ +.Dd $Mdocdate: June 10 2008 $ .Dt PFCTL 8 .Os .Sh NAME .Nm pfctl -.Nd "control the packet filter (PF) and network address translation (NAT) device" +.Nd control the packet filter (PF) device .Sh SYNOPSIS .Nm pfctl .Bk -words @@ -41,7 +41,10 @@ .Op Fl f Ar file .Op Fl i Ar interface .Op Fl K Ar host | network -.Op Fl k Ar host | network +.Xo +.Oo Fl k +.Ar host | network | label | id +.Oc Xc .Op Fl o Ar level .Op Fl p Ar device .Op Fl s Ar modifier @@ -249,22 +252,28 @@ or .Fl K Ar network option may be specified, which will kill all the source tracking entries from the first host/network to the second. -.It Fl k Ar host | network -Kill all of the state entries originating from the specified -.Ar host +.It Xo +.Fl k +.Ar host | network | label | id +.Xc +Kill all of the state entries matching the specified +.Ar host , +.Ar network , +.Ar label , or -.Ar network . +.Ar id . +.Pp +For example, to kill all of the state entries originating from +.Dq host : +.Pp +.Dl # pfctl -k host +.Pp A second .Fl k Ar host or .Fl k Ar network option may be specified, which will kill all the state entries from the first host/network to the second. -For example, to kill all of the state entries originating from -.Dq host : -.Pp -.Dl # pfctl -k host -.Pp To kill all of the state entries from .Dq host1 to @@ -281,6 +290,32 @@ To kill all states with the target .Dq host2 : .Pp .Dl # pfctl -k 0.0.0.0/0 -k host2 +.Pp +It is also possible to kill states by rule label or state ID. +In this mode the first +.Fl k +argument is used to specify the type +of the second argument. +The following command would kill all states that have been created +from rules carrying the label +.Dq foobar : +.Pp +.Dl # pfctl -k label -k foobar +.Pp +To kill one specific state by its unique state ID +(as shown by pfctl -s state -vv), +use the +.Ar id +modifier and as a second argument the state ID and optional creator ID. +To kill a state with ID 4823e84500000003 use: +.Pp +.Dl # pfctl -k id -k 4823e84500000003 +.Pp +To kill a state with ID 4823e84500000018 created from a backup +firewall with hostid 00000002 use: +.Pp +.Dl # pfctl -k id -k 4823e84500000018/2 +.Pp .It Fl m Merge in explicitly given options without resetting those which are omitted. @@ -375,7 +410,7 @@ When used together with source tracking statistics are also shown. .It Fl s Cm labels Show per-rule statistics (label, evaluations, packets total, bytes total, -packets in, bytes in, packets out, bytes out) of +packets in, bytes in, packets out, bytes out, state creations) of filter rules with labels, useful for accounting. .It Fl s Cm timeouts Show the current global timeouts. @@ -486,7 +521,7 @@ attributes. The address/network has been cleared (statistics). .El .Pp -Each table maintains a set of counters that can be retrieved using the +Each table can maintain a set of counters that can be retrieved using the .Fl v flag of .Nm . @@ -497,7 +532,7 @@ FTP server. The following commands configure the firewall and send 10 pings to the FTP server: .Bd -literal -offset indent -# printf "table { ftp.openbsd.org }\en \e +# printf "table counters { ftp.openbsd.org }\en \e pass out to \en" | pfctl -f- # ping -qc10 ftp.openbsd.org .Ed @@ -531,7 +566,7 @@ the number of rules which reference the table, and the global packet statistics for the whole table: .Bd -literal -offset indent # pfctl -vvsTables ---a-r- test +--a-r-C test Addresses: 1 Cleared: Thu Feb 13 18:55:18 2003 References: [ Anchors: 0 Rules: 1 ] @@ -591,6 +626,8 @@ For tables which are referenced (used) by rules. .It h This flag is set when a table in the main ruleset is hidden by one or more tables of the same name from anchors attached below it. +.It C +This flag is set when per-address counters are enabled on the table. .El .It Fl t Ar table Specify the name of the table. diff --git a/pfctl/pfctl.c b/pfctl/pfctl.c index 3829f2cb413..f01b6a92717 100644 --- a/pfctl/pfctl.c +++ b/pfctl/pfctl.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl.c,v 1.273 2008/02/13 19:55:12 kettenis Exp $ */ +/* $OpenBSD: pfctl.c,v 1.277 2008/07/24 10:52:43 henning Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -68,7 +68,9 @@ int pfctl_clear_src_nodes(int, int); int pfctl_clear_states(int, const char *, int); void pfctl_addrprefix(char *, struct pf_addr *); int pfctl_kill_src_nodes(int, const char *, int); -int pfctl_kill_states(int, const char *, int); +int pfctl_net_kill_states(int, const char *, int); +int pfctl_label_kill_states(int, const char *, int); +int pfctl_id_kill_states(int, const char *, int); void pfctl_init_options(struct pfctl *); int pfctl_load_options(struct pfctl *); int pfctl_load_limit(struct pfctl *, unsigned int, unsigned int); @@ -229,7 +231,7 @@ usage(void) fprintf(stderr, "usage: %s [-AdeghmNnOqRrvz] ", __progname); fprintf(stderr, "[-a anchor] [-D macro=value] [-F modifier]\n"); fprintf(stderr, "\t[-f file] [-i interface] [-K host | network] "); - fprintf(stderr, "[-k host | network]\n"); + fprintf(stderr, "[-k host | network | label | id]\n"); fprintf(stderr, "\t[-o level] [-p device] [-s modifier]\n"); fprintf(stderr, "\t[-t table -T command [address ...]] [-x level]\n"); exit(1); @@ -376,7 +378,7 @@ pfctl_clear_states(int dev, const char *iface, int opts) if (ioctl(dev, DIOCCLRSTATES, &psk)) err(1, "DIOCCLRSTATES"); if ((opts & PF_OPT_QUIET) == 0) - fprintf(stderr, "%d states cleared\n", psk.psk_af); + fprintf(stderr, "%d states cleared\n", psk.psk_killed); return (0); } @@ -515,17 +517,13 @@ pfctl_kill_src_nodes(int dev, const char *iface, int opts) if (ioctl(dev, DIOCKILLSRCNODES, &psnk)) err(1, "DIOCKILLSRCNODES"); - killed += psnk.psnk_af; - /* fixup psnk.psnk_af */ - psnk.psnk_af = resp[1]->ai_family; + killed += psnk.psnk_killed; } freeaddrinfo(res[1]); } else { if (ioctl(dev, DIOCKILLSRCNODES, &psnk)) err(1, "DIOCKILLSRCNODES"); - killed += psnk.psnk_af; - /* fixup psnk.psnk_af */ - psnk.psnk_af = res[0]->ai_family; + killed += psnk.psnk_killed; } } @@ -538,7 +536,7 @@ pfctl_kill_src_nodes(int dev, const char *iface, int opts) } int -pfctl_kill_states(int dev, const char *iface, int opts) +pfctl_net_kill_states(int dev, const char *iface, int opts) { struct pfioc_state_kill psk; struct addrinfo *res[2], *resp[2]; @@ -625,17 +623,13 @@ pfctl_kill_states(int dev, const char *iface, int opts) if (ioctl(dev, DIOCKILLSTATES, &psk)) err(1, "DIOCKILLSTATES"); - killed += psk.psk_af; - /* fixup psk.psk_af */ - psk.psk_af = resp[1]->ai_family; + killed += psk.psk_killed; } freeaddrinfo(res[1]); } else { if (ioctl(dev, DIOCKILLSTATES, &psk)) err(1, "DIOCKILLSTATES"); - killed += psk.psk_af; - /* fixup psk.psk_af */ - psk.psk_af = res[0]->ai_family; + killed += psk.psk_killed; } } @@ -647,6 +641,68 @@ pfctl_kill_states(int dev, const char *iface, int opts) return (0); } +int +pfctl_label_kill_states(int dev, const char *iface, int opts) +{ + struct pfioc_state_kill psk; + + if (state_killers != 2 || (strlen(state_kill[1]) == 0)) { + warnx("no label specified"); + usage(); + } + memset(&psk, 0, sizeof(psk)); + if (iface != NULL && strlcpy(psk.psk_ifname, iface, + sizeof(psk.psk_ifname)) >= sizeof(psk.psk_ifname)) + errx(1, "invalid interface: %s", iface); + + if (strlcpy(psk.psk_label, state_kill[1], sizeof(psk.psk_label)) >= + sizeof(psk.psk_label)) + errx(1, "label too long: %s", state_kill[1]); + + if (ioctl(dev, DIOCKILLSTATES, &psk)) + err(1, "DIOCKILLSTATES"); + + if ((opts & PF_OPT_QUIET) == 0) + fprintf(stderr, "killed %d states\n", psk.psk_killed); + + return (0); +} + +int +pfctl_id_kill_states(int dev, const char *iface, int opts) +{ + struct pfioc_state_kill psk; + + if (state_killers != 2 || (strlen(state_kill[1]) == 0)) { + warnx("no id specified"); + usage(); + } + + memset(&psk, 0, sizeof(psk)); + if ((sscanf(state_kill[1], "%llx/%x", + &psk.psk_pfcmp.id, &psk.psk_pfcmp.creatorid)) == 2) + HTONL(psk.psk_pfcmp.creatorid); + else if ((sscanf(state_kill[1], "%llx", &psk.psk_pfcmp.id)) == 1) { + psk.psk_pfcmp.creatorid = 0; + } else { + warnx("wrong id format specified"); + usage(); + } + if (psk.psk_pfcmp.id == 0) { + warnx("cannot kill id 0"); + usage(); + } + + psk.psk_pfcmp.id = htobe64(psk.psk_pfcmp.id); + if (ioctl(dev, DIOCKILLSTATES, &psk)) + err(1, "DIOCKILLSTATES"); + + if ((opts & PF_OPT_QUIET) == 0) + fprintf(stderr, "killed %d states\n", psk.psk_killed); + + return (0); +} + int pfctl_get_pool(int dev, struct pf_pool *pool, u_int32_t nr, u_int32_t ticket, int r_action, char *anchorname) @@ -734,10 +790,12 @@ pfctl_print_rule_counters(struct pf_rule *rule, int opts) (unsigned long long)(rule->packets[0] + rule->packets[1]), (unsigned long long)(rule->bytes[0] + - rule->bytes[1]), rule->states); + rule->bytes[1]), rule->states_cur); if (!(opts & PF_OPT_DEBUG)) - printf(" [ Inserted: uid %u pid %u ]\n", - (unsigned)rule->cuid, (unsigned)rule->cpid); + printf(" [ Inserted: uid %u pid %u " + "State Creations: %-6u]\n", + (unsigned)rule->cuid, (unsigned)rule->cpid, + rule->states_tot); } } @@ -804,19 +862,6 @@ pfctl_show_rules(int dev, char *path, int opts, enum pfctl_show format, switch (format) { case PFCTL_SHOW_LABELS: - if (pr.rule.label[0]) { - printf("%s ", pr.rule.label); - printf("%llu %llu %llu %llu %llu %llu %llu\n", - (unsigned long long)pr.rule.evaluations, - (unsigned long long)(pr.rule.packets[0] + - pr.rule.packets[1]), - (unsigned long long)(pr.rule.bytes[0] + - pr.rule.bytes[1]), - (unsigned long long)pr.rule.packets[0], - (unsigned long long)pr.rule.bytes[0], - (unsigned long long)pr.rule.packets[1], - (unsigned long long)pr.rule.bytes[1]); - } break; case PFCTL_SHOW_RULES: if (pr.rule.label[0] && (opts & PF_OPT_SHOWALL)) @@ -850,8 +895,9 @@ pfctl_show_rules(int dev, char *path, int opts, enum pfctl_show format, switch (format) { case PFCTL_SHOW_LABELS: if (pr.rule.label[0]) { - printf("%s ", pr.rule.label); - printf("%llu %llu %llu %llu %llu %llu %llu\n", + printf("%s %llu %llu %llu %llu" + " %llu %llu %llu %llu\n", + pr.rule.label, (unsigned long long)pr.rule.evaluations, (unsigned long long)(pr.rule.packets[0] + pr.rule.packets[1]), @@ -860,7 +906,8 @@ pfctl_show_rules(int dev, char *path, int opts, enum pfctl_show format, (unsigned long long)pr.rule.packets[0], (unsigned long long)pr.rule.bytes[0], (unsigned long long)pr.rule.packets[1], - (unsigned long long)pr.rule.bytes[1]); + (unsigned long long)pr.rule.bytes[1], + (unsigned long long)pr.rule.states_tot); } break; case PFCTL_SHOW_RULES: @@ -1526,7 +1573,8 @@ pfctl_init_options(struct pfctl *pf) mib[0] = CTL_HW; mib[1] = HW_PHYSMEM64; size = sizeof(mem); - (void) sysctl(mib, 2, &mem, &size, NULL, 0); + if (sysctl(mib, 2, &mem, &size, NULL, 0) == -1) + err(1, "sysctl"); if (mem <= 100*1024*1024) pf->limit[PF_LIMIT_TABLE_ENTRIES] = PFR_KENTRY_HIWAT_SMALL; @@ -2256,8 +2304,14 @@ main(int argc, char *argv[]) break; } } - if (state_killers) - pfctl_kill_states(dev, ifaceopt, opts); + if (state_killers) { + if (!strcmp(state_kill[0], "label")) + pfctl_label_kill_states(dev, ifaceopt, opts); + else if (!strcmp(state_kill[0], "id")) + pfctl_id_kill_states(dev, ifaceopt, opts); + else + pfctl_net_kill_states(dev, ifaceopt, opts); + } if (src_node_killers) pfctl_kill_src_nodes(dev, ifaceopt, opts); diff --git a/pfctl/pfctl.h b/pfctl/pfctl.h index 7b7156e735d..f9db55072dd 100644 --- a/pfctl/pfctl.h +++ b/pfctl/pfctl.h @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl.h,v 1.42 2007/12/05 12:01:47 chl Exp $ */ +/* $OpenBSD: pfctl.h,v 1.43 2008/05/29 01:00:53 mcbride Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -109,7 +109,7 @@ struct pf_altq *pfaltq_lookup(const char *); char *rate2str(double); void print_addr(struct pf_addr_wrap *, sa_family_t, int); -void print_host(struct pfsync_state_host *, sa_family_t, int); +void print_host(struct pf_addr *, u_int16_t p, sa_family_t, int); void print_seq(struct pfsync_state_peer *); void print_state(struct pfsync_state *, int); int unmask(struct pf_addr *, sa_family_t); diff --git a/pfctl/pfctl_altq.c b/pfctl/pfctl_altq.c index d1a46609ccb..0a174e5f46b 100644 --- a/pfctl/pfctl_altq.c +++ b/pfctl/pfctl_altq.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_altq.c,v 1.93 2007/10/15 02:16:35 deraadt Exp $ */ +/* $OpenBSD: pfctl_altq.c,v 1.94 2008/07/25 17:43:44 martynas Exp $ */ /* * Copyright (c) 2002 @@ -875,7 +875,6 @@ print_hfsc_opts(const struct pf_altq *a, const struct node_queue_opt *qopts) /* * admission control using generalized service curve */ -#define INFINITY HUGE_VAL /* positive infinity defined in */ /* add a new service curve to a generalized service curve */ static void diff --git a/pfctl/pfctl_optimize.c b/pfctl/pfctl_optimize.c index 8a80232cc5b..bbed611d2fe 100644 --- a/pfctl/pfctl_optimize.c +++ b/pfctl/pfctl_optimize.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_optimize.c,v 1.16 2008/01/26 13:16:36 mcbride Exp $ */ +/* $OpenBSD: pfctl_optimize.c,v 1.18 2008/05/07 06:23:30 markus Exp $ */ /* * Copyright (c) 2004 Mike Frantzen @@ -182,7 +182,8 @@ struct pf_rule_field { PF_RULE_FIELD(packets, DC), PF_RULE_FIELD(bytes, DC), PF_RULE_FIELD(kif, DC), - PF_RULE_FIELD(states, DC), + PF_RULE_FIELD(states_cur, DC), + PF_RULE_FIELD(states_tot, DC), PF_RULE_FIELD(src_nodes, DC), PF_RULE_FIELD(nr, DC), PF_RULE_FIELD(entries, DC), @@ -198,6 +199,7 @@ struct pf_rule_field { PF_RULE_FIELD(natpass, NEVER), PF_RULE_FIELD(max_mss, NEVER), PF_RULE_FIELD(min_ttl, NEVER), + PF_RULE_FIELD(set_tos, NEVER), }; diff --git a/pfctl/pfctl_parser.c b/pfctl/pfctl_parser.c index e88306b30f4..7368dbe7d3c 100644 --- a/pfctl/pfctl_parser.c +++ b/pfctl/pfctl_parser.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_parser.c,v 1.235 2007/10/15 02:16:35 deraadt Exp $ */ +/* $OpenBSD: pfctl_parser.c,v 1.240 2008/06/10 20:55:02 mcbride Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -860,6 +860,8 @@ print_rule(struct pf_rule *r, const char *anchor_call, int verbose) opts = 1; if (r->rule_flag & PFRULE_IFBOUND) opts = 1; + if (r->rule_flag & PFRULE_STATESLOPPY) + opts = 1; for (i = 0; !opts && i < PFTM_MAX; ++i) if (r->timeout[i]) opts = 1; @@ -926,6 +928,12 @@ print_rule(struct pf_rule *r, const char *anchor_call, int verbose) printf("if-bound"); opts = 0; } + if (r->rule_flag & PFRULE_STATESLOPPY) { + if (!opts) + printf(", "); + printf("sloppy"); + opts = 0; + } for (i = 0; i < PFTM_MAX; ++i) if (r->timeout[i]) { int j; @@ -953,6 +961,8 @@ print_rule(struct pf_rule *r, const char *anchor_call, int verbose) printf(" min-ttl %d", r->min_ttl); if (r->max_mss) printf(" max-mss %d", r->max_mss); + if (r->rule_flag & PFRULE_SET_TOS) + printf(" set-tos 0x%2.2x", r->set_tos); if (r->allow_opts) printf(" allow-opts"); if (r->action == PF_SCRUB) { @@ -981,6 +991,22 @@ print_rule(struct pf_rule *r, const char *anchor_call, int verbose) } if (r->rtableid != -1) printf(" rtable %u", r->rtableid); + if (r->divert.port) { + if (PF_AZERO(&r->divert.addr, r->af)) { + printf(" divert-reply"); + } else { + /* XXX cut&paste from print_addr */ + char buf[48]; + + printf(" divert-to "); + if (inet_ntop(r->af, &r->divert.addr, buf, + sizeof(buf)) == NULL) + printf("?"); + else + printf("%s", buf); + printf(" port %u", ntohs(r->divert.port)); + } + } if (!anchor_call[0] && (r->action == PF_NAT || r->action == PF_BINAT || r->action == PF_RDR)) { printf(" -> "); @@ -1001,6 +1027,8 @@ print_tabledef(const char *name, int flags, int addrs, printf(" const"); if (flags & PFR_TFLAG_PERSIST) printf(" persist"); + if (flags & PFR_TFLAG_COUNTERS) + printf(" counters"); SIMPLEQ_FOREACH(ti, nodes, entries) { if (ti->file) { printf(" file \"%s\"", ti->file); diff --git a/pfctl/pfctl_table.c b/pfctl/pfctl_table.c index bee57862650..fa4ae6a6e18 100644 --- a/pfctl/pfctl_table.c +++ b/pfctl/pfctl_table.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_table.c,v 1.66 2007/03/01 17:20:54 deraadt Exp $ */ +/* $OpenBSD: pfctl_table.c,v 1.68 2008/06/21 10:34:08 mcbride Exp $ */ /* * Copyright (c) 2002 Cedric Berger @@ -272,12 +272,14 @@ pfctl_table(int argc, char *argv[], char *tname, const char *command, if (b.pfrb_size <= b.pfrb_msize) break; } - PFRB_FOREACH(p, &b) + PFRB_FOREACH(p, &b) { + ((struct pfr_astats *)p)->pfras_a.pfra_fback = 0; if (time(NULL) - ((struct pfr_astats *)p)->pfras_tzero > lifetime) if (pfr_buf_add(&b2, &((struct pfr_astats *)p)->pfras_a)) err(1, "duplicate buffer"); + } if (opts & PF_OPT_VERBOSE) flags |= PFR_FLAG_FEEDBACK; @@ -364,13 +366,14 @@ print_table(struct pfr_table *ta, int verbose, int debug) if (!debug && !(ta->pfrt_flags & PFR_TFLAG_ACTIVE)) return; if (verbose) { - printf("%c%c%c%c%c%c\t%s", + printf("%c%c%c%c%c%c%c\t%s", (ta->pfrt_flags & PFR_TFLAG_CONST) ? 'c' : '-', (ta->pfrt_flags & PFR_TFLAG_PERSIST) ? 'p' : '-', (ta->pfrt_flags & PFR_TFLAG_ACTIVE) ? 'a' : '-', (ta->pfrt_flags & PFR_TFLAG_INACTIVE) ? 'i' : '-', (ta->pfrt_flags & PFR_TFLAG_REFERENCED) ? 'r' : '-', (ta->pfrt_flags & PFR_TFLAG_REFDANCHOR) ? 'h' : '-', + (ta->pfrt_flags & PFR_TFLAG_COUNTERS) ? 'C' : '-', ta->pfrt_name); if (ta->pfrt_anchor[0]) printf("\t%s", ta->pfrt_anchor); @@ -425,7 +428,7 @@ void print_addrx(struct pfr_addr *ad, struct pfr_addr *rad, int dns) { char ch, buf[256] = "{error}"; - char fb[] = { ' ', 'M', 'A', 'D', 'C', 'Z', 'X', ' ', 'Y' }; + char fb[] = { ' ', 'M', 'A', 'D', 'C', 'Z', 'X', ' ', 'Y', ' ' }; unsigned int fback, hostnet; fback = (rad != NULL) ? rad->pfra_fback : ad->pfra_fback; @@ -474,6 +477,8 @@ print_astats(struct pfr_astats *as, int dns) print_addrx(&as->pfras_a, NULL, dns); printf("\tCleared: %s", ctime(&time)); + if (as->pfras_a.pfra_fback == PFR_FB_NOCOUNT) + return; for (dir = 0; dir < PFR_DIR_MAX; dir++) for (op = 0; op < PFR_OP_ADDR_MAX; op++) printf("\t%-12s [ Packets: %-18llu Bytes: %-18llu ]\n", diff --git a/pflogd/privsep_fdpass.c b/pflogd/privsep_fdpass.c index 50afdfc2859..0e6c3c4c1e8 100644 --- a/pflogd/privsep_fdpass.c +++ b/pflogd/privsep_fdpass.c @@ -1,4 +1,4 @@ -/* $OpenBSD: privsep_fdpass.c,v 1.2 2004/08/13 02:51:48 djm Exp $ */ +/* $OpenBSD: privsep_fdpass.c,v 1.5 2008/03/24 16:11:08 deraadt Exp $ */ /* * Copyright 2001 Niels Provos @@ -50,7 +50,10 @@ void send_fd(int sock, int fd) { struct msghdr msg; - char tmp[CMSG_SPACE(sizeof(int))]; + union { + struct cmsghdr hdr; + char buf[CMSG_SPACE(sizeof(int))]; + } cmsgbuf; struct cmsghdr *cmsg; struct iovec vec; int result = 0; @@ -59,8 +62,8 @@ send_fd(int sock, int fd) memset(&msg, 0, sizeof(msg)); if (fd >= 0) { - msg.msg_control = (caddr_t)tmp; - msg.msg_controllen = CMSG_LEN(sizeof(int)); + msg.msg_control = (caddr_t)&cmsgbuf.buf; + msg.msg_controllen = sizeof(cmsgbuf.buf); cmsg = CMSG_FIRSTHDR(&msg); cmsg->cmsg_len = CMSG_LEN(sizeof(int)); cmsg->cmsg_level = SOL_SOCKET; @@ -86,7 +89,10 @@ int receive_fd(int sock) { struct msghdr msg; - char tmp[CMSG_SPACE(sizeof(int))]; + union { + struct cmsghdr hdr; + char buf[CMSG_SPACE(sizeof(int))]; + } cmsgbuf; struct cmsghdr *cmsg; struct iovec vec; ssize_t n; @@ -98,8 +104,8 @@ receive_fd(int sock) vec.iov_len = sizeof(int); msg.msg_iov = &vec; msg.msg_iovlen = 1; - msg.msg_control = tmp; - msg.msg_controllen = sizeof(tmp); + msg.msg_control = &cmsgbuf.buf; + msg.msg_controllen = sizeof(cmsgbuf.buf); if ((n = recvmsg(sock, &msg, 0)) == -1) warn("%s: recvmsg", __func__); diff --git a/tftp-proxy/tftp-proxy.c b/tftp-proxy/tftp-proxy.c index 18d3323e911..d2d2875717a 100644 --- a/tftp-proxy/tftp-proxy.c +++ b/tftp-proxy/tftp-proxy.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tftp-proxy.c,v 1.2 2006/12/20 03:33:38 joel Exp $ +/* $OpenBSD: tftp-proxy.c,v 1.6 2008/04/13 00:22:17 djm Exp $ * * Copyright (c) 2005 DLS Internet Services * Copyright (c) 2004, 2005 Camiel Dobbelaar, @@ -75,8 +75,10 @@ main(int argc, char *argv[]) char *p; struct tftphdr *tp; struct passwd *pw; - - char cbuf[CMSG_SPACE(sizeof(struct sockaddr_storage))]; + union { + struct cmsghdr hdr; + char buf[CMSG_SPACE(sizeof(struct sockaddr_storage))]; + } cmsgbuf; char req[PKTSIZE]; struct cmsghdr *cmsg; struct msghdr msg; @@ -161,8 +163,8 @@ main(int argc, char *argv[]) msg.msg_namelen = sizeof(from); msg.msg_iov = &iov; msg.msg_iovlen = 1; - msg.msg_control = cbuf; - msg.msg_controllen = CMSG_LEN(sizeof(struct sockaddr_storage)); + msg.msg_control = &cmsgbuf.buf; + msg.msg_controllen = sizeof(cmsgbuf.buf); if (recvmsg(fd, &msg, 0) < 0) { syslog(LOG_ERR, "recvmsg: %m"); @@ -381,8 +383,8 @@ sock_ntop(struct sockaddr *sa) u_int16_t pick_proxy_port(void) { - return (IPPORT_HIFIRSTAUTO + (arc4random() % - (IPPORT_HILASTAUTO - IPPORT_HIFIRSTAUTO))); + return (IPPORT_HIFIRSTAUTO + + arc4random_uniform(IPPORT_HILASTAUTO - IPPORT_HIFIRSTAUTO)); } static void From 739de636d7c95255cef4fc68a2c80cd8af54e502 Mon Sep 17 00:00:00 2001 From: Max Laier Date: Tue, 18 Aug 2009 16:13:59 +0000 Subject: [PATCH 06/39] eri@ wants to start on porting the latest pf in his user space so we can finally have a new version in 9.0. Import pf as of OPENBSD_4_5_BASE to help with that. --- authpf/Makefile | 2 +- authpf/authpf.8 | 8 ++- authpf/authpf.c | 90 ++++++++++++++++++++++-------- authpf/pathnames.h | 2 +- ftp-proxy/Makefile | 2 +- ftp-proxy/filter.c | 2 +- ftp-proxy/filter.h | 2 +- ftp-proxy/ftp-proxy.8 | 2 +- ftp-proxy/ftp-proxy.c | 2 +- libevent/buffer.c | 16 +++--- libevent/evbuffer.c | 8 ++- libevent/event-internal.h | 2 + libevent/event.c | 21 +++---- libevent/event.h | 17 +++--- libevent/evsignal.h | 2 + libevent/kqueue.c | 28 +++++----- libevent/log.c | 14 ++--- libevent/log.h | 2 + libevent/poll.c | 7 ++- libevent/select.c | 4 +- libevent/signal.c | 4 +- man/pf.4 | 9 ++- man/pf.conf.5 | 26 +++++++-- man/pf.os.5 | 2 +- man/pflog.4 | 2 +- man/pflow.4 | 113 ++++++++++++++++++++++++++++++++++++++ man/pfsync.4 | 87 ++++++++++++----------------- pfctl/Makefile | 2 +- pfctl/parse.y | 64 ++++++++++++++++----- pfctl/pf_print_state.c | 6 +- pfctl/pfctl.8 | 2 +- pfctl/pfctl.c | 11 ++-- pfctl/pfctl.h | 2 +- pfctl/pfctl_altq.c | 2 +- pfctl/pfctl_optimize.c | 2 +- pfctl/pfctl_osfp.c | 2 +- pfctl/pfctl_parser.c | 6 ++ pfctl/pfctl_parser.h | 2 +- pfctl/pfctl_qstats.c | 2 +- pfctl/pfctl_radix.c | 2 +- pfctl/pfctl_table.c | 2 +- pflogd/Makefile | 2 +- pflogd/pflogd.8 | 9 ++- pflogd/pflogd.c | 37 ++++++++++--- pflogd/pflogd.h | 2 +- pflogd/privsep.c | 2 +- pflogd/privsep_fdpass.c | 2 +- tftp-proxy/Makefile | 2 +- tftp-proxy/filter.c | 2 +- tftp-proxy/filter.h | 2 +- tftp-proxy/tftp-proxy.8 | 2 +- tftp-proxy/tftp-proxy.c | 2 +- 52 files changed, 447 insertions(+), 200 deletions(-) create mode 100644 man/pflow.4 diff --git a/authpf/Makefile b/authpf/Makefile index 100001a0a74..b0d26a6d3df 100644 --- a/authpf/Makefile +++ b/authpf/Makefile @@ -1,4 +1,4 @@ -# $OpenBSD: Makefile,v 1.13 2008/02/14 01:49:17 mcbride Exp $ +# $OpenBSD: Makefile,v 1.12 2004/04/25 19:24:52 deraadt Exp $ PROG= authpf MAN= authpf.8 diff --git a/authpf/authpf.8 b/authpf/authpf.8 index 6b6afa4616c..4b6f13be418 100644 --- a/authpf/authpf.8 +++ b/authpf/authpf.8 @@ -14,7 +14,7 @@ .\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF .\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .\" -.Dd $Mdocdate: February 14 2008 $ +.Dd $Mdocdate: March 18 2008 $ .Dt AUTHPF 8 .Os .Sh NAME @@ -202,6 +202,9 @@ It is also possible to configure to only allow specific users access. This is done by listing their login names, one per line, in .Pa /etc/authpf/authpf.allow . +A group of users can also be indicated by prepending "%" to the group name, +and all members of a login class can be indicated by prepending "@" to the +login class name. If "*" is found on a line, then all usernames match. If .Nm @@ -314,7 +317,8 @@ They have a wireless network which they would like to protect from unauthorized use. To accomplish this, they create the file .Pa /etc/authpf/authpf.allow -which lists their login ids, one per line. +which lists their login ids, group prepended with "%", or login class +prepended with "@", one per line. At this point, even if eve could authenticate to .Xr sshd 8 , she would not be allowed to use the gateway. diff --git a/authpf/authpf.c b/authpf/authpf.c index 1416b0db917..208de3ac5b6 100644 --- a/authpf/authpf.c +++ b/authpf/authpf.c @@ -1,4 +1,4 @@ -/* $OpenBSD: authpf.c,v 1.107 2008/02/14 01:49:17 mcbride Exp $ */ +/* $OpenBSD: authpf.c,v 1.111 2009/01/10 17:17:32 todd Exp $ */ /* * Copyright (C) 1998 - 2007 Bob Beck (beck@openbsd.org). @@ -32,6 +32,7 @@ #include #include #include +#include #include #include #include @@ -43,7 +44,7 @@ static int read_config(FILE *); static void print_message(char *); -static int allowed_luser(char *); +static int allowed_luser(struct passwd *); static int check_luser(char *, char *); static int remove_stale_rulesets(void); static int recursive_ruleset_purge(char *, char *); @@ -58,6 +59,7 @@ char tablename[PF_TABLE_NAME_SIZE] = "authpf_users"; int user_ip = 1; /* controls whether $user_ip is set */ FILE *pidfp; +int pidfd = -1; char luser[MAXLOGNAME]; /* username */ char ipsrc[256]; /* ip as a string */ char pidfile[MAXPATHLEN]; /* we save pid in this file. */ @@ -78,7 +80,7 @@ extern char *__progname; /* program name */ int main(int argc, char *argv[]) { - int lockcnt = 0, n, pidfd; + int lockcnt = 0, n; FILE *config; struct in6_addr ina; struct passwd *pw; @@ -93,7 +95,7 @@ main(int argc, char *argv[]) config = fopen(PATH_CONFFILE, "r"); if (config == NULL) { - syslog(LOG_ERR, "can not open %s (%m)", PATH_CONFFILE); + syslog(LOG_ERR, "cannot open %s (%m)", PATH_CONFFILE); exit(1); } @@ -186,6 +188,14 @@ main(int argc, char *argv[]) goto die; } + signal(SIGTERM, need_death); + signal(SIGINT, need_death); + signal(SIGALRM, need_death); + signal(SIGPIPE, need_death); + signal(SIGHUP, need_death); + signal(SIGQUIT, need_death); + signal(SIGTSTP, need_death); + /* * If someone else is already using this ip, then this person * wants to switch users - so kill the old process and exit @@ -239,15 +249,17 @@ main(int argc, char *argv[]) } /* - * we try to kill the previous process and acquire the lock + * We try to kill the previous process and acquire the lock * for 10 seconds, trying once a second. if we can't after - * 10 attempts we log an error and give up + * 10 attempts we log an error and give up. */ - if (++lockcnt > 10) { - syslog(LOG_ERR, "cannot kill previous authpf (pid %d)", - otherpid); + if (want_death || ++lockcnt > 10) { + if (!want_death) + syslog(LOG_ERR, "cannot kill previous authpf (pid %d)", + otherpid); fclose(pidfp); pidfp = NULL; + pidfd = -1; goto dogdeath; } sleep(1); @@ -258,6 +270,7 @@ main(int argc, char *argv[]) */ fclose(pidfp); pidfp = NULL; + pidfd = -1; } while (1); /* whack the group list */ @@ -275,7 +288,7 @@ main(int argc, char *argv[]) } openlog("authpf", LOG_PID | LOG_NDELAY, LOG_DAEMON); - if (!check_luser(PATH_BAN_DIR, luser) || !allowed_luser(luser)) { + if (!check_luser(PATH_BAN_DIR, luser) || !allowed_luser(pw)) { syslog(LOG_INFO, "user %s prohibited", luser); do_death(0); } @@ -306,13 +319,6 @@ main(int argc, char *argv[]) do_death(0); } - signal(SIGTERM, need_death); - signal(SIGINT, need_death); - signal(SIGALRM, need_death); - signal(SIGPIPE, need_death); - signal(SIGHUP, need_death); - signal(SIGQUIT, need_death); - signal(SIGTSTP, need_death); while (1) { printf("\r\nHello %s. ", luser); printf("You are authenticated from host \"%s\"\r\n", ipsrc); @@ -434,6 +440,7 @@ print_message(char *filename) * allowed_luser checks to see if user "luser" is allowed to * use this gateway by virtue of being listed in an allowed * users file, namely /etc/authpf/authpf.allow . + * Users may be listed by , %, or @. * * If /etc/authpf/authpf.allow does not exist, then we assume that * all users who are allowed in by sshd(8) are permitted to @@ -442,7 +449,7 @@ print_message(char *filename) * the session terminates in the same manner as being banned. */ static int -allowed_luser(char *luser) +allowed_luser(struct passwd *pw) { char *buf, *lbuf; int matched; @@ -474,8 +481,14 @@ allowed_luser(char *luser) * "public" gateway, such as it is, so let * everyone use it. */ + int gl_init = 0, ngroups = NGROUPS + 1; + gid_t groups[NGROUPS + 1]; + lbuf = NULL; + matched = 0; + while ((buf = fgetln(f, &len))) { + if (buf[len - 1] == '\n') buf[len - 1] = '\0'; else { @@ -486,7 +499,40 @@ allowed_luser(char *luser) buf = lbuf; } - matched = strcmp(luser, buf) == 0 || strcmp("*", buf) == 0; + if (buf[0] == '@') { + /* check login class */ + if (strcmp(pw->pw_class, buf + 1) == 0) + matched++; + } else if (buf[0] == '%') { + /* check group membership */ + int cnt; + struct group *group; + + if ((group = getgrnam(buf + 1)) == NULL) { + syslog(LOG_ERR, + "invalid group '%s' in %s (%s)", + buf + 1, PATH_ALLOWFILE, + strerror(errno)); + return (0); + } + + if (!gl_init) { + (void) getgrouplist(pw->pw_name, + pw->pw_gid, groups, &ngroups); + gl_init++; + } + + for ( cnt = 0; cnt < ngroups; cnt++) { + if (group->gr_gid == groups[cnt]) { + matched++; + break; + } + } + } else { + /* check username and wildcard */ + matched = strcmp(pw->pw_name, buf) == 0 || + strcmp("*", buf) == 0; + } if (lbuf != NULL) { free(lbuf); @@ -494,10 +540,10 @@ allowed_luser(char *luser) } if (matched) - return (1); /* matched an allowed username */ + return (1); /* matched an allowed user/group */ } syslog(LOG_INFO, "denied access to %s: not listed in %s", - luser, PATH_ALLOWFILE); + pw->pw_name, PATH_ALLOWFILE); /* reuse buf */ buf = "\n\nSorry, you are not allowed to use this facility!\n"; @@ -878,7 +924,7 @@ do_death(int active) authpf_kill_states(); } } - if (pidfile[0] && (pidfp != NULL)) + if (pidfile[0] && pidfd != -1) if (unlink(pidfile) == -1) syslog(LOG_ERR, "cannot unlink %s (%m)", pidfile); exit(ret); diff --git a/authpf/pathnames.h b/authpf/pathnames.h index e02cf77c9fe..494b6ecab95 100644 --- a/authpf/pathnames.h +++ b/authpf/pathnames.h @@ -1,4 +1,4 @@ -/* $OpenBSD: pathnames.h,v 1.8 2008/02/14 01:49:17 mcbride Exp $ */ +/* $OpenBSD: pathnames.h,v 1.7 2004/04/25 18:40:42 beck Exp $ */ /* * Copyright (C) 2002 Chris Kuethe (ckuethe@ualberta.ca) diff --git a/ftp-proxy/Makefile b/ftp-proxy/Makefile index 9541b955e7f..2c9e912bc10 100644 --- a/ftp-proxy/Makefile +++ b/ftp-proxy/Makefile @@ -1,4 +1,4 @@ -# $OpenBSD: Makefile,v 1.3 2006/11/26 11:31:13 deraadt Exp $ +# $OpenBSD: Makefile,v 1.2 2005/06/07 14:12:07 camield Exp $ PROG= ftp-proxy SRCS= ftp-proxy.c filter.c diff --git a/ftp-proxy/filter.c b/ftp-proxy/filter.c index 80625a6fd9c..05f3965c9ed 100644 --- a/ftp-proxy/filter.c +++ b/ftp-proxy/filter.c @@ -1,4 +1,4 @@ -/* $OpenBSD: filter.c,v 1.8 2008/06/13 07:25:26 claudio Exp $ */ +/* $OpenBSD: filter.c,v 1.7 2008/02/26 18:52:53 henning Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, diff --git a/ftp-proxy/filter.h b/ftp-proxy/filter.h index 150bc49d3ce..db33c574a0f 100644 --- a/ftp-proxy/filter.h +++ b/ftp-proxy/filter.h @@ -1,4 +1,4 @@ -/* $OpenBSD: filter.h,v 1.4 2007/08/01 09:31:41 henning Exp $ */ +/* $OpenBSD: filter.h,v 1.3 2005/06/07 14:12:07 camield Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, diff --git a/ftp-proxy/ftp-proxy.8 b/ftp-proxy/ftp-proxy.8 index 30a75415c18..a1129613465 100644 --- a/ftp-proxy/ftp-proxy.8 +++ b/ftp-proxy/ftp-proxy.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: ftp-proxy.8,v 1.11 2008/02/26 18:52:53 henning Exp $ +.\" $OpenBSD: ftp-proxy.8,v 1.10 2007/08/01 15:45:41 jmc Exp $ .\" .\" Copyright (c) 2004, 2005 Camiel Dobbelaar, .\" diff --git a/ftp-proxy/ftp-proxy.c b/ftp-proxy/ftp-proxy.c index 131991a4bb8..d0ac687e98e 100644 --- a/ftp-proxy/ftp-proxy.c +++ b/ftp-proxy/ftp-proxy.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ftp-proxy.c,v 1.19 2008/06/13 07:25:26 claudio Exp $ */ +/* $OpenBSD: ftp-proxy.c,v 1.18 2008/04/22 02:22:22 joel Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, diff --git a/libevent/buffer.c b/libevent/buffer.c index 0327eb54938..e01a5749d80 100644 --- a/libevent/buffer.c +++ b/libevent/buffer.c @@ -1,3 +1,5 @@ +/* $OpenBSD: buffer.c,v 1.14 2007/03/19 15:12:49 millert Exp $ */ + /* * Copyright (c) 2002, 2003 Niels Provos * All rights reserved. @@ -62,7 +64,7 @@ struct evbuffer * evbuffer_new(void) { struct evbuffer *buffer; - + buffer = calloc(1, sizeof(struct evbuffer)); return (buffer); @@ -76,7 +78,7 @@ evbuffer_free(struct evbuffer *buffer) free(buffer); } -/* +/* * This is a destructive add. The data from one buffer moves into * the other buffer. */ @@ -104,16 +106,16 @@ evbuffer_add_buffer(struct evbuffer *outbuf, struct evbuffer *inbuf) SWAP(outbuf, inbuf); SWAP(inbuf, &tmp); - /* + /* * Optimization comes with a price; we need to notify the * buffer if necessary of the changes. oldoff is the amount - * of data that we transfered from inbuf to outbuf + * of data that we transferred from inbuf to outbuf */ if (inbuf->off != oldoff && inbuf->cb != NULL) (*inbuf->cb)(inbuf, oldoff, inbuf->off, inbuf->cbarg); if (oldoff && outbuf->cb != NULL) (*outbuf->cb)(outbuf, 0, oldoff, outbuf->cbarg); - + return (0); } @@ -196,7 +198,7 @@ evbuffer_remove(struct evbuffer *buf, void *data, size_t datlen) memcpy(data, buf->buffer, nread); evbuffer_drain(buf, nread); - + return (nread); } @@ -371,7 +373,7 @@ evbuffer_read(struct evbuffer *buf, int fd, int howmuch) if (n < EVBUFFER_MAX_READ) n = EVBUFFER_MAX_READ; } -#endif +#endif if (howmuch < 0 || howmuch > n) howmuch = n; diff --git a/libevent/evbuffer.c b/libevent/evbuffer.c index 52712bce585..494e45f63e8 100644 --- a/libevent/evbuffer.c +++ b/libevent/evbuffer.c @@ -1,3 +1,5 @@ +/* $OpenBSD: evbuffer.c,v 1.10 2007/03/19 15:12:49 millert Exp $ */ + /* * Copyright (c) 2002-2004 Niels Provos * All rights reserved. @@ -64,7 +66,7 @@ bufferevent_add(struct event *ev, int timeout) return (event_add(ev, ptv)); } -/* +/* * This callback is executed when the size of the input buffer changes. * We use it to apply back pressure on the reading side. */ @@ -73,7 +75,7 @@ void bufferevent_read_pressure_cb(struct evbuffer *buf, size_t old, size_t now, void *arg) { struct bufferevent *bufev = arg; - /* + /* * If we are below the watermark then reschedule reading if it's * still enabled. */ @@ -288,7 +290,7 @@ bufferevent_free(struct bufferevent *bufev) */ int -bufferevent_write(struct bufferevent *bufev, void *data, size_t size) +bufferevent_write(struct bufferevent *bufev, const void *data, size_t size) { int res; diff --git a/libevent/event-internal.h b/libevent/event-internal.h index 7fd4b6c690f..a6dbe9b1445 100644 --- a/libevent/event-internal.h +++ b/libevent/event-internal.h @@ -1,3 +1,5 @@ +/* $OpenBSD: event-internal.h,v 1.4 2007/03/19 15:12:49 millert Exp $ */ + /* * Copyright (c) 2000-2004 Niels Provos * All rights reserved. diff --git a/libevent/event.c b/libevent/event.c index 15bf14cf3b4..9362e4eca5e 100644 --- a/libevent/event.c +++ b/libevent/event.c @@ -1,3 +1,5 @@ +/* $OpenBSD: event.c,v 1.18 2008/05/02 06:09:11 brad Exp $ */ + /* * Copyright (c) 2000-2004 Niels Provos * All rights reserved. @@ -38,7 +40,7 @@ #include #ifdef HAVE_SYS_TIME_H #include -#else +#else #include #endif #include @@ -180,7 +182,7 @@ RB_PROTOTYPE(event_tree, event, ev_timeout_node, compare); RB_GENERATE(event_tree, event, ev_timeout_node, compare); -void * +struct event_base * event_init(void) { int i; @@ -194,13 +196,13 @@ event_init(void) detect_monotonic(); gettime(&base->event_tv); - + RB_INIT(&base->timetree); TAILQ_INIT(&base->eventqueue); TAILQ_INIT(&base->sig.signalqueue); base->sig.ev_signal_pair[0] = -1; base->sig.ev_signal_pair[1] = -1; - + base->evbase = NULL; for (i = 0; eventops[i] && !base->evbase; i++) { base->evsel = eventops[i]; @@ -321,7 +323,7 @@ event_process_active(struct event_base *base) for (ev = TAILQ_FIRST(activeq); ev; ev = TAILQ_FIRST(activeq)) { event_queue_remove(base, ev, EVLIST_ACTIVE); - + /* Allows deletes to work */ ncalls = ev->ev_ncalls; ev->ev_pncalls = &ncalls; @@ -430,7 +432,7 @@ event_base_loop(struct event_base *base, int flags) */ timerclear(&tv); } - + /* If we have no events, we just exit */ if (!event_haveevents(base)) { event_debug(("%s: no events registered.", __func__)); @@ -439,7 +441,6 @@ event_base_loop(struct event_base *base, int flags) res = evsel->dispatch(base, evbase, tv_p); - if (res == -1) return (-1); @@ -652,7 +653,7 @@ event_add(struct event *ev, struct timeval *tv) /* Abort loop */ *ev->ev_pncalls = 0; } - + event_queue_remove(base, ev, EVLIST_ACTIVE); } @@ -913,10 +914,10 @@ event_queue_insert(struct event_base *base, struct event *ev, int queue) const char * event_get_version(void) { - return (VERSION); + return (LIBEVENT_VERSION); } -/* +/* * No thread-safe interface needed - the information should be the same * for all threads. */ diff --git a/libevent/event.h b/libevent/event.h index 4c39939cc50..eb16e9044e2 100644 --- a/libevent/event.h +++ b/libevent/event.h @@ -1,3 +1,5 @@ +/* $OpenBSD: event.h,v 1.19 2008/05/02 06:09:11 brad Exp $ */ + /* * Copyright (c) 2000-2004 Niels Provos * All rights reserved. @@ -43,6 +45,8 @@ typedef unsigned char u_char; typedef unsigned short u_short; #endif +#define LIBEVENT_VERSION "1.3e" + #define EVLIST_TIMEOUT 0x01 #define EVLIST_INSERTED 0x02 #define EVLIST_SIGNAL 0x04 @@ -141,7 +145,7 @@ struct eventop { void (*dealloc)(struct event_base *, void *); }; -void *event_init(void); +struct event_base *event_init(void); int event_dispatch(void); int event_base_dispatch(struct event_base *); void event_base_free(struct event_base *); @@ -169,12 +173,6 @@ int event_base_loopexit(struct event_base *, struct timeval *); #define evtimer_pending(ev, tv) event_pending(ev, EV_TIMEOUT, tv) #define evtimer_initialized(ev) ((ev)->ev_flags & EVLIST_INIT) -#define timeout_add(ev, tv) event_add(ev, tv) -#define timeout_set(ev, cb, arg) event_set(ev, -1, 0, cb, arg) -#define timeout_del(ev) event_del(ev) -#define timeout_pending(ev, tv) event_pending(ev, EV_TIMEOUT, tv) -#define timeout_initialized(ev) ((ev)->ev_flags & EVLIST_INIT) - #define signal_add(ev, tv) event_add(ev, tv) #define signal_set(ev, x, cb, arg) \ event_set(ev, x, EV_SIGNAL|EV_PERSIST, cb, arg) @@ -264,7 +262,8 @@ struct bufferevent *bufferevent_new(int fd, int bufferevent_base_set(struct event_base *base, struct bufferevent *bufev); int bufferevent_priority_set(struct bufferevent *bufev, int pri); void bufferevent_free(struct bufferevent *bufev); -int bufferevent_write(struct bufferevent *bufev, void *data, size_t size); +int bufferevent_write(struct bufferevent *bufev, + const void *data, size_t size); int bufferevent_write_buffer(struct bufferevent *bufev, struct evbuffer *buf); size_t bufferevent_read(struct bufferevent *bufev, void *data, size_t size); int bufferevent_enable(struct bufferevent *bufev, short event); @@ -292,7 +291,7 @@ int evbuffer_read(struct evbuffer *, int, int); u_char *evbuffer_find(struct evbuffer *, const u_char *, size_t); void evbuffer_setcb(struct evbuffer *, void (*)(struct evbuffer *, size_t, size_t, void *), void *); -/* +/* * Marshaling tagged data - We assume that all tags are inserted in their * numeric order - so that unknown tags will always be higher than the * known ones - and we can just ignore the end of an event buffer. diff --git a/libevent/evsignal.h b/libevent/evsignal.h index 7efbcabec89..6db8a057747 100644 --- a/libevent/evsignal.h +++ b/libevent/evsignal.h @@ -1,3 +1,5 @@ +/* $OpenBSD: evsignal.h,v 1.2 2004/04/28 06:53:12 brad Exp $ */ + /* * Copyright 2000-2002 Niels Provos * All rights reserved. diff --git a/libevent/kqueue.c b/libevent/kqueue.c index 059d94a0b4d..6f865f5006e 100644 --- a/libevent/kqueue.c +++ b/libevent/kqueue.c @@ -1,4 +1,4 @@ -/* $OpenBSD: kqueue.c,v 1.5 2002/07/10 14:41:31 art Exp $ */ +/* $OpenBSD: kqueue.c,v 1.23 2007/09/02 15:19:18 deraadt Exp $ */ /* * Copyright 2000-2002 Niels Provos @@ -97,14 +97,14 @@ kq_init(struct event_base *base) struct kqop *kqueueop; /* Disable kqueue when this environment variable is set */ - if (getenv("EVENT_NOKQUEUE")) + if (!issetugid() && getenv("EVENT_NOKQUEUE")) return (NULL); if (!(kqueueop = calloc(1, sizeof(struct kqop)))) return (NULL); /* Initalize the kernel queue */ - + if ((kq = kqueue()) == -1) { event_warn("kqueue"); free (kqueueop); @@ -114,12 +114,12 @@ kq_init(struct event_base *base) kqueueop->kq = kq; /* Initalize fields */ - kqueueop->changes = malloc(NEVENT * sizeof(struct kevent)); + kqueueop->changes = calloc(NEVENT, sizeof(struct kevent)); if (kqueueop->changes == NULL) { free (kqueueop); return (NULL); } - kqueueop->events = malloc(NEVENT * sizeof(struct kevent)); + kqueueop->events = calloc(NEVENT, sizeof(struct kevent)); if (kqueueop->events == NULL) { free (kqueueop->changes); free (kqueueop); @@ -131,7 +131,7 @@ kq_init(struct event_base *base) kqueueop->changes[0].ident = -1; kqueueop->changes[0].filter = EVFILT_READ; kqueueop->changes[0].flags = EV_ADD; - /* + /* * If kqueue works, then kevent will succeed, and it will * stick an error in events[0]. If kqueue is broken, then * kevent will fail. @@ -195,7 +195,7 @@ kq_insert(struct kqop *kqop, struct kevent *kev) memcpy(&kqop->changes[kqop->nchanges++], kev, sizeof(struct kevent)); event_debug(("%s: fd %d %s%s", - __func__, kev->ident, + __func__, kev->ident, kev->filter == EVFILT_READ ? "EVFILT_READ" : "EVFILT_WRITE", kev->flags == EV_DELETE ? " (del)" : "")); @@ -241,7 +241,7 @@ kq_dispatch(struct event_base *base, void *arg, struct timeval *tv) int which = 0; if (events[i].flags & EV_ERROR) { - /* + /* * Error messages that can happen, when a delete fails. * EBADF happens when the file discriptor has been * closed, @@ -301,7 +301,7 @@ kq_add(void *arg, struct event *ev) if (!(ev->ev_events & EV_PERSIST)) kev.flags |= EV_ONESHOT; kev.udata = PTR_TO_UDATA(ev); - + if (kq_insert(kqop, &kev) == -1) return (-1); @@ -324,7 +324,7 @@ kq_add(void *arg, struct event *ev) if (!(ev->ev_events & EV_PERSIST)) kev.flags |= EV_ONESHOT; kev.udata = PTR_TO_UDATA(ev); - + if (kq_insert(kqop, &kev) == -1) return (-1); @@ -339,7 +339,7 @@ kq_add(void *arg, struct event *ev) if (!(ev->ev_events & EV_PERSIST)) kev.flags |= EV_ONESHOT; kev.udata = PTR_TO_UDATA(ev); - + if (kq_insert(kqop, &kev) == -1) return (-1); @@ -365,7 +365,7 @@ kq_del(void *arg, struct event *ev) kev.ident = nsignal; kev.filter = EVFILT_SIGNAL; kev.flags = EV_DELETE; - + if (kq_insert(kqop, &kev) == -1) return (-1); @@ -381,7 +381,7 @@ kq_del(void *arg, struct event *ev) kev.ident = ev->ev_fd; kev.filter = EVFILT_READ; kev.flags = EV_DELETE; - + if (kq_insert(kqop, &kev) == -1) return (-1); @@ -393,7 +393,7 @@ kq_del(void *arg, struct event *ev) kev.ident = ev->ev_fd; kev.filter = EVFILT_WRITE; kev.flags = EV_DELETE; - + if (kq_insert(kqop, &kev) == -1) return (-1); diff --git a/libevent/log.c b/libevent/log.c index c9275e363fc..95898bd8c13 100644 --- a/libevent/log.c +++ b/libevent/log.c @@ -1,4 +1,4 @@ -/* $OpenBSD: err.c,v 1.2 2002/06/25 15:50:15 mickey Exp $ */ +/* $OpenBSD: log.c,v 1.4 2005/05/04 03:17:48 brad Exp $ */ /* * log.c @@ -102,7 +102,7 @@ void event_err(int eval, const char *fmt, ...) { va_list ap; - + va_start(ap, fmt); _warn_helper(_EVENT_LOG_ERR, errno, fmt, ap); va_end(ap); @@ -113,7 +113,7 @@ void event_warn(const char *fmt, ...) { va_list ap; - + va_start(ap, fmt); _warn_helper(_EVENT_LOG_WARN, errno, fmt, ap); va_end(ap); @@ -123,7 +123,7 @@ void event_errx(int eval, const char *fmt, ...) { va_list ap; - + va_start(ap, fmt); _warn_helper(_EVENT_LOG_ERR, -1, fmt, ap); va_end(ap); @@ -134,7 +134,7 @@ void event_warnx(const char *fmt, ...) { va_list ap; - + va_start(ap, fmt); _warn_helper(_EVENT_LOG_WARN, -1, fmt, ap); va_end(ap); @@ -144,7 +144,7 @@ void event_msgx(const char *fmt, ...) { va_list ap; - + va_start(ap, fmt); _warn_helper(_EVENT_LOG_MSG, -1, fmt, ap); va_end(ap); @@ -154,7 +154,7 @@ void _event_debugx(const char *fmt, ...) { va_list ap; - + va_start(ap, fmt); _warn_helper(_EVENT_LOG_DEBUG, -1, fmt, ap); va_end(ap); diff --git a/libevent/log.h b/libevent/log.h index 1f843cf984e..9acc219d181 100644 --- a/libevent/log.h +++ b/libevent/log.h @@ -1,3 +1,5 @@ +/* $OpenBSD: log.h,v 1.4 2007/03/19 15:12:49 millert Exp $ */ + /* * Copyright (c) 2000-2004 Niels Provos * All rights reserved. diff --git a/libevent/poll.c b/libevent/poll.c index 123d36a5602..b2565c293b5 100644 --- a/libevent/poll.c +++ b/libevent/poll.c @@ -1,4 +1,4 @@ -/* $OpenBSD: poll.c,v 1.2 2002/06/25 15:50:15 mickey Exp $ */ +/* $OpenBSD: poll.c,v 1.13 2006/11/26 15:24:34 brad Exp $ */ /* * Copyright 2000-2003 Niels Provos @@ -89,7 +89,7 @@ poll_init(struct event_base *base) struct pollop *pollop; /* Disable poll when this environment variable is set */ - if (getenv("EVENT_NOPOLL")) + if (!issetugid() && getenv("EVENT_NOPOLL")) return (NULL); if (!(pollop = calloc(1, sizeof(struct pollop)))) @@ -179,6 +179,7 @@ poll_dispatch(struct event_base *base, void *arg, struct timeval *tv) for (i = 0; i < nfds; i++) { int what = pop->event_set[i].revents; struct event *r_ev = NULL, *w_ev = NULL; + if (!what) continue; @@ -356,7 +357,7 @@ poll_del(void *arg, struct event *ev) --pop->nfds; if (i != pop->nfds) { - /* + /* * Shift the last pollfd down into the now-unoccupied * position. */ diff --git a/libevent/select.c b/libevent/select.c index d645f1a3703..2cc54ce8aef 100644 --- a/libevent/select.c +++ b/libevent/select.c @@ -1,4 +1,4 @@ -/* $OpenBSD: select.c,v 1.2 2002/06/25 15:50:15 mickey Exp $ */ +/* $OpenBSD: select.c,v 1.13 2007/03/19 15:12:49 millert Exp $ */ /* * Copyright 2000-2002 Niels Provos @@ -96,7 +96,7 @@ select_init(struct event_base *base) struct selectop *sop; /* Disable select when this environment variable is set */ - if (getenv("EVENT_NOSELECT")) + if (!issetugid() && getenv("EVENT_NOSELECT")) return (NULL); if (!(sop = calloc(1, sizeof(struct selectop)))) diff --git a/libevent/signal.c b/libevent/signal.c index 6c0953d9e12..2364821848f 100644 --- a/libevent/signal.c +++ b/libevent/signal.c @@ -1,4 +1,4 @@ -/* $OpenBSD: select.c,v 1.2 2002/06/25 15:50:15 mickey Exp $ */ +/* $OpenBSD: signal.c,v 1.11 2007/03/19 15:12:49 millert Exp $ */ /* * Copyright 2000-2002 Niels Provos @@ -85,7 +85,7 @@ evsignal_cb(int fd, short what, void *arg) void evsignal_init(struct event_base *base) { - /* + /* * Our signal handler is going to write to one end of the socket * pair to wake up our event loop. The event loop then scans for * signals that got delivered. diff --git a/man/pf.4 b/man/pf.4 index ab9ad88f82c..8acf5e0610b 100644 --- a/man/pf.4 +++ b/man/pf.4 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pf.4,v 1.60 2007/12/02 12:08:04 pascoe Exp $ +.\" $OpenBSD: pf.4,v 1.61 2008/09/04 13:50:37 jmc Exp $ .\" .\" Copyright (C) 2001, Kjell Wooding. All rights reserved. .\" @@ -26,7 +26,7 @@ .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF .\" SUCH DAMAGE. .\" -.Dd $Mdocdate: May 31 2007 $ +.Dd $Mdocdate: September 4 2008 $ .Dt PF 4 .Os .Sh NAME @@ -1050,12 +1050,14 @@ internal interface description. The filtering process is the same as for .Dv DIOCIGETIFACES . .Bd -literal -#define PFI_IFLAG_SKIP 0x0100 /* skip filtering on interface */ +#define PFI_IFLAG_SKIP 0x0100 /* skip filtering on interface */ .Ed .It Dv DIOCCLRIFFLAG Fa "struct pfioc_iface *io" Works as .Dv DIOCSETIFFLAG above but clears the flags. +.It Dv DIOCKILLSRCNODES Fa "struct pfioc_iface *io" +Explicitly remove source tracking nodes. .El .Sh FILES .Bl -tag -width /dev/pf -compact @@ -1133,6 +1135,7 @@ main(int argc, char *argv[]) .Xr ioctl 2 , .Xr bridge 4 , .Xr pflog 4 , +.Xr pflow 4 , .Xr pfsync 4 , .Xr pfctl 8 , .Xr altq 9 diff --git a/man/pf.conf.5 b/man/pf.conf.5 index 5e49a3c2493..3adc6395f84 100644 --- a/man/pf.conf.5 +++ b/man/pf.conf.5 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pf.conf.5,v 1.402 2008/06/11 07:21:00 jmc Exp $ +.\" $OpenBSD: pf.conf.5,v 1.405 2008/10/02 12:36:32 henning Exp $ .\" .\" Copyright (c) 2002, Daniel Hartmeier .\" All rights reserved. @@ -27,7 +27,7 @@ .\" ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE .\" POSSIBILITY OF SUCH DAMAGE. .\" -.Dd $Mdocdate: June 10 2008 $ +.Dd $Mdocdate: October 2 2008 $ .Dt PF.CONF 5 .Os .Sh NAME @@ -517,6 +517,16 @@ For example: .Bd -literal -offset indent set state-policy if-bound .Ed +.It Ar set state-defaults +The +.Ar state-defaults +option sets the state options for states created from rules +without an explicit +.Ar keep state . +For example: +.Bd -literal -offset indent +set state-defaults pflow, no-sync +.Ed .It Ar set hostid The 32-bit .Ar hostid @@ -901,7 +911,7 @@ Defines a list of subqueues to create on an interface. .El .Pp In the following example, the interface dc0 -should queue up to 5 Mbit/s in four second-level queues using +should queue up to 5Mbps in four second-level queues using Class Based Queueing. Those four queues will be shown in a later example. .Bd -literal -offset indent @@ -1488,7 +1498,7 @@ Translates to the network(s) attached to the interface. .It Ar :broadcast Translates to the interface's broadcast address(es). .It Ar :peer -Translates to the point to point interface's peer address(es). +Translates to the point-to-point interface's peer address(es). .It Ar :0 Do not include interface aliases. .El @@ -2098,6 +2108,10 @@ easier. This is intended to be used in situations where one does not see all packets of a connection, e.g. in asymmetric routing situations. Cannot be used with modulate or synproxy state. +.It Ar pflow +States created by this rule are exported on the +.Xr pflow 4 +interface. .El .Pp Multiple options can be specified, separated by commas: @@ -2821,6 +2835,7 @@ option = "set" ( [ "timeout" ( timeout | "{" timeout-list "}" ) ] | [ "loginterface" ( interface-name | "none" ) ] | [ "block-policy" ( "drop" | "return" ) ] | [ "state-policy" ( "if-bound" | "floating" ) ] + [ "state-defaults" state-opts ] [ "require-order" ( "yes" | "no" ) ] [ "fingerprints" filename ] | [ "skip on" ifspec ] | @@ -2963,7 +2978,7 @@ tos = ( "lowdelay" | "throughput" | "reliability" | [ "0x" ] number ) state-opts = state-opt [ [ "," ] state-opts ] -state-opt = ( "max" number | "no-sync" | timeout | sloppy | +state-opt = ( "max" number | "no-sync" | timeout | "sloppy" | "pflow" | "source-track" [ ( "rule" | "global" ) ] | "max-src-nodes" number | "max-src-states" number | "max-src-conn" number | @@ -3026,6 +3041,7 @@ Service name database. .Xr ip 4 , .Xr ip6 4 , .Xr pf 4 , +.Xr pflow 4 , .Xr pfsync 4 , .Xr route 4 , .Xr tcp 4 , diff --git a/man/pf.os.5 b/man/pf.os.5 index 7ee63ce52f4..0920f91acfc 100644 --- a/man/pf.os.5 +++ b/man/pf.os.5 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pf.os.5,v 1.8 2007/05/31 19:19:58 jmc Exp $ +.\" $OpenBSD: pf.os.5,v 1.7 2005/11/16 20:07:18 stevesk Exp $ .\" .\" Copyright (c) 2003 Mike Frantzen .\" diff --git a/man/pflog.4 b/man/pflog.4 index 1b42a83f437..cd5145e978c 100644 --- a/man/pflog.4 +++ b/man/pflog.4 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pflog.4,v 1.10 2007/05/31 19:19:51 jmc Exp $ +.\" $OpenBSD: pflog.4,v 1.9 2006/10/25 12:51:31 jmc Exp $ .\" .\" Copyright (c) 2001 Tobias Weingartner .\" All rights reserved. diff --git a/man/pflow.4 b/man/pflow.4 new file mode 100644 index 00000000000..9f6dbe33129 --- /dev/null +++ b/man/pflow.4 @@ -0,0 +1,113 @@ +.\" $OpenBSD: pflow.4,v 1.8 2008/10/28 16:55:37 gollo Exp $ +.\" +.\" Copyright (c) 2008 Henning Brauer +.\" Copyright (c) 2008 Joerg Goltermann +.\" +.\" Permission to use, copy, modify, and distribute this software for any +.\" purpose with or without fee is hereby granted, provided that the above +.\" copyright notice and this permission notice appear in all copies. +.\" +.\" THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALLWARRANTIES +.\" WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +.\" MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BELIABLE FOR +.\" ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +.\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +.\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISINGOUT OF +.\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. +.\" +.Dd $Mdocdate: October 28 2008 $ +.Dt PFLOW 4 +.Os +.Sh NAME +.Nm pflow +.Nd kernel interface for pflow data export +.Sh SYNOPSIS +.Cd "pseudo-device pflow" +.Sh DESCRIPTION +The +.Nm +interface is a pseudo-device which exports +.Nm +accounting data from the kernel using +.Xr udp 4 +packets. +.Nm +is compatible with netflow v5. +The data is extracted from the +.Xr pf 4 +state table. +.Pp +Multiple +.Nm +interfaces can be created at runtime using the +.Ic ifconfig pflow Ns Ar N Ic create +command. +Each interface must be configured with a flow receiver IP address and +port number. +.Pp +Only states created by a rule marked with the +.Ar pflow +keyword are exported by the +.Nm +interface. +.Pp +The +.Nm +interface will attempt to export multiple +.Nm +records in one +UDP packet, but will not hold a record for longer than 30 seconds. +The packet size and thus the maximum number of flows is controlled by the +.Cm mtu +parameter of +.Xr ifconfig 8 . +.Pp +Each packet seen on this interface has one header and a variable number of +flows. +The header indicates the version of the protocol, number of +flows in the packet, a unique sequence number, system time, and an engine +ID and type. +Header and flow structs are defined in +.Aq Pa net/if_pflow.h . +.Pp +There is a one-to-one correspondence between packets seen by +.Xr bpf 4 +on the +.Nm +interface and packets sent out to the flow receiver. +That is, a packet with 30 flows on +.Nm +means that the same 30 flows were sent out to the receiver. +.Pp +The +.Nm +source and destination addresses are controlled by +.Xr ifconfig 8 . +.Cm flowsrc +is the sender IP address of the UDP packet which can be used +to identify the source of the data on the +.Nm +collector. +.Cm flowdst +defines the collector IP address and the port. +The +.Cm flowdst +IP address and port must be defined to enable the export of flows. +.Pp +For example, the following command sets 10.0.0.1 as the source +and 10.0.0.2:1234 as destination: +.Bd -literal -offset indent +# ifconfig pflow0 flowsrc 10.0.0.1 flowdst 10.0.0.2:1234 +.Ed +.Sh SEE ALSO +.Xr netintro 4 , +.Xr pf 4 , +.Xr udp 4 , +.Xr pf.conf 5 , +.Xr ifconfig 8 , +.Xr tcpdump 8 +.Sh HISTORY +The +.Nm +device first appeared in +.Ox 4.5 . diff --git a/man/pfsync.4 b/man/pfsync.4 index d10131457ad..da64eaa9430 100644 --- a/man/pfsync.4 +++ b/man/pfsync.4 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pfsync.4,v 1.27 2008/06/03 19:51:02 jmc Exp $ +.\" $OpenBSD: pfsync.4,v 1.26 2007/09/20 20:50:07 mpf Exp $ .\" .\" Copyright (c) 2002 Michael Shalayeff .\" Copyright (c) 2003-2004 Ryan McBride @@ -29,7 +29,7 @@ .Os .Sh NAME .Nm pfsync -.Nd packet filter state table logging interface +.Nd packet filter state table sychronisation interface .Sh SYNOPSIS .Cd "pseudo-device pfsync" .Sh DESCRIPTION @@ -45,18 +45,18 @@ on the interface. If configured with a physical synchronisation interface, .Nm -will also send state changes out on that interface using IP multicast, +will also send state changes out on that interface, and insert state changes received on that interface from other systems into the state table. .Pp By default, all local changes to the state table are exposed via .Nm . -However, state changes from packets received by +State changes from packets received by .Nm over the network are not rebroadcast. -States created by a rule marked with the +Updates to states created by a rule marked with the .Ar no-sync -keyword are omitted from the +keyword are ignored by the .Nm interface (see .Xr pf.conf 5 @@ -64,33 +64,19 @@ for details). .Pp The .Nm -interface will attempt to collapse multiple updates of the same -state into one message where possible. -The maximum number of times this can be done before the update is sent out -is controlled by the +interface will attempt to collapse multiple state updates into a single +packet where possible. +The maximum number of times a single state can be updated before a +.Nm +packet will be sent out is controlled by the .Ar maxupd parameter to ifconfig (see .Xr ifconfig 8 and the example below for more details). -.Pp -Each packet retrieved on this interface has a header associated -with it of length -.Dv PFSYNC_HDRLEN . -The header indicates the version of the protocol, address family, -action taken on the following states, and the number of state -table entries attached in this packet. -This structure is defined in -.Aq Pa net/if_pfsync.h -as: -.Bd -literal -offset indent -struct pfsync_header { - u_int8_t version; - u_int8_t af; - u_int8_t action; - u_int8_t count; -}; -.Ed +The sending out of a +.Nm +packet will be delayed by a maximum of one second. .Sh NETWORK SYNCHRONISATION States can be synchronised between two or more firewalls using this interface, by specifying a synchronisation interface using @@ -102,14 +88,15 @@ interface: .Ed .Pp By default, state change messages are sent out on the synchronisation -interface using IP multicast packets. -The protocol is IP protocol 240, PFSYNC, and the multicast group -used is 224.0.0.240. -When a peer address is specified using the +interface using IP multicast packets to the 244.0.0.240 group address. +An alternative destination address for +.Nm +packets can be specified using the .Ic syncpeer -keyword, the peer address is used as a destination for the pfsync traffic, -and the traffic can then be protected using -.Xr ipsec 4 . +keyword. +This can be used in combination with +.Xr ipsec 4 +to protect the synchronisation traffic. In such a configuration, the syncdev should be set to the .Xr enc 4 interface, as this is where the traffic arrives when it is decapsulated, @@ -125,27 +112,15 @@ Either run the pfsync protocol on a trusted network \- ideally a network dedicated to pfsync messages such as a crossover cable between two firewalls, or specify a peer address and protect the traffic with .Xr ipsec 4 . -.Pp -There is a one-to-one correspondence between packets seen by -.Xr bpf 4 -on the -.Nm -interface, and packets sent out on the synchronisation interface, i.e.\& -a packet with 4 state deletion messages on -.Nm -means that the same 4 deletions were sent out on the synchronisation -interface. -However, the actual packet contents may differ as the messages -sent over the network are "compressed" where possible, containing -only the necessary information. .Sh EXAMPLES .Nm and .Xr carp 4 can be used together to provide automatic failover of a pair of firewalls configured in parallel. -One firewall handles all traffic \- if it dies or -is shut down, the second firewall takes over automatically. +One firewall will handle all traffic until it dies, is shut down, or is +manually demoted, at which point the second firewall will take over +automatically. .Pp Both firewalls in this example have three .Xr sis 4 @@ -203,8 +178,8 @@ pass quick on { sis2 } proto pfsync keep state (no-sync) pass on { sis0 sis1 } proto carp keep state (no-sync) .Ed .Pp -If it is preferable that one firewall handle the traffic, -the +It is preferable that one firewall handle the forwarding of all the traffic, +therefore the .Ar advskew on the backup firewall's .Xr carp 4 @@ -243,3 +218,11 @@ The .Nm device first appeared in .Ox 3.3 . +.Pp +The +.Nm +protocol and kernel implementation were significantly modified between +.Ox 4.4 +and +.Ox 4.5 . +The two protocols are incompatible and will not interoperate. diff --git a/pfctl/Makefile b/pfctl/Makefile index df74f88c63f..b0a24648053 100644 --- a/pfctl/Makefile +++ b/pfctl/Makefile @@ -1,4 +1,4 @@ -# $OpenBSD: Makefile,v 1.19 2006/12/24 18:52:43 miod Exp $ +# $OpenBSD: Makefile,v 1.18 2006/10/28 14:29:05 mcbride Exp $ PROG= pfctl SRCS= pfctl.c parse.y pfctl_parser.c pf_print_state.c pfctl_altq.c diff --git a/pfctl/parse.y b/pfctl/parse.y index 55c3a755373..e4c47d1ac7f 100644 --- a/pfctl/parse.y +++ b/pfctl/parse.y @@ -1,4 +1,4 @@ -/* $OpenBSD: parse.y,v 1.549 2008/07/03 16:09:34 deraadt Exp $ */ +/* $OpenBSD: parse.y,v 1.554 2008/10/17 12:59:53 henning Exp $ */ /* * Copyright (c) 2001 Markus Friedl. All rights reserved. @@ -153,7 +153,8 @@ enum { PF_STATE_OPT_MAX, PF_STATE_OPT_NOSYNC, PF_STATE_OPT_SRCTRACK, PF_STATE_OPT_MAX_SRC_STATES, PF_STATE_OPT_MAX_SRC_CONN, PF_STATE_OPT_MAX_SRC_CONN_RATE, PF_STATE_OPT_MAX_SRC_NODES, PF_STATE_OPT_OVERLOAD, PF_STATE_OPT_STATELOCK, - PF_STATE_OPT_TIMEOUT, PF_STATE_OPT_SLOPPY }; + PF_STATE_OPT_TIMEOUT, PF_STATE_OPT_SLOPPY, + PF_STATE_OPT_PFLOW }; enum { PF_SRCTRACK_NONE, PF_SRCTRACK, PF_SRCTRACK_GLOBAL, PF_SRCTRACK_RULE }; @@ -293,7 +294,8 @@ struct pool_opts { } pool_opts; -struct node_hfsc_opts hfsc_opts; +struct node_hfsc_opts hfsc_opts; +struct node_state_opt *keep_state_defaults = NULL; int disallow_table(struct node_host *, const char *); int disallow_urpf_failed(struct node_host *, const char *); @@ -442,8 +444,8 @@ int parseport(char *, struct range *r, int); %token QUEUE PRIORITY QLIMIT RTABLE %token LOAD RULESET_OPTIMIZATION %token STICKYADDRESS MAXSRCSTATES MAXSRCNODES SOURCETRACK GLOBAL RULE -%token MAXSRCCONN MAXSRCCONNRATE OVERLOAD FLUSH SLOPPY -%token TAGGED TAG IFBOUND FLOATING STATEPOLICY ROUTE SETTOS +%token MAXSRCCONN MAXSRCCONNRATE OVERLOAD FLUSH SLOPPY PFLOW +%token TAGGED TAG IFBOUND FLOATING STATEPOLICY STATEDEFAULTS ROUTE SETTOS %token DIVERTTO DIVERTREPLY %token STRING %token NUMBER @@ -552,7 +554,7 @@ optimizer : string { else if (!strcmp($1, "profile")) $$ = PF_OPTIMIZE_BASIC | PF_OPTIMIZE_PROFILE; else { - yyerror("unknown ruleset-optimization %s", $$); + yyerror("unknown ruleset-optimization %s", $1); YYERROR; } } @@ -670,6 +672,13 @@ option : SET OPTIMIZATION STRING { YYERROR; } } + | SET STATEDEFAULTS state_opt_list { + if (keep_state_defaults != NULL) { + yyerror("cannot redefine state-defaults"); + YYERROR; + } + keep_state_defaults = $3; + } ; stringall : STRING { $$ = $1; } @@ -1245,6 +1254,7 @@ antispoof : ANTISPOOF logquick antispoof_ifspc af antispoof_opts { r.action = PF_DROP; r.direction = PF_IN; r.log = $2.log; + r.logif = $2.logif; r.quick = $2.quick; r.af = $4; if (rule_label(&r, $5.label)) @@ -1265,7 +1275,7 @@ antispoof : ANTISPOOF logquick antispoof_ifspc af antispoof_opts { } ; -antispoof_ifspc : FOR antispoof_if { $$ = $2; } +antispoof_ifspc : FOR antispoof_if { $$ = $2; } | FOR '{' optnl antispoof_iflst '}' { $$ = $4; } ; @@ -1277,8 +1287,8 @@ antispoof_iflst : antispoof_if optnl { $$ = $1; } } ; -antispoof_if : if_item { $$ = $1; } - | '(' if_item ')' { +antispoof_if : if_item { $$ = $1; } + | '(' if_item ')' { $2->dynamic = 1; $$ = $2; } @@ -1831,6 +1841,7 @@ pfrule : action dir logquick interface route af proto fromto int srctrack = 0; int statelock = 0; int adaptive = 0; + int defaults = 0; if (check_rulestate(PFCTL_STATE_FILTER)) YYERROR; @@ -1913,13 +1924,16 @@ pfrule : action dir logquick interface route af proto fromto r.tos = $9.tos; r.keep_state = $9.keep.action; + o = $9.keep.options; /* 'keep state' by default on pass rules. */ if (!r.keep_state && !r.action && - !($9.marker & FOM_KEEP)) + !($9.marker & FOM_KEEP)) { r.keep_state = PF_STATE_NORMAL; + o = keep_state_defaults; + defaults = 1; + } - o = $9.keep.options; while (o) { struct node_state_opt *p = o; @@ -2060,6 +2074,15 @@ pfrule : action dir logquick interface route af proto fromto } r.rule_flag |= PFRULE_STATESLOPPY; break; + case PF_STATE_OPT_PFLOW: + if (r.rule_flag & PFRULE_PFLOW) { + yyerror("state pflow " + "option: multiple " + "definitions"); + YYERROR; + } + r.rule_flag |= PFRULE_PFLOW; + break; case PF_STATE_OPT_TIMEOUT: if (o->data.timeout.number == PFTM_ADAPTIVE_START || @@ -2077,7 +2100,8 @@ pfrule : action dir logquick interface route af proto fromto o->data.timeout.seconds; } o = o->next; - free(p); + if (!defaults) + free(p); } /* 'flags S/SA' by default on stateful rules */ @@ -3540,6 +3564,14 @@ state_opt_item : MAXIMUM NUMBER { $$->next = NULL; $$->tail = $$; } + | PFLOW { + $$ = calloc(1, sizeof(struct node_state_opt)); + if ($$ == NULL) + err(1, "state_opt_item: calloc"); + $$->type = PF_STATE_OPT_PFLOW; + $$->next = NULL; + $$->tail = $$; + } | STRING NUMBER { int i; @@ -5255,6 +5287,7 @@ lookup(char *s) { "out", OUT}, { "overload", OVERLOAD}, { "pass", PASS}, + { "pflow", PFLOW}, { "port", PORT}, { "priority", PRIORITY}, { "priq", PRIQ}, @@ -5289,6 +5322,7 @@ lookup(char *s) { "source-hash", SOURCEHASH}, { "source-track", SOURCETRACK}, { "state", STATE}, + { "state-defaults", STATEDEFAULTS}, { "state-policy", STATEPOLICY}, { "static-port", STATICPORT}, { "sticky-address", STICKYADDRESS}, @@ -5397,11 +5431,13 @@ findeol(void) int c; parsebuf = NULL; - pushback_index = 0; /* skip to either EOF or the first real EOL */ while (1) { - c = lgetc(0); + if (pushback_index) + c = pushback_buffer[--pushback_index]; + else + c = lgetc(0); if (c == '\n') { file->lineno++; break; diff --git a/pfctl/pf_print_state.c b/pfctl/pf_print_state.c index e95f2b04a06..7996127f8c5 100644 --- a/pfctl/pf_print_state.c +++ b/pfctl/pf_print_state.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pf_print_state.c,v 1.51 2008/06/29 08:42:15 mcbride Exp $ */ +/* $OpenBSD: pf_print_state.c,v 1.52 2008/08/12 16:40:18 david Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -306,7 +306,7 @@ print_state(struct pfsync_state *s, int opts) printf(" age %.2u:%.2u:%.2u", creation, min, sec); sec = expire % 60; expire /= 60; - min = s->expire % 60; + min = expire % 60; expire /= 60; printf(", expires in %.2u:%.2u:%.2u", expire, min, sec); @@ -325,6 +325,8 @@ print_state(struct pfsync_state *s, int opts) printf(", rule %u", ntohl(s->rule)); if (s->state_flags & PFSTATE_SLOPPY) printf(", sloppy"); + if (s->state_flags & PFSTATE_PFLOW) + printf(", pflow"); if (s->sync_flags & PFSYNC_FLAG_SRCNODE) printf(", source-track"); if (s->sync_flags & PFSYNC_FLAG_NATSRCNODE) diff --git a/pfctl/pfctl.8 b/pfctl/pfctl.8 index 9ce34ce4112..f483e65b148 100644 --- a/pfctl/pfctl.8 +++ b/pfctl/pfctl.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: pfctl.8,v 1.139 2008/06/11 07:23:36 jmc Exp $ +.\" $OpenBSD: pfctl.8,v 1.138 2008/06/10 20:55:02 mcbride Exp $ .\" .\" Copyright (c) 2001 Kjell Wooding. All rights reserved. .\" diff --git a/pfctl/pfctl.c b/pfctl/pfctl.c index f01b6a92717..12dab0c3304 100644 --- a/pfctl/pfctl.c +++ b/pfctl/pfctl.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl.c,v 1.277 2008/07/24 10:52:43 henning Exp $ */ +/* $OpenBSD: pfctl.c,v 1.278 2008/08/31 20:18:17 jmc Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -230,10 +230,11 @@ usage(void) fprintf(stderr, "usage: %s [-AdeghmNnOqRrvz] ", __progname); fprintf(stderr, "[-a anchor] [-D macro=value] [-F modifier]\n"); - fprintf(stderr, "\t[-f file] [-i interface] [-K host | network] "); - fprintf(stderr, "[-k host | network | label | id]\n"); - fprintf(stderr, "\t[-o level] [-p device] [-s modifier]\n"); - fprintf(stderr, "\t[-t table -T command [address ...]] [-x level]\n"); + fprintf(stderr, "\t[-f file] [-i interface] [-K host | network]\n"); + fprintf(stderr, "\t[-k host | network | label | id] "); + fprintf(stderr, "[-o level] [-p device]\n"); + fprintf(stderr, "\t[-s modifier] "); + fprintf(stderr, "[-t table -T command [address ...]] [-x level]\n"); exit(1); } diff --git a/pfctl/pfctl.h b/pfctl/pfctl.h index f9db55072dd..918999cc166 100644 --- a/pfctl/pfctl.h +++ b/pfctl/pfctl.h @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl.h,v 1.43 2008/05/29 01:00:53 mcbride Exp $ */ +/* $OpenBSD: pfctl.h,v 1.42 2007/12/05 12:01:47 chl Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier diff --git a/pfctl/pfctl_altq.c b/pfctl/pfctl_altq.c index 0a174e5f46b..c3cd9bf3ac5 100644 --- a/pfctl/pfctl_altq.c +++ b/pfctl/pfctl_altq.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_altq.c,v 1.94 2008/07/25 17:43:44 martynas Exp $ */ +/* $OpenBSD: pfctl_altq.c,v 1.93 2007/10/15 02:16:35 deraadt Exp $ */ /* * Copyright (c) 2002 diff --git a/pfctl/pfctl_optimize.c b/pfctl/pfctl_optimize.c index bbed611d2fe..08cfcf7295c 100644 --- a/pfctl/pfctl_optimize.c +++ b/pfctl/pfctl_optimize.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_optimize.c,v 1.18 2008/05/07 06:23:30 markus Exp $ */ +/* $OpenBSD: pfctl_optimize.c,v 1.17 2008/05/06 03:45:21 mpf Exp $ */ /* * Copyright (c) 2004 Mike Frantzen diff --git a/pfctl/pfctl_osfp.c b/pfctl/pfctl_osfp.c index 7018d6cd365..df789811ddb 100644 --- a/pfctl/pfctl_osfp.c +++ b/pfctl/pfctl_osfp.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_osfp.c,v 1.15 2006/12/13 05:10:15 itojun Exp $ */ +/* $OpenBSD: pfctl_osfp.c,v 1.14 2006/04/08 02:13:14 ray Exp $ */ /* * Copyright (c) 2003 Mike Frantzen diff --git a/pfctl/pfctl_parser.c b/pfctl/pfctl_parser.c index 7368dbe7d3c..a9141840fb8 100644 --- a/pfctl/pfctl_parser.c +++ b/pfctl/pfctl_parser.c @@ -934,6 +934,12 @@ print_rule(struct pf_rule *r, const char *anchor_call, int verbose) printf("sloppy"); opts = 0; } + if (r->rule_flag & PFRULE_PFLOW) { + if (!opts) + printf(", "); + printf("pflow"); + opts = 0; + } for (i = 0; i < PFTM_MAX; ++i) if (r->timeout[i]) { int j; diff --git a/pfctl/pfctl_parser.h b/pfctl/pfctl_parser.h index 97b0325ddc7..8e8f3c3549e 100644 --- a/pfctl/pfctl_parser.h +++ b/pfctl/pfctl_parser.h @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_parser.h,v 1.87 2007/10/13 16:35:18 deraadt Exp $ */ +/* $OpenBSD: pfctl_parser.h,v 1.86 2006/10/31 23:46:25 mcbride Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier diff --git a/pfctl/pfctl_qstats.c b/pfctl/pfctl_qstats.c index ba0c18aef5b..22f0f6bf256 100644 --- a/pfctl/pfctl_qstats.c +++ b/pfctl/pfctl_qstats.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_qstats.c,v 1.31 2007/10/15 02:16:35 deraadt Exp $ */ +/* $OpenBSD: pfctl_qstats.c,v 1.30 2004/04/27 21:47:32 kjc Exp $ */ /* * Copyright (c) Henning Brauer diff --git a/pfctl/pfctl_radix.c b/pfctl/pfctl_radix.c index becd0305b83..585c5bd3342 100644 --- a/pfctl/pfctl_radix.c +++ b/pfctl/pfctl_radix.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_radix.c,v 1.28 2007/12/05 12:01:47 chl Exp $ */ +/* $OpenBSD: pfctl_radix.c,v 1.27 2005/05/21 21:03:58 henning Exp $ */ /* * Copyright (c) 2002 Cedric Berger diff --git a/pfctl/pfctl_table.c b/pfctl/pfctl_table.c index fa4ae6a6e18..a9da9e66d27 100644 --- a/pfctl/pfctl_table.c +++ b/pfctl/pfctl_table.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pfctl_table.c,v 1.68 2008/06/21 10:34:08 mcbride Exp $ */ +/* $OpenBSD: pfctl_table.c,v 1.67 2008/06/10 20:55:02 mcbride Exp $ */ /* * Copyright (c) 2002 Cedric Berger diff --git a/pflogd/Makefile b/pflogd/Makefile index 377cad99635..e5383e35f6c 100644 --- a/pflogd/Makefile +++ b/pflogd/Makefile @@ -1,4 +1,4 @@ -# $OpenBSD: Makefile,v 1.7 2006/11/26 11:31:08 deraadt Exp $ +# $OpenBSD: Makefile,v 1.6 2003/11/20 23:23:09 avsm Exp $ CFLAGS+=-Wall -Wmissing-prototypes -Wshadow LDADD+= -lpcap -lutil diff --git a/pflogd/pflogd.8 b/pflogd/pflogd.8 index e16f866ea85..783559e0943 100644 --- a/pflogd/pflogd.8 +++ b/pflogd/pflogd.8 @@ -24,7 +24,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.Dd $Mdocdate: May 31 2007 $ +.Dd $Mdocdate: January 14 2008 $ .Dt PFLOGD 8 .Os .Sh NAME @@ -95,6 +95,13 @@ or a .Dv SIGALRM is received. .Pp +.Nm +will also log the pcap statistics for the +.Xr pflog 4 +interface to syslog when a +.Dv SIGUSR1 +is received. +.Pp The options are as follows: .Bl -tag -width Ds .It Fl D diff --git a/pflogd/pflogd.c b/pflogd/pflogd.c index cd7a273924a..302635be21f 100644 --- a/pflogd/pflogd.c +++ b/pflogd/pflogd.c @@ -58,7 +58,7 @@ int Debug = 0; static int snaplen = DEF_SNAPLEN; static int cur_snaplen = DEF_SNAPLEN; -volatile sig_atomic_t gotsig_close, gotsig_alrm, gotsig_hup; +volatile sig_atomic_t gotsig_close, gotsig_alrm, gotsig_hup, gotsig_usr1; char *filename = PFLOGD_LOG_FILE; char *interface = PFLOGD_DEFAULT_IF; @@ -72,6 +72,7 @@ unsigned int delay = FLUSH_DELAY; char *copy_argv(char * const *); void dump_packet(u_char *, const struct pcap_pkthdr *, const u_char *); void dump_packet_nobuf(u_char *, const struct pcap_pkthdr *, const u_char *); +void log_pcap_stats(void); int flush_buffer(FILE *); int if_exists(char *); int init_pcap(void); @@ -82,6 +83,7 @@ int scan_dump(FILE *, off_t); int set_snaplen(int); void set_suspended(int); void sig_alrm(int); +void sig_usr1(int); void sig_close(int); void sig_hup(int); void usage(void); @@ -178,6 +180,12 @@ sig_alrm(int sig) gotsig_alrm = 1; } +void +sig_usr1(int sig) +{ + gotsig_usr1 = 1; +} + void set_pcap_filter(void) { @@ -550,10 +558,21 @@ dump_packet(u_char *user, const struct pcap_pkthdr *h, const u_char *sp) return; } +void +log_pcap_stats(void) +{ + struct pcap_stat pstat; + if (pcap_stats(hpcap, &pstat) < 0) + logmsg(LOG_WARNING, "Reading stats: %s", pcap_geterr(hpcap)); + else + logmsg(LOG_NOTICE, + "%u packets received, %u/%u dropped (kernel/pflogd)", + pstat.ps_recv, pstat.ps_drop, packets_dropped); +} + int main(int argc, char **argv) { - struct pcap_stat pstat; int ch, np, ret, Xflag = 0; pcap_handler phandler = dump_packet; const char *errstr = NULL; @@ -648,6 +667,7 @@ main(int argc, char **argv) signal(SIGINT, sig_close); signal(SIGQUIT, sig_close); signal(SIGALRM, sig_alrm); + signal(SIGUSR1, sig_usr1); signal(SIGHUP, sig_hup); alarm(delay); @@ -703,6 +723,11 @@ main(int argc, char **argv) gotsig_alrm = 0; alarm(delay); } + + if (gotsig_usr1) { + log_pcap_stats(); + gotsig_usr1 = 0; + } } logmsg(LOG_NOTICE, "Exiting"); @@ -712,13 +737,7 @@ main(int argc, char **argv) } purge_buffer(); - if (pcap_stats(hpcap, &pstat) < 0) - logmsg(LOG_WARNING, "Reading stats: %s", pcap_geterr(hpcap)); - else - logmsg(LOG_NOTICE, - "%u packets received, %u/%u dropped (kernel/pflogd)", - pstat.ps_recv, pstat.ps_drop, packets_dropped); - + log_pcap_stats(); pcap_close(hpcap); if (!Debug) closelog(); diff --git a/pflogd/pflogd.h b/pflogd/pflogd.h index 596e6969261..967f44a24af 100644 --- a/pflogd/pflogd.h +++ b/pflogd/pflogd.h @@ -1,4 +1,4 @@ -/* $OpenBSD: pflogd.h,v 1.3 2006/01/15 16:38:04 canacar Exp $ */ +/* $OpenBSD: pflogd.h,v 1.2 2004/01/15 20:15:14 canacar Exp $ */ /* * Copyright (c) 2003 Can Erkin Acar diff --git a/pflogd/privsep.c b/pflogd/privsep.c index 1139cb40f96..bba6b868f72 100644 --- a/pflogd/privsep.c +++ b/pflogd/privsep.c @@ -1,4 +1,4 @@ -/* $OpenBSD: privsep.c,v 1.16 2006/10/25 20:55:04 moritz Exp $ */ +/* $OpenBSD: privsep.c,v 1.15 2006/03/06 10:45:56 djm Exp $ */ /* * Copyright (c) 2003 Can Erkin Acar diff --git a/pflogd/privsep_fdpass.c b/pflogd/privsep_fdpass.c index 0e6c3c4c1e8..ed56c0b6f4f 100644 --- a/pflogd/privsep_fdpass.c +++ b/pflogd/privsep_fdpass.c @@ -1,4 +1,4 @@ -/* $OpenBSD: privsep_fdpass.c,v 1.5 2008/03/24 16:11:08 deraadt Exp $ */ +/* $OpenBSD: privsep_fdpass.c,v 1.4 2008/03/15 16:19:02 deraadt Exp $ */ /* * Copyright 2001 Niels Provos diff --git a/tftp-proxy/Makefile b/tftp-proxy/Makefile index b5f4eefc089..7f22f10b0d2 100644 --- a/tftp-proxy/Makefile +++ b/tftp-proxy/Makefile @@ -1,4 +1,4 @@ -# $OpenBSD: Makefile,v 1.1 2005/12/28 19:07:07 jcs Exp $ +# $OpenBSD$ PROG= tftp-proxy SRCS= tftp-proxy.c filter.c diff --git a/tftp-proxy/filter.c b/tftp-proxy/filter.c index 61b3a1756bb..2e055f529a6 100644 --- a/tftp-proxy/filter.c +++ b/tftp-proxy/filter.c @@ -1,4 +1,4 @@ -/* $OpenBSD: filter.c,v 1.2 2007/06/23 15:51:21 jcs Exp $ */ +/* $OpenBSD: filter.c,v 1.1 2005/12/28 19:07:07 jcs Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, diff --git a/tftp-proxy/filter.h b/tftp-proxy/filter.h index 04d43f737cb..c75d278826d 100644 --- a/tftp-proxy/filter.h +++ b/tftp-proxy/filter.h @@ -1,4 +1,4 @@ -/* $OpenBSD: filter.h,v 1.1 2005/12/28 19:07:07 jcs Exp $ */ +/* $OpenBSD: filter.h,v 1.3 2005/06/07 14:12:07 camield Exp $ */ /* * Copyright (c) 2004, 2005 Camiel Dobbelaar, diff --git a/tftp-proxy/tftp-proxy.8 b/tftp-proxy/tftp-proxy.8 index 511b641bce3..e0344388711 100644 --- a/tftp-proxy/tftp-proxy.8 +++ b/tftp-proxy/tftp-proxy.8 @@ -1,4 +1,4 @@ -.\" $OpenBSD: tftp-proxy.8,v 1.2 2007/05/31 19:19:41 jmc Exp $ +.\" $OpenBSD: tftp-proxy.8,v 1.1 2005/12/28 19:07:07 jcs Exp $ .\" .\" Copyright (c) 2005 joshua stein .\" diff --git a/tftp-proxy/tftp-proxy.c b/tftp-proxy/tftp-proxy.c index d2d2875717a..399143ba93d 100644 --- a/tftp-proxy/tftp-proxy.c +++ b/tftp-proxy/tftp-proxy.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tftp-proxy.c,v 1.6 2008/04/13 00:22:17 djm Exp $ +/* $OpenBSD: tftp-proxy.c,v 1.5 2008/03/24 16:11:00 deraadt Exp $ * * Copyright (c) 2005 DLS Internet Services * Copyright (c) 2004, 2005 Camiel Dobbelaar, From 79f67f37a7cbe46f0d064a1267266dcb7a8cf4eb Mon Sep 17 00:00:00 2001 From: Tim Kientzle Date: Sun, 26 Jun 2011 17:54:11 +0000 Subject: [PATCH 07/39] The --newer-than test should descend into old directories to look for new files. PR: bin/150890 Submitted by: Tobias Herre MFC after: 3 weeks --- usr.bin/tar/write.c | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) diff --git a/usr.bin/tar/write.c b/usr.bin/tar/write.c index 838dffb4576..9d9025a04ab 100644 --- a/usr.bin/tar/write.c +++ b/usr.bin/tar/write.c @@ -752,6 +752,9 @@ write_hierarchy(struct bsdtar *bsdtar, struct archive *a, const char *path) break; } + if (bsdtar->option_no_subdirs) + descend = 0; + /* * Are we about to cross to a new filesystem? */ @@ -764,7 +767,6 @@ write_hierarchy(struct bsdtar *bsdtar, struct archive *a, const char *path) } else if (descend == 0) { /* We're not descending, so no need to check. */ } else if (bsdtar->option_dont_traverse_mounts) { - /* User has asked us not to cross mount points. */ descend = 0; } else { /* We're prepared to cross a mount point. */ @@ -791,8 +793,15 @@ write_hierarchy(struct bsdtar *bsdtar, struct archive *a, const char *path) * In -u mode, check that the file is newer than what's * already in the archive; in all modes, obey --newerXXX flags. */ - if (!new_enough(bsdtar, name, st)) + if (!new_enough(bsdtar, name, st)) { + if (!descend) + continue; + if (bsdtar->option_interactive && + !yes("add '%s'", name)) + continue; + tree_descend(tree); continue; + } archive_entry_free(entry); entry = archive_entry_new(); @@ -868,8 +877,7 @@ write_hierarchy(struct bsdtar *bsdtar, struct archive *a, const char *path) !yes("add '%s'", name)) continue; - /* Note: if user vetoes, we won't descend. */ - if (descend && !bsdtar->option_no_subdirs) + if (descend) tree_descend(tree); /* From aaa232d41db01998423d03fef6a2fbac37da7248 Mon Sep 17 00:00:00 2001 From: Ed Schouten Date: Sun, 26 Jun 2011 18:25:10 +0000 Subject: [PATCH 08/39] Fix various whitespace inconsistencies in sys/teken. --- sys/teken/demo/teken_demo.c | 6 +++--- sys/teken/gensequences | 4 ++-- sys/teken/libteken/teken.3 | 2 +- sys/teken/teken.c | 2 +- sys/teken/teken_subr.h | 4 ++-- 5 files changed, 9 insertions(+), 9 deletions(-) diff --git a/sys/teken/demo/teken_demo.c b/sys/teken/demo/teken_demo.c index 070076379d4..16bb4b7b198 100644 --- a/sys/teken/demo/teken_demo.c +++ b/sys/teken/demo/teken_demo.c @@ -88,7 +88,7 @@ printchar(const teken_pos_t *p) getyx(stdscr, y, x); - px = &buffer[p->tp_col][p->tp_row]; + px = &buffer[p->tp_col][p->tp_row]; /* Convert Unicode to UTF-8. */ if (px->c < 0x80) { @@ -169,10 +169,10 @@ test_copy(void *s __unused, const teken_rect_t *r, const teken_pos_t *p) * Copying is a little tricky. We must make sure we do it in * correct order, to make sure we don't overwrite our own data. */ - + nrow = r->tr_end.tp_row - r->tr_begin.tp_row; ncol = r->tr_end.tp_col - r->tr_begin.tp_col; - + if (p->tp_row < r->tr_begin.tp_row) { /* Copy from top to bottom. */ if (p->tp_col < r->tr_begin.tp_col) { diff --git a/sys/teken/gensequences b/sys/teken/gensequences index 86c7979c730..e0fccd4c80a 100644 --- a/sys/teken/gensequences +++ b/sys/teken/gensequences @@ -3,7 +3,7 @@ #- # Copyright (c) 2008-2009 Ed Schouten # All rights reserved. -# +# # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: @@ -12,7 +12,7 @@ # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in the # documentation and/or other materials provided with the distribution. -# +# # THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE diff --git a/sys/teken/libteken/teken.3 b/sys/teken/libteken/teken.3 index 2a9b2917f8f..1c2ebbe3b44 100644 --- a/sys/teken/libteken/teken.3 +++ b/sys/teken/libteken/teken.3 @@ -148,7 +148,7 @@ These defaults can be modified using and .Fn teken_set_defattr . .Pp -The +The .Fn teken_get_sequence function is a utility function that can be used to obtain escape sequences of special keyboard keys, generated by user input. diff --git a/sys/teken/teken.c b/sys/teken/teken.c index cdc2cb32e2b..8ca88d23815 100644 --- a/sys/teken/teken.c +++ b/sys/teken/teken.c @@ -526,7 +526,7 @@ teken_get_sequence(teken_t *t, unsigned int k) /* Default xterm sequences. */ if (k < sizeof special_strings_normal / sizeof(char *)) return (special_strings_normal[k]); - + return (NULL); } diff --git a/sys/teken/teken_subr.h b/sys/teken/teken_subr.h index 2934bcc838d..f4c78f4ede3 100644 --- a/sys/teken/teken_subr.h +++ b/sys/teken/teken_subr.h @@ -260,7 +260,7 @@ teken_subr_cursor_backward_tabulation(teken_t *t, unsigned int ntabs) break; t->t_cursor.tp_col--; - + /* Tab marker set. */ if (teken_tab_isset(t, t->t_cursor.tp_col)) ntabs--; @@ -303,7 +303,7 @@ teken_subr_cursor_forward_tabulation(teken_t *t, unsigned int ntabs) break; t->t_cursor.tp_col++; - + /* Tab marker set. */ if (teken_tab_isset(t, t->t_cursor.tp_col)) ntabs--; From 7c9669276e4a26554643756f0c0ff180b990b625 Mon Sep 17 00:00:00 2001 From: Ed Schouten Date: Sun, 26 Jun 2011 18:26:20 +0000 Subject: [PATCH 09/39] Fix whitespace inconsistencies in the TTY layer and its drivers owned by me. --- sys/dev/pty/pty.c | 6 +++--- sys/dev/snp/snp.c | 4 ++-- sys/dev/syscons/scterm-teken.c | 4 ++-- sys/kern/tty.c | 24 ++++++++++++------------ sys/kern/tty_inq.c | 8 ++++---- sys/kern/tty_outq.c | 2 +- sys/kern/tty_pts.c | 6 +++--- sys/kern/tty_ttydisc.c | 20 ++++++++++---------- 8 files changed, 37 insertions(+), 37 deletions(-) diff --git a/sys/dev/pty/pty.c b/sys/dev/pty/pty.c index 5a542cb6c5b..5e2d822fe29 100644 --- a/sys/dev/pty/pty.c +++ b/sys/dev/pty/pty.c @@ -79,7 +79,7 @@ ptydev_fdopen(struct cdev *dev, int fflags, struct thread *td, struct file *fp) /* Raise a warning when a legacy PTY has been allocated. */ if (pty_warningcnt > 0) { pty_warningcnt--; - log(LOG_INFO, "pid %d (%s) is using legacy pty devices%s\n", + log(LOG_INFO, "pid %d (%s) is using legacy pty devices%s\n", td->td_proc->p_pid, td->td_name, pty_warningcnt ? "" : " - not logging anymore"); } @@ -139,8 +139,8 @@ static int pty_modevent(module_t mod, int type, void *data) { - switch(type) { - case MOD_LOAD: + switch(type) { + case MOD_LOAD: EVENTHANDLER_REGISTER(dev_clone, pty_clone, 0, 1000); make_dev_credf(MAKEDEV_ETERNAL_KLD, &ptmx_cdevsw, 0, NULL, UID_ROOT, GID_WHEEL, 0666, "ptmx"); diff --git a/sys/dev/snp/snp.c b/sys/dev/snp/snp.c index 37d996563f9..b05ad2a81b9 100644 --- a/sys/dev/snp/snp.c +++ b/sys/dev/snp/snp.c @@ -158,7 +158,7 @@ snp_read(struct cdev *dev, struct uio *uio, int flag) error = devfs_get_cdevpriv((void **)&ss); if (error != 0) return (error); - + tp = ss->snp_tty; if (tp == NULL || tty_gone(tp)) return (EIO); @@ -198,7 +198,7 @@ snp_write(struct cdev *dev, struct uio *uio, int flag) error = devfs_get_cdevpriv((void **)&ss); if (error != 0) return (error); - + tp = ss->snp_tty; if (tp == NULL || tty_gone(tp)) return (EIO); diff --git a/sys/dev/syscons/scterm-teken.c b/sys/dev/syscons/scterm-teken.c index 1d110ab91c0..725f9f517cc 100644 --- a/sys/dev/syscons/scterm-teken.c +++ b/sys/dev/syscons/scterm-teken.c @@ -643,7 +643,7 @@ scteken_copy(void *arg, const teken_rect_t *r, const teken_pos_t *p) while (src < end) { sc_vtb_move(&scp->vtb, src, dst, width); - + src += scp->xsize; dst += scp->xsize; } @@ -658,7 +658,7 @@ scteken_copy(void *arg, const teken_rect_t *r, const teken_pos_t *p) while (src >= end) { sc_vtb_move(&scp->vtb, src, dst, width); - + src -= scp->xsize; dst -= scp->xsize; } diff --git a/sys/kern/tty.c b/sys/kern/tty.c index 8aa3af2e89e..f6475cbc64e 100644 --- a/sys/kern/tty.c +++ b/sys/kern/tty.c @@ -470,10 +470,10 @@ ttydev_write(struct cdev *dev, struct uio *uio, int ioflag) if (error) goto done; } - - tp->t_flags |= TF_BUSY_OUT; + + tp->t_flags |= TF_BUSY_OUT; error = ttydisc_write(tp, uio, ioflag); - tp->t_flags &= ~TF_BUSY_OUT; + tp->t_flags &= ~TF_BUSY_OUT; cv_signal(&tp->t_outserwait); } @@ -1054,7 +1054,7 @@ tty_rel_pgrp(struct tty *tp, struct pgrp *pg) if (tp->t_pgrp == pg) tp->t_pgrp = NULL; - + tty_unlock(tp); } @@ -1241,7 +1241,7 @@ tty_signal_sessleader(struct tty *tp, int sig) /* Make signals start output again. */ tp->t_flags &= ~TF_STOPPED; - + if (tp->t_session != NULL && tp->t_session->s_leader != NULL) { p = tp->t_session->s_leader; PROC_LOCK(p); @@ -1305,7 +1305,7 @@ tty_wait(struct tty *tp, struct cv *cv) /* Restart the system call when we may have been revoked. */ if (tp->t_revokecnt != revokecnt) return (ERESTART); - + /* Bail out when the device slipped away. */ if (tty_gone(tp)) return (ENXIO); @@ -1327,7 +1327,7 @@ tty_timedwait(struct tty *tp, struct cv *cv, int hz) /* Restart the system call when we may have been revoked. */ if (tp->t_revokecnt != revokecnt) return (ERESTART); - + /* Bail out when the device slipped away. */ if (tty_gone(tp)) return (ENXIO); @@ -1469,7 +1469,7 @@ tty_generic_ioctl(struct tty *tp, u_long cmd, void *data, int fflag, return (error); /* XXX: CLOCAL? */ - + tp->t_termios.c_cflag = t->c_cflag & ~CIGNORE; tp->t_termios.c_ispeed = t->c_ispeed; tp->t_termios.c_ospeed = t->c_ospeed; @@ -1708,7 +1708,7 @@ tty_ioctl(struct tty *tp, u_long cmd, void *data, int fflag, struct thread *td) if (tty_gone(tp)) return (ENXIO); - + error = ttydevsw_ioctl(tp, cmd, data, td); if (error == ENOIOCTL) error = tty_generic_ioctl(tp, cmd, data, fflag, td); @@ -1786,7 +1786,7 @@ ttyhook_defrint(struct tty *tp, char c, int flags) if (ttyhook_rint_bypass(tp, &c, 1) != 1) return (-1); - + return (0); } @@ -1812,7 +1812,7 @@ ttyhook_register(struct tty **rtp, struct proc *p, int fd, error = EBADF; goto done1; } - + /* * Make sure the vnode is bound to a character device. * Unlocked check for the vnode type is ok there, because we @@ -1910,7 +1910,7 @@ ttyconsdev_open(struct cdev *dev, int oflags, int devtype, struct thread *td) /* System console has no TTY associated. */ if (dev_console->si_drv1 == NULL) return (ENXIO); - + return (ttydev_open(dev, oflags, devtype, td)); } diff --git a/sys/kern/tty_inq.c b/sys/kern/tty_inq.c index b0e9b18a788..0c39a293ded 100644 --- a/sys/kern/tty_inq.c +++ b/sys/kern/tty_inq.c @@ -142,7 +142,7 @@ void ttyinq_free(struct ttyinq *ti) { struct ttyinq_block *tib; - + ttyinq_flush(ti); ti->ti_quota = 0; @@ -276,7 +276,7 @@ ttyinq_write(struct ttyinq *ti, const void *buf, size_t nbytes, int quote) struct ttyinq_block *tib; unsigned int boff; size_t l; - + while (nbytes > 0) { boff = ti->ti_end % TTYINQ_DATASIZE; @@ -313,7 +313,7 @@ ttyinq_write(struct ttyinq *ti, const void *buf, size_t nbytes, int quote) nbytes -= l; ti->ti_end += l; } - + return (cbuf - (const char *)buf); } @@ -397,7 +397,7 @@ ttyinq_peekchar(struct ttyinq *ti, char *c, int *quote) *c = tib->tib_data[boff]; *quote = GETBIT(tib, boff); - + return (0); } diff --git a/sys/kern/tty_outq.c b/sys/kern/tty_outq.c index d5ed221efa0..5d40abe1a85 100644 --- a/sys/kern/tty_outq.c +++ b/sys/kern/tty_outq.c @@ -119,7 +119,7 @@ void ttyoutq_free(struct ttyoutq *to) { struct ttyoutq_block *tob; - + ttyoutq_flush(to); to->to_quota = 0; diff --git a/sys/kern/tty_pts.c b/sys/kern/tty_pts.c index d89c1830e3a..a3db59bfc5a 100644 --- a/sys/kern/tty_pts.c +++ b/sys/kern/tty_pts.c @@ -295,7 +295,7 @@ ptsdev_ioctl(struct file *fp, u_long cmd, void *data, return (EINVAL); return copyout(p, fgn->buf, i); } - + /* * We need to implement TIOCGPGRP and TIOCGSID here again. When * called on the pseudo-terminal master, it should not check if @@ -563,7 +563,7 @@ ptsdev_stat(struct file *fp, struct stat *sb, struct ucred *active_cred, sb->st_uid = dev->si_uid; sb->st_gid = dev->si_gid; sb->st_mode = dev->si_mode | S_IFCHR; - + return (0); } @@ -823,7 +823,7 @@ posix_openpt(struct thread *td, struct posix_openpt_args *uap) */ if (uap->flags & ~(O_RDWR|O_NOCTTY)) return (EINVAL); - + error = falloc(td, &fp, &fd, 0); if (error) return (error); diff --git a/sys/kern/tty_ttydisc.c b/sys/kern/tty_ttydisc.c index 6afac8df5e9..2a0bb4b7c6f 100644 --- a/sys/kern/tty_ttydisc.c +++ b/sys/kern/tty_ttydisc.c @@ -270,13 +270,13 @@ ttydisc_read_raw_interbyte_timer(struct tty *tp, struct uio *uio, int ioflag) MPASS(tp->t_termios.c_cc[VMIN] != 0); MPASS(tp->t_termios.c_cc[VTIME] != 0); - + /* * When using the interbyte timer, the timer should be started * after the first byte has been received. We just call into the * generic read timer code after we've received the first byte. */ - + for (;;) { error = ttyinq_read_uio(&tp->t_inq, tp, uio, uio->uio_resid, 0); @@ -331,7 +331,7 @@ ttydisc_read(struct tty *tp, struct uio *uio, int ioflag) /* Unset the input watermark when we've got enough space. */ tty_hiwat_in_unblock(tp); } - + return (error); } @@ -521,7 +521,7 @@ ttydisc_write(struct tty *tp, struct uio *uio, int ioflag) error = EWOULDBLOCK; goto done; } - + /* * The driver may write back the data * synchronously. Be sure to check the high @@ -567,7 +567,7 @@ ttydisc_optimize(struct tty *tp) } else if (!CMP_FLAG(i, ICRNL|IGNCR|IMAXBEL|INLCR|ISTRIP|IXON) && (!CMP_FLAG(i, BRKINT) || CMP_FLAG(i, IGNBRK)) && (!CMP_FLAG(i, PARMRK) || - CMP_FLAG(i, IGNPAR|IGNBRK) == (IGNPAR|IGNBRK)) && + CMP_FLAG(i, IGNPAR|IGNBRK) == (IGNPAR|IGNBRK)) && !CMP_FLAG(l, ECHO|ICANON|IEXTEN|ISIG|PENDIN)) { tp->t_flags |= TF_BYPASS; } else { @@ -583,7 +583,7 @@ ttydisc_modem(struct tty *tp, int open) if (open) cv_broadcast(&tp->t_dcdwait); - + /* * Ignore modem status lines when CLOCAL is turned on, but don't * enter the zombie state when the TTY isn't opened, because @@ -834,7 +834,7 @@ ttydisc_rint(struct tty *tp, char c, int flags) if (ttyhook_hashook(tp, rint)) return ttyhook_rint(tp, c, flags); - + if (tp->t_flags & TF_BYPASS) goto processed; @@ -1072,7 +1072,7 @@ ttydisc_rint_bypass(struct tty *tp, const void *buf, size_t len) size_t ret; tty_lock_assert(tp, MA_OWNED); - + MPASS(tp->t_flags & TF_BYPASS); atomic_add_long(&tty_nin, len); @@ -1122,7 +1122,7 @@ ttydisc_rint_poll(struct tty *tp) l = ttyinq_bytesleft(&tp->t_inq); if (l == 0 && (tp->t_flags & TF_HIWAT_IN) == 0) return (1); - + return (l); } @@ -1201,7 +1201,7 @@ ttydisc_getc_uio(struct tty *tp, struct uio *uio) tty_unlock(tp); error = uiomove(buf, len, uio); tty_lock(tp); - + if (error != 0) break; } From 1d9a9b79d0111a5465b05863b492a7d375e243fd Mon Sep 17 00:00:00 2001 From: Ed Schouten Date: Sun, 26 Jun 2011 18:27:17 +0000 Subject: [PATCH 10/39] Fix whitespace inconsistencies in libc in files copyrighted by me. --- lib/libc/gen/getutxent.3 | 4 ++-- lib/libc/gen/posix_spawn.3 | 2 +- lib/libc/gen/posix_spawn.c | 4 ++-- lib/libc/gen/pututxline.c | 4 ++-- lib/libc/stdlib/ptsname.c | 2 +- 5 files changed, 8 insertions(+), 8 deletions(-) diff --git a/lib/libc/gen/getutxent.3 b/lib/libc/gen/getutxent.3 index 5c8b7936027..19205556a87 100644 --- a/lib/libc/gen/getutxent.3 +++ b/lib/libc/gen/getutxent.3 @@ -175,7 +175,7 @@ prefix, corresponding with the device used to facilitate the user login session. If no TTY character device is used, this field is left blank. This field is only applicable to entries of type -.Dv USER_PROCESS +.Dv USER_PROCESS and .Dv LOGIN_PROCESS . .It Fa ut_host @@ -473,7 +473,7 @@ are extensions. .Sh HISTORY These functions appeared in .Fx 9.0 . -They replaced the +They replaced the .In utmp.h interface. .Sh AUTHORS diff --git a/lib/libc/gen/posix_spawn.3 b/lib/libc/gen/posix_spawn.3 index 3d902bf24ac..73359b44b16 100644 --- a/lib/libc/gen/posix_spawn.3 +++ b/lib/libc/gen/posix_spawn.3 @@ -167,7 +167,7 @@ group IDs for the child process are changed as specified in the attributes object referenced by .Fa attrp . .It -The file actions specified by the spawn file actions object are +The file actions specified by the spawn file actions object are performed in the order in which they were added to the spawn file actions object. .It diff --git a/lib/libc/gen/posix_spawn.c b/lib/libc/gen/posix_spawn.c index 58044b3a64f..e4ceb2085e2 100644 --- a/lib/libc/gen/posix_spawn.c +++ b/lib/libc/gen/posix_spawn.c @@ -182,7 +182,7 @@ process_file_actions(const posix_spawn_file_actions_t fa) if (error) return (error); } - return (0); + return (0); } static int @@ -193,7 +193,7 @@ do_posix_spawn(pid_t *pid, const char *path, { pid_t p; volatile int error = 0; - + p = vfork(); switch (p) { case -1: diff --git a/lib/libc/gen/pututxline.c b/lib/libc/gen/pututxline.c index 4caa00c9d16..0cc7a0168ca 100644 --- a/lib/libc/gen/pututxline.c +++ b/lib/libc/gen/pututxline.c @@ -57,7 +57,7 @@ futx_open(const char *file) errno = EFTYPE; return (NULL); } - + fp = fdopen(fd, "r+"); if (fp == NULL) { _close(fd); @@ -103,7 +103,7 @@ utx_active_add(const struct futx *fu) /* Allow us to overwrite unused records. */ if (partial == -1) { partial = ftello(fp); - /* + /* * Distinguish errors from valid values so we * don't overwrite good data by accident. */ diff --git a/lib/libc/stdlib/ptsname.c b/lib/libc/stdlib/ptsname.c index fc3b719a1f1..40b140de761 100644 --- a/lib/libc/stdlib/ptsname.c +++ b/lib/libc/stdlib/ptsname.c @@ -82,7 +82,7 @@ ptsname(int fildes) /* Make sure fildes points to a master device. */ if (__isptmaster(fildes) != 0) goto done; - + if (fdevname_r(fildes, pt_slave + (sizeof _PATH_DEV - 1), sizeof pt_slave - (sizeof _PATH_DEV - 1)) != NULL) ret = pt_slave; From 4b9414ab9204b77d922f5c44abecc67eabe3a902 Mon Sep 17 00:00:00 2001 From: Dimitry Andric Date: Sun, 26 Jun 2011 19:03:33 +0000 Subject: [PATCH 11/39] For some reason, contrib/traceroute/traceroute.c ensures MAXHOSTNAMELEN is defined, but then proceeds to use a hardcoded maximum hostname length of 64 anyway. Fix this by checking against MAXHOSTNAMELEN instead. PR: bin/157732 MFC after: 3 days --- contrib/traceroute/traceroute.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contrib/traceroute/traceroute.c b/contrib/traceroute/traceroute.c index 2a5fea218c8..1c98262bacf 100644 --- a/contrib/traceroute/traceroute.c +++ b/contrib/traceroute/traceroute.c @@ -1618,7 +1618,7 @@ gethostinfo(register char *hostname) register char **p; register u_int32_t addr, *ap; - if (strlen(hostname) > 64) { + if (strlen(hostname) >= MAXHOSTNAMELEN) { Fprintf(stderr, "%s: hostname \"%.32s...\" is too long\n", prog, hostname); exit(1); From 4004e05e8a99fe4b781285956e572feb42cd6860 Mon Sep 17 00:00:00 2001 From: Jilles Tjoelker Date: Sun, 26 Jun 2011 20:12:05 +0000 Subject: [PATCH 12/39] sh: Include instead of non-standard . --- bin/sh/arith_yacc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bin/sh/arith_yacc.c b/bin/sh/arith_yacc.c index f1ac59e8e44..041e638211e 100644 --- a/bin/sh/arith_yacc.c +++ b/bin/sh/arith_yacc.c @@ -35,7 +35,7 @@ #include __FBSDID("$FreeBSD$"); -#include +#include #include #include #include From 02d98cd4da82a09c88230a56f14b8c46820b9595 Mon Sep 17 00:00:00 2001 From: Colin Percival Date: Mon, 27 Jun 2011 02:10:10 +0000 Subject: [PATCH 13/39] Rewrite HISTORY: The SHA256 code first appeared in 6.0, and the SHA512 code in 9.0; neither existed in FreeBSD 4.0. --- lib/libmd/sha256.3 | 2 +- lib/libmd/sha512.3 | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/libmd/sha256.3 b/lib/libmd/sha256.3 index fb96100733b..f40e6dfd8b4 100644 --- a/lib/libmd/sha256.3 +++ b/lib/libmd/sha256.3 @@ -127,7 +127,7 @@ argument is non-null it must point to at least 65 characters of buffer space. .Xr sha 3 .Sh HISTORY These functions appeared in -.Fx 4.0 . +.Fx 6.0 . .Sh AUTHORS The core hash routines were implemented by Colin Percival based on the published diff --git a/lib/libmd/sha512.3 b/lib/libmd/sha512.3 index 45a40963c6c..953ee25539a 100644 --- a/lib/libmd/sha512.3 +++ b/lib/libmd/sha512.3 @@ -127,7 +127,7 @@ argument is non-null it must point to at least 65 characters of buffer space. .Xr sha 3 .Sh HISTORY These functions appeared in -.Fx 4.0 . +.Fx 9.0 . .Sh AUTHORS The core hash routines were implemented by Colin Percival based on the published From e1ab183c5e3650ba72ea15270c4b36b97ec959e9 Mon Sep 17 00:00:00 2001 From: Adrian Chadd Date: Mon, 27 Jun 2011 05:57:14 +0000 Subject: [PATCH 14/39] Print out a big warning if DFS can't find a channel to use. This way people debugging DFS won't be surprised when their AP stops talking. --- sys/net80211/ieee80211_dfs.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/sys/net80211/ieee80211_dfs.c b/sys/net80211/ieee80211_dfs.c index e15445d6a5f..19e552d31cf 100644 --- a/sys/net80211/ieee80211_dfs.c +++ b/sys/net80211/ieee80211_dfs.c @@ -320,6 +320,8 @@ ieee80211_dfs_notify_radar(struct ieee80211com *ic, struct ieee80211_channel *ch * on the NOL to expire. */ /*XXX*/ + if_printf(ic->ic_ifp, "%s: No free channels; waiting for entry " + "on NOL to expire\n", __func__); } } else { /* From 133d75ed187c4e4d73965a6768584f5a62a7549c Mon Sep 17 00:00:00 2001 From: Pawel Jakub Dawidek Date: Mon, 27 Jun 2011 09:10:48 +0000 Subject: [PATCH 15/39] Log a warning if we cannot sandbox using capsicum, but only under debug level 1. It would be too noisy to log it as a proper warning as CAPABILITIES are not compiled into GENERIC by default. MFC after: 3 days --- sbin/hastd/subr.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/sbin/hastd/subr.c b/sbin/hastd/subr.c index 806338b4bfc..4e9dee09273 100644 --- a/sbin/hastd/subr.c +++ b/sbin/hastd/subr.c @@ -230,9 +230,13 @@ drop_privs(struct hast_resource *res) * ioctls and secondary uses ioctls to handle BIO_DELETE and BIO_FLUSH. * For now capsicum is only used to sandbox hastctl. */ - if (res == NULL) + if (res == NULL) { capsicum = (cap_enter() == 0); - else + if (!capsicum) { + pjdlog_common(LOG_DEBUG, 1, errno, + "Unable to sandbox using capsicum"); + } + } else capsicum = false; /* From 699b26bdce09db5d87d1442f2499595712916183 Mon Sep 17 00:00:00 2001 From: Pawel Jakub Dawidek Date: Mon, 27 Jun 2011 09:14:25 +0000 Subject: [PATCH 16/39] Compile capsicum support only if HAVE_CAPSICUM is defined. MFC after: 3 days --- sbin/hastd/subr.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/sbin/hastd/subr.c b/sbin/hastd/subr.c index 4e9dee09273..89ffda0fe2f 100644 --- a/sbin/hastd/subr.c +++ b/sbin/hastd/subr.c @@ -31,7 +31,9 @@ #include __FBSDID("$FreeBSD$"); +#ifdef HAVE_CAPSICUM #include +#endif #include #include #include @@ -230,6 +232,7 @@ drop_privs(struct hast_resource *res) * ioctls and secondary uses ioctls to handle BIO_DELETE and BIO_FLUSH. * For now capsicum is only used to sandbox hastctl. */ +#ifdef HAVE_CAPSICUM if (res == NULL) { capsicum = (cap_enter() == 0); if (!capsicum) { @@ -237,6 +240,7 @@ drop_privs(struct hast_resource *res) "Unable to sandbox using capsicum"); } } else +#endif capsicum = false; /* From a6de1e5c85b8ee7df2c8cdaeef096bf0ea9048f3 Mon Sep 17 00:00:00 2001 From: Pawel Jakub Dawidek Date: Mon, 27 Jun 2011 09:15:41 +0000 Subject: [PATCH 17/39] Compile hastd and hastctl with capsicum support. X-MFC after: capsicum merge --- sbin/hastctl/Makefile | 1 + sbin/hastd/Makefile | 3 ++- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/sbin/hastctl/Makefile b/sbin/hastctl/Makefile index b7b1db93481..af946a20eca 100644 --- a/sbin/hastctl/Makefile +++ b/sbin/hastctl/Makefile @@ -21,6 +21,7 @@ MAN= hastctl.8 NO_WFORMAT= CFLAGS+=-I${.CURDIR}/../hastd +CFLAGS+=-DHAVE_CAPSICUM CFLAGS+=-DINET .if ${MK_INET6_SUPPORT} != "no" CFLAGS+=-DINET6 diff --git a/sbin/hastd/Makefile b/sbin/hastd/Makefile index 1ffd0a244bc..3c4eef18da4 100644 --- a/sbin/hastd/Makefile +++ b/sbin/hastd/Makefile @@ -20,8 +20,9 @@ SRCS+= y.tab.h MAN= hastd.8 hast.conf.5 NO_WFORMAT= -CFLAGS+=-DPROTO_TCP_DEFAULT_PORT=8457 CFLAGS+=-I${.CURDIR} +CFLAGS+=-DHAVE_CAPSICUM +CFLAGS+=-DPROTO_TCP_DEFAULT_PORT=8457 CFLAGS+=-DINET .if ${MK_INET6_SUPPORT} != "no" CFLAGS+=-DINET6 From 61162e857a8439f0a33582fee9e3a9b3c860412f Mon Sep 17 00:00:00 2001 From: "Andrey V. Elsukov" Date: Mon, 27 Jun 2011 10:42:06 +0000 Subject: [PATCH 18/39] MS Windows NT+ uses 4 bytes at offset 0x1b8 in the MBR to identify disk drive. The boot0cfg(8) utility preserves these 4 bytes when is writing bootcode to keep a multiboot ability. Change gpart's bootcode method to keep DSN if it is not zero. Also do not allow writing bootcode with size not equal to MBRSIZE. PR: kern/157819 Tested by: Eir Nym MFC after: 1 month --- sys/geom/part/g_part_mbr.c | 14 ++++++++------ sys/sys/diskmbr.h | 1 + 2 files changed, 9 insertions(+), 6 deletions(-) diff --git a/sys/geom/part/g_part_mbr.c b/sys/geom/part/g_part_mbr.c index 825a1095934..bebdfee4420 100644 --- a/sys/geom/part/g_part_mbr.c +++ b/sys/geom/part/g_part_mbr.c @@ -237,14 +237,16 @@ static int g_part_mbr_bootcode(struct g_part_table *basetable, struct g_part_parms *gpp) { struct g_part_mbr_table *table; - size_t codesz; + uint32_t dsn; + + if (gpp->gpp_codesize != MBRSIZE) + return (ENODEV); - codesz = DOSPARTOFF; table = (struct g_part_mbr_table *)basetable; - bzero(table->mbr, codesz); - codesz = MIN(codesz, gpp->gpp_codesize); - if (codesz > 0) - bcopy(gpp->gpp_codeptr, table->mbr, codesz); + dsn = *(uint32_t *)(table->mbr + DOSDSNOFF); + bcopy(gpp->gpp_codeptr, table->mbr, DOSPARTOFF); + if (dsn != 0) + *(uint32_t *)(table->mbr + DOSDSNOFF) = dsn; return (0); } diff --git a/sys/sys/diskmbr.h b/sys/sys/diskmbr.h index 5aa275ce14f..5b62e646850 100644 --- a/sys/sys/diskmbr.h +++ b/sys/sys/diskmbr.h @@ -36,6 +36,7 @@ #include #define DOSBBSECTOR 0 /* DOS boot block relative sector number */ +#define DOSDSNOFF 440 /* WinNT/2K/XP Drive Serial Number offset */ #define DOSPARTOFF 446 #define DOSPARTSIZE 16 #define NDOSPART 4 From 812f1d32e7cce15029a7444cb70a46e464b14496 Mon Sep 17 00:00:00 2001 From: Gleb Smirnoff Date: Mon, 27 Jun 2011 12:21:11 +0000 Subject: [PATCH 19/39] Add possibility to pass IPv6 packets to a divert(4) socket. Submitted by: sem --- sys/modules/ipdivert/Makefile | 7 +- sys/netinet/ip_divert.c | 159 ++++++++++++++++++++++------------ sys/netinet/ipfw/ip_fw_pfil.c | 30 ++++++- 3 files changed, 137 insertions(+), 59 deletions(-) diff --git a/sys/modules/ipdivert/Makefile b/sys/modules/ipdivert/Makefile index 203b4bf6871..886802a516b 100644 --- a/sys/modules/ipdivert/Makefile +++ b/sys/modules/ipdivert/Makefile @@ -3,6 +3,11 @@ .PATH: ${.CURDIR}/../../netinet KMOD= ipdivert -SRCS= ip_divert.c +SRCS= ip_divert.c opt_inet6.h + +.if !defined(KERNBUILDDIR) +opt_inet6.h: + echo "#define INET6 1" > ${.TARGET} +.endif .include diff --git a/sys/netinet/ip_divert.c b/sys/netinet/ip_divert.c index 527ce568334..29a5d424fdd 100644 --- a/sys/netinet/ip_divert.c +++ b/sys/netinet/ip_divert.c @@ -37,6 +37,7 @@ __FBSDID("$FreeBSD$"); #error "IPDIVERT requires INET." #endif #endif +#include "opt_inet6.h" #include #include @@ -62,6 +63,10 @@ __FBSDID("$FreeBSD$"); #include #include #include +#ifdef INET6 +#include +#include +#endif #ifdef SCTP #include #endif @@ -312,10 +317,10 @@ static int div_output(struct socket *so, struct mbuf *m, struct sockaddr_in *sin, struct mbuf *control) { + struct ip *const ip = mtod(m, struct ip *); struct m_tag *mtag; struct ipfw_rule_ref *dt; int error = 0; - struct mbuf *options; /* * An mbuf may hasn't come from userland, but we pretend @@ -367,71 +372,103 @@ div_output(struct socket *so, struct mbuf *m, struct sockaddr_in *sin, /* Reinject packet into the system as incoming or outgoing */ if (!sin || sin->sin_addr.s_addr == 0) { - struct ip *const ip = mtod(m, struct ip *); + struct mbuf *options = NULL; struct inpcb *inp; dt->info |= IPFW_IS_DIVERT | IPFW_INFO_OUT; inp = sotoinpcb(so); INP_RLOCK(inp); - /* - * Don't allow both user specified and setsockopt options, - * and don't allow packet length sizes that will crash - */ - if (((ip->ip_hl != (sizeof (*ip) >> 2)) && inp->inp_options) || - ((u_short)ntohs(ip->ip_len) > m->m_pkthdr.len)) { - error = EINVAL; - INP_RUNLOCK(inp); - m_freem(m); - } else { + switch (ip->ip_v) { + case IPVERSION: + /* + * Don't allow both user specified and setsockopt + * options, and don't allow packet length sizes that + * will crash. + */ + if ((((ip->ip_hl << 2) != sizeof(struct ip)) && + inp->inp_options != NULL) || + ((u_short)ntohs(ip->ip_len) > m->m_pkthdr.len)) { + error = EINVAL; + INP_RUNLOCK(inp); + goto cantsend; + } + /* Convert fields to host order for ip_output() */ ip->ip_len = ntohs(ip->ip_len); ip->ip_off = ntohs(ip->ip_off); + break; +#ifdef INET6 + case IPV6_VERSION >> 4: + { + struct ip6_hdr *const ip6 = mtod(m, struct ip6_hdr *); - /* Send packet to output processing */ - KMOD_IPSTAT_INC(ips_rawout); /* XXX */ + /* Don't allow packet length sizes that will crash */ + if (((u_short)ntohs(ip6->ip6_plen) > m->m_pkthdr.len)) { + error = EINVAL; + INP_RUNLOCK(inp); + goto cantsend; + } + + ip6->ip6_plen = ntohs(ip6->ip6_plen); + } +#endif + default: + error = EINVAL; + INP_RUNLOCK(inp); + goto cantsend; + } + + /* Send packet to output processing */ + KMOD_IPSTAT_INC(ips_rawout); /* XXX */ #ifdef MAC - mac_inpcb_create_mbuf(inp, m); + mac_inpcb_create_mbuf(inp, m); #endif - /* - * Get ready to inject the packet into ip_output(). - * Just in case socket options were specified on the - * divert socket, we duplicate them. This is done - * to avoid having to hold the PCB locks over the call - * to ip_output(), as doing this results in a number of - * lock ordering complexities. - * - * Note that we set the multicast options argument for - * ip_output() to NULL since it should be invariant that - * they are not present. - */ - KASSERT(inp->inp_moptions == NULL, - ("multicast options set on a divert socket")); - options = NULL; - /* - * XXXCSJP: It is unclear to me whether or not it makes - * sense for divert sockets to have options. However, - * for now we will duplicate them with the INP locks - * held so we can use them in ip_output() without - * requring a reference to the pcb. - */ - if (inp->inp_options != NULL) { - options = m_dup(inp->inp_options, M_DONTWAIT); - if (options == NULL) - error = ENOBUFS; + /* + * Get ready to inject the packet into ip_output(). + * Just in case socket options were specified on the + * divert socket, we duplicate them. This is done + * to avoid having to hold the PCB locks over the call + * to ip_output(), as doing this results in a number of + * lock ordering complexities. + * + * Note that we set the multicast options argument for + * ip_output() to NULL since it should be invariant that + * they are not present. + */ + KASSERT(inp->inp_moptions == NULL, + ("multicast options set on a divert socket")); + /* + * XXXCSJP: It is unclear to me whether or not it makes + * sense for divert sockets to have options. However, + * for now we will duplicate them with the INP locks + * held so we can use them in ip_output() without + * requring a reference to the pcb. + */ + if (inp->inp_options != NULL) { + options = m_dup(inp->inp_options, M_NOWAIT); + if (options == NULL) { + INP_RUNLOCK(inp); + error = ENOBUFS; + goto cantsend; } - INP_RUNLOCK(inp); - if (error == ENOBUFS) { - m_freem(m); - return (error); - } - error = ip_output(m, options, NULL, - ((so->so_options & SO_DONTROUTE) ? - IP_ROUTETOIF : 0) | IP_ALLOWBROADCAST | - IP_RAWOUTPUT, NULL, NULL); - if (options != NULL) - m_freem(options); } + INP_RUNLOCK(inp); + + switch (ip->ip_v) { + case IPVERSION: + error = ip_output(m, options, NULL, + ((so->so_options & SO_DONTROUTE) ? IP_ROUTETOIF : 0) + | IP_ALLOWBROADCAST | IP_RAWOUTPUT, NULL, NULL); + break; +#ifdef INET6 + case IPV6_VERSION >> 4: + error = ip6_output(m, NULL, NULL, 0, NULL, NULL, NULL); + break; +#endif + } + if (options != NULL) + m_freem(options); } else { dt->info |= IPFW_IS_DIVERT | IPFW_INFO_IN; if (m->m_pkthdr.rcvif == NULL) { @@ -456,14 +493,26 @@ div_output(struct socket *so, struct mbuf *m, struct sockaddr_in *sin, mac_socket_create_mbuf(so, m); #endif /* Send packet to input processing via netisr */ - netisr_queue_src(NETISR_IP, (uintptr_t)so, m); + switch (ip->ip_v) { + case IPVERSION: + netisr_queue_src(NETISR_IP, (uintptr_t)so, m); + break; +#ifdef INET6 + case IPV6_VERSION >> 4: + netisr_queue_src(NETISR_IPV6, (uintptr_t)so, m); + break; +#endif + default: + error = EINVAL; + goto cantsend; + } } - return error; + return (error); cantsend: m_freem(m); - return error; + return (error); } static int diff --git a/sys/netinet/ipfw/ip_fw_pfil.c b/sys/netinet/ipfw/ip_fw_pfil.c index f076436fa86..736615b947a 100644 --- a/sys/netinet/ipfw/ip_fw_pfil.c +++ b/sys/netinet/ipfw/ip_fw_pfil.c @@ -58,6 +58,10 @@ __FBSDID("$FreeBSD$"); #include #include #include +#ifdef INET6 +#include +#include +#endif #include #include @@ -265,7 +269,7 @@ ipfw_divert(struct mbuf **m0, int incoming, struct ipfw_rule_ref *rule, * If not tee, consume packet and send it to divert socket. */ struct mbuf *clone; - struct ip *ip; + struct ip *ip = mtod(*m0, struct ip *); struct m_tag *tag; /* Cloning needed for tee? */ @@ -289,8 +293,9 @@ ipfw_divert(struct mbuf **m0, int incoming, struct ipfw_rule_ref *rule, * Note that we now have the 'reass' ipfw option so if we care * we can do it before a 'tee'. */ - ip = mtod(clone, struct ip *); - if (!tee && ntohs(ip->ip_off) & (IP_MF | IP_OFFMASK)) { + if (!tee) switch (ip->ip_v) { + case IPVERSION: + if (ntohs(ip->ip_off) & (IP_MF | IP_OFFMASK)) { int hlen; struct mbuf *reass; @@ -312,7 +317,26 @@ ipfw_divert(struct mbuf **m0, int incoming, struct ipfw_rule_ref *rule, else ip->ip_sum = in_cksum(reass, hlen); clone = reass; + } + break; +#ifdef INET6 + case IPV6_VERSION >> 4: + { + struct ip6_hdr *const ip6 = mtod(clone, struct ip6_hdr *); + + if (ip6->ip6_nxt == IPPROTO_FRAGMENT) { + int nxt, off; + + off = sizeof(struct ip6_hdr); + nxt = frag6_input(&clone, &off, 0); + if (nxt == IPPROTO_DONE) + return (0); + } + break; + } +#endif } + /* attach a tag to the packet with the reinject info */ tag = m_tag_alloc(MTAG_IPFW_RULE, 0, sizeof(struct ipfw_rule_ref), M_NOWAIT); From 671dfdbf117f02c6e46a3664bfe87b98a96b4b17 Mon Sep 17 00:00:00 2001 From: "Andrey V. Elsukov" Date: Mon, 27 Jun 2011 12:42:48 +0000 Subject: [PATCH 20/39] EBR could contain an early stage of boot code. But we do not support it. Remove message about non empty bootcode, we can not break something while GEOM_PART_EBR_COMPAT is defined. But without GEOM_PART_EBR_COMPAT any changes in EBR are allowed and we can accidentally wipe the boot code. To do not break anything save the first EBR chunk and keep it untouched each time when we are changing EBR. Note that we are still not support boot code for EBR. PR: kern/141235 MFC after: 1 month --- sys/geom/part/g_part_ebr.c | 36 ++++++++++++++++++++---------------- 1 file changed, 20 insertions(+), 16 deletions(-) diff --git a/sys/geom/part/g_part_ebr.c b/sys/geom/part/g_part_ebr.c index 8ea9b47c5dc..85b8a8a9e6d 100644 --- a/sys/geom/part/g_part_ebr.c +++ b/sys/geom/part/g_part_ebr.c @@ -59,6 +59,9 @@ FEATURE(geom_part_ebr_compat, struct g_part_ebr_table { struct g_part_table base; +#ifndef GEOM_PART_EBR_COMPAT + u_char ebr[EBRSIZE]; +#endif }; struct g_part_ebr_entry { @@ -459,7 +462,7 @@ g_part_ebr_read(struct g_part_table *basetable, struct g_consumer *cp) u_char *buf; off_t ofs, msize; u_int lba; - int error, index, sum; + int error, index; pp = cp->provider; table = (struct g_part_ebr_table *)basetable; @@ -482,20 +485,11 @@ g_part_ebr_read(struct g_part_table *basetable, struct g_consumer *cp) printf("GEOM: %s: invalid entries in the EBR ignored.\n", pp->name); } - /* We do not support bootcode for EBR. If bootcode area is - * not zeroes, then mark this EBR as corrupt to do not break - * anything for another OS'es. - */ - if (lba == 0) { - sum = 0; - for (index = 0; index < DOSPARTOFF; index++) - sum += buf[index]; - if (sum != 0) { - basetable->gpt_corrupt = 1; - printf("GEOM: %s: EBR has non empty bootcode.\n", - pp->name); - } - } +#ifndef GEOM_PART_EBR_COMPAT + /* Save the first EBR, it can contain a boot code */ + if (lba == 0) + bcopy(buf, table->ebr, sizeof(table->ebr)); +#endif g_free(buf); if (ent[0].dp_typ == 0) @@ -583,6 +577,9 @@ g_part_ebr_type(struct g_part_table *basetable, struct g_part_entry *baseentry, static int g_part_ebr_write(struct g_part_table *basetable, struct g_consumer *cp) { +#ifndef GEOM_PART_EBR_COMPAT + struct g_part_ebr_table *table; +#endif struct g_provider *pp; struct g_part_entry *baseentry, *next; struct g_part_ebr_entry *entry; @@ -592,6 +589,10 @@ g_part_ebr_write(struct g_part_table *basetable, struct g_consumer *cp) pp = cp->provider; buf = g_malloc(pp->sectorsize, M_WAITOK | M_ZERO); +#ifndef GEOM_PART_EBR_COMPAT + table = (struct g_part_ebr_table *)basetable; + bcopy(table->ebr, buf, DOSPARTOFF); +#endif le16enc(buf + DOSMAGICOFFSET, DOSMAGIC); baseentry = LIST_FIRST(&basetable->gpt_entry); @@ -644,7 +645,10 @@ g_part_ebr_write(struct g_part_table *basetable, struct g_consumer *cp) error = g_write_data(cp, baseentry->gpe_start * pp->sectorsize, buf, pp->sectorsize); - +#ifndef GEOM_PART_EBR_COMPAT + if (baseentry->gpe_start == 0) + bzero(buf, DOSPARTOFF); +#endif baseentry = next; } while (!error && baseentry != NULL); From cf78df8a0e44042b4e35b42021724bd21bb13dfe Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Stefan=20E=C3=9Fer?= Date: Mon, 27 Jun 2011 13:23:51 +0000 Subject: [PATCH 21/39] Add macros to specify owner, group and mode of config files for installation. Submitted by: Chris Rees (crees) --- share/mk/bsd.own.mk | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/share/mk/bsd.own.mk b/share/mk/bsd.own.mk index a589fba8fbc..ee786199019 100644 --- a/share/mk/bsd.own.mk +++ b/share/mk/bsd.own.mk @@ -63,6 +63,15 @@ # SHAREMODE ASCII text file mode. [${NOBINMODE}] # # +# CONFDIR Base path for configuration files. [/etc] +# +# CONFOWN Configuration file owner. [root] +# +# CONFGRP Configuration file group. [wheel] +# +# CONFMODE Configuration file mode. [644] +# +# # DOCDIR Base path for system documentation (e.g. PSD, USD, # handbook, FAQ etc.). [${SHAREDIR}/doc] # @@ -145,6 +154,11 @@ SHAREOWN?= root SHAREGRP?= wheel SHAREMODE?= ${NOBINMODE} +CONFDIR?= /etc +CONFOWN?= root +CONFGRP?= wheel +CONFMODE?= 644 + MANDIR?= ${SHAREDIR}/man/man MANOWN?= ${SHAREOWN} MANGRP?= ${SHAREGRP} From 4c7b01b9f8bd2b0fb4d06ca8b35de8aa96f4b9d0 Mon Sep 17 00:00:00 2001 From: John Baldwin Date: Mon, 27 Jun 2011 13:58:24 +0000 Subject: [PATCH 22/39] - Remove the fake BPB from zfsldr. zfsldr doesn't support booting from floppies, so it will not be used as the start of an emulated floppy image on a bootable CD which is what the fake BPB was used for. - Only check that EDD packet mode is available once at the start of zfsldr rather than for each disk sector now that we read data in one sector at a time. As a result, collapse the remaining bits of read up into nread and rename nread to read. - Restore a return at the end of putstr that I removed in the previous revision. Tested by: Henri Hennebert (earlier version) MFC after: 1 week --- sys/boot/i386/zfsboot/Makefile | 2 +- sys/boot/i386/zfsboot/zfsldr.S | 111 +++++++++------------------------ 2 files changed, 31 insertions(+), 82 deletions(-) diff --git a/sys/boot/i386/zfsboot/Makefile b/sys/boot/i386/zfsboot/Makefile index 65df86fad49..16b2e534f09 100644 --- a/sys/boot/i386/zfsboot/Makefile +++ b/sys/boot/i386/zfsboot/Makefile @@ -57,7 +57,7 @@ zfsboot1: zfsldr.out objcopy -S -O binary zfsldr.out ${.TARGET} zfsldr.out: zfsldr.o - ${LD} ${LDFLAGS} -e start -Ttext ${ORG1} -o ${.TARGET} zfsldr.o + ${LD} ${LDFLAGS} -e main -Ttext ${ORG1} -o ${.TARGET} zfsldr.o CLEANFILES+= zfsboot2 zfsboot.ld zfsboot.ldr zfsboot.bin zfsboot.out \ zfsboot.o zfsboot.s zfsboot.s.tmp sio.o cons.o drv.o util.o diff --git a/sys/boot/i386/zfsboot/zfsldr.S b/sys/boot/i386/zfsboot/zfsldr.S index 471a0429caa..87e04d5278f 100644 --- a/sys/boot/i386/zfsboot/zfsldr.S +++ b/sys/boot/i386/zfsboot/zfsldr.S @@ -34,46 +34,9 @@ .set SIZ_SEC,0x200 # Sector size .set NSECT,0x80 - .globl start + .globl main .code16 -start: jmp main # Start recognizably - -/* - * This is the start of a standard BIOS Parameter Block (BPB). Most bootable - * FAT disks have this at the start of their MBR. While normal BIOS's will - * work fine without this section, IBM's El Torito emulation "fixes" up the - * BPB by writing into the memory copy of the MBR. Rather than have data - * written into our code, we'll define a BPB to work around it. - * The data marked with (T) indicates a field required for a ThinkPad to - * recognize the disk and (W) indicates fields written from IBM BIOS code. - * The use of the BPB is based on what OpenBSD and NetBSD implemented in - * their boot code but the required fields were determined by trial and error. - * - * Note: If additional space is needed in boot1, one solution would be to - * move the "prompt" message data (below) to replace the OEM ID. - */ - .org 0x03, 0x00 -oemid: .space 0x08, 0x00 # OEM ID - - .org 0x0b, 0x00 -bpb: .word 512 # sector size (T) - .byte 0 # sectors/clustor - .word 0 # reserved sectors - .byte 0 # number of FATs - .word 0 # root entries - .word 0 # small sectors - .byte 0 # media type (W) - .word 0 # sectors/fat - .word 18 # sectors per track (T) - .word 2 # number of heads (T) - .long 0 # hidden sectors (W) - .long 0 # large sectors - - .org 0x24, 0x00 -ebpb: .byte 0 # BIOS physical drive number (W) - - .org 0x25,0x90 /* * Load the rest of zfsboot2 and BTX up, copy the parts to the right locations, * and start it all up. @@ -90,18 +53,17 @@ main: cld # String ops inc mov %cx,%ss # Set up mov $start,%sp # stack /* - * If we are on a hard drive, then load the MBR and look for the first - * FreeBSD slice. We use the fake partition entry below that points to - * the MBR when we call nread. The first pass looks for the first active - * FreeBSD slice. The second pass looks for the first non-active FreeBSD - * slice if the first one fails. + * Load the MBR and look for the first FreeBSD slice. We use the fake + * partition entry below that points to the MBR when we call read. + * The first pass looks for the first active FreeBSD slice. The + * second pass looks for the first non-active FreeBSD slice if the + * first one fails. */ + call check_edd # Make sure EDD works mov $part4,%si # Dummy partition - cmpb $0x80,%dl # Hard drive? - jb main.4 # No xor %eax,%eax # Read MBR movl $MEM_BUF,%ebx # from first - callw nread # sector + call read # sector mov $0x1,%cx # Two passes main.1: mov $MEM_BUF+PRT_OFF,%si # Partition table movb $0x1,%dh # Partition @@ -122,10 +84,6 @@ main.3: add $0x10,%si # Next entry */ mov $msg_part,%si # Message jmp error # Error -/* - * Floppies use partition 0 of drive 0. - */ -main.4: xor %dx,%dx # Partition:drive /* * Ok, we have a slice and drive in %dx now, so use that to locate and @@ -153,7 +111,7 @@ main.5: mov %dx,MEM_ARG # Save args movl $1024,%eax # Offset to boot2 mov $MEM_BTX,%ebx # Destination buffer main.6: pushal # Save params - callw nread # Read disk + call read # Read disk popal # Restore incl %eax # Advance to add $SIZ_SEC,%ebx # next sector @@ -200,16 +158,16 @@ seta20.3: sti # Enable interrupts /* - * Trampoline used to call read from within zfsldr. Sets up an EDD - * packet on the stack and passes it to read. We assume that the - * destination address is always segment-aligned. + * Read a sector from the disk. Sets up an EDD packet on the stack + * and passes it to read. We assume that the destination address is + * always segment-aligned. * * %eax - int - LBA to read in relative to partition start * %ebx - ptr - destination address * %dl - byte - drive to read from * %si - ptr - MBR partition entry */ -nread: xor %ecx,%ecx # Get +read: xor %ecx,%ecx # Get addl 0x8(%si),%eax # LBA adc $0,%ecx pushl %ecx # Starting absolute block @@ -219,12 +177,13 @@ nread: xor %ecx,%ecx # Get push $0 # transfer buffer push $0x1 # Read 1 sector push $0x10 # Size of packet - mov %sp,%bp # Packet pointer - callw read # Read from disk - jc nread.1 # If error, fail - lea 0x10(%bp),%sp # Clear stack + mov %sp,%si # Packet pointer + mov $0x42,%ah # BIOS: Extended + int $0x13 # read + jc read.1 # If error, fail + lea 0x10(%si),%sp # Clear stack ret # If success, return -nread.1: mov %ah,%al # Format +read.1: mov %ah,%al # Format mov $read_err,%di # error call hex8 # code mov $msg_read,%si # Set the error message and @@ -250,36 +209,26 @@ putstr.0: mov $0x7,%bx # Page:attribute putstr: lodsb # Get char testb %al,%al # End of string? jne putstr.0 # No - + ret # To caller /* - * Reads sectors from the disk. If EDD is enabled, then check if it is - * installed and use it if it is. If it is not installed or not enabled, then - * fall back to using CHS. Since we use a LBA, if we are using CHS, we have to - * fetch the drive parameters from the BIOS and divide it out ourselves. - * Call with: - * - * %dl - byte - drive number - * stack - 10 bytes - EDD Packet + * Check to see if the disk supports EDD. zfsboot requires EDD and does not + * support older C/H/S disk I/O. */ -read: cmpb $0x80,%dl # Hard drive? - jb read.1 # No, use CHS +check_edd: cmpb $0x80,%dl # Hard drive? + jb check_edd.1 # No, fail to boot mov $0x55aa,%bx # Magic push %dx # Save movb $0x41,%ah # BIOS: Check int $0x13 # extensions present pop %dx # Restore - jc read.1 # If error, use CHS + jc check_edd.1 # If error, fail cmp $0xaa55,%bx # Magic? - jne read.1 # No, so use CHS + jne check_edd.1 # No, so fail testb $0x1,%cl # Packet interface? - jz read.1 # No, so use CHS - mov %bp,%si # Disk packet - movb $0x42,%ah # BIOS: Extended - int $0x13 # read - retw # To caller -read.1: mov $msg_chs,%si - jmp error - + jz check_edd.1 # No, so fail + ret # EDD ok, keep booting +check_edd.1: mov $msg_chs,%si # Warn that CHS is + jmp error # unsupported and fail /* * AL to hex, saving the result to [EDI]. */ From 68a108e6263b57dcf1b78b68ca80239479d7c51d Mon Sep 17 00:00:00 2001 From: Nathan Whitehorn Date: Mon, 27 Jun 2011 16:24:36 +0000 Subject: [PATCH 23/39] Build Scrt.o on powerpc64. Its introduction on other platforms got lost during the period of time the powerpc64 port was on a project branch. --- lib/csu/powerpc64/Makefile | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/lib/csu/powerpc64/Makefile b/lib/csu/powerpc64/Makefile index 04926adb888..095a9ad14a6 100644 --- a/lib/csu/powerpc64/Makefile +++ b/lib/csu/powerpc64/Makefile @@ -4,15 +4,14 @@ SRCS= crt1.c crti.S crtn.S OBJS= ${SRCS:N*.h:R:S/$/.o/g} -OBJS+= gcrt1.o -CFLAGS+= -Wall -Wno-unused \ - -I${.CURDIR}/../common \ +OBJS+= Scrt1.o gcrt1.o +CFLAGS+= -I${.CURDIR}/../common \ -I${.CURDIR}/../../libc/include all: ${OBJS} CLEANFILES= ${OBJS} -CLEANFILES+= crt1.s gcrt1.s +CLEANFILES+= crt1.s gcrt1.s Scrt1.s # See the comment in lib/csu/common/crtbrand.c for the reason crt1.c is not # directly compiled to .o files. @@ -31,6 +30,13 @@ gcrt1.s: crt1.c gcrt1.o: gcrt1.s ${CC} ${CFLAGS} -c -o ${.TARGET} gcrt1.s +Scrt1.s: crt1.c + ${CC} ${CFLAGS} -fPIC -DPIC -S -o ${.TARGET} ${.CURDIR}/crt1.c + sed -i "" -e '/\.note\.ABI-tag/s/progbits/note/' ${.TARGET} + +Scrt1.o: Scrt1.s + ${CC} ${CFLAGS} -c -o ${.TARGET} Scrt1.s + realinstall: ${INSTALL} -o ${LIBOWN} -g ${LIBGRP} -m ${LIBMODE} \ ${OBJS} ${DESTDIR}${LIBDIR} From 88bf23ef94f624c0d8a66239d308290368126f26 Mon Sep 17 00:00:00 2001 From: Hans Petter Selasky Date: Mon, 27 Jun 2011 20:32:19 +0000 Subject: [PATCH 24/39] Regenerate usb.conf after r223566. --- etc/devd/usb.conf | 10 +--------- 1 file changed, 1 insertion(+), 9 deletions(-) diff --git a/etc/devd/usb.conf b/etc/devd/usb.conf index 5dbbd0a8d32..568be15fba6 100644 --- a/etc/devd/usb.conf +++ b/etc/devd/usb.conf @@ -1533,15 +1533,7 @@ nomatch 32 { match "bus" "uhub[0-9]+"; match "mode" "host"; match "vendor" "0x083a"; - match "product" "0x4506"; - action "kldload if_uath"; -}; - -nomatch 32 { - match "bus" "uhub[0-9]+"; - match "mode" "host"; - match "vendor" "0x083a"; - match "product" "0x4506"; + match "product" "(0x4505|0x4506)"; action "kldload if_zyd"; }; From e8449b7908e237a6ef64d0a4166fe2176024ff13 Mon Sep 17 00:00:00 2001 From: Pyun YongHyeon Date: Mon, 27 Jun 2011 21:27:12 +0000 Subject: [PATCH 25/39] Disable microcode loading for 82550 and 82550C controllers. Loading the microcode caused SCB timeouts. Linux driver does not allow microcode loading for these controllers and jfv also confirmed that there is no need to do and it shouldn't. PR: kern/103332 Additional confirmation from: jfv MFC after: 1 week --- sys/dev/fxp/if_fxp.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/sys/dev/fxp/if_fxp.c b/sys/dev/fxp/if_fxp.c index e02d5801e2e..ea948218dd4 100644 --- a/sys/dev/fxp/if_fxp.c +++ b/sys/dev/fxp/if_fxp.c @@ -3012,8 +3012,10 @@ static uint32_t fxp_ucode_d101a[] = D101_A_RCVBUNDLE_UCODE; static uint32_t fxp_ucode_d101b0[] = D101_B0_RCVBUNDLE_UCODE; static uint32_t fxp_ucode_d101ma[] = D101M_B_RCVBUNDLE_UCODE; static uint32_t fxp_ucode_d101s[] = D101S_RCVBUNDLE_UCODE; +#ifdef notyet static uint32_t fxp_ucode_d102[] = D102_B_RCVBUNDLE_UCODE; static uint32_t fxp_ucode_d102c[] = D102_C_RCVBUNDLE_UCODE; +#endif static uint32_t fxp_ucode_d102e[] = D102_E_RCVBUNDLE_UCODE; #define UCODE(x) x, sizeof(x)/sizeof(uint32_t) @@ -3031,10 +3033,12 @@ static const struct ucode { D101M_CPUSAVER_DWORD, D101M_CPUSAVER_BUNDLE_MAX_DWORD }, { FXP_REV_82559S_A, UCODE(fxp_ucode_d101s), D101S_CPUSAVER_DWORD, D101S_CPUSAVER_BUNDLE_MAX_DWORD }, +#ifdef notyet { FXP_REV_82550, UCODE(fxp_ucode_d102), D102_B_CPUSAVER_DWORD, D102_B_CPUSAVER_BUNDLE_MAX_DWORD }, { FXP_REV_82550_C, UCODE(fxp_ucode_d102c), D102_C_CPUSAVER_DWORD, D102_C_CPUSAVER_BUNDLE_MAX_DWORD }, +#endif { FXP_REV_82551_F, UCODE(fxp_ucode_d102e), D102_E_CPUSAVER_DWORD, D102_E_CPUSAVER_BUNDLE_MAX_DWORD }, { 0, NULL, 0, 0, 0 } From 50df388d0ef6237d473f88c68b07b2324b0c8d9b Mon Sep 17 00:00:00 2001 From: Pyun YongHyeon Date: Mon, 27 Jun 2011 21:37:38 +0000 Subject: [PATCH 26/39] Enable CPUSaver D102 E-step microcode loading for 82551 revision 0x10. --- sys/dev/fxp/if_fxp.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/sys/dev/fxp/if_fxp.c b/sys/dev/fxp/if_fxp.c index ea948218dd4..62c8dc2f4f0 100644 --- a/sys/dev/fxp/if_fxp.c +++ b/sys/dev/fxp/if_fxp.c @@ -3041,6 +3041,8 @@ static const struct ucode { #endif { FXP_REV_82551_F, UCODE(fxp_ucode_d102e), D102_E_CPUSAVER_DWORD, D102_E_CPUSAVER_BUNDLE_MAX_DWORD }, + { FXP_REV_82551_10, UCODE(fxp_ucode_d102e), + D102_E_CPUSAVER_DWORD, D102_E_CPUSAVER_BUNDLE_MAX_DWORD }, { 0, NULL, 0, 0, 0 } }; From bda6775d59026d73817bbc208e4c9d5dea89ee79 Mon Sep 17 00:00:00 2001 From: John Baldwin Date: Mon, 27 Jun 2011 21:43:56 +0000 Subject: [PATCH 27/39] Revert the entry point label to 'start' to unbreak the build. Pointy hat to: jhb --- sys/boot/i386/zfsboot/Makefile | 2 +- sys/boot/i386/zfsboot/zfsldr.S | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/sys/boot/i386/zfsboot/Makefile b/sys/boot/i386/zfsboot/Makefile index 16b2e534f09..65df86fad49 100644 --- a/sys/boot/i386/zfsboot/Makefile +++ b/sys/boot/i386/zfsboot/Makefile @@ -57,7 +57,7 @@ zfsboot1: zfsldr.out objcopy -S -O binary zfsldr.out ${.TARGET} zfsldr.out: zfsldr.o - ${LD} ${LDFLAGS} -e main -Ttext ${ORG1} -o ${.TARGET} zfsldr.o + ${LD} ${LDFLAGS} -e start -Ttext ${ORG1} -o ${.TARGET} zfsldr.o CLEANFILES+= zfsboot2 zfsboot.ld zfsboot.ldr zfsboot.bin zfsboot.out \ zfsboot.o zfsboot.s zfsboot.s.tmp sio.o cons.o drv.o util.o diff --git a/sys/boot/i386/zfsboot/zfsldr.S b/sys/boot/i386/zfsboot/zfsldr.S index 87e04d5278f..b8be28265fc 100644 --- a/sys/boot/i386/zfsboot/zfsldr.S +++ b/sys/boot/i386/zfsboot/zfsldr.S @@ -34,7 +34,7 @@ .set SIZ_SEC,0x200 # Sector size .set NSECT,0x80 - .globl main + .globl start .code16 /* @@ -46,7 +46,7 @@ * Setup the segment registers to flat addressing (segment 0) and setup the * stack to end just below the start of our code. */ -main: cld # String ops inc +start: cld # String ops inc xor %cx,%cx # Zero mov %cx,%es # Address mov %cx,%ds # data From 3c4401ecabafff3507d8a1b07a87ca7022182250 Mon Sep 17 00:00:00 2001 From: Michael Tuexen Date: Mon, 27 Jun 2011 22:03:33 +0000 Subject: [PATCH 28/39] Add support for SCTP_PR_SCTP_NONE which I misded to add. This constant is defined in the socket API ID. MFC after: 2 months. --- sys/netinet/sctp_uio.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/sys/netinet/sctp_uio.h b/sys/netinet/sctp_uio.h index a798682b1f9..d3b186d4d84 100644 --- a/sys/netinet/sctp_uio.h +++ b/sys/netinet/sctp_uio.h @@ -251,12 +251,13 @@ struct sctp_snd_all_completes { /* for the endpoint */ /* The lower byte is an enumeration of PR-SCTP policies */ +#define SCTP_PR_SCTP_NONE 0x0000/* Reliable transfer */ #define SCTP_PR_SCTP_TTL 0x0001/* Time based PR-SCTP */ #define SCTP_PR_SCTP_BUF 0x0002/* Buffer based PR-SCTP */ #define SCTP_PR_SCTP_RTX 0x0003/* Number of retransmissions based PR-SCTP */ #define PR_SCTP_POLICY(x) ((x) & 0x0f) -#define PR_SCTP_ENABLED(x) (PR_SCTP_POLICY(x) != 0) +#define PR_SCTP_ENABLED(x) (PR_SCTP_POLICY(x) != SCTP_PR_SCTP_NONE) #define PR_SCTP_TTL_ENABLED(x) (PR_SCTP_POLICY(x) == SCTP_PR_SCTP_TTL) #define PR_SCTP_BUF_ENABLED(x) (PR_SCTP_POLICY(x) == SCTP_PR_SCTP_BUF) #define PR_SCTP_RTX_ENABLED(x) (PR_SCTP_POLICY(x) == SCTP_PR_SCTP_RTX) From 7d12b6e1725a2d5c319fbff63d93f0d37944204f Mon Sep 17 00:00:00 2001 From: Adrian Chadd Date: Tue, 28 Jun 2011 00:01:55 +0000 Subject: [PATCH 29/39] Make sure the extended regdomain word is initialised. As with the AR9285, the AR9287 has a default word of 0x1F which means all the various bits in that field are set on by default. --- sys/dev/ath/ath_hal/ah_eeprom_9287.h | 2 ++ sys/dev/ath/ath_hal/ar9002/ar9287_attach.c | 1 + 2 files changed, 3 insertions(+) diff --git a/sys/dev/ath/ath_hal/ah_eeprom_9287.h b/sys/dev/ath/ath_hal/ah_eeprom_9287.h index d429c39c9ad..ff8080aa3a6 100644 --- a/sys/dev/ath/ath_hal/ah_eeprom_9287.h +++ b/sys/dev/ath/ath_hal/ah_eeprom_9287.h @@ -31,6 +31,8 @@ #define AR9287_EEP_MINOR_VER_b AR9287_EEP_MINOR_VER #define AR9287_EEP_NO_BACK_VER AR9287_EEP_MINOR_VER_1 +#define AR9287_RDEXT_DEFAULT 0x1F + #define AR9287_EEP_START_LOC 128 #define AR9287_HTC_EEP_START_LOC 256 #define AR9287_NUM_2G_CAL_PIERS 3 diff --git a/sys/dev/ath/ath_hal/ar9002/ar9287_attach.c b/sys/dev/ath/ath_hal/ar9002/ar9287_attach.c index f3b403b8ae8..ed9feb8fe75 100644 --- a/sys/dev/ath/ath_hal/ar9002/ar9287_attach.c +++ b/sys/dev/ath/ath_hal/ar9002/ar9287_attach.c @@ -320,6 +320,7 @@ ar9287Attach(uint16_t devid, HAL_SOFTC sc, /* Read Reg Domain */ AH_PRIVATE(ah)->ah_currentRD = ath_hal_eepromGet(ah, AR_EEP_REGDMN_0, AH_NULL); + AH_PRIVATE(ah)->ah_currentRDext = AR9287_RDEXT_DEFAULT; /* * ah_miscMode is populated by ar5416FillCapabilityInfo() From c62908a982ccfb82c24246d237b56bc66a237927 Mon Sep 17 00:00:00 2001 From: Xin LI Date: Tue, 28 Jun 2011 00:58:12 +0000 Subject: [PATCH 30/39] Incorporate vendor commit ecdc5c0a7f7591a7cd4a: In userland, sign extend the offset for JA instructions. We currently use that to implement "ip6 protochain", and "pc" might be wider than "pc->k", in which case we need to arrange that "pc->k" be sign-extended, by casting it to bpf_int32. PR: kern/157188 Submitted by: plosher MFC after: 2 weeks --- contrib/libpcap/bpf/net/bpf_filter.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/contrib/libpcap/bpf/net/bpf_filter.c b/contrib/libpcap/bpf/net/bpf_filter.c index db12bb2bad9..f172384fa8c 100644 --- a/contrib/libpcap/bpf/net/bpf_filter.c +++ b/contrib/libpcap/bpf/net/bpf_filter.c @@ -405,7 +405,18 @@ bpf_filter(pc, p, wirelen, buflen) continue; case BPF_JMP|BPF_JA: +#if defined(KERNEL) || defined(_KERNEL) + /* + * No backward jumps allowed. + */ pc += pc->k; +#else + /* + * XXX - we currently implement "ip6 protochain" + * with backward jumps, so sign-extend pc->k. + */ + pc += (bpf_int32)pc->k; +#endif continue; case BPF_JMP|BPF_JGT|BPF_K: From 855c3824172a94b18ce6805ece79dc9e01d6b2be Mon Sep 17 00:00:00 2001 From: Martin Matuska Date: Tue, 28 Jun 2011 06:16:33 +0000 Subject: [PATCH 31/39] Allow mountpoints as arguments for the 'zfs get' command. Illumos-gate revision: 13295 Obtained from: Illumos (Feature #510) MFC after: 1 week --- cddl/contrib/opensolaris/cmd/zfs/zfs_main.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/cddl/contrib/opensolaris/cmd/zfs/zfs_main.c b/cddl/contrib/opensolaris/cmd/zfs/zfs_main.c index 8383dbc2dde..bc5a66292d7 100644 --- a/cddl/contrib/opensolaris/cmd/zfs/zfs_main.c +++ b/cddl/contrib/opensolaris/cmd/zfs/zfs_main.c @@ -21,7 +21,7 @@ /* * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved. - * Copyright 2010 Nexenta Systems, Inc. All rights reserved. + * Copyright 2011 Nexenta Systems, Inc. All rights reserved. */ #include @@ -1292,7 +1292,7 @@ static int zfs_do_get(int argc, char **argv) { zprop_get_cbdata_t cb = { 0 }; - int i, c, flags = 0; + int i, c, flags = ZFS_ITER_ARGS_CAN_BE_PATHS; char *value, *fields; int ret; int limit = 0; From 85a418012f2cd6af07f1fa1d870da80373e91f78 Mon Sep 17 00:00:00 2001 From: Martin Matuska Date: Tue, 28 Jun 2011 06:32:35 +0000 Subject: [PATCH 32/39] Disable vdev cache (readahead) by default. The vdev cache is very underutilized (hit ratio 30%-70%) and may consume excessive memory on systems with many vdevs. Illumos-gate revision: 13346 Obtained from: Illumos (Bug #175) MFC after: 1 week --- .../contrib/opensolaris/uts/common/fs/zfs/vdev_cache.c | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_cache.c b/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_cache.c index 7978d612501..ef9d4b5dc58 100644 --- a/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_cache.c +++ b/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_cache.c @@ -71,9 +71,16 @@ * 1< Date: Tue, 28 Jun 2011 07:52:01 +0000 Subject: [PATCH 33/39] Add a new "REFCOMPRESSRATIO" property. For snapshots, this is the same as COMPRESSRATIO, but for filesystems/volumes, the COMPRESSRATIO is based on the data "USED" (ie, includes blocks in children, but not blocks shared with the origin). This is needed to figure out how much space a filesystem would use if it were not compressed (ignoring snapshots). Illumos-gate revision: 13387 Obtained from: Illumos (Feature #1092) MFC after: 2 weeks --- cddl/contrib/opensolaris/cmd/zfs/zfs.8 | 16 ++++++++++++++-- .../lib/libzfs/common/libzfs_dataset.c | 2 ++ .../contrib/opensolaris/common/zfs/zfs_prop.c | 4 ++++ .../opensolaris/uts/common/fs/zfs/dsl_dataset.c | 13 ++++++++----- .../contrib/opensolaris/uts/common/sys/fs/zfs.h | 2 ++ 5 files changed, 30 insertions(+), 7 deletions(-) diff --git a/cddl/contrib/opensolaris/cmd/zfs/zfs.8 b/cddl/contrib/opensolaris/cmd/zfs/zfs.8 index 0d40a9083c7..e5d859001e1 100644 --- a/cddl/contrib/opensolaris/cmd/zfs/zfs.8 +++ b/cddl/contrib/opensolaris/cmd/zfs/zfs.8 @@ -6,6 +6,7 @@ .\" The contents of this file are subject to the terms of the Common Development and Distribution License (the "License"). You may not use this file except in compliance with the License. You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE or http://www.opensolaris.org/os/licensing. .\" See the License for the specific language governing permissions and limitations under the License. When distributing Covered Code, include this CDDL HEADER in each file and include the License file at usr/src/OPENSOLARIS.LICENSE. If applicable, add the following below this CDDL HEADER, with .\" the fields enclosed by brackets "[]" replaced with your own identifying information: Portions Copyright [yyyy] [name of copyright owner] +.\" Copyright 2011 by Delphix. All rights reserved. .TH zfs 1M "24 Sep 2009" "SunOS 5.11" "System Administration Commands" .SH NAME zfs \- configures ZFS file systems @@ -389,7 +390,7 @@ This property can also be referred to by its shortened column name, \fBavail\fR. .ad .sp .6 .RS 4n -The compression ratio achieved for this dataset, expressed as a multiplier. Compression can be turned on by running: \fBzfs set compression=on \fIdataset\fR\fR. The default value is \fBoff\fR. +For non-snapshots, the compression ratio achieved for the \fBused\fR space of this dataset, expressed as a multiplier. The \fBused\fR property includes descendant datasets, and, for clones, does not include the space shared with the origin snapshot. For snapshots, the \fBcompressratio\fR is the same as the \fBrefcompressratio\fR property. Compression can be turned on by running: \fBzfs set compression=on \fIdataset\fR\fR. The default value is \fBoff\fR. .RE .sp @@ -449,6 +450,17 @@ The amount of data that is accessible by this dataset, which may or may not be s This property can also be referred to by its shortened column name, \fBrefer\fR. .RE +.sp +.ne 2 +.mk +.na +\fB\fBrefcompressratio\fR\fR +.ad +.sp .6 +.RS 4n +The compression ratio achieved for the \fBreferenced\fR space of this dataset, expressed as a multiplier. See also the \fBcompressratio\fR property. +.RE + .sp .ne 2 .mk @@ -1278,7 +1290,7 @@ Recursively destroy all dependents, including cloned file systems outside the ta Force an unmount of any file systems using the \fBunmount -f\fR command. This option has no effect on non-file systems or unmounted file systems. .RE -Extreme care should be taken when applying either the \fB-r\fR or the \fB-f\fR options, as they can destroy large portions of a pool and cause unexpected behavior for mounted file systems in use. +Extreme care should be taken when applying either the \fB-r\fR or the \fB-R\fR options, as they can destroy large portions of a pool and cause unexpected behavior for mounted file systems in use. .RE .sp diff --git a/cddl/contrib/opensolaris/lib/libzfs/common/libzfs_dataset.c b/cddl/contrib/opensolaris/lib/libzfs/common/libzfs_dataset.c index 824834e4676..82f4925bd32 100644 --- a/cddl/contrib/opensolaris/lib/libzfs/common/libzfs_dataset.c +++ b/cddl/contrib/opensolaris/lib/libzfs/common/libzfs_dataset.c @@ -22,6 +22,7 @@ /* * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved. * Copyright 2010 Nexenta Systems, Inc. All rights reserved. + * Copyright (c) 2011 by Delphix. All rights reserved. */ #include @@ -2038,6 +2039,7 @@ zfs_prop_get(zfs_handle_t *zhp, zfs_prop_t prop, char *propbuf, size_t proplen, } break; + case ZFS_PROP_REFRATIO: case ZFS_PROP_COMPRESSRATIO: if (get_numeric_property(zhp, prop, src, &source, &val) != 0) return (-1); diff --git a/sys/cddl/contrib/opensolaris/common/zfs/zfs_prop.c b/sys/cddl/contrib/opensolaris/common/zfs/zfs_prop.c index 434b4829d92..4fa75195970 100644 --- a/sys/cddl/contrib/opensolaris/common/zfs/zfs_prop.c +++ b/sys/cddl/contrib/opensolaris/common/zfs/zfs_prop.c @@ -20,6 +20,7 @@ */ /* * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2011 by Delphix. All rights reserved. */ /* Portions Copyright 2010 Robert Milkowski */ @@ -311,6 +312,9 @@ zfs_prop_init(void) zprop_register_number(ZFS_PROP_COMPRESSRATIO, "compressratio", 0, PROP_READONLY, ZFS_TYPE_DATASET, "<1.00x or higher if compressed>", "RATIO"); + zprop_register_number(ZFS_PROP_REFRATIO, "refcompressratio", 0, + PROP_READONLY, ZFS_TYPE_DATASET, + "<1.00x or higher if compressed>", "REFRATIO"); zprop_register_number(ZFS_PROP_VOLBLOCKSIZE, "volblocksize", ZVOL_DEFAULT_BLOCKSIZE, PROP_ONETIME, ZFS_TYPE_VOLUME, "512 to 128k, power of 2", "VOLBLOCK"); diff --git a/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/dsl_dataset.c b/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/dsl_dataset.c index 7170abaeaa8..498352e7fdd 100644 --- a/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/dsl_dataset.c +++ b/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/dsl_dataset.c @@ -20,6 +20,7 @@ */ /* * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2011 by Delphix. All rights reserved. */ #include @@ -2150,7 +2151,7 @@ dsl_dataset_sync(dsl_dataset_t *ds, zio_t *zio, dmu_tx_t *tx) void dsl_dataset_stats(dsl_dataset_t *ds, nvlist_t *nv) { - uint64_t refd, avail, uobjs, aobjs; + uint64_t refd, avail, uobjs, aobjs, ratio; dsl_dir_stats(ds->ds_dir, nv); @@ -2177,6 +2178,11 @@ dsl_dataset_stats(dsl_dataset_t *ds, nvlist_t *nv) dsl_prop_nvlist_add_uint64(nv, ZFS_PROP_DEFER_DESTROY, DS_IS_DEFER_DESTROY(ds) ? 1 : 0); + ratio = ds->ds_phys->ds_compressed_bytes == 0 ? 100 : + (ds->ds_phys->ds_uncompressed_bytes * 100 / + ds->ds_phys->ds_compressed_bytes); + dsl_prop_nvlist_add_uint64(nv, ZFS_PROP_REFRATIO, ratio); + if (ds->ds_phys->ds_next_snap_obj) { /* * This is a snapshot; override the dd's space used with @@ -2184,10 +2190,7 @@ dsl_dataset_stats(dsl_dataset_t *ds, nvlist_t *nv) */ dsl_prop_nvlist_add_uint64(nv, ZFS_PROP_USED, ds->ds_phys->ds_unique_bytes); - dsl_prop_nvlist_add_uint64(nv, ZFS_PROP_COMPRESSRATIO, - ds->ds_phys->ds_compressed_bytes == 0 ? 100 : - (ds->ds_phys->ds_uncompressed_bytes * 100 / - ds->ds_phys->ds_compressed_bytes)); + dsl_prop_nvlist_add_uint64(nv, ZFS_PROP_COMPRESSRATIO, ratio); } } diff --git a/sys/cddl/contrib/opensolaris/uts/common/sys/fs/zfs.h b/sys/cddl/contrib/opensolaris/uts/common/sys/fs/zfs.h index edc26cde394..e4070c25dfa 100644 --- a/sys/cddl/contrib/opensolaris/uts/common/sys/fs/zfs.h +++ b/sys/cddl/contrib/opensolaris/uts/common/sys/fs/zfs.h @@ -21,6 +21,7 @@ /* * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2011 by Delphix. All rights reserved. */ /* Portions Copyright 2010 Robert Milkowski */ @@ -124,6 +125,7 @@ typedef enum { ZFS_PROP_DEDUP, ZFS_PROP_MLSLABEL, ZFS_PROP_SYNC, + ZFS_PROP_REFRATIO, ZFS_NUM_PROPS } zfs_prop_t; From ee6eac62f7525e948d3b693e4eef182f84625852 Mon Sep 17 00:00:00 2001 From: Kevin Lo Date: Tue, 28 Jun 2011 08:36:48 +0000 Subject: [PATCH 34/39] Remove duplicate header includes --- sys/dev/acpica/acpi_thermal.c | 1 - sys/dev/an/if_an.c | 1 - sys/dev/dc/dcphy.c | 1 - sys/dev/dc/pnphy.c | 1 - sys/dev/en/if_en_pci.c | 3 --- sys/dev/et/if_et.c | 1 - sys/dev/fdc/fdc_pccard.c | 2 -- sys/dev/iicbus/if_ic.c | 3 --- sys/dev/mfi/mfi_cam.c | 3 --- sys/dev/my/if_my.c | 1 - sys/dev/sis/if_sis.c | 1 - sys/dev/tdfx/tdfx_pci.c | 1 - sys/dev/usb/usb_msctest.c | 1 - 13 files changed, 20 deletions(-) diff --git a/sys/dev/acpica/acpi_thermal.c b/sys/dev/acpica/acpi_thermal.c index 7226b6c39c7..18996bd7bb4 100644 --- a/sys/dev/acpica/acpi_thermal.c +++ b/sys/dev/acpica/acpi_thermal.c @@ -36,7 +36,6 @@ __FBSDID("$FreeBSD$"); #include #include #include -#include #include #include #include diff --git a/sys/dev/an/if_an.c b/sys/dev/an/if_an.c index 645fe419ebe..0898961e955 100644 --- a/sys/dev/an/if_an.c +++ b/sys/dev/an/if_an.c @@ -102,7 +102,6 @@ __FBSDID("$FreeBSD$"); #include #include -#include #include #include #include diff --git a/sys/dev/dc/dcphy.c b/sys/dev/dc/dcphy.c index f4fc5124d2c..5c60ad55f54 100644 --- a/sys/dev/dc/dcphy.c +++ b/sys/dev/dc/dcphy.c @@ -62,7 +62,6 @@ __FBSDID("$FreeBSD$"); #include #include -#include #include diff --git a/sys/dev/dc/pnphy.c b/sys/dev/dc/pnphy.c index 6468fbf3c8f..6546acdd712 100644 --- a/sys/dev/dc/pnphy.c +++ b/sys/dev/dc/pnphy.c @@ -60,7 +60,6 @@ __FBSDID("$FreeBSD$"); #include #include -#include #include diff --git a/sys/dev/en/if_en_pci.c b/sys/dev/en/if_en_pci.c index 09ba8bcac1e..3886c9e4137 100644 --- a/sys/dev/en/if_en_pci.c +++ b/sys/dev/en/if_en_pci.c @@ -44,9 +44,6 @@ __FBSDID("$FreeBSD$"); * thanks to Matt Thomas for figuring out FreeBSD vs NetBSD vs etc.. diffs. */ -#include -__FBSDID("$FreeBSD$"); - #include #include #include diff --git a/sys/dev/et/if_et.c b/sys/dev/et/if_et.c index 82c6217570c..9bd68e84a47 100644 --- a/sys/dev/et/if_et.c +++ b/sys/dev/et/if_et.c @@ -57,7 +57,6 @@ __FBSDID("$FreeBSD$"); #include #include #include -#include #include #include diff --git a/sys/dev/fdc/fdc_pccard.c b/sys/dev/fdc/fdc_pccard.c index 72a356857bf..d9590603b96 100644 --- a/sys/dev/fdc/fdc_pccard.c +++ b/sys/dev/fdc/fdc_pccard.c @@ -38,8 +38,6 @@ __FBSDID("$FreeBSD$"); #include #include -#include - #include #include #include "pccarddevs.h" diff --git a/sys/dev/iicbus/if_ic.c b/sys/dev/iicbus/if_ic.c index 4a05b163f6b..6ac6401cb1f 100644 --- a/sys/dev/iicbus/if_ic.c +++ b/sys/dev/iicbus/if_ic.c @@ -49,9 +49,6 @@ __FBSDID("$FreeBSD$"); #include #include -#include -#include -#include #include #include #include diff --git a/sys/dev/mfi/mfi_cam.c b/sys/dev/mfi/mfi_cam.c index 5137c36bf3c..747b6c06231 100644 --- a/sys/dev/mfi/mfi_cam.c +++ b/sys/dev/mfi/mfi_cam.c @@ -54,12 +54,9 @@ __FBSDID("$FreeBSD$"); #include #include -#include -#include #include #include #include -#include #include #include diff --git a/sys/dev/my/if_my.c b/sys/dev/my/if_my.c index 951473a3ba7..4b59c480559 100644 --- a/sys/dev/my/if_my.c +++ b/sys/dev/my/if_my.c @@ -39,7 +39,6 @@ __FBSDID("$FreeBSD$"); #include #include #include -#include #include #include #include diff --git a/sys/dev/sis/if_sis.c b/sys/dev/sis/if_sis.c index 63417a0b0d9..9290ff7591b 100644 --- a/sys/dev/sis/if_sis.c +++ b/sys/dev/sis/if_sis.c @@ -87,7 +87,6 @@ __FBSDID("$FreeBSD$"); #include #include -#include #include #include diff --git a/sys/dev/tdfx/tdfx_pci.c b/sys/dev/tdfx/tdfx_pci.c index 770c6721e0a..27308a9bc00 100644 --- a/sys/dev/tdfx/tdfx_pci.c +++ b/sys/dev/tdfx/tdfx_pci.c @@ -42,7 +42,6 @@ __FBSDID("$FreeBSD$"); #include #include -#include #include #include #include diff --git a/sys/dev/usb/usb_msctest.c b/sys/dev/usb/usb_msctest.c index 45bd36384fa..0b6024b3d76 100644 --- a/sys/dev/usb/usb_msctest.c +++ b/sys/dev/usb/usb_msctest.c @@ -62,7 +62,6 @@ #include #include #include -#include #include #include #include From 235195988ba8b409ab69a0aa14f4f7ac0e8224ac Mon Sep 17 00:00:00 2001 From: Sergey Kandaurov Date: Tue, 28 Jun 2011 08:41:44 +0000 Subject: [PATCH 35/39] Update ifc_len field of struct ifconf passed for the ioctl SIOCGIFCONF32 (i.e. under COMPAT_FREEBSD32) in case ifconf() returned success to match the native SIOCGIFCONF behavior. PR: kern/158369 Reported by: Paul Procacci MFC after: 1 week --- sys/net/if.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/sys/net/if.c b/sys/net/if.c index b7c2ad144d6..a5a3a8edbb2 100644 --- a/sys/net/if.c +++ b/sys/net/if.c @@ -2467,6 +2467,8 @@ ifioctl(struct socket *so, u_long cmd, caddr_t data, struct thread *td) error = ifconf(SIOCGIFCONF, (void *)&ifc); CURVNET_RESTORE(); + if (error == 0) + ifc32->ifc_len = ifc.ifc_len; return (error); } #endif From a9b394783712e3c14846cc2ebb54439d6fc4186e Mon Sep 17 00:00:00 2001 From: "Bjoern A. Zeeb" Date: Tue, 28 Jun 2011 09:46:25 +0000 Subject: [PATCH 36/39] Compare port numbers correctly. They are stored by SRCPORT() in host byte order, so we need to compare them as such. Properly compare IPv6 addresses as well. This allows the, by default, 8 badaddrs slots per address family to work correctly and only print sendto() errors once. The change is no longer applicable to any latest upstream versions. Approved by: roberto Sponsored by: Sandvine Incorporated MFC after: 1 week --- contrib/ntp/ntpd/ntp_io.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/contrib/ntp/ntpd/ntp_io.c b/contrib/ntp/ntpd/ntp_io.c index 8dac3c494b8..2d5572a2156 100644 --- a/contrib/ntp/ntpd/ntp_io.c +++ b/contrib/ntp/ntpd/ntp_io.c @@ -2716,14 +2716,14 @@ sendpkt( for (slot = ERRORCACHESIZE; --slot >= 0; ) if(dest->ss_family == AF_INET) { - if (badaddrs[slot].port == ((struct sockaddr_in*)dest)->sin_port && + if (badaddrs[slot].port == SRCPORT(dest) && badaddrs[slot].addr.s_addr == ((struct sockaddr_in*)dest)->sin_addr.s_addr) break; } #ifdef INCLUDE_IPV6_SUPPORT else if (dest->ss_family == AF_INET6) { - if (badaddrs6[slot].port == ((struct sockaddr_in6*)dest)->sin6_port && - badaddrs6[slot].addr.s6_addr == ((struct sockaddr_in6*)dest)->sin6_addr.s6_addr) + if (badaddrs6[slot].port == SRCPORT(dest) && + !memcmp(&badaddrs6[slot].addr, &((struct sockaddr_in6*)dest)->sin6_addr, sizeof(struct in6_addr))) break; } #endif /* INCLUDE_IPV6_SUPPORT */ From 0b50722bc13e8d66a5aa90b8d833e6a1d74c0a30 Mon Sep 17 00:00:00 2001 From: Edwin Groothuis Date: Tue, 28 Jun 2011 10:11:40 +0000 Subject: [PATCH 37/39] Vendor import of tzdata2011h: - Russia scraps DST in 2011 - Remove Netherlands Antilles, add Bonaire, Curacao, Sint Maarten Obtained from: ftp://elsie.nci.nih.gov/pub/ --- antarctica | 14 +---------- asia | 6 ++++- europe | 70 +++++++++++++++++++++++++++++++++++++++------------- iso3166.tab | 10 ++++++-- southamerica | 10 +++++++- zone.tab | 6 +++-- 6 files changed, 80 insertions(+), 36 deletions(-) diff --git a/antarctica b/antarctica index 629b2d7b815..d19fbde0fcf 100644 --- a/antarctica +++ b/antarctica @@ -1,5 +1,5 @@ #
-# @(#)antarctica	8.8
+# @(#)antarctica	8.9
 # This file is in the public domain, so clarified as of
 # 2009-05-17 by Arthur David Olson.
 
@@ -19,18 +19,6 @@
 # I made up all time zone abbreviations mentioned here; corrections welcome!
 # FORMAT is `zzz' and GMTOFF is 0 for locations while uninhabited.
 
-# These rules are stolen from the `europe' file.
-# Rule	NAME	FROM	TO	TYPE	IN	ON	AT	SAVE	LETTER/S
-Rule	RussAQ	1981	1984	-	Apr	 1	 0:00	1:00	S
-Rule	RussAQ	1981	1983	-	Oct	 1	 0:00	0	-
-Rule	RussAQ	1984	1991	-	Sep	lastSun	 2:00s	0	-
-Rule	RussAQ	1985	1991	-	Mar	lastSun	 2:00s	1:00	S
-Rule	RussAQ	1992	only	-	Mar	lastSat	 23:00	1:00	S
-Rule	RussAQ	1992	only	-	Sep	lastSat	 23:00	0	-
-Rule	RussAQ	1993	max	-	Mar	lastSun	 2:00s	1:00	S
-Rule	RussAQ	1993	1995	-	Sep	lastSun	 2:00s	0	-
-Rule	RussAQ	1996	max	-	Oct	lastSun	 2:00s	0	-
-
 # These rules are stolen from the `southamerica' file.
 # Rule	NAME	FROM	TO	TYPE	IN	ON	AT	SAVE	LETTER/S
 Rule	ArgAQ	1964	1966	-	Mar	 1	0:00	0	-
diff --git a/asia b/asia
index d415ba801c6..1fc61f0b491 100644
--- a/asia
+++ b/asia
@@ -1,4 +1,4 @@
-# @(#)asia	8.64
+# @(#)asia	8.65
 # This file is in the public domain, so clarified as of
 # 2009-05-17 by Arthur David Olson.
 
@@ -77,6 +77,10 @@ Rule RussiaAsia	1993	max	-	Mar	lastSun	 2:00s	1:00	S
 Rule RussiaAsia	1993	1995	-	Sep	lastSun	 2:00s	0	-
 Rule RussiaAsia	1996	max	-	Oct	lastSun	 2:00s	0	-
 
+# From Arthur David Olson (2011-06-15):
+# While Russia abandoned DST in 2011, Armenia may choose to
+# follow Russia's "old" rules.
+
 # Afghanistan
 # Zone	NAME		GMTOFF	RULES	FORMAT	[UNTIL]
 Zone	Asia/Kabul	4:36:48 -	LMT	1890
diff --git a/europe b/europe
index f7fc1896f5b..aab6833114e 100644
--- a/europe
+++ b/europe
@@ -1,5 +1,5 @@
 # 
-# @(#)europe	8.32
+# @(#)europe	8.33
 # This file is in the public domain, so clarified as of
 # 2009-05-17 by Arthur David Olson.
 
@@ -565,6 +565,26 @@ Rule	Russia	1993	max	-	Mar	lastSun	 2:00s	1:00	S
 Rule	Russia	1993	1995	-	Sep	lastSun	 2:00s	0	-
 Rule	Russia	1996	max	-	Oct	lastSun	 2:00s	0	-
 
+# From Alexander Krivenyshev (2011-06-14):
+# According to Kremlin press service, Russian President Dmitry Medvedev
+# signed a federal law "On calculation of time" on June 9, 2011.
+# According to the law Russia is abolishing daylight saving time.
+# 
+# Medvedev signed a law "On the Calculation of Time" (in russian): 
+# 
+# http://bmockbe.ru/events/?ID=7583
+# 
+# 
+# Medvedev signed a law on the calculation of the time (in russian):
+# 
+# http://www.regnum.ru/news/polit/1413906.html
+# 
+
+# From Arthur David Olson (2011-06-15):
+# Take "abolishing daylight saving time" to mean that time is now considered
+# to be standard.
+# At least for now, keep the "old" Russia rules for the benefit of Belarus.
+
 # These are for backward compatibility with older versions.
 
 # Zone	NAME		GMTOFF	RULES	FORMAT	[UNTIL]
@@ -2013,7 +2033,8 @@ Zone Europe/Kaliningrad	 1:22:00 -	LMT	1893 Apr
 			 1:00	C-Eur	CE%sT	1945
 			 2:00	Poland	CE%sT	1946
 			 3:00	Russia	MSK/MSD	1991 Mar 31 2:00s
-			 2:00	Russia	EE%sT
+			 2:00	Russia	EE%sT	2011 Mar 27 2:00s
+			 3:00	-	EET
 #
 # From Oscar van Vlijmen (2001-08-25): [This region consists of]
 # Respublika Adygeya, Arkhangel'skaya oblast',
@@ -2042,7 +2063,8 @@ Zone Europe/Moscow	 2:30:20 -	LMT	1880
 			 2:00	-	EET	1930 Jun 21
 			 3:00	Russia	MSK/MSD	1991 Mar 31 2:00s
 			 2:00	Russia	EE%sT	1992 Jan 19 2:00s
-			 3:00	Russia	MSK/MSD
+			 3:00	Russia	MSK/MSD	2011 Mar 27 2:00s
+			 4:00	-	MSK
 #
 # Astrakhanskaya oblast', Kirovskaya oblast', Saratovskaya oblast',
 # Volgogradskaya oblast'.  Shanks & Pottenger say Kirov is still at +0400
@@ -2055,7 +2077,8 @@ Zone Europe/Volgograd	 2:57:40 -	LMT	1920 Jan  3
 			 4:00	Russia	VOL%sT	1989 Mar 26 2:00s # Volgograd T
 			 3:00	Russia	VOL%sT	1991 Mar 31 2:00s
 			 4:00	-	VOLT	1992 Mar 29 2:00s
-			 3:00	Russia	VOL%sT
+			 3:00	Russia	VOL%sT	2011 Mar 27 2:00s
+			 4:00	-	VOLT
 #
 # From Oscar van Vlijmen (2001-08-25): [This region consists of]
 # Samarskaya oblast', Udmyrtskaya respublika
@@ -2067,7 +2090,8 @@ Zone Europe/Samara	 3:20:36 -	LMT	1919 Jul  1 2:00
 			 2:00	Russia	KUY%sT	1991 Sep 29 2:00s
 			 3:00	-	KUYT	1991 Oct 20 3:00
 			 4:00	Russia	SAM%sT	2010 Mar 28 2:00s # Samara Time
-			 3:00	Russia	SAM%sT
+			 3:00	Russia	SAM%sT	2011 Mar 27 2:00s
+			 4:00	-	SAMT
 
 #
 # From Oscar van Vlijmen (2001-08-25): [This region consists of]
@@ -2080,7 +2104,8 @@ Zone Asia/Yekaterinburg	 4:02:24 -	LMT	1919 Jul 15 4:00
 			 4:00	-	SVET	1930 Jun 21 # Sverdlovsk Time
 			 5:00	Russia	SVE%sT	1991 Mar 31 2:00s
 			 4:00	Russia	SVE%sT	1992 Jan 19 2:00s
-			 5:00	Russia	YEK%sT	# Yekaterinburg Time
+			 5:00	Russia	YEK%sT	2011 Mar 27 2:00s
+			 6:00	-	YEKT	# Yekaterinburg Time
 #
 # From Oscar van Vlijmen (2001-08-25): [This region consists of]
 # Respublika Altaj, Altajskij kraj, Omskaya oblast'.
@@ -2088,7 +2113,8 @@ Zone Asia/Omsk		 4:53:36 -	LMT	1919 Nov 14
 			 5:00	-	OMST	1930 Jun 21 # Omsk TIme
 			 6:00	Russia	OMS%sT	1991 Mar 31 2:00s
 			 5:00	Russia	OMS%sT	1992 Jan 19 2:00s
-			 6:00	Russia	OMS%sT
+			 6:00	Russia	OMS%sT	2011 Mar 27 2:00s
+			 7:00	-	OMST
 #
 # From Paul Eggert (2006-08-19): I'm guessing about Tomsk here; it's
 # not clear when it switched from +7 to +6.
@@ -2098,7 +2124,8 @@ Zone Asia/Novosibirsk	 5:31:40 -	LMT	1919 Dec 14 6:00
 			 7:00	Russia	NOV%sT	1991 Mar 31 2:00s
 			 6:00	Russia	NOV%sT	1992 Jan 19 2:00s
 			 7:00	Russia	NOV%sT	1993 May 23 # say Shanks & P.
-			 6:00	Russia	NOV%sT
+			 6:00	Russia	NOV%sT	2011 Mar 27 2:00s
+			 7:00	-	NOVT
 
 # From Alexander Krivenyshev (2009-10-13):
 # Kemerovo oblast' (Kemerovo region) in Russia will change current time zone on
@@ -2131,7 +2158,8 @@ Zone Asia/Novokuznetsk	 5:48:48 -	NMT	1920 Jan  6
 			 7:00	Russia	KRA%sT	1991 Mar 31 2:00s
 			 6:00	Russia	KRA%sT	1992 Jan 19 2:00s
 			 7:00	Russia	KRA%sT	2010 Mar 28 2:00s
-			 6:00	Russia	NOV%sT # Novosibirsk/Novokuznetsk Time
+			 6:00	Russia	NOV%sT	2011 Mar 27 2:00s
+			 7:00	-	NOVT # Novosibirsk/Novokuznetsk Time
 
 #
 # From Oscar van Vlijmen (2001-08-25): [This region consists of]
@@ -2142,7 +2170,8 @@ Zone Asia/Krasnoyarsk	 6:11:20 -	LMT	1920 Jan  6
 			 6:00	-	KRAT	1930 Jun 21 # Krasnoyarsk Time
 			 7:00	Russia	KRA%sT	1991 Mar 31 2:00s
 			 6:00	Russia	KRA%sT	1992 Jan 19 2:00s
-			 7:00	Russia	KRA%sT
+			 7:00	Russia	KRA%sT	2011 Mar 27 2:00s
+			 8:00	-	KRAT
 #
 # From Oscar van Vlijmen (2001-08-25): [This region consists of]
 # Respublika Buryatiya, Irkutskaya oblast',
@@ -2152,7 +2181,8 @@ Zone Asia/Irkutsk	 6:57:20 -	LMT	1880
 			 7:00	-	IRKT	1930 Jun 21 # Irkutsk Time
 			 8:00	Russia	IRK%sT	1991 Mar 31 2:00s
 			 7:00	Russia	IRK%sT	1992 Jan 19 2:00s
-			 8:00	Russia	IRK%sT
+			 8:00	Russia	IRK%sT	2011 Mar 27 2:00s
+			 9:00	-	IRKT
 #
 # From Oscar van Vlijmen (2003-10-18): [This region consists of]
 # Aginskij Buryatskij avtonomnyj okrug, Amurskaya oblast',
@@ -2175,7 +2205,8 @@ Zone Asia/Yakutsk	 8:38:40 -	LMT	1919 Dec 15
 			 8:00	-	YAKT	1930 Jun 21 # Yakutsk Time
 			 9:00	Russia	YAK%sT	1991 Mar 31 2:00s
 			 8:00	Russia	YAK%sT	1992 Jan 19 2:00s
-			 9:00	Russia	YAK%sT
+			 9:00	Russia	YAK%sT	2011 Mar 27 2:00s
+			 10:00	-	YAKT
 #
 # From Oscar van Vlijmen (2003-10-18): [This region consists of]
 # Evrejskaya avtonomnaya oblast', Khabarovskij kraj, Primorskij kraj,
@@ -2188,7 +2219,8 @@ Zone Asia/Vladivostok	 8:47:44 -	LMT	1922 Nov 15
 			 9:00	-	VLAT	1930 Jun 21 # Vladivostok Time
 			10:00	Russia	VLA%sT	1991 Mar 31 2:00s
 			 9:00	Russia	VLA%sST	1992 Jan 19 2:00s
-			10:00	Russia	VLA%sT
+			10:00	Russia	VLA%sT	2011 Mar 27 2:00s
+			11:00	-	VLAT
 #
 # Sakhalinskaya oblast'.
 # The Zone name should be Yuzhno-Sakhalinsk, but that's too long.
@@ -2198,7 +2230,8 @@ Zone Asia/Sakhalin	 9:30:48 -	LMT	1905 Aug 23
 			11:00	Russia	SAK%sT	1991 Mar 31 2:00s # Sakhalin T.
 			10:00	Russia	SAK%sT	1992 Jan 19 2:00s
 			11:00	Russia	SAK%sT	1997 Mar lastSun 2:00s
-			10:00	Russia	SAK%sT
+			10:00	Russia	SAK%sT	2011 Mar 27 2:00s
+			11:00	-	SAKT
 #
 # From Oscar van Vlijmen (2003-10-18): [This region consists of]
 # Magadanskaya oblast', Respublika Sakha (Yakutiya).
@@ -2211,7 +2244,8 @@ Zone Asia/Magadan	10:03:12 -	LMT	1924 May  2
 			10:00	-	MAGT	1930 Jun 21 # Magadan Time
 			11:00	Russia	MAG%sT	1991 Mar 31 2:00s
 			10:00	Russia	MAG%sT	1992 Jan 19 2:00s
-			11:00	Russia	MAG%sT
+			11:00	Russia	MAG%sT	2011 Mar 27 2:00s
+			12:00	-	MAGT
 #
 # From Oscar van Vlijmen (2001-08-25): [This region consists of]
 # Kamchatskaya oblast', Koryakskij avtonomnyj okrug.
@@ -2222,7 +2256,8 @@ Zone Asia/Kamchatka	10:34:36 -	LMT	1922 Nov 10
 			12:00	Russia	PET%sT	1991 Mar 31 2:00s
 			11:00	Russia	PET%sT	1992 Jan 19 2:00s
 			12:00	Russia	PET%sT	2010 Mar 28 2:00s
-			11:00	Russia	PET%sT
+			11:00	Russia	PET%sT	2011 Mar 27 2:00s
+			12:00	-	PETT
 #
 # Chukotskij avtonomnyj okrug
 Zone Asia/Anadyr	11:49:56 -	LMT	1924 May  2
@@ -2231,7 +2266,8 @@ Zone Asia/Anadyr	11:49:56 -	LMT	1924 May  2
 			12:00	Russia	ANA%sT	1991 Mar 31 2:00s
 			11:00	Russia	ANA%sT	1992 Jan 19 2:00s
 			12:00	Russia	ANA%sT	2010 Mar 28 2:00s
-			11:00	Russia	ANA%sT
+			11:00	Russia	ANA%sT	2011 Mar 27 2:00s
+			12:00	-	ANAT
 
 # Serbia
 # Zone	NAME		GMTOFF	RULES	FORMAT	[UNTIL]
diff --git a/iso3166.tab b/iso3166.tab
index b8a2592c008..4bc420c72d5 100644
--- a/iso3166.tab
+++ b/iso3166.tab
@@ -1,5 +1,5 @@
 # 
-# @(#)iso3166.tab	8.6
+# @(#)iso3166.tab	8.9
 # This file is in the public domain, so clarified as of
 # 2009-05-17 by Arthur David Olson.
 # ISO 3166 alpha-2 country codes
@@ -21,6 +21,10 @@
 #
 # Lines beginning with `#' are comments.
 #
+# From Arthur David Olson (2011-06-15):
+# Resynchronized today with the ISO3116 site
+# (deleting AN and adding BQ, CW, and SX).
+#
 #country-
 #code	country name
 AD	Andorra
@@ -30,7 +34,6 @@ AG	Antigua & Barbuda
 AI	Anguilla
 AL	Albania
 AM	Armenia
-AN	Netherlands Antilles
 AO	Angola
 AQ	Antarctica
 AR	Argentina
@@ -53,6 +56,7 @@ BL	St Barthelemy
 BM	Bermuda
 BN	Brunei
 BO	Bolivia
+BQ	Bonaire Sint Eustatius & Saba
 BR	Brazil
 BS	Bahamas
 BT	Bhutan
@@ -75,6 +79,7 @@ CO	Colombia
 CR	Costa Rica
 CU	Cuba
 CV	Cape Verde
+CW	Curacao
 CX	Christmas Island
 CY	Cyprus
 CZ	Czech Republic
@@ -231,6 +236,7 @@ SO	Somalia
 SR	Suriname
 ST	Sao Tome & Principe
 SV	El Salvador
+SX	Sint Maarten
 SY	Syria
 SZ	Swaziland
 TC	Turks & Caicos Is
diff --git a/southamerica b/southamerica
index 919dc25beb2..90f531d712f 100644
--- a/southamerica
+++ b/southamerica
@@ -1,5 +1,5 @@
 # 
-# @(#)southamerica	8.49
+# @(#)southamerica	8.50
 # This file is in the public domain, so clarified as of
 # 2009-05-17 by Arthur David Olson.
 
@@ -1276,6 +1276,14 @@ Zone	America/Curacao	-4:35:44 -	LMT	1912 Feb 12	# Willemstad
 			-4:30	-	ANT	1965 # Netherlands Antilles Time
 			-4:00	-	AST
 
+# From Arthur David Olson (2011-06-15):
+# At least for now, use links for places with new iso3166 codes.
+# The name "Lower Prince's Quarter" is both longer than fourteen charaters
+# and contains an apostrophe; use "Lower_Princes" below.
+
+Link	America/Curacao	America/Lower_Princes # Sint Maarten
+Link	America/Curacao	America/Kralendijk # Bonaire, Sint Estatius and Saba
+
 # Ecuador
 #
 # From Paul Eggert (2007-03-04):
diff --git a/zone.tab b/zone.tab
index b06ace4282b..fce3b985c09 100644
--- a/zone.tab
+++ b/zone.tab
@@ -1,5 +1,5 @@
 # 
-# @(#)zone.tab	8.43
+# @(#)zone.tab	8.45
 # This file is in the public domain, so clarified as of
 # 2009-05-17 by Arthur David Olson.
 #
@@ -32,7 +32,6 @@ AG	+1703-06148	America/Antigua
 AI	+1812-06304	America/Anguilla
 AL	+4120+01950	Europe/Tirane
 AM	+4011+04430	Asia/Yerevan
-AN	+1211-06900	America/Curacao
 AO	-0848+01314	Africa/Luanda
 AQ	-7750+16636	Antarctica/McMurdo	McMurdo Station, Ross Island
 AQ	-9000+00000	Antarctica/South_Pole	Amundsen-Scott Station, South Pole
@@ -87,6 +86,7 @@ BL	+1753-06251	America/St_Barthelemy
 BM	+3217-06446	Atlantic/Bermuda
 BN	+0456+11455	Asia/Brunei
 BO	-1630-06809	America/La_Paz
+BQ	+120903-0681636	America/Kralendijk
 BR	-0351-03225	America/Noronha	Atlantic islands
 BR	-0127-04829	America/Belem	Amapa, E Para
 BR	-0343-03830	America/Fortaleza	NE Brazil (MA, PI, CE, RN, PB)
@@ -155,6 +155,7 @@ CO	+0436-07405	America/Bogota
 CR	+0956-08405	America/Costa_Rica
 CU	+2308-08222	America/Havana
 CV	+1455-02331	Atlantic/Cape_Verde
+CW	+1211-06900	America/Curacao
 CX	-1025+10543	Indian/Christmas
 CY	+3510+03322	Asia/Nicosia
 CZ	+5005+01426	Europe/Prague
@@ -362,6 +363,7 @@ SO	+0204+04522	Africa/Mogadishu
 SR	+0550-05510	America/Paramaribo
 ST	+0020+00644	Africa/Sao_Tome
 SV	+1342-08912	America/El_Salvador
+SX	+180305-0630250	America/Lower_Princes
 SY	+3330+03618	Asia/Damascus
 SZ	-2618+03106	Africa/Mbabane
 TC	+2128-07108	America/Grand_Turk

From e6df989fe417530d0f5f3390b19eb8373289cfab Mon Sep 17 00:00:00 2001
From: Edwin Groothuis 
Date: Tue, 28 Jun 2011 10:38:12 +0000
Subject: [PATCH 38/39] Remove AN again now that tzdata2011h has been imported.

---
 share/misc/iso3166 | 1 -
 1 file changed, 1 deletion(-)

diff --git a/share/misc/iso3166 b/share/misc/iso3166
index d8d5972c9cb..23c9bd65e31 100644
--- a/share/misc/iso3166
+++ b/share/misc/iso3166
@@ -176,7 +176,6 @@ NA	NAM	516	Namibia
 NR	NRU	520	Nauru
 NP	NPL	524	Nepal
 NL	NLD	528	Netherlands
-AN	ANT	530	Netherlands Antilles
 NC	NCL	540	New Caledonia
 NZ	NZL	554	New Zealand
 NI	NIC	558	Nicaragua

From 877854f6679c98c4c669d214d5c174cb9a4d3f2f Mon Sep 17 00:00:00 2001
From: "Sergey A. Osokin" 
Date: Tue, 28 Jun 2011 12:32:24 +0000
Subject: [PATCH 39/39] Remove needless file due to Russia scraps DST in 2011.

---
 .../calendar/calendars/ru_RU.KOI8-R/calendar.all |  1 -
 .../calendar/calendars/ru_RU.KOI8-R/calendar.msk | 16 ----------------
 2 files changed, 17 deletions(-)
 delete mode 100644 usr.bin/calendar/calendars/ru_RU.KOI8-R/calendar.msk

diff --git a/usr.bin/calendar/calendars/ru_RU.KOI8-R/calendar.all b/usr.bin/calendar/calendars/ru_RU.KOI8-R/calendar.all
index b2de01ee8e5..25b7b595c47 100644
--- a/usr.bin/calendar/calendars/ru_RU.KOI8-R/calendar.all
+++ b/usr.bin/calendar/calendars/ru_RU.KOI8-R/calendar.all
@@ -10,7 +10,6 @@
 #include 
 #include 
 #include 
-#include 
 #include 
 #include 
 
diff --git a/usr.bin/calendar/calendars/ru_RU.KOI8-R/calendar.msk b/usr.bin/calendar/calendars/ru_RU.KOI8-R/calendar.msk
deleted file mode 100644
index 5e279859b7f..00000000000
--- a/usr.bin/calendar/calendars/ru_RU.KOI8-R/calendar.msk
+++ /dev/null
@@ -1,16 +0,0 @@
-/*
- * Перевод часов для московской временной зоны
- *
- * $FreeBSD$
- */
-
-#ifndef _ru_RU_KOI8_R_msk_
-#define _ru_RU_KOI8_R_msk_
-
-LANG=ru_RU.KOI8-R
-
-03/SunLast	Начало московского летнего времени; часы переводятся вперед
-10/SunLast	Конец московского летнего времени; часы переводятся назад
-
-#endif /* !_ru_RU_KOI8_R_msk_ */
-