1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * Xilinx Zynq MPSoC Firmware layer 4 * 5 * Copyright (C) 2014-2021 Xilinx, Inc. 6 * 7 * Michal Simek <michal.simek@xilinx.com> 8 * Davorin Mista <davorin.mista@aggios.com> 9 * Jolly Shah <jollys@xilinx.com> 10 * Rajan Vaja <rajanv@xilinx.com> 11 */ 12 13 #include <linux/arm-smccc.h> 14 #include <linux/compiler.h> 15 #include <linux/device.h> 16 #include <linux/init.h> 17 #include <linux/mfd/core.h> 18 #include <linux/module.h> 19 #include <linux/of.h> 20 #include <linux/of_platform.h> 21 #include <linux/slab.h> 22 #include <linux/uaccess.h> 23 #include <linux/hashtable.h> 24 25 #include <linux/firmware/xlnx-zynqmp.h> 26 #include "zynqmp-debug.h" 27 28 /* Max HashMap Order for PM API feature check (1<<7 = 128) */ 29 #define PM_API_FEATURE_CHECK_MAX_ORDER 7 30 31 /* CRL registers and bitfields */ 32 #define CRL_APB_BASE 0xFF5E0000U 33 /* BOOT_PIN_CTRL- Used to control the mode pins after boot */ 34 #define CRL_APB_BOOT_PIN_CTRL (CRL_APB_BASE + (0x250U)) 35 /* BOOT_PIN_CTRL_MASK- out_val[11:8], out_en[3:0] */ 36 #define CRL_APB_BOOTPIN_CTRL_MASK 0xF0FU 37 38 static bool feature_check_enabled; 39 static DEFINE_HASHTABLE(pm_api_features_map, PM_API_FEATURE_CHECK_MAX_ORDER); 40 41 /** 42 * struct pm_api_feature_data - PM API Feature data 43 * @pm_api_id: PM API Id, used as key to index into hashmap 44 * @feature_status: status of PM API feature: valid, invalid 45 * @hentry: hlist_node that hooks this entry into hashtable 46 */ 47 struct pm_api_feature_data { 48 u32 pm_api_id; 49 int feature_status; 50 struct hlist_node hentry; 51 }; 52 53 static const struct mfd_cell firmware_devs[] = { 54 { 55 .name = "zynqmp_power_controller", 56 }, 57 }; 58 59 /** 60 * zynqmp_pm_ret_code() - Convert PMU-FW error codes to Linux error codes 61 * @ret_status: PMUFW return code 62 * 63 * Return: corresponding Linux error code 64 */ 65 static int zynqmp_pm_ret_code(u32 ret_status) 66 { 67 switch (ret_status) { 68 case XST_PM_SUCCESS: 69 case XST_PM_DOUBLE_REQ: 70 return 0; 71 case XST_PM_NO_FEATURE: 72 return -ENOTSUPP; 73 case XST_PM_NO_ACCESS: 74 return -EACCES; 75 case XST_PM_ABORT_SUSPEND: 76 return -ECANCELED; 77 case XST_PM_MULT_USER: 78 return -EUSERS; 79 case XST_PM_INTERNAL: 80 case XST_PM_CONFLICT: 81 case XST_PM_INVALID_NODE: 82 default: 83 return -EINVAL; 84 } 85 } 86 87 static noinline int do_fw_call_fail(u64 arg0, u64 arg1, u64 arg2, 88 u32 *ret_payload) 89 { 90 return -ENODEV; 91 } 92 93 /* 94 * PM function call wrapper 95 * Invoke do_fw_call_smc or do_fw_call_hvc, depending on the configuration 96 */ 97 static int (*do_fw_call)(u64, u64, u64, u32 *ret_payload) = do_fw_call_fail; 98 99 /** 100 * do_fw_call_smc() - Call system-level platform management layer (SMC) 101 * @arg0: Argument 0 to SMC call 102 * @arg1: Argument 1 to SMC call 103 * @arg2: Argument 2 to SMC call 104 * @ret_payload: Returned value array 105 * 106 * Invoke platform management function via SMC call (no hypervisor present). 107 * 108 * Return: Returns status, either success or error+reason 109 */ 110 static noinline int do_fw_call_smc(u64 arg0, u64 arg1, u64 arg2, 111 u32 *ret_payload) 112 { 113 struct arm_smccc_res res; 114 115 arm_smccc_smc(arg0, arg1, arg2, 0, 0, 0, 0, 0, &res); 116 117 if (ret_payload) { 118 ret_payload[0] = lower_32_bits(res.a0); 119 ret_payload[1] = upper_32_bits(res.a0); 120 ret_payload[2] = lower_32_bits(res.a1); 121 ret_payload[3] = upper_32_bits(res.a1); 122 } 123 124 return zynqmp_pm_ret_code((enum pm_ret_status)res.a0); 125 } 126 127 /** 128 * do_fw_call_hvc() - Call system-level platform management layer (HVC) 129 * @arg0: Argument 0 to HVC call 130 * @arg1: Argument 1 to HVC call 131 * @arg2: Argument 2 to HVC call 132 * @ret_payload: Returned value array 133 * 134 * Invoke platform management function via HVC 135 * HVC-based for communication through hypervisor 136 * (no direct communication with ATF). 137 * 138 * Return: Returns status, either success or error+reason 139 */ 140 static noinline int do_fw_call_hvc(u64 arg0, u64 arg1, u64 arg2, 141 u32 *ret_payload) 142 { 143 struct arm_smccc_res res; 144 145 arm_smccc_hvc(arg0, arg1, arg2, 0, 0, 0, 0, 0, &res); 146 147 if (ret_payload) { 148 ret_payload[0] = lower_32_bits(res.a0); 149 ret_payload[1] = upper_32_bits(res.a0); 150 ret_payload[2] = lower_32_bits(res.a1); 151 ret_payload[3] = upper_32_bits(res.a1); 152 } 153 154 return zynqmp_pm_ret_code((enum pm_ret_status)res.a0); 155 } 156 157 /** 158 * zynqmp_pm_feature() - Check weather given feature is supported or not 159 * @api_id: API ID to check 160 * 161 * Return: Returns status, either success or error+reason 162 */ 163 int zynqmp_pm_feature(const u32 api_id) 164 { 165 int ret; 166 u32 ret_payload[PAYLOAD_ARG_CNT]; 167 u64 smc_arg[2]; 168 struct pm_api_feature_data *feature_data; 169 170 if (!feature_check_enabled) 171 return 0; 172 173 /* Check for existing entry in hash table for given api */ 174 hash_for_each_possible(pm_api_features_map, feature_data, hentry, 175 api_id) { 176 if (feature_data->pm_api_id == api_id) 177 return feature_data->feature_status; 178 } 179 180 /* Add new entry if not present */ 181 feature_data = kmalloc(sizeof(*feature_data), GFP_KERNEL); 182 if (!feature_data) 183 return -ENOMEM; 184 185 feature_data->pm_api_id = api_id; 186 smc_arg[0] = PM_SIP_SVC | PM_FEATURE_CHECK; 187 smc_arg[1] = api_id; 188 189 ret = do_fw_call(smc_arg[0], smc_arg[1], 0, ret_payload); 190 if (ret) 191 ret = -EOPNOTSUPP; 192 else 193 ret = ret_payload[1]; 194 195 feature_data->feature_status = ret; 196 hash_add(pm_api_features_map, &feature_data->hentry, api_id); 197 198 return ret; 199 } 200 EXPORT_SYMBOL_GPL(zynqmp_pm_feature); 201 202 /** 203 * zynqmp_pm_invoke_fn() - Invoke the system-level platform management layer 204 * caller function depending on the configuration 205 * @pm_api_id: Requested PM-API call 206 * @arg0: Argument 0 to requested PM-API call 207 * @arg1: Argument 1 to requested PM-API call 208 * @arg2: Argument 2 to requested PM-API call 209 * @arg3: Argument 3 to requested PM-API call 210 * @ret_payload: Returned value array 211 * 212 * Invoke platform management function for SMC or HVC call, depending on 213 * configuration. 214 * Following SMC Calling Convention (SMCCC) for SMC64: 215 * Pm Function Identifier, 216 * PM_SIP_SVC + PM_API_ID = 217 * ((SMC_TYPE_FAST << FUNCID_TYPE_SHIFT) 218 * ((SMC_64) << FUNCID_CC_SHIFT) 219 * ((SIP_START) << FUNCID_OEN_SHIFT) 220 * ((PM_API_ID) & FUNCID_NUM_MASK)) 221 * 222 * PM_SIP_SVC - Registered ZynqMP SIP Service Call. 223 * PM_API_ID - Platform Management API ID. 224 * 225 * Return: Returns status, either success or error+reason 226 */ 227 int zynqmp_pm_invoke_fn(u32 pm_api_id, u32 arg0, u32 arg1, 228 u32 arg2, u32 arg3, u32 *ret_payload) 229 { 230 /* 231 * Added SIP service call Function Identifier 232 * Make sure to stay in x0 register 233 */ 234 u64 smc_arg[4]; 235 int ret; 236 237 /* Check if feature is supported or not */ 238 ret = zynqmp_pm_feature(pm_api_id); 239 if (ret < 0) 240 return ret; 241 242 smc_arg[0] = PM_SIP_SVC | pm_api_id; 243 smc_arg[1] = ((u64)arg1 << 32) | arg0; 244 smc_arg[2] = ((u64)arg3 << 32) | arg2; 245 246 return do_fw_call(smc_arg[0], smc_arg[1], smc_arg[2], ret_payload); 247 } 248 249 static u32 pm_api_version; 250 static u32 pm_tz_version; 251 252 /** 253 * zynqmp_pm_get_api_version() - Get version number of PMU PM firmware 254 * @version: Returned version value 255 * 256 * Return: Returns status, either success or error+reason 257 */ 258 int zynqmp_pm_get_api_version(u32 *version) 259 { 260 u32 ret_payload[PAYLOAD_ARG_CNT]; 261 int ret; 262 263 if (!version) 264 return -EINVAL; 265 266 /* Check is PM API version already verified */ 267 if (pm_api_version > 0) { 268 *version = pm_api_version; 269 return 0; 270 } 271 ret = zynqmp_pm_invoke_fn(PM_GET_API_VERSION, 0, 0, 0, 0, ret_payload); 272 *version = ret_payload[1]; 273 274 return ret; 275 } 276 EXPORT_SYMBOL_GPL(zynqmp_pm_get_api_version); 277 278 /** 279 * zynqmp_pm_get_chipid - Get silicon ID registers 280 * @idcode: IDCODE register 281 * @version: version register 282 * 283 * Return: Returns the status of the operation and the idcode and version 284 * registers in @idcode and @version. 285 */ 286 int zynqmp_pm_get_chipid(u32 *idcode, u32 *version) 287 { 288 u32 ret_payload[PAYLOAD_ARG_CNT]; 289 int ret; 290 291 if (!idcode || !version) 292 return -EINVAL; 293 294 ret = zynqmp_pm_invoke_fn(PM_GET_CHIPID, 0, 0, 0, 0, ret_payload); 295 *idcode = ret_payload[1]; 296 *version = ret_payload[2]; 297 298 return ret; 299 } 300 EXPORT_SYMBOL_GPL(zynqmp_pm_get_chipid); 301 302 /** 303 * zynqmp_pm_get_trustzone_version() - Get secure trustzone firmware version 304 * @version: Returned version value 305 * 306 * Return: Returns status, either success or error+reason 307 */ 308 static int zynqmp_pm_get_trustzone_version(u32 *version) 309 { 310 u32 ret_payload[PAYLOAD_ARG_CNT]; 311 int ret; 312 313 if (!version) 314 return -EINVAL; 315 316 /* Check is PM trustzone version already verified */ 317 if (pm_tz_version > 0) { 318 *version = pm_tz_version; 319 return 0; 320 } 321 ret = zynqmp_pm_invoke_fn(PM_GET_TRUSTZONE_VERSION, 0, 0, 322 0, 0, ret_payload); 323 *version = ret_payload[1]; 324 325 return ret; 326 } 327 328 /** 329 * get_set_conduit_method() - Choose SMC or HVC based communication 330 * @np: Pointer to the device_node structure 331 * 332 * Use SMC or HVC-based functions to communicate with EL2/EL3. 333 * 334 * Return: Returns 0 on success or error code 335 */ 336 static int get_set_conduit_method(struct device_node *np) 337 { 338 const char *method; 339 340 if (of_property_read_string(np, "method", &method)) { 341 pr_warn("%s missing \"method\" property\n", __func__); 342 return -ENXIO; 343 } 344 345 if (!strcmp("hvc", method)) { 346 do_fw_call = do_fw_call_hvc; 347 } else if (!strcmp("smc", method)) { 348 do_fw_call = do_fw_call_smc; 349 } else { 350 pr_warn("%s Invalid \"method\" property: %s\n", 351 __func__, method); 352 return -EINVAL; 353 } 354 355 return 0; 356 } 357 358 /** 359 * zynqmp_pm_query_data() - Get query data from firmware 360 * @qdata: Variable to the zynqmp_pm_query_data structure 361 * @out: Returned output value 362 * 363 * Return: Returns status, either success or error+reason 364 */ 365 int zynqmp_pm_query_data(struct zynqmp_pm_query_data qdata, u32 *out) 366 { 367 int ret; 368 369 ret = zynqmp_pm_invoke_fn(PM_QUERY_DATA, qdata.qid, qdata.arg1, 370 qdata.arg2, qdata.arg3, out); 371 372 /* 373 * For clock name query, all bytes in SMC response are clock name 374 * characters and return code is always success. For invalid clocks, 375 * clock name bytes would be zeros. 376 */ 377 return qdata.qid == PM_QID_CLOCK_GET_NAME ? 0 : ret; 378 } 379 EXPORT_SYMBOL_GPL(zynqmp_pm_query_data); 380 381 /** 382 * zynqmp_pm_clock_enable() - Enable the clock for given id 383 * @clock_id: ID of the clock to be enabled 384 * 385 * This function is used by master to enable the clock 386 * including peripherals and PLL clocks. 387 * 388 * Return: Returns status, either success or error+reason 389 */ 390 int zynqmp_pm_clock_enable(u32 clock_id) 391 { 392 return zynqmp_pm_invoke_fn(PM_CLOCK_ENABLE, clock_id, 0, 0, 0, NULL); 393 } 394 EXPORT_SYMBOL_GPL(zynqmp_pm_clock_enable); 395 396 /** 397 * zynqmp_pm_clock_disable() - Disable the clock for given id 398 * @clock_id: ID of the clock to be disable 399 * 400 * This function is used by master to disable the clock 401 * including peripherals and PLL clocks. 402 * 403 * Return: Returns status, either success or error+reason 404 */ 405 int zynqmp_pm_clock_disable(u32 clock_id) 406 { 407 return zynqmp_pm_invoke_fn(PM_CLOCK_DISABLE, clock_id, 0, 0, 0, NULL); 408 } 409 EXPORT_SYMBOL_GPL(zynqmp_pm_clock_disable); 410 411 /** 412 * zynqmp_pm_clock_getstate() - Get the clock state for given id 413 * @clock_id: ID of the clock to be queried 414 * @state: 1/0 (Enabled/Disabled) 415 * 416 * This function is used by master to get the state of clock 417 * including peripherals and PLL clocks. 418 * 419 * Return: Returns status, either success or error+reason 420 */ 421 int zynqmp_pm_clock_getstate(u32 clock_id, u32 *state) 422 { 423 u32 ret_payload[PAYLOAD_ARG_CNT]; 424 int ret; 425 426 ret = zynqmp_pm_invoke_fn(PM_CLOCK_GETSTATE, clock_id, 0, 427 0, 0, ret_payload); 428 *state = ret_payload[1]; 429 430 return ret; 431 } 432 EXPORT_SYMBOL_GPL(zynqmp_pm_clock_getstate); 433 434 /** 435 * zynqmp_pm_clock_setdivider() - Set the clock divider for given id 436 * @clock_id: ID of the clock 437 * @divider: divider value 438 * 439 * This function is used by master to set divider for any clock 440 * to achieve desired rate. 441 * 442 * Return: Returns status, either success or error+reason 443 */ 444 int zynqmp_pm_clock_setdivider(u32 clock_id, u32 divider) 445 { 446 return zynqmp_pm_invoke_fn(PM_CLOCK_SETDIVIDER, clock_id, divider, 447 0, 0, NULL); 448 } 449 EXPORT_SYMBOL_GPL(zynqmp_pm_clock_setdivider); 450 451 /** 452 * zynqmp_pm_clock_getdivider() - Get the clock divider for given id 453 * @clock_id: ID of the clock 454 * @divider: divider value 455 * 456 * This function is used by master to get divider values 457 * for any clock. 458 * 459 * Return: Returns status, either success or error+reason 460 */ 461 int zynqmp_pm_clock_getdivider(u32 clock_id, u32 *divider) 462 { 463 u32 ret_payload[PAYLOAD_ARG_CNT]; 464 int ret; 465 466 ret = zynqmp_pm_invoke_fn(PM_CLOCK_GETDIVIDER, clock_id, 0, 467 0, 0, ret_payload); 468 *divider = ret_payload[1]; 469 470 return ret; 471 } 472 EXPORT_SYMBOL_GPL(zynqmp_pm_clock_getdivider); 473 474 /** 475 * zynqmp_pm_clock_setrate() - Set the clock rate for given id 476 * @clock_id: ID of the clock 477 * @rate: rate value in hz 478 * 479 * This function is used by master to set rate for any clock. 480 * 481 * Return: Returns status, either success or error+reason 482 */ 483 int zynqmp_pm_clock_setrate(u32 clock_id, u64 rate) 484 { 485 return zynqmp_pm_invoke_fn(PM_CLOCK_SETRATE, clock_id, 486 lower_32_bits(rate), 487 upper_32_bits(rate), 488 0, NULL); 489 } 490 EXPORT_SYMBOL_GPL(zynqmp_pm_clock_setrate); 491 492 /** 493 * zynqmp_pm_clock_getrate() - Get the clock rate for given id 494 * @clock_id: ID of the clock 495 * @rate: rate value in hz 496 * 497 * This function is used by master to get rate 498 * for any clock. 499 * 500 * Return: Returns status, either success or error+reason 501 */ 502 int zynqmp_pm_clock_getrate(u32 clock_id, u64 *rate) 503 { 504 u32 ret_payload[PAYLOAD_ARG_CNT]; 505 int ret; 506 507 ret = zynqmp_pm_invoke_fn(PM_CLOCK_GETRATE, clock_id, 0, 508 0, 0, ret_payload); 509 *rate = ((u64)ret_payload[2] << 32) | ret_payload[1]; 510 511 return ret; 512 } 513 EXPORT_SYMBOL_GPL(zynqmp_pm_clock_getrate); 514 515 /** 516 * zynqmp_pm_clock_setparent() - Set the clock parent for given id 517 * @clock_id: ID of the clock 518 * @parent_id: parent id 519 * 520 * This function is used by master to set parent for any clock. 521 * 522 * Return: Returns status, either success or error+reason 523 */ 524 int zynqmp_pm_clock_setparent(u32 clock_id, u32 parent_id) 525 { 526 return zynqmp_pm_invoke_fn(PM_CLOCK_SETPARENT, clock_id, 527 parent_id, 0, 0, NULL); 528 } 529 EXPORT_SYMBOL_GPL(zynqmp_pm_clock_setparent); 530 531 /** 532 * zynqmp_pm_clock_getparent() - Get the clock parent for given id 533 * @clock_id: ID of the clock 534 * @parent_id: parent id 535 * 536 * This function is used by master to get parent index 537 * for any clock. 538 * 539 * Return: Returns status, either success or error+reason 540 */ 541 int zynqmp_pm_clock_getparent(u32 clock_id, u32 *parent_id) 542 { 543 u32 ret_payload[PAYLOAD_ARG_CNT]; 544 int ret; 545 546 ret = zynqmp_pm_invoke_fn(PM_CLOCK_GETPARENT, clock_id, 0, 547 0, 0, ret_payload); 548 *parent_id = ret_payload[1]; 549 550 return ret; 551 } 552 EXPORT_SYMBOL_GPL(zynqmp_pm_clock_getparent); 553 554 /** 555 * zynqmp_pm_set_pll_frac_mode() - PM API for set PLL mode 556 * 557 * @clk_id: PLL clock ID 558 * @mode: PLL mode (PLL_MODE_FRAC/PLL_MODE_INT) 559 * 560 * This function sets PLL mode 561 * 562 * Return: Returns status, either success or error+reason 563 */ 564 int zynqmp_pm_set_pll_frac_mode(u32 clk_id, u32 mode) 565 { 566 return zynqmp_pm_invoke_fn(PM_IOCTL, 0, IOCTL_SET_PLL_FRAC_MODE, 567 clk_id, mode, NULL); 568 } 569 EXPORT_SYMBOL_GPL(zynqmp_pm_set_pll_frac_mode); 570 571 /** 572 * zynqmp_pm_get_pll_frac_mode() - PM API for get PLL mode 573 * 574 * @clk_id: PLL clock ID 575 * @mode: PLL mode 576 * 577 * This function return current PLL mode 578 * 579 * Return: Returns status, either success or error+reason 580 */ 581 int zynqmp_pm_get_pll_frac_mode(u32 clk_id, u32 *mode) 582 { 583 return zynqmp_pm_invoke_fn(PM_IOCTL, 0, IOCTL_GET_PLL_FRAC_MODE, 584 clk_id, 0, mode); 585 } 586 EXPORT_SYMBOL_GPL(zynqmp_pm_get_pll_frac_mode); 587 588 /** 589 * zynqmp_pm_set_pll_frac_data() - PM API for setting pll fraction data 590 * 591 * @clk_id: PLL clock ID 592 * @data: fraction data 593 * 594 * This function sets fraction data. 595 * It is valid for fraction mode only. 596 * 597 * Return: Returns status, either success or error+reason 598 */ 599 int zynqmp_pm_set_pll_frac_data(u32 clk_id, u32 data) 600 { 601 return zynqmp_pm_invoke_fn(PM_IOCTL, 0, IOCTL_SET_PLL_FRAC_DATA, 602 clk_id, data, NULL); 603 } 604 EXPORT_SYMBOL_GPL(zynqmp_pm_set_pll_frac_data); 605 606 /** 607 * zynqmp_pm_get_pll_frac_data() - PM API for getting pll fraction data 608 * 609 * @clk_id: PLL clock ID 610 * @data: fraction data 611 * 612 * This function returns fraction data value. 613 * 614 * Return: Returns status, either success or error+reason 615 */ 616 int zynqmp_pm_get_pll_frac_data(u32 clk_id, u32 *data) 617 { 618 return zynqmp_pm_invoke_fn(PM_IOCTL, 0, IOCTL_GET_PLL_FRAC_DATA, 619 clk_id, 0, data); 620 } 621 EXPORT_SYMBOL_GPL(zynqmp_pm_get_pll_frac_data); 622 623 /** 624 * zynqmp_pm_set_sd_tapdelay() - Set tap delay for the SD device 625 * 626 * @node_id: Node ID of the device 627 * @type: Type of tap delay to set (input/output) 628 * @value: Value to set fot the tap delay 629 * 630 * This function sets input/output tap delay for the SD device. 631 * 632 * Return: Returns status, either success or error+reason 633 */ 634 int zynqmp_pm_set_sd_tapdelay(u32 node_id, u32 type, u32 value) 635 { 636 return zynqmp_pm_invoke_fn(PM_IOCTL, node_id, IOCTL_SET_SD_TAPDELAY, 637 type, value, NULL); 638 } 639 EXPORT_SYMBOL_GPL(zynqmp_pm_set_sd_tapdelay); 640 641 /** 642 * zynqmp_pm_sd_dll_reset() - Reset DLL logic 643 * 644 * @node_id: Node ID of the device 645 * @type: Reset type 646 * 647 * This function resets DLL logic for the SD device. 648 * 649 * Return: Returns status, either success or error+reason 650 */ 651 int zynqmp_pm_sd_dll_reset(u32 node_id, u32 type) 652 { 653 return zynqmp_pm_invoke_fn(PM_IOCTL, node_id, IOCTL_SD_DLL_RESET, 654 type, 0, NULL); 655 } 656 EXPORT_SYMBOL_GPL(zynqmp_pm_sd_dll_reset); 657 658 /** 659 * zynqmp_pm_ospi_mux_select() - OSPI Mux selection 660 * 661 * @dev_id: Device Id of the OSPI device. 662 * @select: OSPI Mux select value. 663 * 664 * This function select the OSPI Mux. 665 * 666 * Return: Returns status, either success or error+reason 667 */ 668 int zynqmp_pm_ospi_mux_select(u32 dev_id, u32 select) 669 { 670 return zynqmp_pm_invoke_fn(PM_IOCTL, dev_id, IOCTL_OSPI_MUX_SELECT, 671 select, 0, NULL); 672 } 673 EXPORT_SYMBOL_GPL(zynqmp_pm_ospi_mux_select); 674 675 /** 676 * zynqmp_pm_write_ggs() - PM API for writing global general storage (ggs) 677 * @index: GGS register index 678 * @value: Register value to be written 679 * 680 * This function writes value to GGS register. 681 * 682 * Return: Returns status, either success or error+reason 683 */ 684 int zynqmp_pm_write_ggs(u32 index, u32 value) 685 { 686 return zynqmp_pm_invoke_fn(PM_IOCTL, 0, IOCTL_WRITE_GGS, 687 index, value, NULL); 688 } 689 EXPORT_SYMBOL_GPL(zynqmp_pm_write_ggs); 690 691 /** 692 * zynqmp_pm_read_ggs() - PM API for reading global general storage (ggs) 693 * @index: GGS register index 694 * @value: Register value to be written 695 * 696 * This function returns GGS register value. 697 * 698 * Return: Returns status, either success or error+reason 699 */ 700 int zynqmp_pm_read_ggs(u32 index, u32 *value) 701 { 702 return zynqmp_pm_invoke_fn(PM_IOCTL, 0, IOCTL_READ_GGS, 703 index, 0, value); 704 } 705 EXPORT_SYMBOL_GPL(zynqmp_pm_read_ggs); 706 707 /** 708 * zynqmp_pm_write_pggs() - PM API for writing persistent global general 709 * storage (pggs) 710 * @index: PGGS register index 711 * @value: Register value to be written 712 * 713 * This function writes value to PGGS register. 714 * 715 * Return: Returns status, either success or error+reason 716 */ 717 int zynqmp_pm_write_pggs(u32 index, u32 value) 718 { 719 return zynqmp_pm_invoke_fn(PM_IOCTL, 0, IOCTL_WRITE_PGGS, index, value, 720 NULL); 721 } 722 EXPORT_SYMBOL_GPL(zynqmp_pm_write_pggs); 723 724 /** 725 * zynqmp_pm_read_pggs() - PM API for reading persistent global general 726 * storage (pggs) 727 * @index: PGGS register index 728 * @value: Register value to be written 729 * 730 * This function returns PGGS register value. 731 * 732 * Return: Returns status, either success or error+reason 733 */ 734 int zynqmp_pm_read_pggs(u32 index, u32 *value) 735 { 736 return zynqmp_pm_invoke_fn(PM_IOCTL, 0, IOCTL_READ_PGGS, index, 0, 737 value); 738 } 739 EXPORT_SYMBOL_GPL(zynqmp_pm_read_pggs); 740 741 /** 742 * zynqmp_pm_set_boot_health_status() - PM API for setting healthy boot status 743 * @value: Status value to be written 744 * 745 * This function sets healthy bit value to indicate boot health status 746 * to firmware. 747 * 748 * Return: Returns status, either success or error+reason 749 */ 750 int zynqmp_pm_set_boot_health_status(u32 value) 751 { 752 return zynqmp_pm_invoke_fn(PM_IOCTL, 0, IOCTL_SET_BOOT_HEALTH_STATUS, 753 value, 0, NULL); 754 } 755 756 /** 757 * zynqmp_pm_reset_assert - Request setting of reset (1 - assert, 0 - release) 758 * @reset: Reset to be configured 759 * @assert_flag: Flag stating should reset be asserted (1) or 760 * released (0) 761 * 762 * Return: Returns status, either success or error+reason 763 */ 764 int zynqmp_pm_reset_assert(const enum zynqmp_pm_reset reset, 765 const enum zynqmp_pm_reset_action assert_flag) 766 { 767 return zynqmp_pm_invoke_fn(PM_RESET_ASSERT, reset, assert_flag, 768 0, 0, NULL); 769 } 770 EXPORT_SYMBOL_GPL(zynqmp_pm_reset_assert); 771 772 /** 773 * zynqmp_pm_reset_get_status - Get status of the reset 774 * @reset: Reset whose status should be returned 775 * @status: Returned status 776 * 777 * Return: Returns status, either success or error+reason 778 */ 779 int zynqmp_pm_reset_get_status(const enum zynqmp_pm_reset reset, u32 *status) 780 { 781 u32 ret_payload[PAYLOAD_ARG_CNT]; 782 int ret; 783 784 if (!status) 785 return -EINVAL; 786 787 ret = zynqmp_pm_invoke_fn(PM_RESET_GET_STATUS, reset, 0, 788 0, 0, ret_payload); 789 *status = ret_payload[1]; 790 791 return ret; 792 } 793 EXPORT_SYMBOL_GPL(zynqmp_pm_reset_get_status); 794 795 /** 796 * zynqmp_pm_fpga_load - Perform the fpga load 797 * @address: Address to write to 798 * @size: pl bitstream size 799 * @flags: Bitstream type 800 * -XILINX_ZYNQMP_PM_FPGA_FULL: FPGA full reconfiguration 801 * -XILINX_ZYNQMP_PM_FPGA_PARTIAL: FPGA partial reconfiguration 802 * 803 * This function provides access to pmufw. To transfer 804 * the required bitstream into PL. 805 * 806 * Return: Returns status, either success or error+reason 807 */ 808 int zynqmp_pm_fpga_load(const u64 address, const u32 size, const u32 flags) 809 { 810 return zynqmp_pm_invoke_fn(PM_FPGA_LOAD, lower_32_bits(address), 811 upper_32_bits(address), size, flags, NULL); 812 } 813 EXPORT_SYMBOL_GPL(zynqmp_pm_fpga_load); 814 815 /** 816 * zynqmp_pm_fpga_get_status - Read value from PCAP status register 817 * @value: Value to read 818 * 819 * This function provides access to the pmufw to get the PCAP 820 * status 821 * 822 * Return: Returns status, either success or error+reason 823 */ 824 int zynqmp_pm_fpga_get_status(u32 *value) 825 { 826 u32 ret_payload[PAYLOAD_ARG_CNT]; 827 int ret; 828 829 if (!value) 830 return -EINVAL; 831 832 ret = zynqmp_pm_invoke_fn(PM_FPGA_GET_STATUS, 0, 0, 0, 0, ret_payload); 833 *value = ret_payload[1]; 834 835 return ret; 836 } 837 EXPORT_SYMBOL_GPL(zynqmp_pm_fpga_get_status); 838 839 /** 840 * zynqmp_pm_pinctrl_request - Request Pin from firmware 841 * @pin: Pin number to request 842 * 843 * This function requests pin from firmware. 844 * 845 * Return: Returns status, either success or error+reason. 846 */ 847 int zynqmp_pm_pinctrl_request(const u32 pin) 848 { 849 return zynqmp_pm_invoke_fn(PM_PINCTRL_REQUEST, pin, 0, 0, 0, NULL); 850 } 851 EXPORT_SYMBOL_GPL(zynqmp_pm_pinctrl_request); 852 853 /** 854 * zynqmp_pm_pinctrl_release - Inform firmware that Pin control is released 855 * @pin: Pin number to release 856 * 857 * This function release pin from firmware. 858 * 859 * Return: Returns status, either success or error+reason. 860 */ 861 int zynqmp_pm_pinctrl_release(const u32 pin) 862 { 863 return zynqmp_pm_invoke_fn(PM_PINCTRL_RELEASE, pin, 0, 0, 0, NULL); 864 } 865 EXPORT_SYMBOL_GPL(zynqmp_pm_pinctrl_release); 866 867 /** 868 * zynqmp_pm_pinctrl_get_function - Read function id set for the given pin 869 * @pin: Pin number 870 * @id: Buffer to store function ID 871 * 872 * This function provides the function currently set for the given pin. 873 * 874 * Return: Returns status, either success or error+reason 875 */ 876 int zynqmp_pm_pinctrl_get_function(const u32 pin, u32 *id) 877 { 878 u32 ret_payload[PAYLOAD_ARG_CNT]; 879 int ret; 880 881 if (!id) 882 return -EINVAL; 883 884 ret = zynqmp_pm_invoke_fn(PM_PINCTRL_GET_FUNCTION, pin, 0, 885 0, 0, ret_payload); 886 *id = ret_payload[1]; 887 888 return ret; 889 } 890 EXPORT_SYMBOL_GPL(zynqmp_pm_pinctrl_get_function); 891 892 /** 893 * zynqmp_pm_pinctrl_set_function - Set requested function for the pin 894 * @pin: Pin number 895 * @id: Function ID to set 896 * 897 * This function sets requested function for the given pin. 898 * 899 * Return: Returns status, either success or error+reason. 900 */ 901 int zynqmp_pm_pinctrl_set_function(const u32 pin, const u32 id) 902 { 903 return zynqmp_pm_invoke_fn(PM_PINCTRL_SET_FUNCTION, pin, id, 904 0, 0, NULL); 905 } 906 EXPORT_SYMBOL_GPL(zynqmp_pm_pinctrl_set_function); 907 908 /** 909 * zynqmp_pm_pinctrl_get_config - Get configuration parameter for the pin 910 * @pin: Pin number 911 * @param: Parameter to get 912 * @value: Buffer to store parameter value 913 * 914 * This function gets requested configuration parameter for the given pin. 915 * 916 * Return: Returns status, either success or error+reason. 917 */ 918 int zynqmp_pm_pinctrl_get_config(const u32 pin, const u32 param, 919 u32 *value) 920 { 921 u32 ret_payload[PAYLOAD_ARG_CNT]; 922 int ret; 923 924 if (!value) 925 return -EINVAL; 926 927 ret = zynqmp_pm_invoke_fn(PM_PINCTRL_CONFIG_PARAM_GET, pin, param, 928 0, 0, ret_payload); 929 *value = ret_payload[1]; 930 931 return ret; 932 } 933 EXPORT_SYMBOL_GPL(zynqmp_pm_pinctrl_get_config); 934 935 /** 936 * zynqmp_pm_pinctrl_set_config - Set configuration parameter for the pin 937 * @pin: Pin number 938 * @param: Parameter to set 939 * @value: Parameter value to set 940 * 941 * This function sets requested configuration parameter for the given pin. 942 * 943 * Return: Returns status, either success or error+reason. 944 */ 945 int zynqmp_pm_pinctrl_set_config(const u32 pin, const u32 param, 946 u32 value) 947 { 948 return zynqmp_pm_invoke_fn(PM_PINCTRL_CONFIG_PARAM_SET, pin, 949 param, value, 0, NULL); 950 } 951 EXPORT_SYMBOL_GPL(zynqmp_pm_pinctrl_set_config); 952 953 /** 954 * zynqmp_pm_bootmode_read() - PM Config API for read bootpin status 955 * @ps_mode: Returned output value of ps_mode 956 * 957 * This API function is to be used for notify the power management controller 958 * to read bootpin status. 959 * 960 * Return: status, either success or error+reason 961 */ 962 unsigned int zynqmp_pm_bootmode_read(u32 *ps_mode) 963 { 964 unsigned int ret; 965 u32 ret_payload[PAYLOAD_ARG_CNT]; 966 967 ret = zynqmp_pm_invoke_fn(PM_MMIO_READ, CRL_APB_BOOT_PIN_CTRL, 0, 968 0, 0, ret_payload); 969 970 *ps_mode = ret_payload[1]; 971 972 return ret; 973 } 974 EXPORT_SYMBOL_GPL(zynqmp_pm_bootmode_read); 975 976 /** 977 * zynqmp_pm_bootmode_write() - PM Config API for Configure bootpin 978 * @ps_mode: Value to be written to the bootpin ctrl register 979 * 980 * This API function is to be used for notify the power management controller 981 * to configure bootpin. 982 * 983 * Return: Returns status, either success or error+reason 984 */ 985 int zynqmp_pm_bootmode_write(u32 ps_mode) 986 { 987 return zynqmp_pm_invoke_fn(PM_MMIO_WRITE, CRL_APB_BOOT_PIN_CTRL, 988 CRL_APB_BOOTPIN_CTRL_MASK, ps_mode, 0, NULL); 989 } 990 EXPORT_SYMBOL_GPL(zynqmp_pm_bootmode_write); 991 992 /** 993 * zynqmp_pm_init_finalize() - PM call to inform firmware that the caller 994 * master has initialized its own power management 995 * 996 * Return: Returns status, either success or error+reason 997 * 998 * This API function is to be used for notify the power management controller 999 * about the completed power management initialization. 1000 */ 1001 int zynqmp_pm_init_finalize(void) 1002 { 1003 return zynqmp_pm_invoke_fn(PM_PM_INIT_FINALIZE, 0, 0, 0, 0, NULL); 1004 } 1005 EXPORT_SYMBOL_GPL(zynqmp_pm_init_finalize); 1006 1007 /** 1008 * zynqmp_pm_set_suspend_mode() - Set system suspend mode 1009 * @mode: Mode to set for system suspend 1010 * 1011 * This API function is used to set mode of system suspend. 1012 * 1013 * Return: Returns status, either success or error+reason 1014 */ 1015 int zynqmp_pm_set_suspend_mode(u32 mode) 1016 { 1017 return zynqmp_pm_invoke_fn(PM_SET_SUSPEND_MODE, mode, 0, 0, 0, NULL); 1018 } 1019 EXPORT_SYMBOL_GPL(zynqmp_pm_set_suspend_mode); 1020 1021 /** 1022 * zynqmp_pm_request_node() - Request a node with specific capabilities 1023 * @node: Node ID of the slave 1024 * @capabilities: Requested capabilities of the slave 1025 * @qos: Quality of service (not supported) 1026 * @ack: Flag to specify whether acknowledge is requested 1027 * 1028 * This function is used by master to request particular node from firmware. 1029 * Every master must request node before using it. 1030 * 1031 * Return: Returns status, either success or error+reason 1032 */ 1033 int zynqmp_pm_request_node(const u32 node, const u32 capabilities, 1034 const u32 qos, const enum zynqmp_pm_request_ack ack) 1035 { 1036 return zynqmp_pm_invoke_fn(PM_REQUEST_NODE, node, capabilities, 1037 qos, ack, NULL); 1038 } 1039 EXPORT_SYMBOL_GPL(zynqmp_pm_request_node); 1040 1041 /** 1042 * zynqmp_pm_release_node() - Release a node 1043 * @node: Node ID of the slave 1044 * 1045 * This function is used by master to inform firmware that master 1046 * has released node. Once released, master must not use that node 1047 * without re-request. 1048 * 1049 * Return: Returns status, either success or error+reason 1050 */ 1051 int zynqmp_pm_release_node(const u32 node) 1052 { 1053 return zynqmp_pm_invoke_fn(PM_RELEASE_NODE, node, 0, 0, 0, NULL); 1054 } 1055 EXPORT_SYMBOL_GPL(zynqmp_pm_release_node); 1056 1057 /** 1058 * zynqmp_pm_set_requirement() - PM call to set requirement for PM slaves 1059 * @node: Node ID of the slave 1060 * @capabilities: Requested capabilities of the slave 1061 * @qos: Quality of service (not supported) 1062 * @ack: Flag to specify whether acknowledge is requested 1063 * 1064 * This API function is to be used for slaves a PU already has requested 1065 * to change its capabilities. 1066 * 1067 * Return: Returns status, either success or error+reason 1068 */ 1069 int zynqmp_pm_set_requirement(const u32 node, const u32 capabilities, 1070 const u32 qos, 1071 const enum zynqmp_pm_request_ack ack) 1072 { 1073 return zynqmp_pm_invoke_fn(PM_SET_REQUIREMENT, node, capabilities, 1074 qos, ack, NULL); 1075 } 1076 EXPORT_SYMBOL_GPL(zynqmp_pm_set_requirement); 1077 1078 /** 1079 * zynqmp_pm_load_pdi - Load and process PDI 1080 * @src: Source device where PDI is located 1081 * @address: PDI src address 1082 * 1083 * This function provides support to load PDI from linux 1084 * 1085 * Return: Returns status, either success or error+reason 1086 */ 1087 int zynqmp_pm_load_pdi(const u32 src, const u64 address) 1088 { 1089 return zynqmp_pm_invoke_fn(PM_LOAD_PDI, src, 1090 lower_32_bits(address), 1091 upper_32_bits(address), 0, NULL); 1092 } 1093 EXPORT_SYMBOL_GPL(zynqmp_pm_load_pdi); 1094 1095 /** 1096 * zynqmp_pm_aes_engine - Access AES hardware to encrypt/decrypt the data using 1097 * AES-GCM core. 1098 * @address: Address of the AesParams structure. 1099 * @out: Returned output value 1100 * 1101 * Return: Returns status, either success or error code. 1102 */ 1103 int zynqmp_pm_aes_engine(const u64 address, u32 *out) 1104 { 1105 u32 ret_payload[PAYLOAD_ARG_CNT]; 1106 int ret; 1107 1108 if (!out) 1109 return -EINVAL; 1110 1111 ret = zynqmp_pm_invoke_fn(PM_SECURE_AES, upper_32_bits(address), 1112 lower_32_bits(address), 1113 0, 0, ret_payload); 1114 *out = ret_payload[1]; 1115 1116 return ret; 1117 } 1118 EXPORT_SYMBOL_GPL(zynqmp_pm_aes_engine); 1119 1120 /** 1121 * zynqmp_pm_register_notifier() - PM API for register a subsystem 1122 * to be notified about specific 1123 * event/error. 1124 * @node: Node ID to which the event is related. 1125 * @event: Event Mask of Error events for which wants to get notified. 1126 * @wake: Wake subsystem upon capturing the event if value 1 1127 * @enable: Enable the registration for value 1, disable for value 0 1128 * 1129 * This function is used to register/un-register for particular node-event 1130 * combination in firmware. 1131 * 1132 * Return: Returns status, either success or error+reason 1133 */ 1134 1135 int zynqmp_pm_register_notifier(const u32 node, const u32 event, 1136 const u32 wake, const u32 enable) 1137 { 1138 return zynqmp_pm_invoke_fn(PM_REGISTER_NOTIFIER, node, event, 1139 wake, enable, NULL); 1140 } 1141 EXPORT_SYMBOL_GPL(zynqmp_pm_register_notifier); 1142 1143 /** 1144 * zynqmp_pm_system_shutdown - PM call to request a system shutdown or restart 1145 * @type: Shutdown or restart? 0 for shutdown, 1 for restart 1146 * @subtype: Specifies which system should be restarted or shut down 1147 * 1148 * Return: Returns status, either success or error+reason 1149 */ 1150 int zynqmp_pm_system_shutdown(const u32 type, const u32 subtype) 1151 { 1152 return zynqmp_pm_invoke_fn(PM_SYSTEM_SHUTDOWN, type, subtype, 1153 0, 0, NULL); 1154 } 1155 1156 /** 1157 * struct zynqmp_pm_shutdown_scope - Struct for shutdown scope 1158 * @subtype: Shutdown subtype 1159 * @name: Matching string for scope argument 1160 * 1161 * This struct encapsulates mapping between shutdown scope ID and string. 1162 */ 1163 struct zynqmp_pm_shutdown_scope { 1164 const enum zynqmp_pm_shutdown_subtype subtype; 1165 const char *name; 1166 }; 1167 1168 static struct zynqmp_pm_shutdown_scope shutdown_scopes[] = { 1169 [ZYNQMP_PM_SHUTDOWN_SUBTYPE_SUBSYSTEM] = { 1170 .subtype = ZYNQMP_PM_SHUTDOWN_SUBTYPE_SUBSYSTEM, 1171 .name = "subsystem", 1172 }, 1173 [ZYNQMP_PM_SHUTDOWN_SUBTYPE_PS_ONLY] = { 1174 .subtype = ZYNQMP_PM_SHUTDOWN_SUBTYPE_PS_ONLY, 1175 .name = "ps_only", 1176 }, 1177 [ZYNQMP_PM_SHUTDOWN_SUBTYPE_SYSTEM] = { 1178 .subtype = ZYNQMP_PM_SHUTDOWN_SUBTYPE_SYSTEM, 1179 .name = "system", 1180 }, 1181 }; 1182 1183 static struct zynqmp_pm_shutdown_scope *selected_scope = 1184 &shutdown_scopes[ZYNQMP_PM_SHUTDOWN_SUBTYPE_SYSTEM]; 1185 1186 /** 1187 * zynqmp_pm_is_shutdown_scope_valid - Check if shutdown scope string is valid 1188 * @scope_string: Shutdown scope string 1189 * 1190 * Return: Return pointer to matching shutdown scope struct from 1191 * array of available options in system if string is valid, 1192 * otherwise returns NULL. 1193 */ 1194 static struct zynqmp_pm_shutdown_scope* 1195 zynqmp_pm_is_shutdown_scope_valid(const char *scope_string) 1196 { 1197 int count; 1198 1199 for (count = 0; count < ARRAY_SIZE(shutdown_scopes); count++) 1200 if (sysfs_streq(scope_string, shutdown_scopes[count].name)) 1201 return &shutdown_scopes[count]; 1202 1203 return NULL; 1204 } 1205 1206 static ssize_t shutdown_scope_show(struct device *device, 1207 struct device_attribute *attr, 1208 char *buf) 1209 { 1210 int i; 1211 1212 for (i = 0; i < ARRAY_SIZE(shutdown_scopes); i++) { 1213 if (&shutdown_scopes[i] == selected_scope) { 1214 strcat(buf, "["); 1215 strcat(buf, shutdown_scopes[i].name); 1216 strcat(buf, "]"); 1217 } else { 1218 strcat(buf, shutdown_scopes[i].name); 1219 } 1220 strcat(buf, " "); 1221 } 1222 strcat(buf, "\n"); 1223 1224 return strlen(buf); 1225 } 1226 1227 static ssize_t shutdown_scope_store(struct device *device, 1228 struct device_attribute *attr, 1229 const char *buf, size_t count) 1230 { 1231 int ret; 1232 struct zynqmp_pm_shutdown_scope *scope; 1233 1234 scope = zynqmp_pm_is_shutdown_scope_valid(buf); 1235 if (!scope) 1236 return -EINVAL; 1237 1238 ret = zynqmp_pm_system_shutdown(ZYNQMP_PM_SHUTDOWN_TYPE_SETSCOPE_ONLY, 1239 scope->subtype); 1240 if (ret) { 1241 pr_err("unable to set shutdown scope %s\n", buf); 1242 return ret; 1243 } 1244 1245 selected_scope = scope; 1246 1247 return count; 1248 } 1249 1250 static DEVICE_ATTR_RW(shutdown_scope); 1251 1252 static ssize_t health_status_store(struct device *device, 1253 struct device_attribute *attr, 1254 const char *buf, size_t count) 1255 { 1256 int ret; 1257 unsigned int value; 1258 1259 ret = kstrtouint(buf, 10, &value); 1260 if (ret) 1261 return ret; 1262 1263 ret = zynqmp_pm_set_boot_health_status(value); 1264 if (ret) { 1265 dev_err(device, "unable to set healthy bit value to %u\n", 1266 value); 1267 return ret; 1268 } 1269 1270 return count; 1271 } 1272 1273 static DEVICE_ATTR_WO(health_status); 1274 1275 static ssize_t ggs_show(struct device *device, 1276 struct device_attribute *attr, 1277 char *buf, 1278 u32 reg) 1279 { 1280 int ret; 1281 u32 ret_payload[PAYLOAD_ARG_CNT]; 1282 1283 ret = zynqmp_pm_read_ggs(reg, ret_payload); 1284 if (ret) 1285 return ret; 1286 1287 return sprintf(buf, "0x%x\n", ret_payload[1]); 1288 } 1289 1290 static ssize_t ggs_store(struct device *device, 1291 struct device_attribute *attr, 1292 const char *buf, size_t count, 1293 u32 reg) 1294 { 1295 long value; 1296 int ret; 1297 1298 if (reg >= GSS_NUM_REGS) 1299 return -EINVAL; 1300 1301 ret = kstrtol(buf, 16, &value); 1302 if (ret) { 1303 count = -EFAULT; 1304 goto err; 1305 } 1306 1307 ret = zynqmp_pm_write_ggs(reg, value); 1308 if (ret) 1309 count = -EFAULT; 1310 err: 1311 return count; 1312 } 1313 1314 /* GGS register show functions */ 1315 #define GGS0_SHOW(N) \ 1316 ssize_t ggs##N##_show(struct device *device, \ 1317 struct device_attribute *attr, \ 1318 char *buf) \ 1319 { \ 1320 return ggs_show(device, attr, buf, N); \ 1321 } 1322 1323 static GGS0_SHOW(0); 1324 static GGS0_SHOW(1); 1325 static GGS0_SHOW(2); 1326 static GGS0_SHOW(3); 1327 1328 /* GGS register store function */ 1329 #define GGS0_STORE(N) \ 1330 ssize_t ggs##N##_store(struct device *device, \ 1331 struct device_attribute *attr, \ 1332 const char *buf, \ 1333 size_t count) \ 1334 { \ 1335 return ggs_store(device, attr, buf, count, N); \ 1336 } 1337 1338 static GGS0_STORE(0); 1339 static GGS0_STORE(1); 1340 static GGS0_STORE(2); 1341 static GGS0_STORE(3); 1342 1343 static ssize_t pggs_show(struct device *device, 1344 struct device_attribute *attr, 1345 char *buf, 1346 u32 reg) 1347 { 1348 int ret; 1349 u32 ret_payload[PAYLOAD_ARG_CNT]; 1350 1351 ret = zynqmp_pm_read_pggs(reg, ret_payload); 1352 if (ret) 1353 return ret; 1354 1355 return sprintf(buf, "0x%x\n", ret_payload[1]); 1356 } 1357 1358 static ssize_t pggs_store(struct device *device, 1359 struct device_attribute *attr, 1360 const char *buf, size_t count, 1361 u32 reg) 1362 { 1363 long value; 1364 int ret; 1365 1366 if (reg >= GSS_NUM_REGS) 1367 return -EINVAL; 1368 1369 ret = kstrtol(buf, 16, &value); 1370 if (ret) { 1371 count = -EFAULT; 1372 goto err; 1373 } 1374 1375 ret = zynqmp_pm_write_pggs(reg, value); 1376 if (ret) 1377 count = -EFAULT; 1378 1379 err: 1380 return count; 1381 } 1382 1383 #define PGGS0_SHOW(N) \ 1384 ssize_t pggs##N##_show(struct device *device, \ 1385 struct device_attribute *attr, \ 1386 char *buf) \ 1387 { \ 1388 return pggs_show(device, attr, buf, N); \ 1389 } 1390 1391 #define PGGS0_STORE(N) \ 1392 ssize_t pggs##N##_store(struct device *device, \ 1393 struct device_attribute *attr, \ 1394 const char *buf, \ 1395 size_t count) \ 1396 { \ 1397 return pggs_store(device, attr, buf, count, N); \ 1398 } 1399 1400 /* PGGS register show functions */ 1401 static PGGS0_SHOW(0); 1402 static PGGS0_SHOW(1); 1403 static PGGS0_SHOW(2); 1404 static PGGS0_SHOW(3); 1405 1406 /* PGGS register store functions */ 1407 static PGGS0_STORE(0); 1408 static PGGS0_STORE(1); 1409 static PGGS0_STORE(2); 1410 static PGGS0_STORE(3); 1411 1412 /* GGS register attributes */ 1413 static DEVICE_ATTR_RW(ggs0); 1414 static DEVICE_ATTR_RW(ggs1); 1415 static DEVICE_ATTR_RW(ggs2); 1416 static DEVICE_ATTR_RW(ggs3); 1417 1418 /* PGGS register attributes */ 1419 static DEVICE_ATTR_RW(pggs0); 1420 static DEVICE_ATTR_RW(pggs1); 1421 static DEVICE_ATTR_RW(pggs2); 1422 static DEVICE_ATTR_RW(pggs3); 1423 1424 static struct attribute *zynqmp_firmware_attrs[] = { 1425 &dev_attr_ggs0.attr, 1426 &dev_attr_ggs1.attr, 1427 &dev_attr_ggs2.attr, 1428 &dev_attr_ggs3.attr, 1429 &dev_attr_pggs0.attr, 1430 &dev_attr_pggs1.attr, 1431 &dev_attr_pggs2.attr, 1432 &dev_attr_pggs3.attr, 1433 &dev_attr_shutdown_scope.attr, 1434 &dev_attr_health_status.attr, 1435 NULL, 1436 }; 1437 1438 ATTRIBUTE_GROUPS(zynqmp_firmware); 1439 1440 static int zynqmp_firmware_probe(struct platform_device *pdev) 1441 { 1442 struct device *dev = &pdev->dev; 1443 struct device_node *np; 1444 int ret; 1445 1446 np = of_find_compatible_node(NULL, NULL, "xlnx,zynqmp"); 1447 if (!np) { 1448 np = of_find_compatible_node(NULL, NULL, "xlnx,versal"); 1449 if (!np) 1450 return 0; 1451 1452 feature_check_enabled = true; 1453 } 1454 of_node_put(np); 1455 1456 ret = get_set_conduit_method(dev->of_node); 1457 if (ret) 1458 return ret; 1459 1460 /* Check PM API version number */ 1461 zynqmp_pm_get_api_version(&pm_api_version); 1462 if (pm_api_version < ZYNQMP_PM_VERSION) { 1463 panic("%s Platform Management API version error. Expected: v%d.%d - Found: v%d.%d\n", 1464 __func__, 1465 ZYNQMP_PM_VERSION_MAJOR, ZYNQMP_PM_VERSION_MINOR, 1466 pm_api_version >> 16, pm_api_version & 0xFFFF); 1467 } 1468 1469 pr_info("%s Platform Management API v%d.%d\n", __func__, 1470 pm_api_version >> 16, pm_api_version & 0xFFFF); 1471 1472 /* Check trustzone version number */ 1473 ret = zynqmp_pm_get_trustzone_version(&pm_tz_version); 1474 if (ret) 1475 panic("Legacy trustzone found without version support\n"); 1476 1477 if (pm_tz_version < ZYNQMP_TZ_VERSION) 1478 panic("%s Trustzone version error. Expected: v%d.%d - Found: v%d.%d\n", 1479 __func__, 1480 ZYNQMP_TZ_VERSION_MAJOR, ZYNQMP_TZ_VERSION_MINOR, 1481 pm_tz_version >> 16, pm_tz_version & 0xFFFF); 1482 1483 pr_info("%s Trustzone version v%d.%d\n", __func__, 1484 pm_tz_version >> 16, pm_tz_version & 0xFFFF); 1485 1486 ret = mfd_add_devices(&pdev->dev, PLATFORM_DEVID_NONE, firmware_devs, 1487 ARRAY_SIZE(firmware_devs), NULL, 0, NULL); 1488 if (ret) { 1489 dev_err(&pdev->dev, "failed to add MFD devices %d\n", ret); 1490 return ret; 1491 } 1492 1493 zynqmp_pm_api_debugfs_init(); 1494 1495 return of_platform_populate(dev->of_node, NULL, NULL, dev); 1496 } 1497 1498 static int zynqmp_firmware_remove(struct platform_device *pdev) 1499 { 1500 struct pm_api_feature_data *feature_data; 1501 struct hlist_node *tmp; 1502 int i; 1503 1504 mfd_remove_devices(&pdev->dev); 1505 zynqmp_pm_api_debugfs_exit(); 1506 1507 hash_for_each_safe(pm_api_features_map, i, tmp, feature_data, hentry) { 1508 hash_del(&feature_data->hentry); 1509 kfree(feature_data); 1510 } 1511 1512 return 0; 1513 } 1514 1515 static const struct of_device_id zynqmp_firmware_of_match[] = { 1516 {.compatible = "xlnx,zynqmp-firmware"}, 1517 {.compatible = "xlnx,versal-firmware"}, 1518 {}, 1519 }; 1520 MODULE_DEVICE_TABLE(of, zynqmp_firmware_of_match); 1521 1522 static struct platform_driver zynqmp_firmware_driver = { 1523 .driver = { 1524 .name = "zynqmp_firmware", 1525 .of_match_table = zynqmp_firmware_of_match, 1526 .dev_groups = zynqmp_firmware_groups, 1527 }, 1528 .probe = zynqmp_firmware_probe, 1529 .remove = zynqmp_firmware_remove, 1530 }; 1531 module_platform_driver(zynqmp_firmware_driver); 1532