summaryrefslogtreecommitdiffstats
path: root/sys/netpfil
diff options
context:
space:
mode:
authorglebius <glebius@FreeBSD.org>2014-08-22 13:39:56 +0000
committerglebius <glebius@FreeBSD.org>2014-08-22 13:39:56 +0000
commit3d5a7426d58b33e4f0df098287e5847aa755b457 (patch)
tree8701ca14178c4dba7639226703200dd1e4a6a8ff /sys/netpfil
parent396919643bc13b3760e21e882607f3e266425c74 (diff)
downloadFreeBSD-src-3d5a7426d58b33e4f0df098287e5847aa755b457.zip
FreeBSD-src-3d5a7426d58b33e4f0df098287e5847aa755b457.tar.gz
Merge r268492:
On machines with strict alignment copy pfsync_state_key from packet on stack to avoid unaligned access. PR: 187381
Diffstat (limited to 'sys/netpfil')
-rw-r--r--sys/netpfil/pf/if_pfsync.c41
1 files changed, 26 insertions, 15 deletions
diff --git a/sys/netpfil/pf/if_pfsync.c b/sys/netpfil/pf/if_pfsync.c
index 2afb668..ddd9d9b 100644
--- a/sys/netpfil/pf/if_pfsync.c
+++ b/sys/netpfil/pf/if_pfsync.c
@@ -400,6 +400,10 @@ static int
pfsync_state_import(struct pfsync_state *sp, u_int8_t flags)
{
struct pfsync_softc *sc = V_pfsyncif;
+#ifndef __NO_STRICT_ALIGNMENT
+ struct pfsync_state_key key[2];
+#endif
+ struct pfsync_state_key *kw, *ks;
struct pf_state *st = NULL;
struct pf_state_key *skw = NULL, *sks = NULL;
struct pf_rule *r = NULL;
@@ -449,12 +453,19 @@ pfsync_state_import(struct pfsync_state *sp, u_int8_t flags)
if ((skw = uma_zalloc(V_pf_state_key_z, M_NOWAIT)) == NULL)
goto cleanup;
- if (PF_ANEQ(&sp->key[PF_SK_WIRE].addr[0],
- &sp->key[PF_SK_STACK].addr[0], sp->af) ||
- PF_ANEQ(&sp->key[PF_SK_WIRE].addr[1],
- &sp->key[PF_SK_STACK].addr[1], sp->af) ||
- sp->key[PF_SK_WIRE].port[0] != sp->key[PF_SK_STACK].port[0] ||
- sp->key[PF_SK_WIRE].port[1] != sp->key[PF_SK_STACK].port[1]) {
+#ifndef __NO_STRICT_ALIGNMENT
+ bcopy(&sp->key, key, sizeof(struct pfsync_state_key) * 2);
+ kw = &key[PF_SK_WIRE];
+ ks = &key[PF_SK_STACK];
+#else
+ kw = &sp->key[PF_SK_WIRE];
+ ks = &sp->key[PF_SK_STACK];
+#endif
+
+ if (PF_ANEQ(&kw->addr[0], &ks->addr[0], sp->af) ||
+ PF_ANEQ(&kw->addr[1], &ks->addr[1], sp->af) ||
+ kw->port[0] != ks->port[0] ||
+ kw->port[1] != ks->port[1]) {
sks = uma_zalloc(V_pf_state_key_z, M_NOWAIT);
if (sks == NULL)
goto cleanup;
@@ -466,18 +477,18 @@ pfsync_state_import(struct pfsync_state *sp, u_int8_t flags)
pfsync_alloc_scrub_memory(&sp->dst, &st->dst))
goto cleanup;
- /* copy to state key(s) */
- skw->addr[0] = sp->key[PF_SK_WIRE].addr[0];
- skw->addr[1] = sp->key[PF_SK_WIRE].addr[1];
- skw->port[0] = sp->key[PF_SK_WIRE].port[0];
- skw->port[1] = sp->key[PF_SK_WIRE].port[1];
+ /* Copy to state key(s). */
+ skw->addr[0] = kw->addr[0];
+ skw->addr[1] = kw->addr[1];
+ skw->port[0] = kw->port[0];
+ skw->port[1] = kw->port[1];
skw->proto = sp->proto;
skw->af = sp->af;
if (sks != skw) {
- sks->addr[0] = sp->key[PF_SK_STACK].addr[0];
- sks->addr[1] = sp->key[PF_SK_STACK].addr[1];
- sks->port[0] = sp->key[PF_SK_STACK].port[0];
- sks->port[1] = sp->key[PF_SK_STACK].port[1];
+ sks->addr[0] = ks->addr[0];
+ sks->addr[1] = ks->addr[1];
+ sks->port[0] = ks->port[0];
+ sks->port[1] = ks->port[1];
sks->proto = sp->proto;
sks->af = sp->af;
}
OpenPOWER on IntegriCloud