mirror of
https://github.com/opnsense/src.git
synced 2026-05-28 04:12:45 -04:00
hyperv/vmbus: Fix the primary channel revoking on vmbus side.
Drivers can now use vmbus_chan_{is_revoked,set_orphan,unset_orphan}() and
vmbus_xact_ctx_orphan() to fix their attach/detach DEVMETHODs for revoked
primary channels.
MFC after: 1 week
Sponsored by: Microsoft
Differential Revision: https://reviews.freebsd.org/D8545
This commit is contained in:
parent
494ec41ae2
commit
5ab84aaf2f
3 changed files with 44 additions and 1 deletions
|
|
@ -116,6 +116,7 @@ struct vmbus_chan_br {
|
|||
};
|
||||
|
||||
struct vmbus_channel;
|
||||
struct vmbus_xact_ctx;
|
||||
struct hyperv_guid;
|
||||
struct task;
|
||||
struct taskqueue;
|
||||
|
|
@ -138,6 +139,9 @@ void vmbus_chan_close(struct vmbus_channel *chan);
|
|||
void vmbus_chan_intr_drain(struct vmbus_channel *chan);
|
||||
void vmbus_chan_run_task(struct vmbus_channel *chan,
|
||||
struct task *task);
|
||||
void vmbus_chan_set_orphan(struct vmbus_channel *chan,
|
||||
struct vmbus_xact_ctx *);
|
||||
void vmbus_chan_unset_orphan(struct vmbus_channel *chan);
|
||||
|
||||
int vmbus_chan_gpadl_connect(struct vmbus_channel *chan,
|
||||
bus_addr_t paddr, int size, uint32_t *gpadl);
|
||||
|
|
|
|||
|
|
@ -43,6 +43,7 @@ __FBSDID("$FreeBSD$");
|
|||
#include <machine/stdarg.h>
|
||||
|
||||
#include <dev/hyperv/include/hyperv_busdma.h>
|
||||
#include <dev/hyperv/include/vmbus_xact.h>
|
||||
#include <dev/hyperv/vmbus/hyperv_var.h>
|
||||
#include <dev/hyperv/vmbus/vmbus_reg.h>
|
||||
#include <dev/hyperv/vmbus/vmbus_var.h>
|
||||
|
|
@ -1115,6 +1116,7 @@ vmbus_chan_alloc(struct vmbus_softc *sc)
|
|||
|
||||
chan->ch_vmbus = sc;
|
||||
mtx_init(&chan->ch_subchan_lock, "vmbus subchan", NULL, MTX_DEF);
|
||||
sx_init(&chan->ch_orphan_lock, "vmbus chorphan");
|
||||
TAILQ_INIT(&chan->ch_subchans);
|
||||
vmbus_rxbr_init(&chan->ch_rxbr);
|
||||
vmbus_txbr_init(&chan->ch_txbr);
|
||||
|
|
@ -1133,8 +1135,12 @@ vmbus_chan_free(struct vmbus_channel *chan)
|
|||
VMBUS_CHAN_ST_ONPRIL |
|
||||
VMBUS_CHAN_ST_ONSUBL |
|
||||
VMBUS_CHAN_ST_ONLIST)) == 0, ("free busy channel"));
|
||||
KASSERT(chan->ch_orphan_xact == NULL,
|
||||
("still has orphan xact installed"));
|
||||
|
||||
hyperv_dmamem_free(&chan->ch_monprm_dma, chan->ch_monprm);
|
||||
mtx_destroy(&chan->ch_subchan_lock);
|
||||
sx_destroy(&chan->ch_orphan_lock);
|
||||
vmbus_rxbr_deinit(&chan->ch_rxbr);
|
||||
vmbus_txbr_deinit(&chan->ch_txbr);
|
||||
free(chan, M_DEVBUF);
|
||||
|
|
@ -1403,10 +1409,21 @@ vmbus_chan_msgproc_chrescind(struct vmbus_softc *sc,
|
|||
mtx_unlock(&sc->vmbus_prichan_lock);
|
||||
}
|
||||
|
||||
/*
|
||||
* NOTE:
|
||||
* The following processing order is critical:
|
||||
* Set the REVOKED state flag before orphaning the installed xact.
|
||||
*/
|
||||
|
||||
if (atomic_testandset_int(&chan->ch_stflags,
|
||||
VMBUS_CHAN_ST_REVOKED_SHIFT))
|
||||
panic("channel has already been revoked");
|
||||
|
||||
sx_xlock(&chan->ch_orphan_lock);
|
||||
if (chan->ch_orphan_xact != NULL)
|
||||
vmbus_xact_ctx_orphan(chan->ch_orphan_xact);
|
||||
sx_xunlock(&chan->ch_orphan_lock);
|
||||
|
||||
if (bootverbose)
|
||||
vmbus_chan_printf(chan, "chan%u revoked\n", note->chm_chanid);
|
||||
|
||||
|
|
@ -1708,3 +1725,21 @@ vmbus_chan_is_revoked(const struct vmbus_channel *chan)
|
|||
return (true);
|
||||
return (false);
|
||||
}
|
||||
|
||||
void
|
||||
vmbus_chan_set_orphan(struct vmbus_channel *chan, struct vmbus_xact_ctx *xact)
|
||||
{
|
||||
|
||||
sx_xlock(&chan->ch_orphan_lock);
|
||||
chan->ch_orphan_xact = xact;
|
||||
sx_xunlock(&chan->ch_orphan_lock);
|
||||
}
|
||||
|
||||
void
|
||||
vmbus_chan_unset_orphan(struct vmbus_channel *chan)
|
||||
{
|
||||
|
||||
sx_xlock(&chan->ch_orphan_lock);
|
||||
chan->ch_orphan_xact = NULL;
|
||||
sx_xunlock(&chan->ch_orphan_lock);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -33,8 +33,9 @@
|
|||
#include <sys/lock.h>
|
||||
#include <sys/mutex.h>
|
||||
#include <sys/queue.h>
|
||||
#include <sys/taskqueue.h>
|
||||
#include <sys/sysctl.h>
|
||||
#include <sys/sx.h>
|
||||
#include <sys/taskqueue.h>
|
||||
|
||||
#include <dev/hyperv/include/hyperv.h>
|
||||
#include <dev/hyperv/include/hyperv_busdma.h>
|
||||
|
|
@ -138,6 +139,9 @@ struct vmbus_channel {
|
|||
struct hyperv_guid ch_guid_type;
|
||||
struct hyperv_guid ch_guid_inst;
|
||||
|
||||
struct sx ch_orphan_lock;
|
||||
struct vmbus_xact_ctx *ch_orphan_xact;
|
||||
|
||||
struct sysctl_ctx_list ch_sysctl_ctx;
|
||||
} __aligned(CACHE_LINE_SIZE);
|
||||
|
||||
|
|
|
|||
Loading…
Reference in a new issue