[Skiboot] [PATCH 2/7] opal-msg: Add get_opal_msg2
Jeremy Kerr
jk at ozlabs.org
Mon Apr 1 23:48:59 AEDT 2019
Hi Vasant,
Overall, looks pretty good to me. Since we're altering the OPAL API
here, I have a few comments inline:
> Linux uses get_opal_msg (GET_OPAL_MSG) API to get OPAL messages. This
> interface
> supports upto 8 params (64 bytes). Also OPAL doesn't return actual
> message.
>
> We have a requirement to send bigger data to Linux. Hence this patch
> introduces
> new API - GET_OPAL_MSG2.
All of these are OPAL_GET_MSG*, not GET_OPAL_MSG*, right? Might be best
to update the documentation so that it's easily grep-able.
> - get_opal_msg2(uint64_t *buffer, uint64_t *size)
> Linux will allocate and send buffer and buffer size to OPAL.
> OPAL copies opal_msg to buffer and updates size with actual message
> size.
>
> - Replaced `reserved` feild in "struct opal_msg" with `size`. So that
> Linux side get_opal_msg2 user can detect message data size.
Doesn't the kernel already have the size, through the (output) size
value of the opal_get_msg2 call?
> - Add new internal function (opal_queue_msg_extended()) to queue
> opal_msg with bigger data.
I would prefer not to call these messages "extended", as they're all
using the same channel as the existing messages. How about we have:
opal_queue_msg()
- for the __VA_ARGS__ variant
and:
opal_queue_msg_buf()
- for the pointer + size variant
(then opal_queue_msg can just be a macro for opal_queue_msg_buf()).
>
> + /* Check whether opal_get_msg2 is supported by kernel */
> + if (!opal_msg2_supported &&
> + params_size > OPAL_MSG_FIXED_PARAMS_SIZE) {
> + prerror("Discarding extra parameters\n");
> + params_size = OPAL_MSG_FIXED_PARAMS_SIZE;
> + }
So this potentially truncates the message? Shouldn't we reject the
enqueue instead?
[Also, we may need to think about what happens when opal_msg2_supported
is unset when we already have a large message enqueued. Maybe we need to
return the error through the complete() callback?]
> +static int64_t __opal_get_msg(uint64_t *buffer, uint64_t *size)
> +{
> + int rc = OPAL_SUCCESS;
> + int msg_size;
> + struct opal_msg *msg = (struct opal_msg *)buffer;
> struct opal_msg_entry *entry;
> void (*callback)(void *data);
> void *data;
>
> - if (size < sizeof(struct opal_msg) || !buffer)
> + if (*size < sizeof(struct opal_msg) || !buffer)
> return OPAL_PARAMETER;
>
> if (!opal_addr_valid(buffer))
> @@ -92,7 +128,25 @@ static int64_t opal_get_msg(uint64_t *buffer,
> uint64_t size)
> return OPAL_RESOURCE;
> }
>
> - memcpy(buffer, &entry->msg, sizeof(entry->msg));
> + msg_size = offsetof(struct opal_msg, params) +
> + be32_to_cpu(entry->msg.size);
> + /* check whether params[0] contains address or actual data */
So we have different formats of message on the queue? Can we unify the
queue just to have one type, regardless of size?
> + if (be32_to_cpu(entry->msg.size) > OPAL_MSG_FIXED_PARAMS_SIZE) {
> + if (*size < msg_size) {
> + /* Send error message to Linux */
> + rc = OPAL_PARAMETER;
> + } else {
> + msg->msg_type = entry->msg.msg_type;
> + msg->size = entry->msg.size;
> + memcpy((void *)msg->params,
> + (void *)entry->msg.params[0],
> + be32_to_cpu(entry->msg.size));
> + }
> + } else {
> + memcpy(buffer, &entry->msg, sizeof(entry->msg));
> + }
> +
[...]
> diff --git a/doc/opal-api/opal-get-msg2-170.rst b/doc/opal-api/opal-
> get-msg2-170.rst
> new file mode 100644
> index 000000000..42af5e2b3
> --- /dev/null
> +++ b/doc/opal-api/opal-get-msg2-170.rst
> @@ -0,0 +1,30 @@
> +OPAL_GET_MSG2
> +=============
> +
> +OPAL_GET_MSG2 will get the next pending OPAL Message (see :ref:`opal-
> messages`).
> +
> +Parameters: ::
> +
> + buffer to copy message into
> + sizeof buffer to copy message into, OPAL will return actual
> message size
> +
> +The maximum size of an opal message is specified in the device tree
> passed
> +to the host OS: ::
> +
> + ibm,opal {
> + opal-msg-size = <0x10000>;
> + }
> +
> +A host OS *SHOULD* always supply a buffer to OPAL_GET_MSG2 of "opal-
> msg-size"
> +bytes.
I think that opal_get_msg2() should always return an error if the size
is less than that specified in the device tree - ie., make this a MUST.
This should help to prevent misuse of the API.
Cheers,
Jeremy
More information about the Skiboot
mailing list