Updates from the ONLP development repository.

This commit is contained in:
Jeffrey Townsend
2016-03-23 19:47:21 +00:00
parent c1a795d085
commit 9a21c3317e
30 changed files with 836 additions and 98 deletions

View File

@@ -74,13 +74,16 @@ cdefs: &cdefs
default: 1
- ONLP_CONFIG_API_LOCK_GLOBAL_SHARED:
doc: "If 0, the API lock is a simple semaphore. If 1, the API lock is a global shared mutex."
default: 0
default: 1
- ONLP_CONFIG_API_LOCK_TIMEOUT:
doc: "The maximum amount of time (in usecs) to wait while attempting to acquire the API lock. Failure to acquire is fatal. A value of zero disables this feature. "
default: 60000000
- ONLP_CONFIG_INFO_STR_MAX:
doc: "The maximum size of static information string buffers."
default: 64
- ONLP_CONFIG_INCLUDE_THERMAL_THRESHOLDS:
doc: "Include thermal threshold reporting."
default: 1
# Error codes
onlp_status: &onlp_status

View File

@@ -211,7 +211,7 @@
#ifndef ONLP_CONFIG_API_LOCK_GLOBAL_SHARED
#define ONLP_CONFIG_API_LOCK_GLOBAL_SHARED 0
#define ONLP_CONFIG_API_LOCK_GLOBAL_SHARED 1
#endif
/**
@@ -234,6 +234,16 @@
#define ONLP_CONFIG_INFO_STR_MAX 64
#endif
/**
* ONLP_CONFIG_INCLUDE_THERMAL_THRESHOLDS
*
* Include thermal threshold reporting. */
#ifndef ONLP_CONFIG_INCLUDE_THERMAL_THRESHOLDS
#define ONLP_CONFIG_INCLUDE_THERMAL_THRESHOLDS 1
#endif
/**

View File

@@ -71,6 +71,34 @@ int onlp_sfpi_rx_los_bitmap_get(onlp_sfp_bitmap_t* dst);
*/
int onlp_sfpi_eeprom_read(int port, uint8_t data[256]);
/**
* @brief Read a byte from an address on the given SFP port's bus.
* @param port The port number.
* @param devaddr The device address.
* @param addr The address.
*/
int onlp_sfpi_dev_readb(int port, uint8_t devaddr, uint8_t addr);
/**
* @brief Write a byte to an address on the given SFP port's bus.
*/
int onlp_sfpi_dev_writeb(int port, uint8_t devaddr, uint8_t addr, uint8_t value);
/**
* @brief Read a byte from an address on the given SFP port's bus.
* @param port The port number.
* @param devaddr The device address.
* @param addr The address.
* @returns The word if successful, error otherwise.
*/
int onlp_sfpi_dev_readw(int port, uint8_t devaddr, uint8_t addr);
/**
* @brief Write a byte to an address on the given SFP port's bus.
*/
int onlp_sfpi_dev_writew(int port, uint8_t devaddr, uint8_t addr, uint16_t value);
/**
* @brief Read the SFP DOM EEPROM.
* @param port The port number.

View File

@@ -154,4 +154,9 @@ int onlp_sysi_platform_info_get(onlp_platform_info_t* info);
*/
void onlp_sysi_platform_info_free(onlp_platform_info_t* info);
/**
* @brief Builtin platform debug tool.
*/
int onlp_sysi_debug(aim_pvs_t* pvs, int argc, char** argv);
#endif /* __ONLP_SYSI_H__ */

View File

@@ -143,6 +143,36 @@ int onlp_sfp_denit(void);
*/
int onlp_sfp_rx_los_bitmap_get(onlp_sfp_bitmap_t* dst);
/**
* @brief Read a byte from an address on the given SFP port's bus.
* @param port The port number.
* @param devaddr The device address.
* @param addr The address.
*/
int onlp_sfp_dev_readb(int port, uint8_t devaddr, uint8_t addr);
/**
* @brief Write a byte to an address on the given SFP port's bus.
*/
int onlp_sfp_dev_writeb(int port, uint8_t devaddr, uint8_t addr, uint8_t value);
/**
* @brief Read a byte from an address on the given SFP port's bus.
* @param port The port number.
* @param devaddr The device address.
* @param addr The address.
*/
int onlp_sfp_dev_readw(int port, uint8_t devaddr, uint8_t addr);
/**
* @brief Write a byte to an address on the given SFP port's bus.
*/
int onlp_sfp_dev_writew(int port, uint8_t devaddr, uint8_t addr, uint16_t value);
/**
* @brief Dump the status of all SFPs
* @param pvs The output pvs.

View File

@@ -117,4 +117,6 @@ int onlp_sys_platform_manage_join(void);
void onlp_sys_platform_manage_now(void);
int onlp_sys_debug(aim_pvs_t* pvs, int argc, char** argv);
#endif /* __ONLP_SYS_H_ */

View File

@@ -244,14 +244,29 @@ onlp_fan_show(onlp_oid_t oid, aim_pvs_t* pvs, uint32_t flags)
int rv;
iof_t iof;
onlp_fan_info_t fi;
int yaml;
onlp_oid_show_iof_init_default(&iof, pvs, flags);
rv = onlp_fan_info_get(oid, &fi);
iof_push(&iof, "Fan %d", ONLP_OID_ID_GET(oid));
yaml = flags & ONLP_OID_SHOW_F_YAML;
if(yaml) {
iof_push(&iof, "- ");
iof_iprintf(&iof, "Name: Fan %d", ONLP_OID_ID_GET(oid));
}
else {
iof_push(&iof, "Fan %d", ONLP_OID_ID_GET(oid));
}
if(rv < 0) {
onlp_oid_info_get_error(&iof, rv);
if(yaml) {
iof_iprintf(&iof, "State: Error");
iof_iprintf(&iof, "Error: %{onlp_status}", rv);
} else {
onlp_oid_info_get_error(&iof, rv);
}
}
else {
onlp_oid_show_description(&iof, &fi.hdr);
@@ -259,10 +274,10 @@ onlp_fan_show(onlp_oid_t oid, aim_pvs_t* pvs, uint32_t flags)
/* Present */
iof_iprintf(&iof, "State: Present");
if(fi.status & ONLP_FAN_STATUS_FAILED) {
iof_iprintf(&iof, "Status: FAILED");
iof_iprintf(&iof, "Status: Failed");
}
else {
iof_iprintf(&iof, "Status: Running.");
iof_iprintf(&iof, "Status: Running");
if(fi.model[0]) {
iof_iprintf(&iof, "Model: %s", fi.model);
}
@@ -270,16 +285,16 @@ onlp_fan_show(onlp_oid_t oid, aim_pvs_t* pvs, uint32_t flags)
iof_iprintf(&iof, "SN: %s", fi.serial);
}
if(fi.caps & ONLP_FAN_CAPS_GET_RPM) {
iof_iprintf(&iof, "RPM: %d.", fi.rpm);
iof_iprintf(&iof, "RPM: %d", fi.rpm);
}
if(fi.caps & ONLP_FAN_CAPS_GET_PERCENTAGE) {
iof_iprintf(&iof, "Speed: %d%%.", fi.percentage);
iof_iprintf(&iof, "Speed: %d%%", fi.percentage);
}
if(fi.status & ONLP_FAN_STATUS_B2F) {
iof_iprintf(&iof, "Airflow: Back-to-Front.");
iof_iprintf(&iof, "Airflow: Back-to-Front");
}
if(fi.status & ONLP_FAN_STATUS_F2B) {
iof_iprintf(&iof, "Airflow: Front-to-Back.");
iof_iprintf(&iof, "Airflow: Front-to-Back");
}
}
}

