Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

at v4.12 1040 lines 25 kB view raw
1/* 2 * intel_pmc_ipc.c: Driver for the Intel PMC IPC mechanism 3 * 4 * (C) Copyright 2014-2015 Intel Corporation 5 * 6 * This driver is based on Intel SCU IPC driver(intel_scu_opc.c) by 7 * Sreedhara DS <sreedhara.ds@intel.com> 8 * 9 * This program is free software; you can redistribute it and/or 10 * modify it under the terms of the GNU General Public License 11 * as published by the Free Software Foundation; version 2 12 * of the License. 13 * 14 * PMC running in ARC processor communicates with other entity running in IA 15 * core through IPC mechanism which in turn messaging between IA core ad PMC. 16 */ 17 18#include <linux/module.h> 19#include <linux/delay.h> 20#include <linux/errno.h> 21#include <linux/init.h> 22#include <linux/device.h> 23#include <linux/pm.h> 24#include <linux/pci.h> 25#include <linux/platform_device.h> 26#include <linux/interrupt.h> 27#include <linux/pm_qos.h> 28#include <linux/kernel.h> 29#include <linux/bitops.h> 30#include <linux/sched.h> 31#include <linux/atomic.h> 32#include <linux/notifier.h> 33#include <linux/suspend.h> 34#include <linux/acpi.h> 35#include <linux/io-64-nonatomic-lo-hi.h> 36 37#include <asm/intel_pmc_ipc.h> 38 39#include <linux/platform_data/itco_wdt.h> 40 41/* 42 * IPC registers 43 * The IA write to IPC_CMD command register triggers an interrupt to the ARC, 44 * The ARC handles the interrupt and services it, writing optional data to 45 * the IPC1 registers, updates the IPC_STS response register with the status. 46 */ 47#define IPC_CMD 0x0 48#define IPC_CMD_MSI 0x100 49#define IPC_CMD_SIZE 16 50#define IPC_CMD_SUBCMD 12 51#define IPC_STATUS 0x04 52#define IPC_STATUS_IRQ 0x4 53#define IPC_STATUS_ERR 0x2 54#define IPC_STATUS_BUSY 0x1 55#define IPC_SPTR 0x08 56#define IPC_DPTR 0x0C 57#define IPC_WRITE_BUFFER 0x80 58#define IPC_READ_BUFFER 0x90 59 60/* Residency with clock rate at 19.2MHz to usecs */ 61#define S0IX_RESIDENCY_IN_USECS(d, s) \ 62({ \ 63 u64 result = 10ull * ((d) + (s)); \ 64 do_div(result, 192); \ 65 result; \ 66}) 67 68/* 69 * 16-byte buffer for sending data associated with IPC command. 70 */ 71#define IPC_DATA_BUFFER_SIZE 16 72 73#define IPC_LOOP_CNT 3000000 74#define IPC_MAX_SEC 3 75 76#define IPC_TRIGGER_MODE_IRQ true 77 78/* exported resources from IFWI */ 79#define PLAT_RESOURCE_IPC_INDEX 0 80#define PLAT_RESOURCE_IPC_SIZE 0x1000 81#define PLAT_RESOURCE_GCR_OFFSET 0x1000 82#define PLAT_RESOURCE_GCR_SIZE 0x1000 83#define PLAT_RESOURCE_BIOS_DATA_INDEX 1 84#define PLAT_RESOURCE_BIOS_IFACE_INDEX 2 85#define PLAT_RESOURCE_TELEM_SSRAM_INDEX 3 86#define PLAT_RESOURCE_ISP_DATA_INDEX 4 87#define PLAT_RESOURCE_ISP_IFACE_INDEX 5 88#define PLAT_RESOURCE_GTD_DATA_INDEX 6 89#define PLAT_RESOURCE_GTD_IFACE_INDEX 7 90#define PLAT_RESOURCE_ACPI_IO_INDEX 0 91 92/* 93 * BIOS does not create an ACPI device for each PMC function, 94 * but exports multiple resources from one ACPI device(IPC) for 95 * multiple functions. This driver is responsible to create a 96 * platform device and to export resources for those functions. 97 */ 98#define TCO_DEVICE_NAME "iTCO_wdt" 99#define SMI_EN_OFFSET 0x40 100#define SMI_EN_SIZE 4 101#define TCO_BASE_OFFSET 0x60 102#define TCO_REGS_SIZE 16 103#define PUNIT_DEVICE_NAME "intel_punit_ipc" 104#define TELEMETRY_DEVICE_NAME "intel_telemetry" 105#define TELEM_SSRAM_SIZE 240 106#define TELEM_PMC_SSRAM_OFFSET 0x1B00 107#define TELEM_PUNIT_SSRAM_OFFSET 0x1A00 108#define TCO_PMC_OFFSET 0x8 109#define TCO_PMC_SIZE 0x4 110 111/* PMC register bit definitions */ 112 113/* PMC_CFG_REG bit masks */ 114#define PMC_CFG_NO_REBOOT_MASK (1 << 4) 115#define PMC_CFG_NO_REBOOT_EN (1 << 4) 116#define PMC_CFG_NO_REBOOT_DIS (0 << 4) 117 118static struct intel_pmc_ipc_dev { 119 struct device *dev; 120 void __iomem *ipc_base; 121 bool irq_mode; 122 int irq; 123 int cmd; 124 struct completion cmd_complete; 125 126 /* The following PMC BARs share the same ACPI device with the IPC */ 127 resource_size_t acpi_io_base; 128 int acpi_io_size; 129 struct platform_device *tco_dev; 130 131 /* gcr */ 132 void __iomem *gcr_mem_base; 133 bool has_gcr_regs; 134 135 /* punit */ 136 struct platform_device *punit_dev; 137 138 /* Telemetry */ 139 resource_size_t telem_pmc_ssram_base; 140 resource_size_t telem_punit_ssram_base; 141 int telem_pmc_ssram_size; 142 int telem_punit_ssram_size; 143 u8 telem_res_inval; 144 struct platform_device *telemetry_dev; 145} ipcdev; 146 147static char *ipc_err_sources[] = { 148 [IPC_ERR_NONE] = 149 "no error", 150 [IPC_ERR_CMD_NOT_SUPPORTED] = 151 "command not supported", 152 [IPC_ERR_CMD_NOT_SERVICED] = 153 "command not serviced", 154 [IPC_ERR_UNABLE_TO_SERVICE] = 155 "unable to service", 156 [IPC_ERR_CMD_INVALID] = 157 "command invalid", 158 [IPC_ERR_CMD_FAILED] = 159 "command failed", 160 [IPC_ERR_EMSECURITY] = 161 "Invalid Battery", 162 [IPC_ERR_UNSIGNEDKERNEL] = 163 "Unsigned kernel", 164}; 165 166/* Prevent concurrent calls to the PMC */ 167static DEFINE_MUTEX(ipclock); 168 169static inline void ipc_send_command(u32 cmd) 170{ 171 ipcdev.cmd = cmd; 172 if (ipcdev.irq_mode) { 173 reinit_completion(&ipcdev.cmd_complete); 174 cmd |= IPC_CMD_MSI; 175 } 176 writel(cmd, ipcdev.ipc_base + IPC_CMD); 177} 178 179static inline u32 ipc_read_status(void) 180{ 181 return readl(ipcdev.ipc_base + IPC_STATUS); 182} 183 184static inline void ipc_data_writel(u32 data, u32 offset) 185{ 186 writel(data, ipcdev.ipc_base + IPC_WRITE_BUFFER + offset); 187} 188 189static inline u8 ipc_data_readb(u32 offset) 190{ 191 return readb(ipcdev.ipc_base + IPC_READ_BUFFER + offset); 192} 193 194static inline u32 ipc_data_readl(u32 offset) 195{ 196 return readl(ipcdev.ipc_base + IPC_READ_BUFFER + offset); 197} 198 199static inline u64 gcr_data_readq(u32 offset) 200{ 201 return readq(ipcdev.gcr_mem_base + offset); 202} 203 204static inline int is_gcr_valid(u32 offset) 205{ 206 if (!ipcdev.has_gcr_regs) 207 return -EACCES; 208 209 if (offset > PLAT_RESOURCE_GCR_SIZE) 210 return -EINVAL; 211 212 return 0; 213} 214 215/** 216 * intel_pmc_gcr_read() - Read PMC GCR register 217 * @offset: offset of GCR register from GCR address base 218 * @data: data pointer for storing the register output 219 * 220 * Reads the PMC GCR register of given offset. 221 * 222 * Return: negative value on error or 0 on success. 223 */ 224int intel_pmc_gcr_read(u32 offset, u32 *data) 225{ 226 int ret; 227 228 mutex_lock(&ipclock); 229 230 ret = is_gcr_valid(offset); 231 if (ret < 0) { 232 mutex_unlock(&ipclock); 233 return ret; 234 } 235 236 *data = readl(ipcdev.gcr_mem_base + offset); 237 238 mutex_unlock(&ipclock); 239 240 return 0; 241} 242EXPORT_SYMBOL_GPL(intel_pmc_gcr_read); 243 244/** 245 * intel_pmc_gcr_write() - Write PMC GCR register 246 * @offset: offset of GCR register from GCR address base 247 * @data: register update value 248 * 249 * Writes the PMC GCR register of given offset with given 250 * value. 251 * 252 * Return: negative value on error or 0 on success. 253 */ 254int intel_pmc_gcr_write(u32 offset, u32 data) 255{ 256 int ret; 257 258 mutex_lock(&ipclock); 259 260 ret = is_gcr_valid(offset); 261 if (ret < 0) { 262 mutex_unlock(&ipclock); 263 return ret; 264 } 265 266 writel(data, ipcdev.gcr_mem_base + offset); 267 268 mutex_unlock(&ipclock); 269 270 return 0; 271} 272EXPORT_SYMBOL_GPL(intel_pmc_gcr_write); 273 274/** 275 * intel_pmc_gcr_update() - Update PMC GCR register bits 276 * @offset: offset of GCR register from GCR address base 277 * @mask: bit mask for update operation 278 * @val: update value 279 * 280 * Updates the bits of given GCR register as specified by 281 * @mask and @val. 282 * 283 * Return: negative value on error or 0 on success. 284 */ 285int intel_pmc_gcr_update(u32 offset, u32 mask, u32 val) 286{ 287 u32 new_val; 288 int ret = 0; 289 290 mutex_lock(&ipclock); 291 292 ret = is_gcr_valid(offset); 293 if (ret < 0) 294 goto gcr_ipc_unlock; 295 296 new_val = readl(ipcdev.gcr_mem_base + offset); 297 298 new_val &= ~mask; 299 new_val |= val & mask; 300 301 writel(new_val, ipcdev.gcr_mem_base + offset); 302 303 new_val = readl(ipcdev.gcr_mem_base + offset); 304 305 /* check whether the bit update is successful */ 306 if ((new_val & mask) != (val & mask)) { 307 ret = -EIO; 308 goto gcr_ipc_unlock; 309 } 310 311gcr_ipc_unlock: 312 mutex_unlock(&ipclock); 313 return ret; 314} 315EXPORT_SYMBOL_GPL(intel_pmc_gcr_update); 316 317static int update_no_reboot_bit(void *priv, bool set) 318{ 319 u32 value = set ? PMC_CFG_NO_REBOOT_EN : PMC_CFG_NO_REBOOT_DIS; 320 321 return intel_pmc_gcr_update(PMC_GCR_PMC_CFG_REG, 322 PMC_CFG_NO_REBOOT_MASK, value); 323} 324 325static int intel_pmc_ipc_check_status(void) 326{ 327 int status; 328 int ret = 0; 329 330 if (ipcdev.irq_mode) { 331 if (0 == wait_for_completion_timeout( 332 &ipcdev.cmd_complete, IPC_MAX_SEC * HZ)) 333 ret = -ETIMEDOUT; 334 } else { 335 int loop_count = IPC_LOOP_CNT; 336 337 while ((ipc_read_status() & IPC_STATUS_BUSY) && --loop_count) 338 udelay(1); 339 if (loop_count == 0) 340 ret = -ETIMEDOUT; 341 } 342 343 status = ipc_read_status(); 344 if (ret == -ETIMEDOUT) { 345 dev_err(ipcdev.dev, 346 "IPC timed out, TS=0x%x, CMD=0x%x\n", 347 status, ipcdev.cmd); 348 return ret; 349 } 350 351 if (status & IPC_STATUS_ERR) { 352 int i; 353 354 ret = -EIO; 355 i = (status >> IPC_CMD_SIZE) & 0xFF; 356 if (i < ARRAY_SIZE(ipc_err_sources)) 357 dev_err(ipcdev.dev, 358 "IPC failed: %s, STS=0x%x, CMD=0x%x\n", 359 ipc_err_sources[i], status, ipcdev.cmd); 360 else 361 dev_err(ipcdev.dev, 362 "IPC failed: unknown, STS=0x%x, CMD=0x%x\n", 363 status, ipcdev.cmd); 364 if ((i == IPC_ERR_UNSIGNEDKERNEL) || (i == IPC_ERR_EMSECURITY)) 365 ret = -EACCES; 366 } 367 368 return ret; 369} 370 371/** 372 * intel_pmc_ipc_simple_command() - Simple IPC command 373 * @cmd: IPC command code. 374 * @sub: IPC command sub type. 375 * 376 * Send a simple IPC command to PMC when don't need to specify 377 * input/output data and source/dest pointers. 378 * 379 * Return: an IPC error code or 0 on success. 380 */ 381int intel_pmc_ipc_simple_command(int cmd, int sub) 382{ 383 int ret; 384 385 mutex_lock(&ipclock); 386 if (ipcdev.dev == NULL) { 387 mutex_unlock(&ipclock); 388 return -ENODEV; 389 } 390 ipc_send_command(sub << IPC_CMD_SUBCMD | cmd); 391 ret = intel_pmc_ipc_check_status(); 392 mutex_unlock(&ipclock); 393 394 return ret; 395} 396EXPORT_SYMBOL_GPL(intel_pmc_ipc_simple_command); 397 398/** 399 * intel_pmc_ipc_raw_cmd() - IPC command with data and pointers 400 * @cmd: IPC command code. 401 * @sub: IPC command sub type. 402 * @in: input data of this IPC command. 403 * @inlen: input data length in bytes. 404 * @out: output data of this IPC command. 405 * @outlen: output data length in dwords. 406 * @sptr: data writing to SPTR register. 407 * @dptr: data writing to DPTR register. 408 * 409 * Send an IPC command to PMC with input/output data and source/dest pointers. 410 * 411 * Return: an IPC error code or 0 on success. 412 */ 413int intel_pmc_ipc_raw_cmd(u32 cmd, u32 sub, u8 *in, u32 inlen, u32 *out, 414 u32 outlen, u32 dptr, u32 sptr) 415{ 416 u32 wbuf[4] = { 0 }; 417 int ret; 418 int i; 419 420 if (inlen > IPC_DATA_BUFFER_SIZE || outlen > IPC_DATA_BUFFER_SIZE / 4) 421 return -EINVAL; 422 423 mutex_lock(&ipclock); 424 if (ipcdev.dev == NULL) { 425 mutex_unlock(&ipclock); 426 return -ENODEV; 427 } 428 memcpy(wbuf, in, inlen); 429 writel(dptr, ipcdev.ipc_base + IPC_DPTR); 430 writel(sptr, ipcdev.ipc_base + IPC_SPTR); 431 /* The input data register is 32bit register and inlen is in Byte */ 432 for (i = 0; i < ((inlen + 3) / 4); i++) 433 ipc_data_writel(wbuf[i], 4 * i); 434 ipc_send_command((inlen << IPC_CMD_SIZE) | 435 (sub << IPC_CMD_SUBCMD) | cmd); 436 ret = intel_pmc_ipc_check_status(); 437 if (!ret) { 438 /* out is read from 32bit register and outlen is in 32bit */ 439 for (i = 0; i < outlen; i++) 440 *out++ = ipc_data_readl(4 * i); 441 } 442 mutex_unlock(&ipclock); 443 444 return ret; 445} 446EXPORT_SYMBOL_GPL(intel_pmc_ipc_raw_cmd); 447 448/** 449 * intel_pmc_ipc_command() - IPC command with input/output data 450 * @cmd: IPC command code. 451 * @sub: IPC command sub type. 452 * @in: input data of this IPC command. 453 * @inlen: input data length in bytes. 454 * @out: output data of this IPC command. 455 * @outlen: output data length in dwords. 456 * 457 * Send an IPC command to PMC with input/output data. 458 * 459 * Return: an IPC error code or 0 on success. 460 */ 461int intel_pmc_ipc_command(u32 cmd, u32 sub, u8 *in, u32 inlen, 462 u32 *out, u32 outlen) 463{ 464 return intel_pmc_ipc_raw_cmd(cmd, sub, in, inlen, out, outlen, 0, 0); 465} 466EXPORT_SYMBOL_GPL(intel_pmc_ipc_command); 467 468static irqreturn_t ioc(int irq, void *dev_id) 469{ 470 int status; 471 472 if (ipcdev.irq_mode) { 473 status = ipc_read_status(); 474 writel(status | IPC_STATUS_IRQ, ipcdev.ipc_base + IPC_STATUS); 475 } 476 complete(&ipcdev.cmd_complete); 477 478 return IRQ_HANDLED; 479} 480 481static int ipc_pci_probe(struct pci_dev *pdev, const struct pci_device_id *id) 482{ 483 resource_size_t pci_resource; 484 int ret; 485 int len; 486 487 ipcdev.dev = &pci_dev_get(pdev)->dev; 488 ipcdev.irq_mode = IPC_TRIGGER_MODE_IRQ; 489 490 ret = pci_enable_device(pdev); 491 if (ret) 492 return ret; 493 494 ret = pci_request_regions(pdev, "intel_pmc_ipc"); 495 if (ret) 496 return ret; 497 498 pci_resource = pci_resource_start(pdev, 0); 499 len = pci_resource_len(pdev, 0); 500 if (!pci_resource || !len) { 501 dev_err(&pdev->dev, "Failed to get resource\n"); 502 return -ENOMEM; 503 } 504 505 init_completion(&ipcdev.cmd_complete); 506 507 if (request_irq(pdev->irq, ioc, 0, "intel_pmc_ipc", &ipcdev)) { 508 dev_err(&pdev->dev, "Failed to request irq\n"); 509 return -EBUSY; 510 } 511 512 ipcdev.ipc_base = ioremap_nocache(pci_resource, len); 513 if (!ipcdev.ipc_base) { 514 dev_err(&pdev->dev, "Failed to ioremap ipc base\n"); 515 free_irq(pdev->irq, &ipcdev); 516 ret = -ENOMEM; 517 } 518 519 return ret; 520} 521 522static void ipc_pci_remove(struct pci_dev *pdev) 523{ 524 free_irq(pdev->irq, &ipcdev); 525 pci_release_regions(pdev); 526 pci_dev_put(pdev); 527 iounmap(ipcdev.ipc_base); 528 ipcdev.dev = NULL; 529} 530 531static const struct pci_device_id ipc_pci_ids[] = { 532 {PCI_VDEVICE(INTEL, 0x0a94), 0}, 533 {PCI_VDEVICE(INTEL, 0x1a94), 0}, 534 {PCI_VDEVICE(INTEL, 0x5a94), 0}, 535 { 0,} 536}; 537MODULE_DEVICE_TABLE(pci, ipc_pci_ids); 538 539static struct pci_driver ipc_pci_driver = { 540 .name = "intel_pmc_ipc", 541 .id_table = ipc_pci_ids, 542 .probe = ipc_pci_probe, 543 .remove = ipc_pci_remove, 544}; 545 546static ssize_t intel_pmc_ipc_simple_cmd_store(struct device *dev, 547 struct device_attribute *attr, 548 const char *buf, size_t count) 549{ 550 int subcmd; 551 int cmd; 552 int ret; 553 554 ret = sscanf(buf, "%d %d", &cmd, &subcmd); 555 if (ret != 2) { 556 dev_err(dev, "Error args\n"); 557 return -EINVAL; 558 } 559 560 ret = intel_pmc_ipc_simple_command(cmd, subcmd); 561 if (ret) { 562 dev_err(dev, "command %d error with %d\n", cmd, ret); 563 return ret; 564 } 565 return (ssize_t)count; 566} 567 568static ssize_t intel_pmc_ipc_northpeak_store(struct device *dev, 569 struct device_attribute *attr, 570 const char *buf, size_t count) 571{ 572 unsigned long val; 573 int subcmd; 574 int ret; 575 576 if (kstrtoul(buf, 0, &val)) 577 return -EINVAL; 578 579 if (val) 580 subcmd = 1; 581 else 582 subcmd = 0; 583 ret = intel_pmc_ipc_simple_command(PMC_IPC_NORTHPEAK_CTRL, subcmd); 584 if (ret) { 585 dev_err(dev, "command north %d error with %d\n", subcmd, ret); 586 return ret; 587 } 588 return (ssize_t)count; 589} 590 591static DEVICE_ATTR(simplecmd, S_IWUSR, 592 NULL, intel_pmc_ipc_simple_cmd_store); 593static DEVICE_ATTR(northpeak, S_IWUSR, 594 NULL, intel_pmc_ipc_northpeak_store); 595 596static struct attribute *intel_ipc_attrs[] = { 597 &dev_attr_northpeak.attr, 598 &dev_attr_simplecmd.attr, 599 NULL 600}; 601 602static const struct attribute_group intel_ipc_group = { 603 .attrs = intel_ipc_attrs, 604}; 605 606static struct resource punit_res_array[] = { 607 /* Punit BIOS */ 608 { 609 .flags = IORESOURCE_MEM, 610 }, 611 { 612 .flags = IORESOURCE_MEM, 613 }, 614 /* Punit ISP */ 615 { 616 .flags = IORESOURCE_MEM, 617 }, 618 { 619 .flags = IORESOURCE_MEM, 620 }, 621 /* Punit GTD */ 622 { 623 .flags = IORESOURCE_MEM, 624 }, 625 { 626 .flags = IORESOURCE_MEM, 627 }, 628}; 629 630#define TCO_RESOURCE_ACPI_IO 0 631#define TCO_RESOURCE_SMI_EN_IO 1 632#define TCO_RESOURCE_GCR_MEM 2 633static struct resource tco_res[] = { 634 /* ACPI - TCO */ 635 { 636 .flags = IORESOURCE_IO, 637 }, 638 /* ACPI - SMI */ 639 { 640 .flags = IORESOURCE_IO, 641 }, 642}; 643 644static struct itco_wdt_platform_data tco_info = { 645 .name = "Apollo Lake SoC", 646 .version = 5, 647 .no_reboot_priv = &ipcdev, 648 .update_no_reboot_bit = update_no_reboot_bit, 649}; 650 651#define TELEMETRY_RESOURCE_PUNIT_SSRAM 0 652#define TELEMETRY_RESOURCE_PMC_SSRAM 1 653static struct resource telemetry_res[] = { 654 /*Telemetry*/ 655 { 656 .flags = IORESOURCE_MEM, 657 }, 658 { 659 .flags = IORESOURCE_MEM, 660 }, 661}; 662 663static int ipc_create_punit_device(void) 664{ 665 struct platform_device *pdev; 666 const struct platform_device_info pdevinfo = { 667 .parent = ipcdev.dev, 668 .name = PUNIT_DEVICE_NAME, 669 .id = -1, 670 .res = punit_res_array, 671 .num_res = ARRAY_SIZE(punit_res_array), 672 }; 673 674 pdev = platform_device_register_full(&pdevinfo); 675 if (IS_ERR(pdev)) 676 return PTR_ERR(pdev); 677 678 ipcdev.punit_dev = pdev; 679 680 return 0; 681} 682 683static int ipc_create_tco_device(void) 684{ 685 struct platform_device *pdev; 686 struct resource *res; 687 const struct platform_device_info pdevinfo = { 688 .parent = ipcdev.dev, 689 .name = TCO_DEVICE_NAME, 690 .id = -1, 691 .res = tco_res, 692 .num_res = ARRAY_SIZE(tco_res), 693 .data = &tco_info, 694 .size_data = sizeof(tco_info), 695 }; 696 697 res = tco_res + TCO_RESOURCE_ACPI_IO; 698 res->start = ipcdev.acpi_io_base + TCO_BASE_OFFSET; 699 res->end = res->start + TCO_REGS_SIZE - 1; 700 701 res = tco_res + TCO_RESOURCE_SMI_EN_IO; 702 res->start = ipcdev.acpi_io_base + SMI_EN_OFFSET; 703 res->end = res->start + SMI_EN_SIZE - 1; 704 705 pdev = platform_device_register_full(&pdevinfo); 706 if (IS_ERR(pdev)) 707 return PTR_ERR(pdev); 708 709 ipcdev.tco_dev = pdev; 710 711 return 0; 712} 713 714static int ipc_create_telemetry_device(void) 715{ 716 struct platform_device *pdev; 717 struct resource *res; 718 const struct platform_device_info pdevinfo = { 719 .parent = ipcdev.dev, 720 .name = TELEMETRY_DEVICE_NAME, 721 .id = -1, 722 .res = telemetry_res, 723 .num_res = ARRAY_SIZE(telemetry_res), 724 }; 725 726 res = telemetry_res + TELEMETRY_RESOURCE_PUNIT_SSRAM; 727 res->start = ipcdev.telem_punit_ssram_base; 728 res->end = res->start + ipcdev.telem_punit_ssram_size - 1; 729 730 res = telemetry_res + TELEMETRY_RESOURCE_PMC_SSRAM; 731 res->start = ipcdev.telem_pmc_ssram_base; 732 res->end = res->start + ipcdev.telem_pmc_ssram_size - 1; 733 734 pdev = platform_device_register_full(&pdevinfo); 735 if (IS_ERR(pdev)) 736 return PTR_ERR(pdev); 737 738 ipcdev.telemetry_dev = pdev; 739 740 return 0; 741} 742 743static int ipc_create_pmc_devices(void) 744{ 745 int ret; 746 747 /* If we have ACPI based watchdog use that instead */ 748 if (!acpi_has_watchdog()) { 749 ret = ipc_create_tco_device(); 750 if (ret) { 751 dev_err(ipcdev.dev, "Failed to add tco platform device\n"); 752 return ret; 753 } 754 } 755 756 ret = ipc_create_punit_device(); 757 if (ret) { 758 dev_err(ipcdev.dev, "Failed to add punit platform device\n"); 759 platform_device_unregister(ipcdev.tco_dev); 760 } 761 762 if (!ipcdev.telem_res_inval) { 763 ret = ipc_create_telemetry_device(); 764 if (ret) 765 dev_warn(ipcdev.dev, 766 "Failed to add telemetry platform device\n"); 767 } 768 769 return ret; 770} 771 772static int ipc_plat_get_res(struct platform_device *pdev) 773{ 774 struct resource *res, *punit_res; 775 void __iomem *addr; 776 int size; 777 778 res = platform_get_resource(pdev, IORESOURCE_IO, 779 PLAT_RESOURCE_ACPI_IO_INDEX); 780 if (!res) { 781 dev_err(&pdev->dev, "Failed to get io resource\n"); 782 return -ENXIO; 783 } 784 size = resource_size(res); 785 ipcdev.acpi_io_base = res->start; 786 ipcdev.acpi_io_size = size; 787 dev_info(&pdev->dev, "io res: %pR\n", res); 788 789 punit_res = punit_res_array; 790 /* This is index 0 to cover BIOS data register */ 791 res = platform_get_resource(pdev, IORESOURCE_MEM, 792 PLAT_RESOURCE_BIOS_DATA_INDEX); 793 if (!res) { 794 dev_err(&pdev->dev, "Failed to get res of punit BIOS data\n"); 795 return -ENXIO; 796 } 797 *punit_res = *res; 798 dev_info(&pdev->dev, "punit BIOS data res: %pR\n", res); 799 800 /* This is index 1 to cover BIOS interface register */ 801 res = platform_get_resource(pdev, IORESOURCE_MEM, 802 PLAT_RESOURCE_BIOS_IFACE_INDEX); 803 if (!res) { 804 dev_err(&pdev->dev, "Failed to get res of punit BIOS iface\n"); 805 return -ENXIO; 806 } 807 *++punit_res = *res; 808 dev_info(&pdev->dev, "punit BIOS interface res: %pR\n", res); 809 810 /* This is index 2 to cover ISP data register, optional */ 811 res = platform_get_resource(pdev, IORESOURCE_MEM, 812 PLAT_RESOURCE_ISP_DATA_INDEX); 813 ++punit_res; 814 if (res) { 815 *punit_res = *res; 816 dev_info(&pdev->dev, "punit ISP data res: %pR\n", res); 817 } 818 819 /* This is index 3 to cover ISP interface register, optional */ 820 res = platform_get_resource(pdev, IORESOURCE_MEM, 821 PLAT_RESOURCE_ISP_IFACE_INDEX); 822 ++punit_res; 823 if (res) { 824 *punit_res = *res; 825 dev_info(&pdev->dev, "punit ISP interface res: %pR\n", res); 826 } 827 828 /* This is index 4 to cover GTD data register, optional */ 829 res = platform_get_resource(pdev, IORESOURCE_MEM, 830 PLAT_RESOURCE_GTD_DATA_INDEX); 831 ++punit_res; 832 if (res) { 833 *punit_res = *res; 834 dev_info(&pdev->dev, "punit GTD data res: %pR\n", res); 835 } 836 837 /* This is index 5 to cover GTD interface register, optional */ 838 res = platform_get_resource(pdev, IORESOURCE_MEM, 839 PLAT_RESOURCE_GTD_IFACE_INDEX); 840 ++punit_res; 841 if (res) { 842 *punit_res = *res; 843 dev_info(&pdev->dev, "punit GTD interface res: %pR\n", res); 844 } 845 846 res = platform_get_resource(pdev, IORESOURCE_MEM, 847 PLAT_RESOURCE_IPC_INDEX); 848 if (!res) { 849 dev_err(&pdev->dev, "Failed to get ipc resource\n"); 850 return -ENXIO; 851 } 852 size = PLAT_RESOURCE_IPC_SIZE + PLAT_RESOURCE_GCR_SIZE; 853 854 if (!request_mem_region(res->start, size, pdev->name)) { 855 dev_err(&pdev->dev, "Failed to request ipc resource\n"); 856 return -EBUSY; 857 } 858 addr = ioremap_nocache(res->start, size); 859 if (!addr) { 860 dev_err(&pdev->dev, "I/O memory remapping failed\n"); 861 release_mem_region(res->start, size); 862 return -ENOMEM; 863 } 864 ipcdev.ipc_base = addr; 865 866 ipcdev.gcr_mem_base = addr + PLAT_RESOURCE_GCR_OFFSET; 867 dev_info(&pdev->dev, "ipc res: %pR\n", res); 868 869 ipcdev.telem_res_inval = 0; 870 res = platform_get_resource(pdev, IORESOURCE_MEM, 871 PLAT_RESOURCE_TELEM_SSRAM_INDEX); 872 if (!res) { 873 dev_err(&pdev->dev, "Failed to get telemetry ssram resource\n"); 874 ipcdev.telem_res_inval = 1; 875 } else { 876 ipcdev.telem_punit_ssram_base = res->start + 877 TELEM_PUNIT_SSRAM_OFFSET; 878 ipcdev.telem_punit_ssram_size = TELEM_SSRAM_SIZE; 879 ipcdev.telem_pmc_ssram_base = res->start + 880 TELEM_PMC_SSRAM_OFFSET; 881 ipcdev.telem_pmc_ssram_size = TELEM_SSRAM_SIZE; 882 dev_info(&pdev->dev, "telemetry ssram res: %pR\n", res); 883 } 884 885 return 0; 886} 887 888/** 889 * intel_pmc_s0ix_counter_read() - Read S0ix residency. 890 * @data: Out param that contains current S0ix residency count. 891 * 892 * Return: an error code or 0 on success. 893 */ 894int intel_pmc_s0ix_counter_read(u64 *data) 895{ 896 u64 deep, shlw; 897 898 if (!ipcdev.has_gcr_regs) 899 return -EACCES; 900 901 deep = gcr_data_readq(PMC_GCR_TELEM_DEEP_S0IX_REG); 902 shlw = gcr_data_readq(PMC_GCR_TELEM_SHLW_S0IX_REG); 903 904 *data = S0IX_RESIDENCY_IN_USECS(deep, shlw); 905 906 return 0; 907} 908EXPORT_SYMBOL_GPL(intel_pmc_s0ix_counter_read); 909 910#ifdef CONFIG_ACPI 911static const struct acpi_device_id ipc_acpi_ids[] = { 912 { "INT34D2", 0}, 913 { } 914}; 915MODULE_DEVICE_TABLE(acpi, ipc_acpi_ids); 916#endif 917 918static int ipc_plat_probe(struct platform_device *pdev) 919{ 920 struct resource *res; 921 int ret; 922 923 ipcdev.dev = &pdev->dev; 924 ipcdev.irq_mode = IPC_TRIGGER_MODE_IRQ; 925 init_completion(&ipcdev.cmd_complete); 926 927 ipcdev.irq = platform_get_irq(pdev, 0); 928 if (ipcdev.irq < 0) { 929 dev_err(&pdev->dev, "Failed to get irq\n"); 930 return -EINVAL; 931 } 932 933 ret = ipc_plat_get_res(pdev); 934 if (ret) { 935 dev_err(&pdev->dev, "Failed to request resource\n"); 936 return ret; 937 } 938 939 ret = ipc_create_pmc_devices(); 940 if (ret) { 941 dev_err(&pdev->dev, "Failed to create pmc devices\n"); 942 goto err_device; 943 } 944 945 if (request_irq(ipcdev.irq, ioc, IRQF_NO_SUSPEND, 946 "intel_pmc_ipc", &ipcdev)) { 947 dev_err(&pdev->dev, "Failed to request irq\n"); 948 ret = -EBUSY; 949 goto err_irq; 950 } 951 952 ret = sysfs_create_group(&pdev->dev.kobj, &intel_ipc_group); 953 if (ret) { 954 dev_err(&pdev->dev, "Failed to create sysfs group %d\n", 955 ret); 956 goto err_sys; 957 } 958 959 ipcdev.has_gcr_regs = true; 960 961 return 0; 962err_sys: 963 free_irq(ipcdev.irq, &ipcdev); 964err_irq: 965 platform_device_unregister(ipcdev.tco_dev); 966 platform_device_unregister(ipcdev.punit_dev); 967 platform_device_unregister(ipcdev.telemetry_dev); 968err_device: 969 iounmap(ipcdev.ipc_base); 970 res = platform_get_resource(pdev, IORESOURCE_MEM, 971 PLAT_RESOURCE_IPC_INDEX); 972 if (res) { 973 release_mem_region(res->start, 974 PLAT_RESOURCE_IPC_SIZE + 975 PLAT_RESOURCE_GCR_SIZE); 976 } 977 return ret; 978} 979 980static int ipc_plat_remove(struct platform_device *pdev) 981{ 982 struct resource *res; 983 984 sysfs_remove_group(&pdev->dev.kobj, &intel_ipc_group); 985 free_irq(ipcdev.irq, &ipcdev); 986 platform_device_unregister(ipcdev.tco_dev); 987 platform_device_unregister(ipcdev.punit_dev); 988 platform_device_unregister(ipcdev.telemetry_dev); 989 iounmap(ipcdev.ipc_base); 990 res = platform_get_resource(pdev, IORESOURCE_MEM, 991 PLAT_RESOURCE_IPC_INDEX); 992 if (res) { 993 release_mem_region(res->start, 994 PLAT_RESOURCE_IPC_SIZE + 995 PLAT_RESOURCE_GCR_SIZE); 996 } 997 ipcdev.dev = NULL; 998 return 0; 999} 1000 1001static struct platform_driver ipc_plat_driver = { 1002 .remove = ipc_plat_remove, 1003 .probe = ipc_plat_probe, 1004 .driver = { 1005 .name = "pmc-ipc-plat", 1006 .acpi_match_table = ACPI_PTR(ipc_acpi_ids), 1007 }, 1008}; 1009 1010static int __init intel_pmc_ipc_init(void) 1011{ 1012 int ret; 1013 1014 ret = platform_driver_register(&ipc_plat_driver); 1015 if (ret) { 1016 pr_err("Failed to register PMC ipc platform driver\n"); 1017 return ret; 1018 } 1019 ret = pci_register_driver(&ipc_pci_driver); 1020 if (ret) { 1021 pr_err("Failed to register PMC ipc pci driver\n"); 1022 platform_driver_unregister(&ipc_plat_driver); 1023 return ret; 1024 } 1025 return ret; 1026} 1027 1028static void __exit intel_pmc_ipc_exit(void) 1029{ 1030 pci_unregister_driver(&ipc_pci_driver); 1031 platform_driver_unregister(&ipc_plat_driver); 1032} 1033 1034MODULE_AUTHOR("Zha Qipeng <qipeng.zha@intel.com>"); 1035MODULE_DESCRIPTION("Intel PMC IPC driver"); 1036MODULE_LICENSE("GPL"); 1037 1038/* Some modules are dependent on this, so init earlier */ 1039fs_initcall(intel_pmc_ipc_init); 1040module_exit(intel_pmc_ipc_exit);