diags/ibportstate: Support changing LinkSpeedEnabled on any IB port

Signed-off-by: Hal Rosenstock <[EMAIL PROTECTED]>

Index: src/ibportstate.c
===================================================================
--- src/ibportstate.c   (revision 9687)
+++ src/ibportstate.c   (working copy)
@@ -99,10 +99,11 @@ get_node_info(ib_portid_t *dest, char *d
 }
 
 static char *
-get_port_info(ib_portid_t *dest, char *data, char **argv, int argc)
+get_port_info(ib_portid_t *dest, char *data, char **argv, int argc, int 
port_op)
 {
        char buf[2048];
        int portnum = 0;
+       char val[64];
 
        if (argc > 0)
                portnum = strtol(argv[0], 0, 0);
@@ -110,17 +111,24 @@ get_port_info(ib_portid_t *dest, char *d
        if (!smp_query(data, dest, IB_ATTR_PORT_INFO, portnum, 0))
                return "smp query portinfo failed";
 
-       mad_dump_portstates(buf, sizeof buf, data, sizeof data);
+       if (port_op != 4)
+               mad_dump_portstates(buf, sizeof buf, data, sizeof data);
+       else {
+               mad_decode_field(data, IB_PORT_LINK_SPEED_ENABLED_F, val);
+               mad_dump_field(IB_PORT_LINK_SPEED_ENABLED_F, buf, sizeof buf, 
val);
+               sprintf(buf+strlen(buf), "%s", "\n");
+       }
 
        printf("# Port info: %s port %d\n%s", portid2str(dest), portnum, buf);
        return 0;
 }
 
 static char * 
-set_port_info(ib_portid_t *dest, char *data, char **argv, int argc)
+set_port_info(ib_portid_t *dest, char *data, char **argv, int argc, int 
port_op)
 {
        char buf[2048];
        int portnum = 0;
+       char val[64];
 
        if (argc > 0)
                portnum = strtol(argv[0], 0, 0);
@@ -128,9 +136,15 @@ set_port_info(ib_portid_t *dest, char *d
        if (!smp_set(data, dest, IB_ATTR_PORT_INFO, portnum, 0))
                return "smp set failed";
 
-       mad_dump_portstates(buf, sizeof buf, data, sizeof data);
+       if (port_op != 4)
+               mad_dump_portstates(buf, sizeof buf, data, sizeof data);
+       else {
+               mad_decode_field(data, IB_PORT_LINK_SPEED_ENABLED_F, val);
+               mad_dump_field(IB_PORT_LINK_SPEED_ENABLED_F, buf, sizeof buf, 
val);
+               sprintf(buf+strlen(buf), "%s", "\n");
+       }
 
-       printf("\nPort states after set:\n");
+       printf("\nAfter PortInfo set:\n");
        printf("# Port info: %s port %d\n%s", portid2str(dest), portnum, buf);
        return 0;
 }
@@ -148,11 +162,13 @@ usage(void)
        fprintf(stderr, "Usage: %s [-d(ebug) -e(rr_show) -v(erbose) -D(irect) 
-G(uid) -s smlid -V(ersion) -C ca_name -P ca_port "
                        "-t(imeout) timeout_ms] <dest dr_path|lid|guid> 
<portnum> [<op>]\n",
                        basename);
-       fprintf(stderr, "\tsupported ops: enable, disable, reset, query\n");
+       fprintf(stderr, "\tsupported ops: enable, disable, reset, speed, 
query\n");
        fprintf(stderr, "\n\texamples:\n");
        fprintf(stderr, "\t\t%s 3 1 disable\t\t\t# by lid\n", basename);
        fprintf(stderr, "\t\t%s -G 0x2C9000100D051 1 enable\t# by guid\n", 
basename);
-       fprintf(stderr, "\t\t%s -D 0 1\t\t\t# by direct route\n", basename);
+       fprintf(stderr, "\t\t%s -D 0 1\t\t\t# (query) by direct route\n", 
basename);
+       fprintf(stderr, "\t\t%s 3 1 reset\t\t\t# by lid\n", basename);
+       fprintf(stderr, "\t\t%s 3 1 speed 1\t\t\t# by lid\n", basename);
        exit(-1);
 }
 
@@ -167,6 +183,7 @@ main(int argc, char **argv)
        char *ca = 0;
        int ca_port = 0;
        int port_op = 0;        /* default to query */
+       int speed = 15;
        char *err;
        char data[IB_SMP_DATA_SIZE];
 
@@ -254,14 +271,23 @@ main(int argc, char **argv)
                        port_op = 2;
                else if (!strcmp(argv[2], "reset"))
                        port_op = 3;
+               else if (!strcmp(argv[2], "speed")) {
+                       if (argc < 4)
+                               IBERROR("speed requires an additional 
parameter");
+                       port_op = 4;
+                       /* Parse speed value */
+                       speed = strtoul(argv[3], 0, 0);
+                       if (speed > 15)
+                               IBERROR("invalid speed value %d", speed);
+               }
        }
 
-       if (port_op)
+       if (port_op && (port_op != 4))
                if ((err = get_node_info(&portid, data, argv+1, argc-1)))
                        IBERROR("smpquery nodeinfo: %s", err);
 
-       printf("Initial port states:\n");
-       if ((err = get_port_info(&portid, data, argv+1, argc-1)))
+       printf("Initial PortInfo:\n");
+       if ((err = get_port_info(&portid, data, argv+1, argc-1, port_op)))
                IBERROR("smpquery portinfo: %s", err);
 
        /* Only if one of the "set" options is chosen */
@@ -271,13 +297,17 @@ main(int argc, char **argv)
                else if ((port_op == 2) || (port_op == 3)) { /* Disable port */
                        mad_set_field(data, 0, IB_PORT_STATE_F, 1);             
/* Down */
                        mad_set_field(data, 0, IB_PORT_PHYS_STATE_F, 3);        
/* Disabled */
+               } else if (port_op == 4) {      /* Set speed */
+                       mad_set_field(data, 0, IB_PORT_LINK_SPEED_ENABLED_F, 
speed);
+                       mad_set_field(data, 0, IB_PORT_STATE_F, 0);
+                       mad_set_field(data, 0, IB_PORT_PHYS_STATE_F, 0);
                }
 
-               if ((err = set_port_info(&portid, data, argv+1, argc-1)))
+               if ((err = set_port_info(&portid, data, argv+1, argc-1, 
port_op)))
                        IBERROR("smpset portinfo: %s", err);
                if (port_op == 3) {     /* Reset port - so also enable */
                        mad_set_field(data, 0, IB_PORT_PHYS_STATE_F, 2);        
/* Polling */
-                       if ((err = set_port_info(&portid, data, argv+1, 
argc-1)))
+                       if ((err = set_port_info(&portid, data, argv+1, argc-1, 
port_op)))
                                IBERROR("smpset portinfo: %s", err);
                }
        }
Index: man/ibportstate.8
===================================================================
--- man/ibportstate.8   (revision 9686)
+++ man/ibportstate.8   (working copy)
@@ -1,7 +1,7 @@
 .TH IBPORTSTATE 8 "October 3, 2006" "OpenIB" "OpenIB Diagnostics"
 
 .SH NAME
-ibportstate \- handle port state and port physical state of an InfiniBand port 
+ibportstate \- handle port (physical) state and link speed of an InfiniBand 
port 
 
 .SH SYNOPSIS
 .B ibportstate
@@ -10,7 +10,8 @@ ibportstate \- handle port state and por
 .SH DESCRIPTION
 .PP
 ibportstate allows the port state and port physical state of an IB port
-to be queried or a switch port to be disabled, enabled, or reset.
+to be queried or a switch port to be disabled, enabled, or reset. It 
+also allows the link speed enabled on any IB port to be adjusted.
 
 .SH OPTIONS
 
@@ -18,10 +19,17 @@ to be queried or a switch port to be dis
 .TP
 op
 Port operations allowed
- supported ops: enable, disable, reset, query
+ supported ops: enable, disable, reset, speed, query
  Default is query
+.PP
  ops enable, disable, and reset are only allowed on switch ports
- (An error is returned if attempted on CA or router ports)
+ (An error is indicated if attempted on CA or router ports)
+ speed op is allowed on any port
+ speed values are legal values for PortInfo:LinkSpeedEnabled
+ (An error is indicated if PortInfo:LinkSpeedSupported does not support
+  this setting)
+ (NOTE: Speed changes are not effected until the port goes through
+  link renegotiation)
 
 .SH COMMON OPTIONS
 
@@ -84,7 +92,11 @@ ibportstate 3 1 disable                 
 .PP
 ibportstate -G 0x2C9000100D051 1 enable # by guid
 .PP
-ibportstate -D 0 1                      # by direct route
+ibportstate -D 0 1                      # (query) by direct route
+.PP
+ibportstate 3 1 reset                          # by lid
+.PP
+ibportstate 3 1 speed 1                                # by lid
 
 .SH AUTHOR
 .TP




_______________________________________________
openib-general mailing list
[email protected]
http://openib.org/mailman/listinfo/openib-general

To unsubscribe, please visit http://openib.org/mailman/listinfo/openib-general

Reply via email to