iproute2/dcb/dcb_dcbx.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0+
   2
   3#include <errno.h>
   4#include <inttypes.h>
   5#include <stdio.h>
   6#include <linux/dcbnl.h>
   7
   8#include "dcb.h"
   9#include "utils.h"
  10
  11static void dcb_dcbx_help_set(void)
  12{
  13        fprintf(stderr,
  14                "Usage: dcb dcbx set dev STRING\n"
  15                "           [ host | lld-managed ]\n"
  16                "           [ cee | ieee ] [ static ]\n"
  17                "\n"
  18        );
  19}
  20
  21static void dcb_dcbx_help_show(void)
  22{
  23        fprintf(stderr,
  24                "Usage: dcb dcbx show dev STRING\n"
  25                "\n"
  26        );
  27}
  28
  29static void dcb_dcbx_help(void)
  30{
  31        fprintf(stderr,
  32                "Usage: dcb dcbx help\n"
  33                "\n"
  34        );
  35        dcb_dcbx_help_show();
  36        dcb_dcbx_help_set();
  37}
  38
  39struct dcb_dcbx_flag {
  40        __u8 value;
  41        const char *key_fp;
  42        const char *key_json;
  43};
  44
  45static struct dcb_dcbx_flag dcb_dcbx_flags[] = {
  46        {DCB_CAP_DCBX_HOST, "host"},
  47        {DCB_CAP_DCBX_LLD_MANAGED, "lld-managed", "lld_managed"},
  48        {DCB_CAP_DCBX_VER_CEE, "cee"},
  49        {DCB_CAP_DCBX_VER_IEEE, "ieee"},
  50        {DCB_CAP_DCBX_STATIC, "static"},
  51};
  52
  53static void dcb_dcbx_print(__u8 dcbx)
  54{
  55        int bit;
  56        int i;
  57
  58        while ((bit = ffs(dcbx))) {
  59                bool found = false;
  60
  61                bit--;
  62                for (i = 0; i < ARRAY_SIZE(dcb_dcbx_flags); i++) {
  63                        struct dcb_dcbx_flag *flag = &dcb_dcbx_flags[i];
  64
  65                        if (flag->value == 1 << bit) {
  66                                print_bool(PRINT_JSON, flag->key_json ?: flag->key_fp,
  67                                           NULL, true);
  68                                print_string(PRINT_FP, NULL, "%s ", flag->key_fp);
  69                                found = true;
  70                                break;
  71                        }
  72                }
  73
  74                if (!found)
  75                        fprintf(stderr, "Unknown DCBX bit %#x.\n", 1 << bit);
  76
  77                dcbx &= ~(1 << bit);
  78        }
  79
  80        print_nl();
  81}
  82
  83static int dcb_dcbx_get(struct dcb *dcb, const char *dev, __u8 *dcbx)
  84{
  85        __u16 payload_len;
  86        void *payload;
  87        int err;
  88
  89        err = dcb_get_attribute_bare(dcb, DCB_CMD_IEEE_GET, dev, DCB_ATTR_DCBX,
  90                                     &payload, &payload_len);
  91        if (err != 0)
  92                return err;
  93
  94        if (payload_len != 1) {
  95                fprintf(stderr, "DCB_ATTR_DCBX payload has size %d, expected 1.\n",
  96                        payload_len);
  97                return -EINVAL;
  98        }
  99        *dcbx = *(__u8 *) payload;
 100        return 0;
 101}
 102
 103static int dcb_dcbx_set(struct dcb *dcb, const char *dev, __u8 dcbx)
 104{
 105        return dcb_set_attribute_bare(dcb, DCB_CMD_SDCBX, dev, DCB_ATTR_DCBX,
 106                                      &dcbx, 1, DCB_ATTR_DCBX);
 107}
 108
 109static int dcb_cmd_dcbx_set(struct dcb *dcb, const char *dev, int argc, char **argv)
 110{
 111        __u8 dcbx = 0;
 112        __u8 i;
 113
 114        if (!argc) {
 115                dcb_dcbx_help_set();
 116                return 0;
 117        }
 118
 119        do {
 120                if (matches(*argv, "help") == 0) {
 121                        dcb_dcbx_help_set();
 122                        return 0;
 123                }
 124
 125                for (i = 0; i < ARRAY_SIZE(dcb_dcbx_flags); i++) {
 126                        struct dcb_dcbx_flag *flag = &dcb_dcbx_flags[i];
 127
 128                        if (matches(*argv, flag->key_fp) == 0) {
 129                                dcbx |= flag->value;
 130                                NEXT_ARG_FWD();
 131                                goto next;
 132                        }
 133                }
 134
 135                fprintf(stderr, "What is \"%s\"?\n", *argv);
 136                dcb_dcbx_help_set();
 137                return -EINVAL;
 138
 139next:
 140                ;
 141        } while (argc > 0);
 142
 143        return dcb_dcbx_set(dcb, dev, dcbx);
 144}
 145
 146static int dcb_cmd_dcbx_show(struct dcb *dcb, const char *dev, int argc, char **argv)
 147{
 148        __u8 dcbx;
 149        int ret;
 150
 151        ret = dcb_dcbx_get(dcb, dev, &dcbx);
 152        if (ret != 0)
 153                return ret;
 154
 155        while (argc > 0) {
 156                if (matches(*argv, "help") == 0) {
 157                        dcb_dcbx_help_show();
 158                        return 0;
 159                } else {
 160                        fprintf(stderr, "What is \"%s\"?\n", *argv);
 161                        dcb_dcbx_help_show();
 162                        return -EINVAL;
 163                }
 164
 165                NEXT_ARG_FWD();
 166        }
 167
 168        open_json_object(NULL);
 169        dcb_dcbx_print(dcbx);
 170        close_json_object();
 171        return 0;
 172}
 173
 174int dcb_cmd_dcbx(struct dcb *dcb, int argc, char **argv)
 175{
 176        if (!argc || matches(*argv, "help") == 0) {
 177                dcb_dcbx_help();
 178                return 0;
 179        } else if (matches(*argv, "show") == 0) {
 180                NEXT_ARG_FWD();
 181                return dcb_cmd_parse_dev(dcb, argc, argv,
 182                                         dcb_cmd_dcbx_show, dcb_dcbx_help_show);
 183        } else if (matches(*argv, "set") == 0) {
 184                NEXT_ARG_FWD();
 185                return dcb_cmd_parse_dev(dcb, argc, argv,
 186                                         dcb_cmd_dcbx_set, dcb_dcbx_help_set);
 187        } else {
 188                fprintf(stderr, "What is \"%s\"?\n", *argv);
 189                dcb_dcbx_help();
 190                return -EINVAL;
 191        }
 192}
 193