commit 6521d1107a5b638fd499d76a474ea8439f15594a Author: overweight <5324761+overweight@user.noreply.gitee.com> Date: Mon Sep 30 10:53:18 2019 -0400 Package init diff --git a/0001-CVE-2011-4339-OpenIPMI.patch b/0001-CVE-2011-4339-OpenIPMI.patch new file mode 100644 index 0000000..437c9ad --- /dev/null +++ b/0001-CVE-2011-4339-OpenIPMI.patch @@ -0,0 +1,25 @@ +From 152efd46931a70ab4e3d81e99d312df7dcd666e6 Mon Sep 17 00:00:00 2001 +From: Boris Ranto +Date: Tue, 10 May 2016 19:12:08 +0200 +Subject: [PATCH] CVE-2011-4339 OpenIPMI + +IPMI event daemon creates PID file with world writeable permissions +--- + lib/helper.c | 1 - + 1 file changed, 1 deletion(-) + +diff --git a/lib/helper.c b/lib/helper.c +index de91438..c3a1c80 100644 +--- a/lib/helper.c ++++ b/lib/helper.c +@@ -829,7 +829,6 @@ ipmi_start_daemon(struct ipmi_intf *intf) + #endif + + chdir("/"); +- umask(0); + + for (fd=0; fd<64; fd++) { + if (fd != intf->fd) +-- +2.7.4 + diff --git a/0002-openssl.patch b/0002-openssl.patch new file mode 100644 index 0000000..ff5e705 --- /dev/null +++ b/0002-openssl.patch @@ -0,0 +1,89 @@ +diff -urNp old/src/plugins/lanplus/lanplus_crypt_impl.c new/src/plugins/lanplus/lanplus_crypt_impl.c +--- old/src/plugins/lanplus/lanplus_crypt_impl.c 2016-05-28 10:20:20.000000000 +0200 ++++ new/src/plugins/lanplus/lanplus_crypt_impl.c 2017-02-21 10:50:21.634873466 +0100 +@@ -164,10 +164,10 @@ lanplus_encrypt_aes_cbc_128(const uint8_ + uint8_t * output, + uint32_t * bytes_written) + { +- EVP_CIPHER_CTX ctx; +- EVP_CIPHER_CTX_init(&ctx); +- EVP_EncryptInit_ex(&ctx, EVP_aes_128_cbc(), NULL, key, iv); +- EVP_CIPHER_CTX_set_padding(&ctx, 0); ++ EVP_CIPHER_CTX *ctx = EVP_CIPHER_CTX_new(); ++ EVP_CIPHER_CTX_init(ctx); ++ EVP_EncryptInit_ex(ctx, EVP_aes_128_cbc(), NULL, key, iv); ++ EVP_CIPHER_CTX_set_padding(ctx, 0); + + + *bytes_written = 0; +@@ -191,7 +191,7 @@ lanplus_encrypt_aes_cbc_128(const uint8_ + assert((input_length % IPMI_CRYPT_AES_CBC_128_BLOCK_SIZE) == 0); + + +- if(!EVP_EncryptUpdate(&ctx, output, (int *)bytes_written, input, input_length)) ++ if(!EVP_EncryptUpdate(ctx, output, (int *)bytes_written, input, input_length)) + { + /* Error */ + *bytes_written = 0; +@@ -201,7 +201,7 @@ lanplus_encrypt_aes_cbc_128(const uint8_ + { + uint32_t tmplen; + +- if(!EVP_EncryptFinal_ex(&ctx, output + *bytes_written, (int *)&tmplen)) ++ if(!EVP_EncryptFinal_ex(ctx, output + *bytes_written, (int *)&tmplen)) + { + *bytes_written = 0; + return; /* Error */ +@@ -210,7 +210,8 @@ lanplus_encrypt_aes_cbc_128(const uint8_ + { + /* Success */ + *bytes_written += tmplen; +- EVP_CIPHER_CTX_cleanup(&ctx); ++ EVP_CIPHER_CTX_cleanup(ctx); ++ EVP_CIPHER_CTX_free(ctx); + } + } + } +@@ -239,10 +240,10 @@ lanplus_decrypt_aes_cbc_128(const uint8_ + uint8_t * output, + uint32_t * bytes_written) + { +- EVP_CIPHER_CTX ctx; +- EVP_CIPHER_CTX_init(&ctx); +- EVP_DecryptInit_ex(&ctx, EVP_aes_128_cbc(), NULL, key, iv); +- EVP_CIPHER_CTX_set_padding(&ctx, 0); ++ EVP_CIPHER_CTX *ctx = EVP_CIPHER_CTX_new(); ++ EVP_CIPHER_CTX_init(ctx); ++ EVP_DecryptInit_ex(ctx, EVP_aes_128_cbc(), NULL, key, iv); ++ EVP_CIPHER_CTX_set_padding(ctx, 0); + + + if (verbose >= 5) +@@ -266,7 +267,7 @@ lanplus_decrypt_aes_cbc_128(const uint8_ + assert((input_length % IPMI_CRYPT_AES_CBC_128_BLOCK_SIZE) == 0); + + +- if (!EVP_DecryptUpdate(&ctx, output, (int *)bytes_written, input, input_length)) ++ if (!EVP_DecryptUpdate(ctx, output, (int *)bytes_written, input, input_length)) + { + /* Error */ + lprintf(LOG_DEBUG, "ERROR: decrypt update failed"); +@@ -277,7 +278,7 @@ lanplus_decrypt_aes_cbc_128(const uint8_ + { + uint32_t tmplen; + +- if (!EVP_DecryptFinal_ex(&ctx, output + *bytes_written, (int *)&tmplen)) ++ if (!EVP_DecryptFinal_ex(ctx, output + *bytes_written, (int *)&tmplen)) + { + char buffer[1000]; + ERR_error_string(ERR_get_error(), buffer); +@@ -290,7 +291,8 @@ lanplus_decrypt_aes_cbc_128(const uint8_ + { + /* Success */ + *bytes_written += tmplen; +- EVP_CIPHER_CTX_cleanup(&ctx); ++ EVP_CIPHER_CTX_cleanup(ctx); ++ EVP_CIPHER_CTX_free(ctx); + } + } + diff --git a/0003-ipmitool-1.8.11-set-kg-key.patch b/0003-ipmitool-1.8.11-set-kg-key.patch new file mode 100644 index 0000000..00a396e --- /dev/null +++ b/0003-ipmitool-1.8.11-set-kg-key.patch @@ -0,0 +1,240 @@ +diff -urNp old/doc/ipmitool.1 new/doc/ipmitool.1 +--- old/doc/ipmitool.1 2017-02-06 10:20:02.254362909 +0100 ++++ new/doc/ipmitool.1 2017-02-06 10:33:41.729294474 +0100 +@@ -372,6 +372,20 @@ Configure user access information on the + + Displays the list of cipher suites supported for the given + application (ipmi or sol) on the given channel. ++.TP ++\fIsetkg\fP <\fIhex\fP|\fIplain\fP> <\fBkey\fP> [<\fBchannel\fR>] ++.br ++ ++Sets K_g key to given value. Use \fIplain\fP to specify \fBkey\fR as simple ASCII string. ++Use \fIhex\fP to specify \fBkey\fR as sequence of hexadecimal codes of ASCII charactes. ++I.e. following two examples are equivalent: ++ ++.RS ++ipmitool channel setkg plain PASSWORD ++ ++ipmitool channel setkg hex 50415353574F5244 ++.RE ++ + .RE + .RE + .TP +diff -urNp old/include/ipmitool/helper.h new/include/ipmitool/helper.h +--- old/include/ipmitool/helper.h 2017-02-06 10:20:02.254362909 +0100 ++++ new/include/ipmitool/helper.h 2017-02-06 10:40:07.336136844 +0100 +@@ -58,6 +58,8 @@ + # define IPMI_UID_MAX 63 + #endif + ++#define IPMI_KG_BUFFER_SIZE 21 /* key plus null byte */ ++ + struct ipmi_intf; + + struct valstr { +diff -urNp old/include/ipmitool/ipmi_channel.h new/include/ipmitool/ipmi_channel.h +--- old/include/ipmitool/ipmi_channel.h 2017-02-06 10:20:02.253316684 +0100 ++++ new/include/ipmitool/ipmi_channel.h 2017-02-06 10:58:15.291287621 +0100 +@@ -49,6 +49,10 @@ + #define IPMI_GET_USER_NAME 0x46 + #define IPMI_SET_USER_PASSWORD 0x47 + #define IPMI_GET_CHANNEL_CIPHER_SUITES 0x54 ++#define IPMI_SET_CHANNEL_SECURITY_KEYS 0x56 ++ ++#define IPMI_KG_KEY_ID 1 ++#define IPMI_SET_CHANNEL_SECURITY_KEYS_OP_SET 1 + + /* These are for channel_info_t.session_support */ + #define IPMI_CHANNEL_SESSION_LESS 0x00 +@@ -137,6 +141,40 @@ int _ipmi_set_channel_access(struct ipmi + struct channel_access_t channel_access, uint8_t access_option, + uint8_t privilege_option); + ++struct set_channel_security_keys_req { ++#if WORDS_BIGENDIAN ++ uint8_t __reserved1 :4; ++ uint8_t channel :4; ++ ++ uint8_t __reserved2 :6; ++ uint8_t operation :2; ++ ++ uint8_t key_id; ++ unsigned char key_value[IPMI_KG_BUFFER_SIZE-1]; /* we don't want space for '\0' at the end */ ++#else ++ uint8_t channel :4; ++ uint8_t __reserved1 :4; ++ ++ uint8_t operation :2; ++ uint8_t __reserved2 :6; ++ ++ uint8_t key_id; ++ unsigned char key_value[IPMI_KG_BUFFER_SIZE-1]; /* we don't want space for '\0' at the end */ ++#endif ++} __attribute__ ((packed)); ++ ++struct set_channel_security_keys_rsp { ++#if WORDS_BIGENDIAN ++ uint8_t __reserved1 :6; ++ uint8_t lock_status :2; ++ unsigned char key_value; /* just the first character, use &key_value to explore the rest */ ++#else ++ uint8_t lock_status :2; ++ uint8_t __reserved1 :6; ++ unsigned char key_value; /* just the first character, use &key_value to explore the rest */ ++#endif ++} __attribute__ ((packed)); ++ + uint8_t ipmi_get_channel_medium(struct ipmi_intf * intf, uint8_t channel); + uint8_t ipmi_current_channel_medium(struct ipmi_intf * intf); + int ipmi_channel_main(struct ipmi_intf * intf, int argc, char ** argv); +diff -urNp old/include/ipmitool/ipmi_intf.h new/include/ipmitool/ipmi_intf.h +--- old/include/ipmitool/ipmi_intf.h 2017-02-06 10:20:02.254362909 +0100 ++++ new/include/ipmitool/ipmi_intf.h 2017-02-06 10:40:40.264577602 +0100 +@@ -60,7 +60,6 @@ enum LANPLUS_SESSION_STATE { + + #define IPMI_AUTHCODE_BUFFER_SIZE 20 + #define IPMI_SIK_BUFFER_SIZE IPMI_MAX_MD_SIZE +-#define IPMI_KG_BUFFER_SIZE 21 /* key plus null byte */ + + struct ipmi_session_params { + char * hostname; +diff -urNp old/lib/ipmi_channel.c new/lib/ipmi_channel.c +--- old/lib/ipmi_channel.c 2017-02-06 10:20:02.255409134 +0100 ++++ new/lib/ipmi_channel.c 2017-02-06 12:32:14.222282317 +0100 +@@ -821,6 +821,92 @@ ipmi_set_user_access(struct ipmi_intf *i + return 0; + } + ++int ++ipmi_set_channel_security_keys (struct ipmi_intf *intf, uint8_t channel, const char *method, const char *key) ++{ ++ uint8_t kgkey[IPMI_KG_BUFFER_SIZE]; ++ struct ipmi_rs *rsp; ++ struct ipmi_rq req; ++ struct set_channel_security_keys_req req_data; ++ int rc = -1; ++ ++ /* convert provided key to array of bytes */ ++ if (strcmp(method, "hex") == 0) { ++ if (strlen(key) > (IPMI_KG_BUFFER_SIZE-1)*2) { ++ lprintf(LOG_ERR, "Provided key is too long, max. length is %d bytes", (IPMI_KG_BUFFER_SIZE-1)); ++ printf_channel_usage(); ++ return -1; ++ } ++ ++ rc = ipmi_parse_hex(key, kgkey, sizeof(kgkey)-1); ++ if (rc == -1) { ++ lprintf(LOG_ERR, "Number of Kg key characters is not even"); ++ return rc; ++ } else if (rc == -3) { ++ lprintf(LOG_ERR, "Kg key is not hexadecimal number"); ++ return rc; ++ } else if (rc > (IPMI_KG_BUFFER_SIZE-1)) { ++ lprintf(LOG_ERR, "Kg key is too long"); ++ return rc; ++ } ++ ++ } else if (strcmp(method, "plain") == 0) { ++ if (strlen(key) > IPMI_KG_BUFFER_SIZE-1) { ++ lprintf(LOG_ERR, "Provided key is too long, max. length is %d bytes", (IPMI_KG_BUFFER_SIZE -1)); ++ printf_channel_usage(); ++ return rc; ++ } ++ ++ strncpy(kgkey, key, IPMI_KG_BUFFER_SIZE-1); ++ } else { ++ printf_channel_usage(); ++ return rc; ++ } ++ ++ /* assemble and send request to set kg key */ ++ memset(&req_data, 0, sizeof(req_data)); ++ req_data.channel = channel; ++ req_data.operation = IPMI_SET_CHANNEL_SECURITY_KEYS_OP_SET; ++ req_data.key_id = IPMI_KG_KEY_ID; ++ memcpy(req_data.key_value, kgkey, IPMI_KG_BUFFER_SIZE-1); ++ ++ memset(&req, 0, sizeof(req)); ++ req.msg.netfn = IPMI_NETFN_APP; ++ req.msg.cmd = IPMI_SET_CHANNEL_SECURITY_KEYS; ++ req.msg.data = (uint8_t*) &req_data; ++ req.msg.data_len = sizeof(req_data); ++ ++ rsp = intf->sendrecv(intf, &req); ++ if (rsp == NULL) { ++ lprintf(LOG_ERR, "Set Channel Security Keys command failed"); ++ return rc; ++ } ++ if (rsp->ccode > 0) { ++ const char *error = NULL; ++ switch (rsp->ccode) { ++ case 0x80: ++ error = "Key is locked"; ++ break; ++ case 0x81: ++ error = "Insufficient key bytes"; ++ break; ++ case 0x82: ++ error = "Too many key bytes"; ++ break; ++ case 0x83: ++ error = "Key value does not meet criteria for K_g key"; ++ break; ++ default: ++ error = val2str(rsp->ccode, completion_code_vals); ++ } ++ lprintf(LOG_ERR, "Error setting security key: %X (%s)", rsp->ccode, error); ++ return rc; ++ } ++ ++ lprintf(LOG_NOTICE, "Set Channel Security Keys command succeeded"); ++ return 0; ++} ++ + int + ipmi_channel_main(struct ipmi_intf *intf, int argc, char **argv) + { +@@ -890,6 +976,19 @@ ipmi_channel_main(struct ipmi_intf *intf + retval = ipmi_get_channel_cipher_suites(intf, + argv[1], /* ipmi | sol */ + channel); ++ } else if (strncmp(argv[0], "setkg", 5) == 0) { ++ if (argc < 3 || argc > 4) ++ printf_channel_usage(); ++ else { ++ uint8_t ch = 0xe; ++ char *method = argv[1]; ++ char *key = argv[2]; ++ if (argc == 4) { ++ ch = (uint8_t)strtol(argv[3], NULL, 0); ++ } ++ ++ retval = ipmi_set_channel_security_keys(intf, ch, method, key); ++ } + } else { + lprintf(LOG_ERR, "Invalid CHANNEL command: %s\n", argv[0]); + printf_channel_usage(); +@@ -916,6 +1015,10 @@ printf_channel_usage() + lprintf(LOG_NOTICE, + ""); + lprintf(LOG_NOTICE, ++" setkg hex|plain [channel]"); ++ lprintf(LOG_NOTICE, ++""); ++ lprintf(LOG_NOTICE, + "Possible privilege levels are:"); + lprintf(LOG_NOTICE, + " 1 Callback level"); +diff -urNp old/src/plugins/ipmi_intf.c new/src/plugins/ipmi_intf.c +--- old/src/plugins/ipmi_intf.c 2017-02-06 10:20:02.257501584 +0100 ++++ new/src/plugins/ipmi_intf.c 2017-02-06 10:42:12.585257810 +0100 +@@ -55,6 +55,7 @@ + #include + #include + #include ++#include + + #define IPMI_DEFAULT_PAYLOAD_SIZE 25 + diff --git a/0004-slowswid.patch b/0004-slowswid.patch new file mode 100644 index 0000000..c5f91b7 --- /dev/null +++ b/0004-slowswid.patch @@ -0,0 +1,16 @@ +diff --git a/lib/ipmi_sdr.c b/lib/ipmi_sdr.c +index fa7b082..9bc5ac2 100644 +--- a/lib/ipmi_sdr.c ++++ b/lib/ipmi_sdr.c +@@ -572,6 +572,8 @@ ipmi_sdr_get_sensor_reading_ipmb(struct ipmi_intf *intf, uint8_t sensor, + uint32_t save_addr; + uint32_t save_channel; + ++ if (target == (uint8_t) 0xb1) ++ return ipmi_sdr_get_sensor_reading(intf, sensor); + if ( BRIDGE_TO_SENSOR(intf, target, channel) ) { + lprintf(LOG_DEBUG, + "Bridge to Sensor " +-- +2.1.0 + diff --git a/0005-sensor-id-length.patch b/0005-sensor-id-length.patch new file mode 100644 index 0000000..0cb8313 --- /dev/null +++ b/0005-sensor-id-length.patch @@ -0,0 +1,16 @@ +diff --git a/include/ipmitool/ipmi_sdr.h b/include/ipmitool/ipmi_sdr.h +index ccf0cf0..47d3949 100644 +--- a/include/ipmitool/ipmi_sdr.h ++++ b/include/ipmitool/ipmi_sdr.h +@@ -819,7 +819,7 @@ static const char *sensor_type_desc[] __attribute__ ((unused)) = { + "Version Change", "FRU State" }; + + struct sensor_reading { +- char s_id[17]; /* name of the sensor */ ++ char s_id[33]; /* name of the sensor */ + struct sdr_record_full_sensor *full; + struct sdr_record_compact_sensor *compact; + uint8_t s_reading_valid; /* read value valididity */ +-- +2.1.0 + diff --git a/0006-enable-usb.patch b/0006-enable-usb.patch new file mode 100644 index 0000000..d3bfba5 --- /dev/null +++ b/0006-enable-usb.patch @@ -0,0 +1,21 @@ +diff -urNp old/configure.ac new/configure.ac +--- old/configure.ac 2017-02-02 14:20:33.230784269 +0100 ++++ new/configure.ac 2017-02-02 14:22:53.528510336 +0100 +@@ -63,7 +63,7 @@ xenable_intf_imb=yes + xenable_intf_lipmi=yes + xenable_intf_open=yes + #xenable_intf_serial=yes +-xenable_intf_usb=no ++xenable_intf_usb=yes + xenable_ipmishell=yes + + dnl set some things so we build with GNU tools on Solaris +@@ -209,7 +209,7 @@ fi + dnl enable IPMI USB interface + AC_ARG_ENABLE([intf-usb], + [AC_HELP_STRING([--enable-intf-usb], +- [enable IPMI USB interface [default=auto]])], ++ [enable IPMI USB interface [default=yes]])], + [xenable_intf_usb=$enableval], + [xenable_intf_usb=$xenable_intf_usb]) + if test "x$xenable_intf_usb" = "xstatic" || test "x$xenable_intf_usb" = "xplugin"; then diff --git a/0007-check-input.patch b/0007-check-input.patch new file mode 100644 index 0000000..030fd2a --- /dev/null +++ b/0007-check-input.patch @@ -0,0 +1,41 @@ +diff -urNp old/doc/ipmitool.1 new/doc/ipmitool.1 +--- old/doc/ipmitool.1 2017-10-03 16:10:50.446539988 +0200 ++++ new/doc/ipmitool.1 2017-10-03 16:16:37.039673239 +0200 +@@ -3170,13 +3170,14 @@ SOL configuration data for the currently + + Enable, disable or show status of SOL payload for the user on the specified channel. + .TP +-\fIset\fP <\fBparameter\fR> <\fBvalue\fR> [<\fBchannel\fR>] ++\fIset\fP <\fBparameter\fR> <\fBvalue\fR> [<\fBchannel\fR>] [\fBnoguard\fR] + .br + + Configure parameters for Serial Over Lan. If no channel is given, + it will display SOL configuration data for the currently used + channel. Configuration parameter updates are automatically guarded +-with the updates to the set\-in\-progress parameter. ++with the updates to the set\-in\-progress parameter, unless \fInoguard\fR ++parameter is present. + .RS + .TP + Valid parameters and values are: +diff -urNp old/lib/ipmi_sol.c new/lib/ipmi_sol.c +--- old/lib/ipmi_sol.c 2017-10-03 16:10:50.447539996 +0200 ++++ new/lib/ipmi_sol.c 2017-10-03 16:18:37.079006949 +0200 +@@ -1875,7 +1875,7 @@ static void + print_sol_usage(void) + { + lprintf(LOG_NOTICE, "SOL Commands: info []"); +- lprintf(LOG_NOTICE, " set [channel]"); ++ lprintf(LOG_NOTICE, " set [channel] [noguard]"); + lprintf(LOG_NOTICE, " payload [channel] [userid]"); + lprintf(LOG_NOTICE, " activate [] [instance=]"); + lprintf(LOG_NOTICE, " deactivate [instance=]"); +@@ -1890,6 +1890,8 @@ print_sol_usage(void) + static void + print_sol_set_usage(void) + { ++ lprintf(LOG_NOTICE, "\nSOL set usage: \n"); ++ lprintf(LOG_NOTICE, " sol set [channel] [noguard]\n"); + lprintf(LOG_NOTICE, "\nSOL set parameters and values: \n"); + lprintf(LOG_NOTICE, " set-in-progress set-complete | " + "set-in-progress | commit-write"); diff --git a/ID-472-Fix-The-Most-recent-Addition-Erase-date.patch b/ID-472-Fix-The-Most-recent-Addition-Erase-date.patch new file mode 100644 index 0000000..d94e1cd --- /dev/null +++ b/ID-472-Fix-The-Most-recent-Addition-Erase-date.patch @@ -0,0 +1,109 @@ +From ecb4cfbff855bb24099f2a80a6dd558518702c7d Mon Sep 17 00:00:00 2001 +From: srinivasa_mareedu +Date: Mon, 23 Jan 2017 16:41:09 +0530 +Subject: [PATCH 019/119] ID:472 - Fix The Most recent Addition/Erase date + +Fix the Most recent Addition/Erase date are not matched between in-band and +out-band. + +ipmitool SDR code doesn't have to check for valid date to print +based on 'Delete SDR command supported' and 'Partial Add SDR command +supported', if 0xffffffff is taken. Also 'Timestamp' data type needs to change +to time_t(long) because same data type is using for gmtime(time_t) API, it has +different behaviour for Linux and Windows C. +--- + lib/ipmi_sdr.c | 64 ++++++++++++++++++++++++++++++++++++-------------- + 1 file changed, 47 insertions(+), 17 deletions(-) + +diff --git a/lib/ipmi_sdr.c b/lib/ipmi_sdr.c +index 2a9cbe3..167c252 100644 +--- a/lib/ipmi_sdr.c ++++ b/lib/ipmi_sdr.c +@@ -4217,7 +4217,7 @@ ipmi_sdr_get_info(struct ipmi_intf *intf, + * returns pointer to static buffer + */ + static char * +-ipmi_sdr_timestamp(uint32_t stamp) ++ipmi_sdr_timestamp(time_t stamp) + { + static char tbuf[40]; + time_t s = (time_t) stamp; +@@ -4240,7 +4240,7 @@ ipmi_sdr_timestamp(uint32_t stamp) + int + ipmi_sdr_print_info(struct ipmi_intf *intf) + { +- uint32_t timestamp; ++ time_t timestamp; + uint16_t free_space; + + struct get_sdr_repository_info_rsp sdr_repository_info; +@@ -4274,21 +4274,51 @@ ipmi_sdr_print_info(struct ipmi_intf *intf) + break; + } + +- timestamp = +- (sdr_repository_info.most_recent_addition_timestamp[3] << 24) | +- (sdr_repository_info.most_recent_addition_timestamp[2] << 16) | +- (sdr_repository_info.most_recent_addition_timestamp[1] << 8) | +- sdr_repository_info.most_recent_addition_timestamp[0]; +- printf("Most recent Addition : %s\n", +- ipmi_sdr_timestamp(timestamp)); +- +- timestamp = +- (sdr_repository_info.most_recent_erase_timestamp[3] << 24) | +- (sdr_repository_info.most_recent_erase_timestamp[2] << 16) | +- (sdr_repository_info.most_recent_erase_timestamp[1] << 8) | +- sdr_repository_info.most_recent_erase_timestamp[0]; +- printf("Most recent Erase : %s\n", +- ipmi_sdr_timestamp(timestamp)); ++ if(sdr_repository_info.delete_sdr_supported && sdr_repository_info.partial_add_sdr_supported) ++ { ++ timestamp = ++ (sdr_repository_info.most_recent_addition_timestamp[3] << 24) | ++ (sdr_repository_info.most_recent_addition_timestamp[2] << 16) | ++ (sdr_repository_info.most_recent_addition_timestamp[1] << 8) | ++ sdr_repository_info.most_recent_addition_timestamp[0]; ++ printf("Most recent Addition : %s\n", ++ ipmi_sdr_timestamp(timestamp)); ++ ++ timestamp = ++ (sdr_repository_info.most_recent_erase_timestamp[3] << 24) | ++ (sdr_repository_info.most_recent_erase_timestamp[2] << 16) | ++ (sdr_repository_info.most_recent_erase_timestamp[1] << 8) | ++ sdr_repository_info.most_recent_erase_timestamp[0]; ++ printf("Most recent Erase : %s\n", ++ ipmi_sdr_timestamp(timestamp)); ++ } ++ else if (sdr_repository_info.partial_add_sdr_supported) ++ { ++ timestamp = ++ (sdr_repository_info.most_recent_addition_timestamp[3] << 24) | ++ (sdr_repository_info.most_recent_addition_timestamp[2] << 16) | ++ (sdr_repository_info.most_recent_addition_timestamp[1] << 8) | ++ sdr_repository_info.most_recent_addition_timestamp[0]; ++ printf("Most recent Addition : %s\n", ++ ipmi_sdr_timestamp(timestamp)); ++ printf("Most recent Erase : NA\n"); ++ } ++ else if(sdr_repository_info.delete_sdr_supported) ++ { ++ printf("Most recent Addition : NA\n"); ++ timestamp = ++ (sdr_repository_info.most_recent_erase_timestamp[3] << 24) | ++ (sdr_repository_info.most_recent_erase_timestamp[2] << 16) | ++ (sdr_repository_info.most_recent_erase_timestamp[1] << 8) | ++ sdr_repository_info.most_recent_erase_timestamp[0]; ++ printf("Most recent Erase : %s\n", ++ ipmi_sdr_timestamp(timestamp)); ++ } ++ else ++ { ++ printf("Most recent Addition : NA\n"); ++ printf("Most recent Erase : NA\n"); ++ } + + printf("SDR overflow : %s\n", + (sdr_repository_info.overflow_flag ? "yes" : "no")); +-- +2.19.1 + diff --git a/ID-477-fru-Fix-decoding-of-non-text-data-in-get_fru_.patch b/ID-477-fru-Fix-decoding-of-non-text-data-in-get_fru_.patch new file mode 100644 index 0000000..596a867 --- /dev/null +++ b/ID-477-fru-Fix-decoding-of-non-text-data-in-get_fru_.patch @@ -0,0 +1,121 @@ +From 497f7767cd8e80ad67d08680ae165271441017fc Mon Sep 17 00:00:00 2001 +From: Alexander Amelkin +Date: Thu, 2 Feb 2017 15:25:44 +0300 +Subject: [PATCH 015/119] ID:477 - fru: Fix decoding of non-text data in + get_fru_area_str() + +The get_fru_area_str() function is used to decode FRU area +fields into text. Areas may be encoded as text, binary, +BCDplus or 6-bit ASCII. Decoding of 6-bit ASCII and BCDplus +was broken. There was an error in the formulas used to +calculate the resulting string length, plus the decoding +formulas for BCDplus was wrong. + +For BCDplus the resulting length was considered equal +the encoded data length, while in fact it's twice as big. +Only one character instead of two was being extracted from +a single input byte while two nibbles must have been taken +into account. + +For 6-bit ASCII rounding of 3 to 4 bytes conversion was done +improperly adding 2 to the original length instead of the +result of multiplication. +--- + lib/ipmi_fru.c | 32 ++++++++++++++++---------------- + 1 file changed, 16 insertions(+), 16 deletions(-) + +diff --git a/lib/ipmi_fru.c b/lib/ipmi_fru.c +index cf00eff..42c1f19 100644 +--- a/lib/ipmi_fru.c ++++ b/lib/ipmi_fru.c +@@ -107,7 +107,7 @@ char * get_fru_area_str(uint8_t * data, uint32_t * offset) + { + static const char bcd_plus[] = "0123456789 -.:,_"; + char * str; +- int len, off, size, i, j, k, typecode; ++ int len, off, size, i, j, k, typecode, char_idx; + union { + uint32_t bits; + char chars[4]; +@@ -126,15 +126,15 @@ char * get_fru_area_str(uint8_t * data, uint32_t * offset) + + switch (typecode) { + case 0: /* 00b: binary/unspecified */ +- /* hex dump -> 2x length */ +- size = (len*2); ++ case 1: /* 01b: BCD plus */ ++ /* hex dump or BCD -> 2x length */ ++ size = (len * 2); + break; + case 2: /* 10b: 6-bit ASCII */ + /* 4 chars per group of 1-3 bytes */ +- size = ((((len+2)*4)/3) & ~3); ++ size = (((len * 4 + 2) / 3) & ~3); + break; + case 3: /* 11b: 8-bit ASCII */ +- case 1: /* 01b: BCD plus */ + /* no length adjustment */ + size = len; + break; +@@ -149,7 +149,7 @@ char * get_fru_area_str(uint8_t * data, uint32_t * offset) + return NULL; + memset(str, 0, size+1); + +- if (len == 0) { ++ if (size == 0) { + str[0] = '\0'; + *offset = off; + return str; +@@ -157,30 +157,30 @@ char * get_fru_area_str(uint8_t * data, uint32_t * offset) + + switch (typecode) { + case 0: /* Binary */ +- strncpy(str, buf2str(&data[off], len), len*2); ++ strncpy(str, buf2str(&data[off], len), size); + break; + + case 1: /* BCD plus */ +- for (k=0; k> ((k % 2) ? 0 : 4)) & 0x0f)]; + str[k] = '\0'; + break; + + case 2: /* 6-bit ASCII */ +- for (i=j=0; i 1 ? data[off+i+1] : 0); + u.chars[1] = (k > 2 ? data[off+i+2] : 0); +-#define CHAR_IDX 3 ++ char_idx = 3; + #else + memcpy((void *)&u.bits, &data[off+i], k); +-#define CHAR_IDX 0 ++ char_idx = 0; + #endif + for (k=0; k<4; k++) { +- str[j++] = ((u.chars[CHAR_IDX] & 0x3f) + 0x20); ++ str[j++] = ((u.chars[char_idx] & 0x3f) + 0x20); + u.bits >>= 6; + } + } +@@ -188,8 +188,8 @@ char * get_fru_area_str(uint8_t * data, uint32_t * offset) + break; + + case 3: +- memcpy(str, &data[off], len); +- str[len] = '\0'; ++ memcpy(str, &data[off], size); ++ str[size] = '\0'; + break; + } + +-- +2.19.1 + diff --git a/ID-480-Call-EVP_CIPHER_CTX_free-instead-of-EVP_CIPHE.patch b/ID-480-Call-EVP_CIPHER_CTX_free-instead-of-EVP_CIPHE.patch new file mode 100644 index 0000000..38ae5d3 --- /dev/null +++ b/ID-480-Call-EVP_CIPHER_CTX_free-instead-of-EVP_CIPHE.patch @@ -0,0 +1,149 @@ +From 1664902525a1c3771b4d8b3ccab7ea1ba6b2bdd1 Mon Sep 17 00:00:00 2001 +From: Holger Liebig +Date: Tue, 4 Apr 2017 20:43:05 +0200 +Subject: [PATCH 018/119] ID:480 - Call EVP_CIPHER_CTX_free() instead of + EVP_CIPHER_CTX_cleanup() + +Call EVP_CIPHER_CTX_free() instead of EVP_CIPHER_CTX_cleanup() to fix memory +leak. +--- + src/plugins/lanplus/lanplus_crypt_impl.c | 49 ++++++++++++------------ + 1 file changed, 24 insertions(+), 25 deletions(-) + +diff --git a/src/plugins/lanplus/lanplus_crypt_impl.c b/src/plugins/lanplus/lanplus_crypt_impl.c +index f54bdda..8203a5f 100644 +--- a/src/plugins/lanplus/lanplus_crypt_impl.c ++++ b/src/plugins/lanplus/lanplus_crypt_impl.c +@@ -165,14 +165,6 @@ lanplus_encrypt_aes_cbc_128(const uint8_t * iv, + uint32_t * bytes_written) + { + EVP_CIPHER_CTX *ctx = NULL; +- ctx = EVP_CIPHER_CTX_new(); +- if (ctx == NULL) { +- *bytes_written = 0; +- return; +- } +- EVP_EncryptInit_ex(ctx, EVP_aes_128_cbc(), NULL, key, iv); +- EVP_CIPHER_CTX_set_padding(ctx, 0); +- + + *bytes_written = 0; + +@@ -186,6 +178,14 @@ lanplus_encrypt_aes_cbc_128(const uint8_t * iv, + printbuf(input, input_length, "encrypting this data"); + } + ++ ctx = EVP_CIPHER_CTX_new(); ++ if (ctx == NULL) { ++ lprintf(LOG_DEBUG, "ERROR: EVP_CIPHER_CTX_new() failed"); ++ return; ++ } ++ EVP_CIPHER_CTX_init(ctx); ++ EVP_EncryptInit_ex(ctx, EVP_aes_128_cbc(), NULL, key, iv); ++ EVP_CIPHER_CTX_set_padding(ctx, 0); + + /* + * The default implementation adds a whole block of padding if the input +@@ -199,7 +199,6 @@ lanplus_encrypt_aes_cbc_128(const uint8_t * iv, + { + /* Error */ + *bytes_written = 0; +- return; + } + else + { +@@ -207,17 +206,17 @@ lanplus_encrypt_aes_cbc_128(const uint8_t * iv, + + if(!EVP_EncryptFinal_ex(ctx, output + *bytes_written, (int *)&tmplen)) + { ++ /* Error */ + *bytes_written = 0; +- return; /* Error */ + } + else + { + /* Success */ + *bytes_written += tmplen; +- EVP_CIPHER_CTX_cleanup(ctx); +- EVP_CIPHER_CTX_free(ctx); + } + } ++ /* performs cleanup and free */ ++ EVP_CIPHER_CTX_free(ctx); + } + + +@@ -245,14 +244,6 @@ lanplus_decrypt_aes_cbc_128(const uint8_t * iv, + uint32_t * bytes_written) + { + EVP_CIPHER_CTX *ctx = NULL; +- ctx = EVP_CIPHER_CTX_new(); +- if (ctx == NULL) { +- *bytes_written = 0; +- return; +- } +- EVP_DecryptInit_ex(ctx, EVP_aes_128_cbc(), NULL, key, iv); +- EVP_CIPHER_CTX_set_padding(ctx, 0); +- + + if (verbose >= 5) + { +@@ -261,12 +252,21 @@ lanplus_decrypt_aes_cbc_128(const uint8_t * iv, + printbuf(input, input_length, "decrypting this data"); + } + +- + *bytes_written = 0; + + if (input_length == 0) + return; + ++ ctx = EVP_CIPHER_CTX_new(); ++ if (ctx == NULL) { ++ lprintf(LOG_DEBUG, "ERROR: EVP_CIPHER_CTX_new() failed"); ++ return; ++ } ++ EVP_CIPHER_CTX_init(ctx); ++ EVP_DecryptInit_ex(ctx, EVP_aes_128_cbc(), NULL, key, iv); ++ EVP_CIPHER_CTX_set_padding(ctx, 0); ++ ++ + /* + * The default implementation adds a whole block of padding if the input + * data is perfectly aligned. We would like to keep that from happening. +@@ -280,7 +280,6 @@ lanplus_decrypt_aes_cbc_128(const uint8_t * iv, + /* Error */ + lprintf(LOG_DEBUG, "ERROR: decrypt update failed"); + *bytes_written = 0; +- return; + } + else + { +@@ -288,21 +287,21 @@ lanplus_decrypt_aes_cbc_128(const uint8_t * iv, + + if (!EVP_DecryptFinal_ex(ctx, output + *bytes_written, (int *)&tmplen)) + { ++ /* Error */ + char buffer[1000]; + ERR_error_string(ERR_get_error(), buffer); + lprintf(LOG_DEBUG, "the ERR error %s", buffer); + lprintf(LOG_DEBUG, "ERROR: decrypt final failed"); + *bytes_written = 0; +- return; /* Error */ + } + else + { + /* Success */ + *bytes_written += tmplen; +- EVP_CIPHER_CTX_cleanup(ctx); +- EVP_CIPHER_CTX_free(ctx); + } + } ++ /* performs cleanup and free */ ++ EVP_CIPHER_CTX_free(ctx); + + if (verbose >= 5) + { +-- +2.19.1 + diff --git a/ID-480-ipmitool-coredumps-in-EVP_CIPHER_CTX_init.patch b/ID-480-ipmitool-coredumps-in-EVP_CIPHER_CTX_init.patch new file mode 100644 index 0000000..3decd28 --- /dev/null +++ b/ID-480-ipmitool-coredumps-in-EVP_CIPHER_CTX_init.patch @@ -0,0 +1,50 @@ +From f004b4b7197fc83e7d47ec8cbcaefffa9a922717 Mon Sep 17 00:00:00 2001 +From: Zdenek Styblik +Date: Sun, 12 Mar 2017 14:00:35 +0100 +Subject: [PATCH 017/119] ID:480 - ipmitool coredumps in EVP_CIPHER_CTX_init + +IPMI tool coredumps due to changes introduced in ID:461. This shouldn't be +surprise as a NULL pointer is passed to init. Commit addresses this issue by +calling EVP_CIPHER_CTX_new() instead of EVP_CIPHER_CTX_init(), which is +deprecated, and by checking return value of call to former function. +--- + src/plugins/lanplus/lanplus_crypt_impl.c | 16 ++++++++++++---- + 1 file changed, 12 insertions(+), 4 deletions(-) + +diff --git a/src/plugins/lanplus/lanplus_crypt_impl.c b/src/plugins/lanplus/lanplus_crypt_impl.c +index bc130a0..f54bdda 100644 +--- a/src/plugins/lanplus/lanplus_crypt_impl.c ++++ b/src/plugins/lanplus/lanplus_crypt_impl.c +@@ -164,8 +164,12 @@ lanplus_encrypt_aes_cbc_128(const uint8_t * iv, + uint8_t * output, + uint32_t * bytes_written) + { +- EVP_CIPHER_CTX *ctx = EVP_CIPHER_CTX_new(); +- EVP_CIPHER_CTX_init(ctx); ++ EVP_CIPHER_CTX *ctx = NULL; ++ ctx = EVP_CIPHER_CTX_new(); ++ if (ctx == NULL) { ++ *bytes_written = 0; ++ return; ++ } + EVP_EncryptInit_ex(ctx, EVP_aes_128_cbc(), NULL, key, iv); + EVP_CIPHER_CTX_set_padding(ctx, 0); + +@@ -240,8 +244,12 @@ lanplus_decrypt_aes_cbc_128(const uint8_t * iv, + uint8_t * output, + uint32_t * bytes_written) + { +- EVP_CIPHER_CTX *ctx = EVP_CIPHER_CTX_new(); +- EVP_CIPHER_CTX_init(ctx); ++ EVP_CIPHER_CTX *ctx = NULL; ++ ctx = EVP_CIPHER_CTX_new(); ++ if (ctx == NULL) { ++ *bytes_written = 0; ++ return; ++ } + EVP_DecryptInit_ex(ctx, EVP_aes_128_cbc(), NULL, key, iv); + EVP_CIPHER_CTX_set_padding(ctx, 0); + +-- +2.19.1 + diff --git a/ID-508-Fix-segfaults-in-dcmi-command-handlers.patch b/ID-508-Fix-segfaults-in-dcmi-command-handlers.patch new file mode 100644 index 0000000..828bfd8 --- /dev/null +++ b/ID-508-Fix-segfaults-in-dcmi-command-handlers.patch @@ -0,0 +1,356 @@ +From 6d9c540f6b2dc16486abc557516f21f8313d6d72 Mon Sep 17 00:00:00 2001 +From: Alexander Amelkin +Date: Tue, 3 Apr 2018 19:46:35 +0300 +Subject: [PATCH 022/119] ID:508 - Fix segfaults in dcmi command handlers + +Some command lists were not terminated properly. +This commit fixes that. +--- + lib/ipmi_dcmi.c | 76 ++++++++++++++++++++++++++----------------------- + 1 file changed, 41 insertions(+), 35 deletions(-) + +diff --git a/lib/ipmi_dcmi.c b/lib/ipmi_dcmi.c +index 2cfe48f..a76b1f2 100755 +--- a/lib/ipmi_dcmi.c ++++ b/lib/ipmi_dcmi.c +@@ -74,6 +74,8 @@ static int ipmi_print_sensor_info(struct ipmi_intf *intf, uint16_t rec_id); + * to change a lot of the code in the main(). * + ******************************************************************************/ + ++#define DCMI_CMD_END { 0xFF, NULL, NULL } ++ + /* Main set of DCMI commands */ + const struct dcmi_cmd dcmi_cmd_vals[] = { + { 0x00, "discover", " Used to discover supported DCMI capabilities" }, +@@ -88,7 +90,7 @@ const struct dcmi_cmd dcmi_cmd_vals[] = { + { 0x09, "get_conf_param", " Get DCMI Config Parameters" }, + { 0x0A, "set_conf_param", " Set DCMI Config Parameters" }, + { 0x0B, "oob_discover", " Ping/Pong Message for DCMI Discovery" }, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* get capabilites */ +@@ -98,7 +100,7 @@ const struct dcmi_cmd dcmi_capable_vals[] = { + "temperature attributes" }, + { 0x03, "optional_attributes", " Lists power capabilities" }, + { 0x04, "managebility access", " Lists OOB channel information" }, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* platform capabilities +@@ -110,13 +112,13 @@ const struct dcmi_cmd dcmi_mandatory_platform_capabilities[] = { + { 0x02, "SEL logging available", "" }, + { 0x03, "Chassis power available", "" }, + { 0x04, "Temperature monitor available", "" }, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* optional capabilities */ + const struct dcmi_cmd dcmi_optional_platform_capabilities[] = { + { 0x01, "Power management available", "" }, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* access capabilties */ +@@ -127,7 +129,7 @@ const struct dcmi_cmd dcmi_management_access_capabilities[] = { + { 0x04, "Out-of-band primary LAN channel available", "" }, + { 0x05, "SOL enabled", "" }, + { 0x06, "VLAN capable", "" }, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* identification capabilities */ +@@ -135,7 +137,7 @@ const struct dcmi_cmd dcmi_id_capabilities_vals[] = { + { 0x01, "GUID", "" }, + { 0x02, "DHCP hostname", "" }, + { 0x03, "Asset tag", "" }, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* Configuration parameters*/ +@@ -145,7 +147,7 @@ const struct dcmi_cmd dcmi_conf_param_vals[] = { + { 0x03, "init", "\t\tInitial timeout interval" }, + { 0x04, "timeout", "\t\tServer contact timeout interval" }, + { 0x05, "retry", "\t\tServer contact retry interval" }, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + +@@ -154,7 +156,7 @@ const struct dcmi_cmd dcmi_temp_monitoring_vals[] = { + { 0x01, "inlet", " Inlet air temperature sensors" }, + { 0x02, "cpu", " CPU temperature sensors" }, + { 0x03, "baseboard", "Baseboard temperature sensors" }, +- { 0xff, NULL, NULL } ++ { 0xff, NULL, NULL } + }; + + /* These are not comands. These are the DCMI temp sensors and their numbers +@@ -165,7 +167,7 @@ const struct dcmi_cmd dcmi_discvry_snsr_vals[] = { + { 0x40, "Inlet", " Inlet air temperature sensors" }, + { 0x41, "CPU", " CPU temperature sensors" }, + { 0x42, "Baseboard", "Baseboard temperature sensors" }, +- { 0xff, NULL, NULL } ++ { 0xff, NULL, NULL } + }; + + /* Temperature Readings */ +@@ -173,7 +175,7 @@ const struct dcmi_cmd dcmi_temp_read_vals[] = { + { 0x40, "Inlet", "Inlet air temperature(40h) " }, + { 0x41, "CPU", "CPU temperature sensors(41h) " }, + { 0x42, "Baseboard", "Baseboard temperature sensors(42h) " }, +- { 0xff, NULL, NULL } ++ { 0xff, NULL, NULL } + }; + + /* power management/control commands */ +@@ -183,7 +185,7 @@ const struct dcmi_cmd dcmi_pwrmgmt_vals[] = { + { 0x02, "set_limit", " Set a power limit option" }, + { 0x03, "activate", " Activate the set power limit" }, + { 0x04, "deactivate", "Deactivate the set power limit" }, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* set power limit commands */ +@@ -192,7 +194,7 @@ const struct dcmi_cmd dcmi_pwrmgmt_set_usage_vals[] = { + { 0x01, "limit", " " }, + { 0x02, "correction", "" }, + { 0x03, "sample", " " }, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* power management/get action commands */ +@@ -217,7 +219,7 @@ const struct dcmi_cmd dcmi_pwrmgmt_get_action_vals[] = { + { 0x10, "OEM reserved (10h)", ""}, + + { 0x11, "Log Event to SEL", ""}, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* power management/set action commands */ +@@ -242,21 +244,21 @@ const struct dcmi_cmd dcmi_pwrmgmt_action_vals[] = { + { 0x0f, "oem_0f", "OEM reserved (0fh)"}, + { 0x10, "oem_10", "OEM reserved (10h)"}, + +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* thermal policy action commands */ + const struct dcmi_cmd dcmi_thermalpolicy_vals[] = { + { 0x00, "get", "Get thermal policy" }, + { 0x01, "set", "Set thermal policy" }, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* thermal policy action commands */ + const struct dcmi_cmd dcmi_confparameters_vals[] = { + { 0x00, "get", "Get configuration parameters" }, + { 0x01, "set", "Set configuration parameters" }, +- { 0xFF, NULL, NULL } ++ DCMI_CMD_END + }; + + /* entityIDs used in thermap policy */ +@@ -268,7 +270,7 @@ const struct dcmi_cmd dcmi_thermalpolicy_set_parameters_vals[] = { + { 0x01, "sel", " Log event to SEL" }, + { 0x00, "nosel", " No 'Log event to SEL' action" }, + { 0x00, "disabled", " Disabled" }, +- { 0x00, NULL, NULL } ++ { 0x00, NULL, NULL } + }; + + +@@ -325,20 +327,20 @@ const struct dcmi_cmd nm_cmd_vals[] = { + { 0x07, "reset", "Reset Statistics" }, + { 0x08, "alert", "Set/Get/Clear Alert destination" }, + { 0x09, "threshold", "Set/Get Alert Thresholds" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_ctl_cmds[] = { + { 0x01, "enable", " " }, + { 0x00, "disable", ""}, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_ctl_domain[] = { + { 0x00, "global", "" }, + { 0x02, "per_domain", " (default is platform)" }, + { 0x04, "per_policy", "<0-7>" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + /* Node Manager Domain codes */ +@@ -348,7 +350,7 @@ const struct dcmi_cmd nm_domain_vals[] = { + { 0x02, "Memory", "" }, + { 0x03, "protection", "" }, + { 0x04, "I/O", "" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_version_vals[] = { +@@ -357,7 +359,7 @@ const struct dcmi_cmd nm_version_vals[] = { + { 0x03, "2.0", "" }, + { 0x04, "2.5", "" }, + { 0x05, "3.0", "" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_capability_opts[] = { +@@ -366,7 +368,7 @@ const struct dcmi_cmd nm_capability_opts[] = { + { 0x03, "missing", "Missing Power reading trigger" }, + { 0x04, "reset", "Time after Host reset trigger" }, + { 0x05, "boot", "Boot time policy" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_policy_type_vals[] = { +@@ -375,13 +377,13 @@ const struct dcmi_cmd nm_policy_type_vals[] = { + { 0x02, "Missing Power reading trigger", "" }, + { 0x03, "Time after Host reset trigger", "" }, + { 0x04, "number of cores to disable at boot time", "" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_stats_opts[] = { + { 0x01, "domain", " (default is platform)" }, + { 0x02, "policy_id", "<0-7>" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_stats_mode[] = { +@@ -395,7 +397,7 @@ const struct dcmi_cmd nm_stats_mode[] = { + { 0x1D, "cpu_throttling", "CPU throttling" }, + { 0x1E, "mem_throttling", "memory throttling" }, + { 0x1F, "comm_fail", "host communication failures" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_policy_action[] = { +@@ -403,7 +405,7 @@ const struct dcmi_cmd nm_policy_action[] = { + { 0x04, "add", "nm policy add policy_id <0-7> [domain ] correction auto|soft|hard power |inlet trig_lim stats enable|disable" }, + { 0x05, "remove", "nm policy remove policy_id <0-7> [domain ]" }, + { 0x06, "limiting", "nm policy limiting [domain ]" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + const struct dcmi_cmd nm_policy_options[] = { + { 0x01, "enable", "" }, +@@ -417,7 +419,7 @@ const struct dcmi_cmd nm_policy_options[] = { + { 0x0B, "policy_id", "policy number" }, + { 0x0C, "volatile", "save policy in volatiel memory" }, + { 0x0D, "cores_off", "at boot time, disable N cores" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + /* if "trigger" command used from nm_policy_options */ +@@ -426,7 +428,7 @@ const struct dcmi_cmd nm_trigger[] = { + { 0x01, "temp", "" }, + { 0x02, "reset", "" }, + { 0x03, "boot", "" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + /* if "correction" used from nm_policy_options */ +@@ -434,7 +436,7 @@ const struct dcmi_cmd nm_correction[] = { + { 0x00, "auto", "" }, + { 0x01, "soft", "" }, + { 0x02, "hard", "" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + /* returned codes from get policy */ +@@ -442,7 +444,7 @@ const struct dcmi_cmd nm_correction_vals[] = { + { 0x00, "no T-state use", "" }, + { 0x01, "no T-state use", "" }, + { 0x02, "use T-states", "" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + /* if "exception" used from nm_policy_options */ +@@ -450,7 +452,7 @@ const struct dcmi_cmd nm_exception[] = { + { 0x00, "none", "" }, + { 0x01, "alert", "" }, + { 0x02, "shutdown", "" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_reset_mode[] = { +@@ -461,42 +463,46 @@ const struct dcmi_cmd nm_reset_mode[] = { + { 0x1D, "throttling", "" }, + { 0x1E, "memory", "", }, + { 0x1F, "comm", "" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_power_range[] = { + { 0x01, "domain", "domain (default is platform)" }, + { 0x02, "min", " min " }, + { 0x03, "max", "max " }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_alert_opts[] = { + { 0x01, "set", "nm alert set chan dest string " }, + { 0x02, "get", "nm alert get" }, + { 0x03, "clear", "nm alert clear dest " }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_set_alert_param[] = { + { 0x01, "chan", "chan " }, + { 0x02, "dest", "dest " }, + { 0x03, "string", "string " }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_thresh_cmds[] = { + { 0x01, "set", "nm thresh set [domain ] policy_id thresh_array" }, + { 0x02, "get", "nm thresh get [domain ] policy_id " }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_thresh_param[] = { + { 0x01, "domain", " (default is platform)" }, + { 0x02, "policy_id", "<0-7>" }, +- { 0xFF, NULL, NULL }, ++ DCMI_CMD_END, + }; + + const struct dcmi_cmd nm_suspend_cmds[] = { + { 0x01, "set", "nm suspend set [domain policy_id " }, + { 0x02, "get", "nm suspend get [domain policy_id " }, ++ DCMI_CMD_END, + }; + + const struct valstr nm_ccode_vals[] = { +-- +2.19.1 + diff --git a/ID-508-Refix-6d9c540-Forgotten-changes.patch b/ID-508-Refix-6d9c540-Forgotten-changes.patch new file mode 100644 index 0000000..aff2098 --- /dev/null +++ b/ID-508-Refix-6d9c540-Forgotten-changes.patch @@ -0,0 +1,412 @@ +From f498e3e29671ec4e2105b44084516485452a32d7 Mon Sep 17 00:00:00 2001 +From: Alexander Amelkin +Date: Thu, 5 Apr 2018 20:09:25 +0300 +Subject: [PATCH 023/119] ID:508 - Refix 6d9c540: Forgotten changes + +Some array terminators were left unmodifed. +This commit removes the diversity to make all terminators unified. +--- + lib/ipmi_dcmi.c | 125 ++++++++++++++++++++++++++++++++---------------- + 1 file changed, 84 insertions(+), 41 deletions(-) + +diff --git a/lib/ipmi_dcmi.c b/lib/ipmi_dcmi.c +index a76b1f2..1dc4a19 100755 +--- a/lib/ipmi_dcmi.c ++++ b/lib/ipmi_dcmi.c +@@ -74,7 +74,12 @@ static int ipmi_print_sensor_info(struct ipmi_intf *intf, uint16_t rec_id); + * to change a lot of the code in the main(). * + ******************************************************************************/ + +-#define DCMI_CMD_END { 0xFF, NULL, NULL } ++/* ++ * This is a termination macro for all struct dcmi_cmd arrays, ++ * def argument is the default value returned by str2val2() ++ * when string is not found in the array ++ */ ++#define DCMI_CMD_END(def) { (def), NULL, NULL } + + /* Main set of DCMI commands */ + const struct dcmi_cmd dcmi_cmd_vals[] = { +@@ -90,7 +95,8 @@ const struct dcmi_cmd dcmi_cmd_vals[] = { + { 0x09, "get_conf_param", " Get DCMI Config Parameters" }, + { 0x0A, "set_conf_param", " Set DCMI Config Parameters" }, + { 0x0B, "oob_discover", " Ping/Pong Message for DCMI Discovery" }, +- DCMI_CMD_END ++ ++ DCMI_CMD_END(0xFF) + }; + + /* get capabilites */ +@@ -100,7 +106,8 @@ const struct dcmi_cmd dcmi_capable_vals[] = { + "temperature attributes" }, + { 0x03, "optional_attributes", " Lists power capabilities" }, + { 0x04, "managebility access", " Lists OOB channel information" }, +- DCMI_CMD_END ++ ++ DCMI_CMD_END(0xFF) + }; + + /* platform capabilities +@@ -112,13 +119,14 @@ const struct dcmi_cmd dcmi_mandatory_platform_capabilities[] = { + { 0x02, "SEL logging available", "" }, + { 0x03, "Chassis power available", "" }, + { 0x04, "Temperature monitor available", "" }, +- DCMI_CMD_END ++ ++ DCMI_CMD_END(0xFF) + }; + + /* optional capabilities */ + const struct dcmi_cmd dcmi_optional_platform_capabilities[] = { + { 0x01, "Power management available", "" }, +- DCMI_CMD_END ++ DCMI_CMD_END(0xFF) + }; + + /* access capabilties */ +@@ -129,7 +137,8 @@ const struct dcmi_cmd dcmi_management_access_capabilities[] = { + { 0x04, "Out-of-band primary LAN channel available", "" }, + { 0x05, "SOL enabled", "" }, + { 0x06, "VLAN capable", "" }, +- DCMI_CMD_END ++ ++ DCMI_CMD_END(0xFF) + }; + + /* identification capabilities */ +@@ -137,7 +146,8 @@ const struct dcmi_cmd dcmi_id_capabilities_vals[] = { + { 0x01, "GUID", "" }, + { 0x02, "DHCP hostname", "" }, + { 0x03, "Asset tag", "" }, +- DCMI_CMD_END ++ ++ DCMI_CMD_END(0xFF) + }; + + /* Configuration parameters*/ +@@ -147,7 +157,8 @@ const struct dcmi_cmd dcmi_conf_param_vals[] = { + { 0x03, "init", "\t\tInitial timeout interval" }, + { 0x04, "timeout", "\t\tServer contact timeout interval" }, + { 0x05, "retry", "\t\tServer contact retry interval" }, +- DCMI_CMD_END ++ ++ DCMI_CMD_END(0xFF) + }; + + +@@ -156,7 +167,8 @@ const struct dcmi_cmd dcmi_temp_monitoring_vals[] = { + { 0x01, "inlet", " Inlet air temperature sensors" }, + { 0x02, "cpu", " CPU temperature sensors" }, + { 0x03, "baseboard", "Baseboard temperature sensors" }, +- { 0xff, NULL, NULL } ++ ++ DCMI_CMD_END(0xFF) + }; + + /* These are not comands. These are the DCMI temp sensors and their numbers +@@ -167,7 +179,8 @@ const struct dcmi_cmd dcmi_discvry_snsr_vals[] = { + { 0x40, "Inlet", " Inlet air temperature sensors" }, + { 0x41, "CPU", " CPU temperature sensors" }, + { 0x42, "Baseboard", "Baseboard temperature sensors" }, +- { 0xff, NULL, NULL } ++ ++ DCMI_CMD_END(0xFF) + }; + + /* Temperature Readings */ +@@ -175,7 +188,8 @@ const struct dcmi_cmd dcmi_temp_read_vals[] = { + { 0x40, "Inlet", "Inlet air temperature(40h) " }, + { 0x41, "CPU", "CPU temperature sensors(41h) " }, + { 0x42, "Baseboard", "Baseboard temperature sensors(42h) " }, +- { 0xff, NULL, NULL } ++ ++ DCMI_CMD_END(0xFF) + }; + + /* power management/control commands */ +@@ -185,7 +199,8 @@ const struct dcmi_cmd dcmi_pwrmgmt_vals[] = { + { 0x02, "set_limit", " Set a power limit option" }, + { 0x03, "activate", " Activate the set power limit" }, + { 0x04, "deactivate", "Deactivate the set power limit" }, +- DCMI_CMD_END ++ ++ DCMI_CMD_END(0xFF) + }; + + /* set power limit commands */ +@@ -194,7 +209,8 @@ const struct dcmi_cmd dcmi_pwrmgmt_set_usage_vals[] = { + { 0x01, "limit", " " }, + { 0x02, "correction", "" }, + { 0x03, "sample", " " }, +- DCMI_CMD_END ++ ++ DCMI_CMD_END(0xFF) + }; + + /* power management/get action commands */ +@@ -219,7 +235,8 @@ const struct dcmi_cmd dcmi_pwrmgmt_get_action_vals[] = { + { 0x10, "OEM reserved (10h)", ""}, + + { 0x11, "Log Event to SEL", ""}, +- DCMI_CMD_END ++ ++ DCMI_CMD_END(0xFF) + }; + + /* power management/set action commands */ +@@ -244,21 +261,23 @@ const struct dcmi_cmd dcmi_pwrmgmt_action_vals[] = { + { 0x0f, "oem_0f", "OEM reserved (0fh)"}, + { 0x10, "oem_10", "OEM reserved (10h)"}, + +- DCMI_CMD_END ++ DCMI_CMD_END(0xFF) + }; + + /* thermal policy action commands */ + const struct dcmi_cmd dcmi_thermalpolicy_vals[] = { + { 0x00, "get", "Get thermal policy" }, + { 0x01, "set", "Set thermal policy" }, +- DCMI_CMD_END ++ ++ DCMI_CMD_END(0xFF) + }; + + /* thermal policy action commands */ + const struct dcmi_cmd dcmi_confparameters_vals[] = { + { 0x00, "get", "Get configuration parameters" }, + { 0x01, "set", "Set configuration parameters" }, +- DCMI_CMD_END ++ ++ DCMI_CMD_END(0xFF) + }; + + /* entityIDs used in thermap policy */ +@@ -270,7 +289,8 @@ const struct dcmi_cmd dcmi_thermalpolicy_set_parameters_vals[] = { + { 0x01, "sel", " Log event to SEL" }, + { 0x00, "nosel", " No 'Log event to SEL' action" }, + { 0x00, "disabled", " Disabled" }, +- { 0x00, NULL, NULL } ++ ++ DCMI_CMD_END(0) + }; + + +@@ -312,7 +332,8 @@ const struct dcmi_cmd dcmi_sampling_vals[] = { + { 0x4F, "15_min", "" }, + { 0x5E, "30_min", "" }, + { 0x81, "1_hour", ""}, +- { 0x00, NULL, NULL }, ++ ++ DCMI_CMD_END(0) + }; + + /* Primary Node Manager commands */ +@@ -327,20 +348,23 @@ const struct dcmi_cmd nm_cmd_vals[] = { + { 0x07, "reset", "Reset Statistics" }, + { 0x08, "alert", "Set/Get/Clear Alert destination" }, + { 0x09, "threshold", "Set/Get Alert Thresholds" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_ctl_cmds[] = { + { 0x01, "enable", " " }, + { 0x00, "disable", ""}, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_ctl_domain[] = { + { 0x00, "global", "" }, + { 0x02, "per_domain", " (default is platform)" }, + { 0x04, "per_policy", "<0-7>" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + /* Node Manager Domain codes */ +@@ -350,7 +374,8 @@ const struct dcmi_cmd nm_domain_vals[] = { + { 0x02, "Memory", "" }, + { 0x03, "protection", "" }, + { 0x04, "I/O", "" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_version_vals[] = { +@@ -359,7 +384,8 @@ const struct dcmi_cmd nm_version_vals[] = { + { 0x03, "2.0", "" }, + { 0x04, "2.5", "" }, + { 0x05, "3.0", "" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_capability_opts[] = { +@@ -368,7 +394,8 @@ const struct dcmi_cmd nm_capability_opts[] = { + { 0x03, "missing", "Missing Power reading trigger" }, + { 0x04, "reset", "Time after Host reset trigger" }, + { 0x05, "boot", "Boot time policy" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_policy_type_vals[] = { +@@ -377,13 +404,15 @@ const struct dcmi_cmd nm_policy_type_vals[] = { + { 0x02, "Missing Power reading trigger", "" }, + { 0x03, "Time after Host reset trigger", "" }, + { 0x04, "number of cores to disable at boot time", "" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_stats_opts[] = { + { 0x01, "domain", " (default is platform)" }, + { 0x02, "policy_id", "<0-7>" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_stats_mode[] = { +@@ -397,7 +426,8 @@ const struct dcmi_cmd nm_stats_mode[] = { + { 0x1D, "cpu_throttling", "CPU throttling" }, + { 0x1E, "mem_throttling", "memory throttling" }, + { 0x1F, "comm_fail", "host communication failures" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_policy_action[] = { +@@ -405,7 +435,8 @@ const struct dcmi_cmd nm_policy_action[] = { + { 0x04, "add", "nm policy add policy_id <0-7> [domain ] correction auto|soft|hard power |inlet trig_lim stats enable|disable" }, + { 0x05, "remove", "nm policy remove policy_id <0-7> [domain ]" }, + { 0x06, "limiting", "nm policy limiting [domain ]" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + const struct dcmi_cmd nm_policy_options[] = { + { 0x01, "enable", "" }, +@@ -419,7 +450,8 @@ const struct dcmi_cmd nm_policy_options[] = { + { 0x0B, "policy_id", "policy number" }, + { 0x0C, "volatile", "save policy in volatiel memory" }, + { 0x0D, "cores_off", "at boot time, disable N cores" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + /* if "trigger" command used from nm_policy_options */ +@@ -428,7 +460,8 @@ const struct dcmi_cmd nm_trigger[] = { + { 0x01, "temp", "" }, + { 0x02, "reset", "" }, + { 0x03, "boot", "" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + /* if "correction" used from nm_policy_options */ +@@ -436,7 +469,8 @@ const struct dcmi_cmd nm_correction[] = { + { 0x00, "auto", "" }, + { 0x01, "soft", "" }, + { 0x02, "hard", "" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + /* returned codes from get policy */ +@@ -444,7 +478,8 @@ const struct dcmi_cmd nm_correction_vals[] = { + { 0x00, "no T-state use", "" }, + { 0x01, "no T-state use", "" }, + { 0x02, "use T-states", "" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + /* if "exception" used from nm_policy_options */ +@@ -452,7 +487,8 @@ const struct dcmi_cmd nm_exception[] = { + { 0x00, "none", "" }, + { 0x01, "alert", "" }, + { 0x02, "shutdown", "" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_reset_mode[] = { +@@ -463,46 +499,53 @@ const struct dcmi_cmd nm_reset_mode[] = { + { 0x1D, "throttling", "" }, + { 0x1E, "memory", "", }, + { 0x1F, "comm", "" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_power_range[] = { + { 0x01, "domain", "domain (default is platform)" }, + { 0x02, "min", " min " }, + { 0x03, "max", "max " }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_alert_opts[] = { + { 0x01, "set", "nm alert set chan dest string " }, + { 0x02, "get", "nm alert get" }, + { 0x03, "clear", "nm alert clear dest " }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_set_alert_param[] = { + { 0x01, "chan", "chan " }, + { 0x02, "dest", "dest " }, + { 0x03, "string", "string " }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_thresh_cmds[] = { + { 0x01, "set", "nm thresh set [domain ] policy_id thresh_array" }, + { 0x02, "get", "nm thresh get [domain ] policy_id " }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_thresh_param[] = { + { 0x01, "domain", " (default is platform)" }, + { 0x02, "policy_id", "<0-7>" }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct dcmi_cmd nm_suspend_cmds[] = { + { 0x01, "set", "nm suspend set [domain policy_id " }, + { 0x02, "get", "nm suspend get [domain policy_id " }, +- DCMI_CMD_END, ++ ++ DCMI_CMD_END(0xFF), + }; + + const struct valstr nm_ccode_vals[] = { +-- +2.19.1 + diff --git a/Re-apply-commit-58d510f90feb.patch b/Re-apply-commit-58d510f90feb.patch new file mode 100644 index 0000000..03d0a19 --- /dev/null +++ b/Re-apply-commit-58d510f90feb.patch @@ -0,0 +1,48 @@ +From ef7564a7acd20f8f8d99511def96ff9dd65e5a3e Mon Sep 17 00:00:00 2001 +From: Thomas Abraham +Date: Mon, 7 May 2018 15:26:43 -0400 +Subject: [PATCH 025/119] Re-apply commit 58d510f90feb + +Commit 58d510f90feb ("ID : 103 picmg discover messages should +be DEBUG, not INFO") changed picmg discover messages from DEBUG +to INFO. However, commit f1c6118c722b ("ID:320 - Add VITA 46.11 +support") reverted this without explanation. + +This patch reverts the picmg discover messages back to DEBUG. +--- + lib/ipmi_picmg.c | 8 ++++---- + 1 file changed, 4 insertions(+), 4 deletions(-) + +diff --git a/lib/ipmi_picmg.c b/lib/ipmi_picmg.c +index 2166cbe..6c24dec 100644 +--- a/lib/ipmi_picmg.c ++++ b/lib/ipmi_picmg.c +@@ -2348,13 +2348,13 @@ picmg_discover(struct ipmi_intf *intf) { + req.msg.data_len = 1; + msg_data = 0; + +- lprintf(LOG_INFO, "Running Get PICMG Properties my_addr %#x, transit %#x, target %#x", ++ lprintf(LOG_DEBUG, "Running Get PICMG Properties my_addr %#x, transit %#x, target %#x", + intf->my_addr, intf->transit_addr, intf->target_addr); + rsp = intf->sendrecv(intf, &req); + if (rsp == NULL) { +- lprintf(LOG_INFO,"No response from Get PICMG Properties"); ++ lprintf(LOG_DEBUG,"No response from Get PICMG Properties"); + } else if (rsp->ccode != 0) { +- lprintf(LOG_INFO,"Error response %#x from Get PICMG Properities", ++ lprintf(LOG_DEBUG,"Error response %#x from Get PICMG Properities", + rsp->ccode); + } else if (rsp->data_len < 4) { + lprintf(LOG_INFO,"Invalid Get PICMG Properties response length %d", +@@ -2369,7 +2369,7 @@ picmg_discover(struct ipmi_intf *intf) { + (rsp->data[1] & 0x0F), (rsp->data[1] >> 4)); + } else { + picmg_avail = 1; +- lprintf(LOG_INFO, "Discovered PICMG Extension Version %d.%d", ++ lprintf(LOG_DEBUG, "Discovered PICMG Extension Version %d.%d", + (rsp->data[1] & 0x0f), (rsp->data[1] >> 4)); + } + +-- +2.19.1 + diff --git a/Refactor-free_n-function.patch b/Refactor-free_n-function.patch new file mode 100644 index 0000000..2b7b5b7 --- /dev/null +++ b/Refactor-free_n-function.patch @@ -0,0 +1,45 @@ +From 08348f1b72de27681549894f7a506674fba19ff2 Mon Sep 17 00:00:00 2001 +From: Alexander Amelkin +Date: Wed, 20 Feb 2019 14:56:37 +0300 +Subject: [PATCH 114/119] Refactor free_n() function + +Make the argument to free_n() compatible with any pointers, +thus reducing the number of compilation warnings. + +End-user-impact: None +Signed-off-by: Alexander Amelkin +--- + include/ipmitool/helper.h | 10 ++++++---- + 1 file changed, 6 insertions(+), 4 deletions(-) + +diff --git a/include/ipmitool/helper.h b/include/ipmitool/helper.h +index c03c931..0d4f6e3 100644 +--- a/include/ipmitool/helper.h ++++ b/include/ipmitool/helper.h +@@ -37,6 +37,7 @@ + #include + #include + #include ++#include /* For free() */ + + #ifndef TRUE + #define TRUE 1 +@@ -115,10 +116,11 @@ uint16_t ipmi_get_oem_id(struct ipmi_intf *intf); + * Free the memory and clear the pointer. + * @param[in] ptr - a pointer to your pointer to free. + */ +-static inline void free_n(void **ptr) { +- if (ptr && *ptr) { +- free(*ptr); +- *ptr = NULL; ++static inline void free_n(void *ptr) { ++ void **pptr = (void **)ptr; ++ if (pptr && *pptr) { ++ free(*pptr); ++ *pptr = NULL; + } + } + +-- +2.19.1 + diff --git a/Replace-user_id-masks-with-a-macro-8.patch b/Replace-user_id-masks-with-a-macro-8.patch new file mode 100644 index 0000000..93b71f2 --- /dev/null +++ b/Replace-user_id-masks-with-a-macro-8.patch @@ -0,0 +1,96 @@ +From 432f06db3f1fe253025ab1e0a29b0d139afa8de6 Mon Sep 17 00:00:00 2001 +From: Alexander Amelkin +Date: Wed, 30 May 2018 18:57:20 +0300 +Subject: [PATCH 027/119] Replace user_id masks with a macro (#8) + +In multiple places throughout ipmi_user.c a user id mask +was used as a magic number, in some places the mask was wrong. +This commit replaces all those magic numbers with a single +IPMI_UID() macro. + +Resolves ipmitool/ipmitool#6 +--- + include/ipmitool/ipmi_user.h | 3 +++ + lib/ipmi_user.c | 16 +++++++++------- + 2 files changed, 12 insertions(+), 7 deletions(-) + +diff --git a/include/ipmitool/ipmi_user.h b/include/ipmitool/ipmi_user.h +index fd727ca..0fbab0c 100644 +--- a/include/ipmitool/ipmi_user.h ++++ b/include/ipmitool/ipmi_user.h +@@ -48,6 +48,9 @@ + #define IPMI_USER_ENABLE_DISABLED 0x80 + #define IPMI_USER_ENABLE_RESERVED 0xC0 + ++#define IPMI_UID_MASK 0x3F /* The user_id is 6-bit and is usually in bits [5:0] */ ++#define IPMI_UID(id) ((id) & IPMI_UID_MASK) ++ + /* (22.27) Get and (22.26) Set User Access */ + struct user_access_t { + uint8_t callin_callback; +diff --git a/lib/ipmi_user.c b/lib/ipmi_user.c +index 2780e61..cbbe3d5 100644 +--- a/lib/ipmi_user.c ++++ b/lib/ipmi_user.c +@@ -76,7 +76,7 @@ _ipmi_get_user_access(struct ipmi_intf *intf, + return (-3); + } + data[0] = user_access_rsp->channel & 0x0F; +- data[1] = user_access_rsp->user_id & 0x3F; ++ data[1] = IPMI_UID(user_access_rsp->user_id); + req.msg.netfn = IPMI_NETFN_APP; + req.msg.cmd = IPMI_GET_USER_ACCESS; + req.msg.data = data; +@@ -89,10 +89,10 @@ _ipmi_get_user_access(struct ipmi_intf *intf, + } else if (rsp->data_len != 4) { + return (-2); + } +- user_access_rsp->max_user_ids = rsp->data[0] & 0x3F; ++ user_access_rsp->max_user_ids = IPMI_UID(rsp->data[0]); + user_access_rsp->enable_status = rsp->data[1] & 0xC0; +- user_access_rsp->enabled_user_ids = rsp->data[1] & 0x3F; +- user_access_rsp->fixed_user_ids = rsp->data[2] & 0x3F; ++ user_access_rsp->enabled_user_ids = IPMI_UID(rsp->data[1]); ++ user_access_rsp->fixed_user_ids = IPMI_UID(rsp->data[2]); + user_access_rsp->callin_callback = rsp->data[3] & 0x40; + user_access_rsp->link_auth = rsp->data[3] & 0x20; + user_access_rsp->ipmi_messaging = rsp->data[3] & 0x10; +@@ -117,7 +117,7 @@ _ipmi_get_user_name(struct ipmi_intf *intf, struct user_name_t *user_name_ptr) + if (user_name_ptr == NULL) { + return (-3); + } +- data[0] = user_name_ptr->user_id & 0x3F; ++ data[0] = IPMI_UID(user_name_ptr->user_id); + req.msg.netfn = IPMI_NETFN_APP; + req.msg.cmd = IPMI_GET_USER_NAME; + req.msg.data = data; +@@ -165,7 +165,7 @@ _ipmi_set_user_access(struct ipmi_intf *intf, + data[0] |= 0x10; + } + data[0] |= (user_access_req->channel & 0x0F); +- data[1] = user_access_req->user_id & 0x3F; ++ data[1] = IPMI_UID(user_access_req->user_id); + data[2] = user_access_req->privilege_limit & 0x0F; + data[3] = user_access_req->session_limit & 0x0F; + req.msg.netfn = IPMI_NETFN_APP; +@@ -205,7 +205,7 @@ _ipmi_set_user_password(struct ipmi_intf *intf, uint8_t user_id, + } + memset(data, 0, data_len); + data[0] = (is_twenty_byte) ? 0x80 : 0x00; +- data[0] |= (0x0F & user_id); ++ data[0] |= IPMI_UID(user_id); + data[1] = 0x03 & operation; + if (password != NULL) { + size_t copy_len = strlen(password); +@@ -371,6 +371,8 @@ ipmi_user_set_username( + req.msg.data_len = sizeof(msg_data); + memset(msg_data, 0, sizeof(msg_data)); + ++ user_id = IPMI_UID(user_id); ++ + /* The channel number will remain constant throughout this function */ + msg_data[0] = user_id; + strncpy((char *)(msg_data + 1), name, strlen(name)); +-- +2.19.1 + diff --git a/exchange-bmc-os-info b/exchange-bmc-os-info new file mode 100644 index 0000000..c23b507 --- /dev/null +++ b/exchange-bmc-os-info @@ -0,0 +1,326 @@ +#!/bin/sh +############################################################################# +# +# exchange-bmc-os-info: Set OS and BMC (Baseboard Management Controller) +# parameters during system startup. +# +# version: 0.72 +# +# Authors: Charles Rose +# Jordan Hargrave +# +# Description: Script to set OS information in the BMC; fetch BMC IP/URL +# and set in the OS for use by other scripts/user. +# +# BMC IP and URL are made available in /var/run/bmc-info +# +# Example to launch BMC web-interface: +# # . /var/run/bmc-info +# # xdg-open $BMC_URL +# +# See here for details: +# https://fedoraproject.org/wiki/Features/AgentFreeManagement +# +# OEM Specific: OEM specific ipmi commands go in: +# 'oem_set_os_version' and 'oem_get_bmc_url' +############################################################################# +# +# chkconfig: 345 99 00 +# description: Set OS name, hostname in BMC; make BMC IP/URL available in OS +# processname: exchange-bmc-os-info +# config: /etc/sysconfig/exchange-bmc-os-info +# +### BEGIN INIT INFO +# Provides: exchange-bmc-os-info +# Required-Start: ipmi +# Default-Start: 3 4 5 +# Default-Stop: 0 1 2 6 + + +############################################################################# +# GLOBALS +############################################################################# +CONFIGFILE=/etc/sysconfig/exchange-bmc-os-info +IPMI_TOOL=/usr/bin/ipmitool +BMC_INFO=/var/run/bmc-info + +# BMC Manufacturer ID used in 'oem_set_os_version' and 'oem_get_bmc_url' +DELL="674" +#OTHER_OEM="123" + +# Defaults for ${CONFIGFILE} +SET_OS_INFO="yes" +RESET_OS_INFO="no" +SET_BMC_INFO="yes" + +# getsysinfo and setsysinfo commands +IPMI_SET_SYSINFO="${IPMI_TOOL} mc setsysinfo" +IPMI_GET_SYSINFO="${IPMI_TOOL} mc getsysinfo" +############################################################################# +SCRIPT_NAME=$(basename $0) + +# source config +[ -r ${CONFIGFILE} ] && . ${CONFIGFILE} + +RETVAL=0 + +if [ -f /bin/gettext.sh ]; then + GETTEXT=1 + . /bin/gettext.sh + OUTPUT="eval_gettext" +else + GETTEXT=0 + OUTPUT="echo" +fi + +############################################################################# +# Get Vendor ID of BMC for use in 'oem_set_os_version' and 'oem_get_bmc_url' +# +get_bmc_vendor_id() +{ + BMC_VENDOR=$(${IPMI_TOOL} mc info 2>/dev/null | \ + sed -n "s#^Manufacturer ID.*: ##p") + [ -z "${BMC_VENDOR}" ] && RETVAL=4 +} + +# set/getsysinfo support was added to ipmitool post v1.8.12 via this patch +# http://sourceforge.net/mailarchive/message.php?msg_id=29647222 +check_ipmitool() +{ + if [ -x ${IPMI_TOOL} ]; then + [ ! ${IPMI_GET_SYSINFO} >/dev/null 2>&1 ] && \ + RETVAL=3 + else + RETVAL=2 + fi +} + +bmc_exists() +{ + check_ipmitool + [ $RETVAL -eq 0 ] && get_bmc_vendor_id + return $RETVAL +} +############################################################################# + +get_os_info() +{ + OS_HOSTNAME=$(hostname) + KERNEL_VERSION=$(uname -r -m) + + if [ -e /etc/lsb-release ] ; then + . /etc/lsb-release + NAME=${DISTRIB_ID} + VERSION="${DISTRIB_RELEASE} ${DISTRIB_CODENAME}" + fi + + # we prefer systemd's /etc/os-release over other sources + [ -e /etc/os-release ] && . /etc/os-release + + OS_NAME=${NAME} + OS_VERSION="${VERSION} kernel ${KERNEL_VERSION}" +} + +oem_set_os_version() +{ + # OS Version setting is not standard yet + # we need per vendor oem commands + case "${BMC_VENDOR}" in + $DELL) ${IPMI_SET_SYSINFO} delloem_os_version \ + "${OS_VERSION}" > /dev/null 2>&1 + return $? + ;; +# Add OEM specific commands. +# Example: +# $OTHER_OEM) ${IPMI_SET_SYSINFO} otheroem_os_version \ +# "${OS_VERSION}" > /dev/null 2>&1 +# return $? +# ;; + *) return 0 + ;; + esac +} + +set_os_info() +{ + # Set and reset OS info in the BMC + if [ "$1" = "reset" ]; then + OS_NAME="" + OS_HOSTNAME="" + OS_VERSION="" + fi + + ${IPMI_SET_SYSINFO} os_name "${OS_NAME}" >/dev/null 2>&1 \ + || RETVAL=6 + ${IPMI_SET_SYSINFO} primary_os_name "${OS_NAME}" >/dev/null 2>&1 \ + || RETVAL=6 + ${IPMI_SET_SYSINFO} system_name "${OS_HOSTNAME}" >/dev/null 2>&1 \ + || RETVAL=6 + oem_set_os_version || RETVAL=6 +} + +############################################################################# +valid_url() +{ + url="(https?|http)://[a-z0-9-]+(\.[a-z0-9-]+)+([/?].*)?" + printf -- "%s" "${TMP_URL}"| grep -Eq "^${url}" + return $? +} + +oem_get_bmc_url() +{ + # BMC URL is not standard yet + # we need per vendor oem commands + case "$BMC_VENDOR" in + $DELL) TMP_URL=$(${IPMI_GET_SYSINFO} delloem_url 2> /dev/null) + ;; +# Add OEM specific commands +# Example: +# $OTHER_OEM) +# TMP_URL=$(${IPMI_GET_SYSINFO} otheroem_url 2> /dev/null) +# ;; + *) TMP_URL="" ;; + esac + + valid_url && BMC_URL=${TMP_URL} || BMC_URL="" +} + +valid_ip() +{ + #Thanks to mkyong.com + octet="([01]?[[:digit:]][[:digit:]]?|2[0-4][[:digit:]]|25[0-5])" + + printf -- "%s" "${TMP_IPv4}"| grep -Eq "^${octet}\\.${octet}\\.${octet}\\.${octet}$" + return $? +} + +get_bmc_ip() +{ + #Thanks to http://ingvar.blog.redpill-linpro.com + for CHANNEL in `seq 1 14` + do + [ $(${IPMI_TOOL} lan print ${CHANNEL} 2>/dev/null \ + | grep -q "^Set") ] || break + done + + # Get BMC_IPv4 and BMC_URL from BMC + TMP_IPv4=$(${IPMI_TOOL} lan print ${CHANNEL} 2>/dev/null \ + | sed -n "s#^IP Address .*: ##p") + + valid_ip && BMC_IPv4=${TMP_IPv4} || BMC_IPv4="" +} + +get_bmc_info() +{ + get_bmc_ip + if [ -z "${BMC_IPv4}" ] || [ "${BMC_IPv4}" = "0.0.0.0" ]; then + BMC_IPv4="" + RETVAL=5 + else + # URL makes sense only if there is an IP + oem_get_bmc_url + fi +} + +set_bmc_info() +{ + if [ ! $(touch "${BMC_INFO}" && chmod 600 "${BMC_INFO}") ]; then + printf "BMC_IPv4=%s\n" "${BMC_IPv4}" > "${BMC_INFO}" + [ -n "${BMC_URL}" ] && \ + printf "BMC_URL=%s\n" "${BMC_URL}" >> "${BMC_INFO}" + else + RETVAL=5 + fi +} + +unset_bmc_info() +{ + [ -f ${BMC_INFO} ] && rm -f ${BMC_INFO} > /dev/null 2>&1 +} + +############################################################################# +start() +{ + if bmc_exists; then + [ "${SET_OS_INFO}" = "yes" ] && \ + get_os_info && set_os_info + + if [ "${SET_BMC_INFO}" = "yes" ]; then + get_bmc_info + if [ ${RETVAL} -eq 0 ]; then + set_bmc_info + fi + fi + fi +} + +############################################################################# +stop() +{ + if bmc_exists; then + # reset OS info while system reboots + # aids with debugging OS boot-up issues + if [ "${RESET_OS_INFO}" = "yes" ]; then + set_os_info reset + fi + unset_bmc_info + fi +} + +############################################################################# +restart() +{ + stop + [ $RETVAL -eq 0 ] && start +} + +############################################################################# +status() +{ + [ -r ${BMC_INFO} ] && \ + grep -q "BMC_IPv4" "${BMC_INFO}" >/dev/null 1>&2 && \ + BMC_STATUS="ok" || BMC_STATUS="inactive" + ${OUTPUT} "${SCRIPT_NAME}: ${BMC_STATUS}" 1>&2 + [ ${GETTEXT} -eq 1 ] && echo +} + +############################################################################# +usage() +{ + ${OUTPUT} "Usage: ${SCRIPT_NAME} {start|stop|restart|status}" 1>&2 + [ ${GETTEXT} -eq 1 ] && echo + RETVAL=1 +} + +############################################################################# +# MAIN +############################################################################# +case "$1" in + start) start ;; + stop) stop ;; + restart) restart ;; + status) status ;; + *) usage ;; +esac + +case "$RETVAL" in + 0|1) ;; + 2) ${OUTPUT} "${SCRIPT_NAME}: ipmitool(1) not found." 1>&2 ;; + 3) ${OUTPUT} "${SCRIPT_NAME}: this version of ipmitool does not support getsysinfo." 1>&2 ;; + 4) ${OUTPUT} "${SCRIPT_NAME}: failed to communicate with BMC." 1>&2 ;; + 5) ${OUTPUT} "${SCRIPT_NAME}: failed to set OS information in BMC." 1>&2 ;; + 6) ${OUTPUT} "${SCRIPT_NAME}: failed to get BMC information." 1>&2 ;; + *) ${OUTPUT} "${SCRIPT_NAME}: unexpected error." 1>&2 ;; +esac + +if [ ${RETVAL} -gt 1 ]; then + ${OUTPUT} " Return code: ${RETVAL}" 1>&2 + [ ${GETTEXT} -eq 1 ] && echo +fi + + +exit ${RETVAL} + +############################################################################# +# end of file +############################################################################# diff --git a/exchange-bmc-os-info.service b/exchange-bmc-os-info.service new file mode 100644 index 0000000..100493b --- /dev/null +++ b/exchange-bmc-os-info.service @@ -0,0 +1,13 @@ +[Unit] +Description=Exchange Information between BMC and OS +After=ipmi.service network.target +Requires=ipmi.service + +[Service] +Type=oneshot +RemainAfterExit=yes +ExecStart=/usr/libexec/exchange-bmc-os-info start +ExecStop=/usr/libexec/exchange-bmc-os-info stop + +[Install] +WantedBy=multi-user.target diff --git a/exchange-bmc-os-info.sysconf b/exchange-bmc-os-info.sysconf new file mode 100644 index 0000000..2f0e675 --- /dev/null +++ b/exchange-bmc-os-info.sysconf @@ -0,0 +1,26 @@ +# exchange-bmc-os-info +# +# Config file to control Exchange of information between +# the OS and Service Processor/Baseboard Management Controller (BMC) +# +# See here for details +# https://fedoraproject.org/wiki/Features/AgentFreeManagement + +### Set OS Info in BMC/Service Processor ### +# Name: SET_OS_INFO +# Description: Set OS Name, Version and Hostname in the Service Processor (BMC) +# Default: yes +SET_OS_INFO="yes" + +### Reset OS Info in BMC/Service Processor ### +# Name: RESET_OS_INFO +# Description: Reset OS Name, Version and Hostname in the Service Processor (BMC). +# Useful when the OS Name/Hostname should be empty on reboot +# Default: no +RESET_OS_INFO="no" + +### Set BMC/Service Processor Info in OS ### +# Name; SET_BMC_INFO +# Description: Set IP Address and URL of Service Processor/BMC in /run/bmc-info +# Default: yes +SET_BMC_INFO="yes" diff --git a/fru-fixup-array-bounds-checking.patch b/fru-fixup-array-bounds-checking.patch new file mode 100644 index 0000000..639ec36 --- /dev/null +++ b/fru-fixup-array-bounds-checking.patch @@ -0,0 +1,69 @@ +From 6d515dd06bcb89598465cc69e89e37684577e289 Mon Sep 17 00:00:00 2001 +From: Patrick Venture +Date: Mon, 26 Nov 2018 12:38:04 -0800 +Subject: [PATCH 098/119] fru: fixup array bounds checking + +Fixup the following array bounds checking bugs: +[lib/ipmi_fru.c:1003]: (style) Array index 'i' is +used before limits check. +[lib/ipmi_fru.c:1127]: (style) Array index 'i' is +used before limits check. +[lib/ipmi_fru.c:1262]: (style) Array index 'i' is +used before limits check. + +Signed-off-by: Patrick Venture +--- + include/ipmitool/ipmi_fru.h | 2 ++ + lib/ipmi_fru.c | 9 +++------ + 2 files changed, 5 insertions(+), 6 deletions(-) + +diff --git a/include/ipmitool/ipmi_fru.h b/include/ipmitool/ipmi_fru.h +index 65696ba..c543efc 100644 +--- a/include/ipmitool/ipmi_fru.h ++++ b/include/ipmitool/ipmi_fru.h +@@ -41,6 +41,8 @@ + # include + #endif + ++#define FRU_END_OF_FIELDS 0xc1 ++ + #define GET_FRU_INFO 0x10 + #define GET_FRU_DATA 0x11 + #define SET_FRU_DATA 0x12 +diff --git a/lib/ipmi_fru.c b/lib/ipmi_fru.c +index 6115ae6..5057dc3 100644 +--- a/lib/ipmi_fru.c ++++ b/lib/ipmi_fru.c +@@ -957,8 +957,7 @@ fru_area_print_chassis(struct ipmi_intf * intf, struct fru_info * fru, + } + + /* read any extra fields */ +- while ((fru_data[i] != 0xc1) && (i < fru_len)) +- { ++ while ((i < fru_len) && (fru_data[i] != FRU_END_OF_FIELDS)) { + int j = i; + fru_area = get_fru_area_str(fru_data, &i); + if (fru_area != NULL) { +@@ -1083,8 +1082,7 @@ fru_area_print_board(struct ipmi_intf * intf, struct fru_info * fru, + } + + /* read any extra fields */ +- while ((fru_data[i] != 0xc1) && (i < fru_len)) +- { ++ while ((i < fru_len) && (fru_data[i] != FRU_END_OF_FIELDS)) { + int j = i; + fru_area = get_fru_area_str(fru_data, &i); + if (fru_area != NULL) { +@@ -1218,8 +1216,7 @@ fru_area_print_product(struct ipmi_intf * intf, struct fru_info * fru, + } + + /* read any extra fields */ +- while ((fru_data[i] != 0xc1) && (i < fru_len)) +- { ++ while ((i < fru_len) && (fru_data[i] != FRU_END_OF_FIELDS)) { + int j = i; + fru_area = get_fru_area_str(fru_data, &i); + if (fru_area != NULL) { +-- +2.19.1 + diff --git a/fru-internaluse-Fix-segmentation-fault-9.patch b/fru-internaluse-Fix-segmentation-fault-9.patch new file mode 100644 index 0000000..5152b6b --- /dev/null +++ b/fru-internaluse-Fix-segmentation-fault-9.patch @@ -0,0 +1,31 @@ +From 564aef2aff5a0ed9b0c4024c82f846c8633253f4 Mon Sep 17 00:00:00 2001 +From: Hnan-Ting Lo +Date: Wed, 30 May 2018 23:31:24 +0800 +Subject: [PATCH 026/119] fru: internaluse: Fix segmentation fault (#9) + +A segmentation fault was trigged by executing 'ipmitool fru internaluse 1 info'. +A memset() was attempted on the address of a pointer, not on the pointer itself. +The erroneous memset() is removed with this commit because it duplicates +the memset() in line 4072. + +Resolves ipmitool/ipmitool#9 +Signed-off-by: Kylix Lo +--- + lib/ipmi_fru.c | 1 - + 1 file changed, 1 deletion(-) + +diff --git a/lib/ipmi_fru.c b/lib/ipmi_fru.c +index 42c1f19..6115ae6 100644 +--- a/lib/ipmi_fru.c ++++ b/lib/ipmi_fru.c +@@ -4095,7 +4095,6 @@ ipmi_fru_get_internal_use_info( struct ipmi_intf * intf, + return -1; + } + +- memset(&fru, 0, sizeof(fru)); + fru->size = (rsp->data[1] << 8) | rsp->data[0]; + fru->access = rsp->data[2] & 0x1; + +-- +2.19.1 + diff --git a/fru-swap-free-calls-for-free_n.patch b/fru-swap-free-calls-for-free_n.patch new file mode 100644 index 0000000..288b206 --- /dev/null +++ b/fru-swap-free-calls-for-free_n.patch @@ -0,0 +1,510 @@ +From a8b3b6282b3d2bb7fa0e54ce47b06302a96439d7 Mon Sep 17 00:00:00 2001 +From: Patrick Venture +Date: Tue, 25 Dec 2018 06:12:01 -0800 +Subject: [PATCH 113/119] fru: swap free() calls for free_n() + +Swap calls to free() with calls to free_n() to leverage helper method +and handle clearing pointers after freeing in one step. + +Signed-off-by: Patrick Venture +--- + lib/ipmi_fru.c | 182 ++++++++++++++----------------------------------- + 1 file changed, 50 insertions(+), 132 deletions(-) + +diff --git a/lib/ipmi_fru.c b/lib/ipmi_fru.c +index 5057dc3..ad99ebe 100644 +--- a/lib/ipmi_fru.c ++++ b/lib/ipmi_fru.c +@@ -428,8 +428,7 @@ free_fru_bloc(t_ipmi_fru_bloc *bloc) + while (bloc) { + del = bloc; + bloc = bloc->next; +- free(del); +- del = NULL; ++ free_n(&del); + } + } + +@@ -878,8 +877,7 @@ fru_area_print_multirec_bloc(struct ipmi_intf * intf, struct fru_info * fru, + + lprintf(LOG_DEBUG ,"Multi-Record area ends at: %i (%xh)",i,i); + +- free(fru_data); +- fru_data = NULL; ++ free_n(&fru_data); + } + + +@@ -920,8 +918,7 @@ fru_area_print_chassis(struct ipmi_intf * intf, struct fru_info * fru, + + /* read in the full fru */ + if (read_fru_area(intf, fru, id, offset, fru_len, fru_data) < 0) { +- free(fru_data); +- fru_data = NULL; ++ free_n(&fru_data); + return; + } + +@@ -943,8 +940,7 @@ fru_area_print_chassis(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Chassis Part Number : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + fru_area = get_fru_area_str(fru_data, &i); +@@ -952,8 +948,7 @@ fru_area_print_chassis(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Chassis Serial : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + /* read any extra fields */ +@@ -964,8 +959,7 @@ fru_area_print_chassis(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Chassis Extra : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + if (i == j) { +@@ -973,10 +967,7 @@ fru_area_print_chassis(struct ipmi_intf * intf, struct fru_info * fru, + } + } + +- if (fru_data != NULL) { +- free(fru_data); +- fru_data = NULL; +- } ++ free_n(&fru_data); + } + + /* fru_area_print_board - Print FRU Board Area +@@ -1018,8 +1009,7 @@ fru_area_print_board(struct ipmi_intf * intf, struct fru_info * fru, + + /* read in the full fru */ + if (read_fru_area(intf, fru, id, offset, fru_len, fru_data) < 0) { +- free(fru_data); +- fru_data = NULL; ++ free_n(&fru_data); + return; + } + +@@ -1041,8 +1031,7 @@ fru_area_print_board(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Board Mfg : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + fru_area = get_fru_area_str(fru_data, &i); +@@ -1050,8 +1039,7 @@ fru_area_print_board(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Board Product : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + fru_area = get_fru_area_str(fru_data, &i); +@@ -1059,8 +1047,7 @@ fru_area_print_board(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Board Serial : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + fru_area = get_fru_area_str(fru_data, &i); +@@ -1068,8 +1055,7 @@ fru_area_print_board(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Board Part Number : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + fru_area = get_fru_area_str(fru_data, &i); +@@ -1077,8 +1063,7 @@ fru_area_print_board(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0 && verbose > 0) { + printf(" Board FRU ID : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + /* read any extra fields */ +@@ -1089,17 +1074,13 @@ fru_area_print_board(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Board Extra : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + if (i == j) + break; + } + +- if (fru_data != NULL) { +- free(fru_data); +- fru_data = NULL; +- } ++ free_n(&fru_data); + } + + /* fru_area_print_product - Print FRU Product Area +@@ -1140,8 +1121,7 @@ fru_area_print_product(struct ipmi_intf * intf, struct fru_info * fru, + + /* read in the full fru */ + if (read_fru_area(intf, fru, id, offset, fru_len, fru_data) < 0) { +- free(fru_data); +- fru_data = NULL; ++ free_n(&fru_data); + return; + } + +@@ -1157,8 +1137,7 @@ fru_area_print_product(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Product Manufacturer : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + fru_area = get_fru_area_str(fru_data, &i); +@@ -1166,8 +1145,7 @@ fru_area_print_product(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Product Name : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + fru_area = get_fru_area_str(fru_data, &i); +@@ -1175,8 +1153,7 @@ fru_area_print_product(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Product Part Number : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + fru_area = get_fru_area_str(fru_data, &i); +@@ -1184,8 +1161,7 @@ fru_area_print_product(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Product Version : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + fru_area = get_fru_area_str(fru_data, &i); +@@ -1193,8 +1169,7 @@ fru_area_print_product(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Product Serial : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + fru_area = get_fru_area_str(fru_data, &i); +@@ -1202,8 +1177,7 @@ fru_area_print_product(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Product Asset Tag : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + fru_area = get_fru_area_str(fru_data, &i); +@@ -1211,8 +1185,7 @@ fru_area_print_product(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0 && verbose > 0) { + printf(" Product FRU ID : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + + /* read any extra fields */ +@@ -1223,17 +1196,13 @@ fru_area_print_product(struct ipmi_intf * intf, struct fru_info * fru, + if (strlen(fru_area) > 0) { + printf(" Product Extra : %s\n", fru_area); + } +- free(fru_area); +- fru_area = NULL; ++ free_n(&fru_area); + } + if (i == j) + break; + } + +- if (fru_data != NULL) { +- free(fru_data); +- fru_data = NULL; +- } ++ free_n(&fru_data); + } + + /* fru_area_print_multirec - Print FRU Multi Record Area +@@ -1425,7 +1394,7 @@ fru_area_print_multirec(struct ipmi_intf * intf, struct fru_info * fru, + + lprintf(LOG_DEBUG ,"Multi-Record area ends at: %i (%xh)", last_off, last_off); + +- free(fru_data); ++ free_n(&fru_data); + } + + /* ipmi_fru_query_new_value - Query new values to replace original FRU content +@@ -1462,7 +1431,7 @@ int ipmi_fru_query_new_value(uint8_t *data,int offset, size_t len) + for( i=0;itarget_addr = save_addr; + } +- +- if (mc) { +- free(mc); +- mc = NULL; +- } +- ++ free_n(&mc); + continue; + } + +@@ -3170,15 +3133,11 @@ ipmi_fru_print_all(struct ipmi_intf * intf) + fru = (struct sdr_record_fru_locator *) + ipmi_sdr_get_record(intf, header, itr); + if (fru == NULL || !fru->logical) { +- if (fru) { +- free(fru); +- fru = NULL; +- } ++ free_n(&fru); + continue; + } + rc = ipmi_fru_print(intf, fru); +- free(fru); +- fru = NULL; ++ free_n(&fru); + } + + ipmi_sdr_end(intf, itr); +@@ -3254,14 +3213,12 @@ ipmi_fru_read_to_bin(struct ipmi_intf * intf, + printf("Done\n"); + } else { + lprintf(LOG_ERR, "Error opening file %s\n", pFileName); +- free(pFruBuf); +- pFruBuf = NULL; ++ free_n(&pFruBuf); + return; + } + fclose(pFile); + } +- free(pFruBuf); +- pFruBuf = NULL; ++ free_n(&pFruBuf); + } + + static void +@@ -3325,8 +3282,7 @@ ipmi_fru_write_from_bin(struct ipmi_intf * intf, + lprintf(LOG_INFO,"Done"); + } + +- free(pFruBuf); +- pFruBuf = NULL; ++ free_n(&pFruBuf); + } + + /* ipmi_fru_write_help() - print help text for 'write' +@@ -3529,8 +3485,7 @@ ipmi_fru_edit_multirec(struct ipmi_intf * intf, uint8_t id , + i += h->len + sizeof (struct fru_multirec_header); + } while (!(h->format & 0x80) && (error != 1)); + +- free(fru_data); +- fru_data = NULL; ++ free_n(&fru_data); + } + return 0; + } +@@ -3714,8 +3669,7 @@ ipmi_fru_get_multirec(struct ipmi_intf * intf, uint8_t id , + i += h->len + sizeof (struct fru_multirec_header); + } while (!(h->format & 0x80) && (error != 1)); + +- free(fru_data); +- fru_data = NULL; ++ free_n(&fru_data); + } + return 0; + } +@@ -3755,33 +3709,21 @@ ipmi_fru_upg_ekeying(struct ipmi_intf * intf, + if (ipmi_fru_get_multirec_from_file(pFileName, buf, fileMultiRecSize, + offFileMultiRec) != 0) { + lprintf(LOG_ERR, "Failed to get multirec from file '%s'.", pFileName); +- if (buf != NULL) { +- free(buf); +- buf = NULL; +- } ++ free_n(&buf); + return (-1); + } + if (ipmi_fru_get_adjust_size_from_buffer(buf, &fileMultiRecSize) != 0) { + lprintf(LOG_ERR, "Failed to adjust size from buffer."); +- if (buf != NULL) { +- free(buf); +- buf = NULL; +- } ++ free_n(&buf); + return (-1); + } + if (write_fru_area(intf, &fruInfo, fruId, 0, offFruMultiRec, + fileMultiRecSize, buf) != 0) { + lprintf(LOG_ERR, "Failed to write FRU area."); +- if (buf != NULL) { +- free(buf); +- buf = NULL; +- } ++ free_n(&buf); + return (-1); + } +- if (buf != NULL) { +- free(buf); +- buf = NULL; +- } ++ free_n(&buf); + lprintf(LOG_INFO, "Done upgrading Ekey."); + return 0; + } +@@ -4283,8 +4225,7 @@ ipmi_fru_read_internal_use(struct ipmi_intf * intf, uint8_t id, char * pFileName + else + { + lprintf(LOG_ERR, "Error opening file %s\n", pFileName); +- free(frubuf); +- frubuf = NULL; ++ free_n(&frubuf); + return -1; + } + fclose(pFile); +@@ -4292,8 +4233,7 @@ ipmi_fru_read_internal_use(struct ipmi_intf * intf, uint8_t id, char * pFileName + } + printf("\n"); + +- free(frubuf); +- frubuf = NULL; ++ free_n(&frubuf); + } + + } +@@ -4376,8 +4316,7 @@ ipmi_fru_write_internal_use(struct ipmi_intf * intf, uint8_t id, char * pFileNam + lprintf(LOG_ERR, "Unable to read file: %i\n", fru_read_size); + } + +- free(frubuf); +- frubuf = NULL; ++ free_n(&frubuf); + } + fclose(fp); + fp = NULL; +@@ -4778,10 +4717,7 @@ f_type, uint8_t f_index, char *f_string) + /*Seek to field index */ + for (i=0; i <= f_index; i++) { + fru_field_offset_tmp = fru_field_offset; +- if (fru_area != NULL) { +- free(fru_area); +- fru_area = NULL; +- } ++ free_n(&fru_area); + fru_area = (uint8_t *) get_fru_area_str(fru_data, &fru_field_offset); + } + +@@ -4827,14 +4763,8 @@ f_type, uint8_t f_index, char *f_string) + } + + ipmi_fru_set_field_string_out: +- if (fru_data != NULL) { +- free(fru_data); +- fru_data = NULL; +- } +- if (fru_area != NULL) { +- free(fru_area); +- fru_area = NULL; +- } ++ free_n(&fru_data); ++ free_n(&fru_area); + + return rc; + } +@@ -4956,10 +4886,7 @@ ipmi_fru_set_field_string_rebuild(struct ipmi_intf * intf, uint8_t fruId, + 3) Seek to field index */ + for (i = 0;i <= f_index; i++) { + fru_field_offset_tmp = fru_field_offset; +- if (fru_area != NULL) { +- free(fru_area); +- fru_area = NULL; +- } ++ free_n(&fru_area); + fru_area = (uint8_t *) get_fru_area_str(fru_data_old, &fru_field_offset); + } + +@@ -5191,18 +5118,9 @@ ipmi_fru_set_field_string_rebuild(struct ipmi_intf * intf, uint8_t fruId, + printf("Done.\n"); + + ipmi_fru_set_field_string_rebuild_out: +- if (fru_area != NULL) { +- free(fru_area); +- fru_area = NULL; +- } +- if (fru_data_new != NULL) { +- free(fru_data_new); +- fru_data_new = NULL; +- } +- if (fru_data_old != NULL) { +- free(fru_data_old); +- fru_data_old = NULL; +- } ++ free_n(&fru_area); ++ free_n(&fru_data_new); ++ free_n(&fru_data_old); + + return rc; + } +-- +2.19.1 + diff --git a/helper-add-free_n-method-to-handle-clearing-pointers.patch b/helper-add-free_n-method-to-handle-clearing-pointers.patch new file mode 100644 index 0000000..2c3c23a --- /dev/null +++ b/helper-add-free_n-method-to-handle-clearing-pointers.patch @@ -0,0 +1,41 @@ +From 8b6d127bb14b9ad7ef28da1fc5f8c965df2123cd Mon Sep 17 00:00:00 2001 +From: Patrick Venture +Date: Wed, 5 Dec 2018 08:55:59 -0800 +Subject: [PATCH 093/119] helper: add free_n method to handle clearing pointers + +free_n() will free the memory and clear the pointer, which will reduce +the probability a developer will forget to clear the pointer after +freeing. + +Resolves: #79 + +Signed-off-by: Patrick Venture +--- + include/ipmitool/helper.h | 11 +++++++++++ + 1 file changed, 11 insertions(+) + +diff --git a/include/ipmitool/helper.h b/include/ipmitool/helper.h +index c53736f..c03c931 100644 +--- a/include/ipmitool/helper.h ++++ b/include/ipmitool/helper.h +@@ -111,6 +111,17 @@ FILE * ipmi_open_file(const char * file, int rw); + void ipmi_start_daemon(struct ipmi_intf *intf); + uint16_t ipmi_get_oem_id(struct ipmi_intf *intf); + ++/** ++ * Free the memory and clear the pointer. ++ * @param[in] ptr - a pointer to your pointer to free. ++ */ ++static inline void free_n(void **ptr) { ++ if (ptr && *ptr) { ++ free(*ptr); ++ *ptr = NULL; ++ } ++} ++ + #define ipmi_open_file_read(file) ipmi_open_file(file, 0) + #define ipmi_open_file_write(file) ipmi_open_file(file, 1) + +-- +2.19.1 + diff --git a/hpm-Fix-resource-leak.patch b/hpm-Fix-resource-leak.patch new file mode 100644 index 0000000..439f020 --- /dev/null +++ b/hpm-Fix-resource-leak.patch @@ -0,0 +1,26 @@ +From 272d9d0d9b29f41b6b10a870d856fec8d19233e2 Mon Sep 17 00:00:00 2001 +From: Josef Moellers +Date: Thu, 24 Jan 2019 09:16:49 +0100 +Subject: [PATCH 095/119] hpm: Fix resource leak + +fclose(pImageFile) was missing before returning from +HpmfwupgGetBufferFromFile() +--- + lib/ipmi_hpmfwupg.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/lib/ipmi_hpmfwupg.c b/lib/ipmi_hpmfwupg.c +index ac1d90f..4783eec 100644 +--- a/lib/ipmi_hpmfwupg.c ++++ b/lib/ipmi_hpmfwupg.c +@@ -1398,6 +1398,7 @@ HpmfwupgGetBufferFromFile(char *imageFilename, + if (ret != 0) { + lprintf(LOG_ERR, "Failed to seek in the image file '%s'", + imageFilename); ++ fclose(pImageFile); + return HPMFWUPG_ERROR; + } + pFwupgCtx->imageSize = ftell(pImageFile); +-- +2.19.1 + diff --git a/ipmievd.service b/ipmievd.service new file mode 100644 index 0000000..88c22c2 --- /dev/null +++ b/ipmievd.service @@ -0,0 +1,13 @@ +[Unit] +Description=Ipmievd Daemon +After=syslog.target +After=ipmi.service + +[Service] +EnvironmentFile=-/etc/sysconfig/ipmievd +ExecStart=/usr/sbin/ipmievd $IPMIEVD_OPTIONS +Type=forking +PIDFile=/var/run/ipmievd.pid + +[Install] +WantedBy=multi-user.target diff --git a/ipmitool-1.8.18.tar.bz2 b/ipmitool-1.8.18.tar.bz2 new file mode 100644 index 0000000..2d3f0f6 Binary files /dev/null and b/ipmitool-1.8.18.tar.bz2 differ diff --git a/ipmitool.spec b/ipmitool.spec new file mode 100644 index 0000000..3b35932 --- /dev/null +++ b/ipmitool.spec @@ -0,0 +1,129 @@ +Name: ipmitool +Version: 1.8.18 +Release: 11 +Summary: Utility for IPMI control +License: BSD +URL: http://ipmitool.sourceforge.net/ +Source0: http://downloads.sourceforge.net/project/%{name}/%{name}/%{version}/%{name}-%{version}.tar.bz2 +Source1: openipmi-ipmievd.sysconf +Source2: ipmievd.service +Source3: exchange-bmc-os-info.service +Source4: exchange-bmc-os-info.sysconf +Source5: set-bmc-url.sh +Source6: exchange-bmc-os-info + +# patch1 to patch 7 come from fedora +Patch1: 0001-CVE-2011-4339-OpenIPMI.patch +Patch2: 0002-openssl.patch +Patch3: 0003-ipmitool-1.8.11-set-kg-key.patch +Patch4: 0004-slowswid.patch +Patch5: 0005-sensor-id-length.patch +Patch6: 0006-enable-usb.patch +Patch7: 0007-check-input.patch +Patch6000: ID-477-fru-Fix-decoding-of-non-text-data-in-get_fru_.patch +Patch6001: ID-480-ipmitool-coredumps-in-EVP_CIPHER_CTX_init.patch +Patch6002: ID-480-Call-EVP_CIPHER_CTX_free-instead-of-EVP_CIPHE.patch +Patch6003: ID-472-Fix-The-Most-recent-Addition-Erase-date.patch +Patch6004: ID-508-Fix-segfaults-in-dcmi-command-handlers.patch +Patch6005: ID-508-Refix-6d9c540-Forgotten-changes.patch +Patch6006: Re-apply-commit-58d510f90feb.patch +Patch6007: fru-internaluse-Fix-segmentation-fault-9.patch +Patch6008: Replace-user_id-masks-with-a-macro-8.patch +Patch6009: plugins-open-Fix-for-interrupted-select.patch +Patch6010: plugins-open-Properly-enable-event-receiver-35.patch +Patch6011: lanplus-Cleanup.-Refix-6dec83ff-fix-be2c0c4b.patch +Patch6012: lanplus-Fix-segfault-for-truncated-dcmi-response.patch +Patch6013: helper-add-free_n-method-to-handle-clearing-pointers.patch +Patch6014: sol-Make-interface-timeout-obey-the-N-option.patch +Patch6015: hpm-Fix-resource-leak.patch +Patch6016: fru-fixup-array-bounds-checking.patch +Patch6017: fru-swap-free-calls-for-free_n.patch +Patch6018: Refactor-free_n-function.patch +Patch6019: open-checking-received-msg-id-against-expectation.patch + +BuildRequires: openssl-devel readline-devel ncurses-devel git +%{?systemd_requires} +BuildRequires: systemd +BuildRequires: automake autoconf libtool +Requires: net-snmp hostname +Obsoletes: OpenIPMI-tools < 2.0.14-3 +Provides: OpenIPMI-tools = 2.0.14-3 +Obsoletes: ipmievd bmc-snmp-proxy exchange-bmc-os-info +Provides: ipmievd bmc-snmp-proxy exchange-bmc-os-info + +%description +This package provides a simple command-line interface to IPMI-enabled devices +through an IPMIv1.5 or IPMIv2.0 LAN interface or Linux/Solaris kernel driver. + +%package_help + +%prep +%autosetup -n %{name}-%{version} -p1 -S git + +for f in AUTHORS ChangeLog; do + iconv -f iso-8859-1 -t utf8 < ${f} > ${f}.utf8 + mv ${f}.utf8 ${f} +done + +%build +aclocal +libtoolize --automake --copy +autoheader +automake --foreign --add-missing --copy +aclocal +autoconf +automake --foreign + +%configure --disable-dependency-tracking --enable-file-security --disable-intf-free +%make_build + +%install +%make_install + +install -Dpm 644 %{SOURCE2} %{buildroot}%{_unitdir}/ipmievd.service +install -Dpm 644 %{SOURCE1} %{buildroot}%{_sysconfdir}/sysconfig/ipmievd +install -Dm 644 %{SOURCE3} %{buildroot}%{_unitdir}/exchange-bmc-os-info.service +install -Dm 644 %{SOURCE4} %{buildroot}%{_sysconfdir}/sysconfig/exchange-bmc-os-info +install -Dm 644 %{SOURCE5} %{buildroot}%{_sysconfdir}/profile.d/set-bmc-url.sh +install -Dm 755 %{SOURCE6} %{buildroot}%{_libexecdir}/exchange-bmc-os-info +install -Dm 644 contrib/bmc-snmp-proxy.sysconf %{buildroot}%{_sysconfdir}/sysconfig/bmc-snmp-proxy +install -Dm 644 contrib/bmc-snmp-proxy.service %{buildroot}%{_unitdir}/bmc-snmp-proxy.service +install -Dm 755 contrib/bmc-snmp-proxy %{buildroot}%{_libexecdir}/bmc-snmp-proxy + +%post +%systemd_post ipmievd.service +%systemd_post exchange-bmc-os-info.service + +%preun +%systemd_preun ipmievd.service +%systemd_preun exchange-bmc-os-info.service + +%postun +%systemd_postun_with_restart ipmievd.service +%systemd_postun_with_restart exchange-bmc-os-info.service + +%triggerun -- %{name} +/usr/bin/systemd-sysv-convert --save ipmievd >/dev/null 2>&1 ||: +/sbin/chkconfig --del ipmievd >/dev/null 2>&1 || : +/bin/systemctl try-restart ipmievd.service >/dev/null 2>&1 || : + +%files +%doc %{_datadir}/doc/ipmitool/AUTHORS +%doc %{_datadir}/doc/ipmitool/COPYING +%config(noreplace) %{_sysconfdir}/sysconfig/* +%{_sysconfdir}/profile.d/set-bmc-url.sh +%{_bindir}/ipmitool +%{_sbindir}/ipmievd +%{_unitdir}/*.service +%{_libexecdir}/* +%{_datadir}/ipmitool + +%files help +%doc %{_datadir}/doc/ipmitool/README +%doc %{_datadir}/doc/ipmitool/ChangeLog +%{_mandir}/man1/ipmitool.1* +%{_mandir}/man8/ipmievd.8* + +%changelog +* Sat Sep 21 2019 openEuler Buildteam - 1.8.18-11 +- Package init diff --git a/lanplus-Cleanup.-Refix-6dec83ff-fix-be2c0c4b.patch b/lanplus-Cleanup.-Refix-6dec83ff-fix-be2c0c4b.patch new file mode 100644 index 0000000..9cdd648 --- /dev/null +++ b/lanplus-Cleanup.-Refix-6dec83ff-fix-be2c0c4b.patch @@ -0,0 +1,40 @@ +From 64727f59c4a1412fdb73e092fb838ae66e2aad1a Mon Sep 17 00:00:00 2001 +From: Alexander Amelkin +Date: Thu, 29 Nov 2018 13:10:53 +0300 +Subject: [PATCH 090/119] lanplus: Cleanup. Refix 6dec83ff, fix be2c0c4b + +This is a cleanup commit. + +Commit 6dec83ff removed assignment of `rsp` pointer +in SOL-processing block of ipmi_lan_poll_single(), +but left the check for the pointer validity in place. +Although that has effectively fixed the bug of potentially +accessing the null `rsp` pointer in the `else` block introduced +with be2c0c4b, the resulting if/else looked suspicious and left +and impression that a NULL pointer could still be accessed. + +This commit removes the check for `rsp` from the `if` +as it is checked at the start of the function where `rsp` +is initialized (and that is the only place where it is ever changed). + +Signed-off-by: Alexander Amelkin +--- + src/plugins/lanplus/lanplus.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/src/plugins/lanplus/lanplus.c b/src/plugins/lanplus/lanplus.c +index c4041a8..aabcf94 100644 +--- a/src/plugins/lanplus/lanplus.c ++++ b/src/plugins/lanplus/lanplus.c +@@ -844,7 +844,7 @@ ipmi_lan_poll_single(struct ipmi_intf * intf) + } + read_sol_packet(rsp, &offset); + extra_data_length = payload_size - (offset - payload_start); +- if (rsp && extra_data_length) { ++ if (extra_data_length) { + rsp->data_len = extra_data_length; + memmove(rsp->data, rsp->data + offset, extra_data_length); + } else { +-- +2.19.1 + diff --git a/lanplus-Fix-segfault-for-truncated-dcmi-response.patch b/lanplus-Fix-segfault-for-truncated-dcmi-response.patch new file mode 100644 index 0000000..7684358 --- /dev/null +++ b/lanplus-Fix-segfault-for-truncated-dcmi-response.patch @@ -0,0 +1,44 @@ +From 9ec2232321a7bca7e1fb8f939d071f12c8dfa7fd Mon Sep 17 00:00:00 2001 +From: pjdhpe <44778156+pjdhpe@users.noreply.github.com> +Date: Wed, 28 Nov 2018 07:27:29 -0600 +Subject: [PATCH 091/119] lanplus: Fix segfault for truncated dcmi response + +On occasion a dcmi power reading will return error C6, and a +truncated response payload. As the decrypted payload is shorter +than the expected length, lanplus_decrypt_aes_cbc_128() adjusts +the payload_size downward by one byte. In ipmi_lan_poll_single() +the calculation to determine if the payload size has increased +erroniously sets extra_data_length to -1, with a subsequent +segv when calling a memmove to shift response data. +The fix is to check for a positive value in the extra_data_length. + +Resolves ipmitool/ipmitool#72 +--- + src/plugins/lanplus/lanplus.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/src/plugins/lanplus/lanplus.c b/src/plugins/lanplus/lanplus.c +index aabcf94..28cb31c 100644 +--- a/src/plugins/lanplus/lanplus.c ++++ b/src/plugins/lanplus/lanplus.c +@@ -790,7 +790,7 @@ ipmi_lan_poll_single(struct ipmi_intf * intf) + * rsp->data_len becomes the length of that data + */ + extra_data_length = payload_size - (offset - payload_start) - 1; +- if (extra_data_length) { ++ if (extra_data_length > 0) { + rsp->data_len = extra_data_length; + memmove(rsp->data, rsp->data + offset, extra_data_length); + } else { +@@ -844,7 +844,7 @@ ipmi_lan_poll_single(struct ipmi_intf * intf) + } + read_sol_packet(rsp, &offset); + extra_data_length = payload_size - (offset - payload_start); +- if (extra_data_length) { ++ if (extra_data_length > 0) { + rsp->data_len = extra_data_length; + memmove(rsp->data, rsp->data + offset, extra_data_length); + } else { +-- +2.19.1 + diff --git a/open-checking-received-msg-id-against-expectation.patch b/open-checking-received-msg-id-against-expectation.patch new file mode 100644 index 0000000..fc45628 --- /dev/null +++ b/open-checking-received-msg-id-against-expectation.patch @@ -0,0 +1,125 @@ +From 51634fd77c836e3cb5acd9b9b72e7ede20321d56 Mon Sep 17 00:00:00 2001 +From: Patrick Venture +Date: Tue, 4 Dec 2018 16:47:09 -0800 +Subject: [PATCH 116/119] open: checking received msg id against expectation + +Check the received IPMI response message id against +the id expected given the IPMI request. They need to +match. It is possible that request A times out, +request B is sent, and then request A responds to the +request B. The value for request B may be behind it +in the queue. + +Note: This may only be possible if the file is kept +open between multiple IPMI messages (a common +occurrence). + +Resolves: #82 + +Signed-off-by: Patrick Venture +--- + src/plugins/open/open.c | 80 +++++++++++++++++++++++------------------ + 1 file changed, 46 insertions(+), 34 deletions(-) + +diff --git a/src/plugins/open/open.c b/src/plugins/open/open.c +index 2235509..101676f 100644 +--- a/src/plugins/open/open.c ++++ b/src/plugins/open/open.c +@@ -336,48 +336,60 @@ ipmi_openipmi_send_cmd(struct ipmi_intf * intf, struct ipmi_rq * req) + read_timeout.tv_sec = IPMI_OPENIPMI_READ_TIMEOUT; + read_timeout.tv_usec = 0; + do { +- retval = select(intf->fd+1, &rset, NULL, NULL, &read_timeout); +- } while (retval < 0 && errno == EINTR); +- if (retval < 0) { +- lperror(LOG_ERR, "I/O Error"); +- if (data != NULL) { +- free(data); ++ do { ++ retval = select(intf->fd+1, &rset, NULL, NULL, &read_timeout); ++ } while (retval < 0 && errno == EINTR); ++ if (retval < 0) { ++ lperror(LOG_ERR, "I/O Error"); ++ if (data != NULL) { ++ free(data); + data = NULL; +- } +- return NULL; +- } else if (retval == 0) { +- lprintf(LOG_ERR, "No data available"); +- if (data != NULL) { +- free(data); +- data = NULL; ++ } ++ return NULL; ++ } else if (retval == 0) { ++ lprintf(LOG_ERR, "No data available"); ++ if (data != NULL) { ++ free(data); ++ data = NULL; ++ } ++ return NULL; + } +- return NULL; +- } +- if (FD_ISSET(intf->fd, &rset) == 0) { +- lprintf(LOG_ERR, "No data available"); +- if (data != NULL) { +- free(data); ++ if (FD_ISSET(intf->fd, &rset) == 0) { ++ lprintf(LOG_ERR, "No data available"); ++ if (data != NULL) { ++ free(data); + data = NULL; +- } +- return NULL; +- } ++ } ++ return NULL; ++ } + +- recv.addr = (unsigned char *) &addr; +- recv.addr_len = sizeof(addr); +- recv.msg.data = rsp.data; +- recv.msg.data_len = sizeof(rsp.data); ++ recv.addr = (unsigned char *) &addr; ++ recv.addr_len = sizeof(addr); ++ recv.msg.data = rsp.data; ++ recv.msg.data_len = sizeof(rsp.data); + +- /* get data */ +- if (ioctl(intf->fd, IPMICTL_RECEIVE_MSG_TRUNC, &recv) < 0) { +- lperror(LOG_ERR, "Error receiving message"); +- if (errno != EMSGSIZE) { +- if (data != NULL) { ++ /* get data */ ++ if (ioctl(intf->fd, IPMICTL_RECEIVE_MSG_TRUNC, &recv) < 0) { ++ lperror(LOG_ERR, "Error receiving message"); ++ if (errno != EMSGSIZE) { ++ if (data != NULL) { + free(data); + data = NULL; + } +- return NULL; +- } +- } ++ return NULL; ++ } ++ } ++ /* If the message received wasn't expected, try to grab the ++ * next message until it's out of messages. -EAGAIN is ++ * returned if the list empty, but basically if it returns a ++ * message, check if it's alright. ++ */ ++ if (_req.msgid != recv.msgid) { ++ lprintf(LOG_NOTICE, ++ "Received a response with unexpected ID %ld vs. %ld", ++ recv.msgid, _req.msgid); ++ } ++ } while (_req.msgid != recv.msgid); + + if (verbose > 4) { + fprintf(stderr, "Got message:"); +-- +2.19.1 + diff --git a/openipmi-ipmievd.sysconf b/openipmi-ipmievd.sysconf new file mode 100644 index 0000000..8cc15e0 --- /dev/null +++ b/openipmi-ipmievd.sysconf @@ -0,0 +1 @@ +IPMIEVD_OPTIONS="sel daemon pidfile=/var/run/ipmievd.pid" diff --git a/plugins-open-Fix-for-interrupted-select.patch b/plugins-open-Fix-for-interrupted-select.patch new file mode 100644 index 0000000..6215902 --- /dev/null +++ b/plugins-open-Fix-for-interrupted-select.patch @@ -0,0 +1,33 @@ +From f222df3081d965051be76b85ea52b4aff222edf1 Mon Sep 17 00:00:00 2001 +From: "William A. Kennington III" +Date: Fri, 15 Jun 2018 14:47:12 -0700 +Subject: [PATCH 029/119] plugins/open: Fix for interrupted select + +The select syscall can be interrupted for signals like SIGPROF. The IPMI +command sent will still be outstanding but the send_command will return +an error. When the next command is sent it will get the completion for +the previous command and has the tendency to break state of end users. + +Signed-off-by: William A. Kennington III +--- + src/plugins/open/open.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +diff --git a/src/plugins/open/open.c b/src/plugins/open/open.c +index 5beeac7..59b736d 100644 +--- a/src/plugins/open/open.c ++++ b/src/plugins/open/open.c +@@ -335,7 +335,9 @@ ipmi_openipmi_send_cmd(struct ipmi_intf * intf, struct ipmi_rq * req) + FD_SET(intf->fd, &rset); + read_timeout.tv_sec = IPMI_OPENIPMI_READ_TIMEOUT; + read_timeout.tv_usec = 0; +- retval = select(intf->fd+1, &rset, NULL, NULL, &read_timeout); ++ do { ++ retval = select(intf->fd+1, &rset, NULL, NULL, &read_timeout); ++ } while (retval < 0 && errno == EINTR); + if (retval < 0) { + lperror(LOG_ERR, "I/O Error"); + if (data != NULL) { +-- +2.19.1 + diff --git a/plugins-open-Properly-enable-event-receiver-35.patch b/plugins-open-Properly-enable-event-receiver-35.patch new file mode 100644 index 0000000..b389f18 --- /dev/null +++ b/plugins-open-Properly-enable-event-receiver-35.patch @@ -0,0 +1,41 @@ +From c70665c3d1ae8d19634eb2ea386d1065a4cff506 Mon Sep 17 00:00:00 2001 +From: BenjaminFair +Date: Sun, 9 Sep 2018 04:48:58 -0700 +Subject: [PATCH 065/119] plugins: open: Properly enable event receiver (#35) + +The ioctl to enable the event receiver in the OpenIPMI interface is +called with an argument of 0, which tells OpenIPMI to disable it. Set +the argument to 1 instead so that it will be enabled. + +Signed-off-by: Benjamin Fair +--- + src/plugins/open/open.c | 6 +++--- + 1 file changed, 3 insertions(+), 3 deletions(-) + +diff --git a/src/plugins/open/open.c b/src/plugins/open/open.c +index fd1defd..63f3624 100644 +--- a/src/plugins/open/open.c ++++ b/src/plugins/open/open.c +@@ -91,8 +91,6 @@ extern int verbose; + static int + ipmi_openipmi_open(struct ipmi_intf * intf) + { +- int i = 0; +- + char ipmi_dev[16]; + char ipmi_devfs[16]; + char ipmi_devfs2[16]; +@@ -119,7 +117,9 @@ ipmi_openipmi_open(struct ipmi_intf * intf) + } + } + +- if (ioctl(intf->fd, IPMICTL_SET_GETS_EVENTS_CMD, &i) < 0) { ++ int receive_events = TRUE; ++ ++ if (ioctl(intf->fd, IPMICTL_SET_GETS_EVENTS_CMD, &receive_events) < 0) { + lperror(LOG_ERR, "Could not enable event receiver"); + return -1; + } +-- +2.19.1 + diff --git a/set-bmc-url.sh b/set-bmc-url.sh new file mode 100644 index 0000000..a179981 --- /dev/null +++ b/set-bmc-url.sh @@ -0,0 +1,11 @@ +# Export BMC URL +# + +BMC_INFO="/var/run/bmc-info" + +if [ "$(id -u)" = "0" ]; then + [ -f ${BMC_INFO} ] && . ${BMC_INFO} && \ + export "${BMC_URL}" "${BMC_IPv4}" >/dev/null 2>&1 +fi + +unset BMC_INFO diff --git a/sol-Make-interface-timeout-obey-the-N-option.patch b/sol-Make-interface-timeout-obey-the-N-option.patch new file mode 100644 index 0000000..2c5a114 --- /dev/null +++ b/sol-Make-interface-timeout-obey-the-N-option.patch @@ -0,0 +1,32 @@ +From 0ca9c66b84a9e20a941d44314070601d7fe16aa6 Mon Sep 17 00:00:00 2001 +From: Alexander Amelkin +Date: Fri, 28 Dec 2018 16:33:18 +0300 +Subject: [PATCH 094/119] sol: Make interface timeout obey the -N option + +For `sol activate` the timeout on lanplus interface was hard-coded +to 1 second, overriding the value set with the `-N` option. + +Resolves ipmitool/ipmitool#87 + +Signed-off-by: Alexander Amelkin +--- + lib/ipmi_sol.c | 3 --- + 1 file changed, 3 deletions(-) + +diff --git a/lib/ipmi_sol.c b/lib/ipmi_sol.c +index e08fa9b..adf5df8 100644 +--- a/lib/ipmi_sol.c ++++ b/lib/ipmi_sol.c +@@ -1818,9 +1818,6 @@ ipmi_sol_activate(struct ipmi_intf * intf, int looptest, int interval, + (ap_rsp.payload_udp_port[1] << 8) | + ap_rsp.payload_udp_port[0]; + +- intf->session->timeout = 1; +- +- + /* NOTE: the spec does allow for SOL traffic to be sent on + * a different port. we do not yet support that feature. */ + if (intf->session->sol_data.port != intf->ssn_params.port) +-- +2.19.1 +