aboutsummaryrefslogtreecommitdiff
path: root/src/or/connection_edge.c
diff options
context:
space:
mode:
authorNick Mathewson <nickm@torproject.org>2006-08-10 09:01:54 +0000
committerNick Mathewson <nickm@torproject.org>2006-08-10 09:01:54 +0000
commitcd560d85284f27f25a676dbc40849cfa97b9e662 (patch)
treede3ee7fce796aa6c9c476b9a2f6845cb45b2aa0e /src/or/connection_edge.c
parentd893d8c52ed7a66eaea630cffe94cdaf82fbc99d (diff)
downloadtor-cd560d85284f27f25a676dbc40849cfa97b9e662.tar
tor-cd560d85284f27f25a676dbc40849cfa97b9e662.tar.gz
r7301@Kushana: nickm | 2006-08-10 01:41:27 -0700
Only open /dev/pf once. svn:r7009
Diffstat (limited to 'src/or/connection_edge.c')
-rw-r--r--src/or/connection_edge.c47
1 files changed, 30 insertions, 17 deletions
diff --git a/src/or/connection_edge.c b/src/or/connection_edge.c
index 62fa699e0..12ffb3fa2 100644
--- a/src/or/connection_edge.c
+++ b/src/or/connection_edge.c
@@ -1236,6 +1236,33 @@ connection_ap_handshake_rewrite_and_attach(edge_connection_t *conn,
return 0; /* unreached but keeps the compiler happy */
}
+#ifdef TRANS_PF
+static int pf_socket = -1;
+static int
+get_pf_socket(void)
+{
+ int pf;
+ /* Ideally, this should be opened before dropping privs. */
+ if (pf_socket >= 0)
+ return pf_socket;
+
+#ifdef OPENBSD
+ /* only works on OpenBSD */
+ pf = open("/dev/pf", O_RDONLY);
+#else
+ /* works on NetBSD and FreeBSD */
+ pf = open("/dev/pf", O_RDWR);
+#endif
+
+ if (pf < 0) {
+ log_warn(LD_NET, "open(\"/dev/pf\") failed: %s", strerror(errno));
+ return -1;
+ }
+
+ pf_socket = pf;
+}
+#endif
+
/** Fetch the original destination address and port from a
* system-specific interface and put them into a
* socks_request_t as if they came from a socks request.
@@ -1287,29 +1314,15 @@ connection_ap_get_original_destination(edge_connection_t *conn,
pnl.sport = htons(conn->_base.port);
pnl.daddr.v4.s_addr = proxy_addr.sin_addr.s_addr;
pnl.dport = proxy_addr.sin_port;
-
- /* XXX We should open the /dev/pf device once and close it at cleanup time
- * instead of reopening it for every connection. Ideally, it should be
- * opened before dropping privs. */
-#ifdef OPENBSD
- /* only works on OpenBSD */
- pf = open("/dev/pf", O_RDONLY);
-#else
- /* works on NetBSD and FreeBSD */
- pf = open("/dev/pf", O_RDWR);
-#endif
-
- if (pf < 0) {
- log_warn(LD_NET, "open(\"/dev/pf\") failed: %s", strerror(errno));
+
+ pf = get_pf_socket();
+ if (pf<0)
return -1;
- }
if (ioctl(pf, DIOCNATLOOK, &pnl) < 0) {
log_warn(LD_NET, "ioctl(DIOCNATLOOK) failed: %s", strerror(errno));
- close(pf);
return -1;
}
- close(pf);
tor_inet_ntoa(&pnl.rdaddr.v4, tmpbuf, sizeof(tmpbuf));
strlcpy(req->address, tmpbuf, sizeof(req->address));