greybus: operation: add incoming-operation flag
Add flag field to struct gb_operation, and a first flag GB_OPERATION_FLAG_INCOMING to identify incoming operations. Pass an initial set of flags when allocating new operations, and use these to identify incoming operations rather than overloading the meaning of GB_OPERATION_TYPE_INVALID. This also allows us to set the type for all operations during allocation. Also add convenience helper to identify incoming operations. Signed-off-by: Johan Hovold <johan@hovoldconsulting.com> Signed-off-by: Greg Kroah-Hartman <gregkh@google.com>hifive-unleashed-5.1
parent
73f9d73f12
commit
710067e2ef
|
@ -413,7 +413,7 @@ EXPORT_SYMBOL_GPL(gb_operation_response_alloc);
|
||||||
static struct gb_operation *
|
static struct gb_operation *
|
||||||
gb_operation_create_common(struct gb_connection *connection, u8 type,
|
gb_operation_create_common(struct gb_connection *connection, u8 type,
|
||||||
size_t request_size, size_t response_size,
|
size_t request_size, size_t response_size,
|
||||||
gfp_t gfp_flags)
|
unsigned long op_flags, gfp_t gfp_flags)
|
||||||
{
|
{
|
||||||
struct greybus_host_device *hd = connection->hd;
|
struct greybus_host_device *hd = connection->hd;
|
||||||
struct gb_operation *operation;
|
struct gb_operation *operation;
|
||||||
|
@ -431,11 +431,13 @@ gb_operation_create_common(struct gb_connection *connection, u8 type,
|
||||||
operation->request->operation = operation;
|
operation->request->operation = operation;
|
||||||
|
|
||||||
/* Allocate the response buffer for outgoing operations */
|
/* Allocate the response buffer for outgoing operations */
|
||||||
if (type != GB_OPERATION_TYPE_INVALID) {
|
if (!(op_flags & GB_OPERATION_FLAG_INCOMING)) {
|
||||||
if (!gb_operation_response_alloc(operation, response_size))
|
if (!gb_operation_response_alloc(operation, response_size))
|
||||||
goto err_request;
|
goto err_request;
|
||||||
operation->type = type;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
operation->flags = op_flags;
|
||||||
|
operation->type = type;
|
||||||
operation->errno = -EBADR; /* Initial value--means "never set" */
|
operation->errno = -EBADR; /* Initial value--means "never set" */
|
||||||
|
|
||||||
INIT_WORK(&operation->work, gb_operation_work);
|
INIT_WORK(&operation->work, gb_operation_work);
|
||||||
|
@ -475,7 +477,7 @@ struct gb_operation *gb_operation_create(struct gb_connection *connection,
|
||||||
type &= ~GB_MESSAGE_TYPE_RESPONSE;
|
type &= ~GB_MESSAGE_TYPE_RESPONSE;
|
||||||
|
|
||||||
return gb_operation_create_common(connection, type,
|
return gb_operation_create_common(connection, type,
|
||||||
request_size, response_size, gfp);
|
request_size, response_size, 0, gfp);
|
||||||
}
|
}
|
||||||
EXPORT_SYMBOL_GPL(gb_operation_create);
|
EXPORT_SYMBOL_GPL(gb_operation_create);
|
||||||
|
|
||||||
|
@ -493,16 +495,15 @@ gb_operation_create_incoming(struct gb_connection *connection, u16 id,
|
||||||
{
|
{
|
||||||
struct gb_operation *operation;
|
struct gb_operation *operation;
|
||||||
size_t request_size;
|
size_t request_size;
|
||||||
|
unsigned long flags = GB_OPERATION_FLAG_INCOMING;
|
||||||
|
|
||||||
/* Caller has made sure we at least have a message header. */
|
/* Caller has made sure we at least have a message header. */
|
||||||
request_size = size - sizeof(struct gb_operation_msg_hdr);
|
request_size = size - sizeof(struct gb_operation_msg_hdr);
|
||||||
|
|
||||||
operation = gb_operation_create_common(connection,
|
operation = gb_operation_create_common(connection, type,
|
||||||
GB_OPERATION_TYPE_INVALID,
|
request_size, 0, flags, GFP_ATOMIC);
|
||||||
request_size, 0, GFP_ATOMIC);
|
|
||||||
if (operation) {
|
if (operation) {
|
||||||
operation->id = id;
|
operation->id = id;
|
||||||
operation->type = type;
|
|
||||||
memcpy(operation->request->header, data, size);
|
memcpy(operation->request->header, data, size);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -89,6 +89,8 @@ struct gb_message {
|
||||||
void *hcpriv;
|
void *hcpriv;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#define GB_OPERATION_FLAG_INCOMING BIT(0)
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* A Greybus operation is a remote procedure call performed over a
|
* A Greybus operation is a remote procedure call performed over a
|
||||||
* connection between two UniPro interfaces.
|
* connection between two UniPro interfaces.
|
||||||
|
@ -113,8 +115,9 @@ struct gb_operation {
|
||||||
struct gb_connection *connection;
|
struct gb_connection *connection;
|
||||||
struct gb_message *request;
|
struct gb_message *request;
|
||||||
struct gb_message *response;
|
struct gb_message *response;
|
||||||
u8 type;
|
|
||||||
|
|
||||||
|
unsigned long flags;
|
||||||
|
u8 type;
|
||||||
u16 id;
|
u16 id;
|
||||||
int errno; /* Operation result */
|
int errno; /* Operation result */
|
||||||
|
|
||||||
|
@ -126,6 +129,12 @@ struct gb_operation {
|
||||||
struct list_head links; /* connection->operations */
|
struct list_head links; /* connection->operations */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static inline bool
|
||||||
|
gb_operation_is_incoming(struct gb_operation *operation)
|
||||||
|
{
|
||||||
|
return operation->flags & GB_OPERATION_FLAG_INCOMING;
|
||||||
|
}
|
||||||
|
|
||||||
void gb_connection_recv(struct gb_connection *connection,
|
void gb_connection_recv(struct gb_connection *connection,
|
||||||
void *data, size_t size);
|
void *data, size_t size);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue