]> Git Repo - linux.git/commitdiff
xfrm: add extack to xfrm_alloc_userspi
authorSabrina Dubroca <[email protected]>
Thu, 24 Nov 2022 14:43:43 +0000 (15:43 +0100)
committerSteffen Klassert <[email protected]>
Fri, 25 Nov 2022 09:11:42 +0000 (10:11 +0100)
Signed-off-by: Sabrina Dubroca <[email protected]>
Signed-off-by: Steffen Klassert <[email protected]>
include/net/xfrm.h
net/key/af_key.c
net/xfrm/xfrm_state.c
net/xfrm/xfrm_user.c

index 576566bd0be95274d758035196c4e6edd6654b94..e0cc6791c001c293e43c1341fb9e0cc97da8a8fc 100644 (file)
@@ -1681,8 +1681,9 @@ struct xfrm_policy *xfrm_policy_byid(struct net *net,
 int xfrm_policy_flush(struct net *net, u8 type, bool task_valid);
 void xfrm_policy_hash_rebuild(struct net *net);
 u32 xfrm_get_acqseq(void);
-int verify_spi_info(u8 proto, u32 min, u32 max);
-int xfrm_alloc_spi(struct xfrm_state *x, u32 minspi, u32 maxspi);
+int verify_spi_info(u8 proto, u32 min, u32 max, struct netlink_ext_ack *extack);
+int xfrm_alloc_spi(struct xfrm_state *x, u32 minspi, u32 maxspi,
+                  struct netlink_ext_ack *extack);
 struct xfrm_state *xfrm_find_acq(struct net *net, const struct xfrm_mark *mark,
                                 u8 mode, u32 reqid, u32 if_id, u8 proto,
                                 const xfrm_address_t *daddr,
index 7f4ff5fe22576acb77d19dcfbc0c001331977197..e1d2155605aa0d7865274d879ff13681b4c65efb 100644 (file)
@@ -1377,13 +1377,13 @@ static int pfkey_getspi(struct sock *sk, struct sk_buff *skb, const struct sadb_
                max_spi = range->sadb_spirange_max;
        }
 
-       err = verify_spi_info(x->id.proto, min_spi, max_spi);
+       err = verify_spi_info(x->id.proto, min_spi, max_spi, NULL);
        if (err) {
                xfrm_state_put(x);
                return err;
        }
 
-       err = xfrm_alloc_spi(x, min_spi, max_spi);
+       err = xfrm_alloc_spi(x, min_spi, max_spi, NULL);
        resp_skb = err ? ERR_PTR(err) : pfkey_xfrm_state2msg(x);
 
        if (IS_ERR(resp_skb)) {
index 81df34b3da6ed5141760e7415a57fceb2de3a647..d0ae17e3bb38c64216e916bb51943c5df0ab7bde 100644 (file)
@@ -2017,7 +2017,7 @@ u32 xfrm_get_acqseq(void)
 }
 EXPORT_SYMBOL(xfrm_get_acqseq);
 
-int verify_spi_info(u8 proto, u32 min, u32 max)
+int verify_spi_info(u8 proto, u32 min, u32 max, struct netlink_ext_ack *extack)
 {
        switch (proto) {
        case IPPROTO_AH:
@@ -2026,22 +2026,28 @@ int verify_spi_info(u8 proto, u32 min, u32 max)
 
        case IPPROTO_COMP:
                /* IPCOMP spi is 16-bits. */
-               if (max >= 0x10000)
+               if (max >= 0x10000) {
+                       NL_SET_ERR_MSG(extack, "IPCOMP SPI must be <= 65535");
                        return -EINVAL;
+               }
                break;
 
        default:
+               NL_SET_ERR_MSG(extack, "Invalid protocol, must be one of AH, ESP, IPCOMP");
                return -EINVAL;
        }
 
-       if (min > max)
+       if (min > max) {
+               NL_SET_ERR_MSG(extack, "Invalid SPI range: min > max");
                return -EINVAL;
+       }
 
        return 0;
 }
 EXPORT_SYMBOL(verify_spi_info);
 
-int xfrm_alloc_spi(struct xfrm_state *x, u32 low, u32 high)
+int xfrm_alloc_spi(struct xfrm_state *x, u32 low, u32 high,
+                  struct netlink_ext_ack *extack)
 {
        struct net *net = xs_net(x);
        unsigned int h;
@@ -2053,8 +2059,10 @@ int xfrm_alloc_spi(struct xfrm_state *x, u32 low, u32 high)
        u32 mark = x->mark.v & x->mark.m;
 
        spin_lock_bh(&x->lock);
-       if (x->km.state == XFRM_STATE_DEAD)
+       if (x->km.state == XFRM_STATE_DEAD) {
+               NL_SET_ERR_MSG(extack, "Target ACQUIRE is in DEAD state");
                goto unlock;
+       }
 
        err = 0;
        if (x->id.spi)
@@ -2065,6 +2073,7 @@ int xfrm_alloc_spi(struct xfrm_state *x, u32 low, u32 high)
        if (minspi == maxspi) {
                x0 = xfrm_state_lookup(net, mark, &x->id.daddr, minspi, x->id.proto, x->props.family);
                if (x0) {
+                       NL_SET_ERR_MSG(extack, "Requested SPI is already in use");
                        xfrm_state_put(x0);
                        goto unlock;
                }
@@ -2089,6 +2098,8 @@ int xfrm_alloc_spi(struct xfrm_state *x, u32 low, u32 high)
                spin_unlock_bh(&net->xfrm.xfrm_state_lock);
 
                err = 0;
+       } else {
+               NL_SET_ERR_MSG(extack, "No SPI available in the requested range");
        }
 
 unlock:
index c5d6a92d73cbf4a42be004830a9cbba7cd6b4897..5c280e04e02c219c7dec8b30b65c9913ac0dba15 100644 (file)
@@ -1523,7 +1523,7 @@ static int xfrm_alloc_userspi(struct sk_buff *skb, struct nlmsghdr *nlh,
        u32 if_id = 0;
 
        p = nlmsg_data(nlh);
-       err = verify_spi_info(p->info.id.proto, p->min, p->max);
+       err = verify_spi_info(p->info.id.proto, p->min, p->max, extack);
        if (err)
                goto out_noput;
 
@@ -1551,10 +1551,12 @@ static int xfrm_alloc_userspi(struct sk_buff *skb, struct nlmsghdr *nlh,
                                  &p->info.saddr, 1,
                                  family);
        err = -ENOENT;
-       if (!x)
+       if (!x) {
+               NL_SET_ERR_MSG(extack, "Target ACQUIRE not found");
                goto out_noput;
+       }
 
-       err = xfrm_alloc_spi(x, p->min, p->max);
+       err = xfrm_alloc_spi(x, p->min, p->max, extack);
        if (err)
                goto out;
 
This page took 0.065931 seconds and 4 git commands to generate.