1 /* 2 * Copyright (C) 2006-2009 Freescale Semiconductor, Inc. 3 * 4 * See file CREDITS for list of people who contributed to this 5 * project. 6 * 7 * This program is free software; you can redistribute it and/or 8 * modify it under the terms of the GNU General Public License as 9 * published by the Free Software Foundation; either version 2 of 10 * the License, or (at your option) any later version. 11 */ 12 13 #include <common.h> 14 #include <mpc83xx.h> 15 #include <pci.h> 16 #include <asm/io.h> 17 18 static struct pci_region pci_regions[] = { 19 { 20 bus_start: CONFIG_SYS_PCI_MEM_BASE, 21 phys_start: CONFIG_SYS_PCI_MEM_PHYS, 22 size: CONFIG_SYS_PCI_MEM_SIZE, 23 flags: PCI_REGION_MEM | PCI_REGION_PREFETCH 24 }, 25 { 26 bus_start: CONFIG_SYS_PCI_MMIO_BASE, 27 phys_start: CONFIG_SYS_PCI_MMIO_PHYS, 28 size: CONFIG_SYS_PCI_MMIO_SIZE, 29 flags: PCI_REGION_MEM 30 }, 31 { 32 bus_start: CONFIG_SYS_PCI_IO_BASE, 33 phys_start: CONFIG_SYS_PCI_IO_PHYS, 34 size: CONFIG_SYS_PCI_IO_SIZE, 35 flags: PCI_REGION_IO 36 } 37 }; 38 39 static struct pci_region pcie_regions_0[] = { 40 { 41 .bus_start = CONFIG_SYS_PCIE1_MEM_BASE, 42 .phys_start = CONFIG_SYS_PCIE1_MEM_PHYS, 43 .size = CONFIG_SYS_PCIE1_MEM_SIZE, 44 .flags = PCI_REGION_MEM, 45 }, 46 { 47 .bus_start = CONFIG_SYS_PCIE1_IO_BASE, 48 .phys_start = CONFIG_SYS_PCIE1_IO_PHYS, 49 .size = CONFIG_SYS_PCIE1_IO_SIZE, 50 .flags = PCI_REGION_IO, 51 }, 52 }; 53 54 static struct pci_region pcie_regions_1[] = { 55 { 56 .bus_start = CONFIG_SYS_PCIE2_MEM_BASE, 57 .phys_start = CONFIG_SYS_PCIE2_MEM_PHYS, 58 .size = CONFIG_SYS_PCIE2_MEM_SIZE, 59 .flags = PCI_REGION_MEM, 60 }, 61 { 62 .bus_start = CONFIG_SYS_PCIE2_IO_BASE, 63 .phys_start = CONFIG_SYS_PCIE2_IO_PHYS, 64 .size = CONFIG_SYS_PCIE2_IO_SIZE, 65 .flags = PCI_REGION_IO, 66 }, 67 }; 68 69 void pci_init_board(void) 70 { 71 volatile immap_t *immr = (volatile immap_t *)CONFIG_SYS_IMMR; 72 volatile sysconf83xx_t *sysconf = &immr->sysconf; 73 volatile clk83xx_t *clk = (volatile clk83xx_t *)&immr->clk; 74 volatile law83xx_t *pci_law = immr->sysconf.pcilaw; 75 volatile law83xx_t *pcie_law = sysconf->pcielaw; 76 struct pci_region *reg[] = { pci_regions }; 77 struct pci_region *pcie_reg[] = { pcie_regions_0, pcie_regions_1, }; 78 u32 spridr = in_be32(&immr->sysconf.spridr); 79 80 /* Enable all 5 PCI_CLK_OUTPUTS */ 81 clk->occr |= 0xf8000000; 82 udelay(2000); 83 84 /* Configure PCI Local Access Windows */ 85 pci_law[0].bar = CONFIG_SYS_PCI_MEM_PHYS & LAWBAR_BAR; 86 pci_law[0].ar = LBLAWAR_EN | LBLAWAR_512MB; 87 88 pci_law[1].bar = CONFIG_SYS_PCI_IO_PHYS & LAWBAR_BAR; 89 pci_law[1].ar = LBLAWAR_EN | LBLAWAR_1MB; 90 91 mpc83xx_pci_init(1, reg); 92 93 /* There is no PEX in MPC8379 parts. */ 94 if (PARTID_NO_E(spridr) == SPR_8379) 95 return; 96 97 /* Configure the clock for PCIE controller */ 98 clrsetbits_be32(&clk->sccr, SCCR_PCIEXP1CM | SCCR_PCIEXP2CM, 99 SCCR_PCIEXP1CM_1 | SCCR_PCIEXP2CM_1); 100 101 /* Deassert the resets in the control register */ 102 out_be32(&sysconf->pecr1, 0xE0008000); 103 out_be32(&sysconf->pecr2, 0xE0008000); 104 udelay(2000); 105 106 /* Configure PCI Express Local Access Windows */ 107 out_be32(&pcie_law[0].bar, CONFIG_SYS_PCIE1_BASE & LAWBAR_BAR); 108 out_be32(&pcie_law[0].ar, LBLAWAR_EN | LBLAWAR_512MB); 109 110 out_be32(&pcie_law[1].bar, CONFIG_SYS_PCIE2_BASE & LAWBAR_BAR); 111 out_be32(&pcie_law[1].ar, LBLAWAR_EN | LBLAWAR_512MB); 112 113 mpc83xx_pcie_init(2, pcie_reg); 114 } 115