netlink.c 1.4 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364
  1. // SPDX-License-Identifier: GPL-2.0
  2. /* Copyright 2022 NXP
  3. */
  4. #include <linux/netdevice.h>
  5. #include <net/rtnetlink.h>
  6. #include "netlink.h"
  7. #include "user.h"
  8. static const struct nla_policy dsa_policy[IFLA_DSA_MAX + 1] = {
  9. [IFLA_DSA_CONDUIT] = { .type = NLA_U32 },
  10. };
  11. static int dsa_changelink(struct net_device *dev, struct nlattr *tb[],
  12. struct nlattr *data[],
  13. struct netlink_ext_ack *extack)
  14. {
  15. int err;
  16. if (!data)
  17. return 0;
  18. if (data[IFLA_DSA_CONDUIT]) {
  19. u32 ifindex = nla_get_u32(data[IFLA_DSA_CONDUIT]);
  20. struct net_device *conduit;
  21. conduit = __dev_get_by_index(dev_net(dev), ifindex);
  22. if (!conduit)
  23. return -EINVAL;
  24. err = dsa_user_change_conduit(dev, conduit, extack);
  25. if (err)
  26. return err;
  27. }
  28. return 0;
  29. }
  30. static size_t dsa_get_size(const struct net_device *dev)
  31. {
  32. return nla_total_size(sizeof(u32)) + /* IFLA_DSA_CONDUIT */
  33. 0;
  34. }
  35. static int dsa_fill_info(struct sk_buff *skb, const struct net_device *dev)
  36. {
  37. struct net_device *conduit = dsa_user_to_conduit(dev);
  38. if (nla_put_u32(skb, IFLA_DSA_CONDUIT, conduit->ifindex))
  39. return -EMSGSIZE;
  40. return 0;
  41. }
  42. struct rtnl_link_ops dsa_link_ops __read_mostly = {
  43. .kind = "dsa",
  44. .priv_size = sizeof(struct dsa_port),
  45. .maxtype = IFLA_DSA_MAX,
  46. .policy = dsa_policy,
  47. .changelink = dsa_changelink,
  48. .get_size = dsa_get_size,
  49. .fill_info = dsa_fill_info,
  50. .netns_refund = true,
  51. };