| From 791bb3fcafcedd11f9066da9fee9342ecb6904d0 Mon Sep 17 00:00:00 2001 |
| From: Mark Starovoytov <mstarovoitov@marvell.com> |
| Date: Wed, 25 Mar 2020 16:01:34 +0300 |
| Subject: net: macsec: add support for specifying offload upon link creation |
| |
| This patch adds new netlink attribute to allow a user to (optionally) |
| specify the desired offload mode immediately upon MACSec link creation. |
| |
| Separate iproute patch will be required to support this from user space. |
| |
| Signed-off-by: Mark Starovoytov <mstarovoitov@marvell.com> |
| Signed-off-by: Igor Russkikh <irusskikh@marvell.com> |
| Signed-off-by: David S. Miller <davem@davemloft.net> |
| --- |
| drivers/net/macsec.c | 31 +++++++++++++++++++++++++++++-- |
| include/uapi/linux/if_link.h | 1 + |
| tools/include/uapi/linux/if_link.h | 1 + |
| 3 files changed, 31 insertions(+), 2 deletions(-) |
| |
| diff --git a/drivers/net/macsec.c b/drivers/net/macsec.c |
| index 2dad91cba459c..da82d7f16a09d 100644 |
| --- a/drivers/net/macsec.c |
| +++ b/drivers/net/macsec.c |
| @@ -1469,6 +1469,11 @@ static struct net_device *get_dev_from_nl(struct net *net, |
| return dev; |
| } |
| |
| +static enum macsec_offload nla_get_offload(const struct nlattr *nla) |
| +{ |
| + return (__force enum macsec_offload)nla_get_u8(nla); |
| +} |
| + |
| static sci_t nla_get_sci(const struct nlattr *nla) |
| { |
| return (__force sci_t)nla_get_u64(nla); |
| @@ -4012,8 +4017,16 @@ static int macsec_newlink(struct net *net, struct net_device *dev, |
| |
| macsec->real_dev = real_dev; |
| |
| - /* MACsec offloading is off by default */ |
| - macsec->offload = MACSEC_OFFLOAD_OFF; |
| + if (data && data[IFLA_MACSEC_OFFLOAD]) |
| + macsec->offload = nla_get_offload(data[IFLA_MACSEC_OFFLOAD]); |
| + else |
| + /* MACsec offloading is off by default */ |
| + macsec->offload = MACSEC_OFFLOAD_OFF; |
| + |
| + /* Check if the offloading mode is supported by the underlying layers */ |
| + if (macsec->offload != MACSEC_OFFLOAD_OFF && |
| + !macsec_check_offload(macsec->offload, macsec)) |
| + return -EOPNOTSUPP; |
| |
| if (data && data[IFLA_MACSEC_ICV_LEN]) |
| icv_len = nla_get_u8(data[IFLA_MACSEC_ICV_LEN]); |
| @@ -4056,6 +4069,20 @@ static int macsec_newlink(struct net *net, struct net_device *dev, |
| goto del_dev; |
| } |
| |
| + /* If h/w offloading is available, propagate to the device */ |
| + if (macsec_is_offloaded(macsec)) { |
| + const struct macsec_ops *ops; |
| + struct macsec_context ctx; |
| + |
| + ops = macsec_get_ops(macsec, &ctx); |
| + if (ops) { |
| + ctx.secy = &macsec->secy; |
| + err = macsec_offload(ops->mdo_add_secy, &ctx); |
| + if (err) |
| + goto del_dev; |
| + } |
| + } |
| + |
| err = register_macsec_dev(real_dev, dev); |
| if (err < 0) |
| goto del_dev; |
| diff --git a/include/uapi/linux/if_link.h b/include/uapi/linux/if_link.h |
| index d6ccd0105c050..e204c3e4dce10 100644 |
| --- a/include/uapi/linux/if_link.h |
| +++ b/include/uapi/linux/if_link.h |
| @@ -463,6 +463,7 @@ enum { |
| IFLA_MACSEC_REPLAY_PROTECT, |
| IFLA_MACSEC_VALIDATION, |
| IFLA_MACSEC_PAD, |
| + IFLA_MACSEC_OFFLOAD, |
| __IFLA_MACSEC_MAX, |
| }; |
| |
| diff --git a/tools/include/uapi/linux/if_link.h b/tools/include/uapi/linux/if_link.h |
| index 771371d5b9960..24cf6fe075f74 100644 |
| --- a/tools/include/uapi/linux/if_link.h |
| +++ b/tools/include/uapi/linux/if_link.h |
| @@ -463,6 +463,7 @@ enum { |
| IFLA_MACSEC_REPLAY_PROTECT, |
| IFLA_MACSEC_VALIDATION, |
| IFLA_MACSEC_PAD, |
| + IFLA_MACSEC_OFFLOAD, |
| __IFLA_MACSEC_MAX, |
| }; |
| |
| -- |
| cgit 1.2.3-1.el7 |
| |