msicap_cfgwrite(struct pci_vdev *dev, int capoff, int offset,
		int bytes, uint32_t val)
{
	uint16_t msgctrl, rwmask, msgdata, mme;
	uint32_t addrlo;

	/*
	 * If guest is writing to the message control register make sure
	 * we do not overwrite read-only fields.
	 */
	if ((offset - capoff) == 2 && bytes == 2) {
		rwmask = PCIM_MSICTRL_MME_MASK | PCIM_MSICTRL_MSI_ENABLE;
		msgctrl = pci_get_cfgdata16(dev, offset);
		msgctrl &= ~rwmask;
		msgctrl |= val & rwmask;
		val = msgctrl;

		addrlo = pci_get_cfgdata32(dev, capoff + 4);
		if (msgctrl & PCIM_MSICTRL_64BIT)
			msgdata = pci_get_cfgdata16(dev, capoff + 12);
		else
			msgdata = pci_get_cfgdata16(dev, capoff + 8);

		mme = msgctrl & PCIM_MSICTRL_MME_MASK;
		dev->msi.enabled = msgctrl & PCIM_MSICTRL_MSI_ENABLE ? 1 : 0;
		if (dev->msi.enabled) {
			dev->msi.addr = addrlo;
			dev->msi.msg_data = msgdata;
			dev->msi.maxmsgnum = 1 << (mme >> 4);
		} else {
			dev->msi.maxmsgnum = 0;
		}
		pci_lintr_update(dev);
	}

	CFGWRITE(dev, offset, val, bytes);
}
msicap_cfgwrite(struct pci_vdev *dev, int capoff, int offset,
		int bytes, uint32_t val)
{
	uint16_t msgctrl, rwmask, msgdata, mme;
	uint32_t addrlo;

	 
	if ((offset - capoff) == 2 && bytes == 2) {
		rwmask = PCIM_MSICTRL_MME_MASK | PCIM_MSICTRL_MSI_ENABLE;
		msgctrl = pci_get_cfgdata16(dev, offset);
		msgctrl &= ~rwmask;
		msgctrl |= val & rwmask;
		val = msgctrl;

		addrlo = pci_get_cfgdata32(dev, capoff + 4);
		if (msgctrl & PCIM_MSICTRL_64BIT)
			msgdata = pci_get_cfgdata16(dev, capoff + 12);
		else
			msgdata = pci_get_cfgdata16(dev, capoff + 8);

		mme = msgctrl & PCIM_MSICTRL_MME_MASK;
		dev->msi.enabled = msgctrl & PCIM_MSICTRL_MSI_ENABLE ? 1 : 0;
		if (dev->msi.enabled) {
			dev->msi.addr = addrlo;
			dev->msi.msg_data = msgdata;
			dev->msi.maxmsgnum = 1 << (mme >> 4);
		} else {
			dev->msi.maxmsgnum = 0;
		}
		pci_lintr_update(dev);
	}

	CFGWRITE(dev, offset, val, bytes);
}