xref: /aosp_15_r20/external/iproute2/ip/iplink_bond_slave.c (revision de1e4e894b0c224df933550f0afdecc354b238c4)
1*de1e4e89SAndroid Build Coastguard Worker /*
2*de1e4e89SAndroid Build Coastguard Worker  * iplink_bond_slave.c	Bonding slave device support
3*de1e4e89SAndroid Build Coastguard Worker  *
4*de1e4e89SAndroid Build Coastguard Worker  *              This program is free software; you can redistribute it and/or
5*de1e4e89SAndroid Build Coastguard Worker  *              modify it under the terms of the GNU General Public License
6*de1e4e89SAndroid Build Coastguard Worker  *              as published by the Free Software Foundation; either version
7*de1e4e89SAndroid Build Coastguard Worker  *              2 of the License, or (at your option) any later version.
8*de1e4e89SAndroid Build Coastguard Worker  *
9*de1e4e89SAndroid Build Coastguard Worker  * Authors:     Jiri Pirko <[email protected]>
10*de1e4e89SAndroid Build Coastguard Worker  */
11*de1e4e89SAndroid Build Coastguard Worker 
12*de1e4e89SAndroid Build Coastguard Worker #include <stdio.h>
13*de1e4e89SAndroid Build Coastguard Worker #include <sys/socket.h>
14*de1e4e89SAndroid Build Coastguard Worker #include <linux/if_bonding.h>
15*de1e4e89SAndroid Build Coastguard Worker 
16*de1e4e89SAndroid Build Coastguard Worker #include "rt_names.h"
17*de1e4e89SAndroid Build Coastguard Worker #include "utils.h"
18*de1e4e89SAndroid Build Coastguard Worker #include "ip_common.h"
19*de1e4e89SAndroid Build Coastguard Worker 
print_explain(FILE * f)20*de1e4e89SAndroid Build Coastguard Worker static void print_explain(FILE *f)
21*de1e4e89SAndroid Build Coastguard Worker {
22*de1e4e89SAndroid Build Coastguard Worker 	fprintf(f, "Usage: ... bond_slave [ queue_id ID ]\n");
23*de1e4e89SAndroid Build Coastguard Worker }
24*de1e4e89SAndroid Build Coastguard Worker 
explain(void)25*de1e4e89SAndroid Build Coastguard Worker static void explain(void)
26*de1e4e89SAndroid Build Coastguard Worker {
27*de1e4e89SAndroid Build Coastguard Worker 	print_explain(stderr);
28*de1e4e89SAndroid Build Coastguard Worker }
29*de1e4e89SAndroid Build Coastguard Worker 
30*de1e4e89SAndroid Build Coastguard Worker static const char *slave_states[] = {
31*de1e4e89SAndroid Build Coastguard Worker 	[BOND_STATE_ACTIVE] = "ACTIVE",
32*de1e4e89SAndroid Build Coastguard Worker 	[BOND_STATE_BACKUP] = "BACKUP",
33*de1e4e89SAndroid Build Coastguard Worker };
34*de1e4e89SAndroid Build Coastguard Worker 
print_slave_state(FILE * f,struct rtattr * tb)35*de1e4e89SAndroid Build Coastguard Worker static void print_slave_state(FILE *f, struct rtattr *tb)
36*de1e4e89SAndroid Build Coastguard Worker {
37*de1e4e89SAndroid Build Coastguard Worker 	unsigned int state = rta_getattr_u8(tb);
38*de1e4e89SAndroid Build Coastguard Worker 
39*de1e4e89SAndroid Build Coastguard Worker 	if (state >= ARRAY_SIZE(slave_states))
40*de1e4e89SAndroid Build Coastguard Worker 		print_int(PRINT_ANY, "state_index", "state %d ", state);
41*de1e4e89SAndroid Build Coastguard Worker 	else
42*de1e4e89SAndroid Build Coastguard Worker 		print_string(PRINT_ANY,
43*de1e4e89SAndroid Build Coastguard Worker 			     "state",
44*de1e4e89SAndroid Build Coastguard Worker 			     "state %s ",
45*de1e4e89SAndroid Build Coastguard Worker 			     slave_states[state]);
46*de1e4e89SAndroid Build Coastguard Worker }
47*de1e4e89SAndroid Build Coastguard Worker 
48*de1e4e89SAndroid Build Coastguard Worker static const char *slave_mii_status[] = {
49*de1e4e89SAndroid Build Coastguard Worker 	[BOND_LINK_UP] = "UP",
50*de1e4e89SAndroid Build Coastguard Worker 	[BOND_LINK_FAIL] = "GOING_DOWN",
51*de1e4e89SAndroid Build Coastguard Worker 	[BOND_LINK_DOWN] = "DOWN",
52*de1e4e89SAndroid Build Coastguard Worker 	[BOND_LINK_BACK] = "GOING_BACK",
53*de1e4e89SAndroid Build Coastguard Worker };
54*de1e4e89SAndroid Build Coastguard Worker 
print_slave_mii_status(FILE * f,struct rtattr * tb)55*de1e4e89SAndroid Build Coastguard Worker static void print_slave_mii_status(FILE *f, struct rtattr *tb)
56*de1e4e89SAndroid Build Coastguard Worker {
57*de1e4e89SAndroid Build Coastguard Worker 	unsigned int status = rta_getattr_u8(tb);
58*de1e4e89SAndroid Build Coastguard Worker 
59*de1e4e89SAndroid Build Coastguard Worker 	if (status >= ARRAY_SIZE(slave_mii_status))
60*de1e4e89SAndroid Build Coastguard Worker 		print_int(PRINT_ANY,
61*de1e4e89SAndroid Build Coastguard Worker 			  "mii_status_index",
62*de1e4e89SAndroid Build Coastguard Worker 			  "mii_status %d ",
63*de1e4e89SAndroid Build Coastguard Worker 			  status);
64*de1e4e89SAndroid Build Coastguard Worker 	else
65*de1e4e89SAndroid Build Coastguard Worker 		print_string(PRINT_ANY,
66*de1e4e89SAndroid Build Coastguard Worker 			     "mii_status",
67*de1e4e89SAndroid Build Coastguard Worker 			     "mii_status %s ",
68*de1e4e89SAndroid Build Coastguard Worker 			     slave_mii_status[status]);
69*de1e4e89SAndroid Build Coastguard Worker }
70*de1e4e89SAndroid Build Coastguard Worker 
bond_slave_print_opt(struct link_util * lu,FILE * f,struct rtattr * tb[])71*de1e4e89SAndroid Build Coastguard Worker static void bond_slave_print_opt(struct link_util *lu, FILE *f, struct rtattr *tb[])
72*de1e4e89SAndroid Build Coastguard Worker {
73*de1e4e89SAndroid Build Coastguard Worker 	SPRINT_BUF(b1);
74*de1e4e89SAndroid Build Coastguard Worker 	if (!tb)
75*de1e4e89SAndroid Build Coastguard Worker 		return;
76*de1e4e89SAndroid Build Coastguard Worker 
77*de1e4e89SAndroid Build Coastguard Worker 	if (tb[IFLA_BOND_SLAVE_STATE])
78*de1e4e89SAndroid Build Coastguard Worker 		print_slave_state(f, tb[IFLA_BOND_SLAVE_STATE]);
79*de1e4e89SAndroid Build Coastguard Worker 
80*de1e4e89SAndroid Build Coastguard Worker 	if (tb[IFLA_BOND_SLAVE_MII_STATUS])
81*de1e4e89SAndroid Build Coastguard Worker 		print_slave_mii_status(f, tb[IFLA_BOND_SLAVE_MII_STATUS]);
82*de1e4e89SAndroid Build Coastguard Worker 
83*de1e4e89SAndroid Build Coastguard Worker 	if (tb[IFLA_BOND_SLAVE_LINK_FAILURE_COUNT])
84*de1e4e89SAndroid Build Coastguard Worker 		print_int(PRINT_ANY,
85*de1e4e89SAndroid Build Coastguard Worker 			  "link_failure_count",
86*de1e4e89SAndroid Build Coastguard Worker 			  "link_failure_count %d ",
87*de1e4e89SAndroid Build Coastguard Worker 			  rta_getattr_u32(tb[IFLA_BOND_SLAVE_LINK_FAILURE_COUNT]));
88*de1e4e89SAndroid Build Coastguard Worker 
89*de1e4e89SAndroid Build Coastguard Worker 	if (tb[IFLA_BOND_SLAVE_PERM_HWADDR])
90*de1e4e89SAndroid Build Coastguard Worker 		print_string(PRINT_ANY,
91*de1e4e89SAndroid Build Coastguard Worker 			     "perm_hwaddr",
92*de1e4e89SAndroid Build Coastguard Worker 			     "perm_hwaddr %s ",
93*de1e4e89SAndroid Build Coastguard Worker 			     ll_addr_n2a(RTA_DATA(tb[IFLA_BOND_SLAVE_PERM_HWADDR]),
94*de1e4e89SAndroid Build Coastguard Worker 					 RTA_PAYLOAD(tb[IFLA_BOND_SLAVE_PERM_HWADDR]),
95*de1e4e89SAndroid Build Coastguard Worker 					 0, b1, sizeof(b1)));
96*de1e4e89SAndroid Build Coastguard Worker 
97*de1e4e89SAndroid Build Coastguard Worker 	if (tb[IFLA_BOND_SLAVE_QUEUE_ID])
98*de1e4e89SAndroid Build Coastguard Worker 		print_int(PRINT_ANY,
99*de1e4e89SAndroid Build Coastguard Worker 			  "queue_id",
100*de1e4e89SAndroid Build Coastguard Worker 			  "queue_id %d ",
101*de1e4e89SAndroid Build Coastguard Worker 			  rta_getattr_u16(tb[IFLA_BOND_SLAVE_QUEUE_ID]));
102*de1e4e89SAndroid Build Coastguard Worker 
103*de1e4e89SAndroid Build Coastguard Worker 	if (tb[IFLA_BOND_SLAVE_AD_AGGREGATOR_ID])
104*de1e4e89SAndroid Build Coastguard Worker 		print_int(PRINT_ANY,
105*de1e4e89SAndroid Build Coastguard Worker 			  "ad_aggregator_id",
106*de1e4e89SAndroid Build Coastguard Worker 			  "ad_aggregator_id %d ",
107*de1e4e89SAndroid Build Coastguard Worker 			  rta_getattr_u16(tb[IFLA_BOND_SLAVE_AD_AGGREGATOR_ID]));
108*de1e4e89SAndroid Build Coastguard Worker 
109*de1e4e89SAndroid Build Coastguard Worker 	if (tb[IFLA_BOND_SLAVE_AD_ACTOR_OPER_PORT_STATE])
110*de1e4e89SAndroid Build Coastguard Worker 		print_int(PRINT_ANY,
111*de1e4e89SAndroid Build Coastguard Worker 			  "ad_actor_oper_port_state",
112*de1e4e89SAndroid Build Coastguard Worker 			  "ad_actor_oper_port_state %d ",
113*de1e4e89SAndroid Build Coastguard Worker 			  rta_getattr_u8(tb[IFLA_BOND_SLAVE_AD_ACTOR_OPER_PORT_STATE]));
114*de1e4e89SAndroid Build Coastguard Worker 
115*de1e4e89SAndroid Build Coastguard Worker 	if (tb[IFLA_BOND_SLAVE_AD_PARTNER_OPER_PORT_STATE])
116*de1e4e89SAndroid Build Coastguard Worker 		print_int(PRINT_ANY,
117*de1e4e89SAndroid Build Coastguard Worker 			  "ad_partner_oper_port_state",
118*de1e4e89SAndroid Build Coastguard Worker 			  "ad_partner_oper_port_state %d ",
119*de1e4e89SAndroid Build Coastguard Worker 			  rta_getattr_u16(tb[IFLA_BOND_SLAVE_AD_PARTNER_OPER_PORT_STATE]));
120*de1e4e89SAndroid Build Coastguard Worker }
121*de1e4e89SAndroid Build Coastguard Worker 
bond_slave_parse_opt(struct link_util * lu,int argc,char ** argv,struct nlmsghdr * n)122*de1e4e89SAndroid Build Coastguard Worker static int bond_slave_parse_opt(struct link_util *lu, int argc, char **argv,
123*de1e4e89SAndroid Build Coastguard Worker 				struct nlmsghdr *n)
124*de1e4e89SAndroid Build Coastguard Worker {
125*de1e4e89SAndroid Build Coastguard Worker 	__u16 queue_id;
126*de1e4e89SAndroid Build Coastguard Worker 
127*de1e4e89SAndroid Build Coastguard Worker 	while (argc > 0) {
128*de1e4e89SAndroid Build Coastguard Worker 		if (matches(*argv, "queue_id") == 0) {
129*de1e4e89SAndroid Build Coastguard Worker 			NEXT_ARG();
130*de1e4e89SAndroid Build Coastguard Worker 			if (get_u16(&queue_id, *argv, 0))
131*de1e4e89SAndroid Build Coastguard Worker 				invarg("queue_id is invalid", *argv);
132*de1e4e89SAndroid Build Coastguard Worker 			addattr16(n, 1024, IFLA_BOND_SLAVE_QUEUE_ID, queue_id);
133*de1e4e89SAndroid Build Coastguard Worker 		} else {
134*de1e4e89SAndroid Build Coastguard Worker 			if (matches(*argv, "help") != 0)
135*de1e4e89SAndroid Build Coastguard Worker 				fprintf(stderr,
136*de1e4e89SAndroid Build Coastguard Worker 					"bond_slave: unknown option \"%s\"?\n",
137*de1e4e89SAndroid Build Coastguard Worker 					*argv);
138*de1e4e89SAndroid Build Coastguard Worker 			explain();
139*de1e4e89SAndroid Build Coastguard Worker 			return -1;
140*de1e4e89SAndroid Build Coastguard Worker 		}
141*de1e4e89SAndroid Build Coastguard Worker 		argc--, argv++;
142*de1e4e89SAndroid Build Coastguard Worker 	}
143*de1e4e89SAndroid Build Coastguard Worker 
144*de1e4e89SAndroid Build Coastguard Worker 	return 0;
145*de1e4e89SAndroid Build Coastguard Worker }
146*de1e4e89SAndroid Build Coastguard Worker 
bond_slave_print_help(struct link_util * lu,int argc,char ** argv,FILE * f)147*de1e4e89SAndroid Build Coastguard Worker static void bond_slave_print_help(struct link_util *lu, int argc, char **argv,
148*de1e4e89SAndroid Build Coastguard Worker 				  FILE *f)
149*de1e4e89SAndroid Build Coastguard Worker {
150*de1e4e89SAndroid Build Coastguard Worker 	print_explain(f);
151*de1e4e89SAndroid Build Coastguard Worker }
152*de1e4e89SAndroid Build Coastguard Worker 
153*de1e4e89SAndroid Build Coastguard Worker struct link_util bond_slave_link_util = {
154*de1e4e89SAndroid Build Coastguard Worker 	.id		= "bond_slave",
155*de1e4e89SAndroid Build Coastguard Worker 	.maxattr	= IFLA_BOND_SLAVE_MAX,
156*de1e4e89SAndroid Build Coastguard Worker 	.print_opt	= bond_slave_print_opt,
157*de1e4e89SAndroid Build Coastguard Worker 	.parse_opt	= bond_slave_parse_opt,
158*de1e4e89SAndroid Build Coastguard Worker 	.print_help	= bond_slave_print_help,
159*de1e4e89SAndroid Build Coastguard Worker };
160