mirror of
https://github.com/ipmitool/ipmitool.git
synced 2025-05-10 18:47:22 +00:00
updates from sourceforge,
changes to support settable SOL escape char
This commit is contained in:
parent
ed8a467f6d
commit
d6e85b8427
@ -68,7 +68,7 @@ enum LANPLUS_SESSION_STATE {
|
||||
|
||||
struct ipmi_session {
|
||||
uint8_t hostname[64];
|
||||
uint8_t username[16];
|
||||
uint8_t username[17];
|
||||
uint8_t authcode[IPMI_AUTHCODE_BUFFER_SIZE + 1];
|
||||
uint8_t challenge[16];
|
||||
uint8_t authtype;
|
||||
@ -82,6 +82,7 @@ struct ipmi_session {
|
||||
uint8_t authextra;
|
||||
uint8_t privlvl;
|
||||
uint8_t cipher_suite_id;
|
||||
char sol_escape_char;
|
||||
int password;
|
||||
int port;
|
||||
int active;
|
||||
@ -194,6 +195,8 @@ void ipmi_intf_session_set_username(struct ipmi_intf * intf, char * username);
|
||||
void ipmi_intf_session_set_password(struct ipmi_intf * intf, char * password);
|
||||
void ipmi_intf_session_set_privlvl(struct ipmi_intf * intf, uint8_t privlvl);
|
||||
void ipmi_intf_session_set_cipher_suite_id(struct ipmi_intf * intf, uint8_t cipher_suite_id);
|
||||
void ipmi_intf_session_set_sol_escape_char(struct ipmi_intf * intf, char sol_escape_char);
|
||||
void ipmi_intf_session_set_kgkey(struct ipmi_intf * intf, char * kgkey);
|
||||
void ipmi_intf_session_set_port(struct ipmi_intf * intf, int port);
|
||||
void ipmi_intf_session_set_authtype(struct ipmi_intf * intf, uint8_t authtype);
|
||||
void ipmi_intf_session_set_timeout(struct ipmi_intf * intf, uint32_t timeout);
|
||||
|
@ -39,6 +39,7 @@
|
||||
|
||||
#include <ipmitool/ipmi.h>
|
||||
|
||||
#define SOL_ESCAPE_CHARACTER_DEFAULT '~'
|
||||
|
||||
#define IPMI_SOL_SERIAL_ALERT_MASK_SUCCEED 0x08
|
||||
#define IPMI_SOL_SERIAL_ALERT_MASK_DEFERRED 0x04
|
||||
|
@ -48,6 +48,17 @@
|
||||
# include <config.h>
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Apparently some systems have problems with FRU access greater than 16 bytes
|
||||
* at a time, even when using byte (not word) access. In order to ensure we
|
||||
* work with the widest variety of hardware request size is capped at 16 bytes.
|
||||
* Since this may result in slowdowns on some systems with lots of FRU data you
|
||||
* can undefine this to enable larger (up to 32 bytes at a time) access.
|
||||
*
|
||||
* TODO: make this a command line option
|
||||
*/
|
||||
#define LIMIT_ALL_REQUEST_SIZE 1
|
||||
|
||||
extern int verbose;
|
||||
extern int ipmi_spd_print(struct ipmi_intf * intf, uint8_t id);
|
||||
static void ipmi_fru_read_to_bin(struct ipmi_intf * intf,unsigned char * pFileName, unsigned char fruId);
|
||||
@ -216,9 +227,13 @@ write_fru_area(struct ipmi_intf * intf, struct fru_info *fru, unsigned char id,
|
||||
req.msg.netfn = IPMI_NETFN_STORAGE;
|
||||
req.msg.cmd = SET_FRU_DATA;
|
||||
req.msg.data = msg_data;
|
||||
|
||||
|
||||
#ifdef LIMIT_ALL_REQUEST_SIZE
|
||||
if (fru_data_rqst_size > 16)
|
||||
#else
|
||||
if (fru->access && fru_data_rqst_size > 16)
|
||||
fru_data_rqst_size = 16;
|
||||
#endif
|
||||
fru_data_rqst_size = 16;
|
||||
do
|
||||
{
|
||||
/* real destination offset */
|
||||
@ -301,7 +316,11 @@ read_fru_area(struct ipmi_intf * intf, struct fru_info *fru, uint8_t id,
|
||||
req.msg.data = msg_data;
|
||||
req.msg.data_len = 4;
|
||||
|
||||
#ifdef LIMIT_ALL_REQUEST_SIZE
|
||||
if (fru_data_rqst_size > 16)
|
||||
#else
|
||||
if (fru->access && fru_data_rqst_size > 16)
|
||||
#endif
|
||||
fru_data_rqst_size = 16;
|
||||
do {
|
||||
tmp = fru->access ? off >> 1 : off;
|
||||
@ -320,8 +339,6 @@ read_fru_area(struct ipmi_intf * intf, struct fru_info *fru, uint8_t id,
|
||||
break;
|
||||
}
|
||||
if (rsp->ccode > 0) {
|
||||
lprintf(LOG_NOTICE, "FRU Read failed: %s",
|
||||
val2str(rsp->ccode, completion_code_vals));
|
||||
/* if we get C7 or C8 or CA return code then we requested too
|
||||
* many bytes at once so try again with smaller size */
|
||||
if ((rsp->ccode == 0xc7 || rsp->ccode == 0xc8 || rsp->ccode == 0xca) &&
|
||||
@ -330,6 +347,8 @@ read_fru_area(struct ipmi_intf * intf, struct fru_info *fru, uint8_t id,
|
||||
fru_data_rqst_size);
|
||||
continue;
|
||||
}
|
||||
lprintf(LOG_NOTICE, "FRU Read failed: %s",
|
||||
val2str(rsp->ccode, completion_code_vals));
|
||||
break;
|
||||
}
|
||||
|
||||
@ -1159,15 +1178,15 @@ __ipmi_fru_print(struct ipmi_intf * intf, uint8_t id)
|
||||
lprintf(LOG_DEBUG, "fru.header.version: 0x%x",
|
||||
header.version);
|
||||
lprintf(LOG_DEBUG, "fru.header.offset.internal: 0x%x",
|
||||
header.offset.internal);
|
||||
header.offset.internal * 8);
|
||||
lprintf(LOG_DEBUG, "fru.header.offset.chassis: 0x%x",
|
||||
header.offset.chassis);
|
||||
header.offset.chassis * 8);
|
||||
lprintf(LOG_DEBUG, "fru.header.offset.board: 0x%x",
|
||||
header.offset.board);
|
||||
header.offset.board * 8);
|
||||
lprintf(LOG_DEBUG, "fru.header.offset.product: 0x%x",
|
||||
header.offset.product);
|
||||
header.offset.product * 8);
|
||||
lprintf(LOG_DEBUG, "fru.header.offset.multi: 0x%x",
|
||||
header.offset.multi);
|
||||
header.offset.multi * 8);
|
||||
|
||||
/*
|
||||
* rather than reading the entire part
|
||||
|
@ -74,7 +74,7 @@
|
||||
#endif
|
||||
|
||||
#ifdef ENABLE_ALL_OPTIONS
|
||||
# define OPTION_STRING "I:hVvcgsEao:H:P:f:U:p:C:L:A:t:m:S:l:b:"
|
||||
# define OPTION_STRING "I:hVvcgsEao:H:P:f:U:p:C:L:A:t:m:S:l:b:e:k:"
|
||||
#else
|
||||
# define OPTION_STRING "I:hVvcH:f:U:p:S:"
|
||||
#endif
|
||||
@ -227,7 +227,9 @@ ipmi_option_usage(const char * progname, struct ipmi_cmd * cmdlist, struct ipmi_
|
||||
lprintf(LOG_NOTICE, " -S sdr Use local file for remote SDR cache");
|
||||
#ifdef ENABLE_ALL_OPTIONS
|
||||
lprintf(LOG_NOTICE, " -a Prompt for remote password");
|
||||
lprintf(LOG_NOTICE, " -e char Set SOL escape character");
|
||||
lprintf(LOG_NOTICE, " -C ciphersuite Cipher suite to be used by lanplus interface");
|
||||
lprintf(LOG_NOTICE, " -k key Use Kg key for IPMIv2 authentication");
|
||||
lprintf(LOG_NOTICE, " -L level Remote session privilege level [default=ADMINISTRATOR]");
|
||||
lprintf(LOG_NOTICE, " -A authtype Force use of auth type NONE, PASSWORD, MD2, MD5 or OEM");
|
||||
lprintf(LOG_NOTICE, " -P password Remote session password");
|
||||
@ -235,7 +237,6 @@ ipmi_option_usage(const char * progname, struct ipmi_cmd * cmdlist, struct ipmi_
|
||||
lprintf(LOG_NOTICE, " -m address Set local IPMB address");
|
||||
lprintf(LOG_NOTICE, " -b channel Set destination channel for bridged request");
|
||||
lprintf(LOG_NOTICE, " -l lun Set destination lun for raw commands");
|
||||
|
||||
lprintf(LOG_NOTICE, " -t address Bridge request to remote target address");
|
||||
lprintf(LOG_NOTICE, " -o oemtype Setup for OEM (use 'list' to see available OEM types)");
|
||||
#endif
|
||||
@ -279,10 +280,12 @@ ipmi_main(int argc, char ** argv,
|
||||
char * progname = NULL;
|
||||
char * oemtype = NULL;
|
||||
char * sdrcache = NULL;
|
||||
char * kgkey = NULL;
|
||||
int port = 0;
|
||||
int cipher_suite_id = 3; /* See table 22-19 of the IPMIv2 spec */
|
||||
int argflag, i, found;
|
||||
int rc = -1;
|
||||
char sol_escape_char = SOL_ESCAPE_CHARACTER_DEFAULT;
|
||||
|
||||
/* save program name */
|
||||
progname = strrchr(argv[0], '/');
|
||||
@ -364,6 +367,13 @@ ipmi_main(int argc, char ** argv,
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 'k':
|
||||
kgkey = strdup(optarg);
|
||||
if (kgkey == NULL) {
|
||||
lprintf(LOG_ERR, "%s: malloc failure", progname);
|
||||
goto out_free;
|
||||
}
|
||||
break;
|
||||
case 'U':
|
||||
username = strdup(optarg);
|
||||
if (username == NULL) {
|
||||
@ -457,6 +467,9 @@ ipmi_main(int argc, char ** argv,
|
||||
case 'm':
|
||||
my_addr = (uint8_t)strtol(optarg, NULL, 0);
|
||||
break;
|
||||
case 'e':
|
||||
sol_escape_char = optarg[0];
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
ipmi_option_usage(progname, cmdlist, intflist);
|
||||
@ -533,6 +546,8 @@ ipmi_main(int argc, char ** argv,
|
||||
ipmi_intf_session_set_username(intf, username);
|
||||
if (password != NULL)
|
||||
ipmi_intf_session_set_password(intf, password);
|
||||
if (kgkey != NULL)
|
||||
ipmi_intf_session_set_kgkey(intf, kgkey);
|
||||
if (port > 0)
|
||||
ipmi_intf_session_set_port(intf, port);
|
||||
if (authtype >= 0)
|
||||
@ -543,13 +558,14 @@ ipmi_main(int argc, char ** argv,
|
||||
ipmi_intf_session_set_privlvl(intf,
|
||||
IPMI_SESSION_PRIV_ADMIN); /* default */
|
||||
|
||||
ipmi_intf_session_set_sol_escape_char(intf, sol_escape_char);
|
||||
ipmi_intf_session_set_cipher_suite_id(intf, cipher_suite_id);
|
||||
|
||||
/* setup destination lun if given */
|
||||
intf->target_lun = target_lun ;
|
||||
/* setup destination lun if given */
|
||||
intf->target_lun = target_lun ;
|
||||
|
||||
/* setup destination channel if given */
|
||||
intf->target_channel = target_channel ;
|
||||
/* setup destination channel if given */
|
||||
intf->target_channel = target_channel ;
|
||||
|
||||
/* setup IPMB local and target address if given */
|
||||
intf->my_addr = my_addr ? : IPMI_BMC_SLAVE_ADDR;
|
||||
|
@ -67,8 +67,6 @@
|
||||
#define SOL_PARAMETER_SOL_PAYLOAD_CHANNEL 0x07
|
||||
#define SOL_PARAMETER_SOL_PAYLOAD_PORT 0x08
|
||||
|
||||
#define SOL_ESCAPE_CHARACTER '~'
|
||||
|
||||
const struct valstr sol_parameter_vals[] = {
|
||||
{ SOL_PARAMETER_SET_IN_PROGRESS, "Set In Progress (0)" },
|
||||
{ SOL_PARAMETER_SOL_ENABLE, "Enable (1)" },
|
||||
@ -1048,7 +1046,7 @@ suspendSelf(int bRestoreTty)
|
||||
* Send some useful documentation to the user
|
||||
*/
|
||||
static void
|
||||
printSolEscapeSequences(void)
|
||||
printSolEscapeSequences(struct ipmi_intf * intf)
|
||||
{
|
||||
printf(
|
||||
"%c?\r\n\
|
||||
@ -1060,14 +1058,14 @@ printSolEscapeSequences(void)
|
||||
%c? - this message\r\n\
|
||||
%c%c - send the escape character by typing it twice\r\n\
|
||||
(Note that escapes are only recognized immediately after newline.)\r\n",
|
||||
SOL_ESCAPE_CHARACTER,
|
||||
SOL_ESCAPE_CHARACTER,
|
||||
SOL_ESCAPE_CHARACTER,
|
||||
SOL_ESCAPE_CHARACTER,
|
||||
SOL_ESCAPE_CHARACTER,
|
||||
SOL_ESCAPE_CHARACTER,
|
||||
SOL_ESCAPE_CHARACTER,
|
||||
SOL_ESCAPE_CHARACTER);
|
||||
intf->session->sol_escape_char,
|
||||
intf->session->sol_escape_char,
|
||||
intf->session->sol_escape_char,
|
||||
intf->session->sol_escape_char,
|
||||
intf->session->sol_escape_char,
|
||||
intf->session->sol_escape_char,
|
||||
intf->session->sol_escape_char,
|
||||
intf->session->sol_escape_char);
|
||||
}
|
||||
|
||||
|
||||
@ -1158,7 +1156,7 @@ static int
|
||||
processSolUserInput(
|
||||
struct ipmi_intf * intf,
|
||||
uint8_t * input,
|
||||
uint16_t buffer_length)
|
||||
uint16_t buffer_length)
|
||||
{
|
||||
static int escape_pending = 0;
|
||||
static int last_was_cr = 1;
|
||||
@ -1186,38 +1184,44 @@ processSolUserInput(
|
||||
*/
|
||||
switch (ch) {
|
||||
case '.':
|
||||
printf("%c. [terminated ipmitool]\r\n", SOL_ESCAPE_CHARACTER);
|
||||
printf("%c. [terminated ipmitool]\r\n",
|
||||
intf->session->sol_escape_char);
|
||||
retval = 1;
|
||||
break;
|
||||
|
||||
case 'Z' - 64:
|
||||
printf("%c^Z [suspend ipmitool]\r\n", SOL_ESCAPE_CHARACTER);
|
||||
printf("%c^Z [suspend ipmitool]\r\n",
|
||||
intf->session->sol_escape_char);
|
||||
suspendSelf(1); /* Restore tty back to raw */
|
||||
continue;
|
||||
|
||||
case 'X' - 64:
|
||||
printf("%c^Z [suspend ipmitool]\r\n", SOL_ESCAPE_CHARACTER);
|
||||
printf("%c^Z [suspend ipmitool]\r\n",
|
||||
intf->session->sol_escape_char);
|
||||
suspendSelf(0); /* Don't restore to raw mode */
|
||||
continue;
|
||||
|
||||
case 'B':
|
||||
printf("%cb [send break]\r\n", SOL_ESCAPE_CHARACTER);
|
||||
printf("%cb [send break]\r\n",
|
||||
intf->session->sol_escape_char);
|
||||
sendBreak(intf);
|
||||
continue;
|
||||
|
||||
case '?':
|
||||
printSolEscapeSequences();
|
||||
printSolEscapeSequences(intf);
|
||||
continue;
|
||||
|
||||
default:
|
||||
if (ch != SOL_ESCAPE_CHARACTER)
|
||||
if (ch != intf->session->sol_escape_char)
|
||||
v2_payload.payload.sol_packet.data[length++] =
|
||||
SOL_ESCAPE_CHARACTER;
|
||||
intf->session->sol_escape_char;
|
||||
v2_payload.payload.sol_packet.data[length++] = ch;
|
||||
}
|
||||
}
|
||||
|
||||
else
|
||||
{
|
||||
if (last_was_cr && (ch == SOL_ESCAPE_CHARACTER)) {
|
||||
if (last_was_cr && (ch == intf->session->sol_escape_char)) {
|
||||
escape_pending = 1;
|
||||
continue;
|
||||
}
|
||||
@ -1413,7 +1417,7 @@ ipmi_sol_activate(struct ipmi_intf * intf)
|
||||
intf->session->sol_data.sol_input_handler = output;
|
||||
|
||||
|
||||
memset(&req, 0, sizeof(req));
|
||||
memset(&req, 0, sizeof(req));
|
||||
req.msg.netfn = IPMI_NETFN_APP;
|
||||
req.msg.cmd = IPMI_ACTIVATE_PAYLOAD;
|
||||
req.msg.data_len = 6;
|
||||
@ -1519,7 +1523,7 @@ ipmi_sol_activate(struct ipmi_intf * intf)
|
||||
|
||||
|
||||
printf("[SOL Session operational. Use %c? for help]\r\n",
|
||||
SOL_ESCAPE_CHARACTER);
|
||||
intf->session->sol_escape_char);
|
||||
|
||||
|
||||
/*
|
||||
|
@ -180,7 +180,7 @@ ipmi_intf_session_set_username(struct ipmi_intf * intf, char * username)
|
||||
if (intf->session == NULL)
|
||||
return;
|
||||
|
||||
memset(intf->session->username, 0, 16);
|
||||
memset(intf->session->username, 0, 17);
|
||||
|
||||
if (username == NULL)
|
||||
return;
|
||||
@ -224,6 +224,30 @@ ipmi_intf_session_set_cipher_suite_id(struct ipmi_intf * intf, uint8_t cipher_su
|
||||
intf->session->cipher_suite_id = cipher_suite_id;
|
||||
}
|
||||
|
||||
void
|
||||
ipmi_intf_session_set_sol_escape_char(struct ipmi_intf * intf, char sol_escape_char)
|
||||
{
|
||||
if (intf->session == NULL)
|
||||
return;
|
||||
|
||||
intf->session->sol_escape_char = sol_escape_char;
|
||||
}
|
||||
|
||||
void
|
||||
ipmi_intf_session_set_kgkey(struct ipmi_intf * intf, char * kgkey)
|
||||
{
|
||||
if (intf->session == NULL)
|
||||
return;
|
||||
|
||||
memset(intf->session->v2_data.kg, 0, IPMI_KG_BUFFER_SIZE);
|
||||
|
||||
if (kgkey == NULL)
|
||||
return;
|
||||
|
||||
memcpy(intf->session->v2_data.kg, kgkey,
|
||||
__min(strlen(kgkey), IPMI_KG_BUFFER_SIZE));
|
||||
}
|
||||
|
||||
void
|
||||
ipmi_intf_session_set_port(struct ipmi_intf * intf, int port)
|
||||
{
|
||||
|
@ -3238,7 +3238,9 @@ ipmi_lanplus_open(struct ipmi_intf * intf)
|
||||
//session->sol_data.last_received_sequence_number = 0;
|
||||
//session->sol_data.last_received_byte_count = 0;
|
||||
memset(session->v2_data.sik, 0, IPMI_SIK_BUFFER_SIZE);
|
||||
memset(session->v2_data.kg, 0, IPMI_KG_BUFFER_SIZE);
|
||||
|
||||
/* Kg is set in ipmi_intf */
|
||||
//memset(session->v2_data.kg, 0, IPMI_KG_BUFFER_SIZE);
|
||||
|
||||
|
||||
/* open port to BMC */
|
||||
|
@ -528,13 +528,10 @@ int lanplus_generate_sik(struct ipmi_session * session)
|
||||
{
|
||||
/* We will be hashing with Kg */
|
||||
/*
|
||||
* TODO: Section 13.31 of the IPMI v2 spec describes the SIK creation
|
||||
* using Kg. It specifies that Kg should not be truncated, but I
|
||||
* do not know what is meant by that.
|
||||
* Section 13.31 of the IPMI v2 spec describes the SIK creation
|
||||
* using Kg. It specifies that Kg should not be truncated.
|
||||
* Kg is set in ipmi_intf.
|
||||
*/
|
||||
lprintf(LOG_ERR, "lanplus_generate_sik: We dont yet support hashing with Kg");
|
||||
assert(0);
|
||||
|
||||
input_key = session->v2_data.kg;
|
||||
}
|
||||
else
|
||||
|
Loading…
x
Reference in New Issue
Block a user