1 /*- 2 * Copyright (c) 2004, 2005 Jung-uk Kim <jkim@FreeBSD.org> 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 14 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 15 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 17 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 18 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 19 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 20 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 21 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 22 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 23 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 24 * SUCH DAMAGE. 25 */ 26 27 #include <sys/param.h> 28 #include <sys/systm.h> 29 #include <sys/device.h> 30 31 #include <dev/pci/pcivar.h> 32 #include <dev/pci/pcireg.h> 33 #include <dev/pci/agpvar.h> 34 #include <dev/pci/agpreg.h> 35 36 #include <dev/pci/pcidevs.h> 37 38 #include <machine/bus.h> 39 40 /* 41 * AMD64 GART registers 42 */ 43 #define AGP_AMD64_APCTRL 0x90 44 #define AGP_AMD64_APBASE 0x94 45 #define AGP_AMD64_ATTBASE 0x98 46 #define AGP_AMD64_CACHECTRL 0x9c 47 #define AGP_AMD64_APCTRL_GARTEN 0x00000001 48 #define AGP_AMD64_APCTRL_SIZE_MASK 0x0000000e 49 #define AGP_AMD64_APCTRL_DISGARTCPU 0x00000010 50 #define AGP_AMD64_APCTRL_DISGARTIO 0x00000020 51 #define AGP_AMD64_APCTRL_DISWLKPRB 0x00000040 52 #define AGP_AMD64_APBASE_MASK 0x00007fff 53 #define AGP_AMD64_ATTBASE_MASK 0xfffffff0 54 #define AGP_AMD64_CACHECTRL_INVGART 0x00000001 55 #define AGP_AMD64_CACHECTRL_PTEERR 0x00000002 56 57 /* 58 * NVIDIA nForce3 registers 59 */ 60 #define AGP_AMD64_NVIDIA_0_APBASE 0x10 61 #define AGP_AMD64_NVIDIA_1_APBASE1 0x50 62 #define AGP_AMD64_NVIDIA_1_APLIMIT1 0x54 63 #define AGP_AMD64_NVIDIA_1_APSIZE 0xa8 64 #define AGP_AMD64_NVIDIA_1_APBASE2 0xd8 65 #define AGP_AMD64_NVIDIA_1_APLIMIT2 0xdc 66 67 /* 68 * ULi M1689 registers 69 */ 70 #define AGP_AMD64_ULI_APBASE 0x10 71 #define AGP_AMD64_ULI_HTT_FEATURE 0x50 72 #define AGP_AMD64_ULI_ENU_SCR 0x54 73 74 75 #define AMD64_MAX_MCTRL 8 76 77 /* XXX nForce3 requires secondary AGP bridge at 0:11:0. */ 78 #define AGP_AMD64_NVIDIA_PCITAG(pc) pci_make_tag(pc, 0, 11, 0) 79 /* XXX Some VIA bridge requires secondary AGP bridge at 0:1:0. */ 80 #define AGP_AMD64_VIA_PCITAG(pc) pci_make_tag(pc, 0, 1, 0) 81 82 83 int mmuagp_probe(struct device *, void *, void *); 84 void mmuagp_attach(struct device *, struct device *, void *); 85 bus_size_t mmuagp_get_aperture(void *); 86 int mmuagp_set_aperture(void *, bus_size_t); 87 void mmuagp_bind_page(void *, bus_addr_t, paddr_t, int); 88 void mmuagp_unbind_page(void *, bus_addr_t); 89 void mmuagp_flush_tlb(void *); 90 91 void mmuagp_apbase_fixup(void *); 92 93 void mmuagp_uli_init(void *); 94 int mmuagp_uli_set_aperture(void *, bus_size_t); 95 96 int mmuagp_nvidia_match(const struct pci_attach_args *, uint16_t); 97 void mmuagp_nvidia_init(void *); 98 int mmuagp_nvidia_set_aperture(void *, bus_size_t); 99 100 int mmuagp_via_match(const struct pci_attach_args *); 101 void mmuagp_via_init(void *); 102 int mmuagp_via_set_aperture(void *, bus_size_t); 103 104 struct mmuagp_softc { 105 struct device dev; 106 struct agp_softc *agpdev; 107 struct agp_gatt *gatt; 108 bus_addr_t msc_apaddr; 109 bus_size_t msc_apsize; 110 uint32_t apbase; 111 pcitag_t ctrl_tag; /* use NVIDIA and VIA */ 112 pcitag_t mctrl_tag[AMD64_MAX_MCTRL]; 113 pci_chipset_tag_t msc_pc; 114 pcitag_t msc_tag; 115 int n_mctrl; 116 }; 117 118 const struct cfattach mmuagp_ca = { 119 sizeof(struct mmuagp_softc), mmuagp_probe, mmuagp_attach 120 }; 121 122 struct cfdriver mmuagp_cd = { 123 NULL, "mmuagp", DV_DULL 124 }; 125 126 const struct agp_methods mmuagp_methods = { 127 mmuagp_bind_page, 128 mmuagp_unbind_page, 129 mmuagp_flush_tlb, 130 }; 131 132 int 133 mmuagp_probe(struct device *parent, void *match, void *aux) 134 { 135 struct agp_attach_args *aa = aux; 136 struct pci_attach_args *pa = aa->aa_pa; 137 138 /* Must be a pchb, don't attach to iommu-style agp devs */ 139 if (agpbus_probe(aa) == 0) 140 return (0); 141 142 switch (PCI_VENDOR(pa->pa_id)) { 143 case PCI_VENDOR_ALI: 144 switch (PCI_PRODUCT(pa->pa_id)) { 145 case PCI_PRODUCT_ALI_M1689: 146 return (1); 147 } 148 break; 149 case PCI_VENDOR_AMD: 150 switch (PCI_PRODUCT(pa->pa_id)) { 151 case PCI_PRODUCT_AMD_8151_SC: 152 return (1); 153 } 154 break; 155 case PCI_VENDOR_NVIDIA: 156 switch (PCI_PRODUCT(pa->pa_id)) { 157 case PCI_PRODUCT_NVIDIA_NFORCE3_PCHB: 158 return (mmuagp_nvidia_match(pa, 159 PCI_PRODUCT_NVIDIA_NFORCE3_PPB2)); 160 /* NOTREACHED */ 161 case PCI_PRODUCT_NVIDIA_NFORCE3_250_PCHB: 162 return (mmuagp_nvidia_match(pa, 163 PCI_PRODUCT_NVIDIA_NFORCE3_250_AGP)); 164 /* NOTREACHED */ 165 } 166 break; 167 case PCI_VENDOR_SIS: 168 switch (PCI_PRODUCT(pa->pa_id)) { 169 case PCI_PRODUCT_SIS_755: 170 case PCI_PRODUCT_SIS_760: 171 return (1); 172 } 173 break; 174 case PCI_VENDOR_VIATECH: 175 switch (PCI_PRODUCT(pa->pa_id)) { 176 case PCI_PRODUCT_VIATECH_K8M800_0: 177 case PCI_PRODUCT_VIATECH_K8T890_0: 178 case PCI_PRODUCT_VIATECH_K8HTB_0: 179 case PCI_PRODUCT_VIATECH_K8HTB: 180 return (1); 181 } 182 break; 183 } 184 185 return (0); 186 } 187 188 int 189 mmuagp_nvidia_match(const struct pci_attach_args *pa, uint16_t devid) 190 { 191 pcitag_t tag; 192 pcireg_t reg; 193 194 tag = AGP_AMD64_NVIDIA_PCITAG(pa->pa_pc); 195 196 reg = pci_conf_read(pa->pa_pc, tag, PCI_CLASS_REG); 197 if (PCI_CLASS(reg) != PCI_CLASS_BRIDGE || 198 PCI_SUBCLASS(reg) != PCI_SUBCLASS_BRIDGE_PCI) 199 return 0; 200 201 reg = pci_conf_read(pa->pa_pc, tag, PCI_ID_REG); 202 if (PCI_VENDOR(reg) != PCI_VENDOR_NVIDIA || PCI_PRODUCT(reg) != devid) 203 return 0; 204 205 return 1; 206 } 207 208 int 209 mmuagp_via_match(const struct pci_attach_args *pa) 210 { 211 pcitag_t tag; 212 pcireg_t reg; 213 214 tag = AGP_AMD64_VIA_PCITAG(pa->pa_pc); 215 216 reg = pci_conf_read(pa->pa_pc, tag, PCI_CLASS_REG); 217 if (PCI_CLASS(reg) != PCI_CLASS_BRIDGE || 218 PCI_SUBCLASS(reg) != PCI_SUBCLASS_BRIDGE_PCI) 219 return 0; 220 221 reg = pci_conf_read(pa->pa_pc, tag, PCI_ID_REG); 222 if (PCI_VENDOR(reg) != PCI_VENDOR_VIATECH || 223 PCI_PRODUCT(reg) != PCI_PRODUCT_VIATECH_K8HTB_AGP) 224 return 0; 225 226 return 1; 227 } 228 229 void 230 mmuagp_attach(struct device *parent, struct device *self, void *aux) 231 { 232 struct mmuagp_softc *msc = (struct mmuagp_softc *)self ; 233 struct agp_attach_args *aa = aux; 234 struct pci_attach_args *pa = aa->aa_pa; 235 struct agp_gatt *gatt; 236 int (*set_aperture)(void *, bus_size_t) = NULL; 237 pcireg_t id, attbase, apctrl; 238 pcitag_t tag; 239 int maxdevs, i, n; 240 241 if (pci_mapreg_info(pa->pa_pc, pa->pa_tag, AGP_APBASE, 242 PCI_MAPREG_TYPE_MEM, &msc->msc_apaddr, NULL, NULL) != 0) { 243 printf(": can't get aperture info\n"); 244 return; 245 } 246 247 msc->msc_pc = pa->pa_pc; 248 msc->msc_tag = pa->pa_tag; 249 250 maxdevs = pci_bus_maxdevs(pa->pa_pc, 0); 251 for (i = 0, n = 0; i < maxdevs && n < AMD64_MAX_MCTRL; i++) { 252 tag = pci_make_tag(pa->pa_pc, 0, i, 3); 253 id = pci_conf_read(pa->pa_pc, tag, PCI_ID_REG); 254 if (PCI_VENDOR(id) == PCI_VENDOR_AMD && 255 PCI_PRODUCT(id) == PCI_PRODUCT_AMD_0F_MISC) { 256 msc->mctrl_tag[n] = tag; 257 n++; 258 } 259 } 260 if (n == 0) { 261 printf(": no Miscellaneous Control units found\n"); 262 return; 263 } 264 msc->n_mctrl = n; 265 266 printf(": %d Miscellaneous Control unit(s) found", msc->n_mctrl); 267 268 msc->msc_apsize = mmuagp_get_aperture(msc); 269 270 for (;;) { 271 gatt = agp_alloc_gatt(pa->pa_dmat, msc->msc_apsize); 272 if (gatt != NULL) 273 break; 274 275 /* 276 * Probably failed to alloc contiguous memory. Try reducing the 277 * aperture so that the gatt size reduces. 278 */ 279 msc->msc_apsize /= 2; 280 if (mmuagp_set_aperture(msc, msc->msc_apsize)) { 281 printf(" can't set aperture size\n"); 282 return; 283 } 284 } 285 msc->gatt = gatt; 286 287 switch (PCI_VENDOR(pa->pa_id)) { 288 case PCI_VENDOR_ALI: 289 mmuagp_uli_init(msc); 290 set_aperture = mmuagp_uli_set_aperture; 291 break; 292 293 case PCI_VENDOR_NVIDIA: 294 msc->ctrl_tag = AGP_AMD64_NVIDIA_PCITAG(pa->pa_pc); 295 mmuagp_nvidia_init(msc); 296 set_aperture = mmuagp_nvidia_set_aperture; 297 break; 298 299 case PCI_VENDOR_VIATECH: 300 /* do we have to set the extra bridge too? */ 301 if (mmuagp_via_match(pa)) { 302 msc->ctrl_tag = AGP_AMD64_VIA_PCITAG(pa->pa_pc); 303 mmuagp_via_init(msc); 304 set_aperture = mmuagp_via_set_aperture; 305 } 306 break; 307 } 308 309 if (set_aperture != NULL) { 310 if ((*set_aperture)(msc, msc->msc_apsize)) { 311 printf(", failed aperture set\n"); 312 return; 313 } 314 } 315 316 /* Install the gatt and enable aperture. */ 317 attbase = (uint32_t)(gatt->ag_physical >> 8) & AGP_AMD64_ATTBASE_MASK; 318 for (i = 0; i < msc->n_mctrl; i++) { 319 pci_conf_write(pa->pa_pc, msc->mctrl_tag[i], AGP_AMD64_ATTBASE, 320 attbase); 321 apctrl = pci_conf_read(pa->pa_pc, msc->mctrl_tag[i], 322 AGP_AMD64_APCTRL); 323 apctrl |= AGP_AMD64_APCTRL_GARTEN; 324 apctrl &= 325 ~(AGP_AMD64_APCTRL_DISGARTCPU | AGP_AMD64_APCTRL_DISGARTIO); 326 pci_conf_write(pa->pa_pc, msc->mctrl_tag[i], AGP_AMD64_APCTRL, 327 apctrl); 328 } 329 330 agp_flush_cache(); 331 332 msc->agpdev = (struct agp_softc *)agp_attach_bus(pa, &mmuagp_methods, 333 msc->msc_apaddr, msc->msc_apsize, &msc->dev); 334 return; 335 } 336 337 338 static bus_size_t mmuagp_table[] = { 339 0x02000000, /* 32 MB */ 340 0x04000000, /* 64 MB */ 341 0x08000000, /* 128 MB */ 342 0x10000000, /* 256 MB */ 343 0x20000000, /* 512 MB */ 344 0x40000000, /* 1024 MB */ 345 0x80000000, /* 2048 MB */ 346 }; 347 348 #define AGP_AMD64_TABLE_SIZE \ 349 (sizeof(mmuagp_table) / sizeof(mmuagp_table[0])) 350 351 bus_size_t 352 mmuagp_get_aperture(void *sc) 353 { 354 struct mmuagp_softc *msc = sc; 355 uint32_t i; 356 357 i = (pci_conf_read(msc->msc_pc, msc->mctrl_tag[0], AGP_AMD64_APCTRL) & 358 AGP_AMD64_APCTRL_SIZE_MASK) >> 1; 359 360 if (i >= AGP_AMD64_TABLE_SIZE) 361 return 0; 362 363 return mmuagp_table[i]; 364 } 365 366 int 367 mmuagp_set_aperture(void *sc, bus_size_t aperture) 368 { 369 struct mmuagp_softc *msc = sc; 370 uint32_t i; 371 pcireg_t apctrl; 372 int j; 373 374 for (i = 0; i < AGP_AMD64_TABLE_SIZE; i++) 375 if (mmuagp_table[i] == aperture) 376 break; 377 if (i >= AGP_AMD64_TABLE_SIZE) 378 return (EINVAL); 379 380 for (j = 0; j < msc->n_mctrl; j++) { 381 apctrl = pci_conf_read(msc->msc_pc, msc->mctrl_tag[0], 382 AGP_AMD64_APCTRL); 383 pci_conf_write(msc->msc_pc, msc->mctrl_tag[0], AGP_AMD64_APCTRL, 384 (apctrl & ~(AGP_AMD64_APCTRL_SIZE_MASK)) | (i << 1)); 385 } 386 387 return (0); 388 } 389 390 void 391 mmuagp_bind_page(void *sc, bus_addr_t offset, paddr_t physical, int flags) 392 { 393 struct mmuagp_softc *msc = sc; 394 395 msc->gatt->ag_virtual[(offset - msc->msc_apaddr) >> AGP_PAGE_SHIFT] = 396 (physical & 0xfffff000) | ((physical >> 28) & 0x00000ff0) | 3; 397 } 398 399 void 400 mmuagp_unbind_page(void *sc, bus_addr_t offset) 401 { 402 struct mmuagp_softc *msc = sc; 403 404 msc->gatt->ag_virtual[(offset - msc->msc_apaddr) >> AGP_PAGE_SHIFT] = 0; 405 } 406 407 void 408 mmuagp_flush_tlb(void *sc) 409 { 410 struct mmuagp_softc *msc = sc; 411 pcireg_t cachectrl; 412 int i; 413 414 for (i = 0; i < msc->n_mctrl; i++) { 415 cachectrl = pci_conf_read(msc->msc_pc, msc->mctrl_tag[i], 416 AGP_AMD64_CACHECTRL); 417 pci_conf_write(msc->msc_pc, msc->mctrl_tag[i], 418 AGP_AMD64_CACHECTRL, 419 cachectrl | AGP_AMD64_CACHECTRL_INVGART); 420 } 421 } 422 423 void 424 mmuagp_apbase_fixup(void *sc) 425 { 426 struct mmuagp_softc *msc = sc; 427 uint32_t apbase; 428 int i; 429 430 apbase = pci_conf_read(msc->msc_pc, msc->msc_tag, AGP_APBASE); 431 msc->apbase = PCI_MAPREG_MEM_ADDR(apbase); 432 apbase = (msc->apbase >> 25) & AGP_AMD64_APBASE_MASK; 433 for (i = 0; i < msc->n_mctrl; i++) 434 pci_conf_write(msc->msc_pc, msc->mctrl_tag[i], AGP_AMD64_APBASE, 435 apbase); 436 } 437 438 void 439 mmuagp_uli_init(void *sc) 440 { 441 struct mmuagp_softc *msc = sc; 442 pcireg_t apbase; 443 444 mmuagp_apbase_fixup(msc); 445 apbase = pci_conf_read(msc->msc_pc, msc->msc_tag, 446 AGP_AMD64_ULI_APBASE); 447 pci_conf_write(msc->msc_pc, msc->msc_tag, AGP_AMD64_ULI_APBASE, 448 (apbase & 0x0000000f) | msc->apbase); 449 pci_conf_write(msc->msc_pc, msc->msc_tag, AGP_AMD64_ULI_HTT_FEATURE, 450 msc->apbase); 451 } 452 453 int 454 mmuagp_uli_set_aperture(void *sc, bus_size_t aperture) 455 { 456 struct mmuagp_softc *msc = sc; 457 458 switch (aperture) { 459 case 0x02000000: /* 32 MB */ 460 case 0x04000000: /* 64 MB */ 461 case 0x08000000: /* 128 MB */ 462 case 0x10000000: /* 256 MB */ 463 break; 464 default: 465 return EINVAL; 466 } 467 468 pci_conf_write(msc->msc_pc, msc->msc_tag, AGP_AMD64_ULI_ENU_SCR, 469 msc->apbase + aperture - 1); 470 471 return 0; 472 } 473 474 void 475 mmuagp_nvidia_init(void *sc) 476 { 477 struct mmuagp_softc *msc = sc; 478 pcireg_t apbase; 479 480 mmuagp_apbase_fixup(msc); 481 apbase = pci_conf_read(msc->msc_pc, msc->msc_tag, 482 AGP_AMD64_NVIDIA_0_APBASE); 483 pci_conf_write(msc->msc_pc, msc->msc_tag, AGP_AMD64_NVIDIA_0_APBASE, 484 (apbase & 0x0000000f) | msc->apbase); 485 pci_conf_write(msc->msc_pc, msc->ctrl_tag, AGP_AMD64_NVIDIA_1_APBASE1, 486 msc->apbase); 487 pci_conf_write(msc->msc_pc, msc->ctrl_tag, AGP_AMD64_NVIDIA_1_APBASE2, 488 msc->apbase); 489 } 490 491 int 492 mmuagp_nvidia_set_aperture(void *sc, bus_size_t aperture) 493 { 494 struct mmuagp_softc *msc = sc; 495 bus_size_t apsize; 496 497 switch (aperture) { 498 case 0x02000000: /* 32 MB */ 499 apsize = 0x0f; 500 break; 501 case 0x04000000: /* 64 MB */ 502 apsize = 0x0e; 503 break; 504 case 0x08000000: /* 128 MB */ 505 apsize = 0x0c; 506 break; 507 case 0x10000000: /* 256 MB */ 508 apsize = 0x08; 509 break; 510 case 0x20000000: /* 512 MB */ 511 apsize = 0x00; 512 break; 513 default: 514 return (EINVAL); 515 } 516 517 pci_conf_write(msc->msc_pc, msc->ctrl_tag, AGP_AMD64_NVIDIA_1_APSIZE, 518 (pci_conf_read(msc->msc_pc, msc->ctrl_tag, 519 AGP_AMD64_NVIDIA_1_APSIZE) & 0xfffffff0) | apsize); 520 pci_conf_write(msc->msc_pc, msc->ctrl_tag, AGP_AMD64_NVIDIA_1_APLIMIT1, 521 msc->apbase + aperture - 1); 522 pci_conf_write(msc->msc_pc, msc->ctrl_tag, AGP_AMD64_NVIDIA_1_APLIMIT2, 523 msc->apbase + aperture - 1); 524 525 return (0); 526 } 527 528 void 529 mmuagp_via_init(void *sc) 530 { 531 struct mmuagp_softc *msc = sc; 532 533 mmuagp_apbase_fixup(sc); 534 pci_conf_write(msc->msc_pc, msc->ctrl_tag, AGP3_VIA_ATTBASE, 535 msc->gatt->ag_physical); 536 pci_conf_write(msc->msc_pc, msc->ctrl_tag, AGP3_VIA_GARTCTRL, 537 pci_conf_read(msc->msc_pc, msc->ctrl_tag, AGP3_VIA_ATTBASE) | 538 0x180); 539 } 540 541 int 542 mmuagp_via_set_aperture(void *sc, bus_size_t aperture) 543 { 544 struct mmuagp_softc *msc = sc; 545 bus_size_t apsize; 546 547 apsize = ((aperture - 1) >> 20) ^ 0xff; 548 if ((((apsize ^ 0xff) << 20) | ((1 << 20) - 1)) + 1 != aperture) 549 return (EINVAL); 550 pci_conf_write(msc->msc_pc, msc->ctrl_tag, AGP3_VIA_APSIZE, 551 (pci_conf_read(msc->msc_pc, msc->ctrl_tag, AGP3_VIA_APSIZE) & 552 ~0xff) | apsize); 553 554 return 0; 555 } 556