1cd248341SJan Glauber /* 2cd248341SJan Glauber * Copyright IBM Corp. 2012 3cd248341SJan Glauber * 4cd248341SJan Glauber * Author(s): 5cd248341SJan Glauber * Jan Glauber <jang@linux.vnet.ibm.com> 6cd248341SJan Glauber * 7cd248341SJan Glauber * The System z PCI code is a rewrite from a prototype by 8cd248341SJan Glauber * the following people (Kudoz!): 9bedef755SJan Glauber * Alexander Schmidt 10bedef755SJan Glauber * Christoph Raisch 11bedef755SJan Glauber * Hannes Hering 12bedef755SJan Glauber * Hoang-Nam Nguyen 13bedef755SJan Glauber * Jan-Bernd Themann 14bedef755SJan Glauber * Stefan Roscher 15bedef755SJan Glauber * Thomas Klein 16cd248341SJan Glauber */ 17cd248341SJan Glauber 18cd248341SJan Glauber #define COMPONENT "zPCI" 19cd248341SJan Glauber #define pr_fmt(fmt) COMPONENT ": " fmt 20cd248341SJan Glauber 21cd248341SJan Glauber #include <linux/kernel.h> 22cd248341SJan Glauber #include <linux/slab.h> 23cd248341SJan Glauber #include <linux/err.h> 24cd248341SJan Glauber #include <linux/export.h> 25cd248341SJan Glauber #include <linux/delay.h> 269a4da8a5SJan Glauber #include <linux/irq.h> 279a4da8a5SJan Glauber #include <linux/kernel_stat.h> 28cd248341SJan Glauber #include <linux/seq_file.h> 29cd248341SJan Glauber #include <linux/pci.h> 30cd248341SJan Glauber #include <linux/msi.h> 31cd248341SJan Glauber 329a4da8a5SJan Glauber #include <asm/isc.h> 339a4da8a5SJan Glauber #include <asm/airq.h> 34cd248341SJan Glauber #include <asm/facility.h> 35cd248341SJan Glauber #include <asm/pci_insn.h> 36a755a45dSJan Glauber #include <asm/pci_clp.h> 37828b35f6SJan Glauber #include <asm/pci_dma.h> 38cd248341SJan Glauber 39cd248341SJan Glauber #define DEBUG /* enable pr_debug */ 40cd248341SJan Glauber 419a4da8a5SJan Glauber #define SIC_IRQ_MODE_ALL 0 429a4da8a5SJan Glauber #define SIC_IRQ_MODE_SINGLE 1 439a4da8a5SJan Glauber 44cd248341SJan Glauber #define ZPCI_NR_DMA_SPACES 1 459a4da8a5SJan Glauber #define ZPCI_MSI_VEC_BITS 6 46cd248341SJan Glauber #define ZPCI_NR_DEVICES CONFIG_PCI_NR_FUNCTIONS 47cd248341SJan Glauber 48cd248341SJan Glauber /* list of all detected zpci devices */ 49cd248341SJan Glauber LIST_HEAD(zpci_list); 507441b062SJan Glauber EXPORT_SYMBOL_GPL(zpci_list); 51cd248341SJan Glauber DEFINE_MUTEX(zpci_list_lock); 527441b062SJan Glauber EXPORT_SYMBOL_GPL(zpci_list_lock); 537441b062SJan Glauber 547441b062SJan Glauber struct pci_hp_callback_ops hotplug_ops; 557441b062SJan Glauber EXPORT_SYMBOL_GPL(hotplug_ops); 56cd248341SJan Glauber 57cd248341SJan Glauber static DECLARE_BITMAP(zpci_domain, ZPCI_NR_DEVICES); 58cd248341SJan Glauber static DEFINE_SPINLOCK(zpci_domain_lock); 59cd248341SJan Glauber 609a4da8a5SJan Glauber struct callback { 619a4da8a5SJan Glauber irq_handler_t handler; 629a4da8a5SJan Glauber void *data; 639a4da8a5SJan Glauber }; 649a4da8a5SJan Glauber 659a4da8a5SJan Glauber struct zdev_irq_map { 669a4da8a5SJan Glauber unsigned long aibv; /* AI bit vector */ 679a4da8a5SJan Glauber int msi_vecs; /* consecutive MSI-vectors used */ 689a4da8a5SJan Glauber int __unused; 699a4da8a5SJan Glauber struct callback cb[ZPCI_NR_MSI_VECS]; /* callback handler array */ 709a4da8a5SJan Glauber spinlock_t lock; /* protect callbacks against de-reg */ 719a4da8a5SJan Glauber }; 729a4da8a5SJan Glauber 739a4da8a5SJan Glauber struct intr_bucket { 749a4da8a5SJan Glauber /* amap of adapters, one bit per dev, corresponds to one irq nr */ 759a4da8a5SJan Glauber unsigned long *alloc; 769a4da8a5SJan Glauber /* AI summary bit, global page for all devices */ 779a4da8a5SJan Glauber unsigned long *aisb; 789a4da8a5SJan Glauber /* pointer to aibv and callback data in zdev */ 799a4da8a5SJan Glauber struct zdev_irq_map *imap[ZPCI_NR_DEVICES]; 809a4da8a5SJan Glauber /* protects the whole bucket struct */ 819a4da8a5SJan Glauber spinlock_t lock; 829a4da8a5SJan Glauber }; 839a4da8a5SJan Glauber 849a4da8a5SJan Glauber static struct intr_bucket *bucket; 859a4da8a5SJan Glauber 869a4da8a5SJan Glauber /* Adapter local summary indicator */ 879a4da8a5SJan Glauber static u8 *zpci_irq_si; 889a4da8a5SJan Glauber 899a4da8a5SJan Glauber static atomic_t irq_retries = ATOMIC_INIT(0); 909a4da8a5SJan Glauber 91cd248341SJan Glauber /* I/O Map */ 92cd248341SJan Glauber static DEFINE_SPINLOCK(zpci_iomap_lock); 93cd248341SJan Glauber static DECLARE_BITMAP(zpci_iomap, ZPCI_IOMAP_MAX_ENTRIES); 94cd248341SJan Glauber struct zpci_iomap_entry *zpci_iomap_start; 95cd248341SJan Glauber EXPORT_SYMBOL_GPL(zpci_iomap_start); 96cd248341SJan Glauber 979a4da8a5SJan Glauber /* highest irq summary bit */ 989a4da8a5SJan Glauber static int __read_mostly aisb_max; 999a4da8a5SJan Glauber 1009a4da8a5SJan Glauber static struct kmem_cache *zdev_irq_cache; 101*d0b08853SJan Glauber static struct kmem_cache *zdev_fmb_cache; 102*d0b08853SJan Glauber 103*d0b08853SJan Glauber debug_info_t *pci_debug_msg_id; 104*d0b08853SJan Glauber debug_info_t *pci_debug_err_id; 1059a4da8a5SJan Glauber 1069a4da8a5SJan Glauber static inline int irq_to_msi_nr(unsigned int irq) 1079a4da8a5SJan Glauber { 1089a4da8a5SJan Glauber return irq & ZPCI_MSI_MASK; 1099a4da8a5SJan Glauber } 1109a4da8a5SJan Glauber 1119a4da8a5SJan Glauber static inline int irq_to_dev_nr(unsigned int irq) 1129a4da8a5SJan Glauber { 1139a4da8a5SJan Glauber return irq >> ZPCI_MSI_VEC_BITS; 1149a4da8a5SJan Glauber } 1159a4da8a5SJan Glauber 1169a4da8a5SJan Glauber static inline struct zdev_irq_map *get_imap(unsigned int irq) 1179a4da8a5SJan Glauber { 1189a4da8a5SJan Glauber return bucket->imap[irq_to_dev_nr(irq)]; 1199a4da8a5SJan Glauber } 1209a4da8a5SJan Glauber 121cd248341SJan Glauber struct zpci_dev *get_zdev(struct pci_dev *pdev) 122cd248341SJan Glauber { 123cd248341SJan Glauber return (struct zpci_dev *) pdev->sysdata; 124cd248341SJan Glauber } 125cd248341SJan Glauber 126cd248341SJan Glauber struct zpci_dev *get_zdev_by_fid(u32 fid) 127cd248341SJan Glauber { 128cd248341SJan Glauber struct zpci_dev *tmp, *zdev = NULL; 129cd248341SJan Glauber 130cd248341SJan Glauber mutex_lock(&zpci_list_lock); 131cd248341SJan Glauber list_for_each_entry(tmp, &zpci_list, entry) { 132cd248341SJan Glauber if (tmp->fid == fid) { 133cd248341SJan Glauber zdev = tmp; 134cd248341SJan Glauber break; 135cd248341SJan Glauber } 136cd248341SJan Glauber } 137cd248341SJan Glauber mutex_unlock(&zpci_list_lock); 138cd248341SJan Glauber return zdev; 139cd248341SJan Glauber } 140cd248341SJan Glauber 141cd248341SJan Glauber bool zpci_fid_present(u32 fid) 142cd248341SJan Glauber { 143cd248341SJan Glauber return (get_zdev_by_fid(fid) != NULL) ? true : false; 144cd248341SJan Glauber } 145cd248341SJan Glauber 146cd248341SJan Glauber static struct zpci_dev *get_zdev_by_bus(struct pci_bus *bus) 147cd248341SJan Glauber { 148cd248341SJan Glauber return (bus && bus->sysdata) ? (struct zpci_dev *) bus->sysdata : NULL; 149cd248341SJan Glauber } 150cd248341SJan Glauber 151cd248341SJan Glauber int pci_domain_nr(struct pci_bus *bus) 152cd248341SJan Glauber { 153cd248341SJan Glauber return ((struct zpci_dev *) bus->sysdata)->domain; 154cd248341SJan Glauber } 155cd248341SJan Glauber EXPORT_SYMBOL_GPL(pci_domain_nr); 156cd248341SJan Glauber 157cd248341SJan Glauber int pci_proc_domain(struct pci_bus *bus) 158cd248341SJan Glauber { 159cd248341SJan Glauber return pci_domain_nr(bus); 160cd248341SJan Glauber } 161cd248341SJan Glauber EXPORT_SYMBOL_GPL(pci_proc_domain); 162cd248341SJan Glauber 163cd248341SJan Glauber /* Store PCI function information block */ 164cd248341SJan Glauber static int zpci_store_fib(struct zpci_dev *zdev, u8 *fc) 165cd248341SJan Glauber { 166cd248341SJan Glauber struct zpci_fib *fib; 167cd248341SJan Glauber u8 status, cc; 168cd248341SJan Glauber 169cd248341SJan Glauber fib = (void *) get_zeroed_page(GFP_KERNEL); 170cd248341SJan Glauber if (!fib) 171cd248341SJan Glauber return -ENOMEM; 172cd248341SJan Glauber 173cd248341SJan Glauber do { 174cd248341SJan Glauber cc = __stpcifc(zdev->fh, 0, fib, &status); 175cd248341SJan Glauber if (cc == 2) { 176cd248341SJan Glauber msleep(ZPCI_INSN_BUSY_DELAY); 177cd248341SJan Glauber memset(fib, 0, PAGE_SIZE); 178cd248341SJan Glauber } 179cd248341SJan Glauber } while (cc == 2); 180cd248341SJan Glauber 181cd248341SJan Glauber if (cc) 182cd248341SJan Glauber pr_err_once("%s: cc: %u status: %u\n", 183cd248341SJan Glauber __func__, cc, status); 184cd248341SJan Glauber 185cd248341SJan Glauber /* Return PCI function controls */ 186cd248341SJan Glauber *fc = fib->fc; 187cd248341SJan Glauber 188cd248341SJan Glauber free_page((unsigned long) fib); 189cd248341SJan Glauber return (cc) ? -EIO : 0; 190cd248341SJan Glauber } 191cd248341SJan Glauber 1929a4da8a5SJan Glauber /* Modify PCI: Register adapter interruptions */ 1939a4da8a5SJan Glauber static int zpci_register_airq(struct zpci_dev *zdev, unsigned int aisb, 1949a4da8a5SJan Glauber u64 aibv) 1959a4da8a5SJan Glauber { 1969a4da8a5SJan Glauber u64 req = ZPCI_CREATE_REQ(zdev->fh, 0, ZPCI_MOD_FC_REG_INT); 1979a4da8a5SJan Glauber struct zpci_fib *fib; 1989a4da8a5SJan Glauber int rc; 1999a4da8a5SJan Glauber 2009a4da8a5SJan Glauber fib = (void *) get_zeroed_page(GFP_KERNEL); 2019a4da8a5SJan Glauber if (!fib) 2029a4da8a5SJan Glauber return -ENOMEM; 2039a4da8a5SJan Glauber 2049a4da8a5SJan Glauber fib->isc = PCI_ISC; 2059a4da8a5SJan Glauber fib->noi = zdev->irq_map->msi_vecs; 2069a4da8a5SJan Glauber fib->sum = 1; /* enable summary notifications */ 2079a4da8a5SJan Glauber fib->aibv = aibv; 2089a4da8a5SJan Glauber fib->aibvo = 0; /* every function has its own page */ 2099a4da8a5SJan Glauber fib->aisb = (u64) bucket->aisb + aisb / 8; 2109a4da8a5SJan Glauber fib->aisbo = aisb & ZPCI_MSI_MASK; 2119a4da8a5SJan Glauber 2129a4da8a5SJan Glauber rc = mpcifc_instr(req, fib); 2139a4da8a5SJan Glauber pr_debug("%s mpcifc returned noi: %d\n", __func__, fib->noi); 2149a4da8a5SJan Glauber 2159a4da8a5SJan Glauber free_page((unsigned long) fib); 2169a4da8a5SJan Glauber return rc; 2179a4da8a5SJan Glauber } 2189a4da8a5SJan Glauber 2199a4da8a5SJan Glauber struct mod_pci_args { 2209a4da8a5SJan Glauber u64 base; 2219a4da8a5SJan Glauber u64 limit; 2229a4da8a5SJan Glauber u64 iota; 223*d0b08853SJan Glauber u64 fmb_addr; 2249a4da8a5SJan Glauber }; 2259a4da8a5SJan Glauber 2269a4da8a5SJan Glauber static int mod_pci(struct zpci_dev *zdev, int fn, u8 dmaas, struct mod_pci_args *args) 2279a4da8a5SJan Glauber { 2289a4da8a5SJan Glauber u64 req = ZPCI_CREATE_REQ(zdev->fh, dmaas, fn); 2299a4da8a5SJan Glauber struct zpci_fib *fib; 2309a4da8a5SJan Glauber int rc; 2319a4da8a5SJan Glauber 2329a4da8a5SJan Glauber /* The FIB must be available even if it's not used */ 2339a4da8a5SJan Glauber fib = (void *) get_zeroed_page(GFP_KERNEL); 2349a4da8a5SJan Glauber if (!fib) 2359a4da8a5SJan Glauber return -ENOMEM; 2369a4da8a5SJan Glauber 2379a4da8a5SJan Glauber fib->pba = args->base; 2389a4da8a5SJan Glauber fib->pal = args->limit; 2399a4da8a5SJan Glauber fib->iota = args->iota; 240*d0b08853SJan Glauber fib->fmb_addr = args->fmb_addr; 2419a4da8a5SJan Glauber 2429a4da8a5SJan Glauber rc = mpcifc_instr(req, fib); 2439a4da8a5SJan Glauber free_page((unsigned long) fib); 2449a4da8a5SJan Glauber return rc; 2459a4da8a5SJan Glauber } 2469a4da8a5SJan Glauber 247828b35f6SJan Glauber /* Modify PCI: Register I/O address translation parameters */ 248828b35f6SJan Glauber int zpci_register_ioat(struct zpci_dev *zdev, u8 dmaas, 249828b35f6SJan Glauber u64 base, u64 limit, u64 iota) 250828b35f6SJan Glauber { 251*d0b08853SJan Glauber struct mod_pci_args args = { base, limit, iota, 0 }; 252828b35f6SJan Glauber 253828b35f6SJan Glauber WARN_ON_ONCE(iota & 0x3fff); 254828b35f6SJan Glauber args.iota |= ZPCI_IOTA_RTTO_FLAG; 255828b35f6SJan Glauber return mod_pci(zdev, ZPCI_MOD_FC_REG_IOAT, dmaas, &args); 256828b35f6SJan Glauber } 257828b35f6SJan Glauber 258828b35f6SJan Glauber /* Modify PCI: Unregister I/O address translation parameters */ 259828b35f6SJan Glauber int zpci_unregister_ioat(struct zpci_dev *zdev, u8 dmaas) 260828b35f6SJan Glauber { 261*d0b08853SJan Glauber struct mod_pci_args args = { 0, 0, 0, 0 }; 262828b35f6SJan Glauber 263828b35f6SJan Glauber return mod_pci(zdev, ZPCI_MOD_FC_DEREG_IOAT, dmaas, &args); 264828b35f6SJan Glauber } 265828b35f6SJan Glauber 2669a4da8a5SJan Glauber /* Modify PCI: Unregister adapter interruptions */ 2679a4da8a5SJan Glauber static int zpci_unregister_airq(struct zpci_dev *zdev) 2689a4da8a5SJan Glauber { 269*d0b08853SJan Glauber struct mod_pci_args args = { 0, 0, 0, 0 }; 2709a4da8a5SJan Glauber 2719a4da8a5SJan Glauber return mod_pci(zdev, ZPCI_MOD_FC_DEREG_INT, 0, &args); 2729a4da8a5SJan Glauber } 2739a4da8a5SJan Glauber 274*d0b08853SJan Glauber /* Modify PCI: Set PCI function measurement parameters */ 275*d0b08853SJan Glauber int zpci_fmb_enable_device(struct zpci_dev *zdev) 276*d0b08853SJan Glauber { 277*d0b08853SJan Glauber struct mod_pci_args args = { 0, 0, 0, 0 }; 278*d0b08853SJan Glauber 279*d0b08853SJan Glauber if (zdev->fmb) 280*d0b08853SJan Glauber return -EINVAL; 281*d0b08853SJan Glauber 282*d0b08853SJan Glauber zdev->fmb = kmem_cache_alloc(zdev_fmb_cache, GFP_KERNEL); 283*d0b08853SJan Glauber if (!zdev->fmb) 284*d0b08853SJan Glauber return -ENOMEM; 285*d0b08853SJan Glauber memset(zdev->fmb, 0, sizeof(*zdev->fmb)); 286*d0b08853SJan Glauber WARN_ON((u64) zdev->fmb & 0xf); 287*d0b08853SJan Glauber 288*d0b08853SJan Glauber args.fmb_addr = virt_to_phys(zdev->fmb); 289*d0b08853SJan Glauber return mod_pci(zdev, ZPCI_MOD_FC_SET_MEASURE, 0, &args); 290*d0b08853SJan Glauber } 291*d0b08853SJan Glauber 292*d0b08853SJan Glauber /* Modify PCI: Disable PCI function measurement */ 293*d0b08853SJan Glauber int zpci_fmb_disable_device(struct zpci_dev *zdev) 294*d0b08853SJan Glauber { 295*d0b08853SJan Glauber struct mod_pci_args args = { 0, 0, 0, 0 }; 296*d0b08853SJan Glauber int rc; 297*d0b08853SJan Glauber 298*d0b08853SJan Glauber if (!zdev->fmb) 299*d0b08853SJan Glauber return -EINVAL; 300*d0b08853SJan Glauber 301*d0b08853SJan Glauber /* Function measurement is disabled if fmb address is zero */ 302*d0b08853SJan Glauber rc = mod_pci(zdev, ZPCI_MOD_FC_SET_MEASURE, 0, &args); 303*d0b08853SJan Glauber 304*d0b08853SJan Glauber kmem_cache_free(zdev_fmb_cache, zdev->fmb); 305*d0b08853SJan Glauber zdev->fmb = NULL; 306*d0b08853SJan Glauber return rc; 307*d0b08853SJan Glauber } 308*d0b08853SJan Glauber 309cd248341SJan Glauber #define ZPCI_PCIAS_CFGSPC 15 310cd248341SJan Glauber 311cd248341SJan Glauber static int zpci_cfg_load(struct zpci_dev *zdev, int offset, u32 *val, u8 len) 312cd248341SJan Glauber { 313cd248341SJan Glauber u64 req = ZPCI_CREATE_REQ(zdev->fh, ZPCI_PCIAS_CFGSPC, len); 314cd248341SJan Glauber u64 data; 315cd248341SJan Glauber int rc; 316cd248341SJan Glauber 317cd248341SJan Glauber rc = pcilg_instr(&data, req, offset); 318cd248341SJan Glauber data = data << ((8 - len) * 8); 319cd248341SJan Glauber data = le64_to_cpu(data); 320cd248341SJan Glauber if (!rc) 321cd248341SJan Glauber *val = (u32) data; 322cd248341SJan Glauber else 323cd248341SJan Glauber *val = 0xffffffff; 324cd248341SJan Glauber return rc; 325cd248341SJan Glauber } 326cd248341SJan Glauber 327cd248341SJan Glauber static int zpci_cfg_store(struct zpci_dev *zdev, int offset, u32 val, u8 len) 328cd248341SJan Glauber { 329cd248341SJan Glauber u64 req = ZPCI_CREATE_REQ(zdev->fh, ZPCI_PCIAS_CFGSPC, len); 330cd248341SJan Glauber u64 data = val; 331cd248341SJan Glauber int rc; 332cd248341SJan Glauber 333cd248341SJan Glauber data = cpu_to_le64(data); 334cd248341SJan Glauber data = data >> ((8 - len) * 8); 335cd248341SJan Glauber rc = pcistg_instr(data, req, offset); 336cd248341SJan Glauber return rc; 337cd248341SJan Glauber } 338cd248341SJan Glauber 3399a4da8a5SJan Glauber void synchronize_irq(unsigned int irq) 3409a4da8a5SJan Glauber { 3419a4da8a5SJan Glauber /* 3429a4da8a5SJan Glauber * Not needed, the handler is protected by a lock and IRQs that occur 3439a4da8a5SJan Glauber * after the handler is deleted are just NOPs. 3449a4da8a5SJan Glauber */ 3459a4da8a5SJan Glauber } 3469a4da8a5SJan Glauber EXPORT_SYMBOL_GPL(synchronize_irq); 3479a4da8a5SJan Glauber 3489a4da8a5SJan Glauber void enable_irq(unsigned int irq) 3499a4da8a5SJan Glauber { 3509a4da8a5SJan Glauber struct msi_desc *msi = irq_get_msi_desc(irq); 3519a4da8a5SJan Glauber 3529a4da8a5SJan Glauber zpci_msi_set_mask_bits(msi, 1, 0); 3539a4da8a5SJan Glauber } 3549a4da8a5SJan Glauber EXPORT_SYMBOL_GPL(enable_irq); 3559a4da8a5SJan Glauber 3569a4da8a5SJan Glauber void disable_irq(unsigned int irq) 3579a4da8a5SJan Glauber { 3589a4da8a5SJan Glauber struct msi_desc *msi = irq_get_msi_desc(irq); 3599a4da8a5SJan Glauber 3609a4da8a5SJan Glauber zpci_msi_set_mask_bits(msi, 1, 1); 3619a4da8a5SJan Glauber } 3629a4da8a5SJan Glauber EXPORT_SYMBOL_GPL(disable_irq); 3639a4da8a5SJan Glauber 3649a4da8a5SJan Glauber void disable_irq_nosync(unsigned int irq) 3659a4da8a5SJan Glauber { 3669a4da8a5SJan Glauber disable_irq(irq); 3679a4da8a5SJan Glauber } 3689a4da8a5SJan Glauber EXPORT_SYMBOL_GPL(disable_irq_nosync); 3699a4da8a5SJan Glauber 3709a4da8a5SJan Glauber unsigned long probe_irq_on(void) 3719a4da8a5SJan Glauber { 3729a4da8a5SJan Glauber return 0; 3739a4da8a5SJan Glauber } 3749a4da8a5SJan Glauber EXPORT_SYMBOL_GPL(probe_irq_on); 3759a4da8a5SJan Glauber 3769a4da8a5SJan Glauber int probe_irq_off(unsigned long val) 3779a4da8a5SJan Glauber { 3789a4da8a5SJan Glauber return 0; 3799a4da8a5SJan Glauber } 3809a4da8a5SJan Glauber EXPORT_SYMBOL_GPL(probe_irq_off); 3819a4da8a5SJan Glauber 3829a4da8a5SJan Glauber unsigned int probe_irq_mask(unsigned long val) 3839a4da8a5SJan Glauber { 3849a4da8a5SJan Glauber return val; 3859a4da8a5SJan Glauber } 3869a4da8a5SJan Glauber EXPORT_SYMBOL_GPL(probe_irq_mask); 3879a4da8a5SJan Glauber 388cd248341SJan Glauber void __devinit pcibios_fixup_bus(struct pci_bus *bus) 389cd248341SJan Glauber { 390cd248341SJan Glauber } 391cd248341SJan Glauber 392cd248341SJan Glauber resource_size_t pcibios_align_resource(void *data, const struct resource *res, 393cd248341SJan Glauber resource_size_t size, 394cd248341SJan Glauber resource_size_t align) 395cd248341SJan Glauber { 396cd248341SJan Glauber return 0; 397cd248341SJan Glauber } 398cd248341SJan Glauber 39987bc359bSJan Glauber /* combine single writes by using store-block insn */ 40087bc359bSJan Glauber void __iowrite64_copy(void __iomem *to, const void *from, size_t count) 40187bc359bSJan Glauber { 40287bc359bSJan Glauber zpci_memcpy_toio(to, from, count); 40387bc359bSJan Glauber } 40487bc359bSJan Glauber 405cd248341SJan Glauber /* Create a virtual mapping cookie for a PCI BAR */ 406cd248341SJan Glauber void __iomem *pci_iomap(struct pci_dev *pdev, int bar, unsigned long max) 407cd248341SJan Glauber { 408cd248341SJan Glauber struct zpci_dev *zdev = get_zdev(pdev); 409cd248341SJan Glauber u64 addr; 410cd248341SJan Glauber int idx; 411cd248341SJan Glauber 412cd248341SJan Glauber if ((bar & 7) != bar) 413cd248341SJan Glauber return NULL; 414cd248341SJan Glauber 415cd248341SJan Glauber idx = zdev->bars[bar].map_idx; 416cd248341SJan Glauber spin_lock(&zpci_iomap_lock); 417cd248341SJan Glauber zpci_iomap_start[idx].fh = zdev->fh; 418cd248341SJan Glauber zpci_iomap_start[idx].bar = bar; 419cd248341SJan Glauber spin_unlock(&zpci_iomap_lock); 420cd248341SJan Glauber 421cd248341SJan Glauber addr = ZPCI_IOMAP_ADDR_BASE | ((u64) idx << 48); 422cd248341SJan Glauber return (void __iomem *) addr; 423cd248341SJan Glauber } 424cd248341SJan Glauber EXPORT_SYMBOL_GPL(pci_iomap); 425cd248341SJan Glauber 426cd248341SJan Glauber void pci_iounmap(struct pci_dev *pdev, void __iomem *addr) 427cd248341SJan Glauber { 428cd248341SJan Glauber unsigned int idx; 429cd248341SJan Glauber 430cd248341SJan Glauber idx = (((__force u64) addr) & ~ZPCI_IOMAP_ADDR_BASE) >> 48; 431cd248341SJan Glauber spin_lock(&zpci_iomap_lock); 432cd248341SJan Glauber zpci_iomap_start[idx].fh = 0; 433cd248341SJan Glauber zpci_iomap_start[idx].bar = 0; 434cd248341SJan Glauber spin_unlock(&zpci_iomap_lock); 435cd248341SJan Glauber } 436cd248341SJan Glauber EXPORT_SYMBOL_GPL(pci_iounmap); 437cd248341SJan Glauber 438cd248341SJan Glauber static int pci_read(struct pci_bus *bus, unsigned int devfn, int where, 439cd248341SJan Glauber int size, u32 *val) 440cd248341SJan Glauber { 441cd248341SJan Glauber struct zpci_dev *zdev = get_zdev_by_bus(bus); 442cd248341SJan Glauber 443cd248341SJan Glauber if (!zdev || devfn != ZPCI_DEVFN) 444cd248341SJan Glauber return 0; 445cd248341SJan Glauber return zpci_cfg_load(zdev, where, val, size); 446cd248341SJan Glauber } 447cd248341SJan Glauber 448cd248341SJan Glauber static int pci_write(struct pci_bus *bus, unsigned int devfn, int where, 449cd248341SJan Glauber int size, u32 val) 450cd248341SJan Glauber { 451cd248341SJan Glauber struct zpci_dev *zdev = get_zdev_by_bus(bus); 452cd248341SJan Glauber 453cd248341SJan Glauber if (!zdev || devfn != ZPCI_DEVFN) 454cd248341SJan Glauber return 0; 455cd248341SJan Glauber return zpci_cfg_store(zdev, where, val, size); 456cd248341SJan Glauber } 457cd248341SJan Glauber 458cd248341SJan Glauber static struct pci_ops pci_root_ops = { 459cd248341SJan Glauber .read = pci_read, 460cd248341SJan Glauber .write = pci_write, 461cd248341SJan Glauber }; 462cd248341SJan Glauber 4639a4da8a5SJan Glauber /* store the last handled bit to implement fair scheduling of devices */ 4649a4da8a5SJan Glauber static DEFINE_PER_CPU(unsigned long, next_sbit); 4659a4da8a5SJan Glauber 4669a4da8a5SJan Glauber static void zpci_irq_handler(void *dont, void *need) 4679a4da8a5SJan Glauber { 4689a4da8a5SJan Glauber unsigned long sbit, mbit, last = 0, start = __get_cpu_var(next_sbit); 4699a4da8a5SJan Glauber int rescan = 0, max = aisb_max; 4709a4da8a5SJan Glauber struct zdev_irq_map *imap; 4719a4da8a5SJan Glauber 4729a4da8a5SJan Glauber kstat_cpu(smp_processor_id()).irqs[IOINT_PCI]++; 4739a4da8a5SJan Glauber sbit = start; 4749a4da8a5SJan Glauber 4759a4da8a5SJan Glauber scan: 4769a4da8a5SJan Glauber /* find summary_bit */ 4779a4da8a5SJan Glauber for_each_set_bit_left_cont(sbit, bucket->aisb, max) { 4789a4da8a5SJan Glauber clear_bit(63 - (sbit & 63), bucket->aisb + (sbit >> 6)); 4799a4da8a5SJan Glauber last = sbit; 4809a4da8a5SJan Glauber 4819a4da8a5SJan Glauber /* find vector bit */ 4829a4da8a5SJan Glauber imap = bucket->imap[sbit]; 4839a4da8a5SJan Glauber for_each_set_bit_left(mbit, &imap->aibv, imap->msi_vecs) { 4849a4da8a5SJan Glauber kstat_cpu(smp_processor_id()).irqs[IOINT_MSI]++; 4859a4da8a5SJan Glauber clear_bit(63 - mbit, &imap->aibv); 4869a4da8a5SJan Glauber 4879a4da8a5SJan Glauber spin_lock(&imap->lock); 4889a4da8a5SJan Glauber if (imap->cb[mbit].handler) 4899a4da8a5SJan Glauber imap->cb[mbit].handler(mbit, 4909a4da8a5SJan Glauber imap->cb[mbit].data); 4919a4da8a5SJan Glauber spin_unlock(&imap->lock); 4929a4da8a5SJan Glauber } 4939a4da8a5SJan Glauber } 4949a4da8a5SJan Glauber 4959a4da8a5SJan Glauber if (rescan) 4969a4da8a5SJan Glauber goto out; 4979a4da8a5SJan Glauber 4989a4da8a5SJan Glauber /* scan the skipped bits */ 4999a4da8a5SJan Glauber if (start > 0) { 5009a4da8a5SJan Glauber sbit = 0; 5019a4da8a5SJan Glauber max = start; 5029a4da8a5SJan Glauber start = 0; 5039a4da8a5SJan Glauber goto scan; 5049a4da8a5SJan Glauber } 5059a4da8a5SJan Glauber 5069a4da8a5SJan Glauber /* enable interrupts again */ 5079a4da8a5SJan Glauber sic_instr(SIC_IRQ_MODE_SINGLE, NULL, PCI_ISC); 5089a4da8a5SJan Glauber 5099a4da8a5SJan Glauber /* check again to not lose initiative */ 5109a4da8a5SJan Glauber rmb(); 5119a4da8a5SJan Glauber max = aisb_max; 5129a4da8a5SJan Glauber sbit = find_first_bit_left(bucket->aisb, max); 5139a4da8a5SJan Glauber if (sbit != max) { 5149a4da8a5SJan Glauber atomic_inc(&irq_retries); 5159a4da8a5SJan Glauber rescan++; 5169a4da8a5SJan Glauber goto scan; 5179a4da8a5SJan Glauber } 5189a4da8a5SJan Glauber out: 5199a4da8a5SJan Glauber /* store next device bit to scan */ 5209a4da8a5SJan Glauber __get_cpu_var(next_sbit) = (++last >= aisb_max) ? 0 : last; 5219a4da8a5SJan Glauber } 5229a4da8a5SJan Glauber 5239a4da8a5SJan Glauber /* msi_vecs - number of requested interrupts, 0 place function to error state */ 5249a4da8a5SJan Glauber static int zpci_setup_msi(struct pci_dev *pdev, int msi_vecs) 5259a4da8a5SJan Glauber { 5269a4da8a5SJan Glauber struct zpci_dev *zdev = get_zdev(pdev); 5279a4da8a5SJan Glauber unsigned int aisb, msi_nr; 5289a4da8a5SJan Glauber struct msi_desc *msi; 5299a4da8a5SJan Glauber int rc; 5309a4da8a5SJan Glauber 5319a4da8a5SJan Glauber /* store the number of used MSI vectors */ 5329a4da8a5SJan Glauber zdev->irq_map->msi_vecs = min(msi_vecs, ZPCI_NR_MSI_VECS); 5339a4da8a5SJan Glauber 5349a4da8a5SJan Glauber spin_lock(&bucket->lock); 5359a4da8a5SJan Glauber aisb = find_first_zero_bit(bucket->alloc, PAGE_SIZE); 5369a4da8a5SJan Glauber /* alloc map exhausted? */ 5379a4da8a5SJan Glauber if (aisb == PAGE_SIZE) { 5389a4da8a5SJan Glauber spin_unlock(&bucket->lock); 5399a4da8a5SJan Glauber return -EIO; 5409a4da8a5SJan Glauber } 5419a4da8a5SJan Glauber set_bit(aisb, bucket->alloc); 5429a4da8a5SJan Glauber spin_unlock(&bucket->lock); 5439a4da8a5SJan Glauber 5449a4da8a5SJan Glauber zdev->aisb = aisb; 5459a4da8a5SJan Glauber if (aisb + 1 > aisb_max) 5469a4da8a5SJan Glauber aisb_max = aisb + 1; 5479a4da8a5SJan Glauber 5489a4da8a5SJan Glauber /* wire up IRQ shortcut pointer */ 5499a4da8a5SJan Glauber bucket->imap[zdev->aisb] = zdev->irq_map; 5509a4da8a5SJan Glauber pr_debug("%s: imap[%u] linked to %p\n", __func__, zdev->aisb, zdev->irq_map); 5519a4da8a5SJan Glauber 5529a4da8a5SJan Glauber /* TODO: irq number 0 wont be found if we return less than requested MSIs. 5539a4da8a5SJan Glauber * ignore it for now and fix in common code. 5549a4da8a5SJan Glauber */ 5559a4da8a5SJan Glauber msi_nr = aisb << ZPCI_MSI_VEC_BITS; 5569a4da8a5SJan Glauber 5579a4da8a5SJan Glauber list_for_each_entry(msi, &pdev->msi_list, list) { 5589a4da8a5SJan Glauber rc = zpci_setup_msi_irq(zdev, msi, msi_nr, 5599a4da8a5SJan Glauber aisb << ZPCI_MSI_VEC_BITS); 5609a4da8a5SJan Glauber if (rc) 5619a4da8a5SJan Glauber return rc; 5629a4da8a5SJan Glauber msi_nr++; 5639a4da8a5SJan Glauber } 5649a4da8a5SJan Glauber 5659a4da8a5SJan Glauber rc = zpci_register_airq(zdev, aisb, (u64) &zdev->irq_map->aibv); 5669a4da8a5SJan Glauber if (rc) { 5679a4da8a5SJan Glauber clear_bit(aisb, bucket->alloc); 5689a4da8a5SJan Glauber dev_err(&pdev->dev, "register MSI failed with: %d\n", rc); 5699a4da8a5SJan Glauber return rc; 5709a4da8a5SJan Glauber } 5719a4da8a5SJan Glauber return (zdev->irq_map->msi_vecs == msi_vecs) ? 5729a4da8a5SJan Glauber 0 : zdev->irq_map->msi_vecs; 5739a4da8a5SJan Glauber } 5749a4da8a5SJan Glauber 5759a4da8a5SJan Glauber static void zpci_teardown_msi(struct pci_dev *pdev) 5769a4da8a5SJan Glauber { 5779a4da8a5SJan Glauber struct zpci_dev *zdev = get_zdev(pdev); 5789a4da8a5SJan Glauber struct msi_desc *msi; 5799a4da8a5SJan Glauber int aisb, rc; 5809a4da8a5SJan Glauber 5819a4da8a5SJan Glauber rc = zpci_unregister_airq(zdev); 5829a4da8a5SJan Glauber if (rc) { 5839a4da8a5SJan Glauber dev_err(&pdev->dev, "deregister MSI failed with: %d\n", rc); 5849a4da8a5SJan Glauber return; 5859a4da8a5SJan Glauber } 5869a4da8a5SJan Glauber 5879a4da8a5SJan Glauber msi = list_first_entry(&pdev->msi_list, struct msi_desc, list); 5889a4da8a5SJan Glauber aisb = irq_to_dev_nr(msi->irq); 5899a4da8a5SJan Glauber 5909a4da8a5SJan Glauber list_for_each_entry(msi, &pdev->msi_list, list) 5919a4da8a5SJan Glauber zpci_teardown_msi_irq(zdev, msi); 5929a4da8a5SJan Glauber 5939a4da8a5SJan Glauber clear_bit(aisb, bucket->alloc); 5949a4da8a5SJan Glauber if (aisb + 1 == aisb_max) 5959a4da8a5SJan Glauber aisb_max--; 5969a4da8a5SJan Glauber } 5979a4da8a5SJan Glauber 5989a4da8a5SJan Glauber int arch_setup_msi_irqs(struct pci_dev *pdev, int nvec, int type) 5999a4da8a5SJan Glauber { 6009a4da8a5SJan Glauber pr_debug("%s: requesting %d MSI-X interrupts...", __func__, nvec); 6019a4da8a5SJan Glauber if (type != PCI_CAP_ID_MSIX && type != PCI_CAP_ID_MSI) 6029a4da8a5SJan Glauber return -EINVAL; 6039a4da8a5SJan Glauber return zpci_setup_msi(pdev, nvec); 6049a4da8a5SJan Glauber } 6059a4da8a5SJan Glauber 6069a4da8a5SJan Glauber void arch_teardown_msi_irqs(struct pci_dev *pdev) 6079a4da8a5SJan Glauber { 6089a4da8a5SJan Glauber pr_info("%s: on pdev: %p\n", __func__, pdev); 6099a4da8a5SJan Glauber zpci_teardown_msi(pdev); 6109a4da8a5SJan Glauber } 6119a4da8a5SJan Glauber 612cd248341SJan Glauber static void zpci_map_resources(struct zpci_dev *zdev) 613cd248341SJan Glauber { 614cd248341SJan Glauber struct pci_dev *pdev = zdev->pdev; 615cd248341SJan Glauber resource_size_t len; 616cd248341SJan Glauber int i; 617cd248341SJan Glauber 618cd248341SJan Glauber for (i = 0; i < PCI_BAR_COUNT; i++) { 619cd248341SJan Glauber len = pci_resource_len(pdev, i); 620cd248341SJan Glauber if (!len) 621cd248341SJan Glauber continue; 622cd248341SJan Glauber pdev->resource[i].start = (resource_size_t) pci_iomap(pdev, i, 0); 623cd248341SJan Glauber pdev->resource[i].end = pdev->resource[i].start + len - 1; 624cd248341SJan Glauber pr_debug("BAR%i: -> start: %Lx end: %Lx\n", 625cd248341SJan Glauber i, pdev->resource[i].start, pdev->resource[i].end); 626cd248341SJan Glauber } 627cd248341SJan Glauber }; 628cd248341SJan Glauber 629cd248341SJan Glauber static void zpci_unmap_resources(struct pci_dev *pdev) 630cd248341SJan Glauber { 631cd248341SJan Glauber resource_size_t len; 632cd248341SJan Glauber int i; 633cd248341SJan Glauber 634cd248341SJan Glauber for (i = 0; i < PCI_BAR_COUNT; i++) { 635cd248341SJan Glauber len = pci_resource_len(pdev, i); 636cd248341SJan Glauber if (!len) 637cd248341SJan Glauber continue; 638cd248341SJan Glauber pci_iounmap(pdev, (void *) pdev->resource[i].start); 639cd248341SJan Glauber } 640cd248341SJan Glauber }; 641cd248341SJan Glauber 642cd248341SJan Glauber struct zpci_dev *zpci_alloc_device(void) 643cd248341SJan Glauber { 644cd248341SJan Glauber struct zpci_dev *zdev; 645cd248341SJan Glauber 646cd248341SJan Glauber /* Alloc memory for our private pci device data */ 647cd248341SJan Glauber zdev = kzalloc(sizeof(*zdev), GFP_KERNEL); 648cd248341SJan Glauber if (!zdev) 649cd248341SJan Glauber return ERR_PTR(-ENOMEM); 6509a4da8a5SJan Glauber 6519a4da8a5SJan Glauber /* Alloc aibv & callback space */ 6524118fee7SWei Yongjun zdev->irq_map = kmem_cache_zalloc(zdev_irq_cache, GFP_KERNEL); 6539a4da8a5SJan Glauber if (!zdev->irq_map) 6549a4da8a5SJan Glauber goto error; 6559a4da8a5SJan Glauber WARN_ON((u64) zdev->irq_map & 0xff); 656cd248341SJan Glauber return zdev; 6579a4da8a5SJan Glauber 6589a4da8a5SJan Glauber error: 6599a4da8a5SJan Glauber kfree(zdev); 6609a4da8a5SJan Glauber return ERR_PTR(-ENOMEM); 661cd248341SJan Glauber } 662cd248341SJan Glauber 663cd248341SJan Glauber void zpci_free_device(struct zpci_dev *zdev) 664cd248341SJan Glauber { 6659a4da8a5SJan Glauber kmem_cache_free(zdev_irq_cache, zdev->irq_map); 666cd248341SJan Glauber kfree(zdev); 667cd248341SJan Glauber } 668cd248341SJan Glauber 669cd248341SJan Glauber /* Called on removal of pci_dev, leaves zpci and bus device */ 670cd248341SJan Glauber static void zpci_remove_device(struct pci_dev *pdev) 671cd248341SJan Glauber { 672cd248341SJan Glauber struct zpci_dev *zdev = get_zdev(pdev); 673cd248341SJan Glauber 674cd248341SJan Glauber dev_info(&pdev->dev, "Removing device %u\n", zdev->domain); 675cd248341SJan Glauber zdev->state = ZPCI_FN_STATE_CONFIGURED; 676828b35f6SJan Glauber zpci_dma_exit_device(zdev); 677*d0b08853SJan Glauber zpci_fmb_disable_device(zdev); 6781e8da956SJan Glauber zpci_sysfs_remove_device(&pdev->dev); 679cd248341SJan Glauber zpci_unmap_resources(pdev); 680cd248341SJan Glauber list_del(&zdev->entry); /* can be called from init */ 681cd248341SJan Glauber zdev->pdev = NULL; 682cd248341SJan Glauber } 683cd248341SJan Glauber 684cd248341SJan Glauber static void zpci_scan_devices(void) 685cd248341SJan Glauber { 686cd248341SJan Glauber struct zpci_dev *zdev; 687cd248341SJan Glauber 688cd248341SJan Glauber mutex_lock(&zpci_list_lock); 689cd248341SJan Glauber list_for_each_entry(zdev, &zpci_list, entry) 690cd248341SJan Glauber if (zdev->state == ZPCI_FN_STATE_CONFIGURED) 691cd248341SJan Glauber zpci_scan_device(zdev); 692cd248341SJan Glauber mutex_unlock(&zpci_list_lock); 693cd248341SJan Glauber } 694cd248341SJan Glauber 695cd248341SJan Glauber /* 696cd248341SJan Glauber * Too late for any s390 specific setup, since interrupts must be set up 697cd248341SJan Glauber * already which requires DMA setup too and the pci scan will access the 698cd248341SJan Glauber * config space, which only works if the function handle is enabled. 699cd248341SJan Glauber */ 700cd248341SJan Glauber int pcibios_enable_device(struct pci_dev *pdev, int mask) 701cd248341SJan Glauber { 702cd248341SJan Glauber struct resource *res; 703cd248341SJan Glauber u16 cmd; 704cd248341SJan Glauber int i; 705cd248341SJan Glauber 706cd248341SJan Glauber pci_read_config_word(pdev, PCI_COMMAND, &cmd); 707cd248341SJan Glauber 708cd248341SJan Glauber for (i = 0; i < PCI_BAR_COUNT; i++) { 709cd248341SJan Glauber res = &pdev->resource[i]; 710cd248341SJan Glauber 711cd248341SJan Glauber if (res->flags & IORESOURCE_IO) 712cd248341SJan Glauber return -EINVAL; 713cd248341SJan Glauber 714cd248341SJan Glauber if (res->flags & IORESOURCE_MEM) 715cd248341SJan Glauber cmd |= PCI_COMMAND_MEMORY; 716cd248341SJan Glauber } 717cd248341SJan Glauber pci_write_config_word(pdev, PCI_COMMAND, cmd); 718cd248341SJan Glauber return 0; 719cd248341SJan Glauber } 720cd248341SJan Glauber 721cd248341SJan Glauber void pcibios_disable_device(struct pci_dev *pdev) 722cd248341SJan Glauber { 723cd248341SJan Glauber zpci_remove_device(pdev); 724cd248341SJan Glauber pdev->sysdata = NULL; 725cd248341SJan Glauber } 726cd248341SJan Glauber 7271e8da956SJan Glauber int pcibios_add_platform_entries(struct pci_dev *pdev) 7281e8da956SJan Glauber { 7291e8da956SJan Glauber return zpci_sysfs_add_device(&pdev->dev); 7301e8da956SJan Glauber } 7311e8da956SJan Glauber 7329a4da8a5SJan Glauber int zpci_request_irq(unsigned int irq, irq_handler_t handler, void *data) 7339a4da8a5SJan Glauber { 7349a4da8a5SJan Glauber int msi_nr = irq_to_msi_nr(irq); 7359a4da8a5SJan Glauber struct zdev_irq_map *imap; 7369a4da8a5SJan Glauber struct msi_desc *msi; 7379a4da8a5SJan Glauber 7389a4da8a5SJan Glauber msi = irq_get_msi_desc(irq); 7399a4da8a5SJan Glauber if (!msi) 7409a4da8a5SJan Glauber return -EIO; 7419a4da8a5SJan Glauber 7429a4da8a5SJan Glauber imap = get_imap(irq); 7439a4da8a5SJan Glauber spin_lock_init(&imap->lock); 7449a4da8a5SJan Glauber 7459a4da8a5SJan Glauber pr_debug("%s: register handler for IRQ:MSI %d:%d\n", __func__, irq >> 6, msi_nr); 7469a4da8a5SJan Glauber imap->cb[msi_nr].handler = handler; 7479a4da8a5SJan Glauber imap->cb[msi_nr].data = data; 7489a4da8a5SJan Glauber 7499a4da8a5SJan Glauber /* 7509a4da8a5SJan Glauber * The generic MSI code returns with the interrupt disabled on the 7519a4da8a5SJan Glauber * card, using the MSI mask bits. Firmware doesn't appear to unmask 7529a4da8a5SJan Glauber * at that level, so we do it here by hand. 7539a4da8a5SJan Glauber */ 7549a4da8a5SJan Glauber zpci_msi_set_mask_bits(msi, 1, 0); 7559a4da8a5SJan Glauber return 0; 7569a4da8a5SJan Glauber } 7579a4da8a5SJan Glauber 7589a4da8a5SJan Glauber void zpci_free_irq(unsigned int irq) 7599a4da8a5SJan Glauber { 7609a4da8a5SJan Glauber struct zdev_irq_map *imap = get_imap(irq); 7619a4da8a5SJan Glauber int msi_nr = irq_to_msi_nr(irq); 7629a4da8a5SJan Glauber unsigned long flags; 7639a4da8a5SJan Glauber 7649a4da8a5SJan Glauber pr_debug("%s: for irq: %d\n", __func__, irq); 7659a4da8a5SJan Glauber 7669a4da8a5SJan Glauber spin_lock_irqsave(&imap->lock, flags); 7679a4da8a5SJan Glauber imap->cb[msi_nr].handler = NULL; 7689a4da8a5SJan Glauber imap->cb[msi_nr].data = NULL; 7699a4da8a5SJan Glauber spin_unlock_irqrestore(&imap->lock, flags); 7709a4da8a5SJan Glauber } 7719a4da8a5SJan Glauber 7729a4da8a5SJan Glauber int request_irq(unsigned int irq, irq_handler_t handler, 7739a4da8a5SJan Glauber unsigned long irqflags, const char *devname, void *dev_id) 7749a4da8a5SJan Glauber { 7759a4da8a5SJan Glauber pr_debug("%s: irq: %d handler: %p flags: %lx dev: %s\n", 7769a4da8a5SJan Glauber __func__, irq, handler, irqflags, devname); 7779a4da8a5SJan Glauber 7789a4da8a5SJan Glauber return zpci_request_irq(irq, handler, dev_id); 7799a4da8a5SJan Glauber } 7809a4da8a5SJan Glauber EXPORT_SYMBOL_GPL(request_irq); 7819a4da8a5SJan Glauber 7829a4da8a5SJan Glauber void free_irq(unsigned int irq, void *dev_id) 7839a4da8a5SJan Glauber { 7849a4da8a5SJan Glauber zpci_free_irq(irq); 7859a4da8a5SJan Glauber } 7869a4da8a5SJan Glauber EXPORT_SYMBOL_GPL(free_irq); 7879a4da8a5SJan Glauber 7889a4da8a5SJan Glauber static int __init zpci_irq_init(void) 7899a4da8a5SJan Glauber { 7909a4da8a5SJan Glauber int cpu, rc; 7919a4da8a5SJan Glauber 7929a4da8a5SJan Glauber bucket = kzalloc(sizeof(*bucket), GFP_KERNEL); 7939a4da8a5SJan Glauber if (!bucket) 7949a4da8a5SJan Glauber return -ENOMEM; 7959a4da8a5SJan Glauber 7969a4da8a5SJan Glauber bucket->aisb = (unsigned long *) get_zeroed_page(GFP_KERNEL); 7979a4da8a5SJan Glauber if (!bucket->aisb) { 7989a4da8a5SJan Glauber rc = -ENOMEM; 7999a4da8a5SJan Glauber goto out_aisb; 8009a4da8a5SJan Glauber } 8019a4da8a5SJan Glauber 8029a4da8a5SJan Glauber bucket->alloc = (unsigned long *) get_zeroed_page(GFP_KERNEL); 8039a4da8a5SJan Glauber if (!bucket->alloc) { 8049a4da8a5SJan Glauber rc = -ENOMEM; 8059a4da8a5SJan Glauber goto out_alloc; 8069a4da8a5SJan Glauber } 8079a4da8a5SJan Glauber 8089a4da8a5SJan Glauber isc_register(PCI_ISC); 8099a4da8a5SJan Glauber zpci_irq_si = s390_register_adapter_interrupt(&zpci_irq_handler, NULL, PCI_ISC); 8109a4da8a5SJan Glauber if (IS_ERR(zpci_irq_si)) { 8119a4da8a5SJan Glauber rc = PTR_ERR(zpci_irq_si); 8129a4da8a5SJan Glauber zpci_irq_si = NULL; 8139a4da8a5SJan Glauber goto out_ai; 8149a4da8a5SJan Glauber } 8159a4da8a5SJan Glauber 8169a4da8a5SJan Glauber for_each_online_cpu(cpu) 8179a4da8a5SJan Glauber per_cpu(next_sbit, cpu) = 0; 8189a4da8a5SJan Glauber 8199a4da8a5SJan Glauber spin_lock_init(&bucket->lock); 8209a4da8a5SJan Glauber /* set summary to 1 to be called every time for the ISC */ 8219a4da8a5SJan Glauber *zpci_irq_si = 1; 8229a4da8a5SJan Glauber sic_instr(SIC_IRQ_MODE_SINGLE, NULL, PCI_ISC); 8239a4da8a5SJan Glauber return 0; 8249a4da8a5SJan Glauber 8259a4da8a5SJan Glauber out_ai: 8269a4da8a5SJan Glauber isc_unregister(PCI_ISC); 8279a4da8a5SJan Glauber free_page((unsigned long) bucket->alloc); 8289a4da8a5SJan Glauber out_alloc: 8299a4da8a5SJan Glauber free_page((unsigned long) bucket->aisb); 8309a4da8a5SJan Glauber out_aisb: 8319a4da8a5SJan Glauber kfree(bucket); 8329a4da8a5SJan Glauber return rc; 8339a4da8a5SJan Glauber } 8349a4da8a5SJan Glauber 8359a4da8a5SJan Glauber static void zpci_irq_exit(void) 8369a4da8a5SJan Glauber { 8379a4da8a5SJan Glauber free_page((unsigned long) bucket->alloc); 8389a4da8a5SJan Glauber free_page((unsigned long) bucket->aisb); 8399a4da8a5SJan Glauber s390_unregister_adapter_interrupt(zpci_irq_si, PCI_ISC); 8409a4da8a5SJan Glauber isc_unregister(PCI_ISC); 8419a4da8a5SJan Glauber kfree(bucket); 8429a4da8a5SJan Glauber } 8439a4da8a5SJan Glauber 844*d0b08853SJan Glauber void zpci_debug_info(struct zpci_dev *zdev, struct seq_file *m) 845*d0b08853SJan Glauber { 846*d0b08853SJan Glauber if (!zdev) 847*d0b08853SJan Glauber return; 848*d0b08853SJan Glauber 849*d0b08853SJan Glauber seq_printf(m, "global irq retries: %u\n", atomic_read(&irq_retries)); 850*d0b08853SJan Glauber seq_printf(m, "aibv[0]:%016lx aibv[1]:%016lx aisb:%016lx\n", 851*d0b08853SJan Glauber get_imap(0)->aibv, get_imap(1)->aibv, *bucket->aisb); 852*d0b08853SJan Glauber } 853*d0b08853SJan Glauber 854cd248341SJan Glauber static struct resource *zpci_alloc_bus_resource(unsigned long start, unsigned long size, 855cd248341SJan Glauber unsigned long flags, int domain) 856cd248341SJan Glauber { 857cd248341SJan Glauber struct resource *r; 858cd248341SJan Glauber char *name; 859cd248341SJan Glauber int rc; 860cd248341SJan Glauber 861cd248341SJan Glauber r = kzalloc(sizeof(*r), GFP_KERNEL); 862cd248341SJan Glauber if (!r) 863cd248341SJan Glauber return ERR_PTR(-ENOMEM); 864cd248341SJan Glauber r->start = start; 865cd248341SJan Glauber r->end = r->start + size - 1; 866cd248341SJan Glauber r->flags = flags; 867cd248341SJan Glauber r->parent = &iomem_resource; 868cd248341SJan Glauber name = kmalloc(18, GFP_KERNEL); 869cd248341SJan Glauber if (!name) { 870cd248341SJan Glauber kfree(r); 871cd248341SJan Glauber return ERR_PTR(-ENOMEM); 872cd248341SJan Glauber } 873cd248341SJan Glauber sprintf(name, "PCI Bus: %04x:%02x", domain, ZPCI_BUS_NR); 874cd248341SJan Glauber r->name = name; 875cd248341SJan Glauber 876cd248341SJan Glauber rc = request_resource(&iomem_resource, r); 877cd248341SJan Glauber if (rc) 878cd248341SJan Glauber pr_debug("request resource %pR failed\n", r); 879cd248341SJan Glauber return r; 880cd248341SJan Glauber } 881cd248341SJan Glauber 882cd248341SJan Glauber static int zpci_alloc_iomap(struct zpci_dev *zdev) 883cd248341SJan Glauber { 884cd248341SJan Glauber int entry; 885cd248341SJan Glauber 886cd248341SJan Glauber spin_lock(&zpci_iomap_lock); 887cd248341SJan Glauber entry = find_first_zero_bit(zpci_iomap, ZPCI_IOMAP_MAX_ENTRIES); 888cd248341SJan Glauber if (entry == ZPCI_IOMAP_MAX_ENTRIES) { 889cd248341SJan Glauber spin_unlock(&zpci_iomap_lock); 890cd248341SJan Glauber return -ENOSPC; 891cd248341SJan Glauber } 892cd248341SJan Glauber set_bit(entry, zpci_iomap); 893cd248341SJan Glauber spin_unlock(&zpci_iomap_lock); 894cd248341SJan Glauber return entry; 895cd248341SJan Glauber } 896cd248341SJan Glauber 897cd248341SJan Glauber static void zpci_free_iomap(struct zpci_dev *zdev, int entry) 898cd248341SJan Glauber { 899cd248341SJan Glauber spin_lock(&zpci_iomap_lock); 900cd248341SJan Glauber memset(&zpci_iomap_start[entry], 0, sizeof(struct zpci_iomap_entry)); 901cd248341SJan Glauber clear_bit(entry, zpci_iomap); 902cd248341SJan Glauber spin_unlock(&zpci_iomap_lock); 903cd248341SJan Glauber } 904cd248341SJan Glauber 905cd248341SJan Glauber static int zpci_create_device_bus(struct zpci_dev *zdev) 906cd248341SJan Glauber { 907cd248341SJan Glauber struct resource *res; 908cd248341SJan Glauber LIST_HEAD(resources); 909cd248341SJan Glauber int i; 910cd248341SJan Glauber 911cd248341SJan Glauber /* allocate mapping entry for each used bar */ 912cd248341SJan Glauber for (i = 0; i < PCI_BAR_COUNT; i++) { 913cd248341SJan Glauber unsigned long addr, size, flags; 914cd248341SJan Glauber int entry; 915cd248341SJan Glauber 916cd248341SJan Glauber if (!zdev->bars[i].size) 917cd248341SJan Glauber continue; 918cd248341SJan Glauber entry = zpci_alloc_iomap(zdev); 919cd248341SJan Glauber if (entry < 0) 920cd248341SJan Glauber return entry; 921cd248341SJan Glauber zdev->bars[i].map_idx = entry; 922cd248341SJan Glauber 923cd248341SJan Glauber /* only MMIO is supported */ 924cd248341SJan Glauber flags = IORESOURCE_MEM; 925cd248341SJan Glauber if (zdev->bars[i].val & 8) 926cd248341SJan Glauber flags |= IORESOURCE_PREFETCH; 927cd248341SJan Glauber if (zdev->bars[i].val & 4) 928cd248341SJan Glauber flags |= IORESOURCE_MEM_64; 929cd248341SJan Glauber 930cd248341SJan Glauber addr = ZPCI_IOMAP_ADDR_BASE + ((u64) entry << 48); 931cd248341SJan Glauber 932cd248341SJan Glauber size = 1UL << zdev->bars[i].size; 933cd248341SJan Glauber 934cd248341SJan Glauber res = zpci_alloc_bus_resource(addr, size, flags, zdev->domain); 935cd248341SJan Glauber if (IS_ERR(res)) { 936cd248341SJan Glauber zpci_free_iomap(zdev, entry); 937cd248341SJan Glauber return PTR_ERR(res); 938cd248341SJan Glauber } 939cd248341SJan Glauber pci_add_resource(&resources, res); 940cd248341SJan Glauber } 941cd248341SJan Glauber 942cd248341SJan Glauber zdev->bus = pci_create_root_bus(NULL, ZPCI_BUS_NR, &pci_root_ops, 943cd248341SJan Glauber zdev, &resources); 944cd248341SJan Glauber if (!zdev->bus) 945cd248341SJan Glauber return -EIO; 946cd248341SJan Glauber 947cd248341SJan Glauber zdev->bus->max_bus_speed = zdev->max_bus_speed; 948cd248341SJan Glauber return 0; 949cd248341SJan Glauber } 950cd248341SJan Glauber 951cd248341SJan Glauber static int zpci_alloc_domain(struct zpci_dev *zdev) 952cd248341SJan Glauber { 953cd248341SJan Glauber spin_lock(&zpci_domain_lock); 954cd248341SJan Glauber zdev->domain = find_first_zero_bit(zpci_domain, ZPCI_NR_DEVICES); 955cd248341SJan Glauber if (zdev->domain == ZPCI_NR_DEVICES) { 956cd248341SJan Glauber spin_unlock(&zpci_domain_lock); 957cd248341SJan Glauber return -ENOSPC; 958cd248341SJan Glauber } 959cd248341SJan Glauber set_bit(zdev->domain, zpci_domain); 960cd248341SJan Glauber spin_unlock(&zpci_domain_lock); 961cd248341SJan Glauber return 0; 962cd248341SJan Glauber } 963cd248341SJan Glauber 964cd248341SJan Glauber static void zpci_free_domain(struct zpci_dev *zdev) 965cd248341SJan Glauber { 966cd248341SJan Glauber spin_lock(&zpci_domain_lock); 967cd248341SJan Glauber clear_bit(zdev->domain, zpci_domain); 968cd248341SJan Glauber spin_unlock(&zpci_domain_lock); 969cd248341SJan Glauber } 970cd248341SJan Glauber 971a755a45dSJan Glauber int zpci_enable_device(struct zpci_dev *zdev) 972a755a45dSJan Glauber { 973a755a45dSJan Glauber int rc; 974a755a45dSJan Glauber 975a755a45dSJan Glauber rc = clp_enable_fh(zdev, ZPCI_NR_DMA_SPACES); 976a755a45dSJan Glauber if (rc) 977a755a45dSJan Glauber goto out; 978a755a45dSJan Glauber pr_info("Enabled fh: 0x%x fid: 0x%x\n", zdev->fh, zdev->fid); 979828b35f6SJan Glauber 980828b35f6SJan Glauber rc = zpci_dma_init_device(zdev); 981828b35f6SJan Glauber if (rc) 982828b35f6SJan Glauber goto out_dma; 983a755a45dSJan Glauber return 0; 984828b35f6SJan Glauber 985828b35f6SJan Glauber out_dma: 986828b35f6SJan Glauber clp_disable_fh(zdev); 987a755a45dSJan Glauber out: 988a755a45dSJan Glauber return rc; 989a755a45dSJan Glauber } 990a755a45dSJan Glauber EXPORT_SYMBOL_GPL(zpci_enable_device); 991a755a45dSJan Glauber 992cd248341SJan Glauber int zpci_create_device(struct zpci_dev *zdev) 993cd248341SJan Glauber { 994cd248341SJan Glauber int rc; 995cd248341SJan Glauber 996cd248341SJan Glauber rc = zpci_alloc_domain(zdev); 997cd248341SJan Glauber if (rc) 998cd248341SJan Glauber goto out; 999cd248341SJan Glauber 1000cd248341SJan Glauber rc = zpci_create_device_bus(zdev); 1001cd248341SJan Glauber if (rc) 1002cd248341SJan Glauber goto out_bus; 1003cd248341SJan Glauber 1004cd248341SJan Glauber mutex_lock(&zpci_list_lock); 1005cd248341SJan Glauber list_add_tail(&zdev->entry, &zpci_list); 10067441b062SJan Glauber if (hotplug_ops.create_slot) 10077441b062SJan Glauber hotplug_ops.create_slot(zdev); 1008cd248341SJan Glauber mutex_unlock(&zpci_list_lock); 1009cd248341SJan Glauber 1010cd248341SJan Glauber if (zdev->state == ZPCI_FN_STATE_STANDBY) 1011cd248341SJan Glauber return 0; 1012cd248341SJan Glauber 1013a755a45dSJan Glauber rc = zpci_enable_device(zdev); 1014a755a45dSJan Glauber if (rc) 1015a755a45dSJan Glauber goto out_start; 1016cd248341SJan Glauber return 0; 1017cd248341SJan Glauber 1018a755a45dSJan Glauber out_start: 1019a755a45dSJan Glauber mutex_lock(&zpci_list_lock); 1020a755a45dSJan Glauber list_del(&zdev->entry); 10217441b062SJan Glauber if (hotplug_ops.remove_slot) 10227441b062SJan Glauber hotplug_ops.remove_slot(zdev); 1023a755a45dSJan Glauber mutex_unlock(&zpci_list_lock); 1024cd248341SJan Glauber out_bus: 1025cd248341SJan Glauber zpci_free_domain(zdev); 1026cd248341SJan Glauber out: 1027cd248341SJan Glauber return rc; 1028cd248341SJan Glauber } 1029cd248341SJan Glauber 1030cd248341SJan Glauber void zpci_stop_device(struct zpci_dev *zdev) 1031cd248341SJan Glauber { 1032828b35f6SJan Glauber zpci_dma_exit_device(zdev); 1033cd248341SJan Glauber /* 1034cd248341SJan Glauber * Note: SCLP disables fh via set-pci-fn so don't 1035cd248341SJan Glauber * do that here. 1036cd248341SJan Glauber */ 1037cd248341SJan Glauber } 1038cd248341SJan Glauber EXPORT_SYMBOL_GPL(zpci_stop_device); 1039cd248341SJan Glauber 1040cd248341SJan Glauber int zpci_scan_device(struct zpci_dev *zdev) 1041cd248341SJan Glauber { 1042cd248341SJan Glauber zdev->pdev = pci_scan_single_device(zdev->bus, ZPCI_DEVFN); 1043cd248341SJan Glauber if (!zdev->pdev) { 1044cd248341SJan Glauber pr_err("pci_scan_single_device failed for fid: 0x%x\n", 1045cd248341SJan Glauber zdev->fid); 1046cd248341SJan Glauber goto out; 1047cd248341SJan Glauber } 1048cd248341SJan Glauber 1049*d0b08853SJan Glauber zpci_debug_init_device(zdev); 1050*d0b08853SJan Glauber zpci_fmb_enable_device(zdev); 1051cd248341SJan Glauber zpci_map_resources(zdev); 1052cd248341SJan Glauber pci_bus_add_devices(zdev->bus); 1053cd248341SJan Glauber 1054cd248341SJan Glauber /* now that pdev was added to the bus mark it as used */ 1055cd248341SJan Glauber zdev->state = ZPCI_FN_STATE_ONLINE; 1056cd248341SJan Glauber return 0; 1057cd248341SJan Glauber 1058cd248341SJan Glauber out: 1059828b35f6SJan Glauber zpci_dma_exit_device(zdev); 1060a755a45dSJan Glauber clp_disable_fh(zdev); 1061cd248341SJan Glauber return -EIO; 1062cd248341SJan Glauber } 1063cd248341SJan Glauber EXPORT_SYMBOL_GPL(zpci_scan_device); 1064cd248341SJan Glauber 1065cd248341SJan Glauber static inline int barsize(u8 size) 1066cd248341SJan Glauber { 1067cd248341SJan Glauber return (size) ? (1 << size) >> 10 : 0; 1068cd248341SJan Glauber } 1069cd248341SJan Glauber 1070cd248341SJan Glauber static int zpci_mem_init(void) 1071cd248341SJan Glauber { 10729a4da8a5SJan Glauber zdev_irq_cache = kmem_cache_create("PCI_IRQ_cache", sizeof(struct zdev_irq_map), 10739a4da8a5SJan Glauber L1_CACHE_BYTES, SLAB_HWCACHE_ALIGN, NULL); 10749a4da8a5SJan Glauber if (!zdev_irq_cache) 10759a4da8a5SJan Glauber goto error_zdev; 10769a4da8a5SJan Glauber 1077*d0b08853SJan Glauber zdev_fmb_cache = kmem_cache_create("PCI_FMB_cache", sizeof(struct zpci_fmb), 1078*d0b08853SJan Glauber 16, 0, NULL); 1079*d0b08853SJan Glauber if (!zdev_fmb_cache) 1080*d0b08853SJan Glauber goto error_fmb; 1081*d0b08853SJan Glauber 1082cd248341SJan Glauber /* TODO: use realloc */ 1083cd248341SJan Glauber zpci_iomap_start = kzalloc(ZPCI_IOMAP_MAX_ENTRIES * sizeof(*zpci_iomap_start), 1084cd248341SJan Glauber GFP_KERNEL); 1085cd248341SJan Glauber if (!zpci_iomap_start) 10869a4da8a5SJan Glauber goto error_iomap; 1087cd248341SJan Glauber return 0; 1088cd248341SJan Glauber 10899a4da8a5SJan Glauber error_iomap: 1090*d0b08853SJan Glauber kmem_cache_destroy(zdev_fmb_cache); 1091*d0b08853SJan Glauber error_fmb: 10929a4da8a5SJan Glauber kmem_cache_destroy(zdev_irq_cache); 1093cd248341SJan Glauber error_zdev: 1094cd248341SJan Glauber return -ENOMEM; 1095cd248341SJan Glauber } 1096cd248341SJan Glauber 1097cd248341SJan Glauber static void zpci_mem_exit(void) 1098cd248341SJan Glauber { 1099cd248341SJan Glauber kfree(zpci_iomap_start); 11009a4da8a5SJan Glauber kmem_cache_destroy(zdev_irq_cache); 1101*d0b08853SJan Glauber kmem_cache_destroy(zdev_fmb_cache); 1102cd248341SJan Glauber } 1103cd248341SJan Glauber 1104cd248341SJan Glauber unsigned int pci_probe = 1; 1105cd248341SJan Glauber EXPORT_SYMBOL_GPL(pci_probe); 1106cd248341SJan Glauber 1107cd248341SJan Glauber char * __init pcibios_setup(char *str) 1108cd248341SJan Glauber { 1109cd248341SJan Glauber if (!strcmp(str, "off")) { 1110cd248341SJan Glauber pci_probe = 0; 1111cd248341SJan Glauber return NULL; 1112cd248341SJan Glauber } 1113cd248341SJan Glauber return str; 1114cd248341SJan Glauber } 1115cd248341SJan Glauber 1116cd248341SJan Glauber static int __init pci_base_init(void) 1117cd248341SJan Glauber { 1118cd248341SJan Glauber int rc; 1119cd248341SJan Glauber 1120cd248341SJan Glauber if (!pci_probe) 1121cd248341SJan Glauber return 0; 1122cd248341SJan Glauber 1123cd248341SJan Glauber if (!test_facility(2) || !test_facility(69) 1124cd248341SJan Glauber || !test_facility(71) || !test_facility(72)) 1125cd248341SJan Glauber return 0; 1126cd248341SJan Glauber 1127cd248341SJan Glauber pr_info("Probing PCI hardware: PCI:%d SID:%d AEN:%d\n", 1128cd248341SJan Glauber test_facility(69), test_facility(70), 1129cd248341SJan Glauber test_facility(71)); 1130cd248341SJan Glauber 1131*d0b08853SJan Glauber rc = zpci_debug_init(); 1132*d0b08853SJan Glauber if (rc) 1133*d0b08853SJan Glauber return rc; 1134*d0b08853SJan Glauber 1135cd248341SJan Glauber rc = zpci_mem_init(); 1136cd248341SJan Glauber if (rc) 1137cd248341SJan Glauber goto out_mem; 1138cd248341SJan Glauber 11399a4da8a5SJan Glauber rc = zpci_msihash_init(); 11409a4da8a5SJan Glauber if (rc) 11419a4da8a5SJan Glauber goto out_hash; 11429a4da8a5SJan Glauber 11439a4da8a5SJan Glauber rc = zpci_irq_init(); 11449a4da8a5SJan Glauber if (rc) 11459a4da8a5SJan Glauber goto out_irq; 11469a4da8a5SJan Glauber 1147828b35f6SJan Glauber rc = zpci_dma_init(); 1148828b35f6SJan Glauber if (rc) 1149828b35f6SJan Glauber goto out_dma; 1150828b35f6SJan Glauber 1151a755a45dSJan Glauber rc = clp_find_pci_devices(); 1152a755a45dSJan Glauber if (rc) 1153a755a45dSJan Glauber goto out_find; 1154a755a45dSJan Glauber 1155cd248341SJan Glauber zpci_scan_devices(); 1156cd248341SJan Glauber return 0; 1157cd248341SJan Glauber 1158a755a45dSJan Glauber out_find: 1159828b35f6SJan Glauber zpci_dma_exit(); 1160828b35f6SJan Glauber out_dma: 11619a4da8a5SJan Glauber zpci_irq_exit(); 11629a4da8a5SJan Glauber out_irq: 11639a4da8a5SJan Glauber zpci_msihash_exit(); 11649a4da8a5SJan Glauber out_hash: 1165cd248341SJan Glauber zpci_mem_exit(); 1166cd248341SJan Glauber out_mem: 1167*d0b08853SJan Glauber zpci_debug_exit(); 1168cd248341SJan Glauber return rc; 1169cd248341SJan Glauber } 1170cd248341SJan Glauber subsys_initcall(pci_base_init); 1171