| OLD | NEW |
| 1 /* Copyright (c) 2011 The Chromium OS Authors. All rights reserved. | 1 /* Copyright (c) 2011 The Chromium OS Authors. All rights reserved. |
| 2 * Use of this source code is governed by a BSD-style license that can be | 2 * Use of this source code is governed by a BSD-style license that can be |
| 3 * found in the LICENSE file. | 3 * found in the LICENSE file. |
| 4 */ | 4 */ |
| 5 | 5 |
| 6 #include <stdio.h> | 6 #include <stdio.h> |
| 7 #include <string.h> | 7 #include <string.h> |
| 8 #include <sys/types.h> | 8 #include <sys/types.h> |
| 9 #include <sys/stat.h> | 9 #include <sys/stat.h> |
| 10 #include <unistd.h> | 10 #include <unistd.h> |
| (...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 87 | 87 |
| 88 /* A structure to contain buffer data retrieved from the ACPI. */ | 88 /* A structure to contain buffer data retrieved from the ACPI. */ |
| 89 typedef struct { | 89 typedef struct { |
| 90 int buffer_size; | 90 int buffer_size; |
| 91 uint8_t* buffer; | 91 uint8_t* buffer; |
| 92 } AcpiBuffer; | 92 } AcpiBuffer; |
| 93 | 93 |
| 94 | 94 |
| 95 /* Fields that GetVdatString() can get */ | 95 /* Fields that GetVdatString() can get */ |
| 96 typedef enum VdatStringField { | 96 typedef enum VdatStringField { |
| 97 VDAT_STRING_TIMERS = 0, /* Timer values */ | 97 VDAT_STRING_TIMERS = 0, /* Timer values */ |
| 98 VDAT_STRING_LOAD_FIRMWARE_DEBUG /* LoadFirmware() debug information */ | 98 VDAT_STRING_LOAD_FIRMWARE_DEBUG, /* LoadFirmware() debug information */ |
| 99 VDAT_STRING_LOAD_KERNEL_DEBUG /* LoadKernel() debug information */ |
| 99 } VdatStringField; | 100 } VdatStringField; |
| 100 | 101 |
| 101 | 102 |
| 102 /* Fields that GetVdatInt() can get */ | 103 /* Fields that GetVdatInt() can get */ |
| 103 typedef enum VdatIntField { | 104 typedef enum VdatIntField { |
| 104 VDAT_INT_FLAGS = 0, /* Flags */ | 105 VDAT_INT_FLAGS = 0, /* Flags */ |
| 105 VDAT_INT_FW_VERSION_TPM, /* Current firmware version in TPM */ | 106 VDAT_INT_FW_VERSION_TPM, /* Current firmware version in TPM */ |
| 106 VDAT_INT_KERNEL_VERSION_TPM, /* Current kernel version in TPM */ | 107 VDAT_INT_KERNEL_VERSION_TPM, /* Current kernel version in TPM */ |
| 107 VDAT_INT_TRIED_FIRMWARE_B, /* Tried firmware B due to fwb_tries */ | 108 VDAT_INT_TRIED_FIRMWARE_B, /* Tried firmware B due to fwb_tries */ |
| 108 VDAT_INT_KERNEL_KEY_VERIFIED /* Kernel key verified using | 109 VDAT_INT_KERNEL_KEY_VERIFIED /* Kernel key verified using |
| (...skipping 502 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 611 /* Normal new firmware or older Chrome OS firmware allows debug if the | 612 /* Normal new firmware or older Chrome OS firmware allows debug if the |
| 612 * dev switch is on. */ | 613 * dev switch is on. */ |
| 613 if (1 == ReadFileBit(ACPI_CHSW_PATH, CHSW_DEV_BOOT)) | 614 if (1 == ReadFileBit(ACPI_CHSW_PATH, CHSW_DEV_BOOT)) |
| 614 return 1; | 615 return 1; |
| 615 | 616 |
| 616 /* All other cases disallow debug. */ | 617 /* All other cases disallow debug. */ |
| 617 return 0; | 618 return 0; |
| 618 } | 619 } |
| 619 | 620 |
| 620 | 621 |
| 622 char* GetVdatLoadFirmwareDebug(char* dest, int size, |
| 623 const VbSharedDataHeader* sh) { |
| 624 snprintf(dest, size, |
| 625 "Check A result=%d\n" |
| 626 "Check B result=%d\n" |
| 627 "Firmware index booted=0x%02x\n" |
| 628 "TPM combined version at start=0x%08x\n" |
| 629 "Lowest combined version from firmware=0x%08x\n", |
| 630 sh->check_fw_a_result, |
| 631 sh->check_fw_b_result, |
| 632 sh->firmware_index, |
| 633 sh->fw_version_tpm_start, |
| 634 sh->fw_version_lowest); |
| 635 return dest; |
| 636 } |
| 637 |
| 638 |
| 639 #define TRUNCATED "\n(truncated)\n" |
| 640 |
| 641 char* GetVdatLoadKernelDebug(char* dest, int size, |
| 642 const VbSharedDataHeader* sh) { |
| 643 int used = 0; |
| 644 int first_call_tracked = 0; |
| 645 int call; |
| 646 |
| 647 /* Make sure we have space for truncation warning */ |
| 648 if (size < strlen(TRUNCATED) + 1) |
| 649 return NULL; |
| 650 size -= strlen(TRUNCATED) + 1; |
| 651 |
| 652 used += snprintf( |
| 653 dest + used, size - used, |
| 654 "Calls to LoadKernel()=%d\n", |
| 655 sh->lk_call_count); |
| 656 if (used > size) |
| 657 goto LoadKernelDebugExit; |
| 658 |
| 659 /* Report on the last calls */ |
| 660 if (sh->lk_call_count > VBSD_MAX_KERNEL_CALLS) |
| 661 first_call_tracked = sh->lk_call_count - VBSD_MAX_KERNEL_CALLS; |
| 662 for (call = first_call_tracked; call < sh->lk_call_count; call++) { |
| 663 const VbSharedDataKernelCall* shc = |
| 664 sh->lk_calls + (call & (VBSD_MAX_KERNEL_CALLS - 1)); |
| 665 int first_part_tracked = 0; |
| 666 int part; |
| 667 |
| 668 used += snprintf( |
| 669 dest + used, size - used, |
| 670 "Call %d:\n" |
| 671 " Boot flags=0x%02x\n" |
| 672 " Boot mode=%d\n" |
| 673 " Test error=%d\n" |
| 674 " Return code=%d\n" |
| 675 " Debug flags=0x%02x\n" |
| 676 " Drive sectors=%" PRIu64 "\n" |
| 677 " Sector size=%d\n" |
| 678 " Check result=%d\n" |
| 679 " Kernel partitions found=%d\n", |
| 680 call + 1, |
| 681 shc->boot_flags, |
| 682 shc->boot_mode, |
| 683 shc->test_error_num, |
| 684 shc->return_code, |
| 685 shc->flags, |
| 686 shc->sector_count, |
| 687 shc->sector_size, |
| 688 shc->check_result, |
| 689 shc->kernel_parts_found); |
| 690 if (used > size) |
| 691 goto LoadKernelDebugExit; |
| 692 |
| 693 /* If we found too many partitions, only prints ones where the |
| 694 * structure has info. */ |
| 695 if (shc->kernel_parts_found > VBSD_MAX_KERNEL_PARTS) |
| 696 first_part_tracked = shc->kernel_parts_found - VBSD_MAX_KERNEL_PARTS; |
| 697 |
| 698 /* Report on the partitions checked */ |
| 699 for (part = first_part_tracked; part < shc->kernel_parts_found; part++) { |
| 700 const VbSharedDataKernelPart* shp = |
| 701 shc->parts + (part & (VBSD_MAX_KERNEL_PARTS - 1)); |
| 702 |
| 703 used += snprintf( |
| 704 dest + used, size - used, |
| 705 " Kernel %d:\n" |
| 706 " GPT index=%d\n" |
| 707 " Start sector=%" PRIu64 "\n" |
| 708 " Sector count=%" PRIu64 "\n" |
| 709 " Combined version=0x%08x\n" |
| 710 " Check result=%d\n" |
| 711 " Debug flags=0x%02x\n", |
| 712 part + 1, |
| 713 shp->gpt_index, |
| 714 shp->sector_start, |
| 715 shp->sector_count, |
| 716 shp->combined_version, |
| 717 shp->check_result, |
| 718 shp->flags); |
| 719 if (used > size) |
| 720 goto LoadKernelDebugExit; |
| 721 } |
| 722 } |
| 723 |
| 724 LoadKernelDebugExit: |
| 725 |
| 726 /* Warn if data was truncated; we left space for this above. */ |
| 727 if (used > size) |
| 728 strcat(dest, TRUNCATED); |
| 729 |
| 730 return dest; |
| 731 } |
| 732 |
| 733 |
| 621 char* GetVdatString(char* dest, int size, VdatStringField field) | 734 char* GetVdatString(char* dest, int size, VdatStringField field) |
| 622 { | 735 { |
| 623 VbSharedDataHeader* sh; | 736 VbSharedDataHeader* sh; |
| 624 AcpiBuffer* ab = VbGetBuffer(ACPI_VDAT_PATH); | 737 AcpiBuffer* ab = VbGetBuffer(ACPI_VDAT_PATH); |
| 738 char* value = dest; |
| 625 if (!ab) | 739 if (!ab) |
| 626 return NULL; | 740 return NULL; |
| 627 | 741 |
| 628 sh = (VbSharedDataHeader*)ab->buffer; | 742 sh = (VbSharedDataHeader*)ab->buffer; |
| 629 | 743 |
| 630 switch (field) { | 744 switch (field) { |
| 631 case VDAT_STRING_TIMERS: | 745 case VDAT_STRING_TIMERS: |
| 632 snprintf(dest, size, | 746 snprintf(dest, size, |
| 633 "LFS=%" PRIu64 ",%" PRIu64 | 747 "LFS=%" PRIu64 ",%" PRIu64 |
| 634 " LF=%" PRIu64 ",%" PRIu64 | 748 " LF=%" PRIu64 ",%" PRIu64 |
| 635 " LK=%" PRIu64 ",%" PRIu64, | 749 " LK=%" PRIu64 ",%" PRIu64, |
| 636 sh->timer_load_firmware_start_enter, | 750 sh->timer_load_firmware_start_enter, |
| 637 sh->timer_load_firmware_start_exit, | 751 sh->timer_load_firmware_start_exit, |
| 638 sh->timer_load_firmware_enter, | 752 sh->timer_load_firmware_enter, |
| 639 sh->timer_load_firmware_exit, | 753 sh->timer_load_firmware_exit, |
| 640 sh->timer_load_kernel_enter, | 754 sh->timer_load_kernel_enter, |
| 641 sh->timer_load_kernel_exit); | 755 sh->timer_load_kernel_exit); |
| 642 break; | 756 break; |
| 643 | 757 |
| 644 case VDAT_STRING_LOAD_FIRMWARE_DEBUG: | 758 case VDAT_STRING_LOAD_FIRMWARE_DEBUG: |
| 645 snprintf(dest, size, | 759 value = GetVdatLoadFirmwareDebug(dest, size, sh); |
| 646 "check=%d,%d index=0x%02x tpmver=0x%x lowestver=0x%x", | 760 break; |
| 647 sh->check_fw_a_result, | 761 |
| 648 sh->check_fw_b_result, | 762 case VDAT_STRING_LOAD_KERNEL_DEBUG: |
| 649 sh->firmware_index, | 763 value = GetVdatLoadKernelDebug(dest, size, sh); |
| 650 sh->fw_version_tpm_start, | |
| 651 sh->fw_version_lowest); | |
| 652 break; | 764 break; |
| 653 | 765 |
| 654 default: | 766 default: |
| 655 Free(ab); | 767 Free(ab); |
| 656 return NULL; | 768 return NULL; |
| 657 } | 769 } |
| 658 | 770 |
| 659 Free(ab); | 771 Free(ab); |
| 660 return dest; | 772 return value; |
| 661 } | 773 } |
| 662 | 774 |
| 663 | 775 |
| 664 int GetVdatInt(VdatIntField field) { | 776 int GetVdatInt(VdatIntField field) { |
| 665 VbSharedDataHeader* sh; | 777 VbSharedDataHeader* sh; |
| 666 AcpiBuffer* ab = VbGetBuffer(ACPI_VDAT_PATH); | 778 AcpiBuffer* ab = VbGetBuffer(ACPI_VDAT_PATH); |
| 667 int value = -1; | 779 int value = -1; |
| 668 | 780 |
| 669 if (!ab) | 781 if (!ab) |
| 670 return -1; | 782 return -1; |
| (...skipping 141 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 812 return "hash"; | 924 return "hash"; |
| 813 case 1: | 925 case 1: |
| 814 return "sig"; | 926 return "sig"; |
| 815 default: | 927 default: |
| 816 return NULL; | 928 return NULL; |
| 817 } | 929 } |
| 818 } else if (!strcasecmp(name, "vdat_timers")) { | 930 } else if (!strcasecmp(name, "vdat_timers")) { |
| 819 return GetVdatString(dest, size, VDAT_STRING_TIMERS); | 931 return GetVdatString(dest, size, VDAT_STRING_TIMERS); |
| 820 } else if (!strcasecmp(name, "vdat_lfdebug")) { | 932 } else if (!strcasecmp(name, "vdat_lfdebug")) { |
| 821 return GetVdatString(dest, size, VDAT_STRING_LOAD_FIRMWARE_DEBUG); | 933 return GetVdatString(dest, size, VDAT_STRING_LOAD_FIRMWARE_DEBUG); |
| 934 } else if (!strcasecmp(name, "vdat_lkdebug")) { |
| 935 return GetVdatString(dest, size, VDAT_STRING_LOAD_KERNEL_DEBUG); |
| 822 } else | 936 } else |
| 823 return NULL; | 937 return NULL; |
| 824 } | 938 } |
| 825 | 939 |
| 826 | 940 |
| 827 /* Set a system property integer. | 941 /* Set a system property integer. |
| 828 * | 942 * |
| 829 * Returns 0 if success, -1 if error. */ | 943 * Returns 0 if success, -1 if error. */ |
| 830 int VbSetSystemPropertyInt(const char* name, int value) { | 944 int VbSetSystemPropertyInt(const char* name, int value) { |
| 831 | 945 |
| (...skipping 29 matching lines...) Expand all Loading... |
| 861 | 975 |
| 862 | 976 |
| 863 /* Set a system property string. | 977 /* Set a system property string. |
| 864 * | 978 * |
| 865 * Returns 0 if success, -1 if error. */ | 979 * Returns 0 if success, -1 if error. */ |
| 866 int VbSetSystemPropertyString(const char* name, const char* value) { | 980 int VbSetSystemPropertyString(const char* name, const char* value) { |
| 867 | 981 |
| 868 /* TODO: support setting */ | 982 /* TODO: support setting */ |
| 869 return -1; | 983 return -1; |
| 870 } | 984 } |
| OLD | NEW |