1 // SPDX-License-Identifier: GPL-2.0 2 3 /* 4 * Copyright 2016-2019 HabanaLabs, Ltd. 5 * All Rights Reserved. 6 */ 7 8 #include "habanalabs.h" 9 10 #include <linux/pci.h> 11 #include <linux/hwmon.h> 12 13 #define HWMON_NR_SENSOR_TYPES (hwmon_max) 14 15 #ifdef _HAS_HWMON_HWMON_T_ENABLE 16 17 static u32 fixup_flags_legacy_fw(struct hl_device *hdev, enum hwmon_sensor_types type, 18 u32 cpucp_flags) 19 { 20 u32 flags; 21 22 switch (type) { 23 case hwmon_temp: 24 flags = (cpucp_flags << 1) | HWMON_T_ENABLE; 25 break; 26 27 case hwmon_in: 28 flags = (cpucp_flags << 1) | HWMON_I_ENABLE; 29 break; 30 31 case hwmon_curr: 32 flags = (cpucp_flags << 1) | HWMON_C_ENABLE; 33 break; 34 35 case hwmon_fan: 36 flags = (cpucp_flags << 1) | HWMON_F_ENABLE; 37 break; 38 39 case hwmon_power: 40 flags = (cpucp_flags << 1) | HWMON_P_ENABLE; 41 break; 42 43 case hwmon_pwm: 44 /* enable bit was here from day 1, so no need to adjust */ 45 flags = cpucp_flags; 46 break; 47 48 default: 49 dev_err(hdev->dev, "unsupported h/w sensor type %d\n", type); 50 flags = cpucp_flags; 51 break; 52 } 53 54 return flags; 55 } 56 57 static u32 fixup_attr_legacy_fw(u32 attr) 58 { 59 return (attr - 1); 60 } 61 62 #else 63 64 static u32 fixup_flags_legacy_fw(struct hl_device *hdev, enum hwmon_sensor_types type, 65 u32 cpucp_flags) 66 { 67 return cpucp_flags; 68 } 69 70 static u32 fixup_attr_legacy_fw(u32 attr) 71 { 72 return attr; 73 } 74 75 #endif /* !_HAS_HWMON_HWMON_T_ENABLE */ 76 77 static u32 adjust_hwmon_flags(struct hl_device *hdev, enum hwmon_sensor_types type, u32 cpucp_flags) 78 { 79 u32 flags, cpucp_input_val; 80 bool use_cpucp_enum; 81 82 use_cpucp_enum = (hdev->asic_prop.fw_app_cpu_boot_dev_sts0 & 83 CPU_BOOT_DEV_STS0_MAP_HWMON_EN) ? true : false; 84 85 /* If f/w is using it's own enum, we need to check if the properties values are aligned. 86 * If not, it means we need to adjust the values to the new format that is used in the 87 * kernel since 5.6 (enum values were incremented by 1 by adding a new enable value). 88 */ 89 if (use_cpucp_enum) { 90 switch (type) { 91 case hwmon_temp: 92 cpucp_input_val = cpucp_temp_input; 93 if (cpucp_input_val == hwmon_temp_input) 94 flags = cpucp_flags; 95 else 96 flags = (cpucp_flags << 1) | HWMON_T_ENABLE; 97 break; 98 99 case hwmon_in: 100 cpucp_input_val = cpucp_in_input; 101 if (cpucp_input_val == hwmon_in_input) 102 flags = cpucp_flags; 103 else 104 flags = (cpucp_flags << 1) | HWMON_I_ENABLE; 105 break; 106 107 case hwmon_curr: 108 cpucp_input_val = cpucp_curr_input; 109 if (cpucp_input_val == hwmon_curr_input) 110 flags = cpucp_flags; 111 else 112 flags = (cpucp_flags << 1) | HWMON_C_ENABLE; 113 break; 114 115 case hwmon_fan: 116 cpucp_input_val = cpucp_fan_input; 117 if (cpucp_input_val == hwmon_fan_input) 118 flags = cpucp_flags; 119 else 120 flags = (cpucp_flags << 1) | HWMON_F_ENABLE; 121 break; 122 123 case hwmon_pwm: 124 /* enable bit was here from day 1, so no need to adjust */ 125 flags = cpucp_flags; 126 break; 127 128 case hwmon_power: 129 cpucp_input_val = CPUCP_POWER_INPUT; 130 if (cpucp_input_val == hwmon_power_input) 131 flags = cpucp_flags; 132 else 133 flags = (cpucp_flags << 1) | HWMON_P_ENABLE; 134 break; 135 136 default: 137 dev_err(hdev->dev, "unsupported h/w sensor type %d\n", type); 138 flags = cpucp_flags; 139 break; 140 } 141 } else { 142 flags = fixup_flags_legacy_fw(hdev, type, cpucp_flags); 143 } 144 145 return flags; 146 } 147 148 int hl_build_hwmon_channel_info(struct hl_device *hdev, struct cpucp_sensor *sensors_arr) 149 { 150 u32 num_sensors_for_type, flags, num_active_sensor_types = 0, arr_size = 0, *curr_arr; 151 u32 sensors_by_type_next_index[HWMON_NR_SENSOR_TYPES] = {0}; 152 u32 *sensors_by_type[HWMON_NR_SENSOR_TYPES] = {NULL}; 153 struct hwmon_channel_info **channels_info; 154 u32 counts[HWMON_NR_SENSOR_TYPES] = {0}; 155 enum hwmon_sensor_types type; 156 int rc, i, j; 157 158 for (i = 0 ; i < CPUCP_MAX_SENSORS ; i++) { 159 type = le32_to_cpu(sensors_arr[i].type); 160 161 if ((type == 0) && (sensors_arr[i].flags == 0)) 162 break; 163 164 if (type >= HWMON_NR_SENSOR_TYPES) { 165 dev_err(hdev->dev, "Got wrong sensor type %d from device\n", type); 166 return -EINVAL; 167 } 168 169 counts[type]++; 170 arr_size++; 171 } 172 173 for (i = 0 ; i < HWMON_NR_SENSOR_TYPES ; i++) { 174 if (counts[i] == 0) 175 continue; 176 177 num_sensors_for_type = counts[i] + 1; 178 dev_dbg(hdev->dev, "num_sensors_for_type %d = %d\n", i, num_sensors_for_type); 179 180 curr_arr = kcalloc(num_sensors_for_type, sizeof(*curr_arr), GFP_KERNEL); 181 if (!curr_arr) { 182 rc = -ENOMEM; 183 goto sensors_type_err; 184 } 185 186 num_active_sensor_types++; 187 sensors_by_type[i] = curr_arr; 188 } 189 190 for (i = 0 ; i < arr_size ; i++) { 191 type = le32_to_cpu(sensors_arr[i].type); 192 curr_arr = sensors_by_type[type]; 193 flags = adjust_hwmon_flags(hdev, type, le32_to_cpu(sensors_arr[i].flags)); 194 curr_arr[sensors_by_type_next_index[type]++] = flags; 195 } 196 197 channels_info = kcalloc(num_active_sensor_types + 1, sizeof(struct hwmon_channel_info *), 198 GFP_KERNEL); 199 if (!channels_info) { 200 rc = -ENOMEM; 201 goto channels_info_array_err; 202 } 203 204 for (i = 0 ; i < num_active_sensor_types ; i++) { 205 channels_info[i] = kzalloc(sizeof(*channels_info[i]), GFP_KERNEL); 206 if (!channels_info[i]) { 207 rc = -ENOMEM; 208 goto channel_info_err; 209 } 210 } 211 212 for (i = 0, j = 0 ; i < HWMON_NR_SENSOR_TYPES ; i++) { 213 if (!sensors_by_type[i]) 214 continue; 215 216 channels_info[j]->type = i; 217 channels_info[j]->config = sensors_by_type[i]; 218 j++; 219 } 220 221 hdev->hl_chip_info->info = (const struct hwmon_channel_info **)channels_info; 222 223 return 0; 224 225 channel_info_err: 226 for (i = 0 ; i < num_active_sensor_types ; i++) { 227 if (channels_info[i]) { 228 kfree(channels_info[i]->config); 229 kfree(channels_info[i]); 230 } 231 } 232 kfree(channels_info); 233 234 channels_info_array_err: 235 sensors_type_err: 236 for (i = 0 ; i < HWMON_NR_SENSOR_TYPES ; i++) 237 kfree(sensors_by_type[i]); 238 239 return rc; 240 } 241 242 static int hl_read(struct device *dev, enum hwmon_sensor_types type, 243 u32 attr, int channel, long *val) 244 { 245 struct hl_device *hdev = dev_get_drvdata(dev); 246 bool use_cpucp_enum; 247 u32 cpucp_attr; 248 int rc; 249 250 if (!hl_device_operational(hdev, NULL)) 251 return -ENODEV; 252 253 use_cpucp_enum = (hdev->asic_prop.fw_app_cpu_boot_dev_sts0 & 254 CPU_BOOT_DEV_STS0_MAP_HWMON_EN) ? true : false; 255 256 switch (type) { 257 case hwmon_temp: 258 switch (attr) { 259 case hwmon_temp_input: 260 cpucp_attr = cpucp_temp_input; 261 break; 262 case hwmon_temp_max: 263 cpucp_attr = cpucp_temp_max; 264 break; 265 case hwmon_temp_crit: 266 cpucp_attr = cpucp_temp_crit; 267 break; 268 case hwmon_temp_max_hyst: 269 cpucp_attr = cpucp_temp_max_hyst; 270 break; 271 case hwmon_temp_crit_hyst: 272 cpucp_attr = cpucp_temp_crit_hyst; 273 break; 274 case hwmon_temp_offset: 275 cpucp_attr = cpucp_temp_offset; 276 break; 277 case hwmon_temp_highest: 278 cpucp_attr = cpucp_temp_highest; 279 break; 280 default: 281 return -EINVAL; 282 } 283 284 if (use_cpucp_enum) 285 rc = hl_get_temperature(hdev, channel, cpucp_attr, val); 286 else 287 rc = hl_get_temperature(hdev, channel, fixup_attr_legacy_fw(attr), val); 288 break; 289 case hwmon_in: 290 switch (attr) { 291 case hwmon_in_input: 292 cpucp_attr = cpucp_in_input; 293 break; 294 case hwmon_in_min: 295 cpucp_attr = cpucp_in_min; 296 break; 297 case hwmon_in_max: 298 cpucp_attr = cpucp_in_max; 299 break; 300 case hwmon_in_highest: 301 cpucp_attr = cpucp_in_highest; 302 break; 303 default: 304 return -EINVAL; 305 } 306 307 if (use_cpucp_enum) 308 rc = hl_get_voltage(hdev, channel, cpucp_attr, val); 309 else 310 rc = hl_get_voltage(hdev, channel, fixup_attr_legacy_fw(attr), val); 311 break; 312 case hwmon_curr: 313 switch (attr) { 314 case hwmon_curr_input: 315 cpucp_attr = cpucp_curr_input; 316 break; 317 case hwmon_curr_min: 318 cpucp_attr = cpucp_curr_min; 319 break; 320 case hwmon_curr_max: 321 cpucp_attr = cpucp_curr_max; 322 break; 323 case hwmon_curr_highest: 324 cpucp_attr = cpucp_curr_highest; 325 break; 326 default: 327 return -EINVAL; 328 } 329 330 if (use_cpucp_enum) 331 rc = hl_get_current(hdev, channel, cpucp_attr, val); 332 else 333 rc = hl_get_current(hdev, channel, fixup_attr_legacy_fw(attr), val); 334 break; 335 case hwmon_fan: 336 switch (attr) { 337 case hwmon_fan_input: 338 cpucp_attr = cpucp_fan_input; 339 break; 340 case hwmon_fan_min: 341 cpucp_attr = cpucp_fan_min; 342 break; 343 case hwmon_fan_max: 344 cpucp_attr = cpucp_fan_max; 345 break; 346 default: 347 return -EINVAL; 348 } 349 350 if (use_cpucp_enum) 351 rc = hl_get_fan_speed(hdev, channel, cpucp_attr, val); 352 else 353 rc = hl_get_fan_speed(hdev, channel, fixup_attr_legacy_fw(attr), val); 354 break; 355 case hwmon_pwm: 356 switch (attr) { 357 case hwmon_pwm_input: 358 cpucp_attr = cpucp_pwm_input; 359 break; 360 case hwmon_pwm_enable: 361 cpucp_attr = cpucp_pwm_enable; 362 break; 363 default: 364 return -EINVAL; 365 } 366 367 if (use_cpucp_enum) 368 rc = hl_get_pwm_info(hdev, channel, cpucp_attr, val); 369 else 370 /* no need for fixup as pwm was aligned from day 1 */ 371 rc = hl_get_pwm_info(hdev, channel, attr, val); 372 break; 373 case hwmon_power: 374 switch (attr) { 375 case hwmon_power_input: 376 cpucp_attr = CPUCP_POWER_INPUT; 377 break; 378 case hwmon_power_input_highest: 379 cpucp_attr = CPUCP_POWER_INPUT_HIGHEST; 380 break; 381 default: 382 return -EINVAL; 383 } 384 385 if (use_cpucp_enum) 386 rc = hl_get_power(hdev, channel, cpucp_attr, val); 387 else 388 rc = hl_get_power(hdev, channel, fixup_attr_legacy_fw(attr), val); 389 break; 390 default: 391 return -EINVAL; 392 } 393 return rc; 394 } 395 396 static int hl_write(struct device *dev, enum hwmon_sensor_types type, 397 u32 attr, int channel, long val) 398 { 399 struct hl_device *hdev = dev_get_drvdata(dev); 400 u32 cpucp_attr; 401 bool use_cpucp_enum = (hdev->asic_prop.fw_app_cpu_boot_dev_sts0 & 402 CPU_BOOT_DEV_STS0_MAP_HWMON_EN) ? true : false; 403 404 if (!hl_device_operational(hdev, NULL)) 405 return -ENODEV; 406 407 switch (type) { 408 case hwmon_temp: 409 switch (attr) { 410 case hwmon_temp_offset: 411 cpucp_attr = cpucp_temp_offset; 412 break; 413 case hwmon_temp_reset_history: 414 cpucp_attr = cpucp_temp_reset_history; 415 break; 416 default: 417 return -EINVAL; 418 } 419 420 if (use_cpucp_enum) 421 hl_set_temperature(hdev, channel, cpucp_attr, val); 422 else 423 hl_set_temperature(hdev, channel, fixup_attr_legacy_fw(attr), val); 424 break; 425 case hwmon_pwm: 426 switch (attr) { 427 case hwmon_pwm_input: 428 cpucp_attr = cpucp_pwm_input; 429 break; 430 case hwmon_pwm_enable: 431 cpucp_attr = cpucp_pwm_enable; 432 break; 433 default: 434 return -EINVAL; 435 } 436 437 if (use_cpucp_enum) 438 hl_set_pwm_info(hdev, channel, cpucp_attr, val); 439 else 440 /* no need for fixup as pwm was aligned from day 1 */ 441 hl_set_pwm_info(hdev, channel, attr, val); 442 break; 443 case hwmon_in: 444 switch (attr) { 445 case hwmon_in_reset_history: 446 cpucp_attr = cpucp_in_reset_history; 447 break; 448 default: 449 return -EINVAL; 450 } 451 452 if (use_cpucp_enum) 453 hl_set_voltage(hdev, channel, cpucp_attr, val); 454 else 455 hl_set_voltage(hdev, channel, fixup_attr_legacy_fw(attr), val); 456 break; 457 case hwmon_curr: 458 switch (attr) { 459 case hwmon_curr_reset_history: 460 cpucp_attr = cpucp_curr_reset_history; 461 break; 462 default: 463 return -EINVAL; 464 } 465 466 if (use_cpucp_enum) 467 hl_set_current(hdev, channel, cpucp_attr, val); 468 else 469 hl_set_current(hdev, channel, fixup_attr_legacy_fw(attr), val); 470 break; 471 case hwmon_power: 472 switch (attr) { 473 case hwmon_power_reset_history: 474 cpucp_attr = CPUCP_POWER_RESET_INPUT_HISTORY; 475 break; 476 default: 477 return -EINVAL; 478 } 479 480 if (use_cpucp_enum) 481 hl_set_power(hdev, channel, cpucp_attr, val); 482 else 483 hl_set_power(hdev, channel, fixup_attr_legacy_fw(attr), val); 484 break; 485 default: 486 return -EINVAL; 487 } 488 return 0; 489 } 490 491 static umode_t hl_is_visible(const void *data, enum hwmon_sensor_types type, 492 u32 attr, int channel) 493 { 494 switch (type) { 495 case hwmon_temp: 496 switch (attr) { 497 case hwmon_temp_input: 498 case hwmon_temp_max: 499 case hwmon_temp_max_hyst: 500 case hwmon_temp_crit: 501 case hwmon_temp_crit_hyst: 502 case hwmon_temp_highest: 503 return 0444; 504 case hwmon_temp_offset: 505 return 0644; 506 case hwmon_temp_reset_history: 507 return 0200; 508 } 509 break; 510 case hwmon_in: 511 switch (attr) { 512 case hwmon_in_input: 513 case hwmon_in_min: 514 case hwmon_in_max: 515 case hwmon_in_highest: 516 return 0444; 517 case hwmon_in_reset_history: 518 return 0200; 519 } 520 break; 521 case hwmon_curr: 522 switch (attr) { 523 case hwmon_curr_input: 524 case hwmon_curr_min: 525 case hwmon_curr_max: 526 case hwmon_curr_highest: 527 return 0444; 528 case hwmon_curr_reset_history: 529 return 0200; 530 } 531 break; 532 case hwmon_fan: 533 switch (attr) { 534 case hwmon_fan_input: 535 case hwmon_fan_min: 536 case hwmon_fan_max: 537 return 0444; 538 } 539 break; 540 case hwmon_pwm: 541 switch (attr) { 542 case hwmon_pwm_input: 543 case hwmon_pwm_enable: 544 return 0644; 545 } 546 break; 547 case hwmon_power: 548 switch (attr) { 549 case hwmon_power_input: 550 case hwmon_power_input_highest: 551 return 0444; 552 case hwmon_power_reset_history: 553 return 0200; 554 } 555 break; 556 default: 557 break; 558 } 559 return 0; 560 } 561 562 static const struct hwmon_ops hl_hwmon_ops = { 563 .is_visible = hl_is_visible, 564 .read = hl_read, 565 .write = hl_write 566 }; 567 568 int hl_get_temperature(struct hl_device *hdev, 569 int sensor_index, u32 attr, long *value) 570 { 571 struct cpucp_packet pkt; 572 u64 result; 573 int rc; 574 575 memset(&pkt, 0, sizeof(pkt)); 576 577 pkt.ctl = cpu_to_le32(CPUCP_PACKET_TEMPERATURE_GET << 578 CPUCP_PKT_CTL_OPCODE_SHIFT); 579 pkt.sensor_index = __cpu_to_le16(sensor_index); 580 pkt.type = __cpu_to_le16(attr); 581 582 dev_dbg(hdev->dev, "get temp, ctl 0x%x, sensor %d, type %d\n", 583 pkt.ctl, pkt.sensor_index, pkt.type); 584 585 rc = hdev->asic_funcs->send_cpu_message(hdev, (u32 *) &pkt, sizeof(pkt), 586 0, &result); 587 588 *value = (long) result; 589 590 if (rc) { 591 dev_err(hdev->dev, 592 "Failed to get temperature from sensor %d, error %d\n", 593 sensor_index, rc); 594 *value = 0; 595 } 596 597 return rc; 598 } 599 600 int hl_set_temperature(struct hl_device *hdev, 601 int sensor_index, u32 attr, long value) 602 { 603 struct cpucp_packet pkt; 604 int rc; 605 606 memset(&pkt, 0, sizeof(pkt)); 607 608 pkt.ctl = cpu_to_le32(CPUCP_PACKET_TEMPERATURE_SET << 609 CPUCP_PKT_CTL_OPCODE_SHIFT); 610 pkt.sensor_index = __cpu_to_le16(sensor_index); 611 pkt.type = __cpu_to_le16(attr); 612 pkt.value = __cpu_to_le64(value); 613 614 rc = hdev->asic_funcs->send_cpu_message(hdev, (u32 *) &pkt, sizeof(pkt), 615 0, NULL); 616 617 if (rc) 618 dev_err(hdev->dev, 619 "Failed to set temperature of sensor %d, error %d\n", 620 sensor_index, rc); 621 622 return rc; 623 } 624 625 int hl_get_voltage(struct hl_device *hdev, 626 int sensor_index, u32 attr, long *value) 627 { 628 struct cpucp_packet pkt; 629 u64 result; 630 int rc; 631 632 memset(&pkt, 0, sizeof(pkt)); 633 634 pkt.ctl = cpu_to_le32(CPUCP_PACKET_VOLTAGE_GET << 635 CPUCP_PKT_CTL_OPCODE_SHIFT); 636 pkt.sensor_index = __cpu_to_le16(sensor_index); 637 pkt.type = __cpu_to_le16(attr); 638 639 rc = hdev->asic_funcs->send_cpu_message(hdev, (u32 *) &pkt, sizeof(pkt), 640 0, &result); 641 642 *value = (long) result; 643 644 if (rc) { 645 dev_err(hdev->dev, 646 "Failed to get voltage from sensor %d, error %d\n", 647 sensor_index, rc); 648 *value = 0; 649 } 650 651 return rc; 652 } 653 654 int hl_get_current(struct hl_device *hdev, 655 int sensor_index, u32 attr, long *value) 656 { 657 struct cpucp_packet pkt; 658 u64 result; 659 int rc; 660 661 memset(&pkt, 0, sizeof(pkt)); 662 663 pkt.ctl = cpu_to_le32(CPUCP_PACKET_CURRENT_GET << 664 CPUCP_PKT_CTL_OPCODE_SHIFT); 665 pkt.sensor_index = __cpu_to_le16(sensor_index); 666 pkt.type = __cpu_to_le16(attr); 667 668 rc = hdev->asic_funcs->send_cpu_message(hdev, (u32 *) &pkt, sizeof(pkt), 669 0, &result); 670 671 *value = (long) result; 672 673 if (rc) { 674 dev_err(hdev->dev, 675 "Failed to get current from sensor %d, error %d\n", 676 sensor_index, rc); 677 *value = 0; 678 } 679 680 return rc; 681 } 682 683 int hl_get_fan_speed(struct hl_device *hdev, 684 int sensor_index, u32 attr, long *value) 685 { 686 struct cpucp_packet pkt; 687 u64 result; 688 int rc; 689 690 memset(&pkt, 0, sizeof(pkt)); 691 692 pkt.ctl = cpu_to_le32(CPUCP_PACKET_FAN_SPEED_GET << 693 CPUCP_PKT_CTL_OPCODE_SHIFT); 694 pkt.sensor_index = __cpu_to_le16(sensor_index); 695 pkt.type = __cpu_to_le16(attr); 696 697 rc = hdev->asic_funcs->send_cpu_message(hdev, (u32 *) &pkt, sizeof(pkt), 698 0, &result); 699 700 *value = (long) result; 701 702 if (rc) { 703 dev_err(hdev->dev, 704 "Failed to get fan speed from sensor %d, error %d\n", 705 sensor_index, rc); 706 *value = 0; 707 } 708 709 return rc; 710 } 711 712 int hl_get_pwm_info(struct hl_device *hdev, 713 int sensor_index, u32 attr, long *value) 714 { 715 struct cpucp_packet pkt; 716 u64 result; 717 int rc; 718 719 memset(&pkt, 0, sizeof(pkt)); 720 721 pkt.ctl = cpu_to_le32(CPUCP_PACKET_PWM_GET << 722 CPUCP_PKT_CTL_OPCODE_SHIFT); 723 pkt.sensor_index = __cpu_to_le16(sensor_index); 724 pkt.type = __cpu_to_le16(attr); 725 726 rc = hdev->asic_funcs->send_cpu_message(hdev, (u32 *) &pkt, sizeof(pkt), 727 0, &result); 728 729 *value = (long) result; 730 731 if (rc) { 732 dev_err(hdev->dev, 733 "Failed to get pwm info from sensor %d, error %d\n", 734 sensor_index, rc); 735 *value = 0; 736 } 737 738 return rc; 739 } 740 741 void hl_set_pwm_info(struct hl_device *hdev, int sensor_index, u32 attr, 742 long value) 743 { 744 struct cpucp_packet pkt; 745 int rc; 746 747 memset(&pkt, 0, sizeof(pkt)); 748 749 pkt.ctl = cpu_to_le32(CPUCP_PACKET_PWM_SET << 750 CPUCP_PKT_CTL_OPCODE_SHIFT); 751 pkt.sensor_index = __cpu_to_le16(sensor_index); 752 pkt.type = __cpu_to_le16(attr); 753 pkt.value = cpu_to_le64(value); 754 755 rc = hdev->asic_funcs->send_cpu_message(hdev, (u32 *) &pkt, sizeof(pkt), 756 0, NULL); 757 758 if (rc) 759 dev_err(hdev->dev, 760 "Failed to set pwm info to sensor %d, error %d\n", 761 sensor_index, rc); 762 } 763 764 int hl_set_voltage(struct hl_device *hdev, 765 int sensor_index, u32 attr, long value) 766 { 767 struct cpucp_packet pkt; 768 int rc; 769 770 memset(&pkt, 0, sizeof(pkt)); 771 772 pkt.ctl = cpu_to_le32(CPUCP_PACKET_VOLTAGE_SET << 773 CPUCP_PKT_CTL_OPCODE_SHIFT); 774 pkt.sensor_index = __cpu_to_le16(sensor_index); 775 pkt.type = __cpu_to_le16(attr); 776 pkt.value = __cpu_to_le64(value); 777 778 rc = hdev->asic_funcs->send_cpu_message(hdev, (u32 *) &pkt, sizeof(pkt), 779 0, NULL); 780 781 if (rc) 782 dev_err(hdev->dev, 783 "Failed to set voltage of sensor %d, error %d\n", 784 sensor_index, rc); 785 786 return rc; 787 } 788 789 int hl_set_current(struct hl_device *hdev, 790 int sensor_index, u32 attr, long value) 791 { 792 struct cpucp_packet pkt; 793 int rc; 794 795 memset(&pkt, 0, sizeof(pkt)); 796 797 pkt.ctl = cpu_to_le32(CPUCP_PACKET_CURRENT_SET << 798 CPUCP_PKT_CTL_OPCODE_SHIFT); 799 pkt.sensor_index = __cpu_to_le16(sensor_index); 800 pkt.type = __cpu_to_le16(attr); 801 pkt.value = __cpu_to_le64(value); 802 803 rc = hdev->asic_funcs->send_cpu_message(hdev, (u32 *) &pkt, sizeof(pkt), 804 0, NULL); 805 806 if (rc) 807 dev_err(hdev->dev, 808 "Failed to set current of sensor %d, error %d\n", 809 sensor_index, rc); 810 811 return rc; 812 } 813 814 int hl_set_power(struct hl_device *hdev, 815 int sensor_index, u32 attr, long value) 816 { 817 struct cpucp_packet pkt; 818 struct asic_fixed_properties *prop = &hdev->asic_prop; 819 int rc; 820 821 memset(&pkt, 0, sizeof(pkt)); 822 823 if (prop->use_get_power_for_reset_history) 824 pkt.ctl = cpu_to_le32(CPUCP_PACKET_POWER_GET << 825 CPUCP_PKT_CTL_OPCODE_SHIFT); 826 else 827 pkt.ctl = cpu_to_le32(CPUCP_PACKET_POWER_SET << 828 CPUCP_PKT_CTL_OPCODE_SHIFT); 829 830 pkt.sensor_index = __cpu_to_le16(sensor_index); 831 pkt.type = __cpu_to_le16(attr); 832 pkt.value = __cpu_to_le64(value); 833 834 rc = hdev->asic_funcs->send_cpu_message(hdev, (u32 *) &pkt, sizeof(pkt), 835 0, NULL); 836 837 if (rc) 838 dev_err(hdev->dev, 839 "Failed to set power of sensor %d, error %d\n", 840 sensor_index, rc); 841 842 return rc; 843 } 844 845 int hl_get_power(struct hl_device *hdev, 846 int sensor_index, u32 attr, long *value) 847 { 848 struct cpucp_packet pkt; 849 u64 result; 850 int rc; 851 852 memset(&pkt, 0, sizeof(pkt)); 853 854 pkt.ctl = cpu_to_le32(CPUCP_PACKET_POWER_GET << 855 CPUCP_PKT_CTL_OPCODE_SHIFT); 856 pkt.sensor_index = __cpu_to_le16(sensor_index); 857 pkt.type = __cpu_to_le16(attr); 858 859 rc = hdev->asic_funcs->send_cpu_message(hdev, (u32 *) &pkt, sizeof(pkt), 860 0, &result); 861 862 *value = (long) result; 863 864 if (rc) { 865 dev_err(hdev->dev, 866 "Failed to get power of sensor %d, error %d\n", 867 sensor_index, rc); 868 *value = 0; 869 } 870 871 return rc; 872 } 873 874 int hl_hwmon_init(struct hl_device *hdev) 875 { 876 struct device *dev = hdev->pdev ? &hdev->pdev->dev : hdev->dev; 877 struct asic_fixed_properties *prop = &hdev->asic_prop; 878 int rc; 879 880 if ((hdev->hwmon_initialized) || !(hdev->cpu_queues_enable)) 881 return 0; 882 883 if (hdev->hl_chip_info->info) { 884 hdev->hl_chip_info->ops = &hl_hwmon_ops; 885 886 hdev->hwmon_dev = hwmon_device_register_with_info(dev, 887 prop->cpucp_info.card_name, hdev, 888 hdev->hl_chip_info, NULL); 889 if (IS_ERR(hdev->hwmon_dev)) { 890 rc = PTR_ERR(hdev->hwmon_dev); 891 dev_err(hdev->dev, 892 "Unable to register hwmon device: %d\n", rc); 893 return rc; 894 } 895 896 dev_info(hdev->dev, "%s: add sensors information\n", 897 dev_name(hdev->hwmon_dev)); 898 899 hdev->hwmon_initialized = true; 900 } else { 901 dev_info(hdev->dev, "no available sensors\n"); 902 } 903 904 return 0; 905 } 906 907 void hl_hwmon_fini(struct hl_device *hdev) 908 { 909 if (!hdev->hwmon_initialized) 910 return; 911 912 hwmon_device_unregister(hdev->hwmon_dev); 913 } 914 915 void hl_hwmon_release_resources(struct hl_device *hdev) 916 { 917 const struct hwmon_channel_info * const *channel_info_arr; 918 int i = 0; 919 920 if (!hdev->hl_chip_info->info) 921 return; 922 923 channel_info_arr = hdev->hl_chip_info->info; 924 925 while (channel_info_arr[i]) { 926 kfree(channel_info_arr[i]->config); 927 kfree(channel_info_arr[i]); 928 i++; 929 } 930 931 kfree(channel_info_arr); 932 933 hdev->hl_chip_info->info = NULL; 934 } 935