On Fri, Feb 7, 2014 at 5:46 AM, Zdenek Styblik <zdenek.styb...@gmail.com> wrote:
> Hello,
>
> here is my proposal to re-design and re-work of ipmitool's PEF user
> interface. This is as a reaction to Jordan Hargrave's request to add
> 'pef setpolicy'.
> This is all based on chapter 30. PEF and Alerting Commands, IPMIv2.0
> p.375. Aim isn't to implement all these commands, but to outline user
> interface, so these commands can be implemented eventually.
> There are couple unresolved commands and feel free to chip in your
> ideas how to solve them. :)
>
> Let's set deadline for comments until 28th February 2014.
>
> <Chapter> <Title>
> 30.0 Help
> * 'pef help'
>
> 30.1 Get PEF Capabilities
> * 'pef info' - it's ok, but should be accompanied/complemented with
> 'pef capabilities' or something
>
> 30.2 Arm PEF Postpone Timer
> * 'pef timer get' - this implies user input equal to 0xFFh
> * 'pef timer set <0x00-0xFFh>'
>
> 30.3 Set PEF Config Parameters
> 30.4 Get PEF Config Parameters
> * 'pef policy list'
> * 'pef policy enable <policy_id>'
> * 'pef policy disable <policy_id>'
> * 'pef policy create <policy_id> <params>'
> * 'pef policy delete <policy_id>'
> * and the same thing for 'pef filters'
>
> 30.6 Set Last Processed Event ID
> * unresolved despite it pretty much is '<something> <SEL_id>', but to
> figure out name of <something> :)
>
> 30.7 Get Last Processed Event ID
> * 'pef status' -> I have no idea, but 'status' is misleading/wrong
> given the context, although Oracle's documentation puts it in a way it
> makes sense, quote: ``Print the current PEF status (the last SEL entry
> processed by the BMC, etc).''
>
> 30.8 PET Acknowledge
> * 'pef pet ack <params>'
>
> 30.7 Alert Immediate
> * unresolved - I haven't figured out this one
>
> Changes to current/standing commands:
> * 'pef list' - it lists all entries in PEF
> * 'pef policy' - replaced with 'pef policy list'
>
> Best regards,
> Z.
>
Attached is a patch for proposition above. This should make way for
``Add support for enable/disable PEF policy entries'' -
https://sourceforge.net/p/ipmitool/bugs/323/
Comments and code reviews are welcome. After all, that's the way forward.
Regards,
Z.
> --
> Zdenek Styblik
> email: zdenek.styb...@gmail.com
> jabber: zdenek.styb...@gmail.com
diff --git a/lib/ipmi_pef.c b/lib/ipmi_pef.c
index 154bf40..b6d6687 100644
--- a/lib/ipmi_pef.c
+++ b/lib/ipmi_pef.c
@@ -75,6 +75,8 @@ static const char * pef_flag_fmts[][3] = {
};
static const char * listitem[] = {" | %s", ",%s", "%s"};
+void ipmi_pef_policy_help(void);
+
const char *
ipmi_pef_bit_desc(struct bit_desc_map * map, uint32_t value)
{ /*
@@ -226,14 +228,18 @@ ipmi_pef_get_policy_table(struct ipmi_intf * intf,
req.msg.data = (uint8_t *)&psel;
req.msg.data_len = sizeof(psel);
rsp = ipmi_pef_msg_exchange(intf, &req, "Alert policy table size");
- if (!rsp)
+ if (!rsp) {
return(0);
+ }
tbl_size = (rsp->data[1] & PEF_POLICY_TABLE_SIZE_MASK);
i = (tbl_size * sizeof(struct pef_cfgparm_policy_table_entry));
- if (!i
- || (ptbl = (struct pef_cfgparm_policy_table_entry *)malloc(i)) == NULL)
+ if (!i) {
+ return 0;
+ }
+ ptbl = (struct pef_cfgparm_policy_table_entry *)malloc(i);
+ if (ptbl == NULL) {
return(0);
-
+ }
memset(&psel, 0, sizeof(psel));
psel.id = PEF_CFGPARM_ID_PEF_ALERT_POLICY_TABLE_ENTRY;
for (ptmp=ptbl, i=1; i<=tbl_size; i++) {
@@ -660,25 +666,27 @@ ipmi_pef_list_entries(struct ipmi_intf * intf)
}
}
-static void
+/* ipmi_pef_list_policies - list PEF alert policies
+ */
+int
ipmi_pef_list_policies(struct ipmi_intf * intf)
-{ /*
- // list PEF alert policies
- */
+{
struct ipmi_rs * rsp;
struct ipmi_rq req;
struct pef_cfgparm_policy_table_entry * ptbl = NULL;
struct pef_cfgparm_policy_table_entry * ptmp = NULL;
- uint32_t i;
+ int rc = 0;
uint8_t wrk, ch, medium, tbl_size;
+ uint32_t i;
tbl_size = ipmi_pef_get_policy_table(intf, &ptbl);
- if (!tbl_size) {
+ if (tbl_size == 0) {
if (!ptbl) {
free(ptbl);
ptbl = NULL;
}
- return;
+ lprintf(LOG_ERR, "Failed to get PEF policy table.");
+ return (-1);
}
memset(&req, 0, sizeof(req));
req.msg.netfn = IPMI_NETFN_APP;
@@ -686,53 +694,57 @@ ipmi_pef_list_policies(struct ipmi_intf * intf)
req.msg.data = &ch;
req.msg.data_len = sizeof(ch);
for (ptmp=ptbl, i=1; i<=tbl_size; i++, ptmp++) {
- if ((ptmp->entry.policy & PEF_POLICY_ENABLED) == PEF_POLICY_ENABLED) {
- if (i > 1)
- printf("\n");
- first_field = 1;
- ipmi_pef_print_dec("Alert policy table entry",
- (ptmp->data1 & PEF_POLICY_TABLE_ID_MASK));
- ipmi_pef_print_dec("Policy set",
- (ptmp->entry.policy & PEF_POLICY_ID_MASK) >> PEF_POLICY_ID_SHIFT);
- ipmi_pef_print_str("Policy entry rule",
- ipmi_pef_bit_desc(&pef_b2s_policies, (ptmp->entry.policy & PEF_POLICY_FLAGS_MASK)));
-
- if (ptmp->entry.alert_string_key & PEF_POLICY_EVENT_SPECIFIC) {
- ipmi_pef_print_str("Event-specific", "true");
-// continue;
- }
- wrk = ptmp->entry.chan_dest;
-
- /* channel/description */
- ch = (wrk & PEF_POLICY_CHANNEL_MASK) >> PEF_POLICY_CHANNEL_SHIFT;
- rsp = ipmi_pef_msg_exchange(intf, &req, "Channel info");
- if (!rsp || rsp->data[0] != ch) {
- lprintf(LOG_ERR, " **Error retrieving %s",
- "Channel info");
- continue;
- }
- medium = rsp->data[1];
- ipmi_pef_print_dec("Channel number", ch);
- ipmi_pef_print_str("Channel medium",
- ipmi_pef_bit_desc(&pef_b2s_ch_medium, medium));
-
- /* destination/description */
- wrk &= PEF_POLICY_DESTINATION_MASK;
- switch (medium) {
- case PEF_CH_MEDIUM_TYPE_LAN:
- ipmi_pef_print_lan_dest(intf, ch, wrk);
- break;
- case PEF_CH_MEDIUM_TYPE_SERIAL:
- ipmi_pef_print_serial_dest(intf, ch, wrk);
- break;
- default:
- ipmi_pef_print_dest(intf, ch, wrk);
- break;
- }
+ if ((ptmp->entry.policy & PEF_POLICY_ENABLED) != PEF_POLICY_ENABLED) {
+ /* Why do we list only enabled policies?! */
+ continue;
+ }
+ if (i > 1) {
+ printf("\n");
+ }
+ first_field = 1;
+ ipmi_pef_print_dec("Alert policy table entry",
+ (ptmp->data1 & PEF_POLICY_TABLE_ID_MASK));
+ ipmi_pef_print_dec("Policy set",
+ (ptmp->entry.policy & PEF_POLICY_ID_MASK) >> PEF_POLICY_ID_SHIFT);
+ ipmi_pef_print_str("Policy entry rule",
+ ipmi_pef_bit_desc(&pef_b2s_policies,
+ (ptmp->entry.policy & PEF_POLICY_FLAGS_MASK)));
+
+ if (ptmp->entry.alert_string_key & PEF_POLICY_EVENT_SPECIFIC) {
+ ipmi_pef_print_str("Event-specific", "true");
+ }
+ wrk = ptmp->entry.chan_dest;
+
+ /* channel/description */
+ ch = (wrk & PEF_POLICY_CHANNEL_MASK) >> PEF_POLICY_CHANNEL_SHIFT;
+ rsp = ipmi_pef_msg_exchange(intf, &req, "Channel info");
+ if (!rsp || rsp->data[0] != ch) {
+ lprintf(LOG_ERR, " **Error retrieving %s", "Channel info");
+ rc = (-1);
+ continue;
+ }
+ medium = rsp->data[1];
+ ipmi_pef_print_dec("Channel number", ch);
+ ipmi_pef_print_str("Channel medium",
+ ipmi_pef_bit_desc(&pef_b2s_ch_medium, medium));
+
+ /* destination/description */
+ wrk &= PEF_POLICY_DESTINATION_MASK;
+ switch (medium) {
+ case PEF_CH_MEDIUM_TYPE_LAN:
+ ipmi_pef_print_lan_dest(intf, ch, wrk);
+ break;
+ case PEF_CH_MEDIUM_TYPE_SERIAL:
+ ipmi_pef_print_serial_dest(intf, ch, wrk);
+ break;
+ default:
+ ipmi_pef_print_dest(intf, ch, wrk);
+ break;
}
}
free(ptbl);
ptbl = NULL;
+ return rc;
}
static void
@@ -794,11 +806,15 @@ ipmi_pef_get_status(struct ipmi_intf * intf)
ipmi_pef_print_flags(&pef_b2s_actions, P_ACTV, rsp->data[1]);
}
-static void
-ipmi_pef_get_info(struct ipmi_intf * intf)
-{ /*
- // report PEF capabilities + System GUID
- */
+/* ipmi_pef_get_capabilities - get PEF Capabilities of BMC as described in 30.1
+ * Get PEF Capabilities Command in IPMIv2.0 specification
+ *
+ * returns zero on success
+ * returns (-1) on error
+ */
+int
+ipmi_pef_get_capabilities(struct ipmi_intf *intf)
+{
struct ipmi_rs * rsp;
struct ipmi_rq req;
struct pef_capabilities * pcap;
@@ -817,10 +833,18 @@ ipmi_pef_get_info(struct ipmi_intf * intf)
req.msg.netfn = IPMI_NETFN_SE;
req.msg.cmd = IPMI_CMD_GET_PEF_CAPABILITIES;
rsp = ipmi_pef_msg_exchange(intf, &req, "PEF capabilities");
- if (!rsp)
- return;
+ if (rsp == NULL) {
+ lprintf(LOG_ERR, "No response received.");
+ return (-1);
+ } else if (rsp->ccode != 0x00) {
+ lprintf(LOG_ERR, "Get PEF Capabilities command failed: %s",
+ val2str(rsp->ccode, completion_code_vals));
+ return (-1);
+ } else if (rsp->data_len != 4) {
+ lprintf(LOG_ERR, "Invalid data received");
+ return (-1);
+ }
pcap = (struct pef_capabilities *)rsp->data;
-
ipmi_pef_print_1xd("Version", pcap->version);
ipmi_pef_print_dec("PEF table size", pcap->tblsize);
ipmi_pef_print_dec("Alert policy table size", tbl_size);
@@ -835,56 +859,158 @@ ipmi_pef_get_info(struct ipmi_intf * intf)
req.msg.data_len = sizeof(psel);
rsp = ipmi_pef_msg_exchange(intf, &req, "System GUID");
uid = NULL;
- if (rsp && (rsp->data[1] & PEF_SYSTEM_GUID_USED_IN_PET))
+ if (rsp != NULL && rsp->data_len > 1
+ && (rsp->data[1] & PEF_SYSTEM_GUID_USED_IN_PET)) {
uid = &rsp->data[2];
- else {
+ } else {
memset(&req, 0, sizeof(req));
req.msg.netfn = IPMI_NETFN_APP;
req.msg.cmd = IPMI_CMD_GET_SYSTEM_GUID;
rsp = ipmi_pef_msg_exchange(intf, &req, "System GUID");
- if (rsp)
+ if (rsp != NULL && rsp->data_len > 0) {
uid = &rsp->data[0];
+ }
}
- if (uid) { /* got GUID? */
- if (verbose)
+ /* got GUID? */
+ if (uid != NULL) {
+ if (verbose) {
printf(pef_fld_fmts[F_UID][0], KYWD_LENGTH, "System GUID",
uid[0], uid[1], uid[2], uid[3], uid[4], uid[5], uid[6], uid[7],
uid[8], uid[9], uid[10],uid[11],uid[12],uid[13],uid[14],uid[15]);
- else
+ } else {
printf(pef_fld_fmts[F_UID][1],
uid[0], uid[1], uid[2], uid[3], uid[4], uid[5], uid[6], uid[7],
uid[8], uid[9], uid[10],uid[11],uid[12],uid[13],uid[14],uid[15]);
+ }
}
ipmi_pef_print_flags(&pef_b2s_actions, P_SUPP, actions);
+ return 0;
}
-int ipmi_pef_main(struct ipmi_intf * intf, int argc, char ** argv)
-{ /*
- // PEF subcommand handling
- */
- int help = 0;
- int rc = 0;
-
- if (!argc || !strncmp(argv[0], "info", 4))
- ipmi_pef_get_info(intf);
- else if (!strncmp(argv[0], "help", 4))
- help = 1;
- else if (!strncmp(argv[0], "status", 6))
- ipmi_pef_get_status(intf);
- else if (!strncmp(argv[0], "policy", 6))
- ipmi_pef_list_policies(intf);
- else if (!strncmp(argv[0], "list", 4))
- ipmi_pef_list_entries(intf);
- else {
- help = 1;
- rc = -1;
- lprintf(LOG_ERR, "Invalid PEF command: '%s'\n", argv[0]);
+int
+ipmi_pef_event(struct ipmi_intf *intf, int argc, char **argv)
+{
+ lprintf(LOG_ERR, "Not implemented");
+ return (-1);
+}
+
+int
+ipmi_pef_filter(struct ipmi_intf *intf, int argc, char **argv)
+{
+ lprintf(LOG_ERR, "Not implemented");
+ return (-1);
+}
+
+/* ipmi_pef_help - print-out help text
+ *
+ * returns void
+ */
+void
+ipmi_pef_help(void)
+{
+ lprintf(LOG_NOTICE,
+"usage: pef <command> [options]");
+ lprintf(LOG_NOTICE,
+" capabilities Display PEF capabilities");
+ lprintf(LOG_NOTICE,
+" info Equivalent to capabilities");
+ lprintf(LOG_NOTICE,
+" policy Manage PEF policies");
+ lprintf(LOG_NOTICE,
+" status Display status of PEF processing");
+}
+
+int
+ipmi_pef_pet(struct ipmi_intf *intf, int argc, char **argv)
+{
+ lprintf(LOG_ERR, "Not implemented");
+ return (-1);
+}
+
+int
+ipmi_pef_policy(struct ipmi_intf *intf, int argc, char **argv)
+{
+ int rc = 0;
+ if (argc < 1) {
+ lprintf(LOG_ERR, "Not enough parameters given.");
+ return (-1);
+ }
+ if (!strncmp(argv[0], "help\0", 5)) {
+ ipmi_pef_policy_help();
+ rc = 0;
+ } else if (!strncmp(argv[0], "list\0", 5)) {
+ rc = ipmi_pef_list_policies(intf);
+ } else if (!strncmp(argv[0], "enable\0", 7)) {
+ lprintf(LOG_ERR, "Not implemented");
+ rc = (-1);
+ } else if (!strncmp(argv[0], "disable\0", 8)) {
+ lprintf(LOG_ERR, "Not implemented");
+ rc = (-1);
+ } else if (!strncmp(argv[0], "create\0", 7)) {
+ lprintf(LOG_ERR, "Not implemented");
+ rc = (-1);
+ } else if (!strncmp(argv[0], "delete\0", 7)) {
+ lprintf(LOG_ERR, "Not implemented");
+ rc = (-1);
+ } else {
+ lprintf(LOG_ERR, "Invalid PEF policy command: %s", argv[0]);
+ ipmi_pef_policy_help();
+ rc = (-1);
}
+ return rc;
+}
- if (help)
- lprintf(LOG_NOTICE, "PEF commands: info status policy list");
- else if (!verbose)
- printf("\n");
+void
+ipmi_pef_policy_help(void)
+{
+ lprintf(LOG_NOTICE,
+"usage: pef policy <command> [options]");
+ lprintf(LOG_NOTICE,
+" list List enabled PEF policies");
+}
+
+int
+ipmi_pef_timer(struct ipmi_intf *intf, int argc, char **argv)
+{
+ lprintf(LOG_ERR, "Not implemented");
+ return (-1);
+}
+int
+ipmi_pef_main(struct ipmi_intf *intf, int argc, char **argv)
+{
+ /* TODO - missing:
+ * - 30.5 Set Last Processed Event ID
+ * - 30.6 Get Last Processed Event ID - actually covered by 'status'
+ * - 30.7 Alert Immediate
+ */
+ int rc = 0;
+ if (argc < 1) {
+ lprintf(LOG_ERR, "Not enough parameters given.");
+ ipmi_pef_help();
+ rc = (-1);
+ }
+ if (!strncmp(argv[0], "help\0", 5)) {
+ ipmi_pef_help();
+ rc = 0;
+ } else if (!strncmp(argv[0], "info\0", 5)
+ || !strncmp(argv[0], "capabilities\0", 13)) {
+ rc = ipmi_pef_get_capabilities(intf);
+ } else if (!strncmp(argv[0], "event\0", 6)) {
+ rc = ipmi_pef_event(intf, (argc - 1), ++argv);
+ } else if (!strncmp(argv[0], "filter\0", 7)) {
+ rc = ipmi_pef_filter(intf, (argc - 1), ++argv);
+ } else if (!strncmp(argv[0], "policy\0", 7)) {
+ rc = ipmi_pef_policy(intf, (argc - 1), ++argv);
+ } else if (!strncmp(argv[0], "pet\0", 4)) {
+ rc = ipmi_pef_pet(intf, (argc - 1), ++argv);
+ } else if (!strncmp(argv[0], "status\0", 7)) {
+ ipmi_pef_get_status(intf);
+ } else if (!strncmp(argv[0], "timer\0", 6)) {
+ rc = ipmi_pef_timer(intf, (argc - 1), ++argv);
+ } else {
+ lprintf(LOG_ERR, "Invalid PEF command: %s", argv[0]);
+ rc = (-1);
+ }
return rc;
}
------------------------------------------------------------------------------
"Accelerate Dev Cycles with Automated Cross-Browser Testing - For FREE
Instantly run your Selenium tests across 300+ browser/OS combos.
Get unparalleled scalability from the best Selenium testing platform available
Simple to use. Nothing to install. Get started now for free."
http://p.sf.net/sfu/SauceLabs
_______________________________________________
Ipmitool-devel mailing list
Ipmitool-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ipmitool-devel