[virtio_magma] Add image APIs

Change-Id: I483ab834c260479b793dea3b9deb01561862ba61
diff --git a/drivers/virtio/virtio_magma.c b/drivers/virtio/virtio_magma.c
index 7a9cfa4..7f49cb9 100644
--- a/drivers/virtio/virtio_magma.c
+++ b/drivers/virtio/virtio_magma.c
@@ -1260,7 +1260,7 @@
 	}
 
 	if (response->buffer_size_out > request->buffer_size) {
-		pr_err("virtmagma: magma_read_notification_channel returned buffer_size_out (%lld) larger than buffer_size (%lld)",
+		pr_err("virtmagma: magma_read_notification_channel returned buffer_size_out (%lu) larger than buffer_size (%lld)",
 		       response->buffer_size_out, request->buffer_size);
 		return -EIO;
 	}
@@ -1308,7 +1308,7 @@
 	}
 
 	if (response->buffer_size_out > request->buffer_size) {
-		pr_err("virtmagma: magma_read_notification_channel2 returned buffer_size_out (%lld) larger than buffer_size (%lld)",
+		pr_err("virtmagma: magma_read_notification_channel2 returned buffer_size_out (%lu) larger than buffer_size (%lld)",
 		       response->buffer_size_out, request->buffer_size);
 		return -EIO;
 	}
@@ -1318,6 +1318,193 @@
 			    response->buffer_size_out);
 }
 
