From: Johan Hovold Date: Fri, 29 Apr 2016 15:08:33 +0000 (+0200) Subject: greybus: operation: add helper functions for unidirectional operations X-Git-Url: https://git.karo-electronics.de/?a=commitdiff_plain;h=5fdc027d5441aecb94ce44de0402bdec3a731de8;p=linux-beck.git greybus: operation: add helper functions for unidirectional operations Add helper functions for initiating unidirectional operations and waiting for them to have been acknowledged as sent by the host device. Signed-off-by: Johan Hovold Signed-off-by: Greg Kroah-Hartman --- diff --git a/drivers/staging/greybus/operation.c b/drivers/staging/greybus/operation.c index 9fb7993a86e8..fcae74793740 100644 --- a/drivers/staging/greybus/operation.c +++ b/drivers/staging/greybus/operation.c @@ -1090,6 +1090,53 @@ int gb_operation_sync_timeout(struct gb_connection *connection, int type, } EXPORT_SYMBOL_GPL(gb_operation_sync_timeout); +/** + * gb_operation_unidirectional_timeout() - initiate a unidirectional operation + * @connection: connection to use + * @type: type of operation to send + * @request: memory buffer to copy the request from + * @request_size: size of @request + * @timeout: send timeout in milliseconds + * + * Initiate a unidirectional operation by sending a request message and + * waiting for it to be acknowledged as sent by the host device. + * + * Note that successful send of a unidirectional operation does not imply that + * the request as actually reached the remote end of the connection. + */ +int gb_operation_unidirectional_timeout(struct gb_connection *connection, + int type, void *request, int request_size, + unsigned int timeout) +{ + struct gb_operation *operation; + int ret; + + if (request_size && !request) + return -EINVAL; + + operation = gb_operation_create_flags(connection, type, + request_size, 0, + GB_OPERATION_FLAG_UNIDIRECTIONAL, + GFP_KERNEL); + if (!operation) + return -ENOMEM; + + if (request_size) + memcpy(operation->request->payload, request, request_size); + + ret = gb_operation_request_send_sync_timeout(operation, timeout); + if (ret) { + dev_err(&connection->hd->dev, + "%s: unidirectional operation of type 0x%02x failed: %d\n", + connection->name, type, ret); + } + + gb_operation_put(operation); + + return ret; +} +EXPORT_SYMBOL_GPL(gb_operation_unidirectional_timeout); + int __init gb_operation_init(void) { gb_message_cache = kmem_cache_create("gb_message_cache", diff --git a/drivers/staging/greybus/operation.h b/drivers/staging/greybus/operation.h index c88efe11c22b..8ef8f514dafa 100644 --- a/drivers/staging/greybus/operation.h +++ b/drivers/staging/greybus/operation.h @@ -178,6 +178,9 @@ int gb_operation_sync_timeout(struct gb_connection *connection, int type, void *request, int request_size, void *response, int response_size, unsigned int timeout); +int gb_operation_unidirectional_timeout(struct gb_connection *connection, + int type, void *request, int request_size, + unsigned int timeout); static inline int gb_operation_sync(struct gb_connection *connection, int type, void *request, int request_size, @@ -188,6 +191,13 @@ static inline int gb_operation_sync(struct gb_connection *connection, int type, GB_OPERATION_TIMEOUT_DEFAULT); } +static inline int gb_operation_unidirectional(struct gb_connection *connection, + int type, void *request, int request_size) +{ + return gb_operation_unidirectional_timeout(connection, type, + request, request_size, GB_OPERATION_TIMEOUT_DEFAULT); +} + int gb_operation_init(void); void gb_operation_exit(void);