OSDN Git Service

platform/surface: aggregator: Add helper macros for requests with argument and return...
authorMaximilian Luz <luzmaximilian@gmail.com>
Fri, 24 Jun 2022 18:36:39 +0000 (20:36 +0200)
committerHans de Goede <hdegoede@redhat.com>
Sat, 2 Jul 2022 09:11:07 +0000 (11:11 +0200)
Add helper macros for synchronous stack-allocated Surface Aggregator
request with both argument and return value, similar to the current
argument-only and return-value-only ones.

Signed-off-by: Maximilian Luz <luzmaximilian@gmail.com>
Link: https://lore.kernel.org/r/20220624183642.910893-2-luzmaximilian@gmail.com
Reviewed-by: Hans de Goede <hdegoede@redhat.com>
Signed-off-by: Hans de Goede <hdegoede@redhat.com>
include/linux/surface_aggregator/controller.h
include/linux/surface_aggregator/device.h

index 50a2b49..d11a1c6 100644 (file)
@@ -470,6 +470,67 @@ struct ssam_request_spec_md {
        }
 
 /**
+ * SSAM_DEFINE_SYNC_REQUEST_WR() - Define synchronous SAM request function with
+ * both argument and return value.
+ * @name:  Name of the generated function.
+ * @atype: Type of the request's argument.
+ * @rtype: Type of the request's return value.
+ * @spec:  Specification (&struct ssam_request_spec) defining the request.
+ *
+ * Defines a function executing the synchronous SAM request specified by @spec,
+ * with the request taking an argument of type @atype and having a return value
+ * of type @rtype. The generated function takes care of setting up the request
+ * and response structs, buffer allocation, as well as execution of the request
+ * itself, returning once the request has been fully completed. The required
+ * transport buffer will be allocated on the stack.
+ *
+ * The generated function is defined as ``static int name(struct
+ * ssam_controller *ctrl, const atype *arg, rtype *ret)``, returning the status
+ * of the request, which is zero on success and negative on failure. The
+ * ``ctrl`` parameter is the controller via which the request is sent. The
+ * request argument is specified via the ``arg`` pointer. The request's return
+ * value is written to the memory pointed to by the ``ret`` parameter.
+ *
+ * Refer to ssam_request_sync_onstack() for more details on the behavior of
+ * the generated function.
+ */
+#define SSAM_DEFINE_SYNC_REQUEST_WR(name, atype, rtype, spec...)               \
+       static int name(struct ssam_controller *ctrl, const atype *arg, rtype *ret) \
+       {                                                                       \
+               struct ssam_request_spec s = (struct ssam_request_spec)spec;    \
+               struct ssam_request rqst;                                       \
+               struct ssam_response rsp;                                       \
+               int status;                                                     \
+                                                                               \
+               rqst.target_category = s.target_category;                       \
+               rqst.target_id = s.target_id;                                   \
+               rqst.command_id = s.command_id;                                 \
+               rqst.instance_id = s.instance_id;                               \
+               rqst.flags = s.flags | SSAM_REQUEST_HAS_RESPONSE;               \
+               rqst.length = sizeof(atype);                                    \
+               rqst.payload = (u8 *)arg;                                       \
+                                                                               \
+               rsp.capacity = sizeof(rtype);                                   \
+               rsp.length = 0;                                                 \
+               rsp.pointer = (u8 *)ret;                                        \
+                                                                               \
+               status = ssam_request_sync_onstack(ctrl, &rqst, &rsp, sizeof(atype)); \
+               if (status)                                                     \
+                       return status;                                          \
+                                                                               \
+               if (rsp.length != sizeof(rtype)) {                              \
+                       struct device *dev = ssam_controller_device(ctrl);      \
+                       dev_err(dev,                                            \
+                               "rqst: invalid response length, expected %zu, got %zu (tc: %#04x, cid: %#04x)", \
+                               sizeof(rtype), rsp.length, rqst.target_category,\
+                               rqst.command_id);                               \
+                       return -EIO;                                            \
+               }                                                               \
+                                                                               \
+               return 0;                                                       \
+       }
+
+/**
  * SSAM_DEFINE_SYNC_REQUEST_MD_N() - Define synchronous multi-device SAM
  * request function with neither argument nor return value.
  * @name: Name of the generated function.
@@ -613,6 +674,70 @@ struct ssam_request_spec_md {
                return 0;                                                       \
        }
 
+/**
+ * SSAM_DEFINE_SYNC_REQUEST_MD_WR() - Define synchronous multi-device SAM
+ * request function with both argument and return value.
+ * @name:  Name of the generated function.
+ * @atype: Type of the request's argument.
+ * @rtype: Type of the request's return value.
+ * @spec:  Specification (&struct ssam_request_spec_md) defining the request.
+ *
+ * Defines a function executing the synchronous SAM request specified by @spec,
+ * with the request taking an argument of type @atype and having a return value
+ * of type @rtype. Device specifying parameters are not hard-coded, but instead
+ * must be provided to the function. The generated function takes care of
+ * setting up the request and response structs, buffer allocation, as well as
+ * execution of the request itself, returning once the request has been fully
+ * completed. The required transport buffer will be allocated on the stack.
+ *
+ * The generated function is defined as ``static int name(struct
+ * ssam_controller *ctrl, u8 tid, u8 iid, const atype *arg, rtype *ret)``,
+ * returning the status of the request, which is zero on success and negative
+ * on failure. The ``ctrl`` parameter is the controller via which the request
+ * is sent, ``tid`` the target ID for the request, and ``iid`` the instance ID.
+ * The request argument is specified via the ``arg`` pointer. The request's
+ * return value is written to the memory pointed to by the ``ret`` parameter.
+ *
+ * Refer to ssam_request_sync_onstack() for more details on the behavior of
+ * the generated function.
+ */
+#define SSAM_DEFINE_SYNC_REQUEST_MD_WR(name, atype, rtype, spec...)            \
+       static int name(struct ssam_controller *ctrl, u8 tid, u8 iid,           \
+                       const atype *arg, rtype *ret)                           \
+       {                                                                       \
+               struct ssam_request_spec_md s = (struct ssam_request_spec_md)spec; \
+               struct ssam_request rqst;                                       \
+               struct ssam_response rsp;                                       \
+               int status;                                                     \
+                                                                               \
+               rqst.target_category = s.target_category;                       \
+               rqst.target_id = tid;                                           \
+               rqst.command_id = s.command_id;                                 \
+               rqst.instance_id = iid;                                         \
+               rqst.flags = s.flags | SSAM_REQUEST_HAS_RESPONSE;               \
+               rqst.length = sizeof(atype);                                    \
+               rqst.payload = (u8 *)arg;                                       \
+                                                                               \
+               rsp.capacity = sizeof(rtype);                                   \
+               rsp.length = 0;                                                 \
+               rsp.pointer = (u8 *)ret;                                        \
+                                                                               \
+               status = ssam_request_sync_onstack(ctrl, &rqst, &rsp, sizeof(atype)); \
+               if (status)                                                     \
+                       return status;                                          \
+                                                                               \
+               if (rsp.length != sizeof(rtype)) {                              \
+                       struct device *dev = ssam_controller_device(ctrl);      \
+                       dev_err(dev,                                            \
+                               "rqst: invalid response length, expected %zu, got %zu (tc: %#04x, cid: %#04x)", \
+                               sizeof(rtype), rsp.length, rqst.target_category,\
+                               rqst.command_id);                               \
+                       return -EIO;                                            \
+               }                                                               \
+                                                                               \
+               return 0;                                                       \
+       }
+
 
 /* -- Event notifier/callbacks. --------------------------------------------- */
 