+static int get_buffer_size(struct virtmagma_instance *instance,
+			   uintptr_t buffer, uint64_t *size_out)
+{
+	struct virtio_magma_get_buffer_size_ctrl *request;
+	struct virtio_magma_get_buffer_size_resp *response;
+	int ret;
+
+	request = kmem_cache_alloc(instance->msg_cache, GFP_KERNEL);
+	if (!request)
+		return -ENOMEM;
+
+	response = kmem_cache_alloc(instance->msg_cache, GFP_KERNEL);
+	if (!response) {
+		kmem_cache_free(instance->msg_cache, request);
+		return -ENOMEM;
+	}
+
+	request->hdr.type = VIRTIO_MAGMA_CMD_GET_BUFFER_SIZE;
+	request->hdr.flags = 0;
+	request->buffer = buffer;
+
+	{
+		struct virtmagma_virtio_command command = {
+			.request_ptr = request,
+			.request_size = sizeof(*request),
+			.response_ptr = response,
+			.response_size = sizeof(*response)
+		};
+
+		ret = vq_out_send_sync(instance->vi, &command);
+	}
+
+	if (ret == 0) {
+		ret = virtmagma_check_expected_response_type(request, response);
+		if (ret == 0) {
+			*size_out = response->result_return;
+		}
+	}
+
+	kmem_cache_free(instance->msg_cache, request);
+	kmem_cache_free(instance->msg_cache, response);
+
+	return ret;
+}
+
+static int virtmagma_command_magma_virt_create_image(
+	struct virtmagma_instance *instance,
+	struct virtmagma_virtio_command *command)
+{
+	struct virtmagma_connection *connection;
+	struct virtio_magma_virt_create_image_ctrl *request =
+		command->request_ptr;
+	struct virtio_magma_virt_create_image_resp *response =
+		command->response_ptr;
+	struct virtmagma_create_image_wrapper wrapper;
+	uint64_t buffer_size;
+	char *ptr;
+	int ret;
+
+	if (!COMMAND_OK(command, request, response))
+		return -EINVAL;
+
+	connection = get_connection(instance, request->connection);
+	if (!connection)
+		return -EINVAL;
+
+	/* The wrapper struct includes pointers to the actual structs and their sizes. */
+	ret = copy_from_user(&wrapper, (void *)request->create_info,
+			     sizeof(wrapper));
+	if (ret)
+		return ret;
+
+	/* reallocate request buffer with enough space for the structures */
+	command->request_size = sizeof(*request) + wrapper.create_info_size;
+	/* memory will be freed by the caller */
+	ptr = kzalloc(command->request_size, GFP_KERNEL);
+	if (!ptr)
+		return -ENOMEM;
+
+	memcpy(ptr, request, sizeof(*request));
+	command->request_ptr = ptr;
+
+	/* ptr set to create_info */
+	ptr += sizeof(*request);
+	ret = copy_from_user(ptr, (void *)wrapper.create_info,
+			     wrapper.create_info_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;
+
+	/* pass on magma errors without creating buffer */
+	if (response->result_return) {
+		pr_warn("virtmagma: magma_virt_create_image returned %d",
+			(int32_t)response->result_return);
+		return 0; /* the ioctl is still successful */
+	}
+
+	ret = get_buffer_size(instance, response->image_out, &buffer_size);
+	if (ret)
+		return ret;
+
+	{
+		struct virtmagma_connection_object *object =
+			kzalloc(sizeof(*object), GFP_KERNEL);
+		if (!object)
+			return -ENOMEM;
+
+		object->parent_connection = connection;
+		object->host_value = response->image_out;
+		object->type = MAGMA_BUFFER;
+		object->buffer.size_requested = buffer_size;
+		object->buffer.size_allocated = buffer_size;
+
+		hash_add(connection->objects, &object->node,
+			 object->host_value);
+	}
+
+	return 0;
+}
+
+static int virtmagma_command_magma_virt_get_image_info(
+	struct virtmagma_instance *instance,
+	struct virtmagma_virtio_command *command)
+{
+	struct virtmagma_connection *connection;
+	struct virtio_magma_virt_get_image_info_ctrl *request =
+		command->request_ptr;
+	struct virtio_magma_virt_get_image_info_resp *response =
+		command->response_ptr;
+	struct virtmagma_get_image_info_wrapper wrapper;
+	char *ptr;
+	int ret;
+
+	if (!COMMAND_OK(command, request, response))
+		return -EINVAL;
+
+	connection = get_connection(instance, request->connection);
+	if (!connection)
+		return -EINVAL;
+
+	/* The wrapper struct includes pointers to the actual structs and their sizes. */
+	ret = copy_from_user(&wrapper, (void *)request->image_info_out,
+			     sizeof(wrapper));
+	if (ret)
+		return ret;
+
+	/* reallocate request buffer with enough space for the structures */
+	command->request_size = sizeof(*request) + wrapper.image_info_size;
+	/* memory will be freed by the caller */
+	ptr = kzalloc(command->request_size, GFP_KERNEL);
+	if (!ptr)
+		return -ENOMEM;
+
+	memcpy(ptr, request, sizeof(*request));
+	command->request_ptr = ptr;
+
+	ret = vq_out_send_sync(instance->vi, command);
+	if (ret)
+		return ret;
+
+	ret = virtmagma_check_expected_response_type(request, response);
+	if (ret)
+		return ret;
+
+	/* pass on magma errors without creating buffer */
+	if (response->result_return) {
+		pr_warn("virtmagma: magma_virt_get_image_info returned %d",
+			(int32_t)response->result_return);
+		return 0; /* the ioctl is still successful */
+	}
+
+	ptr += sizeof(*request);
+	ret = copy_to_user((void *)wrapper.image_info_out, ptr,
+			   wrapper.image_info_size);
+	if (ret)
+		return ret;
+
+	return 0;
+}
+
 #if IS_ENABLED(CONFIG_VIRTIO_WL)
 /* use the implementation in the virtio_wl module */
 extern int virtwl_create_fd_for_vfd(void *filp_private_data, uint32_t vfd_id);
@@ -1357,7 +1544,7 @@
 	ret = virtwl_create_fd_for_vfd(instance->wayland_device_private_data,
 				       response->buffer_handle_out);
 	if (ret < 0) {
-		pr_err("virtmagma: failed to get vfd creation info for vfd id %lld",
+		pr_err("virtmagma: failed to get vfd creation info for vfd id %lu",
 		       response->buffer_handle_out);
 		return ret;
 	}
@@ -1550,6 +1737,14 @@
 		ret = virtmagma_command_magma_get_buffer_handle(instance,
 								&command);
 		break;
+	case VIRTIO_MAGMA_CMD_VIRT_CREATE_IMAGE:
+		ret = virtmagma_command_magma_virt_create_image(instance,
+								&command);
+		break;
+	case VIRTIO_MAGMA_CMD_VIRT_GET_IMAGE_INFO:
+		ret = virtmagma_command_magma_virt_get_image_info(instance,
+								    &command);
+		break;
 	/* pass-through handlers */
 	case VIRTIO_MAGMA_CMD_QUERY2:
 	case VIRTIO_MAGMA_CMD_GET_ERROR:
diff --git a/include/uapi/linux/virtio_magma.h b/include/uapi/linux/virtio_magma.h
index 3430b83..93cb232 100644
--- a/include/uapi/linux/virtio_magma.h
+++ b/include/uapi/linux/virtio_magma.h
@@ -4,7 +4,7 @@
  */
 
 /* NOTE: DO NOT EDIT THIS FILE! It is generated automatically by:
-     //src/graphics/lib/magma/include/virtio/virtio_magma.h.gen.py
+     //src/graphics/lib/magma/include/virtio/virtio_magma_h_gen.py
  */
 
 #ifndef _LINUX_VIRTIO_MAGMA_H
@@ -71,6 +71,8 @@
 	VIRTIO_MAGMA_CMD_BUFFER_GET_INFO = 0x1042,
 	VIRTIO_MAGMA_CMD_GET_BUFFER_HANDLE = 0x1043,
 	VIRTIO_MAGMA_CMD_READ_NOTIFICATION_CHANNEL2 = 0x1046,
+	VIRTIO_MAGMA_CMD_VIRT_CREATE_IMAGE = 0x1047,
+	VIRTIO_MAGMA_CMD_VIRT_GET_IMAGE_INFO = 0x1048,
 	VIRTIO_MAGMA_CMD_INTERNAL_MAP = 0x1044,
 	VIRTIO_MAGMA_CMD_INTERNAL_UNMAP = 0x1045,
 	/* magma success responses
@@ -125,6 +127,8 @@
 	VIRTIO_MAGMA_RESP_BUFFER_GET_INFO = 0x2042,
 	VIRTIO_MAGMA_RESP_GET_BUFFER_HANDLE = 0x2043,
 	VIRTIO_MAGMA_RESP_READ_NOTIFICATION_CHANNEL2 = 0x2046,
+	VIRTIO_MAGMA_RESP_VIRT_CREATE_IMAGE = 0x2047,
+	VIRTIO_MAGMA_RESP_VIRT_GET_IMAGE_INFO = 0x2048,
 	VIRTIO_MAGMA_RESP_INTERNAL_MAP = 0x2044,
 	VIRTIO_MAGMA_RESP_INTERNAL_UNMAP = 0x2045,
 	/* magma error responses
@@ -239,6 +243,10 @@
 		case VIRTIO_MAGMA_RESP_GET_BUFFER_HANDLE: return "VIRTIO_MAGMA_RESP_GET_BUFFER_HANDLE";
 		case VIRTIO_MAGMA_CMD_READ_NOTIFICATION_CHANNEL2: return "VIRTIO_MAGMA_CMD_READ_NOTIFICATION_CHANNEL2";
 		case VIRTIO_MAGMA_RESP_READ_NOTIFICATION_CHANNEL2: return "VIRTIO_MAGMA_RESP_READ_NOTIFICATION_CHANNEL2";
+		case VIRTIO_MAGMA_CMD_VIRT_CREATE_IMAGE: return "VIRTIO_MAGMA_CMD_VIRT_CREATE_IMAGE";
+		case VIRTIO_MAGMA_RESP_VIRT_CREATE_IMAGE: return "VIRTIO_MAGMA_RESP_VIRT_CREATE_IMAGE";
+		case VIRTIO_MAGMA_CMD_VIRT_GET_IMAGE_INFO: return "VIRTIO_MAGMA_CMD_VIRT_GET_IMAGE_INFO";
+		case VIRTIO_MAGMA_RESP_VIRT_GET_IMAGE_INFO: return "VIRTIO_MAGMA_RESP_VIRT_GET_IMAGE_INFO";
 		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";
@@ -305,6 +313,8 @@
 		case VIRTIO_MAGMA_CMD_BUFFER_GET_INFO: return VIRTIO_MAGMA_RESP_BUFFER_GET_INFO;
 		case VIRTIO_MAGMA_CMD_GET_BUFFER_HANDLE: return VIRTIO_MAGMA_RESP_GET_BUFFER_HANDLE;
 		case VIRTIO_MAGMA_CMD_READ_NOTIFICATION_CHANNEL2: return VIRTIO_MAGMA_RESP_READ_NOTIFICATION_CHANNEL2;
+		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_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;
@@ -342,7 +352,7 @@
 
 struct virtio_magma_create_context_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 context_id_out;
+	uintptr_t context_id_out;
 } __attribute((packed));
 
 struct virtio_magma_release_context_ctrl {
@@ -363,8 +373,8 @@
 
 struct virtio_magma_create_buffer_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 size_out;
-	__le64 buffer_out;
+	uintptr_t size_out;
+	uintptr_t buffer_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -439,7 +449,7 @@
 
 struct virtio_magma_get_buffer_cache_policy_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 cache_policy_out;
+	uintptr_t cache_policy_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -489,7 +499,7 @@
 
 struct virtio_magma_export_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 buffer_handle_out;
+	uintptr_t buffer_handle_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -501,7 +511,7 @@
 
 struct virtio_magma_import_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 buffer_out;
+	uintptr_t buffer_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -509,9 +519,9 @@
 	struct virtio_magma_ctrl_hdr hdr;
 	__le64 connection;
 	__le32 context_id;
-	__le64 command_buffer;
-	__le64 resources;
-	__le64 semaphore_ids;
+	uintptr_t command_buffer;
+	uintptr_t resources;
+	uintptr_t semaphore_ids;
 } __attribute((packed));
 
 struct virtio_magma_execute_command_buffer_with_resources_resp {
@@ -523,7 +533,7 @@
 	__le64 connection;
 	__le32 context_id;
 	__le64 command_count;
-	__le64 command_buffers;
+	uintptr_t command_buffers;
 } __attribute((packed));
 
 struct virtio_magma_execute_immediate_commands2_resp {
@@ -537,7 +547,7 @@
 
 struct virtio_magma_create_semaphore_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 semaphore_out;
+	uintptr_t semaphore_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -587,7 +597,7 @@
 
 struct virtio_magma_export_semaphore_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 semaphore_handle_out;
+	uintptr_t semaphore_handle_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -599,7 +609,7 @@
 
 struct virtio_magma_import_semaphore_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 semaphore_out;
+	uintptr_t semaphore_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -616,13 +626,13 @@
 struct virtio_magma_read_notification_channel_ctrl {
 	struct virtio_magma_ctrl_hdr hdr;
 	__le64 connection;
-	__le64 buffer;
+	uintptr_t buffer;
 	__le64 buffer_size;
 } __attribute((packed));
 
 struct virtio_magma_read_notification_channel_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 buffer_size_out;
+	uintptr_t buffer_size_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -643,7 +653,7 @@
 
 struct virtio_magma_device_import_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 device_out;
+	uintptr_t device_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -664,7 +674,7 @@
 
 struct virtio_magma_query2_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 value_out;
+	uintptr_t value_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -676,7 +686,7 @@
 
 struct virtio_magma_query_returns_buffer2_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 handle_out;
+	uintptr_t handle_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -687,7 +697,7 @@
 
 struct virtio_magma_create_connection2_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 connection_out;
+	uintptr_t connection_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -703,7 +713,7 @@
 
 struct virtio_magma_poll_ctrl {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 items;
+	uintptr_t items;
 	__le32 count;
 	__le64 timeout_ns;
 } __attribute((packed));
@@ -727,7 +737,7 @@
 struct virtio_magma_connection_enable_performance_counters_ctrl {
 	struct virtio_magma_ctrl_hdr hdr;
 	__le64 connection;
-	__le64 counters;
+	uintptr_t counters;
 	__le64 counters_count;
 } __attribute((packed));
 
@@ -743,8 +753,8 @@
 
 struct virtio_magma_connection_create_performance_counter_buffer_pool_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 pool_out;
-	__le64 notification_handle_out;
+	uintptr_t pool_out;
+	uintptr_t notification_handle_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -763,7 +773,7 @@
 	struct virtio_magma_ctrl_hdr hdr;
 	__le64 connection;
 	__le64 pool;
-	__le64 offsets;
+	uintptr_t offsets;
 	__le64 offsets_count;
 } __attribute((packed));
 
@@ -799,7 +809,7 @@
 struct virtio_magma_connection_clear_performance_counters_ctrl {
 	struct virtio_magma_ctrl_hdr hdr;
 	__le64 connection;
-	__le64 counters;
+	uintptr_t counters;
 	__le64 counters_count;
 } __attribute((packed));
 
@@ -816,11 +826,11 @@
 
 struct virtio_magma_connection_read_performance_counter_completion_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 trigger_id_out;
-	__le64 buffer_id_out;
-	__le64 buffer_offset_out;
-	__le64 time_out;
-	__le64 result_flags_out;
+	uintptr_t trigger_id_out;
+	uintptr_t buffer_id_out;
+	uintptr_t buffer_offset_out;
+	uintptr_t time_out;
+	uintptr_t result_flags_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -828,7 +838,7 @@
 	struct virtio_magma_ctrl_hdr hdr;
 	__le64 connection;
 	__le64 buffer;
-	__le64 name;
+	uintptr_t name;
 } __attribute((packed));
 
 struct virtio_magma_buffer_set_name_resp {
@@ -858,7 +868,7 @@
 
 struct virtio_magma_buffer_get_info_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 info_out;
+	uintptr_t info_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -870,21 +880,45 @@
 
 struct virtio_magma_get_buffer_handle_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 handle_out;
+	uintptr_t handle_out;
 	__le64 result_return;
 } __attribute((packed));
 
 struct virtio_magma_read_notification_channel2_ctrl {
 	struct virtio_magma_ctrl_hdr hdr;
 	__le64 connection;
-	__le64 buffer;
+	uintptr_t buffer;
 	__le64 buffer_size;
 } __attribute((packed));
 
 struct virtio_magma_read_notification_channel2_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 buffer_size_out;
-	__le64 more_data_out;
+	uintptr_t buffer_size_out;
+	uintptr_t more_data_out;
+	__le64 result_return;
+} __attribute((packed));
+
+struct virtio_magma_virt_create_image_ctrl {
+	struct virtio_magma_ctrl_hdr hdr;
+	__le64 connection;
+	uintptr_t create_info;
+} __attribute((packed));
+
+struct virtio_magma_virt_create_image_resp {
+	struct virtio_magma_ctrl_hdr hdr;
+	uintptr_t image_out;
+	__le64 result_return;
+} __attribute((packed));
+
+struct virtio_magma_virt_get_image_info_ctrl {
+	struct virtio_magma_ctrl_hdr hdr;
+	__le64 connection;
+	__le64 image;
+	uintptr_t image_info_out;
+} __attribute((packed));
+
+struct virtio_magma_virt_get_image_info_resp {
+	struct virtio_magma_ctrl_hdr hdr;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -897,7 +931,7 @@
 
 struct virtio_magma_internal_map_resp {
 	struct virtio_magma_ctrl_hdr hdr;
-	__le64 address_out;
+	uintptr_t address_out;
 	__le64 result_return;
 } __attribute((packed));
 
@@ -905,7 +939,7 @@
 	struct virtio_magma_ctrl_hdr hdr;
 	__le64 connection;
 	__le64 buffer;
-	__le64 address;
+	uintptr_t address;
 } __attribute((packed));
 
 struct virtio_magma_internal_unmap_resp {
diff --git a/include/uapi/linux/virtmagma.h b/include/uapi/linux/virtmagma.h
index 55b7436..9f29724 100644
--- a/include/uapi/linux/virtmagma.h
+++ b/include/uapi/linux/virtmagma.h
@@ -8,21 +8,20 @@
 #include <asm/ioctl.h>
 #include <linux/types.h>
 
-#define VIRTMAGMA_IOCTL_BASE	 'm'
-#define VIRTMAGMA_IO(nr)	 _IO(VIRTMAGMA_IOCTL_BASE, nr)
-#define VIRTMAGMA_IOR(nr, type)	 _IOR(VIRTMAGMA_IOCTL_BASE, nr, type)
-#define VIRTMAGMA_IOW(nr, type)	 _IOW(VIRTMAGMA_IOCTL_BASE, nr, type)
+#define VIRTMAGMA_IOCTL_BASE 'm'
+#define VIRTMAGMA_IO(nr) _IO(VIRTMAGMA_IOCTL_BASE, nr)
+#define VIRTMAGMA_IOR(nr, type) _IOR(VIRTMAGMA_IOCTL_BASE, nr, type)
+#define VIRTMAGMA_IOW(nr, type) _IOW(VIRTMAGMA_IOCTL_BASE, nr, type)
 #define VIRTMAGMA_IOWR(nr, type) _IOWR(VIRTMAGMA_IOCTL_BASE, nr, type)
-#define VIRTMAGMA_MAKE_VERSION(major, minor, patch) \
+#define VIRTMAGMA_MAKE_VERSION(major, minor, patch)                            \
 	(((major) << 24) | ((minor) << 12) | (patch))
-#define VIRTMAGMA_GET_VERSION(version, major, minor, patch) (\
-	(major = ((version) >> 24)), \
-	(minor = ((version) >> 12) & 0x3FF), \
-	(patch = (version) & 0x3FF), (version))
+#define VIRTMAGMA_GET_VERSION(version, major, minor, patch)                    \
+	((major = ((version) >> 24)), (minor = ((version) >> 12) & 0x3FF),     \
+	 (patch = (version)&0x3FF), (version))
 
 #define VIRTMAGMA_HANDSHAKE_SEND 0x46434853
 #define VIRTMAGMA_HANDSHAKE_RECV 0x474F4F47
-#define VIRTMAGMA_VERSION VIRTMAGMA_MAKE_VERSION(0,1,0)
+#define VIRTMAGMA_VERSION VIRTMAGMA_MAKE_VERSION(0, 1, 0)
 struct virtmagma_ioctl_args_handshake {
 	__u32 handshake_inout;
 	__u32 version_out;
@@ -44,7 +43,20 @@
 	__u64 semaphores;
 };
 
-#define VIRTMAGMA_IOCTL_HANDSHAKE VIRTMAGMA_IOWR(0x00, struct virtmagma_ioctl_args_handshake)
-#define VIRTMAGMA_IOCTL_MAGMA_COMMAND VIRTMAGMA_IOWR(0x02, struct virtmagma_ioctl_args_magma_command)
+struct virtmagma_create_image_wrapper {
+	uintptr_t create_info;
+	__u64 create_info_size;
+};
+
+struct virtmagma_get_image_info_wrapper {
+	uintptr_t image_info_out;
+	__u64 image_info_size;
+};
+
+#define VIRTMAGMA_IOCTL_HANDSHAKE                                              \
+	VIRTMAGMA_IOWR(0x00, struct virtmagma_ioctl_args_handshake)
+// Removed: VIRTMAGMA_IOCTL_GET_MMFD (0x01)
+#define VIRTMAGMA_IOCTL_MAGMA_COMMAND                                          \
+	VIRTMAGMA_IOWR(0x02, struct virtmagma_ioctl_args_magma_command)
 
 #endif /* _LINUX_VIRTMAGMA_H */