--- /dev/null
+diff --git a/drivers/xen/v2v/v2v.c b/drivers/xen/v2v/v2v.c
+index 1bcab10..c79a2ed 100644
+--- a/drivers/xen/v2v/v2v.c
++++ b/drivers/xen/v2v/v2v.c
+@@ -1253,7 +1253,26 @@ v2v_disconnect_supplicant(const struct v2v_channel *_channel)
+ int err;
+ struct v2v_channel *channel = (struct v2v_channel *)_channel;
+
+- /* The grant mapping and vm areas are cleaned up in v2v_destroy_channel() */
++ /* Have to clean up the grant mapping and vm areas here before setting the state to disconnected
++ or the temple disconnect could fail. */
++ v2v_xenops_grant_unmap(channel->u.supplicant.prod_area,
++ channel->u.supplicant.prod_shmem_handles,
++ channel->nr_cons_ring_pages,
++ 1);
++ channel->u.supplicant.prod_area = NULL;
++
++ v2v_xenops_grant_unmap(channel->u.supplicant.cons_area,
++ channel->u.supplicant.cons_shmem_handles,
++ channel->nr_prod_ring_pages,
++ 0);
++ channel->u.supplicant.cons_area = NULL;
++
++ v2v_xenops_grant_unmap(channel->u.supplicant.control_area,
++ &channel->u.supplicant.control_shmem_handle,
++ 1,
++ 0);
++ channel->u.supplicant.control_area = NULL;
++
+ channel->prod_sring = NULL;
+ channel->cons_sring = NULL;
+ channel->control = NULL;
+@@ -1261,6 +1280,7 @@ v2v_disconnect_supplicant(const struct v2v_channel *_channel)
+ v2v_close_receive_evtchn(channel);
+ v2v_close_send_evtchn(channel);
+
++ /* Now go to the disconnected state and clean everything up. */
+ err = v2v_change_local_state(channel, XBT_NIL, v2v_state_disconnected);
+ if (err) {
+ EPRINTK("v2v_disconnect_supplicant - v2v_change_local_state(disconnected) failed - err: %d\n", err);