Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags   |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   1) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   2)  * This file is subject to the terms and conditions of the GNU General Public
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   3)  * License.  See the file "COPYING" in the main directory of this archive
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   4)  * for more details.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   5)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   6)  * Copyright (C) 2005-2009, 2010 Cavium Networks
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   7)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   8) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   9) #include <linux/init.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  10) #include <linux/msi.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  11) #include <linux/spinlock.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  12) #include <linux/interrupt.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  13) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  14) #include <asm/octeon/octeon.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  15) #include <asm/octeon/cvmx-npi-defs.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  16) #include <asm/octeon/cvmx-pci-defs.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  17) #include <asm/octeon/cvmx-npei-defs.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  18) #include <asm/octeon/cvmx-sli-defs.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  19) #include <asm/octeon/cvmx-pexp-defs.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  20) #include <asm/octeon/pci-octeon.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  21) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  22) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  23)  * Each bit in msi_free_irq_bitmask represents a MSI interrupt that is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  24)  * in use.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  25)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  26) static u64 msi_free_irq_bitmask[4];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  27) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  28) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  29)  * Each bit in msi_multiple_irq_bitmask tells that the device using
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  30)  * this bit in msi_free_irq_bitmask is also using the next bit. This
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  31)  * is used so we can disable all of the MSI interrupts when a device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  32)  * uses multiple.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  33)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  34) static u64 msi_multiple_irq_bitmask[4];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  35) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  36) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  37)  * This lock controls updates to msi_free_irq_bitmask and
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  38)  * msi_multiple_irq_bitmask.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  39)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  40) static DEFINE_SPINLOCK(msi_free_irq_bitmask_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  41) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  42) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  43)  * Number of MSI IRQs used. This variable is set up in
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  44)  * the module init time.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  45)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  46) static int msi_irq_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  47) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  48) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  49)  * Called when a driver request MSI interrupts instead of the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  50)  * legacy INT A-D. This routine will allocate multiple interrupts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  51)  * for MSI devices that support them. A device can override this by
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  52)  * programming the MSI control bits [6:4] before calling
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  53)  * pci_enable_msi().
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  54)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  55)  * @dev:    Device requesting MSI interrupts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  56)  * @desc:   MSI descriptor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  57)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  58)  * Returns 0 on success.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  59)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  60) int arch_setup_msi_irq(struct pci_dev *dev, struct msi_desc *desc)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  61) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  62) 	struct msi_msg msg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  63) 	u16 control;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  64) 	int configured_private_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  65) 	int request_private_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  66) 	int irq = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  67) 	int irq_step;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  68) 	u64 search_mask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  69) 	int index;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  70) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  71) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  72) 	 * Read the MSI config to figure out how many IRQs this device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  73) 	 * wants.  Most devices only want 1, which will give
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  74) 	 * configured_private_bits and request_private_bits equal 0.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  75) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  76) 	pci_read_config_word(dev, dev->msi_cap + PCI_MSI_FLAGS, &control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  77) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  78) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  79) 	 * If the number of private bits has been configured then use
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  80) 	 * that value instead of the requested number. This gives the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  81) 	 * driver the chance to override the number of interrupts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  82) 	 * before calling pci_enable_msi().
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  83) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  84) 	configured_private_bits = (control & PCI_MSI_FLAGS_QSIZE) >> 4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  85) 	if (configured_private_bits == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  86) 		/* Nothing is configured, so use the hardware requested size */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  87) 		request_private_bits = (control & PCI_MSI_FLAGS_QMASK) >> 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  88) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  89) 		/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  90) 		 * Use the number of configured bits, assuming the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  91) 		 * driver wanted to override the hardware request
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  92) 		 * value.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  93) 		 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  94) 		request_private_bits = configured_private_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  95) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  96) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  97) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  98) 	 * The PCI 2.3 spec mandates that there are at most 32
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  99) 	 * interrupts. If this device asks for more, only give it one.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) 	if (request_private_bits > 5)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) 		request_private_bits = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) try_only_one:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) 	 * The IRQs have to be aligned on a power of two based on the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) 	 * number being requested.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) 	irq_step = 1 << request_private_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) 	/* Mask with one bit for each IRQ */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) 	search_mask = (1 << irq_step) - 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) 	 * We're going to search msi_free_irq_bitmask_lock for zero
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) 	 * bits. This represents an MSI interrupt number that isn't in
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) 	 * use.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) 	spin_lock(&msi_free_irq_bitmask_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) 	for (index = 0; index < msi_irq_size/64; index++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) 		for (irq = 0; irq < 64; irq += irq_step) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) 			if ((msi_free_irq_bitmask[index] & (search_mask << irq)) == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) 				msi_free_irq_bitmask[index] |= search_mask << irq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) 				msi_multiple_irq_bitmask[index] |= (search_mask >> 1) << irq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) 				goto msi_irq_allocated;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) 			}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) msi_irq_allocated:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) 	spin_unlock(&msi_free_irq_bitmask_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) 	/* Make sure the search for available interrupts didn't fail */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) 	if (irq >= 64) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) 		if (request_private_bits) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) 			pr_err("arch_setup_msi_irq: Unable to find %d free interrupts, trying just one",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) 			       1 << request_private_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) 			request_private_bits = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) 			goto try_only_one;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) 		} else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) 			panic("arch_setup_msi_irq: Unable to find a free MSI interrupt");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) 	/* MSI interrupts start at logical IRQ OCTEON_IRQ_MSI_BIT0 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) 	irq += index*64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) 	irq += OCTEON_IRQ_MSI_BIT0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) 	switch (octeon_dma_bar_type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) 	case OCTEON_DMA_BAR_TYPE_SMALL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) 		/* When not using big bar, Bar 0 is based at 128MB */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) 		msg.address_lo =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) 			((128ul << 20) + CVMX_PCI_MSI_RCV) & 0xffffffff;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) 		msg.address_hi = ((128ul << 20) + CVMX_PCI_MSI_RCV) >> 32;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) 	case OCTEON_DMA_BAR_TYPE_BIG:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) 		/* When using big bar, Bar 0 is based at 0 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) 		msg.address_lo = (0 + CVMX_PCI_MSI_RCV) & 0xffffffff;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) 		msg.address_hi = (0 + CVMX_PCI_MSI_RCV) >> 32;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) 	case OCTEON_DMA_BAR_TYPE_PCIE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) 		/* When using PCIe, Bar 0 is based at 0 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) 		/* FIXME CVMX_NPEI_MSI_RCV* other than 0? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) 		msg.address_lo = (0 + CVMX_NPEI_PCIE_MSI_RCV) & 0xffffffff;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) 		msg.address_hi = (0 + CVMX_NPEI_PCIE_MSI_RCV) >> 32;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) 	case OCTEON_DMA_BAR_TYPE_PCIE2:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) 		/* When using PCIe2, Bar 0 is based at 0 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) 		msg.address_lo = (0 + CVMX_SLI_PCIE_MSI_RCV) & 0xffffffff;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) 		msg.address_hi = (0 + CVMX_SLI_PCIE_MSI_RCV) >> 32;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) 		panic("arch_setup_msi_irq: Invalid octeon_dma_bar_type");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) 	msg.data = irq - OCTEON_IRQ_MSI_BIT0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) 	/* Update the number of IRQs the device has available to it */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) 	control &= ~PCI_MSI_FLAGS_QSIZE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) 	control |= request_private_bits << 4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) 	pci_write_config_word(dev, dev->msi_cap + PCI_MSI_FLAGS, control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) 	irq_set_msi_desc(irq, desc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) 	pci_write_msi_msg(irq, &msg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) int arch_setup_msi_irqs(struct pci_dev *dev, int nvec, int type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) 	struct msi_desc *entry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) 	 * MSI-X is not supported.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) 	if (type == PCI_CAP_ID_MSIX)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) 	 * If an architecture wants to support multiple MSI, it needs to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) 	 * override arch_setup_msi_irqs()
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) 	if (type == PCI_CAP_ID_MSI && nvec > 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) 		return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) 	for_each_pci_msi_entry(entry, dev) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) 		ret = arch_setup_msi_irq(dev, entry);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) 		if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) 			return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) 		if (ret > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) 			return -ENOSPC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215)  * Called when a device no longer needs its MSI interrupts. All
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216)  * MSI interrupts for the device are freed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218)  * @irq:    The devices first irq number. There may be multple in sequence.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) void arch_teardown_msi_irq(unsigned int irq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) 	int number_irqs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) 	u64 bitmask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) 	int index = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) 	int irq0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) 	if ((irq < OCTEON_IRQ_MSI_BIT0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) 		|| (irq > msi_irq_size + OCTEON_IRQ_MSI_BIT0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) 		panic("arch_teardown_msi_irq: Attempted to teardown illegal "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) 		      "MSI interrupt (%d)", irq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) 	irq -= OCTEON_IRQ_MSI_BIT0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) 	index = irq / 64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) 	irq0 = irq % 64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) 	 * Count the number of IRQs we need to free by looking at the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) 	 * msi_multiple_irq_bitmask. Each bit set means that the next
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) 	 * IRQ is also owned by this device.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) 	number_irqs = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) 	while ((irq0 + number_irqs < 64) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) 	       (msi_multiple_irq_bitmask[index]
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) 		& (1ull << (irq0 + number_irqs))))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) 		number_irqs++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) 	number_irqs++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) 	/* Mask with one bit for each IRQ */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) 	bitmask = (1 << number_irqs) - 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) 	/* Shift the mask to the correct bit location */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) 	bitmask <<= irq0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) 	if ((msi_free_irq_bitmask[index] & bitmask) != bitmask)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) 		panic("arch_teardown_msi_irq: Attempted to teardown MSI "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) 		      "interrupt (%d) not in use", irq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) 	/* Checks are done, update the in use bitmask */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) 	spin_lock(&msi_free_irq_bitmask_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) 	msi_free_irq_bitmask[index] &= ~bitmask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) 	msi_multiple_irq_bitmask[index] &= ~bitmask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) 	spin_unlock(&msi_free_irq_bitmask_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) static DEFINE_RAW_SPINLOCK(octeon_irq_msi_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) static u64 msi_rcv_reg[4];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) static u64 mis_ena_reg[4];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) static void octeon_irq_msi_enable_pcie(struct irq_data *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) 	u64 en;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) 	unsigned long flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) 	int msi_number = data->irq - OCTEON_IRQ_MSI_BIT0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) 	int irq_index = msi_number >> 6;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) 	int irq_bit = msi_number & 0x3f;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) 	raw_spin_lock_irqsave(&octeon_irq_msi_lock, flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) 	en = cvmx_read_csr(mis_ena_reg[irq_index]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) 	en |= 1ull << irq_bit;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) 	cvmx_write_csr(mis_ena_reg[irq_index], en);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) 	cvmx_read_csr(mis_ena_reg[irq_index]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) 	raw_spin_unlock_irqrestore(&octeon_irq_msi_lock, flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) static void octeon_irq_msi_disable_pcie(struct irq_data *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) 	u64 en;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) 	unsigned long flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) 	int msi_number = data->irq - OCTEON_IRQ_MSI_BIT0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) 	int irq_index = msi_number >> 6;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) 	int irq_bit = msi_number & 0x3f;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) 	raw_spin_lock_irqsave(&octeon_irq_msi_lock, flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) 	en = cvmx_read_csr(mis_ena_reg[irq_index]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) 	en &= ~(1ull << irq_bit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) 	cvmx_write_csr(mis_ena_reg[irq_index], en);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) 	cvmx_read_csr(mis_ena_reg[irq_index]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) 	raw_spin_unlock_irqrestore(&octeon_irq_msi_lock, flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) static struct irq_chip octeon_irq_chip_msi_pcie = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) 	.name = "MSI",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) 	.irq_enable = octeon_irq_msi_enable_pcie,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) 	.irq_disable = octeon_irq_msi_disable_pcie,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) static void octeon_irq_msi_enable_pci(struct irq_data *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) 	 * Octeon PCI doesn't have the ability to mask/unmask MSI
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) 	 * interrupts individually. Instead of masking/unmasking them
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) 	 * in groups of 16, we simple assume MSI devices are well
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) 	 * behaved. MSI interrupts are always enable and the ACK is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) 	 * assumed to be enough
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) static void octeon_irq_msi_disable_pci(struct irq_data *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) 	/* See comment in enable */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) static struct irq_chip octeon_irq_chip_msi_pci = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) 	.name = "MSI",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) 	.irq_enable = octeon_irq_msi_enable_pci,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) 	.irq_disable = octeon_irq_msi_disable_pci,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328)  * Called by the interrupt handling code when an MSI interrupt
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329)  * occurs.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) static irqreturn_t __octeon_msi_do_interrupt(int index, u64 msi_bits)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) 	int irq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) 	int bit;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) 	bit = fls64(msi_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) 	if (bit) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) 		bit--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) 		/* Acknowledge it first. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) 		cvmx_write_csr(msi_rcv_reg[index], 1ull << bit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) 		irq = bit + OCTEON_IRQ_MSI_BIT0 + 64 * index;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) 		do_IRQ(irq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) 		return IRQ_HANDLED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) 	return IRQ_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) #define OCTEON_MSI_INT_HANDLER_X(x)					\
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) static irqreturn_t octeon_msi_interrupt##x(int cpl, void *dev_id)	\
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) {									\
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) 	u64 msi_bits = cvmx_read_csr(msi_rcv_reg[(x)]);			\
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) 	return __octeon_msi_do_interrupt((x), msi_bits);		\
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357)  * Create octeon_msi_interrupt{0-3} function body
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) OCTEON_MSI_INT_HANDLER_X(0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) OCTEON_MSI_INT_HANDLER_X(1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) OCTEON_MSI_INT_HANDLER_X(2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) OCTEON_MSI_INT_HANDLER_X(3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365)  * Initializes the MSI interrupt handling code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) int __init octeon_msi_initialize(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) 	int irq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) 	struct irq_chip *msi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) 	if (octeon_dma_bar_type == OCTEON_DMA_BAR_TYPE_INVALID) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) 	} else if (octeon_dma_bar_type == OCTEON_DMA_BAR_TYPE_PCIE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) 		msi_rcv_reg[0] = CVMX_PEXP_NPEI_MSI_RCV0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) 		msi_rcv_reg[1] = CVMX_PEXP_NPEI_MSI_RCV1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) 		msi_rcv_reg[2] = CVMX_PEXP_NPEI_MSI_RCV2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) 		msi_rcv_reg[3] = CVMX_PEXP_NPEI_MSI_RCV3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) 		mis_ena_reg[0] = CVMX_PEXP_NPEI_MSI_ENB0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) 		mis_ena_reg[1] = CVMX_PEXP_NPEI_MSI_ENB1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) 		mis_ena_reg[2] = CVMX_PEXP_NPEI_MSI_ENB2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) 		mis_ena_reg[3] = CVMX_PEXP_NPEI_MSI_ENB3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) 		msi = &octeon_irq_chip_msi_pcie;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) 		msi_rcv_reg[0] = CVMX_NPI_NPI_MSI_RCV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) #define INVALID_GENERATE_ADE 0x8700000000000000ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) 		msi_rcv_reg[1] = INVALID_GENERATE_ADE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) 		msi_rcv_reg[2] = INVALID_GENERATE_ADE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) 		msi_rcv_reg[3] = INVALID_GENERATE_ADE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) 		mis_ena_reg[0] = INVALID_GENERATE_ADE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) 		mis_ena_reg[1] = INVALID_GENERATE_ADE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) 		mis_ena_reg[2] = INVALID_GENERATE_ADE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) 		mis_ena_reg[3] = INVALID_GENERATE_ADE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) 		msi = &octeon_irq_chip_msi_pci;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) 	for (irq = OCTEON_IRQ_MSI_BIT0; irq <= OCTEON_IRQ_MSI_LAST; irq++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) 		irq_set_chip_and_handler(irq, msi, handle_simple_irq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) 	if (octeon_has_feature(OCTEON_FEATURE_PCIE)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) 		if (request_irq(OCTEON_IRQ_PCI_MSI0, octeon_msi_interrupt0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) 				0, "MSI[0:63]", octeon_msi_interrupt0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) 			panic("request_irq(OCTEON_IRQ_PCI_MSI0) failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) 		if (request_irq(OCTEON_IRQ_PCI_MSI1, octeon_msi_interrupt1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) 				0, "MSI[64:127]", octeon_msi_interrupt1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) 			panic("request_irq(OCTEON_IRQ_PCI_MSI1) failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) 		if (request_irq(OCTEON_IRQ_PCI_MSI2, octeon_msi_interrupt2,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) 				0, "MSI[127:191]", octeon_msi_interrupt2))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) 			panic("request_irq(OCTEON_IRQ_PCI_MSI2) failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) 		if (request_irq(OCTEON_IRQ_PCI_MSI3, octeon_msi_interrupt3,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) 				0, "MSI[192:255]", octeon_msi_interrupt3))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) 			panic("request_irq(OCTEON_IRQ_PCI_MSI3) failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) 		msi_irq_size = 256;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) 	} else if (octeon_is_pci_host()) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) 		if (request_irq(OCTEON_IRQ_PCI_MSI0, octeon_msi_interrupt0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) 				0, "MSI[0:15]", octeon_msi_interrupt0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) 			panic("request_irq(OCTEON_IRQ_PCI_MSI0) failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) 		if (request_irq(OCTEON_IRQ_PCI_MSI1, octeon_msi_interrupt0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) 				0, "MSI[16:31]", octeon_msi_interrupt0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) 			panic("request_irq(OCTEON_IRQ_PCI_MSI1) failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) 		if (request_irq(OCTEON_IRQ_PCI_MSI2, octeon_msi_interrupt0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) 				0, "MSI[32:47]", octeon_msi_interrupt0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) 			panic("request_irq(OCTEON_IRQ_PCI_MSI2) failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) 		if (request_irq(OCTEON_IRQ_PCI_MSI3, octeon_msi_interrupt0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) 				0, "MSI[48:63]", octeon_msi_interrupt0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) 			panic("request_irq(OCTEON_IRQ_PCI_MSI3) failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) 		msi_irq_size = 64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) subsys_initcall(octeon_msi_initialize);