index c418f7f..6cf7e80 100644 (file)
@@ -483,6 +483,42 @@ static inline void ssam_remove_clients(struct device *dev) {}
                                    sdev->uid.instance, ret);           \
        }
 
+/**
+ * SSAM_DEFINE_SYNC_REQUEST_CL_WR() - Define synchronous client-device SAM
+ * request function with argument and return value.
+ * @name:  Name of the generated function.
+ * @atype: Type of the request's argument.
+ * @rtype: Type of the request's return value.
+ * @spec:  Specification (&struct ssam_request_spec_md) defining the request.
+ *
+ * Defines a function executing the synchronous SAM request specified by @spec,
+ * with the request taking an argument of type @atype and having a return value
+ * of type @rtype. Device specifying parameters are not hard-coded, but instead
+ * are provided via the client device, specifically its UID, supplied when
+ * calling this function. The generated function takes care of setting up the
+ * request struct, buffer allocation, as well as execution of the request
+ * itself, returning once the request has been fully completed. The required
+ * transport buffer will be allocated on the stack.
+ *
+ * The generated function is defined as ``static int name(struct ssam_device
+ * *sdev, const atype *arg, rtype *ret)``, returning the status of the request,
+ * which is zero on success and negative on failure. The ``sdev`` parameter
+ * specifies both the target device of the request and by association the
+ * controller via which the request is sent. The request's argument is
+ * specified via the ``arg`` pointer. The request's return value is written to
+ * the memory pointed to by the ``ret`` parameter.
+ *
+ * Refer to ssam_request_sync_onstack() for more details on the behavior of
+ * the generated function.
+ */
+#define SSAM_DEFINE_SYNC_REQUEST_CL_WR(name, atype, rtype, spec...)            \
+       SSAM_DEFINE_SYNC_REQUEST_MD_WR(__raw_##name, atype, rtype, spec)        \
+       static int name(struct ssam_device *sdev, const atype *arg, rtype *ret) \
+       {                                                                       \
+               return __raw_##name(sdev->ctrl, sdev->uid.target,               \
+                                   sdev->uid.instance, arg, ret);              \
+       }
+
 
 /* -- Helpers for client-device notifiers. ---------------------------------- */