in common/ipmi/ipmi.c [284:427]
void IPMI_handler(void *arug0, void *arug1, void *arug2)
{
uint8_t i;
ipmi_msg_cfg msg_cfg;
while (1) {
k_msgq_get(&ipmi_msgq, &msg_cfg, K_FOREVER);
if (DEBUG_IPMI) {
printf("IPMI_handler[%d]: netfn: %x\n", msg_cfg.buffer.data_len,
msg_cfg.buffer.netfn);
for (i = 0; i < msg_cfg.buffer.data_len; i++) {
printf(" 0x%2x", msg_cfg.buffer.data[i]);
}
printf("\n");
}
msg_cfg.buffer.completion_code = CC_INVALID_CMD;
switch (msg_cfg.buffer.netfn) {
case NETFN_CHASSIS_REQ:
IPMI_CHASSIS_handler(&msg_cfg.buffer);
break;
case NETFN_BRIDGE_REQ:
// IPMI_BRIDGE_handler();
break;
case NETFN_SENSOR_REQ:
IPMI_SENSOR_handler(&msg_cfg.buffer);
break;
case NETFN_APP_REQ:
IPMI_APP_handler(&msg_cfg.buffer);
break;
case NETFN_FIRMWARE_REQ:
break;
case NETFN_STORAGE_REQ:
IPMI_Storage_handler(&msg_cfg.buffer);
break;
case NETFN_TRANSPORT_REQ:
break;
case NETFN_DCMI_REQ:
break;
case NETFN_NM_REQ:
break;
case NETFN_OEM_REQ:
IPMI_OEM_handler(&msg_cfg.buffer);
break;
case NETFN_OEM_1S_REQ:
if ((msg_cfg.buffer.data[0] | (msg_cfg.buffer.data[1] << 8) |
(msg_cfg.buffer.data[2] << 16)) == WW_IANA_ID) {
memcpy(&msg_cfg.buffer.data[0], &msg_cfg.buffer.data[3],
msg_cfg.buffer.data_len);
msg_cfg.buffer.data_len -= 3;
IPMI_OEM_1S_handler(&msg_cfg.buffer);
break;
} else if (pal_is_not_return_cmd(msg_cfg.buffer.netfn,
msg_cfg.buffer.cmd)) {
msg_cfg.buffer.completion_code = CC_INVALID_IANA;
IPMI_OEM_1S_handler(
&msg_cfg.buffer); // Due to command not returning to bridge command source, enter command handler and return with other invalid CC
break;
} else {
msg_cfg.buffer.completion_code = CC_INVALID_IANA;
msg_cfg.buffer.data_len = 0;
break;
}
default: // invalid net function
printf("invalid msg netfn: %x, cmd: %x\n", msg_cfg.buffer.netfn,
msg_cfg.buffer.cmd);
msg_cfg.buffer.data_len = 0;
break;
}
if (pal_is_not_return_cmd(msg_cfg.buffer.netfn, msg_cfg.buffer.cmd)) {
;
} else {
ipmb_error status;
if (msg_cfg.buffer.completion_code != CC_SUCCESS) {
msg_cfg.buffer.data_len = 0;
} else if (msg_cfg.buffer.netfn == NETFN_OEM_1S_REQ) {
uint8_t copy_data[msg_cfg.buffer.data_len];
memcpy(©_data[0], &msg_cfg.buffer.data[0],
msg_cfg.buffer.data_len);
memcpy(&msg_cfg.buffer.data[3], ©_data[0],
msg_cfg.buffer.data_len);
msg_cfg.buffer.data_len += 3;
msg_cfg.buffer.data[0] = WW_IANA_ID & 0xFF;
msg_cfg.buffer.data[1] = (WW_IANA_ID >> 8) & 0xFF;
msg_cfg.buffer.data[2] = (WW_IANA_ID >> 16) & 0xFF;
}
if (msg_cfg.buffer.InF_source == BMC_USB_IFs) {
USB_write(&msg_cfg.buffer);
#ifdef CONFIG_IPMI_KCS_ASPEED
} else if (msg_cfg.buffer.InF_source == HOST_KCS_IFs) {
uint8_t *kcs_buff;
kcs_buff = malloc(KCS_buff_size * sizeof(uint8_t));
if (kcs_buff == NULL) { // allocate fail, retry allocate
k_msleep(10);
kcs_buff = malloc(KCS_buff_size * sizeof(uint8_t));
if (kcs_buff == NULL) {
printk("IPMI_handler: Fail to malloc for kcs_buff\n");
continue;
}
}
kcs_buff[0] = (msg_cfg.buffer.netfn + 1)
<< 2; // ipmi netfn response package
kcs_buff[1] = msg_cfg.buffer.cmd;
kcs_buff[2] = msg_cfg.buffer.completion_code;
if (msg_cfg.buffer.data_len) {
if (msg_cfg.buffer.data_len <= (KCS_buff_size - 3))
memcpy(&kcs_buff[3], msg_cfg.buffer.data,
msg_cfg.buffer.data_len);
else
memcpy(&kcs_buff[3], msg_cfg.buffer.data,
(KCS_buff_size - 3));
}
if (DEBUG_KCS) {
printk("kcs from ipmi netfn %x, cmd %x, length %d, cc %x\n",
kcs_buff[0], kcs_buff[1], msg_cfg.buffer.data_len,
kcs_buff[2]);
}
kcs_write(kcs_buff, msg_cfg.buffer.data_len + 3);
if (kcs_buff != NULL)
free(kcs_buff);
#endif
} else if (msg_cfg.buffer.InF_source == PLDM_IFs) {
/* the message should be passed to source by pldm
* format */
send_msg_by_pldm(&msg_cfg);
} else {
status = ipmb_send_response(
&msg_cfg.buffer,
IPMB_inf_index_map[msg_cfg.buffer.InF_source]);
if (status != ipmb_error_success) {
printf("IPMI_handler send IPMB resp fail status: %x",
status);
}
}
}
}
}