1 /* 2 * Copyright (C) 2013, Red Hat Inc, Michael S. Tsirkin <mst@redhat.com> 3 * 4 * This work is licensed under the terms of the GNU LGPL, version 2. 5 */ 6 #include <linux/pci_regs.h> 7 #include "pci.h" 8 #include "asm/pci.h" 9 10 typedef void (*pci_cap_handler)(struct pci_dev *dev, int cap_offset); 11 12 static void pci_cap_msi_handler(struct pci_dev *dev, int cap_offset) 13 { 14 printf("Detected MSI for device 0x%x offset 0x%x\n", 15 dev->bdf, cap_offset); 16 dev->msi_offset = cap_offset; 17 } 18 19 static pci_cap_handler cap_handlers[PCI_CAP_ID_MAX + 1] = { 20 [PCI_CAP_ID_MSI] = pci_cap_msi_handler, 21 }; 22 23 void pci_cap_walk(struct pci_dev *dev) 24 { 25 uint8_t cap_offset; 26 uint8_t cap_id; 27 int count = 0; 28 29 cap_offset = pci_config_readb(dev->bdf, PCI_CAPABILITY_LIST); 30 while (cap_offset) { 31 cap_id = pci_config_readb(dev->bdf, cap_offset); 32 printf("PCI detected cap 0x%x\n", cap_id); 33 assert(cap_id < PCI_CAP_ID_MAX + 1); 34 if (cap_handlers[cap_id]) 35 cap_handlers[cap_id](dev, cap_offset); 36 cap_offset = pci_config_readb(dev->bdf, cap_offset + 1); 37 /* Avoid dead loop during cap walk */ 38 assert(++count <= 255); 39 } 40 } 41 42 void pci_msi_set_enable(struct pci_dev *dev, bool enabled) 43 { 44 uint16_t msi_control; 45 uint16_t offset; 46 47 offset = dev->msi_offset; 48 msi_control = pci_config_readw(dev->bdf, offset + PCI_MSI_FLAGS); 49 50 if (enabled) 51 msi_control |= PCI_MSI_FLAGS_ENABLE; 52 else 53 msi_control &= ~PCI_MSI_FLAGS_ENABLE; 54 55 pci_config_writew(dev->bdf, offset + PCI_MSI_FLAGS, msi_control); 56 } 57 58 bool pci_setup_msi(struct pci_dev *dev, uint64_t msi_addr, uint32_t msi_data) 59 { 60 uint16_t msi_control; 61 uint16_t offset; 62 pcidevaddr_t addr; 63 64 assert(dev); 65 66 if (!dev->msi_offset) { 67 printf("MSI: dev 0x%x does not support MSI.\n", dev->bdf); 68 return false; 69 } 70 71 addr = dev->bdf; 72 offset = dev->msi_offset; 73 msi_control = pci_config_readw(addr, offset + PCI_MSI_FLAGS); 74 pci_config_writel(addr, offset + PCI_MSI_ADDRESS_LO, 75 msi_addr & 0xffffffff); 76 77 if (msi_control & PCI_MSI_FLAGS_64BIT) { 78 pci_config_writel(addr, offset + PCI_MSI_ADDRESS_HI, 79 (uint32_t)(msi_addr >> 32)); 80 pci_config_writel(addr, offset + PCI_MSI_DATA_64, msi_data); 81 printf("MSI: dev 0x%x init 64bit address: ", addr); 82 } else { 83 pci_config_writel(addr, offset + PCI_MSI_DATA_32, msi_data); 84 printf("MSI: dev 0x%x init 32bit address: ", addr); 85 } 86 printf("addr=0x%" PRIx64 ", data=0x%x\n", msi_addr, msi_data); 87 88 pci_msi_set_enable(dev, true); 89 90 return true; 91 } 92 93 void pci_cmd_set_clr(struct pci_dev *dev, uint16_t set, uint16_t clr) 94 { 95 uint16_t val = pci_config_readw(dev->bdf, PCI_COMMAND); 96 97 /* No overlap is allowed */ 98 assert((set & clr) == 0); 99 val |= set; 100 val &= ~clr; 101 102 pci_config_writew(dev->bdf, PCI_COMMAND, val); 103 } 104 105 bool pci_dev_exists(pcidevaddr_t dev) 106 { 107 return (pci_config_readw(dev, PCI_VENDOR_ID) != 0xffff && 108 pci_config_readw(dev, PCI_DEVICE_ID) != 0xffff); 109 } 110 111 void pci_dev_init(struct pci_dev *dev, pcidevaddr_t bdf) 112 { 113 memset(dev, 0, sizeof(*dev)); 114 dev->bdf = bdf; 115 } 116 117 /* Scan bus look for a specific device. Only bus 0 scanned for now. */ 118 pcidevaddr_t pci_find_dev(uint16_t vendor_id, uint16_t device_id) 119 { 120 pcidevaddr_t dev; 121 122 for (dev = 0; dev < PCI_DEVFN_MAX; ++dev) { 123 if (pci_config_readw(dev, PCI_VENDOR_ID) == vendor_id && 124 pci_config_readw(dev, PCI_DEVICE_ID) == device_id) 125 return dev; 126 } 127 128 return PCIDEVADDR_INVALID; 129 } 130 131 uint32_t pci_bar_mask(uint32_t bar) 132 { 133 return (bar & PCI_BASE_ADDRESS_SPACE_IO) ? 134 PCI_BASE_ADDRESS_IO_MASK : PCI_BASE_ADDRESS_MEM_MASK; 135 } 136 137 uint32_t pci_bar_get(struct pci_dev *dev, int bar_num) 138 { 139 return pci_config_readl(dev->bdf, PCI_BASE_ADDRESS_0 + 140 bar_num * 4); 141 } 142 143 phys_addr_t pci_bar_get_addr(struct pci_dev *dev, int bar_num) 144 { 145 uint32_t bar = pci_bar_get(dev, bar_num); 146 uint32_t mask = pci_bar_mask(bar); 147 uint64_t addr = bar & mask; 148 phys_addr_t phys_addr; 149 150 if (pci_bar_is64(dev, bar_num)) 151 addr |= (uint64_t)pci_bar_get(dev, bar_num + 1) << 32; 152 153 phys_addr = pci_translate_addr(dev->bdf, addr); 154 assert(phys_addr != INVALID_PHYS_ADDR); 155 156 return phys_addr; 157 } 158 159 void pci_bar_set_addr(struct pci_dev *dev, int bar_num, phys_addr_t addr) 160 { 161 int off = PCI_BASE_ADDRESS_0 + bar_num * 4; 162 163 pci_config_writel(dev->bdf, off, (uint32_t)addr); 164 165 if (pci_bar_is64(dev, bar_num)) 166 pci_config_writel(dev->bdf, off + 4, 167 (uint32_t)(addr >> 32)); 168 } 169 170 /* 171 * To determine the amount of address space needed by a PCI device, 172 * one must save the original value of the BAR, write a value of 173 * all 1's to the register, and then read it back. The amount of 174 * memory can be then determined by masking the information bits, 175 * performing a bitwise NOT, and incrementing the value by 1. 176 * 177 * The following pci_bar_size_helper() and pci_bar_size() functions 178 * implement the algorithm. 179 */ 180 static uint32_t pci_bar_size_helper(struct pci_dev *dev, int bar_num) 181 { 182 int off = PCI_BASE_ADDRESS_0 + bar_num * 4; 183 uint16_t bdf = dev->bdf; 184 uint32_t bar, val; 185 186 bar = pci_config_readl(bdf, off); 187 pci_config_writel(bdf, off, ~0u); 188 val = pci_config_readl(bdf, off); 189 pci_config_writel(bdf, off, bar); 190 191 return val; 192 } 193 194 phys_addr_t pci_bar_size(struct pci_dev *dev, int bar_num) 195 { 196 uint32_t bar, size; 197 198 size = pci_bar_size_helper(dev, bar_num); 199 if (!size) 200 return 0; 201 202 bar = pci_bar_get(dev, bar_num); 203 size &= pci_bar_mask(bar); 204 205 if (pci_bar_is64(dev, bar_num)) { 206 phys_addr_t size64 = pci_bar_size_helper(dev, bar_num + 1); 207 size64 = (size64 << 32) | size; 208 209 return ~size64 + 1; 210 } else { 211 return ~size + 1; 212 } 213 } 214 215 bool pci_bar_is_memory(struct pci_dev *dev, int bar_num) 216 { 217 uint32_t bar = pci_bar_get(dev, bar_num); 218 219 return !(bar & PCI_BASE_ADDRESS_SPACE_IO); 220 } 221 222 bool pci_bar_is_valid(struct pci_dev *dev, int bar_num) 223 { 224 return pci_bar_get(dev, bar_num); 225 } 226 227 bool pci_bar_is64(struct pci_dev *dev, int bar_num) 228 { 229 uint32_t bar = pci_bar_get(dev, bar_num); 230 231 if (bar & PCI_BASE_ADDRESS_SPACE_IO) 232 return false; 233 234 return (bar & PCI_BASE_ADDRESS_MEM_TYPE_MASK) == 235 PCI_BASE_ADDRESS_MEM_TYPE_64; 236 } 237 238 void pci_bar_print(struct pci_dev *dev, int bar_num) 239 { 240 phys_addr_t size, start, end; 241 uint32_t bar; 242 243 size = pci_bar_size(dev, bar_num); 244 if (!size) 245 return; 246 247 bar = pci_bar_get(dev, bar_num); 248 start = pci_bar_get_addr(dev, bar_num); 249 end = start + size - 1; 250 251 if (pci_bar_is64(dev, bar_num)) { 252 printf("BAR#%d,%d [%" PRIx64 "-%" PRIx64 " ", 253 bar_num, bar_num + 1, start, end); 254 } else { 255 printf("BAR#%d [%02x-%02x ", 256 bar_num, (uint32_t)start, (uint32_t)end); 257 } 258 259 if (bar & PCI_BASE_ADDRESS_SPACE_IO) { 260 printf("PIO"); 261 } else { 262 printf("MEM"); 263 switch (bar & PCI_BASE_ADDRESS_MEM_TYPE_MASK) { 264 case PCI_BASE_ADDRESS_MEM_TYPE_32: 265 printf("32"); 266 break; 267 case PCI_BASE_ADDRESS_MEM_TYPE_1M: 268 printf("1M"); 269 break; 270 case PCI_BASE_ADDRESS_MEM_TYPE_64: 271 printf("64"); 272 break; 273 default: 274 assert(0); 275 } 276 } 277 278 if (bar & PCI_BASE_ADDRESS_MEM_PREFETCH) 279 printf("/p"); 280 281 printf("]"); 282 } 283 284 void pci_dev_print_id(pcidevaddr_t dev) 285 { 286 printf("00.%02x.%1x %04x:%04x", dev / 8, dev % 8, 287 pci_config_readw(dev, PCI_VENDOR_ID), 288 pci_config_readw(dev, PCI_DEVICE_ID)); 289 } 290 291 static void pci_dev_print(pcidevaddr_t dev) 292 { 293 uint8_t header = pci_config_readb(dev, PCI_HEADER_TYPE); 294 uint8_t progif = pci_config_readb(dev, PCI_CLASS_PROG); 295 uint8_t subclass = pci_config_readb(dev, PCI_CLASS_DEVICE); 296 uint8_t class = pci_config_readb(dev, PCI_CLASS_DEVICE + 1); 297 struct pci_dev pci_dev; 298 int i; 299 300 pci_dev_init(&pci_dev, dev); 301 302 pci_dev_print_id(dev); 303 printf(" type %02x progif %02x class %02x subclass %02x\n", 304 header, progif, class, subclass); 305 306 if ((header & PCI_HEADER_TYPE_MASK) != PCI_HEADER_TYPE_NORMAL) 307 return; 308 309 for (i = 0; i < PCI_BAR_NUM; i++) { 310 if (pci_bar_size(&pci_dev, i)) { 311 printf("\t"); 312 pci_bar_print(&pci_dev, i); 313 printf("\n"); 314 } 315 if (pci_bar_is64(&pci_dev, i)) 316 i++; 317 } 318 } 319 320 void pci_print(void) 321 { 322 pcidevaddr_t dev; 323 324 for (dev = 0; dev < PCI_DEVFN_MAX; ++dev) { 325 if (pci_dev_exists(dev)) 326 pci_dev_print(dev); 327 } 328 } 329 330 void pci_scan_bars(struct pci_dev *dev) 331 { 332 int i; 333 334 for (i = 0; i < PCI_BAR_NUM; i++) { 335 if (!pci_bar_is_valid(dev, i)) 336 continue; 337 dev->resource[i] = pci_bar_get_addr(dev, i); 338 if (pci_bar_is64(dev, i)) { 339 i++; 340 dev->resource[i] = (phys_addr_t)0; 341 } 342 } 343 } 344 345 uint8_t pci_intx_line(struct pci_dev *dev) 346 { 347 return pci_config_readb(dev->bdf, PCI_INTERRUPT_LINE); 348 } 349 350 void pci_enable_defaults(struct pci_dev *dev) 351 { 352 pci_scan_bars(dev); 353 /* Enable device DMA operations */ 354 pci_cmd_set_clr(dev, PCI_COMMAND_MASTER, 0); 355 pci_cap_walk(dev); 356 } 357