View File

@@ -158,18 +158,36 @@ onlp_led_show(onlp_oid_t id, aim_pvs_t* pvs, uint32_t flags)
int rv;
iof_t iof;
onlp_led_info_t info;
int yaml;
VALIDATENR(id);
onlp_oid_show_iof_init_default(&iof, pvs, flags);
iof_push(&iof, "LED %d", ONLP_OID_ID_GET(id));
yaml = flags & ONLP_OID_SHOW_F_YAML;
if(yaml) {
iof_push(&iof, " -");
iof_iprintf(&iof, "Name: LED %d", ONLP_OID_ID_GET(id));
}
else {
iof_push(&iof, "LED %d", ONLP_OID_ID_GET(id));
}
rv = onlp_led_info_get(id, &info);
if(rv < 0) {
onlp_oid_info_get_error(&iof, rv);
if(yaml) {
iof_iprintf(&iof, "State: Error");
iof_iprintf(&iof, "Error: %{onlp_status}", rv);
}
else {
onlp_oid_info_get_error(&iof, rv);
}
}
else {
onlp_oid_show_description(&iof, &info.hdr);
if(info.status & 1) {
/* Present */
iof_iprintf(&iof, "State: Present");
iof_iprintf(&iof, "Mode: %{onlp_led_mode}", info.mode);
}
else {

View File

@@ -124,6 +124,11 @@ onlp_config_settings_t onlp_config_settings[] =
{ __onlp_config_STRINGIFY_NAME(ONLP_CONFIG_INFO_STR_MAX), __onlp_config_STRINGIFY_VALUE(ONLP_CONFIG_INFO_STR_MAX) },
#else
{ ONLP_CONFIG_INFO_STR_MAX(__onlp_config_STRINGIFY_NAME), "__undefined__" },
#endif
#ifdef ONLP_CONFIG_INCLUDE_THERMAL_THRESHOLDS
{ __onlp_config_STRINGIFY_NAME(ONLP_CONFIG_INCLUDE_THERMAL_THRESHOLDS), __onlp_config_STRINGIFY_VALUE(ONLP_CONFIG_INCLUDE_THERMAL_THRESHOLDS) },
#else
{ ONLP_CONFIG_INCLUDE_THERMAL_THRESHOLDS(__onlp_config_STRINGIFY_NAME), "__undefined__" },
#endif
{ NULL, NULL }
};

View File

@@ -174,7 +174,15 @@ onlpdump_main(int argc, char* argv[])
const char* O = NULL;
const char* t = NULL;
while( (c = getopt(argc, argv, "srehdojmM:ipxlSt:O:")) != -1) {
/**
* debug trap
*/
if(argc > 1 && !strcmp(argv[1], "debug")) {
onlp_init();
return onlp_sys_debug(&aim_pvs_stdout, argc-2, argv+2);
}
while( (c = getopt(argc, argv, "srehdojmyM:ipxlSt:O:")) != -1) {
switch(c)
{
case 's': show=1; break;
@@ -193,21 +201,18 @@ onlpdump_main(int argc, char* argv[])
case 'O': O = optarg; break;
case 'S': S=1; break;
case 'l': l=1; break;
case 'y': show=1; showflags |= ONLP_OID_SHOW_F_YAML; break;
default: help=1; rv = 1; break;
}
}
if(M) {
platform_manager_daemon__(pidfile);
exit(0);
}
if(help) {
printf("Usage: %s [OPTIONS]\n", argv[0]);
printf(" -d Use dump(). This is the default.\n");
printf(" -s Use show() instead of dump().\n");
printf(" -r Recursive show(). Implies -s\n");
printf(" -e Extended show(). Implies -s\n");
printf(" -y Yaml show(). Implies -s\n");
printf(" -o Dump ONIE data only.\n");
printf(" -x Dump Platform Info only.\n");
printf(" -j Dump ONIE data in JSON format.\n");
@@ -223,7 +228,7 @@ onlpdump_main(int argc, char* argv[])
}
if(t){
if(t) {
int rv;
onlp_onie_info_t onie;
rv = onlp_onie_decode_file(&onie, t);
@@ -240,6 +245,11 @@ onlpdump_main(int argc, char* argv[])
onlp_init();
if(M) {
platform_manager_daemon__(pidfile);
exit(0);
}
if(l) {
extern int onlp_api_lock_test(void);
int i;

View File

@@ -49,12 +49,7 @@ onlp_oid_show_iof_init_default(iof_t* iof, aim_pvs_t* pvs, uint32_t flags)
iof->level=1;
iof->indent_terminator="";
iof->pop_string = NULL;
if(flags & ONLP_OID_SHOW_F_YAML) {
iof->push_string = ":";
}
else {
iof->push_string = "";
}
iof->push_string = "";
}
}

View File

@@ -284,6 +284,7 @@ onlp_sys_platform_manage_join(void)
return 0;
}
static int
platform_psus_notify__(void)
{

View File

@@ -129,13 +129,28 @@ onlp_psu_show(onlp_oid_t id, aim_pvs_t* pvs, uint32_t flags)
int rv;
iof_t iof;
onlp_psu_info_t pi;
int yaml;
onlp_oid_show_iof_init_default(&iof, pvs, flags);
rv = onlp_psu_info_get(id, &pi);
iof_push(&iof, "PSU %d", ONLP_OID_ID_GET(id));
yaml = flags & ONLP_OID_SHOW_F_YAML;
if(yaml) {
iof_push(&iof, "- ");
iof_iprintf(&iof, "Name: PSU %d", ONLP_OID_ID_GET(id));
} else {
iof_push(&iof, "PSU %d", ONLP_OID_ID_GET(id));
}
if(rv < 0) {
onlp_oid_info_get_error(&iof, rv);
if(yaml) {
iof_iprintf(&iof, "State: Error");
iof_iprintf(&iof, "Error: %{onlp_status}", rv);
}
else {
onlp_oid_info_get_error(&iof, rv);
}
}
else {
onlp_oid_show_description(&iof, &pi.hdr);
@@ -146,10 +161,10 @@ onlp_psu_show(onlp_oid_t id, aim_pvs_t* pvs, uint32_t flags)
iof_iprintf(&iof, "Status: Unplugged");
}
else if(pi.status & ONLP_PSU_STATUS_FAILED) {
iof_iprintf(&iof, "Status: Unplugged or Failed.");
iof_iprintf(&iof, "Status: Unplugged or Failed");
}
else {
iof_iprintf(&iof, "Status: Running.");
iof_iprintf(&iof, "Status: Running");
iof_iprintf(&iof, "Model: %s", pi.model[0] ? pi.model : "Unknown");
if(pi.serial[0]) iof_iprintf(&iof, "SN: %s", pi.serial);
if(pi.caps & ONLP_PSU_CAPS_AC) {
@@ -162,7 +177,7 @@ onlp_psu_show(onlp_oid_t id, aim_pvs_t* pvs, uint32_t flags)
iof_iprintf(&iof, "Type: DC 48V");
}
else {
iof_iprintf(&iof, "Type: Unknown.");
iof_iprintf(&iof, "Type: Unknown");
}
if(pi.caps & ONLP_PSU_CAPS_VIN) {
iof_iprintf(&iof, "Vin: %d.%d",
@@ -197,12 +212,26 @@ onlp_psu_show(onlp_oid_t id, aim_pvs_t* pvs, uint32_t flags)
* Fans and Thermal Sensors.
*/
onlp_oid_t* oidp;
if(yaml) {
iof_push(&iof, "Fans: ");
}
ONLP_OID_TABLE_ITER_TYPE(pi.hdr.coids, oidp, FAN) {
onlp_oid_show(*oidp, &iof.inherit, flags);
}
if(yaml) {
iof_pop(&iof);
}
if(yaml) {
iof_push(&iof, "Thermals: ");
}
ONLP_OID_TABLE_ITER_TYPE(pi.hdr.coids, oidp, THERMAL) {
onlp_oid_show(*oidp, &iof.inherit, flags);
}
if(yaml) {
iof_pop(&iof);
}
if(flags & ONLP_OID_SHOW_F_EXTENDED) {
/* Include all other types as well. */

View File

@@ -399,3 +399,34 @@ onlp_sfp_vioctl_locked__(int port, va_list vargs)
ONLP_LOCKED_API2(onlp_sfp_vioctl, int, port, va_list, vargs);
int
onlp_sfp_dev_readb_locked__(int port, uint8_t devaddr, uint8_t addr)
{
ONLP_SFP_PORT_VALIDATE_AND_MAP(port);
return onlp_sfpi_dev_readb(port, devaddr, addr);
}
ONLP_LOCKED_API3(onlp_sfp_dev_readb, int, port, uint8_t, devaddr, uint8_t, addr);
int
onlp_sfp_dev_writeb_locked__(int port, uint8_t devaddr, uint8_t addr, uint8_t value)
{
ONLP_SFP_PORT_VALIDATE_AND_MAP(port);
return onlp_sfpi_dev_writeb(port, devaddr, addr, value);
}
ONLP_LOCKED_API4(onlp_sfp_dev_writeb, int, port, uint8_t, devaddr, uint8_t, addr, uint8_t, value);
int
onlp_sfp_dev_readw_locked__(int port, uint8_t devaddr, uint8_t addr)
{
ONLP_SFP_PORT_VALIDATE_AND_MAP(port);
return onlp_sfpi_dev_readw(port, devaddr, addr);
}
ONLP_LOCKED_API3(onlp_sfp_dev_readw, int, port, uint8_t, devaddr, uint8_t, addr);
int
onlp_sfp_dev_writew_locked__(int port, uint8_t devaddr, uint8_t addr, uint16_t value)
{
ONLP_SFP_PORT_VALIDATE_AND_MAP(port);
return onlp_sfpi_dev_writew(port, devaddr, addr, value);
}
ONLP_LOCKED_API4(onlp_sfp_dev_writew, int, port, uint8_t, devaddr, uint8_t, addr, uint16_t, value);

View File

@@ -181,7 +181,7 @@ onlp_sys_dump(onlp_oid_t id, aim_pvs_t* pvs, uint32_t flags)
return;
}
iof_push(&iof, "System Information");
iof_push(&iof, "System Information:");
rv = onlp_sys_info_get(&si);
if(rv < 0) {
onlp_oid_info_get_error(&iof, rv);
@@ -227,7 +227,7 @@ onlp_sys_show(onlp_oid_t id, aim_pvs_t* pvs, uint32_t flags)
if(yaml ||
flags & ONLP_OID_SHOW_F_EXTENDED ||
(flags & ONLP_OID_SHOW_F_RECURSE) == 0) {
iof_push(&iof, "System Information");
iof_push(&iof, "System Information:");
onlp_onie_show(&si.onie_info, &iof.inherit);
iof_pop(&iof);
}
@@ -237,21 +237,21 @@ onlp_sys_show(onlp_oid_t id, aim_pvs_t* pvs, uint32_t flags)
onlp_oid_t* oidp;
/** Show all Chassis Fans */
YPUSH("Fans");
YPUSH("Fans:");
ONLP_OID_TABLE_ITER_TYPE(si.hdr.coids, oidp, FAN) {
onlp_oid_show(*oidp, &iof.inherit, flags);
}
YPOP();
/** Show all System Thermals */
YPUSH("Thermals");
YPUSH("Thermals:");
ONLP_OID_TABLE_ITER_TYPE(si.hdr.coids, oidp, THERMAL) {
onlp_oid_show(*oidp, &iof.inherit, flags);
}
YPOP();
/** Show all PSUs */
YPUSH("PSUs");
YPUSH("PSUs:");
ONLP_OID_TABLE_ITER_TYPE(si.hdr.coids, oidp, PSU) {
onlp_oid_show(*oidp, &iof.inherit, flags);
}
@@ -259,7 +259,7 @@ onlp_sys_show(onlp_oid_t id, aim_pvs_t* pvs, uint32_t flags)
if(flags & ONLP_OID_SHOW_F_EXTENDED) {
/** Show all LEDs */
YPUSH("LEDs");
YPUSH("LEDs:");
ONLP_OID_TABLE_ITER_TYPE(si.hdr.coids, oidp, LED) {
onlp_oid_show(*oidp, &iof.inherit, flags);
}
@@ -287,3 +287,9 @@ onlp_sys_vioctl_locked__(int code, va_list vargs)
}
ONLP_LOCKED_API2(onlp_sys_vioctl, int, code, va_list, vargs);
static int
onlp_sys_debug_locked__(aim_pvs_t* pvs, int argc, char* argv[])
{
return onlp_sysi_debug(pvs, argc, argv);
}
ONLP_LOCKED_API3(onlp_sys_debug, aim_pvs_t*, pvs, int, argc, char**, argv);

View File

@@ -164,44 +164,64 @@ onlp_thermal_show(onlp_oid_t id, aim_pvs_t* pvs, uint32_t flags)
iof_t iof;
onlp_thermal_info_t ti;
VALIDATENR(id);
int yaml;
onlp_oid_show_iof_init_default(&iof, pvs, flags);
rv = onlp_thermal_info_get(id, &ti);
iof_push(&iof, "Thermal %d", ONLP_OID_ID_GET(id));
yaml = flags & ONLP_OID_SHOW_F_YAML;
if(yaml) {
iof_push(&iof, "- ");
iof_iprintf(&iof, "Name: Thermal %d", ONLP_OID_ID_GET(id));
}
else {
iof_push(&iof, "Thermal %d", ONLP_OID_ID_GET(id));
}
if(rv < 0) {
onlp_oid_info_get_error(&iof, rv);
if(yaml) {
iof_iprintf(&iof, "State: Error");
iof_iprintf(&iof, "Error: %{onlp_status}", rv);
}
else {
onlp_oid_info_get_error(&iof, rv);
}
}
else {
onlp_oid_show_description(&iof, &ti.hdr);
if(ti.status & 0x1) {
/* Present */
if(ti.status & ONLP_THERMAL_STATUS_FAILED) {
iof_iprintf(&iof, "Status: Sensor FAILED");
iof_iprintf(&iof, "Status: Failed");
}
else {
iof_iprintf(&iof, "Status: Sensor Functional");
iof_iprintf(&iof, "Status: Functional");
if(ti.caps & ONLP_THERMAL_CAPS_GET_TEMPERATURE) {
iof_iprintf(&iof, "Temperature: %d.%d C.",
iof_iprintf(&iof, "Temperature: %d.%d C",
ONLP_MILLI_NORMAL_INTEGER_TENTHS(ti.mcelsius));
}
#if ONLP_CONFIG_INCLUDE_THERMAL_THRESHOLDS == 1
if(ti.caps & ONLP_THERMAL_CAPS_GET_ANY_THRESHOLD) {
iof_push(&iof, "Thresholds");
iof_push(&iof, "Thresholds:");
if(ti.caps & ONLP_THERMAL_CAPS_GET_WARNING_THRESHOLD) {
iof_iprintf(&iof, "Warning : %d.%d C.",
iof_iprintf(&iof, "Warning : %d.%d C",
ONLP_MILLI_NORMAL_INTEGER_TENTHS(ti.thresholds.warning));
}
if(ti.caps & ONLP_THERMAL_CAPS_GET_ERROR_THRESHOLD) {
iof_iprintf(&iof, "Error : %d.%d C.",
iof_iprintf(&iof, "Error : %d.%d C",
ONLP_MILLI_NORMAL_INTEGER_TENTHS(ti.thresholds.error));
}
if(ti.caps & ONLP_THERMAL_CAPS_GET_SHUTDOWN_THRESHOLD) {
iof_iprintf(&iof, "Shutdown: %d.%d C.",
iof_iprintf(&iof, "Shutdown: %d.%d C",
ONLP_MILLI_NORMAL_INTEGER_TENTHS(ti.thresholds.shutdown));
}
iof_pop(&iof);
}
#endif
}
}
else {

View File

@@ -40,3 +40,7 @@ __ONLP_DEFAULTI_IMPLEMENTATION(onlp_sfpi_ioctl(int port, va_list vargs));
__ONLP_DEFAULTI_IMPLEMENTATION(onlp_sfpi_control_supported(int port, onlp_sfp_control_t control, int* rv));
__ONLP_DEFAULTI_IMPLEMENTATION(onlp_sfpi_control_set(int port, onlp_sfp_control_t control, int value));
__ONLP_DEFAULTI_IMPLEMENTATION(onlp_sfpi_control_get(int port, onlp_sfp_control_t control, int* value));
__ONLP_DEFAULTI_IMPLEMENTATION(onlp_sfpi_dev_readb(int port, uint8_t devaddr, uint8_t addr));
__ONLP_DEFAULTI_IMPLEMENTATION(onlp_sfpi_dev_writeb(int port, uint8_t devaddr, uint8_t addr, uint8_t value));
__ONLP_DEFAULTI_IMPLEMENTATION(onlp_sfpi_dev_readw(int port, uint8_t devaddr, uint8_t addr));
__ONLP_DEFAULTI_IMPLEMENTATION(onlp_sfpi_dev_writew(int port, uint8_t devaddr, uint8_t addr, uint16_t value));

View File

@@ -48,6 +48,13 @@ onlp_sysi_platform_get(void)
return ONLP_SYSI_PLATFORM_NAME_DEFAULT;
}
int __ONLP_DEFAULTI
onlp_sysi_debug(aim_pvs_t* pvs, int argc, char* argv[])
{
aim_printf(pvs, "This platform does not support debug features.\n");
return -1;
}
__ONLP_DEFAULTI_IMPLEMENTATION(onlp_sysi_platform_set(const char* p));
__ONLP_DEFAULTI_IMPLEMENTATION(onlp_sysi_init(void));
__ONLP_DEFAULTI_IMPLEMENTATION(onlp_sysi_onie_data_phys_addr_get(void** physaddr));

View File

@@ -3,7 +3,7 @@
#
# Inclusive Makefile for the onlp_platform_defaults module.
#
# Autogenerated 2016-01-07 22:54:28.940349
# Autogenerated 2016-03-23 18:28:25.688419
#
###############################################################################
onlp_platform_defaults_BASEDIR := $(dir $(abspath $(lastword $(MAKEFILE_LIST))))

View File

@@ -45,6 +45,23 @@
*/
#define ONLP_I2C_F_PEC 0x4
/**
* Do not deselect mux channels after device operations.
* The default is to deselect all intermediate muxes if possible.
*/
#define ONLP_I2C_F_NO_MUX_DESELECT 0x8
/**
* Do not select mux channels prior to device operations.
* The default is to select all intermediate muxes.
*
* This option is useful if you want to manually select
* the mux channels for multiple operations.
*/
#define ONLP_I2C_F_NO_MUX_SELECT 0x10
/**
* @brief Open and prepare for reading or writing.
* @param bus The i2c bus number.
@@ -150,6 +167,178 @@ int onlp_i2c_writew(int bus, uint8_t addr, uint8_t offset, uint16_t word,
uint32_t flags);
/****************************************************************************
*
* I2C Mux/Device Management.
*
*
***************************************************************************/
/**
* An i2c mux device driver.
*/
typedef struct onlp_i2c_mux_driver_s {
/** Driver Name */
const char* name;
/** Control register address for this mux. */
uint8_t control;
/** Channel select values. */
struct {
int channel;
uint8_t value;
} channels[16];
} onlp_i2c_mux_driver_t;
/**
* An i2c mux device.
*
*/
typedef struct onlp_i2c_mux_device_s {
/* Instance description. */
const char* name;
/** i2c bus number */
int bus;
/** i2c address for this instance */
uint8_t devaddr;
/** Mux device driver */
onlp_i2c_mux_driver_t* driver;
} onlp_i2c_mux_device_t;
/**
* Description of a channel.
*/
typedef struct onlp_i2c_mux_channel_s {
onlp_i2c_mux_device_t* mux;
int channel;
} onlp_i2c_mux_channel_t;
/**
* A set of i2c mux channels to program.
*/
typedef struct onlp_i2c_mux_channels_s {
onlp_i2c_mux_channel_t channels[8];
} onlp_i2c_mux_channels_t;
/**
* An i2c device.
*
* The device can be accessed only after selecting it's channel tree.
*/
typedef struct onlp_i2c_dev_s {
const char* name;
/**
* The sequence of mux channels can be specified
* inline or via pointer.
*/
onlp_i2c_mux_channels_t ichannels;
onlp_i2c_mux_channels_t* pchannels;
/**
* Bus and address for this device after channel tree selection.
*/
int bus;
uint8_t addr;
} onlp_i2c_dev_t;
/**
* @brief Select a mux channel.
* @param muxdev The mux device instance.
* @param channel The channel number to select.
*/
int onlp_i2c_mux_select(onlp_i2c_mux_device_t* muxdev, int channel);
/**
* @brief Deselect a mux channel.
* @param muxdev The mux device instance.
*/
int onlp_i2c_mux_deselect(onlp_i2c_mux_device_t* muxdev);
/**
* @brief Select a mux channel.
*/
int onlp_i2c_mux_channel_select(onlp_i2c_mux_channel_t* mc);
/**
* @brief Select a mux channel.
*/
int onlp_i2c_mux_channel_deselect(onlp_i2c_mux_channel_t* mc);
/**
* @brief Select a mux channel tree.
*/
int onlp_i2c_mux_channels_select(onlp_i2c_mux_channels_t* channels);
/**
* @brief Deselect a mux channel tree.
*/
int onlp_i2c_mux_channels_deselect(onlp_i2c_mux_channels_t* channels);
/**
* @brief Select a device's mux channel tree.
*/
int onlp_i2c_dev_mux_channels_select(onlp_i2c_dev_t* dev);
/**
* @brief Deselect a device's mux channel tree.
*/
int onlp_i2c_dev_mux_channels_deselect(onlp_i2c_dev_t* dev);
/**
* @brief Read from an device.
*/
int onlp_i2c_dev_read(onlp_i2c_dev_t* dev, uint8_t offset, int size,
uint8_t* rdata, uint32_t flags);
/**
* @brief Write to a device.
*/
int onlp_i2c_dev_write(onlp_i2c_dev_t* dev,
uint8_t offset, int size,
uint8_t* data, uint32_t flags);
int onlp_i2c_dev_readb(onlp_i2c_dev_t* dev,
uint8_t offset, uint32_t flags);
int onlp_i2c_dev_writeb(onlp_i2c_dev_t* dev,
uint8_t offset, uint8_t byte, uint32_t flags);
int onlp_i2c_dev_readw(onlp_i2c_dev_t* dev,
uint8_t offset, uint32_t flags);
int onlp_i2c_dev_writew(onlp_i2c_dev_t* dev,
uint8_t offset, uint16_t word, uint32_t flags);
/**************************************************************************//**
*
* Reusable MUX device drivers.
*
*****************************************************************************/
extern onlp_i2c_mux_driver_t onlp_i2c_mux_driver_pca9547a;
extern onlp_i2c_mux_driver_t onlp_i2c_mux_driver_pca9548;
#endif /* ONLPLIB_CONFIG_INCLUDE_I2C */
#endif /* __ONLP_I2C_H__ */

View File

@@ -39,7 +39,7 @@
} while(0)
#define ONLP_ACTIVE_LOW_MASKS_BIT(_enable, _bit, _andmask, _ormask) \
ONLP_ACTIVE_LOAS_MASKS(_enable, (1 << (_bit)), _andmask, _ormask)
ONLP_ACTIVE_LOW_MASKS(_enable, (1 << (_bit)), _andmask, _ormask)
/**
* Set and & or masks for active high bits.

View File

@@ -255,4 +255,315 @@ onlp_i2c_writew(int bus, uint8_t addr, uint8_t offset, uint16_t word,
}
int
onlp_i2c_mux_select(onlp_i2c_mux_device_t* dev, int channel)
{
int i;
for(i = 0; i < AIM_ARRAYSIZE(dev->driver->channels); i++) {
if(dev->driver->channels[i].channel == channel) {
AIM_LOG_VERBOSE("i2c_mux_select: Selecting channel %2d on device '%s' [ bus=%d addr=0x%x offset=0x%x value=0x%x ]...",
channel, dev->name, dev->bus, dev->devaddr,
dev->driver->control, dev->driver->channels[i].value);
int rv = onlp_i2c_writeb(dev->bus,
dev->devaddr,
dev->driver->control,
dev->driver->channels[i].value,
0);
if(rv < 0) {
AIM_LOG_ERROR("i2c_mux_select: Selecting channel %2d on device '%s' [ bus=%d addr=0x%x offset=0x%x value=0x%x ] failed: %d",
channel, dev->name, dev->bus, dev->devaddr,
dev->driver->control, dev->driver->channels[i].value, rv);
}
return rv;
}
}
return ONLP_STATUS_E_PARAM;
}
int
onlp_i2c_mux_deselect(onlp_i2c_mux_device_t* dev)
{
return onlp_i2c_mux_select(dev, -1);
}
int
onlp_i2c_mux_channel_select(onlp_i2c_mux_channel_t* mc)
{
return onlp_i2c_mux_select(mc->mux, mc->channel);
}
int
onlp_i2c_mux_channel_deselect(onlp_i2c_mux_channel_t* mc)
{
return onlp_i2c_mux_deselect(mc->mux);
}
int
onlp_i2c_mux_channels_select(onlp_i2c_mux_channels_t* mcs)
{
int i;
for(i = 0; i < AIM_ARRAYSIZE(mcs->channels); i++) {
if(mcs->channels[i].mux) {
int rv = onlp_i2c_mux_channel_select(mcs->channels + i);
if(rv < 0) {
/** Error already reported */
return rv;
}
}
}
return 0;
}
int
onlp_i2c_mux_channels_deselect(onlp_i2c_mux_channels_t* mcs)
{
int i;
for(i = AIM_ARRAYSIZE(mcs->channels) - 1; i >= 0; i--) {
if(mcs->channels[i].mux) {
int rv = onlp_i2c_mux_channel_deselect(mcs->channels + i);
if(rv < 0) {
/** Error already reported. */
return rv;
}
}
}
return 0;
}
int
onlp_i2c_dev_mux_channels_select(onlp_i2c_dev_t* dev)
{
if(dev->pchannels) {
return onlp_i2c_mux_channels_select(dev->pchannels);
}
else {
return onlp_i2c_mux_channels_select(&dev->ichannels);
}
}
int
onlp_i2c_dev_mux_channels_deselect(onlp_i2c_dev_t* dev)
{
if(dev->pchannels) {
return onlp_i2c_mux_channels_deselect(dev->pchannels);
}
else {
return onlp_i2c_mux_channels_deselect(&dev->ichannels);
}
}
static int
dev_mux_channels_select__(onlp_i2c_dev_t* dev, uint32_t flags)
{
if(flags & ONLP_I2C_F_NO_MUX_SELECT) {
return 0;
}
return onlp_i2c_dev_mux_channels_select(dev);
}
static int
dev_mux_channels_deselect__(onlp_i2c_dev_t* dev, uint32_t flags)
{
if(flags & ONLP_I2C_F_NO_MUX_DESELECT) {
return 0;
}
return onlp_i2c_dev_mux_channels_deselect(dev);
}
int
onlp_i2c_dev_read(onlp_i2c_dev_t* dev, uint8_t offset, int size,
uint8_t* rdata, uint32_t flags)
{
int error, rv;
if( (error = dev_mux_channels_select__(dev, flags)) < 0) {
return error;
}
if( (rv = onlp_i2c_read(dev->bus, dev->addr, offset, size, rdata, flags)) < 0) {
AIM_LOG_ERROR("Device %s: read() failed: %d",
dev->name, rv);
return rv;
}
if( (error = dev_mux_channels_deselect__(dev, flags)) < 0) {
return error;
}
return rv;
}
int
onlp_i2c_dev_write(onlp_i2c_dev_t* dev,
uint8_t offset, int size, uint8_t* data, uint32_t flags)
{
int error, rv;
if( (error = dev_mux_channels_select__(dev, flags)) < 0) {
return error;
}
if( (rv = onlp_i2c_write(dev->bus, dev->addr, offset, size, data, flags)) < 0) {
AIM_LOG_ERROR("Device %s: write() failed: %d",
dev->name, rv);
return rv;
}
if( (error = dev_mux_channels_deselect__(dev, flags)) < 0) {
return error;
}
return rv;
}
int
onlp_i2c_dev_readb(onlp_i2c_dev_t* dev, uint8_t offset, uint32_t flags)
{
int error, rv;
if( (error = dev_mux_channels_select__(dev, flags)) < 0) {
return error;
}
if( (rv = onlp_i2c_readb(dev->bus, dev->addr, offset, flags)) < 0) {
AIM_LOG_ERROR("Device %s: readb() failed: %d",
dev->name, rv);
return rv;
}
if( (error = dev_mux_channels_deselect__(dev, flags)) < 0) {
return error;
}
return rv;
}
int
onlp_i2c_dev_writeb(onlp_i2c_dev_t* dev,
uint8_t offset, uint8_t byte, uint32_t flags)
{
int error, rv;
if( (error = dev_mux_channels_select__(dev, flags)) < 0) {
return error;
}
if( (rv = onlp_i2c_writeb(dev->bus, dev->addr, offset, byte, flags)) < 0) {
AIM_LOG_ERROR("Device %s: writeb() failed: %d",
dev->name, rv);
return rv;
}
if( (error = dev_mux_channels_deselect__(dev, flags)) < 0) {
return error;
}
return rv;
}
int
onlp_i2c_dev_readw(onlp_i2c_dev_t* dev,
uint8_t offset, uint32_t flags)
{
int error, rv;
if( (error = dev_mux_channels_select__(dev, flags)) < 0) {
return error;
}
if( (rv = onlp_i2c_readw(dev->bus, dev->addr, offset, flags)) < 0) {
AIM_LOG_ERROR("Device %s: readw() failed: %d",
dev->name, rv);
return rv;
}
if( (error = dev_mux_channels_deselect__(dev, flags)) < 0) {
return error;
}
return rv;
}
int
onlp_i2c_dev_writew(onlp_i2c_dev_t* dev,
uint8_t offset, uint16_t word, uint32_t flags)
{
int error, rv;
if( (error = dev_mux_channels_select__(dev, flags)) < 0) {
return error;
}
if( (rv = onlp_i2c_writew(dev->bus, dev->addr, offset, word, flags)) < 0) {
AIM_LOG_ERROR("Device %s: writew() failed: %d",
dev->name, rv);
return rv;
}
if( (error = dev_mux_channels_deselect__(dev, flags)) < 0) {
return error;
}
return rv;
}
/**
* PCA9547A
*/
onlp_i2c_mux_driver_t onlp_i2c_mux_driver_pca9547a =
{
.name = "PCA9547A",
.control = 0,
.channels =
{
{ -1, 0 },
{ 0, 0x8 },
{ 1, 0x9 },
{ 2, 0xA },
{ 3, 0xB },
{ 4, 0xC },
{ 5, 0xD },
{ 6, 0xE },
{ 7, 0xF },
},
};
/**
* PCA9548
*/
onlp_i2c_mux_driver_t onlp_i2c_mux_driver_pca9548 =
{
.name = "PCA9548A",
.control = 0,
.channels =
{
{ -1, 0x00 },
{ 0, 0x01 },
{ 1, 0x02 },
{ 2, 0x04 },
{ 3, 0x08 },
{ 4, 0x10 },
{ 5, 0x20 },
{ 6, 0x40 },
{ 7, 0x80 },
},
};
#endif /* ONLPLIB_CONFIG_INCLUDE_I2C */

View File

@@ -3,7 +3,7 @@
#
# Inclusive Makefile for the onlplib module.
#
# Autogenerated 2016-01-07 22:54:29.056595
# Autogenerated 2016-03-23 18:28:25.806397
#
###############################################################################
onlplib_BASEDIR := $(dir $(abspath $(lastword $(MAKEFILE_LIST))))

View File

@@ -48,6 +48,8 @@ sff_module_types: &sff_module_types
desc: "100GBASE-SR4"
- 100G_BASE_LR4:
desc: "100GBASE-LR4"
- 100G_CWDM4:
desc: "100G-CWDM4"
- 40G_BASE_CR4:
desc: "40GBASE-CR4"
- 40G_BASE_SR4:

View File

@@ -777,13 +777,18 @@ _sff8472_media_zr(const uint8_t *idprom)
if (SFF8472_MEDIA_XGE_LRM(idprom)) return 0;
if (SFF8472_MEDIA_XGE_ER(idprom)) return 0;
/* advertise media and tech as per FC */
if (_sff8472_tech_fc_ll(idprom) == 0) return 0;
if (_sff8472_fc_media_sm(idprom) == 0) return 0;
/* JSM-01ZWBA1 from JDSU does not have FC field(idprom[7~9] programmed,
* so check other fields first */
/* at least 10GbE */
if (!_sff8472_bitrate_xge(idprom)) return 0;
/* JSM-01ZWBA1 from JDSU is 80km */
if (idprom[14] == 80)
return 1;
/* advertise media and tech as per FC */
if (_sff8472_tech_fc_ll(idprom) == 0) return 0;
if (_sff8472_fc_media_sm(idprom) == 0) return 0;
/* at least 40km of single-mode */
if ((idprom[14] > 40) && (idprom[15] == 0xff))
return 1;

View File

@@ -129,10 +129,9 @@
#define SFF8636_CC192_100GE_AOC 0x01
#define SFF8636_CC192_100GE_SR4 0x02
#define SFF8636_CC192_100GE_LR4 0x03
#define SFF8636_CC192_100GE_CWDM4_FEC 0x06
#define SFF8636_CC192_100GE_CWDM4 0x06
#define SFF8636_CC192_100GE_PSM4 0x07
#define SFF8636_CC192_100GE_ACC 0x08
#define SFF8636_CC192_100GE_CWDM4_NOFEC 0x09
#define SFF8636_CC192_100GE_CR4 0x0B
#define SFF8636_MEDIA_100GE_AOC(idprom) \
@@ -141,6 +140,8 @@
(idprom[192] == SFF8636_CC192_100GE_SR4)
#define SFF8636_MEDIA_100GE_LR4(idprom) \
(idprom[192] == SFF8636_CC192_100GE_LR4)
#define SFF8636_MEDIA_100GE_CWDM4(idprom) \
(idprom[192] == SFF8636_CC192_100GE_CWDM4)
#define SFF8636_MEDIA_100GE_CR4(idprom) \
(idprom[192] == SFF8636_CC192_100GE_CR4)

View File

@@ -99,6 +99,7 @@ typedef enum sff_module_type_e {
SFF_MODULE_TYPE_100G_BASE_CR4,
SFF_MODULE_TYPE_100G_BASE_SR4,
SFF_MODULE_TYPE_100G_BASE_LR4,
SFF_MODULE_TYPE_100G_CWDM4,
SFF_MODULE_TYPE_40G_BASE_CR4,
SFF_MODULE_TYPE_40G_BASE_SR4,
SFF_MODULE_TYPE_40G_BASE_LR4,
@@ -132,6 +133,7 @@ typedef enum sff_module_type_e {
"100G_BASE_CR4", \
"100G_BASE_SR4", \
"100G_BASE_LR4", \
"100G_CWDM4", \
"40G_BASE_CR4", \
"40G_BASE_SR4", \
"40G_BASE_LR4", \

View File

@@ -68,6 +68,11 @@ sff_module_type_get(const uint8_t* idprom)
&& SFF8636_MEDIA_EXTENDED(idprom)
&& SFF8636_MEDIA_100GE_CR4(idprom))
return SFF_MODULE_TYPE_100G_BASE_CR4;
if (SFF8636_MODULE_QSFP28(idprom)
&& SFF8636_MEDIA_EXTENDED(idprom)
&& SFF8636_MEDIA_100GE_CWDM4(idprom))
return SFF_MODULE_TYPE_100G_CWDM4;
if (SFF8436_MODULE_QSFP_PLUS_V2(idprom)
&& SFF8436_MEDIA_40GE_CR4(idprom))
@@ -214,6 +219,7 @@ sff_media_type_get(const uint8_t* idprom)
case SFF_MODULE_TYPE_100G_AOC:
case SFF_MODULE_TYPE_100G_BASE_SR4:
case SFF_MODULE_TYPE_100G_BASE_LR4:
case SFF_MODULE_TYPE_100G_CWDM4:
case SFF_MODULE_TYPE_40G_BASE_SR4:
case SFF_MODULE_TYPE_40G_BASE_LR4:
case SFF_MODULE_TYPE_40G_BASE_ACTIVE:
@@ -257,6 +263,7 @@ sff_module_caps_get(const uint8_t* idprom, uint32_t *caps)
case SFF_MODULE_TYPE_100G_BASE_SR4:
case SFF_MODULE_TYPE_100G_BASE_LR4:
case SFF_MODULE_TYPE_100G_BASE_CR4:
case SFF_MODULE_TYPE_100G_CWDM4:
*caps |= SFF_MODULE_CAPS_F_100G;
return 0;
@@ -373,6 +380,49 @@ sff_info_init(sff_info_t* rv, uint8_t* eeprom)
}
rv->sfp_type_name = sff_sfp_type_desc(rv->sfp_type);
const uint8_t *vendor, *model, *serial;
switch(rv->sfp_type)
{
case SFF_SFP_TYPE_QSFP_PLUS:
case SFF_SFP_TYPE_QSFP28:
vendor=rv->eeprom+148;
model=rv->eeprom+168;
serial=rv->eeprom+196;
break;
case SFF_SFP_TYPE_SFP:
default:
vendor=rv->eeprom+20;
model=rv->eeprom+40;
serial=rv->eeprom+68;
break;
}
/* handle NULL fields, they should actually be space-padded */
const char *empty = " ";
if (*vendor) {
aim_strlcpy(rv->vendor, (char*)vendor, sizeof(rv->vendor));
make_printable__(rv->vendor);
}
else {
aim_strlcpy(rv->vendor, empty, 17);
}
if (*model) {
aim_strlcpy(rv->model, (char*)model, sizeof(rv->model));
make_printable__(rv->model);
}
else {
aim_strlcpy(rv->model, empty, 17);
}
if (*serial) {
aim_strlcpy(rv->serial, (char*)serial, sizeof(rv->serial));
make_printable__(rv->serial);
}
else {
aim_strlcpy(rv->serial, empty, 17);
}
rv->module_type = sff_module_type_get(rv->eeprom);
if(rv->module_type == SFF_MODULE_TYPE_INVALID) {
AIM_LOG_ERROR("sff_info_init() failed: invalid module type");
@@ -429,49 +479,6 @@ sff_info_init(sff_info_t* rv, uint8_t* eeprom)
rv->length = -1;
}
const uint8_t *vendor, *model, *serial;
switch(rv->sfp_type)
{
case SFF_SFP_TYPE_QSFP_PLUS:
case SFF_SFP_TYPE_QSFP28:
vendor=rv->eeprom+148;
model=rv->eeprom+168;
serial=rv->eeprom+196;
break;
case SFF_SFP_TYPE_SFP:
default:
vendor=rv->eeprom+20;
model=rv->eeprom+40;
serial=rv->eeprom+68;
break;
}
/* handle NULL fields, they should actually be space-padded */
const char *empty = " ";
if (*vendor) {
aim_strlcpy(rv->vendor, (char*)vendor, sizeof(rv->vendor));
make_printable__(rv->vendor);
}
else {
aim_strlcpy(rv->vendor, empty, 17);
}
if (*model) {
aim_strlcpy(rv->model, (char*)model, sizeof(rv->model));
make_printable__(rv->model);
}
else {
aim_strlcpy(rv->model, empty, 17);
}
if (*serial) {
aim_strlcpy(rv->serial, (char*)serial, sizeof(rv->serial));
make_printable__(rv->serial);
}
else {
aim_strlcpy(rv->serial, empty, 17);
}
if(rv->length == -1) {
rv->length_desc[0] = 0;
}

View File

@@ -133,6 +133,7 @@ aim_map_si_t sff_module_type_map[] =
{ "100G_BASE_CR4", SFF_MODULE_TYPE_100G_BASE_CR4 },
{ "100G_BASE_SR4", SFF_MODULE_TYPE_100G_BASE_SR4 },
{ "100G_BASE_LR4", SFF_MODULE_TYPE_100G_BASE_LR4 },
{ "100G_CWDM4", SFF_MODULE_TYPE_100G_CWDM4 },
{ "40G_BASE_CR4", SFF_MODULE_TYPE_40G_BASE_CR4 },
{ "40G_BASE_SR4", SFF_MODULE_TYPE_40G_BASE_SR4 },
{ "40G_BASE_LR4", SFF_MODULE_TYPE_40G_BASE_LR4 },
@@ -163,6 +164,7 @@ aim_map_si_t sff_module_type_desc_map[] =
{ "100GBASE-CR4", SFF_MODULE_TYPE_100G_BASE_CR4 },
{ "100GBASE-SR4", SFF_MODULE_TYPE_100G_BASE_SR4 },
{ "100GBASE-LR4", SFF_MODULE_TYPE_100G_BASE_LR4 },
{ "100G-CWDM4", SFF_MODULE_TYPE_100G_CWDM4 },
{ "40GBASE-CR4", SFF_MODULE_TYPE_40G_BASE_CR4 },
{ "40GBASE-SR4", SFF_MODULE_TYPE_40G_BASE_SR4 },
{ "40GBASE-LR4", SFF_MODULE_TYPE_40G_BASE_LR4 },

View File

@@ -3,7 +3,7 @@
#
# Inclusive Makefile for the sff module.
#
# Autogenerated 2016-01-07 22:54:29.117990
# Autogenerated 2016-03-23 18:28:25.869697
#
###############################################################################
sff_BASEDIR := $(dir $(abspath $(lastword $(MAKEFILE_LIST))))