Support magma_execute_command_buffer_with_resources2
Change-Id: I76a35ffb577e62e0eb8b2bb911944aaa31c177eb
diff --git a/drivers/virtio/virtio_magma.c b/drivers/virtio/virtio_magma.c
index 49f5b3f..31c7c370 100644
--- a/drivers/virtio/virtio_magma.c
+++ b/drivers/virtio/virtio_magma.c
@@ -1015,6 +1015,81 @@
return 0;
}
+static int virtmagma_command_magma_execute_command_buffer_with_resources2(
+ struct virtmagma_instance *instance,
+ struct virtmagma_virtio_command *command)
+{
+ struct virtio_magma_execute_command_buffer_with_resources2_ctrl *request =
+ command->request_ptr;
+ struct virtio_magma_execute_command_buffer_with_resources2_resp
+ *response = command->response_ptr;
+ struct virtmagma_connection *connection;
+ struct virtmagma_command_buffer virt_command_buffer;
+ char *dst_ptr;
+ int ret;
+
+ if (!COMMAND_OK(command, request, response))
+ return -EINVAL;
+
+ connection = get_connection(instance, request->connection);
+ if (!connection)
+ return -EINVAL;
+
+ if (!get_connection_object(connection, request->context_id,
+ MAGMA_CONTEXT))
+ return -EINVAL;
+
+ /* The virtmagma_comand_buffer includes the resources and semaphore data
+ and their lengths, so we ignore the corresponding members of the request. */
+ ret = copy_from_user(&virt_command_buffer,
+ (void *)request->command_buffer,
+ sizeof(virt_command_buffer));
+ if (ret)
+ return ret;
+
+ /* reallocate request buffer with enough space for the structures */
+ command->request_size = sizeof(*request) +
+ virt_command_buffer.command_buffer_size +
+ virt_command_buffer.resource_size +
+ virt_command_buffer.semaphore_size;
+ /* memory will be freed by the caller */
+ dst_ptr = kzalloc(command->request_size, GFP_KERNEL);
+ if (!dst_ptr)
+ return -ENOMEM;
+
+ memcpy(dst_ptr, request, sizeof(*request));
+ command->request_ptr = dst_ptr;
+
+ dst_ptr += sizeof(*request);
+ ret = copy_from_user(dst_ptr,
+ (void *)virt_command_buffer.command_buffer,
+ virt_command_buffer.command_buffer_size);
+ if (ret)
+ return ret;
+
+ dst_ptr += virt_command_buffer.command_buffer_size;
+ ret = copy_from_user(dst_ptr, (void *)virt_command_buffer.resources,
+ virt_command_buffer.resource_size);
+ if (ret)
+ return ret;
+
+ dst_ptr += virt_command_buffer.resource_size;
+ ret = copy_from_user(dst_ptr, (void *)virt_command_buffer.semaphores,
+ virt_command_buffer.semaphore_size);
+ if (ret)
+ return ret;
+
+ ret = vq_out_send_sync(instance->vi, command);
+ if (ret)
+ return ret;
+
+ ret = virtmagma_check_expected_response_type(request, response);
+ if (ret)
+ return ret;
+
+ return 0;
+}
+
static int virtmagma_command_magma_create_semaphore(
struct virtmagma_instance *instance,
struct virtmagma_virtio_command *command)
@@ -1727,6 +1802,10 @@
ret = virtmagma_command_magma_execute_command_buffer_with_resources(
instance, &command);
break;
+ case VIRTIO_MAGMA_CMD_EXECUTE_COMMAND_BUFFER_WITH_RESOURCES2:
+ ret = virtmagma_command_magma_execute_command_buffer_with_resources2(
+ instance, &command);
+ break;
case VIRTIO_MAGMA_CMD_CREATE_SEMAPHORE:
ret = virtmagma_command_magma_create_semaphore(instance,
&command);
diff --git a/include/uapi/linux/virtio_magma.h b/include/uapi/linux/virtio_magma.h
index 7925f9d..4c93d2e 100644
--- a/include/uapi/linux/virtio_magma.h
+++ b/include/uapi/linux/virtio_magma.h
@@ -72,6 +72,7 @@
VIRTIO_MAGMA_CMD_VIRT_CREATE_IMAGE = 0x1047,
VIRTIO_MAGMA_CMD_VIRT_GET_IMAGE_INFO = 0x1048,
VIRTIO_MAGMA_CMD_SYNC = 0x1049,
+ VIRTIO_MAGMA_CMD_EXECUTE_COMMAND_BUFFER_WITH_RESOURCES2 = 0x104A,
VIRTIO_MAGMA_CMD_INTERNAL_MAP = 0x1044,
VIRTIO_MAGMA_CMD_INTERNAL_UNMAP = 0x1045,
/* magma success responses
@@ -127,6 +128,7 @@
VIRTIO_MAGMA_RESP_VIRT_CREATE_IMAGE = 0x2047,
VIRTIO_MAGMA_RESP_VIRT_GET_IMAGE_INFO = 0x2048,
VIRTIO_MAGMA_RESP_SYNC = 0x2049,
+ VIRTIO_MAGMA_RESP_EXECUTE_COMMAND_BUFFER_WITH_RESOURCES2 = 0x204A,
VIRTIO_MAGMA_RESP_INTERNAL_MAP = 0x2044,
VIRTIO_MAGMA_RESP_INTERNAL_UNMAP = 0x2045,
/* magma error responses
@@ -243,6 +245,8 @@
case VIRTIO_MAGMA_RESP_VIRT_GET_IMAGE_INFO: return "VIRTIO_MAGMA_RESP_VIRT_GET_IMAGE_INFO";
case VIRTIO_MAGMA_CMD_SYNC: return "VIRTIO_MAGMA_CMD_SYNC";
case VIRTIO_MAGMA_RESP_SYNC: return "VIRTIO_MAGMA_RESP_SYNC";
+ case VIRTIO_MAGMA_CMD_EXECUTE_COMMAND_BUFFER_WITH_RESOURCES2: return "VIRTIO_MAGMA_CMD_EXECUTE_COMMAND_BUFFER_WITH_RESOURCES2";
+ case VIRTIO_MAGMA_RESP_EXECUTE_COMMAND_BUFFER_WITH_RESOURCES2: return "VIRTIO_MAGMA_RESP_EXECUTE_COMMAND_BUFFER_WITH_RESOURCES2";
case VIRTIO_MAGMA_CMD_INTERNAL_MAP: return "VIRTIO_MAGMA_CMD_INTERNAL_MAP";
case VIRTIO_MAGMA_RESP_INTERNAL_MAP: return "VIRTIO_MAGMA_RESP_INTERNAL_MAP";
case VIRTIO_MAGMA_CMD_INTERNAL_UNMAP: return "VIRTIO_MAGMA_CMD_INTERNAL_UNMAP";
@@ -310,6 +314,7 @@
case VIRTIO_MAGMA_CMD_VIRT_CREATE_IMAGE: return VIRTIO_MAGMA_RESP_VIRT_CREATE_IMAGE;
case VIRTIO_MAGMA_CMD_VIRT_GET_IMAGE_INFO: return VIRTIO_MAGMA_RESP_VIRT_GET_IMAGE_INFO;
case VIRTIO_MAGMA_CMD_SYNC: return VIRTIO_MAGMA_RESP_SYNC;
+ case VIRTIO_MAGMA_CMD_EXECUTE_COMMAND_BUFFER_WITH_RESOURCES2: return VIRTIO_MAGMA_RESP_EXECUTE_COMMAND_BUFFER_WITH_RESOURCES2;
case VIRTIO_MAGMA_CMD_INTERNAL_MAP: return VIRTIO_MAGMA_RESP_INTERNAL_MAP;
case VIRTIO_MAGMA_CMD_INTERNAL_UNMAP: return VIRTIO_MAGMA_RESP_INTERNAL_UNMAP;
default: return VIRTIO_MAGMA_RESP_ERR_INVALID_COMMAND;
@@ -348,6 +353,7 @@
struct virtio_magma_create_context_resp {
struct virtio_magma_ctrl_hdr hdr;
uintptr_t context_id_out;
+ __le64 result_return;
} __attribute((packed));
struct virtio_magma_release_context_ctrl {
@@ -450,6 +456,7 @@
struct virtio_magma_map_buffer_gpu_resp {
struct virtio_magma_ctrl_hdr hdr;
+ __le64 result_return;
} __attribute((packed));
struct virtio_magma_unmap_buffer_gpu_ctrl {
@@ -511,6 +518,7 @@
struct virtio_magma_execute_command_buffer_with_resources_resp {
struct virtio_magma_ctrl_hdr hdr;
+ __le64 result_return;
} __attribute((packed));
struct virtio_magma_execute_immediate_commands2_ctrl {
@@ -523,6 +531,7 @@
struct virtio_magma_execute_immediate_commands2_resp {
struct virtio_magma_ctrl_hdr hdr;
+ __le64 result_return;
} __attribute((packed));
struct virtio_magma_create_semaphore_ctrl {
@@ -904,6 +913,20 @@
__le64 result_return;
} __attribute((packed));
+struct virtio_magma_execute_command_buffer_with_resources2_ctrl {
+ struct virtio_magma_ctrl_hdr hdr;
+ __le64 connection;
+ __le32 context_id;
+ uintptr_t command_buffer;
+ uintptr_t resources;
+ uintptr_t semaphore_ids;
+} __attribute((packed));
+
+struct virtio_magma_execute_command_buffer_with_resources2_resp {
+ struct virtio_magma_ctrl_hdr hdr;
+ __le64 result_return;
+} __attribute((packed));
+
struct virtio_magma_internal_map_ctrl {
struct virtio_magma_ctrl_hdr hdr;
__le64 connection;