Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 2db84eff authored by K. Y. Srinivasan's avatar K. Y. Srinivasan Committed by Greg Kroah-Hartman
Browse files

Drivers: hv: vmbus: Implement the protocol for tearing down vmbus state



Implement the protocol for tearing down the monitor state established with
the host.

Signed-off-by: default avatarK. Y. Srinivasan <kys@microsoft.com>
Tested-by: default avatarVitaly Kuznetsov <vkuznets@redhat.com>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
parent db9ba208
Loading
Loading
Loading
Loading
+25 −0
Original line number Diff line number Diff line
@@ -421,6 +421,30 @@ static void init_vp_index(struct vmbus_channel *channel, const uuid_le *type_gui
	channel->target_vp = hv_context.vp_index[cur_cpu];
}

/*
 * vmbus_unload_response - Handler for the unload response.
 */
static void vmbus_unload_response(struct vmbus_channel_message_header *hdr)
{
	/*
	 * This is a global event; just wakeup the waiting thread.
	 * Once we successfully unload, we can cleanup the monitor state.
	 */
	complete(&vmbus_connection.unload_event);
}

void vmbus_initiate_unload(void)
{
	struct vmbus_channel_message_header hdr;

	init_completion(&vmbus_connection.unload_event);
	memset(&hdr, 0, sizeof(struct vmbus_channel_message_header));
	hdr.msgtype = CHANNELMSG_UNLOAD;
	vmbus_post_msg(&hdr, sizeof(struct vmbus_channel_message_header));

	wait_for_completion(&vmbus_connection.unload_event);
}

/*
 * vmbus_onoffer - Handler for channel offers from vmbus in parent partition.
 *
@@ -717,6 +741,7 @@ struct vmbus_channel_message_table_entry
	{CHANNELMSG_INITIATE_CONTACT,		0, NULL},
	{CHANNELMSG_VERSION_RESPONSE,		1, vmbus_onversion_response},
	{CHANNELMSG_UNLOAD,			0, NULL},
	{CHANNELMSG_UNLOAD_RESPONSE,		1, vmbus_unload_response},
};

/*
+5 −0
Original line number Diff line number Diff line
@@ -227,6 +227,11 @@ int vmbus_connect(void)

void vmbus_disconnect(void)
{
	/*
	 * First send the unload request to the host.
	 */
	vmbus_initiate_unload();

	if (vmbus_connection.work_queue) {
		drain_workqueue(vmbus_connection.work_queue);
		destroy_workqueue(vmbus_connection.work_queue);
+2 −0
Original line number Diff line number Diff line
@@ -647,6 +647,7 @@ struct vmbus_connection {

	atomic_t next_gpadl_handle;

	struct completion  unload_event;
	/*
	 * Represents channel interrupts. Each bit position represents a
	 * channel.  When a channel sends an interrupt via VMBUS, it finds its
@@ -741,6 +742,7 @@ void hv_vss_onchannelcallback(void *);
int hv_fcopy_init(struct hv_util_service *);
void hv_fcopy_deinit(void);
void hv_fcopy_onchannelcallback(void *);
void vmbus_initiate_unload(void);

static inline void hv_poll_channel(struct vmbus_channel *channel,
				   void (*cb)(void *))
+1 −1
Original line number Diff line number Diff line
@@ -1106,6 +1106,7 @@ static void __exit vmbus_exit(void)

	vmbus_connection.conn_state = DISCONNECTED;
	hv_synic_clockevents_cleanup();
	vmbus_disconnect();
	hv_remove_vmbus_irq();
	vmbus_free_channels();
	if (ms_hyperv.features & HV_FEATURE_GUEST_CRASH_MSR_AVAILABLE) {
@@ -1118,7 +1119,6 @@ static void __exit vmbus_exit(void)
		smp_call_function_single(cpu, hv_synic_cleanup, NULL, 1);
	acpi_bus_unregister_driver(&vmbus_acpi_driver);
	hv_cpu_hotplug_quirk(false);
	vmbus_disconnect();
}


+1 −0
Original line number Diff line number Diff line
@@ -389,6 +389,7 @@ enum vmbus_channel_message_type {
	CHANNELMSG_INITIATE_CONTACT		= 14,
	CHANNELMSG_VERSION_RESPONSE		= 15,
	CHANNELMSG_UNLOAD			= 16,
	CHANNELMSG_UNLOAD_RESPONSE		= 17,
	CHANNELMSG_COUNT
};