1 /*- 2 * Copyright (c) 2005 Poul-Henning Kamp 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 * $FreeBSD: src/sys/dev/acpica/acpi_hpet.c,v 1.12.2.1.2.1 2008/11/25 02:59:29 kensmith Exp $ 27 */ 28 29 #include "opt_acpi.h" 30 31 #include <sys/param.h> 32 #include <sys/bus.h> 33 #include <sys/kernel.h> 34 #include <sys/module.h> 35 #include <sys/systimer.h> 36 #include <sys/rman.h> 37 38 #if !defined(KLD_MODULE) 39 #include <machine/pmap.h> 40 #endif 41 42 #include "acpi.h" 43 #include "accommon.h" 44 #include "acpivar.h" 45 #include "acpi_hpet.h" 46 47 #if !defined(KLD_MODULE) 48 #include <platform/pc64/acpica/acpi_sdt_var.h> 49 #endif 50 51 /* Hooks for the ACPICA debugging infrastructure */ 52 #define _COMPONENT ACPI_TIMER 53 ACPI_MODULE_NAME("HPET") 54 55 static bus_space_handle_t acpi_hpet_bsh; 56 static bus_space_tag_t acpi_hpet_bst; 57 static u_long acpi_hpet_res_start; 58 59 struct acpi_hpet_softc { 60 device_t dev; 61 struct resource *mem_res; 62 ACPI_HANDLE handle; 63 }; 64 65 #define DEV_HPET(x) (acpi_get_magic(x) == (uintptr_t)&acpi_hpet_devclass) 66 67 static sysclock_t acpi_hpet_get_timecount(void); 68 static void acpi_hpet_construct(struct cputimer *, sysclock_t); 69 70 static int acpi_hpet_identify(driver_t *, device_t); 71 static int acpi_hpet_probe(device_t); 72 static int acpi_hpet_attach(device_t); 73 static int acpi_hpet_resume(device_t); 74 static int acpi_hpet_suspend(device_t); 75 76 static void acpi_hpet_test(struct acpi_hpet_softc *sc); 77 static u_int acpi_hpet_read(void); 78 static void acpi_hpet_enable(struct acpi_hpet_softc *); 79 static void acpi_hpet_disable(struct acpi_hpet_softc *); 80 81 static char *hpet_ids[] = { "PNP0103", NULL }; 82 83 static struct cputimer acpi_hpet_timer = { 84 .next = SLIST_ENTRY_INITIALIZER, 85 .name = "HPET", 86 .pri = CPUTIMER_PRI_HPET, 87 .type = CPUTIMER_HPET, 88 .count = acpi_hpet_get_timecount, 89 .fromhz = cputimer_default_fromhz, 90 .fromus = cputimer_default_fromus, 91 .construct = acpi_hpet_construct, 92 .destruct = cputimer_default_destruct, 93 .freq = 0 /* determined later */ 94 }; 95 96 static device_method_t acpi_hpet_methods[] = { 97 DEVMETHOD(device_identify, acpi_hpet_identify), 98 DEVMETHOD(device_probe, acpi_hpet_probe), 99 DEVMETHOD(device_attach, acpi_hpet_attach), 100 DEVMETHOD(device_suspend, acpi_hpet_suspend), 101 DEVMETHOD(device_resume, acpi_hpet_resume), 102 DEVMETHOD_END 103 }; 104 105 static driver_t acpi_hpet_driver = { 106 "acpi_hpet", 107 acpi_hpet_methods, 108 sizeof(struct acpi_hpet_softc), 109 .gpri = KOBJ_GPRI_ACPI+2 110 }; 111 112 static devclass_t acpi_hpet_devclass; 113 DRIVER_MODULE(acpi_hpet, acpi, acpi_hpet_driver, acpi_hpet_devclass, NULL, NULL); 114 MODULE_DEPEND(acpi_hpet, acpi, 1, 1, 1); 115 116 static u_int 117 acpi_hpet_read(void) 118 { 119 return bus_space_read_4(acpi_hpet_bst, acpi_hpet_bsh, 120 HPET_MAIN_COUNTER); 121 } 122 123 #if !defined(KLD_MODULE) 124 extern int i8254_cputimer_disable; 125 126 static vm_offset_t ptr = 0; 127 128 static int acpi_hpet_for_calibration = 1; 129 TUNABLE_INT("hw.calibrate_timers_with_hpet", &acpi_hpet_for_calibration); 130 131 static sysclock_t 132 acpi_hpet_early_get_timecount(void) 133 { 134 return readl(ptr + HPET_MAIN_COUNTER) + acpi_hpet_timer.base; 135 } 136 137 static void 138 acpi_hpet_early_construct(struct cputimer *timer, sysclock_t oldclock) 139 { 140 uint32_t val; 141 142 val = readl(ptr + HPET_CONFIG); 143 writel(ptr + HPET_CONFIG, val | HPET_CNF_ENABLE); 144 145 timer->base = 0; 146 timer->base = oldclock - acpi_hpet_early_get_timecount(); 147 } 148 149 static void 150 acpi_hpet_early_destruct(struct cputimer *timer) 151 { 152 uint32_t val; 153 154 val = readl(ptr + HPET_CONFIG); 155 writel(ptr + HPET_CONFIG, val & ~HPET_CNF_ENABLE); 156 } 157 158 static int 159 acpi_hpet_early_init(void) 160 { 161 uintmax_t freq; 162 uint64_t old_tsc, new_tsc; 163 uint32_t val, val2; 164 165 val = readl(ptr + HPET_CONFIG); 166 writel(ptr + HPET_CONFIG, val | HPET_CNF_ENABLE); 167 168 /* Read basic statistics about the timer. */ 169 val = readl(ptr + HPET_PERIOD); 170 if (val == 0) { 171 kprintf("acpi_hpet: invalid period\n"); 172 val = readl(ptr + HPET_CONFIG); 173 writel(ptr + HPET_CONFIG, val & ~HPET_CNF_ENABLE); 174 return ENXIO; 175 } 176 177 freq = (1000000000000000LL + val / 2) / val; 178 if (bootverbose) { 179 val = readl(ptr + HPET_CAPABILITIES); 180 kprintf("acpi_hpet: " 181 "vend: 0x%x, rev: 0x%x, num: %d, opts:%s%s\n", 182 val >> 16, val & HPET_CAP_REV_ID, 183 (val & HPET_CAP_NUM_TIM) >> 8, 184 (val & HPET_CAP_LEG_RT) ? " legacy_route" : "", 185 (val & HPET_CAP_COUNT_SIZE) ? " 64-bit" : ""); 186 } 187 188 #if 0 189 if (ktestenv("debug.acpi.hpet_test")) 190 acpi_hpet_test(sc); 191 #endif 192 193 /* 194 * Don't attach if the timer never increments. Since the spec 195 * requires it to be at least 10 MHz, it has to change in 1 us. 196 */ 197 val = readl(ptr + HPET_MAIN_COUNTER); 198 /* This delay correspond to 1us, even at 6 GHz TSC. */ 199 old_tsc = rdtsc(); 200 do { 201 cpu_pause(); 202 new_tsc = rdtsc(); 203 } while (new_tsc - old_tsc < 6000); 204 val2 = readl(ptr + HPET_MAIN_COUNTER); 205 if (val == val2) { 206 kprintf("acpi_hpet: HPET never increments, disabling\n"); 207 val = readl(ptr + HPET_CONFIG); 208 writel(ptr + HPET_CONFIG, val & ~HPET_CNF_ENABLE); 209 return ENXIO; 210 } 211 212 val = readl(ptr + HPET_CONFIG); 213 writel(ptr + HPET_CONFIG, val & ~HPET_CNF_ENABLE); 214 acpi_hpet_timer.freq = freq; 215 kprintf("acpi_hpet: frequency %u\n", acpi_hpet_timer.freq); 216 217 acpi_hpet_timer.count = acpi_hpet_early_get_timecount; 218 acpi_hpet_timer.construct = acpi_hpet_early_construct; 219 acpi_hpet_timer.destruct = acpi_hpet_early_destruct; 220 221 cputimer_register(&acpi_hpet_timer); 222 cputimer_select(&acpi_hpet_timer, 0); 223 return 0; 224 } 225 226 static void 227 acpi_hpet_cputimer_register(void) 228 { 229 ACPI_TABLE_HPET *hpet; 230 vm_paddr_t hpet_paddr; 231 232 if (acpi_hpet_for_calibration == 0) 233 return; 234 235 if (acpi_disabled("hpet")) 236 return; 237 238 hpet_paddr = sdt_search(ACPI_SIG_HPET); 239 if (hpet_paddr == 0) { 240 if (bootverbose) 241 kprintf("acpi_hpet: can't locate HPET\n"); 242 return; 243 } 244 245 hpet = sdt_sdth_map(hpet_paddr); 246 if (hpet == NULL) 247 return; 248 249 if (hpet->Header.Length < 56) { 250 kprintf("acpi_hpet: HPET table too short. Length: 0x%x\n", 251 hpet->Header.Length); 252 return; 253 } 254 255 if (hpet->Sequence != 0) { 256 kprintf("acpi_hpet: " 257 "HPET table Sequence not 0. Sequence: 0x%x\n", hpet->Id); 258 goto done; 259 } 260 261 acpi_hpet_res_start = hpet->Address.Address; 262 if (acpi_hpet_res_start == 0) 263 goto done; 264 265 ptr = (vm_offset_t)pmap_mapdev(acpi_hpet_res_start, HPET_MEM_WIDTH); 266 if (acpi_hpet_early_init() == 0) { 267 i8254_cputimer_disable = 1; 268 } else { 269 pmap_unmapdev(ptr, HPET_MEM_WIDTH); 270 ptr = 0; 271 } 272 273 done: 274 sdt_sdth_unmap(&hpet->Header); 275 return; 276 } 277 278 TIMECOUNTER_INIT(acpi_hpet_init, acpi_hpet_cputimer_register); 279 #endif 280 281 /* 282 * Locate the ACPI timer using the FADT, set up and allocate the I/O resources 283 * we will be using. 284 */ 285 static int 286 acpi_hpet_identify(driver_t *driver, device_t parent) 287 { 288 ACPI_TABLE_HPET *hpet; 289 ACPI_TABLE_HEADER *hdr; 290 ACPI_STATUS status; 291 device_t child; 292 293 /* 294 * Just try once, do nothing if the 'acpi' bus is rescanned. 295 */ 296 if (device_get_state(parent) == DS_ATTACHED) 297 return 0; 298 299 ACPI_FUNCTION_TRACE((char *)(uintptr_t) __func__); 300 301 /* Only one HPET device can be added. */ 302 if (devclass_get_device(acpi_hpet_devclass, 0)) 303 return ENXIO; 304 305 #if !defined(KLD_MODULE) 306 if (ptr != 0) { 307 /* Use data from early boot for attachment. */ 308 child = BUS_ADD_CHILD(parent, parent, 0, "acpi_hpet", 0); 309 if (child == NULL) { 310 device_printf(parent, "%s: can't add acpi_hpet0\n", 311 __func__); 312 return ENXIO; 313 } 314 315 /* Record a magic value so we can detect this device later. */ 316 acpi_set_magic(child, (uintptr_t)&acpi_hpet_devclass); 317 318 if (bus_set_resource(child, SYS_RES_MEMORY, 0, 319 acpi_hpet_res_start, HPET_MEM_WIDTH, -1)) { 320 device_printf(child, 321 "could not set iomem resources: 0x%jx, %d\n", 322 (uintmax_t)acpi_hpet_res_start, HPET_MEM_WIDTH); 323 return ENOMEM; 324 } 325 326 return 0; 327 } 328 #endif 329 330 /* Currently, ID and minimum clock tick info is unused. */ 331 332 status = AcpiGetTable(ACPI_SIG_HPET, 1, &hdr); 333 if (ACPI_FAILURE(status)) 334 return ENXIO; 335 336 /* 337 * The unit number could be derived from hdr->Sequence but we only 338 * support one HPET device. 339 */ 340 hpet = (ACPI_TABLE_HPET *)hdr; 341 if (hpet->Sequence != 0) { 342 kprintf("ACPI HPET table warning: Sequence is non-zero (%d)\n", 343 hpet->Sequence); 344 } 345 346 child = BUS_ADD_CHILD(parent, parent, 0, "acpi_hpet", 0); 347 if (child == NULL) { 348 device_printf(parent, "%s: can't add acpi_hpet0\n", __func__); 349 return ENXIO; 350 } 351 352 /* Record a magic value so we can detect this device later. */ 353 acpi_set_magic(child, (uintptr_t)&acpi_hpet_devclass); 354 355 acpi_hpet_res_start = hpet->Address.Address; 356 if (bus_set_resource(child, SYS_RES_MEMORY, 0, 357 hpet->Address.Address, HPET_MEM_WIDTH, -1)) { 358 device_printf(child, "could not set iomem resources: " 359 "0x%jx, %d\n", (uintmax_t)hpet->Address.Address, 360 HPET_MEM_WIDTH); 361 return ENOMEM; 362 } 363 return 0; 364 } 365 366 static int 367 acpi_hpet_probe(device_t dev) 368 { 369 ACPI_FUNCTION_TRACE((char *)(uintptr_t) __func__); 370 371 if (acpi_disabled("hpet")) 372 return ENXIO; 373 374 if (!DEV_HPET(dev) && 375 (ACPI_ID_PROBE(device_get_parent(dev), dev, hpet_ids) == NULL || 376 device_get_unit(dev) != 0)) 377 return ENXIO; 378 379 device_set_desc(dev, "High Precision Event Timer"); 380 return 0; 381 } 382 383 static int 384 acpi_hpet_attach(device_t dev) 385 { 386 struct acpi_hpet_softc *sc; 387 int rid; 388 uint32_t val, val2; 389 uintmax_t freq; 390 391 ACPI_FUNCTION_TRACE((char *)(uintptr_t) __func__); 392 393 sc = device_get_softc(dev); 394 sc->dev = dev; 395 sc->handle = acpi_get_handle(dev); 396 397 rid = 0; 398 sc->mem_res = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid, 399 RF_ACTIVE); 400 if (sc->mem_res == NULL) { 401 /* 402 * We only need to make sure that main counter 403 * is accessable. 404 */ 405 device_printf(dev, "can't map %dB register space, try %dB\n", 406 HPET_MEM_WIDTH, HPET_MEM_WIDTH_MIN); 407 rid = 0; 408 sc->mem_res = bus_alloc_resource(dev, SYS_RES_MEMORY, &rid, 409 acpi_hpet_res_start, 410 acpi_hpet_res_start + HPET_MEM_WIDTH_MIN - 1, 411 HPET_MEM_WIDTH_MIN, RF_ACTIVE); 412 if (sc->mem_res == NULL) 413 return ENOMEM; 414 } 415 416 /* Validate that we can access the whole region. */ 417 if (rman_get_size(sc->mem_res) < HPET_MEM_WIDTH_MIN) { 418 device_printf(dev, "memory region width %ld too small\n", 419 rman_get_size(sc->mem_res)); 420 bus_release_resource(dev, SYS_RES_MEMORY, rid, sc->mem_res); 421 return ENXIO; 422 } 423 424 acpi_hpet_bsh = rman_get_bushandle(sc->mem_res); 425 acpi_hpet_bst = rman_get_bustag(sc->mem_res); 426 427 #if !defined(KLD_MODULE) 428 if (ptr != 0) { 429 /* Use data from early boot for attachment. */ 430 if (ktestenv("debug.acpi.hpet_test")) 431 acpi_hpet_test(sc); 432 return 0; 433 } 434 #endif 435 436 /* Be sure timer is enabled. */ 437 acpi_hpet_enable(sc); 438 439 /* Read basic statistics about the timer. */ 440 val = bus_space_read_4(acpi_hpet_bst, acpi_hpet_bsh, HPET_PERIOD); 441 if (val == 0) { 442 device_printf(dev, "invalid period\n"); 443 acpi_hpet_disable(sc); 444 bus_release_resource(dev, SYS_RES_MEMORY, rid, sc->mem_res); 445 return ENXIO; 446 } 447 448 freq = (1000000000000000LL + val / 2) / val; 449 if (bootverbose) { 450 val = bus_space_read_4(acpi_hpet_bst, acpi_hpet_bsh, 451 HPET_CAPABILITIES); 452 device_printf(dev, 453 "vend: 0x%x, rev: 0x%x, num: %d, opts:%s%s\n", 454 val >> 16, val & HPET_CAP_REV_ID, 455 (val & HPET_CAP_NUM_TIM) >> 8, 456 (val & HPET_CAP_LEG_RT) ? " legacy_route" : "", 457 (val & HPET_CAP_COUNT_SIZE) ? " 64-bit" : ""); 458 } 459 460 if (ktestenv("debug.acpi.hpet_test")) 461 acpi_hpet_test(sc); 462 463 /* 464 * Don't attach if the timer never increments. Since the spec 465 * requires it to be at least 10 MHz, it has to change in 1 us. 466 */ 467 val = bus_space_read_4(acpi_hpet_bst, acpi_hpet_bsh, 468 HPET_MAIN_COUNTER); 469 DELAY(1); 470 val2 = bus_space_read_4(acpi_hpet_bst, acpi_hpet_bsh, 471 HPET_MAIN_COUNTER); 472 if (val == val2) { 473 device_printf(dev, "HPET never increments, disabling\n"); 474 acpi_hpet_disable(sc); 475 bus_release_resource(dev, SYS_RES_MEMORY, rid, sc->mem_res); 476 return ENXIO; 477 } 478 479 acpi_hpet_timer.freq = freq; 480 device_printf(dev, "frequency %u\n", acpi_hpet_timer.freq); 481 482 cputimer_register(&acpi_hpet_timer); 483 cputimer_select(&acpi_hpet_timer, 0); 484 485 return 0; 486 } 487 488 /* 489 * Construct the timer. Adjust the base so the system clock does not 490 * jump weirdly. 491 */ 492 static void 493 acpi_hpet_construct(struct cputimer *timer, sysclock_t oldclock) 494 { 495 timer->base = 0; 496 timer->base = oldclock - acpi_hpet_get_timecount(); 497 } 498 499 static sysclock_t 500 acpi_hpet_get_timecount(void) 501 { 502 return acpi_hpet_read() + acpi_hpet_timer.base; 503 } 504 505 static void 506 acpi_hpet_enable(struct acpi_hpet_softc *sc) 507 { 508 uint32_t val; 509 510 val = bus_space_read_4(acpi_hpet_bst, acpi_hpet_bsh, HPET_CONFIG); 511 bus_space_write_4(acpi_hpet_bst, acpi_hpet_bsh, HPET_CONFIG, 512 val | HPET_CNF_ENABLE); 513 } 514 515 static void 516 acpi_hpet_disable(struct acpi_hpet_softc *sc) 517 { 518 uint32_t val; 519 520 val = bus_space_read_4(acpi_hpet_bst, acpi_hpet_bsh, HPET_CONFIG); 521 bus_space_write_4(acpi_hpet_bst, acpi_hpet_bsh, HPET_CONFIG, 522 val & ~HPET_CNF_ENABLE); 523 } 524 525 static int 526 acpi_hpet_suspend(device_t dev) 527 { 528 /* 529 * According to IA-PC HPET specification rev 1.0a 530 * 531 * Page 10, 2.3.3: 532 * "1. The Event Timer registers (including the main counter) 533 * are not expected to be preserved through an S3, S4, or S5 534 * state." 535 * 536 * Page 11, 2.3.3: 537 * "3. The main counter is permitted, but not required, to run 538 * during S1 or S2 states. ..." 539 * 540 * These mean we are not allowed to enter any of Sx states, 541 * if HPET is used as the sys_cputimer. 542 */ 543 if (sys_cputimer != &acpi_hpet_timer) { 544 struct acpi_hpet_softc *sc; 545 546 sc = device_get_softc(dev); 547 acpi_hpet_disable(sc); 548 549 return 0; 550 } else { 551 return EOPNOTSUPP; 552 } 553 } 554 555 static int 556 acpi_hpet_resume(device_t dev) 557 { 558 if (sys_cputimer != &acpi_hpet_timer) { 559 struct acpi_hpet_softc *sc; 560 561 sc = device_get_softc(dev); 562 acpi_hpet_enable(sc); 563 } 564 return 0; 565 } 566 567 /* Print some basic latency/rate information to assist in debugging. */ 568 static void 569 acpi_hpet_test(struct acpi_hpet_softc *sc) 570 { 571 int i; 572 uint32_t u1, u2; 573 struct timeval b0, b1, b2; 574 struct timespec ts; 575 576 microuptime(&b0); 577 microuptime(&b0); 578 microuptime(&b1); 579 u1 = bus_space_read_4(acpi_hpet_bst, acpi_hpet_bsh, HPET_MAIN_COUNTER); 580 for (i = 1; i < 1000; i++) { 581 u2 = bus_space_read_4(acpi_hpet_bst, acpi_hpet_bsh, 582 HPET_MAIN_COUNTER); 583 } 584 microuptime(&b2); 585 u2 = bus_space_read_4(acpi_hpet_bst, acpi_hpet_bsh, HPET_MAIN_COUNTER); 586 587 timevalsub(&b2, &b1); 588 timevalsub(&b1, &b0); 589 timevalsub(&b2, &b1); 590 591 TIMEVAL_TO_TIMESPEC(&b2, &ts); 592 593 device_printf(sc->dev, "%ld.%09ld: %u ... %u = %u\n", 594 (long)b2.tv_sec, b2.tv_usec, u1, u2, u2 - u1); 595 596 device_printf(sc->dev, "time per call: %ld ns\n", ts.tv_nsec / 1000); 597 } 598