1 // SPDX-License-Identifier: GPL-2.0-or-later 2 /* 3 * Think LMI BIOS configuration driver 4 * 5 * Copyright(C) 2019-2021 Lenovo 6 * 7 * Original code from Thinkpad-wmi project https://github.com/iksaif/thinkpad-wmi 8 * Copyright(C) 2017 Corentin Chary <corentin.chary@gmail.com> 9 * Distributed under the GPL-2.0 license 10 */ 11 12 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt 13 14 #include <linux/acpi.h> 15 #include <linux/errno.h> 16 #include <linux/fs.h> 17 #include <linux/mutex.h> 18 #include <linux/string_helpers.h> 19 #include <linux/types.h> 20 #include <linux/dmi.h> 21 #include <linux/wmi.h> 22 #include "firmware_attributes_class.h" 23 #include "think-lmi.h" 24 25 static bool debug_support; 26 module_param(debug_support, bool, 0444); 27 MODULE_PARM_DESC(debug_support, "Enable debug command support"); 28 29 /* 30 * Name: BiosSetting 31 * Description: Get item name and settings for current LMI instance. 32 * Type: Query 33 * Returns: "Item,Value" 34 * Example: "WakeOnLAN,Enable" 35 */ 36 #define LENOVO_BIOS_SETTING_GUID "51F5230E-9677-46CD-A1CF-C0B23EE34DB7" 37 38 /* 39 * Name: SetBiosSetting 40 * Description: Change the BIOS setting to the desired value using the SetBiosSetting 41 * class. To save the settings, use the SaveBiosSetting class. 42 * BIOS settings and values are case sensitive. 43 * After making changes to the BIOS settings, you must reboot the computer 44 * before the changes will take effect. 45 * Type: Method 46 * Arguments: "Item,Value,Password,Encoding,KbdLang;" 47 * Example: "WakeOnLAN,Disable,pa55w0rd,ascii,us;" 48 */ 49 #define LENOVO_SET_BIOS_SETTINGS_GUID "98479A64-33F5-4E33-A707-8E251EBBC3A1" 50 51 /* 52 * Name: SaveBiosSettings 53 * Description: Save any pending changes in settings. 54 * Type: Method 55 * Arguments: "Password,Encoding,KbdLang;" 56 * Example: "pa55w0rd,ascii,us;" 57 */ 58 #define LENOVO_SAVE_BIOS_SETTINGS_GUID "6A4B54EF-A5ED-4D33-9455-B0D9B48DF4B3" 59 60 /* 61 * Name: BiosPasswordSettings 62 * Description: Return BIOS Password settings 63 * Type: Query 64 * Returns: PasswordMode, PasswordState, MinLength, MaxLength, 65 * SupportedEncoding, SupportedKeyboard 66 */ 67 #define LENOVO_BIOS_PASSWORD_SETTINGS_GUID "8ADB159E-1E32-455C-BC93-308A7ED98246" 68 69 /* 70 * Name: SetBiosPassword 71 * Description: Change a specific password. 72 * - BIOS settings cannot be changed at the same boot as power-on 73 * passwords (POP) and hard disk passwords (HDP). If you want to change 74 * BIOS settings and POP or HDP, you must reboot the system after changing 75 * one of them. 76 * - A password cannot be set using this method when one does not already 77 * exist. Passwords can only be updated or cleared. 78 * Type: Method 79 * Arguments: "PasswordType,CurrentPassword,NewPassword,Encoding,KbdLang;" 80 * Example: "pop,pa55w0rd,newpa55w0rd,ascii,us;” 81 */ 82 #define LENOVO_SET_BIOS_PASSWORD_GUID "2651D9FD-911C-4B69-B94E-D0DED5963BD7" 83 84 /* 85 * Name: GetBiosSelections 86 * Description: Return a list of valid settings for a given item. 87 * Type: Method 88 * Arguments: "Item" 89 * Returns: "Value1,Value2,Value3,..." 90 * Example: 91 * -> "FlashOverLAN" 92 * <- "Enabled,Disabled" 93 */ 94 #define LENOVO_GET_BIOS_SELECTIONS_GUID "7364651A-132F-4FE7-ADAA-40C6C7EE2E3B" 95 96 /* 97 * Name: DebugCmd 98 * Description: Debug entry method for entering debug commands to the BIOS 99 */ 100 #define LENOVO_DEBUG_CMD_GUID "7FF47003-3B6C-4E5E-A227-E979824A85D1" 101 102 /* 103 * Name: OpcodeIF 104 * Description: Opcode interface which provides the ability to set multiple 105 * parameters and then trigger an action with a final command. 106 * This is particularly useful for simplifying setting passwords. 107 * With this support comes the ability to set System, HDD and NVMe 108 * passwords. 109 * This is currently available on ThinkCenter and ThinkStations platforms 110 */ 111 #define LENOVO_OPCODE_IF_GUID "DFDDEF2C-57D4-48ce-B196-0FB787D90836" 112 113 /* 114 * Name: SetBiosCert 115 * Description: Install BIOS certificate. 116 * Type: Method 117 * Arguments: "Certificate,Password" 118 * You must reboot the computer before the changes will take effect. 119 */ 120 #define LENOVO_SET_BIOS_CERT_GUID "26861C9F-47E9-44C4-BD8B-DFE7FA2610FE" 121 122 /* 123 * Name: UpdateBiosCert 124 * Description: Update BIOS certificate. 125 * Type: Method 126 * Format: "Certificate,Signature" 127 * You must reboot the computer before the changes will take effect. 128 */ 129 #define LENOVO_UPDATE_BIOS_CERT_GUID "9AA3180A-9750-41F7-B9F7-D5D3B1BAC3CE" 130 131 /* 132 * Name: ClearBiosCert 133 * Description: Uninstall BIOS certificate. 134 * Type: Method 135 * Format: "Serial,Signature" 136 * You must reboot the computer before the changes will take effect. 137 */ 138 #define LENOVO_CLEAR_BIOS_CERT_GUID "B2BC39A7-78DD-4D71-B059-A510DEC44890" 139 /* 140 * Name: CertToPassword 141 * Description: Switch from certificate to password authentication. 142 * Type: Method 143 * Format: "Password,Signature" 144 * You must reboot the computer before the changes will take effect. 145 */ 146 #define LENOVO_CERT_TO_PASSWORD_GUID "0DE8590D-5510-4044-9621-77C227F5A70D" 147 148 /* 149 * Name: SetBiosSettingCert 150 * Description: Set attribute using certificate authentication. 151 * Type: Method 152 * Format: "Item,Value,Signature" 153 */ 154 #define LENOVO_SET_BIOS_SETTING_CERT_GUID "34A008CC-D205-4B62-9E67-31DFA8B90003" 155 156 /* 157 * Name: SaveBiosSettingCert 158 * Description: Save any pending changes in settings. 159 * Type: Method 160 * Format: "Signature" 161 */ 162 #define LENOVO_SAVE_BIOS_SETTING_CERT_GUID "C050FB9D-DF5F-4606-B066-9EFC401B2551" 163 164 /* 165 * Name: CertThumbprint 166 * Description: Display Certificate thumbprints 167 * Type: Query 168 * Returns: MD5, SHA1 & SHA256 thumbprints 169 */ 170 #define LENOVO_CERT_THUMBPRINT_GUID "C59119ED-1C0D-4806-A8E9-59AA318176C4" 171 172 #define TLMI_POP_PWD BIT(0) /* Supervisor */ 173 #define TLMI_PAP_PWD BIT(1) /* Power-on */ 174 #define TLMI_HDD_PWD BIT(2) /* HDD/NVME */ 175 #define TLMI_SMP_PWD BIT(6) /* System Management */ 176 #define TLMI_CERT BIT(7) /* Certificate Based */ 177 178 static const struct tlmi_err_codes tlmi_errs[] = { 179 {"Success", 0}, 180 {"Not Supported", -EOPNOTSUPP}, 181 {"Invalid Parameter", -EINVAL}, 182 {"Access Denied", -EACCES}, 183 {"System Busy", -EBUSY}, 184 }; 185 186 static const char * const encoding_options[] = { 187 [TLMI_ENCODING_ASCII] = "ascii", 188 [TLMI_ENCODING_SCANCODE] = "scancode", 189 }; 190 static const char * const level_options[] = { 191 [TLMI_LEVEL_USER] = "user", 192 [TLMI_LEVEL_MASTER] = "master", 193 }; 194 static struct think_lmi tlmi_priv; 195 static const struct class *fw_attr_class; 196 static DEFINE_MUTEX(tlmi_mutex); 197 198 static inline struct tlmi_pwd_setting *to_tlmi_pwd_setting(struct kobject *kobj) 199 { 200 return container_of(kobj, struct tlmi_pwd_setting, kobj); 201 } 202 203 static inline struct tlmi_attr_setting *to_tlmi_attr_setting(struct kobject *kobj) 204 { 205 return container_of(kobj, struct tlmi_attr_setting, kobj); 206 } 207 208 /* Convert BIOS WMI error string to suitable error code */ 209 static int tlmi_errstr_to_err(const char *errstr) 210 { 211 int i; 212 213 for (i = 0; i < sizeof(tlmi_errs)/sizeof(struct tlmi_err_codes); i++) { 214 if (!strcmp(tlmi_errs[i].err_str, errstr)) 215 return tlmi_errs[i].err_code; 216 } 217 return -EPERM; 218 } 219 220 /* Extract error string from WMI return buffer */ 221 static int tlmi_extract_error(const struct acpi_buffer *output) 222 { 223 const union acpi_object *obj; 224 225 obj = output->pointer; 226 if (!obj) 227 return -ENOMEM; 228 if (obj->type != ACPI_TYPE_STRING || !obj->string.pointer) 229 return -EIO; 230 231 return tlmi_errstr_to_err(obj->string.pointer); 232 } 233 234 /* Utility function to execute WMI call to BIOS */ 235 static int tlmi_simple_call(const char *guid, const char *arg) 236 { 237 const struct acpi_buffer input = { strlen(arg), (char *)arg }; 238 struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL }; 239 acpi_status status; 240 int i, err; 241 242 /* 243 * Duplicated call required to match BIOS workaround for behavior 244 * seen when WMI accessed via scripting on other OS. 245 */ 246 for (i = 0; i < 2; i++) { 247 /* (re)initialize output buffer to default state */ 248 output.length = ACPI_ALLOCATE_BUFFER; 249 output.pointer = NULL; 250 251 status = wmi_evaluate_method(guid, 0, 0, &input, &output); 252 if (ACPI_FAILURE(status)) { 253 kfree(output.pointer); 254 return -EIO; 255 } 256 err = tlmi_extract_error(&output); 257 kfree(output.pointer); 258 if (err) 259 return err; 260 } 261 return 0; 262 } 263 264 /* Extract output string from WMI return buffer */ 265 static int tlmi_extract_output_string(const struct acpi_buffer *output, 266 char **string) 267 { 268 const union acpi_object *obj; 269 char *s; 270 271 obj = output->pointer; 272 if (!obj) 273 return -ENOMEM; 274 if (obj->type != ACPI_TYPE_STRING || !obj->string.pointer) 275 return -EIO; 276 277 s = kstrdup(obj->string.pointer, GFP_KERNEL); 278 if (!s) 279 return -ENOMEM; 280 *string = s; 281 return 0; 282 } 283 284 /* ------ Core interface functions ------------*/ 285 286 /* Get password settings from BIOS */ 287 static int tlmi_get_pwd_settings(struct tlmi_pwdcfg *pwdcfg) 288 { 289 struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL }; 290 const union acpi_object *obj; 291 acpi_status status; 292 int copy_size; 293 294 if (!tlmi_priv.can_get_password_settings) 295 return -EOPNOTSUPP; 296 297 status = wmi_query_block(LENOVO_BIOS_PASSWORD_SETTINGS_GUID, 0, 298 &output); 299 if (ACPI_FAILURE(status)) 300 return -EIO; 301 302 obj = output.pointer; 303 if (!obj) 304 return -ENOMEM; 305 if (obj->type != ACPI_TYPE_BUFFER || !obj->buffer.pointer) { 306 kfree(obj); 307 return -EIO; 308 } 309 /* 310 * The size of thinkpad_wmi_pcfg on ThinkStation is larger than ThinkPad. 311 * To make the driver compatible on different brands, we permit it to get 312 * the data in below case. 313 * Settings must have at minimum the core fields available 314 */ 315 if (obj->buffer.length < sizeof(struct tlmi_pwdcfg_core)) { 316 pr_warn("Unknown pwdcfg buffer length %d\n", obj->buffer.length); 317 kfree(obj); 318 return -EIO; 319 } 320 321 copy_size = min_t(size_t, obj->buffer.length, sizeof(struct tlmi_pwdcfg)); 322 323 memcpy(pwdcfg, obj->buffer.pointer, copy_size); 324 kfree(obj); 325 326 if (WARN_ON(pwdcfg->core.max_length >= TLMI_PWD_BUFSIZE)) 327 pwdcfg->core.max_length = TLMI_PWD_BUFSIZE - 1; 328 return 0; 329 } 330 331 static int tlmi_save_bios_settings(const char *password) 332 { 333 return tlmi_simple_call(LENOVO_SAVE_BIOS_SETTINGS_GUID, 334 password); 335 } 336 337 static int tlmi_opcode_setting(char *setting, const char *value) 338 { 339 char *opcode_str; 340 int ret; 341 342 opcode_str = kasprintf(GFP_KERNEL, "%s:%s;", setting, value); 343 if (!opcode_str) 344 return -ENOMEM; 345 346 ret = tlmi_simple_call(LENOVO_OPCODE_IF_GUID, opcode_str); 347 kfree(opcode_str); 348 return ret; 349 } 350 351 static int tlmi_setting(int item, char **value, const char *guid_string) 352 { 353 struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL }; 354 acpi_status status; 355 int ret; 356 357 status = wmi_query_block(guid_string, item, &output); 358 if (ACPI_FAILURE(status)) { 359 kfree(output.pointer); 360 return -EIO; 361 } 362 363 ret = tlmi_extract_output_string(&output, value); 364 kfree(output.pointer); 365 return ret; 366 } 367 368 static int tlmi_get_bios_selections(const char *item, char **value) 369 { 370 const struct acpi_buffer input = { strlen(item), (char *)item }; 371 struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL }; 372 acpi_status status; 373 int ret; 374 375 status = wmi_evaluate_method(LENOVO_GET_BIOS_SELECTIONS_GUID, 376 0, 0, &input, &output); 377 378 if (ACPI_FAILURE(status)) { 379 kfree(output.pointer); 380 return -EIO; 381 } 382 383 ret = tlmi_extract_output_string(&output, value); 384 kfree(output.pointer); 385 return ret; 386 } 387 388 /* ---- Authentication sysfs --------------------------------------------------------- */ 389 static ssize_t is_enabled_show(struct kobject *kobj, struct kobj_attribute *attr, 390 char *buf) 391 { 392 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 393 394 return sysfs_emit(buf, "%d\n", setting->valid); 395 } 396 397 static struct kobj_attribute auth_is_pass_set = __ATTR_RO(is_enabled); 398 399 static ssize_t current_password_store(struct kobject *kobj, 400 struct kobj_attribute *attr, 401 const char *buf, size_t count) 402 { 403 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 404 size_t pwdlen; 405 406 pwdlen = strlen(buf); 407 /* pwdlen == 0 is allowed to clear the password */ 408 if (pwdlen && ((pwdlen < setting->minlen) || (pwdlen > setting->maxlen))) 409 return -EINVAL; 410 411 strscpy(setting->password, buf, setting->maxlen); 412 /* Strip out CR if one is present, setting password won't work if it is present */ 413 strreplace(setting->password, '\n', '\0'); 414 return count; 415 } 416 417 static struct kobj_attribute auth_current_password = __ATTR_WO(current_password); 418 419 static ssize_t new_password_store(struct kobject *kobj, 420 struct kobj_attribute *attr, 421 const char *buf, size_t count) 422 { 423 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 424 char *auth_str, *new_pwd; 425 size_t pwdlen; 426 int ret; 427 428 if (!capable(CAP_SYS_ADMIN)) 429 return -EPERM; 430 431 if (!tlmi_priv.can_set_bios_password) 432 return -EOPNOTSUPP; 433 434 /* Strip out CR if one is present, setting password won't work if it is present */ 435 new_pwd = kstrdup_and_replace(buf, '\n', '\0', GFP_KERNEL); 436 if (!new_pwd) 437 return -ENOMEM; 438 439 /* Use lock in case multiple WMI operations needed */ 440 mutex_lock(&tlmi_mutex); 441 442 pwdlen = strlen(new_pwd); 443 /* pwdlen == 0 is allowed to clear the password */ 444 if (pwdlen && ((pwdlen < setting->minlen) || (pwdlen > setting->maxlen))) { 445 ret = -EINVAL; 446 goto out; 447 } 448 449 /* If opcode support is present use that interface */ 450 if (tlmi_priv.opcode_support) { 451 char pwd_type[8]; 452 453 /* Special handling required for HDD and NVMe passwords */ 454 if (setting == tlmi_priv.pwd_hdd) { 455 if (setting->level == TLMI_LEVEL_USER) 456 sprintf(pwd_type, "uhdp%d", setting->index); 457 else 458 sprintf(pwd_type, "mhdp%d", setting->index); 459 } else if (setting == tlmi_priv.pwd_nvme) { 460 if (setting->level == TLMI_LEVEL_USER) 461 sprintf(pwd_type, "udrp%d", setting->index); 462 else 463 sprintf(pwd_type, "adrp%d", setting->index); 464 } else { 465 sprintf(pwd_type, "%s", setting->pwd_type); 466 } 467 468 ret = tlmi_opcode_setting("WmiOpcodePasswordType", pwd_type); 469 if (ret) 470 goto out; 471 472 if (tlmi_priv.pwd_admin->valid) { 473 ret = tlmi_opcode_setting("WmiOpcodePasswordAdmin", 474 tlmi_priv.pwd_admin->password); 475 if (ret) 476 goto out; 477 } 478 ret = tlmi_opcode_setting("WmiOpcodePasswordCurrent01", setting->password); 479 if (ret) 480 goto out; 481 ret = tlmi_opcode_setting("WmiOpcodePasswordNew01", new_pwd); 482 if (ret) 483 goto out; 484 ret = tlmi_simple_call(LENOVO_OPCODE_IF_GUID, "WmiOpcodePasswordSetUpdate;"); 485 } else { 486 /* Format: 'PasswordType,CurrentPw,NewPw,Encoding,KbdLang;' */ 487 auth_str = kasprintf(GFP_KERNEL, "%s,%s,%s,%s,%s;", 488 setting->pwd_type, setting->password, new_pwd, 489 encoding_options[setting->encoding], setting->kbdlang); 490 if (!auth_str) { 491 ret = -ENOMEM; 492 goto out; 493 } 494 ret = tlmi_simple_call(LENOVO_SET_BIOS_PASSWORD_GUID, auth_str); 495 kfree(auth_str); 496 } 497 out: 498 mutex_unlock(&tlmi_mutex); 499 kfree(new_pwd); 500 return ret ?: count; 501 } 502 503 static struct kobj_attribute auth_new_password = __ATTR_WO(new_password); 504 505 static ssize_t min_password_length_show(struct kobject *kobj, struct kobj_attribute *attr, 506 char *buf) 507 { 508 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 509 510 return sysfs_emit(buf, "%d\n", setting->minlen); 511 } 512 513 static struct kobj_attribute auth_min_pass_length = __ATTR_RO(min_password_length); 514 515 static ssize_t max_password_length_show(struct kobject *kobj, struct kobj_attribute *attr, 516 char *buf) 517 { 518 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 519 520 return sysfs_emit(buf, "%d\n", setting->maxlen); 521 } 522 static struct kobj_attribute auth_max_pass_length = __ATTR_RO(max_password_length); 523 524 static ssize_t mechanism_show(struct kobject *kobj, struct kobj_attribute *attr, 525 char *buf) 526 { 527 return sysfs_emit(buf, "password\n"); 528 } 529 static struct kobj_attribute auth_mechanism = __ATTR_RO(mechanism); 530 531 static ssize_t encoding_show(struct kobject *kobj, struct kobj_attribute *attr, 532 char *buf) 533 { 534 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 535 536 return sysfs_emit(buf, "%s\n", encoding_options[setting->encoding]); 537 } 538 539 static ssize_t encoding_store(struct kobject *kobj, 540 struct kobj_attribute *attr, 541 const char *buf, size_t count) 542 { 543 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 544 int i; 545 546 /* Scan for a matching profile */ 547 i = sysfs_match_string(encoding_options, buf); 548 if (i < 0) 549 return -EINVAL; 550 551 setting->encoding = i; 552 return count; 553 } 554 555 static struct kobj_attribute auth_encoding = __ATTR_RW(encoding); 556 557 static ssize_t kbdlang_show(struct kobject *kobj, struct kobj_attribute *attr, 558 char *buf) 559 { 560 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 561 562 return sysfs_emit(buf, "%s\n", setting->kbdlang); 563 } 564 565 static ssize_t kbdlang_store(struct kobject *kobj, 566 struct kobj_attribute *attr, 567 const char *buf, size_t count) 568 { 569 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 570 int length; 571 572 /* Calculate length till '\n' or terminating 0 */ 573 length = strchrnul(buf, '\n') - buf; 574 if (!length || length >= TLMI_LANG_MAXLEN) 575 return -EINVAL; 576 577 memcpy(setting->kbdlang, buf, length); 578 setting->kbdlang[length] = '\0'; 579 return count; 580 } 581 582 static struct kobj_attribute auth_kbdlang = __ATTR_RW(kbdlang); 583 584 static ssize_t role_show(struct kobject *kobj, struct kobj_attribute *attr, 585 char *buf) 586 { 587 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 588 589 return sysfs_emit(buf, "%s\n", setting->role); 590 } 591 static struct kobj_attribute auth_role = __ATTR_RO(role); 592 593 static ssize_t index_show(struct kobject *kobj, struct kobj_attribute *attr, 594 char *buf) 595 { 596 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 597 598 return sysfs_emit(buf, "%d\n", setting->index); 599 } 600 601 static ssize_t index_store(struct kobject *kobj, 602 struct kobj_attribute *attr, 603 const char *buf, size_t count) 604 { 605 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 606 int err, val; 607 608 err = kstrtoint(buf, 10, &val); 609 if (err < 0) 610 return err; 611 612 if (val < 0 || val > TLMI_INDEX_MAX) 613 return -EINVAL; 614 615 setting->index = val; 616 return count; 617 } 618 619 static struct kobj_attribute auth_index = __ATTR_RW(index); 620 621 static ssize_t level_show(struct kobject *kobj, struct kobj_attribute *attr, 622 char *buf) 623 { 624 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 625 626 return sysfs_emit(buf, "%s\n", level_options[setting->level]); 627 } 628 629 static ssize_t level_store(struct kobject *kobj, 630 struct kobj_attribute *attr, 631 const char *buf, size_t count) 632 { 633 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 634 int i; 635 636 /* Scan for a matching profile */ 637 i = sysfs_match_string(level_options, buf); 638 if (i < 0) 639 return -EINVAL; 640 641 setting->level = i; 642 return count; 643 } 644 645 static struct kobj_attribute auth_level = __ATTR_RW(level); 646 647 static ssize_t cert_thumbprint(char *buf, const char *arg, int count) 648 { 649 const struct acpi_buffer input = { strlen(arg), (char *)arg }; 650 struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL }; 651 const union acpi_object *obj; 652 acpi_status status; 653 654 status = wmi_evaluate_method(LENOVO_CERT_THUMBPRINT_GUID, 0, 0, &input, &output); 655 if (ACPI_FAILURE(status)) { 656 kfree(output.pointer); 657 return -EIO; 658 } 659 obj = output.pointer; 660 if (!obj) 661 return -ENOMEM; 662 if (obj->type != ACPI_TYPE_STRING || !obj->string.pointer) { 663 kfree(output.pointer); 664 return -EIO; 665 } 666 count += sysfs_emit_at(buf, count, "%s : %s\n", arg, (char *)obj->string.pointer); 667 kfree(output.pointer); 668 669 return count; 670 } 671 672 static ssize_t certificate_thumbprint_show(struct kobject *kobj, struct kobj_attribute *attr, 673 char *buf) 674 { 675 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 676 int count = 0; 677 678 if (!tlmi_priv.certificate_support || !setting->cert_installed) 679 return -EOPNOTSUPP; 680 681 count += cert_thumbprint(buf, "Md5", count); 682 count += cert_thumbprint(buf, "Sha1", count); 683 count += cert_thumbprint(buf, "Sha256", count); 684 return count; 685 } 686 687 static struct kobj_attribute auth_cert_thumb = __ATTR_RO(certificate_thumbprint); 688 689 static ssize_t cert_to_password_store(struct kobject *kobj, 690 struct kobj_attribute *attr, 691 const char *buf, size_t count) 692 { 693 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 694 char *auth_str, *passwd; 695 int ret; 696 697 if (!capable(CAP_SYS_ADMIN)) 698 return -EPERM; 699 700 if (!tlmi_priv.certificate_support) 701 return -EOPNOTSUPP; 702 703 if (!setting->cert_installed) 704 return -EINVAL; 705 706 if (!setting->signature || !setting->signature[0]) 707 return -EACCES; 708 709 /* Strip out CR if one is present */ 710 passwd = kstrdup_and_replace(buf, '\n', '\0', GFP_KERNEL); 711 if (!passwd) 712 return -ENOMEM; 713 714 /* Format: 'Password,Signature' */ 715 auth_str = kasprintf(GFP_KERNEL, "%s,%s", passwd, setting->signature); 716 if (!auth_str) { 717 kfree_sensitive(passwd); 718 return -ENOMEM; 719 } 720 ret = tlmi_simple_call(LENOVO_CERT_TO_PASSWORD_GUID, auth_str); 721 kfree(auth_str); 722 kfree_sensitive(passwd); 723 724 return ret ?: count; 725 } 726 727 static struct kobj_attribute auth_cert_to_password = __ATTR_WO(cert_to_password); 728 729 static ssize_t certificate_store(struct kobject *kobj, 730 struct kobj_attribute *attr, 731 const char *buf, size_t count) 732 { 733 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 734 char *auth_str, *new_cert; 735 char *guid; 736 int ret; 737 738 if (!capable(CAP_SYS_ADMIN)) 739 return -EPERM; 740 741 if (!tlmi_priv.certificate_support) 742 return -EOPNOTSUPP; 743 744 /* If empty then clear installed certificate */ 745 if ((buf[0] == '\0') || (buf[0] == '\n')) { /* Clear installed certificate */ 746 /* Check that signature is set */ 747 if (!setting->signature || !setting->signature[0]) 748 return -EACCES; 749 750 /* Format: 'serial#, signature' */ 751 auth_str = kasprintf(GFP_KERNEL, "%s,%s", 752 dmi_get_system_info(DMI_PRODUCT_SERIAL), 753 setting->signature); 754 if (!auth_str) 755 return -ENOMEM; 756 757 ret = tlmi_simple_call(LENOVO_CLEAR_BIOS_CERT_GUID, auth_str); 758 kfree(auth_str); 759 760 return ret ?: count; 761 } 762 763 /* Strip out CR if one is present */ 764 new_cert = kstrdup_and_replace(buf, '\n', '\0', GFP_KERNEL); 765 if (!new_cert) 766 return -ENOMEM; 767 768 if (setting->cert_installed) { 769 /* Certificate is installed so this is an update */ 770 if (!setting->signature || !setting->signature[0]) { 771 kfree(new_cert); 772 return -EACCES; 773 } 774 guid = LENOVO_UPDATE_BIOS_CERT_GUID; 775 /* Format: 'Certificate,Signature' */ 776 auth_str = kasprintf(GFP_KERNEL, "%s,%s", 777 new_cert, setting->signature); 778 } else { 779 /* This is a fresh install */ 780 if (!setting->valid || !setting->password[0]) { 781 kfree(new_cert); 782 return -EACCES; 783 } 784 guid = LENOVO_SET_BIOS_CERT_GUID; 785 /* Format: 'Certificate,Admin-password' */ 786 auth_str = kasprintf(GFP_KERNEL, "%s,%s", 787 new_cert, setting->password); 788 } 789 kfree(new_cert); 790 if (!auth_str) 791 return -ENOMEM; 792 793 ret = tlmi_simple_call(guid, auth_str); 794 kfree(auth_str); 795 796 return ret ?: count; 797 } 798 799 static struct kobj_attribute auth_certificate = __ATTR_WO(certificate); 800 801 static ssize_t signature_store(struct kobject *kobj, 802 struct kobj_attribute *attr, 803 const char *buf, size_t count) 804 { 805 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 806 char *new_signature; 807 808 if (!capable(CAP_SYS_ADMIN)) 809 return -EPERM; 810 811 if (!tlmi_priv.certificate_support) 812 return -EOPNOTSUPP; 813 814 /* Strip out CR if one is present */ 815 new_signature = kstrdup_and_replace(buf, '\n', '\0', GFP_KERNEL); 816 if (!new_signature) 817 return -ENOMEM; 818 819 /* Free any previous signature */ 820 kfree(setting->signature); 821 setting->signature = new_signature; 822 823 return count; 824 } 825 826 static struct kobj_attribute auth_signature = __ATTR_WO(signature); 827 828 static ssize_t save_signature_store(struct kobject *kobj, 829 struct kobj_attribute *attr, 830 const char *buf, size_t count) 831 { 832 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 833 char *new_signature; 834 835 if (!capable(CAP_SYS_ADMIN)) 836 return -EPERM; 837 838 if (!tlmi_priv.certificate_support) 839 return -EOPNOTSUPP; 840 841 /* Strip out CR if one is present */ 842 new_signature = kstrdup_and_replace(buf, '\n', '\0', GFP_KERNEL); 843 if (!new_signature) 844 return -ENOMEM; 845 846 /* Free any previous signature */ 847 kfree(setting->save_signature); 848 setting->save_signature = new_signature; 849 850 return count; 851 } 852 853 static struct kobj_attribute auth_save_signature = __ATTR_WO(save_signature); 854 855 static umode_t auth_attr_is_visible(struct kobject *kobj, 856 struct attribute *attr, int n) 857 { 858 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 859 860 /* We only want to display level and index settings on HDD/NVMe */ 861 if (attr == &auth_index.attr || attr == &auth_level.attr) { 862 if ((setting == tlmi_priv.pwd_hdd) || (setting == tlmi_priv.pwd_nvme)) 863 return attr->mode; 864 return 0; 865 } 866 867 /* We only display certificates on Admin account, if supported */ 868 if (attr == &auth_certificate.attr || 869 attr == &auth_signature.attr || 870 attr == &auth_save_signature.attr || 871 attr == &auth_cert_thumb.attr || 872 attr == &auth_cert_to_password.attr) { 873 if ((setting == tlmi_priv.pwd_admin) && tlmi_priv.certificate_support) 874 return attr->mode; 875 return 0; 876 } 877 878 /* Don't display un-needed settings if opcode available */ 879 if ((attr == &auth_encoding.attr || attr == &auth_kbdlang.attr) && 880 tlmi_priv.opcode_support) 881 return 0; 882 883 return attr->mode; 884 } 885 886 static struct attribute *auth_attrs[] = { 887 &auth_is_pass_set.attr, 888 &auth_min_pass_length.attr, 889 &auth_max_pass_length.attr, 890 &auth_current_password.attr, 891 &auth_new_password.attr, 892 &auth_role.attr, 893 &auth_mechanism.attr, 894 &auth_encoding.attr, 895 &auth_kbdlang.attr, 896 &auth_index.attr, 897 &auth_level.attr, 898 &auth_certificate.attr, 899 &auth_signature.attr, 900 &auth_save_signature.attr, 901 &auth_cert_thumb.attr, 902 &auth_cert_to_password.attr, 903 NULL 904 }; 905 906 static const struct attribute_group auth_attr_group = { 907 .is_visible = auth_attr_is_visible, 908 .attrs = auth_attrs, 909 }; 910 911 /* ---- Attributes sysfs --------------------------------------------------------- */ 912 static ssize_t display_name_show(struct kobject *kobj, struct kobj_attribute *attr, 913 char *buf) 914 { 915 struct tlmi_attr_setting *setting = to_tlmi_attr_setting(kobj); 916 917 return sysfs_emit(buf, "%s\n", setting->display_name); 918 } 919 920 static ssize_t current_value_show(struct kobject *kobj, struct kobj_attribute *attr, char *buf) 921 { 922 struct tlmi_attr_setting *setting = to_tlmi_attr_setting(kobj); 923 char *item, *value; 924 int ret; 925 926 ret = tlmi_setting(setting->index, &item, LENOVO_BIOS_SETTING_GUID); 927 if (ret) 928 return ret; 929 930 /* validate and split from `item,value` -> `value` */ 931 value = strpbrk(item, ","); 932 if (!value || value == item || !strlen(value + 1)) 933 ret = -EINVAL; 934 else { 935 /* On Workstations remove the Options part after the value */ 936 strreplace(value, ';', '\0'); 937 ret = sysfs_emit(buf, "%s\n", value + 1); 938 } 939 kfree(item); 940 941 return ret; 942 } 943 944 static ssize_t possible_values_show(struct kobject *kobj, struct kobj_attribute *attr, char *buf) 945 { 946 struct tlmi_attr_setting *setting = to_tlmi_attr_setting(kobj); 947 948 return sysfs_emit(buf, "%s\n", setting->possible_values); 949 } 950 951 static ssize_t type_show(struct kobject *kobj, struct kobj_attribute *attr, 952 char *buf) 953 { 954 struct tlmi_attr_setting *setting = to_tlmi_attr_setting(kobj); 955 956 if (setting->possible_values) { 957 /* Figure out what setting type is as BIOS does not return this */ 958 if (strchr(setting->possible_values, ';')) 959 return sysfs_emit(buf, "enumeration\n"); 960 } 961 /* Anything else is going to be a string */ 962 return sysfs_emit(buf, "string\n"); 963 } 964 965 static ssize_t current_value_store(struct kobject *kobj, 966 struct kobj_attribute *attr, 967 const char *buf, size_t count) 968 { 969 struct tlmi_attr_setting *setting = to_tlmi_attr_setting(kobj); 970 char *set_str = NULL, *new_setting = NULL; 971 char *auth_str = NULL; 972 int ret; 973 974 if (!tlmi_priv.can_set_bios_settings) 975 return -EOPNOTSUPP; 976 977 /* 978 * If we are using bulk saves a reboot should be done once save has 979 * been called 980 */ 981 if (tlmi_priv.save_mode == TLMI_SAVE_BULK && tlmi_priv.reboot_required) 982 return -EPERM; 983 984 /* Strip out CR if one is present */ 985 new_setting = kstrdup_and_replace(buf, '\n', '\0', GFP_KERNEL); 986 if (!new_setting) 987 return -ENOMEM; 988 989 /* Use lock in case multiple WMI operations needed */ 990 mutex_lock(&tlmi_mutex); 991 992 /* Check if certificate authentication is enabled and active */ 993 if (tlmi_priv.certificate_support && tlmi_priv.pwd_admin->cert_installed) { 994 if (!tlmi_priv.pwd_admin->signature || !tlmi_priv.pwd_admin->save_signature) { 995 ret = -EINVAL; 996 goto out; 997 } 998 set_str = kasprintf(GFP_KERNEL, "%s,%s,%s", setting->display_name, 999 new_setting, tlmi_priv.pwd_admin->signature); 1000 if (!set_str) { 1001 ret = -ENOMEM; 1002 goto out; 1003 } 1004 1005 ret = tlmi_simple_call(LENOVO_SET_BIOS_SETTING_CERT_GUID, set_str); 1006 if (ret) 1007 goto out; 1008 if (tlmi_priv.save_mode == TLMI_SAVE_BULK) 1009 tlmi_priv.save_required = true; 1010 else 1011 ret = tlmi_simple_call(LENOVO_SAVE_BIOS_SETTING_CERT_GUID, 1012 tlmi_priv.pwd_admin->save_signature); 1013 } else if (tlmi_priv.opcode_support) { 1014 /* 1015 * If opcode support is present use that interface. 1016 * Note - this sets the variable and then the password as separate 1017 * WMI calls. Function tlmi_save_bios_settings will error if the 1018 * password is incorrect. 1019 * Workstation's require the opcode to be set before changing the 1020 * attribute. 1021 */ 1022 if (tlmi_priv.pwd_admin->valid && tlmi_priv.pwd_admin->password[0]) { 1023 ret = tlmi_opcode_setting("WmiOpcodePasswordAdmin", 1024 tlmi_priv.pwd_admin->password); 1025 if (ret) 1026 goto out; 1027 } 1028 1029 set_str = kasprintf(GFP_KERNEL, "%s,%s;", setting->display_name, 1030 new_setting); 1031 if (!set_str) { 1032 ret = -ENOMEM; 1033 goto out; 1034 } 1035 1036 ret = tlmi_simple_call(LENOVO_SET_BIOS_SETTINGS_GUID, set_str); 1037 if (ret) 1038 goto out; 1039 1040 if (tlmi_priv.save_mode == TLMI_SAVE_BULK) 1041 tlmi_priv.save_required = true; 1042 else 1043 ret = tlmi_save_bios_settings(""); 1044 } else { /* old non-opcode based authentication method (deprecated) */ 1045 if (tlmi_priv.pwd_admin->valid && tlmi_priv.pwd_admin->password[0]) { 1046 auth_str = kasprintf(GFP_KERNEL, "%s,%s,%s;", 1047 tlmi_priv.pwd_admin->password, 1048 encoding_options[tlmi_priv.pwd_admin->encoding], 1049 tlmi_priv.pwd_admin->kbdlang); 1050 if (!auth_str) { 1051 ret = -ENOMEM; 1052 goto out; 1053 } 1054 } 1055 1056 if (auth_str) 1057 set_str = kasprintf(GFP_KERNEL, "%s,%s,%s", setting->display_name, 1058 new_setting, auth_str); 1059 else 1060 set_str = kasprintf(GFP_KERNEL, "%s,%s;", setting->display_name, 1061 new_setting); 1062 if (!set_str) { 1063 ret = -ENOMEM; 1064 goto out; 1065 } 1066 1067 ret = tlmi_simple_call(LENOVO_SET_BIOS_SETTINGS_GUID, set_str); 1068 if (ret) 1069 goto out; 1070 1071 if (tlmi_priv.save_mode == TLMI_SAVE_BULK) { 1072 tlmi_priv.save_required = true; 1073 } else { 1074 if (auth_str) 1075 ret = tlmi_save_bios_settings(auth_str); 1076 else 1077 ret = tlmi_save_bios_settings(""); 1078 } 1079 } 1080 if (!ret && !tlmi_priv.pending_changes) { 1081 tlmi_priv.pending_changes = true; 1082 /* let userland know it may need to check reboot pending again */ 1083 kobject_uevent(&tlmi_priv.class_dev->kobj, KOBJ_CHANGE); 1084 } 1085 out: 1086 mutex_unlock(&tlmi_mutex); 1087 kfree(auth_str); 1088 kfree(set_str); 1089 kfree(new_setting); 1090 return ret ?: count; 1091 } 1092 1093 static struct kobj_attribute attr_displ_name = __ATTR_RO(display_name); 1094 1095 static struct kobj_attribute attr_possible_values = __ATTR_RO(possible_values); 1096 1097 static struct kobj_attribute attr_current_val = __ATTR_RW_MODE(current_value, 0600); 1098 1099 static struct kobj_attribute attr_type = __ATTR_RO(type); 1100 1101 static umode_t attr_is_visible(struct kobject *kobj, 1102 struct attribute *attr, int n) 1103 { 1104 struct tlmi_attr_setting *setting = to_tlmi_attr_setting(kobj); 1105 1106 /* We don't want to display possible_values attributes if not available */ 1107 if ((attr == &attr_possible_values.attr) && (!setting->possible_values)) 1108 return 0; 1109 1110 return attr->mode; 1111 } 1112 1113 static struct attribute *tlmi_attrs[] = { 1114 &attr_displ_name.attr, 1115 &attr_current_val.attr, 1116 &attr_possible_values.attr, 1117 &attr_type.attr, 1118 NULL 1119 }; 1120 1121 static const struct attribute_group tlmi_attr_group = { 1122 .is_visible = attr_is_visible, 1123 .attrs = tlmi_attrs, 1124 }; 1125 1126 static void tlmi_attr_setting_release(struct kobject *kobj) 1127 { 1128 struct tlmi_attr_setting *setting = to_tlmi_attr_setting(kobj); 1129 1130 kfree(setting->possible_values); 1131 kfree(setting); 1132 } 1133 1134 static void tlmi_pwd_setting_release(struct kobject *kobj) 1135 { 1136 struct tlmi_pwd_setting *setting = to_tlmi_pwd_setting(kobj); 1137 1138 kfree(setting); 1139 } 1140 1141 static const struct kobj_type tlmi_attr_setting_ktype = { 1142 .release = &tlmi_attr_setting_release, 1143 .sysfs_ops = &kobj_sysfs_ops, 1144 }; 1145 1146 static const struct kobj_type tlmi_pwd_setting_ktype = { 1147 .release = &tlmi_pwd_setting_release, 1148 .sysfs_ops = &kobj_sysfs_ops, 1149 }; 1150 1151 static ssize_t pending_reboot_show(struct kobject *kobj, struct kobj_attribute *attr, 1152 char *buf) 1153 { 1154 return sprintf(buf, "%d\n", tlmi_priv.pending_changes); 1155 } 1156 1157 static struct kobj_attribute pending_reboot = __ATTR_RO(pending_reboot); 1158 1159 static const char * const save_mode_strings[] = { 1160 [TLMI_SAVE_SINGLE] = "single", 1161 [TLMI_SAVE_BULK] = "bulk", 1162 [TLMI_SAVE_SAVE] = "save" 1163 }; 1164 1165 static ssize_t save_settings_show(struct kobject *kobj, struct kobj_attribute *attr, 1166 char *buf) 1167 { 1168 /* Check that setting is valid */ 1169 if (WARN_ON(tlmi_priv.save_mode < TLMI_SAVE_SINGLE || 1170 tlmi_priv.save_mode > TLMI_SAVE_BULK)) 1171 return -EIO; 1172 return sysfs_emit(buf, "%s\n", save_mode_strings[tlmi_priv.save_mode]); 1173 } 1174 1175 static ssize_t save_settings_store(struct kobject *kobj, struct kobj_attribute *attr, 1176 const char *buf, size_t count) 1177 { 1178 char *auth_str = NULL; 1179 int ret = 0; 1180 int cmd; 1181 1182 cmd = sysfs_match_string(save_mode_strings, buf); 1183 if (cmd < 0) 1184 return cmd; 1185 1186 /* Use lock in case multiple WMI operations needed */ 1187 mutex_lock(&tlmi_mutex); 1188 1189 switch (cmd) { 1190 case TLMI_SAVE_SINGLE: 1191 case TLMI_SAVE_BULK: 1192 tlmi_priv.save_mode = cmd; 1193 goto out; 1194 case TLMI_SAVE_SAVE: 1195 /* Check if supported*/ 1196 if (!tlmi_priv.can_set_bios_settings || 1197 tlmi_priv.save_mode == TLMI_SAVE_SINGLE) { 1198 ret = -EOPNOTSUPP; 1199 goto out; 1200 } 1201 /* Check there is actually something to save */ 1202 if (!tlmi_priv.save_required) { 1203 ret = -ENOENT; 1204 goto out; 1205 } 1206 /* Check if certificate authentication is enabled and active */ 1207 if (tlmi_priv.certificate_support && tlmi_priv.pwd_admin->cert_installed) { 1208 if (!tlmi_priv.pwd_admin->signature || 1209 !tlmi_priv.pwd_admin->save_signature) { 1210 ret = -EINVAL; 1211 goto out; 1212 } 1213 ret = tlmi_simple_call(LENOVO_SAVE_BIOS_SETTING_CERT_GUID, 1214 tlmi_priv.pwd_admin->save_signature); 1215 if (ret) 1216 goto out; 1217 } else if (tlmi_priv.opcode_support) { 1218 if (tlmi_priv.pwd_admin->valid && tlmi_priv.pwd_admin->password[0]) { 1219 ret = tlmi_opcode_setting("WmiOpcodePasswordAdmin", 1220 tlmi_priv.pwd_admin->password); 1221 if (ret) 1222 goto out; 1223 } 1224 ret = tlmi_save_bios_settings(""); 1225 } else { /* old non-opcode based authentication method (deprecated) */ 1226 if (tlmi_priv.pwd_admin->valid && tlmi_priv.pwd_admin->password[0]) { 1227 auth_str = kasprintf(GFP_KERNEL, "%s,%s,%s;", 1228 tlmi_priv.pwd_admin->password, 1229 encoding_options[tlmi_priv.pwd_admin->encoding], 1230 tlmi_priv.pwd_admin->kbdlang); 1231 if (!auth_str) { 1232 ret = -ENOMEM; 1233 goto out; 1234 } 1235 } 1236 1237 if (auth_str) 1238 ret = tlmi_save_bios_settings(auth_str); 1239 else 1240 ret = tlmi_save_bios_settings(""); 1241 } 1242 tlmi_priv.save_required = false; 1243 tlmi_priv.reboot_required = true; 1244 1245 if (!ret && !tlmi_priv.pending_changes) { 1246 tlmi_priv.pending_changes = true; 1247 /* let userland know it may need to check reboot pending again */ 1248 kobject_uevent(&tlmi_priv.class_dev->kobj, KOBJ_CHANGE); 1249 } 1250 break; 1251 } 1252 out: 1253 mutex_unlock(&tlmi_mutex); 1254 kfree(auth_str); 1255 return ret ?: count; 1256 } 1257 1258 static struct kobj_attribute save_settings = __ATTR_RW(save_settings); 1259 1260 /* ---- Debug interface--------------------------------------------------------- */ 1261 static ssize_t debug_cmd_store(struct kobject *kobj, struct kobj_attribute *attr, 1262 const char *buf, size_t count) 1263 { 1264 char *set_str = NULL, *new_setting = NULL; 1265 char *auth_str = NULL; 1266 int ret; 1267 1268 if (!tlmi_priv.can_debug_cmd) 1269 return -EOPNOTSUPP; 1270 1271 /* Strip out CR if one is present */ 1272 new_setting = kstrdup_and_replace(buf, '\n', '\0', GFP_KERNEL); 1273 if (!new_setting) 1274 return -ENOMEM; 1275 1276 if (tlmi_priv.pwd_admin->valid && tlmi_priv.pwd_admin->password[0]) { 1277 auth_str = kasprintf(GFP_KERNEL, "%s,%s,%s;", 1278 tlmi_priv.pwd_admin->password, 1279 encoding_options[tlmi_priv.pwd_admin->encoding], 1280 tlmi_priv.pwd_admin->kbdlang); 1281 if (!auth_str) { 1282 ret = -ENOMEM; 1283 goto out; 1284 } 1285 } 1286 1287 if (auth_str) 1288 set_str = kasprintf(GFP_KERNEL, "%s,%s", new_setting, auth_str); 1289 else 1290 set_str = kasprintf(GFP_KERNEL, "%s;", new_setting); 1291 if (!set_str) { 1292 ret = -ENOMEM; 1293 goto out; 1294 } 1295 1296 ret = tlmi_simple_call(LENOVO_DEBUG_CMD_GUID, set_str); 1297 if (ret) 1298 goto out; 1299 1300 if (!ret && !tlmi_priv.pending_changes) { 1301 tlmi_priv.pending_changes = true; 1302 /* let userland know it may need to check reboot pending again */ 1303 kobject_uevent(&tlmi_priv.class_dev->kobj, KOBJ_CHANGE); 1304 } 1305 out: 1306 kfree(auth_str); 1307 kfree(set_str); 1308 kfree(new_setting); 1309 return ret ?: count; 1310 } 1311 1312 static struct kobj_attribute debug_cmd = __ATTR_WO(debug_cmd); 1313 1314 /* ---- Initialisation --------------------------------------------------------- */ 1315 static void tlmi_release_attr(void) 1316 { 1317 int i; 1318 1319 /* Attribute structures */ 1320 for (i = 0; i < TLMI_SETTINGS_COUNT; i++) { 1321 if (tlmi_priv.setting[i]) { 1322 sysfs_remove_group(&tlmi_priv.setting[i]->kobj, &tlmi_attr_group); 1323 kobject_put(&tlmi_priv.setting[i]->kobj); 1324 } 1325 } 1326 sysfs_remove_file(&tlmi_priv.attribute_kset->kobj, &pending_reboot.attr); 1327 sysfs_remove_file(&tlmi_priv.attribute_kset->kobj, &save_settings.attr); 1328 1329 if (tlmi_priv.can_debug_cmd && debug_support) 1330 sysfs_remove_file(&tlmi_priv.attribute_kset->kobj, &debug_cmd.attr); 1331 1332 kset_unregister(tlmi_priv.attribute_kset); 1333 1334 /* Free up any saved signatures */ 1335 kfree(tlmi_priv.pwd_admin->signature); 1336 kfree(tlmi_priv.pwd_admin->save_signature); 1337 1338 /* Authentication structures */ 1339 sysfs_remove_group(&tlmi_priv.pwd_admin->kobj, &auth_attr_group); 1340 kobject_put(&tlmi_priv.pwd_admin->kobj); 1341 sysfs_remove_group(&tlmi_priv.pwd_power->kobj, &auth_attr_group); 1342 kobject_put(&tlmi_priv.pwd_power->kobj); 1343 1344 if (tlmi_priv.opcode_support) { 1345 sysfs_remove_group(&tlmi_priv.pwd_system->kobj, &auth_attr_group); 1346 kobject_put(&tlmi_priv.pwd_system->kobj); 1347 sysfs_remove_group(&tlmi_priv.pwd_hdd->kobj, &auth_attr_group); 1348 kobject_put(&tlmi_priv.pwd_hdd->kobj); 1349 sysfs_remove_group(&tlmi_priv.pwd_nvme->kobj, &auth_attr_group); 1350 kobject_put(&tlmi_priv.pwd_nvme->kobj); 1351 } 1352 1353 kset_unregister(tlmi_priv.authentication_kset); 1354 } 1355 1356 static int tlmi_validate_setting_name(struct kset *attribute_kset, char *name) 1357 { 1358 struct kobject *duplicate; 1359 1360 if (!strcmp(name, "Reserved")) 1361 return -EINVAL; 1362 1363 duplicate = kset_find_obj(attribute_kset, name); 1364 if (duplicate) { 1365 pr_debug("Duplicate attribute name found - %s\n", name); 1366 /* kset_find_obj() returns a reference */ 1367 kobject_put(duplicate); 1368 return -EBUSY; 1369 } 1370 1371 return 0; 1372 } 1373 1374 static int tlmi_sysfs_init(void) 1375 { 1376 int i, ret; 1377 1378 ret = fw_attributes_class_get(&fw_attr_class); 1379 if (ret) 1380 return ret; 1381 1382 tlmi_priv.class_dev = device_create(fw_attr_class, NULL, MKDEV(0, 0), 1383 NULL, "%s", "thinklmi"); 1384 if (IS_ERR(tlmi_priv.class_dev)) { 1385 ret = PTR_ERR(tlmi_priv.class_dev); 1386 goto fail_class_created; 1387 } 1388 1389 tlmi_priv.attribute_kset = kset_create_and_add("attributes", NULL, 1390 &tlmi_priv.class_dev->kobj); 1391 if (!tlmi_priv.attribute_kset) { 1392 ret = -ENOMEM; 1393 goto fail_device_created; 1394 } 1395 1396 for (i = 0; i < TLMI_SETTINGS_COUNT; i++) { 1397 /* Check if index is a valid setting - skip if it isn't */ 1398 if (!tlmi_priv.setting[i]) 1399 continue; 1400 1401 /* check for duplicate or reserved values */ 1402 if (tlmi_validate_setting_name(tlmi_priv.attribute_kset, 1403 tlmi_priv.setting[i]->display_name) < 0) { 1404 kfree(tlmi_priv.setting[i]->possible_values); 1405 kfree(tlmi_priv.setting[i]); 1406 tlmi_priv.setting[i] = NULL; 1407 continue; 1408 } 1409 1410 /* Build attribute */ 1411 tlmi_priv.setting[i]->kobj.kset = tlmi_priv.attribute_kset; 1412 ret = kobject_add(&tlmi_priv.setting[i]->kobj, NULL, 1413 "%s", tlmi_priv.setting[i]->display_name); 1414 if (ret) 1415 goto fail_create_attr; 1416 1417 ret = sysfs_create_group(&tlmi_priv.setting[i]->kobj, &tlmi_attr_group); 1418 if (ret) 1419 goto fail_create_attr; 1420 } 1421 1422 ret = sysfs_create_file(&tlmi_priv.attribute_kset->kobj, &pending_reboot.attr); 1423 if (ret) 1424 goto fail_create_attr; 1425 1426 ret = sysfs_create_file(&tlmi_priv.attribute_kset->kobj, &save_settings.attr); 1427 if (ret) 1428 goto fail_create_attr; 1429 1430 if (tlmi_priv.can_debug_cmd && debug_support) { 1431 ret = sysfs_create_file(&tlmi_priv.attribute_kset->kobj, &debug_cmd.attr); 1432 if (ret) 1433 goto fail_create_attr; 1434 } 1435 1436 /* Create authentication entries */ 1437 tlmi_priv.authentication_kset = kset_create_and_add("authentication", NULL, 1438 &tlmi_priv.class_dev->kobj); 1439 if (!tlmi_priv.authentication_kset) { 1440 ret = -ENOMEM; 1441 goto fail_create_attr; 1442 } 1443 tlmi_priv.pwd_admin->kobj.kset = tlmi_priv.authentication_kset; 1444 ret = kobject_add(&tlmi_priv.pwd_admin->kobj, NULL, "%s", "Admin"); 1445 if (ret) 1446 goto fail_create_attr; 1447 1448 ret = sysfs_create_group(&tlmi_priv.pwd_admin->kobj, &auth_attr_group); 1449 if (ret) 1450 goto fail_create_attr; 1451 1452 tlmi_priv.pwd_power->kobj.kset = tlmi_priv.authentication_kset; 1453 ret = kobject_add(&tlmi_priv.pwd_power->kobj, NULL, "%s", "Power-on"); 1454 if (ret) 1455 goto fail_create_attr; 1456 1457 ret = sysfs_create_group(&tlmi_priv.pwd_power->kobj, &auth_attr_group); 1458 if (ret) 1459 goto fail_create_attr; 1460 1461 if (tlmi_priv.opcode_support) { 1462 tlmi_priv.pwd_system->kobj.kset = tlmi_priv.authentication_kset; 1463 ret = kobject_add(&tlmi_priv.pwd_system->kobj, NULL, "%s", "System"); 1464 if (ret) 1465 goto fail_create_attr; 1466 1467 ret = sysfs_create_group(&tlmi_priv.pwd_system->kobj, &auth_attr_group); 1468 if (ret) 1469 goto fail_create_attr; 1470 1471 tlmi_priv.pwd_hdd->kobj.kset = tlmi_priv.authentication_kset; 1472 ret = kobject_add(&tlmi_priv.pwd_hdd->kobj, NULL, "%s", "HDD"); 1473 if (ret) 1474 goto fail_create_attr; 1475 1476 ret = sysfs_create_group(&tlmi_priv.pwd_hdd->kobj, &auth_attr_group); 1477 if (ret) 1478 goto fail_create_attr; 1479 1480 tlmi_priv.pwd_nvme->kobj.kset = tlmi_priv.authentication_kset; 1481 ret = kobject_add(&tlmi_priv.pwd_nvme->kobj, NULL, "%s", "NVMe"); 1482 if (ret) 1483 goto fail_create_attr; 1484 1485 ret = sysfs_create_group(&tlmi_priv.pwd_nvme->kobj, &auth_attr_group); 1486 if (ret) 1487 goto fail_create_attr; 1488 } 1489 1490 return ret; 1491 1492 fail_create_attr: 1493 tlmi_release_attr(); 1494 fail_device_created: 1495 device_destroy(fw_attr_class, MKDEV(0, 0)); 1496 fail_class_created: 1497 fw_attributes_class_put(); 1498 return ret; 1499 } 1500 1501 /* ---- Base Driver -------------------------------------------------------- */ 1502 static struct tlmi_pwd_setting *tlmi_create_auth(const char *pwd_type, 1503 const char *pwd_role) 1504 { 1505 struct tlmi_pwd_setting *new_pwd; 1506 1507 new_pwd = kzalloc(sizeof(struct tlmi_pwd_setting), GFP_KERNEL); 1508 if (!new_pwd) 1509 return NULL; 1510 1511 strscpy(new_pwd->kbdlang, "us", TLMI_LANG_MAXLEN); 1512 new_pwd->encoding = TLMI_ENCODING_ASCII; 1513 new_pwd->pwd_type = pwd_type; 1514 new_pwd->role = pwd_role; 1515 new_pwd->minlen = tlmi_priv.pwdcfg.core.min_length; 1516 new_pwd->maxlen = tlmi_priv.pwdcfg.core.max_length; 1517 new_pwd->index = 0; 1518 1519 kobject_init(&new_pwd->kobj, &tlmi_pwd_setting_ktype); 1520 1521 return new_pwd; 1522 } 1523 1524 static int tlmi_analyze(void) 1525 { 1526 int i, ret; 1527 1528 if (wmi_has_guid(LENOVO_SET_BIOS_SETTINGS_GUID) && 1529 wmi_has_guid(LENOVO_SAVE_BIOS_SETTINGS_GUID)) 1530 tlmi_priv.can_set_bios_settings = true; 1531 1532 if (wmi_has_guid(LENOVO_GET_BIOS_SELECTIONS_GUID)) 1533 tlmi_priv.can_get_bios_selections = true; 1534 1535 if (wmi_has_guid(LENOVO_SET_BIOS_PASSWORD_GUID)) 1536 tlmi_priv.can_set_bios_password = true; 1537 1538 if (wmi_has_guid(LENOVO_BIOS_PASSWORD_SETTINGS_GUID)) 1539 tlmi_priv.can_get_password_settings = true; 1540 1541 if (wmi_has_guid(LENOVO_DEBUG_CMD_GUID)) 1542 tlmi_priv.can_debug_cmd = true; 1543 1544 if (wmi_has_guid(LENOVO_OPCODE_IF_GUID)) 1545 tlmi_priv.opcode_support = true; 1546 1547 if (wmi_has_guid(LENOVO_SET_BIOS_CERT_GUID) && 1548 wmi_has_guid(LENOVO_SET_BIOS_SETTING_CERT_GUID) && 1549 wmi_has_guid(LENOVO_SAVE_BIOS_SETTING_CERT_GUID)) 1550 tlmi_priv.certificate_support = true; 1551 1552 /* 1553 * Try to find the number of valid settings of this machine 1554 * and use it to create sysfs attributes. 1555 */ 1556 for (i = 0; i < TLMI_SETTINGS_COUNT; ++i) { 1557 struct tlmi_attr_setting *setting; 1558 char *item = NULL; 1559 1560 tlmi_priv.setting[i] = NULL; 1561 ret = tlmi_setting(i, &item, LENOVO_BIOS_SETTING_GUID); 1562 if (ret) 1563 break; 1564 if (!item) 1565 break; 1566 if (!*item) { 1567 kfree(item); 1568 continue; 1569 } 1570 1571 /* It is not allowed to have '/' for file name. Convert it into '\'. */ 1572 strreplace(item, '/', '\\'); 1573 1574 /* Remove the value part */ 1575 strreplace(item, ',', '\0'); 1576 1577 /* Create a setting entry */ 1578 setting = kzalloc(sizeof(*setting), GFP_KERNEL); 1579 if (!setting) { 1580 ret = -ENOMEM; 1581 kfree(item); 1582 goto fail_clear_attr; 1583 } 1584 setting->index = i; 1585 strscpy(setting->display_name, item, TLMI_SETTINGS_MAXLEN); 1586 /* If BIOS selections supported, load those */ 1587 if (tlmi_priv.can_get_bios_selections) { 1588 ret = tlmi_get_bios_selections(setting->display_name, 1589 &setting->possible_values); 1590 if (ret || !setting->possible_values) 1591 pr_info("Error retrieving possible values for %d : %s\n", 1592 i, setting->display_name); 1593 } else { 1594 /* 1595 * Older Thinkstations don't support the bios_selections API. 1596 * Instead they store this as a [Optional:Option1,Option2] section of the 1597 * name string. 1598 * Try and pull that out if it's available. 1599 */ 1600 char *optitem, *optstart, *optend; 1601 1602 if (!tlmi_setting(setting->index, &optitem, LENOVO_BIOS_SETTING_GUID)) { 1603 optstart = strstr(optitem, "[Optional:"); 1604 if (optstart) { 1605 optstart += strlen("[Optional:"); 1606 optend = strstr(optstart, "]"); 1607 if (optend) 1608 setting->possible_values = 1609 kstrndup(optstart, optend - optstart, 1610 GFP_KERNEL); 1611 } 1612 kfree(optitem); 1613 } 1614 } 1615 /* 1616 * firmware-attributes requires that possible_values are separated by ';' but 1617 * Lenovo FW uses ','. Replace appropriately. 1618 */ 1619 if (setting->possible_values) 1620 strreplace(setting->possible_values, ',', ';'); 1621 1622 kobject_init(&setting->kobj, &tlmi_attr_setting_ktype); 1623 tlmi_priv.setting[i] = setting; 1624 kfree(item); 1625 } 1626 1627 /* Create password setting structure */ 1628 ret = tlmi_get_pwd_settings(&tlmi_priv.pwdcfg); 1629 if (ret) 1630 goto fail_clear_attr; 1631 1632 /* All failures below boil down to kmalloc failures */ 1633 ret = -ENOMEM; 1634 1635 tlmi_priv.pwd_admin = tlmi_create_auth("pap", "bios-admin"); 1636 if (!tlmi_priv.pwd_admin) 1637 goto fail_clear_attr; 1638 1639 if (tlmi_priv.pwdcfg.core.password_state & TLMI_PAP_PWD) 1640 tlmi_priv.pwd_admin->valid = true; 1641 1642 tlmi_priv.pwd_power = tlmi_create_auth("pop", "power-on"); 1643 if (!tlmi_priv.pwd_power) 1644 goto fail_clear_attr; 1645 1646 if (tlmi_priv.pwdcfg.core.password_state & TLMI_POP_PWD) 1647 tlmi_priv.pwd_power->valid = true; 1648 1649 if (tlmi_priv.opcode_support) { 1650 tlmi_priv.pwd_system = tlmi_create_auth("smp", "system"); 1651 if (!tlmi_priv.pwd_system) 1652 goto fail_clear_attr; 1653 1654 if (tlmi_priv.pwdcfg.core.password_state & TLMI_SMP_PWD) 1655 tlmi_priv.pwd_system->valid = true; 1656 1657 tlmi_priv.pwd_hdd = tlmi_create_auth("hdd", "hdd"); 1658 if (!tlmi_priv.pwd_hdd) 1659 goto fail_clear_attr; 1660 1661 tlmi_priv.pwd_nvme = tlmi_create_auth("nvm", "nvme"); 1662 if (!tlmi_priv.pwd_nvme) 1663 goto fail_clear_attr; 1664 1665 /* Set default hdd/nvme index to 1 as there is no device 0 */ 1666 tlmi_priv.pwd_hdd->index = 1; 1667 tlmi_priv.pwd_nvme->index = 1; 1668 1669 if (tlmi_priv.pwdcfg.core.password_state & TLMI_HDD_PWD) { 1670 /* Check if PWD is configured and set index to first drive found */ 1671 if (tlmi_priv.pwdcfg.ext.hdd_user_password || 1672 tlmi_priv.pwdcfg.ext.hdd_master_password) { 1673 tlmi_priv.pwd_hdd->valid = true; 1674 if (tlmi_priv.pwdcfg.ext.hdd_master_password) 1675 tlmi_priv.pwd_hdd->index = 1676 ffs(tlmi_priv.pwdcfg.ext.hdd_master_password) - 1; 1677 else 1678 tlmi_priv.pwd_hdd->index = 1679 ffs(tlmi_priv.pwdcfg.ext.hdd_user_password) - 1; 1680 } 1681 if (tlmi_priv.pwdcfg.ext.nvme_user_password || 1682 tlmi_priv.pwdcfg.ext.nvme_master_password) { 1683 tlmi_priv.pwd_nvme->valid = true; 1684 if (tlmi_priv.pwdcfg.ext.nvme_master_password) 1685 tlmi_priv.pwd_nvme->index = 1686 ffs(tlmi_priv.pwdcfg.ext.nvme_master_password) - 1; 1687 else 1688 tlmi_priv.pwd_nvme->index = 1689 ffs(tlmi_priv.pwdcfg.ext.nvme_user_password) - 1; 1690 } 1691 } 1692 } 1693 1694 if (tlmi_priv.certificate_support && 1695 (tlmi_priv.pwdcfg.core.password_state & TLMI_CERT)) 1696 tlmi_priv.pwd_admin->cert_installed = true; 1697 1698 return 0; 1699 1700 fail_clear_attr: 1701 for (i = 0; i < TLMI_SETTINGS_COUNT; ++i) { 1702 if (tlmi_priv.setting[i]) { 1703 kfree(tlmi_priv.setting[i]->possible_values); 1704 kfree(tlmi_priv.setting[i]); 1705 } 1706 } 1707 kfree(tlmi_priv.pwd_admin); 1708 kfree(tlmi_priv.pwd_power); 1709 kfree(tlmi_priv.pwd_system); 1710 kfree(tlmi_priv.pwd_hdd); 1711 kfree(tlmi_priv.pwd_nvme); 1712 return ret; 1713 } 1714 1715 static void tlmi_remove(struct wmi_device *wdev) 1716 { 1717 tlmi_release_attr(); 1718 device_destroy(fw_attr_class, MKDEV(0, 0)); 1719 fw_attributes_class_put(); 1720 } 1721 1722 static int tlmi_probe(struct wmi_device *wdev, const void *context) 1723 { 1724 int ret; 1725 1726 ret = tlmi_analyze(); 1727 if (ret) 1728 return ret; 1729 1730 return tlmi_sysfs_init(); 1731 } 1732 1733 static const struct wmi_device_id tlmi_id_table[] = { 1734 { .guid_string = LENOVO_BIOS_SETTING_GUID }, 1735 { } 1736 }; 1737 MODULE_DEVICE_TABLE(wmi, tlmi_id_table); 1738 1739 static struct wmi_driver tlmi_driver = { 1740 .driver = { 1741 .name = "think-lmi", 1742 }, 1743 .id_table = tlmi_id_table, 1744 .probe = tlmi_probe, 1745 .remove = tlmi_remove, 1746 }; 1747 1748 MODULE_AUTHOR("Sugumaran L <slacshiminar@lenovo.com>"); 1749 MODULE_AUTHOR("Mark Pearson <markpearson@lenovo.com>"); 1750 MODULE_AUTHOR("Corentin Chary <corentin.chary@gmail.com>"); 1751 MODULE_DESCRIPTION("ThinkLMI Driver"); 1752 MODULE_LICENSE("GPL"); 1753 1754 module_wmi_driver(tlmi_driver); 1755