diff options
author | melifaro <melifaro@FreeBSD.org> | 2015-05-16 13:11:35 +0000 |
---|---|---|
committer | melifaro <melifaro@FreeBSD.org> | 2015-05-16 13:11:35 +0000 |
commit | bd614cce8ba8e6ab392c994f7f7ba45b5ce393e2 (patch) | |
tree | 573fb3db94636125e1779dc384ff2a30c0b1854d /sbin/ifconfig | |
parent | 8df65c37f21b6d4bbed84f9f1029a48cf07c980a (diff) | |
download | FreeBSD-src-bd614cce8ba8e6ab392c994f7f7ba45b5ce393e2.zip FreeBSD-src-bd614cce8ba8e6ab392c994f7f7ba45b5ce393e2.tar.gz |
* Update SFF-8024 Identifier constants.
* Fix SFF_8436_CC_EXT in SFF-8436 memory map.
* Add SFF-8436/8636 bits (revision compliance/nominal bitrate).
* Do some small style/type fixes.
Diffstat (limited to 'sbin/ifconfig')
-rw-r--r-- | sbin/ifconfig/sfp.c | 71 |
1 files changed, 67 insertions, 4 deletions
diff --git a/sbin/ifconfig/sfp.c b/sbin/ifconfig/sfp.c index 4ceb91a..7c090e1 100644 --- a/sbin/ifconfig/sfp.c +++ b/sbin/ifconfig/sfp.c @@ -182,6 +182,18 @@ static struct _nv eth_1040g[] = { { 0, NULL } }; +/* SFF-8636 Rev. 2.5 table 6.3: Revision compliance */ +static struct _nv rev_compl[] = { + { 0x1, "SFF-8436 rev <=4.8" }, + { 0x2, "SFF-8436 rev <=4.8" }, + { 0x3, "SFF-8636 rev <=1.3" }, + { 0x4, "SFF-8636 rev <=1.4" }, + { 0x5, "SFF-8636 rev <=1.5" }, + { 0x6, "SFF-8636 rev <=2.0" }, + { 0x7, "SFF-8636 rev <=2.5" }, + { 0x0, "Unspecified" } +}; + const char * find_value(struct _nv *x, int value) { @@ -246,6 +258,19 @@ convert_sff_connector(char *buf, size_t size, uint8_t value) } static void +convert_sff_rev_compliance(char *buf, size_t size, uint8_t value) +{ + const char *x; + + if (value > 0x07) + x = "Unallocated"; + else + x = find_value(rev_compl, value); + + snprintf(buf, size, "%s", x); +} + +static void get_sfp_identifier(struct i2c_info *ii, char *buf, size_t size) { uint8_t data; @@ -604,23 +629,50 @@ get_sfp_tx_power(struct i2c_info *ii, char *buf, size_t size) static void get_qsfp_rx_power(struct i2c_info *ii, char *buf, size_t size, int chan) { - char xbuf[2]; + uint8_t xbuf[2]; memset(xbuf, 0, sizeof(xbuf)); - read_i2c(ii, SFF_8436_BASE, SFF_8436_RX_CH1_MSB + (chan - 1) * 2, 2, xbuf); + read_i2c(ii, SFF_8436_BASE, SFF_8436_RX_CH1_MSB + (chan-1)*2, 2, xbuf); convert_sff_power(ii, buf, size, xbuf); } static void get_qsfp_tx_power(struct i2c_info *ii, char *buf, size_t size, int chan) { - char xbuf[2]; + uint8_t xbuf[2]; memset(xbuf, 0, sizeof(xbuf)); - read_i2c(ii, SFF_8436_BASE, SFF_8436_TX_CH1_MSB + (chan -1) * 2, 2, xbuf); + read_i2c(ii, SFF_8436_BASE, SFF_8436_TX_CH1_MSB + (chan-1)*2, 2, xbuf); convert_sff_power(ii, buf, size, xbuf); } +static void +get_qsfp_rev_compliance(struct i2c_info *ii, char *buf, size_t size) +{ + uint8_t xbuf; + + xbuf = 0; + read_i2c(ii, SFF_8436_BASE, SFF_8436_STATUS, 1, &xbuf); + convert_sff_rev_compliance(buf, size, xbuf); +} + +static uint32_t +get_qsfp_br(struct i2c_info *ii) +{ + uint8_t xbuf; + uint32_t rate; + + xbuf = 0; + read_i2c(ii, SFF_8436_BASE, SFF_8436_BITRATE, 1, &xbuf); + rate = xbuf * 100; + if (xbuf == 0xFF) { + read_i2c(ii, SFF_8436_BASE, SFF_8636_BITRATE, 1, &xbuf); + rate = xbuf * 250; + } + + return (rate); +} + /* * Reads i2c data from opened kernel socket. */ @@ -689,6 +741,7 @@ print_qsfp_status(struct i2c_info *ii, int verbose) { char buf[80], buf2[40], buf3[40]; uint8_t diag_type; + uint32_t bitrate; int i; /* Read diagnostic monitoring type */ @@ -715,6 +768,16 @@ print_qsfp_status(struct i2c_info *ii, int verbose) if (ii->error == 0) printf("\t%s\n", buf); + if (verbose > 1) { + get_qsfp_rev_compliance(ii, buf, sizeof(buf)); + if (ii->error == 0) + printf("\tcompliance level: %s\n", buf); + + bitrate = get_qsfp_br(ii); + if (ii->error == 0 && bitrate > 0) + printf("\tnominal bitrate: %u Mbps\n", bitrate); + } + /* Request current measurements if they are provided: */ if (ii->do_diag != 0) { get_qsfp_temp(ii, buf, sizeof(buf)); |