Commit 6a787d6f authored by David S. Miller's avatar David S. Miller

Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/klassert/ipsec

Steffen Klassert says:

====================
1) Copy policy family in clone_policy, otherwise this can
   trigger a BUG_ON in af_key. From Herbert Xu.

2) Revert "xfrm: Fix stack-out-of-bounds read in xfrm_state_find."
   This added a regression with transport mode when no addresses
   are configured on the policy template.

Both patches are stable candidates.
====================
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parents d871c321 94802151
...@@ -1305,6 +1305,7 @@ static struct xfrm_policy *clone_policy(const struct xfrm_policy *old, int dir) ...@@ -1305,6 +1305,7 @@ static struct xfrm_policy *clone_policy(const struct xfrm_policy *old, int dir)
newp->xfrm_nr = old->xfrm_nr; newp->xfrm_nr = old->xfrm_nr;
newp->index = old->index; newp->index = old->index;
newp->type = old->type; newp->type = old->type;
newp->family = old->family;
memcpy(newp->xfrm_vec, old->xfrm_vec, memcpy(newp->xfrm_vec, old->xfrm_vec,
newp->xfrm_nr*sizeof(struct xfrm_tmpl)); newp->xfrm_nr*sizeof(struct xfrm_tmpl));
spin_lock_bh(&net->xfrm.xfrm_policy_lock); spin_lock_bh(&net->xfrm.xfrm_policy_lock);
...@@ -1360,29 +1361,36 @@ xfrm_tmpl_resolve_one(struct xfrm_policy *policy, const struct flowi *fl, ...@@ -1360,29 +1361,36 @@ xfrm_tmpl_resolve_one(struct xfrm_policy *policy, const struct flowi *fl,
struct net *net = xp_net(policy); struct net *net = xp_net(policy);
int nx; int nx;
int i, error; int i, error;
xfrm_address_t *daddr = xfrm_flowi_daddr(fl, family);
xfrm_address_t *saddr = xfrm_flowi_saddr(fl, family);
xfrm_address_t tmp; xfrm_address_t tmp;
for (nx = 0, i = 0; i < policy->xfrm_nr; i++) { for (nx = 0, i = 0; i < policy->xfrm_nr; i++) {
struct xfrm_state *x; struct xfrm_state *x;
xfrm_address_t *local; xfrm_address_t *remote = daddr;
xfrm_address_t *remote; xfrm_address_t *local = saddr;
struct xfrm_tmpl *tmpl = &policy->xfrm_vec[i]; struct xfrm_tmpl *tmpl = &policy->xfrm_vec[i];
remote = &tmpl->id.daddr; if (tmpl->mode == XFRM_MODE_TUNNEL ||
local = &tmpl->saddr; tmpl->mode == XFRM_MODE_BEET) {
if (xfrm_addr_any(local, tmpl->encap_family)) { remote = &tmpl->id.daddr;
error = xfrm_get_saddr(net, fl->flowi_oif, local = &tmpl->saddr;
&tmp, remote, if (xfrm_addr_any(local, tmpl->encap_family)) {
tmpl->encap_family, 0); error = xfrm_get_saddr(net, fl->flowi_oif,
if (error) &tmp, remote,
goto fail; tmpl->encap_family, 0);
local = &tmp; if (error)
goto fail;
local = &tmp;
}
} }
x = xfrm_state_find(remote, local, fl, tmpl, policy, &error, family); x = xfrm_state_find(remote, local, fl, tmpl, policy, &error, family);
if (x && x->km.state == XFRM_STATE_VALID) { if (x && x->km.state == XFRM_STATE_VALID) {
xfrm[nx++] = x; xfrm[nx++] = x;
daddr = remote;
saddr = local;
continue; continue;
} }
if (x) { if (x) {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment