diff options
Diffstat (limited to 'hw/prd.c')
-rw-r--r-- | hw/prd.c | 24 |
1 files changed, 16 insertions, 8 deletions
@@ -89,7 +89,7 @@ static void prd_msg_consumed(void *data) uint8_t event = 0; lock(&events_lock); - switch (msg->type) { + switch (msg->hdr.type) { case OPAL_PRD_MSG_TYPE_ATTN: proc = msg->attn.proc; @@ -169,19 +169,20 @@ static void send_pending_events(void) prd_msg_inuse = true; prd_msg.token = 0; + prd_msg.hdr.size = sizeof(prd_msg); if (event & EVENT_ATTN) { - prd_msg.type = OPAL_PRD_MSG_TYPE_ATTN; + prd_msg.hdr.type = OPAL_PRD_MSG_TYPE_ATTN; populate_ipoll_msg(&prd_msg, proc); event = EVENT_ATTN; } else if (event & EVENT_OCC_ERROR) { - prd_msg.type = OPAL_PRD_MSG_TYPE_OCC_ERROR; + prd_msg.hdr.type = OPAL_PRD_MSG_TYPE_OCC_ERROR; prd_msg.occ_error.chip = proc; event = EVENT_OCC_ERROR; } else if (event & EVENT_OCC_RESET) { - prd_msg.type = OPAL_PRD_MSG_TYPE_OCC_RESET; + prd_msg.hdr.type = OPAL_PRD_MSG_TYPE_OCC_RESET; prd_msg.occ_reset.chip = proc; event = EVENT_OCC_RESET; @@ -325,13 +326,20 @@ static int64_t opal_prd_msg(struct opal_prd_msg *msg) { int rc; - switch (msg->type) { + /* fini is a little special: the kernel (which may not have the entire + * opal_prd_msg definition) can send a FINI message, so we don't check + * the full size */ + if (msg->hdr.size >= sizeof(struct opal_prd_msg_header) && + msg->hdr.type == OPAL_PRD_MSG_TYPE_FINI) + return prd_msg_handle_fini(); + + if (msg->hdr.size != sizeof(*msg)) + return OPAL_PARAMETER; + + switch (msg->hdr.type) { case OPAL_PRD_MSG_TYPE_INIT: rc = prd_msg_handle_init(msg); break; - case OPAL_PRD_MSG_TYPE_FINI: - rc = prd_msg_handle_fini(); - break; case OPAL_PRD_MSG_TYPE_ATTN_ACK: rc = prd_msg_handle_attn_ack(msg); break; |