|
Packit |
857059 |
/* BEGIN_ICS_COPYRIGHT4 ****************************************
|
|
Packit |
857059 |
|
|
Packit |
857059 |
Copyright (c) 2015-2017, Intel Corporation
|
|
Packit |
857059 |
|
|
Packit |
857059 |
Redistribution and use in source and binary forms, with or without
|
|
Packit |
857059 |
modification, are permitted provided that the following conditions are met:
|
|
Packit |
857059 |
|
|
Packit |
857059 |
* Redistributions of source code must retain the above copyright notice,
|
|
Packit |
857059 |
this list of conditions and the following disclaimer.
|
|
Packit |
857059 |
* Redistributions in binary form must reproduce the above copyright
|
|
Packit |
857059 |
notice, this list of conditions and the following disclaimer in the
|
|
Packit |
857059 |
documentation and/or other materials provided with the distribution.
|
|
Packit |
857059 |
* Neither the name of Intel Corporation nor the names of its contributors
|
|
Packit |
857059 |
may be used to endorse or promote products derived from this software
|
|
Packit |
857059 |
without specific prior written permission.
|
|
Packit |
857059 |
|
|
Packit |
857059 |
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
|
Packit |
857059 |
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
|
Packit |
857059 |
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
Packit |
857059 |
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
|
|
Packit |
857059 |
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
|
Packit |
857059 |
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
|
Packit |
857059 |
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
|
Packit |
857059 |
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
|
Packit |
857059 |
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
|
Packit |
857059 |
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
Packit |
857059 |
|
|
Packit |
857059 |
** END_ICS_COPYRIGHT4 ****************************************/
|
|
Packit |
857059 |
/*!
|
|
Packit |
857059 |
|
|
Packit |
857059 |
\file dsap_module.c
|
|
Packit |
857059 |
|
|
Packit |
857059 |
$Revision: 1.5 $
|
|
Packit |
857059 |
$Date: 2015/01/27 23:00:24 $
|
|
Packit |
857059 |
|
|
Packit |
857059 |
\brief Provider initialization and cleanup functions.
|
|
Packit |
857059 |
*/
|
|
Packit |
857059 |
|
|
Packit |
857059 |
#include <ctype.h>
|
|
Packit |
857059 |
|
|
Packit |
857059 |
|
|
Packit |
857059 |
/*
|
|
Packit |
857059 |
ICS IBT stuff
|
|
Packit |
857059 |
*/
|
|
Packit |
857059 |
#include "iba/ibt.h"
|
|
Packit |
857059 |
#include "iba/public/isemaphore.h"
|
|
Packit |
857059 |
#include "opasadb_debug.h"
|
|
Packit |
857059 |
|
|
Packit |
857059 |
/*
|
|
Packit |
857059 |
Module stuff
|
|
Packit |
857059 |
*/
|
|
Packit |
857059 |
#include "dsap.h"
|
|
Packit |
857059 |
|
|
Packit |
857059 |
// Module parameters
|
|
Packit |
857059 |
|
|
Packit |
857059 |
|
|
Packit |
857059 |
uint32 dsap_dbg_level = _DBG_LVL_NOTICE;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
#define LOG_FILE_LENGTH 256
|
|
Packit |
857059 |
static char dsap_log_file[LOG_FILE_LENGTH] = {0};
|
|
Packit |
857059 |
static FILE *omgt_log_file = NULL;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
/*
|
|
Packit |
857059 |
* Parameter handling - replaces module parameters.
|
|
Packit |
857059 |
*
|
|
Packit |
857059 |
* name - variable name of the parameter.
|
|
Packit |
857059 |
* desc - human readable description
|
|
Packit |
857059 |
* type - enumerated type of the parameter (integer, unsigned, boolean, etc.)
|
|
Packit |
857059 |
* length - for string parameters, the max length of the string.
|
|
Packit |
857059 |
* ptr - pointer to the variable.
|
|
Packit |
857059 |
* parser - points to a function to handle special parameters.
|
|
Packit |
857059 |
* printer - points to a function that can print special parameters.
|
|
Packit |
857059 |
*/
|
|
Packit |
857059 |
typedef struct parameter {
|
|
Packit |
857059 |
char name[32];
|
|
Packit |
857059 |
char desc[256];
|
|
Packit |
857059 |
char type;
|
|
Packit |
857059 |
int length;
|
|
Packit |
857059 |
void *ptr;
|
|
Packit |
857059 |
int (*parser)(char *str, void *ptr);
|
|
Packit |
857059 |
char *(*printer)(void *ptr);
|
|
Packit |
857059 |
} parameter_t;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
static parameter_t parameters[] = {
|
|
Packit |
857059 |
{ .name="NoSubscribe",
|
|
Packit |
857059 |
.type='b',
|
|
Packit |
857059 |
.desc="Do not subscribe to SM for notifications.",
|
|
Packit |
857059 |
.length = 0,
|
|
Packit |
857059 |
.ptr=(void*)&dsap_no_subscribe},
|
|
Packit |
857059 |
{ .name="ScanFrequency",
|
|
Packit |
857059 |
.type='u',
|
|
Packit |
857059 |
.desc="Number of seconds between unconditional sweeps.",
|
|
Packit |
857059 |
.length = 0,
|
|
Packit |
857059 |
.ptr=(void*)&dsap_scan_frequency},
|
|
Packit |
857059 |
{ .name="UnsubscribedScanFrequency",
|
|
Packit |
857059 |
.type='u',
|
|
Packit |
857059 |
.desc="Number of seconds between sweeps when not receiving "
|
|
Packit |
857059 |
"notifications.",
|
|
Packit |
857059 |
.length = 0,
|
|
Packit |
857059 |
.ptr=(void*)&dsap_unsub_scan_frequency},
|
|
Packit |
857059 |
{ .name="Dbg",
|
|
Packit |
857059 |
.type='x',
|
|
Packit |
857059 |
.desc="Debug logging controls. Uses syslog log levels, ranging"
|
|
Packit |
857059 |
" from 1 (least)\n\tto 7 (trace level).",
|
|
Packit |
857059 |
.length = 0,
|
|
Packit |
857059 |
.ptr=(void*)&dsap_dbg_level},
|
|
Packit |
857059 |
{ .name="Publish",
|
|
Packit |
857059 |
.type='b',
|
|
Packit |
857059 |
.desc="Publish paths to shared memory. Defaults to true.",
|
|
Packit |
857059 |
.length = 0,
|
|
Packit |
857059 |
.ptr=(void*)&dsap_publish},
|
|
Packit |
857059 |
{ .name="SID",
|
|
Packit |
857059 |
.type='S',
|
|
Packit |
857059 |
.desc="Service ID that identifies a virtual fabric to include "
|
|
Packit |
857059 |
"in the cache.\n\tCan be specified multiple times.",
|
|
Packit |
857059 |
.parser=dsap_service_id_range_parser,
|
|
Packit |
857059 |
.printer=dsap_service_id_range_printer,
|
|
Packit |
857059 |
.ptr=(void*)&sid_range_args},
|
|
Packit |
857059 |
{ .name="LogFile",
|
|
Packit |
857059 |
.type='s',
|
|
Packit |
857059 |
.desc="Write log messages to a file instead of the system log"
|
|
Packit |
857059 |
"\n\tor stderr.",
|
|
Packit |
857059 |
.length = LOG_FILE_LENGTH,
|
|
Packit |
857059 |
.ptr=(void*)&dsap_log_file},
|
|
Packit |
857059 |
{ .name="dsap_default_fabric",
|
|
Packit |
857059 |
.type='S',
|
|
Packit |
857059 |
.desc="normal = do not match SIDs to the default fabric unless"
|
|
Packit |
857059 |
" they don't\n\t match any other fabric.\n\tnone = never"
|
|
Packit |
857059 |
" match SIDs to the default fabric.\n\t Defaults to "
|
|
Packit |
857059 |
"normal.",
|
|
Packit |
857059 |
.parser=dsap_default_fabric_parser,
|
|
Packit |
857059 |
.printer=dsap_default_fabric_printer,
|
|
Packit |
857059 |
.ptr=(void*)&dsap_default_fabric },
|
|
Packit |
857059 |
{"", "", 0, 0, NULL}
|
|
Packit |
857059 |
};
|
|
Packit |
857059 |
|
|
Packit |
857059 |
static void dsap_dump_params(parameter_t *params)
|
|
Packit |
857059 |
{
|
|
Packit |
857059 |
int i=0;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
while (params[i].ptr != NULL) {
|
|
Packit |
857059 |
switch (params[i].type) {
|
|
Packit |
857059 |
case 'S':
|
|
Packit |
857059 |
acm_log(0, "%s = %s\n", params[i].name,
|
|
Packit |
857059 |
params[i].printer(params[i].ptr));
|
|
Packit |
857059 |
break;
|
|
Packit |
857059 |
case 'X':
|
|
Packit |
857059 |
acm_log(0, "%s = 0x%016"PRIx64"\n", params[i].name,
|
|
Packit |
857059 |
(*(uint64 *) params[i].ptr));
|
|
Packit |
857059 |
break;
|
|
Packit |
857059 |
case 'x':
|
|
Packit |
857059 |
acm_log(0, "%s = 0x%x\n", params[i].name,
|
|
Packit |
857059 |
(*(uint32 *) params[i].ptr));
|
|
Packit |
857059 |
break;
|
|
Packit |
857059 |
case 'u':
|
|
Packit |
857059 |
acm_log(0, "%s = %u\n", params[i].name,
|
|
Packit |
857059 |
(*(uint32 *) params[i].ptr));
|
|
Packit |
857059 |
break;
|
|
Packit |
857059 |
case 'i':
|
|
Packit |
857059 |
acm_log(0, "%s = %i\n", params[i].name,
|
|
Packit |
857059 |
(*(int32 *) params[i].ptr));
|
|
Packit |
857059 |
break;
|
|
Packit |
857059 |
case 'b':
|
|
Packit |
857059 |
acm_log(0, "%s = %s\n", params[i].name,
|
|
Packit |
857059 |
(*(uint32 *) params[i].ptr) ? "yes" : "no");
|
|
Packit |
857059 |
break;
|
|
Packit |
857059 |
case 's':
|
|
Packit |
857059 |
acm_log(0, "%s = %s\n", params[i].name,
|
|
Packit |
857059 |
(char *)params[i].ptr);
|
|
Packit |
857059 |
break;
|
|
Packit |
857059 |
default:
|
|
Packit |
857059 |
acm_log(0, "%s = Unhandled parameter type.\n",
|
|
Packit |
857059 |
params[i].name);
|
|
Packit |
857059 |
break;
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
i++;
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
static char *dsap_trim(char *buffer)
|
|
Packit |
857059 |
{
|
|
Packit |
857059 |
char *p;
|
|
Packit |
857059 |
int j = strlen(buffer) - 1;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
/* Trim trailing whitespace. */
|
|
Packit |
857059 |
while (j>0 && isspace(buffer[j])) {
|
|
Packit |
857059 |
buffer[j] = 0;
|
|
Packit |
857059 |
j--;
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
p=buffer;
|
|
Packit |
857059 |
/* Trim leading whitespce.*/
|
|
Packit |
857059 |
j=0;
|
|
Packit |
857059 |
while (buffer[j]!=0 && isspace(buffer[j])) j++;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
p=&buffer[j];
|
|
Packit |
857059 |
if (*p == '#' || *p == '\n' || *p == 0)
|
|
Packit |
857059 |
return NULL;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
return p;
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
static int dsap_parse_record(parameter_t *params, char *buffer)
|
|
Packit |
857059 |
{
|
|
Packit |
857059 |
char *k, *v, *l;
|
|
Packit |
857059 |
int i=0;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
k=strtok_r(buffer, "=", &l);
|
|
Packit |
857059 |
v=strtok_r(NULL, "=", &l);
|
|
Packit |
857059 |
|
|
Packit |
857059 |
if (!k || !v) {
|
|
Packit |
857059 |
acm_log(0, "Config syntax error: %s\n", buffer);
|
|
Packit |
857059 |
return -1;
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
/* strip white space */
|
|
Packit |
857059 |
k=dsap_trim(k);
|
|
Packit |
857059 |
v=dsap_trim(v);
|
|
Packit |
857059 |
if (!k || !v) {
|
|
Packit |
857059 |
acm_log(0, "Config syntax error: %s\n", buffer);
|
|
Packit |
857059 |
return -1;
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
while (params[i].ptr != NULL && (k != NULL && v != NULL)) {
|
|
Packit |
857059 |
if (strncasecmp(k, params[i].name, strlen(k)) == 0) {
|
|
Packit |
857059 |
switch (params[i].type) {
|
|
Packit |
857059 |
case 'S':
|
|
Packit |
857059 |
return params[i].parser(v, params[i].ptr);
|
|
Packit |
857059 |
case 'X':
|
|
Packit |
857059 |
(*(uint64 *) params[i].ptr) =
|
|
Packit |
857059 |
strtoull(v, NULL, 0);
|
|
Packit |
857059 |
return 0;
|
|
Packit |
857059 |
case 'x':
|
|
Packit |
857059 |
case 'u':
|
|
Packit |
857059 |
(*(uint32 *) params[i].ptr) =
|
|
Packit |
857059 |
strtoul(v, NULL, 0);
|
|
Packit |
857059 |
return 0;
|
|
Packit |
857059 |
case 'i':
|
|
Packit |
857059 |
(*(int32 *) params[i].ptr) =
|
|
Packit |
857059 |
strtol(v, NULL, 0);
|
|
Packit |
857059 |
return 0;
|
|
Packit |
857059 |
case 's':
|
|
Packit |
857059 |
strncpy((char *) params[i].ptr, v,
|
|
Packit |
857059 |
params[i].length);
|
|
Packit |
857059 |
((char *) params[i].ptr)[params[i].length - 1] = 0;
|
|
Packit |
857059 |
return 0;
|
|
Packit |
857059 |
case 'b':
|
|
Packit |
857059 |
if (strcmp(v,"yes")==0 ||
|
|
Packit |
857059 |
strcmp(v,"y") == 0 ||
|
|
Packit |
857059 |
strcmp(v,"true") == 0 ||
|
|
Packit |
857059 |
strcmp(v,"t") == 0)
|
|
Packit |
857059 |
(*(uint32 *) params[i].ptr) = 1;
|
|
Packit |
857059 |
else
|
|
Packit |
857059 |
(*(uint32 *) params[i].ptr) =
|
|
Packit |
857059 |
strtol(v, NULL, 0);
|
|
Packit |
857059 |
return 0;
|
|
Packit |
857059 |
default:
|
|
Packit |
857059 |
acm_log(0, "Unrecognized token in config.\n");
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
i++;
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
return -1;
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
static int dsap_parse_settings(char *filename, parameter_t *params)
|
|
Packit |
857059 |
{
|
|
Packit |
857059 |
int err = 0;
|
|
Packit |
857059 |
char *ptr;
|
|
Packit |
857059 |
char record[1024];
|
|
Packit |
857059 |
FILE *f;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
acm_log(2, "\n");
|
|
Packit |
857059 |
f = fopen(filename,"r");
|
|
Packit |
857059 |
if (!f) {
|
|
Packit |
857059 |
acm_log(0, "Unable to open config file %s.\n", filename);
|
|
Packit |
857059 |
err=-1;
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
while(!err && fgets(record, 1024, f)) {
|
|
Packit |
857059 |
ptr = dsap_trim(record);
|
|
Packit |
857059 |
if (ptr) {
|
|
Packit |
857059 |
if ((err = dsap_parse_record(params, record)))
|
|
Packit |
857059 |
acm_log(0, "Invalid Config Option: %s\n", ptr);
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
if (f) fclose(f);
|
|
Packit |
857059 |
return err;
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
/* Get dsap's own configuration parameters */
|
|
Packit |
857059 |
void dsap_get_config(char *filename)
|
|
Packit |
857059 |
{
|
|
Packit |
857059 |
if (dsap_parse_settings(filename, parameters))
|
|
Packit |
857059 |
return;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
if (dsap_dbg_level > 7) dsap_dbg_level = 7;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
if (strlen(dsap_log_file) > 0) {
|
|
Packit |
857059 |
op_log_set_file(dsap_log_file);
|
|
Packit |
857059 |
op_log_set_level(dsap_dbg_level);
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
dsap_dump_params(parameters);
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
|
|
Packit |
857059 |
/*!
|
|
Packit |
857059 |
\brief Cleanup function called when the provider is unloaded.
|
|
Packit |
857059 |
*/
|
|
Packit |
857059 |
|
|
Packit |
857059 |
void dsap_cleanup(void)
|
|
Packit |
857059 |
{
|
|
Packit |
857059 |
acm_log(2, "\n");
|
|
Packit |
857059 |
|
|
Packit |
857059 |
dsap_scanner_cleanup();
|
|
Packit |
857059 |
dsap_topology_cleanup();
|
|
Packit |
857059 |
|
|
Packit |
857059 |
if (omgt_log_file)
|
|
Packit |
857059 |
fclose(omgt_log_file);
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
|
|
Packit |
857059 |
/*!
|
|
Packit |
857059 |
\brief Init function called when the provider is loaded.
|
|
Packit |
857059 |
*/
|
|
Packit |
857059 |
|
|
Packit |
857059 |
FSTATUS
|
|
Packit |
857059 |
dsap_init(void)
|
|
Packit |
857059 |
{
|
|
Packit |
857059 |
FSTATUS fstatus = FERROR;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
acm_log(2, "\n");
|
|
Packit |
857059 |
|
|
Packit |
857059 |
|
|
Packit |
857059 |
fstatus = dsap_topology_init();
|
|
Packit |
857059 |
if (fstatus != FSUCCESS)
|
|
Packit |
857059 |
goto exit;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
fstatus = dsap_scanner_init();
|
|
Packit |
857059 |
if (FSUCCESS != fstatus)
|
|
Packit |
857059 |
goto exit;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
/* Guard against scans without timeout */
|
|
Packit |
857059 |
if (dsap_unsub_scan_frequency == 0)
|
|
Packit |
857059 |
dsap_unsub_scan_frequency = 10;
|
|
Packit |
857059 |
|
|
Packit |
857059 |
fstatus = dsap_scanner_start();
|
|
Packit |
857059 |
|
|
Packit |
857059 |
exit:
|
|
Packit |
857059 |
return fstatus;
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
void dsap_omgt_log_init(struct omgt_port *omgt_port)
|
|
Packit |
857059 |
{
|
|
Packit |
857059 |
if (strlen(dsap_log_file) > 0) {
|
|
Packit |
857059 |
omgt_log_file = op_log_get_file();
|
|
Packit |
857059 |
omgt_set_err(omgt_port, omgt_log_file);
|
|
Packit |
857059 |
if (dsap_dbg_level >= 7)
|
|
Packit |
857059 |
omgt_set_dbg(omgt_port, omgt_log_file);
|
|
Packit |
857059 |
}
|
|
Packit |
857059 |
}
|